diff --git a/.pick_status.json b/.pick_status.json index f7f4d7d6aeb..fb616ef0b4e 100644 --- a/.pick_status.json +++ b/.pick_status.json @@ -2754,7 +2754,7 @@ "description": "mesa: check driver format support for certain GetInternalformativ queries", "nominated": true, "nomination_type": 0, - "resolution": 0, + "resolution": 1, "main_sha": null, "because_sha": null, "notes": null diff --git a/src/mesa/main/formatquery.c b/src/mesa/main/formatquery.c index ae59413d345..396fa0a4014 100644 --- a/src/mesa/main/formatquery.c +++ b/src/mesa/main/formatquery.c @@ -1112,6 +1112,12 @@ _mesa_GetInternalformativ(GLenum target, GLenum internalformat, GLenum pname, if (get_pname == 0) goto end; + /* if the resource is unsupported, zero is returned */ + if (!st_QueryTextureFormatSupport(ctx, target, internalformat)) { + buffer[0] = 0; + break; + } + _mesa_GetIntegerv(get_pname, buffer); break; } @@ -1123,6 +1129,12 @@ _mesa_GetInternalformativ(GLenum target, GLenum internalformat, GLenum pname, if (!_mesa_is_array_texture(target)) goto end; + /* if the resource is unsupported, zero is returned */ + if (!st_QueryTextureFormatSupport(ctx, target, internalformat)) { + buffer[0] = 0; + break; + } + _mesa_GetIntegerv(GL_MAX_ARRAY_TEXTURE_LAYERS, buffer); break; @@ -1137,6 +1149,12 @@ _mesa_GetInternalformativ(GLenum target, GLenum internalformat, GLenum pname, unsigned i; GLint current_value; + /* if the resource is unsupported, zero is returned */ + if (!st_QueryTextureFormatSupport(ctx, target, internalformat)) { + buffer[0] = 0; + break; + } + /* Combining the dimensions. Note that for array targets, this would * automatically include the value of MAX_LAYERS, as that value is * returned as MAX_HEIGHT or MAX_DEPTH */ @@ -1515,6 +1533,14 @@ _mesa_GetInternalformativ(GLenum target, GLenum internalformat, GLenum pname, if (targetIndex < 0 || targetIndex == TEXTURE_BUFFER_INDEX) goto end; + /* If the resource is not supported for image textures, + * or if image textures are not supported, NONE is returned. + */ + if (!st_QueryTextureFormatSupport(ctx, target, internalformat)) { + buffer[0] = GL_NONE; + break; + } + /* From spec: "Equivalent to calling GetTexParameter with set * to IMAGE_FORMAT_COMPATIBILITY_TYPE." * diff --git a/src/mesa/state_tracker/st_format.c b/src/mesa/state_tracker/st_format.c index 6dcd5db202f..e2af7724608 100644 --- a/src/mesa/state_tracker/st_format.c +++ b/src/mesa/state_tracker/st_format.c @@ -1507,6 +1507,49 @@ st_QuerySamplesForFormat(struct gl_context *ctx, GLenum target, return num_sample_counts; } +/* check whether any texture can be allocated for a given format */ +bool +st_QueryTextureFormatSupport(struct gl_context *ctx, GLenum target, GLenum internalFormat) +{ + struct st_context *st = st_context(ctx); + + /* If an sRGB framebuffer is unsupported, sRGB formats behave like linear + * formats. + */ + if (!ctx->Extensions.EXT_sRGB) { + internalFormat = _mesa_get_linear_internalformat(internalFormat); + } + + /* multisample textures need >= 2 samples */ + unsigned min_samples = target == GL_TEXTURE_2D_MULTISAMPLE || + target == GL_TEXTURE_2D_MULTISAMPLE_ARRAY ? 1 : 0; + unsigned max_samples = min_samples ? 16 : 1; + + /* compressed textures will be allocated as e.g., RGBA8, so check that instead */ + enum pipe_format pf = st_choose_format(st, internalFormat, GL_NONE, GL_NONE, + PIPE_TEXTURE_2D, 0, 0, 0, + false, false); + if (util_format_is_compressed(pf)) { + enum pipe_format fmts[2] = {0}; + pf = st_mesa_format_to_pipe_format(st, st_pipe_format_to_mesa_format(pf)); + fmts[0] = pf; + for (unsigned i = max_samples; i > min_samples; i >>= 1) { + if (find_supported_format(st->screen, fmts, PIPE_TEXTURE_2D, + i, i, PIPE_BIND_SAMPLER_VIEW, false)) + return true; + } + return false; + } + for (unsigned i = max_samples; i > min_samples; i >>= 1) { + if (st_choose_format(st, internalFormat, GL_NONE, GL_NONE, + PIPE_TEXTURE_2D, i, i, PIPE_BIND_SAMPLER_VIEW, + false, false)) + return true; + } + + return false; +} + /** * ARB_internalformat_query2 driver hook. diff --git a/src/mesa/state_tracker/st_format.h b/src/mesa/state_tracker/st_format.h index 9692a0bc583..21b1a7bb4bf 100644 --- a/src/mesa/state_tracker/st_format.h +++ b/src/mesa/state_tracker/st_format.h @@ -70,7 +70,8 @@ extern mesa_format st_ChooseTextureFormat(struct gl_context * ctx, GLenum target, GLint internalFormat, GLenum format, GLenum type); - +bool +st_QueryTextureFormatSupport(struct gl_context *ctx, GLenum target, GLenum internalFormat); void st_QueryInternalFormat(struct gl_context *ctx, GLenum target, GLenum internalFormat, GLenum pname, GLint *params);