From be68782d9aebf6f6575bb8cc9cfc66b7bad79644 Mon Sep 17 00:00:00 2001 From: Ben Skeggs Date: Tue, 1 Mar 2011 13:09:41 +1000 Subject: [PATCH] nv50: sync textures with render targets ourselves Port of the nvc0 commit doing the same. Signed-off-by: Ben Skeggs --- src/gallium/drivers/nouveau/nouveau_buffer.c | 6 +++--- src/gallium/drivers/nouveau/nouveau_buffer.h | 5 +++-- src/gallium/drivers/nv50/nv50_3d.xml.h | 2 +- src/gallium/drivers/nv50/nv50_screen.h | 5 +++++ src/gallium/drivers/nv50/nv50_state_validate.c | 16 ++++++++++++++++ src/gallium/drivers/nv50/nv50_tex.c | 8 ++++++++ src/gallium/drivers/nv50/nv50_winsys.h | 2 +- 7 files changed, 37 insertions(+), 7 deletions(-) diff --git a/src/gallium/drivers/nouveau/nouveau_buffer.c b/src/gallium/drivers/nouveau/nouveau_buffer.c index 4f4b24fdd21..efb16824e46 100644 --- a/src/gallium/drivers/nouveau/nouveau_buffer.c +++ b/src/gallium/drivers/nouveau/nouveau_buffer.c @@ -112,7 +112,7 @@ nouveau_buffer_download(struct pipe_context *pipe, struct nv04_resource *buf, memcpy(buf->data + start, bounce->map, size); nouveau_bo_unmap(bounce); - buf->status &= ~NOUVEAU_BUFFER_STATUS_DIRTY; + buf->status &= ~NOUVEAU_BUFFER_STATUS_GPU_WRITING; nouveau_bo_ref(NULL, &bounce); if (mm) @@ -152,7 +152,7 @@ nouveau_buffer_upload(struct pipe_context *pipe, struct nv04_resource *buf, release_allocation(&mm, screen->fence.current); if (start == 0 && size == buf->base.width0) - buf->status &= ~NOUVEAU_BUFFER_STATUS_DIRTY; + buf->status &= ~NOUVEAU_BUFFER_STATUS_GPU_WRITING; return TRUE; } @@ -174,7 +174,7 @@ nouveau_buffer_transfer_get(struct pipe_context *pipe, if (buf->domain == NOUVEAU_BO_VRAM) { if (usage & PIPE_TRANSFER_READ) { - if (buf->status & NOUVEAU_BUFFER_STATUS_DIRTY) + if (buf->status & NOUVEAU_BUFFER_STATUS_GPU_WRITING) nouveau_buffer_download(pipe, buf, 0, buf->base.width0); } } diff --git a/src/gallium/drivers/nouveau/nouveau_buffer.h b/src/gallium/drivers/nouveau/nouveau_buffer.h index d75bc4e0c38..c3e0c2cf924 100644 --- a/src/gallium/drivers/nouveau/nouveau_buffer.h +++ b/src/gallium/drivers/nouveau/nouveau_buffer.h @@ -17,7 +17,8 @@ struct nouveau_bo; * USER_MEMORY: resource->data is a pointer to client memory and may change * between GL calls */ -#define NOUVEAU_BUFFER_STATUS_DIRTY (1 << 0) +#define NOUVEAU_BUFFER_STATUS_GPU_READING (1 << 0) +#define NOUVEAU_BUFFER_STATUS_GPU_WRITING (1 << 1) #define NOUVEAU_BUFFER_STATUS_USER_MEMORY (1 << 7) /* Resources, if mapped into the GPU's address space, are guaranteed to @@ -84,7 +85,7 @@ nouveau_resource_map_offset(struct pipe_context *pipe, nouveau_buffer_adjust_score(pipe, res, -250); if ((res->domain == NOUVEAU_BO_VRAM) && - (res->status & NOUVEAU_BUFFER_STATUS_DIRTY)) + (res->status & NOUVEAU_BUFFER_STATUS_GPU_WRITING)) nouveau_buffer_download(pipe, res, 0, res->base.width0); if ((res->domain != NOUVEAU_BO_GART) || diff --git a/src/gallium/drivers/nv50/nv50_3d.xml.h b/src/gallium/drivers/nv50/nv50_3d.xml.h index eb05bd40951..9bb3211728c 100644 --- a/src/gallium/drivers/nv50/nv50_3d.xml.h +++ b/src/gallium/drivers/nv50/nv50_3d.xml.h @@ -74,7 +74,7 @@ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ - +#define NV50_3D_SERIALIZE 0x00000110 #define NV50_3D_DMA_NOTIFY 0x00000180 diff --git a/src/gallium/drivers/nv50/nv50_screen.h b/src/gallium/drivers/nv50/nv50_screen.h index eb9743a05d0..3886d8068cc 100644 --- a/src/gallium/drivers/nv50/nv50_screen.h +++ b/src/gallium/drivers/nv50/nv50_screen.h @@ -93,6 +93,11 @@ nv50_resource_validate(struct nv04_resource *res, uint32_t flags) if (likely(res->bo)) { nouveau_bo_validate(screen->base.channel, res->bo, flags); + if (flags & NOUVEAU_BO_WR) + res->status |= NOUVEAU_BUFFER_STATUS_GPU_WRITING; + if (flags & NOUVEAU_BO_RD) + res->status |= NOUVEAU_BUFFER_STATUS_GPU_READING; + nv50_resource_fence(res, flags); } } diff --git a/src/gallium/drivers/nv50/nv50_state_validate.c b/src/gallium/drivers/nv50/nv50_state_validate.c index a8f48b2a28e..c97927624e4 100644 --- a/src/gallium/drivers/nv50/nv50_state_validate.c +++ b/src/gallium/drivers/nv50/nv50_state_validate.c @@ -8,6 +8,7 @@ nv50_validate_fb(struct nv50_context *nv50) struct nouveau_channel *chan = nv50->screen->base.channel; struct pipe_framebuffer_state *fb = &nv50->framebuffer; unsigned i; + boolean serialize = FALSE; nv50_bufctx_reset(nv50, NV50_BUFCTX_FRAME); @@ -37,6 +38,11 @@ nv50_validate_fb(struct nv50_context *nv50) BEGIN_RING(chan, RING_3D(RT_ARRAY_MODE), 1); OUT_RING (chan, sf->depth); + if (mt->base.status & NOUVEAU_BUFFER_STATUS_GPU_READING) + serialize = TRUE; + mt->base.status |= NOUVEAU_BUFFER_STATUS_GPU_WRITING; + mt->base.status &= NOUVEAU_BUFFER_STATUS_GPU_READING; + nv50_bufctx_add_resident(nv50, NV50_BUFCTX_FRAME, &mt->base, NOUVEAU_BO_VRAM | NOUVEAU_BO_RDWR); } @@ -62,6 +68,11 @@ nv50_validate_fb(struct nv50_context *nv50) OUT_RING (chan, sf->height); OUT_RING (chan, (unk << 16) | sf->depth); + if (mt->base.status & NOUVEAU_BUFFER_STATUS_GPU_READING) + serialize = TRUE; + mt->base.status |= NOUVEAU_BUFFER_STATUS_GPU_WRITING; + mt->base.status &= NOUVEAU_BUFFER_STATUS_GPU_READING; + nv50_bufctx_add_resident(nv50, NV50_BUFCTX_FRAME, &mt->base, NOUVEAU_BO_VRAM | NOUVEAU_BO_RDWR); } else { @@ -72,6 +83,11 @@ nv50_validate_fb(struct nv50_context *nv50) BEGIN_RING(chan, RING_3D(VIEWPORT_HORIZ(0)), 2); OUT_RING (chan, fb->width << 16); OUT_RING (chan, fb->height << 16); + + if (serialize) { + BEGIN_RING(chan, RING_3D(SERIALIZE), 1); + OUT_RING (chan, 0); + } } static void diff --git a/src/gallium/drivers/nv50/nv50_tex.c b/src/gallium/drivers/nv50/nv50_tex.c index eaee0a1107f..a76139ad37e 100644 --- a/src/gallium/drivers/nv50/nv50_tex.c +++ b/src/gallium/drivers/nv50/nv50_tex.c @@ -212,9 +212,17 @@ nv50_validate_tic(struct nv50_context *nv50, int s) OUT_RINGp (chan, &tic->tic[3], 5); need_flush = TRUE; + } else + if (res->status & NOUVEAU_BUFFER_STATUS_GPU_WRITING) { + BEGIN_RING(chan, RING_3D(TEX_CACHE_CTL), 1); + OUT_RING (chan, 0x20); //(tic->id << 4) | 1); } + nv50->screen->tic.lock[tic->id / 32] |= 1 << (tic->id % 32); + res->status &= NOUVEAU_BUFFER_STATUS_GPU_WRITING; + res->status |= NOUVEAU_BUFFER_STATUS_GPU_READING; + nv50_bufctx_add_resident(nv50, NV50_BUFCTX_TEXTURES, res, NOUVEAU_BO_VRAM | NOUVEAU_BO_RD); diff --git a/src/gallium/drivers/nv50/nv50_winsys.h b/src/gallium/drivers/nv50/nv50_winsys.h index 35e79210a66..afa2a00c7a2 100644 --- a/src/gallium/drivers/nv50/nv50_winsys.h +++ b/src/gallium/drivers/nv50/nv50_winsys.h @@ -81,7 +81,7 @@ OUT_RESRCl(struct nouveau_channel *chan, struct nv04_resource *res, unsigned delta, unsigned flags) { if (flags & NOUVEAU_BO_WR) - res->status |= NOUVEAU_BUFFER_STATUS_DIRTY; + res->status |= NOUVEAU_BUFFER_STATUS_GPU_WRITING; return OUT_RELOCl(chan, res->bo, res->offset + delta, res->domain | flags); } -- 2.30.2