1af69d88dSmrg/* 2af69d88dSmrg * Copyright © 2014 Intel Corporation 3af69d88dSmrg * 4af69d88dSmrg * Permission is hereby granted, free of charge, to any person obtaining a 5af69d88dSmrg * copy of this software and associated documentation files (the "Software"), 6af69d88dSmrg * to deal in the Software without restriction, including without limitation 7af69d88dSmrg * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8af69d88dSmrg * and/or sell copies of the Software, and to permit persons to whom the 9af69d88dSmrg * Software is furnished to do so, subject to the following conditions: 10af69d88dSmrg * 11af69d88dSmrg * The above copyright notice and this permission notice (including the next 12af69d88dSmrg * paragraph) shall be included in all copies or substantial portions of the 13af69d88dSmrg * Software. 14af69d88dSmrg * 15af69d88dSmrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16af69d88dSmrg * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17af69d88dSmrg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 18af69d88dSmrg * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19af69d88dSmrg * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 20af69d88dSmrg * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 21af69d88dSmrg * DEALINGS IN THE SOFTWARE. 22af69d88dSmrg */ 23af69d88dSmrg 24af69d88dSmrg#include "glheader.h" 2501e04c3fSmrg#include "bufferobj.h" 26af69d88dSmrg#include "compute.h" 27af69d88dSmrg#include "context.h" 28af69d88dSmrg 2901e04c3fSmrgstatic bool 3001e04c3fSmrgcheck_valid_to_compute(struct gl_context *ctx, const char *function) 3101e04c3fSmrg{ 3201e04c3fSmrg if (!_mesa_has_compute_shaders(ctx)) { 3301e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 3401e04c3fSmrg "unsupported function (%s) called", 3501e04c3fSmrg function); 3601e04c3fSmrg return false; 3701e04c3fSmrg } 3801e04c3fSmrg 3901e04c3fSmrg /* From the OpenGL 4.3 Core Specification, Chapter 19, Compute Shaders: 4001e04c3fSmrg * 4101e04c3fSmrg * "An INVALID_OPERATION error is generated if there is no active program 4201e04c3fSmrg * for the compute shader stage." 4301e04c3fSmrg */ 4401e04c3fSmrg if (ctx->_Shader->CurrentProgram[MESA_SHADER_COMPUTE] == NULL) { 4501e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 4601e04c3fSmrg "%s(no active compute shader)", 4701e04c3fSmrg function); 4801e04c3fSmrg return false; 4901e04c3fSmrg } 5001e04c3fSmrg 5101e04c3fSmrg return true; 5201e04c3fSmrg} 5301e04c3fSmrg 5401e04c3fSmrgstatic bool 5501e04c3fSmrgvalidate_DispatchCompute(struct gl_context *ctx, const GLuint *num_groups) 5601e04c3fSmrg{ 5701e04c3fSmrg if (!check_valid_to_compute(ctx, "glDispatchCompute")) 5801e04c3fSmrg return GL_FALSE; 5901e04c3fSmrg 6001e04c3fSmrg for (int i = 0; i < 3; i++) { 6101e04c3fSmrg /* From the OpenGL 4.3 Core Specification, Chapter 19, Compute Shaders: 6201e04c3fSmrg * 6301e04c3fSmrg * "An INVALID_VALUE error is generated if any of num_groups_x, 6401e04c3fSmrg * num_groups_y and num_groups_z are greater than or equal to the 6501e04c3fSmrg * maximum work group count for the corresponding dimension." 6601e04c3fSmrg * 6701e04c3fSmrg * However, the "or equal to" portions appears to be a specification 6801e04c3fSmrg * bug. In all other areas, the specification appears to indicate that 6901e04c3fSmrg * the number of workgroups can match the MAX_COMPUTE_WORK_GROUP_COUNT 7001e04c3fSmrg * value. For example, under DispatchComputeIndirect: 7101e04c3fSmrg * 7201e04c3fSmrg * "If any of num_groups_x, num_groups_y or num_groups_z is greater than 7301e04c3fSmrg * the value of MAX_COMPUTE_WORK_GROUP_COUNT for the corresponding 7401e04c3fSmrg * dimension then the results are undefined." 7501e04c3fSmrg * 7601e04c3fSmrg * Additionally, the OpenGLES 3.1 specification does not contain "or 7701e04c3fSmrg * equal to" as an error condition. 7801e04c3fSmrg */ 7901e04c3fSmrg if (num_groups[i] > ctx->Const.MaxComputeWorkGroupCount[i]) { 8001e04c3fSmrg _mesa_error(ctx, GL_INVALID_VALUE, 8101e04c3fSmrg "glDispatchCompute(num_groups_%c)", 'x' + i); 8201e04c3fSmrg return GL_FALSE; 8301e04c3fSmrg } 8401e04c3fSmrg } 8501e04c3fSmrg 8601e04c3fSmrg /* The ARB_compute_variable_group_size spec says: 8701e04c3fSmrg * 8801e04c3fSmrg * "An INVALID_OPERATION error is generated by DispatchCompute if the active 8901e04c3fSmrg * program for the compute shader stage has a variable work group size." 9001e04c3fSmrg */ 9101e04c3fSmrg struct gl_program *prog = ctx->_Shader->CurrentProgram[MESA_SHADER_COMPUTE]; 927ec681f3Smrg if (prog->info.workgroup_size_variable) { 9301e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 9401e04c3fSmrg "glDispatchCompute(variable work group size forbidden)"); 9501e04c3fSmrg return GL_FALSE; 9601e04c3fSmrg } 9701e04c3fSmrg 9801e04c3fSmrg return GL_TRUE; 9901e04c3fSmrg} 10001e04c3fSmrg 10101e04c3fSmrgstatic bool 10201e04c3fSmrgvalidate_DispatchComputeGroupSizeARB(struct gl_context *ctx, 10301e04c3fSmrg const GLuint *num_groups, 10401e04c3fSmrg const GLuint *group_size) 10501e04c3fSmrg{ 10601e04c3fSmrg if (!check_valid_to_compute(ctx, "glDispatchComputeGroupSizeARB")) 10701e04c3fSmrg return GL_FALSE; 10801e04c3fSmrg 10901e04c3fSmrg /* The ARB_compute_variable_group_size spec says: 11001e04c3fSmrg * 11101e04c3fSmrg * "An INVALID_OPERATION error is generated by 11201e04c3fSmrg * DispatchComputeGroupSizeARB if the active program for the compute 11301e04c3fSmrg * shader stage has a fixed work group size." 11401e04c3fSmrg */ 11501e04c3fSmrg struct gl_program *prog = ctx->_Shader->CurrentProgram[MESA_SHADER_COMPUTE]; 1167ec681f3Smrg if (!prog->info.workgroup_size_variable) { 11701e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 11801e04c3fSmrg "glDispatchComputeGroupSizeARB(fixed work group size " 11901e04c3fSmrg "forbidden)"); 12001e04c3fSmrg return GL_FALSE; 12101e04c3fSmrg } 12201e04c3fSmrg 12301e04c3fSmrg for (int i = 0; i < 3; i++) { 12401e04c3fSmrg /* The ARB_compute_variable_group_size spec says: 12501e04c3fSmrg * 12601e04c3fSmrg * "An INVALID_VALUE error is generated if any of num_groups_x, 12701e04c3fSmrg * num_groups_y and num_groups_z are greater than or equal to the 12801e04c3fSmrg * maximum work group count for the corresponding dimension." 12901e04c3fSmrg */ 13001e04c3fSmrg if (num_groups[i] > ctx->Const.MaxComputeWorkGroupCount[i]) { 13101e04c3fSmrg _mesa_error(ctx, GL_INVALID_VALUE, 13201e04c3fSmrg "glDispatchComputeGroupSizeARB(num_groups_%c)", 'x' + i); 13301e04c3fSmrg return GL_FALSE; 13401e04c3fSmrg } 13501e04c3fSmrg 13601e04c3fSmrg /* The ARB_compute_variable_group_size spec says: 13701e04c3fSmrg * 13801e04c3fSmrg * "An INVALID_VALUE error is generated by DispatchComputeGroupSizeARB if 13901e04c3fSmrg * any of <group_size_x>, <group_size_y>, or <group_size_z> is less than 14001e04c3fSmrg * or equal to zero or greater than the maximum local work group size 14101e04c3fSmrg * for compute shaders with variable group size 14201e04c3fSmrg * (MAX_COMPUTE_VARIABLE_GROUP_SIZE_ARB) in the corresponding 14301e04c3fSmrg * dimension." 14401e04c3fSmrg * 14501e04c3fSmrg * However, the "less than" is a spec bug because they are declared as 14601e04c3fSmrg * unsigned integers. 14701e04c3fSmrg */ 14801e04c3fSmrg if (group_size[i] == 0 || 14901e04c3fSmrg group_size[i] > ctx->Const.MaxComputeVariableGroupSize[i]) { 15001e04c3fSmrg _mesa_error(ctx, GL_INVALID_VALUE, 15101e04c3fSmrg "glDispatchComputeGroupSizeARB(group_size_%c)", 'x' + i); 15201e04c3fSmrg return GL_FALSE; 15301e04c3fSmrg } 15401e04c3fSmrg } 15501e04c3fSmrg 15601e04c3fSmrg /* The ARB_compute_variable_group_size spec says: 15701e04c3fSmrg * 15801e04c3fSmrg * "An INVALID_VALUE error is generated by DispatchComputeGroupSizeARB if 15901e04c3fSmrg * the product of <group_size_x>, <group_size_y>, and <group_size_z> exceeds 16001e04c3fSmrg * the implementation-dependent maximum local work group invocation count 16101e04c3fSmrg * for compute shaders with variable group size 16201e04c3fSmrg * (MAX_COMPUTE_VARIABLE_GROUP_INVOCATIONS_ARB)." 16301e04c3fSmrg */ 1647ec681f3Smrg uint64_t total_invocations = group_size[0] * group_size[1]; 1657ec681f3Smrg if (total_invocations <= UINT32_MAX) { 1667ec681f3Smrg /* Only bother multiplying the third value if total still fits in 1677ec681f3Smrg * 32-bit, since MaxComputeVariableGroupInvocations is also 32-bit. 1687ec681f3Smrg */ 1697ec681f3Smrg total_invocations *= group_size[2]; 1707ec681f3Smrg } 17101e04c3fSmrg if (total_invocations > ctx->Const.MaxComputeVariableGroupInvocations) { 17201e04c3fSmrg _mesa_error(ctx, GL_INVALID_VALUE, 17301e04c3fSmrg "glDispatchComputeGroupSizeARB(product of local_sizes " 17401e04c3fSmrg "exceeds MAX_COMPUTE_VARIABLE_GROUP_INVOCATIONS_ARB " 1757ec681f3Smrg "(%u * %u * %u > %u))", 1767ec681f3Smrg group_size[0], group_size[1], group_size[2], 17701e04c3fSmrg ctx->Const.MaxComputeVariableGroupInvocations); 17801e04c3fSmrg return GL_FALSE; 17901e04c3fSmrg } 18001e04c3fSmrg 1817ec681f3Smrg /* The NV_compute_shader_derivatives spec says: 1827ec681f3Smrg * 1837ec681f3Smrg * "An INVALID_VALUE error is generated by DispatchComputeGroupSizeARB if 1847ec681f3Smrg * the active program for the compute shader stage has a compute shader 1857ec681f3Smrg * using the "derivative_group_quadsNV" layout qualifier and 1867ec681f3Smrg * <group_size_x> or <group_size_y> is not a multiple of two. 1877ec681f3Smrg * 1887ec681f3Smrg * An INVALID_VALUE error is generated by DispatchComputeGroupSizeARB if 1897ec681f3Smrg * the active program for the compute shader stage has a compute shader 1907ec681f3Smrg * using the "derivative_group_linearNV" layout qualifier and the product 1917ec681f3Smrg * of <group_size_x>, <group_size_y>, and <group_size_z> is not a multiple 1927ec681f3Smrg * of four." 1937ec681f3Smrg */ 1947ec681f3Smrg if (prog->info.cs.derivative_group == DERIVATIVE_GROUP_QUADS && 1957ec681f3Smrg ((group_size[0] & 1) || (group_size[1] & 1))) { 1967ec681f3Smrg _mesa_error(ctx, GL_INVALID_VALUE, 1977ec681f3Smrg "glDispatchComputeGroupSizeARB(derivative_group_quadsNV " 1987ec681f3Smrg "requires group_size_x (%d) and group_size_y (%d) to be " 1997ec681f3Smrg "divisble by 2)", group_size[0], group_size[1]); 2007ec681f3Smrg return GL_FALSE; 2017ec681f3Smrg } 2027ec681f3Smrg 2037ec681f3Smrg if (prog->info.cs.derivative_group == DERIVATIVE_GROUP_LINEAR && 2047ec681f3Smrg total_invocations & 3) { 2057ec681f3Smrg _mesa_error(ctx, GL_INVALID_VALUE, 2067ec681f3Smrg "glDispatchComputeGroupSizeARB(derivative_group_linearNV " 2077ec681f3Smrg "requires product of group sizes (%"PRIu64") to be divisible " 2087ec681f3Smrg "by 4)", total_invocations); 2097ec681f3Smrg return GL_FALSE; 2107ec681f3Smrg } 2117ec681f3Smrg 21201e04c3fSmrg return GL_TRUE; 21301e04c3fSmrg} 21401e04c3fSmrg 21501e04c3fSmrgstatic bool 21601e04c3fSmrgvalid_dispatch_indirect(struct gl_context *ctx, GLintptr indirect) 21701e04c3fSmrg{ 21801e04c3fSmrg GLsizei size = 3 * sizeof(GLuint); 21901e04c3fSmrg const uint64_t end = (uint64_t) indirect + size; 22001e04c3fSmrg const char *name = "glDispatchComputeIndirect"; 22101e04c3fSmrg 22201e04c3fSmrg if (!check_valid_to_compute(ctx, name)) 22301e04c3fSmrg return GL_FALSE; 22401e04c3fSmrg 22501e04c3fSmrg /* From the OpenGL 4.3 Core Specification, Chapter 19, Compute Shaders: 22601e04c3fSmrg * 22701e04c3fSmrg * "An INVALID_VALUE error is generated if indirect is negative or is not a 22801e04c3fSmrg * multiple of four." 22901e04c3fSmrg */ 23001e04c3fSmrg if (indirect & (sizeof(GLuint) - 1)) { 23101e04c3fSmrg _mesa_error(ctx, GL_INVALID_VALUE, 23201e04c3fSmrg "%s(indirect is not aligned)", name); 23301e04c3fSmrg return GL_FALSE; 23401e04c3fSmrg } 23501e04c3fSmrg 23601e04c3fSmrg if (indirect < 0) { 23701e04c3fSmrg _mesa_error(ctx, GL_INVALID_VALUE, 23801e04c3fSmrg "%s(indirect is less than zero)", name); 23901e04c3fSmrg return GL_FALSE; 24001e04c3fSmrg } 24101e04c3fSmrg 24201e04c3fSmrg /* From the OpenGL 4.3 Core Specification, Chapter 19, Compute Shaders: 24301e04c3fSmrg * 24401e04c3fSmrg * "An INVALID_OPERATION error is generated if no buffer is bound to the 24501e04c3fSmrg * DRAW_INDIRECT_BUFFER binding, or if the command would source data 24601e04c3fSmrg * beyond the end of the buffer object." 24701e04c3fSmrg */ 2487ec681f3Smrg if (!ctx->DispatchIndirectBuffer) { 24901e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 25001e04c3fSmrg "%s: no buffer bound to DISPATCH_INDIRECT_BUFFER", name); 25101e04c3fSmrg return GL_FALSE; 25201e04c3fSmrg } 25301e04c3fSmrg 25401e04c3fSmrg if (_mesa_check_disallowed_mapping(ctx->DispatchIndirectBuffer)) { 25501e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 25601e04c3fSmrg "%s(DISPATCH_INDIRECT_BUFFER is mapped)", name); 25701e04c3fSmrg return GL_FALSE; 25801e04c3fSmrg } 25901e04c3fSmrg 26001e04c3fSmrg if (ctx->DispatchIndirectBuffer->Size < end) { 26101e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 26201e04c3fSmrg "%s(DISPATCH_INDIRECT_BUFFER too small)", name); 26301e04c3fSmrg return GL_FALSE; 26401e04c3fSmrg } 26501e04c3fSmrg 26601e04c3fSmrg /* The ARB_compute_variable_group_size spec says: 26701e04c3fSmrg * 26801e04c3fSmrg * "An INVALID_OPERATION error is generated if the active program for the 26901e04c3fSmrg * compute shader stage has a variable work group size." 27001e04c3fSmrg */ 27101e04c3fSmrg struct gl_program *prog = ctx->_Shader->CurrentProgram[MESA_SHADER_COMPUTE]; 2727ec681f3Smrg if (prog->info.workgroup_size_variable) { 27301e04c3fSmrg _mesa_error(ctx, GL_INVALID_OPERATION, 27401e04c3fSmrg "%s(variable work group size forbidden)", name); 27501e04c3fSmrg return GL_FALSE; 27601e04c3fSmrg } 27701e04c3fSmrg 27801e04c3fSmrg return GL_TRUE; 27901e04c3fSmrg} 28001e04c3fSmrg 28101e04c3fSmrgstatic ALWAYS_INLINE void 28201e04c3fSmrgdispatch_compute(GLuint num_groups_x, GLuint num_groups_y, 28301e04c3fSmrg GLuint num_groups_z, bool no_error) 28401e04c3fSmrg{ 28501e04c3fSmrg GET_CURRENT_CONTEXT(ctx); 28601e04c3fSmrg const GLuint num_groups[3] = { num_groups_x, num_groups_y, num_groups_z }; 28701e04c3fSmrg 2887ec681f3Smrg FLUSH_VERTICES(ctx, 0, 0); 28901e04c3fSmrg 29001e04c3fSmrg if (MESA_VERBOSE & VERBOSE_API) 29101e04c3fSmrg _mesa_debug(ctx, "glDispatchCompute(%d, %d, %d)\n", 29201e04c3fSmrg num_groups_x, num_groups_y, num_groups_z); 29301e04c3fSmrg 29401e04c3fSmrg if (!no_error && !validate_DispatchCompute(ctx, num_groups)) 29501e04c3fSmrg return; 29601e04c3fSmrg 29701e04c3fSmrg if (num_groups_x == 0u || num_groups_y == 0u || num_groups_z == 0u) 29801e04c3fSmrg return; 29901e04c3fSmrg 30001e04c3fSmrg ctx->Driver.DispatchCompute(ctx, num_groups); 3017ec681f3Smrg 3027ec681f3Smrg if (MESA_DEBUG_FLAGS & DEBUG_ALWAYS_FLUSH) 3037ec681f3Smrg _mesa_flush(ctx); 30401e04c3fSmrg} 30501e04c3fSmrg 30601e04c3fSmrgvoid GLAPIENTRY 30701e04c3fSmrg_mesa_DispatchCompute_no_error(GLuint num_groups_x, GLuint num_groups_y, 30801e04c3fSmrg GLuint num_groups_z) 30901e04c3fSmrg{ 31001e04c3fSmrg dispatch_compute(num_groups_x, num_groups_y, num_groups_z, true); 31101e04c3fSmrg} 31201e04c3fSmrg 313af69d88dSmrgvoid GLAPIENTRY 314af69d88dSmrg_mesa_DispatchCompute(GLuint num_groups_x, 315af69d88dSmrg GLuint num_groups_y, 316af69d88dSmrg GLuint num_groups_z) 31701e04c3fSmrg{ 31801e04c3fSmrg dispatch_compute(num_groups_x, num_groups_y, num_groups_z, false); 31901e04c3fSmrg} 32001e04c3fSmrg 32101e04c3fSmrgstatic ALWAYS_INLINE void 32201e04c3fSmrgdispatch_compute_indirect(GLintptr indirect, bool no_error) 323af69d88dSmrg{ 324af69d88dSmrg GET_CURRENT_CONTEXT(ctx); 325af69d88dSmrg 3267ec681f3Smrg FLUSH_VERTICES(ctx, 0, 0); 32701e04c3fSmrg 32801e04c3fSmrg if (MESA_VERBOSE & VERBOSE_API) 32901e04c3fSmrg _mesa_debug(ctx, "glDispatchComputeIndirect(%ld)\n", (long) indirect); 33001e04c3fSmrg 33101e04c3fSmrg if (!no_error && !valid_dispatch_indirect(ctx, indirect)) 33201e04c3fSmrg return; 33301e04c3fSmrg 33401e04c3fSmrg ctx->Driver.DispatchComputeIndirect(ctx, indirect); 3357ec681f3Smrg 3367ec681f3Smrg if (MESA_DEBUG_FLAGS & DEBUG_ALWAYS_FLUSH) 3377ec681f3Smrg _mesa_flush(ctx); 33801e04c3fSmrg} 33901e04c3fSmrg 34001e04c3fSmrgextern void GLAPIENTRY 34101e04c3fSmrg_mesa_DispatchComputeIndirect_no_error(GLintptr indirect) 34201e04c3fSmrg{ 34301e04c3fSmrg dispatch_compute_indirect(indirect, true); 344af69d88dSmrg} 345af69d88dSmrg 346af69d88dSmrgextern void GLAPIENTRY 347af69d88dSmrg_mesa_DispatchComputeIndirect(GLintptr indirect) 34801e04c3fSmrg{ 34901e04c3fSmrg dispatch_compute_indirect(indirect, false); 35001e04c3fSmrg} 35101e04c3fSmrg 35201e04c3fSmrgstatic ALWAYS_INLINE void 35301e04c3fSmrgdispatch_compute_group_size(GLuint num_groups_x, GLuint num_groups_y, 35401e04c3fSmrg GLuint num_groups_z, GLuint group_size_x, 35501e04c3fSmrg GLuint group_size_y, GLuint group_size_z, 35601e04c3fSmrg bool no_error) 357af69d88dSmrg{ 358af69d88dSmrg GET_CURRENT_CONTEXT(ctx); 35901e04c3fSmrg const GLuint num_groups[3] = { num_groups_x, num_groups_y, num_groups_z }; 36001e04c3fSmrg const GLuint group_size[3] = { group_size_x, group_size_y, group_size_z }; 361af69d88dSmrg 3627ec681f3Smrg FLUSH_VERTICES(ctx, 0, 0); 36301e04c3fSmrg 36401e04c3fSmrg if (MESA_VERBOSE & VERBOSE_API) 36501e04c3fSmrg _mesa_debug(ctx, 36601e04c3fSmrg "glDispatchComputeGroupSizeARB(%d, %d, %d, %d, %d, %d)\n", 36701e04c3fSmrg num_groups_x, num_groups_y, num_groups_z, 36801e04c3fSmrg group_size_x, group_size_y, group_size_z); 36901e04c3fSmrg 37001e04c3fSmrg if (!no_error && 37101e04c3fSmrg !validate_DispatchComputeGroupSizeARB(ctx, num_groups, group_size)) 37201e04c3fSmrg return; 37301e04c3fSmrg 37401e04c3fSmrg if (num_groups_x == 0u || num_groups_y == 0u || num_groups_z == 0u) 37501e04c3fSmrg return; 37601e04c3fSmrg 37701e04c3fSmrg ctx->Driver.DispatchComputeGroupSize(ctx, num_groups, group_size); 3787ec681f3Smrg 3797ec681f3Smrg if (MESA_DEBUG_FLAGS & DEBUG_ALWAYS_FLUSH) 3807ec681f3Smrg _mesa_flush(ctx); 38101e04c3fSmrg} 38201e04c3fSmrg 38301e04c3fSmrgvoid GLAPIENTRY 38401e04c3fSmrg_mesa_DispatchComputeGroupSizeARB_no_error(GLuint num_groups_x, 38501e04c3fSmrg GLuint num_groups_y, 38601e04c3fSmrg GLuint num_groups_z, 38701e04c3fSmrg GLuint group_size_x, 38801e04c3fSmrg GLuint group_size_y, 38901e04c3fSmrg GLuint group_size_z) 39001e04c3fSmrg{ 39101e04c3fSmrg dispatch_compute_group_size(num_groups_x, num_groups_y, num_groups_z, 39201e04c3fSmrg group_size_x, group_size_y, group_size_z, 39301e04c3fSmrg true); 39401e04c3fSmrg} 39501e04c3fSmrg 39601e04c3fSmrgvoid GLAPIENTRY 39701e04c3fSmrg_mesa_DispatchComputeGroupSizeARB(GLuint num_groups_x, GLuint num_groups_y, 39801e04c3fSmrg GLuint num_groups_z, GLuint group_size_x, 39901e04c3fSmrg GLuint group_size_y, GLuint group_size_z) 40001e04c3fSmrg{ 40101e04c3fSmrg dispatch_compute_group_size(num_groups_x, num_groups_y, num_groups_z, 40201e04c3fSmrg group_size_x, group_size_y, group_size_z, 40301e04c3fSmrg false); 404af69d88dSmrg} 405