2 * Mesa 3-D graphics library
5 * Copyright (C) 2004-2008 Brian Paul All Rights Reserved.
6 * Copyright (C) 2009 VMware, Inc. All Rights Reserved.
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 * Implementation of GLSL-related API functions
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/hash.h"
42 #include "main/macros.h"
43 #include "shader/program.h"
44 #include "shader/prog_parameter.h"
45 #include "shader/prog_print.h"
46 #include "shader/prog_statevars.h"
47 #include "shader/prog_uniform.h"
48 #include "shader/shader_api.h"
49 #include "shader/slang/slang_compile.h"
50 #include "shader/slang/slang_link.h"
51 #include "glapi/dispatch.h"
55 * Allocate a new gl_shader_program object, initialize it.
57 static struct gl_shader_program
*
58 _mesa_new_shader_program(GLcontext
*ctx
, GLuint name
)
60 struct gl_shader_program
*shProg
;
61 shProg
= CALLOC_STRUCT(gl_shader_program
);
63 shProg
->Type
= GL_SHADER_PROGRAM_MESA
;
66 shProg
->Attributes
= _mesa_new_parameter_list();
73 * Clear (free) the shader program state that gets produced by linking.
76 _mesa_clear_shader_program_data(GLcontext
*ctx
,
77 struct gl_shader_program
*shProg
)
79 _mesa_reference_vertprog(ctx
, &shProg
->VertexProgram
, NULL
);
80 _mesa_reference_fragprog(ctx
, &shProg
->FragmentProgram
, NULL
);
82 if (shProg
->Uniforms
) {
83 _mesa_free_uniform_list(shProg
->Uniforms
);
84 shProg
->Uniforms
= NULL
;
87 if (shProg
->Varying
) {
88 _mesa_free_parameter_list(shProg
->Varying
);
89 shProg
->Varying
= NULL
;
95 * Free all the data that hangs off a shader program object, but not the
99 _mesa_free_shader_program_data(GLcontext
*ctx
,
100 struct gl_shader_program
*shProg
)
104 assert(shProg
->Type
== GL_SHADER_PROGRAM_MESA
);
106 _mesa_clear_shader_program_data(ctx
, shProg
);
108 if (shProg
->Attributes
) {
109 _mesa_free_parameter_list(shProg
->Attributes
);
110 shProg
->Attributes
= NULL
;
114 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
115 _mesa_reference_shader(ctx
, &shProg
->Shaders
[i
], NULL
);
117 shProg
->NumShaders
= 0;
119 if (shProg
->Shaders
) {
120 _mesa_free(shProg
->Shaders
);
121 shProg
->Shaders
= NULL
;
124 if (shProg
->InfoLog
) {
125 _mesa_free(shProg
->InfoLog
);
126 shProg
->InfoLog
= NULL
;
132 * Free/delete a shader program object.
135 _mesa_free_shader_program(GLcontext
*ctx
, struct gl_shader_program
*shProg
)
137 _mesa_free_shader_program_data(ctx
, shProg
);
144 * Set ptr to point to shProg.
145 * If ptr is pointing to another object, decrement its refcount (and delete
146 * if refcount hits zero).
147 * Then set ptr to point to shProg, incrementing its refcount.
149 /* XXX this could be static */
151 _mesa_reference_shader_program(GLcontext
*ctx
,
152 struct gl_shader_program
**ptr
,
153 struct gl_shader_program
*shProg
)
156 if (*ptr
== shProg
) {
161 /* Unreference the old shader program */
162 GLboolean deleteFlag
= GL_FALSE
;
163 struct gl_shader_program
*old
= *ptr
;
165 ASSERT(old
->RefCount
> 0);
168 printf("ShaderProgram %p ID=%u RefCount-- to %d\n",
169 (void *) old
, old
->Name
, old
->RefCount
);
171 deleteFlag
= (old
->RefCount
== 0);
174 _mesa_HashRemove(ctx
->Shared
->ShaderObjects
, old
->Name
);
175 _mesa_free_shader_program(ctx
, old
);
185 printf("ShaderProgram %p ID=%u RefCount++ to %d\n",
186 (void *) shProg
, shProg
->Name
, shProg
->RefCount
);
194 * Lookup a GLSL program object.
196 struct gl_shader_program
*
197 _mesa_lookup_shader_program(GLcontext
*ctx
, GLuint name
)
199 struct gl_shader_program
*shProg
;
201 shProg
= (struct gl_shader_program
*)
202 _mesa_HashLookup(ctx
->Shared
->ShaderObjects
, name
);
203 /* Note that both gl_shader and gl_shader_program objects are kept
204 * in the same hash table. Check the object's type to be sure it's
205 * what we're expecting.
207 if (shProg
&& shProg
->Type
!= GL_SHADER_PROGRAM_MESA
) {
217 * As above, but record an error if program is not found.
219 static struct gl_shader_program
*
220 _mesa_lookup_shader_program_err(GLcontext
*ctx
, GLuint name
,
224 _mesa_error(ctx
, GL_INVALID_VALUE
, caller
);
228 struct gl_shader_program
*shProg
= (struct gl_shader_program
*)
229 _mesa_HashLookup(ctx
->Shared
->ShaderObjects
, name
);
231 _mesa_error(ctx
, GL_INVALID_VALUE
, caller
);
234 if (shProg
->Type
!= GL_SHADER_PROGRAM_MESA
) {
235 _mesa_error(ctx
, GL_INVALID_OPERATION
, caller
);
246 * Allocate a new gl_shader object, initialize it.
249 _mesa_new_shader(GLcontext
*ctx
, GLuint name
, GLenum type
)
251 struct gl_shader
*shader
;
252 assert(type
== GL_FRAGMENT_SHADER
|| type
== GL_VERTEX_SHADER
);
253 shader
= CALLOC_STRUCT(gl_shader
);
257 shader
->RefCount
= 1;
264 _mesa_free_shader(GLcontext
*ctx
, struct gl_shader
*sh
)
267 _mesa_free((void *) sh
->Source
);
269 _mesa_free(sh
->InfoLog
);
270 _mesa_reference_program(ctx
, &sh
->Program
, NULL
);
276 * Set ptr to point to sh.
277 * If ptr is pointing to another shader, decrement its refcount (and delete
278 * if refcount hits zero).
279 * Then set ptr to point to sh, incrementing its refcount.
281 /* XXX this could be static */
283 _mesa_reference_shader(GLcontext
*ctx
, struct gl_shader
**ptr
,
284 struct gl_shader
*sh
)
292 /* Unreference the old shader */
293 GLboolean deleteFlag
= GL_FALSE
;
294 struct gl_shader
*old
= *ptr
;
296 ASSERT(old
->RefCount
> 0);
298 /*printf("SHADER DECR %p (%d) to %d\n",
299 (void*) old, old->Name, old->RefCount);*/
300 deleteFlag
= (old
->RefCount
== 0);
303 _mesa_HashRemove(ctx
->Shared
->ShaderObjects
, old
->Name
);
304 _mesa_free_shader(ctx
, old
);
314 /*printf("SHADER INCR %p (%d) to %d\n",
315 (void*) sh, sh->Name, sh->RefCount);*/
322 * Lookup a GLSL shader object.
325 _mesa_lookup_shader(GLcontext
*ctx
, GLuint name
)
328 struct gl_shader
*sh
= (struct gl_shader
*)
329 _mesa_HashLookup(ctx
->Shared
->ShaderObjects
, name
);
330 /* Note that both gl_shader and gl_shader_program objects are kept
331 * in the same hash table. Check the object's type to be sure it's
332 * what we're expecting.
334 if (sh
&& sh
->Type
== GL_SHADER_PROGRAM_MESA
) {
344 * As above, but record an error if shader is not found.
346 static struct gl_shader
*
347 _mesa_lookup_shader_err(GLcontext
*ctx
, GLuint name
, const char *caller
)
350 _mesa_error(ctx
, GL_INVALID_VALUE
, caller
);
354 struct gl_shader
*sh
= (struct gl_shader
*)
355 _mesa_HashLookup(ctx
->Shared
->ShaderObjects
, name
);
357 _mesa_error(ctx
, GL_INVALID_VALUE
, caller
);
360 if (sh
->Type
== GL_SHADER_PROGRAM_MESA
) {
361 _mesa_error(ctx
, GL_INVALID_OPERATION
, caller
);
370 * Return mask of GLSL_x flags by examining the MESA_GLSL env var.
373 get_shader_flags(void)
375 GLbitfield flags
= 0x0;
376 const char *env
= _mesa_getenv("MESA_GLSL");
379 if (_mesa_strstr(env
, "dump"))
381 if (_mesa_strstr(env
, "log"))
383 if (_mesa_strstr(env
, "nopvert"))
384 flags
|= GLSL_NOP_VERT
;
385 if (_mesa_strstr(env
, "nopfrag"))
386 flags
|= GLSL_NOP_FRAG
;
387 if (_mesa_strstr(env
, "nopt"))
388 flags
|= GLSL_NO_OPT
;
389 else if (_mesa_strstr(env
, "opt"))
391 if (_mesa_strstr(env
, "uniform"))
392 flags
|= GLSL_UNIFORMS
;
400 * Initialize context's shader state.
403 _mesa_init_shader_state(GLcontext
* ctx
)
405 /* Device drivers may override these to control what kind of instructions
406 * are generated by the GLSL compiler.
408 ctx
->Shader
.EmitHighLevelInstructions
= GL_TRUE
;
409 ctx
->Shader
.EmitContReturn
= GL_TRUE
;
410 ctx
->Shader
.EmitCondCodes
= GL_FALSE
;
411 ctx
->Shader
.EmitComments
= GL_FALSE
;
412 ctx
->Shader
.Flags
= get_shader_flags();
414 /* Default pragma settings */
415 ctx
->Shader
.DefaultPragmas
.IgnoreOptimize
= GL_FALSE
;
416 ctx
->Shader
.DefaultPragmas
.IgnoreDebug
= GL_FALSE
;
417 ctx
->Shader
.DefaultPragmas
.Optimize
= GL_TRUE
;
418 ctx
->Shader
.DefaultPragmas
.Debug
= GL_FALSE
;
423 * Free the per-context shader-related state.
426 _mesa_free_shader_state(GLcontext
*ctx
)
428 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentProgram
, NULL
);
433 * Copy string from <src> to <dst>, up to maxLength characters, returning
434 * length of <dst> in <length>.
435 * \param src the strings source
436 * \param maxLength max chars to copy
437 * \param length returns number of chars copied
438 * \param dst the string destination
441 copy_string(GLchar
*dst
, GLsizei maxLength
, GLsizei
*length
, const GLchar
*src
)
444 for (len
= 0; len
< maxLength
- 1 && src
&& src
[len
]; len
++)
454 _mesa_is_program(GLcontext
*ctx
, GLuint name
)
456 struct gl_shader_program
*shProg
= _mesa_lookup_shader_program(ctx
, name
);
457 return shProg
? GL_TRUE
: GL_FALSE
;
462 _mesa_is_shader(GLcontext
*ctx
, GLuint name
)
464 struct gl_shader
*shader
= _mesa_lookup_shader(ctx
, name
);
465 return shader
? GL_TRUE
: GL_FALSE
;
470 * Called via ctx->Driver.AttachShader()
473 _mesa_attach_shader(GLcontext
*ctx
, GLuint program
, GLuint shader
)
475 struct gl_shader_program
*shProg
;
476 struct gl_shader
*sh
;
479 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glAttachShader");
483 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glAttachShader");
488 n
= shProg
->NumShaders
;
489 for (i
= 0; i
< n
; i
++) {
490 if (shProg
->Shaders
[i
] == sh
) {
491 /* The shader is already attched to this program. The
492 * GL_ARB_shader_objects spec says:
494 * "The error INVALID_OPERATION is generated by AttachObjectARB
495 * if <obj> is already attached to <containerObj>."
497 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glAttachShader");
503 shProg
->Shaders
= (struct gl_shader
**)
504 _mesa_realloc(shProg
->Shaders
,
505 n
* sizeof(struct gl_shader
*),
506 (n
+ 1) * sizeof(struct gl_shader
*));
507 if (!shProg
->Shaders
) {
508 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glAttachShader");
513 shProg
->Shaders
[n
] = NULL
; /* since realloc() didn't zero the new space */
514 _mesa_reference_shader(ctx
, &shProg
->Shaders
[n
], sh
);
515 shProg
->NumShaders
++;
520 _mesa_get_attrib_location(GLcontext
*ctx
, GLuint program
,
523 struct gl_shader_program
*shProg
524 = _mesa_lookup_shader_program_err(ctx
, program
, "glGetAttribLocation");
530 if (!shProg
->LinkStatus
) {
531 _mesa_error(ctx
, GL_INVALID_OPERATION
,
532 "glGetAttribLocation(program not linked)");
539 if (shProg
->VertexProgram
) {
540 const struct gl_program_parameter_list
*attribs
=
541 shProg
->VertexProgram
->Base
.Attributes
;
543 GLint i
= _mesa_lookup_parameter_index(attribs
, -1, name
);
545 return attribs
->Parameters
[i
].StateIndexes
[0];
554 _mesa_bind_attrib_location(GLcontext
*ctx
, GLuint program
, GLuint index
,
557 struct gl_shader_program
*shProg
;
558 const GLint size
= -1; /* unknown size */
560 GLenum datatype
= GL_FLOAT_VEC4
;
562 shProg
= _mesa_lookup_shader_program_err(ctx
, program
,
563 "glBindAttribLocation");
571 if (strncmp(name
, "gl_", 3) == 0) {
572 _mesa_error(ctx
, GL_INVALID_OPERATION
,
573 "glBindAttribLocation(illegal name)");
577 if (index
>= ctx
->Const
.VertexProgram
.MaxAttribs
) {
578 _mesa_error(ctx
, GL_INVALID_VALUE
, "glBindAttribLocation(index)");
582 if (shProg
->LinkStatus
) {
583 /* get current index/location for the attribute */
584 oldIndex
= _mesa_get_attrib_location(ctx
, program
, name
);
590 /* this will replace the current value if it's already in the list */
591 i
= _mesa_add_attribute(shProg
->Attributes
, name
, size
, datatype
, index
);
593 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glBindAttribLocation");
598 * Note that this attribute binding won't go into effect until
599 * glLinkProgram is called again.
605 _mesa_create_shader(GLcontext
*ctx
, GLenum type
)
607 struct gl_shader
*sh
;
610 name
= _mesa_HashFindFreeKeyBlock(ctx
->Shared
->ShaderObjects
, 1);
613 case GL_FRAGMENT_SHADER
:
614 case GL_VERTEX_SHADER
:
615 sh
= _mesa_new_shader(ctx
, name
, type
);
618 _mesa_error(ctx
, GL_INVALID_ENUM
, "CreateShader(type)");
622 _mesa_HashInsert(ctx
->Shared
->ShaderObjects
, name
, sh
);
629 _mesa_create_program(GLcontext
*ctx
)
632 struct gl_shader_program
*shProg
;
634 name
= _mesa_HashFindFreeKeyBlock(ctx
->Shared
->ShaderObjects
, 1);
635 shProg
= _mesa_new_shader_program(ctx
, name
);
637 _mesa_HashInsert(ctx
->Shared
->ShaderObjects
, name
, shProg
);
639 assert(shProg
->RefCount
== 1);
646 * Named w/ "2" to indicate OpenGL 2.x vs GL_ARB_fragment_programs's
650 _mesa_delete_program2(GLcontext
*ctx
, GLuint name
)
653 * NOTE: deleting shaders/programs works a bit differently than
654 * texture objects (and buffer objects, etc). Shader/program
655 * handles/IDs exist in the hash table until the object is really
656 * deleted (refcount==0). With texture objects, the handle/ID is
657 * removed from the hash table in glDeleteTextures() while the tex
658 * object itself might linger until its refcount goes to zero.
660 struct gl_shader_program
*shProg
;
662 shProg
= _mesa_lookup_shader_program_err(ctx
, name
, "glDeleteProgram");
666 shProg
->DeletePending
= GL_TRUE
;
668 /* effectively, decr shProg's refcount */
669 _mesa_reference_shader_program(ctx
, &shProg
, NULL
);
674 _mesa_delete_shader(GLcontext
*ctx
, GLuint shader
)
676 struct gl_shader
*sh
;
678 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glDeleteShader");
682 sh
->DeletePending
= GL_TRUE
;
684 /* effectively, decr sh's refcount */
685 _mesa_reference_shader(ctx
, &sh
, NULL
);
690 _mesa_detach_shader(GLcontext
*ctx
, GLuint program
, GLuint shader
)
692 struct gl_shader_program
*shProg
;
696 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glDetachShader");
700 n
= shProg
->NumShaders
;
702 for (i
= 0; i
< n
; i
++) {
703 if (shProg
->Shaders
[i
]->Name
== shader
) {
705 struct gl_shader
**newList
;
708 _mesa_reference_shader(ctx
, &shProg
->Shaders
[i
], NULL
);
710 /* alloc new, smaller array */
711 newList
= (struct gl_shader
**)
712 _mesa_malloc((n
- 1) * sizeof(struct gl_shader
*));
714 _mesa_error(ctx
, GL_OUT_OF_MEMORY
, "glDetachShader");
717 for (j
= 0; j
< i
; j
++) {
718 newList
[j
] = shProg
->Shaders
[j
];
721 newList
[j
++] = shProg
->Shaders
[i
];
722 _mesa_free(shProg
->Shaders
);
724 shProg
->Shaders
= newList
;
725 shProg
->NumShaders
= n
- 1;
730 for (j
= 0; j
< shProg
->NumShaders
; j
++) {
731 assert(shProg
->Shaders
[j
]->Type
== GL_VERTEX_SHADER
||
732 shProg
->Shaders
[j
]->Type
== GL_FRAGMENT_SHADER
);
733 assert(shProg
->Shaders
[j
]->RefCount
> 0);
745 if (_mesa_is_shader(ctx
, shader
))
746 err
= GL_INVALID_OPERATION
;
747 else if (_mesa_is_program(ctx
, shader
))
748 err
= GL_INVALID_OPERATION
;
750 err
= GL_INVALID_VALUE
;
751 _mesa_error(ctx
, err
, "glDetachProgram(shader)");
758 sizeof_glsl_type(GLenum type
)
767 case GL_SAMPLER_CUBE
:
768 case GL_SAMPLER_1D_SHADOW
:
769 case GL_SAMPLER_2D_SHADOW
:
770 case GL_SAMPLER_2D_RECT_ARB
:
771 case GL_SAMPLER_2D_RECT_SHADOW_ARB
:
772 case GL_SAMPLER_1D_ARRAY_SHADOW_EXT
:
773 case GL_SAMPLER_2D_ARRAY_SHADOW_EXT
:
774 case GL_SAMPLER_CUBE_SHADOW_EXT
:
789 case GL_FLOAT_MAT2x3
:
790 case GL_FLOAT_MAT2x4
:
791 return 8; /* two float[4] vectors */
793 case GL_FLOAT_MAT3x2
:
794 case GL_FLOAT_MAT3x4
:
795 return 12; /* three float[4] vectors */
797 case GL_FLOAT_MAT4x2
:
798 case GL_FLOAT_MAT4x3
:
799 return 16; /* four float[4] vectors */
801 _mesa_problem(NULL
, "Invalid type in sizeof_glsl_type()");
808 is_boolean_type(GLenum type
)
823 is_integer_type(GLenum type
)
838 is_sampler_type(GLenum type
)
844 case GL_SAMPLER_CUBE
:
845 case GL_SAMPLER_1D_SHADOW
:
846 case GL_SAMPLER_2D_SHADOW
:
847 case GL_SAMPLER_2D_RECT_ARB
:
848 case GL_SAMPLER_2D_RECT_SHADOW_ARB
:
849 case GL_SAMPLER_1D_ARRAY_EXT
:
850 case GL_SAMPLER_2D_ARRAY_EXT
:
859 _mesa_get_active_attrib(GLcontext
*ctx
, GLuint program
, GLuint index
,
860 GLsizei maxLength
, GLsizei
*length
, GLint
*size
,
861 GLenum
*type
, GLchar
*nameOut
)
863 const struct gl_program_parameter_list
*attribs
= NULL
;
864 struct gl_shader_program
*shProg
;
866 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glGetActiveAttrib");
870 if (shProg
->VertexProgram
)
871 attribs
= shProg
->VertexProgram
->Base
.Attributes
;
873 if (!attribs
|| index
>= attribs
->NumParameters
) {
874 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetActiveAttrib(index)");
878 copy_string(nameOut
, maxLength
, length
, attribs
->Parameters
[index
].Name
);
881 *size
= attribs
->Parameters
[index
].Size
882 / sizeof_glsl_type(attribs
->Parameters
[index
].DataType
);
885 *type
= attribs
->Parameters
[index
].DataType
;
889 static struct gl_program_parameter
*
890 get_uniform_parameter(const struct gl_shader_program
*shProg
, GLuint index
)
892 const struct gl_program
*prog
= NULL
;
895 progPos
= shProg
->Uniforms
->Uniforms
[index
].VertPos
;
897 prog
= &shProg
->VertexProgram
->Base
;
900 progPos
= shProg
->Uniforms
->Uniforms
[index
].FragPos
;
902 prog
= &shProg
->FragmentProgram
->Base
;
906 if (!prog
|| progPos
< 0)
907 return NULL
; /* should never happen */
909 return &prog
->Parameters
->Parameters
[progPos
];
914 * Called via ctx->Driver.GetActiveUniform().
917 _mesa_get_active_uniform(GLcontext
*ctx
, GLuint program
, GLuint index
,
918 GLsizei maxLength
, GLsizei
*length
, GLint
*size
,
919 GLenum
*type
, GLchar
*nameOut
)
921 const struct gl_shader_program
*shProg
;
922 const struct gl_program
*prog
= NULL
;
923 const struct gl_program_parameter
*param
;
926 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glGetActiveUniform");
930 if (!shProg
->Uniforms
|| index
>= shProg
->Uniforms
->NumUniforms
) {
931 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetActiveUniform(index)");
935 progPos
= shProg
->Uniforms
->Uniforms
[index
].VertPos
;
937 prog
= &shProg
->VertexProgram
->Base
;
940 progPos
= shProg
->Uniforms
->Uniforms
[index
].FragPos
;
942 prog
= &shProg
->FragmentProgram
->Base
;
946 if (!prog
|| progPos
< 0)
947 return; /* should never happen */
949 ASSERT(progPos
< prog
->Parameters
->NumParameters
);
950 param
= &prog
->Parameters
->Parameters
[progPos
];
953 copy_string(nameOut
, maxLength
, length
, param
->Name
);
957 GLint typeSize
= sizeof_glsl_type(param
->DataType
);
958 if (param
->Size
> typeSize
) {
960 * Array elements are placed on vector[4] boundaries so they're
961 * a multiple of four floats. We round typeSize up to next multiple
962 * of four to get the right size below.
964 typeSize
= (typeSize
+ 3) & ~3;
966 /* Note that the returned size is in units of the <type>, not bytes */
967 *size
= param
->Size
/ typeSize
;
971 *type
= param
->DataType
;
977 * Called via ctx->Driver.GetAttachedShaders().
980 _mesa_get_attached_shaders(GLcontext
*ctx
, GLuint program
, GLsizei maxCount
,
981 GLsizei
*count
, GLuint
*obj
)
983 struct gl_shader_program
*shProg
=
984 _mesa_lookup_shader_program_err(ctx
, program
, "glGetAttachedShaders");
987 for (i
= 0; i
< (GLuint
) maxCount
&& i
< shProg
->NumShaders
; i
++) {
988 obj
[i
] = shProg
->Shaders
[i
]->Name
;
997 _mesa_get_handle(GLcontext
*ctx
, GLenum pname
)
1001 if (pname
== GL_PROGRAM_OBJECT_ARB
) {
1002 CALL_GetIntegerv(ctx
->Exec
, (GL_CURRENT_PROGRAM
, &handle
));
1004 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetHandleARB");
1012 _mesa_get_programiv(GLcontext
*ctx
, GLuint program
,
1013 GLenum pname
, GLint
*params
)
1015 const struct gl_program_parameter_list
*attribs
;
1016 struct gl_shader_program
*shProg
1017 = _mesa_lookup_shader_program(ctx
, program
);
1020 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramiv(program)");
1024 if (shProg
->VertexProgram
)
1025 attribs
= shProg
->VertexProgram
->Base
.Attributes
;
1030 case GL_DELETE_STATUS
:
1031 *params
= shProg
->DeletePending
;
1033 case GL_LINK_STATUS
:
1034 *params
= shProg
->LinkStatus
;
1036 case GL_VALIDATE_STATUS
:
1037 *params
= shProg
->Validated
;
1039 case GL_INFO_LOG_LENGTH
:
1040 *params
= shProg
->InfoLog
? strlen(shProg
->InfoLog
) + 1 : 0;
1042 case GL_ATTACHED_SHADERS
:
1043 *params
= shProg
->NumShaders
;
1045 case GL_ACTIVE_ATTRIBUTES
:
1046 *params
= attribs
? attribs
->NumParameters
: 0;
1048 case GL_ACTIVE_ATTRIBUTE_MAX_LENGTH
:
1049 *params
= _mesa_longest_parameter_name(attribs
, PROGRAM_INPUT
) + 1;
1051 case GL_ACTIVE_UNIFORMS
:
1052 *params
= shProg
->Uniforms
? shProg
->Uniforms
->NumUniforms
: 0;
1054 case GL_ACTIVE_UNIFORM_MAX_LENGTH
:
1055 *params
= _mesa_longest_uniform_name(shProg
->Uniforms
);
1057 (*params
)++; /* add one for terminating zero */
1059 case GL_PROGRAM_BINARY_LENGTH_OES
:
1063 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetProgramiv(pname)");
1070 _mesa_get_shaderiv(GLcontext
*ctx
, GLuint name
, GLenum pname
, GLint
*params
)
1072 struct gl_shader
*shader
= _mesa_lookup_shader_err(ctx
, name
, "glGetShaderiv");
1079 case GL_SHADER_TYPE
:
1080 *params
= shader
->Type
;
1082 case GL_DELETE_STATUS
:
1083 *params
= shader
->DeletePending
;
1085 case GL_COMPILE_STATUS
:
1086 *params
= shader
->CompileStatus
;
1088 case GL_INFO_LOG_LENGTH
:
1089 *params
= shader
->InfoLog
? strlen(shader
->InfoLog
) + 1 : 0;
1091 case GL_SHADER_SOURCE_LENGTH
:
1092 *params
= shader
->Source
? strlen((char *) shader
->Source
) + 1 : 0;
1095 _mesa_error(ctx
, GL_INVALID_ENUM
, "glGetShaderiv(pname)");
1102 _mesa_get_program_info_log(GLcontext
*ctx
, GLuint program
, GLsizei bufSize
,
1103 GLsizei
*length
, GLchar
*infoLog
)
1105 struct gl_shader_program
*shProg
1106 = _mesa_lookup_shader_program(ctx
, program
);
1108 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetProgramInfoLog(program)");
1111 copy_string(infoLog
, bufSize
, length
, shProg
->InfoLog
);
1116 _mesa_get_shader_info_log(GLcontext
*ctx
, GLuint shader
, GLsizei bufSize
,
1117 GLsizei
*length
, GLchar
*infoLog
)
1119 struct gl_shader
*sh
= _mesa_lookup_shader(ctx
, shader
);
1121 _mesa_error(ctx
, GL_INVALID_VALUE
, "glGetShaderInfoLog(shader)");
1124 copy_string(infoLog
, bufSize
, length
, sh
->InfoLog
);
1129 * Called via ctx->Driver.GetShaderSource().
1132 _mesa_get_shader_source(GLcontext
*ctx
, GLuint shader
, GLsizei maxLength
,
1133 GLsizei
*length
, GLchar
*sourceOut
)
1135 struct gl_shader
*sh
;
1136 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glGetShaderSource");
1140 copy_string(sourceOut
, maxLength
, length
, sh
->Source
);
1145 get_matrix_dims(GLenum type
, GLint
*rows
, GLint
*cols
)
1151 case GL_FLOAT_MAT2x3
:
1155 case GL_FLOAT_MAT2x4
:
1163 case GL_FLOAT_MAT3x2
:
1167 case GL_FLOAT_MAT3x4
:
1175 case GL_FLOAT_MAT4x2
:
1179 case GL_FLOAT_MAT4x3
:
1190 * Determine the number of rows and columns occupied by a uniform
1191 * according to its datatype. For non-matrix types (such as GL_FLOAT_VEC4),
1192 * the number of rows = 1 and cols = number of elements in the vector.
1195 get_uniform_rows_cols(const struct gl_program_parameter
*p
,
1196 GLint
*rows
, GLint
*cols
)
1198 get_matrix_dims(p
->DataType
, rows
, cols
);
1199 if (*rows
== 0 && *cols
== 0) {
1200 /* not a matrix type, probably a float or vector */
1206 *rows
= p
->Size
/ 4 + 1;
1207 if (p
->Size
% 4 == 0)
1210 *cols
= p
->Size
% 4;
1217 * Helper for get_uniform[fi]v() functions.
1218 * Given a shader program name and uniform location, return a pointer
1219 * to the shader program and return the program parameter position.
1222 lookup_uniform_parameter(GLcontext
*ctx
, GLuint program
, GLint location
,
1223 struct gl_program
**progOut
, GLint
*paramPosOut
)
1225 struct gl_shader_program
*shProg
1226 = _mesa_lookup_shader_program_err(ctx
, program
, "glGetUniform[if]v");
1227 struct gl_program
*prog
= NULL
;
1230 /* if shProg is NULL, we'll have already recorded an error */
1233 if (!shProg
->Uniforms
||
1235 location
>= (GLint
) shProg
->Uniforms
->NumUniforms
) {
1236 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glGetUniformfv(location)");
1239 /* OK, find the gl_program and program parameter location */
1240 progPos
= shProg
->Uniforms
->Uniforms
[location
].VertPos
;
1242 prog
= &shProg
->VertexProgram
->Base
;
1245 progPos
= shProg
->Uniforms
->Uniforms
[location
].FragPos
;
1247 prog
= &shProg
->FragmentProgram
->Base
;
1254 *paramPosOut
= progPos
;
1259 * Called via ctx->Driver.GetUniformfv().
1262 _mesa_get_uniformfv(GLcontext
*ctx
, GLuint program
, GLint location
,
1265 struct gl_program
*prog
;
1268 lookup_uniform_parameter(ctx
, program
, location
, &prog
, ¶mPos
);
1271 const struct gl_program_parameter
*p
=
1272 &prog
->Parameters
->Parameters
[paramPos
];
1273 GLint rows
, cols
, i
, j
, k
;
1275 get_uniform_rows_cols(p
, &rows
, &cols
);
1278 for (i
= 0; i
< rows
; i
++) {
1279 for (j
= 0; j
< cols
; j
++ ) {
1280 params
[k
++] = prog
->Parameters
->ParameterValues
[paramPos
+i
][j
];
1288 * Called via ctx->Driver.GetUniformiv().
1289 * \sa _mesa_get_uniformfv, only difference is a cast.
1292 _mesa_get_uniformiv(GLcontext
*ctx
, GLuint program
, GLint location
,
1295 struct gl_program
*prog
;
1298 lookup_uniform_parameter(ctx
, program
, location
, &prog
, ¶mPos
);
1301 const struct gl_program_parameter
*p
=
1302 &prog
->Parameters
->Parameters
[paramPos
];
1303 GLint rows
, cols
, i
, j
, k
;
1305 get_uniform_rows_cols(p
, &rows
, &cols
);
1308 for (i
= 0; i
< rows
; i
++) {
1309 for (j
= 0; j
< cols
; j
++ ) {
1310 params
[k
++] = (GLint
) prog
->Parameters
->ParameterValues
[paramPos
+i
][j
];
1318 * The value returned by GetUniformLocation actually encodes two things:
1319 * 1. the index into the prog->Uniforms[] array for the uniform
1320 * 2. an offset in the prog->ParameterValues[] array for specifying array
1321 * elements or structure fields.
1322 * This function merges those two values.
1325 merge_location_offset(GLint
*location
, GLint offset
)
1327 *location
= *location
| (offset
<< 16);
1332 * Seperate the uniform location and parameter offset. See above.
1335 split_location_offset(GLint
*location
, GLint
*offset
)
1337 *offset
= (*location
>> 16);
1338 *location
= *location
& 0xffff;
1343 * Called via ctx->Driver.GetUniformLocation().
1345 * The return value will encode two values, the uniform location and an
1346 * offset (used for arrays, structs).
1349 _mesa_get_uniform_location(GLcontext
*ctx
, GLuint program
, const GLchar
*name
)
1351 GLint offset
= 0, location
= -1;
1353 struct gl_shader_program
*shProg
=
1354 _mesa_lookup_shader_program_err(ctx
, program
, "glGetUniformLocation");
1359 if (shProg
->LinkStatus
== GL_FALSE
) {
1360 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glGetUniformfv(program)");
1364 /* XXX we should return -1 if the uniform was declared, but not
1368 /* XXX we need to be able to parse uniform names for structs and arrays
1375 /* handle 1-dimension arrays here... */
1376 char *c
= strchr(name
, '[');
1378 /* truncate name at [ */
1379 const GLint len
= c
- name
;
1380 GLchar
*newName
= _mesa_malloc(len
+ 1);
1382 return -1; /* out of mem */
1383 _mesa_memcpy(newName
, name
, len
);
1386 location
= _mesa_lookup_uniform(shProg
->Uniforms
, newName
);
1387 if (location
>= 0) {
1388 const GLint element
= _mesa_atoi(c
+ 1);
1390 /* get type of the uniform array element */
1391 struct gl_program_parameter
*p
;
1392 p
= get_uniform_parameter(shProg
, location
);
1395 get_matrix_dims(p
->DataType
, &rows
, &cols
);
1398 offset
= element
* rows
;
1403 _mesa_free(newName
);
1408 location
= _mesa_lookup_uniform(shProg
->Uniforms
, name
);
1411 if (location
>= 0) {
1412 merge_location_offset(&location
, offset
);
1421 * Called via ctx->Driver.ShaderSource()
1424 _mesa_shader_source(GLcontext
*ctx
, GLuint shader
, const GLchar
*source
)
1426 struct gl_shader
*sh
;
1428 sh
= _mesa_lookup_shader_err(ctx
, shader
, "glShaderSource");
1432 /* free old shader source string and install new one */
1434 _mesa_free((void *) sh
->Source
);
1436 sh
->Source
= source
;
1437 sh
->CompileStatus
= GL_FALSE
;
1439 sh
->SourceChecksum
= _mesa_str_checksum(sh
->Source
);
1445 * Called via ctx->Driver.CompileShader()
1448 _mesa_compile_shader(GLcontext
*ctx
, GLuint shaderObj
)
1450 struct gl_shader
*sh
;
1452 sh
= _mesa_lookup_shader_err(ctx
, shaderObj
, "glCompileShader");
1456 /* set default pragma state for shader */
1457 sh
->Pragmas
= ctx
->Shader
.DefaultPragmas
;
1459 /* this call will set the sh->CompileStatus field to indicate if
1460 * compilation was successful.
1462 (void) _slang_compile(ctx
, sh
);
1467 * Called via ctx->Driver.LinkProgram()
1470 _mesa_link_program(GLcontext
*ctx
, GLuint program
)
1472 struct gl_shader_program
*shProg
;
1474 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glLinkProgram");
1478 FLUSH_VERTICES(ctx
, _NEW_PROGRAM
);
1480 _slang_link(ctx
, program
, shProg
);
1486 _mesa_printf("Link %u shaders in program %u: %s\n",
1487 shProg
->NumShaders
, shProg
->Name
,
1488 shProg
->LinkStatus
? "Success" : "Failed");
1490 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
1491 _mesa_printf(" shader %u, type 0x%x\n",
1492 shProg
->Shaders
[i
]->Name
,
1493 shProg
->Shaders
[i
]->Type
);
1500 * Called via ctx->Driver.UseProgram()
1503 _mesa_use_program(GLcontext
*ctx
, GLuint program
)
1505 struct gl_shader_program
*shProg
;
1507 if (ctx
->Shader
.CurrentProgram
&&
1508 ctx
->Shader
.CurrentProgram
->Name
== program
) {
1513 FLUSH_VERTICES(ctx
, _NEW_PROGRAM
| _NEW_PROGRAM_CONSTANTS
);
1516 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glUseProgram");
1520 if (!shProg
->LinkStatus
) {
1521 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1522 "glUseProgram(program %u not linked)", program
);
1529 _mesa_printf("Use Shader %u\n", shProg
->Name
);
1530 for (i
= 0; i
< shProg
->NumShaders
; i
++) {
1531 _mesa_printf(" shader %u, type 0x%x, checksum %u\n",
1532 shProg
->Shaders
[i
]->Name
,
1533 shProg
->Shaders
[i
]->Type
,
1534 shProg
->Shaders
[i
]->SourceChecksum
);
1536 if (shProg
->VertexProgram
)
1537 printf(" vert prog %u\n", shProg
->VertexProgram
->Base
.Id
);
1538 if (shProg
->FragmentProgram
)
1539 printf(" frag prog %u\n", shProg
->FragmentProgram
->Base
.Id
);
1546 _mesa_reference_shader_program(ctx
, &ctx
->Shader
.CurrentProgram
, shProg
);
1552 * Update the vertex/fragment program's TexturesUsed array.
1554 * This needs to be called after glUniform(set sampler var) is called.
1555 * A call to glUniform(samplerVar, value) causes a sampler to point to a
1556 * particular texture unit. We know the sampler's texture target
1557 * (1D/2D/3D/etc) from compile time but the sampler's texture unit is
1558 * set by glUniform() calls.
1560 * So, scan the program->SamplerUnits[] and program->SamplerTargets[]
1561 * information to update the prog->TexturesUsed[] values.
1562 * Each value of TexturesUsed[unit] is one of zero, TEXTURE_1D_INDEX,
1563 * TEXTURE_2D_INDEX, TEXTURE_3D_INDEX, etc.
1564 * We'll use that info for state validation before rendering.
1567 _mesa_update_shader_textures_used(struct gl_program
*prog
)
1571 memset(prog
->TexturesUsed
, 0, sizeof(prog
->TexturesUsed
));
1573 for (s
= 0; s
< MAX_SAMPLERS
; s
++) {
1574 if (prog
->SamplersUsed
& (1 << s
)) {
1575 GLuint unit
= prog
->SamplerUnits
[s
];
1576 GLuint tgt
= prog
->SamplerTargets
[s
];
1577 assert(unit
< MAX_TEXTURE_IMAGE_UNITS
);
1578 assert(tgt
< NUM_TEXTURE_TARGETS
);
1579 prog
->TexturesUsed
[unit
] |= (1 << tgt
);
1586 * Check if the type given by userType is allowed to set a uniform of the
1587 * target type. Generally, equivalence is required, but setting Boolean
1588 * uniforms can be done with glUniformiv or glUniformfv.
1591 compatible_types(GLenum userType
, GLenum targetType
)
1593 if (userType
== targetType
)
1596 if (targetType
== GL_BOOL
&& (userType
== GL_FLOAT
|| userType
== GL_INT
))
1599 if (targetType
== GL_BOOL_VEC2
&& (userType
== GL_FLOAT_VEC2
||
1600 userType
== GL_INT_VEC2
))
1603 if (targetType
== GL_BOOL_VEC3
&& (userType
== GL_FLOAT_VEC3
||
1604 userType
== GL_INT_VEC3
))
1607 if (targetType
== GL_BOOL_VEC4
&& (userType
== GL_FLOAT_VEC4
||
1608 userType
== GL_INT_VEC4
))
1611 if (is_sampler_type(targetType
) && userType
== GL_INT
)
1619 * Set the value of a program's uniform variable.
1620 * \param program the program whose uniform to update
1621 * \param index the index of the program parameter for the uniform
1622 * \param offset additional parameter slot offset (for arrays)
1623 * \param type the incoming datatype of 'values'
1624 * \param count the number of uniforms to set
1625 * \param elems number of elements per uniform (1, 2, 3 or 4)
1626 * \param values the new values, of datatype 'type'
1629 set_program_uniform(GLcontext
*ctx
, struct gl_program
*program
,
1630 GLint index
, GLint offset
,
1631 GLenum type
, GLsizei count
, GLint elems
,
1634 const struct gl_program_parameter
*param
=
1635 &program
->Parameters
->Parameters
[index
];
1637 assert(offset
>= 0);
1641 if (!compatible_types(type
, param
->DataType
)) {
1642 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniform(type mismatch)");
1646 if (index
+ offset
> (GLint
) program
->Parameters
->Size
) {
1647 /* out of bounds! */
1651 if (param
->Type
== PROGRAM_SAMPLER
) {
1652 /* This controls which texture unit which is used by a sampler */
1653 GLboolean changed
= GL_FALSE
;
1656 /* this should have been caught by the compatible_types() check */
1657 ASSERT(type
== GL_INT
);
1659 /* loop over number of samplers to change */
1660 for (i
= 0; i
< count
; i
++) {
1662 (GLuint
) program
->Parameters
->ParameterValues
[index
+ offset
+ i
][0];
1663 GLuint texUnit
= ((GLuint
*) values
)[i
];
1665 /* check that the sampler (tex unit index) is legal */
1666 if (texUnit
>= ctx
->Const
.MaxTextureImageUnits
) {
1667 _mesa_error(ctx
, GL_INVALID_VALUE
,
1668 "glUniform1(invalid sampler/tex unit index)");
1672 /* This maps a sampler to a texture unit: */
1673 if (sampler
< MAX_SAMPLERS
) {
1675 _mesa_printf("Set program %p sampler %d '%s' to unit %u\n",
1676 program
, sampler
, param
->Name
, texUnit
);
1678 if (program
->SamplerUnits
[sampler
] != texUnit
) {
1679 program
->SamplerUnits
[sampler
] = texUnit
;
1686 /* When a sampler's value changes it usually requires rewriting
1687 * a GPU program's TEX instructions since there may not be a
1688 * sampler->texture lookup table. We signal this with the
1689 * ProgramStringNotify() callback.
1691 FLUSH_VERTICES(ctx
, _NEW_TEXTURE
| _NEW_PROGRAM
);
1692 _mesa_update_shader_textures_used(program
);
1693 ctx
->Driver
.ProgramStringNotify(ctx
, program
->Target
, program
);
1697 /* ordinary uniform variable */
1698 const GLboolean isUniformBool
= is_boolean_type(param
->DataType
);
1699 const GLboolean areIntValues
= is_integer_type(type
);
1700 const GLint slots
= (param
->Size
+ 3) / 4;
1701 const GLint typeSize
= sizeof_glsl_type(param
->DataType
);
1704 if (param
->Size
> typeSize
) {
1706 /* we'll ignore extra data below */
1709 /* non-array: count must be at most one; count == 0 is handled by the loop below */
1711 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1712 "glUniform(uniform is not an array)");
1717 /* loop over number of array elements */
1718 for (k
= 0; k
< count
; k
++) {
1719 GLfloat
*uniformVal
;
1721 if (offset
+ k
>= slots
) {
1722 /* Extra array data is ignored */
1726 /* uniformVal (the destination) is always float[4] */
1727 uniformVal
= program
->Parameters
->ParameterValues
[index
+ offset
+ k
];
1730 /* convert user's ints to floats */
1731 const GLint
*iValues
= ((const GLint
*) values
) + k
* elems
;
1732 for (i
= 0; i
< elems
; i
++) {
1733 uniformVal
[i
] = (GLfloat
) iValues
[i
];
1737 const GLfloat
*fValues
= ((const GLfloat
*) values
) + k
* elems
;
1738 for (i
= 0; i
< elems
; i
++) {
1739 uniformVal
[i
] = fValues
[i
];
1743 /* if the uniform is bool-valued, convert to 1.0 or 0.0 */
1744 if (isUniformBool
) {
1745 for (i
= 0; i
< elems
; i
++) {
1746 uniformVal
[i
] = uniformVal
[i
] ? 1.0f
: 0.0f
;
1755 * Called via ctx->Driver.Uniform().
1758 _mesa_uniform(GLcontext
*ctx
, GLint location
, GLsizei count
,
1759 const GLvoid
*values
, GLenum type
)
1761 struct gl_shader_program
*shProg
= ctx
->Shader
.CurrentProgram
;
1762 struct gl_uniform
*uniform
;
1763 GLint elems
, offset
;
1766 if (!shProg
|| !shProg
->LinkStatus
) {
1767 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniform(program not linked)");
1772 return; /* The standard specifies this as a no-op */
1774 if (location
< -1) {
1775 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniform(location)");
1779 split_location_offset(&location
, &offset
);
1781 if (location
< 0 || location
>= (GLint
) shProg
->Uniforms
->NumUniforms
) {
1782 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniform(location)");
1787 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniform(count < 0)");
1793 basicType
= GL_FLOAT
;
1801 basicType
= GL_FLOAT
;
1809 basicType
= GL_FLOAT
;
1817 basicType
= GL_FLOAT
;
1825 _mesa_problem(ctx
, "Invalid type in _mesa_uniform");
1829 FLUSH_VERTICES(ctx
, _NEW_PROGRAM_CONSTANTS
);
1831 uniform
= &shProg
->Uniforms
->Uniforms
[location
];
1833 if (ctx
->Shader
.Flags
& GLSL_UNIFORMS
) {
1835 _mesa_printf("Mesa: set program %u uniform %s (loc %d) to: ",
1836 shProg
->Name
, uniform
->Name
, location
);
1837 if (basicType
== GL_INT
) {
1838 const GLint
*v
= (const GLint
*) values
;
1839 for (i
= 0; i
< count
* elems
; i
++) {
1840 _mesa_printf("%d ", v
[i
]);
1844 const GLfloat
*v
= (const GLfloat
*) values
;
1845 for (i
= 0; i
< count
* elems
; i
++) {
1846 _mesa_printf("%g ", v
[i
]);
1852 /* A uniform var may be used by both a vertex shader and a fragment
1853 * shader. We may need to update one or both shader's uniform here:
1855 if (shProg
->VertexProgram
) {
1856 /* convert uniform location to program parameter index */
1857 GLint index
= uniform
->VertPos
;
1859 set_program_uniform(ctx
, &shProg
->VertexProgram
->Base
,
1860 index
, offset
, type
, count
, elems
, values
);
1864 if (shProg
->FragmentProgram
) {
1865 /* convert uniform location to program parameter index */
1866 GLint index
= uniform
->FragPos
;
1868 set_program_uniform(ctx
, &shProg
->FragmentProgram
->Base
,
1869 index
, offset
, type
, count
, elems
, values
);
1873 uniform
->Initialized
= GL_TRUE
;
1878 * Set a matrix-valued program parameter.
1881 set_program_uniform_matrix(GLcontext
*ctx
, struct gl_program
*program
,
1882 GLuint index
, GLuint offset
,
1883 GLuint count
, GLuint rows
, GLuint cols
,
1884 GLboolean transpose
, const GLfloat
*values
)
1886 GLuint mat
, row
, col
;
1888 const struct gl_program_parameter
* param
= &program
->Parameters
->Parameters
[index
];
1889 const GLint slots
= (param
->Size
+ 3) / 4;
1890 const GLint typeSize
= sizeof_glsl_type(param
->DataType
);
1893 /* check that the number of rows, columns is correct */
1894 get_matrix_dims(param
->DataType
, &nr
, &nc
);
1895 if (rows
!= nr
|| cols
!= nc
) {
1896 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1897 "glUniformMatrix(matrix size mismatch)");
1901 if (param
->Size
<= typeSize
) {
1902 /* non-array: count must be at most one; count == 0 is handled by the loop below */
1904 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1905 "glUniformMatrix(uniform is not an array)");
1911 * Note: the _columns_ of a matrix are stored in program registers, not
1912 * the rows. So, the loops below look a little funny.
1913 * XXX could optimize this a bit...
1916 /* loop over matrices */
1917 for (mat
= 0; mat
< count
; mat
++) {
1920 for (col
= 0; col
< cols
; col
++) {
1922 if (offset
>= slots
) {
1923 /* Ignore writes beyond the end of (the used part of) an array */
1926 v
= program
->Parameters
->ParameterValues
[index
+ offset
];
1927 for (row
= 0; row
< rows
; row
++) {
1929 v
[row
] = values
[src
+ row
* cols
+ col
];
1932 v
[row
] = values
[src
+ col
* rows
+ row
];
1939 src
+= rows
* cols
; /* next matrix */
1945 * Called by ctx->Driver.UniformMatrix().
1946 * Note: cols=2, rows=4 ==> array[2] of vec4
1949 _mesa_uniform_matrix(GLcontext
*ctx
, GLint cols
, GLint rows
,
1950 GLint location
, GLsizei count
,
1951 GLboolean transpose
, const GLfloat
*values
)
1953 struct gl_shader_program
*shProg
= ctx
->Shader
.CurrentProgram
;
1954 struct gl_uniform
*uniform
;
1957 if (!shProg
|| !shProg
->LinkStatus
) {
1958 _mesa_error(ctx
, GL_INVALID_OPERATION
,
1959 "glUniformMatrix(program not linked)");
1964 return; /* The standard specifies this as a no-op */
1966 if (location
< -1) {
1967 _mesa_error(ctx
, GL_INVALID_OPERATION
, "glUniformMatrix(location)");
1971 split_location_offset(&location
, &offset
);
1973 if (location
< 0 || location
>= (GLint
) shProg
->Uniforms
->NumUniforms
) {
1974 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniformMatrix(location)");
1977 if (values
== NULL
) {
1978 _mesa_error(ctx
, GL_INVALID_VALUE
, "glUniformMatrix");
1982 FLUSH_VERTICES(ctx
, _NEW_PROGRAM_CONSTANTS
);
1984 uniform
= &shProg
->Uniforms
->Uniforms
[location
];
1986 if (shProg
->VertexProgram
) {
1987 /* convert uniform location to program parameter index */
1988 GLint index
= uniform
->VertPos
;
1990 set_program_uniform_matrix(ctx
, &shProg
->VertexProgram
->Base
,
1992 count
, rows
, cols
, transpose
, values
);
1996 if (shProg
->FragmentProgram
) {
1997 /* convert uniform location to program parameter index */
1998 GLint index
= uniform
->FragPos
;
2000 set_program_uniform_matrix(ctx
, &shProg
->FragmentProgram
->Base
,
2002 count
, rows
, cols
, transpose
, values
);
2006 uniform
->Initialized
= GL_TRUE
;
2011 * Validate a program's samplers.
2012 * Specifically, check that there aren't two samplers of different types
2013 * pointing to the same texture unit.
2014 * \return GL_TRUE if valid, GL_FALSE if invalid
2017 validate_samplers(GLcontext
*ctx
, const struct gl_program
*prog
, char *errMsg
)
2019 static const char *targetName
[] = {
2028 GLint targetUsed
[MAX_TEXTURE_IMAGE_UNITS
];
2029 GLbitfield samplersUsed
= prog
->SamplersUsed
;
2032 assert(Elements(targetName
) == NUM_TEXTURE_TARGETS
);
2034 if (samplersUsed
== 0x0)
2037 for (i
= 0; i
< Elements(targetUsed
); i
++)
2040 /* walk over bits which are set in 'samplers' */
2041 while (samplersUsed
) {
2043 gl_texture_index target
;
2044 GLint sampler
= _mesa_ffs(samplersUsed
) - 1;
2045 assert(sampler
>= 0);
2046 assert(sampler
< MAX_TEXTURE_IMAGE_UNITS
);
2047 unit
= prog
->SamplerUnits
[sampler
];
2048 target
= prog
->SamplerTargets
[sampler
];
2049 if (targetUsed
[unit
] != -1 && targetUsed
[unit
] != target
) {
2050 _mesa_snprintf(errMsg
, 100,
2051 "Texture unit %d is accessed both as %s and %s",
2052 unit
, targetName
[targetUsed
[unit
]], targetName
[target
]);
2055 targetUsed
[unit
] = target
;
2056 samplersUsed
^= (1 << sampler
);
2064 * Do validation of the given shader program.
2065 * \param errMsg returns error message if validation fails.
2066 * \return GL_TRUE if valid, GL_FALSE if invalid (and set errMsg)
2069 _mesa_validate_shader_program(GLcontext
*ctx
,
2070 const struct gl_shader_program
*shProg
,
2073 const struct gl_vertex_program
*vp
= shProg
->VertexProgram
;
2074 const struct gl_fragment_program
*fp
= shProg
->FragmentProgram
;
2076 if (!shProg
->LinkStatus
) {
2080 /* From the GL spec, a program is invalid if any of these are true:
2082 any two active samplers in the current program object are of
2083 different types, but refer to the same texture image unit,
2085 any active sampler in the current program object refers to a texture
2086 image unit where fixed-function fragment processing accesses a
2087 texture target that does not match the sampler type, or
2089 the sum of the number of active samplers in the program and the
2090 number of texture image units enabled for fixed-function fragment
2091 processing exceeds the combined limit on the total number of texture
2092 image units allowed.
2097 * Check: any two active samplers in the current program object are of
2098 * different types, but refer to the same texture image unit,
2100 if (vp
&& !validate_samplers(ctx
, &vp
->Base
, errMsg
)) {
2103 if (fp
&& !validate_samplers(ctx
, &fp
->Base
, errMsg
)) {
2112 * Called via glValidateProgram()
2115 _mesa_validate_program(GLcontext
*ctx
, GLuint program
)
2117 struct gl_shader_program
*shProg
;
2120 shProg
= _mesa_lookup_shader_program_err(ctx
, program
, "glValidateProgram");
2125 shProg
->Validated
= _mesa_validate_shader_program(ctx
, shProg
, errMsg
);
2126 if (!shProg
->Validated
) {
2127 /* update info log */
2128 if (shProg
->InfoLog
) {
2129 _mesa_free(shProg
->InfoLog
);
2131 shProg
->InfoLog
= _mesa_strdup(errMsg
);
2137 * Plug in Mesa's GLSL functions into the device driver function table.
2140 _mesa_init_glsl_driver_functions(struct dd_function_table
*driver
)
2142 driver
->AttachShader
= _mesa_attach_shader
;
2143 driver
->BindAttribLocation
= _mesa_bind_attrib_location
;
2144 driver
->CompileShader
= _mesa_compile_shader
;
2145 driver
->CreateProgram
= _mesa_create_program
;
2146 driver
->CreateShader
= _mesa_create_shader
;
2147 driver
->DeleteProgram2
= _mesa_delete_program2
;
2148 driver
->DeleteShader
= _mesa_delete_shader
;
2149 driver
->DetachShader
= _mesa_detach_shader
;
2150 driver
->GetActiveAttrib
= _mesa_get_active_attrib
;
2151 driver
->GetActiveUniform
= _mesa_get_active_uniform
;
2152 driver
->GetAttachedShaders
= _mesa_get_attached_shaders
;
2153 driver
->GetAttribLocation
= _mesa_get_attrib_location
;
2154 driver
->GetHandle
= _mesa_get_handle
;
2155 driver
->GetProgramiv
= _mesa_get_programiv
;
2156 driver
->GetProgramInfoLog
= _mesa_get_program_info_log
;
2157 driver
->GetShaderiv
= _mesa_get_shaderiv
;
2158 driver
->GetShaderInfoLog
= _mesa_get_shader_info_log
;
2159 driver
->GetShaderSource
= _mesa_get_shader_source
;
2160 driver
->GetUniformfv
= _mesa_get_uniformfv
;
2161 driver
->GetUniformiv
= _mesa_get_uniformiv
;
2162 driver
->GetUniformLocation
= _mesa_get_uniform_location
;
2163 driver
->IsProgram
= _mesa_is_program
;
2164 driver
->IsShader
= _mesa_is_shader
;
2165 driver
->LinkProgram
= _mesa_link_program
;
2166 driver
->ShaderSource
= _mesa_shader_source
;
2167 driver
->Uniform
= _mesa_uniform
;
2168 driver
->UniformMatrix
= _mesa_uniform_matrix
;
2169 driver
->UseProgram
= _mesa_use_program
;
2170 driver
->ValidateProgram
= _mesa_validate_program
;