OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
110 kPreParseStackOverflow, | 110 kPreParseStackOverflow, |
111 kPreParseSuccess | 111 kPreParseSuccess |
112 }; | 112 }; |
113 | 113 |
114 | 114 |
115 PreParser(i::Scanner* scanner, | 115 PreParser(i::Scanner* scanner, |
116 i::ParserRecorder* log, | 116 i::ParserRecorder* log, |
117 uintptr_t stack_limit, | 117 uintptr_t stack_limit, |
118 bool allow_lazy, | 118 bool allow_lazy, |
119 bool allow_natives_syntax, | 119 bool allow_natives_syntax, |
120 bool allow_modules) | 120 bool allow_modules, |
| 121 bool allow_generators) |
121 : scanner_(scanner), | 122 : scanner_(scanner), |
122 log_(log), | 123 log_(log), |
123 scope_(NULL), | 124 scope_(NULL), |
124 stack_limit_(stack_limit), | 125 stack_limit_(stack_limit), |
125 strict_mode_violation_location_(i::Scanner::Location::invalid()), | 126 strict_mode_violation_location_(i::Scanner::Location::invalid()), |
126 strict_mode_violation_type_(NULL), | 127 strict_mode_violation_type_(NULL), |
127 stack_overflow_(false), | 128 stack_overflow_(false), |
128 allow_lazy_(allow_lazy), | 129 allow_lazy_(allow_lazy), |
129 allow_modules_(allow_modules), | 130 allow_modules_(allow_modules), |
130 allow_natives_syntax_(allow_natives_syntax), | 131 allow_natives_syntax_(allow_natives_syntax), |
| 132 allow_generators_(allow_generators), |
131 parenthesized_function_(false), | 133 parenthesized_function_(false), |
132 harmony_scoping_(scanner->HarmonyScoping()) { } | 134 harmony_scoping_(scanner->HarmonyScoping()) { } |
133 | 135 |
134 ~PreParser() {} | 136 ~PreParser() {} |
135 | 137 |
136 // Pre-parse the program from the character stream; returns true on | 138 // Pre-parse the program from the character stream; returns true on |
137 // success (even if parsing failed, the pre-parse data successfully | 139 // success (even if parsing failed, the pre-parse data successfully |
138 // captured the syntax error), and false if a stack-overflow happened | 140 // captured the syntax error), and false if a stack-overflow happened |
139 // during parsing. | 141 // during parsing. |
140 static PreParseResult PreParseProgram(i::Scanner* scanner, | 142 static PreParseResult PreParseProgram(i::Scanner* scanner, |
141 i::ParserRecorder* log, | 143 i::ParserRecorder* log, |
142 int flags, | 144 int flags, |
143 uintptr_t stack_limit) { | 145 uintptr_t stack_limit) { |
144 bool allow_lazy = (flags & i::kAllowLazy) != 0; | 146 bool allow_lazy = (flags & i::kAllowLazy) != 0; |
145 bool allow_natives_syntax = (flags & i::kAllowNativesSyntax) != 0; | 147 bool allow_natives_syntax = (flags & i::kAllowNativesSyntax) != 0; |
146 bool allow_modules = (flags & i::kAllowModules) != 0; | 148 bool allow_modules = (flags & i::kAllowModules) != 0; |
| 149 bool allow_generators = (flags & i::kAllowGenerators) != 0; |
147 return PreParser(scanner, log, stack_limit, allow_lazy, | 150 return PreParser(scanner, log, stack_limit, allow_lazy, |
148 allow_natives_syntax, allow_modules).PreParse(); | 151 allow_natives_syntax, allow_modules, |
| 152 allow_generators).PreParse(); |
149 } | 153 } |
150 | 154 |
151 // Parses a single function literal, from the opening parentheses before | 155 // Parses a single function literal, from the opening parentheses before |
152 // parameters to the closing brace after the body. | 156 // parameters to the closing brace after the body. |
153 // Returns a FunctionEntry describing the body of the function in enough | 157 // Returns a FunctionEntry describing the body of the function in enough |
154 // detail that it can be lazily compiled. | 158 // detail that it can be lazily compiled. |
155 // The scanner is expected to have matched the "function" keyword and | 159 // The scanner is expected to have matched the "function" or "function*" |
156 // parameters, and have consumed the initial '{'. | 160 // keyword and parameters, and have consumed the initial '{'. |
157 // At return, unless an error occurred, the scanner is positioned before the | 161 // At return, unless an error occurred, the scanner is positioned before the |
158 // the final '}'. | 162 // the final '}'. |
159 PreParseResult PreParseLazyFunction(i::LanguageMode mode, | 163 PreParseResult PreParseLazyFunction(i::LanguageMode mode, |
| 164 bool is_generator, |
160 i::ParserRecorder* log); | 165 i::ParserRecorder* log); |
161 | 166 |
162 private: | 167 private: |
163 // Used to detect duplicates in object literals. Each of the values | 168 // Used to detect duplicates in object literals. Each of the values |
164 // kGetterProperty, kSetterProperty and kValueProperty represents | 169 // kGetterProperty, kSetterProperty and kValueProperty represents |
165 // a type of object literal property. When parsing a property, its | 170 // a type of object literal property. When parsing a property, its |
166 // type value is stored in the DuplicateFinder for the property name. | 171 // type value is stored in the DuplicateFinder for the property name. |
167 // Values are chosen so that having intersection bits means the there is | 172 // Values are chosen so that having intersection bits means the there is |
168 // an incompatibility. | 173 // an incompatibility. |
169 // I.e., you can add a getter to a property that already has a setter, since | 174 // I.e., you can add a getter to a property that already has a setter, since |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
233 } | 238 } |
234 static Identifier Arguments() { | 239 static Identifier Arguments() { |
235 return Identifier(kArgumentsIdentifier); | 240 return Identifier(kArgumentsIdentifier); |
236 } | 241 } |
237 static Identifier FutureReserved() { | 242 static Identifier FutureReserved() { |
238 return Identifier(kFutureReservedIdentifier); | 243 return Identifier(kFutureReservedIdentifier); |
239 } | 244 } |
240 static Identifier FutureStrictReserved() { | 245 static Identifier FutureStrictReserved() { |
241 return Identifier(kFutureStrictReservedIdentifier); | 246 return Identifier(kFutureStrictReservedIdentifier); |
242 } | 247 } |
| 248 static Identifier Yield() { |
| 249 return Identifier(kYieldIdentifier); |
| 250 } |
243 bool IsEval() { return type_ == kEvalIdentifier; } | 251 bool IsEval() { return type_ == kEvalIdentifier; } |
244 bool IsArguments() { return type_ == kArgumentsIdentifier; } | 252 bool IsArguments() { return type_ == kArgumentsIdentifier; } |
245 bool IsEvalOrArguments() { return type_ >= kEvalIdentifier; } | 253 bool IsEvalOrArguments() { return type_ >= kEvalIdentifier; } |
| 254 bool IsYield() { return type_ == kYieldIdentifier; } |
246 bool IsFutureReserved() { return type_ == kFutureReservedIdentifier; } | 255 bool IsFutureReserved() { return type_ == kFutureReservedIdentifier; } |
247 bool IsFutureStrictReserved() { | 256 bool IsFutureStrictReserved() { |
248 return type_ == kFutureStrictReservedIdentifier; | 257 return type_ == kFutureStrictReservedIdentifier; |
249 } | 258 } |
250 bool IsValidStrictVariable() { return type_ == kUnknownIdentifier; } | 259 bool IsValidStrictVariable() { return type_ == kUnknownIdentifier; } |
251 | 260 |
252 private: | 261 private: |
253 enum Type { | 262 enum Type { |
254 kUnknownIdentifier, | 263 kUnknownIdentifier, |
255 kFutureReservedIdentifier, | 264 kFutureReservedIdentifier, |
256 kFutureStrictReservedIdentifier, | 265 kFutureStrictReservedIdentifier, |
| 266 kYieldIdentifier, |
257 kEvalIdentifier, | 267 kEvalIdentifier, |
258 kArgumentsIdentifier | 268 kArgumentsIdentifier |
259 }; | 269 }; |
260 explicit Identifier(Type type) : type_(type) { } | 270 explicit Identifier(Type type) : type_(type) { } |
261 Type type_; | 271 Type type_; |
262 | 272 |
263 friend class Expression; | 273 friend class Expression; |
264 }; | 274 }; |
265 | 275 |
266 // Bits 0 and 1 are used to identify the type of expression: | 276 // Bits 0 and 1 are used to identify the type of expression: |
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
340 bool IsStrictFunction() { | 350 bool IsStrictFunction() { |
341 return code_ == kStrictFunctionExpression; | 351 return code_ == kStrictFunctionExpression; |
342 } | 352 } |
343 | 353 |
344 Expression Parenthesize() { | 354 Expression Parenthesize() { |
345 int type = code_ & 3; | 355 int type = code_ & 3; |
346 if (type != 0) { | 356 if (type != 0) { |
347 // Identifiers and string literals can be parenthesized. | 357 // Identifiers and string literals can be parenthesized. |
348 // They no longer work as labels or directive prologues, | 358 // They no longer work as labels or directive prologues, |
349 // but are still recognized in other contexts. | 359 // but are still recognized in other contexts. |
350 return Expression(code_ | kParentesizedExpressionFlag); | 360 return Expression(code_ | kParenthesizedExpressionFlag); |
351 } | 361 } |
352 // For other types of expressions, it's not important to remember | 362 // For other types of expressions, it's not important to remember |
353 // the parentheses. | 363 // the parentheses. |
354 return *this; | 364 return *this; |
355 } | 365 } |
356 | 366 |
357 private: | 367 private: |
358 // First two/three bits are used as flags. | 368 // First two/three bits are used as flags. |
359 // Bit 0 and 1 represent identifiers or strings literals, and are | 369 // Bit 0 and 1 represent identifiers or strings literals, and are |
360 // mutually exclusive, but can both be absent. | 370 // mutually exclusive, but can both be absent. |
361 // If bit 0 or 1 are set, bit 2 marks that the expression has | 371 // If bit 0 or 1 are set, bit 2 marks that the expression has |
362 // been wrapped in parentheses (a string literal can no longer | 372 // been wrapped in parentheses (a string literal can no longer |
363 // be a directive prologue, and an identifier can no longer be | 373 // be a directive prologue, and an identifier can no longer be |
364 // a label. | 374 // a label. |
365 enum { | 375 enum { |
366 kUnknownExpression = 0, | 376 kUnknownExpression = 0, |
367 // Identifiers | 377 // Identifiers |
368 kIdentifierFlag = 1, // Used to detect labels. | 378 kIdentifierFlag = 1, // Used to detect labels. |
369 kIdentifierShift = 3, | 379 kIdentifierShift = 3, |
370 | 380 |
371 kStringLiteralFlag = 2, // Used to detect directive prologue. | 381 kStringLiteralFlag = 2, // Used to detect directive prologue. |
372 kUnknownStringLiteral = kStringLiteralFlag, | 382 kUnknownStringLiteral = kStringLiteralFlag, |
373 kUseStrictString = kStringLiteralFlag | 8, | 383 kUseStrictString = kStringLiteralFlag | 8, |
374 kStringLiteralMask = kUseStrictString, | 384 kStringLiteralMask = kUseStrictString, |
375 | 385 |
376 kParentesizedExpressionFlag = 4, // Only if identifier or string literal. | 386 // Only if identifier or string literal. |
| 387 kParenthesizedExpressionFlag = 4, |
377 | 388 |
378 // Below here applies if neither identifier nor string literal. | 389 // Below here applies if neither identifier nor string literal. |
379 kThisExpression = 4, | 390 kThisExpression = 4, |
380 kThisPropertyExpression = 8, | 391 kThisPropertyExpression = 8, |
381 kStrictFunctionExpression = 12 | 392 kStrictFunctionExpression = 12 |
382 }; | 393 }; |
383 | 394 |
384 explicit Expression(int expression_code) : code_(expression_code) { } | 395 explicit Expression(int expression_code) : code_(expression_code) { } |
385 | 396 |
386 int code_; | 397 int code_; |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
444 class Scope { | 455 class Scope { |
445 public: | 456 public: |
446 Scope(Scope** variable, ScopeType type) | 457 Scope(Scope** variable, ScopeType type) |
447 : variable_(variable), | 458 : variable_(variable), |
448 prev_(*variable), | 459 prev_(*variable), |
449 type_(type), | 460 type_(type), |
450 materialized_literal_count_(0), | 461 materialized_literal_count_(0), |
451 expected_properties_(0), | 462 expected_properties_(0), |
452 with_nesting_count_(0), | 463 with_nesting_count_(0), |
453 language_mode_( | 464 language_mode_( |
454 (prev_ != NULL) ? prev_->language_mode() : i::CLASSIC_MODE) { | 465 (prev_ != NULL) ? prev_->language_mode() : i::CLASSIC_MODE), |
| 466 is_generator_(false) { |
455 *variable = this; | 467 *variable = this; |
456 } | 468 } |
457 ~Scope() { *variable_ = prev_; } | 469 ~Scope() { *variable_ = prev_; } |
458 void NextMaterializedLiteralIndex() { materialized_literal_count_++; } | 470 void NextMaterializedLiteralIndex() { materialized_literal_count_++; } |
459 void AddProperty() { expected_properties_++; } | 471 void AddProperty() { expected_properties_++; } |
460 ScopeType type() { return type_; } | 472 ScopeType type() { return type_; } |
461 int expected_properties() { return expected_properties_; } | 473 int expected_properties() { return expected_properties_; } |
462 int materialized_literal_count() { return materialized_literal_count_; } | 474 int materialized_literal_count() { return materialized_literal_count_; } |
463 bool IsInsideWith() { return with_nesting_count_ != 0; } | 475 bool IsInsideWith() { return with_nesting_count_ != 0; } |
| 476 bool is_generator() { return is_generator_; } |
| 477 void set_is_generator(bool is_generator) { is_generator_ = is_generator; } |
464 bool is_classic_mode() { | 478 bool is_classic_mode() { |
465 return language_mode_ == i::CLASSIC_MODE; | 479 return language_mode_ == i::CLASSIC_MODE; |
466 } | 480 } |
467 i::LanguageMode language_mode() { | 481 i::LanguageMode language_mode() { |
468 return language_mode_; | 482 return language_mode_; |
469 } | 483 } |
470 void set_language_mode(i::LanguageMode language_mode) { | 484 void set_language_mode(i::LanguageMode language_mode) { |
471 language_mode_ = language_mode; | 485 language_mode_ = language_mode; |
472 } | 486 } |
473 | 487 |
(...skipping 11 matching lines...) Expand all Loading... |
485 }; | 499 }; |
486 | 500 |
487 private: | 501 private: |
488 Scope** const variable_; | 502 Scope** const variable_; |
489 Scope* const prev_; | 503 Scope* const prev_; |
490 const ScopeType type_; | 504 const ScopeType type_; |
491 int materialized_literal_count_; | 505 int materialized_literal_count_; |
492 int expected_properties_; | 506 int expected_properties_; |
493 int with_nesting_count_; | 507 int with_nesting_count_; |
494 i::LanguageMode language_mode_; | 508 i::LanguageMode language_mode_; |
| 509 bool is_generator_; |
495 }; | 510 }; |
496 | 511 |
497 // Preparse the program. Only called in PreParseProgram after creating | 512 // Preparse the program. Only called in PreParseProgram after creating |
498 // the instance. | 513 // the instance. |
499 PreParseResult PreParse() { | 514 PreParseResult PreParse() { |
500 Scope top_scope(&scope_, kTopLevelScope); | 515 Scope top_scope(&scope_, kTopLevelScope); |
501 bool ok = true; | 516 bool ok = true; |
502 int start_position = scanner_->peek_location().beg_pos; | 517 int start_position = scanner_->peek_location().beg_pos; |
503 ParseSourceElements(i::Token::EOS, &ok); | 518 ParseSourceElements(i::Token::EOS, &ok); |
504 if (stack_overflow_) return kPreParseStackOverflow; | 519 if (stack_overflow_) return kPreParseStackOverflow; |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
550 Statement ParseSwitchStatement(bool* ok); | 565 Statement ParseSwitchStatement(bool* ok); |
551 Statement ParseDoWhileStatement(bool* ok); | 566 Statement ParseDoWhileStatement(bool* ok); |
552 Statement ParseWhileStatement(bool* ok); | 567 Statement ParseWhileStatement(bool* ok); |
553 Statement ParseForStatement(bool* ok); | 568 Statement ParseForStatement(bool* ok); |
554 Statement ParseThrowStatement(bool* ok); | 569 Statement ParseThrowStatement(bool* ok); |
555 Statement ParseTryStatement(bool* ok); | 570 Statement ParseTryStatement(bool* ok); |
556 Statement ParseDebuggerStatement(bool* ok); | 571 Statement ParseDebuggerStatement(bool* ok); |
557 | 572 |
558 Expression ParseExpression(bool accept_IN, bool* ok); | 573 Expression ParseExpression(bool accept_IN, bool* ok); |
559 Expression ParseAssignmentExpression(bool accept_IN, bool* ok); | 574 Expression ParseAssignmentExpression(bool accept_IN, bool* ok); |
| 575 Expression ParseYieldExpression(bool* ok); |
560 Expression ParseConditionalExpression(bool accept_IN, bool* ok); | 576 Expression ParseConditionalExpression(bool accept_IN, bool* ok); |
561 Expression ParseBinaryExpression(int prec, bool accept_IN, bool* ok); | 577 Expression ParseBinaryExpression(int prec, bool accept_IN, bool* ok); |
562 Expression ParseUnaryExpression(bool* ok); | 578 Expression ParseUnaryExpression(bool* ok); |
563 Expression ParsePostfixExpression(bool* ok); | 579 Expression ParsePostfixExpression(bool* ok); |
564 Expression ParseLeftHandSideExpression(bool* ok); | 580 Expression ParseLeftHandSideExpression(bool* ok); |
565 Expression ParseNewExpression(bool* ok); | 581 Expression ParseNewExpression(bool* ok); |
566 Expression ParseMemberExpression(bool* ok); | 582 Expression ParseMemberExpression(bool* ok); |
567 Expression ParseMemberWithNewPrefixesExpression(unsigned new_count, bool* ok); | 583 Expression ParseMemberWithNewPrefixesExpression(unsigned new_count, bool* ok); |
568 Expression ParsePrimaryExpression(bool* ok); | 584 Expression ParsePrimaryExpression(bool* ok); |
569 Expression ParseArrayLiteral(bool* ok); | 585 Expression ParseArrayLiteral(bool* ok); |
570 Expression ParseObjectLiteral(bool* ok); | 586 Expression ParseObjectLiteral(bool* ok); |
571 Expression ParseRegExpLiteral(bool seen_equal, bool* ok); | 587 Expression ParseRegExpLiteral(bool seen_equal, bool* ok); |
572 Expression ParseV8Intrinsic(bool* ok); | 588 Expression ParseV8Intrinsic(bool* ok); |
573 | 589 |
574 Arguments ParseArguments(bool* ok); | 590 Arguments ParseArguments(bool* ok); |
575 Expression ParseFunctionLiteral(bool* ok); | 591 Expression ParseFunctionLiteral(bool is_generator, bool* ok); |
576 void ParseLazyFunctionLiteralBody(bool* ok); | 592 void ParseLazyFunctionLiteralBody(bool* ok); |
577 | 593 |
578 Identifier ParseIdentifier(bool* ok); | 594 Identifier ParseIdentifier(bool* ok); |
579 Identifier ParseIdentifierName(bool* ok); | 595 Identifier ParseIdentifierName(bool* ok); |
580 Identifier ParseIdentifierNameOrGetOrSet(bool* is_get, | 596 Identifier ParseIdentifierNameOrGetOrSet(bool* is_get, |
581 bool* is_set, | 597 bool* is_set, |
582 bool* ok); | 598 bool* ok); |
583 | 599 |
584 // Logs the currently parsed literal as a symbol in the preparser data. | 600 // Logs the currently parsed literal as a symbol in the preparser data. |
585 void LogSymbol(); | 601 void LogSymbol(); |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
657 i::Scanner* scanner_; | 673 i::Scanner* scanner_; |
658 i::ParserRecorder* log_; | 674 i::ParserRecorder* log_; |
659 Scope* scope_; | 675 Scope* scope_; |
660 uintptr_t stack_limit_; | 676 uintptr_t stack_limit_; |
661 i::Scanner::Location strict_mode_violation_location_; | 677 i::Scanner::Location strict_mode_violation_location_; |
662 const char* strict_mode_violation_type_; | 678 const char* strict_mode_violation_type_; |
663 bool stack_overflow_; | 679 bool stack_overflow_; |
664 bool allow_lazy_; | 680 bool allow_lazy_; |
665 bool allow_modules_; | 681 bool allow_modules_; |
666 bool allow_natives_syntax_; | 682 bool allow_natives_syntax_; |
| 683 bool allow_generators_; |
667 bool parenthesized_function_; | 684 bool parenthesized_function_; |
668 bool harmony_scoping_; | 685 bool harmony_scoping_; |
669 }; | 686 }; |
670 } } // v8::preparser | 687 } } // v8::preparser |
671 | 688 |
672 #endif // V8_PREPARSER_H | 689 #endif // V8_PREPARSER_H |
OLD | NEW |