mesa/main: support astc_hdr formats

This gets a bit annoying because Vulkan has separate format enums for
the LDR and HDR ASTC formats, whereas OpenGL uses the same format enums,
but allows additional color-endpoint encodings when HDR is supported.

Either of these behaviors makes sense on their own, but since we share
pipe_format definitions between the APIs, we need to resolve this. This
patch does that by checking if the HDR extension is supported, and
always using the HDR formats. This works, because the HDR formats are
supersets of the LDR formats in terms of features.

Not all of the LDR formats have HDR variants, either because they're
sRGB or 3D, which either is nonsensical or just not exposed by the
ASTC HDR extensions. So we only need to map a subset of the ASTC formats
with this HDR-aware mapping.

Reviewed-by: Alyssa Rosenzweig <alyssa@rosenzweig.io>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/35132>
This commit is contained in:
Erik Faye-Lund 2025-05-23 11:43:23 +02:00 committed by Marge Bot
parent 6cd898dbc2
commit fd42cdfc01
9 changed files with 106 additions and 41 deletions

View file

@ -1574,7 +1574,7 @@ _mesa_GetInternalformativ(GLenum target, GLenum internalformat, GLenum pname,
mesa_format mesaformat;
GLint block_size;
mesaformat = _mesa_glenum_to_compressed_format(internalformat);
mesaformat = _mesa_glenum_to_compressed_format(ctx, internalformat);
if (mesaformat == MESA_FORMAT_NONE)
goto end;

View file

@ -335,6 +335,21 @@ MESA_FORMAT_RGBA_ASTC_10x10 , astc ,10,10, 1, x128, , ,
MESA_FORMAT_RGBA_ASTC_12x10 , astc ,12,10, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_12x12 , astc ,12,12, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_4x4_FLOAT , astc , 4, 4, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_5x4_FLOAT , astc , 5, 4, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_5x5_FLOAT , astc , 5, 5, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_6x5_FLOAT , astc , 6, 5, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_6x6_FLOAT , astc , 6, 6, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_8x5_FLOAT , astc , 8, 5, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_8x6_FLOAT , astc , 8, 6, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_8x8_FLOAT , astc , 8, 8, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_10x5_FLOAT , astc ,10, 5, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_10x6_FLOAT , astc ,10, 6, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_10x8_FLOAT , astc ,10, 8, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_10x10_FLOAT , astc ,10,10, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_12x10_FLOAT , astc ,12,10, 1, x128, , , , xyzw, rgb
MESA_FORMAT_RGBA_ASTC_12x12_FLOAT , astc ,12,12, 1, x128, , , , xyzw, rgb
MESA_FORMAT_SRGB8_ALPHA8_ASTC_4x4 , astc , 4, 4, 1, x128, , , , xyzw, srgb
MESA_FORMAT_SRGB8_ALPHA8_ASTC_5x4 , astc , 5, 4, 1, x128, , , , xyzw, srgb
MESA_FORMAT_SRGB8_ALPHA8_ASTC_5x5 , astc , 5, 5, 1, x128, , , , xyzw, srgb

Can't render this file because it contains an unexpected character in line 9 and column 3.

View file

@ -598,6 +598,22 @@ typedef enum pipe_format mesa_format;
#define MESA_FORMAT_SRGB8_ALPHA8_ASTC_10x10 PIPE_FORMAT_ASTC_10x10_SRGB
#define MESA_FORMAT_SRGB8_ALPHA8_ASTC_12x10 PIPE_FORMAT_ASTC_12x10_SRGB
#define MESA_FORMAT_SRGB8_ALPHA8_ASTC_12x12 PIPE_FORMAT_ASTC_12x12_SRGB
#define MESA_FORMAT_RGBA_ASTC_4x4_FLOAT PIPE_FORMAT_ASTC_4x4_FLOAT
#define MESA_FORMAT_RGBA_ASTC_5x4_FLOAT PIPE_FORMAT_ASTC_5x4_FLOAT
#define MESA_FORMAT_RGBA_ASTC_5x5_FLOAT PIPE_FORMAT_ASTC_5x5_FLOAT
#define MESA_FORMAT_RGBA_ASTC_6x5_FLOAT PIPE_FORMAT_ASTC_6x5_FLOAT
#define MESA_FORMAT_RGBA_ASTC_6x6_FLOAT PIPE_FORMAT_ASTC_6x6_FLOAT
#define MESA_FORMAT_RGBA_ASTC_8x5_FLOAT PIPE_FORMAT_ASTC_8x5_FLOAT
#define MESA_FORMAT_RGBA_ASTC_8x6_FLOAT PIPE_FORMAT_ASTC_8x6_FLOAT
#define MESA_FORMAT_RGBA_ASTC_8x8_FLOAT PIPE_FORMAT_ASTC_8x8_FLOAT
#define MESA_FORMAT_RGBA_ASTC_10x5_FLOAT PIPE_FORMAT_ASTC_10x5_FLOAT
#define MESA_FORMAT_RGBA_ASTC_10x6_FLOAT PIPE_FORMAT_ASTC_10x6_FLOAT
#define MESA_FORMAT_RGBA_ASTC_10x8_FLOAT PIPE_FORMAT_ASTC_10x8_FLOAT
#define MESA_FORMAT_RGBA_ASTC_10x10_FLOAT PIPE_FORMAT_ASTC_10x10_FLOAT
#define MESA_FORMAT_RGBA_ASTC_12x10_FLOAT PIPE_FORMAT_ASTC_12x10_FLOAT
#define MESA_FORMAT_RGBA_ASTC_12x12_FLOAT PIPE_FORMAT_ASTC_12x12_FLOAT
#define MESA_FORMAT_RGBA_ASTC_3x3x3 PIPE_FORMAT_ASTC_3x3x3
#define MESA_FORMAT_RGBA_ASTC_4x3x3 PIPE_FORMAT_ASTC_4x3x3
#define MESA_FORMAT_RGBA_ASTC_4x4x3 PIPE_FORMAT_ASTC_4x4x3

View file

@ -1333,7 +1333,7 @@ _mesa_is_generic_compressed_format(const struct gl_context *ctx,
GLboolean
_mesa_is_compressed_format(const struct gl_context *ctx, GLenum format)
{
mesa_format m_format = _mesa_glenum_to_compressed_format(format);
mesa_format m_format = _mesa_glenum_to_compressed_format(ctx, format);
/* Some formats in this switch have an equivalent mesa_format_layout
* to the compressed formats in the layout switch below and thus

View file

@ -477,12 +477,43 @@ _mesa_get_compressed_formats(struct gl_context *ctx, GLint *formats)
return n;
}
static mesa_format
_mesa_astc_ldrhdr_glenum_to_format(const struct gl_context *ctx, GLenum format)
{
bool has_hdr = _mesa_has_KHR_texture_compression_astc_hdr(ctx);
switch (format) {
#define CASE(x) \
case GL_COMPRESSED_RGBA_ASTC_ ## x ## _KHR: \
return has_hdr ? MESA_FORMAT_RGBA_ASTC_ ## x ## _FLOAT : \
MESA_FORMAT_RGBA_ASTC_ ## x;
CASE(4x4)
CASE(5x4)
CASE(5x5)
CASE(6x5)
CASE(6x6)
CASE(8x5)
CASE(8x6)
CASE(8x8)
CASE(10x5)
CASE(10x6)
CASE(10x8)
CASE(10x10)
CASE(12x10)
CASE(12x12)
#undef CASE
default:
unreachable("unexpected format");
}
}
/**
* Convert GLenum to a compressed MESA_FORMAT_x.
*/
mesa_format
_mesa_glenum_to_compressed_format(GLenum format)
_mesa_glenum_to_compressed_format(const struct gl_context *ctx, GLenum format)
{
switch (format) {
case GL_COMPRESSED_RGB_FXT1_3DFX:
@ -564,33 +595,21 @@ _mesa_glenum_to_compressed_format(GLenum format)
return MESA_FORMAT_BPTC_RGB_UNSIGNED_FLOAT;
case GL_COMPRESSED_RGBA_ASTC_4x4_KHR:
return MESA_FORMAT_RGBA_ASTC_4x4;
case GL_COMPRESSED_RGBA_ASTC_5x4_KHR:
return MESA_FORMAT_RGBA_ASTC_5x4;
case GL_COMPRESSED_RGBA_ASTC_5x5_KHR:
return MESA_FORMAT_RGBA_ASTC_5x5;
case GL_COMPRESSED_RGBA_ASTC_6x5_KHR:
return MESA_FORMAT_RGBA_ASTC_6x5;
case GL_COMPRESSED_RGBA_ASTC_6x6_KHR:
return MESA_FORMAT_RGBA_ASTC_6x6;
case GL_COMPRESSED_RGBA_ASTC_8x5_KHR:
return MESA_FORMAT_RGBA_ASTC_8x5;
case GL_COMPRESSED_RGBA_ASTC_8x6_KHR:
return MESA_FORMAT_RGBA_ASTC_8x6;
case GL_COMPRESSED_RGBA_ASTC_8x8_KHR:
return MESA_FORMAT_RGBA_ASTC_8x8;
case GL_COMPRESSED_RGBA_ASTC_10x5_KHR:
return MESA_FORMAT_RGBA_ASTC_10x5;
case GL_COMPRESSED_RGBA_ASTC_10x6_KHR:
return MESA_FORMAT_RGBA_ASTC_10x6;
case GL_COMPRESSED_RGBA_ASTC_10x8_KHR:
return MESA_FORMAT_RGBA_ASTC_10x8;
case GL_COMPRESSED_RGBA_ASTC_10x10_KHR:
return MESA_FORMAT_RGBA_ASTC_10x10;
case GL_COMPRESSED_RGBA_ASTC_12x10_KHR:
return MESA_FORMAT_RGBA_ASTC_12x10;
case GL_COMPRESSED_RGBA_ASTC_12x12_KHR:
return MESA_FORMAT_RGBA_ASTC_12x12;
return _mesa_astc_ldrhdr_glenum_to_format(ctx, format);
case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_4x4_KHR:
return MESA_FORMAT_SRGB8_ALPHA8_ASTC_4x4;
case GL_COMPRESSED_SRGB8_ALPHA8_ASTC_5x4_KHR:

View file

@ -37,7 +37,7 @@ extern GLuint
_mesa_get_compressed_formats(struct gl_context *ctx, GLint *formats);
extern mesa_format
_mesa_glenum_to_compressed_format(GLenum format);
_mesa_glenum_to_compressed_format(const struct gl_context *ctx, GLenum format);
extern GLenum
_mesa_compressed_format_to_glenum(struct gl_context *ctx, mesa_format mesaFormat);

View file

@ -1487,7 +1487,7 @@ _mesa_target_can_be_compressed(const struct gl_context *ctx, GLenum target,
GLenum intFormat, GLenum *error)
{
GLboolean target_can_be_compresed = GL_FALSE;
mesa_format format = _mesa_glenum_to_compressed_format(intFormat);
mesa_format format = _mesa_glenum_to_compressed_format(ctx, intFormat);
enum mesa_format_layout layout = _mesa_get_format_layout(format);
switch (target) {
@ -1775,10 +1775,10 @@ mutable_tex_object(struct gl_texture_object *texObj)
* Return expected size of a compressed texture.
*/
static GLuint
compressed_tex_size(GLsizei width, GLsizei height, GLsizei depth,
GLenum glformat)
compressed_tex_size(const struct gl_context *ctx, GLsizei width, GLsizei height,
GLsizei depth, GLenum glformat)
{
mesa_format mesaFormat = _mesa_glenum_to_compressed_format(glformat);
mesa_format mesaFormat = _mesa_glenum_to_compressed_format(ctx, glformat);
return _mesa_format_image_size(mesaFormat, width, height, depth);
}
@ -2209,7 +2209,7 @@ compressed_texture_error_check(struct gl_context *ctx, GLint dimensions,
/* Figure out the expected texture size (in bytes). This will be
* checked against the actual size later.
*/
expectedSize = compressed_tex_size(width, height, depth, internalFormat);
expectedSize = compressed_tex_size(ctx, width, height, depth, internalFormat);
break;
}
@ -3245,7 +3245,7 @@ teximage(struct gl_context *ctx, GLboolean compressed, GLuint dims,
* texture format since we'll never transcode the user's compressed
* image data. The internalFormat was error checked earlier.
*/
texFormat = _mesa_glenum_to_compressed_format(internalFormat);
texFormat = _mesa_glenum_to_compressed_format(ctx, internalFormat);
}
else {
/* In case of HALF_FLOAT_OES or FLOAT_OES, find corresponding sized
@ -5662,7 +5662,7 @@ compressed_subtexture_target_check(struct gl_context *ctx, GLenum target,
*
* "Modify the "3D Tex." column to be checked for all ASTC formats."
*/
format = _mesa_glenum_to_compressed_format(intFormat);
format = _mesa_glenum_to_compressed_format(ctx, intFormat);
layout = _mesa_get_format_layout(format);
switch (layout) {
case MESA_FORMAT_LAYOUT_BPTC:
@ -5764,7 +5764,7 @@ compressed_subtexture_error_check(struct gl_context *ctx, GLint dims,
return GL_TRUE;
}
expectedSize = compressed_tex_size(width, height, depth, format);
expectedSize = compressed_tex_size(ctx, width, height, depth, format);
if (expectedSize != imageSize) {
_mesa_error(ctx, GL_INVALID_VALUE, "%s(size=%d)", callerName, imageSize);
return GL_TRUE;

View file

@ -408,6 +408,21 @@ st_pbo_get_dst_format(struct gl_context *ctx, enum pipe_texture_target target,
case PIPE_FORMAT_BPTC_RGB_UFLOAT:
if (!ctx->Extensions.ARB_texture_float)
return PIPE_FORMAT_NONE;
FALLTHROUGH;
case PIPE_FORMAT_ASTC_4x4_FLOAT:
case PIPE_FORMAT_ASTC_5x4_FLOAT:
case PIPE_FORMAT_ASTC_5x5_FLOAT:
case PIPE_FORMAT_ASTC_6x5_FLOAT:
case PIPE_FORMAT_ASTC_6x6_FLOAT:
case PIPE_FORMAT_ASTC_8x5_FLOAT:
case PIPE_FORMAT_ASTC_8x6_FLOAT:
case PIPE_FORMAT_ASTC_8x8_FLOAT:
case PIPE_FORMAT_ASTC_10x5_FLOAT:
case PIPE_FORMAT_ASTC_10x6_FLOAT:
case PIPE_FORMAT_ASTC_10x8_FLOAT:
case PIPE_FORMAT_ASTC_10x10_FLOAT:
case PIPE_FORMAT_ASTC_12x10_FLOAT:
case PIPE_FORMAT_ASTC_12x12_FLOAT:
dst_glformat = GL_RGBA32F;
break;
case PIPE_FORMAT_ETC2_R11_UNORM:

View file

@ -717,59 +717,59 @@ static const struct format_mapping format_map[] = {
/* ASTC */
{
{ GL_COMPRESSED_RGBA_ASTC_4x4_KHR, 0 },
{ PIPE_FORMAT_ASTC_4x4, 0},
{ PIPE_FORMAT_ASTC_4x4_FLOAT, PIPE_FORMAT_ASTC_4x4, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_5x4_KHR, 0 },
{ PIPE_FORMAT_ASTC_5x4, 0},
{ PIPE_FORMAT_ASTC_5x4_FLOAT, PIPE_FORMAT_ASTC_5x4, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_5x5_KHR, 0 },
{ PIPE_FORMAT_ASTC_5x5, 0},
{ PIPE_FORMAT_ASTC_5x5_FLOAT, PIPE_FORMAT_ASTC_5x5, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_6x5_KHR, 0 },
{ PIPE_FORMAT_ASTC_6x5, 0},
{ PIPE_FORMAT_ASTC_6x5_FLOAT, PIPE_FORMAT_ASTC_6x5, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_6x6_KHR, 0 },
{ PIPE_FORMAT_ASTC_6x6, 0},
{ PIPE_FORMAT_ASTC_6x6_FLOAT, PIPE_FORMAT_ASTC_6x6, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_8x5_KHR, 0 },
{ PIPE_FORMAT_ASTC_8x5, 0},
{ PIPE_FORMAT_ASTC_8x5_FLOAT, PIPE_FORMAT_ASTC_8x5, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_8x6_KHR, 0 },
{ PIPE_FORMAT_ASTC_8x6, 0},
{ PIPE_FORMAT_ASTC_8x6_FLOAT, PIPE_FORMAT_ASTC_8x6, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_8x8_KHR, 0 },
{ PIPE_FORMAT_ASTC_8x8, 0},
{ PIPE_FORMAT_ASTC_8x8_FLOAT, PIPE_FORMAT_ASTC_8x8, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_10x5_KHR, 0 },
{ PIPE_FORMAT_ASTC_10x5, 0},
{ PIPE_FORMAT_ASTC_10x5_FLOAT, PIPE_FORMAT_ASTC_10x5, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_10x6_KHR, 0 },
{ PIPE_FORMAT_ASTC_10x6, 0},
{ PIPE_FORMAT_ASTC_10x6_FLOAT, PIPE_FORMAT_ASTC_10x6, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_10x8_KHR, 0 },
{ PIPE_FORMAT_ASTC_10x8, 0},
{ PIPE_FORMAT_ASTC_10x8_FLOAT, PIPE_FORMAT_ASTC_10x8, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_10x10_KHR, 0 },
{ PIPE_FORMAT_ASTC_10x10, 0},
{ PIPE_FORMAT_ASTC_10x10_FLOAT, PIPE_FORMAT_ASTC_10x10, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_12x10_KHR, 0 },
{ PIPE_FORMAT_ASTC_12x10, 0},
{ PIPE_FORMAT_ASTC_12x10_FLOAT, PIPE_FORMAT_ASTC_12x10, 0},
},
{
{ GL_COMPRESSED_RGBA_ASTC_12x12_KHR, 0 },
{ PIPE_FORMAT_ASTC_12x12, 0},
{ PIPE_FORMAT_ASTC_12x12_FLOAT, PIPE_FORMAT_ASTC_12x12, 0},
},
{
@ -1453,7 +1453,7 @@ st_ChooseTextureFormat(struct gl_context *ctx, GLenum target,
}
if (pFormat == PIPE_FORMAT_NONE) {
mFormat = _mesa_glenum_to_compressed_format(internalFormat);
mFormat = _mesa_glenum_to_compressed_format(ctx, internalFormat);
if (st_compressed_format_fallback(st, mFormat))
return mFormat;