aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorTakoroka <137927095+Takoroka@users.noreply.github.com>2026-10-30 04:39:39 -0400
committerTakoroka <137927095+Takoroka@users.noreply.github.com>2026-10-30 04:40:23 -0400
commitf0d1bbff79e933ffcdf466ed6286b0cba5b71dfb (patch)
tree78375a7fad49bb3b9acc9e88045b0b79643db12e /src
parent0218eacfd560d0ce48b3ffe64d279ee85bbf1347 (diff)
vk_texture_cache: trim huge ASTC arrays harder on small GPUs
A trimmed ASTC array kept up to 512 MiB on the host. On GPUs with less than 7 GiB it now keeps up to 256 MiB (one mip level less): Mario Kart World's two terrain arrays took 724 MiB of a 6 GB card next to ~1.2 GB of other sparse terrain textures. EDEN_NX2_ASTC_ARRAY_MIB=<MiB> sets the limit.
Diffstat (limited to 'src')
-rw-r--r--src/video_core/renderer_vulkan/vk_texture_cache.cpp17
1 files changed, 16 insertions, 1 deletions
diff --git a/src/video_core/renderer_vulkan/vk_texture_cache.cpp b/src/video_core/renderer_vulkan/vk_texture_cache.cpp
index f5fcdd1380..b6b7e686f9 100644
--- a/src/video_core/renderer_vulkan/vk_texture_cache.cpp
+++ b/src/video_core/renderer_vulkan/vk_texture_cache.cpp
@@ -219,6 +219,20 @@ constexpr std::array<VkFormat, 2> OpaqueAstcViewFormats{VK_FORMAT_BC1_RGBA_UNORM
info.size.depth == 1;
}
+// The most a trimmed ASTC array keeps on the host: 512 MiB, 256 MiB on GPUs with less than 7 GiB
+// (title 1's two terrain arrays took 724 MiB of a 6 GB card next to ~1.2 GB of other sparse terrain
+// textures). EDEN_NX2_ASTC_ARRAY_MIB=<MiB> sets it.
+[[nodiscard]] u64 TrimmedAstcArrayLimit(const Device& device) {
+ static const u64 forced = [] {
+ const char* value = std::getenv("EDEN_NX2_ASTC_ARRAY_MIB");
+ return value != nullptr ? std::strtoull(value, nullptr, 10) << 20 : 0ULL;
+ }();
+ if (forced != 0) {
+ return forced;
+ }
+ return device.GetDeviceLocalMemory() < (u64{7} << 30) ? (u64{256} << 20) : (u64{512} << 20);
+}
+
// The host shape of an image whose decoded copy would not fit in VRAM: a GPU-decoded ASTC array
// over 1 GiB as RGBA8 (title 1's 8192x8192x68 ASTC 8x8 virtual textures are 24 GB each) keeps only
// its mip levels from `level_offset` on, so host mip 0 is guest mip `level_offset`. Normalized
@@ -239,8 +253,9 @@ constexpr std::array<VkFormat, 2> OpaqueAstcViewFormats{VK_FORMAT_BC1_RGBA_UNORM
if (decoded_bytes(0) <= (u64{1} << 30)) {
return info;
}
+ const u64 limit = TrimmedAstcArrayLimit(device);
while (level_offset + 1 < static_cast<u32>(info.resources.levels) &&
- decoded_bytes(level_offset) > (u64{512} << 20)) {
+ decoded_bytes(level_offset) > limit) {
++level_offset;
}
ImageInfo host = info;