diff options
author | Marek Olšák <[email protected]> | 2014-04-23 16:15:36 +0200 |
---|---|---|
committer | Marek Olšák <[email protected]> | 2014-07-18 01:58:58 +0200 |
commit | 09056b352d6de42d24decafdcd6819ad70dc98f1 (patch) | |
tree | a01e2e6d914a09447e5106891d1164d994ce9a24 | |
parent | a66d9341393b9a82aa197e8bab942c6de1ecf02e (diff) |
radeonsi: use an SGPR instead of VGT_INDX_OFFSET
The draw indirect packets cannot set VGT_INDX_OFFSET, they can only set user
data SGPRs. This is the only way to support start/index_bias with indirect
drawing.
Reviewed-by: Michel Dänzer <[email protected]>
-rw-r--r-- | src/gallium/drivers/radeonsi/si_shader.c | 11 | ||||
-rw-r--r-- | src/gallium/drivers/radeonsi/si_shader.h | 10 | ||||
-rw-r--r-- | src/gallium/drivers/radeonsi/si_state.c | 1 | ||||
-rw-r--r-- | src/gallium/drivers/radeonsi/si_state_draw.c | 15 |
4 files changed, 23 insertions, 14 deletions
diff --git a/src/gallium/drivers/radeonsi/si_shader.c b/src/gallium/drivers/radeonsi/si_shader.c index 5d9c497b0bc..4c3e83f9605 100644 --- a/src/gallium/drivers/radeonsi/si_shader.c +++ b/src/gallium/drivers/radeonsi/si_shader.c @@ -223,10 +223,12 @@ static void declare_input_vs( si_shader_ctx->shader->shader.uses_instanceid = true; buffer_index = get_instance_index_for_fetch(&si_shader_ctx->radeon_bld, divisor); } else { - /* Load the buffer index, which is always stored in VGPR0 - * for Vertex Shaders */ - buffer_index = LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, - si_shader_ctx->param_vertex_id); + /* Load the buffer index for vertices. */ + LLVMValueRef vertex_id = LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, + si_shader_ctx->param_vertex_id); + LLVMValueRef base_vertex = LLVMGetParam(radeon_bld->main_fn, + SI_PARAM_BASE_VERTEX); + buffer_index = LLVMBuildAdd(gallivm->builder, base_vertex, vertex_id, ""); } vec4_type = LLVMVectorType(base->elem_type, 4); @@ -2342,6 +2344,7 @@ static void create_function(struct si_shader_context *si_shader_ctx) switch (si_shader_ctx->type) { case TGSI_PROCESSOR_VERTEX: params[SI_PARAM_VERTEX_BUFFER] = const_array(v16i8, SI_NUM_VERTEX_BUFFERS); + params[SI_PARAM_BASE_VERTEX] = i32; params[SI_PARAM_START_INSTANCE] = i32; num_params = SI_PARAM_START_INSTANCE+1; if (shader->key.vs.as_es) { diff --git a/src/gallium/drivers/radeonsi/si_shader.h b/src/gallium/drivers/radeonsi/si_shader.h index 81997c0b586..6891604db6c 100644 --- a/src/gallium/drivers/radeonsi/si_shader.h +++ b/src/gallium/drivers/radeonsi/si_shader.h @@ -36,10 +36,11 @@ #define SI_SGPR_RESOURCE 4 #define SI_SGPR_RW_BUFFERS 6 /* rings (& stream-out, VS only) */ #define SI_SGPR_VERTEX_BUFFER 8 /* VS only */ -#define SI_SGPR_START_INSTANCE 10 /* VS only */ +#define SI_SGPR_BASE_VERTEX 10 /* VS only */ +#define SI_SGPR_START_INSTANCE 11 /* VS only */ #define SI_SGPR_ALPHA_REF 8 /* PS only */ -#define SI_VS_NUM_USER_SGPR 11 +#define SI_VS_NUM_USER_SGPR 12 #define SI_GS_NUM_USER_SGPR 8 #define SI_PS_NUM_USER_SGPR 9 @@ -51,11 +52,12 @@ /* VS only parameters */ #define SI_PARAM_VERTEX_BUFFER 4 -#define SI_PARAM_START_INSTANCE 5 +#define SI_PARAM_BASE_VERTEX 5 +#define SI_PARAM_START_INSTANCE 6 /* the other VS parameters are assigned dynamically */ /* ES only parameters */ -#define SI_PARAM_ES2GS_OFFSET 6 +#define SI_PARAM_ES2GS_OFFSET 7 /* GS only parameters */ #define SI_PARAM_GS2VS_OFFSET 4 diff --git a/src/gallium/drivers/radeonsi/si_state.c b/src/gallium/drivers/radeonsi/si_state.c index 49fba731c5f..c106747a67d 100644 --- a/src/gallium/drivers/radeonsi/si_state.c +++ b/src/gallium/drivers/radeonsi/si_state.c @@ -3209,6 +3209,7 @@ void si_init_config(struct si_context *sctx) S_02800C_FORCE_HIS_ENABLE1(V_02800C_FORCE_DISABLE)); si_pm4_set_reg(pm4, R_028400_VGT_MAX_VTX_INDX, ~0); si_pm4_set_reg(pm4, R_028404_VGT_MIN_VTX_INDX, 0); + si_pm4_set_reg(pm4, R_028408_VGT_INDX_OFFSET, 0); if (sctx->b.chip_class >= CIK) { si_pm4_set_reg(pm4, R_00B118_SPI_SHADER_PGM_RSRC3_VS, S_00B118_CU_EN(0xffff)); diff --git a/src/gallium/drivers/radeonsi/si_state_draw.c b/src/gallium/drivers/radeonsi/si_state_draw.c index 01564eba843..0007a70fe69 100644 --- a/src/gallium/drivers/radeonsi/si_state_draw.c +++ b/src/gallium/drivers/radeonsi/si_state_draw.c @@ -426,14 +426,8 @@ static bool si_update_draw_info_state(struct si_context *sctx, } si_pm4_set_reg(pm4, R_028A6C_VGT_GS_OUT_PRIM_TYPE, gs_out_prim); - si_pm4_set_reg(pm4, R_028408_VGT_INDX_OFFSET, - info->indexed ? info->index_bias : info->start); si_pm4_set_reg(pm4, R_02840C_VGT_MULTI_PRIM_IB_RESET_INDX, info->restart_index); si_pm4_set_reg(pm4, R_028A94_VGT_MULTI_PRIM_IB_RESET_EN, info->primitive_restart); - si_pm4_set_reg(pm4, SI_SGPR_START_INSTANCE * 4 + - (sctx->gs_shader ? R_00B330_SPI_SHADER_USER_DATA_ES_0 : - R_00B130_SPI_SHADER_USER_DATA_VS_0), - info->start_instance); if (prim == V_008958_DI_PT_LINELIST) ls_mask = 1; @@ -730,6 +724,8 @@ static void si_state_draw(struct si_context *sctx, const struct pipe_draw_info *info, const struct pipe_index_buffer *ib) { + unsigned sh_base_reg = (sctx->gs_shader ? R_00B330_SPI_SHADER_USER_DATA_ES_0 : + R_00B130_SPI_SHADER_USER_DATA_VS_0); struct si_pm4_state *pm4 = si_pm4_alloc_state(sctx); if (pm4 == NULL) @@ -791,6 +787,13 @@ static void si_state_draw(struct si_context *sctx, si_pm4_cmd_add(pm4, info->instance_count); si_pm4_cmd_end(pm4, sctx->b.predicate_drawing); + if (!info->indirect) { + si_pm4_set_reg(pm4, sh_base_reg + SI_SGPR_BASE_VERTEX * 4, + info->indexed ? info->index_bias : info->start); + si_pm4_set_reg(pm4, sh_base_reg + SI_SGPR_START_INSTANCE * 4, + info->start_instance); + } + if (info->indexed) { uint32_t max_size = (ib->buffer->width0 - ib->offset) / sctx->index_buffer.index_size; |