Add support for VK_KHR_imageless_framebuffer

This commit is contained in:
baldurk
2019-08-14 18:14:48 +01:00
parent 211d1b694f
commit 9589d2d893
24 changed files with 801 additions and 153 deletions
+15 -7
View File
@@ -654,8 +654,8 @@ DECLARE_REFLECTION_STRUCT(VkBindImageMemorySwapchainInfoKHR);
DECLARE_REFLECTION_STRUCT(VkBindImagePlaneMemoryInfo);
DECLARE_REFLECTION_STRUCT(VkBindSparseInfo);
DECLARE_REFLECTION_STRUCT(VkBufferCreateInfo);
DECLARE_REFLECTION_STRUCT(VkBufferDeviceAddressInfoEXT);
DECLARE_REFLECTION_STRUCT(VkBufferDeviceAddressCreateInfoEXT);
DECLARE_REFLECTION_STRUCT(VkBufferDeviceAddressInfoEXT);
DECLARE_REFLECTION_STRUCT(VkBufferMemoryBarrier);
DECLARE_REFLECTION_STRUCT(VkBufferMemoryRequirementsInfo2);
DECLARE_REFLECTION_STRUCT(VkBufferViewCreateInfo);
@@ -725,6 +725,8 @@ DECLARE_REFLECTION_STRUCT(VkExternalSemaphoreProperties);
DECLARE_REFLECTION_STRUCT(VkFenceCreateInfo);
DECLARE_REFLECTION_STRUCT(VkFenceGetFdInfoKHR);
DECLARE_REFLECTION_STRUCT(VkFormatProperties2);
DECLARE_REFLECTION_STRUCT(VkFramebufferAttachmentImageInfoKHR);
DECLARE_REFLECTION_STRUCT(VkFramebufferAttachmentsCreateInfoKHR);
DECLARE_REFLECTION_STRUCT(VkFramebufferCreateInfo);
DECLARE_REFLECTION_STRUCT(VkGraphicsPipelineCreateInfo);
DECLARE_REFLECTION_STRUCT(VkHdrMetadataEXT);
@@ -734,8 +736,8 @@ DECLARE_REFLECTION_STRUCT(VkImageFormatProperties2);
DECLARE_REFLECTION_STRUCT(VkImageMemoryBarrier);
DECLARE_REFLECTION_STRUCT(VkImageMemoryRequirementsInfo2);
DECLARE_REFLECTION_STRUCT(VkImagePlaneMemoryRequirementsInfo);
DECLARE_REFLECTION_STRUCT(VkImageStencilUsageCreateInfoEXT);
DECLARE_REFLECTION_STRUCT(VkImageSparseMemoryRequirementsInfo2);
DECLARE_REFLECTION_STRUCT(VkImageStencilUsageCreateInfoEXT);
DECLARE_REFLECTION_STRUCT(VkImageSwapchainCreateInfoKHR);
DECLARE_REFLECTION_STRUCT(VkImageViewASTCDecodeModeEXT);
DECLARE_REFLECTION_STRUCT(VkImageViewCreateInfo);
@@ -782,6 +784,7 @@ DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceGroupProperties);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceHostQueryResetFeaturesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceIDProperties);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceImageFormatInfo2);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceImagelessFramebufferFeaturesKHR);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceIndexTypeUint8FeaturesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceMaintenance3Properties);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceMemoryBudgetPropertiesEXT);
@@ -812,15 +815,15 @@ DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceTexelBufferAlignmentPropertiesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceTransformFeedbackFeaturesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceTransformFeedbackPropertiesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceUniformBufferStandardLayoutFeaturesKHR);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceVariablePointerFeatures);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceVertexAttributeDivisorFeaturesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceUniformBufferStandardLayoutFeaturesKHR);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceVulkanMemoryModelFeaturesKHR);
DECLARE_REFLECTION_STRUCT(VkPhysicalDeviceYcbcrImageArraysFeaturesEXT);
DECLARE_REFLECTION_STRUCT(VkPipelineCacheCreateInfo);
DECLARE_REFLECTION_STRUCT(VkPipelineCreationFeedbackCreateInfoEXT);
DECLARE_REFLECTION_STRUCT(VkPipelineColorBlendStateCreateInfo);
DECLARE_REFLECTION_STRUCT(VkPipelineCreationFeedbackCreateInfoEXT);
DECLARE_REFLECTION_STRUCT(VkPipelineDepthStencilStateCreateInfo);
DECLARE_REFLECTION_STRUCT(VkPipelineDiscardRectangleStateCreateInfoEXT);
DECLARE_REFLECTION_STRUCT(VkPipelineDynamicStateCreateInfo);
@@ -843,6 +846,7 @@ DECLARE_REFLECTION_STRUCT(VkPresentRegionsKHR);
DECLARE_REFLECTION_STRUCT(VkProtectedSubmitInfo);
DECLARE_REFLECTION_STRUCT(VkQueryPoolCreateInfo);
DECLARE_REFLECTION_STRUCT(VkQueueFamilyProperties2);
DECLARE_REFLECTION_STRUCT(VkRenderPassAttachmentBeginInfoKHR);
DECLARE_REFLECTION_STRUCT(VkRenderPassBeginInfo);
DECLARE_REFLECTION_STRUCT(VkRenderPassCreateInfo);
DECLARE_REFLECTION_STRUCT(VkRenderPassCreateInfo2KHR);
@@ -966,6 +970,8 @@ DECLARE_DESERIALISE_TYPE(VkExternalSemaphoreProperties);
DECLARE_DESERIALISE_TYPE(VkFenceCreateInfo);
DECLARE_DESERIALISE_TYPE(VkFenceGetFdInfoKHR);
DECLARE_DESERIALISE_TYPE(VkFormatProperties2);
DECLARE_DESERIALISE_TYPE(VkFramebufferAttachmentImageInfoKHR);
DECLARE_DESERIALISE_TYPE(VkFramebufferAttachmentsCreateInfoKHR);
DECLARE_DESERIALISE_TYPE(VkFramebufferCreateInfo);
DECLARE_DESERIALISE_TYPE(VkGraphicsPipelineCreateInfo);
DECLARE_DESERIALISE_TYPE(VkImageCreateInfo);
@@ -974,8 +980,8 @@ DECLARE_DESERIALISE_TYPE(VkImageFormatProperties2);
DECLARE_DESERIALISE_TYPE(VkImageMemoryBarrier);
DECLARE_DESERIALISE_TYPE(VkImageMemoryRequirementsInfo2);
DECLARE_DESERIALISE_TYPE(VkImagePlaneMemoryRequirementsInfo);
DECLARE_DESERIALISE_TYPE(VkImageStencilUsageCreateInfoEXT);
DECLARE_DESERIALISE_TYPE(VkImageSparseMemoryRequirementsInfo2);
DECLARE_DESERIALISE_TYPE(VkImageStencilUsageCreateInfoEXT);
DECLARE_DESERIALISE_TYPE(VkImageSwapchainCreateInfoKHR);
DECLARE_DESERIALISE_TYPE(VkImageViewASTCDecodeModeEXT);
DECLARE_DESERIALISE_TYPE(VkImageViewCreateInfo);
@@ -1021,6 +1027,7 @@ DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceGroupProperties);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceHostQueryResetFeaturesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceIDProperties);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceImageFormatInfo2);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceImagelessFramebufferFeaturesKHR);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceIndexTypeUint8FeaturesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceMaintenance3Properties);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceMemoryBudgetPropertiesEXT);
@@ -1051,15 +1058,15 @@ DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceTexelBufferAlignmentPropertiesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceTransformFeedbackFeaturesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceTransformFeedbackPropertiesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceUniformBufferStandardLayoutFeaturesKHR);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceVariablePointerFeatures);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceVertexAttributeDivisorFeaturesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceUniformBufferStandardLayoutFeaturesKHR);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceVulkanMemoryModelFeaturesKHR);
DECLARE_DESERIALISE_TYPE(VkPhysicalDeviceYcbcrImageArraysFeaturesEXT);
DECLARE_DESERIALISE_TYPE(VkPipelineCacheCreateInfo);
DECLARE_DESERIALISE_TYPE(VkPipelineCreationFeedbackCreateInfoEXT);
DECLARE_DESERIALISE_TYPE(VkPipelineColorBlendStateCreateInfo);
DECLARE_DESERIALISE_TYPE(VkPipelineCreationFeedbackCreateInfoEXT);
DECLARE_DESERIALISE_TYPE(VkPipelineDepthStencilStateCreateInfo);
DECLARE_DESERIALISE_TYPE(VkPipelineDiscardRectangleStateCreateInfoEXT);
DECLARE_DESERIALISE_TYPE(VkPipelineDynamicStateCreateInfo);
@@ -1082,6 +1089,7 @@ DECLARE_DESERIALISE_TYPE(VkPresentRegionsKHR);
DECLARE_DESERIALISE_TYPE(VkProtectedSubmitInfo);
DECLARE_DESERIALISE_TYPE(VkQueryPoolCreateInfo);
DECLARE_DESERIALISE_TYPE(VkQueueFamilyProperties2);
DECLARE_DESERIALISE_TYPE(VkRenderPassAttachmentBeginInfoKHR);
DECLARE_DESERIALISE_TYPE(VkRenderPassBeginInfo);
DECLARE_DESERIALISE_TYPE(VkRenderPassCreateInfo);
DECLARE_DESERIALISE_TYPE(VkRenderPassCreateInfo2KHR);
+22 -18
View File
@@ -915,6 +915,9 @@ static const VkExtensionProperties supportedExtensions[] = {
{
VK_KHR_IMAGE_FORMAT_LIST_EXTENSION_NAME, VK_KHR_IMAGE_FORMAT_LIST_SPEC_VERSION,
},
{
VK_KHR_IMAGELESS_FRAMEBUFFER_EXTENSION_NAME, VK_KHR_IMAGELESS_FRAMEBUFFER_SPEC_VERSION,
},
{
VK_KHR_INCREMENTAL_PRESENT_EXTENSION_NAME, VK_KHR_INCREMENTAL_PRESENT_SPEC_VERSION,
},
@@ -3589,8 +3592,7 @@ void WrappedVulkan::AddDrawcall(const DrawcallDescription &d, bool hasEvents)
if(fb != ResourceId() && rp != ResourceId())
{
std::vector<VulkanCreationInfo::Framebuffer::Attachment> &atts =
m_CreationInfo.m_Framebuffer[fb].attachments;
std::vector<ResourceId> &atts = m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments;
RDCASSERT(sp < m_CreationInfo.m_RenderPass[rp].subpasses.size());
@@ -3605,15 +3607,15 @@ void WrappedVulkan::AddDrawcall(const DrawcallDescription &d, bool hasEvents)
continue;
RDCASSERT(colAtt[i] < atts.size());
draw.outputs[i] = GetResourceManager()->GetOriginalID(
m_CreationInfo.m_ImageView[atts[colAtt[i]].view].image);
draw.outputs[i] =
GetResourceManager()->GetOriginalID(m_CreationInfo.m_ImageView[atts[colAtt[i]]].image);
}
if(dsAtt != -1)
{
RDCASSERT(dsAtt < (int32_t)atts.size());
draw.depthOut =
GetResourceManager()->GetOriginalID(m_CreationInfo.m_ImageView[atts[dsAtt].view].image);
GetResourceManager()->GetOriginalID(m_CreationInfo.m_ImageView[atts[dsAtt]].image);
}
}
}
@@ -3837,11 +3839,13 @@ void WrappedVulkan::AddUsage(VulkanDrawcallTreeNode &drawNode,
//////////////////////////////
// Framebuffer/renderpass
AddFramebufferUsage(drawNode, state.renderPass, state.framebuffer, state.subpass);
AddFramebufferUsage(drawNode, state.renderPass, state.framebuffer, state.subpass,
state.fbattachments);
}
void WrappedVulkan::AddFramebufferUsage(VulkanDrawcallTreeNode &drawNode, ResourceId renderPass,
ResourceId framebuffer, uint32_t subpass)
ResourceId framebuffer, uint32_t subpass,
const std::vector<ResourceId> &fbattachments)
{
VulkanCreationInfo &c = m_CreationInfo;
uint32_t e = drawNode.draw.eventId;
@@ -3849,7 +3853,6 @@ void WrappedVulkan::AddFramebufferUsage(VulkanDrawcallTreeNode &drawNode, Resour
if(renderPass != ResourceId() && framebuffer != ResourceId())
{
const VulkanCreationInfo::RenderPass &rp = c.m_RenderPass[renderPass];
const VulkanCreationInfo::Framebuffer &fb = c.m_Framebuffer[framebuffer];
if(subpass >= rp.subpasses.size())
{
@@ -3866,8 +3869,8 @@ void WrappedVulkan::AddFramebufferUsage(VulkanDrawcallTreeNode &drawNode, Resour
if(att == VK_ATTACHMENT_UNUSED)
continue;
drawNode.resourceUsage.push_back(
make_rdcpair(c.m_ImageView[fb.attachments[att].view].image,
EventUsage(e, ResourceUsage::InputTarget, fb.attachments[att].view)));
make_rdcpair(c.m_ImageView[fbattachments[att]].image,
EventUsage(e, ResourceUsage::InputTarget, fbattachments[att])));
}
for(size_t i = 0; i < sub.colorAttachments.size(); i++)
@@ -3876,16 +3879,16 @@ void WrappedVulkan::AddFramebufferUsage(VulkanDrawcallTreeNode &drawNode, Resour
if(att == VK_ATTACHMENT_UNUSED)
continue;
drawNode.resourceUsage.push_back(
make_rdcpair(c.m_ImageView[fb.attachments[att].view].image,
EventUsage(e, ResourceUsage::ColorTarget, fb.attachments[att].view)));
make_rdcpair(c.m_ImageView[fbattachments[att]].image,
EventUsage(e, ResourceUsage::ColorTarget, fbattachments[att])));
}
if(sub.depthstencilAttachment >= 0)
{
int32_t att = sub.depthstencilAttachment;
drawNode.resourceUsage.push_back(make_rdcpair(
c.m_ImageView[fb.attachments[att].view].image,
EventUsage(e, ResourceUsage::DepthStencilTarget, fb.attachments[att].view)));
drawNode.resourceUsage.push_back(
make_rdcpair(c.m_ImageView[fbattachments[att]].image,
EventUsage(e, ResourceUsage::DepthStencilTarget, fbattachments[att])));
}
}
}
@@ -3893,12 +3896,13 @@ void WrappedVulkan::AddFramebufferUsage(VulkanDrawcallTreeNode &drawNode, Resour
void WrappedVulkan::AddFramebufferUsageAllChildren(VulkanDrawcallTreeNode &drawNode,
ResourceId renderPass, ResourceId framebuffer,
uint32_t subpass)
uint32_t subpass,
const std::vector<ResourceId> &fbattachments)
{
for(VulkanDrawcallTreeNode &c : drawNode.children)
AddFramebufferUsageAllChildren(c, renderPass, framebuffer, subpass);
AddFramebufferUsageAllChildren(c, renderPass, framebuffer, subpass, fbattachments);
AddFramebufferUsage(drawNode, renderPass, framebuffer, subpass);
AddFramebufferUsage(drawNode, renderPass, framebuffer, subpass, fbattachments);
}
void WrappedVulkan::AddEvent()
+5 -2
View File
@@ -544,6 +544,7 @@ private:
ResourceId renderPass;
ResourceId framebuffer;
std::vector<ResourceId> fbattachments;
uint32_t subpass = 0;
struct ConditionalRendering
@@ -877,9 +878,11 @@ private:
void AddUsage(VulkanDrawcallTreeNode &drawNode, std::vector<DebugMessage> &debugMessages);
void AddFramebufferUsage(VulkanDrawcallTreeNode &drawNode, ResourceId renderPass,
ResourceId framebuffer, uint32_t subpass);
ResourceId framebuffer, uint32_t subpass,
const std::vector<ResourceId> &fbattachments);
void AddFramebufferUsageAllChildren(VulkanDrawcallTreeNode &drawNode, ResourceId renderPass,
ResourceId framebuffer, uint32_t subpass);
ResourceId framebuffer, uint32_t subpass,
const std::vector<ResourceId> &fbattachments);
// no copy semantics
WrappedVulkan(const WrappedVulkan &);
+30 -3
View File
@@ -801,11 +801,38 @@ void VulkanCreationInfo::Framebuffer::Init(VulkanResourceManager *resourceMan,
height = pCreateInfo->height;
layers = pCreateInfo->layers;
imageless = false;
attachments.resize(pCreateInfo->attachmentCount);
for(uint32_t i = 0; i < pCreateInfo->attachmentCount; i++)
if(pCreateInfo->flags & VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT_KHR)
{
attachments[i].view = GetResID(pCreateInfo->pAttachments[i]);
attachments[i].format = info.m_ImageView[attachments[i].view].format;
imageless = true;
// VK_KHR_imageless_framebuffer
const VkFramebufferAttachmentsCreateInfoKHR *attachmentsInfo =
(const VkFramebufferAttachmentsCreateInfoKHR *)FindNextStruct(
pCreateInfo, VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR);
RDCASSERTEQUAL(pCreateInfo->attachmentCount, attachmentsInfo->attachmentImageInfoCount);
for(uint32_t i = 0; i < pCreateInfo->attachmentCount; i++)
{
attachments[i].createdView = ResourceId();
// there must be at least one format in the list so we can safely look at [0].
// also all entries must be compatible, so if [0] doesn't have stencil then none of them do,
// and vice-versa.
attachments[i].hasStencil =
IsStencilFormat(attachmentsInfo->pAttachmentImageInfos[i].pViewFormats[0]);
}
}
else
{
for(uint32_t i = 0; i < pCreateInfo->attachmentCount; i++)
{
attachments[i].createdView = GetResID(pCreateInfo->pAttachments[i]);
attachments[i].hasStencil =
IsStencilFormat(info.m_ImageView[attachments[i].createdView].format);
}
}
}
+3 -2
View File
@@ -345,10 +345,11 @@ struct VulkanCreationInfo
struct Attachment
{
ResourceId view;
VkFormat format;
ResourceId createdView;
bool hasStencil;
};
std::vector<Attachment> attachments;
bool imageless;
uint32_t width, height, layers;
+41 -7
View File
@@ -134,6 +134,10 @@ static void AppendModifiedChainedStruct(byte *&tempMem, VkStruct *outputStruct,
COPY_STRUCT(VK_STRUCTURE_TYPE_FENCE_CREATE_INFO, VkFenceCreateInfo); \
COPY_STRUCT(VK_STRUCTURE_TYPE_FILTER_CUBIC_IMAGE_VIEW_IMAGE_FORMAT_PROPERTIES_EXT, \
VkFilterCubicImageViewImageFormatPropertiesEXT); \
COPY_STRUCT(VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR, \
VkFramebufferAttachmentsCreateInfoKHR) \
COPY_STRUCT(VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO_KHR, \
VkFramebufferAttachmentImageInfoKHR) \
COPY_STRUCT(VK_STRUCTURE_TYPE_FORMAT_PROPERTIES_2, VkFormatProperties2); \
COPY_STRUCT(VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO, VkImageCreateInfo); \
COPY_STRUCT(VK_STRUCTURE_TYPE_IMAGE_FORMAT_LIST_CREATE_INFO_KHR, VkImageFormatListCreateInfoKHR); \
@@ -202,6 +206,8 @@ static void AppendModifiedChainedStruct(byte *&tempMem, VkStruct *outputStruct,
VkPhysicalDeviceImageFormatInfo2); \
COPY_STRUCT(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_VIEW_IMAGE_FORMAT_INFO_EXT, \
VkPhysicalDeviceImageViewImageFormatInfoEXT); \
COPY_STRUCT(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR, \
VkPhysicalDeviceImagelessFramebufferFeaturesKHR) \
COPY_STRUCT(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_INDEX_TYPE_UINT8_FEATURES_EXT, \
VkPhysicalDeviceIndexTypeUint8FeaturesEXT); \
COPY_STRUCT(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_3_PROPERTIES, \
@@ -483,8 +489,6 @@ static void AppendModifiedChainedStruct(byte *&tempMem, VkStruct *outputStruct,
case VK_STRUCTURE_TYPE_DRM_FORMAT_MODIFIER_PROPERTIES_EXT: \
case VK_STRUCTURE_TYPE_DRM_FORMAT_MODIFIER_PROPERTIES_LIST_EXT: \
case VK_STRUCTURE_TYPE_EXTERNAL_FORMAT_ANDROID: \
case VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR: \
case VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO_KHR: \
case VK_STRUCTURE_TYPE_FRAMEBUFFER_MIXED_SAMPLES_COMBINATION_NV: \
case VK_STRUCTURE_TYPE_GEOMETRY_AABB_NV: \
case VK_STRUCTURE_TYPE_GEOMETRY_NV: \
@@ -518,7 +522,6 @@ static void AppendModifiedChainedStruct(byte *&tempMem, VkStruct *outputStruct,
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADER_BARYCENTRIC_FEATURES_NV: \
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_GROUP_PROPERTIES: \
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_DRM_FORMAT_MODIFIER_INFO_EXT: \
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR: \
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_INLINE_UNIFORM_BLOCK_FEATURES_EXT: \
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_INLINE_UNIFORM_BLOCK_PROPERTIES_EXT: \
case VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_LINE_RASTERIZATION_FEATURES_EXT: \
@@ -562,7 +565,6 @@ static void AppendModifiedChainedStruct(byte *&tempMem, VkStruct *outputStruct,
case VK_STRUCTURE_TYPE_QUEUE_FAMILY_CHECKPOINT_PROPERTIES_NV: \
case VK_STRUCTURE_TYPE_RAY_TRACING_PIPELINE_CREATE_INFO_NV: \
case VK_STRUCTURE_TYPE_RAY_TRACING_SHADER_GROUP_CREATE_INFO_NV: \
case VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR: \
case VK_STRUCTURE_TYPE_SURFACE_CAPABILITIES_FULL_SCREEN_EXCLUSIVE_EXT: \
case VK_STRUCTURE_TYPE_SURFACE_FULL_SCREEN_EXCLUSIVE_INFO_EXT: \
case VK_STRUCTURE_TYPE_SURFACE_FULL_SCREEN_EXCLUSIVE_WIN32_INFO_EXT: \
@@ -688,6 +690,14 @@ size_t GetNextPatchSize(const void *pNext)
memSize += info->swapchainCount * sizeof(VkSwapchainKHR);
break;
}
case VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR:
{
memSize += sizeof(VkRenderPassAttachmentBeginInfoKHR);
VkRenderPassAttachmentBeginInfoKHR *info = (VkRenderPassAttachmentBeginInfoKHR *)next;
memSize += info->attachmentCount * sizeof(VkImageView);
break;
}
case VK_STRUCTURE_TYPE_SUBMIT_INFO:
{
memSize += sizeof(VkSubmitInfo);
@@ -1079,9 +1089,12 @@ void UnwrapNextChain(CaptureState state, const char *structName, byte *&tempMem,
*out = *in;
UnwrapInPlace(out->renderPass);
out->pAttachments = outAttachments;
for(uint32_t i = 0; i < in->attachmentCount; i++)
outAttachments[i] = Unwrap(in->pAttachments[i]);
if((out->flags & VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT_KHR) == 0)
{
out->pAttachments = outAttachments;
for(uint32_t i = 0; i < in->attachmentCount; i++)
outAttachments[i] = Unwrap(in->pAttachments[i]);
}
break;
}
@@ -1169,6 +1182,27 @@ void UnwrapNextChain(CaptureState state, const char *structName, byte *&tempMem,
break;
}
case VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR:
{
const VkRenderPassAttachmentBeginInfoKHR *in =
(const VkRenderPassAttachmentBeginInfoKHR *)nextInput;
VkRenderPassAttachmentBeginInfoKHR *out = (VkRenderPassAttachmentBeginInfoKHR *)tempMem;
// append immediately so tempMem is incremented
AppendModifiedChainedStruct(tempMem, out, nextChainTail);
// allocate unwrapped array
VkImageView *outAttachments = (VkImageView *)tempMem;
tempMem += sizeof(VkImageView) * in->attachmentCount;
*out = *in;
out->pAttachments = outAttachments;
for(uint32_t i = 0; i < in->attachmentCount; i++)
outAttachments[i] = Unwrap(in->pAttachments[i]);
break;
}
case VK_STRUCTURE_TYPE_SUBMIT_INFO:
{
const VkSubmitInfo *in = (const VkSubmitInfo *)nextInput;
+12 -10
View File
@@ -409,7 +409,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
// refreshed before the UI layer can update the current texture.
{
const VulkanCreationInfo::Framebuffer &fb =
m_pDriver->m_CreationInfo.m_Framebuffer[m_pDriver->m_RenderState.framebuffer];
m_pDriver->m_CreationInfo.m_Framebuffer[m_pDriver->m_RenderState.GetFramebuffer()];
if(fb.width != iminfo.extent.width || fb.height != iminfo.extent.height)
return GetResID(m_Overlay.Image);
@@ -833,7 +833,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
// modify state
m_pDriver->m_RenderState.renderPass = GetResID(m_Overlay.NoDepthRP);
m_pDriver->m_RenderState.subpass = 0;
m_pDriver->m_RenderState.framebuffer = GetResID(m_Overlay.NoDepthFB);
m_pDriver->m_RenderState.SetFramebuffer(GetResID(m_Overlay.NoDepthFB));
m_pDriver->m_RenderState.graphics.pipeline = GetResID(pipe);
@@ -1167,7 +1167,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
// modify state
m_pDriver->m_RenderState.renderPass = GetResID(m_Overlay.NoDepthRP);
m_pDriver->m_RenderState.subpass = 0;
m_pDriver->m_RenderState.framebuffer = GetResID(m_Overlay.NoDepthFB);
m_pDriver->m_RenderState.SetFramebuffer(GetResID(m_Overlay.NoDepthFB));
m_pDriver->m_RenderState.graphics.pipeline = GetResID(pipe[0]);
@@ -1242,7 +1242,8 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
// make a renderpass and framebuffer for rendering to overlay color and using
// depth buffer from the orignial render
if(dsIdx >= 0 && dsIdx < (int32_t)createinfo.m_Framebuffer[state.framebuffer].attachments.size())
if(dsIdx >= 0 &&
dsIdx < (int32_t)createinfo.m_Framebuffer[state.GetFramebuffer()].attachments.size())
{
VkAttachmentDescription attDescs[] = {
{0, VK_FORMAT_R16G16B16A16_SFLOAT, VK_SAMPLE_COUNT_1_BIT, VK_ATTACHMENT_LOAD_OP_LOAD,
@@ -1255,7 +1256,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL},
};
ResourceId depthView = createinfo.m_Framebuffer[state.framebuffer].attachments[dsIdx].view;
ResourceId depthView = state.GetFramebufferAttachments()[dsIdx];
VulkanCreationInfo::ImageView &depthViewInfo = createinfo.m_ImageView[depthView];
ResourceId depthIm = depthViewInfo.image;
@@ -1465,7 +1466,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
// modify state
m_pDriver->m_RenderState.renderPass = GetResID(m_Overlay.NoDepthRP);
m_pDriver->m_RenderState.subpass = 0;
m_pDriver->m_RenderState.framebuffer = GetResID(m_Overlay.NoDepthFB);
m_pDriver->m_RenderState.SetFramebuffer(GetResID(m_Overlay.NoDepthFB));
m_pDriver->m_RenderState.graphics.pipeline = GetResID(failpipe);
@@ -1487,7 +1488,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
if(depthRP != VK_NULL_HANDLE)
{
m_pDriver->m_RenderState.renderPass = GetResID(depthRP);
m_pDriver->m_RenderState.framebuffer = GetResID(depthFB);
m_pDriver->m_RenderState.SetFramebuffer(GetResID(depthFB));
}
m_pDriver->ReplayLog(0, eventId, eReplay_OnlyDraw);
@@ -1599,7 +1600,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
std::vector<VkClearAttachment> atts;
VulkanCreationInfo::Framebuffer &fb =
m_pDriver->m_CreationInfo.m_Framebuffer[m_pDriver->m_RenderState.framebuffer];
m_pDriver->m_CreationInfo.m_Framebuffer[m_pDriver->m_RenderState.GetFramebuffer()];
VulkanCreationInfo::RenderPass &rp =
m_pDriver->m_CreationInfo.m_RenderPass[m_pDriver->m_RenderState.renderPass];
@@ -1997,7 +1998,8 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
// make a renderpass and framebuffer for rendering to overlay color and using
// depth buffer from the orignial render
if(dsIdx >= 0 && dsIdx < (int32_t)createinfo.m_Framebuffer[state.framebuffer].attachments.size())
if(dsIdx >= 0 &&
dsIdx < (int32_t)createinfo.m_Framebuffer[state.GetFramebuffer()].attachments.size())
{
depthUsed = true;
@@ -2012,7 +2014,7 @@ ResourceId VulkanReplay::RenderOverlay(ResourceId texid, CompType typeHint, Floa
VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL},
};
ResourceId depthView = createinfo.m_Framebuffer[state.framebuffer].attachments[dsIdx].view;
ResourceId depthView = state.GetFramebufferAttachments()[dsIdx];
VulkanCreationInfo::ImageView &depthViewInfo = createinfo.m_ImageView[depthView];
ResourceId depthIm = depthViewInfo.image;
+4 -3
View File
@@ -370,7 +370,8 @@ struct VulkanPixelHistoryCallback : public VulkanDrawcallCallback
VulkanRenderState &pipestate = m_pDriver->GetRenderState();
ResourceId prevState = pipestate.graphics.pipeline;
ResourceId prevRenderpass = pipestate.renderPass;
ResourceId prevFramebuffer = pipestate.framebuffer;
ResourceId prevFramebuffer = pipestate.GetFramebuffer();
std::vector<ResourceId> prevFBattachments = pipestate.GetFramebufferAttachments();
uint32_t prevSubpass = pipestate.subpass;
{
@@ -395,7 +396,7 @@ struct VulkanPixelHistoryCallback : public VulkanDrawcallCallback
for(uint32_t i = 0; i < pipestate.views.size(); i++)
UpdateScissor(pipestate.views[i], pipestate.scissors[i]);
pipestate.framebuffer = GetResID(m_OffscreenFB);
pipestate.SetFramebuffer(GetResID(m_OffscreenFB));
pipestate.renderPass = GetResID(m_RenderPass);
pipestate.subpass = 0;
pipestate.graphics.pipeline = GetResID(replacements.occlusion);
@@ -410,7 +411,7 @@ struct VulkanPixelHistoryCallback : public VulkanDrawcallCallback
// Restore the state.
m_pDriver->GetRenderState() = m_PrevState;
pipestate.framebuffer = prevFramebuffer;
pipestate.SetFramebuffer(prevFramebuffer, prevFBattachments);
pipestate.renderPass = prevRenderpass;
pipestate.subpass = prevSubpass;
+1 -1
View File
@@ -2775,7 +2775,7 @@ void VulkanReplay::FetchTessGSOut(uint32_t eventId)
RDCASSERTEQUAL(vkr, VK_SUCCESS);
state.graphics.pipeline = GetResID(pipe);
state.framebuffer = GetResID(fb);
state.SetFramebuffer(GetResID(fb));
state.renderPass = GetResID(rp);
state.subpass = 0;
state.renderArea.offset.x = 0;
+10 -10
View File
@@ -1272,21 +1272,21 @@ void VulkanReplay::SavePipelineState(uint32_t eventId)
c.m_RenderPass[state.renderPass].subpasses[state.subpass].multiviews;
}
m_VulkanPipelineState.currentPass.framebuffer.resourceId = rm->GetOriginalID(state.framebuffer);
ResourceId fb = state.GetFramebuffer();
if(state.framebuffer != ResourceId())
m_VulkanPipelineState.currentPass.framebuffer.resourceId = rm->GetOriginalID(fb);
if(fb != ResourceId())
{
m_VulkanPipelineState.currentPass.framebuffer.width = c.m_Framebuffer[state.framebuffer].width;
m_VulkanPipelineState.currentPass.framebuffer.height =
c.m_Framebuffer[state.framebuffer].height;
m_VulkanPipelineState.currentPass.framebuffer.layers =
c.m_Framebuffer[state.framebuffer].layers;
m_VulkanPipelineState.currentPass.framebuffer.width = c.m_Framebuffer[fb].width;
m_VulkanPipelineState.currentPass.framebuffer.height = c.m_Framebuffer[fb].height;
m_VulkanPipelineState.currentPass.framebuffer.layers = c.m_Framebuffer[fb].layers;
m_VulkanPipelineState.currentPass.framebuffer.attachments.resize(
c.m_Framebuffer[state.framebuffer].attachments.size());
for(size_t i = 0; i < c.m_Framebuffer[state.framebuffer].attachments.size(); i++)
c.m_Framebuffer[fb].attachments.size());
for(size_t i = 0; i < c.m_Framebuffer[fb].attachments.size(); i++)
{
ResourceId viewid = c.m_Framebuffer[state.framebuffer].attachments[i].view;
ResourceId viewid = state.GetFramebufferAttachments()[i];
if(viewid != ResourceId())
{
+5
View File
@@ -983,6 +983,11 @@ struct CmdBufferRecordingInfo
// submit with latest binding refs.
std::set<VkDescriptorSet> boundDescSets;
// barriers to apply when the current render pass ends. Calculated at begin time in case the
// framebuffer is imageless and we need to use the image views passed in at begin time to
// construct the proper barriers.
std::vector<VkImageMemoryBarrier> rpbarriers;
std::vector<VkResourceRecord *> subcmds;
std::map<ResourceId, ImgRefs> imgFrameRefs;
+94 -14
View File
@@ -767,6 +767,16 @@ SERIALISE_VK_HANDLES();
/* VK_KHR_image_format_list */ \
PNEXT_STRUCT(VK_STRUCTURE_TYPE_IMAGE_FORMAT_LIST_CREATE_INFO_KHR, VkImageFormatListCreateInfoKHR) \
\
/* VK_KHR_imageless_framebuffer */ \
PNEXT_STRUCT(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR, \
VkPhysicalDeviceImagelessFramebufferFeaturesKHR) \
PNEXT_STRUCT(VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR, \
VkFramebufferAttachmentsCreateInfoKHR) \
PNEXT_STRUCT(VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO_KHR, \
VkFramebufferAttachmentImageInfoKHR) \
PNEXT_STRUCT(VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR, \
VkRenderPassAttachmentBeginInfoKHR) \
\
/* VK_KHR_incremental_present */ \
PNEXT_STRUCT(VK_STRUCTURE_TYPE_PRESENT_REGIONS_KHR, VkPresentRegionsKHR) \
\
@@ -956,12 +966,6 @@ SERIALISE_VK_HANDLES();
/* VK_INTEL_shader_integer_functions2 */ \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_INTEGER_FUNCTIONS_2_FEATURES_INTEL) \
\
/* VK_KHR_imageless_framebuffer */ \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR) \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR) \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO_KHR) \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR) \
\
/* VK_KHR_pipeline_executable_properties */ \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_EXECUTABLE_PROPERTIES_FEATURES_KHR) \
PNEXT_UNSUPPORTED(VK_STRUCTURE_TYPE_PIPELINE_INFO_KHR) \
@@ -4327,6 +4331,78 @@ void Deserialise(const VkImageFormatListCreateInfoKHR &el)
delete[] el.pViewFormats;
}
template <typename SerialiserType>
void DoSerialise(SerialiserType &ser, VkPhysicalDeviceImagelessFramebufferFeaturesKHR &el)
{
RDCASSERT(ser.IsReading() ||
el.sType == VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR);
SerialiseNext(ser, el.sType, el.pNext);
SERIALISE_MEMBER(imagelessFramebuffer);
}
template <>
void Deserialise(const VkPhysicalDeviceImagelessFramebufferFeaturesKHR &el)
{
DeserialiseNext(el.pNext);
}
template <typename SerialiserType>
void DoSerialise(SerialiserType &ser, VkFramebufferAttachmentsCreateInfoKHR &el)
{
RDCASSERT(ser.IsReading() || el.sType == VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR);
SerialiseNext(ser, el.sType, el.pNext);
SERIALISE_MEMBER(attachmentImageInfoCount);
SERIALISE_MEMBER_ARRAY(pAttachmentImageInfos, attachmentImageInfoCount);
}
template <>
void Deserialise(const VkFramebufferAttachmentsCreateInfoKHR &el)
{
DeserialiseNext(el.pNext);
delete[] el.pAttachmentImageInfos;
}
template <typename SerialiserType>
void DoSerialise(SerialiserType &ser, VkFramebufferAttachmentImageInfoKHR &el)
{
RDCASSERT(ser.IsReading() || el.sType == VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO_KHR);
SerialiseNext(ser, el.sType, el.pNext);
SERIALISE_MEMBER_VKFLAGS(VkImageCreateFlags, flags);
SERIALISE_MEMBER_VKFLAGS(VkImageUsageFlags, usage);
SERIALISE_MEMBER(width);
SERIALISE_MEMBER(height);
SERIALISE_MEMBER(layerCount);
SERIALISE_MEMBER(viewFormatCount);
SERIALISE_MEMBER_ARRAY(pViewFormats, viewFormatCount);
}
template <>
void Deserialise(const VkFramebufferAttachmentImageInfoKHR &el)
{
DeserialiseNext(el.pNext);
delete[] el.pViewFormats;
}
template <typename SerialiserType>
void DoSerialise(SerialiserType &ser, VkRenderPassAttachmentBeginInfoKHR &el)
{
RDCASSERT(ser.IsReading() || el.sType == VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
SerialiseNext(ser, el.sType, el.pNext);
SERIALISE_MEMBER(attachmentCount);
SERIALISE_MEMBER_ARRAY(pAttachments, attachmentCount);
}
template <>
void Deserialise(const VkRenderPassAttachmentBeginInfoKHR &el)
{
DeserialiseNext(el.pNext);
delete[] el.pAttachments;
}
template <typename SerialiserType>
void DoSerialise(SerialiserType &ser, VkRectLayerKHR &el)
{
@@ -6878,18 +6954,19 @@ INSTANTIATE_SERIALISE_TYPE(VkBindImageMemorySwapchainInfoKHR);
INSTANTIATE_SERIALISE_TYPE(VkBindImagePlaneMemoryInfo);
INSTANTIATE_SERIALISE_TYPE(VkBindSparseInfo);
INSTANTIATE_SERIALISE_TYPE(VkBufferCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkBufferDeviceAddressInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkBufferDeviceAddressCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkBufferDeviceAddressInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkBufferMemoryBarrier);
INSTANTIATE_SERIALISE_TYPE(VkBufferMemoryRequirementsInfo2);
INSTANTIATE_SERIALISE_TYPE(VkBufferViewCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkCalibratedTimestampInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkCommandBufferAllocateInfo);
INSTANTIATE_SERIALISE_TYPE(VkCommandBufferBeginInfo);
INSTANTIATE_SERIALISE_TYPE(VkCommandBufferInheritanceInfo);
INSTANTIATE_SERIALISE_TYPE(VkCommandBufferInheritanceConditionalRenderingInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkCommandBufferInheritanceInfo);
INSTANTIATE_SERIALISE_TYPE(VkCommandPoolCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkComputePipelineCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkConditionalRenderingBeginInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkCopyDescriptorSet);
INSTANTIATE_SERIALISE_TYPE(VkDebugMarkerMarkerInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkDebugMarkerObjectNameInfoEXT);
@@ -6948,6 +7025,8 @@ INSTANTIATE_SERIALISE_TYPE(VkExternalSemaphoreProperties);
INSTANTIATE_SERIALISE_TYPE(VkFenceCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkFenceGetFdInfoKHR);
INSTANTIATE_SERIALISE_TYPE(VkFormatProperties2);
INSTANTIATE_SERIALISE_TYPE(VkFramebufferAttachmentImageInfoKHR);
INSTANTIATE_SERIALISE_TYPE(VkFramebufferAttachmentsCreateInfoKHR);
INSTANTIATE_SERIALISE_TYPE(VkFramebufferCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkGraphicsPipelineCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkHdrMetadataEXT);
@@ -6957,8 +7036,8 @@ INSTANTIATE_SERIALISE_TYPE(VkImageFormatProperties2);
INSTANTIATE_SERIALISE_TYPE(VkImageMemoryBarrier);
INSTANTIATE_SERIALISE_TYPE(VkImageMemoryRequirementsInfo2);
INSTANTIATE_SERIALISE_TYPE(VkImagePlaneMemoryRequirementsInfo);
INSTANTIATE_SERIALISE_TYPE(VkImageStencilUsageCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkImageSparseMemoryRequirementsInfo2);
INSTANTIATE_SERIALISE_TYPE(VkImageStencilUsageCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkImageSwapchainCreateInfoKHR);
INSTANTIATE_SERIALISE_TYPE(VkImageViewASTCDecodeModeEXT);
INSTANTIATE_SERIALISE_TYPE(VkImageViewCreateInfo);
@@ -6986,8 +7065,8 @@ INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceASTCDecodeFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceBufferDeviceAddressFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceConditionalRenderingFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceConservativeRasterizationPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceDepthStencilResolvePropertiesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceDepthClipEnableFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceDepthStencilResolvePropertiesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceDescriptorIndexingFeaturesEXT)
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceDescriptorIndexingPropertiesEXT)
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceDiscardRectanglePropertiesEXT);
@@ -7004,6 +7083,7 @@ INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceGroupProperties);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceHostQueryResetFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceIDProperties);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceImageFormatInfo2);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceImagelessFramebufferFeaturesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceIndexTypeUint8FeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceMaintenance3Properties);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceMemoryBudgetPropertiesEXT);
@@ -7017,6 +7097,7 @@ INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceProperties2);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceProtectedMemoryFeatures);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceProtectedMemoryProperties);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDevicePushDescriptorPropertiesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSampleLocationsPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSamplerFilterMinmaxPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSamplerYcbcrConversionFeatures);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceScalarBlockLayoutFeaturesEXT);
@@ -7024,7 +7105,6 @@ INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceShaderAtomicInt64FeaturesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceShaderCorePropertiesAMD);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceShaderDemoteToHelperInvocationFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceShaderDrawParametersFeatures);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSampleLocationsPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSparseImageFormatInfo2);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSubgroupProperties);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceSurfaceInfo2KHR);
@@ -7032,15 +7112,15 @@ INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceTexelBufferAlignmentPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceTransformFeedbackFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceTransformFeedbackPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceUniformBufferStandardLayoutFeaturesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceVariablePointerFeatures);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceVertexAttributeDivisorFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceUniformBufferStandardLayoutFeaturesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceVulkanMemoryModelFeaturesKHR);
INSTANTIATE_SERIALISE_TYPE(VkPhysicalDeviceYcbcrImageArraysFeaturesEXT);
INSTANTIATE_SERIALISE_TYPE(VkPipelineCacheCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkPipelineCreationFeedbackCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkPipelineColorBlendStateCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkPipelineCreationFeedbackCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkPipelineDepthStencilStateCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkPipelineDiscardRectangleStateCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkPipelineDynamicStateCreateInfo);
@@ -7063,6 +7143,7 @@ INSTANTIATE_SERIALISE_TYPE(VkPresentRegionsKHR);
INSTANTIATE_SERIALISE_TYPE(VkProtectedSubmitInfo);
INSTANTIATE_SERIALISE_TYPE(VkQueryPoolCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkQueueFamilyProperties2);
INSTANTIATE_SERIALISE_TYPE(VkRenderPassAttachmentBeginInfoKHR);
INSTANTIATE_SERIALISE_TYPE(VkRenderPassBeginInfo);
INSTANTIATE_SERIALISE_TYPE(VkRenderPassCreateInfo);
INSTANTIATE_SERIALISE_TYPE(VkRenderPassCreateInfo2KHR);
@@ -7100,7 +7181,6 @@ INSTANTIATE_SERIALISE_TYPE(VkTextureLODGatherFormatPropertiesAMD);
INSTANTIATE_SERIALISE_TYPE(VkValidationCacheCreateInfoEXT);
INSTANTIATE_SERIALISE_TYPE(VkValidationFlagsEXT);
INSTANTIATE_SERIALISE_TYPE(VkWriteDescriptorSet);
INSTANTIATE_SERIALISE_TYPE(VkConditionalRenderingBeginInfoEXT);
// plain structs with no next chain
INSTANTIATE_SERIALISE_TYPE(VkAllocationCallbacks);
+42 -1
View File
@@ -68,15 +68,35 @@ void VulkanRenderState::BeginRenderPassAndApplyState(VkCommandBuffer cmd, Pipeli
RDCASSERT(ARRAY_COUNT(empty) >= m_CreationInfo->m_RenderPass[renderPass].attachments.size());
VulkanCreationInfo::Framebuffer fbinfo = m_CreationInfo->m_Framebuffer[framebuffer];
VkRenderPassBeginInfo rpbegin = {
VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO,
NULL,
Unwrap(m_CreationInfo->m_RenderPass[renderPass].loadRPs[subpass]),
Unwrap(m_CreationInfo->m_Framebuffer[framebuffer].loadFBs[subpass]),
Unwrap(fbinfo.loadFBs[subpass]),
renderArea,
(uint32_t)m_CreationInfo->m_RenderPass[renderPass].attachments.size(),
empty,
};
VkRenderPassAttachmentBeginInfoKHR imagelessAttachments = {
VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR,
};
std::vector<VkImageView> imagelessViews;
if(fbinfo.imageless)
{
rpbegin.pNext = &imagelessAttachments;
imagelessAttachments.attachmentCount = (uint32_t)fbattachments.size();
for(size_t i = 0; i < fbattachments.size(); i++)
imagelessViews.push_back(
Unwrap(GetResourceManager()->GetCurrentHandle<VkImageView>(fbattachments[i])));
imagelessAttachments.pAttachments = imagelessViews.data();
}
ObjDisp(cmd)->CmdBeginRenderPass(Unwrap(cmd), &rpbegin, VK_SUBPASS_CONTENTS_INLINE);
BindPipeline(cmd, binding, true);
@@ -540,6 +560,27 @@ void VulkanRenderState::BindDescriptorSet(const DescSetLayout &descLayout, VkCom
}
}
void VulkanRenderState::SetFramebuffer(ResourceId fb,
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo)
{
framebuffer = fb;
VulkanCreationInfo::Framebuffer fbinfo = m_CreationInfo->m_Framebuffer[fb];
fbattachments.resize(fbinfo.attachments.size());
if(!fbinfo.imageless)
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
fbattachments[i] = fbinfo.attachments[i].createdView;
}
else
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
fbattachments[i] = GetResID(attachmentsInfo->pAttachments[i]);
}
}
VulkanResourceManager *VulkanRenderState::GetResourceManager()
{
return m_pDriver->GetResourceManager();
+17 -1
View File
@@ -100,7 +100,19 @@ struct VulkanRenderState
ResourceId renderPass;
uint32_t subpass;
ResourceId framebuffer;
// framebuffer accessors - to allow for imageless framebuffers and prevent accidentally changing
// only the framebuffer without updating the attachments
void SetFramebuffer(ResourceId fb,
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo = NULL);
void SetFramebuffer(ResourceId fb, const std::vector<ResourceId> &dynamicAttachments)
{
framebuffer = fb;
fbattachments = dynamicAttachments;
}
ResourceId GetFramebuffer() const { return framebuffer; }
const std::vector<ResourceId> &GetFramebufferAttachments() const { return fbattachments; }
//
VkRect2D renderArea;
VulkanStatePipeline compute, graphics;
@@ -147,4 +159,8 @@ struct VulkanRenderState
VulkanResourceManager *GetResourceManager();
VulkanCreationInfo *m_CreationInfo;
WrappedVulkan *m_pDriver;
private:
ResourceId framebuffer;
std::vector<ResourceId> fbattachments;
};
+211 -56
View File
@@ -48,16 +48,19 @@ static std::string ToHumanStr(const VkAttachmentStoreOp &el)
std::vector<VkImageMemoryBarrier> WrappedVulkan::GetImplicitRenderPassBarriers(uint32_t subpass)
{
ResourceId rp, fb;
std::vector<ResourceId> fbattachments;
if(m_LastCmdBufferID == ResourceId())
{
rp = m_RenderState.renderPass;
fb = m_RenderState.framebuffer;
fb = m_RenderState.GetFramebuffer();
fbattachments = m_RenderState.GetFramebufferAttachments();
}
else
{
rp = m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass;
fb = m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer;
fbattachments = m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments;
}
std::vector<VkImageMemoryBarrier> ret;
@@ -138,7 +141,7 @@ std::vector<VkImageMemoryBarrier> WrappedVulkan::GetImplicitRenderPassBarriers(u
VkImageMemoryBarrier barrier = {VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER};
ResourceId view = fbinfo.attachments[idx].view;
ResourceId view = fbattachments[idx];
barrier.subresourceRange = m_CreationInfo.m_ImageView[view].range;
barrier.image = Unwrap(
@@ -252,7 +255,7 @@ std::string WrappedVulkan::MakeRenderPassOpString(bool store)
// component and if the subpass is depth only (no other attachments)
if(dsAttach >= 0)
{
hasStencil = !IsDepthOnlyFormat(fbinfo.attachments[dsAttach].format);
hasStencil = fbinfo.attachments[dsAttach].hasStencil;
depthonly = info.subpasses[subpass].colorAttachments.size() == 0;
}
@@ -1158,8 +1161,34 @@ bool WrappedVulkan::Serialise_vkCmdBeginRenderPass(SerialiserType &ser, VkComman
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.subpass = 0;
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass =
GetResID(RenderPassBegin.renderPass);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer =
GetResID(RenderPassBegin.framebuffer);
ResourceId fb = GetResID(RenderPassBegin.framebuffer);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer = fb;
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo =
(const VkRenderPassAttachmentBeginInfoKHR *)FindNextStruct(
&RenderPassBegin, VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
// set framebuffer attachments - by default from the ones used to create it, but if it is
// imageless then look for the attachments in our pNext chain
{
VulkanCreationInfo::Framebuffer fbinfo = m_CreationInfo.m_Framebuffer[fb];
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments.resize(
fbinfo.attachments.size());
if(!fbinfo.imageless)
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
fbinfo.attachments[i].createdView;
}
else
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
GetResID(attachmentsInfo->pAttachments[i]);
}
}
// only if we're partially recording do we update this state
if(ShouldUpdateRenderState(m_LastCmdBufferID, true))
@@ -1169,7 +1198,7 @@ bool WrappedVulkan::Serialise_vkCmdBeginRenderPass(SerialiserType &ser, VkComman
m_RenderState.subpass = 0;
m_RenderState.renderPass = GetResID(RenderPassBegin.renderPass);
m_RenderState.framebuffer = GetResID(RenderPassBegin.framebuffer);
m_RenderState.SetFramebuffer(GetResID(RenderPassBegin.framebuffer), attachmentsInfo);
m_RenderState.renderArea = RenderPassBegin.renderArea;
}
@@ -1189,8 +1218,33 @@ bool WrappedVulkan::Serialise_vkCmdBeginRenderPass(SerialiserType &ser, VkComman
// track while reading, for fetching the right set of outputs in AddDrawcall
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.subpass = 0;
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass = GetResID(RenderPassBegin.renderPass);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer =
GetResID(RenderPassBegin.framebuffer);
ResourceId fb = GetResID(RenderPassBegin.framebuffer);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer = fb;
// set framebuffer attachments - by default from the ones used to create it, but if it is
// imageless then look for the attachments in our pNext chain
{
VulkanCreationInfo::Framebuffer fbinfo = m_CreationInfo.m_Framebuffer[fb];
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments.resize(fbinfo.attachments.size());
if(!fbinfo.imageless)
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
fbinfo.attachments[i].createdView;
}
else
{
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo =
(const VkRenderPassAttachmentBeginInfoKHR *)FindNextStruct(
&RenderPassBegin, VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
GetResID(attachmentsInfo->pAttachments[i]);
}
}
std::vector<VkImageMemoryBarrier> imgBarriers = GetImplicitRenderPassBarriers();
@@ -1243,13 +1297,49 @@ void WrappedVulkan::vkCmdBeginRenderPass(VkCommandBuffer commandBuffer,
VkResourceRecord *fb = GetRecord(pRenderPassBegin->framebuffer);
record->MarkResourceFrameReferenced(fb->GetResourceID(), eFrameRef_Read);
for(size_t i = 0; fb->imageAttachments[i].barrier.sType; i++)
{
VkResourceRecord *att = fb->imageAttachments[i].record;
if(att == NULL)
break;
record->MarkImageViewFrameReferenced(att, ImageRange(), eFrameRef_ReadBeforeWrite);
std::vector<VkImageMemoryBarrier> &barriers = record->cmdInfo->rpbarriers;
barriers.clear();
if(fb->imageAttachments[0].barrier.sType && fb->imageAttachments[0].record)
{
for(size_t i = 0; fb->imageAttachments[i].barrier.sType; i++)
{
VkResourceRecord *att = fb->imageAttachments[i].record;
if(att == NULL)
break;
record->MarkImageViewFrameReferenced(att, ImageRange(), eFrameRef_ReadBeforeWrite);
if(fb->imageAttachments[i].barrier.oldLayout != fb->imageAttachments[i].barrier.newLayout)
barriers.push_back(fb->imageAttachments[i].barrier);
}
}
else if(fb->imageAttachments[0].barrier.sType)
{
// if we have attachments but the framebuffer doesn't have images, then it's imageless. Look
// for the image records now
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo =
(const VkRenderPassAttachmentBeginInfoKHR *)FindNextStruct(
pRenderPassBegin, VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
for(uint32_t i = 0; i < attachmentsInfo->attachmentCount; i++)
{
VkResourceRecord *att = GetRecord(attachmentsInfo->pAttachments[i]);
record->MarkImageViewFrameReferenced(att, ImageRange(), eFrameRef_ReadBeforeWrite);
if(fb->imageAttachments[i].barrier.oldLayout != fb->imageAttachments[i].barrier.newLayout)
{
VkImageMemoryBarrier barrier = fb->imageAttachments[i].barrier;
barrier.image = GetResourceManager()->GetCurrentHandle<VkImage>(att->baseResource);
barrier.subresourceRange = att->viewRange;
barriers.push_back(barrier);
}
}
}
record->cmdInfo->framebuffer = fb;
@@ -1363,6 +1453,7 @@ bool WrappedVulkan::Serialise_vkCmdEndRenderPass(SerialiserType &ser, VkCommandB
// always track this, for WrappedVulkan::IsDrawInRenderPass()
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass = ResourceId();
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer = ResourceId();
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments.clear();
if(ShouldUpdateRenderState(m_LastCmdBufferID, true))
{
@@ -1404,6 +1495,7 @@ bool WrappedVulkan::Serialise_vkCmdEndRenderPass(SerialiserType &ser, VkCommandB
// but only AFTER the above AddDrawcall (we want it grouped together)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass = ResourceId();
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer = ResourceId();
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments.clear();
}
}
@@ -1427,17 +1519,7 @@ void WrappedVulkan::vkCmdEndRenderPass(VkCommandBuffer commandBuffer)
record->AddChunk(scope.Get());
VkResourceRecord *fb = record->cmdInfo->framebuffer;
std::vector<VkImageMemoryBarrier> barriers;
for(size_t i = 0; fb->imageAttachments[i].barrier.sType; i++)
{
if(fb->imageAttachments[i].barrier.oldLayout == fb->imageAttachments[i].barrier.newLayout)
continue;
barriers.push_back(fb->imageAttachments[i].barrier);
}
const std::vector<VkImageMemoryBarrier> &barriers = record->cmdInfo->rpbarriers;
// apply the implicit layout transitions here
{
@@ -1490,8 +1572,34 @@ bool WrappedVulkan::Serialise_vkCmdBeginRenderPass2KHR(SerialiserType &ser,
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.subpass = 0;
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass =
GetResID(RenderPassBegin.renderPass);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer =
GetResID(RenderPassBegin.framebuffer);
ResourceId fb = GetResID(RenderPassBegin.framebuffer);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer = fb;
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo =
(const VkRenderPassAttachmentBeginInfoKHR *)FindNextStruct(
&RenderPassBegin, VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
// set framebuffer attachments - by default from the ones used to create it, but if it is
// imageless then look for the attachments in our pNext chain
{
VulkanCreationInfo::Framebuffer fbinfo = m_CreationInfo.m_Framebuffer[fb];
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments.resize(
fbinfo.attachments.size());
if(!fbinfo.imageless)
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
fbinfo.attachments[i].createdView;
}
else
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
GetResID(attachmentsInfo->pAttachments[i]);
}
}
// only if we're partially recording do we update this state
if(ShouldUpdateRenderState(m_LastCmdBufferID, true))
@@ -1501,7 +1609,7 @@ bool WrappedVulkan::Serialise_vkCmdBeginRenderPass2KHR(SerialiserType &ser,
m_RenderState.subpass = 0;
m_RenderState.renderPass = GetResID(RenderPassBegin.renderPass);
m_RenderState.framebuffer = GetResID(RenderPassBegin.framebuffer);
m_RenderState.SetFramebuffer(GetResID(RenderPassBegin.framebuffer), attachmentsInfo);
m_RenderState.renderArea = RenderPassBegin.renderArea;
}
@@ -1523,8 +1631,33 @@ bool WrappedVulkan::Serialise_vkCmdBeginRenderPass2KHR(SerialiserType &ser,
// track while reading, for fetching the right set of outputs in AddDrawcall
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.subpass = 0;
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.renderPass = GetResID(RenderPassBegin.renderPass);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer =
GetResID(RenderPassBegin.framebuffer);
ResourceId fb = GetResID(RenderPassBegin.framebuffer);
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.framebuffer = fb;
// set framebuffer attachments - by default from the ones used to create it, but if it is
// imageless then look for the attachments in our pNext chain
{
VulkanCreationInfo::Framebuffer fbinfo = m_CreationInfo.m_Framebuffer[fb];
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments.resize(fbinfo.attachments.size());
if(!fbinfo.imageless)
{
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
fbinfo.attachments[i].createdView;
}
else
{
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo =
(const VkRenderPassAttachmentBeginInfoKHR *)FindNextStruct(
&RenderPassBegin, VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
for(size_t i = 0; i < fbinfo.attachments.size(); i++)
m_BakedCmdBufferInfo[m_LastCmdBufferID].state.fbattachments[i] =
GetResID(attachmentsInfo->pAttachments[i]);
}
}
std::vector<VkImageMemoryBarrier> imgBarriers = GetImplicitRenderPassBarriers();
@@ -1583,18 +1716,49 @@ void WrappedVulkan::vkCmdBeginRenderPass2KHR(VkCommandBuffer commandBuffer,
VkResourceRecord *fb = GetRecord(pRenderPassBegin->framebuffer);
record->MarkResourceFrameReferenced(fb->GetResourceID(), eFrameRef_Read);
for(size_t i = 0; fb->imageAttachments[i].barrier.sType; i++)
{
VkResourceRecord *att = fb->imageAttachments[i].record;
if(att == NULL)
break;
record->MarkResourceFrameReferenced(att->baseResource, eFrameRef_ReadBeforeWrite);
if(att->baseResourceMem != ResourceId())
record->MarkResourceFrameReferenced(att->baseResourceMem, eFrameRef_Read);
if(att->resInfo && att->resInfo->IsSparse())
record->cmdInfo->sparse.insert(att->resInfo);
record->cmdInfo->dirtied.insert(att->baseResource);
std::vector<VkImageMemoryBarrier> &barriers = record->cmdInfo->rpbarriers;
barriers.clear();
if(fb->imageAttachments[0].barrier.sType && fb->imageAttachments[0].record)
{
for(size_t i = 0; fb->imageAttachments[i].barrier.sType; i++)
{
VkResourceRecord *att = fb->imageAttachments[i].record;
if(att == NULL)
break;
record->MarkImageViewFrameReferenced(att, ImageRange(), eFrameRef_ReadBeforeWrite);
if(fb->imageAttachments[i].barrier.oldLayout != fb->imageAttachments[i].barrier.newLayout)
barriers.push_back(fb->imageAttachments[i].barrier);
}
}
else
{
// if we have attachments but the framebuffer doesn't have images, then it's imageless. Look
// for the image records now
const VkRenderPassAttachmentBeginInfoKHR *attachmentsInfo =
(const VkRenderPassAttachmentBeginInfoKHR *)FindNextStruct(
pRenderPassBegin, VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR);
for(uint32_t i = 0; i < attachmentsInfo->attachmentCount; i++)
{
VkResourceRecord *att = GetRecord(attachmentsInfo->pAttachments[i]);
record->MarkImageViewFrameReferenced(att, ImageRange(), eFrameRef_ReadBeforeWrite);
if(fb->imageAttachments[i].barrier.oldLayout != fb->imageAttachments[i].barrier.newLayout)
{
VkImageMemoryBarrier barrier = fb->imageAttachments[i].barrier;
barrier.image = GetResourceManager()->GetCurrentHandle<VkImage>(att->baseResource);
barrier.subresourceRange = att->viewRange;
barriers.push_back(barrier);
}
}
}
record->cmdInfo->framebuffer = fb;
@@ -1811,17 +1975,7 @@ void WrappedVulkan::vkCmdEndRenderPass2KHR(VkCommandBuffer commandBuffer,
record->AddChunk(scope.Get());
VkResourceRecord *fb = record->cmdInfo->framebuffer;
std::vector<VkImageMemoryBarrier> barriers;
for(size_t i = 0; fb->imageAttachments[i].barrier.sType; i++)
{
if(fb->imageAttachments[i].barrier.oldLayout == fb->imageAttachments[i].barrier.newLayout)
continue;
barriers.push_back(fb->imageAttachments[i].barrier);
}
const std::vector<VkImageMemoryBarrier> &barriers = record->cmdInfo->rpbarriers;
// apply the implicit layout transitions here
{
@@ -3079,10 +3233,10 @@ bool WrappedVulkan::Serialise_vkCmdExecuteCommands(SerialiserType &ser, VkComman
// primary command buffer's state
for(size_t i = 0; i < numChildren; i++)
{
AddFramebufferUsageAllChildren(parentCmdBufInfo.draw->children[total - numChildren + i],
parentCmdBufInfo.state.renderPass,
parentCmdBufInfo.state.framebuffer,
parentCmdBufInfo.state.subpass);
AddFramebufferUsageAllChildren(
parentCmdBufInfo.draw->children[total - numChildren + i],
parentCmdBufInfo.state.renderPass, parentCmdBufInfo.state.framebuffer,
parentCmdBufInfo.state.subpass, parentCmdBufInfo.state.fbattachments);
}
}
@@ -3150,6 +3304,7 @@ bool WrappedVulkan::Serialise_vkCmdExecuteCommands(SerialiserType &ser, VkComman
m_BakedCmdBufferInfo[cmd].state.renderPass = parentCmdBufInfo.state.renderPass;
m_BakedCmdBufferInfo[cmd].state.subpass = parentCmdBufInfo.state.subpass;
m_BakedCmdBufferInfo[cmd].state.framebuffer = parentCmdBufInfo.state.framebuffer;
m_BakedCmdBufferInfo[cmd].state.fbattachments = parentCmdBufInfo.state.fbattachments;
// propagate conditional rendering
if(m_BakedCmdBufferInfo[cmd].inheritConditionalRendering &&
@@ -2112,6 +2112,13 @@ bool WrappedVulkan::Serialise_vkCreateDevice(SerialiserType &ser, VkPhysicalDevi
CHECK_PHYS_EXT_FEATURE(indexTypeUint8);
}
END_PHYS_EXT_CHECK();
BEGIN_PHYS_EXT_CHECK(VkPhysicalDeviceImagelessFramebufferFeaturesKHR,
VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR);
{
CHECK_PHYS_EXT_FEATURE(imagelessFramebuffer);
}
END_PHYS_EXT_CHECK();
}
if(availFeatures.depthClamp)
@@ -2334,7 +2334,6 @@ bool WrappedVulkan::Serialise_vkCmdClearAttachments(SerialiserType &ser,
if(state.renderPass != ResourceId() && state.framebuffer != ResourceId())
{
VulkanCreationInfo::RenderPass &rp = m_CreationInfo.m_RenderPass[state.renderPass];
VulkanCreationInfo::Framebuffer &fb = m_CreationInfo.m_Framebuffer[state.framebuffer];
RDCASSERT(state.subpass < rp.subpasses.size());
@@ -2348,9 +2347,9 @@ bool WrappedVulkan::Serialise_vkCmdClearAttachments(SerialiserType &ser,
{
att = rp.subpasses[state.subpass].colorAttachments[att];
drawNode.resourceUsage.push_back(
make_rdcpair(m_CreationInfo.m_ImageView[fb.attachments[att].view].image,
make_rdcpair(m_CreationInfo.m_ImageView[state.fbattachments[att]].image,
EventUsage(drawNode.draw.eventId, ResourceUsage::Clear,
fb.attachments[att].view)));
state.fbattachments[att])));
}
}
else if(pAttachments[a].aspectMask & VK_IMAGE_ASPECT_DEPTH_BIT)
@@ -2359,9 +2358,9 @@ bool WrappedVulkan::Serialise_vkCmdClearAttachments(SerialiserType &ser,
{
att = (uint32_t)rp.subpasses[state.subpass].depthstencilAttachment;
drawNode.resourceUsage.push_back(
make_rdcpair(m_CreationInfo.m_ImageView[fb.attachments[att].view].image,
make_rdcpair(m_CreationInfo.m_ImageView[state.fbattachments[att]].image,
EventUsage(drawNode.draw.eventId, ResourceUsage::Clear,
fb.attachments[att].view)));
state.fbattachments[att])));
}
}
}
@@ -75,12 +75,15 @@ VkFramebufferCreateInfo WrappedVulkan::UnwrapInfo(const VkFramebufferCreateInfo
{
VkFramebufferCreateInfo ret = *info;
VkImageView *unwrapped = GetTempArray<VkImageView>(info->attachmentCount);
for(uint32_t i = 0; i < info->attachmentCount; i++)
unwrapped[i] = Unwrap(info->pAttachments[i]);
if((ret.flags & VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT_KHR) == 0)
{
VkImageView *unwrapped = GetTempArray<VkImageView>(info->attachmentCount);
for(uint32_t i = 0; i < info->attachmentCount; i++)
unwrapped[i] = Unwrap(info->pAttachments[i]);
ret.pAttachments = unwrapped;
}
ret.renderPass = Unwrap(ret.renderPass);
ret.pAttachments = unwrapped;
return ret;
}
@@ -677,14 +680,18 @@ VkResult WrappedVulkan::vkCreateFramebuffer(VkDevice device,
for(uint32_t i = 0; i < pCreateInfo->attachmentCount; i++)
{
VkResourceRecord *attRecord = GetRecord(pCreateInfo->pAttachments[i]);
record->AddParent(attRecord);
record->imageAttachments[i].record = attRecord;
record->imageAttachments[i].barrier = rpRecord->imageAttachments[i].barrier;
record->imageAttachments[i].barrier.image =
GetResourceManager()->GetCurrentHandle<VkImage>(attRecord->baseResource);
record->imageAttachments[i].barrier.subresourceRange = attRecord->viewRange;
if((pCreateInfo->flags & VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT_KHR) == 0)
{
VkResourceRecord *attRecord = GetRecord(pCreateInfo->pAttachments[i]);
record->AddParent(attRecord);
record->imageAttachments[i].record = attRecord;
record->imageAttachments[i].barrier.image =
GetResourceManager()->GetCurrentHandle<VkImage>(attRecord->baseResource);
record->imageAttachments[i].barrier.subresourceRange = attRecord->viewRange;
}
}
}
else
+1
View File
@@ -13,6 +13,7 @@ set(VULKAN_SRC
vk/vk_discard_rects.cpp
vk/vk_draw_zoo.cpp
vk/vk_image_layouts.cpp
vk/vk_imageless_framebuffer.cpp
vk/vk_indirect.cpp
vk/vk_int8_ibuffer.cpp
vk/vk_multi_thread_windows.cpp
+1
View File
@@ -208,6 +208,7 @@
<ClCompile Include="3rdparty\lz4\lz4.c" />
<ClCompile Include="main.cpp" />
<ClCompile Include="test_common.cpp" />
<ClCompile Include="vk\vk_imageless_framebuffer.cpp" />
<ClCompile Include="vk\vk_image_layouts.cpp" />
<ClCompile Include="vk\vk_int8_ibuffer.cpp" />
<ClCompile Include="vk\vk_multi_thread_windows.cpp" />
+3
View File
@@ -312,6 +312,9 @@
<ClCompile Include="vk\vk_int8_ibuffer.cpp">
<Filter>Vulkan\demos</Filter>
</ClCompile>
<ClCompile Include="vk\vk_imageless_framebuffer.cpp">
<Filter>Vulkan\demos</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<Filter Include="D3D11">
+8 -2
View File
@@ -657,11 +657,11 @@ struct AttachmentDescription : public VkAttachmentDescription
struct FramebufferCreateInfo : public VkFramebufferCreateInfo
{
FramebufferCreateInfo(VkRenderPass renderPass, const std::vector<VkImageView> &attachments,
VkExtent2D extent, uint32_t layers = 1)
VkExtent2D extent, uint32_t layers = 1, VkFramebufferCreateFlags flags = 0)
{
sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO;
pNext = NULL;
this->flags = 0;
this->flags = flags;
this->renderPass = renderPass;
this->attachmentCount = (uint32_t)attachments.size();
this->pAttachments = attachments.data();
@@ -670,6 +670,12 @@ struct FramebufferCreateInfo : public VkFramebufferCreateInfo
this->layers = layers;
}
FramebufferCreateInfo &next(const void *next)
{
this->pNext = next;
return *this;
}
operator const VkFramebufferCreateInfo *() const { return this; }
};
@@ -0,0 +1,213 @@
/******************************************************************************
* The MIT License (MIT)
*
* Copyright (c) 2018-2019 Baldur Karlsson
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
******************************************************************************/
#include "vk_test.h"
TEST(VK_Imageless_Framebuffer, VulkanGraphicsTest)
{
static constexpr const char *Description =
"Test using VK_KHR_imageless_framebuffer to specify image views at the last second";
std::string common = R"EOSHADER(
#version 420 core
struct v2f
{
vec4 pos;
vec4 col;
vec4 uv;
};
)EOSHADER";
const std::string vertex = R"EOSHADER(
layout(location = 0) in vec3 Position;
layout(location = 1) in vec4 Color;
layout(location = 2) in vec2 UV;
layout(location = 0) out v2f vertOut;
void main()
{
vertOut.pos = vec4(Position.xyz*vec3(1,-1,1), 1);
gl_Position = vertOut.pos;
vertOut.col = Color;
vertOut.uv = vec4(UV.xy, 0, 1);
}
)EOSHADER";
const std::string pixel = R"EOSHADER(
layout(location = 0) in v2f vertIn;
layout(location = 0, index = 0) out vec4 Color;
void main()
{
Color = vec4(1, 0, 0, 1);
}
)EOSHADER";
void Prepare(int argc, char **argv)
{
devExts.push_back(VK_KHR_IMAGELESS_FRAMEBUFFER_EXTENSION_NAME);
// dependencies of VK_EXT_descriptor_indexing
devExts.push_back(VK_KHR_MAINTENANCE2_EXTENSION_NAME);
devExts.push_back(VK_KHR_IMAGE_FORMAT_LIST_EXTENSION_NAME);
VulkanGraphicsTest::Prepare(argc, argv);
if(!Avail.empty())
return;
static VkPhysicalDeviceImagelessFramebufferFeaturesKHR imageless = {
VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES_KHR,
};
getPhysFeatures2(&imageless);
if(!imageless.imagelessFramebuffer)
Avail = "feature 'imagelessFramebuffer' not available";
devInfoNext = &imageless;
}
int main()
{
// initialise, create window, create context, etc
if(!Init())
return 3;
VkPipelineLayout layout = createPipelineLayout(vkh::PipelineLayoutCreateInfo());
vkh::GraphicsPipelineCreateInfo pipeCreateInfo;
pipeCreateInfo.layout = layout;
pipeCreateInfo.renderPass = mainWindow->rp;
pipeCreateInfo.vertexInputState.vertexBindingDescriptions = {vkh::vertexBind(0, DefaultA2V)};
pipeCreateInfo.vertexInputState.vertexAttributeDescriptions = {
vkh::vertexAttr(0, 0, DefaultA2V, pos), vkh::vertexAttr(1, 0, DefaultA2V, col),
vkh::vertexAttr(2, 0, DefaultA2V, uv),
};
pipeCreateInfo.stages = {
CompileShaderModule(common + vertex, ShaderLang::glsl, ShaderStage::vert, "main"),
CompileShaderModule(common + pixel, ShaderLang::glsl, ShaderStage::frag, "main"),
};
VkPipeline pipe = createGraphicsPipeline(pipeCreateInfo);
AllocatedBuffer vb(
allocator, vkh::BufferCreateInfo(sizeof(DefaultTri), VK_BUFFER_USAGE_VERTEX_BUFFER_BIT |
VK_BUFFER_USAGE_TRANSFER_DST_BIT),
VmaAllocationCreateInfo({0, VMA_MEMORY_USAGE_CPU_TO_GPU}));
vb.upload(DefaultTri);
int lastWidth = -1;
VkFramebuffer fb = VK_NULL_HANDLE;
while(Running())
{
if(lastWidth != (int)mainWindow->scissor.extent.width)
{
lastWidth = (int)mainWindow->scissor.extent.width;
if(fb != VK_NULL_HANDLE)
{
// be lazy, hard sync
vkDeviceWaitIdle(device);
vkDestroyFramebuffer(device, fb, NULL);
}
VkFramebufferAttachmentImageInfoKHR imageInfo = {
VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENT_IMAGE_INFO_KHR,
};
imageInfo.width = mainWindow->scissor.extent.width;
imageInfo.height = mainWindow->scissor.extent.height;
imageInfo.layerCount = 1;
imageInfo.usage = VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT;
imageInfo.viewFormatCount = 1;
imageInfo.pViewFormats = &mainWindow->format;
VkFramebufferAttachmentsCreateInfoKHR viewsInfo = {
VK_STRUCTURE_TYPE_FRAMEBUFFER_ATTACHMENTS_CREATE_INFO_KHR, NULL, 1, &imageInfo,
};
CHECK_VKR(vkCreateFramebuffer(
device,
vkh::FramebufferCreateInfo(mainWindow->rp, {VK_NULL_HANDLE}, mainWindow->scissor.extent,
1, VK_FRAMEBUFFER_CREATE_IMAGELESS_BIT_KHR)
.next(&viewsInfo),
NULL, &fb));
}
VkCommandBuffer cmd = GetCommandBuffer();
vkBeginCommandBuffer(cmd, vkh::CommandBufferBeginInfo());
VkImage swapimg =
StartUsingBackbuffer(cmd, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_GENERAL);
vkCmdClearColorImage(cmd, swapimg, VK_IMAGE_LAYOUT_GENERAL,
vkh::ClearColorValue(0.4f, 0.5f, 0.6f, 1.0f), 1,
vkh::ImageSubresourceRange());
VkImageView curView = mainWindow->GetView();
VkRenderPassAttachmentBeginInfoKHR usedView = {
VK_STRUCTURE_TYPE_RENDER_PASS_ATTACHMENT_BEGIN_INFO_KHR, NULL, 1, &curView,
};
vkCmdBeginRenderPass(
cmd, vkh::RenderPassBeginInfo(mainWindow->rp, fb, mainWindow->scissor).next(&usedView),
VK_SUBPASS_CONTENTS_INLINE);
vkCmdBindPipeline(cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, pipe);
vkCmdSetViewport(cmd, 0, 1, &mainWindow->viewport);
vkCmdSetScissor(cmd, 0, 1, &mainWindow->scissor);
vkh::cmdBindVertexBuffers(cmd, 0, {vb.buffer}, {0});
vkCmdDraw(cmd, 3, 1, 0, 0);
vkCmdEndRenderPass(cmd);
FinishUsingBackbuffer(cmd, VK_ACCESS_TRANSFER_WRITE_BIT, VK_IMAGE_LAYOUT_GENERAL);
vkEndCommandBuffer(cmd);
Submit(0, 1, {cmd});
Present();
}
return 0;
}
};
REGISTER_TEST();
@@ -0,0 +1,34 @@
import renderdoc as rd
import rdtest
class VK_Imageless_Framebuffer(rdtest.TestCase):
demos_test_name = 'VK_Imageless_Framebuffer'
def check_capture(self):
draw = self.find_draw("Draw")
self.check(draw is not None)
self.controller.SetFrameEvent(draw.eventId, False)
# Make an output so we can pick pixels
out: rd.ReplayOutput = self.controller.CreateOutput(rd.CreateHeadlessWindowingData(100, 100), rd.ReplayOutputType.Texture)
pipe: rd.PipeState = self.controller.GetPipelineState()
tex = rd.TextureDisplay()
tex.resourceId = pipe.GetOutputTargets()[0].resourceId
out.SetTextureDisplay(tex)
texdetails = self.get_texture(tex.resourceId)
picked: rd.PixelValue = out.PickPixel(tex.resourceId, False,
int(texdetails.width / 2), int(texdetails.height / 2), 0, 0, 0)
if not rdtest.value_compare(picked.floatValue, [1.0, 0.0, 0.0, 1.0]):
raise rdtest.TestFailureException("Picked value {} doesn't match expectation".format(picked.floatValue))
rdtest.log.success("picked value is as expected")
out.Shutdown()