With drivers supporting runtime pm it's generally not a good idea to
touch the hardware when it's off. Add an option to the commit_planes
helper to support this case.

Note that the helpers already add all planes on a crtc when a modeset
happens, hence plane updates will not be lost if drivers set this to
true.

Cc: Thierry Reding <treding at nvidia.com>
Cc: Maarten Lankhorst <maarten.lankhorst at linux.intel.com>
Cc: Laurent Pinchart <laurent.pinchart+renesas at ideasonboard.com>
Signed-off-by: Daniel Vetter <daniel.vetter at intel.com>
---
 drivers/gpu/drm/drm_atomic_helper.c    | 15 +++++++++++++--
 drivers/gpu/drm/exynos/exynos_drm_fb.c |  2 +-
 drivers/gpu/drm/msm/msm_atomic.c       |  2 +-
 drivers/gpu/drm/omapdrm/omap_drv.c     |  2 +-
 drivers/gpu/drm/rcar-du/rcar_du_kms.c  |  2 +-
 drivers/gpu/drm/sti/sti_drm_drv.c      |  2 +-
 drivers/gpu/drm/tegra/drm.c            |  2 +-
 include/drm/drm_atomic_helper.h        |  3 ++-
 8 files changed, 21 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/drm_atomic_helper.c 
b/drivers/gpu/drm/drm_atomic_helper.c
index 91ad6bd13734..192412277586 100644
--- a/drivers/gpu/drm/drm_atomic_helper.c
+++ b/drivers/gpu/drm/drm_atomic_helper.c
@@ -989,7 +989,7 @@ int drm_atomic_helper_commit(struct drm_device *dev,

        drm_atomic_helper_commit_modeset_disables(dev, state);

-       drm_atomic_helper_commit_planes(dev, state);
+       drm_atomic_helper_commit_planes(dev, state, false);

        drm_atomic_helper_commit_modeset_enables(dev, state);

@@ -1108,6 +1108,7 @@ EXPORT_SYMBOL(drm_atomic_helper_prepare_planes);
  * drm_atomic_helper_commit_planes - commit plane state
  * @dev: DRM device
  * @old_state: atomic state object with old state structures
+ * @active_only: Only commit on active CRTC if set
  *
  * This function commits the new plane state using the plane and atomic helper
  * functions for planes and crtcs. It assumes that the atomic state has already
@@ -1122,7 +1123,8 @@ EXPORT_SYMBOL(drm_atomic_helper_prepare_planes);
  * drm_atomic_helper_commit_planes_on_crtc() instead.
  */
 void drm_atomic_helper_commit_planes(struct drm_device *dev,
-                                    struct drm_atomic_state *old_state)
+                                    struct drm_atomic_state *old_state,
+                                    bool active_only)
 {
        struct drm_crtc *crtc;
        struct drm_crtc_state *old_crtc_state;
@@ -1138,6 +1140,9 @@ void drm_atomic_helper_commit_planes(struct drm_device 
*dev,
                if (!funcs || !funcs->atomic_begin)
                        continue;

+               if (active_only && !crtc->state->active)
+                       continue;
+
                funcs->atomic_begin(crtc);
        }

@@ -1149,6 +1154,9 @@ void drm_atomic_helper_commit_planes(struct drm_device 
*dev,
                if (!funcs)
                        continue;

+               if (active_only && !plane->state->crtc->state->active)
+                       continue;
+
                /*
                 * Special-case disabling the plane if drivers support it.
                 */
@@ -1168,6 +1176,9 @@ void drm_atomic_helper_commit_planes(struct drm_device 
*dev,
                if (!funcs || !funcs->atomic_flush)
                        continue;

+               if (active_only && !crtc->state->active)
+                       continue;
+
                funcs->atomic_flush(crtc);
        }
 }
diff --git a/drivers/gpu/drm/exynos/exynos_drm_fb.c 
b/drivers/gpu/drm/exynos/exynos_drm_fb.c
index 2b6320e6eae2..7b383acbb5af 100644
--- a/drivers/gpu/drm/exynos/exynos_drm_fb.c
+++ b/drivers/gpu/drm/exynos/exynos_drm_fb.c
@@ -293,7 +293,7 @@ static int exynos_atomic_commit(struct drm_device *dev,
         * have the relevant clocks enabled to perform the update.
         */

-       drm_atomic_helper_commit_planes(dev, state);
+       drm_atomic_helper_commit_planes(dev, state, false);

        drm_atomic_helper_cleanup_planes(dev, state);

diff --git a/drivers/gpu/drm/msm/msm_atomic.c b/drivers/gpu/drm/msm/msm_atomic.c
index 1b22d8bfe142..0709b97251bf 100644
--- a/drivers/gpu/drm/msm/msm_atomic.c
+++ b/drivers/gpu/drm/msm/msm_atomic.c
@@ -125,7 +125,7 @@ static void complete_commit(struct msm_commit *c)

        drm_atomic_helper_commit_modeset_disables(dev, state);

-       drm_atomic_helper_commit_planes(dev, state);
+       drm_atomic_helper_commit_planes(dev, state, false);

        drm_atomic_helper_commit_modeset_enables(dev, state);

diff --git a/drivers/gpu/drm/omapdrm/omap_drv.c 
b/drivers/gpu/drm/omapdrm/omap_drv.c
index e888a831dd3c..0ecce79fc782 100644
--- a/drivers/gpu/drm/omapdrm/omap_drv.c
+++ b/drivers/gpu/drm/omapdrm/omap_drv.c
@@ -96,7 +96,7 @@ static void omap_atomic_complete(struct 
omap_atomic_state_commit *commit)
        dispc_runtime_get();

        drm_atomic_helper_commit_modeset_disables(dev, old_state);
-       drm_atomic_helper_commit_planes(dev, old_state);
+       drm_atomic_helper_commit_planes(dev, old_state, false);
        drm_atomic_helper_commit_modeset_enables(dev, old_state);

        omap_atomic_wait_for_completion(dev, old_state);
diff --git a/drivers/gpu/drm/rcar-du/rcar_du_kms.c 
b/drivers/gpu/drm/rcar-du/rcar_du_kms.c
index 56518eb1269a..ca12e8ca5552 100644
--- a/drivers/gpu/drm/rcar-du/rcar_du_kms.c
+++ b/drivers/gpu/drm/rcar-du/rcar_du_kms.c
@@ -456,7 +456,7 @@ static void rcar_du_atomic_complete(struct rcar_du_commit 
*commit)
        /* Apply the atomic update. */
        drm_atomic_helper_commit_modeset_disables(dev, old_state);
        drm_atomic_helper_commit_modeset_enables(dev, old_state);
-       drm_atomic_helper_commit_planes(dev, old_state);
+       drm_atomic_helper_commit_planes(dev, old_state, false);

        drm_atomic_helper_wait_for_vblanks(dev, old_state);

diff --git a/drivers/gpu/drm/sti/sti_drm_drv.c 
b/drivers/gpu/drm/sti/sti_drm_drv.c
index 59d558b400b3..123f1408d508 100644
--- a/drivers/gpu/drm/sti/sti_drm_drv.c
+++ b/drivers/gpu/drm/sti/sti_drm_drv.c
@@ -59,7 +59,7 @@ static void sti_drm_atomic_complete(struct sti_drm_private 
*private,
         */

        drm_atomic_helper_commit_modeset_disables(drm, state);
-       drm_atomic_helper_commit_planes(drm, state);
+       drm_atomic_helper_commit_planes(drm, state, false);
        drm_atomic_helper_commit_modeset_enables(drm, state);

        drm_atomic_helper_wait_for_vblanks(drm, state);
diff --git a/drivers/gpu/drm/tegra/drm.c b/drivers/gpu/drm/tegra/drm.c
index c6276aebfec3..783edc242648 100644
--- a/drivers/gpu/drm/tegra/drm.c
+++ b/drivers/gpu/drm/tegra/drm.c
@@ -56,7 +56,7 @@ static void tegra_atomic_complete(struct tegra_drm *tegra,
         */

        drm_atomic_helper_commit_modeset_disables(drm, state);
-       drm_atomic_helper_commit_planes(drm, state);
+       drm_atomic_helper_commit_planes(drm, state, false);
        drm_atomic_helper_commit_modeset_enables(drm, state);

        drm_atomic_helper_wait_for_vblanks(drm, state);
diff --git a/include/drm/drm_atomic_helper.h b/include/drm/drm_atomic_helper.h
index cc1fee8a12d0..c7b6aa54be37 100644
--- a/include/drm/drm_atomic_helper.h
+++ b/include/drm/drm_atomic_helper.h
@@ -55,7 +55,8 @@ void drm_atomic_helper_commit_modeset_enables(struct 
drm_device *dev,
 int drm_atomic_helper_prepare_planes(struct drm_device *dev,
                                     struct drm_atomic_state *state);
 void drm_atomic_helper_commit_planes(struct drm_device *dev,
-                                    struct drm_atomic_state *state);
+                                    struct drm_atomic_state *state,
+                                    bool active_only);
 void drm_atomic_helper_cleanup_planes(struct drm_device *dev,
                                      struct drm_atomic_state *old_state);
 void drm_atomic_helper_commit_planes_on_crtc(struct drm_crtc_state 
*old_crtc_state);
-- 
2.1.4

Reply via email to