1/*------------------------------------------------------------------------ 2 * Vulkan Conformance Tests 3 * ------------------------ 4 * 5 * Copyright (c) 2018 The Khronos Group Inc. 6 * Copyright (c) 2018 Google Inc. 7 * Copyright (c) 2018 ARM Limited. 8 * Copyright (c) 2023 LunarG, Inc. 9 * Copyright (c) 2023 Nintendo 10 * 11 * Licensed under the Apache License, Version 2.0 (the "License"); 12 * you may not use this file except in compliance with the License. 13 * You may obtain a copy of the License at 14 * 15 * http://www.apache.org/licenses/LICENSE-2.0 16 * 17 * Unless required by applicable law or agreed to in writing, software 18 * distributed under the License is distributed on an "AS IS" BASIS, 19 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 20 * See the License for the specific language governing permissions and 21 * limitations under the License. 22 * 23 *//*! 24 * \file 25 * \brief Push Descriptor Tests 26 *//*--------------------------------------------------------------------*/ 27 28#include "vktPipelinePushDescriptorTests.hpp" 29#include "vktPipelineClearUtil.hpp" 30#include "vktPipelineImageUtil.hpp" 31#include "vktPipelineVertexUtil.hpp" 32#include "vktPipelineReferenceRenderer.hpp" 33#include "vktTestCase.hpp" 34#include "vktCustomInstancesDevices.hpp" 35#include "vkImageUtil.hpp" 36#include "vkMemUtil.hpp" 37#include "vkPrograms.hpp" 38#include "vkQueryUtil.hpp" 39#include "vkRef.hpp" 40#include "vkRefUtil.hpp" 41#include "vkTypeUtil.hpp" 42#include "vkCmdUtil.hpp" 43#include "vkObjUtil.hpp" 44#include "vkDeviceUtil.hpp" 45#include "tcuImageCompare.hpp" 46#include "deMemory.h" 47#include "deUniquePtr.hpp" 48#include "tcuTestLog.hpp" 49#include "tcuCommandLine.hpp" 50#include <vector> 51 52namespace vkt 53{ 54namespace pipeline 55{ 56 57using namespace vk; 58using namespace std; 59 60namespace 61{ 62typedef vector<VkExtensionProperties> Extensions; 63typedef de::SharedPtr<Unique<VkBuffer> > VkBufferSp; 64typedef de::SharedPtr<Unique<VkImage> > VkImageSp; 65typedef de::SharedPtr<Unique<VkImageView> > VkImageViewSp; 66typedef de::SharedPtr<Unique<VkBufferView> > VkBufferViewSp; 67typedef de::SharedPtr<Allocation> AllocationSp; 68typedef de::SharedPtr<RenderPassWrapper> VkRenderPassSp; 69 70constexpr VkDeviceSize kSizeofVec4 = static_cast<VkDeviceSize>(sizeof(tcu::Vec4)); 71 72struct TestParams 73{ 74 PipelineConstructionType pipelineConstructionType; // Used only by graphics pipeline tests 75 VkDescriptorType descriptorType; 76 deUint32 binding; 77 deUint32 numCalls; // Number of draw or dispatch calls 78 bool useMaintenance5; 79}; 80 81VkDeviceSize calcItemSize (const InstanceInterface& vki, VkPhysicalDevice physicalDevice, deUint32 numElements = 1u) 82{ 83 const auto minAlignment = getPhysicalDeviceProperties(vki, physicalDevice).limits.minStorageBufferOffsetAlignment; 84 const auto lcm = de::lcm(de::max(VkDeviceSize{1}, minAlignment), kSizeofVec4); 85 return de::roundUp(kSizeofVec4 * numElements, lcm); 86} 87 88void checkAllSupported (const Extensions& supportedExtensions, const vector<string>& requiredExtensions) 89{ 90 for (auto& requiredExtName : requiredExtensions) 91 { 92 if (!isExtensionStructSupported(supportedExtensions, RequiredExtension(requiredExtName))) 93 TCU_THROW(NotSupportedError, (requiredExtName + " is not supported").c_str()); 94 } 95} 96 97CustomInstance createInstanceWithGetPhysicalDeviceProperties2 (Context& context, 98 const Extensions& supportedExtensions) 99{ 100 vector<string> requiredExtensions = { "VK_KHR_get_physical_device_properties2" }; 101 checkAllSupported(supportedExtensions, requiredExtensions); 102 103 return createCustomInstanceWithExtensions(context, requiredExtensions); 104} 105 106const char *innerCString(const string &str) 107{ 108 return str.c_str(); 109} 110 111Move<VkDevice> createDeviceWithPushDescriptor (const Context& context, 112 const PlatformInterface& vkp, 113 VkInstance instance, 114 const InstanceInterface& vki, 115 VkPhysicalDevice physicalDevice, 116 const Extensions& supportedExtensions, 117 const deUint32 queueFamilyIndex, 118 const TestParams& params, 119 std::vector<std::string>& enabledExtensions) 120{ 121 122 const float queuePriority = 1.0f; 123 const VkDeviceQueueCreateInfo queueInfo = 124 { 125 VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO, 126 DE_NULL, 127 (VkDeviceQueueCreateFlags)0, 128 queueFamilyIndex, 129 1u, 130 &queuePriority 131 }; 132 133 VkPhysicalDeviceFeatures features; 134 deMemset(&features, 0, sizeof(features)); 135 136 vector<string> requiredExtensionsStr = { "VK_KHR_push_descriptor" }; 137 VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT graphicsPipelineLibraryFeaturesEXT = initVulkanStructure(); 138 VkPhysicalDeviceDynamicRenderingFeaturesKHR dynamicRenderingFeaturesKHR = initVulkanStructure(&graphicsPipelineLibraryFeaturesEXT); 139 VkPhysicalDeviceShaderObjectFeaturesEXT shaderObjectFeaturesEXT = initVulkanStructure(&dynamicRenderingFeaturesKHR); 140 VkPhysicalDeviceFeatures2 features2 = initVulkanStructure(&shaderObjectFeaturesEXT); 141 if (isConstructionTypeLibrary(params.pipelineConstructionType)) 142 { 143 requiredExtensionsStr.push_back("VK_KHR_pipeline_library"); 144 requiredExtensionsStr.push_back("VK_EXT_graphics_pipeline_library"); 145 vki.getPhysicalDeviceFeatures2(physicalDevice, &features2); 146 if (!graphicsPipelineLibraryFeaturesEXT.graphicsPipelineLibrary) 147 TCU_THROW(NotSupportedError, "graphicsPipelineLibraryFeaturesEXT.graphicsPipelineLibrary required"); 148 } 149 else if (isConstructionTypeShaderObject(params.pipelineConstructionType)) 150 { 151 requiredExtensionsStr.push_back("VK_EXT_shader_object"); 152 vki.getPhysicalDeviceFeatures2(physicalDevice, &features2); 153 if (!shaderObjectFeaturesEXT.shaderObject) 154 TCU_THROW(NotSupportedError, "shaderObjectFeaturesEXT.shaderObject required"); 155 } 156 vector<const char *> requiredExtensions; 157 checkAllSupported(supportedExtensions, requiredExtensionsStr); 158 // We need the contents of requiredExtensionsStr as a vector<const char*> in VkDeviceCreateInfo. 159 transform(begin(requiredExtensionsStr), end(requiredExtensionsStr), back_inserter(requiredExtensions), innerCString); 160 161 // Enable validation layers on this device if validation has been requested from the command line. 162 const VkDeviceCreateInfo deviceParams = 163 { 164 VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO, 165 params.pipelineConstructionType != PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC ? &features2 : DE_NULL, 166 (VkDeviceCreateFlags)0, 167 1u, 168 &queueInfo, 169 0u, 170 DE_NULL, 171 static_cast<deUint32>(requiredExtensions.size()), 172 (requiredExtensions.empty() ? DE_NULL : requiredExtensions.data()), 173 params.pipelineConstructionType != PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC ? DE_NULL : &features 174 }; 175 176 for (const auto& enabledExt : requiredExtensions) 177 enabledExtensions.push_back(enabledExt); 178 179 return createCustomDevice(context.getTestContext().getCommandLine().isValidationEnabled(), vkp, instance, vki, physicalDevice, &deviceParams, DE_NULL); 180} 181 182vector<Vertex4RGBA> createQuads (deUint32 numQuads, float size) 183{ 184 vector<Vertex4RGBA> vertices; 185 186 for (deUint32 quadNdx = 0; quadNdx < numQuads; quadNdx++) 187 { 188 const float xOffset = -0.5f + (float)quadNdx; 189 const tcu::Vec4 color (0.0f); 190 const Vertex4RGBA lowerLeftVertex = {tcu::Vec4(-size + xOffset, -size, 0.0f, 1.0f), color}; 191 const Vertex4RGBA lowerRightVertex = {tcu::Vec4(size + xOffset, -size, 0.0f, 1.0f), color}; 192 const Vertex4RGBA UpperLeftVertex = {tcu::Vec4(-size + xOffset, size, 0.0f, 1.0f), color}; 193 const Vertex4RGBA UpperRightVertex = {tcu::Vec4(size + xOffset, size, 0.0f, 1.0f), color}; 194 195 vertices.push_back(lowerLeftVertex); 196 vertices.push_back(lowerRightVertex); 197 vertices.push_back(UpperLeftVertex); 198 vertices.push_back(UpperLeftVertex); 199 vertices.push_back(lowerRightVertex); 200 vertices.push_back(UpperRightVertex); 201 } 202 203 return vertices; 204} 205 206vector<Vertex4Tex4> createTexQuads (deUint32 numQuads, float size) 207{ 208 vector<Vertex4Tex4> vertices; 209 210 for (deUint32 quadNdx = 0; quadNdx < numQuads; quadNdx++) 211 { 212 const float xOffset = -0.5f + (float)quadNdx; 213 const Vertex4Tex4 lowerLeftVertex = {tcu::Vec4(-size + xOffset, -size, 0.0f, 1.0f), tcu::Vec4(-0.2f, -0.2f, 0.0f, 0.0f)}; 214 const Vertex4Tex4 lowerRightVertex = {tcu::Vec4(size + xOffset, -size, 0.0f, 1.0f), tcu::Vec4(1.2f, -0.2f, 0.0f, 0.0f)}; 215 const Vertex4Tex4 UpperLeftVertex = {tcu::Vec4(-size + xOffset, size, 0.0f, 1.0f), tcu::Vec4(-0.2f, 1.2f, 0.0f, 0.0f)}; 216 const Vertex4Tex4 UpperRightVertex = {tcu::Vec4(size + xOffset, size, 0.0f, 1.0f), tcu::Vec4(1.2f, 1.2f, 0.0f, 0.0f)}; 217 218 vertices.push_back(lowerLeftVertex); 219 vertices.push_back(lowerRightVertex); 220 vertices.push_back(UpperLeftVertex); 221 vertices.push_back(UpperLeftVertex); 222 vertices.push_back(lowerRightVertex); 223 vertices.push_back(UpperRightVertex); 224 } 225 226 return vertices; 227} 228 229static const tcu::Vec4 defaultTestColors[] = 230 231{ 232 tcu::Vec4(1.0f, 0.0f, 0.0f, 1.0f), 233 tcu::Vec4(0.0f, 1.0f, 0.0f, 1.0f) 234}; 235 236class PushDescriptorBufferGraphicsTestInstance : public vkt::TestInstance 237{ 238public: 239 PushDescriptorBufferGraphicsTestInstance (Context& context, const TestParams& params); 240 virtual ~PushDescriptorBufferGraphicsTestInstance (void); 241 void init (void); 242 virtual tcu::TestStatus iterate (void); 243 tcu::TestStatus verifyImage (void); 244 245private: 246 const TestParams m_params; 247 const PlatformInterface& m_vkp; 248 const Extensions m_instanceExtensions; 249 const CustomInstance m_instance; 250 const InstanceDriver& m_vki; 251 const VkPhysicalDevice m_physicalDevice; 252 const deUint32 m_queueFamilyIndex; 253 const Extensions m_deviceExtensions; 254 std::vector<std::string> m_deviceEnabledExtensions; 255 const Unique<VkDevice> m_device; 256 const DeviceDriver m_vkd; 257 const VkQueue m_queue; 258 SimpleAllocator m_allocator; 259 const tcu::UVec2 m_renderSize; 260 const VkFormat m_colorFormat; 261 Move<VkImage> m_colorImage; 262 de::MovePtr<Allocation> m_colorImageAlloc; 263 Move<VkImageView> m_colorAttachmentView; 264 RenderPassWrapper m_renderPass; 265 Move<VkFramebuffer> m_framebuffer; 266 ShaderWrapper m_vertexShaderModule; 267 ShaderWrapper m_fragmentShaderModule; 268 Move<VkBuffer> m_vertexBuffer; 269 de::MovePtr<Allocation> m_vertexBufferAlloc; 270 vector<VkBufferSp> m_buffers; 271 vector<AllocationSp> m_bufferAllocs; 272 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 273 PipelineLayoutWrapper m_preRasterizationStatePipelineLayout; 274 PipelineLayoutWrapper m_fragmentStatePipelineLayout; 275 GraphicsPipelineWrapper m_graphicsPipeline; 276 Move<VkCommandPool> m_cmdPool; 277 Move<VkCommandBuffer> m_cmdBuffer; 278 vector<Vertex4RGBA> m_vertices; 279}; 280 281PushDescriptorBufferGraphicsTestInstance::PushDescriptorBufferGraphicsTestInstance (Context& context, const TestParams& params) 282 : vkt::TestInstance (context) 283 , m_params (params) 284 , m_vkp (context.getPlatformInterface()) 285 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 286 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 287 , m_vki (m_instance.getDriver()) 288 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 289 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_GRAPHICS_BIT)) 290 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 291 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 292 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 293 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 294 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 295 , m_renderSize (32, 32) 296 , m_colorFormat (VK_FORMAT_R8G8B8A8_UNORM) 297 , m_graphicsPipeline (m_vki, m_vkd, m_physicalDevice, *m_device, m_deviceEnabledExtensions, params.pipelineConstructionType) 298 , m_vertices (createQuads(params.numCalls, 0.25f)) 299{ 300} 301 302void PushDescriptorBufferGraphicsTestInstance::init (void) 303{ 304 const VkComponentMapping componentMappingRGBA = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A }; 305 306 // Create color image 307 { 308 309 const VkImageCreateInfo colorImageParams = 310 { 311 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 312 DE_NULL, // const void* pNext; 313 0u, // VkImageCreateFlags flags; 314 VK_IMAGE_TYPE_2D, // VkImageType imageType; 315 m_colorFormat, // VkFormat format; 316 { m_renderSize.x(), m_renderSize.y(), 1u }, // VkExtent3D extent; 317 1u, // deUint32 mipLevels; 318 1u, // deUint32 arrayLayers; 319 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 320 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 321 VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT, // VkImageUsageFlags usage; 322 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 323 1u, // deUint32 queueFamilyIndexCount; 324 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 325 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout initialLayout; 326 }; 327 328 m_colorImage = createImage(m_vkd, *m_device, &colorImageParams); 329 330 // Allocate and bind color image memory 331 m_colorImageAlloc = m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, *m_colorImage), MemoryRequirement::Any); 332 VK_CHECK(m_vkd.bindImageMemory(*m_device, *m_colorImage, m_colorImageAlloc->getMemory(), m_colorImageAlloc->getOffset())); 333 } 334 335 // Create color attachment view 336 { 337 const VkImageViewCreateInfo colorAttachmentViewParams = 338 { 339 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 340 DE_NULL, // const void* pNext; 341 0u, // VkImageViewCreateFlags flags; 342 *m_colorImage, // VkImage image; 343 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 344 m_colorFormat, // VkFormat format; 345 componentMappingRGBA, // VkChannelMapping channels; 346 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u }, // VkImageSubresourceRange subresourceRange; 347 }; 348 349 m_colorAttachmentView = createImageView(m_vkd, *m_device, &colorAttachmentViewParams); 350 } 351 352 // Create render pass 353 m_renderPass = RenderPassWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, m_colorFormat); 354 355 // Create framebuffer 356 { 357 const VkImageView attachmentBindInfos[] = 358 { 359 *m_colorAttachmentView 360 }; 361 362 const VkFramebufferCreateInfo framebufferParams = 363 { 364 VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, // VkStructureType sType; 365 DE_NULL, // const void* pNext; 366 0u, // VkFramebufferCreateFlags flags; 367 *m_renderPass, // VkRenderPass renderPass; 368 1u, // deUint32 attachmentCount; 369 attachmentBindInfos, // const VkImageView* pAttachments; 370 (deUint32)m_renderSize.x(), // deUint32 width; 371 (deUint32)m_renderSize.y(), // deUint32 height; 372 1u // deUint32 layers; 373 }; 374 375 m_renderPass.createFramebuffer(m_vkd, *m_device, &framebufferParams, *m_colorImage); 376 } 377 378 // Create pipeline layout 379 { 380 // Create descriptor set layout 381 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 382 { 383 m_params.binding, // uint32_t binding; 384 m_params.descriptorType, // VkDescriptorType descriptorType; 385 1u, // uint32_t descriptorCount; 386 VK_SHADER_STAGE_VERTEX_BIT, // VkShaderStageFlags stageFlags; 387 DE_NULL // const VkSampler* pImmutableSamplers; 388 }; 389 390 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 391 { 392 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 393 DE_NULL, // const void* pNext; 394 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 395 1u, // uint32_t bindingCount; 396 &descriptorSetLayoutBinding // const VkDescriptorSetLayoutBinding* pBindings; 397 }; 398 399 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 400 401 // Create pipeline layout 402 VkPipelineLayoutCreateFlags pipelineLayoutFlags = (m_params.pipelineConstructionType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) ? 0u : deUint32(VK_PIPELINE_LAYOUT_CREATE_INDEPENDENT_SETS_BIT_EXT); 403 VkPipelineLayoutCreateInfo pipelineLayoutParams 404 { 405 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 406 DE_NULL, // const void* pNext; 407 pipelineLayoutFlags, // VkPipelineLayoutCreateFlags flags; 408 1u, // deUint32 setLayoutCount; 409 &(*m_descriptorSetLayout), // const VkDescriptorSetLayout* pSetLayouts; 410 0u, // deUint32 pushConstantRangeCount; 411 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 412 }; 413 414 m_preRasterizationStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 415 pipelineLayoutParams.setLayoutCount = 0u; 416 pipelineLayoutParams.pSetLayouts = DE_NULL; 417 m_fragmentStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 418 } 419 420 // Create buffers. One color value in each buffer. 421 { 422 VkBufferUsageFlags2CreateInfoKHR bufferUsageFlags2 = vk::initVulkanStructure(); 423 for (deUint32 bufIdx = 0; bufIdx < DE_LENGTH_OF_ARRAY(defaultTestColors); bufIdx++) 424 { 425 const VkBufferUsageFlags usageFlags = m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER ? VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT : VK_BUFFER_USAGE_STORAGE_BUFFER_BIT; 426 427 VkBufferCreateInfo bufferCreateInfo 428 { 429 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 430 DE_NULL, // const void* pNext; 431 0u, // VkBufferCreateFlags flags 432 kSizeofVec4, // VkDeviceSize size; 433 usageFlags, // VkBufferUsageFlags usage; 434 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 435 1u, // deUint32 queueFamilyCount; 436 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 437 }; 438 439 if (m_params.useMaintenance5) 440 { 441 bufferUsageFlags2.usage = (VkBufferUsageFlagBits2KHR)usageFlags; 442 bufferCreateInfo.pNext = &bufferUsageFlags2; 443 bufferCreateInfo.usage = 0; 444 } 445 446 m_buffers.push_back(VkBufferSp(new Unique<VkBuffer>(createBuffer(m_vkd, *m_device, &bufferCreateInfo)))); 447 m_bufferAllocs.push_back(AllocationSp(m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, **m_buffers[bufIdx]), MemoryRequirement::HostVisible).release())); 448 VK_CHECK(m_vkd.bindBufferMemory(*m_device, **m_buffers[bufIdx], m_bufferAllocs[bufIdx]->getMemory(), m_bufferAllocs[bufIdx]->getOffset())); 449 450 deMemcpy(m_bufferAllocs[bufIdx]->getHostPtr(), &defaultTestColors[bufIdx], static_cast<size_t>(kSizeofVec4)); 451 flushAlloc(m_vkd, *m_device, *m_bufferAllocs[bufIdx]); 452 } 453 } 454 455 // Create shaders 456 { 457 m_vertexShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("vert"), 0u); 458 m_fragmentShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("frag"), 0u); 459 } 460 461 // Create pipeline 462 { 463 const VkVertexInputBindingDescription vertexInputBindingDescription = 464 { 465 0u, // deUint32 binding; 466 sizeof(Vertex4RGBA), // deUint32 strideInBytes; 467 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputStepRate stepRate; 468 }; 469 470 const VkVertexInputAttributeDescription vertexInputAttributeDescriptions[] = 471 { 472 { 473 0u, // deUint32 location; 474 0u, // deUint32 binding; 475 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 476 0u // deUint32 offsetInBytes; 477 }, 478 { 479 1u, // deUint32 location; 480 0u, // deUint32 binding; 481 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 482 DE_OFFSET_OF(Vertex4RGBA, color), // deUint32 offset; 483 } 484 }; 485 486 const VkPipelineVertexInputStateCreateInfo vertexInputStateParams = 487 { 488 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // VkStructureType sType; 489 DE_NULL, // const void* pNext; 490 0u, // vkPipelineVertexInputStateCreateFlags flags; 491 1u, // deUint32 bindingCount; 492 &vertexInputBindingDescription, // const VkVertexInputBindingDescription* pVertexBindingDescriptions; 493 2u, // deUint32 attributeCount; 494 vertexInputAttributeDescriptions // const VkVertexInputAttributeDescription* pVertexAttributeDescriptions; 495 }; 496 497 const VkPrimitiveTopology topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST; 498 499 const vector<VkViewport> viewports { makeViewport(m_renderSize) }; 500 const vector<VkRect2D> scissors { makeRect2D(m_renderSize) }; 501 502 m_graphicsPipeline.setDefaultRasterizationState() 503 .setDefaultDepthStencilState() 504 .setDefaultMultisampleState() 505 .setDefaultColorBlendState() 506 .setDefaultTopology(topology) 507 .setupVertexInputState(&vertexInputStateParams) 508 .setupPreRasterizationShaderState(viewports, 509 scissors, 510 m_preRasterizationStatePipelineLayout, 511 *m_renderPass, 512 0u, 513 m_vertexShaderModule) 514 .setupFragmentShaderState(m_fragmentStatePipelineLayout, *m_renderPass, 0u, m_fragmentShaderModule) 515 .setupFragmentOutputState(*m_renderPass) 516 .setMonolithicPipelineLayout(m_preRasterizationStatePipelineLayout) 517 .buildPipeline(); 518 } 519 520 // Create vertex buffer 521 { 522 const VkBufferCreateInfo vertexBufferParams = 523 { 524 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 525 DE_NULL, // const void* pNext; 526 0u, // VkBufferCreateFlags flags; 527 (VkDeviceSize)(sizeof(Vertex4RGBA) * m_vertices.size()), // VkDeviceSize size; 528 VK_BUFFER_USAGE_VERTEX_BUFFER_BIT, // VkBufferUsageFlags usage; 529 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 530 1u, // deUint32 queueFamilyCount; 531 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 532 }; 533 534 m_vertexBuffer = createBuffer(m_vkd, *m_device, &vertexBufferParams); 535 m_vertexBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_vertexBuffer), MemoryRequirement::HostVisible); 536 537 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_vertexBuffer, m_vertexBufferAlloc->getMemory(), m_vertexBufferAlloc->getOffset())); 538 539 // Load vertices into vertex buffer 540 deMemcpy(m_vertexBufferAlloc->getHostPtr(), m_vertices.data(), m_vertices.size() * sizeof(Vertex4RGBA)); 541 flushAlloc(m_vkd, *m_device, *m_vertexBufferAlloc); 542 } 543 544 // Create command pool 545 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 546 547 // Create command buffer 548 { 549 const VkClearValue attachmentClearValue = defaultClearValue(m_colorFormat); 550 const VkDeviceSize vertexBufferOffset = 0; 551 552 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 553 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 554 m_renderPass.begin(m_vkd, *m_cmdBuffer, makeRect2D(0, 0, m_renderSize.x(), m_renderSize.y()), attachmentClearValue); 555 m_graphicsPipeline.bind(*m_cmdBuffer); 556 m_vkd.cmdBindVertexBuffers(*m_cmdBuffer, 0, 1, &m_vertexBuffer.get(), &vertexBufferOffset); 557 558 // Draw quads. Switch input buffer which contains the quad color for each draw call. 559 for (deUint32 quadNdx = 0; quadNdx < m_params.numCalls; quadNdx++) 560 { 561 VkDescriptorBufferInfo descriptorBufferInfo = 562 { 563 **m_buffers[quadNdx], // VkBuffer buffer; 564 0u, // VkDeviceSize offset; 565 kSizeofVec4, // VkDeviceSize range; 566 }; 567 568 VkWriteDescriptorSet writeDescriptorSet = 569 { 570 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 571 DE_NULL, // const void* pNext; 572 0u, // VkDescriptorSet dstSet; 573 m_params.binding, // uint32_t dstBinding; 574 0u, // uint32_t dstArrayElement; 575 1u, // uint32_t descriptorCount; 576 m_params.descriptorType, // VkDescriptorType descriptorType; 577 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 578 &descriptorBufferInfo, // const VkDescriptorBufferInfo* pBufferInfo; 579 DE_NULL // const VkBufferView* pTexelBufferView; 580 }; 581 582 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *m_preRasterizationStatePipelineLayout, 0, 1, &writeDescriptorSet); 583 m_vkd.cmdDraw(*m_cmdBuffer, 6, 1, 6 * quadNdx, 0); 584 } 585 586 m_renderPass.end(m_vkd, *m_cmdBuffer); 587 endCommandBuffer(m_vkd, *m_cmdBuffer); 588 } 589} 590 591PushDescriptorBufferGraphicsTestInstance::~PushDescriptorBufferGraphicsTestInstance (void) 592{ 593} 594 595tcu::TestStatus PushDescriptorBufferGraphicsTestInstance::iterate (void) 596{ 597 init(); 598 599 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 600 601 return verifyImage(); 602} 603 604tcu::TestStatus PushDescriptorBufferGraphicsTestInstance::verifyImage (void) 605{ 606 const tcu::TextureFormat tcuColorFormat = mapVkFormat(m_colorFormat); 607 const tcu::TextureFormat tcuDepthFormat = tcu::TextureFormat(); 608 const ColorVertexShader vertexShader; 609 const ColorFragmentShader fragmentShader (tcuColorFormat, tcuDepthFormat); 610 const rr::Program program (&vertexShader, &fragmentShader); 611 ReferenceRenderer refRenderer (m_renderSize.x(), m_renderSize.y(), 1, tcuColorFormat, tcuDepthFormat, &program); 612 bool compareOk = false; 613 614 // Render reference image 615 { 616 for (deUint32 quadIdx = 0; quadIdx < m_params.numCalls; quadIdx++) 617 for (deUint32 vertexIdx = 0; vertexIdx < 6; vertexIdx++) 618 m_vertices[quadIdx * 6 + vertexIdx].color.xyzw() = defaultTestColors[quadIdx]; 619 620 refRenderer.draw(rr::RenderState(refRenderer.getViewportState(), m_context.getDeviceProperties().limits.subPixelPrecisionBits), 621 rr::PRIMITIVETYPE_TRIANGLES, m_vertices); 622 } 623 624 // Compare result with reference image 625 { 626 de::MovePtr<tcu::TextureLevel> result = readColorAttachment(m_vkd, *m_device, m_queue, m_queueFamilyIndex, m_allocator, *m_colorImage, m_colorFormat, m_renderSize); 627 628 compareOk = tcu::intThresholdPositionDeviationCompare(m_context.getTestContext().getLog(), 629 "IntImageCompare", 630 "Image comparison", 631 refRenderer.getAccess(), 632 result->getAccess(), 633 tcu::UVec4(2, 2, 2, 2), 634 tcu::IVec3(1, 1, 0), 635 true, 636 tcu::COMPARE_LOG_RESULT); 637 } 638 639 if (compareOk) 640 return tcu::TestStatus::pass("Result image matches reference"); 641 else 642 return tcu::TestStatus::fail("Image mismatch"); 643} 644 645class PushDescriptorBufferGraphicsTest : public vkt::TestCase 646{ 647public: 648 PushDescriptorBufferGraphicsTest (tcu::TestContext& testContext, 649 const string& name, 650 const TestParams& params); 651 ~PushDescriptorBufferGraphicsTest (void); 652 void checkSupport (Context& context) const; 653 void initPrograms (SourceCollections& sourceCollections) const; 654 TestInstance* createInstance (Context& context) const; 655 656protected: 657 const TestParams m_params; 658}; 659 660PushDescriptorBufferGraphicsTest::PushDescriptorBufferGraphicsTest (tcu::TestContext& testContext, 661 const string& name, 662 const TestParams& params) 663 : vkt::TestCase (testContext, name) 664 , m_params (params) 665{ 666} 667 668PushDescriptorBufferGraphicsTest::~PushDescriptorBufferGraphicsTest (void) 669{ 670} 671 672TestInstance* PushDescriptorBufferGraphicsTest::createInstance (Context& context) const 673{ 674 return new PushDescriptorBufferGraphicsTestInstance(context, m_params); 675} 676 677void PushDescriptorBufferGraphicsTest::checkSupport(Context& context) const 678{ 679 if (m_params.useMaintenance5) 680 context.requireDeviceFunctionality("VK_KHR_maintenance5"); 681 682 checkPipelineConstructionRequirements(context.getInstanceInterface(), context.getPhysicalDevice(), m_params.pipelineConstructionType); 683} 684 685void PushDescriptorBufferGraphicsTest::initPrograms (SourceCollections& sourceCollections) const 686{ 687 const string bufferType = m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER ? "uniform" : "readonly buffer"; 688 const string vertexSrc = 689 "#version 450\n" 690 "layout(location = 0) in highp vec4 position;\n" 691 "layout(location = 1) in highp vec4 color;\n" 692 "layout(location = 0) out highp vec4 vtxColor;\n" 693 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") " + bufferType + " Block\n" 694 "{\n" 695 " vec4 color;\n" 696 "} inputData;\n" 697 "\n" 698 "out gl_PerVertex { vec4 gl_Position; };\n" 699 "\n" 700 "void main()\n" 701 "{\n" 702 " gl_Position = position;\n" 703 " vtxColor = inputData.color;\n" 704 "}\n"; 705 706 const string fragmentSrc = 707 "#version 450\n" 708 "layout(location = 0) in highp vec4 vtxColor;\n" 709 "layout(location = 0) out highp vec4 fragColor;\n" 710 "\n" 711 "void main (void)\n" 712 "{\n" 713 " fragColor = vtxColor;\n" 714 "}\n"; 715 716 sourceCollections.glslSources.add("vert") << glu::VertexSource(vertexSrc); 717 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 718} 719 720class PushDescriptorBufferComputeTestInstance : public vkt::TestInstance 721{ 722public: 723 PushDescriptorBufferComputeTestInstance (Context& context, const TestParams& params); 724 virtual ~PushDescriptorBufferComputeTestInstance (void); 725 void init (void); 726 virtual tcu::TestStatus iterate (void); 727 tcu::TestStatus verifyOutput (void); 728 729private: 730 const TestParams m_params; 731 const PlatformInterface& m_vkp; 732 const Extensions m_instanceExtensions; 733 const CustomInstance m_instance; 734 const InstanceDriver& m_vki; 735 const VkPhysicalDevice m_physicalDevice; 736 const deUint32 m_queueFamilyIndex; 737 const Extensions m_deviceExtensions; 738 std::vector<std::string> m_deviceEnabledExtensions; 739 const Unique<VkDevice> m_device; 740 const DeviceDriver m_vkd; 741 const VkQueue m_queue; 742 const VkDeviceSize m_itemSize; 743 SimpleAllocator m_allocator; 744 Move<VkShaderModule> m_computeShaderModule; 745 vector<VkBufferSp> m_buffers; 746 vector<AllocationSp> m_bufferAllocs; 747 Move<VkBuffer> m_outputBuffer; 748 de::MovePtr<Allocation> m_outputBufferAlloc; 749 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 750 Move<VkPipelineLayout> m_pipelineLayout; 751 Move<VkPipeline> m_computePipeline; 752 Move<VkCommandPool> m_cmdPool; 753 Move<VkCommandBuffer> m_cmdBuffer; 754 std::vector<tcu::Vec4> m_testColors; 755}; 756 757PushDescriptorBufferComputeTestInstance::PushDescriptorBufferComputeTestInstance (Context& context, const TestParams& params) 758 : vkt::TestInstance (context) 759 , m_params (params) 760 , m_vkp (context.getPlatformInterface()) 761 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 762 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 763 , m_vki (m_instance.getDriver()) 764 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 765 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_COMPUTE_BIT)) 766 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 767 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 768 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 769 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 770 , m_itemSize (calcItemSize(m_vki, m_physicalDevice)) 771 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 772{ 773} 774 775void PushDescriptorBufferComputeTestInstance::init (void) 776{ 777 // Create pipeline layout 778 { 779 // Create descriptor set layout 780 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindings[] = 781 { 782 { 783 m_params.binding, // uint32_t binding; 784 m_params.descriptorType, // VkDescriptorType descriptorType; 785 1u, // uint32_t descriptorCount; 786 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 787 DE_NULL // const VkSampler* pImmutableSamplers; 788 }, 789 { 790 m_params.binding + 1, // uint32_t binding; 791 VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // VkDescriptorType descriptorType; 792 1u, // uint32_t descriptorCount; 793 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 794 DE_NULL // const VkSampler* pImmutableSamplers; 795 } 796 }; 797 798 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 799 { 800 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 801 DE_NULL, // const void* pNext; 802 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 803 2u, // uint32_t bindingCount; 804 descriptorSetLayoutBindings // const VkDescriptorSetLayoutBinding* pBindings; 805 }; 806 807 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 808 809 // Create pipeline layout 810 const VkPipelineLayoutCreateInfo pipelineLayoutParams = 811 { 812 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 813 DE_NULL, // const void* pNext; 814 0u, // VkPipelineLayoutCreateFlags flags; 815 1u, // deUint32 descriptorSetCount; 816 &(*m_descriptorSetLayout), // const VkDescriptorSetLayout* pSetLayouts; 817 0u, // deUint32 pushConstantRangeCount; 818 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 819 }; 820 821 m_pipelineLayout = createPipelineLayout(m_vkd, *m_device, &pipelineLayoutParams); 822 } 823 824 // Fill the test colors table 825 m_testColors.resize(m_params.numCalls); 826 for (deUint32 colorIdx = 0; colorIdx < m_params.numCalls; colorIdx++) 827 { 828 if (colorIdx < DE_LENGTH_OF_ARRAY(defaultTestColors)) 829 m_testColors[colorIdx] = defaultTestColors[colorIdx]; 830 else 831 { 832 const float mix = static_cast<float>(colorIdx) / static_cast<float>(m_params.numCalls - 1); 833 834 // interpolate between first and last color, require these colors to be different 835 DE_ASSERT(defaultTestColors[0] != defaultTestColors[DE_LENGTH_OF_ARRAY(defaultTestColors) - 1]); 836 m_testColors[colorIdx] = defaultTestColors[0] * mix + defaultTestColors[DE_LENGTH_OF_ARRAY(defaultTestColors) - 1] * (1.0f - mix); 837 } 838 } 839 840 // Create buffers. One color value in each buffer. 841 { 842 for (deUint32 bufIdx = 0; bufIdx < m_params.numCalls; bufIdx++) 843 { 844 const VkBufferUsageFlags usageFlags = m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER ? VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT : VK_BUFFER_USAGE_STORAGE_BUFFER_BIT; 845 846 const VkBufferCreateInfo bufferCreateInfo = 847 { 848 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 849 DE_NULL, // const void* pNext; 850 0u, // VkBufferCreateFlags flags 851 kSizeofVec4, // VkDeviceSize size; 852 usageFlags, // VkBufferUsageFlags usage; 853 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 854 1u, // deUint32 queueFamilyCount; 855 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 856 }; 857 858 m_buffers.push_back(VkBufferSp(new Unique<VkBuffer>(createBuffer(m_vkd, *m_device, &bufferCreateInfo)))); 859 m_bufferAllocs.push_back(AllocationSp(m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, **m_buffers[bufIdx]), MemoryRequirement::HostVisible).release())); 860 VK_CHECK(m_vkd.bindBufferMemory(*m_device, **m_buffers[bufIdx], m_bufferAllocs[bufIdx]->getMemory(), m_bufferAllocs[bufIdx]->getOffset())); 861 862 deMemcpy(m_bufferAllocs[bufIdx]->getHostPtr(), &m_testColors[bufIdx], static_cast<size_t>(kSizeofVec4)); 863 flushAlloc(m_vkd, *m_device, *m_bufferAllocs[bufIdx]); 864 } 865 } 866 867 // Create output buffer 868 { 869 const VkBufferCreateInfo bufferCreateInfo = 870 { 871 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 872 DE_NULL, // const void* pNext; 873 0u, // VkBufferCreateFlags flags 874 m_itemSize * m_params.numCalls, // VkDeviceSize size; 875 VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, // VkBufferUsageFlags usage; 876 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 877 1u, // deUint32 queueFamilyCount; 878 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 879 }; 880 881 m_outputBuffer = createBuffer(m_vkd, *m_device, &bufferCreateInfo); 882 m_outputBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_outputBuffer), MemoryRequirement::HostVisible); 883 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_outputBuffer, m_outputBufferAlloc->getMemory(), m_outputBufferAlloc->getOffset())); 884 } 885 886 // Create shader 887 { 888 m_computeShaderModule = createShaderModule(m_vkd, *m_device, m_context.getBinaryCollection().get("compute"), 0u); 889 } 890 891 // Create pipeline 892 { 893 const VkPipelineShaderStageCreateInfo stageCreateInfo = 894 { 895 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, // VkStructureType sType; 896 DE_NULL, // const void* pNext; 897 0u, // VkPipelineShaderStageCreateFlags flags; 898 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlagBits stage; 899 *m_computeShaderModule, // VkShaderModule module; 900 "main", // const char* pName; 901 DE_NULL // const VkSpecializationInfo* pSpecializationInfo; 902 }; 903 904 const VkComputePipelineCreateInfo createInfo = 905 { 906 VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, // VkStructureType sType; 907 DE_NULL, // const void* pNext; 908 0u, // VkPipelineCreateFlags flags; 909 stageCreateInfo, // VkPipelineShaderStageCreateInfo stage; 910 *m_pipelineLayout, // VkPipelineLayout layout; 911 (VkPipeline)0, // VkPipeline basePipelineHandle; 912 0u, // int32_t basePipelineIndex; 913 }; 914 915 m_computePipeline = createComputePipeline(m_vkd, *m_device, (vk::VkPipelineCache)0u, &createInfo); 916 } 917 918 // Create command pool 919 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 920 921 // Create command buffer 922 { 923 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 924 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 925 m_vkd.cmdBindPipeline(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_computePipeline); 926 927 // Dispatch: Each dispatch switches the input buffer. 928 // Output buffer is exposed as a vec4 sized window. 929 for (deUint32 dispatchNdx = 0; dispatchNdx < m_params.numCalls; dispatchNdx++) 930 { 931 VkDescriptorBufferInfo descriptorBufferInfoUbo = 932 { 933 **m_buffers[dispatchNdx], // VkBuffer buffer; 934 0u, // VkDeviceSize offset; 935 kSizeofVec4, // VkDeviceSize range; 936 }; 937 938 VkDescriptorBufferInfo descriptorBufferInfoOutput = 939 { 940 *m_outputBuffer, // VkBuffer buffer; 941 m_itemSize * dispatchNdx, // VkDeviceSize offset; 942 kSizeofVec4, // VkDeviceSize range; 943 }; 944 945 VkWriteDescriptorSet writeDescriptorSets[] = 946 { 947 { 948 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 949 DE_NULL, // const void* pNext; 950 0u, // VkDescriptorSet dstSet; 951 m_params.binding, // uint32_t dstBinding; 952 0u, // uint32_t dstArrayElement; 953 1u, // uint32_t descriptorCount; 954 m_params.descriptorType, // VkDescriptorType descriptorType; 955 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 956 &descriptorBufferInfoUbo, // const VkDescriptorBufferInfo* pBufferInfo; 957 DE_NULL // const VkBufferView* pTexelBufferView; 958 }, 959 { 960 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 961 DE_NULL, // const void* pNext; 962 0u, // VkDescriptorSet dstSet; 963 m_params.binding + 1, // uint32_t dstBinding; 964 0u, // uint32_t dstArrayElement; 965 1u, // uint32_t descriptorCount; 966 VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // VkDescriptorType descriptorType; 967 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 968 &descriptorBufferInfoOutput, // const VkDescriptorBufferInfo* pBufferInfo; 969 DE_NULL // const VkBufferView* pTexelBufferView; 970 } 971 }; 972 973 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_pipelineLayout, 0, 2, writeDescriptorSets); 974 m_vkd.cmdDispatch(*m_cmdBuffer, 1, 1, 1); 975 } 976 977 endCommandBuffer(m_vkd, *m_cmdBuffer); 978 } 979} 980 981PushDescriptorBufferComputeTestInstance::~PushDescriptorBufferComputeTestInstance (void) 982{ 983} 984 985tcu::TestStatus PushDescriptorBufferComputeTestInstance::iterate (void) 986{ 987 init(); 988 989 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 990 991 return verifyOutput(); 992} 993 994tcu::TestStatus PushDescriptorBufferComputeTestInstance::verifyOutput (void) 995{ 996 invalidateAlloc(m_vkd, *m_device, *m_outputBufferAlloc); 997 998 // Verify result 999 auto bufferPtr = reinterpret_cast<const char*>(m_outputBufferAlloc->getHostPtr()); 1000 for (deUint32 i = 0; i < m_params.numCalls; ++i) 1001 { 1002 if (deMemCmp(&m_testColors[i], bufferPtr + (i * m_itemSize), static_cast<size_t>(kSizeofVec4)) != 0) 1003 TCU_FAIL("Output mismatch at output item " + de::toString(i)); 1004 } 1005 1006 return tcu::TestStatus::pass("Output matches expected values"); 1007} 1008 1009class PushDescriptorBufferComputeTest : public vkt::TestCase 1010{ 1011public: 1012 PushDescriptorBufferComputeTest (tcu::TestContext& testContext, 1013 const string& name, 1014 const TestParams& params); 1015 ~PushDescriptorBufferComputeTest (void); 1016 void initPrograms (SourceCollections& sourceCollections) const; 1017 TestInstance* createInstance (Context& context) const; 1018 1019protected: 1020 const TestParams m_params; 1021}; 1022 1023PushDescriptorBufferComputeTest::PushDescriptorBufferComputeTest (tcu::TestContext& testContext, 1024 const string& name, 1025 const TestParams& params) 1026 : vkt::TestCase (testContext, name) 1027 , m_params (params) 1028{ 1029} 1030 1031PushDescriptorBufferComputeTest::~PushDescriptorBufferComputeTest (void) 1032{ 1033} 1034 1035TestInstance* PushDescriptorBufferComputeTest::createInstance (Context& context) const 1036{ 1037 return new PushDescriptorBufferComputeTestInstance(context, m_params); 1038} 1039 1040void PushDescriptorBufferComputeTest::initPrograms (SourceCollections& sourceCollections) const 1041{ 1042 const string bufferType = m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER ? "uniform" : "buffer"; 1043 const string computeSrc = 1044 "#version 450\n" 1045 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") " + bufferType + " Block\n" 1046 "{\n" 1047 " vec4 color;\n" 1048 "} inputData;\n" 1049 "\n" 1050 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") writeonly buffer Output\n" 1051 "{\n" 1052 " vec4 color;\n" 1053 "} outData;\n" 1054 "\n" 1055 "void main()\n" 1056 "{\n" 1057 " outData.color = inputData.color;\n" 1058 "}\n"; 1059 1060 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 1061} 1062 1063class PushDescriptorImageGraphicsTestInstance : public vkt::TestInstance 1064{ 1065public: 1066 PushDescriptorImageGraphicsTestInstance (Context& context, const TestParams& params); 1067 virtual ~PushDescriptorImageGraphicsTestInstance (void); 1068 void init (void); 1069 virtual tcu::TestStatus iterate (void); 1070 tcu::TestStatus verifyImage (void); 1071 1072private: 1073 const TestParams m_params; 1074 const PlatformInterface& m_vkp; 1075 const Extensions m_instanceExtensions; 1076 const CustomInstance m_instance; 1077 const InstanceDriver& m_vki; 1078 const VkPhysicalDevice m_physicalDevice; 1079 const deUint32 m_queueFamilyIndex; 1080 const Extensions m_deviceExtensions; 1081 std::vector<std::string> m_deviceEnabledExtensions; 1082 const Unique<VkDevice> m_device; 1083 const DeviceDriver m_vkd; 1084 const VkQueue m_queue; 1085 SimpleAllocator m_allocator; 1086 const tcu::UVec2 m_renderSize; 1087 const tcu::UVec2 m_textureSize; 1088 const VkFormat m_colorFormat; 1089 Move<VkImage> m_colorImage; 1090 de::MovePtr<Allocation> m_colorImageAlloc; 1091 Move<VkImageView> m_colorAttachmentView; 1092 vector<VkImageSp> m_textureImages; 1093 vector<AllocationSp> m_textureImageAllocs; 1094 vector<VkImageViewSp> m_textureViews; 1095 Move<VkSampler> m_whiteBorderSampler; 1096 Move<VkSampler> m_blackBorderSampler; 1097 RenderPassWrapper m_renderPass; 1098 Move<VkFramebuffer> m_framebuffer; 1099 ShaderWrapper m_vertexShaderModule; 1100 ShaderWrapper m_fragmentShaderModule; 1101 Move<VkBuffer> m_vertexBuffer; 1102 de::MovePtr<Allocation> m_vertexBufferAlloc; 1103 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 1104 PipelineLayoutWrapper m_preRasterizationStatePipelineLayout; 1105 PipelineLayoutWrapper m_fragmentStatePipelineLayout; 1106 GraphicsPipelineWrapper m_graphicsPipeline; 1107 Move<VkCommandPool> m_cmdPool; 1108 Move<VkCommandBuffer> m_cmdBuffer; 1109 vector<Vertex4Tex4> m_vertices; 1110}; 1111 1112PushDescriptorImageGraphicsTestInstance::PushDescriptorImageGraphicsTestInstance (Context& context, const TestParams& params) 1113 : vkt::TestInstance (context) 1114 , m_params (params) 1115 , m_vkp (context.getPlatformInterface()) 1116 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 1117 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 1118 , m_vki (m_instance.getDriver()) 1119 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 1120 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_GRAPHICS_BIT)) 1121 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 1122 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 1123 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 1124 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 1125 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 1126 , m_renderSize (32, 32) 1127 , m_textureSize (32, 32) 1128 , m_colorFormat (VK_FORMAT_R8G8B8A8_UNORM) 1129 , m_graphicsPipeline (m_vki, m_vkd, m_physicalDevice, *m_device, m_deviceEnabledExtensions, params.pipelineConstructionType) 1130 , m_vertices (createTexQuads(params.numCalls, 0.25f)) 1131{ 1132} 1133 1134void PushDescriptorImageGraphicsTestInstance::init (void) 1135{ 1136 const VkComponentMapping componentMappingRGBA = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A }; 1137 1138 // Create color image 1139 { 1140 1141 const VkImageCreateInfo colorImageParams = 1142 { 1143 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 1144 DE_NULL, // const void* pNext; 1145 0u, // VkImageCreateFlags flags; 1146 VK_IMAGE_TYPE_2D, // VkImageType imageType; 1147 m_colorFormat, // VkFormat format; 1148 { m_renderSize.x(), m_renderSize.y(), 1u }, // VkExtent3D extent; 1149 1u, // deUint32 mipLevels; 1150 1u, // deUint32 arrayLayers; 1151 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 1152 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 1153 VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT, // VkImageUsageFlags usage; 1154 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 1155 1u, // deUint32 queueFamilyIndexCount; 1156 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 1157 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout; 1158 }; 1159 1160 m_colorImage = createImage(m_vkd, *m_device, &colorImageParams); 1161 1162 // Allocate and bind color image memory 1163 m_colorImageAlloc = m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, *m_colorImage), MemoryRequirement::Any); 1164 VK_CHECK(m_vkd.bindImageMemory(*m_device, *m_colorImage, m_colorImageAlloc->getMemory(), m_colorImageAlloc->getOffset())); 1165 } 1166 1167 // Create color attachment view 1168 { 1169 const VkImageViewCreateInfo colorAttachmentViewParams = 1170 { 1171 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 1172 DE_NULL, // const void* pNext; 1173 0u, // VkImageViewCreateFlags flags; 1174 *m_colorImage, // VkImage image; 1175 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 1176 m_colorFormat, // VkFormat format; 1177 componentMappingRGBA, // VkChannelMapping channels; 1178 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u } // VkImageSubresourceRange subresourceRange; 1179 }; 1180 1181 m_colorAttachmentView = createImageView(m_vkd, *m_device, &colorAttachmentViewParams); 1182 } 1183 1184 // Create texture images 1185 for (deUint32 texIdx = 0; texIdx < 2; texIdx++) 1186 { 1187 VkImageUsageFlags usageFlags = VK_IMAGE_USAGE_TRANSFER_DST_BIT; 1188 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 1189 usageFlags |= VK_IMAGE_USAGE_SAMPLED_BIT; 1190 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) 1191 usageFlags |= VK_IMAGE_USAGE_STORAGE_BIT; 1192 1193 const VkImageCreateInfo textureImageParams = 1194 { 1195 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 1196 DE_NULL, // const void* pNext; 1197 0u, // VkImageCreateFlags flags; 1198 VK_IMAGE_TYPE_2D, // VkImageType imageType; 1199 m_colorFormat, // VkFormat format; 1200 { m_textureSize.x(), m_textureSize.y(), 1u }, // VkExtent3D extent; 1201 1u, // deUint32 mipLevels; 1202 1u, // deUint32 arrayLayers; 1203 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 1204 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 1205 usageFlags, // VkImageUsageFlags usage; 1206 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 1207 1u, // deUint32 queueFamilyIndexCount; 1208 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 1209 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout; 1210 }; 1211 1212 m_textureImages.push_back(VkImageSp(new Unique<VkImage>(createImage(m_vkd, *m_device, &textureImageParams)))); 1213 1214 // Allocate and bind texture image memory 1215 m_textureImageAllocs.push_back(AllocationSp(m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, **m_textureImages.back()), MemoryRequirement::Any).release())); 1216 VK_CHECK(m_vkd.bindImageMemory(*m_device, **m_textureImages.back(), m_textureImageAllocs.back()->getMemory(), m_textureImageAllocs.back()->getOffset())); 1217 } 1218 1219 // Create texture image views 1220 for (deUint32 texIdx = 0; texIdx < 2; texIdx++) 1221 { 1222 const VkImageViewCreateInfo textureViewParams = 1223 { 1224 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 1225 DE_NULL, // const void* pNext; 1226 0u, // VkImageViewCreateFlags flags; 1227 **m_textureImages[texIdx], // VkImage image; 1228 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 1229 m_colorFormat, // VkFormat format; 1230 componentMappingRGBA, // VkChannelMapping channels; 1231 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u } // VkImageSubresourceRange subresourceRange; 1232 }; 1233 1234 m_textureViews.push_back(VkImageViewSp(new Unique<VkImageView>(createImageView(m_vkd, *m_device, &textureViewParams)))); 1235 } 1236 1237 VkClearValue clearValues[2]; 1238 clearValues[0].color.float32[0] = 0.0f; 1239 clearValues[0].color.float32[1] = 1.0f; 1240 clearValues[0].color.float32[2] = 0.0f; 1241 clearValues[0].color.float32[3] = 1.0f; 1242 clearValues[1].color.float32[0] = 1.0f; 1243 clearValues[1].color.float32[1] = 0.0f; 1244 clearValues[1].color.float32[2] = 0.0f; 1245 clearValues[1].color.float32[3] = 1.0f; 1246 1247 const VkImageLayout textureImageLayout = (m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) ? 1248 VK_IMAGE_LAYOUT_GENERAL : VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL; 1249 1250 // Clear textures 1251 for (deUint32 texIdx = 0; texIdx < 2; texIdx++) 1252 { 1253 const VkImageAspectFlags aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; 1254 Move<VkCommandPool> cmdPool; 1255 Move<VkCommandBuffer> cmdBuffer; 1256 1257 cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 1258 cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 1259 1260 const VkImageMemoryBarrier preImageBarrier = 1261 { 1262 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType; 1263 DE_NULL, // const void* pNext; 1264 0u, // VkAccessFlags srcAccessMask; 1265 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags dstAccessMask; 1266 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout oldLayout; 1267 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout newLayout; 1268 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex; 1269 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex; 1270 **m_textureImages[texIdx], // VkImage image; 1271 { // VkImageSubresourceRange subresourceRange; 1272 aspectMask, // VkImageAspect aspect; 1273 0u, // deUint32 baseMipLevel; 1274 1u, // deUint32 mipLevels; 1275 0u, // deUint32 baseArraySlice; 1276 1u // deUint32 arraySize; 1277 } 1278 }; 1279 1280 const VkImageMemoryBarrier postImageBarrier = 1281 { 1282 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType; 1283 DE_NULL, // const void* pNext; 1284 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags srcAccessMask; 1285 VK_ACCESS_SHADER_READ_BIT, // VkAccessFlags dstAccessMask; 1286 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout oldLayout; 1287 textureImageLayout, // VkImageLayout newLayout; 1288 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex; 1289 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex; 1290 **m_textureImages[texIdx], // VkImage image; 1291 { // VkImageSubresourceRange subresourceRange; 1292 aspectMask, // VkImageAspect aspect; 1293 0u, // deUint32 baseMipLevel; 1294 1u, // deUint32 mipLevels; 1295 0u, // deUint32 baseArraySlice; 1296 1u // deUint32 arraySize; 1297 } 1298 }; 1299 1300 const VkImageSubresourceRange clearRange = 1301 { 1302 aspectMask, // VkImageAspectFlags aspectMask; 1303 0u, // deUint32 baseMipLevel; 1304 1u, // deUint32 levelCount; 1305 0u, // deUint32 baseArrayLayer; 1306 1u // deUint32 layerCount; 1307 }; 1308 1309 beginCommandBuffer(m_vkd, *cmdBuffer); 1310 m_vkd.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_HOST_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &preImageBarrier); 1311 m_vkd.cmdClearColorImage(*cmdBuffer, **m_textureImages[texIdx], VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearValues[texIdx].color, 1, &clearRange); 1312 m_vkd.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &postImageBarrier); 1313 endCommandBuffer(m_vkd, *cmdBuffer); 1314 1315 submitCommandsAndWait(m_vkd, *m_device, m_queue, cmdBuffer.get()); 1316 } 1317 1318 // Create samplers: one with white and one with black border color to have a visible effect on switching the sampler 1319 { 1320 VkSamplerCreateInfo samplerParams = 1321 { 1322 VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO, // VkStructureType sType; 1323 DE_NULL, // const void* pNext; 1324 0u, // VkSamplerCreateFlags flags; 1325 VK_FILTER_NEAREST, // VkFilter magFilter; 1326 VK_FILTER_NEAREST, // VkFilter minFilter; 1327 VK_SAMPLER_MIPMAP_MODE_NEAREST, // VkSamplerMipmapMode mipmapMode; 1328 VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER, // VkSamplerAddressMode addressModeU; 1329 VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER, // VkSamplerAddressMode addressModeV; 1330 VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER, // VkSamplerAddressMode addressModeW; 1331 0.0f, // float mipLodBias; 1332 VK_FALSE, // VkBool32 anisotropyEnable; 1333 0.0f, // float maxAnisotropy; 1334 VK_FALSE, // VkBool32 compareEnable; 1335 VK_COMPARE_OP_NEVER, // VkCompareOp compareOp; 1336 0.0f, // float minLod; 1337 0.0f, // float maxLod; 1338 VK_BORDER_COLOR_FLOAT_OPAQUE_WHITE, // VkBorderColor borderColor; 1339 VK_FALSE // VkBool32 unnormalizedCoordinates; 1340 }; 1341 1342 m_whiteBorderSampler = createSampler(m_vkd, *m_device, &samplerParams); 1343 samplerParams.borderColor = VK_BORDER_COLOR_FLOAT_OPAQUE_BLACK; 1344 m_blackBorderSampler = createSampler(m_vkd, *m_device, &samplerParams); 1345 } 1346 1347 // Create render pass 1348 { 1349 const VkAttachmentDescription attachmentDescription = 1350 { 1351 (VkAttachmentDescriptionFlags)0, // VkAttachmentDescriptionFlags flags 1352 VK_FORMAT_R8G8B8A8_UNORM, // VkFormat format 1353 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples 1354 VK_ATTACHMENT_LOAD_OP_CLEAR, // VkAttachmentLoadOp loadOp 1355 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp 1356 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp 1357 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp 1358 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout initialLayout 1359 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL // VkImageLayout finalLayout 1360 }; 1361 1362 const VkAttachmentReference resultAttachmentRef = 1363 { 1364 0u, // deUint32 attachment 1365 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL // VkImageLayout layout 1366 }; 1367 1368 const VkSubpassDescription subpassDescription = 1369 { 1370 (VkSubpassDescriptionFlags)0, // VkSubpassDescriptionFlags flags 1371 VK_PIPELINE_BIND_POINT_GRAPHICS, // VkPipelineBindPoint pipelineBindPoint 1372 0u, // deUint32 inputAttachmentCount 1373 DE_NULL, // const VkAttachmentReference* pInputAttachments 1374 1u, // deUint32 colorAttachmentCount 1375 &resultAttachmentRef, // const VkAttachmentReference* pColorAttachments 1376 DE_NULL, // const VkAttachmentReference* pResolveAttachments 1377 DE_NULL, // const VkAttachmentReference* pDepthStencilAttachment 1378 0u, // deUint32 preserveAttachmentCount 1379 DE_NULL // const deUint32* pPreserveAttachments 1380 }; 1381 1382 const VkRenderPassCreateInfo renderPassInfo = 1383 { 1384 VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO, // VkStructureTypei sType 1385 DE_NULL, // const void* pNext 1386 (VkRenderPassCreateFlags)0, // VkRenderPassCreateFlags flags 1387 1u, // deUint32 attachmentCount 1388 &attachmentDescription, // const VkAttachmentDescription* pAttachments 1389 1u, // deUint32 subpassCount 1390 &subpassDescription, // const VkSubpassDescription* pSubpasses 1391 0u, // deUint32 dependencyCount 1392 DE_NULL // const VkSubpassDependency* pDependencies 1393 }; 1394 1395 m_renderPass = RenderPassWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &renderPassInfo); 1396 } 1397 1398 // Create framebuffer 1399 { 1400 const VkImageView attachmentBindInfos[] = 1401 { 1402 *m_colorAttachmentView 1403 }; 1404 1405 const VkFramebufferCreateInfo framebufferParams = 1406 { 1407 VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, // VkStructureType sType; 1408 DE_NULL, // const void* pNext; 1409 0u, // VkFramebufferCreateFlags flags; 1410 *m_renderPass, // VkRenderPass renderPass; 1411 1u, // deUint32 attachmentCount; 1412 attachmentBindInfos, // const VkImageView* pAttachments; 1413 (deUint32)m_renderSize.x(), // deUint32 width; 1414 (deUint32)m_renderSize.y(), // deUint32 height; 1415 1u // deUint32 layers; 1416 }; 1417 1418 m_renderPass.createFramebuffer(m_vkd, *m_device, &framebufferParams, *m_colorImage); 1419 } 1420 1421 // Create pipeline layout 1422 { 1423 // Create descriptor set layout 1424 vector<VkDescriptorSetLayoutBinding> layoutBindings; 1425 1426 switch(m_params.descriptorType) 1427 { 1428 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: 1429 { 1430 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 1431 { 1432 m_params.binding, // uint32_t binding; 1433 VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, // VkDescriptorType descriptorType; 1434 1u, // uint32_t descriptorCount; 1435 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 1436 DE_NULL // const VkSampler* pImmutableSamplers; 1437 }; 1438 layoutBindings.push_back(descriptorSetLayoutBinding); 1439 } 1440 break; 1441 1442 case VK_DESCRIPTOR_TYPE_SAMPLER: 1443 { 1444 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingSampler = 1445 { 1446 m_params.binding, // uint32_t binding; 1447 VK_DESCRIPTOR_TYPE_SAMPLER, // VkDescriptorType descriptorType; 1448 1u, // uint32_t descriptorCount; 1449 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 1450 DE_NULL // const VkSampler* pImmutableSamplers; 1451 }; 1452 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingTex = 1453 { 1454 m_params.binding + 1, // uint32_t binding; 1455 VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, // VkDescriptorType descriptorType; 1456 1u, // uint32_t descriptorCount; 1457 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 1458 DE_NULL // const VkSampler* pImmutableSamplers; 1459 }; 1460 layoutBindings.push_back(descriptorSetLayoutBindingSampler); 1461 layoutBindings.push_back(descriptorSetLayoutBindingTex); 1462 } 1463 break; 1464 1465 case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: 1466 { 1467 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingSampler = 1468 { 1469 m_params.binding + 1, // uint32_t binding; 1470 VK_DESCRIPTOR_TYPE_SAMPLER, // VkDescriptorType descriptorType; 1471 1u, // uint32_t descriptorCount; 1472 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 1473 DE_NULL // const VkSampler* pImmutableSamplers; 1474 }; 1475 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingTex = 1476 { 1477 m_params.binding, // uint32_t binding; 1478 VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, // VkDescriptorType descriptorType; 1479 1u, // uint32_t descriptorCount; 1480 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 1481 DE_NULL // const VkSampler* pImmutableSamplers; 1482 }; 1483 layoutBindings.push_back(descriptorSetLayoutBindingSampler); 1484 layoutBindings.push_back(descriptorSetLayoutBindingTex); 1485 } 1486 break; 1487 1488 case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: 1489 { 1490 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 1491 { 1492 m_params.binding, // uint32_t binding; 1493 VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, // VkDescriptorType descriptorType; 1494 1u, // uint32_t descriptorCount; 1495 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 1496 DE_NULL // const VkSampler* pImmutableSamplers; 1497 }; 1498 layoutBindings.push_back(descriptorSetLayoutBinding); 1499 } 1500 break; 1501 1502 default: 1503 DE_FATAL("unexpected descriptor type"); 1504 break; 1505 } 1506 1507 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 1508 { 1509 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 1510 DE_NULL, // const void* pNext; 1511 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 1512 (deUint32)layoutBindings.size(), // uint32_t bindingCount; 1513 layoutBindings.data() // const VkDescriptorSetLayoutBinding* pBindings; 1514 }; 1515 1516 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 1517 1518 // Create pipeline layout 1519 VkPipelineLayoutCreateFlags pipelineLayoutFlags = (m_params.pipelineConstructionType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) ? 0u : deUint32(VK_PIPELINE_LAYOUT_CREATE_INDEPENDENT_SETS_BIT_EXT); 1520 VkPipelineLayoutCreateInfo pipelineLayoutParams 1521 { 1522 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 1523 DE_NULL, // const void* pNext; 1524 pipelineLayoutFlags, // VkPipelineLayoutCreateFlags flags; 1525 0u, // deUint32 setLayoutCount; 1526 DE_NULL, // const VkDescriptorSetLayout* pSetLayouts; 1527 0u, // deUint32 pushConstantRangeCount; 1528 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 1529 }; 1530 1531 m_preRasterizationStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 1532 pipelineLayoutParams.setLayoutCount = 1u; 1533 pipelineLayoutParams.pSetLayouts = &(*m_descriptorSetLayout); 1534 m_fragmentStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 1535 } 1536 1537 // Create shaders 1538 { 1539 m_vertexShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("vert"), 0u); 1540 m_fragmentShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("frag"), 0u); 1541 } 1542 1543 // Create pipeline 1544 { 1545 const VkVertexInputBindingDescription vertexInputBindingDescription = 1546 { 1547 0u, // deUint32 binding; 1548 sizeof(Vertex4Tex4), // deUint32 strideInBytes; 1549 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputStepRate stepRate; 1550 }; 1551 1552 const VkVertexInputAttributeDescription vertexInputAttributeDescriptions[] = 1553 { 1554 { 1555 0u, // deUint32 location; 1556 0u, // deUint32 binding; 1557 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 1558 0u // deUint32 offsetInBytes; 1559 }, 1560 { 1561 1u, // deUint32 location; 1562 0u, // deUint32 binding; 1563 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 1564 DE_OFFSET_OF(Vertex4Tex4, texCoord), // deUint32 offset; 1565 } 1566 }; 1567 1568 const VkPipelineVertexInputStateCreateInfo vertexInputStateParams = 1569 { 1570 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // VkStructureType sType; 1571 DE_NULL, // const void* pNext; 1572 0u, // vkPipelineVertexInputStateCreateFlags flags; 1573 1u, // deUint32 bindingCount; 1574 &vertexInputBindingDescription, // const VkVertexInputBindingDescription* pVertexBindingDescriptions; 1575 2u, // deUint32 attributeCount; 1576 vertexInputAttributeDescriptions // const VkVertexInputAttributeDescription* pVertexAttributeDescriptions; 1577 }; 1578 1579 const vector<VkViewport> viewports { makeViewport(m_renderSize) }; 1580 const vector<VkRect2D> scissors { makeRect2D(m_renderSize) }; 1581 1582 m_graphicsPipeline.setMonolithicPipelineLayout(m_fragmentStatePipelineLayout) 1583 .setDefaultRasterizationState() 1584 .setDefaultDepthStencilState() 1585 .setDefaultMultisampleState() 1586 .setDefaultColorBlendState() 1587 .setupVertexInputState(&vertexInputStateParams) 1588 .setupPreRasterizationShaderState(viewports, 1589 scissors, 1590 m_preRasterizationStatePipelineLayout, 1591 *m_renderPass, 1592 0u, 1593 m_vertexShaderModule) 1594 .setupFragmentShaderState(m_fragmentStatePipelineLayout, *m_renderPass, 0u, m_fragmentShaderModule) 1595 .setupFragmentOutputState(*m_renderPass) 1596 .buildPipeline(); 1597 } 1598 1599 // Create vertex buffer 1600 { 1601 const VkBufferCreateInfo vertexBufferParams = 1602 { 1603 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 1604 DE_NULL, // const void* pNext; 1605 0u, // VkBufferCreateFlags flags; 1606 (VkDeviceSize)(sizeof(Vertex4RGBA) * m_vertices.size()), // VkDeviceSize size; 1607 VK_BUFFER_USAGE_VERTEX_BUFFER_BIT, // VkBufferUsageFlags usage; 1608 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 1609 1u, // deUint32 queueFamilyCount; 1610 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 1611 }; 1612 1613 m_vertexBuffer = createBuffer(m_vkd, *m_device, &vertexBufferParams); 1614 m_vertexBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_vertexBuffer), MemoryRequirement::HostVisible); 1615 1616 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_vertexBuffer, m_vertexBufferAlloc->getMemory(), m_vertexBufferAlloc->getOffset())); 1617 1618 // Load vertices into vertex buffer 1619 deMemcpy(m_vertexBufferAlloc->getHostPtr(), m_vertices.data(), m_vertices.size() * sizeof(Vertex4Tex4)); 1620 flushAlloc(m_vkd, *m_device, *m_vertexBufferAlloc); 1621 } 1622 1623 // Create command pool 1624 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 1625 1626 // Create command buffer 1627 { 1628 const VkClearValue attachmentClearValue = defaultClearValue(m_colorFormat); 1629 const VkDeviceSize vertexBufferOffset = 0; 1630 1631 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 1632 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 1633 m_renderPass.begin(m_vkd, *m_cmdBuffer, makeRect2D(0, 0, m_renderSize.x(), m_renderSize.y()), attachmentClearValue); 1634 m_graphicsPipeline.bind(*m_cmdBuffer); 1635 m_vkd.cmdBindVertexBuffers(*m_cmdBuffer, 0, 1, &m_vertexBuffer.get(), &vertexBufferOffset); 1636 1637 // Draw quads. Switch sampler or image view depending on the test. 1638 vector<VkSampler> samplers; 1639 vector<VkImageView> imageViews; 1640 1641 samplers.push_back(*m_whiteBorderSampler); 1642 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER) 1643 { 1644 // Vary sampler between draws 1645 samplers.push_back(*m_blackBorderSampler); 1646 } 1647 else 1648 { 1649 // Usa a single sampler 1650 samplers.push_back(*m_whiteBorderSampler); 1651 } 1652 1653 imageViews.push_back(**m_textureViews[0]); 1654 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE || m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) 1655 { 1656 // Vary image view between draws 1657 imageViews.push_back(**m_textureViews[1]); 1658 } 1659 else 1660 { 1661 // Usa a single image view 1662 imageViews.push_back(**m_textureViews[0]); 1663 } 1664 1665 for (deUint32 quadNdx = 0; quadNdx < m_params.numCalls; quadNdx++) 1666 { 1667 VkDescriptorImageInfo descriptorImageInfo = 1668 { 1669 samplers[quadNdx], // VkSampler sampler; 1670 imageViews[quadNdx], // VkImageView imageView; 1671 textureImageLayout // VkImageLayout imageLayout; 1672 }; 1673 1674 VkWriteDescriptorSet writeDescriptorSet = 1675 { 1676 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 1677 DE_NULL, // const void* pNext; 1678 0u, // VkDescriptorSet dstSet; 1679 m_params.binding, // uint32_t dstBinding; 1680 0u, // uint32_t dstArrayElement; 1681 1u, // uint32_t descriptorCount; 1682 m_params.descriptorType, // VkDescriptorType descriptorType; 1683 &descriptorImageInfo, // const VkDescriptorImageInfo* pImageInfo; 1684 DE_NULL, // const VkDescriptorBufferInfo* pBufferInfo; 1685 DE_NULL // const VkBufferView* pTexelBufferView; 1686 }; 1687 1688 vector<VkWriteDescriptorSet> writeDescriptorSets; 1689 writeDescriptorSets.push_back(writeDescriptorSet); 1690 1691 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER) 1692 { 1693 // Sampler also needs an image. 1694 writeDescriptorSet.dstBinding++; 1695 writeDescriptorSet.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE; 1696 writeDescriptorSets.push_back(writeDescriptorSet); 1697 } 1698 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 1699 { 1700 // Image also needs a sampler. 1701 writeDescriptorSet.dstBinding++; 1702 writeDescriptorSet.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER; 1703 writeDescriptorSets.push_back(writeDescriptorSet); 1704 } 1705 1706 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *m_fragmentStatePipelineLayout, 0, (deUint32)writeDescriptorSets.size(), writeDescriptorSets.data()); 1707 m_vkd.cmdDraw(*m_cmdBuffer, 6, 1, 6 * quadNdx, 0); 1708 } 1709 1710 m_renderPass.end(m_vkd, *m_cmdBuffer); 1711 endCommandBuffer(m_vkd, *m_cmdBuffer); 1712 } 1713} 1714 1715PushDescriptorImageGraphicsTestInstance::~PushDescriptorImageGraphicsTestInstance (void) 1716{ 1717} 1718 1719tcu::TestStatus PushDescriptorImageGraphicsTestInstance::iterate (void) 1720{ 1721 init(); 1722 1723 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 1724 1725 return verifyImage(); 1726} 1727 1728tcu::TestStatus PushDescriptorImageGraphicsTestInstance::verifyImage (void) 1729{ 1730 const tcu::TextureFormat tcuColorFormat = mapVkFormat(m_colorFormat); 1731 const tcu::TextureFormat tcuDepthFormat = tcu::TextureFormat(); 1732 const ColorVertexShader vertexShader; 1733 const ColorFragmentShader fragmentShader (tcuColorFormat, tcuDepthFormat); 1734 const rr::Program program (&vertexShader, &fragmentShader); 1735 ReferenceRenderer refRenderer (m_renderSize.x(), m_renderSize.y(), 1, tcuColorFormat, tcuDepthFormat, &program); 1736 bool compareOk = false; 1737 1738 // Render reference image 1739 { 1740 vector<Vertex4RGBA> refQuadsOuter = createQuads(m_params.numCalls, 0.25f); 1741 vector<Vertex4RGBA> refQuadsInner = createQuads(m_params.numCalls, 0.25f * 0.8f); 1742 tcu::Vec4 outerColor[2]; 1743 tcu::Vec4 innerColor[2]; 1744 const bool hasBorder = m_params.descriptorType != VK_DESCRIPTOR_TYPE_STORAGE_IMAGE; 1745 1746 if (hasBorder) 1747 { 1748 outerColor[0] = tcu::Vec4(1.0f, 1.0f, 1.0f, 1.0f); 1749 innerColor[0] = tcu::Vec4(0.0f, 1.0f, 0.0f, 1.0f); 1750 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 1751 outerColor[1] = tcu::Vec4(1.0f, 1.0f, 1.0f, 1.0f); 1752 else 1753 outerColor[1] = tcu::Vec4(0.0f, 0.0f, 0.0f, 1.0f); 1754 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER) 1755 innerColor[1] = tcu::Vec4(0.0f, 1.0f, 0.0f, 1.0f); 1756 else 1757 innerColor[1] = tcu::Vec4(1.0f, 0.0f, 0.0f, 1.0f); 1758 } 1759 else 1760 { 1761 outerColor[0] = tcu::Vec4(0.0f, 1.0f, 0.0f, 1.0f); 1762 outerColor[1] = tcu::Vec4(1.0f, 0.0f, 0.0f, 1.0f); 1763 } 1764 1765 for (deUint32 quadIdx = 0; quadIdx < m_params.numCalls; quadIdx++) 1766 for (deUint32 vertexIdx = 0; vertexIdx < 6; vertexIdx++) 1767 { 1768 const deUint32 idx = quadIdx * 6 + vertexIdx; 1769 refQuadsOuter[idx].color.xyzw() = outerColor[quadIdx]; 1770 refQuadsInner[idx].color.xyzw() = innerColor[quadIdx]; 1771 } 1772 1773 if (hasBorder) 1774 refQuadsOuter.insert(refQuadsOuter.end(), refQuadsInner.begin(), refQuadsInner.end()); 1775 1776 refRenderer.draw(rr::RenderState(refRenderer.getViewportState(), m_context.getDeviceProperties().limits.subPixelPrecisionBits), 1777 rr::PRIMITIVETYPE_TRIANGLES, refQuadsOuter); 1778 } 1779 1780 // Compare result with reference image 1781 { 1782 de::MovePtr<tcu::TextureLevel> result = readColorAttachment(m_vkd, *m_device, m_queue, m_queueFamilyIndex, m_allocator, *m_colorImage, m_colorFormat, m_renderSize); 1783 1784 compareOk = tcu::intThresholdPositionDeviationCompare(m_context.getTestContext().getLog(), 1785 "IntImageCompare", 1786 "Image comparison", 1787 refRenderer.getAccess(), 1788 result->getAccess(), 1789 tcu::UVec4(2, 2, 2, 2), 1790 tcu::IVec3(1, 1, 0), 1791 true, 1792 tcu::COMPARE_LOG_RESULT); 1793 } 1794 1795 if (compareOk) 1796 return tcu::TestStatus::pass("Result image matches reference"); 1797 else 1798 return tcu::TestStatus::fail("Image mismatch"); 1799} 1800 1801class PushDescriptorImageGraphicsTest : public vkt::TestCase 1802{ 1803public: 1804 PushDescriptorImageGraphicsTest (tcu::TestContext& testContext, 1805 const string& name, 1806 const TestParams& params); 1807 ~PushDescriptorImageGraphicsTest (void); 1808 1809 void checkSupport (Context& context) const; 1810 void initPrograms (SourceCollections& sourceCollections) const; 1811 TestInstance* createInstance (Context& context) const; 1812 1813protected: 1814 const TestParams m_params; 1815}; 1816 1817PushDescriptorImageGraphicsTest::PushDescriptorImageGraphicsTest (tcu::TestContext& testContext, 1818 const string& name, 1819 const TestParams& params) 1820 : vkt::TestCase (testContext, name) 1821 , m_params (params) 1822{ 1823} 1824 1825PushDescriptorImageGraphicsTest::~PushDescriptorImageGraphicsTest (void) 1826{ 1827} 1828 1829TestInstance* PushDescriptorImageGraphicsTest::createInstance (Context& context) const 1830{ 1831 return new PushDescriptorImageGraphicsTestInstance(context, m_params); 1832} 1833 1834void PushDescriptorImageGraphicsTest::checkSupport(Context& context) const 1835{ 1836 checkPipelineConstructionRequirements(context.getInstanceInterface(), context.getPhysicalDevice(), m_params.pipelineConstructionType); 1837} 1838 1839void PushDescriptorImageGraphicsTest::initPrograms (SourceCollections& sourceCollections) const 1840{ 1841 const string vertexSrc = 1842 "#version 450\n" 1843 "layout(location = 0) in highp vec4 position;\n" 1844 "layout(location = 1) in highp vec4 texcoordVtx;\n" 1845 "layout(location = 0) out highp vec2 texcoordFrag;\n" 1846 "\n" 1847 "out gl_PerVertex { vec4 gl_Position; };\n" 1848 "\n" 1849 "void main()\n" 1850 "{\n" 1851 " gl_Position = position;\n" 1852 " texcoordFrag = texcoordVtx.xy;\n" 1853 "}\n"; 1854 1855 sourceCollections.glslSources.add("vert") << glu::VertexSource(vertexSrc); 1856 1857 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER) 1858 { 1859 const string fragmentSrc = 1860 "#version 450\n" 1861 "layout(location = 0) in highp vec2 texcoordFrag;\n" 1862 "layout(location = 0) out highp vec4 fragColor;\n" 1863 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform sampler2D combinedSampler;\n" 1864 "\n" 1865 "void main (void)\n" 1866 "{\n" 1867 " fragColor = texture(combinedSampler, texcoordFrag);\n" 1868 "}\n"; 1869 1870 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 1871 } 1872 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER) 1873 { 1874 const string fragmentSrc = 1875 "#version 450\n" 1876 "layout(location = 0) in highp vec2 texcoordFrag;\n" 1877 "layout(location = 0) out highp vec4 fragColor;\n" 1878 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform sampler texSampler;\n" 1879 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") uniform texture2D texImage;\n" 1880 "\n" 1881 "void main (void)\n" 1882 "{\n" 1883 " fragColor = texture(sampler2D(texImage, texSampler), texcoordFrag);\n" 1884 "}\n"; 1885 1886 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 1887 } 1888 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 1889 { 1890 const string fragmentSrc = 1891 "#version 450\n" 1892 "layout(location = 0) in highp vec2 texcoordFrag;\n" 1893 "layout(location = 0) out highp vec4 fragColor;\n" 1894 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") uniform sampler texSampler;\n" 1895 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform texture2D texImage;\n" 1896 "\n" 1897 "void main (void)\n" 1898 "{\n" 1899 " fragColor = texture(sampler2D(texImage, texSampler), texcoordFrag);\n" 1900 "}\n"; 1901 1902 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 1903 } 1904 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) 1905 { 1906 const string fragmentSrc = 1907 "#version 450\n" 1908 "layout(location = 0) in highp vec2 texcoordFrag;\n" 1909 "layout(location = 0) out highp vec4 fragColor;\n" 1910 "layout(set = 0, binding = " + de::toString(m_params.binding) + ", rgba8) uniform readonly image2D storageImage;\n" 1911 "\n" 1912 "void main (void)\n" 1913 "{\n" 1914 " fragColor = imageLoad(storageImage, ivec2(0));\n" 1915 "}\n"; 1916 1917 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 1918 } 1919 else 1920 { 1921 DE_FATAL("Unexpected descriptor type"); 1922 } 1923} 1924 1925class PushDescriptorImageComputeTestInstance : public vkt::TestInstance 1926{ 1927public: 1928 PushDescriptorImageComputeTestInstance (Context& context, const TestParams& params); 1929 virtual ~PushDescriptorImageComputeTestInstance (void); 1930 void init (void); 1931 virtual tcu::TestStatus iterate (void); 1932 tcu::TestStatus verifyOutput (void); 1933 1934private: 1935 const TestParams m_params; 1936 const PlatformInterface& m_vkp; 1937 const Extensions m_instanceExtensions; 1938 const CustomInstance m_instance; 1939 const InstanceDriver& m_vki; 1940 const VkPhysicalDevice m_physicalDevice; 1941 const deUint32 m_queueFamilyIndex; 1942 const Extensions m_deviceExtensions; 1943 std::vector<std::string> m_deviceEnabledExtensions; 1944 const Unique<VkDevice> m_device; 1945 const DeviceDriver m_vkd; 1946 const VkQueue m_queue; 1947 const VkDeviceSize m_itemSize; 1948 const VkDeviceSize m_blockSize; 1949 SimpleAllocator m_allocator; 1950 const tcu::UVec2 m_textureSize; 1951 const VkFormat m_colorFormat; 1952 Move<VkShaderModule> m_computeShaderModule; 1953 vector<VkImageSp> m_textureImages; 1954 vector<AllocationSp> m_textureImageAllocs; 1955 vector<VkImageViewSp> m_textureViews; 1956 Move<VkSampler> m_whiteBorderSampler; 1957 Move<VkSampler> m_blackBorderSampler; 1958 Move<VkBuffer> m_outputBuffer; 1959 de::MovePtr<Allocation> m_outputBufferAlloc; 1960 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 1961 Move<VkPipelineLayout> m_pipelineLayout; 1962 Move<VkPipeline> m_computePipeline; 1963 Move<VkCommandPool> m_cmdPool; 1964 Move<VkCommandBuffer> m_cmdBuffer; 1965 deUint32 m_outputBufferBinding; 1966}; 1967 1968PushDescriptorImageComputeTestInstance::PushDescriptorImageComputeTestInstance (Context& context, const TestParams& params) 1969 : vkt::TestInstance (context) 1970 , m_params (params) 1971 , m_vkp (context.getPlatformInterface()) 1972 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 1973 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 1974 , m_vki (m_instance.getDriver()) 1975 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 1976 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_COMPUTE_BIT | VK_QUEUE_GRAPHICS_BIT)) 1977 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 1978 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 1979 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 1980 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 1981 , m_itemSize (calcItemSize(m_vki, m_physicalDevice, 2u)) 1982 , m_blockSize (kSizeofVec4 * 2u) 1983 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 1984 , m_textureSize (32, 32) 1985 , m_colorFormat (VK_FORMAT_R8G8B8A8_UNORM) 1986 , m_outputBufferBinding (0) 1987{ 1988} 1989 1990void PushDescriptorImageComputeTestInstance::init (void) 1991{ 1992 const VkComponentMapping componentMappingRGBA = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A }; 1993 1994 // Create texture images 1995 for (deUint32 texIdx = 0; texIdx < 2; texIdx++) 1996 { 1997 VkImageUsageFlags usageFlags = VK_IMAGE_USAGE_TRANSFER_DST_BIT; 1998 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 1999 usageFlags |= VK_IMAGE_USAGE_SAMPLED_BIT; 2000 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) 2001 usageFlags |= VK_IMAGE_USAGE_STORAGE_BIT; 2002 2003 const VkImageCreateInfo textureImageParams = 2004 { 2005 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 2006 DE_NULL, // const void* pNext; 2007 0u, // VkImageCreateFlags flags; 2008 VK_IMAGE_TYPE_2D, // VkImageType imageType; 2009 m_colorFormat, // VkFormat format; 2010 { m_textureSize.x(), m_textureSize.y(), 1u }, // VkExtent3D extent; 2011 1u, // deUint32 mipLevels; 2012 1u, // deUint32 arrayLayers; 2013 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 2014 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 2015 usageFlags, // VkImageUsageFlags usage; 2016 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 2017 1u, // deUint32 queueFamilyIndexCount; 2018 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 2019 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout; 2020 }; 2021 2022 m_textureImages.push_back(VkImageSp(new Unique<VkImage>(createImage(m_vkd, *m_device, &textureImageParams)))); 2023 2024 // Allocate and bind texture image memory 2025 m_textureImageAllocs.push_back(AllocationSp(m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, **m_textureImages.back()), MemoryRequirement::Any).release())); 2026 VK_CHECK(m_vkd.bindImageMemory(*m_device, **m_textureImages.back(), m_textureImageAllocs.back()->getMemory(), m_textureImageAllocs.back()->getOffset())); 2027 } 2028 2029 // Create texture image views 2030 for (deUint32 texIdx = 0; texIdx < 2; texIdx++) 2031 { 2032 const VkImageViewCreateInfo textureViewParams = 2033 { 2034 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 2035 DE_NULL, // const void* pNext; 2036 0u, // VkImageViewCreateFlags flags; 2037 **m_textureImages[texIdx], // VkImage image; 2038 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 2039 m_colorFormat, // VkFormat format; 2040 componentMappingRGBA, // VkChannelMapping channels; 2041 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u } // VkImageSubresourceRange subresourceRange; 2042 }; 2043 2044 m_textureViews.push_back(VkImageViewSp(new Unique<VkImageView>(createImageView(m_vkd, *m_device, &textureViewParams)))); 2045 } 2046 2047 VkClearValue clearValues[2]; 2048 clearValues[0].color.float32[0] = 0.0f; 2049 clearValues[0].color.float32[1] = 1.0f; 2050 clearValues[0].color.float32[2] = 0.0f; 2051 clearValues[0].color.float32[3] = 1.0f; 2052 clearValues[1].color.float32[0] = 1.0f; 2053 clearValues[1].color.float32[1] = 0.0f; 2054 clearValues[1].color.float32[2] = 0.0f; 2055 clearValues[1].color.float32[3] = 1.0f; 2056 2057 const VkImageLayout textureImageLayout = (m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) ? 2058 VK_IMAGE_LAYOUT_GENERAL : VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL; 2059 2060 // Clear textures 2061 for (deUint32 texIdx = 0; texIdx < 2; texIdx++) 2062 { 2063 const VkImageAspectFlags aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; 2064 Move<VkCommandPool> cmdPool; 2065 Move<VkCommandBuffer> cmdBuffer; 2066 2067 cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 2068 cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 2069 2070 const VkImageMemoryBarrier preImageBarrier = 2071 { 2072 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType; 2073 DE_NULL, // const void* pNext; 2074 0u, // VkAccessFlags srcAccessMask; 2075 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags dstAccessMask; 2076 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout oldLayout; 2077 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout newLayout; 2078 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex; 2079 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex; 2080 **m_textureImages[texIdx], // VkImage image; 2081 { // VkImageSubresourceRange subresourceRange; 2082 aspectMask, // VkImageAspect aspect; 2083 0u, // deUint32 baseMipLevel; 2084 1u, // deUint32 mipLevels; 2085 0u, // deUint32 baseArraySlice; 2086 1u // deUint32 arraySize; 2087 } 2088 }; 2089 2090 const VkImageMemoryBarrier postImageBarrier = 2091 { 2092 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType; 2093 DE_NULL, // const void* pNext; 2094 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags srcAccessMask; 2095 VK_ACCESS_SHADER_READ_BIT, // VkAccessFlags dstAccessMask; 2096 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout oldLayout; 2097 textureImageLayout, // VkImageLayout newLayout; 2098 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex; 2099 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex; 2100 **m_textureImages[texIdx], // VkImage image; 2101 { // VkImageSubresourceRange subresourceRange; 2102 aspectMask, // VkImageAspect aspect; 2103 0u, // deUint32 baseMipLevel; 2104 1u, // deUint32 mipLevels; 2105 0u, // deUint32 baseArraySlice; 2106 1u // deUint32 arraySize; 2107 } 2108 }; 2109 2110 const VkImageSubresourceRange clearRange = 2111 { 2112 aspectMask, // VkImageAspectFlags aspectMask; 2113 0u, // deUint32 baseMipLevel; 2114 1u, // deUint32 levelCount; 2115 0u, // deUint32 baseArrayLayer; 2116 1u // deUint32 layerCount; 2117 }; 2118 2119 beginCommandBuffer(m_vkd, *cmdBuffer); 2120 m_vkd.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_HOST_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &preImageBarrier); 2121 m_vkd.cmdClearColorImage(*cmdBuffer, **m_textureImages[texIdx], VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearValues[texIdx].color, 1, &clearRange); 2122 m_vkd.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &postImageBarrier); 2123 endCommandBuffer(m_vkd, *cmdBuffer); 2124 2125 submitCommandsAndWait(m_vkd, *m_device, m_queue, cmdBuffer.get()); 2126 } 2127 2128 // Create samplers: one with white and one with black border color to have a visible effect on switching the sampler 2129 { 2130 VkSamplerCreateInfo samplerParams = 2131 { 2132 VK_STRUCTURE_TYPE_SAMPLER_CREATE_INFO, // VkStructureType sType; 2133 DE_NULL, // const void* pNext; 2134 0u, // VkSamplerCreateFlags flags; 2135 VK_FILTER_NEAREST, // VkFilter magFilter; 2136 VK_FILTER_NEAREST, // VkFilter minFilter; 2137 VK_SAMPLER_MIPMAP_MODE_NEAREST, // VkSamplerMipmapMode mipmapMode; 2138 VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER, // VkSamplerAddressMode addressModeU; 2139 VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER, // VkSamplerAddressMode addressModeV; 2140 VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_BORDER, // VkSamplerAddressMode addressModeW; 2141 0.0f, // float mipLodBias; 2142 VK_FALSE, // VkBool32 anisotropyEnable; 2143 0.0f, // float maxAnisotropy; 2144 VK_FALSE, // VkBool32 compareEnable; 2145 VK_COMPARE_OP_NEVER, // VkCompareOp compareOp; 2146 0.0f, // float minLod; 2147 0.0f, // float maxLod; 2148 VK_BORDER_COLOR_FLOAT_OPAQUE_WHITE, // VkBorderColor borderColor; 2149 VK_FALSE // VkBool32 unnormalizedCoordinates; 2150 }; 2151 2152 m_whiteBorderSampler = createSampler(m_vkd, *m_device, &samplerParams); 2153 samplerParams.borderColor = VK_BORDER_COLOR_FLOAT_OPAQUE_BLACK; 2154 m_blackBorderSampler = createSampler(m_vkd, *m_device, &samplerParams); 2155 } 2156 2157 // Create pipeline layout 2158 { 2159 // Create descriptor set layout 2160 vector<VkDescriptorSetLayoutBinding> layoutBindings; 2161 2162 switch(m_params.descriptorType) 2163 { 2164 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: 2165 { 2166 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 2167 { 2168 m_params.binding, // uint32_t binding; 2169 VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, // VkDescriptorType descriptorType; 2170 1u, // uint32_t descriptorCount; 2171 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2172 DE_NULL // const VkSampler* pImmutableSamplers; 2173 }; 2174 layoutBindings.push_back(descriptorSetLayoutBinding); 2175 m_outputBufferBinding = m_params.binding + 1; 2176 } 2177 break; 2178 2179 case VK_DESCRIPTOR_TYPE_SAMPLER: 2180 { 2181 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingSampler = 2182 { 2183 m_params.binding, // uint32_t binding; 2184 VK_DESCRIPTOR_TYPE_SAMPLER, // VkDescriptorType descriptorType; 2185 1u, // uint32_t descriptorCount; 2186 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2187 DE_NULL // const VkSampler* pImmutableSamplers; 2188 }; 2189 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingTex = 2190 { 2191 m_params.binding + 1, // uint32_t binding; 2192 VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, // VkDescriptorType descriptorType; 2193 1u, // uint32_t descriptorCount; 2194 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2195 DE_NULL // const VkSampler* pImmutableSamplers; 2196 }; 2197 layoutBindings.push_back(descriptorSetLayoutBindingSampler); 2198 layoutBindings.push_back(descriptorSetLayoutBindingTex); 2199 m_outputBufferBinding = m_params.binding + 2; 2200 } 2201 break; 2202 2203 case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: 2204 { 2205 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingSampler = 2206 { 2207 m_params.binding + 1, // uint32_t binding; 2208 VK_DESCRIPTOR_TYPE_SAMPLER, // VkDescriptorType descriptorType; 2209 1u, // uint32_t descriptorCount; 2210 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2211 DE_NULL // const VkSampler* pImmutableSamplers; 2212 }; 2213 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingTex = 2214 { 2215 m_params.binding, // uint32_t binding; 2216 VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, // VkDescriptorType descriptorType; 2217 1u, // uint32_t descriptorCount; 2218 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2219 DE_NULL // const VkSampler* pImmutableSamplers; 2220 }; 2221 layoutBindings.push_back(descriptorSetLayoutBindingSampler); 2222 layoutBindings.push_back(descriptorSetLayoutBindingTex); 2223 m_outputBufferBinding = m_params.binding + 2; 2224 } 2225 break; 2226 2227 case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: 2228 { 2229 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 2230 { 2231 m_params.binding, // uint32_t binding; 2232 VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, // VkDescriptorType descriptorType; 2233 1u, // uint32_t descriptorCount; 2234 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2235 DE_NULL // const VkSampler* pImmutableSamplers; 2236 }; 2237 layoutBindings.push_back(descriptorSetLayoutBinding); 2238 m_outputBufferBinding = m_params.binding + 1; 2239 } 2240 break; 2241 2242 default: 2243 DE_FATAL("unexpected descriptor type"); 2244 break; 2245 } 2246 2247 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindingOutputBuffer = 2248 { 2249 m_outputBufferBinding, // uint32_t binding; 2250 VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // VkDescriptorType descriptorType; 2251 1u, // uint32_t descriptorCount; 2252 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 2253 DE_NULL // const VkSampler* pImmutableSamplers; 2254 }; 2255 2256 layoutBindings.push_back(descriptorSetLayoutBindingOutputBuffer); 2257 2258 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 2259 { 2260 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 2261 DE_NULL, // const void* pNext; 2262 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 2263 (deUint32)layoutBindings.size(), // uint32_t bindingCount; 2264 layoutBindings.data() // const VkDescriptorSetLayoutBinding* pBindings; 2265 }; 2266 2267 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 2268 2269 // Create pipeline layout 2270 const VkPipelineLayoutCreateInfo pipelineLayoutParams = 2271 { 2272 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 2273 DE_NULL, // const void* pNext; 2274 0u, // VkPipelineLayoutCreateFlags flags; 2275 1u, // deUint32 descriptorSetCount; 2276 &(*m_descriptorSetLayout), // const VkDescriptorSetLayout* pSetLayouts; 2277 0u, // deUint32 pushConstantRangeCount; 2278 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 2279 }; 2280 2281 m_pipelineLayout = createPipelineLayout(m_vkd, *m_device, &pipelineLayoutParams); 2282 } 2283 2284 // Create output buffer 2285 { 2286 DE_ASSERT(m_params.numCalls <= 2u); 2287 2288 const VkBufferCreateInfo bufferCreateInfo = 2289 { 2290 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 2291 DE_NULL, // const void* pNext; 2292 0u, // VkBufferCreateFlags flags 2293 m_itemSize * 2u, // VkDeviceSize size; 2294 VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, // VkBufferUsageFlags usage; 2295 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 2296 1u, // deUint32 queueFamilyCount; 2297 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 2298 }; 2299 2300 m_outputBuffer = createBuffer(m_vkd, *m_device, &bufferCreateInfo); 2301 m_outputBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_outputBuffer), MemoryRequirement::HostVisible); 2302 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_outputBuffer, m_outputBufferAlloc->getMemory(), m_outputBufferAlloc->getOffset())); 2303 } 2304 2305 // Create shader 2306 { 2307 m_computeShaderModule = createShaderModule(m_vkd, *m_device, m_context.getBinaryCollection().get("compute"), 0u); 2308 } 2309 2310 // Create pipeline 2311 { 2312 const VkPipelineShaderStageCreateInfo stageCreateInfo = 2313 { 2314 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, // VkStructureType sType; 2315 DE_NULL, // const void* pNext; 2316 0u, // VkPipelineShaderStageCreateFlags flags; 2317 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlagBits stage; 2318 *m_computeShaderModule, // VkShaderModule module; 2319 "main", // const char* pName; 2320 DE_NULL // const VkSpecializationInfo* pSpecializationInfo; 2321 }; 2322 2323 const VkComputePipelineCreateInfo createInfo = 2324 { 2325 VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, // VkStructureType sType; 2326 DE_NULL, // const void* pNext; 2327 0u, // VkPipelineCreateFlags flags; 2328 stageCreateInfo, // VkPipelineShaderStageCreateInfo stage; 2329 *m_pipelineLayout, // VkPipelineLayout layout; 2330 (VkPipeline)0, // VkPipeline basePipelineHandle; 2331 0u, // int32_t basePipelineIndex; 2332 }; 2333 2334 m_computePipeline = createComputePipeline(m_vkd, *m_device, (vk::VkPipelineCache)0u, &createInfo); 2335 } 2336 2337 // Create command pool 2338 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 2339 2340 // Create command buffer 2341 { 2342 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 2343 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 2344 m_vkd.cmdBindPipeline(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_computePipeline); 2345 2346 // Dispatch: Each dispatch switches the input image. 2347 // Output buffer is exposed as a 2 x vec4 sized window. 2348 for (deUint32 dispatchNdx = 0; dispatchNdx < m_params.numCalls; dispatchNdx++) 2349 { 2350 vector<VkSampler> samplers; 2351 vector<VkImageView> imageViews; 2352 2353 samplers.push_back(*m_whiteBorderSampler); 2354 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER) 2355 { 2356 // Vary sampler between draws 2357 samplers.push_back(*m_blackBorderSampler); 2358 } 2359 else 2360 { 2361 // Usa a single sampler 2362 samplers.push_back(*m_whiteBorderSampler); 2363 } 2364 2365 imageViews.push_back(**m_textureViews[0]); 2366 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE || m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER || m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) 2367 { 2368 // Vary image view between draws 2369 imageViews.push_back(**m_textureViews[1]); 2370 } 2371 else 2372 { 2373 // Usa a single image view 2374 imageViews.push_back(**m_textureViews[0]); 2375 } 2376 2377 const VkDescriptorImageInfo descriptorImageInfo = 2378 { 2379 samplers[dispatchNdx], // VkSampler sampler; 2380 imageViews[dispatchNdx], // VkImageView imageView; 2381 textureImageLayout // VkImageLayout imageLayout; 2382 }; 2383 2384 VkWriteDescriptorSet writeDescriptorSet = 2385 { 2386 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 2387 DE_NULL, // const void* pNext; 2388 0u, // VkDescriptorSet dstSet; 2389 m_params.binding, // uint32_t dstBinding; 2390 0u, // uint32_t dstArrayElement; 2391 1u, // uint32_t descriptorCount; 2392 m_params.descriptorType, // VkDescriptorType descriptorType; 2393 &descriptorImageInfo, // const VkDescriptorImageInfo* pImageInfo; 2394 DE_NULL, // const VkDescriptorBufferInfo* pBufferInfo; 2395 DE_NULL // const VkBufferView* pTexelBufferView; 2396 }; 2397 2398 vector<VkWriteDescriptorSet> writeDescriptorSets; 2399 writeDescriptorSets.push_back(writeDescriptorSet); 2400 2401 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER) 2402 { 2403 // Sampler also needs an image. 2404 writeDescriptorSet.dstBinding++; 2405 writeDescriptorSet.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE; 2406 writeDescriptorSets.push_back(writeDescriptorSet); 2407 } 2408 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 2409 { 2410 // Image also needs a sampler. 2411 writeDescriptorSet.dstBinding++; 2412 writeDescriptorSet.descriptorType = VK_DESCRIPTOR_TYPE_SAMPLER; 2413 writeDescriptorSets.push_back(writeDescriptorSet); 2414 } 2415 2416 const VkDescriptorBufferInfo descriptorBufferInfoOutput = 2417 { 2418 *m_outputBuffer, // VkBuffer buffer; 2419 m_itemSize * dispatchNdx, // VkDeviceSize offset; 2420 m_blockSize, // VkDeviceSize range; 2421 }; 2422 2423 // Write output buffer descriptor set 2424 const VkWriteDescriptorSet writeDescriptorSetOutput = 2425 { 2426 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 2427 DE_NULL, // const void* pNext; 2428 0u, // VkDescriptorSet dstSet; 2429 m_outputBufferBinding, // uint32_t dstBinding; 2430 0u, // uint32_t dstArrayElement; 2431 1u, // uint32_t descriptorCount; 2432 VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // VkDescriptorType descriptorType; 2433 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 2434 &descriptorBufferInfoOutput, // const VkDescriptorBufferInfo* pBufferInfo; 2435 DE_NULL // const VkBufferView* pTexelBufferView; 2436 }; 2437 2438 writeDescriptorSets.push_back(writeDescriptorSetOutput); 2439 2440 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_pipelineLayout, 0, (deUint32)writeDescriptorSets.size(), writeDescriptorSets.data()); 2441 m_vkd.cmdDispatch(*m_cmdBuffer, 1, 1, 1); 2442 } 2443 2444 endCommandBuffer(m_vkd, *m_cmdBuffer); 2445 } 2446} 2447 2448PushDescriptorImageComputeTestInstance::~PushDescriptorImageComputeTestInstance (void) 2449{ 2450} 2451 2452tcu::TestStatus PushDescriptorImageComputeTestInstance::iterate (void) 2453{ 2454 init(); 2455 2456 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 2457 2458 return verifyOutput(); 2459} 2460 2461tcu::TestStatus PushDescriptorImageComputeTestInstance::verifyOutput (void) 2462{ 2463 const auto floatsPerDispatch = 8u; // 8 floats (2 vec4s) per dispatch. 2464 std::vector<float> ref (floatsPerDispatch * 2u); 2465 2466 invalidateAlloc(m_vkd, *m_device, *m_outputBufferAlloc); 2467 2468 switch(m_params.descriptorType) 2469 { 2470 case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: 2471 // Dispatch 1: inner & outer = green 2472 ref[0] = ref[4] = 0.0f; 2473 ref[1] = ref[5] = 1.0f; 2474 ref[2] = ref[6] = 0.0f; 2475 ref[3] = ref[7] = 1.0f; 2476 2477 // Dispatch 2: inner & outer = red 2478 ref[8] = ref[12] = 1.0f; 2479 ref[9] = ref[13] = 0.0f; 2480 ref[10] = ref[14] = 0.0f; 2481 ref[11] = ref[15] = 1.0f; 2482 break; 2483 2484 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: 2485 // Dispatch 1: inner = green, outer = white 2486 ref[0] = 0.0f; 2487 ref[1] = 1.0f; 2488 ref[2] = 0.0f; 2489 ref[3] = 1.0f; 2490 2491 ref[4] = 1.0f; 2492 ref[5] = 1.0f; 2493 ref[6] = 1.0f; 2494 ref[7] = 1.0f; 2495 2496 // Dispatch 2: inner = red, outer = black 2497 ref[8] = 1.0f; 2498 ref[9] = 0.0f; 2499 ref[10] = 0.0f; 2500 ref[11] = 1.0f; 2501 2502 ref[12] = 0.0f; 2503 ref[13] = 0.0f; 2504 ref[14] = 0.0f; 2505 ref[15] = 1.0f; 2506 break; 2507 2508 case VK_DESCRIPTOR_TYPE_SAMPLER: 2509 // Dispatch 1: inner = green, outer = white 2510 ref[0] = 0.0f; 2511 ref[1] = 1.0f; 2512 ref[2] = 0.0f; 2513 ref[3] = 1.0f; 2514 2515 ref[4] = 1.0f; 2516 ref[5] = 1.0f; 2517 ref[6] = 1.0f; 2518 ref[7] = 1.0f; 2519 2520 // Dispatch 2: inner = green, outer = black 2521 ref[8] = 0.0f; 2522 ref[9] = 1.0f; 2523 ref[10] = 0.0f; 2524 ref[11] = 1.0f; 2525 2526 ref[12] = 0.0f; 2527 ref[13] = 0.0f; 2528 ref[14] = 0.0f; 2529 ref[15] = 1.0f; 2530 break; 2531 2532 case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: 2533 // Dispatch 1: inner = green, outer = white 2534 ref[0] = 0.0f; 2535 ref[1] = 1.0f; 2536 ref[2] = 0.0f; 2537 ref[3] = 1.0f; 2538 2539 ref[4] = 1.0f; 2540 ref[5] = 1.0f; 2541 ref[6] = 1.0f; 2542 ref[7] = 1.0f; 2543 2544 // Dispatch 2: inner = red, outer = white 2545 ref[8] = 1.0f; 2546 ref[9] = 0.0f; 2547 ref[10] = 0.0f; 2548 ref[11] = 1.0f; 2549 2550 ref[12] = 1.0f; 2551 ref[13] = 1.0f; 2552 ref[14] = 1.0f; 2553 ref[15] = 1.0f; 2554 break; 2555 2556 default: 2557 DE_FATAL("unexpected descriptor type"); 2558 break; 2559 } 2560 2561 // Verify result 2562 const auto bufferDataPtr = reinterpret_cast<const char*>(m_outputBufferAlloc->getHostPtr()); 2563 const auto blockSize = static_cast<size_t>(m_blockSize); 2564 2565 for (deUint32 dispatchNdx = 0u; dispatchNdx < m_params.numCalls; ++dispatchNdx) 2566 { 2567 const auto refIdx = floatsPerDispatch * dispatchNdx; 2568 const auto bufferOffset = m_itemSize * dispatchNdx; // Each dispatch uses m_itemSize bytes in the buffer to meet alignment reqs. 2569 2570 if (deMemCmp(&ref[refIdx], bufferDataPtr + bufferOffset, blockSize) != 0) 2571 { 2572 std::vector<float> buffferValues (floatsPerDispatch); 2573 std::vector<float> refValues (floatsPerDispatch); 2574 2575 deMemcpy(refValues.data(), &ref[refIdx], blockSize); 2576 deMemcpy(buffferValues.data(), bufferDataPtr + bufferOffset, blockSize); 2577 2578 std::ostringstream msg; 2579 msg << "Output mismatch at dispatch " << dispatchNdx << ": Reference "; 2580 for (deUint32 i = 0; i < floatsPerDispatch; ++i) 2581 msg << ((i == 0) ? "[" : ", ") << refValues[i]; 2582 msg << "]; Buffer "; 2583 for (deUint32 i = 0; i < floatsPerDispatch; ++i) 2584 msg << ((i == 0) ? "[" : ", ") << buffferValues[i]; 2585 msg << "]"; 2586 2587 m_context.getTestContext().getLog() << tcu::TestLog::Message << msg.str() << tcu::TestLog::EndMessage; 2588 return tcu::TestStatus::fail("Output mismatch"); 2589 } 2590 } 2591 2592 return tcu::TestStatus::pass("Output matches expected values"); 2593} 2594 2595class PushDescriptorImageComputeTest : public vkt::TestCase 2596{ 2597public: 2598 PushDescriptorImageComputeTest (tcu::TestContext& testContext, 2599 const string& name, 2600 const TestParams& params); 2601 ~PushDescriptorImageComputeTest (void); 2602 void initPrograms (SourceCollections& sourceCollections) const; 2603 TestInstance* createInstance (Context& context) const; 2604 2605protected: 2606 const TestParams m_params; 2607}; 2608 2609PushDescriptorImageComputeTest::PushDescriptorImageComputeTest (tcu::TestContext& testContext, 2610 const string& name, 2611 const TestParams& params) 2612 : vkt::TestCase (testContext, name) 2613 , m_params (params) 2614{ 2615} 2616 2617PushDescriptorImageComputeTest::~PushDescriptorImageComputeTest (void) 2618{ 2619} 2620 2621TestInstance* PushDescriptorImageComputeTest::createInstance (Context& context) const 2622{ 2623 return new PushDescriptorImageComputeTestInstance(context, m_params); 2624} 2625 2626void PushDescriptorImageComputeTest::initPrograms (SourceCollections& sourceCollections) const 2627{ 2628 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER) 2629 { 2630 const string computeSrc = 2631 "#version 450\n" 2632 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform sampler2D combinedSampler;\n" 2633 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") writeonly buffer Output\n" 2634 "{\n" 2635 " vec4 innerColor;\n" 2636 " vec4 outerColor;\n" 2637 "} outData;\n" 2638 "\n" 2639 "void main()\n" 2640 "{\n" 2641 " outData.innerColor = texture(combinedSampler, vec2(0.5));\n" 2642 " outData.outerColor = texture(combinedSampler, vec2(-0.1));\n" 2643 "}\n"; 2644 2645 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 2646 } 2647 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLER) 2648 { 2649 const string computeSrc = 2650 "#version 450\n" 2651 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform sampler texSampler;\n" 2652 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") uniform texture2D texImage;\n" 2653 "layout(set = 0, binding = " + de::toString(m_params.binding + 2) + ") writeonly buffer Output\n" 2654 "{\n" 2655 " vec4 innerColor;\n" 2656 " vec4 outerColor;\n" 2657 "} outData;\n" 2658 "\n" 2659 "void main()\n" 2660 "{\n" 2661 " outData.innerColor = texture(sampler2D(texImage, texSampler), vec2(0.5));\n" 2662 " outData.outerColor = texture(sampler2D(texImage, texSampler), vec2(-0.1));\n" 2663 "}\n"; 2664 2665 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 2666 } 2667 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE) 2668 { 2669 const string computeSrc = 2670 "#version 450\n" 2671 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") uniform sampler texSampler;\n" 2672 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform texture2D texImage;\n" 2673 "layout(set = 0, binding = " + de::toString(m_params.binding + 2) + ") writeonly buffer Output\n" 2674 "{\n" 2675 " vec4 innerColor;\n" 2676 " vec4 outerColor;\n" 2677 "} outData;\n" 2678 "\n" 2679 "void main()\n" 2680 "{\n" 2681 " outData.innerColor = texture(sampler2D(texImage, texSampler), vec2(0.5));\n" 2682 " outData.outerColor = texture(sampler2D(texImage, texSampler), vec2(-0.1));\n" 2683 "}\n"; 2684 2685 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 2686 } 2687 else if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE) 2688 { 2689 const string computeSrc = 2690 "#version 450\n" 2691 "layout(set = 0, binding = " + de::toString(m_params.binding) + ", rgba8) uniform readonly image2D storageImage;\n" 2692 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") writeonly buffer Output\n" 2693 "{\n" 2694 " vec4 innerColor;\n" 2695 " vec4 outerColor;\n" 2696 "} outData;\n" 2697 "\n" 2698 "void main()\n" 2699 "{\n" 2700 " outData.innerColor = imageLoad(storageImage, ivec2(0));\n" 2701 " outData.outerColor = imageLoad(storageImage, ivec2(0));\n" 2702 "}\n"; 2703 2704 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 2705 } 2706 else 2707 { 2708 DE_FATAL("Unexpected descriptor type"); 2709 } 2710} 2711 2712class PushDescriptorTexelBufferGraphicsTestInstance : public vkt::TestInstance 2713{ 2714public: 2715 PushDescriptorTexelBufferGraphicsTestInstance (Context& context, const TestParams& params); 2716 virtual ~PushDescriptorTexelBufferGraphicsTestInstance (void); 2717 void init (void); 2718 virtual tcu::TestStatus iterate (void); 2719 tcu::TestStatus verifyImage (void); 2720 2721private: 2722 const TestParams m_params; 2723 const PlatformInterface& m_vkp; 2724 const Extensions m_instanceExtensions; 2725 const CustomInstance m_instance; 2726 const InstanceDriver& m_vki; 2727 const VkPhysicalDevice m_physicalDevice; 2728 const deUint32 m_queueFamilyIndex; 2729 const Extensions m_deviceExtensions; 2730 std::vector<std::string> m_deviceEnabledExtensions; 2731 const Unique<VkDevice> m_device; 2732 const DeviceDriver m_vkd; 2733 const VkQueue m_queue; 2734 SimpleAllocator m_allocator; 2735 const tcu::UVec2 m_renderSize; 2736 const VkFormat m_colorFormat; 2737 Move<VkImage> m_colorImage; 2738 de::MovePtr<Allocation> m_colorImageAlloc; 2739 Move<VkImageView> m_colorAttachmentView; 2740 vector<VkBufferSp> m_buffers; 2741 vector<AllocationSp> m_bufferAllocs; 2742 vector<VkBufferViewSp> m_bufferViews; 2743 const VkFormat m_bufferFormat; 2744 RenderPassWrapper m_renderPass; 2745 Move<VkFramebuffer> m_framebuffer; 2746 ShaderWrapper m_vertexShaderModule; 2747 ShaderWrapper m_fragmentShaderModule; 2748 Move<VkBuffer> m_vertexBuffer; 2749 de::MovePtr<Allocation> m_vertexBufferAlloc; 2750 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 2751 PipelineLayoutWrapper m_preRasterizationStatePipelineLayout; 2752 PipelineLayoutWrapper m_fragmentStatePipelineLayout; 2753 GraphicsPipelineWrapper m_graphicsPipeline; 2754 Move<VkCommandPool> m_cmdPool; 2755 Move<VkCommandBuffer> m_cmdBuffer; 2756 vector<Vertex4RGBA> m_vertices; 2757}; 2758 2759PushDescriptorTexelBufferGraphicsTestInstance::PushDescriptorTexelBufferGraphicsTestInstance (Context& context, const TestParams& params) 2760 : vkt::TestInstance (context) 2761 , m_params (params) 2762 , m_vkp (context.getPlatformInterface()) 2763 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 2764 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 2765 , m_vki (m_instance.getDriver()) 2766 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 2767 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_GRAPHICS_BIT)) 2768 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 2769 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 2770 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 2771 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 2772 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 2773 , m_renderSize (32, 32) 2774 , m_colorFormat (VK_FORMAT_R8G8B8A8_UNORM) 2775 , m_bufferFormat (VK_FORMAT_R32G32B32A32_SFLOAT) 2776 , m_graphicsPipeline (m_vki, m_vkd, m_physicalDevice, *m_device, m_deviceEnabledExtensions, params.pipelineConstructionType) 2777 , m_vertices (createQuads(params.numCalls, 0.25f)) 2778{ 2779} 2780 2781void PushDescriptorTexelBufferGraphicsTestInstance::init (void) 2782{ 2783 const VkComponentMapping componentMappingRGBA = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A }; 2784 2785 // Create color image 2786 { 2787 2788 const VkImageCreateInfo colorImageParams = 2789 { 2790 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 2791 DE_NULL, // const void* pNext; 2792 0u, // VkImageCreateFlags flags; 2793 VK_IMAGE_TYPE_2D, // VkImageType imageType; 2794 m_colorFormat, // VkFormat format; 2795 { m_renderSize.x(), m_renderSize.y(), 1u }, // VkExtent3D extent; 2796 1u, // deUint32 mipLevels; 2797 1u, // deUint32 arrayLayers; 2798 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 2799 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 2800 VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT, // VkImageUsageFlags usage; 2801 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 2802 1u, // deUint32 queueFamilyIndexCount; 2803 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 2804 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout; 2805 }; 2806 2807 m_colorImage = createImage(m_vkd, *m_device, &colorImageParams); 2808 2809 // Allocate and bind color image memory 2810 m_colorImageAlloc = m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, *m_colorImage), MemoryRequirement::Any); 2811 VK_CHECK(m_vkd.bindImageMemory(*m_device, *m_colorImage, m_colorImageAlloc->getMemory(), m_colorImageAlloc->getOffset())); 2812 } 2813 2814 // Create color attachment view 2815 { 2816 const VkImageViewCreateInfo colorAttachmentViewParams = 2817 { 2818 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 2819 DE_NULL, // const void* pNext; 2820 0u, // VkImageViewCreateFlags flags; 2821 *m_colorImage, // VkImage image; 2822 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 2823 m_colorFormat, // VkFormat format; 2824 componentMappingRGBA, // VkChannelMapping channels; 2825 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u } // VkImageSubresourceRange subresourceRange; 2826 }; 2827 2828 m_colorAttachmentView = createImageView(m_vkd, *m_device, &colorAttachmentViewParams); 2829 } 2830 2831 // Create buffers 2832 VkBufferUsageFlags2CreateInfoKHR bufferUsageFlags2 = vk::initVulkanStructure(); 2833 for (deUint32 bufIdx = 0; bufIdx < DE_LENGTH_OF_ARRAY(defaultTestColors); bufIdx++) 2834 { 2835 const VkBufferUsageFlags usageFlags = m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER ? VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT : VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT; 2836 2837 VkBufferCreateInfo bufferCreateInfo 2838 { 2839 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 2840 DE_NULL, // const void* pNext; 2841 0u, // VkBufferCreateFlags flags 2842 kSizeofVec4, // VkDeviceSize size; 2843 usageFlags, // VkBufferUsageFlags usage; 2844 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 2845 1u, // deUint32 queueFamilyCount; 2846 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 2847 }; 2848 2849 if (m_params.useMaintenance5) 2850 { 2851 bufferUsageFlags2.usage = (VkBufferUsageFlagBits2KHR)usageFlags; 2852 bufferCreateInfo.pNext = &bufferUsageFlags2; 2853 bufferCreateInfo.usage = 0; 2854 } 2855 2856 m_buffers.push_back(VkBufferSp(new Unique<VkBuffer>(createBuffer(m_vkd, *m_device, &bufferCreateInfo)))); 2857 m_bufferAllocs.push_back(AllocationSp(m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, **m_buffers[bufIdx]), MemoryRequirement::HostVisible).release())); 2858 VK_CHECK(m_vkd.bindBufferMemory(*m_device, **m_buffers[bufIdx], m_bufferAllocs[bufIdx]->getMemory(), m_bufferAllocs[bufIdx]->getOffset())); 2859 2860 deMemcpy(m_bufferAllocs[bufIdx]->getHostPtr(), &defaultTestColors[bufIdx], static_cast<size_t>(kSizeofVec4)); 2861 flushAlloc(m_vkd, *m_device, *m_bufferAllocs[bufIdx]); 2862 } 2863 2864 // Create buffer views 2865 for (deUint32 bufIdx = 0; bufIdx < DE_LENGTH_OF_ARRAY(defaultTestColors); bufIdx++) 2866 { 2867 const VkBufferViewCreateInfo bufferViewParams = 2868 { 2869 VK_STRUCTURE_TYPE_BUFFER_VIEW_CREATE_INFO, // VkStructureType sType; 2870 DE_NULL, // const void* pNext; 2871 0u, // VkBufferViewCreateFlags flags; 2872 **m_buffers[bufIdx], // VkBuffer buffer; 2873 m_bufferFormat, // VkFormat format; 2874 0u, // VkDeviceSize offset; 2875 VK_WHOLE_SIZE // VkDeviceSize range; 2876 }; 2877 2878 m_bufferViews.push_back(VkBufferViewSp(new Unique<VkBufferView>(createBufferView(m_vkd, *m_device, &bufferViewParams)))); 2879 } 2880 2881 // Create render pass 2882 m_renderPass = RenderPassWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, m_colorFormat); 2883 2884 // Create framebuffer 2885 { 2886 const VkImageView attachmentBindInfos[] = 2887 { 2888 *m_colorAttachmentView 2889 }; 2890 2891 const VkFramebufferCreateInfo framebufferParams = 2892 { 2893 VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, // VkStructureType sType; 2894 DE_NULL, // const void* pNext; 2895 0u, // VkFramebufferCreateFlags flags; 2896 *m_renderPass, // VkRenderPass renderPass; 2897 1u, // deUint32 attachmentCount; 2898 attachmentBindInfos, // const VkImageView* pAttachments; 2899 (deUint32)m_renderSize.x(), // deUint32 width; 2900 (deUint32)m_renderSize.y(), // deUint32 height; 2901 1u // deUint32 layers; 2902 }; 2903 2904 m_renderPass.createFramebuffer(m_vkd, *m_device, &framebufferParams, *m_colorImage); 2905 } 2906 2907 // Create pipeline layout 2908 { 2909 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 2910 { 2911 m_params.binding, // uint32_t binding; 2912 m_params.descriptorType, // VkDescriptorType descriptorType; 2913 1u, // uint32_t descriptorCount; 2914 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 2915 DE_NULL // const VkSampler* pImmutableSamplers; 2916 }; 2917 2918 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 2919 { 2920 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 2921 DE_NULL, // const void* pNext; 2922 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 2923 1u, // uint32_t bindingCount; 2924 &descriptorSetLayoutBinding // const VkDescriptorSetLayoutBinding* pBindings; 2925 }; 2926 2927 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 2928 2929 VkPipelineLayoutCreateFlags pipelineLayoutFlags = (m_params.pipelineConstructionType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) ? 0u : deUint32(VK_PIPELINE_LAYOUT_CREATE_INDEPENDENT_SETS_BIT_EXT); 2930 VkPipelineLayoutCreateInfo pipelineLayoutParams 2931 { 2932 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 2933 DE_NULL, // const void* pNext; 2934 pipelineLayoutFlags, // VkPipelineLayoutCreateFlags flags; 2935 0u, // deUint32 setLayoutCount; 2936 DE_NULL, // const VkDescriptorSetLayout* pSetLayouts; 2937 0u, // deUint32 pushConstantRangeCount; 2938 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 2939 }; 2940 2941 m_preRasterizationStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 2942 pipelineLayoutParams.setLayoutCount = 1u; 2943 pipelineLayoutParams.pSetLayouts = &(*m_descriptorSetLayout); 2944 m_fragmentStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 2945 } 2946 2947 // Create shaders 2948 { 2949 m_vertexShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("vert"), 0u); 2950 m_fragmentShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("frag"), 0u); 2951 } 2952 2953 // Create pipeline 2954 { 2955 const VkVertexInputBindingDescription vertexInputBindingDescription = 2956 { 2957 0u, // deUint32 binding; 2958 sizeof(Vertex4RGBA), // deUint32 strideInBytes; 2959 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputStepRate stepRate; 2960 }; 2961 2962 const VkVertexInputAttributeDescription vertexInputAttributeDescriptions[] = 2963 { 2964 { 2965 0u, // deUint32 location; 2966 0u, // deUint32 binding; 2967 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 2968 0u // deUint32 offsetInBytes; 2969 }, 2970 { 2971 1u, // deUint32 location; 2972 0u, // deUint32 binding; 2973 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 2974 DE_OFFSET_OF(Vertex4RGBA, color) // deUint32 offset; 2975 } 2976 }; 2977 2978 const VkPipelineVertexInputStateCreateInfo vertexInputStateParams = 2979 { 2980 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // VkStructureType sType; 2981 DE_NULL, // const void* pNext; 2982 0u, // vkPipelineVertexInputStateCreateFlags flags; 2983 1u, // deUint32 bindingCount; 2984 &vertexInputBindingDescription, // const VkVertexInputBindingDescription* pVertexBindingDescriptions; 2985 2u, // deUint32 attributeCount; 2986 vertexInputAttributeDescriptions // const VkVertexInputAttributeDescription* pVertexAttributeDescriptions; 2987 }; 2988 2989 const vector<VkViewport> viewports { makeViewport(m_renderSize) }; 2990 const vector<VkRect2D> scissors { makeRect2D(m_renderSize) }; 2991 2992 m_graphicsPipeline.setMonolithicPipelineLayout(m_fragmentStatePipelineLayout) 2993 .setDefaultRasterizationState() 2994 .setDefaultDepthStencilState() 2995 .setDefaultMultisampleState() 2996 .setDefaultColorBlendState() 2997 .setupVertexInputState(&vertexInputStateParams) 2998 .setupPreRasterizationShaderState(viewports, 2999 scissors, 3000 m_preRasterizationStatePipelineLayout, 3001 *m_renderPass, 3002 0u, 3003 m_vertexShaderModule) 3004 .setupFragmentShaderState(m_fragmentStatePipelineLayout, *m_renderPass, 0u, m_fragmentShaderModule) 3005 .setupFragmentOutputState(*m_renderPass) 3006 .buildPipeline(); 3007 } 3008 3009 // Create vertex buffer 3010 { 3011 const VkBufferCreateInfo vertexBufferParams = 3012 { 3013 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 3014 DE_NULL, // const void* pNext; 3015 0u, // VkBufferCreateFlags flags; 3016 (VkDeviceSize)(sizeof(Vertex4RGBA) * m_vertices.size()), // VkDeviceSize size; 3017 VK_BUFFER_USAGE_VERTEX_BUFFER_BIT, // VkBufferUsageFlags usage; 3018 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 3019 1u, // deUint32 queueFamilyCount; 3020 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 3021 }; 3022 3023 m_vertexBuffer = createBuffer(m_vkd, *m_device, &vertexBufferParams); 3024 m_vertexBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_vertexBuffer), MemoryRequirement::HostVisible); 3025 3026 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_vertexBuffer, m_vertexBufferAlloc->getMemory(), m_vertexBufferAlloc->getOffset())); 3027 3028 // Load vertices into vertex buffer 3029 deMemcpy(m_vertexBufferAlloc->getHostPtr(), m_vertices.data(), m_vertices.size() * sizeof(Vertex4RGBA)); 3030 flushAlloc(m_vkd, *m_device, *m_vertexBufferAlloc); 3031 } 3032 3033 // Create command pool 3034 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 3035 3036 // Create command buffer 3037 { 3038 const VkClearValue attachmentClearValue = defaultClearValue(m_colorFormat); 3039 const VkDeviceSize vertexBufferOffset = 0; 3040 3041 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 3042 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 3043 m_renderPass.begin(m_vkd, *m_cmdBuffer, makeRect2D(0, 0, m_renderSize.x(), m_renderSize.y()), attachmentClearValue); 3044 m_graphicsPipeline.bind(*m_cmdBuffer); 3045 m_vkd.cmdBindVertexBuffers(*m_cmdBuffer, 0, 1, &m_vertexBuffer.get(), &vertexBufferOffset); 3046 3047 // Draw quads. Switch buffer view between draws. 3048 for (deUint32 quadNdx = 0; quadNdx < m_params.numCalls; quadNdx++) 3049 { 3050 VkWriteDescriptorSet writeDescriptorSet = 3051 { 3052 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 3053 DE_NULL, // const void* pNext; 3054 0u, // VkDescriptorSet dstSet; 3055 m_params.binding, // uint32_t dstBinding; 3056 0u, // uint32_t dstArrayElement; 3057 1u, // uint32_t descriptorCount; 3058 m_params.descriptorType, // VkDescriptorType descriptorType; 3059 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 3060 DE_NULL, // const VkDescriptorBufferInfo* pBufferInfo; 3061 &m_bufferViews[quadNdx]->get() // const VkBufferView* pTexelBufferView; 3062 }; 3063 3064 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *m_fragmentStatePipelineLayout, 0, 1u, &writeDescriptorSet); 3065 m_vkd.cmdDraw(*m_cmdBuffer, 6, 1, 6 * quadNdx, 0); 3066 } 3067 3068 m_renderPass.end(m_vkd, *m_cmdBuffer); 3069 endCommandBuffer(m_vkd, *m_cmdBuffer); 3070 } 3071} 3072 3073PushDescriptorTexelBufferGraphicsTestInstance::~PushDescriptorTexelBufferGraphicsTestInstance (void) 3074{ 3075} 3076 3077tcu::TestStatus PushDescriptorTexelBufferGraphicsTestInstance::iterate (void) 3078{ 3079 init(); 3080 3081 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 3082 3083 return verifyImage(); 3084} 3085 3086tcu::TestStatus PushDescriptorTexelBufferGraphicsTestInstance::verifyImage (void) 3087{ 3088 const tcu::TextureFormat tcuColorFormat = mapVkFormat(m_colorFormat); 3089 const tcu::TextureFormat tcuDepthFormat = tcu::TextureFormat(); 3090 const ColorVertexShader vertexShader; 3091 const ColorFragmentShader fragmentShader (tcuColorFormat, tcuDepthFormat); 3092 const rr::Program program (&vertexShader, &fragmentShader); 3093 ReferenceRenderer refRenderer (m_renderSize.x(), m_renderSize.y(), 1, tcuColorFormat, tcuDepthFormat, &program); 3094 bool compareOk = false; 3095 3096 // Render reference image 3097 { 3098 for (deUint32 quadIdx = 0; quadIdx < m_params.numCalls; quadIdx++) 3099 for (deUint32 vertexIdx = 0; vertexIdx < 6; vertexIdx++) 3100 m_vertices[quadIdx * 6 + vertexIdx].color.xyzw() = defaultTestColors[quadIdx]; 3101 3102 refRenderer.draw(rr::RenderState(refRenderer.getViewportState(), m_context.getDeviceProperties().limits.subPixelPrecisionBits), 3103 rr::PRIMITIVETYPE_TRIANGLES, m_vertices); 3104 } 3105 3106 // Compare result with reference image 3107 { 3108 de::MovePtr<tcu::TextureLevel> result = readColorAttachment(m_vkd, *m_device, m_queue, m_queueFamilyIndex, m_allocator, *m_colorImage, m_colorFormat, m_renderSize); 3109 3110 compareOk = tcu::intThresholdPositionDeviationCompare(m_context.getTestContext().getLog(), 3111 "IntImageCompare", 3112 "Image comparison", 3113 refRenderer.getAccess(), 3114 result->getAccess(), 3115 tcu::UVec4(2, 2, 2, 2), 3116 tcu::IVec3(1, 1, 0), 3117 true, 3118 tcu::COMPARE_LOG_RESULT); 3119 } 3120 3121 if (compareOk) 3122 return tcu::TestStatus::pass("Result image matches reference"); 3123 else 3124 return tcu::TestStatus::fail("Image mismatch"); 3125} 3126 3127class PushDescriptorTexelBufferGraphicsTest : public vkt::TestCase 3128{ 3129public: 3130 PushDescriptorTexelBufferGraphicsTest (tcu::TestContext& testContext, 3131 const string& name, 3132 const TestParams& params); 3133 ~PushDescriptorTexelBufferGraphicsTest (void); 3134 3135 void checkSupport (Context& context) const; 3136 void initPrograms (SourceCollections& sourceCollections) const; 3137 TestInstance* createInstance (Context& context) const; 3138 3139protected: 3140 const TestParams m_params; 3141}; 3142 3143PushDescriptorTexelBufferGraphicsTest::PushDescriptorTexelBufferGraphicsTest (tcu::TestContext& testContext, 3144 const string& name, 3145 const TestParams& params) 3146 : vkt::TestCase (testContext, name) 3147 , m_params (params) 3148{ 3149} 3150 3151PushDescriptorTexelBufferGraphicsTest::~PushDescriptorTexelBufferGraphicsTest (void) 3152{ 3153} 3154 3155TestInstance* PushDescriptorTexelBufferGraphicsTest::createInstance (Context& context) const 3156{ 3157 return new PushDescriptorTexelBufferGraphicsTestInstance(context, m_params); 3158} 3159 3160void PushDescriptorTexelBufferGraphicsTest::checkSupport(Context& context) const 3161{ 3162 if (m_params.useMaintenance5) 3163 context.requireDeviceFunctionality("VK_KHR_maintenance5"); 3164 3165 checkPipelineConstructionRequirements(context.getInstanceInterface(), context.getPhysicalDevice(), m_params.pipelineConstructionType); 3166} 3167 3168void PushDescriptorTexelBufferGraphicsTest::initPrograms (SourceCollections& sourceCollections) const 3169{ 3170 const string vertexSrc = 3171 "#version 450\n" 3172 "layout(location = 0) in highp vec4 position;\n" 3173 "layout(location = 1) in highp vec4 texcoordVtx;\n" 3174 "layout(location = 0) out highp vec2 texcoordFrag;\n" 3175 "\n" 3176 "out gl_PerVertex { vec4 gl_Position; };\n" 3177 "\n" 3178 "void main()\n" 3179 "{\n" 3180 " gl_Position = position;\n" 3181 " texcoordFrag = texcoordVtx.xy;\n" 3182 "}\n"; 3183 3184 sourceCollections.glslSources.add("vert") << glu::VertexSource(vertexSrc); 3185 3186 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER) 3187 { 3188 const string fragmentSrc = 3189 "#version 450\n" 3190 "layout(location = 0) in highp vec2 texcoordFrag;\n" 3191 "layout(location = 0) out highp vec4 fragColor;\n" 3192 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform textureBuffer texelBuffer;\n" 3193 "\n" 3194 "void main (void)\n" 3195 "{\n" 3196 " fragColor = texelFetch(texelBuffer, 0);\n" 3197 "}\n"; 3198 3199 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 3200 } 3201 else 3202 { 3203 DE_ASSERT(m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER); 3204 const string fragmentSrc = 3205 "#version 450\n" 3206 "layout(location = 0) in highp vec2 texcoordFrag;\n" 3207 "layout(location = 0) out highp vec4 fragColor;\n" 3208 "layout(set = 0, binding = " + de::toString(m_params.binding) + ", rgba32f) uniform readonly imageBuffer texelBuffer;\n" 3209 "\n" 3210 "void main (void)\n" 3211 "{\n" 3212 " fragColor = imageLoad(texelBuffer, 0);\n" 3213 "}\n"; 3214 3215 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 3216 } 3217} 3218 3219class PushDescriptorTexelBufferComputeTestInstance : public vkt::TestInstance 3220{ 3221public: 3222 PushDescriptorTexelBufferComputeTestInstance (Context& context, const TestParams& params); 3223 virtual ~PushDescriptorTexelBufferComputeTestInstance (void); 3224 void init (void); 3225 virtual tcu::TestStatus iterate (void); 3226 tcu::TestStatus verifyOutput (void); 3227 3228private: 3229 const TestParams m_params; 3230 const PlatformInterface& m_vkp; 3231 const Extensions m_instanceExtensions; 3232 const CustomInstance m_instance; 3233 const InstanceDriver& m_vki; 3234 const VkPhysicalDevice m_physicalDevice; 3235 const deUint32 m_queueFamilyIndex; 3236 const Extensions m_deviceExtensions; 3237 std::vector<std::string> m_deviceEnabledExtensions; 3238 const Unique<VkDevice> m_device; 3239 const DeviceDriver m_vkd; 3240 const VkQueue m_queue; 3241 const VkDeviceSize m_itemSize; 3242 SimpleAllocator m_allocator; 3243 vector<VkBufferSp> m_buffers; 3244 vector<AllocationSp> m_bufferAllocs; 3245 vector<VkBufferViewSp> m_bufferViews; 3246 const VkFormat m_bufferFormat; 3247 Move<VkShaderModule> m_computeShaderModule; 3248 Move<VkBuffer> m_outputBuffer; 3249 de::MovePtr<Allocation> m_outputBufferAlloc; 3250 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 3251 Move<VkPipelineLayout> m_pipelineLayout; 3252 Move<VkPipeline> m_computePipeline; 3253 Move<VkCommandPool> m_cmdPool; 3254 Move<VkCommandBuffer> m_cmdBuffer; 3255}; 3256 3257PushDescriptorTexelBufferComputeTestInstance::PushDescriptorTexelBufferComputeTestInstance (Context& context, const TestParams& params) 3258 : vkt::TestInstance (context) 3259 , m_params (params) 3260 , m_vkp (context.getPlatformInterface()) 3261 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 3262 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 3263 , m_vki (m_instance.getDriver()) 3264 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 3265 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_COMPUTE_BIT)) 3266 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 3267 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 3268 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 3269 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 3270 , m_itemSize (calcItemSize(m_vki, m_physicalDevice)) 3271 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 3272 , m_bufferFormat (VK_FORMAT_R32G32B32A32_SFLOAT) 3273{ 3274} 3275 3276void PushDescriptorTexelBufferComputeTestInstance::init (void) 3277{ 3278 // Create buffers 3279 for (deUint32 bufIdx = 0; bufIdx < DE_LENGTH_OF_ARRAY(defaultTestColors); bufIdx++) 3280 { 3281 const VkBufferUsageFlags usageFlags = m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER ? VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT : VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT; 3282 3283 const VkBufferCreateInfo bufferCreateInfo = 3284 { 3285 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 3286 DE_NULL, // const void* pNext; 3287 0u, // VkBufferCreateFlags flags 3288 kSizeofVec4, // VkDeviceSize size; 3289 usageFlags, // VkBufferUsageFlags usage; 3290 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 3291 1u, // deUint32 queueFamilyCount; 3292 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 3293 }; 3294 3295 m_buffers.push_back(VkBufferSp(new Unique<VkBuffer>(createBuffer(m_vkd, *m_device, &bufferCreateInfo)))); 3296 m_bufferAllocs.push_back(AllocationSp(m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, **m_buffers[bufIdx]), MemoryRequirement::HostVisible).release())); 3297 VK_CHECK(m_vkd.bindBufferMemory(*m_device, **m_buffers[bufIdx], m_bufferAllocs[bufIdx]->getMemory(), m_bufferAllocs[bufIdx]->getOffset())); 3298 3299 deMemcpy(m_bufferAllocs[bufIdx]->getHostPtr(), &defaultTestColors[bufIdx], static_cast<size_t>(kSizeofVec4)); 3300 flushAlloc(m_vkd, *m_device, *m_bufferAllocs[bufIdx]); 3301 } 3302 3303 // Create buffer views 3304 for (deUint32 bufIdx = 0; bufIdx < DE_LENGTH_OF_ARRAY(defaultTestColors); bufIdx++) 3305 { 3306 const VkBufferViewCreateInfo bufferViewParams = 3307 { 3308 VK_STRUCTURE_TYPE_BUFFER_VIEW_CREATE_INFO, // VkStructureType sType; 3309 DE_NULL, // const void* pNext; 3310 0u, // VkBufferViewCreateFlags flags; 3311 **m_buffers[bufIdx], // VkBuffer buffer; 3312 m_bufferFormat, // VkFormat format; 3313 0u, // VkDeviceSize offset; 3314 VK_WHOLE_SIZE // VkDeviceSize range; 3315 }; 3316 3317 m_bufferViews.push_back(VkBufferViewSp(new Unique<VkBufferView>(createBufferView(m_vkd, *m_device, &bufferViewParams)))); 3318 } 3319 3320 // Create pipeline layout 3321 { 3322 vector<VkDescriptorSetLayoutBinding> layoutBindings; 3323 3324 const VkDescriptorSetLayoutBinding descriptorSetLayoutBindings[] = 3325 { 3326 { 3327 m_params.binding, // uint32_t binding; 3328 m_params.descriptorType, // VkDescriptorType descriptorType; 3329 1u, // uint32_t descriptorCount; 3330 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 3331 DE_NULL // const VkSampler* pImmutableSamplers; 3332 }, 3333 { 3334 m_params.binding + 1, // uint32_t binding; 3335 VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // VkDescriptorType descriptorType; 3336 1u, // uint32_t descriptorCount; 3337 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlags stageFlags; 3338 DE_NULL // const VkSampler* pImmutableSamplers; 3339 } 3340 }; 3341 3342 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 3343 { 3344 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 3345 DE_NULL, // const void* pNext; 3346 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 3347 2u, // uint32_t bindingCount; 3348 descriptorSetLayoutBindings // const VkDescriptorSetLayoutBinding* pBindings; 3349 }; 3350 3351 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 3352 3353 const VkPipelineLayoutCreateInfo pipelineLayoutParams = 3354 { 3355 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 3356 DE_NULL, // const void* pNext; 3357 0u, // VkPipelineLayoutCreateFlags flags; 3358 1u, // deUint32 descriptorSetCount; 3359 &(*m_descriptorSetLayout), // const VkDescriptorSetLayout* pSetLayouts; 3360 0u, // deUint32 pushConstantRangeCount; 3361 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 3362 }; 3363 3364 m_pipelineLayout = createPipelineLayout(m_vkd, *m_device, &pipelineLayoutParams); 3365 } 3366 3367 // Create output buffer 3368 { 3369 DE_ASSERT(m_params.numCalls <= 2u); 3370 3371 const VkBufferCreateInfo bufferCreateInfo = 3372 { 3373 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 3374 DE_NULL, // const void* pNext; 3375 0u, // VkBufferCreateFlags flags 3376 m_itemSize * m_params.numCalls, // VkDeviceSize size; 3377 VK_BUFFER_USAGE_STORAGE_BUFFER_BIT, // VkBufferUsageFlags usage; 3378 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 3379 1u, // deUint32 queueFamilyCount; 3380 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 3381 }; 3382 3383 m_outputBuffer = createBuffer(m_vkd, *m_device, &bufferCreateInfo); 3384 m_outputBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_outputBuffer), MemoryRequirement::HostVisible); 3385 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_outputBuffer, m_outputBufferAlloc->getMemory(), m_outputBufferAlloc->getOffset())); 3386 } 3387 3388 // Create shader 3389 { 3390 m_computeShaderModule = createShaderModule(m_vkd, *m_device, m_context.getBinaryCollection().get("compute"), 0u); 3391 } 3392 3393 // Create pipeline 3394 { 3395 const VkPipelineShaderStageCreateInfo stageCreateInfo = 3396 { 3397 VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO, // VkStructureType sType; 3398 DE_NULL, // const void* pNext; 3399 0u, // VkPipelineShaderStageCreateFlags flags; 3400 VK_SHADER_STAGE_COMPUTE_BIT, // VkShaderStageFlagBits stage; 3401 *m_computeShaderModule, // VkShaderModule module; 3402 "main", // const char* pName; 3403 DE_NULL // const VkSpecializationInfo* pSpecializationInfo; 3404 }; 3405 3406 const VkComputePipelineCreateInfo createInfo = 3407 { 3408 VK_STRUCTURE_TYPE_COMPUTE_PIPELINE_CREATE_INFO, // VkStructureType sType; 3409 DE_NULL, // const void* pNext; 3410 0u, // VkPipelineCreateFlags flags; 3411 stageCreateInfo, // VkPipelineShaderStageCreateInfo stage; 3412 *m_pipelineLayout, // VkPipelineLayout layout; 3413 (VkPipeline)0, // VkPipeline basePipelineHandle; 3414 0u, // int32_t basePipelineIndex; 3415 }; 3416 3417 m_computePipeline = createComputePipeline(m_vkd, *m_device, (vk::VkPipelineCache)0u, &createInfo); 3418 } 3419 3420 // Create command pool 3421 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 3422 3423 // Create command buffer 3424 { 3425 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 3426 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 3427 m_vkd.cmdBindPipeline(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_computePipeline); 3428 3429 // Dispatch: Each dispatch switches the input image. 3430 // Output buffer is exposed as a vec4 sized window. 3431 for (deUint32 dispatchNdx = 0; dispatchNdx < m_params.numCalls; dispatchNdx++) 3432 { 3433 VkWriteDescriptorSet writeDescriptorSet = 3434 { 3435 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 3436 DE_NULL, // const void* pNext; 3437 0u, // VkDescriptorSet dstSet; 3438 m_params.binding, // uint32_t dstBinding; 3439 0u, // uint32_t dstArrayElement; 3440 1u, // uint32_t descriptorCount; 3441 m_params.descriptorType, // VkDescriptorType descriptorType; 3442 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 3443 DE_NULL, // const VkDescriptorBufferInfo* pBufferInfo; 3444 &m_bufferViews[dispatchNdx]->get() // const VkBufferView* pTexelBufferView; 3445 }; 3446 3447 vector<VkWriteDescriptorSet> writeDescriptorSets; 3448 writeDescriptorSets.push_back(writeDescriptorSet); 3449 3450 const VkDescriptorBufferInfo descriptorBufferInfoOutput = 3451 { 3452 *m_outputBuffer, // VkBuffer buffer; 3453 m_itemSize * dispatchNdx, // VkDeviceSize offset; 3454 kSizeofVec4, // VkDeviceSize range; 3455 }; 3456 3457 // Write output buffer descriptor set 3458 const VkWriteDescriptorSet writeDescriptorSetOutput = 3459 { 3460 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 3461 DE_NULL, // const void* pNext; 3462 0u, // VkDescriptorSet dstSet; 3463 m_params.binding + 1, // uint32_t dstBinding; 3464 0u, // uint32_t dstArrayElement; 3465 1u, // uint32_t descriptorCount; 3466 VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, // VkDescriptorType descriptorType; 3467 DE_NULL, // const VkDescriptorImageInfo* pImageInfo; 3468 &descriptorBufferInfoOutput, // const VkDescriptorBufferInfo* pBufferInfo; 3469 DE_NULL // const VkBufferView* pTexelBufferView; 3470 }; 3471 3472 writeDescriptorSets.push_back(writeDescriptorSetOutput); 3473 3474 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_COMPUTE, *m_pipelineLayout, 0, (deUint32)writeDescriptorSets.size(), writeDescriptorSets.data()); 3475 m_vkd.cmdDispatch(*m_cmdBuffer, 1, 1, 1); 3476 } 3477 3478 endCommandBuffer(m_vkd, *m_cmdBuffer); 3479 } 3480} 3481 3482PushDescriptorTexelBufferComputeTestInstance::~PushDescriptorTexelBufferComputeTestInstance (void) 3483{ 3484} 3485 3486tcu::TestStatus PushDescriptorTexelBufferComputeTestInstance::iterate (void) 3487{ 3488 init(); 3489 3490 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 3491 3492 return verifyOutput(); 3493} 3494 3495tcu::TestStatus PushDescriptorTexelBufferComputeTestInstance::verifyOutput (void) 3496{ 3497 const tcu::Vec4 ref[2] = { { 1.0f, 0.0f, 0.0f, 1.0f }, { 0.0f, 1.0f, 0.0f, 1.0f } }; 3498 invalidateAlloc(m_vkd, *m_device, *m_outputBufferAlloc); 3499 3500 // Verify result 3501 DE_ASSERT(m_params.numCalls <= 2u); 3502 3503 auto bufferPtr = reinterpret_cast<const char*>(m_outputBufferAlloc->getHostPtr()); 3504 for (deUint32 i = 0; i < m_params.numCalls; ++i) 3505 { 3506 tcu::Vec4 bufferColor; 3507 deMemcpy(&bufferColor, bufferPtr + (i * m_itemSize), static_cast<size_t>(kSizeofVec4)); 3508 3509 if (bufferColor != ref[i]) 3510 { 3511 std::ostringstream msg; 3512 msg << "Output mismatch at item " << i << ": expected " << ref[i] << " but found " << bufferColor; 3513 TCU_FAIL(msg.str()); 3514 } 3515 } 3516 3517 return tcu::TestStatus::pass("Output matches expected values"); 3518} 3519 3520class PushDescriptorTexelBufferComputeTest : public vkt::TestCase 3521{ 3522public: 3523 PushDescriptorTexelBufferComputeTest (tcu::TestContext& testContext, 3524 const string& name, 3525 const TestParams& params); 3526 ~PushDescriptorTexelBufferComputeTest (void); 3527 void initPrograms (SourceCollections& sourceCollections) const; 3528 TestInstance* createInstance (Context& context) const; 3529 3530protected: 3531 const TestParams m_params; 3532}; 3533 3534PushDescriptorTexelBufferComputeTest::PushDescriptorTexelBufferComputeTest (tcu::TestContext& testContext, 3535 const string& name, 3536 const TestParams& params) 3537 : vkt::TestCase (testContext, name) 3538 , m_params (params) 3539{ 3540} 3541 3542PushDescriptorTexelBufferComputeTest::~PushDescriptorTexelBufferComputeTest (void) 3543{ 3544} 3545 3546TestInstance* PushDescriptorTexelBufferComputeTest::createInstance (Context& context) const 3547{ 3548 return new PushDescriptorTexelBufferComputeTestInstance(context, m_params); 3549} 3550 3551void PushDescriptorTexelBufferComputeTest::initPrograms (SourceCollections& sourceCollections) const 3552{ 3553 if (m_params.descriptorType == VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER) 3554 { 3555 const string computeSrc = 3556 "#version 450\n" 3557 "layout(set = 0, binding = " + de::toString(m_params.binding) + ") uniform textureBuffer texelBuffer;\n" 3558 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") writeonly buffer Output\n" 3559 "{\n" 3560 " vec4 color;\n" 3561 "} outData;\n" 3562 "\n" 3563 "void main()\n" 3564 "{\n" 3565 " outData.color = texelFetch(texelBuffer, 0);\n" 3566 "}\n"; 3567 3568 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 3569 } 3570 else 3571 { 3572 DE_ASSERT(m_params.descriptorType == VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER); 3573 3574 const string computeSrc = 3575 "#version 450\n" 3576 "layout(set = 0, binding = " + de::toString(m_params.binding) + ", rgba32f) uniform readonly imageBuffer texelBuffer;\n" 3577 "layout(set = 0, binding = " + de::toString(m_params.binding + 1) + ") writeonly buffer Output\n" 3578 "{\n" 3579 " vec4 color;\n" 3580 "} outData;\n" 3581 "\n" 3582 "void main()\n" 3583 "{\n" 3584 " outData.color = imageLoad(texelBuffer, 0);\n" 3585 "}\n"; 3586 3587 sourceCollections.glslSources.add("compute") << glu::ComputeSource(computeSrc); 3588 } 3589} 3590 3591class PushDescriptorInputAttachmentGraphicsTestInstance : public vkt::TestInstance 3592{ 3593public: 3594 PushDescriptorInputAttachmentGraphicsTestInstance (Context& context, const TestParams& params); 3595 virtual ~PushDescriptorInputAttachmentGraphicsTestInstance (void); 3596 void init (void); 3597 virtual tcu::TestStatus iterate (void); 3598 tcu::TestStatus verifyImage (void); 3599 3600private: 3601 const TestParams m_params; 3602 const PlatformInterface& m_vkp; 3603 const Extensions m_instanceExtensions; 3604 const CustomInstance m_instance; 3605 const InstanceDriver& m_vki; 3606 const VkPhysicalDevice m_physicalDevice; 3607 const deUint32 m_queueFamilyIndex; 3608 const Extensions m_deviceExtensions; 3609 std::vector<std::string> m_deviceEnabledExtensions; 3610 const Unique<VkDevice> m_device; 3611 const DeviceDriver m_vkd; 3612 const VkQueue m_queue; 3613 SimpleAllocator m_allocator; 3614 const tcu::UVec2 m_renderSize; 3615 const tcu::UVec2 m_textureSize; 3616 const VkFormat m_colorFormat; 3617 Move<VkImage> m_colorImage; 3618 de::MovePtr<Allocation> m_colorImageAlloc; 3619 Move<VkImageView> m_colorAttachmentView; 3620 vector<VkImageSp> m_inputImages; 3621 vector<AllocationSp> m_inputImageAllocs; 3622 vector<VkImageViewSp> m_inputImageViews; 3623 vector<VkRenderPassSp> m_renderPasses; 3624 ShaderWrapper m_vertexShaderModule; 3625 ShaderWrapper m_fragmentShaderModule; 3626 Move<VkBuffer> m_vertexBuffer; 3627 de::MovePtr<Allocation> m_vertexBufferAlloc; 3628 Move<VkDescriptorSetLayout> m_descriptorSetLayout; 3629 PipelineLayoutWrapper m_preRasterizationStatePipelineLayout; 3630 PipelineLayoutWrapper m_fragmentStatePipelineLayout; 3631 vector<GraphicsPipelineWrapper> m_graphicsPipelines; 3632 Move<VkCommandPool> m_cmdPool; 3633 Move<VkCommandBuffer> m_cmdBuffer; 3634 vector<Vertex4Tex4> m_vertices; 3635}; 3636 3637PushDescriptorInputAttachmentGraphicsTestInstance::PushDescriptorInputAttachmentGraphicsTestInstance (Context& context, const TestParams& params) 3638 : vkt::TestInstance (context) 3639 , m_params (params) 3640 , m_vkp (context.getPlatformInterface()) 3641 , m_instanceExtensions (enumerateInstanceExtensionProperties(m_vkp, DE_NULL)) 3642 , m_instance (createInstanceWithGetPhysicalDeviceProperties2(context, m_instanceExtensions)) 3643 , m_vki (m_instance.getDriver()) 3644 , m_physicalDevice (chooseDevice(m_vki, m_instance, context.getTestContext().getCommandLine())) 3645 , m_queueFamilyIndex (findQueueFamilyIndexWithCaps(m_vki, m_physicalDevice, VK_QUEUE_GRAPHICS_BIT)) 3646 , m_deviceExtensions (enumerateDeviceExtensionProperties(m_vki, m_physicalDevice, DE_NULL)) 3647 , m_device (createDeviceWithPushDescriptor(context, m_vkp, m_instance, m_vki, m_physicalDevice, m_deviceExtensions, m_queueFamilyIndex, params, m_deviceEnabledExtensions)) 3648 , m_vkd (m_vkp, m_instance, *m_device, context.getUsedApiVersion()) 3649 , m_queue (getDeviceQueue(m_vkd, *m_device, m_queueFamilyIndex, 0u)) 3650 , m_allocator (m_vkd, *m_device, getPhysicalDeviceMemoryProperties(m_vki, m_physicalDevice)) 3651 , m_renderSize (32, 32) 3652 , m_textureSize (32, 32) 3653 , m_colorFormat (VK_FORMAT_R8G8B8A8_UNORM) 3654 , m_vertices (createTexQuads(params.numCalls, 0.25f)) 3655{ 3656} 3657 3658void PushDescriptorInputAttachmentGraphicsTestInstance::init (void) 3659{ 3660 const VkComponentMapping componentMappingRGBA = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A }; 3661 3662 // Create color image 3663 { 3664 3665 const VkImageCreateInfo colorImageParams = 3666 { 3667 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 3668 DE_NULL, // const void* pNext; 3669 0u, // VkImageCreateFlags flags; 3670 VK_IMAGE_TYPE_2D, // VkImageType imageType; 3671 m_colorFormat, // VkFormat format; 3672 { m_renderSize.x(), m_renderSize.y(), 1u }, // VkExtent3D extent; 3673 1u, // deUint32 mipLevels; 3674 1u, // deUint32 arrayLayers; 3675 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 3676 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 3677 VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT, // VkImageUsageFlags usage; 3678 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 3679 1u, // deUint32 queueFamilyIndexCount; 3680 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 3681 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout; 3682 }; 3683 3684 m_colorImage = createImage(m_vkd, *m_device, &colorImageParams); 3685 3686 // Allocate and bind color image memory 3687 m_colorImageAlloc = m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, *m_colorImage), MemoryRequirement::Any); 3688 VK_CHECK(m_vkd.bindImageMemory(*m_device, *m_colorImage, m_colorImageAlloc->getMemory(), m_colorImageAlloc->getOffset())); 3689 } 3690 3691 // Create color attachment view 3692 { 3693 const VkImageViewCreateInfo colorAttachmentViewParams = 3694 { 3695 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 3696 DE_NULL, // const void* pNext; 3697 0u, // VkImageViewCreateFlags flags; 3698 *m_colorImage, // VkImage image; 3699 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 3700 m_colorFormat, // VkFormat format; 3701 componentMappingRGBA, // VkChannelMapping channels; 3702 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u } // VkImageSubresourceRange subresourceRange; 3703 }; 3704 3705 m_colorAttachmentView = createImageView(m_vkd, *m_device, &colorAttachmentViewParams); 3706 } 3707 3708 // Create input images 3709 for (deUint32 imageIdx = 0; imageIdx < 2; imageIdx++) 3710 { 3711 const VkImageUsageFlags usageFlags = VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT; 3712 3713 const VkImageCreateInfo inputImageParams = 3714 { 3715 VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, // VkStructureType sType; 3716 DE_NULL, // const void* pNext; 3717 0u, // VkImageCreateFlags flags; 3718 VK_IMAGE_TYPE_2D, // VkImageType imageType; 3719 m_colorFormat, // VkFormat format; 3720 { m_textureSize.x(), m_textureSize.y(), 1u }, // VkExtent3D extent; 3721 1u, // deUint32 mipLevels; 3722 1u, // deUint32 arrayLayers; 3723 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples; 3724 VK_IMAGE_TILING_OPTIMAL, // VkImageTiling tiling; 3725 usageFlags, // VkImageUsageFlags usage; 3726 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 3727 1u, // deUint32 queueFamilyIndexCount; 3728 &m_queueFamilyIndex, // const deUint32* pQueueFamilyIndices; 3729 VK_IMAGE_LAYOUT_UNDEFINED // VkImageLayout initialLayout; 3730 }; 3731 3732 m_inputImages.push_back(VkImageSp(new Unique<VkImage>(createImage(m_vkd, *m_device, &inputImageParams)))); 3733 3734 // Allocate and bind image memory 3735 m_inputImageAllocs.push_back(AllocationSp(m_allocator.allocate(getImageMemoryRequirements(m_vkd, *m_device, **m_inputImages.back()), MemoryRequirement::Any).release())); 3736 VK_CHECK(m_vkd.bindImageMemory(*m_device, **m_inputImages.back(), m_inputImageAllocs.back()->getMemory(), m_inputImageAllocs.back()->getOffset())); 3737 } 3738 3739 // Create texture image views 3740 for (deUint32 imageIdx = 0; imageIdx < 2; imageIdx++) 3741 { 3742 const VkImageViewCreateInfo textureViewParams = 3743 { 3744 VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, // VkStructureType sType; 3745 DE_NULL, // const void* pNext; 3746 0u, // VkImageViewCreateFlags flags; 3747 **m_inputImages[imageIdx], // VkImage image; 3748 VK_IMAGE_VIEW_TYPE_2D, // VkImageViewType viewType; 3749 m_colorFormat, // VkFormat format; 3750 componentMappingRGBA, // VkChannelMapping channels; 3751 { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u } // VkImageSubresourceRange subresourceRange; 3752 }; 3753 3754 m_inputImageViews.push_back(VkImageViewSp(new Unique<VkImageView>(createImageView(m_vkd, *m_device, &textureViewParams)))); 3755 } 3756 3757 VkClearValue clearValues[2]; 3758 clearValues[0].color.float32[0] = 0.0f; 3759 clearValues[0].color.float32[1] = 1.0f; 3760 clearValues[0].color.float32[2] = 0.0f; 3761 clearValues[0].color.float32[3] = 1.0f; 3762 clearValues[1].color.float32[0] = 1.0f; 3763 clearValues[1].color.float32[1] = 0.0f; 3764 clearValues[1].color.float32[2] = 0.0f; 3765 clearValues[1].color.float32[3] = 1.0f; 3766 3767 // Clear input images 3768 for (deUint32 imageIdx = 0; imageIdx < 2; imageIdx++) 3769 { 3770 const VkImageAspectFlags aspectMask = VK_IMAGE_ASPECT_COLOR_BIT; 3771 Move<VkCommandPool> cmdPool; 3772 Move<VkCommandBuffer> cmdBuffer; 3773 const VkAccessFlags accessFlags = VK_ACCESS_INPUT_ATTACHMENT_READ_BIT; 3774 3775 cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 3776 cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 3777 3778 const VkImageMemoryBarrier preImageBarrier = 3779 { 3780 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType; 3781 DE_NULL, // const void* pNext; 3782 0u, // VkAccessFlags srcAccessMask; 3783 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags dstAccessMask; 3784 VK_IMAGE_LAYOUT_UNDEFINED, // VkImageLayout oldLayout; 3785 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout newLayout; 3786 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex; 3787 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex; 3788 **m_inputImages[imageIdx], // VkImage image; 3789 { // VkImageSubresourceRange subresourceRange; 3790 aspectMask, // VkImageAspect aspect; 3791 0u, // deUint32 baseMipLevel; 3792 1u, // deUint32 mipLevels; 3793 0u, // deUint32 baseArraySlice; 3794 1u // deUint32 arraySize; 3795 } 3796 }; 3797 3798 const VkImageMemoryBarrier postImageBarrier = 3799 { 3800 VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // VkStructureType sType; 3801 DE_NULL, // const void* pNext; 3802 VK_ACCESS_TRANSFER_WRITE_BIT, // VkAccessFlags srcAccessMask; 3803 accessFlags, // VkAccessFlags dstAccessMask; 3804 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, // VkImageLayout oldLayout; 3805 VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, // VkImageLayout newLayout; 3806 VK_QUEUE_FAMILY_IGNORED, // deUint32 srcQueueFamilyIndex; 3807 VK_QUEUE_FAMILY_IGNORED, // deUint32 dstQueueFamilyIndex; 3808 **m_inputImages[imageIdx], // VkImage image; 3809 { // VkImageSubresourceRange subresourceRange; 3810 aspectMask, // VkImageAspect aspect; 3811 0u, // deUint32 baseMipLevel; 3812 1u, // deUint32 mipLevels; 3813 0u, // deUint32 baseArraySlice; 3814 1u // deUint32 arraySize; 3815 } 3816 }; 3817 3818 const VkImageSubresourceRange clearRange = 3819 { 3820 aspectMask, // VkImageAspectFlags aspectMask; 3821 0u, // deUint32 baseMipLevel; 3822 1u, // deUint32 levelCount; 3823 0u, // deUint32 baseArrayLayer; 3824 1u // deUint32 layerCount; 3825 }; 3826 3827 beginCommandBuffer(m_vkd, *cmdBuffer); 3828 m_vkd.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_HOST_BIT, VK_PIPELINE_STAGE_TRANSFER_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &preImageBarrier); 3829 m_vkd.cmdClearColorImage(*cmdBuffer, **m_inputImages[imageIdx], VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, &clearValues[imageIdx].color, 1, &clearRange); 3830 m_vkd.cmdPipelineBarrier(*cmdBuffer, VK_PIPELINE_STAGE_TRANSFER_BIT, VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT, (VkDependencyFlags)0, 0, (const VkMemoryBarrier*)DE_NULL, 0, (const VkBufferMemoryBarrier*)DE_NULL, 1, &postImageBarrier); 3831 endCommandBuffer(m_vkd, *cmdBuffer); 3832 3833 submitCommandsAndWait(m_vkd, *m_device, m_queue, cmdBuffer.get()); 3834 } 3835 3836 // Create render passes 3837 for (deUint32 renderPassIdx = 0; renderPassIdx < 2; renderPassIdx++) 3838 { 3839 // The first pass clears the output image, and the second one draws on top of the first pass. 3840 const VkAttachmentLoadOp loadOps[] = 3841 { 3842 VK_ATTACHMENT_LOAD_OP_CLEAR, 3843 VK_ATTACHMENT_LOAD_OP_LOAD 3844 }; 3845 3846 const VkImageLayout initialLayouts[] = 3847 { 3848 VK_IMAGE_LAYOUT_UNDEFINED, 3849 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL 3850 }; 3851 3852 const VkAttachmentDescription attachmentDescriptions[] = 3853 { 3854 // Result attachment 3855 { 3856 (VkAttachmentDescriptionFlags)0, // VkAttachmentDescriptionFlags flags 3857 VK_FORMAT_R8G8B8A8_UNORM, // VkFormat format 3858 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples 3859 loadOps[renderPassIdx], // VkAttachmentLoadOp loadOp 3860 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp 3861 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp 3862 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp 3863 initialLayouts[renderPassIdx], // VkImageLayout initialLayout 3864 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL // VkImageLayout finalLayout 3865 }, 3866 // Input attachment 3867 { 3868 (VkAttachmentDescriptionFlags)0, // VkAttachmentDescriptionFlags flags 3869 VK_FORMAT_R8G8B8A8_UNORM, // VkFormat format 3870 VK_SAMPLE_COUNT_1_BIT, // VkSampleCountFlagBits samples 3871 VK_ATTACHMENT_LOAD_OP_LOAD, // VkAttachmentLoadOp loadOp 3872 VK_ATTACHMENT_STORE_OP_STORE, // VkAttachmentStoreOp storeOp 3873 VK_ATTACHMENT_LOAD_OP_DONT_CARE, // VkAttachmentLoadOp stencilLoadOp 3874 VK_ATTACHMENT_STORE_OP_DONT_CARE, // VkAttachmentStoreOp stencilStoreOp 3875 VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL, // VkImageLayout initialLayout 3876 VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL // VkImageLayout finalLayout 3877 } 3878 }; 3879 3880 const VkAttachmentReference resultAttachmentRef = 3881 { 3882 0u, // deUint32 attachment 3883 VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL // VkImageLayout layout 3884 }; 3885 3886 const VkAttachmentReference inputAttachmentRef = 3887 { 3888 1u, // deUint32 attachment 3889 VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL // VkImageLayout layout 3890 }; 3891 3892 const VkSubpassDescription subpassDescription = 3893 { 3894 (VkSubpassDescriptionFlags)0, // VkSubpassDescriptionFlags flags 3895 VK_PIPELINE_BIND_POINT_GRAPHICS, // VkPipelineBindPoint pipelineBindPoint 3896 1u, // deUint32 inputAttachmentCount 3897 &inputAttachmentRef, // const VkAttachmentReference* pInputAttachments 3898 1u, // deUint32 colorAttachmentCount 3899 &resultAttachmentRef, // const VkAttachmentReference* pColorAttachments 3900 DE_NULL, // const VkAttachmentReference* pResolveAttachments 3901 DE_NULL, // const VkAttachmentReference* pDepthStencilAttachment 3902 0u, // deUint32 preserveAttachmentCount 3903 DE_NULL // const deUint32* pPreserveAttachments 3904 }; 3905 3906 const VkSubpassDependency subpassDependency = 3907 { 3908 VK_SUBPASS_EXTERNAL, // deUint32 srcSubpass 3909 0, // deUint32 dstSubpass 3910 VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, // VkPipelineStageFlags srcStageMask 3911 VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT, // VkPipelineStageFlags dstStageMask 3912 VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // VkAccessFlags srcAccessMask 3913 VK_ACCESS_INPUT_ATTACHMENT_READ_BIT | VK_ACCESS_SHADER_READ_BIT, // dstAccessMask 3914 VK_DEPENDENCY_BY_REGION_BIT // VkDependencyFlags dependencyFlags 3915 }; 3916 3917 const VkRenderPassCreateInfo renderPassInfo = 3918 { 3919 VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO, // VkStructureTypei sType 3920 DE_NULL, // const void* pNext 3921 (VkRenderPassCreateFlags)0, // VkRenderPassCreateFlags flags 3922 2u, // deUint32 attachmentCount 3923 attachmentDescriptions, // const VkAttachmentDescription* pAttachments 3924 1u, // deUint32 subpassCount 3925 &subpassDescription, // const VkSubpassDescription* pSubpasses 3926 1u, // deUint32 dependencyCount 3927 &subpassDependency // const VkSubpassDependency* pDependencies 3928 }; 3929 3930 m_renderPasses.push_back(VkRenderPassSp(new RenderPassWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &renderPassInfo))); 3931 3932 std::vector<VkImage> images = 3933 { 3934 *m_colorImage, 3935 **m_inputImages[renderPassIdx], 3936 }; 3937 3938 const VkImageView attachmentBindInfos[] = 3939 { 3940 *m_colorAttachmentView, 3941 **m_inputImageViews[renderPassIdx], 3942 }; 3943 3944 const VkFramebufferCreateInfo framebufferParams = 3945 { 3946 VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, // VkStructureType sType; 3947 DE_NULL, // const void* pNext; 3948 0u, // VkFramebufferCreateFlags flags; 3949 **m_renderPasses[renderPassIdx], // VkRenderPass renderPass; 3950 2u, // deUint32 attachmentCount; 3951 attachmentBindInfos, // const VkImageView* pAttachments; 3952 (deUint32)m_renderSize.x(), // deUint32 width; 3953 (deUint32)m_renderSize.y(), // deUint32 height; 3954 1u // deUint32 layers; 3955 }; 3956 3957 m_renderPasses[renderPassIdx]->createFramebuffer(m_vkd, *m_device, &framebufferParams, images); 3958 } 3959 3960 // Create pipeline layout 3961 { 3962 // Create descriptor set layout 3963 const VkDescriptorSetLayoutBinding descriptorSetLayoutBinding = 3964 { 3965 m_params.binding, // uint32_t binding; 3966 VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, // VkDescriptorType descriptorType; 3967 1u, // uint32_t descriptorCount; 3968 VK_SHADER_STAGE_FRAGMENT_BIT, // VkShaderStageFlags stageFlags; 3969 DE_NULL // const VkSampler* pImmutableSamplers; 3970 }; 3971 3972 const VkDescriptorSetLayoutCreateInfo descriptorSetLayoutCreateInfo = 3973 { 3974 VK_STRUCTURE_TYPE_DESCRIPTOR_SET_LAYOUT_CREATE_INFO, // VkStructureType sType; 3975 DE_NULL, // const void* pNext; 3976 VK_DESCRIPTOR_SET_LAYOUT_CREATE_PUSH_DESCRIPTOR_BIT_KHR, // VkDescriptorSetLayoutCreateFlags flags; 3977 1u, // uint32_t bindingCount; 3978 &descriptorSetLayoutBinding // const VkDescriptorSetLayoutBinding* pBindings; 3979 }; 3980 3981 m_descriptorSetLayout = createDescriptorSetLayout(m_vkd, *m_device, &descriptorSetLayoutCreateInfo, DE_NULL); 3982 3983 // Create pipeline layout 3984 VkPipelineLayoutCreateFlags pipelineLayoutFlags = (m_params.pipelineConstructionType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) ? 0u : deUint32(VK_PIPELINE_LAYOUT_CREATE_INDEPENDENT_SETS_BIT_EXT); 3985 VkPipelineLayoutCreateInfo pipelineLayoutParams 3986 { 3987 VK_STRUCTURE_TYPE_PIPELINE_LAYOUT_CREATE_INFO, // VkStructureType sType; 3988 DE_NULL, // const void* pNext; 3989 pipelineLayoutFlags, // VkPipelineLayoutCreateFlags flags; 3990 0u, // deUint32 setLayoutCount; 3991 DE_NULL, // const VkDescriptorSetLayout* pSetLayouts; 3992 0u, // deUint32 pushConstantRangeCount; 3993 DE_NULL // const VkPushDescriptorRange* pPushDescriptorRanges; 3994 }; 3995 3996 m_preRasterizationStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 3997 pipelineLayoutParams.setLayoutCount = 1u; 3998 pipelineLayoutParams.pSetLayouts = &(*m_descriptorSetLayout); 3999 m_fragmentStatePipelineLayout = PipelineLayoutWrapper(m_params.pipelineConstructionType, m_vkd, *m_device, &pipelineLayoutParams); 4000 } 4001 4002 // Create shaders 4003 { 4004 m_vertexShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("vert"), 0u); 4005 m_fragmentShaderModule = ShaderWrapper(m_vkd, *m_device, m_context.getBinaryCollection().get("frag"), 0u); 4006 } 4007 4008 m_graphicsPipelines.reserve(2); 4009 4010 // Create pipelines 4011 for (deUint32 pipelineIdx = 0; pipelineIdx < 2; pipelineIdx++) 4012 { 4013 const VkVertexInputBindingDescription vertexInputBindingDescription = 4014 { 4015 0u, // deUint32 binding; 4016 sizeof(Vertex4Tex4), // deUint32 strideInBytes; 4017 VK_VERTEX_INPUT_RATE_VERTEX // VkVertexInputStepRate stepRate; 4018 }; 4019 4020 const VkVertexInputAttributeDescription vertexInputAttributeDescriptions[] = 4021 { 4022 { 4023 0u, // deUint32 location; 4024 0u, // deUint32 binding; 4025 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 4026 0u // deUint32 offsetInBytes; 4027 }, 4028 { 4029 1u, // deUint32 location; 4030 0u, // deUint32 binding; 4031 VK_FORMAT_R32G32B32A32_SFLOAT, // VkFormat format; 4032 DE_OFFSET_OF(Vertex4Tex4, texCoord), // deUint32 offset; 4033 } 4034 }; 4035 4036 const VkPipelineVertexInputStateCreateInfo vertexInputStateParams = 4037 { 4038 VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, // VkStructureType sType; 4039 DE_NULL, // const void* pNext; 4040 0u, // vkPipelineVertexInputStateCreateFlags flags; 4041 1u, // deUint32 bindingCount; 4042 &vertexInputBindingDescription, // const VkVertexInputBindingDescription* pVertexBindingDescriptions; 4043 2u, // deUint32 attributeCount; 4044 vertexInputAttributeDescriptions // const VkVertexInputAttributeDescription* pVertexAttributeDescriptions; 4045 }; 4046 4047 const vector<VkViewport> viewports { makeViewport(m_renderSize) }; 4048 const vector<VkRect2D> scissors { makeRect2D(m_renderSize) }; 4049 4050 m_graphicsPipelines.emplace_back(m_vki, m_vkd, m_physicalDevice, *m_device, m_deviceEnabledExtensions, m_params.pipelineConstructionType); 4051 m_graphicsPipelines.back().setMonolithicPipelineLayout(m_fragmentStatePipelineLayout) 4052 .setDefaultRasterizationState() 4053 .setDefaultDepthStencilState() 4054 .setDefaultMultisampleState() 4055 .setDefaultColorBlendState() 4056 .setupVertexInputState(&vertexInputStateParams) 4057 .setupPreRasterizationShaderState(viewports, 4058 scissors, 4059 m_preRasterizationStatePipelineLayout, 4060 **m_renderPasses[pipelineIdx], 4061 0u, 4062 m_vertexShaderModule) 4063 .setupFragmentShaderState(m_fragmentStatePipelineLayout, **m_renderPasses[pipelineIdx], 0u, m_fragmentShaderModule) 4064 .setupFragmentOutputState(**m_renderPasses[pipelineIdx]) 4065 .buildPipeline(); 4066 } 4067 4068 // Create vertex buffer 4069 { 4070 const VkBufferCreateInfo vertexBufferParams = 4071 { 4072 VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO, // VkStructureType sType; 4073 DE_NULL, // const void* pNext; 4074 0u, // VkBufferCreateFlags flags; 4075 (VkDeviceSize)(sizeof(Vertex4RGBA) * m_vertices.size()), // VkDeviceSize size; 4076 VK_BUFFER_USAGE_VERTEX_BUFFER_BIT, // VkBufferUsageFlags usage; 4077 VK_SHARING_MODE_EXCLUSIVE, // VkSharingMode sharingMode; 4078 1u, // deUint32 queueFamilyCount; 4079 &m_queueFamilyIndex // const deUint32* pQueueFamilyIndices; 4080 }; 4081 4082 m_vertexBuffer = createBuffer(m_vkd, *m_device, &vertexBufferParams); 4083 m_vertexBufferAlloc = m_allocator.allocate(getBufferMemoryRequirements(m_vkd, *m_device, *m_vertexBuffer), MemoryRequirement::HostVisible); 4084 4085 VK_CHECK(m_vkd.bindBufferMemory(*m_device, *m_vertexBuffer, m_vertexBufferAlloc->getMemory(), m_vertexBufferAlloc->getOffset())); 4086 4087 // Load vertices into vertex buffer 4088 deMemcpy(m_vertexBufferAlloc->getHostPtr(), m_vertices.data(), m_vertices.size() * sizeof(Vertex4Tex4)); 4089 flushAlloc(m_vkd, *m_device, *m_vertexBufferAlloc); 4090 } 4091 4092 // Create command pool 4093 m_cmdPool = createCommandPool(m_vkd, *m_device, VK_COMMAND_POOL_CREATE_TRANSIENT_BIT, m_queueFamilyIndex); 4094 4095 // Create command buffer 4096 { 4097 const VkClearValue attachmentClearValue = defaultClearValue(m_colorFormat); 4098 const VkDeviceSize vertexBufferOffset = 0; 4099 4100 m_cmdBuffer = allocateCommandBuffer(m_vkd, *m_device, *m_cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY); 4101 beginCommandBuffer(m_vkd, *m_cmdBuffer, 0u); 4102 for (deUint32 quadNdx = 0; quadNdx < m_params.numCalls; quadNdx++) 4103 { 4104 (*m_renderPasses[quadNdx]).begin(m_vkd, *m_cmdBuffer, makeRect2D(0, 0, m_renderSize.x(), m_renderSize.y()), attachmentClearValue); 4105 m_graphicsPipelines[quadNdx].bind(*m_cmdBuffer); 4106 m_vkd.cmdBindVertexBuffers(*m_cmdBuffer, 0, 1, &m_vertexBuffer.get(), &vertexBufferOffset); 4107 4108 VkDescriptorImageInfo descriptorImageInfo = 4109 { 4110 0, // VkSampler sampler; 4111 **m_inputImageViews[quadNdx], // VkImageView imageView; 4112 VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL // VkImageLayout imageLayout; 4113 }; 4114 4115 VkWriteDescriptorSet writeDescriptorSet = 4116 { 4117 VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET, // VkStructureType sType; 4118 DE_NULL, // const void* pNext; 4119 0u, // VkDescriptorSet dstSet; 4120 m_params.binding, // uint32_t dstBinding; 4121 0u, // uint32_t dstArrayElement; 4122 1u, // uint32_t descriptorCount; 4123 m_params.descriptorType, // VkDescriptorType descriptorType; 4124 &descriptorImageInfo, // const VkDescriptorImageInfo* pImageInfo; 4125 DE_NULL, // const VkDescriptorBufferInfo* pBufferInfo; 4126 DE_NULL // const VkBufferView* pTexelBufferView; 4127 }; 4128 4129 m_vkd.cmdPushDescriptorSetKHR(*m_cmdBuffer, VK_PIPELINE_BIND_POINT_GRAPHICS, *m_fragmentStatePipelineLayout, 0, 1, &writeDescriptorSet); 4130 m_vkd.cmdDraw(*m_cmdBuffer, 6, 1, 6 * quadNdx, 0); 4131 4132 (*m_renderPasses[quadNdx]).end(m_vkd, *m_cmdBuffer); 4133 } 4134 4135 endCommandBuffer(m_vkd, *m_cmdBuffer); 4136 } 4137} 4138 4139PushDescriptorInputAttachmentGraphicsTestInstance::~PushDescriptorInputAttachmentGraphicsTestInstance (void) 4140{ 4141} 4142 4143tcu::TestStatus PushDescriptorInputAttachmentGraphicsTestInstance::iterate (void) 4144{ 4145 init(); 4146 4147 submitCommandsAndWait(m_vkd, *m_device, m_queue, m_cmdBuffer.get()); 4148 4149 return verifyImage(); 4150} 4151 4152tcu::TestStatus PushDescriptorInputAttachmentGraphicsTestInstance::verifyImage (void) 4153{ 4154 const tcu::TextureFormat tcuColorFormat = mapVkFormat(m_colorFormat); 4155 const tcu::TextureFormat tcuDepthFormat = tcu::TextureFormat(); 4156 const ColorVertexShader vertexShader; 4157 const ColorFragmentShader fragmentShader (tcuColorFormat, tcuDepthFormat); 4158 const rr::Program program (&vertexShader, &fragmentShader); 4159 ReferenceRenderer refRenderer (m_renderSize.x(), m_renderSize.y(), 1, tcuColorFormat, tcuDepthFormat, &program); 4160 bool compareOk = false; 4161 4162 // Render reference image 4163 { 4164 vector<Vertex4RGBA> refQuads = createQuads(m_params.numCalls, 0.25f); 4165 tcu::Vec4 colors[2]; 4166 4167 colors[0] = tcu::Vec4(0.0f, 1.0f, 0.0f, 1.0f); 4168 colors[1] = tcu::Vec4(1.0f, 0.0f, 0.0f, 1.0f); 4169 4170 for (deUint32 quadIdx = 0; quadIdx < m_params.numCalls; quadIdx++) 4171 for (deUint32 vertexIdx = 0; vertexIdx < 6; vertexIdx++) 4172 { 4173 const deUint32 idx = quadIdx * 6 + vertexIdx; 4174 refQuads[idx].color.xyzw() = colors[quadIdx]; 4175 } 4176 4177 refRenderer.draw(rr::RenderState(refRenderer.getViewportState(), m_context.getDeviceProperties().limits.subPixelPrecisionBits), 4178 rr::PRIMITIVETYPE_TRIANGLES, refQuads); 4179 } 4180 4181 // Compare result with reference image 4182 { 4183 de::MovePtr<tcu::TextureLevel> result = readColorAttachment(m_vkd, *m_device, m_queue, m_queueFamilyIndex, m_allocator, *m_colorImage, m_colorFormat, m_renderSize); 4184 4185 compareOk = tcu::intThresholdPositionDeviationCompare(m_context.getTestContext().getLog(), 4186 "IntImageCompare", 4187 "Image comparison", 4188 refRenderer.getAccess(), 4189 result->getAccess(), 4190 tcu::UVec4(2, 2, 2, 2), 4191 tcu::IVec3(1, 1, 0), 4192 true, 4193 tcu::COMPARE_LOG_RESULT); 4194 } 4195 4196 if (compareOk) 4197 return tcu::TestStatus::pass("Result image matches reference"); 4198 else 4199 return tcu::TestStatus::fail("Image mismatch"); 4200} 4201 4202class PushDescriptorInputAttachmentGraphicsTest : public vkt::TestCase 4203{ 4204public: 4205 PushDescriptorInputAttachmentGraphicsTest (tcu::TestContext& testContext, 4206 const string& name, 4207 const TestParams& params); 4208 ~PushDescriptorInputAttachmentGraphicsTest (void); 4209 4210 void checkSupport (Context& context) const; 4211 void initPrograms (SourceCollections& sourceCollections) const; 4212 TestInstance* createInstance (Context& context) const; 4213 4214protected: 4215 const TestParams m_params; 4216}; 4217 4218PushDescriptorInputAttachmentGraphicsTest::PushDescriptorInputAttachmentGraphicsTest (tcu::TestContext& testContext, 4219 const string& name, 4220 const TestParams& params) 4221 : vkt::TestCase (testContext, name) 4222 , m_params (params) 4223{ 4224} 4225 4226PushDescriptorInputAttachmentGraphicsTest::~PushDescriptorInputAttachmentGraphicsTest (void) 4227{ 4228} 4229 4230TestInstance* PushDescriptorInputAttachmentGraphicsTest::createInstance (Context& context) const 4231{ 4232 return new PushDescriptorInputAttachmentGraphicsTestInstance(context, m_params); 4233} 4234 4235void PushDescriptorInputAttachmentGraphicsTest::checkSupport(Context& context) const 4236{ 4237 checkPipelineConstructionRequirements(context.getInstanceInterface(), context.getPhysicalDevice(), m_params.pipelineConstructionType); 4238} 4239 4240void PushDescriptorInputAttachmentGraphicsTest::initPrograms (SourceCollections& sourceCollections) const 4241{ 4242 const string vertexSrc = 4243 "#version 450\n" 4244 "layout(location = 0) in highp vec4 position;\n" 4245 "layout(location = 1) in highp vec4 texcoordVtx;\n" 4246 "layout(location = 0) out highp vec2 texcoordFrag;\n" 4247 "\n" 4248 "out gl_PerVertex { vec4 gl_Position; };\n" 4249 "\n" 4250 "void main()\n" 4251 "{\n" 4252 " gl_Position = position;\n" 4253 " texcoordFrag = texcoordVtx.xy;\n" 4254 "}\n"; 4255 4256 sourceCollections.glslSources.add("vert") << glu::VertexSource(vertexSrc); 4257 4258 const string fragmentSrc = 4259 "#version 450\n" 4260 "layout(location = 0) in highp vec2 texcoordFrag;\n" 4261 "layout(location = 0) out highp vec4 fragColor;\n" 4262 "layout(input_attachment_index = 0, set = 0, binding = " + de::toString(m_params.binding) + ") uniform subpassInput inputColor;\n" 4263 "\n" 4264 "void main (void)\n" 4265 "{\n" 4266 " fragColor = subpassLoad(inputColor);\n" 4267 "}\n"; 4268 4269 sourceCollections.glslSources.add("frag") << glu::FragmentSource(fragmentSrc); 4270} 4271 4272} // anonymous 4273 4274tcu::TestCaseGroup* createPushDescriptorTests (tcu::TestContext& testCtx, PipelineConstructionType pipelineType) 4275{ 4276 const TestParams params[] 4277 { 4278 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 0u, 1u, false }, 4279 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 0u, 2u, false }, 4280 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 1u, 2u, false }, 4281 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER, 3u, 2u, false }, 4282 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 0u, 1u, false }, 4283 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 0u, 2u, false }, 4284 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1u, 2u, false }, 4285 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 3u, 2u, false }, 4286 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_BUFFER, 1u, 128u, false }, 4287 { pipelineType, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 0u, 1u, false }, 4288 { pipelineType, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 0u, 2u, false }, 4289 { pipelineType, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 1u, 2u, false }, 4290 { pipelineType, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 3u, 2u, false }, 4291 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLER, 0u, 1u, false }, 4292 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLER, 0u, 2u, false }, 4293 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLER, 1u, 2u, false }, 4294 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLER, 3u, 2u, false }, 4295 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 0u, 1u, false }, 4296 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 0u, 2u, false }, 4297 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 1u, 2u, false }, 4298 { pipelineType, VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE, 3u, 2u, false }, 4299 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, 0u, 1u, false }, 4300 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, 0u, 2u, false }, 4301 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, 1u, 2u, false }, 4302 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_IMAGE, 3u, 2u, false }, 4303 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, 0u, 1u, false }, 4304 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, 0u, 2u, false }, 4305 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, 1u, 2u, false }, 4306 { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, 3u, 2u, false }, 4307 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, 0u, 1u, false }, 4308 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, 0u, 2u, false }, 4309 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, 1u, 2u, false }, 4310 { pipelineType, VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER, 3u, 2u, false }, 4311 { pipelineType, VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, 0u, 1u, false }, 4312 { pipelineType, VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, 0u, 2u, false }, 4313 { pipelineType, VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, 1u, 2u, false }, 4314 { pipelineType, VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT, 3u, 2u, false } 4315 }; 4316 4317 de::MovePtr<tcu::TestCaseGroup> pushDescriptorTests (new tcu::TestCaseGroup(testCtx, "push_descriptor")); 4318 4319 de::MovePtr<tcu::TestCaseGroup> graphicsTests (new tcu::TestCaseGroup(testCtx, "graphics")); 4320 de::MovePtr<tcu::TestCaseGroup> computeTests (new tcu::TestCaseGroup(testCtx, "compute")); 4321 4322 for (deUint32 testIdx = 0; testIdx < DE_LENGTH_OF_ARRAY(params); testIdx++) 4323 { 4324 string testName; 4325 testName += "binding" + de::toString(params[testIdx].binding) + "_numcalls" + de::toString(params[testIdx].numCalls); 4326 switch(params[testIdx].descriptorType) 4327 { 4328 case VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER: 4329 testName += "_uniform_buffer"; 4330 if (params[testIdx].numCalls <= 2) 4331 graphicsTests->addChild(new PushDescriptorBufferGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4332 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4333 computeTests->addChild(new PushDescriptorBufferComputeTest(testCtx, testName.c_str(), params[testIdx])); 4334 break; 4335 4336 case VK_DESCRIPTOR_TYPE_STORAGE_BUFFER: 4337 testName += "_storage_buffer"; 4338 if (params[testIdx].numCalls <= 2) 4339 graphicsTests->addChild(new PushDescriptorBufferGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4340 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4341 computeTests->addChild(new PushDescriptorBufferComputeTest(testCtx, testName.c_str(), params[testIdx])); 4342 break; 4343 4344 case VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER: 4345 testName += "_combined_image_sampler"; 4346 graphicsTests->addChild(new PushDescriptorImageGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4347 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4348 computeTests->addChild(new PushDescriptorImageComputeTest(testCtx, testName.c_str(), params[testIdx])); 4349 break; 4350 4351 case VK_DESCRIPTOR_TYPE_SAMPLED_IMAGE: 4352 testName += "_sampled_image"; 4353 graphicsTests->addChild(new PushDescriptorImageGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4354 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4355 computeTests->addChild(new PushDescriptorImageComputeTest(testCtx, testName.c_str(), params[testIdx])); 4356 break; 4357 4358 case VK_DESCRIPTOR_TYPE_SAMPLER: 4359 testName += "_sampler"; 4360 graphicsTests->addChild(new PushDescriptorImageGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4361 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4362 computeTests->addChild(new PushDescriptorImageComputeTest(testCtx, testName.c_str(), params[testIdx])); 4363 break; 4364 4365 case VK_DESCRIPTOR_TYPE_STORAGE_IMAGE: 4366 testName += "_storage_image"; 4367 graphicsTests->addChild(new PushDescriptorImageGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4368 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4369 computeTests->addChild(new PushDescriptorImageComputeTest(testCtx, testName.c_str(), params[testIdx])); 4370 break; 4371 4372 case VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER: 4373 testName += "_uniform_texel_buffer"; 4374 graphicsTests->addChild(new PushDescriptorTexelBufferGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4375 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4376 computeTests->addChild(new PushDescriptorTexelBufferComputeTest(testCtx, testName.c_str(), params[testIdx])); 4377 break; 4378 4379 case VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER: 4380 testName += "_storage_texel_buffer"; 4381 graphicsTests->addChild(new PushDescriptorTexelBufferGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4382 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4383 computeTests->addChild(new PushDescriptorTexelBufferComputeTest(testCtx, testName.c_str(), params[testIdx])); 4384 break; 4385 4386 case VK_DESCRIPTOR_TYPE_INPUT_ATTACHMENT: 4387 // Input attachments are not supported with dynamic rendering 4388 if (!vk::isConstructionTypeShaderObject(pipelineType)) 4389 { 4390 testName += "_input_attachment"; 4391 graphicsTests->addChild(new PushDescriptorInputAttachmentGraphicsTest(testCtx, testName.c_str(), params[testIdx])); 4392 } 4393 break; 4394 4395 default: 4396 DE_FATAL("Unexpected descriptor type"); 4397 break; 4398 } 4399 } 4400 4401 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4402 { 4403 TestParams testParams = { pipelineType, VK_DESCRIPTOR_TYPE_UNIFORM_TEXEL_BUFFER, 0u, 1u, true }; 4404 graphicsTests->addChild(new PushDescriptorTexelBufferGraphicsTest(testCtx, "maintenance5_uniform_texel_buffer", testParams)); 4405 testParams.descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER; 4406 graphicsTests->addChild(new PushDescriptorTexelBufferGraphicsTest(testCtx, "maintenance5_storage_texel_buffer", testParams)); 4407 testParams.descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER; 4408 graphicsTests->addChild(new PushDescriptorBufferGraphicsTest(testCtx, "maintenance5_uniform_buffer", testParams)); 4409 } 4410 4411 pushDescriptorTests->addChild(graphicsTests.release()); 4412 if (pipelineType == PIPELINE_CONSTRUCTION_TYPE_MONOLITHIC) 4413 pushDescriptorTests->addChild(computeTests.release()); 4414 4415 return pushDescriptorTests.release(); 4416} 4417 4418} // pipeline 4419} // vkt 4420