Upstream version 7.36.149.0
[platform/framework/web/crosswalk.git] / src / v8 / src / preparser.h
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_PREPARSER_H
6 #define V8_PREPARSER_H
7
8 #include "func-name-inferrer.h"
9 #include "hashmap.h"
10 #include "scopes.h"
11 #include "token.h"
12 #include "scanner.h"
13 #include "v8.h"
14
15 namespace v8 {
16 namespace internal {
17
18 // Common base class shared between parser and pre-parser. Traits encapsulate
19 // the differences between Parser and PreParser:
20
21 // - Return types: For example, Parser functions return Expression* and
22 // PreParser functions return PreParserExpression.
23
24 // - Creating parse tree nodes: Parser generates an AST during the recursive
25 // descent. PreParser doesn't create a tree. Instead, it passes around minimal
26 // data objects (PreParserExpression, PreParserIdentifier etc.) which contain
27 // just enough data for the upper layer functions. PreParserFactory is
28 // responsible for creating these dummy objects. It provides a similar kind of
29 // interface as AstNodeFactory, so ParserBase doesn't need to care which one is
30 // used.
31
32 // - Miscellanous other tasks interleaved with the recursive descent. For
33 // example, Parser keeps track of which function literals should be marked as
34 // pretenured, and PreParser doesn't care.
35
36 // The traits are expected to contain the following typedefs:
37 // struct Traits {
38 //   // In particular...
39 //   struct Type {
40 //     // Used by FunctionState and BlockState.
41 //     typedef Scope;
42 //     typedef GeneratorVariable;
43 //     typedef Zone;
44 //     // Return types for traversing functions.
45 //     typedef Identifier;
46 //     typedef Expression;
47 //     typedef FunctionLiteral;
48 //     typedef ObjectLiteralProperty;
49 //     typedef Literal;
50 //     typedef ExpressionList;
51 //     typedef PropertyList;
52 //     // For constructing objects returned by the traversing functions.
53 //     typedef Factory;
54 //   };
55 //   // ...
56 // };
57
58 template <typename Traits>
59 class ParserBase : public Traits {
60  public:
61   // Shorten type names defined by Traits.
62   typedef typename Traits::Type::Expression ExpressionT;
63   typedef typename Traits::Type::Identifier IdentifierT;
64
65   ParserBase(Scanner* scanner, uintptr_t stack_limit,
66              v8::Extension* extension,
67              ParserRecorder* log,
68              typename Traits::Type::Zone* zone,
69              typename Traits::Type::Parser this_object)
70       : Traits(this_object),
71         parenthesized_function_(false),
72         scope_(NULL),
73         function_state_(NULL),
74         extension_(extension),
75         fni_(NULL),
76         log_(log),
77         mode_(PARSE_EAGERLY),  // Lazy mode must be set explicitly.
78         scanner_(scanner),
79         stack_limit_(stack_limit),
80         stack_overflow_(false),
81         allow_lazy_(false),
82         allow_natives_syntax_(false),
83         allow_generators_(false),
84         allow_for_of_(false),
85         zone_(zone) { }
86
87   // Getters that indicate whether certain syntactical constructs are
88   // allowed to be parsed by this instance of the parser.
89   bool allow_lazy() const { return allow_lazy_; }
90   bool allow_natives_syntax() const { return allow_natives_syntax_; }
91   bool allow_generators() const { return allow_generators_; }
92   bool allow_for_of() const { return allow_for_of_; }
93   bool allow_modules() const { return scanner()->HarmonyModules(); }
94   bool allow_harmony_scoping() const { return scanner()->HarmonyScoping(); }
95   bool allow_harmony_numeric_literals() const {
96     return scanner()->HarmonyNumericLiterals();
97   }
98
99   // Setters that determine whether certain syntactical constructs are
100   // allowed to be parsed by this instance of the parser.
101   void set_allow_lazy(bool allow) { allow_lazy_ = allow; }
102   void set_allow_natives_syntax(bool allow) { allow_natives_syntax_ = allow; }
103   void set_allow_generators(bool allow) { allow_generators_ = allow; }
104   void set_allow_for_of(bool allow) { allow_for_of_ = allow; }
105   void set_allow_modules(bool allow) { scanner()->SetHarmonyModules(allow); }
106   void set_allow_harmony_scoping(bool allow) {
107     scanner()->SetHarmonyScoping(allow);
108   }
109   void set_allow_harmony_numeric_literals(bool allow) {
110     scanner()->SetHarmonyNumericLiterals(allow);
111   }
112
113  protected:
114   enum AllowEvalOrArgumentsAsIdentifier {
115     kAllowEvalOrArguments,
116     kDontAllowEvalOrArguments
117   };
118
119   enum Mode {
120     PARSE_LAZILY,
121     PARSE_EAGERLY
122   };
123
124   // ---------------------------------------------------------------------------
125   // FunctionState and BlockState together implement the parser's scope stack.
126   // The parser's current scope is in scope_. BlockState and FunctionState
127   // constructors push on the scope stack and the destructors pop. They are also
128   // used to hold the parser's per-function and per-block state.
129   class BlockState BASE_EMBEDDED {
130    public:
131     BlockState(typename Traits::Type::Scope** scope_stack,
132                typename Traits::Type::Scope* scope)
133         : scope_stack_(scope_stack),
134           outer_scope_(*scope_stack),
135           scope_(scope) {
136       *scope_stack_ = scope_;
137     }
138     ~BlockState() { *scope_stack_ = outer_scope_; }
139
140    private:
141     typename Traits::Type::Scope** scope_stack_;
142     typename Traits::Type::Scope* outer_scope_;
143     typename Traits::Type::Scope* scope_;
144   };
145
146   class FunctionState BASE_EMBEDDED {
147    public:
148     FunctionState(
149         FunctionState** function_state_stack,
150         typename Traits::Type::Scope** scope_stack,
151         typename Traits::Type::Scope* scope,
152         typename Traits::Type::Zone* zone = NULL);
153     ~FunctionState();
154
155     int NextMaterializedLiteralIndex() {
156       return next_materialized_literal_index_++;
157     }
158     int materialized_literal_count() {
159       return next_materialized_literal_index_ - JSFunction::kLiteralsPrefixSize;
160     }
161
162     int NextHandlerIndex() { return next_handler_index_++; }
163     int handler_count() { return next_handler_index_; }
164
165     void AddProperty() { expected_property_count_++; }
166     int expected_property_count() { return expected_property_count_; }
167
168     void set_is_generator(bool is_generator) { is_generator_ = is_generator; }
169     bool is_generator() const { return is_generator_; }
170
171     void set_generator_object_variable(
172         typename Traits::Type::GeneratorVariable* variable) {
173       ASSERT(variable != NULL);
174       ASSERT(!is_generator());
175       generator_object_variable_ = variable;
176       is_generator_ = true;
177     }
178     typename Traits::Type::GeneratorVariable* generator_object_variable()
179         const {
180       return generator_object_variable_;
181     }
182
183     typename Traits::Type::Factory* factory() { return &factory_; }
184
185    private:
186     // Used to assign an index to each literal that needs materialization in
187     // the function.  Includes regexp literals, and boilerplate for object and
188     // array literals.
189     int next_materialized_literal_index_;
190
191     // Used to assign a per-function index to try and catch handlers.
192     int next_handler_index_;
193
194     // Properties count estimation.
195     int expected_property_count_;
196
197     // Whether the function is a generator.
198     bool is_generator_;
199     // For generators, this variable may hold the generator object. It variable
200     // is used by yield expressions and return statements. It is not necessary
201     // for generator functions to have this variable set.
202     Variable* generator_object_variable_;
203
204     FunctionState** function_state_stack_;
205     FunctionState* outer_function_state_;
206     typename Traits::Type::Scope** scope_stack_;
207     typename Traits::Type::Scope* outer_scope_;
208     int saved_ast_node_id_;  // Only used by ParserTraits.
209     typename Traits::Type::Zone* extra_param_;
210     typename Traits::Type::Factory factory_;
211
212     friend class ParserTraits;
213   };
214
215   class ParsingModeScope BASE_EMBEDDED {
216    public:
217     ParsingModeScope(ParserBase* parser, Mode mode)
218         : parser_(parser),
219           old_mode_(parser->mode()) {
220       parser_->mode_ = mode;
221     }
222     ~ParsingModeScope() {
223       parser_->mode_ = old_mode_;
224     }
225
226    private:
227     ParserBase* parser_;
228     Mode old_mode_;
229   };
230
231   Scanner* scanner() const { return scanner_; }
232   int position() { return scanner_->location().beg_pos; }
233   int peek_position() { return scanner_->peek_location().beg_pos; }
234   bool stack_overflow() const { return stack_overflow_; }
235   void set_stack_overflow() { stack_overflow_ = true; }
236   Mode mode() const { return mode_; }
237   typename Traits::Type::Zone* zone() const { return zone_; }
238
239   INLINE(Token::Value peek()) {
240     if (stack_overflow_) return Token::ILLEGAL;
241     return scanner()->peek();
242   }
243
244   INLINE(Token::Value Next()) {
245     if (stack_overflow_) return Token::ILLEGAL;
246     {
247       int marker;
248       if (reinterpret_cast<uintptr_t>(&marker) < stack_limit_) {
249         // Any further calls to Next or peek will return the illegal token.
250         // The current call must return the next token, which might already
251         // have been peek'ed.
252         stack_overflow_ = true;
253       }
254     }
255     return scanner()->Next();
256   }
257
258   void Consume(Token::Value token) {
259     Token::Value next = Next();
260     USE(next);
261     USE(token);
262     ASSERT(next == token);
263   }
264
265   bool Check(Token::Value token) {
266     Token::Value next = peek();
267     if (next == token) {
268       Consume(next);
269       return true;
270     }
271     return false;
272   }
273
274   void Expect(Token::Value token, bool* ok) {
275     Token::Value next = Next();
276     if (next != token) {
277       ReportUnexpectedToken(next);
278       *ok = false;
279     }
280   }
281
282   void ExpectSemicolon(bool* ok) {
283     // Check for automatic semicolon insertion according to
284     // the rules given in ECMA-262, section 7.9, page 21.
285     Token::Value tok = peek();
286     if (tok == Token::SEMICOLON) {
287       Next();
288       return;
289     }
290     if (scanner()->HasAnyLineTerminatorBeforeNext() ||
291         tok == Token::RBRACE ||
292         tok == Token::EOS) {
293       return;
294     }
295     Expect(Token::SEMICOLON, ok);
296   }
297
298   bool peek_any_identifier() {
299     Token::Value next = peek();
300     return next == Token::IDENTIFIER ||
301         next == Token::FUTURE_RESERVED_WORD ||
302         next == Token::FUTURE_STRICT_RESERVED_WORD ||
303         next == Token::YIELD;
304   }
305
306   bool CheckContextualKeyword(Vector<const char> keyword) {
307     if (peek() == Token::IDENTIFIER &&
308         scanner()->is_next_contextual_keyword(keyword)) {
309       Consume(Token::IDENTIFIER);
310       return true;
311     }
312     return false;
313   }
314
315   void ExpectContextualKeyword(Vector<const char> keyword, bool* ok) {
316     Expect(Token::IDENTIFIER, ok);
317     if (!*ok) return;
318     if (!scanner()->is_literal_contextual_keyword(keyword)) {
319       ReportUnexpectedToken(scanner()->current_token());
320       *ok = false;
321     }
322   }
323
324   // Checks whether an octal literal was last seen between beg_pos and end_pos.
325   // If so, reports an error. Only called for strict mode.
326   void CheckOctalLiteral(int beg_pos, int end_pos, bool* ok) {
327     Scanner::Location octal = scanner()->octal_position();
328     if (octal.IsValid() && beg_pos <= octal.beg_pos &&
329         octal.end_pos <= end_pos) {
330       ReportMessageAt(octal, "strict_octal_literal");
331       scanner()->clear_octal_position();
332       *ok = false;
333     }
334   }
335
336   // Determine precedence of given token.
337   static int Precedence(Token::Value token, bool accept_IN) {
338     if (token == Token::IN && !accept_IN)
339       return 0;  // 0 precedence will terminate binary expression parsing
340     return Token::Precedence(token);
341   }
342
343   typename Traits::Type::Factory* factory() {
344     return function_state_->factory();
345   }
346
347   StrictMode strict_mode() { return scope_->strict_mode(); }
348   bool is_generator() const { return function_state_->is_generator(); }
349
350   // Report syntax errors.
351   void ReportMessage(const char* message, Vector<const char*> args,
352                      bool is_reference_error = false) {
353     Scanner::Location source_location = scanner()->location();
354     Traits::ReportMessageAt(source_location, message, args, is_reference_error);
355   }
356
357   void ReportMessageAt(Scanner::Location location, const char* message,
358                        bool is_reference_error = false) {
359     Traits::ReportMessageAt(location, message, Vector<const char*>::empty(),
360                             is_reference_error);
361   }
362
363   void ReportUnexpectedToken(Token::Value token);
364
365   // Recursive descent functions:
366
367   // Parses an identifier that is valid for the current scope, in particular it
368   // fails on strict mode future reserved keywords in a strict scope. If
369   // allow_eval_or_arguments is kAllowEvalOrArguments, we allow "eval" or
370   // "arguments" as identifier even in strict mode (this is needed in cases like
371   // "var foo = eval;").
372   IdentifierT ParseIdentifier(
373       AllowEvalOrArgumentsAsIdentifier,
374       bool* ok);
375   // Parses an identifier or a strict mode future reserved word, and indicate
376   // whether it is strict mode future reserved.
377   IdentifierT ParseIdentifierOrStrictReservedWord(
378       bool* is_strict_reserved,
379       bool* ok);
380   IdentifierT ParseIdentifierName(bool* ok);
381   // Parses an identifier and determines whether or not it is 'get' or 'set'.
382   IdentifierT ParseIdentifierNameOrGetOrSet(bool* is_get,
383                                             bool* is_set,
384                                             bool* ok);
385
386   ExpressionT ParseRegExpLiteral(bool seen_equal, bool* ok);
387
388   ExpressionT ParsePrimaryExpression(bool* ok);
389   ExpressionT ParseExpression(bool accept_IN, bool* ok);
390   ExpressionT ParseArrayLiteral(bool* ok);
391   ExpressionT ParseObjectLiteral(bool* ok);
392   typename Traits::Type::ExpressionList ParseArguments(bool* ok);
393   ExpressionT ParseAssignmentExpression(bool accept_IN, bool* ok);
394   ExpressionT ParseYieldExpression(bool* ok);
395   ExpressionT ParseConditionalExpression(bool accept_IN, bool* ok);
396   ExpressionT ParseBinaryExpression(int prec, bool accept_IN, bool* ok);
397   ExpressionT ParseUnaryExpression(bool* ok);
398   ExpressionT ParsePostfixExpression(bool* ok);
399   ExpressionT ParseLeftHandSideExpression(bool* ok);
400   ExpressionT ParseMemberWithNewPrefixesExpression(bool* ok);
401   ExpressionT ParseMemberExpression(bool* ok);
402   ExpressionT ParseMemberExpressionContinuation(ExpressionT expression,
403                                                 bool* ok);
404
405   // Checks if the expression is a valid reference expression (e.g., on the
406   // left-hand side of assignments). Although ruled out by ECMA as early errors,
407   // we allow calls for web compatibility and rewrite them to a runtime throw.
408   ExpressionT CheckAndRewriteReferenceExpression(
409       ExpressionT expression,
410       Scanner::Location location, const char* message, bool* ok);
411
412   // Used to detect duplicates in object literals. Each of the values
413   // kGetterProperty, kSetterProperty and kValueProperty represents
414   // a type of object literal property. When parsing a property, its
415   // type value is stored in the DuplicateFinder for the property name.
416   // Values are chosen so that having intersection bits means the there is
417   // an incompatibility.
418   // I.e., you can add a getter to a property that already has a setter, since
419   // kGetterProperty and kSetterProperty doesn't intersect, but not if it
420   // already has a getter or a value. Adding the getter to an existing
421   // setter will store the value (kGetterProperty | kSetterProperty), which
422   // is incompatible with adding any further properties.
423   enum PropertyKind {
424     kNone = 0,
425     // Bit patterns representing different object literal property types.
426     kGetterProperty = 1,
427     kSetterProperty = 2,
428     kValueProperty = 7,
429     // Helper constants.
430     kValueFlag = 4
431   };
432
433   // Validation per ECMA 262 - 11.1.5 "Object Initialiser".
434   class ObjectLiteralChecker {
435    public:
436     ObjectLiteralChecker(ParserBase* parser, StrictMode strict_mode)
437         : parser_(parser),
438           finder_(scanner()->unicode_cache()),
439           strict_mode_(strict_mode) { }
440
441     void CheckProperty(Token::Value property, PropertyKind type, bool* ok);
442
443    private:
444     ParserBase* parser() const { return parser_; }
445     Scanner* scanner() const { return parser_->scanner(); }
446
447     // Checks the type of conflict based on values coming from PropertyType.
448     bool HasConflict(PropertyKind type1, PropertyKind type2) {
449       return (type1 & type2) != 0;
450     }
451     bool IsDataDataConflict(PropertyKind type1, PropertyKind type2) {
452       return ((type1 & type2) & kValueFlag) != 0;
453     }
454     bool IsDataAccessorConflict(PropertyKind type1, PropertyKind type2) {
455       return ((type1 ^ type2) & kValueFlag) != 0;
456     }
457     bool IsAccessorAccessorConflict(PropertyKind type1, PropertyKind type2) {
458       return ((type1 | type2) & kValueFlag) == 0;
459     }
460
461     ParserBase* parser_;
462     DuplicateFinder finder_;
463     StrictMode strict_mode_;
464   };
465
466   // If true, the next (and immediately following) function literal is
467   // preceded by a parenthesis.
468   // Heuristically that means that the function will be called immediately,
469   // so never lazily compile it.
470   bool parenthesized_function_;
471
472   typename Traits::Type::Scope* scope_;  // Scope stack.
473   FunctionState* function_state_;  // Function state stack.
474   v8::Extension* extension_;
475   FuncNameInferrer* fni_;
476   ParserRecorder* log_;
477   Mode mode_;
478
479  private:
480   Scanner* scanner_;
481   uintptr_t stack_limit_;
482   bool stack_overflow_;
483
484   bool allow_lazy_;
485   bool allow_natives_syntax_;
486   bool allow_generators_;
487   bool allow_for_of_;
488
489   typename Traits::Type::Zone* zone_;  // Only used by Parser.
490 };
491
492
493 class PreParserIdentifier {
494  public:
495   PreParserIdentifier() : type_(kUnknownIdentifier) {}
496   static PreParserIdentifier Default() {
497     return PreParserIdentifier(kUnknownIdentifier);
498   }
499   static PreParserIdentifier Eval() {
500     return PreParserIdentifier(kEvalIdentifier);
501   }
502   static PreParserIdentifier Arguments() {
503     return PreParserIdentifier(kArgumentsIdentifier);
504   }
505   static PreParserIdentifier FutureReserved() {
506     return PreParserIdentifier(kFutureReservedIdentifier);
507   }
508   static PreParserIdentifier FutureStrictReserved() {
509     return PreParserIdentifier(kFutureStrictReservedIdentifier);
510   }
511   static PreParserIdentifier Yield() {
512     return PreParserIdentifier(kYieldIdentifier);
513   }
514   bool IsEval() { return type_ == kEvalIdentifier; }
515   bool IsArguments() { return type_ == kArgumentsIdentifier; }
516   bool IsEvalOrArguments() { return type_ >= kEvalIdentifier; }
517   bool IsYield() { return type_ == kYieldIdentifier; }
518   bool IsFutureReserved() { return type_ == kFutureReservedIdentifier; }
519   bool IsFutureStrictReserved() {
520     return type_ == kFutureStrictReservedIdentifier;
521   }
522   bool IsValidStrictVariable() { return type_ == kUnknownIdentifier; }
523
524  private:
525   enum Type {
526     kUnknownIdentifier,
527     kFutureReservedIdentifier,
528     kFutureStrictReservedIdentifier,
529     kYieldIdentifier,
530     kEvalIdentifier,
531     kArgumentsIdentifier
532   };
533   explicit PreParserIdentifier(Type type) : type_(type) {}
534   Type type_;
535
536   friend class PreParserExpression;
537 };
538
539
540 // Bits 0 and 1 are used to identify the type of expression:
541 // If bit 0 is set, it's an identifier.
542 // if bit 1 is set, it's a string literal.
543 // If neither is set, it's no particular type, and both set isn't
544 // use yet.
545 class PreParserExpression {
546  public:
547   static PreParserExpression Default() {
548     return PreParserExpression(kUnknownExpression);
549   }
550
551   static PreParserExpression FromIdentifier(PreParserIdentifier id) {
552     return PreParserExpression(kIdentifierFlag |
553                                (id.type_ << kIdentifierShift));
554   }
555
556   static PreParserExpression StringLiteral() {
557     return PreParserExpression(kUnknownStringLiteral);
558   }
559
560   static PreParserExpression UseStrictStringLiteral() {
561     return PreParserExpression(kUseStrictString);
562   }
563
564   static PreParserExpression This() {
565     return PreParserExpression(kThisExpression);
566   }
567
568   static PreParserExpression ThisProperty() {
569     return PreParserExpression(kThisPropertyExpression);
570   }
571
572   static PreParserExpression Property() {
573     return PreParserExpression(kPropertyExpression);
574   }
575
576   static PreParserExpression Call() {
577     return PreParserExpression(kCallExpression);
578   }
579
580   bool IsIdentifier() { return (code_ & kIdentifierFlag) != 0; }
581
582   PreParserIdentifier AsIdentifier() {
583     ASSERT(IsIdentifier());
584     return PreParserIdentifier(
585         static_cast<PreParserIdentifier::Type>(code_ >> kIdentifierShift));
586   }
587
588   bool IsStringLiteral() { return (code_ & kStringLiteralFlag) != 0; }
589
590   bool IsUseStrictLiteral() {
591     return (code_ & kStringLiteralMask) == kUseStrictString;
592   }
593
594   bool IsThis() { return code_ == kThisExpression; }
595
596   bool IsThisProperty() { return code_ == kThisPropertyExpression; }
597
598   bool IsProperty() {
599     return code_ == kPropertyExpression || code_ == kThisPropertyExpression;
600   }
601
602   bool IsCall() { return code_ == kCallExpression; }
603
604   bool IsValidReferenceExpression() {
605     return IsIdentifier() || IsProperty();
606   }
607
608   // At the moment PreParser doesn't track these expression types.
609   bool IsFunctionLiteral() const { return false; }
610   bool IsCallNew() const { return false; }
611
612   PreParserExpression AsFunctionLiteral() { return *this; }
613
614   // Dummy implementation for making expression->somefunc() work in both Parser
615   // and PreParser.
616   PreParserExpression* operator->() { return this; }
617
618   // More dummy implementations of things PreParser doesn't need to track:
619   void set_index(int index) {}  // For YieldExpressions
620   void set_parenthesized() {}
621
622  private:
623   // Least significant 2 bits are used as flags. Bits 0 and 1 represent
624   // identifiers or strings literals, and are mutually exclusive, but can both
625   // be absent. If the expression is an identifier or a string literal, the
626   // other bits describe the type (see PreParserIdentifier::Type and string
627   // literal constants below).
628   enum {
629     kUnknownExpression = 0,
630     // Identifiers
631     kIdentifierFlag = 1,  // Used to detect labels.
632     kIdentifierShift = 3,
633
634     kStringLiteralFlag = 2,  // Used to detect directive prologue.
635     kUnknownStringLiteral = kStringLiteralFlag,
636     kUseStrictString = kStringLiteralFlag | 8,
637     kStringLiteralMask = kUseStrictString,
638
639     // Below here applies if neither identifier nor string literal. Reserve the
640     // 2 least significant bits for flags.
641     kThisExpression = 1 << 2,
642     kThisPropertyExpression = 2 << 2,
643     kPropertyExpression = 3 << 2,
644     kCallExpression = 4 << 2
645   };
646
647   explicit PreParserExpression(int expression_code) : code_(expression_code) {}
648
649   int code_;
650 };
651
652
653 // PreParserExpressionList doesn't actually store the expressions because
654 // PreParser doesn't need to.
655 class PreParserExpressionList {
656  public:
657   // These functions make list->Add(some_expression) work (and do nothing).
658   PreParserExpressionList() : length_(0) {}
659   PreParserExpressionList* operator->() { return this; }
660   void Add(PreParserExpression, void*) { ++length_; }
661   int length() const { return length_; }
662  private:
663   int length_;
664 };
665
666
667 class PreParserStatement {
668  public:
669   static PreParserStatement Default() {
670     return PreParserStatement(kUnknownStatement);
671   }
672
673   static PreParserStatement FunctionDeclaration() {
674     return PreParserStatement(kFunctionDeclaration);
675   }
676
677   // Creates expression statement from expression.
678   // Preserves being an unparenthesized string literal, possibly
679   // "use strict".
680   static PreParserStatement ExpressionStatement(
681       PreParserExpression expression) {
682     if (expression.IsUseStrictLiteral()) {
683       return PreParserStatement(kUseStrictExpressionStatement);
684     }
685     if (expression.IsStringLiteral()) {
686       return PreParserStatement(kStringLiteralExpressionStatement);
687     }
688     return Default();
689   }
690
691   bool IsStringLiteral() {
692     return code_ == kStringLiteralExpressionStatement;
693   }
694
695   bool IsUseStrictLiteral() {
696     return code_ == kUseStrictExpressionStatement;
697   }
698
699   bool IsFunctionDeclaration() {
700     return code_ == kFunctionDeclaration;
701   }
702
703  private:
704   enum Type {
705     kUnknownStatement,
706     kStringLiteralExpressionStatement,
707     kUseStrictExpressionStatement,
708     kFunctionDeclaration
709   };
710
711   explicit PreParserStatement(Type code) : code_(code) {}
712   Type code_;
713 };
714
715
716
717 // PreParserStatementList doesn't actually store the statements because
718 // the PreParser does not need them.
719 class PreParserStatementList {
720  public:
721   // These functions make list->Add(some_expression) work as no-ops.
722   PreParserStatementList() {}
723   PreParserStatementList* operator->() { return this; }
724   void Add(PreParserStatement, void*) {}
725 };
726
727
728 class PreParserScope {
729  public:
730   explicit PreParserScope(PreParserScope* outer_scope, ScopeType scope_type)
731       : scope_type_(scope_type) {
732     strict_mode_ = outer_scope ? outer_scope->strict_mode() : SLOPPY;
733   }
734
735   ScopeType type() { return scope_type_; }
736   StrictMode strict_mode() const { return strict_mode_; }
737   void SetStrictMode(StrictMode strict_mode) { strict_mode_ = strict_mode; }
738
739  private:
740   ScopeType scope_type_;
741   StrictMode strict_mode_;
742 };
743
744
745 class PreParserFactory {
746  public:
747   explicit PreParserFactory(void* extra_param) {}
748   PreParserExpression NewLiteral(PreParserIdentifier identifier,
749                                  int pos) {
750     return PreParserExpression::Default();
751   }
752   PreParserExpression NewNumberLiteral(double number,
753                                        int pos) {
754     return PreParserExpression::Default();
755   }
756   PreParserExpression NewRegExpLiteral(PreParserIdentifier js_pattern,
757                                        PreParserIdentifier js_flags,
758                                        int literal_index,
759                                        int pos) {
760     return PreParserExpression::Default();
761   }
762   PreParserExpression NewArrayLiteral(PreParserExpressionList values,
763                                       int literal_index,
764                                       int pos) {
765     return PreParserExpression::Default();
766   }
767   PreParserExpression NewObjectLiteralProperty(bool is_getter,
768                                                PreParserExpression value,
769                                                int pos) {
770     return PreParserExpression::Default();
771   }
772   PreParserExpression NewObjectLiteralProperty(PreParserExpression key,
773                                                PreParserExpression value) {
774     return PreParserExpression::Default();
775   }
776   PreParserExpression NewObjectLiteral(PreParserExpressionList properties,
777                                        int literal_index,
778                                        int boilerplate_properties,
779                                        bool has_function,
780                                        int pos) {
781     return PreParserExpression::Default();
782   }
783   PreParserExpression NewVariableProxy(void* generator_variable) {
784     return PreParserExpression::Default();
785   }
786   PreParserExpression NewProperty(PreParserExpression obj,
787                                   PreParserExpression key,
788                                   int pos) {
789     if (obj.IsThis()) {
790       return PreParserExpression::ThisProperty();
791     }
792     return PreParserExpression::Property();
793   }
794   PreParserExpression NewUnaryOperation(Token::Value op,
795                                         PreParserExpression expression,
796                                         int pos) {
797     return PreParserExpression::Default();
798   }
799   PreParserExpression NewBinaryOperation(Token::Value op,
800                                          PreParserExpression left,
801                                          PreParserExpression right, int pos) {
802     return PreParserExpression::Default();
803   }
804   PreParserExpression NewCompareOperation(Token::Value op,
805                                           PreParserExpression left,
806                                           PreParserExpression right, int pos) {
807     return PreParserExpression::Default();
808   }
809   PreParserExpression NewAssignment(Token::Value op,
810                                     PreParserExpression left,
811                                     PreParserExpression right,
812                                     int pos) {
813     return PreParserExpression::Default();
814   }
815   PreParserExpression NewYield(PreParserExpression generator_object,
816                                PreParserExpression expression,
817                                Yield::Kind yield_kind,
818                                int pos) {
819     return PreParserExpression::Default();
820   }
821   PreParserExpression NewConditional(PreParserExpression condition,
822                                      PreParserExpression then_expression,
823                                      PreParserExpression else_expression,
824                                      int pos) {
825     return PreParserExpression::Default();
826   }
827   PreParserExpression NewCountOperation(Token::Value op,
828                                         bool is_prefix,
829                                         PreParserExpression expression,
830                                         int pos) {
831     return PreParserExpression::Default();
832   }
833   PreParserExpression NewCall(PreParserExpression expression,
834                               PreParserExpressionList arguments,
835                               int pos) {
836     return PreParserExpression::Call();
837   }
838   PreParserExpression NewCallNew(PreParserExpression expression,
839                                  PreParserExpressionList arguments,
840                                  int pos) {
841     return PreParserExpression::Default();
842   }
843 };
844
845
846 class PreParser;
847
848 class PreParserTraits {
849  public:
850   struct Type {
851     // TODO(marja): To be removed. The Traits object should contain all the data
852     // it needs.
853     typedef PreParser* Parser;
854
855     // Used by FunctionState and BlockState.
856     typedef PreParserScope Scope;
857     // PreParser doesn't need to store generator variables.
858     typedef void GeneratorVariable;
859     // No interaction with Zones.
860     typedef void Zone;
861
862     // Return types for traversing functions.
863     typedef PreParserIdentifier Identifier;
864     typedef PreParserExpression Expression;
865     typedef PreParserExpression YieldExpression;
866     typedef PreParserExpression FunctionLiteral;
867     typedef PreParserExpression ObjectLiteralProperty;
868     typedef PreParserExpression Literal;
869     typedef PreParserExpressionList ExpressionList;
870     typedef PreParserExpressionList PropertyList;
871     typedef PreParserStatementList StatementList;
872
873     // For constructing objects returned by the traversing functions.
874     typedef PreParserFactory Factory;
875   };
876
877   explicit PreParserTraits(PreParser* pre_parser) : pre_parser_(pre_parser) {}
878
879   // Custom operations executed when FunctionStates are created and
880   // destructed. (The PreParser doesn't need to do anything.)
881   template<typename FunctionState>
882   static void SetUpFunctionState(FunctionState* function_state, void*) {}
883   template<typename FunctionState>
884   static void TearDownFunctionState(FunctionState* function_state, void*) {}
885
886   // Helper functions for recursive descent.
887   static bool IsEvalOrArguments(PreParserIdentifier identifier) {
888     return identifier.IsEvalOrArguments();
889   }
890
891   // Returns true if the expression is of type "this.foo".
892   static bool IsThisProperty(PreParserExpression expression) {
893     return expression.IsThisProperty();
894   }
895
896   static bool IsIdentifier(PreParserExpression expression) {
897     return expression.IsIdentifier();
898   }
899
900   static PreParserIdentifier AsIdentifier(PreParserExpression expression) {
901     return expression.AsIdentifier();
902   }
903
904   static bool IsBoilerplateProperty(PreParserExpression property) {
905     // PreParser doesn't count boilerplate properties.
906     return false;
907   }
908
909   static bool IsArrayIndex(PreParserIdentifier string, uint32_t* index) {
910     return false;
911   }
912
913   // Functions for encapsulating the differences between parsing and preparsing;
914   // operations interleaved with the recursive descent.
915   static void PushLiteralName(FuncNameInferrer* fni, PreParserIdentifier id) {
916     // PreParser should not use FuncNameInferrer.
917     UNREACHABLE();
918   }
919   static void PushPropertyName(FuncNameInferrer* fni,
920                                PreParserExpression expression) {
921     // PreParser should not use FuncNameInferrer.
922     UNREACHABLE();
923   }
924
925   static void CheckFunctionLiteralInsideTopLevelObjectLiteral(
926       PreParserScope* scope, PreParserExpression value, bool* has_function) {}
927
928   static void CheckAssigningFunctionLiteralToProperty(
929       PreParserExpression left, PreParserExpression right) {}
930
931   // PreParser doesn't need to keep track of eval calls.
932   static void CheckPossibleEvalCall(PreParserExpression expression,
933                                     PreParserScope* scope) {}
934
935   static PreParserExpression MarkExpressionAsLValue(
936       PreParserExpression expression) {
937     // TODO(marja): To be able to produce the same errors, the preparser needs
938     // to start tracking which expressions are variables and which are lvalues.
939     return expression;
940   }
941
942   bool ShortcutNumericLiteralBinaryExpression(PreParserExpression* x,
943                                               PreParserExpression y,
944                                               Token::Value op,
945                                               int pos,
946                                               PreParserFactory* factory) {
947     return false;
948   }
949
950   PreParserExpression BuildUnaryExpression(PreParserExpression expression,
951                                            Token::Value op, int pos,
952                                            PreParserFactory* factory) {
953     return PreParserExpression::Default();
954   }
955
956   PreParserExpression NewThrowReferenceError(const char* type, int pos) {
957     return PreParserExpression::Default();
958   }
959   PreParserExpression NewThrowSyntaxError(
960       const char* type, Handle<Object> arg, int pos) {
961     return PreParserExpression::Default();
962   }
963   PreParserExpression NewThrowTypeError(
964       const char* type, Handle<Object> arg, int pos) {
965     return PreParserExpression::Default();
966   }
967
968   // Reporting errors.
969   void ReportMessageAt(Scanner::Location location,
970                        const char* message,
971                        Vector<const char*> args,
972                        bool is_reference_error = false);
973   void ReportMessageAt(Scanner::Location location,
974                        const char* type,
975                        const char* name_opt,
976                        bool is_reference_error = false);
977   void ReportMessageAt(int start_pos,
978                        int end_pos,
979                        const char* type,
980                        const char* name_opt,
981                        bool is_reference_error = false);
982
983   // "null" return type creators.
984   static PreParserIdentifier EmptyIdentifier() {
985     return PreParserIdentifier::Default();
986   }
987   static PreParserExpression EmptyExpression() {
988     return PreParserExpression::Default();
989   }
990   static PreParserExpression EmptyLiteral() {
991     return PreParserExpression::Default();
992   }
993   static PreParserExpressionList NullExpressionList() {
994     return PreParserExpressionList();
995   }
996
997   // Odd-ball literal creators.
998   static PreParserExpression GetLiteralTheHole(int position,
999                                                PreParserFactory* factory) {
1000     return PreParserExpression::Default();
1001   }
1002
1003   // Producing data during the recursive descent.
1004   PreParserIdentifier GetSymbol(Scanner* scanner);
1005   static PreParserIdentifier NextLiteralString(Scanner* scanner,
1006                                                PretenureFlag tenured) {
1007     return PreParserIdentifier::Default();
1008   }
1009
1010   static PreParserExpression ThisExpression(PreParserScope* scope,
1011                                             PreParserFactory* factory) {
1012     return PreParserExpression::This();
1013   }
1014
1015   static PreParserExpression ExpressionFromLiteral(
1016       Token::Value token, int pos, Scanner* scanner,
1017       PreParserFactory* factory) {
1018     return PreParserExpression::Default();
1019   }
1020
1021   static PreParserExpression ExpressionFromIdentifier(
1022       PreParserIdentifier name, int pos, PreParserScope* scope,
1023       PreParserFactory* factory) {
1024     return PreParserExpression::FromIdentifier(name);
1025   }
1026
1027   PreParserExpression ExpressionFromString(int pos,
1028                                            Scanner* scanner,
1029                                            PreParserFactory* factory = NULL);
1030
1031   static PreParserExpressionList NewExpressionList(int size, void* zone) {
1032     return PreParserExpressionList();
1033   }
1034
1035   static PreParserStatementList NewStatementList(int size, void* zone) {
1036     return PreParserStatementList();
1037   }
1038
1039   static PreParserExpressionList NewPropertyList(int size, void* zone) {
1040     return PreParserExpressionList();
1041   }
1042
1043   // Temporary glue; these functions will move to ParserBase.
1044   PreParserExpression ParseV8Intrinsic(bool* ok);
1045   PreParserExpression ParseFunctionLiteral(
1046       PreParserIdentifier name,
1047       Scanner::Location function_name_location,
1048       bool name_is_strict_reserved,
1049       bool is_generator,
1050       int function_token_position,
1051       FunctionLiteral::FunctionType type,
1052       bool* ok);
1053
1054  private:
1055   PreParser* pre_parser_;
1056 };
1057
1058
1059 // Preparsing checks a JavaScript program and emits preparse-data that helps
1060 // a later parsing to be faster.
1061 // See preparse-data-format.h for the data format.
1062
1063 // The PreParser checks that the syntax follows the grammar for JavaScript,
1064 // and collects some information about the program along the way.
1065 // The grammar check is only performed in order to understand the program
1066 // sufficiently to deduce some information about it, that can be used
1067 // to speed up later parsing. Finding errors is not the goal of pre-parsing,
1068 // rather it is to speed up properly written and correct programs.
1069 // That means that contextual checks (like a label being declared where
1070 // it is used) are generally omitted.
1071 class PreParser : public ParserBase<PreParserTraits> {
1072  public:
1073   typedef PreParserIdentifier Identifier;
1074   typedef PreParserExpression Expression;
1075   typedef PreParserStatement Statement;
1076
1077   enum PreParseResult {
1078     kPreParseStackOverflow,
1079     kPreParseSuccess
1080   };
1081
1082   PreParser(Scanner* scanner, ParserRecorder* log, uintptr_t stack_limit)
1083       : ParserBase<PreParserTraits>(scanner, stack_limit, NULL, log, NULL,
1084                                     this) {}
1085
1086   // Pre-parse the program from the character stream; returns true on
1087   // success (even if parsing failed, the pre-parse data successfully
1088   // captured the syntax error), and false if a stack-overflow happened
1089   // during parsing.
1090   PreParseResult PreParseProgram() {
1091     PreParserScope scope(scope_, GLOBAL_SCOPE);
1092     FunctionState top_scope(&function_state_, &scope_, &scope, NULL);
1093     bool ok = true;
1094     int start_position = scanner()->peek_location().beg_pos;
1095     ParseSourceElements(Token::EOS, &ok);
1096     if (stack_overflow()) return kPreParseStackOverflow;
1097     if (!ok) {
1098       ReportUnexpectedToken(scanner()->current_token());
1099     } else if (scope_->strict_mode() == STRICT) {
1100       CheckOctalLiteral(start_position, scanner()->location().end_pos, &ok);
1101     }
1102     return kPreParseSuccess;
1103   }
1104
1105   // Parses a single function literal, from the opening parentheses before
1106   // parameters to the closing brace after the body.
1107   // Returns a FunctionEntry describing the body of the function in enough
1108   // detail that it can be lazily compiled.
1109   // The scanner is expected to have matched the "function" or "function*"
1110   // keyword and parameters, and have consumed the initial '{'.
1111   // At return, unless an error occurred, the scanner is positioned before the
1112   // the final '}'.
1113   PreParseResult PreParseLazyFunction(StrictMode strict_mode,
1114                                       bool is_generator,
1115                                       ParserRecorder* log);
1116
1117  private:
1118   friend class PreParserTraits;
1119
1120   // These types form an algebra over syntactic categories that is just
1121   // rich enough to let us recognize and propagate the constructs that
1122   // are either being counted in the preparser data, or is important
1123   // to throw the correct syntax error exceptions.
1124
1125   enum VariableDeclarationContext {
1126     kSourceElement,
1127     kStatement,
1128     kForStatement
1129   };
1130
1131   // If a list of variable declarations includes any initializers.
1132   enum VariableDeclarationProperties {
1133     kHasInitializers,
1134     kHasNoInitializers
1135   };
1136
1137
1138   enum SourceElements {
1139     kUnknownSourceElements
1140   };
1141
1142   // All ParseXXX functions take as the last argument an *ok parameter
1143   // which is set to false if parsing failed; it is unchanged otherwise.
1144   // By making the 'exception handling' explicit, we are forced to check
1145   // for failure at the call sites.
1146   Statement ParseSourceElement(bool* ok);
1147   SourceElements ParseSourceElements(int end_token, bool* ok);
1148   Statement ParseStatement(bool* ok);
1149   Statement ParseFunctionDeclaration(bool* ok);
1150   Statement ParseBlock(bool* ok);
1151   Statement ParseVariableStatement(VariableDeclarationContext var_context,
1152                                    bool* ok);
1153   Statement ParseVariableDeclarations(VariableDeclarationContext var_context,
1154                                       VariableDeclarationProperties* decl_props,
1155                                       int* num_decl,
1156                                       bool* ok);
1157   Statement ParseExpressionOrLabelledStatement(bool* ok);
1158   Statement ParseIfStatement(bool* ok);
1159   Statement ParseContinueStatement(bool* ok);
1160   Statement ParseBreakStatement(bool* ok);
1161   Statement ParseReturnStatement(bool* ok);
1162   Statement ParseWithStatement(bool* ok);
1163   Statement ParseSwitchStatement(bool* ok);
1164   Statement ParseDoWhileStatement(bool* ok);
1165   Statement ParseWhileStatement(bool* ok);
1166   Statement ParseForStatement(bool* ok);
1167   Statement ParseThrowStatement(bool* ok);
1168   Statement ParseTryStatement(bool* ok);
1169   Statement ParseDebuggerStatement(bool* ok);
1170   Expression ParseConditionalExpression(bool accept_IN, bool* ok);
1171   Expression ParseObjectLiteral(bool* ok);
1172   Expression ParseV8Intrinsic(bool* ok);
1173
1174   Expression ParseFunctionLiteral(
1175       Identifier name,
1176       Scanner::Location function_name_location,
1177       bool name_is_strict_reserved,
1178       bool is_generator,
1179       int function_token_pos,
1180       FunctionLiteral::FunctionType function_type,
1181       bool* ok);
1182   void ParseLazyFunctionLiteralBody(bool* ok);
1183
1184   bool CheckInOrOf(bool accept_OF);
1185 };
1186
1187 template<class Traits>
1188 ParserBase<Traits>::FunctionState::FunctionState(
1189     FunctionState** function_state_stack,
1190     typename Traits::Type::Scope** scope_stack,
1191     typename Traits::Type::Scope* scope,
1192     typename Traits::Type::Zone* extra_param)
1193     : next_materialized_literal_index_(JSFunction::kLiteralsPrefixSize),
1194       next_handler_index_(0),
1195       expected_property_count_(0),
1196       is_generator_(false),
1197       generator_object_variable_(NULL),
1198       function_state_stack_(function_state_stack),
1199       outer_function_state_(*function_state_stack),
1200       scope_stack_(scope_stack),
1201       outer_scope_(*scope_stack),
1202       saved_ast_node_id_(0),
1203       extra_param_(extra_param),
1204       factory_(extra_param) {
1205   *scope_stack_ = scope;
1206   *function_state_stack = this;
1207   Traits::SetUpFunctionState(this, extra_param);
1208 }
1209
1210
1211 template<class Traits>
1212 ParserBase<Traits>::FunctionState::~FunctionState() {
1213   *scope_stack_ = outer_scope_;
1214   *function_state_stack_ = outer_function_state_;
1215   Traits::TearDownFunctionState(this, extra_param_);
1216 }
1217
1218
1219 template<class Traits>
1220 void ParserBase<Traits>::ReportUnexpectedToken(Token::Value token) {
1221   Scanner::Location source_location = scanner()->location();
1222
1223   // Four of the tokens are treated specially
1224   switch (token) {
1225     case Token::EOS:
1226       return ReportMessageAt(source_location, "unexpected_eos");
1227     case Token::NUMBER:
1228       return ReportMessageAt(source_location, "unexpected_token_number");
1229     case Token::STRING:
1230       return ReportMessageAt(source_location, "unexpected_token_string");
1231     case Token::IDENTIFIER:
1232       return ReportMessageAt(source_location, "unexpected_token_identifier");
1233     case Token::FUTURE_RESERVED_WORD:
1234       return ReportMessageAt(source_location, "unexpected_reserved");
1235     case Token::YIELD:
1236     case Token::FUTURE_STRICT_RESERVED_WORD:
1237       return ReportMessageAt(source_location, strict_mode() == SLOPPY
1238           ? "unexpected_token_identifier" : "unexpected_strict_reserved");
1239     default:
1240       const char* name = Token::String(token);
1241       ASSERT(name != NULL);
1242       Traits::ReportMessageAt(
1243           source_location, "unexpected_token", Vector<const char*>(&name, 1));
1244   }
1245 }
1246
1247
1248 template<class Traits>
1249 typename ParserBase<Traits>::IdentifierT ParserBase<Traits>::ParseIdentifier(
1250     AllowEvalOrArgumentsAsIdentifier allow_eval_or_arguments,
1251     bool* ok) {
1252   Token::Value next = Next();
1253   if (next == Token::IDENTIFIER) {
1254     IdentifierT name = this->GetSymbol(scanner());
1255     if (allow_eval_or_arguments == kDontAllowEvalOrArguments &&
1256         strict_mode() == STRICT && this->IsEvalOrArguments(name)) {
1257       ReportMessageAt(scanner()->location(), "strict_eval_arguments");
1258       *ok = false;
1259     }
1260     return name;
1261   } else if (strict_mode() == SLOPPY &&
1262              (next == Token::FUTURE_STRICT_RESERVED_WORD ||
1263              (next == Token::YIELD && !is_generator()))) {
1264     return this->GetSymbol(scanner());
1265   } else {
1266     this->ReportUnexpectedToken(next);
1267     *ok = false;
1268     return Traits::EmptyIdentifier();
1269   }
1270 }
1271
1272
1273 template <class Traits>
1274 typename ParserBase<Traits>::IdentifierT ParserBase<
1275     Traits>::ParseIdentifierOrStrictReservedWord(bool* is_strict_reserved,
1276                                                  bool* ok) {
1277   Token::Value next = Next();
1278   if (next == Token::IDENTIFIER) {
1279     *is_strict_reserved = false;
1280   } else if (next == Token::FUTURE_STRICT_RESERVED_WORD ||
1281              (next == Token::YIELD && !this->is_generator())) {
1282     *is_strict_reserved = true;
1283   } else {
1284     ReportUnexpectedToken(next);
1285     *ok = false;
1286     return Traits::EmptyIdentifier();
1287   }
1288   return this->GetSymbol(scanner());
1289 }
1290
1291
1292 template <class Traits>
1293 typename ParserBase<Traits>::IdentifierT
1294 ParserBase<Traits>::ParseIdentifierName(bool* ok) {
1295   Token::Value next = Next();
1296   if (next != Token::IDENTIFIER && next != Token::FUTURE_RESERVED_WORD &&
1297       next != Token::FUTURE_STRICT_RESERVED_WORD && !Token::IsKeyword(next)) {
1298     this->ReportUnexpectedToken(next);
1299     *ok = false;
1300     return Traits::EmptyIdentifier();
1301   }
1302   return this->GetSymbol(scanner());
1303 }
1304
1305
1306 template <class Traits>
1307 typename ParserBase<Traits>::IdentifierT
1308 ParserBase<Traits>::ParseIdentifierNameOrGetOrSet(bool* is_get,
1309                                                   bool* is_set,
1310                                                   bool* ok) {
1311   IdentifierT result = ParseIdentifierName(ok);
1312   if (!*ok) return Traits::EmptyIdentifier();
1313   scanner()->IsGetOrSet(is_get, is_set);
1314   return result;
1315 }
1316
1317
1318 template <class Traits>
1319 typename ParserBase<Traits>::ExpressionT ParserBase<Traits>::ParseRegExpLiteral(
1320     bool seen_equal, bool* ok) {
1321   int pos = peek_position();
1322   if (!scanner()->ScanRegExpPattern(seen_equal)) {
1323     Next();
1324     ReportMessage("unterminated_regexp", Vector<const char*>::empty());
1325     *ok = false;
1326     return Traits::EmptyExpression();
1327   }
1328
1329   int literal_index = function_state_->NextMaterializedLiteralIndex();
1330
1331   IdentifierT js_pattern = this->NextLiteralString(scanner(), TENURED);
1332   if (!scanner()->ScanRegExpFlags()) {
1333     Next();
1334     ReportMessageAt(scanner()->location(), "invalid_regexp_flags");
1335     *ok = false;
1336     return Traits::EmptyExpression();
1337   }
1338   IdentifierT js_flags = this->NextLiteralString(scanner(), TENURED);
1339   Next();
1340   return factory()->NewRegExpLiteral(js_pattern, js_flags, literal_index, pos);
1341 }
1342
1343
1344 #define CHECK_OK  ok); \
1345   if (!*ok) return this->EmptyExpression(); \
1346   ((void)0
1347 #define DUMMY )  // to make indentation work
1348 #undef DUMMY
1349
1350 // Used in functions where the return type is not ExpressionT.
1351 #define CHECK_OK_CUSTOM(x) ok); \
1352   if (!*ok) return this->x(); \
1353   ((void)0
1354 #define DUMMY )  // to make indentation work
1355 #undef DUMMY
1356
1357 template <class Traits>
1358 typename ParserBase<Traits>::ExpressionT
1359 ParserBase<Traits>::ParsePrimaryExpression(bool* ok) {
1360   // PrimaryExpression ::
1361   //   'this'
1362   //   'null'
1363   //   'true'
1364   //   'false'
1365   //   Identifier
1366   //   Number
1367   //   String
1368   //   ArrayLiteral
1369   //   ObjectLiteral
1370   //   RegExpLiteral
1371   //   '(' Expression ')'
1372
1373   int pos = peek_position();
1374   ExpressionT result = this->EmptyExpression();
1375   Token::Value token = peek();
1376   switch (token) {
1377     case Token::THIS: {
1378       Consume(Token::THIS);
1379       result = this->ThisExpression(scope_, factory());
1380       break;
1381     }
1382
1383     case Token::NULL_LITERAL:
1384     case Token::TRUE_LITERAL:
1385     case Token::FALSE_LITERAL:
1386     case Token::NUMBER:
1387       Next();
1388       result = this->ExpressionFromLiteral(token, pos, scanner(), factory());
1389       break;
1390
1391     case Token::IDENTIFIER:
1392     case Token::YIELD:
1393     case Token::FUTURE_STRICT_RESERVED_WORD: {
1394       // Using eval or arguments in this context is OK even in strict mode.
1395       IdentifierT name = ParseIdentifier(kAllowEvalOrArguments, CHECK_OK);
1396       result = this->ExpressionFromIdentifier(name, pos, scope_, factory());
1397       break;
1398     }
1399
1400     case Token::STRING: {
1401       Consume(Token::STRING);
1402       result = this->ExpressionFromString(pos, scanner(), factory());
1403       break;
1404     }
1405
1406     case Token::ASSIGN_DIV:
1407       result = this->ParseRegExpLiteral(true, CHECK_OK);
1408       break;
1409
1410     case Token::DIV:
1411       result = this->ParseRegExpLiteral(false, CHECK_OK);
1412       break;
1413
1414     case Token::LBRACK:
1415       result = this->ParseArrayLiteral(CHECK_OK);
1416       break;
1417
1418     case Token::LBRACE:
1419       result = this->ParseObjectLiteral(CHECK_OK);
1420       break;
1421
1422     case Token::LPAREN:
1423       Consume(Token::LPAREN);
1424       // Heuristically try to detect immediately called functions before
1425       // seeing the call parentheses.
1426       parenthesized_function_ = (peek() == Token::FUNCTION);
1427       result = this->ParseExpression(true, CHECK_OK);
1428       Expect(Token::RPAREN, CHECK_OK);
1429       break;
1430
1431     case Token::MOD:
1432       if (allow_natives_syntax() || extension_ != NULL) {
1433         result = this->ParseV8Intrinsic(CHECK_OK);
1434         break;
1435       }
1436       // If we're not allowing special syntax we fall-through to the
1437       // default case.
1438
1439     default: {
1440       Next();
1441       ReportUnexpectedToken(token);
1442       *ok = false;
1443     }
1444   }
1445
1446   return result;
1447 }
1448
1449 // Precedence = 1
1450 template <class Traits>
1451 typename ParserBase<Traits>::ExpressionT ParserBase<Traits>::ParseExpression(
1452     bool accept_IN, bool* ok) {
1453   // Expression ::
1454   //   AssignmentExpression
1455   //   Expression ',' AssignmentExpression
1456
1457   ExpressionT result = this->ParseAssignmentExpression(accept_IN, CHECK_OK);
1458   while (peek() == Token::COMMA) {
1459     Expect(Token::COMMA, CHECK_OK);
1460     int pos = position();
1461     ExpressionT right = this->ParseAssignmentExpression(accept_IN, CHECK_OK);
1462     result = factory()->NewBinaryOperation(Token::COMMA, result, right, pos);
1463   }
1464   return result;
1465 }
1466
1467
1468 template <class Traits>
1469 typename ParserBase<Traits>::ExpressionT ParserBase<Traits>::ParseArrayLiteral(
1470     bool* ok) {
1471   // ArrayLiteral ::
1472   //   '[' Expression? (',' Expression?)* ']'
1473
1474   int pos = peek_position();
1475   typename Traits::Type::ExpressionList values =
1476       this->NewExpressionList(4, zone_);
1477   Expect(Token::LBRACK, CHECK_OK);
1478   while (peek() != Token::RBRACK) {
1479     ExpressionT elem = this->EmptyExpression();
1480     if (peek() == Token::COMMA) {
1481       elem = this->GetLiteralTheHole(peek_position(), factory());
1482     } else {
1483       elem = this->ParseAssignmentExpression(true, CHECK_OK);
1484     }
1485     values->Add(elem, zone_);
1486     if (peek() != Token::RBRACK) {
1487       Expect(Token::COMMA, CHECK_OK);
1488     }
1489   }
1490   Expect(Token::RBRACK, CHECK_OK);
1491
1492   // Update the scope information before the pre-parsing bailout.
1493   int literal_index = function_state_->NextMaterializedLiteralIndex();
1494
1495   return factory()->NewArrayLiteral(values, literal_index, pos);
1496 }
1497
1498
1499 template <class Traits>
1500 typename ParserBase<Traits>::ExpressionT ParserBase<Traits>::ParseObjectLiteral(
1501     bool* ok) {
1502   // ObjectLiteral ::
1503   // '{' ((
1504   //       ((IdentifierName | String | Number) ':' AssignmentExpression) |
1505   //       (('get' | 'set') (IdentifierName | String | Number) FunctionLiteral)
1506   //      ) ',')* '}'
1507   // (Except that trailing comma is not required and not allowed.)
1508
1509   int pos = peek_position();
1510   typename Traits::Type::PropertyList properties =
1511       this->NewPropertyList(4, zone_);
1512   int number_of_boilerplate_properties = 0;
1513   bool has_function = false;
1514
1515   ObjectLiteralChecker checker(this, strict_mode());
1516
1517   Expect(Token::LBRACE, CHECK_OK);
1518
1519   while (peek() != Token::RBRACE) {
1520     if (fni_ != NULL) fni_->Enter();
1521
1522     typename Traits::Type::Literal key = this->EmptyLiteral();
1523     Token::Value next = peek();
1524     int next_pos = peek_position();
1525
1526     switch (next) {
1527       case Token::FUTURE_RESERVED_WORD:
1528       case Token::FUTURE_STRICT_RESERVED_WORD:
1529       case Token::IDENTIFIER: {
1530         bool is_getter = false;
1531         bool is_setter = false;
1532         IdentifierT id =
1533             ParseIdentifierNameOrGetOrSet(&is_getter, &is_setter, CHECK_OK);
1534         if (fni_ != NULL) this->PushLiteralName(fni_, id);
1535
1536         if ((is_getter || is_setter) && peek() != Token::COLON) {
1537           // Special handling of getter and setter syntax:
1538           // { ... , get foo() { ... }, ... , set foo(v) { ... v ... } , ... }
1539           // We have already read the "get" or "set" keyword.
1540           Token::Value next = Next();
1541           if (next != i::Token::IDENTIFIER &&
1542               next != i::Token::FUTURE_RESERVED_WORD &&
1543               next != i::Token::FUTURE_STRICT_RESERVED_WORD &&
1544               next != i::Token::NUMBER &&
1545               next != i::Token::STRING &&
1546               !Token::IsKeyword(next)) {
1547             ReportUnexpectedToken(next);
1548             *ok = false;
1549             return this->EmptyLiteral();
1550           }
1551           // Validate the property.
1552           PropertyKind type = is_getter ? kGetterProperty : kSetterProperty;
1553           checker.CheckProperty(next, type, CHECK_OK);
1554           IdentifierT name = this->GetSymbol(scanner_);
1555           typename Traits::Type::FunctionLiteral value =
1556               this->ParseFunctionLiteral(
1557                   name, scanner()->location(),
1558                   false,  // reserved words are allowed here
1559                   false,  // not a generator
1560                   RelocInfo::kNoPosition, FunctionLiteral::ANONYMOUS_EXPRESSION,
1561                   CHECK_OK);
1562           // Allow any number of parameters for compatibilty with JSC.
1563           // Specification only allows zero parameters for get and one for set.
1564           typename Traits::Type::ObjectLiteralProperty property =
1565               factory()->NewObjectLiteralProperty(is_getter, value, next_pos);
1566           if (this->IsBoilerplateProperty(property)) {
1567             number_of_boilerplate_properties++;
1568           }
1569           properties->Add(property, zone());
1570           if (peek() != Token::RBRACE) {
1571             // Need {} because of the CHECK_OK macro.
1572             Expect(Token::COMMA, CHECK_OK);
1573           }
1574
1575           if (fni_ != NULL) {
1576             fni_->Infer();
1577             fni_->Leave();
1578           }
1579           continue;  // restart the while
1580         }
1581         // Failed to parse as get/set property, so it's just a normal property
1582         // (which might be called "get" or "set" or something else).
1583         key = factory()->NewLiteral(id, next_pos);
1584         break;
1585       }
1586       case Token::STRING: {
1587         Consume(Token::STRING);
1588         IdentifierT string = this->GetSymbol(scanner_);
1589         if (fni_ != NULL) this->PushLiteralName(fni_, string);
1590         uint32_t index;
1591         if (this->IsArrayIndex(string, &index)) {
1592           key = factory()->NewNumberLiteral(index, next_pos);
1593           break;
1594         }
1595         key = factory()->NewLiteral(string, next_pos);
1596         break;
1597       }
1598       case Token::NUMBER: {
1599         Consume(Token::NUMBER);
1600         key = this->ExpressionFromLiteral(Token::NUMBER, next_pos, scanner_,
1601                                           factory());
1602         break;
1603       }
1604       default:
1605         if (Token::IsKeyword(next)) {
1606           Consume(next);
1607           IdentifierT string = this->GetSymbol(scanner_);
1608           key = factory()->NewLiteral(string, next_pos);
1609         } else {
1610           Token::Value next = Next();
1611           ReportUnexpectedToken(next);
1612           *ok = false;
1613           return this->EmptyLiteral();
1614         }
1615     }
1616
1617     // Validate the property
1618     checker.CheckProperty(next, kValueProperty, CHECK_OK);
1619
1620     Expect(Token::COLON, CHECK_OK);
1621     ExpressionT value = this->ParseAssignmentExpression(true, CHECK_OK);
1622
1623     typename Traits::Type::ObjectLiteralProperty property =
1624         factory()->NewObjectLiteralProperty(key, value);
1625
1626     // Mark top-level object literals that contain function literals and
1627     // pretenure the literal so it can be added as a constant function
1628     // property. (Parser only.)
1629     this->CheckFunctionLiteralInsideTopLevelObjectLiteral(scope_, value,
1630                                                           &has_function);
1631
1632     // Count CONSTANT or COMPUTED properties to maintain the enumeration order.
1633     if (this->IsBoilerplateProperty(property)) {
1634       number_of_boilerplate_properties++;
1635     }
1636     properties->Add(property, zone());
1637
1638     // TODO(1240767): Consider allowing trailing comma.
1639     if (peek() != Token::RBRACE) {
1640       // Need {} because of the CHECK_OK macro.
1641       Expect(Token::COMMA, CHECK_OK);
1642     }
1643
1644     if (fni_ != NULL) {
1645       fni_->Infer();
1646       fni_->Leave();
1647     }
1648   }
1649   Expect(Token::RBRACE, CHECK_OK);
1650
1651   // Computation of literal_index must happen before pre parse bailout.
1652   int literal_index = function_state_->NextMaterializedLiteralIndex();
1653
1654   return factory()->NewObjectLiteral(properties,
1655                                      literal_index,
1656                                      number_of_boilerplate_properties,
1657                                      has_function,
1658                                      pos);
1659 }
1660
1661
1662 template <class Traits>
1663 typename Traits::Type::ExpressionList ParserBase<Traits>::ParseArguments(
1664     bool* ok) {
1665   // Arguments ::
1666   //   '(' (AssignmentExpression)*[','] ')'
1667
1668   typename Traits::Type::ExpressionList result =
1669       this->NewExpressionList(4, zone_);
1670   Expect(Token::LPAREN, CHECK_OK_CUSTOM(NullExpressionList));
1671   bool done = (peek() == Token::RPAREN);
1672   while (!done) {
1673     ExpressionT argument = this->ParseAssignmentExpression(
1674         true, CHECK_OK_CUSTOM(NullExpressionList));
1675     result->Add(argument, zone_);
1676     if (result->length() > Code::kMaxArguments) {
1677       ReportMessageAt(scanner()->location(), "too_many_arguments");
1678       *ok = false;
1679       return this->NullExpressionList();
1680     }
1681     done = (peek() == Token::RPAREN);
1682     if (!done) {
1683       // Need {} because of the CHECK_OK_CUSTOM macro.
1684       Expect(Token::COMMA, CHECK_OK_CUSTOM(NullExpressionList));
1685     }
1686   }
1687   Expect(Token::RPAREN, CHECK_OK_CUSTOM(NullExpressionList));
1688   return result;
1689 }
1690
1691 // Precedence = 2
1692 template <class Traits>
1693 typename ParserBase<Traits>::ExpressionT
1694 ParserBase<Traits>::ParseAssignmentExpression(bool accept_IN, bool* ok) {
1695   // AssignmentExpression ::
1696   //   ConditionalExpression
1697   //   YieldExpression
1698   //   LeftHandSideExpression AssignmentOperator AssignmentExpression
1699
1700   Scanner::Location lhs_location = scanner()->peek_location();
1701
1702   if (peek() == Token::YIELD && is_generator()) {
1703     return this->ParseYieldExpression(ok);
1704   }
1705
1706   if (fni_ != NULL) fni_->Enter();
1707   ExpressionT expression =
1708       this->ParseConditionalExpression(accept_IN, CHECK_OK);
1709
1710   if (!Token::IsAssignmentOp(peek())) {
1711     if (fni_ != NULL) fni_->Leave();
1712     // Parsed conditional expression only (no assignment).
1713     return expression;
1714   }
1715
1716   expression = this->CheckAndRewriteReferenceExpression(
1717       expression, lhs_location, "invalid_lhs_in_assignment", CHECK_OK);
1718   expression = this->MarkExpressionAsLValue(expression);
1719
1720   Token::Value op = Next();  // Get assignment operator.
1721   int pos = position();
1722   ExpressionT right = this->ParseAssignmentExpression(accept_IN, CHECK_OK);
1723
1724   // TODO(1231235): We try to estimate the set of properties set by
1725   // constructors. We define a new property whenever there is an
1726   // assignment to a property of 'this'. We should probably only add
1727   // properties if we haven't seen them before. Otherwise we'll
1728   // probably overestimate the number of properties.
1729   if (op == Token::ASSIGN && this->IsThisProperty(expression)) {
1730     function_state_->AddProperty();
1731   }
1732
1733   this->CheckAssigningFunctionLiteralToProperty(expression, right);
1734
1735   if (fni_ != NULL) {
1736     // Check if the right hand side is a call to avoid inferring a
1737     // name if we're dealing with "a = function(){...}();"-like
1738     // expression.
1739     if ((op == Token::INIT_VAR
1740          || op == Token::INIT_CONST_LEGACY
1741          || op == Token::ASSIGN)
1742         && (!right->IsCall() && !right->IsCallNew())) {
1743       fni_->Infer();
1744     } else {
1745       fni_->RemoveLastFunction();
1746     }
1747     fni_->Leave();
1748   }
1749
1750   return factory()->NewAssignment(op, expression, right, pos);
1751 }
1752
1753 template <class Traits>
1754 typename ParserBase<Traits>::ExpressionT
1755 ParserBase<Traits>::ParseYieldExpression(bool* ok) {
1756   // YieldExpression ::
1757   //   'yield' '*'? AssignmentExpression
1758   int pos = peek_position();
1759   Expect(Token::YIELD, CHECK_OK);
1760   Yield::Kind kind =
1761       Check(Token::MUL) ? Yield::DELEGATING : Yield::SUSPEND;
1762   ExpressionT generator_object =
1763       factory()->NewVariableProxy(function_state_->generator_object_variable());
1764   ExpressionT expression =
1765       ParseAssignmentExpression(false, CHECK_OK);
1766   typename Traits::Type::YieldExpression yield =
1767       factory()->NewYield(generator_object, expression, kind, pos);
1768   if (kind == Yield::DELEGATING) {
1769     yield->set_index(function_state_->NextHandlerIndex());
1770   }
1771   return yield;
1772 }
1773
1774
1775 // Precedence = 3
1776 template <class Traits>
1777 typename ParserBase<Traits>::ExpressionT
1778 ParserBase<Traits>::ParseConditionalExpression(bool accept_IN, bool* ok) {
1779   // ConditionalExpression ::
1780   //   LogicalOrExpression
1781   //   LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression
1782
1783   int pos = peek_position();
1784   // We start using the binary expression parser for prec >= 4 only!
1785   ExpressionT expression = this->ParseBinaryExpression(4, accept_IN, CHECK_OK);
1786   if (peek() != Token::CONDITIONAL) return expression;
1787   Consume(Token::CONDITIONAL);
1788   // In parsing the first assignment expression in conditional
1789   // expressions we always accept the 'in' keyword; see ECMA-262,
1790   // section 11.12, page 58.
1791   ExpressionT left = ParseAssignmentExpression(true, CHECK_OK);
1792   Expect(Token::COLON, CHECK_OK);
1793   ExpressionT right = ParseAssignmentExpression(accept_IN, CHECK_OK);
1794   return factory()->NewConditional(expression, left, right, pos);
1795 }
1796
1797
1798 // Precedence >= 4
1799 template <class Traits>
1800 typename ParserBase<Traits>::ExpressionT
1801 ParserBase<Traits>::ParseBinaryExpression(int prec, bool accept_IN, bool* ok) {
1802   ASSERT(prec >= 4);
1803   ExpressionT x = this->ParseUnaryExpression(CHECK_OK);
1804   for (int prec1 = Precedence(peek(), accept_IN); prec1 >= prec; prec1--) {
1805     // prec1 >= 4
1806     while (Precedence(peek(), accept_IN) == prec1) {
1807       Token::Value op = Next();
1808       int pos = position();
1809       ExpressionT y = ParseBinaryExpression(prec1 + 1, accept_IN, CHECK_OK);
1810
1811       if (this->ShortcutNumericLiteralBinaryExpression(&x, y, op, pos,
1812                                                        factory())) {
1813         continue;
1814       }
1815
1816       // For now we distinguish between comparisons and other binary
1817       // operations.  (We could combine the two and get rid of this
1818       // code and AST node eventually.)
1819       if (Token::IsCompareOp(op)) {
1820         // We have a comparison.
1821         Token::Value cmp = op;
1822         switch (op) {
1823           case Token::NE: cmp = Token::EQ; break;
1824           case Token::NE_STRICT: cmp = Token::EQ_STRICT; break;
1825           default: break;
1826         }
1827         x = factory()->NewCompareOperation(cmp, x, y, pos);
1828         if (cmp != op) {
1829           // The comparison was negated - add a NOT.
1830           x = factory()->NewUnaryOperation(Token::NOT, x, pos);
1831         }
1832
1833       } else {
1834         // We have a "normal" binary operation.
1835         x = factory()->NewBinaryOperation(op, x, y, pos);
1836       }
1837     }
1838   }
1839   return x;
1840 }
1841
1842
1843 template <class Traits>
1844 typename ParserBase<Traits>::ExpressionT
1845 ParserBase<Traits>::ParseUnaryExpression(bool* ok) {
1846   // UnaryExpression ::
1847   //   PostfixExpression
1848   //   'delete' UnaryExpression
1849   //   'void' UnaryExpression
1850   //   'typeof' UnaryExpression
1851   //   '++' UnaryExpression
1852   //   '--' UnaryExpression
1853   //   '+' UnaryExpression
1854   //   '-' UnaryExpression
1855   //   '~' UnaryExpression
1856   //   '!' UnaryExpression
1857
1858   Token::Value op = peek();
1859   if (Token::IsUnaryOp(op)) {
1860     op = Next();
1861     int pos = position();
1862     ExpressionT expression = ParseUnaryExpression(CHECK_OK);
1863
1864     // "delete identifier" is a syntax error in strict mode.
1865     if (op == Token::DELETE && strict_mode() == STRICT &&
1866         this->IsIdentifier(expression)) {
1867       ReportMessage("strict_delete", Vector<const char*>::empty());
1868       *ok = false;
1869       return this->EmptyExpression();
1870     }
1871
1872     // Allow Traits do rewrite the expression.
1873     return this->BuildUnaryExpression(expression, op, pos, factory());
1874   } else if (Token::IsCountOp(op)) {
1875     op = Next();
1876     Scanner::Location lhs_location = scanner()->peek_location();
1877     ExpressionT expression = this->ParseUnaryExpression(CHECK_OK);
1878     expression = this->CheckAndRewriteReferenceExpression(
1879         expression, lhs_location, "invalid_lhs_in_prefix_op", CHECK_OK);
1880     this->MarkExpressionAsLValue(expression);
1881
1882     return factory()->NewCountOperation(op,
1883                                         true /* prefix */,
1884                                         expression,
1885                                         position());
1886
1887   } else {
1888     return this->ParsePostfixExpression(ok);
1889   }
1890 }
1891
1892
1893 template <class Traits>
1894 typename ParserBase<Traits>::ExpressionT
1895 ParserBase<Traits>::ParsePostfixExpression(bool* ok) {
1896   // PostfixExpression ::
1897   //   LeftHandSideExpression ('++' | '--')?
1898
1899   Scanner::Location lhs_location = scanner()->peek_location();
1900   ExpressionT expression = this->ParseLeftHandSideExpression(CHECK_OK);
1901   if (!scanner()->HasAnyLineTerminatorBeforeNext() &&
1902       Token::IsCountOp(peek())) {
1903     expression = this->CheckAndRewriteReferenceExpression(
1904         expression, lhs_location, "invalid_lhs_in_postfix_op", CHECK_OK);
1905     expression = this->MarkExpressionAsLValue(expression);
1906
1907     Token::Value next = Next();
1908     expression =
1909         factory()->NewCountOperation(next,
1910                                      false /* postfix */,
1911                                      expression,
1912                                      position());
1913   }
1914   return expression;
1915 }
1916
1917
1918 template <class Traits>
1919 typename ParserBase<Traits>::ExpressionT
1920 ParserBase<Traits>::ParseLeftHandSideExpression(bool* ok) {
1921   // LeftHandSideExpression ::
1922   //   (NewExpression | MemberExpression) ...
1923
1924   ExpressionT result = this->ParseMemberWithNewPrefixesExpression(CHECK_OK);
1925
1926   while (true) {
1927     switch (peek()) {
1928       case Token::LBRACK: {
1929         Consume(Token::LBRACK);
1930         int pos = position();
1931         ExpressionT index = ParseExpression(true, CHECK_OK);
1932         result = factory()->NewProperty(result, index, pos);
1933         Expect(Token::RBRACK, CHECK_OK);
1934         break;
1935       }
1936
1937       case Token::LPAREN: {
1938         int pos;
1939         if (scanner()->current_token() == Token::IDENTIFIER) {
1940           // For call of an identifier we want to report position of
1941           // the identifier as position of the call in the stack trace.
1942           pos = position();
1943         } else {
1944           // For other kinds of calls we record position of the parenthesis as
1945           // position of the call. Note that this is extremely important for
1946           // expressions of the form function(){...}() for which call position
1947           // should not point to the closing brace otherwise it will intersect
1948           // with positions recorded for function literal and confuse debugger.
1949           pos = peek_position();
1950           // Also the trailing parenthesis are a hint that the function will
1951           // be called immediately. If we happen to have parsed a preceding
1952           // function literal eagerly, we can also compile it eagerly.
1953           if (result->IsFunctionLiteral() && mode() == PARSE_EAGERLY) {
1954             result->AsFunctionLiteral()->set_parenthesized();
1955           }
1956         }
1957         typename Traits::Type::ExpressionList args = ParseArguments(CHECK_OK);
1958
1959         // Keep track of eval() calls since they disable all local variable
1960         // optimizations.
1961         // The calls that need special treatment are the
1962         // direct eval calls. These calls are all of the form eval(...), with
1963         // no explicit receiver.
1964         // These calls are marked as potentially direct eval calls. Whether
1965         // they are actually direct calls to eval is determined at run time.
1966         this->CheckPossibleEvalCall(result, scope_);
1967         result = factory()->NewCall(result, args, pos);
1968         if (fni_ != NULL) fni_->RemoveLastFunction();
1969         break;
1970       }
1971
1972       case Token::PERIOD: {
1973         Consume(Token::PERIOD);
1974         int pos = position();
1975         IdentifierT name = ParseIdentifierName(CHECK_OK);
1976         result = factory()->NewProperty(
1977             result, factory()->NewLiteral(name, pos), pos);
1978         if (fni_ != NULL) this->PushLiteralName(fni_, name);
1979         break;
1980       }
1981
1982       default:
1983         return result;
1984     }
1985   }
1986 }
1987
1988
1989 template <class Traits>
1990 typename ParserBase<Traits>::ExpressionT
1991 ParserBase<Traits>::ParseMemberWithNewPrefixesExpression(bool* ok) {
1992   // NewExpression ::
1993   //   ('new')+ MemberExpression
1994
1995   // The grammar for new expressions is pretty warped. We can have several 'new'
1996   // keywords following each other, and then a MemberExpression. When we see '('
1997   // after the MemberExpression, it's associated with the rightmost unassociated
1998   // 'new' to create a NewExpression with arguments. However, a NewExpression
1999   // can also occur without arguments.
2000
2001   // Examples of new expression:
2002   // new foo.bar().baz means (new (foo.bar)()).baz
2003   // new foo()() means (new foo())()
2004   // new new foo()() means (new (new foo())())
2005   // new new foo means new (new foo)
2006   // new new foo() means new (new foo())
2007   // new new foo().bar().baz means (new (new foo()).bar()).baz
2008
2009   if (peek() == Token::NEW) {
2010     Consume(Token::NEW);
2011     int new_pos = position();
2012     ExpressionT result = this->ParseMemberWithNewPrefixesExpression(CHECK_OK);
2013     if (peek() == Token::LPAREN) {
2014       // NewExpression with arguments.
2015       typename Traits::Type::ExpressionList args =
2016           this->ParseArguments(CHECK_OK);
2017       result = factory()->NewCallNew(result, args, new_pos);
2018       // The expression can still continue with . or [ after the arguments.
2019       result = this->ParseMemberExpressionContinuation(result, CHECK_OK);
2020       return result;
2021     }
2022     // NewExpression without arguments.
2023     return factory()->NewCallNew(result, this->NewExpressionList(0, zone_),
2024                                  new_pos);
2025   }
2026   // No 'new' keyword.
2027   return this->ParseMemberExpression(ok);
2028 }
2029
2030
2031 template <class Traits>
2032 typename ParserBase<Traits>::ExpressionT
2033 ParserBase<Traits>::ParseMemberExpression(bool* ok) {
2034   // MemberExpression ::
2035   //   (PrimaryExpression | FunctionLiteral)
2036   //     ('[' Expression ']' | '.' Identifier | Arguments)*
2037
2038   // The '[' Expression ']' and '.' Identifier parts are parsed by
2039   // ParseMemberExpressionContinuation, and the Arguments part is parsed by the
2040   // caller.
2041
2042   // Parse the initial primary or function expression.
2043   ExpressionT result = this->EmptyExpression();
2044   if (peek() == Token::FUNCTION) {
2045     Consume(Token::FUNCTION);
2046     int function_token_position = position();
2047     bool is_generator = allow_generators() && Check(Token::MUL);
2048     IdentifierT name = this->EmptyIdentifier();
2049     bool is_strict_reserved_name = false;
2050     Scanner::Location function_name_location = Scanner::Location::invalid();
2051     FunctionLiteral::FunctionType function_type =
2052         FunctionLiteral::ANONYMOUS_EXPRESSION;
2053     if (peek_any_identifier()) {
2054       name = ParseIdentifierOrStrictReservedWord(&is_strict_reserved_name,
2055                                                  CHECK_OK);
2056       function_name_location = scanner()->location();
2057       function_type = FunctionLiteral::NAMED_EXPRESSION;
2058     }
2059     result = this->ParseFunctionLiteral(name,
2060                                         function_name_location,
2061                                         is_strict_reserved_name,
2062                                         is_generator,
2063                                         function_token_position,
2064                                         function_type,
2065                                         CHECK_OK);
2066   } else {
2067     result = ParsePrimaryExpression(CHECK_OK);
2068   }
2069
2070   result = ParseMemberExpressionContinuation(result, CHECK_OK);
2071   return result;
2072 }
2073
2074
2075 template <class Traits>
2076 typename ParserBase<Traits>::ExpressionT
2077 ParserBase<Traits>::ParseMemberExpressionContinuation(ExpressionT expression,
2078                                                       bool* ok) {
2079   // Parses this part of MemberExpression:
2080   // ('[' Expression ']' | '.' Identifier)*
2081   while (true) {
2082     switch (peek()) {
2083       case Token::LBRACK: {
2084         Consume(Token::LBRACK);
2085         int pos = position();
2086         ExpressionT index = this->ParseExpression(true, CHECK_OK);
2087         expression = factory()->NewProperty(expression, index, pos);
2088         if (fni_ != NULL) {
2089           this->PushPropertyName(fni_, index);
2090         }
2091         Expect(Token::RBRACK, CHECK_OK);
2092         break;
2093       }
2094       case Token::PERIOD: {
2095         Consume(Token::PERIOD);
2096         int pos = position();
2097         IdentifierT name = ParseIdentifierName(CHECK_OK);
2098         expression = factory()->NewProperty(
2099             expression, factory()->NewLiteral(name, pos), pos);
2100         if (fni_ != NULL) {
2101           this->PushLiteralName(fni_, name);
2102         }
2103         break;
2104       }
2105       default:
2106         return expression;
2107     }
2108   }
2109   ASSERT(false);
2110   return this->EmptyExpression();
2111 }
2112
2113
2114 template <typename Traits>
2115 typename ParserBase<Traits>::ExpressionT
2116 ParserBase<Traits>::CheckAndRewriteReferenceExpression(
2117     ExpressionT expression,
2118     Scanner::Location location, const char* message, bool* ok) {
2119   if (strict_mode() == STRICT && this->IsIdentifier(expression) &&
2120       this->IsEvalOrArguments(this->AsIdentifier(expression))) {
2121     this->ReportMessageAt(location, "strict_eval_arguments", false);
2122     *ok = false;
2123     return this->EmptyExpression();
2124   } else if (expression->IsValidReferenceExpression()) {
2125     return expression;
2126   } else if (expression->IsCall()) {
2127     // If it is a call, make it a runtime error for legacy web compatibility.
2128     // Rewrite `expr' to `expr[throw ReferenceError]'.
2129     int pos = location.beg_pos;
2130     ExpressionT error = this->NewThrowReferenceError(message, pos);
2131     return factory()->NewProperty(expression, error, pos);
2132   } else {
2133     this->ReportMessageAt(location, message, true);
2134     *ok = false;
2135     return this->EmptyExpression();
2136   }
2137 }
2138
2139
2140 #undef CHECK_OK
2141 #undef CHECK_OK_CUSTOM
2142
2143
2144 template <typename Traits>
2145 void ParserBase<Traits>::ObjectLiteralChecker::CheckProperty(
2146     Token::Value property,
2147     PropertyKind type,
2148     bool* ok) {
2149   int old;
2150   if (property == Token::NUMBER) {
2151     old = scanner()->FindNumber(&finder_, type);
2152   } else {
2153     old = scanner()->FindSymbol(&finder_, type);
2154   }
2155   PropertyKind old_type = static_cast<PropertyKind>(old);
2156   if (HasConflict(old_type, type)) {
2157     if (IsDataDataConflict(old_type, type)) {
2158       // Both are data properties.
2159       if (strict_mode_ == SLOPPY) return;
2160       parser()->ReportMessageAt(scanner()->location(),
2161                                "strict_duplicate_property");
2162     } else if (IsDataAccessorConflict(old_type, type)) {
2163       // Both a data and an accessor property with the same name.
2164       parser()->ReportMessageAt(scanner()->location(),
2165                                "accessor_data_property");
2166     } else {
2167       ASSERT(IsAccessorAccessorConflict(old_type, type));
2168       // Both accessors of the same type.
2169       parser()->ReportMessageAt(scanner()->location(),
2170                                "accessor_get_set");
2171     }
2172     *ok = false;
2173   }
2174 }
2175
2176
2177 } }  // v8::internal
2178
2179 #endif  // V8_PREPARSER_H