Refactored glGenerateMipmap and added ES3 validation.
TRAC #23277
Signed-off-by: Jamie Madill
Signed-off-by: Shannon Woods
Author: Geoff Lang
diff --git a/src/libGLESv2/libGLESv2.cpp b/src/libGLESv2/libGLESv2.cpp
index 4b83f9f..7d0b154 100644
--- a/src/libGLESv2/libGLESv2.cpp
+++ b/src/libGLESv2/libGLESv2.cpp
@@ -3880,35 +3880,36 @@
if (context)
{
+ gl::Texture *texture = NULL;
+ GLint internalFormat = GL_NONE;
+ bool isCompressed = false;
+ bool isDepth = false;
+
switch (target)
{
case GL_TEXTURE_2D:
{
gl::Texture2D *tex2d = context->getTexture2D();
-
- if (tex2d->isCompressed(0))
+ if (tex2d)
{
- return gl::error(GL_INVALID_OPERATION);
+ internalFormat = tex2d->getInternalFormat(0);
+ isCompressed = tex2d->isCompressed(0);
+ isDepth = tex2d->isDepth(0);
+ texture = tex2d;
}
- if (tex2d->isDepth(0))
- {
- return gl::error(GL_INVALID_OPERATION);
- }
-
- tex2d->generateMipmaps();
break;
}
case GL_TEXTURE_CUBE_MAP:
{
gl::TextureCubeMap *texcube = context->getTextureCubeMap();
-
- if (texcube->isCompressed(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0))
+ if (texcube)
{
- return gl::error(GL_INVALID_OPERATION);
+ internalFormat = texcube->getInternalFormat(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0);
+ isCompressed = texcube->isCompressed(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0);
+ isDepth = false;
+ texture = texcube;
}
-
- texcube->generateMipmaps();
break;
}
@@ -3920,12 +3921,13 @@
}
gl::Texture3D *tex3D = context->getTexture3D();
- if (tex3D->isCompressed(0))
+ if (tex3D)
{
- return gl::error(GL_INVALID_OPERATION);
+ internalFormat = tex3D->getInternalFormat(0);
+ isCompressed = tex3D->isCompressed(0);
+ isDepth = tex3D->isDepth(0);
+ texture = tex3D;
}
-
- tex3D->generateMipmaps();
break;
}
@@ -3937,18 +3939,35 @@
}
gl::Texture2DArray *tex2darr = context->getTexture2DArray();
- if (tex2darr->isCompressed(0))
+ if (tex2darr)
{
- return gl::error(GL_INVALID_OPERATION);
+ internalFormat = tex2darr->getInternalFormat(0);
+ isCompressed = tex2darr->isCompressed(0);
+ isDepth = tex2darr->isDepth(0);
+ texture = tex2darr;
}
-
- tex2darr->generateMipmaps();
break;
}
default:
return gl::error(GL_INVALID_ENUM);
}
+
+ if (!texture)
+ {
+ return gl::error(GL_INVALID_OPERATION);
+ }
+
+ // Internally, all texture formats are sized so checking if the format
+ // is color renderable and filterable will not fail.
+ if (isDepth || isCompressed ||
+ !gl::IsColorRenderingSupported(internalFormat, context) ||
+ !gl::IsTextureFilteringSupported(internalFormat, context))
+ {
+ return gl::error(GL_INVALID_OPERATION);
+ }
+
+ texture->generateMipmaps();
}
}
catch(std::bad_alloc&)