28 spirv::ImageOperandsAttr attr,
34 return imageOp->
emitError(
"the Image Operands should encode what operands "
35 "follow, as per Image Operands");
38 if (spirv::bitEnumContainsAll(attr.getValue(),
39 spirv::ImageOperands::Lod |
40 spirv::ImageOperands::Grad))
42 "it is invalid to set both the Lod and Grad bits");
49 if (spirv::bitEnumContainsAny(attr.getValue(), spirv::ImageOperands::Bias)) {
50 if (!isa<spirv::ImplicitLodOpInterface>(imageOp))
52 "Bias is only valid with implicit-lod instructions");
54 if (
index + 1 > operands.size())
55 return imageOp->
emitError(
"Bias operand requires 1 argument");
58 return imageOp->
emitError(
"Bias must be a floating-point type scalar");
60 auto samplingOp = cast<spirv::SamplingOpInterface>(imageOp);
61 auto sampledImageType =
62 cast<spirv::SampledImageType>(samplingOp.getSampledImage().getType());
63 auto imageType = cast<spirv::ImageType>(sampledImageType.getImageType());
65 if (!llvm::is_contained({spirv::Dim::Dim1D, spirv::Dim::Dim2D,
66 spirv::Dim::Dim3D, spirv::Dim::Cube},
69 "Bias must only be used with an image type that has "
70 "a dim operand of 1D, 2D, 3D, or Cube");
72 if (imageType.getSamplingInfo() != spirv::ImageSamplingInfo::SingleSampled)
73 return imageOp->
emitError(
"Bias must only be used with an image type "
74 "that has a MS operand of 0");
79 if (spirv::bitEnumContainsAny(attr.getValue(), spirv::ImageOperands::Lod)) {
80 if (!isa<spirv::ExplicitLodOpInterface>(imageOp) &&
81 !isa<spirv::FetchOpInterface>(imageOp))
83 "Lod is only valid with explicit-lod and fetch instructions");
85 if (
index + 1 > operands.size())
86 return imageOp->
emitError(
"Lod operand requires 1 argument");
90 if (isa<spirv::SamplingOpInterface>(imageOp)) {
92 return imageOp->
emitError(
"for sampling operations, Lod must be a "
93 "floating-point type scalar");
95 auto samplingOp = cast<spirv::SamplingOpInterface>(imageOp);
96 auto sampledImageType =
97 cast<spirv::SampledImageType>(samplingOp.getSampledImage().getType());
98 imageType = cast<spirv::ImageType>(sampledImageType.getImageType());
102 "for fetch operations, Lod must be an integer type scalar");
104 auto fetchOp = cast<spirv::FetchOpInterface>(imageOp);
105 imageType = cast<spirv::ImageType>(fetchOp.getImage().getType());
108 if (!llvm::is_contained({spirv::Dim::Dim1D, spirv::Dim::Dim2D,
109 spirv::Dim::Dim3D, spirv::Dim::Cube},
112 "Lod must only be used with an image type that has "
113 "a dim operand of 1D, 2D, 3D, or Cube");
115 if (imageType.
getSamplingInfo() != spirv::ImageSamplingInfo::SingleSampled)
116 return imageOp->
emitError(
"Lod must only be used with an image type that "
117 "has a MS operand of 0");
122 if (spirv::bitEnumContainsAny(attr.getValue(), spirv::ImageOperands::Grad)) {
123 if (!isa<spirv::ExplicitLodOpInterface>(imageOp))
125 "Grad is only valid with explicit-lod instructions");
127 if (
index + 2 > operands.size())
129 "Grad operand requires 2 arguments (scalars or vectors)");
131 auto samplingOp = cast<spirv::SamplingOpInterface>(imageOp);
132 auto sampledImageType =
133 cast<spirv::SampledImageType>(samplingOp.getSampledImage().getType());
134 auto imageType = cast<spirv::ImageType>(sampledImageType.getImageType());
136 if (imageType.getSamplingInfo() != spirv::ImageSamplingInfo::SingleSampled)
137 return imageOp->
emitError(
"Grad must only be used with an image type "
138 "that has a MS operand of 0");
140 int64_t numberOfComponents = 0;
143 dyn_cast<mlir::VectorType>(samplingOp.getCoordinate().getType());
145 numberOfComponents = coordVector.getNumElements();
146 if (imageType.getArrayedInfo() == spirv::ImageArrayedInfo::Arrayed)
147 numberOfComponents -= 1;
149 numberOfComponents = 1;
152 assert(numberOfComponents > 0);
154 auto dXVector = dyn_cast<mlir::VectorType>(operands[
index].
getType());
155 auto dYVector = dyn_cast<mlir::VectorType>(operands[
index + 1].
getType());
156 if (dXVector && dYVector) {
157 if (dXVector.getNumElements() != dYVector.getNumElements() ||
158 dXVector.getNumElements() != numberOfComponents)
160 "number of components of each Grad argument must equal the number "
161 "of components in coordinate, minus the array layer component, if "
167 "Grad arguments must be a vector of floating-point type");
170 if (numberOfComponents != 1)
172 "number of components of each Grad argument must equal the number "
173 "of components in coordinate, minus the array layer component, if "
177 "Grad arguments must be a scalar or vector of floating-point type");
184 spirv::ImageOperands noSupportOperands =
185 spirv::ImageOperands::ConstOffset | spirv::ImageOperands::Offset |
186 spirv::ImageOperands::ConstOffsets | spirv::ImageOperands::Sample |
187 spirv::ImageOperands::MinLod | spirv::ImageOperands::MakeTexelAvailable |
188 spirv::ImageOperands::MakeTexelVisible |
189 spirv::ImageOperands::SignExtend | spirv::ImageOperands::ZeroExtend;
191 assert(!spirv::bitEnumContainsAny(attr.getValue(), noSupportOperands) &&
192 "unimplemented operands of Image Operands");
193 (
void)noSupportOperands;
195 if (
index < operands.size())
197 "too many image operand arguments have been provided");