Test includes: - texture uploads - mipmap generation - framebuffer creation - rendering to - reading from - interaction with GL_EXT_copy_image
v2: code cleanup Signed-off-by: Tapani Pälli <tapani.pa...@intel.com> --- tests/all.py | 5 + tests/spec/CMakeLists.txt | 1 + tests/spec/ext_texture_norm16/CMakeLists.gles2.txt | 7 + tests/spec/ext_texture_norm16/CMakeLists.txt | 1 + tests/spec/ext_texture_norm16/render.c | 374 +++++++++++++++++++++ 5 files changed, 388 insertions(+) create mode 100644 tests/spec/ext_texture_norm16/CMakeLists.gles2.txt create mode 100644 tests/spec/ext_texture_norm16/CMakeLists.txt create mode 100644 tests/spec/ext_texture_norm16/render.c diff --git a/tests/all.py b/tests/all.py index 26638cd82..101a6c149 100644 --- a/tests/all.py +++ b/tests/all.py @@ -3187,6 +3187,11 @@ with profile.test_list.group_manager( with profile.test_list.group_manager( PiglitGLTest, + grouptools.join('spec', 'ext_texture_norm16')) as g: + g(['ext_texture_norm16-render'], 'render') + +with profile.test_list.group_manager( + PiglitGLTest, grouptools.join('spec', 'ext_frag_depth')) as g: g(['fragdepth_gles2']) diff --git a/tests/spec/CMakeLists.txt b/tests/spec/CMakeLists.txt index dc14beb4e..405d35a53 100644 --- a/tests/spec/CMakeLists.txt +++ b/tests/spec/CMakeLists.txt @@ -178,3 +178,4 @@ add_subdirectory (arb_fragment_shader_interlock) add_subdirectory (ext_occlusion_query_boolean) add_subdirectory (ext_disjoint_timer_query) add_subdirectory (intel_blackhole_render) +add_subdirectory (ext_texture_norm16) diff --git a/tests/spec/ext_texture_norm16/CMakeLists.gles2.txt b/tests/spec/ext_texture_norm16/CMakeLists.gles2.txt new file mode 100644 index 000000000..e9cebd101 --- /dev/null +++ b/tests/spec/ext_texture_norm16/CMakeLists.gles2.txt @@ -0,0 +1,7 @@ +link_libraries ( + piglitutil_${piglit_target_api} +) + +piglit_add_executable (ext_texture_norm16-render render.c) + +# vim: ft=cmake: diff --git a/tests/spec/ext_texture_norm16/CMakeLists.txt b/tests/spec/ext_texture_norm16/CMakeLists.txt new file mode 100644 index 000000000..144a306f4 --- /dev/null +++ b/tests/spec/ext_texture_norm16/CMakeLists.txt @@ -0,0 +1 @@ +piglit_include_target_api() diff --git a/tests/spec/ext_texture_norm16/render.c b/tests/spec/ext_texture_norm16/render.c new file mode 100644 index 000000000..f99b1fd9c --- /dev/null +++ b/tests/spec/ext_texture_norm16/render.c @@ -0,0 +1,374 @@ +/* + * Copyright © 2018 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 + * Basic tests for formats added by GL_EXT_texture_norm16 extension + * + * https://www.khronos.org/registry/OpenGL/extensions/EXT/EXT_texture_norm16.txt + * + * Test includes: + * - texture uploads + * - mipmap generation + * - framebuffer creation + * - rendering to + * - reading from + * - interaction with GL_EXT_copy_image + */ + +#include "piglit-util-gl.h" + +PIGLIT_GL_TEST_CONFIG_BEGIN + config.supports_gl_es_version = 31; + config.window_visual = PIGLIT_GL_VISUAL_RGBA; +PIGLIT_GL_TEST_CONFIG_END + +static const char vs_source[] = + "#version 310 es\n" + "layout(location = 0) in highp vec4 vertex;\n" + "layout(location = 1) in highp vec4 uv;\n" + "out highp vec2 tex_coord;\n" + "\n" + "void main()\n" + "{\n" + " gl_Position = vertex;\n" + " tex_coord = uv.st;\n" + "}\n"; + +static const char fs_source[] = + "#version 310 es\n" + "layout(location = 0) uniform sampler2D texture;\n" + "in highp vec2 tex_coord;\n" + "out highp vec4 color;\n" + "void main()\n" + "{\n" + " color = texture2D(texture, tex_coord);\n" + "}\n"; + +/* trianglestrip, interleaved vertices + texcoords */ +static const GLfloat vertex_data[] = { + -1.0f, 1.0f, + 0.0f, 1.0f, + 1.0f, 1.0f, + 1.0f, 1.0f, + -1.0f, -1.0f, + 0.0f, 0.0f, + 1.0f, -1.0f, + 1.0f, 0.0f +}; + +static const struct fmt_test { + GLenum iformat; + GLenum base_format; + unsigned bpp; + GLenum type; + bool req_render; + bool can_read; +} tests[] = { + { GL_R16_EXT, GL_RED, 2, GL_UNSIGNED_SHORT, true, true, }, + { GL_RG16_EXT, GL_RG, 4, GL_UNSIGNED_SHORT, true, true, }, + { GL_RGB16_EXT, GL_RGB, 6, GL_UNSIGNED_SHORT, false, true, }, + { GL_RGBA16_EXT, GL_RGBA, 8, GL_UNSIGNED_SHORT, true, true, }, + { GL_R16_SNORM_EXT, GL_RED, 2, GL_SHORT, false, false, }, + { GL_RG16_SNORM_EXT, GL_RG, 4, GL_SHORT, false, false, }, + { GL_RGB16_SNORM_EXT, GL_RGB, 6, GL_SHORT, false, false, }, + { GL_RGBA16_SNORM_EXT, GL_RGBA, 8, GL_SHORT, false, false, }, +}; + +static void +upload(const struct fmt_test *test, void *data) +{ + /* glGenerateMipmap only for color renderable formats. */ + if (test->req_render) { + glTexStorage2D(GL_TEXTURE_2D, 4, test->iformat, piglit_width, + piglit_height); + glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, piglit_width, + piglit_height, test->base_format, test->type, + data); + glGenerateMipmap(GL_TEXTURE_2D); + return; + } + glTexImage2D(GL_TEXTURE_2D, 0, test->iformat, piglit_width, + piglit_height, 0, test->base_format, test->type, data); +} + +static unsigned +get_max_value(GLenum type) +{ + return type == GL_SHORT ? SHRT_MAX : USHRT_MAX; +} + +static void +value_for_format(const struct fmt_test *test, unsigned short *value) +{ + unsigned short val = get_max_value(test->type); + + /* red */ + value[0] = val; + /* yellow */ + if (test->bpp > 2) + value[1] = val; + /* pink */ + if (test->bpp > 4) { + value[2] = val; + value[1] = 0; + } + /* blue */ + if (test->bpp > 6) { + value[3] = val; + value[0] = 0; + } +} + +static void +generate_data(const struct fmt_test *test) +{ + unsigned pixels = piglit_width * piglit_height; + char *data = malloc (pixels * test->bpp); + unsigned short *p = (unsigned short *) data; + + for (unsigned i = 0; i < pixels; i++, p += test->bpp / 2) + value_for_format(test, p); + + upload(test, data); + free(data); +} + +static GLuint +create_texture(const struct fmt_test *test) +{ + GLuint tex; + glGenTextures(1, &tex); + glBindTexture(GL_TEXTURE_2D, tex); + + generate_data(test); + + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); + + return tex; +} + +static GLuint +create_fbo(const struct fmt_test *test, GLuint *tex) +{ + GLuint fbo; + GLuint fbo_tex = create_texture(test); + + *tex = fbo_tex; + + glGenFramebuffers(1, &fbo); + glBindFramebuffer(GL_FRAMEBUFFER, fbo); + glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, + GL_TEXTURE_2D, fbo_tex, 0); + return fbo; +} + +static void +render_texture(GLuint texture, GLuint target) +{ + glBindTexture(GL_TEXTURE_2D, texture); + glBindFramebuffer(GL_FRAMEBUFFER, target); + + glViewport(0, 0, piglit_width, piglit_height); + + glClear(GL_COLOR_BUFFER_BIT); + glDrawArrays(GL_TRIANGLE_STRIP, 0, 4); +} + +static bool +verify_contents(const struct fmt_test *test) +{ + bool result = true; + unsigned amount = piglit_width * piglit_height; + unsigned short *pix = malloc (amount * 8); + glReadPixels(0, 0, piglit_width, piglit_height, GL_RGBA, + GL_UNSIGNED_SHORT, pix); + + /* Setup expected value, alpha is always max in the test. */ + unsigned short value[4] = { 0 }; + value_for_format(test, value); + value[3] = get_max_value(test->type); + + unsigned short *p = pix; + for (unsigned i = 0; i < amount; i++, p += 4) { + if (memcmp(p, value, sizeof(value)) == 0) + continue; + + piglit_report_subtest_result(PIGLIT_FAIL, + "format 0x%x read fail", + test->iformat); + result = false; + break; + } + + free(pix); + return result; +} + +static bool +verify_contents_float(const struct fmt_test *test) +{ + /* Setup expected value, alpha is always max in the test. */ + unsigned short value[4] = { 0 }; + unsigned short max = get_max_value(test->type); + value_for_format(test, value); + value[3] = max; + + const float expected[4] = { + value[0] / max, + value[1] / max, + value[2] / max, + value[3] / max, + }; + + bool res = piglit_probe_rect_rgba(0, 0, piglit_width, piglit_height, + expected); + + if (!res) + piglit_report_subtest_result(PIGLIT_FAIL, + "format 0x%x read fail", + test->iformat); + return res; +} + +static bool +test_copy_image(const struct fmt_test *test, GLuint src, GLuint *texture) +{ + bool result = true; + GLuint tex = create_texture(test); + *texture = tex; + glCopyImageSubData(src, GL_TEXTURE_2D, 0, 0, 0, 0, tex, GL_TEXTURE_2D, + 0, 0, 0, 0, piglit_width, piglit_height, 0); + + if (!piglit_check_gl_error(GL_NO_ERROR)) { + piglit_report_subtest_result(PIGLIT_FAIL, + "format 0x%x copyimage fail", + test->iformat); + result = false; + } + return result; +} + +enum piglit_result +piglit_display(void) +{ + GLint prog = piglit_build_simple_program(vs_source, fs_source); + glUseProgram(prog); + + glEnableVertexAttribArray(0); + glEnableVertexAttribArray(1); + + glActiveTexture(GL_TEXTURE0); + glUniform1i(0 /* explicit loc */, 0); + + glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(float), + vertex_data); + glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 4 * sizeof(float), + (void*) (vertex_data + (2 * sizeof(float)))); + + bool pass = true; + + /* Loop over each format. */ + const struct fmt_test *test = tests; + for (unsigned i = 0; i < ARRAY_SIZE(tests); i++, test++) { + + /* Create a texture, upload data */ + const GLuint texture = create_texture(test); + + glBindTexture(GL_TEXTURE_2D, texture); + + /* Can only texture from. */ + if (!test->req_render) { + /* Render texture to window and verify contents. */ + render_texture(texture, 0); + pass &= verify_contents_float(test); + piglit_present_results(); + if (pass) + piglit_report_subtest_result(PIGLIT_PASS, + "format 0x%x", + test->iformat); + glDeleteTextures(1, &texture); + continue; + } + + GLuint fbo_tex; + const GLuint fbo = create_fbo(test, &fbo_tex); + + if (glCheckFramebufferStatus(GL_FRAMEBUFFER) != + GL_FRAMEBUFFER_COMPLETE) { + piglit_report_subtest_result(PIGLIT_FAIL, + "format 0x%x fbo fail", + test->iformat); + pass &= false; + } + + render_texture(texture, fbo); + + /* If GL_EXT_copy_image is supported then create another + * texture, copy contents and render result to fbo. + */ + GLuint texture_copy = 0; + if (piglit_is_extension_supported("GL_EXT_copy_image")) { + pass &= test_copy_image(test, texture, &texture_copy); + render_texture(texture_copy, fbo); + } else { + piglit_report_subtest_result(PIGLIT_SKIP, + "copy test skipped"); + } + + /* If format can be read, verify contents. */ + if (test->can_read) + pass &= verify_contents(test); + + /* Render fbo contents to window. */ + render_texture(fbo_tex, 0); + + piglit_present_results(); + + glDeleteFramebuffers(1, &fbo); + glDeleteTextures(1, &texture); + glDeleteTextures(1, &texture_copy); + + if (pass) + piglit_report_subtest_result(PIGLIT_PASS, + "format 0x%x", + test->iformat); + + } + + glDeleteProgram(prog); + + if (!piglit_check_gl_error(GL_NO_ERROR)) + piglit_report_result(PIGLIT_FAIL); + + return pass ? PIGLIT_PASS : PIGLIT_FAIL; +} + +void +piglit_init(int argc, char **argv) +{ + piglit_require_extension("GL_EXT_texture_norm16"); +} -- 2.13.6 _______________________________________________ Piglit mailing list Piglit@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/piglit