From: Ian Romanick Date: Wed, 16 Jul 2014 22:37:10 +0000 (-0700) Subject: linker: Add a last_field parameter to various program_resource_visitor methods X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=47c6fc5b04774737404b55b01cbab5c3baf1c183;p=mesa.git linker: Add a last_field parameter to various program_resource_visitor methods I also considered renaming visit_field(const glsl_struct_field *) to entry_record and adding an exit_record method. This would be more similar to the hierarchical visitor. Signed-off-by: Ian Romanick Reviewed-by: Matt Turner --- diff --git a/src/glsl/link_uniform_blocks.cpp b/src/glsl/link_uniform_blocks.cpp index 0b1291d9a9b..ddd134a348a 100644 --- a/src/glsl/link_uniform_blocks.cpp +++ b/src/glsl/link_uniform_blocks.cpp @@ -68,7 +68,8 @@ private: } virtual void visit_field(const glsl_type *type, const char *name, - bool row_major, const glsl_type *record_type) + bool row_major, const glsl_type *record_type, + bool last_field) { assert(this->index < this->num_variables); diff --git a/src/glsl/link_uniforms.cpp b/src/glsl/link_uniforms.cpp index 74895362c7d..8014a3d9a99 100644 --- a/src/glsl/link_uniforms.cpp +++ b/src/glsl/link_uniforms.cpp @@ -63,7 +63,7 @@ program_resource_visitor::process(const glsl_type *type, const char *name) || type->without_array()->is_interface()); char *name_copy = ralloc_strdup(NULL, name); - recursion(type, &name_copy, strlen(name), false, NULL); + recursion(type, &name_copy, strlen(name), false, NULL, false); ralloc_free(name_copy); } @@ -108,7 +108,7 @@ program_resource_visitor::process(ir_variable *var) * lowering is only applied to non-uniform interface blocks, so we * can safely pass false for row_major. */ - recursion(var->type, &name, new_length, false, NULL); + recursion(var->type, &name, new_length, false, NULL, false); } ralloc_free(name); } else if (var->data.from_named_ifc_block_nonarray) { @@ -132,29 +132,30 @@ program_resource_visitor::process(ir_variable *var) * is only applied to non-uniform interface blocks, so we can safely * pass false for row_major. */ - recursion(var->type, &name, strlen(name), false, NULL); + recursion(var->type, &name, strlen(name), false, NULL, false); ralloc_free(name); } else if (t->without_array()->is_record()) { char *name = ralloc_strdup(NULL, var->name); - recursion(var->type, &name, strlen(name), false, NULL); + recursion(var->type, &name, strlen(name), false, NULL, false); ralloc_free(name); } else if (t->is_interface()) { char *name = ralloc_strdup(NULL, var->type->name); - recursion(var->type, &name, strlen(name), false, NULL); + recursion(var->type, &name, strlen(name), false, NULL, false); ralloc_free(name); } else if (t->is_array() && t->fields.array->is_interface()) { char *name = ralloc_strdup(NULL, var->type->fields.array->name); - recursion(var->type, &name, strlen(name), false, NULL); + recursion(var->type, &name, strlen(name), false, NULL, false); ralloc_free(name); } else { - this->visit_field(t, var->name, false, NULL); + this->visit_field(t, var->name, false, NULL, false); } } void program_resource_visitor::recursion(const glsl_type *t, char **name, size_t name_length, bool row_major, - const glsl_type *record_type) + const glsl_type *record_type, + bool last_field) { /* Records need to have each field processed individually. * @@ -181,7 +182,8 @@ program_resource_visitor::recursion(const glsl_type *t, char **name, } recursion(t->fields.structure[i].type, name, new_length, - t->fields.structure[i].row_major, record_type); + t->fields.structure[i].row_major, record_type, + (i + 1) == t->length); /* Only the first leaf-field of the record gets called with the * record type pointer. @@ -200,7 +202,8 @@ program_resource_visitor::recursion(const glsl_type *t, char **name, ralloc_asprintf_rewrite_tail(name, &new_length, "[%u]", i); recursion(t->fields.array, name, new_length, row_major, - record_type); + record_type, + (i + 1) == t->length); /* Only the first leaf-field of the record gets called with the * record type pointer. @@ -208,14 +211,15 @@ program_resource_visitor::recursion(const glsl_type *t, char **name, record_type = NULL; } } else { - this->visit_field(t, *name, row_major, record_type); + this->visit_field(t, *name, row_major, record_type, last_field); } } void program_resource_visitor::visit_field(const glsl_type *type, const char *name, bool row_major, - const glsl_type *) + const glsl_type *, + bool /* last_field */) { visit_field(type, name, row_major); } @@ -508,7 +512,8 @@ private: } virtual void visit_field(const glsl_type *type, const char *name, - bool row_major, const glsl_type *record_type) + bool row_major, const glsl_type *record_type, + bool /* last_field */) { assert(!type->without_array()->is_record()); assert(!type->without_array()->is_interface()); diff --git a/src/glsl/linker.h b/src/glsl/linker.h index 130915db412..8851da6c8b4 100644 --- a/src/glsl/linker.h +++ b/src/glsl/linker.h @@ -138,11 +138,15 @@ protected: * \param name Fully qualified name of the field. * \param row_major For a matrix type, is it stored row-major. * \param record_type Type of the record containing the field. + * \param last_field Set if \c name is the last field of the structure + * containing it. This will always be false for items + * not contained in a structure or interface block. * * The default implementation just calls the other \c visit_field method. */ virtual void visit_field(const glsl_type *type, const char *name, - bool row_major, const glsl_type *record_type); + bool row_major, const glsl_type *record_type, + bool last_field); /** * Method invoked for each leaf of the variable @@ -168,9 +172,13 @@ private: /** * \param name_length Length of the current name \b not including the * terminating \c NUL character. + * \param last_field Set if \c name is the last field of the structure + * containing it. This will always be false for items + * not contained in a structure or interface block. */ void recursion(const glsl_type *t, char **name, size_t name_length, - bool row_major, const glsl_type *record_type); + bool row_major, const glsl_type *record_type, + bool last_field); }; void