Mesa (master): gallium/radeon: always flush asynchronously and wait after begin_new_cs

Marek Olšák mareko at kemper.freedesktop.org
Sun Apr 16 23:30:59 UTC 2017


Module: Mesa
Branch: master
Commit: 2769dadb0fafdbafc98630fdf96924a3bb209ab7
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=2769dadb0fafdbafc98630fdf96924a3bb209ab7

Author: Marek Olšák <marek.olsak at amd.com>
Date:   Thu Apr 13 23:46:59 2017 +0200

gallium/radeon: always flush asynchronously and wait after begin_new_cs

This hides the overhead of everything in the driver after the CS flush and
before returning from pipe_context::flush.
Only microbenchmarks will benefit.

+2% FPS for glxgears.

Reviewed-by: Nicolai Hähnle <nicolai.haehnle at amd.com>

---

 src/gallium/drivers/radeon/r600_pipe_common.c | 12 ++++++++----
 src/gallium/drivers/radeonsi/si_hw_context.c  |  3 +++
 2 files changed, 11 insertions(+), 4 deletions(-)

diff --git a/src/gallium/drivers/radeon/r600_pipe_common.c b/src/gallium/drivers/radeon/r600_pipe_common.c
index 47d4058e60..ce84139a2f 100644
--- a/src/gallium/drivers/radeon/r600_pipe_common.c
+++ b/src/gallium/drivers/radeon/r600_pipe_common.c
@@ -366,15 +366,13 @@ static void r600_flush_from_st(struct pipe_context *ctx,
 	struct pipe_screen *screen = ctx->screen;
 	struct r600_common_context *rctx = (struct r600_common_context *)ctx;
 	struct radeon_winsys *ws = rctx->ws;
-	unsigned rflags = 0;
 	struct pipe_fence_handle *gfx_fence = NULL;
 	struct pipe_fence_handle *sdma_fence = NULL;
 	bool deferred_fence = false;
+	unsigned rflags = RADEON_FLUSH_ASYNC;
 
 	if (flags & PIPE_FLUSH_END_OF_FRAME)
 		rflags |= RADEON_FLUSH_END_OF_FRAME;
-	if (flags & PIPE_FLUSH_DEFERRED)
-		rflags |= RADEON_FLUSH_ASYNC;
 
 	/* DMA IBs are preambles to gfx IBs, therefore must be flushed first. */
 	if (rctx->dma.cs)
@@ -383,7 +381,7 @@ static void r600_flush_from_st(struct pipe_context *ctx,
 	if (!radeon_emitted(rctx->gfx.cs, rctx->initial_gfx_cs_size)) {
 		if (fence)
 			ws->fence_reference(&gfx_fence, rctx->last_gfx_fence);
-		if (!(rflags & RADEON_FLUSH_ASYNC))
+		if (!(flags & PIPE_FLUSH_DEFERRED))
 			ws->cs_sync_flush(rctx->gfx.cs);
 	} else {
 		/* Instead of flushing, create a deferred fence. Constraints:
@@ -419,6 +417,12 @@ static void r600_flush_from_st(struct pipe_context *ctx,
 		screen->fence_reference(screen, fence, NULL);
 		*fence = (struct pipe_fence_handle*)multi_fence;
 	}
+
+	if (!(flags & PIPE_FLUSH_DEFERRED)) {
+		if (rctx->dma.cs)
+			ws->cs_sync_flush(rctx->dma.cs);
+		ws->cs_sync_flush(rctx->gfx.cs);
+	}
 }
 
 static void r600_flush_dma_ring(void *ctx, unsigned flags,
diff --git a/src/gallium/drivers/radeonsi/si_hw_context.c b/src/gallium/drivers/radeonsi/si_hw_context.c
index e51abfc5c5..e15f6a9cc6 100644
--- a/src/gallium/drivers/radeonsi/si_hw_context.c
+++ b/src/gallium/drivers/radeonsi/si_hw_context.c
@@ -108,6 +108,9 @@ void si_context_gfx_flush(void *context, unsigned flags,
 	if (r600_check_device_reset(&ctx->b))
 		return;
 
+	if (ctx->screen->b.debug_flags & DBG_CHECK_VM)
+		flags &= ~RADEON_FLUSH_ASYNC;
+
 	/* If the state tracker is flushing the GFX IB, r600_flush_from_st is
 	 * responsible for flushing the DMA IB and merging the fences from both.
 	 * This code is only needed when the driver flushes the GFX IB




More information about the mesa-commit mailing list