From 2a8a569276ded3528917ddf9f006eb7b1d1d66ad Mon Sep 17 00:00:00 2001 From: Constantine Kharlamov Date: Thu, 13 Apr 2017 23:56:28 +0300 Subject: [PATCH] r600g: update dirty_level_mask after the 1-st draw after FB change MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit Ported from radeonsi. Testing with Kane&Lynch2 shows ≈1k skipped updates per frame on average. No piglit changes with tests/gpu.py, gbm mode. Signed-off-by: Constantine Kharlamov Tested-by: Dieter Nützel Reviewed-by: Nicolai Hähnle --- src/gallium/drivers/r600/evergreen_state.c | 1 + src/gallium/drivers/r600/r600_pipe.h | 1 + src/gallium/drivers/r600/r600_state.c | 1 + src/gallium/drivers/r600/r600_state_common.c | 41 ++++++++++++++++------------ 4 files changed, 26 insertions(+), 18 deletions(-) diff --git a/src/gallium/drivers/r600/evergreen_state.c b/src/gallium/drivers/r600/evergreen_state.c index 5697da4..19ad504 100644 --- a/src/gallium/drivers/r600/evergreen_state.c +++ b/src/gallium/drivers/r600/evergreen_state.c @@ -1550,6 +1550,7 @@ static void evergreen_set_framebuffer_state(struct pipe_context *ctx, r600_mark_atom_dirty(rctx, &rctx->framebuffer.atom); r600_set_sample_locations_constant_buffer(rctx); + rctx->framebuffer.do_update_surf_dirtiness = true; } static void evergreen_set_min_samples(struct pipe_context *ctx, unsigned min_samples) diff --git a/src/gallium/drivers/r600/r600_pipe.h b/src/gallium/drivers/r600/r600_pipe.h index 7f1ecc2..e1715e8 100644 --- a/src/gallium/drivers/r600/r600_pipe.h +++ b/src/gallium/drivers/r600/r600_pipe.h @@ -189,6 +189,7 @@ struct r600_framebuffer { bool cb0_is_integer; bool is_msaa_resolve; bool dual_src_blend; + bool do_update_surf_dirtiness; }; struct r600_sample_mask { diff --git a/src/gallium/drivers/r600/r600_state.c b/src/gallium/drivers/r600/r600_state.c index 06100ab..fc93eb0 100644 --- a/src/gallium/drivers/r600/r600_state.c +++ b/src/gallium/drivers/r600/r600_state.c @@ -1209,6 +1209,7 @@ static void r600_set_framebuffer_state(struct pipe_context *ctx, r600_mark_atom_dirty(rctx, &rctx->framebuffer.atom); r600_set_sample_locations_constant_buffer(rctx); + rctx->framebuffer.do_update_surf_dirtiness = true; } static uint32_t sample_locs_2x[] = { diff --git a/src/gallium/drivers/r600/r600_state_common.c b/src/gallium/drivers/r600/r600_state_common.c index 5be49dc..7b52be3 100644 --- a/src/gallium/drivers/r600/r600_state_common.c +++ b/src/gallium/drivers/r600/r600_state_common.c @@ -99,6 +99,7 @@ static void r600_texture_barrier(struct pipe_context *ctx, unsigned flags) R600_CONTEXT_FLUSH_AND_INV_CB | R600_CONTEXT_FLUSH_AND_INV | R600_CONTEXT_WAIT_3D_IDLE; + rctx->framebuffer.do_update_surf_dirtiness = true; } static unsigned r600_conv_pipe_prim(unsigned prim) @@ -1732,6 +1733,7 @@ static void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info if (unlikely(dirty_tex_counter != rctx->b.last_dirty_tex_counter)) { rctx->b.last_dirty_tex_counter = dirty_tex_counter; r600_mark_atom_dirty(rctx, &rctx->framebuffer.atom); + rctx->framebuffer.do_update_surf_dirtiness = true; } if (!r600_update_derived_state(rctx)) { @@ -2034,29 +2036,32 @@ static void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info radeon_emit(cs, EVENT_TYPE(EVENT_TYPE_SQ_NON_EVENT)); } - /* Set the depth buffer as dirty. */ - if (rctx->framebuffer.state.zsbuf) { - struct pipe_surface *surf = rctx->framebuffer.state.zsbuf; - struct r600_texture *rtex = (struct r600_texture *)surf->texture; + if (rctx->framebuffer.do_update_surf_dirtiness) { + /* Set the depth buffer as dirty. */ + if (rctx->framebuffer.state.zsbuf) { + struct pipe_surface *surf = rctx->framebuffer.state.zsbuf; + struct r600_texture *rtex = (struct r600_texture *)surf->texture; - rtex->dirty_level_mask |= 1 << surf->u.tex.level; + rtex->dirty_level_mask |= 1 << surf->u.tex.level; - if (rtex->surface.flags & RADEON_SURF_SBUFFER) - rtex->stencil_dirty_level_mask |= 1 << surf->u.tex.level; - } - if (rctx->framebuffer.compressed_cb_mask) { - struct pipe_surface *surf; - struct r600_texture *rtex; - unsigned mask = rctx->framebuffer.compressed_cb_mask; + if (rtex->surface.flags & RADEON_SURF_SBUFFER) + rtex->stencil_dirty_level_mask |= 1 << surf->u.tex.level; + } + if (rctx->framebuffer.compressed_cb_mask) { + struct pipe_surface *surf; + struct r600_texture *rtex; + unsigned mask = rctx->framebuffer.compressed_cb_mask; - do { - unsigned i = u_bit_scan(&mask); - surf = rctx->framebuffer.state.cbufs[i]; - rtex = (struct r600_texture*)surf->texture; + do { + unsigned i = u_bit_scan(&mask); + surf = rctx->framebuffer.state.cbufs[i]; + rtex = (struct r600_texture*)surf->texture; - rtex->dirty_level_mask |= 1 << surf->u.tex.level; + rtex->dirty_level_mask |= 1 << surf->u.tex.level; - } while (mask); + } while (mask); + } + rctx->framebuffer.do_update_surf_dirtiness = false; } pipe_resource_reference(&ib.buffer, NULL); -- 2.7.4