Changeset 188355 in webkit
- Timestamp:
- Aug 12, 2015, 1:38:45 PM (10 years ago)
- Location:
- trunk/Source/JavaScriptCore
- Files:
-
- 5 added
- 18 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/JavaScriptCore/CMakeLists.txt
r188329 r188355 386 386 387 387 parser/Lexer.cpp 388 parser/ModuleAnalyzer.cpp 389 parser/ModuleRecord.cpp 388 390 parser/Nodes.cpp 391 parser/NodesAnalyzeModule.cpp 389 392 parser/Parser.cpp 390 393 parser/ParserArena.cpp -
trunk/Source/JavaScriptCore/ChangeLog
r188351 r188355 1 2015-08-12 Yusuke Suzuki <[email protected]> 2 3 [ES6] Add ES6 Modules preparsing phase to collect the dependencies 4 https://bugs.webkit.org/show_bug.cgi?id=147353 5 6 Reviewed by Geoffrey Garen. 7 8 This patch implements ModuleRecord and ModuleAnalyzer. 9 ModuleAnalyzer analyzes the produced AST from the parser. 10 By collaborating with the parser, ModuleAnalyzer collects the information 11 that is necessary to request the loading for the dependent modules and 12 construct module's environment and namespace object before executing the actual 13 module body. 14 15 In the parser, we annotate which variable is imported binding and which variable 16 is exported from the current module. This information is leveraged in the ModuleAnalyzer 17 to categorize the export entries. 18 19 To preparse the modules in the parser, we just add the new flag `ModuleParseMode` 20 instead of introducing a new TreeContext type. This is because only 2 users use the 21 parseModuleSourceElements; preparser and actual compiler. Adding the flag is simple 22 enough to switch the context to the SyntaxChecker when parsing the non-module related 23 statement in the preparsing phase. 24 25 To demonstrate the module analyzer, we added the new option dumpModuleRecord option 26 into the JSC shell. By specifying this, the result of analysis is dumped when the module 27 is parsed and analyzed. 28 29 * CMakeLists.txt: 30 * JavaScriptCore.vcxproj/JavaScriptCore.vcxproj: 31 * JavaScriptCore.vcxproj/JavaScriptCore.vcxproj.filters: 32 * JavaScriptCore.xcodeproj/project.pbxproj: 33 * builtins/BuiltinNames.h: 34 * parser/ASTBuilder.h: 35 (JSC::ASTBuilder::createExportDefaultDeclaration): 36 * parser/ModuleAnalyzer.cpp: Added. 37 (JSC::ModuleAnalyzer::ModuleAnalyzer): 38 (JSC::ModuleAnalyzer::exportedBinding): 39 (JSC::ModuleAnalyzer::declareExportAlias): 40 (JSC::ModuleAnalyzer::exportVariable): 41 (JSC::ModuleAnalyzer::analyze): 42 * parser/ModuleAnalyzer.h: Added. 43 (JSC::ModuleAnalyzer::vm): 44 (JSC::ModuleAnalyzer::moduleRecord): 45 * parser/ModuleRecord.cpp: Added. 46 (JSC::printableName): 47 (JSC::ModuleRecord::dump): 48 * parser/ModuleRecord.h: Added. 49 (JSC::ModuleRecord::ImportEntry::isNamespace): 50 (JSC::ModuleRecord::create): 51 (JSC::ModuleRecord::appendRequestedModule): 52 (JSC::ModuleRecord::addImportEntry): 53 (JSC::ModuleRecord::addExportEntry): 54 (JSC::ModuleRecord::addStarExportEntry): 55 * parser/NodeConstructors.h: 56 (JSC::ModuleDeclarationNode::ModuleDeclarationNode): 57 (JSC::ImportDeclarationNode::ImportDeclarationNode): 58 (JSC::ExportAllDeclarationNode::ExportAllDeclarationNode): 59 (JSC::ExportDefaultDeclarationNode::ExportDefaultDeclarationNode): 60 (JSC::ExportLocalDeclarationNode::ExportLocalDeclarationNode): 61 (JSC::ExportNamedDeclarationNode::ExportNamedDeclarationNode): 62 * parser/Nodes.h: 63 (JSC::ExportDefaultDeclarationNode::localName): 64 * parser/NodesAnalyzeModule.cpp: Added. 65 (JSC::ScopeNode::analyzeModule): 66 (JSC::SourceElements::analyzeModule): 67 (JSC::ImportDeclarationNode::analyzeModule): 68 (JSC::ExportAllDeclarationNode::analyzeModule): 69 (JSC::ExportDefaultDeclarationNode::analyzeModule): 70 (JSC::ExportLocalDeclarationNode::analyzeModule): 71 (JSC::ExportNamedDeclarationNode::analyzeModule): 72 * parser/Parser.cpp: 73 (JSC::Parser<LexerType>::parseInner): 74 (JSC::Parser<LexerType>::parseModuleSourceElements): 75 (JSC::Parser<LexerType>::parseVariableDeclarationList): 76 (JSC::Parser<LexerType>::createBindingPattern): 77 (JSC::Parser<LexerType>::parseFunctionDeclaration): 78 (JSC::Parser<LexerType>::parseClassDeclaration): 79 (JSC::Parser<LexerType>::parseImportClauseItem): 80 (JSC::Parser<LexerType>::parseExportSpecifier): 81 (JSC::Parser<LexerType>::parseExportDeclaration): 82 * parser/Parser.h: 83 (JSC::Scope::lexicalVariables): 84 (JSC::Scope::declareLexicalVariable): 85 (JSC::Parser::declareVariable): 86 (JSC::Parser::exportName): 87 (JSC::Parser<LexerType>::parse): 88 (JSC::parse): 89 * parser/ParserModes.h: 90 * parser/SyntaxChecker.h: 91 (JSC::SyntaxChecker::createExportDefaultDeclaration): 92 * parser/VariableEnvironment.cpp: 93 (JSC::VariableEnvironment::markVariableAsImported): 94 (JSC::VariableEnvironment::markVariableAsExported): 95 * parser/VariableEnvironment.h: 96 (JSC::VariableEnvironmentEntry::isExported): 97 (JSC::VariableEnvironmentEntry::isImported): 98 (JSC::VariableEnvironmentEntry::setIsExported): 99 (JSC::VariableEnvironmentEntry::setIsImported): 100 * runtime/CommonIdentifiers.h: 101 * runtime/Completion.cpp: 102 (JSC::checkModuleSyntax): 103 * runtime/Options.h: 104 1 105 2015-08-12 Geoffrey Garen <[email protected]> 2 106 -
trunk/Source/JavaScriptCore/JavaScriptCore.vcxproj/JavaScriptCore.vcxproj
r188329 r188355 661 661 <ClCompile Include="..\llvm\LLVMAPI.cpp" /> 662 662 <ClCompile Include="..\parser\Lexer.cpp" /> 663 <ClCompile Include="..\parser\ModuleAnalyzer.cpp" /> 664 <ClCompile Include="..\parser\ModuleRecord.cpp" /> 663 665 <ClCompile Include="..\parser\Nodes.cpp" /> 666 <ClCompile Include="..\parser\NodesAnalyzeModule.cpp" /> 664 667 <ClCompile Include="..\parser\Parser.cpp" /> 665 668 <ClCompile Include="..\parser\ParserArena.cpp" /> … … 1449 1452 <ClInclude Include="..\parser\ASTBuilder.h" /> 1450 1453 <ClInclude Include="..\parser\Lexer.h" /> 1454 <ClInclude Include="..\parser\ModuleAnalyzer.h" /> 1455 <ClInclude Include="..\parser\ModuleRecord.h" /> 1451 1456 <ClInclude Include="..\parser\NodeConstructors.h" /> 1452 1457 <ClInclude Include="..\parser\Nodes.h" /> -
trunk/Source/JavaScriptCore/JavaScriptCore.vcxproj/JavaScriptCore.vcxproj.filters
r188329 r188355 457 457 <Filter>parser</Filter> 458 458 </ClCompile> 459 <ClCompile Include="..\parser\ModuleAnalyzer.cpp"> 460 <Filter>parser</Filter> 461 </ClCompile> 462 <ClCompile Include="..\parser\ModuleRecord.cpp"> 463 <Filter>parser</Filter> 464 </ClCompile> 459 465 <ClCompile Include="..\parser\Nodes.cpp"> 466 <Filter>parser</Filter> 467 </ClCompile> 468 <ClCompile Include="..\parser\NodesAnalyzeModule.cpp"> 460 469 <Filter>parser</Filter> 461 470 </ClCompile> … … 2479 2488 </ClInclude> 2480 2489 <ClInclude Include="..\parser\Lexer.h"> 2490 <Filter>parser</Filter> 2491 </ClInclude> 2492 <ClInclude Include="..\parser\ModuleAnalyzer.h"> 2493 <Filter>parser</Filter> 2494 </ClInclude> 2495 <ClInclude Include="..\parser\ModuleRecord.h"> 2481 2496 <Filter>parser</Filter> 2482 2497 </ClInclude> -
trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj
r188329 r188355 1694 1694 E33637A61B63220200EE0840 /* ReflectObject.h in Headers */ = {isa = PBXBuildFile; fileRef = E33637A41B63220200EE0840 /* ReflectObject.h */; settings = {ATTRIBUTES = (Private, ); }; }; 1695 1695 E354622B1B6065D100545386 /* ConstructAbility.h in Headers */ = {isa = PBXBuildFile; fileRef = E354622A1B6065D100545386 /* ConstructAbility.h */; settings = {ATTRIBUTES = (Private, ); }; }; 1696 E3794E751B77EB97005543AE /* ModuleAnalyzer.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E3794E731B77EB97005543AE /* ModuleAnalyzer.cpp */; }; 1697 E3794E761B77EB97005543AE /* ModuleAnalyzer.h in Headers */ = {isa = PBXBuildFile; fileRef = E3794E741B77EB97005543AE /* ModuleAnalyzer.h */; settings = {ATTRIBUTES = (Private, ); }; }; 1698 E3963CED1B73F75000EB4CE5 /* ModuleRecord.h in Headers */ = {isa = PBXBuildFile; fileRef = E3963CEB1B73F75000EB4CE5 /* ModuleRecord.h */; settings = {ATTRIBUTES = (Private, ); }; }; 1699 E3963CEE1B73F75000EB4CE5 /* NodesAnalyzeModule.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E3963CEC1B73F75000EB4CE5 /* NodesAnalyzeModule.cpp */; }; 1700 E3C09F551B79692A00EE36A2 /* ModuleRecord.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E3C09F541B79692A00EE36A2 /* ModuleRecord.cpp */; }; 1696 1701 E3EF88741B66DF23003F26CB /* JSPropertyNameIterator.cpp in Sources */ = {isa = PBXBuildFile; fileRef = E3EF88721B66DF23003F26CB /* JSPropertyNameIterator.cpp */; }; 1697 1702 E3EF88751B66DF23003F26CB /* JSPropertyNameIterator.h in Headers */ = {isa = PBXBuildFile; fileRef = E3EF88731B66DF23003F26CB /* JSPropertyNameIterator.h */; settings = {ATTRIBUTES = (Private, ); }; }; … … 3518 3523 E33637A41B63220200EE0840 /* ReflectObject.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ReflectObject.h; sourceTree = "<group>"; }; 3519 3524 E354622A1B6065D100545386 /* ConstructAbility.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ConstructAbility.h; sourceTree = "<group>"; }; 3525 E3794E731B77EB97005543AE /* ModuleAnalyzer.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ModuleAnalyzer.cpp; sourceTree = "<group>"; }; 3526 E3794E741B77EB97005543AE /* ModuleAnalyzer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ModuleAnalyzer.h; sourceTree = "<group>"; }; 3527 E3963CEB1B73F75000EB4CE5 /* ModuleRecord.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ModuleRecord.h; sourceTree = "<group>"; }; 3528 E3963CEC1B73F75000EB4CE5 /* NodesAnalyzeModule.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = NodesAnalyzeModule.cpp; sourceTree = "<group>"; }; 3529 E3C09F541B79692A00EE36A2 /* ModuleRecord.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ModuleRecord.cpp; sourceTree = "<group>"; }; 3520 3530 E3EF88721B66DF23003F26CB /* JSPropertyNameIterator.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSPropertyNameIterator.cpp; sourceTree = "<group>"; }; 3521 3531 E3EF88731B66DF23003F26CB /* JSPropertyNameIterator.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = JSPropertyNameIterator.h; sourceTree = "<group>"; }; … … 4427 4437 F692A8650255597D01FF60F7 /* Lexer.cpp */, 4428 4438 F692A8660255597D01FF60F7 /* Lexer.h */, 4439 E3794E731B77EB97005543AE /* ModuleAnalyzer.cpp */, 4440 E3794E741B77EB97005543AE /* ModuleAnalyzer.h */, 4441 E3C09F541B79692A00EE36A2 /* ModuleRecord.cpp */, 4442 E3963CEB1B73F75000EB4CE5 /* ModuleRecord.h */, 4429 4443 930DAD030FB1EB1A0082D205 /* NodeConstructors.h */, 4430 4444 F692A86D0255597D01FF60F7 /* Nodes.cpp */, 4431 4445 F692A86E0255597D01FF60F7 /* Nodes.h */, 4446 E3963CEC1B73F75000EB4CE5 /* NodesAnalyzeModule.cpp */, 4432 4447 93F0B3A909BB4DC00068FCE3 /* Parser.cpp */, 4433 4448 93F0B3AA09BB4DC00068FCE3 /* Parser.h */, … … 6162 6177 9E72940B190F0514001A91B5 /* BundlePath.h in Headers */, 6163 6178 0F48532A187DFDEC0083B687 /* FTLRecoveryOpcode.h in Headers */, 6179 E3794E761B77EB97005543AE /* ModuleAnalyzer.h in Headers */, 6164 6180 0F6B1CC41862C47800845D97 /* FTLRegisterAtOffset.h in Headers */, 6165 6181 0FCEFAAC1804C13E00472CE4 /* FTLSaveRestore.h in Headers */, 6166 6182 0F25F1B2181635F300522F39 /* FTLSlowPathCall.h in Headers */, 6167 6183 E354622B1B6065D100545386 /* ConstructAbility.h in Headers */, 6184 E3963CED1B73F75000EB4CE5 /* ModuleRecord.h in Headers */, 6168 6185 0F25F1B4181635F300522F39 /* FTLSlowPathCallKey.h in Headers */, 6169 6186 0F9D339B1803ADB70073C2BC /* FTLStackMaps.h in Headers */, … … 7221 7238 147F39BD107EC37600427A48 /* ArgList.cpp in Sources */, 7222 7239 0F6B1CC918641DF800845D97 /* ArityCheckFailReturnThunks.cpp in Sources */, 7240 E3794E751B77EB97005543AE /* ModuleAnalyzer.cpp in Sources */, 7223 7241 0F743BAA16B88249009F9277 /* ARM64Disassembler.cpp in Sources */, 7224 7242 86D3B2C310156BDE002865E7 /* ARMAssembler.cpp in Sources */, … … 7585 7603 0F2D4DE819832DAC007D4B19 /* ToThisStatus.cpp in Sources */, 7586 7604 FE384EE51ADDB7AD0055DE2C /* JSDollarVM.cpp in Sources */, 7605 E3C09F551B79692A00EE36A2 /* ModuleRecord.cpp in Sources */, 7587 7606 978801401471AD920041B016 /* JSDateMath.cpp in Sources */, 7588 7607 0FE050171AA9091100D33B33 /* DirectArguments.cpp in Sources */, … … 7852 7871 86704B8612DBA33700A9FE7B /* YarrJIT.cpp in Sources */, 7853 7872 86704B8912DBA33700A9FE7B /* YarrPattern.cpp in Sources */, 7873 E3963CEE1B73F75000EB4CE5 /* NodesAnalyzeModule.cpp in Sources */, 7854 7874 86704B4212DB8A8100A9FE7B /* YarrSyntaxChecker.cpp in Sources */, 7855 7875 ); -
trunk/Source/JavaScriptCore/builtins/BuiltinNames.h
r184828 r188355 32 32 namespace JSC { 33 33 34 #define INITIALISE_BUILTIN_NAMES(name) , m_##name(Identifier::fromString(vm, #name)), m_##name##PrivateName(Identifier::fromUid(PrivateName( )))34 #define INITIALISE_BUILTIN_NAMES(name) , m_##name(Identifier::fromString(vm, #name)), m_##name##PrivateName(Identifier::fromUid(PrivateName(PrivateName::Description, ASCIILiteral("PrivateSymbol." #name)))) 35 35 #define DECLARE_BUILTIN_NAMES(name) const Identifier m_##name; const Identifier m_##name##PrivateName; 36 36 #define DECLARE_BUILTIN_IDENTIFIER_ACCESSOR(name) \ -
trunk/Source/JavaScriptCore/parser/ASTBuilder.h
r188219 r188355 93 93 UnaryExprContext(ASTBuilder&) {} 94 94 }; 95 96 95 97 96 typedef ExpressionNode* Expression; … … 651 650 } 652 651 653 StatementNode* createExportDefaultDeclaration(const JSTokenLocation& location, StatementNode* declaration )654 { 655 return new (m_parserArena) ExportDefaultDeclarationNode(location, declaration );652 StatementNode* createExportDefaultDeclaration(const JSTokenLocation& location, StatementNode* declaration, const Identifier& localName) 653 { 654 return new (m_parserArena) ExportDefaultDeclarationNode(location, declaration, localName); 656 655 } 657 656 -
trunk/Source/JavaScriptCore/parser/NodeConstructors.h
r188219 r188355 734 734 } 735 735 736 inline ModuleDeclarationNode::ModuleDeclarationNode(const JSTokenLocation& location) 737 : StatementNode(location) 738 { 739 } 740 736 741 inline ModuleSpecifierNode::ModuleSpecifierNode(const JSTokenLocation& location, const Identifier& moduleName) 737 742 : Node(location) … … 748 753 749 754 inline ImportDeclarationNode::ImportDeclarationNode(const JSTokenLocation& location, ImportSpecifierListNode* importSpecifierList, ModuleSpecifierNode* moduleSpecifier) 750 : StatementNode(location)755 : ModuleDeclarationNode(location) 751 756 , m_specifierList(importSpecifierList) 752 757 , m_moduleSpecifier(moduleSpecifier) … … 755 760 756 761 inline ExportAllDeclarationNode::ExportAllDeclarationNode(const JSTokenLocation& location, ModuleSpecifierNode* moduleSpecifier) 757 : StatementNode(location)762 : ModuleDeclarationNode(location) 758 763 , m_moduleSpecifier(moduleSpecifier) 759 764 { 760 765 } 761 766 762 inline ExportDefaultDeclarationNode::ExportDefaultDeclarationNode(const JSTokenLocation& location, StatementNode* declaration )763 : StatementNode(location)767 inline ExportDefaultDeclarationNode::ExportDefaultDeclarationNode(const JSTokenLocation& location, StatementNode* declaration, const Identifier& localName) 768 : ModuleDeclarationNode(location) 764 769 , m_declaration(declaration) 770 , m_localName(localName) 765 771 { 766 772 } 767 773 768 774 inline ExportLocalDeclarationNode::ExportLocalDeclarationNode(const JSTokenLocation& location, StatementNode* declaration) 769 : StatementNode(location)775 : ModuleDeclarationNode(location) 770 776 , m_declaration(declaration) 771 777 { … … 773 779 774 780 inline ExportNamedDeclarationNode::ExportNamedDeclarationNode(const JSTokenLocation& location, ExportSpecifierListNode* exportSpecifierList, ModuleSpecifierNode* moduleSpecifier) 775 : StatementNode(location)781 : ModuleDeclarationNode(location) 776 782 , m_specifierList(exportSpecifierList) 777 783 , m_moduleSpecifier(moduleSpecifier) -
trunk/Source/JavaScriptCore/parser/Nodes.h
r188219 r188355 50 50 class JSScope; 51 51 class ScopeNode; 52 class ModuleAnalyzer; 52 53 53 54 enum Operator { … … 1277 1278 1278 1279 void emitBytecode(BytecodeGenerator&, RegisterID* destination); 1280 void analyzeModule(ModuleAnalyzer&); 1279 1281 1280 1282 private: … … 1575 1577 void setClosedVariables(Vector<RefPtr<UniquedStringImpl>>&&) { } 1576 1578 1579 void analyzeModule(ModuleAnalyzer&); 1580 1577 1581 protected: 1578 1582 int m_startLineNumber; … … 1674 1678 }; 1675 1679 1676 class ImportDeclarationNode : public StatementNode { 1680 class ModuleDeclarationNode : public StatementNode { 1681 public: 1682 virtual void analyzeModule(ModuleAnalyzer&) = 0; 1683 1684 protected: 1685 ModuleDeclarationNode(const JSTokenLocation&); 1686 }; 1687 1688 class ImportDeclarationNode : public ModuleDeclarationNode { 1677 1689 public: 1678 1690 ImportDeclarationNode(const JSTokenLocation&, ImportSpecifierListNode*, ModuleSpecifierNode*); … … 1683 1695 private: 1684 1696 virtual void emitBytecode(BytecodeGenerator&, RegisterID* = 0) override; 1697 virtual void analyzeModule(ModuleAnalyzer&) override; 1685 1698 1686 1699 ImportSpecifierListNode* m_specifierList; … … 1688 1701 }; 1689 1702 1690 class ExportAllDeclarationNode : public StatementNode {1703 class ExportAllDeclarationNode : public ModuleDeclarationNode { 1691 1704 public: 1692 1705 ExportAllDeclarationNode(const JSTokenLocation&, ModuleSpecifierNode*); … … 1696 1709 private: 1697 1710 virtual void emitBytecode(BytecodeGenerator&, RegisterID* = 0) override; 1711 virtual void analyzeModule(ModuleAnalyzer&) override; 1712 1698 1713 ModuleSpecifierNode* m_moduleSpecifier; 1699 1714 }; 1700 1715 1701 class ExportDefaultDeclarationNode : public StatementNode {1702 public: 1703 ExportDefaultDeclarationNode(const JSTokenLocation&, StatementNode* );1716 class ExportDefaultDeclarationNode : public ModuleDeclarationNode { 1717 public: 1718 ExportDefaultDeclarationNode(const JSTokenLocation&, StatementNode*, const Identifier& localName); 1704 1719 1705 1720 const StatementNode& declaration() const { return *m_declaration; } 1706 1707 private: 1708 virtual void emitBytecode(BytecodeGenerator&, RegisterID* = 0) override; 1721 const Identifier& localName() const { return m_localName; } 1722 1723 private: 1724 virtual void emitBytecode(BytecodeGenerator&, RegisterID* = 0) override; 1725 virtual void analyzeModule(ModuleAnalyzer&) override; 1709 1726 StatementNode* m_declaration; 1710 }; 1711 1712 class ExportLocalDeclarationNode : public StatementNode { 1727 const Identifier& m_localName; 1728 }; 1729 1730 class ExportLocalDeclarationNode : public ModuleDeclarationNode { 1713 1731 public: 1714 1732 ExportLocalDeclarationNode(const JSTokenLocation&, StatementNode*); … … 1718 1736 private: 1719 1737 virtual void emitBytecode(BytecodeGenerator&, RegisterID* = 0) override; 1738 virtual void analyzeModule(ModuleAnalyzer&) override; 1720 1739 StatementNode* m_declaration; 1721 1740 }; … … 1747 1766 }; 1748 1767 1749 class ExportNamedDeclarationNode : public StatementNode {1768 class ExportNamedDeclarationNode : public ModuleDeclarationNode { 1750 1769 public: 1751 1770 ExportNamedDeclarationNode(const JSTokenLocation&, ExportSpecifierListNode*, ModuleSpecifierNode*); … … 1756 1775 private: 1757 1776 virtual void emitBytecode(BytecodeGenerator&, RegisterID* = 0) override; 1777 virtual void analyzeModule(ModuleAnalyzer&) override; 1758 1778 ExportSpecifierListNode* m_specifierList; 1759 1779 ModuleSpecifierNode* m_moduleSpecifier { nullptr }; -
trunk/Source/JavaScriptCore/parser/Parser.cpp
r188219 r188355 236 236 237 237 template <typename LexerType> 238 String Parser<LexerType>::parseInner(const Identifier& calleeName, FunctionParseMode parseMode) 239 { 238 String Parser<LexerType>::parseInner(const Identifier& calleeName, FunctionParseMode parseMode, ModuleParseMode moduleParseMode) 239 { 240 UNUSED_PARAM(moduleParseMode); 241 240 242 String parseError = String(); 241 243 … … 273 275 #if ENABLE(ES6_MODULES) 274 276 else if (m_codeType == JSParserCodeType::Module) 275 sourceElements = parseModuleSourceElements(context );277 sourceElements = parseModuleSourceElements(context, moduleParseMode); 276 278 #endif 277 279 else … … 413 415 414 416 template <typename LexerType> 415 template <class TreeBuilder> TreeSourceElements Parser<LexerType>::parseModuleSourceElements(TreeBuilder& context )417 template <class TreeBuilder> TreeSourceElements Parser<LexerType>::parseModuleSourceElements(TreeBuilder& context, ModuleParseMode moduleParseMode) 416 418 { 417 419 TreeSourceElements sourceElements = context.createSourceElements(); 418 419 // FIXME: When some sort of ModuleAnalyzer TreeBuilder is landed, 420 // this SyntaxChecker will be replaced with typedef under the TreeBuilder, 421 // like TreeBuilder::ModuleStatementItemBuilder. 422 // https://bugs.webkit.org/show_bug.cgi?id=147353 423 SyntaxChecker moduleStatementItemBuilder(const_cast<VM*>(m_vm), m_lexer.get()); 420 SyntaxChecker syntaxChecker(const_cast<VM*>(m_vm), m_lexer.get()); 424 421 425 422 while (true) { 426 if (match(IMPORT) || match(EXPORT)) { 427 TreeStatement statement = 0; 428 if (match(IMPORT)) 429 statement = parseImportDeclaration(context); 430 else 431 statement = parseExportDeclaration(context); 432 433 if (!statement) 434 break; 435 context.appendStatement(sourceElements, statement); 436 } else { 423 TreeStatement statement = 0; 424 if (match(IMPORT)) 425 statement = parseImportDeclaration(context); 426 else if (match(EXPORT)) 427 statement = parseExportDeclaration(context); 428 else { 437 429 const Identifier* directive = 0; 438 430 unsigned directiveLiteralLength = 0; 439 if (!parseStatementListItem(moduleStatementItemBuilder, directive, &directiveLiteralLength)) 440 break; 441 } 431 if (moduleParseMode == ModuleParseMode::Analyze) { 432 if (!parseStatementListItem(syntaxChecker, directive, &directiveLiteralLength)) 433 break; 434 continue; 435 } 436 statement = parseStatementListItem(context, directive, &directiveLiteralLength); 437 } 438 439 if (!statement) 440 break; 441 context.appendStatement(sourceElements, statement); 442 442 } 443 443 444 444 propagateError(); 445 445 446 for (const auto& uid : currentScope()->moduleScopeData().exportedBindings()) 447 semanticFailIfFalse(currentScope()->hasDeclaredVariable(uid) || currentScope()->hasLexicallyDeclaredVariable(uid), "Exported binding '", uid.get(), "' needs to refer to a top-level declared variable"); 446 for (const auto& uid : currentScope()->moduleScopeData().exportedBindings()) { 447 if (currentScope()->hasDeclaredVariable(uid)) { 448 currentScope()->declaredVariables().markVariableAsExported(uid); 449 continue; 450 } 451 452 if (currentScope()->hasLexicallyDeclaredVariable(uid)) { 453 currentScope()->lexicalVariables().markVariableAsExported(uid); 454 continue; 455 } 456 457 semanticFail("Exported binding '", uid.get(), "' needs to refer to a top-level declared variable"); 458 } 448 459 449 460 return sourceElements; … … 602 613 } 603 614 } 604 semanticFailIfTrue(exportType == ExportType::Exported && !currentScope()->moduleScopeData().exportName(*name), "Cannot export a duplicate name '", name->impl(), "'"); 615 if (exportType == ExportType::Exported) { 616 semanticFailIfFalse(exportName(*name), "Cannot export a duplicate name '", name->impl(), "'"); 617 currentScope()->moduleScopeData().exportBinding(*name); 618 } 605 619 606 620 if (hasInitializer) { … … 706 720 } 707 721 708 semanticFailIfTrue(exportType == ExportType::Exported && !currentScope()->moduleScopeData().exportName(name), "Cannot export a duplicate name '", name.impl(), "'"); 722 if (exportType == ExportType::Exported) { 723 semanticFailIfFalse(exportName(name), "Cannot export a duplicate name '", name.impl(), "'"); 724 currentScope()->moduleScopeData().exportBinding(name); 725 } 709 726 return context.createBindingLocation(token.m_location, name, token.m_startPosition, token.m_endPosition, bindingContext); 710 727 } … … 1857 1874 failIfFalse(functionInfo.name, "Function statements must have a name"); 1858 1875 failIfTrueIfStrict(declareVariable(functionInfo.name) & DeclarationResult::InvalidStrictMode, "Cannot declare a function named '", functionInfo.name->impl(), "' in strict mode"); 1859 semanticFailIfTrue(exportType == ExportType::Exported && !currentScope()->moduleScopeData().exportName(*functionInfo.name), "Cannot export a duplicate function name: '", functionInfo.name->impl(), "'"); 1876 if (exportType == ExportType::Exported) { 1877 semanticFailIfFalse(exportName(*functionInfo.name), "Cannot export a duplicate function name: '", functionInfo.name->impl(), "'"); 1878 currentScope()->moduleScopeData().exportBinding(*functionInfo.name); 1879 } 1860 1880 return context.createFuncDeclStatement(location, functionInfo); 1861 1881 } … … 1877 1897 if (declarationResult & DeclarationResult::InvalidDuplicateDeclaration) 1878 1898 internalFailWithMessage(false, "Cannot declare a class twice: '", info.className->impl(), "'"); 1879 semanticFailIfTrue(exportType == ExportType::Exported && !currentScope()->moduleScopeData().exportName(*info.className), "Cannot export a duplicate class name: '", info.className->impl(), "'"); 1899 if (exportType == ExportType::Exported) { 1900 semanticFailIfFalse(exportName(*info.className), "Cannot export a duplicate class name: '", info.className->impl(), "'"); 1901 currentScope()->moduleScopeData().exportBinding(*info.className); 1902 } 1880 1903 1881 1904 JSTextPosition classEnd = lastTokenEndPosition(); … … 2283 2306 2284 2307 semanticFailIfTrue(localNameToken.m_type & KeywordTokenFlag, "Cannot use keyword as imported binding name"); 2285 DeclarationResultMask declarationResult = declareVariable(localName, DeclarationType::ConstDeclaration );2308 DeclarationResultMask declarationResult = declareVariable(localName, DeclarationType::ConstDeclaration, DeclarationImportType::Imported); 2286 2309 if (declarationResult != DeclarationResult::Valid) { 2287 2310 failIfTrueIfStrict(declarationResult & DeclarationResult::InvalidStrictMode, "Cannot declare an imported binding named ", localName->impl(), " in strict mode"); … … 2385 2408 } 2386 2409 2387 semanticFailIfFalse( currentScope()->moduleScopeData().exportName(*exportedName), "Cannot export a duplicate name '", exportedName->impl(), "'");2410 semanticFailIfFalse(exportName(*exportedName), "Cannot export a duplicate name '", exportedName->impl(), "'"); 2388 2411 maybeLocalNames.append(localName); 2389 2412 return context.createExportSpecifier(specifierLocation, *localName, *exportedName); … … 2408 2431 failIfFalse(moduleSpecifier, "Cannot parse the 'from' clause"); 2409 2432 failIfFalse(autoSemiColon(), "Expected a ';' following a targeted export declaration"); 2433 2410 2434 return context.createExportAllDeclaration(exportLocation, moduleSpecifier); 2411 2435 } … … 2419 2443 2420 2444 TreeStatement result = 0; 2421 bool hasName = false;2422 2445 bool isFunctionOrClassDeclaration = false; 2446 const Identifier* localName = nullptr; 2423 2447 SavePoint savePoint = createSavePoint(); 2424 2448 if (match(FUNCTION) … … 2430 2454 next(); 2431 2455 // FIXME: When landing ES6 generators, we need to take care of that '*' comes. 2432 hasName = match(IDENT); 2456 if (match(IDENT)) 2457 localName = m_token.m_data.ident; 2433 2458 restoreSavePoint(savePoint); 2434 2459 } 2435 2460 2436 if ( hasName) {2461 if (localName) { 2437 2462 if (match(FUNCTION)) 2438 2463 result = parseFunctionDeclaration(context); … … 2444 2469 #endif 2445 2470 } else { 2471 // export default expr; 2472 // 2473 // It should be treated as the same to the following. 2474 // 2475 // const *default* = expr; 2476 // export { *default* as default } 2446 2477 JSTokenLocation location(tokenLocation()); 2447 2478 JSTextPosition start = tokenStartPosition(); 2448 2479 TreeExpression expression = parseAssignmentExpression(context); 2449 2480 failIfFalse(expression, "Cannot parse expression"); 2450 result = context.createExprStatement(location, expression, start, tokenEndPosition()); 2481 2482 DeclarationResultMask declarationResult = declareVariable(&m_vm->propertyNames->starDefaultPrivateName, DeclarationType::ConstDeclaration); 2483 if (declarationResult & DeclarationResult::InvalidDuplicateDeclaration) 2484 internalFailWithMessage(false, "Cannot export 'default' name twice: '"); 2485 2486 TreeExpression assignment = context.createAssignResolve(location, m_vm->propertyNames->starDefaultPrivateName, expression, start, start, tokenEndPosition(), AssignmentContext::ConstDeclarationStatement); 2487 result = context.createExprStatement(location, assignment, start, tokenEndPosition()); 2451 2488 if (!isFunctionOrClassDeclaration) 2452 2489 failIfFalse(autoSemiColon(), "Expected a ';' following a targeted export declaration"); 2490 localName = &m_vm->propertyNames->starDefaultPrivateName; 2453 2491 } 2454 2492 failIfFalse(result, "Cannot parse the declaration"); 2455 semanticFailIfFalse(currentScope()->moduleScopeData().exportName(m_vm->propertyNames->defaultKeyword), "Cannot export 'default' name twice."); 2456 2457 return context.createExportDefaultDeclaration(exportLocation, result); 2493 2494 semanticFailIfFalse(exportName(m_vm->propertyNames->defaultKeyword), "Cannot export 'default' name twice."); 2495 currentScope()->moduleScopeData().exportBinding(*localName); 2496 return context.createExportDefaultDeclaration(exportLocation, result, *localName); 2458 2497 } 2459 2498 -
trunk/Source/JavaScriptCore/parser/Parser.h
r188219 r188355 99 99 }; 100 100 101 enum class DeclarationImportType { 102 Imported, 103 NotImported 104 }; 105 101 106 enum DeclarationResult { 102 107 Valid = 0, … … 258 263 259 264 VariableEnvironment& declaredVariables() { return m_declaredVariables; } 265 VariableEnvironment& lexicalVariables() { return m_lexicalVariables; } 260 266 VariableEnvironment& finalizeLexicalEnvironment() 261 267 { … … 316 322 } 317 323 318 DeclarationResultMask declareLexicalVariable(const Identifier* ident, bool isConstant )324 DeclarationResultMask declareLexicalVariable(const Identifier* ident, bool isConstant, DeclarationImportType importType = DeclarationImportType::NotImported) 319 325 { 320 326 ASSERT(m_allowsLexicalDeclarations); … … 327 333 else 328 334 addResult.iterator->value.setIsLet(); 335 336 if (importType == DeclarationImportType::Imported) 337 addResult.iterator->value.setIsImported(); 329 338 330 339 if (!addResult.isNewEntry) … … 612 621 613 622 template <class ParsedNode> 614 std::unique_ptr<ParsedNode> parse(ParserError&, const Identifier&, FunctionParseMode );623 std::unique_ptr<ParsedNode> parse(ParserError&, const Identifier&, FunctionParseMode, ModuleParseMode); 615 624 616 625 JSTextPosition positionBeforeLastNewline() const { return m_lexer->positionBeforeLastNewline(); } … … 770 779 } 771 780 772 DeclarationResultMask declareVariable(const Identifier* ident, DeclarationType type = DeclarationType::VarDeclaration )781 DeclarationResultMask declareVariable(const Identifier* ident, DeclarationType type = DeclarationType::VarDeclaration, DeclarationImportType importType = DeclarationImportType::NotImported) 773 782 { 774 783 unsigned i = m_scopeStack.size() - 1; … … 795 804 } 796 805 797 return m_scopeStack[i].declareLexicalVariable(ident, type == DeclarationType::ConstDeclaration );806 return m_scopeStack[i].declareLexicalVariable(ident, type == DeclarationType::ConstDeclaration, importType); 798 807 } 799 808 … … 826 835 } 827 836 837 bool exportName(const Identifier& ident) 838 { 839 ASSERT(currentScope().index() == 0); 840 return currentScope()->moduleScopeData().exportName(ident); 841 } 842 828 843 ScopeStack m_scopeStack; 829 844 … … 834 849 835 850 Parser(); 836 String parseInner(const Identifier&, FunctionParseMode );851 String parseInner(const Identifier&, FunctionParseMode, ModuleParseMode); 837 852 838 853 void didFinishParsing(SourceElements*, DeclarationStacks::FunctionStack&, VariableEnvironment&, CodeFeatures, int, const Vector<RefPtr<UniquedStringImpl>>&&); … … 1099 1114 template <class TreeBuilder> NEVER_INLINE TreeDestructuringPattern tryParseDestructuringPatternExpression(TreeBuilder&, AssignmentContext); 1100 1115 template <class TreeBuilder> NEVER_INLINE TreeExpression parseDefaultValueForDestructuringPattern(TreeBuilder&); 1101 template <class TreeBuilder> TreeSourceElements parseModuleSourceElements(TreeBuilder& );1116 template <class TreeBuilder> TreeSourceElements parseModuleSourceElements(TreeBuilder&, ModuleParseMode); 1102 1117 enum class ImportSpecifierType { NamespaceImport, NamedImport, DefaultImport }; 1103 1118 template <class TreeBuilder> typename TreeBuilder::ImportSpecifier parseImportClauseItem(TreeBuilder&, ImportSpecifierType); … … 1256 1271 template <typename LexerType> 1257 1272 template <class ParsedNode> 1258 std::unique_ptr<ParsedNode> Parser<LexerType>::parse(ParserError& error, const Identifier& calleeName, FunctionParseMode parseMode )1273 std::unique_ptr<ParsedNode> Parser<LexerType>::parse(ParserError& error, const Identifier& calleeName, FunctionParseMode parseMode, ModuleParseMode moduleParseMode) 1259 1274 { 1260 1275 int errLine; … … 1273 1288 unsigned startColumn = m_source->startColumn() - 1; 1274 1289 1275 String parseError = parseInner(calleeName, parseMode );1290 String parseError = parseInner(calleeName, parseMode, moduleParseMode); 1276 1291 1277 1292 int lineNumber = m_lexer->lineNumber(); … … 1341 1356 JSParserStrictMode strictMode, JSParserCodeType codeType, 1342 1357 ParserError& error, JSTextPosition* positionBeforeLastNewline = nullptr, 1343 FunctionParseMode parseMode = NotAFunctionMode, ConstructorKind defaultConstructorKind = ConstructorKind::None, 1344 ThisTDZMode thisTDZMode = ThisTDZMode::CheckIfNeeded) 1358 FunctionParseMode parseMode = NotAFunctionMode, ConstructorKind defaultConstructorKind = ConstructorKind::None, 1359 ThisTDZMode thisTDZMode = ThisTDZMode::CheckIfNeeded, 1360 ModuleParseMode moduleParseMode = ModuleParseMode::Analyze) 1345 1361 { 1346 1362 SamplingRegion samplingRegion("Parsing"); … … 1349 1365 if (source.provider()->source().is8Bit()) { 1350 1366 Parser<Lexer<LChar>> parser(vm, source, builtinMode, strictMode, codeType, defaultConstructorKind, thisTDZMode); 1351 std::unique_ptr<ParsedNode> result = parser.parse<ParsedNode>(error, name, parseMode );1367 std::unique_ptr<ParsedNode> result = parser.parse<ParsedNode>(error, name, parseMode, moduleParseMode); 1352 1368 if (positionBeforeLastNewline) 1353 1369 *positionBeforeLastNewline = parser.positionBeforeLastNewline(); … … 1362 1378 ASSERT_WITH_MESSAGE(defaultConstructorKind == ConstructorKind::None, "BuiltinExecutables::createDefaultConstructor should always use a 8-bit string"); 1363 1379 Parser<Lexer<UChar>> parser(vm, source, builtinMode, strictMode, codeType, defaultConstructorKind, thisTDZMode); 1364 std::unique_ptr<ParsedNode> result = parser.parse<ParsedNode>(error, name, parseMode );1380 std::unique_ptr<ParsedNode> result = parser.parse<ParsedNode>(error, name, parseMode, moduleParseMode); 1365 1381 if (positionBeforeLastNewline) 1366 1382 *positionBeforeLastNewline = parser.positionBeforeLastNewline(); -
trunk/Source/JavaScriptCore/parser/ParserModes.h
r187890 r188355 39 39 enum class SuperBinding { Needed, NotNeeded }; 40 40 enum class ThisTDZMode { AlwaysCheck, CheckIfNeeded }; 41 enum class ModuleParseMode { Analyze, Evaluate }; 41 42 42 43 enum ProfilerMode { ProfilerOff, ProfilerOn }; -
trunk/Source/JavaScriptCore/parser/SyntaxChecker.h
r188219 r188355 266 266 int createImportDeclaration(const JSTokenLocation&, ImportSpecifierList, ModuleSpecifier) { return StatementResult; } 267 267 int createExportAllDeclaration(const JSTokenLocation&, ModuleSpecifier) { return StatementResult; } 268 int createExportDefaultDeclaration(const JSTokenLocation&, int ) { return StatementResult; }268 int createExportDefaultDeclaration(const JSTokenLocation&, int, const Identifier&) { return StatementResult; } 269 269 int createExportLocalDeclaration(const JSTokenLocation&, int) { return StatementResult; } 270 270 int createExportNamedDeclaration(const JSTokenLocation&, ExportSpecifierList, ModuleSpecifier) { return StatementResult; } -
trunk/Source/JavaScriptCore/parser/VariableEnvironment.cpp
r186860 r188355 82 82 } 83 83 84 void VariableEnvironment::markVariableAsImported(const RefPtr<UniquedStringImpl>& identifier) 85 { 86 auto findResult = m_map.find(identifier); 87 RELEASE_ASSERT(findResult != m_map.end()); 88 findResult->value.setIsImported(); 89 } 90 91 void VariableEnvironment::markVariableAsExported(const RefPtr<UniquedStringImpl>& identifier) 92 { 93 auto findResult = m_map.find(identifier); 94 RELEASE_ASSERT(findResult != m_map.end()); 95 findResult->value.setIsExported(); 96 } 97 84 98 } // namespace JSC -
trunk/Source/JavaScriptCore/parser/VariableEnvironment.h
r187012 r188355 39 39 ALWAYS_INLINE bool isVar() const { return m_bits & IsVar; } 40 40 ALWAYS_INLINE bool isLet() const { return m_bits & IsLet; } 41 ALWAYS_INLINE bool isExported() const { return m_bits & IsExported; } 42 ALWAYS_INLINE bool isImported() const { return m_bits & IsImported; } 41 43 42 44 ALWAYS_INLINE void setIsCaptured() { m_bits |= IsCaptured; } … … 44 46 ALWAYS_INLINE void setIsVar() { m_bits |= IsVar; } 45 47 ALWAYS_INLINE void setIsLet() { m_bits |= IsLet; } 48 ALWAYS_INLINE void setIsExported() { m_bits |= IsExported; } 49 ALWAYS_INLINE void setIsImported() { m_bits |= IsImported; } 46 50 47 51 ALWAYS_INLINE void clearIsVar() { m_bits &= ~IsVar; } … … 52 56 IsConst = 1 << 1, 53 57 IsVar = 1 << 2, 54 IsLet = 1 << 3 58 IsLet = 1 << 3, 59 IsExported = 1 << 4, 60 IsImported = 1 << 5 55 61 }; 56 62 uint8_t m_bits { 0 }; … … 80 86 bool hasCapturedVariables() const; 81 87 bool captures(UniquedStringImpl* identifier) const; 88 void markVariableAsImported(const RefPtr<UniquedStringImpl>& identifier); 89 void markVariableAsExported(const RefPtr<UniquedStringImpl>& identifier); 82 90 83 91 private: -
trunk/Source/JavaScriptCore/runtime/CommonIdentifiers.h
r187890 r188355 302 302 macro(promiseResult) \ 303 303 macro(capabilities) \ 304 macro(starDefault) \ 304 305 305 306 -
trunk/Source/JavaScriptCore/runtime/Completion.cpp
r187890 r188355 32 32 #include "JSLock.h" 33 33 #include "JSCInlines.h" 34 #include "ModuleAnalyzer.h" 35 #include "ModuleRecord.h" 34 36 #include "Parser.h" 35 37 #include <wtf/WTFThreadData.h> … … 66 68 JSLockHolder lock(vm); 67 69 RELEASE_ASSERT(vm.atomicStringTable() == wtfThreadData().atomicStringTable()); 68 return !!parse<ModuleProgramNode>(70 std::unique_ptr<ModuleProgramNode> moduleProgramNode = parse<ModuleProgramNode>( 69 71 &vm, source, Identifier(), JSParserBuiltinMode::NotBuiltin, 70 72 JSParserStrictMode::Strict, JSParserCodeType::Module, error); 73 if (!moduleProgramNode) 74 return false; 75 76 ModuleAnalyzer moduleAnalyzer(vm, moduleProgramNode->varDeclarations(), moduleProgramNode->lexicalVariables()); 77 moduleAnalyzer.analyze(*moduleProgramNode); 78 return true; 71 79 } 72 80 -
trunk/Source/JavaScriptCore/runtime/Options.h
r188338 r188355 323 323 \ 324 324 v(unsigned, watchdog, 0, "watchdog timeout (0 = Disabled, N = a timeout period of N milliseconds)") \ 325 \ 326 v(bool, dumpModuleRecord, false, nullptr) \ 325 327 326 328 class Options {
Note:
See TracChangeset
for help on using the changeset viewer.