For the series:

Reviewed-by: Nicolai Hähnle <nicolai.haeh...@amd.com>

On 06.09.2016 00:46, Marek Olšák wrote:
From: Marek Olšák <marek.ol...@amd.com>

Ported from Vulkan.
---
 src/gallium/drivers/radeonsi/si_hw_context.c |  1 +
 src/gallium/drivers/radeonsi/si_pipe.h       |  1 +
 src/gallium/drivers/radeonsi/si_state_draw.c | 50 +++++++++++++++++-----------
 3 files changed, 32 insertions(+), 20 deletions(-)

diff --git a/src/gallium/drivers/radeonsi/si_hw_context.c 
b/src/gallium/drivers/radeonsi/si_hw_context.c
index a03b327..24b0360 100644
--- a/src/gallium/drivers/radeonsi/si_hw_context.c
+++ b/src/gallium/drivers/radeonsi/si_hw_context.c
@@ -218,20 +218,21 @@ void si_begin_new_cs(struct si_context *ctx)
        si_mark_atom_dirty(ctx, &ctx->b.viewports.atom);

        r600_postflush_resume_features(&ctx->b);

        assert(!ctx->b.gfx.cs->prev_dw);
        ctx->b.initial_gfx_cs_size = ctx->b.gfx.cs->current.cdw;

        /* Invalidate various draw states so that they are emitted before
         * the first draw call. */
        si_invalidate_draw_sh_constants(ctx);
+       ctx->last_index_size = -1;
        ctx->last_primitive_restart_en = -1;
        ctx->last_restart_index = SI_RESTART_INDEX_UNKNOWN;
        ctx->last_gs_out_prim = -1;
        ctx->last_prim = -1;
        ctx->last_multi_vgt_param = -1;
        ctx->last_ls_hs_config = -1;
        ctx->last_rast_prim = -1;
        ctx->last_sc_line_stipple = ~0;
        ctx->last_vtx_reuse_depth = -1;
        ctx->emit_scratch_reloc = true;
diff --git a/src/gallium/drivers/radeonsi/si_pipe.h 
b/src/gallium/drivers/radeonsi/si_pipe.h
index 5c041ce..a648d86 100644
--- a/src/gallium/drivers/radeonsi/si_pipe.h
+++ b/src/gallium/drivers/radeonsi/si_pipe.h
@@ -300,20 +300,21 @@ struct si_context {
        bool                    db_flush_depth_inplace;
        bool                    db_flush_stencil_inplace;
        bool                    db_depth_clear;
        bool                    db_depth_disable_expclear;
        bool                    db_stencil_clear;
        bool                    db_stencil_disable_expclear;
        unsigned                ps_db_shader_control;
        bool                    occlusion_queries_disabled;

        /* Emitted draw state. */
+       int                     last_index_size;
        int                     last_base_vertex;
        int                     last_start_instance;
        int                     last_drawid;
        int                     last_sh_base_reg;
        int                     last_primitive_restart_en;
        int                     last_restart_index;
        int                     last_gs_out_prim;
        int                     last_prim;
        int                     last_multi_vgt_param;
        int                     last_ls_hs_config;
diff --git a/src/gallium/drivers/radeonsi/si_state_draw.c 
b/src/gallium/drivers/radeonsi/si_state_draw.c
index d4447a9..d7325ff 100644
--- a/src/gallium/drivers/radeonsi/si_state_draw.c
+++ b/src/gallium/drivers/radeonsi/si_state_draw.c
@@ -546,49 +546,59 @@ static void si_emit_draw_packets(struct si_context *sctx,
                radeon_emit(cs, R_028B2C_VGT_STRMOUT_DRAW_OPAQUE_BUFFER_FILLED_SIZE 
>> 2);
                radeon_emit(cs, 0); /* unused */

                radeon_add_to_buffer_list(&sctx->b, &sctx->b.gfx,
                                      t->buf_filled_size, RADEON_USAGE_READ,
                                      RADEON_PRIO_SO_FILLED_SIZE);
        }

        /* draw packet */
        if (info->indexed) {
-               radeon_emit(cs, PKT3(PKT3_INDEX_TYPE, 0, 0));
-
-               /* index type */
-               switch (ib->index_size) {
-               case 1:
-                       radeon_emit(cs, V_028A7C_VGT_INDEX_8);
-                       break;
-               case 2:
-                       radeon_emit(cs, V_028A7C_VGT_INDEX_16 |
-                                   (SI_BIG_ENDIAN && sctx->b.chip_class <= CIK 
?
-                                            V_028A7C_VGT_DMA_SWAP_16_BIT : 0));
-                       break;
-               case 4:
-                       radeon_emit(cs, V_028A7C_VGT_INDEX_32 |
-                                   (SI_BIG_ENDIAN && sctx->b.chip_class <= CIK 
?
-                                            V_028A7C_VGT_DMA_SWAP_32_BIT : 0));
-                       break;
-               default:
-                       assert(!"unreachable");
-                       return;
+               if (ib->index_size != sctx->last_index_size) {
+                       radeon_emit(cs, PKT3(PKT3_INDEX_TYPE, 0, 0));
+
+                       /* index type */
+                       switch (ib->index_size) {
+                       case 1:
+                               radeon_emit(cs, V_028A7C_VGT_INDEX_8);
+                               break;
+                       case 2:
+                               radeon_emit(cs, V_028A7C_VGT_INDEX_16 |
+                                           (SI_BIG_ENDIAN && sctx->b.chip_class 
<= CIK ?
+                                                    
V_028A7C_VGT_DMA_SWAP_16_BIT : 0));
+                               break;
+                       case 4:
+                               radeon_emit(cs, V_028A7C_VGT_INDEX_32 |
+                                           (SI_BIG_ENDIAN && sctx->b.chip_class 
<= CIK ?
+                                                    
V_028A7C_VGT_DMA_SWAP_32_BIT : 0));
+                               break;
+                       default:
+                               assert(!"unreachable");
+                               return;
+                       }
+
+                       sctx->last_index_size = ib->index_size;
                }

                index_max_size = (ib->buffer->width0 - ib->offset) /
                                  ib->index_size;
                index_va = r600_resource(ib->buffer)->gpu_address + ib->offset;

                radeon_add_to_buffer_list(&sctx->b, &sctx->b.gfx,
                                      (struct r600_resource *)ib->buffer,
                                      RADEON_USAGE_READ, 
RADEON_PRIO_INDEX_BUFFER);
+       } else {
+               /* On CI and later, non-indexed draws overwrite VGT_INDEX_TYPE,
+                * so the state must be re-emitted before the next indexed draw.
+                */
+               if (sctx->b.chip_class >= CIK)
+                       sctx->last_index_size = -1;
        }

        if (!info->indirect) {
                int base_vertex;

                radeon_emit(cs, PKT3(PKT3_NUM_INSTANCES, 0, 0));
                radeon_emit(cs, info->instance_count);

                /* Base vertex and start instance. */
                base_vertex = info->indexed ? info->index_bias : info->start;

_______________________________________________
mesa-dev mailing list
mesa-dev@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/mesa-dev

Reply via email to