1 /*------------------------------------------------------------------------
2 * Vulkan Conformance Tests
3 * ------------------------
4 *
5 * Copyright (c) 2020 The Khronos Group Inc.
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 *
19 *//*!
20 * \file
21 * \brief Ray Query Builtin tests
22 *//*--------------------------------------------------------------------*/
23
24 #include "vktRayQueryBuiltinTests.hpp"
25
26 #include "vkDefs.hpp"
27
28 #include "vktTestCase.hpp"
29 #include "vktCustomInstancesDevices.hpp"
30 #include "vktTestGroupUtil.hpp"
31 #include "vkCmdUtil.hpp"
32 #include "vkObjUtil.hpp"
33 #include "vkBuilderUtil.hpp"
34 #include "vkBarrierUtil.hpp"
35 #include "vkBufferWithMemory.hpp"
36 #include "vkImageWithMemory.hpp"
37 #include "vkTypeUtil.hpp"
38 #include "vkImageUtil.hpp"
39 #include "deRandom.hpp"
40 #include "tcuTexture.hpp"
41 #include "tcuTextureUtil.hpp"
42 #include "tcuTestLog.hpp"
43 #include "tcuImageCompare.hpp"
44 #include "tcuCommandLine.hpp"
45
46 #include "vkRayTracingUtil.hpp"
47
48 namespace vkt
49 {
50 namespace RayQuery
51 {
52 namespace
53 {
54 using namespace vk;
55 using namespace vkt;
56
57 static const VkFlags ALL_RAY_TRACING_STAGES = VK_SHADER_STAGE_RAYGEN_BIT_KHR | VK_SHADER_STAGE_ANY_HIT_BIT_KHR |
58 VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR | VK_SHADER_STAGE_MISS_BIT_KHR |
59 VK_SHADER_STAGE_INTERSECTION_BIT_KHR | VK_SHADER_STAGE_CALLABLE_BIT_KHR;
60
61 enum TestType
62 {
63 TEST_TYPE_FLOW = 0,
64 TEST_TYPE_PRIMITIVE_ID,
65 TEST_TYPE_INSTANCE_ID,
66 TEST_TYPE_INSTANCE_CUSTOM_INDEX,
67 TEST_TYPE_INTERSECTION_T_KHR,
68 TEST_TYPE_OBJECT_RAY_ORIGIN_KHR,
69 TEST_TYPE_OBJECT_RAY_DIRECTION_KHR,
70 TEST_TYPE_OBJECT_TO_WORLD_KHR,
71 TEST_TYPE_WORLD_TO_OBJECT_KHR,
72 TEST_TYPE_NULL_ACCELERATION_STRUCTURE,
73 TEST_TYPE_USING_WRAPPER_FUNCTION,
74 TEST_TYPE_GET_RAY_TMIN,
75 TEST_TYPE_GET_WORLD_RAY_ORIGIN,
76 TEST_TYPE_GET_WORLD_RAY_DIRECTION,
77 TEST_TYPE_GET_INTERSECTION_CANDIDATE_AABB_OPAQUE,
78 TEST_TYPE_GET_INTERSECTION_FRONT_FACE_CANDIDATE,
79 TEST_TYPE_GET_INTERSECTION_FRONT_FACE_COMMITTED,
80 TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_CANDIDATE,
81 TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_COMMITTED,
82 TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE,
83 TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED,
84 TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_CANDIDATE,
85 TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_COMMITTED,
86 TEST_TYPE_RAY_QUERY_TERMINATE,
87 TEST_TYPE_GET_INTERSECTION_TYPE_CANDIDATE,
88 TEST_TYPE_GET_INTERSECTION_TYPE_COMMITTED,
89
90 TEST_TYPE_LAST
91 };
92
93 enum GeomType
94 {
95 GEOM_TYPE_TRIANGLES,
96 GEOM_TYPE_AABBS,
97 GEOM_TYPE_LAST,
98 };
99
100 const uint32_t TEST_WIDTH = 8;
101 const uint32_t TEST_HEIGHT = 8;
102 const uint32_t FIXED_POINT_DIVISOR = 1024 * 1024;
103 const uint32_t FIXED_POINT_ALLOWED_ERROR = static_cast<uint32_t>(float(1e-3f) * FIXED_POINT_DIVISOR);
104
105 struct TestParams;
106
107 // Similar to a subset of the test context but allows us to plug in a custom device when needed.
108 // Note TestEnvironment objects do not own the resources they point to.
109 struct TestEnvironment
110 {
111 const InstanceInterface *vki;
112 VkPhysicalDevice physicalDevice;
113 const DeviceInterface *vkd;
114 VkDevice device;
115 Allocator *allocator;
116 VkQueue queue;
117 uint32_t queueFamilyIndex;
118 BinaryCollection *binaryCollection;
119 tcu::TestLog *log;
120 };
121
122 typedef void (*CheckSupportFunc)(Context &context, const TestParams &testParams);
123 typedef void (*InitProgramsFunc)(SourceCollections &programCollection, const TestParams &testParams);
124 typedef const std::string (*ShaderBodyTextFunc)(const TestParams &testParams);
125
126 class PipelineConfiguration
127 {
128 public:
PipelineConfiguration()129 PipelineConfiguration()
130 {
131 }
~PipelineConfiguration()132 virtual ~PipelineConfiguration()
133 {
134 }
135
136 virtual void initConfiguration(const TestEnvironment &env, TestParams &testParams) = 0;
137 virtual void fillCommandBuffer(const TestEnvironment &env, TestParams &testParams, VkCommandBuffer commandBuffer,
138 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
139 const VkDescriptorImageInfo &resultImageInfo) = 0;
140 };
141
142 class TestConfiguration
143 {
144 public:
TestConfiguration(Context & context)145 TestConfiguration(Context &context)
146 : m_bottomAccelerationStructures()
147 , m_topAccelerationStructure()
148 , m_expected()
149 , m_testEnvironment()
150 {
151 prepareTestEnvironment(context);
152 }
~TestConfiguration()153 virtual ~TestConfiguration()
154 {
155 }
156
157 const TestEnvironment &getTestEnvironment() const;
158 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
159 VkCommandBuffer cmdBuffer) = 0;
160 virtual bool verify(BufferWithMemory *resultBuffer, TestParams &testParams);
161
162 protected:
163 void prepareTestEnvironment(Context &context);
164
165 std::vector<de::SharedPtr<BottomLevelAccelerationStructure>> m_bottomAccelerationStructures;
166 de::SharedPtr<TopLevelAccelerationStructure> m_topAccelerationStructure;
167 std::vector<int32_t> m_expected;
168 de::MovePtr<TestEnvironment> m_testEnvironment;
169 };
170
171 class TestConfigurationFloat : public TestConfiguration
172 {
173 public:
TestConfigurationFloat(Context & context)174 TestConfigurationFloat(Context &context) : TestConfiguration(context)
175 {
176 }
~TestConfigurationFloat()177 virtual ~TestConfigurationFloat()
178 {
179 }
180 virtual bool verify(BufferWithMemory *resultBuffer, TestParams &testParams) override;
181 };
182
183 class TestConfigurationVector : public TestConfiguration
184 {
185 public:
TestConfigurationVector(Context & context,bool useStrictComponentMatching=true)186 TestConfigurationVector(Context &context, bool useStrictComponentMatching = true)
187 : TestConfiguration(context)
188 , m_useStrictComponentMatching(useStrictComponentMatching)
189 {
190 }
~TestConfigurationVector()191 virtual ~TestConfigurationVector()
192 {
193 }
194 virtual bool verify(BufferWithMemory *resultBuffer, TestParams &testParams) override;
195
196 private:
197 bool m_useStrictComponentMatching;
198 };
199
200 class TestConfigurationMatrix : public TestConfiguration
201 {
202 public:
TestConfigurationMatrix(Context & context)203 TestConfigurationMatrix(Context &context) : TestConfiguration(context)
204 {
205 }
~TestConfigurationMatrix()206 virtual ~TestConfigurationMatrix()
207 {
208 }
209 virtual bool verify(BufferWithMemory *resultBuffer, TestParams &testParams) override;
210 };
211
212 struct TestParams
213 {
214 uint32_t width;
215 uint32_t height;
216 uint32_t depth;
217 TestType testType;
218 VkShaderStageFlagBits stage;
219 GeomType geomType;
220 uint32_t squaresGroupCount;
221 uint32_t geometriesGroupCount;
222 uint32_t instancesGroupCount;
223 VkFormat format;
224 CheckSupportFunc pipelineCheckSupport;
225 InitProgramsFunc pipelineInitPrograms;
226 ShaderBodyTextFunc testConfigShaderBodyText;
227 bool isSPIRV; // determines if shader body is defined in SPIR-V
228 CheckSupportFunc testConfigCheckSupport;
229 };
230
getShaderGroupHandleSize(const InstanceInterface & vki,const VkPhysicalDevice physicalDevice)231 uint32_t getShaderGroupHandleSize(const InstanceInterface &vki, const VkPhysicalDevice physicalDevice)
232 {
233 de::MovePtr<RayTracingProperties> rayTracingPropertiesKHR;
234
235 rayTracingPropertiesKHR = makeRayTracingProperties(vki, physicalDevice);
236
237 return rayTracingPropertiesKHR->getShaderGroupHandleSize();
238 }
239
getShaderGroupBaseAlignment(const InstanceInterface & vki,const VkPhysicalDevice physicalDevice)240 uint32_t getShaderGroupBaseAlignment(const InstanceInterface &vki, const VkPhysicalDevice physicalDevice)
241 {
242 de::MovePtr<RayTracingProperties> rayTracingPropertiesKHR;
243
244 rayTracingPropertiesKHR = makeRayTracingProperties(vki, physicalDevice);
245
246 return rayTracingPropertiesKHR->getShaderGroupBaseAlignment();
247 }
248
makeImageCreateInfo(VkFormat format,uint32_t width,uint32_t height,uint32_t depth,VkImageType imageType=VK_IMAGE_TYPE_3D,VkImageUsageFlags usageFlags=VK_IMAGE_USAGE_STORAGE_BIT|VK_IMAGE_USAGE_TRANSFER_SRC_BIT|VK_IMAGE_USAGE_TRANSFER_DST_BIT)249 VkImageCreateInfo makeImageCreateInfo(VkFormat format, uint32_t width, uint32_t height, uint32_t depth,
250 VkImageType imageType = VK_IMAGE_TYPE_3D,
251 VkImageUsageFlags usageFlags = VK_IMAGE_USAGE_STORAGE_BIT |
252 VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
253 VK_IMAGE_USAGE_TRANSFER_DST_BIT)
254 {
255 const VkImageCreateInfo imageCreateInfo = {
256 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType;
257 DE_NULL, // const void* pNext;
258 (VkImageCreateFlags)0u, // VkImageCreateFlags flags;
259 imageType, // VkImageType imageType;
260 format, // VkFormat format;
261 makeExtent3D(width, height, depth), // VkExtent3D extent;
262 1u, // uint32_t mipLevels;
263 1u, // uint32_t arrayLayers;
264 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples;
265 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling;
266 usageFlags, // VkImageUsageFlags usage;
267 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
268 0u, // uint32_t queueFamilyIndexCount;
269 DE_NULL, // const uint32_t* pQueueFamilyIndices;
270 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout;
271 };
272
273 return imageCreateInfo;
274 }
275
getMissPassthrough(void)276 static const std::string getMissPassthrough(void)
277 {
278 const std::string missPassthrough = "#version 460 core\n"
279 "#extension GL_EXT_ray_tracing : require\n"
280 "layout(location = 0) rayPayloadInEXT vec3 hitValue;\n"
281 "\n"
282 "void main()\n"
283 "{\n"
284 "}\n";
285
286 return missPassthrough;
287 }
288
getHitPassthrough(void)289 static const std::string getHitPassthrough(void)
290 {
291 const std::string hitPassthrough = "#version 460 core\n"
292 "#extension GL_EXT_ray_tracing : require\n"
293 "hitAttributeEXT vec3 attribs;\n"
294 "layout(location = 0) rayPayloadInEXT vec3 hitValue;\n"
295 "\n"
296 "void main()\n"
297 "{\n"
298 "}\n";
299
300 return hitPassthrough;
301 }
302
getGraphicsPassthrough(void)303 static const std::string getGraphicsPassthrough(void)
304 {
305 std::ostringstream src;
306
307 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
308 << "\n"
309 << "void main(void)\n"
310 << "{\n"
311 << "}\n";
312
313 return src.str();
314 }
315
getVertexPassthrough(void)316 static const std::string getVertexPassthrough(void)
317 {
318 std::ostringstream src;
319
320 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
321 << "\n"
322 << "layout(location = 0) in vec4 in_position;\n"
323 << "\n"
324 << "void main(void)\n"
325 << "{\n"
326 << " gl_Position = in_position;\n"
327 << "}\n";
328
329 return src.str();
330 }
331
getGeomName(bool writePointSize)332 static const std::string getGeomName(bool writePointSize)
333 {
334 std::ostringstream str;
335 str << "geom" << (writePointSize ? "_point_size" : "");
336 return str.str();
337 }
338
339 class GraphicsConfiguration : public PipelineConfiguration
340 {
341 public:
342 static void checkSupport(Context &context, const TestParams &testParams);
343 static void initPrograms(SourceCollections &programCollection, const TestParams &testParams);
344
345 GraphicsConfiguration();
~GraphicsConfiguration()346 virtual ~GraphicsConfiguration()
347 {
348 }
349
350 void initVertexBuffer(const TestEnvironment &env, TestParams &testParams);
351 Move<VkPipeline> makeGraphicsPipeline(const TestEnvironment &env, TestParams &testParams);
352 virtual void initConfiguration(const TestEnvironment &env, TestParams &testParams) override;
353 virtual void fillCommandBuffer(const TestEnvironment &env, TestParams &testParams, VkCommandBuffer commandBuffer,
354 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
355 const VkDescriptorImageInfo &resultImageInfo) override;
356
357 private:
358 Move<VkDescriptorSetLayout> m_descriptorSetLayout;
359 Move<VkDescriptorPool> m_descriptorPool;
360 Move<VkDescriptorSet> m_descriptorSet;
361
362 VkFormat m_framebufferFormat;
363 Move<VkImage> m_framebufferImage;
364 de::MovePtr<Allocation> m_framebufferImageAlloc;
365 Move<VkImageView> m_framebufferAttachment;
366
367 Move<VkShaderModule> m_vertShaderModule;
368 Move<VkShaderModule> m_geomShaderModule;
369 Move<VkShaderModule> m_tescShaderModule;
370 Move<VkShaderModule> m_teseShaderModule;
371 Move<VkShaderModule> m_fragShaderModule;
372
373 Move<VkRenderPass> m_renderPass;
374 Move<VkFramebuffer> m_framebuffer;
375 Move<VkPipelineLayout> m_pipelineLayout;
376 Move<VkPipeline> m_pipeline;
377
378 uint32_t m_vertexCount;
379 Move<VkBuffer> m_vertexBuffer;
380 de::MovePtr<Allocation> m_vertexBufferAlloc;
381 };
382
GraphicsConfiguration()383 GraphicsConfiguration::GraphicsConfiguration()
384 : PipelineConfiguration()
385 , m_descriptorSetLayout()
386 , m_descriptorPool()
387 , m_descriptorSet()
388 , m_framebufferFormat(VK_FORMAT_R8G8B8A8_UNORM)
389 , m_framebufferImage()
390 , m_framebufferImageAlloc()
391 , m_framebufferAttachment()
392 , m_vertShaderModule()
393 , m_geomShaderModule()
394 , m_tescShaderModule()
395 , m_teseShaderModule()
396 , m_fragShaderModule()
397 , m_renderPass()
398 , m_framebuffer()
399 , m_pipelineLayout()
400 , m_pipeline()
401 , m_vertexCount(0)
402 , m_vertexBuffer()
403 , m_vertexBufferAlloc()
404 {
405 }
406
checkSupport(Context & context,const TestParams & testParams)407 void GraphicsConfiguration::checkSupport(Context &context, const TestParams &testParams)
408 {
409 switch (testParams.stage)
410 {
411 case VK_SHADER_STAGE_VERTEX_BIT:
412 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
413 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
414 case VK_SHADER_STAGE_GEOMETRY_BIT:
415 context.requireDeviceCoreFeature(DEVICE_CORE_FEATURE_VERTEX_PIPELINE_STORES_AND_ATOMICS);
416 break;
417 default:
418 break;
419 }
420
421 switch (testParams.stage)
422 {
423 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
424 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
425 context.requireDeviceCoreFeature(DEVICE_CORE_FEATURE_TESSELLATION_SHADER);
426 break;
427 case VK_SHADER_STAGE_GEOMETRY_BIT:
428 context.requireDeviceCoreFeature(DEVICE_CORE_FEATURE_GEOMETRY_SHADER);
429 break;
430 default:
431 break;
432 }
433 }
434
initPrograms(SourceCollections & programCollection,const TestParams & testParams)435 void GraphicsConfiguration::initPrograms(SourceCollections &programCollection, const TestParams &testParams)
436 {
437 const vk::ShaderBuildOptions buildOptions(programCollection.usedVulkanVersion, vk::SPIRV_VERSION_1_4, 0u, true);
438
439 const std::string testShaderBody = testParams.testConfigShaderBodyText(testParams);
440
441 switch (testParams.stage)
442 {
443 case VK_SHADER_STAGE_VERTEX_BIT:
444 {
445 {
446 std::ostringstream src;
447 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
448 << "#extension GL_EXT_ray_query : require\n"
449 << "#extension GL_EXT_ray_tracing : require\n"
450 << "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
451 << "layout(set = 0, binding = 1) uniform accelerationStructureEXT "
452 "rayQueryTopLevelAccelerationStructure;\n"
453 << "\n"
454 << "void testFunc(ivec3 pos, ivec3 size)\n"
455 << "{\n"
456 << testShaderBody << "}\n"
457 << "\n"
458 << "void main(void)\n"
459 << "{\n"
460 << " const int posId = int(gl_VertexIndex / 3);\n"
461 << " const int vertId = int(gl_VertexIndex % 3);\n"
462 << " const ivec3 size = ivec3(" << testParams.width << ", " << testParams.height << ", 1);\n"
463 << " const ivec3 pos = ivec3(posId % size.x, posId / size.x, 0);\n"
464 << "\n"
465 << " if (vertId == 0)\n"
466 << " {\n"
467 << " testFunc(pos, size);\n"
468 << " }\n"
469 << "}\n";
470
471 programCollection.glslSources.add("vert") << glu::VertexSource(src.str()) << buildOptions;
472 }
473
474 programCollection.glslSources.add("frag") << glu::FragmentSource(getGraphicsPassthrough()) << buildOptions;
475
476 break;
477 }
478
479 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
480 {
481 {
482 std::ostringstream src;
483 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
484 << "\n"
485 << "layout(location = 0) in vec4 in_position;\n"
486 << "out gl_PerVertex\n"
487 << "{\n"
488 << " vec4 gl_Position;\n"
489 << "};\n"
490 << "\n"
491 << "void main(void)\n"
492 << "{\n"
493 << " gl_Position = in_position;\n"
494 << "}\n";
495
496 programCollection.glslSources.add("vert") << glu::VertexSource(src.str()) << buildOptions;
497 }
498
499 {
500 std::ostringstream src;
501 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
502 << "#extension GL_EXT_tessellation_shader : require\n"
503 << "#extension GL_EXT_ray_query : require\n"
504 << "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
505 << "layout(set = 0, binding = 1) uniform accelerationStructureEXT "
506 "rayQueryTopLevelAccelerationStructure;\n"
507 << "in gl_PerVertex\n"
508 << "{\n"
509 << " vec4 gl_Position;\n"
510 << "} gl_in[];\n"
511 << "layout(vertices = 4) out;\n"
512 << "out gl_PerVertex\n"
513 << "{\n"
514 << " vec4 gl_Position;\n"
515 << "} gl_out[];\n"
516 << "\n"
517 << "void testFunc(ivec3 pos, ivec3 size)\n"
518 << "{\n"
519 << testShaderBody << "}\n"
520 << "\n"
521 << "void main(void)\n"
522 << "{\n"
523 << "\n"
524 << " if (gl_InvocationID == 0)\n"
525 << " {\n"
526 << " const ivec3 size = ivec3(" << testParams.width << ", " << testParams.height << ", 1);\n"
527 << " for (int y = 0; y < size.y; y++)\n"
528 << " for (int x = 0; x < size.x; x++)\n"
529 << " {\n"
530 << " const ivec3 pos = ivec3(x, y, 0);\n"
531 << " testFunc(pos, size);\n"
532 << " }\n"
533 << " }\n"
534 << "\n"
535 << " gl_out[gl_InvocationID].gl_Position = gl_in[gl_InvocationID].gl_Position;\n"
536 << " gl_TessLevelInner[0] = 1;\n"
537 << " gl_TessLevelInner[1] = 1;\n"
538 << " gl_TessLevelOuter[gl_InvocationID] = 1;\n"
539 << "}\n";
540
541 programCollection.glslSources.add("tesc") << glu::TessellationControlSource(src.str()) << buildOptions;
542 }
543
544 {
545 std::ostringstream src;
546 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
547 << "#extension GL_EXT_tessellation_shader : require\n"
548 << "layout(quads, equal_spacing, ccw) in;\n"
549 << "in gl_PerVertex\n"
550 << "{\n"
551 << " vec4 gl_Position;\n"
552 << "} gl_in[];\n"
553 << "\n"
554 << "void main(void)\n"
555 << "{\n"
556 << " gl_Position = gl_in[0].gl_Position;\n"
557 << "}\n";
558
559 programCollection.glslSources.add("tese") << glu::TessellationEvaluationSource(src.str()) << buildOptions;
560 }
561
562 break;
563 }
564
565 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
566 {
567 {
568 std::ostringstream src;
569 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
570 << "\n"
571 << "layout(location = 0) in vec4 in_position;\n"
572 << "out gl_PerVertex"
573 << "{\n"
574 << " vec4 gl_Position;\n"
575 << "};\n"
576 << "\n"
577 << "void main(void)\n"
578 << "{\n"
579 << " gl_Position = in_position;\n"
580 << "}\n";
581
582 programCollection.glslSources.add("vert") << glu::VertexSource(src.str()) << buildOptions;
583 }
584
585 {
586 std::ostringstream src;
587 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
588 << "#extension GL_EXT_tessellation_shader : require\n"
589 << "in gl_PerVertex\n"
590 << "{\n"
591 << " vec4 gl_Position;\n"
592 << "} gl_in[];\n"
593 << "layout(vertices = 4) out;\n"
594 << "out gl_PerVertex\n"
595 << "{\n"
596 << " vec4 gl_Position;\n"
597 << "} gl_out[];\n"
598 << "\n"
599 << "void main(void)\n"
600 << "{\n"
601 << " gl_out[gl_InvocationID].gl_Position = gl_in[gl_InvocationID].gl_Position;\n"
602 << " gl_TessLevelInner[0] = 1;\n"
603 << " gl_TessLevelInner[1] = 1;\n"
604 << " gl_TessLevelOuter[gl_InvocationID] = 1;\n"
605 << "}\n";
606
607 programCollection.glslSources.add("tesc") << glu::TessellationControlSource(src.str()) << buildOptions;
608 }
609
610 {
611 std::ostringstream src;
612 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
613 << "#extension GL_EXT_tessellation_shader : require\n"
614 << "#extension GL_EXT_ray_query : require\n"
615 << "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
616 << "layout(set = 0, binding = 1) uniform accelerationStructureEXT "
617 "rayQueryTopLevelAccelerationStructure;\n"
618 << "layout(quads, equal_spacing, ccw) in;\n"
619 << "in gl_PerVertex\n"
620 << "{\n"
621 << " vec4 gl_Position;\n"
622 << "} gl_in[];\n"
623 << "\n"
624 << "void testFunc(ivec3 pos, ivec3 size)\n"
625 << "{\n"
626 << testShaderBody << "}\n"
627 << "\n"
628 << "void main(void)\n"
629 << "{\n"
630 << " const ivec3 size = ivec3(" << testParams.width << ", " << testParams.height << ", 1);\n"
631 << "\n"
632 << " if (gl_PrimitiveID == 0)\n"
633 << " {\n"
634 << " const ivec3 size = ivec3(" << testParams.width << ", " << testParams.height << ", 1);\n"
635 << " for (int y = 0; y < size.y; y++)\n"
636 << " for (int x = 0; x < size.x; x++)\n"
637 << " {\n"
638 << " const ivec3 pos = ivec3(x, y, 0);\n"
639 << " testFunc(pos, size);\n"
640 << " }\n"
641 << " }\n"
642 << "\n"
643 << " gl_Position = gl_in[0].gl_Position;\n"
644 << "}\n";
645
646 programCollection.glslSources.add("tese") << glu::TessellationEvaluationSource(src.str()) << buildOptions;
647 }
648
649 break;
650 }
651
652 case VK_SHADER_STAGE_GEOMETRY_BIT:
653 {
654 programCollection.glslSources.add("vert") << glu::VertexSource(getVertexPassthrough()) << buildOptions;
655
656 for (uint32_t i = 0; i < 2; ++i)
657 {
658 const bool writePointSize = i == 1;
659 std::string pointSize = writePointSize ? " gl_PointSize = 1.0f;\n" : "";
660
661 std::ostringstream src;
662 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
663 << "#extension GL_EXT_ray_query : require\n"
664 << "layout(triangles) in;\n"
665 << "layout(points, max_vertices = 1) out;\n"
666 << "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
667 << "layout(set = 0, binding = 1) uniform accelerationStructureEXT "
668 "rayQueryTopLevelAccelerationStructure;\n"
669 << "\n"
670 << "void testFunc(ivec3 pos, ivec3 size)\n"
671 << "{\n"
672 << testShaderBody << "}\n"
673 << "\n"
674 << "void main(void)\n"
675 << "{\n"
676 << " const int posId = int(gl_PrimitiveIDIn);\n"
677 << " const ivec3 size = ivec3(" << testParams.width << ", " << testParams.height << ", 1);\n"
678 << " const ivec3 pos = ivec3(posId % size.x, posId / size.x, 0);\n"
679 << "\n"
680 << " testFunc(pos, size);\n"
681 << pointSize << "}\n";
682
683 programCollection.glslSources.add(getGeomName(writePointSize))
684 << glu::GeometrySource(src.str()) << buildOptions;
685 }
686
687 break;
688 }
689
690 case VK_SHADER_STAGE_FRAGMENT_BIT:
691 {
692 programCollection.glslSources.add("vert") << glu::VertexSource(getVertexPassthrough()) << buildOptions;
693
694 {
695 std::ostringstream src;
696 src << glu::getGLSLVersionDeclaration(glu::GLSL_VERSION_460) << "\n"
697 << "#extension GL_EXT_ray_query : require\n"
698 << "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
699 << "layout(set = 0, binding = 1) uniform accelerationStructureEXT "
700 "rayQueryTopLevelAccelerationStructure;\n"
701 << "\n"
702 << "void testFunc(ivec3 pos, ivec3 size)\n"
703 << "{\n"
704 << testShaderBody << "}\n"
705 << "\n"
706 << "void main(void)\n"
707 << "{\n"
708 << " const ivec3 size = ivec3(" << testParams.width << ", " << testParams.height << ", 1);\n"
709 << " const ivec3 pos = ivec3(int(gl_FragCoord.x - 0.5f), int(gl_FragCoord.y - 0.5f), 0);\n"
710 << "\n"
711 << " testFunc(pos, size);\n"
712 << "}\n";
713
714 programCollection.glslSources.add("frag") << glu::FragmentSource(src.str()) << buildOptions;
715 }
716
717 break;
718 }
719
720 default:
721 TCU_THROW(InternalError, "Unknown stage");
722 }
723 }
724
initVertexBuffer(const TestEnvironment & env,TestParams & testParams)725 void GraphicsConfiguration::initVertexBuffer(const TestEnvironment &env, TestParams &testParams)
726 {
727 const DeviceInterface &vkd = *env.vkd;
728 const VkDevice device = env.device;
729 Allocator &allocator = *env.allocator;
730 const uint32_t width = testParams.width;
731 const uint32_t height = testParams.height;
732 std::vector<tcu::Vec4> vertices;
733
734 switch (testParams.stage)
735 {
736 case VK_SHADER_STAGE_VERTEX_BIT:
737 {
738 const float z = 0.0f;
739 const float w = 1.0f;
740
741 vertices.reserve(3 * height * width);
742
743 for (uint32_t y = 0; y < height; ++y)
744 for (uint32_t x = 0; x < width; ++x)
745 {
746 const float x0 = float(x + 0) / float(width);
747 const float y0 = float(y + 0) / float(height);
748 const float x1 = float(x + 1) / float(width);
749 const float y1 = float(y + 1) / float(height);
750 const float xm = (x0 + x1) / 2.0f;
751 const float ym = (y0 + y1) / 2.0f;
752
753 vertices.push_back(tcu::Vec4(x0, y0, z, w));
754 vertices.push_back(tcu::Vec4(xm, y1, z, w));
755 vertices.push_back(tcu::Vec4(x1, ym, z, w));
756 }
757
758 break;
759 }
760
761 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
762 {
763 const float z = 0.0f;
764 const float w = 1.0f;
765 const tcu::Vec4 a = tcu::Vec4(-1.0f, -1.0f, z, w);
766 const tcu::Vec4 b = tcu::Vec4(+1.0f, -1.0f, z, w);
767 const tcu::Vec4 c = tcu::Vec4(+1.0f, +1.0f, z, w);
768 const tcu::Vec4 d = tcu::Vec4(-1.0f, +1.0f, z, w);
769
770 vertices.push_back(a);
771 vertices.push_back(b);
772 vertices.push_back(c);
773 vertices.push_back(d);
774
775 break;
776 }
777
778 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
779 {
780 const float z = 0.0f;
781 const float w = 1.0f;
782 const tcu::Vec4 a = tcu::Vec4(-1.0f, -1.0f, z, w);
783 const tcu::Vec4 b = tcu::Vec4(+1.0f, -1.0f, z, w);
784 const tcu::Vec4 c = tcu::Vec4(+1.0f, +1.0f, z, w);
785 const tcu::Vec4 d = tcu::Vec4(-1.0f, +1.0f, z, w);
786
787 vertices.push_back(a);
788 vertices.push_back(b);
789 vertices.push_back(c);
790 vertices.push_back(d);
791
792 break;
793 }
794
795 case VK_SHADER_STAGE_GEOMETRY_BIT:
796 {
797 const float z = 0.0f;
798 const float w = 1.0f;
799
800 vertices.reserve(3 * height * width);
801
802 for (uint32_t y = 0; y < height; ++y)
803 for (uint32_t x = 0; x < width; ++x)
804 {
805 const float x0 = float(x + 0) / float(width);
806 const float y0 = float(y + 0) / float(height);
807 const float x1 = float(x + 1) / float(width);
808 const float y1 = float(y + 1) / float(height);
809 const float xm = (x0 + x1) / 2.0f;
810 const float ym = (y0 + y1) / 2.0f;
811
812 vertices.push_back(tcu::Vec4(x0, y0, z, w));
813 vertices.push_back(tcu::Vec4(xm, y1, z, w));
814 vertices.push_back(tcu::Vec4(x1, ym, z, w));
815 }
816
817 break;
818 }
819
820 case VK_SHADER_STAGE_FRAGMENT_BIT:
821 {
822 const float z = 1.0f;
823 const float w = 1.0f;
824 const tcu::Vec4 a = tcu::Vec4(-1.0f, -1.0f, z, w);
825 const tcu::Vec4 b = tcu::Vec4(+1.0f, -1.0f, z, w);
826 const tcu::Vec4 c = tcu::Vec4(-1.0f, +1.0f, z, w);
827 const tcu::Vec4 d = tcu::Vec4(+1.0f, +1.0f, z, w);
828
829 vertices.push_back(a);
830 vertices.push_back(b);
831 vertices.push_back(c);
832
833 vertices.push_back(b);
834 vertices.push_back(c);
835 vertices.push_back(d);
836
837 break;
838 }
839
840 default:
841 TCU_THROW(InternalError, "Unknown stage");
842 }
843
844 // Initialize vertex buffer
845 {
846 const VkDeviceSize vertexBufferSize = sizeof(vertices[0][0]) * vertices[0].SIZE * vertices.size();
847 const VkBufferCreateInfo vertexBufferCreateInfo =
848 makeBufferCreateInfo(vertexBufferSize, VK_BUFFER_USAGE_VERTEX_BUFFER_BIT);
849
850 m_vertexCount = static_cast<uint32_t>(vertices.size());
851 m_vertexBuffer = createBuffer(vkd, device, &vertexBufferCreateInfo);
852 m_vertexBufferAlloc = bindBuffer(vkd, device, allocator, *m_vertexBuffer, vk::MemoryRequirement::HostVisible);
853
854 deMemcpy(m_vertexBufferAlloc->getHostPtr(), vertices.data(), (size_t)vertexBufferSize);
855 flushAlloc(vkd, device, *m_vertexBufferAlloc);
856 }
857 }
858
makeGraphicsPipeline(const TestEnvironment & env,TestParams & testParams)859 Move<VkPipeline> GraphicsConfiguration::makeGraphicsPipeline(const TestEnvironment &env, TestParams &testParams)
860 {
861 const DeviceInterface &vkd = *env.vkd;
862 const VkDevice device = env.device;
863 const bool tessStageTest = (testParams.stage == VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT ||
864 testParams.stage == VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT);
865 const VkPrimitiveTopology topology =
866 tessStageTest ? VK_PRIMITIVE_TOPOLOGY_PATCH_LIST : VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
867 const uint32_t patchControlPoints = tessStageTest ? 4 : 0;
868 const std::vector<VkViewport> viewports(1, makeViewport(testParams.width, testParams.height));
869 const std::vector<VkRect2D> scissors(1, makeRect2D(testParams.width, testParams.height));
870
871 return vk::makeGraphicsPipeline(vkd, device, *m_pipelineLayout, *m_vertShaderModule, *m_tescShaderModule,
872 *m_teseShaderModule, *m_geomShaderModule, *m_fragShaderModule, *m_renderPass,
873 viewports, scissors, topology, 0, patchControlPoints);
874 }
875
initConfiguration(const TestEnvironment & env,TestParams & testParams)876 void GraphicsConfiguration::initConfiguration(const TestEnvironment &env, TestParams &testParams)
877 {
878 const InstanceInterface &vki = *env.vki;
879 const DeviceInterface &vkd = *env.vkd;
880 const VkPhysicalDevice physicalDevice = env.physicalDevice;
881 const VkDevice device = env.device;
882 Allocator &allocator = *env.allocator;
883 vk::BinaryCollection &collection = *env.binaryCollection;
884 VkShaderStageFlags shaders = static_cast<VkShaderStageFlags>(0);
885 uint32_t shaderCount = 0;
886
887 VkPhysicalDeviceFeatures features;
888 vki.getPhysicalDeviceFeatures(physicalDevice, &features);
889 const bool pointSizeRequired = features.shaderTessellationAndGeometryPointSize;
890
891 if (collection.contains("vert"))
892 shaders |= VK_SHADER_STAGE_VERTEX_BIT;
893 if (collection.contains(getGeomName(pointSizeRequired)))
894 shaders |= VK_SHADER_STAGE_GEOMETRY_BIT;
895 if (collection.contains("tesc"))
896 shaders |= VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT;
897 if (collection.contains("tese"))
898 shaders |= VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT;
899 if (collection.contains("frag"))
900 shaders |= VK_SHADER_STAGE_FRAGMENT_BIT;
901
902 for (BinaryCollection::Iterator it = collection.begin(); it != collection.end(); ++it)
903 shaderCount++;
904
905 if (collection.contains(getGeomName(!pointSizeRequired)))
906 --shaderCount;
907
908 if (shaderCount != (uint32_t)dePop32(shaders))
909 TCU_THROW(InternalError, "Unused shaders detected in the collection");
910
911 if (0 != (shaders & VK_SHADER_STAGE_VERTEX_BIT))
912 m_vertShaderModule = createShaderModule(vkd, device, collection.get("vert"), 0);
913 if (0 != (shaders & VK_SHADER_STAGE_GEOMETRY_BIT))
914 m_geomShaderModule = createShaderModule(vkd, device, collection.get(getGeomName(pointSizeRequired)), 0);
915 if (0 != (shaders & VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT))
916 m_tescShaderModule = createShaderModule(vkd, device, collection.get("tesc"), 0);
917 if (0 != (shaders & VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT))
918 m_teseShaderModule = createShaderModule(vkd, device, collection.get("tese"), 0);
919 if (0 != (shaders & VK_SHADER_STAGE_FRAGMENT_BIT))
920 m_fragShaderModule = createShaderModule(vkd, device, collection.get("frag"), 0);
921
922 m_descriptorSetLayout =
923 DescriptorSetLayoutBuilder()
924 .addSingleBinding(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, VK_SHADER_STAGE_ALL_GRAPHICS)
925 .addSingleBinding(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, VK_SHADER_STAGE_ALL_GRAPHICS)
926 .build(vkd, device);
927 m_descriptorPool = DescriptorPoolBuilder()
928 .addType(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE)
929 .addType(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR)
930 .build(vkd, device, VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, 1u);
931 m_descriptorSet = makeDescriptorSet(vkd, device, *m_descriptorPool, *m_descriptorSetLayout);
932 m_framebufferImage = makeImage(vkd, device,
933 makeImageCreateInfo(m_framebufferFormat, testParams.width, testParams.height, 1u,
934 VK_IMAGE_TYPE_2D, VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT));
935 m_framebufferImageAlloc = bindImage(vkd, device, allocator, *m_framebufferImage, MemoryRequirement::Any);
936 m_framebufferAttachment =
937 makeImageView(vkd, device, *m_framebufferImage, VK_IMAGE_VIEW_TYPE_2D, m_framebufferFormat,
938 makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u));
939 m_renderPass = makeRenderPass(vkd, device, m_framebufferFormat);
940 m_framebuffer =
941 makeFramebuffer(vkd, device, *m_renderPass, *m_framebufferAttachment, testParams.width, testParams.height);
942 m_pipelineLayout = makePipelineLayout(vkd, device, m_descriptorSetLayout.get());
943 m_pipeline = makeGraphicsPipeline(env, testParams);
944
945 initVertexBuffer(env, testParams);
946 }
947
fillCommandBuffer(const TestEnvironment & env,TestParams & testParams,VkCommandBuffer cmdBuffer,const VkAccelerationStructureKHR * rayQueryTopAccelerationStructurePtr,const VkDescriptorImageInfo & resultImageInfo)948 void GraphicsConfiguration::fillCommandBuffer(const TestEnvironment &env, TestParams &testParams,
949 VkCommandBuffer cmdBuffer,
950 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
951 const VkDescriptorImageInfo &resultImageInfo)
952 {
953 const DeviceInterface &vkd = *env.vkd;
954 const VkDevice device = env.device;
955 const VkDeviceSize vertexBufferOffset = 0;
956 const VkWriteDescriptorSetAccelerationStructureKHR rayQueryAccelerationStructureWriteDescriptorSet = {
957 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET_ACCELERATION_STRUCTURE_KHR, // VkStructureType sType;
958 DE_NULL, // const void* pNext;
959 1u, // uint32_t accelerationStructureCount;
960 rayQueryTopAccelerationStructurePtr, // const VkAccelerationStructureKHR* pAccelerationStructures;
961 };
962
963 DescriptorSetUpdateBuilder()
964 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(0u),
965 VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, &resultImageInfo)
966 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(1u),
967 VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, &rayQueryAccelerationStructureWriteDescriptorSet)
968 .update(vkd, device);
969
970 vkd.cmdBindDescriptorSets(cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *m_pipelineLayout, 0, 1,
971 &m_descriptorSet.get(), 0, DE_NULL);
972 vkd.cmdBindPipeline(cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *m_pipeline);
973 vkd.cmdBindVertexBuffers(cmdBuffer, 0u, 1u, &m_vertexBuffer.get(), &vertexBufferOffset);
974
975 beginRenderPass(vkd, cmdBuffer, *m_renderPass, *m_framebuffer,
976 makeRect2D(0, 0, testParams.width, testParams.height), tcu::UVec4());
977
978 vkd.cmdDraw(cmdBuffer, m_vertexCount, 1u, 0u, 0u);
979
980 endRenderPass(vkd, cmdBuffer);
981 }
982
983 class ComputeConfiguration : public PipelineConfiguration
984 {
985 public:
986 ComputeConfiguration();
~ComputeConfiguration()987 virtual ~ComputeConfiguration()
988 {
989 }
990
991 static void checkSupport(Context &context, const TestParams &testParams);
992 static void initPrograms(SourceCollections &programCollection, const TestParams &testParams);
993
994 virtual void initConfiguration(const TestEnvironment &env, TestParams &testParams) override;
995 virtual void fillCommandBuffer(const TestEnvironment &env, TestParams &testParams, VkCommandBuffer commandBuffer,
996 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
997 const VkDescriptorImageInfo &resultImageInfo) override;
998
999 protected:
1000 Move<VkDescriptorSetLayout> m_descriptorSetLayout;
1001 Move<VkDescriptorPool> m_descriptorPool;
1002 Move<VkDescriptorSet> m_descriptorSet;
1003 Move<VkPipelineLayout> m_pipelineLayout;
1004
1005 Move<VkShaderModule> m_shaderModule;
1006
1007 Move<VkPipeline> m_pipeline;
1008 };
1009
ComputeConfiguration()1010 ComputeConfiguration::ComputeConfiguration()
1011 : PipelineConfiguration()
1012 , m_descriptorSetLayout()
1013 , m_descriptorPool()
1014 , m_descriptorSet()
1015 , m_pipelineLayout()
1016
1017 , m_shaderModule()
1018
1019 , m_pipeline()
1020 {
1021 }
1022
checkSupport(Context & context,const TestParams & testParams)1023 void ComputeConfiguration::checkSupport(Context &context, const TestParams &testParams)
1024 {
1025 DE_UNREF(context);
1026 DE_UNREF(testParams);
1027 }
1028
initPrograms(SourceCollections & programCollection,const TestParams & testParams)1029 void ComputeConfiguration::initPrograms(SourceCollections &programCollection, const TestParams &testParams)
1030 {
1031 DE_ASSERT(testParams.stage == VK_SHADER_STAGE_COMPUTE_BIT);
1032
1033 if (testParams.isSPIRV)
1034 {
1035 const vk::SpirVAsmBuildOptions spvBuildOptions(programCollection.usedVulkanVersion, vk::SPIRV_VERSION_1_4,
1036 true);
1037
1038 programCollection.spirvAsmSources.add("comp")
1039 << testParams.testConfigShaderBodyText(testParams) << spvBuildOptions;
1040 }
1041 else
1042 {
1043 const vk::ShaderBuildOptions buildOptions(programCollection.usedVulkanVersion, vk::SPIRV_VERSION_1_4, 0u, true);
1044 const std::string testShaderBody = testParams.testConfigShaderBodyText(testParams);
1045 const std::string testBody = " ivec3 pos = ivec3(gl_WorkGroupID);\n"
1046 " ivec3 size = ivec3(gl_NumWorkGroups);\n" +
1047 testShaderBody;
1048
1049 std::stringstream css;
1050 css << "#version 460 core\n"
1051 "#extension GL_EXT_ray_query : require\n"
1052 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1053 "layout(set = 0, binding = 1) uniform accelerationStructureEXT rayQueryTopLevelAccelerationStructure;\n"
1054 "\n"
1055 "void main()\n"
1056 "{\n"
1057 << testBody << "}\n";
1058
1059 programCollection.glslSources.add("comp")
1060 << glu::ComputeSource(updateRayTracingGLSL(css.str())) << buildOptions;
1061 }
1062 }
1063
initConfiguration(const TestEnvironment & env,TestParams & testParams)1064 void ComputeConfiguration::initConfiguration(const TestEnvironment &env, TestParams &testParams)
1065 {
1066 DE_UNREF(testParams);
1067
1068 const DeviceInterface &vkd = *env.vkd;
1069 const VkDevice device = env.device;
1070 vk::BinaryCollection &collection = *env.binaryCollection;
1071
1072 m_descriptorSetLayout =
1073 DescriptorSetLayoutBuilder()
1074 .addSingleBinding(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, VK_SHADER_STAGE_COMPUTE_BIT)
1075 .addSingleBinding(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, VK_SHADER_STAGE_COMPUTE_BIT)
1076 .build(vkd, device);
1077 m_descriptorPool = DescriptorPoolBuilder()
1078 .addType(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE)
1079 .addType(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR)
1080 .build(vkd, device, VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, 1u);
1081 m_descriptorSet = makeDescriptorSet(vkd, device, *m_descriptorPool, *m_descriptorSetLayout);
1082 m_pipelineLayout = makePipelineLayout(vkd, device, m_descriptorSetLayout.get());
1083 m_shaderModule = createShaderModule(vkd, device, collection.get("comp"), 0);
1084 m_pipeline = makeComputePipeline(vkd, device, *m_pipelineLayout, *m_shaderModule);
1085 }
1086
fillCommandBuffer(const TestEnvironment & env,TestParams & testParams,VkCommandBuffer cmdBuffer,const VkAccelerationStructureKHR * rayQueryTopAccelerationStructurePtr,const VkDescriptorImageInfo & resultImageInfo)1087 void ComputeConfiguration::fillCommandBuffer(const TestEnvironment &env, TestParams &testParams,
1088 VkCommandBuffer cmdBuffer,
1089 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
1090 const VkDescriptorImageInfo &resultImageInfo)
1091 {
1092 const DeviceInterface &vkd = *env.vkd;
1093 const VkDevice device = env.device;
1094 const VkWriteDescriptorSetAccelerationStructureKHR rayQueryAccelerationStructureWriteDescriptorSet = {
1095 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET_ACCELERATION_STRUCTURE_KHR, // VkStructureType sType;
1096 DE_NULL, // const void* pNext;
1097 1u, // uint32_t accelerationStructureCount;
1098 rayQueryTopAccelerationStructurePtr, // const VkAccelerationStructureKHR* pAccelerationStructures;
1099 };
1100
1101 DescriptorSetUpdateBuilder()
1102 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(0u),
1103 VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, &resultImageInfo)
1104 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(1u),
1105 VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, &rayQueryAccelerationStructureWriteDescriptorSet)
1106 .update(vkd, device);
1107
1108 vkd.cmdBindDescriptorSets(cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_pipelineLayout, 0, 1,
1109 &m_descriptorSet.get(), 0, DE_NULL);
1110
1111 vkd.cmdBindPipeline(cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, m_pipeline.get());
1112
1113 vkd.cmdDispatch(cmdBuffer, testParams.width, testParams.height, 1);
1114 }
1115
1116 class RayTracingConfiguration : public PipelineConfiguration
1117 {
1118 public:
1119 RayTracingConfiguration();
~RayTracingConfiguration()1120 virtual ~RayTracingConfiguration()
1121 {
1122 }
1123
1124 static void checkSupport(Context &context, const TestParams &testParams);
1125 static void initPrograms(SourceCollections &programCollection, const TestParams &testParams);
1126
1127 virtual void initConfiguration(const TestEnvironment &env, TestParams &testParams) override;
1128 virtual void fillCommandBuffer(const TestEnvironment &env, TestParams &testParams, VkCommandBuffer commandBuffer,
1129 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
1130 const VkDescriptorImageInfo &resultImageInfo) override;
1131
1132 protected:
1133 de::MovePtr<BufferWithMemory> createShaderBindingTable(const InstanceInterface &vki, const DeviceInterface &vkd,
1134 const VkDevice device, const VkPhysicalDevice physicalDevice,
1135 const VkPipeline pipeline, Allocator &allocator,
1136 de::MovePtr<RayTracingPipeline> &rayTracingPipeline,
1137 const uint32_t group);
1138
1139 protected:
1140 uint32_t m_shaders;
1141 uint32_t m_raygenShaderGroup;
1142 uint32_t m_missShaderGroup;
1143 uint32_t m_hitShaderGroup;
1144 uint32_t m_callableShaderGroup;
1145 uint32_t m_shaderGroupCount;
1146
1147 Move<VkDescriptorSetLayout> m_descriptorSetLayout;
1148 Move<VkDescriptorPool> m_descriptorPool;
1149 Move<VkDescriptorSet> m_descriptorSet;
1150 Move<VkPipelineLayout> m_pipelineLayout;
1151
1152 de::MovePtr<RayTracingPipeline> m_rayTracingPipeline;
1153 Move<VkPipeline> m_pipeline;
1154
1155 de::MovePtr<BufferWithMemory> m_raygenShaderBindingTable;
1156 de::MovePtr<BufferWithMemory> m_hitShaderBindingTable;
1157 de::MovePtr<BufferWithMemory> m_missShaderBindingTable;
1158 de::MovePtr<BufferWithMemory> m_callableShaderBindingTable;
1159
1160 VkStridedDeviceAddressRegionKHR m_raygenShaderBindingTableRegion;
1161 VkStridedDeviceAddressRegionKHR m_missShaderBindingTableRegion;
1162 VkStridedDeviceAddressRegionKHR m_hitShaderBindingTableRegion;
1163 VkStridedDeviceAddressRegionKHR m_callableShaderBindingTableRegion;
1164
1165 de::SharedPtr<BottomLevelAccelerationStructure> m_bottomLevelAccelerationStructure;
1166 de::SharedPtr<TopLevelAccelerationStructure> m_topLevelAccelerationStructure;
1167 };
1168
RayTracingConfiguration()1169 RayTracingConfiguration::RayTracingConfiguration()
1170 : m_shaders(0)
1171 , m_raygenShaderGroup(~0u)
1172 , m_missShaderGroup(~0u)
1173 , m_hitShaderGroup(~0u)
1174 , m_callableShaderGroup(~0u)
1175 , m_shaderGroupCount(0)
1176
1177 , m_descriptorSetLayout()
1178 , m_descriptorPool()
1179 , m_descriptorSet()
1180 , m_pipelineLayout()
1181
1182 , m_rayTracingPipeline()
1183 , m_pipeline()
1184
1185 , m_raygenShaderBindingTable()
1186 , m_hitShaderBindingTable()
1187 , m_missShaderBindingTable()
1188 , m_callableShaderBindingTable()
1189
1190 , m_raygenShaderBindingTableRegion()
1191 , m_missShaderBindingTableRegion()
1192 , m_hitShaderBindingTableRegion()
1193 , m_callableShaderBindingTableRegion()
1194
1195 , m_bottomLevelAccelerationStructure()
1196 , m_topLevelAccelerationStructure()
1197 {
1198 }
1199
checkSupport(Context & context,const TestParams & testParams)1200 void RayTracingConfiguration::checkSupport(Context &context, const TestParams &testParams)
1201 {
1202 DE_UNREF(testParams);
1203
1204 context.requireDeviceFunctionality("VK_KHR_ray_tracing_pipeline");
1205 const VkPhysicalDeviceRayTracingPipelineFeaturesKHR &rayTracingPipelineFeaturesKHR =
1206 context.getRayTracingPipelineFeatures();
1207 if (rayTracingPipelineFeaturesKHR.rayTracingPipeline == false)
1208 TCU_THROW(NotSupportedError, "Requires VkPhysicalDeviceRayTracingPipelineFeaturesKHR.rayTracingPipeline");
1209 }
1210
initPrograms(SourceCollections & programCollection,const TestParams & testParams)1211 void RayTracingConfiguration::initPrograms(SourceCollections &programCollection, const TestParams &testParams)
1212 {
1213 const vk::ShaderBuildOptions buildOptions(programCollection.usedVulkanVersion, vk::SPIRV_VERSION_1_4, 0u, true);
1214
1215 const std::string testShaderBody = testParams.testConfigShaderBodyText(testParams);
1216 const std::string testBody = " ivec3 pos = ivec3(gl_LaunchIDEXT);\n"
1217 " ivec3 size = ivec3(gl_LaunchSizeEXT);\n" +
1218 testShaderBody;
1219
1220 switch (testParams.stage)
1221 {
1222 case VK_SHADER_STAGE_RAYGEN_BIT_KHR:
1223 {
1224 std::stringstream css;
1225 css << "#version 460 core\n"
1226 "#extension GL_EXT_ray_tracing : require\n"
1227 "#extension GL_EXT_ray_query : require\n"
1228 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1229 "layout(set = 0, binding = 2) uniform accelerationStructureEXT rayQueryTopLevelAccelerationStructure;\n"
1230 "\n"
1231 "void main()\n"
1232 "{\n"
1233 << testBody << "}\n";
1234
1235 programCollection.glslSources.add("rgen") << glu::RaygenSource(updateRayTracingGLSL(css.str())) << buildOptions;
1236
1237 break;
1238 }
1239
1240 case VK_SHADER_STAGE_ANY_HIT_BIT_KHR:
1241 {
1242 programCollection.glslSources.add("rgen")
1243 << glu::RaygenSource(updateRayTracingGLSL(getCommonRayGenerationShader())) << buildOptions;
1244
1245 {
1246 std::stringstream css;
1247 css << "#version 460 core\n"
1248 "#extension GL_EXT_ray_tracing : require\n"
1249 "#extension GL_EXT_ray_query : require\n"
1250 "hitAttributeEXT vec3 attribs;\n"
1251 "layout(location = 0) rayPayloadInEXT vec3 hitValue;\n"
1252 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1253 "layout(set = 0, binding = 2) uniform accelerationStructureEXT "
1254 "rayQueryTopLevelAccelerationStructure;\n"
1255 "\n"
1256 "void main()\n"
1257 "{\n"
1258 << testBody << "}\n";
1259
1260 programCollection.glslSources.add("ahit")
1261 << glu::AnyHitSource(updateRayTracingGLSL(css.str())) << buildOptions;
1262 }
1263
1264 programCollection.glslSources.add("chit")
1265 << glu::ClosestHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1266 programCollection.glslSources.add("miss")
1267 << glu::MissSource(updateRayTracingGLSL(getMissPassthrough())) << buildOptions;
1268
1269 break;
1270 }
1271
1272 case VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR:
1273 {
1274 programCollection.glslSources.add("rgen")
1275 << glu::RaygenSource(updateRayTracingGLSL(getCommonRayGenerationShader())) << buildOptions;
1276
1277 {
1278 std::stringstream css;
1279 css << "#version 460 core\n"
1280 "#extension GL_EXT_ray_tracing : require\n"
1281 "#extension GL_EXT_ray_query : require\n"
1282 "layout(location = 0) rayPayloadInEXT vec3 hitValue;\n"
1283 "hitAttributeEXT vec3 attribs;\n"
1284 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1285 "layout(set = 0, binding = 2) uniform accelerationStructureEXT "
1286 "rayQueryTopLevelAccelerationStructure;\n"
1287 "\n"
1288 "void main()\n"
1289 "{\n"
1290 << testBody << "}\n";
1291
1292 programCollection.glslSources.add("chit")
1293 << glu::ClosestHitSource(updateRayTracingGLSL(css.str())) << buildOptions;
1294 }
1295
1296 programCollection.glslSources.add("ahit")
1297 << glu::AnyHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1298 programCollection.glslSources.add("miss")
1299 << glu::MissSource(updateRayTracingGLSL(getMissPassthrough())) << buildOptions;
1300
1301 break;
1302 }
1303
1304 case VK_SHADER_STAGE_INTERSECTION_BIT_KHR:
1305 {
1306 programCollection.glslSources.add("rgen")
1307 << glu::RaygenSource(updateRayTracingGLSL(getCommonRayGenerationShader())) << buildOptions;
1308
1309 {
1310 std::stringstream css;
1311 css << "#version 460 core\n"
1312 "#extension GL_EXT_ray_tracing : require\n"
1313 "#extension GL_EXT_ray_query : require\n"
1314 "hitAttributeEXT vec3 hitAttribute;\n"
1315 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1316 "layout(set = 0, binding = 2) uniform accelerationStructureEXT "
1317 "rayQueryTopLevelAccelerationStructure;\n"
1318 "\n"
1319 "void main()\n"
1320 "{\n"
1321 << testBody
1322 << " hitAttribute = vec3(0.0f, 0.0f, 0.0f);\n"
1323 " reportIntersectionEXT(1.0f, 0);\n"
1324 "}\n";
1325
1326 programCollection.glslSources.add("sect")
1327 << glu::IntersectionSource(updateRayTracingGLSL(css.str())) << buildOptions;
1328 }
1329
1330 programCollection.glslSources.add("ahit")
1331 << glu::AnyHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1332 programCollection.glslSources.add("chit")
1333 << glu::ClosestHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1334 programCollection.glslSources.add("miss")
1335 << glu::MissSource(updateRayTracingGLSL(getMissPassthrough())) << buildOptions;
1336
1337 break;
1338 }
1339
1340 case VK_SHADER_STAGE_MISS_BIT_KHR:
1341 {
1342 programCollection.glslSources.add("rgen")
1343 << glu::RaygenSource(updateRayTracingGLSL(getCommonRayGenerationShader())) << buildOptions;
1344
1345 {
1346 std::stringstream css;
1347 css << "#version 460 core\n"
1348 "#extension GL_EXT_ray_tracing : require\n"
1349 "#extension GL_EXT_ray_query : require\n"
1350 "layout(location = 0) rayPayloadInEXT vec3 hitValue;\n"
1351 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1352 "layout(set = 0, binding = 2) uniform accelerationStructureEXT "
1353 "rayQueryTopLevelAccelerationStructure;\n"
1354 "\n"
1355 "void main()\n"
1356 "{\n"
1357 << testBody << "}\n";
1358
1359 programCollection.glslSources.add("miss")
1360 << glu::MissSource(updateRayTracingGLSL(css.str())) << buildOptions;
1361 }
1362
1363 programCollection.glslSources.add("ahit")
1364 << glu::AnyHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1365 programCollection.glslSources.add("chit")
1366 << glu::ClosestHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1367
1368 break;
1369 }
1370
1371 case VK_SHADER_STAGE_CALLABLE_BIT_KHR:
1372 {
1373 {
1374 std::stringstream css;
1375 css << "#version 460 core\n"
1376 "#extension GL_EXT_ray_tracing : require\n"
1377 "#extension GL_EXT_ray_query : require\n"
1378 "layout(location = 0) callableDataEXT float dummy;"
1379 "layout(set = 0, binding = 1) uniform accelerationStructureEXT topLevelAS;\n"
1380 "\n"
1381 "void main()\n"
1382 "{\n"
1383 " executeCallableEXT(0, 0);\n"
1384 "}\n";
1385
1386 programCollection.glslSources.add("rgen")
1387 << glu::RaygenSource(updateRayTracingGLSL(css.str())) << buildOptions;
1388 }
1389
1390 {
1391 std::stringstream css;
1392 css << "#version 460 core\n"
1393 "#extension GL_EXT_ray_tracing : require\n"
1394 "#extension GL_EXT_ray_query : require\n"
1395 "layout(location = 0) callableDataInEXT float dummy;"
1396 "layout(set = 0, binding = 0, r32i) uniform iimage3D result;\n"
1397 "layout(set = 0, binding = 2) uniform accelerationStructureEXT "
1398 "rayQueryTopLevelAccelerationStructure;\n"
1399 "\n"
1400 "void main()\n"
1401 "{\n"
1402 << testBody << "}\n";
1403
1404 programCollection.glslSources.add("call")
1405 << glu::CallableSource(updateRayTracingGLSL(css.str())) << buildOptions;
1406 }
1407
1408 programCollection.glslSources.add("ahit")
1409 << glu::AnyHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1410 programCollection.glslSources.add("chit")
1411 << glu::ClosestHitSource(updateRayTracingGLSL(getHitPassthrough())) << buildOptions;
1412 programCollection.glslSources.add("miss")
1413 << glu::MissSource(updateRayTracingGLSL(getMissPassthrough())) << buildOptions;
1414
1415 break;
1416 }
1417
1418 default:
1419 TCU_THROW(InternalError, "Unknown stage");
1420 }
1421 }
1422
createShaderBindingTable(const InstanceInterface & vki,const DeviceInterface & vkd,const VkDevice device,const VkPhysicalDevice physicalDevice,const VkPipeline pipeline,Allocator & allocator,de::MovePtr<RayTracingPipeline> & rayTracingPipeline,const uint32_t group)1423 de::MovePtr<BufferWithMemory> RayTracingConfiguration::createShaderBindingTable(
1424 const InstanceInterface &vki, const DeviceInterface &vkd, const VkDevice device,
1425 const VkPhysicalDevice physicalDevice, const VkPipeline pipeline, Allocator &allocator,
1426 de::MovePtr<RayTracingPipeline> &rayTracingPipeline, const uint32_t group)
1427 {
1428 de::MovePtr<BufferWithMemory> shaderBindingTable;
1429
1430 if (group < m_shaderGroupCount)
1431 {
1432 const uint32_t shaderGroupHandleSize = getShaderGroupHandleSize(vki, physicalDevice);
1433 const uint32_t shaderGroupBaseAlignment = getShaderGroupBaseAlignment(vki, physicalDevice);
1434
1435 shaderBindingTable = rayTracingPipeline->createShaderBindingTable(
1436 vkd, device, pipeline, allocator, shaderGroupHandleSize, shaderGroupBaseAlignment, group, 1u);
1437 }
1438
1439 return shaderBindingTable;
1440 }
1441
initConfiguration(const TestEnvironment & env,TestParams & testParams)1442 void RayTracingConfiguration::initConfiguration(const TestEnvironment &env, TestParams &testParams)
1443 {
1444 DE_UNREF(testParams);
1445
1446 const InstanceInterface &vki = *env.vki;
1447 const DeviceInterface &vkd = *env.vkd;
1448 const VkDevice device = env.device;
1449 const VkPhysicalDevice physicalDevice = env.physicalDevice;
1450 vk::BinaryCollection &collection = *env.binaryCollection;
1451 Allocator &allocator = *env.allocator;
1452 const uint32_t shaderGroupHandleSize = getShaderGroupHandleSize(vki, physicalDevice);
1453 const VkShaderStageFlags hitStages =
1454 VK_SHADER_STAGE_ANY_HIT_BIT_KHR | VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR | VK_SHADER_STAGE_INTERSECTION_BIT_KHR;
1455 uint32_t shaderCount = 0;
1456
1457 m_shaderGroupCount = 0;
1458
1459 if (collection.contains("rgen"))
1460 m_shaders |= VK_SHADER_STAGE_RAYGEN_BIT_KHR;
1461 if (collection.contains("ahit"))
1462 m_shaders |= VK_SHADER_STAGE_ANY_HIT_BIT_KHR;
1463 if (collection.contains("chit"))
1464 m_shaders |= VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR;
1465 if (collection.contains("miss"))
1466 m_shaders |= VK_SHADER_STAGE_MISS_BIT_KHR;
1467 if (collection.contains("sect"))
1468 m_shaders |= VK_SHADER_STAGE_INTERSECTION_BIT_KHR;
1469 if (collection.contains("call"))
1470 m_shaders |= VK_SHADER_STAGE_CALLABLE_BIT_KHR;
1471
1472 for (BinaryCollection::Iterator it = collection.begin(); it != collection.end(); ++it)
1473 shaderCount++;
1474
1475 if (shaderCount != (uint32_t)dePop32(m_shaders))
1476 TCU_THROW(InternalError, "Unused shaders detected in the collection");
1477
1478 if (0 != (m_shaders & VK_SHADER_STAGE_RAYGEN_BIT_KHR))
1479 m_raygenShaderGroup = m_shaderGroupCount++;
1480
1481 if (0 != (m_shaders & VK_SHADER_STAGE_MISS_BIT_KHR))
1482 m_missShaderGroup = m_shaderGroupCount++;
1483
1484 if (0 != (m_shaders & hitStages))
1485 m_hitShaderGroup = m_shaderGroupCount++;
1486
1487 if (0 != (m_shaders & VK_SHADER_STAGE_CALLABLE_BIT_KHR))
1488 m_callableShaderGroup = m_shaderGroupCount++;
1489
1490 m_rayTracingPipeline = de::newMovePtr<RayTracingPipeline>();
1491
1492 m_descriptorSetLayout = DescriptorSetLayoutBuilder()
1493 .addSingleBinding(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, ALL_RAY_TRACING_STAGES)
1494 .addSingleBinding(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, ALL_RAY_TRACING_STAGES)
1495 .addSingleBinding(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, ALL_RAY_TRACING_STAGES)
1496 .build(vkd, device);
1497 m_descriptorPool = DescriptorPoolBuilder()
1498 .addType(VK_DESCRIPTOR_TYPE_STORAGE_IMAGE)
1499 .addType(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR)
1500 .addType(VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR)
1501 .build(vkd, device, VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, 1u);
1502 m_descriptorSet = makeDescriptorSet(vkd, device, *m_descriptorPool, *m_descriptorSetLayout);
1503
1504 if (0 != (m_shaders & VK_SHADER_STAGE_RAYGEN_BIT_KHR))
1505 m_rayTracingPipeline->addShader(VK_SHADER_STAGE_RAYGEN_BIT_KHR,
1506 createShaderModule(vkd, device, collection.get("rgen"), 0),
1507 m_raygenShaderGroup);
1508 if (0 != (m_shaders & VK_SHADER_STAGE_ANY_HIT_BIT_KHR))
1509 m_rayTracingPipeline->addShader(VK_SHADER_STAGE_ANY_HIT_BIT_KHR,
1510 createShaderModule(vkd, device, collection.get("ahit"), 0), m_hitShaderGroup);
1511 if (0 != (m_shaders & VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR))
1512 m_rayTracingPipeline->addShader(VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR,
1513 createShaderModule(vkd, device, collection.get("chit"), 0), m_hitShaderGroup);
1514 if (0 != (m_shaders & VK_SHADER_STAGE_MISS_BIT_KHR))
1515 m_rayTracingPipeline->addShader(VK_SHADER_STAGE_MISS_BIT_KHR,
1516 createShaderModule(vkd, device, collection.get("miss"), 0), m_missShaderGroup);
1517 if (0 != (m_shaders & VK_SHADER_STAGE_INTERSECTION_BIT_KHR))
1518 m_rayTracingPipeline->addShader(VK_SHADER_STAGE_INTERSECTION_BIT_KHR,
1519 createShaderModule(vkd, device, collection.get("sect"), 0), m_hitShaderGroup);
1520 if (0 != (m_shaders & VK_SHADER_STAGE_CALLABLE_BIT_KHR))
1521 m_rayTracingPipeline->addShader(VK_SHADER_STAGE_CALLABLE_BIT_KHR,
1522 createShaderModule(vkd, device, collection.get("call"), 0),
1523 m_callableShaderGroup);
1524
1525 m_pipelineLayout = makePipelineLayout(vkd, device, m_descriptorSetLayout.get());
1526 m_pipeline = m_rayTracingPipeline->createPipeline(vkd, device, *m_pipelineLayout);
1527
1528 m_raygenShaderBindingTable = createShaderBindingTable(vki, vkd, device, physicalDevice, *m_pipeline, allocator,
1529 m_rayTracingPipeline, m_raygenShaderGroup);
1530 m_missShaderBindingTable = createShaderBindingTable(vki, vkd, device, physicalDevice, *m_pipeline, allocator,
1531 m_rayTracingPipeline, m_missShaderGroup);
1532 m_hitShaderBindingTable = createShaderBindingTable(vki, vkd, device, physicalDevice, *m_pipeline, allocator,
1533 m_rayTracingPipeline, m_hitShaderGroup);
1534 m_callableShaderBindingTable = createShaderBindingTable(vki, vkd, device, physicalDevice, *m_pipeline, allocator,
1535 m_rayTracingPipeline, m_callableShaderGroup);
1536
1537 m_raygenShaderBindingTableRegion =
1538 m_raygenShaderBindingTable.get() != NULL ?
1539 makeStridedDeviceAddressRegionKHR(getBufferDeviceAddress(vkd, device, m_raygenShaderBindingTable->get(), 0),
1540 shaderGroupHandleSize, shaderGroupHandleSize) :
1541 makeStridedDeviceAddressRegionKHR(DE_NULL, 0, 0);
1542 m_missShaderBindingTableRegion =
1543 m_missShaderBindingTable.get() != NULL ?
1544 makeStridedDeviceAddressRegionKHR(getBufferDeviceAddress(vkd, device, m_missShaderBindingTable->get(), 0),
1545 shaderGroupHandleSize, shaderGroupHandleSize) :
1546 makeStridedDeviceAddressRegionKHR(DE_NULL, 0, 0);
1547 m_hitShaderBindingTableRegion =
1548 m_hitShaderBindingTable.get() != NULL ?
1549 makeStridedDeviceAddressRegionKHR(getBufferDeviceAddress(vkd, device, m_hitShaderBindingTable->get(), 0),
1550 shaderGroupHandleSize, shaderGroupHandleSize) :
1551 makeStridedDeviceAddressRegionKHR(DE_NULL, 0, 0);
1552 m_callableShaderBindingTableRegion =
1553 m_callableShaderBindingTable.get() != NULL ?
1554 makeStridedDeviceAddressRegionKHR(
1555 getBufferDeviceAddress(vkd, device, m_callableShaderBindingTable->get(), 0), shaderGroupHandleSize,
1556 shaderGroupHandleSize) :
1557 makeStridedDeviceAddressRegionKHR(DE_NULL, 0, 0);
1558 }
1559
fillCommandBuffer(const TestEnvironment & env,TestParams & testParams,VkCommandBuffer commandBuffer,const VkAccelerationStructureKHR * rayQueryTopAccelerationStructurePtr,const VkDescriptorImageInfo & resultImageInfo)1560 void RayTracingConfiguration::fillCommandBuffer(const TestEnvironment &env, TestParams &testParams,
1561 VkCommandBuffer commandBuffer,
1562 const VkAccelerationStructureKHR *rayQueryTopAccelerationStructurePtr,
1563 const VkDescriptorImageInfo &resultImageInfo)
1564 {
1565 const DeviceInterface &vkd = *env.vkd;
1566 const VkDevice device = env.device;
1567 Allocator &allocator = *env.allocator;
1568 de::MovePtr<BottomLevelAccelerationStructure> bottomLevelAccelerationStructure =
1569 makeBottomLevelAccelerationStructure();
1570 de::MovePtr<TopLevelAccelerationStructure> topLevelAccelerationStructure = makeTopLevelAccelerationStructure();
1571
1572 m_bottomLevelAccelerationStructure =
1573 de::SharedPtr<BottomLevelAccelerationStructure>(bottomLevelAccelerationStructure.release());
1574 m_bottomLevelAccelerationStructure->setDefaultGeometryData(testParams.stage);
1575 m_bottomLevelAccelerationStructure->createAndBuild(vkd, device, commandBuffer, allocator);
1576
1577 m_topLevelAccelerationStructure =
1578 de::SharedPtr<TopLevelAccelerationStructure>(topLevelAccelerationStructure.release());
1579 m_topLevelAccelerationStructure->setInstanceCount(1);
1580 m_topLevelAccelerationStructure->addInstance(m_bottomLevelAccelerationStructure);
1581 m_topLevelAccelerationStructure->createAndBuild(vkd, device, commandBuffer, allocator);
1582
1583 const TopLevelAccelerationStructure *topLevelAccelerationStructurePtr = m_topLevelAccelerationStructure.get();
1584 const VkWriteDescriptorSetAccelerationStructureKHR accelerationStructureWriteDescriptorSet = {
1585 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET_ACCELERATION_STRUCTURE_KHR, // VkStructureType sType;
1586 DE_NULL, // const void* pNext;
1587 1u, // uint32_t accelerationStructureCount;
1588 topLevelAccelerationStructurePtr->getPtr(), // const VkAccelerationStructureKHR* pAccelerationStructures;
1589 };
1590 const VkWriteDescriptorSetAccelerationStructureKHR rayQueryAccelerationStructureWriteDescriptorSet = {
1591 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET_ACCELERATION_STRUCTURE_KHR, // VkStructureType sType;
1592 DE_NULL, // const void* pNext;
1593 1u, // uint32_t accelerationStructureCount;
1594 rayQueryTopAccelerationStructurePtr, // const VkAccelerationStructureKHR* pAccelerationStructures;
1595 };
1596
1597 DescriptorSetUpdateBuilder()
1598 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(0u),
1599 VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, &resultImageInfo)
1600 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(1u),
1601 VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, &accelerationStructureWriteDescriptorSet)
1602 .writeSingle(*m_descriptorSet, DescriptorSetUpdateBuilder::Location::binding(2u),
1603 VK_DESCRIPTOR_TYPE_ACCELERATION_STRUCTURE_KHR, &rayQueryAccelerationStructureWriteDescriptorSet)
1604 .update(vkd, device);
1605
1606 vkd.cmdBindDescriptorSets(commandBuffer, VK_PIPELINE_BIND_POINT_RAY_TRACING_KHR, *m_pipelineLayout, 0, 1,
1607 &m_descriptorSet.get(), 0, DE_NULL);
1608
1609 vkd.cmdBindPipeline(commandBuffer, VK_PIPELINE_BIND_POINT_RAY_TRACING_KHR, m_pipeline.get());
1610
1611 cmdTraceRays(vkd, commandBuffer, &m_raygenShaderBindingTableRegion, &m_missShaderBindingTableRegion,
1612 &m_hitShaderBindingTableRegion, &m_callableShaderBindingTableRegion, testParams.width,
1613 testParams.height, 1);
1614 }
1615
prepareTestEnvironment(Context & context)1616 void TestConfiguration::prepareTestEnvironment(Context &context)
1617 {
1618 // By default, all data comes from the context.
1619 m_testEnvironment = de::MovePtr<TestEnvironment>(new TestEnvironment{
1620 &context.getInstanceInterface(), // const InstanceInterface* vki;
1621 context.getPhysicalDevice(), // VkPhysicalDevice physicalDevice;
1622 &context.getDeviceInterface(), // const DeviceInterface* vkd;
1623 context.getDevice(), // VkDevice device;
1624 &context.getDefaultAllocator(), // Allocator* allocator;
1625 context.getUniversalQueue(), // VkQueue queue;
1626 context.getUniversalQueueFamilyIndex(), // uint32_t queueFamilyIndex;
1627 &context.getBinaryCollection(), // BinaryCollection* binaryCollection;
1628 &context.getTestContext().getLog(), // tcu::TestLog* log;
1629 });
1630 }
1631
getTestEnvironment() const1632 const TestEnvironment &TestConfiguration::getTestEnvironment() const
1633 {
1634 return *m_testEnvironment;
1635 }
1636
verify(BufferWithMemory * resultBuffer,TestParams & testParams)1637 bool TestConfiguration::verify(BufferWithMemory *resultBuffer, TestParams &testParams)
1638 {
1639 tcu::TestLog &log = *(m_testEnvironment->log);
1640 const uint32_t width = testParams.width;
1641 const uint32_t height = testParams.height;
1642 const int32_t *resultPtr = (int32_t *)resultBuffer->getAllocation().getHostPtr();
1643 const int32_t *expectedPtr = m_expected.data();
1644 uint32_t failures = 0;
1645 uint32_t pos = 0;
1646
1647 for (uint32_t y = 0; y < height; ++y)
1648 for (uint32_t x = 0; x < width; ++x)
1649 {
1650 if (resultPtr[pos] != expectedPtr[pos])
1651 failures++;
1652
1653 pos++;
1654 }
1655
1656 if (failures != 0)
1657 {
1658 const char *names[] = {"Retrieved:", "Expected:"};
1659
1660 for (uint32_t n = 0; n < 2; ++n)
1661 {
1662 std::stringstream css;
1663
1664 pos = 0;
1665
1666 for (uint32_t y = 0; y < height; ++y)
1667 {
1668 for (uint32_t x = 0; x < width; ++x)
1669 {
1670 if (resultPtr[pos] != expectedPtr[pos])
1671 css << std::setw(12) << (n == 0 ? resultPtr[pos] : expectedPtr[pos]) << ",";
1672 else
1673 css << "____________,";
1674
1675 pos++;
1676 }
1677
1678 css << std::endl;
1679 }
1680
1681 log << tcu::TestLog::Message << names[n] << tcu::TestLog::EndMessage;
1682 log << tcu::TestLog::Message << css.str() << tcu::TestLog::EndMessage;
1683 }
1684 }
1685
1686 return (failures == 0);
1687 }
1688
verify(BufferWithMemory * resultBuffer,TestParams & testParams)1689 bool TestConfigurationFloat::verify(BufferWithMemory *resultBuffer, TestParams &testParams)
1690 {
1691 tcu::TestLog &log = *(m_testEnvironment->log);
1692 const float eps = float(FIXED_POINT_ALLOWED_ERROR) / float(FIXED_POINT_DIVISOR);
1693 const uint32_t width = testParams.width;
1694 const uint32_t height = testParams.height;
1695 const int32_t *resultPtr = (int32_t *)resultBuffer->getAllocation().getHostPtr();
1696 const int32_t *expectedPtr = m_expected.data();
1697 uint32_t failures = 0;
1698 uint32_t pos = 0;
1699
1700 for (uint32_t y = 0; y < height; ++y)
1701 for (uint32_t x = 0; x < width; ++x)
1702 {
1703 const float retrievedValue = float(resultPtr[pos]) / float(FIXED_POINT_DIVISOR);
1704 const float expectedValue = float(expectedPtr[pos]) / float(FIXED_POINT_DIVISOR);
1705
1706 if (deFloatAbs(retrievedValue - expectedValue) > eps)
1707 failures++;
1708
1709 pos++;
1710 }
1711
1712 if (failures != 0)
1713 {
1714 const char *names[] = {"Retrieved:", "Expected:"};
1715
1716 for (uint32_t n = 0; n < 2; ++n)
1717 {
1718 std::stringstream css;
1719
1720 pos = 0;
1721
1722 for (uint32_t y = 0; y < height; ++y)
1723 {
1724 for (uint32_t x = 0; x < width; ++x)
1725 {
1726 const float retrievedValue = float(resultPtr[pos]) / float(FIXED_POINT_DIVISOR);
1727 const float expectedValue = float(expectedPtr[pos]) / float(FIXED_POINT_DIVISOR);
1728
1729 if (deFloatAbs(retrievedValue - expectedValue) > eps)
1730 css << std::setprecision(8) << std::setw(12) << (n == 0 ? retrievedValue : expectedValue)
1731 << ",";
1732 else
1733 css << "____________,";
1734
1735 pos++;
1736 }
1737
1738 css << std::endl;
1739 }
1740
1741 log << tcu::TestLog::Message << names[n] << tcu::TestLog::EndMessage;
1742 log << tcu::TestLog::Message << css.str() << tcu::TestLog::EndMessage;
1743 }
1744 }
1745
1746 return (failures == 0);
1747 }
1748
verify(BufferWithMemory * resultBuffer,TestParams & testParams)1749 bool TestConfigurationVector::verify(BufferWithMemory *resultBuffer, TestParams &testParams)
1750 {
1751 tcu::TestLog &log = *(m_testEnvironment->log);
1752 const float eps = float(FIXED_POINT_ALLOWED_ERROR) / float(FIXED_POINT_DIVISOR);
1753 const uint32_t width = testParams.width;
1754 const uint32_t height = testParams.height;
1755 const uint32_t depth = 3u; // vec3
1756 const int32_t *resultPtr = (int32_t *)resultBuffer->getAllocation().getHostPtr();
1757 const int32_t *expectedPtr = m_expected.data();
1758 uint32_t failures = 0;
1759 uint32_t pos = 0;
1760
1761 if (m_useStrictComponentMatching)
1762 {
1763 for (uint32_t z = 0; z < depth; ++z)
1764 {
1765 for (uint32_t y = 0; y < height; ++y)
1766 {
1767 for (uint32_t x = 0; x < width; ++x)
1768 {
1769 const float retrievedValue = float(resultPtr[pos]) / float(FIXED_POINT_DIVISOR);
1770 const float expectedValue = float(expectedPtr[pos]) / float(FIXED_POINT_DIVISOR);
1771
1772 if (deFloatAbs(retrievedValue - expectedValue) > eps)
1773 failures++;
1774
1775 ++pos;
1776 }
1777 }
1778 }
1779 }
1780 else
1781 {
1782 // This path is taken for barycentric coords, which can be returned in any order.
1783 //
1784 // We need to ensure that:
1785 // 1. Each component value found in the retrieved value has a match in the expected value vec.
1786 // 2. Only one mapping exists per each component in the expected value vec.
1787 const auto nSquares = width * height;
1788
1789 for (uint32_t y = 0; y < height; ++y)
1790 {
1791 for (uint32_t x = 0; x < width; ++x)
1792 {
1793 bool expectedVectorComponentUsed[3] = {false};
1794 const auto squareNdx = y * width + x;
1795
1796 for (uint32_t retrievedComponentNdx = 0; retrievedComponentNdx < 3 /* vec3 */; ++retrievedComponentNdx)
1797 {
1798 const float retrievedValue =
1799 float(resultPtr[nSquares * retrievedComponentNdx + squareNdx]) / float(FIXED_POINT_DIVISOR);
1800
1801 for (uint32_t expectedComponentNdx = 0; expectedComponentNdx < 3 /* vec3 */; ++expectedComponentNdx)
1802 {
1803 const float expectedValue = float(expectedPtr[nSquares * expectedComponentNdx + squareNdx]) /
1804 float(FIXED_POINT_DIVISOR);
1805
1806 if (deFloatAbs(retrievedValue - expectedValue) <= eps &&
1807 expectedVectorComponentUsed[expectedComponentNdx] == false)
1808 {
1809 expectedVectorComponentUsed[expectedComponentNdx] = true;
1810
1811 break;
1812 }
1813
1814 ++pos;
1815 }
1816 }
1817
1818 if (expectedVectorComponentUsed[0] == false || expectedVectorComponentUsed[1] == false ||
1819 expectedVectorComponentUsed[2] == false)
1820 {
1821 ++failures;
1822 }
1823 }
1824 }
1825 }
1826
1827 if (failures != 0)
1828 {
1829 const char *names[] = {
1830 "Retrieved", (m_useStrictComponentMatching) ? "Expected" : "Expected (component order is irrelevant)"};
1831
1832 std::stringstream css;
1833
1834 for (uint32_t y = 0; y < height; ++y)
1835 {
1836 for (uint32_t x = 0; x < width; ++x)
1837 {
1838 for (uint32_t n = 0; n < 2; ++n)
1839 {
1840 css << names[n] << " at (" << x << "," << y << ") {";
1841
1842 for (uint32_t z = 0; z < depth; ++z)
1843 {
1844 pos = x + width * (y + height * z);
1845
1846 const float retrievedValue = float(resultPtr[pos]) / float(FIXED_POINT_DIVISOR);
1847 const float expectedValue = float(expectedPtr[pos]) / float(FIXED_POINT_DIVISOR);
1848
1849 if (deFloatAbs(retrievedValue - expectedValue) > eps || m_useStrictComponentMatching == false)
1850 {
1851 css << std::setprecision(8) << std::setw(12) << (n == 0 ? retrievedValue : expectedValue)
1852 << ",";
1853 }
1854 else
1855 css << "____________,";
1856 }
1857
1858 css << "}" << std::endl;
1859 }
1860 }
1861 }
1862
1863 log << tcu::TestLog::Message << css.str() << tcu::TestLog::EndMessage;
1864 }
1865
1866 return failures == 0;
1867 }
1868
verify(BufferWithMemory * resultBuffer,TestParams & testParams)1869 bool TestConfigurationMatrix::verify(BufferWithMemory *resultBuffer, TestParams &testParams)
1870 {
1871 tcu::TestLog &log = *(m_testEnvironment->log);
1872 const float eps = float(FIXED_POINT_ALLOWED_ERROR) / float(FIXED_POINT_DIVISOR);
1873 const uint32_t width = testParams.width;
1874 const uint32_t height = testParams.height;
1875 const uint32_t depth = 12u; // mat3x4 or mat4x3
1876 const int32_t *resultPtr = (int32_t *)resultBuffer->getAllocation().getHostPtr();
1877 const int32_t *expectedPtr = m_expected.data();
1878 uint32_t failures = 0;
1879 uint32_t pos = 0;
1880
1881 for (uint32_t z = 0; z < depth; ++z)
1882 for (uint32_t y = 0; y < height; ++y)
1883 for (uint32_t x = 0; x < width; ++x)
1884 {
1885 const float retrievedValue = float(resultPtr[pos]) / float(FIXED_POINT_DIVISOR);
1886 const float expectedValue = float(expectedPtr[pos]) / float(FIXED_POINT_DIVISOR);
1887
1888 if (deFloatAbs(retrievedValue - expectedValue) > eps)
1889 failures++;
1890
1891 ++pos;
1892 }
1893
1894 if (failures != 0)
1895 {
1896 const char *names[] = {"Retrieved", "Expected"};
1897 std::stringstream css;
1898
1899 for (uint32_t y = 0; y < height; ++y)
1900 {
1901 for (uint32_t x = 0; x < width; ++x)
1902 {
1903 css << "At (" << x << "," << y << ")" << std::endl;
1904 for (uint32_t n = 0; n < 2; ++n)
1905 {
1906 css << names[n] << std::endl << "{" << std::endl;
1907
1908 for (uint32_t z = 0; z < depth; ++z)
1909 {
1910 pos = x + width * (y + height * z);
1911
1912 const float retrievedValue = float(resultPtr[pos]) / float(FIXED_POINT_DIVISOR);
1913 const float expectedValue = float(expectedPtr[pos]) / float(FIXED_POINT_DIVISOR);
1914
1915 if (z % 4 == 0)
1916 css << " {";
1917
1918 if (deFloatAbs(retrievedValue - expectedValue) > eps)
1919 css << std::setprecision(5) << std::setw(9) << (n == 0 ? retrievedValue : expectedValue)
1920 << ",";
1921 else
1922 css << "_________,";
1923
1924 if (z % 4 == 3)
1925 css << "}" << std::endl;
1926 }
1927
1928 css << "}" << std::endl;
1929 }
1930 }
1931 }
1932
1933 log << tcu::TestLog::Message << css.str() << tcu::TestLog::EndMessage;
1934 }
1935
1936 return failures == 0;
1937 }
1938
1939 class TestConfigurationFlow : public TestConfiguration
1940 {
1941 public:
TestConfigurationFlow(Context & context)1942 TestConfigurationFlow(Context &context) : TestConfiguration(context)
1943 {
1944 }
1945
1946 static const std::string getShaderBodyText(const TestParams &testParams);
1947
1948 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
1949 VkCommandBuffer cmdBuffer) override;
1950 };
1951
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)1952 const VkAccelerationStructureKHR *TestConfigurationFlow::initAccelerationStructures(TestParams &testParams,
1953 VkCommandBuffer cmdBuffer)
1954 {
1955 const DeviceInterface &vkd = *m_testEnvironment->vkd;
1956 const VkDevice device = m_testEnvironment->device;
1957 Allocator &allocator = *m_testEnvironment->allocator;
1958 const uint32_t width = testParams.width;
1959 const uint32_t height = testParams.height;
1960 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
1961 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
1962 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
1963 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
1964 const float z = -1.0f;
1965 tcu::UVec2 startPos = tcu::UVec2(0, 0);
1966 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
1967 makeTopLevelAccelerationStructure();
1968
1969 m_topAccelerationStructure =
1970 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
1971
1972 m_expected = std::vector<int32_t>(width * height, 1);
1973
1974 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
1975
1976 for (size_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
1977 {
1978 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
1979 makeBottomLevelAccelerationStructure();
1980
1981 for (size_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
1982 {
1983 std::vector<tcu::Vec3> geometryData;
1984
1985 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
1986
1987 for (size_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
1988 {
1989 const uint32_t n = width * startPos.y() + startPos.x();
1990 const uint32_t m = n + 1;
1991 const float x0 = float(startPos.x() + 0) / float(width);
1992 const float y0 = float(startPos.y() + 0) / float(height);
1993 const float x1 = float(startPos.x() + 1) / float(width);
1994 const float y1 = float(startPos.y() + 1) / float(height);
1995
1996 if (triangles)
1997 {
1998 const float xm = (x0 + x1) / 2.0f;
1999 const float ym = (y0 + y1) / 2.0f;
2000
2001 geometryData.push_back(tcu::Vec3(x0, y0, z));
2002 geometryData.push_back(tcu::Vec3(xm, y1, z));
2003 geometryData.push_back(tcu::Vec3(x1, ym, z));
2004 }
2005 else
2006 {
2007 geometryData.push_back(tcu::Vec3(x0, y0, z));
2008 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
2009 }
2010
2011 startPos.y() = m / width;
2012 startPos.x() = m % width;
2013 }
2014
2015 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
2016 }
2017
2018 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2019 m_bottomAccelerationStructures.push_back(
2020 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
2021 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back());
2022 }
2023
2024 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2025
2026 return m_topAccelerationStructure.get()->getPtr();
2027 }
2028
getShaderBodyText(const TestParams & testParams)2029 const std::string TestConfigurationFlow::getShaderBodyText(const TestParams &testParams)
2030 {
2031 if (testParams.geomType == GEOM_TYPE_AABBS)
2032 {
2033 const std::string result =
2034 " uint rayFlags = 0;\n"
2035 " uint cullMask = 0xFF;\n"
2036 " float tmin = 0.0;\n"
2037 " float tmax = 9.0;\n"
2038 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
2039 "float(size.y), 0.0);\n"
2040 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
2041 " uint value = 4;\n"
2042 " rayQueryEXT rayQuery;\n"
2043 "\n"
2044 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2045 "tmin, direct, tmax);\n"
2046 "\n"
2047 " if (rayQueryProceedEXT(rayQuery))\n"
2048 " {\n"
2049 " value--;\n"
2050 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
2051 " {\n"
2052 " value--;\n"
2053 " rayQueryGenerateIntersectionEXT(rayQuery, 0.5f);\n"
2054 "\n"
2055 " rayQueryProceedEXT(rayQuery);\n"
2056 "\n"
2057 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
2058 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
2059 " value--;\n"
2060 " }\n"
2061 " }\n"
2062 "\n"
2063 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
2064
2065 return result;
2066 }
2067 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
2068 {
2069 const std::string result =
2070 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
2071 " uint cullMask = 0xFF;\n"
2072 " float tmin = 0.0;\n"
2073 " float tmax = 9.0;\n"
2074 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
2075 "float(size.y), 0.0);\n"
2076 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
2077 " uint value = 4;\n"
2078 " rayQueryEXT rayQuery;\n"
2079 "\n"
2080 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2081 "tmin, direct, tmax);\n"
2082 "\n"
2083 " if (rayQueryProceedEXT(rayQuery))\n"
2084 " {\n"
2085 " value--;\n"
2086 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
2087 " {\n"
2088 " value--;\n"
2089 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
2090 "\n"
2091 " rayQueryProceedEXT(rayQuery);\n"
2092 "\n"
2093 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
2094 " value--;\n"
2095 " }\n"
2096 " }\n"
2097 "\n"
2098 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
2099
2100 return result;
2101 }
2102 else
2103 {
2104 TCU_THROW(InternalError, "Unknown geometry type");
2105 }
2106 }
2107
2108 class TestConfigurationPrimitiveId : public TestConfiguration
2109 {
2110 public:
TestConfigurationPrimitiveId(Context & context)2111 TestConfigurationPrimitiveId(Context &context) : TestConfiguration(context)
2112 {
2113 }
2114 static const std::string getShaderBodyText(const TestParams &testParams);
2115
2116 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
2117 VkCommandBuffer cmdBuffer) override;
2118 };
2119
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)2120 const VkAccelerationStructureKHR *TestConfigurationPrimitiveId::initAccelerationStructures(TestParams &testParams,
2121 VkCommandBuffer cmdBuffer)
2122 {
2123 const DeviceInterface &vkd = *m_testEnvironment->vkd;
2124 const VkDevice device = m_testEnvironment->device;
2125 Allocator &allocator = *m_testEnvironment->allocator;
2126 const uint32_t width = testParams.width;
2127 const uint32_t height = testParams.height;
2128 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
2129 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
2130 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
2131 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
2132 const float z = -1.0f;
2133 tcu::UVec2 startPos = tcu::UVec2(0, 0);
2134 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
2135 makeTopLevelAccelerationStructure();
2136
2137 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
2138
2139 m_topAccelerationStructure =
2140 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
2141
2142 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
2143
2144 m_expected.resize(width * height);
2145
2146 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
2147 {
2148 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
2149 makeBottomLevelAccelerationStructure();
2150
2151 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
2152 {
2153 std::vector<tcu::Vec3> geometryData;
2154
2155 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
2156
2157 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2158 {
2159 const uint32_t n = width * startPos.y() + startPos.x();
2160 const uint32_t m = (n + 11) % (width * height);
2161 const float x0 = float(startPos.x() + 0) / float(width);
2162 const float y0 = float(startPos.y() + 0) / float(height);
2163 const float x1 = float(startPos.x() + 1) / float(width);
2164 const float y1 = float(startPos.y() + 1) / float(height);
2165
2166 if (triangles)
2167 {
2168 const float xm = (x0 + x1) / 2.0f;
2169 const float ym = (y0 + y1) / 2.0f;
2170
2171 geometryData.push_back(tcu::Vec3(x0, y0, z));
2172 geometryData.push_back(tcu::Vec3(xm, y1, z));
2173 geometryData.push_back(tcu::Vec3(x1, ym, z));
2174 }
2175 else
2176 {
2177 geometryData.push_back(tcu::Vec3(x0, y0, z));
2178 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
2179 }
2180
2181 m_expected[n] = squareNdx;
2182
2183 startPos.y() = m / width;
2184 startPos.x() = m % width;
2185 }
2186
2187 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
2188 }
2189
2190 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2191 m_bottomAccelerationStructures.push_back(
2192 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
2193 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
2194 instanceNdx + 1);
2195 }
2196
2197 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2198
2199 return m_topAccelerationStructure.get()->getPtr();
2200 }
2201
getShaderBodyText(const TestParams & testParams)2202 const std::string TestConfigurationPrimitiveId::getShaderBodyText(const TestParams &testParams)
2203 {
2204 if (testParams.geomType == GEOM_TYPE_AABBS)
2205 {
2206 const std::string result =
2207 " uint rayFlags = 0;\n"
2208 " uint cullMask = 0xFF;\n"
2209 " float tmin = 0.0;\n"
2210 " float tmax = 9.0;\n"
2211 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
2212 "float(size.y), 0.0);\n"
2213 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
2214 " uint value = -1;\n"
2215 " rayQueryEXT rayQuery;\n"
2216 "\n"
2217 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2218 "tmin, direct, tmax);\n"
2219 "\n"
2220 " if (rayQueryProceedEXT(rayQuery))\n"
2221 " {\n"
2222 " value--;\n"
2223 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
2224 " {\n"
2225 " value--;\n"
2226 " rayQueryGenerateIntersectionEXT(rayQuery, 0.5f);\n"
2227 "\n"
2228 " rayQueryProceedEXT(rayQuery);\n"
2229 "\n"
2230 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
2231 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
2232 " value = rayQueryGetIntersectionPrimitiveIndexEXT(rayQuery, true);\n"
2233 " }\n"
2234 " }\n"
2235 "\n"
2236 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
2237
2238 return result;
2239 }
2240 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
2241 {
2242 const std::string result =
2243 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
2244 " uint cullMask = 0xFF;\n"
2245 " float tmin = 0.0;\n"
2246 " float tmax = 9.0;\n"
2247 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
2248 "float(size.y), 0.0);\n"
2249 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
2250 " uint value = -1;\n"
2251 " rayQueryEXT rayQuery;\n"
2252 "\n"
2253 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2254 "tmin, direct, tmax);\n"
2255 "\n"
2256 " if (rayQueryProceedEXT(rayQuery))\n"
2257 " {\n"
2258 " value--;\n"
2259 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
2260 " {\n"
2261 " value--;\n"
2262 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
2263 "\n"
2264 " rayQueryProceedEXT(rayQuery);\n"
2265 "\n"
2266 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
2267 " value = rayQueryGetIntersectionPrimitiveIndexEXT(rayQuery, true);\n"
2268 " }\n"
2269 " }\n"
2270 "\n"
2271 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
2272
2273 return result;
2274 }
2275 else
2276 {
2277 TCU_THROW(InternalError, "Unknown geometry type");
2278 }
2279 }
2280
2281 class TestConfigurationGetRayTMin : public TestConfiguration
2282 {
2283 public:
TestConfigurationGetRayTMin(Context & context)2284 TestConfigurationGetRayTMin(Context &context) : TestConfiguration(context)
2285 {
2286 }
2287 static const std::string getShaderBodyText(const TestParams &testParams);
2288
2289 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
2290 VkCommandBuffer cmdBuffer) override;
2291 };
2292
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)2293 const VkAccelerationStructureKHR *TestConfigurationGetRayTMin::initAccelerationStructures(TestParams &testParams,
2294 VkCommandBuffer cmdBuffer)
2295 {
2296 const DeviceInterface &vkd = *m_testEnvironment->vkd;
2297 const VkDevice device = m_testEnvironment->device;
2298 Allocator &allocator = *m_testEnvironment->allocator;
2299 const uint32_t width = testParams.width;
2300 const uint32_t height = testParams.height;
2301 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
2302 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
2303 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
2304 const bool usesTriangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
2305 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
2306 makeTopLevelAccelerationStructure();
2307
2308 DE_ASSERT(instancesGroupCount == 1);
2309 DE_ASSERT(geometriesGroupCount == 1);
2310 DE_ASSERT(squaresGroupCount == width * height);
2311
2312 m_topAccelerationStructure =
2313 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
2314
2315 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
2316
2317 m_expected.resize(width * height);
2318
2319 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
2320 {
2321 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
2322 makeBottomLevelAccelerationStructure();
2323
2324 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
2325 {
2326 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2327 {
2328 std::vector<tcu::Vec3> geometryData;
2329
2330 const auto squareX = (squareNdx % width);
2331 const auto squareY = (squareNdx / width);
2332
2333 const float x0 = float(squareX + 0) / float(width);
2334 const float y0 = float(squareY + 0) / float(height);
2335 const float x1 = float(squareX + 1) / float(width);
2336 const float y1 = float(squareY + 1) / float(height);
2337
2338 if (usesTriangles)
2339 {
2340 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
2341 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
2342 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
2343
2344 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
2345 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
2346 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
2347 }
2348 else
2349 {
2350 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
2351 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
2352 }
2353
2354 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, usesTriangles);
2355 }
2356 }
2357
2358 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2359 m_bottomAccelerationStructures.push_back(
2360 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
2361 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
2362 instanceNdx + 1);
2363 }
2364
2365 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2366
2367 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2368 {
2369 const float expected_value = 1.0f + static_cast<float>(squareNdx) / static_cast<float>(squaresGroupCount);
2370 const auto expected_value_i32 = static_cast<int32_t>(expected_value * FIXED_POINT_DIVISOR);
2371
2372 m_expected.at(squareNdx) = expected_value_i32;
2373 }
2374
2375 return m_topAccelerationStructure.get()->getPtr();
2376 }
2377
getShaderBodyText(const TestParams & testParams)2378 const std::string TestConfigurationGetRayTMin::getShaderBodyText(const TestParams &testParams)
2379 {
2380 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
2381 {
2382 const std::string result =
2383 " uint rayFlags = 0;\n"
2384 " uint cullMask = 0xFF;\n"
2385 " float tmin = 1.0 + float(pos.y * size.x + pos.x) / float(size.x * size.y);\n"
2386 " float tmax = 9.0;\n"
2387 " vec3 origin = vec3(0.0, 0.0, -1.0);\n"
2388 " vec3 direct = vec3(0.0, 0.0, 1.0);\n"
2389 " rayQueryEXT rayQuery;\n"
2390 "\n"
2391 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2392 "tmin, direct, tmax);\n"
2393 "\n"
2394 " while (rayQueryProceedEXT(rayQuery))\n"
2395 " {\n"
2396 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
2397 " {\n"
2398 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
2399 " }\n"
2400 " }\n"
2401 "\n"
2402 " float result_fp32 = rayQueryGetRayTMinEXT(rayQuery);\n"
2403 " imageStore(result, pos, ivec4(int(result_fp32 * " +
2404 de::toString(FIXED_POINT_DIVISOR) + "), 0, 0, 0));\n";
2405
2406 return result;
2407 }
2408 else
2409 {
2410 TCU_THROW(InternalError, "Unknown geometry type");
2411 }
2412 }
2413
2414 class TestConfigurationGetWorldRayOrigin : public TestConfigurationVector
2415 {
2416 public:
TestConfigurationGetWorldRayOrigin(Context & context)2417 TestConfigurationGetWorldRayOrigin(Context &context) : TestConfigurationVector(context)
2418 {
2419 }
2420 static const std::string getShaderBodyText(const TestParams &testParams);
2421
2422 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
2423 VkCommandBuffer cmdBuffer) override;
2424 };
2425
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)2426 const VkAccelerationStructureKHR *TestConfigurationGetWorldRayOrigin::initAccelerationStructures(
2427 TestParams &testParams, VkCommandBuffer cmdBuffer)
2428 {
2429 const DeviceInterface &vkd = *m_testEnvironment->vkd;
2430 const VkDevice device = m_testEnvironment->device;
2431 Allocator &allocator = *m_testEnvironment->allocator;
2432 const uint32_t width = testParams.width;
2433 const uint32_t height = testParams.height;
2434 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
2435 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
2436 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
2437 const bool usesTriangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
2438 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
2439 makeTopLevelAccelerationStructure();
2440
2441 DE_ASSERT(instancesGroupCount == 1);
2442 DE_ASSERT(geometriesGroupCount == 1);
2443 DE_ASSERT(squaresGroupCount == width * height);
2444
2445 m_topAccelerationStructure =
2446 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
2447
2448 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
2449
2450 m_expected.resize(width * height * 4 /* components */);
2451
2452 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
2453 {
2454 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
2455 makeBottomLevelAccelerationStructure();
2456
2457 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
2458 {
2459 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2460 {
2461 std::vector<tcu::Vec3> geometryData;
2462
2463 const auto squareX = (squareNdx % width);
2464 const auto squareY = (squareNdx / width);
2465
2466 const float x0 = float(squareX + 0) / float(width);
2467 const float y0 = float(squareY + 0) / float(height);
2468 const float x1 = float(squareX + 1) / float(width);
2469 const float y1 = float(squareY + 1) / float(height);
2470
2471 if (usesTriangles)
2472 {
2473 geometryData.push_back(tcu::Vec3(x0, y0, -0.2f));
2474 geometryData.push_back(tcu::Vec3(x0, y1, -0.2f));
2475 geometryData.push_back(tcu::Vec3(x1, y1, -0.2f));
2476
2477 geometryData.push_back(tcu::Vec3(x1, y1, -0.2f));
2478 geometryData.push_back(tcu::Vec3(x1, y0, -0.2f));
2479 geometryData.push_back(tcu::Vec3(x0, y0, -0.2f));
2480 }
2481 else
2482 {
2483 geometryData.push_back(tcu::Vec3(x0, y0, -0.2f));
2484 geometryData.push_back(tcu::Vec3(x1, y1, -0.2f));
2485 }
2486
2487 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, usesTriangles);
2488 }
2489 }
2490
2491 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2492 m_bottomAccelerationStructures.push_back(
2493 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
2494 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
2495 instanceNdx + 1);
2496 }
2497
2498 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2499
2500 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2501 {
2502 const auto squareX = squareNdx % width;
2503 const auto squareY = squareNdx / width;
2504
2505 const float expected_values[3] = {
2506 (float(squareX) + 0.5f) / float(width),
2507 (float(squareY) + 0.5f) / float(height),
2508 float(squareX + squareY) / float(width + height),
2509 };
2510
2511 const int32_t expected_value_i32vec3[3] = {
2512 static_cast<int32_t>(expected_values[0] * FIXED_POINT_DIVISOR),
2513 static_cast<int32_t>(expected_values[1] * FIXED_POINT_DIVISOR),
2514 static_cast<int32_t>(expected_values[2] * FIXED_POINT_DIVISOR),
2515 };
2516
2517 /* m_expected data layout is:
2518 *
2519 * XXXXXXXX ..
2520 * YYYYYYYY ..
2521 * ZZZZZZZZ ..
2522 * WWWWWWWW
2523 */
2524 m_expected.at(0 * squaresGroupCount + squareNdx) = expected_value_i32vec3[0];
2525 m_expected.at(1 * squaresGroupCount + squareNdx) = expected_value_i32vec3[1];
2526 m_expected.at(2 * squaresGroupCount + squareNdx) = expected_value_i32vec3[2];
2527 m_expected.at(3 * squaresGroupCount + squareNdx) = 0;
2528 }
2529
2530 return m_topAccelerationStructure.get()->getPtr();
2531 }
2532
getShaderBodyText(const TestParams & testParams)2533 const std::string TestConfigurationGetWorldRayOrigin::getShaderBodyText(const TestParams &testParams)
2534 {
2535 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
2536 {
2537 const std::string result =
2538 " uint rayFlags = 0;\n"
2539 " uint cullMask = 0xFF;\n"
2540 " float tmin = 0.00001;\n"
2541 " float tmax = 9.0;\n"
2542 " vec3 origin = vec3((float(pos.x) + 0.5)/ float(size.x), float(float(pos.y) + 0.5) / "
2543 "float(size.y), float(pos.x + pos.y) / float(size.x + size.y));\n"
2544 " vec3 direct = vec3(0, 0, -1);\n"
2545 " rayQueryEXT rayQuery;\n"
2546 "\n"
2547 " bool intersection_found = false;\n"
2548 "\n"
2549 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2550 "tmin, direct, tmax);\n"
2551 "\n"
2552 " while (rayQueryProceedEXT(rayQuery))\n"
2553 " {\n"
2554 " intersection_found = true;\n"
2555 "\n"
2556 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
2557 " }\n"
2558 "\n"
2559 " vec3 result_fp32 = (intersection_found) ? rayQueryGetWorldRayOriginEXT(rayQuery)\n"
2560 " : vec3(1234.0, 5678, 9.0);\n"
2561 "\n"
2562 " imageStore(result, ivec3(pos.xy, 0), ivec4(result_fp32.x * " +
2563 de::toString(FIXED_POINT_DIVISOR) +
2564 ", 0, 0, 0) );\n"
2565 " imageStore(result, ivec3(pos.xy, 1), ivec4(result_fp32.y * " +
2566 de::toString(FIXED_POINT_DIVISOR) +
2567 ", 0, 0, 0) );\n"
2568 " imageStore(result, ivec3(pos.xy, 2), ivec4(result_fp32.z * " +
2569 de::toString(FIXED_POINT_DIVISOR) + ", 0, 0, 0) );\n";
2570
2571 return result;
2572 }
2573 else
2574 {
2575 TCU_THROW(InternalError, "Unknown geometry type");
2576 }
2577 }
2578
2579 class TestConfigurationGetWorldRayDirection : public TestConfigurationVector
2580 {
2581 public:
TestConfigurationGetWorldRayDirection(Context & context)2582 TestConfigurationGetWorldRayDirection(Context &context) : TestConfigurationVector(context)
2583 {
2584 }
2585 static const std::string getShaderBodyText(const TestParams &testParams);
2586
2587 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
2588 VkCommandBuffer cmdBuffer) override;
2589 };
2590
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)2591 const VkAccelerationStructureKHR *TestConfigurationGetWorldRayDirection::initAccelerationStructures(
2592 TestParams &testParams, VkCommandBuffer cmdBuffer)
2593 {
2594 const DeviceInterface &vkd = *m_testEnvironment->vkd;
2595 const VkDevice device = m_testEnvironment->device;
2596 Allocator &allocator = *m_testEnvironment->allocator;
2597 const uint32_t width = testParams.width;
2598 const uint32_t height = testParams.height;
2599 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
2600 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
2601 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
2602 const bool usesTriangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
2603 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
2604 makeTopLevelAccelerationStructure();
2605
2606 DE_ASSERT(instancesGroupCount == 1);
2607 DE_ASSERT(geometriesGroupCount == 1);
2608 DE_ASSERT(squaresGroupCount == width * height);
2609
2610 m_topAccelerationStructure =
2611 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
2612
2613 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
2614
2615 m_expected.resize(width * height * 3 /* components in vec3 */);
2616
2617 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
2618 {
2619 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
2620 makeBottomLevelAccelerationStructure();
2621
2622 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
2623 {
2624 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2625 {
2626 std::vector<tcu::Vec3> geometryData;
2627
2628 const auto squareX = (squareNdx % width);
2629 const auto squareY = (squareNdx / width);
2630
2631 const float x0 = float(squareX + 0) / float(width);
2632 const float y0 = float(squareY + 0) / float(height);
2633 const float x1 = float(squareX + 1) / float(width);
2634 const float y1 = float(squareY + 1) / float(height);
2635
2636 if (usesTriangles)
2637 {
2638 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
2639 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
2640 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
2641
2642 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
2643 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
2644 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
2645 }
2646 else
2647 {
2648 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
2649 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
2650 }
2651
2652 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, usesTriangles);
2653 }
2654 }
2655
2656 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2657 m_bottomAccelerationStructures.push_back(
2658 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
2659 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
2660 instanceNdx + 1);
2661 }
2662
2663 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2664
2665 const auto normalize = [](const tcu::Vec3 &in_vec3)
2666 {
2667 const auto distance = deFloatSqrt(in_vec3[0] * in_vec3[0] + in_vec3[1] * in_vec3[1] + in_vec3[2] * in_vec3[2]);
2668
2669 return tcu::Vec3(in_vec3[0] / distance, in_vec3[1] / distance, in_vec3[2] / distance);
2670 };
2671
2672 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2673 {
2674 const auto squareX = squareNdx % width;
2675 const auto squareY = squareNdx / width;
2676
2677 const auto origin = tcu::Vec3(0.5f, 0.5f, -1.0f);
2678 const auto target =
2679 tcu::Vec3((float(squareX) + 0.5f) / float(width), (float(squareY) + 0.5f) / float(height), 0.0);
2680 const auto dir_vector = target - origin;
2681 const auto dir_vector_normalized = normalize(dir_vector);
2682
2683 const int32_t expected_value_i32vec3[3] = {
2684 static_cast<int32_t>(dir_vector_normalized[0] * FIXED_POINT_DIVISOR),
2685 static_cast<int32_t>(dir_vector_normalized[1] * FIXED_POINT_DIVISOR),
2686 static_cast<int32_t>(dir_vector_normalized[2] * FIXED_POINT_DIVISOR),
2687 };
2688
2689 /* Data layout for m_expected is:
2690 *
2691 * XXXX...XX
2692 * YYYY...YY
2693 * ZZZZ...ZZ
2694 * WWWW...WW
2695 */
2696 m_expected.at(0 * squaresGroupCount + squareNdx) = expected_value_i32vec3[0];
2697 m_expected.at(1 * squaresGroupCount + squareNdx) = expected_value_i32vec3[1];
2698 m_expected.at(2 * squaresGroupCount + squareNdx) = expected_value_i32vec3[2];
2699 }
2700
2701 return m_topAccelerationStructure.get()->getPtr();
2702 }
2703
getShaderBodyText(const TestParams & testParams)2704 const std::string TestConfigurationGetWorldRayDirection::getShaderBodyText(const TestParams &testParams)
2705 {
2706 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
2707 {
2708 const std::string result =
2709 " uint rayFlags = 0;\n"
2710 " uint cullMask = 0xFF;\n"
2711 " float tmin = 0.00001;\n"
2712 " float tmax = 9.0;\n"
2713 " vec3 origin = vec3(0.5, 0.5, -1.0);\n"
2714 " vec3 target = vec3(float(float(pos.x) + 0.5) / float(size.x), float(float(pos.y) + 0.5) / "
2715 "float(size.y), 0.0);\n"
2716 " vec3 direct = normalize(target - origin);\n"
2717 " rayQueryEXT rayQuery;\n"
2718 "\n"
2719 " bool intersection_found = false;\n"
2720 "\n"
2721 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2722 "tmin, direct, tmax);\n"
2723 "\n"
2724 " while (rayQueryProceedEXT(rayQuery))\n"
2725 " {\n"
2726 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
2727 "\n"
2728 " intersection_found = true;\n"
2729 " }\n"
2730 "\n"
2731 " vec3 result_fp32 = (intersection_found) ? rayQueryGetWorldRayDirectionEXT(rayQuery)\n"
2732 " : vec3(1234.0, 5678.0, 9.0);\n"
2733 "\n"
2734 " imageStore(result, ivec3(pos.xy, 0), ivec4(result_fp32.x * " +
2735 de::toString(FIXED_POINT_DIVISOR) +
2736 ", 0, 0, 0) );\n"
2737 " imageStore(result, ivec3(pos.xy, 1), ivec4(result_fp32.y * " +
2738 de::toString(FIXED_POINT_DIVISOR) +
2739 ", 0, 0, 0) );\n"
2740 " imageStore(result, ivec3(pos.xy, 2), ivec4(result_fp32.z * " +
2741 de::toString(FIXED_POINT_DIVISOR) + ", 0, 0, 0) );\n";
2742
2743 return result;
2744 }
2745 else
2746 {
2747 TCU_THROW(InternalError, "Unknown geometry type");
2748 }
2749 }
2750
2751 class TestConfigurationInstanceId : public TestConfiguration
2752 {
2753 public:
TestConfigurationInstanceId(Context & context)2754 TestConfigurationInstanceId(Context &context) : TestConfiguration(context)
2755 {
2756 }
2757 static const std::string getShaderBodyText(const TestParams &testParams);
2758
2759 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
2760 VkCommandBuffer cmdBuffer) override;
2761 };
2762
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)2763 const VkAccelerationStructureKHR *TestConfigurationInstanceId::initAccelerationStructures(TestParams &testParams,
2764 VkCommandBuffer cmdBuffer)
2765 {
2766 const DeviceInterface &vkd = *m_testEnvironment->vkd;
2767 const VkDevice device = m_testEnvironment->device;
2768 Allocator &allocator = *m_testEnvironment->allocator;
2769 const uint32_t width = testParams.width;
2770 const uint32_t height = testParams.height;
2771 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
2772 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
2773 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
2774 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
2775 const float z = -1.0f;
2776 tcu::UVec2 startPos = tcu::UVec2(0, 0);
2777 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
2778 makeTopLevelAccelerationStructure();
2779
2780 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
2781
2782 m_topAccelerationStructure =
2783 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
2784
2785 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
2786
2787 m_expected.resize(width * height);
2788
2789 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
2790 {
2791 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
2792 makeBottomLevelAccelerationStructure();
2793
2794 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
2795 {
2796 std::vector<tcu::Vec3> geometryData;
2797
2798 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
2799
2800 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2801 {
2802 const uint32_t n = width * startPos.y() + startPos.x();
2803 const uint32_t m = (n + 11) % (width * height);
2804 const float x0 = float(startPos.x() + 0) / float(width);
2805 const float y0 = float(startPos.y() + 0) / float(height);
2806 const float x1 = float(startPos.x() + 1) / float(width);
2807 const float y1 = float(startPos.y() + 1) / float(height);
2808
2809 m_expected[n] = instanceNdx;
2810
2811 if (triangles)
2812 {
2813 const float xm = (x0 + x1) / 2.0f;
2814 const float ym = (y0 + y1) / 2.0f;
2815
2816 geometryData.push_back(tcu::Vec3(x0, y0, z));
2817 geometryData.push_back(tcu::Vec3(xm, y1, z));
2818 geometryData.push_back(tcu::Vec3(x1, ym, z));
2819 }
2820 else
2821 {
2822 geometryData.push_back(tcu::Vec3(x0, y0, z));
2823 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
2824 }
2825
2826 startPos.y() = m / width;
2827 startPos.x() = m % width;
2828 }
2829
2830 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
2831 }
2832
2833 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2834 m_bottomAccelerationStructures.push_back(
2835 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
2836 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
2837 instanceNdx + 1);
2838 }
2839
2840 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
2841
2842 return m_topAccelerationStructure.get()->getPtr();
2843 }
2844
getShaderBodyText(const TestParams & testParams)2845 const std::string TestConfigurationInstanceId::getShaderBodyText(const TestParams &testParams)
2846 {
2847 if (testParams.geomType == GEOM_TYPE_AABBS)
2848 {
2849 const std::string result =
2850 " uint rayFlags = 0;\n"
2851 " uint cullMask = 0xFF;\n"
2852 " float tmin = 0.0;\n"
2853 " float tmax = 9.0;\n"
2854 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
2855 "float(size.y), 0.0);\n"
2856 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
2857 " uint value = -1;\n"
2858 " rayQueryEXT rayQuery;\n"
2859 "\n"
2860 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2861 "tmin, direct, tmax);\n"
2862 "\n"
2863 " if (rayQueryProceedEXT(rayQuery))\n"
2864 " {\n"
2865 " value--;\n"
2866 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
2867 " {\n"
2868 " value--;\n"
2869 " rayQueryGenerateIntersectionEXT(rayQuery, 0.5f);\n"
2870 "\n"
2871 " rayQueryProceedEXT(rayQuery);\n"
2872 "\n"
2873 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
2874 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
2875 " value = rayQueryGetIntersectionInstanceIdEXT(rayQuery, true);\n"
2876 " }\n"
2877 " }\n"
2878 "\n"
2879 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
2880
2881 return result;
2882 }
2883 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
2884 {
2885 const std::string result =
2886 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
2887 " uint cullMask = 0xFF;\n"
2888 " float tmin = 0.0;\n"
2889 " float tmax = 9.0;\n"
2890 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
2891 "float(size.y), 0.0);\n"
2892 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
2893 " uint value = -1;\n"
2894 " rayQueryEXT rayQuery;\n"
2895 "\n"
2896 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
2897 "tmin, direct, tmax);\n"
2898 "\n"
2899 " if (rayQueryProceedEXT(rayQuery))\n"
2900 " {\n"
2901 " value--;\n"
2902 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
2903 " {\n"
2904 " value--;\n"
2905 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
2906 "\n"
2907 " rayQueryProceedEXT(rayQuery);\n"
2908 "\n"
2909 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
2910 " value = rayQueryGetIntersectionInstanceIdEXT(rayQuery, true);\n"
2911 " }\n"
2912 " }\n"
2913 "\n"
2914 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
2915
2916 return result;
2917 }
2918 else
2919 {
2920 TCU_THROW(InternalError, "Unknown geometry type");
2921 }
2922 }
2923
2924 class TestConfigurationInstanceCustomIndex : public TestConfiguration
2925 {
2926 public:
TestConfigurationInstanceCustomIndex(Context & context)2927 TestConfigurationInstanceCustomIndex(Context &context) : TestConfiguration(context)
2928 {
2929 }
2930 static const std::string getShaderBodyText(const TestParams &testParams);
2931
2932 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
2933 VkCommandBuffer cmdBuffer) override;
2934 };
2935
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)2936 const VkAccelerationStructureKHR *TestConfigurationInstanceCustomIndex::initAccelerationStructures(
2937 TestParams &testParams, VkCommandBuffer cmdBuffer)
2938 {
2939 const DeviceInterface &vkd = *m_testEnvironment->vkd;
2940 const VkDevice device = m_testEnvironment->device;
2941 Allocator &allocator = *m_testEnvironment->allocator;
2942 const uint32_t width = testParams.width;
2943 const uint32_t height = testParams.height;
2944 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
2945 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
2946 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
2947 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
2948 const float z = -1.0f;
2949 tcu::UVec2 startPos = tcu::UVec2(0, 0);
2950 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
2951 makeTopLevelAccelerationStructure();
2952
2953 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
2954
2955 m_topAccelerationStructure =
2956 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
2957
2958 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
2959
2960 m_expected.resize(width * height);
2961
2962 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
2963 {
2964 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
2965 makeBottomLevelAccelerationStructure();
2966
2967 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
2968 {
2969 std::vector<tcu::Vec3> geometryData;
2970
2971 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
2972
2973 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
2974 {
2975 const uint32_t n = width * startPos.y() + startPos.x();
2976 const uint32_t m = (n + 11) % (width * height);
2977 const float x0 = float(startPos.x() + 0) / float(width);
2978 const float y0 = float(startPos.y() + 0) / float(height);
2979 const float x1 = float(startPos.x() + 1) / float(width);
2980 const float y1 = float(startPos.y() + 1) / float(height);
2981
2982 m_expected[n] = instanceNdx + 1;
2983
2984 if (triangles)
2985 {
2986 const float xm = (x0 + x1) / 2.0f;
2987 const float ym = (y0 + y1) / 2.0f;
2988
2989 geometryData.push_back(tcu::Vec3(x0, y0, z));
2990 geometryData.push_back(tcu::Vec3(xm, y1, z));
2991 geometryData.push_back(tcu::Vec3(x1, ym, z));
2992 }
2993 else
2994 {
2995 geometryData.push_back(tcu::Vec3(x0, y0, z));
2996 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
2997 }
2998
2999 startPos.y() = m / width;
3000 startPos.x() = m % width;
3001 }
3002
3003 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
3004 }
3005
3006 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3007 m_bottomAccelerationStructures.push_back(
3008 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
3009 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
3010 instanceNdx + 1);
3011 }
3012
3013 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3014
3015 return m_topAccelerationStructure.get()->getPtr();
3016 }
3017
getShaderBodyText(const TestParams & testParams)3018 const std::string TestConfigurationInstanceCustomIndex::getShaderBodyText(const TestParams &testParams)
3019 {
3020 if (testParams.geomType == GEOM_TYPE_AABBS)
3021 {
3022 const std::string result =
3023 " uint rayFlags = 0;\n"
3024 " uint cullMask = 0xFF;\n"
3025 " float tmin = 0.0;\n"
3026 " float tmax = 9.0;\n"
3027 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3028 "float(size.y), 0.0);\n"
3029 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3030 " uint value = -1;\n"
3031 " rayQueryEXT rayQuery;\n"
3032 "\n"
3033 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3034 "tmin, direct, tmax);\n"
3035 "\n"
3036 " if (rayQueryProceedEXT(rayQuery))\n"
3037 " {\n"
3038 " value--;\n"
3039 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
3040 " {\n"
3041 " value--;\n"
3042 " rayQueryGenerateIntersectionEXT(rayQuery, 0.5f);\n"
3043 "\n"
3044 " rayQueryProceedEXT(rayQuery);\n"
3045 "\n"
3046 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
3047 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
3048 " value = rayQueryGetIntersectionInstanceCustomIndexEXT(rayQuery, true);\n"
3049 " }\n"
3050 " }\n"
3051 "\n"
3052 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
3053
3054 return result;
3055 }
3056 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
3057 {
3058 const std::string result =
3059 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
3060 " uint cullMask = 0xFF;\n"
3061 " float tmin = 0.0;\n"
3062 " float tmax = 9.0;\n"
3063 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3064 "float(size.y), 0.0);\n"
3065 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3066 " uint value = -1;\n"
3067 " rayQueryEXT rayQuery;\n"
3068 "\n"
3069 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3070 "tmin, direct, tmax);\n"
3071 "\n"
3072 " if (rayQueryProceedEXT(rayQuery))\n"
3073 " {\n"
3074 " value--;\n"
3075 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
3076 " {\n"
3077 " value--;\n"
3078 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
3079 "\n"
3080 " rayQueryProceedEXT(rayQuery);\n"
3081 "\n"
3082 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
3083 " value = rayQueryGetIntersectionInstanceCustomIndexEXT(rayQuery, true);\n"
3084 " }\n"
3085 " }\n"
3086 "\n"
3087 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
3088
3089 return result;
3090 }
3091 else
3092 {
3093 TCU_THROW(InternalError, "Unknown geometry type");
3094 }
3095 }
3096
3097 class TestConfigurationIntersectionT : public TestConfigurationFloat
3098 {
3099 public:
TestConfigurationIntersectionT(Context & context)3100 TestConfigurationIntersectionT(Context &context) : TestConfigurationFloat(context)
3101 {
3102 }
3103 static const std::string getShaderBodyText(const TestParams &testParams);
3104
3105 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
3106 VkCommandBuffer cmdBuffer) override;
3107 };
3108
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)3109 const VkAccelerationStructureKHR *TestConfigurationIntersectionT::initAccelerationStructures(TestParams &testParams,
3110 VkCommandBuffer cmdBuffer)
3111 {
3112 const DeviceInterface &vkd = *m_testEnvironment->vkd;
3113 const VkDevice device = m_testEnvironment->device;
3114 Allocator &allocator = *m_testEnvironment->allocator;
3115 const uint32_t width = testParams.width;
3116 const uint32_t height = testParams.height;
3117 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
3118 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
3119 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
3120 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
3121 tcu::UVec2 startPos = tcu::UVec2(0, 0);
3122 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
3123 makeTopLevelAccelerationStructure();
3124
3125 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
3126
3127 m_topAccelerationStructure =
3128 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
3129
3130 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
3131
3132 m_expected.resize(width * height);
3133
3134 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
3135 {
3136 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
3137 makeBottomLevelAccelerationStructure();
3138
3139 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
3140 {
3141 std::vector<tcu::Vec3> geometryData;
3142
3143 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
3144
3145 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
3146 {
3147 const uint32_t n = width * startPos.y() + startPos.x();
3148 const uint32_t m = (n + 11) % (width * height);
3149 const float x0 = float(startPos.x() + 0) / float(width);
3150 const float y0 = float(startPos.y() + 0) / float(height);
3151 const float x1 = float(startPos.x() + 1) / float(width);
3152 const float y1 = float(startPos.y() + 1) / float(height);
3153 const float eps = 1.0f / float(FIXED_POINT_DIVISOR);
3154 const float z = -deFloatAbs(eps + float(startPos.x()) * float(startPos.y()) / float(width * height));
3155
3156 m_expected[n] = -int(z * FIXED_POINT_DIVISOR);
3157
3158 if (triangles)
3159 {
3160 const float xm = (x0 + x1) / 2.0f;
3161 const float ym = (y0 + y1) / 2.0f;
3162
3163 geometryData.push_back(tcu::Vec3(x0, y0, z));
3164 geometryData.push_back(tcu::Vec3(xm, y1, z));
3165 geometryData.push_back(tcu::Vec3(x1, ym, z));
3166 }
3167 else
3168 {
3169 geometryData.push_back(tcu::Vec3(x0, y0, z));
3170 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
3171 }
3172
3173 startPos.y() = m / width;
3174 startPos.x() = m % width;
3175 }
3176
3177 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
3178 }
3179
3180 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3181 m_bottomAccelerationStructures.push_back(
3182 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
3183 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4);
3184 }
3185
3186 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3187
3188 return m_topAccelerationStructure.get()->getPtr();
3189 }
3190
getShaderBodyText(const TestParams & testParams)3191 const std::string TestConfigurationIntersectionT::getShaderBodyText(const TestParams &testParams)
3192 {
3193 if (testParams.geomType == GEOM_TYPE_AABBS)
3194 {
3195 const std::string result =
3196 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3197 ";\n"
3198 " uint rayFlags = 0;\n"
3199 " uint cullMask = 0xFF;\n"
3200 " float tmin = 0.0;\n"
3201 " float tmax = 9.0;\n"
3202 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3203 "float(size.y), 0.0);\n"
3204 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3205 " int value = -k;\n"
3206 " const float t = abs(float(pos.x * pos.y) / float (size.x * size.y));\n"
3207 " rayQueryEXT rayQuery;\n"
3208 "\n"
3209 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3210 "tmin, direct, tmax);\n"
3211 "\n"
3212 " if (rayQueryProceedEXT(rayQuery))\n"
3213 " {\n"
3214 " value -= k;\n"
3215 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
3216 " {\n"
3217 " value -= k;\n"
3218 " rayQueryGenerateIntersectionEXT(rayQuery, t);\n"
3219 "\n"
3220 " rayQueryProceedEXT(rayQuery);\n"
3221 "\n"
3222 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
3223 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
3224 " value = int(k * rayQueryGetIntersectionTEXT(rayQuery, true));\n"
3225 " }\n"
3226 " }\n"
3227 "\n"
3228 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
3229
3230 return result;
3231 }
3232 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
3233 {
3234 const std::string result =
3235 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3236 ";\n"
3237 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
3238 " uint cullMask = 0xFF;\n"
3239 " float tmin = 0.0;\n"
3240 " float tmax = 9.0;\n"
3241 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3242 "float(size.y), 0.0);\n"
3243 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3244 " int value = -k;\n"
3245 " rayQueryEXT rayQuery;\n"
3246 "\n"
3247 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3248 "tmin, direct, tmax);\n"
3249 "\n"
3250 " if (rayQueryProceedEXT(rayQuery))\n"
3251 " {\n"
3252 " value -= k;\n"
3253 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
3254 " {\n"
3255 " value -= k;\n"
3256 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
3257 "\n"
3258 " rayQueryProceedEXT(rayQuery);\n"
3259 "\n"
3260 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
3261 " value = int(k * rayQueryGetIntersectionTEXT(rayQuery, true));\n"
3262 " }\n"
3263 " }\n"
3264 "\n"
3265 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
3266
3267 return result;
3268 }
3269 else
3270 {
3271 TCU_THROW(InternalError, "Unknown geometry type");
3272 }
3273 }
3274
3275 class TestConfigurationObjectRayOrigin : public TestConfigurationVector
3276 {
3277 public:
TestConfigurationObjectRayOrigin(Context & context)3278 TestConfigurationObjectRayOrigin(Context &context) : TestConfigurationVector(context)
3279 {
3280 }
3281 static const std::string getShaderBodyText(const TestParams &testParams);
3282
3283 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
3284 VkCommandBuffer cmdBuffer) override;
3285 };
3286
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)3287 const VkAccelerationStructureKHR *TestConfigurationObjectRayOrigin::initAccelerationStructures(
3288 TestParams &testParams, VkCommandBuffer cmdBuffer)
3289 {
3290 const DeviceInterface &vkd = *m_testEnvironment->vkd;
3291 const VkDevice device = m_testEnvironment->device;
3292 Allocator &allocator = *m_testEnvironment->allocator;
3293 const uint32_t width = testParams.width;
3294 const uint32_t height = testParams.height;
3295 const uint32_t depth = testParams.depth;
3296 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
3297 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
3298 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
3299 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
3300 const float z = -1.0f;
3301 tcu::UVec2 startPos = tcu::UVec2(0, 0);
3302 uint32_t pos = 0;
3303 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
3304 makeTopLevelAccelerationStructure();
3305
3306 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
3307
3308 m_topAccelerationStructure =
3309 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
3310
3311 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
3312
3313 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
3314 {
3315 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
3316 makeBottomLevelAccelerationStructure();
3317
3318 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
3319 {
3320 std::vector<tcu::Vec3> geometryData;
3321
3322 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
3323
3324 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
3325 {
3326 const uint32_t n = width * startPos.y() + startPos.x();
3327 const uint32_t m = (n + 11) % (width * height);
3328 const float x0 = float(startPos.x() + 0) / float(width);
3329 const float y0 = float(startPos.y() + 0) / float(height);
3330 const float x1 = float(startPos.x() + 1) / float(width);
3331 const float y1 = float(startPos.y() + 1) / float(height);
3332
3333 if (triangles)
3334 {
3335 const float xm = (x0 + x1) / 2.0f;
3336 const float ym = (y0 + y1) / 2.0f;
3337
3338 geometryData.push_back(tcu::Vec3(x0, y0, z));
3339 geometryData.push_back(tcu::Vec3(xm, y1, z));
3340 geometryData.push_back(tcu::Vec3(x1, ym, z));
3341 }
3342 else
3343 {
3344 geometryData.push_back(tcu::Vec3(x0, y0, z));
3345 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
3346 }
3347
3348 startPos.y() = m / width;
3349 startPos.x() = m % width;
3350 }
3351
3352 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
3353 }
3354
3355 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3356 m_bottomAccelerationStructures.push_back(
3357 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
3358 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4);
3359 }
3360
3361 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3362
3363 m_expected.resize(width * height * depth);
3364 for (uint32_t y = 0; y < height; ++y)
3365 for (uint32_t x = 0; x < width; ++x)
3366 m_expected[pos++] = int(float(FIXED_POINT_DIVISOR) * (0.5f + float(x)) / float(width));
3367
3368 for (uint32_t y = 0; y < height; ++y)
3369 for (uint32_t x = 0; x < width; ++x)
3370 m_expected[pos++] = int(float(FIXED_POINT_DIVISOR) * (0.5f + float(y)) / float(height));
3371
3372 for (uint32_t y = 0; y < height; ++y)
3373 for (uint32_t x = 0; x < width; ++x)
3374 m_expected[pos++] = 0;
3375
3376 return m_topAccelerationStructure.get()->getPtr();
3377 }
3378
getShaderBodyText(const TestParams & testParams)3379 const std::string TestConfigurationObjectRayOrigin::getShaderBodyText(const TestParams &testParams)
3380 {
3381 if (testParams.geomType == GEOM_TYPE_AABBS)
3382 {
3383 const std::string result =
3384 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3385 ";\n"
3386 " uint rayFlags = 0;\n"
3387 " uint cullMask = 0xFF;\n"
3388 " float tmin = 0.0;\n"
3389 " float tmax = 9.0;\n"
3390 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3391 "float(size.y), 0.0);\n"
3392 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3393 " ivec3 value = ivec3(-k);\n"
3394 " const float t = abs(float(pos.x * pos.y) / float (size.x * size.y));\n"
3395 " rayQueryEXT rayQuery;\n"
3396 "\n"
3397 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3398 "tmin, direct, tmax);\n"
3399 "\n"
3400 " if (rayQueryProceedEXT(rayQuery))\n"
3401 " {\n"
3402 " value -= ivec3(k);\n"
3403 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
3404 " {\n"
3405 " value -= ivec3(k);\n"
3406 " rayQueryGenerateIntersectionEXT(rayQuery, t);\n"
3407 "\n"
3408 " rayQueryProceedEXT(rayQuery);\n"
3409 "\n"
3410 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
3411 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
3412 " value = ivec3(k * rayQueryGetIntersectionObjectRayOriginEXT(rayQuery, true));\n"
3413 " }\n"
3414 " }\n"
3415 "\n"
3416 " imageStore(result, ivec3(pos.x, pos.y, 0), ivec4(value.x, 0, 0, 0));\n"
3417 " imageStore(result, ivec3(pos.x, pos.y, 1), ivec4(value.y, 0, 0, 0));\n"
3418 " imageStore(result, ivec3(pos.x, pos.y, 2), ivec4(value.z, 0, 0, 0));\n";
3419
3420 return result;
3421 }
3422 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
3423 {
3424 const std::string result =
3425 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3426 ";\n"
3427 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
3428 " uint cullMask = 0xFF;\n"
3429 " float tmin = 0.0;\n"
3430 " float tmax = 9.0;\n"
3431 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3432 "float(size.y), 0.0);\n"
3433 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3434 " ivec3 value = ivec3(-k);\n"
3435 " rayQueryEXT rayQuery;\n"
3436 "\n"
3437 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3438 "tmin, direct, tmax);\n"
3439 "\n"
3440 " if (rayQueryProceedEXT(rayQuery))\n"
3441 " {\n"
3442 " value -= ivec3(k);\n"
3443 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
3444 " {\n"
3445 " value -= ivec3(k);\n"
3446 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
3447 "\n"
3448 " rayQueryProceedEXT(rayQuery);\n"
3449 "\n"
3450 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
3451 " value = ivec3(k * rayQueryGetIntersectionObjectRayOriginEXT(rayQuery, true));\n"
3452 " }\n"
3453 " }\n"
3454 "\n"
3455 " imageStore(result, ivec3(pos.x, pos.y, 0), ivec4(value.x, 0, 0, 0));\n"
3456 " imageStore(result, ivec3(pos.x, pos.y, 1), ivec4(value.y, 0, 0, 0));\n"
3457 " imageStore(result, ivec3(pos.x, pos.y, 2), ivec4(value.z, 0, 0, 0));\n";
3458
3459 return result;
3460 }
3461 else
3462 {
3463 TCU_THROW(InternalError, "Unknown geometry type");
3464 }
3465 }
3466
3467 class TestConfigurationObjectRayDirection : public TestConfigurationVector
3468 {
3469 public:
TestConfigurationObjectRayDirection(Context & context)3470 TestConfigurationObjectRayDirection(Context &context) : TestConfigurationVector(context)
3471 {
3472 }
3473 static const std::string getShaderBodyText(const TestParams &testParams);
3474
3475 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
3476 VkCommandBuffer cmdBuffer) override;
3477 };
3478
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)3479 const VkAccelerationStructureKHR *TestConfigurationObjectRayDirection::initAccelerationStructures(
3480 TestParams &testParams, VkCommandBuffer cmdBuffer)
3481 {
3482 const DeviceInterface &vkd = *m_testEnvironment->vkd;
3483 const VkDevice device = m_testEnvironment->device;
3484 Allocator &allocator = *m_testEnvironment->allocator;
3485 const uint32_t width = testParams.width;
3486 const uint32_t height = testParams.height;
3487 const uint32_t depth = testParams.depth;
3488 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
3489 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
3490 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
3491 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
3492 const float z = -1.0f;
3493 tcu::UVec2 startPos = tcu::UVec2(0, 0);
3494 uint32_t pos = 0;
3495 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
3496 makeTopLevelAccelerationStructure();
3497
3498 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
3499
3500 m_topAccelerationStructure =
3501 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
3502
3503 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
3504
3505 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
3506 {
3507 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
3508 makeBottomLevelAccelerationStructure();
3509
3510 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
3511 {
3512 std::vector<tcu::Vec3> geometryData;
3513
3514 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
3515
3516 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
3517 {
3518 const uint32_t n = width * startPos.y() + startPos.x();
3519 const uint32_t m = (n + 11) % (width * height);
3520 const float x0 = float(startPos.x() + 0) / float(width);
3521 const float y0 = float(startPos.y() + 0) / float(height);
3522 const float x1 = float(startPos.x() + 1) / float(width);
3523 const float y1 = float(startPos.y() + 1) / float(height);
3524
3525 if (triangles)
3526 {
3527 const float xm = (x0 + x1) / 2.0f;
3528 const float ym = (y0 + y1) / 2.0f;
3529
3530 geometryData.push_back(tcu::Vec3(x0, y0, z));
3531 geometryData.push_back(tcu::Vec3(xm, y1, z));
3532 geometryData.push_back(tcu::Vec3(x1, ym, z));
3533 }
3534 else
3535 {
3536 geometryData.push_back(tcu::Vec3(x0, y0, z));
3537 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
3538 }
3539
3540 startPos.y() = m / width;
3541 startPos.x() = m % width;
3542 }
3543
3544 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
3545 }
3546
3547 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3548 m_bottomAccelerationStructures.push_back(
3549 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
3550 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4);
3551 }
3552
3553 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3554
3555 m_expected.resize(width * height * depth);
3556 for (uint32_t y = 0; y < height; ++y)
3557 for (uint32_t x = 0; x < width; ++x)
3558 m_expected[pos++] = 0;
3559
3560 for (uint32_t y = 0; y < height; ++y)
3561 for (uint32_t x = 0; x < width; ++x)
3562 m_expected[pos++] = 0;
3563
3564 for (uint32_t y = 0; y < height; ++y)
3565 for (uint32_t x = 0; x < width; ++x)
3566 m_expected[pos++] = -static_cast<int32_t>(FIXED_POINT_DIVISOR);
3567
3568 return m_topAccelerationStructure.get()->getPtr();
3569 }
3570
getShaderBodyText(const TestParams & testParams)3571 const std::string TestConfigurationObjectRayDirection::getShaderBodyText(const TestParams &testParams)
3572 {
3573 if (testParams.geomType == GEOM_TYPE_AABBS)
3574 {
3575 const std::string result =
3576 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3577 ";\n"
3578 " uint rayFlags = 0;\n"
3579 " uint cullMask = 0xFF;\n"
3580 " float tmin = 0.0;\n"
3581 " float tmax = 9.0;\n"
3582 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3583 "float(size.y), 0.0);\n"
3584 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3585 " ivec3 value = ivec3(-k);\n"
3586 " const float t = abs(float(pos.x * pos.y) / float (size.x * size.y));\n"
3587 " rayQueryEXT rayQuery;\n"
3588 "\n"
3589 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3590 "tmin, direct, tmax);\n"
3591 "\n"
3592 " if (rayQueryProceedEXT(rayQuery))\n"
3593 " {\n"
3594 " value -= ivec3(k);\n"
3595 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
3596 " {\n"
3597 " value -= ivec3(k);\n"
3598 " rayQueryGenerateIntersectionEXT(rayQuery, t);\n"
3599 "\n"
3600 " rayQueryProceedEXT(rayQuery);\n"
3601 "\n"
3602 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
3603 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
3604 " value = ivec3(k * rayQueryGetIntersectionObjectRayDirectionEXT(rayQuery, true));\n"
3605 " }\n"
3606 " }\n"
3607 "\n"
3608 " imageStore(result, ivec3(pos.x, pos.y, 0), ivec4(value.x, 0, 0, 0));\n"
3609 " imageStore(result, ivec3(pos.x, pos.y, 1), ivec4(value.y, 0, 0, 0));\n"
3610 " imageStore(result, ivec3(pos.x, pos.y, 2), ivec4(value.z, 0, 0, 0));\n";
3611
3612 return result;
3613 }
3614 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
3615 {
3616 const std::string result =
3617 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3618 ";\n"
3619 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
3620 " uint cullMask = 0xFF;\n"
3621 " float tmin = 0.0;\n"
3622 " float tmax = 9.0;\n"
3623 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3624 "float(size.y), 0.0);\n"
3625 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3626 " ivec3 value = ivec3(-k);\n"
3627 " rayQueryEXT rayQuery;\n"
3628 "\n"
3629 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3630 "tmin, direct, tmax);\n"
3631 "\n"
3632 " if (rayQueryProceedEXT(rayQuery))\n"
3633 " {\n"
3634 " value -= ivec3(k);\n"
3635 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
3636 " {\n"
3637 " value -= ivec3(k);\n"
3638 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
3639 "\n"
3640 " rayQueryProceedEXT(rayQuery);\n"
3641 "\n"
3642 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
3643 " value = ivec3(k * rayQueryGetIntersectionObjectRayDirectionEXT(rayQuery, true));\n"
3644 " }\n"
3645 " }\n"
3646 "\n"
3647 " imageStore(result, ivec3(pos.x, pos.y, 0), ivec4(value.x, 0, 0, 0));\n"
3648 " imageStore(result, ivec3(pos.x, pos.y, 1), ivec4(value.y, 0, 0, 0));\n"
3649 " imageStore(result, ivec3(pos.x, pos.y, 2), ivec4(value.z, 0, 0, 0));\n";
3650
3651 return result;
3652 }
3653 else
3654 {
3655 TCU_THROW(InternalError, "Unknown geometry type");
3656 }
3657 }
3658
3659 class TestConfigurationObjectToWorld : public TestConfigurationMatrix
3660 {
3661 public:
TestConfigurationObjectToWorld(Context & context)3662 TestConfigurationObjectToWorld(Context &context) : TestConfigurationMatrix(context)
3663 {
3664 }
3665 static const std::string getShaderBodyText(const TestParams &testParams);
3666
3667 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
3668 VkCommandBuffer cmdBuffer) override;
3669 };
3670
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)3671 const VkAccelerationStructureKHR *TestConfigurationObjectToWorld::initAccelerationStructures(TestParams &testParams,
3672 VkCommandBuffer cmdBuffer)
3673 {
3674 const DeviceInterface &vkd = *m_testEnvironment->vkd;
3675 const VkDevice device = m_testEnvironment->device;
3676 Allocator &allocator = *m_testEnvironment->allocator;
3677 const uint32_t width = testParams.width;
3678 const uint32_t height = testParams.height;
3679 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
3680 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
3681 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
3682 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
3683 const float z = -1.0f;
3684 tcu::UVec2 startPos = tcu::UVec2(0, 0);
3685 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
3686 makeTopLevelAccelerationStructure();
3687
3688 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
3689
3690 m_topAccelerationStructure =
3691 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
3692
3693 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
3694
3695 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
3696 {
3697 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
3698 makeBottomLevelAccelerationStructure();
3699 VkTransformMatrixKHR transform = identityMatrix3x4;
3700
3701 transform.matrix[0][3] = (1.0f / 8.0f) / float(width);
3702 transform.matrix[1][3] = (1.0f / 16.0f) / float(height);
3703
3704 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
3705 {
3706 std::vector<tcu::Vec3> geometryData;
3707
3708 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
3709
3710 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
3711 {
3712 const uint32_t n = width * startPos.y() + startPos.x();
3713 const uint32_t m = (n + 11) % (width * height);
3714 const float x0 = float(startPos.x() + 0) / float(width);
3715 const float y0 = float(startPos.y() + 0) / float(height);
3716 const float x1 = float(startPos.x() + 1) / float(width);
3717 const float y1 = float(startPos.y() + 1) / float(height);
3718
3719 if (triangles)
3720 {
3721 const float xm = (x0 + x1) / 2.0f;
3722 const float ym = (y0 + y1) / 2.0f;
3723
3724 geometryData.push_back(tcu::Vec3(x0, y0, z));
3725 geometryData.push_back(tcu::Vec3(xm, y1, z));
3726 geometryData.push_back(tcu::Vec3(x1, ym, z));
3727 }
3728 else
3729 {
3730 geometryData.push_back(tcu::Vec3(x0, y0, z));
3731 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
3732 }
3733
3734 startPos.y() = m / width;
3735 startPos.x() = m % width;
3736 }
3737
3738 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
3739 }
3740
3741 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3742 m_bottomAccelerationStructures.push_back(
3743 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
3744 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), transform);
3745 }
3746
3747 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3748
3749 {
3750 const uint32_t imageDepth = 4 * 4;
3751 const int translateColumnNumber = 3;
3752 const uint32_t colCount = 4;
3753 const uint32_t rowCount = 3;
3754 const uint32_t zStride = height * width;
3755 const uint32_t expectedFloats = imageDepth * zStride;
3756 const float translateX = (+1.0f / 8.0f) / float(width);
3757 const float translateY = (+1.0f / 16.0f) / float(height);
3758 tcu::Matrix<float, rowCount, colCount> m;
3759
3760 m[translateColumnNumber][0] = translateX;
3761 m[translateColumnNumber][1] = translateY;
3762
3763 m_expected.resize(expectedFloats);
3764
3765 for (uint32_t y = 0; y < height; ++y)
3766 {
3767 for (uint32_t x = 0; x < width; ++x)
3768 {
3769 const uint32_t elem0Pos = x + width * y;
3770
3771 for (uint32_t rowNdx = 0; rowNdx < rowCount; ++rowNdx)
3772 for (uint32_t colNdx = 0; colNdx < colCount; ++colNdx)
3773 {
3774 const uint32_t zNdx = rowNdx * colCount + colNdx;
3775 const uint32_t posNdx = elem0Pos + zStride * zNdx;
3776
3777 m_expected[posNdx] = static_cast<int32_t>(FIXED_POINT_DIVISOR * m[colNdx][rowNdx]);
3778 }
3779 }
3780 }
3781 }
3782
3783 return m_topAccelerationStructure.get()->getPtr();
3784 }
3785
getShaderBodyText(const TestParams & testParams)3786 const std::string TestConfigurationObjectToWorld::getShaderBodyText(const TestParams &testParams)
3787 {
3788 if (testParams.geomType == GEOM_TYPE_AABBS)
3789 {
3790 const std::string result =
3791 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3792 ";\n"
3793 " uint rayFlags = 0;\n"
3794 " uint cullMask = 0xFF;\n"
3795 " float tmin = 0.0;\n"
3796 " float tmax = 9.0;\n"
3797 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3798 "float(size.y), 0.0);\n"
3799 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3800 " mat4x3 value = mat4x3(-k);\n"
3801 " const float t = abs(float(pos.x * pos.y) / float (size.x * size.y));\n"
3802 " rayQueryEXT rayQuery;\n"
3803 "\n"
3804 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3805 "tmin, direct, tmax);\n"
3806 "\n"
3807 " if (rayQueryProceedEXT(rayQuery))\n"
3808 " {\n"
3809 " value -= mat4x3(k);\n"
3810 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
3811 " {\n"
3812 " value -= mat4x3(k);\n"
3813 " rayQueryGenerateIntersectionEXT(rayQuery, t);\n"
3814 "\n"
3815 " rayQueryProceedEXT(rayQuery);\n"
3816 "\n"
3817 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
3818 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
3819 " value = mat4x3(k * rayQueryGetIntersectionObjectToWorldEXT(rayQuery, true));\n"
3820 " }\n"
3821 " }\n"
3822 "\n"
3823 " int ndx = -1;\n"
3824 " for (int row = 0; row < 3; row++)\n"
3825 " for (int col = 0; col < 4; col++)\n"
3826 " {\n"
3827 " ndx++;\n"
3828 " ivec3 p = ivec3(pos.xy, ndx);\n"
3829 " float r = value[col][row];\n"
3830 " ivec4 c = ivec4(int(r),0,0,1);\n"
3831 " imageStore(result, p, c);\n"
3832 " }\n";
3833
3834 return result;
3835 }
3836 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
3837 {
3838 const std::string result =
3839 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
3840 ";\n"
3841 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
3842 " uint cullMask = 0xFF;\n"
3843 " float tmin = 0.0;\n"
3844 " float tmax = 9.0;\n"
3845 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
3846 "float(size.y), 0.0);\n"
3847 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
3848 " mat4x3 value = mat4x3(-k);\n"
3849 " rayQueryEXT rayQuery;\n"
3850 "\n"
3851 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
3852 "tmin, direct, tmax);\n"
3853 "\n"
3854 " if (rayQueryProceedEXT(rayQuery))\n"
3855 " {\n"
3856 " value -= mat4x3(k);\n"
3857 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
3858 " {\n"
3859 " value -= mat4x3(k);\n"
3860 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
3861 "\n"
3862 " rayQueryProceedEXT(rayQuery);\n"
3863 "\n"
3864 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
3865 " value = mat4x3(k * rayQueryGetIntersectionObjectToWorldEXT(rayQuery, true));\n"
3866 " }\n"
3867 " }\n"
3868 "\n"
3869 " int ndx = -1;\n"
3870 " for (int row = 0; row < 3; row++)\n"
3871 " for (int col = 0; col < 4; col++)\n"
3872 " {\n"
3873 " ndx++;\n"
3874 " ivec3 p = ivec3(pos.xy, ndx);\n"
3875 " float r = value[col][row];\n"
3876 " ivec4 c = ivec4(int(r),0,0,1);\n"
3877 " imageStore(result, p, c);\n"
3878 " }\n";
3879
3880 return result;
3881 }
3882 else
3883 {
3884 TCU_THROW(InternalError, "Unknown geometry type");
3885 }
3886 }
3887
3888 class TestConfigurationWorldToObject : public TestConfigurationMatrix
3889 {
3890 public:
TestConfigurationWorldToObject(Context & context)3891 TestConfigurationWorldToObject(Context &context) : TestConfigurationMatrix(context)
3892 {
3893 }
3894 static const std::string getShaderBodyText(const TestParams &testParams);
3895
3896 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
3897 VkCommandBuffer cmdBuffer) override;
3898 };
3899
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)3900 const VkAccelerationStructureKHR *TestConfigurationWorldToObject::initAccelerationStructures(TestParams &testParams,
3901 VkCommandBuffer cmdBuffer)
3902 {
3903 const DeviceInterface &vkd = *m_testEnvironment->vkd;
3904 const VkDevice device = m_testEnvironment->device;
3905 Allocator &allocator = *m_testEnvironment->allocator;
3906 const uint32_t width = testParams.width;
3907 const uint32_t height = testParams.height;
3908 const bool triangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
3909 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
3910 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
3911 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
3912 const float z = -1.0f;
3913 tcu::UVec2 startPos = tcu::UVec2(0, 0);
3914 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
3915 makeTopLevelAccelerationStructure();
3916
3917 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
3918
3919 m_topAccelerationStructure =
3920 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
3921
3922 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
3923
3924 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
3925 {
3926 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
3927 makeBottomLevelAccelerationStructure();
3928 VkTransformMatrixKHR transform = identityMatrix3x4;
3929
3930 transform.matrix[0][3] = (1.0f / 8.0f) / float(width);
3931 transform.matrix[1][3] = (1.0f / 16.0f) / float(height);
3932
3933 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
3934 {
3935 std::vector<tcu::Vec3> geometryData;
3936
3937 geometryData.reserve(squaresGroupCount * (triangles ? 3u : 2u));
3938
3939 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
3940 {
3941 const uint32_t n = width * startPos.y() + startPos.x();
3942 const uint32_t m = (n + 11) % (width * height);
3943 const float x0 = float(startPos.x() + 0) / float(width);
3944 const float y0 = float(startPos.y() + 0) / float(height);
3945 const float x1 = float(startPos.x() + 1) / float(width);
3946 const float y1 = float(startPos.y() + 1) / float(height);
3947
3948 if (triangles)
3949 {
3950 const float xm = (x0 + x1) / 2.0f;
3951 const float ym = (y0 + y1) / 2.0f;
3952
3953 geometryData.push_back(tcu::Vec3(x0, y0, z));
3954 geometryData.push_back(tcu::Vec3(xm, y1, z));
3955 geometryData.push_back(tcu::Vec3(x1, ym, z));
3956 }
3957 else
3958 {
3959 geometryData.push_back(tcu::Vec3(x0, y0, z));
3960 geometryData.push_back(tcu::Vec3(x1, y1, z * 0.9f));
3961 }
3962
3963 startPos.y() = m / width;
3964 startPos.x() = m % width;
3965 }
3966
3967 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, triangles);
3968 }
3969
3970 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3971 m_bottomAccelerationStructures.push_back(
3972 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
3973 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), transform);
3974 }
3975
3976 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
3977
3978 {
3979 const uint32_t imageDepth = 4 * 4;
3980 const int translateColumnNumber = 3;
3981 const uint32_t colCount = 4;
3982 const uint32_t rowCount = 3;
3983 const uint32_t zStride = height * width;
3984 const uint32_t expectedFloats = imageDepth * zStride;
3985 const float translateX = (-1.0f / 8.0f) / float(width);
3986 const float translateY = (-1.0f / 16.0f) / float(height);
3987 tcu::Matrix<float, rowCount, colCount> m;
3988
3989 m[translateColumnNumber][0] = translateX;
3990 m[translateColumnNumber][1] = translateY;
3991
3992 m_expected.resize(expectedFloats);
3993
3994 for (uint32_t y = 0; y < height; ++y)
3995 {
3996 for (uint32_t x = 0; x < width; ++x)
3997 {
3998 const uint32_t elem0Pos = x + width * y;
3999
4000 for (uint32_t rowNdx = 0; rowNdx < rowCount; ++rowNdx)
4001 for (uint32_t colNdx = 0; colNdx < colCount; ++colNdx)
4002 {
4003 const uint32_t zNdx = rowNdx * colCount + colNdx;
4004 const uint32_t posNdx = elem0Pos + zStride * zNdx;
4005
4006 m_expected[posNdx] = static_cast<int32_t>(FIXED_POINT_DIVISOR * m[colNdx][rowNdx]);
4007 }
4008 }
4009 }
4010 }
4011
4012 return m_topAccelerationStructure.get()->getPtr();
4013 }
4014
getShaderBodyText(const TestParams & testParams)4015 const std::string TestConfigurationWorldToObject::getShaderBodyText(const TestParams &testParams)
4016 {
4017 if (testParams.geomType == GEOM_TYPE_AABBS)
4018 {
4019 const std::string result =
4020 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
4021 ";\n"
4022 " uint rayFlags = 0;\n"
4023 " uint cullMask = 0xFF;\n"
4024 " float tmin = 0.0;\n"
4025 " float tmax = 9.0;\n"
4026 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4027 "float(size.y), 0.0);\n"
4028 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
4029 " mat4x3 value = mat4x3(-k);\n"
4030 " const float t = abs(float(pos.x * pos.y) / float (size.x * size.y));\n"
4031 " rayQueryEXT rayQuery;\n"
4032 "\n"
4033 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
4034 "tmin, direct, tmax);\n"
4035 "\n"
4036 " if (rayQueryProceedEXT(rayQuery))\n"
4037 " {\n"
4038 " value -= mat4x3(k);\n"
4039 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
4040 " {\n"
4041 " value -= mat4x3(k);\n"
4042 " rayQueryGenerateIntersectionEXT(rayQuery, t);\n"
4043 "\n"
4044 " rayQueryProceedEXT(rayQuery);\n"
4045 "\n"
4046 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == "
4047 "gl_RayQueryCommittedIntersectionGeneratedEXT)\n"
4048 " value = mat4x3(k * rayQueryGetIntersectionWorldToObjectEXT(rayQuery, true));\n"
4049 " }\n"
4050 " }\n"
4051 "\n"
4052 " int ndx = -1;\n"
4053 " for (int row = 0; row < 3; row++)\n"
4054 " for (int col = 0; col < 4; col++)\n"
4055 " {\n"
4056 " ndx++;\n"
4057 " ivec3 p = ivec3(pos.xy, ndx);\n"
4058 " float r = value[col][row];\n"
4059 " ivec4 c = ivec4(int(r),0,0,1);\n"
4060 " imageStore(result, p, c);\n"
4061 " }\n";
4062
4063 return result;
4064 }
4065 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
4066 {
4067 const std::string result =
4068 " const int k = " + de::toString(FIXED_POINT_DIVISOR) +
4069 ";\n"
4070 " uint rayFlags = gl_RayFlagsNoOpaqueEXT;\n"
4071 " uint cullMask = 0xFF;\n"
4072 " float tmin = 0.0;\n"
4073 " float tmax = 9.0;\n"
4074 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4075 "float(size.y), 0.0);\n"
4076 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
4077 " mat4x3 value = mat4x3(-k);\n"
4078 " rayQueryEXT rayQuery;\n"
4079 "\n"
4080 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
4081 "tmin, direct, tmax);\n"
4082 "\n"
4083 " if (rayQueryProceedEXT(rayQuery))\n"
4084 " {\n"
4085 " value -= mat4x3(k);\n"
4086 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionTriangleEXT)\n"
4087 " {\n"
4088 " value -= mat4x3(k);\n"
4089 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4090 "\n"
4091 " rayQueryProceedEXT(rayQuery);\n"
4092 "\n"
4093 " if (rayQueryGetIntersectionTypeEXT(rayQuery, true) == gl_RayQueryCommittedIntersectionTriangleEXT)\n"
4094 " value = mat4x3(k * rayQueryGetIntersectionWorldToObjectEXT(rayQuery, true));\n"
4095 " }\n"
4096 " }\n"
4097 "\n"
4098 " int ndx = -1;\n"
4099 " for (int row = 0; row < 3; row++)\n"
4100 " for (int col = 0; col < 4; col++)\n"
4101 " {\n"
4102 " ndx++;\n"
4103 " ivec3 p = ivec3(pos.xy, ndx);\n"
4104 " float r = value[col][row];\n"
4105 " ivec4 c = ivec4(int(r),0,0,1);\n"
4106 " imageStore(result, p, c);\n"
4107 " }\n";
4108
4109 return result;
4110 }
4111 else
4112 {
4113 TCU_THROW(InternalError, "Unknown geometry type");
4114 }
4115 }
4116
4117 class TestConfigurationNullASStruct : public TestConfiguration
4118 {
4119 public:
4120 TestConfigurationNullASStruct(Context &context);
4121 ~TestConfigurationNullASStruct();
4122
4123 static const std::string getShaderBodyText(const TestParams &testParams);
4124 static void checkSupport(Context &context, const TestParams &testParams);
4125
4126 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
4127 VkCommandBuffer cmdBuffer) override;
4128
4129 protected:
4130 void prepareTestEnvironment(Context &context);
4131 Move<VkAccelerationStructureKHR> m_emptyAccelerationStructure;
4132
4133 Move<VkDevice> m_device;
4134 de::MovePtr<DeviceDriver> m_vkd;
4135 de::MovePtr<SimpleAllocator> m_allocator;
4136 };
4137
TestConfigurationNullASStruct(Context & context)4138 TestConfigurationNullASStruct::TestConfigurationNullASStruct(Context &context)
4139 : TestConfiguration(context)
4140 , m_emptyAccelerationStructure()
4141 , m_device()
4142 , m_vkd()
4143 , m_allocator()
4144 {
4145 prepareTestEnvironment(context);
4146 }
4147
~TestConfigurationNullASStruct()4148 TestConfigurationNullASStruct::~TestConfigurationNullASStruct()
4149 {
4150 }
4151
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)4152 const VkAccelerationStructureKHR *TestConfigurationNullASStruct::initAccelerationStructures(TestParams &testParams,
4153 VkCommandBuffer cmdBuffer)
4154 {
4155 DE_UNREF(cmdBuffer);
4156
4157 m_expected = std::vector<int32_t>(testParams.width * testParams.height, 1);
4158
4159 return &m_emptyAccelerationStructure.get();
4160 }
4161
checkSupport(Context & context,const TestParams & testParams)4162 void TestConfigurationNullASStruct::checkSupport(Context &context, const TestParams &testParams)
4163 {
4164 DE_UNREF(testParams);
4165
4166 // Check if the physical device supports VK_EXT_robustness2 and the nullDescriptor feature.
4167 const auto &vki = context.getInstanceInterface();
4168 const auto physicalDevice = context.getPhysicalDevice();
4169 const auto &supportedExtensions = enumerateCachedDeviceExtensionProperties(vki, physicalDevice);
4170
4171 if (!isExtensionStructSupported(supportedExtensions, RequiredExtension("VK_EXT_robustness2")))
4172 TCU_THROW(NotSupportedError, "VK_EXT_robustness2 not supported");
4173
4174 VkPhysicalDeviceRobustness2FeaturesEXT robustness2Features = initVulkanStructure();
4175 VkPhysicalDeviceFeatures2 features2 = initVulkanStructure(&robustness2Features);
4176
4177 vki.getPhysicalDeviceFeatures2(physicalDevice, &features2);
4178 if (!robustness2Features.nullDescriptor)
4179 TCU_THROW(NotSupportedError, "VkPhysicalDeviceRobustness2FeaturesEXT::nullDescriptor not supported");
4180 }
4181
prepareTestEnvironment(Context & context)4182 void TestConfigurationNullASStruct::prepareTestEnvironment(Context &context)
4183 {
4184 // Check if the physical device supports VK_EXT_robustness2 and the nullDescriptor feature.
4185 const auto &vkp = context.getPlatformInterface();
4186 const auto &vki = context.getInstanceInterface();
4187 const auto instance = context.getInstance();
4188 const auto physicalDevice = context.getPhysicalDevice();
4189 const auto queueFamilyIndex = context.getUniversalQueueFamilyIndex();
4190 const auto queuePriority = 1.0f;
4191 bool accelStructSupport = false;
4192
4193 // Add anything that's supported and may be needed, including nullDescriptor.
4194 VkPhysicalDeviceFeatures2 features2 = initVulkanStructure();
4195 VkPhysicalDeviceBufferDeviceAddressFeaturesKHR deviceAddressFeatures = initVulkanStructure();
4196 VkPhysicalDeviceAccelerationStructureFeaturesKHR accelerationStructureFeatures = initVulkanStructure();
4197 VkPhysicalDeviceRayQueryFeaturesKHR rayQueryFeatures = initVulkanStructure();
4198 VkPhysicalDeviceRayTracingPipelineFeaturesKHR raytracingPipelineFeatures = initVulkanStructure();
4199 VkPhysicalDeviceRobustness2FeaturesEXT robustness2Features = initVulkanStructure();
4200 std::vector<const char *> deviceExtensions;
4201
4202 if (context.isDeviceFunctionalitySupported("VK_KHR_deferred_host_operations"))
4203 {
4204 deviceExtensions.push_back("VK_KHR_deferred_host_operations");
4205 }
4206 if (context.isDeviceFunctionalitySupported("VK_KHR_buffer_device_address"))
4207 {
4208 deviceAddressFeatures.pNext = features2.pNext;
4209 features2.pNext = &deviceAddressFeatures;
4210 deviceExtensions.push_back("VK_KHR_buffer_device_address");
4211 }
4212 if (context.isDeviceFunctionalitySupported("VK_KHR_acceleration_structure"))
4213 {
4214 accelerationStructureFeatures.pNext = features2.pNext;
4215 features2.pNext = &accelerationStructureFeatures;
4216 deviceExtensions.push_back("VK_KHR_acceleration_structure");
4217 accelStructSupport = true;
4218 }
4219
4220 if (context.isDeviceFunctionalitySupported("VK_KHR_ray_query"))
4221 {
4222 rayQueryFeatures.pNext = features2.pNext;
4223 features2.pNext = &rayQueryFeatures;
4224 deviceExtensions.push_back("VK_KHR_ray_query");
4225 }
4226
4227 if (context.isDeviceFunctionalitySupported("VK_KHR_ray_tracing_pipeline"))
4228 {
4229 raytracingPipelineFeatures.pNext = features2.pNext;
4230 features2.pNext = &raytracingPipelineFeatures;
4231 deviceExtensions.push_back("VK_KHR_ray_tracing_pipeline");
4232 }
4233
4234 vki.getPhysicalDeviceFeatures2(physicalDevice, &features2);
4235
4236 // Add robustness2 features to the chain and make sure robustBufferAccess is consistent with robustBufferAccess2.
4237 features2.features.robustBufferAccess = VK_FALSE;
4238 robustness2Features.nullDescriptor = VK_TRUE;
4239 robustness2Features.pNext = features2.pNext;
4240 features2.pNext = &robustness2Features;
4241
4242 // Add more needed extensions.
4243 deviceExtensions.push_back("VK_EXT_robustness2");
4244 if (accelStructSupport)
4245 {
4246 // Not promoted yet in Vulkan 1.1.
4247 deviceExtensions.push_back("VK_EXT_descriptor_indexing");
4248 deviceExtensions.push_back("VK_KHR_spirv_1_4");
4249 deviceExtensions.push_back("VK_KHR_shader_float_controls");
4250 }
4251
4252 const VkDeviceQueueCreateInfo queueInfo = {
4253 VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO, // VkStructureType sType;
4254 nullptr, // const void* pNext;
4255 0u, // VkDeviceQueueCreateFlags flags;
4256 queueFamilyIndex, // uint32_t queueFamilyIndex;
4257 1u, // uint32_t queueCount;
4258 &queuePriority, // const float* pQueuePriorities;
4259 };
4260
4261 const VkDeviceCreateInfo createInfo = {
4262 VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO, // VkStructureType sType;
4263 features2.pNext, // const void* pNext;
4264 0u, // VkDeviceCreateFlags flags;
4265 1u, // uint32_t queueCreateInfoCount;
4266 &queueInfo, // const VkDeviceQueueCreateInfo* pQueueCreateInfos;
4267 0u, // uint32_t enabledLayerCount;
4268 nullptr, // const char* const* ppEnabledLayerNames;
4269 static_cast<uint32_t>(deviceExtensions.size()), // uint32_t enabledExtensionCount;
4270 deviceExtensions.data(), // const char* const* ppEnabledExtensionNames;
4271 &features2.features, // const VkPhysicalDeviceFeatures* pEnabledFeatures;
4272 };
4273
4274 m_device = createCustomDevice(context.getTestContext().getCommandLine().isValidationEnabled(), vkp, instance, vki,
4275 physicalDevice, &createInfo);
4276 m_vkd = de::MovePtr<DeviceDriver>(new DeviceDriver(vkp, instance, m_device.get(), context.getUsedApiVersion(),
4277 context.getTestContext().getCommandLine()));
4278 const auto queue = getDeviceQueue(*m_vkd, *m_device, queueFamilyIndex, 0u);
4279 m_allocator = de::MovePtr<SimpleAllocator>(
4280 new SimpleAllocator(*m_vkd, m_device.get(), getPhysicalDeviceMemoryProperties(vki, physicalDevice)));
4281
4282 m_testEnvironment = de::MovePtr<TestEnvironment>(new TestEnvironment{
4283 &vki, // const InstanceInterface* vki;
4284 physicalDevice, // VkPhysicalDevice physicalDevice;
4285 m_vkd.get(), // const DeviceInterface* vkd;
4286 m_device.get(), // VkDevice device;
4287 m_allocator.get(), // Allocator* allocator;
4288 queue, // VkQueue queue;
4289 queueFamilyIndex, // uint32_t queueFamilyIndex;
4290 &context.getBinaryCollection(), // BinaryCollection* binaryCollection;
4291 &context.getTestContext().getLog(), // tcu::TestLog* log;
4292 });
4293 }
4294
getShaderBodyText(const TestParams & testParams)4295 const std::string TestConfigurationNullASStruct::getShaderBodyText(const TestParams &testParams)
4296 {
4297 DE_UNREF(testParams);
4298
4299 const std::string result = " uint rayFlags = 0;\n"
4300 " uint cullMask = 0xFF;\n"
4301 " float tmin = 0.0;\n"
4302 " float tmax = 9.0;\n"
4303 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + "
4304 "0.5f) / float(size.y), 0.0);\n"
4305 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
4306 " uint value = 1;\n"
4307 " rayQueryEXT rayQuery;\n"
4308 "\n"
4309 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, "
4310 "cullMask, origin, tmin, direct, tmax);\n"
4311 "\n"
4312 " if (rayQueryProceedEXT(rayQuery))\n"
4313 " {\n"
4314 " value++;\n"
4315 "\n"
4316 " rayQueryTerminateEXT(rayQuery);\n"
4317 " }\n"
4318 "\n"
4319 " imageStore(result, pos, ivec4(value, 0, 0, 0));\n";
4320
4321 return result;
4322 }
4323
4324 class TestConfigurationGetIntersectionCandidateAABBOpaque : public TestConfiguration
4325 {
4326 public:
TestConfigurationGetIntersectionCandidateAABBOpaque(Context & context)4327 TestConfigurationGetIntersectionCandidateAABBOpaque(Context &context) : TestConfiguration(context)
4328 {
4329 }
4330 static const std::string getShaderBodyText(const TestParams &testParams);
4331
4332 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
4333 VkCommandBuffer cmdBuffer) override;
4334 };
4335
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)4336 const VkAccelerationStructureKHR *TestConfigurationGetIntersectionCandidateAABBOpaque::initAccelerationStructures(
4337 TestParams &testParams, VkCommandBuffer cmdBuffer)
4338 {
4339 const DeviceInterface &vkd = *m_testEnvironment->vkd;
4340 const VkDevice device = m_testEnvironment->device;
4341 Allocator &allocator = *m_testEnvironment->allocator;
4342 const uint32_t width = testParams.width;
4343 const uint32_t height = testParams.height;
4344 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
4345 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
4346 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
4347 const bool usesTriangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
4348 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
4349 makeTopLevelAccelerationStructure();
4350
4351 DE_ASSERT(instancesGroupCount == 1);
4352 DE_ASSERT(geometriesGroupCount == 1);
4353 DE_ASSERT(squaresGroupCount == width * height);
4354
4355 m_topAccelerationStructure =
4356 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
4357
4358 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
4359
4360 m_expected.resize(width * height);
4361
4362 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
4363 {
4364 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
4365 makeBottomLevelAccelerationStructure();
4366
4367 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
4368 {
4369 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4370 {
4371 std::vector<tcu::Vec3> geometryData;
4372
4373 const auto squareX = (squareNdx % width);
4374 const auto squareY = (squareNdx / width);
4375 const bool isOpaque = (squareNdx % 2) == 0;
4376 const VkGeometryFlagsKHR flags = (isOpaque) ? VK_GEOMETRY_OPAQUE_BIT_KHR : 0;
4377
4378 const float x0 = float(squareX + 0) / float(width);
4379 const float y0 = float(squareY + 0) / float(height);
4380 const float x1 = float(squareX + 1) / float(width);
4381 const float y1 = float(squareY + 1) / float(height);
4382
4383 if (usesTriangles)
4384 {
4385 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4386 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
4387 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4388
4389 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4390 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
4391 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4392 }
4393 else
4394 {
4395 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4396 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4397 }
4398
4399 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, usesTriangles, flags);
4400 }
4401 }
4402
4403 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4404 m_bottomAccelerationStructures.push_back(
4405 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
4406 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
4407 instanceNdx + 1);
4408 }
4409
4410 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4411
4412 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4413 {
4414 m_expected.at(squareNdx) = (squareNdx % 2) == 0;
4415 }
4416
4417 return m_topAccelerationStructure.get()->getPtr();
4418 }
4419
getShaderBodyText(const TestParams & testParams)4420 const std::string TestConfigurationGetIntersectionCandidateAABBOpaque::getShaderBodyText(const TestParams &testParams)
4421 {
4422 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4423 {
4424 const std::string result =
4425 " uint rayFlags = 0;\n"
4426 " uint cullMask = 0xFF;\n"
4427 " float tmin = 0.0001;\n"
4428 " float tmax = 9.0;\n"
4429 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4430 "float(size.y), 0.2);\n"
4431 " vec3 direct = vec3(0.0, 0.0, -1.0);\n"
4432 " rayQueryEXT rayQuery;\n"
4433 "\n"
4434 " int result_i32 = 0;\n"
4435 "\n"
4436 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
4437 "tmin, direct, tmax);\n"
4438 "\n"
4439 " while (rayQueryProceedEXT(rayQuery))\n"
4440 " {\n"
4441 " if (rayQueryGetIntersectionTypeEXT(rayQuery, false) == gl_RayQueryCandidateIntersectionAABBEXT)\n"
4442 " {\n"
4443 " result_i32 |= rayQueryGetIntersectionCandidateAABBOpaqueEXT(rayQuery) ? 1 : 0;\n"
4444 "\n"
4445 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4446 " }\n"
4447 " }\n"
4448 "\n"
4449 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
4450
4451 return result;
4452 }
4453 else
4454 {
4455 TCU_THROW(InternalError, "Unknown geometry type");
4456 }
4457 }
4458
4459 class TestConfigurationGetIntersectionFrontFace : public TestConfiguration
4460 {
4461 public:
TestConfigurationGetIntersectionFrontFace(Context & context)4462 TestConfigurationGetIntersectionFrontFace(Context &context) : TestConfiguration(context)
4463 {
4464 }
4465 static const std::string getShaderBodyTextCandidate(const TestParams &testParams);
4466 static const std::string getShaderBodyTextCommitted(const TestParams &testParams);
4467
4468 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
4469 VkCommandBuffer cmdBuffer) override;
4470 };
4471
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)4472 const VkAccelerationStructureKHR *TestConfigurationGetIntersectionFrontFace::initAccelerationStructures(
4473 TestParams &testParams, VkCommandBuffer cmdBuffer)
4474 {
4475 const DeviceInterface &vkd = *m_testEnvironment->vkd;
4476 const VkDevice device = m_testEnvironment->device;
4477 Allocator &allocator = *m_testEnvironment->allocator;
4478 const uint32_t width = testParams.width;
4479 const uint32_t height = testParams.height;
4480 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
4481 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
4482 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
4483 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
4484 makeTopLevelAccelerationStructure();
4485
4486 DE_ASSERT(instancesGroupCount == 1);
4487 DE_ASSERT(geometriesGroupCount == 1);
4488 DE_ASSERT(squaresGroupCount == width * height);
4489
4490 m_topAccelerationStructure =
4491 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
4492
4493 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
4494
4495 m_expected.resize(width * height);
4496
4497 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
4498 {
4499 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
4500 makeBottomLevelAccelerationStructure();
4501
4502 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
4503 {
4504 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4505 {
4506 std::vector<tcu::Vec3> geometryData;
4507
4508 const auto squareX = (squareNdx % width);
4509 const auto squareY = (squareNdx / width);
4510
4511 const float x0 = float(squareX + 0) / float(width);
4512 const float y0 = float(squareY + 0) / float(height);
4513 const float x1 = float(squareX + 1) / float(width);
4514 const float y1 = float(squareY + 1) / float(height);
4515
4516 if ((squareNdx % 2) == 0)
4517 {
4518 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4519 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
4520 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4521
4522 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4523 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
4524 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4525 }
4526 else
4527 {
4528 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4529 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
4530 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4531
4532 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4533 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
4534 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4535 }
4536
4537 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, true /* triangles */);
4538 }
4539 }
4540
4541 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4542 m_bottomAccelerationStructures.push_back(
4543 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
4544 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
4545 instanceNdx + 1);
4546 }
4547
4548 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4549
4550 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4551 {
4552 m_expected.at(squareNdx) = (squareNdx % 2) != 0;
4553 }
4554
4555 return m_topAccelerationStructure.get()->getPtr();
4556 }
4557
getShaderBodyTextCandidate(const TestParams & testParams)4558 const std::string TestConfigurationGetIntersectionFrontFace::getShaderBodyTextCandidate(const TestParams &testParams)
4559 {
4560 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4561 {
4562 const std::string result = " uint rayFlags = 0;\n"
4563 " uint cullMask = 0xFF;\n"
4564 " float tmin = 0.0001;\n"
4565 " float tmax = 9.0;\n"
4566 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) "
4567 "+ 0.5f) / float(size.y), 0.2);\n"
4568 " vec3 direct = vec3(0, 0, "
4569 " -1.0);\n"
4570 " rayQueryEXT rayQuery;\n"
4571 "\n"
4572 " int result_i32 = 2;\n"
4573 "\n"
4574 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, "
4575 "cullMask, origin, tmin, direct, tmax);\n"
4576 "\n"
4577 " while (rayQueryProceedEXT(rayQuery))\n"
4578 " {\n"
4579 " result_i32 = rayQueryGetIntersectionFrontFaceEXT(rayQuery, false) ? 1 : 0;\n"
4580 "\n"
4581 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4582 " }\n"
4583 "\n"
4584 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
4585
4586 return result;
4587 }
4588 else
4589 {
4590 TCU_THROW(InternalError, "Unknown geometry type");
4591 }
4592 }
4593
getShaderBodyTextCommitted(const TestParams & testParams)4594 const std::string TestConfigurationGetIntersectionFrontFace::getShaderBodyTextCommitted(const TestParams &testParams)
4595 {
4596 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4597 {
4598 const std::string result =
4599 " uint rayFlags = 0;\n"
4600 " uint cullMask = 0xFF;\n"
4601 " float tmin = 0.0001;\n"
4602 " float tmax = 9.0;\n"
4603 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4604 "float(size.y), 0.2);\n"
4605 " vec3 direct = vec3(0, 0, "
4606 " -1.0);\n"
4607 " rayQueryEXT rayQuery;\n"
4608 "\n"
4609 " bool intersection_found = false;\n"
4610 " int result_i32 = 0;\n"
4611 "\n"
4612 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
4613 "tmin, direct, tmax);\n"
4614 "\n"
4615 " while (rayQueryProceedEXT(rayQuery))\n"
4616 " {\n"
4617 " intersection_found = true;\n"
4618 "\n"
4619 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4620 " }\n"
4621 "\n"
4622 " result_i32 = (intersection_found) ? (rayQueryGetIntersectionFrontFaceEXT(rayQuery, true) ? 1 : 0)\n"
4623 " : 2;\n"
4624 "\n"
4625 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
4626
4627 return result;
4628 }
4629 else
4630 {
4631 TCU_THROW(InternalError, "Unknown geometry type");
4632 }
4633 }
4634
4635 class TestConfigurationGetIntersectionGeometryIndex : public TestConfiguration
4636 {
4637 public:
TestConfigurationGetIntersectionGeometryIndex(Context & context)4638 TestConfigurationGetIntersectionGeometryIndex(Context &context) : TestConfiguration(context)
4639 {
4640 }
4641 static const std::string getShaderBodyTextCandidate(const TestParams &testParams);
4642 static const std::string getShaderBodyTextCommitted(const TestParams &testParams);
4643
4644 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
4645 VkCommandBuffer cmdBuffer) override;
4646 };
4647
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)4648 const VkAccelerationStructureKHR *TestConfigurationGetIntersectionGeometryIndex::initAccelerationStructures(
4649 TestParams &testParams, VkCommandBuffer cmdBuffer)
4650 {
4651 const DeviceInterface &vkd = *m_testEnvironment->vkd;
4652 const VkDevice device = m_testEnvironment->device;
4653 Allocator &allocator = *m_testEnvironment->allocator;
4654 const uint32_t width = testParams.width;
4655 const uint32_t height = testParams.height;
4656 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
4657 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
4658 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
4659 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
4660 makeTopLevelAccelerationStructure();
4661
4662 DE_ASSERT(instancesGroupCount == 1);
4663 DE_ASSERT(geometriesGroupCount == 1);
4664 DE_ASSERT(squaresGroupCount == width * height);
4665
4666 m_topAccelerationStructure =
4667 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
4668
4669 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
4670
4671 m_expected.resize(width * height);
4672
4673 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
4674 {
4675 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
4676 makeBottomLevelAccelerationStructure();
4677
4678 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
4679 {
4680 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4681 {
4682 std::vector<tcu::Vec3> geometryData;
4683
4684 const auto squareX = (squareNdx % width);
4685 const auto squareY = (squareNdx / width);
4686
4687 const float x0 = float(squareX + 0) / float(width);
4688 const float y0 = float(squareY + 0) / float(height);
4689 const float x1 = float(squareX + 1) / float(width);
4690 const float y1 = float(squareY + 1) / float(height);
4691
4692 if ((squareNdx % 2) == 0)
4693 {
4694 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4695 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
4696 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4697
4698 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4699 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
4700 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4701 }
4702 else
4703 {
4704 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4705 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
4706 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4707
4708 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
4709 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
4710 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4711 }
4712
4713 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, true /* triangles */);
4714 }
4715 }
4716
4717 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4718 m_bottomAccelerationStructures.push_back(
4719 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
4720 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
4721 instanceNdx + 1);
4722 }
4723
4724 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4725
4726 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4727 {
4728 m_expected.at(squareNdx) = squareNdx;
4729 }
4730
4731 return m_topAccelerationStructure.get()->getPtr();
4732 }
4733
getShaderBodyTextCandidate(const TestParams & testParams)4734 const std::string TestConfigurationGetIntersectionGeometryIndex::getShaderBodyTextCandidate(
4735 const TestParams &testParams)
4736 {
4737 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4738 {
4739 const std::string result = " uint rayFlags = 0;\n"
4740 " uint cullMask = 0xFF;\n"
4741 " float tmin = 0.0001;\n"
4742 " float tmax = 9.0;\n"
4743 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) "
4744 "+ 0.5f) / float(size.y), 0.2);\n"
4745 " vec3 direct = vec3(0, 0, "
4746 " -1.0);\n"
4747 " rayQueryEXT rayQuery;\n"
4748 "\n"
4749 " int result_i32 = 123456;\n"
4750 "\n"
4751 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, "
4752 "cullMask, origin, tmin, direct, tmax);\n"
4753 "\n"
4754 " while (rayQueryProceedEXT(rayQuery))\n"
4755 " {\n"
4756 " result_i32 = rayQueryGetIntersectionGeometryIndexEXT(rayQuery, false);\n"
4757 "\n"
4758 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4759 " }\n"
4760 "\n"
4761 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
4762
4763 return result;
4764 }
4765 else
4766 {
4767 TCU_THROW(InternalError, "Unknown geometry type");
4768 }
4769 }
4770
getShaderBodyTextCommitted(const TestParams & testParams)4771 const std::string TestConfigurationGetIntersectionGeometryIndex::getShaderBodyTextCommitted(
4772 const TestParams &testParams)
4773 {
4774 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4775 {
4776 const std::string result =
4777 " uint rayFlags = 0;\n"
4778 " uint cullMask = 0xFF;\n"
4779 " float tmin = 0.0001;\n"
4780 " float tmax = 9.0;\n"
4781 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4782 "float(size.y), 0.2);\n"
4783 " vec3 direct = vec3(0, 0, "
4784 " -1.0);\n"
4785 " rayQueryEXT rayQuery;\n"
4786 "\n"
4787 " bool intersection_found = false;\n"
4788 " int result_i32 = 0;\n"
4789 "\n"
4790 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
4791 "tmin, direct, tmax);\n"
4792 "\n"
4793 " while (rayQueryProceedEXT(rayQuery))\n"
4794 " {\n"
4795 " intersection_found = true;\n"
4796 "\n"
4797 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4798 " }\n"
4799 "\n"
4800 " result_i32 = (intersection_found) ? (rayQueryGetIntersectionGeometryIndexEXT(rayQuery, true) )\n"
4801 " : 2;\n"
4802 "\n"
4803 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
4804
4805 return result;
4806 }
4807 else
4808 {
4809 TCU_THROW(InternalError, "Unknown geometry type");
4810 }
4811 }
4812
4813 class TestConfigurationGetIntersectionBarycentrics : public TestConfigurationVector
4814 {
4815 public:
TestConfigurationGetIntersectionBarycentrics(Context & context)4816 TestConfigurationGetIntersectionBarycentrics(Context &context) : TestConfigurationVector(context, false)
4817 {
4818 /* Stub */
4819 }
4820
4821 static const std::string getShaderBodyTextCandidate(const TestParams &testParams);
4822 static const std::string getShaderBodyTextCommitted(const TestParams &testParams);
4823
4824 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
4825 VkCommandBuffer cmdBuffer) override;
4826 };
4827
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)4828 const VkAccelerationStructureKHR *TestConfigurationGetIntersectionBarycentrics::initAccelerationStructures(
4829 TestParams &testParams, VkCommandBuffer cmdBuffer)
4830 {
4831 const DeviceInterface &vkd = *m_testEnvironment->vkd;
4832 const VkDevice device = m_testEnvironment->device;
4833 Allocator &allocator = *m_testEnvironment->allocator;
4834 const uint32_t width = testParams.width;
4835 const uint32_t height = testParams.height;
4836 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
4837 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
4838 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
4839 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
4840 makeTopLevelAccelerationStructure();
4841
4842 DE_ASSERT(instancesGroupCount == 1);
4843 DE_ASSERT(geometriesGroupCount == 1);
4844 DE_ASSERT(squaresGroupCount == width * height);
4845
4846 m_topAccelerationStructure =
4847 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
4848
4849 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
4850
4851 m_expected.resize(width * height * 3);
4852
4853 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
4854 {
4855 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
4856 makeBottomLevelAccelerationStructure();
4857
4858 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
4859 {
4860 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
4861 {
4862 std::vector<tcu::Vec3> geometryData;
4863
4864 const auto squareX = (squareNdx % width);
4865 const auto squareY = (squareNdx / width);
4866
4867 const float x0 = float(squareX + 0) / float(width);
4868 const float y0 = float(squareY + 0) / float(height);
4869 const float x1 = float(squareX + 1) / float(width);
4870 const float y1 = float(squareY + 1) / float(height);
4871
4872 const float x05 = x0 + (x1 - x0) * 0.5f;
4873 const float y05 = y0 + (y1 - y0) * 0.5f;
4874
4875 geometryData.push_back(tcu::Vec3(x05, y0, 0.0));
4876 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
4877 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
4878
4879 /* With each cell, ray target moves from (x1, y1) to (x0.5, y0.5). This guarantees a hit and different barycentric coords
4880 * per each traced ray.
4881 */
4882 const float t = float(squareNdx) / float(squaresGroupCount - 1);
4883
4884 const float hitX = x0 + 0.125f / float(width) + (x1 - x05) * t;
4885 const float hitY = y1 - 0.125f / float(height) - (y1 - y05) * t;
4886
4887 const float barycentricX = ((0 + (x1 - x0) * (hitY - y1)) / (0 + (x1 - x0) * (y0 - y1)));
4888 const float barycentricY =
4889 (((y1 - y0) * (hitX - x1) + (x05 - x1) * (hitY - y1)) / (0 + (x1 - x0) * (y0 - y1)));
4890
4891 m_expected.at(squaresGroupCount * 0 + squareNdx) =
4892 static_cast<int32_t>(FIXED_POINT_DIVISOR * barycentricY);
4893 m_expected.at(squaresGroupCount * 1 + squareNdx) =
4894 static_cast<int32_t>(FIXED_POINT_DIVISOR * barycentricX);
4895 m_expected.at(squaresGroupCount * 2 + squareNdx) =
4896 static_cast<int32_t>(FIXED_POINT_DIVISOR * (1.0f - barycentricX - barycentricY));
4897
4898 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, true /* triangles */);
4899 }
4900 }
4901
4902 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4903 m_bottomAccelerationStructures.push_back(
4904 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
4905 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
4906 instanceNdx + 1);
4907 }
4908
4909 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
4910
4911 return m_topAccelerationStructure.get()->getPtr();
4912 }
4913
getShaderBodyTextCandidate(const TestParams & testParams)4914 const std::string TestConfigurationGetIntersectionBarycentrics::getShaderBodyTextCandidate(const TestParams &testParams)
4915 {
4916 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4917 {
4918 const std::string result =
4919 " uint rayFlags = 0;\n"
4920 " uint cullMask = 0xFF;\n"
4921 " float tmin = 0.0001;\n"
4922 " float tmax = 9.0;\n"
4923 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4924 "float(size.y), 0.2);\n"
4925 "\n"
4926 " int nSquare = pos.y * size.x + pos.x;\n"
4927 " float t = float(pos.y * size.x + pos.x) / float(size.x * size.y - 1);\n"
4928 " float x0 = float(pos.x) / float(size.x);\n"
4929 " float x1 = float(pos.x + 1) / float(size.x);\n"
4930 " float x05 = mix(x0, x1, 0.5);\n"
4931 " float y0 = float(pos.y) / float(size.y);\n"
4932 " float y1 = float(pos.y + 1) / float(size.y);\n"
4933 " float y05 = mix(y0, y1, 0.5);\n"
4934 " vec3 target = vec3(x0 + 0.125 / float(size.x) + (x1 - x05) * t,\n"
4935 " y1 - 0.125 / float(size.y) - (y1 - y05) * t,\n"
4936 " 0.0);\n"
4937 " vec3 direct = normalize(target - origin);\n"
4938 "\n"
4939 " rayQueryEXT rayQuery;\n"
4940 "\n"
4941 " vec2 result_fp32 = vec2(1234, 5678);\n"
4942 "\n"
4943 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
4944 "tmin, direct, tmax);\n"
4945 "\n"
4946 " while (rayQueryProceedEXT(rayQuery))\n"
4947 " {\n"
4948 " result_fp32 = rayQueryGetIntersectionBarycentricsEXT(rayQuery, false);\n"
4949 "\n"
4950 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
4951 " }\n"
4952 "\n"
4953 " imageStore(result, ivec3(pos.xy, 0), ivec4(result_fp32.x * " +
4954 de::toString(FIXED_POINT_DIVISOR) +
4955 ", 0, 0, 0));\n"
4956 " imageStore(result, ivec3(pos.xy, 1), ivec4(result_fp32.y * " +
4957 de::toString(FIXED_POINT_DIVISOR) +
4958 ", 0, 0, 0));\n"
4959 " imageStore(result, ivec3(pos.xy, 2), ivec4((1.0 - result_fp32.x - result_fp32.y) * " +
4960 de::toString(FIXED_POINT_DIVISOR) + ", 0, 0, 0));\n";
4961
4962 return result;
4963 }
4964 else
4965 {
4966 TCU_THROW(InternalError, "Unknown geometry type");
4967 }
4968 }
4969
getShaderBodyTextCommitted(const TestParams & testParams)4970 const std::string TestConfigurationGetIntersectionBarycentrics::getShaderBodyTextCommitted(const TestParams &testParams)
4971 {
4972 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
4973 {
4974 const std::string result =
4975 " uint rayFlags = 0;\n"
4976 " uint cullMask = 0xFF;\n"
4977 " float tmin = 0.0001;\n"
4978 " float tmax = 9.0;\n"
4979 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
4980 "float(size.y), 0.2);\n"
4981 "\n"
4982 " int nSquare = pos.y * size.x + pos.x;\n"
4983 " float t = float(pos.y * size.x + pos.x) / float(size.x * size.y - 1);\n"
4984 " float x0 = float(pos.x) / float(size.x);\n"
4985 " float x1 = float(pos.x + 1) / float(size.x);\n"
4986 " float x05 = mix(x0, x1, 0.5);\n"
4987 " float y0 = float(pos.y) / float(size.y);\n"
4988 " float y1 = float(pos.y + 1) / float(size.y);\n"
4989 " float y05 = mix(y0, y1, 0.5);\n"
4990 " vec3 target = vec3(x0 + 0.125 / float(size.x) + (x1 - x05) * t,\n"
4991 " y1 - 0.125 / float(size.y) - (y1 - y05) * t,\n"
4992 " 0.0);\n"
4993 " vec3 direct = normalize(target - origin);\n"
4994 "\n"
4995 " rayQueryEXT rayQuery;\n"
4996 "\n"
4997 " bool intersection_found = false;\n"
4998 " vec2 result_fp32 = vec2(1234, 5678);\n"
4999 "\n"
5000 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
5001 "tmin, direct, tmax);\n"
5002 "\n"
5003 " while (rayQueryProceedEXT(rayQuery))\n"
5004 " {\n"
5005 " intersection_found = true;\n"
5006 "\n"
5007 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
5008 " }\n"
5009 "\n"
5010 " if (intersection_found)\n"
5011 " {\n"
5012 " result_fp32 = rayQueryGetIntersectionBarycentricsEXT(rayQuery, true);\n"
5013 " }\n"
5014 "\n"
5015 " imageStore(result, ivec3(pos.xy, 0), ivec4(result_fp32.x * " +
5016 de::toString(FIXED_POINT_DIVISOR) +
5017 ", 0, 0, 0));\n"
5018 " imageStore(result, ivec3(pos.xy, 1), ivec4(result_fp32.y * " +
5019 de::toString(FIXED_POINT_DIVISOR) +
5020 ", 0, 0, 0));\n"
5021 " imageStore(result, ivec3(pos.xy, 2), ivec4((1.0 - result_fp32.x - result_fp32.y) * " +
5022 de::toString(FIXED_POINT_DIVISOR) + ", 0, 0, 0));\n";
5023
5024 return result;
5025 }
5026 else
5027 {
5028 TCU_THROW(InternalError, "Unknown geometry type");
5029 }
5030 }
5031
5032 /// <summary>
5033 class TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset : public TestConfiguration
5034 {
5035 public:
TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset(Context & context)5036 TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset(Context &context)
5037 : TestConfiguration(context)
5038 {
5039 }
5040 static const std::string getShaderBodyTextCandidate(const TestParams &testParams);
5041 static const std::string getShaderBodyTextCommitted(const TestParams &testParams);
5042
5043 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
5044 VkCommandBuffer cmdBuffer) override;
5045 };
5046
5047 const VkAccelerationStructureKHR *TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset::
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)5048 initAccelerationStructures(TestParams &testParams, VkCommandBuffer cmdBuffer)
5049 {
5050 const DeviceInterface &vkd = *m_testEnvironment->vkd;
5051 const VkDevice device = m_testEnvironment->device;
5052 Allocator &allocator = *m_testEnvironment->allocator;
5053 const uint32_t width = testParams.width;
5054 const uint32_t height = testParams.height;
5055 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
5056 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
5057 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
5058 uint32_t squareNdx = 0;
5059 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
5060 makeTopLevelAccelerationStructure();
5061
5062 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
5063
5064 m_topAccelerationStructure =
5065 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
5066
5067 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
5068
5069 m_expected.resize(width * height);
5070
5071 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
5072 {
5073 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
5074 {
5075 for (uint32_t groupNdx = 0; groupNdx < squaresGroupCount; ++groupNdx, ++squareNdx)
5076 {
5077 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
5078 makeBottomLevelAccelerationStructure();
5079 std::vector<tcu::Vec3> geometryData;
5080
5081 const auto squareX = (squareNdx % width);
5082 const auto squareY = (squareNdx / width);
5083
5084 const float x0 = float(squareX + 0) / float(width);
5085 const float y0 = float(squareY + 0) / float(height);
5086 const float x1 = float(squareX + 1) / float(width);
5087 const float y1 = float(squareY + 1) / float(height);
5088
5089 if ((squareNdx % 2) == 0)
5090 {
5091 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5092 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
5093 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5094
5095 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5096 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
5097 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5098 }
5099 else
5100 {
5101 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5102 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
5103 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5104
5105 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5106 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
5107 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5108 }
5109
5110 m_expected.at(squareNdx) = ((1 << 24) - 1) / static_cast<uint32_t>(m_expected.size()) * squareNdx;
5111
5112 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, true /* triangles */);
5113
5114 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5115 m_bottomAccelerationStructures.push_back(de::SharedPtr<BottomLevelAccelerationStructure>(
5116 rayQueryBottomLevelAccelerationStructure.release()));
5117
5118 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
5119 instanceNdx + 1, 255U, m_expected.at(squareNdx));
5120 }
5121 }
5122 }
5123
5124 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5125
5126 return m_topAccelerationStructure.get()->getPtr();
5127 }
5128
getShaderBodyTextCandidate(const TestParams & testParams)5129 const std::string TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset::getShaderBodyTextCandidate(
5130 const TestParams &testParams)
5131 {
5132 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
5133 {
5134 const std::string result =
5135 " uint rayFlags = 0;\n"
5136 " uint cullMask = 0xFF;\n"
5137 " float tmin = 0.0001;\n"
5138 " float tmax = 9.0;\n"
5139 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
5140 "float(size.y), 0.2);\n"
5141 " vec3 direct = vec3(0, 0, "
5142 " -1.0);\n"
5143 " rayQueryEXT rayQuery;\n"
5144 "\n"
5145 " int result_i32 = 2;\n"
5146 "\n"
5147 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
5148 "tmin, direct, tmax);\n"
5149 "\n"
5150 " while (rayQueryProceedEXT(rayQuery))\n"
5151 " {\n"
5152 " result_i32 = int(rayQueryGetIntersectionInstanceShaderBindingTableRecordOffsetEXT(rayQuery, false) "
5153 ");\n"
5154 "\n"
5155 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
5156 " }\n"
5157 "\n"
5158 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
5159
5160 return result;
5161 }
5162 else
5163 {
5164 TCU_THROW(InternalError, "Unknown geometry type");
5165 }
5166 }
5167
getShaderBodyTextCommitted(const TestParams & testParams)5168 const std::string TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset::getShaderBodyTextCommitted(
5169 const TestParams &testParams)
5170 {
5171 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
5172 {
5173 const std::string result =
5174 " uint rayFlags = 0;\n"
5175 " uint cullMask = 0xFF;\n"
5176 " float tmin = 0.0001;\n"
5177 " float tmax = 9.0;\n"
5178 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / "
5179 "float(size.y), 0.2);\n"
5180 " vec3 direct = vec3(0, 0, "
5181 " -1.0);\n"
5182 " rayQueryEXT rayQuery;\n"
5183 "\n"
5184 " bool intersection_found = false;\n"
5185 " int result_i32 = 0;\n"
5186 "\n"
5187 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, "
5188 "tmin, direct, tmax);\n"
5189 "\n"
5190 " while (rayQueryProceedEXT(rayQuery))\n"
5191 " {\n"
5192 " intersection_found = true;\n"
5193 "\n"
5194 " rayQueryConfirmIntersectionEXT(rayQuery);\n"
5195 " }\n"
5196 "\n"
5197 " result_i32 = (intersection_found) ? "
5198 "int(rayQueryGetIntersectionInstanceShaderBindingTableRecordOffsetEXT(rayQuery, true) )\n"
5199 " : 2;\n"
5200 "\n"
5201 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
5202
5203 return result;
5204 }
5205 else
5206 {
5207 TCU_THROW(InternalError, "Unknown geometry type");
5208 }
5209 }
5210 /// </summary>
5211
5212 class TestConfigurationRayQueryTerminate : public TestConfiguration
5213 {
5214 public:
TestConfigurationRayQueryTerminate(Context & context)5215 TestConfigurationRayQueryTerminate(Context &context) : TestConfiguration(context)
5216 {
5217 }
5218 static const std::string getShaderBodyText(const TestParams &testParams);
5219
5220 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
5221 VkCommandBuffer cmdBuffer) override;
5222
5223 private:
5224 static const uint32_t N_RAY_QUERIES_TO_USE;
5225 };
5226
5227 const uint32_t TestConfigurationRayQueryTerminate::N_RAY_QUERIES_TO_USE = 8;
5228
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)5229 const VkAccelerationStructureKHR *TestConfigurationRayQueryTerminate::initAccelerationStructures(
5230 TestParams &testParams, VkCommandBuffer cmdBuffer)
5231 {
5232 const DeviceInterface &vkd = *m_testEnvironment->vkd;
5233 const VkDevice device = m_testEnvironment->device;
5234 Allocator &allocator = *m_testEnvironment->allocator;
5235 const uint32_t width = testParams.width;
5236 const uint32_t height = testParams.height;
5237 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
5238 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
5239 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
5240 uint32_t squareNdx = 0;
5241 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
5242 makeTopLevelAccelerationStructure();
5243
5244 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
5245
5246 m_topAccelerationStructure =
5247 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
5248
5249 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
5250
5251 m_expected.resize(width * height);
5252
5253 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
5254 {
5255 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
5256 {
5257 for (uint32_t groupNdx = 0; groupNdx < squaresGroupCount; ++groupNdx, ++squareNdx)
5258 {
5259 std::vector<tcu::Vec3> geometryData;
5260 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
5261 makeBottomLevelAccelerationStructure();
5262
5263 for (int32_t z = -2; z <= 0; ++z)
5264 {
5265 const auto squareX = (squareNdx % width);
5266 const auto squareY = (squareNdx / width);
5267
5268 const float x0 = float(squareX + 0) / float(width);
5269 const float y0 = float(squareY + 0) / float(height);
5270 const float x1 = float(squareX + 1) / float(width);
5271 const float y1 = float(squareY + 1) / float(height);
5272
5273 if (testParams.geomType == GeomType::GEOM_TYPE_TRIANGLES)
5274 {
5275 if ((squareNdx % 2) == 0)
5276 {
5277 geometryData.push_back(tcu::Vec3(x0, y0, static_cast<float>(z)));
5278 geometryData.push_back(tcu::Vec3(x0, y1, static_cast<float>(z)));
5279 geometryData.push_back(tcu::Vec3(x1, y1, static_cast<float>(z)));
5280
5281 geometryData.push_back(tcu::Vec3(x1, y1, static_cast<float>(z)));
5282 geometryData.push_back(tcu::Vec3(x1, y0, static_cast<float>(z)));
5283 geometryData.push_back(tcu::Vec3(x0, y0, static_cast<float>(z)));
5284 }
5285 else
5286 {
5287 geometryData.push_back(tcu::Vec3(x1, y1, static_cast<float>(z)));
5288 geometryData.push_back(tcu::Vec3(x0, y1, static_cast<float>(z)));
5289 geometryData.push_back(tcu::Vec3(x0, y0, static_cast<float>(z)));
5290
5291 geometryData.push_back(tcu::Vec3(x0, y0, static_cast<float>(z)));
5292 geometryData.push_back(tcu::Vec3(x1, y0, static_cast<float>(z)));
5293 geometryData.push_back(tcu::Vec3(x1, y1, static_cast<float>(z)));
5294 }
5295 }
5296 else
5297 {
5298 geometryData.push_back(tcu::Vec3(x0, y0, static_cast<float>(z)));
5299 geometryData.push_back(tcu::Vec3(x1, y1, static_cast<float>(z)));
5300 }
5301 }
5302
5303 m_expected.at(squareNdx) = (1 << N_RAY_QUERIES_TO_USE) - 1;
5304
5305 rayQueryBottomLevelAccelerationStructure->addGeometry(
5306 geometryData, (testParams.geomType == GeomType::GEOM_TYPE_TRIANGLES),
5307 VK_GEOMETRY_NO_DUPLICATE_ANY_HIT_INVOCATION_BIT_KHR);
5308
5309 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5310 m_bottomAccelerationStructures.push_back(de::SharedPtr<BottomLevelAccelerationStructure>(
5311 rayQueryBottomLevelAccelerationStructure.release()));
5312
5313 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4,
5314 instanceNdx + 1, 255U, m_expected.at(squareNdx));
5315 }
5316 }
5317 }
5318
5319 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5320
5321 return m_topAccelerationStructure.get()->getPtr();
5322 }
5323
getShaderBodyText(const TestParams & testParams)5324 const std::string TestConfigurationRayQueryTerminate::getShaderBodyText(const TestParams &testParams)
5325 {
5326 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
5327 {
5328 std::string result =
5329 " const int nQueries = " + de::toString(N_RAY_QUERIES_TO_USE) +
5330 ";\n"
5331 " const int nPassingQuery = nQueries / 2;\n"
5332 "\n"
5333 " const uint rayFlags = 0;\n"
5334 " const uint cullMask = 0xFF;\n"
5335 " const float tmin = 0.0001;\n"
5336 " const float tmax = 9.0;\n"
5337 "\n"
5338 " rayQueryEXT rayQueries [nQueries];\n"
5339 " int nSuccessfulRayQueryProceedCalls[nQueries];\n"
5340 "\n"
5341 " int result_i32 = 0;\n"
5342 "\n"
5343 " for (int nQuery = nQueries - 1; nQuery >= 0; --nQuery)\n"
5344 " {\n"
5345 " vec3 origin = vec3((float(pos.x) + 0.4f) / float(size.x), (float(pos.y) + 0.5f) / float(size.y), "
5346 "0.2);\n"
5347 " vec3 direct = vec3(0, 0, "
5348 "-1.0);\n"
5349 "\n"
5350 " rayQueryInitializeEXT(rayQueries[nQuery], rayQueryTopLevelAccelerationStructure, rayFlags, "
5351 "cullMask, origin, tmin, direct, tmax);\n"
5352 "\n"
5353 " nSuccessfulRayQueryProceedCalls[nQuery] = 0;\n"
5354 " }\n"
5355 "\n"
5356 " while (true)\n"
5357 " {\n"
5358 " int nQueriesSuccessful = 0;\n"
5359 "\n"
5360 " for (int nQuery = 0; nQuery < nQueries; ++nQuery)\n"
5361 " {\n"
5362 " if (rayQueryProceedEXT(rayQueries[nQuery]) )\n"
5363 " {\n"
5364 " nSuccessfulRayQueryProceedCalls[nQuery] ++;\n"
5365 " nQueriesSuccessful ++;\n"
5366 "\n"
5367 " if (nQuery != nPassingQuery)\n"
5368 " {\n"
5369 " rayQueryTerminateEXT(rayQueries[nQuery]);\n"
5370 " }\n"
5371 " }\n"
5372 " }\n"
5373 "\n"
5374 " if (nQueriesSuccessful == 0)\n"
5375 " {\n"
5376 " break;\n"
5377 " }\n"
5378 " }\n"
5379 "\n"
5380 " for (int nQuery = 0; nQuery < nQueries; ++nQuery)\n"
5381 " {\n"
5382 " if (nPassingQuery != nQuery)\n"
5383 " {\n"
5384 " result_i32 |= (nSuccessfulRayQueryProceedCalls[nQuery] == 1) ? (1 << nQuery) : 0;\n"
5385 " }\n"
5386 " else\n"
5387 " {\n"
5388 " result_i32 |= (nSuccessfulRayQueryProceedCalls[nQuery] == 3) ? (1 << nQuery) : 0;\n"
5389 " }\n"
5390 " }\n"
5391 "\n"
5392 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
5393
5394 return result;
5395 }
5396 else
5397 {
5398 TCU_THROW(InternalError, "Unknown geometry type");
5399 }
5400 }
5401
5402 class TestConfigurationGetIntersectionType : public TestConfiguration
5403 {
5404 public:
TestConfigurationGetIntersectionType(Context & context)5405 TestConfigurationGetIntersectionType(Context &context) : TestConfiguration(context)
5406 {
5407 }
5408 static const std::string getShaderBodyTextCandidate(const TestParams &testParams);
5409 static const std::string getShaderBodyTextCommitted(const TestParams &testParams);
5410
5411 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
5412 VkCommandBuffer cmdBuffer) override;
5413 };
5414
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)5415 const VkAccelerationStructureKHR *TestConfigurationGetIntersectionType::initAccelerationStructures(
5416 TestParams &testParams, VkCommandBuffer cmdBuffer)
5417 {
5418 const DeviceInterface &vkd = *m_testEnvironment->vkd;
5419 const VkDevice device = m_testEnvironment->device;
5420 Allocator &allocator = *m_testEnvironment->allocator;
5421 const uint32_t width = testParams.width;
5422 const uint32_t height = testParams.height;
5423 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
5424 const uint32_t geometriesGroupCount = testParams.geometriesGroupCount;
5425 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
5426 uint32_t squareNdx = 0;
5427 de::MovePtr<TopLevelAccelerationStructure> rayQueryTopLevelAccelerationStructure =
5428 makeTopLevelAccelerationStructure();
5429
5430 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == width * height);
5431
5432 m_topAccelerationStructure =
5433 de::SharedPtr<TopLevelAccelerationStructure>(rayQueryTopLevelAccelerationStructure.release());
5434
5435 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
5436
5437 m_expected.resize(width * height);
5438
5439 for (uint32_t instanceNdx = 0; instanceNdx < instancesGroupCount; ++instanceNdx)
5440 {
5441 for (uint32_t geometryNdx = 0; geometryNdx < geometriesGroupCount; ++geometryNdx)
5442 {
5443 for (uint32_t groupNdx = 0; groupNdx < squaresGroupCount; ++groupNdx, ++squareNdx)
5444 {
5445 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
5446 makeBottomLevelAccelerationStructure();
5447 std::vector<tcu::Vec3> geometryData;
5448
5449 const auto squareX = (squareNdx % width);
5450 const auto squareY = (squareNdx / width);
5451
5452 const float x0 = float(squareX + 0) / float(width);
5453 const float y0 = float(squareY + 0) / float(height);
5454 const float x1 = float(squareX + 1) / float(width);
5455 const float y1 = float(squareY + 1) / float(height);
5456
5457 if ((squareNdx % 2) == 0)
5458 {
5459 if (testParams.geomType == GEOM_TYPE_TRIANGLES)
5460 {
5461 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5462 geometryData.push_back(tcu::Vec3(x0, y1, 0.0));
5463 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5464
5465 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5466 geometryData.push_back(tcu::Vec3(x1, y0, 0.0));
5467 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5468 }
5469 else
5470 {
5471 geometryData.push_back(tcu::Vec3(x0, y0, 0.0));
5472 geometryData.push_back(tcu::Vec3(x1, y1, 0.0));
5473 }
5474
5475 m_expected.at(squareNdx) = (testParams.testType == TEST_TYPE_GET_INTERSECTION_TYPE_CANDIDATE) ?
5476 (testParams.geomType == GEOM_TYPE_TRIANGLES) ?
5477 0 /* gl_RayQueryCandidateIntersectionTriangleEXT */
5478 :
5479 1 /* gl_RayQueryCandidateIntersectionAABBEXT */
5480 :
5481 (testParams.geomType == GEOM_TYPE_TRIANGLES) ?
5482 1 /* gl_RayQueryCommittedIntersectionTriangleEXT */
5483 :
5484 2; /* gl_RayQueryCommittedIntersectionGeneratedEXT */
5485
5486 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData,
5487 (testParams.geomType == GEOM_TYPE_TRIANGLES));
5488
5489 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5490 m_bottomAccelerationStructures.push_back(de::SharedPtr<BottomLevelAccelerationStructure>(
5491 rayQueryBottomLevelAccelerationStructure.release()));
5492
5493 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4);
5494 }
5495 else
5496 {
5497 m_expected.at(squareNdx) = (testParams.testType == TEST_TYPE_GET_INTERSECTION_TYPE_CANDIDATE) ?
5498 123 :
5499 0; /* gl_RayQueryCommittedIntersectionNoneEXT */
5500 }
5501 }
5502 }
5503 }
5504
5505 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5506
5507 return m_topAccelerationStructure.get()->getPtr();
5508 }
5509
getShaderBodyTextCandidate(const TestParams & testParams)5510 const std::string TestConfigurationGetIntersectionType::getShaderBodyTextCandidate(const TestParams &testParams)
5511 {
5512 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
5513 {
5514 std::string result = " uint rayFlags = 0;\n"
5515 " uint cullMask = 0xFF;\n"
5516 " float tmin = 0.0001;\n"
5517 " float tmax = 9.0;\n"
5518 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + "
5519 "0.5f) / float(size.y), 0.2);\n"
5520 " vec3 direct = vec3(0, 0, "
5521 " -1.0);\n"
5522 " rayQueryEXT rayQuery;\n"
5523 "\n"
5524 " int result_i32 = 123;\n"
5525 "\n"
5526 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, "
5527 "cullMask, origin, tmin, direct, tmax);\n"
5528 "\n"
5529 " while (rayQueryProceedEXT(rayQuery))\n"
5530 " {\n"
5531 " result_i32 = int(rayQueryGetIntersectionTypeEXT(rayQuery, false) );\n"
5532 "\n";
5533
5534 if (testParams.geomType == GEOM_TYPE_AABBS)
5535 {
5536 result += " rayQueryGenerateIntersectionEXT(rayQuery, 0.5f);\n";
5537 }
5538 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
5539 {
5540 result += " rayQueryConfirmIntersectionEXT(rayQuery);\n";
5541 }
5542
5543 result += " }\n"
5544 "\n"
5545 " imageStore(result, pos, ivec4(result_i32, 0, 0, 0));\n";
5546
5547 return result;
5548 }
5549 else
5550 {
5551 TCU_THROW(InternalError, "Unknown geometry type");
5552 }
5553 }
5554
getShaderBodyTextCommitted(const TestParams & testParams)5555 const std::string TestConfigurationGetIntersectionType::getShaderBodyTextCommitted(const TestParams &testParams)
5556 {
5557 if (testParams.geomType == GEOM_TYPE_AABBS || testParams.geomType == GEOM_TYPE_TRIANGLES)
5558 {
5559 std::string result = " uint rayFlags = 0;\n"
5560 " uint cullMask = 0xFF;\n"
5561 " float tmin = 0.0001;\n"
5562 " float tmax = 9.0;\n"
5563 " vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + "
5564 "0.5f) / float(size.y), 0.2);\n"
5565 " vec3 direct = vec3(0, 0, "
5566 " -1.0);\n"
5567 " rayQueryEXT rayQuery;\n"
5568 "\n"
5569 " uint result_i32 = 123u;\n"
5570 "\n"
5571 " rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, "
5572 "cullMask, origin, tmin, direct, tmax);\n"
5573 "\n"
5574 " while (rayQueryProceedEXT(rayQuery))\n"
5575 " {\n";
5576
5577 if (testParams.geomType == GEOM_TYPE_AABBS)
5578 {
5579 result += " rayQueryGenerateIntersectionEXT(rayQuery, 0.5f);\n";
5580 }
5581 else if (testParams.geomType == GEOM_TYPE_TRIANGLES)
5582 {
5583 result += " rayQueryConfirmIntersectionEXT(rayQuery);\n";
5584 }
5585
5586 result += " }\n"
5587 "\n"
5588 " result_i32 = rayQueryGetIntersectionTypeEXT(rayQuery, true);\n"
5589 "\n"
5590 " imageStore(result, pos, ivec4(int(result_i32), 0, 0, 0));\n";
5591
5592 return result;
5593 }
5594 else
5595 {
5596 TCU_THROW(InternalError, "Unknown geometry type");
5597 }
5598 }
5599
5600 class TestConfigurationUsingWrapperFunction : public TestConfiguration
5601 {
5602 public:
TestConfigurationUsingWrapperFunction(Context & context)5603 TestConfigurationUsingWrapperFunction(Context &context) : TestConfiguration(context)
5604 {
5605 }
5606 virtual const VkAccelerationStructureKHR *initAccelerationStructures(TestParams &testParams,
5607 VkCommandBuffer cmdBuffer) override;
5608
5609 static const std::string getShaderBodyText(const TestParams &testParams);
5610 };
5611
initAccelerationStructures(TestParams & testParams,VkCommandBuffer cmdBuffer)5612 const VkAccelerationStructureKHR *TestConfigurationUsingWrapperFunction::initAccelerationStructures(
5613 TestParams &testParams, VkCommandBuffer cmdBuffer)
5614 {
5615 const DeviceInterface &vkd = *m_testEnvironment->vkd;
5616 const VkDevice device = m_testEnvironment->device;
5617 Allocator &allocator = *m_testEnvironment->allocator;
5618 const uint32_t width = testParams.width;
5619 const uint32_t height = testParams.height;
5620 const uint32_t instancesGroupCount = testParams.instancesGroupCount;
5621 const uint32_t squaresGroupCount = testParams.squaresGroupCount;
5622 const bool usesTriangles = (testParams.geomType == GEOM_TYPE_TRIANGLES);
5623
5624 DE_ASSERT(instancesGroupCount == 1);
5625 DE_ASSERT(squaresGroupCount == width * height);
5626
5627 m_topAccelerationStructure =
5628 de::SharedPtr<TopLevelAccelerationStructure>(makeTopLevelAccelerationStructure().release());
5629 m_topAccelerationStructure->setInstanceCount(instancesGroupCount);
5630
5631 m_expected = std::vector<int32_t>(width * height, 1);
5632
5633 de::MovePtr<BottomLevelAccelerationStructure> rayQueryBottomLevelAccelerationStructure =
5634 makeBottomLevelAccelerationStructure();
5635
5636 for (uint32_t squareNdx = 0; squareNdx < squaresGroupCount; ++squareNdx)
5637 {
5638 std::vector<tcu::Vec3> geometryData;
5639
5640 const auto squareX = (squareNdx % width);
5641 const auto squareY = (squareNdx / width);
5642
5643 const float x0 = float(squareX + 0) / float(width);
5644 const float y0 = float(squareY + 0) / float(height);
5645 const float x1 = float(squareX + 1) / float(width);
5646 const float y1 = float(squareY + 1) / float(height);
5647
5648 if (usesTriangles)
5649 {
5650 geometryData.emplace_back(x0, y0, 0.0f);
5651 geometryData.emplace_back(x0, y1, 0.0f);
5652 geometryData.emplace_back(x1, y1, 0.0f);
5653
5654 geometryData.emplace_back(x1, y1, 0.0f);
5655 geometryData.emplace_back(x1, y0, 0.0f);
5656 geometryData.emplace_back(x0, y0, 0.0f);
5657 }
5658 else
5659 {
5660 geometryData.emplace_back(x0, y0, 0.0f);
5661 geometryData.emplace_back(x1, y1, 0.0f);
5662 }
5663
5664 rayQueryBottomLevelAccelerationStructure->addGeometry(geometryData, usesTriangles);
5665 }
5666
5667 rayQueryBottomLevelAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5668 m_bottomAccelerationStructures.push_back(
5669 de::SharedPtr<BottomLevelAccelerationStructure>(rayQueryBottomLevelAccelerationStructure.release()));
5670 m_topAccelerationStructure->addInstance(m_bottomAccelerationStructures.back(), identityMatrix3x4, 1);
5671 m_topAccelerationStructure->createAndBuild(vkd, device, cmdBuffer, allocator);
5672
5673 return m_topAccelerationStructure.get()->getPtr();
5674 }
5675
getShaderBodyText(const TestParams & testParams)5676 const std::string TestConfigurationUsingWrapperFunction::getShaderBodyText(const TestParams &testParams)
5677 {
5678 DE_UNREF(testParams);
5679 DE_ASSERT(testParams.isSPIRV);
5680
5681 // glslang is compiling rayQueryEXT function parameters to OpTypePointer Function to OpTypeRayQueryKHR
5682 // To test bare rayQueryEXT object passed as function parameter we need to use SPIR-V assembly.
5683 // In it, rayQueryWrapper has been modified to take a bare rayQueryEXT as the third argument, instead of a pointer.
5684 // The SPIR-V assembly shader below is based on the following GLSL code:
5685
5686 // int rayQueryWrapper(rayQueryEXT rq1, int value, rayQueryEXT rq2)
5687 // {
5688 // int result = value;
5689 // while (rayQueryProceedEXT(rq1))
5690 // {
5691 // result = 1;
5692 // rayQueryConfirmIntersectionEXT(rq2);
5693 // }
5694 // return result;
5695 // }
5696 // void main()
5697 // {
5698 // ivec3 pos = ivec3(gl_WorkGroupID);
5699 // ivec3 size = ivec3(gl_NumWorkGroups);
5700 // uint rayFlags = 0;
5701 // uint cullMask = 0xFF;
5702 // float tmin = 0.0001;
5703 // float tmax = 9.0;
5704 // vec3 origin = vec3((float(pos.x) + 0.5f) / float(size.x), (float(pos.y) + 0.5f) / float(size.y), 0.2);
5705 // vec3 direct = vec3(0.0, 0.0, -1.0);
5706 // rayQueryEXT rayQuery;
5707 // rayQueryInitializeEXT(rayQuery, rayQueryTopLevelAccelerationStructure, rayFlags, cullMask, origin, tmin, direct, tmax);
5708 // imageStore(result, pos, ivec4(rayQueryWrapper(rayQuery, 0, rayQuery), 0, 0, 0));
5709 // }
5710
5711 return "OpCapability Shader\n"
5712 "OpCapability RayQueryKHR\n"
5713 "OpExtension \"SPV_KHR_ray_query\"\n"
5714 "%1 = OpExtInstImport \"GLSL.std.450\"\n"
5715 "OpMemoryModel Logical GLSL450\n"
5716 "OpEntryPoint GLCompute %4 \"main\" %35 %39 %83 %93\n"
5717 "OpExecutionMode %4 LocalSize 1 1 1\n"
5718 "OpDecorate %35 BuiltIn WorkgroupId\n"
5719 "OpDecorate %39 BuiltIn NumWorkgroups\n"
5720 "OpDecorate %83 DescriptorSet 0\n"
5721 "OpDecorate %83 Binding 1\n"
5722 "OpDecorate %93 DescriptorSet 0\n"
5723 "OpDecorate %93 Binding 0\n"
5724
5725 // types and constants
5726 "%2 = OpTypeVoid\n"
5727 "%3 = OpTypeFunction %2\n"
5728 "%bare_query_type = OpTypeRayQueryKHR\n"
5729 "%pointer_to_query_type = OpTypePointer Function %bare_query_type\n"
5730 "%8 = OpTypeInt 32 1\n"
5731 "%9 = OpTypePointer Function %8\n"
5732
5733 // this function was modified to take also bare rayQueryEXT type
5734 "%ray_query_wrapper_fun = OpTypeFunction %8 %pointer_to_query_type %9 %bare_query_type\n"
5735
5736 "%23 = OpTypeBool\n"
5737 "%25 = OpConstant %8 1\n"
5738 "%29 = OpTypeVector %8 3\n"
5739 "%30 = OpTypePointer Function %29\n"
5740 "%32 = OpTypeInt 32 0\n"
5741 "%33 = OpTypeVector %32 3\n"
5742 "%34 = OpTypePointer Input %33\n"
5743 "%35 = OpVariable %34 Input\n"
5744 "%39 = OpVariable %34 Input\n"
5745 "%42 = OpTypePointer Function %32\n"
5746 "%44 = OpConstant %32 0\n"
5747 "%46 = OpConstant %32 255\n"
5748 "%47 = OpTypeFloat 32\n"
5749 "%48 = OpTypePointer Function %47\n"
5750 "%50 = OpConstant %47 9.99999975e-05\n"
5751 "%52 = OpConstant %47 9\n"
5752 "%53 = OpTypeVector %47 3\n"
5753 "%54 = OpTypePointer Function %53\n"
5754 "%59 = OpConstant %47 0.5\n"
5755 "%65 = OpConstant %32 1\n"
5756 "%74 = OpConstant %47 0.200000003\n"
5757 "%77 = OpConstant %47 0\n"
5758 "%78 = OpConstant %47 -1\n"
5759 "%79 = OpConstantComposite %53 %77 %77 %78\n"
5760 "%81 = OpTypeAccelerationStructureKHR\n"
5761 "%82 = OpTypePointer UniformConstant %81\n"
5762 "%83 = OpVariable %82 UniformConstant\n"
5763 "%91 = OpTypeImage %8 3D 0 0 0 2 R32i\n"
5764 "%92 = OpTypePointer UniformConstant %91\n"
5765 "%93 = OpVariable %92 UniformConstant\n"
5766 "%96 = OpConstant %8 0\n"
5767 "%99 = OpTypeVector %8 4\n"
5768
5769 // void main()
5770 "%4 = OpFunction %2 None %3\n"
5771 "%5 = OpLabel\n"
5772 "%31 = OpVariable %30 Function\n"
5773 "%38 = OpVariable %30 Function\n"
5774 "%43 = OpVariable %42 Function\n"
5775 "%45 = OpVariable %42 Function\n"
5776 "%49 = OpVariable %48 Function\n"
5777 "%51 = OpVariable %48 Function\n"
5778 "%55 = OpVariable %54 Function\n"
5779 "%76 = OpVariable %54 Function\n"
5780 "%var_ray_query_ptr = OpVariable %pointer_to_query_type Function\n"
5781 "%97 = OpVariable %9 Function\n"
5782 "%36 = OpLoad %33 %35\n"
5783 "%37 = OpBitcast %29 %36\n"
5784 "OpStore %31 %37\n"
5785 "%40 = OpLoad %33 %39\n"
5786 "%41 = OpBitcast %29 %40\n"
5787 "OpStore %38 %41\n"
5788 "OpStore %43 %44\n"
5789 "OpStore %45 %46\n"
5790 "OpStore %49 %50\n"
5791 "OpStore %51 %52\n"
5792 "%56 = OpAccessChain %9 %31 %44\n"
5793 "%57 = OpLoad %8 %56\n"
5794 "%58 = OpConvertSToF %47 %57\n"
5795 "%60 = OpFAdd %47 %58 %59\n"
5796 "%61 = OpAccessChain %9 %38 %44\n"
5797 "%62 = OpLoad %8 %61\n"
5798 "%63 = OpConvertSToF %47 %62\n"
5799 "%64 = OpFDiv %47 %60 %63\n"
5800 "%66 = OpAccessChain %9 %31 %65\n"
5801 "%67 = OpLoad %8 %66\n"
5802 "%68 = OpConvertSToF %47 %67\n"
5803 "%69 = OpFAdd %47 %68 %59\n"
5804 "%70 = OpAccessChain %9 %38 %65\n"
5805 "%71 = OpLoad %8 %70\n"
5806 "%72 = OpConvertSToF %47 %71\n"
5807 "%73 = OpFDiv %47 %69 %72\n"
5808 "%75 = OpCompositeConstruct %53 %64 %73 %74\n"
5809 "OpStore %55 %75\n"
5810 "OpStore %76 %79\n"
5811 "%84 = OpLoad %81 %83\n"
5812 "%85 = OpLoad %32 %43\n"
5813 "%86 = OpLoad %32 %45\n"
5814 "%87 = OpLoad %53 %55\n"
5815 "%88 = OpLoad %47 %49\n"
5816 "%89 = OpLoad %53 %76\n"
5817 "%90 = OpLoad %47 %51\n"
5818 "OpRayQueryInitializeKHR %var_ray_query_ptr %84 %85 %86 %87 %88 %89 %90\n"
5819 "%94 = OpLoad %91 %93\n"
5820 "%95 = OpLoad %29 %31\n"
5821 "OpStore %97 %96\n"
5822 "%var_ray_query_bare = OpLoad %bare_query_type %var_ray_query_ptr\n"
5823 "%98 = OpFunctionCall %8 %14 %var_ray_query_ptr %97 %var_ray_query_bare\n"
5824 "%100 = OpCompositeConstruct %99 %98 %96 %96 %96\n"
5825 "OpImageWrite %94 %95 %100 SignExtend\n"
5826 "OpReturn\n"
5827 "OpFunctionEnd\n"
5828
5829 // int rayQueryWrapper(rayQueryEXT rq1, int value, rayQueryEXT rq2)
5830 // where in SPIRV rq1 is pointer and rq2 is bare type
5831 "%14 = OpFunction %8 None %ray_query_wrapper_fun\n"
5832 "%11 = OpFunctionParameter %pointer_to_query_type\n"
5833 "%12 = OpFunctionParameter %9\n"
5834 "%13 = OpFunctionParameter %bare_query_type\n"
5835 "%15 = OpLabel\n"
5836 "%16 = OpVariable %9 Function\n"
5837 "%local_var_ray_query_ptr = OpVariable %pointer_to_query_type Function\n"
5838 "%17 = OpLoad %8 %12\n"
5839 "OpStore %16 %17\n"
5840 "OpBranch %18\n"
5841 "%18 = OpLabel\n"
5842 "OpLoopMerge %20 %21 None\n"
5843 "OpBranch %22\n"
5844 "%22 = OpLabel\n"
5845 "%24 = OpRayQueryProceedKHR %23 %11\n"
5846 "OpBranchConditional %24 %19 %20\n"
5847 "%19 = OpLabel\n"
5848 "OpStore %16 %25\n"
5849 "OpStore %local_var_ray_query_ptr %13\n"
5850 "OpRayQueryConfirmIntersectionKHR %local_var_ray_query_ptr\n"
5851 "OpBranch %21\n"
5852 "%21 = OpLabel\n"
5853 "OpBranch %18\n"
5854 "%20 = OpLabel\n"
5855 "%26 = OpLoad %8 %16\n"
5856 "OpReturnValue %26\n"
5857 "OpFunctionEnd\n";
5858 }
5859
5860 class RayQueryBuiltinTestInstance : public TestInstance
5861 {
5862 public:
5863 RayQueryBuiltinTestInstance(Context &context, const TestParams &data);
5864 virtual ~RayQueryBuiltinTestInstance(void);
5865 tcu::TestStatus iterate(void);
5866
5867 private:
5868 TestParams m_data;
5869 de::MovePtr<TestConfiguration> m_testConfig;
5870 de::MovePtr<PipelineConfiguration> m_pipelineConfig;
5871 };
5872
RayQueryBuiltinTestInstance(Context & context,const TestParams & data)5873 RayQueryBuiltinTestInstance::RayQueryBuiltinTestInstance(Context &context, const TestParams &data)
5874 : vkt::TestInstance(context)
5875 , m_data(data)
5876 {
5877 switch (m_data.testType)
5878 {
5879 case TEST_TYPE_FLOW:
5880 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationFlow(context));
5881 break;
5882 case TEST_TYPE_PRIMITIVE_ID:
5883 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationPrimitiveId(context));
5884 break;
5885 case TEST_TYPE_INSTANCE_ID:
5886 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationInstanceId(context));
5887 break;
5888 case TEST_TYPE_INSTANCE_CUSTOM_INDEX:
5889 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationInstanceCustomIndex(context));
5890 break;
5891 case TEST_TYPE_INTERSECTION_T_KHR:
5892 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationIntersectionT(context));
5893 break;
5894 case TEST_TYPE_OBJECT_RAY_ORIGIN_KHR:
5895 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationObjectRayOrigin(context));
5896 break;
5897 case TEST_TYPE_OBJECT_RAY_DIRECTION_KHR:
5898 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationObjectRayDirection(context));
5899 break;
5900 case TEST_TYPE_OBJECT_TO_WORLD_KHR:
5901 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationObjectToWorld(context));
5902 break;
5903 case TEST_TYPE_WORLD_TO_OBJECT_KHR:
5904 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationWorldToObject(context));
5905 break;
5906 case TEST_TYPE_NULL_ACCELERATION_STRUCTURE:
5907 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationNullASStruct(context));
5908 break;
5909 case TEST_TYPE_USING_WRAPPER_FUNCTION:
5910 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationUsingWrapperFunction(context));
5911 break;
5912 case TEST_TYPE_GET_RAY_TMIN:
5913 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetRayTMin(context));
5914 break;
5915 case TEST_TYPE_GET_WORLD_RAY_ORIGIN:
5916 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetWorldRayOrigin(context));
5917 break;
5918 case TEST_TYPE_GET_WORLD_RAY_DIRECTION:
5919 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetWorldRayDirection(context));
5920 break;
5921 case TEST_TYPE_GET_INTERSECTION_CANDIDATE_AABB_OPAQUE:
5922 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionCandidateAABBOpaque(context));
5923 break;
5924 case TEST_TYPE_GET_INTERSECTION_FRONT_FACE_CANDIDATE:
5925 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionFrontFace(context));
5926 break;
5927 case TEST_TYPE_GET_INTERSECTION_FRONT_FACE_COMMITTED:
5928 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionFrontFace(context));
5929 break;
5930 case TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_CANDIDATE:
5931 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionGeometryIndex(context));
5932 break;
5933 case TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_COMMITTED:
5934 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionGeometryIndex(context));
5935 break;
5936 case TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE:
5937 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionBarycentrics(context));
5938 break;
5939 case TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED:
5940 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionBarycentrics(context));
5941 break;
5942 case TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_CANDIDATE:
5943 m_testConfig = de::MovePtr<TestConfiguration>(
5944 new TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset(context));
5945 break;
5946 case TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_COMMITTED:
5947 m_testConfig = de::MovePtr<TestConfiguration>(
5948 new TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset(context));
5949 break;
5950 case TEST_TYPE_RAY_QUERY_TERMINATE:
5951 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationRayQueryTerminate(context));
5952 break;
5953 case TEST_TYPE_GET_INTERSECTION_TYPE_CANDIDATE:
5954 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionType(context));
5955 break;
5956 case TEST_TYPE_GET_INTERSECTION_TYPE_COMMITTED:
5957 m_testConfig = de::MovePtr<TestConfiguration>(new TestConfigurationGetIntersectionType(context));
5958 break;
5959
5960 default:
5961 TCU_THROW(InternalError, "Unknown test type");
5962 }
5963
5964 switch (m_data.stage)
5965 {
5966 case VK_SHADER_STAGE_VERTEX_BIT:
5967 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
5968 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
5969 case VK_SHADER_STAGE_GEOMETRY_BIT:
5970 case VK_SHADER_STAGE_FRAGMENT_BIT:
5971 {
5972 m_pipelineConfig = de::MovePtr<PipelineConfiguration>(new GraphicsConfiguration());
5973 break;
5974 }
5975
5976 case VK_SHADER_STAGE_COMPUTE_BIT:
5977 {
5978 m_pipelineConfig = de::MovePtr<PipelineConfiguration>(new ComputeConfiguration());
5979 break;
5980 }
5981
5982 case VK_SHADER_STAGE_RAYGEN_BIT_KHR:
5983 case VK_SHADER_STAGE_ANY_HIT_BIT_KHR:
5984 case VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR:
5985 case VK_SHADER_STAGE_MISS_BIT_KHR:
5986 case VK_SHADER_STAGE_INTERSECTION_BIT_KHR:
5987 case VK_SHADER_STAGE_CALLABLE_BIT_KHR:
5988 {
5989 m_pipelineConfig = de::MovePtr<PipelineConfiguration>(new RayTracingConfiguration());
5990 break;
5991 }
5992
5993 default:
5994 TCU_THROW(InternalError, "Unknown shader stage");
5995 }
5996 }
5997
~RayQueryBuiltinTestInstance(void)5998 RayQueryBuiltinTestInstance::~RayQueryBuiltinTestInstance(void)
5999 {
6000 }
6001
iterate(void)6002 tcu::TestStatus RayQueryBuiltinTestInstance::iterate(void)
6003 {
6004 const TestEnvironment &testEnv = m_testConfig->getTestEnvironment();
6005 const DeviceInterface &vkd = *testEnv.vkd;
6006 const VkDevice device = testEnv.device;
6007 const VkQueue queue = testEnv.queue;
6008 Allocator &allocator = *testEnv.allocator;
6009 const uint32_t queueFamilyIndex = testEnv.queueFamilyIndex;
6010
6011 const uint32_t width = m_data.width;
6012 const uint32_t height = m_data.height;
6013 const uint32_t depth = m_data.depth;
6014 const VkImageCreateInfo imageCreateInfo = makeImageCreateInfo(m_data.format, width, height, depth);
6015 const VkImageSubresourceRange imageSubresourceRange =
6016 makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u);
6017 const de::MovePtr<ImageWithMemory> image = de::MovePtr<ImageWithMemory>(
6018 new ImageWithMemory(vkd, device, allocator, imageCreateInfo, MemoryRequirement::Any));
6019 const Move<VkImageView> imageView =
6020 makeImageView(vkd, device, **image, VK_IMAGE_VIEW_TYPE_3D, m_data.format, imageSubresourceRange);
6021
6022 const uint32_t pixelSize = mapVkFormat(m_data.format).getPixelSize();
6023 const VkBufferCreateInfo resultBufferCreateInfo =
6024 makeBufferCreateInfo(width * height * depth * pixelSize, VK_BUFFER_USAGE_TRANSFER_DST_BIT);
6025 const VkImageSubresourceLayers resultBufferImageSubresourceLayers =
6026 makeImageSubresourceLayers(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 0u, 1u);
6027 const VkBufferImageCopy resultBufferImageRegion =
6028 makeBufferImageCopy(makeExtent3D(width, height, depth), resultBufferImageSubresourceLayers);
6029 de::MovePtr<BufferWithMemory> resultBuffer = de::MovePtr<BufferWithMemory>(
6030 new BufferWithMemory(vkd, device, allocator, resultBufferCreateInfo, MemoryRequirement::HostVisible));
6031
6032 const VkDescriptorImageInfo resultImageInfo = makeDescriptorImageInfo(DE_NULL, *imageView, VK_IMAGE_LAYOUT_GENERAL);
6033
6034 const Move<VkCommandPool> cmdPool = createCommandPool(vkd, device, 0, queueFamilyIndex);
6035 const Move<VkCommandBuffer> cmdBuffer =
6036 allocateCommandBuffer(vkd, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
6037 const VkAccelerationStructureKHR *topAccelerationStructurePtr = DE_NULL;
6038
6039 m_pipelineConfig->initConfiguration(testEnv, m_data);
6040
6041 beginCommandBuffer(vkd, *cmdBuffer, 0u);
6042 {
6043 const VkImageMemoryBarrier preImageBarrier =
6044 makeImageMemoryBarrier(0u, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_UNDEFINED,
6045 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, **image, imageSubresourceRange);
6046 const VkClearValue clearValue = makeClearValueColorU32(0u, 0u, 0u, 0u);
6047 const VkImageMemoryBarrier postImageBarrier = makeImageMemoryBarrier(
6048 VK_ACCESS_TRANSFER_WRITE_BIT,
6049 VK_ACCESS_ACCELERATION_STRUCTURE_READ_BIT_KHR | VK_ACCESS_ACCELERATION_STRUCTURE_WRITE_BIT_KHR,
6050 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, VK_IMAGE_LAYOUT_GENERAL, **image, imageSubresourceRange);
6051 const VkMemoryBarrier postTestMemoryBarrier =
6052 makeMemoryBarrier(VK_ACCESS_SHADER_READ_BIT | VK_ACCESS_SHADER_WRITE_BIT, VK_ACCESS_TRANSFER_READ_BIT);
6053 const VkMemoryBarrier postCopyMemoryBarrier =
6054 makeMemoryBarrier(VK_ACCESS_TRANSFER_WRITE_BIT, VK_ACCESS_HOST_READ_BIT);
6055
6056 cmdPipelineImageMemoryBarrier(vkd, *cmdBuffer, VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT,
6057 VK_PIPELINE_STAGE_TRANSFER_BIT, &preImageBarrier);
6058 vkd.cmdClearColorImage(*cmdBuffer, **image, VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearValue.color, 1,
6059 &imageSubresourceRange);
6060 cmdPipelineImageMemoryBarrier(vkd, *cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT,
6061 VK_PIPELINE_STAGE_ACCELERATION_STRUCTURE_BUILD_BIT_KHR, &postImageBarrier);
6062
6063 topAccelerationStructurePtr = m_testConfig->initAccelerationStructures(m_data, *cmdBuffer);
6064
6065 m_pipelineConfig->fillCommandBuffer(testEnv, m_data, *cmdBuffer, topAccelerationStructurePtr, resultImageInfo);
6066
6067 cmdPipelineMemoryBarrier(vkd, *cmdBuffer, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT,
6068 &postTestMemoryBarrier);
6069
6070 vkd.cmdCopyImageToBuffer(*cmdBuffer, **image, VK_IMAGE_LAYOUT_GENERAL, **resultBuffer, 1u,
6071 &resultBufferImageRegion);
6072
6073 cmdPipelineMemoryBarrier(vkd, *cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_HOST_BIT,
6074 &postCopyMemoryBarrier);
6075 }
6076 endCommandBuffer(vkd, *cmdBuffer);
6077
6078 submitCommandsAndWait(vkd, device, queue, cmdBuffer.get());
6079
6080 invalidateMappedMemoryRange(vkd, device, resultBuffer->getAllocation().getMemory(),
6081 resultBuffer->getAllocation().getOffset(), VK_WHOLE_SIZE);
6082
6083 if (m_testConfig->verify(resultBuffer.get(), m_data))
6084 return tcu::TestStatus::pass("Pass");
6085 else
6086 return tcu::TestStatus::fail("Fail");
6087 }
6088
6089 class RayQueryBuiltinTestCase : public TestCase
6090 {
6091 public:
6092 RayQueryBuiltinTestCase(tcu::TestContext &context, const char *name, const TestParams data);
6093 ~RayQueryBuiltinTestCase(void);
6094
6095 virtual void checkSupport(Context &context) const;
6096 virtual void initPrograms(SourceCollections &programCollection) const;
6097 virtual TestInstance *createInstance(Context &context) const;
6098
6099 private:
6100 TestParams m_data;
6101 };
6102
RayQueryBuiltinTestCase(tcu::TestContext & context,const char * name,const TestParams data)6103 RayQueryBuiltinTestCase::RayQueryBuiltinTestCase(tcu::TestContext &context, const char *name, const TestParams data)
6104 : vkt::TestCase(context, name)
6105 , m_data(data)
6106 {
6107 }
6108
~RayQueryBuiltinTestCase(void)6109 RayQueryBuiltinTestCase::~RayQueryBuiltinTestCase(void)
6110 {
6111 }
6112
checkSupport(Context & context) const6113 void RayQueryBuiltinTestCase::checkSupport(Context &context) const
6114 {
6115 context.requireDeviceFunctionality("VK_KHR_acceleration_structure");
6116 context.requireDeviceFunctionality("VK_KHR_ray_query");
6117
6118 const VkPhysicalDeviceRayQueryFeaturesKHR &rayQueryFeaturesKHR = context.getRayQueryFeatures();
6119 if (rayQueryFeaturesKHR.rayQuery == false)
6120 TCU_THROW(NotSupportedError, "Requires VkPhysicalDeviceRayQueryFeaturesKHR.rayQuery");
6121
6122 const VkPhysicalDeviceAccelerationStructureFeaturesKHR &accelerationStructureFeaturesKHR =
6123 context.getAccelerationStructureFeatures();
6124 if (accelerationStructureFeaturesKHR.accelerationStructure == false)
6125 TCU_THROW(TestError,
6126 "VK_KHR_ray_query requires VkPhysicalDeviceAccelerationStructureFeaturesKHR.accelerationStructure");
6127
6128 m_data.pipelineCheckSupport(context, m_data);
6129
6130 if (m_data.testConfigCheckSupport != DE_NULL)
6131 m_data.testConfigCheckSupport(context, m_data);
6132 }
6133
createInstance(Context & context) const6134 TestInstance *RayQueryBuiltinTestCase::createInstance(Context &context) const
6135 {
6136 return new RayQueryBuiltinTestInstance(context, m_data);
6137 }
6138
initPrograms(SourceCollections & programCollection) const6139 void RayQueryBuiltinTestCase::initPrograms(SourceCollections &programCollection) const
6140 {
6141 m_data.pipelineInitPrograms(programCollection, m_data);
6142 }
6143
getPipelineCheckSupport(const VkShaderStageFlagBits stage)6144 static inline CheckSupportFunc getPipelineCheckSupport(const VkShaderStageFlagBits stage)
6145 {
6146 switch (stage)
6147 {
6148 case VK_SHADER_STAGE_VERTEX_BIT:
6149 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
6150 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
6151 case VK_SHADER_STAGE_GEOMETRY_BIT:
6152 case VK_SHADER_STAGE_FRAGMENT_BIT:
6153 return GraphicsConfiguration::checkSupport;
6154
6155 case VK_SHADER_STAGE_COMPUTE_BIT:
6156 return ComputeConfiguration::checkSupport;
6157
6158 case VK_SHADER_STAGE_RAYGEN_BIT_KHR:
6159 case VK_SHADER_STAGE_ANY_HIT_BIT_KHR:
6160 case VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR:
6161 case VK_SHADER_STAGE_MISS_BIT_KHR:
6162 case VK_SHADER_STAGE_INTERSECTION_BIT_KHR:
6163 case VK_SHADER_STAGE_CALLABLE_BIT_KHR:
6164 return RayTracingConfiguration::checkSupport;
6165
6166 default:
6167 TCU_THROW(InternalError, "Unknown shader stage");
6168 }
6169 }
6170
getPipelineInitPrograms(const VkShaderStageFlagBits stage)6171 static inline InitProgramsFunc getPipelineInitPrograms(const VkShaderStageFlagBits stage)
6172 {
6173 switch (stage)
6174 {
6175 case VK_SHADER_STAGE_VERTEX_BIT:
6176 case VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT:
6177 case VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT:
6178 case VK_SHADER_STAGE_GEOMETRY_BIT:
6179 case VK_SHADER_STAGE_FRAGMENT_BIT:
6180 return GraphicsConfiguration::initPrograms;
6181
6182 case VK_SHADER_STAGE_COMPUTE_BIT:
6183 return ComputeConfiguration::initPrograms;
6184
6185 case VK_SHADER_STAGE_RAYGEN_BIT_KHR:
6186 case VK_SHADER_STAGE_ANY_HIT_BIT_KHR:
6187 case VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR:
6188 case VK_SHADER_STAGE_MISS_BIT_KHR:
6189 case VK_SHADER_STAGE_INTERSECTION_BIT_KHR:
6190 case VK_SHADER_STAGE_CALLABLE_BIT_KHR:
6191 return RayTracingConfiguration::initPrograms;
6192
6193 default:
6194 TCU_THROW(InternalError, "Unknown shader stage");
6195 }
6196 }
6197
getShaderBodyTextFunc(const TestType testType)6198 static inline ShaderBodyTextFunc getShaderBodyTextFunc(const TestType testType)
6199 {
6200 switch (testType)
6201 {
6202 case TEST_TYPE_FLOW:
6203 return TestConfigurationFlow::getShaderBodyText;
6204 case TEST_TYPE_PRIMITIVE_ID:
6205 return TestConfigurationPrimitiveId::getShaderBodyText;
6206 case TEST_TYPE_INSTANCE_ID:
6207 return TestConfigurationInstanceId::getShaderBodyText;
6208 case TEST_TYPE_INSTANCE_CUSTOM_INDEX:
6209 return TestConfigurationInstanceCustomIndex::getShaderBodyText;
6210 case TEST_TYPE_INTERSECTION_T_KHR:
6211 return TestConfigurationIntersectionT::getShaderBodyText;
6212 case TEST_TYPE_OBJECT_RAY_ORIGIN_KHR:
6213 return TestConfigurationObjectRayOrigin::getShaderBodyText;
6214 case TEST_TYPE_OBJECT_RAY_DIRECTION_KHR:
6215 return TestConfigurationObjectRayDirection::getShaderBodyText;
6216 case TEST_TYPE_OBJECT_TO_WORLD_KHR:
6217 return TestConfigurationObjectToWorld::getShaderBodyText;
6218 case TEST_TYPE_WORLD_TO_OBJECT_KHR:
6219 return TestConfigurationWorldToObject::getShaderBodyText;
6220 case TEST_TYPE_NULL_ACCELERATION_STRUCTURE:
6221 return TestConfigurationNullASStruct::getShaderBodyText;
6222 case TEST_TYPE_USING_WRAPPER_FUNCTION:
6223 return TestConfigurationUsingWrapperFunction::getShaderBodyText;
6224 case TEST_TYPE_GET_RAY_TMIN:
6225 return TestConfigurationGetRayTMin::getShaderBodyText;
6226 case TEST_TYPE_GET_WORLD_RAY_ORIGIN:
6227 return TestConfigurationGetWorldRayOrigin::getShaderBodyText;
6228 case TEST_TYPE_GET_WORLD_RAY_DIRECTION:
6229 return TestConfigurationGetWorldRayDirection::getShaderBodyText;
6230 ;
6231 case TEST_TYPE_GET_INTERSECTION_CANDIDATE_AABB_OPAQUE:
6232 return TestConfigurationGetIntersectionCandidateAABBOpaque::getShaderBodyText;
6233 case TEST_TYPE_GET_INTERSECTION_FRONT_FACE_CANDIDATE:
6234 return TestConfigurationGetIntersectionFrontFace::getShaderBodyTextCandidate;
6235 case TEST_TYPE_GET_INTERSECTION_FRONT_FACE_COMMITTED:
6236 return TestConfigurationGetIntersectionFrontFace::getShaderBodyTextCommitted;
6237 case TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_CANDIDATE:
6238 return TestConfigurationGetIntersectionGeometryIndex::getShaderBodyTextCandidate;
6239 case TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_COMMITTED:
6240 return TestConfigurationGetIntersectionGeometryIndex::getShaderBodyTextCommitted;
6241 case TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE:
6242 return TestConfigurationGetIntersectionBarycentrics::getShaderBodyTextCandidate;
6243 case TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED:
6244 return TestConfigurationGetIntersectionBarycentrics::getShaderBodyTextCommitted;
6245 case TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_CANDIDATE:
6246 return TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset::getShaderBodyTextCandidate;
6247 case TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_COMMITTED:
6248 return TestConfigurationGetIntersectionInstanceShaderBindingTableRecordOffset::getShaderBodyTextCommitted;
6249 case TEST_TYPE_RAY_QUERY_TERMINATE:
6250 return TestConfigurationRayQueryTerminate::getShaderBodyText;
6251 case TEST_TYPE_GET_INTERSECTION_TYPE_CANDIDATE:
6252 return TestConfigurationGetIntersectionType::getShaderBodyTextCandidate;
6253 case TEST_TYPE_GET_INTERSECTION_TYPE_COMMITTED:
6254 return TestConfigurationGetIntersectionType::getShaderBodyTextCommitted;
6255
6256 default:
6257 TCU_THROW(InternalError, "Unknown test type");
6258 }
6259 }
6260
getTestConfigCheckSupport(const TestType testType)6261 static inline CheckSupportFunc getTestConfigCheckSupport(const TestType testType)
6262 {
6263 if (testType >= TEST_TYPE_LAST)
6264 TCU_THROW(InternalError, "Unknown test type");
6265
6266 switch (testType)
6267 {
6268 case TEST_TYPE_NULL_ACCELERATION_STRUCTURE:
6269 return TestConfigurationNullASStruct::checkSupport;
6270 default:
6271 return DE_NULL;
6272 }
6273 }
6274
6275 } // namespace
6276
6277 const struct PipelineStages
6278 {
6279 VkShaderStageFlagBits stage;
6280 const char *name;
6281 } pipelineStages[] = {
6282 {VK_SHADER_STAGE_VERTEX_BIT, "vert"},
6283 {VK_SHADER_STAGE_TESSELLATION_CONTROL_BIT, "tesc"},
6284 {VK_SHADER_STAGE_TESSELLATION_EVALUATION_BIT, "tese"},
6285 {VK_SHADER_STAGE_GEOMETRY_BIT, "geom"},
6286 {VK_SHADER_STAGE_FRAGMENT_BIT, "frag"},
6287 {VK_SHADER_STAGE_COMPUTE_BIT, "comp"},
6288 {VK_SHADER_STAGE_RAYGEN_BIT_KHR, "rgen"},
6289 {VK_SHADER_STAGE_ANY_HIT_BIT_KHR, "ahit"},
6290 {VK_SHADER_STAGE_CLOSEST_HIT_BIT_KHR, "chit"},
6291 {VK_SHADER_STAGE_MISS_BIT_KHR, "miss"},
6292 {VK_SHADER_STAGE_INTERSECTION_BIT_KHR, "sect"},
6293 {VK_SHADER_STAGE_CALLABLE_BIT_KHR, "call"},
6294 };
6295
6296 const struct GeomTypes
6297 {
6298 GeomType geomType;
6299 const char *name;
6300 } geomTypes[] = {
6301 {GEOM_TYPE_TRIANGLES, "triangles"},
6302 {GEOM_TYPE_AABBS, "aabbs"},
6303 };
6304
createBuiltinTests(tcu::TestContext & testCtx)6305 tcu::TestCaseGroup *createBuiltinTests(tcu::TestContext &testCtx)
6306 {
6307 // Tests verifying builtins provided by ray query
6308 de::MovePtr<tcu::TestCaseGroup> group(new tcu::TestCaseGroup(testCtx, "builtin"));
6309
6310 const struct TestTypes
6311 {
6312 TestType testType;
6313 const char *name;
6314 } testTypes[] = {
6315 {TEST_TYPE_FLOW, "flow"},
6316 {TEST_TYPE_PRIMITIVE_ID, "primitiveid"},
6317 {TEST_TYPE_INSTANCE_ID, "instanceid"},
6318 {TEST_TYPE_INSTANCE_CUSTOM_INDEX, "instancecustomindex"},
6319 {TEST_TYPE_INTERSECTION_T_KHR, "intersectiont"},
6320 {TEST_TYPE_OBJECT_RAY_ORIGIN_KHR, "objectrayorigin"},
6321 {TEST_TYPE_OBJECT_RAY_DIRECTION_KHR, "objectraydirection"},
6322 {TEST_TYPE_OBJECT_TO_WORLD_KHR, "objecttoworld"},
6323 {TEST_TYPE_WORLD_TO_OBJECT_KHR, "worldtoobject"},
6324 {TEST_TYPE_GET_RAY_TMIN, "getraytmin"},
6325 {TEST_TYPE_GET_WORLD_RAY_ORIGIN, "getworldrayorigin"},
6326 {TEST_TYPE_GET_WORLD_RAY_DIRECTION, "getworldraydirection"},
6327 {TEST_TYPE_GET_INTERSECTION_CANDIDATE_AABB_OPAQUE, "getintersectioncandidateaabbopaque"},
6328 {TEST_TYPE_GET_INTERSECTION_FRONT_FACE_CANDIDATE, "getintersectionfrontfaceCandidate"},
6329 {TEST_TYPE_GET_INTERSECTION_FRONT_FACE_COMMITTED, "getintersectionfrontfaceCommitted"},
6330 {TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_CANDIDATE, "getintersectiongeometryindexCandidate"},
6331 {TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_COMMITTED, "getintersectiongeometryindexCommitted"},
6332 {TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE, "getintersectionbarycentricsCandidate"},
6333 {TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED, "getintersectionbarycentricsCommitted"},
6334 {TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_CANDIDATE,
6335 "getintersectioninstanceshaderbindingtablerecordoffsetCandidate"},
6336 {TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_COMMITTED,
6337 "getintersectioninstanceshaderbindingtablerecordoffsetCommitted"},
6338 {TEST_TYPE_RAY_QUERY_TERMINATE, "rayqueryterminate"},
6339 {TEST_TYPE_GET_INTERSECTION_TYPE_CANDIDATE, "getintersectiontypeCandidate"},
6340 {TEST_TYPE_GET_INTERSECTION_TYPE_COMMITTED, "getintersectiontypeCommitted"},
6341
6342 };
6343
6344 for (size_t testTypeNdx = 0; testTypeNdx < DE_LENGTH_OF_ARRAY(testTypes); ++testTypeNdx)
6345 {
6346 de::MovePtr<tcu::TestCaseGroup> testTypeGroup(
6347 new tcu::TestCaseGroup(group->getTestContext(), testTypes[testTypeNdx].name));
6348 const TestType testType = testTypes[testTypeNdx].testType;
6349 const ShaderBodyTextFunc testConfigShaderBodyTextFunc = getShaderBodyTextFunc(testType);
6350 const bool fixedPointVectorOutput =
6351 testType == TEST_TYPE_OBJECT_RAY_ORIGIN_KHR || testType == TEST_TYPE_OBJECT_RAY_DIRECTION_KHR ||
6352 testType == TEST_TYPE_GET_WORLD_RAY_ORIGIN || testType == TEST_TYPE_GET_WORLD_RAY_DIRECTION ||
6353 testType == TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE ||
6354 testType == TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED ||
6355 testType == TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_CANDIDATE ||
6356 testType == TEST_TYPE_GET_INTERSECTION_INSTANCE_SHADER_BINDING_TABLE_RECORD_OFFSET_COMMITTED;
6357 const bool fixedPointMatrixOutput =
6358 testType == TEST_TYPE_OBJECT_TO_WORLD_KHR || testType == TEST_TYPE_WORLD_TO_OBJECT_KHR;
6359 const bool single =
6360 testTypeNdx == TEST_TYPE_FLOW || testType == TEST_TYPE_OBJECT_RAY_ORIGIN_KHR ||
6361 testType == TEST_TYPE_OBJECT_RAY_DIRECTION_KHR || testType == TEST_TYPE_OBJECT_TO_WORLD_KHR ||
6362 testType == TEST_TYPE_WORLD_TO_OBJECT_KHR || testType == TEST_TYPE_GET_RAY_TMIN ||
6363 testType == TEST_TYPE_GET_WORLD_RAY_ORIGIN || testType == TEST_TYPE_GET_WORLD_RAY_DIRECTION ||
6364 testType == TEST_TYPE_GET_INTERSECTION_CANDIDATE_AABB_OPAQUE ||
6365 testType == TEST_TYPE_GET_INTERSECTION_FRONT_FACE_CANDIDATE ||
6366 testType == TEST_TYPE_GET_INTERSECTION_FRONT_FACE_COMMITTED ||
6367 testType == TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_CANDIDATE ||
6368 testType == TEST_TYPE_GET_INTERSECTION_GEOMETRY_INDEX_COMMITTED ||
6369 testType == TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE ||
6370 testType == TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED || testType == TEST_TYPE_RAY_QUERY_TERMINATE;
6371 const uint32_t imageDepth = fixedPointMatrixOutput ? 4 * 4 : fixedPointVectorOutput ? 4 : 1;
6372
6373 for (size_t pipelineStageNdx = 0; pipelineStageNdx < DE_LENGTH_OF_ARRAY(pipelineStages); ++pipelineStageNdx)
6374 {
6375 de::MovePtr<tcu::TestCaseGroup> sourceTypeGroup(
6376 new tcu::TestCaseGroup(group->getTestContext(), pipelineStages[pipelineStageNdx].name));
6377 const VkShaderStageFlagBits stage = pipelineStages[pipelineStageNdx].stage;
6378 const CheckSupportFunc pipelineCheckSupport = getPipelineCheckSupport(stage);
6379 const InitProgramsFunc pipelineInitPrograms = getPipelineInitPrograms(stage);
6380 const uint32_t instancesGroupCount = single ? 1 : 2;
6381 const uint32_t geometriesGroupCount = single ? 1 : 8;
6382 const uint32_t squaresGroupCount = (TEST_WIDTH * TEST_HEIGHT) / geometriesGroupCount / instancesGroupCount;
6383
6384 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == TEST_WIDTH * TEST_HEIGHT);
6385
6386 for (size_t geomTypeNdx = 0; geomTypeNdx < DE_LENGTH_OF_ARRAY(geomTypes); ++geomTypeNdx)
6387 {
6388 const GeomType geomType = geomTypes[geomTypeNdx].geomType;
6389 const TestParams testParams = {
6390 TEST_WIDTH, // uint32_t width;
6391 TEST_HEIGHT, // uint32_t height;
6392 imageDepth, // uint32_t depth;
6393 testType, // TestType testType;
6394 stage, // VkShaderStageFlagBits stage;
6395 geomType, // GeomType geomType;
6396 squaresGroupCount, // uint32_t squaresGroupCount;
6397 geometriesGroupCount, // uint32_t geometriesGroupCount;
6398 instancesGroupCount, // uint32_t instancesGroupCount;
6399 VK_FORMAT_R32_SINT, // VkFormat format;
6400 pipelineCheckSupport, // CheckSupportFunc pipelineCheckSupport;
6401 pipelineInitPrograms, // InitProgramsFunc pipelineInitPrograms;
6402 testConfigShaderBodyTextFunc, // ShaderTestTextFunc testConfigShaderBodyText;
6403 false, // bool isSPIRV;
6404 DE_NULL, // CheckSupportFunc testConfigCheckSupport;
6405 };
6406
6407 if (geomType != GEOM_TYPE_AABBS && testType == TEST_TYPE_GET_INTERSECTION_CANDIDATE_AABB_OPAQUE)
6408 {
6409 continue;
6410 }
6411
6412 if (geomType != GEOM_TYPE_TRIANGLES && (testType == TEST_TYPE_GET_INTERSECTION_FRONT_FACE_CANDIDATE ||
6413 testType == TEST_TYPE_GET_INTERSECTION_FRONT_FACE_COMMITTED ||
6414 testType == TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_CANDIDATE ||
6415 testType == TEST_TYPE_GET_INTERSECTION_BARYCENTRICS_COMMITTED))
6416 {
6417 continue;
6418 }
6419
6420 sourceTypeGroup->addChild(
6421 new RayQueryBuiltinTestCase(group->getTestContext(), geomTypes[geomTypeNdx].name, testParams));
6422 }
6423
6424 testTypeGroup->addChild(sourceTypeGroup.release());
6425 }
6426
6427 group->addChild(testTypeGroup.release());
6428 }
6429
6430 return group.release();
6431 }
6432
createAdvancedTests(tcu::TestContext & testCtx)6433 tcu::TestCaseGroup *createAdvancedTests(tcu::TestContext &testCtx)
6434 {
6435 de::MovePtr<tcu::TestCaseGroup> group(new tcu::TestCaseGroup(testCtx, "advanced"));
6436
6437 const struct TestTypes
6438 {
6439 TestType testType;
6440 const char *name;
6441 } testTypes[] = {{TEST_TYPE_NULL_ACCELERATION_STRUCTURE, "null_as"},
6442 {TEST_TYPE_USING_WRAPPER_FUNCTION, "using_wrapper_function"}};
6443
6444 for (size_t testTypeNdx = 0; testTypeNdx < DE_LENGTH_OF_ARRAY(testTypes); ++testTypeNdx)
6445 {
6446 de::MovePtr<tcu::TestCaseGroup> testTypeGroup(
6447 new tcu::TestCaseGroup(group->getTestContext(), testTypes[testTypeNdx].name));
6448 const TestType testType = testTypes[testTypeNdx].testType;
6449 const ShaderBodyTextFunc testConfigShaderBodyTextFunc = getShaderBodyTextFunc(testType);
6450 const CheckSupportFunc testConfigCheckSupport = getTestConfigCheckSupport(testType);
6451 const uint32_t imageDepth = 1;
6452 bool useSPIRV = false;
6453
6454 for (size_t pipelineStageNdx = 0; pipelineStageNdx < DE_LENGTH_OF_ARRAY(pipelineStages); ++pipelineStageNdx)
6455 {
6456 const VkShaderStageFlagBits stage = pipelineStages[pipelineStageNdx].stage;
6457
6458 // tests that are implemented using spirv are limit to compute stage
6459 if (testType == TEST_TYPE_USING_WRAPPER_FUNCTION)
6460 {
6461 if (stage != VK_SHADER_STAGE_COMPUTE_BIT)
6462 continue;
6463 useSPIRV = true;
6464 }
6465
6466 de::MovePtr<tcu::TestCaseGroup> sourceTypeGroup(
6467 new tcu::TestCaseGroup(group->getTestContext(), pipelineStages[pipelineStageNdx].name));
6468 const CheckSupportFunc pipelineCheckSupport = getPipelineCheckSupport(stage);
6469 const InitProgramsFunc pipelineInitPrograms = getPipelineInitPrograms(stage);
6470 const uint32_t instancesGroupCount = 1;
6471 const uint32_t geometriesGroupCount = 1;
6472 const uint32_t squaresGroupCount = (TEST_WIDTH * TEST_HEIGHT) / geometriesGroupCount / instancesGroupCount;
6473
6474 DE_ASSERT(instancesGroupCount * geometriesGroupCount * squaresGroupCount == TEST_WIDTH * TEST_HEIGHT);
6475
6476 for (size_t geomTypeNdx = 0; geomTypeNdx < DE_LENGTH_OF_ARRAY(geomTypes); ++geomTypeNdx)
6477 {
6478 const GeomType geomType = geomTypes[geomTypeNdx].geomType;
6479 const TestParams testParams = {
6480 TEST_WIDTH, // uint32_t width;
6481 TEST_HEIGHT, // uint32_t height;
6482 imageDepth, // uint32_t depth;
6483 testType, // TestType testType;
6484 stage, // VkShaderStageFlagBits stage;
6485 geomType, // GeomType geomType;
6486 squaresGroupCount, // uint32_t squaresGroupCount;
6487 geometriesGroupCount, // uint32_t geometriesGroupCount;
6488 instancesGroupCount, // uint32_t instancesGroupCount;
6489 VK_FORMAT_R32_SINT, // VkFormat format;
6490 pipelineCheckSupport, // CheckSupportFunc pipelineCheckSupport;
6491 pipelineInitPrograms, // InitProgramsFunc pipelineInitPrograms;
6492 testConfigShaderBodyTextFunc, // ShaderTestTextFunc testConfigShaderBodyText;
6493 useSPIRV, // bool isSPIRV;
6494 testConfigCheckSupport, // CheckSupportFunc testConfigCheckSupport;
6495 };
6496
6497 sourceTypeGroup->addChild(
6498 new RayQueryBuiltinTestCase(group->getTestContext(), geomTypes[geomTypeNdx].name, testParams));
6499 }
6500
6501 testTypeGroup->addChild(sourceTypeGroup.release());
6502 }
6503
6504 group->addChild(testTypeGroup.release());
6505 }
6506
6507 return group.release();
6508 }
6509
6510 } // namespace RayQuery
6511 } // namespace vkt
6512