summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/radeonsi/si_shader.c
diff options
context:
space:
mode:
authorMarek Olšák <[email protected]>2017-01-24 21:39:42 +0100
committerMarek Olšák <[email protected]>2017-03-30 14:44:33 +0200
commit566defad138161a321ef11b528a7c4fcae273f6e (patch)
treec3f2d7e80b1bca7cc8c4796f053f3ed8a8dc11cc /src/gallium/drivers/radeonsi/si_shader.c
parentfc3c503b5d7fc9843220c8d89c6394f145f096af (diff)
radeonsi/gfx9: add a workaround for 1D depth textures
The same workaround is used by Vulkan. Reviewed-by: Nicolai Hähnle <[email protected]>
Diffstat (limited to 'src/gallium/drivers/radeonsi/si_shader.c')
-rw-r--r--src/gallium/drivers/radeonsi/si_shader.c59
1 files changed, 55 insertions, 4 deletions
diff --git a/src/gallium/drivers/radeonsi/si_shader.c b/src/gallium/drivers/radeonsi/si_shader.c
index 20d6bd732b2..20686bd331c 100644
--- a/src/gallium/drivers/radeonsi/si_shader.c
+++ b/src/gallium/drivers/radeonsi/si_shader.c
@@ -3297,6 +3297,7 @@ static LLVMValueRef image_fetch_coords(
const struct tgsi_full_instruction *inst,
unsigned src)
{
+ struct si_shader_context *ctx = si_shader_context(bld_base);
struct gallivm_state *gallivm = bld_base->base.gallivm;
LLVMBuilderRef builder = gallivm->builder;
unsigned target = inst->Memory.Texture;
@@ -3311,6 +3312,17 @@ static LLVMValueRef image_fetch_coords(
coords[chan] = tmp;
}
+ /* 1D textures are allocated and used as 2D on GFX9. */
+ if (ctx->screen->b.chip_class >= GFX9) {
+ if (target == TGSI_TEXTURE_1D) {
+ coords[1] = bld_base->uint_bld.zero;
+ num_coords++;
+ } else if (target == TGSI_TEXTURE_1D_ARRAY) {
+ coords[2] = coords[1];
+ coords[1] = bld_base->uint_bld.zero;
+ }
+ }
+
if (num_coords == 1)
return coords[0];
@@ -4440,11 +4452,12 @@ static void tex_fetch_args(
/* Pack user derivatives */
if (opcode == TGSI_OPCODE_TXD) {
- int param, num_src_deriv_channels;
+ int param, num_src_deriv_channels, num_dst_deriv_channels;
switch (target) {
case TGSI_TEXTURE_3D:
num_src_deriv_channels = 3;
+ num_dst_deriv_channels = 3;
num_deriv_channels = 3;
break;
case TGSI_TEXTURE_2D:
@@ -4454,6 +4467,7 @@ static void tex_fetch_args(
case TGSI_TEXTURE_2D_ARRAY:
case TGSI_TEXTURE_SHADOW2D_ARRAY:
num_src_deriv_channels = 2;
+ num_dst_deriv_channels = 2;
num_deriv_channels = 2;
break;
case TGSI_TEXTURE_CUBE:
@@ -4462,6 +4476,7 @@ static void tex_fetch_args(
case TGSI_TEXTURE_SHADOWCUBE_ARRAY:
/* Cube derivatives will be converted to 2D. */
num_src_deriv_channels = 3;
+ num_dst_deriv_channels = 3;
num_deriv_channels = 2;
break;
case TGSI_TEXTURE_1D:
@@ -4469,16 +4484,31 @@ static void tex_fetch_args(
case TGSI_TEXTURE_1D_ARRAY:
case TGSI_TEXTURE_SHADOW1D_ARRAY:
num_src_deriv_channels = 1;
- num_deriv_channels = 1;
+
+ /* 1D textures are allocated and used as 2D on GFX9. */
+ if (ctx->screen->b.chip_class >= GFX9) {
+ num_dst_deriv_channels = 2;
+ num_deriv_channels = 2;
+ } else {
+ num_dst_deriv_channels = 1;
+ num_deriv_channels = 1;
+ }
break;
default:
unreachable("invalid target");
}
- for (param = 0; param < 2; param++)
+ for (param = 0; param < 2; param++) {
for (chan = 0; chan < num_src_deriv_channels; chan++)
- derivs[param * num_src_deriv_channels + chan] =
+ derivs[param * num_dst_deriv_channels + chan] =
lp_build_emit_fetch(bld_base, inst, param+1, chan);
+
+ /* Fill in the rest with zeros. */
+ for (chan = num_src_deriv_channels;
+ chan < num_dst_deriv_channels; chan++)
+ derivs[param * num_dst_deriv_channels + chan] =
+ bld_base->base.zero;
+ }
}
if (target == TGSI_TEXTURE_CUBE ||
@@ -4502,6 +4532,27 @@ static void tex_fetch_args(
if (num_coords > 2)
address[count++] = coords[2];
+ /* 1D textures are allocated and used as 2D on GFX9. */
+ if (ctx->screen->b.chip_class >= GFX9) {
+ LLVMValueRef filler;
+
+ /* Use 0.5, so that we don't sample the border color. */
+ if (opcode == TGSI_OPCODE_TXF)
+ filler = bld_base->uint_bld.zero;
+ else
+ filler = LLVMConstReal(ctx->f32, 0.5);
+
+ if (target == TGSI_TEXTURE_1D ||
+ target == TGSI_TEXTURE_SHADOW1D) {
+ address[count++] = filler;
+ } else if (target == TGSI_TEXTURE_1D_ARRAY ||
+ target == TGSI_TEXTURE_SHADOW1D_ARRAY) {
+ address[count] = coords[count - 1];
+ address[count - 1] = filler;
+ count++;
+ }
+ }
+
/* Pack LOD or sample index */
if (opcode == TGSI_OPCODE_TXL || opcode == TGSI_OPCODE_TXF)
address[count++] = coords[3];