我正在尝试做两个简单的子通道,其中第二个通道依赖于第一个。
//subpass 1
VkAttachmentReference colorReferences = { 0, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL };
VkSubpassDescription subpass1 = {};
subpass1.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS;
subpass1.pColorAttachments = &colorReferences;
subpass1.colorAttachmentCount = 1;
//subpass 2
VkAttachmentReference inputRefernce = { 0, VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL };
VkSubpassDescription subpass2 = {};
subpass2.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS;
subpass2.inputAttachmentCount = 1;
subpass2.pInputAttachments = &inputRefernce;
//Render pass
VkAttachmentDescription attachmentDescs = {};
attachmentDescs.samples = VK_SAMPLE_COUNT_1_BIT;
attachmentDescs.loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
attachmentDescs.storeOp = VK_ATTACHMENT_STORE_OP_STORE;
attachmentDescs.stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescs.stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescs.format = VK_FORMAT_R16G16B16A16_SFLOAT;
attachmentDescs.initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
attachmentDescs.finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
VkSubpassDependency dependency = {};
dependency.srcSubpass = 0;
dependency.dstSubpass = 1;
dependency.srcStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT;
dependency.dstStageMask = VK_PIPELINE_STAGE_ALL_GRAPHICS_BIT;
dependency.srcAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT;
dependency.dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
VkSubpassDescription subpasses[2] = { subpass1, subpass2 };
VkRenderPassCreateInfo renderPassInfo = {};
renderPassInfo.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO;
renderPassInfo.pAttachments = &attachmentDescs;
renderPassInfo.attachmentCount = 1;
renderPassInfo.subpassCount = 2;
renderPassInfo.pSubpasses = subpasses;
renderPassInfo.dependencyCount = 1;
renderPassInfo.pDependencies = &dependency;
vkUtils::checkResult(vkCreateRenderPass(_context->device, &renderPassInfo, nullptr, &_renderPass));
我在第一个和第二个子通道之间存在依赖关系。规范说:
如果附件指定
VK_ATTACHMENT_LOAD_OP_CLEAR
加载 操作,然后它将在第一个开始时被逻辑清除 使用它的子通道。
只有在使用附件的第一个子通道开始时才会清除它。并且因为它们之间存在依赖关系,所以不应该在第二个子通道中清除它。
首次使用附件时,不得指定等于的布局 VK_IMAGE_LAYOUT_DEPTH_STENCIL_READ_ONLY_OPTIMAL或 如果附件指定,则为VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL 那个> loadOp是VK_ATTACHMENT_LOAD_OP_CLEAR。 [...]
我从验证层收到此错误:
Cannot clear attachment 0 with invalid first layout VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL.
但是VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL
布局是在第二个子通道中,而不是第一个?
答案 0 :(得分:3)
它似乎是图层中的一个错误,它根本不检查哪个用法是第一个(它可能是在1.0.17 SDK中引入的 - 1.0.13不应该报告这个......): https://github.com/KhronosGroup/Vulkan-LoaderAndValidationLayers/blob/sdk-1.0.17/layers/core_validation.cpp#L8557
规格引用:
如果附件指定
VK_IMAGE_LAYOUT_DEPTH_STENCIL_READ_ONLY_OPTIMAL
为VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL
,首次使用附件必须指定等于loadOp
或VK_ATTACHMENT_LOAD_OP_CLEAR
的布局}。 [...]