• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * Copyright (c) 2021 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_PARSER_CORE_PARSER_IMPL_H
17 #define ES2PANDA_PARSER_CORE_PARSER_IMPL_H
18 
19 #include <binder/binder.h>
20 #include <es2panda.h>
21 #include <ir/astNode.h>
22 #include <ir/base/methodDefinition.h>
23 #include <lexer/token/sourceLocation.h>
24 #include <macros.h>
25 #include <mem/arena_allocator.h>
26 #include <parser/context/parserContext.h>
27 #include <parser/module/sourceTextModuleRecord.h>
28 #include <parser/parserFlags.h>
29 #include <parser/program/program.h>
30 #include <util/enumbitops.h>
31 #include <util/ustring.h>
32 
33 #include <memory>
34 #include <sstream>
35 #include <unordered_map>
36 #include <unordered_set>
37 
38 namespace panda::es2panda::lexer {
39 enum class TokenFlags;
40 enum class TokenType;
41 class LexerPosition;
42 class Token;
43 class Lexer;
44 }  // namespace panda::es2panda::lexer
45 
46 namespace panda::es2panda::ir {
47 class ArrowFunctionExpression;
48 class AstNode;
49 class BlockStatement;
50 class BreakStatement;
51 class CallExpression;
52 class ClassDeclaration;
53 class ClassDefinition;
54 class ContinueStatement;
55 class DoWhileStatement;
56 class ExportAllDeclaration;
57 class ExportDefaultDeclaration;
58 class ExportNamedDeclaration;
59 class ExportNamedDeclaration;
60 class Expression;
61 class FunctionDeclaration;
62 class FunctionExpression;
63 class Identifier;
64 class IfStatement;
65 class ImportDeclaration;
66 class LabelledStatement;
67 class NewExpression;
68 class ObjectExpression;
69 class ReturnStatement;
70 class ScriptFunction;
71 class SequenceExpression;
72 class SpreadElement;
73 class Statement;
74 class StringLiteral;
75 class SwitchCaseStatement;
76 class SwitchStatement;
77 class TSArrayType;
78 class TSEnumDeclaration;
79 class TSFunctionType;
80 class TSInterfaceDeclaration;
81 class TSIntersectionType;
82 class TSTupleType;
83 class TSTypeAliasDeclaration;
84 class TSUnionType;
85 class TSImportType;
86 class TemplateLiteral;
87 class ThrowStatement;
88 class TryStatement;
89 class VariableDeclaration;
90 class WhileStatement;
91 class WithStatement;
92 class TSTypeParameter;
93 class TSTypeParameterDeclaration;
94 class MemberExpression;
95 class MethodDefinition;
96 class TSTypeReference;
97 class TSMappedType;
98 class TSTypePredicate;
99 class Decorator;
100 class TSIndexSignature;
101 class Property;
102 class TSTypeParameterInstantiation;
103 class TSParameterProperty;
104 class TSTypeAssertion;
105 class TSAsExpression;
106 class YieldExpression;
107 class MetaProperty;
108 class TSModuleDeclaration;
109 class TSImportEqualsDeclaration;
110 class TSModuleBlock;
111 class EmptyStatement;
112 class DebuggerStatement;
113 class CatchClause;
114 class VariableDeclarator;
115 
116 enum class PropertyKind;
117 enum class TSTupleKind;
118 enum class MethodDefinitionKind;
119 enum class ModifierFlags;
120 }  // namespace panda::es2panda::ir
121 
122 namespace panda::es2panda::parser {
123 
124 class Program;
125 class ParserContext;
126 
127 class ClassElmentDescriptor {
128 public:
129     ir::MethodDefinitionKind methodKind {};
130     ParserStatus newStatus {};
131     ir::ModifierFlags modifiers {};
132     lexer::SourcePosition methodStart {};
133     lexer::SourcePosition propStart {};
134     bool isPrivateIdent {};
135     bool hasSuperClass {};
136     bool isGenerator {};
137     bool invalidComputedProperty {};
138     bool isComputed {};
139     bool isIndexSignature {};
140     bool classMethod {};
141     bool classField {};
142 };
143 
144 class ArrowFunctionDescriptor {
145 public:
ArrowFunctionDescriptor(ArenaVector<ir::Expression * > && p,binder::FunctionParamScope * ps,lexer::SourcePosition sl,ParserStatus ns)146     explicit ArrowFunctionDescriptor(ArenaVector<ir::Expression *> &&p, binder::FunctionParamScope *ps,
147                                      lexer::SourcePosition sl, ParserStatus ns)
148         : params(p), paramScope(ps), startLoc(sl), newStatus(ns)
149     {
150     }
151 
152     ArenaVector<ir::Expression *> params;
153     binder::FunctionParamScope *paramScope;
154     lexer::SourcePosition startLoc;
155     ParserStatus newStatus;
156 };
157 
158 enum class TypeAnnotationParsingOptions {
159     NO_OPTS = 0,
160     IN_UNION = 1 << 0,
161     ALLOW_CONST = 1 << 1,
162     IN_INTERSECTION = 1 << 2,
163     RESTRICT_EXTENDS = 1 << 3,
164     THROW_ERROR = 1 << 4,
165     CAN_BE_TS_TYPE_PREDICATE = 1 << 5,
166     BREAK_AT_NEW_LINE = 1 << 6,
167     IN_MODIFIER = 1 << 7,
168 };
169 
DEFINE_BITOPS(TypeAnnotationParsingOptions)170 DEFINE_BITOPS(TypeAnnotationParsingOptions)
171 
172 class ArrowFunctionContext;
173 
174 class ParserImpl {
175 public:
176     explicit ParserImpl(es2panda::ScriptExtension extension);
177     NO_COPY_SEMANTIC(ParserImpl);
178     NO_MOVE_SEMANTIC(ParserImpl);
179     ~ParserImpl() = default;
180 
181     Program Parse(const std::string &fileName, const std::string &source,
182                   const std::string &recordName, ScriptKind kind);
183 
184     ScriptExtension Extension() const;
185 
186     void AddPatchFixHelper(util::PatchFix *patchFixHelper);
187 
188     ArenaAllocator *Allocator() const
189     {
190         return program_.Allocator();
191     }
192     bool IsDtsFile() const;
193     void SetDebug(bool isDebug)
194     {
195         program_.SetDebug(isDebug);
196     }
197 
198 private:
199     bool IsStartOfMappedType() const;
200     bool IsStartOfTsTypePredicate() const;
201     bool IsStartOfAbstractConstructorType() const;
202 
203     bool CurrentTokenIsModifier(char32_t nextCp) const;
204     [[noreturn]] void ThrowParameterModifierError(ir::ModifierFlags status) const;
205     [[noreturn]] void ThrowSyntaxError(std::string_view errorMessage) const;
206     [[noreturn]] void ThrowSyntaxError(std::initializer_list<std::string_view> list) const;
207     [[noreturn]] void ThrowSyntaxError(std::initializer_list<std::string_view> list,
208                                        const lexer::SourcePosition &pos) const;
209 
210     [[noreturn]] void ThrowSyntaxError(std::string_view errorMessage, const lexer::SourcePosition &pos) const;
211 
212     template <typename T, typename... Args>
213     T *AllocNode(Args &&... args)
214     {
215         auto ret = program_.Allocator()->New<T>(std::forward<Args>(args)...);
216         if (ret == nullptr) {
217             throw Error(ErrorType::GENERIC, "Unsuccessful allocation during parsing");
218         }
219         return ret;
220     }
221 
222     [[nodiscard]] std::unique_ptr<lexer::Lexer> InitLexer(const std::string &fileName, const std::string &source);
223     void ParseScript();
224     void ParseModule();
225 
226     /*
227      * Transform the commonjs module's AST by wrap the sourceCode & use Reflect.apply to invoke this wrapper with [this]
228      * pointing to [exports] object
229      *
230      * Reflect.apply(function (exports, require, module, __filename, __dirname) {
231      *   [SourceCode]
232      * }, exports, [exports, require, module, __filename, __dirname]);
233      */
234     void ParseCommonjs();
235     void AddCommonjsParams(ArenaVector<ir::Expression *> &params);
236     void AddReflectApplyArgs(ArenaVector<ir::Expression *> &args, ir::FunctionExpression *wrapper);
237     void ParseProgram(ScriptKind kind);
238     bool CheckTopStatementsForRequiredDeclare(const ArenaVector<ir::Statement *> &statements);
239     static ExpressionParseFlags CarryExpressionParserFlag(ExpressionParseFlags origin, ExpressionParseFlags carry);
240     static ExpressionParseFlags CarryPatternFlags(ExpressionParseFlags flags);
241     static ExpressionParseFlags CarryAllowTsParamAndPatternFlags(ExpressionParseFlags flags);
242     bool CurrentIsBasicType();
243     bool CurrentLiteralIsBasicType();
244     static bool CheckTypeNameIsReserved(const util::StringView &paramName);
245     static bool IsPropertyKeysAreSame(const ir::Expression *exp1, const ir::Expression *exp2);
246     static bool IsMemberExpressionsAreSame(const ir::MemberExpression *mExp1, const ir::MemberExpression *mExp2);
247     static bool IsMethodDefinitionsAreSame(const ir::MethodDefinition *property, ir::MethodDefinition *overload);
248     ir::TSTypeReference *ParseTsConstExpression();
249     ir::Expression *ParseTsTypeOperatorOrTypeReference(bool throwError);
250     ir::Expression *ParseTsIdentifierReference(TypeAnnotationParsingOptions options);
251     ir::Expression *ParseTsBasicType(TypeAnnotationParsingOptions options);
252     ir::TSIntersectionType *ParseTsIntersectionType(ir::Expression *type, bool inUnion, bool restrictExtends);
253     ir::TSUnionType *ParseTsUnionType(ir::Expression *type, bool restrictExtends);
254     ir::Expression *ParseTsParenthesizedOrFunctionType(ir::Expression *typeAnnotation, bool throwError);
255     ir::TSArrayType *ParseTsArrayType(ir::Expression *elementType);
256     bool IsTsFunctionType();
257     ir::Expression *ParseTsFunctionType(lexer::SourcePosition startLoc, bool isConstructionType, bool throwError,
258                                         bool abstractConstructor = false);
259     ir::TSTypeParameter *ParseTsMappedTypeParameter();
260     ir::MappedOption ParseMappedOption(lexer::TokenType tokenType);
261     ir::TSMappedType *ParseTsMappedType();
262     ir::TSTypePredicate *ParseTsTypePredicate();
263     ir::Expression *ParseTsTypeLiteralOrInterfaceKey(bool *computed, bool *signature, bool *isIndexSignature);
264     ir::Expression *ParseTsConditionalType(ir::Expression *checkType, bool restrictExtends);
265     ir::Expression *ParseTsTypeLiteralOrInterfaceMember();
266     ArenaVector<ir::Expression *> ParseTsTypeLiteralOrInterface();
267     ir::Expression *ParseTsThisType(bool throwError);
268     ir::Expression *ParseTsIndexAccessType(ir::Expression *typeName, bool throwError);
269     ir::Expression *ParseTsQualifiedReference(ir::Expression *typeName);
270     ir::Expression *ParseTsTypeReferenceOrQuery(TypeAnnotationParsingOptions options, bool parseQuery = false);
271     bool IsTSNamedTupleMember();
272     void HandleRestType(ir::AstNodeType elementType, bool *hasRestType) const;
273     ir::Expression *ParseTsTupleElement(ir::TSTupleKind *kind, bool *seenOptional, bool *hasRestType);
274     ir::TSTupleType *ParseTsTupleType();
275     ir::TSImportType *ParseTsImportType(const lexer::SourcePosition &startLoc, bool isTypeof = false);
276     ir::Expression *ParseTsTypeAnnotation(TypeAnnotationParsingOptions *options);
277     ir::Expression *ParseTsTypeLiteralOrTsMappedType(ir::Expression *typeAnnotation);
278     ir::Expression *ParseTsTypeReferenceOrTsTypePredicate(ir::Expression *typeAnnotation, bool canBeTsTypePredicate,
279                                                           bool throwError);
280     ir::Expression *ParseTsThisTypeOrTsTypePredicate(ir::Expression *typeAnnotation, bool canBeTsTypePredicate,
281                                                      bool throwError);
282     ir::Expression *ParseTsTemplateLiteralType(bool throwError);
283     ir::Expression *ParseTsTypeAnnotationElement(ir::Expression *typeAnnotation, TypeAnnotationParsingOptions *options);
284     ir::ModifierFlags ParseModifiers();
285 
286     void ThrowIfPrivateIdent(ClassElmentDescriptor *desc, const char *msg);
287     void ValidateClassKey(ClassElmentDescriptor *desc, bool isDeclare);
288 
289     void ValidateClassMethodStart(ClassElmentDescriptor *desc, ir::Expression *typeAnnotation);
290     ir::Expression *ParseClassKey(ClassElmentDescriptor *desc, bool isDeclare);
291 
292     void ValidateClassSetter(ClassElmentDescriptor *desc, const ArenaVector<ir::Statement *> &properties,
293                              ir::Expression *propName, ir::ScriptFunction *func, bool hasDecorator,
294                              lexer::SourcePosition errorInfo);
295     void ValidateClassGetter(ClassElmentDescriptor *desc, const ArenaVector<ir::Statement *> &properties,
296                              ir::Expression *propName, ir::ScriptFunction *func, bool hasDecorator,
297                              lexer::SourcePosition errorInfo);
298     ir::MethodDefinition *ParseClassMethod(ClassElmentDescriptor *desc, const ArenaVector<ir::Statement *> &properties,
299                                            ir::Expression *propName, lexer::SourcePosition *propEnd,
300                                            ArenaVector<ir::Decorator *> &&decorators, bool isDeclare);
301     ir::Statement *ParseClassProperty(ClassElmentDescriptor *desc, const ArenaVector<ir::Statement *> &properties,
302                                       ir::Expression *propName, ir::Expression *typeAnnotation,
303                                       ArenaVector<ir::Decorator *> &&decorators, bool isDeclare);
304     void ParseClassKeyModifiers(ClassElmentDescriptor *desc);
305     void CheckClassGeneratorMethod(ClassElmentDescriptor *desc);
306     void CheckClassPrivateIdentifier(ClassElmentDescriptor *desc);
307     ir::Expression *ParseClassKeyAnnotation();
308     ir::Decorator *ParseDecorator();
309     ArenaVector<ir::Decorator *> ParseDecorators();
310     ir::Statement *ParseClassElement(const ArenaVector<ir::Statement *> &properties,
311                                      ArenaVector<ir::TSIndexSignature *> *indexSignatures, bool hasSuperClass,
312                                      bool isDeclare, bool isAbstractClass);
313     ir::MethodDefinition *CreateImplicitConstructor(ir::Expression *superClass,
314                                                     bool hasSuperClass, bool isDeclare = false);
315     ir::MethodDefinition *CheckClassMethodOverload(ir::Statement *property, ir::MethodDefinition **ctor, bool isDeclare,
316                                                    lexer::SourcePosition errorInfo, ir::MethodDefinition *lastOverload,
317                                                    bool implExists, bool isAbstract = false);
318     ir::Identifier *SetIdentNodeInClassDefinition(bool isDeclare, binder::ConstDecl **decl);
319     ir::ClassDefinition *ParseClassDefinition(bool isDeclaration, bool idRequired = true, bool isDeclare = false,
320                                               bool isAbstract = false);
321 
322     void ValidateClassConstructor(ir::MethodDefinition *ctor,
323                                   ArenaVector<ir::Statement *> &properties,
324                                   ir::Expression *superClass,
325                                   bool isDeclare, bool hasConstructorFuncBody, bool hasSuperClass);
326     void FindSuperCallInConstructor(const ir::AstNode *parent, bool *hasSuperCall);
327     void FindSuperCallInConstructorChildNode(const ir::AstNode *childNode, bool *hasSuperCall);
328     bool SuperCallShouldBeFirst(ir::MethodDefinition *ctor, ArenaVector<ir::Statement *> &properties);
329     void ValidateAccessor(ExpressionParseFlags flags, lexer::TokenFlags currentTokenFlags);
330     void CheckPropertyKeyAsycModifier(ParserStatus *methodStatus);
331     ir::Property *ParseShorthandProperty(const lexer::LexerPosition *startPos);
332     void ParseGeneratorPropertyModifier(ExpressionParseFlags flags, ParserStatus *methodStatus);
333     bool ParsePropertyModifiers(ExpressionParseFlags flags, ir::PropertyKind *propertyKind, ParserStatus *methodStatus);
334     ir::Expression *ParsePropertyKey(ExpressionParseFlags flags);
335     ir::Expression *ParsePropertyValue(const ir::PropertyKind *propertyKind, const ParserStatus *methodStatus,
336                                        ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
337     bool ParsePropertyEnd();
338 
339     ir::Expression *ParsePropertyDefinition(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
340     ir::TSTypeParameter *ParseTsTypeParameter(bool throwError, bool addBinding = false);
341     ir::TSTypeParameterDeclaration *ParseTsTypeParameterDeclaration(bool throwError = true);
342     ir::TSTypeParameterInstantiation *ParseTsTypeParameterInstantiation(bool throwError = true);
343     ir::ScriptFunction *ParseFunction(ParserStatus newStatus = ParserStatus::NO_OPTS,
344                                       bool isDeclare = false,
345                                       ArenaVector<ir::ParamDecorators> *paramDecorators = nullptr);
346     void ValidateFunctionParam(const ArenaVector<ir::Expression *> &params, const ir::Expression *parameter,
347                                bool *seenOptional);
348     void ValidateTsFunctionOverloadParams(const ArenaVector<ir::Expression *> &params);
349     void CheckAccessorPair(const ArenaVector<ir::Statement *> &properties, const ir::Expression *propName,
350                            ir::MethodDefinitionKind methodKind, ir::ModifierFlags access, bool hasDecorator,
351                            lexer::SourcePosition errorInfo);
352     ArenaVector<ir::Expression *> ParseFunctionParams(bool isDeclare = false,
353                                                       ArenaVector<ir::ParamDecorators> *paramDecorators = nullptr);
354     ir::SpreadElement *ParseSpreadElement(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
355     ir::TSParameterProperty *CreateTsParameterProperty(ir::Expression *parameter, ir::ModifierFlags modifiers);
356     ir::Expression *ParseFunctionParameter(bool isDeclare);
357     void CreateTSVariableForProperty(ir::AstNode *node, const ir::Expression *key, binder::VariableFlags flags);
358     void CheckObjectTypeForDuplicatedProperties(ir::Expression *member, ArenaVector<ir::Expression *> const &members);
359 
360     // ExpressionParser.Cpp
361 
362     ir::Expression *ParseExpression(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
363     ir::ArrowFunctionExpression *ParseTsGenericArrowFunction();
364     ir::TSTypeAssertion *ParseTsTypeAssertion(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
365     ir::TSAsExpression *ParseTsAsExpression(ir::Expression *expr, ExpressionParseFlags flags);
366     ir::Expression *ParseArrayExpression(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
367     ir::YieldExpression *ParseYieldExpression();
368     ir::Expression *ParsePotentialExpressionSequence(ir::Expression *expr, ExpressionParseFlags flags);
369     ParserStatus ValidateArrowParameter(ir::Expression *expr);
370 
371     ArrowFunctionDescriptor ConvertToArrowParameter(ir::Expression *expr, bool isAsync,
372                                                     binder::FunctionParamScope *paramScope);
373     ir::ArrowFunctionExpression *ParseArrowFunctionExpressionBody(ArrowFunctionContext *arrowFunctionContext,
374                                                                   binder::FunctionScope *functionScope,
375                                                                   ArrowFunctionDescriptor *desc,
376                                                                   ir::TSTypeParameterDeclaration *typeParamDecl,
377                                                                   ir::Expression *returnTypeAnnotation);
378     ir::ArrowFunctionExpression *ParseArrowFunctionExpression(ir::Expression *expr,
379                                                               ir::TSTypeParameterDeclaration *typeParamDecl,
380                                                               ir::Expression *returnTypeAnnotation, bool isAsync);
381     ir::Expression *ParseCoverParenthesizedExpressionAndArrowParameterList();
382     ir::Expression *ParseKeywordExpression();
383     ir::Expression *ParseBinaryExpression(ir::Expression *left);
384     ir::CallExpression *ParseCallExpression(ir::Expression *callee, bool isOptionalChain = false, bool isAsync = false);
385     ir::ArrowFunctionExpression *ParsePotentialArrowExpression(ir::Expression **returnExpression,
386                                                                const lexer::SourcePosition &startLoc,
387                                                                bool ignoreCallExpression);
388 
389     void ValidateUpdateExpression(ir::Expression *returnExpression, bool isChainExpression);
390     bool ParsePotentialTsGenericFunctionCall(ir::Expression **returnExpression, const lexer::SourcePosition &startLoc,
391                                              bool ignoreCallExpression);
392     ir::Expression *ParsePostPrimaryExpression(ir::Expression *primaryExpr, lexer::SourcePosition startLoc,
393                                                bool ignoreCallExpression, bool *isChainExpression);
394     ir::Expression *ParseMemberExpression(bool ignoreCallExpression = false,
395                                           ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
396     ir::ObjectExpression *ParseObjectExpression(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
397     ir::SequenceExpression *ParseSequenceExpression(ir::Expression *startExpr, bool acceptRest = false,
398                                                     bool acceptTsParam = false);
399     ir::Expression *ParseUnaryOrPrefixUpdateExpression(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
400     ir::Expression *ParseLeftHandSideExpression(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
401     ir::MetaProperty *ParsePotentialNewTarget();
402     void CheckInvalidDestructuring(const ir::AstNode *object) const;
403     void ValidateParenthesizedExpression(ir::Expression *lhsExpression);
404     ir::Expression *ParseAssignmentExpression(ir::Expression *lhsExpression,
405                                               ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
406     ir::Expression *ParsePrimaryExpression(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS);
407     ir::NewExpression *ParseNewExpression();
408     void ParsePotentialTsFunctionParameter(ExpressionParseFlags flags, ir::Expression *returnNode,
409                                            bool isDeclare = false);
410     ir::Expression *ParsePatternElement(ExpressionParseFlags flags = ExpressionParseFlags::NO_OPTS,
411                                         bool allowDefault = true, bool isDeclare = false);
412     ir::TemplateLiteral *ParseTemplateLiteral();
413     ir::Expression *ParseImportExpression();
414     ir::FunctionExpression *ParseFunctionExpression(ParserStatus newStatus = ParserStatus::NO_OPTS);
415     ir::Expression *ParseOptionalChain(ir::Expression *leftSideExpr);
416     ir::Expression *ParseOptionalMemberExpression(ir::Expression *object);
417     void ParseNameSpaceImport(ArenaVector<ir::AstNode *> *specifiers, bool isType);
418     ir::Identifier *ParseNamedImport(const lexer::Token &importedToken);
419     binder::Decl *AddImportDecl(bool isType,
420                                 util::StringView name,
421                                 lexer::SourcePosition startPos,
422                                 binder::DeclarationFlags flag);
423 
424     ir::StringLiteral *ParseFromClause(bool requireFrom = true);
425     void ParseNamedImportSpecifiers(ArenaVector<ir::AstNode *> *specifiers, bool isType);
426     ir::Expression *ParseModuleReference();
427     ir::AstNode *ParseImportDefaultSpecifier(ArenaVector<ir::AstNode *> *specifiers, bool isType);
428     ir::AstNode *ParseImportSpecifiers(ArenaVector<ir::AstNode *> *specifiers, bool isType);
429     void ValidateAssignmentTarget(ExpressionParseFlags flags, ir::Expression *node);
430     void ValidateLvalueAssignmentTarget(ir::Expression *node) const;
431     void ValidateArrowParameterBindings(const ir::Expression *node);
432 
433     ir::ExportDefaultDeclaration *ParseExportDefaultDeclaration(const lexer::SourcePosition &startLoc,
434                                                                 ArenaVector<ir::Decorator *> decorators,
435                                                                 bool isExportEquals = false);
436     ir::ExportAllDeclaration *ParseExportAllDeclaration(const lexer::SourcePosition &startLoc);
437     ir::ExportNamedDeclaration *ParseExportNamedSpecifiers(const lexer::SourcePosition &startLoc, bool isType);
438     ir::ExportNamedDeclaration *ParseNamedExportDeclaration(const lexer::SourcePosition &startLoc,
439                                                             ArenaVector<ir::Decorator *> &&decorators);
440     ir::Identifier *ParseNamedExport(const lexer::Token &exportedToken);
441     void CheckStrictReservedWord() const;
442 
443     // StatementParser.Cpp
444 
445     void ConsumeSemicolon(ir::Statement *statement);
446     void CheckFunctionDeclaration(StatementParsingFlags flags);
447 
448     void CheckLabelledFunction(const ir::Statement *node);
449     bool CheckDeclare();
450 
451     bool IsLabelFollowedByIterationStatement();
452 
453     void AddImportEntryItem(const ir::StringLiteral *source, const ArenaVector<ir::AstNode *> *specifiers, bool isType);
454     void AddExportNamedEntryItem(const ArenaVector<ir::ExportSpecifier *> &specifiers,
455                                  const ir::StringLiteral *source, bool isType);
456     void AddExportStarEntryItem(const lexer::SourcePosition &startLoc, const ir::StringLiteral *source,
457                                 const ir::Identifier *exported);
458     void AddExportDefaultEntryItem(const ir::AstNode *declNode);
459     void AddExportLocalEntryItem(const ir::Statement *declNode, bool isTsModule);
460     void AddTsTypeExportLocalEntryItem(const ir::Statement *declNode, bool isTsModule,
461                                        binder::TSModuleScope *tsModuleScope);
462     parser::SourceTextModuleRecord *GetSourceTextModuleRecord();
463     parser::SourceTextModuleRecord *GetSourceTextTypeModuleRecord();
464 
465     bool ParseDirective(ArenaVector<ir::Statement *> *statements);
466     void ParseDirectivePrologue(ArenaVector<ir::Statement *> *statements);
467     ArenaVector<ir::Statement *> ParseStatementList(StatementParsingFlags flags = StatementParsingFlags::ALLOW_LEXICAL);
468     bool IsTsDeclarationStatement() const;
469     ir::Statement *ParseStatement(StatementParsingFlags flags = StatementParsingFlags::NONE);
470     ir::TSModuleDeclaration *ParseTsModuleDeclaration(bool isDeclare, bool isExport = false);
471     ir::TSModuleDeclaration *ParseTsAmbientExternalModuleDeclaration(const lexer::SourcePosition &startLoc,
472                                                                      bool isDeclare);
473     ir::TSModuleDeclaration *ParseTsModuleOrNamespaceDelaration(const lexer::SourcePosition &startLoc,
474                                                                 bool isDeclare,
475                                                                 bool isExport);
476 
477     ir::TSImportEqualsDeclaration *ParseTsImportEqualsDeclaration(const lexer::SourcePosition &startLoc,
478                                                                   bool isExport = false);
479     ir::TSNamespaceExportDeclaration *ParseTsNamespaceExportDeclaration(const lexer::SourcePosition &startLoc);
480     ir::TSModuleBlock *ParseTsModuleBlock();
481     ir::BlockStatement *ParseFunctionBody();
482     ir::BlockStatement *ParseBlockStatement();
483     ir::BlockStatement *ParseBlockStatement(binder::Scope *scope);
484     ir::EmptyStatement *ParseEmptyStatement();
485     ir::DebuggerStatement *ParseDebuggerStatement();
486     ir::BreakStatement *ParseBreakStatement();
487     ir::ContinueStatement *ParseContinueStatement();
488     ir::DoWhileStatement *ParseDoWhileStatement();
489     ir::Statement *ParsePotentialExpressionStatement(StatementParsingFlags flags, bool isDeclare);
490     ir::Statement *ParseVarStatement(bool isDeclare);
491     ir::Statement *ParseLetStatement(StatementParsingFlags flags, bool isDeclare);
492     ir::Statement *ParseConstStatement(StatementParsingFlags flags, bool isDeclare);
493     ir::Statement *ParseExpressionStatement(StatementParsingFlags flags = StatementParsingFlags::NONE);
494     ir::Statement *ParseFunctionStatement(StatementParsingFlags flags, bool isDeclare);
495     ir::FunctionDeclaration *ParseFunctionDeclaration(bool canBeAnonymous = false,
496                                                       ParserStatus newStatus = ParserStatus::NO_OPTS,
497                                                       bool isDeclare = false);
498     void AddFunctionToBinder(ir::ScriptFunction *func, ParserStatus newStatus);
499     void CheckOptionalBindingPatternParameter(ir::ScriptFunction *func) const;
500     ir::Statement *ParseExportDeclaration(StatementParsingFlags flags, ArenaVector<ir::Decorator *> &&decorators);
501     std::tuple<ForStatementKind, ir::AstNode *, ir::Expression *, ir::Expression *> ParseForInOf(
502         ir::Expression *leftNode, ExpressionParseFlags exprFlags, bool isAwait);
503     std::tuple<ForStatementKind, ir::Expression *, ir::Expression *> ParseForInOf(ir::AstNode *initNode,
504                                                                                   ExpressionParseFlags exprFlags,
505                                                                                   bool isAwait);
506     std::tuple<ir::Expression *, ir::Expression *> ParseForUpdate(bool isAwait);
507     ir::Statement *ParseForStatement();
508     ir::IfStatement *ParseIfStatement();
509 
510     ir::Statement *ParseImportDeclaration(StatementParsingFlags flags);
511     ir::LabelledStatement *ParseLabelledStatement(const lexer::LexerPosition &pos);
512     ir::ReturnStatement *ParseReturnStatement();
513     ir::ClassDeclaration *ParseClassStatement(StatementParsingFlags flags, bool isDeclare,
514                                               ArenaVector<ir::Decorator *> &&decorators, bool isAbstract = false);
515     ir::ClassDeclaration *ParseClassDeclaration(bool idRequired, ArenaVector<ir::Decorator *> &&decorators,
516                                                 bool isDeclare = false, bool isAbstract = false,
517                                                 bool isExported = false);
518     ir::TSTypeAliasDeclaration *ParseTsTypeAliasDeclaration(bool isDeclare);
519     ir::TSEnumDeclaration *ParseEnumMembers(ir::Identifier *key, const lexer::SourcePosition &enumStart,
520                                             bool isExport, bool isDeclare, bool isConst);
521     ir::TSEnumDeclaration *ParseEnumDeclaration(bool isExport = false, bool isDeclare = false, bool isConst = false);
522     ir::TSInterfaceDeclaration *ParseTsInterfaceDeclaration(bool isDeclare);
523     ir::SwitchCaseStatement *ParseSwitchCaseStatement(bool *seenDefault);
524     ir::SwitchStatement *ParseSwitchStatement();
525     ir::ThrowStatement *ParseThrowStatement();
526     ir::Expression *ParseCatchParam();
527     ir::CatchClause *ParseCatchClause();
528     ir::TryStatement *ParseTryStatement();
529     void ValidateDeclaratorId();
530     ir::VariableDeclarator *ParseVariableDeclaratorInitializer(ir::Expression *init, VariableParsingFlags flags,
531                                                                const lexer::SourcePosition &startLoc, bool isDeclare);
532     ir::VariableDeclarator *ParseVariableDeclarator(VariableParsingFlags flags, bool isDeclare);
533     ir::Statement *ParseVariableDeclaration(VariableParsingFlags flags = VariableParsingFlags::NO_OPTS,
534                                             bool isDeclare = false, bool isExport = false);
535     ir::WhileStatement *ParseWhileStatement();
536     ir::VariableDeclaration *ParseContextualLet(VariableParsingFlags flags,
537                                                 StatementParsingFlags stmFlags = StatementParsingFlags::ALLOW_LEXICAL,
538                                                 bool isDeclare = false);
539 
540     util::StringView GetNamespaceExportInternalName()
541     {
542         std::string name = std::string(parser::SourceTextModuleRecord::ANONY_NAMESPACE_NAME) +
543                            std::to_string(namespaceExportCount_++);
544         util::UString internalName(name, Allocator());
545         return internalName.View();
546     }
547 
548     binder::Binder *Binder()
549     {
550         return program_.Binder();
551     }
552     static constexpr unsigned maxRecursionDepth = 1024;
553 
554     inline void RecursiveDepthCheck()
555     {
556         if (recursiveDepth_ < maxRecursionDepth) {
557             return;
558         }
559         RecursiveDepthException();
560     }
561 
562     void RecursiveDepthException();
563     // RAII to recursive depth tracking.
564     class TrackRecursive {
565     public:
566         explicit TrackRecursive(ParserImpl *parser) : parser_(parser)
567         {
568             ++parser_->recursiveDepth_;
569         }
570         ~TrackRecursive()
571         {
572             --parser_->recursiveDepth_;
573         }
574     private:
575         ParserImpl *const parser_;
576     };
577 
578     friend class Lexer;
579     friend class SavedParserContext;
580     friend class ArrowFunctionContext;
581 
582     Program program_;
583     ParserContext context_;
584     lexer::Lexer *lexer_ {nullptr};
585     size_t namespaceExportCount_ {0};
586     size_t recursiveDepth_{0};
587 };
588 
589 // Declare a RAII recursive tracker. Check whether the recursion limit has
590 // been exceeded, if so, throw a generic error.
591 // The macro only works from inside parserImpl methods.
592 #define CHECK_PARSER_RECURSIVE_DEPTH                  \
593     TrackRecursive trackRecursive{this};       \
594     RecursiveDepthCheck()
595 
596 template <ParserStatus status>
597 class SavedStatusContext {
598 public:
SavedStatusContext(ParserContext * ctx)599     explicit SavedStatusContext(ParserContext *ctx)
600         // NOLINTNEXTLINE(readability-magic-numbers)
601         : ctx_(ctx), savedStatus_(static_cast<ParserStatus>(ctx->Status()))
602     {
603         // NOLINTNEXTLINE(readability-magic-numbers)
604         ctx->Status() |= status;
605     }
606 
607     NO_COPY_SEMANTIC(SavedStatusContext);
608     NO_MOVE_SEMANTIC(SavedStatusContext);
609 
~SavedStatusContext()610     ~SavedStatusContext()
611     {
612         ctx_->Status() = savedStatus_;
613     }
614 
615 private:
616     ParserContext *ctx_;
617     ParserStatus savedStatus_;
618 };
619 
620 class SwitchContext : public SavedStatusContext<ParserStatus::IN_SWITCH> {
621 public:
SwitchContext(ParserContext * ctx)622     explicit SwitchContext(ParserContext *ctx) : SavedStatusContext(ctx) {}
623     NO_COPY_SEMANTIC(SwitchContext);
624     NO_MOVE_SEMANTIC(SwitchContext);
625     ~SwitchContext() = default;
626 };
627 
628 template <typename T>
629 class IterationContext : public SavedStatusContext<ParserStatus::IN_ITERATION> {
630 public:
IterationContext(ParserContext * ctx,binder::Binder * binder)631     explicit IterationContext(ParserContext *ctx, binder::Binder *binder)
632         : SavedStatusContext(ctx), lexicalScope_(binder)
633     {
634     }
635 
636     NO_COPY_SEMANTIC(IterationContext);
637     NO_MOVE_SEMANTIC(IterationContext);
638     ~IterationContext() = default;
639 
LexicalScope()640     const auto &LexicalScope() const
641     {
642         return lexicalScope_;
643     }
644 
645 private:
646     binder::LexicalScope<T> lexicalScope_;
647 };
648 
649 class FunctionParameterContext : public SavedStatusContext<ParserStatus::FUNCTION_PARAM> {
650 public:
FunctionParameterContext(ParserContext * ctx,binder::Binder * binder)651     explicit FunctionParameterContext(ParserContext *ctx, binder::Binder *binder)
652         : SavedStatusContext(ctx), lexicalScope_(binder)
653     {
654     }
655 
LexicalScope()656     const auto &LexicalScope() const
657     {
658         return lexicalScope_;
659     }
660 
661     NO_COPY_SEMANTIC(FunctionParameterContext);
662     NO_MOVE_SEMANTIC(FunctionParameterContext);
663     ~FunctionParameterContext() = default;
664 
665 private:
666     binder::LexicalScope<binder::FunctionParamScope> lexicalScope_;
667 };
668 
669 class SavedParserContext {
670 public:
671     template <typename... Args>
SavedParserContext(ParserImpl * parser,Args &&...args)672     explicit SavedParserContext(ParserImpl *parser, Args &&... args) : parser_(parser), prev_(parser->context_)
673     {
674         parser_->context_ = ParserContext(&prev_, std::forward<Args>(args)...);
675     }
676 
677     NO_COPY_SEMANTIC(SavedParserContext);
678     DEFAULT_MOVE_SEMANTIC(SavedParserContext);
679 
~SavedParserContext()680     ~SavedParserContext()
681     {
682         parser_->context_ = prev_;
683     }
684 
685 protected:
Binder()686     binder::Binder *Binder()
687     {
688         return parser_->Binder();
689     }
690 
691     ParserImpl *parser_;
692     ParserContext prev_;
693 };
694 
695 class FunctionContext : public SavedParserContext {
696 public:
FunctionContext(ParserImpl * parser,ParserStatus newStatus)697     explicit FunctionContext(ParserImpl *parser, ParserStatus newStatus) : SavedParserContext(parser, newStatus)
698     {
699         if (newStatus & ParserStatus::GENERATOR_FUNCTION) {
700             flags_ |= ir::ScriptFunctionFlags::GENERATOR;
701         }
702 
703         if (newStatus & ParserStatus::ASYNC_FUNCTION) {
704             flags_ |= ir::ScriptFunctionFlags::ASYNC;
705         }
706 
707         if (newStatus & ParserStatus::CONSTRUCTOR_FUNCTION) {
708             flags_ |= ir::ScriptFunctionFlags::CONSTRUCTOR;
709         }
710     }
711 
Flags()712     ir::ScriptFunctionFlags Flags() const
713     {
714         return flags_;
715     }
716 
AddFlag(ir::ScriptFunctionFlags flags)717     void AddFlag(ir::ScriptFunctionFlags flags)
718     {
719         flags_ |= flags;
720     }
721 
722     NO_COPY_SEMANTIC(FunctionContext);
723     NO_MOVE_SEMANTIC(FunctionContext);
724     ~FunctionContext() = default;
725 
726 protected:
727     ir::ScriptFunctionFlags flags_ {ir::ScriptFunctionFlags::NONE};
728 };
729 
730 class ArrowFunctionContext : public FunctionContext {
731 public:
ArrowFunctionContext(ParserImpl * parser,bool isAsync)732     explicit ArrowFunctionContext(ParserImpl *parser, bool isAsync)
733         : FunctionContext(parser, InitialFlags(parser->context_.Status()))
734     {
735         if (isAsync) {
736             AddFlag(ir::ScriptFunctionFlags::ASYNC);
737         }
738 
739         AddFlag(ir::ScriptFunctionFlags::ARROW);
740     }
741 
742     NO_COPY_SEMANTIC(ArrowFunctionContext);
743     NO_MOVE_SEMANTIC(ArrowFunctionContext);
744     ~ArrowFunctionContext() = default;
745 
746 private:
InitialFlags(ParserStatus currentStatus)747     static ParserStatus InitialFlags(ParserStatus currentStatus)
748     {
749         return ParserStatus::FUNCTION | ParserStatus::ARROW_FUNCTION |
750                static_cast<ParserStatus>(currentStatus & (ParserStatus::ALLOW_SUPER | ParserStatus::ALLOW_SUPER_CALL));
751     }
752 };
753 
754 }  // namespace panda::es2panda::parser
755 
756 #endif
757