From 56fada132c314a77bb546d666c47d385ae30e7d8 Mon Sep 17 00:00:00 2001 From: ziga-lunarg Date: Fri, 30 Aug 2024 01:16:08 +0200 Subject: [PATCH] Track external android format The external format from android must be tracked, because in GetImageResourceSizesOptimal we create temporary images from the same format to calculate the resource size If format is VK_FORMAT_UNDEFINED and the external android format is not provided it will crash on android --- framework/decode/vulkan_object_info.h | 2 ++ framework/decode/vulkan_replay_consumer_base.cpp | 7 +++++++ .../decode/vulkan_replay_dump_resources_common.cpp | 1 + framework/encode/vulkan_handle_wrappers.h | 2 ++ framework/encode/vulkan_state_tracker_initializers.h | 11 +++++++++++ framework/encode/vulkan_state_writer.cpp | 2 ++ framework/graphics/vulkan_resources_util.cpp | 9 ++++++++- framework/graphics/vulkan_resources_util.h | 2 ++ 8 files changed, 35 insertions(+), 1 deletion(-) diff --git a/framework/decode/vulkan_object_info.h b/framework/decode/vulkan_object_info.h index c6995b143c..c983cc077e 100644 --- a/framework/decode/vulkan_object_info.h +++ b/framework/decode/vulkan_object_info.h @@ -358,6 +358,8 @@ struct ImageInfo : public VulkanObjectInfo VkImageUsageFlags usage{ 0 }; VkImageType type{}; VkFormat format{}; + // VkExternalFormatANDROID + uint64_t external_format{ 0 }; VkExtent3D extent{ 0, 0, 0 }; VkImageTiling tiling{}; VkSampleCountFlagBits sample_count{}; diff --git a/framework/decode/vulkan_replay_consumer_base.cpp b/framework/decode/vulkan_replay_consumer_base.cpp index e7335b0aaf..3e7a641074 100644 --- a/framework/decode/vulkan_replay_consumer_base.cpp +++ b/framework/decode/vulkan_replay_consumer_base.cpp @@ -4921,6 +4921,13 @@ VulkanReplayConsumerBase::OverrideCreateImage(PFN_vkCreateImage { image_info->queue_family_index = 0; } + + auto external_format_android = graphics::GetPNextStruct( + replay_create_info, VK_STRUCTURE_TYPE_EXTERNAL_FORMAT_ANDROID); + if (external_format_android) + { + image_info->external_format = external_format_android->externalFormat; + } } return result; diff --git a/framework/decode/vulkan_replay_dump_resources_common.cpp b/framework/decode/vulkan_replay_dump_resources_common.cpp index b38bb245f0..e42c8f6887 100644 --- a/framework/decode/vulkan_replay_dump_resources_common.cpp +++ b/framework/decode/vulkan_replay_dump_resources_common.cpp @@ -490,6 +490,7 @@ VkResult DumpImageToFile(const ImageInfo* image_info, VkResult res = resource_util.ReadFromImageResourceStaging( image_info->handle, image_info->format, + image_info->external_format, image_info->type, extent, image_info->level_count, diff --git a/framework/encode/vulkan_handle_wrappers.h b/framework/encode/vulkan_handle_wrappers.h index 1f8b1f6dac..fc1112e2e2 100644 --- a/framework/encode/vulkan_handle_wrappers.h +++ b/framework/encode/vulkan_handle_wrappers.h @@ -211,6 +211,8 @@ struct ImageWrapper : public HandleWrapper uint32_t queue_family_index{ 0 }; VkImageType image_type{ VK_IMAGE_TYPE_2D }; VkFormat format{ VK_FORMAT_UNDEFINED }; + // VkExternalFormatANDROID + uint64_t external_format{ 0 }; VkExtent3D extent{ 0, 0, 0 }; uint32_t mip_levels{ 0 }; uint32_t array_layers{ 0 }; diff --git a/framework/encode/vulkan_state_tracker_initializers.h b/framework/encode/vulkan_state_tracker_initializers.h index 4cead850f9..daa60ede57 100644 --- a/framework/encode/vulkan_state_tracker_initializers.h +++ b/framework/encode/vulkan_state_tracker_initializers.h @@ -648,6 +648,17 @@ inline void InitializeStatequeue_family_index = create_info->pQueueFamilyIndices[0]; } + + auto next = reinterpret_cast(create_info->pNext); + while (next) + { + if (next->sType == VK_STRUCTURE_TYPE_EXTERNAL_FORMAT_ANDROID) + { + auto external_format_android = reinterpret_cast(next); + wrapper->external_format = external_format_android->externalFormat; + } + next = next->pNext; + } } template <> diff --git a/framework/encode/vulkan_state_writer.cpp b/framework/encode/vulkan_state_writer.cpp index e558905127..3f243de2be 100644 --- a/framework/encode/vulkan_state_writer.cpp +++ b/framework/encode/vulkan_state_writer.cpp @@ -1415,6 +1415,7 @@ void VulkanStateWriter::ProcessImageMemory(const vulkan_wrappers::DeviceWrapper* VkResult result = resource_util.ReadFromImageResourceStaging(image_wrapper->handle, image_wrapper->format, + image_wrapper->external_format, image_wrapper->image_type, image_wrapper->extent, image_wrapper->mip_levels, @@ -1731,6 +1732,7 @@ void VulkanStateWriter::WriteImageMemoryState(const VulkanStateTable& state_tabl snapshot_info.resource_size = resource_util.GetImageResourceSizesOptimal(wrapper->handle, wrapper->format, + wrapper->external_format, wrapper->image_type, wrapper->extent, wrapper->mip_levels, diff --git a/framework/graphics/vulkan_resources_util.cpp b/framework/graphics/vulkan_resources_util.cpp index 7bd1ba3a66..891dd81192 100644 --- a/framework/graphics/vulkan_resources_util.cpp +++ b/framework/graphics/vulkan_resources_util.cpp @@ -297,6 +297,7 @@ bool FindMemoryTypeIndex(const VkPhysicalDeviceMemoryProperties& memory_properti uint64_t VulkanResourcesUtil::GetImageResourceSizesOptimal(VkImage image, VkFormat format, + uint64_t external_format, VkImageType type, const VkExtent3D& extent, uint32_t mip_levels, @@ -321,8 +322,12 @@ uint64_t VulkanResourcesUtil::GetImageResourceSizesOptimal(VkImage uint64_t resource_size = 0; + VkExternalFormatANDROID external_format_android = { VK_STRUCTURE_TYPE_EXTERNAL_FORMAT_ANDROID }; + external_format_android.pNext = nullptr; + external_format_android.externalFormat = external_format; + VkImageCreateInfo create_info = { VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO }; - create_info.pNext = nullptr; + create_info.pNext = (external_format != 0) ? &external_format_android : nullptr; create_info.flags = 0; create_info.imageType = type; create_info.format = GetImageAspectFormat(format, aspect); @@ -1137,6 +1142,7 @@ VkResult VulkanResourcesUtil::ResolveImage(VkImage image, VkResult VulkanResourcesUtil::ReadFromImageResourceStaging(VkImage image, VkFormat format, + uint64_t external_format, VkImageType type, const VkExtent3D& extent, uint32_t mip_levels, @@ -1176,6 +1182,7 @@ VkResult VulkanResourcesUtil::ReadFromImageResourceStaging(VkImage resource_size = GetImageResourceSizesOptimal(image, format, + external_format, type, scaled_extent, mip_levels, diff --git a/framework/graphics/vulkan_resources_util.h b/framework/graphics/vulkan_resources_util.h index a0a2fad793..28dd124806 100644 --- a/framework/graphics/vulkan_resources_util.h +++ b/framework/graphics/vulkan_resources_util.h @@ -83,6 +83,7 @@ class VulkanResourcesUtil // Return value is the total size of the image. uint64_t GetImageResourceSizesOptimal(VkImage image, VkFormat format, + uint64_t external_format, VkImageType type, const VkExtent3D& extent, uint32_t mip_levels, @@ -100,6 +101,7 @@ class VulkanResourcesUtil // GetImageResourceSizesOptimal() VkResult ReadFromImageResourceStaging(VkImage image, VkFormat format, + uint64_t external_format, VkImageType type, const VkExtent3D& extent, uint32_t mip_levels,