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.
7 * Permission is hereby granted, free of charge, to any person obtaining a
8 * copy of this software and associated documentation files (the "Software"),
9 * to deal in the Software without restriction, including without limitation
10 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
11 * and/or sell copies of the Software, and to permit persons to whom the
12 * Software is furnished to do so, subject to the following conditions:
14 * The above copyright notice and this permission notice shall be included
15 * in all copies or substantial portions of the Software.
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
20 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
21 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 * Implementation of GLSL-related API functions.
30 * The glUniform* functions are in uniforms.c
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/enums.h"
43 #include "main/hash.h"
44 #include "main/mfeatures.h"
45 #include "main/mtypes.h"
46 #include "main/shaderapi.h"
47 #include "main/shaderobj.h"
48 #include "main/uniforms.h"
49 #include "program/program.h"
50 #include "program/prog_parameter.h"
53 #include "../glsl/glsl_parser_extras.h"
54 #include "../glsl/ir_uniform.h"
56 /** Define this to enable shader substitution (see below) */
57 #define SHADER_SUBST 0
61 * Return mask of GLSL_x flags by examining the MESA_GLSL env var.
64 get_shader_flags(void)
66 GLbitfield flags
= 0x0;
67 const char *env
= _mesa_getenv("MESA_GLSL");
70 if (strstr(env
, "dump"))
72 if (strstr(env
, "log"))
74 if (strstr(env
, "nopvert"))
75 flags
|= GLSL_NOP_VERT
;
76 if (strstr(env
, "nopfrag"))
77 flags
|= GLSL_NOP_FRAG
;
78 if (strstr(env
, "nopt"))
80 else if (strstr(env
, "opt"))
82 if (strstr(env
, "uniform"))
83 flags
|= GLSL_UNIFORMS
;
84 if (strstr(env
, "useprog"))
85 flags
|= GLSL_USE_PROG
;
86 if (strstr(env
, "errors"))
87 flags
|= GLSL_REPORT_ERRORS
;
95 * Initialize context's shader state.
98 _mesa_init_shader_state(struct gl_context
*ctx
)
100 /* Device drivers may override these to control what kind of instructions
101 * are generated by the GLSL compiler.
103 struct gl_shader_compiler_options options
;
106 memset(&options
, 0, sizeof(options
));
107 options
.MaxUnrollIterations
= 32;
109 /* Default pragma settings */
110 options
.DefaultPragmas
.Optimize
= GL_TRUE
;
112 for (sh
= 0; sh
< MESA_SHADER_TYPES
; ++sh
)
113 memcpy(&ctx
->ShaderCompilerOptions
[sh
], &options
, sizeof(options
));
115 ctx
->Shader
.Flags
= get_shader_flags();
120 * Free the per-context shader-related state.
123 _mesa_free_shader_state(struct gl_context
*ctx
)
125 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentVertexProgram
, NULL
);
126 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentGeometryProgram
,
128 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentFragmentProgram
,
130 _mesa_reference_shader_program(ctx
, &ctx
->Shader
._CurrentFragmentProgram
,
132 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.ActiveProgram
, NULL
);
137 * Copy string from <src> to <dst>, up to maxLength characters, returning
138 * length of <dst> in <length>.
139 * \param src the strings source
140 * \param maxLength max chars to copy
141 * \param length returns number of chars copied
142 * \param dst the string destination
145 _mesa_copy_string(GLchar
*dst
, GLsizei maxLength
,
146 GLsizei
*length
, const GLchar
*src
)
149 for (len
= 0; len
< maxLength
- 1 && src
&& src
[len
]; len
++)
160 * Confirm that the a shader type is valid and supported by the implementation
162 * \param ctx Current GL context
163 * \param type Shader target
167 validate_shader_target(const struct gl_context
*ctx
, GLenum type
)
170 #if FEATURE_ARB_fragment_shader
171 case GL_FRAGMENT_SHADER
:
172 return ctx
->Extensions
.ARB_fragment_shader
;
174 #if FEATURE_ARB_vertex_shader
175 case GL_VERTEX_SHADER
:
176 return ctx
->Extensions
.ARB_vertex_shader
;
178 #if FEATURE_ARB_geometry_shader4
179 case GL_GEOMETRY_SHADER_ARB
:
180 return ctx
->Extensions
.ARB_geometry_shader4
;
189 * Find the length of the longest transform feedback varying name
190 * which was specified with glTransformFeedbackVaryings().
193 longest_feedback_varying_name(const struct gl_shader_program
*shProg
)
197 for (i
= 0; i
< shProg
->TransformFeedback
.NumVarying
; i
++) {
198 GLint len
= strlen(shProg
->TransformFeedback
.VaryingNames
[i
]);
208 is_program(struct gl_context
*ctx
, GLuint name
)
210 struct gl_shader_program
*shProg
= _mesa_lookup_shader_program(ctx
, name
);
211 return shProg
? GL_TRUE
: GL_FALSE
;
216 is_shader(struct gl_context
*ctx
, GLuint name
)
218 struct gl_shader
*shader
= _mesa_lookup_shader(ctx
, name
);
219 return shader
? GL_TRUE
: GL_FALSE
;
224 * Attach shader to a shader program.
227 attach_shader(struct gl_context
*ctx
, GLuint program
, GLuint shader
)
229 struct gl_shader_program
*shProg
;
230 struct gl_shader
*sh
;
233 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glAttachShader");
237 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glAttachShader");
242 n
= shProg
->NumShaders
;
243 for (i
= 0; i
< n
; i
++) {
244 if (shProg
->Shaders
[i
] == sh
) {
245 /* The shader is already attched to this program. The
246 * GL_ARB_shader_objects spec says:
248 * "The error INVALID_OPERATION is generated by AttachObjectARB
249 * if <obj> is already attached to <containerObj>."
251 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glAttachShader");
257 shProg
->Shaders
= (struct gl_shader
**)
258 _mesa_realloc(shProg
->Shaders
,
259 n
* sizeof(struct gl_shader
*),
260 (n
+ 1) * sizeof(struct gl_shader
*));
261 if (!shProg
->Shaders
) {
262 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glAttachShader");
267 shProg
->Shaders
[n
] = NULL
; /* since realloc() didn't zero the new space */
268 _mesa_reference_shader(ctx
, &shProg
->Shaders
[n
], sh
);
269 shProg
->NumShaders
++;
274 create_shader(struct gl_context
*ctx
, GLenum type
)
276 struct gl_shader
*sh
;
279 if (!validate_shader_target(ctx
, type
)) {
280 _mesa_error(ctx
, GL_INVALID_ENUM
, "CreateShader(type)");
284 name
= _mesa_HashFindFreeKeyBlock(ctx
->Shared
->ShaderObjects
, 1);
285 sh
= ctx
->Driver
.NewShader(ctx
, name
, type
);
286 _mesa_HashInsert(ctx
->Shared
->ShaderObjects
, name
, sh
);
293 create_shader_program(struct gl_context
*ctx
)
296 struct gl_shader_program
*shProg
;
298 name
= _mesa_HashFindFreeKeyBlock(ctx
->Shared
->ShaderObjects
, 1);
300 shProg
= ctx
->Driver
.NewShaderProgram(ctx
, name
);
302 _mesa_HashInsert(ctx
->Shared
->ShaderObjects
, name
, shProg
);
304 assert(shProg
->RefCount
== 1);
311 * Named w/ "2" to indicate OpenGL 2.x vs GL_ARB_fragment_programs's
315 delete_shader_program(struct gl_context
*ctx
, GLuint name
)
318 * NOTE: deleting shaders/programs works a bit differently than
319 * texture objects (and buffer objects, etc). Shader/program
320 * handles/IDs exist in the hash table until the object is really
321 * deleted (refcount==0). With texture objects, the handle/ID is
322 * removed from the hash table in glDeleteTextures() while the tex
323 * object itself might linger until its refcount goes to zero.
325 struct gl_shader_program
*shProg
;
327 shProg
= _mesa_lookup_shader_program_err(ctx
, name
, "glDeleteProgram");
331 if (!shProg
->DeletePending
) {
332 shProg
->DeletePending
= GL_TRUE
;
334 /* effectively, decr shProg's refcount */
335 _mesa_reference_shader_program(ctx
, &shProg
, NULL
);
341 delete_shader(struct gl_context
*ctx
, GLuint shader
)
343 struct gl_shader
*sh
;
345 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glDeleteShader");
349 if (!sh
->DeletePending
) {
350 sh
->DeletePending
= GL_TRUE
;
352 /* effectively, decr sh's refcount */
353 _mesa_reference_shader(ctx
, &sh
, NULL
);
359 detach_shader(struct gl_context
*ctx
, GLuint program
, GLuint shader
)
361 struct gl_shader_program
*shProg
;
365 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glDetachShader");
369 n
= shProg
->NumShaders
;
371 for (i
= 0; i
< n
; i
++) {
372 if (shProg
->Shaders
[i
]->Name
== shader
) {
374 struct gl_shader
**newList
;
377 _mesa_reference_shader(ctx
, &shProg
->Shaders
[i
], NULL
);
379 /* alloc new, smaller array */
380 newList
= (struct gl_shader
**)
381 malloc((n
- 1) * sizeof(struct gl_shader
*));
383 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glDetachShader");
386 for (j
= 0; j
< i
; j
++) {
387 newList
[j
] = shProg
->Shaders
[j
];
390 newList
[j
++] = shProg
->Shaders
[i
];
391 free(shProg
->Shaders
);
393 shProg
->Shaders
= newList
;
394 shProg
->NumShaders
= n
- 1;
399 for (j
= 0; j
< shProg
->NumShaders
; j
++) {
400 assert(shProg
->Shaders
[j
]->Type
== GL_VERTEX_SHADER
||
401 shProg
->Shaders
[j
]->Type
== GL_FRAGMENT_SHADER
);
402 assert(shProg
->Shaders
[j
]->RefCount
> 0);
414 if (is_shader(ctx
, shader
))
415 err
= GL_INVALID_OPERATION
;
416 else if (is_program(ctx
, shader
))
417 err
= GL_INVALID_OPERATION
;
419 err
= GL_INVALID_VALUE
;
420 _mesa_error(ctx
, err
, "glDetachProgram(shader)");
427 * Return list of shaders attached to shader program.
430 get_attached_shaders(struct gl_context
*ctx
, GLuint program
, GLsizei maxCount
,
431 GLsizei
*count
, GLuint
*obj
)
433 struct gl_shader_program
*shProg
=
434 _mesa_lookup_shader_program_err(ctx
, program
, "glGetAttachedShaders");
437 for (i
= 0; i
< (GLuint
) maxCount
&& i
< shProg
->NumShaders
; i
++) {
438 obj
[i
] = shProg
->Shaders
[i
]->Name
;
447 * glGetHandleARB() - return ID/name of currently bound shader program.
450 get_handle(struct gl_context
*ctx
, GLenum pname
)
452 if (pname
== GL_PROGRAM_OBJECT_ARB
) {
453 if (ctx
->Shader
.ActiveProgram
)
454 return ctx
->Shader
.ActiveProgram
->Name
;
459 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetHandleARB");
466 * glGetProgramiv() - get shader program state.
467 * Note that this is for GLSL shader programs, not ARB vertex/fragment
468 * programs (see glGetProgramivARB).
471 get_programiv(struct gl_context
*ctx
, GLuint program
, GLenum pname
, GLint
*params
)
473 struct gl_shader_program
*shProg
474 = _mesa_lookup_shader_program(ctx
, program
);
477 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramiv(program)");
482 case GL_DELETE_STATUS
:
483 *params
= shProg
->DeletePending
;
486 *params
= shProg
->LinkStatus
;
488 case GL_VALIDATE_STATUS
:
489 *params
= shProg
->Validated
;
491 case GL_INFO_LOG_LENGTH
:
492 *params
= shProg
->InfoLog
? strlen(shProg
->InfoLog
) + 1 : 0;
494 case GL_ATTACHED_SHADERS
:
495 *params
= shProg
->NumShaders
;
497 case GL_ACTIVE_ATTRIBUTES
:
498 *params
= _mesa_count_active_attribs(shProg
);
500 case GL_ACTIVE_ATTRIBUTE_MAX_LENGTH
:
501 *params
= _mesa_longest_attribute_name_length(shProg
);
503 case GL_ACTIVE_UNIFORMS
:
504 *params
= shProg
->NumUserUniformStorage
;
506 case GL_ACTIVE_UNIFORM_MAX_LENGTH
: {
510 for (i
= 0; i
< shProg
->NumUserUniformStorage
; i
++) {
511 /* Add one for the terminating NUL character.
513 const GLint len
= strlen(shProg
->UniformStorage
[i
].name
) + 1;
522 case GL_PROGRAM_BINARY_LENGTH_OES
:
525 #if FEATURE_EXT_transform_feedback
526 case GL_TRANSFORM_FEEDBACK_VARYINGS
:
527 *params
= shProg
->TransformFeedback
.NumVarying
;
529 case GL_TRANSFORM_FEEDBACK_VARYING_MAX_LENGTH
:
530 *params
= longest_feedback_varying_name(shProg
) + 1;
532 case GL_TRANSFORM_FEEDBACK_BUFFER_MODE
:
533 *params
= shProg
->TransformFeedback
.BufferMode
;
536 #if FEATURE_ARB_geometry_shader4
537 case GL_GEOMETRY_VERTICES_OUT_ARB
:
538 *params
= shProg
->Geom
.VerticesOut
;
540 case GL_GEOMETRY_INPUT_TYPE_ARB
:
541 *params
= shProg
->Geom
.InputType
;
543 case GL_GEOMETRY_OUTPUT_TYPE_ARB
:
544 *params
= shProg
->Geom
.OutputType
;
548 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetProgramiv(pname)");
555 * glGetShaderiv() - get GLSL shader state
558 get_shaderiv(struct gl_context
*ctx
, GLuint name
, GLenum pname
, GLint
*params
)
560 struct gl_shader
*shader
=
561 _mesa_lookup_shader_err(ctx
, name
, "glGetShaderiv");
569 *params
= shader
->Type
;
571 case GL_DELETE_STATUS
:
572 *params
= shader
->DeletePending
;
574 case GL_COMPILE_STATUS
:
575 *params
= shader
->CompileStatus
;
577 case GL_INFO_LOG_LENGTH
:
578 *params
= shader
->InfoLog
? strlen(shader
->InfoLog
) + 1 : 0;
580 case GL_SHADER_SOURCE_LENGTH
:
581 *params
= shader
->Source
? strlen((char *) shader
->Source
) + 1 : 0;
584 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetShaderiv(pname)");
591 get_program_info_log(struct gl_context
*ctx
, GLuint program
, GLsizei bufSize
,
592 GLsizei
*length
, GLchar
*infoLog
)
594 struct gl_shader_program
*shProg
595 = _mesa_lookup_shader_program(ctx
, program
);
597 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramInfoLog(program)");
600 _mesa_copy_string(infoLog
, bufSize
, length
, shProg
->InfoLog
);
605 get_shader_info_log(struct gl_context
*ctx
, GLuint shader
, GLsizei bufSize
,
606 GLsizei
*length
, GLchar
*infoLog
)
608 struct gl_shader
*sh
= _mesa_lookup_shader(ctx
, shader
);
610 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetShaderInfoLog(shader)");
613 _mesa_copy_string(infoLog
, bufSize
, length
, sh
->InfoLog
);
618 * Return shader source code.
621 get_shader_source(struct gl_context
*ctx
, GLuint shader
, GLsizei maxLength
,
622 GLsizei
*length
, GLchar
*sourceOut
)
624 struct gl_shader
*sh
;
625 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glGetShaderSource");
629 _mesa_copy_string(sourceOut
, maxLength
, length
, sh
->Source
);
634 * Set/replace shader source code. A helper function used by
635 * glShaderSource[ARB] and glCreateShaderProgramEXT.
638 shader_source(struct gl_context
*ctx
, GLuint shader
, const GLchar
*source
)
640 struct gl_shader
*sh
;
642 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glShaderSource");
646 /* free old shader source string and install new one */
648 free((void *) sh
->Source
);
651 sh
->CompileStatus
= GL_FALSE
;
653 sh
->SourceChecksum
= _mesa_str_checksum(sh
->Source
);
662 compile_shader(struct gl_context
*ctx
, GLuint shaderObj
)
664 struct gl_shader
*sh
;
665 struct gl_shader_compiler_options
*options
;
667 sh
= _mesa_lookup_shader_err(ctx
, shaderObj
, "glCompileShader");
671 options
= &ctx
->ShaderCompilerOptions
[_mesa_shader_type_to_index(sh
->Type
)];
673 /* set default pragma state for shader */
674 sh
->Pragmas
= options
->DefaultPragmas
;
676 /* this call will set the sh->CompileStatus field to indicate if
677 * compilation was successful.
679 _mesa_glsl_compile_shader(ctx
, sh
);
681 if (sh
->CompileStatus
== GL_FALSE
&&
682 (ctx
->Shader
.Flags
& GLSL_REPORT_ERRORS
)) {
683 _mesa_debug(ctx
, "Error compiling shader %u:\n%s\n",
684 sh
->Name
, sh
->InfoLog
);
690 * Link a program's shaders.
693 link_program(struct gl_context
*ctx
, GLuint program
)
695 struct gl_shader_program
*shProg
;
696 struct gl_transform_feedback_object
*obj
=
697 ctx
->TransformFeedback
.CurrentObject
;
699 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glLinkProgram");
704 && (shProg
== ctx
->Shader
.CurrentVertexProgram
705 || shProg
== ctx
->Shader
.CurrentGeometryProgram
706 || shProg
== ctx
->Shader
.CurrentFragmentProgram
)) {
707 _mesa_error(ctx
, GL_INVALID_OPERATION
,
708 "glLinkProgram(transform feedback active)");
712 FLUSH_VERTICES(ctx
, _NEW_PROGRAM
);
714 _mesa_glsl_link_shader(ctx
, shProg
);
716 if (shProg
->LinkStatus
== GL_FALSE
&&
717 (ctx
->Shader
.Flags
& GLSL_REPORT_ERRORS
)) {
718 _mesa_debug(ctx
, "Error linking program %u:\n%s\n",
719 shProg
->Name
, shProg
->InfoLog
);
726 printf("Link %u shaders in program %u: %s\n",
727 shProg
->NumShaders
, shProg
->Name
,
728 shProg
->LinkStatus
? "Success" : "Failed");
730 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
731 printf(" shader %u, type 0x%x\n",
732 shProg
->Shaders
[i
]->Name
,
733 shProg
->Shaders
[i
]->Type
);
740 * Print basic shader info (for debug).
743 print_shader_info(const struct gl_shader_program
*shProg
)
747 printf("Mesa: glUseProgram(%u)\n", shProg
->Name
);
748 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
750 switch (shProg
->Shaders
[i
]->Type
) {
751 case GL_VERTEX_SHADER
:
754 case GL_FRAGMENT_SHADER
:
757 case GL_GEOMETRY_SHADER
:
763 printf(" %s shader %u, checksum %u\n", s
,
764 shProg
->Shaders
[i
]->Name
,
765 shProg
->Shaders
[i
]->SourceChecksum
);
767 if (shProg
->_LinkedShaders
[MESA_SHADER_VERTEX
])
768 printf(" vert prog %u\n",
769 shProg
->_LinkedShaders
[MESA_SHADER_VERTEX
]->Program
->Id
);
770 if (shProg
->_LinkedShaders
[MESA_SHADER_FRAGMENT
])
771 printf(" frag prog %u\n",
772 shProg
->_LinkedShaders
[MESA_SHADER_FRAGMENT
]->Program
->Id
);
773 if (shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
])
774 printf(" geom prog %u\n",
775 shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
]->Program
->Id
);
780 * Use the named shader program for subsequent glUniform calls
783 _mesa_active_program(struct gl_context
*ctx
, struct gl_shader_program
*shProg
,
786 if ((shProg
!= NULL
) && !shProg
->LinkStatus
) {
787 _mesa_error(ctx
, GL_INVALID_OPERATION
,
788 "%s(program %u not linked)", caller
, shProg
->Name
);
792 if (ctx
->Shader
.ActiveProgram
!= shProg
) {
793 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.ActiveProgram
, shProg
);
800 use_shader_program(struct gl_context
*ctx
, GLenum type
,
801 struct gl_shader_program
*shProg
)
803 struct gl_shader_program
**target
;
806 #if FEATURE_ARB_vertex_shader
807 case GL_VERTEX_SHADER
:
808 target
= &ctx
->Shader
.CurrentVertexProgram
;
810 || (shProg
->_LinkedShaders
[MESA_SHADER_VERTEX
] == NULL
)) {
815 #if FEATURE_ARB_geometry_shader4
816 case GL_GEOMETRY_SHADER_ARB
:
817 target
= &ctx
->Shader
.CurrentGeometryProgram
;
819 || (shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
] == NULL
)) {
824 #if FEATURE_ARB_fragment_shader
825 case GL_FRAGMENT_SHADER
:
826 target
= &ctx
->Shader
.CurrentFragmentProgram
;
828 || (shProg
->_LinkedShaders
[MESA_SHADER_FRAGMENT
] == NULL
)) {
837 if (*target
!= shProg
) {
838 FLUSH_VERTICES(ctx
, _NEW_PROGRAM
| _NEW_PROGRAM_CONSTANTS
);
840 /* If the shader is also bound as the current rendering shader, unbind
841 * it from that binding point as well. This ensures that the correct
842 * semantics of glDeleteProgram are maintained.
845 #if FEATURE_ARB_vertex_shader
846 case GL_VERTEX_SHADER
:
850 #if FEATURE_ARB_geometry_shader4
851 case GL_GEOMETRY_SHADER_ARB
:
855 #if FEATURE_ARB_fragment_shader
856 case GL_FRAGMENT_SHADER
:
857 if (*target
== ctx
->Shader
._CurrentFragmentProgram
) {
858 _mesa_reference_shader_program(ctx
,
859 &ctx
->Shader
._CurrentFragmentProgram
,
866 _mesa_reference_shader_program(ctx
, target
, shProg
);
874 * Use the named shader program for subsequent rendering.
877 _mesa_use_program(struct gl_context
*ctx
, struct gl_shader_program
*shProg
)
879 use_shader_program(ctx
, GL_VERTEX_SHADER
, shProg
);
880 use_shader_program(ctx
, GL_GEOMETRY_SHADER_ARB
, shProg
);
881 use_shader_program(ctx
, GL_FRAGMENT_SHADER
, shProg
);
882 _mesa_active_program(ctx
, shProg
, "glUseProgram");
884 if (ctx
->Driver
.UseProgram
)
885 ctx
->Driver
.UseProgram(ctx
, shProg
);
890 * Do validation of the given shader program.
891 * \param errMsg returns error message if validation fails.
892 * \return GL_TRUE if valid, GL_FALSE if invalid (and set errMsg)
895 validate_shader_program(const struct gl_shader_program
*shProg
,
898 if (!shProg
->LinkStatus
) {
902 /* From the GL spec, a program is invalid if any of these are true:
904 any two active samplers in the current program object are of
905 different types, but refer to the same texture image unit,
907 any active sampler in the current program object refers to a texture
908 image unit where fixed-function fragment processing accesses a
909 texture target that does not match the sampler type, or
911 the sum of the number of active samplers in the program and the
912 number of texture image units enabled for fixed-function fragment
913 processing exceeds the combined limit on the total number of texture
919 * Check: any two active samplers in the current program object are of
920 * different types, but refer to the same texture image unit,
922 if (!_mesa_sampler_uniforms_are_valid(shProg
, errMsg
, 100))
930 * Called via glValidateProgram()
933 validate_program(struct gl_context
*ctx
, GLuint program
)
935 struct gl_shader_program
*shProg
;
936 char errMsg
[100] = "";
938 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glValidateProgram");
943 shProg
->Validated
= validate_shader_program(shProg
, errMsg
);
944 if (!shProg
->Validated
) {
945 /* update info log */
946 if (shProg
->InfoLog
) {
947 ralloc_free(shProg
->InfoLog
);
949 shProg
->InfoLog
= ralloc_strdup(shProg
, errMsg
);
956 _mesa_AttachObjectARB(GLhandleARB program
, GLhandleARB shader
)
958 GET_CURRENT_CONTEXT(ctx
);
959 attach_shader(ctx
, program
, shader
);
964 _mesa_AttachShader(GLuint program
, GLuint shader
)
966 GET_CURRENT_CONTEXT(ctx
);
967 attach_shader(ctx
, program
, shader
);
972 _mesa_CompileShaderARB(GLhandleARB shaderObj
)
974 GET_CURRENT_CONTEXT(ctx
);
975 if (MESA_VERBOSE
& VERBOSE_API
)
976 _mesa_debug(ctx
, "glCompileShader %u\n", shaderObj
);
977 compile_shader(ctx
, shaderObj
);
982 _mesa_CreateShader(GLenum type
)
984 GET_CURRENT_CONTEXT(ctx
);
985 if (MESA_VERBOSE
& VERBOSE_API
)
986 _mesa_debug(ctx
, "glCreateShader %s\n", _mesa_lookup_enum_by_nr(type
));
987 return create_shader(ctx
, type
);
991 GLhandleARB GLAPIENTRY
992 _mesa_CreateShaderObjectARB(GLenum type
)
994 GET_CURRENT_CONTEXT(ctx
);
995 return create_shader(ctx
, type
);
1000 _mesa_CreateProgram(void)
1002 GET_CURRENT_CONTEXT(ctx
);
1003 if (MESA_VERBOSE
& VERBOSE_API
)
1004 _mesa_debug(ctx
, "glCreateProgram\n");
1005 return create_shader_program(ctx
);
1009 GLhandleARB GLAPIENTRY
1010 _mesa_CreateProgramObjectARB(void)
1012 GET_CURRENT_CONTEXT(ctx
);
1013 return create_shader_program(ctx
);
1018 _mesa_DeleteObjectARB(GLhandleARB obj
)
1020 if (MESA_VERBOSE
& VERBOSE_API
) {
1021 GET_CURRENT_CONTEXT(ctx
);
1022 _mesa_debug(ctx
, "glDeleteObjectARB(%u)\n", obj
);
1026 GET_CURRENT_CONTEXT(ctx
);
1027 FLUSH_VERTICES(ctx
, 0);
1028 if (is_program(ctx
, obj
)) {
1029 delete_shader_program(ctx
, obj
);
1031 else if (is_shader(ctx
, obj
)) {
1032 delete_shader(ctx
, obj
);
1042 _mesa_DeleteProgram(GLuint name
)
1045 GET_CURRENT_CONTEXT(ctx
);
1046 FLUSH_VERTICES(ctx
, 0);
1047 delete_shader_program(ctx
, name
);
1053 _mesa_DeleteShader(GLuint name
)
1056 GET_CURRENT_CONTEXT(ctx
);
1057 FLUSH_VERTICES(ctx
, 0);
1058 delete_shader(ctx
, name
);
1064 _mesa_DetachObjectARB(GLhandleARB program
, GLhandleARB shader
)
1066 GET_CURRENT_CONTEXT(ctx
);
1067 detach_shader(ctx
, program
, shader
);
1072 _mesa_DetachShader(GLuint program
, GLuint shader
)
1074 GET_CURRENT_CONTEXT(ctx
);
1075 detach_shader(ctx
, program
, shader
);
1080 _mesa_GetAttachedObjectsARB(GLhandleARB container
, GLsizei maxCount
,
1081 GLsizei
* count
, GLhandleARB
* obj
)
1083 GET_CURRENT_CONTEXT(ctx
);
1084 get_attached_shaders(ctx
, container
, maxCount
, count
, obj
);
1089 _mesa_GetAttachedShaders(GLuint program
, GLsizei maxCount
,
1090 GLsizei
*count
, GLuint
*obj
)
1092 GET_CURRENT_CONTEXT(ctx
);
1093 get_attached_shaders(ctx
, program
, maxCount
, count
, obj
);
1098 _mesa_GetInfoLogARB(GLhandleARB object
, GLsizei maxLength
, GLsizei
* length
,
1099 GLcharARB
* infoLog
)
1101 GET_CURRENT_CONTEXT(ctx
);
1102 if (is_program(ctx
, object
)) {
1103 get_program_info_log(ctx
, object
, maxLength
, length
, infoLog
);
1105 else if (is_shader(ctx
, object
)) {
1106 get_shader_info_log(ctx
, object
, maxLength
, length
, infoLog
);
1109 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glGetInfoLogARB");
1115 _mesa_GetObjectParameterivARB(GLhandleARB object
, GLenum pname
, GLint
*params
)
1117 GET_CURRENT_CONTEXT(ctx
);
1118 /* Implement in terms of GetProgramiv, GetShaderiv */
1119 if (is_program(ctx
, object
)) {
1120 if (pname
== GL_OBJECT_TYPE_ARB
) {
1121 *params
= GL_PROGRAM_OBJECT_ARB
;
1124 get_programiv(ctx
, object
, pname
, params
);
1127 else if (is_shader(ctx
, object
)) {
1128 if (pname
== GL_OBJECT_TYPE_ARB
) {
1129 *params
= GL_SHADER_OBJECT_ARB
;
1132 get_shaderiv(ctx
, object
, pname
, params
);
1136 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetObjectParameterivARB");
1142 _mesa_GetObjectParameterfvARB(GLhandleARB object
, GLenum pname
,
1145 GLint iparams
[1]; /* XXX is one element enough? */
1146 _mesa_GetObjectParameterivARB(object
, pname
, iparams
);
1147 params
[0] = (GLfloat
) iparams
[0];
1152 _mesa_GetProgramiv(GLuint program
, GLenum pname
, GLint
*params
)
1154 GET_CURRENT_CONTEXT(ctx
);
1155 get_programiv(ctx
, program
, pname
, params
);
1160 _mesa_GetShaderiv(GLuint shader
, GLenum pname
, GLint
*params
)
1162 GET_CURRENT_CONTEXT(ctx
);
1163 get_shaderiv(ctx
, shader
, pname
, params
);
1168 _mesa_GetProgramInfoLog(GLuint program
, GLsizei bufSize
,
1169 GLsizei
*length
, GLchar
*infoLog
)
1171 GET_CURRENT_CONTEXT(ctx
);
1172 get_program_info_log(ctx
, program
, bufSize
, length
, infoLog
);
1177 _mesa_GetShaderInfoLog(GLuint shader
, GLsizei bufSize
,
1178 GLsizei
*length
, GLchar
*infoLog
)
1180 GET_CURRENT_CONTEXT(ctx
);
1181 get_shader_info_log(ctx
, shader
, bufSize
, length
, infoLog
);
1186 _mesa_GetShaderSourceARB(GLhandleARB shader
, GLsizei maxLength
,
1187 GLsizei
*length
, GLcharARB
*sourceOut
)
1189 GET_CURRENT_CONTEXT(ctx
);
1190 get_shader_source(ctx
, shader
, maxLength
, length
, sourceOut
);
1194 GLhandleARB GLAPIENTRY
1195 _mesa_GetHandleARB(GLenum pname
)
1197 GET_CURRENT_CONTEXT(ctx
);
1198 return get_handle(ctx
, pname
);
1202 GLboolean GLAPIENTRY
1203 _mesa_IsProgram(GLuint name
)
1205 GET_CURRENT_CONTEXT(ctx
);
1206 return is_program(ctx
, name
);
1210 GLboolean GLAPIENTRY
1211 _mesa_IsShader(GLuint name
)
1213 GET_CURRENT_CONTEXT(ctx
);
1214 return is_shader(ctx
, name
);
1219 _mesa_LinkProgramARB(GLhandleARB programObj
)
1221 GET_CURRENT_CONTEXT(ctx
);
1222 link_program(ctx
, programObj
);
1228 * Read shader source code from a file.
1229 * Useful for debugging to override an app's shader.
1232 read_shader(const char *fname
)
1234 const int max
= 50*1000;
1235 FILE *f
= fopen(fname
, "r");
1236 GLcharARB
*buffer
, *shader
;
1243 buffer
= (char *) malloc(max
);
1244 len
= fread(buffer
, 1, max
, f
);
1249 shader
= _mesa_strdup(buffer
);
1257 * Called via glShaderSource() and glShaderSourceARB() API functions.
1258 * Basically, concatenate the source code strings into one long string
1259 * and pass it to _mesa_shader_source().
1262 _mesa_ShaderSourceARB(GLhandleARB shaderObj
, GLsizei count
,
1263 const GLcharARB
** string
, const GLint
* length
)
1265 GET_CURRENT_CONTEXT(ctx
);
1267 GLsizei i
, totalLength
;
1271 if (!shaderObj
|| string
== NULL
) {
1272 _mesa_error(ctx
, GL_INVALID_VALUE
, "glShaderSourceARB");
1277 * This array holds offsets of where the appropriate string ends, thus the
1278 * last element will be set to the total length of the source code.
1280 offsets
= (GLint
*) malloc(count
* sizeof(GLint
));
1281 if (offsets
== NULL
) {
1282 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glShaderSourceARB");
1286 for (i
= 0; i
< count
; i
++) {
1287 if (string
[i
] == NULL
) {
1288 free((GLvoid
*) offsets
);
1289 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1290 "glShaderSourceARB(null string)");
1293 if (length
== NULL
|| length
[i
] < 0)
1294 offsets
[i
] = strlen(string
[i
]);
1296 offsets
[i
] = length
[i
];
1297 /* accumulate string lengths */
1299 offsets
[i
] += offsets
[i
- 1];
1302 /* Total length of source string is sum off all strings plus two.
1303 * One extra byte for terminating zero, another extra byte to silence
1304 * valgrind warnings in the parser/grammer code.
1306 totalLength
= offsets
[count
- 1] + 2;
1307 source
= (GLcharARB
*) malloc(totalLength
* sizeof(GLcharARB
));
1308 if (source
== NULL
) {
1309 free((GLvoid
*) offsets
);
1310 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glShaderSourceARB");
1314 for (i
= 0; i
< count
; i
++) {
1315 GLint start
= (i
> 0) ? offsets
[i
- 1] : 0;
1316 memcpy(source
+ start
, string
[i
],
1317 (offsets
[i
] - start
) * sizeof(GLcharARB
));
1319 source
[totalLength
- 1] = '\0';
1320 source
[totalLength
- 2] = '\0';
1323 /* Compute the shader's source code checksum then try to open a file
1324 * named newshader_<CHECKSUM>. If it exists, use it in place of the
1325 * original shader source code. For debugging.
1328 GLcharARB
*newSource
;
1330 checksum
= _mesa_str_checksum(source
);
1332 _mesa_snprintf(filename
, sizeof(filename
), "newshader_%d", checksum
);
1334 newSource
= read_shader(filename
);
1336 fprintf(stderr
, "Mesa: Replacing shader %u chksum=%d with %s\n",
1337 shaderObj
, checksum
, filename
);
1343 shader_source(ctx
, shaderObj
, source
);
1346 struct gl_shader
*sh
= _mesa_lookup_shader(ctx
, shaderObj
);
1348 sh
->SourceChecksum
= checksum
; /* save original checksum */
1356 _mesa_UseProgramObjectARB(GLhandleARB program
)
1358 GET_CURRENT_CONTEXT(ctx
);
1359 struct gl_shader_program
*shProg
;
1360 struct gl_transform_feedback_object
*obj
=
1361 ctx
->TransformFeedback
.CurrentObject
;
1363 ASSERT_OUTSIDE_BEGIN_END(ctx
);
1365 if (obj
->Active
&& !obj
->Paused
) {
1366 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1367 "glUseProgram(transform feedback active)");
1372 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glUseProgram");
1376 if (!shProg
->LinkStatus
) {
1377 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1378 "glUseProgram(program %u not linked)", program
);
1383 if (ctx
->Shader
.Flags
& GLSL_USE_PROG
) {
1384 print_shader_info(shProg
);
1391 _mesa_use_program(ctx
, shProg
);
1396 _mesa_ValidateProgramARB(GLhandleARB program
)
1398 GET_CURRENT_CONTEXT(ctx
);
1399 validate_program(ctx
, program
);
1405 _mesa_GetShaderPrecisionFormat(GLenum shadertype
, GLenum precisiontype
,
1406 GLint
* range
, GLint
* precision
)
1408 const struct gl_program_constants
*limits
;
1409 const struct gl_precision
*p
;
1410 GET_CURRENT_CONTEXT(ctx
);
1412 switch (shadertype
) {
1413 case GL_VERTEX_SHADER
:
1414 limits
= &ctx
->Const
.VertexProgram
;
1416 case GL_FRAGMENT_SHADER
:
1417 limits
= &ctx
->Const
.FragmentProgram
;
1420 _mesa_error(ctx
, GL_INVALID_ENUM
,
1421 "glGetShaderPrecisionFormat(shadertype)");
1425 switch (precisiontype
) {
1427 p
= &limits
->LowFloat
;
1429 case GL_MEDIUM_FLOAT
:
1430 p
= &limits
->MediumFloat
;
1433 p
= &limits
->HighFloat
;
1436 p
= &limits
->LowInt
;
1439 p
= &limits
->MediumInt
;
1442 p
= &limits
->HighInt
;
1445 _mesa_error(ctx
, GL_INVALID_ENUM
,
1446 "glGetShaderPrecisionFormat(precisiontype)");
1450 range
[0] = p
->RangeMin
;
1451 range
[1] = p
->RangeMax
;
1452 precision
[0] = p
->Precision
;
1457 _mesa_ReleaseShaderCompiler(void)
1459 _mesa_destroy_shader_compiler_caches();
1464 _mesa_ShaderBinary(GLint n
, const GLuint
* shaders
, GLenum binaryformat
,
1465 const void* binary
, GLint length
)
1467 GET_CURRENT_CONTEXT(ctx
);
1470 (void) binaryformat
;
1473 _mesa_error(ctx
, GL_INVALID_OPERATION
, __FUNCTION__
);
1476 #endif /* FEATURE_ES2 */
1479 #if FEATURE_ARB_geometry_shader4
1482 _mesa_ProgramParameteriARB(GLuint program
, GLenum pname
, GLint value
)
1484 struct gl_shader_program
*shProg
;
1485 GET_CURRENT_CONTEXT(ctx
);
1487 ASSERT_OUTSIDE_BEGIN_END(ctx
);
1489 shProg
= _mesa_lookup_shader_program_err(ctx
, program
,
1490 "glProgramParameteri");
1495 case GL_GEOMETRY_VERTICES_OUT_ARB
:
1497 (unsigned) value
> ctx
->Const
.MaxGeometryOutputVertices
) {
1498 _mesa_error(ctx
, GL_INVALID_VALUE
,
1499 "glProgramParameteri(GL_GEOMETRY_VERTICES_OUT_ARB=%d",
1503 shProg
->Geom
.VerticesOut
= value
;
1505 case GL_GEOMETRY_INPUT_TYPE_ARB
:
1509 case GL_LINES_ADJACENCY_ARB
:
1511 case GL_TRIANGLES_ADJACENCY_ARB
:
1512 shProg
->Geom
.InputType
= value
;
1515 _mesa_error(ctx
, GL_INVALID_VALUE
,
1516 "glProgramParameteri(geometry input type = %s",
1517 _mesa_lookup_enum_by_nr(value
));
1521 case GL_GEOMETRY_OUTPUT_TYPE_ARB
:
1525 case GL_TRIANGLE_STRIP
:
1526 shProg
->Geom
.OutputType
= value
;
1529 _mesa_error(ctx
, GL_INVALID_VALUE
,
1530 "glProgramParameteri(geometry output type = %s",
1531 _mesa_lookup_enum_by_nr(value
));
1536 _mesa_error(ctx
, GL_INVALID_ENUM
, "glProgramParameteriARB(pname=%s)",
1537 _mesa_lookup_enum_by_nr(pname
));
1545 _mesa_use_shader_program(struct gl_context
*ctx
, GLenum type
,
1546 struct gl_shader_program
*shProg
)
1548 use_shader_program(ctx
, type
, shProg
);
1550 if (ctx
->Driver
.UseProgram
)
1551 ctx
->Driver
.UseProgram(ctx
, shProg
);
1556 * For GL_EXT_separate_shader_objects
1559 _mesa_UseShaderProgramEXT(GLenum type
, GLuint program
)
1561 GET_CURRENT_CONTEXT(ctx
);
1562 struct gl_shader_program
*shProg
= NULL
;
1564 ASSERT_OUTSIDE_BEGIN_END(ctx
);
1566 if (!validate_shader_target(ctx
, type
)) {
1567 _mesa_error(ctx
, GL_INVALID_ENUM
, "glUseShaderProgramEXT(type)");
1571 if (ctx
->TransformFeedback
.CurrentObject
->Active
&&
1572 !ctx
->TransformFeedback
.CurrentObject
->Paused
) {
1573 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1574 "glUseShaderProgramEXT(transform feedback is active)");
1579 shProg
= _mesa_lookup_shader_program_err(ctx
, program
,
1580 "glUseShaderProgramEXT");
1584 if (!shProg
->LinkStatus
) {
1585 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1586 "glUseShaderProgramEXT(program not linked)");
1591 _mesa_use_shader_program(ctx
, type
, shProg
);
1596 * For GL_EXT_separate_shader_objects
1599 _mesa_ActiveProgramEXT(GLuint program
)
1601 GET_CURRENT_CONTEXT(ctx
);
1602 struct gl_shader_program
*shProg
= (program
!= 0)
1603 ? _mesa_lookup_shader_program_err(ctx
, program
, "glActiveProgramEXT")
1606 _mesa_active_program(ctx
, shProg
, "glActiveProgramEXT");
1612 * For GL_EXT_separate_shader_objects
1615 _mesa_CreateShaderProgramEXT(GLenum type
, const GLchar
*string
)
1617 GET_CURRENT_CONTEXT(ctx
);
1618 const GLuint shader
= create_shader(ctx
, type
);
1622 shader_source(ctx
, shader
, _mesa_strdup(string
));
1623 compile_shader(ctx
, shader
);
1625 program
= create_shader_program(ctx
);
1627 struct gl_shader_program
*shProg
;
1628 struct gl_shader
*sh
;
1629 GLint compiled
= GL_FALSE
;
1631 shProg
= _mesa_lookup_shader_program(ctx
, program
);
1632 sh
= _mesa_lookup_shader(ctx
, shader
);
1634 get_shaderiv(ctx
, shader
, GL_COMPILE_STATUS
, &compiled
);
1636 attach_shader(ctx
, program
, shader
);
1637 link_program(ctx
, program
);
1638 detach_shader(ctx
, program
, shader
);
1642 if (active
-user
-defined
-varyings
-in
-linked
-program
) {
1643 append
-error
-to
-info
-log
;
1644 shProg
->LinkStatus
= GL_FALSE
;
1649 ralloc_strcat(&shProg
->InfoLog
, sh
->InfoLog
);
1652 delete_shader(ctx
, shader
);
1659 * Plug in shader-related functions into API dispatch table.
1662 _mesa_init_shader_dispatch(struct _glapi_table
*exec
)
1665 /* GL_ARB_vertex/fragment_shader */
1666 SET_DeleteObjectARB(exec
, _mesa_DeleteObjectARB
);
1667 SET_GetHandleARB(exec
, _mesa_GetHandleARB
);
1668 SET_DetachObjectARB(exec
, _mesa_DetachObjectARB
);
1669 SET_CreateShaderObjectARB(exec
, _mesa_CreateShaderObjectARB
);
1670 SET_ShaderSourceARB(exec
, _mesa_ShaderSourceARB
);
1671 SET_CompileShaderARB(exec
, _mesa_CompileShaderARB
);
1672 SET_CreateProgramObjectARB(exec
, _mesa_CreateProgramObjectARB
);
1673 SET_AttachObjectARB(exec
, _mesa_AttachObjectARB
);
1674 SET_LinkProgramARB(exec
, _mesa_LinkProgramARB
);
1675 SET_UseProgramObjectARB(exec
, _mesa_UseProgramObjectARB
);
1676 SET_ValidateProgramARB(exec
, _mesa_ValidateProgramARB
);
1677 SET_GetObjectParameterfvARB(exec
, _mesa_GetObjectParameterfvARB
);
1678 SET_GetObjectParameterivARB(exec
, _mesa_GetObjectParameterivARB
);
1679 SET_GetInfoLogARB(exec
, _mesa_GetInfoLogARB
);
1680 SET_GetAttachedObjectsARB(exec
, _mesa_GetAttachedObjectsARB
);
1681 SET_GetShaderSourceARB(exec
, _mesa_GetShaderSourceARB
);
1684 SET_AttachShader(exec
, _mesa_AttachShader
);
1685 SET_CreateProgram(exec
, _mesa_CreateProgram
);
1686 SET_CreateShader(exec
, _mesa_CreateShader
);
1687 SET_DeleteProgram(exec
, _mesa_DeleteProgram
);
1688 SET_DeleteShader(exec
, _mesa_DeleteShader
);
1689 SET_DetachShader(exec
, _mesa_DetachShader
);
1690 SET_GetAttachedShaders(exec
, _mesa_GetAttachedShaders
);
1691 SET_GetProgramiv(exec
, _mesa_GetProgramiv
);
1692 SET_GetProgramInfoLog(exec
, _mesa_GetProgramInfoLog
);
1693 SET_GetShaderiv(exec
, _mesa_GetShaderiv
);
1694 SET_GetShaderInfoLog(exec
, _mesa_GetShaderInfoLog
);
1695 SET_IsProgram(exec
, _mesa_IsProgram
);
1696 SET_IsShader(exec
, _mesa_IsShader
);
1698 #if FEATURE_ARB_vertex_shader
1699 SET_BindAttribLocationARB(exec
, _mesa_BindAttribLocationARB
);
1700 SET_GetActiveAttribARB(exec
, _mesa_GetActiveAttribARB
);
1701 SET_GetAttribLocationARB(exec
, _mesa_GetAttribLocationARB
);
1704 #if FEATURE_ARB_geometry_shader4
1705 SET_ProgramParameteriARB(exec
, _mesa_ProgramParameteriARB
);
1708 SET_UseShaderProgramEXT(exec
, _mesa_UseShaderProgramEXT
);
1709 SET_ActiveProgramEXT(exec
, _mesa_ActiveProgramEXT
);
1710 SET_CreateShaderProgramEXT(exec
, _mesa_CreateShaderProgramEXT
);
1712 /* GL_EXT_gpu_shader4 / GL 3.0 */
1713 SET_BindFragDataLocationEXT(exec
, _mesa_BindFragDataLocation
);
1714 SET_GetFragDataLocationEXT(exec
, _mesa_GetFragDataLocation
);
1716 /* GL_ARB_ES2_compatibility */
1717 SET_ReleaseShaderCompiler(exec
, _mesa_ReleaseShaderCompiler
);
1718 SET_GetShaderPrecisionFormat(exec
, _mesa_GetShaderPrecisionFormat
);
1720 /* GL_ARB_blend_func_extended */
1721 SET_BindFragDataLocationIndexed(exec
, _mesa_BindFragDataLocationIndexed
);
1722 SET_GetFragDataIndex(exec
, _mesa_GetFragDataIndex
);
1723 #endif /* FEATURE_GL */