Index: runtime/vm/parser.cc |
=================================================================== |
--- runtime/vm/parser.cc (revision 28999) |
+++ runtime/vm/parser.cc (working copy) |
@@ -6021,10 +6021,11 @@ |
// or any other class that does not override the == operator. |
// The expressions are compile-time constants and are thus in the form |
// of a LiteralNode. |
-void Parser::CheckCaseExpressions(const GrowableArray<LiteralNode*>& values) { |
+RawType* Parser::CheckCaseExpressions( |
+ const GrowableArray<LiteralNode*>& values) { |
const intptr_t num_expressions = values.length(); |
if (num_expressions == 0) { |
- return; |
+ return Type::DynamicType(); |
} |
const Instance& first_value = values[0]->literal(); |
for (intptr_t i = 0; i < num_expressions; i++) { |
@@ -6059,6 +6060,12 @@ |
} |
} |
} |
+ if (first_value.IsInteger()) { |
+ return Type::IntType(); |
+ } else if (first_value.IsString()) { |
+ return Type::StringType(); |
+ } |
+ return Type::NewNonParameterizedType(Class::Handle(first_value.clazz())); |
} |
@@ -6158,10 +6165,9 @@ |
current_block_->scope->AddLabel(label); |
// Store switch expression in temporary local variable. |
+ Type& temp_var_type = Type::ZoneHandle(Type::DynamicType()); |
LocalVariable* temp_variable = |
- new LocalVariable(expr_pos, |
- Symbols::SwitchExpr(), |
- Type::ZoneHandle(Type::DynamicType())); |
+ new LocalVariable(expr_pos, Symbols::SwitchExpr(), temp_var_type); |
current_block_->scope->AddVariable(temp_variable); |
AstNode* save_switch_expr = |
new StoreLocalNode(expr_pos, temp_variable, switch_expr); |
@@ -6214,8 +6220,11 @@ |
} |
// Check that all expressions in case clauses are of the same class, |
- // or implement int, double or String. |
- CheckCaseExpressions(case_expr_values); |
+ // or implement int, double or String. Patch the type of the temporary |
+ // variable holding the switch expression to match the type of the |
+ // case clause constants. |
+ temp_var_type = CheckCaseExpressions(case_expr_values); |
+ temp_variable->set_type(temp_var_type); |
// Check for unresolved label references. |
SourceLabel* unresolved_label = |