blob: 071ec8d3de55e35347b350d8cb66f15fb20a7b8a [file] [log] [blame]
From 495a4951e724bc9aaa1f18b79546c1b2a208a7fc Mon Sep 17 00:00:00 2001
From: "Kristian H. Kristensen" <hoegsberg@chromium.org>
Date: Fri, 19 Jan 2018 17:06:40 -0800
Subject: [PATCH] CHROMIUM: drm/i915: Wait for vblank after disabling cursor
The cursor disable write is latched on vsync but if we do a modeset
before that happens the write seems to be discarded and the cursor
stays on. The CURCNTL register will still read back 0 as if the write
took, but underlying hardware didn't change. We don't disable the
cursor often, so we can just force the pre-GEN9 path for cursor
that waits for vblank.
BUG=b:138431568
TEST=Toggle primary/extended display as described in bug
Cherry-picked from chromeos-4.4
Conflicts:
Nathan: adapted this from chromeos-4.4 in chromeos-4.19 context:
drivers/gpu/drm/i915/intel_display.c
5.4 uprev - move to display/, update for context - jsbarnes
Change-Id: Ia9f8bddfe5c3b65ebe457dff1755547751ef0f47
Signed-off-by: Kristian H. Kristensen <hoegsberg@chromium.org>
Signed-off-by: Nathan Ciobanu <nathan.d.ciobanu@intel.com>
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/third_party/kernel/+/1721195
Tested-by: Sushma Venkatesh Reddy <sushma.venkatesh.reddy@intel.com>
Tested-by: Nelson Ye <nelson_ye@compal.corp-partner.google.com>
Tested-by: Lucien Kao <lucien_kao@compal.corp-partner.google.com>
Reviewed-by: Simon Glass <sjg@chromium.org>
Commit-Queue: Simon Glass <sjg@chromium.org>
---
drivers/gpu/drm/i915/display/intel_display.c | 25 ++++++--------------
1 file changed, 7 insertions(+), 18 deletions(-)
diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c
index 64e9107d70f7..bb820584d2ff 100644
--- a/drivers/gpu/drm/i915/display/intel_display.c
+++ b/drivers/gpu/drm/i915/display/intel_display.c
@@ -10404,25 +10404,14 @@ static int intel_atomic_commit(struct drm_device *dev,
* updates happen during the correct frames. Gen9+ have
* double buffered watermarks and so shouldn't need this.
*
- * Unset state->legacy_cursor_update before the call to
- * drm_atomic_helper_setup_commit() because otherwise
- * drm_atomic_helper_wait_for_flip_done() is a noop and
- * we get FIFO underruns because we didn't wait
- * for vblank.
- *
- * FIXME doing watermarks and fb cleanup from a vblank worker
- * (assuming we had any) would solve these problems.
+ * Unfortunately, the GEN9+ double buffering seems to be buggy when it
+ * races with a modeset. The result is that the register (CURCNTL)
+ * appears to have been written (reads back as 0), but the cursor is
+ * still on. This manifests itself as garbage in the upper-left corner
+ * of the display (as we set position and base to 0). We work around
+ * that by always falling back to the vblank wait.
*/
- if (DISPLAY_VER(dev_priv) < 9 && state->base.legacy_cursor_update) {
- struct intel_crtc_state *new_crtc_state;
- struct intel_crtc *crtc;
- int i;
-
- for_each_new_intel_crtc_in_state(state, crtc, new_crtc_state, i)
- if (new_crtc_state->wm.need_postvbl_update ||
- new_crtc_state->update_wm_post)
- state->base.legacy_cursor_update = false;
- }
+ state->base.legacy_cursor_update = false;
ret = intel_atomic_prepare_commit(state);
if (ret) {
--
2.17.1