radeonsi/nir: load FS inputs
authorNicolai Hähnle <nicolai.haehnle@amd.com>
Thu, 8 Jun 2017 17:10:33 +0000 (19:10 +0200)
committerNicolai Hähnle <nicolai.haehnle@amd.com>
Mon, 31 Jul 2017 12:55:36 +0000 (14:55 +0200)
Reviewed-by: Marek Olšák <marek.olsak@amd.com>
src/gallium/drivers/radeonsi/si_shader.c
src/gallium/drivers/radeonsi/si_shader_internal.h
src/gallium/drivers/radeonsi/si_shader_nir.c

index 44ba6ad5d919df1df3c79313ba38503c272210b4..20561ad550b26c06d02387456c8217e2ea08ce9c 100644 (file)
@@ -1392,25 +1392,28 @@ static void interp_fs_input(struct si_shader_context *ctx,
        }
 }
 
-static void declare_input_fs(
+void si_llvm_load_input_fs(
        struct si_shader_context *ctx,
        unsigned input_index,
-       const struct tgsi_full_declaration *decl,
        LLVMValueRef out[4])
 {
        struct lp_build_context *base = &ctx->bld_base.base;
        struct si_shader *shader = ctx->shader;
+       struct tgsi_shader_info *info = &shader->selector->info;
        LLVMValueRef main_fn = ctx->main_fn;
        LLVMValueRef interp_param = NULL;
        int interp_param_idx;
+       enum tgsi_semantic semantic_name = info->input_semantic_name[input_index];
+       unsigned semantic_index = info->input_semantic_index[input_index];
+       enum tgsi_interpolate_mode interp_mode = info->input_interpolate[input_index];
+       enum tgsi_interpolate_loc interp_loc = info->input_interpolate_loc[input_index];
 
        /* Get colors from input VGPRs (set by the prolog). */
-       if (decl->Semantic.Name == TGSI_SEMANTIC_COLOR) {
-               unsigned i = decl->Semantic.Index;
+       if (semantic_name == TGSI_SEMANTIC_COLOR) {
                unsigned colors_read = shader->selector->info.colors_read;
-               unsigned mask = colors_read >> (i * 4);
+               unsigned mask = colors_read >> (semantic_index * 4);
                unsigned offset = SI_PARAM_POS_FIXED_PT + 1 +
-                                 (i ? util_bitcount(colors_read & 0xf) : 0);
+                                 (semantic_index ? util_bitcount(colors_read & 0xf) : 0);
 
                out[0] = mask & 0x1 ? LLVMGetParam(main_fn, offset++) : base->undef;
                out[1] = mask & 0x2 ? LLVMGetParam(main_fn, offset++) : base->undef;
@@ -1419,22 +1422,30 @@ static void declare_input_fs(
                return;
        }
 
-       interp_param_idx = lookup_interp_param_index(decl->Interp.Interpolate,
-                                                    decl->Interp.Location);
+       interp_param_idx = lookup_interp_param_index(interp_mode, interp_loc);
        if (interp_param_idx == -1)
                return;
        else if (interp_param_idx) {
                interp_param = LLVMGetParam(ctx->main_fn, interp_param_idx);
        }
 
-       interp_fs_input(ctx, input_index, decl->Semantic.Name,
-                       decl->Semantic.Index, 0, /* this param is unused */
+       interp_fs_input(ctx, input_index, semantic_name,
+                       semantic_index, 0, /* this param is unused */
                        shader->selector->info.colors_read, interp_param,
                        LLVMGetParam(main_fn, SI_PARAM_PRIM_MASK),
                        LLVMGetParam(main_fn, SI_PARAM_FRONT_FACE),
                        &out[0]);
 }
 
+static void declare_input_fs(
+       struct si_shader_context *ctx,
+       unsigned input_index,
+       const struct tgsi_full_declaration *decl,
+       LLVMValueRef out[4])
+{
+       si_llvm_load_input_fs(ctx, input_index, out);
+}
+
 static LLVMValueRef get_sample_id(struct si_shader_context *ctx)
 {
        return unpack_param(ctx, SI_PARAM_ANCILLARY, 8, 4);
index a86fd02217731e059c0c8769f41e6b63acd0695f..81cc018af22d24d54a02ccc750de9a9aa29eb701 100644 (file)
@@ -318,6 +318,10 @@ void si_llvm_load_input_vs(
        struct si_shader_context *ctx,
        unsigned input_index,
        LLVMValueRef out[4]);
+void si_llvm_load_input_fs(
+       struct si_shader_context *ctx,
+       unsigned input_index,
+       LLVMValueRef out[4]);
 
 bool si_nir_build_llvm(struct si_shader_context *ctx, struct nir_shader *nir);
 
index ef0dd9dbf963b4ed18ab1e21d029d6eb1c959a9d..eec5ac15d1b15d68f65c808dd3940b6ecd81545c 100644 (file)
@@ -320,8 +320,31 @@ static void declare_nir_input_vs(struct si_shader_context *ctx,
        si_llvm_load_input_vs(ctx, variable->data.driver_location / 4 + rel, out);
 }
 
+static void declare_nir_input_fs(struct si_shader_context *ctx,
+                                struct nir_variable *variable, unsigned rel,
+                                unsigned *fs_attr_idx,
+                                LLVMValueRef out[4])
+{
+       unsigned slot = variable->data.location + rel;
+
+       assert(variable->data.location >= VARYING_SLOT_VAR0 || rel == 0);
+
+       if (slot == VARYING_SLOT_POS) {
+               out[0] = LLVMGetParam(ctx->main_fn, SI_PARAM_POS_X_FLOAT);
+               out[1] = LLVMGetParam(ctx->main_fn, SI_PARAM_POS_Y_FLOAT);
+               out[2] = LLVMGetParam(ctx->main_fn, SI_PARAM_POS_Z_FLOAT);
+               out[3] = ac_build_fdiv(&ctx->ac, ctx->ac.f32_1,
+                               LLVMGetParam(ctx->main_fn, SI_PARAM_POS_W_FLOAT));
+               return;
+       }
+
+       si_llvm_load_input_fs(ctx, *fs_attr_idx, out);
+       (*fs_attr_idx)++;
+}
+
 bool si_nir_build_llvm(struct si_shader_context *ctx, struct nir_shader *nir)
 {
+       unsigned fs_attr_idx = 0;
        nir_foreach_variable(variable, &nir->inputs) {
                unsigned attrib_count = glsl_count_attribute_slots(variable->type,
                                                                   nir->stage == MESA_SHADER_VERTEX);
@@ -330,7 +353,10 @@ bool si_nir_build_llvm(struct si_shader_context *ctx, struct nir_shader *nir)
                for (unsigned i = 0; i < attrib_count; ++i) {
                        LLVMValueRef data[4];
 
-                       declare_nir_input_vs(ctx, variable, i, data);
+                       if (nir->stage == MESA_SHADER_VERTEX)
+                               declare_nir_input_vs(ctx, variable, i, data);
+                       else if (nir->stage == MESA_SHADER_FRAGMENT)
+                               declare_nir_input_fs(ctx, variable, i, &fs_attr_idx, data);
 
                        for (unsigned chan = 0; chan < 4; chan++) {
                                ctx->inputs[input_idx + chan] =