Index: src/parser.cc |
diff --git a/src/parser.cc b/src/parser.cc |
index 1b177080bb3c0f7c50c983bd4a22f441faef33b6..5439a746185e02366709b9e88355771b3e5d482b 100644 |
--- a/src/parser.cc |
+++ b/src/parser.cc |
@@ -334,7 +334,8 @@ void Parser::SetCachedData(ParseInfo* info) { |
FunctionLiteral* Parser::DefaultConstructor(bool call_super, Scope* scope, |
- int pos, int end_pos) { |
+ int pos, int end_pos, |
+ LanguageMode language_mode) { |
int materialized_literal_count = -1; |
int expected_property_count = -1; |
int parameter_count = 0; |
@@ -345,7 +346,7 @@ FunctionLiteral* Parser::DefaultConstructor(bool call_super, Scope* scope, |
: FunctionKind::kDefaultBaseConstructor; |
Scope* function_scope = NewScope(scope, FUNCTION_SCOPE, kind); |
function_scope->SetLanguageMode( |
- static_cast<LanguageMode>(scope->language_mode() | STRICT_BIT)); |
+ static_cast<LanguageMode>(language_mode | STRICT_BIT)); |
// Set start and end position to the same value |
function_scope->set_start_position(pos); |
function_scope->set_end_position(pos); |
@@ -795,8 +796,9 @@ Expression* ParserTraits::NewTargetExpression(Scope* scope, |
Expression* ParserTraits::DefaultConstructor(bool call_super, Scope* scope, |
- int pos, int end_pos) { |
- return parser_->DefaultConstructor(call_super, scope, pos, end_pos); |
+ int pos, int end_pos, |
+ LanguageMode mode) { |
+ return parser_->DefaultConstructor(call_super, scope, pos, end_pos, mode); |
} |
@@ -873,10 +875,11 @@ FunctionLiteral* ParserTraits::ParseFunctionLiteral( |
const AstRawString* name, Scanner::Location function_name_location, |
FunctionNameValidity function_name_validity, FunctionKind kind, |
int function_token_position, FunctionLiteral::FunctionType type, |
- FunctionLiteral::ArityRestriction arity_restriction, bool* ok) { |
+ FunctionLiteral::ArityRestriction arity_restriction, |
+ LanguageMode language_mode, bool* ok) { |
return parser_->ParseFunctionLiteral( |
name, function_name_location, function_name_validity, kind, |
- function_token_position, type, arity_restriction, ok); |
+ function_token_position, type, arity_restriction, language_mode, ok); |
} |
@@ -1171,7 +1174,6 @@ FunctionLiteral* Parser::ParseLazy(Isolate* isolate, ParseInfo* info, |
DCHECK(is_sloppy(scope->language_mode()) || |
is_strict(info->language_mode())); |
DCHECK(info->language_mode() == shared_info->language_mode()); |
- scope->SetLanguageMode(shared_info->language_mode()); |
FunctionLiteral::FunctionType function_type = shared_info->is_expression() |
? (shared_info->is_anonymous() |
? FunctionLiteral::ANONYMOUS_EXPRESSION |
@@ -1182,6 +1184,7 @@ FunctionLiteral* Parser::ParseLazy(Isolate* isolate, ParseInfo* info, |
if (shared_info->is_arrow()) { |
Scope* scope = |
NewScope(scope_, ARROW_SCOPE, FunctionKind::kArrowFunction); |
+ scope->SetLanguageMode(shared_info->language_mode()); |
scope->set_start_position(shared_info->start_position()); |
ExpressionClassifier formals_classifier; |
ParserFormalParameterParsingState parsing_state(scope); |
@@ -1227,12 +1230,13 @@ FunctionLiteral* Parser::ParseLazy(Isolate* isolate, ParseInfo* info, |
} else if (shared_info->is_default_constructor()) { |
result = DefaultConstructor(IsSubclassConstructor(shared_info->kind()), |
scope, shared_info->start_position(), |
- shared_info->end_position()); |
+ shared_info->end_position(), |
+ shared_info->language_mode()); |
} else { |
- result = ParseFunctionLiteral(raw_name, Scanner::Location::invalid(), |
- kSkipFunctionNameCheck, shared_info->kind(), |
- RelocInfo::kNoPosition, function_type, |
- FunctionLiteral::NORMAL_ARITY, &ok); |
+ result = ParseFunctionLiteral( |
+ raw_name, Scanner::Location::invalid(), kSkipFunctionNameCheck, |
+ shared_info->kind(), RelocInfo::kNoPosition, function_type, |
+ FunctionLiteral::NORMAL_ARITY, shared_info->language_mode(), &ok); |
} |
// Make sure the results agree. |
DCHECK(ok == (result != NULL)); |
@@ -2195,14 +2199,14 @@ Statement* Parser::ParseFunctionDeclaration( |
bool is_strict_reserved = false; |
const AstRawString* name = ParseIdentifierOrStrictReservedWord( |
&is_strict_reserved, CHECK_OK); |
- FunctionLiteral* fun = |
- ParseFunctionLiteral(name, scanner()->location(), |
- is_strict_reserved ? kFunctionNameIsStrictReserved |
- : kFunctionNameValidityUnknown, |
- is_generator ? FunctionKind::kGeneratorFunction |
- : FunctionKind::kNormalFunction, |
- pos, FunctionLiteral::DECLARATION, |
- FunctionLiteral::NORMAL_ARITY, CHECK_OK); |
+ FunctionLiteral* fun = ParseFunctionLiteral( |
+ name, scanner()->location(), |
+ is_strict_reserved ? kFunctionNameIsStrictReserved |
+ : kFunctionNameValidityUnknown, |
+ is_generator ? FunctionKind::kGeneratorFunction |
+ : FunctionKind::kNormalFunction, |
+ pos, FunctionLiteral::DECLARATION, FunctionLiteral::NORMAL_ARITY, |
+ language_mode(), CHECK_OK); |
// Even if we're not at the top-level of the global or a function |
// scope, we treat it as such and introduce the function with its |
// initial value upon entering the corresponding scope. |
@@ -3920,7 +3924,8 @@ FunctionLiteral* Parser::ParseFunctionLiteral( |
const AstRawString* function_name, Scanner::Location function_name_location, |
FunctionNameValidity function_name_validity, FunctionKind kind, |
int function_token_pos, FunctionLiteral::FunctionType function_type, |
- FunctionLiteral::ArityRestriction arity_restriction, bool* ok) { |
+ FunctionLiteral::ArityRestriction arity_restriction, |
+ LanguageMode language_mode, bool* ok) { |
// Function :: |
// '(' FormalParameterList? ')' '{' FunctionBody '}' |
// |
@@ -3976,12 +3981,12 @@ FunctionLiteral* Parser::ParseFunctionLiteral( |
Scope* declaration_scope = scope_->DeclarationScope(); |
Scope* original_declaration_scope = original_scope_->DeclarationScope(); |
Scope* scope = function_type == FunctionLiteral::DECLARATION && |
- is_sloppy(language_mode()) && |
- !allow_harmony_sloppy() && |
+ is_sloppy(language_mode) && !allow_harmony_sloppy() && |
(original_scope_ == original_declaration_scope || |
declaration_scope != original_declaration_scope) |
? NewScope(declaration_scope, FUNCTION_SCOPE, kind) |
: NewScope(scope_, FUNCTION_SCOPE, kind); |
+ scope->SetLanguageMode(language_mode); |
ZoneList<Statement*>* body = NULL; |
int materialized_literal_count = -1; |
int expected_property_count = -1; |
@@ -4035,7 +4040,7 @@ FunctionLiteral* Parser::ParseFunctionLiteral( |
Variable* fvar = NULL; |
Token::Value fvar_init_op = Token::INIT_CONST_LEGACY; |
if (function_type == FunctionLiteral::NAMED_EXPRESSION) { |
- bool use_strict_const = is_strict(language_mode()) || |
+ bool use_strict_const = is_strict(language_mode) || |
(!allow_legacy_const() && allow_harmony_sloppy()); |
if (use_strict_const) { |
fvar_init_op = Token::INIT_CONST; |
@@ -4118,34 +4123,37 @@ FunctionLiteral* Parser::ParseFunctionLiteral( |
fvar_init_op, kind, CHECK_OK); |
materialized_literal_count = function_state.materialized_literal_count(); |
expected_property_count = function_state.expected_property_count(); |
+ } |
- if (is_strong(language_mode()) && IsSubclassConstructor(kind)) { |
- if (!function_state.super_location().IsValid()) { |
- ReportMessageAt(function_name_location, |
- MessageTemplate::kStrongSuperCallMissing, |
- kReferenceError); |
- *ok = false; |
- return nullptr; |
- } |
+ // Parsing the body may change the language mode in our scope. |
+ language_mode = scope->language_mode(); |
+ |
+ if (is_strong(language_mode) && IsSubclassConstructor(kind)) { |
+ if (!function_state.super_location().IsValid()) { |
+ ReportMessageAt(function_name_location, |
+ MessageTemplate::kStrongSuperCallMissing, |
+ kReferenceError); |
+ *ok = false; |
+ return nullptr; |
} |
} |
// Validate name and parameter names. We can do this only after parsing the |
// function, since the function can declare itself strict. |
- CheckFunctionName(language_mode(), function_name, function_name_validity, |
+ CheckFunctionName(language_mode, function_name, function_name_validity, |
function_name_location, CHECK_OK); |
const bool use_strict_params = |
!parsing_state.is_simple_parameter_list || IsConciseMethod(kind); |
const bool allow_duplicate_parameters = |
- is_sloppy(language_mode()) && !use_strict_params; |
- ValidateFormalParameters(&formals_classifier, language_mode(), |
+ is_sloppy(language_mode) && !use_strict_params; |
+ ValidateFormalParameters(&formals_classifier, language_mode, |
allow_duplicate_parameters, CHECK_OK); |
- if (is_strict(language_mode())) { |
+ if (is_strict(language_mode)) { |
CheckStrictOctalLiteral(scope->start_position(), scope->end_position(), |
CHECK_OK); |
} |
- if (is_strict(language_mode()) || allow_harmony_sloppy()) { |
+ if (is_strict(language_mode) || allow_harmony_sloppy()) { |
CheckConflictingVarDeclarations(scope, CHECK_OK); |
} |
} |
@@ -4534,8 +4542,8 @@ ClassLiteral* Parser::ParseClassLiteral(const AstRawString* name, |
int end_pos = scanner()->location().end_pos; |
if (constructor == NULL) { |
- constructor = |
- DefaultConstructor(extends != NULL, block_scope, pos, end_pos); |
+ constructor = DefaultConstructor(extends != NULL, block_scope, pos, end_pos, |
+ block_scope->language_mode()); |
} |
block_scope->set_end_position(end_pos); |