• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2018 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef V8_TORQUE_AST_H_
6 #define V8_TORQUE_AST_H_
7 
8 #include <algorithm>
9 #include <iostream>
10 #include <map>
11 #include <memory>
12 #include <set>
13 #include <string>
14 #include <vector>
15 
16 #include "src/base/optional.h"
17 #include "src/torque/constants.h"
18 #include "src/torque/source-positions.h"
19 #include "src/torque/utils.h"
20 
21 namespace v8 {
22 namespace internal {
23 namespace torque {
24 
25 #define AST_EXPRESSION_NODE_KIND_LIST(V) \
26   V(CallExpression)                      \
27   V(CallMethodExpression)                \
28   V(IntrinsicCallExpression)             \
29   V(StructExpression)                    \
30   V(LogicalOrExpression)                 \
31   V(LogicalAndExpression)                \
32   V(SpreadExpression)                    \
33   V(ConditionalExpression)               \
34   V(IdentifierExpression)                \
35   V(StringLiteralExpression)             \
36   V(NumberLiteralExpression)             \
37   V(FieldAccessExpression)               \
38   V(ElementAccessExpression)             \
39   V(DereferenceExpression)               \
40   V(AssignmentExpression)                \
41   V(IncrementDecrementExpression)        \
42   V(NewExpression)                       \
43   V(AssumeTypeImpossibleExpression)      \
44   V(StatementExpression)                 \
45   V(TryLabelExpression)
46 
47 #define AST_TYPE_EXPRESSION_NODE_KIND_LIST(V) \
48   V(BasicTypeExpression)                      \
49   V(FunctionTypeExpression)                   \
50   V(PrecomputedTypeExpression)                \
51   V(UnionTypeExpression)
52 
53 #define AST_STATEMENT_NODE_KIND_LIST(V) \
54   V(BlockStatement)                     \
55   V(ExpressionStatement)                \
56   V(IfStatement)                        \
57   V(WhileStatement)                     \
58   V(ForLoopStatement)                   \
59   V(BreakStatement)                     \
60   V(ContinueStatement)                  \
61   V(ReturnStatement)                    \
62   V(DebugStatement)                     \
63   V(AssertStatement)                    \
64   V(TailCallStatement)                  \
65   V(VarDeclarationStatement)            \
66   V(GotoStatement)
67 
68 #define AST_TYPE_DECLARATION_NODE_KIND_LIST(V) \
69   V(AbstractTypeDeclaration)                   \
70   V(TypeAliasDeclaration)                      \
71   V(BitFieldStructDeclaration)                 \
72   V(ClassDeclaration)                          \
73   V(StructDeclaration)
74 
75 #define AST_DECLARATION_NODE_KIND_LIST(V) \
76   AST_TYPE_DECLARATION_NODE_KIND_LIST(V)  \
77   V(GenericCallableDeclaration)           \
78   V(GenericTypeDeclaration)               \
79   V(SpecializationDeclaration)            \
80   V(ExternConstDeclaration)               \
81   V(NamespaceDeclaration)                 \
82   V(ConstDeclaration)                     \
83   V(CppIncludeDeclaration)                \
84   V(TorqueMacroDeclaration)               \
85   V(TorqueBuiltinDeclaration)             \
86   V(ExternalMacroDeclaration)             \
87   V(ExternalBuiltinDeclaration)           \
88   V(ExternalRuntimeDeclaration)           \
89   V(IntrinsicDeclaration)
90 
91 #define AST_NODE_KIND_LIST(V)           \
92   AST_EXPRESSION_NODE_KIND_LIST(V)      \
93   AST_TYPE_EXPRESSION_NODE_KIND_LIST(V) \
94   AST_STATEMENT_NODE_KIND_LIST(V)       \
95   AST_DECLARATION_NODE_KIND_LIST(V)     \
96   V(Identifier)                         \
97   V(TryHandler)                         \
98   V(ClassBody)
99 
100 struct AstNode {
101  public:
102   enum class Kind {
103 #define ENUM_ITEM(name) k##name,
104     AST_NODE_KIND_LIST(ENUM_ITEM)
105 #undef ENUM_ITEM
106   };
107 
AstNodeAstNode108   AstNode(Kind kind, SourcePosition pos) : kind(kind), pos(pos) {}
109   virtual ~AstNode() = default;
110 
111   const Kind kind;
112   SourcePosition pos;
113 };
114 
115 struct AstNodeClassCheck {
116   template <class T>
117   static bool IsInstanceOf(AstNode* node);
118 };
119 
120 // Boilerplate for most derived classes.
121 #define DEFINE_AST_NODE_LEAF_BOILERPLATE(T)  \
122   static const Kind kKind = Kind::k##T;      \
123   static T* cast(AstNode* node) {            \
124     DCHECK_EQ(node->kind, kKind);            \
125     return static_cast<T*>(node);            \
126   }                                          \
127   static T* DynamicCast(AstNode* node) {     \
128     if (!node) return nullptr;               \
129     if (node->kind != kKind) return nullptr; \
130     return static_cast<T*>(node);            \
131   }
132 
133 // Boilerplate for classes with subclasses.
134 #define DEFINE_AST_NODE_INNER_BOILERPLATE(T)                       \
135   static T* cast(AstNode* node) {                                  \
136     DCHECK(AstNodeClassCheck::IsInstanceOf<T>(node));              \
137     return static_cast<T*>(node);                                  \
138   }                                                                \
139   static T* DynamicCast(AstNode* node) {                           \
140     if (!node) return nullptr;                                     \
141     if (!AstNodeClassCheck::IsInstanceOf<T>(node)) return nullptr; \
142     return static_cast<T*>(node);                                  \
143   }
144 
145 struct Expression : AstNode {
ExpressionExpression146   Expression(Kind kind, SourcePosition pos) : AstNode(kind, pos) {}
147   DEFINE_AST_NODE_INNER_BOILERPLATE(Expression)
148 
149   using VisitCallback = std::function<void(Expression*)>;
VisitAllSubExpressionsExpression150   virtual void VisitAllSubExpressions(VisitCallback callback) {
151     // TODO(szuend): Hoist this up to AstNode and make it a
152     //               general Ast visitor.
153   }
154 };
155 
156 struct LocationExpression : Expression {
LocationExpressionLocationExpression157   LocationExpression(Kind kind, SourcePosition pos) : Expression(kind, pos) {}
158   DEFINE_AST_NODE_INNER_BOILERPLATE(LocationExpression)
159 };
160 
161 struct TypeExpression : AstNode {
TypeExpressionTypeExpression162   TypeExpression(Kind kind, SourcePosition pos) : AstNode(kind, pos) {}
163   DEFINE_AST_NODE_INNER_BOILERPLATE(TypeExpression)
164 };
165 
166 struct Declaration : AstNode {
DeclarationDeclaration167   Declaration(Kind kind, SourcePosition pos) : AstNode(kind, pos) {}
168   DEFINE_AST_NODE_INNER_BOILERPLATE(Declaration)
169 };
170 
171 struct Statement : AstNode {
StatementStatement172   Statement(Kind kind, SourcePosition pos) : AstNode(kind, pos) {}
173   DEFINE_AST_NODE_INNER_BOILERPLATE(Statement)
174 };
175 
176 class Namespace;
177 
178 struct NamespaceDeclaration : Declaration {
179   DEFINE_AST_NODE_LEAF_BOILERPLATE(NamespaceDeclaration)
NamespaceDeclarationNamespaceDeclaration180   NamespaceDeclaration(SourcePosition pos, std::string name,
181                        std::vector<Declaration*> declarations)
182       : Declaration(kKind, pos),
183         declarations(std::move(declarations)),
184         name(name) {}
185   std::vector<Declaration*> declarations;
186   std::string name;
187 };
188 
189 struct EnumDescription {
190   SourcePosition pos;
191   std::string name;
192   std::string constexpr_generates;
193   bool is_open;
194   std::vector<std::string> entries;
195 
196   EnumDescription(SourcePosition pos, std::string name,
197                   std::string constexpr_generates, bool is_open,
198                   std::vector<std::string> entries = {})
posEnumDescription199       : pos(std::move(pos)),
200         name(std::move(name)),
201         constexpr_generates(std::move(constexpr_generates)),
202         is_open(is_open),
203         entries(std::move(entries)) {}
204 };
205 
206 class Ast {
207  public:
208   Ast() = default;
209 
declarations()210   std::vector<Declaration*>& declarations() { return declarations_; }
declarations()211   const std::vector<Declaration*>& declarations() const {
212     return declarations_;
213   }
214   template <class T>
AddNode(std::unique_ptr<T> node)215   T* AddNode(std::unique_ptr<T> node) {
216     T* result = node.get();
217     nodes_.push_back(std::move(node));
218     return result;
219   }
220 
DeclareImportForCurrentFile(SourceId import_id)221   void DeclareImportForCurrentFile(SourceId import_id) {
222     declared_imports_[CurrentSourcePosition::Get().source].insert(import_id);
223   }
224 
AddEnumDescription(EnumDescription description)225   void AddEnumDescription(EnumDescription description) {
226     std::string name = description.name;
227     DCHECK(!name.empty());
228     auto f = [&](const auto& d) { return d.name == name; };
229     USE(f);  // Suppress unused in release.
230     DCHECK_EQ(
231         std::find_if(enum_descriptions_.begin(), enum_descriptions_.end(), f),
232         enum_descriptions_.end());
233     enum_descriptions_.push_back(std::move(description));
234   }
235 
EnumDescriptions()236   std::vector<EnumDescription>& EnumDescriptions() {
237     return enum_descriptions_;
238   }
239 
240  private:
241   std::vector<Declaration*> declarations_;
242   std::vector<std::unique_ptr<AstNode>> nodes_;
243   std::map<SourceId, std::set<SourceId>> declared_imports_;
244   std::vector<EnumDescription> enum_descriptions_;
245 };
246 
247 static const char* const kThisParameterName = "this";
248 
249 // A Identifier is a string with a SourcePosition attached.
250 struct Identifier : AstNode {
251   DEFINE_AST_NODE_LEAF_BOILERPLATE(Identifier)
IdentifierIdentifier252   Identifier(SourcePosition pos, std::string identifier)
253       : AstNode(kKind, pos), value(std::move(identifier)) {}
254   std::string value;
255 };
256 
257 inline std::ostream& operator<<(std::ostream& os, Identifier* id) {
258   return os << id->value;
259 }
260 
261 struct IdentifierPtrValueEq {
operatorIdentifierPtrValueEq262   bool operator()(const Identifier* a, const Identifier* b) {
263     return a->value < b->value;
264   }
265 };
266 
267 struct IdentifierExpression : LocationExpression {
268   DEFINE_AST_NODE_LEAF_BOILERPLATE(IdentifierExpression)
269   IdentifierExpression(SourcePosition pos,
270                        std::vector<std::string> namespace_qualification,
271                        Identifier* name, std::vector<TypeExpression*> args = {})
LocationExpressionIdentifierExpression272       : LocationExpression(kKind, pos),
273         namespace_qualification(std::move(namespace_qualification)),
274         name(name),
275         generic_arguments(std::move(args)) {}
276   IdentifierExpression(SourcePosition pos, Identifier* name,
277                        std::vector<TypeExpression*> args = {})
278       : IdentifierExpression(pos, {}, name, std::move(args)) {}
IsThisIdentifierExpression279   bool IsThis() const { return name->value == kThisParameterName; }
280 
VisitAllSubExpressionsIdentifierExpression281   void VisitAllSubExpressions(VisitCallback callback) override {
282     callback(this);
283   }
284 
285   std::vector<std::string> namespace_qualification;
286   Identifier* name;
287   std::vector<TypeExpression*> generic_arguments;
288 };
289 
290 struct IntrinsicCallExpression : Expression {
291   DEFINE_AST_NODE_LEAF_BOILERPLATE(IntrinsicCallExpression)
IntrinsicCallExpressionIntrinsicCallExpression292   IntrinsicCallExpression(SourcePosition pos, Identifier* name,
293                           std::vector<TypeExpression*> generic_arguments,
294                           std::vector<Expression*> arguments)
295       : Expression(kKind, pos),
296         name(name),
297         generic_arguments(std::move(generic_arguments)),
298         arguments(std::move(arguments)) {}
299 
VisitAllSubExpressionsIntrinsicCallExpression300   void VisitAllSubExpressions(VisitCallback callback) override {
301     for (auto argument : arguments) {
302       argument->VisitAllSubExpressions(callback);
303     }
304     callback(this);
305   }
306 
307   Identifier* name;
308   std::vector<TypeExpression*> generic_arguments;
309   std::vector<Expression*> arguments;
310 };
311 
312 struct CallMethodExpression : Expression {
313   DEFINE_AST_NODE_LEAF_BOILERPLATE(CallMethodExpression)
CallMethodExpressionCallMethodExpression314   CallMethodExpression(SourcePosition pos, Expression* target,
315                        IdentifierExpression* method,
316                        std::vector<Expression*> arguments,
317                        std::vector<Identifier*> labels)
318       : Expression(kKind, pos),
319         target(target),
320         method(method),
321         arguments(std::move(arguments)),
322         labels(std::move(labels)) {}
323 
VisitAllSubExpressionsCallMethodExpression324   void VisitAllSubExpressions(VisitCallback callback) override {
325     target->VisitAllSubExpressions(callback);
326     method->VisitAllSubExpressions(callback);
327     for (auto argument : arguments) {
328       argument->VisitAllSubExpressions(callback);
329     }
330     callback(this);
331   }
332 
333   Expression* target;
334   IdentifierExpression* method;
335   std::vector<Expression*> arguments;
336   std::vector<Identifier*> labels;
337 };
338 
339 struct CallExpression : Expression {
340   DEFINE_AST_NODE_LEAF_BOILERPLATE(CallExpression)
CallExpressionCallExpression341   CallExpression(SourcePosition pos, IdentifierExpression* callee,
342                  std::vector<Expression*> arguments,
343                  std::vector<Identifier*> labels)
344       : Expression(kKind, pos),
345         callee(callee),
346         arguments(std::move(arguments)),
347         labels(std::move(labels)) {}
348 
VisitAllSubExpressionsCallExpression349   void VisitAllSubExpressions(VisitCallback callback) override {
350     callee->VisitAllSubExpressions(callback);
351     for (auto argument : arguments) {
352       argument->VisitAllSubExpressions(callback);
353     }
354     callback(this);
355   }
356 
357   IdentifierExpression* callee;
358   std::vector<Expression*> arguments;
359   std::vector<Identifier*> labels;
360 };
361 
362 struct NameAndExpression {
363   Identifier* name;
364   Expression* expression;
365 };
366 
367 struct StructExpression : Expression {
368   DEFINE_AST_NODE_LEAF_BOILERPLATE(StructExpression)
StructExpressionStructExpression369   StructExpression(SourcePosition pos, TypeExpression* type,
370                    std::vector<NameAndExpression> initializers)
371       : Expression(kKind, pos),
372         type(type),
373         initializers(std::move(initializers)) {}
374 
VisitAllSubExpressionsStructExpression375   void VisitAllSubExpressions(VisitCallback callback) override {
376     for (auto& initializer : initializers) {
377       initializer.expression->VisitAllSubExpressions(callback);
378     }
379     callback(this);
380   }
381 
382   TypeExpression* type;
383   std::vector<NameAndExpression> initializers;
384 };
385 
386 struct LogicalOrExpression : Expression {
387   DEFINE_AST_NODE_LEAF_BOILERPLATE(LogicalOrExpression)
LogicalOrExpressionLogicalOrExpression388   LogicalOrExpression(SourcePosition pos, Expression* left, Expression* right)
389       : Expression(kKind, pos), left(left), right(right) {}
390 
VisitAllSubExpressionsLogicalOrExpression391   void VisitAllSubExpressions(VisitCallback callback) override {
392     left->VisitAllSubExpressions(callback);
393     right->VisitAllSubExpressions(callback);
394     callback(this);
395   }
396 
397   Expression* left;
398   Expression* right;
399 };
400 
401 struct LogicalAndExpression : Expression {
402   DEFINE_AST_NODE_LEAF_BOILERPLATE(LogicalAndExpression)
LogicalAndExpressionLogicalAndExpression403   LogicalAndExpression(SourcePosition pos, Expression* left, Expression* right)
404       : Expression(kKind, pos), left(left), right(right) {}
405 
VisitAllSubExpressionsLogicalAndExpression406   void VisitAllSubExpressions(VisitCallback callback) override {
407     left->VisitAllSubExpressions(callback);
408     right->VisitAllSubExpressions(callback);
409     callback(this);
410   }
411 
412   Expression* left;
413   Expression* right;
414 };
415 
416 struct SpreadExpression : Expression {
417   DEFINE_AST_NODE_LEAF_BOILERPLATE(SpreadExpression)
SpreadExpressionSpreadExpression418   SpreadExpression(SourcePosition pos, Expression* spreadee)
419       : Expression(kKind, pos), spreadee(spreadee) {}
420 
VisitAllSubExpressionsSpreadExpression421   void VisitAllSubExpressions(VisitCallback callback) override {
422     spreadee->VisitAllSubExpressions(callback);
423     callback(this);
424   }
425 
426   Expression* spreadee;
427 };
428 
429 struct ConditionalExpression : Expression {
430   DEFINE_AST_NODE_LEAF_BOILERPLATE(ConditionalExpression)
ConditionalExpressionConditionalExpression431   ConditionalExpression(SourcePosition pos, Expression* condition,
432                         Expression* if_true, Expression* if_false)
433       : Expression(kKind, pos),
434         condition(condition),
435         if_true(if_true),
436         if_false(if_false) {}
437 
VisitAllSubExpressionsConditionalExpression438   void VisitAllSubExpressions(VisitCallback callback) override {
439     condition->VisitAllSubExpressions(callback);
440     if_true->VisitAllSubExpressions(callback);
441     if_false->VisitAllSubExpressions(callback);
442     callback(this);
443   }
444 
445   Expression* condition;
446   Expression* if_true;
447   Expression* if_false;
448 };
449 
450 struct StringLiteralExpression : Expression {
451   DEFINE_AST_NODE_LEAF_BOILERPLATE(StringLiteralExpression)
StringLiteralExpressionStringLiteralExpression452   StringLiteralExpression(SourcePosition pos, std::string literal)
453       : Expression(kKind, pos), literal(std::move(literal)) {}
454 
VisitAllSubExpressionsStringLiteralExpression455   void VisitAllSubExpressions(VisitCallback callback) override {
456     callback(this);
457   }
458 
459   std::string literal;
460 };
461 
462 struct NumberLiteralExpression : Expression {
463   DEFINE_AST_NODE_LEAF_BOILERPLATE(NumberLiteralExpression)
NumberLiteralExpressionNumberLiteralExpression464   NumberLiteralExpression(SourcePosition pos, double number)
465       : Expression(kKind, pos), number(number) {}
466 
VisitAllSubExpressionsNumberLiteralExpression467   void VisitAllSubExpressions(VisitCallback callback) override {
468     callback(this);
469   }
470 
471   double number;
472 };
473 
474 struct ElementAccessExpression : LocationExpression {
475   DEFINE_AST_NODE_LEAF_BOILERPLATE(ElementAccessExpression)
ElementAccessExpressionElementAccessExpression476   ElementAccessExpression(SourcePosition pos, Expression* array,
477                           Expression* index)
478       : LocationExpression(kKind, pos), array(array), index(index) {}
479 
VisitAllSubExpressionsElementAccessExpression480   void VisitAllSubExpressions(VisitCallback callback) override {
481     array->VisitAllSubExpressions(callback);
482     index->VisitAllSubExpressions(callback);
483     callback(this);
484   }
485 
486   Expression* array;
487   Expression* index;
488 };
489 
490 struct FieldAccessExpression : LocationExpression {
491   DEFINE_AST_NODE_LEAF_BOILERPLATE(FieldAccessExpression)
FieldAccessExpressionFieldAccessExpression492   FieldAccessExpression(SourcePosition pos, Expression* object,
493                         Identifier* field)
494       : LocationExpression(kKind, pos), object(object), field(field) {}
495 
VisitAllSubExpressionsFieldAccessExpression496   void VisitAllSubExpressions(VisitCallback callback) override {
497     object->VisitAllSubExpressions(callback);
498     callback(this);
499   }
500 
501   Expression* object;
502   Identifier* field;
503 };
504 
505 struct DereferenceExpression : LocationExpression {
506   DEFINE_AST_NODE_LEAF_BOILERPLATE(DereferenceExpression)
DereferenceExpressionDereferenceExpression507   DereferenceExpression(SourcePosition pos, Expression* reference)
508       : LocationExpression(kKind, pos), reference(reference) {}
509 
VisitAllSubExpressionsDereferenceExpression510   void VisitAllSubExpressions(VisitCallback callback) override {
511     reference->VisitAllSubExpressions(callback);
512     callback(this);
513   }
514 
515   Expression* reference;
516 };
517 
518 struct AssignmentExpression : Expression {
519   DEFINE_AST_NODE_LEAF_BOILERPLATE(AssignmentExpression)
AssignmentExpressionAssignmentExpression520   AssignmentExpression(SourcePosition pos, Expression* location,
521                        Expression* value)
522       : AssignmentExpression(pos, location, base::nullopt, value) {}
AssignmentExpressionAssignmentExpression523   AssignmentExpression(SourcePosition pos, Expression* location,
524                        base::Optional<std::string> op, Expression* value)
525       : Expression(kKind, pos),
526         location(location),
527         op(std::move(op)),
528         value(value) {}
529 
VisitAllSubExpressionsAssignmentExpression530   void VisitAllSubExpressions(VisitCallback callback) override {
531     location->VisitAllSubExpressions(callback);
532     value->VisitAllSubExpressions(callback);
533     callback(this);
534   }
535 
536   Expression* location;
537   base::Optional<std::string> op;
538   Expression* value;
539 };
540 
541 enum class IncrementDecrementOperator { kIncrement, kDecrement };
542 
543 struct IncrementDecrementExpression : Expression {
544   DEFINE_AST_NODE_LEAF_BOILERPLATE(IncrementDecrementExpression)
IncrementDecrementExpressionIncrementDecrementExpression545   IncrementDecrementExpression(SourcePosition pos, Expression* location,
546                                IncrementDecrementOperator op, bool postfix)
547       : Expression(kKind, pos), location(location), op(op), postfix(postfix) {}
548 
VisitAllSubExpressionsIncrementDecrementExpression549   void VisitAllSubExpressions(VisitCallback callback) override {
550     location->VisitAllSubExpressions(callback);
551     callback(this);
552   }
553 
554   Expression* location;
555   IncrementDecrementOperator op;
556   bool postfix;
557 };
558 
559 // This expression is only used in the desugaring of typeswitch, and it allows
560 // to bake in the static information that certain types are impossible at a
561 // certain position in the control flow.
562 // The result type is the type of {expression} minus the provided type.
563 struct AssumeTypeImpossibleExpression : Expression {
564   DEFINE_AST_NODE_LEAF_BOILERPLATE(AssumeTypeImpossibleExpression)
AssumeTypeImpossibleExpressionAssumeTypeImpossibleExpression565   AssumeTypeImpossibleExpression(SourcePosition pos,
566                                  TypeExpression* excluded_type,
567                                  Expression* expression)
568       : Expression(kKind, pos),
569         excluded_type(excluded_type),
570         expression(expression) {}
571 
VisitAllSubExpressionsAssumeTypeImpossibleExpression572   void VisitAllSubExpressions(VisitCallback callback) override {
573     expression->VisitAllSubExpressions(callback);
574     callback(this);
575   }
576 
577   TypeExpression* excluded_type;
578   Expression* expression;
579 };
580 
581 struct NewExpression : Expression {
582   DEFINE_AST_NODE_LEAF_BOILERPLATE(NewExpression)
NewExpressionNewExpression583   NewExpression(SourcePosition pos, TypeExpression* type,
584                 std::vector<NameAndExpression> initializers, bool pretenured)
585       : Expression(kKind, pos),
586         type(type),
587         initializers(std::move(initializers)),
588         pretenured(pretenured) {}
589 
VisitAllSubExpressionsNewExpression590   void VisitAllSubExpressions(VisitCallback callback) override {
591     for (auto& initializer : initializers) {
592       initializer.expression->VisitAllSubExpressions(callback);
593     }
594     callback(this);
595   }
596 
597   TypeExpression* type;
598   std::vector<NameAndExpression> initializers;
599   bool pretenured;
600 };
601 
602 enum class ImplicitKind { kNoImplicit, kJSImplicit, kImplicit };
603 
604 struct ParameterList {
605   std::vector<Identifier*> names;
606   std::vector<TypeExpression*> types;
607   ImplicitKind implicit_kind = ImplicitKind::kNoImplicit;
608   SourcePosition implicit_kind_pos = SourcePosition::Invalid();
609   size_t implicit_count = 0;
610   bool has_varargs = false;
611   std::string arguments_variable = "";
612 
EmptyParameterList613   static ParameterList Empty() { return {}; }
GetImplicitTypesParameterList614   std::vector<TypeExpression*> GetImplicitTypes() {
615     return std::vector<TypeExpression*>(types.begin(),
616                                         types.begin() + implicit_count);
617   }
GetExplicitTypesParameterList618   std::vector<TypeExpression*> GetExplicitTypes() {
619     return std::vector<TypeExpression*>(types.begin() + implicit_count,
620                                         types.end());
621   }
622 };
623 
624 struct BasicTypeExpression : TypeExpression {
625   DEFINE_AST_NODE_LEAF_BOILERPLATE(BasicTypeExpression)
BasicTypeExpressionBasicTypeExpression626   BasicTypeExpression(SourcePosition pos,
627                       std::vector<std::string> namespace_qualification,
628                       std::string name,
629                       std::vector<TypeExpression*> generic_arguments)
630       : TypeExpression(kKind, pos),
631         namespace_qualification(std::move(namespace_qualification)),
632         is_constexpr(IsConstexprName(name)),
633         name(std::move(name)),
634         generic_arguments(std::move(generic_arguments)) {}
BasicTypeExpressionBasicTypeExpression635   BasicTypeExpression(SourcePosition pos, std::string name)
636       : BasicTypeExpression(pos, {}, std::move(name), {}) {}
637   std::vector<std::string> namespace_qualification;
638   bool is_constexpr;
639   std::string name;
640   std::vector<TypeExpression*> generic_arguments;
641 };
642 
643 struct FunctionTypeExpression : TypeExpression {
644   DEFINE_AST_NODE_LEAF_BOILERPLATE(FunctionTypeExpression)
FunctionTypeExpressionFunctionTypeExpression645   FunctionTypeExpression(SourcePosition pos,
646                          std::vector<TypeExpression*> parameters,
647                          TypeExpression* return_type)
648       : TypeExpression(kKind, pos),
649         parameters(std::move(parameters)),
650         return_type(return_type) {}
651   std::vector<TypeExpression*> parameters;
652   TypeExpression* return_type;
653 };
654 
655 // A PrecomputedTypeExpression is never created directly by the parser. Later
656 // stages can use this to insert AST snippets where the type has already been
657 // resolved.
658 class Type;
659 struct PrecomputedTypeExpression : TypeExpression {
660   DEFINE_AST_NODE_LEAF_BOILERPLATE(PrecomputedTypeExpression)
PrecomputedTypeExpressionPrecomputedTypeExpression661   PrecomputedTypeExpression(SourcePosition pos, const Type* type)
662       : TypeExpression(kKind, pos), type(type) {}
663   const Type* type;
664 };
665 
666 struct UnionTypeExpression : TypeExpression {
667   DEFINE_AST_NODE_LEAF_BOILERPLATE(UnionTypeExpression)
UnionTypeExpressionUnionTypeExpression668   UnionTypeExpression(SourcePosition pos, TypeExpression* a, TypeExpression* b)
669       : TypeExpression(kKind, pos), a(a), b(b) {}
670   TypeExpression* a;
671   TypeExpression* b;
672 };
673 
674 struct ExpressionStatement : Statement {
675   DEFINE_AST_NODE_LEAF_BOILERPLATE(ExpressionStatement)
ExpressionStatementExpressionStatement676   ExpressionStatement(SourcePosition pos, Expression* expression)
677       : Statement(kKind, pos), expression(expression) {}
678   Expression* expression;
679 };
680 
681 struct IfStatement : Statement {
682   DEFINE_AST_NODE_LEAF_BOILERPLATE(IfStatement)
IfStatementIfStatement683   IfStatement(SourcePosition pos, bool is_constexpr, Expression* condition,
684               Statement* if_true, base::Optional<Statement*> if_false)
685       : Statement(kKind, pos),
686         condition(condition),
687         is_constexpr(is_constexpr),
688         if_true(if_true),
689         if_false(if_false) {}
690   Expression* condition;
691   bool is_constexpr;
692   Statement* if_true;
693   base::Optional<Statement*> if_false;
694 };
695 
696 struct WhileStatement : Statement {
697   DEFINE_AST_NODE_LEAF_BOILERPLATE(WhileStatement)
WhileStatementWhileStatement698   WhileStatement(SourcePosition pos, Expression* condition, Statement* body)
699       : Statement(kKind, pos), condition(condition), body(body) {}
700   Expression* condition;
701   Statement* body;
702 };
703 
704 struct ReturnStatement : Statement {
705   DEFINE_AST_NODE_LEAF_BOILERPLATE(ReturnStatement)
ReturnStatementReturnStatement706   ReturnStatement(SourcePosition pos, base::Optional<Expression*> value)
707       : Statement(kKind, pos), value(value) {}
708   base::Optional<Expression*> value;
709 };
710 
711 struct DebugStatement : Statement {
712   DEFINE_AST_NODE_LEAF_BOILERPLATE(DebugStatement)
DebugStatementDebugStatement713   DebugStatement(SourcePosition pos, const std::string& reason,
714                  bool never_continues)
715       : Statement(kKind, pos),
716         reason(reason),
717         never_continues(never_continues) {}
718   std::string reason;
719   bool never_continues;
720 };
721 
722 struct AssertStatement : Statement {
723   DEFINE_AST_NODE_LEAF_BOILERPLATE(AssertStatement)
724   enum class AssertKind { kAssert, kCheck, kStaticAssert };
AssertStatementAssertStatement725   AssertStatement(SourcePosition pos, AssertKind kind, Expression* expression,
726                   std::string source)
727       : Statement(kKind, pos),
728         kind(kind),
729         expression(expression),
730         source(std::move(source)) {}
731   AssertKind kind;
732   Expression* expression;
733   std::string source;
734 };
735 
736 struct TailCallStatement : Statement {
737   DEFINE_AST_NODE_LEAF_BOILERPLATE(TailCallStatement)
TailCallStatementTailCallStatement738   TailCallStatement(SourcePosition pos, CallExpression* call)
739       : Statement(kKind, pos), call(call) {}
740   CallExpression* call;
741 };
742 
743 struct VarDeclarationStatement : Statement {
744   DEFINE_AST_NODE_LEAF_BOILERPLATE(VarDeclarationStatement)
745   VarDeclarationStatement(
746       SourcePosition pos, bool const_qualified, Identifier* name,
747       base::Optional<TypeExpression*> type,
748       base::Optional<Expression*> initializer = base::nullopt)
StatementVarDeclarationStatement749       : Statement(kKind, pos),
750         const_qualified(const_qualified),
751         name(name),
752         type(type),
753         initializer(initializer) {}
754   bool const_qualified;
755   Identifier* name;
756   base::Optional<TypeExpression*> type;
757   base::Optional<Expression*> initializer;
758 };
759 
760 struct BreakStatement : Statement {
DEFINE_AST_NODE_LEAF_BOILERPLATEBreakStatement761   DEFINE_AST_NODE_LEAF_BOILERPLATE(BreakStatement)
762   explicit BreakStatement(SourcePosition pos) : Statement(kKind, pos) {}
763 };
764 
765 struct ContinueStatement : Statement {
DEFINE_AST_NODE_LEAF_BOILERPLATEContinueStatement766   DEFINE_AST_NODE_LEAF_BOILERPLATE(ContinueStatement)
767   explicit ContinueStatement(SourcePosition pos) : Statement(kKind, pos) {}
768 };
769 
770 struct GotoStatement : Statement {
771   DEFINE_AST_NODE_LEAF_BOILERPLATE(GotoStatement)
GotoStatementGotoStatement772   GotoStatement(SourcePosition pos, Identifier* label,
773                 const std::vector<Expression*>& arguments)
774       : Statement(kKind, pos), label(label), arguments(std::move(arguments)) {}
775   Identifier* label;
776   std::vector<Expression*> arguments;
777 };
778 
779 struct ForLoopStatement : Statement {
780   DEFINE_AST_NODE_LEAF_BOILERPLATE(ForLoopStatement)
ForLoopStatementForLoopStatement781   ForLoopStatement(SourcePosition pos, base::Optional<Statement*> declaration,
782                    base::Optional<Expression*> test,
783                    base::Optional<Statement*> action, Statement* body)
784       : Statement(kKind, pos),
785         var_declaration(),
786         test(std::move(test)),
787         action(std::move(action)),
788         body(std::move(body)) {
789     if (declaration)
790       var_declaration = VarDeclarationStatement::cast(*declaration);
791   }
792   base::Optional<VarDeclarationStatement*> var_declaration;
793   base::Optional<Expression*> test;
794   base::Optional<Statement*> action;
795   Statement* body;
796 };
797 
798 struct TryHandler : AstNode {
799   DEFINE_AST_NODE_LEAF_BOILERPLATE(TryHandler)
800   enum class HandlerKind { kCatch, kLabel };
TryHandlerTryHandler801   TryHandler(SourcePosition pos, HandlerKind handler_kind, Identifier* label,
802              const ParameterList& parameters, Statement* body)
803       : AstNode(kKind, pos),
804         handler_kind(handler_kind),
805         label(label),
806         parameters(parameters),
807         body(std::move(body)) {}
808   HandlerKind handler_kind;
809   Identifier* label;
810   ParameterList parameters;
811   Statement* body;
812 };
813 
814 struct StatementExpression : Expression {
815   DEFINE_AST_NODE_LEAF_BOILERPLATE(StatementExpression)
StatementExpressionStatementExpression816   StatementExpression(SourcePosition pos, Statement* statement)
817       : Expression(kKind, pos), statement(statement) {}
818   Statement* statement;
819 };
820 
821 struct TryLabelExpression : Expression {
822   DEFINE_AST_NODE_LEAF_BOILERPLATE(TryLabelExpression)
TryLabelExpressionTryLabelExpression823   TryLabelExpression(SourcePosition pos, Expression* try_expression,
824                      TryHandler* label_block)
825       : Expression(kKind, pos),
826         try_expression(try_expression),
827         label_block(label_block) {}
828   Expression* try_expression;
829   TryHandler* label_block;
830 };
831 
832 struct BlockStatement : Statement {
DEFINE_AST_NODE_LEAF_BOILERPLATEBlockStatement833   DEFINE_AST_NODE_LEAF_BOILERPLATE(BlockStatement)
834   explicit BlockStatement(SourcePosition pos, bool deferred = false,
835                           std::vector<Statement*> statements = {})
836       : Statement(kKind, pos),
837         deferred(deferred),
838         statements(std::move(statements)) {}
839   bool deferred;
840   std::vector<Statement*> statements;
841 };
842 
843 struct TypeDeclaration : Declaration {
844   DEFINE_AST_NODE_INNER_BOILERPLATE(TypeDeclaration)
TypeDeclarationTypeDeclaration845   TypeDeclaration(Kind kKind, SourcePosition pos, Identifier* name)
846       : Declaration(kKind, pos), name(name) {}
847   Identifier* name;
848 };
849 
850 struct InstanceTypeConstraints {
InstanceTypeConstraintsInstanceTypeConstraints851   InstanceTypeConstraints() : value(-1), num_flags_bits(-1) {}
852   int value;
853   int num_flags_bits;
854 };
855 
856 struct AbstractTypeDeclaration : TypeDeclaration {
857   DEFINE_AST_NODE_LEAF_BOILERPLATE(AbstractTypeDeclaration)
AbstractTypeDeclarationAbstractTypeDeclaration858   AbstractTypeDeclaration(SourcePosition pos, Identifier* name,
859                           AbstractTypeFlags flags,
860                           base::Optional<TypeExpression*> extends,
861                           base::Optional<std::string> generates)
862       : TypeDeclaration(kKind, pos, name),
863         flags(flags),
864         extends(extends),
865         generates(std::move(generates)) {
866     CHECK_EQ(IsConstexprName(name->value),
867              !!(flags & AbstractTypeFlag::kConstexpr));
868   }
869 
IsConstexprAbstractTypeDeclaration870   bool IsConstexpr() const { return flags & AbstractTypeFlag::kConstexpr; }
IsTransientAbstractTypeDeclaration871   bool IsTransient() const { return flags & AbstractTypeFlag::kTransient; }
872 
873   AbstractTypeFlags flags;
874   base::Optional<TypeExpression*> extends;
875   base::Optional<std::string> generates;
876 };
877 
878 struct TypeAliasDeclaration : TypeDeclaration {
879   DEFINE_AST_NODE_LEAF_BOILERPLATE(TypeAliasDeclaration)
TypeAliasDeclarationTypeAliasDeclaration880   TypeAliasDeclaration(SourcePosition pos, Identifier* name,
881                        TypeExpression* type)
882       : TypeDeclaration(kKind, pos, name), type(type) {}
883   TypeExpression* type;
884 };
885 
886 struct NameAndTypeExpression {
887   Identifier* name;
888   TypeExpression* type;
889 };
890 
891 struct ImplicitParameters {
892   Identifier* kind;
893   std::vector<NameAndTypeExpression> parameters;
894 };
895 
896 struct StructFieldExpression {
897   NameAndTypeExpression name_and_type;
898   bool const_qualified;
899 };
900 
901 struct BitFieldDeclaration {
902   NameAndTypeExpression name_and_type;
903   int num_bits;
904 };
905 
906 enum class ConditionalAnnotationType {
907   kPositive,
908   kNegative,
909 };
910 
911 struct ConditionalAnnotation {
912   std::string condition;
913   ConditionalAnnotationType type;
914 };
915 
916 struct AnnotationParameter {
917   std::string string_value;
918   int int_value;
919   bool is_int;
920 };
921 
922 struct Annotation {
923   Identifier* name;
924   base::Optional<AnnotationParameter> param;
925 };
926 
927 struct ClassFieldExpression {
928   NameAndTypeExpression name_and_type;
929   base::Optional<Expression*> index;
930   std::vector<ConditionalAnnotation> conditions;
931   bool weak;
932   bool const_qualified;
933   bool generate_verify;
934 };
935 
936 struct LabelAndTypes {
937   Identifier* name;
938   std::vector<TypeExpression*> types;
939 };
940 
941 using LabelAndTypesVector = std::vector<LabelAndTypes>;
942 
943 struct CallableDeclaration : Declaration {
CallableDeclarationCallableDeclaration944   CallableDeclaration(AstNode::Kind kind, SourcePosition pos,
945                       bool transitioning, Identifier* name,
946                       ParameterList parameters, TypeExpression* return_type,
947                       LabelAndTypesVector labels)
948       : Declaration(kind, pos),
949         transitioning(transitioning),
950         name(name),
951         parameters(std::move(parameters)),
952         return_type(return_type),
953         labels(std::move(labels)) {}
954   DEFINE_AST_NODE_INNER_BOILERPLATE(CallableDeclaration)
955   bool transitioning;
956   Identifier* name;
957   ParameterList parameters;
958   TypeExpression* return_type;
959   LabelAndTypesVector labels;
960 };
961 
962 struct MacroDeclaration : CallableDeclaration {
963   DEFINE_AST_NODE_INNER_BOILERPLATE(MacroDeclaration)
MacroDeclarationMacroDeclaration964   MacroDeclaration(AstNode::Kind kind, SourcePosition pos, bool transitioning,
965                    Identifier* name, base::Optional<std::string> op,
966                    ParameterList parameters, TypeExpression* return_type,
967                    const LabelAndTypesVector& labels)
968       : CallableDeclaration(kind, pos, transitioning, name,
969                             std::move(parameters), return_type, labels),
970         op(std::move(op)) {
971     if (parameters.implicit_kind == ImplicitKind::kJSImplicit) {
972       Error("Cannot use \"js-implicit\" with macros, use \"implicit\" instead.")
973           .Position(parameters.implicit_kind_pos);
974     }
975   }
976   base::Optional<std::string> op;
977 };
978 
979 struct ExternalMacroDeclaration : MacroDeclaration {
980   DEFINE_AST_NODE_LEAF_BOILERPLATE(ExternalMacroDeclaration)
ExternalMacroDeclarationExternalMacroDeclaration981   ExternalMacroDeclaration(SourcePosition pos, bool transitioning,
982                            std::string external_assembler_name,
983                            Identifier* name, base::Optional<std::string> op,
984                            ParameterList parameters,
985                            TypeExpression* return_type,
986                            const LabelAndTypesVector& labels)
987       : MacroDeclaration(kKind, pos, transitioning, name, std::move(op),
988                          std::move(parameters), return_type, labels),
989         external_assembler_name(std::move(external_assembler_name)) {}
990   std::string external_assembler_name;
991 };
992 
993 struct IntrinsicDeclaration : CallableDeclaration {
994   DEFINE_AST_NODE_LEAF_BOILERPLATE(IntrinsicDeclaration)
IntrinsicDeclarationIntrinsicDeclaration995   IntrinsicDeclaration(SourcePosition pos, Identifier* name,
996                        ParameterList parameters, TypeExpression* return_type)
997       : CallableDeclaration(kKind, pos, false, name, std::move(parameters),
998                             return_type, {}) {
999     if (parameters.implicit_kind != ImplicitKind::kNoImplicit) {
1000       Error("Intinsics cannot have implicit parameters.");
1001     }
1002   }
1003 };
1004 
1005 struct TorqueMacroDeclaration : MacroDeclaration {
1006   DEFINE_AST_NODE_LEAF_BOILERPLATE(TorqueMacroDeclaration)
TorqueMacroDeclarationTorqueMacroDeclaration1007   TorqueMacroDeclaration(SourcePosition pos, bool transitioning,
1008                          Identifier* name, base::Optional<std::string> op,
1009                          ParameterList parameters, TypeExpression* return_type,
1010                          const LabelAndTypesVector& labels, bool export_to_csa,
1011                          base::Optional<Statement*> body)
1012       : MacroDeclaration(kKind, pos, transitioning, name, std::move(op),
1013                          std::move(parameters), return_type, labels),
1014         export_to_csa(export_to_csa),
1015         body(body) {}
1016   bool export_to_csa;
1017   base::Optional<Statement*> body;
1018 };
1019 
1020 struct BuiltinDeclaration : CallableDeclaration {
1021   DEFINE_AST_NODE_INNER_BOILERPLATE(BuiltinDeclaration)
BuiltinDeclarationBuiltinDeclaration1022   BuiltinDeclaration(AstNode::Kind kind, SourcePosition pos,
1023                      bool javascript_linkage, bool transitioning,
1024                      Identifier* name, ParameterList parameters,
1025                      TypeExpression* return_type)
1026       : CallableDeclaration(kind, pos, transitioning, name,
1027                             std::move(parameters), return_type, {}),
1028         javascript_linkage(javascript_linkage) {
1029     if (parameters.implicit_kind == ImplicitKind::kJSImplicit &&
1030         !javascript_linkage) {
1031       Error(
1032           "\"js-implicit\" is for implicit parameters passed according to the "
1033           "JavaScript calling convention. Use \"implicit\" instead.");
1034     }
1035     if (parameters.implicit_kind == ImplicitKind::kImplicit &&
1036         javascript_linkage) {
1037       Error(
1038           "The JavaScript calling convention implicitly passes a fixed set of "
1039           "values. Use \"js-implicit\" to refer to those.")
1040           .Position(parameters.implicit_kind_pos);
1041     }
1042   }
1043   bool javascript_linkage;
1044 };
1045 
1046 struct ExternalBuiltinDeclaration : BuiltinDeclaration {
1047   DEFINE_AST_NODE_LEAF_BOILERPLATE(ExternalBuiltinDeclaration)
ExternalBuiltinDeclarationExternalBuiltinDeclaration1048   ExternalBuiltinDeclaration(SourcePosition pos, bool transitioning,
1049                              bool javascript_linkage, Identifier* name,
1050                              ParameterList parameters,
1051                              TypeExpression* return_type)
1052       : BuiltinDeclaration(kKind, pos, javascript_linkage, transitioning, name,
1053                            std::move(parameters), return_type) {}
1054 };
1055 
1056 struct TorqueBuiltinDeclaration : BuiltinDeclaration {
1057   DEFINE_AST_NODE_LEAF_BOILERPLATE(TorqueBuiltinDeclaration)
TorqueBuiltinDeclarationTorqueBuiltinDeclaration1058   TorqueBuiltinDeclaration(SourcePosition pos, bool transitioning,
1059                            bool javascript_linkage, Identifier* name,
1060                            ParameterList parameters,
1061                            TypeExpression* return_type,
1062                            base::Optional<Statement*> body)
1063       : BuiltinDeclaration(kKind, pos, javascript_linkage, transitioning, name,
1064                            std::move(parameters), return_type),
1065         body(body) {}
1066   base::Optional<Statement*> body;
1067 };
1068 
1069 struct ExternalRuntimeDeclaration : CallableDeclaration {
1070   DEFINE_AST_NODE_LEAF_BOILERPLATE(ExternalRuntimeDeclaration)
ExternalRuntimeDeclarationExternalRuntimeDeclaration1071   ExternalRuntimeDeclaration(SourcePosition pos, bool transitioning,
1072                              Identifier* name, ParameterList parameters,
1073                              TypeExpression* return_type)
1074       : CallableDeclaration(kKind, pos, transitioning, name, parameters,
1075                             return_type, {}) {}
1076 };
1077 
1078 struct ConstDeclaration : Declaration {
1079   DEFINE_AST_NODE_LEAF_BOILERPLATE(ConstDeclaration)
ConstDeclarationConstDeclaration1080   ConstDeclaration(SourcePosition pos, Identifier* name, TypeExpression* type,
1081                    Expression* expression)
1082       : Declaration(kKind, pos),
1083         name(name),
1084         type(type),
1085         expression(expression) {}
1086   Identifier* name;
1087   TypeExpression* type;
1088   Expression* expression;
1089 };
1090 
1091 struct GenericParameter {
1092   Identifier* name;
1093   base::Optional<TypeExpression*> constraint;
1094 };
1095 
1096 using GenericParameters = std::vector<GenericParameter>;
1097 
1098 // The AST re-shuffles generics from the concrete syntax:
1099 // Instead of the generic parameters being part of a normal declaration,
1100 // a declaration with generic parameters gets wrapped in a generic declaration,
1101 // which holds the generic parameters. This corresponds to how you write
1102 // templates in C++, with the template parameters coming before the declaration.
1103 
1104 struct GenericCallableDeclaration : Declaration {
1105   DEFINE_AST_NODE_LEAF_BOILERPLATE(GenericCallableDeclaration)
GenericCallableDeclarationGenericCallableDeclaration1106   GenericCallableDeclaration(SourcePosition pos,
1107                              GenericParameters generic_parameters,
1108                              CallableDeclaration* declaration)
1109       : Declaration(kKind, pos),
1110         generic_parameters(std::move(generic_parameters)),
1111         declaration(declaration) {}
1112 
1113   GenericParameters generic_parameters;
1114   CallableDeclaration* declaration;
1115 };
1116 
1117 struct GenericTypeDeclaration : Declaration {
1118   DEFINE_AST_NODE_LEAF_BOILERPLATE(GenericTypeDeclaration)
GenericTypeDeclarationGenericTypeDeclaration1119   GenericTypeDeclaration(SourcePosition pos,
1120                          GenericParameters generic_parameters,
1121                          TypeDeclaration* declaration)
1122       : Declaration(kKind, pos),
1123         generic_parameters(std::move(generic_parameters)),
1124         declaration(declaration) {}
1125 
1126   GenericParameters generic_parameters;
1127   TypeDeclaration* declaration;
1128 };
1129 
1130 struct SpecializationDeclaration : CallableDeclaration {
1131   DEFINE_AST_NODE_LEAF_BOILERPLATE(SpecializationDeclaration)
SpecializationDeclarationSpecializationDeclaration1132   SpecializationDeclaration(SourcePosition pos, bool transitioning,
1133                             Identifier* name,
1134                             std::vector<TypeExpression*> generic_parameters,
1135                             ParameterList parameters,
1136                             TypeExpression* return_type,
1137                             LabelAndTypesVector labels, Statement* body)
1138       : CallableDeclaration(kKind, pos, transitioning, name,
1139                             std::move(parameters), return_type,
1140                             std::move(labels)),
1141         generic_parameters(std::move(generic_parameters)),
1142         body(body) {}
1143   std::vector<TypeExpression*> generic_parameters;
1144   Statement* body;
1145 };
1146 
1147 struct ExternConstDeclaration : Declaration {
1148   DEFINE_AST_NODE_LEAF_BOILERPLATE(ExternConstDeclaration)
ExternConstDeclarationExternConstDeclaration1149   ExternConstDeclaration(SourcePosition pos, Identifier* name,
1150                          TypeExpression* type, std::string literal)
1151       : Declaration(kKind, pos),
1152         name(name),
1153         type(type),
1154         literal(std::move(literal)) {}
1155   Identifier* name;
1156   TypeExpression* type;
1157   std::string literal;
1158 };
1159 
1160 struct StructDeclaration : TypeDeclaration {
1161   DEFINE_AST_NODE_LEAF_BOILERPLATE(StructDeclaration)
StructDeclarationStructDeclaration1162   StructDeclaration(SourcePosition pos, StructFlags flags, Identifier* name,
1163                     std::vector<Declaration*> methods,
1164                     std::vector<StructFieldExpression> fields)
1165       : TypeDeclaration(kKind, pos, name),
1166         flags(flags),
1167         methods(std::move(methods)),
1168         fields(std::move(fields)) {}
1169   StructFlags flags;
1170   std::vector<Declaration*> methods;
1171   std::vector<StructFieldExpression> fields;
1172 };
1173 
1174 struct BitFieldStructDeclaration : TypeDeclaration {
1175   DEFINE_AST_NODE_LEAF_BOILERPLATE(BitFieldStructDeclaration)
BitFieldStructDeclarationBitFieldStructDeclaration1176   BitFieldStructDeclaration(SourcePosition pos, Identifier* name,
1177                             TypeExpression* parent,
1178                             std::vector<BitFieldDeclaration> fields)
1179       : TypeDeclaration(kKind, pos, name),
1180         parent(parent),
1181         fields(std::move(fields)) {}
1182   TypeExpression* parent;
1183   std::vector<BitFieldDeclaration> fields;
1184 };
1185 
1186 struct ClassBody : AstNode {
1187   DEFINE_AST_NODE_LEAF_BOILERPLATE(ClassBody)
ClassBodyClassBody1188   ClassBody(SourcePosition pos, std::vector<Declaration*> methods,
1189             std::vector<ClassFieldExpression> fields)
1190       : AstNode(kKind, pos),
1191         methods(std::move(methods)),
1192         fields(std::move(fields)) {}
1193   std::vector<Declaration*> methods;
1194   std::vector<ClassFieldExpression> fields;
1195 };
1196 
1197 struct ClassDeclaration : TypeDeclaration {
1198   DEFINE_AST_NODE_LEAF_BOILERPLATE(ClassDeclaration)
ClassDeclarationClassDeclaration1199   ClassDeclaration(SourcePosition pos, Identifier* name, ClassFlags flags,
1200                    TypeExpression* super, base::Optional<std::string> generates,
1201                    std::vector<Declaration*> methods,
1202                    std::vector<ClassFieldExpression> fields,
1203                    InstanceTypeConstraints instance_type_constraints)
1204       : TypeDeclaration(kKind, pos, name),
1205         flags(flags),
1206         super(super),
1207         generates(std::move(generates)),
1208         methods(std::move(methods)),
1209         fields(std::move(fields)),
1210         instance_type_constraints(std::move(instance_type_constraints)) {}
1211   ClassFlags flags;
1212   TypeExpression* super;
1213   base::Optional<std::string> generates;
1214   std::vector<Declaration*> methods;
1215   std::vector<ClassFieldExpression> fields;
1216   InstanceTypeConstraints instance_type_constraints;
1217 };
1218 
1219 struct CppIncludeDeclaration : Declaration {
1220   DEFINE_AST_NODE_LEAF_BOILERPLATE(CppIncludeDeclaration)
CppIncludeDeclarationCppIncludeDeclaration1221   CppIncludeDeclaration(SourcePosition pos, std::string include_path)
1222       : Declaration(kKind, pos), include_path(std::move(include_path)) {}
1223   std::string include_path;
1224 };
1225 
1226 #define ENUM_ITEM(name)                     \
1227   case AstNode::Kind::k##name:              \
1228     return std::is_base_of<T, name>::value; \
1229     break;
1230 
1231 template <class T>
IsInstanceOf(AstNode * node)1232 bool AstNodeClassCheck::IsInstanceOf(AstNode* node) {
1233   switch (node->kind) {
1234     AST_NODE_KIND_LIST(ENUM_ITEM)
1235     default:
1236       UNIMPLEMENTED();
1237   }
1238   return true;
1239 }
1240 
1241 #undef ENUM_ITEM
1242 
IsDeferred(Statement * stmt)1243 inline bool IsDeferred(Statement* stmt) {
1244   if (auto* block = BlockStatement::DynamicCast(stmt)) {
1245     return block->deferred;
1246   }
1247   return false;
1248 }
1249 
1250 DECLARE_CONTEXTUAL_VARIABLE(CurrentAst, Ast);
1251 
1252 template <class T, class... Args>
MakeNode(Args...args)1253 T* MakeNode(Args... args) {
1254   return CurrentAst::Get().AddNode(
1255       std::make_unique<T>(CurrentSourcePosition::Get(), std::move(args)...));
1256 }
1257 
MakeFieldAccessExpression(Expression * object,std::string field)1258 inline FieldAccessExpression* MakeFieldAccessExpression(Expression* object,
1259                                                         std::string field) {
1260   return MakeNode<FieldAccessExpression>(
1261       object, MakeNode<Identifier>(std::move(field)));
1262 }
1263 
1264 inline IdentifierExpression* MakeIdentifierExpression(
1265     std::vector<std::string> namespace_qualification, std::string name,
1266     std::vector<TypeExpression*> args = {}) {
1267   return MakeNode<IdentifierExpression>(std::move(namespace_qualification),
1268                                         MakeNode<Identifier>(std::move(name)),
1269                                         std::move(args));
1270 }
1271 
MakeIdentifierExpression(std::string name)1272 inline IdentifierExpression* MakeIdentifierExpression(std::string name) {
1273   return MakeIdentifierExpression({}, std::move(name));
1274 }
1275 
1276 inline CallExpression* MakeCallExpression(
1277     IdentifierExpression* callee, std::vector<Expression*> arguments,
1278     std::vector<Identifier*> labels = {}) {
1279   return MakeNode<CallExpression>(callee, std::move(arguments),
1280                                   std::move(labels));
1281 }
1282 
1283 inline CallExpression* MakeCallExpression(
1284     std::string callee, std::vector<Expression*> arguments,
1285     std::vector<Identifier*> labels = {}) {
1286   return MakeCallExpression(MakeIdentifierExpression(std::move(callee)),
1287                             std::move(arguments), std::move(labels));
1288 }
1289 
MakeConstDeclarationStatement(std::string name,Expression * initializer)1290 inline VarDeclarationStatement* MakeConstDeclarationStatement(
1291     std::string name, Expression* initializer) {
1292   return MakeNode<VarDeclarationStatement>(
1293       /*const_qualified=*/true, MakeNode<Identifier>(std::move(name)),
1294       base::Optional<TypeExpression*>{}, initializer);
1295 }
1296 
1297 inline BasicTypeExpression* MakeBasicTypeExpression(
1298     std::vector<std::string> namespace_qualification, std::string name,
1299     std::vector<TypeExpression*> generic_arguments = {}) {
1300   return MakeNode<BasicTypeExpression>(std::move(namespace_qualification),
1301                                        std::move(name),
1302                                        std::move(generic_arguments));
1303 }
1304 
MakeStructExpression(TypeExpression * type,std::vector<NameAndExpression> initializers)1305 inline StructExpression* MakeStructExpression(
1306     TypeExpression* type, std::vector<NameAndExpression> initializers) {
1307   return MakeNode<StructExpression>(type, std::move(initializers));
1308 }
1309 
1310 }  // namespace torque
1311 }  // namespace internal
1312 }  // namespace v8
1313 
1314 #endif  // V8_TORQUE_AST_H_
1315