diff options
author | Marcin Slusarz <marcin.slusarz@gmail.com> | 2011-09-25 16:01:19 +0200 |
---|---|---|
committer | Marcin Slusarz <marcin.slusarz@gmail.com> | 2011-09-25 19:18:45 +0200 |
commit | 65b8eea0644fdb7e9150d0e98c06d7f8ba6d5302 (patch) | |
tree | ae9caf5b26b4e06bb99ad31828081b73690a0f77 | |
parent | a4d72189b271664501338cc93107845f3d40ae54 (diff) |
nouveau: fix crash during fence emission
Fence emission can flush the push buffer, which through flush_notify
unreferences recently emitted fence. If ref count is increased after
fence emission, unreference deletes the fence, which causes SIGSEGV.
Backtrace:
nouveau_fence_del
nouveau_fence_ref
nouveau_fence_next
nouveau_pushbuf_flush
MARK_RING
nv50_screen_fence_emit
nouveau_fence_emit
nv50_flush
This bug manifested as an assertion failure in nouveau_fence.c, because
SIGSEGV handler tried to shutdown the application and used messed up
fence.
This issue was reported by Maxim Levitsky.
Note: This is a candidate for the 7.11 branch.
-rw-r--r-- | src/gallium/drivers/nouveau/nouveau_fence.c | 4 |
1 files changed, 2 insertions, 2 deletions
diff --git a/src/gallium/drivers/nouveau/nouveau_fence.c b/src/gallium/drivers/nouveau/nouveau_fence.c index ea2038cc7e2..26e4775b12d 100644 --- a/src/gallium/drivers/nouveau/nouveau_fence.c +++ b/src/gallium/drivers/nouveau/nouveau_fence.c @@ -93,8 +93,6 @@ nouveau_fence_emit(struct nouveau_fence *fence) /* set this now, so that if fence.emit triggers a flush we don't recurse */ fence->state = NOUVEAU_FENCE_STATE_EMITTED; - screen->fence.emit(&screen->base, fence->sequence); - ++fence->ref; if (screen->fence.tail) @@ -103,6 +101,8 @@ nouveau_fence_emit(struct nouveau_fence *fence) screen->fence.head = fence; screen->fence.tail = fence; + + screen->fence.emit(&screen->base, fence->sequence); } void |