[es6] strict eval/arguments and strong undefined in AssignmentPattern
BUG=v8:4613 LOG=N R=adamk@chromium.org Review URL: https://codereview.chromium.org/1522693002 Cr-Commit-Position: refs/heads/master@{#32888}
This commit is contained in:
parent
291219dafa
commit
8f63710a3d
@ -1523,8 +1523,14 @@ typename ParserBase<Traits>::ExpressionT ParserBase<Traits>::ParseArrayLiteral(
|
||||
first_spread_index = values->length();
|
||||
}
|
||||
|
||||
CheckDestructuringElement(argument, classifier, start_pos,
|
||||
scanner()->location().end_pos);
|
||||
if (argument->IsAssignment()) {
|
||||
classifier->RecordPatternError(
|
||||
Scanner::Location(start_pos, scanner()->location().end_pos),
|
||||
MessageTemplate::kInvalidDestructuringTarget);
|
||||
} else {
|
||||
CheckDestructuringElement(argument, classifier, start_pos,
|
||||
scanner()->location().end_pos);
|
||||
}
|
||||
|
||||
if (peek() == Token::COMMA) {
|
||||
classifier->RecordPatternError(
|
||||
@ -1534,12 +1540,6 @@ typename ParserBase<Traits>::ExpressionT ParserBase<Traits>::ParseArrayLiteral(
|
||||
} else {
|
||||
elem = this->ParseAssignmentExpression(true, kIsPatternElement,
|
||||
classifier, CHECK_OK);
|
||||
if (!this->IsValidReferenceExpression(elem) &&
|
||||
!classifier->is_valid_assignment_pattern()) {
|
||||
classifier->RecordPatternError(
|
||||
Scanner::Location(pos, scanner()->location().end_pos),
|
||||
MessageTemplate::kInvalidDestructuringTarget);
|
||||
}
|
||||
}
|
||||
values->Add(elem, zone_);
|
||||
if (peek() != Token::RBRACK) {
|
||||
@ -1666,18 +1666,10 @@ ParserBase<Traits>::ParsePropertyDefinition(
|
||||
CHECK_OK_CUSTOM(EmptyObjectLiteralProperty));
|
||||
}
|
||||
Consume(Token::COLON);
|
||||
int pos = peek_position();
|
||||
value = this->ParseAssignmentExpression(
|
||||
true, kIsPatternElement, classifier,
|
||||
CHECK_OK_CUSTOM(EmptyObjectLiteralProperty));
|
||||
|
||||
if (!this->IsValidReferenceExpression(value) &&
|
||||
!classifier->is_valid_assignment_pattern()) {
|
||||
classifier->RecordPatternError(
|
||||
Scanner::Location(pos, scanner()->location().end_pos),
|
||||
MessageTemplate::kInvalidDestructuringTarget);
|
||||
}
|
||||
|
||||
return factory()->NewObjectLiteralProperty(name_expression, value, false,
|
||||
*is_computed_name);
|
||||
}
|
||||
@ -1710,6 +1702,7 @@ ParserBase<Traits>::ParsePropertyDefinition(
|
||||
|
||||
ExpressionT lhs = this->ExpressionFromIdentifier(
|
||||
name, next_beg_pos, next_end_pos, scope_, factory());
|
||||
CheckDestructuringElement(lhs, classifier, next_beg_pos, next_end_pos);
|
||||
|
||||
if (peek() == Token::ASSIGN) {
|
||||
Consume(Token::ASSIGN);
|
||||
@ -2045,16 +2038,12 @@ ParserBase<Traits>::ParseAssignmentExpression(bool accept_IN, int flags,
|
||||
|
||||
bool maybe_pattern =
|
||||
expression->IsObjectLiteral() || expression->IsArrayLiteral();
|
||||
// bool binding_pattern =
|
||||
// allow_harmony_destructuring_bind() && maybe_pattern && !is_rhs;
|
||||
|
||||
if (!Token::IsAssignmentOp(peek())) {
|
||||
// Parsed conditional expression only (no assignment).
|
||||
if (is_pattern_element && !this->IsValidReferenceExpression(expression) &&
|
||||
!maybe_pattern) {
|
||||
classifier->RecordPatternError(
|
||||
Scanner::Location(lhs_beg_pos, scanner()->location().end_pos),
|
||||
MessageTemplate::kInvalidDestructuringTarget);
|
||||
if (is_pattern_element) {
|
||||
CheckDestructuringElement(expression, classifier, lhs_beg_pos,
|
||||
scanner()->location().end_pos);
|
||||
} else if (is_rhs && maybe_pattern) {
|
||||
ValidateExpression(classifier, CHECK_OK);
|
||||
}
|
||||
@ -2077,6 +2066,10 @@ ParserBase<Traits>::ParseAssignmentExpression(bool accept_IN, int flags,
|
||||
classifier, expression, lhs_beg_pos, scanner()->location().end_pos,
|
||||
MessageTemplate::kInvalidLhsInAssignment);
|
||||
} else {
|
||||
if (is_pattern_element) {
|
||||
CheckDestructuringElement(expression, classifier, lhs_beg_pos,
|
||||
scanner()->location().end_pos);
|
||||
}
|
||||
expression = this->CheckAndRewriteReferenceExpression(
|
||||
expression, lhs_beg_pos, scanner()->location().end_pos,
|
||||
MessageTemplate::kInvalidLhsInAssignment, CHECK_OK);
|
||||
@ -3283,13 +3276,14 @@ void ParserBase<Traits>::CheckDestructuringElement(
|
||||
int end) {
|
||||
static const MessageTemplate::Template message =
|
||||
MessageTemplate::kInvalidDestructuringTarget;
|
||||
if (!this->IsAssignableIdentifier(expression)) {
|
||||
const Scanner::Location location(begin, end);
|
||||
const Scanner::Location location(begin, end);
|
||||
if (expression->IsArrayLiteral() || expression->IsObjectLiteral() ||
|
||||
expression->IsAssignment())
|
||||
return;
|
||||
if (expression->IsProperty()) {
|
||||
classifier->RecordBindingPatternError(location, message);
|
||||
if (!expression->IsProperty() &&
|
||||
!(expression->IsObjectLiteral() || expression->IsArrayLiteral())) {
|
||||
classifier->RecordAssignmentPatternError(location, message);
|
||||
}
|
||||
} else if (!this->IsAssignableIdentifier(expression)) {
|
||||
classifier->RecordPatternError(location, message);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -125,9 +125,9 @@ class PreParserExpression {
|
||||
right->IsSpreadExpression()));
|
||||
}
|
||||
|
||||
static PreParserExpression AssignmentPattern() {
|
||||
static PreParserExpression Assignment() {
|
||||
return PreParserExpression(TypeField::encode(kExpression) |
|
||||
ExpressionTypeField::encode(kAssignmentPattern));
|
||||
ExpressionTypeField::encode(kAssignment));
|
||||
}
|
||||
|
||||
static PreParserExpression ObjectLiteral() {
|
||||
@ -195,9 +195,9 @@ class PreParserExpression {
|
||||
return PreParserIdentifier(IdentifierTypeField::decode(code_));
|
||||
}
|
||||
|
||||
bool IsAssignmentPattern() const {
|
||||
bool IsAssignment() const {
|
||||
return TypeField::decode(code_) == kExpression &&
|
||||
ExpressionTypeField::decode(code_) == kAssignmentPattern;
|
||||
ExpressionTypeField::decode(code_) == kAssignment;
|
||||
}
|
||||
|
||||
bool IsObjectLiteral() const {
|
||||
@ -308,7 +308,7 @@ class PreParserExpression {
|
||||
kCallExpression,
|
||||
kSuperCallReference,
|
||||
kNoTemplateTagExpression,
|
||||
kAssignmentPattern
|
||||
kAssignment
|
||||
};
|
||||
|
||||
explicit PreParserExpression(uint32_t expression_code)
|
||||
@ -498,12 +498,7 @@ class PreParserFactory {
|
||||
PreParserExpression left,
|
||||
PreParserExpression right,
|
||||
int pos) {
|
||||
return PreParserExpression::Default();
|
||||
}
|
||||
PreParserExpression NewAssignmentPattern(PreParserExpression pattern,
|
||||
int pos) {
|
||||
DCHECK(pattern->IsObjectLiteral() || pattern->IsArrayLiteral());
|
||||
return PreParserExpression::AssignmentPattern();
|
||||
return PreParserExpression::Assignment();
|
||||
}
|
||||
PreParserExpression NewYield(PreParserExpression generator_object,
|
||||
PreParserExpression expression,
|
||||
|
@ -7071,6 +7071,27 @@ TEST(DestructuringAssignmentNegativeTests) {
|
||||
};
|
||||
RunParserSyncTest(empty_context_data, ambiguity_data, kError, NULL, 0,
|
||||
always_flags, arraysize(always_flags));
|
||||
|
||||
// Strict mode errors
|
||||
const char* strict_context_data[][2] = {{"'use strict'; ", " = {}"},
|
||||
{"'use strict'; for (", " of {}) {}"},
|
||||
{"'use strict'; for (", " in {}) {}"},
|
||||
{NULL, NULL}};
|
||||
const char* strict_data[] = {"{ eval }",
|
||||
"{ arguments }",
|
||||
"{ foo: eval }",
|
||||
"{ foo: arguments }",
|
||||
"{ eval = 0 }",
|
||||
"{ arguments = 0 }",
|
||||
"{ foo: eval = 0 }",
|
||||
"{ foo: arguments = 0 }",
|
||||
"[ eval ]",
|
||||
"[ arguments ]",
|
||||
"[ eval = 0 ]",
|
||||
"[ arguments = 0 ]",
|
||||
NULL};
|
||||
RunParserSyncTest(strict_context_data, strict_data, kError, NULL, 0,
|
||||
always_flags, arraysize(always_flags));
|
||||
}
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user