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 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
21 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
23 * OTHER DEALINGS IN THE SOFTWARE.
30 * Implementation of GLSL-related API functions.
31 * The glUniform* functions are in uniforms.c
35 * 1. Check that the right error code is generated for all _mesa_error() calls.
36 * 2. Insert FLUSH_VERTICES calls in various places
40 #include "main/glheader.h"
41 #include "main/context.h"
42 #include "main/dispatch.h"
43 #include "main/enums.h"
44 #include "main/hash.h"
45 #include "main/hash_table.h"
46 #include "main/mtypes.h"
47 #include "main/shaderapi.h"
48 #include "main/shaderobj.h"
49 #include "main/transformfeedback.h"
50 #include "main/uniforms.h"
51 #include "program/program.h"
52 #include "program/prog_print.h"
53 #include "program/prog_parameter.h"
56 #include "../glsl/glsl_parser_extras.h"
57 #include "../glsl/ir.h"
58 #include "../glsl/ir_uniform.h"
59 #include "../glsl/program.h"
61 /** Define this to enable shader substitution (see below) */
62 #define SHADER_SUBST 0
66 * Return mask of GLSL_x flags by examining the MESA_GLSL env var.
69 get_shader_flags(void)
71 GLbitfield flags
= 0x0;
72 const char *env
= _mesa_getenv("MESA_GLSL");
75 if (strstr(env
, "dump_on_error"))
76 flags
|= GLSL_DUMP_ON_ERROR
;
77 else if (strstr(env
, "dump"))
79 if (strstr(env
, "log"))
81 if (strstr(env
, "nopvert"))
82 flags
|= GLSL_NOP_VERT
;
83 if (strstr(env
, "nopfrag"))
84 flags
|= GLSL_NOP_FRAG
;
85 if (strstr(env
, "nopt"))
87 else if (strstr(env
, "opt"))
89 if (strstr(env
, "uniform"))
90 flags
|= GLSL_UNIFORMS
;
91 if (strstr(env
, "useprog"))
92 flags
|= GLSL_USE_PROG
;
93 if (strstr(env
, "errors"))
94 flags
|= GLSL_REPORT_ERRORS
;
102 * Initialize context's shader state.
105 _mesa_init_shader_state(struct gl_context
*ctx
)
107 /* Device drivers may override these to control what kind of instructions
108 * are generated by the GLSL compiler.
110 struct gl_shader_compiler_options options
;
113 memset(&options
, 0, sizeof(options
));
114 options
.MaxUnrollIterations
= 32;
115 options
.MaxIfDepth
= UINT_MAX
;
117 /* Default pragma settings */
118 options
.DefaultPragmas
.Optimize
= GL_TRUE
;
120 for (sh
= 0; sh
< MESA_SHADER_TYPES
; ++sh
)
121 memcpy(&ctx
->ShaderCompilerOptions
[sh
], &options
, sizeof(options
));
123 ctx
->Shader
.Flags
= get_shader_flags();
128 * Free the per-context shader-related state.
131 _mesa_free_shader_state(struct gl_context
*ctx
)
133 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentVertexProgram
, NULL
);
134 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentGeometryProgram
,
136 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentFragmentProgram
,
138 _mesa_reference_shader_program(ctx
, &ctx
->Shader
._CurrentFragmentProgram
,
140 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.ActiveProgram
, NULL
);
145 * Copy string from <src> to <dst>, up to maxLength characters, returning
146 * length of <dst> in <length>.
147 * \param src the strings source
148 * \param maxLength max chars to copy
149 * \param length returns number of chars copied
150 * \param dst the string destination
153 _mesa_copy_string(GLchar
*dst
, GLsizei maxLength
,
154 GLsizei
*length
, const GLchar
*src
)
157 for (len
= 0; len
< maxLength
- 1 && src
&& src
[len
]; len
++)
168 * Confirm that the a shader type is valid and supported by the implementation
170 * \param ctx Current GL context
171 * \param type Shader target
175 validate_shader_target(const struct gl_context
*ctx
, GLenum type
)
178 case GL_FRAGMENT_SHADER
:
179 return ctx
->Extensions
.ARB_fragment_shader
;
180 case GL_VERTEX_SHADER
:
181 return ctx
->Extensions
.ARB_vertex_shader
;
182 case GL_GEOMETRY_SHADER_ARB
:
183 return _mesa_has_geometry_shaders(ctx
);
191 is_program(struct gl_context
*ctx
, GLuint name
)
193 struct gl_shader_program
*shProg
= _mesa_lookup_shader_program(ctx
, name
);
194 return shProg
? GL_TRUE
: GL_FALSE
;
199 is_shader(struct gl_context
*ctx
, GLuint name
)
201 struct gl_shader
*shader
= _mesa_lookup_shader(ctx
, name
);
202 return shader
? GL_TRUE
: GL_FALSE
;
207 * Attach shader to a shader program.
210 attach_shader(struct gl_context
*ctx
, GLuint program
, GLuint shader
)
212 struct gl_shader_program
*shProg
;
213 struct gl_shader
*sh
;
216 const bool same_type_disallowed
= _mesa_is_gles(ctx
);
218 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glAttachShader");
222 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glAttachShader");
227 n
= shProg
->NumShaders
;
228 for (i
= 0; i
< n
; i
++) {
229 if (shProg
->Shaders
[i
] == sh
) {
230 /* The shader is already attched to this program. The
231 * GL_ARB_shader_objects spec says:
233 * "The error INVALID_OPERATION is generated by AttachObjectARB
234 * if <obj> is already attached to <containerObj>."
236 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glAttachShader");
238 } else if (same_type_disallowed
&&
239 shProg
->Shaders
[i
]->Type
== sh
->Type
) {
240 /* Shader with the same type is already attached to this program,
241 * OpenGL ES 2.0 and 3.0 specs say:
243 * "Multiple shader objects of the same type may not be attached
244 * to a single program object. [...] The error INVALID_OPERATION
245 * is generated if [...] another shader object of the same type
246 * as shader is already attached to program."
248 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glAttachShader");
254 shProg
->Shaders
= (struct gl_shader
**)
255 _mesa_realloc(shProg
->Shaders
,
256 n
* sizeof(struct gl_shader
*),
257 (n
+ 1) * sizeof(struct gl_shader
*));
258 if (!shProg
->Shaders
) {
259 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glAttachShader");
264 shProg
->Shaders
[n
] = NULL
; /* since realloc() didn't zero the new space */
265 _mesa_reference_shader(ctx
, &shProg
->Shaders
[n
], sh
);
266 shProg
->NumShaders
++;
271 create_shader(struct gl_context
*ctx
, GLenum type
)
273 struct gl_shader
*sh
;
276 if (!validate_shader_target(ctx
, type
)) {
277 _mesa_error(ctx
, GL_INVALID_ENUM
, "CreateShader(type)");
281 name
= _mesa_HashFindFreeKeyBlock(ctx
->Shared
->ShaderObjects
, 1);
282 sh
= ctx
->Driver
.NewShader(ctx
, name
, type
);
283 _mesa_HashInsert(ctx
->Shared
->ShaderObjects
, name
, sh
);
290 create_shader_program(struct gl_context
*ctx
)
293 struct gl_shader_program
*shProg
;
295 name
= _mesa_HashFindFreeKeyBlock(ctx
->Shared
->ShaderObjects
, 1);
297 shProg
= ctx
->Driver
.NewShaderProgram(ctx
, name
);
299 _mesa_HashInsert(ctx
->Shared
->ShaderObjects
, name
, shProg
);
301 assert(shProg
->RefCount
== 1);
308 * Named w/ "2" to indicate OpenGL 2.x vs GL_ARB_fragment_programs's
312 delete_shader_program(struct gl_context
*ctx
, GLuint name
)
315 * NOTE: deleting shaders/programs works a bit differently than
316 * texture objects (and buffer objects, etc). Shader/program
317 * handles/IDs exist in the hash table until the object is really
318 * deleted (refcount==0). With texture objects, the handle/ID is
319 * removed from the hash table in glDeleteTextures() while the tex
320 * object itself might linger until its refcount goes to zero.
322 struct gl_shader_program
*shProg
;
324 shProg
= _mesa_lookup_shader_program_err(ctx
, name
, "glDeleteProgram");
328 if (!shProg
->DeletePending
) {
329 shProg
->DeletePending
= GL_TRUE
;
331 /* effectively, decr shProg's refcount */
332 _mesa_reference_shader_program(ctx
, &shProg
, NULL
);
338 delete_shader(struct gl_context
*ctx
, GLuint shader
)
340 struct gl_shader
*sh
;
342 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glDeleteShader");
346 if (!sh
->DeletePending
) {
347 sh
->DeletePending
= GL_TRUE
;
349 /* effectively, decr sh's refcount */
350 _mesa_reference_shader(ctx
, &sh
, NULL
);
356 detach_shader(struct gl_context
*ctx
, GLuint program
, GLuint shader
)
358 struct gl_shader_program
*shProg
;
362 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glDetachShader");
366 n
= shProg
->NumShaders
;
368 for (i
= 0; i
< n
; i
++) {
369 if (shProg
->Shaders
[i
]->Name
== shader
) {
371 struct gl_shader
**newList
;
374 _mesa_reference_shader(ctx
, &shProg
->Shaders
[i
], NULL
);
376 /* alloc new, smaller array */
378 malloc((n
- 1) * sizeof(struct gl_shader
*));
380 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glDetachShader");
383 for (j
= 0; j
< i
; j
++) {
384 newList
[j
] = shProg
->Shaders
[j
];
387 newList
[j
++] = shProg
->Shaders
[i
];
388 free(shProg
->Shaders
);
390 shProg
->Shaders
= newList
;
391 shProg
->NumShaders
= n
- 1;
396 for (j
= 0; j
< shProg
->NumShaders
; j
++) {
397 assert(shProg
->Shaders
[j
]->Type
== GL_VERTEX_SHADER
||
398 shProg
->Shaders
[j
]->Type
== GL_FRAGMENT_SHADER
);
399 assert(shProg
->Shaders
[j
]->RefCount
> 0);
411 if (is_shader(ctx
, shader
))
412 err
= GL_INVALID_OPERATION
;
413 else if (is_program(ctx
, shader
))
414 err
= GL_INVALID_OPERATION
;
416 err
= GL_INVALID_VALUE
;
417 _mesa_error(ctx
, err
, "glDetachProgram(shader)");
424 * Return list of shaders attached to shader program.
427 get_attached_shaders(struct gl_context
*ctx
, GLuint program
, GLsizei maxCount
,
428 GLsizei
*count
, GLuint
*obj
)
430 struct gl_shader_program
*shProg
=
431 _mesa_lookup_shader_program_err(ctx
, program
, "glGetAttachedShaders");
434 for (i
= 0; i
< (GLuint
) maxCount
&& i
< shProg
->NumShaders
; i
++) {
435 obj
[i
] = shProg
->Shaders
[i
]->Name
;
444 * glGetHandleARB() - return ID/name of currently bound shader program.
447 get_handle(struct gl_context
*ctx
, GLenum pname
)
449 if (pname
== GL_PROGRAM_OBJECT_ARB
) {
450 if (ctx
->Shader
.ActiveProgram
)
451 return ctx
->Shader
.ActiveProgram
->Name
;
456 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetHandleARB");
463 * Check if a geometry shader query is valid at this time. If not, report an
464 * error and return false.
466 * From GL 3.2 section 6.1.16 (Shader and Program Queries):
468 * "If GEOMETRY_VERTICES_OUT, GEOMETRY_INPUT_TYPE, or GEOMETRY_OUTPUT_TYPE
469 * are queried for a program which has not been linked successfully, or
470 * which does not contain objects to form a geometry shader, then an
471 * INVALID_OPERATION error is generated."
474 check_gs_query(struct gl_context
*ctx
, const struct gl_shader_program
*shProg
)
476 if (shProg
->LinkStatus
&&
477 shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
] != NULL
) {
481 _mesa_error(ctx
, GL_INVALID_OPERATION
,
482 "glGetProgramv(linked geometry shader required)");
488 * glGetProgramiv() - get shader program state.
489 * Note that this is for GLSL shader programs, not ARB vertex/fragment
490 * programs (see glGetProgramivARB).
493 get_programiv(struct gl_context
*ctx
, GLuint program
, GLenum pname
, GLint
*params
)
495 struct gl_shader_program
*shProg
496 = _mesa_lookup_shader_program(ctx
, program
);
498 /* Is transform feedback available in this context?
501 (ctx
->API
== API_OPENGL_COMPAT
&& ctx
->Extensions
.EXT_transform_feedback
)
502 || ctx
->API
== API_OPENGL_CORE
503 || _mesa_is_gles3(ctx
);
505 /* True if geometry shaders (of the form that was adopted into GLSL 1.50
506 * and GL 3.2) are available in this context
508 const bool has_core_gs
= _mesa_is_desktop_gl(ctx
) && ctx
->Version
>= 32;
510 /* Are uniform buffer objects available in this context?
513 (ctx
->API
== API_OPENGL_COMPAT
&& ctx
->Extensions
.ARB_uniform_buffer_object
)
514 || ctx
->API
== API_OPENGL_CORE
515 || _mesa_is_gles3(ctx
);
518 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramiv(program)");
523 case GL_DELETE_STATUS
:
524 *params
= shProg
->DeletePending
;
527 *params
= shProg
->LinkStatus
;
529 case GL_VALIDATE_STATUS
:
530 *params
= shProg
->Validated
;
532 case GL_INFO_LOG_LENGTH
:
533 *params
= shProg
->InfoLog
? strlen(shProg
->InfoLog
) + 1 : 0;
535 case GL_ATTACHED_SHADERS
:
536 *params
= shProg
->NumShaders
;
538 case GL_ACTIVE_ATTRIBUTES
:
539 *params
= _mesa_count_active_attribs(shProg
);
541 case GL_ACTIVE_ATTRIBUTE_MAX_LENGTH
:
542 *params
= _mesa_longest_attribute_name_length(shProg
);
544 case GL_ACTIVE_UNIFORMS
:
545 *params
= shProg
->NumUserUniformStorage
;
547 case GL_ACTIVE_UNIFORM_MAX_LENGTH
: {
551 for (i
= 0; i
< shProg
->NumUserUniformStorage
; i
++) {
552 /* Add one for the terminating NUL character for a non-array, and
553 * 4 for the "[0]" and the NUL for an array.
555 const GLint len
= strlen(shProg
->UniformStorage
[i
].name
) + 1 +
556 ((shProg
->UniformStorage
[i
].array_elements
!= 0) ? 3 : 0);
565 case GL_TRANSFORM_FEEDBACK_VARYINGS
:
568 *params
= shProg
->TransformFeedback
.NumVarying
;
570 case GL_TRANSFORM_FEEDBACK_VARYING_MAX_LENGTH
: {
576 for (i
= 0; i
< shProg
->TransformFeedback
.NumVarying
; i
++) {
577 /* Add one for the terminating NUL character.
579 const GLint len
= strlen(shProg
->TransformFeedback
.VaryingNames
[i
]) + 1;
588 case GL_TRANSFORM_FEEDBACK_BUFFER_MODE
:
591 *params
= shProg
->TransformFeedback
.BufferMode
;
593 case GL_GEOMETRY_VERTICES_OUT
:
596 if (check_gs_query(ctx
, shProg
))
597 *params
= shProg
->Geom
.VerticesOut
;
599 case GL_GEOMETRY_INPUT_TYPE
:
602 if (check_gs_query(ctx
, shProg
))
603 *params
= shProg
->Geom
.InputType
;
605 case GL_GEOMETRY_OUTPUT_TYPE
:
608 if (check_gs_query(ctx
, shProg
))
609 *params
= shProg
->Geom
.OutputType
;
611 case GL_ACTIVE_UNIFORM_BLOCK_MAX_NAME_LENGTH
: {
618 for (i
= 0; i
< shProg
->NumUniformBlocks
; i
++) {
619 /* Add one for the terminating NUL character.
621 const GLint len
= strlen(shProg
->UniformBlocks
[i
].Name
) + 1;
630 case GL_ACTIVE_UNIFORM_BLOCKS
:
634 *params
= shProg
->NumUniformBlocks
;
636 case GL_PROGRAM_BINARY_RETRIEVABLE_HINT
:
637 /* This enum isn't part of the OES extension for OpenGL ES 2.0. It is
638 * only available with desktop OpenGL 3.0+ with the
639 * GL_ARB_get_program_binary extension or OpenGL ES 3.0.
641 * On desktop, we ignore the 3.0+ requirement because it is silly.
643 if (!_mesa_is_desktop_gl(ctx
) && !_mesa_is_gles3(ctx
))
646 *params
= shProg
->BinaryRetreivableHint
;
648 case GL_PROGRAM_BINARY_LENGTH
:
655 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetProgramiv(pname=%s)",
656 _mesa_lookup_enum_by_nr(pname
));
661 * glGetShaderiv() - get GLSL shader state
664 get_shaderiv(struct gl_context
*ctx
, GLuint name
, GLenum pname
, GLint
*params
)
666 struct gl_shader
*shader
=
667 _mesa_lookup_shader_err(ctx
, name
, "glGetShaderiv");
675 *params
= shader
->Type
;
677 case GL_DELETE_STATUS
:
678 *params
= shader
->DeletePending
;
680 case GL_COMPILE_STATUS
:
681 *params
= shader
->CompileStatus
;
683 case GL_INFO_LOG_LENGTH
:
684 *params
= shader
->InfoLog
? strlen(shader
->InfoLog
) + 1 : 0;
686 case GL_SHADER_SOURCE_LENGTH
:
687 *params
= shader
->Source
? strlen((char *) shader
->Source
) + 1 : 0;
690 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetShaderiv(pname)");
697 get_program_info_log(struct gl_context
*ctx
, GLuint program
, GLsizei bufSize
,
698 GLsizei
*length
, GLchar
*infoLog
)
700 struct gl_shader_program
*shProg
701 = _mesa_lookup_shader_program(ctx
, program
);
703 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramInfoLog(program)");
706 _mesa_copy_string(infoLog
, bufSize
, length
, shProg
->InfoLog
);
711 get_shader_info_log(struct gl_context
*ctx
, GLuint shader
, GLsizei bufSize
,
712 GLsizei
*length
, GLchar
*infoLog
)
714 struct gl_shader
*sh
= _mesa_lookup_shader(ctx
, shader
);
716 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetShaderInfoLog(shader)");
719 _mesa_copy_string(infoLog
, bufSize
, length
, sh
->InfoLog
);
724 * Return shader source code.
727 get_shader_source(struct gl_context
*ctx
, GLuint shader
, GLsizei maxLength
,
728 GLsizei
*length
, GLchar
*sourceOut
)
730 struct gl_shader
*sh
;
731 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glGetShaderSource");
735 _mesa_copy_string(sourceOut
, maxLength
, length
, sh
->Source
);
740 * Set/replace shader source code. A helper function used by
741 * glShaderSource[ARB] and glCreateShaderProgramEXT.
744 shader_source(struct gl_context
*ctx
, GLuint shader
, const GLchar
*source
)
746 struct gl_shader
*sh
;
748 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glShaderSource");
752 /* free old shader source string and install new one */
753 free((void *)sh
->Source
);
755 sh
->CompileStatus
= GL_FALSE
;
757 sh
->SourceChecksum
= _mesa_str_checksum(sh
->Source
);
766 compile_shader(struct gl_context
*ctx
, GLuint shaderObj
)
768 struct gl_shader
*sh
;
769 struct gl_shader_compiler_options
*options
;
771 sh
= _mesa_lookup_shader_err(ctx
, shaderObj
, "glCompileShader");
775 options
= &ctx
->ShaderCompilerOptions
[_mesa_shader_type_to_index(sh
->Type
)];
777 /* set default pragma state for shader */
778 sh
->Pragmas
= options
->DefaultPragmas
;
781 /* If the user called glCompileShader without first calling
782 * glShaderSource, we should fail to compile, but not raise a GL_ERROR.
784 sh
->CompileStatus
= GL_FALSE
;
786 if (ctx
->Shader
.Flags
& GLSL_DUMP
) {
787 printf("GLSL source for %s shader %d:\n",
788 _mesa_glsl_shader_target_name(sh
->Type
), sh
->Name
);
789 printf("%s\n", sh
->Source
);
792 /* this call will set the shader->CompileStatus field to indicate if
793 * compilation was successful.
795 _mesa_glsl_compile_shader(ctx
, sh
, false, false);
797 if (ctx
->Shader
.Flags
& GLSL_LOG
) {
798 _mesa_write_shader_to_file(sh
);
801 if (ctx
->Shader
.Flags
& GLSL_DUMP
) {
802 if (sh
->CompileStatus
) {
803 printf("GLSL IR for shader %d:\n", sh
->Name
);
804 _mesa_print_ir(sh
->ir
, NULL
);
807 printf("GLSL shader %d failed to compile.\n", sh
->Name
);
809 if (sh
->InfoLog
&& sh
->InfoLog
[0] != 0) {
810 printf("GLSL shader %d info log:\n", sh
->Name
);
811 printf("%s\n", sh
->InfoLog
);
817 if (!sh
->CompileStatus
) {
818 if (ctx
->Shader
.Flags
& GLSL_DUMP_ON_ERROR
) {
819 fprintf(stderr
, "GLSL source for %s shader %d:\n",
820 _mesa_glsl_shader_target_name(sh
->Type
), sh
->Name
);
821 fprintf(stderr
, "%s\n", sh
->Source
);
824 if (ctx
->Shader
.Flags
& GLSL_REPORT_ERRORS
) {
825 _mesa_debug(ctx
, "Error compiling shader %u:\n%s\n",
826 sh
->Name
, sh
->InfoLog
);
833 * Link a program's shaders.
836 link_program(struct gl_context
*ctx
, GLuint program
)
838 struct gl_shader_program
*shProg
;
840 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glLinkProgram");
844 /* From the ARB_transform_feedback2 specification:
845 * "The error INVALID_OPERATION is generated by LinkProgram if <program> is
846 * the name of a program being used by one or more transform feedback
847 * objects, even if the objects are not currently bound or are paused."
849 if (_mesa_transform_feedback_is_using_program(ctx
, shProg
)) {
850 _mesa_error(ctx
, GL_INVALID_OPERATION
,
851 "glLinkProgram(transform feedback is using the program)");
855 FLUSH_VERTICES(ctx
, _NEW_PROGRAM
);
857 _mesa_glsl_link_shader(ctx
, shProg
);
859 if (shProg
->LinkStatus
== GL_FALSE
&&
860 (ctx
->Shader
.Flags
& GLSL_REPORT_ERRORS
)) {
861 _mesa_debug(ctx
, "Error linking program %u:\n%s\n",
862 shProg
->Name
, shProg
->InfoLog
);
869 printf("Link %u shaders in program %u: %s\n",
870 shProg
->NumShaders
, shProg
->Name
,
871 shProg
->LinkStatus
? "Success" : "Failed");
873 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
874 printf(" shader %u, type 0x%x\n",
875 shProg
->Shaders
[i
]->Name
,
876 shProg
->Shaders
[i
]->Type
);
883 * Print basic shader info (for debug).
886 print_shader_info(const struct gl_shader_program
*shProg
)
890 printf("Mesa: glUseProgram(%u)\n", shProg
->Name
);
891 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
892 printf(" %s shader %u, checksum %u\n",
893 _mesa_glsl_shader_target_name(shProg
->Shaders
[i
]->Type
),
894 shProg
->Shaders
[i
]->Name
,
895 shProg
->Shaders
[i
]->SourceChecksum
);
897 if (shProg
->_LinkedShaders
[MESA_SHADER_VERTEX
])
898 printf(" vert prog %u\n",
899 shProg
->_LinkedShaders
[MESA_SHADER_VERTEX
]->Program
->Id
);
900 if (shProg
->_LinkedShaders
[MESA_SHADER_FRAGMENT
])
901 printf(" frag prog %u\n",
902 shProg
->_LinkedShaders
[MESA_SHADER_FRAGMENT
]->Program
->Id
);
903 if (shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
])
904 printf(" geom prog %u\n",
905 shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
]->Program
->Id
);
910 * Use the named shader program for subsequent glUniform calls
913 _mesa_active_program(struct gl_context
*ctx
, struct gl_shader_program
*shProg
,
916 if ((shProg
!= NULL
) && !shProg
->LinkStatus
) {
917 _mesa_error(ctx
, GL_INVALID_OPERATION
,
918 "%s(program %u not linked)", caller
, shProg
->Name
);
922 if (ctx
->Shader
.ActiveProgram
!= shProg
) {
923 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.ActiveProgram
, shProg
);
930 use_shader_program(struct gl_context
*ctx
, GLenum type
,
931 struct gl_shader_program
*shProg
)
933 struct gl_shader_program
**target
;
936 case GL_VERTEX_SHADER
:
937 target
= &ctx
->Shader
.CurrentVertexProgram
;
939 || (shProg
->_LinkedShaders
[MESA_SHADER_VERTEX
] == NULL
)) {
943 case GL_GEOMETRY_SHADER_ARB
:
944 target
= &ctx
->Shader
.CurrentGeometryProgram
;
946 || (shProg
->_LinkedShaders
[MESA_SHADER_GEOMETRY
] == NULL
)) {
950 case GL_FRAGMENT_SHADER
:
951 target
= &ctx
->Shader
.CurrentFragmentProgram
;
953 || (shProg
->_LinkedShaders
[MESA_SHADER_FRAGMENT
] == NULL
)) {
961 if (*target
!= shProg
) {
962 FLUSH_VERTICES(ctx
, _NEW_PROGRAM
| _NEW_PROGRAM_CONSTANTS
);
964 /* If the shader is also bound as the current rendering shader, unbind
965 * it from that binding point as well. This ensures that the correct
966 * semantics of glDeleteProgram are maintained.
969 case GL_VERTEX_SHADER
:
972 case GL_GEOMETRY_SHADER_ARB
:
975 case GL_FRAGMENT_SHADER
:
976 if (*target
== ctx
->Shader
._CurrentFragmentProgram
) {
977 _mesa_reference_shader_program(ctx
,
978 &ctx
->Shader
._CurrentFragmentProgram
,
984 _mesa_reference_shader_program(ctx
, target
, shProg
);
992 * Use the named shader program for subsequent rendering.
995 _mesa_use_program(struct gl_context
*ctx
, struct gl_shader_program
*shProg
)
997 use_shader_program(ctx
, GL_VERTEX_SHADER
, shProg
);
998 use_shader_program(ctx
, GL_GEOMETRY_SHADER_ARB
, shProg
);
999 use_shader_program(ctx
, GL_FRAGMENT_SHADER
, shProg
);
1000 _mesa_active_program(ctx
, shProg
, "glUseProgram");
1002 if (ctx
->Driver
.UseProgram
)
1003 ctx
->Driver
.UseProgram(ctx
, shProg
);
1008 * Do validation of the given shader program.
1009 * \param errMsg returns error message if validation fails.
1010 * \return GL_TRUE if valid, GL_FALSE if invalid (and set errMsg)
1013 validate_shader_program(const struct gl_shader_program
*shProg
,
1016 if (!shProg
->LinkStatus
) {
1020 /* From the GL spec, a program is invalid if any of these are true:
1022 any two active samplers in the current program object are of
1023 different types, but refer to the same texture image unit,
1025 any active sampler in the current program object refers to a texture
1026 image unit where fixed-function fragment processing accesses a
1027 texture target that does not match the sampler type, or
1029 the sum of the number of active samplers in the program and the
1030 number of texture image units enabled for fixed-function fragment
1031 processing exceeds the combined limit on the total number of texture
1032 image units allowed.
1037 * Check: any two active samplers in the current program object are of
1038 * different types, but refer to the same texture image unit,
1040 if (!_mesa_sampler_uniforms_are_valid(shProg
, errMsg
, 100))
1048 * Called via glValidateProgram()
1051 validate_program(struct gl_context
*ctx
, GLuint program
)
1053 struct gl_shader_program
*shProg
;
1054 char errMsg
[100] = "";
1056 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glValidateProgram");
1061 shProg
->Validated
= validate_shader_program(shProg
, errMsg
);
1062 if (!shProg
->Validated
) {
1063 /* update info log */
1064 if (shProg
->InfoLog
) {
1065 ralloc_free(shProg
->InfoLog
);
1067 shProg
->InfoLog
= ralloc_strdup(shProg
, errMsg
);
1074 _mesa_AttachObjectARB(GLhandleARB program
, GLhandleARB shader
)
1076 GET_CURRENT_CONTEXT(ctx
);
1077 attach_shader(ctx
, program
, shader
);
1082 _mesa_AttachShader(GLuint program
, GLuint shader
)
1084 GET_CURRENT_CONTEXT(ctx
);
1085 attach_shader(ctx
, program
, shader
);
1090 _mesa_CompileShader(GLhandleARB shaderObj
)
1092 GET_CURRENT_CONTEXT(ctx
);
1093 if (MESA_VERBOSE
& VERBOSE_API
)
1094 _mesa_debug(ctx
, "glCompileShader %u\n", shaderObj
);
1095 compile_shader(ctx
, shaderObj
);
1100 _mesa_CreateShader(GLenum type
)
1102 GET_CURRENT_CONTEXT(ctx
);
1103 if (MESA_VERBOSE
& VERBOSE_API
)
1104 _mesa_debug(ctx
, "glCreateShader %s\n", _mesa_lookup_enum_by_nr(type
));
1105 return create_shader(ctx
, type
);
1109 GLhandleARB GLAPIENTRY
1110 _mesa_CreateShaderObjectARB(GLenum type
)
1112 GET_CURRENT_CONTEXT(ctx
);
1113 return create_shader(ctx
, type
);
1118 _mesa_CreateProgram(void)
1120 GET_CURRENT_CONTEXT(ctx
);
1121 if (MESA_VERBOSE
& VERBOSE_API
)
1122 _mesa_debug(ctx
, "glCreateProgram\n");
1123 return create_shader_program(ctx
);
1127 GLhandleARB GLAPIENTRY
1128 _mesa_CreateProgramObjectARB(void)
1130 GET_CURRENT_CONTEXT(ctx
);
1131 return create_shader_program(ctx
);
1136 _mesa_DeleteObjectARB(GLhandleARB obj
)
1138 if (MESA_VERBOSE
& VERBOSE_API
) {
1139 GET_CURRENT_CONTEXT(ctx
);
1140 _mesa_debug(ctx
, "glDeleteObjectARB(%u)\n", obj
);
1144 GET_CURRENT_CONTEXT(ctx
);
1145 FLUSH_VERTICES(ctx
, 0);
1146 if (is_program(ctx
, obj
)) {
1147 delete_shader_program(ctx
, obj
);
1149 else if (is_shader(ctx
, obj
)) {
1150 delete_shader(ctx
, obj
);
1160 _mesa_DeleteProgram(GLuint name
)
1163 GET_CURRENT_CONTEXT(ctx
);
1164 FLUSH_VERTICES(ctx
, 0);
1165 delete_shader_program(ctx
, name
);
1171 _mesa_DeleteShader(GLuint name
)
1174 GET_CURRENT_CONTEXT(ctx
);
1175 FLUSH_VERTICES(ctx
, 0);
1176 delete_shader(ctx
, name
);
1182 _mesa_DetachObjectARB(GLhandleARB program
, GLhandleARB shader
)
1184 GET_CURRENT_CONTEXT(ctx
);
1185 detach_shader(ctx
, program
, shader
);
1190 _mesa_DetachShader(GLuint program
, GLuint shader
)
1192 GET_CURRENT_CONTEXT(ctx
);
1193 detach_shader(ctx
, program
, shader
);
1198 _mesa_GetAttachedObjectsARB(GLhandleARB container
, GLsizei maxCount
,
1199 GLsizei
* count
, GLhandleARB
* obj
)
1201 GET_CURRENT_CONTEXT(ctx
);
1202 get_attached_shaders(ctx
, container
, maxCount
, count
, obj
);
1207 _mesa_GetAttachedShaders(GLuint program
, GLsizei maxCount
,
1208 GLsizei
*count
, GLuint
*obj
)
1210 GET_CURRENT_CONTEXT(ctx
);
1211 get_attached_shaders(ctx
, program
, maxCount
, count
, obj
);
1216 _mesa_GetInfoLogARB(GLhandleARB object
, GLsizei maxLength
, GLsizei
* length
,
1217 GLcharARB
* infoLog
)
1219 GET_CURRENT_CONTEXT(ctx
);
1220 if (is_program(ctx
, object
)) {
1221 get_program_info_log(ctx
, object
, maxLength
, length
, infoLog
);
1223 else if (is_shader(ctx
, object
)) {
1224 get_shader_info_log(ctx
, object
, maxLength
, length
, infoLog
);
1227 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glGetInfoLogARB");
1233 _mesa_GetObjectParameterivARB(GLhandleARB object
, GLenum pname
, GLint
*params
)
1235 GET_CURRENT_CONTEXT(ctx
);
1236 /* Implement in terms of GetProgramiv, GetShaderiv */
1237 if (is_program(ctx
, object
)) {
1238 if (pname
== GL_OBJECT_TYPE_ARB
) {
1239 *params
= GL_PROGRAM_OBJECT_ARB
;
1242 get_programiv(ctx
, object
, pname
, params
);
1245 else if (is_shader(ctx
, object
)) {
1246 if (pname
== GL_OBJECT_TYPE_ARB
) {
1247 *params
= GL_SHADER_OBJECT_ARB
;
1250 get_shaderiv(ctx
, object
, pname
, params
);
1254 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetObjectParameterivARB");
1260 _mesa_GetObjectParameterfvARB(GLhandleARB object
, GLenum pname
,
1263 GLint iparams
[1]; /* XXX is one element enough? */
1264 _mesa_GetObjectParameterivARB(object
, pname
, iparams
);
1265 params
[0] = (GLfloat
) iparams
[0];
1270 _mesa_GetProgramiv(GLuint program
, GLenum pname
, GLint
*params
)
1272 GET_CURRENT_CONTEXT(ctx
);
1273 get_programiv(ctx
, program
, pname
, params
);
1278 _mesa_GetShaderiv(GLuint shader
, GLenum pname
, GLint
*params
)
1280 GET_CURRENT_CONTEXT(ctx
);
1281 get_shaderiv(ctx
, shader
, pname
, params
);
1286 _mesa_GetProgramInfoLog(GLuint program
, GLsizei bufSize
,
1287 GLsizei
*length
, GLchar
*infoLog
)
1289 GET_CURRENT_CONTEXT(ctx
);
1290 get_program_info_log(ctx
, program
, bufSize
, length
, infoLog
);
1295 _mesa_GetShaderInfoLog(GLuint shader
, GLsizei bufSize
,
1296 GLsizei
*length
, GLchar
*infoLog
)
1298 GET_CURRENT_CONTEXT(ctx
);
1299 get_shader_info_log(ctx
, shader
, bufSize
, length
, infoLog
);
1304 _mesa_GetShaderSource(GLhandleARB shader
, GLsizei maxLength
,
1305 GLsizei
*length
, GLcharARB
*sourceOut
)
1307 GET_CURRENT_CONTEXT(ctx
);
1308 get_shader_source(ctx
, shader
, maxLength
, length
, sourceOut
);
1312 GLhandleARB GLAPIENTRY
1313 _mesa_GetHandleARB(GLenum pname
)
1315 GET_CURRENT_CONTEXT(ctx
);
1316 return get_handle(ctx
, pname
);
1320 GLboolean GLAPIENTRY
1321 _mesa_IsProgram(GLuint name
)
1323 GET_CURRENT_CONTEXT(ctx
);
1324 return is_program(ctx
, name
);
1328 GLboolean GLAPIENTRY
1329 _mesa_IsShader(GLuint name
)
1331 GET_CURRENT_CONTEXT(ctx
);
1332 return is_shader(ctx
, name
);
1337 _mesa_LinkProgram(GLhandleARB programObj
)
1339 GET_CURRENT_CONTEXT(ctx
);
1340 link_program(ctx
, programObj
);
1346 * Read shader source code from a file.
1347 * Useful for debugging to override an app's shader.
1350 read_shader(const char *fname
)
1352 const int max
= 50*1000;
1353 FILE *f
= fopen(fname
, "r");
1354 GLcharARB
*buffer
, *shader
;
1361 buffer
= malloc(max
);
1362 len
= fread(buffer
, 1, max
, f
);
1367 shader
= _mesa_strdup(buffer
);
1375 * Called via glShaderSource() and glShaderSourceARB() API functions.
1376 * Basically, concatenate the source code strings into one long string
1377 * and pass it to _mesa_shader_source().
1380 _mesa_ShaderSource(GLhandleARB shaderObj
, GLsizei count
,
1381 const GLcharARB
* const * string
, const GLint
* length
)
1383 GET_CURRENT_CONTEXT(ctx
);
1385 GLsizei i
, totalLength
;
1389 if (!shaderObj
|| string
== NULL
) {
1390 _mesa_error(ctx
, GL_INVALID_VALUE
, "glShaderSourceARB");
1395 * This array holds offsets of where the appropriate string ends, thus the
1396 * last element will be set to the total length of the source code.
1398 offsets
= malloc(count
* sizeof(GLint
));
1399 if (offsets
== NULL
) {
1400 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glShaderSourceARB");
1404 for (i
= 0; i
< count
; i
++) {
1405 if (string
[i
] == NULL
) {
1406 free((GLvoid
*) offsets
);
1407 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1408 "glShaderSourceARB(null string)");
1411 if (length
== NULL
|| length
[i
] < 0)
1412 offsets
[i
] = strlen(string
[i
]);
1414 offsets
[i
] = length
[i
];
1415 /* accumulate string lengths */
1417 offsets
[i
] += offsets
[i
- 1];
1420 /* Total length of source string is sum off all strings plus two.
1421 * One extra byte for terminating zero, another extra byte to silence
1422 * valgrind warnings in the parser/grammer code.
1424 totalLength
= offsets
[count
- 1] + 2;
1425 source
= malloc(totalLength
* sizeof(GLcharARB
));
1426 if (source
== NULL
) {
1427 free((GLvoid
*) offsets
);
1428 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glShaderSourceARB");
1432 for (i
= 0; i
< count
; i
++) {
1433 GLint start
= (i
> 0) ? offsets
[i
- 1] : 0;
1434 memcpy(source
+ start
, string
[i
],
1435 (offsets
[i
] - start
) * sizeof(GLcharARB
));
1437 source
[totalLength
- 1] = '\0';
1438 source
[totalLength
- 2] = '\0';
1441 /* Compute the shader's source code checksum then try to open a file
1442 * named newshader_<CHECKSUM>. If it exists, use it in place of the
1443 * original shader source code. For debugging.
1446 GLcharARB
*newSource
;
1448 checksum
= _mesa_str_checksum(source
);
1450 _mesa_snprintf(filename
, sizeof(filename
), "newshader_%d", checksum
);
1452 newSource
= read_shader(filename
);
1454 fprintf(stderr
, "Mesa: Replacing shader %u chksum=%d with %s\n",
1455 shaderObj
, checksum
, filename
);
1461 shader_source(ctx
, shaderObj
, source
);
1464 struct gl_shader
*sh
= _mesa_lookup_shader(ctx
, shaderObj
);
1466 sh
->SourceChecksum
= checksum
; /* save original checksum */
1474 _mesa_UseProgram(GLhandleARB program
)
1476 GET_CURRENT_CONTEXT(ctx
);
1477 struct gl_shader_program
*shProg
;
1479 if (_mesa_is_xfb_active_and_unpaused(ctx
)) {
1480 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1481 "glUseProgram(transform feedback active)");
1486 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glUseProgram");
1490 if (!shProg
->LinkStatus
) {
1491 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1492 "glUseProgram(program %u not linked)", program
);
1497 if (ctx
->Shader
.Flags
& GLSL_USE_PROG
) {
1498 print_shader_info(shProg
);
1505 _mesa_use_program(ctx
, shProg
);
1510 _mesa_ValidateProgram(GLhandleARB program
)
1512 GET_CURRENT_CONTEXT(ctx
);
1513 validate_program(ctx
, program
);
1518 * For OpenGL ES 2.0, GL_ARB_ES2_compatibility
1521 _mesa_GetShaderPrecisionFormat(GLenum shadertype
, GLenum precisiontype
,
1522 GLint
* range
, GLint
* precision
)
1524 const struct gl_program_constants
*limits
;
1525 const struct gl_precision
*p
;
1526 GET_CURRENT_CONTEXT(ctx
);
1528 switch (shadertype
) {
1529 case GL_VERTEX_SHADER
:
1530 limits
= &ctx
->Const
.VertexProgram
;
1532 case GL_FRAGMENT_SHADER
:
1533 limits
= &ctx
->Const
.FragmentProgram
;
1536 _mesa_error(ctx
, GL_INVALID_ENUM
,
1537 "glGetShaderPrecisionFormat(shadertype)");
1541 switch (precisiontype
) {
1543 p
= &limits
->LowFloat
;
1545 case GL_MEDIUM_FLOAT
:
1546 p
= &limits
->MediumFloat
;
1549 p
= &limits
->HighFloat
;
1552 p
= &limits
->LowInt
;
1555 p
= &limits
->MediumInt
;
1558 p
= &limits
->HighInt
;
1561 _mesa_error(ctx
, GL_INVALID_ENUM
,
1562 "glGetShaderPrecisionFormat(precisiontype)");
1566 range
[0] = p
->RangeMin
;
1567 range
[1] = p
->RangeMax
;
1568 precision
[0] = p
->Precision
;
1573 * For OpenGL ES 2.0, GL_ARB_ES2_compatibility
1576 _mesa_ReleaseShaderCompiler(void)
1578 _mesa_destroy_shader_compiler_caches();
1583 * For OpenGL ES 2.0, GL_ARB_ES2_compatibility
1586 _mesa_ShaderBinary(GLint n
, const GLuint
* shaders
, GLenum binaryformat
,
1587 const void* binary
, GLint length
)
1589 GET_CURRENT_CONTEXT(ctx
);
1592 (void) binaryformat
;
1595 _mesa_error(ctx
, GL_INVALID_OPERATION
, __FUNCTION__
);
1600 _mesa_GetProgramBinary(GLuint program
, GLsizei bufSize
, GLsizei
*length
,
1601 GLenum
*binaryFormat
, GLvoid
*binary
)
1603 struct gl_shader_program
*shProg
;
1604 GET_CURRENT_CONTEXT(ctx
);
1606 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glGetProgramBinary");
1610 if (!shProg
->LinkStatus
) {
1611 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1612 "glGetProgramBinary(program %u not linked)",
1618 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramBinary(bufSize < 0)");
1622 /* The ARB_get_program_binary spec says:
1624 * "If <length> is NULL, then no length is returned."
1629 (void) binaryFormat
;
1634 _mesa_ProgramBinary(GLuint program
, GLenum binaryFormat
,
1635 const GLvoid
*binary
, GLsizei length
)
1637 struct gl_shader_program
*shProg
;
1638 GET_CURRENT_CONTEXT(ctx
);
1640 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glProgramBinary");
1644 (void) binaryFormat
;
1647 _mesa_error(ctx
, GL_INVALID_OPERATION
, __FUNCTION__
);
1652 _mesa_ProgramParameteri(GLuint program
, GLenum pname
, GLint value
)
1654 struct gl_shader_program
*shProg
;
1655 GET_CURRENT_CONTEXT(ctx
);
1657 shProg
= _mesa_lookup_shader_program_err(ctx
, program
,
1658 "glProgramParameteri");
1663 case GL_PROGRAM_BINARY_RETRIEVABLE_HINT
:
1664 /* This enum isn't part of the OES extension for OpenGL ES 2.0, but it
1665 * is part of OpenGL ES 3.0. For the ES2 case, this function shouldn't
1666 * even be in the dispatch table, so we shouldn't need to expclicitly
1669 * On desktop, we ignore the 3.0+ requirement because it is silly.
1672 /* The ARB_get_program_binary extension spec says:
1674 * "An INVALID_VALUE error is generated if the <value> argument to
1675 * ProgramParameteri is not TRUE or FALSE."
1677 if (value
!= GL_TRUE
&& value
!= GL_FALSE
) {
1678 _mesa_error(ctx
, GL_INVALID_VALUE
,
1679 "glProgramParameteri(pname=%s, value=%d): "
1680 "value must be 0 or 1.",
1681 _mesa_lookup_enum_by_nr(pname
),
1686 /* No need to notify the driver. Any changes will actually take effect
1687 * the next time the shader is linked.
1689 * The ARB_get_program_binary extension spec says:
1691 * "To indicate that a program binary is likely to be retrieved,
1692 * ProgramParameteri should be called with <pname>
1693 * PROGRAM_BINARY_RETRIEVABLE_HINT and <value> TRUE. This setting
1694 * will not be in effect until the next time LinkProgram or
1695 * ProgramBinary has been called successfully."
1697 * The resloution of issue 9 in the extension spec also says:
1699 * "The application may use the PROGRAM_BINARY_RETRIEVABLE_HINT hint
1700 * to indicate to the GL implementation that this program will
1701 * likely be saved with GetProgramBinary at some point. This will
1702 * give the GL implementation the opportunity to track any state
1703 * changes made to the program before being saved such that when it
1704 * is loaded again a recompile can be avoided."
1706 shProg
->BinaryRetreivableHint
= value
;
1712 _mesa_error(ctx
, GL_INVALID_ENUM
, "glProgramParameteri(pname=%s)",
1713 _mesa_lookup_enum_by_nr(pname
));
1717 _mesa_use_shader_program(struct gl_context
*ctx
, GLenum type
,
1718 struct gl_shader_program
*shProg
)
1720 use_shader_program(ctx
, type
, shProg
);
1722 if (ctx
->Driver
.UseProgram
)
1723 ctx
->Driver
.UseProgram(ctx
, shProg
);
1728 * For GL_EXT_separate_shader_objects
1731 _mesa_UseShaderProgramEXT(GLenum type
, GLuint program
)
1733 GET_CURRENT_CONTEXT(ctx
);
1734 struct gl_shader_program
*shProg
= NULL
;
1736 if (!validate_shader_target(ctx
, type
)) {
1737 _mesa_error(ctx
, GL_INVALID_ENUM
, "glUseShaderProgramEXT(type)");
1741 if (_mesa_is_xfb_active_and_unpaused(ctx
)) {
1742 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1743 "glUseShaderProgramEXT(transform feedback is active)");
1748 shProg
= _mesa_lookup_shader_program_err(ctx
, program
,
1749 "glUseShaderProgramEXT");
1753 if (!shProg
->LinkStatus
) {
1754 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1755 "glUseShaderProgramEXT(program not linked)");
1760 _mesa_use_shader_program(ctx
, type
, shProg
);
1765 * For GL_EXT_separate_shader_objects
1768 _mesa_ActiveProgramEXT(GLuint program
)
1770 GET_CURRENT_CONTEXT(ctx
);
1771 struct gl_shader_program
*shProg
= (program
!= 0)
1772 ? _mesa_lookup_shader_program_err(ctx
, program
, "glActiveProgramEXT")
1775 _mesa_active_program(ctx
, shProg
, "glActiveProgramEXT");
1781 * For GL_EXT_separate_shader_objects
1784 _mesa_CreateShaderProgramEXT(GLenum type
, const GLchar
*string
)
1786 GET_CURRENT_CONTEXT(ctx
);
1787 const GLuint shader
= create_shader(ctx
, type
);
1791 shader_source(ctx
, shader
, _mesa_strdup(string
));
1792 compile_shader(ctx
, shader
);
1794 program
= create_shader_program(ctx
);
1796 struct gl_shader_program
*shProg
;
1797 struct gl_shader
*sh
;
1798 GLint compiled
= GL_FALSE
;
1800 shProg
= _mesa_lookup_shader_program(ctx
, program
);
1801 sh
= _mesa_lookup_shader(ctx
, shader
);
1803 get_shaderiv(ctx
, shader
, GL_COMPILE_STATUS
, &compiled
);
1805 attach_shader(ctx
, program
, shader
);
1806 link_program(ctx
, program
);
1807 detach_shader(ctx
, program
, shader
);
1811 if (active
-user
-defined
-varyings
-in
-linked
-program
) {
1812 append
-error
-to
-info
-log
;
1813 shProg
->LinkStatus
= GL_FALSE
;
1818 ralloc_strcat(&shProg
->InfoLog
, sh
->InfoLog
);
1821 delete_shader(ctx
, shader
);
1829 * Copy program-specific data generated by linking from the gl_shader_program
1830 * object to a specific gl_program object.
1833 _mesa_copy_linked_program_data(gl_shader_type type
,
1834 const struct gl_shader_program
*src
,
1835 struct gl_program
*dst
)
1838 case MESA_SHADER_VERTEX
:
1839 dst
->UsesClipDistanceOut
= src
->Vert
.UsesClipDistance
;
1841 case MESA_SHADER_GEOMETRY
: {
1842 struct gl_geometry_program
*dst_gp
= (struct gl_geometry_program
*) dst
;
1843 dst_gp
->VerticesIn
= src
->Geom
.VerticesIn
;
1844 dst_gp
->VerticesOut
= src
->Geom
.VerticesOut
;
1845 dst_gp
->InputType
= src
->Geom
.InputType
;
1846 dst_gp
->OutputType
= src
->Geom
.OutputType
;
1847 dst
->UsesClipDistanceOut
= src
->Geom
.UsesClipDistance
;
1848 dst_gp
->UsesEndPrimitive
= src
->Geom
.UsesEndPrimitive
;