Revert of Revert "Revert of [es6] Implement destructuring binding in try/catch" (patchset #2 id:20001 of https://codereview.chromium.org/1411323008/ )
Reason for revert: [Sheriff] Breaks a layout test: https://build.chromium.org/p/client.v8.fyi/builders/V8-Blink%20Linux%2064/builds/2750 Please request rebase upstream first if intended. Original issue's description: > Revert "Revert of [es6] Implement destructuring binding in try/catch" > > Reland try/catch destructuring with a fix for the MemorySanitizer failure: > initialization_pos needs to be initialized in the DeclarationDescriptor. > > This is a one line fix to http://crrev.com/a316db995e6e4253664920652ed4e5a38b2caeba > > BUG=v8:811 > LOG=y > > Committed: https://crrev.com/80a1e004f4ef619b54a2d87bf2108719a8411860 > Cr-Commit-Position: refs/heads/master@{#31834} TBR=littledan@chromium.org,rossberg@chromium.org,adamk@chromium.org NOPRESUBMIT=true NOTREECHECKS=true NOTRY=true BUG=v8:811 Review URL: https://codereview.chromium.org/1421193006 Cr-Commit-Position: refs/heads/master@{#31840}
This commit is contained in:
parent
83f60ab5ac
commit
35a60c211e
@ -255,7 +255,6 @@ class AstValue : public ZoneObject {
|
||||
F(dot_module, ".module") \
|
||||
F(dot_result, ".result") \
|
||||
F(dot_switch_tag, ".switch_tag") \
|
||||
F(dot_catch, ".catch") \
|
||||
F(empty, "") \
|
||||
F(eval, "eval") \
|
||||
F(let, "let") \
|
||||
|
@ -1072,8 +1072,7 @@ FunctionLiteral* Parser::DoParseProgram(ParseInfo* info) {
|
||||
// unchanged if the property already exists.
|
||||
InsertSloppyBlockFunctionVarBindings(scope, &ok);
|
||||
}
|
||||
if (ok && (is_strict(language_mode()) || allow_harmony_sloppy() ||
|
||||
allow_harmony_destructuring())) {
|
||||
if (ok && (is_strict(language_mode()) || allow_harmony_sloppy())) {
|
||||
CheckConflictingVarDeclarations(scope_, &ok);
|
||||
}
|
||||
|
||||
@ -3157,79 +3156,21 @@ TryStatement* Parser::ParseTryStatement(bool* ok) {
|
||||
Scope* catch_scope = NULL;
|
||||
Variable* catch_variable = NULL;
|
||||
Block* catch_block = NULL;
|
||||
const AstRawString* name = NULL;
|
||||
if (tok == Token::CATCH) {
|
||||
Consume(Token::CATCH);
|
||||
|
||||
Expect(Token::LPAREN, CHECK_OK);
|
||||
catch_scope = NewScope(scope_, CATCH_SCOPE);
|
||||
catch_scope->set_start_position(scanner()->location().beg_pos);
|
||||
|
||||
ExpressionClassifier pattern_classifier;
|
||||
Expression* pattern = ParsePrimaryExpression(&pattern_classifier, CHECK_OK);
|
||||
ValidateBindingPattern(&pattern_classifier, CHECK_OK);
|
||||
|
||||
const AstRawString* name = ast_value_factory()->dot_catch_string();
|
||||
bool is_simple = pattern->IsVariableProxy();
|
||||
if (is_simple) {
|
||||
auto proxy = pattern->AsVariableProxy();
|
||||
scope_->RemoveUnresolved(proxy);
|
||||
name = proxy->raw_name();
|
||||
}
|
||||
|
||||
catch_variable = catch_scope->DeclareLocal(name, VAR, kCreatedInitialized,
|
||||
Variable::NORMAL);
|
||||
name = ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK);
|
||||
|
||||
Expect(Token::RPAREN, CHECK_OK);
|
||||
|
||||
{
|
||||
catch_variable = catch_scope->DeclareLocal(name, VAR, kCreatedInitialized,
|
||||
Variable::NORMAL);
|
||||
BlockState block_state(&scope_, catch_scope);
|
||||
|
||||
// TODO(adamk): Make a version of ParseScopedBlock that takes a scope and
|
||||
// a block.
|
||||
catch_block =
|
||||
factory()->NewBlock(nullptr, 16, false, RelocInfo::kNoPosition);
|
||||
Scope* block_scope = NewScope(scope_, BLOCK_SCOPE);
|
||||
|
||||
block_scope->set_start_position(scanner()->location().beg_pos);
|
||||
{
|
||||
BlockState block_state(&scope_, block_scope);
|
||||
Target target(&this->target_stack_, catch_block);
|
||||
|
||||
if (!is_simple) {
|
||||
DeclarationDescriptor descriptor;
|
||||
descriptor.declaration_kind = DeclarationDescriptor::NORMAL;
|
||||
descriptor.parser = this;
|
||||
descriptor.declaration_scope = scope_;
|
||||
descriptor.scope = scope_;
|
||||
descriptor.hoist_scope = nullptr;
|
||||
descriptor.mode = LET;
|
||||
descriptor.is_const = false;
|
||||
descriptor.needs_init = true;
|
||||
descriptor.declaration_pos = pattern->position();
|
||||
descriptor.initialization_pos = pattern->position();
|
||||
descriptor.init_op = Token::INIT_LET;
|
||||
|
||||
DeclarationParsingResult::Declaration decl(
|
||||
pattern, pattern->position(),
|
||||
factory()->NewVariableProxy(catch_variable));
|
||||
|
||||
PatternRewriter::DeclareAndInitializeVariables(
|
||||
catch_block, &descriptor, &decl, nullptr, CHECK_OK);
|
||||
}
|
||||
|
||||
Expect(Token::LBRACE, CHECK_OK);
|
||||
while (peek() != Token::RBRACE) {
|
||||
Statement* stat = ParseStatementListItem(CHECK_OK);
|
||||
if (stat && !stat->IsEmpty()) {
|
||||
catch_block->statements()->Add(stat, zone());
|
||||
}
|
||||
}
|
||||
Consume(Token::RBRACE);
|
||||
}
|
||||
block_scope->set_end_position(scanner()->location().end_pos);
|
||||
block_scope = block_scope->FinalizeBlockScope();
|
||||
catch_block->set_scope(block_scope);
|
||||
}
|
||||
catch_block = ParseBlock(NULL, CHECK_OK);
|
||||
|
||||
catch_scope->set_end_position(scanner()->location().end_pos);
|
||||
tok = peek();
|
||||
@ -4429,8 +4370,7 @@ FunctionLiteral* Parser::ParseFunctionLiteral(
|
||||
if (is_sloppy(language_mode) && allow_harmony_sloppy_function()) {
|
||||
InsertSloppyBlockFunctionVarBindings(scope, CHECK_OK);
|
||||
}
|
||||
if (is_strict(language_mode) || allow_harmony_sloppy() ||
|
||||
allow_harmony_destructuring()) {
|
||||
if (is_strict(language_mode) || allow_harmony_sloppy()) {
|
||||
CheckConflictingVarDeclarations(scope, CHECK_OK);
|
||||
}
|
||||
}
|
||||
|
@ -1039,12 +1039,9 @@ PreParser::Statement PreParser::ParseTryStatement(bool* ok) {
|
||||
if (tok == Token::CATCH) {
|
||||
Consume(Token::CATCH);
|
||||
Expect(Token::LPAREN, CHECK_OK);
|
||||
ExpressionClassifier pattern_classifier;
|
||||
ParsePrimaryExpression(&pattern_classifier, CHECK_OK);
|
||||
ValidateBindingPattern(&pattern_classifier, CHECK_OK);
|
||||
ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK);
|
||||
Expect(Token::RPAREN, CHECK_OK);
|
||||
{
|
||||
// TODO(adamk): Make this CATCH_SCOPE
|
||||
Scope* with_scope = NewScope(scope_, WITH_SCOPE);
|
||||
BlockState block_state(&scope_, with_scope);
|
||||
ParseBlock(CHECK_OK);
|
||||
|
@ -6514,7 +6514,6 @@ TEST(DestructuringPositiveTests) {
|
||||
{"function f(argument1, ", ") {}"},
|
||||
{"var f = (", ") => {};"},
|
||||
{"var f = (argument1,", ") => {};"},
|
||||
{"try {} catch(", ") {}"},
|
||||
{NULL, NULL}};
|
||||
|
||||
// clang-format off
|
||||
@ -6576,7 +6575,6 @@ TEST(DestructuringNegativeTests) {
|
||||
{"var f = (", ") => {};"},
|
||||
{"var f = ", " => {};"},
|
||||
{"var f = (argument1,", ") => {};"},
|
||||
{"try {} catch(", ") {}"},
|
||||
{NULL, NULL}};
|
||||
|
||||
// clang-format off
|
||||
|
@ -1,11 +0,0 @@
|
||||
// Copyright 2015 the V8 project authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
//
|
||||
// Flags: --harmony-destructuring
|
||||
|
||||
"use strict";
|
||||
try {
|
||||
} catch ({x}) {
|
||||
let x;
|
||||
}
|
@ -1,4 +0,0 @@
|
||||
*%(basename)s:10: SyntaxError: Identifier 'x' has already been declared
|
||||
let x;
|
||||
^
|
||||
SyntaxError: Identifier 'x' has already been declared
|
@ -1,10 +0,0 @@
|
||||
// Copyright 2015 the V8 project authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
//
|
||||
// Flags: --harmony-destructuring
|
||||
|
||||
try {
|
||||
} catch ({x}) {
|
||||
var x;
|
||||
}
|
@ -1,4 +0,0 @@
|
||||
*%(basename)s:9: SyntaxError: Identifier 'x' has already been declared
|
||||
var x;
|
||||
^
|
||||
SyntaxError: Identifier 'x' has already been declared
|
@ -1098,36 +1098,8 @@
|
||||
function(){ eval("(class{foo(a, {}) {'use strict';}});") }, SyntaxError);
|
||||
})();
|
||||
|
||||
|
||||
(function TestLegacyConstDestructuringInForLoop() {
|
||||
var result;
|
||||
for (const {foo} of [{foo: 1}]) { result = foo; }
|
||||
assertEquals(1, result);
|
||||
})();
|
||||
|
||||
|
||||
(function TestCatch() {
|
||||
"use strict";
|
||||
|
||||
// For testing proper scoping.
|
||||
var foo = "hello", bar = "world", baz = 42;
|
||||
|
||||
try {
|
||||
throw {foo: 1, bar: 2};
|
||||
} catch ({foo, bar, baz = 3}) {
|
||||
assertEquals(1, foo);
|
||||
assertEquals(2, bar);
|
||||
assertEquals(3, baz);
|
||||
}
|
||||
|
||||
try {
|
||||
throw [1, 2, 3];
|
||||
} catch ([foo, ...bar]) {
|
||||
assertEquals(1, foo);
|
||||
assertEquals([2, 3], bar);
|
||||
}
|
||||
|
||||
assertEquals("hello", foo);
|
||||
assertEquals("world", bar);
|
||||
assertEquals(42, baz);
|
||||
})();
|
||||
|
Loading…
Reference in New Issue
Block a user