1 /*------------------------------------------------------------------------
2 * Vulkan Conformance Tests
3 * ------------------------
5 * Copyright (c) 2017-2020 The Khronos Group Inc.
6 * Copyright (c) 2020 AMD
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
12 * http://www.apache.org/licenses/LICENSE-2.0
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.
22 * \brief Tests for VK_KHR_fragment_shading_rate
23 *//*--------------------------------------------------------------------*/
25 #include "vktFragmentShadingRatePixelConsistency.hpp"
27 #include "vkBufferWithMemory.hpp"
28 #include "vkImageWithMemory.hpp"
29 #include "vkQueryUtil.hpp"
30 #include "vkBuilderUtil.hpp"
31 #include "vkCmdUtil.hpp"
32 #include "vkTypeUtil.hpp"
33 #include "vkObjUtil.hpp"
34 #include "vkImageUtil.hpp"
35 #include "vkQueryUtil.hpp"
36 #include "vkPlatform.hpp"
38 #include "vktTestGroupUtil.hpp"
39 #include "vktTestCase.hpp"
40 #include "vktCustomInstancesDevices.hpp"
45 #include "deSharedPtr.hpp"
48 #include "tcuTestCase.hpp"
49 #include "tcuTestLog.hpp"
50 #include "tcuCommandLine.hpp"
58 namespace FragmentShadingRate
67 VkExtent2D shadingRate;
68 VkSampleCountFlagBits samples;
69 VkExtent2D framebufferExtent;
78 Vertex basicTriangles[6] =
89 Move<VkDevice> createImageRobustnessDevice(Context& context)
91 const InstanceInterface& instance = context.getInstanceInterface();
92 const vk::VkPhysicalDevice physicalDevice = context.getPhysicalDevice();
93 const float queuePriority = 1.0f;
95 // Create a universal queue
96 const VkDeviceQueueCreateInfo queueParams =
98 VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO, // VkStructureType sType;
99 DE_NULL, // const void* pNext;
100 0u, // VkDeviceQueueCreateFlags flags;
101 context.getUniversalQueueFamilyIndex(), // deUint32 queueFamilyIndex;
102 1u, // deUint32 queueCount;
103 &queuePriority // const float* pQueuePriorities;
106 // Add image robustness extension if supported
107 std::vector<const char*> deviceExtensions;
109 if (context.isDeviceFunctionalitySupported("VK_EXT_image_robustness"))
111 deviceExtensions.push_back("VK_EXT_image_robustness");
114 VkPhysicalDeviceFragmentShadingRateFeaturesKHR fsrFeatures =
116 VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADING_RATE_FEATURES_KHR, // VkStructureType sType;
117 DE_NULL, // void* pNext;
118 DE_FALSE, // VkBool32 pipelineFragmentShadingRate;
119 DE_FALSE, // VkBool32 primitiveFragmentShadingRate;
120 DE_FALSE, // VkBool32 attachmentFragmentShadingRate;
123 VkPhysicalDeviceFeatures2 enabledFeatures;
124 enabledFeatures.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2;
125 enabledFeatures.pNext = &fsrFeatures;
127 instance.getPhysicalDeviceFeatures2(physicalDevice, &enabledFeatures);
129 const VkDeviceCreateInfo deviceParams =
131 VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO, // VkStructureType sType;
132 &enabledFeatures, // const void* pNext;
133 0u, // VkDeviceCreateFlags flags;
134 1u, // deUint32 queueCreateInfoCount;
135 &queueParams, // const VkDeviceQueueCreateInfo* pQueueCreateInfos;
136 0u, // deUint32 enabledLayerCount;
137 DE_NULL, // const char* const* ppEnabledLayerNames;
138 static_cast<deUint32>(deviceExtensions.size()), // deUint32 enabledExtensionCount;
139 deviceExtensions.empty() ? DE_NULL : &deviceExtensions[0], // const char* const* ppEnabledExtensionNames;
140 DE_NULL, // const VkPhysicalDeviceFeatures* pEnabledFeatures;
143 return createCustomDevice(context.getTestContext().getCommandLine().isValidationEnabled(), context.getPlatformInterface(),
144 context.getInstance(), context.getInstanceInterface(), context.getPhysicalDevice(), &deviceParams);
147 class FSRPixelConsistencyInstance : public TestInstance
150 FSRPixelConsistencyInstance (Context& context, const CaseDef& data);
151 ~FSRPixelConsistencyInstance(void);
152 tcu::TestStatus iterate (void);
155 void clampShadingRate();
156 tcu::TestStatus verifyResult(tcu::ConstPixelBufferAccess& resultBuffer, const deUint32 index);
159 vector<VkExtent2D> m_shadingRateClamped;
161 deUint32 m_supportedFragmentShadingRateCount;
162 vector<VkPhysicalDeviceFragmentShadingRateKHR> m_supportedFragmentShadingRates;
165 FSRPixelConsistencyInstance::FSRPixelConsistencyInstance(Context& context, const CaseDef& data)
166 : vkt::TestInstance (context)
168 , m_supportedFragmentShadingRateCount(0)
170 // Fetch information about supported fragment shading rates
171 context.getInstanceInterface().getPhysicalDeviceFragmentShadingRatesKHR(context.getPhysicalDevice(), &m_supportedFragmentShadingRateCount, DE_NULL);
173 m_supportedFragmentShadingRates.resize(m_supportedFragmentShadingRateCount);
174 context.getInstanceInterface().getPhysicalDeviceFragmentShadingRatesKHR(context.getPhysicalDevice(), &m_supportedFragmentShadingRateCount, &m_supportedFragmentShadingRates[0]);
179 FSRPixelConsistencyInstance::~FSRPixelConsistencyInstance(void)
183 class FSRPixelConsistencyTestCase : public TestCase
186 FSRPixelConsistencyTestCase (tcu::TestContext& context, const char* name, const char* desc, const CaseDef data);
187 ~FSRPixelConsistencyTestCase (void);
188 virtual void initPrograms (SourceCollections& programCollection) const;
189 virtual TestInstance* createInstance (Context& context) const;
190 virtual void checkSupport (Context& context) const;
197 FSRPixelConsistencyTestCase::FSRPixelConsistencyTestCase(tcu::TestContext& context, const char* name, const char* desc, const CaseDef data)
198 : vkt::TestCase (context, name, desc)
203 FSRPixelConsistencyTestCase::~FSRPixelConsistencyTestCase(void)
207 void FSRPixelConsistencyTestCase::checkSupport(Context& context) const
209 const VkImageUsageFlags cbUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
210 VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT |
211 VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
212 VK_IMAGE_USAGE_TRANSFER_DST_BIT;
214 context.requireDeviceFunctionality("VK_KHR_fragment_shading_rate");
216 if (!context.getFragmentShadingRateFeatures().pipelineFragmentShadingRate)
217 TCU_THROW(NotSupportedError, "pipelineFragmentShadingRate not supported");
219 VkImageFormatProperties imageProperties;
220 VkResult result = context.getInstanceInterface().getPhysicalDeviceImageFormatProperties(context.getPhysicalDevice(), VK_FORMAT_R32G32_UINT, VK_IMAGE_TYPE_2D,
221 VK_IMAGE_TILING_OPTIMAL, cbUsage , 0, &imageProperties);
223 if (result == VK_ERROR_FORMAT_NOT_SUPPORTED)
224 TCU_THROW(NotSupportedError, "VK_FORMAT_R32G32_UINT not supported");
226 if (!(imageProperties.sampleCounts & m_data.samples))
227 TCU_THROW(NotSupportedError, "Image sample count not supported");
229 if ((imageProperties.maxExtent.width < m_data.framebufferExtent.width) || (imageProperties.maxExtent.height < m_data.framebufferExtent.height))
230 TCU_THROW(NotSupportedError, "Image max extents are smaller than required");
233 void FSRPixelConsistencyTestCase::initPrograms (SourceCollections& programCollection) const
235 std::stringstream vss;
238 "#version 450 core\n"
239 "layout(location = 0) in vec2 position;\n"
242 " vec4 gl_Position;\n"
246 " gl_Position = vec4(position, 0, 1);\n"
249 programCollection.glslSources.add("vert") << glu::VertexSource(vss.str());
251 std::stringstream fssPass0;
254 "#version 450 core\n"
255 "layout(push_constant) uniform PC {\n"
256 " uvec2 shadingRate[2];\n"
258 "layout(location = 0) out uvec2 col0;\n"
261 " col0.x = (uint(gl_FragCoord.x) % pc.shadingRate[0].x) + ((uint(gl_FragCoord.y) % pc.shadingRate[0].y) * pc.shadingRate[0].x);\n"
262 " col0.y = (uint(gl_FragCoord.x) % pc.shadingRate[1].x) + ((uint(gl_FragCoord.y) % pc.shadingRate[1].y) * pc.shadingRate[1].x);\n"
265 programCollection.glslSources.add("frag_pass0") << glu::FragmentSource(fssPass0.str());
267 std::stringstream fssPass1;
270 "#version 450 core\n";
272 if (m_data.samples == VK_SAMPLE_COUNT_1_BIT)
275 "layout(input_attachment_index=0, set=0, binding=0) uniform usubpassInput inputAttachment;\n";
280 "layout(input_attachment_index=0, set=0, binding=0) uniform usubpassInputMS inputAttachment;\n";
284 "layout(location = 0) out uvec2 col0;\n"
288 if (m_data.samples == VK_SAMPLE_COUNT_1_BIT)
291 " col0 = subpassLoad(inputAttachment).xy;\n";
296 " col0 = subpassLoad(inputAttachment, 0).xy;\n";
302 programCollection.glslSources.add("frag_pass1") << glu::FragmentSource(fssPass1.str());
305 TestInstance* FSRPixelConsistencyTestCase::createInstance (Context& context) const
307 return new FSRPixelConsistencyInstance(context, m_data);
310 bool compareShadingRate(VkExtent2D ext1, VkExtent2D ext2)
312 deUint32 ratio1 = std::max(ext1.width, ext1.height) / std::min(ext1.width, ext1.height);
313 deUint32 ratio2 = std::max(ext2.width, ext2.height) / std::min(ext2.width, ext2.height);
315 return ratio1 < ratio2;
318 void FSRPixelConsistencyInstance::clampShadingRate()
320 deUint32 desiredSize = m_data.shadingRate.width * m_data.shadingRate.height;
322 while (desiredSize > 0)
324 // Find modes that maximize the area
325 for (deUint32 i = 0; i < m_supportedFragmentShadingRateCount; ++i)
327 const VkPhysicalDeviceFragmentShadingRateKHR& supportedRate = m_supportedFragmentShadingRates[i];
329 if (supportedRate.sampleCounts & VK_SAMPLE_COUNT_1_BIT)
331 // We found exact match
332 if (supportedRate.fragmentSize.width == m_data.shadingRate.width &&
333 supportedRate.fragmentSize.height == m_data.shadingRate.height)
335 m_shadingRateClamped.push_back(supportedRate.fragmentSize);
341 if (supportedRate.fragmentSize.width <= m_data.shadingRate.width &&
342 supportedRate.fragmentSize.height <= m_data.shadingRate.height &&
343 supportedRate.fragmentSize.width * supportedRate.fragmentSize.height == desiredSize)
345 m_shadingRateClamped.push_back(supportedRate.fragmentSize);
350 if (!m_shadingRateClamped.empty())
352 // Sort the modes so that the ones with the smallest aspect ratio are in front
353 std::sort(m_shadingRateClamped.begin(), m_shadingRateClamped.end(), compareShadingRate);
355 deUint32 desiredRatio = std::max(m_shadingRateClamped[0].width, m_shadingRateClamped[0].height) /
356 std::min(m_shadingRateClamped[0].width, m_shadingRateClamped[0].height);
358 // Leave only entries with the smallest aspect ratio
359 auto it = m_shadingRateClamped.begin();
360 while (it != m_shadingRateClamped.end())
362 deUint32 ratio = std::max(it->width, it->height) / std::min(it->width, it->height);
364 if (ratio < desiredRatio)
366 it = m_shadingRateClamped.erase(it, m_shadingRateClamped.end());
386 tcu::TestStatus FSRPixelConsistencyInstance::verifyResult(tcu::ConstPixelBufferAccess& resultBuffer, const deUint32 index)
388 deUint32 pixelIndex = std::numeric_limits<unsigned int>::max();
389 deUint32 pixelOutsideIndex = std::numeric_limits<unsigned int>::max();
391 for (int y = 0; y < resultBuffer.getHeight(); y++)
393 for (int x = 0; x < resultBuffer.getWidth(); x++)
395 deUint32 pixel = resultBuffer.getPixelUint(x, y)[index];
397 // If pixel was not covered by any triangle, we skip it
398 if (pixel == std::numeric_limits<unsigned int>::max())
403 // We check if pixel is part of fragment area that is partially outside of framebuffer area
404 deBool outsideW = (x / m_shadingRateClamped[index].width + 1) * m_shadingRateClamped[index].width > static_cast<deUint32>(resultBuffer.getWidth());
405 deBool outsideH = (y / m_shadingRateClamped[index].height + 1) * m_shadingRateClamped[index].height > static_cast<deUint32>(resultBuffer.getHeight());
407 if (outsideW || outsideH)
409 // If image robustness is enabled such pixel can have either a value of 0 or one of the values from the area inside framebuffer
410 if (m_context.isDeviceFunctionalitySupported("VK_EXT_image_robustness"))
412 if (pixelOutsideIndex == std::numeric_limits<unsigned int>::max() || pixelOutsideIndex == 0)
414 pixelOutsideIndex = pixel;
416 // If value is non-zero we make sure that all 'corner' pixels have the same value
417 else if ((pixel != 0) && (pixelOutsideIndex != pixel))
419 return tcu::TestStatus(QP_TEST_RESULT_FAIL, qpGetTestResultName(QP_TEST_RESULT_FAIL));
422 // If image robustness is not enabled such pixel can have an undefined value, so we skip it
430 if (pixelIndex == std::numeric_limits<unsigned int>::max())
432 if (pixel >= m_shadingRateClamped[index].width * m_shadingRateClamped[index].height)
434 return tcu::TestStatus(QP_TEST_RESULT_FAIL, qpGetTestResultName(QP_TEST_RESULT_FAIL));
439 // If pixel is not part of 'corner' pixels we make sure that is has the same value as other non-'corner' pixels
440 else if (pixelIndex != pixel)
442 return tcu::TestStatus(QP_TEST_RESULT_FAIL, qpGetTestResultName(QP_TEST_RESULT_FAIL));
448 return tcu::TestStatus(QP_TEST_RESULT_PASS, qpGetTestResultName(QP_TEST_RESULT_PASS));
451 tcu::TestStatus FSRPixelConsistencyInstance::iterate (void)
453 const VkPhysicalDeviceMemoryProperties memoryProperties = vk::getPhysicalDeviceMemoryProperties(m_context.getInstanceInterface(), m_context.getPhysicalDevice());
455 Move<VkDevice> vkd = createImageRobustnessDevice(m_context);
456 const VkDevice device = *vkd;
457 de::MovePtr<DeviceDriver> deviceDriver = de::MovePtr<DeviceDriver>(new DeviceDriver(m_context.getPlatformInterface(), m_context.getInstance(), device));
458 const DeviceInterface& vk = *deviceDriver.get();
459 const VkQueue queue = getDeviceQueue(vk, device, m_context.getUniversalQueueFamilyIndex(), 0);
460 de::MovePtr<Allocator> allocator = de::MovePtr<Allocator>(new SimpleAllocator(vk, device, memoryProperties));
462 // Create vertex buffer
463 const VkDeviceSize vertexBufferSize = sizeof(basicTriangles);
465 const VkFormat imageFormat = VK_FORMAT_R32G32_UINT;
467 de::MovePtr<BufferWithMemory> vertexBuffer;
468 vertexBuffer = de::MovePtr<BufferWithMemory>(new BufferWithMemory(
469 vk, device, *allocator, makeBufferCreateInfo(vertexBufferSize, VK_BUFFER_USAGE_VERTEX_BUFFER_BIT), MemoryRequirement::HostVisible));
471 float* vbuf = (float*)vertexBuffer->getAllocation().getHostPtr();
473 deMemcpy(vbuf, basicTriangles, vertexBufferSize);
475 flushAlloc(vk, device, vertexBuffer->getAllocation());
477 // Create color output buffer
478 const VkDeviceSize colorOutputBufferSize = m_data.framebufferExtent.width * m_data.framebufferExtent.height * tcu::getPixelSize(mapVkFormat(imageFormat));
480 de::MovePtr<BufferWithMemory> colorOutputBuffer;
481 colorOutputBuffer = de::MovePtr<BufferWithMemory>(new BufferWithMemory(
482 vk, device, *allocator, makeBufferCreateInfo(colorOutputBufferSize, VK_BUFFER_USAGE_TRANSFER_DST_BIT), MemoryRequirement::HostVisible));
485 // Create color attachment for subpass 0
486 de::MovePtr<ImageWithMemory> cbImagePass0;
487 Move<VkImageView> cbImagePass0View;
489 const VkImageUsageFlags cbUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
490 VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT |
491 VK_IMAGE_USAGE_TRANSFER_DST_BIT;
493 const VkImageCreateInfo imageCreateInfo =
495 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType;
496 DE_NULL, // const void* pNext;
497 (VkImageCreateFlags)0u, // VkImageCreateFlags flags;
498 VK_IMAGE_TYPE_2D, // VkImageType imageType;
499 imageFormat, // VkFormat format;
501 m_data.framebufferExtent.width, // deUint32 width;
502 m_data.framebufferExtent.height, // deUint32 height;
503 1u // deUint32 depth;
504 }, // VkExtent3D extent;
505 1u, // deUint32 mipLevels;
506 1u, // deUint32 arrayLayers;
507 m_data.samples, // VkSampleCountFlagBits samples;
508 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling;
509 cbUsage, // VkImageUsageFlags usage;
510 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
511 0u, // deUint32 queueFamilyIndexCount;
512 DE_NULL, // const deUint32* pQueueFamilyIndices;
513 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout;
515 cbImagePass0 = de::MovePtr<ImageWithMemory>(new ImageWithMemory(
516 vk, device, *allocator, imageCreateInfo, MemoryRequirement::Any));
518 VkImageViewCreateInfo imageViewCreateInfo =
520 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType;
521 DE_NULL, // const void* pNext;
522 (VkImageViewCreateFlags)0u, // VkImageViewCreateFlags flags;
523 **cbImagePass0, // VkImage image;
524 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType;
525 imageFormat, // VkFormat format;
527 VK_COMPONENT_SWIZZLE_R, // VkComponentSwizzle r;
528 VK_COMPONENT_SWIZZLE_G, // VkComponentSwizzle g;
529 VK_COMPONENT_SWIZZLE_B, // VkComponentSwizzle b;
530 VK_COMPONENT_SWIZZLE_A // VkComponentSwizzle a;
531 }, // VkComponentMapping components;
533 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask;
534 0u, // deUint32 baseMipLevel;
535 1u, // deUint32 levelCount;
536 0u, // deUint32 baseArrayLayer;
537 1u // deUint32 layerCount;
538 } // VkImageSubresourceRange subresourceRange;
540 cbImagePass0View = createImageView(vk, device, &imageViewCreateInfo, NULL);
543 // Create color attachment for subpass 1
544 de::MovePtr<ImageWithMemory> cbImagePass1;
545 Move<VkImageView> cbImagePass1View;
547 const VkImageUsageFlags cbUsage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT |
548 VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
549 VK_IMAGE_USAGE_TRANSFER_DST_BIT;
551 const VkImageCreateInfo imageCreateInfo =
553 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType;
554 DE_NULL, // const void* pNext;
555 (VkImageCreateFlags)0u, // VkImageCreateFlags flags;
556 VK_IMAGE_TYPE_2D, // VkImageType imageType;
557 imageFormat, // VkFormat format;
559 m_data.framebufferExtent.width, // deUint32 width;
560 m_data.framebufferExtent.height, // deUint32 height;
561 1u // deUint32 depth;
562 }, // VkExtent3D extent;
563 1u, // deUint32 mipLevels;
564 1u, // deUint32 arrayLayers;
565 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples;
566 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling;
567 cbUsage, // VkImageUsageFlags usage;
568 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode;
569 0u, // deUint32 queueFamilyIndexCount;
570 DE_NULL, // const deUint32* pQueueFamilyIndices;
571 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout;
573 cbImagePass1 = de::MovePtr<ImageWithMemory>(new ImageWithMemory(
574 vk, device, *allocator, imageCreateInfo, MemoryRequirement::Any));
576 VkImageViewCreateInfo imageViewCreateInfo =
578 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType;
579 DE_NULL, // const void* pNext;
580 (VkImageViewCreateFlags)0u, // VkImageViewCreateFlags flags;
581 **cbImagePass1, // VkImage image;
582 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType;
583 imageFormat, // VkFormat format;
585 VK_COMPONENT_SWIZZLE_R, // VkComponentSwizzle r;
586 VK_COMPONENT_SWIZZLE_G, // VkComponentSwizzle g;
587 VK_COMPONENT_SWIZZLE_B, // VkComponentSwizzle b;
588 VK_COMPONENT_SWIZZLE_A // VkComponentSwizzle a;
589 }, // VkComponentMapping components;
591 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask;
592 0u, // deUint32 baseMipLevel;
593 1u, // deUint32 levelCount;
594 0u, // deUint32 baseArrayLayer;
595 1u // deUint32 layerCount;
596 } // VkImageSubresourceRange subresourceRange;
598 cbImagePass1View = createImageView(vk, device, &imageViewCreateInfo, NULL);
601 // Create render pass
602 Move<VkRenderPass> renderPass;
604 const vk::VkAttachmentReference colorAttachment0Reference =
607 vk::VK_IMAGE_LAYOUT_GENERAL, // layout
610 const vk::VkAttachmentReference colorAttachment1Reference =
613 vk::VK_IMAGE_LAYOUT_GENERAL, // layout
616 std::vector<VkAttachmentDescription> attachmentDescriptions;
618 attachmentDescriptions.push_back(
620 (VkAttachmentDescriptionFlags)0u, // VkAttachmentDescriptionFlags flags;
621 imageFormat, // VkFormat format;
622 m_data.samples, // VkSampleCountFlagBits samples;
623 VK_ATTACHMENT_LOAD_OP_LOAD, // VkAttachmentLoadOp loadOp;
624 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp;
625 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp;
626 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp;
627 VK_IMAGE_LAYOUT_GENERAL, // VkImageLayout initialLayout;
628 VK_IMAGE_LAYOUT_GENERAL // VkImageLayout finalLayout;
632 attachmentDescriptions.push_back(
634 (VkAttachmentDescriptionFlags)0u, // VkAttachmentDescriptionFlags flags;
635 imageFormat, // VkFormat format;
636 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples;
637 VK_ATTACHMENT_LOAD_OP_LOAD, // VkAttachmentLoadOp loadOp;
638 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp;
639 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp;
640 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp;
641 VK_IMAGE_LAYOUT_GENERAL, // VkImageLayout initialLayout;
642 VK_IMAGE_LAYOUT_GENERAL // VkImageLayout finalLayout;
646 const VkSubpassDescription subpassDescs[] =
649 (vk::VkSubpassDescriptionFlags)0, // flags
650 vk::VK_PIPELINE_BIND_POINT_GRAPHICS, // pipelineBindPoint
652 DE_NULL, // pInputAttachments
654 &colorAttachment0Reference, // pColorAttachments
655 DE_NULL, // pResolveAttachments
656 DE_NULL, // depthStencilAttachment
658 DE_NULL, // pPreserveAttachments
661 (vk::VkSubpassDescriptionFlags)0, // flags
662 vk::VK_PIPELINE_BIND_POINT_GRAPHICS, // pipelineBindPoint
664 &colorAttachment0Reference, // pInputAttachments
666 &colorAttachment1Reference, // pColorAttachments
667 DE_NULL, // pResolveAttachments
668 DE_NULL, // depthStencilAttachment
670 DE_NULL, // pPreserveAttachments
674 const VkSubpassDependency subpassDependency =
678 VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, // srcStageMask;
679 VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, // dstStageMask;
680 VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // srcAccessMask;
681 VK_ACCESS_INPUT_ATTACHMENT_READ_BIT, // dstAccessMask;
682 0 // dependencyFlags;
685 const VkRenderPassCreateInfo renderPassParams =
687 VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO, // sType
689 (vk::VkRenderPassCreateFlags)0,
690 (deUint32)attachmentDescriptions.size(), // attachmentCount
691 &attachmentDescriptions[0], // pAttachments
692 sizeof(subpassDescs) / sizeof(subpassDescs[0]), // subpassCount
693 subpassDescs, // pSubpasses
694 1u, // dependencyCount
695 &subpassDependency, // pDependencies
698 renderPass = createRenderPass(vk, device, &renderPassParams);
701 // Create framebuffer
702 Move<VkFramebuffer> framebuffer;
704 std::vector<VkImageView> attachments;
705 attachments.push_back(*cbImagePass0View);
706 attachments.push_back(*cbImagePass1View);
708 const vk::VkFramebufferCreateInfo framebufferParams =
710 vk::VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, // sType
712 (vk::VkFramebufferCreateFlags)(0), // createFlags
713 *renderPass, // renderPass
714 (deUint32)attachments.size(), // attachmentCount
715 &attachments[0], // pAttachments
716 m_data.framebufferExtent.width, // width
717 m_data.framebufferExtent.height, // height
721 framebuffer = createFramebuffer(vk, device, &framebufferParams);
725 // Create vertex attribute
726 const VkVertexInputBindingDescription vertexBinding =
728 0u, // deUint32 binding;
729 sizeof(Vertex), // deUint32 stride;
730 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputRate inputRate;
733 const VkVertexInputAttributeDescription vertexInputAttributeDescription =
735 0u, // deUint32 location;
736 0u, // deUint32 binding;
737 VK_FORMAT_R32G32_SFLOAT, // VkFormat format;
738 0u // deUint32 offset;
741 const VkPipelineVertexInputStateCreateInfo vertexInputStateCreateInfo =
743 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // VkStructureType sType;
744 DE_NULL, // const void* pNext;
745 (VkPipelineVertexInputStateCreateFlags)0, // VkPipelineVertexInputStateCreateFlags flags;
746 1u, // deUint32 vertexBindingDescriptionCount;
747 &vertexBinding, // const VkVertexInputBindingDescription* pVertexBindingDescriptions;
748 1u, // deUint32 vertexAttributeDescriptionCount;
749 &vertexInputAttributeDescription // const VkVertexInputAttributeDescription* pVertexAttributeDescriptions;
752 const VkPipelineInputAssemblyStateCreateInfo inputAssemblyStateCreateInfo =
754 VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO, // VkStructureType sType;
755 DE_NULL, // const void* pNext;
756 (VkPipelineInputAssemblyStateCreateFlags)0, // VkPipelineInputAssemblyStateCreateFlags flags;
757 VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST, // VkPrimitiveTopology topology;
758 VK_FALSE // VkBool32 primitiveRestartEnable;
761 // Create rasterization state
762 const VkPipelineRasterizationStateCreateInfo rasterizationStateCreateInfo =
764 VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO, // VkStructureType sType;
765 DE_NULL, // const void* pNext;
766 (VkPipelineRasterizationStateCreateFlags)0, // VkPipelineRasterizationStateCreateFlags flags;
767 VK_FALSE, // VkBool32 depthClampEnable;
768 VK_FALSE, // VkBool32 rasterizerDiscardEnable;
769 VK_POLYGON_MODE_FILL, // VkPolygonMode polygonMode;
770 VK_CULL_MODE_NONE, // VkCullModeFlags cullMode;
771 VK_FRONT_FACE_CLOCKWISE, // VkFrontFace frontFace;
772 VK_FALSE, // VkBool32 depthBiasEnable;
773 0.0f, // float depthBiasConstantFactor;
774 0.0f, // float depthBiasClamp;
775 0.0f, // float depthBiasSlopeFactor;
776 1.0f // float lineWidth;
779 // Create scissor and viewport
780 VkViewport viewport = makeViewport(m_data.framebufferExtent.width, m_data.framebufferExtent.height);
781 VkRect2D scissor = makeRect2D(m_data.framebufferExtent.width, m_data.framebufferExtent.height);
783 const VkPipelineViewportStateCreateInfo viewportStateCreateInfo =
785 VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO, // VkStructureType sType
786 DE_NULL, // const void* pNext
787 (VkPipelineViewportStateCreateFlags)0, // VkPipelineViewportStateCreateFlags flags
788 1u, // deUint32 viewportCount
789 &viewport, // const VkViewport* pViewports
790 1u, // deUint32 scissorCount
791 &scissor // const VkRect2D* pScissors
794 const VkPipelineDynamicStateCreateInfo dynamicStateCreateInfo =
796 VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO, // VkStructureType sType;
797 DE_NULL, // const void* pNext;
798 (VkPipelineDynamicStateCreateFlags)0, // VkPipelineDynamicStateCreateFlags flags;
799 0u, // uint32_t dynamicStateCount;
800 DE_NULL, // const VkDynamicState* pDynamicStates;
803 const VkPipelineColorBlendAttachmentState colorBlendAttachmentState[] =
806 VK_FALSE, // VkBool32 blendEnable;
807 VK_BLEND_FACTOR_ZERO, // VkBlendFactor srcColorBlendFactor;
808 VK_BLEND_FACTOR_ZERO, // VkBlendFactor dstColorBlendFactor;
809 VK_BLEND_OP_ADD, // VkBlendOp colorBlendOp;
810 VK_BLEND_FACTOR_ZERO, // VkBlendFactor srcAlphaBlendFactor;
811 VK_BLEND_FACTOR_ZERO, // VkBlendFactor dstAlphaBlendFactor;
812 VK_BLEND_OP_ADD, // VkBlendOp alphaBlendOp;
813 0xf // VkColorComponentFlags colorWriteMask;
817 const VkPipelineColorBlendStateCreateInfo colorBlendStateCreateInfo =
819 VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO, // VkStructureType sType;
820 DE_NULL, // const void* pNext;
821 0u, // VkPipelineColorBlendStateCreateFlags flags;
822 VK_FALSE, // VkBool32 logicOpEnable;
823 VK_LOGIC_OP_COPY, // VkLogicOp logicOp;
824 sizeof(colorBlendAttachmentState) / sizeof(colorBlendAttachmentState[0]), // deUint32 attachmentCount;
825 colorBlendAttachmentState, // const VkPipelineColorBlendAttachmentState* pAttachments;
826 { 1.0f, 1.0f, 1.0f, 1.0f } // float blendConstants[4];
829 VkPipelineDepthStencilStateCreateInfo depthStencilStateParams =
831 VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO, // VkStructureType sType;
832 DE_NULL, // const void* pNext;
833 0u, // VkPipelineDepthStencilStateCreateFlags flags;
834 VK_FALSE, // VkBool32 depthTestEnable;
835 VK_FALSE, // VkBool32 depthWriteEnable;
836 VK_COMPARE_OP_ALWAYS, // VkCompareOp depthCompareOp;
837 VK_FALSE, // VkBool32 depthBoundsTestEnable;
838 VK_FALSE, // VkBool32 stencilTestEnable;
839 // VkStencilOpState front;
841 VK_STENCIL_OP_REPLACE, // VkStencilOp failOp;
842 VK_STENCIL_OP_REPLACE, // VkStencilOp passOp;
843 VK_STENCIL_OP_REPLACE, // VkStencilOp depthFailOp;
844 VK_COMPARE_OP_ALWAYS, // VkCompareOp compareOp;
845 0u, // deUint32 compareMask;
846 0xFFu, // deUint32 writeMask;
847 0xFFu, // deUint32 reference;
849 // VkStencilOpState back;
851 VK_STENCIL_OP_REPLACE, // VkStencilOp failOp;
852 VK_STENCIL_OP_REPLACE, // VkStencilOp passOp;
853 VK_STENCIL_OP_REPLACE, // VkStencilOp depthFailOp;
854 VK_COMPARE_OP_ALWAYS, // VkCompareOp compareOp;
855 0u, // deUint32 compareMask;
856 0xFFu, // deUint32 writeMask;
857 0xFFu, // deUint32 reference;
859 0.0f, // float minDepthBounds;
860 0.0f, // float maxDepthBounds;
863 // Create pipeline for pass 0
864 Move<VkPipeline> pipelinePass0;
865 Move<VkPipelineLayout> pipelineLayoutPass0;
867 const VkPushConstantRange pushConstantRange =
869 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags;
870 0u, // deUint32 offset;
871 2 * sizeof(VkExtent2D) // deUint32 size;
874 const VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo =
876 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // sType
878 (VkPipelineLayoutCreateFlags)0,
879 0u, // setLayoutCount
880 DE_NULL, // pSetLayouts
881 1u, // pushConstantRangeCount
882 &pushConstantRange, // pPushConstantRanges
885 pipelineLayoutPass0 = createPipelineLayout(vk, device, &pipelineLayoutCreateInfo, NULL);
887 const VkPipelineMultisampleStateCreateInfo multisampleStateCreateInfo =
889 VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, // VkStructureType sType
890 DE_NULL, // const void* pNext
891 0u, // VkPipelineMultisampleStateCreateFlags flags
892 (VkSampleCountFlagBits)m_data.samples, // VkSampleCountFlagBits rasterizationSamples
893 VK_FALSE, // VkBool32 sampleShadingEnable
894 1.0f, // float minSampleShading
895 DE_NULL, // const VkSampleMask* pSampleMask
896 VK_FALSE, // VkBool32 alphaToCoverageEnable
897 VK_FALSE // VkBool32 alphaToOneEnable
900 Move<VkShaderModule> vertShader = createShaderModule(vk, device, m_context.getBinaryCollection().get("vert"), 0);
901 Move<VkShaderModule> fragShader = createShaderModule(vk, device, m_context.getBinaryCollection().get("frag_pass0"), 0);
903 const VkPipelineShaderStageCreateInfo shaderCreateInfo[] =
906 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
908 (VkPipelineShaderStageCreateFlags)0,
909 VK_SHADER_STAGE_VERTEX_BIT, // stage
910 *vertShader, // shader
912 DE_NULL, // pSpecializationInfo
915 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
917 (VkPipelineShaderStageCreateFlags)0,
918 VK_SHADER_STAGE_FRAGMENT_BIT, // stage
919 *fragShader, // shader
921 DE_NULL, // pSpecializationInfo
925 const VkGraphicsPipelineCreateInfo graphicsPipelineCreateInfo =
927 VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO, // VkStructureType sType;
928 DE_NULL, // const void* pNext;
929 (VkPipelineCreateFlags)0, // VkPipelineCreateFlags flags;
930 sizeof(shaderCreateInfo) / sizeof(shaderCreateInfo[0]), // deUint32 stageCount;
931 &shaderCreateInfo[0], // const VkPipelineShaderStageCreateInfo* pStages;
932 &vertexInputStateCreateInfo, // const VkPipelineVertexInputStateCreateInfo* pVertexInputState;
933 &inputAssemblyStateCreateInfo, // const VkPipelineInputAssemblyStateCreateInfo* pInputAssemblyState;
934 DE_NULL, // const VkPipelineTessellationStateCreateInfo* pTessellationState;
935 &viewportStateCreateInfo, // const VkPipelineViewportStateCreateInfo* pViewportState;
936 &rasterizationStateCreateInfo, // const VkPipelineRasterizationStateCreateInfo* pRasterizationState;
937 &multisampleStateCreateInfo, // const VkPipelineMultisampleStateCreateInfo* pMultisampleState;
938 &depthStencilStateParams, // const VkPipelineDepthStencilStateCreateInfo* pDepthStencilState;
939 &colorBlendStateCreateInfo, // const VkPipelineColorBlendStateCreateInfo* pColorBlendState;
940 &dynamicStateCreateInfo, // const VkPipelineDynamicStateCreateInfo* pDynamicState;
941 pipelineLayoutPass0.get(), // VkPipelineLayout layout;
942 renderPass.get(), // VkRenderPass renderPass;
943 0u, // deUint32 subpass;
944 DE_NULL, // VkPipeline basePipelineHandle;
945 0 // int basePipelineIndex;
948 pipelinePass0 = createGraphicsPipeline(vk, device, DE_NULL, &graphicsPipelineCreateInfo);
952 // Create pipeline for pass 1
953 Move<VkPipeline> pipelinePass1;
954 Move<VkPipelineLayout> pipelineLayoutPass1;
955 Move<vk::VkDescriptorPool> descriptorPool;
956 Move<vk::VkDescriptorSetLayout> descriptorSetLayout;
957 Move<vk::VkDescriptorSet> descriptorSet;
959 const VkDescriptorSetLayoutBinding bindings[] =
963 VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, // descriptorType
964 1u, // descriptorCount
965 VK_SHADER_STAGE_FRAGMENT_BIT, // stageFlags
966 DE_NULL, // pImmutableSamplers
970 // Create a layout and allocate a descriptor set for it.
971 const VkDescriptorSetLayoutCreateInfo setLayoutCreateInfo =
973 vk::VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // sType
975 (VkDescriptorSetLayoutCreateFlags)(0), // flags
976 sizeof(bindings) / sizeof(bindings[0]), // bindingCount
977 &bindings[0] // pBindings
980 descriptorSetLayout = vk::createDescriptorSetLayout(vk, device, &setLayoutCreateInfo);
982 vk::DescriptorPoolBuilder poolBuilder;
984 for (deInt32 i = 0; i < (deInt32)(sizeof(bindings) / sizeof(bindings[0])); ++i)
986 poolBuilder.addType(bindings[i].descriptorType, bindings[i].descriptorCount);
989 descriptorPool = poolBuilder.build(vk, device, VK_DESCRIPTOR_POOL_CREATE_FREE_DESCRIPTOR_SET_BIT, 1u);
990 descriptorSet = makeDescriptorSet(vk, device, *descriptorPool, *descriptorSetLayout);
992 VkDescriptorImageInfo imageInfo = makeDescriptorImageInfo(DE_NULL, *cbImagePass0View, VK_IMAGE_LAYOUT_GENERAL);
994 VkWriteDescriptorSet writeDescriptorSet =
996 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // sType
998 *descriptorSet, // dstSet
1000 0u, // dstArrayElement
1001 1u, // descriptorCount
1002 bindings[0].descriptorType, // descriptorType
1003 &imageInfo, // pImageInfo
1004 DE_NULL, // pBufferInfo
1005 DE_NULL, // pTexelBufferView
1008 vk.updateDescriptorSets(device, 1, &writeDescriptorSet, 0, NULL);
1010 const VkPipelineLayoutCreateInfo pipelineLayoutCreateInfo =
1012 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // sType
1014 (VkPipelineLayoutCreateFlags)0,
1015 1u, // setLayoutCount
1016 &descriptorSetLayout.get(), // pSetLayouts
1017 0u, // pushConstantRangeCount
1018 DE_NULL, // pPushConstantRanges
1021 pipelineLayoutPass1 = createPipelineLayout(vk, device, &pipelineLayoutCreateInfo, NULL);
1023 const VkPipelineMultisampleStateCreateInfo multisampleStateCreateInfo =
1025 VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, // VkStructureType sType
1026 DE_NULL, // const void* pNext
1027 0u, // VkPipelineMultisampleStateCreateFlags flags
1028 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits rasterizationSamples
1029 VK_FALSE, // VkBool32 sampleShadingEnable
1030 1.0f, // float minSampleShading
1031 DE_NULL, // const VkSampleMask* pSampleMask
1032 VK_FALSE, // VkBool32 alphaToCoverageEnable
1033 VK_FALSE // VkBool32 alphaToOneEnable
1036 VkPipelineFragmentShadingRateStateCreateInfoKHR shadingRateStateCreateInfo =
1038 VK_STRUCTURE_TYPE_PIPELINE_FRAGMENT_SHADING_RATE_STATE_CREATE_INFO_KHR, // VkStructureType sType;
1039 DE_NULL, // const void* pNext;
1040 m_data.shadingRate, // VkExtent2D fragmentSize;
1041 { VK_FRAGMENT_SHADING_RATE_COMBINER_OP_KEEP_KHR, VK_FRAGMENT_SHADING_RATE_COMBINER_OP_KEEP_KHR }, // VkFragmentShadingRateCombinerOpKHR combinerOps[2];
1044 Move<VkShaderModule> vertShader = createShaderModule(vk, device, m_context.getBinaryCollection().get("vert"), 0);
1045 Move<VkShaderModule> fragShader = createShaderModule(vk, device, m_context.getBinaryCollection().get("frag_pass1"), 0);
1047 const VkPipelineShaderStageCreateInfo shaderCreateInfo[] =
1050 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
1052 (VkPipelineShaderStageCreateFlags)0,
1053 VK_SHADER_STAGE_VERTEX_BIT, // stage
1054 *vertShader, // shader
1056 DE_NULL, // pSpecializationInfo
1059 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
1061 (VkPipelineShaderStageCreateFlags)0,
1062 VK_SHADER_STAGE_FRAGMENT_BIT, // stage
1063 *fragShader, // shader
1065 DE_NULL, // pSpecializationInfo
1069 const VkGraphicsPipelineCreateInfo graphicsPipelineCreateInfo =
1071 VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO, // VkStructureType sType;
1072 &shadingRateStateCreateInfo, // const void* pNext;
1073 (VkPipelineCreateFlags)0, // VkPipelineCreateFlags flags;
1074 sizeof(shaderCreateInfo) / sizeof(shaderCreateInfo[0]), // deUint32 stageCount;
1075 &shaderCreateInfo[0], // const VkPipelineShaderStageCreateInfo* pStages;
1076 &vertexInputStateCreateInfo, // const VkPipelineVertexInputStateCreateInfo* pVertexInputState;
1077 &inputAssemblyStateCreateInfo, // const VkPipelineInputAssemblyStateCreateInfo* pInputAssemblyState;
1078 DE_NULL, // const VkPipelineTessellationStateCreateInfo* pTessellationState;
1079 &viewportStateCreateInfo, // const VkPipelineViewportStateCreateInfo* pViewportState;
1080 &rasterizationStateCreateInfo, // const VkPipelineRasterizationStateCreateInfo* pRasterizationState;
1081 &multisampleStateCreateInfo, // const VkPipelineMultisampleStateCreateInfo* pMultisampleState;
1082 &depthStencilStateParams, // const VkPipelineDepthStencilStateCreateInfo* pDepthStencilState;
1083 &colorBlendStateCreateInfo, // const VkPipelineColorBlendStateCreateInfo* pColorBlendState;
1084 &dynamicStateCreateInfo, // const VkPipelineDynamicStateCreateInfo* pDynamicState;
1085 pipelineLayoutPass1.get(), // VkPipelineLayout layout;
1086 renderPass.get(), // VkRenderPass renderPass;
1087 1u, // deUint32 subpass;
1088 DE_NULL, // VkPipeline basePipelineHandle;
1089 0 // int basePipelineIndex;
1092 pipelinePass1 = createGraphicsPipeline(vk, device, DE_NULL, &graphicsPipelineCreateInfo);
1095 // Create command buffer
1096 Move<VkCommandPool> cmdPool = createCommandPool(vk, device, VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT, m_context.getUniversalQueueFamilyIndex());
1097 Move<VkCommandBuffer> cmdBuffer = allocateCommandBuffer(vk, device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY);
1099 VkImageMemoryBarrier preImageBarrier =
1101 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType
1102 DE_NULL, // const void* pNext
1103 0u, // VkAccessFlags srcAccessMask
1104 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags dstAccessMask
1105 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout oldLayout
1106 VK_IMAGE_LAYOUT_GENERAL, // VkImageLayout newLayout
1107 VK_QUEUE_FAMILY_IGNORED, // uint32_t srcQueueFamilyIndex
1108 VK_QUEUE_FAMILY_IGNORED, // uint32_t dstQueueFamilyIndex
1109 **cbImagePass0, // VkImage image
1111 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask
1112 0u, // uint32_t baseMipLevel
1113 VK_REMAINING_MIP_LEVELS, // uint32_t mipLevels,
1114 0u, // uint32_t baseArray
1115 VK_REMAINING_ARRAY_LAYERS, // uint32_t arraySize
1120 beginCommandBuffer(vk, *cmdBuffer, 0u);
1122 vk.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT,
1123 (VkDependencyFlags)0,
1124 0, (const VkMemoryBarrier*)DE_NULL,
1125 0, (const VkBufferMemoryBarrier*)DE_NULL,
1126 1, &preImageBarrier);
1128 preImageBarrier.image = **cbImagePass1;
1130 vk.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT,
1131 (VkDependencyFlags)0,
1132 0, (const VkMemoryBarrier*)DE_NULL,
1133 0, (const VkBufferMemoryBarrier*)DE_NULL,
1134 1, &preImageBarrier);
1136 // Clear both images to UINT_MAX
1137 VkImageSubresourceRange range = makeImageSubresourceRange(VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u);
1138 VkClearValue clearColor = makeClearValueColorU32(std::numeric_limits<unsigned int>::max(),0,0,0);
1140 vk.cmdClearColorImage(*cmdBuffer, **cbImagePass0, VK_IMAGE_LAYOUT_GENERAL, &clearColor.color, 1, &range);
1141 vk.cmdClearColorImage(*cmdBuffer, **cbImagePass1, VK_IMAGE_LAYOUT_GENERAL, &clearColor.color, 1, &range);
1143 beginRenderPass(vk, *cmdBuffer, *renderPass, *framebuffer,
1144 makeRect2D(m_data.framebufferExtent.width, m_data.framebufferExtent.height),
1145 0, DE_NULL, VK_SUBPASS_CONTENTS_INLINE, DE_NULL);
1147 // Put primitive shading rate in a push constant
1148 if (m_shadingRateClamped.size() == 1)
1150 vk.cmdPushConstants(*cmdBuffer, *pipelineLayoutPass0, VK_SHADER_STAGE_FRAGMENT_BIT, 0, sizeof(m_shadingRateClamped[0]), &m_shadingRateClamped[0]);
1151 vk.cmdPushConstants(*cmdBuffer, *pipelineLayoutPass0, VK_SHADER_STAGE_FRAGMENT_BIT, sizeof(m_shadingRateClamped[0]), sizeof(m_shadingRateClamped[0]), &m_shadingRateClamped[0]);
1155 vk.cmdPushConstants(*cmdBuffer, *pipelineLayoutPass0, VK_SHADER_STAGE_FRAGMENT_BIT, 0, static_cast<deUint32>(m_shadingRateClamped.size() * sizeof(m_shadingRateClamped[0])), &m_shadingRateClamped[0]);
1158 // Bind vertex buffer
1159 const VkDeviceSize vertexBufferOffset = 0;
1160 VkBuffer vb = **vertexBuffer;
1161 vk.cmdBindVertexBuffers(*cmdBuffer, 0, 1, &vb, &vertexBufferOffset);
1164 vk.cmdBindPipeline(*cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *pipelinePass0);
1167 vk.cmdDraw(*cmdBuffer, sizeof(basicTriangles) / sizeof(Vertex), 1u, 0u, 0u);
1169 // Start next subpass
1170 vk.cmdNextSubpass(*cmdBuffer, VK_SUBPASS_CONTENTS_INLINE);
1173 vk.cmdBindDescriptorSets(*cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *pipelineLayoutPass1, 0, 1, &descriptorSet.get(), 0, DE_NULL);
1175 // Bind vertex buffer
1176 vk.cmdBindVertexBuffers(*cmdBuffer, 0, 1, &vb, &vertexBufferOffset);
1179 vk.cmdBindPipeline(*cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *pipelinePass1);
1182 vk.cmdDraw(*cmdBuffer, sizeof(basicTriangles) / sizeof(Vertex), 1u, 0u, 0u);
1184 endRenderPass(vk, *cmdBuffer);
1186 VkImageMemoryBarrier postImageBarrier =
1188 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType
1189 DE_NULL, // const void* pNext
1190 VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // VkAccessFlags srcAccessMask
1191 VK_ACCESS_TRANSFER_READ_BIT, // VkAccessFlags dstAccessMask
1192 VK_IMAGE_LAYOUT_GENERAL, // VkImageLayout oldLayout
1193 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, // VkImageLayout newLayout
1194 VK_QUEUE_FAMILY_IGNORED, // uint32_t srcQueueFamilyIndex
1195 VK_QUEUE_FAMILY_IGNORED, // uint32_t dstQueueFamilyIndex
1196 **cbImagePass1, // VkImage image
1198 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspectMask
1199 0u, // uint32_t baseMipLevel
1200 VK_REMAINING_MIP_LEVELS, // uint32_t mipLevels,
1201 0u, // uint32_t baseArray
1202 VK_REMAINING_ARRAY_LAYERS, // uint32_t arraySize
1206 vk.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &postImageBarrier);
1208 const VkBufferImageCopy copyRegion =
1210 0u, // VkDeviceSize bufferOffset;
1211 0u, // deUint32 bufferRowLength;
1212 0u, // deUint32 bufferImageHeight;
1214 VK_IMAGE_ASPECT_COLOR_BIT, // VkImageAspectFlags aspect;
1215 0u, // deUint32 mipLevel;
1216 0u, // deUint32 baseArrayLayer;
1217 1u, // deUint32 layerCount;
1218 }, // VkImageSubresourceLayers imageSubresource;
1219 { 0, 0, 0 }, // VkOffset3D imageOffset;
1220 {m_data.framebufferExtent.width, m_data.framebufferExtent.height, 1} // VkExtent3D imageExtent;
1224 vk.cmdCopyImageToBuffer(*cmdBuffer, **cbImagePass1, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, **colorOutputBuffer, 1u, ©Region);
1226 const VkBufferMemoryBarrier bufferBarrier =
1228 VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER, // VkStructureType sType;
1229 DE_NULL, // const void* pNext;
1230 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags srcAccessMask;
1231 VK_ACCESS_HOST_READ_BIT, // VkAccessFlags dstAccessMask;
1232 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex;
1233 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex;
1234 **colorOutputBuffer, // VkBuffer buffer;
1235 0ull, // VkDeviceSize offset;
1236 VK_WHOLE_SIZE // VkDeviceSize size;
1239 vk.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_HOST_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 1, &bufferBarrier, 0, (const VkImageMemoryBarrier*)DE_NULL);
1241 endCommandBuffer(vk, *cmdBuffer);
1243 submitCommandsAndWait(vk, device, queue, cmdBuffer.get());
1246 invalidateAlloc(vk, device, colorOutputBuffer->getAllocation());
1248 tcu::ConstPixelBufferAccess resultBuffer = tcu::ConstPixelBufferAccess(
1249 tcu::TextureFormat(tcu::TextureFormat::RG, tcu::TextureFormat::UNSIGNED_INT32),
1250 m_data.framebufferExtent.width, m_data.framebufferExtent.height, 1, (const void *)colorOutputBuffer->getAllocation().getHostPtr());
1252 for (deUint32 i = 0; i < m_shadingRateClamped.size(); i++)
1254 tcu::TestStatus result = verifyResult(resultBuffer, i);
1255 if (result.getCode() == QP_TEST_RESULT_PASS)
1261 return tcu::TestStatus(QP_TEST_RESULT_FAIL, qpGetTestResultName(QP_TEST_RESULT_FAIL));
1266 void createPixelConsistencyTests(tcu::TestContext& testCtx, tcu::TestCaseGroup* parentGroup)
1272 const char* description;
1279 const char* description;
1282 TestGroupCase2D shadingRateCases[] =
1284 { {1, 1}, "rate_1x1", "1x1 shading rate" },
1285 { {1, 2}, "rate_1x2", "1x2 shading rate" },
1286 { {1, 4}, "rate_1x4", "1x4 shading rate" },
1287 { {2, 1}, "rate_2x1", "2x1 shading rate" },
1288 { {2, 2}, "rate_2x2", "2x2 shading rate" },
1289 { {2, 4}, "rate_2x4", "2x4 shading rate" },
1290 { {4, 1}, "rate_4x1", "4x1 shading rate" },
1291 { {4, 2}, "rate_4x2", "4x2 shading rate" },
1292 { {4, 4}, "rate_4x4", "4x4 shading rate" },
1295 TestGroupCase sampCases[] =
1297 { VK_SAMPLE_COUNT_1_BIT, "samples_1", "1 raster sample" },
1298 { VK_SAMPLE_COUNT_2_BIT, "samples_2", "2 raster samples" },
1299 { VK_SAMPLE_COUNT_4_BIT, "samples_4", "4 raster samples" },
1300 { VK_SAMPLE_COUNT_8_BIT, "samples_8", "8 raster samples" },
1301 { VK_SAMPLE_COUNT_16_BIT, "samples_16", "16 raster samples" },
1304 TestGroupCase2D extentCases[] =
1306 { {1, 1}, "extent_1x1", "framebuffer size 1x1" },
1307 { {4, 4}, "extent_4x4", "framebuffer size 4x4" },
1308 { {33, 35}, "extent_33x35", "framebuffer size 33x35" },
1309 { {151, 431}, "extent_151x431", "framebuffer size 151x431" },
1310 { {256, 256}, "extent_256x256", "framebuffer size 256x256" },
1313 de::MovePtr<tcu::TestCaseGroup> pixelGroup(new tcu::TestCaseGroup(testCtx, "pixel_consistency", "Pixel selection consistency"));
1315 for (int rateNdx = 0; rateNdx < DE_LENGTH_OF_ARRAY(shadingRateCases); rateNdx++)
1317 de::MovePtr<tcu::TestCaseGroup> rateGroup(new tcu::TestCaseGroup(testCtx, shadingRateCases[rateNdx].name, shadingRateCases[rateNdx].description));
1319 for (int sampNdx = 0; sampNdx < DE_LENGTH_OF_ARRAY(sampCases); sampNdx++)
1321 de::MovePtr<tcu::TestCaseGroup> sampleGroup(new tcu::TestCaseGroup(testCtx, sampCases[sampNdx].name, sampCases[sampNdx].description));
1323 for (int extNdx = 0; extNdx < DE_LENGTH_OF_ARRAY(extentCases); extNdx++)
1327 shadingRateCases[rateNdx].count,
1328 (VkSampleCountFlagBits)sampCases[sampNdx].count,
1329 extentCases[extNdx].count
1332 sampleGroup->addChild(new FSRPixelConsistencyTestCase(testCtx, extentCases[extNdx].name, extentCases[extNdx].description, c));
1335 rateGroup->addChild(sampleGroup.release());
1338 pixelGroup->addChild(rateGroup.release());
1341 parentGroup->addChild(pixelGroup.release());
1344 } // FragmentShadingRage