From: Nicolai Hähnle <[email protected]>

---
 src/amd/common/ac_shader_abi.h                    | 38 +++++++++++++++++++++++
 src/gallium/drivers/radeonsi/si_shader.c          | 34 ++++++++++----------
 src/gallium/drivers/radeonsi/si_shader_internal.h |  8 ++---
 3 files changed, 58 insertions(+), 22 deletions(-)
 create mode 100644 src/amd/common/ac_shader_abi.h

diff --git a/src/amd/common/ac_shader_abi.h b/src/amd/common/ac_shader_abi.h
new file mode 100644
index 0000000..4168177
--- /dev/null
+++ b/src/amd/common/ac_shader_abi.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2017 Advanced Micro Devices, Inc.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * on the rights to use, copy, modify, merge, publish, distribute, sub
+ * license, and/or sell copies of the Software, and to permit persons to whom
+ * the Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHOR(S) AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM,
+ * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
+ * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
+ * USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef AC_SHADER_ABI_H
+#define AC_SHADER_ABI_H
+
+/* Document the shader ABI during compilation. This is what allows radeonsi and
+ * radv to share a compiler backend.
+ */
+struct ac_shader_abi {
+       int param_base_vertex;
+       int param_start_instance;
+       int param_draw_id;
+       int param_vertex_id;
+       int param_instance_id;
+};
+
+#endif /* AC_SHADER_ABI_H */
diff --git a/src/gallium/drivers/radeonsi/si_shader.c 
b/src/gallium/drivers/radeonsi/si_shader.c
index 9848ea1..5879abc 100644
--- a/src/gallium/drivers/radeonsi/si_shader.c
+++ b/src/gallium/drivers/radeonsi/si_shader.c
@@ -310,21 +310,21 @@ get_tcs_out_current_patch_data_offset(struct 
si_shader_context *ctx)
                            "");
 }
 
 static LLVMValueRef get_instance_index_for_fetch(
        struct si_shader_context *ctx,
        unsigned param_start_instance, unsigned divisor)
 {
        struct gallivm_state *gallivm = &ctx->gallivm;
 
        LLVMValueRef result = LLVMGetParam(ctx->main_fn,
-                                          ctx->param_instance_id);
+                                          ctx->abi.param_instance_id);
 
        /* The division must be done before START_INSTANCE is added. */
        if (divisor > 1)
                result = LLVMBuildUDiv(gallivm->builder, result,
                                LLVMConstInt(ctx->i32, divisor, 0), "");
 
        return LLVMBuildAdd(gallivm->builder, result,
                            LLVMGetParam(ctx->main_fn, param_start_instance), 
"");
 }
 
@@ -1421,29 +1421,29 @@ static void declare_system_value(struct 
si_shader_context *ctx,
 {
        struct lp_build_context *bld = &ctx->bld_base.base;
        struct gallivm_state *gallivm = &ctx->gallivm;
        LLVMValueRef value = 0;
 
        assert(index < RADEON_LLVM_MAX_SYSTEM_VALUES);
 
        switch (decl->Semantic.Name) {
        case TGSI_SEMANTIC_INSTANCEID:
                value = LLVMGetParam(ctx->main_fn,
-                                    ctx->param_instance_id);
+                                    ctx->abi.param_instance_id);
                break;
 
        case TGSI_SEMANTIC_VERTEXID:
                value = LLVMBuildAdd(gallivm->builder,
                                     LLVMGetParam(ctx->main_fn,
-                                                 ctx->param_vertex_id),
+                                                 ctx->abi.param_vertex_id),
                                     LLVMGetParam(ctx->main_fn,
-                                                 ctx->param_base_vertex), "");
+                                                 ctx->abi.param_base_vertex), 
"");
                break;
 
        case TGSI_SEMANTIC_VERTEXID_NOBASE:
                /* Unused. Clarify the meaning in indexed vs. non-indexed
                 * draws if this is ever used again. */
                assert(false);
                break;
 
        case TGSI_SEMANTIC_BASEVERTEX:
        {
@@ -1451,31 +1451,31 @@ static void declare_system_value(struct 
si_shader_context *ctx,
                 * (for direct draws) or the CP (for indirect draws) is the
                 * first vertex ID, but GLSL expects 0 to be returned.
                 */
                LLVMValueRef vs_state = LLVMGetParam(ctx->main_fn, 
ctx->param_vs_state_bits);
                LLVMValueRef indexed;
 
                indexed = LLVMBuildLShr(gallivm->builder, vs_state, ctx->i32_1, 
"");
                indexed = LLVMBuildTrunc(gallivm->builder, indexed, ctx->i1, 
"");
 
                value = LLVMBuildSelect(gallivm->builder, indexed,
-                                       LLVMGetParam(ctx->main_fn, 
ctx->param_base_vertex),
+                                       LLVMGetParam(ctx->main_fn, 
ctx->abi.param_base_vertex),
                                        ctx->i32_0, "");
                break;
        }
 
        case TGSI_SEMANTIC_BASEINSTANCE:
-               value = LLVMGetParam(ctx->main_fn, ctx->param_start_instance);
+               value = LLVMGetParam(ctx->main_fn, 
ctx->abi.param_start_instance);
                break;
 
        case TGSI_SEMANTIC_DRAWID:
-               value = LLVMGetParam(ctx->main_fn, ctx->param_draw_id);
+               value = LLVMGetParam(ctx->main_fn, ctx->abi.param_draw_id);
                break;
 
        case TGSI_SEMANTIC_INVOCATIONID:
                if (ctx->type == PIPE_SHADER_TESS_CTRL)
                        value = unpack_param(ctx, ctx->param_tcs_rel_ids, 8, 5);
                else if (ctx->type == PIPE_SHADER_GEOMETRY)
                        value = LLVMGetParam(ctx->main_fn,
                                             ctx->param_gs_instance_id);
                else
                        assert(!"INVOCATIONID not implemented");
@@ -4112,38 +4112,38 @@ static void declare_default_desc_pointers(struct 
si_shader_context *ctx,
                si_const_array(ctx->v4i32, SI_NUM_RW_BUFFERS);
        declare_per_stage_desc_pointers(ctx, params, num_params, true);
 }
 
 static void declare_vs_specific_input_sgprs(struct si_shader_context *ctx,
                                            LLVMTypeRef *params,
                                            unsigned *num_params)
 {
        params[ctx->param_vertex_buffers = (*num_params)++] =
                si_const_array(ctx->v4i32, SI_NUM_VERTEX_BUFFERS);
-       params[ctx->param_base_vertex = (*num_params)++] = ctx->i32;
-       params[ctx->param_start_instance = (*num_params)++] = ctx->i32;
-       params[ctx->param_draw_id = (*num_params)++] = ctx->i32;
+       params[ctx->abi.param_base_vertex = (*num_params)++] = ctx->i32;
+       params[ctx->abi.param_start_instance = (*num_params)++] = ctx->i32;
+       params[ctx->abi.param_draw_id = (*num_params)++] = ctx->i32;
        params[ctx->param_vs_state_bits = (*num_params)++] = ctx->i32;
 }
 
 static void declare_vs_input_vgprs(struct si_shader_context *ctx,
                                   LLVMTypeRef *params, unsigned *num_params,
                                   unsigned *num_prolog_vgprs)
 {
        struct si_shader *shader = ctx->shader;
 
-       params[ctx->param_vertex_id = (*num_params)++] = ctx->i32;
+       params[ctx->abi.param_vertex_id = (*num_params)++] = ctx->i32;
        if (shader->key.as_ls) {
                params[ctx->param_rel_auto_id = (*num_params)++] = ctx->i32;
-               params[ctx->param_instance_id = (*num_params)++] = ctx->i32;
+               params[ctx->abi.param_instance_id = (*num_params)++] = ctx->i32;
        } else {
-               params[ctx->param_instance_id = (*num_params)++] = ctx->i32;
+               params[ctx->abi.param_instance_id = (*num_params)++] = ctx->i32;
                params[ctx->param_vs_prim_id = (*num_params)++] = ctx->i32;
        }
        params[(*num_params)++] = ctx->i32; /* unused */
 
        if (!shader->is_gs_copy_shader) {
                /* Vertex load indices. */
                ctx->param_vertex_index0 = (*num_params);
                for (unsigned i = 0; i < shader->selector->info.num_inputs; i++)
                        params[(*num_params)++] = ctx->i32;
                *num_prolog_vgprs += shader->selector->info.num_inputs;
@@ -5165,21 +5165,21 @@ si_generate_gs_copy_shader(struct si_screen *sscreen,
        ctx.shader = shader;
        ctx.type = PIPE_SHADER_VERTEX;
 
        builder = gallivm->builder;
 
        create_function(&ctx);
        preload_ring_buffers(&ctx);
 
        LLVMValueRef voffset =
                lp_build_mul_imm(uint, LLVMGetParam(ctx.main_fn,
-                                                   ctx.param_vertex_id), 4);
+                                                   ctx.abi.param_vertex_id), 
4);
 
        /* Fetch the vertex stream ID.*/
        LLVMValueRef stream_id;
 
        if (gs_selector->so.num_outputs)
                stream_id = unpack_param(&ctx, ctx.param_streamout_config, 24, 
2);
        else
                stream_id = ctx.i32_0;
 
        /* Fill in output information. */
@@ -6556,22 +6556,22 @@ static void si_build_vs_prolog_function(struct 
si_shader_context *ctx,
        LLVMTypeRef *params, *returns;
        LLVMValueRef ret, func;
        int last_sgpr, num_params, num_returns, i;
        unsigned first_vs_vgpr = key->vs_prolog.num_input_sgprs +
                                 key->vs_prolog.num_merged_next_stage_vgprs;
        unsigned num_input_vgprs = key->vs_prolog.num_merged_next_stage_vgprs + 
4;
        unsigned num_all_input_regs = key->vs_prolog.num_input_sgprs +
                                      num_input_vgprs;
        unsigned user_sgpr_base = key->vs_prolog.num_merged_next_stage_vgprs ? 
8 : 0;
 
-       ctx->param_vertex_id = first_vs_vgpr;
-       ctx->param_instance_id = first_vs_vgpr + (key->vs_prolog.as_ls ? 2 : 1);
+       ctx->abi.param_vertex_id = first_vs_vgpr;
+       ctx->abi.param_instance_id = first_vs_vgpr + (key->vs_prolog.as_ls ? 2 
: 1);
 
        /* 4 preloaded VGPRs + vertex load indices as prolog outputs */
        params = alloca(num_all_input_regs * sizeof(LLVMTypeRef));
        returns = alloca((num_all_input_regs + key->vs_prolog.last_input + 1) *
                         sizeof(LLVMTypeRef));
        num_params = 0;
        num_returns = 0;
 
        /* Declare input and output SGPRs. */
        num_params = 0;
@@ -6621,21 +6621,21 @@ static void si_build_vs_prolog_function(struct 
si_shader_context *ctx,
 
                if (divisor) {
                        /* InstanceID / Divisor + StartInstance */
                        index = get_instance_index_for_fetch(ctx,
                                                             user_sgpr_base +
                                                             
SI_SGPR_START_INSTANCE,
                                                             divisor);
                } else {
                        /* VertexID + BaseVertex */
                        index = LLVMBuildAdd(gallivm->builder,
-                                            LLVMGetParam(func, 
ctx->param_vertex_id),
+                                            LLVMGetParam(func, 
ctx->abi.param_vertex_id),
                                             LLVMGetParam(func, user_sgpr_base +
                                                                
SI_SGPR_BASE_VERTEX), "");
                }
 
                index = LLVMBuildBitCast(gallivm->builder, index, ctx->f32, "");
                ret = LLVMBuildInsertValue(gallivm->builder, ret, index,
                                           num_params++, "");
        }
 
        si_llvm_build_ret(ctx, ret);
diff --git a/src/gallium/drivers/radeonsi/si_shader_internal.h 
b/src/gallium/drivers/radeonsi/si_shader_internal.h
index 3556e69..90a70b1 100644
--- a/src/gallium/drivers/radeonsi/si_shader_internal.h
+++ b/src/gallium/drivers/radeonsi/si_shader_internal.h
@@ -21,20 +21,21 @@
  * USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
 
 #ifndef SI_SHADER_PRIVATE_H
 #define SI_SHADER_PRIVATE_H
 
 #include "si_shader.h"
 #include "gallivm/lp_bld_init.h"
 #include "gallivm/lp_bld_tgsi.h"
 #include "tgsi/tgsi_parse.h"
+#include "ac_shader_abi.h"
 #include "ac_llvm_util.h"
 #include "ac_llvm_build.h"
 
 #include <llvm-c/Core.h>
 #include <llvm-c/TargetMachine.h>
 
 struct pipe_debug_callback;
 struct ac_shader_binary;
 
 #define RADEON_LLVM_MAX_INPUT_SLOTS 32
@@ -59,20 +60,22 @@ struct si_shader_context {
 
        /* For clamping the non-constant index in resource indexing: */
        unsigned num_const_buffers;
        unsigned num_shader_buffers;
        unsigned num_images;
        unsigned num_samplers;
 
        /* Whether the prolog will be compiled separately. */
        bool separate_prolog;
 
+       struct ac_shader_abi abi;
+
        /** This function is responsible for initilizing the inputs array and 
will be
          * called once for each input declared in the TGSI shader.
          */
        void (*load_input)(struct si_shader_context *,
                           unsigned input_index,
                           const struct tgsi_full_declaration *decl,
                           LLVMValueRef out[4]);
 
        void (*load_system_value)(struct si_shader_context *,
                                  unsigned index,
@@ -115,27 +118,22 @@ struct si_shader_context {
 
        /* Parameter indices for LLVMGetParam. */
        int param_rw_buffers;
        int param_const_and_shader_buffers;
        int param_samplers_and_images;
        /* Common inputs for merged shaders. */
        int param_merged_wave_info;
        int param_merged_scratch_offset;
        /* API VS */
        int param_vertex_buffers;
-       int param_base_vertex;
-       int param_start_instance;
-       int param_draw_id;
-       int param_vertex_id;
        int param_rel_auto_id;
        int param_vs_prim_id;
-       int param_instance_id;
        int param_vertex_index0;
        /* VS states and layout of LS outputs / TCS inputs at the end
         *   [0] = clamp vertex color
         *   [1] = indexed
         *   [8:20] = stride between patches in DW = num_inputs * num_vertices 
* 4
         *            max = 32*32*4 + 32*4
         *   [24:31] = stride between vertices in DW = num_inputs * 4
         *             max = 32*4
         */
        int param_vs_state_bits;
-- 
2.9.3

_______________________________________________
mesa-dev mailing list
[email protected]
https://lists.freedesktop.org/mailman/listinfo/mesa-dev

Reply via email to