From 8dfbc3403113bcc51f0350c3471fa1abf664305f Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 12 Aug 2010 12:07:32 +0100 Subject: [PATCH] drm/i915/overlay: Combine SWITCH_OFF into a single step We can program the h/w to first wait on the flip and then switch off without relying on s/w intervention. This removes the need for a double step switch off, bringing much rejoicing. Signed-off-by: Chris Wilson Reviewed-by: Daniel Vetter --- drivers/gpu/drm/i915/intel_drv.h | 3 +-- drivers/gpu/drm/i915/intel_overlay.c | 38 ++++------------------------ 2 files changed, 6 insertions(+), 35 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index f757fbd7a8de..01ca494c6d87 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -167,8 +167,7 @@ struct intel_overlay { #define HW_WEDGED 1 #define NEEDS_WAIT_FOR_FLIP 2 #define RELEASE_OLD_VID 3 -#define SWITCH_OFF_STAGE_1 4 -#define SWITCH_OFF_STAGE_2 5 +#define SWITCH_OFF 4 }; struct intel_crtc { diff --git a/drivers/gpu/drm/i915/intel_overlay.c b/drivers/gpu/drm/i915/intel_overlay.c index 88c2d1f8d05c..d0f901e4665f 100644 --- a/drivers/gpu/drm/i915/intel_overlay.c +++ b/drivers/gpu/drm/i915/intel_overlay.c @@ -325,7 +325,6 @@ static int intel_overlay_off(struct intel_overlay *overlay) { u32 flip_addr = overlay->flip_addr; struct drm_device *dev = overlay->dev; - int ret; BUG_ON(!overlay->active); @@ -335,29 +334,18 @@ static int intel_overlay_off(struct intel_overlay *overlay) * of the hw. Do it in both cases */ flip_addr |= OFC_UPDATE; + BEGIN_LP_RING(6); /* wait for overlay to go idle */ - BEGIN_LP_RING(4); OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_CONTINUE); OUT_RING(flip_addr); OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP); - OUT_RING(MI_NOOP); - ADVANCE_LP_RING(); - - ret = intel_overlay_do_wait_request(overlay, true, - SWITCH_OFF_STAGE_1); - if (ret) - return ret; - /* turn overlay off */ - BEGIN_LP_RING(4); OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_OFF); OUT_RING(flip_addr); OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP); - OUT_RING(MI_NOOP); ADVANCE_LP_RING(); - return intel_overlay_do_wait_request(overlay, true, - SWITCH_OFF_STAGE_2); + return intel_overlay_do_wait_request(overlay, true, SWITCH_OFF); } static void intel_overlay_off_tail(struct intel_overlay *overlay) @@ -383,9 +371,8 @@ int intel_overlay_recover_from_interrupt(struct intel_overlay *overlay, bool interruptible) { struct drm_device *dev = overlay->dev; - struct drm_gem_object *obj; drm_i915_private_t *dev_priv = dev->dev_private; - u32 flip_addr; + struct drm_gem_object *obj; int ret; if (overlay->hw_wedged == HW_WEDGED) @@ -404,25 +391,10 @@ int intel_overlay_recover_from_interrupt(struct intel_overlay *overlay, overlay->old_vid_bo = NULL; break; - case SWITCH_OFF_STAGE_1: - flip_addr = overlay->flip_addr; - flip_addr |= OFC_UPDATE; - - BEGIN_LP_RING(4); - OUT_RING(MI_OVERLAY_FLIP | MI_OVERLAY_OFF); - OUT_RING(flip_addr); - OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_OVERLAY_FLIP); - OUT_RING(MI_NOOP); - ADVANCE_LP_RING(); - - ret = intel_overlay_do_wait_request(overlay, interruptible, - SWITCH_OFF_STAGE_2); - if (ret) - return ret; - - case SWITCH_OFF_STAGE_2: + case SWITCH_OFF: intel_overlay_off_tail(overlay); break; + default: BUG_ON(overlay->hw_wedged != NEEDS_WAIT_FOR_FLIP); } -- GitLab