summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/radeonsi
diff options
context:
space:
mode:
Diffstat (limited to 'src/gallium/drivers/radeonsi')
-rw-r--r--src/gallium/drivers/radeonsi/si_blit.c15
-rw-r--r--src/gallium/drivers/radeonsi/si_state.c15
-rw-r--r--src/gallium/drivers/radeonsi/si_state_draw.c5
3 files changed, 33 insertions, 2 deletions
diff --git a/src/gallium/drivers/radeonsi/si_blit.c b/src/gallium/drivers/radeonsi/si_blit.c
index 46daeac4ac0..a48c5bc19e1 100644
--- a/src/gallium/drivers/radeonsi/si_blit.c
+++ b/src/gallium/drivers/radeonsi/si_blit.c
@@ -1055,10 +1055,23 @@ static void si_flush_resource(struct pipe_context *ctx,
struct r600_texture *rtex = (struct r600_texture*)res;
assert(res->target != PIPE_BUFFER);
+ assert(!rtex->dcc_separate_buffer || rtex->dcc_gather_statistics);
+
+ /* st/dri calls flush twice per frame (not a bug), this prevents double
+ * decompression. */
+ if (rtex->dcc_separate_buffer && !rtex->separate_dcc_dirty)
+ return;
if (!rtex->is_depth && (rtex->cmask.size || rtex->dcc_offset)) {
si_blit_decompress_color(ctx, rtex, 0, res->last_level,
- 0, util_max_layer(res, 0), false);
+ 0, util_max_layer(res, 0),
+ rtex->dcc_separate_buffer != NULL);
+ }
+
+ /* Always do the analysis even if DCC is disabled at the moment. */
+ if (rtex->dcc_gather_statistics && rtex->separate_dcc_dirty) {
+ rtex->separate_dcc_dirty = false;
+ vi_separate_dcc_process_and_reset_stats(ctx, rtex);
}
}
diff --git a/src/gallium/drivers/radeonsi/si_state.c b/src/gallium/drivers/radeonsi/si_state.c
index 5aed352f55c..26831faa107 100644
--- a/src/gallium/drivers/radeonsi/si_state.c
+++ b/src/gallium/drivers/radeonsi/si_state.c
@@ -2236,6 +2236,15 @@ static void si_set_framebuffer_state(struct pipe_context *ctx,
unsigned old_nr_samples = sctx->framebuffer.nr_samples;
int i;
+ for (i = 0; i < sctx->framebuffer.state.nr_cbufs; i++) {
+ if (!sctx->framebuffer.state.cbufs[i])
+ continue;
+
+ rtex = (struct r600_texture*)sctx->framebuffer.state.cbufs[i]->texture;
+ if (rtex->dcc_gather_statistics)
+ vi_separate_dcc_stop_query(ctx, rtex);
+ }
+
/* Only flush TC when changing the framebuffer state, because
* the only client not using TC that can change textures is
* the framebuffer.
@@ -2307,6 +2316,12 @@ static void si_set_framebuffer_state(struct pipe_context *ctx,
r600_context_add_resource_size(ctx, surf->base.texture);
p_atomic_inc(&rtex->framebuffers_bound);
+
+ if (rtex->dcc_gather_statistics) {
+ /* Dirty tracking must be enabled for DCC usage analysis. */
+ sctx->framebuffer.compressed_cb_mask |= 1 << i;
+ vi_separate_dcc_start_query(ctx, rtex);
+ }
}
/* Set the second SPI format for possible dual-src blending. */
if (i == 1 && surf) {
diff --git a/src/gallium/drivers/radeonsi/si_state_draw.c b/src/gallium/drivers/radeonsi/si_state_draw.c
index ce8def46659..a596bd81381 100644
--- a/src/gallium/drivers/radeonsi/si_state_draw.c
+++ b/src/gallium/drivers/radeonsi/si_state_draw.c
@@ -1042,7 +1042,10 @@ void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
surf = sctx->framebuffer.state.cbufs[i];
rtex = (struct r600_texture*)surf->texture;
- rtex->dirty_level_mask |= 1 << surf->u.tex.level;
+ if (rtex->fmask.size)
+ rtex->dirty_level_mask |= 1 << surf->u.tex.level;
+ if (rtex->dcc_gather_statistics)
+ rtex->separate_dcc_dirty = true;
} while (mask);
}