Implement GL_ANGLE_texture_multisample API part
Support GL_ANGLE_texture_multisample extension.
This patch adds enums of multisampled texture and texStorage2DMultisampleANGLE
API.
TEST=angle_end2end_tests.exe --gtest_filter=TextureMultisampleTest*
TEST=angle_end2end_tests.exe --gtest_filter=NegativeTextureMultisampleTest.Negtive*
BUG=angleproject:2275
Change-Id: I2cab997edc33aa2d0be6082381545335423f64e0
Reviewed-on: https://chromium-review.googlesource.com/c/804613
Commit-Queue: Yizhou Jiang <yizhou.jiang@intel.com>
Reviewed-by: Geoff Lang <geofflang@chromium.org>
diff --git a/src/libANGLE/Caps.cpp b/src/libANGLE/Caps.cpp
index a1121b9..1b495bc 100644
--- a/src/libANGLE/Caps.cpp
+++ b/src/libANGLE/Caps.cpp
@@ -256,7 +256,8 @@
multiviewMultisample(false),
blendFuncExtended(false),
maxDualSourceDrawBuffers(0),
- memorySize(false)
+ memorySize(false),
+ textureMultisample(false)
{
}
@@ -890,6 +891,7 @@
map["GL_OES_texture_storage_multisample_2d_array"] = enableableExtension(&Extensions::textureStorageMultisample2DArray);
map["GL_ANGLE_multiview_multisample"] = enableableExtension(&Extensions::multiviewMultisample);
map["GL_EXT_blend_func_extended"] = enableableExtension(&Extensions::blendFuncExtended);
+ map["GL_ANGLE_texture_multisample"] = enableableExtension(&Extensions::textureMultisample);
// GLES1 extensinos
map["GL_OES_point_size_array"] = enableableExtension(&Extensions::pointSizeArray);
map["GL_OES_texture_cube_map"] = enableableExtension(&Extensions::textureCubeMap);
diff --git a/src/libANGLE/Caps.h b/src/libANGLE/Caps.h
index a5c0035..e9f5c33 100644
--- a/src/libANGLE/Caps.h
+++ b/src/libANGLE/Caps.h
@@ -446,6 +446,9 @@
// GL_ANGLE_memory_size
bool memorySize;
+
+ // GL_ANGLE_texture_multisample
+ bool textureMultisample;
};
struct ExtensionInfo
diff --git a/src/libANGLE/Compiler.cpp b/src/libANGLE/Compiler.cpp
index 84f0687..fb4a723 100644
--- a/src/libANGLE/Compiler.cpp
+++ b/src/libANGLE/Compiler.cpp
@@ -85,6 +85,7 @@
mResources.ARB_texture_rectangle = extensions.textureRectangle;
mResources.OES_texture_storage_multisample_2d_array =
extensions.textureStorageMultisample2DArray;
+ mResources.ANGLE_texture_multisample = extensions.textureMultisample;
// TODO: use shader precision caps to determine if high precision is supported?
mResources.FragmentPrecisionHigh = 1;
mResources.EXT_frag_depth = extensions.fragDepth;
@@ -127,10 +128,10 @@
mResources.MaxComputeAtomicCounterBuffers =
caps.maxShaderAtomicCounterBuffers[ShaderType::Compute];
- mResources.MaxVertexAtomicCounters = caps.maxShaderAtomicCounters[ShaderType::Vertex];
- mResources.MaxFragmentAtomicCounters = caps.maxShaderAtomicCounters[ShaderType::Fragment];
- mResources.MaxCombinedAtomicCounters = caps.maxCombinedAtomicCounters;
- mResources.MaxAtomicCounterBindings = caps.maxAtomicCounterBufferBindings;
+ mResources.MaxVertexAtomicCounters = caps.maxShaderAtomicCounters[ShaderType::Vertex];
+ mResources.MaxFragmentAtomicCounters = caps.maxShaderAtomicCounters[ShaderType::Fragment];
+ mResources.MaxCombinedAtomicCounters = caps.maxCombinedAtomicCounters;
+ mResources.MaxAtomicCounterBindings = caps.maxAtomicCounterBufferBindings;
mResources.MaxVertexAtomicCounterBuffers =
caps.maxShaderAtomicCounterBuffers[ShaderType::Vertex];
mResources.MaxFragmentAtomicCounterBuffers =
@@ -150,12 +151,12 @@
}
// Geometry Shader constants
- mResources.EXT_geometry_shader = extensions.geometryShader;
+ mResources.EXT_geometry_shader = extensions.geometryShader;
mResources.MaxGeometryUniformComponents = caps.maxShaderUniformComponents[ShaderType::Geometry];
- mResources.MaxGeometryUniformBlocks = caps.maxShaderUniformBlocks[ShaderType::Geometry];
- mResources.MaxGeometryInputComponents = caps.maxGeometryInputComponents;
- mResources.MaxGeometryOutputComponents = caps.maxGeometryOutputComponents;
- mResources.MaxGeometryOutputVertices = caps.maxGeometryOutputVertices;
+ mResources.MaxGeometryUniformBlocks = caps.maxShaderUniformBlocks[ShaderType::Geometry];
+ mResources.MaxGeometryInputComponents = caps.maxGeometryInputComponents;
+ mResources.MaxGeometryOutputComponents = caps.maxGeometryOutputComponents;
+ mResources.MaxGeometryOutputVertices = caps.maxGeometryOutputVertices;
mResources.MaxGeometryTotalOutputComponents = caps.maxGeometryTotalOutputComponents;
mResources.MaxGeometryTextureImageUnits = caps.maxShaderTextureImageUnits[ShaderType::Geometry];
diff --git a/src/libANGLE/Context.cpp b/src/libANGLE/Context.cpp
index 902d903..f9a37c8 100644
--- a/src/libANGLE/Context.cpp
+++ b/src/libANGLE/Context.cpp
@@ -417,12 +417,14 @@
Texture *zeroTexture2DArray = new Texture(mImplementation.get(), 0, TextureType::_2DArray);
mZeroTextures[TextureType::_2DArray].set(this, zeroTexture2DArray);
}
- if (getClientVersion() >= Version(3, 1))
+ if (getClientVersion() >= Version(3, 1) || mSupportedExtensions.textureMultisample)
{
- // TODO(http://anglebug.com/2775): These could also be enabled via extension
Texture *zeroTexture2DMultisample =
new Texture(mImplementation.get(), 0, TextureType::_2DMultisample);
mZeroTextures[TextureType::_2DMultisample].set(this, zeroTexture2DMultisample);
+ }
+ if (getClientVersion() >= Version(3, 1))
+ {
Texture *zeroTexture2DMultisampleArray =
new Texture(mImplementation.get(), 0, TextureType::_2DMultisampleArray);
mZeroTextures[TextureType::_2DMultisampleArray].set(this, zeroTexture2DMultisampleArray);
@@ -3183,6 +3185,7 @@
supportedExtensions.multiview = false;
supportedExtensions.maxViews = 1u;
supportedExtensions.copyTexture3d = false;
+ supportedExtensions.textureMultisample = false;
}
if (getClientVersion() < ES_3_1)
@@ -7655,6 +7658,20 @@
}
}
+ if (getExtensions().textureMultisample)
+ {
+ switch (pname)
+ {
+ case GL_MAX_COLOR_TEXTURE_SAMPLES_ANGLE:
+ case GL_MAX_INTEGER_SAMPLES_ANGLE:
+ case GL_MAX_DEPTH_TEXTURE_SAMPLES_ANGLE:
+ case GL_TEXTURE_BINDING_2D_MULTISAMPLE_ANGLE:
+ *type = GL_INT;
+ *numParams = 1;
+ return true;
+ }
+ }
+
if (getClientVersion() < Version(3, 1))
{
return false;
@@ -8239,7 +8256,7 @@
mCachedValidBindTextureTypes = {{
true, /* _2D */
isGLES3, /* _2DArray */
- isGLES31, /* _2DMultisample */
+ isGLES31 || exts.textureMultisample, /* _2DMultisample */
exts.textureStorageMultisample2DArray, /* _2DMultisampleArray */
isGLES3, /* _3D */
exts.eglImageExternal || exts.eglStreamConsumerExternal, /* External */
diff --git a/src/libANGLE/ErrorStrings.h b/src/libANGLE/ErrorStrings.h
index efe054a..99a80d5 100644
--- a/src/libANGLE/ErrorStrings.h
+++ b/src/libANGLE/ErrorStrings.h
@@ -261,6 +261,8 @@
"GL_TIME_ELAPSED_EXT when the number of views in the "
"active draw framebuffer is greater than 1.");
ERRMSG(MultisampleArrayExtensionRequired, "GL_ANGLE_texture_multisample_array not enabled.");
+ERRMSG(MultisampleTextureExtensionOrES31Required,
+ "GL_ANGLE_texture_multisample or GLES 3.1 required.");
ERRMSG(NameBeginsWithGL, "Attributes that begin with 'gl_' are not allowed.");
ERRMSG(NegativeAttachments, "Negative number of attachments.");
ERRMSG(NegativeBufferSize, "Negative buffer size.");
diff --git a/src/libANGLE/State.cpp b/src/libANGLE/State.cpp
index 241aceb..7b332d0 100644
--- a/src/libANGLE/State.cpp
+++ b/src/libANGLE/State.cpp
@@ -314,10 +314,12 @@
mSamplerTextures[TextureType::_2DArray].resize(caps.maxCombinedTextureImageUnits);
mSamplerTextures[TextureType::_3D].resize(caps.maxCombinedTextureImageUnits);
}
+ if (clientVersion >= Version(3, 1) || nativeExtensions.textureMultisample)
+ {
+ mSamplerTextures[TextureType::_2DMultisample].resize(caps.maxCombinedTextureImageUnits);
+ }
if (clientVersion >= Version(3, 1))
{
- // TODO(http://anglebug.com/2775): These could also be enabled via extension
- mSamplerTextures[TextureType::_2DMultisample].resize(caps.maxCombinedTextureImageUnits);
mSamplerTextures[TextureType::_2DMultisampleArray].resize(
caps.maxCombinedTextureImageUnits);
@@ -334,7 +336,7 @@
mSamplerTextures[TextureType::External].resize(caps.maxCombinedTextureImageUnits);
}
mCompleteTextureBindings.reserve(caps.maxCombinedTextureImageUnits);
- mCachedTexturesInitState = InitState::MayNeedInit;
+ mCachedTexturesInitState = InitState::MayNeedInit;
mCachedImageTexturesInitState = InitState::MayNeedInit;
for (uint32_t textureIndex = 0; textureIndex < caps.maxCombinedTextureImageUnits;
++textureIndex)
@@ -2838,7 +2840,7 @@
// Initialize to the 'Initialized' state and set to 'MayNeedInit' if any texture is not
// initialized.
- mCachedTexturesInitState = InitState::Initialized;
+ mCachedTexturesInitState = InitState::Initialized;
mCachedImageTexturesInitState = InitState::Initialized;
const ActiveTextureMask &activeTextures = mProgram->getActiveSamplersMask();
diff --git a/src/libANGLE/entry_points_enum_autogen.h b/src/libANGLE/entry_points_enum_autogen.h
index 090d279..0c7d971 100644
--- a/src/libANGLE/entry_points_enum_autogen.h
+++ b/src/libANGLE/entry_points_enum_autogen.h
@@ -546,6 +546,7 @@
TexStorage2D,
TexStorage2DEXT,
TexStorage2DMultisample,
+ TexStorage2DMultisampleANGLE,
TexStorage3D,
TexStorage3DEXT,
TexStorage3DMultisampleOES,
diff --git a/src/libANGLE/renderer/gl/TextureGL.cpp b/src/libANGLE/renderer/gl/TextureGL.cpp
index 9b7dd94..1ea4573 100644
--- a/src/libANGLE/renderer/gl/TextureGL.cpp
+++ b/src/libANGLE/renderer/gl/TextureGL.cpp
@@ -1037,9 +1037,21 @@
if (nativegl::UseTexImage2D(getType()))
{
ASSERT(size.depth == 1);
- functions->texStorage2DMultisample(ToGLenum(type), samples, texStorageFormat.internalFormat,
- size.width, size.height,
- gl::ConvertToGLBoolean(fixedSampleLocations));
+ if (functions->texStorage2DMultisample)
+ {
+ functions->texStorage2DMultisample(
+ ToGLenum(type), samples, texStorageFormat.internalFormat, size.width, size.height,
+ gl::ConvertToGLBoolean(fixedSampleLocations));
+ }
+ else
+ {
+ // texImage2DMultisample is similar to texStorage2DMultisample of es 3.1 core feature,
+ // On macos and some old drivers which doesn't support OpenGL ES 3.1, the function can
+ // be supported by ARB_texture_multisample or OpenGL 3.2 core feature.
+ functions->texImage2DMultisample(
+ ToGLenum(type), samples, texStorageFormat.internalFormat, size.width, size.height,
+ gl::ConvertToGLBoolean(fixedSampleLocations));
+ }
}
else if (nativegl::UseTexImage3D(getType()))
{
diff --git a/src/libANGLE/renderer/gl/renderergl_utils.cpp b/src/libANGLE/renderer/gl/renderergl_utils.cpp
index 42539be..71c105a 100644
--- a/src/libANGLE/renderer/gl/renderergl_utils.cpp
+++ b/src/libANGLE/renderer/gl/renderergl_utils.cpp
@@ -24,9 +24,9 @@
#include "libANGLE/renderer/gl/WorkaroundsGL.h"
#include "libANGLE/renderer/gl/formatutilsgl.h"
+#include <EGL/eglext.h>
#include <algorithm>
#include <sstream>
-#include <EGL/eglext.h>
using angle::CheckedNumeric;
@@ -61,7 +61,8 @@
namespace nativegl_gl
{
-static bool MeetsRequirements(const FunctionsGL *functions, const nativegl::SupportRequirement &requirements)
+static bool MeetsRequirements(const FunctionsGL *functions,
+ const nativegl::SupportRequirement &requirements)
{
bool hasRequiredExtensions = false;
for (const std::vector<std::string> &exts : requirements.requiredExtensions)
@@ -114,9 +115,11 @@
gl::TextureCaps textureCaps;
- const nativegl::InternalFormat &formatInfo = nativegl::GetInternalFormatInfo(internalFormat, functions->standard);
+ const nativegl::InternalFormat &formatInfo =
+ nativegl::GetInternalFormatInfo(internalFormat, functions->standard);
textureCaps.texturable = MeetsRequirements(functions, formatInfo.texture);
- textureCaps.filterable = textureCaps.texturable && MeetsRequirements(functions, formatInfo.filter);
+ textureCaps.filterable =
+ textureCaps.texturable && MeetsRequirements(functions, formatInfo.filter);
textureCaps.textureAttachment = MeetsRequirements(functions, formatInfo.textureAttachment);
textureCaps.renderbuffer = MeetsRequirements(functions, formatInfo.renderbuffer);
@@ -240,7 +243,9 @@
return result[index];
}
-static gl::TypePrecision QueryTypePrecision(const FunctionsGL *functions, GLenum shaderType, GLenum precisionType)
+static gl::TypePrecision QueryTypePrecision(const FunctionsGL *functions,
+ GLenum shaderType,
+ GLenum precisionType)
{
gl::TypePrecision precision;
functions->getShaderPrecisionFormat(shaderType, precisionType, precision.range.data(),
@@ -288,7 +293,8 @@
*maxSupportedESVersion = gl::Version(3, 1);
// Table 6.28, implementation dependent values
- if (functions->isAtLeastGL(gl::Version(4, 3)) || functions->hasGLExtension("GL_ARB_ES3_compatibility") ||
+ if (functions->isAtLeastGL(gl::Version(4, 3)) ||
+ functions->hasGLExtension("GL_ARB_ES3_compatibility") ||
functions->isAtLeastGLES(gl::Version(3, 0)))
{
caps->maxElementIndex = QuerySingleGLInt64(functions, GL_MAX_ELEMENT_INDEX);
@@ -299,8 +305,8 @@
caps->maxElementIndex = static_cast<GLint64>(std::numeric_limits<unsigned int>::max());
}
- if (functions->isAtLeastGL(gl::Version(1, 2)) ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_OES_texture_3D"))
+ if (functions->isAtLeastGL(gl::Version(1, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_OES_texture_3D"))
{
caps->max3DTextureSize = QuerySingleGLInt(functions, GL_MAX_3D_TEXTURE_SIZE);
}
@@ -310,10 +316,12 @@
LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
}
- caps->max2DTextureSize = QuerySingleGLInt(functions, GL_MAX_TEXTURE_SIZE); // GL 1.0 / ES 2.0
- caps->maxCubeMapTextureSize = QuerySingleGLInt(functions, GL_MAX_CUBE_MAP_TEXTURE_SIZE); // GL 1.3 / ES 2.0
+ caps->max2DTextureSize = QuerySingleGLInt(functions, GL_MAX_TEXTURE_SIZE); // GL 1.0 / ES 2.0
+ caps->maxCubeMapTextureSize =
+ QuerySingleGLInt(functions, GL_MAX_CUBE_MAP_TEXTURE_SIZE); // GL 1.3 / ES 2.0
- if (functions->isAtLeastGL(gl::Version(3, 0)) || functions->hasGLExtension("GL_EXT_texture_array") ||
+ if (functions->isAtLeastGL(gl::Version(3, 0)) ||
+ functions->hasGLExtension("GL_EXT_texture_array") ||
functions->isAtLeastGLES(gl::Version(3, 0)))
{
caps->maxArrayTextureLayers = QuerySingleGLInt(functions, GL_MAX_ARRAY_TEXTURE_LAYERS);
@@ -324,7 +332,8 @@
LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
}
- if (functions->isAtLeastGL(gl::Version(1, 5)) || functions->hasGLExtension("GL_EXT_texture_lod_bias") ||
+ if (functions->isAtLeastGL(gl::Version(1, 5)) ||
+ functions->hasGLExtension("GL_EXT_texture_lod_bias") ||
functions->isAtLeastGLES(gl::Version(3, 0)))
{
caps->maxLODBias = QuerySingleGLFloat(functions, GL_MAX_TEXTURE_LOD_BIAS);
@@ -334,7 +343,8 @@
LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
}
- if (functions->isAtLeastGL(gl::Version(3, 0)) || functions->hasGLExtension("GL_EXT_framebuffer_object") ||
+ if (functions->isAtLeastGL(gl::Version(3, 0)) ||
+ functions->hasGLExtension("GL_EXT_framebuffer_object") ||
functions->isAtLeastGLES(gl::Version(2, 0)))
{
caps->maxRenderbufferSize = QuerySingleGLInt(functions, GL_MAX_RENDERBUFFER_SIZE);
@@ -346,8 +356,10 @@
LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
}
- if (functions->isAtLeastGL(gl::Version(2, 0)) || functions->hasGLExtension("ARB_draw_buffers") ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_EXT_draw_buffers"))
+ if (functions->isAtLeastGL(gl::Version(2, 0)) ||
+ functions->hasGLExtension("ARB_draw_buffers") ||
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_EXT_draw_buffers"))
{
caps->maxDrawBuffers = QuerySingleGLInt(functions, GL_MAX_DRAW_BUFFERS);
}
@@ -359,8 +371,10 @@
LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
}
- caps->maxViewportWidth = QueryGLIntRange(functions, GL_MAX_VIEWPORT_DIMS, 0); // GL 1.0 / ES 2.0
- caps->maxViewportHeight = QueryGLIntRange(functions, GL_MAX_VIEWPORT_DIMS, 1); // GL 1.0 / ES 2.0
+ caps->maxViewportWidth =
+ QueryGLIntRange(functions, GL_MAX_VIEWPORT_DIMS, 0); // GL 1.0 / ES 2.0
+ caps->maxViewportHeight =
+ QueryGLIntRange(functions, GL_MAX_VIEWPORT_DIMS, 1); // GL 1.0 / ES 2.0
if (functions->standard == STANDARD_GL_DESKTOP &&
(functions->profile & GL_CONTEXT_CORE_PROFILE_BIT) != 0)
@@ -378,14 +392,15 @@
caps->maxAliasedPointSize = QueryGLFloatRange(functions, GL_ALIASED_POINT_SIZE_RANGE, 1);
}
- caps->minAliasedLineWidth = QueryGLFloatRange(functions, GL_ALIASED_LINE_WIDTH_RANGE, 0); // GL 1.2 / ES 2.0
- caps->maxAliasedLineWidth = QueryGLFloatRange(functions, GL_ALIASED_LINE_WIDTH_RANGE, 1); // GL 1.2 / ES 2.0
+ caps->minAliasedLineWidth =
+ QueryGLFloatRange(functions, GL_ALIASED_LINE_WIDTH_RANGE, 0); // GL 1.2 / ES 2.0
+ caps->maxAliasedLineWidth =
+ QueryGLFloatRange(functions, GL_ALIASED_LINE_WIDTH_RANGE, 1); // GL 1.2 / ES 2.0
// Table 6.29, implementation dependent values (cont.)
- if (functions->isAtLeastGL(gl::Version(1, 2)) ||
- functions->isAtLeastGLES(gl::Version(3, 0)))
+ if (functions->isAtLeastGL(gl::Version(1, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)))
{
- caps->maxElementsIndices = QuerySingleGLInt(functions, GL_MAX_ELEMENTS_INDICES);
+ caps->maxElementsIndices = QuerySingleGLInt(functions, GL_MAX_ELEMENTS_INDICES);
caps->maxElementsVertices = QuerySingleGLInt(functions, GL_MAX_ELEMENTS_VERTICES);
}
else
@@ -411,22 +426,25 @@
// Doesn't impact supported version
}
- // glGetShaderPrecisionFormat is not available until desktop GL version 4.1 or GL_ARB_ES2_compatibility exists
- if (functions->isAtLeastGL(gl::Version(4, 1)) || functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
+ // glGetShaderPrecisionFormat is not available until desktop GL version 4.1 or
+ // GL_ARB_ES2_compatibility exists
+ if (functions->isAtLeastGL(gl::Version(4, 1)) ||
+ functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
functions->isAtLeastGLES(gl::Version(2, 0)))
{
- caps->vertexHighpFloat = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_HIGH_FLOAT);
+ caps->vertexHighpFloat = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_HIGH_FLOAT);
caps->vertexMediumpFloat = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_MEDIUM_FLOAT);
- caps->vertexLowpFloat = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_LOW_FLOAT);
+ caps->vertexLowpFloat = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_LOW_FLOAT);
caps->fragmentHighpFloat = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_HIGH_FLOAT);
- caps->fragmentMediumpFloat = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_MEDIUM_FLOAT);
- caps->fragmentLowpFloat = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_LOW_FLOAT);
- caps->vertexHighpInt = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_HIGH_INT);
- caps->vertexMediumpInt = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_MEDIUM_INT);
- caps->vertexLowpInt = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_LOW_INT);
- caps->fragmentHighpInt = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_HIGH_INT);
+ caps->fragmentMediumpFloat =
+ QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_MEDIUM_FLOAT);
+ caps->fragmentLowpFloat = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_LOW_FLOAT);
+ caps->vertexHighpInt = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_HIGH_INT);
+ caps->vertexMediumpInt = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_MEDIUM_INT);
+ caps->vertexLowpInt = QueryTypePrecision(functions, GL_VERTEX_SHADER, GL_LOW_INT);
+ caps->fragmentHighpInt = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_HIGH_INT);
caps->fragmentMediumpInt = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_MEDIUM_INT);
- caps->fragmentLowpInt = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_LOW_INT);
+ caps->fragmentLowpInt = QueryTypePrecision(functions, GL_FRAGMENT_SHADER, GL_LOW_INT);
}
else
{
@@ -456,8 +474,7 @@
}
// Table 6.31, implementation dependent vertex shader limits
- if (functions->isAtLeastGL(gl::Version(2, 0)) ||
- functions->isAtLeastGLES(gl::Version(2, 0)))
+ if (functions->isAtLeastGL(gl::Version(2, 0)) || functions->isAtLeastGLES(gl::Version(2, 0)))
{
caps->maxVertexAttributes = QuerySingleGLInt(functions, GL_MAX_VERTEX_ATTRIBS);
caps->maxShaderUniformComponents[gl::ShaderType::Vertex] =
@@ -471,7 +488,8 @@
LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
}
- if (functions->isAtLeastGL(gl::Version(4, 1)) || functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
+ if (functions->isAtLeastGL(gl::Version(4, 1)) ||
+ functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
functions->isAtLeastGLES(gl::Version(2, 0)))
{
caps->maxVertexUniformVectors = QuerySingleGLInt(functions, GL_MAX_VERTEX_UNIFORM_VECTORS);
@@ -488,21 +506,20 @@
caps->maxShaderUniformComponents[gl::ShaderType::Fragment] / 4;
}
- if (functions->isAtLeastGL(gl::Version(3, 2)) ||
- functions->isAtLeastGLES(gl::Version(3, 0)))
+ if (functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)))
{
- caps->maxVertexOutputComponents = QuerySingleGLInt(functions, GL_MAX_VERTEX_OUTPUT_COMPONENTS);
+ caps->maxVertexOutputComponents =
+ QuerySingleGLInt(functions, GL_MAX_VERTEX_OUTPUT_COMPONENTS);
}
else
{
- // There doesn't seem, to be a desktop extension to add this cap, maybe it could be given a safe limit
- // instead of limiting the supported ES version.
+ // There doesn't seem, to be a desktop extension to add this cap, maybe it could be given a
+ // safe limit instead of limiting the supported ES version.
LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
}
// Table 6.32, implementation dependent fragment shader limits
- if (functions->isAtLeastGL(gl::Version(2, 0)) ||
- functions->isAtLeastGLES(gl::Version(2, 0)))
+ if (functions->isAtLeastGL(gl::Version(2, 0)) || functions->isAtLeastGLES(gl::Version(2, 0)))
{
caps->maxShaderUniformComponents[gl::ShaderType::Fragment] =
QuerySingleGLInt(functions, GL_MAX_FRAGMENT_UNIFORM_COMPONENTS);
@@ -515,20 +532,19 @@
LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
}
- if (functions->isAtLeastGL(gl::Version(3, 2)) ||
- functions->isAtLeastGLES(gl::Version(3, 0)))
+ if (functions->isAtLeastGL(gl::Version(3, 2)) || functions->isAtLeastGLES(gl::Version(3, 0)))
{
- caps->maxFragmentInputComponents = QuerySingleGLInt(functions, GL_MAX_FRAGMENT_INPUT_COMPONENTS);
+ caps->maxFragmentInputComponents =
+ QuerySingleGLInt(functions, GL_MAX_FRAGMENT_INPUT_COMPONENTS);
}
else
{
- // There doesn't seem, to be a desktop extension to add this cap, maybe it could be given a safe limit
- // instead of limiting the supported ES version.
+ // There doesn't seem, to be a desktop extension to add this cap, maybe it could be given a
+ // safe limit instead of limiting the supported ES version.
LimitVersion(maxSupportedESVersion, gl::Version(2, 0));
}
- if (functions->isAtLeastGL(gl::Version(3, 0)) ||
- functions->isAtLeastGLES(gl::Version(3, 0)))
+ if (functions->isAtLeastGL(gl::Version(3, 0)) || functions->isAtLeastGLES(gl::Version(3, 0)))
{
caps->minProgramTexelOffset = QuerySingleGLInt(functions, GL_MIN_PROGRAM_TEXEL_OFFSET);
caps->maxProgramTexelOffset = QuerySingleGLInt(functions, GL_MAX_PROGRAM_TEXEL_OFFSET);
@@ -540,16 +556,19 @@
}
// Table 6.33, implementation dependent aggregate shader limits
- if (functions->isAtLeastGL(gl::Version(3, 1)) || functions->hasGLExtension("GL_ARB_uniform_buffer_object") ||
+ if (functions->isAtLeastGL(gl::Version(3, 1)) ||
+ functions->hasGLExtension("GL_ARB_uniform_buffer_object") ||
functions->isAtLeastGLES(gl::Version(3, 0)))
{
caps->maxShaderUniformBlocks[gl::ShaderType::Vertex] =
QuerySingleGLInt(functions, GL_MAX_VERTEX_UNIFORM_BLOCKS);
caps->maxShaderUniformBlocks[gl::ShaderType::Fragment] =
QuerySingleGLInt(functions, GL_MAX_FRAGMENT_UNIFORM_BLOCKS);
- caps->maxUniformBufferBindings = QuerySingleGLInt(functions, GL_MAX_UNIFORM_BUFFER_BINDINGS);
+ caps->maxUniformBufferBindings =
+ QuerySingleGLInt(functions, GL_MAX_UNIFORM_BUFFER_BINDINGS);
caps->maxUniformBlockSize = QuerySingleGLInt64(functions, GL_MAX_UNIFORM_BLOCK_SIZE);
- caps->uniformBufferOffsetAlignment = QuerySingleGLInt(functions, GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT);
+ caps->uniformBufferOffsetAlignment =
+ QuerySingleGLInt(functions, GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT);
GLuint maxCombinedUniformBlocks =
QuerySingleGLInt(functions, GL_MAX_COMBINED_UNIFORM_BLOCKS);
@@ -591,7 +610,8 @@
LimitVersion(maxSupportedESVersion, gl::Version(0, 0));
}
- if (functions->isAtLeastGL(gl::Version(4, 1)) || functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
+ if (functions->isAtLeastGL(gl::Version(4, 1)) ||
+ functions->hasGLExtension("GL_ARB_ES2_compatibility") ||
functions->isAtLeastGLES(gl::Version(2, 0)))
{
caps->maxVaryingVectors = QuerySingleGLInt(functions, GL_MAX_VARYING_VECTORS);
@@ -603,7 +623,8 @@
}
// Determine the max combined texture image units by adding the vertex and fragment limits. If
- // the real cap is queried, it would contain the limits for shader types that are not available to ES.
+ // the real cap is queried, it would contain the limits for shader types that are not available
+ // to ES.
caps->maxCombinedTextureImageUnits = caps->maxShaderTextureImageUnits[gl::ShaderType::Vertex] +
caps->maxShaderTextureImageUnits[gl::ShaderType::Fragment];
@@ -612,9 +633,12 @@
functions->hasGLExtension("GL_ARB_transform_feedback2") ||
functions->isAtLeastGLES(gl::Version(3, 0)))
{
- caps->maxTransformFeedbackInterleavedComponents = QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS);
- caps->maxTransformFeedbackSeparateAttributes = QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS);
- caps->maxTransformFeedbackSeparateComponents = QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS);
+ caps->maxTransformFeedbackInterleavedComponents =
+ QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_INTERLEAVED_COMPONENTS);
+ caps->maxTransformFeedbackSeparateAttributes =
+ QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_ATTRIBS);
+ caps->maxTransformFeedbackSeparateComponents =
+ QuerySingleGLInt(functions, GL_MAX_TRANSFORM_FEEDBACK_SEPARATE_COMPONENTS);
}
else
{
@@ -623,8 +647,10 @@
}
// Table 6.35, Framebuffer Dependent Values
- if (functions->isAtLeastGL(gl::Version(3, 0)) || functions->hasGLExtension("GL_EXT_framebuffer_multisample") ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_EXT_multisampled_render_to_texture"))
+ if (functions->isAtLeastGL(gl::Version(3, 0)) ||
+ functions->hasGLExtension("GL_EXT_framebuffer_multisample") ||
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_EXT_multisampled_render_to_texture"))
{
caps->maxSamples = QuerySingleGLInt(functions, GL_MAX_SAMPLES);
}
@@ -885,30 +911,43 @@
// Extension support
extensions->setTextureExtensionSupport(*textureCapsMap);
extensions->elementIndexUint = functions->standard == STANDARD_GL_DESKTOP ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_OES_element_index_uint");
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_OES_element_index_uint");
extensions->getProgramBinary = caps->programBinaryFormats.size() > 0;
- extensions->readFormatBGRA = functions->isAtLeastGL(gl::Version(1, 2)) || functions->hasGLExtension("GL_EXT_bgra") ||
+ extensions->readFormatBGRA = functions->isAtLeastGL(gl::Version(1, 2)) ||
+ functions->hasGLExtension("GL_EXT_bgra") ||
functions->hasGLESExtension("GL_EXT_read_format_bgra");
extensions->mapBuffer = functions->isAtLeastGL(gl::Version(1, 5)) ||
functions->isAtLeastGLES(gl::Version(3, 0)) ||
functions->hasGLESExtension("GL_OES_mapbuffer");
- extensions->mapBufferRange = functions->isAtLeastGL(gl::Version(3, 0)) || functions->hasGLExtension("GL_ARB_map_buffer_range") ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_EXT_map_buffer_range");
+ extensions->mapBufferRange = functions->isAtLeastGL(gl::Version(3, 0)) ||
+ functions->hasGLExtension("GL_ARB_map_buffer_range") ||
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_EXT_map_buffer_range");
extensions->textureNPOT = functions->standard == STANDARD_GL_DESKTOP ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_OES_texture_npot");
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_OES_texture_npot");
// TODO(jmadill): Investigate emulating EXT_draw_buffers on ES 3.0's core functionality.
extensions->drawBuffers = functions->isAtLeastGL(gl::Version(2, 0)) ||
functions->hasGLExtension("ARB_draw_buffers") ||
functions->hasGLESExtension("GL_EXT_draw_buffers");
extensions->textureStorage = functions->standard == STANDARD_GL_DESKTOP ||
functions->hasGLESExtension("GL_EXT_texture_storage");
- extensions->textureFilterAnisotropic = functions->hasGLExtension("GL_EXT_texture_filter_anisotropic") || functions->hasGLESExtension("GL_EXT_texture_filter_anisotropic");
- extensions->occlusionQueryBoolean = nativegl::SupportsOcclusionQueries(functions);
- extensions->maxTextureAnisotropy = extensions->textureFilterAnisotropic ? QuerySingleGLFloat(functions, GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT) : 0.0f;
- extensions->fence = functions->hasGLExtension("GL_NV_fence") || functions->hasGLESExtension("GL_NV_fence");
- extensions->blendMinMax = functions->isAtLeastGL(gl::Version(1, 5)) || functions->hasGLExtension("GL_EXT_blend_minmax") ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_EXT_blend_minmax");
- extensions->framebufferBlit = (functions->blitFramebuffer != nullptr);
+ extensions->textureFilterAnisotropic =
+ functions->hasGLExtension("GL_EXT_texture_filter_anisotropic") ||
+ functions->hasGLESExtension("GL_EXT_texture_filter_anisotropic");
+ extensions->occlusionQueryBoolean = nativegl::SupportsOcclusionQueries(functions);
+ extensions->maxTextureAnisotropy =
+ extensions->textureFilterAnisotropic
+ ? QuerySingleGLFloat(functions, GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT)
+ : 0.0f;
+ extensions->fence =
+ functions->hasGLExtension("GL_NV_fence") || functions->hasGLESExtension("GL_NV_fence");
+ extensions->blendMinMax = functions->isAtLeastGL(gl::Version(1, 5)) ||
+ functions->hasGLExtension("GL_EXT_blend_minmax") ||
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_EXT_blend_minmax");
+ extensions->framebufferBlit = (functions->blitFramebuffer != nullptr);
extensions->framebufferMultisample = caps->maxSamples > 0;
extensions->standardDerivatives = functions->isAtLeastGL(gl::Version(2, 0)) ||
functions->hasGLExtension("GL_ARB_fragment_shader") ||
@@ -925,15 +964,17 @@
// GL_MAX_ARRAY_TEXTURE_LAYERS is guaranteed to be at least 256.
const int maxLayers = QuerySingleGLInt(functions, GL_MAX_ARRAY_TEXTURE_LAYERS);
// GL_MAX_VIEWPORTS is guaranteed to be at least 16.
- const int maxViewports = QuerySingleGLInt(functions, GL_MAX_VIEWPORTS);
- extensions->maxViews = static_cast<GLuint>(
+ const int maxViewports = QuerySingleGLInt(functions, GL_MAX_VIEWPORTS);
+ extensions->maxViews = static_cast<GLuint>(
std::min(static_cast<int>(gl::IMPLEMENTATION_ANGLE_MULTIVIEW_MAX_VIEWS),
std::min(maxLayers, maxViewports)));
*multiviewImplementationType = MultiviewImplementationTypeGL::NV_VIEWPORT_ARRAY2;
}
- extensions->fboRenderMipmap = functions->isAtLeastGL(gl::Version(3, 0)) || functions->hasGLExtension("GL_EXT_framebuffer_object") ||
- functions->isAtLeastGLES(gl::Version(3, 0)) || functions->hasGLESExtension("GL_OES_fbo_render_mipmap");
+ extensions->fboRenderMipmap = functions->isAtLeastGL(gl::Version(3, 0)) ||
+ functions->hasGLExtension("GL_EXT_framebuffer_object") ||
+ functions->isAtLeastGLES(gl::Version(3, 0)) ||
+ functions->hasGLESExtension("GL_OES_fbo_render_mipmap");
extensions->instancedArrays = functions->isAtLeastGL(gl::Version(3, 1)) ||
(functions->hasGLExtension("GL_ARB_instanced_arrays") &&
(functions->hasGLExtension("GL_ARB_draw_instanced") ||
@@ -976,7 +1017,8 @@
// the EXT_multisample_compatibility is written against ES3.1 but can apply
// to earlier versions so therefore we're only checking for the extension string
// and not the specific GLES version.
- extensions->multisampleCompatibility = functions->isAtLeastGL(gl::Version(1, 3)) ||
+ extensions->multisampleCompatibility =
+ functions->isAtLeastGL(gl::Version(1, 3)) ||
functions->hasGLESExtension("GL_EXT_multisample_compatibility");
extensions->framebufferMixedSamples =
@@ -1006,6 +1048,9 @@
extensions->multiviewMultisample =
extensions->textureStorageMultisample2DArray && extensions->multiview;
+ extensions->textureMultisample = functions->isAtLeastGL(gl::Version(3, 2)) ||
+ functions->hasGLExtension("GL_ARB_texture_multisample");
+
// NV_path_rendering
// We also need interface query which is available in
// >= 4.3 core or ARB_interface_query or >= GLES 3.1
@@ -1014,9 +1059,8 @@
(functions->hasGLExtension("GL_ARB_program_interface_query") ||
functions->isAtLeastGL(gl::Version(4, 3)));
- const bool canEnableESPathRendering =
- functions->hasGLESExtension("GL_NV_path_rendering") &&
- functions->isAtLeastGLES(gl::Version(3, 1));
+ const bool canEnableESPathRendering = functions->hasGLESExtension("GL_NV_path_rendering") &&
+ functions->isAtLeastGLES(gl::Version(3, 1));
extensions->pathRendering = canEnableGLPathRendering || canEnableESPathRendering;
@@ -1177,7 +1221,7 @@
#endif
#if defined(ANGLE_PLATFORM_APPLE)
- workarounds->doWhileGLSLCausesGPUHang = true;
+ workarounds->doWhileGLSLCausesGPUHang = true;
workarounds->useUnusedBlocksWithStandardOrSharedLayout = true;
workarounds->rewriteFloatUnaryMinusOperator = IsIntel(vendor);
#endif
diff --git a/src/libANGLE/validationES.cpp b/src/libANGLE/validationES.cpp
index 9625028..37c424d 100644
--- a/src/libANGLE/validationES.cpp
+++ b/src/libANGLE/validationES.cpp
@@ -510,7 +510,8 @@
return (context->getClientMajorVersion() >= 3);
case TextureType::_2DMultisample:
- return (context->getClientVersion() >= Version(3, 1));
+ return (context->getClientVersion() >= Version(3, 1) ||
+ context->getExtensions().textureMultisample);
case TextureType::_2DMultisampleArray:
return context->getExtensions().textureStorageMultisample2DArray;
@@ -6412,9 +6413,11 @@
break;
case GL_TEXTURE_2D_MULTISAMPLE:
- if (context->getClientVersion() < ES_3_1)
+ if (context->getClientVersion() < ES_3_1 &&
+ !context->getExtensions().textureMultisample)
{
- ANGLE_VALIDATION_ERR(context, InvalidEnum(), TextureTargetRequiresES31);
+ ANGLE_VALIDATION_ERR(context, InvalidEnum(),
+ MultisampleTextureExtensionOrES31Required);
return false;
}
break;
@@ -6539,4 +6542,25 @@
return true;
}
+bool ValidateTexStorage2DMultisampleBase(Context *context,
+ TextureType target,
+ GLsizei samples,
+ GLint internalFormat,
+ GLsizei width,
+ GLsizei height)
+{
+ if (target != TextureType::_2DMultisample)
+ {
+ ANGLE_VALIDATION_ERR(context, InvalidEnum(), InvalidTarget);
+ return false;
+ }
+
+ if (width < 1 || height < 1)
+ {
+ ANGLE_VALIDATION_ERR(context, InvalidValue(), NegativeSize);
+ return false;
+ }
+
+ return ValidateTexStorageMultisample(context, target, samples, internalFormat, width, height);
+}
} // namespace gl
diff --git a/src/libANGLE/validationES.h b/src/libANGLE/validationES.h
index 28b0f6b..b6d9c2b 100644
--- a/src/libANGLE/validationES.h
+++ b/src/libANGLE/validationES.h
@@ -705,6 +705,13 @@
GLsizei width,
GLsizei height);
+bool ValidateTexStorage2DMultisampleBase(Context *context,
+ TextureType target,
+ GLsizei samples,
+ GLint internalFormat,
+ GLsizei width,
+ GLsizei height);
+
// Utility macro for handling implementation methods inside Validation.
#define ANGLE_HANDLE_VALIDATION_ERR(X) \
context->handleError(X); \
diff --git a/src/libANGLE/validationES2.cpp b/src/libANGLE/validationES2.cpp
index 2bcfd24..8db6a85 100644
--- a/src/libANGLE/validationES2.cpp
+++ b/src/libANGLE/validationES2.cpp
@@ -1133,8 +1133,9 @@
break;
case TextureType::_2DMultisample:
- ASSERT(context->getClientVersion() < Version(3, 1));
- ANGLE_VALIDATION_ERR(context, InvalidEnum(), ES31Required);
+ ASSERT(context->getClientVersion() < Version(3, 1) &&
+ !context->getExtensions().textureMultisample);
+ ANGLE_VALIDATION_ERR(context, InvalidEnum(), MultisampleTextureExtensionOrES31Required);
break;
case TextureType::_2DMultisampleArray:
@@ -6035,9 +6036,11 @@
case TextureTarget::_2DMultisample:
{
- if (context->getClientVersion() < ES_3_1)
+ if (context->getClientVersion() < ES_3_1 &&
+ !context->getExtensions().textureMultisample)
{
- ANGLE_VALIDATION_ERR(context, InvalidOperation(), ES31Required);
+ ANGLE_VALIDATION_ERR(context, InvalidOperation(),
+ MultisampleTextureExtensionOrES31Required);
return false;
}
diff --git a/src/libANGLE/validationES3.cpp b/src/libANGLE/validationES3.cpp
index eb12b87..cd2a286 100644
--- a/src/libANGLE/validationES3.cpp
+++ b/src/libANGLE/validationES3.cpp
@@ -4149,4 +4149,23 @@
return true;
}
+bool ValidateTexStorage2DMultisampleANGLE(Context *context,
+ TextureType target,
+ GLsizei samples,
+ GLint internalFormat,
+ GLsizei width,
+ GLsizei height,
+ GLboolean fixedSampleLocations)
+{
+ if (!context->getExtensions().textureMultisample)
+ {
+ ANGLE_VALIDATION_ERR(context, InvalidOperation(),
+ MultisampleTextureExtensionOrES31Required);
+ return false;
+ }
+
+ return ValidateTexStorage2DMultisampleBase(context, target, samples, internalFormat, width,
+ height);
+}
+
} // namespace gl
diff --git a/src/libANGLE/validationES3.h b/src/libANGLE/validationES3.h
index e1a16d8..5f72e24 100644
--- a/src/libANGLE/validationES3.h
+++ b/src/libANGLE/validationES3.h
@@ -633,6 +633,13 @@
const char *name);
bool ValidateGetFragDataIndexEXT(Context *context, GLuint program, const char *name);
+bool ValidateTexStorage2DMultisampleANGLE(Context *context,
+ TextureType target,
+ GLsizei samples,
+ GLint internalFormat,
+ GLsizei width,
+ GLsizei height,
+ GLboolean fixedSampleLocations);
} // namespace gl
#endif // LIBANGLE_VALIDATION_ES3_H_
diff --git a/src/libANGLE/validationES31.cpp b/src/libANGLE/validationES31.cpp
index 96549c0..cd386ad 100644
--- a/src/libANGLE/validationES31.cpp
+++ b/src/libANGLE/validationES31.cpp
@@ -1030,19 +1030,8 @@
return false;
}
- if (target != TextureType::_2DMultisample)
- {
- context->handleError(InvalidEnum() << "Target must be TEXTURE_2D_MULTISAMPLE.");
- return false;
- }
-
- if (width < 1 || height < 1)
- {
- ANGLE_VALIDATION_ERR(context, InvalidValue(), NegativeSize);
- return false;
- }
-
- return ValidateTexStorageMultisample(context, target, samples, internalFormat, width, height);
+ return ValidateTexStorage2DMultisampleBase(context, target, samples, internalFormat, width,
+ height);
}
bool ValidateGetMultisamplefv(Context *context, GLenum pname, GLuint index, GLfloat *val)