Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1101)

Unified Diff: src/parsing/parser.cc

Issue 2520883002: [parser] Fix scopes in rewriting of for-of and destructuring assignments. (Closed)
Patch Set: Remove debug print from test. Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: src/parsing/parser.cc
diff --git a/src/parsing/parser.cc b/src/parsing/parser.cc
index 79d06da50750fca179203bb8abd768b07043d76d..b6d06e3c6656154dbb889114831b54d157cf72b5 100644
--- a/src/parsing/parser.cc
+++ b/src/parsing/parser.cc
@@ -4309,8 +4309,16 @@ void Parser::RewriteDestructuringAssignments() {
pair.assignment->AsRewritableExpression();
DCHECK_NOT_NULL(to_rewrite);
if (!to_rewrite->is_rewritten()) {
- PatternRewriter::RewriteDestructuringAssignment(this, to_rewrite,
- pair.scope);
+ // Since this function is called at the end of parsing the program,
+ // pair.scope may already have been removed by FinalizeBlockScope in the
+ // meantime. In that case, use the first outer non-removed scope.
+ Scope* scope = pair.scope;
+ while (scope != nullptr && scope->HasBeenRemoved()) {
Toon Verwaest 2016/11/23 12:20:45 Move to helper function as mentioned before.
+ scope = scope->outer_scope();
+ }
+ DCHECK_NOT_NULL(scope);
+
+ PatternRewriter::RewriteDestructuringAssignment(this, to_rewrite, scope);
}
}
}
@@ -4745,7 +4753,7 @@ Expression* Parser::RewriteYieldStar(Expression* generator,
Block* then = factory()->NewBlock(nullptr, 4 + 1, false, nopos);
BuildIteratorCloseForCompletion(
- then->statements(), var_iterator,
+ scope(), then->statements(), var_iterator,
factory()->NewSmiLiteral(Parser::kNormalCompletion, nopos));
then->statements()->Add(throw_call, zone());
check_throw = factory()->NewIfStatement(
@@ -5113,9 +5121,9 @@ void Parser::BuildIteratorClose(ZoneList<Statement*>* statements,
statements->Add(validate_output, zone());
}
-void Parser::FinalizeIteratorUse(Variable* completion, Expression* condition,
- Variable* iter, Block* iterator_use,
- Block* target) {
+void Parser::FinalizeIteratorUse(Scope* use_scope, Variable* completion,
+ Expression* condition, Variable* iter,
+ Block* iterator_use, Block* target) {
//
// This function adds two statements to [target], corresponding to the
// following code:
@@ -5171,7 +5179,8 @@ void Parser::FinalizeIteratorUse(Variable* completion, Expression* condition,
{
Block* block = factory()->NewBlock(nullptr, 2, true, nopos);
Expression* proxy = factory()->NewVariableProxy(completion);
- BuildIteratorCloseForCompletion(block->statements(), iter, proxy);
+ BuildIteratorCloseForCompletion(use_scope, block->statements(), iter,
+ proxy);
DCHECK(block->statements()->length() == 2);
maybe_close = factory()->NewBlock(nullptr, 1, true, nopos);
@@ -5188,7 +5197,7 @@ void Parser::FinalizeIteratorUse(Variable* completion, Expression* condition,
// }
Statement* try_catch;
{
- Scope* catch_scope = NewScopeWithParent(scope(), CATCH_SCOPE);
+ Scope* catch_scope = NewScopeWithParent(use_scope, CATCH_SCOPE);
Variable* catch_variable =
catch_scope->DeclareLocal(ast_value_factory()->dot_catch_string(), VAR,
kCreatedInitialized, NORMAL_VARIABLE);
@@ -5228,7 +5237,8 @@ void Parser::FinalizeIteratorUse(Variable* completion, Expression* condition,
target->statements()->Add(try_finally, zone());
}
-void Parser::BuildIteratorCloseForCompletion(ZoneList<Statement*>* statements,
+void Parser::BuildIteratorCloseForCompletion(Scope* scope,
+ ZoneList<Statement*>* statements,
Variable* iterator,
Expression* completion) {
//
@@ -5294,7 +5304,7 @@ void Parser::BuildIteratorCloseForCompletion(ZoneList<Statement*>* statements,
Block* catch_block = factory()->NewBlock(nullptr, 0, false, nopos);
- Scope* catch_scope = NewScope(CATCH_SCOPE);
+ Scope* catch_scope = NewScopeWithParent(scope, CATCH_SCOPE);
Variable* catch_variable =
catch_scope->DeclareLocal(ast_value_factory()->dot_catch_string(), VAR,
kCreatedInitialized, NORMAL_VARIABLE);
@@ -5431,8 +5441,13 @@ Statement* Parser::FinalizeForOfStatement(ForOfStatement* loop,
Block* try_block = factory()->NewBlock(nullptr, 1, false, nopos);
try_block->statements()->Add(loop, zone());
- FinalizeIteratorUse(var_completion, closing_condition, loop->iterator(),
- try_block, final_loop);
+ // The scope in which the parser creates this loop.
+ Scope* loop_scope = scope()->outer_scope();
+ DCHECK_EQ(loop_scope->scope_type(), BLOCK_SCOPE);
+ DCHECK_EQ(scope()->scope_type(), BLOCK_SCOPE);
+
+ FinalizeIteratorUse(loop_scope, var_completion, closing_condition,
+ loop->iterator(), try_block, final_loop);
}
return final_loop;
« src/ast/scopes.cc ('K') | « src/parsing/parser.h ('k') | src/parsing/pattern-rewriter.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698