12a58d062e
N_02-nouveau-more-locking-make-sure-that-fence-work-is-always-done-with-the-push-mutex-acquired.patch N_03-nv30-locking-fixes.patch N_04-nv50-Fix-double-lock-in-nv50_hw_sm_get_query_result.patch N_05-Use-nv50_render_condition-in-nv50_blitctx_post_blit.patch Backport nouveau locking workaround to enable multithreading. Source: https://github.com/imirkin/mesa/commits/locking According to the author, crashes may still happen, but much more rarely. Tested on GK107. N_04-* and N_05-* include untested fixes for nv50. Fixes (boo#997171) as suggested in (fdo#91632). OBS-URL: https://build.opensuse.org/package/show/X11:XOrg/Mesa?expand=0&rev=540
121 lines
4.4 KiB
Diff
121 lines
4.4 KiB
Diff
From: Ilia Mirkin <imirkin@alum.mit.edu>
|
|
Date: Tue Jun 21 22:59:50 2016 -0400
|
|
Subject: [PATCH 3/5]nv30 locking fixes
|
|
Patch-mainline: N/A
|
|
References: boo#997171
|
|
Signed-off-by: Max Staudt <mstaudt@suse.de>
|
|
|
|
Cherry-picked from 940b3a773f264f3f52574160f0d06c48f8e8aeb2
|
|
at https://github.com/imirkin/mesa.git
|
|
|
|
Signed-off-by: Max Staudt <mstaudt@suse.de>
|
|
---
|
|
src/gallium/drivers/nouveau/nv30/nv30_draw.c | 20 ++++++++++++++++++--
|
|
src/gallium/drivers/nouveau/nv30/nv30_fragprog.c | 4 ++++
|
|
2 files changed, 22 insertions(+), 2 deletions(-)
|
|
|
|
diff --git a/src/gallium/drivers/nouveau/nv30/nv30_draw.c b/src/gallium/drivers/nouveau/nv30/nv30_draw.c
|
|
index 7b0d074..1c71534 100644
|
|
--- a/src/gallium/drivers/nouveau/nv30/nv30_draw.c
|
|
+++ b/src/gallium/drivers/nouveau/nv30/nv30_draw.c
|
|
@@ -127,6 +127,8 @@ nv30_render_draw_elements(struct vbuf_render *render,
|
|
struct nouveau_pushbuf *push = nv30->screen->base.pushbuf;
|
|
unsigned i;
|
|
|
|
+ pipe_mutex_lock(nv30->screen->base.push_mutex);
|
|
+
|
|
BEGIN_NV04(push, NV30_3D(VTXBUF(0)), r->vertex_info.num_attribs);
|
|
for (i = 0; i < r->vertex_info.num_attribs; i++) {
|
|
PUSH_RESRC(push, NV30_3D(VTXBUF(i)), BUFCTX_VTXTMP,
|
|
@@ -134,8 +136,10 @@ nv30_render_draw_elements(struct vbuf_render *render,
|
|
NOUVEAU_BO_LOW | NOUVEAU_BO_RD, 0, NV30_3D_VTXBUF_DMA1);
|
|
}
|
|
|
|
- if (!nv30_state_validate(nv30, ~0, false))
|
|
+ if (!nv30_state_validate(nv30, ~0, false)) {
|
|
+ pipe_mutex_unlock(nv30->screen->base.push_mutex);
|
|
return;
|
|
+ }
|
|
|
|
BEGIN_NV04(push, NV30_3D(VERTEX_BEGIN_END), 1);
|
|
PUSH_DATA (push, r->prim);
|
|
@@ -160,6 +164,8 @@ nv30_render_draw_elements(struct vbuf_render *render,
|
|
BEGIN_NV04(push, NV30_3D(VERTEX_BEGIN_END), 1);
|
|
PUSH_DATA (push, NV30_3D_VERTEX_BEGIN_END_STOP);
|
|
PUSH_RESET(push, BUFCTX_VTXTMP);
|
|
+
|
|
+ pipe_mutex_unlock(nv30->screen->base.push_mutex);
|
|
}
|
|
|
|
static void
|
|
@@ -172,6 +178,8 @@ nv30_render_draw_arrays(struct vbuf_render *render, unsigned start, uint nr)
|
|
unsigned ps = fn + (pn ? 1 : 0);
|
|
unsigned i;
|
|
|
|
+ pipe_mutex_lock(nv30->screen->base.push_mutex);
|
|
+
|
|
BEGIN_NV04(push, NV30_3D(VTXBUF(0)), r->vertex_info.num_attribs);
|
|
for (i = 0; i < r->vertex_info.num_attribs; i++) {
|
|
PUSH_RESRC(push, NV30_3D(VTXBUF(i)), BUFCTX_VTXTMP,
|
|
@@ -179,8 +187,10 @@ nv30_render_draw_arrays(struct vbuf_render *render, unsigned start, uint nr)
|
|
NOUVEAU_BO_LOW | NOUVEAU_BO_RD, 0, NV30_3D_VTXBUF_DMA1);
|
|
}
|
|
|
|
- if (!nv30_state_validate(nv30, ~0, false))
|
|
+ if (!nv30_state_validate(nv30, ~0, false)) {
|
|
+ pipe_mutex_unlock(nv30->screen->base.push_mutex);
|
|
return;
|
|
+ }
|
|
|
|
BEGIN_NV04(push, NV30_3D(VERTEX_BEGIN_END), 1);
|
|
PUSH_DATA (push, r->prim);
|
|
@@ -197,6 +207,8 @@ nv30_render_draw_arrays(struct vbuf_render *render, unsigned start, uint nr)
|
|
BEGIN_NV04(push, NV30_3D(VERTEX_BEGIN_END), 1);
|
|
PUSH_DATA (push, NV30_3D_VERTEX_BEGIN_END_STOP);
|
|
PUSH_RESET(push, BUFCTX_VTXTMP);
|
|
+
|
|
+ pipe_mutex_unlock(nv30->screen->base.push_mutex);
|
|
}
|
|
|
|
static void
|
|
@@ -383,6 +395,8 @@ nv30_render_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
|
|
|
|
nv30_render_validate(nv30);
|
|
|
|
+ pipe_mutex_unlock(nv30->screen->base.push_mutex);
|
|
+
|
|
if (nv30->draw_dirty & NV30_NEW_VIEWPORT)
|
|
draw_set_viewport_states(draw, 0, 1, &nv30->viewport);
|
|
if (nv30->draw_dirty & NV30_NEW_RASTERIZER)
|
|
@@ -448,6 +462,8 @@ nv30_render_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info)
|
|
if (transfer[i])
|
|
pipe_buffer_unmap(pipe, transfer[i]);
|
|
|
|
+ pipe_mutex_lock(nv30->screen->base.push_mutex);
|
|
+
|
|
nv30->draw_dirty = 0;
|
|
nv30_state_release(nv30);
|
|
}
|
|
diff --git a/src/gallium/drivers/nouveau/nv30/nv30_fragprog.c b/src/gallium/drivers/nouveau/nv30/nv30_fragprog.c
|
|
index 6de61bc..fd21f99 100644
|
|
--- a/src/gallium/drivers/nouveau/nv30/nv30_fragprog.c
|
|
+++ b/src/gallium/drivers/nouveau/nv30/nv30_fragprog.c
|
|
@@ -38,6 +38,8 @@ nv30_fragprog_upload(struct nv30_context *nv30)
|
|
struct nv30_fragprog *fp = nv30->fragprog.program;
|
|
struct pipe_context *pipe = &nv30->base.pipe;
|
|
|
|
+ pipe_mutex_unlock(nv->screen->push_mutex);
|
|
+
|
|
if (unlikely(!fp->buffer))
|
|
fp->buffer = pipe_buffer_create(pipe->screen, 0, 0, fp->insn_len * 4);
|
|
|
|
@@ -60,6 +62,8 @@ nv30_fragprog_upload(struct nv30_context *nv30)
|
|
|
|
if (nv04_resource(fp->buffer)->domain != NOUVEAU_BO_VRAM)
|
|
nouveau_buffer_migrate(nv, nv04_resource(fp->buffer), NOUVEAU_BO_VRAM);
|
|
+
|
|
+ pipe_mutex_lock(nv->screen->push_mutex);
|
|
}
|
|
|
|
void
|