Mesa (master): r600g: disable early cull optimization when occlusion query running

Jerome Glisse glisse at kemper.freedesktop.org
Sun Sep 26 16:11:28 UTC 2010


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

Author: Jerome Glisse <jglisse at redhat.com>
Date:   Sun Sep 26 12:06:46 2010 -0400

r600g: disable early cull optimization when occlusion query running

When occlusion query are running we want to have accurate
fragment count thus disable any early culling optimization
GPU has.

Based on work from Bas Nieuwenhuizen <bas at basnieuwenhuizen.nl>

Signed-off-by: Jerome Glisse <jglisse at redhat.com>

---

 src/gallium/drivers/r600/r600.h               |    1 +
 src/gallium/winsys/r600/drm/evergreen_state.c |   13 +++++++++++++
 src/gallium/winsys/r600/drm/r600_priv.h       |   21 +++++++++++++++++++++
 src/gallium/winsys/r600/drm/r600_state2.c     |   16 ++++++++++++++++
 src/gallium/winsys/r600/drm/r600d.h           |   10 ++++++++++
 5 files changed, 61 insertions(+), 0 deletions(-)

diff --git a/src/gallium/drivers/r600/r600.h b/src/gallium/drivers/r600/r600.h
index 65b029b..17d3440 100644
--- a/src/gallium/drivers/r600/r600.h
+++ b/src/gallium/drivers/r600/r600.h
@@ -246,6 +246,7 @@ struct r600_context {
 	struct radeon_bo	**bo;
 	u32			*pm4;
 	struct list_head	query_list;
+	unsigned		num_query_running;
 };
 
 struct r600_draw {
diff --git a/src/gallium/winsys/r600/drm/evergreen_state.c b/src/gallium/winsys/r600/drm/evergreen_state.c
index f203863..860c836 100644
--- a/src/gallium/winsys/r600/drm/evergreen_state.c
+++ b/src/gallium/winsys/r600/drm/evergreen_state.c
@@ -75,6 +75,7 @@ static const struct r600_reg evergreen_reg_list[] = {
 	{0, 0, R_009100_SPI_CONFIG_CNTL},
 	{0, 0, R_00913C_SPI_CONFIG_CNTL_1},
 	{0, 0, R_028000_DB_RENDER_CONTROL},
+	{0, 0, R_028004_DB_COUNT_CONTROL},
 	{0, 0, R_028008_DB_DEPTH_VIEW},
 	{0, 0, R_02800C_DB_RENDER_OVERRIDE},
 	{0, 0, R_028010_DB_RENDER_OVERRIDE2},
@@ -589,6 +590,18 @@ void evergreen_context_draw(struct r600_context *ctx, const struct r600_draw *dr
 		}
 	}
 
+	/* queries need some special values */
+	if (ctx->num_query_running) {
+		r600_context_reg(ctx, R600_GROUP_CONTEXT,
+				R_028004_DB_COUNT_CONTROL,
+				S_028004_PERFECT_ZPASS_COUNTS(1),
+				S_028004_PERFECT_ZPASS_COUNTS(1));
+		r600_context_reg(ctx, R600_GROUP_CONTEXT,
+				R_02800C_DB_RENDER_OVERRIDE,
+				S_02800C_NOOP_CULL_DISABLE(1),
+				S_02800C_NOOP_CULL_DISABLE(1));
+	}
+
 	if ((ctx->pm4_dirty_cdwords + ndwords + ctx->pm4_cdwords) > ctx->pm4_ndwords) {
 		/* need to flush */
 		r600_context_flush(ctx);
diff --git a/src/gallium/winsys/r600/drm/r600_priv.h b/src/gallium/winsys/r600/drm/r600_priv.h
index 92b2eb1..25a65c6 100644
--- a/src/gallium/winsys/r600/drm/r600_priv.h
+++ b/src/gallium/winsys/r600/drm/r600_priv.h
@@ -54,4 +54,25 @@ struct r600_reg {
 /* radeon_pciid.c */
 unsigned radeon_family_from_device(unsigned device);
 
+
+static void inline r600_context_reg(struct r600_context *ctx, unsigned group_id,
+					unsigned offset, unsigned value,
+					unsigned mask)
+{
+	struct r600_group *group = &ctx->groups[group_id];
+	struct r600_group_block *block;
+	unsigned id;
+
+	id = group->offset_block_id[(offset - group->start_offset) >> 2];
+	block = &group->blocks[id];
+	id = (offset - block->start_offset) >> 2;
+	block->pm4[id] &= ~mask;
+	block->pm4[id] |= value;
+	if (!(block->status & R600_BLOCK_STATUS_DIRTY)) {
+		ctx->pm4_dirty_cdwords += 2 + block->pm4_ndwords;
+	}
+	block->status |= R600_BLOCK_STATUS_ENABLED;
+	block->status |= R600_BLOCK_STATUS_DIRTY;
+}
+
 #endif
diff --git a/src/gallium/winsys/r600/drm/r600_state2.c b/src/gallium/winsys/r600/drm/r600_state2.c
index e1f32da..d60c37f 100644
--- a/src/gallium/winsys/r600/drm/r600_state2.c
+++ b/src/gallium/winsys/r600/drm/r600_state2.c
@@ -943,6 +943,20 @@ void r600_context_draw(struct r600_context *ctx, const struct r600_draw *draw)
 		}
 	}
 
+	/* queries need some special values */
+	if (ctx->num_query_running) {
+		if (ctx->radeon->family >= CHIP_RV770) {
+			r600_context_reg(ctx, R600_GROUP_CONTEXT,
+					R_028D0C_DB_RENDER_CONTROL,
+					S_028D0C_R700_PERFECT_ZPASS_COUNTS(1),
+					S_028D0C_R700_PERFECT_ZPASS_COUNTS(1));
+		}
+		r600_context_reg(ctx, R600_GROUP_CONTEXT,
+				R_028D10_DB_RENDER_OVERRIDE,
+				S_028D10_NOOP_CULL_DISABLE(1),
+				S_028D10_NOOP_CULL_DISABLE(1));
+	}
+
 	if ((ctx->pm4_dirty_cdwords + ndwords + ctx->pm4_cdwords) > ctx->pm4_ndwords) {
 		/* need to flush */
 		r600_context_flush(ctx);
@@ -1181,6 +1195,7 @@ void r600_query_begin(struct r600_context *ctx, struct r600_query *query)
 
 	query->state |= R600_QUERY_STATE_STARTED;
 	query->state ^= R600_QUERY_STATE_ENDED;
+	ctx->num_query_running++;
 }
 
 void r600_query_end(struct r600_context *ctx, struct r600_query *query)
@@ -1197,6 +1212,7 @@ void r600_query_end(struct r600_context *ctx, struct r600_query *query)
 	query->num_results += 16;
 	query->state ^= R600_QUERY_STATE_STARTED;
 	query->state |= R600_QUERY_STATE_ENDED;
+	ctx->num_query_running--;
 }
 
 struct r600_query *r600_context_query_create(struct r600_context *ctx, unsigned query_type)
diff --git a/src/gallium/winsys/r600/drm/r600d.h b/src/gallium/winsys/r600/drm/r600d.h
index 3c60e5c..fcce293 100644
--- a/src/gallium/winsys/r600/drm/r600d.h
+++ b/src/gallium/winsys/r600/drm/r600d.h
@@ -839,6 +839,16 @@
 #define R_028800_DB_DEPTH_CONTROL                    0x028800
 #define R_02880C_DB_SHADER_CONTROL                   0x02880C
 #define R_028D0C_DB_RENDER_CONTROL                   0x028D0C
+#define   S_028D0C_DEPTH_CLEAR_ENABLE(x)               (((x) & 0x1) << 0)
+#define   S_028D0C_STENCIL_CLEAR_ENABLE(x)             (((x) & 0x1) << 1)
+#define   S_028D0C_DEPTH_COPY_ENABLE(x)                (((x) & 0x1) << 2)
+#define   S_028D0C_STENCIL_COPY_ENABLE(x)              (((x) & 0x1) << 3)
+#define   S_028D0C_RESUMMARIZE_ENABLE(x)               (((x) & 0x1) << 4)
+#define   S_028D0C_STENCIL_COMPRESS_DISABLE(x)         (((x) & 0x1) << 5)
+#define   S_028D0C_DEPTH_COMPRESS_DISABLE(x)           (((x) & 0x1) << 6)
+#define   S_028D0C_COPY_CENTROID(x)                    (((x) & 0x1) << 7)
+#define   S_028D0C_COPY_SAMPLE(x)                      (((x) & 0x1) << 8)
+#define   S_028D0C_R700_PERFECT_ZPASS_COUNTS(x)        (((x) & 0x1) << 15)
 #define R_028D10_DB_RENDER_OVERRIDE                  0x028D10
 #define R_028D2C_DB_SRESULTS_COMPARE_STATE1          0x028D2C
 #define R_028D30_DB_PRELOAD_CONTROL                  0x028D30




More information about the mesa-commit mailing list