parser.h 47.7 KB
Newer Older
1
// Copyright 2012 the V8 project authors. All rights reserved.
2 3
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
4

5 6
#ifndef V8_PARSING_PARSER_H_
#define V8_PARSING_PARSER_H_
7

8 9
#include "src/ast/ast.h"
#include "src/ast/scopes.h"
10 11
#include "src/base/compiler-specific.h"
#include "src/globals.h"
12
#include "src/parsing/parser-base.h"
13
#include "src/parsing/parsing.h"
14
#include "src/parsing/preparse-data-format.h"
15
#include "src/parsing/preparse-data.h"
16
#include "src/parsing/preparser.h"
17
#include "src/pending-compilation-error-handler.h"
18
#include "src/utils.h"
19

20
namespace v8 {
21

22 23
class ScriptCompiler;

24
namespace internal {
25

26 27
class ParseInfo;
class ScriptData;
28 29
class ParserTarget;
class ParserTargetScope;
30
class PreParsedScopeData;
31

32 33
class FunctionEntry BASE_EMBEDDED {
 public:
34 35 36
  enum {
    kStartPositionIndex,
    kEndPositionIndex,
37 38
    kNumParametersIndex,
    kFlagsIndex,
39
    kNumInnerFunctionsIndex,
40 41 42
    kSize
  };

43 44 45 46
  explicit FunctionEntry(Vector<unsigned> backing)
    : backing_(backing) { }

  FunctionEntry() : backing_() { }
47

48 49 50 51 52
  class LanguageModeField : public BitField<LanguageMode, 0, 1> {};
  class UsesSuperPropertyField
      : public BitField<bool, LanguageModeField::kNext, 1> {};

  static uint32_t EncodeFlags(LanguageMode language_mode,
53
                              bool uses_super_property) {
54
    return LanguageModeField::encode(language_mode) |
55
           UsesSuperPropertyField::encode(uses_super_property);
56
  }
57

58 59 60 61 62 63 64 65 66
  int start_pos() const { return backing_[kStartPositionIndex]; }
  int end_pos() const { return backing_[kEndPositionIndex]; }
  int num_parameters() const { return backing_[kNumParametersIndex]; }
  LanguageMode language_mode() const {
    return LanguageModeField::decode(backing_[kFlagsIndex]);
  }
  bool uses_super_property() const {
    return UsesSuperPropertyField::decode(backing_[kFlagsIndex]);
  }
67
  int num_inner_functions() const { return backing_[kNumInnerFunctionsIndex]; }
68 69

  bool is_valid() const { return !backing_.is_empty(); }
70 71 72 73 74 75

 private:
  Vector<unsigned> backing_;
};


76 77
// Wrapper around ScriptData to provide parser-specific functionality.
class ParseData {
78
 public:
79 80 81 82 83 84
  static ParseData* FromCachedData(ScriptData* cached_data) {
    ParseData* pd = new ParseData(cached_data);
    if (pd->IsSane()) return pd;
    cached_data->Reject();
    delete pd;
    return NULL;
85
  }
86

87
  void Initialize();
88
  FunctionEntry GetFunctionEntry(int start);
89 90 91 92
  int FunctionCount();

  unsigned* Data() {  // Writable data as unsigned int array.
    return reinterpret_cast<unsigned*>(const_cast<byte*>(script_data_->data()));
93
  }
94

95 96 97 98
  void Reject() { script_data_->Reject(); }

  bool rejected() const { return script_data_->rejected(); }

99
 private:
100 101
  explicit ParseData(ScriptData* script_data) : script_data_(script_data) {}

102 103 104 105 106 107 108 109
  bool IsSane();
  unsigned Magic();
  unsigned Version();
  int FunctionsSize();
  int Length() const {
    // Script data length is already checked to be a multiple of unsigned size.
    return script_data_->length() / sizeof(unsigned);
  }
110

111 112
  ScriptData* script_data_;
  int function_index_;
113

114
  DISALLOW_COPY_AND_ASSIGN(ParseData);
115 116
};

117 118
// ----------------------------------------------------------------------------
// JAVASCRIPT PARSING
119

120
class Parser;
121

122

123
struct ParserFormalParameters : FormalParametersBase {
124
  struct Parameter : public ZoneObject {
125
    Parameter(const AstRawString* name, Expression* pattern,
126 127
              Expression* initializer, int position,
              int initializer_end_position, bool is_rest)
128 129 130
        : name(name),
          pattern(pattern),
          initializer(initializer),
131
          position(position),
132
          initializer_end_position(initializer_end_position),
133
          is_rest(is_rest) {}
134
    const AstRawString* name;
135
    Expression* pattern;
136
    Expression* initializer;
137
    int position;
138
    int initializer_end_position;
139
    bool is_rest;
140
    Parameter* next_parameter = nullptr;
141 142 143
    bool is_simple() const {
      return pattern->IsVariableProxy() && initializer == nullptr && !is_rest;
    }
144

145 146
    Parameter** next() { return &next_parameter; }
    Parameter* const* next() const { return &next_parameter; }
147 148
  };

149
  explicit ParserFormalParameters(DeclarationScope* scope)
150 151
      : FormalParametersBase(scope) {}
  ThreadedList<Parameter> params;
152 153
};

154
template <>
155 156 157 158
struct ParserTypes<Parser> {
  typedef ParserBase<Parser> Base;
  typedef Parser Impl;

159
  typedef v8::internal::Variable Variable;
160 161 162 163 164 165

  // Return types for traversing functions.
  typedef const AstRawString* Identifier;
  typedef v8::internal::Expression* Expression;
  typedef v8::internal::FunctionLiteral* FunctionLiteral;
  typedef ObjectLiteral::Property* ObjectLiteralProperty;
166
  typedef ClassLiteral::Property* ClassLiteralProperty;
167
  typedef v8::internal::Suspend* Suspend;
168
  typedef ZoneList<v8::internal::Expression*>* ExpressionList;
169 170
  typedef ZoneList<ObjectLiteral::Property*>* ObjectPropertyList;
  typedef ZoneList<ClassLiteral::Property*>* ClassPropertyList;
171
  typedef ParserFormalParameters FormalParameters;
172
  typedef v8::internal::Statement* Statement;
173
  typedef ZoneList<v8::internal::Statement*>* StatementList;
174
  typedef v8::internal::Block* Block;
175 176
  typedef v8::internal::BreakableStatement* BreakableStatement;
  typedef v8::internal::IterationStatement* IterationStatement;
177 178 179

  // For constructing objects returned by the traversing functions.
  typedef AstNodeFactory Factory;
180 181 182

  typedef ParserTarget Target;
  typedef ParserTargetScope TargetScope;
183 184
};

185
class V8_EXPORT_PRIVATE Parser : public NON_EXPORTED_BASE(ParserBase<Parser>) {
186
 public:
187
  explicit Parser(ParseInfo* info);
188
  ~Parser() {
189 190
    delete reusable_preparser_;
    reusable_preparser_ = NULL;
191 192
    delete cached_parse_data_;
    cached_parse_data_ = NULL;
193
  }
194

195
  static bool IsPreParser() { return false; }
196

197
  void ParseOnBackground(ParseInfo* info);
198

199 200
  // Deserialize the scope chain prior to parsing in which the script is going
  // to be executed. If the script is a top-level script, or the scope chain
201 202
  // consists of only a native context, maybe_outer_scope_info should be an
  // empty handle.
203 204 205 206 207
  //
  // This only deserializes the scope chain, but doesn't connect the scopes to
  // their corresponding scope infos. Therefore, looking up variables in the
  // deserialized scopes is not possible.
  void DeserializeScopeChain(ParseInfo* info,
208
                             MaybeHandle<ScopeInfo> maybe_outer_scope_info);
209

210 211 212 213
  // Handle errors detected during parsing
  void ReportErrors(Isolate* isolate, Handle<Script> script);
  // Move statistics to Isolate
  void UpdateStatistics(Isolate* isolate, Handle<Script> script);
214
  void HandleSourceURLComments(Isolate* isolate, Handle<Script> script);
215

216
 private:
217
  friend class ParserBase<Parser>;
218
  friend class v8::internal::ExpressionClassifier<ParserTypes<Parser>>;
219 220
  friend bool v8::internal::parsing::ParseProgram(ParseInfo*, Isolate*, bool);
  friend bool v8::internal::parsing::ParseFunction(ParseInfo*, Isolate*, bool);
221

222 223 224 225 226
  bool AllowsLazyParsingWithoutUnresolvedVariables() const {
    return scope()->AllowsLazyParsingWithoutUnresolvedVariables(
        original_scope_);
  }

227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242
  bool parse_lazily() const { return mode_ == PARSE_LAZILY; }
  enum Mode { PARSE_LAZILY, PARSE_EAGERLY };

  class ParsingModeScope BASE_EMBEDDED {
   public:
    ParsingModeScope(Parser* parser, Mode mode)
        : parser_(parser), old_mode_(parser->mode_) {
      parser_->mode_ = mode;
    }
    ~ParsingModeScope() { parser_->mode_ = old_mode_; }

   private:
    Parser* parser_;
    Mode old_mode_;
  };

243 244 245 246 247 248 249
  // Runtime encoding of different completion modes.
  enum CompletionKind {
    kNormalCompletion,
    kThrowCompletion,
    kAbruptCompletion
  };

250 251 252
  Variable* NewTemporary(const AstRawString* name) {
    return scope()->NewTemporary(name);
  }
253

254
  void PrepareGeneratorVariables();
255

256 257 258 259 260 261 262 263
  // Limit the allowed number of local variables in a function. The hard limit
  // is that offsets computed by FullCodeGenerator::StackOperand and similar
  // functions are ints, and they should not overflow. In addition, accessing
  // local variables creates user-controlled constants in the generated code,
  // and we don't want too much user-controlled memory inside the code (this was
  // the reason why this limit was introduced in the first place; see
  // https://codereview.chromium.org/7003030/ ).
  static const int kMaxNumFunctionLocals = 4194303;  // 2^22-1
264

265
  // Returns NULL if parsing failed.
266
  FunctionLiteral* ParseProgram(Isolate* isolate, ParseInfo* info);
267

268
  FunctionLiteral* ParseFunction(Isolate* isolate, ParseInfo* info);
269
  FunctionLiteral* DoParseFunction(ParseInfo* info);
270

271
  // Called by ParseProgram after setting up the scanner.
wingo's avatar
wingo committed
272
  FunctionLiteral* DoParseProgram(ParseInfo* info);
273

274
  void SetCachedData(ParseInfo* info);
275

276 277
  void StitchAst(ParseInfo* top_level_parse_info, Isolate* isolate);

278
  ScriptCompiler::CompileOptions compile_options() const {
279
    return compile_options_;
280
  }
281
  bool consume_cached_parse_data() const {
282
    return compile_options_ == ScriptCompiler::kConsumeParserCache;
283 284
  }
  bool produce_cached_parse_data() const {
285
    return compile_options_ == ScriptCompiler::kProduceParserCache;
286
  }
287

288 289 290 291 292
  PreParser* reusable_preparser() {
    if (reusable_preparser_ == NULL) {
      reusable_preparser_ =
          new PreParser(zone(), &scanner_, stack_limit_, ast_value_factory(),
                        &pending_error_handler_, runtime_call_stats_,
293
                        preparsed_scope_data_, parsing_on_main_thread_);
294 295
#define SET_ALLOW(name) reusable_preparser_->set_allow_##name(allow_##name());
      SET_ALLOW(natives);
296
      SET_ALLOW(tailcalls);
297 298 299 300 301 302 303
      SET_ALLOW(harmony_do_expressions);
      SET_ALLOW(harmony_function_sent);
      SET_ALLOW(harmony_trailing_commas);
      SET_ALLOW(harmony_class_fields);
      SET_ALLOW(harmony_object_rest_spread);
      SET_ALLOW(harmony_dynamic_import);
      SET_ALLOW(harmony_async_iteration);
304
      SET_ALLOW(harmony_template_escapes);
305 306 307 308 309
#undef SET_ALLOW
    }
    return reusable_preparser_;
  }

neis's avatar
neis committed
310
  void ParseModuleItemList(ZoneList<Statement*>* body, bool* ok);
311
  Statement* ParseModuleItem(bool* ok);
312
  const AstRawString* ParseModuleSpecifier(bool* ok);
neis's avatar
neis committed
313
  void ParseImportDeclaration(bool* ok);
314
  Statement* ParseExportDeclaration(bool* ok);
315
  Statement* ParseExportDefault(bool* ok);
neis's avatar
neis committed
316 317 318 319
  void ParseExportClause(ZoneList<const AstRawString*>* export_names,
                         ZoneList<Scanner::Location>* export_locations,
                         ZoneList<const AstRawString*>* local_names,
                         Scanner::Location* reserved_loc, bool* ok);
320 321 322 323 324 325 326 327 328 329 330
  struct NamedImport : public ZoneObject {
    const AstRawString* import_name;
    const AstRawString* local_name;
    const Scanner::Location location;
    NamedImport(const AstRawString* import_name, const AstRawString* local_name,
                Scanner::Location location)
        : import_name(import_name),
          local_name(local_name),
          location(location) {}
  };
  ZoneList<const NamedImport*>* ParseNamedImports(int pos, bool* ok);
331 332 333
  Block* BuildInitializationBlock(DeclarationParsingResult* parsing_result,
                                  ZoneList<const AstRawString*>* names,
                                  bool* ok);
334 335 336 337
  void DeclareAndInitializeVariables(
      Block* block, const DeclarationDescriptor* declaration_descriptor,
      const DeclarationParsingResult::Declaration* declaration,
      ZoneList<const AstRawString*>* names, bool* ok);
338 339 340 341 342
  ZoneList<const AstRawString*>* DeclareLabel(
      ZoneList<const AstRawString*>* labels, VariableProxy* expr, bool* ok);
  bool ContainsLabel(ZoneList<const AstRawString*>* labels,
                     const AstRawString* label);
  Expression* RewriteReturn(Expression* return_value, int pos);
343 344 345
  Statement* RewriteSwitchStatement(Expression* tag,
                                    SwitchStatement* switch_statement,
                                    ZoneList<CaseClause*>* cases, Scope* scope);
346 347 348 349 350
  void RewriteCatchPattern(CatchInfo* catch_info, bool* ok);
  void ValidateCatchBlock(const CatchInfo& catch_info, bool* ok);
  Statement* RewriteTryStatement(Block* try_block, Block* catch_block,
                                 Block* finally_block,
                                 const CatchInfo& catch_info, int pos);
351

352 353 354 355 356 357 358 359
  void ParseAndRewriteGeneratorFunctionBody(int pos, FunctionKind kind,
                                            ZoneList<Statement*>* body,
                                            bool* ok);
  void CreateFunctionNameAssignment(const AstRawString* function_name, int pos,
                                    FunctionLiteral::FunctionType function_type,
                                    DeclarationScope* function_scope,
                                    ZoneList<Statement*>* result, int index);

360
  Statement* DeclareFunction(const AstRawString* variable_name,
361
                             FunctionLiteral* function, VariableMode mode,
362
                             int pos, bool is_sloppy_block_function,
363
                             ZoneList<const AstRawString*>* names, bool* ok);
364 365 366 367 368
  V8_INLINE Statement* DeclareClass(const AstRawString* variable_name,
                                    Expression* value,
                                    ZoneList<const AstRawString*>* names,
                                    int class_token_pos, int end_pos, bool* ok);
  V8_INLINE void DeclareClassVariable(const AstRawString* name,
369
                                      ClassInfo* class_info,
370 371 372
                                      int class_token_pos, bool* ok);
  V8_INLINE void DeclareClassProperty(const AstRawString* class_name,
                                      ClassLiteralProperty* property,
373 374
                                      ClassLiteralProperty::Kind kind,
                                      bool is_static, bool is_constructor,
375
                                      ClassInfo* class_info, bool* ok);
376 377
  V8_INLINE Expression* RewriteClassLiteral(Scope* block_scope,
                                            const AstRawString* name,
378
                                            ClassInfo* class_info, int pos,
379
                                            int end_pos, bool* ok);
380 381
  V8_INLINE Statement* DeclareNative(const AstRawString* name, int pos,
                                     bool* ok);
382

383 384
  V8_INLINE Block* IgnoreCompletion(Statement* statement);

385 386
  V8_INLINE Scope* NewHiddenCatchScopeWithParent(Scope* parent);

387
  class PatternRewriter final : public AstVisitor<PatternRewriter> {
388 389
   public:
    static void DeclareAndInitializeVariables(
390 391
        Parser* parser, Block* block,
        const DeclarationDescriptor* declaration_descriptor,
392 393 394
        const DeclarationParsingResult::Declaration* declaration,
        ZoneList<const AstRawString*>* names, bool* ok);

395 396 397
    static void RewriteDestructuringAssignment(Parser* parser,
                                               RewritableExpression* expr,
                                               Scope* Scope);
398 399 400 401

    static Expression* RewriteDestructuringAssignment(Parser* parser,
                                                      Assignment* assignment,
                                                      Scope* scope);
402

403 404 405
   private:
    PatternRewriter() {}

406
#define DECLARE_VISIT(type) void Visit##type(v8::internal::type* node);
407 408 409 410
    // Visiting functions for AST nodes make this an AstVisitor.
    AST_NODE_LIST(DECLARE_VISIT)
#undef DECLARE_VISIT

411 412 413 414 415 416 417 418 419 420
    enum PatternContext {
      BINDING,
      INITIALIZER,
      ASSIGNMENT,
      ASSIGNMENT_INITIALIZER
    };

    PatternContext context() const { return context_; }
    void set_context(PatternContext context) { context_ = context; }

421 422 423
    void RecurseIntoSubpattern(AstNode* pattern, Expression* value) {
      Expression* old_value = current_value_;
      current_value_ = value;
424
      recursion_level_++;
425
      Visit(pattern);
426
      recursion_level_--;
427 428 429
      current_value_ = old_value;
    }

430 431 432
    void VisitObjectLiteral(ObjectLiteral* node, Variable** temp_var);
    void VisitArrayLiteral(ArrayLiteral* node, Variable** temp_var);

433 434 435
    bool IsBindingContext() const {
      return context_ == BINDING || context_ == INITIALIZER;
    }
436
    bool IsInitializerContext() const { return context_ != ASSIGNMENT; }
437 438 439
    bool IsAssignmentContext() const {
      return context_ == ASSIGNMENT || context_ == ASSIGNMENT_INITIALIZER;
    }
440
    bool IsSubPattern() const { return recursion_level_ > 1; }
441 442 443
    PatternContext SetAssignmentContextIfNeeded(Expression* node);
    PatternContext SetInitializerContextIfNeeded(Expression* node);

444
    bool DeclaresParameterContainingSloppyEval() const;
445 446
    void RewriteParameterScopes(Expression* expr);

447
    Variable* CreateTempVar(Expression* value = nullptr);
448

449
    AstNodeFactory* factory() const { return parser_->factory(); }
450
    AstValueFactory* ast_value_factory() const {
451
      return parser_->ast_value_factory();
452
    }
453 454
    Zone* zone() const { return parser_->zone(); }
    Scope* scope() const { return scope_; }
455

456 457 458
    Scope* scope_;
    Parser* parser_;
    PatternContext context_;
459 460 461 462 463 464
    Expression* pattern_;
    int initializer_position_;
    Block* block_;
    const DeclarationDescriptor* descriptor_;
    ZoneList<const AstRawString*>* names_;
    Expression* current_value_;
465
    int recursion_level_;
466
    bool* ok_;
467 468

    DEFINE_AST_VISITOR_MEMBERS_WITHOUT_STACKOVERFLOW()
469 470
  };

471 472 473 474 475 476 477
  // [if (IteratorType == kAsync)]
  //     !%_IsJSReceiver(result = Await(iterator.next()) &&
  //         %ThrowIteratorResultNotAnObject(result)
  // [else]
  //     !%_IsJSReceiver(result = iterator.next()) &&
  //         %ThrowIteratorResultNotAnObject(result)
  // [endif]
478
  Expression* BuildIteratorNextResult(Expression* iterator, Variable* result,
479
                                      IteratorType type, int pos);
480

481
  // Initialize the components of a for-in / for-of statement.
482 483
  Statement* InitializeForEachStatement(ForEachStatement* stmt,
                                        Expression* each, Expression* subject,
484
                                        Statement* body);
485 486
  Statement* InitializeForOfStatement(ForOfStatement* stmt, Expression* each,
                                      Expression* iterable, Statement* body,
487
                                      bool finalize, IteratorType type,
488
                                      int next_result_pos = kNoSourcePosition);
489

490 491 492 493 494 495
  Block* RewriteForVarInLegacy(const ForInfo& for_info);
  void DesugarBindingInForEachStatement(ForInfo* for_info, Block** body_block,
                                        Expression** each_variable, bool* ok);
  Block* CreateForEachStatementTDZ(Block* init_block, const ForInfo& for_info,
                                   bool* ok);

rossberg's avatar
rossberg committed
496
  Statement* DesugarLexicalBindingsInForStatement(
497 498
      ForStatement* loop, Statement* init, Expression* cond, Statement* next,
      Statement* body, Scope* inner_scope, const ForInfo& for_info, bool* ok);
499

500
  Expression* RewriteDoExpression(Block* body, int pos, bool* ok);
501

502
  FunctionLiteral* ParseFunctionLiteral(
503
      const AstRawString* name, Scanner::Location function_name_location,
504
      FunctionNameValidity function_name_validity, FunctionKind kind,
505
      int function_token_position, FunctionLiteral::FunctionType type,
506
      LanguageMode language_mode, bool* ok);
507 508

  // Get odd-ball literals.
509
  Literal* GetLiteralUndefined(int position);
510

511 512
  // Check if the scope has conflicting var/let declarations from different
  // scopes. This covers for example
513 514 515 516 517 518 519 520 521
  //
  // function f() { { { var x; } let x; } }
  // function g() { { var x; let x; } }
  //
  // The var declarations are hoisted to the function scope, but originate from
  // a scope where the name has also been let bound or the var declaration is
  // hoisted over such a scope.
  void CheckConflictingVarDeclarations(Scope* scope, bool* ok);

522 523 524 525
  // Insert initializer statements for var-bindings shadowing parameter bindings
  // from a non-simple parameter list.
  void InsertShadowingVarBindingInitializers(Block* block);

526
  // Implement sloppy block-scoped functions, ES2015 Annex B 3.3
527
  void InsertSloppyBlockFunctionVarBindings(DeclarationScope* scope);
528

529
  VariableProxy* NewUnresolved(const AstRawString* name, int begin_pos,
530
                               VariableKind kind = NORMAL_VARIABLE);
531
  VariableProxy* NewUnresolved(const AstRawString* name);
532
  Variable* Declare(Declaration* declaration,
533
                    DeclarationDescriptor::Kind declaration_kind,
534
                    VariableMode mode, InitializationFlag init, bool* ok,
535 536
                    Scope* declaration_scope = nullptr,
                    int var_end_pos = kNoSourcePosition);
537 538 539 540
  Declaration* DeclareVariable(const AstRawString* name, VariableMode mode,
                               int pos, bool* ok);
  Declaration* DeclareVariable(const AstRawString* name, VariableMode mode,
                               InitializationFlag init, int pos, bool* ok);
541

542 543 544
  bool TargetStackContainsLabel(const AstRawString* label);
  BreakableStatement* LookupBreakTarget(const AstRawString* label, bool* ok);
  IterationStatement* LookupContinueTarget(const AstRawString* label, bool* ok);
545

546
  Statement* BuildAssertIsCoercible(Variable* var);
547

548
  // Factory methods.
549
  FunctionLiteral* DefaultConstructor(const AstRawString* name, bool call_super,
550
                                      int pos, int end_pos);
551

552 553
  // Skip over a lazy function, either using cached data if we have it, or
  // by parsing the function with PreParser. Consumes the ending }.
554
  // If may_abort == true, the (pre-)parser may decide to abort skipping
555
  // in order to force the function to be eagerly parsed, after all.
556 557
  LazyParsingResult SkipFunction(FunctionKind kind,
                                 DeclarationScope* function_scope,
558 559
                                 int* num_parameters, bool is_inner_function,
                                 bool may_abort, bool* ok);
560

561
  Block* BuildParameterInitializationBlock(
562
      const ParserFormalParameters& parameters, bool* ok);
563
  Block* BuildRejectPromiseOnException(Block* block);
564

565 566 567 568 569
  ZoneList<Statement*>* ParseFunction(
      const AstRawString* function_name, int pos, FunctionKind kind,
      FunctionLiteral::FunctionType function_type,
      DeclarationScope* function_scope, int* num_parameters,
      int* function_length, bool* has_duplicate_parameters,
570
      int* expected_property_count, bool* ok);
571

572
  void ThrowPendingError(Isolate* isolate, Handle<Script> script);
573

574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604
  class TemplateLiteral : public ZoneObject {
   public:
    TemplateLiteral(Zone* zone, int pos)
        : cooked_(8, zone), raw_(8, zone), expressions_(8, zone), pos_(pos) {}

    const ZoneList<Expression*>* cooked() const { return &cooked_; }
    const ZoneList<Expression*>* raw() const { return &raw_; }
    const ZoneList<Expression*>* expressions() const { return &expressions_; }
    int position() const { return pos_; }

    void AddTemplateSpan(Literal* cooked, Literal* raw, int end, Zone* zone) {
      DCHECK_NOT_NULL(cooked);
      DCHECK_NOT_NULL(raw);
      cooked_.Add(cooked, zone);
      raw_.Add(raw, zone);
    }

    void AddExpression(Expression* expression, Zone* zone) {
      DCHECK_NOT_NULL(expression);
      expressions_.Add(expression, zone);
    }

   private:
    ZoneList<Expression*> cooked_;
    ZoneList<Expression*> raw_;
    ZoneList<Expression*> expressions_;
    int pos_;
  };

  typedef TemplateLiteral* TemplateLiteralState;

605
  TemplateLiteralState OpenTemplateLiteral(int pos);
606 607 608 609 610 611 612 613 614
  // "should_cook" means that the span can be "cooked": in tagged template
  // literals, both the raw and "cooked" representations are available to user
  // code ("cooked" meaning that escape sequences are converted to their
  // interpreted values). With the --harmony-template-escapes flag, invalid
  // escape sequences cause the cooked span to be represented by undefined,
  // instead of being a syntax error.
  // "tail" indicates that this span is the last in the literal.
  void AddTemplateSpan(TemplateLiteralState* state, bool should_cook,
                       bool tail);
615 616 617 618
  void AddTemplateExpression(TemplateLiteralState* state,
                             Expression* expression);
  Expression* CloseTemplateLiteral(TemplateLiteralState* state, int start,
                                   Expression* tag);
619 620
  uint32_t ComputeTemplateLiteralHash(const TemplateLiteral* lit);

621 622
  ZoneList<Expression*>* PrepareSpreadArguments(ZoneList<Expression*>* list);
  Expression* SpreadCall(Expression* function, ZoneList<Expression*>* args,
623
                         int pos, Call::PossiblyEval is_possibly_eval);
624 625
  Expression* SpreadCallNew(Expression* function, ZoneList<Expression*>* args,
                            int pos);
626
  Expression* RewriteSuperCall(Expression* call_expression);
627

628
  void SetLanguageMode(Scope* scope, LanguageMode mode);
629
  void SetAsmModule();
630

631
  V8_INLINE void MarkCollectedTailCallExpressions();
632
  V8_INLINE void MarkTailPosition(Expression* expression);
633

634
  // Rewrite all DestructuringAssignments in the current FunctionState.
635 636
  V8_INLINE void RewriteDestructuringAssignments();

637 638 639 640 641
  V8_INLINE Expression* RewriteExponentiation(Expression* left,
                                              Expression* right, int pos);
  V8_INLINE Expression* RewriteAssignExponentiation(Expression* left,
                                                    Expression* right, int pos);

nikolaos's avatar
nikolaos committed
642 643 644
  friend class NonPatternRewriter;
  V8_INLINE Expression* RewriteSpreads(ArrayLiteral* lit);

645
  // Rewrite expressions that are not used as patterns
646
  V8_INLINE void RewriteNonPattern(bool* ok);
nikolaos's avatar
nikolaos committed
647

648 649 650 651
  V8_INLINE void QueueDestructuringAssignmentForRewriting(
      Expression* assignment);
  V8_INLINE void QueueNonPatternForRewriting(Expression* expr, bool* ok);

652 653 654
  friend class InitializerRewriter;
  void RewriteParameterInitializer(Expression* expr, Scope* scope);

655
  Expression* BuildInitialYield(int pos, FunctionKind kind);
656
  Assignment* BuildCreateJSGeneratorObject(int pos, FunctionKind kind);
657 658
  Expression* BuildResolvePromise(Expression* value, int pos);
  Expression* BuildRejectPromise(Expression* value, int pos);
659
  Variable* PromiseVariable();
660
  Variable* AsyncGeneratorAwaitVariable();
661

662 663 664 665 666
  // Generic AST generator for throwing errors from compiled code.
  Expression* NewThrowError(Runtime::FunctionId function_id,
                            MessageTemplate::Template message,
                            const AstRawString* arg, int pos);

667 668
  void FinalizeIteratorUse(Scope* use_scope, Variable* completion,
                           Expression* condition, Variable* iter,
669 670
                           Block* iterator_use, Block* result,
                           IteratorType type);
671 672

  Statement* FinalizeForOfStatement(ForOfStatement* loop, Variable* completion,
673
                                    IteratorType type, int pos);
674
  void BuildIteratorClose(ZoneList<Statement*>* statements, Variable* iterator,
675
                          Variable* input, Variable* output, IteratorType type);
676 677
  void BuildIteratorCloseForCompletion(Scope* scope,
                                       ZoneList<Statement*>* statements,
678
                                       Variable* iterator,
679 680
                                       Expression* completion,
                                       IteratorType type);
681 682
  Statement* CheckCallable(Variable* var, Expression* error, int pos);

683
  V8_INLINE Expression* RewriteAwaitExpression(Expression* value, int pos);
684 685 686 687 688
  V8_INLINE void PrepareAsyncFunctionBody(ZoneList<Statement*>* body,
                                          FunctionKind kind, int pos);
  V8_INLINE void RewriteAsyncFunctionBody(ZoneList<Statement*>* body,
                                          Block* block,
                                          Expression* return_value, bool* ok);
689

690 691 692
  Expression* RewriteYieldStar(Expression* generator, Expression* expression,
                               int pos);

693 694 695
  void AddArrowFunctionFormalParameters(ParserFormalParameters* parameters,
                                        Expression* params, int end_pos,
                                        bool* ok);
696 697
  void SetFunctionName(Expression* value, const AstRawString* name);

698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721 722
  // Helper functions for recursive descent.
  V8_INLINE bool IsEval(const AstRawString* identifier) const {
    return identifier == ast_value_factory()->eval_string();
  }

  V8_INLINE bool IsArguments(const AstRawString* identifier) const {
    return identifier == ast_value_factory()->arguments_string();
  }

  V8_INLINE bool IsEvalOrArguments(const AstRawString* identifier) const {
    return IsEval(identifier) || IsArguments(identifier);
  }

  V8_INLINE bool IsUndefined(const AstRawString* identifier) const {
    return identifier == ast_value_factory()->undefined_string();
  }

  // Returns true if the expression is of type "this.foo".
  V8_INLINE static bool IsThisProperty(Expression* expression) {
    DCHECK(expression != NULL);
    Property* property = expression->AsProperty();
    return property != NULL && property->obj()->IsVariableProxy() &&
           property->obj()->AsVariableProxy()->is_this();
  }

723 724 725
  // This returns true if the expression is an indentifier (wrapped
  // inside a variable proxy).  We exclude the case of 'this', which
  // has been converted to a variable proxy.
726
  V8_INLINE static bool IsIdentifier(Expression* expression) {
727
    DCHECK_NOT_NULL(expression);
728
    VariableProxy* operand = expression->AsVariableProxy();
729 730
    return operand != nullptr && !operand->is_this() &&
           !operand->is_new_target();
731 732 733 734 735 736 737
  }

  V8_INLINE static const AstRawString* AsIdentifier(Expression* expression) {
    DCHECK(IsIdentifier(expression));
    return expression->AsVariableProxy()->raw_name();
  }

738 739 740 741
  V8_INLINE VariableProxy* AsIdentifierExpression(Expression* expression) {
    return expression->AsVariableProxy();
  }

742 743 744 745 746 747 748 749
  V8_INLINE bool IsPrototype(const AstRawString* identifier) const {
    return identifier == ast_value_factory()->prototype_string();
  }

  V8_INLINE bool IsConstructor(const AstRawString* identifier) const {
    return identifier == ast_value_factory()->constructor_string();
  }

750 751 752 753
  V8_INLINE bool IsName(const AstRawString* identifier) const {
    return identifier == ast_value_factory()->name_string();
  }

754 755
  V8_INLINE static bool IsBoilerplateProperty(
      ObjectLiteral::Property* property) {
756
    return !property->IsPrototype();
757 758
  }

759 760 761 762 763 764 765
  V8_INLINE bool IsNative(Expression* expr) const {
    DCHECK_NOT_NULL(expr);
    return expr->IsVariableProxy() &&
           expr->AsVariableProxy()->raw_name() ==
               ast_value_factory()->native_string();
  }

766 767 768 769 770
  V8_INLINE static bool IsArrayIndex(const AstRawString* string,
                                     uint32_t* index) {
    return string->AsArrayIndex(index);
  }

771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790
  V8_INLINE bool IsUseStrictDirective(Statement* statement) const {
    return IsStringLiteral(statement, ast_value_factory()->use_strict_string());
  }

  V8_INLINE bool IsUseAsmDirective(Statement* statement) const {
    return IsStringLiteral(statement, ast_value_factory()->use_asm_string());
  }

  // Returns true if the statement is an expression statement containing
  // a single string literal.  If a second argument is given, the literal
  // is also compared with it and the result is true only if they are equal.
  V8_INLINE bool IsStringLiteral(Statement* statement,
                                 const AstRawString* arg = nullptr) const {
    ExpressionStatement* e_stat = statement->AsExpressionStatement();
    if (e_stat == nullptr) return false;
    Literal* literal = e_stat->expression()->AsLiteral();
    if (literal == nullptr || !literal->raw_value()->IsString()) return false;
    return arg == nullptr || literal->raw_value()->AsString() == arg;
  }

791
  V8_INLINE static Expression* GetPropertyValue(LiteralProperty* property) {
792 793 794
    return property->value();
  }

795 796 797 798 799 800 801
  V8_INLINE void GetDefaultStrings(
      const AstRawString** default_string,
      const AstRawString** star_default_star_string) {
    *default_string = ast_value_factory()->default_string();
    *star_default_star_string = ast_value_factory()->star_default_star_string();
  }

802 803
  // Functions for encapsulating the differences between parsing and preparsing;
  // operations interleaved with the recursive descent.
804 805 806
  V8_INLINE void PushLiteralName(const AstRawString* id) {
    DCHECK_NOT_NULL(fni_);
    fni_->PushLiteralName(id);
807 808
  }

809 810 811
  V8_INLINE void PushVariableName(const AstRawString* id) {
    DCHECK_NOT_NULL(fni_);
    fni_->PushVariableName(id);
812 813
  }

814 815
  V8_INLINE void PushPropertyName(Expression* expression) {
    DCHECK_NOT_NULL(fni_);
816
    if (expression->IsPropertyName()) {
817
      fni_->PushLiteralName(expression->AsLiteral()->AsRawPropertyName());
818
    } else {
819
      fni_->PushLiteralName(ast_value_factory()->anonymous_function_string());
820 821 822
    }
  }

823 824 825 826 827
  V8_INLINE void PushEnclosingName(const AstRawString* name) {
    DCHECK_NOT_NULL(fni_);
    fni_->PushEnclosingName(name);
  }

828 829
  V8_INLINE void AddFunctionForNameInference(FunctionLiteral* func_to_infer) {
    DCHECK_NOT_NULL(fni_);
830
    fni_->AddFunction(func_to_infer);
831 832
  }

833 834 835 836 837
  V8_INLINE void InferFunctionName() {
    DCHECK_NOT_NULL(fni_);
    fni_->Infer();
  }

838 839 840 841 842 843 844 845 846 847 848 849
  // If we assign a function literal to a property we pretenure the
  // literal so it can be added as a constant function property.
  V8_INLINE static void CheckAssigningFunctionLiteralToProperty(
      Expression* left, Expression* right) {
    DCHECK(left != NULL);
    if (left->IsProperty() && right->IsFunctionLiteral()) {
      right->AsFunctionLiteral()->set_pretenure();
    }
  }

  // Determine if the expression is a variable proxy and mark it as being used
  // in an assignment or with a increment/decrement operator.
850 851 852 853 854
  V8_INLINE static void MarkExpressionAsAssigned(Expression* expression) {
    DCHECK_NOT_NULL(expression);
    if (expression->IsVariableProxy()) {
      expression->AsVariableProxy()->set_is_assigned();
    }
855 856 857 858 859 860 861 862
  }

  // Returns true if we have a binary expression between two numeric
  // literals. In that case, *x will be changed to an expression which is the
  // computed value.
  bool ShortcutNumericLiteralBinaryExpression(Expression** x, Expression* y,
                                              Token::Value op, int pos);

863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930 931 932 933 934 935
  // Rewrites the following types of unary expressions:
  // not <literal> -> true / false
  // + <numeric literal> -> <numeric literal>
  // - <numeric literal> -> <numeric literal with value negated>
  // ! <literal> -> true / false
  // The following rewriting rules enable the collection of type feedback
  // without any special stub and the multiplication is removed later in
  // Crankshaft's canonicalization pass.
  // + foo -> foo * 1
  // - foo -> foo * (-1)
  // ~ foo -> foo ^(~0)
  Expression* BuildUnaryExpression(Expression* expression, Token::Value op,
                                   int pos);

  Expression* BuildIteratorResult(Expression* value, bool done);

  // Generate AST node that throws a ReferenceError with the given type.
  V8_INLINE Expression* NewThrowReferenceError(
      MessageTemplate::Template message, int pos) {
    return NewThrowError(Runtime::kNewReferenceError, message,
                         ast_value_factory()->empty_string(), pos);
  }

  // Generate AST node that throws a SyntaxError with the given
  // type. The first argument may be null (in the handle sense) in
  // which case no arguments are passed to the constructor.
  V8_INLINE Expression* NewThrowSyntaxError(MessageTemplate::Template message,
                                            const AstRawString* arg, int pos) {
    return NewThrowError(Runtime::kNewSyntaxError, message, arg, pos);
  }

  // Generate AST node that throws a TypeError with the given
  // type. Both arguments must be non-null (in the handle sense).
  V8_INLINE Expression* NewThrowTypeError(MessageTemplate::Template message,
                                          const AstRawString* arg, int pos) {
    return NewThrowError(Runtime::kNewTypeError, message, arg, pos);
  }

  // Reporting errors.
  V8_INLINE void ReportMessageAt(Scanner::Location source_location,
                                 MessageTemplate::Template message,
                                 const char* arg = NULL,
                                 ParseErrorType error_type = kSyntaxError) {
    if (stack_overflow()) {
      // Suppress the error message (syntax error or such) in the presence of a
      // stack overflow. The isolate allows only one pending exception at at
      // time
      // and we want to report the stack overflow later.
      return;
    }
    pending_error_handler_.ReportMessageAt(source_location.beg_pos,
                                           source_location.end_pos, message,
                                           arg, error_type);
  }

  V8_INLINE void ReportMessageAt(Scanner::Location source_location,
                                 MessageTemplate::Template message,
                                 const AstRawString* arg,
                                 ParseErrorType error_type = kSyntaxError) {
    if (stack_overflow()) {
      // Suppress the error message (syntax error or such) in the presence of a
      // stack overflow. The isolate allows only one pending exception at at
      // time
      // and we want to report the stack overflow later.
      return;
    }
    pending_error_handler_.ReportMessageAt(source_location.beg_pos,
                                           source_location.end_pos, message,
                                           arg, error_type);
  }

  // "null" return type creators.
  V8_INLINE static const AstRawString* EmptyIdentifier() { return nullptr; }
936 937 938
  V8_INLINE static bool IsEmptyIdentifier(const AstRawString* name) {
    return name == nullptr;
  }
939 940 941 942 943
  V8_INLINE static Expression* EmptyExpression() { return nullptr; }
  V8_INLINE static Literal* EmptyLiteral() { return nullptr; }
  V8_INLINE static ObjectLiteralProperty* EmptyObjectLiteralProperty() {
    return nullptr;
  }
944 945 946
  V8_INLINE static ClassLiteralProperty* EmptyClassLiteralProperty() {
    return nullptr;
  }
947
  V8_INLINE static FunctionLiteral* EmptyFunctionLiteral() { return nullptr; }
948
  V8_INLINE static Block* NullBlock() { return nullptr; }
949

950 951 952 953
  V8_INLINE static bool IsEmptyExpression(Expression* expr) {
    return expr == nullptr;
  }

954 955 956 957
  // Used in error return values.
  V8_INLINE static ZoneList<Expression*>* NullExpressionList() {
    return nullptr;
  }
958 959 960
  V8_INLINE static bool IsNullExpressionList(ZoneList<Expression*>* exprs) {
    return exprs == nullptr;
  }
961
  V8_INLINE static ZoneList<Statement*>* NullStatementList() { return nullptr; }
962 963 964 965
  V8_INLINE static bool IsNullStatementList(ZoneList<Statement*>* stmts) {
    return stmts == nullptr;
  }
  V8_INLINE static Statement* NullStatement() { return nullptr; }
966 967 968 969
  V8_INLINE bool IsNullStatement(Statement* stmt) { return stmt == nullptr; }
  V8_INLINE bool IsEmptyStatement(Statement* stmt) {
    DCHECK_NOT_NULL(stmt);
    return stmt->IsEmpty();
970
  }
971 972 973 974 975 976 977 978 979 980 981

  // Non-NULL empty string.
  V8_INLINE const AstRawString* EmptyIdentifierString() const {
    return ast_value_factory()->empty_string();
  }

  // Odd-ball literal creators.
  V8_INLINE Literal* GetLiteralTheHole(int position) {
    return factory()->NewTheHoleLiteral(kNoSourcePosition);
  }

982 983 984 985 986 987 988 989 990 991 992 993 994 995 996 997 998 999 1000
  // Producing data during the recursive descent.
  V8_INLINE const AstRawString* GetSymbol() const {
    const AstRawString* result = scanner()->CurrentSymbol(ast_value_factory());
    DCHECK(result != NULL);
    return result;
  }

  V8_INLINE const AstRawString* GetNextSymbol() const {
    return scanner()->NextSymbol(ast_value_factory());
  }

  V8_INLINE const AstRawString* GetNumberAsSymbol() const {
    double double_value = scanner()->DoubleValue();
    char array[100];
    const char* string = DoubleToCString(double_value, ArrayVector(array));
    return ast_value_factory()->GetOneByteString(string);
  }

  V8_INLINE Expression* ThisExpression(int pos = kNoSourcePosition) {
1001
    return NewUnresolved(ast_value_factory()->this_string(), pos,
1002
                         THIS_VARIABLE);
1003 1004 1005 1006 1007 1008 1009 1010 1011 1012
  }

  Expression* NewSuperPropertyReference(int pos);
  Expression* NewSuperCallReference(int pos);
  Expression* NewTargetExpression(int pos);
  Expression* FunctionSentExpression(int pos);

  Literal* ExpressionFromLiteral(Token::Value token, int pos);

  V8_INLINE Expression* ExpressionFromIdentifier(
1013
      const AstRawString* name, int start_position,
1014
      InferName infer = InferName::kYes) {
1015
    if (infer == InferName::kYes) {
1016 1017
      fni_->PushVariableName(name);
    }
1018
    return NewUnresolved(name, start_position);
1019 1020 1021 1022
  }

  V8_INLINE Expression* ExpressionFromString(int pos) {
    const AstRawString* symbol = GetSymbol();
1023
    fni_->PushLiteralName(symbol);
1024 1025 1026
    return factory()->NewStringLiteral(symbol, pos);
  }

1027 1028
  V8_INLINE ZoneList<Expression*>* NewExpressionList(int size) const {
    return new (zone()) ZoneList<Expression*>(size, zone());
1029
  }
1030
  V8_INLINE ZoneList<ObjectLiteral::Property*>* NewObjectPropertyList(
1031 1032 1033
      int size) const {
    return new (zone()) ZoneList<ObjectLiteral::Property*>(size, zone());
  }
1034 1035 1036 1037
  V8_INLINE ZoneList<ClassLiteral::Property*>* NewClassPropertyList(
      int size) const {
    return new (zone()) ZoneList<ClassLiteral::Property*>(size, zone());
  }
1038 1039
  V8_INLINE ZoneList<Statement*>* NewStatementList(int size) const {
    return new (zone()) ZoneList<Statement*>(size, zone());
1040
  }
1041 1042 1043
  V8_INLINE ZoneList<CaseClause*>* NewCaseClauseList(int size) const {
    return new (zone()) ZoneList<CaseClause*>(size, zone());
  }
1044

1045 1046 1047 1048
  V8_INLINE Expression* NewV8Intrinsic(const AstRawString* name,
                                       ZoneList<Expression*>* args, int pos,
                                       bool* ok);

1049 1050 1051 1052 1053
  V8_INLINE Statement* NewThrowStatement(Expression* exception, int pos) {
    return factory()->NewExpressionStatement(
        factory()->NewThrow(exception, pos), pos);
  }

1054
  V8_INLINE void AddParameterInitializationBlock(
1055 1056
      const ParserFormalParameters& parameters, ZoneList<Statement*>* body,
      bool is_async, bool* ok) {
1057 1058 1059
    if (parameters.is_simple) return;
    auto* init_block = BuildParameterInitializationBlock(parameters, ok);
    if (!*ok) return;
1060
    if (is_async) {
1061
      init_block = BuildRejectPromiseOnException(init_block);
1062
    }
1063 1064 1065 1066 1067 1068 1069 1070
    if (init_block != nullptr) body->Add(init_block, zone());
  }

  V8_INLINE void AddFormalParameter(ParserFormalParameters* parameters,
                                    Expression* pattern,
                                    Expression* initializer,
                                    int initializer_end_position,
                                    bool is_rest) {
1071
    parameters->UpdateArityAndFunctionLength(initializer != nullptr, is_rest);
1072 1073
    bool has_simple_name = pattern->IsVariableProxy() && initializer == nullptr;
    const AstRawString* name = has_simple_name
1074 1075
                                   ? pattern->AsVariableProxy()->raw_name()
                                   : ast_value_factory()->empty_string();
1076 1077 1078 1079
    auto parameter = new (parameters->scope->zone())
        ParserFormalParameters::Parameter(name, pattern, initializer,
                                          scanner()->location().beg_pos,
                                          initializer_end_position, is_rest);
1080 1081

    parameters->params.Add(parameter);
1082 1083
  }

1084
  V8_INLINE void DeclareFormalParameters(
1085
      DeclarationScope* scope,
1086
      const ThreadedList<ParserFormalParameters::Parameter>& parameters) {
1087 1088
    bool is_simple = classifier()->is_simple_parameter_list();
    if (!is_simple) scope->SetHasNonSimpleParameters();
1089 1090 1091
    for (auto parameter : parameters) {
      bool is_duplicate = false;
      bool is_optional = parameter->initializer != nullptr;
1092 1093 1094 1095
      // If the parameter list is simple, declare the parameters normally with
      // their names. If the parameter list is not simple, declare a temporary
      // for each parameter - the corresponding named variable is declared by
      // BuildParamerterInitializationBlock.
1096
      scope->DeclareParameter(
1097 1098
          is_simple ? parameter->name : ast_value_factory()->empty_string(),
          is_simple ? VAR : TEMPORARY, is_optional, parameter->is_rest,
1099
          &is_duplicate, ast_value_factory(), parameter->position);
1100 1101 1102 1103 1104
      if (is_duplicate &&
          classifier()->is_valid_formal_parameter_list_without_duplicates()) {
        classifier()->RecordDuplicateFormalParameterError(
            scanner()->location());
      }
1105 1106 1107
    }
  }

1108 1109 1110 1111 1112
  void DeclareArrowFunctionFormalParameters(ParserFormalParameters* parameters,
                                            Expression* params,
                                            const Scanner::Location& params_loc,
                                            Scanner::Location* duplicate_loc,
                                            bool* ok);
1113 1114 1115 1116 1117 1118 1119 1120

  V8_INLINE Expression* NoTemplateTag() { return NULL; }
  V8_INLINE static bool IsTaggedTemplate(const Expression* tag) {
    return tag != NULL;
  }

  Expression* ExpressionListToExpression(ZoneList<Expression*>* args);

1121
  void AddAccessorPrefixToFunctionName(bool is_get, FunctionLiteral* function,
1122
                                       const AstRawString* name);
1123 1124

  void SetFunctionNameFromPropertyName(ObjectLiteralProperty* property,
1125
                                       const AstRawString* name);
1126 1127 1128 1129

  void SetFunctionNameFromIdentifierRef(Expression* value,
                                        Expression* identifier);

1130
  V8_INLINE ZoneList<typename ExpressionClassifier::Error>*
1131 1132 1133 1134 1135 1136 1137 1138
  GetReportedErrorList() const {
    return function_state_->GetReportedErrorList();
  }

  V8_INLINE ZoneList<Expression*>* GetNonPatternList() const {
    return function_state_->non_patterns_to_rewrite();
  }

1139 1140 1141 1142
  V8_INLINE void CountUsage(v8::Isolate::UseCounterFeature feature) {
    ++use_counts_[feature];
  }

1143 1144 1145 1146 1147 1148
  // Returns true iff we're parsing the first function literal during
  // CreateDynamicFunction().
  V8_INLINE bool ParsingDynamicFunctionDeclaration() const {
    return parameters_end_pos_ != kNoSourcePosition;
  }

1149
  // Parser's private field members.
1150 1151 1152
  friend class DiscardableZoneScope;  // Uses reusable_preparser_.
  // FIXME(marja): Make reusable_preparser_ always use its own temp Zone (call
  // DeleteAll after each function), so this won't be needed.
1153

1154
  Scanner scanner_;
1155
  PreParser* reusable_preparser_;
1156
  Mode mode_;
1157

1158 1159 1160 1161 1162
  std::vector<FunctionLiteral*> literals_to_stitch_;
  Handle<String> source_;
  CompilerDispatcher* compiler_dispatcher_ = nullptr;
  ParseInfo* main_parse_info_ = nullptr;

1163 1164 1165 1166
  friend class ParserTarget;
  friend class ParserTargetScope;
  ParserTarget* target_stack_;  // for break, continue statements

1167
  ScriptCompiler::CompileOptions compile_options_;
1168
  ParseData* cached_parse_data_;
1169

1170
  PendingCompilationErrorHandler pending_error_handler_;
1171

1172 1173
  // Other information which will be stored in Parser and moved to Isolate after
  // parsing.
1174
  int use_counts_[v8::Isolate::kUseCounterFeatureCount];
1175
  int total_preparse_skipped_;
1176
  bool allow_lazy_;
1177
  bool temp_zoned_;
1178
  ParserLogger* log_;
1179

1180 1181 1182 1183 1184
  // If not kNoSourcePosition, indicates that the first function literal
  // encountered is a dynamic function, see CreateDynamicFunction(). This field
  // indicates the correct position of the ')' that closes the parameter list.
  // After that ')' is encountered, this field is reset to kNoSourcePosition.
  int parameters_end_pos_;
1185
};
1186

1187 1188 1189 1190 1191 1192 1193 1194 1195 1196 1197 1198 1199 1200 1201 1202 1203 1204 1205 1206 1207 1208 1209 1210 1211 1212 1213 1214 1215 1216 1217 1218 1219 1220 1221 1222 1223 1224 1225 1226 1227
// ----------------------------------------------------------------------------
// Target is a support class to facilitate manipulation of the
// Parser's target_stack_ (the stack of potential 'break' and
// 'continue' statement targets). Upon construction, a new target is
// added; it is removed upon destruction.

class ParserTarget BASE_EMBEDDED {
 public:
  ParserTarget(ParserBase<Parser>* parser, BreakableStatement* statement)
      : variable_(&parser->impl()->target_stack_),
        statement_(statement),
        previous_(parser->impl()->target_stack_) {
    parser->impl()->target_stack_ = this;
  }

  ~ParserTarget() { *variable_ = previous_; }

  ParserTarget* previous() { return previous_; }
  BreakableStatement* statement() { return statement_; }

 private:
  ParserTarget** variable_;
  BreakableStatement* statement_;
  ParserTarget* previous_;
};

class ParserTargetScope BASE_EMBEDDED {
 public:
  explicit ParserTargetScope(ParserBase<Parser>* parser)
      : variable_(&parser->impl()->target_stack_),
        previous_(parser->impl()->target_stack_) {
    parser->impl()->target_stack_ = nullptr;
  }

  ~ParserTargetScope() { *variable_ = previous_; }

 private:
  ParserTarget** variable_;
  ParserTarget* previous_;
};

1228 1229
}  // namespace internal
}  // namespace v8
1230

1231
#endif  // V8_PARSING_PARSER_H_