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

Unified Diff: src/parser.cc

Issue 1070633002: [strong] Implement static restrictions on binding/assignment to 'undefined' identifier. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: rebase Created 5 years, 8 months 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
« no previous file with comments | « src/parser.h ('k') | src/preparser.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/parser.cc
diff --git a/src/parser.cc b/src/parser.cc
index fc4138d18621260079dc4a5b7263e68155b1982a..285ddf3e99912cada84107be77297eea7c85dc79 100644
--- a/src/parser.cc
+++ b/src/parser.cc
@@ -465,6 +465,9 @@ bool ParserTraits::IsEvalOrArguments(const AstRawString* identifier) const {
return IsEval(identifier) || IsArguments(identifier);
}
+bool ParserTraits::IsUndefined(const AstRawString* identifier) const {
+ return identifier == parser_->ast_value_factory()->undefined_string();
+}
bool ParserTraits::IsPrototype(const AstRawString* identifier) const {
return identifier == parser_->ast_value_factory()->prototype_string();
@@ -1476,6 +1479,10 @@ ZoneList<ImportDeclaration*>* Parser::ParseNamedImports(int pos, bool* ok) {
*ok = false;
ReportMessage("strict_eval_arguments");
return NULL;
+ } else if (is_strong(language_mode()) && IsUndefined(local_name)) {
+ *ok = false;
+ ReportMessage("strong_undefined");
+ return NULL;
}
VariableProxy* proxy = NewUnresolved(local_name, IMPORT);
ImportDeclaration* declaration =
@@ -1525,7 +1532,7 @@ Statement* Parser::ParseImportDeclaration(bool* ok) {
ImportDeclaration* import_default_declaration = NULL;
if (tok != Token::MUL && tok != Token::LBRACE) {
const AstRawString* local_name =
- ParseIdentifier(kDontAllowEvalOrArguments, CHECK_OK);
+ ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK);
VariableProxy* proxy = NewUnresolved(local_name, IMPORT);
import_default_declaration = factory()->NewImportDeclaration(
proxy, ast_value_factory()->default_string(), NULL, scope_, pos);
@@ -1540,7 +1547,7 @@ Statement* Parser::ParseImportDeclaration(bool* ok) {
Consume(Token::MUL);
ExpectContextualKeyword(CStrVector("as"), CHECK_OK);
module_instance_binding =
- ParseIdentifier(kDontAllowEvalOrArguments, CHECK_OK);
+ ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK);
// TODO(ES6): Add an appropriate declaration.
break;
}
@@ -2033,11 +2040,12 @@ Statement* Parser::ParseNativeDeclaration(bool* ok) {
int pos = peek_position();
Expect(Token::FUNCTION, CHECK_OK);
// Allow "eval" or "arguments" for backward compatibility.
- const AstRawString* name = ParseIdentifier(kAllowEvalOrArguments, CHECK_OK);
+ const AstRawString* name =
+ ParseIdentifier(kAllowRestrictedIdentifiers, CHECK_OK);
Expect(Token::LPAREN, CHECK_OK);
bool done = (peek() == Token::RPAREN);
while (!done) {
- ParseIdentifier(kAllowEvalOrArguments, CHECK_OK);
+ ParseIdentifier(kAllowRestrictedIdentifiers, CHECK_OK);
done = (peek() == Token::RPAREN);
if (!done) {
Expect(Token::COMMA, CHECK_OK);
@@ -2319,7 +2327,7 @@ Block* Parser::ParseVariableDeclarations(
// Parse variable name.
if (nvars > 0) Consume(Token::COMMA);
- name = ParseIdentifier(kDontAllowEvalOrArguments, CHECK_OK);
+ name = ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK);
if (!first_name) first_name = name;
Scanner::Location variable_loc = scanner()->location();
if (fni_ != NULL) fni_->PushVariableName(name);
@@ -2671,7 +2679,7 @@ Statement* Parser::ParseContinueStatement(bool* ok) {
if (!scanner()->HasAnyLineTerminatorBeforeNext() &&
tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) {
// ECMA allows "eval" or "arguments" as labels even in strict mode.
- label = ParseIdentifier(kAllowEvalOrArguments, CHECK_OK);
+ label = ParseIdentifier(kAllowRestrictedIdentifiers, CHECK_OK);
}
IterationStatement* target = LookupContinueTarget(label, CHECK_OK);
if (target == NULL) {
@@ -2701,7 +2709,7 @@ Statement* Parser::ParseBreakStatement(ZoneList<const AstRawString*>* labels,
if (!scanner()->HasAnyLineTerminatorBeforeNext() &&
tok != Token::SEMICOLON && tok != Token::RBRACE && tok != Token::EOS) {
// ECMA allows "eval" or "arguments" as labels even in strict mode.
- label = ParseIdentifier(kAllowEvalOrArguments, CHECK_OK);
+ label = ParseIdentifier(kAllowRestrictedIdentifiers, CHECK_OK);
}
// Parse labeled break statements that target themselves into
// empty statements, e.g. 'l1: l2: l3: break l2;'
@@ -2926,7 +2934,7 @@ TryStatement* Parser::ParseTryStatement(bool* ok) {
Expect(Token::LPAREN, CHECK_OK);
catch_scope = NewScope(scope_, CATCH_SCOPE);
catch_scope->set_start_position(scanner()->location().beg_pos);
- name = ParseIdentifier(kDontAllowEvalOrArguments, CHECK_OK);
+ name = ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK);
Expect(Token::RPAREN, CHECK_OK);
@@ -3873,6 +3881,9 @@ FunctionLiteral* Parser::ParseFunctionLiteral(
Scanner::Location dupe_error_loc = Scanner::Location::invalid();
Scanner::Location reserved_error_loc = Scanner::Location::invalid();
+ // Similarly for strong mode.
+ Scanner::Location undefined_error_loc = Scanner::Location::invalid();
+
bool is_rest = false;
bool done = arity_restriction == FunctionLiteral::GETTER_ARITY ||
(peek() == Token::RPAREN &&
@@ -3891,6 +3902,9 @@ FunctionLiteral* Parser::ParseFunctionLiteral(
if (!eval_args_error_loc.IsValid() && IsEvalOrArguments(param_name)) {
eval_args_error_loc = scanner()->location();
}
+ if (!undefined_error_loc.IsValid() && IsUndefined(param_name)) {
+ undefined_error_loc = scanner()->location();
+ }
if (!reserved_error_loc.IsValid() && is_strict_reserved) {
reserved_error_loc = scanner()->location();
}
@@ -4009,8 +4023,8 @@ FunctionLiteral* Parser::ParseFunctionLiteral(
CHECK_OK);
const bool use_strict_params = is_rest || IsConciseMethod(kind);
CheckFunctionParameterNames(language_mode(), use_strict_params,
- eval_args_error_loc, dupe_error_loc,
- reserved_error_loc, CHECK_OK);
+ eval_args_error_loc, undefined_error_loc,
+ dupe_error_loc, reserved_error_loc, CHECK_OK);
if (is_strict(language_mode())) {
CheckStrictOctalLiteral(scope->start_position(), scope->end_position(),
@@ -4264,6 +4278,11 @@ ClassLiteral* Parser::ParseClassLiteral(const AstRawString* name,
*ok = false;
return NULL;
}
+ if (is_strong(language_mode()) && IsUndefined(name)) {
+ ReportMessageAt(class_name_location, "strong_undefined");
+ *ok = false;
+ return NULL;
+ }
// Create a block scope which is additionally tagged as class scope; this is
// important for resolving variable references to the class name in the strong
@@ -4355,7 +4374,8 @@ Expression* Parser::ParseV8Intrinsic(bool* ok) {
int pos = peek_position();
Expect(Token::MOD, CHECK_OK);
// Allow "eval" or "arguments" for backward compatibility.
- const AstRawString* name = ParseIdentifier(kAllowEvalOrArguments, CHECK_OK);
+ const AstRawString* name = ParseIdentifier(kAllowRestrictedIdentifiers,
+ CHECK_OK);
Scanner::Location spread_pos;
ZoneList<Expression*>* args = ParseArguments(&spread_pos, CHECK_OK);
« no previous file with comments | « src/parser.h ('k') | src/preparser.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698