From 0026ad4994ca88a6cdd4e5ef4098469ab57bdcc1 Mon Sep 17 00:00:00 2001 From: Paul Berry Date: Wed, 31 Jul 2013 08:15:08 -0700 Subject: [PATCH] Move count_attribute_slots() out of the linker and into glsl_type. Our previous justification for leaving this function out of glsl_type was that it implemented counting rules that were specific to GLSL 1.50. However, these counting rules also describe the number of varying slots that Mesa will assign to a varying in the absence of varying packing. That's useful to be able to compute from outside of the linker code (a future patch will use it from ir_set_program_inouts.cpp). So go ahead and move it to glsl_type. Reviewed-by: Ian Romanick Reviewed-by: Kenneth Graunke --- src/glsl/glsl_types.cpp | 28 ++++++++++++++++++++++++++++ src/glsl/glsl_types.h | 12 ++++++++++++ src/glsl/link_varyings.cpp | 2 +- src/glsl/linker.cpp | 37 +------------------------------------ src/glsl/linker.h | 3 --- 5 files changed, 42 insertions(+), 40 deletions(-) diff --git a/src/glsl/glsl_types.cpp b/src/glsl/glsl_types.cpp index 8324b8ade7a..0c639b3eb87 100644 --- a/src/glsl/glsl_types.cpp +++ b/src/glsl/glsl_types.cpp @@ -828,3 +828,31 @@ glsl_type::std140_size(bool row_major) const assert(!"not reached"); return -1; } + + +unsigned +glsl_type::count_attribute_slots() const +{ + /* From page 31 (page 37 of the PDF) of the GLSL 1.50 spec: + * + * "A scalar input counts the same amount against this limit as a vec4, + * so applications may want to consider packing groups of four + * unrelated float inputs together into a vector to better utilize the + * capabilities of the underlying hardware. A matrix input will use up + * multiple locations. The number of locations used will equal the + * number of columns in the matrix." + * + * The spec does not explicitly say how arrays are counted. However, it + * should be safe to assume the total number of slots consumed by an array + * is the number of entries in the array multiplied by the number of slots + * consumed by a single element of the array. + */ + + if (this->is_array()) + return this->array_size() * this->element_type()->count_attribute_slots(); + + if (this->is_matrix()) + return this->matrix_columns; + + return 1; +} diff --git a/src/glsl/glsl_types.h b/src/glsl/glsl_types.h index 8172309a763..647867a23f1 100644 --- a/src/glsl/glsl_types.h +++ b/src/glsl/glsl_types.h @@ -252,6 +252,18 @@ struct glsl_type { */ unsigned component_slots() const; + /** + * Calculate the number of attribute slots required to hold this type + * + * This implements the language rules of GLSL 1.50 for counting the number + * of slots used by a vertex attribute. It also determines the number of + * varying slots the type will use up in the absence of varying packing + * (and thus, it can be used to measure the number of varying slots used by + * the varyings that are generated by lower_packed_varyings). + */ + unsigned count_attribute_slots() const; + + /** * Alignment in bytes of the start of this type in a std140 uniform * block. diff --git a/src/glsl/link_varyings.cpp b/src/glsl/link_varyings.cpp index 2c7e4514e15..e3c8142546d 100644 --- a/src/glsl/link_varyings.cpp +++ b/src/glsl/link_varyings.cpp @@ -1164,7 +1164,7 @@ check_against_varying_limit(struct gl_context *ctx, /* The packing rules used for vertex shader inputs are also * used for fragment shader inputs. */ - varying_vectors += count_attribute_slots(var->type); + varying_vectors += var->type->count_attribute_slots(); } } diff --git a/src/glsl/linker.cpp b/src/glsl/linker.cpp index 942f9061596..82075cbc0e3 100644 --- a/src/glsl/linker.cpp +++ b/src/glsl/linker.cpp @@ -297,41 +297,6 @@ link_invalidate_variable_locations(gl_shader *sh, int input_base, } -/** - * Determine the number of attribute slots required for a particular type - * - * This code is here because it implements the language rules of a specific - * GLSL version. Since it's a property of the language and not a property of - * types in general, it doesn't really belong in glsl_type. - */ -unsigned -count_attribute_slots(const glsl_type *t) -{ - /* From page 31 (page 37 of the PDF) of the GLSL 1.50 spec: - * - * "A scalar input counts the same amount against this limit as a vec4, - * so applications may want to consider packing groups of four - * unrelated float inputs together into a vector to better utilize the - * capabilities of the underlying hardware. A matrix input will use up - * multiple locations. The number of locations used will equal the - * number of columns in the matrix." - * - * The spec does not explicitly say how arrays are counted. However, it - * should be safe to assume the total number of slots consumed by an array - * is the number of entries in the array multiplied by the number of slots - * consumed by a single element of the array. - */ - - if (t->is_array()) - return t->array_size() * count_attribute_slots(t->element_type()); - - if (t->is_matrix()) - return t->matrix_columns; - - return 1; -} - - /** * Verify that a vertex shader executable meets all semantic requirements. * @@ -1334,7 +1299,7 @@ assign_attribute_or_color_locations(gl_shader_program *prog, * that it doesn't collide with other assigned locations. Otherwise, * add it to the list of variables that need linker-assigned locations. */ - const unsigned slots = count_attribute_slots(var->type); + const unsigned slots = var->type->count_attribute_slots(); if (var->location != -1) { if (var->location >= generic_base && var->index < 1) { /* From page 61 of the OpenGL 4.0 spec: diff --git a/src/glsl/linker.h b/src/glsl/linker.h index 0ce747d6cb9..64a683d1545 100644 --- a/src/glsl/linker.h +++ b/src/glsl/linker.h @@ -155,7 +155,4 @@ linker_error(gl_shader_program *prog, const char *fmt, ...); void linker_warning(gl_shader_program *prog, const char *fmt, ...); -unsigned -count_attribute_slots(const glsl_type *t); - #endif /* GLSL_LINKER_H */ -- 2.30.2