1 /*-------------------------------------------------------------------------
2 * Vulkan Conformance Tests
3 * ------------------------
4 *
5 * Copyright (c) 2015 Google Inc.
6 * Copyright (c) 2019-2020 NVIDIA Corporation
7 *
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
11 *
12 * http://www.apache.org/licenses/LICENSE-2.0
13 *
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
19 *
20 *//*!
21 * \file
22 * \brief Fragment Shading Rate tests
23 *//*--------------------------------------------------------------------*/
24
25 #include "vktFragmentShadingRateTests.hpp"
26 #include "vktFragmentShadingRateBasic.hpp"
27 #include "vktFragmentShadingRatePixelConsistency.hpp"
28 #include "vktFragmentShadingRateGroupParams.hpp"
29 #include "vktAttachmentRateTests.hpp"
30 #include "vktTestGroupUtil.hpp"
31 #include "vktTestCaseUtil.hpp"
32 #include "vkPipelineConstructionUtil.hpp"
33 #include "tcuTestLog.hpp"
34 #include <limits>
35
36 namespace vkt
37 {
38 namespace FragmentShadingRate
39 {
40
41 namespace
42 {
43
testLimits(Context & context)44 tcu::TestStatus testLimits(Context& context)
45 {
46 bool allChecksPassed = true;
47 tcu::TestLog& log = context.getTestContext().getLog();
48 const auto& features = context.getDeviceFeatures();
49 const auto& properties = context.getDeviceProperties();
50 const auto& vulkan12Features = context.getDeviceVulkan12Features();
51 const auto& fragmentShadingRateFeatures = context.getFragmentShadingRateFeatures();
52 const auto& fragmentShadingRateProperties = context.getFragmentShadingRateProperties();
53
54 if (!fragmentShadingRateFeatures.pipelineFragmentShadingRate)
55 {
56 log << tcu::TestLog::Message << "pipelineFragmentShadingRate is not supported" << tcu::TestLog::EndMessage;
57 allChecksPassed = false;
58 }
59
60 if (context.getFragmentShadingRateProperties().primitiveFragmentShadingRateWithMultipleViewports && !context.getFragmentShadingRateFeatures().primitiveFragmentShadingRate)
61 {
62 log << tcu::TestLog::Message << "primitiveFragmentShadingRateWithMultipleViewports "
63 "limit should only be supported if primitiveFragmentShadingRate is supported" << tcu::TestLog::EndMessage;
64 allChecksPassed = false;
65 }
66
67 bool requiredFeatures = features.geometryShader || vulkan12Features.shaderOutputViewportIndex || context.isDeviceFunctionalitySupported("VK_EXT_shader_viewport_index_layer");
68 if (context.getFragmentShadingRateProperties().primitiveFragmentShadingRateWithMultipleViewports && !requiredFeatures)
69 {
70 log << tcu::TestLog::Message << "primitiveFragmentShadingRateWithMultipleViewports limit should only "
71 "be supported if at least one of the geometryShader feature, shaderOutputViewportIndex feature, "
72 "or VK_EXT_shader_viewport_index_layer extension is supported" << tcu::TestLog::EndMessage;
73 allChecksPassed = false;
74 }
75
76 if (fragmentShadingRateProperties.layeredShadingRateAttachments && !fragmentShadingRateFeatures.attachmentFragmentShadingRate)
77 {
78 log << tcu::TestLog::Message << "layeredShadingRateAttachments should only be supported if attachmentFragmentShadingRate is supported" << tcu::TestLog::EndMessage;
79 allChecksPassed = false;
80 }
81
82 requiredFeatures = features.geometryShader || context.getMultiviewFeatures().multiview || vulkan12Features.shaderOutputViewportIndex ||
83 context.isDeviceFunctionalitySupported("VK_EXT_shader_viewport_index_layer");
84 if (fragmentShadingRateProperties.layeredShadingRateAttachments && !requiredFeatures)
85 {
86 log << tcu::TestLog::Message << "layeredShadingRateAttachments should only be supported if at least one of the geometryShader feature, multiview feature, "
87 "shaderOutputViewportIndex feature, or VK_EXT_shader_viewport_index_layer extension is supported" << tcu::TestLog::EndMessage;
88 allChecksPassed = false;
89 }
90
91 requiredFeatures = fragmentShadingRateFeatures.primitiveFragmentShadingRate || fragmentShadingRateFeatures.attachmentFragmentShadingRate;
92 if (fragmentShadingRateProperties.fragmentShadingRateNonTrivialCombinerOps && !requiredFeatures)
93 {
94 log << tcu::TestLog::Message << "fragmentShadingRateNonTrivialCombinerOps should only be supported if at least one of primitiveFragmentShadingRate "
95 "or attachmentFragmentShadingRate is supported" << tcu::TestLog::EndMessage;
96 allChecksPassed = false;
97 }
98
99 if (fragmentShadingRateProperties.maxFragmentSizeAspectRatio > std::max(fragmentShadingRateProperties.maxFragmentSize.width, fragmentShadingRateProperties.maxFragmentSize.height))
100 {
101 log << tcu::TestLog::Message << "maxFragmentSizeAspectRatio should be less than or equal to the maximum width / height of maxFragmentSize" << tcu::TestLog::EndMessage;
102 allChecksPassed = false;
103 }
104
105 if (fragmentShadingRateProperties.maxFragmentSizeAspectRatio < 2)
106 {
107 log << tcu::TestLog::Message << "maxFragmentSizeAspectRatio should be at least 2" << tcu::TestLog::EndMessage;
108 allChecksPassed = false;
109 }
110
111 if (!deIntIsPow2(static_cast<int>(fragmentShadingRateProperties.maxFragmentSizeAspectRatio)))
112 {
113 log << tcu::TestLog::Message << "maxFragmentSizeAspectRatio should be power of 2" << tcu::TestLog::EndMessage;
114 allChecksPassed = false;
115 }
116
117 if (fragmentShadingRateProperties.fragmentShadingRateWithShaderSampleMask && (fragmentShadingRateProperties.maxFragmentShadingRateCoverageSamples > (properties.limits.maxSampleMaskWords * 32)))
118 {
119 log << tcu::TestLog::Message << "maxFragmentShadingRateCoverageSamples should be less than or equal maxSampleMaskWords * 32 "
120 "if fragmentShadingRateWithShaderSampleMask is supported" << tcu::TestLog::EndMessage;
121 allChecksPassed = false;
122 }
123
124 deUint32 requiredValue = fragmentShadingRateProperties.maxFragmentSize.width * fragmentShadingRateProperties.maxFragmentSize.height *
125 fragmentShadingRateProperties.maxFragmentShadingRateRasterizationSamples;
126 if (fragmentShadingRateProperties.maxFragmentShadingRateCoverageSamples > requiredValue)
127 {
128 log << tcu::TestLog::Message << "maxFragmentShadingRateCoverageSamples should be less than or equal to the product of the width and height of "
129 "maxFragmentSize and the samples reported by maxFragmentShadingRateRasterizationSamples" << tcu::TestLog::EndMessage;
130 allChecksPassed = false;
131 }
132
133 if (fragmentShadingRateProperties.maxFragmentShadingRateCoverageSamples < 16)
134 {
135 log << tcu::TestLog::Message << "maxFragmentShadingRateCoverageSamples should at least be 16" << tcu::TestLog::EndMessage;
136 allChecksPassed = false;
137 }
138
139 if (fragmentShadingRateProperties.maxFragmentShadingRateRasterizationSamples < vk::VK_SAMPLE_COUNT_4_BIT)
140 {
141 log << tcu::TestLog::Message << "maxFragmentShadingRateRasterizationSamples should supports at least VK_SAMPLE_COUNT_4_BIT" << tcu::TestLog::EndMessage;
142 allChecksPassed = false;
143 }
144
145 if (fragmentShadingRateProperties.fragmentShadingRateWithConservativeRasterization && !context.isDeviceFunctionalitySupported("VK_EXT_conservative_rasterization"))
146 {
147 log << tcu::TestLog::Message << "fragmentShadingRateWithConservativeRasterization should only be supported if VK_EXT_conservative_rasterization is supported" << tcu::TestLog::EndMessage;
148 allChecksPassed = false;
149 }
150
151 if (fragmentShadingRateProperties.fragmentShadingRateWithFragmentShaderInterlock && !context.isDeviceFunctionalitySupported("VK_EXT_fragment_shader_interlock"))
152 {
153 log << tcu::TestLog::Message << "fragmentShadingRateWithFragmentShaderInterlock should only be supported if VK_EXT_fragment_shader_interlock is supported" << tcu::TestLog::EndMessage;
154 allChecksPassed = false;
155 }
156
157 if (fragmentShadingRateProperties.fragmentShadingRateWithCustomSampleLocations && !context.isDeviceFunctionalitySupported("VK_EXT_sample_locations"))
158 {
159 log << tcu::TestLog::Message << "fragmentShadingRateWithCustomSampleLocations should only be supported if VK_EXT_sample_locations is supported" << tcu::TestLog::EndMessage;
160 allChecksPassed = false;
161 }
162
163 if (fragmentShadingRateFeatures.attachmentFragmentShadingRate)
164 {
165 if ((fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.width < 8) ||
166 (fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.height < 8))
167 {
168 log << tcu::TestLog::Message << "maxFragmentShadingRateAttachmentTexelSize should at least be { 8,8 }" << tcu::TestLog::EndMessage;
169 allChecksPassed = false;
170 }
171
172 if ((fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.width > 32) ||
173 (fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.height > 32))
174 {
175 log << tcu::TestLog::Message << "minFragmentShadingRateAttachmentTexelSize should't be greater than { 32,32 }" << tcu::TestLog::EndMessage;
176 allChecksPassed = false;
177 }
178
179 if ((fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.width < fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.width) ||
180 (fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.height < fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.height))
181 {
182 log << tcu::TestLog::Message << "maxFragmentShadingRateAttachmentTexelSize should be greater than or equal to "
183 "minFragmentShadingRateAttachmentTexelSize in each dimension" << tcu::TestLog::EndMessage;
184 allChecksPassed = false;
185 }
186
187 if (!deIntIsPow2(static_cast<int>(fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.width)) ||
188 !deIntIsPow2(static_cast<int>(fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.height)))
189 {
190 log << tcu::TestLog::Message << "maxFragmentShadingRateAttachmentTexelSize should be power of 2" << tcu::TestLog::EndMessage;
191 allChecksPassed = false;
192 }
193
194 if (!deIntIsPow2(static_cast<int>(fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.width)) ||
195 !deIntIsPow2(static_cast<int>(fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.height)))
196 {
197 log << tcu::TestLog::Message << "minFragmentShadingRateAttachmentTexelSize should be power of 2" << tcu::TestLog::EndMessage;
198 allChecksPassed = false;
199 }
200 }
201 else
202 {
203 if ((fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.width != 0) ||
204 (fragmentShadingRateProperties.maxFragmentShadingRateAttachmentTexelSize.height != 0))
205 {
206 log << tcu::TestLog::Message << "maxFragmentShadingRateAttachmentTexelSize should be { 0,0 } when "
207 "attachmentFragmentShadingRate is not supported" << tcu::TestLog::EndMessage;
208 allChecksPassed = false;
209 }
210
211 if ((fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.width != 0) ||
212 (fragmentShadingRateProperties.minFragmentShadingRateAttachmentTexelSize.height != 0))
213 {
214 log << tcu::TestLog::Message << "minFragmentShadingRateAttachmentTexelSize should be { 0,0 } when "
215 "attachmentFragmentShadingRate is not supported" << tcu::TestLog::EndMessage;
216 allChecksPassed = false;
217 }
218 }
219
220 if ((fragmentShadingRateProperties.maxFragmentSize.width < 2) ||
221 (fragmentShadingRateProperties.maxFragmentSize.height < 2))
222 {
223 log << tcu::TestLog::Message << "maxFragmentSize should at least be { 2,2 }" << tcu::TestLog::EndMessage;
224 allChecksPassed = false;
225 }
226
227 if ((fragmentShadingRateProperties.maxFragmentSize.width > 4) ||
228 (fragmentShadingRateProperties.maxFragmentSize.height > 4))
229 {
230 log << tcu::TestLog::Message << "maxFragmentSize should't be greater than{ 4,4 }" << tcu::TestLog::EndMessage;
231 allChecksPassed = false;
232 }
233
234 if (allChecksPassed)
235 return tcu::TestStatus::pass("pass");
236 return tcu::TestStatus::fail("fail");
237 }
238
testShadingRates(Context & context)239 tcu::TestStatus testShadingRates(Context& context)
240 {
241 bool someChecksFailed = false;
242 tcu::TestLog& log = context.getTestContext().getLog();
243 const vk::InstanceInterface& vki = context.getInstanceInterface();
244 vk::VkPhysicalDevice physicalDevice = context.getPhysicalDevice();
245 const auto& fragmentShadingRateProperties = context.getFragmentShadingRateProperties();
246 deUint32 supportedFragmentShadingRateCount = 0;
247
248 vk::VkResult result = vki.getPhysicalDeviceFragmentShadingRatesKHR(physicalDevice, &supportedFragmentShadingRateCount, DE_NULL);
249 if ((result != vk::VK_SUCCESS) && (result != vk::VK_ERROR_OUT_OF_HOST_MEMORY))
250 {
251 someChecksFailed = true;
252 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned invalid result" << tcu::TestLog::EndMessage;
253 }
254
255 std::vector<vk::VkPhysicalDeviceFragmentShadingRateKHR> fragmentShadingRateVect(supportedFragmentShadingRateCount);
256 for (auto& fragmentShadingRate : fragmentShadingRateVect)
257 {
258 fragmentShadingRate.sType = vk::VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADING_RATE_KHR;
259 fragmentShadingRate.pNext = DE_NULL;
260 }
261
262 // Pass a value of 1 into pFragmentShadingRateCount, and an array of at least length one into pFragmentShadingRates.
263 // Check that the returned value is either VK_INCOMPLETE or VK_ERROR_OUT_OF_HOST_MEMORY(and issue a quality warning in the latter case).
264 supportedFragmentShadingRateCount = 1u;
265 result = vki.getPhysicalDeviceFragmentShadingRatesKHR(physicalDevice, &supportedFragmentShadingRateCount, fragmentShadingRateVect.data());
266 if ((result != vk::VK_INCOMPLETE) && (result != vk::VK_ERROR_OUT_OF_HOST_MEMORY))
267 {
268 someChecksFailed = true;
269 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned invalid result" << tcu::TestLog::EndMessage;
270 }
271
272 // Get all available fragment shading rates
273 supportedFragmentShadingRateCount = static_cast<deUint32>(fragmentShadingRateVect.size());
274 result = vki.getPhysicalDeviceFragmentShadingRatesKHR(physicalDevice, &supportedFragmentShadingRateCount, fragmentShadingRateVect.data());
275 if ((result != vk::VK_SUCCESS) && (result != vk::VK_ERROR_OUT_OF_HOST_MEMORY))
276 {
277 someChecksFailed = true;
278 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned invalid result" << tcu::TestLog::EndMessage;
279 }
280
281 bool widthCheckPassed = true;
282 bool heightCheckPassed = true;
283 deUint32 previousWidth = std::numeric_limits<deUint32>::max();
284 deUint32 previousHeight = std::numeric_limits<deUint32>::max();
285
286 for (const auto& fsr : fragmentShadingRateVect)
287 {
288 const auto& fragmentSize = fsr.fragmentSize;
289
290 // Check that rate width and height are power-of-two
291 if (!deIntIsPow2(static_cast<int>(fragmentSize.width)) ||
292 !deIntIsPow2(static_cast<int>(fragmentSize.height)))
293 {
294 log << tcu::TestLog::Message << "fragmentSize should be power of 2" << tcu::TestLog::EndMessage;
295 someChecksFailed = true;
296 }
297
298 // Check that the width and height are less than the values in the maxFragmentSize limit
299 if ((fragmentSize.width > fragmentShadingRateProperties.maxFragmentSize.width) ||
300 (fragmentSize.height > fragmentShadingRateProperties.maxFragmentSize.height))
301 {
302 log << tcu::TestLog::Message << "fragmentSize width and height are not less than the values in the maxFragmentSize" << tcu::TestLog::EndMessage;
303 someChecksFailed = true;
304 }
305
306 if ((fragmentSize.width * fragmentSize.height) == 1)
307 {
308 // special case for fragmentSize {1, 1}
309 if (fsr.sampleCounts != ~0u)
310 {
311 log << tcu::TestLog::Message << "implementations must support sampleCounts equal to ~0 for fragmentSize {1, 1}" << tcu::TestLog::EndMessage;
312 someChecksFailed = true;
313 }
314 }
315 else
316 {
317 // get highest sample count value
318 deUint32 highestSampleCount = 0x80000000;
319 while (highestSampleCount)
320 {
321 if (fsr.sampleCounts & highestSampleCount)
322 break;
323 highestSampleCount >>= 1;
324 }
325
326 // Check that the highest sample count in sampleCounts is less than or equal to maxFragmentShadingRateRasterizationSamples limit
327 if (highestSampleCount > static_cast<deUint32>(fragmentShadingRateProperties.maxFragmentShadingRateRasterizationSamples))
328 {
329 log << tcu::TestLog::Message << "highest sample count value is not less than or equal to the maxFragmentShadingRateRasterizationSamples limit" << tcu::TestLog::EndMessage;
330 someChecksFailed = true;
331 }
332
333 // Check that the product of the width, height, and highest sample count value is less than the maxFragmentShadingRateCoverageSamples limit
334 if ((fragmentSize.width * fragmentSize.height * highestSampleCount) > fragmentShadingRateProperties.maxFragmentShadingRateCoverageSamples)
335 {
336 log << tcu::TestLog::Message << "product of the width, height, and highest sample count value is not less than the maxFragmentShadingRateCoverageSamples limit" << tcu::TestLog::EndMessage;
337 someChecksFailed = true;
338 }
339 }
340
341 // Check that the entries in the array are ordered first by largest to smallest width, then largest to smallest height
342 {
343 const deUint32 currentWidth = fragmentSize.width;
344 if (widthCheckPassed && (currentWidth > previousWidth))
345 {
346 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned entries that are not ordered by largest to smallest width" << tcu::TestLog::EndMessage;
347 widthCheckPassed = false;
348 }
349
350 deUint32 currentHeight = fragmentSize.height;
351 if (heightCheckPassed)
352 {
353 // we can check order of height only for entries that have same width
354 if (currentWidth == previousWidth)
355 {
356 if (currentHeight > previousHeight)
357 {
358 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned entries with same width but height is not ordered by largest to smallest" << tcu::TestLog::EndMessage;
359 heightCheckPassed = false;
360 }
361 }
362 else
363 currentHeight = std::numeric_limits<deUint32>::max();
364 }
365
366 previousWidth = currentWidth;
367 previousHeight = currentHeight;
368 }
369
370 // Check that no two entries in the array have the same fragmentSize.width and fragmentSize.height value
371 {
372 deUint32 count = 0;
373 for (const auto& fsrB : fragmentShadingRateVect)
374 {
375 if ((fragmentSize.width == fsrB.fragmentSize.width) &&
376 (fragmentSize.height == fsrB.fragmentSize.height))
377 {
378 if (++count > 1)
379 {
380 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned entries with same fragmentSize" << tcu::TestLog::EndMessage;
381 someChecksFailed = true;
382 break;
383 }
384 }
385 }
386 }
387
388 // Check that 1x1, 1x2, 2x1, and 2x2 rates are supported with sample counts of 1 and 4
389 if ((fragmentSize.width < 3) && (fragmentSize.height < 3) &&
390 (!(fsr.sampleCounts & vk::VK_SAMPLE_COUNT_1_BIT) || !(fsr.sampleCounts & vk::VK_SAMPLE_COUNT_4_BIT)))
391 {
392 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned 1x1, 1x2, 2x1, and 2x2 rates with sample counts not supporting 1 and 4" << tcu::TestLog::EndMessage;
393 someChecksFailed = true;
394 }
395
396 // If the framebufferColorSampleCounts limit includes a sample count of 2, ensure that a sample count of 2 is also reported for the 1x1, 1x2, 2x1, and 2x2 rates.
397 if (context.getDeviceProperties().limits.framebufferColorSampleCounts & vk::VK_SAMPLE_COUNT_2_BIT)
398 {
399 if ((fragmentSize.width < 3) && (fragmentSize.height < 3) &&
400 !(fsr.sampleCounts & vk::VK_SAMPLE_COUNT_2_BIT))
401 {
402 log << tcu::TestLog::Message << "vkGetPhysicalDeviceFragmentShadingRatesKHR returned 1x1, 1x2, 2x1, and 2x2 rates with sample counts not supporting 2 while framebufferColorSampleCounts does" << tcu::TestLog::EndMessage;
403 someChecksFailed = true;
404 }
405 }
406 }
407
408 if (someChecksFailed || !widthCheckPassed || !heightCheckPassed)
409 return tcu::TestStatus::fail("fail");
410
411 return tcu::TestStatus::pass("pass");
412 }
413
checkSupport(Context & context)414 void checkSupport(Context& context)
415 {
416 context.requireDeviceFunctionality("VK_KHR_fragment_shading_rate");
417 }
418
createMiscTests(tcu::TestContext & testCtx,tcu::TestCaseGroup * parentGroup)419 void createMiscTests(tcu::TestContext& testCtx, tcu::TestCaseGroup* parentGroup)
420 {
421 de::MovePtr<tcu::TestCaseGroup> group(new tcu::TestCaseGroup(testCtx, "misc", ""));
422
423 addFunctionCase(group.get(), "limits", "", checkSupport, testLimits);
424 addFunctionCase(group.get(), "shading_rates", "", checkSupport, testShadingRates);
425
426 parentGroup->addChild(group.release());
427 }
428
createTests(tcu::TestCaseGroup * group,SharedGroupParams groupParams)429 void createTests (tcu::TestCaseGroup* group, SharedGroupParams groupParams)
430 {
431 tcu::TestContext& testCtx = group->getTestContext();
432
433 createBasicTests(testCtx, group, groupParams);
434
435 // attachmentFragmentShadingRate feature is tested with basic tests so there is no need to
436 // duplicating those tests for secondary command buffer;
437 // those tests are also not repeated for non monolithic pipelines
438 if (!groupParams->useSecondaryCmdBuffer && (groupParams->pipelineConstructionType == vk::PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC))
439 createAttachmentRateTests(testCtx, group, groupParams);
440
441 // run pixel consistency tests and misc tests only with renderpass2 and monolithic pipeline
442 if (!groupParams->useDynamicRendering && (groupParams->pipelineConstructionType == vk::PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC))
443 {
444 // there is no point in duplicating those tests for dynamic rendering
445 createMiscTests(testCtx, group);
446
447 // subpasses can't be translated to dynamic rendering
448 createPixelConsistencyTests(testCtx, group);
449 }
450 }
451
createPipelineConstructionTypePermutations(tcu::TestCaseGroup * parentGroup,SharedGroupParams baseGroupParams)452 void createPipelineConstructionTypePermutations(tcu::TestCaseGroup* parentGroup, SharedGroupParams baseGroupParams)
453 {
454 tcu::TestContext& testCtx = parentGroup->getTestContext();
455
456 auto constructGroupParams = [&baseGroupParams](vk::PipelineConstructionType pipelineConstructionType)
457 {
458 return SharedGroupParams(new GroupParams
459 {
460 baseGroupParams->useDynamicRendering,
461 baseGroupParams->useSecondaryCmdBuffer,
462 baseGroupParams->secondaryCmdBufferCompletelyContainsDynamicRenderpass,
463 pipelineConstructionType,
464 });
465 };
466
467 typedef de::MovePtr<tcu::TestCaseGroup> TestGroupPtr;
468 TestGroupPtr monolithic (createTestGroup(testCtx, "monolithic", "Monolithic pipeline tests",
469 createTests, constructGroupParams(vk::PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC)));
470 parentGroup->addChild(monolithic.release());
471
472 #ifndef CTS_USES_VULKANSC
473 TestGroupPtr pipelineLibrary (createTestGroup(testCtx, "pipeline_library", "Graphics pipeline library tests",
474 createTests, constructGroupParams(vk::PIPELINE_CONSTRUCTION_TYPE_LINK_TIME_OPTIMIZED_LIBRARY)));
475 TestGroupPtr fastLinkedLibrary (createTestGroup(testCtx, "fast_linked_library", "Fast linked graphics pipeline library tests",
476 createTests, constructGroupParams(vk::PIPELINE_CONSTRUCTION_TYPE_FAST_LINKED_LIBRARY)));
477
478 parentGroup->addChild(pipelineLibrary.release());
479 parentGroup->addChild(fastLinkedLibrary.release());
480 #endif // CTS_USES_VULKANSC
481 }
482
483 #ifndef CTS_USES_VULKANSC
createDynamicRenderingPermutations(tcu::TestCaseGroup * parentGroup)484 void createDynamicRenderingPermutations(tcu::TestCaseGroup* parentGroup)
485 {
486 tcu::TestContext& testCtx = parentGroup->getTestContext();
487
488 auto constructGroupParams = [](bool useSecondaryCmdBuffer, bool secondaryCmdBufferCompletelyContainsDynamicRenderpass)
489 {
490 return SharedGroupParams(new GroupParams
491 {
492 true, // bool useDynamicRendering;
493 useSecondaryCmdBuffer, // bool useSecondaryCmdBuffer;
494 secondaryCmdBufferCompletelyContainsDynamicRenderpass, // bool secondaryCmdBufferCompletelyContainsDynamicRenderpass;
495 vk::PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC, // PipelineConstructionType pipelineConstructionType;
496 });
497 };
498
499 typedef de::MovePtr<tcu::TestCaseGroup> TestGroupPtr;
500 TestGroupPtr drPrimaryCmdBuffGroup (createTestGroup(testCtx, "primary_cmd_buff", "Draw using Draw commands are recorded in primary command buffer",
501 createPipelineConstructionTypePermutations, constructGroupParams(false, false)));
502 TestGroupPtr drPartialSecondaryCmdBuffGroup (createTestGroup(testCtx, "partial_secondary_cmd_buff", "Secondary command buffer doesn't include begin/endRendering",
503 createTests, constructGroupParams(true, false)));
504 TestGroupPtr drCompleteSecondaryCmdBuffGroup(createTestGroup(testCtx, "complete_secondary_cmd_buff", "Secondary command buffer contains completely dynamic renderpass",
505 createTests, constructGroupParams(true, true)));
506
507 parentGroup->addChild(drPrimaryCmdBuffGroup.release());
508 parentGroup->addChild(drPartialSecondaryCmdBuffGroup.release());
509 parentGroup->addChild(drCompleteSecondaryCmdBuffGroup.release());
510 }
511 #endif // CTS_USES_VULKANSC
512
513 } // anonymous
514
createTests(tcu::TestContext & testCtx)515 tcu::TestCaseGroup* createTests (tcu::TestContext& testCtx)
516 {
517 de::MovePtr<tcu::TestCaseGroup> mainGroup (new tcu::TestCaseGroup(testCtx, "fragment_shading_rate", "Fragment shading rate tests"));
518 de::MovePtr<tcu::TestCaseGroup> renderpass2Group (createTestGroup(testCtx, "renderpass2", "Draw using render pass object",
519 createPipelineConstructionTypePermutations,
520 SharedGroupParams(new GroupParams
521 {
522 false, // bool useDynamicRendering;
523 false, // bool useSecondaryCmdBuffer;
524 false, // bool secondaryCmdBufferCompletelyContainsDynamicRenderpass;
525 vk::PipelineConstructionType(0) // placeholder // PipelineConstructionType pipelineConstructionType;
526 })));
527 mainGroup->addChild(renderpass2Group.release());
528
529 #ifndef CTS_USES_VULKANSC
530 de::MovePtr<tcu::TestCaseGroup> dynamicRenderingGroup(createTestGroup(testCtx, "dynamic_rendering", "Draw using VK_KHR_dynamic_rendering", createDynamicRenderingPermutations));
531 mainGroup->addChild(dynamicRenderingGroup.release());
532 #endif // CTS_USES_VULKANSC
533
534 return mainGroup.release();
535 }
536
537 } // FragmentShadingRate
538 } // vkt
539
540