1 // Copyright (c) 2017 Google Inc.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 // Tests for unique type declaration rules validator.
16
17 #include <sstream>
18 #include <string>
19
20 #include "gmock/gmock.h"
21 #include "test/unit_spirv.h"
22 #include "test/val/val_fixtures.h"
23
24 namespace spvtools {
25 namespace val {
26 namespace {
27
28 using ::testing::HasSubstr;
29 using ::testing::Not;
30
31 using ValidateImage = spvtest::ValidateBase<bool>;
32
GenerateShaderCode(const std::string & body,const std::string & capabilities_and_extensions="",const std::string & execution_model="Fragment",const spv_target_env env=SPV_ENV_UNIVERSAL_1_0,const std::string & memory_model="GLSL450")33 std::string GenerateShaderCode(
34 const std::string& body,
35 const std::string& capabilities_and_extensions = "",
36 const std::string& execution_model = "Fragment",
37 const spv_target_env env = SPV_ENV_UNIVERSAL_1_0,
38 const std::string& memory_model = "GLSL450") {
39 std::ostringstream ss;
40 ss << R"(
41 OpCapability Shader
42 OpCapability InputAttachment
43 OpCapability ImageGatherExtended
44 OpCapability MinLod
45 OpCapability Sampled1D
46 OpCapability ImageQuery
47 OpCapability Int64
48 OpCapability Float64
49 OpCapability SparseResidency
50 OpCapability ImageBuffer
51 )";
52
53 if (env == SPV_ENV_UNIVERSAL_1_0) {
54 ss << "OpCapability SampledRect\n";
55 }
56
57 ss << capabilities_and_extensions;
58 ss << "OpMemoryModel Logical " << memory_model << "\n";
59 ss << "OpEntryPoint " << execution_model << " %main \"main\"\n";
60 if (execution_model == "Fragment") {
61 ss << "OpExecutionMode %main OriginUpperLeft\n";
62 }
63
64 if (env == SPV_ENV_VULKAN_1_0) {
65 ss << R"(
66 OpDecorate %uniform_image_f32_1d_0001 DescriptorSet 0
67 OpDecorate %uniform_image_f32_1d_0001 Binding 0
68 OpDecorate %uniform_image_f32_1d_0002_rgba32f DescriptorSet 0
69 OpDecorate %uniform_image_f32_1d_0002_rgba32f Binding 1
70 OpDecorate %uniform_image_f32_2d_0001 DescriptorSet 0
71 OpDecorate %uniform_image_f32_2d_0001 Binding 2
72 OpDecorate %uniform_image_f32_2d_0010 DescriptorSet 0
73 OpDecorate %uniform_image_f32_2d_0010 Binding 3
74 OpDecorate %uniform_image_u32_2d_0001 DescriptorSet 1
75 OpDecorate %uniform_image_u32_2d_0001 Binding 0
76 OpDecorate %uniform_image_u32_2d_0000 DescriptorSet 1
77 OpDecorate %uniform_image_u32_2d_0000 Binding 1
78 OpDecorate %uniform_image_s32_3d_0001 DescriptorSet 1
79 OpDecorate %uniform_image_s32_3d_0001 Binding 2
80 OpDecorate %uniform_image_f32_2d_0002 DescriptorSet 1
81 OpDecorate %uniform_image_f32_2d_0002 Binding 3
82 OpDecorate %uniform_image_f32_spd_0002 DescriptorSet 2
83 OpDecorate %uniform_image_f32_spd_0002 Binding 0
84 OpDecorate %uniform_image_f32_3d_0111 DescriptorSet 2
85 OpDecorate %uniform_image_f32_3d_0111 Binding 1
86 OpDecorate %uniform_image_f32_cube_0101 DescriptorSet 2
87 OpDecorate %uniform_image_f32_cube_0101 Binding 2
88 OpDecorate %uniform_image_f32_cube_0102_rgba32f DescriptorSet 2
89 OpDecorate %uniform_image_f32_cube_0102_rgba32f Binding 3
90 OpDecorate %uniform_sampler DescriptorSet 3
91 OpDecorate %uniform_sampler Binding 0
92 )";
93 }
94
95 ss << R"(
96 %void = OpTypeVoid
97 %func = OpTypeFunction %void
98 %bool = OpTypeBool
99 %f32 = OpTypeFloat 32
100 %f64 = OpTypeFloat 64
101 %u32 = OpTypeInt 32 0
102 %s32 = OpTypeInt 32 1
103 %u64 = OpTypeInt 64 0
104 %s32vec2 = OpTypeVector %s32 2
105 %u32vec2 = OpTypeVector %u32 2
106 %f32vec2 = OpTypeVector %f32 2
107 %u32vec3 = OpTypeVector %u32 3
108 %s32vec3 = OpTypeVector %s32 3
109 %f32vec3 = OpTypeVector %f32 3
110 %u32vec4 = OpTypeVector %u32 4
111 %s32vec4 = OpTypeVector %s32 4
112 %f32vec4 = OpTypeVector %f32 4
113
114 %f32_0 = OpConstant %f32 0
115 %f32_1 = OpConstant %f32 1
116 %f32_0_5 = OpConstant %f32 0.5
117 %f32_0_25 = OpConstant %f32 0.25
118 %f32_0_75 = OpConstant %f32 0.75
119
120 %f64_0 = OpConstant %f64 0
121 %f64_1 = OpConstant %f64 1
122
123 %s32_0 = OpConstant %s32 0
124 %s32_1 = OpConstant %s32 1
125 %s32_2 = OpConstant %s32 2
126 %s32_3 = OpConstant %s32 3
127 %s32_4 = OpConstant %s32 4
128 %s32_m1 = OpConstant %s32 -1
129
130 %u32_0 = OpConstant %u32 0
131 %u32_1 = OpConstant %u32 1
132 %u32_2 = OpConstant %u32 2
133 %u32_3 = OpConstant %u32 3
134 %u32_4 = OpConstant %u32 4
135
136 %u64_0 = OpConstant %u64 0
137
138 %u32vec2arr4 = OpTypeArray %u32vec2 %u32_4
139 %u32vec2arr3 = OpTypeArray %u32vec2 %u32_3
140 %u32arr4 = OpTypeArray %u32 %u32_4
141 %u32vec3arr4 = OpTypeArray %u32vec3 %u32_4
142
143 %struct_u32_f32vec4 = OpTypeStruct %u32 %f32vec4
144 %struct_u64_f32vec4 = OpTypeStruct %u64 %f32vec4
145 %struct_u32_u32vec4 = OpTypeStruct %u32 %u32vec4
146 %struct_u32_f32vec3 = OpTypeStruct %u32 %f32vec3
147 %struct_f32_f32vec4 = OpTypeStruct %f32 %f32vec4
148 %struct_u32_u32 = OpTypeStruct %u32 %u32
149 %struct_f32_f32 = OpTypeStruct %f32 %f32
150 %struct_u32 = OpTypeStruct %u32
151 %struct_u32_f32_u32 = OpTypeStruct %u32 %f32 %u32
152 %struct_u32_f32vec4_u32 = OpTypeStruct %u32 %f32vec4 %u32
153 %struct_u32_u32arr4 = OpTypeStruct %u32 %u32arr4
154
155 %u32vec2_01 = OpConstantComposite %u32vec2 %u32_0 %u32_1
156 %u32vec2_12 = OpConstantComposite %u32vec2 %u32_1 %u32_2
157 %u32vec3_012 = OpConstantComposite %u32vec3 %u32_0 %u32_1 %u32_2
158 %u32vec3_123 = OpConstantComposite %u32vec3 %u32_1 %u32_2 %u32_3
159 %u32vec4_0123 = OpConstantComposite %u32vec4 %u32_0 %u32_1 %u32_2 %u32_3
160 %u32vec4_1234 = OpConstantComposite %u32vec4 %u32_1 %u32_2 %u32_3 %u32_4
161
162 %s32vec2_01 = OpConstantComposite %s32vec2 %s32_0 %s32_1
163 %s32vec2_12 = OpConstantComposite %s32vec2 %s32_1 %s32_2
164 %s32vec3_012 = OpConstantComposite %s32vec3 %s32_0 %s32_1 %s32_2
165 %s32vec3_123 = OpConstantComposite %s32vec3 %s32_1 %s32_2 %s32_3
166 %s32vec4_0123 = OpConstantComposite %s32vec4 %s32_0 %s32_1 %s32_2 %s32_3
167 %s32vec4_1234 = OpConstantComposite %s32vec4 %s32_1 %s32_2 %s32_3 %s32_4
168
169 %f32vec2_00 = OpConstantComposite %f32vec2 %f32_0 %f32_0
170 %f32vec2_01 = OpConstantComposite %f32vec2 %f32_0 %f32_1
171 %f32vec2_10 = OpConstantComposite %f32vec2 %f32_1 %f32_0
172 %f32vec2_11 = OpConstantComposite %f32vec2 %f32_1 %f32_1
173 %f32vec2_hh = OpConstantComposite %f32vec2 %f32_0_5 %f32_0_5
174
175 %f32vec3_000 = OpConstantComposite %f32vec3 %f32_0 %f32_0 %f32_0
176 %f32vec3_hhh = OpConstantComposite %f32vec3 %f32_0_5 %f32_0_5 %f32_0_5
177
178 %f32vec4_0000 = OpConstantComposite %f32vec4 %f32_0 %f32_0 %f32_0 %f32_0
179
180 %const_offsets = OpConstantComposite %u32vec2arr4 %u32vec2_01 %u32vec2_12 %u32vec2_01 %u32vec2_12
181 %const_offsets3x2 = OpConstantComposite %u32vec2arr3 %u32vec2_01 %u32vec2_12 %u32vec2_01
182 %const_offsets4xu = OpConstantComposite %u32arr4 %u32_0 %u32_0 %u32_0 %u32_0
183 %const_offsets4x3 = OpConstantComposite %u32vec3arr4 %u32vec3_012 %u32vec3_012 %u32vec3_012 %u32vec3_012
184
185 %type_image_f32_1d_0001 = OpTypeImage %f32 1D 0 0 0 1 Unknown
186 %ptr_image_f32_1d_0001 = OpTypePointer UniformConstant %type_image_f32_1d_0001
187 %uniform_image_f32_1d_0001 = OpVariable %ptr_image_f32_1d_0001 UniformConstant
188 %type_sampled_image_f32_1d_0001 = OpTypeSampledImage %type_image_f32_1d_0001
189
190 %type_image_f32_1d_0002_rgba32f = OpTypeImage %f32 1D 0 0 0 2 Rgba32f
191 %ptr_image_f32_1d_0002_rgba32f = OpTypePointer UniformConstant %type_image_f32_1d_0002_rgba32f
192 %uniform_image_f32_1d_0002_rgba32f = OpVariable %ptr_image_f32_1d_0002_rgba32f UniformConstant
193 %type_sampled_image_f32_1d_0002_rgba32f = OpTypeSampledImage %type_image_f32_1d_0002_rgba32f
194
195 %type_image_f32_2d_0001 = OpTypeImage %f32 2D 0 0 0 1 Unknown
196 %ptr_image_f32_2d_0001 = OpTypePointer UniformConstant %type_image_f32_2d_0001
197 %uniform_image_f32_2d_0001 = OpVariable %ptr_image_f32_2d_0001 UniformConstant
198 %type_sampled_image_f32_2d_0001 = OpTypeSampledImage %type_image_f32_2d_0001
199
200 %type_image_f32_2d_0010 = OpTypeImage %f32 2D 0 0 1 0 Unknown
201 %ptr_image_f32_2d_0010 = OpTypePointer UniformConstant %type_image_f32_2d_0010
202 %uniform_image_f32_2d_0010 = OpVariable %ptr_image_f32_2d_0010 UniformConstant
203 %type_sampled_image_f32_2d_0010 = OpTypeSampledImage %type_image_f32_2d_0010
204
205 %type_image_u32_2d_0001 = OpTypeImage %u32 2D 0 0 0 1 Unknown
206 %ptr_image_u32_2d_0001 = OpTypePointer UniformConstant %type_image_u32_2d_0001
207 %uniform_image_u32_2d_0001 = OpVariable %ptr_image_u32_2d_0001 UniformConstant
208 %type_sampled_image_u32_2d_0001 = OpTypeSampledImage %type_image_u32_2d_0001
209
210 %type_image_u32_2d_0000 = OpTypeImage %u32 2D 0 0 0 0 Unknown
211 %ptr_image_u32_2d_0000 = OpTypePointer UniformConstant %type_image_u32_2d_0000
212 %uniform_image_u32_2d_0000 = OpVariable %ptr_image_u32_2d_0000 UniformConstant
213 %type_sampled_image_u32_2d_0000 = OpTypeSampledImage %type_image_u32_2d_0000
214
215 %type_image_s32_3d_0001 = OpTypeImage %s32 3D 0 0 0 1 Unknown
216 %ptr_image_s32_3d_0001 = OpTypePointer UniformConstant %type_image_s32_3d_0001
217 %uniform_image_s32_3d_0001 = OpVariable %ptr_image_s32_3d_0001 UniformConstant
218 %type_sampled_image_s32_3d_0001 = OpTypeSampledImage %type_image_s32_3d_0001
219
220 %type_image_f32_2d_0002 = OpTypeImage %f32 2D 0 0 0 2 Unknown
221 %ptr_image_f32_2d_0002 = OpTypePointer UniformConstant %type_image_f32_2d_0002
222 %uniform_image_f32_2d_0002 = OpVariable %ptr_image_f32_2d_0002 UniformConstant
223 %type_sampled_image_f32_2d_0002 = OpTypeSampledImage %type_image_f32_2d_0002
224
225 %type_image_f32_spd_0002 = OpTypeImage %f32 SubpassData 0 0 0 2 Unknown
226 %ptr_image_f32_spd_0002 = OpTypePointer UniformConstant %type_image_f32_spd_0002
227 %uniform_image_f32_spd_0002 = OpVariable %ptr_image_f32_spd_0002 UniformConstant
228 %type_sampled_image_f32_spd_0002 = OpTypeSampledImage %type_image_f32_spd_0002
229
230 %type_image_f32_3d_0111 = OpTypeImage %f32 3D 0 1 1 1 Unknown
231 %ptr_image_f32_3d_0111 = OpTypePointer UniformConstant %type_image_f32_3d_0111
232 %uniform_image_f32_3d_0111 = OpVariable %ptr_image_f32_3d_0111 UniformConstant
233 %type_sampled_image_f32_3d_0111 = OpTypeSampledImage %type_image_f32_3d_0111
234
235 %type_image_f32_cube_0101 = OpTypeImage %f32 Cube 0 1 0 1 Unknown
236 %ptr_image_f32_cube_0101 = OpTypePointer UniformConstant %type_image_f32_cube_0101
237 %uniform_image_f32_cube_0101 = OpVariable %ptr_image_f32_cube_0101 UniformConstant
238 %type_sampled_image_f32_cube_0101 = OpTypeSampledImage %type_image_f32_cube_0101
239
240 %type_image_f32_cube_0102_rgba32f = OpTypeImage %f32 Cube 0 1 0 2 Rgba32f
241 %ptr_image_f32_cube_0102_rgba32f = OpTypePointer UniformConstant %type_image_f32_cube_0102_rgba32f
242 %uniform_image_f32_cube_0102_rgba32f = OpVariable %ptr_image_f32_cube_0102_rgba32f UniformConstant
243 %type_sampled_image_f32_cube_0102_rgba32f = OpTypeSampledImage %type_image_f32_cube_0102_rgba32f
244
245 %type_sampler = OpTypeSampler
246 %ptr_sampler = OpTypePointer UniformConstant %type_sampler
247 %uniform_sampler = OpVariable %ptr_sampler UniformConstant
248
249 %type_image_u32_buffer_0002_r32ui = OpTypeImage %u32 Buffer 0 0 0 2 R32ui
250 %ptr_Image_u32 = OpTypePointer Image %u32
251 %ptr_image_u32_buffer_0002_r32ui = OpTypePointer Private %type_image_u32_buffer_0002_r32ui
252 %private_image_u32_buffer_0002_r32ui = OpVariable %ptr_image_u32_buffer_0002_r32ui Private
253
254 %ptr_Image_u32arr4 = OpTypePointer Image %u32arr4
255
256 %type_image_u32_spd_0002 = OpTypeImage %u32 SubpassData 0 0 0 2 Unknown
257 %ptr_image_u32_spd_0002 = OpTypePointer Private %type_image_u32_spd_0002
258 %private_image_u32_spd_0002 = OpVariable %ptr_image_u32_spd_0002 Private
259
260 %type_image_f32_buffer_0002_r32ui = OpTypeImage %f32 Buffer 0 0 0 2 R32ui
261 %ptr_Image_f32 = OpTypePointer Image %f32
262 %ptr_image_f32_buffer_0002_r32ui = OpTypePointer Private %type_image_f32_buffer_0002_r32ui
263 %private_image_f32_buffer_0002_r32ui = OpVariable %ptr_image_f32_buffer_0002_r32ui Private
264 )";
265
266 if (env == SPV_ENV_UNIVERSAL_1_0) {
267 ss << R"(
268 %type_image_void_2d_0001 = OpTypeImage %void 2D 0 0 0 1 Unknown
269 %ptr_image_void_2d_0001 = OpTypePointer UniformConstant %type_image_void_2d_0001
270 %uniform_image_void_2d_0001 = OpVariable %ptr_image_void_2d_0001 UniformConstant
271 %type_sampled_image_void_2d_0001 = OpTypeSampledImage %type_image_void_2d_0001
272
273 %type_image_void_2d_0002 = OpTypeImage %void 2D 0 0 0 2 Unknown
274 %ptr_image_void_2d_0002 = OpTypePointer UniformConstant %type_image_void_2d_0002
275 %uniform_image_void_2d_0002 = OpVariable %ptr_image_void_2d_0002 UniformConstant
276 %type_sampled_image_void_2d_0002 = OpTypeSampledImage %type_image_void_2d_0002
277
278 %type_image_f32_rect_0001 = OpTypeImage %f32 Rect 0 0 0 1 Unknown
279 %ptr_image_f32_rect_0001 = OpTypePointer UniformConstant %type_image_f32_rect_0001
280 %uniform_image_f32_rect_0001 = OpVariable %ptr_image_f32_rect_0001 UniformConstant
281 %type_sampled_image_f32_rect_0001 = OpTypeSampledImage %type_image_f32_rect_0001
282 )";
283 }
284
285 ss << R"(
286 %main = OpFunction %void None %func
287 %main_entry = OpLabel
288 )";
289
290 ss << body;
291
292 ss << R"(
293 OpReturn
294 OpFunctionEnd)";
295
296 return ss.str();
297 }
298
GenerateKernelCode(const std::string & body,const std::string & capabilities_and_extensions="")299 std::string GenerateKernelCode(
300 const std::string& body,
301 const std::string& capabilities_and_extensions = "") {
302 std::ostringstream ss;
303 ss << R"(
304 OpCapability Addresses
305 OpCapability Kernel
306 OpCapability Linkage
307 OpCapability ImageQuery
308 OpCapability ImageGatherExtended
309 OpCapability InputAttachment
310 OpCapability SampledRect
311 )";
312
313 ss << capabilities_and_extensions;
314 ss << R"(
315 OpMemoryModel Physical32 OpenCL
316 %void = OpTypeVoid
317 %func = OpTypeFunction %void
318 %bool = OpTypeBool
319 %f32 = OpTypeFloat 32
320 %u32 = OpTypeInt 32 0
321 %u32vec2 = OpTypeVector %u32 2
322 %f32vec2 = OpTypeVector %f32 2
323 %u32vec3 = OpTypeVector %u32 3
324 %f32vec3 = OpTypeVector %f32 3
325 %u32vec4 = OpTypeVector %u32 4
326 %f32vec4 = OpTypeVector %f32 4
327
328 %f32_0 = OpConstant %f32 0
329 %f32_1 = OpConstant %f32 1
330 %f32_0_5 = OpConstant %f32 0.5
331 %f32_0_25 = OpConstant %f32 0.25
332 %f32_0_75 = OpConstant %f32 0.75
333
334 %u32_0 = OpConstant %u32 0
335 %u32_1 = OpConstant %u32 1
336 %u32_2 = OpConstant %u32 2
337 %u32_3 = OpConstant %u32 3
338 %u32_4 = OpConstant %u32 4
339
340 %u32vec2_01 = OpConstantComposite %u32vec2 %u32_0 %u32_1
341 %u32vec2_12 = OpConstantComposite %u32vec2 %u32_1 %u32_2
342 %u32vec3_012 = OpConstantComposite %u32vec3 %u32_0 %u32_1 %u32_2
343 %u32vec3_123 = OpConstantComposite %u32vec3 %u32_1 %u32_2 %u32_3
344 %u32vec4_0123 = OpConstantComposite %u32vec4 %u32_0 %u32_1 %u32_2 %u32_3
345 %u32vec4_1234 = OpConstantComposite %u32vec4 %u32_1 %u32_2 %u32_3 %u32_4
346
347 %f32vec2_00 = OpConstantComposite %f32vec2 %f32_0 %f32_0
348 %f32vec2_01 = OpConstantComposite %f32vec2 %f32_0 %f32_1
349 %f32vec2_10 = OpConstantComposite %f32vec2 %f32_1 %f32_0
350 %f32vec2_11 = OpConstantComposite %f32vec2 %f32_1 %f32_1
351 %f32vec2_hh = OpConstantComposite %f32vec2 %f32_0_5 %f32_0_5
352
353 %f32vec3_000 = OpConstantComposite %f32vec3 %f32_0 %f32_0 %f32_0
354 %f32vec3_hhh = OpConstantComposite %f32vec3 %f32_0_5 %f32_0_5 %f32_0_5
355
356 %f32vec4_0000 = OpConstantComposite %f32vec4 %f32_0 %f32_0 %f32_0 %f32_0
357
358 %type_image_f32_2d_0001 = OpTypeImage %f32 2D 0 0 0 1 Unknown
359 %ptr_image_f32_2d_0001 = OpTypePointer UniformConstant %type_image_f32_2d_0001
360 %uniform_image_f32_2d_0001 = OpVariable %ptr_image_f32_2d_0001 UniformConstant
361 %type_sampled_image_f32_2d_0001 = OpTypeSampledImage %type_image_f32_2d_0001
362
363 %type_image_f32_2d_0010 = OpTypeImage %f32 2D 0 0 1 0 Unknown
364 %ptr_image_f32_2d_0010 = OpTypePointer UniformConstant %type_image_f32_2d_0010
365 %uniform_image_f32_2d_0010 = OpVariable %ptr_image_f32_2d_0010 UniformConstant
366 %type_sampled_image_f32_2d_0010 = OpTypeSampledImage %type_image_f32_2d_0010
367
368 %type_image_f32_3d_0010 = OpTypeImage %f32 3D 0 0 1 0 Unknown
369 %ptr_image_f32_3d_0010 = OpTypePointer UniformConstant %type_image_f32_3d_0010
370 %uniform_image_f32_3d_0010 = OpVariable %ptr_image_f32_3d_0010 UniformConstant
371 %type_sampled_image_f32_3d_0010 = OpTypeSampledImage %type_image_f32_3d_0010
372
373 %type_image_f32_rect_0001 = OpTypeImage %f32 Rect 0 0 0 1 Unknown
374 %ptr_image_f32_rect_0001 = OpTypePointer UniformConstant %type_image_f32_rect_0001
375 %uniform_image_f32_rect_0001 = OpVariable %ptr_image_f32_rect_0001 UniformConstant
376 %type_sampled_image_f32_rect_0001 = OpTypeSampledImage %type_image_f32_rect_0001
377
378 %type_sampler = OpTypeSampler
379 %ptr_sampler = OpTypePointer UniformConstant %type_sampler
380 %uniform_sampler = OpVariable %ptr_sampler UniformConstant
381
382 %main = OpFunction %void None %func
383 %main_entry = OpLabel
384 )";
385
386 ss << body;
387 ss << R"(
388 OpReturn
389 OpFunctionEnd)";
390
391 return ss.str();
392 }
393
GetShaderHeader(const std::string & capabilities_and_extensions="",bool include_entry_point=true)394 std::string GetShaderHeader(const std::string& capabilities_and_extensions = "",
395 bool include_entry_point = true) {
396 std::ostringstream ss;
397 ss << R"(
398 OpCapability Shader
399 OpCapability Int64
400 )";
401
402 ss << capabilities_and_extensions;
403 if (!include_entry_point) {
404 ss << "OpCapability Linkage";
405 }
406
407 ss << R"(
408 OpMemoryModel Logical GLSL450
409 )";
410
411 if (include_entry_point) {
412 ss << "OpEntryPoint Fragment %main \"main\"\n";
413 ss << "OpExecutionMode %main OriginUpperLeft";
414 }
415 ss << R"(
416 %void = OpTypeVoid
417 %func = OpTypeFunction %void
418 %bool = OpTypeBool
419 %f32 = OpTypeFloat 32
420 %u32 = OpTypeInt 32 0
421 %u64 = OpTypeInt 64 0
422 %s32 = OpTypeInt 32 1
423 )";
424
425 return ss.str();
426 }
427
TEST_F(ValidateImage,TypeImageWrongSampledType)428 TEST_F(ValidateImage, TypeImageWrongSampledType) {
429 const std::string code = GetShaderHeader("", false) + R"(
430 %img_type = OpTypeImage %bool 2D 0 0 0 1 Unknown
431 )";
432
433 CompileSuccessfully(code.c_str());
434 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
435 EXPECT_THAT(getDiagnosticString(),
436 HasSubstr("Expected Sampled Type to be either void or "
437 "numerical scalar "
438 "type"));
439 }
440
TEST_F(ValidateImage,TypeImageVoidSampledTypeVulkan)441 TEST_F(ValidateImage, TypeImageVoidSampledTypeVulkan) {
442 const std::string code = GetShaderHeader() + R"(
443 %img_type = OpTypeImage %void 2D 0 0 0 1 Unknown
444 %void_func = OpTypeFunction %void
445 %main = OpFunction %void None %void_func
446 %main_lab = OpLabel
447 OpReturn
448 OpFunctionEnd
449 )";
450
451 const spv_target_env env = SPV_ENV_VULKAN_1_0;
452 CompileSuccessfully(code, env);
453 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions(env));
454 EXPECT_THAT(getDiagnosticString(),
455 HasSubstr("Expected Sampled Type to be a 32-bit int "
456 "or float scalar type for Vulkan environment"));
457 }
458
TEST_F(ValidateImage,TypeImageU64SampledTypeVulkan)459 TEST_F(ValidateImage, TypeImageU64SampledTypeVulkan) {
460 const std::string code = GetShaderHeader() + R"(
461 %img_type = OpTypeImage %u64 2D 0 0 0 1 Unknown
462 %void_func = OpTypeFunction %void
463 %main = OpFunction %void None %void_func
464 %main_lab = OpLabel
465 OpReturn
466 OpFunctionEnd
467 )";
468
469 const spv_target_env env = SPV_ENV_VULKAN_1_0;
470 CompileSuccessfully(code, env);
471 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions(env));
472 EXPECT_THAT(getDiagnosticString(),
473 HasSubstr("Expected Sampled Type to be a 32-bit int "
474 "or float scalar type for Vulkan environment"));
475 }
476
TEST_F(ValidateImage,TypeImageWrongDepth)477 TEST_F(ValidateImage, TypeImageWrongDepth) {
478 const std::string code = GetShaderHeader("", false) + R"(
479 %img_type = OpTypeImage %f32 2D 3 0 0 1 Unknown
480 )";
481
482 CompileSuccessfully(code.c_str());
483 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
484 EXPECT_THAT(getDiagnosticString(),
485 HasSubstr("Invalid Depth 3 (must be 0, 1 or 2)"));
486 }
487
TEST_F(ValidateImage,TypeImageWrongArrayed)488 TEST_F(ValidateImage, TypeImageWrongArrayed) {
489 const std::string code = GetShaderHeader("", false) + R"(
490 %img_type = OpTypeImage %f32 2D 0 2 0 1 Unknown
491 )";
492
493 CompileSuccessfully(code.c_str());
494 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
495 EXPECT_THAT(getDiagnosticString(),
496 HasSubstr("Invalid Arrayed 2 (must be 0 or 1)"));
497 }
498
TEST_F(ValidateImage,TypeImageWrongMS)499 TEST_F(ValidateImage, TypeImageWrongMS) {
500 const std::string code = GetShaderHeader("", false) + R"(
501 %img_type = OpTypeImage %f32 2D 0 0 2 1 Unknown
502 )";
503
504 CompileSuccessfully(code.c_str());
505 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
506 EXPECT_THAT(getDiagnosticString(),
507 HasSubstr("Invalid MS 2 (must be 0 or 1)"));
508 }
509
TEST_F(ValidateImage,TypeImageWrongSampled)510 TEST_F(ValidateImage, TypeImageWrongSampled) {
511 const std::string code = GetShaderHeader("", false) + R"(
512 %img_type = OpTypeImage %f32 2D 0 0 0 3 Unknown
513 )";
514
515 CompileSuccessfully(code.c_str());
516 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
517 EXPECT_THAT(getDiagnosticString(),
518 HasSubstr("Invalid Sampled 3 (must be 0, 1 or 2)"));
519 }
520
TEST_F(ValidateImage,TypeImageWrongSampledForSubpassData)521 TEST_F(ValidateImage, TypeImageWrongSampledForSubpassData) {
522 const std::string code =
523 GetShaderHeader("OpCapability InputAttachment\n", false) +
524 R"(
525 %img_type = OpTypeImage %f32 SubpassData 0 0 0 1 Unknown
526 )";
527
528 CompileSuccessfully(code.c_str());
529 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
530 EXPECT_THAT(getDiagnosticString(),
531 HasSubstr("Dim SubpassData requires Sampled to be 2"));
532 }
533
TEST_F(ValidateImage,TypeImageWrongFormatForSubpassData)534 TEST_F(ValidateImage, TypeImageWrongFormatForSubpassData) {
535 const std::string code =
536 GetShaderHeader("OpCapability InputAttachment\n", false) +
537 R"(
538 %img_type = OpTypeImage %f32 SubpassData 0 0 0 2 Rgba32f
539 )";
540
541 CompileSuccessfully(code.c_str());
542 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
543 EXPECT_THAT(getDiagnosticString(),
544 HasSubstr("Dim SubpassData requires format Unknown"));
545 }
546
TEST_F(ValidateImage,TypeSampledImageNotImage)547 TEST_F(ValidateImage, TypeSampledImageNotImage) {
548 const std::string code = GetShaderHeader("", false) + R"(
549 %simg_type = OpTypeSampledImage %f32
550 )";
551
552 CompileSuccessfully(code.c_str());
553 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
554 EXPECT_THAT(getDiagnosticString(),
555 HasSubstr("Expected Image to be of type OpTypeImage"));
556 }
557
TEST_F(ValidateImage,SampledImageSuccess)558 TEST_F(ValidateImage, SampledImageSuccess) {
559 const std::string body = R"(
560 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
561 %sampler = OpLoad %type_sampler %uniform_sampler
562 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
563 )";
564
565 CompileSuccessfully(GenerateShaderCode(body).c_str());
566 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
567 }
568
TEST_F(ValidateImage,SampledImageVulkanSuccess)569 TEST_F(ValidateImage, SampledImageVulkanSuccess) {
570 const std::string body = R"(
571 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
572 %sampler = OpLoad %type_sampler %uniform_sampler
573 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
574 )";
575
576 const spv_target_env env = SPV_ENV_VULKAN_1_0;
577 CompileSuccessfully(GenerateShaderCode(body, "", "Fragment", env), env);
578 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(env));
579 }
580
TEST_F(ValidateImage,SampledImageWrongResultType)581 TEST_F(ValidateImage, SampledImageWrongResultType) {
582 const std::string body = R"(
583 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
584 %sampler = OpLoad %type_sampler %uniform_sampler
585 %simg = OpSampledImage %type_image_f32_2d_0001 %img %sampler
586 )";
587
588 CompileSuccessfully(GenerateShaderCode(body).c_str());
589 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
590 EXPECT_THAT(getDiagnosticString(),
591 HasSubstr("Expected Result Type to be OpTypeSampledImage"));
592 }
593
TEST_F(ValidateImage,SampledImageNotImage)594 TEST_F(ValidateImage, SampledImageNotImage) {
595 const std::string body = R"(
596 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
597 %sampler = OpLoad %type_sampler %uniform_sampler
598 %simg1 = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
599 %simg2 = OpSampledImage %type_sampled_image_f32_2d_0001 %simg1 %sampler
600 )";
601
602 CompileSuccessfully(GenerateShaderCode(body).c_str());
603 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
604 EXPECT_THAT(getDiagnosticString(),
605 HasSubstr("Expected Image to be of type OpTypeImage"));
606 }
607
TEST_F(ValidateImage,SampledImageImageNotForSampling)608 TEST_F(ValidateImage, SampledImageImageNotForSampling) {
609 const std::string body = R"(
610 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
611 %sampler = OpLoad %type_sampler %uniform_sampler
612 %simg = OpSampledImage %type_sampled_image_f32_2d_0002 %img %sampler
613 )";
614
615 CompileSuccessfully(GenerateShaderCode(body).c_str());
616 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
617 EXPECT_THAT(getDiagnosticString(),
618 HasSubstr("Expected Image 'Sampled' parameter to be 0 or 1"));
619 }
620
TEST_F(ValidateImage,SampledImageVulkanUnknownSampled)621 TEST_F(ValidateImage, SampledImageVulkanUnknownSampled) {
622 const std::string body = R"(
623 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
624 %sampler = OpLoad %type_sampler %uniform_sampler
625 %simg = OpSampledImage %type_sampled_image_u32_2d_0000 %img %sampler
626 )";
627
628 const spv_target_env env = SPV_ENV_VULKAN_1_0;
629 CompileSuccessfully(GenerateShaderCode(body, "", "Fragment", env), env);
630 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions(env));
631 EXPECT_THAT(getDiagnosticString(),
632 HasSubstr("Expected Image 'Sampled' parameter to "
633 "be 1 for Vulkan environment."));
634 }
635
TEST_F(ValidateImage,SampledImageNotSampler)636 TEST_F(ValidateImage, SampledImageNotSampler) {
637 const std::string body = R"(
638 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
639 %sampler = OpLoad %type_sampler %uniform_sampler
640 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %img
641 )";
642
643 CompileSuccessfully(GenerateShaderCode(body).c_str());
644 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
645 EXPECT_THAT(getDiagnosticString(),
646 HasSubstr("Expected Sampler to be of type OpTypeSampler"));
647 }
648
TEST_F(ValidateImage,ImageTexelPointerSuccess)649 TEST_F(ValidateImage, ImageTexelPointerSuccess) {
650 const std::string body = R"(
651 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %private_image_u32_buffer_0002_r32ui %u32_0 %u32_0
652 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
653 )";
654
655 CompileSuccessfully(GenerateShaderCode(body).c_str());
656 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
657 }
658
TEST_F(ValidateImage,ImageTexelPointerResultTypeNotPointer)659 TEST_F(ValidateImage, ImageTexelPointerResultTypeNotPointer) {
660 const std::string body = R"(
661 %texel_ptr = OpImageTexelPointer %type_image_u32_buffer_0002_r32ui %private_image_u32_buffer_0002_r32ui %u32_0 %u32_0
662 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
663 )";
664
665 CompileSuccessfully(GenerateShaderCode(body).c_str());
666 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
667 EXPECT_THAT(getDiagnosticString(),
668 HasSubstr("Expected Result Type to be OpTypePointer"));
669 }
670
TEST_F(ValidateImage,ImageTexelPointerResultTypeNotImageClass)671 TEST_F(ValidateImage, ImageTexelPointerResultTypeNotImageClass) {
672 const std::string body = R"(
673 %texel_ptr = OpImageTexelPointer %ptr_image_f32_cube_0101 %private_image_u32_buffer_0002_r32ui %u32_0 %u32_0
674 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
675 )";
676
677 CompileSuccessfully(GenerateShaderCode(body).c_str());
678 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
679 EXPECT_THAT(getDiagnosticString(),
680 HasSubstr("Expected Result Type to be OpTypePointer whose "
681 "Storage Class operand is Image"));
682 }
683
TEST_F(ValidateImage,ImageTexelPointerResultTypeNotNumericNorVoid)684 TEST_F(ValidateImage, ImageTexelPointerResultTypeNotNumericNorVoid) {
685 const std::string body = R"(
686 %texel_ptr = OpImageTexelPointer %ptr_Image_u32arr4 %private_image_u32_buffer_0002_r32ui %u32_0 %u32_0
687 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
688 )";
689
690 CompileSuccessfully(GenerateShaderCode(body).c_str());
691 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
692 EXPECT_THAT(
693 getDiagnosticString(),
694 HasSubstr("Expected Result Type to be OpTypePointer whose Type operand "
695 "must be a scalar numerical type or OpTypeVoid"));
696 }
697
TEST_F(ValidateImage,ImageTexelPointerImageNotResultTypePointer)698 TEST_F(ValidateImage, ImageTexelPointerImageNotResultTypePointer) {
699 const std::string body = R"(
700 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %type_image_f32_buffer_0002_r32ui %u32_0 %u32_0
701 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
702 )";
703
704 CompileSuccessfully(GenerateShaderCode(body).c_str());
705 ASSERT_EQ(SPV_ERROR_INVALID_ID, ValidateInstructions());
706 EXPECT_THAT(getDiagnosticString(), HasSubstr("Operand 136[%136] cannot be a "
707 "type"));
708 }
709
TEST_F(ValidateImage,ImageTexelPointerImageNotImage)710 TEST_F(ValidateImage, ImageTexelPointerImageNotImage) {
711 const std::string body = R"(
712 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %uniform_sampler %u32_0 %u32_0
713 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
714 )";
715
716 CompileSuccessfully(GenerateShaderCode(body).c_str());
717 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
718 EXPECT_THAT(
719 getDiagnosticString(),
720 HasSubstr("Expected Image to be OpTypePointer with Type OpTypeImage"));
721 }
722
TEST_F(ValidateImage,ImageTexelPointerImageSampledNotResultType)723 TEST_F(ValidateImage, ImageTexelPointerImageSampledNotResultType) {
724 const std::string body = R"(
725 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %uniform_image_f32_cube_0101 %u32_0 %u32_0
726 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
727 )";
728
729 CompileSuccessfully(GenerateShaderCode(body).c_str());
730 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
731 EXPECT_THAT(getDiagnosticString(),
732 HasSubstr("Expected Image 'Sampled Type' to be the same as the "
733 "Type pointed to by Result Type"));
734 }
735
TEST_F(ValidateImage,ImageTexelPointerImageDimSubpassDataBad)736 TEST_F(ValidateImage, ImageTexelPointerImageDimSubpassDataBad) {
737 const std::string body = R"(
738 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %private_image_u32_spd_0002 %u32_0 %u32_0
739 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
740 )";
741
742 CompileSuccessfully(GenerateShaderCode(body).c_str());
743 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
744 EXPECT_THAT(
745 getDiagnosticString(),
746 HasSubstr(
747 "Image Dim SubpassData cannot be used with OpImageTexelPointer"));
748 }
749
TEST_F(ValidateImage,ImageTexelPointerImageCoordTypeBad)750 TEST_F(ValidateImage, ImageTexelPointerImageCoordTypeBad) {
751 const std::string body = R"(
752 %texel_ptr = OpImageTexelPointer %ptr_Image_f32 %private_image_f32_buffer_0002_r32ui %f32_0 %f32_0
753 %sum = OpAtomicIAdd %f32 %texel_ptr %f32_1 %f32_0 %f32_1
754 )";
755
756 CompileSuccessfully(GenerateShaderCode(body).c_str());
757 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
758 EXPECT_THAT(getDiagnosticString(),
759 HasSubstr("Expected Coordinate to be integer scalar or vector"));
760 }
761
TEST_F(ValidateImage,ImageTexelPointerImageCoordSizeBad)762 TEST_F(ValidateImage, ImageTexelPointerImageCoordSizeBad) {
763 const std::string body = R"(
764 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %uniform_image_u32_2d_0000 %u32vec3_012 %u32_0
765 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
766 )";
767
768 CompileSuccessfully(GenerateShaderCode(body).c_str());
769 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
770 EXPECT_THAT(
771 getDiagnosticString(),
772 HasSubstr("Expected Coordinate to have 2 components, but given 3"));
773 }
774
TEST_F(ValidateImage,ImageTexelPointerSampleNotIntScalar)775 TEST_F(ValidateImage, ImageTexelPointerSampleNotIntScalar) {
776 const std::string body = R"(
777 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %private_image_u32_buffer_0002_r32ui %u32_0 %f32_0
778 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
779 )";
780
781 CompileSuccessfully(GenerateShaderCode(body).c_str());
782 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
783 EXPECT_THAT(getDiagnosticString(),
784 HasSubstr("Expected Sample to be integer scalar"));
785 }
786
TEST_F(ValidateImage,ImageTexelPointerSampleNotZeroForImageWithMSZero)787 TEST_F(ValidateImage, ImageTexelPointerSampleNotZeroForImageWithMSZero) {
788 const std::string body = R"(
789 %texel_ptr = OpImageTexelPointer %ptr_Image_u32 %private_image_u32_buffer_0002_r32ui %u32_0 %u32_1
790 %sum = OpAtomicIAdd %u32 %texel_ptr %u32_1 %u32_0 %u32_1
791 )";
792
793 CompileSuccessfully(GenerateShaderCode(body).c_str());
794 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
795 EXPECT_THAT(getDiagnosticString(),
796 HasSubstr("Expected Sample for Image with MS 0 to be a valid "
797 "<id> for the value 0"));
798 }
799
TEST_F(ValidateImage,SampleImplicitLodSuccess)800 TEST_F(ValidateImage, SampleImplicitLodSuccess) {
801 const std::string body = R"(
802 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
803 %sampler = OpLoad %type_sampler %uniform_sampler
804 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
805 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh
806 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Bias %f32_0_25
807 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh ConstOffset %s32vec2_01
808 %res5 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Offset %s32vec2_01
809 %res6 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh MinLod %f32_0_5
810 %res7 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Bias|Offset|MinLod %f32_0_25 %s32vec2_01 %f32_0_5
811 %res8 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh NonPrivateTexelKHR
812 )";
813
814 const std::string extra = R"(
815 OpCapability VulkanMemoryModelKHR
816 OpExtension "SPV_KHR_vulkan_memory_model"
817 )";
818 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
819 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
820 .c_str());
821 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
822 }
823
TEST_F(ValidateImage,SampleImplicitLodWrongResultType)824 TEST_F(ValidateImage, SampleImplicitLodWrongResultType) {
825 const std::string body = R"(
826 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
827 %sampler = OpLoad %type_sampler %uniform_sampler
828 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
829 %res1 = OpImageSampleImplicitLod %f32 %simg %f32vec2_hh
830 )";
831
832 CompileSuccessfully(GenerateShaderCode(body).c_str());
833 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
834 EXPECT_THAT(getDiagnosticString(),
835 HasSubstr("Expected Result Type to be int or float vector type"));
836 }
837
TEST_F(ValidateImage,SampleImplicitLodWrongNumComponentsResultType)838 TEST_F(ValidateImage, SampleImplicitLodWrongNumComponentsResultType) {
839 const std::string body = R"(
840 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
841 %sampler = OpLoad %type_sampler %uniform_sampler
842 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
843 %res1 = OpImageSampleImplicitLod %f32vec3 %simg %f32vec2_hh
844 )";
845
846 CompileSuccessfully(GenerateShaderCode(body).c_str());
847 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
848 EXPECT_THAT(getDiagnosticString(),
849 HasSubstr("Expected Result Type to have 4 components"));
850 }
851
TEST_F(ValidateImage,SampleImplicitLodNotSampledImage)852 TEST_F(ValidateImage, SampleImplicitLodNotSampledImage) {
853 const std::string body = R"(
854 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
855 %res1 = OpImageSampleImplicitLod %f32vec4 %img %f32vec2_hh
856 )";
857
858 CompileSuccessfully(GenerateShaderCode(body).c_str());
859 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
860 EXPECT_THAT(
861 getDiagnosticString(),
862 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
863 }
864
TEST_F(ValidateImage,SampleImplicitLodWrongSampledType)865 TEST_F(ValidateImage, SampleImplicitLodWrongSampledType) {
866 const std::string body = R"(
867 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
868 %sampler = OpLoad %type_sampler %uniform_sampler
869 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
870 %res1 = OpImageSampleImplicitLod %u32vec4 %simg %f32vec2_00
871 )";
872
873 CompileSuccessfully(GenerateShaderCode(body).c_str());
874 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
875 EXPECT_THAT(getDiagnosticString(),
876 HasSubstr("Expected Image 'Sampled Type' to be the same as "
877 "Result Type components"));
878 }
879
TEST_F(ValidateImage,SampleImplicitLodVoidSampledType)880 TEST_F(ValidateImage, SampleImplicitLodVoidSampledType) {
881 const std::string body = R"(
882 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
883 %sampler = OpLoad %type_sampler %uniform_sampler
884 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
885 %res1 = OpImageSampleImplicitLod %u32vec4 %simg %f32vec2_00
886 )";
887
888 CompileSuccessfully(GenerateShaderCode(body).c_str());
889 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
890 }
891
TEST_F(ValidateImage,SampleImplicitLodWrongCoordinateType)892 TEST_F(ValidateImage, SampleImplicitLodWrongCoordinateType) {
893 const std::string body = R"(
894 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
895 %sampler = OpLoad %type_sampler %uniform_sampler
896 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
897 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %img
898 )";
899
900 CompileSuccessfully(GenerateShaderCode(body).c_str());
901 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
902 EXPECT_THAT(getDiagnosticString(),
903 HasSubstr("Expected Coordinate to be float scalar or vector"));
904 }
905
TEST_F(ValidateImage,SampleImplicitLodCoordinateSizeTooSmall)906 TEST_F(ValidateImage, SampleImplicitLodCoordinateSizeTooSmall) {
907 const std::string body = R"(
908 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
909 %sampler = OpLoad %type_sampler %uniform_sampler
910 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
911 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32_0_5
912 )";
913
914 CompileSuccessfully(GenerateShaderCode(body).c_str());
915 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
916 EXPECT_THAT(getDiagnosticString(),
917 HasSubstr("Expected Coordinate to have at least 2 components, "
918 "but given only 1"));
919 }
920
TEST_F(ValidateImage,SampleExplicitLodSuccessShader)921 TEST_F(ValidateImage, SampleExplicitLodSuccessShader) {
922 const std::string body = R"(
923 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
924 %sampler = OpLoad %type_sampler %uniform_sampler
925 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
926 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Lod %f32_1
927 %res2 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_hh Grad %f32vec2_10 %f32vec2_01
928 %res3 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_hh ConstOffset %s32vec2_01
929 %res4 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec3_hhh Offset %s32vec2_01
930 %res5 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_hh Grad|Offset|MinLod %f32vec2_10 %f32vec2_01 %s32vec2_01 %f32_0_5
931 %res6 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Lod|NonPrivateTexelKHR %f32_1
932 )";
933
934 const std::string extra = R"(
935 OpCapability VulkanMemoryModelKHR
936 OpExtension "SPV_KHR_vulkan_memory_model"
937 )";
938 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
939 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
940 .c_str());
941 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
942 }
943
TEST_F(ValidateImage,SampleExplicitLodSuccessKernel)944 TEST_F(ValidateImage, SampleExplicitLodSuccessKernel) {
945 const std::string body = R"(
946 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
947 %sampler = OpLoad %type_sampler %uniform_sampler
948 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
949 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %u32vec4_0123 Lod %f32_1
950 %res2 = OpImageSampleExplicitLod %f32vec4 %simg %u32vec2_01 Grad %f32vec2_10 %f32vec2_01
951 %res3 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_hh ConstOffset %u32vec2_01
952 %res4 = OpImageSampleExplicitLod %f32vec4 %simg %u32vec2_01 Offset %u32vec2_01
953 %res5 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_hh Grad|Offset %f32vec2_10 %f32vec2_01 %u32vec2_01
954 )";
955
956 CompileSuccessfully(GenerateKernelCode(body).c_str());
957 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
958 }
959
TEST_F(ValidateImage,SampleExplicitLodSuccessCubeArrayed)960 TEST_F(ValidateImage, SampleExplicitLodSuccessCubeArrayed) {
961 const std::string body = R"(
962 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
963 %sampler = OpLoad %type_sampler %uniform_sampler
964 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
965 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Grad %f32vec3_hhh %f32vec3_hhh
966 )";
967
968 CompileSuccessfully(GenerateShaderCode(body).c_str());
969 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
970 }
971
TEST_F(ValidateImage,SampleExplicitLodWrongResultType)972 TEST_F(ValidateImage, SampleExplicitLodWrongResultType) {
973 const std::string body = R"(
974 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
975 %sampler = OpLoad %type_sampler %uniform_sampler
976 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
977 %res1 = OpImageSampleExplicitLod %f32 %simg %f32vec2_hh Lod %f32_1
978 )";
979
980 CompileSuccessfully(GenerateShaderCode(body).c_str());
981 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
982 EXPECT_THAT(getDiagnosticString(),
983 HasSubstr("Expected Result Type to be int or float vector type"));
984 }
985
TEST_F(ValidateImage,SampleExplicitLodWrongNumComponentsResultType)986 TEST_F(ValidateImage, SampleExplicitLodWrongNumComponentsResultType) {
987 const std::string body = R"(
988 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
989 %sampler = OpLoad %type_sampler %uniform_sampler
990 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
991 %res1 = OpImageSampleExplicitLod %f32vec3 %simg %f32vec2_hh Lod %f32_1
992 )";
993
994 CompileSuccessfully(GenerateShaderCode(body).c_str());
995 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
996 EXPECT_THAT(getDiagnosticString(),
997 HasSubstr("Expected Result Type to have 4 components"));
998 }
999
TEST_F(ValidateImage,SampleExplicitLodNotSampledImage)1000 TEST_F(ValidateImage, SampleExplicitLodNotSampledImage) {
1001 const std::string body = R"(
1002 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1003 %res1 = OpImageSampleExplicitLod %f32vec4 %img %f32vec2_hh Lod %f32_1
1004 )";
1005
1006 CompileSuccessfully(GenerateShaderCode(body).c_str());
1007 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1008 EXPECT_THAT(
1009 getDiagnosticString(),
1010 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
1011 }
1012
TEST_F(ValidateImage,SampleExplicitLodWrongSampledType)1013 TEST_F(ValidateImage, SampleExplicitLodWrongSampledType) {
1014 const std::string body = R"(
1015 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1016 %sampler = OpLoad %type_sampler %uniform_sampler
1017 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1018 %res1 = OpImageSampleExplicitLod %u32vec4 %simg %f32vec2_00 Lod %f32_1
1019 )";
1020
1021 CompileSuccessfully(GenerateShaderCode(body).c_str());
1022 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1023 EXPECT_THAT(getDiagnosticString(),
1024 HasSubstr("Expected Image 'Sampled Type' to be the same as "
1025 "Result Type components"));
1026 }
1027
TEST_F(ValidateImage,SampleExplicitLodVoidSampledType)1028 TEST_F(ValidateImage, SampleExplicitLodVoidSampledType) {
1029 const std::string body = R"(
1030 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
1031 %sampler = OpLoad %type_sampler %uniform_sampler
1032 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
1033 %res1 = OpImageSampleExplicitLod %u32vec4 %simg %f32vec2_00 Lod %f32_1
1034 )";
1035
1036 CompileSuccessfully(GenerateShaderCode(body).c_str());
1037 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
1038 }
1039
TEST_F(ValidateImage,SampleExplicitLodWrongCoordinateType)1040 TEST_F(ValidateImage, SampleExplicitLodWrongCoordinateType) {
1041 const std::string body = R"(
1042 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1043 %sampler = OpLoad %type_sampler %uniform_sampler
1044 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1045 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %img Lod %f32_1
1046 )";
1047
1048 CompileSuccessfully(GenerateShaderCode(body).c_str());
1049 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1050 EXPECT_THAT(getDiagnosticString(),
1051 HasSubstr("Expected Coordinate to be float scalar or vector"));
1052 }
1053
TEST_F(ValidateImage,SampleExplicitLodCoordinateSizeTooSmall)1054 TEST_F(ValidateImage, SampleExplicitLodCoordinateSizeTooSmall) {
1055 const std::string body = R"(
1056 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1057 %sampler = OpLoad %type_sampler %uniform_sampler
1058 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1059 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32_0_5 Lod %f32_1
1060 )";
1061
1062 CompileSuccessfully(GenerateShaderCode(body).c_str());
1063 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1064 EXPECT_THAT(getDiagnosticString(),
1065 HasSubstr("Expected Coordinate to have at least 2 components, "
1066 "but given only 1"));
1067 }
1068
TEST_F(ValidateImage,SampleExplicitLodBias)1069 TEST_F(ValidateImage, SampleExplicitLodBias) {
1070 const std::string body = R"(
1071 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1072 %sampler = OpLoad %type_sampler %uniform_sampler
1073 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1074 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Bias|Lod %f32_1 %f32_1
1075 )";
1076
1077 CompileSuccessfully(GenerateShaderCode(body).c_str());
1078 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1079 EXPECT_THAT(
1080 getDiagnosticString(),
1081 HasSubstr(
1082 "Image Operand Bias can only be used with ImplicitLod opcodes"));
1083 }
1084
TEST_F(ValidateImage,LodAndGrad)1085 TEST_F(ValidateImage, LodAndGrad) {
1086 const std::string body = R"(
1087 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1088 %sampler = OpLoad %type_sampler %uniform_sampler
1089 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1090 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Lod|Grad %f32_1 %f32vec2_hh %f32vec2_hh
1091 )";
1092
1093 CompileSuccessfully(GenerateShaderCode(body).c_str());
1094 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1095 EXPECT_THAT(
1096 getDiagnosticString(),
1097 HasSubstr(
1098 "Image Operand bits Lod and Grad cannot be set at the same time"));
1099 }
1100
TEST_F(ValidateImage,ImplicitLodWithLod)1101 TEST_F(ValidateImage, ImplicitLodWithLod) {
1102 const std::string body = R"(
1103 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1104 %sampler = OpLoad %type_sampler %uniform_sampler
1105 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1106 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Lod %f32_0_5
1107 )";
1108
1109 CompileSuccessfully(GenerateShaderCode(body).c_str());
1110 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1111 EXPECT_THAT(
1112 getDiagnosticString(),
1113 HasSubstr("Image Operand Lod can only be used with ExplicitLod opcodes "
1114 "and OpImageFetch"));
1115 }
1116
TEST_F(ValidateImage,LodWrongType)1117 TEST_F(ValidateImage, LodWrongType) {
1118 const std::string body = R"(
1119 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1120 %sampler = OpLoad %type_sampler %uniform_sampler
1121 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1122 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Lod %f32vec2_hh)";
1123
1124 CompileSuccessfully(GenerateShaderCode(body).c_str());
1125 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1126 EXPECT_THAT(getDiagnosticString(),
1127 HasSubstr("Expected Image Operand Lod to be float scalar when "
1128 "used with ExplicitLod"));
1129 }
1130
TEST_F(ValidateImage,LodWrongDim)1131 TEST_F(ValidateImage, LodWrongDim) {
1132 const std::string body = R"(
1133 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
1134 %sampler = OpLoad %type_sampler %uniform_sampler
1135 %simg = OpSampledImage %type_sampled_image_f32_rect_0001 %img %sampler
1136 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Lod %f32_0)";
1137
1138 CompileSuccessfully(GenerateShaderCode(body).c_str());
1139 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1140 EXPECT_THAT(getDiagnosticString(),
1141 HasSubstr("Image Operand Lod requires 'Dim' parameter to be 1D, "
1142 "2D, 3D or Cube"));
1143 }
1144
TEST_F(ValidateImage,LodMultisampled)1145 TEST_F(ValidateImage, LodMultisampled) {
1146 const std::string body = R"(
1147 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
1148 %sampler = OpLoad %type_sampler %uniform_sampler
1149 %simg = OpSampledImage %type_sampled_image_f32_2d_0010 %img %sampler
1150 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Lod %f32_0)";
1151
1152 CompileSuccessfully(GenerateShaderCode(body).c_str());
1153 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1154 EXPECT_THAT(getDiagnosticString(),
1155 HasSubstr("Image Operand Lod requires 'MS' parameter to be 0"));
1156 }
1157
TEST_F(ValidateImage,MinLodIncompatible)1158 TEST_F(ValidateImage, MinLodIncompatible) {
1159 const std::string body = R"(
1160 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1161 %sampler = OpLoad %type_sampler %uniform_sampler
1162 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1163 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Lod|MinLod %f32_0 %f32_0)";
1164
1165 CompileSuccessfully(GenerateShaderCode(body).c_str());
1166 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1167 EXPECT_THAT(
1168 getDiagnosticString(),
1169 HasSubstr(
1170 "Image Operand MinLod can only be used with ImplicitLod opcodes or "
1171 "together with Image Operand Grad"));
1172 }
1173
TEST_F(ValidateImage,ImplicitLodWithGrad)1174 TEST_F(ValidateImage, ImplicitLodWithGrad) {
1175 const std::string body = R"(
1176 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1177 %sampler = OpLoad %type_sampler %uniform_sampler
1178 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1179 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Grad %f32vec2_hh %f32vec2_hh
1180 )";
1181
1182 CompileSuccessfully(GenerateShaderCode(body).c_str());
1183 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1184 EXPECT_THAT(
1185 getDiagnosticString(),
1186 HasSubstr(
1187 "Image Operand Grad can only be used with ExplicitLod opcodes"));
1188 }
1189
TEST_F(ValidateImage,SampleImplicitLod3DArrayedMultisampledSuccess)1190 TEST_F(ValidateImage, SampleImplicitLod3DArrayedMultisampledSuccess) {
1191 const std::string body = R"(
1192 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1193 %sampler = OpLoad %type_sampler %uniform_sampler
1194 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1195 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000
1196 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 ConstOffset %s32vec3_012
1197 %res3 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Offset %s32vec3_012
1198 )";
1199
1200 CompileSuccessfully(GenerateShaderCode(body).c_str());
1201 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
1202 }
1203
TEST_F(ValidateImage,SampleImplicitLodCubeArrayedSuccess)1204 TEST_F(ValidateImage, SampleImplicitLodCubeArrayedSuccess) {
1205 const std::string body = R"(
1206 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1207 %sampler = OpLoad %type_sampler %uniform_sampler
1208 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1209 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000
1210 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Bias %f32_0_25
1211 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 MinLod %f32_0_5
1212 %res5 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Bias|MinLod %f32_0_25 %f32_0_5
1213 )";
1214
1215 CompileSuccessfully(GenerateShaderCode(body).c_str());
1216 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
1217 }
1218
TEST_F(ValidateImage,SampleImplicitLodBiasWrongType)1219 TEST_F(ValidateImage, SampleImplicitLodBiasWrongType) {
1220 const std::string body = R"(
1221 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1222 %sampler = OpLoad %type_sampler %uniform_sampler
1223 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1224 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Bias %u32_0
1225 )";
1226
1227 CompileSuccessfully(GenerateShaderCode(body).c_str());
1228 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1229 EXPECT_THAT(getDiagnosticString(),
1230 HasSubstr("Expected Image Operand Bias to be float scalar"));
1231 }
1232
TEST_F(ValidateImage,SampleImplicitLodBiasWrongDim)1233 TEST_F(ValidateImage, SampleImplicitLodBiasWrongDim) {
1234 const std::string body = R"(
1235 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
1236 %sampler = OpLoad %type_sampler %uniform_sampler
1237 %simg = OpSampledImage %type_sampled_image_f32_rect_0001 %img %sampler
1238 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh Bias %f32_0
1239 )";
1240
1241 CompileSuccessfully(GenerateShaderCode(body).c_str());
1242 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1243 EXPECT_THAT(getDiagnosticString(),
1244 HasSubstr("Image Operand Bias requires 'Dim' parameter to be 1D, "
1245 "2D, 3D or Cube"));
1246 }
1247
TEST_F(ValidateImage,SampleImplicitLodBiasMultisampled)1248 TEST_F(ValidateImage, SampleImplicitLodBiasMultisampled) {
1249 const std::string body = R"(
1250 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1251 %sampler = OpLoad %type_sampler %uniform_sampler
1252 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1253 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Bias %f32_0_25
1254 )";
1255
1256 CompileSuccessfully(GenerateShaderCode(body).c_str());
1257 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1258 EXPECT_THAT(getDiagnosticString(),
1259 HasSubstr("Image Operand Bias requires 'MS' parameter to be 0"));
1260 }
1261
TEST_F(ValidateImage,SampleExplicitLodGradDxWrongType)1262 TEST_F(ValidateImage, SampleExplicitLodGradDxWrongType) {
1263 const std::string body = R"(
1264 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1265 %sampler = OpLoad %type_sampler %uniform_sampler
1266 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1267 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Grad %s32vec3_012 %f32vec3_hhh
1268 )";
1269
1270 CompileSuccessfully(GenerateShaderCode(body).c_str());
1271 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1272 EXPECT_THAT(getDiagnosticString(),
1273 HasSubstr("Expected both Image Operand Grad ids to be float "
1274 "scalars or vectors"));
1275 }
1276
TEST_F(ValidateImage,SampleExplicitLodGradDyWrongType)1277 TEST_F(ValidateImage, SampleExplicitLodGradDyWrongType) {
1278 const std::string body = R"(
1279 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1280 %sampler = OpLoad %type_sampler %uniform_sampler
1281 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1282 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Grad %f32vec3_hhh %s32vec3_012
1283 )";
1284
1285 CompileSuccessfully(GenerateShaderCode(body).c_str());
1286 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1287 EXPECT_THAT(getDiagnosticString(),
1288 HasSubstr("Expected both Image Operand Grad ids to be float "
1289 "scalars or vectors"));
1290 }
1291
TEST_F(ValidateImage,SampleExplicitLodGradDxWrongSize)1292 TEST_F(ValidateImage, SampleExplicitLodGradDxWrongSize) {
1293 const std::string body = R"(
1294 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1295 %sampler = OpLoad %type_sampler %uniform_sampler
1296 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1297 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Grad %f32vec2_00 %f32vec3_hhh
1298 )";
1299
1300 CompileSuccessfully(GenerateShaderCode(body).c_str());
1301 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1302 EXPECT_THAT(
1303 getDiagnosticString(),
1304 HasSubstr(
1305 "Expected Image Operand Grad dx to have 3 components, but given 2"));
1306 }
1307
TEST_F(ValidateImage,SampleExplicitLodGradDyWrongSize)1308 TEST_F(ValidateImage, SampleExplicitLodGradDyWrongSize) {
1309 const std::string body = R"(
1310 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1311 %sampler = OpLoad %type_sampler %uniform_sampler
1312 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1313 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Grad %f32vec3_hhh %f32vec2_00
1314 )";
1315
1316 CompileSuccessfully(GenerateShaderCode(body).c_str());
1317 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1318 EXPECT_THAT(
1319 getDiagnosticString(),
1320 HasSubstr(
1321 "Expected Image Operand Grad dy to have 3 components, but given 2"));
1322 }
1323
TEST_F(ValidateImage,SampleExplicitLodGradMultisampled)1324 TEST_F(ValidateImage, SampleExplicitLodGradMultisampled) {
1325 const std::string body = R"(
1326 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1327 %sampler = OpLoad %type_sampler %uniform_sampler
1328 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1329 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec4_0000 Grad %f32vec3_000 %f32vec3_000
1330 )";
1331
1332 CompileSuccessfully(GenerateShaderCode(body).c_str());
1333 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1334 EXPECT_THAT(getDiagnosticString(),
1335 HasSubstr("Image Operand Grad requires 'MS' parameter to be 0"));
1336 }
1337
TEST_F(ValidateImage,SampleImplicitLodConstOffsetCubeDim)1338 TEST_F(ValidateImage, SampleImplicitLodConstOffsetCubeDim) {
1339 const std::string body = R"(
1340 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1341 %sampler = OpLoad %type_sampler %uniform_sampler
1342 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1343 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 ConstOffset %s32vec3_012
1344 )";
1345
1346 CompileSuccessfully(GenerateShaderCode(body).c_str());
1347 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1348 EXPECT_THAT(
1349 getDiagnosticString(),
1350 HasSubstr(
1351 "Image Operand ConstOffset cannot be used with Cube Image 'Dim'"));
1352 }
1353
TEST_F(ValidateImage,SampleImplicitLodConstOffsetWrongType)1354 TEST_F(ValidateImage, SampleImplicitLodConstOffsetWrongType) {
1355 const std::string body = R"(
1356 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1357 %sampler = OpLoad %type_sampler %uniform_sampler
1358 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1359 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 ConstOffset %f32vec3_000
1360 )";
1361
1362 CompileSuccessfully(GenerateShaderCode(body).c_str());
1363 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1364 EXPECT_THAT(
1365 getDiagnosticString(),
1366 HasSubstr(
1367 "Expected Image Operand ConstOffset to be int scalar or vector"));
1368 }
1369
TEST_F(ValidateImage,SampleImplicitLodConstOffsetWrongSize)1370 TEST_F(ValidateImage, SampleImplicitLodConstOffsetWrongSize) {
1371 const std::string body = R"(
1372 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1373 %sampler = OpLoad %type_sampler %uniform_sampler
1374 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1375 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 ConstOffset %s32vec2_01
1376 )";
1377
1378 CompileSuccessfully(GenerateShaderCode(body).c_str());
1379 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1380 EXPECT_THAT(getDiagnosticString(),
1381 HasSubstr("Expected Image Operand ConstOffset to have 3 "
1382 "components, but given 2"));
1383 }
1384
TEST_F(ValidateImage,SampleImplicitLodConstOffsetNotConst)1385 TEST_F(ValidateImage, SampleImplicitLodConstOffsetNotConst) {
1386 const std::string body = R"(
1387 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1388 %sampler = OpLoad %type_sampler %uniform_sampler
1389 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1390 %offset = OpSNegate %s32vec3 %s32vec3_012
1391 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 ConstOffset %offset
1392 )";
1393
1394 CompileSuccessfully(GenerateShaderCode(body).c_str());
1395 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1396 EXPECT_THAT(
1397 getDiagnosticString(),
1398 HasSubstr("Expected Image Operand ConstOffset to be a const object"));
1399 }
1400
TEST_F(ValidateImage,SampleImplicitLodOffsetCubeDim)1401 TEST_F(ValidateImage, SampleImplicitLodOffsetCubeDim) {
1402 const std::string body = R"(
1403 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1404 %sampler = OpLoad %type_sampler %uniform_sampler
1405 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1406 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Offset %s32vec3_012
1407 )";
1408
1409 CompileSuccessfully(GenerateShaderCode(body).c_str());
1410 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1411 EXPECT_THAT(
1412 getDiagnosticString(),
1413 HasSubstr("Image Operand Offset cannot be used with Cube Image 'Dim'"));
1414 }
1415
TEST_F(ValidateImage,SampleImplicitLodOffsetWrongType)1416 TEST_F(ValidateImage, SampleImplicitLodOffsetWrongType) {
1417 const std::string body = R"(
1418 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1419 %sampler = OpLoad %type_sampler %uniform_sampler
1420 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1421 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Offset %f32vec3_000
1422 )";
1423
1424 CompileSuccessfully(GenerateShaderCode(body).c_str());
1425 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1426 EXPECT_THAT(
1427 getDiagnosticString(),
1428 HasSubstr("Expected Image Operand Offset to be int scalar or vector"));
1429 }
1430
TEST_F(ValidateImage,SampleImplicitLodOffsetWrongSize)1431 TEST_F(ValidateImage, SampleImplicitLodOffsetWrongSize) {
1432 const std::string body = R"(
1433 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1434 %sampler = OpLoad %type_sampler %uniform_sampler
1435 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1436 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 Offset %s32vec2_01
1437 )";
1438
1439 CompileSuccessfully(GenerateShaderCode(body).c_str());
1440 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1441 EXPECT_THAT(
1442 getDiagnosticString(),
1443 HasSubstr(
1444 "Expected Image Operand Offset to have 3 components, but given 2"));
1445 }
1446
TEST_F(ValidateImage,SampleImplicitLodMoreThanOneOffset)1447 TEST_F(ValidateImage, SampleImplicitLodMoreThanOneOffset) {
1448 const std::string body = R"(
1449 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1450 %sampler = OpLoad %type_sampler %uniform_sampler
1451 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1452 %res4 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 ConstOffset|Offset %s32vec3_012 %s32vec3_012
1453 )";
1454
1455 CompileSuccessfully(GenerateShaderCode(body).c_str());
1456 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1457 EXPECT_THAT(getDiagnosticString(),
1458 HasSubstr("Image Operands Offset, ConstOffset, ConstOffsets "
1459 "cannot be used together"));
1460 }
1461
TEST_F(ValidateImage,SampleImplicitLodMinLodWrongType)1462 TEST_F(ValidateImage, SampleImplicitLodMinLodWrongType) {
1463 const std::string body = R"(
1464 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
1465 %sampler = OpLoad %type_sampler %uniform_sampler
1466 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
1467 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 MinLod %s32_0
1468 )";
1469
1470 CompileSuccessfully(GenerateShaderCode(body).c_str());
1471 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1472 EXPECT_THAT(getDiagnosticString(),
1473 HasSubstr("Expected Image Operand MinLod to be float scalar"));
1474 }
1475
TEST_F(ValidateImage,SampleImplicitLodMinLodWrongDim)1476 TEST_F(ValidateImage, SampleImplicitLodMinLodWrongDim) {
1477 const std::string body = R"(
1478 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
1479 %sampler = OpLoad %type_sampler %uniform_sampler
1480 %simg = OpSampledImage %type_sampled_image_f32_rect_0001 %img %sampler
1481 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh MinLod %f32_0_25
1482 )";
1483
1484 CompileSuccessfully(GenerateShaderCode(body).c_str());
1485 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1486 EXPECT_THAT(getDiagnosticString(),
1487 HasSubstr("Image Operand MinLod requires 'Dim' parameter to be "
1488 "1D, 2D, 3D or Cube"));
1489 }
1490
TEST_F(ValidateImage,SampleImplicitLodMinLodMultisampled)1491 TEST_F(ValidateImage, SampleImplicitLodMinLodMultisampled) {
1492 const std::string body = R"(
1493 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
1494 %sampler = OpLoad %type_sampler %uniform_sampler
1495 %simg = OpSampledImage %type_sampled_image_f32_3d_0111 %img %sampler
1496 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec4_0000 MinLod %f32_0_25
1497 )";
1498
1499 CompileSuccessfully(GenerateShaderCode(body).c_str());
1500 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1501 EXPECT_THAT(
1502 getDiagnosticString(),
1503 HasSubstr("Image Operand MinLod requires 'MS' parameter to be 0"));
1504 }
1505
TEST_F(ValidateImage,SampleProjExplicitLodSuccess2D)1506 TEST_F(ValidateImage, SampleProjExplicitLodSuccess2D) {
1507 const std::string body = R"(
1508 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1509 %sampler = OpLoad %type_sampler %uniform_sampler
1510 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1511 %res1 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Lod %f32_1
1512 %res3 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Grad %f32vec2_10 %f32vec2_01
1513 %res4 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh ConstOffset %s32vec2_01
1514 %res5 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Offset %s32vec2_01
1515 %res7 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Grad|Offset %f32vec2_10 %f32vec2_01 %s32vec2_01
1516 %res8 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Lod|NonPrivateTexelKHR %f32_1
1517 )";
1518
1519 const std::string extra = R"(
1520 OpCapability VulkanMemoryModelKHR
1521 OpExtension "SPV_KHR_vulkan_memory_model"
1522 )";
1523 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
1524 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
1525 .c_str());
1526 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
1527 }
1528
TEST_F(ValidateImage,SampleProjExplicitLodSuccessRect)1529 TEST_F(ValidateImage, SampleProjExplicitLodSuccessRect) {
1530 const std::string body = R"(
1531 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
1532 %sampler = OpLoad %type_sampler %uniform_sampler
1533 %simg = OpSampledImage %type_sampled_image_f32_rect_0001 %img %sampler
1534 %res1 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Grad %f32vec2_10 %f32vec2_01
1535 %res2 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec3_hhh Grad|Offset %f32vec2_10 %f32vec2_01 %s32vec2_01
1536 )";
1537
1538 CompileSuccessfully(GenerateShaderCode(body).c_str());
1539 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
1540 }
1541
TEST_F(ValidateImage,SampleProjExplicitLodWrongResultType)1542 TEST_F(ValidateImage, SampleProjExplicitLodWrongResultType) {
1543 const std::string body = R"(
1544 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1545 %sampler = OpLoad %type_sampler %uniform_sampler
1546 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1547 %res1 = OpImageSampleProjExplicitLod %f32 %simg %f32vec3_hhh Lod %f32_1
1548 )";
1549
1550 CompileSuccessfully(GenerateShaderCode(body).c_str());
1551 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1552 EXPECT_THAT(getDiagnosticString(),
1553 HasSubstr("Expected Result Type to be int or float vector type"));
1554 }
1555
TEST_F(ValidateImage,SampleProjExplicitLodWrongNumComponentsResultType)1556 TEST_F(ValidateImage, SampleProjExplicitLodWrongNumComponentsResultType) {
1557 const std::string body = R"(
1558 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1559 %sampler = OpLoad %type_sampler %uniform_sampler
1560 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1561 %res1 = OpImageSampleProjExplicitLod %f32vec3 %simg %f32vec3_hhh Lod %f32_1
1562 )";
1563
1564 CompileSuccessfully(GenerateShaderCode(body).c_str());
1565 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1566 EXPECT_THAT(getDiagnosticString(),
1567 HasSubstr("Expected Result Type to have 4 components"));
1568 }
1569
TEST_F(ValidateImage,SampleProjExplicitLodNotSampledImage)1570 TEST_F(ValidateImage, SampleProjExplicitLodNotSampledImage) {
1571 const std::string body = R"(
1572 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1573 %res1 = OpImageSampleProjExplicitLod %f32vec4 %img %f32vec3_hhh Lod %f32_1
1574 )";
1575
1576 CompileSuccessfully(GenerateShaderCode(body).c_str());
1577 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1578 EXPECT_THAT(
1579 getDiagnosticString(),
1580 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
1581 }
1582
TEST_F(ValidateImage,SampleProjExplicitLodWrongSampledType)1583 TEST_F(ValidateImage, SampleProjExplicitLodWrongSampledType) {
1584 const std::string body = R"(
1585 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1586 %sampler = OpLoad %type_sampler %uniform_sampler
1587 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1588 %res1 = OpImageSampleProjExplicitLod %u32vec4 %simg %f32vec3_hhh Lod %f32_1
1589 )";
1590
1591 CompileSuccessfully(GenerateShaderCode(body).c_str());
1592 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1593 EXPECT_THAT(getDiagnosticString(),
1594 HasSubstr("Expected Image 'Sampled Type' to be the same as "
1595 "Result Type components"));
1596 }
1597
TEST_F(ValidateImage,SampleProjExplicitLodVoidSampledType)1598 TEST_F(ValidateImage, SampleProjExplicitLodVoidSampledType) {
1599 const std::string body = R"(
1600 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
1601 %sampler = OpLoad %type_sampler %uniform_sampler
1602 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
1603 %res1 = OpImageSampleProjExplicitLod %u32vec4 %simg %f32vec3_hhh Lod %f32_1
1604 )";
1605
1606 CompileSuccessfully(GenerateShaderCode(body).c_str());
1607 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
1608 }
1609
TEST_F(ValidateImage,SampleProjExplicitLodWrongCoordinateType)1610 TEST_F(ValidateImage, SampleProjExplicitLodWrongCoordinateType) {
1611 const std::string body = R"(
1612 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1613 %sampler = OpLoad %type_sampler %uniform_sampler
1614 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1615 %res1 = OpImageSampleProjExplicitLod %f32vec4 %simg %img Lod %f32_1
1616 )";
1617
1618 CompileSuccessfully(GenerateShaderCode(body).c_str());
1619 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1620 EXPECT_THAT(getDiagnosticString(),
1621 HasSubstr("Expected Coordinate to be float scalar or vector"));
1622 }
1623
TEST_F(ValidateImage,SampleProjExplicitLodCoordinateSizeTooSmall)1624 TEST_F(ValidateImage, SampleProjExplicitLodCoordinateSizeTooSmall) {
1625 const std::string body = R"(
1626 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1627 %sampler = OpLoad %type_sampler %uniform_sampler
1628 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1629 %res1 = OpImageSampleProjExplicitLod %f32vec4 %simg %f32vec2_hh Lod %f32_1
1630 )";
1631
1632 CompileSuccessfully(GenerateShaderCode(body).c_str());
1633 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1634 EXPECT_THAT(getDiagnosticString(),
1635 HasSubstr("Expected Coordinate to have at least 3 components, "
1636 "but given only 2"));
1637 }
1638
TEST_F(ValidateImage,SampleProjImplicitLodSuccess)1639 TEST_F(ValidateImage, SampleProjImplicitLodSuccess) {
1640 const std::string body = R"(
1641 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1642 %sampler = OpLoad %type_sampler %uniform_sampler
1643 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1644 %res1 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh
1645 %res2 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh Bias %f32_0_25
1646 %res4 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh ConstOffset %s32vec2_01
1647 %res5 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh Offset %s32vec2_01
1648 %res6 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh MinLod %f32_0_5
1649 %res7 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh Bias|Offset|MinLod %f32_0_25 %s32vec2_01 %f32_0_5
1650 %res8 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec3_hhh NonPrivateTexelKHR
1651 )";
1652
1653 const std::string extra = R"(
1654 OpCapability VulkanMemoryModelKHR
1655 OpExtension "SPV_KHR_vulkan_memory_model"
1656 )";
1657 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
1658 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
1659 .c_str());
1660 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
1661 }
1662
TEST_F(ValidateImage,SampleProjImplicitLodWrongResultType)1663 TEST_F(ValidateImage, SampleProjImplicitLodWrongResultType) {
1664 const std::string body = R"(
1665 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1666 %sampler = OpLoad %type_sampler %uniform_sampler
1667 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1668 %res1 = OpImageSampleProjImplicitLod %f32 %simg %f32vec3_hhh
1669 )";
1670
1671 CompileSuccessfully(GenerateShaderCode(body).c_str());
1672 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1673 EXPECT_THAT(getDiagnosticString(),
1674 HasSubstr("Expected Result Type to be int or float vector type"));
1675 }
1676
TEST_F(ValidateImage,SampleProjImplicitLodWrongNumComponentsResultType)1677 TEST_F(ValidateImage, SampleProjImplicitLodWrongNumComponentsResultType) {
1678 const std::string body = R"(
1679 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1680 %sampler = OpLoad %type_sampler %uniform_sampler
1681 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1682 %res1 = OpImageSampleProjImplicitLod %f32vec3 %simg %f32vec3_hhh
1683 )";
1684
1685 CompileSuccessfully(GenerateShaderCode(body).c_str());
1686 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1687 EXPECT_THAT(getDiagnosticString(),
1688 HasSubstr("Expected Result Type to have 4 components"));
1689 }
1690
TEST_F(ValidateImage,SampleProjImplicitLodNotSampledImage)1691 TEST_F(ValidateImage, SampleProjImplicitLodNotSampledImage) {
1692 const std::string body = R"(
1693 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1694 %res1 = OpImageSampleProjImplicitLod %f32vec4 %img %f32vec3_hhh
1695 )";
1696
1697 CompileSuccessfully(GenerateShaderCode(body).c_str());
1698 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1699 EXPECT_THAT(
1700 getDiagnosticString(),
1701 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
1702 }
1703
TEST_F(ValidateImage,SampleProjImplicitLodWrongSampledType)1704 TEST_F(ValidateImage, SampleProjImplicitLodWrongSampledType) {
1705 const std::string body = R"(
1706 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1707 %sampler = OpLoad %type_sampler %uniform_sampler
1708 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1709 %res1 = OpImageSampleProjImplicitLod %u32vec4 %simg %f32vec3_hhh
1710 )";
1711
1712 CompileSuccessfully(GenerateShaderCode(body).c_str());
1713 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1714 EXPECT_THAT(getDiagnosticString(),
1715 HasSubstr("Expected Image 'Sampled Type' to be the same as "
1716 "Result Type components"));
1717 }
1718
TEST_F(ValidateImage,SampleProjImplicitLodVoidSampledType)1719 TEST_F(ValidateImage, SampleProjImplicitLodVoidSampledType) {
1720 const std::string body = R"(
1721 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
1722 %sampler = OpLoad %type_sampler %uniform_sampler
1723 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
1724 %res1 = OpImageSampleProjImplicitLod %u32vec4 %simg %f32vec3_hhh
1725 )";
1726
1727 CompileSuccessfully(GenerateShaderCode(body).c_str());
1728 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
1729 }
1730
TEST_F(ValidateImage,SampleProjImplicitLodWrongCoordinateType)1731 TEST_F(ValidateImage, SampleProjImplicitLodWrongCoordinateType) {
1732 const std::string body = R"(
1733 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1734 %sampler = OpLoad %type_sampler %uniform_sampler
1735 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1736 %res1 = OpImageSampleProjImplicitLod %f32vec4 %simg %img
1737 )";
1738
1739 CompileSuccessfully(GenerateShaderCode(body).c_str());
1740 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1741 EXPECT_THAT(getDiagnosticString(),
1742 HasSubstr("Expected Coordinate to be float scalar or vector"));
1743 }
1744
TEST_F(ValidateImage,SampleProjImplicitLodCoordinateSizeTooSmall)1745 TEST_F(ValidateImage, SampleProjImplicitLodCoordinateSizeTooSmall) {
1746 const std::string body = R"(
1747 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1748 %sampler = OpLoad %type_sampler %uniform_sampler
1749 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1750 %res1 = OpImageSampleProjImplicitLod %f32vec4 %simg %f32vec2_hh
1751 )";
1752
1753 CompileSuccessfully(GenerateShaderCode(body).c_str());
1754 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1755 EXPECT_THAT(getDiagnosticString(),
1756 HasSubstr("Expected Coordinate to have at least 3 components, "
1757 "but given only 2"));
1758 }
1759
TEST_F(ValidateImage,SampleDrefImplicitLodSuccess)1760 TEST_F(ValidateImage, SampleDrefImplicitLodSuccess) {
1761 const std::string body = R"(
1762 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
1763 %sampler = OpLoad %type_sampler %uniform_sampler
1764 %simg = OpSampledImage %type_sampled_image_u32_2d_0001 %img %sampler
1765 %res1 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1
1766 %res2 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1 Bias %f32_0_25
1767 %res4 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1 ConstOffset %s32vec2_01
1768 %res5 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1 Offset %s32vec2_01
1769 %res6 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1 MinLod %f32_0_5
1770 %res7 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1 Bias|Offset|MinLod %f32_0_25 %s32vec2_01 %f32_0_5
1771 %res8 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_hh %f32_1 NonPrivateTexelKHR
1772 )";
1773
1774 const std::string extra = R"(
1775 OpCapability VulkanMemoryModelKHR
1776 OpExtension "SPV_KHR_vulkan_memory_model"
1777 )";
1778 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
1779 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
1780 .c_str());
1781 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
1782 }
1783
TEST_F(ValidateImage,SampleDrefImplicitLodWrongResultType)1784 TEST_F(ValidateImage, SampleDrefImplicitLodWrongResultType) {
1785 const std::string body = R"(
1786 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
1787 %sampler = OpLoad %type_sampler %uniform_sampler
1788 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
1789 %res1 = OpImageSampleDrefImplicitLod %void %simg %f32vec2_hh %u32_1
1790 )";
1791
1792 CompileSuccessfully(GenerateShaderCode(body).c_str());
1793 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1794 EXPECT_THAT(getDiagnosticString(),
1795 HasSubstr("Expected Result Type to be int or float scalar type"));
1796 }
1797
TEST_F(ValidateImage,SampleDrefImplicitLodNotSampledImage)1798 TEST_F(ValidateImage, SampleDrefImplicitLodNotSampledImage) {
1799 const std::string body = R"(
1800 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
1801 %res1 = OpImageSampleDrefImplicitLod %u32 %img %f32vec2_hh %u32_1
1802 )";
1803
1804 CompileSuccessfully(GenerateShaderCode(body).c_str());
1805 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1806 EXPECT_THAT(
1807 getDiagnosticString(),
1808 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
1809 }
1810
TEST_F(ValidateImage,SampleDrefImplicitLodWrongSampledType)1811 TEST_F(ValidateImage, SampleDrefImplicitLodWrongSampledType) {
1812 const std::string body = R"(
1813 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
1814 %sampler = OpLoad %type_sampler %uniform_sampler
1815 %simg = OpSampledImage %type_sampled_image_u32_2d_0001 %img %sampler
1816 %res1 = OpImageSampleDrefImplicitLod %f32 %simg %f32vec2_00 %u32_1
1817 )";
1818
1819 CompileSuccessfully(GenerateShaderCode(body).c_str());
1820 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1821 EXPECT_THAT(
1822 getDiagnosticString(),
1823 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
1824 }
1825
TEST_F(ValidateImage,SampleDrefImplicitLodVoidSampledType)1826 TEST_F(ValidateImage, SampleDrefImplicitLodVoidSampledType) {
1827 const std::string body = R"(
1828 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
1829 %sampler = OpLoad %type_sampler %uniform_sampler
1830 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
1831 %res1 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_00 %u32_1
1832 )";
1833
1834 CompileSuccessfully(GenerateShaderCode(body).c_str());
1835 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1836 EXPECT_THAT(
1837 getDiagnosticString(),
1838 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
1839 }
1840
TEST_F(ValidateImage,SampleDrefImplicitLodWrongCoordinateType)1841 TEST_F(ValidateImage, SampleDrefImplicitLodWrongCoordinateType) {
1842 const std::string body = R"(
1843 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
1844 %sampler = OpLoad %type_sampler %uniform_sampler
1845 %simg = OpSampledImage %type_sampled_image_u32_2d_0001 %img %sampler
1846 %res1 = OpImageSampleDrefImplicitLod %u32 %simg %img %u32_1
1847 )";
1848
1849 CompileSuccessfully(GenerateShaderCode(body).c_str());
1850 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1851 EXPECT_THAT(getDiagnosticString(),
1852 HasSubstr("Expected Coordinate to be float scalar or vector"));
1853 }
1854
TEST_F(ValidateImage,SampleDrefImplicitLodCoordinateSizeTooSmall)1855 TEST_F(ValidateImage, SampleDrefImplicitLodCoordinateSizeTooSmall) {
1856 const std::string body = R"(
1857 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
1858 %sampler = OpLoad %type_sampler %uniform_sampler
1859 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
1860 %res1 = OpImageSampleDrefImplicitLod %f32 %simg %f32_0_5 %f32_0_5
1861 )";
1862
1863 CompileSuccessfully(GenerateShaderCode(body).c_str());
1864 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1865 EXPECT_THAT(getDiagnosticString(),
1866 HasSubstr("Expected Coordinate to have at least 2 components, "
1867 "but given only 1"));
1868 }
1869
TEST_F(ValidateImage,SampleDrefImplicitLodWrongDrefType)1870 TEST_F(ValidateImage, SampleDrefImplicitLodWrongDrefType) {
1871 const std::string body = R"(
1872 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
1873 %sampler = OpLoad %type_sampler %uniform_sampler
1874 %simg = OpSampledImage %type_sampled_image_u32_2d_0001 %img %sampler
1875 %res1 = OpImageSampleDrefImplicitLod %u32 %simg %f32vec2_00 %f64_1
1876 )";
1877
1878 CompileSuccessfully(GenerateShaderCode(body).c_str());
1879 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1880 EXPECT_THAT(getDiagnosticString(),
1881 HasSubstr("Expected Dref to be of 32-bit float type"));
1882 }
1883
TEST_F(ValidateImage,SampleDrefExplicitLodSuccess)1884 TEST_F(ValidateImage, SampleDrefExplicitLodSuccess) {
1885 const std::string body = R"(
1886 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1887 %sampler = OpLoad %type_sampler %uniform_sampler
1888 %simg = OpSampledImage %type_sampled_image_s32_3d_0001 %img %sampler
1889 %res1 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec4_0000 %f32_1 Lod %f32_1
1890 %res3 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec3_hhh %f32_1 Grad %f32vec3_hhh %f32vec3_hhh
1891 %res4 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec3_hhh %f32_1 ConstOffset %s32vec3_012
1892 %res5 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec4_0000 %f32_1 Offset %s32vec3_012
1893 %res7 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec3_hhh %f32_1 Grad|Offset %f32vec3_hhh %f32vec3_hhh %s32vec3_012
1894 %res8 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec4_0000 %f32_1 Lod|NonPrivateTexelKHR %f32_1
1895 )";
1896
1897 const std::string extra = R"(
1898 OpCapability VulkanMemoryModelKHR
1899 OpExtension "SPV_KHR_vulkan_memory_model"
1900 )";
1901 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
1902 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
1903 .c_str());
1904 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
1905 }
1906
TEST_F(ValidateImage,SampleDrefExplicitLodWrongResultType)1907 TEST_F(ValidateImage, SampleDrefExplicitLodWrongResultType) {
1908 const std::string body = R"(
1909 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1910 %sampler = OpLoad %type_sampler %uniform_sampler
1911 %simg = OpSampledImage %type_sampled_image_s32_3d_0001 %img %sampler
1912 %res1 = OpImageSampleDrefExplicitLod %bool %simg %f32vec3_hhh %s32_1 Lod %f32_1
1913 )";
1914
1915 CompileSuccessfully(GenerateShaderCode(body).c_str());
1916 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1917 EXPECT_THAT(getDiagnosticString(),
1918 HasSubstr("Expected Result Type to be int or float scalar type"));
1919 }
1920
TEST_F(ValidateImage,SampleDrefExplicitLodNotSampledImage)1921 TEST_F(ValidateImage, SampleDrefExplicitLodNotSampledImage) {
1922 const std::string body = R"(
1923 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1924 %res1 = OpImageSampleDrefExplicitLod %s32 %img %f32vec3_hhh %s32_1 Lod %f32_1
1925 )";
1926
1927 CompileSuccessfully(GenerateShaderCode(body).c_str());
1928 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1929 EXPECT_THAT(
1930 getDiagnosticString(),
1931 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
1932 }
1933
TEST_F(ValidateImage,SampleDrefExplicitLodWrongSampledType)1934 TEST_F(ValidateImage, SampleDrefExplicitLodWrongSampledType) {
1935 const std::string body = R"(
1936 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1937 %sampler = OpLoad %type_sampler %uniform_sampler
1938 %simg = OpSampledImage %type_sampled_image_s32_3d_0001 %img %sampler
1939 %res1 = OpImageSampleDrefExplicitLod %f32 %simg %f32vec3_hhh %s32_1 Lod %f32_1
1940 )";
1941
1942 CompileSuccessfully(GenerateShaderCode(body).c_str());
1943 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1944 EXPECT_THAT(
1945 getDiagnosticString(),
1946 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
1947 }
1948
TEST_F(ValidateImage,SampleDrefExplicitLodVoidSampledType)1949 TEST_F(ValidateImage, SampleDrefExplicitLodVoidSampledType) {
1950 const std::string body = R"(
1951 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
1952 %sampler = OpLoad %type_sampler %uniform_sampler
1953 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
1954 %res1 = OpImageSampleDrefExplicitLod %u32 %simg %f32vec2_00 %s32_1 Lod %f32_1
1955 )";
1956
1957 CompileSuccessfully(GenerateShaderCode(body).c_str());
1958 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1959 EXPECT_THAT(
1960 getDiagnosticString(),
1961 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
1962 }
1963
TEST_F(ValidateImage,SampleDrefExplicitLodWrongCoordinateType)1964 TEST_F(ValidateImage, SampleDrefExplicitLodWrongCoordinateType) {
1965 const std::string body = R"(
1966 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1967 %sampler = OpLoad %type_sampler %uniform_sampler
1968 %simg = OpSampledImage %type_sampled_image_s32_3d_0001 %img %sampler
1969 %res1 = OpImageSampleDrefExplicitLod %s32 %simg %img %s32_1 Lod %f32_1
1970 )";
1971
1972 CompileSuccessfully(GenerateShaderCode(body).c_str());
1973 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1974 EXPECT_THAT(getDiagnosticString(),
1975 HasSubstr("Expected Coordinate to be float scalar or vector"));
1976 }
1977
TEST_F(ValidateImage,SampleDrefExplicitLodCoordinateSizeTooSmall)1978 TEST_F(ValidateImage, SampleDrefExplicitLodCoordinateSizeTooSmall) {
1979 const std::string body = R"(
1980 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1981 %sampler = OpLoad %type_sampler %uniform_sampler
1982 %simg = OpSampledImage %type_sampled_image_s32_3d_0001 %img %sampler
1983 %res1 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec2_hh %s32_1 Lod %f32_1
1984 )";
1985
1986 CompileSuccessfully(GenerateShaderCode(body).c_str());
1987 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
1988 EXPECT_THAT(getDiagnosticString(),
1989 HasSubstr("Expected Coordinate to have at least 3 components, "
1990 "but given only 2"));
1991 }
1992
TEST_F(ValidateImage,SampleDrefExplicitLodWrongDrefType)1993 TEST_F(ValidateImage, SampleDrefExplicitLodWrongDrefType) {
1994 const std::string body = R"(
1995 %img = OpLoad %type_image_s32_3d_0001 %uniform_image_s32_3d_0001
1996 %sampler = OpLoad %type_sampler %uniform_sampler
1997 %simg = OpSampledImage %type_sampled_image_s32_3d_0001 %img %sampler
1998 %res1 = OpImageSampleDrefExplicitLod %s32 %simg %f32vec3_hhh %u32_1 Lod %f32_1
1999 )";
2000
2001 CompileSuccessfully(GenerateShaderCode(body).c_str());
2002 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2003 EXPECT_THAT(getDiagnosticString(),
2004 HasSubstr("Expected Dref to be of 32-bit float type"));
2005 }
2006
TEST_F(ValidateImage,SampleProjDrefImplicitLodSuccess)2007 TEST_F(ValidateImage, SampleProjDrefImplicitLodSuccess) {
2008 const std::string body = R"(
2009 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2010 %sampler = OpLoad %type_sampler %uniform_sampler
2011 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2012 %res1 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5
2013 %res2 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 Bias %f32_0_25
2014 %res4 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 ConstOffset %s32vec2_01
2015 %res5 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 Offset %s32vec2_01
2016 %res6 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 MinLod %f32_0_5
2017 %res7 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 Bias|Offset|MinLod %f32_0_25 %s32vec2_01 %f32_0_5
2018 %res8 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 NonPrivateTexelKHR
2019 )";
2020
2021 const std::string extra = R"(
2022 OpCapability VulkanMemoryModelKHR
2023 OpExtension "SPV_KHR_vulkan_memory_model"
2024 )";
2025 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
2026 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
2027 .c_str());
2028 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
2029 }
2030
TEST_F(ValidateImage,SampleProjDrefImplicitLodWrongResultType)2031 TEST_F(ValidateImage, SampleProjDrefImplicitLodWrongResultType) {
2032 const std::string body = R"(
2033 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2034 %sampler = OpLoad %type_sampler %uniform_sampler
2035 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2036 %res1 = OpImageSampleProjDrefImplicitLod %void %simg %f32vec3_hhh %f32_0_5
2037 )";
2038
2039 CompileSuccessfully(GenerateShaderCode(body).c_str());
2040 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2041 EXPECT_THAT(getDiagnosticString(),
2042 HasSubstr("Expected Result Type to be int or float scalar type"));
2043 }
2044
TEST_F(ValidateImage,SampleProjDrefImplicitLodNotSampledImage)2045 TEST_F(ValidateImage, SampleProjDrefImplicitLodNotSampledImage) {
2046 const std::string body = R"(
2047 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2048 %res1 = OpImageSampleProjDrefImplicitLod %f32 %img %f32vec3_hhh %f32_0_5
2049 )";
2050
2051 CompileSuccessfully(GenerateShaderCode(body).c_str());
2052 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2053 EXPECT_THAT(
2054 getDiagnosticString(),
2055 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
2056 }
2057
TEST_F(ValidateImage,SampleProjDrefImplicitLodWrongSampledType)2058 TEST_F(ValidateImage, SampleProjDrefImplicitLodWrongSampledType) {
2059 const std::string body = R"(
2060 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2061 %sampler = OpLoad %type_sampler %uniform_sampler
2062 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2063 %res1 = OpImageSampleProjDrefImplicitLod %u32 %simg %f32vec3_hhh %f32_0_5
2064 )";
2065
2066 CompileSuccessfully(GenerateShaderCode(body).c_str());
2067 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2068 EXPECT_THAT(
2069 getDiagnosticString(),
2070 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
2071 }
2072
TEST_F(ValidateImage,SampleProjDrefImplicitLodVoidSampledType)2073 TEST_F(ValidateImage, SampleProjDrefImplicitLodVoidSampledType) {
2074 const std::string body = R"(
2075 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
2076 %sampler = OpLoad %type_sampler %uniform_sampler
2077 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
2078 %res1 = OpImageSampleProjDrefImplicitLod %u32 %simg %f32vec3_hhh %f32_0_5
2079 )";
2080
2081 CompileSuccessfully(GenerateShaderCode(body).c_str());
2082 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2083 EXPECT_THAT(
2084 getDiagnosticString(),
2085 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
2086 }
2087
TEST_F(ValidateImage,SampleProjDrefImplicitLodWrongCoordinateType)2088 TEST_F(ValidateImage, SampleProjDrefImplicitLodWrongCoordinateType) {
2089 const std::string body = R"(
2090 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2091 %sampler = OpLoad %type_sampler %uniform_sampler
2092 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2093 %res1 = OpImageSampleProjDrefImplicitLod %f32 %simg %img %f32_0_5
2094 )";
2095
2096 CompileSuccessfully(GenerateShaderCode(body).c_str());
2097 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2098 EXPECT_THAT(getDiagnosticString(),
2099 HasSubstr("Expected Coordinate to be float scalar or vector"));
2100 }
2101
TEST_F(ValidateImage,SampleProjDrefImplicitLodCoordinateSizeTooSmall)2102 TEST_F(ValidateImage, SampleProjDrefImplicitLodCoordinateSizeTooSmall) {
2103 const std::string body = R"(
2104 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2105 %sampler = OpLoad %type_sampler %uniform_sampler
2106 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2107 %res1 = OpImageSampleProjDrefImplicitLod %f32 %simg %f32vec2_hh %f32_0_5
2108 )";
2109
2110 CompileSuccessfully(GenerateShaderCode(body).c_str());
2111 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2112 EXPECT_THAT(getDiagnosticString(),
2113 HasSubstr("Expected Coordinate to have at least 3 components, "
2114 "but given only 2"));
2115 }
2116
TEST_F(ValidateImage,SampleProjDrefImplicitLodWrongDrefType)2117 TEST_F(ValidateImage, SampleProjDrefImplicitLodWrongDrefType) {
2118 const std::string body = R"(
2119 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
2120 %sampler = OpLoad %type_sampler %uniform_sampler
2121 %simg = OpSampledImage %type_sampled_image_u32_2d_0001 %img %sampler
2122 %res1 = OpImageSampleProjDrefImplicitLod %u32 %simg %f32vec3_hhh %f32vec4_0000
2123 )";
2124
2125 CompileSuccessfully(GenerateShaderCode(body).c_str());
2126 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2127 EXPECT_THAT(getDiagnosticString(),
2128 HasSubstr("Expected Dref to be of 32-bit float type"));
2129 }
2130
TEST_F(ValidateImage,SampleProjDrefExplicitLodSuccess)2131 TEST_F(ValidateImage, SampleProjDrefExplicitLodSuccess) {
2132 const std::string body = R"(
2133 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2134 %sampler = OpLoad %type_sampler %uniform_sampler
2135 %simg = OpSampledImage %type_sampled_image_f32_1d_0001 %img %sampler
2136 %res1 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32vec2_hh %f32_0_5 Lod %f32_1
2137 %res2 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32vec3_hhh %f32_0_5 Grad %f32_0_5 %f32_0_5
2138 %res3 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32vec2_hh %f32_0_5 ConstOffset %s32_1
2139 %res4 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32vec2_hh %f32_0_5 Offset %s32_1
2140 %res5 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32vec2_hh %f32_0_5 Grad|Offset %f32_0_5 %f32_0_5 %s32_1
2141 %res6 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32vec2_hh %f32_0_5 Lod|NonPrivateTexelKHR %f32_1
2142 )";
2143
2144 const std::string extra = R"(
2145 OpCapability VulkanMemoryModelKHR
2146 OpExtension "SPV_KHR_vulkan_memory_model"
2147 )";
2148 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
2149 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
2150 .c_str());
2151 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
2152 }
2153
TEST_F(ValidateImage,SampleProjDrefExplicitLodWrongResultType)2154 TEST_F(ValidateImage, SampleProjDrefExplicitLodWrongResultType) {
2155 const std::string body = R"(
2156 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2157 %sampler = OpLoad %type_sampler %uniform_sampler
2158 %simg = OpSampledImage %type_sampled_image_f32_1d_0001 %img %sampler
2159 %res1 = OpImageSampleProjDrefExplicitLod %bool %simg %f32vec2_hh %f32_0_5 Lod %f32_1
2160 )";
2161
2162 CompileSuccessfully(GenerateShaderCode(body).c_str());
2163 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2164 EXPECT_THAT(getDiagnosticString(),
2165 HasSubstr("Expected Result Type to be int or float scalar type"));
2166 }
2167
TEST_F(ValidateImage,SampleProjDrefExplicitLodNotSampledImage)2168 TEST_F(ValidateImage, SampleProjDrefExplicitLodNotSampledImage) {
2169 const std::string body = R"(
2170 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2171 %res1 = OpImageSampleProjDrefExplicitLod %f32 %img %f32vec2_hh %f32_0_5 Lod %f32_1
2172 )";
2173
2174 CompileSuccessfully(GenerateShaderCode(body).c_str());
2175 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2176 EXPECT_THAT(
2177 getDiagnosticString(),
2178 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
2179 }
2180
TEST_F(ValidateImage,SampleProjDrefExplicitLodWrongSampledType)2181 TEST_F(ValidateImage, SampleProjDrefExplicitLodWrongSampledType) {
2182 const std::string body = R"(
2183 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2184 %sampler = OpLoad %type_sampler %uniform_sampler
2185 %simg = OpSampledImage %type_sampled_image_f32_1d_0001 %img %sampler
2186 %res1 = OpImageSampleProjDrefExplicitLod %u32 %simg %f32vec2_hh %f32_0_5 Lod %f32_1
2187 )";
2188
2189 CompileSuccessfully(GenerateShaderCode(body).c_str());
2190 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2191 EXPECT_THAT(
2192 getDiagnosticString(),
2193 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
2194 }
2195
TEST_F(ValidateImage,SampleProjDrefExplicitLodVoidSampledType)2196 TEST_F(ValidateImage, SampleProjDrefExplicitLodVoidSampledType) {
2197 const std::string body = R"(
2198 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
2199 %sampler = OpLoad %type_sampler %uniform_sampler
2200 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
2201 %res1 = OpImageSampleProjDrefExplicitLod %u32 %simg %f32vec3_hhh %f32_0_5 Lod %f32_1
2202 )";
2203
2204 CompileSuccessfully(GenerateShaderCode(body).c_str());
2205 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2206 EXPECT_THAT(
2207 getDiagnosticString(),
2208 HasSubstr("Expected Image 'Sampled Type' to be the same as Result Type"));
2209 }
2210
TEST_F(ValidateImage,SampleProjDrefExplicitLodWrongCoordinateType)2211 TEST_F(ValidateImage, SampleProjDrefExplicitLodWrongCoordinateType) {
2212 const std::string body = R"(
2213 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2214 %sampler = OpLoad %type_sampler %uniform_sampler
2215 %simg = OpSampledImage %type_sampled_image_f32_1d_0001 %img %sampler
2216 %res1 = OpImageSampleProjDrefExplicitLod %f32 %simg %img %f32_0_5 Lod %f32_1
2217 )";
2218
2219 CompileSuccessfully(GenerateShaderCode(body).c_str());
2220 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2221 EXPECT_THAT(getDiagnosticString(),
2222 HasSubstr("Expected Coordinate to be float scalar or vector"));
2223 }
2224
TEST_F(ValidateImage,SampleProjDrefExplicitLodCoordinateSizeTooSmall)2225 TEST_F(ValidateImage, SampleProjDrefExplicitLodCoordinateSizeTooSmall) {
2226 const std::string body = R"(
2227 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2228 %sampler = OpLoad %type_sampler %uniform_sampler
2229 %simg = OpSampledImage %type_sampled_image_f32_1d_0001 %img %sampler
2230 %res1 = OpImageSampleProjDrefExplicitLod %f32 %simg %f32_0_5 %f32_0_5 Lod %f32_1
2231 )";
2232
2233 CompileSuccessfully(GenerateShaderCode(body).c_str());
2234 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2235 EXPECT_THAT(getDiagnosticString(),
2236 HasSubstr("Expected Coordinate to have at least 2 components, "
2237 "but given only 1"));
2238 }
2239
TEST_F(ValidateImage,FetchSuccess)2240 TEST_F(ValidateImage, FetchSuccess) {
2241 const std::string body = R"(
2242 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
2243 %res1 = OpImageFetch %f32vec4 %img %u32vec2_01
2244 %res2 = OpImageFetch %f32vec4 %img %u32vec2_01 NonPrivateTexelKHR
2245 )";
2246
2247 const std::string extra = R"(
2248 OpCapability VulkanMemoryModelKHR
2249 OpExtension "SPV_KHR_vulkan_memory_model"
2250 )";
2251 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
2252 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
2253 .c_str());
2254 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
2255 }
2256
TEST_F(ValidateImage,FetchWrongResultType)2257 TEST_F(ValidateImage, FetchWrongResultType) {
2258 const std::string body = R"(
2259 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
2260 %res1 = OpImageFetch %f32 %img %u32vec2_01
2261 )";
2262
2263 CompileSuccessfully(GenerateShaderCode(body).c_str());
2264 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2265 EXPECT_THAT(getDiagnosticString(),
2266 HasSubstr("Expected Result Type to be int or float vector type"));
2267 }
2268
TEST_F(ValidateImage,FetchWrongNumComponentsResultType)2269 TEST_F(ValidateImage, FetchWrongNumComponentsResultType) {
2270 const std::string body = R"(
2271 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
2272 %res1 = OpImageFetch %f32vec3 %img %u32vec2_01
2273 )";
2274
2275 CompileSuccessfully(GenerateShaderCode(body).c_str());
2276 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2277 EXPECT_THAT(getDiagnosticString(),
2278 HasSubstr("Expected Result Type to have 4 components"));
2279 }
2280
TEST_F(ValidateImage,FetchNotImage)2281 TEST_F(ValidateImage, FetchNotImage) {
2282 const std::string body = R"(
2283 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2284 %sampler = OpLoad %type_sampler %uniform_sampler
2285 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2286 %res1 = OpImageFetch %f32vec4 %simg %u32vec2_01
2287 )";
2288
2289 CompileSuccessfully(GenerateShaderCode(body).c_str());
2290 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2291 EXPECT_THAT(getDiagnosticString(),
2292 HasSubstr("Expected Image to be of type OpTypeImage"));
2293 }
2294
TEST_F(ValidateImage,FetchNotSampled)2295 TEST_F(ValidateImage, FetchNotSampled) {
2296 const std::string body = R"(
2297 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2298 %res1 = OpImageFetch %u32vec4 %img %u32vec2_01
2299 )";
2300
2301 CompileSuccessfully(GenerateShaderCode(body).c_str());
2302 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2303 EXPECT_THAT(getDiagnosticString(),
2304 HasSubstr("Expected Image 'Sampled' parameter to be 1"));
2305 }
2306
TEST_F(ValidateImage,FetchCube)2307 TEST_F(ValidateImage, FetchCube) {
2308 const std::string body = R"(
2309 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2310 %res1 = OpImageFetch %f32vec4 %img %u32vec3_012
2311 )";
2312
2313 CompileSuccessfully(GenerateShaderCode(body).c_str());
2314 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2315 EXPECT_THAT(getDiagnosticString(), HasSubstr("Image 'Dim' cannot be Cube"));
2316 }
2317
TEST_F(ValidateImage,FetchWrongSampledType)2318 TEST_F(ValidateImage, FetchWrongSampledType) {
2319 const std::string body = R"(
2320 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
2321 %res1 = OpImageFetch %u32vec4 %img %u32vec2_01
2322 )";
2323
2324 CompileSuccessfully(GenerateShaderCode(body).c_str());
2325 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2326 EXPECT_THAT(getDiagnosticString(),
2327 HasSubstr("Expected Image 'Sampled Type' to be the same as "
2328 "Result Type components"));
2329 }
2330
TEST_F(ValidateImage,FetchVoidSampledType)2331 TEST_F(ValidateImage, FetchVoidSampledType) {
2332 const std::string body = R"(
2333 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
2334 %res1 = OpImageFetch %f32vec4 %img %u32vec2_01
2335 %res2 = OpImageFetch %u32vec4 %img %u32vec2_01
2336 %res3 = OpImageFetch %s32vec4 %img %u32vec2_01
2337 )";
2338
2339 CompileSuccessfully(GenerateShaderCode(body).c_str());
2340 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2341 }
2342
TEST_F(ValidateImage,FetchWrongCoordinateType)2343 TEST_F(ValidateImage, FetchWrongCoordinateType) {
2344 const std::string body = R"(
2345 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
2346 %res1 = OpImageFetch %f32vec4 %img %f32vec2_00
2347 )";
2348
2349 CompileSuccessfully(GenerateShaderCode(body).c_str());
2350 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2351 EXPECT_THAT(getDiagnosticString(),
2352 HasSubstr("Expected Coordinate to be int scalar or vector"));
2353 }
2354
TEST_F(ValidateImage,FetchCoordinateSizeTooSmall)2355 TEST_F(ValidateImage, FetchCoordinateSizeTooSmall) {
2356 const std::string body = R"(
2357 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
2358 %res1 = OpImageFetch %f32vec4 %img %u32_1
2359 )";
2360
2361 CompileSuccessfully(GenerateShaderCode(body).c_str());
2362 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2363 EXPECT_THAT(getDiagnosticString(),
2364 HasSubstr("Expected Coordinate to have at least 2 components, "
2365 "but given only 1"));
2366 }
2367
TEST_F(ValidateImage,FetchLodNotInt)2368 TEST_F(ValidateImage, FetchLodNotInt) {
2369 const std::string body = R"(
2370 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2371 %res1 = OpImageFetch %f32vec4 %img %u32vec2_01 Lod %f32_1
2372 )";
2373
2374 CompileSuccessfully(GenerateShaderCode(body).c_str());
2375 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2376 EXPECT_THAT(getDiagnosticString(),
2377 HasSubstr("Expected Image Operand Lod to be int scalar when used "
2378 "with OpImageFetch"));
2379 }
2380
TEST_F(ValidateImage,GatherSuccess)2381 TEST_F(ValidateImage, GatherSuccess) {
2382 const std::string body = R"(
2383 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2384 %sampler = OpLoad %type_sampler %uniform_sampler
2385 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2386 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1
2387 %res2 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %const_offsets
2388 %res3 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 NonPrivateTexelKHR
2389 )";
2390
2391 const std::string extra = R"(
2392 OpCapability VulkanMemoryModelKHR
2393 OpExtension "SPV_KHR_vulkan_memory_model"
2394 )";
2395 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
2396 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
2397 .c_str());
2398 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
2399 }
2400
TEST_F(ValidateImage,GatherWrongResultType)2401 TEST_F(ValidateImage, GatherWrongResultType) {
2402 const std::string body = R"(
2403 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2404 %sampler = OpLoad %type_sampler %uniform_sampler
2405 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2406 %res1 = OpImageGather %f32 %simg %f32vec4_0000 %u32_1
2407 )";
2408
2409 CompileSuccessfully(GenerateShaderCode(body).c_str());
2410 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2411 EXPECT_THAT(getDiagnosticString(),
2412 HasSubstr("Expected Result Type to be int or float vector type"));
2413 }
2414
TEST_F(ValidateImage,GatherWrongNumComponentsResultType)2415 TEST_F(ValidateImage, GatherWrongNumComponentsResultType) {
2416 const std::string body = R"(
2417 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2418 %sampler = OpLoad %type_sampler %uniform_sampler
2419 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2420 %res1 = OpImageGather %f32vec3 %simg %f32vec4_0000 %u32_1
2421 )";
2422
2423 CompileSuccessfully(GenerateShaderCode(body).c_str());
2424 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2425 EXPECT_THAT(getDiagnosticString(),
2426 HasSubstr("Expected Result Type to have 4 components"));
2427 }
2428
TEST_F(ValidateImage,GatherNotSampledImage)2429 TEST_F(ValidateImage, GatherNotSampledImage) {
2430 const std::string body = R"(
2431 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2432 %res1 = OpImageGather %f32vec4 %img %f32vec4_0000 %u32_1
2433 )";
2434
2435 CompileSuccessfully(GenerateShaderCode(body).c_str());
2436 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2437 EXPECT_THAT(
2438 getDiagnosticString(),
2439 HasSubstr("Expected Sampled Image to be of type OpTypeSampledImage"));
2440 }
2441
TEST_F(ValidateImage,GatherWrongSampledType)2442 TEST_F(ValidateImage, GatherWrongSampledType) {
2443 const std::string body = R"(
2444 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2445 %sampler = OpLoad %type_sampler %uniform_sampler
2446 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2447 %res1 = OpImageGather %u32vec4 %simg %f32vec4_0000 %u32_1
2448 )";
2449
2450 CompileSuccessfully(GenerateShaderCode(body).c_str());
2451 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2452 EXPECT_THAT(getDiagnosticString(),
2453 HasSubstr("Expected Image 'Sampled Type' to be the same as "
2454 "Result Type components"));
2455 }
2456
TEST_F(ValidateImage,GatherVoidSampledType)2457 TEST_F(ValidateImage, GatherVoidSampledType) {
2458 const std::string body = R"(
2459 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
2460 %sampler = OpLoad %type_sampler %uniform_sampler
2461 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
2462 %res1 = OpImageGather %u32vec4 %simg %f32vec2_00 %u32_1
2463 )";
2464
2465 CompileSuccessfully(GenerateShaderCode(body).c_str());
2466 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2467 }
2468
TEST_F(ValidateImage,GatherWrongCoordinateType)2469 TEST_F(ValidateImage, GatherWrongCoordinateType) {
2470 const std::string body = R"(
2471 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2472 %sampler = OpLoad %type_sampler %uniform_sampler
2473 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2474 %res1 = OpImageGather %f32vec4 %simg %u32vec4_0123 %u32_1
2475 )";
2476
2477 CompileSuccessfully(GenerateShaderCode(body).c_str());
2478 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2479 EXPECT_THAT(getDiagnosticString(),
2480 HasSubstr("Expected Coordinate to be float scalar or vector"));
2481 }
2482
TEST_F(ValidateImage,GatherCoordinateSizeTooSmall)2483 TEST_F(ValidateImage, GatherCoordinateSizeTooSmall) {
2484 const std::string body = R"(
2485 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2486 %sampler = OpLoad %type_sampler %uniform_sampler
2487 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2488 %res1 = OpImageGather %f32vec4 %simg %f32_0_5 %u32_1
2489 )";
2490
2491 CompileSuccessfully(GenerateShaderCode(body).c_str());
2492 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2493 EXPECT_THAT(getDiagnosticString(),
2494 HasSubstr("Expected Coordinate to have at least 4 components, "
2495 "but given only 1"));
2496 }
2497
TEST_F(ValidateImage,GatherWrongComponentType)2498 TEST_F(ValidateImage, GatherWrongComponentType) {
2499 const std::string body = R"(
2500 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2501 %sampler = OpLoad %type_sampler %uniform_sampler
2502 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2503 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %f32_1
2504 )";
2505
2506 CompileSuccessfully(GenerateShaderCode(body).c_str());
2507 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2508 EXPECT_THAT(getDiagnosticString(),
2509 HasSubstr("Expected Component to be 32-bit int scalar"));
2510 }
2511
TEST_F(ValidateImage,GatherComponentNot32Bit)2512 TEST_F(ValidateImage, GatherComponentNot32Bit) {
2513 const std::string body = R"(
2514 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2515 %sampler = OpLoad %type_sampler %uniform_sampler
2516 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2517 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u64_0
2518 )";
2519
2520 CompileSuccessfully(GenerateShaderCode(body).c_str());
2521 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2522 EXPECT_THAT(getDiagnosticString(),
2523 HasSubstr("Expected Component to be 32-bit int scalar"));
2524 }
2525
TEST_F(ValidateImage,GatherDimCube)2526 TEST_F(ValidateImage, GatherDimCube) {
2527 const std::string body = R"(
2528 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2529 %sampler = OpLoad %type_sampler %uniform_sampler
2530 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2531 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %const_offsets
2532 )";
2533
2534 CompileSuccessfully(GenerateShaderCode(body).c_str());
2535 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2536 EXPECT_THAT(
2537 getDiagnosticString(),
2538 HasSubstr(
2539 "Image Operand ConstOffsets cannot be used with Cube Image 'Dim'"));
2540 }
2541
TEST_F(ValidateImage,GatherConstOffsetsNotArray)2542 TEST_F(ValidateImage, GatherConstOffsetsNotArray) {
2543 const std::string body = R"(
2544 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2545 %sampler = OpLoad %type_sampler %uniform_sampler
2546 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2547 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %u32vec4_0123
2548 )";
2549
2550 CompileSuccessfully(GenerateShaderCode(body).c_str());
2551 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2552 EXPECT_THAT(
2553 getDiagnosticString(),
2554 HasSubstr(
2555 "Expected Image Operand ConstOffsets to be an array of size 4"));
2556 }
2557
TEST_F(ValidateImage,GatherConstOffsetsArrayWrongSize)2558 TEST_F(ValidateImage, GatherConstOffsetsArrayWrongSize) {
2559 const std::string body = R"(
2560 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2561 %sampler = OpLoad %type_sampler %uniform_sampler
2562 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2563 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %const_offsets3x2
2564 )";
2565
2566 CompileSuccessfully(GenerateShaderCode(body).c_str());
2567 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2568 EXPECT_THAT(
2569 getDiagnosticString(),
2570 HasSubstr(
2571 "Expected Image Operand ConstOffsets to be an array of size 4"));
2572 }
2573
TEST_F(ValidateImage,GatherConstOffsetsArrayNotVector)2574 TEST_F(ValidateImage, GatherConstOffsetsArrayNotVector) {
2575 const std::string body = R"(
2576 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2577 %sampler = OpLoad %type_sampler %uniform_sampler
2578 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2579 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %const_offsets4xu
2580 )";
2581
2582 CompileSuccessfully(GenerateShaderCode(body).c_str());
2583 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2584 EXPECT_THAT(getDiagnosticString(),
2585 HasSubstr("Expected Image Operand ConstOffsets array componenets "
2586 "to be int vectors of size 2"));
2587 }
2588
TEST_F(ValidateImage,GatherConstOffsetsArrayVectorWrongSize)2589 TEST_F(ValidateImage, GatherConstOffsetsArrayVectorWrongSize) {
2590 const std::string body = R"(
2591 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2592 %sampler = OpLoad %type_sampler %uniform_sampler
2593 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2594 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %const_offsets4x3
2595 )";
2596
2597 CompileSuccessfully(GenerateShaderCode(body).c_str());
2598 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2599 EXPECT_THAT(getDiagnosticString(),
2600 HasSubstr("Expected Image Operand ConstOffsets array componenets "
2601 "to be int vectors of size 2"));
2602 }
2603
TEST_F(ValidateImage,GatherConstOffsetsArrayNotConst)2604 TEST_F(ValidateImage, GatherConstOffsetsArrayNotConst) {
2605 const std::string body = R"(
2606 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2607 %sampler = OpLoad %type_sampler %uniform_sampler
2608 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2609 %offsets = OpUndef %u32vec2arr4
2610 %res1 = OpImageGather %f32vec4 %simg %f32vec4_0000 %u32_1 ConstOffsets %offsets
2611 )";
2612
2613 CompileSuccessfully(GenerateShaderCode(body).c_str());
2614 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2615 EXPECT_THAT(
2616 getDiagnosticString(),
2617 HasSubstr("Expected Image Operand ConstOffsets to be a const object"));
2618 }
2619
TEST_F(ValidateImage,NotGatherWithConstOffsets)2620 TEST_F(ValidateImage, NotGatherWithConstOffsets) {
2621 const std::string body = R"(
2622 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2623 %sampler = OpLoad %type_sampler %uniform_sampler
2624 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2625 %res2 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh ConstOffsets %const_offsets
2626 )";
2627
2628 CompileSuccessfully(GenerateShaderCode(body).c_str());
2629 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2630 EXPECT_THAT(
2631 getDiagnosticString(),
2632 HasSubstr(
2633 "Image Operand ConstOffsets can only be used with OpImageGather "
2634 "and OpImageDrefGather"));
2635 }
2636
TEST_F(ValidateImage,DrefGatherSuccess)2637 TEST_F(ValidateImage, DrefGatherSuccess) {
2638 const std::string body = R"(
2639 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2640 %sampler = OpLoad %type_sampler %uniform_sampler
2641 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
2642 %res1 = OpImageDrefGather %f32vec4 %simg %f32vec4_0000 %f32_0_5
2643 %res2 = OpImageDrefGather %f32vec4 %simg %f32vec4_0000 %f32_0_5 ConstOffsets %const_offsets
2644 %res3 = OpImageDrefGather %f32vec4 %simg %f32vec4_0000 %f32_0_5 NonPrivateTexelKHR
2645 )";
2646
2647 const std::string extra = R"(
2648 OpCapability VulkanMemoryModelKHR
2649 OpExtension "SPV_KHR_vulkan_memory_model"
2650 )";
2651 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
2652 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
2653 .c_str());
2654 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
2655 }
2656
TEST_F(ValidateImage,DrefGatherVoidSampledType)2657 TEST_F(ValidateImage, DrefGatherVoidSampledType) {
2658 const std::string body = R"(
2659 %img = OpLoad %type_image_void_2d_0001 %uniform_image_void_2d_0001
2660 %sampler = OpLoad %type_sampler %uniform_sampler
2661 %simg = OpSampledImage %type_sampled_image_void_2d_0001 %img %sampler
2662 %res1 = OpImageDrefGather %u32vec4 %simg %f32vec2_00 %f32_0_5
2663 )";
2664
2665 CompileSuccessfully(GenerateShaderCode(body).c_str());
2666 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2667 EXPECT_THAT(getDiagnosticString(),
2668 HasSubstr("Expected Image 'Sampled Type' to be the same as "
2669 "Result Type components"));
2670 }
2671
TEST_F(ValidateImage,DrefGatherWrongDrefType)2672 TEST_F(ValidateImage, DrefGatherWrongDrefType) {
2673 const std::string body = R"(
2674 %img = OpLoad %type_image_f32_cube_0101 %uniform_image_f32_cube_0101
2675 %sampler = OpLoad %type_sampler %uniform_sampler
2676 %simg = OpSampledImage %type_sampled_image_f32_cube_0101 %img %sampler
2677 %res1 = OpImageDrefGather %f32vec4 %simg %f32vec4_0000 %u32_1
2678 )";
2679
2680 CompileSuccessfully(GenerateShaderCode(body).c_str());
2681 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2682 EXPECT_THAT(getDiagnosticString(),
2683 HasSubstr("Expected Dref to be of 32-bit float type"));
2684 }
2685
TEST_F(ValidateImage,ReadSuccess1)2686 TEST_F(ValidateImage, ReadSuccess1) {
2687 const std::string body = R"(
2688 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2689 %res1 = OpImageRead %u32vec4 %img %u32vec2_01
2690 )";
2691
2692 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2693 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2694 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2695 }
2696
TEST_F(ValidateImage,ReadSuccess2)2697 TEST_F(ValidateImage, ReadSuccess2) {
2698 const std::string body = R"(
2699 %img = OpLoad %type_image_f32_1d_0002_rgba32f %uniform_image_f32_1d_0002_rgba32f
2700 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
2701 )";
2702
2703 const std::string extra = "\nOpCapability Image1D\n";
2704 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2705 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2706 }
2707
TEST_F(ValidateImage,ReadSuccess3)2708 TEST_F(ValidateImage, ReadSuccess3) {
2709 const std::string body = R"(
2710 %img = OpLoad %type_image_f32_cube_0102_rgba32f %uniform_image_f32_cube_0102_rgba32f
2711 %res1 = OpImageRead %f32vec4 %img %u32vec3_012
2712 )";
2713
2714 const std::string extra = "\nOpCapability ImageCubeArray\n";
2715 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2716 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2717 }
2718
TEST_F(ValidateImage,ReadSuccess4)2719 TEST_F(ValidateImage, ReadSuccess4) {
2720 const std::string body = R"(
2721 %img = OpLoad %type_image_f32_spd_0002 %uniform_image_f32_spd_0002
2722 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
2723 )";
2724
2725 CompileSuccessfully(GenerateShaderCode(body).c_str());
2726 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2727 }
2728
TEST_F(ValidateImage,ReadNeedCapabilityStorageImageReadWithoutFormat)2729 TEST_F(ValidateImage, ReadNeedCapabilityStorageImageReadWithoutFormat) {
2730 const std::string body = R"(
2731 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2732 %res1 = OpImageRead %u32vec4 %img %u32vec2_01
2733 )";
2734
2735 CompileSuccessfully(GenerateShaderCode(body).c_str());
2736 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2737 EXPECT_THAT(getDiagnosticString(),
2738 HasSubstr("Capability StorageImageReadWithoutFormat is required "
2739 "to read storage image"));
2740 }
2741
TEST_F(ValidateImage,ReadNeedCapabilityImage1D)2742 TEST_F(ValidateImage, ReadNeedCapabilityImage1D) {
2743 const std::string body = R"(
2744 %img = OpLoad %type_image_f32_1d_0002_rgba32f %uniform_image_f32_1d_0002_rgba32f
2745 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
2746 )";
2747
2748 CompileSuccessfully(GenerateShaderCode(body).c_str());
2749 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2750 EXPECT_THAT(
2751 getDiagnosticString(),
2752 HasSubstr("Capability Image1D is required to access storage image"));
2753 }
2754
TEST_F(ValidateImage,ReadNeedCapabilityImageCubeArray)2755 TEST_F(ValidateImage, ReadNeedCapabilityImageCubeArray) {
2756 const std::string body = R"(
2757 %img = OpLoad %type_image_f32_cube_0102_rgba32f %uniform_image_f32_cube_0102_rgba32f
2758 %res1 = OpImageRead %f32vec4 %img %u32vec3_012
2759 )";
2760
2761 CompileSuccessfully(GenerateShaderCode(body).c_str());
2762 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2763 EXPECT_THAT(
2764 getDiagnosticString(),
2765 HasSubstr(
2766 "Capability ImageCubeArray is required to access storage image"));
2767 }
2768
2769 // TODO(atgoo@github.com) Disabled until the spec is clarified.
TEST_F(ValidateImage,DISABLED_ReadWrongResultType)2770 TEST_F(ValidateImage, DISABLED_ReadWrongResultType) {
2771 const std::string body = R"(
2772 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2773 %res1 = OpImageRead %f32 %img %u32vec2_01
2774 )";
2775
2776 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2777 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2778 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2779 EXPECT_THAT(getDiagnosticString(),
2780 HasSubstr("Expected Result Type to be int or float vector type"));
2781 }
2782
2783 // TODO(atgoo@github.com) Disabled until the spec is clarified.
TEST_F(ValidateImage,DISABLED_ReadWrongNumComponentsResultType)2784 TEST_F(ValidateImage, DISABLED_ReadWrongNumComponentsResultType) {
2785 const std::string body = R"(
2786 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2787 %res1 = OpImageRead %f32vec3 %img %u32vec2_01
2788 )";
2789
2790 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2791 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2792 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2793 EXPECT_THAT(getDiagnosticString(),
2794 HasSubstr("Expected Result Type to have 4 components"));
2795 }
2796
TEST_F(ValidateImage,ReadNotImage)2797 TEST_F(ValidateImage, ReadNotImage) {
2798 const std::string body = R"(
2799 %sampler = OpLoad %type_sampler %uniform_sampler
2800 %res1 = OpImageRead %f32vec4 %sampler %u32vec2_01
2801 )";
2802
2803 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2804 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2805 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2806 EXPECT_THAT(getDiagnosticString(),
2807 HasSubstr("Expected Image to be of type OpTypeImage"));
2808 }
2809
TEST_F(ValidateImage,ReadImageSampled)2810 TEST_F(ValidateImage, ReadImageSampled) {
2811 const std::string body = R"(
2812 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2813 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
2814 )";
2815
2816 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2817 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2818 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2819 EXPECT_THAT(getDiagnosticString(),
2820 HasSubstr("Expected Image 'Sampled' parameter to be 0 or 2"));
2821 }
2822
TEST_F(ValidateImage,ReadWrongSampledType)2823 TEST_F(ValidateImage, ReadWrongSampledType) {
2824 const std::string body = R"(
2825 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2826 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
2827 )";
2828
2829 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2830 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2831 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2832 EXPECT_THAT(getDiagnosticString(),
2833 HasSubstr("Expected Image 'Sampled Type' to be the same as "
2834 "Result Type components"));
2835 }
2836
TEST_F(ValidateImage,ReadVoidSampledType)2837 TEST_F(ValidateImage, ReadVoidSampledType) {
2838 const std::string body = R"(
2839 %img = OpLoad %type_image_void_2d_0002 %uniform_image_void_2d_0002
2840 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
2841 %res2 = OpImageRead %u32vec4 %img %u32vec2_01
2842 %res3 = OpImageRead %s32vec4 %img %u32vec2_01
2843 )";
2844
2845 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2846 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2847 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2848 }
2849
TEST_F(ValidateImage,ReadWrongCoordinateType)2850 TEST_F(ValidateImage, ReadWrongCoordinateType) {
2851 const std::string body = R"(
2852 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2853 %res1 = OpImageRead %u32vec4 %img %f32vec2_00
2854 )";
2855
2856 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2857 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2858 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2859 EXPECT_THAT(getDiagnosticString(),
2860 HasSubstr("Expected Coordinate to be int scalar or vector"));
2861 }
2862
TEST_F(ValidateImage,ReadCoordinateSizeTooSmall)2863 TEST_F(ValidateImage, ReadCoordinateSizeTooSmall) {
2864 const std::string body = R"(
2865 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2866 %res1 = OpImageRead %u32vec4 %img %u32_1
2867 )";
2868
2869 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
2870 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2871 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2872 EXPECT_THAT(getDiagnosticString(),
2873 HasSubstr("Expected Coordinate to have at least 2 components, "
2874 "but given only 1"));
2875 }
2876
TEST_F(ValidateImage,WriteSuccess1)2877 TEST_F(ValidateImage, WriteSuccess1) {
2878 const std::string body = R"(
2879 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2880 %res1 = OpImageWrite %img %u32vec2_01 %u32vec4_0123
2881 )";
2882
2883 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
2884 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2885 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2886 }
2887
TEST_F(ValidateImage,WriteSuccess2)2888 TEST_F(ValidateImage, WriteSuccess2) {
2889 const std::string body = R"(
2890 %img = OpLoad %type_image_f32_1d_0002_rgba32f %uniform_image_f32_1d_0002_rgba32f
2891 %res1 = OpImageWrite %img %u32_1 %f32vec4_0000
2892 )";
2893
2894 const std::string extra = "\nOpCapability Image1D\n";
2895 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2896 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2897 }
2898
TEST_F(ValidateImage,WriteSuccess3)2899 TEST_F(ValidateImage, WriteSuccess3) {
2900 const std::string body = R"(
2901 %img = OpLoad %type_image_f32_cube_0102_rgba32f %uniform_image_f32_cube_0102_rgba32f
2902 %res1 = OpImageWrite %img %u32vec3_012 %f32vec4_0000
2903 )";
2904
2905 const std::string extra = "\nOpCapability ImageCubeArray\n";
2906 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2907 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2908 }
2909
TEST_F(ValidateImage,WriteSuccess4)2910 TEST_F(ValidateImage, WriteSuccess4) {
2911 const std::string body = R"(
2912 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
2913 ;TODO(atgoo@github.com) Is it legal to write to MS image without sample index?
2914 %res1 = OpImageWrite %img %u32vec2_01 %f32vec4_0000
2915 %res2 = OpImageWrite %img %u32vec2_01 %f32vec4_0000 Sample %u32_1
2916 )";
2917
2918 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
2919 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2920 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
2921 }
2922
TEST_F(ValidateImage,WriteSubpassData)2923 TEST_F(ValidateImage, WriteSubpassData) {
2924 const std::string body = R"(
2925 %img = OpLoad %type_image_f32_spd_0002 %uniform_image_f32_spd_0002
2926 %res1 = OpImageWrite %img %u32vec2_01 %f32vec4_0000
2927 )";
2928
2929 CompileSuccessfully(GenerateShaderCode(body).c_str());
2930 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2931 EXPECT_THAT(getDiagnosticString(),
2932 HasSubstr("Image 'Dim' cannot be SubpassData"));
2933 }
2934
TEST_F(ValidateImage,WriteNeedCapabilityStorageImageWriteWithoutFormat)2935 TEST_F(ValidateImage, WriteNeedCapabilityStorageImageWriteWithoutFormat) {
2936 const std::string body = R"(
2937 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
2938 %res1 = OpImageWrite %img %u32vec2_01 %u32vec4_0123
2939 )";
2940
2941 CompileSuccessfully(GenerateShaderCode(body).c_str());
2942 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2943 EXPECT_THAT(
2944 getDiagnosticString(),
2945 HasSubstr(
2946 "Capability StorageImageWriteWithoutFormat is required to write to "
2947 "storage image"));
2948 }
2949
TEST_F(ValidateImage,WriteNeedCapabilityImage1D)2950 TEST_F(ValidateImage, WriteNeedCapabilityImage1D) {
2951 const std::string body = R"(
2952 %img = OpLoad %type_image_f32_1d_0002_rgba32f %uniform_image_f32_1d_0002_rgba32f
2953 %res1 = OpImageWrite %img %u32vec2_01 %f32vec4_0000
2954 )";
2955
2956 CompileSuccessfully(GenerateShaderCode(body).c_str());
2957 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2958 EXPECT_THAT(getDiagnosticString(),
2959 HasSubstr("Capability Image1D is required to access storage "
2960 "image"));
2961 }
2962
TEST_F(ValidateImage,WriteNeedCapabilityImageCubeArray)2963 TEST_F(ValidateImage, WriteNeedCapabilityImageCubeArray) {
2964 const std::string body = R"(
2965 %img = OpLoad %type_image_f32_cube_0102_rgba32f %uniform_image_f32_cube_0102_rgba32f
2966 %res1 = OpImageWrite %img %u32vec3_012 %f32vec4_0000
2967 )";
2968
2969 CompileSuccessfully(GenerateShaderCode(body).c_str());
2970 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2971 EXPECT_THAT(
2972 getDiagnosticString(),
2973 HasSubstr(
2974 "Capability ImageCubeArray is required to access storage image"));
2975 }
2976
TEST_F(ValidateImage,WriteNotImage)2977 TEST_F(ValidateImage, WriteNotImage) {
2978 const std::string body = R"(
2979 %sampler = OpLoad %type_sampler %uniform_sampler
2980 %res1 = OpImageWrite %sampler %u32vec2_01 %f32vec4_0000
2981 )";
2982
2983 CompileSuccessfully(GenerateShaderCode(body).c_str());
2984 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2985 EXPECT_THAT(getDiagnosticString(),
2986 HasSubstr("Expected Image to be of type OpTypeImage"));
2987 }
2988
TEST_F(ValidateImage,WriteImageSampled)2989 TEST_F(ValidateImage, WriteImageSampled) {
2990 const std::string body = R"(
2991 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
2992 %res1 = OpImageWrite %img %u32vec2_01 %f32vec4_0000
2993 )";
2994
2995 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
2996 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
2997 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
2998 EXPECT_THAT(getDiagnosticString(),
2999 HasSubstr("Expected Image 'Sampled' parameter to be 0 or 2"));
3000 }
3001
TEST_F(ValidateImage,WriteWrongCoordinateType)3002 TEST_F(ValidateImage, WriteWrongCoordinateType) {
3003 const std::string body = R"(
3004 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
3005 %res1 = OpImageWrite %img %f32vec2_00 %u32vec4_0123
3006 )";
3007
3008 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3009 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3010 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3011 EXPECT_THAT(getDiagnosticString(),
3012 HasSubstr("Expected Coordinate to be int scalar or vector"));
3013 }
3014
TEST_F(ValidateImage,WriteCoordinateSizeTooSmall)3015 TEST_F(ValidateImage, WriteCoordinateSizeTooSmall) {
3016 const std::string body = R"(
3017 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
3018 %res1 = OpImageWrite %img %u32_1 %u32vec4_0123
3019 )";
3020
3021 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3022 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3023 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3024 EXPECT_THAT(getDiagnosticString(),
3025 HasSubstr("Expected Coordinate to have at least 2 components, "
3026 "but given only 1"));
3027 }
3028
TEST_F(ValidateImage,WriteTexelWrongType)3029 TEST_F(ValidateImage, WriteTexelWrongType) {
3030 const std::string body = R"(
3031 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
3032 %res1 = OpImageWrite %img %u32vec2_01 %img
3033 )";
3034
3035 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3036 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3037 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3038 EXPECT_THAT(getDiagnosticString(),
3039 HasSubstr("Expected Texel to be int or float vector or scalar"));
3040 }
3041
TEST_F(ValidateImage,DISABLED_WriteTexelNotVector4)3042 TEST_F(ValidateImage, DISABLED_WriteTexelNotVector4) {
3043 const std::string body = R"(
3044 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
3045 %res1 = OpImageWrite %img %u32vec2_01 %u32vec3_012
3046 )";
3047
3048 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3049 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3050 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3051 EXPECT_THAT(getDiagnosticString(),
3052 HasSubstr("Expected Texel to have 4 components"));
3053 }
3054
TEST_F(ValidateImage,WriteTexelWrongComponentType)3055 TEST_F(ValidateImage, WriteTexelWrongComponentType) {
3056 const std::string body = R"(
3057 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
3058 %res1 = OpImageWrite %img %u32vec2_01 %f32vec4_0000
3059 )";
3060
3061 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3062 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3063 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3064 EXPECT_THAT(
3065 getDiagnosticString(),
3066 HasSubstr(
3067 "Expected Image 'Sampled Type' to be the same as Texel components"));
3068 }
3069
TEST_F(ValidateImage,WriteSampleNotInteger)3070 TEST_F(ValidateImage, WriteSampleNotInteger) {
3071 const std::string body = R"(
3072 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3073 %res1 = OpImageWrite %img %u32vec2_01 %f32vec4_0000 Sample %f32_1
3074 )";
3075
3076 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3077 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3078 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3079 EXPECT_THAT(getDiagnosticString(),
3080 HasSubstr("Expected Image Operand Sample to be int scalar"));
3081 }
3082
TEST_F(ValidateImage,SampleNotMultisampled)3083 TEST_F(ValidateImage, SampleNotMultisampled) {
3084 const std::string body = R"(
3085 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
3086 %res2 = OpImageWrite %img %u32vec2_01 %f32vec4_0000 Sample %u32_1
3087 )";
3088
3089 const std::string extra = "\nOpCapability StorageImageWriteWithoutFormat\n";
3090 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3091 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3092 EXPECT_THAT(
3093 getDiagnosticString(),
3094 HasSubstr("Image Operand Sample requires non-zero 'MS' parameter"));
3095 }
3096
TEST_F(ValidateImage,SampleWrongOpcode)3097 TEST_F(ValidateImage, SampleWrongOpcode) {
3098 const std::string body = R"(
3099 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3100 %sampler = OpLoad %type_sampler %uniform_sampler
3101 %simg = OpSampledImage %type_sampled_image_f32_2d_0010 %img %sampler
3102 %res1 = OpImageSampleExplicitLod %f32vec4 %simg %f32vec2_00 Sample %u32_1
3103 )";
3104
3105 CompileSuccessfully(GenerateShaderCode(body).c_str());
3106 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3107 EXPECT_THAT(getDiagnosticString(),
3108 HasSubstr("Image Operand Sample can only be used with "
3109 "OpImageFetch, OpImageRead, OpImageWrite, "
3110 "OpImageSparseFetch and OpImageSparseRead"));
3111 }
3112
TEST_F(ValidateImage,SampleImageToImageSuccess)3113 TEST_F(ValidateImage, SampleImageToImageSuccess) {
3114 const std::string body = R"(
3115 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3116 %sampler = OpLoad %type_sampler %uniform_sampler
3117 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3118 %img2 = OpImage %type_image_f32_2d_0001 %simg
3119 )";
3120
3121 CompileSuccessfully(GenerateShaderCode(body).c_str());
3122 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3123 }
3124
TEST_F(ValidateImage,SampleImageToImageWrongResultType)3125 TEST_F(ValidateImage, SampleImageToImageWrongResultType) {
3126 const std::string body = R"(
3127 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3128 %sampler = OpLoad %type_sampler %uniform_sampler
3129 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3130 %img2 = OpImage %type_sampled_image_f32_2d_0001 %simg
3131 )";
3132
3133 CompileSuccessfully(GenerateShaderCode(body).c_str());
3134 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3135 EXPECT_THAT(getDiagnosticString(),
3136 HasSubstr("Expected Result Type to be OpTypeImage"));
3137 }
3138
TEST_F(ValidateImage,SampleImageToImageNotSampledImage)3139 TEST_F(ValidateImage, SampleImageToImageNotSampledImage) {
3140 const std::string body = R"(
3141 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3142 %img2 = OpImage %type_image_f32_2d_0001 %img
3143 )";
3144
3145 CompileSuccessfully(GenerateShaderCode(body).c_str());
3146 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3147 EXPECT_THAT(
3148 getDiagnosticString(),
3149 HasSubstr("Expected Sample Image to be of type OpTypeSampleImage"));
3150 }
3151
TEST_F(ValidateImage,SampleImageToImageNotTheSameImageType)3152 TEST_F(ValidateImage, SampleImageToImageNotTheSameImageType) {
3153 const std::string body = R"(
3154 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3155 %sampler = OpLoad %type_sampler %uniform_sampler
3156 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3157 %img2 = OpImage %type_image_f32_2d_0002 %simg
3158 )";
3159
3160 CompileSuccessfully(GenerateShaderCode(body).c_str());
3161 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3162 EXPECT_THAT(getDiagnosticString(),
3163 HasSubstr("Expected Sample Image image type to be equal to "
3164 "Result Type"));
3165 }
3166
TEST_F(ValidateImage,QueryFormatSuccess)3167 TEST_F(ValidateImage, QueryFormatSuccess) {
3168 const std::string body = R"(
3169 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3170 %res1 = OpImageQueryFormat %u32 %img
3171 )";
3172
3173 CompileSuccessfully(GenerateKernelCode(body).c_str());
3174 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3175 }
3176
TEST_F(ValidateImage,QueryFormatWrongResultType)3177 TEST_F(ValidateImage, QueryFormatWrongResultType) {
3178 const std::string body = R"(
3179 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3180 %res1 = OpImageQueryFormat %bool %img
3181 )";
3182
3183 CompileSuccessfully(GenerateKernelCode(body).c_str());
3184 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3185 EXPECT_THAT(getDiagnosticString(),
3186 HasSubstr("Expected Result Type to be int scalar type"));
3187 }
3188
TEST_F(ValidateImage,QueryFormatNotImage)3189 TEST_F(ValidateImage, QueryFormatNotImage) {
3190 const std::string body = R"(
3191 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3192 %sampler = OpLoad %type_sampler %uniform_sampler
3193 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3194 %res1 = OpImageQueryFormat %u32 %simg
3195 )";
3196
3197 CompileSuccessfully(GenerateKernelCode(body).c_str());
3198 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3199 EXPECT_THAT(getDiagnosticString(),
3200 HasSubstr("Expected operand to be of type OpTypeImage"));
3201 }
3202
TEST_F(ValidateImage,QueryOrderSuccess)3203 TEST_F(ValidateImage, QueryOrderSuccess) {
3204 const std::string body = R"(
3205 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3206 %res1 = OpImageQueryOrder %u32 %img
3207 )";
3208
3209 CompileSuccessfully(GenerateKernelCode(body).c_str());
3210 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3211 }
3212
TEST_F(ValidateImage,QueryOrderWrongResultType)3213 TEST_F(ValidateImage, QueryOrderWrongResultType) {
3214 const std::string body = R"(
3215 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3216 %res1 = OpImageQueryOrder %bool %img
3217 )";
3218
3219 CompileSuccessfully(GenerateKernelCode(body).c_str());
3220 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3221 EXPECT_THAT(getDiagnosticString(),
3222 HasSubstr("Expected Result Type to be int scalar type"));
3223 }
3224
TEST_F(ValidateImage,QueryOrderNotImage)3225 TEST_F(ValidateImage, QueryOrderNotImage) {
3226 const std::string body = R"(
3227 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3228 %sampler = OpLoad %type_sampler %uniform_sampler
3229 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3230 %res1 = OpImageQueryOrder %u32 %simg
3231 )";
3232
3233 CompileSuccessfully(GenerateKernelCode(body).c_str());
3234 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3235 EXPECT_THAT(getDiagnosticString(),
3236 HasSubstr("Expected operand to be of type OpTypeImage"));
3237 }
3238
TEST_F(ValidateImage,QuerySizeLodSuccess)3239 TEST_F(ValidateImage, QuerySizeLodSuccess) {
3240 const std::string body = R"(
3241 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3242 %res1 = OpImageQuerySizeLod %u32vec2 %img %u32_1
3243 )";
3244
3245 CompileSuccessfully(GenerateKernelCode(body).c_str());
3246 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3247 }
3248
TEST_F(ValidateImage,QuerySizeLodWrongResultType)3249 TEST_F(ValidateImage, QuerySizeLodWrongResultType) {
3250 const std::string body = R"(
3251 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3252 %res1 = OpImageQuerySizeLod %f32vec2 %img %u32_1
3253 )";
3254
3255 CompileSuccessfully(GenerateKernelCode(body).c_str());
3256 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3257 EXPECT_THAT(
3258 getDiagnosticString(),
3259 HasSubstr("Expected Result Type to be int scalar or vector type"));
3260 }
3261
TEST_F(ValidateImage,QuerySizeLodResultTypeWrongSize)3262 TEST_F(ValidateImage, QuerySizeLodResultTypeWrongSize) {
3263 const std::string body = R"(
3264 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3265 %res1 = OpImageQuerySizeLod %u32 %img %u32_1
3266 )";
3267
3268 CompileSuccessfully(GenerateKernelCode(body).c_str());
3269 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3270 EXPECT_THAT(getDiagnosticString(),
3271 HasSubstr("Result Type has 1 components, but 2 expected"));
3272 }
3273
TEST_F(ValidateImage,QuerySizeLodNotImage)3274 TEST_F(ValidateImage, QuerySizeLodNotImage) {
3275 const std::string body = R"(
3276 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3277 %sampler = OpLoad %type_sampler %uniform_sampler
3278 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3279 %res1 = OpImageQuerySizeLod %u32vec2 %simg %u32_1
3280 )";
3281
3282 CompileSuccessfully(GenerateKernelCode(body).c_str());
3283 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3284 EXPECT_THAT(getDiagnosticString(),
3285 HasSubstr("Expected Image to be of type OpTypeImage"));
3286 }
3287
TEST_F(ValidateImage,QuerySizeLodWrongImageDim)3288 TEST_F(ValidateImage, QuerySizeLodWrongImageDim) {
3289 const std::string body = R"(
3290 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3291 %res1 = OpImageQuerySizeLod %u32vec2 %img %u32_1
3292 )";
3293
3294 CompileSuccessfully(GenerateKernelCode(body).c_str());
3295 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3296 EXPECT_THAT(getDiagnosticString(),
3297 HasSubstr("Image 'Dim' must be 1D, 2D, 3D or Cube"));
3298 }
3299
TEST_F(ValidateImage,QuerySizeLodMultisampled)3300 TEST_F(ValidateImage, QuerySizeLodMultisampled) {
3301 const std::string body = R"(
3302 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3303 %res1 = OpImageQuerySizeLod %u32vec2 %img %u32_1
3304 )";
3305
3306 CompileSuccessfully(GenerateKernelCode(body).c_str());
3307 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3308 EXPECT_THAT(getDiagnosticString(), HasSubstr("Image 'MS' must be 0"));
3309 }
3310
TEST_F(ValidateImage,QuerySizeLodWrongLodType)3311 TEST_F(ValidateImage, QuerySizeLodWrongLodType) {
3312 const std::string body = R"(
3313 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3314 %res1 = OpImageQuerySizeLod %u32vec2 %img %f32_0
3315 )";
3316
3317 CompileSuccessfully(GenerateKernelCode(body).c_str());
3318 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3319 EXPECT_THAT(getDiagnosticString(),
3320 HasSubstr("Expected Level of Detail to be int scalar"));
3321 }
3322
TEST_F(ValidateImage,QuerySizeSuccess)3323 TEST_F(ValidateImage, QuerySizeSuccess) {
3324 const std::string body = R"(
3325 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3326 %res1 = OpImageQuerySize %u32vec2 %img
3327 )";
3328
3329 CompileSuccessfully(GenerateKernelCode(body).c_str());
3330 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3331 }
3332
TEST_F(ValidateImage,QuerySizeWrongResultType)3333 TEST_F(ValidateImage, QuerySizeWrongResultType) {
3334 const std::string body = R"(
3335 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3336 %res1 = OpImageQuerySize %f32vec2 %img
3337 )";
3338
3339 CompileSuccessfully(GenerateKernelCode(body).c_str());
3340 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3341 EXPECT_THAT(
3342 getDiagnosticString(),
3343 HasSubstr("Expected Result Type to be int scalar or vector type"));
3344 }
3345
TEST_F(ValidateImage,QuerySizeNotImage)3346 TEST_F(ValidateImage, QuerySizeNotImage) {
3347 const std::string body = R"(
3348 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3349 %sampler = OpLoad %type_sampler %uniform_sampler
3350 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3351 %res1 = OpImageQuerySize %u32vec2 %simg
3352 )";
3353
3354 CompileSuccessfully(GenerateKernelCode(body).c_str());
3355 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3356 EXPECT_THAT(getDiagnosticString(),
3357 HasSubstr("Expected Image to be of type OpTypeImage"));
3358 }
3359
TEST_F(ValidateImage,QuerySizeDimSubpassDataBad)3360 TEST_F(ValidateImage, QuerySizeDimSubpassDataBad) {
3361 const std::string body = R"(
3362 %img = OpLoad %type_image_f32_spd_0002 %uniform_image_f32_spd_0002
3363 %res1 = OpImageQuerySize %u32vec2 %img
3364 )";
3365
3366 CompileSuccessfully(GenerateShaderCode(body).c_str());
3367 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3368 EXPECT_THAT(
3369 getDiagnosticString(),
3370 HasSubstr("Image 'Dim' must be 1D, Buffer, 2D, Cube, 3D or Rect"));
3371 }
3372
TEST_F(ValidateImage,QuerySizeWrongSampling)3373 TEST_F(ValidateImage, QuerySizeWrongSampling) {
3374 const std::string body = R"(
3375 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3376 %res1 = OpImageQuerySize %u32vec2 %img
3377 )";
3378
3379 CompileSuccessfully(GenerateKernelCode(body).c_str());
3380 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3381 EXPECT_THAT(
3382 getDiagnosticString(),
3383 HasSubstr("Image must have either 'MS'=1 or 'Sampled'=0 or 'Sampled'=2"));
3384 }
3385
TEST_F(ValidateImage,QuerySizeWrongNumberOfComponents)3386 TEST_F(ValidateImage, QuerySizeWrongNumberOfComponents) {
3387 const std::string body = R"(
3388 %img = OpLoad %type_image_f32_3d_0111 %uniform_image_f32_3d_0111
3389 %res1 = OpImageQuerySize %u32vec2 %img
3390 )";
3391
3392 CompileSuccessfully(GenerateShaderCode(body).c_str());
3393 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3394 EXPECT_THAT(getDiagnosticString(),
3395 HasSubstr("Result Type has 2 components, but 4 expected"));
3396 }
3397
TEST_F(ValidateImage,QueryLodSuccessKernel)3398 TEST_F(ValidateImage, QueryLodSuccessKernel) {
3399 const std::string body = R"(
3400 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3401 %sampler = OpLoad %type_sampler %uniform_sampler
3402 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3403 %res1 = OpImageQueryLod %f32vec2 %simg %f32vec2_hh
3404 %res2 = OpImageQueryLod %f32vec2 %simg %u32vec2_01
3405 )";
3406
3407 CompileSuccessfully(GenerateKernelCode(body).c_str());
3408 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3409 }
3410
TEST_F(ValidateImage,QueryLodSuccessShader)3411 TEST_F(ValidateImage, QueryLodSuccessShader) {
3412 const std::string body = R"(
3413 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3414 %sampler = OpLoad %type_sampler %uniform_sampler
3415 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3416 %res1 = OpImageQueryLod %f32vec2 %simg %f32vec2_hh
3417 )";
3418
3419 CompileSuccessfully(GenerateShaderCode(body).c_str());
3420 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3421 }
3422
TEST_F(ValidateImage,QueryLodWrongResultType)3423 TEST_F(ValidateImage, QueryLodWrongResultType) {
3424 const std::string body = R"(
3425 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3426 %sampler = OpLoad %type_sampler %uniform_sampler
3427 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3428 %res1 = OpImageQueryLod %u32vec2 %simg %f32vec2_hh
3429 )";
3430
3431 CompileSuccessfully(GenerateKernelCode(body).c_str());
3432 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3433 EXPECT_THAT(getDiagnosticString(),
3434 HasSubstr("Expected Result Type to be float vector type"));
3435 }
3436
TEST_F(ValidateImage,QueryLodResultTypeWrongSize)3437 TEST_F(ValidateImage, QueryLodResultTypeWrongSize) {
3438 const std::string body = R"(
3439 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3440 %sampler = OpLoad %type_sampler %uniform_sampler
3441 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3442 %res1 = OpImageQueryLod %f32vec3 %simg %f32vec2_hh
3443 )";
3444
3445 CompileSuccessfully(GenerateKernelCode(body).c_str());
3446 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3447 EXPECT_THAT(getDiagnosticString(),
3448 HasSubstr("Expected Result Type to have 2 components"));
3449 }
3450
TEST_F(ValidateImage,QueryLodNotSampledImage)3451 TEST_F(ValidateImage, QueryLodNotSampledImage) {
3452 const std::string body = R"(
3453 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3454 %res1 = OpImageQueryLod %f32vec2 %img %f32vec2_hh
3455 )";
3456
3457 CompileSuccessfully(GenerateKernelCode(body).c_str());
3458 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3459 EXPECT_THAT(
3460 getDiagnosticString(),
3461 HasSubstr("Expected Image operand to be of type OpTypeSampledImage"));
3462 }
3463
TEST_F(ValidateImage,QueryLodWrongDim)3464 TEST_F(ValidateImage, QueryLodWrongDim) {
3465 const std::string body = R"(
3466 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3467 %sampler = OpLoad %type_sampler %uniform_sampler
3468 %simg = OpSampledImage %type_sampled_image_f32_rect_0001 %img %sampler
3469 %res1 = OpImageQueryLod %f32vec2 %simg %f32vec2_hh
3470 )";
3471
3472 CompileSuccessfully(GenerateKernelCode(body).c_str());
3473 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3474 EXPECT_THAT(getDiagnosticString(),
3475 HasSubstr("Image 'Dim' must be 1D, 2D, 3D or Cube"));
3476 }
3477
TEST_F(ValidateImage,QueryLodWrongCoordinateType)3478 TEST_F(ValidateImage, QueryLodWrongCoordinateType) {
3479 const std::string body = R"(
3480 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3481 %sampler = OpLoad %type_sampler %uniform_sampler
3482 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3483 %res1 = OpImageQueryLod %f32vec2 %simg %u32vec2_01
3484 )";
3485
3486 CompileSuccessfully(GenerateShaderCode(body).c_str());
3487 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3488 EXPECT_THAT(getDiagnosticString(),
3489 HasSubstr("Expected Coordinate to be float scalar or vector"));
3490 }
3491
TEST_F(ValidateImage,QueryLodCoordinateSizeTooSmall)3492 TEST_F(ValidateImage, QueryLodCoordinateSizeTooSmall) {
3493 const std::string body = R"(
3494 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3495 %sampler = OpLoad %type_sampler %uniform_sampler
3496 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3497 %res1 = OpImageQueryLod %f32vec2 %simg %f32_0
3498 )";
3499
3500 CompileSuccessfully(GenerateShaderCode(body).c_str());
3501 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3502 EXPECT_THAT(getDiagnosticString(),
3503 HasSubstr("Expected Coordinate to have at least 2 components, "
3504 "but given only 1"));
3505 }
3506
TEST_F(ValidateImage,QueryLevelsSuccess)3507 TEST_F(ValidateImage, QueryLevelsSuccess) {
3508 const std::string body = R"(
3509 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3510 %res1 = OpImageQueryLevels %u32 %img
3511 )";
3512
3513 CompileSuccessfully(GenerateKernelCode(body).c_str());
3514 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3515 }
3516
TEST_F(ValidateImage,QueryLevelsWrongResultType)3517 TEST_F(ValidateImage, QueryLevelsWrongResultType) {
3518 const std::string body = R"(
3519 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3520 %res1 = OpImageQueryLevels %f32 %img
3521 )";
3522
3523 CompileSuccessfully(GenerateKernelCode(body).c_str());
3524 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3525 EXPECT_THAT(getDiagnosticString(),
3526 HasSubstr("Expected Result Type to be int scalar type"));
3527 }
3528
TEST_F(ValidateImage,QueryLevelsNotImage)3529 TEST_F(ValidateImage, QueryLevelsNotImage) {
3530 const std::string body = R"(
3531 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3532 %sampler = OpLoad %type_sampler %uniform_sampler
3533 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3534 %res1 = OpImageQueryLevels %u32 %simg
3535 )";
3536
3537 CompileSuccessfully(GenerateKernelCode(body).c_str());
3538 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3539 EXPECT_THAT(getDiagnosticString(),
3540 HasSubstr("Expected Image to be of type OpTypeImage"));
3541 }
3542
TEST_F(ValidateImage,QueryLevelsWrongDim)3543 TEST_F(ValidateImage, QueryLevelsWrongDim) {
3544 const std::string body = R"(
3545 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3546 %res1 = OpImageQueryLevels %u32 %img
3547 )";
3548
3549 CompileSuccessfully(GenerateKernelCode(body).c_str());
3550 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3551 EXPECT_THAT(getDiagnosticString(),
3552 HasSubstr("Image 'Dim' must be 1D, 2D, 3D or Cube"));
3553 }
3554
TEST_F(ValidateImage,QuerySamplesSuccess)3555 TEST_F(ValidateImage, QuerySamplesSuccess) {
3556 const std::string body = R"(
3557 %img = OpLoad %type_image_f32_2d_0010 %uniform_image_f32_2d_0010
3558 %res1 = OpImageQuerySamples %u32 %img
3559 )";
3560
3561 CompileSuccessfully(GenerateKernelCode(body).c_str());
3562 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3563 }
3564
TEST_F(ValidateImage,QuerySamplesNot2D)3565 TEST_F(ValidateImage, QuerySamplesNot2D) {
3566 const std::string body = R"(
3567 %img = OpLoad %type_image_f32_3d_0010 %uniform_image_f32_3d_0010
3568 %res1 = OpImageQuerySamples %u32 %img
3569 )";
3570
3571 CompileSuccessfully(GenerateKernelCode(body).c_str());
3572 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3573 EXPECT_THAT(getDiagnosticString(), HasSubstr("Image 'Dim' must be 2D"));
3574 }
3575
TEST_F(ValidateImage,QuerySamplesNotMultisampled)3576 TEST_F(ValidateImage, QuerySamplesNotMultisampled) {
3577 const std::string body = R"(
3578 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3579 %res1 = OpImageQuerySamples %u32 %img
3580 )";
3581
3582 CompileSuccessfully(GenerateKernelCode(body).c_str());
3583 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3584 EXPECT_THAT(getDiagnosticString(), HasSubstr("Image 'MS' must be 1"));
3585 }
3586
TEST_F(ValidateImage,QueryLodWrongExecutionModel)3587 TEST_F(ValidateImage, QueryLodWrongExecutionModel) {
3588 const std::string body = R"(
3589 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3590 %sampler = OpLoad %type_sampler %uniform_sampler
3591 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3592 %res1 = OpImageQueryLod %f32vec2 %simg %f32vec2_hh
3593 )";
3594
3595 CompileSuccessfully(GenerateShaderCode(body, "", "Vertex").c_str());
3596 ASSERT_EQ(SPV_ERROR_INVALID_ID, ValidateInstructions());
3597 EXPECT_THAT(getDiagnosticString(),
3598 HasSubstr("OpImageQueryLod requires Fragment execution model"));
3599 }
3600
TEST_F(ValidateImage,QueryLodWrongExecutionModelWithFunc)3601 TEST_F(ValidateImage, QueryLodWrongExecutionModelWithFunc) {
3602 const std::string body = R"(
3603 %call_ret = OpFunctionCall %void %my_func
3604 OpReturn
3605 OpFunctionEnd
3606 %my_func = OpFunction %void None %func
3607 %my_func_entry = OpLabel
3608 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3609 %sampler = OpLoad %type_sampler %uniform_sampler
3610 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3611 %res1 = OpImageQueryLod %f32vec2 %simg %f32vec2_hh
3612 )";
3613
3614 CompileSuccessfully(GenerateShaderCode(body, "", "Vertex").c_str());
3615 ASSERT_EQ(SPV_ERROR_INVALID_ID, ValidateInstructions());
3616 EXPECT_THAT(getDiagnosticString(),
3617 HasSubstr("OpImageQueryLod requires Fragment execution model"));
3618 }
3619
TEST_F(ValidateImage,ImplicitLodWrongExecutionModel)3620 TEST_F(ValidateImage, ImplicitLodWrongExecutionModel) {
3621 const std::string body = R"(
3622 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3623 %sampler = OpLoad %type_sampler %uniform_sampler
3624 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3625 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh
3626 )";
3627
3628 CompileSuccessfully(GenerateShaderCode(body, "", "Vertex").c_str());
3629 ASSERT_EQ(SPV_ERROR_INVALID_ID, ValidateInstructions());
3630 EXPECT_THAT(
3631 getDiagnosticString(),
3632 HasSubstr("ImplicitLod instructions require Fragment execution model"));
3633 }
3634
TEST_F(ValidateImage,ReadSubpassDataWrongExecutionModel)3635 TEST_F(ValidateImage, ReadSubpassDataWrongExecutionModel) {
3636 const std::string body = R"(
3637 %img = OpLoad %type_image_f32_spd_0002 %uniform_image_f32_spd_0002
3638 %res1 = OpImageRead %f32vec4 %img %u32vec2_01
3639 )";
3640
3641 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
3642 CompileSuccessfully(GenerateShaderCode(body, extra, "Vertex").c_str());
3643 ASSERT_EQ(SPV_ERROR_INVALID_ID, ValidateInstructions());
3644 EXPECT_THAT(getDiagnosticString(),
3645 HasSubstr("Dim SubpassData requires Fragment execution model"));
3646 }
3647
TEST_F(ValidateImage,SparseSampleImplicitLodSuccess)3648 TEST_F(ValidateImage, SparseSampleImplicitLodSuccess) {
3649 const std::string body = R"(
3650 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3651 %sampler = OpLoad %type_sampler %uniform_sampler
3652 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3653 %res1 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4 %simg %f32vec2_hh
3654 %res2 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4 %simg %f32vec2_hh Bias %f32_0_25
3655 %res4 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4 %simg %f32vec2_hh ConstOffset %s32vec2_01
3656 %res5 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4 %simg %f32vec2_hh Offset %s32vec2_01
3657 %res6 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4 %simg %f32vec2_hh MinLod %f32_0_5
3658 %res7 = OpImageSparseSampleImplicitLod %struct_u64_f32vec4 %simg %f32vec2_hh Bias|Offset|MinLod %f32_0_25 %s32vec2_01 %f32_0_5
3659 %res8 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4 %simg %f32vec2_hh NonPrivateTexelKHR
3660 )";
3661
3662 const std::string extra = R"(
3663 OpCapability VulkanMemoryModelKHR
3664 OpExtension "SPV_KHR_vulkan_memory_model"
3665 )";
3666 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
3667 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
3668 .c_str());
3669 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
3670 }
3671
TEST_F(ValidateImage,SparseSampleImplicitLodResultTypeNotStruct)3672 TEST_F(ValidateImage, SparseSampleImplicitLodResultTypeNotStruct) {
3673 const std::string body = R"(
3674 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3675 %sampler = OpLoad %type_sampler %uniform_sampler
3676 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3677 %res1 = OpImageSparseSampleImplicitLod %f32 %simg %f32vec2_hh
3678 )";
3679
3680 CompileSuccessfully(GenerateShaderCode(body).c_str());
3681 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3682 EXPECT_THAT(getDiagnosticString(),
3683 HasSubstr("Expected Result Type to be OpTypeStruct"));
3684 }
3685
TEST_F(ValidateImage,SparseSampleImplicitLodResultTypeNotTwoMembers1)3686 TEST_F(ValidateImage, SparseSampleImplicitLodResultTypeNotTwoMembers1) {
3687 const std::string body = R"(
3688 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3689 %sampler = OpLoad %type_sampler %uniform_sampler
3690 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3691 %res1 = OpImageSparseSampleImplicitLod %struct_u32 %simg %f32vec2_hh
3692 )";
3693
3694 CompileSuccessfully(GenerateShaderCode(body).c_str());
3695 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3696 EXPECT_THAT(getDiagnosticString(),
3697 HasSubstr("Expected Result Type to be a struct containing an int "
3698 "scalar and a texel"));
3699 }
3700
TEST_F(ValidateImage,SparseSampleImplicitLodResultTypeNotTwoMembers2)3701 TEST_F(ValidateImage, SparseSampleImplicitLodResultTypeNotTwoMembers2) {
3702 const std::string body = R"(
3703 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3704 %sampler = OpLoad %type_sampler %uniform_sampler
3705 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3706 %res1 = OpImageSparseSampleImplicitLod %struct_u32_f32vec4_u32 %simg %f32vec2_hh
3707 )";
3708
3709 CompileSuccessfully(GenerateShaderCode(body).c_str());
3710 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3711 EXPECT_THAT(getDiagnosticString(),
3712 HasSubstr("Expected Result Type to be a struct containing an "
3713 "int scalar and a texel"));
3714 }
3715
TEST_F(ValidateImage,SparseSampleImplicitLodResultTypeFirstMemberNotInt)3716 TEST_F(ValidateImage, SparseSampleImplicitLodResultTypeFirstMemberNotInt) {
3717 const std::string body = R"(
3718 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3719 %sampler = OpLoad %type_sampler %uniform_sampler
3720 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3721 %res1 = OpImageSparseSampleImplicitLod %struct_f32_f32vec4 %simg %f32vec2_hh
3722 )";
3723
3724 CompileSuccessfully(GenerateShaderCode(body).c_str());
3725 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3726 EXPECT_THAT(getDiagnosticString(),
3727 HasSubstr("Expected Result Type to be a struct containing an "
3728 "int scalar and a texel"));
3729 }
3730
TEST_F(ValidateImage,SparseSampleImplicitLodResultTypeTexelNotVector)3731 TEST_F(ValidateImage, SparseSampleImplicitLodResultTypeTexelNotVector) {
3732 const std::string body = R"(
3733 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3734 %sampler = OpLoad %type_sampler %uniform_sampler
3735 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3736 %res1 = OpImageSparseSampleImplicitLod %struct_u32_u32 %simg %f32vec2_hh
3737 )";
3738
3739 CompileSuccessfully(GenerateShaderCode(body).c_str());
3740 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3741 EXPECT_THAT(getDiagnosticString(),
3742 HasSubstr("Expected Result Type's second member to be int or "
3743 "float vector type"));
3744 }
3745
TEST_F(ValidateImage,SparseSampleImplicitLodWrongNumComponentsTexel)3746 TEST_F(ValidateImage, SparseSampleImplicitLodWrongNumComponentsTexel) {
3747 const std::string body = R"(
3748 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3749 %sampler = OpLoad %type_sampler %uniform_sampler
3750 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3751 %res1 = OpImageSparseSampleImplicitLod %struct_u32_f32vec3 %simg %f32vec2_hh
3752 )";
3753
3754 CompileSuccessfully(GenerateShaderCode(body).c_str());
3755 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3756 EXPECT_THAT(getDiagnosticString(),
3757 HasSubstr("Expected Result Type's second member to have 4 "
3758 "components"));
3759 }
3760
TEST_F(ValidateImage,SparseSampleImplicitLodWrongComponentTypeTexel)3761 TEST_F(ValidateImage, SparseSampleImplicitLodWrongComponentTypeTexel) {
3762 const std::string body = R"(
3763 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3764 %sampler = OpLoad %type_sampler %uniform_sampler
3765 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3766 %res1 = OpImageSparseSampleImplicitLod %struct_u32_u32vec4 %simg %f32vec2_hh
3767 )";
3768
3769 CompileSuccessfully(GenerateShaderCode(body).c_str());
3770 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3771 EXPECT_THAT(getDiagnosticString(),
3772 HasSubstr("Expected Image 'Sampled Type' to be the same as "
3773 "Result Type's second member components"));
3774 }
3775
TEST_F(ValidateImage,SparseSampleDrefImplicitLodSuccess)3776 TEST_F(ValidateImage, SparseSampleDrefImplicitLodSuccess) {
3777 const std::string body = R"(
3778 %img = OpLoad %type_image_u32_2d_0001 %uniform_image_u32_2d_0001
3779 %sampler = OpLoad %type_sampler %uniform_sampler
3780 %simg = OpSampledImage %type_sampled_image_u32_2d_0001 %img %sampler
3781 %res1 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1
3782 %res2 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1 Bias %f32_0_25
3783 %res4 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1 ConstOffset %s32vec2_01
3784 %res5 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1 Offset %s32vec2_01
3785 %res6 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1 MinLod %f32_0_5
3786 %res7 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1 Bias|Offset|MinLod %f32_0_25 %s32vec2_01 %f32_0_5
3787 %res8 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1 NonPrivateTexelKHR
3788 )";
3789
3790 const std::string extra = R"(
3791 OpCapability VulkanMemoryModelKHR
3792 OpExtension "SPV_KHR_vulkan_memory_model"
3793 )";
3794 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
3795 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
3796 .c_str());
3797 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
3798 }
3799
TEST_F(ValidateImage,SparseSampleDrefImplicitLodResultTypeNotStruct)3800 TEST_F(ValidateImage, SparseSampleDrefImplicitLodResultTypeNotStruct) {
3801 const std::string body = R"(
3802 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3803 %sampler = OpLoad %type_sampler %uniform_sampler
3804 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3805 %res1 = OpImageSparseSampleDrefImplicitLod %f32 %simg %f32vec2_hh %f32_1
3806 )";
3807
3808 CompileSuccessfully(GenerateShaderCode(body).c_str());
3809 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3810 EXPECT_THAT(getDiagnosticString(),
3811 HasSubstr("Expected Result Type to be OpTypeStruct"));
3812 }
3813
TEST_F(ValidateImage,SparseSampleDrefImplicitLodResultTypeNotTwoMembers1)3814 TEST_F(ValidateImage, SparseSampleDrefImplicitLodResultTypeNotTwoMembers1) {
3815 const std::string body = R"(
3816 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3817 %sampler = OpLoad %type_sampler %uniform_sampler
3818 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3819 %res1 = OpImageSparseSampleDrefImplicitLod %struct_u32 %simg %f32vec2_hh %f32_1
3820 )";
3821
3822 CompileSuccessfully(GenerateShaderCode(body).c_str());
3823 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3824 EXPECT_THAT(
3825 getDiagnosticString(),
3826 HasSubstr("Expected Result Type to be a struct containing an int scalar "
3827 "and a texel"));
3828 }
3829
TEST_F(ValidateImage,SparseSampleDrefImplicitLodResultTypeNotTwoMembers2)3830 TEST_F(ValidateImage, SparseSampleDrefImplicitLodResultTypeNotTwoMembers2) {
3831 const std::string body = R"(
3832 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3833 %sampler = OpLoad %type_sampler %uniform_sampler
3834 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3835 %res1 = OpImageSparseSampleDrefImplicitLod %struct_u32_f32_u32 %simg %f32vec2_hh %f32_1
3836 )";
3837
3838 CompileSuccessfully(GenerateShaderCode(body).c_str());
3839 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3840 EXPECT_THAT(
3841 getDiagnosticString(),
3842 HasSubstr("Expected Result Type to be a struct containing an int scalar "
3843 "and a texel"));
3844 }
3845
TEST_F(ValidateImage,SparseSampleDrefImplicitLodResultTypeFirstMemberNotInt)3846 TEST_F(ValidateImage, SparseSampleDrefImplicitLodResultTypeFirstMemberNotInt) {
3847 const std::string body = R"(
3848 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3849 %sampler = OpLoad %type_sampler %uniform_sampler
3850 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3851 %res1 = OpImageSparseSampleDrefImplicitLod %struct_f32_f32 %simg %f32vec2_hh %f32_1
3852 )";
3853
3854 CompileSuccessfully(GenerateShaderCode(body).c_str());
3855 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3856 EXPECT_THAT(
3857 getDiagnosticString(),
3858 HasSubstr("Expected Result Type to be a struct containing an int scalar "
3859 "and a texel"));
3860 }
3861
TEST_F(ValidateImage,SparseSampleDrefImplicitLodDifferentSampledType)3862 TEST_F(ValidateImage, SparseSampleDrefImplicitLodDifferentSampledType) {
3863 const std::string body = R"(
3864 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
3865 %sampler = OpLoad %type_sampler %uniform_sampler
3866 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
3867 %res1 = OpImageSparseSampleDrefImplicitLod %struct_u32_u32 %simg %f32vec2_hh %f32_1
3868 )";
3869
3870 CompileSuccessfully(GenerateShaderCode(body).c_str());
3871 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3872 EXPECT_THAT(getDiagnosticString(),
3873 HasSubstr("Expected Image 'Sampled Type' to be the same as "
3874 "Result Type's second member"));
3875 }
3876
TEST_F(ValidateImage,SparseFetchSuccess)3877 TEST_F(ValidateImage, SparseFetchSuccess) {
3878 const std::string body = R"(
3879 %img = OpLoad %type_image_f32_1d_0001 %uniform_image_f32_1d_0001
3880 %res1 = OpImageSparseFetch %struct_u32_f32vec4 %img %u32vec2_01
3881 %res2 = OpImageSparseFetch %struct_u32_f32vec4 %img %u32vec2_01 NonPrivateTexelKHR
3882 )";
3883
3884 const std::string extra = R"(
3885 OpCapability VulkanMemoryModelKHR
3886 OpExtension "SPV_KHR_vulkan_memory_model"
3887 )";
3888 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
3889 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
3890 .c_str());
3891 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
3892 }
3893
TEST_F(ValidateImage,SparseFetchResultTypeNotStruct)3894 TEST_F(ValidateImage, SparseFetchResultTypeNotStruct) {
3895 const std::string body = R"(
3896 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3897 %res1 = OpImageSparseFetch %f32 %img %u32vec2_01
3898 )";
3899
3900 CompileSuccessfully(GenerateShaderCode(body).c_str());
3901 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3902 EXPECT_THAT(getDiagnosticString(),
3903 HasSubstr("Expected Result Type to be OpTypeStruct"));
3904 }
3905
TEST_F(ValidateImage,SparseFetchResultTypeNotTwoMembers1)3906 TEST_F(ValidateImage, SparseFetchResultTypeNotTwoMembers1) {
3907 const std::string body = R"(
3908 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3909 %res1 = OpImageSparseFetch %struct_u32 %img %u32vec2_01
3910 )";
3911
3912 CompileSuccessfully(GenerateShaderCode(body).c_str());
3913 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3914 EXPECT_THAT(getDiagnosticString(),
3915 HasSubstr("Expected Result Type to be a struct containing an "
3916 "int scalar and a texel"));
3917 }
3918
TEST_F(ValidateImage,SparseFetchResultTypeNotTwoMembers2)3919 TEST_F(ValidateImage, SparseFetchResultTypeNotTwoMembers2) {
3920 const std::string body = R"(
3921 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3922 %res1 = OpImageSparseFetch %struct_u32_f32vec4_u32 %img %u32vec2_01
3923 )";
3924
3925 CompileSuccessfully(GenerateShaderCode(body).c_str());
3926 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3927 EXPECT_THAT(getDiagnosticString(),
3928 HasSubstr("Expected Result Type to be a struct containing an "
3929 "int scalar and a texel"));
3930 }
3931
TEST_F(ValidateImage,SparseFetchResultTypeFirstMemberNotInt)3932 TEST_F(ValidateImage, SparseFetchResultTypeFirstMemberNotInt) {
3933 const std::string body = R"(
3934 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3935 %res1 = OpImageSparseFetch %struct_f32_f32vec4 %img %u32vec2_01
3936 )";
3937
3938 CompileSuccessfully(GenerateShaderCode(body).c_str());
3939 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3940 EXPECT_THAT(getDiagnosticString(),
3941 HasSubstr("Expected Result Type to be a struct containing an "
3942 "int scalar and a texel"));
3943 }
3944
TEST_F(ValidateImage,SparseFetchResultTypeTexelNotVector)3945 TEST_F(ValidateImage, SparseFetchResultTypeTexelNotVector) {
3946 const std::string body = R"(
3947 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3948 %res1 = OpImageSparseFetch %struct_u32_u32 %img %u32vec2_01
3949 )";
3950
3951 CompileSuccessfully(GenerateShaderCode(body).c_str());
3952 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3953 EXPECT_THAT(getDiagnosticString(),
3954 HasSubstr("Expected Result Type's second member to be int or "
3955 "float vector type"));
3956 }
3957
TEST_F(ValidateImage,SparseFetchWrongNumComponentsTexel)3958 TEST_F(ValidateImage, SparseFetchWrongNumComponentsTexel) {
3959 const std::string body = R"(
3960 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3961 %res1 = OpImageSparseFetch %struct_u32_f32vec3 %img %u32vec2_01
3962 )";
3963
3964 CompileSuccessfully(GenerateShaderCode(body).c_str());
3965 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3966 EXPECT_THAT(getDiagnosticString(),
3967 HasSubstr("Expected Result Type's second member to have 4 "
3968 "components"));
3969 }
3970
TEST_F(ValidateImage,SparseFetchWrongComponentTypeTexel)3971 TEST_F(ValidateImage, SparseFetchWrongComponentTypeTexel) {
3972 const std::string body = R"(
3973 %img = OpLoad %type_image_f32_rect_0001 %uniform_image_f32_rect_0001
3974 %res1 = OpImageSparseFetch %struct_u32_u32vec4 %img %u32vec2_01
3975 )";
3976
3977 CompileSuccessfully(GenerateShaderCode(body).c_str());
3978 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
3979 EXPECT_THAT(getDiagnosticString(),
3980 HasSubstr("Expected Image 'Sampled Type' to be the same as "
3981 "Result Type's second member components"));
3982 }
3983
TEST_F(ValidateImage,SparseReadSuccess)3984 TEST_F(ValidateImage, SparseReadSuccess) {
3985 const std::string body = R"(
3986 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
3987 %res1 = OpImageSparseRead %struct_u32_f32vec4 %img %u32vec2_01
3988 )";
3989
3990 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
3991 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
3992 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
3993 }
3994
TEST_F(ValidateImage,SparseReadResultTypeNotStruct)3995 TEST_F(ValidateImage, SparseReadResultTypeNotStruct) {
3996 const std::string body = R"(
3997 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
3998 %res1 = OpImageSparseRead %f32 %img %u32vec2_01
3999 )";
4000
4001 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4002 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
4003 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4004 EXPECT_THAT(getDiagnosticString(),
4005 HasSubstr("Expected Result Type to be OpTypeStruct"));
4006 }
4007
TEST_F(ValidateImage,SparseReadResultTypeNotTwoMembers1)4008 TEST_F(ValidateImage, SparseReadResultTypeNotTwoMembers1) {
4009 const std::string body = R"(
4010 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
4011 %res1 = OpImageSparseRead %struct_u32 %img %u32vec2_01
4012 )";
4013
4014 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4015 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
4016 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4017 EXPECT_THAT(getDiagnosticString(),
4018 HasSubstr("Expected Result Type to be a struct containing an "
4019 "int scalar and a texel"));
4020 }
4021
TEST_F(ValidateImage,SparseReadResultTypeNotTwoMembers2)4022 TEST_F(ValidateImage, SparseReadResultTypeNotTwoMembers2) {
4023 const std::string body = R"(
4024 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
4025 %res1 = OpImageSparseRead %struct_u32_f32vec4_u32 %img %u32vec2_01
4026 )";
4027
4028 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4029 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
4030 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4031 EXPECT_THAT(getDiagnosticString(),
4032 HasSubstr("Expected Result Type to be a struct containing an "
4033 "int scalar and a texel"));
4034 }
4035
TEST_F(ValidateImage,SparseReadResultTypeFirstMemberNotInt)4036 TEST_F(ValidateImage, SparseReadResultTypeFirstMemberNotInt) {
4037 const std::string body = R"(
4038 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
4039 %res1 = OpImageSparseRead %struct_f32_f32vec4 %img %u32vec2_01
4040 )";
4041
4042 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4043 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
4044 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4045 EXPECT_THAT(getDiagnosticString(),
4046 HasSubstr("Expected Result Type to be a struct containing an "
4047 "int scalar and a texel"));
4048 }
4049
TEST_F(ValidateImage,SparseReadResultTypeTexelWrongType)4050 TEST_F(ValidateImage, SparseReadResultTypeTexelWrongType) {
4051 const std::string body = R"(
4052 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
4053 %res1 = OpImageSparseRead %struct_u32_u32arr4 %img %u32vec2_01
4054 )";
4055
4056 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4057 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
4058 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4059 EXPECT_THAT(getDiagnosticString(),
4060 HasSubstr("Expected Result Type's second member to be int or "
4061 "float scalar or vector type"));
4062 }
4063
TEST_F(ValidateImage,SparseReadWrongComponentTypeTexel)4064 TEST_F(ValidateImage, SparseReadWrongComponentTypeTexel) {
4065 const std::string body = R"(
4066 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
4067 %res1 = OpImageSparseRead %struct_u32_u32vec4 %img %u32vec2_01
4068 )";
4069
4070 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4071 CompileSuccessfully(GenerateShaderCode(body, extra).c_str());
4072 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4073 EXPECT_THAT(getDiagnosticString(),
4074 HasSubstr("Expected Image 'Sampled Type' to be the same as "
4075 "Result Type's second member components"));
4076 }
4077
TEST_F(ValidateImage,SparseReadSubpassDataNotAllowed)4078 TEST_F(ValidateImage, SparseReadSubpassDataNotAllowed) {
4079 const std::string body = R"(
4080 %img = OpLoad %type_image_f32_spd_0002 %uniform_image_f32_spd_0002
4081 %res1 = OpImageSparseRead %struct_u32_f32vec4 %img %u32vec2_01
4082 )";
4083
4084 const std::string extra = "\nOpCapability StorageImageReadWithoutFormat\n";
4085 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment").c_str());
4086 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4087 EXPECT_THAT(
4088 getDiagnosticString(),
4089 HasSubstr("Image Dim SubpassData cannot be used with ImageSparseRead"));
4090 }
4091
TEST_F(ValidateImage,SparseGatherSuccess)4092 TEST_F(ValidateImage, SparseGatherSuccess) {
4093 const std::string body = R"(
4094 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4095 %sampler = OpLoad %type_sampler %uniform_sampler
4096 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4097 %res1 = OpImageSparseGather %struct_u32_f32vec4 %simg %f32vec4_0000 %u32_1
4098 %res2 = OpImageSparseGather %struct_u32_f32vec4 %simg %f32vec4_0000 %u32_1 NonPrivateTexelKHR
4099 )";
4100
4101 const std::string extra = R"(
4102 OpCapability VulkanMemoryModelKHR
4103 OpExtension "SPV_KHR_vulkan_memory_model"
4104 )";
4105 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4106 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4107 .c_str());
4108 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4109 }
4110
TEST_F(ValidateImage,SparseGatherResultTypeNotStruct)4111 TEST_F(ValidateImage, SparseGatherResultTypeNotStruct) {
4112 const std::string body = R"(
4113 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4114 %sampler = OpLoad %type_sampler %uniform_sampler
4115 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4116 %res1 = OpImageSparseGather %f32 %simg %f32vec2_hh %u32_1
4117 )";
4118
4119 CompileSuccessfully(GenerateShaderCode(body).c_str());
4120 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4121 EXPECT_THAT(getDiagnosticString(),
4122 HasSubstr("Expected Result Type to be OpTypeStruct"));
4123 }
4124
TEST_F(ValidateImage,SparseGatherResultTypeNotTwoMembers1)4125 TEST_F(ValidateImage, SparseGatherResultTypeNotTwoMembers1) {
4126 const std::string body = R"(
4127 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4128 %sampler = OpLoad %type_sampler %uniform_sampler
4129 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4130 %res1 = OpImageSparseGather %struct_u32 %simg %f32vec2_hh %u32_1
4131 )";
4132
4133 CompileSuccessfully(GenerateShaderCode(body).c_str());
4134 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4135 EXPECT_THAT(getDiagnosticString(),
4136 HasSubstr("Expected Result Type to be a struct containing an int "
4137 "scalar and a texel"));
4138 }
4139
TEST_F(ValidateImage,SparseGatherResultTypeNotTwoMembers2)4140 TEST_F(ValidateImage, SparseGatherResultTypeNotTwoMembers2) {
4141 const std::string body = R"(
4142 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4143 %sampler = OpLoad %type_sampler %uniform_sampler
4144 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4145 %res1 = OpImageSparseGather %struct_u32_f32vec4_u32 %simg %f32vec2_hh %u32_1
4146 )";
4147
4148 CompileSuccessfully(GenerateShaderCode(body).c_str());
4149 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4150 EXPECT_THAT(getDiagnosticString(),
4151 HasSubstr("Expected Result Type to be a struct containing an int "
4152 "scalar and a texel"));
4153 }
4154
TEST_F(ValidateImage,SparseGatherResultTypeFirstMemberNotInt)4155 TEST_F(ValidateImage, SparseGatherResultTypeFirstMemberNotInt) {
4156 const std::string body = R"(
4157 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4158 %sampler = OpLoad %type_sampler %uniform_sampler
4159 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4160 %res1 = OpImageSparseGather %struct_f32_f32vec4 %simg %f32vec2_hh %u32_1
4161 )";
4162
4163 CompileSuccessfully(GenerateShaderCode(body).c_str());
4164 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4165 EXPECT_THAT(getDiagnosticString(),
4166 HasSubstr("Expected Result Type to be a struct containing an "
4167 "int scalar and a texel"));
4168 }
4169
TEST_F(ValidateImage,SparseGatherResultTypeTexelNotVector)4170 TEST_F(ValidateImage, SparseGatherResultTypeTexelNotVector) {
4171 const std::string body = R"(
4172 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4173 %sampler = OpLoad %type_sampler %uniform_sampler
4174 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4175 %res1 = OpImageSparseGather %struct_u32_u32 %simg %f32vec2_hh %u32_1
4176 )";
4177
4178 CompileSuccessfully(GenerateShaderCode(body).c_str());
4179 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4180 EXPECT_THAT(getDiagnosticString(),
4181 HasSubstr("Expected Result Type's second member to be int or "
4182 "float vector type"));
4183 }
4184
TEST_F(ValidateImage,SparseGatherWrongNumComponentsTexel)4185 TEST_F(ValidateImage, SparseGatherWrongNumComponentsTexel) {
4186 const std::string body = R"(
4187 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4188 %sampler = OpLoad %type_sampler %uniform_sampler
4189 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4190 %res1 = OpImageSparseGather %struct_u32_f32vec3 %simg %f32vec2_hh %u32_1
4191 )";
4192
4193 CompileSuccessfully(GenerateShaderCode(body).c_str());
4194 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4195 EXPECT_THAT(getDiagnosticString(),
4196 HasSubstr("Expected Result Type's second member to have 4 "
4197 "components"));
4198 }
4199
TEST_F(ValidateImage,SparseGatherWrongComponentTypeTexel)4200 TEST_F(ValidateImage, SparseGatherWrongComponentTypeTexel) {
4201 const std::string body = R"(
4202 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4203 %sampler = OpLoad %type_sampler %uniform_sampler
4204 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4205 %res1 = OpImageSparseGather %struct_u32_u32vec4 %simg %f32vec2_hh %u32_1
4206 )";
4207
4208 CompileSuccessfully(GenerateShaderCode(body).c_str());
4209 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4210 EXPECT_THAT(getDiagnosticString(),
4211 HasSubstr("Expected Image 'Sampled Type' to be the same as "
4212 "Result Type's second member components"));
4213 }
4214
TEST_F(ValidateImage,SparseTexelsResidentSuccess)4215 TEST_F(ValidateImage, SparseTexelsResidentSuccess) {
4216 const std::string body = R"(
4217 %res1 = OpImageSparseTexelsResident %bool %u32_1
4218 )";
4219
4220 CompileSuccessfully(GenerateShaderCode(body).c_str());
4221 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions());
4222 }
4223
TEST_F(ValidateImage,SparseTexelsResidentResultTypeNotBool)4224 TEST_F(ValidateImage, SparseTexelsResidentResultTypeNotBool) {
4225 const std::string body = R"(
4226 %res1 = OpImageSparseTexelsResident %u32 %u32_1
4227 )";
4228
4229 CompileSuccessfully(GenerateShaderCode(body).c_str());
4230 ASSERT_EQ(SPV_ERROR_INVALID_DATA, ValidateInstructions());
4231 EXPECT_THAT(getDiagnosticString(),
4232 HasSubstr("Expected Result Type to be bool scalar type"));
4233 }
4234
TEST_F(ValidateImage,MakeTexelVisibleKHRSuccessImageRead)4235 TEST_F(ValidateImage, MakeTexelVisibleKHRSuccessImageRead) {
4236 const std::string body = R"(
4237 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4238 %res1 = OpImageRead %u32vec4 %img %u32vec2_01 MakeTexelVisibleKHR|NonPrivateTexelKHR %u32_2
4239 )";
4240
4241 const std::string extra = R"(
4242 OpCapability StorageImageReadWithoutFormat
4243 OpCapability VulkanMemoryModelKHR
4244 OpExtension "SPV_KHR_vulkan_memory_model"
4245 )";
4246 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4247 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4248 .c_str());
4249 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4250 }
4251
TEST_F(ValidateImage,MakeTexelVisibleKHRSuccessImageSparseRead)4252 TEST_F(ValidateImage, MakeTexelVisibleKHRSuccessImageSparseRead) {
4253 const std::string body = R"(
4254 %img = OpLoad %type_image_f32_2d_0002 %uniform_image_f32_2d_0002
4255 %res1 = OpImageSparseRead %struct_u32_f32vec4 %img %u32vec2_01 MakeTexelVisibleKHR|NonPrivateTexelKHR %u32_2
4256 )";
4257
4258 const std::string extra = R"(
4259 OpCapability StorageImageReadWithoutFormat
4260 OpCapability VulkanMemoryModelKHR
4261 OpExtension "SPV_KHR_vulkan_memory_model"
4262 )";
4263 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4264 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4265 .c_str());
4266 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4267 }
4268
TEST_F(ValidateImage,MakeTexelVisibleKHRFailureOpcode)4269 TEST_F(ValidateImage, MakeTexelVisibleKHRFailureOpcode) {
4270 const std::string body = R"(
4271 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4272 %sampler = OpLoad %type_sampler %uniform_sampler
4273 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4274 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh MakeTexelVisibleKHR|NonPrivateTexelKHR %u32_1
4275 )";
4276
4277 const std::string extra = R"(
4278 OpCapability StorageImageReadWithoutFormat
4279 OpCapability VulkanMemoryModelKHR
4280 OpExtension "SPV_KHR_vulkan_memory_model"
4281 )";
4282 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4283 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4284 .c_str());
4285 ASSERT_EQ(SPV_ERROR_INVALID_DATA,
4286 ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4287 EXPECT_THAT(
4288 getDiagnosticString(),
4289 HasSubstr("Image Operand MakeTexelVisibleKHR can only be used with "
4290 "OpImageRead or OpImageSparseRead: OpImageSampleImplicitLod"));
4291 }
4292
TEST_F(ValidateImage,MakeTexelVisibleKHRFailureMissingNonPrivate)4293 TEST_F(ValidateImage, MakeTexelVisibleKHRFailureMissingNonPrivate) {
4294 const std::string body = R"(
4295 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4296 %res1 = OpImageRead %u32vec4 %img %u32vec2_01 MakeTexelVisibleKHR %u32_1
4297 )";
4298
4299 const std::string extra = R"(
4300 OpCapability StorageImageReadWithoutFormat
4301 OpCapability VulkanMemoryModelKHR
4302 OpExtension "SPV_KHR_vulkan_memory_model"
4303 )";
4304 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4305 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4306 .c_str());
4307 ASSERT_EQ(SPV_ERROR_INVALID_DATA,
4308 ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4309 EXPECT_THAT(getDiagnosticString(),
4310 HasSubstr("Image Operand MakeTexelVisibleKHR requires "
4311 "NonPrivateTexelKHR is also specified: OpImageRead"));
4312 }
4313
TEST_F(ValidateImage,MakeTexelAvailableKHRSuccessImageWrite)4314 TEST_F(ValidateImage, MakeTexelAvailableKHRSuccessImageWrite) {
4315 const std::string body = R"(
4316 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4317 %res1 = OpImageWrite %img %u32vec2_01 %u32vec4_0123 MakeTexelAvailableKHR|NonPrivateTexelKHR %u32_2
4318 )";
4319
4320 const std::string extra = R"(
4321 OpCapability StorageImageWriteWithoutFormat
4322 OpCapability VulkanMemoryModelKHR
4323 OpExtension "SPV_KHR_vulkan_memory_model"
4324 )";
4325 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4326 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4327 .c_str());
4328 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4329 }
4330
TEST_F(ValidateImage,MakeTexelAvailableKHRFailureOpcode)4331 TEST_F(ValidateImage, MakeTexelAvailableKHRFailureOpcode) {
4332 const std::string body = R"(
4333 %img = OpLoad %type_image_f32_2d_0001 %uniform_image_f32_2d_0001
4334 %sampler = OpLoad %type_sampler %uniform_sampler
4335 %simg = OpSampledImage %type_sampled_image_f32_2d_0001 %img %sampler
4336 %res1 = OpImageSampleImplicitLod %f32vec4 %simg %f32vec2_hh MakeTexelAvailableKHR|NonPrivateTexelKHR %u32_1
4337 )";
4338
4339 const std::string extra = R"(
4340 OpCapability StorageImageReadWithoutFormat
4341 OpCapability VulkanMemoryModelKHR
4342 OpExtension "SPV_KHR_vulkan_memory_model"
4343 )";
4344 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4345 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4346 .c_str());
4347 ASSERT_EQ(SPV_ERROR_INVALID_DATA,
4348 ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4349 EXPECT_THAT(getDiagnosticString(),
4350 HasSubstr("Image Operand MakeTexelAvailableKHR can only be used "
4351 "with OpImageWrite: OpImageSampleImplicitLod"));
4352 }
4353
TEST_F(ValidateImage,MakeTexelAvailableKHRFailureMissingNonPrivate)4354 TEST_F(ValidateImage, MakeTexelAvailableKHRFailureMissingNonPrivate) {
4355 const std::string body = R"(
4356 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4357 %res1 = OpImageWrite %img %u32vec2_01 %u32vec4_0123 MakeTexelAvailableKHR %u32_1
4358 )";
4359
4360 const std::string extra = R"(
4361 OpCapability StorageImageWriteWithoutFormat
4362 OpCapability VulkanMemoryModelKHR
4363 OpExtension "SPV_KHR_vulkan_memory_model"
4364 )";
4365 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4366 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4367 .c_str());
4368 ASSERT_EQ(SPV_ERROR_INVALID_DATA,
4369 ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4370 EXPECT_THAT(getDiagnosticString(),
4371 HasSubstr("Image Operand MakeTexelAvailableKHR requires "
4372 "NonPrivateTexelKHR is also specified: OpImageWrite"));
4373 }
4374
TEST_F(ValidateImage,VulkanMemoryModelDeviceScopeImageWriteBad)4375 TEST_F(ValidateImage, VulkanMemoryModelDeviceScopeImageWriteBad) {
4376 const std::string body = R"(
4377 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4378 %res1 = OpImageWrite %img %u32vec2_01 %u32vec4_0123 MakeTexelAvailableKHR|NonPrivateTexelKHR %u32_1
4379 )";
4380
4381 const std::string extra = R"(
4382 OpCapability StorageImageWriteWithoutFormat
4383 OpCapability VulkanMemoryModelKHR
4384 OpExtension "SPV_KHR_vulkan_memory_model"
4385 )";
4386 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4387 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4388 .c_str());
4389 ASSERT_EQ(SPV_ERROR_INVALID_DATA,
4390 ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4391 EXPECT_THAT(
4392 getDiagnosticString(),
4393 HasSubstr("Use of device scope with VulkanKHR memory model requires the "
4394 "VulkanMemoryModelDeviceScopeKHR capability"));
4395 }
4396
TEST_F(ValidateImage,VulkanMemoryModelDeviceScopeImageWriteGood)4397 TEST_F(ValidateImage, VulkanMemoryModelDeviceScopeImageWriteGood) {
4398 const std::string body = R"(
4399 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4400 %res1 = OpImageWrite %img %u32vec2_01 %u32vec4_0123 MakeTexelAvailableKHR|NonPrivateTexelKHR %u32_1
4401 )";
4402
4403 const std::string extra = R"(
4404 OpCapability StorageImageWriteWithoutFormat
4405 OpCapability VulkanMemoryModelKHR
4406 OpCapability VulkanMemoryModelDeviceScopeKHR
4407 OpExtension "SPV_KHR_vulkan_memory_model"
4408 )";
4409 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4410 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4411 .c_str());
4412 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4413 }
4414
TEST_F(ValidateImage,VulkanMemoryModelDeviceScopeImageReadBad)4415 TEST_F(ValidateImage, VulkanMemoryModelDeviceScopeImageReadBad) {
4416 const std::string body = R"(
4417 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4418 %res1 = OpImageRead %u32vec4 %img %u32vec2_01 MakeTexelVisibleKHR|NonPrivateTexelKHR %u32_1
4419 )";
4420
4421 const std::string extra = R"(
4422 OpCapability StorageImageReadWithoutFormat
4423 OpCapability VulkanMemoryModelKHR
4424 OpExtension "SPV_KHR_vulkan_memory_model"
4425 )";
4426 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4427 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4428 .c_str());
4429 ASSERT_EQ(SPV_ERROR_INVALID_DATA,
4430 ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4431 EXPECT_THAT(
4432 getDiagnosticString(),
4433 HasSubstr("Use of device scope with VulkanKHR memory model requires the "
4434 "VulkanMemoryModelDeviceScopeKHR capability"));
4435 }
4436
TEST_F(ValidateImage,VulkanMemoryModelDeviceScopeImageReadGood)4437 TEST_F(ValidateImage, VulkanMemoryModelDeviceScopeImageReadGood) {
4438 const std::string body = R"(
4439 %img = OpLoad %type_image_u32_2d_0000 %uniform_image_u32_2d_0000
4440 %res1 = OpImageRead %u32vec4 %img %u32vec2_01 MakeTexelVisibleKHR|NonPrivateTexelKHR %u32_1
4441 )";
4442
4443 const std::string extra = R"(
4444 OpCapability StorageImageReadWithoutFormat
4445 OpCapability VulkanMemoryModelKHR
4446 OpCapability VulkanMemoryModelDeviceScopeKHR
4447 OpExtension "SPV_KHR_vulkan_memory_model"
4448 )";
4449 CompileSuccessfully(GenerateShaderCode(body, extra, "Fragment",
4450 SPV_ENV_UNIVERSAL_1_3, "VulkanKHR")
4451 .c_str());
4452 ASSERT_EQ(SPV_SUCCESS, ValidateInstructions(SPV_ENV_UNIVERSAL_1_3));
4453 }
4454
4455 } // namespace
4456 } // namespace val
4457 } // namespace spvtools
4458