Mesa (7.10): glsl: Process redeclarations before initializers
Ian Romanick
idr at kemper.freedesktop.org
Thu Mar 24 20:39:45 UTC 2011
Module: Mesa
Branch: 7.10
Commit: 856a661d2fa1936d81c3c2b50f2ee0e796008527
URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=856a661d2fa1936d81c3c2b50f2ee0e796008527
Author: Ian Romanick <ian.d.romanick at intel.com>
Date: Fri Mar 4 16:15:20 2011 -0800
glsl: Process redeclarations before initializers
If an array redeclaration includes an initializer, the initializer
would previously be dropped on the floor. Instead, directly apply the
initializer to the correct ir_variable instance and append the
generated instructions.
Fixes bugzilla #34374 and piglit tests glsl-{vs,fs}-array-redeclaration.
NOTE: This is a candidate for stable release branches. 0292ffb8 and
8e6cb9fe are also necessary.
(cherry picked from commit 09a4ba0fc31fa8fc193dfb7b4fd78e32722b8312)
---
src/glsl/ast_to_hir.cpp | 87 ++++++++++++++++++++++++-----------------------
1 files changed, 44 insertions(+), 43 deletions(-)
diff --git a/src/glsl/ast_to_hir.cpp b/src/glsl/ast_to_hir.cpp
index a05b4cf..799ccdb 100644
--- a/src/glsl/ast_to_hir.cpp
+++ b/src/glsl/ast_to_hir.cpp
@@ -2511,8 +2511,11 @@ ast_declarator_list::hir(exec_list *instructions,
* instruction stream.
*/
exec_list initializer_instructions;
+ ir_variable *earlier = get_variable_being_redeclared(var, decl, state);
+
if (decl->initializer != NULL) {
- result = process_initializer(var, decl, this->type,
+ result = process_initializer((earlier == NULL) ? var : earlier,
+ decl, this->type,
&initializer_instructions, state);
}
@@ -2528,52 +2531,50 @@ ast_declarator_list::hir(exec_list *instructions,
decl->identifier);
}
- ir_variable *earlier = get_variable_being_redeclared(var, decl, state);
- if (earlier != NULL) {
- continue;
- }
-
- /* By now, we know it's a new variable declaration (we didn't hit the
- * above "continue").
- *
- * From page 15 (page 21 of the PDF) of the GLSL 1.10 spec,
- *
- * "Identifiers starting with "gl_" are reserved for use by
- * OpenGL, and may not be declared in a shader as either a
- * variable or a function."
+ /* If the declaration is not a redeclaration, there are a few additional
+ * semantic checks that must be applied. In addition, variable that was
+ * created for the declaration should be added to the IR stream.
*/
- if (strncmp(decl->identifier, "gl_", 3) == 0)
- _mesa_glsl_error(& loc, state,
- "identifier `%s' uses reserved `gl_' prefix",
- decl->identifier);
+ if (earlier == NULL) {
+ /* From page 15 (page 21 of the PDF) of the GLSL 1.10 spec,
+ *
+ * "Identifiers starting with "gl_" are reserved for use by
+ * OpenGL, and may not be declared in a shader as either a
+ * variable or a function."
+ */
+ if (strncmp(decl->identifier, "gl_", 3) == 0)
+ _mesa_glsl_error(& loc, state,
+ "identifier `%s' uses reserved `gl_' prefix",
+ decl->identifier);
- /* Add the variable to the symbol table. Note that the initializer's
- * IR was already processed earlier (though it hasn't been emitted yet),
- * without the variable in scope.
- *
- * This differs from most C-like languages, but it follows the GLSL
- * specification. From page 28 (page 34 of the PDF) of the GLSL 1.50
- * spec:
- *
- * "Within a declaration, the scope of a name starts immediately
- * after the initializer if present or immediately after the name
- * being declared if not."
- */
- if (!state->symbols->add_variable(var)) {
- YYLTYPE loc = this->get_location();
- _mesa_glsl_error(&loc, state, "name `%s' already taken in the "
- "current scope", decl->identifier);
- continue;
+ /* Add the variable to the symbol table. Note that the initializer's
+ * IR was already processed earlier (though it hasn't been emitted
+ * yet), without the variable in scope.
+ *
+ * This differs from most C-like languages, but it follows the GLSL
+ * specification. From page 28 (page 34 of the PDF) of the GLSL 1.50
+ * spec:
+ *
+ * "Within a declaration, the scope of a name starts immediately
+ * after the initializer if present or immediately after the name
+ * being declared if not."
+ */
+ if (!state->symbols->add_variable(var)) {
+ YYLTYPE loc = this->get_location();
+ _mesa_glsl_error(&loc, state, "name `%s' already taken in the "
+ "current scope", decl->identifier);
+ continue;
+ }
+
+ /* Push the variable declaration to the top. It means that all the
+ * variable declarations will appear in a funny last-to-first order,
+ * but otherwise we run into trouble if a function is prototyped, a
+ * global var is decled, then the function is defined with usage of
+ * the global var. See glslparsertest's CorrectModule.frag.
+ */
+ instructions->push_head(var);
}
- /* Push the variable declaration to the top. It means that all
- * the variable declarations will appear in a funny
- * last-to-first order, but otherwise we run into trouble if a
- * function is prototyped, a global var is decled, then the
- * function is defined with usage of the global var. See
- * glslparsertest's CorrectModule.frag.
- */
- instructions->push_head(var);
instructions->append_list(&initializer_instructions);
}
More information about the mesa-commit
mailing list