/*-------------------------------------------------------------------------
* 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