[Mesa-dev] [PATCH 2/9] radeonsi: don't make a copy of pipe_index_buffer in draw_vbo
Marek Olšák
maraeo at gmail.com
Wed Mar 29 17:58:47 UTC 2017
From: Marek Olšák <marek.olsak at amd.com>
---
src/gallium/drivers/radeonsi/si_state_draw.c | 59 +++++++++++++---------------
1 file changed, 27 insertions(+), 32 deletions(-)
diff --git a/src/gallium/drivers/radeonsi/si_state_draw.c b/src/gallium/drivers/radeonsi/si_state_draw.c
index 1ff1547..6882ff4 100644
--- a/src/gallium/drivers/radeonsi/si_state_draw.c
+++ b/src/gallium/drivers/radeonsi/si_state_draw.c
@@ -991,21 +991,22 @@ void si_ce_post_draw_synchronization(struct si_context *sctx)
radeon_emit(sctx->b.gfx.cs, 0);
sctx->ce_need_synchronization = false;
}
}
void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
{
struct si_context *sctx = (struct si_context *)ctx;
struct si_state_rasterizer *rs = sctx->queued.named.rasterizer;
- struct pipe_index_buffer ib = {};
+ const struct pipe_index_buffer *ib = &sctx->index_buffer;
+ struct pipe_index_buffer ib_tmp; /* for index buffer uploads only */
unsigned mask, dirty_tex_counter, rast_prim;
if (likely(!info->indirect)) {
/* SI-CI treat instance_count==0 as instance_count==1. There is
* no workaround for indirect draws, but we can at least skip
* direct draws.
*/
if (unlikely(!info->instance_count))
return;
@@ -1076,78 +1077,72 @@ void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
sctx->do_update_shaders = true;
}
}
if (sctx->do_update_shaders && !si_update_shaders(sctx))
return;
if (!si_upload_graphics_shader_descriptors(sctx))
return;
- if (info->indexed) {
- /* Initialize the index buffer struct. */
- pipe_resource_reference(&ib.buffer, sctx->index_buffer.buffer);
- ib.user_buffer = sctx->index_buffer.user_buffer;
- ib.index_size = sctx->index_buffer.index_size;
- ib.offset = sctx->index_buffer.offset;
+ ib_tmp.buffer = NULL;
+ if (info->indexed) {
/* Translate or upload, if needed. */
/* 8-bit indices are supported on VI. */
- if (sctx->b.chip_class <= CIK && ib.index_size == 1) {
- struct pipe_resource *out_buffer = NULL;
- unsigned out_offset, start, count, start_offset, size;
+ if (sctx->b.chip_class <= CIK && ib->index_size == 1) {
+ unsigned start, count, start_offset, size;
void *ptr;
si_get_draw_start_count(sctx, info, &start, &count);
start_offset = start * 2;
size = count * 2;
u_upload_alloc(ctx->stream_uploader, start_offset,
size,
si_optimal_tcc_alignment(sctx, size),
- &out_offset, &out_buffer, &ptr);
- if (!out_buffer) {
- pipe_resource_reference(&ib.buffer, NULL);
+ &ib_tmp.offset, &ib_tmp.buffer, &ptr);
+ if (!ib_tmp.buffer)
return;
- }
- util_shorten_ubyte_elts_to_userptr(&sctx->b.b, &ib, 0, 0,
- ib.offset + start,
+ util_shorten_ubyte_elts_to_userptr(&sctx->b.b, ib, 0, 0,
+ ib->offset + start,
count, ptr);
- pipe_resource_reference(&ib.buffer, NULL);
- ib.user_buffer = NULL;
- ib.buffer = out_buffer;
/* info->start will be added by the drawing code */
- ib.offset = out_offset - start_offset;
- ib.index_size = 2;
- } else if (ib.user_buffer && !ib.buffer) {
+ ib_tmp.offset -= start_offset;
+ ib_tmp.index_size = 2;
+ ib = &ib_tmp;
+ } else if (ib->user_buffer && !ib->buffer) {
unsigned start, count, start_offset;
si_get_draw_start_count(sctx, info, &start, &count);
- start_offset = start * ib.index_size;
+ start_offset = start * ib->index_size;
u_upload_data(ctx->stream_uploader, start_offset,
- count * ib.index_size,
+ count * ib->index_size,
sctx->screen->b.info.tcc_cache_line_size,
- (char*)ib.user_buffer + start_offset,
- &ib.offset, &ib.buffer);
- if (!ib.buffer)
+ (char*)ib->user_buffer + start_offset,
+ &ib_tmp.offset, &ib_tmp.buffer);
+ if (!ib_tmp.buffer)
return;
+
/* info->start will be added by the drawing code */
- ib.offset -= start_offset;
+ ib_tmp.offset -= start_offset;
+ ib_tmp.index_size = ib->index_size;
+ ib = &ib_tmp;
} else if (sctx->b.chip_class <= CIK &&
- r600_resource(ib.buffer)->TC_L2_dirty) {
+ r600_resource(ib->buffer)->TC_L2_dirty) {
/* VI reads index buffers through TC L2, so it doesn't
* need this. */
sctx->b.flags |= SI_CONTEXT_WRITEBACK_GLOBAL_L2;
- r600_resource(ib.buffer)->TC_L2_dirty = false;
+ r600_resource(ib->buffer)->TC_L2_dirty = false;
}
}
if (info->indirect) {
/* Add the buffer size for memory checking in need_cs_space. */
r600_context_add_resource_size(ctx, info->indirect);
if (r600_resource(info->indirect)->TC_L2_dirty) {
sctx->b.flags |= SI_CONTEXT_WRITEBACK_GLOBAL_L2;
r600_resource(info->indirect)->TC_L2_dirty = false;
@@ -1193,21 +1188,21 @@ void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
si_pm4_emit(sctx, state);
sctx->emitted.array[i] = state;
}
sctx->dirty_states = 0;
si_emit_rasterizer_prim_state(sctx);
si_emit_draw_registers(sctx, info);
si_ce_pre_draw_synchronization(sctx);
- si_emit_draw_packets(sctx, info, &ib);
+ si_emit_draw_packets(sctx, info, ib);
si_ce_post_draw_synchronization(sctx);
if (sctx->trace_buf)
si_trace_emit(sctx);
/* Workaround for a VGT hang when streamout is enabled.
* It must be done after drawing. */
if ((sctx->b.family == CHIP_HAWAII ||
sctx->b.family == CHIP_TONGA ||
sctx->b.family == CHIP_FIJI) &&
@@ -1239,21 +1234,21 @@ void si_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
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);
}
sctx->framebuffer.do_update_surf_dirtiness = false;
}
- pipe_resource_reference(&ib.buffer, NULL);
+ pipe_resource_reference(&ib_tmp.buffer, NULL);
sctx->b.num_draw_calls++;
if (G_0286E8_WAVESIZE(sctx->spi_tmpring_size))
sctx->b.num_spill_draw_calls++;
}
void si_trace_emit(struct si_context *sctx)
{
struct radeon_winsys_cs *cs = sctx->b.gfx.cs;
sctx->trace_id++;
--
2.7.4
More information about the mesa-dev
mailing list