From e057694a4f34b617452e6d35970d4154ad969bf5 Mon Sep 17 00:00:00 2001 From: wildcard Date: Tue, 26 Aug 2025 16:09:48 +0200 Subject: [PATCH] [Vulkan][TextureCache] Always use identity-swizzled views for storage images Validation flagged writes to a VK_DESCRIPTOR_TYPE_STORAGE_IMAGE descriptor because the bound VkImageView had a non-identity component mapping and hence the vuid-00336 error, this fixes the said error. --- .../renderer_vulkan/vk_texture_cache.cpp | 32 +++++++++++++------ 1 file changed, 23 insertions(+), 9 deletions(-) diff --git a/src/video_core/renderer_vulkan/vk_texture_cache.cpp b/src/video_core/renderer_vulkan/vk_texture_cache.cpp index ba58060d20..eda9ff2a5a 100644 --- a/src/video_core/renderer_vulkan/vk_texture_cache.cpp +++ b/src/video_core/renderer_vulkan/vk_texture_cache.cpp @@ -2160,20 +2160,34 @@ VkImageView ImageView::StorageView(Shader::TextureType texture_type, if (!image_handle) { return VK_NULL_HANDLE; } - if (image_format == Shader::ImageFormat::Typeless) { - return Handle(texture_type); - } - const bool is_signed{image_format == Shader::ImageFormat::R8_SINT || - image_format == Shader::ImageFormat::R16_SINT}; + if (!storage_views) { storage_views = std::make_unique(); } - auto& views{is_signed ? storage_views->signeds : storage_views->unsigneds}; - auto& view{views[static_cast(texture_type)]}; - if (view) { + + // Storage images MUST use identity component mapping. + // Typeless: use the underlying image's native format. + if (image_format == Shader::ImageFormat::Typeless) { + auto& view = storage_views->unsigneds[static_cast(texture_type)]; + if (view) { + return *view; + } + const auto fmt_info = + MaxwellToVK::SurfaceFormat(*device, FormatType::Optimal, /*is_image=*/true, format); + const VkFormat vk_format = fmt_info.format; + // Storage images are color-aspect only + view = MakeView(vk_format, VK_IMAGE_ASPECT_COLOR_BIT); // identity components inside return *view; } - view = MakeView(Format(image_format), VK_IMAGE_ASPECT_COLOR_BIT); + const bool is_signed = (image_format == Shader::ImageFormat::R8_SINT ||image_format == Shader::ImageFormat::R16_SINT); + auto& views = is_signed ? storage_views->signeds : storage_views->unsigneds; + auto& view = views[static_cast(texture_type)]; + if (view) { + return *view; + } + + const VkFormat vk_format = Format(image_format); + view = MakeView(vk_format, VK_IMAGE_ASPECT_COLOR_BIT);// identity components inside return *view; } -- 2.39.5