Signed-off-by: Ilia Mirkin <imir...@alum.mit.edu>
Tested-by: Fredrik Bruhn <f...@unibap.com>
---

Fredrik ran the ARB_shader_texture_image_samples tests and they
passed. No further testing was done.

 docs/GL3.txt                             |  2 +-
 docs/relnotes/11.1.0.html                |  2 +-
 src/gallium/drivers/radeonsi/si_pipe.c   |  2 +-
 src/gallium/drivers/radeonsi/si_shader.c | 92 +++++++++++++++++++++++---------
 4 files changed, 71 insertions(+), 27 deletions(-)

diff --git a/docs/GL3.txt b/docs/GL3.txt
index bd44d12..92941cf 100644
--- a/docs/GL3.txt
+++ b/docs/GL3.txt
@@ -194,7 +194,7 @@ GL 4.5, GLSL 4.50:
   GL_ARB_derivative_control                            DONE (i965, nv50, nvc0, 
r600, radeonsi)
   GL_ARB_direct_state_access                           DONE (all drivers)
   GL_ARB_get_texture_sub_image                         DONE (all drivers)
-  GL_ARB_shader_texture_image_samples                  DONE (i965, nv50, nvc0, 
r600)
+  GL_ARB_shader_texture_image_samples                  DONE (i965, nv50, nvc0, 
r600, radeonsi)
   GL_ARB_texture_barrier                               DONE (nv50, nvc0, r600, 
radeonsi)
   GL_KHR_context_flush_control                         DONE (all - but needs 
GLX/EGL extension to be useful)
   GL_KHR_robust_buffer_access_behavior                 not started
diff --git a/docs/relnotes/11.1.0.html b/docs/relnotes/11.1.0.html
index 24fdf2e..89b9a19 100644
--- a/docs/relnotes/11.1.0.html
+++ b/docs/relnotes/11.1.0.html
@@ -45,7 +45,7 @@ Note: some of the new features are only available with 
certain drivers.
 
 <ul>
 <li>GL_ARB_blend_func_extended on freedreno (a3xx)</li>
-<li>GL_ARB_shader_texture_image_samples on i965, nv50, nvc0, r600</li>
+<li>GL_ARB_shader_texture_image_samples on i965, nv50, nvc0, r600, 
radeonsi</li>
 <li>GL_ARB_texture_query_lod on softpipe</li>
 <li>GL_ARB_gpu_shader_fp64 on r600 for Cypress/Cayman/Aruba chips</li>
 </ul>
diff --git a/src/gallium/drivers/radeonsi/si_pipe.c 
b/src/gallium/drivers/radeonsi/si_pipe.c
index ae1ff7e..01fa525 100644
--- a/src/gallium/drivers/radeonsi/si_pipe.c
+++ b/src/gallium/drivers/radeonsi/si_pipe.c
@@ -284,6 +284,7 @@ static int si_get_param(struct pipe_screen* pscreen, enum 
pipe_cap param)
        case PIPE_CAP_DEPTH_BOUNDS_TEST:
        case PIPE_CAP_TEXTURE_QUERY_LOD:
        case PIPE_CAP_TEXTURE_GATHER_SM5:
+       case PIPE_CAP_TGSI_TXQS:
                return 1;
 
        case PIPE_CAP_RESOURCE_FROM_USER_MEMORY:
@@ -325,7 +326,6 @@ static int si_get_param(struct pipe_screen* pscreen, enum 
pipe_cap param)
        case PIPE_CAP_TEXTURE_GATHER_OFFSETS:
        case PIPE_CAP_SAMPLER_VIEW_TARGET:
        case PIPE_CAP_VERTEXID_NOBASE:
-       case PIPE_CAP_TGSI_TXQS:
                return 0;
 
        case PIPE_CAP_MAX_SHADER_PATCH_VARYINGS:
diff --git a/src/gallium/drivers/radeonsi/si_shader.c 
b/src/gallium/drivers/radeonsi/si_shader.c
index e92a3d2..2e49a21 100644
--- a/src/gallium/drivers/radeonsi/si_shader.c
+++ b/src/gallium/drivers/radeonsi/si_shader.c
@@ -2305,29 +2305,17 @@ static void set_tex_fetch_args(struct gallivm_state 
*gallivm,
 
 static const struct lp_build_tgsi_action tex_action;
 
-static void tex_fetch_args(
+static void tex_fetch_ptrs(
        struct lp_build_tgsi_context * bld_base,
-       struct lp_build_emit_data * emit_data)
+       struct lp_build_emit_data * emit_data,
+       LLVMValueRef *res_ptr, LLVMValueRef *samp_ptr, LLVMValueRef *fmask_ptr)
 {
        struct si_shader_context *si_shader_ctx = si_shader_context(bld_base);
        struct gallivm_state *gallivm = bld_base->base.gallivm;
-       LLVMBuilderRef builder = gallivm->builder;
        const struct tgsi_full_instruction * inst = emit_data->inst;
-       unsigned opcode = inst->Instruction.Opcode;
        unsigned target = inst->Texture.Texture;
-       LLVMValueRef coords[5], derivs[6];
-       LLVMValueRef address[16];
-       int ref_pos;
-       unsigned num_coords = tgsi_util_get_texture_coord_dim(target, &ref_pos);
-       unsigned count = 0;
-       unsigned chan;
        unsigned sampler_src;
        unsigned sampler_index;
-       unsigned num_deriv_channels = 0;
-       bool has_offset = inst->Texture.NumOffsets > 0;
-       LLVMValueRef res_ptr, samp_ptr, fmask_ptr = NULL;
-       LLVMTypeRef i32 = LLVMInt32TypeInContext(gallivm->context);
-       unsigned dmask = 0xf;
 
        sampler_src = emit_data->inst->Instruction.NumSrcRegs - 1;
        sampler_index = emit_data->inst->Src[sampler_src].Register.Index;
@@ -2338,25 +2326,50 @@ static void tex_fetch_args(
 
                ind_index = get_indirect_index(si_shader_ctx, &reg->Indirect, 
reg->Register.Index);
 
-               res_ptr = LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, 
SI_PARAM_RESOURCE);
-               res_ptr = build_indexed_load_const(si_shader_ctx, res_ptr, 
ind_index);
+               *res_ptr = LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, 
SI_PARAM_RESOURCE);
+               *res_ptr = build_indexed_load_const(si_shader_ctx, *res_ptr, 
ind_index);
 
-               samp_ptr = LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, 
SI_PARAM_SAMPLER);
-               samp_ptr = build_indexed_load_const(si_shader_ctx, samp_ptr, 
ind_index);
+               *samp_ptr = LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, 
SI_PARAM_SAMPLER);
+               *samp_ptr = build_indexed_load_const(si_shader_ctx, *samp_ptr, 
ind_index);
 
                if (target == TGSI_TEXTURE_2D_MSAA ||
                    target == TGSI_TEXTURE_2D_ARRAY_MSAA) {
                        ind_index = LLVMBuildAdd(gallivm->builder, ind_index,
                                                 lp_build_const_int32(gallivm,
                                                                      
SI_FMASK_TEX_OFFSET), "");
-                       fmask_ptr = 
LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, SI_PARAM_RESOURCE);
-                       fmask_ptr = build_indexed_load_const(si_shader_ctx, 
fmask_ptr, ind_index);
+                       *fmask_ptr = 
LLVMGetParam(si_shader_ctx->radeon_bld.main_fn, SI_PARAM_RESOURCE);
+                       *fmask_ptr = build_indexed_load_const(si_shader_ctx, 
*fmask_ptr, ind_index);
                }
        } else {
-               res_ptr = si_shader_ctx->resources[sampler_index];
-               samp_ptr = si_shader_ctx->samplers[sampler_index];
-               fmask_ptr = si_shader_ctx->resources[SI_FMASK_TEX_OFFSET + 
sampler_index];
+               *res_ptr = si_shader_ctx->resources[sampler_index];
+               *samp_ptr = si_shader_ctx->samplers[sampler_index];
+               *fmask_ptr = si_shader_ctx->resources[SI_FMASK_TEX_OFFSET + 
sampler_index];
        }
+}
+
+static void tex_fetch_args(
+       struct lp_build_tgsi_context * bld_base,
+       struct lp_build_emit_data * emit_data)
+{
+       struct si_shader_context *si_shader_ctx = si_shader_context(bld_base);
+       struct gallivm_state *gallivm = bld_base->base.gallivm;
+       LLVMBuilderRef builder = gallivm->builder;
+       const struct tgsi_full_instruction * inst = emit_data->inst;
+       unsigned opcode = inst->Instruction.Opcode;
+       unsigned target = inst->Texture.Texture;
+       LLVMValueRef coords[5], derivs[6];
+       LLVMValueRef address[16];
+       int ref_pos;
+       unsigned num_coords = tgsi_util_get_texture_coord_dim(target, &ref_pos);
+       unsigned count = 0;
+       unsigned chan;
+       unsigned num_deriv_channels = 0;
+       bool has_offset = inst->Texture.NumOffsets > 0;
+       LLVMValueRef res_ptr, samp_ptr, fmask_ptr = NULL;
+       LLVMTypeRef i32 = LLVMInt32TypeInContext(gallivm->context);
+       unsigned dmask = 0xf;
+
+       tex_fetch_ptrs(bld_base, emit_data, &res_ptr, &samp_ptr, &fmask_ptr);
 
        if (opcode == TGSI_OPCODE_TXQ) {
                if (target == TGSI_TEXTURE_BUFFER) {
@@ -2800,6 +2813,36 @@ static void build_tex_intrinsic(const struct 
lp_build_tgsi_action * action,
        }
 }
 
+static void si_llvm_emit_txqs(
+       const struct lp_build_tgsi_action * action,
+       struct lp_build_tgsi_context * bld_base,
+       struct lp_build_emit_data * emit_data)
+{
+       struct gallivm_state *gallivm = bld_base->base.gallivm;
+       LLVMBuilderRef builder = gallivm->builder;
+       LLVMTypeRef i32 = LLVMInt32TypeInContext(gallivm->context);
+       LLVMTypeRef v8i32 = LLVMVectorType(i32, 8);
+       LLVMValueRef res, samples;
+       LLVMValueRef res_ptr, samp_ptr, fmask_ptr = NULL;
+
+       tex_fetch_ptrs(bld_base, emit_data, &res_ptr, &samp_ptr, &fmask_ptr);
+
+
+       /* Read the samples from the descriptor directly. */
+       res = LLVMBuildBitCast(builder, res_ptr, v8i32, "");
+       samples = LLVMBuildExtractElement(
+               builder, res,
+               lp_build_const_int32(gallivm, 3), "");
+       samples = LLVMBuildLShr(builder, samples,
+                               lp_build_const_int32(gallivm, 16), "");
+       samples = LLVMBuildAnd(builder, samples,
+                              lp_build_const_int32(gallivm, 0xf), "");
+       samples = LLVMBuildShl(builder, lp_build_const_int32(gallivm, 1),
+                              samples, "");
+
+       emit_data->output[emit_data->chan] = samples;
+}
+
 /*
  * SI implements derivatives using the local data store (LDS)
  * All writes to the LDS happen in all executing threads at
@@ -3975,6 +4018,7 @@ int si_shader_create(struct si_screen *sscreen, 
LLVMTargetMachineRef tm,
        bld_base->op_actions[TGSI_OPCODE_TXQ] = tex_action;
        bld_base->op_actions[TGSI_OPCODE_TG4] = tex_action;
        bld_base->op_actions[TGSI_OPCODE_LODQ] = tex_action;
+       bld_base->op_actions[TGSI_OPCODE_TXQS].emit = si_llvm_emit_txqs;
 
        bld_base->op_actions[TGSI_OPCODE_DDX].emit = si_llvm_emit_ddxy;
        bld_base->op_actions[TGSI_OPCODE_DDY].emit = si_llvm_emit_ddxy;
-- 
2.4.6

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

Reply via email to