diff mbox

Go patch committed: accept a, a, a = 1, 2, 3

Message ID CAOyqgcWnu6KgZiLRaKeH04stM3ov=f2yDp072NDuL1p=a25-3Q@mail.gmail.com
State New
Headers show

Commit Message

Ian Lance Taylor July 22, 2016, 12:21 a.m. UTC
The Go frontend was incorrectly rejecting
    a, a, a = 1, 2, 3
This was a misfire of the code that detects and rejects
    a, a, a := 1, 2, 3
The former is valid, albeit not very useful, Go.  This patch fixes the
problem.  Bootstrapped and ran Go testsuite on x86_64-pc-linux-gnu.
Committed to mainline.

A test for this has been sent to the master testsuite in
https://golang.org/cl/25143.

Ian
diff mbox

Patch

Index: gcc/go/gofrontend/MERGE
===================================================================
--- gcc/go/gofrontend/MERGE	(revision 238266)
+++ gcc/go/gofrontend/MERGE	(working copy)
@@ -1,4 +1,4 @@ 
-5ea5c078829ae83bccb598772fff7c1a04e23e65
+4c88f31a83ca28963d29d6dc9fcdb2e9b093610c
 
 The first line of this file holds the git revision number of the last
 merge done from the gofrontend repository.
Index: gcc/go/gofrontend/parse.cc
===================================================================
--- gcc/go/gofrontend/parse.cc	(revision 236804)
+++ gcc/go/gofrontend/parse.cc	(working copy)
@@ -2106,6 +2106,8 @@  Parse::simple_var_decl_or_assignment(con
 
   std::set<std::string> uniq_idents;
   uniq_idents.insert(name);
+  std::string dup_name;
+  Location dup_loc;
 
   // We've seen one identifier.  If we see a comma now, this could be
   // "a, *p = 1, 2".
@@ -2145,8 +2147,10 @@  Parse::simple_var_decl_or_assignment(con
 	  id = this->gogo_->pack_hidden_name(id, is_id_exported);
 	  ins = uniq_idents.insert(id);
 	  if (!ins.second && !Gogo::is_sink_name(id))
-	    error_at(id_location, "multiple assignments to %s",
-		     Gogo::message_name(id).c_str());
+	    {
+	      dup_name = Gogo::message_name(id);
+	      dup_loc = id_location;
+	    }
 	  til.push_back(Typed_identifier(id, NULL, location));
 	}
 
@@ -2182,6 +2186,9 @@  Parse::simple_var_decl_or_assignment(con
   go_assert(this->peek_token()->is_op(OPERATOR_COLONEQ));
   const Token* token = this->advance_token();
 
+  if (!dup_name.empty())
+    error_at(dup_loc, "multiple assignments to %s", dup_name.c_str());
+
   if (p_range_clause != NULL && token->is_keyword(KEYWORD_RANGE))
     {
       this->range_clause_decl(&til, p_range_clause);