Index: src/preparser.cc |
diff --git a/src/preparser.cc b/src/preparser.cc |
index 1685724fe4482780d2ae64e820ce3773f894dcb9..daec9bfb25f3bfafd80a12a92289257569d9615d 100644 |
--- a/src/preparser.cc |
+++ b/src/preparser.cc |
@@ -235,6 +235,11 @@ PreParser::Statement PreParser::ParseStatement(bool* ok) { |
// Statement :: |
// EmptyStatement |
// ... |
+ |
+ if (peek() == Token::SEMICOLON) { |
+ Next(); |
+ return Statement::Default(); |
+ } |
return ParseSubStatement(ok); |
} |
@@ -395,15 +400,16 @@ PreParser::Statement PreParser::ParseBlock(bool* ok) { |
// (ECMA-262, 3rd, 12.2) |
// |
Expect(Token::LBRACE, CHECK_OK); |
+ Statement final = Statement::Default(); |
while (peek() != Token::RBRACE) { |
if (is_strict(language_mode())) { |
- ParseStatementListItem(CHECK_OK); |
+ final = ParseStatementListItem(CHECK_OK); |
} else { |
- ParseStatement(CHECK_OK); |
+ final = ParseStatement(CHECK_OK); |
} |
} |
Expect(Token::RBRACE, ok); |
- return Statement::Default(); |
+ return final; |
} |
@@ -545,7 +551,8 @@ PreParser::Statement PreParser::ParseExpressionOrLabelledStatement(bool* ok) { |
DCHECK(is_sloppy(language_mode()) || |
!IsFutureStrictReserved(expr.AsIdentifier())); |
Consume(Token::COLON); |
- return ParseStatement(ok); |
+ Statement statement = ParseStatement(ok); |
+ return statement.IsJumpStatement() ? Statement::Default() : statement; |
// Preparsing is disabled for extensions (because the extension details |
// aren't passed to lazily compiled functions), so we don't |
// accept "native function" in the preparser. |
@@ -571,12 +578,16 @@ PreParser::Statement PreParser::ParseIfStatement(bool* ok) { |
Expect(Token::LPAREN, CHECK_OK); |
ParseExpression(true, CHECK_OK); |
Expect(Token::RPAREN, CHECK_OK); |
- ParseSubStatement(CHECK_OK); |
+ Statement stat = ParseSubStatement(CHECK_OK); |
if (peek() == Token::ELSE) { |
Next(); |
- ParseSubStatement(CHECK_OK); |
+ Statement else_stat = ParseSubStatement(CHECK_OK); |
+ stat = (stat.IsJumpStatement() && else_stat.IsJumpStatement()) ? |
+ Statement::Jump() : Statement::Default(); |
+ } else { |
+ stat = Statement::Default(); |
} |
- return Statement::Default(); |
+ return stat; |
} |
@@ -594,7 +605,7 @@ PreParser::Statement PreParser::ParseContinueStatement(bool* ok) { |
ParseIdentifier(kAllowRestrictedIdentifiers, CHECK_OK); |
} |
ExpectSemicolon(CHECK_OK); |
- return Statement::Default(); |
+ return Statement::Jump(); |
} |
@@ -612,7 +623,7 @@ PreParser::Statement PreParser::ParseBreakStatement(bool* ok) { |
ParseIdentifier(kAllowRestrictedIdentifiers, CHECK_OK); |
} |
ExpectSemicolon(CHECK_OK); |
- return Statement::Default(); |
+ return Statement::Jump(); |
} |
@@ -647,7 +658,7 @@ PreParser::Statement PreParser::ParseReturnStatement(bool* ok) { |
ParseExpression(true, CHECK_OK); |
} |
ExpectSemicolon(CHECK_OK); |
- return Statement::Default(); |
+ return Statement::Jump(); |
} |
@@ -691,12 +702,19 @@ PreParser::Statement PreParser::ParseSwitchStatement(bool* ok) { |
} |
Expect(Token::COLON, CHECK_OK); |
token = peek(); |
+ Statement statement = Statement::Jump(); |
while (token != Token::CASE && |
token != Token::DEFAULT && |
token != Token::RBRACE) { |
- ParseStatementListItem(CHECK_OK); |
+ statement = ParseStatementListItem(CHECK_OK); |
token = peek(); |
} |
+ if (is_strong(language_mode()) && !statement.IsJumpStatement() && |
+ token != Token::RBRACE) { |
+ ReportMessageAt(scanner()->location(), "strong_switch_fallthrough"); |
+ *ok = false; |
+ return Statement::Default(); |
+ } |
} |
Expect(Token::RBRACE, ok); |
return Statement::Default(); |
@@ -827,7 +845,7 @@ PreParser::Statement PreParser::ParseThrowStatement(bool* ok) { |
} |
ParseExpression(true, CHECK_OK); |
ExpectSemicolon(ok); |
- return Statement::Default(); |
+ return Statement::Jump(); |
} |