/** * Copyright 2017 Intel Corporation * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), * to deal in the Software without restriction, including without limitation * the rights to use, copy, modify, merge, publish, distribute, sublicense, * and/or sell copies of the Software, and to permit persons to whom the * Software is furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice (including the next * paragraph) shall be included in all copies or substantial portions of the * Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER * DEALINGS IN THE SOFTWARE. */ /** @file named-framebuffer-read-buffer-errors.c * * Test that NamedFramebufferReadBuffer() returns correct error * message for different values. * * All spec quotes come from OpenGL 4.5 spec, section 18.2.1 * "Selecting Buffers for Reading", page 502 (524 on PDF). * * Note that for 4.5, they are the same errors that for ReadBuffer, so * we get that method tested it, although indirectly. Also some spec * quotes could mention ReadBuffer too. * * From OpenGL 4.5, section 18.2.1 "Selecting Buffers for Reading", * page 502: * * "When reading pixels from a color buffer of a framebuffer object, * the buffer selected for reading is termed the read buffer, and is * controlled with the commands: * * void ReadBuffer( enum src ); * void NamedFramebufferReadBuffer( uint framebuffer, enum src ); * * For ReadBuffer, the target framebuffer object is that bound to * READ_- FRAMEBUFFER . For NamedFramebufferReadBuffer, framebuffer * is zero or the name of the target framebuffer object. If * framebuffer is zero, then the default read framebuffer is * affected." */ #include "piglit-util-gl.h" PIGLIT_GL_TEST_CONFIG_BEGIN config.supports_gl_core_version = 45; config.window_visual = PIGLIT_GL_VISUAL_RGBA | PIGLIT_GL_VISUAL_DOUBLE; config.khr_no_error_support = PIGLIT_HAS_ERRORS; PIGLIT_GL_TEST_CONFIG_END static const GLenum table_17_4[] = { GL_NONE, GL_FRONT_LEFT, GL_FRONT_RIGHT, GL_BACK_LEFT, GL_BACK_RIGHT, GL_FRONT, GL_BACK, GL_LEFT, GL_RIGHT, GL_FRONT_AND_BACK }; void piglit_init(int argc, char **argv) { bool pass = true; GLuint framebuffer; GLuint default_framebuffer = 0; bool subtest_pass; int i; glCreateFramebuffers(1, &framebuffer); piglit_check_gl_error(GL_NO_ERROR); /* * "An INVALID_OPERATION error is generated by * NamedFramebuffer- ReadBuffer if framebuffer is not zero or * the name of an existing framebuffer object. */ glNamedFramebufferReadBuffer(5, GL_BACK); PIGLIT_SUBTEST_ERROR(GL_INVALID_OPERATION, pass, "INVALID_OPERATION if " "framebuffer is not zero or the name of an existing " "framebuffer"); /* * "An INVALID_ENUM error is generated if src is not one of the values in * tables 17.4 or 17.5." */ subtest_pass = true; glNamedFramebufferReadBuffer(default_framebuffer, GL_RED); subtest_pass = subtest_pass && piglit_check_gl_error(GL_INVALID_ENUM); glNamedFramebufferReadBuffer(framebuffer, GL_RED); subtest_pass = subtest_pass && piglit_check_gl_error(GL_INVALID_ENUM); PIGLIT_SUBTEST_CONDITION(subtest_pass, pass, "INVALID_ENUM error is " "generated if any value in bufs is not one of " "the values in tables 17.4 or 17.5."); /* * "An INVALID_OPERATION error is generated if the default * framebuffer is affected and src is a value (other than * NONE) that does not indicate any of the color buffers * allocated to the default framebuffer." * * So for the default framebuffer the value returned should be * NO_ERROR or INVALID_OPERATION. */ subtest_pass = true; for (i = 0; i < ARRAY_SIZE(table_17_4); i++) { GLenum err = 0; glNamedFramebufferReadBuffer(default_framebuffer, table_17_4[i]); err = glGetError(); if (err != GL_NO_ERROR && err != GL_INVALID_OPERATION) { printf("Expected GL_NO_ERROR or GL_INVALID_OPERATION " "with %s but received: %s\n", piglit_get_gl_enum_name(table_17_4[i]), piglit_get_gl_error_name(err)); subtest_pass = false; } } PIGLIT_SUBTEST_CONDITION(subtest_pass, pass, "An INVALID_OPERATION error" " is generated if the default framebuffer is " "affected and src is a value (other than NONE) " "that does not indicate any of the color buffers" " allocated to the default framebuffer."); /* * "An INVALID_OPERATION error is generated if a framebuffer * object is affected, and src is one of the constants from * table 17.4 (other than NONE , or COLOR_ATTACHMENTm where m * is greater than or equal to the value of * MAX_COLOR_ATTACHMENTS ). */ int max_attachments; glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS, &max_attachments); subtest_pass = true; /* Starting at 1, as GL_NONE is valid */ for (i = 1; i < ARRAY_SIZE(table_17_4); i++) { GLenum err = 0; glNamedFramebufferReadBuffer(framebuffer, table_17_4[i]); err = glGetError(); if (err != GL_INVALID_OPERATION) { printf("Expected GL_INVALID_OPERATION with" " %s but received: %s\n", piglit_get_gl_enum_name(table_17_4[i]), piglit_get_gl_error_name(err)); subtest_pass = false; } } glNamedFramebufferReadBuffer(framebuffer, GL_COLOR_ATTACHMENT0 + max_attachments); subtest_pass = subtest_pass && piglit_check_gl_error(GL_INVALID_OPERATION); PIGLIT_SUBTEST_CONDITION(subtest_pass, pass, "An INVALID_OPERATION error" " is generated if a framebuffer object is " "affected, and src is one of the constants from " "table 17.4 (other than NONE, or COLOR_ATTACHMENTm" " where m is greater than or equal to the value" " of MAX_COLOR_ATTACHMENTS)"); /* clean up */ glDeleteFramebuffers(1, &framebuffer); piglit_report_result(pass ? PIGLIT_PASS : PIGLIT_FAIL); } enum piglit_result piglit_display(void) { /* UNREACHED */ return PIGLIT_FAIL; }