1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef V8_AST_AST_H_
6 #define V8_AST_AST_H_
7 
8 #include <memory>
9 
10 #include "src/ast/ast-value-factory.h"
11 #include "src/ast/modules.h"
12 #include "src/ast/variables.h"
13 #include "src/base/threaded-list.h"
14 #include "src/codegen/bailout-reason.h"
15 #include "src/codegen/label.h"
16 #include "src/common/globals.h"
17 #include "src/heap/factory.h"
18 #include "src/objects/elements-kind.h"
19 #include "src/objects/function-syntax-kind.h"
20 #include "src/objects/literal-objects.h"
21 #include "src/objects/smi.h"
22 #include "src/parsing/token.h"
23 #include "src/runtime/runtime.h"
24 #include "src/zone/zone-list.h"
25 
26 namespace v8 {
27 namespace internal {
28 
29 // The abstract syntax tree is an intermediate, light-weight
30 // representation of the parsed JavaScript code suitable for
31 // compilation to native code.
32 
33 // Nodes are allocated in a separate zone, which allows faster
34 // allocation and constant-time deallocation of the entire syntax
35 // tree.
36 
37 
38 // ----------------------------------------------------------------------------
39 // Nodes of the abstract syntax tree. Only concrete classes are
40 // enumerated here.
41 
42 #define DECLARATION_NODE_LIST(V) \
43   V(VariableDeclaration)         \
44   V(FunctionDeclaration)
45 
46 #define ITERATION_NODE_LIST(V) \
47   V(DoWhileStatement)          \
48   V(WhileStatement)            \
49   V(ForStatement)              \
50   V(ForInStatement)            \
51   V(ForOfStatement)
52 
53 #define BREAKABLE_NODE_LIST(V) \
54   V(Block)                     \
55   V(SwitchStatement)
56 
57 #define STATEMENT_NODE_LIST(V)       \
58   ITERATION_NODE_LIST(V)             \
59   BREAKABLE_NODE_LIST(V)             \
60   V(ExpressionStatement)             \
61   V(EmptyStatement)                  \
62   V(SloppyBlockFunctionStatement)    \
63   V(IfStatement)                     \
64   V(ContinueStatement)               \
65   V(BreakStatement)                  \
66   V(ReturnStatement)                 \
67   V(WithStatement)                   \
68   V(TryCatchStatement)               \
69   V(TryFinallyStatement)             \
70   V(DebuggerStatement)               \
71   V(InitializeClassMembersStatement) \
72   V(InitializeClassStaticElementsStatement)
73 
74 #define LITERAL_NODE_LIST(V) \
75   V(RegExpLiteral)           \
76   V(ObjectLiteral)           \
77   V(ArrayLiteral)
78 
79 #define EXPRESSION_NODE_LIST(V) \
80   LITERAL_NODE_LIST(V)          \
81   V(Assignment)                 \
82   V(Await)                      \
83   V(BinaryOperation)            \
84   V(NaryOperation)              \
85   V(Call)                       \
86   V(CallNew)                    \
87   V(CallRuntime)                \
88   V(ClassLiteral)               \
89   V(CompareOperation)           \
90   V(CompoundAssignment)         \
91   V(Conditional)                \
92   V(CountOperation)             \
93   V(EmptyParentheses)           \
94   V(FunctionLiteral)            \
95   V(GetTemplateObject)          \
96   V(ImportCallExpression)       \
97   V(Literal)                    \
98   V(NativeFunctionLiteral)      \
99   V(OptionalChain)              \
100   V(Property)                   \
101   V(Spread)                     \
102   V(SuperCallReference)         \
103   V(SuperPropertyReference)     \
104   V(TemplateLiteral)            \
105   V(ThisExpression)             \
106   V(Throw)                      \
107   V(UnaryOperation)             \
108   V(VariableProxy)              \
109   V(Yield)                      \
110   V(YieldStar)
111 
112 #define FAILURE_NODE_LIST(V) V(FailureExpression)
113 
114 #define AST_NODE_LIST(V)                        \
115   DECLARATION_NODE_LIST(V)                      \
116   STATEMENT_NODE_LIST(V)                        \
117   EXPRESSION_NODE_LIST(V)
118 
119 // Forward declarations
120 class Isolate;
121 
122 class AstNode;
123 class AstNodeFactory;
124 class Declaration;
125 class BreakableStatement;
126 class Expression;
127 class IterationStatement;
128 class MaterializedLiteral;
129 class NestedVariableDeclaration;
130 class ProducedPreparseData;
131 class Statement;
132 
133 #define DEF_FORWARD_DECLARATION(type) class type;
134 AST_NODE_LIST(DEF_FORWARD_DECLARATION)
FAILURE_NODE_LIST(DEF_FORWARD_DECLARATION)135 FAILURE_NODE_LIST(DEF_FORWARD_DECLARATION)
136 #undef DEF_FORWARD_DECLARATION
137 
138 class AstNode: public ZoneObject {
139  public:
140 #define DECLARE_TYPE_ENUM(type) k##type,
141   enum NodeType : uint8_t {
142     AST_NODE_LIST(DECLARE_TYPE_ENUM) /* , */
143     FAILURE_NODE_LIST(DECLARE_TYPE_ENUM)
144   };
145 #undef DECLARE_TYPE_ENUM
146 
147   NodeType node_type() const { return NodeTypeField::decode(bit_field_); }
148   int position() const { return position_; }
149 
150 #ifdef DEBUG
151   void Print(Isolate* isolate);
152 #endif  // DEBUG
153 
154   // Type testing & conversion functions overridden by concrete subclasses.
155 #define DECLARE_NODE_FUNCTIONS(type) \
156   V8_INLINE bool Is##type() const;   \
157   V8_INLINE type* As##type();        \
158   V8_INLINE const type* As##type() const;
159   AST_NODE_LIST(DECLARE_NODE_FUNCTIONS)
160   FAILURE_NODE_LIST(DECLARE_NODE_FUNCTIONS)
161 #undef DECLARE_NODE_FUNCTIONS
162 
163   IterationStatement* AsIterationStatement();
164   MaterializedLiteral* AsMaterializedLiteral();
165 
166  private:
167   int position_;
168   using NodeTypeField = base::BitField<NodeType, 0, 6>;
169 
170  protected:
171   uint32_t bit_field_;
172 
173   template <class T, int size>
174   using NextBitField = NodeTypeField::Next<T, size>;
175 
176   AstNode(int position, NodeType type)
177       : position_(position), bit_field_(NodeTypeField::encode(type)) {}
178 };
179 
180 
181 class Statement : public AstNode {
182  protected:
Statement(int position,NodeType type)183   Statement(int position, NodeType type) : AstNode(position, type) {}
184 };
185 
186 
187 class Expression : public AstNode {
188  public:
189   enum Context {
190     // Not assigned a context yet, or else will not be visited during
191     // code generation.
192     kUninitialized,
193     // Evaluated for its side effects.
194     kEffect,
195     // Evaluated for its value (and side effects).
196     kValue,
197     // Evaluated for control flow (and side effects).
198     kTest
199   };
200 
201   // True iff the expression is a valid reference expression.
202   bool IsValidReferenceExpression() const;
203 
204   // True iff the expression is a private name.
205   bool IsPrivateName() const;
206 
207   // Helpers for ToBoolean conversion.
208   bool ToBooleanIsTrue() const;
209   bool ToBooleanIsFalse() const;
210 
211   // Symbols that cannot be parsed as array indices are considered property
212   // names.  We do not treat symbols that can be array indexes as property
213   // names because [] for string objects is handled only by keyed ICs.
214   bool IsPropertyName() const;
215 
216   // True iff the expression is a class or function expression without
217   // a syntactic name.
218   bool IsAnonymousFunctionDefinition() const;
219 
220   // True iff the expression is a concise method definition.
221   bool IsConciseMethodDefinition() const;
222 
223   // True iff the expression is an accessor function definition.
224   bool IsAccessorFunctionDefinition() const;
225 
226   // True iff the expression is a literal represented as a smi.
227   bool IsSmiLiteral() const;
228 
229   // True iff the expression is a literal represented as a number.
230   V8_EXPORT_PRIVATE bool IsNumberLiteral() const;
231 
232   // True iff the expression is a string literal.
233   bool IsStringLiteral() const;
234 
235   // True iff the expression is the null literal.
236   bool IsNullLiteral() const;
237 
238   // True iff the expression is the hole literal.
239   bool IsTheHoleLiteral() const;
240 
241   // True if we can prove that the expression is the undefined literal. Note
242   // that this also checks for loads of the global "undefined" variable.
243   bool IsUndefinedLiteral() const;
244 
245   // True if either null literal or undefined literal.
IsNullOrUndefinedLiteral()246   inline bool IsNullOrUndefinedLiteral() const {
247     return IsNullLiteral() || IsUndefinedLiteral();
248   }
249 
250   // True if a literal and not null or undefined.
251   bool IsLiteralButNotNullOrUndefined() const;
252 
253   bool IsCompileTimeValue();
254 
IsPattern()255   bool IsPattern() {
256     STATIC_ASSERT(kObjectLiteral + 1 == kArrayLiteral);
257     return base::IsInRange(node_type(), kObjectLiteral, kArrayLiteral);
258   }
259 
is_parenthesized()260   bool is_parenthesized() const {
261     return IsParenthesizedField::decode(bit_field_);
262   }
263 
mark_parenthesized()264   void mark_parenthesized() {
265     bit_field_ = IsParenthesizedField::update(bit_field_, true);
266   }
267 
clear_parenthesized()268   void clear_parenthesized() {
269     bit_field_ = IsParenthesizedField::update(bit_field_, false);
270   }
271 
272  private:
273   using IsParenthesizedField = AstNode::NextBitField<bool, 1>;
274 
275  protected:
Expression(int pos,NodeType type)276   Expression(int pos, NodeType type) : AstNode(pos, type) {
277     DCHECK(!is_parenthesized());
278   }
279 
280   template <class T, int size>
281   using NextBitField = IsParenthesizedField::Next<T, size>;
282 };
283 
284 class FailureExpression : public Expression {
285  private:
286   friend class AstNodeFactory;
287   friend Zone;
FailureExpression()288   FailureExpression() : Expression(kNoSourcePosition, kFailureExpression) {}
289 };
290 
291 // V8's notion of BreakableStatement does not correspond to the notion of
292 // BreakableStatement in ECMAScript. In V8, the idea is that a
293 // BreakableStatement is a statement that can be the target of a break
294 // statement.
295 //
296 // Since we don't want to track a list of labels for all kinds of statements, we
297 // only declare switchs, loops, and blocks as BreakableStatements.  This means
298 // that we implement breaks targeting other statement forms as breaks targeting
299 // a substatement thereof. For instance, in "foo: if (b) { f(); break foo; }" we
300 // pretend that foo is the label of the inner block. That's okay because one
301 // can't observe the difference.
302 // TODO(verwaest): Reconsider this optimization now that the tracking of labels
303 // is done at runtime.
304 class BreakableStatement : public Statement {
305  protected:
BreakableStatement(int position,NodeType type)306   BreakableStatement(int position, NodeType type) : Statement(position, type) {}
307 };
308 
309 class Block final : public BreakableStatement {
310  public:
statements()311   ZonePtrList<Statement>* statements() { return &statements_; }
ignore_completion_value()312   bool ignore_completion_value() const {
313     return IgnoreCompletionField::decode(bit_field_);
314   }
is_breakable()315   bool is_breakable() const { return IsBreakableField::decode(bit_field_); }
316 
scope()317   Scope* scope() const { return scope_; }
set_scope(Scope * scope)318   void set_scope(Scope* scope) { scope_ = scope; }
319 
InitializeStatements(const ScopedPtrList<Statement> & statements,Zone * zone)320   void InitializeStatements(const ScopedPtrList<Statement>& statements,
321                             Zone* zone) {
322     DCHECK_EQ(0, statements_.length());
323     statements_ = ZonePtrList<Statement>(statements.ToConstVector(), zone);
324   }
325 
326  private:
327   friend class AstNodeFactory;
328   friend Zone;
329 
330   ZonePtrList<Statement> statements_;
331   Scope* scope_;
332 
333   using IgnoreCompletionField = BreakableStatement::NextBitField<bool, 1>;
334   using IsBreakableField = IgnoreCompletionField::Next<bool, 1>;
335 
336  protected:
Block(Zone * zone,int capacity,bool ignore_completion_value,bool is_breakable)337   Block(Zone* zone, int capacity, bool ignore_completion_value,
338         bool is_breakable)
339       : BreakableStatement(kNoSourcePosition, kBlock),
340         statements_(capacity, zone),
341         scope_(nullptr) {
342     bit_field_ |= IgnoreCompletionField::encode(ignore_completion_value) |
343                   IsBreakableField::encode(is_breakable);
344   }
345 
Block(bool ignore_completion_value,bool is_breakable)346   Block(bool ignore_completion_value, bool is_breakable)
347       : Block(nullptr, 0, ignore_completion_value, is_breakable) {}
348 };
349 
350 class Declaration : public AstNode {
351  public:
352   using List = base::ThreadedList<Declaration>;
353 
var()354   Variable* var() const { return var_; }
set_var(Variable * var)355   void set_var(Variable* var) { var_ = var; }
356 
357  protected:
Declaration(int pos,NodeType type)358   Declaration(int pos, NodeType type) : AstNode(pos, type), next_(nullptr) {}
359 
360  private:
361   Variable* var_;
362   // Declarations list threaded through the declarations.
next()363   Declaration** next() { return &next_; }
364   Declaration* next_;
365   friend List;
366   friend base::ThreadedListTraits<Declaration>;
367 };
368 
369 class VariableDeclaration : public Declaration {
370  public:
371   inline NestedVariableDeclaration* AsNested();
372 
373  private:
374   friend class AstNodeFactory;
375   friend Zone;
376 
377   using IsNestedField = Declaration::NextBitField<bool, 1>;
378 
379  protected:
380   explicit VariableDeclaration(int pos, bool is_nested = false)
Declaration(pos,kVariableDeclaration)381       : Declaration(pos, kVariableDeclaration) {
382     bit_field_ = IsNestedField::update(bit_field_, is_nested);
383   }
384 
385   template <class T, int size>
386   using NextBitField = IsNestedField::Next<T, size>;
387 };
388 
389 // For var declarations that appear in a block scope.
390 // Only distinguished from VariableDeclaration during Scope analysis,
391 // so it doesn't get its own NodeType.
392 class NestedVariableDeclaration final : public VariableDeclaration {
393  public:
scope()394   Scope* scope() const { return scope_; }
395 
396  private:
397   friend class AstNodeFactory;
398   friend Zone;
399 
NestedVariableDeclaration(Scope * scope,int pos)400   NestedVariableDeclaration(Scope* scope, int pos)
401       : VariableDeclaration(pos, true), scope_(scope) {}
402 
403   // Nested scope from which the declaration originated.
404   Scope* scope_;
405 };
406 
AsNested()407 inline NestedVariableDeclaration* VariableDeclaration::AsNested() {
408   return IsNestedField::decode(bit_field_)
409              ? static_cast<NestedVariableDeclaration*>(this)
410              : nullptr;
411 }
412 
413 class FunctionDeclaration final : public Declaration {
414  public:
fun()415   FunctionLiteral* fun() const { return fun_; }
416 
417  private:
418   friend class AstNodeFactory;
419   friend Zone;
420 
FunctionDeclaration(FunctionLiteral * fun,int pos)421   FunctionDeclaration(FunctionLiteral* fun, int pos)
422       : Declaration(pos, kFunctionDeclaration), fun_(fun) {}
423 
424   FunctionLiteral* fun_;
425 };
426 
427 
428 class IterationStatement : public BreakableStatement {
429  public:
body()430   Statement* body() const { return body_; }
set_body(Statement * s)431   void set_body(Statement* s) { body_ = s; }
432 
433  protected:
IterationStatement(int pos,NodeType type)434   IterationStatement(int pos, NodeType type)
435       : BreakableStatement(pos, type), body_(nullptr) {}
Initialize(Statement * body)436   void Initialize(Statement* body) { body_ = body; }
437 
438  private:
439   Statement* body_;
440 };
441 
442 
443 class DoWhileStatement final : public IterationStatement {
444  public:
Initialize(Expression * cond,Statement * body)445   void Initialize(Expression* cond, Statement* body) {
446     IterationStatement::Initialize(body);
447     cond_ = cond;
448   }
449 
cond()450   Expression* cond() const { return cond_; }
451 
452  private:
453   friend class AstNodeFactory;
454   friend Zone;
455 
DoWhileStatement(int pos)456   explicit DoWhileStatement(int pos)
457       : IterationStatement(pos, kDoWhileStatement), cond_(nullptr) {}
458 
459   Expression* cond_;
460 };
461 
462 
463 class WhileStatement final : public IterationStatement {
464  public:
Initialize(Expression * cond,Statement * body)465   void Initialize(Expression* cond, Statement* body) {
466     IterationStatement::Initialize(body);
467     cond_ = cond;
468   }
469 
cond()470   Expression* cond() const { return cond_; }
471 
472  private:
473   friend class AstNodeFactory;
474   friend Zone;
475 
WhileStatement(int pos)476   explicit WhileStatement(int pos)
477       : IterationStatement(pos, kWhileStatement), cond_(nullptr) {}
478 
479   Expression* cond_;
480 };
481 
482 
483 class ForStatement final : public IterationStatement {
484  public:
Initialize(Statement * init,Expression * cond,Statement * next,Statement * body)485   void Initialize(Statement* init, Expression* cond, Statement* next,
486                   Statement* body) {
487     IterationStatement::Initialize(body);
488     init_ = init;
489     cond_ = cond;
490     next_ = next;
491   }
492 
init()493   Statement* init() const { return init_; }
cond()494   Expression* cond() const { return cond_; }
next()495   Statement* next() const { return next_; }
496 
497  private:
498   friend class AstNodeFactory;
499   friend Zone;
500 
ForStatement(int pos)501   explicit ForStatement(int pos)
502       : IterationStatement(pos, kForStatement),
503         init_(nullptr),
504         cond_(nullptr),
505         next_(nullptr) {}
506 
507   Statement* init_;
508   Expression* cond_;
509   Statement* next_;
510 };
511 
512 // Shared class for for-in and for-of statements.
513 class ForEachStatement : public IterationStatement {
514  public:
515   enum VisitMode {
516     ENUMERATE,   // for (each in subject) body;
517     ITERATE      // for (each of subject) body;
518   };
519 
520   using IterationStatement::Initialize;
521 
VisitModeString(VisitMode mode)522   static const char* VisitModeString(VisitMode mode) {
523     return mode == ITERATE ? "for-of" : "for-in";
524   }
525 
Initialize(Expression * each,Expression * subject,Statement * body)526   void Initialize(Expression* each, Expression* subject, Statement* body) {
527     IterationStatement::Initialize(body);
528     each_ = each;
529     subject_ = subject;
530   }
531 
each()532   Expression* each() const { return each_; }
subject()533   Expression* subject() const { return subject_; }
534 
535  protected:
536   friend class AstNodeFactory;
537   friend Zone;
538 
ForEachStatement(int pos,NodeType type)539   ForEachStatement(int pos, NodeType type)
540       : IterationStatement(pos, type), each_(nullptr), subject_(nullptr) {}
541 
542   Expression* each_;
543   Expression* subject_;
544 };
545 
546 class ForInStatement final : public ForEachStatement {
547  private:
548   friend class AstNodeFactory;
549   friend Zone;
550 
ForInStatement(int pos)551   explicit ForInStatement(int pos) : ForEachStatement(pos, kForInStatement) {}
552 };
553 
554 enum class IteratorType { kNormal, kAsync };
555 class ForOfStatement final : public ForEachStatement {
556  public:
type()557   IteratorType type() const { return type_; }
558 
559  private:
560   friend class AstNodeFactory;
561   friend Zone;
562 
ForOfStatement(int pos,IteratorType type)563   ForOfStatement(int pos, IteratorType type)
564       : ForEachStatement(pos, kForOfStatement), type_(type) {}
565 
566   IteratorType type_;
567 };
568 
569 class ExpressionStatement final : public Statement {
570  public:
set_expression(Expression * e)571   void set_expression(Expression* e) { expression_ = e; }
expression()572   Expression* expression() const { return expression_; }
573 
574  private:
575   friend class AstNodeFactory;
576   friend Zone;
577 
ExpressionStatement(Expression * expression,int pos)578   ExpressionStatement(Expression* expression, int pos)
579       : Statement(pos, kExpressionStatement), expression_(expression) {}
580 
581   Expression* expression_;
582 };
583 
584 
585 class JumpStatement : public Statement {
586  protected:
JumpStatement(int pos,NodeType type)587   JumpStatement(int pos, NodeType type) : Statement(pos, type) {}
588 };
589 
590 
591 class ContinueStatement final : public JumpStatement {
592  public:
target()593   IterationStatement* target() const { return target_; }
594 
595  private:
596   friend class AstNodeFactory;
597   friend Zone;
598 
ContinueStatement(IterationStatement * target,int pos)599   ContinueStatement(IterationStatement* target, int pos)
600       : JumpStatement(pos, kContinueStatement), target_(target) {}
601 
602   IterationStatement* target_;
603 };
604 
605 
606 class BreakStatement final : public JumpStatement {
607  public:
target()608   BreakableStatement* target() const { return target_; }
609 
610  private:
611   friend class AstNodeFactory;
612   friend Zone;
613 
BreakStatement(BreakableStatement * target,int pos)614   BreakStatement(BreakableStatement* target, int pos)
615       : JumpStatement(pos, kBreakStatement), target_(target) {}
616 
617   BreakableStatement* target_;
618 };
619 
620 
621 class ReturnStatement final : public JumpStatement {
622  public:
623   enum Type { kNormal, kAsyncReturn, kSyntheticAsyncReturn };
expression()624   Expression* expression() const { return expression_; }
625 
type()626   Type type() const { return TypeField::decode(bit_field_); }
is_async_return()627   bool is_async_return() const { return type() != kNormal; }
is_synthetic_async_return()628   bool is_synthetic_async_return() const {
629     return type() == kSyntheticAsyncReturn;
630   }
631 
632   // This constant is used to indicate that the return position
633   // from the FunctionLiteral should be used when emitting code.
634   static constexpr int kFunctionLiteralReturnPosition = -2;
635   STATIC_ASSERT(kFunctionLiteralReturnPosition == kNoSourcePosition - 1);
636 
end_position()637   int end_position() const { return end_position_; }
638 
639  private:
640   friend class AstNodeFactory;
641   friend Zone;
642 
ReturnStatement(Expression * expression,Type type,int pos,int end_position)643   ReturnStatement(Expression* expression, Type type, int pos, int end_position)
644       : JumpStatement(pos, kReturnStatement),
645         expression_(expression),
646         end_position_(end_position) {
647     bit_field_ |= TypeField::encode(type);
648   }
649 
650   Expression* expression_;
651   int end_position_;
652 
653   using TypeField = JumpStatement::NextBitField<Type, 2>;
654 };
655 
656 
657 class WithStatement final : public Statement {
658  public:
scope()659   Scope* scope() { return scope_; }
expression()660   Expression* expression() const { return expression_; }
statement()661   Statement* statement() const { return statement_; }
set_statement(Statement * s)662   void set_statement(Statement* s) { statement_ = s; }
663 
664  private:
665   friend class AstNodeFactory;
666   friend Zone;
667 
WithStatement(Scope * scope,Expression * expression,Statement * statement,int pos)668   WithStatement(Scope* scope, Expression* expression, Statement* statement,
669                 int pos)
670       : Statement(pos, kWithStatement),
671         scope_(scope),
672         expression_(expression),
673         statement_(statement) {}
674 
675   Scope* scope_;
676   Expression* expression_;
677   Statement* statement_;
678 };
679 
680 class CaseClause final : public ZoneObject {
681  public:
is_default()682   bool is_default() const { return label_ == nullptr; }
label()683   Expression* label() const {
684     DCHECK(!is_default());
685     return label_;
686   }
statements()687   ZonePtrList<Statement>* statements() { return &statements_; }
688 
689  private:
690   friend class AstNodeFactory;
691   friend Zone;
692 
693   CaseClause(Zone* zone, Expression* label,
694              const ScopedPtrList<Statement>& statements);
695 
696   Expression* label_;
697   ZonePtrList<Statement> statements_;
698 };
699 
700 
701 class SwitchStatement final : public BreakableStatement {
702  public:
tag()703   Expression* tag() const { return tag_; }
set_tag(Expression * t)704   void set_tag(Expression* t) { tag_ = t; }
705 
cases()706   ZonePtrList<CaseClause>* cases() { return &cases_; }
707 
708  private:
709   friend class AstNodeFactory;
710   friend Zone;
711 
SwitchStatement(Zone * zone,Expression * tag,int pos)712   SwitchStatement(Zone* zone, Expression* tag, int pos)
713       : BreakableStatement(pos, kSwitchStatement), tag_(tag), cases_(4, zone) {}
714 
715   Expression* tag_;
716   ZonePtrList<CaseClause> cases_;
717 };
718 
719 
720 // If-statements always have non-null references to their then- and
721 // else-parts. When parsing if-statements with no explicit else-part,
722 // the parser implicitly creates an empty statement. Use the
723 // HasThenStatement() and HasElseStatement() functions to check if a
724 // given if-statement has a then- or an else-part containing code.
725 class IfStatement final : public Statement {
726  public:
HasThenStatement()727   bool HasThenStatement() const { return !then_statement_->IsEmptyStatement(); }
HasElseStatement()728   bool HasElseStatement() const { return !else_statement_->IsEmptyStatement(); }
729 
condition()730   Expression* condition() const { return condition_; }
then_statement()731   Statement* then_statement() const { return then_statement_; }
else_statement()732   Statement* else_statement() const { return else_statement_; }
733 
set_then_statement(Statement * s)734   void set_then_statement(Statement* s) { then_statement_ = s; }
set_else_statement(Statement * s)735   void set_else_statement(Statement* s) { else_statement_ = s; }
736 
737  private:
738   friend class AstNodeFactory;
739   friend Zone;
740 
IfStatement(Expression * condition,Statement * then_statement,Statement * else_statement,int pos)741   IfStatement(Expression* condition, Statement* then_statement,
742               Statement* else_statement, int pos)
743       : Statement(pos, kIfStatement),
744         condition_(condition),
745         then_statement_(then_statement),
746         else_statement_(else_statement) {}
747 
748   Expression* condition_;
749   Statement* then_statement_;
750   Statement* else_statement_;
751 };
752 
753 
754 class TryStatement : public Statement {
755  public:
try_block()756   Block* try_block() const { return try_block_; }
set_try_block(Block * b)757   void set_try_block(Block* b) { try_block_ = b; }
758 
759  protected:
TryStatement(Block * try_block,int pos,NodeType type)760   TryStatement(Block* try_block, int pos, NodeType type)
761       : Statement(pos, type), try_block_(try_block) {}
762 
763  private:
764   Block* try_block_;
765 };
766 
767 
768 class TryCatchStatement final : public TryStatement {
769  public:
scope()770   Scope* scope() { return scope_; }
catch_block()771   Block* catch_block() const { return catch_block_; }
set_catch_block(Block * b)772   void set_catch_block(Block* b) { catch_block_ = b; }
773 
774   // Prediction of whether exceptions thrown into the handler for this try block
775   // will be caught.
776   //
777   // BytecodeGenerator tracks the state of catch prediction, which can change
778   // with each TryCatchStatement encountered. The tracked catch prediction is
779   // later compiled into the code's handler table. The runtime uses this
780   // information to implement a feature that notifies the debugger when an
781   // uncaught exception is thrown, _before_ the exception propagates to the top.
782   //
783   // If this try/catch statement is meant to rethrow (HandlerTable::UNCAUGHT),
784   // the catch prediction value is set to the same value as the surrounding
785   // catch prediction.
786   //
787   // Since it's generally undecidable whether an exception will be caught, our
788   // prediction is only an approximation.
789   // ---------------------------------------------------------------------------
GetCatchPrediction(HandlerTable::CatchPrediction outer_catch_prediction)790   inline HandlerTable::CatchPrediction GetCatchPrediction(
791       HandlerTable::CatchPrediction outer_catch_prediction) const {
792     if (catch_prediction_ == HandlerTable::UNCAUGHT) {
793       return outer_catch_prediction;
794     }
795     return catch_prediction_;
796   }
797 
798   // Indicates whether or not code should be generated to clear the pending
799   // exception. The pending exception is cleared for cases where the exception
800   // is not guaranteed to be rethrown, indicated by the value
801   // HandlerTable::UNCAUGHT. If both the current and surrounding catch handler's
802   // are predicted uncaught, the exception is not cleared.
803   //
804   // If this handler is not going to simply rethrow the exception, this method
805   // indicates that the isolate's pending exception message should be cleared
806   // before executing the catch_block.
807   // In the normal use case, this flag is always on because the message object
808   // is not needed anymore when entering the catch block and should not be
809   // kept alive.
810   // The use case where the flag is off is when the catch block is guaranteed
811   // to rethrow the caught exception (using %ReThrow), which reuses the
812   // pending message instead of generating a new one.
813   // (When the catch block doesn't rethrow but is guaranteed to perform an
814   // ordinary throw, not clearing the old message is safe but not very
815   // useful.)
816   //
817   // For scripts in repl mode there is exactly one catch block with
818   // UNCAUGHT_ASYNC_AWAIT prediction. This catch block needs to preserve
819   // the exception so it can be re-used later by the inspector.
ShouldClearPendingException(HandlerTable::CatchPrediction outer_catch_prediction)820   inline bool ShouldClearPendingException(
821       HandlerTable::CatchPrediction outer_catch_prediction) const {
822     if (catch_prediction_ == HandlerTable::UNCAUGHT_ASYNC_AWAIT) {
823       DCHECK_EQ(outer_catch_prediction, HandlerTable::UNCAUGHT);
824       return false;
825     }
826 
827     return catch_prediction_ != HandlerTable::UNCAUGHT ||
828            outer_catch_prediction != HandlerTable::UNCAUGHT;
829   }
830 
is_try_catch_for_async()831   bool is_try_catch_for_async() {
832     return catch_prediction_ == HandlerTable::ASYNC_AWAIT;
833   }
834 
835  private:
836   friend class AstNodeFactory;
837   friend Zone;
838 
TryCatchStatement(Block * try_block,Scope * scope,Block * catch_block,HandlerTable::CatchPrediction catch_prediction,int pos)839   TryCatchStatement(Block* try_block, Scope* scope, Block* catch_block,
840                     HandlerTable::CatchPrediction catch_prediction, int pos)
841       : TryStatement(try_block, pos, kTryCatchStatement),
842         scope_(scope),
843         catch_block_(catch_block),
844         catch_prediction_(catch_prediction) {}
845 
846   Scope* scope_;
847   Block* catch_block_;
848   HandlerTable::CatchPrediction catch_prediction_;
849 };
850 
851 
852 class TryFinallyStatement final : public TryStatement {
853  public:
finally_block()854   Block* finally_block() const { return finally_block_; }
set_finally_block(Block * b)855   void set_finally_block(Block* b) { finally_block_ = b; }
856 
857  private:
858   friend class AstNodeFactory;
859   friend Zone;
860 
TryFinallyStatement(Block * try_block,Block * finally_block,int pos)861   TryFinallyStatement(Block* try_block, Block* finally_block, int pos)
862       : TryStatement(try_block, pos, kTryFinallyStatement),
863         finally_block_(finally_block) {}
864 
865   Block* finally_block_;
866 };
867 
868 
869 class DebuggerStatement final : public Statement {
870  private:
871   friend class AstNodeFactory;
872   friend Zone;
873 
DebuggerStatement(int pos)874   explicit DebuggerStatement(int pos) : Statement(pos, kDebuggerStatement) {}
875 };
876 
877 
878 class EmptyStatement final : public Statement {
879  private:
880   friend class AstNodeFactory;
881   friend Zone;
EmptyStatement()882   EmptyStatement() : Statement(kNoSourcePosition, kEmptyStatement) {}
883 };
884 
885 
886 // Delegates to another statement, which may be overwritten.
887 // This was introduced to implement ES2015 Annex B3.3 for conditionally making
888 // sloppy-mode block-scoped functions have a var binding, which is changed
889 // from one statement to another during parsing.
890 class SloppyBlockFunctionStatement final : public Statement {
891  public:
statement()892   Statement* statement() const { return statement_; }
set_statement(Statement * statement)893   void set_statement(Statement* statement) { statement_ = statement; }
scope()894   Scope* scope() const { return var_->scope(); }
var()895   Variable* var() const { return var_; }
init()896   Token::Value init() const { return TokenField::decode(bit_field_); }
name()897   const AstRawString* name() const { return var_->raw_name(); }
next()898   SloppyBlockFunctionStatement** next() { return &next_; }
899 
900  private:
901   friend class AstNodeFactory;
902   friend Zone;
903 
904   using TokenField = Statement::NextBitField<Token::Value, 8>;
905 
SloppyBlockFunctionStatement(int pos,Variable * var,Token::Value init,Statement * statement)906   SloppyBlockFunctionStatement(int pos, Variable* var, Token::Value init,
907                                Statement* statement)
908       : Statement(pos, kSloppyBlockFunctionStatement),
909         var_(var),
910         statement_(statement),
911         next_(nullptr) {
912     bit_field_ = TokenField::update(bit_field_, init);
913   }
914 
915   Variable* var_;
916   Statement* statement_;
917   SloppyBlockFunctionStatement* next_;
918 };
919 
920 
921 class Literal final : public Expression {
922  public:
923   enum Type {
924     kSmi,
925     kHeapNumber,
926     kBigInt,
927     kString,
928     kBoolean,
929     kUndefined,
930     kNull,
931     kTheHole,
932   };
933 
type()934   Type type() const { return TypeField::decode(bit_field_); }
935 
936   // Returns true if literal represents a property name (i.e. cannot be parsed
937   // as array indices).
938   bool IsPropertyName() const;
939 
940   // Returns true if literal represents an array index.
941   // Note, that in general the following statement is not true:
942   //   key->IsPropertyName() != key->AsArrayIndex(...)
943   // but for non-computed LiteralProperty properties the following is true:
944   //   property->key()->IsPropertyName() != property->key()->AsArrayIndex(...)
945   bool AsArrayIndex(uint32_t* index) const;
946 
AsRawPropertyName()947   const AstRawString* AsRawPropertyName() {
948     DCHECK(IsPropertyName());
949     return string_;
950   }
951 
AsSmiLiteral()952   Smi AsSmiLiteral() const {
953     DCHECK_EQ(kSmi, type());
954     return Smi::FromInt(smi_);
955   }
956 
957   // Returns true if literal represents a Number.
IsNumber()958   bool IsNumber() const { return type() == kHeapNumber || type() == kSmi; }
AsNumber()959   double AsNumber() const {
960     DCHECK(IsNumber());
961     switch (type()) {
962       case kSmi:
963         return smi_;
964       case kHeapNumber:
965         return number_;
966       default:
967         UNREACHABLE();
968     }
969   }
970 
AsBigInt()971   AstBigInt AsBigInt() const {
972     DCHECK_EQ(type(), kBigInt);
973     return bigint_;
974   }
975 
IsString()976   bool IsString() const { return type() == kString; }
AsRawString()977   const AstRawString* AsRawString() {
978     DCHECK_EQ(type(), kString);
979     return string_;
980   }
981 
982   V8_EXPORT_PRIVATE bool ToBooleanIsTrue() const;
ToBooleanIsFalse()983   bool ToBooleanIsFalse() const { return !ToBooleanIsTrue(); }
984 
985   bool ToUint32(uint32_t* value) const;
986 
987   // Returns an appropriate Object representing this Literal, allocating
988   // a heap object if needed.
989   template <typename IsolateT>
990   Handle<Object> BuildValue(IsolateT* isolate) const;
991 
992   // Support for using Literal as a HashMap key. NOTE: Currently, this works
993   // only for string and number literals!
994   uint32_t Hash();
995   static bool Match(void* literal1, void* literal2);
996 
997  private:
998   friend class AstNodeFactory;
999   friend Zone;
1000 
1001   using TypeField = Expression::NextBitField<Type, 4>;
1002 
Literal(int smi,int position)1003   Literal(int smi, int position) : Expression(position, kLiteral), smi_(smi) {
1004     bit_field_ = TypeField::update(bit_field_, kSmi);
1005   }
1006 
Literal(double number,int position)1007   Literal(double number, int position)
1008       : Expression(position, kLiteral), number_(number) {
1009     bit_field_ = TypeField::update(bit_field_, kHeapNumber);
1010   }
1011 
Literal(AstBigInt bigint,int position)1012   Literal(AstBigInt bigint, int position)
1013       : Expression(position, kLiteral), bigint_(bigint) {
1014     bit_field_ = TypeField::update(bit_field_, kBigInt);
1015   }
1016 
Literal(const AstRawString * string,int position)1017   Literal(const AstRawString* string, int position)
1018       : Expression(position, kLiteral), string_(string) {
1019     bit_field_ = TypeField::update(bit_field_, kString);
1020   }
1021 
Literal(bool boolean,int position)1022   Literal(bool boolean, int position)
1023       : Expression(position, kLiteral), boolean_(boolean) {
1024     bit_field_ = TypeField::update(bit_field_, kBoolean);
1025   }
1026 
Literal(Type type,int position)1027   Literal(Type type, int position) : Expression(position, kLiteral) {
1028     DCHECK(type == kNull || type == kUndefined || type == kTheHole);
1029     bit_field_ = TypeField::update(bit_field_, type);
1030   }
1031 
1032   union {
1033     const AstRawString* string_;
1034     int smi_;
1035     double number_;
1036     AstBigInt bigint_;
1037     bool boolean_;
1038   };
1039 };
1040 
1041 // Base class for literals that need space in the type feedback vector.
1042 class MaterializedLiteral : public Expression {
1043  public:
1044   // A Materializedliteral is simple if the values consist of only
1045   // constants and simple object and array literals.
1046   bool IsSimple() const;
1047 
1048  protected:
MaterializedLiteral(int pos,NodeType type)1049   MaterializedLiteral(int pos, NodeType type) : Expression(pos, type) {}
1050 
1051   friend class CompileTimeValue;
1052   friend class ArrayLiteral;
1053   friend class ObjectLiteral;
1054 
1055   // Populate the depth field and any flags the literal has, returns the depth.
1056   int InitDepthAndFlags();
1057 
1058   bool NeedsInitialAllocationSite();
1059 
1060   // Populate the constant properties/elements fixed array.
1061   template <typename IsolateT>
1062   void BuildConstants(IsolateT* isolate);
1063 
1064   // If the expression is a literal, return the literal value;
1065   // if the expression is a materialized literal and is_simple
1066   // then return an Array or Object Boilerplate Description
1067   // Otherwise, return undefined literal as the placeholder
1068   // in the object literal boilerplate.
1069   template <typename IsolateT>
1070   Handle<Object> GetBoilerplateValue(Expression* expression, IsolateT* isolate);
1071 };
1072 
1073 // Node for capturing a regexp literal.
1074 class RegExpLiteral final : public MaterializedLiteral {
1075  public:
pattern()1076   Handle<String> pattern() const { return pattern_->string(); }
raw_pattern()1077   const AstRawString* raw_pattern() const { return pattern_; }
flags()1078   int flags() const { return flags_; }
1079 
1080  private:
1081   friend class AstNodeFactory;
1082   friend Zone;
1083 
RegExpLiteral(const AstRawString * pattern,int flags,int pos)1084   RegExpLiteral(const AstRawString* pattern, int flags, int pos)
1085       : MaterializedLiteral(pos, kRegExpLiteral),
1086         flags_(flags),
1087         pattern_(pattern) {}
1088 
1089   int const flags_;
1090   const AstRawString* const pattern_;
1091 };
1092 
1093 // Base class for Array and Object literals, providing common code for handling
1094 // nested subliterals.
1095 class AggregateLiteral : public MaterializedLiteral {
1096  public:
1097   enum Flags {
1098     kNoFlags = 0,
1099     kIsShallow = 1,
1100     kDisableMementos = 1 << 1,
1101     kNeedsInitialAllocationSite = 1 << 2,
1102     kIsShallowAndDisableMementos = kIsShallow | kDisableMementos,
1103   };
1104 
is_initialized()1105   bool is_initialized() const { return 0 < depth_; }
depth()1106   int depth() const {
1107     DCHECK(is_initialized());
1108     return depth_;
1109   }
1110 
is_shallow()1111   bool is_shallow() const { return depth() == 1; }
needs_initial_allocation_site()1112   bool needs_initial_allocation_site() const {
1113     return NeedsInitialAllocationSiteField::decode(bit_field_);
1114   }
1115 
1116   int ComputeFlags(bool disable_mementos = false) const {
1117     int flags = kNoFlags;
1118     if (is_shallow()) flags |= kIsShallow;
1119     if (disable_mementos) flags |= kDisableMementos;
1120     if (needs_initial_allocation_site()) flags |= kNeedsInitialAllocationSite;
1121     return flags;
1122   }
1123 
1124   // An AggregateLiteral is simple if the values consist of only
1125   // constants and simple object and array literals.
is_simple()1126   bool is_simple() const { return IsSimpleField::decode(bit_field_); }
1127 
boilerplate_descriptor_kind()1128   ElementsKind boilerplate_descriptor_kind() const {
1129     return BoilerplateDescriptorKindField::decode(bit_field_);
1130   }
1131 
1132  private:
1133   int depth_ : 31;
1134   using NeedsInitialAllocationSiteField =
1135       MaterializedLiteral::NextBitField<bool, 1>;
1136   using IsSimpleField = NeedsInitialAllocationSiteField::Next<bool, 1>;
1137   using BoilerplateDescriptorKindField =
1138       IsSimpleField::Next<ElementsKind, kFastElementsKindBits>;
1139 
1140  protected:
1141   friend class AstNodeFactory;
1142   friend Zone;
AggregateLiteral(int pos,NodeType type)1143   AggregateLiteral(int pos, NodeType type)
1144       : MaterializedLiteral(pos, type), depth_(0) {
1145     bit_field_ |=
1146         NeedsInitialAllocationSiteField::encode(false) |
1147         IsSimpleField::encode(false) |
1148         BoilerplateDescriptorKindField::encode(FIRST_FAST_ELEMENTS_KIND);
1149   }
1150 
set_is_simple(bool is_simple)1151   void set_is_simple(bool is_simple) {
1152     bit_field_ = IsSimpleField::update(bit_field_, is_simple);
1153   }
1154 
set_boilerplate_descriptor_kind(ElementsKind kind)1155   void set_boilerplate_descriptor_kind(ElementsKind kind) {
1156     DCHECK(IsFastElementsKind(kind));
1157     bit_field_ = BoilerplateDescriptorKindField::update(bit_field_, kind);
1158   }
1159 
set_depth(int depth)1160   void set_depth(int depth) {
1161     DCHECK(!is_initialized());
1162     depth_ = depth;
1163   }
1164 
set_needs_initial_allocation_site(bool required)1165   void set_needs_initial_allocation_site(bool required) {
1166     bit_field_ = NeedsInitialAllocationSiteField::update(bit_field_, required);
1167   }
1168 
1169   template <class T, int size>
1170   using NextBitField = BoilerplateDescriptorKindField::Next<T, size>;
1171 };
1172 
1173 // Common supertype for ObjectLiteralProperty and ClassLiteralProperty
1174 class LiteralProperty : public ZoneObject {
1175  public:
key()1176   Expression* key() const { return key_and_is_computed_name_.GetPointer(); }
value()1177   Expression* value() const { return value_; }
1178 
is_computed_name()1179   bool is_computed_name() const {
1180     return key_and_is_computed_name_.GetPayload();
1181   }
1182   bool NeedsSetFunctionName() const;
1183 
1184  protected:
LiteralProperty(Expression * key,Expression * value,bool is_computed_name)1185   LiteralProperty(Expression* key, Expression* value, bool is_computed_name)
1186       : key_and_is_computed_name_(key, is_computed_name), value_(value) {}
1187 
1188   PointerWithPayload<Expression, bool, 1> key_and_is_computed_name_;
1189   Expression* value_;
1190 };
1191 
1192 // Property is used for passing information
1193 // about an object literal's properties from the parser
1194 // to the code generator.
1195 class ObjectLiteralProperty final : public LiteralProperty {
1196  public:
1197   enum Kind : uint8_t {
1198     CONSTANT,              // Property with constant value (compile time).
1199     COMPUTED,              // Property with computed value (execution time).
1200     MATERIALIZED_LITERAL,  // Property value is a materialized literal.
1201     GETTER,
1202     SETTER,     // Property is an accessor function.
1203     PROTOTYPE,  // Property is __proto__.
1204     SPREAD
1205   };
1206 
kind()1207   Kind kind() const { return kind_; }
1208 
1209   bool IsCompileTimeValue() const;
1210 
1211   void set_emit_store(bool emit_store);
1212   bool emit_store() const;
1213 
IsNullPrototype()1214   bool IsNullPrototype() const {
1215     return IsPrototype() && value()->IsNullLiteral();
1216   }
IsPrototype()1217   bool IsPrototype() const { return kind() == PROTOTYPE; }
1218 
1219  private:
1220   friend class AstNodeFactory;
1221   friend Zone;
1222 
1223   ObjectLiteralProperty(Expression* key, Expression* value, Kind kind,
1224                         bool is_computed_name);
1225   ObjectLiteralProperty(AstValueFactory* ast_value_factory, Expression* key,
1226                         Expression* value, bool is_computed_name);
1227 
1228   Kind kind_;
1229   bool emit_store_;
1230 };
1231 
1232 // An object literal has a boilerplate object that is used
1233 // for minimizing the work when constructing it at runtime.
1234 class ObjectLiteral final : public AggregateLiteral {
1235  public:
1236   using Property = ObjectLiteralProperty;
1237 
boilerplate_description()1238   Handle<ObjectBoilerplateDescription> boilerplate_description() const {
1239     DCHECK(!boilerplate_description_.is_null());
1240     return boilerplate_description_;
1241   }
properties_count()1242   int properties_count() const { return boilerplate_properties_; }
properties()1243   const ZonePtrList<Property>* properties() const { return &properties_; }
has_elements()1244   bool has_elements() const { return HasElementsField::decode(bit_field_); }
has_rest_property()1245   bool has_rest_property() const {
1246     return HasRestPropertyField::decode(bit_field_);
1247   }
fast_elements()1248   bool fast_elements() const { return FastElementsField::decode(bit_field_); }
has_null_prototype()1249   bool has_null_prototype() const {
1250     return HasNullPrototypeField::decode(bit_field_);
1251   }
1252 
is_empty()1253   bool is_empty() const {
1254     DCHECK(is_initialized());
1255     return !has_elements() && properties_count() == 0 &&
1256            properties()->length() == 0;
1257   }
1258 
IsEmptyObjectLiteral()1259   bool IsEmptyObjectLiteral() const {
1260     return is_empty() && !has_null_prototype();
1261   }
1262 
1263   // Populate the depth field and flags, returns the depth.
1264   int InitDepthAndFlags();
1265 
1266   // Get the boilerplate description, populating it if necessary.
1267   template <typename IsolateT>
GetOrBuildBoilerplateDescription(IsolateT * isolate)1268   Handle<ObjectBoilerplateDescription> GetOrBuildBoilerplateDescription(
1269       IsolateT* isolate) {
1270     if (boilerplate_description_.is_null()) {
1271       BuildBoilerplateDescription(isolate);
1272     }
1273     return boilerplate_description();
1274   }
1275 
1276   // Populate the boilerplate description.
1277   template <typename IsolateT>
1278   void BuildBoilerplateDescription(IsolateT* isolate);
1279 
1280   // Mark all computed expressions that are bound to a key that
1281   // is shadowed by a later occurrence of the same key. For the
1282   // marked expressions, no store code is emitted.
1283   void CalculateEmitStore(Zone* zone);
1284 
1285   // Determines whether the {CreateShallowObjectLiteratal} builtin can be used.
1286   bool IsFastCloningSupported() const;
1287 
1288   // Assemble bitfield of flags for the CreateObjectLiteral helper.
1289   int ComputeFlags(bool disable_mementos = false) const {
1290     int flags = AggregateLiteral::ComputeFlags(disable_mementos);
1291     if (fast_elements()) flags |= kFastElements;
1292     if (has_null_prototype()) flags |= kHasNullPrototype;
1293     return flags;
1294   }
1295 
EncodeLiteralType()1296   int EncodeLiteralType() {
1297     int flags = kNoFlags;
1298     if (fast_elements()) flags |= kFastElements;
1299     if (has_null_prototype()) flags |= kHasNullPrototype;
1300     return flags;
1301   }
1302 
home_object()1303   Variable* home_object() const { return home_object_; }
1304 
1305   enum Flags {
1306     kFastElements = 1 << 3,
1307     kHasNullPrototype = 1 << 4,
1308   };
1309   STATIC_ASSERT(
1310       static_cast<int>(AggregateLiteral::kNeedsInitialAllocationSite) <
1311       static_cast<int>(kFastElements));
1312 
1313  private:
1314   friend class AstNodeFactory;
1315   friend Zone;
1316 
ObjectLiteral(Zone * zone,const ScopedPtrList<Property> & properties,uint32_t boilerplate_properties,int pos,bool has_rest_property,Variable * home_object)1317   ObjectLiteral(Zone* zone, const ScopedPtrList<Property>& properties,
1318                 uint32_t boilerplate_properties, int pos,
1319                 bool has_rest_property, Variable* home_object)
1320       : AggregateLiteral(pos, kObjectLiteral),
1321         boilerplate_properties_(boilerplate_properties),
1322         properties_(properties.ToConstVector(), zone),
1323         home_object_(home_object) {
1324     bit_field_ |= HasElementsField::encode(false) |
1325                   HasRestPropertyField::encode(has_rest_property) |
1326                   FastElementsField::encode(false) |
1327                   HasNullPrototypeField::encode(false);
1328   }
1329 
1330   void InitFlagsForPendingNullPrototype(int i);
1331 
set_has_elements(bool has_elements)1332   void set_has_elements(bool has_elements) {
1333     bit_field_ = HasElementsField::update(bit_field_, has_elements);
1334   }
set_fast_elements(bool fast_elements)1335   void set_fast_elements(bool fast_elements) {
1336     bit_field_ = FastElementsField::update(bit_field_, fast_elements);
1337   }
set_has_null_protoype(bool has_null_prototype)1338   void set_has_null_protoype(bool has_null_prototype) {
1339     bit_field_ = HasNullPrototypeField::update(bit_field_, has_null_prototype);
1340   }
1341   uint32_t boilerplate_properties_;
1342   Handle<ObjectBoilerplateDescription> boilerplate_description_;
1343   ZoneList<Property*> properties_;
1344   Variable* home_object_;
1345 
1346   using HasElementsField = AggregateLiteral::NextBitField<bool, 1>;
1347   using HasRestPropertyField = HasElementsField::Next<bool, 1>;
1348   using FastElementsField = HasRestPropertyField::Next<bool, 1>;
1349   using HasNullPrototypeField = FastElementsField::Next<bool, 1>;
1350 };
1351 
1352 // An array literal has a literals object that is used
1353 // for minimizing the work when constructing it at runtime.
1354 class ArrayLiteral final : public AggregateLiteral {
1355  public:
boilerplate_description()1356   Handle<ArrayBoilerplateDescription> boilerplate_description() const {
1357     return boilerplate_description_;
1358   }
1359 
values()1360   const ZonePtrList<Expression>* values() const { return &values_; }
1361 
first_spread_index()1362   int first_spread_index() const { return first_spread_index_; }
1363 
1364   // Populate the depth field and flags, returns the depth.
1365   int InitDepthAndFlags();
1366 
1367   // Get the boilerplate description, populating it if necessary.
1368   template <typename IsolateT>
GetOrBuildBoilerplateDescription(IsolateT * isolate)1369   Handle<ArrayBoilerplateDescription> GetOrBuildBoilerplateDescription(
1370       IsolateT* isolate) {
1371     if (boilerplate_description_.is_null()) {
1372       BuildBoilerplateDescription(isolate);
1373     }
1374     return boilerplate_description_;
1375   }
1376 
1377   // Populate the boilerplate description.
1378   template <typename IsolateT>
1379   void BuildBoilerplateDescription(IsolateT* isolate);
1380 
1381   // Determines whether the {CreateShallowArrayLiteral} builtin can be used.
1382   bool IsFastCloningSupported() const;
1383 
1384   // Assemble bitfield of flags for the CreateArrayLiteral helper.
1385   int ComputeFlags(bool disable_mementos = false) const {
1386     return AggregateLiteral::ComputeFlags(disable_mementos);
1387   }
1388 
1389  private:
1390   friend class AstNodeFactory;
1391   friend Zone;
1392 
ArrayLiteral(Zone * zone,const ScopedPtrList<Expression> & values,int first_spread_index,int pos)1393   ArrayLiteral(Zone* zone, const ScopedPtrList<Expression>& values,
1394                int first_spread_index, int pos)
1395       : AggregateLiteral(pos, kArrayLiteral),
1396         first_spread_index_(first_spread_index),
1397         values_(values.ToConstVector(), zone) {}
1398 
1399   int first_spread_index_;
1400   Handle<ArrayBoilerplateDescription> boilerplate_description_;
1401   ZonePtrList<Expression> values_;
1402 };
1403 
1404 enum class HoleCheckMode { kRequired, kElided };
1405 
1406 class ThisExpression final : public Expression {
1407  private:
1408   friend class AstNodeFactory;
1409   friend Zone;
ThisExpression(int pos)1410   explicit ThisExpression(int pos) : Expression(pos, kThisExpression) {}
1411 };
1412 
1413 class VariableProxy final : public Expression {
1414  public:
IsValidReferenceExpression()1415   bool IsValidReferenceExpression() const { return !is_new_target(); }
1416 
name()1417   Handle<String> name() const { return raw_name()->string(); }
raw_name()1418   const AstRawString* raw_name() const {
1419     return is_resolved() ? var_->raw_name() : raw_name_;
1420   }
1421 
var()1422   Variable* var() const {
1423     DCHECK(is_resolved());
1424     return var_;
1425   }
set_var(Variable * v)1426   void set_var(Variable* v) {
1427     DCHECK(!is_resolved());
1428     DCHECK_NOT_NULL(v);
1429     var_ = v;
1430   }
1431 
location()1432   Scanner::Location location() {
1433     return Scanner::Location(position(), position() + raw_name()->length());
1434   }
1435 
is_assigned()1436   bool is_assigned() const { return IsAssignedField::decode(bit_field_); }
set_is_assigned()1437   void set_is_assigned() {
1438     bit_field_ = IsAssignedField::update(bit_field_, true);
1439     if (is_resolved()) {
1440       var()->SetMaybeAssigned();
1441     }
1442   }
clear_is_assigned()1443   void clear_is_assigned() {
1444     bit_field_ = IsAssignedField::update(bit_field_, false);
1445   }
1446 
is_resolved()1447   bool is_resolved() const { return IsResolvedField::decode(bit_field_); }
set_is_resolved()1448   void set_is_resolved() {
1449     bit_field_ = IsResolvedField::update(bit_field_, true);
1450   }
1451 
is_new_target()1452   bool is_new_target() const { return IsNewTargetField::decode(bit_field_); }
set_is_new_target()1453   void set_is_new_target() {
1454     bit_field_ = IsNewTargetField::update(bit_field_, true);
1455   }
1456 
hole_check_mode()1457   HoleCheckMode hole_check_mode() const {
1458     HoleCheckMode mode = HoleCheckModeField::decode(bit_field_);
1459     DCHECK_IMPLIES(mode == HoleCheckMode::kRequired,
1460                    var()->binding_needs_init() ||
1461                        var()->local_if_not_shadowed()->binding_needs_init());
1462     return mode;
1463   }
set_needs_hole_check()1464   void set_needs_hole_check() {
1465     bit_field_ =
1466         HoleCheckModeField::update(bit_field_, HoleCheckMode::kRequired);
1467   }
1468 
IsPrivateName()1469   bool IsPrivateName() const { return raw_name()->IsPrivateName(); }
1470 
1471   // Bind this proxy to the variable var.
1472   void BindTo(Variable* var);
1473 
next_unresolved()1474   V8_INLINE VariableProxy* next_unresolved() { return next_unresolved_; }
is_removed_from_unresolved()1475   V8_INLINE bool is_removed_from_unresolved() const {
1476     return IsRemovedFromUnresolvedField::decode(bit_field_);
1477   }
1478 
mark_removed_from_unresolved()1479   void mark_removed_from_unresolved() {
1480     bit_field_ = IsRemovedFromUnresolvedField::update(bit_field_, true);
1481   }
1482 
1483   // Provides filtered access to the unresolved variable proxy threaded list.
1484   struct UnresolvedNext {
filterUnresolvedNext1485     static VariableProxy** filter(VariableProxy** t) {
1486       VariableProxy** n = t;
1487       // Skip over possibly removed values.
1488       while (*n != nullptr && (*n)->is_removed_from_unresolved()) {
1489         n = (*n)->next();
1490       }
1491       return n;
1492     }
1493 
startUnresolvedNext1494     static VariableProxy** start(VariableProxy** head) { return filter(head); }
1495 
nextUnresolvedNext1496     static VariableProxy** next(VariableProxy* t) { return filter(t->next()); }
1497   };
1498 
1499  private:
1500   friend class AstNodeFactory;
1501   friend Zone;
1502 
1503   VariableProxy(Variable* var, int start_position);
1504 
VariableProxy(const AstRawString * name,VariableKind variable_kind,int start_position)1505   VariableProxy(const AstRawString* name, VariableKind variable_kind,
1506                 int start_position)
1507       : Expression(start_position, kVariableProxy),
1508         raw_name_(name),
1509         next_unresolved_(nullptr) {
1510     DCHECK_NE(THIS_VARIABLE, variable_kind);
1511     bit_field_ |= IsAssignedField::encode(false) |
1512                   IsResolvedField::encode(false) |
1513                   IsRemovedFromUnresolvedField::encode(false) |
1514                   HoleCheckModeField::encode(HoleCheckMode::kElided);
1515   }
1516 
1517   explicit VariableProxy(const VariableProxy* copy_from);
1518 
1519   using IsAssignedField = Expression::NextBitField<bool, 1>;
1520   using IsResolvedField = IsAssignedField::Next<bool, 1>;
1521   using IsRemovedFromUnresolvedField = IsResolvedField::Next<bool, 1>;
1522   using IsNewTargetField = IsRemovedFromUnresolvedField::Next<bool, 1>;
1523   using HoleCheckModeField = IsNewTargetField::Next<HoleCheckMode, 1>;
1524 
1525   union {
1526     const AstRawString* raw_name_;  // if !is_resolved_
1527     Variable* var_;                 // if is_resolved_
1528   };
1529 
next()1530   V8_INLINE VariableProxy** next() { return &next_unresolved_; }
1531   VariableProxy* next_unresolved_;
1532 
1533   friend base::ThreadedListTraits<VariableProxy>;
1534 };
1535 
1536 // Wraps an optional chain to provide a wrapper for jump labels.
1537 class OptionalChain final : public Expression {
1538  public:
expression()1539   Expression* expression() const { return expression_; }
1540 
1541  private:
1542   friend class AstNodeFactory;
1543   friend Zone;
1544 
OptionalChain(Expression * expression)1545   explicit OptionalChain(Expression* expression)
1546       : Expression(0, kOptionalChain), expression_(expression) {}
1547 
1548   Expression* expression_;
1549 };
1550 
1551 // Assignments to a property will use one of several types of property access.
1552 // Otherwise, the assignment is to a non-property (a global, a local slot, a
1553 // parameter slot, or a destructuring pattern).
1554 enum AssignType {
1555   NON_PROPERTY,              // destructuring
1556   NAMED_PROPERTY,            // obj.key
1557   KEYED_PROPERTY,            // obj[key]
1558   NAMED_SUPER_PROPERTY,      // super.key
1559   KEYED_SUPER_PROPERTY,      // super[key]
1560   PRIVATE_METHOD,            // obj.#key: #key is a private method
1561   PRIVATE_GETTER_ONLY,       // obj.#key: #key only has a getter defined
1562   PRIVATE_SETTER_ONLY,       // obj.#key: #key only has a setter defined
1563   PRIVATE_GETTER_AND_SETTER  // obj.#key: #key has both accessors defined
1564 };
1565 
1566 class Property final : public Expression {
1567  public:
is_optional_chain_link()1568   bool is_optional_chain_link() const {
1569     return IsOptionalChainLinkField::decode(bit_field_);
1570   }
1571 
IsValidReferenceExpression()1572   bool IsValidReferenceExpression() const { return true; }
1573 
obj()1574   Expression* obj() const { return obj_; }
key()1575   Expression* key() const { return key_; }
1576 
IsSuperAccess()1577   bool IsSuperAccess() { return obj()->IsSuperPropertyReference(); }
IsPrivateReference()1578   bool IsPrivateReference() const { return key()->IsPrivateName(); }
1579 
1580   // Returns the properties assign type.
GetAssignType(Property * property)1581   static AssignType GetAssignType(Property* property) {
1582     if (property == nullptr) return NON_PROPERTY;
1583     if (property->IsPrivateReference()) {
1584       DCHECK(!property->IsSuperAccess());
1585       VariableProxy* proxy = property->key()->AsVariableProxy();
1586       DCHECK_NOT_NULL(proxy);
1587       Variable* var = proxy->var();
1588 
1589       switch (var->mode()) {
1590         case VariableMode::kPrivateMethod:
1591           return PRIVATE_METHOD;
1592         case VariableMode::kConst:
1593           return KEYED_PROPERTY;  // Use KEYED_PROPERTY for private fields.
1594         case VariableMode::kPrivateGetterOnly:
1595           return PRIVATE_GETTER_ONLY;
1596         case VariableMode::kPrivateSetterOnly:
1597           return PRIVATE_SETTER_ONLY;
1598         case VariableMode::kPrivateGetterAndSetter:
1599           return PRIVATE_GETTER_AND_SETTER;
1600         default:
1601           UNREACHABLE();
1602       }
1603     }
1604     bool super_access = property->IsSuperAccess();
1605     return (property->key()->IsPropertyName())
1606                ? (super_access ? NAMED_SUPER_PROPERTY : NAMED_PROPERTY)
1607                : (super_access ? KEYED_SUPER_PROPERTY : KEYED_PROPERTY);
1608   }
1609 
1610  private:
1611   friend class AstNodeFactory;
1612   friend Zone;
1613 
Property(Expression * obj,Expression * key,int pos,bool optional_chain)1614   Property(Expression* obj, Expression* key, int pos, bool optional_chain)
1615       : Expression(pos, kProperty), obj_(obj), key_(key) {
1616     bit_field_ |= IsOptionalChainLinkField::encode(optional_chain);
1617   }
1618 
1619   using IsOptionalChainLinkField = Expression::NextBitField<bool, 1>;
1620 
1621   Expression* obj_;
1622   Expression* key_;
1623 };
1624 
1625 class CallBase : public Expression {
1626  public:
expression()1627   Expression* expression() const { return expression_; }
arguments()1628   const ZonePtrList<Expression>* arguments() const { return &arguments_; }
1629 
1630   enum SpreadPosition { kNoSpread, kHasFinalSpread, kHasNonFinalSpread };
spread_position()1631   SpreadPosition spread_position() const {
1632     return SpreadPositionField::decode(bit_field_);
1633   }
1634 
1635  protected:
CallBase(Zone * zone,NodeType type,Expression * expression,const ScopedPtrList<Expression> & arguments,int pos,bool has_spread)1636   CallBase(Zone* zone, NodeType type, Expression* expression,
1637            const ScopedPtrList<Expression>& arguments, int pos, bool has_spread)
1638       : Expression(pos, type),
1639         expression_(expression),
1640         arguments_(arguments.ToConstVector(), zone) {
1641     DCHECK(type == kCall || type == kCallNew);
1642     if (has_spread) {
1643       ComputeSpreadPosition();
1644     } else {
1645       bit_field_ |= SpreadPositionField::encode(kNoSpread);
1646     }
1647   }
1648 
1649   // Only valid to be called if there is a spread in arguments_.
1650   void ComputeSpreadPosition();
1651 
1652   using SpreadPositionField = Expression::NextBitField<SpreadPosition, 2>;
1653 
1654   template <class T, int size>
1655   using NextBitField = SpreadPositionField::Next<T, size>;
1656 
1657   Expression* expression_;
1658   ZonePtrList<Expression> arguments_;
1659 };
1660 
1661 class Call final : public CallBase {
1662  public:
is_possibly_eval()1663   bool is_possibly_eval() const {
1664     return IsPossiblyEvalField::decode(bit_field_);
1665   }
1666 
is_tagged_template()1667   bool is_tagged_template() const {
1668     return IsTaggedTemplateField::decode(bit_field_);
1669   }
1670 
is_optional_chain_link()1671   bool is_optional_chain_link() const {
1672     return IsOptionalChainLinkField::decode(bit_field_);
1673   }
1674 
1675   enum CallType {
1676     GLOBAL_CALL,
1677     WITH_CALL,
1678     NAMED_PROPERTY_CALL,
1679     KEYED_PROPERTY_CALL,
1680     NAMED_OPTIONAL_CHAIN_PROPERTY_CALL,
1681     KEYED_OPTIONAL_CHAIN_PROPERTY_CALL,
1682     NAMED_SUPER_PROPERTY_CALL,
1683     KEYED_SUPER_PROPERTY_CALL,
1684     PRIVATE_CALL,
1685     PRIVATE_OPTIONAL_CHAIN_CALL,
1686     SUPER_CALL,
1687     OTHER_CALL,
1688   };
1689 
1690   enum PossiblyEval {
1691     IS_POSSIBLY_EVAL,
1692     NOT_EVAL,
1693   };
1694 
1695   // Helpers to determine how to handle the call.
1696   CallType GetCallType() const;
1697 
1698   enum class TaggedTemplateTag { kTrue };
1699 
1700  private:
1701   friend class AstNodeFactory;
1702   friend Zone;
1703 
Call(Zone * zone,Expression * expression,const ScopedPtrList<Expression> & arguments,int pos,bool has_spread,PossiblyEval possibly_eval,bool optional_chain)1704   Call(Zone* zone, Expression* expression,
1705        const ScopedPtrList<Expression>& arguments, int pos, bool has_spread,
1706        PossiblyEval possibly_eval, bool optional_chain)
1707       : CallBase(zone, kCall, expression, arguments, pos, has_spread) {
1708     bit_field_ |=
1709         IsPossiblyEvalField::encode(possibly_eval == IS_POSSIBLY_EVAL) |
1710         IsTaggedTemplateField::encode(false) |
1711         IsOptionalChainLinkField::encode(optional_chain);
1712   }
1713 
Call(Zone * zone,Expression * expression,const ScopedPtrList<Expression> & arguments,int pos,TaggedTemplateTag tag)1714   Call(Zone* zone, Expression* expression,
1715        const ScopedPtrList<Expression>& arguments, int pos,
1716        TaggedTemplateTag tag)
1717       : CallBase(zone, kCall, expression, arguments, pos, false) {
1718     bit_field_ |= IsPossiblyEvalField::encode(false) |
1719                   IsTaggedTemplateField::encode(true) |
1720                   IsOptionalChainLinkField::encode(false);
1721   }
1722 
1723   using IsPossiblyEvalField = CallBase::NextBitField<bool, 1>;
1724   using IsTaggedTemplateField = IsPossiblyEvalField::Next<bool, 1>;
1725   using IsOptionalChainLinkField = IsTaggedTemplateField::Next<bool, 1>;
1726 };
1727 
1728 class CallNew final : public CallBase {
1729  private:
1730   friend class AstNodeFactory;
1731   friend Zone;
1732 
CallNew(Zone * zone,Expression * expression,const ScopedPtrList<Expression> & arguments,int pos,bool has_spread)1733   CallNew(Zone* zone, Expression* expression,
1734           const ScopedPtrList<Expression>& arguments, int pos, bool has_spread)
1735       : CallBase(zone, kCallNew, expression, arguments, pos, has_spread) {}
1736 };
1737 
1738 // The CallRuntime class does not represent any official JavaScript
1739 // language construct. Instead it is used to call a C or JS function
1740 // with a set of arguments. This is used from the builtins that are
1741 // implemented in JavaScript.
1742 class CallRuntime final : public Expression {
1743  public:
arguments()1744   const ZonePtrList<Expression>* arguments() const { return &arguments_; }
is_jsruntime()1745   bool is_jsruntime() const { return function_ == nullptr; }
1746 
context_index()1747   int context_index() const {
1748     DCHECK(is_jsruntime());
1749     return context_index_;
1750   }
function()1751   const Runtime::Function* function() const {
1752     DCHECK(!is_jsruntime());
1753     return function_;
1754   }
1755 
1756   const char* debug_name();
1757 
1758  private:
1759   friend class AstNodeFactory;
1760   friend Zone;
1761 
CallRuntime(Zone * zone,const Runtime::Function * function,const ScopedPtrList<Expression> & arguments,int pos)1762   CallRuntime(Zone* zone, const Runtime::Function* function,
1763               const ScopedPtrList<Expression>& arguments, int pos)
1764       : Expression(pos, kCallRuntime),
1765         function_(function),
1766         arguments_(arguments.ToConstVector(), zone) {}
CallRuntime(Zone * zone,int context_index,const ScopedPtrList<Expression> & arguments,int pos)1767   CallRuntime(Zone* zone, int context_index,
1768               const ScopedPtrList<Expression>& arguments, int pos)
1769       : Expression(pos, kCallRuntime),
1770         context_index_(context_index),
1771         function_(nullptr),
1772         arguments_(arguments.ToConstVector(), zone) {}
1773 
1774   int context_index_;
1775   const Runtime::Function* function_;
1776   ZonePtrList<Expression> arguments_;
1777 };
1778 
1779 
1780 class UnaryOperation final : public Expression {
1781  public:
op()1782   Token::Value op() const { return OperatorField::decode(bit_field_); }
expression()1783   Expression* expression() const { return expression_; }
1784 
1785  private:
1786   friend class AstNodeFactory;
1787   friend Zone;
1788 
UnaryOperation(Token::Value op,Expression * expression,int pos)1789   UnaryOperation(Token::Value op, Expression* expression, int pos)
1790       : Expression(pos, kUnaryOperation), expression_(expression) {
1791     bit_field_ |= OperatorField::encode(op);
1792     DCHECK(Token::IsUnaryOp(op));
1793   }
1794 
1795   Expression* expression_;
1796 
1797   using OperatorField = Expression::NextBitField<Token::Value, 7>;
1798 };
1799 
1800 
1801 class BinaryOperation final : public Expression {
1802  public:
op()1803   Token::Value op() const { return OperatorField::decode(bit_field_); }
left()1804   Expression* left() const { return left_; }
right()1805   Expression* right() const { return right_; }
1806 
1807   // Returns true if one side is a Smi literal, returning the other side's
1808   // sub-expression in |subexpr| and the literal Smi in |literal|.
1809   bool IsSmiLiteralOperation(Expression** subexpr, Smi* literal);
1810 
1811  private:
1812   friend class AstNodeFactory;
1813   friend Zone;
1814 
BinaryOperation(Token::Value op,Expression * left,Expression * right,int pos)1815   BinaryOperation(Token::Value op, Expression* left, Expression* right, int pos)
1816       : Expression(pos, kBinaryOperation), left_(left), right_(right) {
1817     bit_field_ |= OperatorField::encode(op);
1818     DCHECK(Token::IsBinaryOp(op));
1819   }
1820 
1821   Expression* left_;
1822   Expression* right_;
1823 
1824   using OperatorField = Expression::NextBitField<Token::Value, 7>;
1825 };
1826 
1827 class NaryOperation final : public Expression {
1828  public:
op()1829   Token::Value op() const { return OperatorField::decode(bit_field_); }
first()1830   Expression* first() const { return first_; }
subsequent(size_t index)1831   Expression* subsequent(size_t index) const {
1832     return subsequent_[index].expression;
1833   }
1834 
subsequent_length()1835   size_t subsequent_length() const { return subsequent_.size(); }
subsequent_op_position(size_t index)1836   int subsequent_op_position(size_t index) const {
1837     return subsequent_[index].op_position;
1838   }
1839 
AddSubsequent(Expression * expr,int pos)1840   void AddSubsequent(Expression* expr, int pos) {
1841     subsequent_.emplace_back(expr, pos);
1842   }
1843 
1844  private:
1845   friend class AstNodeFactory;
1846   friend Zone;
1847 
NaryOperation(Zone * zone,Token::Value op,Expression * first,size_t initial_subsequent_size)1848   NaryOperation(Zone* zone, Token::Value op, Expression* first,
1849                 size_t initial_subsequent_size)
1850       : Expression(first->position(), kNaryOperation),
1851         first_(first),
1852         subsequent_(zone) {
1853     bit_field_ |= OperatorField::encode(op);
1854     DCHECK(Token::IsBinaryOp(op));
1855     DCHECK_NE(op, Token::EXP);
1856     subsequent_.reserve(initial_subsequent_size);
1857   }
1858 
1859   // Nary operations store the first (lhs) child expression inline, and the
1860   // child expressions (rhs of each op) are stored out-of-line, along with
1861   // their operation's position. Note that the Nary operation expression's
1862   // position has no meaning.
1863   //
1864   // So an nary add:
1865   //
1866   //    expr + expr + expr + ...
1867   //
1868   // is stored as:
1869   //
1870   //    (expr) [(+ expr), (+ expr), ...]
1871   //    '-.--' '-----------.-----------'
1872   //    first    subsequent entry list
1873 
1874   Expression* first_;
1875 
1876   struct NaryOperationEntry {
1877     Expression* expression;
1878     int op_position;
NaryOperationEntryNaryOperationEntry1879     NaryOperationEntry(Expression* e, int pos)
1880         : expression(e), op_position(pos) {}
1881   };
1882   ZoneVector<NaryOperationEntry> subsequent_;
1883 
1884   using OperatorField = Expression::NextBitField<Token::Value, 7>;
1885 };
1886 
1887 class CountOperation final : public Expression {
1888  public:
is_prefix()1889   bool is_prefix() const { return IsPrefixField::decode(bit_field_); }
is_postfix()1890   bool is_postfix() const { return !is_prefix(); }
1891 
op()1892   Token::Value op() const { return TokenField::decode(bit_field_); }
1893 
expression()1894   Expression* expression() const { return expression_; }
1895 
1896  private:
1897   friend class AstNodeFactory;
1898   friend Zone;
1899 
CountOperation(Token::Value op,bool is_prefix,Expression * expr,int pos)1900   CountOperation(Token::Value op, bool is_prefix, Expression* expr, int pos)
1901       : Expression(pos, kCountOperation), expression_(expr) {
1902     bit_field_ |= IsPrefixField::encode(is_prefix) | TokenField::encode(op);
1903   }
1904 
1905   using IsPrefixField = Expression::NextBitField<bool, 1>;
1906   using TokenField = IsPrefixField::Next<Token::Value, 7>;
1907 
1908   Expression* expression_;
1909 };
1910 
1911 
1912 class CompareOperation final : public Expression {
1913  public:
op()1914   Token::Value op() const { return OperatorField::decode(bit_field_); }
left()1915   Expression* left() const { return left_; }
right()1916   Expression* right() const { return right_; }
1917 
1918   // Match special cases.
1919   bool IsLiteralCompareTypeof(Expression** expr, Literal** literal);
1920   bool IsLiteralCompareUndefined(Expression** expr);
1921   bool IsLiteralCompareNull(Expression** expr);
1922 
1923  private:
1924   friend class AstNodeFactory;
1925   friend Zone;
1926 
CompareOperation(Token::Value op,Expression * left,Expression * right,int pos)1927   CompareOperation(Token::Value op, Expression* left, Expression* right,
1928                    int pos)
1929       : Expression(pos, kCompareOperation), left_(left), right_(right) {
1930     bit_field_ |= OperatorField::encode(op);
1931     DCHECK(Token::IsCompareOp(op));
1932   }
1933 
1934   Expression* left_;
1935   Expression* right_;
1936 
1937   using OperatorField = Expression::NextBitField<Token::Value, 7>;
1938 };
1939 
1940 
1941 class Spread final : public Expression {
1942  public:
expression()1943   Expression* expression() const { return expression_; }
1944 
expression_position()1945   int expression_position() const { return expr_pos_; }
1946 
1947  private:
1948   friend class AstNodeFactory;
1949   friend Zone;
1950 
Spread(Expression * expression,int pos,int expr_pos)1951   Spread(Expression* expression, int pos, int expr_pos)
1952       : Expression(pos, kSpread),
1953         expr_pos_(expr_pos),
1954         expression_(expression) {}
1955 
1956   int expr_pos_;
1957   Expression* expression_;
1958 };
1959 
1960 class Conditional final : public Expression {
1961  public:
condition()1962   Expression* condition() const { return condition_; }
then_expression()1963   Expression* then_expression() const { return then_expression_; }
else_expression()1964   Expression* else_expression() const { return else_expression_; }
1965 
1966  private:
1967   friend class AstNodeFactory;
1968   friend Zone;
1969 
Conditional(Expression * condition,Expression * then_expression,Expression * else_expression,int position)1970   Conditional(Expression* condition, Expression* then_expression,
1971               Expression* else_expression, int position)
1972       : Expression(position, kConditional),
1973         condition_(condition),
1974         then_expression_(then_expression),
1975         else_expression_(else_expression) {}
1976 
1977   Expression* condition_;
1978   Expression* then_expression_;
1979   Expression* else_expression_;
1980 };
1981 
1982 class Assignment : public Expression {
1983  public:
op()1984   Token::Value op() const { return TokenField::decode(bit_field_); }
target()1985   Expression* target() const { return target_; }
value()1986   Expression* value() const { return value_; }
1987 
1988   // The assignment was generated as part of block-scoped sloppy-mode
1989   // function hoisting, see
1990   // ES#sec-block-level-function-declarations-web-legacy-compatibility-semantics
lookup_hoisting_mode()1991   LookupHoistingMode lookup_hoisting_mode() const {
1992     return static_cast<LookupHoistingMode>(
1993         LookupHoistingModeField::decode(bit_field_));
1994   }
set_lookup_hoisting_mode(LookupHoistingMode mode)1995   void set_lookup_hoisting_mode(LookupHoistingMode mode) {
1996     bit_field_ =
1997         LookupHoistingModeField::update(bit_field_, static_cast<bool>(mode));
1998   }
1999 
2000  protected:
2001   Assignment(NodeType type, Token::Value op, Expression* target,
2002              Expression* value, int pos);
2003 
2004  private:
2005   friend class AstNodeFactory;
2006   friend Zone;
2007 
2008   using TokenField = Expression::NextBitField<Token::Value, 7>;
2009   using LookupHoistingModeField = TokenField::Next<bool, 1>;
2010 
2011   Expression* target_;
2012   Expression* value_;
2013 };
2014 
2015 class CompoundAssignment final : public Assignment {
2016  public:
binary_operation()2017   BinaryOperation* binary_operation() const { return binary_operation_; }
2018 
2019  private:
2020   friend class AstNodeFactory;
2021   friend Zone;
2022 
CompoundAssignment(Token::Value op,Expression * target,Expression * value,int pos,BinaryOperation * binary_operation)2023   CompoundAssignment(Token::Value op, Expression* target, Expression* value,
2024                      int pos, BinaryOperation* binary_operation)
2025       : Assignment(kCompoundAssignment, op, target, value, pos),
2026         binary_operation_(binary_operation) {}
2027 
2028   BinaryOperation* binary_operation_;
2029 };
2030 
2031 // There are several types of Suspend node:
2032 //
2033 // Yield
2034 // YieldStar
2035 // Await
2036 //
2037 // Our Yield is different from the JS yield in that it "returns" its argument as
2038 // is, without wrapping it in an iterator result object.  Such wrapping, if
2039 // desired, must be done beforehand (see the parser).
2040 class Suspend : public Expression {
2041  public:
2042   // With {kNoControl}, the {Suspend} behaves like yield, except that it never
2043   // throws and never causes the current generator to return. This is used to
2044   // desugar yield*.
2045   // TODO(caitp): remove once yield* desugaring for async generators is handled
2046   // in BytecodeGenerator.
2047   enum OnAbruptResume { kOnExceptionThrow, kNoControl };
2048 
expression()2049   Expression* expression() const { return expression_; }
on_abrupt_resume()2050   OnAbruptResume on_abrupt_resume() const {
2051     return OnAbruptResumeField::decode(bit_field_);
2052   }
2053 
2054  private:
2055   friend class AstNodeFactory;
2056   friend Zone;
2057   friend class Yield;
2058   friend class YieldStar;
2059   friend class Await;
2060 
Suspend(NodeType node_type,Expression * expression,int pos,OnAbruptResume on_abrupt_resume)2061   Suspend(NodeType node_type, Expression* expression, int pos,
2062           OnAbruptResume on_abrupt_resume)
2063       : Expression(pos, node_type), expression_(expression) {
2064     bit_field_ |= OnAbruptResumeField::encode(on_abrupt_resume);
2065   }
2066 
2067   Expression* expression_;
2068 
2069   using OnAbruptResumeField = Expression::NextBitField<OnAbruptResume, 1>;
2070 };
2071 
2072 class Yield final : public Suspend {
2073  private:
2074   friend class AstNodeFactory;
2075   friend Zone;
Yield(Expression * expression,int pos,OnAbruptResume on_abrupt_resume)2076   Yield(Expression* expression, int pos, OnAbruptResume on_abrupt_resume)
2077       : Suspend(kYield, expression, pos, on_abrupt_resume) {}
2078 };
2079 
2080 class YieldStar final : public Suspend {
2081  private:
2082   friend class AstNodeFactory;
2083   friend Zone;
YieldStar(Expression * expression,int pos)2084   YieldStar(Expression* expression, int pos)
2085       : Suspend(kYieldStar, expression, pos,
2086                 Suspend::OnAbruptResume::kNoControl) {}
2087 };
2088 
2089 class Await final : public Suspend {
2090  private:
2091   friend class AstNodeFactory;
2092   friend Zone;
2093 
Await(Expression * expression,int pos)2094   Await(Expression* expression, int pos)
2095       : Suspend(kAwait, expression, pos, Suspend::kOnExceptionThrow) {}
2096 };
2097 
2098 class Throw final : public Expression {
2099  public:
exception()2100   Expression* exception() const { return exception_; }
2101 
2102  private:
2103   friend class AstNodeFactory;
2104   friend Zone;
2105 
Throw(Expression * exception,int pos)2106   Throw(Expression* exception, int pos)
2107       : Expression(pos, kThrow), exception_(exception) {}
2108 
2109   Expression* exception_;
2110 };
2111 
2112 
2113 class FunctionLiteral final : public Expression {
2114  public:
2115   enum ParameterFlag : uint8_t {
2116     kNoDuplicateParameters,
2117     kHasDuplicateParameters
2118   };
2119   enum EagerCompileHint : uint8_t { kShouldEagerCompile, kShouldLazyCompile };
2120 
2121   // Empty handle means that the function does not have a shared name (i.e.
2122   // the name will be set dynamically after creation of the function closure).
2123   template <typename IsolateT>
GetName(IsolateT * isolate)2124   MaybeHandle<String> GetName(IsolateT* isolate) const {
2125     return raw_name_ ? raw_name_->AllocateFlat(isolate) : MaybeHandle<String>();
2126   }
has_shared_name()2127   bool has_shared_name() const { return raw_name_ != nullptr; }
raw_name()2128   const AstConsString* raw_name() const { return raw_name_; }
set_raw_name(const AstConsString * name)2129   void set_raw_name(const AstConsString* name) { raw_name_ = name; }
scope()2130   DeclarationScope* scope() const { return scope_; }
body()2131   ZonePtrList<Statement>* body() { return &body_; }
set_function_token_position(int pos)2132   void set_function_token_position(int pos) { function_token_position_ = pos; }
function_token_position()2133   int function_token_position() const { return function_token_position_; }
2134   int start_position() const;
2135   int end_position() const;
is_anonymous_expression()2136   bool is_anonymous_expression() const {
2137     return syntax_kind() == FunctionSyntaxKind::kAnonymousExpression;
2138   }
2139 
is_toplevel()2140   bool is_toplevel() const {
2141     return function_literal_id() == kFunctionLiteralIdTopLevel;
2142   }
2143   V8_EXPORT_PRIVATE LanguageMode language_mode() const;
2144 
add_expected_properties(int number_properties)2145   void add_expected_properties(int number_properties) {
2146     expected_property_count_ += number_properties;
2147   }
expected_property_count()2148   int expected_property_count() { return expected_property_count_; }
parameter_count()2149   int parameter_count() { return parameter_count_; }
function_length()2150   int function_length() { return function_length_; }
2151 
2152   bool AllowsLazyCompilation();
2153 
CanSuspend()2154   bool CanSuspend() {
2155     if (suspend_count() > 0) {
2156       DCHECK(IsResumableFunction(kind()));
2157       return true;
2158     }
2159     return false;
2160   }
2161 
2162   // Returns either name or inferred name as a cstring.
2163   std::unique_ptr<char[]> GetDebugName() const;
2164 
GetInferredName(Isolate * isolate)2165   Handle<String> GetInferredName(Isolate* isolate) {
2166     if (!inferred_name_.is_null()) {
2167       DCHECK_NULL(raw_inferred_name_);
2168       return inferred_name_;
2169     }
2170     if (raw_inferred_name_ != nullptr) {
2171       return raw_inferred_name_->GetString(isolate);
2172     }
2173     UNREACHABLE();
2174   }
GetInferredName(LocalIsolate * isolate)2175   Handle<String> GetInferredName(LocalIsolate* isolate) const {
2176     DCHECK(inferred_name_.is_null());
2177     DCHECK_NOT_NULL(raw_inferred_name_);
2178     return raw_inferred_name_->GetString(isolate);
2179   }
raw_inferred_name()2180   const AstConsString* raw_inferred_name() { return raw_inferred_name_; }
2181 
2182   // Only one of {set_inferred_name, set_raw_inferred_name} should be called.
2183   void set_inferred_name(Handle<String> inferred_name);
2184   void set_raw_inferred_name(AstConsString* raw_inferred_name);
2185 
pretenure()2186   bool pretenure() const { return Pretenure::decode(bit_field_); }
set_pretenure()2187   void set_pretenure() { bit_field_ = Pretenure::update(bit_field_, true); }
2188 
has_duplicate_parameters()2189   bool has_duplicate_parameters() const {
2190     // Not valid for lazy functions.
2191     DCHECK(ShouldEagerCompile());
2192     return HasDuplicateParameters::decode(bit_field_);
2193   }
2194 
2195   // This is used as a heuristic on when to eagerly compile a function
2196   // literal. We consider the following constructs as hints that the
2197   // function will be called immediately:
2198   // - (function() { ... })();
2199   // - var x = function() { ... }();
2200   V8_EXPORT_PRIVATE bool ShouldEagerCompile() const;
2201   V8_EXPORT_PRIVATE void SetShouldEagerCompile();
2202 
syntax_kind()2203   FunctionSyntaxKind syntax_kind() const {
2204     return FunctionSyntaxKindBits::decode(bit_field_);
2205   }
2206   FunctionKind kind() const;
2207 
dont_optimize()2208   bool dont_optimize() {
2209     return dont_optimize_reason() != BailoutReason::kNoReason;
2210   }
dont_optimize_reason()2211   BailoutReason dont_optimize_reason() {
2212     return DontOptimizeReasonField::decode(bit_field_);
2213   }
set_dont_optimize_reason(BailoutReason reason)2214   void set_dont_optimize_reason(BailoutReason reason) {
2215     bit_field_ = DontOptimizeReasonField::update(bit_field_, reason);
2216   }
2217 
IsAnonymousFunctionDefinition()2218   bool IsAnonymousFunctionDefinition() const {
2219     return is_anonymous_expression();
2220   }
2221 
suspend_count()2222   int suspend_count() { return suspend_count_; }
set_suspend_count(int suspend_count)2223   void set_suspend_count(int suspend_count) { suspend_count_ = suspend_count; }
2224 
return_position()2225   int return_position() {
2226     return std::max(
2227         start_position(),
2228         end_position() - (HasBracesField::decode(bit_field_) ? 1 : 0));
2229   }
2230 
function_literal_id()2231   int function_literal_id() const { return function_literal_id_; }
set_function_literal_id(int function_literal_id)2232   void set_function_literal_id(int function_literal_id) {
2233     function_literal_id_ = function_literal_id;
2234   }
2235 
set_requires_instance_members_initializer(bool value)2236   void set_requires_instance_members_initializer(bool value) {
2237     bit_field_ = RequiresInstanceMembersInitializer::update(bit_field_, value);
2238   }
requires_instance_members_initializer()2239   bool requires_instance_members_initializer() const {
2240     return RequiresInstanceMembersInitializer::decode(bit_field_);
2241   }
2242 
set_has_static_private_methods_or_accessors(bool value)2243   void set_has_static_private_methods_or_accessors(bool value) {
2244     bit_field_ =
2245         HasStaticPrivateMethodsOrAccessorsField::update(bit_field_, value);
2246   }
has_static_private_methods_or_accessors()2247   bool has_static_private_methods_or_accessors() const {
2248     return HasStaticPrivateMethodsOrAccessorsField::decode(bit_field_);
2249   }
2250 
set_class_scope_has_private_brand(bool value)2251   void set_class_scope_has_private_brand(bool value) {
2252     bit_field_ = ClassScopeHasPrivateBrandField::update(bit_field_, value);
2253   }
class_scope_has_private_brand()2254   bool class_scope_has_private_brand() const {
2255     return ClassScopeHasPrivateBrandField::decode(bit_field_);
2256   }
2257 
2258   bool private_name_lookup_skips_outer_class() const;
2259 
produced_preparse_data()2260   ProducedPreparseData* produced_preparse_data() const {
2261     return produced_preparse_data_;
2262   }
2263 
2264  private:
2265   friend class AstNodeFactory;
2266   friend Zone;
2267 
2268   FunctionLiteral(Zone* zone, const AstConsString* name,
2269                   AstValueFactory* ast_value_factory, DeclarationScope* scope,
2270                   const ScopedPtrList<Statement>& body,
2271                   int expected_property_count, int parameter_count,
2272                   int function_length, FunctionSyntaxKind function_syntax_kind,
2273                   ParameterFlag has_duplicate_parameters,
2274                   EagerCompileHint eager_compile_hint, int position,
2275                   bool has_braces, int function_literal_id,
2276                   ProducedPreparseData* produced_preparse_data = nullptr)
Expression(position,kFunctionLiteral)2277       : Expression(position, kFunctionLiteral),
2278         expected_property_count_(expected_property_count),
2279         parameter_count_(parameter_count),
2280         function_length_(function_length),
2281         function_token_position_(kNoSourcePosition),
2282         suspend_count_(0),
2283         function_literal_id_(function_literal_id),
2284         raw_name_(name),
2285         scope_(scope),
2286         body_(body.ToConstVector(), zone),
2287         raw_inferred_name_(ast_value_factory->empty_cons_string()),
2288         produced_preparse_data_(produced_preparse_data) {
2289     bit_field_ |= FunctionSyntaxKindBits::encode(function_syntax_kind) |
2290                   Pretenure::encode(false) |
2291                   HasDuplicateParameters::encode(has_duplicate_parameters ==
2292                                                  kHasDuplicateParameters) |
2293                   DontOptimizeReasonField::encode(BailoutReason::kNoReason) |
2294                   RequiresInstanceMembersInitializer::encode(false) |
2295                   HasBracesField::encode(has_braces);
2296     if (eager_compile_hint == kShouldEagerCompile) SetShouldEagerCompile();
2297   }
2298 
2299   using FunctionSyntaxKindBits =
2300       Expression::NextBitField<FunctionSyntaxKind, 3>;
2301   using Pretenure = FunctionSyntaxKindBits::Next<bool, 1>;
2302   using HasDuplicateParameters = Pretenure::Next<bool, 1>;
2303   using DontOptimizeReasonField =
2304       HasDuplicateParameters::Next<BailoutReason, 8>;
2305   using RequiresInstanceMembersInitializer =
2306       DontOptimizeReasonField::Next<bool, 1>;
2307   using ClassScopeHasPrivateBrandField =
2308       RequiresInstanceMembersInitializer::Next<bool, 1>;
2309   using HasStaticPrivateMethodsOrAccessorsField =
2310       ClassScopeHasPrivateBrandField::Next<bool, 1>;
2311   using HasBracesField = HasStaticPrivateMethodsOrAccessorsField::Next<bool, 1>;
2312 
2313   // expected_property_count_ is the sum of instance fields and properties.
2314   // It can vary depending on whether a function is lazily or eagerly parsed.
2315   int expected_property_count_;
2316   int parameter_count_;
2317   int function_length_;
2318   int function_token_position_;
2319   int suspend_count_;
2320   int function_literal_id_;
2321 
2322   const AstConsString* raw_name_;
2323   DeclarationScope* scope_;
2324   ZonePtrList<Statement> body_;
2325   AstConsString* raw_inferred_name_;
2326   Handle<String> inferred_name_;
2327   ProducedPreparseData* produced_preparse_data_;
2328 };
2329 
2330 // Property is used for passing information
2331 // about a class literal's properties from the parser to the code generator.
2332 class ClassLiteralProperty final : public LiteralProperty {
2333  public:
2334   enum Kind : uint8_t { METHOD, GETTER, SETTER, FIELD };
2335 
kind()2336   Kind kind() const { return kind_; }
2337 
is_static()2338   bool is_static() const { return is_static_; }
2339 
is_private()2340   bool is_private() const { return is_private_; }
2341 
set_computed_name_var(Variable * var)2342   void set_computed_name_var(Variable* var) {
2343     DCHECK_EQ(FIELD, kind());
2344     DCHECK(!is_private());
2345     private_or_computed_name_var_ = var;
2346   }
2347 
computed_name_var()2348   Variable* computed_name_var() const {
2349     DCHECK_EQ(FIELD, kind());
2350     DCHECK(!is_private());
2351     return private_or_computed_name_var_;
2352   }
2353 
set_private_name_var(Variable * var)2354   void set_private_name_var(Variable* var) {
2355     DCHECK(is_private());
2356     private_or_computed_name_var_ = var;
2357   }
private_name_var()2358   Variable* private_name_var() const {
2359     DCHECK(is_private());
2360     return private_or_computed_name_var_;
2361   }
2362 
2363  private:
2364   friend class AstNodeFactory;
2365   friend Zone;
2366 
2367   ClassLiteralProperty(Expression* key, Expression* value, Kind kind,
2368                        bool is_static, bool is_computed_name, bool is_private);
2369 
2370   Kind kind_;
2371   bool is_static_;
2372   bool is_private_;
2373   Variable* private_or_computed_name_var_;
2374 };
2375 
2376 class ClassLiteralStaticElement final : public ZoneObject {
2377  public:
2378   enum Kind : uint8_t { PROPERTY, STATIC_BLOCK };
2379 
kind()2380   Kind kind() const { return kind_; }
2381 
property()2382   ClassLiteralProperty* property() const {
2383     DCHECK(kind() == PROPERTY);
2384     return property_;
2385   }
2386 
static_block()2387   Block* static_block() const {
2388     DCHECK(kind() == STATIC_BLOCK);
2389     return static_block_;
2390   }
2391 
2392  private:
2393   friend class AstNodeFactory;
2394   friend Zone;
2395 
ClassLiteralStaticElement(ClassLiteralProperty * property)2396   explicit ClassLiteralStaticElement(ClassLiteralProperty* property)
2397       : kind_(PROPERTY), property_(property) {}
2398 
ClassLiteralStaticElement(Block * static_block)2399   explicit ClassLiteralStaticElement(Block* static_block)
2400       : kind_(STATIC_BLOCK), static_block_(static_block) {}
2401 
2402   Kind kind_;
2403 
2404   union {
2405     ClassLiteralProperty* property_;
2406     Block* static_block_;
2407   };
2408 };
2409 
2410 class InitializeClassMembersStatement final : public Statement {
2411  public:
2412   using Property = ClassLiteralProperty;
2413 
fields()2414   ZonePtrList<Property>* fields() const { return fields_; }
2415 
2416  private:
2417   friend class AstNodeFactory;
2418   friend Zone;
2419 
InitializeClassMembersStatement(ZonePtrList<Property> * fields,int pos)2420   InitializeClassMembersStatement(ZonePtrList<Property>* fields, int pos)
2421       : Statement(pos, kInitializeClassMembersStatement), fields_(fields) {}
2422 
2423   ZonePtrList<Property>* fields_;
2424 };
2425 
2426 class InitializeClassStaticElementsStatement final : public Statement {
2427  public:
2428   using StaticElement = ClassLiteralStaticElement;
2429 
elements()2430   ZonePtrList<StaticElement>* elements() const { return elements_; }
2431 
2432  private:
2433   friend class AstNodeFactory;
2434   friend Zone;
2435 
InitializeClassStaticElementsStatement(ZonePtrList<StaticElement> * elements,int pos)2436   InitializeClassStaticElementsStatement(ZonePtrList<StaticElement>* elements,
2437                                          int pos)
2438       : Statement(pos, kInitializeClassStaticElementsStatement),
2439         elements_(elements) {}
2440 
2441   ZonePtrList<StaticElement>* elements_;
2442 };
2443 
2444 class ClassLiteral final : public Expression {
2445  public:
2446   using Property = ClassLiteralProperty;
2447   using StaticElement = ClassLiteralStaticElement;
2448 
scope()2449   ClassScope* scope() const { return scope_; }
extends()2450   Expression* extends() const { return extends_; }
constructor()2451   FunctionLiteral* constructor() const { return constructor_; }
public_members()2452   ZonePtrList<Property>* public_members() const { return public_members_; }
private_members()2453   ZonePtrList<Property>* private_members() const { return private_members_; }
start_position()2454   int start_position() const { return position(); }
end_position()2455   int end_position() const { return end_position_; }
has_static_computed_names()2456   bool has_static_computed_names() const {
2457     return HasStaticComputedNames::decode(bit_field_);
2458   }
2459 
is_anonymous_expression()2460   bool is_anonymous_expression() const {
2461     return IsAnonymousExpression::decode(bit_field_);
2462   }
has_private_methods()2463   bool has_private_methods() const {
2464     return HasPrivateMethods::decode(bit_field_);
2465   }
IsAnonymousFunctionDefinition()2466   bool IsAnonymousFunctionDefinition() const {
2467     return is_anonymous_expression();
2468   }
2469 
static_initializer()2470   FunctionLiteral* static_initializer() const { return static_initializer_; }
2471 
instance_members_initializer_function()2472   FunctionLiteral* instance_members_initializer_function() const {
2473     return instance_members_initializer_function_;
2474   }
2475 
home_object()2476   Variable* home_object() const { return home_object_; }
2477 
static_home_object()2478   Variable* static_home_object() const { return static_home_object_; }
2479 
2480  private:
2481   friend class AstNodeFactory;
2482   friend Zone;
2483 
ClassLiteral(ClassScope * scope,Expression * extends,FunctionLiteral * constructor,ZonePtrList<Property> * public_members,ZonePtrList<Property> * private_members,FunctionLiteral * static_initializer,FunctionLiteral * instance_members_initializer_function,int start_position,int end_position,bool has_static_computed_names,bool is_anonymous,bool has_private_methods,Variable * home_object,Variable * static_home_object)2484   ClassLiteral(ClassScope* scope, Expression* extends,
2485                FunctionLiteral* constructor,
2486                ZonePtrList<Property>* public_members,
2487                ZonePtrList<Property>* private_members,
2488                FunctionLiteral* static_initializer,
2489                FunctionLiteral* instance_members_initializer_function,
2490                int start_position, int end_position,
2491                bool has_static_computed_names, bool is_anonymous,
2492                bool has_private_methods, Variable* home_object,
2493                Variable* static_home_object)
2494       : Expression(start_position, kClassLiteral),
2495         end_position_(end_position),
2496         scope_(scope),
2497         extends_(extends),
2498         constructor_(constructor),
2499         public_members_(public_members),
2500         private_members_(private_members),
2501         static_initializer_(static_initializer),
2502         instance_members_initializer_function_(
2503             instance_members_initializer_function),
2504         home_object_(home_object),
2505         static_home_object_(static_home_object) {
2506     bit_field_ |= HasStaticComputedNames::encode(has_static_computed_names) |
2507                   IsAnonymousExpression::encode(is_anonymous) |
2508                   HasPrivateMethods::encode(has_private_methods);
2509   }
2510 
2511   int end_position_;
2512   ClassScope* scope_;
2513   Expression* extends_;
2514   FunctionLiteral* constructor_;
2515   ZonePtrList<Property>* public_members_;
2516   ZonePtrList<Property>* private_members_;
2517   FunctionLiteral* static_initializer_;
2518   FunctionLiteral* instance_members_initializer_function_;
2519   using HasStaticComputedNames = Expression::NextBitField<bool, 1>;
2520   using IsAnonymousExpression = HasStaticComputedNames::Next<bool, 1>;
2521   using HasPrivateMethods = IsAnonymousExpression::Next<bool, 1>;
2522   Variable* home_object_;
2523   Variable* static_home_object_;
2524 };
2525 
2526 
2527 class NativeFunctionLiteral final : public Expression {
2528  public:
name()2529   Handle<String> name() const { return name_->string(); }
raw_name()2530   const AstRawString* raw_name() const { return name_; }
extension()2531   v8::Extension* extension() const { return extension_; }
2532 
2533  private:
2534   friend class AstNodeFactory;
2535   friend Zone;
2536 
NativeFunctionLiteral(const AstRawString * name,v8::Extension * extension,int pos)2537   NativeFunctionLiteral(const AstRawString* name, v8::Extension* extension,
2538                         int pos)
2539       : Expression(pos, kNativeFunctionLiteral),
2540         name_(name),
2541         extension_(extension) {}
2542 
2543   const AstRawString* name_;
2544   v8::Extension* extension_;
2545 };
2546 
2547 
2548 class SuperPropertyReference final : public Expression {
2549  public:
home_object()2550   VariableProxy* home_object() const { return home_object_; }
2551 
2552  private:
2553   friend class AstNodeFactory;
2554   friend Zone;
2555 
SuperPropertyReference(VariableProxy * home_object,int pos)2556   explicit SuperPropertyReference(VariableProxy* home_object, int pos)
2557       : Expression(pos, kSuperPropertyReference), home_object_(home_object) {}
2558 
2559   VariableProxy* home_object_;
2560 };
2561 
2562 
2563 class SuperCallReference final : public Expression {
2564  public:
new_target_var()2565   VariableProxy* new_target_var() const { return new_target_var_; }
this_function_var()2566   VariableProxy* this_function_var() const { return this_function_var_; }
2567 
2568  private:
2569   friend class AstNodeFactory;
2570   friend Zone;
2571 
2572   // We take in ThisExpression* only as a proof that it was accessed.
SuperCallReference(VariableProxy * new_target_var,VariableProxy * this_function_var,int pos)2573   SuperCallReference(VariableProxy* new_target_var,
2574                      VariableProxy* this_function_var, int pos)
2575       : Expression(pos, kSuperCallReference),
2576         new_target_var_(new_target_var),
2577         this_function_var_(this_function_var) {
2578     DCHECK(new_target_var->raw_name()->IsOneByteEqualTo(".new.target"));
2579     DCHECK(this_function_var->raw_name()->IsOneByteEqualTo(".this_function"));
2580   }
2581 
2582   VariableProxy* new_target_var_;
2583   VariableProxy* this_function_var_;
2584 };
2585 
2586 // This AST Node is used to represent a dynamic import call --
2587 // import(argument).
2588 class ImportCallExpression final : public Expression {
2589  public:
specifier()2590   Expression* specifier() const { return specifier_; }
import_assertions()2591   Expression* import_assertions() const { return import_assertions_; }
2592 
2593  private:
2594   friend class AstNodeFactory;
2595   friend Zone;
2596 
ImportCallExpression(Expression * specifier,int pos)2597   ImportCallExpression(Expression* specifier, int pos)
2598       : Expression(pos, kImportCallExpression),
2599         specifier_(specifier),
2600         import_assertions_(nullptr) {}
2601 
ImportCallExpression(Expression * specifier,Expression * import_assertions,int pos)2602   ImportCallExpression(Expression* specifier, Expression* import_assertions,
2603                        int pos)
2604       : Expression(pos, kImportCallExpression),
2605         specifier_(specifier),
2606         import_assertions_(import_assertions) {}
2607 
2608   Expression* specifier_;
2609   Expression* import_assertions_;
2610 };
2611 
2612 // This class is produced when parsing the () in arrow functions without any
2613 // arguments and is not actually a valid expression.
2614 class EmptyParentheses final : public Expression {
2615  private:
2616   friend class AstNodeFactory;
2617   friend Zone;
2618 
EmptyParentheses(int pos)2619   explicit EmptyParentheses(int pos) : Expression(pos, kEmptyParentheses) {
2620     mark_parenthesized();
2621   }
2622 };
2623 
2624 // Represents the spec operation `GetTemplateObject(templateLiteral)`
2625 // (defined at https://tc39.github.io/ecma262/#sec-gettemplateobject).
2626 class GetTemplateObject final : public Expression {
2627  public:
cooked_strings()2628   const ZonePtrList<const AstRawString>* cooked_strings() const {
2629     return cooked_strings_;
2630   }
raw_strings()2631   const ZonePtrList<const AstRawString>* raw_strings() const {
2632     return raw_strings_;
2633   }
2634 
2635   template <typename IsolateT>
2636   Handle<TemplateObjectDescription> GetOrBuildDescription(IsolateT* isolate);
2637 
2638  private:
2639   friend class AstNodeFactory;
2640   friend Zone;
2641 
GetTemplateObject(const ZonePtrList<const AstRawString> * cooked_strings,const ZonePtrList<const AstRawString> * raw_strings,int pos)2642   GetTemplateObject(const ZonePtrList<const AstRawString>* cooked_strings,
2643                     const ZonePtrList<const AstRawString>* raw_strings, int pos)
2644       : Expression(pos, kGetTemplateObject),
2645         cooked_strings_(cooked_strings),
2646         raw_strings_(raw_strings) {}
2647 
2648   const ZonePtrList<const AstRawString>* cooked_strings_;
2649   const ZonePtrList<const AstRawString>* raw_strings_;
2650 };
2651 
2652 class TemplateLiteral final : public Expression {
2653  public:
string_parts()2654   const ZonePtrList<const AstRawString>* string_parts() const {
2655     return string_parts_;
2656   }
substitutions()2657   const ZonePtrList<Expression>* substitutions() const {
2658     return substitutions_;
2659   }
2660 
2661  private:
2662   friend class AstNodeFactory;
2663   friend Zone;
TemplateLiteral(const ZonePtrList<const AstRawString> * parts,const ZonePtrList<Expression> * substitutions,int pos)2664   TemplateLiteral(const ZonePtrList<const AstRawString>* parts,
2665                   const ZonePtrList<Expression>* substitutions, int pos)
2666       : Expression(pos, kTemplateLiteral),
2667         string_parts_(parts),
2668         substitutions_(substitutions) {}
2669 
2670   const ZonePtrList<const AstRawString>* string_parts_;
2671   const ZonePtrList<Expression>* substitutions_;
2672 };
2673 
2674 // ----------------------------------------------------------------------------
2675 // Basic visitor
2676 // Sub-class should parametrize AstVisitor with itself, e.g.:
2677 //   class SpecificVisitor : public AstVisitor<SpecificVisitor> { ... }
2678 
2679 template <class Subclass>
2680 class AstVisitor {
2681  public:
Visit(AstNode * node)2682   void Visit(AstNode* node) { impl()->Visit(node); }
2683 
VisitDeclarations(Declaration::List * declarations)2684   void VisitDeclarations(Declaration::List* declarations) {
2685     for (Declaration* decl : *declarations) Visit(decl);
2686   }
2687 
VisitStatements(const ZonePtrList<Statement> * statements)2688   void VisitStatements(const ZonePtrList<Statement>* statements) {
2689     for (int i = 0; i < statements->length(); i++) {
2690       Statement* stmt = statements->at(i);
2691       Visit(stmt);
2692     }
2693   }
2694 
VisitExpressions(const ZonePtrList<Expression> * expressions)2695   void VisitExpressions(const ZonePtrList<Expression>* expressions) {
2696     for (int i = 0; i < expressions->length(); i++) {
2697       // The variable statement visiting code may pass null expressions
2698       // to this code. Maybe this should be handled by introducing an
2699       // undefined expression or literal? Revisit this code if this
2700       // changes.
2701       Expression* expression = expressions->at(i);
2702       if (expression != nullptr) Visit(expression);
2703     }
2704   }
2705 
2706  protected:
impl()2707   Subclass* impl() { return static_cast<Subclass*>(this); }
2708 };
2709 
2710 #define GENERATE_VISIT_CASE(NodeType)                                   \
2711   case AstNode::k##NodeType:                                            \
2712     return this->impl()->Visit##NodeType(static_cast<NodeType*>(node));
2713 
2714 #define GENERATE_FAILURE_CASE(NodeType) \
2715   case AstNode::k##NodeType:            \
2716     UNREACHABLE();
2717 
2718 #define GENERATE_AST_VISITOR_SWITCH()        \
2719   switch (node->node_type()) {               \
2720     AST_NODE_LIST(GENERATE_VISIT_CASE)       \
2721     FAILURE_NODE_LIST(GENERATE_FAILURE_CASE) \
2722   }
2723 
2724 #define DEFINE_AST_VISITOR_SUBCLASS_MEMBERS()               \
2725  public:                                                    \
2726   void VisitNoStackOverflowCheck(AstNode* node) {           \
2727     GENERATE_AST_VISITOR_SWITCH()                           \
2728   }                                                         \
2729                                                             \
2730   void Visit(AstNode* node) {                               \
2731     if (CheckStackOverflow()) return;                       \
2732     VisitNoStackOverflowCheck(node);                        \
2733   }                                                         \
2734                                                             \
2735   void SetStackOverflow() { stack_overflow_ = true; }       \
2736   void ClearStackOverflow() { stack_overflow_ = false; }    \
2737   bool HasStackOverflow() const { return stack_overflow_; } \
2738                                                             \
2739   bool CheckStackOverflow() {                               \
2740     if (stack_overflow_) return true;                       \
2741     if (GetCurrentStackPosition() < stack_limit_) {         \
2742       stack_overflow_ = true;                               \
2743       return true;                                          \
2744     }                                                       \
2745     return false;                                           \
2746   }                                                         \
2747                                                             \
2748  protected:                                                 \
2749   uintptr_t stack_limit() const { return stack_limit_; }    \
2750                                                             \
2751  private:                                                   \
2752   void InitializeAstVisitor(Isolate* isolate) {             \
2753     stack_limit_ = isolate->stack_guard()->real_climit();   \
2754     stack_overflow_ = false;                                \
2755   }                                                         \
2756                                                             \
2757   void InitializeAstVisitor(uintptr_t stack_limit) {        \
2758     stack_limit_ = stack_limit;                             \
2759     stack_overflow_ = false;                                \
2760   }                                                         \
2761                                                             \
2762   uintptr_t stack_limit_;                                   \
2763   bool stack_overflow_
2764 
2765 #define DEFINE_AST_VISITOR_MEMBERS_WITHOUT_STACKOVERFLOW()    \
2766  public:                                                      \
2767   void Visit(AstNode* node) { GENERATE_AST_VISITOR_SWITCH() } \
2768                                                               \
2769  private:
2770 
2771 // ----------------------------------------------------------------------------
2772 // AstNode factory
2773 
2774 class AstNodeFactory final {
2775  public:
AstNodeFactory(AstValueFactory * ast_value_factory,Zone * zone)2776   AstNodeFactory(AstValueFactory* ast_value_factory, Zone* zone)
2777       : zone_(zone),
2778         ast_value_factory_(ast_value_factory),
2779         empty_statement_(zone->New<class EmptyStatement>()),
2780         this_expression_(zone->New<class ThisExpression>(kNoSourcePosition)),
2781         failure_expression_(zone->New<class FailureExpression>()) {}
2782 
ast_node_factory()2783   AstNodeFactory* ast_node_factory() { return this; }
ast_value_factory()2784   AstValueFactory* ast_value_factory() const { return ast_value_factory_; }
2785 
NewVariableDeclaration(int pos)2786   VariableDeclaration* NewVariableDeclaration(int pos) {
2787     return zone_->New<VariableDeclaration>(pos);
2788   }
2789 
NewNestedVariableDeclaration(Scope * scope,int pos)2790   NestedVariableDeclaration* NewNestedVariableDeclaration(Scope* scope,
2791                                                           int pos) {
2792     return zone_->New<NestedVariableDeclaration>(scope, pos);
2793   }
2794 
NewFunctionDeclaration(FunctionLiteral * fun,int pos)2795   FunctionDeclaration* NewFunctionDeclaration(FunctionLiteral* fun, int pos) {
2796     return zone_->New<FunctionDeclaration>(fun, pos);
2797   }
2798 
NewBlock(int capacity,bool ignore_completion_value)2799   Block* NewBlock(int capacity, bool ignore_completion_value) {
2800     return zone_->New<Block>(zone_, capacity, ignore_completion_value, false);
2801   }
2802 
NewBlock(bool ignore_completion_value,bool is_breakable)2803   Block* NewBlock(bool ignore_completion_value, bool is_breakable) {
2804     return zone_->New<Block>(ignore_completion_value, is_breakable);
2805   }
2806 
NewBlock(bool ignore_completion_value,const ScopedPtrList<Statement> & statements)2807   Block* NewBlock(bool ignore_completion_value,
2808                   const ScopedPtrList<Statement>& statements) {
2809     Block* result = NewBlock(ignore_completion_value, false);
2810     result->InitializeStatements(statements, zone_);
2811     return result;
2812   }
2813 
2814 #define STATEMENT_WITH_POSITION(NodeType) \
2815   NodeType* New##NodeType(int pos) { return zone_->New<NodeType>(pos); }
2816   STATEMENT_WITH_POSITION(DoWhileStatement)
STATEMENT_WITH_POSITION(WhileStatement)2817   STATEMENT_WITH_POSITION(WhileStatement)
2818   STATEMENT_WITH_POSITION(ForStatement)
2819 #undef STATEMENT_WITH_POSITION
2820 
2821   SwitchStatement* NewSwitchStatement(Expression* tag, int pos) {
2822     return zone_->New<SwitchStatement>(zone_, tag, pos);
2823   }
2824 
NewForEachStatement(ForEachStatement::VisitMode visit_mode,int pos)2825   ForEachStatement* NewForEachStatement(ForEachStatement::VisitMode visit_mode,
2826                                         int pos) {
2827     switch (visit_mode) {
2828       case ForEachStatement::ENUMERATE: {
2829         return zone_->New<ForInStatement>(pos);
2830       }
2831       case ForEachStatement::ITERATE: {
2832         return zone_->New<ForOfStatement>(pos, IteratorType::kNormal);
2833       }
2834     }
2835     UNREACHABLE();
2836   }
2837 
NewForOfStatement(int pos,IteratorType type)2838   ForOfStatement* NewForOfStatement(int pos, IteratorType type) {
2839     return zone_->New<ForOfStatement>(pos, type);
2840   }
2841 
NewExpressionStatement(Expression * expression,int pos)2842   ExpressionStatement* NewExpressionStatement(Expression* expression, int pos) {
2843     return zone_->New<ExpressionStatement>(expression, pos);
2844   }
2845 
NewContinueStatement(IterationStatement * target,int pos)2846   ContinueStatement* NewContinueStatement(IterationStatement* target, int pos) {
2847     return zone_->New<ContinueStatement>(target, pos);
2848   }
2849 
NewBreakStatement(BreakableStatement * target,int pos)2850   BreakStatement* NewBreakStatement(BreakableStatement* target, int pos) {
2851     return zone_->New<BreakStatement>(target, pos);
2852   }
2853 
2854   ReturnStatement* NewReturnStatement(
2855       Expression* expression, int pos,
2856       int end_position = ReturnStatement::kFunctionLiteralReturnPosition) {
2857     return zone_->New<ReturnStatement>(expression, ReturnStatement::kNormal,
2858                                        pos, end_position);
2859   }
2860 
NewAsyncReturnStatement(Expression * expression,int pos,int end_position)2861   ReturnStatement* NewAsyncReturnStatement(Expression* expression, int pos,
2862                                            int end_position) {
2863     return zone_->New<ReturnStatement>(
2864         expression, ReturnStatement::kAsyncReturn, pos, end_position);
2865   }
2866 
2867   ReturnStatement* NewSyntheticAsyncReturnStatement(
2868       Expression* expression, int pos,
2869       int end_position = ReturnStatement::kFunctionLiteralReturnPosition) {
2870     return zone_->New<ReturnStatement>(
2871         expression, ReturnStatement::kSyntheticAsyncReturn, pos, end_position);
2872   }
2873 
NewWithStatement(Scope * scope,Expression * expression,Statement * statement,int pos)2874   WithStatement* NewWithStatement(Scope* scope,
2875                                   Expression* expression,
2876                                   Statement* statement,
2877                                   int pos) {
2878     return zone_->New<WithStatement>(scope, expression, statement, pos);
2879   }
2880 
NewIfStatement(Expression * condition,Statement * then_statement,Statement * else_statement,int pos)2881   IfStatement* NewIfStatement(Expression* condition, Statement* then_statement,
2882                               Statement* else_statement, int pos) {
2883     return zone_->New<IfStatement>(condition, then_statement, else_statement,
2884                                    pos);
2885   }
2886 
NewTryCatchStatement(Block * try_block,Scope * scope,Block * catch_block,int pos)2887   TryCatchStatement* NewTryCatchStatement(Block* try_block, Scope* scope,
2888                                           Block* catch_block, int pos) {
2889     return zone_->New<TryCatchStatement>(try_block, scope, catch_block,
2890                                          HandlerTable::CAUGHT, pos);
2891   }
2892 
NewTryCatchStatementForReThrow(Block * try_block,Scope * scope,Block * catch_block,int pos)2893   TryCatchStatement* NewTryCatchStatementForReThrow(Block* try_block,
2894                                                     Scope* scope,
2895                                                     Block* catch_block,
2896                                                     int pos) {
2897     return zone_->New<TryCatchStatement>(try_block, scope, catch_block,
2898                                          HandlerTable::UNCAUGHT, pos);
2899   }
2900 
NewTryCatchStatementForAsyncAwait(Block * try_block,Scope * scope,Block * catch_block,int pos)2901   TryCatchStatement* NewTryCatchStatementForAsyncAwait(Block* try_block,
2902                                                        Scope* scope,
2903                                                        Block* catch_block,
2904                                                        int pos) {
2905     return zone_->New<TryCatchStatement>(try_block, scope, catch_block,
2906                                          HandlerTable::ASYNC_AWAIT, pos);
2907   }
2908 
NewTryCatchStatementForReplAsyncAwait(Block * try_block,Scope * scope,Block * catch_block,int pos)2909   TryCatchStatement* NewTryCatchStatementForReplAsyncAwait(Block* try_block,
2910                                                            Scope* scope,
2911                                                            Block* catch_block,
2912                                                            int pos) {
2913     return zone_->New<TryCatchStatement>(
2914         try_block, scope, catch_block, HandlerTable::UNCAUGHT_ASYNC_AWAIT, pos);
2915   }
2916 
NewTryFinallyStatement(Block * try_block,Block * finally_block,int pos)2917   TryFinallyStatement* NewTryFinallyStatement(Block* try_block,
2918                                               Block* finally_block, int pos) {
2919     return zone_->New<TryFinallyStatement>(try_block, finally_block, pos);
2920   }
2921 
NewDebuggerStatement(int pos)2922   DebuggerStatement* NewDebuggerStatement(int pos) {
2923     return zone_->New<DebuggerStatement>(pos);
2924   }
2925 
EmptyStatement()2926   class EmptyStatement* EmptyStatement() {
2927     return empty_statement_;
2928   }
2929 
ThisExpression()2930   class ThisExpression* ThisExpression() {
2931     // Clear any previously set "parenthesized" flag on this_expression_ so this
2932     // particular token does not inherit the it. The flag is used to check
2933     // during arrow function head parsing whether we came from parenthesized
2934     // exprssion parsing, since additional arrow function verification was done
2935     // there. It does not matter whether a flag is unset after arrow head
2936     // verification, so clearing at this point is fine.
2937     this_expression_->clear_parenthesized();
2938     return this_expression_;
2939   }
2940 
NewThisExpression(int pos)2941   class ThisExpression* NewThisExpression(int pos) {
2942     DCHECK_NE(pos, kNoSourcePosition);
2943     return zone_->New<class ThisExpression>(pos);
2944   }
2945 
FailureExpression()2946   class FailureExpression* FailureExpression() {
2947     return failure_expression_;
2948   }
2949 
NewSloppyBlockFunctionStatement(int pos,Variable * var,Token::Value init)2950   SloppyBlockFunctionStatement* NewSloppyBlockFunctionStatement(
2951       int pos, Variable* var, Token::Value init) {
2952     return zone_->New<SloppyBlockFunctionStatement>(pos, var, init,
2953                                                     EmptyStatement());
2954   }
2955 
NewCaseClause(Expression * label,const ScopedPtrList<Statement> & statements)2956   CaseClause* NewCaseClause(Expression* label,
2957                             const ScopedPtrList<Statement>& statements) {
2958     return zone_->New<CaseClause>(zone_, label, statements);
2959   }
2960 
NewStringLiteral(const AstRawString * string,int pos)2961   Literal* NewStringLiteral(const AstRawString* string, int pos) {
2962     DCHECK_NOT_NULL(string);
2963     return zone_->New<Literal>(string, pos);
2964   }
2965 
2966   Literal* NewNumberLiteral(double number, int pos);
2967 
NewSmiLiteral(int number,int pos)2968   Literal* NewSmiLiteral(int number, int pos) {
2969     return zone_->New<Literal>(number, pos);
2970   }
2971 
NewBigIntLiteral(AstBigInt bigint,int pos)2972   Literal* NewBigIntLiteral(AstBigInt bigint, int pos) {
2973     return zone_->New<Literal>(bigint, pos);
2974   }
2975 
NewBooleanLiteral(bool b,int pos)2976   Literal* NewBooleanLiteral(bool b, int pos) {
2977     return zone_->New<Literal>(b, pos);
2978   }
2979 
NewNullLiteral(int pos)2980   Literal* NewNullLiteral(int pos) {
2981     return zone_->New<Literal>(Literal::kNull, pos);
2982   }
2983 
NewUndefinedLiteral(int pos)2984   Literal* NewUndefinedLiteral(int pos) {
2985     return zone_->New<Literal>(Literal::kUndefined, pos);
2986   }
2987 
NewTheHoleLiteral()2988   Literal* NewTheHoleLiteral() {
2989     return zone_->New<Literal>(Literal::kTheHole, kNoSourcePosition);
2990   }
2991 
2992   ObjectLiteral* NewObjectLiteral(
2993       const ScopedPtrList<ObjectLiteral::Property>& properties,
2994       uint32_t boilerplate_properties, int pos, bool has_rest_property,
2995       Variable* home_object = nullptr) {
2996     return zone_->New<ObjectLiteral>(zone_, properties, boilerplate_properties,
2997                                      pos, has_rest_property, home_object);
2998   }
2999 
NewObjectLiteralProperty(Expression * key,Expression * value,ObjectLiteralProperty::Kind kind,bool is_computed_name)3000   ObjectLiteral::Property* NewObjectLiteralProperty(
3001       Expression* key, Expression* value, ObjectLiteralProperty::Kind kind,
3002       bool is_computed_name) {
3003     return zone_->New<ObjectLiteral::Property>(key, value, kind,
3004                                                is_computed_name);
3005   }
3006 
NewObjectLiteralProperty(Expression * key,Expression * value,bool is_computed_name)3007   ObjectLiteral::Property* NewObjectLiteralProperty(Expression* key,
3008                                                     Expression* value,
3009                                                     bool is_computed_name) {
3010     return zone_->New<ObjectLiteral::Property>(ast_value_factory_, key, value,
3011                                                is_computed_name);
3012   }
3013 
NewRegExpLiteral(const AstRawString * pattern,int flags,int pos)3014   RegExpLiteral* NewRegExpLiteral(const AstRawString* pattern, int flags,
3015                                   int pos) {
3016     return zone_->New<RegExpLiteral>(pattern, flags, pos);
3017   }
3018 
NewArrayLiteral(const ScopedPtrList<Expression> & values,int pos)3019   ArrayLiteral* NewArrayLiteral(const ScopedPtrList<Expression>& values,
3020                                 int pos) {
3021     return zone_->New<ArrayLiteral>(zone_, values, -1, pos);
3022   }
3023 
NewArrayLiteral(const ScopedPtrList<Expression> & values,int first_spread_index,int pos)3024   ArrayLiteral* NewArrayLiteral(const ScopedPtrList<Expression>& values,
3025                                 int first_spread_index, int pos) {
3026     return zone_->New<ArrayLiteral>(zone_, values, first_spread_index, pos);
3027   }
3028 
3029   VariableProxy* NewVariableProxy(Variable* var,
3030                                   int start_position = kNoSourcePosition) {
3031     return zone_->New<VariableProxy>(var, start_position);
3032   }
3033 
3034   VariableProxy* NewVariableProxy(const AstRawString* name,
3035                                   VariableKind variable_kind,
3036                                   int start_position = kNoSourcePosition) {
3037     DCHECK_NOT_NULL(name);
3038     return zone_->New<VariableProxy>(name, variable_kind, start_position);
3039   }
3040 
3041   // Recreates the VariableProxy in this Zone.
CopyVariableProxy(VariableProxy * proxy)3042   VariableProxy* CopyVariableProxy(VariableProxy* proxy) {
3043     return zone_->New<VariableProxy>(proxy);
3044   }
3045 
CopyVariable(Variable * variable)3046   Variable* CopyVariable(Variable* variable) {
3047     return zone_->New<Variable>(variable);
3048   }
3049 
NewOptionalChain(Expression * expression)3050   OptionalChain* NewOptionalChain(Expression* expression) {
3051     return zone_->New<OptionalChain>(expression);
3052   }
3053 
3054   Property* NewProperty(Expression* obj, Expression* key, int pos,
3055                         bool optional_chain = false) {
3056     return zone_->New<Property>(obj, key, pos, optional_chain);
3057   }
3058 
3059   Call* NewCall(Expression* expression,
3060                 const ScopedPtrList<Expression>& arguments, int pos,
3061                 bool has_spread,
3062                 Call::PossiblyEval possibly_eval = Call::NOT_EVAL,
3063                 bool optional_chain = false) {
3064     DCHECK_IMPLIES(possibly_eval == Call::IS_POSSIBLY_EVAL, !optional_chain);
3065     return zone_->New<Call>(zone_, expression, arguments, pos, has_spread,
3066                             possibly_eval, optional_chain);
3067   }
3068 
NewTaggedTemplate(Expression * expression,const ScopedPtrList<Expression> & arguments,int pos)3069   Call* NewTaggedTemplate(Expression* expression,
3070                           const ScopedPtrList<Expression>& arguments, int pos) {
3071     return zone_->New<Call>(zone_, expression, arguments, pos,
3072                             Call::TaggedTemplateTag::kTrue);
3073   }
3074 
NewCallNew(Expression * expression,const ScopedPtrList<Expression> & arguments,int pos,bool has_spread)3075   CallNew* NewCallNew(Expression* expression,
3076                       const ScopedPtrList<Expression>& arguments, int pos,
3077                       bool has_spread) {
3078     return zone_->New<CallNew>(zone_, expression, arguments, pos, has_spread);
3079   }
3080 
NewCallRuntime(Runtime::FunctionId id,const ScopedPtrList<Expression> & arguments,int pos)3081   CallRuntime* NewCallRuntime(Runtime::FunctionId id,
3082                               const ScopedPtrList<Expression>& arguments,
3083                               int pos) {
3084     return zone_->New<CallRuntime>(zone_, Runtime::FunctionForId(id), arguments,
3085                                    pos);
3086   }
3087 
NewCallRuntime(const Runtime::Function * function,const ScopedPtrList<Expression> & arguments,int pos)3088   CallRuntime* NewCallRuntime(const Runtime::Function* function,
3089                               const ScopedPtrList<Expression>& arguments,
3090                               int pos) {
3091     return zone_->New<CallRuntime>(zone_, function, arguments, pos);
3092   }
3093 
NewCallRuntime(int context_index,const ScopedPtrList<Expression> & arguments,int pos)3094   CallRuntime* NewCallRuntime(int context_index,
3095                               const ScopedPtrList<Expression>& arguments,
3096                               int pos) {
3097     return zone_->New<CallRuntime>(zone_, context_index, arguments, pos);
3098   }
3099 
NewUnaryOperation(Token::Value op,Expression * expression,int pos)3100   UnaryOperation* NewUnaryOperation(Token::Value op,
3101                                     Expression* expression,
3102                                     int pos) {
3103     return zone_->New<UnaryOperation>(op, expression, pos);
3104   }
3105 
NewBinaryOperation(Token::Value op,Expression * left,Expression * right,int pos)3106   BinaryOperation* NewBinaryOperation(Token::Value op,
3107                                       Expression* left,
3108                                       Expression* right,
3109                                       int pos) {
3110     return zone_->New<BinaryOperation>(op, left, right, pos);
3111   }
3112 
NewNaryOperation(Token::Value op,Expression * first,size_t initial_subsequent_size)3113   NaryOperation* NewNaryOperation(Token::Value op, Expression* first,
3114                                   size_t initial_subsequent_size) {
3115     return zone_->New<NaryOperation>(zone_, op, first, initial_subsequent_size);
3116   }
3117 
NewCountOperation(Token::Value op,bool is_prefix,Expression * expr,int pos)3118   CountOperation* NewCountOperation(Token::Value op,
3119                                     bool is_prefix,
3120                                     Expression* expr,
3121                                     int pos) {
3122     return zone_->New<CountOperation>(op, is_prefix, expr, pos);
3123   }
3124 
NewCompareOperation(Token::Value op,Expression * left,Expression * right,int pos)3125   CompareOperation* NewCompareOperation(Token::Value op,
3126                                         Expression* left,
3127                                         Expression* right,
3128                                         int pos) {
3129     return zone_->New<CompareOperation>(op, left, right, pos);
3130   }
3131 
NewSpread(Expression * expression,int pos,int expr_pos)3132   Spread* NewSpread(Expression* expression, int pos, int expr_pos) {
3133     return zone_->New<Spread>(expression, pos, expr_pos);
3134   }
3135 
NewConditional(Expression * condition,Expression * then_expression,Expression * else_expression,int position)3136   Conditional* NewConditional(Expression* condition,
3137                               Expression* then_expression,
3138                               Expression* else_expression,
3139                               int position) {
3140     return zone_->New<Conditional>(condition, then_expression, else_expression,
3141                                    position);
3142   }
3143 
NewAssignment(Token::Value op,Expression * target,Expression * value,int pos)3144   Assignment* NewAssignment(Token::Value op,
3145                             Expression* target,
3146                             Expression* value,
3147                             int pos) {
3148     DCHECK(Token::IsAssignmentOp(op));
3149     DCHECK_NOT_NULL(target);
3150     DCHECK_NOT_NULL(value);
3151 
3152     if (op != Token::INIT && target->IsVariableProxy()) {
3153       target->AsVariableProxy()->set_is_assigned();
3154     }
3155 
3156     if (op == Token::ASSIGN || op == Token::INIT) {
3157       return zone_->New<Assignment>(AstNode::kAssignment, op, target, value,
3158                                     pos);
3159     } else {
3160       return zone_->New<CompoundAssignment>(
3161           op, target, value, pos,
3162           NewBinaryOperation(Token::BinaryOpForAssignment(op), target, value,
3163                              pos + 1));
3164     }
3165   }
3166 
NewYield(Expression * expression,int pos,Suspend::OnAbruptResume on_abrupt_resume)3167   Suspend* NewYield(Expression* expression, int pos,
3168                     Suspend::OnAbruptResume on_abrupt_resume) {
3169     if (!expression) expression = NewUndefinedLiteral(pos);
3170     return zone_->New<Yield>(expression, pos, on_abrupt_resume);
3171   }
3172 
NewYieldStar(Expression * expression,int pos)3173   YieldStar* NewYieldStar(Expression* expression, int pos) {
3174     return zone_->New<YieldStar>(expression, pos);
3175   }
3176 
NewAwait(Expression * expression,int pos)3177   Await* NewAwait(Expression* expression, int pos) {
3178     if (!expression) expression = NewUndefinedLiteral(pos);
3179     return zone_->New<Await>(expression, pos);
3180   }
3181 
NewThrow(Expression * exception,int pos)3182   Throw* NewThrow(Expression* exception, int pos) {
3183     return zone_->New<Throw>(exception, pos);
3184   }
3185 
3186   FunctionLiteral* NewFunctionLiteral(
3187       const AstRawString* name, DeclarationScope* scope,
3188       const ScopedPtrList<Statement>& body, int expected_property_count,
3189       int parameter_count, int function_length,
3190       FunctionLiteral::ParameterFlag has_duplicate_parameters,
3191       FunctionSyntaxKind function_syntax_kind,
3192       FunctionLiteral::EagerCompileHint eager_compile_hint, int position,
3193       bool has_braces, int function_literal_id,
3194       ProducedPreparseData* produced_preparse_data = nullptr) {
3195     return zone_->New<FunctionLiteral>(
3196         zone_, name ? ast_value_factory_->NewConsString(name) : nullptr,
3197         ast_value_factory_, scope, body, expected_property_count,
3198         parameter_count, function_length, function_syntax_kind,
3199         has_duplicate_parameters, eager_compile_hint, position, has_braces,
3200         function_literal_id, produced_preparse_data);
3201   }
3202 
3203   // Creates a FunctionLiteral representing a top-level script, the
3204   // result of an eval (top-level or otherwise), or the result of calling
3205   // the Function constructor.
NewScriptOrEvalFunctionLiteral(DeclarationScope * scope,const ScopedPtrList<Statement> & body,int expected_property_count,int parameter_count)3206   FunctionLiteral* NewScriptOrEvalFunctionLiteral(
3207       DeclarationScope* scope, const ScopedPtrList<Statement>& body,
3208       int expected_property_count, int parameter_count) {
3209     return zone_->New<FunctionLiteral>(
3210         zone_, ast_value_factory_->empty_cons_string(), ast_value_factory_,
3211         scope, body, expected_property_count, parameter_count, parameter_count,
3212         FunctionSyntaxKind::kAnonymousExpression,
3213         FunctionLiteral::kNoDuplicateParameters,
3214         FunctionLiteral::kShouldLazyCompile, 0, /* has_braces */ false,
3215         kFunctionLiteralIdTopLevel);
3216   }
3217 
NewClassLiteralProperty(Expression * key,Expression * value,ClassLiteralProperty::Kind kind,bool is_static,bool is_computed_name,bool is_private)3218   ClassLiteral::Property* NewClassLiteralProperty(
3219       Expression* key, Expression* value, ClassLiteralProperty::Kind kind,
3220       bool is_static, bool is_computed_name, bool is_private) {
3221     return zone_->New<ClassLiteral::Property>(key, value, kind, is_static,
3222                                               is_computed_name, is_private);
3223   }
3224 
NewClassLiteralStaticElement(ClassLiteral::Property * property)3225   ClassLiteral::StaticElement* NewClassLiteralStaticElement(
3226       ClassLiteral::Property* property) {
3227     return zone_->New<ClassLiteral::StaticElement>(property);
3228   }
3229 
NewClassLiteralStaticElement(Block * static_block)3230   ClassLiteral::StaticElement* NewClassLiteralStaticElement(
3231       Block* static_block) {
3232     return zone_->New<ClassLiteral::StaticElement>(static_block);
3233   }
3234 
NewClassLiteral(ClassScope * scope,Expression * extends,FunctionLiteral * constructor,ZonePtrList<ClassLiteral::Property> * public_members,ZonePtrList<ClassLiteral::Property> * private_members,FunctionLiteral * static_initializer,FunctionLiteral * instance_members_initializer_function,int start_position,int end_position,bool has_static_computed_names,bool is_anonymous,bool has_private_methods,Variable * home_object,Variable * static_home_object)3235   ClassLiteral* NewClassLiteral(
3236       ClassScope* scope, Expression* extends, FunctionLiteral* constructor,
3237       ZonePtrList<ClassLiteral::Property>* public_members,
3238       ZonePtrList<ClassLiteral::Property>* private_members,
3239       FunctionLiteral* static_initializer,
3240       FunctionLiteral* instance_members_initializer_function,
3241       int start_position, int end_position, bool has_static_computed_names,
3242       bool is_anonymous, bool has_private_methods, Variable* home_object,
3243       Variable* static_home_object) {
3244     return zone_->New<ClassLiteral>(
3245         scope, extends, constructor, public_members, private_members,
3246         static_initializer, instance_members_initializer_function,
3247         start_position, end_position, has_static_computed_names, is_anonymous,
3248         has_private_methods, home_object, static_home_object);
3249   }
3250 
NewNativeFunctionLiteral(const AstRawString * name,v8::Extension * extension,int pos)3251   NativeFunctionLiteral* NewNativeFunctionLiteral(const AstRawString* name,
3252                                                   v8::Extension* extension,
3253                                                   int pos) {
3254     return zone_->New<NativeFunctionLiteral>(name, extension, pos);
3255   }
3256 
NewSuperPropertyReference(VariableProxy * home_object_var,int pos)3257   SuperPropertyReference* NewSuperPropertyReference(
3258       VariableProxy* home_object_var, int pos) {
3259     return zone_->New<SuperPropertyReference>(home_object_var, pos);
3260   }
3261 
NewSuperCallReference(VariableProxy * new_target_var,VariableProxy * this_function_var,int pos)3262   SuperCallReference* NewSuperCallReference(VariableProxy* new_target_var,
3263                                             VariableProxy* this_function_var,
3264                                             int pos) {
3265     return zone_->New<SuperCallReference>(new_target_var, this_function_var,
3266                                           pos);
3267   }
3268 
NewEmptyParentheses(int pos)3269   EmptyParentheses* NewEmptyParentheses(int pos) {
3270     return zone_->New<EmptyParentheses>(pos);
3271   }
3272 
NewGetTemplateObject(const ZonePtrList<const AstRawString> * cooked_strings,const ZonePtrList<const AstRawString> * raw_strings,int pos)3273   GetTemplateObject* NewGetTemplateObject(
3274       const ZonePtrList<const AstRawString>* cooked_strings,
3275       const ZonePtrList<const AstRawString>* raw_strings, int pos) {
3276     return zone_->New<GetTemplateObject>(cooked_strings, raw_strings, pos);
3277   }
3278 
NewTemplateLiteral(const ZonePtrList<const AstRawString> * string_parts,const ZonePtrList<Expression> * substitutions,int pos)3279   TemplateLiteral* NewTemplateLiteral(
3280       const ZonePtrList<const AstRawString>* string_parts,
3281       const ZonePtrList<Expression>* substitutions, int pos) {
3282     return zone_->New<TemplateLiteral>(string_parts, substitutions, pos);
3283   }
3284 
NewImportCallExpression(Expression * specifier,int pos)3285   ImportCallExpression* NewImportCallExpression(Expression* specifier,
3286                                                 int pos) {
3287     return zone_->New<ImportCallExpression>(specifier, pos);
3288   }
3289 
NewImportCallExpression(Expression * specifier,Expression * import_assertions,int pos)3290   ImportCallExpression* NewImportCallExpression(Expression* specifier,
3291                                                 Expression* import_assertions,
3292                                                 int pos) {
3293     return zone_->New<ImportCallExpression>(specifier, import_assertions, pos);
3294   }
3295 
NewInitializeClassMembersStatement(ZonePtrList<ClassLiteral::Property> * args,int pos)3296   InitializeClassMembersStatement* NewInitializeClassMembersStatement(
3297       ZonePtrList<ClassLiteral::Property>* args, int pos) {
3298     return zone_->New<InitializeClassMembersStatement>(args, pos);
3299   }
3300 
3301   InitializeClassStaticElementsStatement*
NewInitializeClassStaticElementsStatement(ZonePtrList<ClassLiteral::StaticElement> * args,int pos)3302   NewInitializeClassStaticElementsStatement(
3303       ZonePtrList<ClassLiteral::StaticElement>* args, int pos) {
3304     return zone_->New<InitializeClassStaticElementsStatement>(args, pos);
3305   }
3306 
zone()3307   Zone* zone() const { return zone_; }
3308 
3309  private:
3310   // This zone may be deallocated upon returning from parsing a function body
3311   // which we can guarantee is not going to be compiled or have its AST
3312   // inspected.
3313   // See ParseFunctionLiteral in parser.cc for preconditions.
3314   Zone* zone_;
3315   AstValueFactory* ast_value_factory_;
3316   class EmptyStatement* empty_statement_;
3317   class ThisExpression* this_expression_;
3318   class FailureExpression* failure_expression_;
3319 };
3320 
3321 
3322 // Type testing & conversion functions overridden by concrete subclasses.
3323 // Inline functions for AstNode.
3324 
3325 #define DECLARE_NODE_FUNCTIONS(type)                                         \
3326   bool AstNode::Is##type() const { return node_type() == AstNode::k##type; } \
3327   type* AstNode::As##type() {                                                \
3328     return node_type() == AstNode::k##type ? reinterpret_cast<type*>(this)   \
3329                                            : nullptr;                        \
3330   }                                                                          \
3331   const type* AstNode::As##type() const {                                    \
3332     return node_type() == AstNode::k##type                                   \
3333                ? reinterpret_cast<const type*>(this)                         \
3334                : nullptr;                                                    \
3335   }
3336 AST_NODE_LIST(DECLARE_NODE_FUNCTIONS)
3337 FAILURE_NODE_LIST(DECLARE_NODE_FUNCTIONS)
3338 #undef DECLARE_NODE_FUNCTIONS
3339 
3340 }  // namespace internal
3341 }  // namespace v8
3342 
3343 #endif  // V8_AST_AST_H_
3344