Refactor client check from ValidateDrawAttribs.
This moves out some shared logic into a more accessible place. We don't
need to validate buffer overflows when using robust resource access but
we do need to validate we are using client side data correctly.
Bug: angleproject:1391
Change-Id: I7a3dca8409c5a1faf1ff7bc732d5ed1bd62eb3b1
Reviewed-on: https://chromium-review.googlesource.com/1148817
Commit-Queue: Jamie Madill <jmadill@chromium.org>
Reviewed-by: Geoff Lang <geofflang@chromium.org>
diff --git a/src/libANGLE/validationES.cpp b/src/libANGLE/validationES.cpp
index a3e2c62..87fd971 100644
--- a/src/libANGLE/validationES.cpp
+++ b/src/libANGLE/validationES.cpp
@@ -79,32 +79,42 @@
return !checkedA.IsValid();
}
+bool ValidateDrawClientAttribs(Context *context)
+{
+ if (!context->getStateCache().hasAnyEnabledClientAttrib())
+ return true;
+
+ const gl::State &state = context->getGLState();
+
+ if (context->getExtensions().webglCompatibility || !state.areClientArraysEnabled())
+ {
+ // [WebGL 1.0] Section 6.5 Enabled Vertex Attributes and Range Checking
+ // If a vertex attribute is enabled as an array via enableVertexAttribArray but no
+ // buffer is bound to that attribute via bindBuffer and vertexAttribPointer, then calls
+ // to drawArrays or drawElements will generate an INVALID_OPERATION error.
+ ANGLE_VALIDATION_ERR(context, InvalidOperation(), VertexArrayNoBuffer);
+ return false;
+ }
+
+ if (state.getVertexArray()->hasEnabledNullPointerClientArray())
+ {
+ // This is an application error that would normally result in a crash, but we catch it
+ // and return an error
+ ANGLE_VALIDATION_ERR(context, InvalidOperation(), VertexArrayNoBufferPointer);
+ return false;
+ }
+
+ return true;
+}
+
bool ValidateDrawAttribs(Context *context, GLint primcount, GLint maxVertex, GLint vertexCount)
{
const gl::State &state = context->getGLState();
const gl::Program *program = state.getProgram();
- const VertexArray *vao = state.getVertexArray();
- bool webglCompatibility = context->getExtensions().webglCompatibility;
-
- if (context->getStateCache().hasAnyEnabledClientAttrib())
+ if (!ValidateDrawClientAttribs(context))
{
- if (webglCompatibility || !state.areClientArraysEnabled())
- {
- // [WebGL 1.0] Section 6.5 Enabled Vertex Attributes and Range Checking
- // If a vertex attribute is enabled as an array via enableVertexAttribArray but no
- // buffer is bound to that attribute via bindBuffer and vertexAttribPointer, then calls
- // to drawArrays or drawElements will generate an INVALID_OPERATION error.
- ANGLE_VALIDATION_ERR(context, InvalidOperation(), VertexArrayNoBuffer);
- return false;
- }
- else if (vao->hasEnabledNullPointerClientArray())
- {
- // This is an application error that would normally result in a crash, but we catch it
- // and return an error
- ANGLE_VALIDATION_ERR(context, InvalidOperation(), VertexArrayNoBufferPointer);
- return false;
- }
+ return false;
}
// If we're drawing zero vertices, we have enough data.
@@ -113,6 +123,7 @@
return true;
}
+ const VertexArray *vao = state.getVertexArray();
const auto &vertexAttribs = vao->getVertexAttributes();
const auto &vertexBindings = vao->getVertexBindings();
@@ -170,12 +181,6 @@
}
}
- if (webglCompatibility && vao->hasTransformFeedbackBindingConflict(activeAttribs))
- {
- ANGLE_VALIDATION_ERR(context, InvalidOperation(), VertexBufferBoundForTransformFeedback);
- return false;
- }
-
return true;
}
@@ -2873,6 +2878,17 @@
{
return false;
}
+
+ if (count > 0)
+ {
+ const VertexArray *vao = context->getGLState().getVertexArray();
+ if (vao->hasTransformFeedbackBindingConflict(context))
+ {
+ ANGLE_VALIDATION_ERR(context, InvalidOperation(),
+ VertexBufferBoundForTransformFeedback);
+ return false;
+ }
+ }
}
}
@@ -3135,20 +3151,10 @@
}
}
- if (context->getExtensions().robustBufferAccessBehavior)
+ if (context->getExtensions().robustBufferAccessBehavior || count == 0)
{
- // Here we use maxVertex = 0 and vertexCount = 1 to avoid retrieving IndexRange when robust
- // access is enabled.
- if (!ValidateDrawAttribs(context, primcount, 0, 1))
- {
- return false;
- }
- }
- else if (count == 0)
- {
- // ValidateDrawAttribs also does some extra validation that is independent of the vertex
- // count.
- if (!ValidateDrawAttribs(context, 0, 0, 0))
+ // Special checks are needed for client attribs. But we don't need to validate overflows.
+ if (!ValidateDrawClientAttribs(context))
{
return false;
}