drm: mxsfb: Move vblank event arm to CRTC .atomic_flush()
authorLaurent Pinchart <laurent.pinchart@ideasonboard.com>
Mon, 27 Jul 2020 02:06:44 +0000 (05:06 +0300)
committerStefan Agner <stefan@agner.ch>
Tue, 28 Jul 2020 15:21:16 +0000 (17:21 +0200)
The vblank event is armed in the plane .atomic_update(). This works fine
as we have a single plane, and was the only option when the driver was
using the drm_simple_kms_helper helper, but will break as soon as
multiple planes are supported. Move it to CRTC .atomic_flush().

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Reviewed-by: Stefan Agner <stefan@agner.ch>
Reviewed-by: Emil Velikov <emil.l.velikov@gmail.com>
Signed-off-by: Stefan Agner <stefan@agner.ch>
Link: https://patchwork.freedesktop.org/patch/msgid/20200727020654.8231-13-laurent.pinchart@ideasonboard.com
drivers/gpu/drm/mxsfb/mxsfb_kms.c

index 2346ad56daea9689d5849f0f14b636912a48a16c..770546e67a8dc1c73318dbd14c780035411fa43b 100644 (file)
@@ -295,6 +295,25 @@ static int mxsfb_crtc_atomic_check(struct drm_crtc *crtc,
        return drm_atomic_add_affected_planes(state->state, crtc);
 }
 
+static void mxsfb_crtc_atomic_flush(struct drm_crtc *crtc,
+                                   struct drm_crtc_state *old_state)
+{
+       struct drm_pending_vblank_event *event;
+
+       event = crtc->state->event;
+       crtc->state->event = NULL;
+
+       if (!event)
+               return;
+
+       spin_lock_irq(&crtc->dev->event_lock);
+       if (drm_crtc_vblank_get(crtc) == 0)
+               drm_crtc_arm_vblank_event(crtc, event);
+       else
+               drm_crtc_send_vblank_event(crtc, event);
+       spin_unlock_irq(&crtc->dev->event_lock);
+}
+
 static void mxsfb_crtc_atomic_enable(struct drm_crtc *crtc,
                                     struct drm_crtc_state *old_state)
 {
@@ -364,6 +383,7 @@ static void mxsfb_crtc_disable_vblank(struct drm_crtc *crtc)
 
 static const struct drm_crtc_helper_funcs mxsfb_crtc_helper_funcs = {
        .atomic_check = mxsfb_crtc_atomic_check,
+       .atomic_flush = mxsfb_crtc_atomic_flush,
        .atomic_enable = mxsfb_crtc_atomic_enable,
        .atomic_disable = mxsfb_crtc_atomic_disable,
 };
@@ -410,23 +430,8 @@ static void mxsfb_plane_atomic_update(struct drm_plane *plane,
                                      struct drm_plane_state *old_pstate)
 {
        struct mxsfb_drm_private *mxsfb = to_mxsfb_drm_private(plane->dev);
-       struct drm_crtc *crtc = &mxsfb->crtc;
-       struct drm_pending_vblank_event *event;
        dma_addr_t paddr;
 
-       spin_lock_irq(&crtc->dev->event_lock);
-       event = crtc->state->event;
-       if (event) {
-               crtc->state->event = NULL;
-
-               if (drm_crtc_vblank_get(crtc) == 0) {
-                       drm_crtc_arm_vblank_event(crtc, event);
-               } else {
-                       drm_crtc_send_vblank_event(crtc, event);
-               }
-       }
-       spin_unlock_irq(&crtc->dev->event_lock);
-
        paddr = mxsfb_get_fb_paddr(mxsfb);
        if (paddr) {
                mxsfb_enable_axi_clk(mxsfb);