summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2014-04-18 09:28:02 +0100
committerChris Wilson <chris@chris-wilson.co.uk>2014-04-19 07:55:18 +0100
commit58a757b64927d8e27c4ac38cc15f8291037ec905 (patch)
tree553dcd31ab1dcbf37822994427b96c8142ac9bba
parentfb0ed43cbc6f34bde670ab846e7ba9e7dbf9b660 (diff)
sna: Do not reuse physical cursors for the kernel is broken, harder
commit 154f7e9668bffdf565b6914a3a3e5bdfe17aa1b9 Author: Chris Wilson <chris@chris-wilson.co.uk> Date: Fri Apr 18 09:28:02 2014 +0100 sna: Do not reuse physical cursors for the kernel is broken was insufficient as it ended up reusing a stale cursor that was still attached, and so after updating the cursor the second pipe found itself with a valid cursor. Hey presto, we had a shared physical cursor, once again demonstrating the buggy kernel. This time, disable all cursor reuse except for the once currently attached to the pipe - this should prevent all sharing. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=77351 Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
-rw-r--r--src/sna/sna_display.c43
1 files changed, 24 insertions, 19 deletions
diff --git a/src/sna/sna_display.c b/src/sna/sna_display.c
index a356e7fa..ab5b5298 100644
--- a/src/sna/sna_display.c
+++ b/src/sna/sna_display.c
@@ -3170,34 +3170,39 @@ static struct sna_cursor *__sna_get_cursor(struct sna *sna, xf86CrtcPtr crtc)
sna->cursor.ref->bits->argb!=NULL));
rotation = crtc->transform_in_use ? crtc->rotation : RR_Rotate_0;
- for (cursor = sna->cursor.cursors; cursor; cursor = cursor->next) {
- if (cursor->serial == sna->cursor.serial && cursor->rotation == rotation && cursor->image) {
- __DBG(("%s: reusing handle=%d, serial=%d, rotation=%d, size=%d\n",
- __FUNCTION__, cursor->handle, cursor->serial, cursor->rotation, cursor->size));
- assert(cursor->size == sna->cursor.size);
- return cursor;
- }
- }
-
size = sna->cursor.size;
- for (cursor = sna->cursor.cursors; cursor; cursor = cursor->next) {
- if (cursor->alloc >= 4*size*size && cursor->rotation == rotation) {
- __DBG(("%s: stealing handle=%d, serial=%d, rotation=%d, alloc=%d\n",
- __FUNCTION__, cursor->handle, cursor->serial, cursor->rotation, cursor->alloc));
- assert(cursor->serial != sna->cursor.serial);
- break;
+ if (cursor && cursor->alloc < 4*size*size)
+ cursor = NULL;
+
+ if (sna->kgem.gen >= 033) { /* Don't allow phys cursor sharing */
+ for (cursor = sna->cursor.cursors; cursor; cursor = cursor->next) {
+ if (cursor->serial == sna->cursor.serial && cursor->rotation == rotation) {
+ __DBG(("%s: reusing handle=%d, serial=%d, rotation=%d, size=%d\n",
+ __FUNCTION__, cursor->handle, cursor->serial, cursor->rotation, cursor->size));
+ assert(cursor->size == sna->cursor.size);
+ return cursor;
+ }
}
- }
- if (cursor == NULL) {
for (cursor = sna->cursor.cursors; cursor; cursor = cursor->next) {
- if (cursor->alloc >= 4*size*size && cursor->serial != sna->cursor.serial) {
+ if (cursor->alloc >= 4*size*size && cursor->rotation == rotation) {
__DBG(("%s: stealing handle=%d, serial=%d, rotation=%d, alloc=%d\n",
__FUNCTION__, cursor->handle, cursor->serial, cursor->rotation, cursor->alloc));
- assert(cursor->rotation != rotation);
+ assert(cursor->serial != sna->cursor.serial);
break;
}
}
+
+ if (cursor == NULL) {
+ for (cursor = sna->cursor.cursors; cursor; cursor = cursor->next) {
+ if (cursor->alloc >= 4*size*size && cursor->serial != sna->cursor.serial) {
+ __DBG(("%s: stealing handle=%d, serial=%d, rotation=%d, alloc=%d\n",
+ __FUNCTION__, cursor->handle, cursor->serial, cursor->rotation, cursor->alloc));
+ assert(cursor->rotation != rotation);
+ break;
+ }
+ }
+ }
}
if (cursor == NULL) {