1 /*
2 * Mesa 3-D graphics library
3 *
4 * Copyright (C) 2004-2008 Brian Paul All Rights Reserved.
5 * Copyright (C) 2009-2010 VMware, Inc. All Rights Reserved.
6 *
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:
13 *
14 * The above copyright notice and this permission notice shall be included
15 * in all copies or substantial portions of the Software.
16 *
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.
24 */
25
26 /**
27 * \file shaderapi.c
28 * \author Brian Paul
29 *
30 * Implementation of GLSL-related API functions.
31 * The glUniform* functions are in uniforms.c
32 */
33
34
35 #include <errno.h>
36 #include <stdbool.h>
37 #include <c99_alloca.h>
38
39 #include "util/glheader.h"
40 #include "main/context.h"
41 #include "draw_validate.h"
42 #include "main/enums.h"
43 #include "main/glspirv.h"
44 #include "main/hash.h"
45 #include "main/mtypes.h"
46 #include "main/pipelineobj.h"
47 #include "main/program_binary.h"
48 #include "main/shaderapi.h"
49 #include "main/shaderobj.h"
50 #include "main/state.h"
51 #include "main/transformfeedback.h"
52 #include "main/uniforms.h"
53 #include "compiler/glsl/builtin_functions.h"
54 #include "compiler/glsl/glsl_parser_extras.h"
55 #include "compiler/glsl/ir.h"
56 #include "compiler/glsl/ir_uniform.h"
57 #include "compiler/glsl/program.h"
58 #include "program/program.h"
59 #include "program/prog_print.h"
60 #include "program/prog_parameter.h"
61 #include "util/ralloc.h"
62 #include "util/hash_table.h"
63 #include "util/crc32.h"
64 #include "util/os_file.h"
65 #include "util/list.h"
66 #include "util/log.h"
67 #include "util/perf/cpu_trace.h"
68 #include "util/u_process.h"
69 #include "util/u_string.h"
70 #include "api_exec_decl.h"
71
72 #include "state_tracker/st_context.h"
73 #include "state_tracker/st_glsl_to_nir.h"
74 #include "state_tracker/st_program.h"
75
76 #ifdef ENABLE_SHADER_CACHE
77 #if CUSTOM_SHADER_REPLACEMENT
78 #include "shader_replacement.h"
79 /* shader_replacement.h must declare a variable like this:
80
81 struct _shader_replacement {
82 // process name. If null, only blake3 is used to match
83 const char *app;
84 // original glsl shader blake3
85 const char *blake3;
86 // shader stage
87 gl_shader_stage stage;
88 ... any other information ...
89 };
90 struct _shader_replacement shader_replacements[...];
91
92 And a method to load a given replacement and return the new
93 glsl source:
94
95 char* load_shader_replacement(struct _shader_replacement *repl);
96
97 And a method to replace the shader without blake3 matching:
98
99 char *try_direct_replace(const char *app, const char *source)
100
101 shader_replacement.h can be generated at build time, or copied
102 from an external folder, or any other method.
103 */
104 #else
105 struct _shader_replacement {
106 const char *app;
107 const char *blake3;
108 gl_shader_stage stage;
109 };
110 struct _shader_replacement shader_replacements[0];
111
try_direct_replace(const char * app,const char * source)112 static char *try_direct_replace(const char *app, const char *source)
113 {
114 return NULL;
115 }
116
load_shader_replacement(struct _shader_replacement * repl)117 static char* load_shader_replacement(struct _shader_replacement *repl)
118 {
119 return NULL;
120 }
121 #endif
122 #endif
123
124 /**
125 * Return mask of GLSL_x flags by examining the MESA_GLSL env var.
126 */
127 GLbitfield
_mesa_get_shader_flags(void)128 _mesa_get_shader_flags(void)
129 {
130 GLbitfield flags = 0x0;
131 const char *env = getenv("MESA_GLSL");
132
133 if (env) {
134 if (strstr(env, "dump_on_error"))
135 flags |= GLSL_DUMP_ON_ERROR;
136 #ifndef CUSTOM_SHADER_REPLACEMENT
137 else if (strstr(env, "dump"))
138 flags |= GLSL_DUMP;
139 if (strstr(env, "log"))
140 flags |= GLSL_LOG;
141 if (strstr(env, "source"))
142 flags |= GLSL_SOURCE;
143 #endif
144 if (strstr(env, "cache_fb"))
145 flags |= GLSL_CACHE_FALLBACK;
146 if (strstr(env, "cache_info"))
147 flags |= GLSL_CACHE_INFO;
148 if (strstr(env, "nopvert"))
149 flags |= GLSL_NOP_VERT;
150 if (strstr(env, "nopfrag"))
151 flags |= GLSL_NOP_FRAG;
152 if (strstr(env, "uniform"))
153 flags |= GLSL_UNIFORMS;
154 if (strstr(env, "useprog"))
155 flags |= GLSL_USE_PROG;
156 if (strstr(env, "errors"))
157 flags |= GLSL_REPORT_ERRORS;
158 }
159
160 return flags;
161 }
162
163 #define ANDROID_SHADER_CAPTURE 0
164
165 #if ANDROID_SHADER_CAPTURE
166 #include "util/u_process.h"
167 #include <sys/stat.h>
168 #include <sys/types.h>
169 #endif
170
171 /**
172 * Memoized version of getenv("MESA_SHADER_CAPTURE_PATH").
173 */
174 const char *
_mesa_get_shader_capture_path(void)175 _mesa_get_shader_capture_path(void)
176 {
177 static bool read_env_var = false;
178 static const char *path = NULL;
179
180 if (!read_env_var) {
181 path = secure_getenv("MESA_SHADER_CAPTURE_PATH");
182 read_env_var = true;
183
184 #if ANDROID_SHADER_CAPTURE
185 if (!path) {
186 char *p;
187 asprintf(&p, "/data/shaders/%s", util_get_process_name());
188 mkdir(p, 0755);
189 path = p;
190 }
191 #endif
192 }
193
194 return path;
195 }
196
197 /**
198 * Initialize context's shader state.
199 */
200 void
_mesa_init_shader_state(struct gl_context * ctx)201 _mesa_init_shader_state(struct gl_context *ctx)
202 {
203 /* Device drivers may override these to control what kind of instructions
204 * are generated by the GLSL compiler.
205 */
206 struct gl_shader_compiler_options options;
207 gl_shader_stage sh;
208 int i;
209
210 memset(&options, 0, sizeof(options));
211 options.MaxIfDepth = UINT_MAX;
212
213 for (sh = 0; sh < MESA_SHADER_STAGES; ++sh)
214 memcpy(&ctx->Const.ShaderCompilerOptions[sh], &options, sizeof(options));
215
216 ctx->Shader.Flags = _mesa_get_shader_flags();
217
218 if (ctx->Shader.Flags != 0)
219 ctx->Const.GenerateTemporaryNames = true;
220
221 /* Extended for ARB_separate_shader_objects */
222 ctx->Shader.RefCount = 1;
223 ctx->TessCtrlProgram.patch_vertices = 3;
224 for (i = 0; i < 4; ++i)
225 ctx->TessCtrlProgram.patch_default_outer_level[i] = 1.0;
226 for (i = 0; i < 2; ++i)
227 ctx->TessCtrlProgram.patch_default_inner_level[i] = 1.0;
228 }
229
230
231 /**
232 * Free the per-context shader-related state.
233 */
234 void
_mesa_free_shader_state(struct gl_context * ctx)235 _mesa_free_shader_state(struct gl_context *ctx)
236 {
237 for (int i = 0; i < MESA_SHADER_STAGES; i++) {
238 _mesa_reference_program(ctx, &ctx->Shader.CurrentProgram[i], NULL);
239 _mesa_reference_shader_program(ctx,
240 &ctx->Shader.ReferencedPrograms[i],
241 NULL);
242 free(ctx->SubroutineIndex[i].IndexPtr);
243 ctx->SubroutineIndex[i].IndexPtr = NULL;
244 }
245 _mesa_reference_shader_program(ctx, &ctx->Shader.ActiveProgram, NULL);
246
247 /* Extended for ARB_separate_shader_objects */
248 _mesa_reference_pipeline_object(ctx, &ctx->_Shader, NULL);
249
250 assert(ctx->Shader.RefCount == 1);
251 }
252
253
254 /**
255 * Copy string from <src> to <dst>, up to maxLength characters, returning
256 * length of <dst> in <length>.
257 * \param src the strings source
258 * \param maxLength max chars to copy
259 * \param length returns number of chars copied
260 * \param dst the string destination
261 */
262 void
_mesa_copy_string(GLchar * dst,GLsizei maxLength,GLsizei * length,const GLchar * src)263 _mesa_copy_string(GLchar *dst, GLsizei maxLength,
264 GLsizei *length, const GLchar *src)
265 {
266 GLsizei len;
267 for (len = 0; len < maxLength - 1 && src && src[len]; len++)
268 dst[len] = src[len];
269 if (maxLength > 0)
270 dst[len] = 0;
271 if (length)
272 *length = len;
273 }
274
275
276
277 /**
278 * Confirm that the a shader type is valid and supported by the implementation
279 *
280 * \param ctx Current GL context
281 * \param type Shader target
282 *
283 */
284 bool
_mesa_validate_shader_target(const struct gl_context * ctx,GLenum type)285 _mesa_validate_shader_target(const struct gl_context *ctx, GLenum type)
286 {
287 /* Note: when building built-in GLSL functions, this function may be
288 * invoked with ctx == NULL. In that case, we can only validate that it's
289 * a shader target we recognize, not that it's supported in the current
290 * context. But that's fine--we don't need any further validation than
291 * that when building built-in GLSL functions.
292 */
293
294 switch (type) {
295 case GL_FRAGMENT_SHADER:
296 return ctx == NULL || ctx->Extensions.ARB_fragment_shader;
297 case GL_VERTEX_SHADER:
298 return ctx == NULL || ctx->Extensions.ARB_vertex_shader;
299 case GL_GEOMETRY_SHADER_ARB:
300 return ctx == NULL || _mesa_has_geometry_shaders(ctx);
301 case GL_TESS_CONTROL_SHADER:
302 case GL_TESS_EVALUATION_SHADER:
303 return ctx == NULL || _mesa_has_tessellation(ctx);
304 case GL_COMPUTE_SHADER:
305 return ctx == NULL || _mesa_has_compute_shaders(ctx);
306 default:
307 return false;
308 }
309 }
310
311
312 static GLboolean
is_program(struct gl_context * ctx,GLuint name)313 is_program(struct gl_context *ctx, GLuint name)
314 {
315 struct gl_shader_program *shProg = _mesa_lookup_shader_program(ctx, name);
316 return shProg ? GL_TRUE : GL_FALSE;
317 }
318
319
320 static GLboolean
is_shader(struct gl_context * ctx,GLuint name)321 is_shader(struct gl_context *ctx, GLuint name)
322 {
323 struct gl_shader *shader = _mesa_lookup_shader(ctx, name);
324 return shader ? GL_TRUE : GL_FALSE;
325 }
326
327
328 /**
329 * Attach shader to a shader program.
330 */
331 static void
attach_shader(struct gl_context * ctx,struct gl_shader_program * shProg,struct gl_shader * sh)332 attach_shader(struct gl_context *ctx, struct gl_shader_program *shProg,
333 struct gl_shader *sh)
334 {
335 GLuint n = shProg->NumShaders;
336
337 shProg->Shaders = realloc(shProg->Shaders,
338 (n + 1) * sizeof(struct gl_shader *));
339 if (!shProg->Shaders) {
340 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glAttachShader");
341 return;
342 }
343
344 /* append */
345 shProg->Shaders[n] = NULL; /* since realloc() didn't zero the new space */
346 _mesa_reference_shader(ctx, &shProg->Shaders[n], sh);
347 shProg->NumShaders++;
348 }
349
350 static void
attach_shader_err(struct gl_context * ctx,GLuint program,GLuint shader,const char * caller)351 attach_shader_err(struct gl_context *ctx, GLuint program, GLuint shader,
352 const char *caller)
353 {
354 struct gl_shader_program *shProg;
355 struct gl_shader *sh;
356 GLuint i, n;
357
358 const bool same_type_disallowed = _mesa_is_gles(ctx);
359
360 shProg = _mesa_lookup_shader_program_err(ctx, program, caller);
361 if (!shProg)
362 return;
363
364 sh = _mesa_lookup_shader_err(ctx, shader, caller);
365 if (!sh) {
366 return;
367 }
368
369 n = shProg->NumShaders;
370 for (i = 0; i < n; i++) {
371 if (shProg->Shaders[i] == sh) {
372 /* The shader is already attched to this program. The
373 * GL_ARB_shader_objects spec says:
374 *
375 * "The error INVALID_OPERATION is generated by AttachObjectARB
376 * if <obj> is already attached to <containerObj>."
377 */
378 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", caller);
379 return;
380 } else if (same_type_disallowed &&
381 shProg->Shaders[i]->Stage == sh->Stage) {
382 /* Shader with the same type is already attached to this program,
383 * OpenGL ES 2.0 and 3.0 specs say:
384 *
385 * "Multiple shader objects of the same type may not be attached
386 * to a single program object. [...] The error INVALID_OPERATION
387 * is generated if [...] another shader object of the same type
388 * as shader is already attached to program."
389 */
390 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", caller);
391 return;
392 }
393 }
394
395 attach_shader(ctx, shProg, sh);
396 }
397
398 static void
attach_shader_no_error(struct gl_context * ctx,GLuint program,GLuint shader)399 attach_shader_no_error(struct gl_context *ctx, GLuint program, GLuint shader)
400 {
401 struct gl_shader_program *shProg;
402 struct gl_shader *sh;
403
404 shProg = _mesa_lookup_shader_program(ctx, program);
405 sh = _mesa_lookup_shader(ctx, shader);
406
407 attach_shader(ctx, shProg, sh);
408 }
409
410 static GLuint
create_shader(struct gl_context * ctx,GLenum type)411 create_shader(struct gl_context *ctx, GLenum type)
412 {
413 struct gl_shader *sh;
414 GLuint name;
415
416 _mesa_HashLockMutex(&ctx->Shared->ShaderObjects);
417 name = _mesa_HashFindFreeKeyBlock(&ctx->Shared->ShaderObjects, 1);
418 sh = _mesa_new_shader(name, _mesa_shader_enum_to_shader_stage(type));
419 sh->Type = type;
420 _mesa_HashInsertLocked(&ctx->Shared->ShaderObjects, name, sh);
421 _mesa_HashUnlockMutex(&ctx->Shared->ShaderObjects);
422
423 return name;
424 }
425
426
427 static GLuint
create_shader_err(struct gl_context * ctx,GLenum type,const char * caller)428 create_shader_err(struct gl_context *ctx, GLenum type, const char *caller)
429 {
430 if (!_mesa_validate_shader_target(ctx, type)) {
431 _mesa_error(ctx, GL_INVALID_ENUM, "%s(%s)",
432 caller, _mesa_enum_to_string(type));
433 return 0;
434 }
435
436 return create_shader(ctx, type);
437 }
438
439
440 static GLuint
create_shader_program(struct gl_context * ctx)441 create_shader_program(struct gl_context *ctx)
442 {
443 GLuint name;
444 struct gl_shader_program *shProg;
445
446 _mesa_HashLockMutex(&ctx->Shared->ShaderObjects);
447
448 name = _mesa_HashFindFreeKeyBlock(&ctx->Shared->ShaderObjects, 1);
449
450 shProg = _mesa_new_shader_program(name);
451
452 _mesa_HashInsertLocked(&ctx->Shared->ShaderObjects, name, shProg);
453
454 assert(shProg->RefCount == 1);
455
456 _mesa_HashUnlockMutex(&ctx->Shared->ShaderObjects);
457
458 return name;
459 }
460
461
462 /**
463 * Delete a shader program. Actually, just decrement the program's
464 * reference count and mark it as DeletePending.
465 * Used to implement glDeleteProgram() and glDeleteObjectARB().
466 */
467 static void
delete_shader_program(struct gl_context * ctx,GLuint name)468 delete_shader_program(struct gl_context *ctx, GLuint name)
469 {
470 /*
471 * NOTE: deleting shaders/programs works a bit differently than
472 * texture objects (and buffer objects, etc). Shader/program
473 * handles/IDs exist in the hash table until the object is really
474 * deleted (refcount==0). With texture objects, the handle/ID is
475 * removed from the hash table in glDeleteTextures() while the tex
476 * object itself might linger until its refcount goes to zero.
477 */
478 struct gl_shader_program *shProg;
479
480 shProg = _mesa_lookup_shader_program_err(ctx, name, "glDeleteProgram");
481 if (!shProg)
482 return;
483
484 if (!shProg->DeletePending) {
485 shProg->DeletePending = GL_TRUE;
486
487 /* effectively, decr shProg's refcount */
488 _mesa_reference_shader_program(ctx, &shProg, NULL);
489 }
490 }
491
492
493 static void
delete_shader(struct gl_context * ctx,GLuint shader)494 delete_shader(struct gl_context *ctx, GLuint shader)
495 {
496 struct gl_shader *sh;
497
498 sh = _mesa_lookup_shader_err(ctx, shader, "glDeleteShader");
499 if (!sh)
500 return;
501
502 if (!sh->DeletePending) {
503 sh->DeletePending = GL_TRUE;
504
505 /* effectively, decr sh's refcount */
506 _mesa_reference_shader(ctx, &sh, NULL);
507 }
508 }
509
510
511 static ALWAYS_INLINE void
detach_shader(struct gl_context * ctx,GLuint program,GLuint shader,bool no_error)512 detach_shader(struct gl_context *ctx, GLuint program, GLuint shader,
513 bool no_error)
514 {
515 struct gl_shader_program *shProg;
516 GLuint n;
517 GLuint i, j;
518
519 if (!no_error) {
520 shProg = _mesa_lookup_shader_program_err(ctx, program, "glDetachShader");
521 if (!shProg)
522 return;
523 } else {
524 shProg = _mesa_lookup_shader_program(ctx, program);
525 }
526
527 n = shProg->NumShaders;
528
529 for (i = 0; i < n; i++) {
530 if (shProg->Shaders[i]->Name == shader) {
531 /* found it */
532 struct gl_shader **newList;
533
534 /* release */
535 _mesa_reference_shader(ctx, &shProg->Shaders[i], NULL);
536
537 /* alloc new, smaller array */
538 newList = malloc((n - 1) * sizeof(struct gl_shader *));
539 if (!newList) {
540 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glDetachShader");
541 return;
542 }
543 /* Copy old list entries to new list, skipping removed entry at [i] */
544 for (j = 0; j < i; j++) {
545 newList[j] = shProg->Shaders[j];
546 }
547 while (++i < n) {
548 newList[j++] = shProg->Shaders[i];
549 }
550
551 /* Free old list and install new one */
552 free(shProg->Shaders);
553 shProg->Shaders = newList;
554 shProg->NumShaders = n - 1;
555
556 #ifndef NDEBUG
557 /* sanity check - make sure the new list's entries are sensible */
558 for (j = 0; j < shProg->NumShaders; j++) {
559 assert(shProg->Shaders[j]->Stage == MESA_SHADER_VERTEX ||
560 shProg->Shaders[j]->Stage == MESA_SHADER_TESS_CTRL ||
561 shProg->Shaders[j]->Stage == MESA_SHADER_TESS_EVAL ||
562 shProg->Shaders[j]->Stage == MESA_SHADER_GEOMETRY ||
563 shProg->Shaders[j]->Stage == MESA_SHADER_FRAGMENT);
564 assert(shProg->Shaders[j]->RefCount > 0);
565 }
566 #endif
567
568 return;
569 }
570 }
571
572 /* not found */
573 if (!no_error) {
574 GLenum err;
575 if (is_shader(ctx, shader) || is_program(ctx, shader))
576 err = GL_INVALID_OPERATION;
577 else
578 err = GL_INVALID_VALUE;
579 _mesa_error(ctx, err, "glDetachShader(shader)");
580 return;
581 }
582 }
583
584
585 static void
detach_shader_error(struct gl_context * ctx,GLuint program,GLuint shader)586 detach_shader_error(struct gl_context *ctx, GLuint program, GLuint shader)
587 {
588 detach_shader(ctx, program, shader, false);
589 }
590
591
592 static void
detach_shader_no_error(struct gl_context * ctx,GLuint program,GLuint shader)593 detach_shader_no_error(struct gl_context *ctx, GLuint program, GLuint shader)
594 {
595 detach_shader(ctx, program, shader, true);
596 }
597
598
599 /**
600 * Return list of shaders attached to shader program.
601 * \param objOut returns GLuint ids
602 * \param handleOut returns GLhandleARB handles
603 */
604 static void
get_attached_shaders(struct gl_context * ctx,GLuint program,GLsizei maxCount,GLsizei * countOut,GLuint * objOut,GLhandleARB * handleOut)605 get_attached_shaders(struct gl_context *ctx, GLuint program, GLsizei maxCount,
606 GLsizei *countOut, GLuint *objOut, GLhandleARB *handleOut)
607 {
608 struct gl_shader_program *shProg;
609
610 if (maxCount < 0) {
611 _mesa_error(ctx, GL_INVALID_VALUE, "glGetAttachedShaders(maxCount < 0)");
612 return;
613 }
614
615 shProg =
616 _mesa_lookup_shader_program_err(ctx, program, "glGetAttachedShaders");
617
618 if (shProg) {
619 GLuint i;
620 for (i = 0; i < (GLuint) maxCount && i < shProg->NumShaders; i++) {
621 if (objOut) {
622 objOut[i] = shProg->Shaders[i]->Name;
623 }
624
625 if (handleOut) {
626 handleOut[i] = (GLhandleARB) shProg->Shaders[i]->Name;
627 }
628 }
629 if (countOut) {
630 *countOut = i;
631 }
632 }
633 }
634
635 /**
636 * glGetHandleARB() - return ID/name of currently bound shader program.
637 */
638 static GLuint
get_handle(struct gl_context * ctx,GLenum pname)639 get_handle(struct gl_context *ctx, GLenum pname)
640 {
641 if (pname == GL_PROGRAM_OBJECT_ARB) {
642 if (ctx->_Shader->ActiveProgram)
643 return ctx->_Shader->ActiveProgram->Name;
644 else
645 return 0;
646 }
647 else {
648 _mesa_error(ctx, GL_INVALID_ENUM, "glGetHandleARB");
649 return 0;
650 }
651 }
652
653
654 /**
655 * Check if a geometry shader query is valid at this time. If not, report an
656 * error and return false.
657 *
658 * From GL 3.2 section 6.1.16 (Shader and Program Queries):
659 *
660 * "If GEOMETRY_VERTICES_OUT, GEOMETRY_INPUT_TYPE, or GEOMETRY_OUTPUT_TYPE
661 * are queried for a program which has not been linked successfully, or
662 * which does not contain objects to form a geometry shader, then an
663 * INVALID_OPERATION error is generated."
664 */
665 static bool
check_gs_query(struct gl_context * ctx,const struct gl_shader_program * shProg)666 check_gs_query(struct gl_context *ctx, const struct gl_shader_program *shProg)
667 {
668 if (shProg->data->LinkStatus &&
669 shProg->_LinkedShaders[MESA_SHADER_GEOMETRY] != NULL) {
670 return true;
671 }
672
673 _mesa_error(ctx, GL_INVALID_OPERATION,
674 "glGetProgramv(linked geometry shader required)");
675 return false;
676 }
677
678
679 /**
680 * Check if a tessellation control shader query is valid at this time.
681 * If not, report an error and return false.
682 *
683 * From GL 4.0 section 6.1.12 (Shader and Program Queries):
684 *
685 * "If TESS_CONTROL_OUTPUT_VERTICES is queried for a program which has
686 * not been linked successfully, or which does not contain objects to
687 * form a tessellation control shader, then an INVALID_OPERATION error is
688 * generated."
689 */
690 static bool
check_tcs_query(struct gl_context * ctx,const struct gl_shader_program * shProg)691 check_tcs_query(struct gl_context *ctx, const struct gl_shader_program *shProg)
692 {
693 if (shProg->data->LinkStatus &&
694 shProg->_LinkedShaders[MESA_SHADER_TESS_CTRL] != NULL) {
695 return true;
696 }
697
698 _mesa_error(ctx, GL_INVALID_OPERATION,
699 "glGetProgramv(linked tessellation control shader required)");
700 return false;
701 }
702
703
704 /**
705 * Check if a tessellation evaluation shader query is valid at this time.
706 * If not, report an error and return false.
707 *
708 * From GL 4.0 section 6.1.12 (Shader and Program Queries):
709 *
710 * "If any of the pname values in this paragraph are queried for a program
711 * which has not been linked successfully, or which does not contain
712 * objects to form a tessellation evaluation shader, then an
713 * INVALID_OPERATION error is generated."
714 *
715 */
716 static bool
check_tes_query(struct gl_context * ctx,const struct gl_shader_program * shProg)717 check_tes_query(struct gl_context *ctx, const struct gl_shader_program *shProg)
718 {
719 if (shProg->data->LinkStatus &&
720 shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL] != NULL) {
721 return true;
722 }
723
724 _mesa_error(ctx, GL_INVALID_OPERATION, "glGetProgramv(linked tessellation "
725 "evaluation shader required)");
726 return false;
727 }
728
729 static bool
get_shader_program_completion_status(struct gl_context * ctx,struct gl_shader_program * shprog)730 get_shader_program_completion_status(struct gl_context *ctx,
731 struct gl_shader_program *shprog)
732 {
733 struct pipe_screen *screen = ctx->screen;
734
735 if (!screen->is_parallel_shader_compilation_finished)
736 return true;
737
738 for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) {
739 struct gl_linked_shader *linked = shprog->_LinkedShaders[i];
740 void *sh = NULL;
741
742 if (!linked || !linked->Program)
743 continue;
744
745 if (linked->Program->variants)
746 sh = linked->Program->variants->driver_shader;
747
748 unsigned type = pipe_shader_type_from_mesa(i);
749
750 if (sh &&
751 !screen->is_parallel_shader_compilation_finished(screen, sh, type))
752 return false;
753 }
754 return true;
755 }
756
757 /**
758 * glGetProgramiv() - get shader program state.
759 * Note that this is for GLSL shader programs, not ARB vertex/fragment
760 * programs (see glGetProgramivARB).
761 */
762 static void
get_programiv(struct gl_context * ctx,GLuint program,GLenum pname,GLint * params)763 get_programiv(struct gl_context *ctx, GLuint program, GLenum pname,
764 GLint *params)
765 {
766 struct gl_shader_program *shProg
767 = _mesa_lookup_shader_program_err(ctx, program, "glGetProgramiv(program)");
768
769 /* Is transform feedback available in this context?
770 */
771 const bool has_xfb =
772 (_mesa_is_desktop_gl_compat(ctx) && ctx->Extensions.EXT_transform_feedback)
773 || _mesa_is_desktop_gl_core(ctx)
774 || _mesa_is_gles3(ctx);
775
776 /* True if geometry shaders (of the form that was adopted into GLSL 1.50
777 * and GL 3.2) are available in this context
778 */
779 const bool has_gs = _mesa_has_geometry_shaders(ctx);
780 const bool has_tess = _mesa_has_tessellation(ctx);
781
782 /* Are uniform buffer objects available in this context?
783 */
784 const bool has_ubo =
785 (_mesa_is_desktop_gl_compat(ctx) &&
786 ctx->Extensions.ARB_uniform_buffer_object)
787 || _mesa_is_desktop_gl_core(ctx)
788 || _mesa_is_gles3(ctx);
789
790 if (!shProg) {
791 return;
792 }
793
794 switch (pname) {
795 case GL_DELETE_STATUS:
796 *params = shProg->DeletePending;
797 return;
798 case GL_COMPLETION_STATUS_ARB:
799 *params = get_shader_program_completion_status(ctx, shProg);
800 return;
801 case GL_LINK_STATUS:
802 *params = shProg->data->LinkStatus ? GL_TRUE : GL_FALSE;
803 return;
804 case GL_VALIDATE_STATUS:
805 *params = shProg->data->Validated;
806 return;
807 case GL_INFO_LOG_LENGTH:
808 *params = (shProg->data->InfoLog && shProg->data->InfoLog[0] != '\0') ?
809 strlen(shProg->data->InfoLog) + 1 : 0;
810 return;
811 case GL_ATTACHED_SHADERS:
812 *params = shProg->NumShaders;
813 return;
814 case GL_ACTIVE_ATTRIBUTES:
815 *params = _mesa_count_active_attribs(shProg);
816 return;
817 case GL_ACTIVE_ATTRIBUTE_MAX_LENGTH:
818 *params = _mesa_longest_attribute_name_length(shProg);
819 return;
820 case GL_ACTIVE_UNIFORMS: {
821 _mesa_get_program_interfaceiv(shProg, GL_UNIFORM, GL_ACTIVE_RESOURCES,
822 params);
823 return;
824 }
825 case GL_ACTIVE_UNIFORM_MAX_LENGTH: {
826 _mesa_get_program_interfaceiv(shProg, GL_UNIFORM, GL_MAX_NAME_LENGTH,
827 params);
828 return;
829 }
830 case GL_TRANSFORM_FEEDBACK_VARYINGS:
831 if (!has_xfb)
832 break;
833
834 /* Check first if there are transform feedback varyings specified in the
835 * shader (ARB_enhanced_layouts). If there isn't any, return the number of
836 * varyings specified using the API.
837 */
838 if (shProg->last_vert_prog &&
839 shProg->last_vert_prog->sh.LinkedTransformFeedback->NumVarying > 0)
840 *params =
841 shProg->last_vert_prog->sh.LinkedTransformFeedback->NumVarying;
842 else
843 *params = shProg->TransformFeedback.NumVarying;
844 return;
845 case GL_TRANSFORM_FEEDBACK_VARYING_MAX_LENGTH: {
846 if (!has_xfb)
847 break;
848
849 _mesa_get_program_interfaceiv(shProg, GL_TRANSFORM_FEEDBACK_VARYING,
850 GL_MAX_NAME_LENGTH, params);
851 return;
852 }
853 case GL_TRANSFORM_FEEDBACK_BUFFER_MODE:
854 if (!has_xfb)
855 break;
856 *params = shProg->TransformFeedback.BufferMode;
857 return;
858 case GL_GEOMETRY_VERTICES_OUT:
859 if (!has_gs)
860 break;
861 if (check_gs_query(ctx, shProg)) {
862 *params = shProg->_LinkedShaders[MESA_SHADER_GEOMETRY]->
863 Program->info.gs.vertices_out;
864 }
865 return;
866 case GL_GEOMETRY_SHADER_INVOCATIONS:
867 if (!has_gs ||
868 (_mesa_is_desktop_gl(ctx) && !ctx->Extensions.ARB_gpu_shader5)) {
869 break;
870 }
871 if (check_gs_query(ctx, shProg)) {
872 *params = shProg->_LinkedShaders[MESA_SHADER_GEOMETRY]->
873 Program->info.gs.invocations;
874 }
875 return;
876 case GL_GEOMETRY_INPUT_TYPE:
877 if (!has_gs)
878 break;
879 if (check_gs_query(ctx, shProg)) {
880 *params = shProg->_LinkedShaders[MESA_SHADER_GEOMETRY]->
881 Program->info.gs.input_primitive;
882 }
883 return;
884 case GL_GEOMETRY_OUTPUT_TYPE:
885 if (!has_gs)
886 break;
887 if (check_gs_query(ctx, shProg)) {
888 *params = shProg->_LinkedShaders[MESA_SHADER_GEOMETRY]->
889 Program->info.gs.output_primitive;
890 }
891 return;
892 case GL_ACTIVE_UNIFORM_BLOCK_MAX_NAME_LENGTH: {
893 if (!has_ubo)
894 break;
895
896 _mesa_get_program_interfaceiv(shProg, GL_UNIFORM_BLOCK,
897 GL_MAX_NAME_LENGTH, params);
898 return;
899 }
900 case GL_ACTIVE_UNIFORM_BLOCKS:
901 if (!has_ubo)
902 break;
903
904 *params = shProg->data->NumUniformBlocks;
905 return;
906 case GL_PROGRAM_BINARY_RETRIEVABLE_HINT:
907 /* This enum isn't part of the OES extension for OpenGL ES 2.0. It is
908 * only available with desktop OpenGL 3.0+ with the
909 * GL_ARB_get_program_binary extension or OpenGL ES 3.0.
910 *
911 * On desktop, we ignore the 3.0+ requirement because it is silly.
912 */
913 if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx))
914 break;
915
916 *params = shProg->BinaryRetrievableHint;
917 return;
918 case GL_PROGRAM_BINARY_LENGTH:
919 if (ctx->Const.NumProgramBinaryFormats == 0 || !shProg->data->LinkStatus) {
920 *params = 0;
921 } else {
922 _mesa_get_program_binary_length(ctx, shProg, params);
923 }
924 return;
925 case GL_ACTIVE_ATOMIC_COUNTER_BUFFERS:
926 if (!ctx->Extensions.ARB_shader_atomic_counters && !_mesa_is_gles31(ctx))
927 break;
928
929 *params = shProg->data->NumAtomicBuffers;
930 return;
931 case GL_COMPUTE_WORK_GROUP_SIZE: {
932 int i;
933 if (!_mesa_has_compute_shaders(ctx))
934 break;
935 if (!shProg->data->LinkStatus) {
936 _mesa_error(ctx, GL_INVALID_OPERATION, "glGetProgramiv(program not "
937 "linked)");
938 return;
939 }
940 if (shProg->_LinkedShaders[MESA_SHADER_COMPUTE] == NULL) {
941 _mesa_error(ctx, GL_INVALID_OPERATION, "glGetProgramiv(no compute "
942 "shaders)");
943 return;
944 }
945 for (i = 0; i < 3; i++)
946 params[i] = shProg->_LinkedShaders[MESA_SHADER_COMPUTE]->
947 Program->info.workgroup_size[i];
948 return;
949 }
950 case GL_PROGRAM_SEPARABLE:
951 /* If the program has not been linked, return initial value 0. */
952 *params = (shProg->data->LinkStatus == LINKING_FAILURE) ? 0 : shProg->SeparateShader;
953 return;
954
955 /* ARB_tessellation_shader */
956 case GL_TESS_CONTROL_OUTPUT_VERTICES:
957 if (!has_tess)
958 break;
959 if (check_tcs_query(ctx, shProg)) {
960 *params = shProg->_LinkedShaders[MESA_SHADER_TESS_CTRL]->
961 Program->info.tess.tcs_vertices_out;
962 }
963 return;
964 case GL_TESS_GEN_MODE:
965 if (!has_tess)
966 break;
967 if (check_tes_query(ctx, shProg)) {
968 const struct gl_linked_shader *tes =
969 shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL];
970 switch (tes->Program->info.tess._primitive_mode) {
971 case TESS_PRIMITIVE_TRIANGLES:
972 *params = GL_TRIANGLES;
973 break;
974 case TESS_PRIMITIVE_QUADS:
975 *params = GL_QUADS;
976 break;
977 case TESS_PRIMITIVE_ISOLINES:
978 *params = GL_ISOLINES;
979 break;
980 case TESS_PRIMITIVE_UNSPECIFIED:
981 *params = 0;
982 break;
983 }
984 }
985 return;
986 case GL_TESS_GEN_SPACING:
987 if (!has_tess)
988 break;
989 if (check_tes_query(ctx, shProg)) {
990 const struct gl_linked_shader *tes =
991 shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL];
992 switch (tes->Program->info.tess.spacing) {
993 case TESS_SPACING_EQUAL:
994 *params = GL_EQUAL;
995 break;
996 case TESS_SPACING_FRACTIONAL_ODD:
997 *params = GL_FRACTIONAL_ODD;
998 break;
999 case TESS_SPACING_FRACTIONAL_EVEN:
1000 *params = GL_FRACTIONAL_EVEN;
1001 break;
1002 case TESS_SPACING_UNSPECIFIED:
1003 *params = 0;
1004 break;
1005 }
1006 }
1007 return;
1008 case GL_TESS_GEN_VERTEX_ORDER:
1009 if (!has_tess)
1010 break;
1011 if (check_tes_query(ctx, shProg)) {
1012 *params = shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL]->
1013 Program->info.tess.ccw ? GL_CCW : GL_CW;
1014 }
1015 return;
1016 case GL_TESS_GEN_POINT_MODE:
1017 if (!has_tess)
1018 break;
1019 if (check_tes_query(ctx, shProg)) {
1020 *params = shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL]->
1021 Program->info.tess.point_mode ? GL_TRUE : GL_FALSE;
1022 }
1023 return;
1024 default:
1025 break;
1026 }
1027
1028 _mesa_error(ctx, GL_INVALID_ENUM, "glGetProgramiv(pname=%s)",
1029 _mesa_enum_to_string(pname));
1030 }
1031
1032
1033 /**
1034 * glGetShaderiv() - get GLSL shader state
1035 */
1036 static void
get_shaderiv(struct gl_context * ctx,GLuint name,GLenum pname,GLint * params)1037 get_shaderiv(struct gl_context *ctx, GLuint name, GLenum pname, GLint *params)
1038 {
1039 struct gl_shader *shader =
1040 _mesa_lookup_shader_err(ctx, name, "glGetShaderiv");
1041
1042 if (!shader) {
1043 return;
1044 }
1045
1046 switch (pname) {
1047 case GL_SHADER_TYPE:
1048 *params = shader->Type;
1049 break;
1050 case GL_DELETE_STATUS:
1051 *params = shader->DeletePending;
1052 break;
1053 case GL_COMPLETION_STATUS_ARB:
1054 /* _mesa_glsl_compile_shader is not offloaded to other threads. */
1055 *params = GL_TRUE;
1056 return;
1057 case GL_COMPILE_STATUS:
1058 *params = shader->CompileStatus ? GL_TRUE : GL_FALSE;
1059 break;
1060 case GL_INFO_LOG_LENGTH:
1061 *params = (shader->InfoLog && shader->InfoLog[0] != '\0') ?
1062 strlen(shader->InfoLog) + 1 : 0;
1063 break;
1064 case GL_SHADER_SOURCE_LENGTH:
1065 *params = shader->Source ? strlen((char *) shader->Source) + 1 : 0;
1066 break;
1067 case GL_SPIR_V_BINARY_ARB:
1068 *params = (shader->spirv_data != NULL);
1069 break;
1070 default:
1071 _mesa_error(ctx, GL_INVALID_ENUM, "glGetShaderiv(pname)");
1072 return;
1073 }
1074 }
1075
1076
1077 static void
get_program_info_log(struct gl_context * ctx,GLuint program,GLsizei bufSize,GLsizei * length,GLchar * infoLog)1078 get_program_info_log(struct gl_context *ctx, GLuint program, GLsizei bufSize,
1079 GLsizei *length, GLchar *infoLog)
1080 {
1081 struct gl_shader_program *shProg;
1082
1083 /* Section 2.5 GL Errors (page 18) of the OpenGL ES 3.0.4 spec and
1084 * section 2.3.1 (Errors) of the OpenGL 4.5 spec say:
1085 *
1086 * "If a negative number is provided where an argument of type sizei or
1087 * sizeiptr is specified, an INVALID_VALUE error is generated."
1088 */
1089 if (bufSize < 0) {
1090 _mesa_error(ctx, GL_INVALID_VALUE, "glGetProgramInfoLog(bufSize < 0)");
1091 return;
1092 }
1093
1094 shProg = _mesa_lookup_shader_program_err(ctx, program,
1095 "glGetProgramInfoLog(program)");
1096 if (!shProg) {
1097 return;
1098 }
1099
1100 _mesa_copy_string(infoLog, bufSize, length, shProg->data->InfoLog);
1101 }
1102
1103
1104 static void
get_shader_info_log(struct gl_context * ctx,GLuint shader,GLsizei bufSize,GLsizei * length,GLchar * infoLog)1105 get_shader_info_log(struct gl_context *ctx, GLuint shader, GLsizei bufSize,
1106 GLsizei *length, GLchar *infoLog)
1107 {
1108 struct gl_shader *sh;
1109
1110 /* Section 2.5 GL Errors (page 18) of the OpenGL ES 3.0.4 spec and
1111 * section 2.3.1 (Errors) of the OpenGL 4.5 spec say:
1112 *
1113 * "If a negative number is provided where an argument of type sizei or
1114 * sizeiptr is specified, an INVALID_VALUE error is generated."
1115 */
1116 if (bufSize < 0) {
1117 _mesa_error(ctx, GL_INVALID_VALUE, "glGetShaderInfoLog(bufSize < 0)");
1118 return;
1119 }
1120
1121 sh = _mesa_lookup_shader_err(ctx, shader, "glGetShaderInfoLog(shader)");
1122 if (!sh) {
1123 return;
1124 }
1125
1126 _mesa_copy_string(infoLog, bufSize, length, sh->InfoLog);
1127 }
1128
1129
1130 /**
1131 * Return shader source code.
1132 */
1133 static void
get_shader_source(struct gl_context * ctx,GLuint shader,GLsizei maxLength,GLsizei * length,GLchar * sourceOut)1134 get_shader_source(struct gl_context *ctx, GLuint shader, GLsizei maxLength,
1135 GLsizei *length, GLchar *sourceOut)
1136 {
1137 struct gl_shader *sh;
1138
1139 if (maxLength < 0) {
1140 _mesa_error(ctx, GL_INVALID_VALUE, "glGetShaderSource(bufSize < 0)");
1141 return;
1142 }
1143
1144 sh = _mesa_lookup_shader_err(ctx, shader, "glGetShaderSource");
1145 if (!sh) {
1146 return;
1147 }
1148 _mesa_copy_string(sourceOut, maxLength, length, sh->Source);
1149 }
1150
1151
1152 /**
1153 * Set/replace shader source code. A helper function used by
1154 * glShaderSource[ARB].
1155 */
1156 static void
set_shader_source(struct gl_shader * sh,const GLchar * source,const blake3_hash original_blake3)1157 set_shader_source(struct gl_shader *sh, const GLchar *source,
1158 const blake3_hash original_blake3)
1159 {
1160 assert(sh);
1161
1162 /* The GL_ARB_gl_spirv spec adds the following to the end of the description
1163 * of ShaderSource:
1164 *
1165 * "If <shader> was previously associated with a SPIR-V module (via the
1166 * ShaderBinary command), that association is broken. Upon successful
1167 * completion of this command the SPIR_V_BINARY_ARB state of <shader>
1168 * is set to FALSE."
1169 */
1170 _mesa_shader_spirv_data_reference(&sh->spirv_data, NULL);
1171
1172 if (sh->CompileStatus == COMPILE_SKIPPED && !sh->FallbackSource) {
1173 /* If shader was previously compiled back-up the source in case of cache
1174 * fallback.
1175 */
1176 sh->FallbackSource = sh->Source;
1177 memcpy(sh->fallback_source_blake3, sh->source_blake3, BLAKE3_OUT_LEN);
1178 sh->Source = source;
1179 } else {
1180 /* free old shader source string and install new one */
1181 free((void *)sh->Source);
1182 sh->Source = source;
1183 }
1184
1185 memcpy(sh->source_blake3, original_blake3, BLAKE3_OUT_LEN);
1186 }
1187
1188 static void
ensure_builtin_types(struct gl_context * ctx)1189 ensure_builtin_types(struct gl_context *ctx)
1190 {
1191 if (!ctx->shader_builtin_ref) {
1192 _mesa_glsl_builtin_functions_init_or_ref();
1193 ctx->shader_builtin_ref = true;
1194 }
1195 }
1196
1197 /**
1198 * Compile a shader.
1199 */
1200 void
_mesa_compile_shader(struct gl_context * ctx,struct gl_shader * sh)1201 _mesa_compile_shader(struct gl_context *ctx, struct gl_shader *sh)
1202 {
1203 if (!sh)
1204 return;
1205
1206 /* The GL_ARB_gl_spirv spec says:
1207 *
1208 * "Add a new error for the CompileShader command:
1209 *
1210 * An INVALID_OPERATION error is generated if the SPIR_V_BINARY_ARB
1211 * state of <shader> is TRUE."
1212 */
1213 if (sh->spirv_data) {
1214 _mesa_error(ctx, GL_INVALID_OPERATION, "glCompileShader(SPIR-V)");
1215 return;
1216 }
1217
1218 if (!sh->Source) {
1219 /* If the user called glCompileShader without first calling
1220 * glShaderSource, we should fail to compile, but not raise a GL_ERROR.
1221 */
1222 sh->CompileStatus = COMPILE_FAILURE;
1223 } else {
1224 if (ctx->_Shader->Flags & (GLSL_DUMP | GLSL_SOURCE)) {
1225 _mesa_log("GLSL source for %s shader %d:\n",
1226 _mesa_shader_stage_to_string(sh->Stage), sh->Name);
1227 _mesa_log_direct(sh->Source);
1228 }
1229
1230 ensure_builtin_types(ctx);
1231
1232 /* this call will set the shader->CompileStatus field to indicate if
1233 * compilation was successful.
1234 */
1235 _mesa_glsl_compile_shader(ctx, sh, false, false, false);
1236
1237 if (ctx->_Shader->Flags & GLSL_LOG) {
1238 _mesa_write_shader_to_file(sh);
1239 }
1240
1241 if (ctx->_Shader->Flags & GLSL_DUMP) {
1242 if (sh->CompileStatus) {
1243 if (sh->ir) {
1244 _mesa_log("GLSL IR for shader %d:\n", sh->Name);
1245 _mesa_print_ir(mesa_log_get_file(), sh->ir, NULL);
1246 } else {
1247 _mesa_log("No GLSL IR for shader %d (shader may be from "
1248 "cache)\n", sh->Name);
1249 }
1250 _mesa_log("\n\n");
1251 } else {
1252 _mesa_log("GLSL shader %d failed to compile.\n", sh->Name);
1253 }
1254 if (sh->InfoLog && sh->InfoLog[0] != 0) {
1255 _mesa_log("GLSL shader %d info log:\n", sh->Name);
1256 _mesa_log("%s\n", sh->InfoLog);
1257 }
1258 }
1259 }
1260
1261 if (!sh->CompileStatus) {
1262 if (ctx->_Shader->Flags & GLSL_DUMP_ON_ERROR) {
1263 _mesa_log("GLSL source for %s shader %d:\n",
1264 _mesa_shader_stage_to_string(sh->Stage), sh->Name);
1265 _mesa_log("%s\n", sh->Source);
1266 _mesa_log("Info Log:\n%s\n", sh->InfoLog);
1267 }
1268
1269 if (ctx->_Shader->Flags & GLSL_REPORT_ERRORS) {
1270 _mesa_debug(ctx, "Error compiling shader %u:\n%s\n",
1271 sh->Name, sh->InfoLog);
1272 }
1273 }
1274 }
1275
1276
1277 struct update_programs_in_pipeline_params
1278 {
1279 struct gl_context *ctx;
1280 struct gl_shader_program *shProg;
1281 };
1282
1283 static void
update_programs_in_pipeline(void * data,void * userData)1284 update_programs_in_pipeline(void *data, void *userData)
1285 {
1286 struct update_programs_in_pipeline_params *params =
1287 (struct update_programs_in_pipeline_params *) userData;
1288 struct gl_pipeline_object *obj = (struct gl_pipeline_object *) data;
1289
1290 for (unsigned stage = 0; stage < MESA_SHADER_STAGES; stage++) {
1291 if (obj->CurrentProgram[stage] &&
1292 obj->CurrentProgram[stage]->Id == params->shProg->Name) {
1293 struct gl_program *prog = params->shProg->_LinkedShaders[stage]->Program;
1294 _mesa_use_program(params->ctx, stage, params->shProg, prog, obj);
1295 }
1296 }
1297 }
1298
1299
1300 /**
1301 * Link a program's shaders.
1302 */
1303 static ALWAYS_INLINE void
link_program(struct gl_context * ctx,struct gl_shader_program * shProg,bool no_error)1304 link_program(struct gl_context *ctx, struct gl_shader_program *shProg,
1305 bool no_error)
1306 {
1307 if (!shProg)
1308 return;
1309
1310 MESA_TRACE_FUNC();
1311
1312 if (!no_error) {
1313 /* From the ARB_transform_feedback2 specification:
1314 * "The error INVALID_OPERATION is generated by LinkProgram if <program>
1315 * is the name of a program being used by one or more transform feedback
1316 * objects, even if the objects are not currently bound or are paused."
1317 */
1318 if (_mesa_transform_feedback_is_using_program(ctx, shProg)) {
1319 _mesa_error(ctx, GL_INVALID_OPERATION,
1320 "glLinkProgram(transform feedback is using the program)");
1321 return;
1322 }
1323 }
1324
1325 unsigned programs_in_use = 0;
1326 if (ctx->_Shader)
1327 for (unsigned stage = 0; stage < MESA_SHADER_STAGES; stage++) {
1328 if (ctx->_Shader->CurrentProgram[stage] &&
1329 ctx->_Shader->CurrentProgram[stage]->Id == shProg->Name) {
1330 programs_in_use |= 1 << stage;
1331 }
1332 }
1333
1334 ensure_builtin_types(ctx);
1335
1336 FLUSH_VERTICES(ctx, 0, 0);
1337 st_link_shader(ctx, shProg);
1338
1339 /* From section 7.3 (Program Objects) of the OpenGL 4.5 spec:
1340 *
1341 * "If LinkProgram or ProgramBinary successfully re-links a program
1342 * object that is active for any shader stage, then the newly generated
1343 * executable code will be installed as part of the current rendering
1344 * state for all shader stages where the program is active.
1345 * Additionally, the newly generated executable code is made part of
1346 * the state of any program pipeline for all stages where the program
1347 * is attached."
1348 */
1349 if (shProg->data->LinkStatus) {
1350 while (programs_in_use) {
1351 const int stage = u_bit_scan(&programs_in_use);
1352
1353 struct gl_program *prog = NULL;
1354 if (shProg->_LinkedShaders[stage])
1355 prog = shProg->_LinkedShaders[stage]->Program;
1356
1357 _mesa_use_program(ctx, stage, shProg, prog, ctx->_Shader);
1358 }
1359
1360 struct update_programs_in_pipeline_params params = {
1361 .ctx = ctx,
1362 .shProg = shProg
1363 };
1364 _mesa_HashWalk(&ctx->Pipeline.Objects, update_programs_in_pipeline,
1365 ¶ms);
1366 }
1367
1368 #ifndef CUSTOM_SHADER_REPLACEMENT
1369 /* Capture .shader_test files. */
1370 const char *capture_path = _mesa_get_shader_capture_path();
1371 if (shProg->Name != 0 && shProg->Name != ~0 && capture_path != NULL) {
1372 /* Find an unused filename. */
1373 FILE *file = NULL;
1374 char *filename = NULL;
1375 for (unsigned i = 0;; i++) {
1376 if (i) {
1377 filename = ralloc_asprintf(NULL, "%s/%u-%u.shader_test",
1378 capture_path, shProg->Name, i);
1379 } else {
1380 filename = ralloc_asprintf(NULL, "%s/%u.shader_test",
1381 capture_path, shProg->Name);
1382 }
1383 file = os_file_create_unique(filename, 0644);
1384 if (file)
1385 break;
1386 /* If we are failing for another reason than "this filename already
1387 * exists", we are likely to fail again with another filename, so
1388 * let's just give up */
1389 if (errno != EEXIST)
1390 break;
1391 ralloc_free(filename);
1392 }
1393 if (file) {
1394 fprintf(file, "[require]\nGLSL%s >= %u.%02u\n",
1395 shProg->IsES ? " ES" : "", shProg->GLSL_Version / 100,
1396 shProg->GLSL_Version % 100);
1397 if (shProg->SeparateShader)
1398 fprintf(file, "GL_ARB_separate_shader_objects\nSSO ENABLED\n");
1399 fprintf(file, "\n");
1400
1401 for (unsigned i = 0; i < shProg->NumShaders; i++) {
1402 fprintf(file, "[%s shader]\n%s\n",
1403 _mesa_shader_stage_to_string(shProg->Shaders[i]->Stage),
1404 shProg->Shaders[i]->Source);
1405 }
1406 fclose(file);
1407 } else {
1408 _mesa_warning(ctx, "Failed to open %s", filename);
1409 }
1410
1411 ralloc_free(filename);
1412 }
1413 #endif
1414
1415 if (shProg->data->LinkStatus == LINKING_FAILURE &&
1416 (ctx->_Shader->Flags & GLSL_REPORT_ERRORS)) {
1417 _mesa_debug(ctx, "Error linking program %u:\n%s\n",
1418 shProg->Name, shProg->data->InfoLog);
1419 }
1420
1421 _mesa_update_vertex_processing_mode(ctx);
1422 _mesa_update_valid_to_render_state(ctx);
1423
1424 shProg->BinaryRetrievableHint = shProg->BinaryRetrievableHintPending;
1425
1426 /* debug code */
1427 if (0) {
1428 GLuint i;
1429
1430 printf("Link %u shaders in program %u: %s\n",
1431 shProg->NumShaders, shProg->Name,
1432 shProg->data->LinkStatus ? "Success" : "Failed");
1433
1434 for (i = 0; i < shProg->NumShaders; i++) {
1435 printf(" shader %u, stage %u\n",
1436 shProg->Shaders[i]->Name,
1437 shProg->Shaders[i]->Stage);
1438 }
1439 }
1440 }
1441
1442
1443 static void
link_program_error(struct gl_context * ctx,struct gl_shader_program * shProg)1444 link_program_error(struct gl_context *ctx, struct gl_shader_program *shProg)
1445 {
1446 link_program(ctx, shProg, false);
1447 }
1448
1449
1450 static void
link_program_no_error(struct gl_context * ctx,struct gl_shader_program * shProg)1451 link_program_no_error(struct gl_context *ctx, struct gl_shader_program *shProg)
1452 {
1453 link_program(ctx, shProg, true);
1454 }
1455
1456
1457 void
_mesa_link_program(struct gl_context * ctx,struct gl_shader_program * shProg)1458 _mesa_link_program(struct gl_context *ctx, struct gl_shader_program *shProg)
1459 {
1460 link_program_error(ctx, shProg);
1461 }
1462
1463
1464 /**
1465 * Print basic shader info (for debug).
1466 */
1467 static void
print_shader_info(const struct gl_shader_program * shProg)1468 print_shader_info(const struct gl_shader_program *shProg)
1469 {
1470 GLuint i;
1471
1472 printf("Mesa: glUseProgram(%u)\n", shProg->Name);
1473 for (i = 0; i < shProg->NumShaders; i++) {
1474 printf(" %s shader %u\n",
1475 _mesa_shader_stage_to_string(shProg->Shaders[i]->Stage),
1476 shProg->Shaders[i]->Name);
1477 }
1478 if (shProg->_LinkedShaders[MESA_SHADER_VERTEX])
1479 printf(" vert prog %u\n",
1480 shProg->_LinkedShaders[MESA_SHADER_VERTEX]->Program->Id);
1481 if (shProg->_LinkedShaders[MESA_SHADER_FRAGMENT])
1482 printf(" frag prog %u\n",
1483 shProg->_LinkedShaders[MESA_SHADER_FRAGMENT]->Program->Id);
1484 if (shProg->_LinkedShaders[MESA_SHADER_GEOMETRY])
1485 printf(" geom prog %u\n",
1486 shProg->_LinkedShaders[MESA_SHADER_GEOMETRY]->Program->Id);
1487 if (shProg->_LinkedShaders[MESA_SHADER_TESS_CTRL])
1488 printf(" tesc prog %u\n",
1489 shProg->_LinkedShaders[MESA_SHADER_TESS_CTRL]->Program->Id);
1490 if (shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL])
1491 printf(" tese prog %u\n",
1492 shProg->_LinkedShaders[MESA_SHADER_TESS_EVAL]->Program->Id);
1493 }
1494
1495
1496 /**
1497 * Use the named shader program for subsequent glUniform calls
1498 */
1499 void
_mesa_active_program(struct gl_context * ctx,struct gl_shader_program * shProg,const char * caller)1500 _mesa_active_program(struct gl_context *ctx, struct gl_shader_program *shProg,
1501 const char *caller)
1502 {
1503 if ((shProg != NULL) && !shProg->data->LinkStatus) {
1504 _mesa_error(ctx, GL_INVALID_OPERATION,
1505 "%s(program %u not linked)", caller, shProg->Name);
1506 return;
1507 }
1508
1509 if (ctx->Shader.ActiveProgram != shProg) {
1510 _mesa_reference_shader_program(ctx, &ctx->Shader.ActiveProgram, shProg);
1511 _mesa_update_valid_to_render_state(ctx);
1512 }
1513 }
1514
1515
1516 /**
1517 * Use the named shader program for subsequent rendering.
1518 */
1519 void
_mesa_use_shader_program(struct gl_context * ctx,struct gl_shader_program * shProg)1520 _mesa_use_shader_program(struct gl_context *ctx,
1521 struct gl_shader_program *shProg)
1522 {
1523 for (int i = 0; i < MESA_SHADER_STAGES; i++) {
1524 struct gl_program *new_prog = NULL;
1525 if (shProg && shProg->_LinkedShaders[i])
1526 new_prog = shProg->_LinkedShaders[i]->Program;
1527 _mesa_use_program(ctx, i, shProg, new_prog, &ctx->Shader);
1528 }
1529 _mesa_active_program(ctx, shProg, "glUseProgram");
1530 }
1531
1532
1533 /**
1534 * Do validation of the given shader program.
1535 * \param errMsg returns error message if validation fails.
1536 * \return GL_TRUE if valid, GL_FALSE if invalid (and set errMsg)
1537 */
1538 static GLboolean
validate_shader_program(const struct gl_shader_program * shProg,char * errMsg)1539 validate_shader_program(const struct gl_shader_program *shProg,
1540 char *errMsg)
1541 {
1542 if (!shProg->data->LinkStatus) {
1543 return GL_FALSE;
1544 }
1545
1546 /* From the GL spec, a program is invalid if any of these are true:
1547
1548 any two active samplers in the current program object are of
1549 different types, but refer to the same texture image unit,
1550
1551 any active sampler in the current program object refers to a texture
1552 image unit where fixed-function fragment processing accesses a
1553 texture target that does not match the sampler type, or
1554
1555 the sum of the number of active samplers in the program and the
1556 number of texture image units enabled for fixed-function fragment
1557 processing exceeds the combined limit on the total number of texture
1558 image units allowed.
1559 */
1560
1561 /*
1562 * Check: any two active samplers in the current program object are of
1563 * different types, but refer to the same texture image unit,
1564 */
1565 if (!_mesa_sampler_uniforms_are_valid(shProg, errMsg, 100))
1566 return GL_FALSE;
1567
1568 return GL_TRUE;
1569 }
1570
1571
1572 /**
1573 * Called via glValidateProgram()
1574 */
1575 static void
validate_program(struct gl_context * ctx,GLuint program)1576 validate_program(struct gl_context *ctx, GLuint program)
1577 {
1578 struct gl_shader_program *shProg;
1579 char errMsg[100] = "";
1580
1581 shProg = _mesa_lookup_shader_program_err(ctx, program, "glValidateProgram");
1582 if (!shProg) {
1583 return;
1584 }
1585
1586 shProg->data->Validated = validate_shader_program(shProg, errMsg);
1587 if (!shProg->data->Validated) {
1588 /* update info log */
1589 if (shProg->data->InfoLog) {
1590 ralloc_free(shProg->data->InfoLog);
1591 }
1592 shProg->data->InfoLog = ralloc_strdup(shProg->data, errMsg);
1593 }
1594 }
1595
1596
1597 void GLAPIENTRY
_mesa_AttachObjectARB_no_error(GLhandleARB program,GLhandleARB shader)1598 _mesa_AttachObjectARB_no_error(GLhandleARB program, GLhandleARB shader)
1599 {
1600 GET_CURRENT_CONTEXT(ctx);
1601 attach_shader_no_error(ctx, program, shader);
1602 }
1603
1604
1605 void GLAPIENTRY
_mesa_AttachObjectARB(GLhandleARB program,GLhandleARB shader)1606 _mesa_AttachObjectARB(GLhandleARB program, GLhandleARB shader)
1607 {
1608 GET_CURRENT_CONTEXT(ctx);
1609 attach_shader_err(ctx, program, shader, "glAttachObjectARB");
1610 }
1611
1612
1613 void GLAPIENTRY
_mesa_AttachShader_no_error(GLuint program,GLuint shader)1614 _mesa_AttachShader_no_error(GLuint program, GLuint shader)
1615 {
1616 GET_CURRENT_CONTEXT(ctx);
1617 attach_shader_no_error(ctx, program, shader);
1618 }
1619
1620
1621 void GLAPIENTRY
_mesa_AttachShader(GLuint program,GLuint shader)1622 _mesa_AttachShader(GLuint program, GLuint shader)
1623 {
1624 GET_CURRENT_CONTEXT(ctx);
1625 attach_shader_err(ctx, program, shader, "glAttachShader");
1626 }
1627
1628
1629 void GLAPIENTRY
_mesa_CompileShader(GLuint shaderObj)1630 _mesa_CompileShader(GLuint shaderObj)
1631 {
1632 GET_CURRENT_CONTEXT(ctx);
1633 if (MESA_VERBOSE & VERBOSE_API)
1634 _mesa_debug(ctx, "glCompileShader %u\n", shaderObj);
1635 _mesa_compile_shader(ctx, _mesa_lookup_shader_err(ctx, shaderObj,
1636 "glCompileShader"));
1637 }
1638
1639
1640 GLuint GLAPIENTRY
_mesa_CreateShader_no_error(GLenum type)1641 _mesa_CreateShader_no_error(GLenum type)
1642 {
1643 GET_CURRENT_CONTEXT(ctx);
1644 return create_shader(ctx, type);
1645 }
1646
1647
1648 GLuint GLAPIENTRY
_mesa_CreateShader(GLenum type)1649 _mesa_CreateShader(GLenum type)
1650 {
1651 GET_CURRENT_CONTEXT(ctx);
1652
1653 if (MESA_VERBOSE & VERBOSE_API)
1654 _mesa_debug(ctx, "glCreateShader %s\n", _mesa_enum_to_string(type));
1655
1656 return create_shader_err(ctx, type, "glCreateShader");
1657 }
1658
1659
1660 GLhandleARB GLAPIENTRY
_mesa_CreateShaderObjectARB_no_error(GLenum type)1661 _mesa_CreateShaderObjectARB_no_error(GLenum type)
1662 {
1663 GET_CURRENT_CONTEXT(ctx);
1664 return create_shader(ctx, type);
1665 }
1666
1667
1668 GLhandleARB GLAPIENTRY
_mesa_CreateShaderObjectARB(GLenum type)1669 _mesa_CreateShaderObjectARB(GLenum type)
1670 {
1671 GET_CURRENT_CONTEXT(ctx);
1672 return create_shader_err(ctx, type, "glCreateShaderObjectARB");
1673 }
1674
1675
1676 GLuint GLAPIENTRY
_mesa_CreateProgram(void)1677 _mesa_CreateProgram(void)
1678 {
1679 GET_CURRENT_CONTEXT(ctx);
1680 if (MESA_VERBOSE & VERBOSE_API)
1681 _mesa_debug(ctx, "glCreateProgram\n");
1682 return create_shader_program(ctx);
1683 }
1684
1685
1686 GLhandleARB GLAPIENTRY
_mesa_CreateProgramObjectARB(void)1687 _mesa_CreateProgramObjectARB(void)
1688 {
1689 GET_CURRENT_CONTEXT(ctx);
1690 return create_shader_program(ctx);
1691 }
1692
1693
1694 void GLAPIENTRY
_mesa_DeleteObjectARB(GLhandleARB obj)1695 _mesa_DeleteObjectARB(GLhandleARB obj)
1696 {
1697 if (MESA_VERBOSE & VERBOSE_API) {
1698 GET_CURRENT_CONTEXT(ctx);
1699 _mesa_debug(ctx, "glDeleteObjectARB(%lu)\n", (unsigned long)obj);
1700 }
1701
1702 if (obj) {
1703 GET_CURRENT_CONTEXT(ctx);
1704 FLUSH_VERTICES(ctx, 0, 0);
1705 if (is_program(ctx, obj)) {
1706 delete_shader_program(ctx, obj);
1707 }
1708 else if (is_shader(ctx, obj)) {
1709 delete_shader(ctx, obj);
1710 }
1711 else {
1712 _mesa_error(ctx, GL_INVALID_VALUE, "glDeleteObjectARB");
1713 }
1714 }
1715 }
1716
1717
1718 void GLAPIENTRY
_mesa_DeleteProgram(GLuint name)1719 _mesa_DeleteProgram(GLuint name)
1720 {
1721 if (name) {
1722 GET_CURRENT_CONTEXT(ctx);
1723 FLUSH_VERTICES(ctx, 0, 0);
1724 delete_shader_program(ctx, name);
1725 }
1726 }
1727
1728
1729 void GLAPIENTRY
_mesa_DeleteShader(GLuint name)1730 _mesa_DeleteShader(GLuint name)
1731 {
1732 if (name) {
1733 GET_CURRENT_CONTEXT(ctx);
1734 FLUSH_VERTICES(ctx, 0, 0);
1735 delete_shader(ctx, name);
1736 }
1737 }
1738
1739
1740 void GLAPIENTRY
_mesa_DetachObjectARB_no_error(GLhandleARB program,GLhandleARB shader)1741 _mesa_DetachObjectARB_no_error(GLhandleARB program, GLhandleARB shader)
1742 {
1743 GET_CURRENT_CONTEXT(ctx);
1744 detach_shader_no_error(ctx, program, shader);
1745 }
1746
1747
1748 void GLAPIENTRY
_mesa_DetachObjectARB(GLhandleARB program,GLhandleARB shader)1749 _mesa_DetachObjectARB(GLhandleARB program, GLhandleARB shader)
1750 {
1751 GET_CURRENT_CONTEXT(ctx);
1752 detach_shader_error(ctx, program, shader);
1753 }
1754
1755
1756 void GLAPIENTRY
_mesa_DetachShader_no_error(GLuint program,GLuint shader)1757 _mesa_DetachShader_no_error(GLuint program, GLuint shader)
1758 {
1759 GET_CURRENT_CONTEXT(ctx);
1760 detach_shader_no_error(ctx, program, shader);
1761 }
1762
1763
1764 void GLAPIENTRY
_mesa_DetachShader(GLuint program,GLuint shader)1765 _mesa_DetachShader(GLuint program, GLuint shader)
1766 {
1767 GET_CURRENT_CONTEXT(ctx);
1768 detach_shader_error(ctx, program, shader);
1769 }
1770
1771
1772 void GLAPIENTRY
_mesa_GetAttachedObjectsARB(GLhandleARB container,GLsizei maxCount,GLsizei * count,GLhandleARB * obj)1773 _mesa_GetAttachedObjectsARB(GLhandleARB container, GLsizei maxCount,
1774 GLsizei * count, GLhandleARB * obj)
1775 {
1776 GET_CURRENT_CONTEXT(ctx);
1777 get_attached_shaders(ctx, (GLuint)container, maxCount, count, NULL, obj);
1778 }
1779
1780
1781 void GLAPIENTRY
_mesa_GetAttachedShaders(GLuint program,GLsizei maxCount,GLsizei * count,GLuint * obj)1782 _mesa_GetAttachedShaders(GLuint program, GLsizei maxCount,
1783 GLsizei *count, GLuint *obj)
1784 {
1785 GET_CURRENT_CONTEXT(ctx);
1786 get_attached_shaders(ctx, program, maxCount, count, obj, NULL);
1787 }
1788
1789
1790 void GLAPIENTRY
_mesa_GetInfoLogARB(GLhandleARB object,GLsizei maxLength,GLsizei * length,GLcharARB * infoLog)1791 _mesa_GetInfoLogARB(GLhandleARB object, GLsizei maxLength, GLsizei * length,
1792 GLcharARB * infoLog)
1793 {
1794 GET_CURRENT_CONTEXT(ctx);
1795 if (is_program(ctx, object)) {
1796 get_program_info_log(ctx, object, maxLength, length, infoLog);
1797 }
1798 else if (is_shader(ctx, object)) {
1799 get_shader_info_log(ctx, object, maxLength, length, infoLog);
1800 }
1801 else {
1802 _mesa_error(ctx, GL_INVALID_OPERATION, "glGetInfoLogARB");
1803 }
1804 }
1805
1806
1807 void GLAPIENTRY
_mesa_GetObjectParameterivARB(GLhandleARB object,GLenum pname,GLint * params)1808 _mesa_GetObjectParameterivARB(GLhandleARB object, GLenum pname, GLint *params)
1809 {
1810 GET_CURRENT_CONTEXT(ctx);
1811 /* Implement in terms of GetProgramiv, GetShaderiv */
1812 if (is_program(ctx, object)) {
1813 if (pname == GL_OBJECT_TYPE_ARB) {
1814 *params = GL_PROGRAM_OBJECT_ARB;
1815 }
1816 else {
1817 get_programiv(ctx, object, pname, params);
1818 }
1819 }
1820 else if (is_shader(ctx, object)) {
1821 if (pname == GL_OBJECT_TYPE_ARB) {
1822 *params = GL_SHADER_OBJECT_ARB;
1823 }
1824 else {
1825 get_shaderiv(ctx, object, pname, params);
1826 }
1827 }
1828 else {
1829 _mesa_error(ctx, GL_INVALID_VALUE, "glGetObjectParameterivARB");
1830 }
1831 }
1832
1833
1834 void GLAPIENTRY
_mesa_GetObjectParameterfvARB(GLhandleARB object,GLenum pname,GLfloat * params)1835 _mesa_GetObjectParameterfvARB(GLhandleARB object, GLenum pname,
1836 GLfloat *params)
1837 {
1838 GLint iparams[1] = {0}; /* XXX is one element enough? */
1839 _mesa_GetObjectParameterivARB(object, pname, iparams);
1840 params[0] = (GLfloat) iparams[0];
1841 }
1842
1843
1844 void GLAPIENTRY
_mesa_GetProgramiv(GLuint program,GLenum pname,GLint * params)1845 _mesa_GetProgramiv(GLuint program, GLenum pname, GLint *params)
1846 {
1847 GET_CURRENT_CONTEXT(ctx);
1848 get_programiv(ctx, program, pname, params);
1849 }
1850
1851
1852 void GLAPIENTRY
_mesa_GetShaderiv(GLuint shader,GLenum pname,GLint * params)1853 _mesa_GetShaderiv(GLuint shader, GLenum pname, GLint *params)
1854 {
1855 GET_CURRENT_CONTEXT(ctx);
1856 get_shaderiv(ctx, shader, pname, params);
1857 }
1858
1859
1860 void GLAPIENTRY
_mesa_GetProgramInfoLog(GLuint program,GLsizei bufSize,GLsizei * length,GLchar * infoLog)1861 _mesa_GetProgramInfoLog(GLuint program, GLsizei bufSize,
1862 GLsizei *length, GLchar *infoLog)
1863 {
1864 GET_CURRENT_CONTEXT(ctx);
1865 get_program_info_log(ctx, program, bufSize, length, infoLog);
1866 }
1867
1868
1869 void GLAPIENTRY
_mesa_GetShaderInfoLog(GLuint shader,GLsizei bufSize,GLsizei * length,GLchar * infoLog)1870 _mesa_GetShaderInfoLog(GLuint shader, GLsizei bufSize,
1871 GLsizei *length, GLchar *infoLog)
1872 {
1873 GET_CURRENT_CONTEXT(ctx);
1874 get_shader_info_log(ctx, shader, bufSize, length, infoLog);
1875 }
1876
1877
1878 void GLAPIENTRY
_mesa_GetShaderSource(GLuint shader,GLsizei maxLength,GLsizei * length,GLchar * sourceOut)1879 _mesa_GetShaderSource(GLuint shader, GLsizei maxLength,
1880 GLsizei *length, GLchar *sourceOut)
1881 {
1882 GET_CURRENT_CONTEXT(ctx);
1883 get_shader_source(ctx, shader, maxLength, length, sourceOut);
1884 }
1885
1886
1887 GLhandleARB GLAPIENTRY
_mesa_GetHandleARB(GLenum pname)1888 _mesa_GetHandleARB(GLenum pname)
1889 {
1890 GET_CURRENT_CONTEXT(ctx);
1891 return get_handle(ctx, pname);
1892 }
1893
1894
1895 GLboolean GLAPIENTRY
_mesa_IsProgram(GLuint name)1896 _mesa_IsProgram(GLuint name)
1897 {
1898 GET_CURRENT_CONTEXT(ctx);
1899 return is_program(ctx, name);
1900 }
1901
1902
1903 GLboolean GLAPIENTRY
_mesa_IsShader(GLuint name)1904 _mesa_IsShader(GLuint name)
1905 {
1906 GET_CURRENT_CONTEXT(ctx);
1907 return is_shader(ctx, name);
1908 }
1909
1910
1911 void GLAPIENTRY
_mesa_LinkProgram_no_error(GLuint programObj)1912 _mesa_LinkProgram_no_error(GLuint programObj)
1913 {
1914 GET_CURRENT_CONTEXT(ctx);
1915
1916 struct gl_shader_program *shProg =
1917 _mesa_lookup_shader_program(ctx, programObj);
1918 link_program_no_error(ctx, shProg);
1919 }
1920
1921
1922 void GLAPIENTRY
_mesa_LinkProgram(GLuint programObj)1923 _mesa_LinkProgram(GLuint programObj)
1924 {
1925 GET_CURRENT_CONTEXT(ctx);
1926
1927 if (MESA_VERBOSE & VERBOSE_API)
1928 _mesa_debug(ctx, "glLinkProgram %u\n", programObj);
1929
1930 struct gl_shader_program *shProg =
1931 _mesa_lookup_shader_program_err(ctx, programObj, "glLinkProgram");
1932 link_program_error(ctx, shProg);
1933 }
1934
1935 #ifdef ENABLE_SHADER_CACHE
1936
1937 /**
1938 * Construct a full path for shader replacement functionality using
1939 * following format:
1940 *
1941 * <path>/<stage prefix>_<CHECKSUM>.glsl
1942 * <path>/<stage prefix>_<CHECKSUM>.arb
1943 */
1944 static char *
construct_name(const gl_shader_stage stage,const char * blake3_str,const char * source,const char * path)1945 construct_name(const gl_shader_stage stage, const char *blake3_str,
1946 const char *source, const char *path)
1947 {
1948 static const char *types[] = {
1949 "VS", "TC", "TE", "GS", "FS", "CS",
1950 };
1951
1952 const char *format = strncmp(source, "!!ARB", 5) ? "glsl" : "arb";
1953
1954 return ralloc_asprintf(NULL, "%s/%s_%s.%s", path, types[stage], blake3_str, format);
1955 }
1956
1957 /**
1958 * Write given shader source to a file in MESA_SHADER_DUMP_PATH.
1959 */
1960 void
_mesa_dump_shader_source(const gl_shader_stage stage,const char * source,const blake3_hash blake3)1961 _mesa_dump_shader_source(const gl_shader_stage stage, const char *source,
1962 const blake3_hash blake3)
1963 {
1964 #ifndef CUSTOM_SHADER_REPLACEMENT
1965 static bool path_exists = true;
1966 char *dump_path;
1967 FILE *f;
1968 char blake3_str[BLAKE3_OUT_LEN * 2 + 1];
1969
1970 if (!path_exists)
1971 return;
1972
1973 dump_path = secure_getenv("MESA_SHADER_DUMP_PATH");
1974 if (!dump_path) {
1975 path_exists = false;
1976 return;
1977 }
1978
1979 _mesa_blake3_format(blake3_str, blake3);
1980 char *name = construct_name(stage, blake3_str, source, dump_path);
1981
1982 f = fopen(name, "w");
1983 if (f) {
1984 fputs(source, f);
1985 fclose(f);
1986 } else {
1987 GET_CURRENT_CONTEXT(ctx);
1988 _mesa_warning(ctx, "could not open %s for dumping shader (%s)", name,
1989 strerror(errno));
1990 }
1991 ralloc_free(name);
1992 #endif
1993 }
1994
1995 /**
1996 * Read shader source code from a file.
1997 * Useful for debugging to override an app's shader.
1998 */
1999 GLcharARB *
_mesa_read_shader_source(const gl_shader_stage stage,const char * source,const blake3_hash blake3)2000 _mesa_read_shader_source(const gl_shader_stage stage, const char *source,
2001 const blake3_hash blake3)
2002 {
2003 char *read_path;
2004 static bool path_exists = true;
2005 int len, shader_size = 0;
2006 GLcharARB *buffer;
2007 FILE *f;
2008 char blake3_str[BLAKE3_OUT_LEN * 2 + 1];
2009
2010 _mesa_blake3_format(blake3_str, blake3);
2011
2012 if (!debug_get_bool_option("MESA_NO_SHADER_REPLACEMENT", false)) {
2013 const char *process_name = util_get_process_name();
2014
2015 char *new_source = try_direct_replace(process_name, source);
2016 if (new_source)
2017 return new_source;
2018
2019 for (size_t i = 0; i < ARRAY_SIZE(shader_replacements); i++) {
2020 if (stage != shader_replacements[i].stage)
2021 continue;
2022
2023 if (shader_replacements[i].app &&
2024 strcmp(process_name, shader_replacements[i].app) != 0)
2025 continue;
2026
2027 if (memcmp(blake3_str, shader_replacements[i].blake3,
2028 BLAKE3_OUT_LEN * 2) != 0)
2029 continue;
2030
2031 return load_shader_replacement(&shader_replacements[i]);
2032 }
2033 }
2034
2035 if (!path_exists)
2036 return NULL;
2037
2038 read_path = getenv("MESA_SHADER_READ_PATH");
2039 if (!read_path) {
2040 path_exists = false;
2041 return NULL;
2042 }
2043
2044 char *name = construct_name(stage, blake3_str, source, read_path);
2045 f = fopen(name, "r");
2046 ralloc_free(name);
2047 if (!f)
2048 return NULL;
2049
2050 /* allocate enough room for the entire shader */
2051 fseek(f, 0, SEEK_END);
2052 shader_size = ftell(f);
2053 rewind(f);
2054 assert(shader_size);
2055
2056 /* add one for terminating zero */
2057 shader_size++;
2058
2059 buffer = malloc(shader_size);
2060 assert(buffer);
2061
2062 len = fread(buffer, 1, shader_size, f);
2063 buffer[len] = 0;
2064
2065 fclose(f);
2066
2067 return buffer;
2068 }
2069
2070 #endif /* ENABLE_SHADER_CACHE */
2071
2072 /**
2073 * Called via glShaderSource() and glShaderSourceARB() API functions.
2074 * Basically, concatenate the source code strings into one long string
2075 * and pass it to _mesa_shader_source().
2076 */
2077 static ALWAYS_INLINE void
shader_source(struct gl_context * ctx,GLuint shaderObj,GLsizei count,const GLchar * const * string,const GLint * length,bool no_error)2078 shader_source(struct gl_context *ctx, GLuint shaderObj, GLsizei count,
2079 const GLchar *const *string, const GLint *length, bool no_error)
2080 {
2081 GLint *offsets;
2082 GLsizei i, totalLength;
2083 GLcharARB *source;
2084 struct gl_shader *sh;
2085
2086 if (!no_error) {
2087 sh = _mesa_lookup_shader_err(ctx, shaderObj, "glShaderSourceARB");
2088 if (!sh)
2089 return;
2090
2091 if (string == NULL || count < 0) {
2092 _mesa_error(ctx, GL_INVALID_VALUE, "glShaderSourceARB");
2093 return;
2094 }
2095 } else {
2096 sh = _mesa_lookup_shader(ctx, shaderObj);
2097 }
2098
2099 /* Return silently the spec doesn't define this as an error */
2100 if (count == 0)
2101 return;
2102
2103 /*
2104 * This array holds offsets of where the appropriate string ends, thus the
2105 * last element will be set to the total length of the source code.
2106 */
2107 offsets = calloc(count, sizeof(GLint));
2108 if (offsets == NULL) {
2109 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glShaderSourceARB");
2110 return;
2111 }
2112
2113 for (i = 0; i < count; i++) {
2114 if (!no_error && string[i] == NULL) {
2115 free((GLvoid *) offsets);
2116 _mesa_error(ctx, GL_INVALID_OPERATION,
2117 "glShaderSourceARB(null string)");
2118 return;
2119 }
2120 if (length == NULL || length[i] < 0)
2121 offsets[i] = strlen(string[i]);
2122 else
2123 offsets[i] = length[i];
2124 /* accumulate string lengths */
2125 if (i > 0)
2126 offsets[i] += offsets[i - 1];
2127 }
2128
2129 /* Total length of source string is sum off all strings plus two.
2130 * One extra byte for terminating zero, another extra byte to silence
2131 * valgrind warnings in the parser/grammer code.
2132 */
2133 totalLength = offsets[count - 1] + 2;
2134 source = malloc(totalLength * sizeof(GLcharARB));
2135 if (source == NULL) {
2136 free((GLvoid *) offsets);
2137 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glShaderSourceARB");
2138 return;
2139 }
2140
2141 for (i = 0; i < count; i++) {
2142 GLint start = (i > 0) ? offsets[i - 1] : 0;
2143 memcpy(source + start, string[i],
2144 (offsets[i] - start) * sizeof(GLcharARB));
2145 }
2146 source[totalLength - 1] = '\0';
2147 source[totalLength - 2] = '\0';
2148
2149 /* Compute the original source blake3 before shader replacement. */
2150 blake3_hash original_blake3;
2151 _mesa_blake3_compute(source, strlen(source), original_blake3);
2152
2153 #ifdef ENABLE_SHADER_CACHE
2154 GLcharARB *replacement;
2155
2156 /* Dump original shader source to MESA_SHADER_DUMP_PATH and replace
2157 * if corresponding entry found from MESA_SHADER_READ_PATH.
2158 */
2159 _mesa_dump_shader_source(sh->Stage, source, original_blake3);
2160
2161 replacement = _mesa_read_shader_source(sh->Stage, source, original_blake3);
2162 if (replacement) {
2163 free(source);
2164 source = replacement;
2165 }
2166 #endif /* ENABLE_SHADER_CACHE */
2167
2168 set_shader_source(sh, source, original_blake3);
2169
2170 free(offsets);
2171 }
2172
2173
2174 void GLAPIENTRY
_mesa_ShaderSource_no_error(GLuint shaderObj,GLsizei count,const GLchar * const * string,const GLint * length)2175 _mesa_ShaderSource_no_error(GLuint shaderObj, GLsizei count,
2176 const GLchar *const *string, const GLint *length)
2177 {
2178 GET_CURRENT_CONTEXT(ctx);
2179 shader_source(ctx, shaderObj, count, string, length, true);
2180 }
2181
2182
2183 void GLAPIENTRY
_mesa_ShaderSource(GLuint shaderObj,GLsizei count,const GLchar * const * string,const GLint * length)2184 _mesa_ShaderSource(GLuint shaderObj, GLsizei count,
2185 const GLchar *const *string, const GLint *length)
2186 {
2187 GET_CURRENT_CONTEXT(ctx);
2188 shader_source(ctx, shaderObj, count, string, length, false);
2189 }
2190
2191
2192 static ALWAYS_INLINE void
use_program(GLuint program,bool no_error)2193 use_program(GLuint program, bool no_error)
2194 {
2195 GET_CURRENT_CONTEXT(ctx);
2196 struct gl_shader_program *shProg = NULL;
2197
2198 if (MESA_VERBOSE & VERBOSE_API)
2199 _mesa_debug(ctx, "glUseProgram %u\n", program);
2200
2201 if (no_error) {
2202 if (program) {
2203 shProg = _mesa_lookup_shader_program(ctx, program);
2204 }
2205 } else {
2206 if (_mesa_is_xfb_active_and_unpaused(ctx)) {
2207 _mesa_error(ctx, GL_INVALID_OPERATION,
2208 "glUseProgram(transform feedback active)");
2209 return;
2210 }
2211
2212 if (program) {
2213 shProg =
2214 _mesa_lookup_shader_program_err(ctx, program, "glUseProgram");
2215 if (!shProg)
2216 return;
2217
2218 if (!shProg->data->LinkStatus) {
2219 _mesa_error(ctx, GL_INVALID_OPERATION,
2220 "glUseProgram(program %u not linked)", program);
2221 return;
2222 }
2223
2224 /* debug code */
2225 if (ctx->_Shader->Flags & GLSL_USE_PROG) {
2226 print_shader_info(shProg);
2227 }
2228 }
2229 }
2230
2231 /* The ARB_separate_shader_object spec says:
2232 *
2233 * "The executable code for an individual shader stage is taken from
2234 * the current program for that stage. If there is a current program
2235 * object established by UseProgram, that program is considered current
2236 * for all stages. Otherwise, if there is a bound program pipeline
2237 * object (section 2.14.PPO), the program bound to the appropriate
2238 * stage of the pipeline object is considered current."
2239 */
2240 if (shProg) {
2241 /* Attach shader state to the binding point */
2242 _mesa_reference_pipeline_object(ctx, &ctx->_Shader, &ctx->Shader);
2243 /* Update the program */
2244 _mesa_use_shader_program(ctx, shProg);
2245 } else {
2246 /* Must be done first: detach the progam */
2247 _mesa_use_shader_program(ctx, shProg);
2248 /* Unattach shader_state binding point */
2249 _mesa_reference_pipeline_object(ctx, &ctx->_Shader,
2250 ctx->Pipeline.Default);
2251 /* If a pipeline was bound, rebind it */
2252 if (ctx->Pipeline.Current) {
2253 if (no_error)
2254 _mesa_BindProgramPipeline_no_error(ctx->Pipeline.Current->Name);
2255 else
2256 _mesa_BindProgramPipeline(ctx->Pipeline.Current->Name);
2257 }
2258 }
2259
2260 _mesa_update_vertex_processing_mode(ctx);
2261 }
2262
2263
2264 void GLAPIENTRY
_mesa_UseProgram_no_error(GLuint program)2265 _mesa_UseProgram_no_error(GLuint program)
2266 {
2267 use_program(program, true);
2268 }
2269
2270
2271 void GLAPIENTRY
_mesa_UseProgram(GLuint program)2272 _mesa_UseProgram(GLuint program)
2273 {
2274 use_program(program, false);
2275 }
2276
2277
2278 void GLAPIENTRY
_mesa_ValidateProgram(GLuint program)2279 _mesa_ValidateProgram(GLuint program)
2280 {
2281 GET_CURRENT_CONTEXT(ctx);
2282 validate_program(ctx, program);
2283 }
2284
2285
2286 /**
2287 * For OpenGL ES 2.0, GL_ARB_ES2_compatibility
2288 */
2289 void GLAPIENTRY
_mesa_GetShaderPrecisionFormat(GLenum shadertype,GLenum precisiontype,GLint * range,GLint * precision)2290 _mesa_GetShaderPrecisionFormat(GLenum shadertype, GLenum precisiontype,
2291 GLint* range, GLint* precision)
2292 {
2293 const struct gl_program_constants *limits;
2294 const struct gl_precision *p;
2295 GET_CURRENT_CONTEXT(ctx);
2296
2297 switch (shadertype) {
2298 case GL_VERTEX_SHADER:
2299 limits = &ctx->Const.Program[MESA_SHADER_VERTEX];
2300 break;
2301 case GL_FRAGMENT_SHADER:
2302 limits = &ctx->Const.Program[MESA_SHADER_FRAGMENT];
2303 break;
2304 default:
2305 _mesa_error(ctx, GL_INVALID_ENUM,
2306 "glGetShaderPrecisionFormat(shadertype)");
2307 return;
2308 }
2309
2310 switch (precisiontype) {
2311 case GL_LOW_FLOAT:
2312 p = &limits->LowFloat;
2313 break;
2314 case GL_MEDIUM_FLOAT:
2315 p = &limits->MediumFloat;
2316 break;
2317 case GL_HIGH_FLOAT:
2318 p = &limits->HighFloat;
2319 break;
2320 case GL_LOW_INT:
2321 p = &limits->LowInt;
2322 break;
2323 case GL_MEDIUM_INT:
2324 p = &limits->MediumInt;
2325 break;
2326 case GL_HIGH_INT:
2327 p = &limits->HighInt;
2328 break;
2329 default:
2330 _mesa_error(ctx, GL_INVALID_ENUM,
2331 "glGetShaderPrecisionFormat(precisiontype)");
2332 return;
2333 }
2334
2335 range[0] = p->RangeMin;
2336 range[1] = p->RangeMax;
2337 precision[0] = p->Precision;
2338 }
2339
2340
2341 /**
2342 * For OpenGL ES 2.0, GL_ARB_ES2_compatibility
2343 */
2344 void GLAPIENTRY
_mesa_ReleaseShaderCompiler(void)2345 _mesa_ReleaseShaderCompiler(void)
2346 {
2347 GET_CURRENT_CONTEXT(ctx);
2348
2349 if (ctx->shader_builtin_ref) {
2350 _mesa_glsl_builtin_functions_decref();
2351 ctx->shader_builtin_ref = false;
2352 }
2353 }
2354
2355
2356 /**
2357 * For OpenGL ES 2.0, GL_ARB_ES2_compatibility
2358 */
2359 void GLAPIENTRY
_mesa_ShaderBinary(GLint n,const GLuint * shaders,GLenum binaryformat,const void * binary,GLint length)2360 _mesa_ShaderBinary(GLint n, const GLuint* shaders, GLenum binaryformat,
2361 const void* binary, GLint length)
2362 {
2363 GET_CURRENT_CONTEXT(ctx);
2364 struct gl_shader **sh;
2365
2366 /* no binary data can be loaded if length==0 */
2367 if (!length)
2368 binary = NULL;
2369
2370 /* Page 68, section 7.2 'Shader Binaries" of the of the OpenGL ES 3.1, and
2371 * page 88 of the OpenGL 4.5 specs state:
2372 *
2373 * "An INVALID_VALUE error is generated if count or length is negative.
2374 * An INVALID_ENUM error is generated if binaryformat is not a supported
2375 * format returned in SHADER_BINARY_FORMATS."
2376 */
2377 if (n < 0 || length < 0) {
2378 _mesa_error(ctx, GL_INVALID_VALUE, "glShaderBinary(count or length < 0)");
2379 return;
2380 }
2381
2382 /* Get all shader objects at once so we can make the operation
2383 * all-or-nothing.
2384 */
2385 if (n > SIZE_MAX / sizeof(*sh)) {
2386 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glShaderBinary(count)");
2387 return;
2388 }
2389
2390 sh = alloca(sizeof(*sh) * (size_t)n);
2391 if (!sh) {
2392 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glShaderBinary");
2393 return;
2394 }
2395
2396 for (int i = 0; i < n; ++i) {
2397 sh[i] = _mesa_lookup_shader_err(ctx, shaders[i], "glShaderBinary");
2398 if (!sh[i])
2399 return;
2400 }
2401
2402 if (binaryformat == GL_SHADER_BINARY_FORMAT_SPIR_V_ARB) {
2403 if (!ctx->Extensions.ARB_gl_spirv) {
2404 _mesa_error(ctx, GL_INVALID_OPERATION, "glShaderBinary(SPIR-V)");
2405 } else if (n > 0) {
2406 _mesa_spirv_shader_binary(ctx, (unsigned) n, sh, binary,
2407 (size_t) length);
2408 }
2409
2410 return;
2411 }
2412
2413 _mesa_error(ctx, GL_INVALID_ENUM, "glShaderBinary(format)");
2414 }
2415
2416
2417 void GLAPIENTRY
_mesa_GetProgramBinary(GLuint program,GLsizei bufSize,GLsizei * length,GLenum * binaryFormat,GLvoid * binary)2418 _mesa_GetProgramBinary(GLuint program, GLsizei bufSize, GLsizei *length,
2419 GLenum *binaryFormat, GLvoid *binary)
2420 {
2421 struct gl_shader_program *shProg;
2422 GLsizei length_dummy;
2423 GET_CURRENT_CONTEXT(ctx);
2424
2425 if (bufSize < 0){
2426 _mesa_error(ctx, GL_INVALID_VALUE, "glGetProgramBinary(bufSize < 0)");
2427 return;
2428 }
2429
2430 shProg = _mesa_lookup_shader_program_err(ctx, program, "glGetProgramBinary");
2431 if (!shProg)
2432 return;
2433
2434 /* The ARB_get_program_binary spec says:
2435 *
2436 * "If <length> is NULL, then no length is returned."
2437 *
2438 * Ensure that length always points to valid storage to avoid multiple NULL
2439 * pointer checks below.
2440 */
2441 if (length == NULL)
2442 length = &length_dummy;
2443
2444
2445 /* The ARB_get_program_binary spec says:
2446 *
2447 * "When a program object's LINK_STATUS is FALSE, its program binary
2448 * length is zero, and a call to GetProgramBinary will generate an
2449 * INVALID_OPERATION error.
2450 */
2451 if (!shProg->data->LinkStatus) {
2452 _mesa_error(ctx, GL_INVALID_OPERATION,
2453 "glGetProgramBinary(program %u not linked)",
2454 shProg->Name);
2455 *length = 0;
2456 return;
2457 }
2458
2459 if (ctx->Const.NumProgramBinaryFormats == 0) {
2460 *length = 0;
2461 _mesa_error(ctx, GL_INVALID_OPERATION,
2462 "glGetProgramBinary(driver supports zero binary formats)");
2463 } else {
2464 _mesa_get_program_binary(ctx, shProg, bufSize, length, binaryFormat,
2465 binary);
2466 assert(*length == 0 || *binaryFormat == GL_PROGRAM_BINARY_FORMAT_MESA);
2467 }
2468 }
2469
2470 void GLAPIENTRY
_mesa_ProgramBinary(GLuint program,GLenum binaryFormat,const GLvoid * binary,GLsizei length)2471 _mesa_ProgramBinary(GLuint program, GLenum binaryFormat,
2472 const GLvoid *binary, GLsizei length)
2473 {
2474 struct gl_shader_program *shProg;
2475 GET_CURRENT_CONTEXT(ctx);
2476
2477 shProg = _mesa_lookup_shader_program_err(ctx, program, "glProgramBinary");
2478 if (!shProg)
2479 return;
2480
2481 _mesa_clear_shader_program_data(ctx, shProg);
2482 shProg->data = _mesa_create_shader_program_data();
2483
2484 /* Section 2.3.1 (Errors) of the OpenGL 4.5 spec says:
2485 *
2486 * "If a negative number is provided where an argument of type sizei or
2487 * sizeiptr is specified, an INVALID_VALUE error is generated."
2488 */
2489 if (length < 0) {
2490 _mesa_error(ctx, GL_INVALID_VALUE, "glProgramBinary(length < 0)");
2491 return;
2492 }
2493
2494 if (ctx->Const.NumProgramBinaryFormats == 0 ||
2495 binaryFormat != GL_PROGRAM_BINARY_FORMAT_MESA) {
2496 /* The ARB_get_program_binary spec says:
2497 *
2498 * "<binaryFormat> and <binary> must be those returned by a previous
2499 * call to GetProgramBinary, and <length> must be the length of the
2500 * program binary as returned by GetProgramBinary or GetProgramiv with
2501 * <pname> PROGRAM_BINARY_LENGTH. Loading the program binary will fail,
2502 * setting the LINK_STATUS of <program> to FALSE, if these conditions
2503 * are not met."
2504 *
2505 * Since any value of binaryFormat passed "is not one of those specified as
2506 * allowable for [this] command, an INVALID_ENUM error is generated."
2507 */
2508 shProg->data->LinkStatus = LINKING_FAILURE;
2509 _mesa_error(ctx, GL_INVALID_ENUM, "glProgramBinary");
2510 } else {
2511 _mesa_program_binary(ctx, shProg, binaryFormat, binary, length);
2512 }
2513 }
2514
2515
2516 static ALWAYS_INLINE void
program_parameteri(struct gl_context * ctx,struct gl_shader_program * shProg,GLuint pname,GLint value,bool no_error)2517 program_parameteri(struct gl_context *ctx, struct gl_shader_program *shProg,
2518 GLuint pname, GLint value, bool no_error)
2519 {
2520 switch (pname) {
2521 case GL_PROGRAM_BINARY_RETRIEVABLE_HINT:
2522 /* This enum isn't part of the OES extension for OpenGL ES 2.0, but it
2523 * is part of OpenGL ES 3.0. For the ES2 case, this function shouldn't
2524 * even be in the dispatch table, so we shouldn't need to expclicitly
2525 * check here.
2526 *
2527 * On desktop, we ignore the 3.0+ requirement because it is silly.
2528 */
2529
2530 /* The ARB_get_program_binary extension spec says:
2531 *
2532 * "An INVALID_VALUE error is generated if the <value> argument to
2533 * ProgramParameteri is not TRUE or FALSE."
2534 */
2535 if (!no_error && value != GL_TRUE && value != GL_FALSE) {
2536 goto invalid_value;
2537 }
2538
2539 /* No need to notify the driver. Any changes will actually take effect
2540 * the next time the shader is linked.
2541 *
2542 * The ARB_get_program_binary extension spec says:
2543 *
2544 * "To indicate that a program binary is likely to be retrieved,
2545 * ProgramParameteri should be called with <pname>
2546 * PROGRAM_BINARY_RETRIEVABLE_HINT and <value> TRUE. This setting
2547 * will not be in effect until the next time LinkProgram or
2548 * ProgramBinary has been called successfully."
2549 *
2550 * The resolution of issue 9 in the extension spec also says:
2551 *
2552 * "The application may use the PROGRAM_BINARY_RETRIEVABLE_HINT hint
2553 * to indicate to the GL implementation that this program will
2554 * likely be saved with GetProgramBinary at some point. This will
2555 * give the GL implementation the opportunity to track any state
2556 * changes made to the program before being saved such that when it
2557 * is loaded again a recompile can be avoided."
2558 */
2559 shProg->BinaryRetrievableHintPending = value;
2560 return;
2561
2562 case GL_PROGRAM_SEPARABLE:
2563 /* Spec imply that the behavior is the same as ARB_get_program_binary
2564 * Chapter 7.3 Program Objects
2565 */
2566 if (!no_error && value != GL_TRUE && value != GL_FALSE) {
2567 goto invalid_value;
2568 }
2569 shProg->SeparateShader = value;
2570 return;
2571
2572 default:
2573 if (!no_error) {
2574 _mesa_error(ctx, GL_INVALID_ENUM, "glProgramParameteri(pname=%s)",
2575 _mesa_enum_to_string(pname));
2576 }
2577 return;
2578 }
2579
2580 invalid_value:
2581 _mesa_error(ctx, GL_INVALID_VALUE,
2582 "glProgramParameteri(pname=%s, value=%d): "
2583 "value must be 0 or 1.",
2584 _mesa_enum_to_string(pname),
2585 value);
2586 }
2587
2588
2589 void GLAPIENTRY
_mesa_ProgramParameteri_no_error(GLuint program,GLenum pname,GLint value)2590 _mesa_ProgramParameteri_no_error(GLuint program, GLenum pname, GLint value)
2591 {
2592 GET_CURRENT_CONTEXT(ctx);
2593
2594 struct gl_shader_program *shProg = _mesa_lookup_shader_program(ctx, program);
2595 program_parameteri(ctx, shProg, pname, value, true);
2596 }
2597
2598
2599 void GLAPIENTRY
_mesa_ProgramParameteri(GLuint program,GLenum pname,GLint value)2600 _mesa_ProgramParameteri(GLuint program, GLenum pname, GLint value)
2601 {
2602 struct gl_shader_program *shProg;
2603 GET_CURRENT_CONTEXT(ctx);
2604
2605 shProg = _mesa_lookup_shader_program_err(ctx, program,
2606 "glProgramParameteri");
2607 if (!shProg)
2608 return;
2609
2610 program_parameteri(ctx, shProg, pname, value, false);
2611 }
2612
2613
2614 void
_mesa_use_program(struct gl_context * ctx,gl_shader_stage stage,struct gl_shader_program * shProg,struct gl_program * prog,struct gl_pipeline_object * shTarget)2615 _mesa_use_program(struct gl_context *ctx, gl_shader_stage stage,
2616 struct gl_shader_program *shProg, struct gl_program *prog,
2617 struct gl_pipeline_object *shTarget)
2618 {
2619 struct gl_program **target;
2620
2621 target = &shTarget->CurrentProgram[stage];
2622 if (prog) {
2623 _mesa_program_init_subroutine_defaults(ctx, prog);
2624 }
2625
2626 if (*target != prog) {
2627 /* Program is current, flush it */
2628 if (shTarget == ctx->_Shader) {
2629 FLUSH_VERTICES(ctx, _NEW_PROGRAM | _NEW_PROGRAM_CONSTANTS, 0);
2630 }
2631
2632 _mesa_reference_shader_program(ctx,
2633 &shTarget->ReferencedPrograms[stage],
2634 shProg);
2635 _mesa_reference_program(ctx, target, prog);
2636 _mesa_update_allow_draw_out_of_order(ctx);
2637 _mesa_update_valid_to_render_state(ctx);
2638 if (stage == MESA_SHADER_VERTEX)
2639 _mesa_update_vertex_processing_mode(ctx);
2640 return;
2641 }
2642
2643 }
2644
2645
2646 /**
2647 * ARB_separate_shader_objects: Compile & Link Program
2648 */
2649 GLuint
_mesa_CreateShaderProgramv_impl(struct gl_context * ctx,GLenum type,GLsizei count,const GLchar * const * strings)2650 _mesa_CreateShaderProgramv_impl(struct gl_context *ctx,
2651 GLenum type, GLsizei count,
2652 const GLchar* const *strings)
2653 {
2654 const GLuint shader = create_shader_err(ctx, type, "glCreateShaderProgramv");
2655 GLuint program = 0;
2656
2657 /*
2658 * According to OpenGL 4.5 and OpenGL ES 3.1 standards, section 7.3:
2659 * GL_INVALID_VALUE should be generated if count < 0
2660 */
2661 if (count < 0) {
2662 _mesa_error(ctx, GL_INVALID_VALUE, "glCreateShaderProgram (count < 0)");
2663 return program;
2664 }
2665
2666 if (shader) {
2667 struct gl_shader *sh = _mesa_lookup_shader(ctx, shader);
2668
2669 _mesa_ShaderSource(shader, count, strings, NULL);
2670 _mesa_compile_shader(ctx, sh);
2671
2672 program = create_shader_program(ctx);
2673 if (program) {
2674 struct gl_shader_program *shProg;
2675 GLint compiled = GL_FALSE;
2676
2677 shProg = _mesa_lookup_shader_program(ctx, program);
2678
2679 shProg->SeparateShader = GL_TRUE;
2680
2681 get_shaderiv(ctx, shader, GL_COMPILE_STATUS, &compiled);
2682 if (compiled) {
2683 attach_shader_err(ctx, program, shader, "glCreateShaderProgramv");
2684 _mesa_link_program(ctx, shProg);
2685 detach_shader_error(ctx, program, shader);
2686
2687 #if 0
2688 /* Possibly... */
2689 if (active-user-defined-varyings-in-linked-program) {
2690 append-error-to-info-log;
2691 shProg->data->LinkStatus = LINKING_FAILURE;
2692 }
2693 #endif
2694 }
2695 if (sh->InfoLog)
2696 ralloc_strcat(&shProg->data->InfoLog, sh->InfoLog);
2697 }
2698
2699 delete_shader(ctx, shader);
2700 }
2701
2702 return program;
2703 }
2704
2705 /**
2706 * ARB_separate_shader_objects: Compile & Link Program
2707 */
2708 GLuint GLAPIENTRY
_mesa_CreateShaderProgramv(GLenum type,GLsizei count,const GLchar * const * strings)2709 _mesa_CreateShaderProgramv(GLenum type, GLsizei count,
2710 const GLchar* const *strings)
2711 {
2712 GET_CURRENT_CONTEXT(ctx);
2713
2714 return _mesa_CreateShaderProgramv_impl(ctx, type, count, strings);
2715 }
2716
2717 static void
set_patch_vertices(struct gl_context * ctx,GLint value)2718 set_patch_vertices(struct gl_context *ctx, GLint value)
2719 {
2720 if (ctx->TessCtrlProgram.patch_vertices != value) {
2721 FLUSH_VERTICES(ctx, 0, GL_CURRENT_BIT);
2722 ctx->NewDriverState |= ST_NEW_TESS_STATE;
2723 ctx->TessCtrlProgram.patch_vertices = value;
2724 }
2725 }
2726
2727 /**
2728 * For GL_ARB_tessellation_shader
2729 */
2730 void GLAPIENTRY
_mesa_PatchParameteri_no_error(GLenum pname,GLint value)2731 _mesa_PatchParameteri_no_error(GLenum pname, GLint value)
2732 {
2733 GET_CURRENT_CONTEXT(ctx);
2734
2735 set_patch_vertices(ctx, value);
2736 }
2737
2738
2739 extern void GLAPIENTRY
_mesa_PatchParameteri(GLenum pname,GLint value)2740 _mesa_PatchParameteri(GLenum pname, GLint value)
2741 {
2742 GET_CURRENT_CONTEXT(ctx);
2743
2744 if (!_mesa_has_tessellation(ctx)) {
2745 _mesa_error(ctx, GL_INVALID_OPERATION, "glPatchParameteri");
2746 return;
2747 }
2748
2749 if (pname != GL_PATCH_VERTICES) {
2750 _mesa_error(ctx, GL_INVALID_ENUM, "glPatchParameteri");
2751 return;
2752 }
2753
2754 if (value <= 0 || value > ctx->Const.MaxPatchVertices) {
2755 _mesa_error(ctx, GL_INVALID_VALUE, "glPatchParameteri");
2756 return;
2757 }
2758
2759 set_patch_vertices(ctx, value);
2760 }
2761
2762
2763 extern void GLAPIENTRY
_mesa_PatchParameterfv(GLenum pname,const GLfloat * values)2764 _mesa_PatchParameterfv(GLenum pname, const GLfloat *values)
2765 {
2766 GET_CURRENT_CONTEXT(ctx);
2767
2768 if (!_mesa_has_tessellation(ctx)) {
2769 _mesa_error(ctx, GL_INVALID_OPERATION, "glPatchParameterfv");
2770 return;
2771 }
2772
2773 switch(pname) {
2774 case GL_PATCH_DEFAULT_OUTER_LEVEL:
2775 FLUSH_VERTICES(ctx, 0, 0);
2776 memcpy(ctx->TessCtrlProgram.patch_default_outer_level, values,
2777 4 * sizeof(GLfloat));
2778 ctx->NewDriverState |= ST_NEW_TESS_STATE;
2779 return;
2780 case GL_PATCH_DEFAULT_INNER_LEVEL:
2781 FLUSH_VERTICES(ctx, 0, 0);
2782 memcpy(ctx->TessCtrlProgram.patch_default_inner_level, values,
2783 2 * sizeof(GLfloat));
2784 ctx->NewDriverState |= ST_NEW_TESS_STATE;
2785 return;
2786 default:
2787 _mesa_error(ctx, GL_INVALID_ENUM, "glPatchParameterfv");
2788 return;
2789 }
2790 }
2791
2792 /**
2793 * ARB_shader_subroutine
2794 */
2795 GLint GLAPIENTRY
_mesa_GetSubroutineUniformLocation(GLuint program,GLenum shadertype,const GLchar * name)2796 _mesa_GetSubroutineUniformLocation(GLuint program, GLenum shadertype,
2797 const GLchar *name)
2798 {
2799 GET_CURRENT_CONTEXT(ctx);
2800 const char *api_name = "glGetSubroutineUniformLocation";
2801 struct gl_shader_program *shProg;
2802 GLenum resource_type;
2803 gl_shader_stage stage;
2804
2805 if (!_mesa_validate_shader_target(ctx, shadertype)) {
2806 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2807 return -1;
2808 }
2809
2810 shProg = _mesa_lookup_shader_program_err(ctx, program, api_name);
2811 if (!shProg)
2812 return -1;
2813
2814 stage = _mesa_shader_enum_to_shader_stage(shadertype);
2815 if (!shProg->_LinkedShaders[stage]) {
2816 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2817 return -1;
2818 }
2819
2820 resource_type = _mesa_shader_stage_to_subroutine_uniform(stage);
2821 return _mesa_program_resource_location(shProg, resource_type, name);
2822 }
2823
2824 GLuint GLAPIENTRY
_mesa_GetSubroutineIndex(GLuint program,GLenum shadertype,const GLchar * name)2825 _mesa_GetSubroutineIndex(GLuint program, GLenum shadertype,
2826 const GLchar *name)
2827 {
2828 GET_CURRENT_CONTEXT(ctx);
2829 const char *api_name = "glGetSubroutineIndex";
2830 struct gl_shader_program *shProg;
2831 struct gl_program_resource *res;
2832 GLenum resource_type;
2833 gl_shader_stage stage;
2834
2835 if (!_mesa_validate_shader_target(ctx, shadertype)) {
2836 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2837 return -1;
2838 }
2839
2840 shProg = _mesa_lookup_shader_program_err(ctx, program, api_name);
2841 if (!shProg)
2842 return -1;
2843
2844 stage = _mesa_shader_enum_to_shader_stage(shadertype);
2845 if (!shProg->_LinkedShaders[stage]) {
2846 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2847 return -1;
2848 }
2849
2850 resource_type = _mesa_shader_stage_to_subroutine(stage);
2851 res = _mesa_program_resource_find_name(shProg, resource_type, name, NULL);
2852 if (!res) {
2853 return -1;
2854 }
2855
2856 return _mesa_program_resource_index(shProg, res);
2857 }
2858
2859
2860 GLvoid GLAPIENTRY
_mesa_GetActiveSubroutineUniformiv(GLuint program,GLenum shadertype,GLuint index,GLenum pname,GLint * values)2861 _mesa_GetActiveSubroutineUniformiv(GLuint program, GLenum shadertype,
2862 GLuint index, GLenum pname, GLint *values)
2863 {
2864 GET_CURRENT_CONTEXT(ctx);
2865 const char *api_name = "glGetActiveSubroutineUniformiv";
2866 struct gl_shader_program *shProg;
2867 struct gl_linked_shader *sh;
2868 gl_shader_stage stage;
2869 struct gl_program_resource *res;
2870 const struct gl_uniform_storage *uni;
2871 GLenum resource_type;
2872 int count, i, j;
2873
2874 if (!_mesa_validate_shader_target(ctx, shadertype)) {
2875 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2876 return;
2877 }
2878
2879 shProg = _mesa_lookup_shader_program_err(ctx, program, api_name);
2880 if (!shProg)
2881 return;
2882
2883 stage = _mesa_shader_enum_to_shader_stage(shadertype);
2884 resource_type = _mesa_shader_stage_to_subroutine_uniform(stage);
2885
2886 sh = shProg->_LinkedShaders[stage];
2887 if (!sh) {
2888 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2889 return;
2890 }
2891
2892 struct gl_program *p = shProg->_LinkedShaders[stage]->Program;
2893 if (index >= p->sh.NumSubroutineUniforms) {
2894 _mesa_error(ctx, GL_INVALID_VALUE, "%s: invalid index greater than GL_ACTIVE_SUBROUTINE_UNIFORMS", api_name);
2895 return;
2896 }
2897
2898 switch (pname) {
2899 case GL_NUM_COMPATIBLE_SUBROUTINES: {
2900 res = _mesa_program_resource_find_index(shProg, resource_type, index);
2901 if (res) {
2902 uni = res->Data;
2903 values[0] = uni->num_compatible_subroutines;
2904 }
2905 break;
2906 }
2907 case GL_COMPATIBLE_SUBROUTINES: {
2908 res = _mesa_program_resource_find_index(shProg, resource_type, index);
2909 if (res) {
2910 uni = res->Data;
2911 count = 0;
2912 for (i = 0; i < p->sh.NumSubroutineFunctions; i++) {
2913 struct gl_subroutine_function *fn = &p->sh.SubroutineFunctions[i];
2914 for (j = 0; j < fn->num_compat_types; j++) {
2915 if (fn->types[j] == uni->type) {
2916 values[count++] = i;
2917 break;
2918 }
2919 }
2920 }
2921 }
2922 break;
2923 }
2924 case GL_UNIFORM_SIZE:
2925 res = _mesa_program_resource_find_index(shProg, resource_type, index);
2926 if (res) {
2927 uni = res->Data;
2928 values[0] = uni->array_elements ? uni->array_elements : 1;
2929 }
2930 break;
2931 case GL_UNIFORM_NAME_LENGTH:
2932 res = _mesa_program_resource_find_index(shProg, resource_type, index);
2933 if (res) {
2934 values[0] = _mesa_program_resource_name_length(res) + 1
2935 + ((_mesa_program_resource_array_size(res) != 0) ? 3 : 0);
2936 }
2937 break;
2938 default:
2939 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2940 return;
2941 }
2942 }
2943
2944
2945 GLvoid GLAPIENTRY
_mesa_GetActiveSubroutineUniformName(GLuint program,GLenum shadertype,GLuint index,GLsizei bufsize,GLsizei * length,GLchar * name)2946 _mesa_GetActiveSubroutineUniformName(GLuint program, GLenum shadertype,
2947 GLuint index, GLsizei bufsize,
2948 GLsizei *length, GLchar *name)
2949 {
2950 GET_CURRENT_CONTEXT(ctx);
2951 const char *api_name = "glGetActiveSubroutineUniformName";
2952 struct gl_shader_program *shProg;
2953 GLenum resource_type;
2954 gl_shader_stage stage;
2955
2956 if (!_mesa_validate_shader_target(ctx, shadertype)) {
2957 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2958 return;
2959 }
2960
2961 shProg = _mesa_lookup_shader_program_err(ctx, program, api_name);
2962 if (!shProg)
2963 return;
2964
2965 stage = _mesa_shader_enum_to_shader_stage(shadertype);
2966 if (!shProg->_LinkedShaders[stage]) {
2967 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2968 return;
2969 }
2970
2971 resource_type = _mesa_shader_stage_to_subroutine_uniform(stage);
2972 /* get program resource name */
2973 _mesa_get_program_resource_name(shProg, resource_type,
2974 index, bufsize,
2975 length, name, false, api_name);
2976 }
2977
2978
2979 GLvoid GLAPIENTRY
_mesa_GetActiveSubroutineName(GLuint program,GLenum shadertype,GLuint index,GLsizei bufsize,GLsizei * length,GLchar * name)2980 _mesa_GetActiveSubroutineName(GLuint program, GLenum shadertype,
2981 GLuint index, GLsizei bufsize,
2982 GLsizei *length, GLchar *name)
2983 {
2984 GET_CURRENT_CONTEXT(ctx);
2985 const char *api_name = "glGetActiveSubroutineName";
2986 struct gl_shader_program *shProg;
2987 GLenum resource_type;
2988 gl_shader_stage stage;
2989
2990 if (!_mesa_validate_shader_target(ctx, shadertype)) {
2991 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
2992 return;
2993 }
2994
2995 shProg = _mesa_lookup_shader_program_err(ctx, program, api_name);
2996 if (!shProg)
2997 return;
2998
2999 stage = _mesa_shader_enum_to_shader_stage(shadertype);
3000 if (!shProg->_LinkedShaders[stage]) {
3001 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3002 return;
3003 }
3004 resource_type = _mesa_shader_stage_to_subroutine(stage);
3005 _mesa_get_program_resource_name(shProg, resource_type,
3006 index, bufsize,
3007 length, name, false, api_name);
3008 }
3009
3010 GLvoid GLAPIENTRY
_mesa_UniformSubroutinesuiv(GLenum shadertype,GLsizei count,const GLuint * indices)3011 _mesa_UniformSubroutinesuiv(GLenum shadertype, GLsizei count,
3012 const GLuint *indices)
3013 {
3014 GET_CURRENT_CONTEXT(ctx);
3015 const char *api_name = "glUniformSubroutinesuiv";
3016 gl_shader_stage stage;
3017 int i;
3018
3019 if (!_mesa_validate_shader_target(ctx, shadertype)) {
3020 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3021 return;
3022 }
3023
3024 stage = _mesa_shader_enum_to_shader_stage(shadertype);
3025 struct gl_program *p = ctx->_Shader->CurrentProgram[stage];
3026 if (!p) {
3027 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3028 return;
3029 }
3030
3031 if (count != p->sh.NumSubroutineUniformRemapTable) {
3032 _mesa_error(ctx, GL_INVALID_VALUE, "%s", api_name);
3033 return;
3034 }
3035
3036 i = 0;
3037 bool flushed = false;
3038 do {
3039 struct gl_uniform_storage *uni = p->sh.SubroutineUniformRemapTable[i];
3040 if (uni == NULL) {
3041 i++;
3042 continue;
3043 }
3044
3045 if (!flushed) {
3046 _mesa_flush_vertices_for_uniforms(ctx, uni);
3047 flushed = true;
3048 }
3049
3050 int uni_count = uni->array_elements ? uni->array_elements : 1;
3051 int j, k, f;
3052
3053 for (j = i; j < i + uni_count; j++) {
3054 struct gl_subroutine_function *subfn = NULL;
3055 if (indices[j] > p->sh.MaxSubroutineFunctionIndex) {
3056 _mesa_error(ctx, GL_INVALID_VALUE, "%s", api_name);
3057 return;
3058 }
3059
3060 for (f = 0; f < p->sh.NumSubroutineFunctions; f++) {
3061 if (p->sh.SubroutineFunctions[f].index == indices[j])
3062 subfn = &p->sh.SubroutineFunctions[f];
3063 }
3064
3065 if (!subfn) {
3066 continue;
3067 }
3068
3069 for (k = 0; k < subfn->num_compat_types; k++) {
3070 if (subfn->types[k] == uni->type)
3071 break;
3072 }
3073 if (k == subfn->num_compat_types) {
3074 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3075 return;
3076 }
3077
3078 ctx->SubroutineIndex[p->info.stage].IndexPtr[j] = indices[j];
3079 }
3080 i += uni_count;
3081 } while(i < count);
3082 }
3083
3084
3085 GLvoid GLAPIENTRY
_mesa_GetUniformSubroutineuiv(GLenum shadertype,GLint location,GLuint * params)3086 _mesa_GetUniformSubroutineuiv(GLenum shadertype, GLint location,
3087 GLuint *params)
3088 {
3089 GET_CURRENT_CONTEXT(ctx);
3090 const char *api_name = "glGetUniformSubroutineuiv";
3091 gl_shader_stage stage;
3092
3093 if (!_mesa_validate_shader_target(ctx, shadertype)) {
3094 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3095 return;
3096 }
3097
3098 stage = _mesa_shader_enum_to_shader_stage(shadertype);
3099 struct gl_program *p = ctx->_Shader->CurrentProgram[stage];
3100 if (!p) {
3101 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3102 return;
3103 }
3104
3105 if (location >= p->sh.NumSubroutineUniformRemapTable) {
3106 _mesa_error(ctx, GL_INVALID_VALUE, "%s", api_name);
3107 return;
3108 }
3109
3110 *params = ctx->SubroutineIndex[p->info.stage].IndexPtr[location];
3111 }
3112
3113
3114 GLvoid GLAPIENTRY
_mesa_GetProgramStageiv(GLuint program,GLenum shadertype,GLenum pname,GLint * values)3115 _mesa_GetProgramStageiv(GLuint program, GLenum shadertype,
3116 GLenum pname, GLint *values)
3117 {
3118 GET_CURRENT_CONTEXT(ctx);
3119 const char *api_name = "glGetProgramStageiv";
3120 struct gl_shader_program *shProg;
3121 struct gl_linked_shader *sh;
3122 gl_shader_stage stage;
3123
3124 if (!_mesa_validate_shader_target(ctx, shadertype)) {
3125 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3126 return;
3127 }
3128
3129 shProg = _mesa_lookup_shader_program_err(ctx, program, api_name);
3130 if (!shProg)
3131 return;
3132
3133 stage = _mesa_shader_enum_to_shader_stage(shadertype);
3134 sh = shProg->_LinkedShaders[stage];
3135
3136 /* ARB_shader_subroutine doesn't ask the program to be linked, or list any
3137 * INVALID_OPERATION in the case of not be linked.
3138 *
3139 * And for some pnames, like GL_ACTIVE_SUBROUTINE_UNIFORMS, you can ask the
3140 * same info using other specs (ARB_program_interface_query), without the
3141 * need of the program to be linked, being the value for that case 0.
3142 *
3143 * But at the same time, some other methods require the program to be
3144 * linked for pname related to locations, so it would be inconsistent to
3145 * not do the same here. So we are:
3146 * * Return GL_INVALID_OPERATION if not linked only for locations.
3147 * * Setting a default value of 0, to be returned if not linked.
3148 */
3149 if (!sh) {
3150 values[0] = 0;
3151 if (pname == GL_ACTIVE_SUBROUTINE_UNIFORM_LOCATIONS) {
3152 _mesa_error(ctx, GL_INVALID_OPERATION, "%s", api_name);
3153 }
3154 return;
3155 }
3156
3157 struct gl_program *p = sh->Program;
3158 switch (pname) {
3159 case GL_ACTIVE_SUBROUTINES:
3160 values[0] = p->sh.NumSubroutineFunctions;
3161 break;
3162 case GL_ACTIVE_SUBROUTINE_UNIFORM_LOCATIONS:
3163 values[0] = p->sh.NumSubroutineUniformRemapTable;
3164 break;
3165 case GL_ACTIVE_SUBROUTINE_UNIFORMS:
3166 values[0] = p->sh.NumSubroutineUniforms;
3167 break;
3168 case GL_ACTIVE_SUBROUTINE_MAX_LENGTH:
3169 {
3170 unsigned i;
3171 GLint max_len = 0;
3172 GLenum resource_type;
3173 struct gl_program_resource *res;
3174
3175 resource_type = _mesa_shader_stage_to_subroutine(stage);
3176 for (i = 0; i < p->sh.NumSubroutineFunctions; i++) {
3177 res = _mesa_program_resource_find_index(shProg, resource_type, i);
3178 if (res) {
3179 const GLint len = _mesa_program_resource_name_length(res) + 1;
3180 if (len > max_len)
3181 max_len = len;
3182 }
3183 }
3184 values[0] = max_len;
3185 break;
3186 }
3187 case GL_ACTIVE_SUBROUTINE_UNIFORM_MAX_LENGTH:
3188 {
3189 unsigned i;
3190 GLint max_len = 0;
3191 GLenum resource_type;
3192 struct gl_program_resource *res;
3193
3194 resource_type = _mesa_shader_stage_to_subroutine_uniform(stage);
3195 for (i = 0; i < p->sh.NumSubroutineUniformRemapTable; i++) {
3196 res = _mesa_program_resource_find_index(shProg, resource_type, i);
3197 if (res) {
3198 const GLint len = _mesa_program_resource_name_length(res) + 1
3199 + ((_mesa_program_resource_array_size(res) != 0) ? 3 : 0);
3200
3201 if (len > max_len)
3202 max_len = len;
3203 }
3204 }
3205 values[0] = max_len;
3206 break;
3207 }
3208 default:
3209 _mesa_error(ctx, GL_INVALID_ENUM, "%s", api_name);
3210 values[0] = -1;
3211 break;
3212 }
3213 }
3214
3215 /* This is simple list entry that will be used to hold a list of string
3216 * tokens of a parsed shader include path.
3217 */
3218 struct sh_incl_path_entry
3219 {
3220 struct list_head list;
3221
3222 char *path;
3223 };
3224
3225 /* Nodes of the shader include tree */
3226 struct sh_incl_path_ht_entry
3227 {
3228 struct hash_table *path;
3229 char *shader_source;
3230 };
3231
3232 struct shader_includes {
3233 /* Array to hold include paths given to glCompileShaderIncludeARB() */
3234 struct sh_incl_path_entry **include_paths;
3235 size_t num_include_paths;
3236 size_t relative_path_cursor;
3237
3238 /* Root hash table holding the shader include tree */
3239 struct hash_table *shader_include_tree;
3240 };
3241
3242 void
_mesa_init_shader_includes(struct gl_shared_state * shared)3243 _mesa_init_shader_includes(struct gl_shared_state *shared)
3244 {
3245 shared->ShaderIncludes = calloc(1, sizeof(struct shader_includes));
3246 shared->ShaderIncludes->shader_include_tree =
3247 _mesa_hash_table_create(NULL, _mesa_hash_string,
3248 _mesa_key_string_equal);
3249 }
3250
3251 size_t
_mesa_get_shader_include_cursor(struct gl_shared_state * shared)3252 _mesa_get_shader_include_cursor(struct gl_shared_state *shared)
3253 {
3254 return shared->ShaderIncludes->relative_path_cursor;
3255 }
3256
3257 void
_mesa_set_shader_include_cursor(struct gl_shared_state * shared,size_t cursor)3258 _mesa_set_shader_include_cursor(struct gl_shared_state *shared, size_t cursor)
3259 {
3260 shared->ShaderIncludes->relative_path_cursor = cursor;
3261 }
3262
3263 static void
destroy_shader_include(struct hash_entry * entry)3264 destroy_shader_include(struct hash_entry *entry)
3265 {
3266 struct sh_incl_path_ht_entry *sh_incl_ht_entry =
3267 (struct sh_incl_path_ht_entry *) entry->data;
3268
3269 _mesa_hash_table_destroy(sh_incl_ht_entry->path, destroy_shader_include);
3270 free(sh_incl_ht_entry->shader_source);
3271 free(sh_incl_ht_entry);
3272 free((void *)entry->key);
3273 }
3274
3275 void
_mesa_destroy_shader_includes(struct gl_shared_state * shared)3276 _mesa_destroy_shader_includes(struct gl_shared_state *shared)
3277 {
3278 _mesa_hash_table_destroy(shared->ShaderIncludes->shader_include_tree,
3279 destroy_shader_include);
3280 free(shared->ShaderIncludes);
3281 }
3282
3283 static bool
valid_path_format(const char * str,bool relative_path)3284 valid_path_format(const char *str, bool relative_path)
3285 {
3286 int i = 0;
3287
3288 if (!str[i] || (!relative_path && str[i] != '/'))
3289 return false;
3290
3291 i++;
3292
3293 while (str[i]) {
3294 const char c = str[i++];
3295 if (('A' <= c && c <= 'Z') ||
3296 ('a' <= c && c <= 'z') ||
3297 ('0' <= c && c <= '9'))
3298 continue;
3299
3300 if (c == '/') {
3301 if (str[i - 2] == '/')
3302 return false;
3303
3304 continue;
3305 }
3306
3307 if (strchr("^. _+*%[](){}|&~=!:;,?-", c) == NULL)
3308 return false;
3309 }
3310
3311 if (str[i - 1] == '/')
3312 return false;
3313
3314 return true;
3315 }
3316
3317
3318 static bool
validate_and_tokenise_sh_incl(struct gl_context * ctx,void * mem_ctx,struct sh_incl_path_entry ** path_list,char * full_path,bool error_check)3319 validate_and_tokenise_sh_incl(struct gl_context *ctx,
3320 void *mem_ctx,
3321 struct sh_incl_path_entry **path_list,
3322 char *full_path, bool error_check)
3323 {
3324 bool relative_path = ctx->Shared->ShaderIncludes->num_include_paths;
3325
3326 if (!valid_path_format(full_path, relative_path)) {
3327 if (error_check) {
3328 _mesa_error(ctx, GL_INVALID_VALUE,
3329 "glNamedStringARB(invalid name %s)", full_path);
3330 }
3331 return false;
3332 }
3333
3334 char *save_ptr = NULL;
3335 char *path_str = strtok_r(full_path, "/", &save_ptr);
3336
3337 *path_list = rzalloc(mem_ctx, struct sh_incl_path_entry);
3338 struct sh_incl_path_entry * list = *path_list;
3339 list_inithead(&list->list);
3340
3341 while (path_str != NULL) {
3342 if (strlen(path_str) == 0) {
3343 if (error_check) {
3344 _mesa_error(ctx, GL_INVALID_VALUE,
3345 "glNamedStringARB(invalid name %s)", full_path);
3346 }
3347
3348 return false;
3349 }
3350
3351 if (strcmp(path_str, ".") == 0) {
3352 /* Do nothing */
3353 } else if (strcmp(path_str, "..") == 0) {
3354 list_del(list->list.prev);
3355 } else {
3356 struct sh_incl_path_entry *path =
3357 rzalloc(mem_ctx, struct sh_incl_path_entry);
3358
3359 path->path = ralloc_strdup(mem_ctx, path_str);
3360 list_addtail(&path->list, &list->list);
3361 }
3362
3363 path_str = strtok_r(NULL, "/", &save_ptr);
3364 }
3365
3366 return true;
3367 }
3368
3369 static struct sh_incl_path_ht_entry *
lookup_shader_include(struct gl_context * ctx,char * path,bool error_check)3370 lookup_shader_include(struct gl_context *ctx, char *path,
3371 bool error_check)
3372 {
3373 void *mem_ctx = ralloc_context(NULL);
3374 struct sh_incl_path_entry *path_list;
3375
3376 if (!validate_and_tokenise_sh_incl(ctx, mem_ctx, &path_list, path,
3377 error_check)) {
3378 ralloc_free(mem_ctx);
3379 return NULL;
3380 }
3381
3382 struct sh_incl_path_ht_entry *sh_incl_ht_entry = NULL;
3383 struct hash_table *path_ht =
3384 ctx->Shared->ShaderIncludes->shader_include_tree;
3385
3386 size_t count = ctx->Shared->ShaderIncludes->num_include_paths;
3387 bool relative_path = path[0] != '/';
3388
3389 size_t i = ctx->Shared->ShaderIncludes->relative_path_cursor;
3390 bool use_cursor = ctx->Shared->ShaderIncludes->relative_path_cursor;
3391
3392 do {
3393 struct sh_incl_path_entry *entry;
3394
3395 if (relative_path) {
3396 next_relative_path:
3397 {
3398 struct sh_incl_path_entry *rel_path_list =
3399 ctx->Shared->ShaderIncludes->include_paths[i];
3400 LIST_FOR_EACH_ENTRY(entry, &rel_path_list->list, list) {
3401 struct hash_entry *ht_entry =
3402 _mesa_hash_table_search(path_ht, entry->path);
3403
3404 if (!ht_entry) {
3405 /* Reset search path and skip to the next include path */
3406 path_ht = ctx->Shared->ShaderIncludes->shader_include_tree;
3407 sh_incl_ht_entry = NULL;
3408 if (use_cursor) {
3409 i = 0;
3410 use_cursor = false;
3411
3412 goto next_relative_path;
3413 }
3414 i++;
3415 if (i < count)
3416 goto next_relative_path;
3417 else
3418 break;
3419 } else {
3420 sh_incl_ht_entry =
3421 (struct sh_incl_path_ht_entry *) ht_entry->data;
3422 }
3423
3424 path_ht = sh_incl_ht_entry->path;
3425 }
3426 }
3427 }
3428
3429 LIST_FOR_EACH_ENTRY(entry, &path_list->list, list) {
3430 struct hash_entry *ht_entry =
3431 _mesa_hash_table_search(path_ht, entry->path);
3432
3433 if (!ht_entry) {
3434 /* Reset search path and skip to the next include path */
3435 path_ht = ctx->Shared->ShaderIncludes->shader_include_tree;
3436 sh_incl_ht_entry = NULL;
3437 if (use_cursor) {
3438 i = 0;
3439 use_cursor = false;
3440
3441 break;
3442 }
3443 i++;
3444 break;
3445 } else {
3446
3447 sh_incl_ht_entry =
3448 (struct sh_incl_path_ht_entry *) ht_entry->data;
3449 }
3450
3451 path_ht = sh_incl_ht_entry->path;
3452 }
3453
3454 if (i < count &&
3455 (sh_incl_ht_entry == NULL || !sh_incl_ht_entry->shader_source))
3456 continue;
3457
3458 /* If we get here then we have found a matching path or exahusted our
3459 * relative search paths.
3460 */
3461 ctx->Shared->ShaderIncludes->relative_path_cursor = i;
3462 break;
3463 } while (i < count);
3464
3465 ralloc_free(mem_ctx);
3466
3467 return sh_incl_ht_entry;
3468 }
3469
3470 const char *
_mesa_lookup_shader_include(struct gl_context * ctx,char * path,bool error_check)3471 _mesa_lookup_shader_include(struct gl_context *ctx, char *path,
3472 bool error_check)
3473 {
3474 struct sh_incl_path_ht_entry *shader_include =
3475 lookup_shader_include(ctx, path, error_check);
3476
3477 return shader_include ? shader_include->shader_source : NULL;
3478 }
3479
3480 static char *
copy_string(struct gl_context * ctx,const char * str,int str_len,const char * caller)3481 copy_string(struct gl_context *ctx, const char *str, int str_len,
3482 const char *caller)
3483 {
3484 if (!str) {
3485 _mesa_error(ctx, GL_INVALID_VALUE, "%s(NULL string)", caller);
3486 return NULL;
3487 }
3488
3489 char *cp;
3490 if (str_len == -1)
3491 cp = strdup(str);
3492 else {
3493 cp = calloc(sizeof(char), str_len + 1);
3494 memcpy(cp, str, str_len);
3495 }
3496
3497 return cp;
3498 }
3499
3500 GLvoid GLAPIENTRY
_mesa_NamedStringARB(GLenum type,GLint namelen,const GLchar * name,GLint stringlen,const GLchar * string)3501 _mesa_NamedStringARB(GLenum type, GLint namelen, const GLchar *name,
3502 GLint stringlen, const GLchar *string)
3503 {
3504 GET_CURRENT_CONTEXT(ctx);
3505 const char *caller = "glNamedStringARB";
3506
3507 if (type != GL_SHADER_INCLUDE_ARB) {
3508 _mesa_error(ctx, GL_INVALID_VALUE, "%s(invalid type)", caller);
3509 return;
3510 }
3511
3512 char *name_cp = copy_string(ctx, name, namelen, caller);
3513 char *string_cp = copy_string(ctx, string, stringlen, caller);
3514 if (!name_cp || !string_cp) {
3515 free(string_cp);
3516 free(name_cp);
3517 return;
3518 }
3519
3520 void *mem_ctx = ralloc_context(NULL);
3521 struct sh_incl_path_entry *path_list;
3522
3523 if (!validate_and_tokenise_sh_incl(ctx, mem_ctx, &path_list, name_cp,
3524 true)) {
3525 free(string_cp);
3526 free(name_cp);
3527 ralloc_free(mem_ctx);
3528 return;
3529 }
3530
3531 simple_mtx_lock(&ctx->Shared->ShaderIncludeMutex);
3532
3533 struct hash_table *path_ht =
3534 ctx->Shared->ShaderIncludes->shader_include_tree;
3535
3536 struct sh_incl_path_entry *entry;
3537 LIST_FOR_EACH_ENTRY(entry, &path_list->list, list) {
3538 struct hash_entry *ht_entry =
3539 _mesa_hash_table_search(path_ht, entry->path);
3540
3541 struct sh_incl_path_ht_entry *sh_incl_ht_entry;
3542 if (!ht_entry) {
3543 sh_incl_ht_entry = calloc(1, sizeof(struct sh_incl_path_ht_entry));
3544 sh_incl_ht_entry->path =
3545 _mesa_hash_table_create(NULL, _mesa_hash_string,
3546 _mesa_key_string_equal);
3547 _mesa_hash_table_insert(path_ht, strdup(entry->path),
3548 sh_incl_ht_entry);
3549 } else {
3550 sh_incl_ht_entry = (struct sh_incl_path_ht_entry *) ht_entry->data;
3551 }
3552
3553 path_ht = sh_incl_ht_entry->path;
3554
3555 if (list_last_entry(&path_list->list, struct sh_incl_path_entry, list) == entry) {
3556 free(sh_incl_ht_entry->shader_source);
3557 sh_incl_ht_entry->shader_source = string_cp;
3558 }
3559 }
3560
3561 simple_mtx_unlock(&ctx->Shared->ShaderIncludeMutex);
3562
3563 free(name_cp);
3564 ralloc_free(mem_ctx);
3565 }
3566
3567 GLvoid GLAPIENTRY
_mesa_DeleteNamedStringARB(GLint namelen,const GLchar * name)3568 _mesa_DeleteNamedStringARB(GLint namelen, const GLchar *name)
3569 {
3570 GET_CURRENT_CONTEXT(ctx);
3571 const char *caller = "glDeleteNamedStringARB";
3572
3573 char *name_cp = copy_string(ctx, name, namelen, caller);
3574 if (!name_cp)
3575 return;
3576
3577 struct sh_incl_path_ht_entry *shader_include =
3578 lookup_shader_include(ctx, name_cp, true);
3579
3580 if (!shader_include) {
3581 _mesa_error(ctx, GL_INVALID_OPERATION,
3582 "%s(no string associated with path %s)", caller, name_cp);
3583 free(name_cp);
3584 return;
3585 }
3586
3587 simple_mtx_lock(&ctx->Shared->ShaderIncludeMutex);
3588
3589 free(shader_include->shader_source);
3590 shader_include->shader_source = NULL;
3591
3592 simple_mtx_unlock(&ctx->Shared->ShaderIncludeMutex);
3593
3594 free(name_cp);
3595 }
3596
3597 GLvoid GLAPIENTRY
_mesa_CompileShaderIncludeARB(GLuint shader,GLsizei count,const GLchar * const * path,const GLint * length)3598 _mesa_CompileShaderIncludeARB(GLuint shader, GLsizei count,
3599 const GLchar* const *path, const GLint *length)
3600 {
3601 GET_CURRENT_CONTEXT(ctx);
3602 const char *caller = "glCompileShaderIncludeARB";
3603
3604 if (count > 0 && path == NULL) {
3605 _mesa_error(ctx, GL_INVALID_VALUE, "%s(count > 0 && path == NULL)",
3606 caller);
3607 return;
3608 }
3609
3610 void *mem_ctx = ralloc_context(NULL);
3611
3612 simple_mtx_lock(&ctx->Shared->ShaderIncludeMutex);
3613
3614 ctx->Shared->ShaderIncludes->include_paths =
3615 ralloc_array_size(mem_ctx, sizeof(struct sh_incl_path_entry *), count);
3616
3617 for (size_t i = 0; i < count; i++) {
3618 char *path_cp = copy_string(ctx, path[i], length ? length[i] : -1,
3619 caller);
3620 if (!path_cp) {
3621 goto exit;
3622 }
3623
3624 struct sh_incl_path_entry *path_list;
3625
3626 if (!validate_and_tokenise_sh_incl(ctx, mem_ctx, &path_list, path_cp,
3627 true)) {
3628 free(path_cp);
3629 goto exit;
3630 }
3631
3632 ctx->Shared->ShaderIncludes->include_paths[i] = path_list;
3633
3634 free(path_cp);
3635 }
3636
3637 /* We must set this *after* all calls to validate_and_tokenise_sh_incl()
3638 * are done as we use this to decide if we need to check the start of the
3639 * path for a '/'
3640 */
3641 ctx->Shared->ShaderIncludes->num_include_paths = count;
3642
3643 struct gl_shader *sh = _mesa_lookup_shader(ctx, shader);
3644 if (!sh) {
3645 _mesa_error(ctx, GL_INVALID_OPERATION, "%s(shader)", caller);
3646 goto exit;
3647 }
3648
3649 _mesa_compile_shader(ctx, sh);
3650
3651 exit:
3652 ctx->Shared->ShaderIncludes->num_include_paths = 0;
3653 ctx->Shared->ShaderIncludes->relative_path_cursor = 0;
3654 ctx->Shared->ShaderIncludes->include_paths = NULL;
3655
3656 simple_mtx_unlock(&ctx->Shared->ShaderIncludeMutex);
3657
3658 ralloc_free(mem_ctx);
3659 }
3660
3661 GLboolean GLAPIENTRY
_mesa_IsNamedStringARB(GLint namelen,const GLchar * name)3662 _mesa_IsNamedStringARB(GLint namelen, const GLchar *name)
3663 {
3664 GET_CURRENT_CONTEXT(ctx);
3665
3666 if (!name)
3667 return false;
3668
3669 char *name_cp = copy_string(ctx, name, namelen, "");
3670
3671 const char *source = _mesa_lookup_shader_include(ctx, name_cp, false);
3672 free(name_cp);
3673
3674 if (!source)
3675 return false;
3676
3677 return true;
3678 }
3679
3680 GLvoid GLAPIENTRY
_mesa_GetNamedStringARB(GLint namelen,const GLchar * name,GLsizei bufSize,GLint * stringlen,GLchar * string)3681 _mesa_GetNamedStringARB(GLint namelen, const GLchar *name, GLsizei bufSize,
3682 GLint *stringlen, GLchar *string)
3683 {
3684 GET_CURRENT_CONTEXT(ctx);
3685 const char *caller = "glGetNamedStringARB";
3686
3687 char *name_cp = copy_string(ctx, name, namelen, caller);
3688 if (!name_cp)
3689 return;
3690
3691 const char *source = _mesa_lookup_shader_include(ctx, name_cp, true);
3692 if (!source) {
3693 _mesa_error(ctx, GL_INVALID_OPERATION,
3694 "%s(no string associated with path %s)", caller, name_cp);
3695 free(name_cp);
3696 return;
3697 }
3698
3699 size_t size = MIN2(strlen(source), bufSize - 1);
3700 memcpy(string, source, size);
3701 string[size] = '\0';
3702
3703 *stringlen = size;
3704
3705 free(name_cp);
3706 }
3707
3708 GLvoid GLAPIENTRY
_mesa_GetNamedStringivARB(GLint namelen,const GLchar * name,GLenum pname,GLint * params)3709 _mesa_GetNamedStringivARB(GLint namelen, const GLchar *name,
3710 GLenum pname, GLint *params)
3711 {
3712 GET_CURRENT_CONTEXT(ctx);
3713 const char *caller = "glGetNamedStringivARB";
3714
3715 char *name_cp = copy_string(ctx, name, namelen, caller);
3716 if (!name_cp)
3717 return;
3718
3719 const char *source = _mesa_lookup_shader_include(ctx, name_cp, true);
3720 if (!source) {
3721 _mesa_error(ctx, GL_INVALID_OPERATION,
3722 "%s(no string associated with path %s)", caller, name_cp);
3723 free(name_cp);
3724 return;
3725 }
3726
3727 switch (pname) {
3728 case GL_NAMED_STRING_LENGTH_ARB:
3729 *params = strlen(source) + 1;
3730 break;
3731 case GL_NAMED_STRING_TYPE_ARB:
3732 *params = GL_SHADER_INCLUDE_ARB;
3733 break;
3734 default:
3735 _mesa_error(ctx, GL_INVALID_ENUM, "%s(pname)", caller);
3736 break;
3737 }
3738
3739 free(name_cp);
3740 }
3741
3742 static int
find_compat_subroutine(struct gl_program * p,const struct glsl_type * type)3743 find_compat_subroutine(struct gl_program *p, const struct glsl_type *type)
3744 {
3745 int i, j;
3746
3747 for (i = 0; i < p->sh.NumSubroutineFunctions; i++) {
3748 struct gl_subroutine_function *fn = &p->sh.SubroutineFunctions[i];
3749 for (j = 0; j < fn->num_compat_types; j++) {
3750 if (fn->types[j] == type)
3751 return i;
3752 }
3753 }
3754 return 0;
3755 }
3756
3757 static void
_mesa_shader_write_subroutine_index(struct gl_context * ctx,struct gl_program * p)3758 _mesa_shader_write_subroutine_index(struct gl_context *ctx,
3759 struct gl_program *p)
3760 {
3761 int i, j;
3762
3763 if (p->sh.NumSubroutineUniformRemapTable == 0)
3764 return;
3765
3766 i = 0;
3767 do {
3768 struct gl_uniform_storage *uni = p->sh.SubroutineUniformRemapTable[i];
3769 int uni_count;
3770 int val;
3771
3772 if (!uni) {
3773 i++;
3774 continue;
3775 }
3776
3777 uni_count = uni->array_elements ? uni->array_elements : 1;
3778 for (j = 0; j < uni_count; j++) {
3779 val = ctx->SubroutineIndex[p->info.stage].IndexPtr[i + j];
3780 memcpy(&uni->storage[j], &val, sizeof(int));
3781 }
3782
3783 _mesa_propagate_uniforms_to_driver_storage(uni, 0, uni_count);
3784 i += uni_count;
3785 } while(i < p->sh.NumSubroutineUniformRemapTable);
3786 }
3787
3788 void
_mesa_shader_write_subroutine_indices(struct gl_context * ctx,gl_shader_stage stage)3789 _mesa_shader_write_subroutine_indices(struct gl_context *ctx,
3790 gl_shader_stage stage)
3791 {
3792 if (ctx->_Shader->CurrentProgram[stage])
3793 _mesa_shader_write_subroutine_index(ctx,
3794 ctx->_Shader->CurrentProgram[stage]);
3795 }
3796
3797 void
_mesa_program_init_subroutine_defaults(struct gl_context * ctx,struct gl_program * p)3798 _mesa_program_init_subroutine_defaults(struct gl_context *ctx,
3799 struct gl_program *p)
3800 {
3801 assert(p);
3802
3803 struct gl_subroutine_index_binding *binding = &ctx->SubroutineIndex[p->info.stage];
3804 if (binding->NumIndex != p->sh.NumSubroutineUniformRemapTable) {
3805 binding->IndexPtr = realloc(binding->IndexPtr,
3806 p->sh.NumSubroutineUniformRemapTable * (sizeof(GLuint)));
3807 binding->NumIndex = p->sh.NumSubroutineUniformRemapTable;
3808 }
3809
3810 for (int i = 0; i < p->sh.NumSubroutineUniformRemapTable; i++) {
3811 struct gl_uniform_storage *uni = p->sh.SubroutineUniformRemapTable[i];
3812
3813 if (!uni)
3814 continue;
3815
3816 binding->IndexPtr[i] = find_compat_subroutine(p, uni->type);
3817 }
3818 }
3819