yuzu-emu
/
yuzu-mainline
Archived
1
0
Fork 0

Merge pull request #3086 from ReinUsesLisp/format-lookups

texture_cache: Use a flat table instead of switch for texture format lookups
This commit is contained in:
bunnei 2019-11-19 18:29:17 -05:00 committed by GitHub
commit b0819e2ffb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
12 changed files with 442 additions and 555 deletions

View File

@ -127,6 +127,8 @@ add_library(video_core STATIC
shader/track.cpp shader/track.cpp
surface.cpp surface.cpp
surface.h surface.h
texture_cache/format_lookup_table.cpp
texture_cache/format_lookup_table.h
texture_cache/surface_base.cpp texture_cache/surface_base.cpp
texture_cache/surface_base.h texture_cache/surface_base.h
texture_cache/surface_params.cpp texture_cache/surface_params.cpp

View File

@ -742,14 +742,6 @@ Texture::TICEntry Maxwell3D::GetTICEntry(u32 tic_index) const {
Texture::TICEntry tic_entry; Texture::TICEntry tic_entry;
memory_manager.ReadBlockUnsafe(tic_address_gpu, &tic_entry, sizeof(Texture::TICEntry)); memory_manager.ReadBlockUnsafe(tic_address_gpu, &tic_entry, sizeof(Texture::TICEntry));
[[maybe_unused]] const auto r_type{tic_entry.r_type.Value()};
[[maybe_unused]] const auto g_type{tic_entry.g_type.Value()};
[[maybe_unused]] const auto b_type{tic_entry.b_type.Value()};
[[maybe_unused]] const auto a_type{tic_entry.a_type.Value()};
// TODO(Subv): Different data types for separate components are not supported
DEBUG_ASSERT(r_type == g_type && r_type == b_type && r_type == a_type);
return tic_entry; return tic_entry;
} }

View File

@ -23,7 +23,6 @@ namespace OpenGL {
using Tegra::Texture::SwizzleSource; using Tegra::Texture::SwizzleSource;
using VideoCore::MortonSwizzleMode; using VideoCore::MortonSwizzleMode;
using VideoCore::Surface::ComponentType;
using VideoCore::Surface::PixelFormat; using VideoCore::Surface::PixelFormat;
using VideoCore::Surface::SurfaceCompression; using VideoCore::Surface::SurfaceCompression;
using VideoCore::Surface::SurfaceTarget; using VideoCore::Surface::SurfaceTarget;
@ -40,114 +39,95 @@ struct FormatTuple {
GLint internal_format; GLint internal_format;
GLenum format; GLenum format;
GLenum type; GLenum type;
ComponentType component_type;
bool compressed; bool compressed;
}; };
constexpr std::array<FormatTuple, VideoCore::Surface::MaxPixelFormat> tex_format_tuples = {{ constexpr std::array<FormatTuple, VideoCore::Surface::MaxPixelFormat> tex_format_tuples = {{
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV, ComponentType::UNorm, false}, // ABGR8U {GL_RGBA8, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV, false}, // ABGR8U
{GL_RGBA8, GL_RGBA, GL_BYTE, ComponentType::SNorm, false}, // ABGR8S {GL_RGBA8, GL_RGBA, GL_BYTE, false}, // ABGR8S
{GL_RGBA8UI, GL_RGBA_INTEGER, GL_UNSIGNED_BYTE, ComponentType::UInt, false}, // ABGR8UI {GL_RGBA8UI, GL_RGBA_INTEGER, GL_UNSIGNED_BYTE, false}, // ABGR8UI
{GL_RGB565, GL_RGB, GL_UNSIGNED_SHORT_5_6_5_REV, ComponentType::UNorm, false}, // B5G6R5U {GL_RGB565, GL_RGB, GL_UNSIGNED_SHORT_5_6_5_REV, false}, // B5G6R5U
{GL_RGB10_A2, GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV, ComponentType::UNorm, {GL_RGB10_A2, GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV, false}, // A2B10G10R10U
false}, // A2B10G10R10U {GL_RGB5_A1, GL_RGBA, GL_UNSIGNED_SHORT_1_5_5_5_REV, false}, // A1B5G5R5U
{GL_RGB5_A1, GL_RGBA, GL_UNSIGNED_SHORT_1_5_5_5_REV, ComponentType::UNorm, false}, // A1B5G5R5U {GL_R8, GL_RED, GL_UNSIGNED_BYTE, false}, // R8U
{GL_R8, GL_RED, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // R8U {GL_R8UI, GL_RED_INTEGER, GL_UNSIGNED_BYTE, false}, // R8UI
{GL_R8UI, GL_RED_INTEGER, GL_UNSIGNED_BYTE, ComponentType::UInt, false}, // R8UI {GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT, false}, // RGBA16F
{GL_RGBA16F, GL_RGBA, GL_HALF_FLOAT, ComponentType::Float, false}, // RGBA16F {GL_RGBA16, GL_RGBA, GL_UNSIGNED_SHORT, false}, // RGBA16U
{GL_RGBA16, GL_RGBA, GL_UNSIGNED_SHORT, ComponentType::UNorm, false}, // RGBA16U {GL_RGBA16UI, GL_RGBA_INTEGER, GL_UNSIGNED_SHORT, false}, // RGBA16UI
{GL_RGBA16UI, GL_RGBA_INTEGER, GL_UNSIGNED_SHORT, ComponentType::UInt, false}, // RGBA16UI {GL_R11F_G11F_B10F, GL_RGB, GL_UNSIGNED_INT_10F_11F_11F_REV, false}, // R11FG11FB10F
{GL_R11F_G11F_B10F, GL_RGB, GL_UNSIGNED_INT_10F_11F_11F_REV, ComponentType::Float, {GL_RGBA32UI, GL_RGBA_INTEGER, GL_UNSIGNED_INT, false}, // RGBA32UI
false}, // R11FG11FB10F {GL_COMPRESSED_RGBA_S3TC_DXT1_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // DXT1
{GL_RGBA32UI, GL_RGBA_INTEGER, GL_UNSIGNED_INT, ComponentType::UInt, false}, // RGBA32UI {GL_COMPRESSED_RGBA_S3TC_DXT3_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // DXT23
{GL_COMPRESSED_RGBA_S3TC_DXT1_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // DXT45
true}, // DXT1 {GL_COMPRESSED_RED_RGTC1, GL_RED, GL_UNSIGNED_INT_8_8_8_8, true}, // DXN1
{GL_COMPRESSED_RGBA_S3TC_DXT3_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_COMPRESSED_RG_RGTC2, GL_RG, GL_UNSIGNED_INT_8_8_8_8, true}, // DXN2UNORM
true}, // DXT23 {GL_COMPRESSED_SIGNED_RG_RGTC2, GL_RG, GL_INT, true}, // DXN2SNORM
{GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_COMPRESSED_RGBA_BPTC_UNORM, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // BC7U
true}, // DXT45 {GL_COMPRESSED_RGB_BPTC_UNSIGNED_FLOAT, GL_RGB, GL_UNSIGNED_INT_8_8_8_8, true}, // BC6H_UF16
{GL_COMPRESSED_RED_RGTC1, GL_RED, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, true}, // DXN1 {GL_COMPRESSED_RGB_BPTC_SIGNED_FLOAT, GL_RGB, GL_UNSIGNED_INT_8_8_8_8, true}, // BC6H_SF16
{GL_COMPRESSED_RG_RGTC2, GL_RG, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_4X4
true}, // DXN2UNORM {GL_RGBA8, GL_BGRA, GL_UNSIGNED_BYTE, false}, // BGRA8
{GL_COMPRESSED_SIGNED_RG_RGTC2, GL_RG, GL_INT, ComponentType::SNorm, true}, // DXN2SNORM {GL_RGBA32F, GL_RGBA, GL_FLOAT, false}, // RGBA32F
{GL_COMPRESSED_RGBA_BPTC_UNORM, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_RG32F, GL_RG, GL_FLOAT, false}, // RG32F
true}, // BC7U {GL_R32F, GL_RED, GL_FLOAT, false}, // R32F
{GL_COMPRESSED_RGB_BPTC_UNSIGNED_FLOAT, GL_RGB, GL_UNSIGNED_INT_8_8_8_8, ComponentType::Float, {GL_R16F, GL_RED, GL_HALF_FLOAT, false}, // R16F
true}, // BC6H_UF16 {GL_R16, GL_RED, GL_UNSIGNED_SHORT, false}, // R16U
{GL_COMPRESSED_RGB_BPTC_SIGNED_FLOAT, GL_RGB, GL_UNSIGNED_INT_8_8_8_8, ComponentType::Float, {GL_R16_SNORM, GL_RED, GL_SHORT, false}, // R16S
true}, // BC6H_SF16 {GL_R16UI, GL_RED_INTEGER, GL_UNSIGNED_SHORT, false}, // R16UI
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_4X4 {GL_R16I, GL_RED_INTEGER, GL_SHORT, false}, // R16I
{GL_RGBA8, GL_BGRA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // BGRA8 {GL_RG16, GL_RG, GL_UNSIGNED_SHORT, false}, // RG16
{GL_RGBA32F, GL_RGBA, GL_FLOAT, ComponentType::Float, false}, // RGBA32F {GL_RG16F, GL_RG, GL_HALF_FLOAT, false}, // RG16F
{GL_RG32F, GL_RG, GL_FLOAT, ComponentType::Float, false}, // RG32F {GL_RG16UI, GL_RG_INTEGER, GL_UNSIGNED_SHORT, false}, // RG16UI
{GL_R32F, GL_RED, GL_FLOAT, ComponentType::Float, false}, // R32F {GL_RG16I, GL_RG_INTEGER, GL_SHORT, false}, // RG16I
{GL_R16F, GL_RED, GL_HALF_FLOAT, ComponentType::Float, false}, // R16F {GL_RG16_SNORM, GL_RG, GL_SHORT, false}, // RG16S
{GL_R16, GL_RED, GL_UNSIGNED_SHORT, ComponentType::UNorm, false}, // R16U {GL_RGB32F, GL_RGB, GL_FLOAT, false}, // RGB32F
{GL_R16_SNORM, GL_RED, GL_SHORT, ComponentType::SNorm, false}, // R16S {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV, false}, // RGBA8_SRGB
{GL_R16UI, GL_RED_INTEGER, GL_UNSIGNED_SHORT, ComponentType::UInt, false}, // R16UI {GL_RG8, GL_RG, GL_UNSIGNED_BYTE, false}, // RG8U
{GL_R16I, GL_RED_INTEGER, GL_SHORT, ComponentType::SInt, false}, // R16I {GL_RG8, GL_RG, GL_BYTE, false}, // RG8S
{GL_RG16, GL_RG, GL_UNSIGNED_SHORT, ComponentType::UNorm, false}, // RG16 {GL_RG32UI, GL_RG_INTEGER, GL_UNSIGNED_INT, false}, // RG32UI
{GL_RG16F, GL_RG, GL_HALF_FLOAT, ComponentType::Float, false}, // RG16F {GL_RGB16F, GL_RGBA16, GL_HALF_FLOAT, false}, // RGBX16F
{GL_RG16UI, GL_RG_INTEGER, GL_UNSIGNED_SHORT, ComponentType::UInt, false}, // RG16UI {GL_R32UI, GL_RED_INTEGER, GL_UNSIGNED_INT, false}, // R32UI
{GL_RG16I, GL_RG_INTEGER, GL_SHORT, ComponentType::SInt, false}, // RG16I {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_8X8
{GL_RG16_SNORM, GL_RG, GL_SHORT, ComponentType::SNorm, false}, // RG16S {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_8X5
{GL_RGB32F, GL_RGB, GL_FLOAT, ComponentType::Float, false}, // RGB32F {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_5X4
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8_REV, ComponentType::UNorm, {GL_SRGB8_ALPHA8, GL_BGRA, GL_UNSIGNED_BYTE, false}, // BGRA8
false}, // RGBA8_SRGB
{GL_RG8, GL_RG, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // RG8U
{GL_RG8, GL_RG, GL_BYTE, ComponentType::SNorm, false}, // RG8S
{GL_RG32UI, GL_RG_INTEGER, GL_UNSIGNED_INT, ComponentType::UInt, false}, // RG32UI
{GL_RGB16F, GL_RGBA16, GL_HALF_FLOAT, ComponentType::Float, false}, // RGBX16F
{GL_R32UI, GL_RED_INTEGER, GL_UNSIGNED_INT, ComponentType::UInt, false}, // R32UI
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_8X8
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_8X5
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_5X4
{GL_SRGB8_ALPHA8, GL_BGRA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // BGRA8
// Compressed sRGB formats // Compressed sRGB formats
{GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT1_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // DXT1_SRGB
true}, // DXT1_SRGB {GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // DXT23_SRGB
{GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT3_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // DXT45_SRGB
true}, // DXT23_SRGB {GL_COMPRESSED_SRGB_ALPHA_BPTC_UNORM, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, true}, // BC7U_SRGB
{GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_RGBA4, GL_RGBA, GL_UNSIGNED_SHORT_4_4_4_4_REV, false}, // R4G4B4A4U
true}, // DXT45_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_4X4_SRGB
{GL_COMPRESSED_SRGB_ALPHA_BPTC_UNORM, GL_RGBA, GL_UNSIGNED_INT_8_8_8_8, ComponentType::UNorm, {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_8X8_SRGB
true}, // BC7U_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_8X5_SRGB
{GL_RGBA4, GL_RGBA, GL_UNSIGNED_SHORT_4_4_4_4_REV, ComponentType::UNorm, false}, // R4G4B4A4U {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_5X4_SRGB
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_4X4_SRGB {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_5X5
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_8X8_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_5X5_SRGB
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_8X5_SRGB {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_10X8
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_5X4_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_10X8_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_5X5 {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_6X6
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_5X5_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_6X6_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_10X8 {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_10X10
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_10X8_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_10X10_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_6X6 {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_12X12
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_6X6_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_12X12_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_10X10 {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_8X6
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_10X10_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_8X6_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_12X12 {GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_6X5
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_12X12_SRGB {GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, false}, // ASTC_2D_6X5_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_8X6 {GL_RGB9_E5, GL_RGB, GL_UNSIGNED_INT_5_9_9_9_REV, false}, // E5B9G9R9F
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_8X6_SRGB
{GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_6X5
{GL_SRGB8_ALPHA8, GL_RGBA, GL_UNSIGNED_BYTE, ComponentType::UNorm, false}, // ASTC_2D_6X5_SRGB
{GL_RGB9_E5, GL_RGB, GL_UNSIGNED_INT_5_9_9_9_REV, ComponentType::Float, false}, // E5B9G9R9F
// Depth formats // Depth formats
{GL_DEPTH_COMPONENT32F, GL_DEPTH_COMPONENT, GL_FLOAT, ComponentType::Float, false}, // Z32F {GL_DEPTH_COMPONENT32F, GL_DEPTH_COMPONENT, GL_FLOAT, false}, // Z32F
{GL_DEPTH_COMPONENT16, GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT, ComponentType::UNorm, {GL_DEPTH_COMPONENT16, GL_DEPTH_COMPONENT, GL_UNSIGNED_SHORT, false}, // Z16
false}, // Z16
// DepthStencil formats // DepthStencil formats
{GL_DEPTH24_STENCIL8, GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8, ComponentType::UNorm, {GL_DEPTH24_STENCIL8, GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8, false}, // Z24S8
false}, // Z24S8 {GL_DEPTH24_STENCIL8, GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8, false}, // S8Z24
{GL_DEPTH24_STENCIL8, GL_DEPTH_STENCIL, GL_UNSIGNED_INT_24_8, ComponentType::UNorm, {GL_DEPTH32F_STENCIL8, GL_DEPTH_STENCIL, GL_FLOAT_32_UNSIGNED_INT_24_8_REV, false}, // Z32FS8
false}, // S8Z24
{GL_DEPTH32F_STENCIL8, GL_DEPTH_STENCIL, GL_FLOAT_32_UNSIGNED_INT_24_8_REV,
ComponentType::Float, false}, // Z32FS8
}}; }};
const FormatTuple& GetFormatTuple(PixelFormat pixel_format, ComponentType component_type) { const FormatTuple& GetFormatTuple(PixelFormat pixel_format) {
ASSERT(static_cast<std::size_t>(pixel_format) < tex_format_tuples.size()); ASSERT(static_cast<std::size_t>(pixel_format) < tex_format_tuples.size());
const auto& format{tex_format_tuples[static_cast<std::size_t>(pixel_format)]}; const auto& format{tex_format_tuples[static_cast<std::size_t>(pixel_format)]};
return format; return format;
@ -249,7 +229,7 @@ OGLTexture CreateTexture(const SurfaceParams& params, GLenum target, GLenum inte
CachedSurface::CachedSurface(const GPUVAddr gpu_addr, const SurfaceParams& params) CachedSurface::CachedSurface(const GPUVAddr gpu_addr, const SurfaceParams& params)
: VideoCommon::SurfaceBase<View>(gpu_addr, params) { : VideoCommon::SurfaceBase<View>(gpu_addr, params) {
const auto& tuple{GetFormatTuple(params.pixel_format, params.component_type)}; const auto& tuple{GetFormatTuple(params.pixel_format)};
internal_format = tuple.internal_format; internal_format = tuple.internal_format;
format = tuple.format; format = tuple.format;
type = tuple.type; type = tuple.type;
@ -451,8 +431,7 @@ OGLTextureView CachedSurfaceView::CreateTextureView() const {
texture_view.Create(); texture_view.Create();
const GLuint handle{texture_view.handle}; const GLuint handle{texture_view.handle};
const FormatTuple& tuple{ const FormatTuple& tuple{GetFormatTuple(owner_params.pixel_format)};
GetFormatTuple(owner_params.pixel_format, owner_params.component_type)};
glTextureView(handle, target, surface.texture.handle, tuple.internal_format, params.base_level, glTextureView(handle, target, surface.texture.handle, tuple.internal_format, params.base_level,
params.num_levels, params.base_layer, params.num_layers); params.num_levels, params.base_layer, params.num_layers);
@ -562,8 +541,8 @@ void TextureCacheOpenGL::BufferCopy(Surface& src_surface, Surface& dst_surface)
const auto& dst_params = dst_surface->GetSurfaceParams(); const auto& dst_params = dst_surface->GetSurfaceParams();
UNIMPLEMENTED_IF(src_params.num_levels > 1 || dst_params.num_levels > 1); UNIMPLEMENTED_IF(src_params.num_levels > 1 || dst_params.num_levels > 1);
const auto source_format = GetFormatTuple(src_params.pixel_format, src_params.component_type); const auto source_format = GetFormatTuple(src_params.pixel_format);
const auto dest_format = GetFormatTuple(dst_params.pixel_format, dst_params.component_type); const auto dest_format = GetFormatTuple(dst_params.pixel_format);
const std::size_t source_size = src_surface->GetHostSizeInBytes(); const std::size_t source_size = src_surface->GetHostSizeInBytes();
const std::size_t dest_size = dst_surface->GetHostSizeInBytes(); const std::size_t dest_size = dst_surface->GetHostSizeInBytes();

View File

@ -95,83 +95,82 @@ vk::CompareOp DepthCompareFunction(Tegra::Texture::DepthCompareFunc depth_compar
} // namespace Sampler } // namespace Sampler
struct FormatTuple { struct FormatTuple {
vk::Format format; ///< Vulkan format vk::Format format; ///< Vulkan format
ComponentType component_type; ///< Abstracted component type bool attachable; ///< True when this format can be used as an attachment
bool attachable; ///< True when this format can be used as an attachment
}; };
static constexpr std::array<FormatTuple, VideoCore::Surface::MaxPixelFormat> tex_format_tuples = {{ static constexpr std::array<FormatTuple, VideoCore::Surface::MaxPixelFormat> tex_format_tuples = {{
{vk::Format::eA8B8G8R8UnormPack32, ComponentType::UNorm, true}, // ABGR8U {vk::Format::eA8B8G8R8UnormPack32, true}, // ABGR8U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ABGR8S {vk::Format::eUndefined, false}, // ABGR8S
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ABGR8UI {vk::Format::eUndefined, false}, // ABGR8UI
{vk::Format::eB5G6R5UnormPack16, ComponentType::UNorm, false}, // B5G6R5U {vk::Format::eB5G6R5UnormPack16, false}, // B5G6R5U
{vk::Format::eA2B10G10R10UnormPack32, ComponentType::UNorm, true}, // A2B10G10R10U {vk::Format::eA2B10G10R10UnormPack32, true}, // A2B10G10R10U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // A1B5G5R5U {vk::Format::eUndefined, false}, // A1B5G5R5U
{vk::Format::eR8Unorm, ComponentType::UNorm, true}, // R8U {vk::Format::eR8Unorm, true}, // R8U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R8UI {vk::Format::eUndefined, false}, // R8UI
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGBA16F {vk::Format::eUndefined, false}, // RGBA16F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGBA16U {vk::Format::eUndefined, false}, // RGBA16U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGBA16UI {vk::Format::eUndefined, false}, // RGBA16UI
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R11FG11FB10F {vk::Format::eUndefined, false}, // R11FG11FB10F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGBA32UI {vk::Format::eUndefined, false}, // RGBA32UI
{vk::Format::eBc1RgbaUnormBlock, ComponentType::UNorm, false}, // DXT1 {vk::Format::eBc1RgbaUnormBlock, false}, // DXT1
{vk::Format::eBc2UnormBlock, ComponentType::UNorm, false}, // DXT23 {vk::Format::eBc2UnormBlock, false}, // DXT23
{vk::Format::eBc3UnormBlock, ComponentType::UNorm, false}, // DXT45 {vk::Format::eBc3UnormBlock, false}, // DXT45
{vk::Format::eBc4UnormBlock, ComponentType::UNorm, false}, // DXN1 {vk::Format::eBc4UnormBlock, false}, // DXN1
{vk::Format::eUndefined, ComponentType::Invalid, false}, // DXN2UNORM {vk::Format::eUndefined, false}, // DXN2UNORM
{vk::Format::eUndefined, ComponentType::Invalid, false}, // DXN2SNORM {vk::Format::eUndefined, false}, // DXN2SNORM
{vk::Format::eUndefined, ComponentType::Invalid, false}, // BC7U {vk::Format::eUndefined, false}, // BC7U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // BC6H_UF16 {vk::Format::eUndefined, false}, // BC6H_UF16
{vk::Format::eUndefined, ComponentType::Invalid, false}, // BC6H_SF16 {vk::Format::eUndefined, false}, // BC6H_SF16
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_4X4 {vk::Format::eUndefined, false}, // ASTC_2D_4X4
{vk::Format::eUndefined, ComponentType::Invalid, false}, // BGRA8 {vk::Format::eUndefined, false}, // BGRA8
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGBA32F {vk::Format::eUndefined, false}, // RGBA32F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG32F {vk::Format::eUndefined, false}, // RG32F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R32F {vk::Format::eUndefined, false}, // R32F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R16F {vk::Format::eUndefined, false}, // R16F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R16U {vk::Format::eUndefined, false}, // R16U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R16S {vk::Format::eUndefined, false}, // R16S
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R16UI {vk::Format::eUndefined, false}, // R16UI
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R16I {vk::Format::eUndefined, false}, // R16I
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG16 {vk::Format::eUndefined, false}, // RG16
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG16F {vk::Format::eUndefined, false}, // RG16F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG16UI {vk::Format::eUndefined, false}, // RG16UI
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG16I {vk::Format::eUndefined, false}, // RG16I
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG16S {vk::Format::eUndefined, false}, // RG16S
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGB32F {vk::Format::eUndefined, false}, // RGB32F
{vk::Format::eA8B8G8R8SrgbPack32, ComponentType::UNorm, true}, // RGBA8_SRGB {vk::Format::eA8B8G8R8SrgbPack32, true}, // RGBA8_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG8U {vk::Format::eUndefined, false}, // RG8U
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG8S {vk::Format::eUndefined, false}, // RG8S
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RG32UI {vk::Format::eUndefined, false}, // RG32UI
{vk::Format::eUndefined, ComponentType::Invalid, false}, // RGBX16F {vk::Format::eUndefined, false}, // RGBX16F
{vk::Format::eUndefined, ComponentType::Invalid, false}, // R32UI {vk::Format::eUndefined, false}, // R32UI
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_8X8 {vk::Format::eUndefined, false}, // ASTC_2D_8X8
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_8X5 {vk::Format::eUndefined, false}, // ASTC_2D_8X5
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_5X4 {vk::Format::eUndefined, false}, // ASTC_2D_5X4
// Compressed sRGB formats // Compressed sRGB formats
{vk::Format::eUndefined, ComponentType::Invalid, false}, // BGRA8_SRGB {vk::Format::eUndefined, false}, // BGRA8_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // DXT1_SRGB {vk::Format::eUndefined, false}, // DXT1_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // DXT23_SRGB {vk::Format::eUndefined, false}, // DXT23_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // DXT45_SRGB {vk::Format::eUndefined, false}, // DXT45_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // BC7U_SRGB {vk::Format::eUndefined, false}, // BC7U_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_4X4_SRGB {vk::Format::eUndefined, false}, // ASTC_2D_4X4_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_8X8_SRGB {vk::Format::eUndefined, false}, // ASTC_2D_8X8_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_8X5_SRGB {vk::Format::eUndefined, false}, // ASTC_2D_8X5_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_5X4_SRGB {vk::Format::eUndefined, false}, // ASTC_2D_5X4_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_5X5 {vk::Format::eUndefined, false}, // ASTC_2D_5X5
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_5X5_SRGB {vk::Format::eUndefined, false}, // ASTC_2D_5X5_SRGB
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_10X8 {vk::Format::eUndefined, false}, // ASTC_2D_10X8
{vk::Format::eUndefined, ComponentType::Invalid, false}, // ASTC_2D_10X8_SRGB {vk::Format::eUndefined, false}, // ASTC_2D_10X8_SRGB
// Depth formats // Depth formats
{vk::Format::eD32Sfloat, ComponentType::Float, true}, // Z32F {vk::Format::eD32Sfloat, true}, // Z32F
{vk::Format::eD16Unorm, ComponentType::UNorm, true}, // Z16 {vk::Format::eD16Unorm, true}, // Z16
// DepthStencil formats // DepthStencil formats
{vk::Format::eD24UnormS8Uint, ComponentType::UNorm, true}, // Z24S8 {vk::Format::eD24UnormS8Uint, true}, // Z24S8
{vk::Format::eD24UnormS8Uint, ComponentType::UNorm, true}, // S8Z24 (emulated) {vk::Format::eD24UnormS8Uint, true}, // S8Z24 (emulated)
{vk::Format::eUndefined, ComponentType::Invalid, false}, // Z32FS8 {vk::Format::eUndefined, false}, // Z32FS8
}}; }};
static constexpr bool IsZetaFormat(PixelFormat pixel_format) { static constexpr bool IsZetaFormat(PixelFormat pixel_format) {
@ -180,14 +179,13 @@ static constexpr bool IsZetaFormat(PixelFormat pixel_format) {
} }
std::pair<vk::Format, bool> SurfaceFormat(const VKDevice& device, FormatType format_type, std::pair<vk::Format, bool> SurfaceFormat(const VKDevice& device, FormatType format_type,
PixelFormat pixel_format, ComponentType component_type) { PixelFormat pixel_format) {
ASSERT(static_cast<std::size_t>(pixel_format) < tex_format_tuples.size()); ASSERT(static_cast<std::size_t>(pixel_format) < tex_format_tuples.size());
const auto tuple = tex_format_tuples[static_cast<u32>(pixel_format)]; const auto tuple = tex_format_tuples[static_cast<u32>(pixel_format)];
UNIMPLEMENTED_IF_MSG(tuple.format == vk::Format::eUndefined, UNIMPLEMENTED_IF_MSG(tuple.format == vk::Format::eUndefined,
"Unimplemented texture format with pixel format={} and component type={}", "Unimplemented texture format with pixel format={}",
static_cast<u32>(pixel_format), static_cast<u32>(component_type)); static_cast<u32>(pixel_format));
ASSERT_MSG(component_type == tuple.component_type, "Component type mismatch");
auto usage = vk::FormatFeatureFlagBits::eSampledImage | auto usage = vk::FormatFeatureFlagBits::eSampledImage |
vk::FormatFeatureFlagBits::eTransferDst | vk::FormatFeatureFlagBits::eTransferSrc; vk::FormatFeatureFlagBits::eTransferDst | vk::FormatFeatureFlagBits::eTransferSrc;

View File

@ -16,7 +16,6 @@ namespace Vulkan::MaxwellToVK {
using Maxwell = Tegra::Engines::Maxwell3D::Regs; using Maxwell = Tegra::Engines::Maxwell3D::Regs;
using PixelFormat = VideoCore::Surface::PixelFormat; using PixelFormat = VideoCore::Surface::PixelFormat;
using ComponentType = VideoCore::Surface::ComponentType;
namespace Sampler { namespace Sampler {
@ -31,7 +30,7 @@ vk::CompareOp DepthCompareFunction(Tegra::Texture::DepthCompareFunc depth_compar
} // namespace Sampler } // namespace Sampler
std::pair<vk::Format, bool> SurfaceFormat(const VKDevice& device, FormatType format_type, std::pair<vk::Format, bool> SurfaceFormat(const VKDevice& device, FormatType format_type,
PixelFormat pixel_format, ComponentType component_type); PixelFormat pixel_format);
vk::ShaderStageFlagBits ShaderStage(Maxwell::ShaderStage stage); vk::ShaderStageFlagBits ShaderStage(Maxwell::ShaderStage stage);

View File

@ -168,311 +168,6 @@ PixelFormat PixelFormatFromRenderTargetFormat(Tegra::RenderTargetFormat format)
} }
} }
PixelFormat PixelFormatFromTextureFormat(Tegra::Texture::TextureFormat format,
Tegra::Texture::ComponentType component_type,
bool is_srgb) {
// TODO(Subv): Properly implement this
switch (format) {
case Tegra::Texture::TextureFormat::A8R8G8B8:
if (is_srgb) {
return PixelFormat::RGBA8_SRGB;
}
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::ABGR8U;
case Tegra::Texture::ComponentType::SNORM:
return PixelFormat::ABGR8S;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::ABGR8UI;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::B5G6R5:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::B5G6R5U;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::A2B10G10R10:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::A2B10G10R10U;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::A1B5G5R5:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::A1B5G5R5U;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::A4B4G4R4:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::R4G4B4A4U;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R8:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::R8U;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::R8UI;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::G8R8:
// TextureFormat::G8R8 is actually ordered red then green, as such we can use
// PixelFormat::RG8U and PixelFormat::RG8S. This was tested with The Legend of Zelda: Breath
// of the Wild, which uses this format to render the hearts on the UI.
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::RG8U;
case Tegra::Texture::ComponentType::SNORM:
return PixelFormat::RG8S;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R16_G16_B16_A16:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::RGBA16U;
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::RGBA16F;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::RGBA16UI;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::BF10GF11RF11:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::R11FG11FB10F;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R32_G32_B32_A32:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::RGBA32F;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::RGBA32UI;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R32_G32:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::RG32F;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::RG32UI;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R32_G32_B32:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::RGB32F;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R16:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::R16F;
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::R16U;
case Tegra::Texture::ComponentType::SNORM:
return PixelFormat::R16S;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::R16UI;
case Tegra::Texture::ComponentType::SINT:
return PixelFormat::R16I;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::R32:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::R32F;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::R32UI;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::E5B9G9R9_SHAREDEXP:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::E5B9G9R9F;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::ZF32:
return PixelFormat::Z32F;
case Tegra::Texture::TextureFormat::Z16:
return PixelFormat::Z16;
case Tegra::Texture::TextureFormat::S8Z24:
return PixelFormat::S8Z24;
case Tegra::Texture::TextureFormat::ZF32_X24S8:
return PixelFormat::Z32FS8;
case Tegra::Texture::TextureFormat::DXT1:
return is_srgb ? PixelFormat::DXT1_SRGB : PixelFormat::DXT1;
case Tegra::Texture::TextureFormat::DXT23:
return is_srgb ? PixelFormat::DXT23_SRGB : PixelFormat::DXT23;
case Tegra::Texture::TextureFormat::DXT45:
return is_srgb ? PixelFormat::DXT45_SRGB : PixelFormat::DXT45;
case Tegra::Texture::TextureFormat::DXN1:
return PixelFormat::DXN1;
case Tegra::Texture::TextureFormat::DXN2:
switch (component_type) {
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::DXN2UNORM;
case Tegra::Texture::ComponentType::SNORM:
return PixelFormat::DXN2SNORM;
default:
break;
}
break;
case Tegra::Texture::TextureFormat::BC7U:
return is_srgb ? PixelFormat::BC7U_SRGB : PixelFormat::BC7U;
case Tegra::Texture::TextureFormat::BC6H_UF16:
return PixelFormat::BC6H_UF16;
case Tegra::Texture::TextureFormat::BC6H_SF16:
return PixelFormat::BC6H_SF16;
case Tegra::Texture::TextureFormat::ASTC_2D_4X4:
return is_srgb ? PixelFormat::ASTC_2D_4X4_SRGB : PixelFormat::ASTC_2D_4X4;
case Tegra::Texture::TextureFormat::ASTC_2D_5X4:
return is_srgb ? PixelFormat::ASTC_2D_5X4_SRGB : PixelFormat::ASTC_2D_5X4;
case Tegra::Texture::TextureFormat::ASTC_2D_5X5:
return is_srgb ? PixelFormat::ASTC_2D_5X5_SRGB : PixelFormat::ASTC_2D_5X5;
case Tegra::Texture::TextureFormat::ASTC_2D_8X8:
return is_srgb ? PixelFormat::ASTC_2D_8X8_SRGB : PixelFormat::ASTC_2D_8X8;
case Tegra::Texture::TextureFormat::ASTC_2D_8X5:
return is_srgb ? PixelFormat::ASTC_2D_8X5_SRGB : PixelFormat::ASTC_2D_8X5;
case Tegra::Texture::TextureFormat::ASTC_2D_10X8:
return is_srgb ? PixelFormat::ASTC_2D_10X8_SRGB : PixelFormat::ASTC_2D_10X8;
case Tegra::Texture::TextureFormat::ASTC_2D_6X6:
return is_srgb ? PixelFormat::ASTC_2D_6X6_SRGB : PixelFormat::ASTC_2D_6X6;
case Tegra::Texture::TextureFormat::ASTC_2D_10X10:
return is_srgb ? PixelFormat::ASTC_2D_10X10_SRGB : PixelFormat::ASTC_2D_10X10;
case Tegra::Texture::TextureFormat::ASTC_2D_12X12:
return is_srgb ? PixelFormat::ASTC_2D_12X12_SRGB : PixelFormat::ASTC_2D_12X12;
case Tegra::Texture::TextureFormat::ASTC_2D_8X6:
return is_srgb ? PixelFormat::ASTC_2D_8X6_SRGB : PixelFormat::ASTC_2D_8X6;
case Tegra::Texture::TextureFormat::ASTC_2D_6X5:
return is_srgb ? PixelFormat::ASTC_2D_6X5_SRGB : PixelFormat::ASTC_2D_6X5;
case Tegra::Texture::TextureFormat::R16_G16:
switch (component_type) {
case Tegra::Texture::ComponentType::FLOAT:
return PixelFormat::RG16F;
case Tegra::Texture::ComponentType::UNORM:
return PixelFormat::RG16;
case Tegra::Texture::ComponentType::SNORM:
return PixelFormat::RG16S;
case Tegra::Texture::ComponentType::UINT:
return PixelFormat::RG16UI;
case Tegra::Texture::ComponentType::SINT:
return PixelFormat::RG16I;
default:
break;
}
break;
default:
break;
}
LOG_CRITICAL(HW_GPU, "Unimplemented format={}, component_type={}", static_cast<u32>(format),
static_cast<u32>(component_type));
UNREACHABLE();
return PixelFormat::ABGR8U;
}
ComponentType ComponentTypeFromTexture(Tegra::Texture::ComponentType type) {
// TODO(Subv): Implement more component types
switch (type) {
case Tegra::Texture::ComponentType::UNORM:
return ComponentType::UNorm;
case Tegra::Texture::ComponentType::FLOAT:
return ComponentType::Float;
case Tegra::Texture::ComponentType::SNORM:
return ComponentType::SNorm;
case Tegra::Texture::ComponentType::UINT:
return ComponentType::UInt;
case Tegra::Texture::ComponentType::SINT:
return ComponentType::SInt;
default:
LOG_CRITICAL(HW_GPU, "Unimplemented component type={}", static_cast<u32>(type));
UNREACHABLE();
return ComponentType::UNorm;
}
}
ComponentType ComponentTypeFromRenderTarget(Tegra::RenderTargetFormat format) {
// TODO(Subv): Implement more render targets
switch (format) {
case Tegra::RenderTargetFormat::RGBA8_UNORM:
case Tegra::RenderTargetFormat::RGBA8_SRGB:
case Tegra::RenderTargetFormat::BGRA8_UNORM:
case Tegra::RenderTargetFormat::BGRA8_SRGB:
case Tegra::RenderTargetFormat::RGB10_A2_UNORM:
case Tegra::RenderTargetFormat::R8_UNORM:
case Tegra::RenderTargetFormat::RG16_UNORM:
case Tegra::RenderTargetFormat::R16_UNORM:
case Tegra::RenderTargetFormat::B5G6R5_UNORM:
case Tegra::RenderTargetFormat::BGR5A1_UNORM:
case Tegra::RenderTargetFormat::RG8_UNORM:
case Tegra::RenderTargetFormat::RGBA16_UNORM:
return ComponentType::UNorm;
case Tegra::RenderTargetFormat::RGBA8_SNORM:
case Tegra::RenderTargetFormat::RG16_SNORM:
case Tegra::RenderTargetFormat::R16_SNORM:
case Tegra::RenderTargetFormat::RG8_SNORM:
return ComponentType::SNorm;
case Tegra::RenderTargetFormat::RGBA16_FLOAT:
case Tegra::RenderTargetFormat::RGBX16_FLOAT:
case Tegra::RenderTargetFormat::R11G11B10_FLOAT:
case Tegra::RenderTargetFormat::RGBA32_FLOAT:
case Tegra::RenderTargetFormat::RG32_FLOAT:
case Tegra::RenderTargetFormat::RG16_FLOAT:
case Tegra::RenderTargetFormat::R16_FLOAT:
case Tegra::RenderTargetFormat::R32_FLOAT:
return ComponentType::Float;
case Tegra::RenderTargetFormat::RGBA32_UINT:
case Tegra::RenderTargetFormat::RGBA16_UINT:
case Tegra::RenderTargetFormat::RG16_UINT:
case Tegra::RenderTargetFormat::R8_UINT:
case Tegra::RenderTargetFormat::R16_UINT:
case Tegra::RenderTargetFormat::RG32_UINT:
case Tegra::RenderTargetFormat::R32_UINT:
case Tegra::RenderTargetFormat::RGBA8_UINT:
return ComponentType::UInt;
case Tegra::RenderTargetFormat::RG16_SINT:
case Tegra::RenderTargetFormat::R16_SINT:
return ComponentType::SInt;
default:
LOG_CRITICAL(HW_GPU, "Unimplemented format={}", static_cast<u32>(format));
UNREACHABLE();
return ComponentType::UNorm;
}
}
PixelFormat PixelFormatFromGPUPixelFormat(Tegra::FramebufferConfig::PixelFormat format) { PixelFormat PixelFormatFromGPUPixelFormat(Tegra::FramebufferConfig::PixelFormat format) {
switch (format) { switch (format) {
case Tegra::FramebufferConfig::PixelFormat::ABGR8: case Tegra::FramebufferConfig::PixelFormat::ABGR8:
@ -487,22 +182,6 @@ PixelFormat PixelFormatFromGPUPixelFormat(Tegra::FramebufferConfig::PixelFormat
} }
} }
ComponentType ComponentTypeFromDepthFormat(Tegra::DepthFormat format) {
switch (format) {
case Tegra::DepthFormat::Z16_UNORM:
case Tegra::DepthFormat::S8_Z24_UNORM:
case Tegra::DepthFormat::Z24_S8_UNORM:
return ComponentType::UNorm;
case Tegra::DepthFormat::Z32_FLOAT:
case Tegra::DepthFormat::Z32_S8_X24_FLOAT:
return ComponentType::Float;
default:
LOG_CRITICAL(HW_GPU, "Unimplemented format={}", static_cast<u32>(format));
UNREACHABLE();
return ComponentType::UNorm;
}
}
SurfaceType GetFormatType(PixelFormat pixel_format) { SurfaceType GetFormatType(PixelFormat pixel_format) {
if (static_cast<std::size_t>(pixel_format) < if (static_cast<std::size_t>(pixel_format) <
static_cast<std::size_t>(PixelFormat::MaxColorFormat)) { static_cast<std::size_t>(PixelFormat::MaxColorFormat)) {

View File

@ -106,18 +106,8 @@ enum class PixelFormat {
Max = MaxDepthStencilFormat, Max = MaxDepthStencilFormat,
Invalid = 255, Invalid = 255,
}; };
static constexpr std::size_t MaxPixelFormat = static_cast<std::size_t>(PixelFormat::Max); static constexpr std::size_t MaxPixelFormat = static_cast<std::size_t>(PixelFormat::Max);
enum class ComponentType {
Invalid = 0,
SNorm = 1,
UNorm = 2,
SInt = 3,
UInt = 4,
Float = 5,
};
enum class SurfaceType { enum class SurfaceType {
ColorTexture = 0, ColorTexture = 0,
Depth = 1, Depth = 1,
@ -609,18 +599,8 @@ PixelFormat PixelFormatFromDepthFormat(Tegra::DepthFormat format);
PixelFormat PixelFormatFromRenderTargetFormat(Tegra::RenderTargetFormat format); PixelFormat PixelFormatFromRenderTargetFormat(Tegra::RenderTargetFormat format);
PixelFormat PixelFormatFromTextureFormat(Tegra::Texture::TextureFormat format,
Tegra::Texture::ComponentType component_type,
bool is_srgb);
ComponentType ComponentTypeFromTexture(Tegra::Texture::ComponentType type);
ComponentType ComponentTypeFromRenderTarget(Tegra::RenderTargetFormat format);
PixelFormat PixelFormatFromGPUPixelFormat(Tegra::FramebufferConfig::PixelFormat format); PixelFormat PixelFormatFromGPUPixelFormat(Tegra::FramebufferConfig::PixelFormat format);
ComponentType ComponentTypeFromDepthFormat(Tegra::DepthFormat format);
SurfaceType GetFormatType(PixelFormat pixel_format); SurfaceType GetFormatType(PixelFormat pixel_format);
bool IsPixelFormatASTC(PixelFormat format); bool IsPixelFormatASTC(PixelFormat format);

View File

@ -0,0 +1,208 @@
// Copyright 2019 yuzu Emulator Project
// Licensed under GPLv2 or any later version
// Refer to the license.txt file included.
#include <array>
#include "common/common_types.h"
#include "common/logging/log.h"
#include "video_core/texture_cache/format_lookup_table.h"
namespace VideoCommon {
using Tegra::Texture::ComponentType;
using Tegra::Texture::TextureFormat;
using VideoCore::Surface::PixelFormat;
namespace {
constexpr auto SNORM = ComponentType::SNORM;
constexpr auto UNORM = ComponentType::UNORM;
constexpr auto SINT = ComponentType::SINT;
constexpr auto UINT = ComponentType::UINT;
constexpr auto SNORM_FORCE_FP16 = ComponentType::SNORM_FORCE_FP16;
constexpr auto UNORM_FORCE_FP16 = ComponentType::UNORM_FORCE_FP16;
constexpr auto FLOAT = ComponentType::FLOAT;
constexpr bool C = false; // Normal color
constexpr bool S = true; // Srgb
struct Table {
constexpr Table(TextureFormat texture_format, bool is_srgb, ComponentType red_component,
ComponentType green_component, ComponentType blue_component,
ComponentType alpha_component, PixelFormat pixel_format)
: texture_format{texture_format}, pixel_format{pixel_format}, red_component{red_component},
green_component{green_component}, blue_component{blue_component},
alpha_component{alpha_component}, is_srgb{is_srgb} {}
TextureFormat texture_format;
PixelFormat pixel_format;
ComponentType red_component;
ComponentType green_component;
ComponentType blue_component;
ComponentType alpha_component;
bool is_srgb;
};
constexpr std::array<Table, 74> DefinitionTable = {{
{TextureFormat::A8R8G8B8, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ABGR8U},
{TextureFormat::A8R8G8B8, C, SNORM, SNORM, SNORM, SNORM, PixelFormat::ABGR8S},
{TextureFormat::A8R8G8B8, C, UINT, UINT, UINT, UINT, PixelFormat::ABGR8UI},
{TextureFormat::A8R8G8B8, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::RGBA8_SRGB},
{TextureFormat::B5G6R5, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::B5G6R5U},
{TextureFormat::A2B10G10R10, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::A2B10G10R10U},
{TextureFormat::A1B5G5R5, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::A1B5G5R5U},
{TextureFormat::A4B4G4R4, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::R4G4B4A4U},
{TextureFormat::R8, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::R8U},
{TextureFormat::R8, C, UINT, UINT, UINT, UINT, PixelFormat::R8UI},
{TextureFormat::G8R8, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::RG8U},
{TextureFormat::G8R8, C, SNORM, SNORM, SNORM, SNORM, PixelFormat::RG8S},
{TextureFormat::R16_G16_B16_A16, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::RGBA16U},
{TextureFormat::R16_G16_B16_A16, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::RGBA16F},
{TextureFormat::R16_G16_B16_A16, C, UINT, UINT, UINT, UINT, PixelFormat::RGBA16UI},
{TextureFormat::R16_G16, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::RG16F},
{TextureFormat::R16_G16, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::RG16},
{TextureFormat::R16_G16, C, SNORM, SNORM, SNORM, SNORM, PixelFormat::RG16S},
{TextureFormat::R16_G16, C, UINT, UINT, UINT, UINT, PixelFormat::RG16UI},
{TextureFormat::R16_G16, C, SINT, SINT, SINT, SINT, PixelFormat::RG16I},
{TextureFormat::R16, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::R16F},
{TextureFormat::R16, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::R16U},
{TextureFormat::R16, C, SNORM, SNORM, SNORM, SNORM, PixelFormat::R16S},
{TextureFormat::R16, C, UINT, UINT, UINT, UINT, PixelFormat::R16UI},
{TextureFormat::R16, C, SINT, SINT, SINT, SINT, PixelFormat::R16I},
{TextureFormat::BF10GF11RF11, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::R11FG11FB10F},
{TextureFormat::R32_G32_B32_A32, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::RGBA32F},
{TextureFormat::R32_G32_B32_A32, C, UINT, UINT, UINT, UINT, PixelFormat::RGBA32UI},
{TextureFormat::R32_G32_B32, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::RGB32F},
{TextureFormat::R32_G32, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::RG32F},
{TextureFormat::R32_G32, C, UINT, UINT, UINT, UINT, PixelFormat::RG32UI},
{TextureFormat::R32, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::R32F},
{TextureFormat::R32, C, UINT, UINT, UINT, UINT, PixelFormat::R32UI},
{TextureFormat::E5B9G9R9_SHAREDEXP, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::E5B9G9R9F},
{TextureFormat::ZF32, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::Z32F},
{TextureFormat::Z16, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::Z16},
{TextureFormat::S8Z24, C, UINT, UNORM, UNORM, UNORM, PixelFormat::S8Z24},
{TextureFormat::ZF32_X24S8, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::Z32FS8},
{TextureFormat::DXT1, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXT1},
{TextureFormat::DXT1, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXT1_SRGB},
{TextureFormat::DXT23, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXT23},
{TextureFormat::DXT23, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXT23_SRGB},
{TextureFormat::DXT45, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXT45},
{TextureFormat::DXT45, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXT45_SRGB},
// TODO: Use a different pixel format for SNORM
{TextureFormat::DXN1, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXN1},
{TextureFormat::DXN1, C, SNORM, SNORM, SNORM, SNORM, PixelFormat::DXN1},
{TextureFormat::DXN2, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::DXN2UNORM},
{TextureFormat::DXN2, C, SNORM, SNORM, SNORM, SNORM, PixelFormat::DXN2SNORM},
{TextureFormat::BC7U, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::BC7U},
{TextureFormat::BC7U, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::BC7U_SRGB},
{TextureFormat::BC6H_SF16, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::BC6H_SF16},
{TextureFormat::BC6H_UF16, C, FLOAT, FLOAT, FLOAT, FLOAT, PixelFormat::BC6H_UF16},
{TextureFormat::ASTC_2D_4X4, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_4X4},
{TextureFormat::ASTC_2D_4X4, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_4X4_SRGB},
{TextureFormat::ASTC_2D_5X4, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_5X4},
{TextureFormat::ASTC_2D_5X4, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_5X4_SRGB},
{TextureFormat::ASTC_2D_5X5, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_5X5},
{TextureFormat::ASTC_2D_5X5, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_5X5_SRGB},
{TextureFormat::ASTC_2D_8X8, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_8X8},
{TextureFormat::ASTC_2D_8X8, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_8X8_SRGB},
{TextureFormat::ASTC_2D_8X5, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_8X5},
{TextureFormat::ASTC_2D_8X5, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_8X5_SRGB},
{TextureFormat::ASTC_2D_10X8, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_10X8},
{TextureFormat::ASTC_2D_10X8, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_10X8_SRGB},
{TextureFormat::ASTC_2D_6X6, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_6X6},
{TextureFormat::ASTC_2D_6X6, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_6X6_SRGB},
{TextureFormat::ASTC_2D_10X10, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_10X10},
{TextureFormat::ASTC_2D_10X10, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_10X10_SRGB},
{TextureFormat::ASTC_2D_12X12, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_12X12},
{TextureFormat::ASTC_2D_12X12, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_12X12_SRGB},
{TextureFormat::ASTC_2D_8X6, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_8X6},
{TextureFormat::ASTC_2D_8X6, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_8X6_SRGB},
{TextureFormat::ASTC_2D_6X5, C, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_6X5},
{TextureFormat::ASTC_2D_6X5, S, UNORM, UNORM, UNORM, UNORM, PixelFormat::ASTC_2D_6X5_SRGB},
}};
} // Anonymous namespace
FormatLookupTable::FormatLookupTable() {
table.fill(static_cast<u8>(PixelFormat::Invalid));
for (const auto& entry : DefinitionTable) {
table[CalculateIndex(entry.texture_format, entry.is_srgb != 0, entry.red_component,
entry.green_component, entry.blue_component, entry.alpha_component)] =
static_cast<u8>(entry.pixel_format);
}
}
PixelFormat FormatLookupTable::GetPixelFormat(TextureFormat format, bool is_srgb,
ComponentType red_component,
ComponentType green_component,
ComponentType blue_component,
ComponentType alpha_component) const noexcept {
const auto pixel_format = static_cast<PixelFormat>(table[CalculateIndex(
format, is_srgb, red_component, green_component, blue_component, alpha_component)]);
// [[likely]]
if (pixel_format != PixelFormat::Invalid) {
return pixel_format;
}
UNIMPLEMENTED_MSG("texture format={} srgb={} components={{{} {} {} {}}}",
static_cast<int>(format), is_srgb, static_cast<int>(red_component),
static_cast<int>(green_component), static_cast<int>(blue_component),
static_cast<int>(alpha_component));
return PixelFormat::ABGR8U;
}
void FormatLookupTable::Set(TextureFormat format, bool is_srgb, ComponentType red_component,
ComponentType green_component, ComponentType blue_component,
ComponentType alpha_component, PixelFormat pixel_format) {}
std::size_t FormatLookupTable::CalculateIndex(TextureFormat format, bool is_srgb,
ComponentType red_component,
ComponentType green_component,
ComponentType blue_component,
ComponentType alpha_component) noexcept {
const auto format_index = static_cast<std::size_t>(format);
const auto red_index = static_cast<std::size_t>(red_component);
const auto green_index = static_cast<std::size_t>(red_component);
const auto blue_index = static_cast<std::size_t>(red_component);
const auto alpha_index = static_cast<std::size_t>(red_component);
const std::size_t srgb_index = is_srgb ? 1 : 0;
return format_index * PerFormat +
srgb_index * PerComponent * PerComponent * PerComponent * PerComponent +
alpha_index * PerComponent * PerComponent * PerComponent +
blue_index * PerComponent * PerComponent + green_index * PerComponent + red_index;
}
} // namespace VideoCommon

View File

@ -0,0 +1,51 @@
// Copyright 2019 yuzu Emulator Project
// Licensed under GPLv2 or any later version
// Refer to the license.txt file included.
#pragma once
#include <array>
#include <limits>
#include "video_core/surface.h"
#include "video_core/textures/texture.h"
namespace VideoCommon {
class FormatLookupTable {
public:
explicit FormatLookupTable();
VideoCore::Surface::PixelFormat GetPixelFormat(
Tegra::Texture::TextureFormat format, bool is_srgb,
Tegra::Texture::ComponentType red_component, Tegra::Texture::ComponentType green_component,
Tegra::Texture::ComponentType blue_component,
Tegra::Texture::ComponentType alpha_component) const noexcept;
private:
static_assert(VideoCore::Surface::MaxPixelFormat <= std::numeric_limits<u8>::max());
static constexpr std::size_t NumTextureFormats = 128;
static constexpr std::size_t PerComponent = 8;
static constexpr std::size_t PerComponents2 = PerComponent * PerComponent;
static constexpr std::size_t PerComponents3 = PerComponents2 * PerComponent;
static constexpr std::size_t PerComponents4 = PerComponents3 * PerComponent;
static constexpr std::size_t PerFormat = PerComponents4 * 2;
static std::size_t CalculateIndex(Tegra::Texture::TextureFormat format, bool is_srgb,
Tegra::Texture::ComponentType red_component,
Tegra::Texture::ComponentType green_component,
Tegra::Texture::ComponentType blue_component,
Tegra::Texture::ComponentType alpha_component) noexcept;
void Set(Tegra::Texture::TextureFormat format, bool is_srgb,
Tegra::Texture::ComponentType red_component,
Tegra::Texture::ComponentType green_component,
Tegra::Texture::ComponentType blue_component,
Tegra::Texture::ComponentType alpha_component,
VideoCore::Surface::PixelFormat pixel_format);
std::array<u8, NumTextureFormats * PerFormat> table;
};
} // namespace VideoCommon

View File

@ -2,24 +2,23 @@
// Licensed under GPLv2 or any later version // Licensed under GPLv2 or any later version
// Refer to the license.txt file included. // Refer to the license.txt file included.
#include <map> #include <algorithm>
#include <string>
#include <tuple>
#include "common/alignment.h" #include "common/alignment.h"
#include "common/bit_util.h" #include "common/bit_util.h"
#include "core/core.h" #include "core/core.h"
#include "video_core/engines/shader_bytecode.h" #include "video_core/engines/shader_bytecode.h"
#include "video_core/surface.h" #include "video_core/surface.h"
#include "video_core/texture_cache/format_lookup_table.h"
#include "video_core/texture_cache/surface_params.h" #include "video_core/texture_cache/surface_params.h"
namespace VideoCommon { namespace VideoCommon {
using VideoCore::Surface::ComponentTypeFromDepthFormat;
using VideoCore::Surface::ComponentTypeFromRenderTarget;
using VideoCore::Surface::ComponentTypeFromTexture;
using VideoCore::Surface::PixelFormat; using VideoCore::Surface::PixelFormat;
using VideoCore::Surface::PixelFormatFromDepthFormat; using VideoCore::Surface::PixelFormatFromDepthFormat;
using VideoCore::Surface::PixelFormatFromRenderTargetFormat; using VideoCore::Surface::PixelFormatFromRenderTargetFormat;
using VideoCore::Surface::PixelFormatFromTextureFormat;
using VideoCore::Surface::SurfaceTarget; using VideoCore::Surface::SurfaceTarget;
using VideoCore::Surface::SurfaceTargetFromTextureType; using VideoCore::Surface::SurfaceTargetFromTextureType;
using VideoCore::Surface::SurfaceType; using VideoCore::Surface::SurfaceType;
@ -69,7 +68,8 @@ constexpr u32 GetMipmapSize(bool uncompressed, u32 mip_size, u32 tile) {
} // Anonymous namespace } // Anonymous namespace
SurfaceParams SurfaceParams::CreateForTexture(const Tegra::Texture::TICEntry& tic, SurfaceParams SurfaceParams::CreateForTexture(const FormatLookupTable& lookup_table,
const Tegra::Texture::TICEntry& tic,
const VideoCommon::Shader::Sampler& entry) { const VideoCommon::Shader::Sampler& entry) {
SurfaceParams params; SurfaceParams params;
params.is_tiled = tic.IsTiled(); params.is_tiled = tic.IsTiled();
@ -78,8 +78,8 @@ SurfaceParams SurfaceParams::CreateForTexture(const Tegra::Texture::TICEntry& ti
params.block_height = params.is_tiled ? tic.BlockHeight() : 0, params.block_height = params.is_tiled ? tic.BlockHeight() : 0,
params.block_depth = params.is_tiled ? tic.BlockDepth() : 0, params.block_depth = params.is_tiled ? tic.BlockDepth() : 0,
params.tile_width_spacing = params.is_tiled ? (1 << tic.tile_width_spacing.Value()) : 1; params.tile_width_spacing = params.is_tiled ? (1 << tic.tile_width_spacing.Value()) : 1;
params.pixel_format = params.pixel_format = lookup_table.GetPixelFormat(
PixelFormatFromTextureFormat(tic.format, tic.r_type.Value(), params.srgb_conversion); tic.format, params.srgb_conversion, tic.r_type, tic.g_type, tic.b_type, tic.a_type);
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
if (entry.IsShadow() && params.type == SurfaceType::ColorTexture) { if (entry.IsShadow() && params.type == SurfaceType::ColorTexture) {
switch (params.pixel_format) { switch (params.pixel_format) {
@ -99,7 +99,6 @@ SurfaceParams SurfaceParams::CreateForTexture(const Tegra::Texture::TICEntry& ti
} }
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
} }
params.component_type = ComponentTypeFromTexture(tic.r_type.Value());
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
// TODO: on 1DBuffer we should use the tic info. // TODO: on 1DBuffer we should use the tic info.
if (tic.IsBuffer()) { if (tic.IsBuffer()) {
@ -128,7 +127,8 @@ SurfaceParams SurfaceParams::CreateForTexture(const Tegra::Texture::TICEntry& ti
return params; return params;
} }
SurfaceParams SurfaceParams::CreateForImage(const Tegra::Texture::TICEntry& tic, SurfaceParams SurfaceParams::CreateForImage(const FormatLookupTable& lookup_table,
const Tegra::Texture::TICEntry& tic,
const VideoCommon::Shader::Image& entry) { const VideoCommon::Shader::Image& entry) {
SurfaceParams params; SurfaceParams params;
params.is_tiled = tic.IsTiled(); params.is_tiled = tic.IsTiled();
@ -137,10 +137,9 @@ SurfaceParams SurfaceParams::CreateForImage(const Tegra::Texture::TICEntry& tic,
params.block_height = params.is_tiled ? tic.BlockHeight() : 0, params.block_height = params.is_tiled ? tic.BlockHeight() : 0,
params.block_depth = params.is_tiled ? tic.BlockDepth() : 0, params.block_depth = params.is_tiled ? tic.BlockDepth() : 0,
params.tile_width_spacing = params.is_tiled ? (1 << tic.tile_width_spacing.Value()) : 1; params.tile_width_spacing = params.is_tiled ? (1 << tic.tile_width_spacing.Value()) : 1;
params.pixel_format = params.pixel_format = lookup_table.GetPixelFormat(
PixelFormatFromTextureFormat(tic.format, tic.r_type.Value(), params.srgb_conversion); tic.format, params.srgb_conversion, tic.r_type, tic.g_type, tic.b_type, tic.a_type);
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
params.component_type = ComponentTypeFromTexture(tic.r_type.Value());
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
params.target = ImageTypeToSurfaceTarget(entry.GetType()); params.target = ImageTypeToSurfaceTarget(entry.GetType());
// TODO: on 1DBuffer we should use the tic info. // TODO: on 1DBuffer we should use the tic info.
@ -181,7 +180,6 @@ SurfaceParams SurfaceParams::CreateForDepthBuffer(
params.block_depth = std::min(block_depth, 5U); params.block_depth = std::min(block_depth, 5U);
params.tile_width_spacing = 1; params.tile_width_spacing = 1;
params.pixel_format = PixelFormatFromDepthFormat(format); params.pixel_format = PixelFormatFromDepthFormat(format);
params.component_type = ComponentTypeFromDepthFormat(format);
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
params.width = zeta_width; params.width = zeta_width;
params.height = zeta_height; params.height = zeta_height;
@ -206,7 +204,6 @@ SurfaceParams SurfaceParams::CreateForFramebuffer(Core::System& system, std::siz
params.block_depth = config.memory_layout.block_depth; params.block_depth = config.memory_layout.block_depth;
params.tile_width_spacing = 1; params.tile_width_spacing = 1;
params.pixel_format = PixelFormatFromRenderTargetFormat(config.format); params.pixel_format = PixelFormatFromRenderTargetFormat(config.format);
params.component_type = ComponentTypeFromRenderTarget(config.format);
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
if (params.is_tiled) { if (params.is_tiled) {
params.pitch = 0; params.pitch = 0;
@ -236,7 +233,6 @@ SurfaceParams SurfaceParams::CreateForFermiCopySurface(
params.block_depth = params.is_tiled ? std::min(config.BlockDepth(), 5U) : 0, params.block_depth = params.is_tiled ? std::min(config.BlockDepth(), 5U) : 0,
params.tile_width_spacing = 1; params.tile_width_spacing = 1;
params.pixel_format = PixelFormatFromRenderTargetFormat(config.format); params.pixel_format = PixelFormatFromRenderTargetFormat(config.format);
params.component_type = ComponentTypeFromRenderTarget(config.format);
params.type = GetFormatType(params.pixel_format); params.type = GetFormatType(params.pixel_format);
params.width = config.width; params.width = config.width;
params.height = config.height; params.height = config.height;
@ -355,10 +351,10 @@ std::size_t SurfaceParams::GetInnerMipmapMemorySize(u32 level, bool as_host_size
bool SurfaceParams::operator==(const SurfaceParams& rhs) const { bool SurfaceParams::operator==(const SurfaceParams& rhs) const {
return std::tie(is_tiled, block_width, block_height, block_depth, tile_width_spacing, width, return std::tie(is_tiled, block_width, block_height, block_depth, tile_width_spacing, width,
height, depth, pitch, num_levels, pixel_format, component_type, type, target) == height, depth, pitch, num_levels, pixel_format, type, target) ==
std::tie(rhs.is_tiled, rhs.block_width, rhs.block_height, rhs.block_depth, std::tie(rhs.is_tiled, rhs.block_width, rhs.block_height, rhs.block_depth,
rhs.tile_width_spacing, rhs.width, rhs.height, rhs.depth, rhs.pitch, rhs.tile_width_spacing, rhs.width, rhs.height, rhs.depth, rhs.pitch,
rhs.num_levels, rhs.pixel_format, rhs.component_type, rhs.type, rhs.target); rhs.num_levels, rhs.pixel_format, rhs.type, rhs.target);
} }
std::string SurfaceParams::TargetName() const { std::string SurfaceParams::TargetName() const {

View File

@ -16,16 +16,20 @@
namespace VideoCommon { namespace VideoCommon {
class FormatLookupTable;
using VideoCore::Surface::SurfaceCompression; using VideoCore::Surface::SurfaceCompression;
class SurfaceParams { class SurfaceParams {
public: public:
/// Creates SurfaceCachedParams from a texture configuration. /// Creates SurfaceCachedParams from a texture configuration.
static SurfaceParams CreateForTexture(const Tegra::Texture::TICEntry& tic, static SurfaceParams CreateForTexture(const FormatLookupTable& lookup_table,
const Tegra::Texture::TICEntry& tic,
const VideoCommon::Shader::Sampler& entry); const VideoCommon::Shader::Sampler& entry);
/// Creates SurfaceCachedParams from an image configuration. /// Creates SurfaceCachedParams from an image configuration.
static SurfaceParams CreateForImage(const Tegra::Texture::TICEntry& tic, static SurfaceParams CreateForImage(const FormatLookupTable& lookup_table,
const Tegra::Texture::TICEntry& tic,
const VideoCommon::Shader::Image& entry); const VideoCommon::Shader::Image& entry);
/// Creates SurfaceCachedParams for a depth buffer configuration. /// Creates SurfaceCachedParams for a depth buffer configuration.
@ -248,7 +252,6 @@ public:
u32 num_levels; u32 num_levels;
u32 emulated_levels; u32 emulated_levels;
VideoCore::Surface::PixelFormat pixel_format; VideoCore::Surface::PixelFormat pixel_format;
VideoCore::Surface::ComponentType component_type;
VideoCore::Surface::SurfaceType type; VideoCore::Surface::SurfaceType type;
VideoCore::Surface::SurfaceTarget target; VideoCore::Surface::SurfaceTarget target;

View File

@ -29,6 +29,7 @@
#include "video_core/rasterizer_interface.h" #include "video_core/rasterizer_interface.h"
#include "video_core/surface.h" #include "video_core/surface.h"
#include "video_core/texture_cache/copy_params.h" #include "video_core/texture_cache/copy_params.h"
#include "video_core/texture_cache/format_lookup_table.h"
#include "video_core/texture_cache/surface_base.h" #include "video_core/texture_cache/surface_base.h"
#include "video_core/texture_cache/surface_params.h" #include "video_core/texture_cache/surface_params.h"
#include "video_core/texture_cache/surface_view.h" #include "video_core/texture_cache/surface_view.h"
@ -96,7 +97,7 @@ public:
if (!gpu_addr) { if (!gpu_addr) {
return {}; return {};
} }
const auto params{SurfaceParams::CreateForTexture(tic, entry)}; const auto params{SurfaceParams::CreateForTexture(format_lookup_table, tic, entry)};
const auto [surface, view] = GetSurface(gpu_addr, params, true, false); const auto [surface, view] = GetSurface(gpu_addr, params, true, false);
if (guard_samplers) { if (guard_samplers) {
sampled_textures.push_back(surface); sampled_textures.push_back(surface);
@ -111,7 +112,7 @@ public:
if (!gpu_addr) { if (!gpu_addr) {
return {}; return {};
} }
const auto params{SurfaceParams::CreateForImage(tic, entry)}; const auto params{SurfaceParams::CreateForImage(format_lookup_table, tic, entry)};
const auto [surface, view] = GetSurface(gpu_addr, params, true, false); const auto [surface, view] = GetSurface(gpu_addr, params, true, false);
if (guard_samplers) { if (guard_samplers) {
sampled_textures.push_back(surface); sampled_textures.push_back(surface);
@ -485,15 +486,13 @@ private:
GetSiblingFormat(cr_params.pixel_format) == params.pixel_format) { GetSiblingFormat(cr_params.pixel_format) == params.pixel_format) {
SurfaceParams new_params = params; SurfaceParams new_params = params;
new_params.pixel_format = cr_params.pixel_format; new_params.pixel_format = cr_params.pixel_format;
new_params.component_type = cr_params.component_type;
new_params.type = cr_params.type; new_params.type = cr_params.type;
new_surface = GetUncachedSurface(gpu_addr, new_params); new_surface = GetUncachedSurface(gpu_addr, new_params);
} else { } else {
new_surface = GetUncachedSurface(gpu_addr, params); new_surface = GetUncachedSurface(gpu_addr, params);
} }
const auto& final_params = new_surface->GetSurfaceParams(); const auto& final_params = new_surface->GetSurfaceParams();
if (cr_params.type != final_params.type || if (cr_params.type != final_params.type) {
(cr_params.component_type != final_params.component_type)) {
BufferCopy(current_surface, new_surface); BufferCopy(current_surface, new_surface);
} else { } else {
std::vector<CopyParams> bricks = current_surface->BreakDown(final_params); std::vector<CopyParams> bricks = current_surface->BreakDown(final_params);
@ -835,12 +834,11 @@ private:
} }
} }
const auto inherit_format = ([](SurfaceParams& to, TSurface from) { const auto inherit_format = [](SurfaceParams& to, TSurface from) {
const SurfaceParams& params = from->GetSurfaceParams(); const SurfaceParams& params = from->GetSurfaceParams();
to.pixel_format = params.pixel_format; to.pixel_format = params.pixel_format;
to.component_type = params.component_type;
to.type = params.type; to.type = params.type;
}); };
// Now we got the cases where one or both is Depth and the other is not known // Now we got the cases where one or both is Depth and the other is not known
if (!incomplete_src) { if (!incomplete_src) {
inherit_format(src_params, deduced_src.surface); inherit_format(src_params, deduced_src.surface);
@ -956,6 +954,8 @@ private:
VideoCore::RasterizerInterface& rasterizer; VideoCore::RasterizerInterface& rasterizer;
FormatLookupTable format_lookup_table;
u64 ticks{}; u64 ticks{};
// Guards the cache for protection conflicts. // Guards the cache for protection conflicts.