From: Marek Olšák <marek.ol...@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 _______________________________________________ mesa-dev mailing list mesa-dev@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/mesa-dev