diff --git a/src/xenia/gpu/shaders/texture_address.xesli b/src/xenia/gpu/shaders/texture_address.xesli index 98a5003a3..a0fb1bae1 100644 --- a/src/xenia/gpu/shaders/texture_address.xesli +++ b/src/xenia/gpu/shaders/texture_address.xesli @@ -12,6 +12,11 @@ #include "../../ui/shaders/xesl.xesli" +#define XENOS_TEXTURE_MACRO_TILE_WIDTH_LOG2 5 +#define XENOS_TEXTURE_MACRO_TILE_HEIGHT_2D_LOG2 5 +#define XENOS_TEXTURE_MACRO_TILE_HEIGHT_3D_LOG2 4 +#define XENOS_TEXTURE_MACRO_TILE_DEPTH_LOG2 2 + int XenosTextureAddressTiledCombine(const int outer_inner_bytes, const int bank, const int pipe, const int y_lsb) { return (y_lsb << 4) | (pipe << 6) | (bank << 11) | (outer_inner_bytes & 0xF) | @@ -20,10 +25,13 @@ int XenosTextureAddressTiledCombine(const int outer_inner_bytes, const int bank, (outer_inner_bytes >> 8 << 12); } -int XenosTextureAddressTiled2D(const int2_xe p, const uint pitch_aligned_shr5, +int XenosTextureAddressTiled2D(const int2_xe p, const uint pitch_macro_tiles, const uint bytes_per_element_log2) { const int outer_elements = - ((p.y >> 5) * int(pitch_aligned_shr5) + (p.x >> 5)) << 6; + ((p.y >> XENOS_TEXTURE_MACRO_TILE_HEIGHT_2D_LOG2) * + int(pitch_macro_tiles) + + (p.x >> XENOS_TEXTURE_MACRO_TILE_WIDTH_LOG2)) + << 6; const int inner_elements = (((p.y >> 1) & 0x7) << 3) | (p.x & 0x7); const int outer_inner_bytes = (outer_elements | inner_elements) << bytes_per_element_log2; @@ -33,13 +41,15 @@ int XenosTextureAddressTiled2D(const int2_xe p, const uint pitch_aligned_shr5, p.y & 1); } -int XenosTextureAddressTiled3D(const int3_xe p, const uint pitch_aligned_shr5, - const uint height_aligned_shr4, +int XenosTextureAddressTiled3D(const int3_xe p, const uint pitch_macro_tiles, + const uint height_macro_tiles, const uint bytes_per_element_log2) { const int outer_elements = - ((((p.z >> 2) * int(height_aligned_shr4) + (p.y >> 4)) * - int(pitch_aligned_shr5)) + - (p.x >> 5)) + ((((p.z >> XENOS_TEXTURE_MACRO_TILE_DEPTH_LOG2) * + int(height_macro_tiles) + + (p.y >> XENOS_TEXTURE_MACRO_TILE_HEIGHT_3D_LOG2)) * + int(pitch_macro_tiles)) + + (p.x >> XENOS_TEXTURE_MACRO_TILE_WIDTH_LOG2)) << 7; const int inner_elements = ((p.z & 0x3) << 5) | (((p.y >> 1) & 0x3) << 3) | (p.x & 0x7); diff --git a/src/xenia/gpu/texture_address.h b/src/xenia/gpu/texture_address.h index fca47a637..5f1c49d37 100644 --- a/src/xenia/gpu/texture_address.h +++ b/src/xenia/gpu/texture_address.h @@ -168,6 +168,15 @@ constexpr uint32_t kStorageDepthAlignmentElements = // offsetting - more specifically, it's limited by the page size and the macro // tile size, whichever is greater. +constexpr unsigned int kMacroTileWidthLog2 = 5; +constexpr uint32_t kMacroTileWidth = uint32_t(1) << kMacroTileWidthLog2; +constexpr unsigned int kMacroTileHeight2DLog2 = 5; +constexpr uint32_t kMacroTileHeight2D = uint32_t(1) << kMacroTileHeight2DLog2; +constexpr unsigned int kMacroTileHeight3DLog2 = 4; +constexpr uint32_t kMacroTileHeight3D = uint32_t(1) << kMacroTileHeight3DLog2; +constexpr unsigned int kMacroTileDepthLog2 = 2; +constexpr uint32_t kMacroTileDepth = uint32_t(1) << kMacroTileDepthLog2; + template Address TiledCombine(const Address outer_inner_bytes, const uint32_t bank, const uint32_t pipe, const uint32_t y_lsb) { @@ -193,7 +202,10 @@ inline int32_t Tiled2D(const int32_t x, const int32_t y, // the actual storage dimensions. assert_zero(pitch_aligned & (kStoragePitchHeightAlignmentElements - 1)); const int32_t outer_elements = - ((y >> 5) * int32_t(pitch_aligned >> 5) + (x >> 5)) << 6; + ((y >> kMacroTileHeight2DLog2) * + int32_t(pitch_aligned >> kMacroTileWidthLog2) + + (x >> kMacroTileWidthLog2)) + << 6; const int32_t inner_elements = (((y >> 1) & 0b111) << 3) | (x & 0b111); const int32_t outer_inner_bytes = (outer_elements | inner_elements) << bytes_per_element_log2; @@ -217,9 +229,11 @@ inline int64_t Tiled3D(const int32_t x, const int32_t y, const int32_t z, // The absolute of `outer_elements` is below (1024 / 4) * (2048 / 16) * // (16384 / 32) * 128 = 2^31. const int32_t outer_elements = - ((((z >> 2) * (height_aligned >> 4) + (y >> 4)) * - int32_t(pitch_aligned >> 5)) + - (x >> 5)) + ((((z >> kMacroTileDepthLog2) * + (height_aligned >> kMacroTileHeight3DLog2) + + (y >> kMacroTileHeight3DLog2)) * + int32_t(pitch_aligned >> kMacroTileWidthLog2)) + + (x >> kMacroTileWidthLog2)) << 7; const int32_t inner_elements = ((z & 0b11) << 5) | (((y >> 1) & 0b11) << 3) | (x & 0b111);