drm/armada: move mode set vblank handling and disable/enable
authorRussell King <rmk+kernel@armlinux.org.uk>
Mon, 30 Jul 2018 10:52:34 +0000 (11:52 +0100)
committerRussell King <rmk+kernel@armlinux.org.uk>
Mon, 30 Jul 2018 10:52:34 +0000 (11:52 +0100)
Move the mode set vblank handling and controller enable/disable to the
prepare() and commit() callbacks.  This will be needed when we move to
mode_set_nofb() as we should not enable the controller without the
plane coordinates and location having been properly updated.

Signed-off-by: Russell King <rmk+kernel@armlinux.org.uk>
drivers/gpu/drm/armada/armada_crtc.c
drivers/gpu/drm/armada/armada_crtc.h

index 205d5dc7ba81d70929b896a43e476c9c5ea08cfb..683b2cec3d5548e27d97e27ba36fb6587f602694 100644 (file)
@@ -399,6 +399,7 @@ static void armada_drm_crtc_prepare(struct drm_crtc *crtc)
 {
        struct armada_crtc *dcrtc = drm_to_armada_crtc(crtc);
        struct drm_plane *plane;
+       u32 val;
 
        /*
         * If we have an overlay plane associated with this CRTC, disable
@@ -411,6 +412,18 @@ static void armada_drm_crtc_prepare(struct drm_crtc *crtc)
                WARN_ON(!armada_drm_plane_work_wait(drm_to_armada_plane(plane),
                                                    HZ));
        }
+
+       /* Wait for pending flips to complete */
+       armada_drm_plane_work_wait(drm_to_armada_plane(dcrtc->crtc.primary),
+                                  MAX_SCHEDULE_TIMEOUT);
+
+       drm_crtc_vblank_off(crtc);
+
+       val = dcrtc->dumb_ctrl & ~CFG_DUMB_ENA;
+       if (val != dcrtc->dumb_ctrl) {
+               dcrtc->dumb_ctrl = val;
+               writel_relaxed(val, dcrtc->base + LCD_SPU_DUMB_CTRL);
+       }
 }
 
 /* The mode_config.mutex will be held for this call */
@@ -418,10 +431,12 @@ static void armada_drm_crtc_commit(struct drm_crtc *crtc)
 {
        struct armada_crtc *dcrtc = drm_to_armada_crtc(crtc);
 
-       if (dcrtc->dpms != DRM_MODE_DPMS_ON) {
-               dcrtc->dpms = DRM_MODE_DPMS_ON;
-               armada_drm_crtc_update(dcrtc);
-       }
+       dcrtc->dpms = DRM_MODE_DPMS_ON;
+       armada_drm_crtc_update(dcrtc);
+       drm_crtc_vblank_on(crtc);
+
+       if (dcrtc->old_modeset_fb)
+               armada_drm_crtc_finish_fb(dcrtc, dcrtc->old_modeset_fb, false);
 }
 
 /* The mode_config.mutex will be held for this call */
@@ -623,6 +638,7 @@ static int armada_drm_crtc_mode_set(struct drm_crtc *crtc,
        bool interlaced;
 
        drm_framebuffer_get(crtc->primary->fb);
+       dcrtc->old_modeset_fb = old_fb;
 
        interlaced = !!(adj->flags & DRM_MODE_FLAG_INTERLACE);
 
@@ -656,18 +672,6 @@ static int armada_drm_crtc_mode_set(struct drm_crtc *crtc,
                adj->crtc_vsync_end,
                adj->crtc_vtotal, tm, bm);
 
-       /* Wait for pending flips to complete */
-       armada_drm_plane_work_wait(drm_to_armada_plane(dcrtc->crtc.primary),
-                                  MAX_SCHEDULE_TIMEOUT);
-
-       drm_crtc_vblank_off(crtc);
-
-       val = dcrtc->dumb_ctrl & ~CFG_DUMB_ENA;
-       if (val != dcrtc->dumb_ctrl) {
-               dcrtc->dumb_ctrl = val;
-               writel_relaxed(val, dcrtc->base + LCD_SPU_DUMB_CTRL);
-       }
-
        /*
         * If we are blanked, we would have disabled the clock.  Re-enable
         * it so that compute_clock() does the right thing.
@@ -739,11 +743,6 @@ static int armada_drm_crtc_mode_set(struct drm_crtc *crtc,
        armada_drm_primary_set(crtc, crtc->primary, x, y);
        spin_unlock_irqrestore(&dcrtc->irq_lock, flags);
 
-       armada_drm_crtc_update(dcrtc);
-
-       drm_crtc_vblank_on(crtc);
-       armada_drm_crtc_finish_fb(dcrtc, old_fb, dpms_blanked(dcrtc->dpms));
-
        return 0;
 }
 
index 445829b8877af4b328c2fb8d1402a69700612c7b..8edcfd1fa75f0f7d6431b169771f8b9b9af952d8 100644 (file)
@@ -93,6 +93,7 @@ struct armada_crtc {
        uint8_t                 csc_rgb_mode;
 
        struct drm_plane        *plane;
+       struct drm_framebuffer  *old_modeset_fb;
 
        struct armada_gem_object        *cursor_obj;
        int                     cursor_x;