Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions tools/clang/include/clang/SPIRV/SpirvBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -339,6 +339,10 @@ class SpirvBuilder {

/// \brief Creates SPIR-V instructions for gathering the given image.
///
/// If the of `image` is a sampled image, then that image will be gathered.
/// In this case, `sampler` must be `nullptr`. If `image` is not a sampled
/// image, a sampled image will be created by combining `image` and `sampler`.
///
/// If compareVal is given a non-null value, OpImageDrefGather or
/// OpImageSparseDrefGather will be generated; otherwise, OpImageGather or
/// OpImageSparseGather will be generated.
Expand Down
11 changes: 9 additions & 2 deletions tools/clang/lib/SPIRV/SpirvBuilder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -714,8 +714,15 @@ SpirvInstruction *SpirvBuilder::createImageGather(
assert(insertPoint && "null insert point");

// An OpSampledImage is required to do the image sampling.
auto *sampledImage =
createSampledImage(imageType, image, sampler, loc, range);
// Skip creating OpSampledImage if the imageType is a sampled texture.
SpirvInstruction *sampledImage = nullptr;
if (isSampledTexture(imageType)) {
assert(!sampler &&
"sampler must be null when sampling from a sampled texture");
sampledImage = image;
} else {
sampledImage = createSampledImage(imageType, image, sampler, loc, range);
}

// TODO: Update ImageGather to accept minLod if necessary.
const auto mask = composeImageOperandsMask(
Expand Down
400 changes: 310 additions & 90 deletions tools/clang/lib/SPIRV/SpirvEmitter.cpp

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
// RUN: %dxc -T ps_6_8 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability ImageQuery

vk::SampledTexture2D<float4> t1 : register(t0);

// CHECK: %type_2d_image = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: %type_sampled_image = OpTypeSampledImage %type_2d_image
// CHECK: [[ptr:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant %type_sampled_image

// CHECK: %t1 = OpVariable [[ptr]] UniformConstant

void main() {
float2 xy = float2(0.5, 0.5);

//CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpLoad %type_sampled_image %t1
//CHECK-NEXT: [[xy_load:%[a-zA-Z0-9_]+]] = OpLoad %v2float %xy
//CHECK-NEXT: [[query:%[a-zA-Z0-9_]+]] = OpImageQueryLod %v2float [[tex1]] [[xy_load]]
//CHECK-NEXT: {{%[0-9]+}} = OpCompositeExtract %float [[query]] 1
float lod1 = t1.CalculateLevelOfDetailUnclamped(xy);
}
32 changes: 32 additions & 0 deletions tools/clang/test/CodeGenSPIRV/vk.sampledtexture.cmp-level.hlsl
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
// RUN: %dxc -T ps_6_0 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability SparseResidency

// CHECK: [[v2fc:%[0-9]+]] = OpConstantComposite %v2float %float_0_5 %float_0_25
// CHECK: [[v2ic:%[0-9]+]] = OpConstantComposite %v2int %int_2 %int_3

// CHECK: [[type_2d_image_1:%[a-zA-Z0-9_]+]] = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: [[type_sampled_image_1:%[a-zA-Z0-9_]+]] = OpTypeSampledImage [[type_2d_image_1]]
// CHECK: [[ptr_type_1:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant [[type_sampled_image_1]]

// CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpVariable [[ptr_type_1]] UniformConstant

vk::SampledTexture2D<float4> tex1 : register(t0);

float4 main() : SV_Target {
// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[sampled_result1:%[a-zA-Z0-9_]+]] = OpImageSampleDrefExplicitLod %float [[tex1_load]] [[v2fc]] %float_2 Lod %float_1
float val1 = tex1.SampleCmpLevel(float2(0.5, 0.25), 2.0f, 1.0f);

// CHECK: [[tex2_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[sampled_result2:%[a-zA-Z0-9_]+]] = OpImageSampleDrefExplicitLod %float [[tex2_load]] [[v2fc]] %float_2 Lod|ConstOffset %float_1 [[v2ic]]
float val2 = tex1.SampleCmpLevel(float2(0.5, 0.25), 2.0f, 1.0f, int2(2,3));

// CHECK: [[tex3_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[sampled_result3:%[a-zA-Z0-9_]+]] = OpImageSparseSampleDrefExplicitLod %SparseResidencyStruct [[tex3_load]] [[v2fc]] %float_2 Lod|ConstOffset %float_1 [[v2ic]]
// CHECK: [[status_0:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[sampled_result3]] 0
// CHECK: OpStore %status [[status_0]]
uint status;
float val3 = tex1.SampleCmpLevel(float2(0.5, 0.25), 2.0f, 1.0f, int2(2,3), status);
return 1.0;
}
54 changes: 54 additions & 0 deletions tools/clang/test/CodeGenSPIRV/vk.sampledtexture.gather-alpha.hlsl
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// RUN: %dxc -T ps_6_0 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability SparseResidency

// CHECK: [[v2fc:%[0-9]+]] = OpConstantComposite %v2float %float_0_5 %float_0_25
// CHECK: [[v2ic:%[0-9]+]] = OpConstantComposite %v2int %int_2 %int_3

// CHECK: [[type_2d_image_1:%[a-zA-Z0-9_]+]] = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: [[type_sampled_image_1:%[a-zA-Z0-9_]+]] = OpTypeSampledImage [[type_2d_image_1]]
// CHECK: [[ptr_type_1:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant [[type_sampled_image_1]]

// CHECK: [[type_struct_result:%[a-zA-Z0-9_]+]] = OpTypeStruct %uint %v4float

// CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpVariable [[ptr_type_1]] UniformConstant

vk::SampledTexture2D<float4> tex1 : register(t1);

float4 main() : SV_Target {
uint status;
float4 val = 0;

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_alpha:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_3
// CHECK: OpStore %val [[val_alpha]]
val = tex1.GatherAlpha(float2(0.5, 0.25));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_alpha_o:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_3 ConstOffset [[v2ic]]
// CHECK: OpStore %val [[val_alpha_o]]
val = tex1.GatherAlpha(float2(0.5, 0.25), int2(2, 3));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_alpha_o4:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_3 ConstOffsets [[const_offsets:%[a-zA-Z0-9_]+]]
// CHECK: OpStore %val [[val_alpha_o4]]
val = tex1.GatherAlpha(float2(0.5, 0.25), int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_alpha_s:%[a-zA-Z0-9_]+]] = OpImageSparseGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %int_3 ConstOffset [[v2ic]]
// CHECK: [[status_alpha_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_alpha_s]] 0
// CHECK: OpStore %status [[status_alpha_s]]
// CHECK: [[res_alpha_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_alpha_s]] 1
// CHECK: OpStore %val [[res_alpha_s]]
val = tex1.GatherAlpha(float2(0.5, 0.25), int2(2, 3), status);

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_alpha_o4_s:%[a-zA-Z0-9_]+]] = OpImageSparseGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %int_3 ConstOffsets [[const_offsets]]
// CHECK: [[status_alpha_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_alpha_o4_s]] 0
// CHECK: OpStore %status [[status_alpha_o4_s]]
// CHECK: [[res_alpha_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_alpha_o4_s]] 1
// CHECK: OpStore %val [[res_alpha_o4_s]]
val = tex1.GatherAlpha(float2(0.5, 0.25), int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8), status);

return val;
}
54 changes: 54 additions & 0 deletions tools/clang/test/CodeGenSPIRV/vk.sampledtexture.gather-blue.hlsl
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// RUN: %dxc -T ps_6_0 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability SparseResidency

// CHECK: [[v2fc:%[0-9]+]] = OpConstantComposite %v2float %float_0_5 %float_0_25
// CHECK: [[v2ic:%[0-9]+]] = OpConstantComposite %v2int %int_2 %int_3

// CHECK: [[type_2d_image_1:%[a-zA-Z0-9_]+]] = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: [[type_sampled_image_1:%[a-zA-Z0-9_]+]] = OpTypeSampledImage [[type_2d_image_1]]
// CHECK: [[ptr_type_1:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant [[type_sampled_image_1]]

// CHECK: [[type_struct_result:%[a-zA-Z0-9_]+]] = OpTypeStruct %uint %v4float

// CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpVariable [[ptr_type_1]] UniformConstant

vk::SampledTexture2D<float4> tex1 : register(t1);

float4 main() : SV_Target {
uint status;
float4 val = 0;

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_blue:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_2
// CHECK: OpStore %val [[val_blue]]
val = tex1.GatherBlue(float2(0.5, 0.25));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_blue_o:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_2 ConstOffset [[v2ic]]
// CHECK: OpStore %val [[val_blue_o]]
val = tex1.GatherBlue(float2(0.5, 0.25), int2(2, 3));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_blue_o4:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_2 ConstOffsets [[const_offsets:%[a-zA-Z0-9_]+]]
// CHECK: OpStore %val [[val_blue_o4]]
val = tex1.GatherBlue(float2(0.5, 0.25), int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_blue_s:%[a-zA-Z0-9_]+]] = OpImageSparseGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %int_2 ConstOffset [[v2ic]]
// CHECK: [[status_blue_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_blue_s]] 0
// CHECK: OpStore %status [[status_blue_s]]
// CHECK: [[res_blue_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_blue_s]] 1
// CHECK: OpStore %val [[res_blue_s]]
val = tex1.GatherBlue(float2(0.5, 0.25), int2(2, 3), status);

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_blue_o4_s:%[a-zA-Z0-9_]+]] = OpImageSparseGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %int_2 ConstOffsets [[const_offsets]]
// CHECK: [[status_blue_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_blue_o4_s]] 0
// CHECK: OpStore %status [[status_blue_o4_s]]
// CHECK: [[res_blue_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_blue_o4_s]] 1
// CHECK: OpStore %val [[res_blue_o4_s]]
val = tex1.GatherBlue(float2(0.5, 0.25), int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8), status);

return val;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// RUN: not %dxc -T ps_6_0 -E main -fcgl %s -spirv 2>&1 | FileCheck %s

SamplerComparisonState gSampler : register(s5);

Texture2D<float4> myTexture : register(t1);

float4 main(float2 location: A, float comparator: B) : SV_Target {
return myTexture.GatherCmpAlpha(gSampler, location, comparator, int2(1, 2));
}

// CHECK: :8:22: error: no equivalent for GatherCmpAlpha intrinsic method in Vulkan
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// RUN: not %dxc -T ps_6_0 -E main -fcgl %s -spirv 2>&1 | FileCheck %s

SamplerComparisonState gSampler : register(s5);

Texture2D<float4> myTexture : register(t1);

float4 main(float2 location: A, float comparator: B) : SV_Target {
return myTexture.GatherCmpBlue(gSampler, location, comparator, int2(1, 2));
}

// CHECK: :8:22: error: no equivalent for GatherCmpBlue intrinsic method in Vulkan
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// RUN: not %dxc -T ps_6_0 -E main -fcgl %s -spirv 2>&1 | FileCheck %s

SamplerComparisonState gSampler : register(s5);

Texture2D<float4> myTexture : register(t1);

float4 main(float2 location: A, float comparator: B) : SV_Target {
return myTexture.GatherCmpGreen(gSampler, location, comparator, int2(1, 2));
}

// CHECK: :8:22: error: no equivalent for GatherCmpGreen intrinsic method in Vulkan
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// RUN: %dxc -T ps_6_0 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability SparseResidency

// CHECK: [[v2fc:%[0-9]+]] = OpConstantComposite %v2float %float_0_5 %float_0_25
// CHECK: [[v2ic:%[0-9]+]] = OpConstantComposite %v2int %int_2 %int_3

// CHECK: [[type_2d_image_1:%[a-zA-Z0-9_]+]] = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: [[type_sampled_image_1:%[a-zA-Z0-9_]+]] = OpTypeSampledImage [[type_2d_image_1]]
// CHECK: [[ptr_type_1:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant [[type_sampled_image_1]]

// CHECK: [[type_struct_result:%[a-zA-Z0-9_]+]] = OpTypeStruct %uint %v4float

// CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpVariable [[ptr_type_1]] UniformConstant

vk::SampledTexture2D<float4> tex1 : register(t1);

float4 main() : SV_Target {
uint status;
float4 val = 0;

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_red:%[a-zA-Z0-9_]+]] = OpImageDrefGather %v4float [[tex1_load]] [[v2fc]] %float_0_5 None
// CHECK: OpStore %val [[val_red]]
val = tex1.GatherCmpRed(float2(0.5, 0.25), 0.5);

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_red_o:%[a-zA-Z0-9_]+]] = OpImageDrefGather %v4float [[tex1_load]] [[v2fc]] %float_0_5 ConstOffset [[v2ic]]
// CHECK: OpStore %val [[val_red_o]]
val = tex1.GatherCmpRed(float2(0.5, 0.25), 0.5, int2(2, 3));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_red_o4:%[a-zA-Z0-9_]+]] = OpImageDrefGather %v4float [[tex1_load]] [[v2fc]] %float_0_5 ConstOffsets [[const_offsets:%[a-zA-Z0-9_]+]]
// CHECK: OpStore %val [[val_red_o4]]
val = tex1.GatherCmpRed(float2(0.5, 0.25), 0.5, int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_cmp_s:%[a-zA-Z0-9_]+]] = OpImageSparseDrefGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %float_0_5 ConstOffset [[v2ic]]
// CHECK: [[status_cmp_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_cmp_s]] 0
// CHECK: OpStore %status [[status_cmp_s]]
// CHECK: [[res_cmp_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_cmp_s]] 1
// CHECK: OpStore %val [[res_cmp_s]]
val = tex1.GatherCmpRed(float2(0.5, 0.25), 0.5, int2(2, 3), status);

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_cmp_o4_s:%[a-zA-Z0-9_]+]] = OpImageSparseDrefGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %float_0_5 ConstOffsets [[const_offsets]]
// CHECK: [[status_cmp_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_cmp_o4_s]] 0
// CHECK: OpStore %status [[status_cmp_o4_s]]
// CHECK: [[res_cmp_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_cmp_o4_s]] 1
// CHECK: OpStore %val [[res_cmp_o4_s]]
val = tex1.GatherCmpRed(float2(0.5, 0.25), 0.5, int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8), status);

return val;
}
40 changes: 40 additions & 0 deletions tools/clang/test/CodeGenSPIRV/vk.sampledtexture.gather-cmp.hlsl
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
// RUN: %dxc -T ps_6_0 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability SparseResidency

// CHECK: [[v2fc:%[0-9]+]] = OpConstantComposite %v2float %float_0_5 %float_0_25
// CHECK: [[v2ic:%[0-9]+]] = OpConstantComposite %v2int %int_1 %int_2

// CHECK: [[type_2d_image_1:%[a-zA-Z0-9_]+]] = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: [[type_sampled_image_1:%[a-zA-Z0-9_]+]] = OpTypeSampledImage [[type_2d_image_1]]
// CHECK: [[ptr_type_1:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant [[type_sampled_image_1]]
// CHECK: [[type_struct_result:%[a-zA-Z0-9_]+]] = OpTypeStruct %uint %v4float

// CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpVariable [[ptr_type_1]] UniformConstant

vk::SampledTexture2D<float4> tex1 : register(t1);

float4 main() : SV_Target {
uint status;
float4 val = 0;

// CHECK: [[tex1_load_1:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_1:%[a-zA-Z0-9_]+]] = OpImageDrefGather %v4float [[tex1_load_1]] [[v2fc]] %float_0_5
// CHECK: OpStore %val [[val_1]]
val = tex1.GatherCmp(float2(0.5, 0.25), 0.5);

// CHECK: [[tex1_load_2:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_2:%[a-zA-Z0-9_]+]] = OpImageDrefGather %v4float [[tex1_load_2]] [[v2fc]] %float_0_5 ConstOffset [[v2ic]]
// CHECK: OpStore %val [[val_2]]
val = tex1.GatherCmp(float2(0.5, 0.25), 0.5, int2(1, 2));

// CHECK: [[tex1_load_3:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_struct:%[a-zA-Z0-9_]+]] = OpImageSparseDrefGather [[type_struct_result]] [[tex1_load_3]] [[v2fc]] %float_0_5 ConstOffset [[v2ic]]
// CHECK: [[status_1:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_struct]] 0
// CHECK: OpStore %status [[status_1]]
// CHECK: [[res_1:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_struct]] 1
// CHECK: OpStore %val [[res_1]]
val = tex1.GatherCmp(float2(0.5, 0.25), 0.5, int2(1, 2), status);

return val;
}
54 changes: 54 additions & 0 deletions tools/clang/test/CodeGenSPIRV/vk.sampledtexture.gather-green.hlsl
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// RUN: %dxc -T ps_6_0 -E main -fcgl %s -spirv | FileCheck %s

// CHECK: OpCapability SparseResidency

// CHECK: [[v2fc:%[0-9]+]] = OpConstantComposite %v2float %float_0_5 %float_0_25
// CHECK: [[v2ic:%[0-9]+]] = OpConstantComposite %v2int %int_2 %int_3

// CHECK: [[type_2d_image_1:%[a-zA-Z0-9_]+]] = OpTypeImage %float 2D 0 0 0 1 Unknown
// CHECK: [[type_sampled_image_1:%[a-zA-Z0-9_]+]] = OpTypeSampledImage [[type_2d_image_1]]
// CHECK: [[ptr_type_1:%[a-zA-Z0-9_]+]] = OpTypePointer UniformConstant [[type_sampled_image_1]]

// CHECK: [[type_struct_result:%[a-zA-Z0-9_]+]] = OpTypeStruct %uint %v4float

// CHECK: [[tex1:%[a-zA-Z0-9_]+]] = OpVariable [[ptr_type_1]] UniformConstant

vk::SampledTexture2D<float4> tex1 : register(t1);

float4 main() : SV_Target {
uint status;
float4 val = 0;

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_green:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_1
// CHECK: OpStore %val [[val_green]]
val = tex1.GatherGreen(float2(0.5, 0.25));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_green_o:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_1 ConstOffset [[v2ic]]
// CHECK: OpStore %val [[val_green_o]]
val = tex1.GatherGreen(float2(0.5, 0.25), int2(2, 3));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_green_o4:%[a-zA-Z0-9_]+]] = OpImageGather %v4float [[tex1_load]] [[v2fc]] %int_1 ConstOffsets [[const_offsets:%[a-zA-Z0-9_]+]]
// CHECK: OpStore %val [[val_green_o4]]
val = tex1.GatherGreen(float2(0.5, 0.25), int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8));

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_green_s:%[a-zA-Z0-9_]+]] = OpImageSparseGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %int_1 ConstOffset [[v2ic]]
// CHECK: [[status_green_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_green_s]] 0
// CHECK: OpStore %status [[status_green_s]]
// CHECK: [[res_green_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_green_s]] 1
// CHECK: OpStore %val [[res_green_s]]
val = tex1.GatherGreen(float2(0.5, 0.25), int2(2, 3), status);

// CHECK: [[tex1_load:%[a-zA-Z0-9_]+]] = OpLoad [[type_sampled_image_1]] [[tex1]]
// CHECK: [[val_green_o4_s:%[a-zA-Z0-9_]+]] = OpImageSparseGather [[type_struct_result]] [[tex1_load]] [[v2fc]] %int_1 ConstOffsets [[const_offsets]]
// CHECK: [[status_green_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %uint [[val_green_o4_s]] 0
// CHECK: OpStore %status [[status_green_o4_s]]
// CHECK: [[res_green_o4_s:%[a-zA-Z0-9_]+]] = OpCompositeExtract %v4float [[val_green_o4_s]] 1
// CHECK: OpStore %val [[res_green_o4_s]]
val = tex1.GatherGreen(float2(0.5, 0.25), int2(1, 2), int2(3, 4), int2(5, 6), int2(7, 8), status);

return val;
}
Loading