• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #ifndef ES2PANDA_TYPESCRIPT_EXACTOR_TYPEEXTRACTOR_H
17 #define ES2PANDA_TYPESCRIPT_EXACTOR_TYPEEXTRACTOR_H
18 
19 #include <ir/statements/blockStatement.h>
20 #include <macros.h>
21 #include <unordered_set>
22 
23 #include "typeRecorder.h"
24 
25 namespace panda::es2panda::extractor {
26 
27 using Getter = std::function<int64_t(const ir::AstNode *, bool isNewInstance)>;
28 using Handler = std::function<void(const ir::AstNode *)>;
29 
30 class TypeExtractor {
31 public:
32     explicit TypeExtractor(const ir::BlockStatement *rootNode, bool typeDtsExtractor, bool typeDtsBuiltin,
33         ArenaAllocator *allocator, compiler::CompilerContext *context);
34     ~TypeExtractor() = default;
35     NO_COPY_SEMANTIC(TypeExtractor);
36     NO_MOVE_SEMANTIC(TypeExtractor);
37 
38     void StartTypeExtractor(const parser::Program *program);
39 
40     bool GetTypeDtsExtractor() const;
41     bool GetTypeDtsBuiltin() const;
42     TypeRecorder *Recorder() const;
43 
44     const ir::Identifier *GetIdentifierFromExpression(const ir::Expression *expression);
45     const ir::AstNode *GetDeclNodeFromIdentifier(const ir::Identifier *identifier, const ir::Identifier **variable);
46     int64_t GetTypeIndexFromAnnotation(const ir::Expression *typeAnnotation, bool isNewInstance = true);
47     int64_t GetTypeIndexFromIdentifier(const ir::Identifier *identifier);
48     int64_t GetTypeIndexFromInitializer(const ir::Expression *initializer);
49     int64_t GetTypeIndexFromClassInst(int64_t typeIndex, const ir::AstNode *node,
50         int64_t builtinTypeIndex = TypeRecorder::PRIMITIVETYPE_ANY);
51 
SetGenericParamTypeMap(const ArenaMap<util::StringView,int64_t> * genericParamTypeMap)52     void SetGenericParamTypeMap(const ArenaMap<util::StringView, int64_t> *genericParamTypeMap)
53     {
54         genericParamTypeMap_ = genericParamTypeMap;
55     }
56 
GetGenericParamTypeMap()57     const ArenaMap<util::StringView, int64_t> *GetGenericParamTypeMap() const
58     {
59         return genericParamTypeMap_;
60     }
61 
62     static int64_t GetBuiltinTypeIndex(util::StringView name);
63 
AddSearchingTypeRefNodes(const ir::Expression * node)64     bool AddSearchingTypeRefNodes(const ir::Expression * node)
65     {
66         if (!IsInSearchingTypeRefNodes(node)) {
67             searchingTypeRefNodes_.insert(node);
68             return true;
69         }
70         return false;
71     }
72 
RemoveSearchingTypeRefNodes(const ir::Expression * node)73     void RemoveSearchingTypeRefNodes(const ir::Expression * node)
74     {
75         if (IsInSearchingTypeRefNodes(node)) {
76             searchingTypeRefNodes_.erase(node);
77         }
78     }
79 
IsInSearchingTypeRefNodes(const ir::Expression * node)80     bool IsInSearchingTypeRefNodes(const ir::Expression * node)
81     {
82         return searchingTypeRefNodes_.find(node) != searchingTypeRefNodes_.end();
83     }
84 
85 private:
86     const ir::BlockStatement *rootNode_;
87     std::unordered_set<const ir::Expression *> searchingTypeRefNodes_;
88     const bool typeDtsExtractor_;
89     const bool typeDtsBuiltin_;
90     std::unique_ptr<TypeRecorder> recorder_;
91     std::unordered_map<ir::AstNodeType, Getter> getterMap_;
92     std::unordered_map<ir::AstNodeType, Handler> handlerMap_;
93     const ArenaMap<util::StringView, int64_t> *genericParamTypeMap_ {nullptr};
94 
95     void ExtractNodesType(const ir::AstNode *parent);
96     void ExtractNodeType(const ir::AstNode *parent, const ir::AstNode *childNode);
97     void ExtractImport(const parser::Program *program);
98     void ExtractExport(const parser::Program *program);
99     void ExtractImportModuleRecord(parser::SourceTextModuleRecord *moduleRecord);
100     void ExtractExportModuleRecord(parser::SourceTextModuleRecord *moduleRecord);
101 
102     const ir::AstNode *GetDeclNodeFromInitializer(const ir::Expression *initializer, const ir::Identifier **variable);
103 
104     int64_t GetTypeIndexFromDeclNode(const ir::AstNode *node, bool isNewInstance);
105     int64_t GetTypeIndexFromIdentifierNode(const ir::AstNode *node, bool isNewInstance);
106     int64_t GetTypeIndexFromClassExpression(const ir::AstNode *node, bool isNewInstance);
107     int64_t GetTypeIndexFromClassDefinition(const ir::AstNode *node, bool isNewInstance);
108     int64_t GetTypeIndexFromInterfaceNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
109     int64_t GetTypeIndexFromFunctionNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
110     int64_t GetTypeIndexFromImportNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
111     int64_t GetTypeIndexFromTypeAliasNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
112     int64_t GetTypeIndexFromAsNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
113     int64_t GetTypeIndexFromAssertionNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
114     int64_t GetTypeIndexFromMemberNode(const ir::AstNode *node, [[maybe_unused]] bool isNewInstance);
115     int64_t GetTypeIndexFromTSQualifiedNode(const ir::AstNode *node, bool isNewInstance);
116 
117     void HandleVariableDeclaration(const ir::AstNode *node);
118     void HandleFunctionDeclaration(const ir::AstNode *node);
119     void HandleClassDeclaration(const ir::AstNode *node);
120     void HandleInterfaceDeclaration(const ir::AstNode *node);
121     void HandleTypeAliasDeclaration(const ir::AstNode *node);
122     void HandleNewlyGenFuncExpression(const ir::AstNode *node);
123     void HandleArrowFunctionExpression(const ir::AstNode *node);
124 
125     // Helpers
126     int64_t GetTypeIndexFromTypeReference(const ir::TSTypeReference *typeReference, bool isNewInstance);
127     int64_t GetTypeIndexFromTSLiteralType(const ir::TSLiteralType *tsLiteralType);
128 
129     // Builtin and Generic Helpers
130     int64_t GetTypeIndexFromBuiltin(const util::StringView &name, const ir::TSTypeParameterInstantiation *node);
131     int64_t GetTypeIndexFromBuiltinInst(int64_t typeIndexBuiltin, const ir::TSTypeParameterInstantiation *node);
132     int64_t GetTypeIndexFromGenericInst(const ir::AstNode *declNode, const ir::TSTypeParameterInstantiation *node);
133 
134     // Other Helpers
135     bool IsExportNode(const ir::AstNode *node) const;
136     bool IsDeclareNode(const ir::AstNode *node) const;
137     void GetVariablesFromTSQualifiedNodes(const binder::Variable *variable,
138         ArenaDeque<const ir::Identifier *> &identifiers, ArenaVector<const binder::Variable *> &variables) const;
139     void GetVariablesFromNamespace(const binder::NamespaceVariable *variable, ArenaVector<binder::Variable *> &findRes,
140         ArenaDeque<const ir::Identifier *> &identifiers, ArenaVector<const binder::Variable *> &variables) const;
141 };
142 
143 class GenericParamTypeBindScope {
144 public:
145     GenericParamTypeBindScope() = delete;
146 
GenericParamTypeBindScope(TypeExtractor * extractor,const ArenaMap<util::StringView,int64_t> * genericParamTypeMap)147     explicit GenericParamTypeBindScope(TypeExtractor *extractor,
148         const ArenaMap<util::StringView, int64_t> *genericParamTypeMap) : extractor_(extractor)
149     {
150         ASSERT(extractor_ != nullptr);
151         extractor_->SetGenericParamTypeMap(genericParamTypeMap);
152     }
153 
~GenericParamTypeBindScope()154     ~GenericParamTypeBindScope()
155     {
156         extractor_->SetGenericParamTypeMap(nullptr);
157     }
158 
159     NO_COPY_SEMANTIC(GenericParamTypeBindScope);
160     NO_MOVE_SEMANTIC(GenericParamTypeBindScope);
161 
162 private:
163     TypeExtractor *extractor_;
164 };
165 
166 }  // namespace panda::es2panda::extractor
167 
168 #endif  // ES2PANDA_TYPESCRIPT_EXACTOR_TYPEEXTRACTOR_H
169