2 * Mesa 3-D graphics library
4 * Copyright (C) 2004-2008 Brian Paul All Rights Reserved.
5 * Copyright (C) 2009-2010 VMware, Inc. All Rights Reserved.
6 * Copyright © 2010 Intel Corporation
8 * Permission is hereby granted, free of charge, to any person obtaining a
9 * copy of this software and associated documentation files (the "Software"),
10 * to deal in the Software without restriction, including without limitation
11 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
12 * and/or sell copies of the Software, and to permit persons to whom the
13 * Software is furnished to do so, subject to the following conditions:
15 * The above copyright notice and this permission notice shall be included
16 * in all copies or substantial portions of the Software.
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
23 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
28 * Functions related to GLSL uniform variables.
34 * 1. Check that the right error code is generated for all _mesa_error() calls.
35 * 2. Insert FLUSH_VERTICES calls in various places
39 #include "main/glheader.h"
40 #include "main/context.h"
41 #include "main/dispatch.h"
42 #include "main/mfeatures.h"
43 #include "main/mtypes.h"
44 #include "main/shaderapi.h"
45 #include "main/shaderobj.h"
46 #include "main/uniforms.h"
47 #include "program/prog_parameter.h"
48 #include "program/prog_statevars.h"
49 #include "program/prog_uniform.h"
50 #include "program/prog_instruction.h"
54 base_uniform_type(GLenum type
)
57 #if 0 /* not needed, for now */
70 case GL_UNSIGNED_INT_VEC2
:
71 case GL_UNSIGNED_INT_VEC3
:
72 case GL_UNSIGNED_INT_VEC4
:
73 return GL_UNSIGNED_INT
;
80 _mesa_problem(NULL
, "Invalid type in base_uniform_type()");
85 static struct gl_builtin_uniform_element gl_DepthRange_elements
[] = {
86 {"near", {STATE_DEPTH_RANGE
, 0, 0}, SWIZZLE_XXXX
},
87 {"far", {STATE_DEPTH_RANGE
, 0, 0}, SWIZZLE_YYYY
},
88 {"diff", {STATE_DEPTH_RANGE
, 0, 0}, SWIZZLE_ZZZZ
},
91 static struct gl_builtin_uniform_element gl_ClipPlane_elements
[] = {
92 {NULL
, {STATE_CLIPPLANE
, 0, 0}, SWIZZLE_XYZW
}
95 static struct gl_builtin_uniform_element gl_Point_elements
[] = {
96 {"size", {STATE_POINT_SIZE
}, SWIZZLE_XXXX
},
97 {"sizeMin", {STATE_POINT_SIZE
}, SWIZZLE_YYYY
},
98 {"sizeMax", {STATE_POINT_SIZE
}, SWIZZLE_ZZZZ
},
99 {"fadeThresholdSize", {STATE_POINT_SIZE
}, SWIZZLE_WWWW
},
100 {"distanceConstantAttenuation", {STATE_POINT_ATTENUATION
}, SWIZZLE_XXXX
},
101 {"distanceLinearAttenuation", {STATE_POINT_ATTENUATION
}, SWIZZLE_YYYY
},
102 {"distanceQuadraticAttenuation", {STATE_POINT_ATTENUATION
}, SWIZZLE_ZZZZ
},
105 static struct gl_builtin_uniform_element gl_FrontMaterial_elements
[] = {
106 {"emission", {STATE_MATERIAL
, 0, STATE_EMISSION
}, SWIZZLE_XYZW
},
107 {"ambient", {STATE_MATERIAL
, 0, STATE_AMBIENT
}, SWIZZLE_XYZW
},
108 {"diffuse", {STATE_MATERIAL
, 0, STATE_DIFFUSE
}, SWIZZLE_XYZW
},
109 {"specular", {STATE_MATERIAL
, 0, STATE_SPECULAR
}, SWIZZLE_XYZW
},
110 {"shininess", {STATE_MATERIAL
, 0, STATE_SHININESS
}, SWIZZLE_XXXX
},
113 static struct gl_builtin_uniform_element gl_BackMaterial_elements
[] = {
114 {"emission", {STATE_MATERIAL
, 1, STATE_EMISSION
}, SWIZZLE_XYZW
},
115 {"ambient", {STATE_MATERIAL
, 1, STATE_AMBIENT
}, SWIZZLE_XYZW
},
116 {"diffuse", {STATE_MATERIAL
, 1, STATE_DIFFUSE
}, SWIZZLE_XYZW
},
117 {"specular", {STATE_MATERIAL
, 1, STATE_SPECULAR
}, SWIZZLE_XYZW
},
118 {"shininess", {STATE_MATERIAL
, 1, STATE_SHININESS
}, SWIZZLE_XXXX
},
121 static struct gl_builtin_uniform_element gl_LightSource_elements
[] = {
122 {"ambient", {STATE_LIGHT
, 0, STATE_AMBIENT
}, SWIZZLE_XYZW
},
123 {"diffuse", {STATE_LIGHT
, 0, STATE_DIFFUSE
}, SWIZZLE_XYZW
},
124 {"specular", {STATE_LIGHT
, 0, STATE_SPECULAR
}, SWIZZLE_XYZW
},
125 {"position", {STATE_LIGHT
, 0, STATE_POSITION
}, SWIZZLE_XYZW
},
126 {"halfVector", {STATE_LIGHT
, 0, STATE_HALF_VECTOR
}, SWIZZLE_XYZW
},
127 {"spotDirection", {STATE_LIGHT
, 0, STATE_SPOT_DIRECTION
},
128 MAKE_SWIZZLE4(SWIZZLE_X
,
132 {"spotCosCutoff", {STATE_LIGHT
, 0, STATE_SPOT_DIRECTION
}, SWIZZLE_WWWW
},
133 {"spotCutoff", {STATE_LIGHT
, 0, STATE_SPOT_CUTOFF
}, SWIZZLE_XXXX
},
134 {"spotExponent", {STATE_LIGHT
, 0, STATE_ATTENUATION
}, SWIZZLE_WWWW
},
135 {"constantAttenuation", {STATE_LIGHT
, 0, STATE_ATTENUATION
}, SWIZZLE_XXXX
},
136 {"linearAttenuation", {STATE_LIGHT
, 0, STATE_ATTENUATION
}, SWIZZLE_YYYY
},
137 {"quadraticAttenuation", {STATE_LIGHT
, 0, STATE_ATTENUATION
}, SWIZZLE_ZZZZ
},
140 static struct gl_builtin_uniform_element gl_LightModel_elements
[] = {
141 {"ambient", {STATE_LIGHTMODEL_AMBIENT
, 0}, SWIZZLE_XYZW
},
144 static struct gl_builtin_uniform_element gl_FrontLightModelProduct_elements
[] = {
145 {"sceneColor", {STATE_LIGHTMODEL_SCENECOLOR
, 0}, SWIZZLE_XYZW
},
148 static struct gl_builtin_uniform_element gl_BackLightModelProduct_elements
[] = {
149 {"sceneColor", {STATE_LIGHTMODEL_SCENECOLOR
, 1}, SWIZZLE_XYZW
},
152 static struct gl_builtin_uniform_element gl_FrontLightProduct_elements
[] = {
153 {"ambient", {STATE_LIGHTPROD
, 0, 0, STATE_AMBIENT
}, SWIZZLE_XYZW
},
154 {"diffuse", {STATE_LIGHTPROD
, 0, 0, STATE_DIFFUSE
}, SWIZZLE_XYZW
},
155 {"specular", {STATE_LIGHTPROD
, 0, 0, STATE_SPECULAR
}, SWIZZLE_XYZW
},
158 static struct gl_builtin_uniform_element gl_BackLightProduct_elements
[] = {
159 {"ambient", {STATE_LIGHTPROD
, 0, 1, STATE_AMBIENT
}, SWIZZLE_XYZW
},
160 {"diffuse", {STATE_LIGHTPROD
, 0, 1, STATE_DIFFUSE
}, SWIZZLE_XYZW
},
161 {"specular", {STATE_LIGHTPROD
, 0, 1, STATE_SPECULAR
}, SWIZZLE_XYZW
},
164 static struct gl_builtin_uniform_element gl_TextureEnvColor_elements
[] = {
165 {NULL
, {STATE_TEXENV_COLOR
, 0}, SWIZZLE_XYZW
},
168 static struct gl_builtin_uniform_element gl_EyePlaneS_elements
[] = {
169 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_EYE_S
}, SWIZZLE_XYZW
},
172 static struct gl_builtin_uniform_element gl_EyePlaneT_elements
[] = {
173 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_EYE_T
}, SWIZZLE_XYZW
},
176 static struct gl_builtin_uniform_element gl_EyePlaneR_elements
[] = {
177 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_EYE_R
}, SWIZZLE_XYZW
},
180 static struct gl_builtin_uniform_element gl_EyePlaneQ_elements
[] = {
181 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_EYE_Q
}, SWIZZLE_XYZW
},
184 static struct gl_builtin_uniform_element gl_ObjectPlaneS_elements
[] = {
185 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_OBJECT_S
}, SWIZZLE_XYZW
},
188 static struct gl_builtin_uniform_element gl_ObjectPlaneT_elements
[] = {
189 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_OBJECT_T
}, SWIZZLE_XYZW
},
192 static struct gl_builtin_uniform_element gl_ObjectPlaneR_elements
[] = {
193 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_OBJECT_R
}, SWIZZLE_XYZW
},
196 static struct gl_builtin_uniform_element gl_ObjectPlaneQ_elements
[] = {
197 {NULL
, {STATE_TEXGEN
, 0, STATE_TEXGEN_OBJECT_Q
}, SWIZZLE_XYZW
},
200 static struct gl_builtin_uniform_element gl_Fog_elements
[] = {
201 {"color", {STATE_FOG_COLOR
}, SWIZZLE_XYZW
},
202 {"density", {STATE_FOG_PARAMS
}, SWIZZLE_XXXX
},
203 {"start", {STATE_FOG_PARAMS
}, SWIZZLE_YYYY
},
204 {"end", {STATE_FOG_PARAMS
}, SWIZZLE_ZZZZ
},
205 {"scale", {STATE_FOG_PARAMS
}, SWIZZLE_WWWW
},
208 static struct gl_builtin_uniform_element gl_NormalScale_elements
[] = {
209 {NULL
, {STATE_NORMAL_SCALE
}, SWIZZLE_XXXX
},
212 static struct gl_builtin_uniform_element gl_MESABumpRotMatrix0_elements
[] = {
213 {NULL
, {STATE_INTERNAL
, STATE_ROT_MATRIX_0
}, SWIZZLE_XYZW
},
216 static struct gl_builtin_uniform_element gl_MESABumpRotMatrix1_elements
[] = {
217 {NULL
, {STATE_INTERNAL
, STATE_ROT_MATRIX_1
}, SWIZZLE_XYZW
},
220 static struct gl_builtin_uniform_element gl_MESAFogParamsOptimized_elements
[] = {
221 {NULL
, {STATE_INTERNAL
, STATE_FOG_PARAMS_OPTIMIZED
}, SWIZZLE_XYZW
},
224 #define MATRIX(name, statevar, modifier) \
225 static struct gl_builtin_uniform_element name ## _elements[] = { \
226 { NULL, { statevar, 0, 0, 0, modifier}, SWIZZLE_XYZW }, \
227 { NULL, { statevar, 0, 1, 1, modifier}, SWIZZLE_XYZW }, \
228 { NULL, { statevar, 0, 2, 2, modifier}, SWIZZLE_XYZW }, \
229 { NULL, { statevar, 0, 3, 3, modifier}, SWIZZLE_XYZW }, \
232 MATRIX(gl_ModelViewMatrix
,
233 STATE_MODELVIEW_MATRIX
, STATE_MATRIX_TRANSPOSE
);
234 MATRIX(gl_ModelViewMatrixInverse
,
235 STATE_MODELVIEW_MATRIX
, STATE_MATRIX_INVTRANS
);
236 MATRIX(gl_ModelViewMatrixTranspose
,
237 STATE_MODELVIEW_MATRIX
, 0);
238 MATRIX(gl_ModelViewMatrixInverseTranspose
,
239 STATE_MODELVIEW_MATRIX
, STATE_MATRIX_INVERSE
);
241 MATRIX(gl_ProjectionMatrix
,
242 STATE_PROJECTION_MATRIX
, STATE_MATRIX_TRANSPOSE
);
243 MATRIX(gl_ProjectionMatrixInverse
,
244 STATE_PROJECTION_MATRIX
, STATE_MATRIX_INVTRANS
);
245 MATRIX(gl_ProjectionMatrixTranspose
,
246 STATE_PROJECTION_MATRIX
, 0);
247 MATRIX(gl_ProjectionMatrixInverseTranspose
,
248 STATE_PROJECTION_MATRIX
, STATE_MATRIX_INVERSE
);
250 MATRIX(gl_ModelViewProjectionMatrix
,
251 STATE_MVP_MATRIX
, STATE_MATRIX_TRANSPOSE
);
252 MATRIX(gl_ModelViewProjectionMatrixInverse
,
253 STATE_MVP_MATRIX
, STATE_MATRIX_INVTRANS
);
254 MATRIX(gl_ModelViewProjectionMatrixTranspose
,
255 STATE_MVP_MATRIX
, 0);
256 MATRIX(gl_ModelViewProjectionMatrixInverseTranspose
,
257 STATE_MVP_MATRIX
, STATE_MATRIX_INVERSE
);
259 MATRIX(gl_TextureMatrix
,
260 STATE_TEXTURE_MATRIX
, STATE_MATRIX_TRANSPOSE
);
261 MATRIX(gl_TextureMatrixInverse
,
262 STATE_TEXTURE_MATRIX
, STATE_MATRIX_INVTRANS
);
263 MATRIX(gl_TextureMatrixTranspose
,
264 STATE_TEXTURE_MATRIX
, 0);
265 MATRIX(gl_TextureMatrixInverseTranspose
,
266 STATE_TEXTURE_MATRIX
, STATE_MATRIX_INVERSE
);
268 static struct gl_builtin_uniform_element gl_NormalMatrix_elements
[] = {
269 { NULL
, { STATE_MODELVIEW_MATRIX
, 0, 0, 0, STATE_MATRIX_INVERSE
},
271 { NULL
, { STATE_MODELVIEW_MATRIX
, 0, 1, 1, STATE_MATRIX_INVERSE
},
273 { NULL
, { STATE_MODELVIEW_MATRIX
, 0, 2, 2, STATE_MATRIX_INVERSE
},
279 #define STATEVAR(name) {#name, name ## _elements, Elements(name ## _elements)}
281 const struct gl_builtin_uniform_desc _mesa_builtin_uniform_desc
[] = {
282 STATEVAR(gl_DepthRange
),
283 STATEVAR(gl_ClipPlane
),
285 STATEVAR(gl_FrontMaterial
),
286 STATEVAR(gl_BackMaterial
),
287 STATEVAR(gl_LightSource
),
288 STATEVAR(gl_LightModel
),
289 STATEVAR(gl_FrontLightModelProduct
),
290 STATEVAR(gl_BackLightModelProduct
),
291 STATEVAR(gl_FrontLightProduct
),
292 STATEVAR(gl_BackLightProduct
),
293 STATEVAR(gl_TextureEnvColor
),
294 STATEVAR(gl_EyePlaneS
),
295 STATEVAR(gl_EyePlaneT
),
296 STATEVAR(gl_EyePlaneR
),
297 STATEVAR(gl_EyePlaneQ
),
298 STATEVAR(gl_ObjectPlaneS
),
299 STATEVAR(gl_ObjectPlaneT
),
300 STATEVAR(gl_ObjectPlaneR
),
301 STATEVAR(gl_ObjectPlaneQ
),
304 STATEVAR(gl_ModelViewMatrix
),
305 STATEVAR(gl_ModelViewMatrixInverse
),
306 STATEVAR(gl_ModelViewMatrixTranspose
),
307 STATEVAR(gl_ModelViewMatrixInverseTranspose
),
309 STATEVAR(gl_ProjectionMatrix
),
310 STATEVAR(gl_ProjectionMatrixInverse
),
311 STATEVAR(gl_ProjectionMatrixTranspose
),
312 STATEVAR(gl_ProjectionMatrixInverseTranspose
),
314 STATEVAR(gl_ModelViewProjectionMatrix
),
315 STATEVAR(gl_ModelViewProjectionMatrixInverse
),
316 STATEVAR(gl_ModelViewProjectionMatrixTranspose
),
317 STATEVAR(gl_ModelViewProjectionMatrixInverseTranspose
),
319 STATEVAR(gl_TextureMatrix
),
320 STATEVAR(gl_TextureMatrixInverse
),
321 STATEVAR(gl_TextureMatrixTranspose
),
322 STATEVAR(gl_TextureMatrixInverseTranspose
),
324 STATEVAR(gl_NormalMatrix
),
325 STATEVAR(gl_NormalScale
),
327 STATEVAR(gl_MESABumpRotMatrix0
),
328 STATEVAR(gl_MESABumpRotMatrix1
),
329 STATEVAR(gl_MESAFogParamsOptimized
),
335 is_boolean_type(GLenum type
)
350 is_sampler_type(GLenum type
)
356 case GL_SAMPLER_CUBE
:
357 case GL_SAMPLER_1D_SHADOW
:
358 case GL_SAMPLER_2D_SHADOW
:
359 case GL_SAMPLER_2D_RECT_ARB
:
360 case GL_SAMPLER_2D_RECT_SHADOW_ARB
:
361 case GL_SAMPLER_1D_ARRAY_EXT
:
362 case GL_SAMPLER_2D_ARRAY_EXT
:
363 case GL_SAMPLER_1D_ARRAY_SHADOW_EXT
:
364 case GL_SAMPLER_2D_ARRAY_SHADOW_EXT
:
372 static struct gl_program_parameter
*
373 get_uniform_parameter(const struct gl_shader_program
*shProg
, GLuint index
)
375 const struct gl_program
*prog
= NULL
;
378 progPos
= shProg
->Uniforms
->Uniforms
[index
].VertPos
;
380 prog
= &shProg
->VertexProgram
->Base
;
383 progPos
= shProg
->Uniforms
->Uniforms
[index
].FragPos
;
385 prog
= &shProg
->FragmentProgram
->Base
;
387 progPos
= shProg
->Uniforms
->Uniforms
[index
].GeomPos
;
389 prog
= &shProg
->GeometryProgram
->Base
;
394 if (!prog
|| progPos
< 0)
395 return NULL
; /* should never happen */
397 return &prog
->Parameters
->Parameters
[progPos
];
402 * Called by glGetActiveUniform().
405 _mesa_get_active_uniform(struct gl_context
*ctx
, GLuint program
, GLuint index
,
406 GLsizei maxLength
, GLsizei
*length
, GLint
*size
,
407 GLenum
*type
, GLchar
*nameOut
)
409 const struct gl_shader_program
*shProg
;
410 const struct gl_program
*prog
= NULL
;
411 const struct gl_program_parameter
*param
;
414 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glGetActiveUniform");
418 if (!shProg
->Uniforms
|| index
>= shProg
->Uniforms
->NumUniforms
) {
419 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetActiveUniform(index)");
423 progPos
= shProg
->Uniforms
->Uniforms
[index
].VertPos
;
425 prog
= &shProg
->VertexProgram
->Base
;
428 progPos
= shProg
->Uniforms
->Uniforms
[index
].FragPos
;
430 prog
= &shProg
->FragmentProgram
->Base
;
432 progPos
= shProg
->Uniforms
->Uniforms
[index
].GeomPos
;
434 prog
= &shProg
->GeometryProgram
->Base
;
439 if (!prog
|| progPos
< 0)
440 return; /* should never happen */
442 ASSERT(progPos
< prog
->Parameters
->NumParameters
);
443 param
= &prog
->Parameters
->Parameters
[progPos
];
446 _mesa_copy_string(nameOut
, maxLength
, length
, param
->Name
);
450 GLint typeSize
= _mesa_sizeof_glsl_type(param
->DataType
);
451 if ((GLint
) param
->Size
> typeSize
) {
453 * Array elements are placed on vector[4] boundaries so they're
454 * a multiple of four floats. We round typeSize up to next multiple
455 * of four to get the right size below.
457 typeSize
= (typeSize
+ 3) & ~3;
459 /* Note that the returned size is in units of the <type>, not bytes */
460 *size
= param
->Size
/ typeSize
;
464 *type
= param
->DataType
;
470 get_vector_elements(GLenum type
)
476 case GL_UNSIGNED_INT
:
477 default: /* Catch all the various sampler types. */
483 case GL_UNSIGNED_INT_VEC2
:
489 case GL_UNSIGNED_INT_VEC3
:
495 case GL_UNSIGNED_INT_VEC4
:
501 get_matrix_dims(GLenum type
, GLint
*rows
, GLint
*cols
)
507 case GL_FLOAT_MAT2x3
:
511 case GL_FLOAT_MAT2x4
:
519 case GL_FLOAT_MAT3x2
:
523 case GL_FLOAT_MAT3x4
:
531 case GL_FLOAT_MAT4x2
:
535 case GL_FLOAT_MAT4x3
:
546 * Determine the number of rows and columns occupied by a uniform
547 * according to its datatype. For non-matrix types (such as GL_FLOAT_VEC4),
548 * the number of rows = 1 and cols = number of elements in the vector.
551 get_uniform_rows_cols(const struct gl_program_parameter
*p
,
552 GLint
*rows
, GLint
*cols
)
554 get_matrix_dims(p
->DataType
, rows
, cols
);
555 if (*rows
== 0 && *cols
== 0) {
556 /* not a matrix type, probably a float or vector */
558 *cols
= get_vector_elements(p
->DataType
);
564 * Helper for get_uniform[fi]v() functions.
565 * Given a shader program name and uniform location, return a pointer
566 * to the shader program and return the program parameter position.
569 lookup_uniform_parameter(struct gl_context
*ctx
, GLuint program
, GLint location
,
570 struct gl_program
**progOut
, GLint
*paramPosOut
)
572 struct gl_shader_program
*shProg
573 = _mesa_lookup_shader_program_err(ctx
, program
, "glGetUniform[if]v");
574 struct gl_program
*prog
= NULL
;
577 /* if shProg is NULL, we'll have already recorded an error */
580 if (!shProg
->Uniforms
||
582 location
>= (GLint
) shProg
->Uniforms
->NumUniforms
) {
583 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glGetUniformfv(location)");
586 /* OK, find the gl_program and program parameter location */
587 progPos
= shProg
->Uniforms
->Uniforms
[location
].VertPos
;
589 prog
= &shProg
->VertexProgram
->Base
;
592 progPos
= shProg
->Uniforms
->Uniforms
[location
].FragPos
;
594 prog
= &shProg
->FragmentProgram
->Base
;
596 progPos
= shProg
->Uniforms
->Uniforms
[location
].GeomPos
;
598 prog
= &shProg
->GeometryProgram
->Base
;
606 *paramPosOut
= progPos
;
611 * GLGL uniform arrays and structs require special handling.
613 * The GL_ARB_shader_objects spec says that if you use
614 * glGetUniformLocation to get the location of an array, you CANNOT
615 * access other elements of the array by adding an offset to the
616 * returned location. For example, you must call
617 * glGetUniformLocation("foo[16]") if you want to set the 16th element
618 * of the array with glUniform().
620 * HOWEVER, some other OpenGL drivers allow accessing array elements
621 * by adding an offset to the returned array location. And some apps
622 * seem to depend on that behaviour.
624 * Mesa's gl_uniform_list doesn't directly support this since each
625 * entry in the list describes one uniform variable, not one uniform
626 * element. We could insert dummy entries in the list for each array
627 * element after [0] but that causes complications elsewhere.
629 * We solve this problem by encoding two values in the location that's
630 * returned by glGetUniformLocation():
631 * a) index into gl_uniform_list::Uniforms[] for the uniform
632 * b) an array/field offset (0 for simple types)
634 * These two values are encoded in the high and low halves of a GLint.
635 * By putting the uniform number in the high part and the offset in the
636 * low part, we can support the unofficial ability to index into arrays
637 * by adding offsets to the location value.
640 merge_location_offset(GLint
*location
, GLint offset
)
642 *location
= (*location
<< 16) | offset
;
647 * Separate the uniform location and parameter offset. See above.
650 split_location_offset(GLint
*location
, GLint
*offset
)
652 *offset
= *location
& 0xffff;
653 *location
= *location
>> 16;
659 * Called via glGetUniformfv().
662 _mesa_get_uniformfv(struct gl_context
*ctx
, GLuint program
, GLint location
,
665 struct gl_program
*prog
;
669 split_location_offset(&location
, &offset
);
671 lookup_uniform_parameter(ctx
, program
, location
, &prog
, ¶mPos
);
674 const struct gl_program_parameter
*p
=
675 &prog
->Parameters
->Parameters
[paramPos
];
676 GLint rows
, cols
, i
, j
, k
;
678 get_uniform_rows_cols(p
, &rows
, &cols
);
681 for (i
= 0; i
< rows
; i
++) {
682 const int base
= paramPos
+ offset
+ i
;
684 for (j
= 0; j
< cols
; j
++ ) {
685 params
[k
++] = prog
->Parameters
->ParameterValues
[base
][j
];
693 * Called via glGetUniformiv().
694 * \sa _mesa_get_uniformfv, only difference is a cast.
697 _mesa_get_uniformiv(struct gl_context
*ctx
, GLuint program
, GLint location
,
700 struct gl_program
*prog
;
704 split_location_offset(&location
, &offset
);
706 lookup_uniform_parameter(ctx
, program
, location
, &prog
, ¶mPos
);
709 const struct gl_program_parameter
*p
=
710 &prog
->Parameters
->Parameters
[paramPos
];
711 GLint rows
, cols
, i
, j
, k
;
713 get_uniform_rows_cols(p
, &rows
, &cols
);
716 for (i
= 0; i
< rows
; i
++) {
717 const int base
= paramPos
+ offset
+ i
;
719 for (j
= 0; j
< cols
; j
++ ) {
720 params
[k
++] = (GLint
) prog
->Parameters
->ParameterValues
[base
][j
];
728 * Called via glGetUniformuiv().
729 * New in GL_EXT_gpu_shader4, OpenGL 3.0
730 * \sa _mesa_get_uniformfv, only difference is a cast.
733 _mesa_get_uniformuiv(struct gl_context
*ctx
, GLuint program
, GLint location
,
736 struct gl_program
*prog
;
740 split_location_offset(&location
, &offset
);
742 lookup_uniform_parameter(ctx
, program
, location
, &prog
, ¶mPos
);
745 const struct gl_program_parameter
*p
=
746 &prog
->Parameters
->Parameters
[paramPos
];
747 GLint rows
, cols
, i
, j
, k
;
749 get_uniform_rows_cols(p
, &rows
, &cols
);
752 for (i
= 0; i
< rows
; i
++) {
753 const int base
= paramPos
+ offset
+ i
;
755 for (j
= 0; j
< cols
; j
++ ) {
756 params
[k
++] = (GLuint
) prog
->Parameters
->ParameterValues
[base
][j
];
764 * Called via glGetUniformLocation().
766 * The return value will encode two values, the uniform location and an
767 * offset (used for arrays, structs).
770 _mesa_get_uniform_location(struct gl_context
*ctx
, struct gl_shader_program
*shProg
,
773 GLint offset
= 0, location
= -1;
775 if (shProg
->LinkStatus
== GL_FALSE
) {
776 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glGetUniformfv(program)");
780 /* XXX we should return -1 if the uniform was declared, but not
784 /* XXX we need to be able to parse uniform names for structs and arrays
791 /* handle 1-dimension arrays here... */
792 char *c
= strchr(name
, '[');
794 /* truncate name at [ */
795 const GLint len
= c
- name
;
796 GLchar
*newName
= malloc(len
+ 1);
798 return -1; /* out of mem */
799 memcpy(newName
, name
, len
);
802 location
= _mesa_lookup_uniform(shProg
->Uniforms
, newName
);
804 const GLint element
= atoi(c
+ 1);
806 /* get type of the uniform array element */
807 struct gl_program_parameter
*p
;
808 p
= get_uniform_parameter(shProg
, location
);
811 get_matrix_dims(p
->DataType
, &rows
, &cols
);
814 offset
= element
* rows
;
824 location
= _mesa_lookup_uniform(shProg
->Uniforms
, name
);
828 merge_location_offset(&location
, offset
);
837 * Update the vertex/fragment program's TexturesUsed array.
839 * This needs to be called after glUniform(set sampler var) is called.
840 * A call to glUniform(samplerVar, value) causes a sampler to point to a
841 * particular texture unit. We know the sampler's texture target
842 * (1D/2D/3D/etc) from compile time but the sampler's texture unit is
843 * set by glUniform() calls.
845 * So, scan the program->SamplerUnits[] and program->SamplerTargets[]
846 * information to update the prog->TexturesUsed[] values.
847 * Each value of TexturesUsed[unit] is one of zero, TEXTURE_1D_INDEX,
848 * TEXTURE_2D_INDEX, TEXTURE_3D_INDEX, etc.
849 * We'll use that info for state validation before rendering.
852 _mesa_update_shader_textures_used(struct gl_program
*prog
)
856 memset(prog
->TexturesUsed
, 0, sizeof(prog
->TexturesUsed
));
858 for (s
= 0; s
< MAX_SAMPLERS
; s
++) {
859 if (prog
->SamplersUsed
& (1 << s
)) {
860 GLuint unit
= prog
->SamplerUnits
[s
];
861 GLuint tgt
= prog
->SamplerTargets
[s
];
862 assert(unit
< MAX_TEXTURE_IMAGE_UNITS
);
863 assert(tgt
< NUM_TEXTURE_TARGETS
);
864 prog
->TexturesUsed
[unit
] |= (1 << tgt
);
871 * Check if the type given by userType is allowed to set a uniform of the
872 * target type. Generally, equivalence is required, but setting Boolean
873 * uniforms can be done with glUniformiv or glUniformfv.
876 compatible_types(GLenum userType
, GLenum targetType
)
878 if (userType
== targetType
)
881 if (targetType
== GL_BOOL
&& (userType
== GL_FLOAT
||
882 userType
== GL_UNSIGNED_INT
||
886 if (targetType
== GL_BOOL_VEC2
&& (userType
== GL_FLOAT_VEC2
||
887 userType
== GL_UNSIGNED_INT_VEC2
||
888 userType
== GL_INT_VEC2
))
891 if (targetType
== GL_BOOL_VEC3
&& (userType
== GL_FLOAT_VEC3
||
892 userType
== GL_UNSIGNED_INT_VEC3
||
893 userType
== GL_INT_VEC3
))
896 if (targetType
== GL_BOOL_VEC4
&& (userType
== GL_FLOAT_VEC4
||
897 userType
== GL_UNSIGNED_INT_VEC4
||
898 userType
== GL_INT_VEC4
))
901 if (is_sampler_type(targetType
) && userType
== GL_INT
)
909 * Set the value of a program's uniform variable.
910 * \param program the program whose uniform to update
911 * \param index the index of the program parameter for the uniform
912 * \param offset additional parameter slot offset (for arrays)
913 * \param type the incoming datatype of 'values'
914 * \param count the number of uniforms to set
915 * \param elems number of elements per uniform (1, 2, 3 or 4)
916 * \param values the new values, of datatype 'type'
919 set_program_uniform(struct gl_context
*ctx
, struct gl_program
*program
,
920 GLint index
, GLint offset
,
921 GLenum type
, GLsizei count
, GLint elems
,
924 const struct gl_program_parameter
*param
=
925 &program
->Parameters
->Parameters
[index
];
931 if (!compatible_types(type
, param
->DataType
)) {
932 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniform(type mismatch)");
936 if (index
+ offset
> (GLint
) program
->Parameters
->Size
) {
941 if (param
->Type
== PROGRAM_SAMPLER
) {
942 /* This controls which texture unit which is used by a sampler */
943 GLboolean changed
= GL_FALSE
;
946 /* this should have been caught by the compatible_types() check */
947 ASSERT(type
== GL_INT
);
949 /* loop over number of samplers to change */
950 for (i
= 0; i
< count
; i
++) {
952 (GLuint
) program
->Parameters
->ParameterValues
[index
+ offset
+ i
][0];
953 GLuint texUnit
= ((GLuint
*) values
)[i
];
955 /* check that the sampler (tex unit index) is legal */
956 if (texUnit
>= ctx
->Const
.MaxTextureImageUnits
) {
957 _mesa_error(ctx
, GL_INVALID_VALUE
,
958 "glUniform1(invalid sampler/tex unit index for '%s')",
963 /* This maps a sampler to a texture unit: */
964 if (sampler
< MAX_SAMPLERS
) {
966 printf("Set program %p sampler %d '%s' to unit %u\n",
967 program
, sampler
, param
->Name
, texUnit
);
969 if (program
->SamplerUnits
[sampler
] != texUnit
) {
970 program
->SamplerUnits
[sampler
] = texUnit
;
977 /* When a sampler's value changes it usually requires rewriting
978 * a GPU program's TEX instructions since there may not be a
979 * sampler->texture lookup table. We signal this with the
980 * ProgramStringNotify() callback.
982 FLUSH_VERTICES(ctx
, _NEW_TEXTURE
| _NEW_PROGRAM
);
983 _mesa_update_shader_textures_used(program
);
984 /* Do we need to care about the return value here?
985 * This should not be the first time the driver was notified of
988 (void) ctx
->Driver
.ProgramStringNotify(ctx
, program
->Target
, program
);
992 /* ordinary uniform variable */
993 const GLboolean isUniformBool
= is_boolean_type(param
->DataType
);
994 const GLenum basicType
= base_uniform_type(type
);
995 const GLint slots
= (param
->Size
+ 3) / 4;
996 const GLint typeSize
= _mesa_sizeof_glsl_type(param
->DataType
);
999 if ((GLint
) param
->Size
> typeSize
) {
1001 /* we'll ignore extra data below */
1004 /* non-array: count must be at most one; count == 0 is handled by the loop below */
1006 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1007 "glUniform(uniform '%s' is not an array)",
1013 /* loop over number of array elements */
1014 for (k
= 0; k
< count
; k
++) {
1015 GLfloat
*uniformVal
;
1017 if (offset
+ k
>= slots
) {
1018 /* Extra array data is ignored */
1022 /* uniformVal (the destination) is always float[4] */
1023 uniformVal
= program
->Parameters
->ParameterValues
[index
+ offset
+ k
];
1025 if (basicType
== GL_INT
) {
1026 /* convert user's ints to floats */
1027 const GLint
*iValues
= ((const GLint
*) values
) + k
* elems
;
1028 for (i
= 0; i
< elems
; i
++) {
1029 uniformVal
[i
] = (GLfloat
) iValues
[i
];
1032 else if (basicType
== GL_UNSIGNED_INT
) {
1033 /* convert user's uints to floats */
1034 const GLuint
*iValues
= ((const GLuint
*) values
) + k
* elems
;
1035 for (i
= 0; i
< elems
; i
++) {
1036 uniformVal
[i
] = (GLfloat
) iValues
[i
];
1040 const GLfloat
*fValues
= ((const GLfloat
*) values
) + k
* elems
;
1041 assert(basicType
== GL_FLOAT
);
1042 for (i
= 0; i
< elems
; i
++) {
1043 uniformVal
[i
] = fValues
[i
];
1047 /* if the uniform is bool-valued, convert to 1.0 or 0.0 */
1048 if (isUniformBool
) {
1049 for (i
= 0; i
< elems
; i
++) {
1050 uniformVal
[i
] = uniformVal
[i
] ? 1.0f
: 0.0f
;
1059 * Called via glUniform*() functions.
1062 _mesa_uniform(struct gl_context
*ctx
, struct gl_shader_program
*shProg
,
1063 GLint location
, GLsizei count
,
1064 const GLvoid
*values
, GLenum type
)
1066 struct gl_uniform
*uniform
;
1067 GLint elems
, offset
;
1069 if (!shProg
|| !shProg
->LinkStatus
) {
1070 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniform(program not linked)");
1075 return; /* The standard specifies this as a no-op */
1077 if (location
< -1) {
1078 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniform(location=%d)",
1083 split_location_offset(&location
, &offset
);
1085 if (location
< 0 || location
>= (GLint
) shProg
->Uniforms
->NumUniforms
) {
1086 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniform(location=%d)", location
);
1091 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniform(count < 0)");
1095 elems
= _mesa_sizeof_glsl_type(type
);
1097 FLUSH_VERTICES(ctx
, _NEW_PROGRAM_CONSTANTS
);
1099 uniform
= &shProg
->Uniforms
->Uniforms
[location
];
1101 if (ctx
->Shader
.Flags
& GLSL_UNIFORMS
) {
1102 const GLenum basicType
= base_uniform_type(type
);
1104 printf("Mesa: set program %u uniform %s (loc %d) to: ",
1105 shProg
->Name
, uniform
->Name
, location
);
1106 if (basicType
== GL_INT
) {
1107 const GLint
*v
= (const GLint
*) values
;
1108 for (i
= 0; i
< count
* elems
; i
++) {
1109 printf("%d ", v
[i
]);
1112 else if (basicType
== GL_UNSIGNED_INT
) {
1113 const GLuint
*v
= (const GLuint
*) values
;
1114 for (i
= 0; i
< count
* elems
; i
++) {
1115 printf("%u ", v
[i
]);
1119 const GLfloat
*v
= (const GLfloat
*) values
;
1120 assert(basicType
== GL_FLOAT
);
1121 for (i
= 0; i
< count
* elems
; i
++) {
1122 printf("%g ", v
[i
]);
1128 /* A uniform var may be used by both a vertex shader and a fragment
1129 * shader. We may need to update one or both shader's uniform here:
1131 if (shProg
->VertexProgram
) {
1132 /* convert uniform location to program parameter index */
1133 GLint index
= uniform
->VertPos
;
1135 set_program_uniform(ctx
, &shProg
->VertexProgram
->Base
,
1136 index
, offset
, type
, count
, elems
, values
);
1140 if (shProg
->FragmentProgram
) {
1141 /* convert uniform location to program parameter index */
1142 GLint index
= uniform
->FragPos
;
1144 set_program_uniform(ctx
, &shProg
->FragmentProgram
->Base
,
1145 index
, offset
, type
, count
, elems
, values
);
1149 if (shProg
->GeometryProgram
) {
1150 /* convert uniform location to program parameter index */
1151 GLint index
= uniform
->GeomPos
;
1153 set_program_uniform(ctx
, &shProg
->GeometryProgram
->Base
,
1154 index
, offset
, type
, count
, elems
, values
);
1158 uniform
->Initialized
= GL_TRUE
;
1163 * Set a matrix-valued program parameter.
1166 set_program_uniform_matrix(struct gl_context
*ctx
, struct gl_program
*program
,
1167 GLuint index
, GLuint offset
,
1168 GLuint count
, GLuint rows
, GLuint cols
,
1169 GLboolean transpose
, const GLfloat
*values
)
1171 GLuint mat
, row
, col
;
1173 const struct gl_program_parameter
* param
= &program
->Parameters
->Parameters
[index
];
1174 const GLuint slots
= (param
->Size
+ 3) / 4;
1175 const GLint typeSize
= _mesa_sizeof_glsl_type(param
->DataType
);
1178 /* check that the number of rows, columns is correct */
1179 get_matrix_dims(param
->DataType
, &nr
, &nc
);
1180 if (rows
!= nr
|| cols
!= nc
) {
1181 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1182 "glUniformMatrix(matrix size mismatch)");
1186 if ((GLint
) param
->Size
<= typeSize
) {
1187 /* non-array: count must be at most one; count == 0 is handled by the loop below */
1189 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1190 "glUniformMatrix(uniform is not an array)");
1196 * Note: the _columns_ of a matrix are stored in program registers, not
1197 * the rows. So, the loops below look a little funny.
1198 * XXX could optimize this a bit...
1201 /* loop over matrices */
1202 for (mat
= 0; mat
< count
; mat
++) {
1205 for (col
= 0; col
< cols
; col
++) {
1207 if (offset
>= slots
) {
1208 /* Ignore writes beyond the end of (the used part of) an array */
1211 v
= program
->Parameters
->ParameterValues
[index
+ offset
];
1212 for (row
= 0; row
< rows
; row
++) {
1214 v
[row
] = values
[src
+ row
* cols
+ col
];
1217 v
[row
] = values
[src
+ col
* rows
+ row
];
1224 src
+= rows
* cols
; /* next matrix */
1230 * Called by glUniformMatrix*() functions.
1231 * Note: cols=2, rows=4 ==> array[2] of vec4
1234 _mesa_uniform_matrix(struct gl_context
*ctx
, struct gl_shader_program
*shProg
,
1235 GLint cols
, GLint rows
,
1236 GLint location
, GLsizei count
,
1237 GLboolean transpose
, const GLfloat
*values
)
1239 struct gl_uniform
*uniform
;
1242 if (!shProg
|| !shProg
->LinkStatus
) {
1243 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1244 "glUniformMatrix(program not linked)");
1249 return; /* The standard specifies this as a no-op */
1251 if (location
< -1) {
1252 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniformMatrix(location)");
1256 split_location_offset(&location
, &offset
);
1258 if (location
< 0 || location
>= (GLint
) shProg
->Uniforms
->NumUniforms
) {
1259 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniformMatrix(location)");
1262 if (values
== NULL
) {
1263 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniformMatrix");
1267 FLUSH_VERTICES(ctx
, _NEW_PROGRAM_CONSTANTS
);
1269 uniform
= &shProg
->Uniforms
->Uniforms
[location
];
1271 if (shProg
->VertexProgram
) {
1272 /* convert uniform location to program parameter index */
1273 GLint index
= uniform
->VertPos
;
1275 set_program_uniform_matrix(ctx
, &shProg
->VertexProgram
->Base
,
1277 count
, rows
, cols
, transpose
, values
);
1281 if (shProg
->FragmentProgram
) {
1282 /* convert uniform location to program parameter index */
1283 GLint index
= uniform
->FragPos
;
1285 set_program_uniform_matrix(ctx
, &shProg
->FragmentProgram
->Base
,
1287 count
, rows
, cols
, transpose
, values
);
1291 if (shProg
->GeometryProgram
) {
1292 /* convert uniform location to program parameter index */
1293 GLint index
= uniform
->GeomPos
;
1295 set_program_uniform_matrix(ctx
, &shProg
->GeometryProgram
->Base
,
1297 count
, rows
, cols
, transpose
, values
);
1301 uniform
->Initialized
= GL_TRUE
;
1306 _mesa_Uniform1fARB(GLint location
, GLfloat v0
)
1308 GET_CURRENT_CONTEXT(ctx
);
1309 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, &v0
, GL_FLOAT
);
1313 _mesa_Uniform2fARB(GLint location
, GLfloat v0
, GLfloat v1
)
1315 GET_CURRENT_CONTEXT(ctx
);
1319 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_FLOAT_VEC2
);
1323 _mesa_Uniform3fARB(GLint location
, GLfloat v0
, GLfloat v1
, GLfloat v2
)
1325 GET_CURRENT_CONTEXT(ctx
);
1330 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_FLOAT_VEC3
);
1334 _mesa_Uniform4fARB(GLint location
, GLfloat v0
, GLfloat v1
, GLfloat v2
,
1337 GET_CURRENT_CONTEXT(ctx
);
1343 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_FLOAT_VEC4
);
1347 _mesa_Uniform1iARB(GLint location
, GLint v0
)
1349 GET_CURRENT_CONTEXT(ctx
);
1350 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, &v0
, GL_INT
);
1354 _mesa_Uniform2iARB(GLint location
, GLint v0
, GLint v1
)
1356 GET_CURRENT_CONTEXT(ctx
);
1360 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_INT_VEC2
);
1364 _mesa_Uniform3iARB(GLint location
, GLint v0
, GLint v1
, GLint v2
)
1366 GET_CURRENT_CONTEXT(ctx
);
1371 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_INT_VEC3
);
1375 _mesa_Uniform4iARB(GLint location
, GLint v0
, GLint v1
, GLint v2
, GLint v3
)
1377 GET_CURRENT_CONTEXT(ctx
);
1383 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_INT_VEC4
);
1387 _mesa_Uniform1fvARB(GLint location
, GLsizei count
, const GLfloat
* value
)
1389 GET_CURRENT_CONTEXT(ctx
);
1390 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_FLOAT
);
1394 _mesa_Uniform2fvARB(GLint location
, GLsizei count
, const GLfloat
* value
)
1396 GET_CURRENT_CONTEXT(ctx
);
1397 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_FLOAT_VEC2
);
1401 _mesa_Uniform3fvARB(GLint location
, GLsizei count
, const GLfloat
* value
)
1403 GET_CURRENT_CONTEXT(ctx
);
1404 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_FLOAT_VEC3
);
1408 _mesa_Uniform4fvARB(GLint location
, GLsizei count
, const GLfloat
* value
)
1410 GET_CURRENT_CONTEXT(ctx
);
1411 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_FLOAT_VEC4
);
1415 _mesa_Uniform1ivARB(GLint location
, GLsizei count
, const GLint
* value
)
1417 GET_CURRENT_CONTEXT(ctx
);
1418 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_INT
);
1422 _mesa_Uniform2ivARB(GLint location
, GLsizei count
, const GLint
* value
)
1424 GET_CURRENT_CONTEXT(ctx
);
1425 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_INT_VEC2
);
1429 _mesa_Uniform3ivARB(GLint location
, GLsizei count
, const GLint
* value
)
1431 GET_CURRENT_CONTEXT(ctx
);
1432 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_INT_VEC3
);
1436 _mesa_Uniform4ivARB(GLint location
, GLsizei count
, const GLint
* value
)
1438 GET_CURRENT_CONTEXT(ctx
);
1439 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_INT_VEC4
);
1443 /** OpenGL 3.0 GLuint-valued functions **/
1445 _mesa_Uniform1ui(GLint location
, GLuint v0
)
1447 GET_CURRENT_CONTEXT(ctx
);
1448 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, &v0
, GL_UNSIGNED_INT
);
1452 _mesa_Uniform2ui(GLint location
, GLuint v0
, GLuint v1
)
1454 GET_CURRENT_CONTEXT(ctx
);
1458 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_UNSIGNED_INT_VEC2
);
1462 _mesa_Uniform3ui(GLint location
, GLuint v0
, GLuint v1
, GLuint v2
)
1464 GET_CURRENT_CONTEXT(ctx
);
1469 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_UNSIGNED_INT_VEC3
);
1473 _mesa_Uniform4ui(GLint location
, GLuint v0
, GLuint v1
, GLuint v2
, GLuint v3
)
1475 GET_CURRENT_CONTEXT(ctx
);
1481 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, 1, v
, GL_UNSIGNED_INT_VEC4
);
1485 _mesa_Uniform1uiv(GLint location
, GLsizei count
, const GLuint
*value
)
1487 GET_CURRENT_CONTEXT(ctx
);
1488 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_UNSIGNED_INT
);
1492 _mesa_Uniform2uiv(GLint location
, GLsizei count
, const GLuint
*value
)
1494 GET_CURRENT_CONTEXT(ctx
);
1495 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_UNSIGNED_INT_VEC2
);
1499 _mesa_Uniform3uiv(GLint location
, GLsizei count
, const GLuint
*value
)
1501 GET_CURRENT_CONTEXT(ctx
);
1502 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_UNSIGNED_INT_VEC3
);
1506 _mesa_Uniform4uiv(GLint location
, GLsizei count
, const GLuint
*value
)
1508 GET_CURRENT_CONTEXT(ctx
);
1509 _mesa_uniform(ctx
, ctx
->Shader
.ActiveProgram
, location
, count
, value
, GL_UNSIGNED_INT_VEC4
);
1515 _mesa_UniformMatrix2fvARB(GLint location
, GLsizei count
, GLboolean transpose
,
1516 const GLfloat
* value
)
1518 GET_CURRENT_CONTEXT(ctx
);
1519 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1520 2, 2, location
, count
, transpose
, value
);
1524 _mesa_UniformMatrix3fvARB(GLint location
, GLsizei count
, GLboolean transpose
,
1525 const GLfloat
* value
)
1527 GET_CURRENT_CONTEXT(ctx
);
1528 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1529 3, 3, location
, count
, transpose
, value
);
1533 _mesa_UniformMatrix4fvARB(GLint location
, GLsizei count
, GLboolean transpose
,
1534 const GLfloat
* value
)
1536 GET_CURRENT_CONTEXT(ctx
);
1537 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1538 4, 4, location
, count
, transpose
, value
);
1543 * Non-square UniformMatrix are OpenGL 2.1
1546 _mesa_UniformMatrix2x3fv(GLint location
, GLsizei count
, GLboolean transpose
,
1547 const GLfloat
*value
)
1549 GET_CURRENT_CONTEXT(ctx
);
1550 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1551 2, 3, location
, count
, transpose
, value
);
1555 _mesa_UniformMatrix3x2fv(GLint location
, GLsizei count
, GLboolean transpose
,
1556 const GLfloat
*value
)
1558 GET_CURRENT_CONTEXT(ctx
);
1559 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1560 3, 2, location
, count
, transpose
, value
);
1564 _mesa_UniformMatrix2x4fv(GLint location
, GLsizei count
, GLboolean transpose
,
1565 const GLfloat
*value
)
1567 GET_CURRENT_CONTEXT(ctx
);
1568 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1569 2, 4, location
, count
, transpose
, value
);
1573 _mesa_UniformMatrix4x2fv(GLint location
, GLsizei count
, GLboolean transpose
,
1574 const GLfloat
*value
)
1576 GET_CURRENT_CONTEXT(ctx
);
1577 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1578 4, 2, location
, count
, transpose
, value
);
1582 _mesa_UniformMatrix3x4fv(GLint location
, GLsizei count
, GLboolean transpose
,
1583 const GLfloat
*value
)
1585 GET_CURRENT_CONTEXT(ctx
);
1586 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1587 3, 4, location
, count
, transpose
, value
);
1591 _mesa_UniformMatrix4x3fv(GLint location
, GLsizei count
, GLboolean transpose
,
1592 const GLfloat
*value
)
1594 GET_CURRENT_CONTEXT(ctx
);
1595 _mesa_uniform_matrix(ctx
, ctx
->Shader
.ActiveProgram
,
1596 4, 3, location
, count
, transpose
, value
);
1601 _mesa_GetUniformfvARB(GLhandleARB program
, GLint location
, GLfloat
*params
)
1603 GET_CURRENT_CONTEXT(ctx
);
1604 _mesa_get_uniformfv(ctx
, program
, location
, params
);
1609 _mesa_GetUniformivARB(GLhandleARB program
, GLint location
, GLint
*params
)
1611 GET_CURRENT_CONTEXT(ctx
);
1612 _mesa_get_uniformiv(ctx
, program
, location
, params
);
1618 _mesa_GetUniformuiv(GLhandleARB program
, GLint location
, GLuint
*params
)
1620 GET_CURRENT_CONTEXT(ctx
);
1621 _mesa_get_uniformuiv(ctx
, program
, location
, params
);
1627 _mesa_GetUniformLocationARB(GLhandleARB programObj
, const GLcharARB
*name
)
1629 struct gl_shader_program
*shProg
;
1631 GET_CURRENT_CONTEXT(ctx
);
1633 shProg
= _mesa_lookup_shader_program_err(ctx
, programObj
,
1634 "glGetUniformLocation");
1638 return _mesa_get_uniform_location(ctx
, shProg
, name
);
1643 _mesa_GetActiveUniformARB(GLhandleARB program
, GLuint index
,
1644 GLsizei maxLength
, GLsizei
* length
, GLint
* size
,
1645 GLenum
* type
, GLcharARB
* name
)
1647 GET_CURRENT_CONTEXT(ctx
);
1648 _mesa_get_active_uniform(ctx
, program
, index
, maxLength
, length
, size
,
1654 * Plug in shader uniform-related functions into API dispatch table.
1657 _mesa_init_shader_uniform_dispatch(struct _glapi_table
*exec
)
1660 SET_Uniform1fARB(exec
, _mesa_Uniform1fARB
);
1661 SET_Uniform2fARB(exec
, _mesa_Uniform2fARB
);
1662 SET_Uniform3fARB(exec
, _mesa_Uniform3fARB
);
1663 SET_Uniform4fARB(exec
, _mesa_Uniform4fARB
);
1664 SET_Uniform1iARB(exec
, _mesa_Uniform1iARB
);
1665 SET_Uniform2iARB(exec
, _mesa_Uniform2iARB
);
1666 SET_Uniform3iARB(exec
, _mesa_Uniform3iARB
);
1667 SET_Uniform4iARB(exec
, _mesa_Uniform4iARB
);
1668 SET_Uniform1fvARB(exec
, _mesa_Uniform1fvARB
);
1669 SET_Uniform2fvARB(exec
, _mesa_Uniform2fvARB
);
1670 SET_Uniform3fvARB(exec
, _mesa_Uniform3fvARB
);
1671 SET_Uniform4fvARB(exec
, _mesa_Uniform4fvARB
);
1672 SET_Uniform1ivARB(exec
, _mesa_Uniform1ivARB
);
1673 SET_Uniform2ivARB(exec
, _mesa_Uniform2ivARB
);
1674 SET_Uniform3ivARB(exec
, _mesa_Uniform3ivARB
);
1675 SET_Uniform4ivARB(exec
, _mesa_Uniform4ivARB
);
1676 SET_UniformMatrix2fvARB(exec
, _mesa_UniformMatrix2fvARB
);
1677 SET_UniformMatrix3fvARB(exec
, _mesa_UniformMatrix3fvARB
);
1678 SET_UniformMatrix4fvARB(exec
, _mesa_UniformMatrix4fvARB
);
1680 SET_GetActiveUniformARB(exec
, _mesa_GetActiveUniformARB
);
1681 SET_GetUniformLocationARB(exec
, _mesa_GetUniformLocationARB
);
1682 SET_GetUniformfvARB(exec
, _mesa_GetUniformfvARB
);
1683 SET_GetUniformivARB(exec
, _mesa_GetUniformivARB
);
1686 SET_UniformMatrix2x3fv(exec
, _mesa_UniformMatrix2x3fv
);
1687 SET_UniformMatrix3x2fv(exec
, _mesa_UniformMatrix3x2fv
);
1688 SET_UniformMatrix2x4fv(exec
, _mesa_UniformMatrix2x4fv
);
1689 SET_UniformMatrix4x2fv(exec
, _mesa_UniformMatrix4x2fv
);
1690 SET_UniformMatrix3x4fv(exec
, _mesa_UniformMatrix3x4fv
);
1691 SET_UniformMatrix4x3fv(exec
, _mesa_UniformMatrix4x3fv
);
1694 /* XXX finish dispatch */
1695 SET_Uniform1uiEXT(exec
, _mesa_Uniform1ui
);
1696 SET_Uniform2uiEXT(exec
, _mesa_Uniform2ui
);
1697 SET_Uniform3uiEXT(exec
, _mesa_Uniform3ui
);
1698 SET_Uniform4uiEXT(exec
, _mesa_Uniform4ui
);
1699 SET_Uniform1uivEXT(exec
, _mesa_Uniform1uiv
);
1700 SET_Uniform2uivEXT(exec
, _mesa_Uniform2uiv
);
1701 SET_Uniform3uivEXT(exec
, _mesa_Uniform3uiv
);
1702 SET_Uniform4uivEXT(exec
, _mesa_Uniform4uiv
);
1703 SET_GetUniformuivEXT(exec
, _mesa_GetUniformuiv
);
1706 #endif /* FEATURE_GL */