/*------------------------------------------------------------------------- * drawElements Quality Program OpenGL ES 2.0 Module * ------------------------------------------------- * * Copyright 2014 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * *//*! * \file * \brief Negative Vertex Array API tests. *//*--------------------------------------------------------------------*/ #include "es2fNegativeVertexArrayApiTests.hpp" #include "es2fApiCase.hpp" #include "gluShaderProgram.hpp" #include "gluContextInfo.hpp" #include "deString.h" #include "glwEnums.hpp" #include "glwDefs.hpp" using namespace glw; // GL types namespace deqp { namespace gles2 { namespace Functional { static const char* vertexShaderSource = "void main (void) { gl_Position = vec4(0.0); }\n\0"; static const char* fragmentShaderSource = "void main (void) { gl_FragColor = vec4(0.0); }\n\0"; using tcu::TestLog; NegativeVertexArrayApiTests::NegativeVertexArrayApiTests (Context& context) : TestCaseGroup(context, "vertex_array", "Negative Vertex Array API Cases") { } NegativeVertexArrayApiTests::~NegativeVertexArrayApiTests (void) { } void NegativeVertexArrayApiTests::init (void) { ES2F_ADD_API_CASE(vertex_attrib, "Invalid glVertexAttrib() usage", { m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if index is greater than or equal to GL_MAX_VERTEX_ATTRIBS."); int maxVertexAttribs = m_context.getContextInfo().getInt(GL_MAX_VERTEX_ATTRIBS); glVertexAttrib1f(maxVertexAttribs, 0.0f); expectError(GL_INVALID_VALUE); glVertexAttrib2f(maxVertexAttribs, 0.0f, 0.0f); expectError(GL_INVALID_VALUE); glVertexAttrib3f(maxVertexAttribs, 0.0f, 0.0f, 0.0f); expectError(GL_INVALID_VALUE); glVertexAttrib4f(maxVertexAttribs, 0.0f, 0.0f, 0.0f, 0.0f); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(vertex_attribv, "Invalid glVertexAttribv() usage", { m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if index is greater than or equal to GL_MAX_VERTEX_ATTRIBS."); int maxVertexAttribs = m_context.getContextInfo().getInt(GL_MAX_VERTEX_ATTRIBS); float v[4] = {0.0f}; glVertexAttrib1fv(maxVertexAttribs, &v[0]); expectError(GL_INVALID_VALUE); glVertexAttrib2fv(maxVertexAttribs, &v[0]); expectError(GL_INVALID_VALUE); glVertexAttrib3fv(maxVertexAttribs, &v[0]); expectError(GL_INVALID_VALUE); glVertexAttrib4fv(maxVertexAttribs, &v[0]); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(vertex_attrib_pointer, "Invalid glVertexAttribPointer() usage", { m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if type is not an accepted value."); glVertexAttribPointer(0, 1, 0, GL_TRUE, 0, 0); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if index is greater than or equal to GL_MAX_VERTEX_ATTRIBS."); int maxVertexAttribs = m_context.getContextInfo().getInt(GL_MAX_VERTEX_ATTRIBS); glVertexAttribPointer(maxVertexAttribs, 1, GL_BYTE, GL_TRUE, 0, 0); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if size is not 1, 2, 3, or 4."); glVertexAttribPointer(0, 0, GL_BYTE, GL_TRUE, 0, 0); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if stride is negative."); glVertexAttribPointer(0, 1, GL_BYTE, GL_TRUE, -1, 0); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(enable_vertex_attrib_array, "Invalid glEnableVertexAttribArray() usage", { m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if index is greater than or equal to GL_MAX_VERTEX_ATTRIBS."); int maxVertexAttribs = m_context.getContextInfo().getInt(GL_MAX_VERTEX_ATTRIBS); glEnableVertexAttribArray(maxVertexAttribs); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(disable_vertex_attrib_array, "Invalid glDisableVertexAttribArray() usage", { m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if index is greater than or equal to GL_MAX_VERTEX_ATTRIBS."); int maxVertexAttribs = m_context.getContextInfo().getInt(GL_MAX_VERTEX_ATTRIBS); glDisableVertexAttribArray(maxVertexAttribs); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(draw_arrays, "Invalid glDrawArrays() usage", { glu::ShaderProgram program(m_context.getRenderContext(), glu::makeVtxFragSources(vertexShaderSource, fragmentShaderSource)); glUseProgram(program.getProgram()); m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if mode is not an accepted value."); glDrawArrays(-1, 0, 1); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if count is negative."); glDrawArrays(GL_POINTS, 0, -1); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_FRAMEBUFFER_OPERATION is generated if the currently bound framebuffer is not framebuffer complete."); GLuint fbo; glGenFramebuffers(1, &fbo); glBindFramebuffer(GL_FRAMEBUFFER, fbo); glCheckFramebufferStatus(GL_FRAMEBUFFER); glDrawArrays(GL_POINTS, 0, 1); expectError(GL_INVALID_FRAMEBUFFER_OPERATION); glBindFramebuffer(GL_FRAMEBUFFER, 0); glDeleteFramebuffers(1, &fbo); m_log << tcu::TestLog::EndSection; glUseProgram(0); }); ES2F_ADD_API_CASE(draw_arrays_invalid_program, "Invalid glDrawArrays() usage", { glUseProgram(0); m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if mode is not an accepted value."); glDrawArrays(-1, 0, 1); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if count is negative."); glDrawArrays(GL_POINTS, 0, -1); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_FRAMEBUFFER_OPERATION is generated if the currently bound framebuffer is not framebuffer complete."); GLuint fbo; glGenFramebuffers(1, &fbo); glBindFramebuffer(GL_FRAMEBUFFER, fbo); glCheckFramebufferStatus(GL_FRAMEBUFFER); glDrawArrays(GL_POINTS, 0, 1); expectError(GL_INVALID_FRAMEBUFFER_OPERATION); glBindFramebuffer(GL_FRAMEBUFFER, 0); glDeleteFramebuffers(1, &fbo); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(draw_arrays_incomplete_primitive, "Invalid glDrawArrays() usage", { glu::ShaderProgram program(m_context.getRenderContext(), glu::makeVtxFragSources(vertexShaderSource, fragmentShaderSource)); glUseProgram(program.getProgram()); m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if mode is not an accepted value."); glDrawArrays(-1, 0, 1); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if count is negative."); glDrawArrays(GL_TRIANGLES, 0, -1); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_FRAMEBUFFER_OPERATION is generated if the currently bound framebuffer is not framebuffer complete."); GLuint fbo; glGenFramebuffers(1, &fbo); glBindFramebuffer(GL_FRAMEBUFFER, fbo); glCheckFramebufferStatus(GL_FRAMEBUFFER); glDrawArrays(GL_TRIANGLES, 0, 1); expectError(GL_INVALID_FRAMEBUFFER_OPERATION); glBindFramebuffer(GL_FRAMEBUFFER, 0); glDeleteFramebuffers(1, &fbo); m_log << tcu::TestLog::EndSection; glUseProgram(0); }); ES2F_ADD_API_CASE(draw_elements, "Invalid glDrawElements() usage", { glu::ShaderProgram program(m_context.getRenderContext(), glu::makeVtxFragSources(vertexShaderSource, fragmentShaderSource)); glUseProgram(program.getProgram()); GLfloat vertices[1] = { 0.0f }; m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if mode is not an accepted value."); glDrawElements(-1, 1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if type is not GL_UNSIGNED_BYTE or GL_UNSIGNED_SHORT."); glDrawElements(GL_POINTS, 1, -1, vertices); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if count is negative."); glDrawElements(GL_POINTS, -1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_FRAMEBUFFER_OPERATION is generated if the currently bound framebuffer is not framebuffer complete."); GLuint fbo; glGenFramebuffers(1, &fbo); glBindFramebuffer(GL_FRAMEBUFFER, fbo); glCheckFramebufferStatus(GL_FRAMEBUFFER); glDrawElements(GL_POINTS, 1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_FRAMEBUFFER_OPERATION); glBindFramebuffer(GL_FRAMEBUFFER, 0); glDeleteFramebuffers(1, &fbo); m_log << tcu::TestLog::EndSection; glUseProgram(0); }); ES2F_ADD_API_CASE(draw_elements_invalid_program, "Invalid glDrawElements() usage", { glUseProgram(0); GLfloat vertices[1] = { 0.0f }; m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if mode is not an accepted value."); glDrawElements(-1, 1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if type is not GL_UNSIGNED_BYTE or GL_UNSIGNED_SHORT."); glDrawElements(GL_POINTS, 1, -1, vertices); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if count is negative."); glDrawElements(GL_POINTS, -1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_FRAMEBUFFER_OPERATION is generated if the currently bound framebuffer is not framebuffer complete."); GLuint fbo; glGenFramebuffers(1, &fbo); glBindFramebuffer(GL_FRAMEBUFFER, fbo); glCheckFramebufferStatus(GL_FRAMEBUFFER); glDrawElements(GL_POINTS, 1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_FRAMEBUFFER_OPERATION); glBindFramebuffer(GL_FRAMEBUFFER, 0); glDeleteFramebuffers(1, &fbo); m_log << tcu::TestLog::EndSection; }); ES2F_ADD_API_CASE(draw_elements_incomplete_primitive, "Invalid glDrawElements() usage", { glu::ShaderProgram program(m_context.getRenderContext(), glu::makeVtxFragSources(vertexShaderSource, fragmentShaderSource)); glUseProgram(program.getProgram()); GLfloat vertices[1] = { 0.0f }; m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if mode is not an accepted value."); glDrawElements(-1, 1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_ENUM is generated if type is not GL_UNSIGNED_BYTE or GL_UNSIGNED_SHORT."); glDrawElements(GL_TRIANGLES, 1, -1, vertices); expectError(GL_INVALID_ENUM); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_VALUE is generated if count is negative."); glDrawElements(GL_TRIANGLES, -1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_VALUE); m_log << tcu::TestLog::EndSection; m_log << tcu::TestLog::Section("", "GL_INVALID_FRAMEBUFFER_OPERATION is generated if the currently bound framebuffer is not framebuffer complete."); GLuint fbo; glGenFramebuffers(1, &fbo); glBindFramebuffer(GL_FRAMEBUFFER, fbo); glCheckFramebufferStatus(GL_FRAMEBUFFER); glDrawElements(GL_TRIANGLES, 1, GL_UNSIGNED_BYTE, vertices); expectError(GL_INVALID_FRAMEBUFFER_OPERATION); glBindFramebuffer(GL_FRAMEBUFFER, 0); glDeleteFramebuffers(1, &fbo); m_log << tcu::TestLog::EndSection; glUseProgram(0); }); } } // Functional } // gles2 } // deqp