#include "main/enums.h"
#include "main/formats.h"
#include "main/glformats.h"
+#include "main/texcompress.h"
#include "main/texgetimage.h"
#include "main/teximage.h"
#include "main/texstore.h"
#define DEFAULT_RGBA_FORMATS \
- PIPE_FORMAT_B8G8R8A8_UNORM, \
PIPE_FORMAT_R8G8B8A8_UNORM, \
+ PIPE_FORMAT_B8G8R8A8_UNORM, \
PIPE_FORMAT_A8R8G8B8_UNORM, \
PIPE_FORMAT_A8B8G8R8_UNORM, \
0
#define DEFAULT_RGB_FORMATS \
- PIPE_FORMAT_B8G8R8X8_UNORM, \
PIPE_FORMAT_R8G8B8X8_UNORM, \
+ PIPE_FORMAT_B8G8R8X8_UNORM, \
PIPE_FORMAT_X8R8G8B8_UNORM, \
PIPE_FORMAT_X8B8G8R8_UNORM, \
PIPE_FORMAT_B5G6R5_UNORM, \
DEFAULT_RGBA_FORMATS
#define DEFAULT_SRGBA_FORMATS \
- PIPE_FORMAT_B8G8R8A8_SRGB, \
PIPE_FORMAT_R8G8B8A8_SRGB, \
+ PIPE_FORMAT_B8G8R8A8_SRGB, \
PIPE_FORMAT_A8R8G8B8_SRGB, \
PIPE_FORMAT_A8B8G8R8_SRGB, \
0
},
{
{ GL_RGB10_A2, 0 },
- { PIPE_FORMAT_B10G10R10A2_UNORM, PIPE_FORMAT_R10G10B10A2_UNORM,
+ { PIPE_FORMAT_R10G10B10A2_UNORM, PIPE_FORMAT_B10G10R10A2_UNORM,
DEFAULT_RGBA_FORMATS }
},
{
{ 4, GL_RGBA, GL_RGBA8, 0 },
- { DEFAULT_RGBA_FORMATS }
+ { PIPE_FORMAT_R8G8B8A8_UNORM, DEFAULT_RGBA_FORMATS }
},
{
{ GL_BGRA, 0 },
},
{
{ 3, GL_RGB, GL_RGB8, 0 },
- { DEFAULT_RGB_FORMATS }
+ { PIPE_FORMAT_R8G8B8X8_UNORM, DEFAULT_RGB_FORMATS }
},
{
{ GL_RGB12, GL_RGB16, 0 },
/* basic Alpha formats */
{
{ GL_ALPHA12, GL_ALPHA16, 0 },
- { PIPE_FORMAT_A16_UNORM, PIPE_FORMAT_A8_UNORM,
- DEFAULT_RGBA_FORMATS }
+ { PIPE_FORMAT_A16_UNORM, PIPE_FORMAT_R16G16B16A16_UNORM,
+ PIPE_FORMAT_A8_UNORM, DEFAULT_RGBA_FORMATS }
},
{
{ GL_ALPHA, GL_ALPHA4, GL_ALPHA8, GL_COMPRESSED_ALPHA, 0 },
/* basic Luminance formats */
{
{ GL_LUMINANCE12, GL_LUMINANCE16, 0 },
- { PIPE_FORMAT_L16_UNORM, PIPE_FORMAT_L8_UNORM, DEFAULT_RGB_FORMATS }
+ { PIPE_FORMAT_L16_UNORM, PIPE_FORMAT_R16G16B16A16_UNORM,
+ PIPE_FORMAT_L8_UNORM, DEFAULT_RGB_FORMATS }
},
{
{ 1, GL_LUMINANCE, GL_LUMINANCE4, GL_LUMINANCE8, 0 },
{
{ GL_LUMINANCE12_ALPHA4, GL_LUMINANCE12_ALPHA12,
GL_LUMINANCE16_ALPHA16, 0},
- { PIPE_FORMAT_L16A16_UNORM, PIPE_FORMAT_L8A8_UNORM,
- DEFAULT_RGBA_FORMATS }
+ { PIPE_FORMAT_L16A16_UNORM, PIPE_FORMAT_R16G16B16A16_UNORM,
+ PIPE_FORMAT_L8A8_UNORM, DEFAULT_RGBA_FORMATS }
},
{
{ 2, GL_LUMINANCE_ALPHA, GL_LUMINANCE6_ALPHA2, GL_LUMINANCE8_ALPHA8, 0 },
/* basic Intensity formats */
{
{ GL_INTENSITY12, GL_INTENSITY16, 0 },
- { PIPE_FORMAT_I16_UNORM, PIPE_FORMAT_I8_UNORM, DEFAULT_RGBA_FORMATS }
+ { PIPE_FORMAT_I16_UNORM, PIPE_FORMAT_R16G16B16A16_UNORM,
+ PIPE_FORMAT_I8_UNORM, DEFAULT_RGBA_FORMATS }
},
{
{ GL_INTENSITY, GL_INTENSITY4, GL_INTENSITY8,
},
{
{ GL_SRGB_ALPHA_EXT, GL_SRGB8_ALPHA8_EXT, 0 },
- { DEFAULT_SRGBA_FORMATS }
+ { PIPE_FORMAT_R8G8B8A8_SRGB, DEFAULT_SRGBA_FORMATS }
},
{
{ GL_COMPRESSED_SRGB_EXT, GL_COMPRESSED_SRGB_S3TC_DXT1_EXT, 0 },
{ 0, 0, 0 }
};
-static const struct exact_format_mapping rgba1010102_tbl[] =
-{
- { GL_BGRA, GL_UNSIGNED_INT_2_10_10_10_REV, PIPE_FORMAT_B10G10R10A2_UNORM },
- /* No Mesa formats for these Gallium formats:
- { GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV, PIPE_FORMAT_R10G10B10A2_UNORM },
- { GL_ABGR_EXT, GL_UNSIGNED_INT_10_10_10_2, PIPE_FORMAT_R10G10B10A2_UNORM },
- { GL_ABGR_EXT, GL_UNSIGNED_INT, PIPE_FORMAT_R10G10B10A2_UNORM },
- */
- { 0, 0, 0 }
-};
-
/**
- * If there is an exact pipe_format match for {internalFormat, format, type}
- * return that, otherwise return PIPE_FORMAT_NONE so we can do fuzzy matching.
+ * For unsized/base internal formats, we may choose a convenient effective
+ * internal format for {format, type}. If one exists, return that, otherwise
+ * return PIPE_FORMAT_NONE.
*/
static enum pipe_format
find_exact_format(GLint internalFormat, GLenum format, GLenum type)
switch (internalFormat) {
case 4:
case GL_RGBA:
- case GL_RGBA8:
tbl = rgba8888_tbl;
break;
case 3:
case GL_RGB:
- case GL_RGB8:
tbl = rgbx8888_tbl;
break;
- case GL_RGB10_A2:
- tbl = rgba1010102_tbl;
- break;
default:
return PIPE_FORMAT_NONE;
}
enum pipe_format pFormat;
mesa_format mFormat;
unsigned bindings;
- enum pipe_texture_target pTarget = gl_target_to_pipe(target);
+ bool is_renderbuffer = false;
+ enum pipe_texture_target pTarget;
+
+ if (target == GL_RENDERBUFFER) {
+ pTarget = PIPE_TEXTURE_2D;
+ is_renderbuffer = true;
+ } else {
+ pTarget = gl_target_to_pipe(target);
+ }
if (target == GL_TEXTURE_1D || target == GL_TEXTURE_1D_ARRAY) {
/* We don't do compression for these texture targets because of
bindings = PIPE_BIND_SAMPLER_VIEW;
if (_mesa_is_depth_or_stencil_format(internalFormat))
bindings |= PIPE_BIND_DEPTH_STENCIL;
- else if (internalFormat == 3 || internalFormat == 4 ||
+ else if (is_renderbuffer || internalFormat == 3 || internalFormat == 4 ||
internalFormat == GL_RGB || internalFormat == GL_RGBA ||
internalFormat == GL_RGB8 || internalFormat == GL_RGBA8 ||
internalFormat == GL_BGRA ||
if (pFormat != PIPE_FORMAT_NONE)
return st_pipe_format_to_mesa_format(pFormat);
- /* try choosing format again, this time without render target bindings */
- pFormat = st_choose_matching_format(st, PIPE_BIND_SAMPLER_VIEW,
- format, type,
- ctx->Unpack.SwapBytes);
- if (pFormat != PIPE_FORMAT_NONE)
- return st_pipe_format_to_mesa_format(pFormat);
+ if (!is_renderbuffer) {
+ /* try choosing format again, this time without render target bindings */
+ pFormat = st_choose_matching_format(st, PIPE_BIND_SAMPLER_VIEW,
+ format, type,
+ ctx->Unpack.SwapBytes);
+ if (pFormat != PIPE_FORMAT_NONE)
+ return st_pipe_format_to_mesa_format(pFormat);
+ }
}
}
pFormat = st_choose_format(st, internalFormat, format, type,
pTarget, 0, bindings, ctx->Mesa_DXTn);
- if (pFormat == PIPE_FORMAT_NONE) {
+ if (pFormat == PIPE_FORMAT_NONE && !is_renderbuffer) {
/* try choosing format again, this time without render target bindings */
pFormat = st_choose_format(st, internalFormat, format, type,
pTarget, 0, PIPE_BIND_SAMPLER_VIEW,
}
if (pFormat == PIPE_FORMAT_NONE) {
+ /* lie about using etc1/etc2 natively if we do decoding tricks */
+ mFormat = _mesa_glenum_to_compressed_format(internalFormat);
+ if ((mFormat == MESA_FORMAT_ETC1_RGB8 && !st->has_etc1) ||
+ (_mesa_is_format_etc2(mFormat) && !st->has_etc2))
+ return mFormat;
+
/* no luck at all */
return MESA_FORMAT_NONE;
}
st_QueryInternalFormat(struct gl_context *ctx, GLenum target,
GLenum internalFormat, GLenum pname, GLint *params)
{
+ struct st_context *st = st_context(ctx);
/* The API entry-point gives us a temporary params buffer that is non-NULL
* and guaranteed to have at least 16 elements.
*/
params[0] = (GLint) num_samples;
break;
}
-
+ case GL_INTERNALFORMAT_PREFERRED: {
+ params[0] = GL_NONE;
+
+ /* We need to resolve an internal format that is compatible with
+ * the passed internal format, and optimal to the driver. By now,
+ * we just validate that the passed internal format is supported by
+ * the driver, and if so return the same internal format, otherwise
+ * return GL_NONE.
+ */
+ uint usage;
+ if (_mesa_is_depth_or_stencil_format(internalFormat))
+ usage = PIPE_BIND_DEPTH_STENCIL;
+ else
+ usage = PIPE_BIND_RENDER_TARGET;
+ enum pipe_format pformat = st_choose_format(st,
+ internalFormat,
+ GL_NONE,
+ GL_NONE,
+ PIPE_TEXTURE_2D, 1,
+ usage, FALSE);
+ if (pformat)
+ params[0] = internalFormat;
+ break;
+ }
default:
/* For the rest of the pnames, we call back the Mesa's default
* function for drivers that don't implement ARB_internalformat_query2.