---
 src/gallium/drivers/r600/r600_llvm.c               | 125 ++++++++++++---------
 src/gallium/drivers/r600/r600_shader.c             |   2 +
 src/gallium/drivers/radeon/radeon_llvm.h           |   1 +
 .../drivers/radeon/radeon_setup_tgsi_llvm.c        |   2 +-
 4 files changed, 75 insertions(+), 55 deletions(-)

diff --git a/src/gallium/drivers/r600/r600_llvm.c 
b/src/gallium/drivers/r600/r600_llvm.c
index 5afe3cb..8dcda1a 100644
--- a/src/gallium/drivers/r600/r600_llvm.c
+++ b/src/gallium/drivers/r600/r600_llvm.c
@@ -87,37 +87,50 @@ static void llvm_load_system_value(
 }
 
 static LLVMValueRef
-llvm_load_input_helper(
-       struct radeon_llvm_context * ctx,
-       unsigned idx, int interp, int ij_index)
+llvm_load_input_vector(
+       struct radeon_llvm_context * ctx, unsigned location, unsigned ijregs,
+       boolean interp)
 {
-       const struct lp_build_context * bb = &ctx->soa.bld_base.base;
-       LLVMValueRef arg[2];
-       int arg_count;
-       const char * intrinsic;
-
-       arg[0] = lp_build_const_int32(bb->gallivm, idx);
-
-       if (interp) {
-               intrinsic = "llvm.R600.interp.input";
-               arg[1] = lp_build_const_int32(bb->gallivm, ij_index);
-               arg_count = 2;
-       } else {
-               intrinsic = "llvm.R600.load.input";
-               arg_count = 1;
-       }
-
-       return build_intrinsic(bb->gallivm->builder, intrinsic,
-               bb->elem_type, &arg[0], arg_count, LLVMReadNoneAttribute);
+               LLVMTypeRef VecType;
+               LLVMValueRef Args[2] = {
+                       lp_build_const_int32(&(ctx->gallivm), location)
+               };
+               unsigned ArgCount = 1;
+               if (interp) {
+                       VecType = 
LLVMVectorType(ctx->soa.bld_base.base.elem_type, 2);
+                       LLVMValueRef IJIndex = LLVMGetParam(ctx->main_fn, 
ijregs / 2);
+                       Args[ArgCount++] = 
LLVMBuildExtractElement(ctx->gallivm.builder, IJIndex,
+                       lp_build_const_int32(&(ctx->gallivm), 2 * (ijregs % 
2)), "");
+                       Args[ArgCount++] = 
LLVMBuildExtractElement(ctx->gallivm.builder, IJIndex,
+                       lp_build_const_int32(&(ctx->gallivm), 2 * (ijregs % 2) 
+ 1), "");
+                       LLVMValueRef HalfVec[2] = {
+                               build_intrinsic(ctx->gallivm.builder, 
"llvm.R600.interp.xy",
+                                       VecType, Args, ArgCount, 
LLVMReadNoneAttribute),
+                               build_intrinsic(ctx->gallivm.builder, 
"llvm.R600.interp.zw",
+                                       VecType, Args, ArgCount, 
LLVMReadNoneAttribute)
+                       };
+                       LLVMValueRef MaskInputs[4] = {
+                               lp_build_const_int32(&(ctx->gallivm), 0),
+                               lp_build_const_int32(&(ctx->gallivm), 1),
+                               lp_build_const_int32(&(ctx->gallivm), 2),
+                               lp_build_const_int32(&(ctx->gallivm), 3)
+                       };
+                       LLVMValueRef Mask = LLVMConstVector(MaskInputs, 4);
+                       return LLVMBuildShuffleVector(ctx->gallivm.builder, 
HalfVec[0], HalfVec[1],
+                               Mask, "");
+               } else {
+                       VecType = 
LLVMVectorType(ctx->soa.bld_base.base.elem_type, 4);
+                       return build_intrinsic(ctx->gallivm.builder, 
"llvm.R600.interp.const",
+                               VecType, Args, ArgCount, LLVMReadNoneAttribute);
+               }
 }
 
 static LLVMValueRef
 llvm_face_select_helper(
        struct radeon_llvm_context * ctx,
-       unsigned face_loc, LLVMValueRef front_color, LLVMValueRef back_color)
+       LLVMValueRef face, LLVMValueRef front_color, LLVMValueRef back_color)
 {
        const struct lp_build_context * bb = &ctx->soa.bld_base.base;
-       LLVMValueRef face = llvm_load_input_helper(ctx, face_loc, 0, 0);
        LLVMValueRef is_front = LLVMBuildFCmp(
                bb->gallivm->builder, LLVMRealUGT, face,
                lp_build_const_float(bb->gallivm, 0.0f),        "");
@@ -132,50 +145,46 @@ static void llvm_load_input(
 {
        const struct r600_shader_io * input = &ctx->r600_inputs[input_index];
        unsigned chan;
-       unsigned interp = 0;
-       int ij_index;
        int two_side = (ctx->two_side && input->name == TGSI_SEMANTIC_COLOR);
        LLVMValueRef v;
+       boolean require_interp_intrinsic = ctx->chip_class >= EVERGREEN &&
+               ctx->type == TGSI_PROCESSOR_FRAGMENT;
 
-       if (ctx->chip_class >= EVERGREEN && ctx->type == 
TGSI_PROCESSOR_FRAGMENT &&
-                       input->spi_sid) {
-               interp = 1;
-               ij_index = (input->interpolate > 0) ? input->ij_index : -1;
-       }
+       if (require_interp_intrinsic && input->spi_sid) {
+               v = llvm_load_input_vector(ctx, input->lds_pos, input->ij_index,
+                       (input->interpolate > 0));
+       } else
+               v = LLVMGetParam(ctx->main_fn, input->gpr);
 
-       for (chan = 0; chan < 4; chan++) {
-               unsigned soa_index = radeon_llvm_reg_index_soa(input_index, 
chan);
-               int loc;
+               if (two_side) {
+                       struct r600_shader_io * back_input =
+                               &ctx->r600_inputs[input->back_color_input];
+                       LLVMValueRef v2;
+                       LLVMValueRef face = LLVMGetParam(ctx->main_fn, 
ctx->face_gpr);
+                       face = LLVMBuildExtractElement(ctx->gallivm.builder, 
face,
+                               lp_build_const_int32(&(ctx->gallivm), 0), "");
 
-               if (interp) {
-                       loc = 4 * input->lds_pos + chan;
-               } else {
-                       if (input->name == TGSI_SEMANTIC_FACE)
-                               loc = 4 * ctx->face_gpr;
+                       if (require_interp_intrinsic && back_input->spi_sid)
+                               v2 = llvm_load_input_vector(ctx, 
back_input->lds_pos,
+                                       back_input->ij_index, 
(back_input->interpolate > 0));
                        else
-                               loc = 4 * input->gpr + chan;
+                               v2 = LLVMGetParam(ctx->main_fn, 
back_input->gpr);
+                       v = llvm_face_select_helper(ctx, face, v, v2);
                }
 
-               v = llvm_load_input_helper(ctx, loc, interp, ij_index);
+       for (chan = 0; chan < 4; chan++) {
+               unsigned soa_index = radeon_llvm_reg_index_soa(input_index, 
chan);
 
-               if (two_side) {
-                       struct r600_shader_io * back_input =
-                                       
&ctx->r600_inputs[input->back_color_input];
-                       int back_loc = interp ? back_input->lds_pos : 
back_input->gpr;
-                       LLVMValueRef v2;
+               ctx->inputs[soa_index] = 
LLVMBuildExtractElement(ctx->gallivm.builder, v,
+                       lp_build_const_int32(&(ctx->gallivm), chan), "");
 
-                       back_loc = 4 * back_loc + chan;
-                       v2 = llvm_load_input_helper(ctx, back_loc, interp, 
ij_index);
-                       v = llvm_face_select_helper(ctx, 4 * ctx->face_gpr, v, 
v2);
-               } else if (input->name == TGSI_SEMANTIC_POSITION &&
+               if (input->name == TGSI_SEMANTIC_POSITION &&
                                ctx->type == TGSI_PROCESSOR_FRAGMENT && chan == 
3) {
                        /* RCP for fragcoord.w */
-                       v = LLVMBuildFDiv(ctx->gallivm.builder,
+                       ctx->inputs[soa_index] = 
LLVMBuildFDiv(ctx->gallivm.builder,
                                        lp_build_const_float(&(ctx->gallivm), 
1.0f),
-                                       v, "");
+                                       ctx->inputs[soa_index], "");
                }
-
-               ctx->inputs[soa_index] = v;
        }
 }
 
@@ -657,7 +666,15 @@ LLVMModuleRef r600_tgsi_llvm(
        struct tgsi_shader_info shader_info;
        struct lp_build_tgsi_context * bld_base = &ctx->soa.bld_base;
        radeon_llvm_context_init(ctx);
-       radeon_llvm_create_func(ctx, NULL, 0);
+       LLVMTypeRef Arguments[32];
+       unsigned ArgumentsCount = 0;
+       for (unsigned i = 0; i < ctx->inputs_count; i++)
+               Arguments[ArgumentsCount++] = 
LLVMVectorType(bld_base->base.elem_type, 4);
+       radeon_llvm_create_func(ctx, Arguments, ArgumentsCount);
+       for (unsigned i = 0; i < ctx->inputs_count; i++) {
+               LLVMValueRef P = LLVMGetParam(ctx->main_fn, i);
+               LLVMAddAttribute(P, LLVMInRegAttribute);
+       }
        tgsi_scan_shader(tokens, &shader_info);
 
        bld_base->info = &shader_info;
diff --git a/src/gallium/drivers/r600/r600_shader.c 
b/src/gallium/drivers/r600/r600_shader.c
index aed2100..ae134d1 100644
--- a/src/gallium/drivers/r600/r600_shader.c
+++ b/src/gallium/drivers/r600/r600_shader.c
@@ -899,6 +899,7 @@ static int r600_shader_from_tgsi(struct r600_screen 
*rscreen,
 #ifdef R600_USE_LLVM
        use_llvm = !(rscreen->b.debug_flags & DBG_NO_LLVM);
 #endif
+
        ctx.bc = &shader->bc;
        ctx.shader = shader;
        ctx.native_integers = true;
@@ -1102,6 +1103,7 @@ static int r600_shader_from_tgsi(struct r600_screen 
*rscreen,
                radeon_llvm_ctx.type = ctx.type;
                radeon_llvm_ctx.two_side = shader->two_side;
                radeon_llvm_ctx.face_gpr = ctx.face_gpr;
+               radeon_llvm_ctx.inputs_count = ctx.shader->ninput + 1;
                radeon_llvm_ctx.r600_inputs = ctx.shader->input;
                radeon_llvm_ctx.r600_outputs = ctx.shader->output;
                radeon_llvm_ctx.color_buffer_count = max_color_exports;
diff --git a/src/gallium/drivers/radeon/radeon_llvm.h 
b/src/gallium/drivers/radeon/radeon_llvm.h
index ef09dc8..2cab6b0 100644
--- a/src/gallium/drivers/radeon/radeon_llvm.h
+++ b/src/gallium/drivers/radeon/radeon_llvm.h
@@ -60,6 +60,7 @@ struct radeon_llvm_context {
        unsigned face_gpr;
        unsigned two_side;
        unsigned clip_vertex;
+       unsigned inputs_count;
        struct r600_shader_io * r600_inputs;
        struct r600_shader_io * r600_outputs;
        struct pipe_stream_output_info *stream_outputs;
diff --git a/src/gallium/drivers/radeon/radeon_setup_tgsi_llvm.c 
b/src/gallium/drivers/radeon/radeon_setup_tgsi_llvm.c
index 43ebe7f..9ed671c 100644
--- a/src/gallium/drivers/radeon/radeon_setup_tgsi_llvm.c
+++ b/src/gallium/drivers/radeon/radeon_setup_tgsi_llvm.c
@@ -1252,7 +1252,7 @@ void radeon_llvm_context_init(struct radeon_llvm_context 
* ctx)
        bld_base->op_actions[TGSI_OPCODE_ENDIF].emit = endif_emit;
        bld_base->op_actions[TGSI_OPCODE_ENDLOOP].emit = endloop_emit;
        bld_base->op_actions[TGSI_OPCODE_EX2].emit = build_tgsi_intrinsic_nomem;
-       bld_base->op_actions[TGSI_OPCODE_EX2].intr_name = "llvm.AMDIL.exp.";
+       bld_base->op_actions[TGSI_OPCODE_EX2].intr_name = "llvm.exp2.f32";
        bld_base->op_actions[TGSI_OPCODE_FLR].emit = 
build_tgsi_intrinsic_readonly;
        bld_base->op_actions[TGSI_OPCODE_FLR].intr_name = "floor";
        bld_base->op_actions[TGSI_OPCODE_FRC].emit = build_tgsi_intrinsic_nomem;
-- 
1.8.3.1

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

Reply via email to