Commit ea411f84 by Ian Lance Taylor

compiler: Permit "for range x" clauses.

Fixes Issue 8370.

From-SVN: r216051
parent 3369b919
......@@ -3836,6 +3836,12 @@ Parse::simple_stat(bool may_be_composite_lit, bool* return_exp,
this->unget_token(Token::make_identifier_token(identifier, is_exported,
location));
}
else if (p_range_clause != NULL && token->is_keyword(KEYWORD_RANGE))
{
Typed_identifier_list til;
this->range_clause_decl(&til, p_range_clause);
return NULL;
}
Expression* exp = this->expression(PRECEDENCE_NORMAL, true,
may_be_composite_lit,
......@@ -5278,7 +5284,7 @@ Parse::for_clause(Expression** cond, Block** post)
}
}
// RangeClause = IdentifierList ( "=" | ":=" ) "range" Expression .
// RangeClause = [ IdentifierList ( "=" | ":=" ) ] "range" Expression .
// This is the := version. It is called with a list of identifiers.
......@@ -5291,7 +5297,6 @@ Parse::range_clause_decl(const Typed_identifier_list* til,
p_range_clause->found = true;
go_assert(til->size() >= 1);
if (til->size() > 2)
error_at(this->location(), "too many variables for range clause");
......@@ -5300,6 +5305,9 @@ Parse::range_clause_decl(const Typed_identifier_list* til,
NULL);
p_range_clause->range = expr;
if (til->empty())
return;
bool any_new = false;
const Typed_identifier* pti = &til->front();
......@@ -5347,6 +5355,9 @@ Parse::range_clause_expr(const Expression_list* vals,
p_range_clause->range = this->expression(PRECEDENCE_NORMAL, false, false,
NULL, NULL);
if (vals->empty())
return;
p_range_clause->index = vals->front();
if (vals->size() == 1)
p_range_clause->value = NULL;
......
......@@ -5305,8 +5305,12 @@ Statement::make_for_statement(Block* init, Expression* cond, Block* post,
int
For_range_statement::do_traverse(Traverse* traverse)
{
if (this->traverse_expression(traverse, &this->index_var_) == TRAVERSE_EXIT)
if (this->index_var_ != NULL)
{
if (this->traverse_expression(traverse, &this->index_var_)
== TRAVERSE_EXIT)
return TRAVERSE_EXIT;
}
if (this->value_var_ != NULL)
{
if (this->traverse_expression(traverse, &this->value_var_)
......@@ -5434,12 +5438,13 @@ For_range_statement::do_lower(Gogo* gogo, Named_object*, Block* enclosing,
if (iter_init != NULL)
body->add_statement(Statement::make_block_statement(iter_init, loc));
if (this->index_var_ != NULL)
{
Statement* assign;
Expression* index_ref = Expression::make_temporary_reference(index_temp, loc);
Expression* index_ref =
Expression::make_temporary_reference(index_temp, loc);
if (this->value_var_ == NULL)
{
assign = Statement::make_assignment(this->index_var_, index_ref, loc);
}
else
{
Expression_list* lhs = new Expression_list();
......@@ -5453,6 +5458,7 @@ For_range_statement::do_lower(Gogo* gogo, Named_object*, Block* enclosing,
assign = Statement::make_tuple_assignment(lhs, rhs, loc);
}
body->add_statement(assign);
}
body->add_statement(Statement::make_block_statement(this->statements_, loc));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment