df9c5d36f0b0b1dea091d4a15644e7f2cb6c00f7
[mesa.git] / src / glsl / glsl_types.cpp
1 /*
2 * Copyright © 2009 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
22 */
23
24 #include <stdio.h>
25 #include <stdlib.h>
26 #include "main/core.h" /* for Elements */
27 #include "glsl_symbol_table.h"
28 #include "glsl_parser_extras.h"
29 #include "glsl_types.h"
30 #include "builtin_types.h"
31 extern "C" {
32 #include "program/hash_table.h"
33 }
34
35 hash_table *glsl_type::array_types = NULL;
36 hash_table *glsl_type::record_types = NULL;
37 hash_table *glsl_type::interface_types = NULL;
38 void *glsl_type::mem_ctx = NULL;
39
40 void
41 glsl_type::init_ralloc_type_ctx(void)
42 {
43 if (glsl_type::mem_ctx == NULL) {
44 glsl_type::mem_ctx = ralloc_autofree_context();
45 assert(glsl_type::mem_ctx != NULL);
46 }
47 }
48
49 glsl_type::glsl_type(GLenum gl_type,
50 glsl_base_type base_type, unsigned vector_elements,
51 unsigned matrix_columns, const char *name) :
52 gl_type(gl_type),
53 base_type(base_type),
54 sampler_dimensionality(0), sampler_shadow(0), sampler_array(0),
55 sampler_type(0), interface_packing(0),
56 vector_elements(vector_elements), matrix_columns(matrix_columns),
57 length(0)
58 {
59 init_ralloc_type_ctx();
60 assert(name != NULL);
61 this->name = ralloc_strdup(this->mem_ctx, name);
62 /* Neither dimension is zero or both dimensions are zero.
63 */
64 assert((vector_elements == 0) == (matrix_columns == 0));
65 memset(& fields, 0, sizeof(fields));
66 }
67
68 glsl_type::glsl_type(GLenum gl_type,
69 enum glsl_sampler_dim dim, bool shadow, bool array,
70 unsigned type, const char *name) :
71 gl_type(gl_type),
72 base_type(GLSL_TYPE_SAMPLER),
73 sampler_dimensionality(dim), sampler_shadow(shadow),
74 sampler_array(array), sampler_type(type), interface_packing(0),
75 vector_elements(0), matrix_columns(0),
76 length(0)
77 {
78 init_ralloc_type_ctx();
79 assert(name != NULL);
80 this->name = ralloc_strdup(this->mem_ctx, name);
81 memset(& fields, 0, sizeof(fields));
82 }
83
84 glsl_type::glsl_type(const glsl_struct_field *fields, unsigned num_fields,
85 const char *name) :
86 gl_type(0),
87 base_type(GLSL_TYPE_STRUCT),
88 sampler_dimensionality(0), sampler_shadow(0), sampler_array(0),
89 sampler_type(0), interface_packing(0),
90 vector_elements(0), matrix_columns(0),
91 length(num_fields)
92 {
93 unsigned int i;
94
95 init_ralloc_type_ctx();
96 assert(name != NULL);
97 this->name = ralloc_strdup(this->mem_ctx, name);
98 this->fields.structure = ralloc_array(this->mem_ctx,
99 glsl_struct_field, length);
100 for (i = 0; i < length; i++) {
101 this->fields.structure[i].type = fields[i].type;
102 this->fields.structure[i].name = ralloc_strdup(this->fields.structure,
103 fields[i].name);
104 this->fields.structure[i].row_major = fields[i].row_major;
105 }
106 }
107
108 glsl_type::glsl_type(const glsl_struct_field *fields, unsigned num_fields,
109 enum glsl_interface_packing packing, const char *name) :
110 gl_type(0),
111 base_type(GLSL_TYPE_INTERFACE),
112 sampler_dimensionality(0), sampler_shadow(0), sampler_array(0),
113 sampler_type(0), interface_packing((unsigned) packing),
114 vector_elements(0), matrix_columns(0),
115 length(num_fields)
116 {
117 unsigned int i;
118
119 init_ralloc_type_ctx();
120 assert(name != NULL);
121 this->name = ralloc_strdup(this->mem_ctx, name);
122 this->fields.structure = ralloc_array(this->mem_ctx,
123 glsl_struct_field, length);
124 for (i = 0; i < length; i++) {
125 this->fields.structure[i].type = fields[i].type;
126 this->fields.structure[i].name = ralloc_strdup(this->fields.structure,
127 fields[i].name);
128 this->fields.structure[i].row_major = fields[i].row_major;
129 }
130 }
131
132 static void
133 add_types_to_symbol_table(glsl_symbol_table *symtab,
134 const struct glsl_type *types,
135 unsigned num_types, bool warn,
136 bool skip_1d)
137 {
138 (void) warn;
139
140 for (unsigned i = 0; i < num_types; i++) {
141 if (skip_1d && types[i].base_type == GLSL_TYPE_SAMPLER
142 && types[i].sampler_dimensionality == GLSL_SAMPLER_DIM_1D)
143 continue;
144
145 symtab->add_type(types[i].name, & types[i]);
146 }
147 }
148
149 bool
150 glsl_type::contains_sampler() const
151 {
152 if (this->is_array()) {
153 return this->fields.array->contains_sampler();
154 } else if (this->is_record()) {
155 for (unsigned int i = 0; i < this->length; i++) {
156 if (this->fields.structure[i].type->contains_sampler())
157 return true;
158 }
159 return false;
160 } else {
161 return this->is_sampler();
162 }
163 }
164
165
166 bool
167 glsl_type::contains_integer() const
168 {
169 if (this->is_array()) {
170 return this->fields.array->contains_integer();
171 } else if (this->is_record()) {
172 for (unsigned int i = 0; i < this->length; i++) {
173 if (this->fields.structure[i].type->contains_integer())
174 return true;
175 }
176 return false;
177 } else {
178 return this->is_integer();
179 }
180 }
181
182
183 gl_texture_index
184 glsl_type::sampler_index() const
185 {
186 const glsl_type *const t = (this->is_array()) ? this->fields.array : this;
187
188 assert(t->is_sampler());
189
190 switch (t->sampler_dimensionality) {
191 case GLSL_SAMPLER_DIM_1D:
192 return (t->sampler_array) ? TEXTURE_1D_ARRAY_INDEX : TEXTURE_1D_INDEX;
193 case GLSL_SAMPLER_DIM_2D:
194 return (t->sampler_array) ? TEXTURE_2D_ARRAY_INDEX : TEXTURE_2D_INDEX;
195 case GLSL_SAMPLER_DIM_3D:
196 return TEXTURE_3D_INDEX;
197 case GLSL_SAMPLER_DIM_CUBE:
198 return (t->sampler_array) ? TEXTURE_CUBE_ARRAY_INDEX : TEXTURE_CUBE_INDEX;
199 case GLSL_SAMPLER_DIM_RECT:
200 return TEXTURE_RECT_INDEX;
201 case GLSL_SAMPLER_DIM_BUF:
202 return TEXTURE_BUFFER_INDEX;
203 case GLSL_SAMPLER_DIM_EXTERNAL:
204 return TEXTURE_EXTERNAL_INDEX;
205 case GLSL_SAMPLER_DIM_MS:
206 return (t->sampler_array) ? TEXTURE_2D_MULTISAMPLE_ARRAY_INDEX : TEXTURE_2D_MULTISAMPLE_INDEX;
207 default:
208 assert(!"Should not get here.");
209 return TEXTURE_BUFFER_INDEX;
210 }
211 }
212
213 void
214 glsl_type::generate_100ES_types(glsl_symbol_table *symtab)
215 {
216 bool skip_1d = false;
217 add_types_to_symbol_table(symtab, builtin_core_types,
218 Elements(builtin_core_types),
219 false, skip_1d);
220 add_types_to_symbol_table(symtab, builtin_structure_types,
221 Elements(builtin_structure_types),
222 false, skip_1d);
223 add_types_to_symbol_table(symtab, void_type, 1, false, skip_1d);
224 }
225
226 void
227 glsl_type::generate_300ES_types(glsl_symbol_table *symtab)
228 {
229 /* GLSL 3.00 ES types are the same as GLSL 1.30 types, except that 1D
230 * samplers are skipped, and samplerCubeShadow is added.
231 */
232 bool add_deprecated = false;
233 bool skip_1d = true;
234
235 generate_130_types(symtab, add_deprecated, skip_1d);
236
237 add_types_to_symbol_table(symtab, &_samplerCubeShadow_type, 1, false,
238 skip_1d);
239 }
240
241 void
242 glsl_type::generate_110_types(glsl_symbol_table *symtab, bool add_deprecated,
243 bool skip_1d)
244 {
245 generate_100ES_types(symtab);
246
247 add_types_to_symbol_table(symtab, builtin_110_types,
248 Elements(builtin_110_types),
249 false, skip_1d);
250 add_types_to_symbol_table(symtab, &_sampler3D_type, 1, false, skip_1d);
251 if (add_deprecated) {
252 add_types_to_symbol_table(symtab, builtin_110_deprecated_structure_types,
253 Elements(builtin_110_deprecated_structure_types),
254 false, skip_1d);
255 }
256 }
257
258
259 void
260 glsl_type::generate_120_types(glsl_symbol_table *symtab, bool add_deprecated,
261 bool skip_1d)
262 {
263 generate_110_types(symtab, add_deprecated, skip_1d);
264
265 add_types_to_symbol_table(symtab, builtin_120_types,
266 Elements(builtin_120_types), false, skip_1d);
267 }
268
269
270 void
271 glsl_type::generate_130_types(glsl_symbol_table *symtab, bool add_deprecated,
272 bool skip_1d)
273 {
274 generate_120_types(symtab, add_deprecated, skip_1d);
275
276 add_types_to_symbol_table(symtab, builtin_130_types,
277 Elements(builtin_130_types), false, skip_1d);
278 generate_EXT_texture_array_types(symtab, false);
279 }
280
281
282 void
283 glsl_type::generate_140_types(glsl_symbol_table *symtab)
284 {
285 bool skip_1d = false;
286
287 generate_130_types(symtab, false, skip_1d);
288
289 add_types_to_symbol_table(symtab, builtin_140_types,
290 Elements(builtin_140_types), false, skip_1d);
291
292 add_types_to_symbol_table(symtab, builtin_EXT_texture_buffer_object_types,
293 Elements(builtin_EXT_texture_buffer_object_types),
294 false, skip_1d);
295 }
296
297
298 void
299 glsl_type::generate_150_types(glsl_symbol_table *symtab)
300 {
301 generate_140_types(symtab);
302 generate_ARB_texture_multisample_types(symtab, false);
303 }
304
305
306 void
307 glsl_type::generate_ARB_texture_rectangle_types(glsl_symbol_table *symtab,
308 bool warn)
309 {
310 bool skip_1d = false;
311
312 add_types_to_symbol_table(symtab, builtin_ARB_texture_rectangle_types,
313 Elements(builtin_ARB_texture_rectangle_types),
314 warn, skip_1d);
315 }
316
317
318 void
319 glsl_type::generate_EXT_texture_array_types(glsl_symbol_table *symtab,
320 bool warn)
321 {
322 bool skip_1d = false;
323
324 add_types_to_symbol_table(symtab, builtin_EXT_texture_array_types,
325 Elements(builtin_EXT_texture_array_types),
326 warn, skip_1d);
327 }
328
329
330 void
331 glsl_type::generate_OES_texture_3D_types(glsl_symbol_table *symtab, bool warn)
332 {
333 bool skip_1d = false;
334
335 add_types_to_symbol_table(symtab, &_sampler3D_type, 1, warn, skip_1d);
336 }
337
338
339 void
340 glsl_type::generate_OES_EGL_image_external_types(glsl_symbol_table *symtab,
341 bool warn)
342 {
343 bool skip_1d = false;
344
345 add_types_to_symbol_table(symtab, builtin_OES_EGL_image_external_types,
346 Elements(builtin_OES_EGL_image_external_types),
347 warn, skip_1d);
348 }
349
350 void
351 glsl_type::generate_ARB_texture_cube_map_array_types(glsl_symbol_table *symtab,
352 bool warn)
353 {
354 bool skip_1d = false;
355
356 add_types_to_symbol_table(symtab, builtin_ARB_texture_cube_map_array_types,
357 Elements(builtin_ARB_texture_cube_map_array_types),
358 warn, skip_1d);
359 }
360
361 void
362 glsl_type::generate_ARB_texture_multisample_types(glsl_symbol_table *symtab,
363 bool warn)
364 {
365 bool skip_1d = false;
366 add_types_to_symbol_table(symtab, builtin_ARB_texture_multisample_types,
367 Elements(builtin_ARB_texture_multisample_types),
368 warn, skip_1d);
369 }
370
371 void
372 _mesa_glsl_initialize_types(struct _mesa_glsl_parse_state *state)
373 {
374 if (state->es_shader) {
375 switch (state->language_version) {
376 case 100:
377 assert(state->es_shader);
378 glsl_type::generate_100ES_types(state->symbols);
379 break;
380 case 300:
381 glsl_type::generate_300ES_types(state->symbols);
382 break;
383 default:
384 assert(!"Unexpected language version");
385 break;
386 }
387 } else {
388 bool skip_1d = false;
389 switch (state->language_version) {
390 case 110:
391 glsl_type::generate_110_types(state->symbols, true, skip_1d);
392 break;
393 case 120:
394 glsl_type::generate_120_types(state->symbols, true, skip_1d);
395 break;
396 case 130:
397 glsl_type::generate_130_types(state->symbols, true, skip_1d);
398 break;
399 case 140:
400 glsl_type::generate_140_types(state->symbols);
401 break;
402 case 150:
403 glsl_type::generate_150_types(state->symbols);
404 break;
405 default:
406 assert(!"Unexpected language version");
407 break;
408 }
409 }
410
411 if (state->ARB_texture_rectangle_enable ||
412 state->is_version(140, 0)) {
413 glsl_type::generate_ARB_texture_rectangle_types(state->symbols,
414 state->ARB_texture_rectangle_warn);
415 }
416 if (state->OES_texture_3D_enable
417 && state->is_version(0, 100)) {
418 glsl_type::generate_OES_texture_3D_types(state->symbols,
419 state->OES_texture_3D_warn);
420 }
421
422 if (state->EXT_texture_array_enable
423 && !state->is_version(130, 0)) {
424 // These are already included in 130; don't create twice.
425 glsl_type::generate_EXT_texture_array_types(state->symbols,
426 state->EXT_texture_array_warn);
427 }
428
429 /* We cannot check for language_version == 100 here because we need the
430 * types to support fixed-function program generation. But this is fine
431 * since the extension is never enabled for OpenGL contexts.
432 */
433 if (state->OES_EGL_image_external_enable) {
434 glsl_type::generate_OES_EGL_image_external_types(state->symbols,
435 state->OES_EGL_image_external_warn);
436 }
437
438 if (state->ARB_texture_cube_map_array_enable) {
439 glsl_type::generate_ARB_texture_cube_map_array_types(state->symbols,
440 state->ARB_texture_cube_map_array_warn);
441 }
442
443 if (state->ARB_texture_multisample_enable) {
444 glsl_type::generate_ARB_texture_multisample_types(state->symbols,
445 state->ARB_texture_multisample_warn);
446 }
447 }
448
449
450 const glsl_type *glsl_type::get_base_type() const
451 {
452 switch (base_type) {
453 case GLSL_TYPE_UINT:
454 return uint_type;
455 case GLSL_TYPE_INT:
456 return int_type;
457 case GLSL_TYPE_FLOAT:
458 return float_type;
459 case GLSL_TYPE_BOOL:
460 return bool_type;
461 default:
462 return error_type;
463 }
464 }
465
466
467 const glsl_type *glsl_type::get_scalar_type() const
468 {
469 const glsl_type *type = this;
470
471 /* Handle arrays */
472 while (type->base_type == GLSL_TYPE_ARRAY)
473 type = type->fields.array;
474
475 /* Handle vectors and matrices */
476 switch (type->base_type) {
477 case GLSL_TYPE_UINT:
478 return uint_type;
479 case GLSL_TYPE_INT:
480 return int_type;
481 case GLSL_TYPE_FLOAT:
482 return float_type;
483 case GLSL_TYPE_BOOL:
484 return bool_type;
485 default:
486 /* Handle everything else */
487 return type;
488 }
489 }
490
491
492 void
493 _mesa_glsl_release_types(void)
494 {
495 if (glsl_type::array_types != NULL) {
496 hash_table_dtor(glsl_type::array_types);
497 glsl_type::array_types = NULL;
498 }
499
500 if (glsl_type::record_types != NULL) {
501 hash_table_dtor(glsl_type::record_types);
502 glsl_type::record_types = NULL;
503 }
504 }
505
506
507 glsl_type::glsl_type(const glsl_type *array, unsigned length) :
508 base_type(GLSL_TYPE_ARRAY),
509 sampler_dimensionality(0), sampler_shadow(0), sampler_array(0),
510 sampler_type(0), interface_packing(0),
511 vector_elements(0), matrix_columns(0),
512 name(NULL), length(length)
513 {
514 this->fields.array = array;
515 /* Inherit the gl type of the base. The GL type is used for
516 * uniform/statevar handling in Mesa and the arrayness of the type
517 * is represented by the size rather than the type.
518 */
519 this->gl_type = array->gl_type;
520
521 /* Allow a maximum of 10 characters for the array size. This is enough
522 * for 32-bits of ~0. The extra 3 are for the '[', ']', and terminating
523 * NUL.
524 */
525 const unsigned name_length = strlen(array->name) + 10 + 3;
526 char *const n = (char *) ralloc_size(this->mem_ctx, name_length);
527
528 if (length == 0)
529 snprintf(n, name_length, "%s[]", array->name);
530 else
531 snprintf(n, name_length, "%s[%u]", array->name, length);
532
533 this->name = n;
534 }
535
536
537 const glsl_type *
538 glsl_type::get_instance(unsigned base_type, unsigned rows, unsigned columns)
539 {
540 if (base_type == GLSL_TYPE_VOID)
541 return void_type;
542
543 if ((rows < 1) || (rows > 4) || (columns < 1) || (columns > 4))
544 return error_type;
545
546 /* Treat GLSL vectors as Nx1 matrices.
547 */
548 if (columns == 1) {
549 switch (base_type) {
550 case GLSL_TYPE_UINT:
551 return uint_type + (rows - 1);
552 case GLSL_TYPE_INT:
553 return int_type + (rows - 1);
554 case GLSL_TYPE_FLOAT:
555 return float_type + (rows - 1);
556 case GLSL_TYPE_BOOL:
557 return bool_type + (rows - 1);
558 default:
559 return error_type;
560 }
561 } else {
562 if ((base_type != GLSL_TYPE_FLOAT) || (rows == 1))
563 return error_type;
564
565 /* GLSL matrix types are named mat{COLUMNS}x{ROWS}. Only the following
566 * combinations are valid:
567 *
568 * 1 2 3 4
569 * 1
570 * 2 x x x
571 * 3 x x x
572 * 4 x x x
573 */
574 #define IDX(c,r) (((c-1)*3) + (r-1))
575
576 switch (IDX(columns, rows)) {
577 case IDX(2,2): return mat2_type;
578 case IDX(2,3): return mat2x3_type;
579 case IDX(2,4): return mat2x4_type;
580 case IDX(3,2): return mat3x2_type;
581 case IDX(3,3): return mat3_type;
582 case IDX(3,4): return mat3x4_type;
583 case IDX(4,2): return mat4x2_type;
584 case IDX(4,3): return mat4x3_type;
585 case IDX(4,4): return mat4_type;
586 default: return error_type;
587 }
588 }
589
590 assert(!"Should not get here.");
591 return error_type;
592 }
593
594
595 const glsl_type *
596 glsl_type::get_array_instance(const glsl_type *base, unsigned array_size)
597 {
598
599 if (array_types == NULL) {
600 array_types = hash_table_ctor(64, hash_table_string_hash,
601 hash_table_string_compare);
602 }
603
604 /* Generate a name using the base type pointer in the key. This is
605 * done because the name of the base type may not be unique across
606 * shaders. For example, two shaders may have different record types
607 * named 'foo'.
608 */
609 char key[128];
610 snprintf(key, sizeof(key), "%p[%u]", (void *) base, array_size);
611
612 const glsl_type *t = (glsl_type *) hash_table_find(array_types, key);
613 if (t == NULL) {
614 t = new glsl_type(base, array_size);
615
616 hash_table_insert(array_types, (void *) t, ralloc_strdup(mem_ctx, key));
617 }
618
619 assert(t->base_type == GLSL_TYPE_ARRAY);
620 assert(t->length == array_size);
621 assert(t->fields.array == base);
622
623 return t;
624 }
625
626
627 int
628 glsl_type::record_key_compare(const void *a, const void *b)
629 {
630 const glsl_type *const key1 = (glsl_type *) a;
631 const glsl_type *const key2 = (glsl_type *) b;
632
633 /* Return zero is the types match (there is zero difference) or non-zero
634 * otherwise.
635 */
636 if (strcmp(key1->name, key2->name) != 0)
637 return 1;
638
639 if (key1->length != key2->length)
640 return 1;
641
642 if (key1->interface_packing != key2->interface_packing)
643 return 1;
644
645 for (unsigned i = 0; i < key1->length; i++) {
646 if (key1->fields.structure[i].type != key2->fields.structure[i].type)
647 return 1;
648 if (strcmp(key1->fields.structure[i].name,
649 key2->fields.structure[i].name) != 0)
650 return 1;
651 if (key1->fields.structure[i].row_major
652 != key2->fields.structure[i].row_major)
653 return 1;
654 }
655
656 return 0;
657 }
658
659
660 unsigned
661 glsl_type::record_key_hash(const void *a)
662 {
663 const glsl_type *const key = (glsl_type *) a;
664 char hash_key[128];
665 unsigned size = 0;
666
667 size = snprintf(hash_key, sizeof(hash_key), "%08x", key->length);
668
669 for (unsigned i = 0; i < key->length; i++) {
670 if (size >= sizeof(hash_key))
671 break;
672
673 size += snprintf(& hash_key[size], sizeof(hash_key) - size,
674 "%p", (void *) key->fields.structure[i].type);
675 }
676
677 return hash_table_string_hash(& hash_key);
678 }
679
680
681 const glsl_type *
682 glsl_type::get_record_instance(const glsl_struct_field *fields,
683 unsigned num_fields,
684 const char *name)
685 {
686 const glsl_type key(fields, num_fields, name);
687
688 if (record_types == NULL) {
689 record_types = hash_table_ctor(64, record_key_hash, record_key_compare);
690 }
691
692 const glsl_type *t = (glsl_type *) hash_table_find(record_types, & key);
693 if (t == NULL) {
694 t = new glsl_type(fields, num_fields, name);
695
696 hash_table_insert(record_types, (void *) t, t);
697 }
698
699 assert(t->base_type == GLSL_TYPE_STRUCT);
700 assert(t->length == num_fields);
701 assert(strcmp(t->name, name) == 0);
702
703 return t;
704 }
705
706
707 const glsl_type *
708 glsl_type::get_interface_instance(const glsl_struct_field *fields,
709 unsigned num_fields,
710 enum glsl_interface_packing packing,
711 const char *name)
712 {
713 const glsl_type key(fields, num_fields, packing, name);
714
715 if (interface_types == NULL) {
716 interface_types = hash_table_ctor(64, record_key_hash, record_key_compare);
717 }
718
719 const glsl_type *t = (glsl_type *) hash_table_find(interface_types, & key);
720 if (t == NULL) {
721 t = new glsl_type(fields, num_fields, packing, name);
722
723 hash_table_insert(interface_types, (void *) t, t);
724 }
725
726 assert(t->base_type == GLSL_TYPE_INTERFACE);
727 assert(t->length == num_fields);
728 assert(strcmp(t->name, name) == 0);
729
730 return t;
731 }
732
733
734 const glsl_type *
735 glsl_type::field_type(const char *name) const
736 {
737 if (this->base_type != GLSL_TYPE_STRUCT
738 && this->base_type != GLSL_TYPE_INTERFACE)
739 return error_type;
740
741 for (unsigned i = 0; i < this->length; i++) {
742 if (strcmp(name, this->fields.structure[i].name) == 0)
743 return this->fields.structure[i].type;
744 }
745
746 return error_type;
747 }
748
749
750 int
751 glsl_type::field_index(const char *name) const
752 {
753 if (this->base_type != GLSL_TYPE_STRUCT
754 && this->base_type != GLSL_TYPE_INTERFACE)
755 return -1;
756
757 for (unsigned i = 0; i < this->length; i++) {
758 if (strcmp(name, this->fields.structure[i].name) == 0)
759 return i;
760 }
761
762 return -1;
763 }
764
765
766 unsigned
767 glsl_type::component_slots() const
768 {
769 switch (this->base_type) {
770 case GLSL_TYPE_UINT:
771 case GLSL_TYPE_INT:
772 case GLSL_TYPE_FLOAT:
773 case GLSL_TYPE_BOOL:
774 return this->components();
775
776 case GLSL_TYPE_STRUCT:
777 case GLSL_TYPE_INTERFACE: {
778 unsigned size = 0;
779
780 for (unsigned i = 0; i < this->length; i++)
781 size += this->fields.structure[i].type->component_slots();
782
783 return size;
784 }
785
786 case GLSL_TYPE_ARRAY:
787 return this->length * this->fields.array->component_slots();
788
789 case GLSL_TYPE_SAMPLER:
790 case GLSL_TYPE_VOID:
791 case GLSL_TYPE_ERROR:
792 break;
793 }
794
795 return 0;
796 }
797
798 bool
799 glsl_type::can_implicitly_convert_to(const glsl_type *desired) const
800 {
801 if (this == desired)
802 return true;
803
804 /* There is no conversion among matrix types. */
805 if (this->matrix_columns > 1 || desired->matrix_columns > 1)
806 return false;
807
808 /* int and uint can be converted to float. */
809 return desired->is_float()
810 && this->is_integer()
811 && this->vector_elements == desired->vector_elements;
812 }
813
814 unsigned
815 glsl_type::std140_base_alignment(bool row_major) const
816 {
817 /* (1) If the member is a scalar consuming <N> basic machine units, the
818 * base alignment is <N>.
819 *
820 * (2) If the member is a two- or four-component vector with components
821 * consuming <N> basic machine units, the base alignment is 2<N> or
822 * 4<N>, respectively.
823 *
824 * (3) If the member is a three-component vector with components consuming
825 * <N> basic machine units, the base alignment is 4<N>.
826 */
827 if (this->is_scalar() || this->is_vector()) {
828 switch (this->vector_elements) {
829 case 1:
830 return 4;
831 case 2:
832 return 8;
833 case 3:
834 case 4:
835 return 16;
836 }
837 }
838
839 /* (4) If the member is an array of scalars or vectors, the base alignment
840 * and array stride are set to match the base alignment of a single
841 * array element, according to rules (1), (2), and (3), and rounded up
842 * to the base alignment of a vec4. The array may have padding at the
843 * end; the base offset of the member following the array is rounded up
844 * to the next multiple of the base alignment.
845 *
846 * (6) If the member is an array of <S> column-major matrices with <C>
847 * columns and <R> rows, the matrix is stored identically to a row of
848 * <S>*<C> column vectors with <R> components each, according to rule
849 * (4).
850 *
851 * (8) If the member is an array of <S> row-major matrices with <C> columns
852 * and <R> rows, the matrix is stored identically to a row of <S>*<R>
853 * row vectors with <C> components each, according to rule (4).
854 *
855 * (10) If the member is an array of <S> structures, the <S> elements of
856 * the array are laid out in order, according to rule (9).
857 */
858 if (this->is_array()) {
859 if (this->fields.array->is_scalar() ||
860 this->fields.array->is_vector() ||
861 this->fields.array->is_matrix()) {
862 return MAX2(this->fields.array->std140_base_alignment(row_major), 16);
863 } else {
864 assert(this->fields.array->is_record());
865 return this->fields.array->std140_base_alignment(row_major);
866 }
867 }
868
869 /* (5) If the member is a column-major matrix with <C> columns and
870 * <R> rows, the matrix is stored identically to an array of
871 * <C> column vectors with <R> components each, according to
872 * rule (4).
873 *
874 * (7) If the member is a row-major matrix with <C> columns and <R>
875 * rows, the matrix is stored identically to an array of <R>
876 * row vectors with <C> components each, according to rule (4).
877 */
878 if (this->is_matrix()) {
879 const struct glsl_type *vec_type, *array_type;
880 int c = this->matrix_columns;
881 int r = this->vector_elements;
882
883 if (row_major) {
884 vec_type = get_instance(GLSL_TYPE_FLOAT, c, 1);
885 array_type = glsl_type::get_array_instance(vec_type, r);
886 } else {
887 vec_type = get_instance(GLSL_TYPE_FLOAT, r, 1);
888 array_type = glsl_type::get_array_instance(vec_type, c);
889 }
890
891 return array_type->std140_base_alignment(false);
892 }
893
894 /* (9) If the member is a structure, the base alignment of the
895 * structure is <N>, where <N> is the largest base alignment
896 * value of any of its members, and rounded up to the base
897 * alignment of a vec4. The individual members of this
898 * sub-structure are then assigned offsets by applying this set
899 * of rules recursively, where the base offset of the first
900 * member of the sub-structure is equal to the aligned offset
901 * of the structure. The structure may have padding at the end;
902 * the base offset of the member following the sub-structure is
903 * rounded up to the next multiple of the base alignment of the
904 * structure.
905 */
906 if (this->is_record()) {
907 unsigned base_alignment = 16;
908 for (unsigned i = 0; i < this->length; i++) {
909 const struct glsl_type *field_type = this->fields.structure[i].type;
910 base_alignment = MAX2(base_alignment,
911 field_type->std140_base_alignment(row_major));
912 }
913 return base_alignment;
914 }
915
916 assert(!"not reached");
917 return -1;
918 }
919
920 unsigned
921 glsl_type::std140_size(bool row_major) const
922 {
923 /* (1) If the member is a scalar consuming <N> basic machine units, the
924 * base alignment is <N>.
925 *
926 * (2) If the member is a two- or four-component vector with components
927 * consuming <N> basic machine units, the base alignment is 2<N> or
928 * 4<N>, respectively.
929 *
930 * (3) If the member is a three-component vector with components consuming
931 * <N> basic machine units, the base alignment is 4<N>.
932 */
933 if (this->is_scalar() || this->is_vector()) {
934 return this->vector_elements * 4;
935 }
936
937 /* (5) If the member is a column-major matrix with <C> columns and
938 * <R> rows, the matrix is stored identically to an array of
939 * <C> column vectors with <R> components each, according to
940 * rule (4).
941 *
942 * (6) If the member is an array of <S> column-major matrices with <C>
943 * columns and <R> rows, the matrix is stored identically to a row of
944 * <S>*<C> column vectors with <R> components each, according to rule
945 * (4).
946 *
947 * (7) If the member is a row-major matrix with <C> columns and <R>
948 * rows, the matrix is stored identically to an array of <R>
949 * row vectors with <C> components each, according to rule (4).
950 *
951 * (8) If the member is an array of <S> row-major matrices with <C> columns
952 * and <R> rows, the matrix is stored identically to a row of <S>*<R>
953 * row vectors with <C> components each, according to rule (4).
954 */
955 if (this->is_matrix() || (this->is_array() &&
956 this->fields.array->is_matrix())) {
957 const struct glsl_type *element_type;
958 const struct glsl_type *vec_type;
959 unsigned int array_len;
960
961 if (this->is_array()) {
962 element_type = this->fields.array;
963 array_len = this->length;
964 } else {
965 element_type = this;
966 array_len = 1;
967 }
968
969 if (row_major) {
970 vec_type = get_instance(GLSL_TYPE_FLOAT,
971 element_type->matrix_columns, 1);
972 array_len *= element_type->vector_elements;
973 } else {
974 vec_type = get_instance(GLSL_TYPE_FLOAT,
975 element_type->vector_elements, 1);
976 array_len *= element_type->matrix_columns;
977 }
978 const glsl_type *array_type = glsl_type::get_array_instance(vec_type,
979 array_len);
980
981 return array_type->std140_size(false);
982 }
983
984 /* (4) If the member is an array of scalars or vectors, the base alignment
985 * and array stride are set to match the base alignment of a single
986 * array element, according to rules (1), (2), and (3), and rounded up
987 * to the base alignment of a vec4. The array may have padding at the
988 * end; the base offset of the member following the array is rounded up
989 * to the next multiple of the base alignment.
990 *
991 * (10) If the member is an array of <S> structures, the <S> elements of
992 * the array are laid out in order, according to rule (9).
993 */
994 if (this->is_array()) {
995 if (this->fields.array->is_record()) {
996 return this->length * this->fields.array->std140_size(row_major);
997 } else {
998 unsigned element_base_align =
999 this->fields.array->std140_base_alignment(row_major);
1000 return this->length * MAX2(element_base_align, 16);
1001 }
1002 }
1003
1004 /* (9) If the member is a structure, the base alignment of the
1005 * structure is <N>, where <N> is the largest base alignment
1006 * value of any of its members, and rounded up to the base
1007 * alignment of a vec4. The individual members of this
1008 * sub-structure are then assigned offsets by applying this set
1009 * of rules recursively, where the base offset of the first
1010 * member of the sub-structure is equal to the aligned offset
1011 * of the structure. The structure may have padding at the end;
1012 * the base offset of the member following the sub-structure is
1013 * rounded up to the next multiple of the base alignment of the
1014 * structure.
1015 */
1016 if (this->is_record()) {
1017 unsigned size = 0;
1018 for (unsigned i = 0; i < this->length; i++) {
1019 const struct glsl_type *field_type = this->fields.structure[i].type;
1020 unsigned align = field_type->std140_base_alignment(row_major);
1021 size = glsl_align(size, align);
1022 size += field_type->std140_size(row_major);
1023 }
1024 size = glsl_align(size,
1025 this->fields.structure[0].type->std140_base_alignment(row_major));
1026 return size;
1027 }
1028
1029 assert(!"not reached");
1030 return -1;
1031 }