/* * Copyright (C) 2016 Samuel Pitoiset * * 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 * * Test cases in which the ARB_compute_variable_group_size API is expected to * generate an error. */ #include "piglit-util-gl.h" #include "piglit-shader.h" static struct piglit_gl_test_config *piglit_config; PIGLIT_GL_TEST_CONFIG_BEGIN piglit_config = &config; config.supports_gl_compat_version = 33; config.supports_gl_core_version = 33; config.khr_no_error_support = PIGLIT_HAS_ERRORS; PIGLIT_GL_TEST_CONFIG_END static const char *variable_work_group_size_shader = "#version 330\n" "#extension GL_ARB_compute_shader: enable\n" "#extension GL_ARB_compute_variable_group_size: enable\n" "\n" "layout(local_size_variable) in;\n" "\n" "void main()\n" "{\n" "}\n"; static const char *fixed_work_group_size_shader = "#version 330\n" "#extension GL_ARB_compute_shader: enable\n" "\n" "layout(local_size_x = 1) in;\n" "\n" "void main()\n" "{\n" "}\n"; static enum piglit_result use_variable_work_group_size_normal(void *data) { /* The ARB_compute_variable_group_size spec says: * * An INVALID_OPERATION error is generated by DispatchCompute or * DispatchComputeIndirect if the active program for the compute * shader stage has a variable work group size. */ GLint prog = piglit_build_simple_program_multiple_shaders( GL_COMPUTE_SHADER, variable_work_group_size_shader, 0); glUseProgram(prog); glDispatchCompute(1, 1, 1); if (!piglit_check_gl_error(GL_INVALID_OPERATION)) return PIGLIT_FAIL; return PIGLIT_PASS; } static enum piglit_result use_variable_work_group_size_indirect(void *data) { /* The ARB_compute_variable_group_size spec says: * * An INVALID_OPERATION error is generated by DispatchCompute or * DispatchComputeIndirect if the active program for the compute * shader stage has a variable work group size. */ GLuint indirect_buf[3] = { 1, 1, 1 }; GLuint indirect_bo = 0; GLint prog; glGenBuffers(1, &indirect_bo); if (!piglit_check_gl_error(GL_NO_ERROR)) return PIGLIT_FAIL; glBindBuffer(GL_DISPATCH_INDIRECT_BUFFER, indirect_bo); glBufferData(GL_DISPATCH_INDIRECT_BUFFER, sizeof(indirect_buf), indirect_buf, GL_STREAM_READ); prog = piglit_build_simple_program_multiple_shaders( GL_COMPUTE_SHADER, variable_work_group_size_shader, 0); glUseProgram(prog); glBindBuffer(GL_DISPATCH_INDIRECT_BUFFER, indirect_bo); glDispatchComputeIndirect(0); if (!piglit_check_gl_error(GL_INVALID_OPERATION)) return PIGLIT_FAIL; glDeleteBuffers(1, &indirect_bo); return PIGLIT_PASS; } static enum piglit_result use_fixed_work_group_size(void *data) { /* The ARB_compute_variable_group_size spec says: * * An INVALID_OPERATION error is generated by * DispatchComputeGroupSizeARB if the active program for the * compute shader stage has a fixed work group size. */ GLint prog = piglit_build_simple_program_multiple_shaders( GL_COMPUTE_SHADER, fixed_work_group_size_shader, 0); glUseProgram(prog); glDispatchComputeGroupSizeARB(1, 1, 1, 1, 1, 1); if (!piglit_check_gl_error(GL_INVALID_OPERATION)) return PIGLIT_FAIL; return PIGLIT_PASS; } static enum piglit_result use_invalid_work_group_count_values(void *data) { GLint prog, v[3]; /* The ARB_compute_variable_group_size spec says: * * An INVALID_VALUE error is generated if any of num_groups_x, * num_groups_y and num_groups_z are greater than or equal to the * maximum work group count for the corresponding dimension. */ prog = piglit_build_simple_program_multiple_shaders( GL_COMPUTE_SHADER, variable_work_group_size_shader, 0); glUseProgram(prog); /* Use values greater than the maximum work group count. */ glGetIntegeri_v(GL_MAX_COMPUTE_WORK_GROUP_COUNT, 0, &v[0]); glGetIntegeri_v(GL_MAX_COMPUTE_WORK_GROUP_COUNT, 1, &v[1]); glGetIntegeri_v(GL_MAX_COMPUTE_WORK_GROUP_COUNT, 2, &v[2]); glDispatchComputeGroupSizeARB(v[0] + 1, v[1] + 1, v[2] + 1, 1, 1, 1); if (!piglit_check_gl_error(GL_INVALID_VALUE)) return PIGLIT_FAIL; return PIGLIT_PASS; } static enum piglit_result use_invalid_variable_work_group_size_values(void *data) { /* The ARB_compute_variable_group_size spec says: * * An INVALID_VALUE error is generated by * DispatchComputeGroupSizeARB if any of , * , or is less than or equal to zero * or greater than the maximum local work group size for compute * shaders with variable group size * (MAX_COMPUTE_VARIABLE_GROUP_SIZE_ARB) in the corresponding * dimension. */ GLint prog, v[3]; prog = piglit_build_simple_program_multiple_shaders( GL_COMPUTE_SHADER, variable_work_group_size_shader, 0); glUseProgram(prog); /* Use values equal to zero (because "less than" is a spec bug). */ glDispatchComputeGroupSizeARB(1, 1, 1, 0, 0, 0); if (!piglit_check_gl_error(GL_INVALID_VALUE)) return PIGLIT_FAIL; /* Use values greater than the maximum local work group size. */ glGetIntegeri_v(GL_MAX_COMPUTE_VARIABLE_GROUP_SIZE_ARB, 0, &v[0]); glGetIntegeri_v(GL_MAX_COMPUTE_VARIABLE_GROUP_SIZE_ARB, 1, &v[1]); glGetIntegeri_v(GL_MAX_COMPUTE_VARIABLE_GROUP_SIZE_ARB, 2, &v[2]); glDispatchComputeGroupSizeARB(1, 1, 1, v[0] + 1, v[1] + 1, v[0] + 1); if (!piglit_check_gl_error(GL_INVALID_VALUE)) return PIGLIT_FAIL; return PIGLIT_PASS; } static enum piglit_result use_invalid_variable_group_invocations_values(void *data) { /* The ARB_compute_variable_group_size spec says: * * An INVALID_VALUE error is generated by * DispatchComputeGroupSizeARB if the product of , * , and exceeds the * implementation-dependent maximum local work group invocation * count for compute shaders with variable group size * (MAX_COMPUTE_VARIABLE_GROUP_INVOCATIONS_ARB). */ GLint prog, v; prog = piglit_build_simple_program_multiple_shaders( GL_COMPUTE_SHADER, variable_work_group_size_shader, 0); glUseProgram(prog); glGetIntegerv(GL_MAX_COMPUTE_VARIABLE_GROUP_INVOCATIONS_ARB, &v); glDispatchComputeGroupSizeARB(1, 1, 1, v, v, v); if (!piglit_check_gl_error(GL_INVALID_VALUE)) return PIGLIT_FAIL; return PIGLIT_PASS; } static const struct piglit_subtest subtests[] = { { "Use a variable work group size with DispatchCompute", "use_variable_work_group_size_normal", use_variable_work_group_size_normal, NULL }, { "Use a variable work group size with DispatchComputeIndirect", "use_variable_work_group_size_indirect", use_variable_work_group_size_indirect, NULL }, { "Use a fixed work group size with DispatchComputeGroupSizeARB", "use_fixed_work_group_size", use_fixed_work_group_size, NULL }, { "Use invalid work group count values", "use_invalid_work_group_count_values", use_invalid_work_group_count_values, NULL }, { "Use invalid variable work group size values", "use_invalid_variable_work_group_size_values", use_invalid_variable_work_group_size_values, NULL }, { "Use invalid variable group invocations values", "use_invalid_variable_group_invocations_values", use_invalid_variable_group_invocations_values, NULL }, { NULL, NULL, NULL, NULL } }; enum piglit_result piglit_display(void) { return PIGLIT_FAIL; } void piglit_init(int argc, char **argv) { enum piglit_result result; piglit_require_extension("GL_ARB_compute_variable_group_size"); result = piglit_run_selected_subtests(subtests, piglit_config->selected_subtests, piglit_config->num_selected_subtests, PIGLIT_SKIP); piglit_report_result(result); }