From: Eric Anholt Date: Tue, 6 Apr 2010 17:30:54 +0000 (-0700) Subject: Handle constant expressions using derefs of const values. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=326c676236e6a3c90db63e4d0c893aa4f9c21876;p=mesa.git Handle constant expressions using derefs of const values. Fixes CorrectParse1.frag and makes for a ton of folding in CorrectParse2.frag. --- diff --git a/ast_to_hir.cpp b/ast_to_hir.cpp index 9d067be02d7..ddeab8db67c 100644 --- a/ast_to_hir.cpp +++ b/ast_to_hir.cpp @@ -1603,12 +1603,15 @@ ast_declarator_list::hir(exec_list *instructions, * declaration. */ if (this->type->qualifier.constant) { - rhs = rhs->constant_expression_value(); - if (!rhs) { + ir_constant *constant_value = rhs->constant_expression_value(); + if (!constant_value) { _mesa_glsl_error(& initializer_loc, state, "initializer of const variable `%s' must be a " "constant expression", decl->identifier); + } else { + rhs = constant_value; + var->constant_value = constant_value; } } diff --git a/ir.cpp b/ir.cpp index 88308ce1790..0708e492850 100644 --- a/ir.cpp +++ b/ir.cpp @@ -338,6 +338,7 @@ ir_variable::ir_variable(const struct glsl_type *type, const char *name) { this->type = type; this->name = name; + this->constant_value = NULL; if (type && type->base_type == GLSL_TYPE_SAMPLER) this->read_only = true; diff --git a/ir.h b/ir.h index 5267d2bc787..a515d9a7d0a 100644 --- a/ir.h +++ b/ir.h @@ -154,6 +154,11 @@ public: * equality). This flag enables this behavior. */ unsigned array_lvalue:1; + + /** + * Value assigned in the initializer of a variable declared "const" + */ + ir_constant *constant_value; }; diff --git a/ir_constant_expression.cpp b/ir_constant_expression.cpp index 6325df5cc73..9c98ceb66cf 100644 --- a/ir_constant_expression.cpp +++ b/ir_constant_expression.cpp @@ -395,8 +395,15 @@ ir_constant_visitor::visit(ir_swizzle *ir) void ir_constant_visitor::visit(ir_dereference *ir) { - (void) ir; value = NULL; + + if (ir->mode == ir_dereference::ir_reference_variable) { + ir_variable *var = ir->var->as_variable(); + if (var && var->constant_value) { + value = new ir_constant(ir->type, &var->constant_value->value); + } + } + /* FINISHME: Other dereference modes. */ }