Reviewers: arv, rossberg,

Message:
PTAL.
Turned out to be easy enough after my ParseVariableDeclarations refactoring.

Description:
[destructuring] Implement pattern matching in lexcal for-of/for-in.

R=a...@chromium.org,rossb...@chromium.org
BUG=v8:811
LOG=N

Please review this at https://codereview.chromium.org/1152503002/

Base URL: https://chromium.googlesource.com/v8/v8.git@master

Affected files (+44, -14 lines):
  M src/parser.cc
  M test/mjsunit/harmony/destructuring.js


Index: src/parser.cc
diff --git a/src/parser.cc b/src/parser.cc
index c2e7c6dbf8bf77aedfac4ebed582e143edc339c8..8f11a8ad778d899e51d654d4b7008c12b8213df6 100644
--- a/src/parser.cc
+++ b/src/parser.cc
@@ -3484,8 +3484,6 @@ Statement* Parser::ParseForStatement(ZoneList<const AstRawString*>* labels,
       is_const = peek() == Token::CONST;
       ParseVariableDeclarations(kForStatement, &parsing_result, CHECK_OK);
       DCHECK(parsing_result.descriptor.pos != RelocInfo::kNoPosition);
-      Block* variable_statement =
- parsing_result.BuildInitializationBlock(&lexical_bindings, CHECK_OK);

       int num_decl = parsing_result.declarations.length();
       bool accept_IN = num_decl >= 1;
@@ -3546,19 +3544,29 @@ Statement* Parser::ParseForStatement(ZoneList<const AstRawString*>* labels,
         scope_ = for_scope;
         Expect(Token::RPAREN, CHECK_OK);

-        VariableProxy* each =
-            scope_->NewUnresolved(factory(), parsing_result.SingleName(),
-                                  Variable::NORMAL, each_end_pos);
+        // VariableProxy* each =
+        //    scope_->NewUnresolved(factory(), parsing_result.SingleName(),
+        //                          Variable::NORMAL, each_end_pos);
         Statement* body = ParseSubStatement(NULL, CHECK_OK);
         Block* body_block =
             factory()->NewBlock(NULL, 3, false, RelocInfo::kNoPosition);
- Token::Value init_op = is_const ? Token::INIT_CONST : Token::ASSIGN;
-        Assignment* assignment = factory()->NewAssignment(
-            init_op, each, temp_proxy, RelocInfo::kNoPosition);
- Statement* assignment_statement = factory()->NewExpressionStatement(
-            assignment, RelocInfo::kNoPosition);
-        body_block->AddStatement(variable_statement, zone());
-        body_block->AddStatement(assignment_statement, zone());
+        // Assignment* assignment = factory()->NewAssignment(
+        //    init_op, each, temp_proxy, RelocInfo::kNoPosition);
+ // Statement* assignment_statement = factory()->NewExpressionStatement(
+        //    assignment, RelocInfo::kNoPosition);
+        auto each_initialization_block = factory()->NewBlock(
+            nullptr, 1, true, parsing_result.descriptor.pos);
+        {
+          DCHECK(parsing_result.declarations.length() == 1);
+          DeclarationParsingResult::Declaration decl =
+              parsing_result.declarations[0];
+          decl.initializer = temp_proxy;
+          PatternRewriter::DeclareAndInitializeVariables(
+              each_initialization_block, &parsing_result.descriptor, &decl,
+              &lexical_bindings, CHECK_OK);
+        }
+
+        body_block->AddStatement(each_initialization_block, zone());
         body_block->AddStatement(body, zone());
InitializeForEachStatement(loop, temp_proxy, enumerable, body_block);
         scope_ = saved_scope;
@@ -3567,9 +3575,9 @@ Statement* Parser::ParseForStatement(ZoneList<const AstRawString*>* labels,
         body_block->set_scope(for_scope);
         // Parsed for-in loop w/ let declaration.
         return loop;
-
       } else {
-        init = variable_statement;
+        init = parsing_result.BuildInitializationBlock(&lexical_bindings,
+                                                       CHECK_OK);
       }
     } else {
       Scanner::Location lhs_location = scanner()->peek_location();
Index: test/mjsunit/harmony/destructuring.js
diff --git a/test/mjsunit/harmony/destructuring.js b/test/mjsunit/harmony/destructuring.js index 11a0bebcbfb29ac17d10d81a89de56e82b49d387..29751b81070923154bff02eab641fc65eb4ec598 100644
--- a/test/mjsunit/harmony/destructuring.js
+++ b/test/mjsunit/harmony/destructuring.js
@@ -623,3 +623,25 @@
     assertArrayEquals(["1", "2"], log);
   }());
 }());
+
+
+(function TestForEachLexical() {
+  'use strict';
+  let a = [{x:1, y:-1}, {x:2,y:-2}, {x:3,y:-3}];
+  let sumX = 0;
+  let sumY = 0;
+  let fs = [];
+  for (let {x,y} of a) {
+    sumX += x;
+    sumY += y;
+    fs.push({fx : function() { return x; }, fy : function() { return y }});
+  }
+  assertSame(6, sumX);
+  assertSame(-6, sumY);
+  assertSame(3, fs.length);
+  for (let i = 0; i < fs.length; i++) {
+    let {fx,fy} = fs[i];
+    assertSame(i+1, fx());
+    assertSame(-(i+1), fy());
+  }
+}());


--
--
v8-dev mailing list
v8-dev@googlegroups.com
http://groups.google.com/group/v8-dev
--- You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to v8-dev+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to