aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/i915/intel_display.c
diff options
context:
space:
mode:
authorSimon Farnsworth <simon.farnsworth@onelan.co.uk>2010-09-01 17:47:52 +0100
committerChris Wilson <chris@chris-wilson.co.uk>2010-09-07 11:16:35 +0100
commit4e5359cd053bfb7d8dabe4a63624a5726848ffbc (patch)
treeea7b81407d31dc62fe495d5a5899c79ea692db33 /drivers/gpu/drm/i915/intel_display.c
parentdrm/i915: Tightly scope intel_encoder to prevent invalid use (diff)
downloadlinux-dev-4e5359cd053bfb7d8dabe4a63624a5726848ffbc.tar.xz
linux-dev-4e5359cd053bfb7d8dabe4a63624a5726848ffbc.zip
drm/i915: Avoid pageflipping freeze when we miss the flip prepare interrupt
When we miss the flip prepare interrupt, we never get into the software state needed to restart userspace, resulting in a freeze of a full-screen OpenGL application (such as a compositor). Work around this by checking DSPxSURF/DSPxBASE to see if the page flip has actually happened. If it has, do the work we would have done when the flip prepare interrupt comes in. Also, add debugfs information to tell us what's going on (based on the patch from Chris Wilson attached to bugs.fdo bug #29798). Signed-off-by: Simon Farnsworth <simon.farnsworth@onelan.co.uk> Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Diffstat (limited to '')
-rw-r--r--drivers/gpu/drm/i915/intel_display.c14
1 files changed, 4 insertions, 10 deletions
diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c
index 0b90443f1eb3..1bd0c672ec90 100644
--- a/drivers/gpu/drm/i915/intel_display.c
+++ b/drivers/gpu/drm/i915/intel_display.c
@@ -4864,15 +4864,6 @@ static void intel_crtc_destroy(struct drm_crtc *crtc)
kfree(intel_crtc);
}
-struct intel_unpin_work {
- struct work_struct work;
- struct drm_device *dev;
- struct drm_gem_object *old_fb_obj;
- struct drm_gem_object *pending_flip_obj;
- struct drm_pending_vblank_event *event;
- int pending;
-};
-
static void intel_unpin_work_fn(struct work_struct *__work)
{
struct intel_unpin_work *work =
@@ -4960,7 +4951,8 @@ void intel_prepare_page_flip(struct drm_device *dev, int plane)
spin_lock_irqsave(&dev->event_lock, flags);
if (intel_crtc->unpin_work) {
- intel_crtc->unpin_work->pending = 1;
+ if ((++intel_crtc->unpin_work->pending) > 1)
+ DRM_ERROR("Prepared flip multiple times\n");
} else {
DRM_DEBUG_DRIVER("preparing flip with no unpin work?\n");
}
@@ -5044,6 +5036,8 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
ADVANCE_LP_RING();
}
+ work->enable_stall_check = true;
+
/* Offset into the new buffer for cases of shared fbs between CRTCs */
offset = crtc->y * fb->pitch + crtc->x * fb->bits_per_pixel/8;