diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/video_core/texture_cache/util.cpp | 41 |
1 files changed, 20 insertions, 21 deletions
diff --git a/src/video_core/texture_cache/util.cpp b/src/video_core/texture_cache/util.cpp index 0a86ce139..2e8160db0 100644 --- a/src/video_core/texture_cache/util.cpp +++ b/src/video_core/texture_cache/util.cpp | |||
| @@ -68,6 +68,7 @@ struct LevelInfo { | |||
| 68 | Extent2D tile_size; | 68 | Extent2D tile_size; |
| 69 | u32 bpp_log2; | 69 | u32 bpp_log2; |
| 70 | u32 tile_width_spacing; | 70 | u32 tile_width_spacing; |
| 71 | u32 num_levels; | ||
| 71 | }; | 72 | }; |
| 72 | 73 | ||
| 73 | [[nodiscard]] constexpr u32 AdjustTileSize(u32 shift, u32 unit_factor, u32 dimension) { | 74 | [[nodiscard]] constexpr u32 AdjustTileSize(u32 shift, u32 unit_factor, u32 dimension) { |
| @@ -118,11 +119,11 @@ template <u32 GOB_EXTENT> | |||
| 118 | } | 119 | } |
| 119 | 120 | ||
| 120 | [[nodiscard]] constexpr Extent3D AdjustMipBlockSize(Extent3D num_tiles, Extent3D block_size, | 121 | [[nodiscard]] constexpr Extent3D AdjustMipBlockSize(Extent3D num_tiles, Extent3D block_size, |
| 121 | u32 level) { | 122 | u32 level, u32 num_levels) { |
| 122 | return { | 123 | return { |
| 123 | .width = AdjustMipBlockSize<GOB_SIZE_X>(num_tiles.width, block_size.width, level), | 124 | .width = AdjustMipBlockSize<GOB_SIZE_X>(num_tiles.width, block_size.width, level), |
| 124 | .height = AdjustMipBlockSize<GOB_SIZE_Y>(num_tiles.height, block_size.height, level), | 125 | .height = AdjustMipBlockSize<GOB_SIZE_Y>(num_tiles.height, block_size.height, level), |
| 125 | .depth = level == 0 | 126 | .depth = level == 0 && num_levels == 1 |
| 126 | ? block_size.depth | 127 | ? block_size.depth |
| 127 | : AdjustMipBlockSize<GOB_SIZE_Z>(num_tiles.depth, block_size.depth, level), | 128 | : AdjustMipBlockSize<GOB_SIZE_Z>(num_tiles.depth, block_size.depth, level), |
| 128 | }; | 129 | }; |
| @@ -166,13 +167,6 @@ template <u32 GOB_EXTENT> | |||
| 166 | } | 167 | } |
| 167 | 168 | ||
| 168 | [[nodiscard]] constexpr Extent3D TileShift(const LevelInfo& info, u32 level) { | 169 | [[nodiscard]] constexpr Extent3D TileShift(const LevelInfo& info, u32 level) { |
| 169 | if (level == 0) { | ||
| 170 | return Extent3D{ | ||
| 171 | .width = info.block.width, | ||
| 172 | .height = info.block.height, | ||
| 173 | .depth = info.block.depth, | ||
| 174 | }; | ||
| 175 | } | ||
| 176 | const Extent3D blocks = NumLevelBlocks(info, level); | 170 | const Extent3D blocks = NumLevelBlocks(info, level); |
| 177 | return Extent3D{ | 171 | return Extent3D{ |
| 178 | .width = AdjustTileSize(info.block.width, GOB_SIZE_X, blocks.width), | 172 | .width = AdjustTileSize(info.block.width, GOB_SIZE_X, blocks.width), |
| @@ -257,7 +251,7 @@ template <u32 GOB_EXTENT> | |||
| 257 | } | 251 | } |
| 258 | 252 | ||
| 259 | [[nodiscard]] constexpr LevelInfo MakeLevelInfo(PixelFormat format, Extent3D size, Extent3D block, | 253 | [[nodiscard]] constexpr LevelInfo MakeLevelInfo(PixelFormat format, Extent3D size, Extent3D block, |
| 260 | u32 tile_width_spacing) { | 254 | u32 tile_width_spacing, u32 num_levels) { |
| 261 | const u32 bytes_per_block = BytesPerBlock(format); | 255 | const u32 bytes_per_block = BytesPerBlock(format); |
| 262 | return { | 256 | return { |
| 263 | .size = | 257 | .size = |
| @@ -270,16 +264,18 @@ template <u32 GOB_EXTENT> | |||
| 270 | .tile_size = DefaultBlockSize(format), | 264 | .tile_size = DefaultBlockSize(format), |
| 271 | .bpp_log2 = BytesPerBlockLog2(bytes_per_block), | 265 | .bpp_log2 = BytesPerBlockLog2(bytes_per_block), |
| 272 | .tile_width_spacing = tile_width_spacing, | 266 | .tile_width_spacing = tile_width_spacing, |
| 267 | .num_levels = num_levels, | ||
| 273 | }; | 268 | }; |
| 274 | } | 269 | } |
| 275 | 270 | ||
| 276 | [[nodiscard]] constexpr LevelInfo MakeLevelInfo(const ImageInfo& info) { | 271 | [[nodiscard]] constexpr LevelInfo MakeLevelInfo(const ImageInfo& info) { |
| 277 | return MakeLevelInfo(info.format, info.size, info.block, info.tile_width_spacing); | 272 | return MakeLevelInfo(info.format, info.size, info.block, info.tile_width_spacing, |
| 273 | info.resources.levels); | ||
| 278 | } | 274 | } |
| 279 | 275 | ||
| 280 | [[nodiscard]] constexpr u32 CalculateLevelOffset(PixelFormat format, Extent3D size, Extent3D block, | 276 | [[nodiscard]] constexpr u32 CalculateLevelOffset(PixelFormat format, Extent3D size, Extent3D block, |
| 281 | u32 tile_width_spacing, u32 level) { | 277 | u32 tile_width_spacing, u32 level) { |
| 282 | const LevelInfo info = MakeLevelInfo(format, size, block, tile_width_spacing); | 278 | const LevelInfo info = MakeLevelInfo(format, size, block, tile_width_spacing, level); |
| 283 | u32 offset = 0; | 279 | u32 offset = 0; |
| 284 | for (u32 current_level = 0; current_level < level; ++current_level) { | 280 | for (u32 current_level = 0; current_level < level; ++current_level) { |
| 285 | offset += CalculateLevelSize(info, current_level); | 281 | offset += CalculateLevelSize(info, current_level); |
| @@ -466,7 +462,7 @@ template <u32 GOB_EXTENT> | |||
| 466 | }; | 462 | }; |
| 467 | const u32 bpp_log2 = BytesPerBlockLog2(info.format); | 463 | const u32 bpp_log2 = BytesPerBlockLog2(info.format); |
| 468 | const u32 alignment = StrideAlignment(num_tiles, info.block, bpp_log2, info.tile_width_spacing); | 464 | const u32 alignment = StrideAlignment(num_tiles, info.block, bpp_log2, info.tile_width_spacing); |
| 469 | const Extent3D mip_block = AdjustMipBlockSize(num_tiles, info.block, 0); | 465 | const Extent3D mip_block = AdjustMipBlockSize(num_tiles, info.block, 0, info.resources.levels); |
| 470 | return Extent3D{ | 466 | return Extent3D{ |
| 471 | .width = Common::AlignUpLog2(num_tiles.width, alignment), | 467 | .width = Common::AlignUpLog2(num_tiles.width, alignment), |
| 472 | .height = Common::AlignUpLog2(num_tiles.height, GOB_SIZE_Y_SHIFT + mip_block.height), | 468 | .height = Common::AlignUpLog2(num_tiles.height, GOB_SIZE_Y_SHIFT + mip_block.height), |
| @@ -533,7 +529,8 @@ void SwizzleBlockLinearImage(Tegra::MemoryManager& gpu_memory, GPUVAddr gpu_addr | |||
| 533 | UNIMPLEMENTED_IF(copy.image_extent != level_size); | 529 | UNIMPLEMENTED_IF(copy.image_extent != level_size); |
| 534 | 530 | ||
| 535 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); | 531 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); |
| 536 | const Extent3D block = AdjustMipBlockSize(num_tiles, level_info.block, level); | 532 | const Extent3D block = |
| 533 | AdjustMipBlockSize(num_tiles, level_info.block, level, level_info.num_levels); | ||
| 537 | 534 | ||
| 538 | size_t host_offset = copy.buffer_offset; | 535 | size_t host_offset = copy.buffer_offset; |
| 539 | 536 | ||
| @@ -698,7 +695,7 @@ u32 CalculateLevelStrideAlignment(const ImageInfo& info, u32 level) { | |||
| 698 | const Extent2D tile_size = DefaultBlockSize(info.format); | 695 | const Extent2D tile_size = DefaultBlockSize(info.format); |
| 699 | const Extent3D level_size = AdjustMipSize(info.size, level); | 696 | const Extent3D level_size = AdjustMipSize(info.size, level); |
| 700 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); | 697 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); |
| 701 | const Extent3D block = AdjustMipBlockSize(num_tiles, info.block, level); | 698 | const Extent3D block = AdjustMipBlockSize(num_tiles, info.block, level, info.resources.levels); |
| 702 | const u32 bpp_log2 = BytesPerBlockLog2(info.format); | 699 | const u32 bpp_log2 = BytesPerBlockLog2(info.format); |
| 703 | return StrideAlignment(num_tiles, block, bpp_log2, info.tile_width_spacing); | 700 | return StrideAlignment(num_tiles, block, bpp_log2, info.tile_width_spacing); |
| 704 | } | 701 | } |
| @@ -887,7 +884,8 @@ boost::container::small_vector<BufferImageCopy, 16> UnswizzleImage(Tegra::Memory | |||
| 887 | .image_extent = level_size, | 884 | .image_extent = level_size, |
| 888 | }; | 885 | }; |
| 889 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); | 886 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); |
| 890 | const Extent3D block = AdjustMipBlockSize(num_tiles, level_info.block, level); | 887 | const Extent3D block = |
| 888 | AdjustMipBlockSize(num_tiles, info.block, level, level_info.num_levels); | ||
| 891 | const u32 stride_alignment = StrideAlignment(num_tiles, info.block, gob, bpp_log2); | 889 | const u32 stride_alignment = StrideAlignment(num_tiles, info.block, gob, bpp_log2); |
| 892 | size_t guest_layer_offset = 0; | 890 | size_t guest_layer_offset = 0; |
| 893 | 891 | ||
| @@ -1041,7 +1039,7 @@ Extent3D MipBlockSize(const ImageInfo& info, u32 level) { | |||
| 1041 | const Extent2D tile_size = DefaultBlockSize(info.format); | 1039 | const Extent2D tile_size = DefaultBlockSize(info.format); |
| 1042 | const Extent3D level_size = AdjustMipSize(info.size, level); | 1040 | const Extent3D level_size = AdjustMipSize(info.size, level); |
| 1043 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); | 1041 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); |
| 1044 | return AdjustMipBlockSize(num_tiles, level_info.block, level); | 1042 | return AdjustMipBlockSize(num_tiles, level_info.block, level, level_info.num_levels); |
| 1045 | } | 1043 | } |
| 1046 | 1044 | ||
| 1047 | boost::container::small_vector<SwizzleParameters, 16> FullUploadSwizzles(const ImageInfo& info) { | 1045 | boost::container::small_vector<SwizzleParameters, 16> FullUploadSwizzles(const ImageInfo& info) { |
| @@ -1063,7 +1061,8 @@ boost::container::small_vector<SwizzleParameters, 16> FullUploadSwizzles(const I | |||
| 1063 | for (s32 level = 0; level < num_levels; ++level) { | 1061 | for (s32 level = 0; level < num_levels; ++level) { |
| 1064 | const Extent3D level_size = AdjustMipSize(size, level); | 1062 | const Extent3D level_size = AdjustMipSize(size, level); |
| 1065 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); | 1063 | const Extent3D num_tiles = AdjustTileSize(level_size, tile_size); |
| 1066 | const Extent3D block = AdjustMipBlockSize(num_tiles, level_info.block, level); | 1064 | const Extent3D block = |
| 1065 | AdjustMipBlockSize(num_tiles, info.block, level, level_info.num_levels); | ||
| 1067 | params[level] = SwizzleParameters{ | 1066 | params[level] = SwizzleParameters{ |
| 1068 | .num_tiles = num_tiles, | 1067 | .num_tiles = num_tiles, |
| 1069 | .block = block, | 1068 | .block = block, |
| @@ -1292,11 +1291,11 @@ u32 MapSizeBytes(const ImageBase& image) { | |||
| 1292 | } | 1291 | } |
| 1293 | } | 1292 | } |
| 1294 | 1293 | ||
| 1295 | static_assert(CalculateLevelSize(LevelInfo{{1920, 1080, 1}, {0, 2, 0}, {1, 1}, 2, 0}, 0) == | 1294 | static_assert(CalculateLevelSize(LevelInfo{{1920, 1080, 1}, {0, 2, 0}, {1, 1}, 2, 0, 1}, 0) == |
| 1296 | 0x7f8000); | 1295 | 0x7f8000); |
| 1297 | static_assert(CalculateLevelSize(LevelInfo{{32, 32, 1}, {0, 0, 4}, {1, 1}, 4, 0}, 0) == 0x40000); | 1296 | static_assert(CalculateLevelSize(LevelInfo{{32, 32, 1}, {0, 0, 4}, {1, 1}, 4, 0, 1}, 0) == 0x4000); |
| 1298 | 1297 | ||
| 1299 | static_assert(CalculateLevelSize(LevelInfo{{128, 8, 1}, {0, 4, 0}, {1, 1}, 4, 0}, 0) == 0x40000); | 1298 | static_assert(CalculateLevelSize(LevelInfo{{128, 8, 1}, {0, 4, 0}, {1, 1}, 4, 0, 1}, 0) == 0x4000); |
| 1300 | 1299 | ||
| 1301 | static_assert(CalculateLevelOffset(PixelFormat::R8_SINT, {1920, 1080, 1}, {0, 2, 0}, 0, 7) == | 1300 | static_assert(CalculateLevelOffset(PixelFormat::R8_SINT, {1920, 1080, 1}, {0, 2, 0}, 0, 7) == |
| 1302 | 0x2afc00); | 1301 | 0x2afc00); |