| OLD | NEW | 
|     1 // Copyright 2012 the V8 project authors. All rights reserved. |     1 // Copyright 2012 the V8 project authors. All rights reserved. | 
|     2 // Use of this source code is governed by a BSD-style license that can be |     2 // Use of this source code is governed by a BSD-style license that can be | 
|     3 // found in the LICENSE file. |     3 // found in the LICENSE file. | 
|     4  |     4  | 
|     5 #include "src/parsing/parser.h" |     5 #include "src/parsing/parser.h" | 
|     6  |     6  | 
|     7 #include <memory> |     7 #include <memory> | 
|     8  |     8  | 
|     9 #include "src/api.h" |     9 #include "src/api.h" | 
|    10 #include "src/ast/ast-expression-rewriter.h" |    10 #include "src/ast/ast-expression-rewriter.h" | 
| (...skipping 1486 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1497   // other functions are set up when entering the surrounding scope. |  1497   // other functions are set up when entering the surrounding scope. | 
|  1498   Declaration* decl = DeclareVariable(name, VAR, pos, CHECK_OK); |  1498   Declaration* decl = DeclareVariable(name, VAR, pos, CHECK_OK); | 
|  1499   NativeFunctionLiteral* lit = |  1499   NativeFunctionLiteral* lit = | 
|  1500       factory()->NewNativeFunctionLiteral(name, extension_, kNoSourcePosition); |  1500       factory()->NewNativeFunctionLiteral(name, extension_, kNoSourcePosition); | 
|  1501   return factory()->NewExpressionStatement( |  1501   return factory()->NewExpressionStatement( | 
|  1502       factory()->NewAssignment(Token::INIT, decl->proxy(), lit, |  1502       factory()->NewAssignment(Token::INIT, decl->proxy(), lit, | 
|  1503                                kNoSourcePosition), |  1503                                kNoSourcePosition), | 
|  1504       pos); |  1504       pos); | 
|  1505 } |  1505 } | 
|  1506  |  1506  | 
|  1507 Statement* Parser::ParseHoistableDeclaration( |  | 
|  1508     ZoneList<const AstRawString*>* names, bool default_export, bool* ok) { |  | 
|  1509   Expect(Token::FUNCTION, CHECK_OK); |  | 
|  1510   int pos = position(); |  | 
|  1511   ParseFunctionFlags flags = ParseFunctionFlags::kIsNormal; |  | 
|  1512   if (Check(Token::MUL)) { |  | 
|  1513     flags |= ParseFunctionFlags::kIsGenerator; |  | 
|  1514   } |  | 
|  1515   return ParseHoistableDeclaration(pos, flags, names, default_export, ok); |  | 
|  1516 } |  | 
|  1517  |  | 
|  1518 Statement* Parser::ParseAsyncFunctionDeclaration( |  1507 Statement* Parser::ParseAsyncFunctionDeclaration( | 
|  1519     ZoneList<const AstRawString*>* names, bool default_export, bool* ok) { |  1508     ZoneList<const AstRawString*>* names, bool default_export, bool* ok) { | 
|  1520   DCHECK_EQ(scanner()->current_token(), Token::ASYNC); |  1509   DCHECK_EQ(scanner()->current_token(), Token::ASYNC); | 
|  1521   int pos = position(); |  1510   int pos = position(); | 
|  1522   if (scanner()->HasAnyLineTerminatorBeforeNext()) { |  1511   if (scanner()->HasAnyLineTerminatorBeforeNext()) { | 
|  1523     *ok = false; |  1512     *ok = false; | 
|  1524     ReportUnexpectedToken(scanner()->current_token()); |  1513     ReportUnexpectedToken(scanner()->current_token()); | 
|  1525     return nullptr; |  1514     return nullptr; | 
|  1526   } |  1515   } | 
|  1527   Expect(Token::FUNCTION, CHECK_OK); |  1516   Expect(Token::FUNCTION, CHECK_OK); | 
|  1528   ParseFunctionFlags flags = ParseFunctionFlags::kIsAsync; |  1517   ParseFunctionFlags flags = ParseFunctionFlags::kIsAsync; | 
|  1529   return ParseHoistableDeclaration(pos, flags, names, default_export, ok); |  1518   return ParseHoistableDeclaration(pos, flags, names, default_export, ok); | 
|  1530 } |  1519 } | 
|  1531  |  1520  | 
|  1532 Statement* Parser::ParseHoistableDeclaration( |  | 
|  1533     int pos, ParseFunctionFlags flags, ZoneList<const AstRawString*>* names, |  | 
|  1534     bool default_export, bool* ok) { |  | 
|  1535   // FunctionDeclaration :: |  | 
|  1536   //   'function' Identifier '(' FormalParameters ')' '{' FunctionBody '}' |  | 
|  1537   //   'function' '(' FormalParameters ')' '{' FunctionBody '}' |  | 
|  1538   // GeneratorDeclaration :: |  | 
|  1539   //   'function' '*' Identifier '(' FormalParameters ')' '{' FunctionBody '}' |  | 
|  1540   //   'function' '*' '(' FormalParameters ')' '{' FunctionBody '}' |  | 
|  1541   // |  | 
|  1542   // The anonymous forms are allowed iff [default_export] is true. |  | 
|  1543   // |  | 
|  1544   // 'function' and '*' (if present) have been consumed by the caller. |  | 
|  1545  |  | 
|  1546   const bool is_generator = flags & ParseFunctionFlags::kIsGenerator; |  | 
|  1547   const bool is_async = flags & ParseFunctionFlags::kIsAsync; |  | 
|  1548   DCHECK(!is_generator || !is_async); |  | 
|  1549  |  | 
|  1550   const AstRawString* name; |  | 
|  1551   FunctionNameValidity name_validity; |  | 
|  1552   const AstRawString* variable_name; |  | 
|  1553   if (default_export && peek() == Token::LPAREN) { |  | 
|  1554     name = ast_value_factory()->default_string(); |  | 
|  1555     name_validity = kSkipFunctionNameCheck; |  | 
|  1556     variable_name = ast_value_factory()->star_default_star_string(); |  | 
|  1557   } else { |  | 
|  1558     bool is_strict_reserved; |  | 
|  1559     name = ParseIdentifierOrStrictReservedWord(&is_strict_reserved, CHECK_OK); |  | 
|  1560     name_validity = is_strict_reserved ? kFunctionNameIsStrictReserved |  | 
|  1561                                        : kFunctionNameValidityUnknown; |  | 
|  1562     variable_name = name; |  | 
|  1563   } |  | 
|  1564  |  | 
|  1565   FuncNameInferrer::State fni_state(fni_); |  | 
|  1566   DCHECK_NOT_NULL(fni_); |  | 
|  1567   fni_->PushEnclosingName(name); |  | 
|  1568   FunctionLiteral* fun = ParseFunctionLiteral( |  | 
|  1569       name, scanner()->location(), name_validity, |  | 
|  1570       is_generator ? FunctionKind::kGeneratorFunction |  | 
|  1571                    : is_async ? FunctionKind::kAsyncFunction |  | 
|  1572                               : FunctionKind::kNormalFunction, |  | 
|  1573       pos, FunctionLiteral::kDeclaration, language_mode(), CHECK_OK); |  | 
|  1574  |  | 
|  1575   // In ES6, a function behaves as a lexical binding, except in |  | 
|  1576   // a script scope, or the initial scope of eval or another function. |  | 
|  1577   VariableMode mode = |  | 
|  1578       (!scope()->is_declaration_scope() || scope()->is_module_scope()) ? LET |  | 
|  1579                                                                        : VAR; |  | 
|  1580   VariableProxy* proxy = NewUnresolved(variable_name); |  | 
|  1581   Declaration* declaration = |  | 
|  1582       factory()->NewFunctionDeclaration(proxy, fun, scope(), pos); |  | 
|  1583   Declare(declaration, DeclarationDescriptor::NORMAL, mode, kCreatedInitialized, |  | 
|  1584           CHECK_OK); |  | 
|  1585   if (names) names->Add(variable_name, zone()); |  | 
|  1586   // Async functions don't undergo sloppy mode block scoped hoisting, and don't |  | 
|  1587   // allow duplicates in a block. Both are represented by the |  | 
|  1588   // sloppy_block_function_map. Don't add them to the map for async functions. |  | 
|  1589   // Generators are also supposed to be prohibited; currently doing this behind |  | 
|  1590   // a flag and UseCounting violations to assess web compatibility. |  | 
|  1591   if (is_sloppy(language_mode()) && !scope()->is_declaration_scope() && |  | 
|  1592       !is_async && !(allow_harmony_restrictive_generators() && is_generator)) { |  | 
|  1593     SloppyBlockFunctionStatement* delegate = |  | 
|  1594         factory()->NewSloppyBlockFunctionStatement(scope()); |  | 
|  1595     DeclarationScope* target_scope = GetDeclarationScope(); |  | 
|  1596     target_scope->DeclareSloppyBlockFunction(variable_name, delegate); |  | 
|  1597     return delegate; |  | 
|  1598   } |  | 
|  1599   return factory()->NewEmptyStatement(kNoSourcePosition); |  | 
|  1600 } |  | 
|  1601  |  | 
|  1602 Statement* Parser::ParseClassDeclaration(ZoneList<const AstRawString*>* names, |  1521 Statement* Parser::ParseClassDeclaration(ZoneList<const AstRawString*>* names, | 
|  1603                                          bool default_export, bool* ok) { |  1522                                          bool default_export, bool* ok) { | 
|  1604   // ClassDeclaration :: |  1523   // ClassDeclaration :: | 
|  1605   //   'class' Identifier ('extends' LeftHandExpression)? '{' ClassBody '}' |  1524   //   'class' Identifier ('extends' LeftHandExpression)? '{' ClassBody '}' | 
|  1606   //   'class' ('extends' LeftHandExpression)? '{' ClassBody '}' |  1525   //   'class' ('extends' LeftHandExpression)? '{' ClassBody '}' | 
|  1607   // |  1526   // | 
|  1608   // The anonymous form is allowed iff [default_export] is true. |  1527   // The anonymous form is allowed iff [default_export] is true. | 
|  1609   // |  1528   // | 
|  1610   // 'class' is expected to be consumed by the caller. |  1529   // 'class' is expected to be consumed by the caller. | 
|  1611   // |  1530   // | 
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1662  |  1581  | 
|  1663 void Parser::DeclareAndInitializeVariables( |  1582 void Parser::DeclareAndInitializeVariables( | 
|  1664     Block* block, const DeclarationDescriptor* declaration_descriptor, |  1583     Block* block, const DeclarationDescriptor* declaration_descriptor, | 
|  1665     const DeclarationParsingResult::Declaration* declaration, |  1584     const DeclarationParsingResult::Declaration* declaration, | 
|  1666     ZoneList<const AstRawString*>* names, bool* ok) { |  1585     ZoneList<const AstRawString*>* names, bool* ok) { | 
|  1667   DCHECK_NOT_NULL(block); |  1586   DCHECK_NOT_NULL(block); | 
|  1668   PatternRewriter::DeclareAndInitializeVariables( |  1587   PatternRewriter::DeclareAndInitializeVariables( | 
|  1669       this, block, declaration_descriptor, declaration, names, ok); |  1588       this, block, declaration_descriptor, declaration, names, ok); | 
|  1670 } |  1589 } | 
|  1671  |  1590  | 
 |  1591 Statement* Parser::DeclareFunction(const AstRawString* variable_name, | 
 |  1592                                    FunctionLiteral* function, int pos, | 
 |  1593                                    bool is_generator, bool is_async, | 
 |  1594                                    ZoneList<const AstRawString*>* names, | 
 |  1595                                    bool* ok) { | 
 |  1596   // In ES6, a function behaves as a lexical binding, except in | 
 |  1597   // a script scope, or the initial scope of eval or another function. | 
 |  1598   VariableMode mode = | 
 |  1599       (!scope()->is_declaration_scope() || scope()->is_module_scope()) ? LET | 
 |  1600                                                                        : VAR; | 
 |  1601   VariableProxy* proxy = NewUnresolved(variable_name); | 
 |  1602   Declaration* declaration = | 
 |  1603       factory()->NewFunctionDeclaration(proxy, function, scope(), pos); | 
 |  1604   Declare(declaration, DeclarationDescriptor::NORMAL, mode, kCreatedInitialized, | 
 |  1605           CHECK_OK); | 
 |  1606   if (names) names->Add(variable_name, zone()); | 
 |  1607   // Async functions don't undergo sloppy mode block scoped hoisting, and don't | 
 |  1608   // allow duplicates in a block. Both are represented by the | 
 |  1609   // sloppy_block_function_map. Don't add them to the map for async functions. | 
 |  1610   // Generators are also supposed to be prohibited; currently doing this behind | 
 |  1611   // a flag and UseCounting violations to assess web compatibility. | 
 |  1612   if (is_sloppy(language_mode()) && !scope()->is_declaration_scope() && | 
 |  1613       !is_async && !(allow_harmony_restrictive_generators() && is_generator)) { | 
 |  1614     SloppyBlockFunctionStatement* delegate = | 
 |  1615         factory()->NewSloppyBlockFunctionStatement(scope()); | 
 |  1616     DeclarationScope* target_scope = GetDeclarationScope(); | 
 |  1617     target_scope->DeclareSloppyBlockFunction(variable_name, delegate); | 
 |  1618     return delegate; | 
 |  1619   } | 
 |  1620   return factory()->NewEmptyStatement(kNoSourcePosition); | 
 |  1621 } | 
 |  1622  | 
|  1672 static bool ContainsLabel(ZoneList<const AstRawString*>* labels, |  1623 static bool ContainsLabel(ZoneList<const AstRawString*>* labels, | 
|  1673                           const AstRawString* label) { |  1624                           const AstRawString* label) { | 
|  1674   DCHECK(label != NULL); |  1625   DCHECK(label != NULL); | 
|  1675   if (labels != NULL) { |  1626   if (labels != NULL) { | 
|  1676     for (int i = labels->length(); i-- > 0; ) { |  1627     for (int i = labels->length(); i-- > 0; ) { | 
|  1677       if (labels->at(i) == label) { |  1628       if (labels->at(i) == label) { | 
|  1678         return true; |  1629         return true; | 
|  1679       } |  1630       } | 
|  1680     } |  1631     } | 
|  1681   } |  1632   } | 
| (...skipping 4342 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  6024   node->Print(Isolate::Current()); |  5975   node->Print(Isolate::Current()); | 
|  6025 } |  5976 } | 
|  6026 #endif  // DEBUG |  5977 #endif  // DEBUG | 
|  6027  |  5978  | 
|  6028 #undef CHECK_OK |  5979 #undef CHECK_OK | 
|  6029 #undef CHECK_OK_VOID |  5980 #undef CHECK_OK_VOID | 
|  6030 #undef CHECK_FAILED |  5981 #undef CHECK_FAILED | 
|  6031  |  5982  | 
|  6032 }  // namespace internal |  5983 }  // namespace internal | 
|  6033 }  // namespace v8 |  5984 }  // namespace v8 | 
| OLD | NEW |