Commit b1196687 by Geoff Lang

Update validation functions to use new error mechanisms.

BUG=angle:520 Change-Id: I1c64af2e57cf2d89138bd23da2b07d5873742e4e Reviewed-on: https://chromium-review.googlesource.com/209880Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Tested-by: 's avatarGeoff Lang <geofflang@chromium.org>
parent 05881a0f
This source diff could not be displayed because it is too large. You can view the blob instead.
......@@ -168,7 +168,7 @@ bool ValidMipLevel(const Context *context, GLenum target, GLint level)
return level <= gl::log2(maxDimension);
}
bool ValidImageSize(const gl::Context *context, GLenum target, GLint level,
bool ValidImageSize(const Context *context, GLenum target, GLint level,
GLsizei width, GLsizei height, GLsizei depth)
{
if (level < 0 || width < 0 || height < 0 || depth < 0)
......@@ -190,7 +190,7 @@ bool ValidImageSize(const gl::Context *context, GLenum target, GLint level,
return true;
}
bool ValidCompressedImageSize(const gl::Context *context, GLenum internalFormat, GLsizei width, GLsizei height)
bool ValidCompressedImageSize(const Context *context, GLenum internalFormat, GLsizei width, GLsizei height)
{
const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalFormat);
if (!formatInfo.compressed)
......@@ -224,7 +224,7 @@ bool ValidQueryType(const Context *context, GLenum queryType)
}
}
bool ValidProgram(const Context *context, GLuint id)
bool ValidProgram(Context *context, GLuint id)
{
// ES3 spec (section 2.11.1) -- "Commands that accept shader or program object names will generate the
// error INVALID_VALUE if the provided name is not the name of either a shader or program object and
......@@ -237,16 +237,18 @@ bool ValidProgram(const Context *context, GLuint id)
else if (context->getShader(id) != NULL)
{
// ID is the wrong type
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
// No shader/program object has this ID
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
bool ValidateAttachmentTarget(const gl::Context *context, GLenum attachment)
bool ValidateAttachmentTarget(gl::Context *context, GLenum attachment)
{
if (attachment >= GL_COLOR_ATTACHMENT0_EXT && attachment <= GL_COLOR_ATTACHMENT15_EXT)
{
......@@ -254,7 +256,8 @@ bool ValidateAttachmentTarget(const gl::Context *context, GLenum attachment)
if (colorAttachment >= context->getCaps().maxColorAttachments)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
else
......@@ -268,19 +271,21 @@ bool ValidateAttachmentTarget(const gl::Context *context, GLenum attachment)
case GL_DEPTH_STENCIL_ATTACHMENT:
if (context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
return true;
}
bool ValidateRenderbufferStorageParameters(const gl::Context *context, GLenum target, GLsizei samples,
bool ValidateRenderbufferStorageParameters(gl::Context *context, GLenum target, GLsizei samples,
GLenum internalformat, GLsizei width, GLsizei height,
bool angleExtension)
{
......@@ -289,18 +294,21 @@ bool ValidateRenderbufferStorageParameters(const gl::Context *context, GLenum ta
case GL_RENDERBUFFER:
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (width < 0 || height < 0 || samples < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalformat);
if (!formatInfo.textureSupport(context->getClientVersion(), context->getExtensions()))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
// ANGLE_framebuffer_multisample does not explicitly state that the internal format must be
......@@ -309,23 +317,27 @@ bool ValidateRenderbufferStorageParameters(const gl::Context *context, GLenum ta
// internal format must be sized and not an integer format if samples is greater than zero.
if (formatInfo.pixelBytes == 0)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if ((formatInfo.componentType == GL_UNSIGNED_INT || formatInfo.componentType == GL_INT) && samples > 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const TextureCaps &formatCaps = context->getTextureCaps().get(internalformat);
if (!formatCaps.renderable)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (static_cast<GLuint>(std::max(width, height)) > context->getCaps().maxRenderbufferSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
// ANGLE_framebuffer_multisample states that the value of samples must be less than or equal
......@@ -337,27 +349,31 @@ bool ValidateRenderbufferStorageParameters(const gl::Context *context, GLenum ta
ASSERT(context->getExtensions().framebufferMultisample);
if (static_cast<GLuint>(samples) > context->getExtensions().maxSamples)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
// Check if this specific format supports enough samples
if (static_cast<GLuint>(samples) > formatCaps.getMaxSamples())
{
return gl::error(GL_OUT_OF_MEMORY, false);
context->recordError(Error(GL_OUT_OF_MEMORY));
return false;
}
}
else
{
if (static_cast<GLuint>(samples) > formatCaps.getMaxSamples())
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
GLuint handle = context->getState().getRenderbufferId();
if (handle == 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
......@@ -368,7 +384,8 @@ bool ValidateFramebufferRenderbufferParameters(gl::Context *context, GLenum targ
{
if (!ValidFramebufferTarget(target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
gl::Framebuffer *framebuffer = context->getState().getTargetFramebuffer(target);
......@@ -376,7 +393,8 @@ bool ValidateFramebufferRenderbufferParameters(gl::Context *context, GLenum targ
if (!framebuffer || (framebufferHandle == 0 && renderbuffer != 0))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!ValidateAttachmentTarget(context, attachment))
......@@ -392,7 +410,8 @@ bool ValidateFramebufferRenderbufferParameters(gl::Context *context, GLenum targ
{
if (!context->getRenderbuffer(renderbuffer))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -434,16 +453,19 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
case GL_LINEAR:
if (fromAngleExtension)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if ((mask & ~(GL_COLOR_BUFFER_BIT | GL_STENCIL_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)) != 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (mask == 0)
......@@ -456,14 +478,16 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
if (fromAngleExtension && (srcX1 - srcX0 != dstX1 - dstX0 || srcY1 - srcY0 != dstY1 - dstY0))
{
ERR("Scaling and flipping in BlitFramebufferANGLE not supported by this implementation.");
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// ES3.0 spec, section 4.3.2 states that linear filtering is only available for the
// color buffer, leaving only nearest being unfiltered from above
if ((mask & ~GL_COLOR_BUFFER_BIT) != 0 && filter != GL_NEAREST)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (context->getState().getReadFramebuffer()->id() == context->getState().getDrawFramebuffer()->id())
......@@ -473,7 +497,8 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
ERR("Blits with the same source and destination framebuffer are not supported by this "
"implementation.");
}
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
gl::Framebuffer *readFramebuffer = context->getState().getReadFramebuffer();
......@@ -481,12 +506,14 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
if (!readFramebuffer || readFramebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE ||
!drawFramebuffer || drawFramebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_FRAMEBUFFER_OPERATION, false);
context->recordError(Error(GL_INVALID_FRAMEBUFFER_OPERATION));
return false;
}
if (drawFramebuffer->getSamples() != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
bool sameBounds = srcX0 == dstX0 && srcY0 == dstY0 && srcX1 == dstX1 && srcY1 == dstY1;
......@@ -515,29 +542,34 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
if ( (readFormatInfo.componentType == GL_UNSIGNED_NORMALIZED || readFormatInfo.componentType == GL_SIGNED_NORMALIZED) &&
!(drawFormatInfo.componentType == GL_UNSIGNED_NORMALIZED || drawFormatInfo.componentType == GL_SIGNED_NORMALIZED))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (readFormatInfo.componentType == GL_UNSIGNED_INT && drawFormatInfo.componentType != GL_UNSIGNED_INT)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (readFormatInfo.componentType == GL_INT && drawFormatInfo.componentType != GL_INT)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (readColorBuffer->getSamples() > 0 && (readInternalFormat != drawInternalFormat || !sameBounds))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
}
if ((readFormatInfo.componentType == GL_INT || readFormatInfo.componentType == GL_UNSIGNED_INT) && filter == GL_LINEAR)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (fromAngleExtension)
......@@ -545,7 +577,8 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
const GLenum readColorbufferType = readFramebuffer->getReadColorbufferType();
if (readColorbufferType != GL_TEXTURE_2D && readColorbufferType != GL_RENDERBUFFER)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
for (unsigned int colorAttachment = 0; colorAttachment < gl::IMPLEMENTATION_MAX_DRAW_BUFFERS; colorAttachment++)
......@@ -557,12 +590,14 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
if (attachment->type() != GL_TEXTURE_2D && attachment->type() != GL_RENDERBUFFER)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (attachment->getActualFormat() != readColorBuffer->getActualFormat())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
}
......@@ -570,7 +605,8 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
srcX0, srcY0, srcX1, srcY1,
dstX0, dstY0, dstX1, dstY1))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
}
......@@ -585,12 +621,14 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
{
if (readDepthBuffer->getActualFormat() != drawDepthBuffer->getActualFormat())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (readDepthBuffer->getSamples() > 0 && !sameBounds)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (fromAngleExtension)
......@@ -599,12 +637,14 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1))
{
ERR("Only whole-buffer depth and stencil blits are supported by this implementation.");
return gl::error(GL_INVALID_OPERATION, false); // only whole-buffer copies are permitted
context->recordError(Error(GL_INVALID_OPERATION)); // only whole-buffer copies are permitted
return false;
}
if (readDepthBuffer->getSamples() != 0 || drawDepthBuffer->getSamples() != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
}
......@@ -619,12 +659,14 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
{
if (readStencilBuffer->getActualFormat() != drawStencilBuffer->getActualFormat())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (readStencilBuffer->getSamples() > 0 && !sameBounds)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (fromAngleExtension)
......@@ -633,12 +675,14 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
srcX0, srcY0, srcX1, srcY1, dstX0, dstY0, dstX1, dstY1))
{
ERR("Only whole-buffer depth and stencil blits are supported by this implementation.");
return gl::error(GL_INVALID_OPERATION, false); // only whole-buffer copies are permitted
context->recordError(Error(GL_INVALID_OPERATION)); // only whole-buffer copies are permitted
return false;
}
if (readStencilBuffer->getSamples() != 0 || drawStencilBuffer->getSamples() != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
}
......@@ -647,7 +691,7 @@ bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint
return true;
}
bool ValidateGetVertexAttribParameters(GLenum pname, int clientVersion)
bool ValidateGetVertexAttribParameters(Context *context, GLenum pname)
{
switch (pname)
{
......@@ -667,10 +711,16 @@ bool ValidateGetVertexAttribParameters(GLenum pname, int clientVersion)
return true;
case GL_VERTEX_ATTRIB_ARRAY_INTEGER:
return ((clientVersion >= 3) ? true : gl::error(GL_INVALID_ENUM, false));
if (context->getClientVersion() < 3)
{
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
......@@ -691,7 +741,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_TEXTURE_MAX_LOD:
if (context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
......@@ -710,7 +761,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_MIRRORED_REPEAT:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
case GL_TEXTURE_MIN_FILTER:
......@@ -724,7 +776,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_LINEAR_MIPMAP_LINEAR:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
......@@ -735,7 +788,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_LINEAR:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
......@@ -746,20 +800,23 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_FRAMEBUFFER_ATTACHMENT_ANGLE:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_TEXTURE_MAX_ANISOTROPY_EXT:
if (!context->getExtensions().textureFilterAnisotropic)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
// we assume the parameter passed to this validation method is truncated, not rounded
if (param < 1)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
return true;
......@@ -776,7 +833,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_COMPARE_REF_TO_TEXTURE:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
......@@ -794,7 +852,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_NEVER:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
......@@ -812,7 +871,8 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_ONE:
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
......@@ -820,16 +880,18 @@ bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param)
case GL_TEXTURE_MAX_LEVEL:
if (param < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
bool ValidateSamplerObjectParameter(GLenum pname)
bool ValidateSamplerObjectParameter(gl::Context *context, GLenum pname)
{
switch (pname)
{
......@@ -845,7 +907,8 @@ bool ValidateSamplerObjectParameter(GLenum pname)
return true;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
......@@ -857,17 +920,20 @@ bool ValidateReadPixelsParameters(gl::Context *context, GLint x, GLint y, GLsize
if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_FRAMEBUFFER_OPERATION, false);
context->recordError(Error(GL_INVALID_FRAMEBUFFER_OPERATION));
return false;
}
if (context->getState().getReadFramebuffer()->id() != 0 && framebuffer->getSamples() != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!framebuffer->getReadColorbuffer())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
GLenum currentInternalFormat, currentFormat, currentType;
......@@ -880,7 +946,8 @@ bool ValidateReadPixelsParameters(gl::Context *context, GLint x, GLint y, GLsize
if (!(currentFormat == format && currentType == type) && !validReadFormat)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
GLenum sizedInternalFormat = GetSizedInternalFormat(format, type);
......@@ -893,7 +960,8 @@ bool ValidateReadPixelsParameters(gl::Context *context, GLint x, GLint y, GLsize
int requiredSize = outputPitch * height;
if (requiredSize > *bufSize)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -904,12 +972,14 @@ bool ValidateBeginQuery(gl::Context *context, GLenum target, GLuint id)
{
if (!ValidQueryType(context, target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (id == 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// From EXT_occlusion_query_boolean: If BeginQueryEXT is called with an <id>
......@@ -929,7 +999,8 @@ bool ValidateBeginQuery(gl::Context *context, GLenum target, GLuint id)
// no query may be active for either if glBeginQuery targets either.
if (context->getState().isQueryActive())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
Query *queryObject = context->getQuery(id, true, target);
......@@ -937,13 +1008,15 @@ bool ValidateBeginQuery(gl::Context *context, GLenum target, GLuint id)
// check that name was obtained with glGenQueries
if (!queryObject)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// check for type mismatch
if (queryObject->getType() != target)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
......@@ -953,19 +1026,22 @@ bool ValidateEndQuery(gl::Context *context, GLenum target)
{
if (!ValidQueryType(context, target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
const Query *queryObject = context->getState().getActiveQuery(target);
if (queryObject == NULL)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!queryObject->isStarted())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
......@@ -976,13 +1052,15 @@ static bool ValidateUniformCommonBase(gl::Context *context, GLenum targetUniform
{
if (count < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::ProgramBinary *programBinary = context->getState().getCurrentProgramBinary();
if (!programBinary)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (location == -1)
......@@ -993,7 +1071,8 @@ static bool ValidateUniformCommonBase(gl::Context *context, GLenum targetUniform
if (!programBinary->isValidUniformLocation(location))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
LinkedUniform *uniform = programBinary->getUniformByLocation(location);
......@@ -1001,7 +1080,8 @@ static bool ValidateUniformCommonBase(gl::Context *context, GLenum targetUniform
// attempting to write an array to a non-array uniform is an INVALID_OPERATION
if (uniform->elementCount() == 1 && count > 1)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
*uniformOut = uniform;
......@@ -1013,7 +1093,8 @@ bool ValidateUniform(gl::Context *context, GLenum uniformType, GLint location, G
// Check for ES3 uniform entry points
if (VariableComponentType(uniformType) == GL_UNSIGNED_INT && context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
LinkedUniform *uniform = NULL;
......@@ -1026,7 +1107,8 @@ bool ValidateUniform(gl::Context *context, GLenum uniformType, GLint location, G
bool samplerUniformCheck = (IsSampler(uniform->type) && uniformType == GL_INT);
if (!samplerUniformCheck && uniformType != uniform->type && targetBoolType != uniform->type)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
......@@ -1040,12 +1122,14 @@ bool ValidateUniformMatrix(gl::Context *context, GLenum matrixType, GLint locati
int cols = VariableColumnCount(matrixType);
if (rows != cols && context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (transpose != GL_FALSE && context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
LinkedUniform *uniform = NULL;
......@@ -1056,7 +1140,8 @@ bool ValidateUniformMatrix(gl::Context *context, GLenum matrixType, GLint locati
if (uniform->type != matrixType)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
......@@ -1066,7 +1151,8 @@ bool ValidateStateQuery(gl::Context *context, GLenum pname, GLenum *nativeType,
{
if (!context->getQueryParameterInfo(pname, nativeType, numParams))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (pname >= GL_DRAW_BUFFER0 && pname <= GL_DRAW_BUFFER15)
......@@ -1075,7 +1161,8 @@ bool ValidateStateQuery(gl::Context *context, GLenum pname, GLenum *nativeType,
if (colorAttachment >= context->getCaps().maxDrawBuffers)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -1087,7 +1174,8 @@ bool ValidateStateQuery(gl::Context *context, GLenum pname, GLenum *nativeType,
case GL_TEXTURE_BINDING_2D_ARRAY:
if (context->getState().getActiveSampler() >= context->getCaps().maxCombinedTextureImageUnits)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
......@@ -1098,13 +1186,15 @@ bool ValidateStateQuery(gl::Context *context, GLenum pname, GLenum *nativeType,
ASSERT(framebuffer);
if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
FramebufferAttachment *attachment = framebuffer->getReadColorbuffer();
if (!attachment)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
break;
......@@ -1129,38 +1219,45 @@ bool ValidateCopyTexImageParametersBase(gl::Context* context, GLenum target, GLi
if (!ValidTexture2DDestinationTarget(context, target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (level < 0 || xoffset < 0 || yoffset < 0 || zoffset < 0 || width < 0 || height < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (std::numeric_limits<GLsizei>::max() - xoffset < width || std::numeric_limits<GLsizei>::max() - yoffset < height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (border != 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!ValidMipLevel(context, target, level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Framebuffer *framebuffer = context->getState().getReadFramebuffer();
if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_FRAMEBUFFER_OPERATION, false);
context->recordError(Error(GL_INVALID_FRAMEBUFFER_OPERATION));
return false;
}
if (context->getState().getReadFramebuffer()->id() != 0 && framebuffer->getSamples() != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::Caps &caps = context->getCaps();
......@@ -1240,24 +1337,28 @@ bool ValidateCopyTexImageParametersBase(gl::Context* context, GLenum target, GLi
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (!texture)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (texture->isImmutable() && !isSubImage)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalformat);
if (formatInfo.depthBits > 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (formatInfo.compressed)
......@@ -1265,7 +1366,8 @@ bool ValidateCopyTexImageParametersBase(gl::Context* context, GLenum target, GLi
if (((width % formatInfo.compressedBlockWidth) != 0 && width != textureLevelWidth) ||
((height % formatInfo.compressedBlockHeight) != 0 && height != textureLevelHeight))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -1275,25 +1377,29 @@ bool ValidateCopyTexImageParametersBase(gl::Context* context, GLenum target, GLi
yoffset + height > textureLevelHeight ||
zoffset >= textureLevelDepth)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
else
{
if (IsCubemapTextureTarget(target) && width != height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!formatInfo.textureSupport(context->getClientVersion(), context->getExtensions()))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
int maxLevelDimension = (maxDimension >> level);
if (static_cast<int>(width) > maxLevelDimension || static_cast<int>(height) > maxLevelDimension)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
......@@ -1301,7 +1407,7 @@ bool ValidateCopyTexImageParametersBase(gl::Context* context, GLenum target, GLi
return true;
}
static bool ValidateDrawBase(const gl::State &state, GLenum mode, GLsizei count, GLsizei maxVertex, GLsizei primcount)
static bool ValidateDrawBase(Context *context, GLenum mode, GLsizei count, GLsizei maxVertex, GLsizei primcount)
{
switch (mode)
{
......@@ -1314,18 +1420,23 @@ static bool ValidateDrawBase(const gl::State &state, GLenum mode, GLsizei count,
case GL_TRIANGLE_FAN:
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (count < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
const State &state = context->getState();
// Check for mapped buffers
if (state.hasMappedBuffer(GL_ARRAY_BUFFER))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::DepthStencilState &depthStencilState = state.getDepthStencilState();
......@@ -1337,24 +1448,28 @@ static bool ValidateDrawBase(const gl::State &state, GLenum mode, GLsizei count,
// See Section 6.10 of the WebGL 1.0 spec
ERR("This ANGLE implementation does not support separate front/back stencil "
"writemasks, reference values, or stencil mask values.");
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::Framebuffer *fbo = state.getDrawFramebuffer();
if (!fbo || fbo->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_FRAMEBUFFER_OPERATION, false);
context->recordError(Error(GL_INVALID_FRAMEBUFFER_OPERATION));
return false;
}
if (state.getCurrentProgramId() == 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
gl::ProgramBinary *programBinary = state.getCurrentProgramBinary();
if (!programBinary->validateSamplers(NULL))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// Buffer validations
......@@ -1388,15 +1503,16 @@ static bool ValidateDrawBase(const gl::State &state, GLenum mode, GLsizei count,
// enough backing data.
if (attribDataSize > buffer->getSize())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
else if (attrib.pointer == NULL)
{
// This is an application error that would normally result in a crash,
// but we catch it and return an error
ERR("An enabled vertex array has no buffer and no pointer.");
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION, "An enabled vertex array has no buffer and no pointer."));
return false;
}
}
}
......@@ -1405,11 +1521,12 @@ static bool ValidateDrawBase(const gl::State &state, GLenum mode, GLsizei count,
return (count > 0);
}
bool ValidateDrawArrays(const gl::Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount)
bool ValidateDrawArrays(Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount)
{
if (first < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
const State &state = context->getState();
......@@ -1420,10 +1537,11 @@ bool ValidateDrawArrays(const gl::Context *context, GLenum mode, GLint first, GL
// It is an invalid operation to call DrawArrays or DrawArraysInstanced with a draw mode
// that does not match the current transform feedback object's draw mode (if transform feedback
// is active), (3.0.2, section 2.14, pg 86)
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!ValidateDrawBase(state, mode, count, count, primcount))
if (!ValidateDrawBase(context, mode, count, count, primcount))
{
return false;
}
......@@ -1431,11 +1549,12 @@ bool ValidateDrawArrays(const gl::Context *context, GLenum mode, GLint first, GL
return true;
}
bool ValidateDrawArraysInstanced(const gl::Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount)
bool ValidateDrawArraysInstanced(Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount)
{
if (primcount < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!ValidateDrawArrays(context, mode, first, count, primcount))
......@@ -1447,7 +1566,7 @@ bool ValidateDrawArraysInstanced(const gl::Context *context, GLenum mode, GLint
return (primcount > 0);
}
bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count, GLenum type,
bool ValidateDrawElements(Context *context, GLenum mode, GLsizei count, GLenum type,
const GLvoid* indices, GLsizei primcount, rx::RangeUI *indexRangeOut)
{
switch (type)
......@@ -1458,11 +1577,13 @@ bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count
case GL_UNSIGNED_INT:
if (!context->getExtensions().elementIndexUint)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
const State &state = context->getState();
......@@ -1472,20 +1593,23 @@ bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count
{
// It is an invalid operation to call DrawElements, DrawRangeElements or DrawElementsInstanced
// while transform feedback is active, (3.0.2, section 2.14, pg 86)
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// Check for mapped buffers
if (state.hasMappedBuffer(GL_ELEMENT_ARRAY_BUFFER))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::VertexArray *vao = state.getVertexArray();
const gl::Buffer *elementArrayBuffer = vao->getElementArrayBuffer();
if (!indices && !elementArrayBuffer)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (elementArrayBuffer)
......@@ -1499,19 +1623,22 @@ bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count
if (static_cast<GLuint>(count) > (std::numeric_limits<GLuint>::max() / typeInfo.bytes) ||
byteCount > static_cast<GLint64>(std::numeric_limits<GLuint>::max()))
{
return gl::error(GL_OUT_OF_MEMORY, false);
context->recordError(Error(GL_OUT_OF_MEMORY));
return false;
}
// Check for reading past the end of the bound buffer object
if (byteCount > elementArrayBuffer->getSize())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
else if (!indices)
{
// Catch this programming error here
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// Use max index to validate if our vertex buffers are large enough for the pull.
......@@ -1532,7 +1659,7 @@ bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count
*indexRangeOut = rx::IndexRangeCache::ComputeRange(type, indices, count);
}
if (!ValidateDrawBase(state, mode, count, static_cast<GLsizei>(indexRangeOut->end), primcount))
if (!ValidateDrawBase(context, mode, count, static_cast<GLsizei>(indexRangeOut->end), primcount))
{
return false;
}
......@@ -1540,14 +1667,15 @@ bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count
return true;
}
bool ValidateDrawElementsInstanced(const gl::Context *context,
bool ValidateDrawElementsInstanced(Context *context,
GLenum mode, GLsizei count, GLenum type,
const GLvoid *indices, GLsizei primcount,
rx::RangeUI *indexRangeOut)
{
if (primcount < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!ValidateDrawElements(context, mode, count, type, indices, primcount, indexRangeOut))
......@@ -1559,12 +1687,13 @@ bool ValidateDrawElementsInstanced(const gl::Context *context,
return (primcount > 0);
}
bool ValidateFramebufferTextureBase(const gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferTextureBase(Context *context, GLenum target, GLenum attachment,
GLuint texture, GLint level)
{
if (!ValidFramebufferTarget(target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (!ValidateAttachmentTarget(context, attachment))
......@@ -1578,12 +1707,14 @@ bool ValidateFramebufferTextureBase(const gl::Context *context, GLenum target, G
if (tex == NULL)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (level < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
......@@ -1592,19 +1723,21 @@ bool ValidateFramebufferTextureBase(const gl::Context *context, GLenum target, G
if (framebufferHandle == 0 || !framebuffer)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
}
bool ValidateFramebufferTexture2D(const gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferTexture2D(Context *context, GLenum target, GLenum attachment,
GLenum textarget, GLuint texture, GLint level)
{
// Attachments are required to be bound to level 0 in ES2
if (context->getClientVersion() < 3 && level != 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!ValidateFramebufferTextureBase(context, target, attachment, texture, level))
......@@ -1625,16 +1758,19 @@ bool ValidateFramebufferTexture2D(const gl::Context *context, GLenum target, GLe
{
if (level > gl::log2(caps.max2DTextureSize))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (tex->getTarget() != GL_TEXTURE_2D)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
gl::Texture2D *tex2d = static_cast<gl::Texture2D *>(tex);
if (tex2d->isCompressed(level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
break;
......@@ -1648,67 +1784,75 @@ bool ValidateFramebufferTexture2D(const gl::Context *context, GLenum target, GLe
{
if (level > gl::log2(caps.maxCubeMapTextureSize))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (tex->getTarget() != GL_TEXTURE_CUBE_MAP)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
gl::TextureCubeMap *texcube = static_cast<gl::TextureCubeMap *>(tex);
if (texcube->isCompressed(textarget, level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
return true;
}
bool ValidateGetUniformBase(const gl::Context *context, GLuint program, GLint location)
bool ValidateGetUniformBase(Context *context, GLuint program, GLint location)
{
if (program == 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Program *programObject = context->getProgram(program);
if (!programObject || !programObject->isLinked())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
gl::ProgramBinary *programBinary = programObject->getProgramBinary();
if (!programBinary)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!programBinary->isValidUniformLocation(location))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
}
bool ValidateGetUniformfv(const gl::Context *context, GLuint program, GLint location, GLfloat* params)
bool ValidateGetUniformfv(Context *context, GLuint program, GLint location, GLfloat* params)
{
return ValidateGetUniformBase(context, program, location);
}
bool ValidateGetUniformiv(const gl::Context *context, GLuint program, GLint location, GLint* params)
bool ValidateGetUniformiv(Context *context, GLuint program, GLint location, GLint* params)
{
return ValidateGetUniformBase(context, program, location);
}
static bool ValidateSizedGetUniform(const gl::Context *context, GLuint program, GLint location, GLsizei bufSize)
static bool ValidateSizedGetUniform(Context *context, GLuint program, GLint location, GLsizei bufSize)
{
if (!ValidateGetUniformBase(context, program, location))
{
......@@ -1722,18 +1866,19 @@ static bool ValidateSizedGetUniform(const gl::Context *context, GLuint program,
size_t requiredBytes = VariableExternalSize(uniform->type);
if (static_cast<size_t>(bufSize) < requiredBytes)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
}
bool ValidateGetnUniformfvEXT(const gl::Context *context, GLuint program, GLint location, GLsizei bufSize, GLfloat* params)
bool ValidateGetnUniformfvEXT(Context *context, GLuint program, GLint location, GLsizei bufSize, GLfloat* params)
{
return ValidateSizedGetUniform(context, program, location, bufSize);
}
bool ValidateGetnUniformivEXT(const gl::Context *context, GLuint program, GLint location, GLsizei bufSize, GLint* params)
bool ValidateGetnUniformivEXT(Context *context, GLuint program, GLint location, GLsizei bufSize, GLint* params)
{
return ValidateSizedGetUniform(context, program, location, bufSize);
}
......
......@@ -26,63 +26,63 @@ bool ValidFramebufferTarget(GLenum target);
bool ValidBufferTarget(const Context *context, GLenum target);
bool ValidBufferParameter(const Context *context, GLenum pname);
bool ValidMipLevel(const Context *context, GLenum target, GLint level);
bool ValidImageSize(const gl::Context *context, GLenum target, GLint level, GLsizei width, GLsizei height, GLsizei depth);
bool ValidCompressedImageSize(const gl::Context *context, GLenum internalFormat, GLsizei width, GLsizei height);
bool ValidQueryType(const gl::Context *context, GLenum queryType);
bool ValidProgram(const gl::Context *context, GLuint id);
bool ValidImageSize(const Context *context, GLenum target, GLint level, GLsizei width, GLsizei height, GLsizei depth);
bool ValidCompressedImageSize(const Context *context, GLenum internalFormat, GLsizei width, GLsizei height);
bool ValidQueryType(const Context *context, GLenum queryType);
bool ValidProgram(Context *context, GLuint id);
bool ValidateAttachmentTarget(const gl::Context *context, GLenum attachment);
bool ValidateRenderbufferStorageParameters(const gl::Context *context, GLenum target, GLsizei samples,
bool ValidateAttachmentTarget(Context *context, GLenum attachment);
bool ValidateRenderbufferStorageParameters(Context *context, GLenum target, GLsizei samples,
GLenum internalformat, GLsizei width, GLsizei height,
bool angleExtension);
bool ValidateFramebufferRenderbufferParameters(gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferRenderbufferParameters(Context *context, GLenum target, GLenum attachment,
GLenum renderbuffertarget, GLuint renderbuffer);
bool ValidateBlitFramebufferParameters(gl::Context *context, GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1,
bool ValidateBlitFramebufferParameters(Context *context, GLint srcX0, GLint srcY0, GLint srcX1, GLint srcY1,
GLint dstX0, GLint dstY0, GLint dstX1, GLint dstY1, GLbitfield mask,
GLenum filter, bool fromAngleExtension);
bool ValidateGetVertexAttribParameters(GLenum pname, int clientVersion);
bool ValidateGetVertexAttribParameters(Context *context, GLenum pname);
bool ValidateTexParamParameters(gl::Context *context, GLenum pname, GLint param);
bool ValidateTexParamParameters(Context *context, GLenum pname, GLint param);
bool ValidateSamplerObjectParameter(GLenum pname);
bool ValidateSamplerObjectParameter(Context *context, GLenum pname);
bool ValidateReadPixelsParameters(gl::Context *context, GLint x, GLint y, GLsizei width, GLsizei height,
bool ValidateReadPixelsParameters(Context *context, GLint x, GLint y, GLsizei width, GLsizei height,
GLenum format, GLenum type, GLsizei *bufSize, GLvoid *pixels);
bool ValidateBeginQuery(gl::Context *context, GLenum target, GLuint id);
bool ValidateEndQuery(gl::Context *context, GLenum target);
bool ValidateBeginQuery(Context *context, GLenum target, GLuint id);
bool ValidateEndQuery(Context *context, GLenum target);
bool ValidateUniform(gl::Context *context, GLenum uniformType, GLint location, GLsizei count);
bool ValidateUniformMatrix(gl::Context *context, GLenum matrixType, GLint location, GLsizei count,
bool ValidateUniform(Context *context, GLenum uniformType, GLint location, GLsizei count);
bool ValidateUniformMatrix(Context *context, GLenum matrixType, GLint location, GLsizei count,
GLboolean transpose);
bool ValidateStateQuery(gl::Context *context, GLenum pname, GLenum *nativeType, unsigned int *numParams);
bool ValidateStateQuery(Context *context, GLenum pname, GLenum *nativeType, unsigned int *numParams);
bool ValidateCopyTexImageParametersBase(gl::Context* context, GLenum target, GLint level, GLenum internalformat, bool isSubImage,
bool ValidateCopyTexImageParametersBase(Context* context, GLenum target, GLint level, GLenum internalformat, bool isSubImage,
GLint xoffset, GLint yoffset, GLint zoffset, GLint x, GLint y, GLsizei width, GLsizei height,
GLint border, GLenum *textureInternalFormatOut);
bool ValidateDrawArrays(const gl::Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount);
bool ValidateDrawArraysInstanced(const gl::Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount);
bool ValidateDrawArrays(Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount);
bool ValidateDrawArraysInstanced(Context *context, GLenum mode, GLint first, GLsizei count, GLsizei primcount);
bool ValidateDrawElements(const gl::Context *context, GLenum mode, GLsizei count, GLenum type,
bool ValidateDrawElements(Context *context, GLenum mode, GLsizei count, GLenum type,
const GLvoid* indices, GLsizei primcount, rx::RangeUI *indexRangeOut);
bool ValidateDrawElementsInstanced(const gl::Context *context, GLenum mode, GLsizei count, GLenum type,
bool ValidateDrawElementsInstanced(Context *context, GLenum mode, GLsizei count, GLenum type,
const GLvoid *indices, GLsizei primcount, rx::RangeUI *indexRangeOut);
bool ValidateFramebufferTextureBase(const gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferTextureBase(Context *context, GLenum target, GLenum attachment,
GLuint texture, GLint level);
bool ValidateFramebufferTexture2D(const gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferTexture2D(Context *context, GLenum target, GLenum attachment,
GLenum textarget, GLuint texture, GLint level);
bool ValidateGetUniformBase(const gl::Context *context, GLuint program, GLint location);
bool ValidateGetUniformfv(const gl::Context *context, GLuint program, GLint location, GLfloat* params);
bool ValidateGetUniformiv(const gl::Context *context, GLuint program, GLint location, GLint* params);
bool ValidateGetnUniformfvEXT(const gl::Context *context, GLuint program, GLint location, GLsizei bufSize, GLfloat* params);
bool ValidateGetnUniformivEXT(const gl::Context *context, GLuint program, GLint location, GLsizei bufSize, GLint* params);
bool ValidateGetUniformBase(Context *context, GLuint program, GLint location);
bool ValidateGetUniformfv(Context *context, GLuint program, GLint location, GLfloat* params);
bool ValidateGetUniformiv(Context *context, GLuint program, GLint location, GLint* params);
bool ValidateGetnUniformfvEXT(Context *context, GLuint program, GLint location, GLsizei bufSize, GLfloat* params);
bool ValidateGetnUniformivEXT(Context *context, GLuint program, GLint location, GLsizei bufSize, GLint* params);
}
......
......@@ -22,25 +22,28 @@
namespace gl
{
static bool validateSubImageParams2D(bool compressed, GLsizei width, GLsizei height,
static bool ValidateSubImageParams2D(Context *context, bool compressed, GLsizei width, GLsizei height,
GLint xoffset, GLint yoffset, GLint level, GLenum format, GLenum type,
gl::Texture2D *texture)
{
if (!texture)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (compressed != texture->isCompressed(level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (format != GL_NONE)
{
if (gl::GetFormatTypeInfo(format, type).internalFormat != texture->getInternalFormat(level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -49,38 +52,43 @@ static bool validateSubImageParams2D(bool compressed, GLsizei width, GLsizei hei
if ((width % 4 != 0 && width != texture->getWidth(level)) ||
(height % 4 != 0 && height != texture->getHeight(level)))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
if (xoffset + width > texture->getWidth(level) ||
yoffset + height > texture->getHeight(level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
return true;
}
static bool validateSubImageParamsCube(bool compressed, GLsizei width, GLsizei height,
static bool ValidateSubImageParamsCube(Context *context, bool compressed, GLsizei width, GLsizei height,
GLint xoffset, GLint yoffset, GLenum target, GLint level, GLenum format, GLenum type,
gl::TextureCubeMap *texture)
{
if (!texture)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (compressed != texture->isCompressed(target, level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (format != GL_NONE)
{
if (gl::GetFormatTypeInfo(format, type).internalFormat != texture->getInternalFormat(target, level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -89,43 +97,49 @@ static bool validateSubImageParamsCube(bool compressed, GLsizei width, GLsizei h
if ((width % 4 != 0 && width != texture->getWidth(target, 0)) ||
(height % 4 != 0 && height != texture->getHeight(target, 0)))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
if (xoffset + width > texture->getWidth(target, level) ||
yoffset + height > texture->getHeight(target, level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
return true;
}
bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
bool ValidateES2TexImageParameters(Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
GLint border, GLenum format, GLenum type, const GLvoid *pixels)
{
if (!ValidTexture2DDestinationTarget(context, target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (!ValidImageSize(context, target, level, width, height, 1))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (level < 0 || xoffset < 0 ||
std::numeric_limits<GLsizei>::max() - xoffset < width ||
std::numeric_limits<GLsizei>::max() - yoffset < height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!isSubImage && !isCompressed && internalformat != format)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::Caps &caps = context->getCaps();
......@@ -142,7 +156,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
if (static_cast<GLuint>(width) > (caps.max2DTextureSize >> level) ||
static_cast<GLuint>(height) > (caps.max2DTextureSize >> level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Texture2D *tex2d = context->getTexture2D();
......@@ -155,7 +170,7 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
texture = tex2d;
}
if (isSubImage && !validateSubImageParams2D(isCompressed, width, height, xoffset, yoffset,
if (isSubImage && !ValidateSubImageParams2D(context, isCompressed, width, height, xoffset, yoffset,
level, format, type, tex2d))
{
return false;
......@@ -174,13 +189,15 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
{
if (!isSubImage && width != height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (static_cast<GLuint>(width) > (caps.maxCubeMapTextureSize >> level) ||
static_cast<GLuint>(height) > (caps.maxCubeMapTextureSize >> level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::TextureCubeMap *texCube = context->getTextureCubeMap();
......@@ -193,7 +210,7 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
texture = texCube;
}
if (isSubImage && !validateSubImageParamsCube(isCompressed, width, height, xoffset, yoffset,
if (isSubImage && !ValidateSubImageParamsCube(context, isCompressed, width, height, xoffset, yoffset,
target, level, format, type, texCube))
{
return false;
......@@ -202,23 +219,27 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (!texture)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!isSubImage && texture->isImmutable())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// Verify zero border
if (border != 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
GLenum actualInternalFormat = isSubImage ? textureInternalFormat : internalformat;
......@@ -226,7 +247,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
{
if (!ValidCompressedImageSize(context, actualInternalFormat, width, height))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
switch (actualInternalFormat)
......@@ -235,23 +257,27 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
if (!context->getExtensions().textureCompressionDXT1)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
if (!context->getExtensions().textureCompressionDXT1)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
if (!context->getExtensions().textureCompressionDXT5)
if (!context->getExtensions().textureCompressionDXT5)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
else
......@@ -270,7 +296,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_FLOAT:
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
// validate <format> + <type> combinations
......@@ -287,15 +314,17 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_FLOAT:
case GL_HALF_FLOAT_OES:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
default:
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RED:
case GL_RG:
if (!context->getExtensions().textureRG)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
switch (type)
{
......@@ -304,7 +333,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_HALF_FLOAT_OES:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RGB:
......@@ -316,7 +346,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_HALF_FLOAT_OES:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RGBA:
......@@ -329,7 +360,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_HALF_FLOAT_OES:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_BGRA_EXT:
......@@ -338,21 +370,24 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_UNSIGNED_BYTE:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_SRGB_EXT:
case GL_SRGB_ALPHA_EXT:
if (!context->getExtensions().sRGB)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
switch (type)
{
case GL_UNSIGNED_BYTE:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_COMPRESSED_RGB_S3TC_DXT1_EXT: // error cases for compressed textures are handled below
......@@ -367,7 +402,8 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_UNSIGNED_INT:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_DEPTH_STENCIL_OES:
......@@ -376,11 +412,13 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_UNSIGNED_INT_24_8_OES:
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
switch (format)
......@@ -389,48 +427,57 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
if (context->getExtensions().textureCompressionDXT1)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
if (context->getExtensions().textureCompressionDXT3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
if (context->getExtensions().textureCompressionDXT5)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_DEPTH_COMPONENT:
case GL_DEPTH_STENCIL_OES:
if (!context->getExtensions().depthTextures)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (target != GL_TEXTURE_2D)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// OES_depth_texture supports loading depth data and multiple levels,
// but ANGLE_depth_texture does not
if (pixels != NULL || level != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
default:
......@@ -441,14 +488,16 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
{
if (!context->getExtensions().textureFloat)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
else if (type == GL_HALF_FLOAT_OES)
{
if (!context->getExtensions().textureHalfFloat)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
}
......@@ -458,7 +507,7 @@ bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint le
bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLint level, GLenum internalformat, bool isSubImage,
bool ValidateES2CopyTexImageParameters(Context* context, GLenum target, GLint level, GLenum internalformat, bool isSubImage,
GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height,
GLint border)
{
......@@ -485,7 +534,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_RGB5_A1 &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_LUMINANCE:
......@@ -497,7 +547,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_RGB5_A1 &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RED_EXT:
......@@ -509,7 +560,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_RGB5_A1 &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RG_EXT:
......@@ -520,7 +572,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_RGB5_A1 &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RGB:
......@@ -530,7 +583,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_RGB5_A1 &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_LUMINANCE_ALPHA:
......@@ -539,19 +593,23 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_RGB5_A1 &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
case GL_DEPTH_COMPONENT:
case GL_DEPTH_STENCIL_OES:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
else
......@@ -565,7 +623,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_BGRA8_EXT &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_LUMINANCE:
......@@ -578,7 +637,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_BGRA8_EXT &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RED_EXT:
......@@ -591,7 +651,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_BGRA8_EXT &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RG_EXT:
......@@ -603,7 +664,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_BGRA8_EXT &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_RGB:
......@@ -614,7 +676,8 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_BGRA8_EXT &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_LUMINANCE_ALPHA:
......@@ -624,38 +687,45 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
colorbufferFormat != GL_BGRA8_EXT &&
colorbufferFormat != GL_RGBA8_OES)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
if (context->getExtensions().textureCompressionDXT1)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
if (context->getExtensions().textureCompressionDXT3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
if (context->getExtensions().textureCompressionDXT5)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_DEPTH_COMPONENT:
......@@ -665,14 +735,17 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
case GL_DEPTH24_STENCIL8_OES:
if (context->getExtensions().depthTextures)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
else
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
......@@ -680,33 +753,38 @@ bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLin
return (width > 0 && height > 0);
}
bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsizei levels, GLenum internalformat,
bool ValidateES2TexStorageParameters(Context *context, GLenum target, GLsizei levels, GLenum internalformat,
GLsizei width, GLsizei height)
{
if (target != GL_TEXTURE_2D && target != GL_TEXTURE_CUBE_MAP)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (width < 1 || height < 1 || levels < 1)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (target == GL_TEXTURE_CUBE_MAP && width != height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (levels != 1 && levels != gl::log2(std::max(width, height)) + 1)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalformat);
if (formatInfo.format == GL_NONE || formatInfo.type == GL_NONE)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
const gl::Caps &caps = context->getCaps();
......@@ -717,25 +795,29 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
if (static_cast<GLuint>(width) > caps.max2DTextureSize ||
static_cast<GLuint>(height) > caps.max2DTextureSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
break;
case GL_TEXTURE_CUBE_MAP:
if (static_cast<GLuint>(width) > caps.maxCubeMapTextureSize ||
static_cast<GLuint>(height) > caps.maxCubeMapTextureSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (levels != 1 && !context->getExtensions().textureNPOT)
{
if (!gl::isPow2(width) || !gl::isPow2(height))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -745,19 +827,22 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
if (!context->getExtensions().textureCompressionDXT1)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT3_ANGLE:
if (!context->getExtensions().textureCompressionDXT3)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COMPRESSED_RGBA_S3TC_DXT5_ANGLE:
if (!context->getExtensions().textureCompressionDXT5)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_RGBA32F_EXT:
......@@ -767,7 +852,8 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
case GL_LUMINANCE_ALPHA32F_EXT:
if (!context->getExtensions().textureFloat)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_RGBA16F_EXT:
......@@ -777,7 +863,8 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
case GL_LUMINANCE_ALPHA16F_EXT:
if (!context->getExtensions().textureHalfFloat)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_R8_EXT:
......@@ -788,7 +875,8 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
case GL_RG32F_EXT:
if (!context->getExtensions().textureRG)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_DEPTH_COMPONENT16:
......@@ -796,16 +884,19 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
case GL_DEPTH24_STENCIL8_OES:
if (!context->getExtensions().depthTextures)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (target != GL_TEXTURE_2D)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// ANGLE_depth_texture only supports 1-level textures
if (levels != 1)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
break;
default:
......@@ -827,19 +918,21 @@ bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsize
if (!texture || texture->id() == 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (texture->isImmutable())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
}
// check for combinations of format and type that are valid for ReadPixels
bool ValidES2ReadFormatType(gl::Context *context, GLenum format, GLenum type)
bool ValidES2ReadFormatType(Context *context, GLenum format, GLenum type)
{
switch (format)
{
......
......@@ -16,18 +16,18 @@ namespace gl
class Context;
bool ValidateES2TexImageParameters(gl::Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
bool ValidateES2TexImageParameters(Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
GLint xoffset, GLint yoffset, GLsizei width, GLsizei height,
GLint border, GLenum format, GLenum type, const GLvoid *pixels);
bool ValidateES2CopyTexImageParameters(gl::Context* context, GLenum target, GLint level, GLenum internalformat, bool isSubImage,
bool ValidateES2CopyTexImageParameters(Context* context, GLenum target, GLint level, GLenum internalformat, bool isSubImage,
GLint xoffset, GLint yoffset, GLint x, GLint y, GLsizei width, GLsizei height,
GLint border);
bool ValidateES2TexStorageParameters(gl::Context *context, GLenum target, GLsizei levels, GLenum internalformat,
bool ValidateES2TexStorageParameters(Context *context, GLenum target, GLsizei levels, GLenum internalformat,
GLsizei width, GLsizei height);
bool ValidES2ReadFormatType(gl::Context *context, GLenum format, GLenum type);
bool ValidES2ReadFormatType(Context *context, GLenum format, GLenum type);
}
......
......@@ -21,7 +21,6 @@
namespace gl
{
// ES3 has a specific set of permutations of internal formats, formats and types which are acceptable.
struct ES3FormatCombination
{
GLenum internalFormat;
......@@ -224,7 +223,8 @@ static bool ValidateTexImageFormatCombination(gl::Context *context, GLenum inter
const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalFormat);
if (!formatInfo.textureSupport(context->getClientVersion(), context->getExtensions()))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
// The type and format are valid if any supported internal format has that type and format
......@@ -257,7 +257,8 @@ static bool ValidateTexImageFormatCombination(gl::Context *context, GLenum inter
if (!typeSupported || !formatSupported)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
// Check if this is a valid format combination to load texture data
......@@ -268,31 +269,35 @@ static bool ValidateTexImageFormatCombination(gl::Context *context, GLenum inter
if (es3FormatSet.find(searchFormat) == es3FormatSet.end())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return true;
}
bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
bool ValidateES3TexImageParameters(Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
GLint xoffset, GLint yoffset, GLint zoffset, GLsizei width, GLsizei height, GLsizei depth,
GLint border, GLenum format, GLenum type, const GLvoid *pixels)
{
if (!ValidTexture2DDestinationTarget(context, target))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
// Validate image size
if (!ValidImageSize(context, target, level, width, height, depth))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
// Verify zero border
if (border != 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (xoffset < 0 || yoffset < 0 || zoffset < 0 ||
......@@ -300,7 +305,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
std::numeric_limits<GLsizei>::max() - yoffset < height ||
std::numeric_limits<GLsizei>::max() - zoffset < depth)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
const gl::Caps &caps = context->getCaps();
......@@ -318,7 +324,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
if (static_cast<GLuint>(width) > (caps.max2DTextureSize >> level) ||
static_cast<GLuint>(height) > (caps.max2DTextureSize >> level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Texture2D *texture2d = context->getTexture2D();
......@@ -343,12 +350,14 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
{
if (!isSubImage && width != height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (static_cast<GLuint>(width) > (caps.maxCubeMapTextureSize >> level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::TextureCubeMap *textureCube = context->getTextureCubeMap();
......@@ -370,7 +379,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
static_cast<GLuint>(height) > (caps.max3DTextureSize >> level) ||
static_cast<GLuint>(depth) > (caps.max3DTextureSize >> level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Texture3D *texture3d = context->getTexture3D();
......@@ -392,7 +402,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
static_cast<GLuint>(height) > (caps.max2DTextureSize >> level) ||
static_cast<GLuint>(depth) > (caps.maxArrayTextureLayers >> level))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Texture2DArray *texture2darray = context->getTexture2DArray();
......@@ -409,17 +420,20 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (!texture)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (texture->isImmutable() && !isSubImage)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// Validate texture formats
......@@ -429,17 +443,20 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
{
if (!ValidCompressedImageSize(context, actualInternalFormat, width, height))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (!actualFormatInfo.compressed)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (target == GL_TEXTURE_3D)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
else
......@@ -451,7 +468,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
if (target == GL_TEXTURE_3D && (format == GL_DEPTH_COMPONENT || format == GL_DEPTH_STENCIL))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -460,7 +478,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
{
if (isCompressed != textureCompressed)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (isCompressed)
......@@ -468,7 +487,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
if ((width % 4 != 0 && width != textureLevelWidth) ||
(height % 4 != 0 && height != textureLevelHeight))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -479,21 +499,24 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
if (xoffset < 0 || yoffset < 0 || zoffset < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (std::numeric_limits<GLsizei>::max() - xoffset < width ||
std::numeric_limits<GLsizei>::max() - yoffset < height ||
std::numeric_limits<GLsizei>::max() - zoffset < depth)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (xoffset + width > textureLevelWidth ||
yoffset + height > textureLevelHeight ||
zoffset + depth > textureLevelDepth)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
......@@ -515,7 +538,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
!rx::IsUnsignedMultiplicationSafe(widthSize * heightSize * depthSize, pixelBytes))
{
// Overflow past the end of the buffer
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
size_t copyBytes = widthSize * heightSize * depthSize * pixelBytes;
......@@ -525,7 +549,8 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
((offset + copyBytes) > static_cast<size_t>(pixelUnpackBuffer->getSize())))
{
// Overflow past the end of the buffer
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// ...data is not evenly divisible into the number of bytes needed to store in memory a datum
......@@ -534,13 +559,15 @@ bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint le
if ((offset % dataBytesPerPixel) != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
// ...the buffer object's data store is currently mapped.
if (pixelUnpackBuffer->isMapped())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -831,7 +858,7 @@ static bool IsValidES3CopyTexImageCombination(GLenum textureInternalFormat, GLen
return false;
}
bool ValidateES3CopyTexImageParameters(gl::Context *context, GLenum target, GLint level, GLenum internalformat,
bool ValidateES3CopyTexImageParameters(Context *context, GLenum target, GLint level, GLenum internalformat,
bool isSubImage, GLint xoffset, GLint yoffset, GLint zoffset,
GLint x, GLint y, GLsizei width, GLsizei height, GLint border)
{
......@@ -847,12 +874,14 @@ bool ValidateES3CopyTexImageParameters(gl::Context *context, GLenum target, GLin
if (framebuffer->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_FRAMEBUFFER_OPERATION, false);
context->recordError(Error(GL_INVALID_FRAMEBUFFER_OPERATION));
return false;
}
if (context->getState().getReadFramebuffer()->id() != 0 && framebuffer->getSamples() != 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
gl::FramebufferAttachment *source = framebuffer->getReadColorbuffer();
......@@ -863,7 +892,8 @@ bool ValidateES3CopyTexImageParameters(gl::Context *context, GLenum target, GLin
if (!IsValidES3CopyTexImageCombination(textureInternalFormat, colorbufferInternalFormat,
context->getState().getReadFramebuffer()->id()))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
else
......@@ -871,7 +901,8 @@ bool ValidateES3CopyTexImageParameters(gl::Context *context, GLenum target, GLin
if (!gl::IsValidES3CopyTexImageCombination(internalformat, colorbufferInternalFormat,
context->getState().getReadFramebuffer()->id()))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
......@@ -879,17 +910,19 @@ bool ValidateES3CopyTexImageParameters(gl::Context *context, GLenum target, GLin
return (width > 0 && height > 0);
}
bool ValidateES3TexStorageParameters(gl::Context *context, GLenum target, GLsizei levels, GLenum internalformat,
bool ValidateES3TexStorageParameters(Context *context, GLenum target, GLsizei levels, GLenum internalformat,
GLsizei width, GLsizei height, GLsizei depth)
{
if (width < 1 || height < 1 || depth < 1 || levels < 1)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (levels > gl::log2(std::max(std::max(width, height), depth)) + 1)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::Caps &caps = context->getCaps();
......@@ -904,7 +937,8 @@ bool ValidateES3TexStorageParameters(gl::Context *context, GLenum target, GLsize
if (static_cast<GLuint>(width) > caps.max2DTextureSize ||
static_cast<GLuint>(height) > caps.max2DTextureSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
break;
......@@ -915,12 +949,14 @@ bool ValidateES3TexStorageParameters(gl::Context *context, GLenum target, GLsize
if (width != height)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (static_cast<GLuint>(width) > caps.maxCubeMapTextureSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
break;
......@@ -933,7 +969,8 @@ bool ValidateES3TexStorageParameters(gl::Context *context, GLenum target, GLsize
static_cast<GLuint>(height) > caps.max3DTextureSize ||
static_cast<GLuint>(depth) > caps.max3DTextureSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
break;
......@@ -946,50 +983,58 @@ bool ValidateES3TexStorageParameters(gl::Context *context, GLenum target, GLsize
static_cast<GLuint>(height) > caps.max2DTextureSize ||
static_cast<GLuint>(depth) > caps.maxArrayTextureLayers)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (!texture || texture->id() == 0)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (texture->isImmutable())
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::InternalFormat &formatInfo = gl::GetInternalFormatInfo(internalformat);
if (!formatInfo.textureSupport(context->getClientVersion(), context->getExtensions()))
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (formatInfo.pixelBytes == 0)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
return true;
}
bool ValidateFramebufferTextureLayer(const gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferTextureLayer(Context *context, GLenum target, GLenum attachment,
GLuint texture, GLint level, GLint layer)
{
if (context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
if (layer < 0)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (!ValidateFramebufferTextureBase(context, target, attachment, texture, level))
......@@ -1009,18 +1054,21 @@ bool ValidateFramebufferTextureLayer(const gl::Context *context, GLenum target,
{
if (level > gl::log2(caps.max2DTextureSize))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (static_cast<GLuint>(layer) >= caps.maxArrayTextureLayers)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Texture2DArray *texArray = static_cast<gl::Texture2DArray *>(tex);
if (texArray->isCompressed(level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
break;
......@@ -1029,31 +1077,35 @@ bool ValidateFramebufferTextureLayer(const gl::Context *context, GLenum target,
{
if (level > gl::log2(caps.max3DTextureSize))
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
if (static_cast<GLuint>(layer) >= caps.max3DTextureSize)
{
return gl::error(GL_INVALID_VALUE, false);
context->recordError(Error(GL_INVALID_VALUE));
return false;
}
gl::Texture3D *tex3d = static_cast<gl::Texture3D *>(tex);
if (tex3d->isCompressed(level))
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
break;
default:
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
return true;
}
bool ValidES3ReadFormatType(gl::Context *context, GLenum internalFormat, GLenum format, GLenum type)
bool ValidES3ReadFormatType(Context *context, GLenum internalFormat, GLenum format, GLenum type)
{
const gl::InternalFormat &internalFormatInfo = gl::GetInternalFormatInfo(internalFormat);
......@@ -1130,7 +1182,7 @@ bool ValidES3ReadFormatType(gl::Context *context, GLenum internalFormat, GLenum
return true;
}
bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target, GLsizei numAttachments,
bool ValidateInvalidateFramebufferParameters(Context *context, GLenum target, GLsizei numAttachments,
const GLenum* attachments)
{
bool defaultFramebuffer = false;
......@@ -1145,7 +1197,8 @@ bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target
defaultFramebuffer = context->getState().getReadFramebuffer()->id() == 0;
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
for (int i = 0; i < numAttachments; ++i)
......@@ -1154,12 +1207,14 @@ bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target
{
if (defaultFramebuffer)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
if (attachments[i] >= GL_COLOR_ATTACHMENT0 + context->getCaps().maxColorAttachments)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
}
else
......@@ -1171,7 +1226,8 @@ bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target
case GL_DEPTH_STENCIL_ATTACHMENT:
if (defaultFramebuffer)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
case GL_COLOR:
......@@ -1179,11 +1235,13 @@ bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target
case GL_STENCIL:
if (!defaultFramebuffer)
{
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
break;
default:
return gl::error(GL_INVALID_ENUM, false);
context->recordError(Error(GL_INVALID_ENUM));
return false;
}
}
}
......@@ -1191,27 +1249,30 @@ bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target
return true;
}
bool ValidateClearBuffer(const gl::Context *context)
bool ValidateClearBuffer(Context *context)
{
if (context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
const gl::Framebuffer *fbo = context->getState().getDrawFramebuffer();
if (!fbo || fbo->completeness() != GL_FRAMEBUFFER_COMPLETE)
{
return gl::error(GL_INVALID_FRAMEBUFFER_OPERATION, false);
context->recordError(Error(GL_INVALID_FRAMEBUFFER_OPERATION));
return false;
}
return true;
}
bool ValidateGetUniformuiv(const gl::Context *context, GLuint program, GLint location, GLuint* params)
bool ValidateGetUniformuiv(Context *context, GLuint program, GLint location, GLuint* params)
{
if (context->getClientVersion() < 3)
{
return gl::error(GL_INVALID_OPERATION, false);
context->recordError(Error(GL_INVALID_OPERATION));
return false;
}
return ValidateGetUniformBase(context, program, location);
......
......@@ -16,28 +16,28 @@ namespace gl
class Context;
bool ValidateES3TexImageParameters(gl::Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
bool ValidateES3TexImageParameters(Context *context, GLenum target, GLint level, GLenum internalformat, bool isCompressed, bool isSubImage,
GLint xoffset, GLint yoffset, GLint zoffset, GLsizei width, GLsizei height, GLsizei depth,
GLint border, GLenum format, GLenum type, const GLvoid *pixels);
bool ValidateES3CopyTexImageParameters(gl::Context *context, GLenum target, GLint level, GLenum internalformat,
bool ValidateES3CopyTexImageParameters(Context *context, GLenum target, GLint level, GLenum internalformat,
bool isSubImage, GLint xoffset, GLint yoffset, GLint zoffset, GLint x, GLint y,
GLsizei width, GLsizei height, GLint border);
bool ValidateES3TexStorageParameters(gl::Context *context, GLenum target, GLsizei levels, GLenum internalformat,
bool ValidateES3TexStorageParameters(Context *context, GLenum target, GLsizei levels, GLenum internalformat,
GLsizei width, GLsizei height, GLsizei depth);
bool ValidateFramebufferTextureLayer(const gl::Context *context, GLenum target, GLenum attachment,
bool ValidateFramebufferTextureLayer(Context *context, GLenum target, GLenum attachment,
GLuint texture, GLint level, GLint layer);
bool ValidES3ReadFormatType(gl::Context *context, GLenum internalFormat, GLenum format, GLenum type);
bool ValidES3ReadFormatType(Context *context, GLenum internalFormat, GLenum format, GLenum type);
bool ValidateInvalidateFramebufferParameters(gl::Context *context, GLenum target, GLsizei numAttachments,
bool ValidateInvalidateFramebufferParameters(Context *context, GLenum target, GLsizei numAttachments,
const GLenum* attachments);
bool ValidateClearBuffer(const gl::Context *context);
bool ValidateClearBuffer(Context *context);
bool ValidateGetUniformuiv(const gl::Context *context, GLuint program, GLint location, GLuint* params);
bool ValidateGetUniformuiv(Context *context, GLuint program, GLint location, GLuint* params);
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment