OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef V8_PARSING_PARSER_BASE_H | 5 #ifndef V8_PARSING_PARSER_BASE_H |
6 #define V8_PARSING_PARSER_BASE_H | 6 #define V8_PARSING_PARSER_BASE_H |
7 | 7 |
8 #include "src/ast/ast.h" | 8 #include "src/ast/ast.h" |
9 #include "src/ast/scopes.h" | 9 #include "src/ast/scopes.h" |
10 #include "src/bailout-reason.h" | 10 #include "src/bailout-reason.h" |
(...skipping 2562 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2573 Scanner::Location* first_spread_arg_loc, bool maybe_arrow, bool* ok) { | 2573 Scanner::Location* first_spread_arg_loc, bool maybe_arrow, bool* ok) { |
2574 // Arguments :: | 2574 // Arguments :: |
2575 // '(' (AssignmentExpression)*[','] ')' | 2575 // '(' (AssignmentExpression)*[','] ')' |
2576 | 2576 |
2577 Scanner::Location spread_arg = Scanner::Location::invalid(); | 2577 Scanner::Location spread_arg = Scanner::Location::invalid(); |
2578 ExpressionListT result = impl()->NewExpressionList(4); | 2578 ExpressionListT result = impl()->NewExpressionList(4); |
2579 Expect(Token::LPAREN, CHECK_OK_CUSTOM(NullExpressionList)); | 2579 Expect(Token::LPAREN, CHECK_OK_CUSTOM(NullExpressionList)); |
2580 bool done = (peek() == Token::RPAREN); | 2580 bool done = (peek() == Token::RPAREN); |
2581 bool was_unspread = false; | 2581 bool was_unspread = false; |
2582 int unspread_sequences_count = 0; | 2582 int unspread_sequences_count = 0; |
| 2583 int spread_count = 0; |
2583 while (!done) { | 2584 while (!done) { |
2584 int start_pos = peek_position(); | 2585 int start_pos = peek_position(); |
2585 bool is_spread = Check(Token::ELLIPSIS); | 2586 bool is_spread = Check(Token::ELLIPSIS); |
2586 int expr_pos = peek_position(); | 2587 int expr_pos = peek_position(); |
2587 | 2588 |
2588 ExpressionT argument = | 2589 ExpressionT argument = |
2589 ParseAssignmentExpression(true, CHECK_OK_CUSTOM(NullExpressionList)); | 2590 ParseAssignmentExpression(true, CHECK_OK_CUSTOM(NullExpressionList)); |
2590 if (!maybe_arrow) { | 2591 if (!maybe_arrow) { |
2591 impl()->RewriteNonPattern(CHECK_OK_CUSTOM(NullExpressionList)); | 2592 impl()->RewriteNonPattern(CHECK_OK_CUSTOM(NullExpressionList)); |
2592 } | 2593 } |
2593 if (is_spread) { | 2594 if (is_spread) { |
2594 if (!spread_arg.IsValid()) { | 2595 if (!spread_arg.IsValid()) { |
2595 spread_arg.beg_pos = start_pos; | 2596 spread_arg.beg_pos = start_pos; |
2596 spread_arg.end_pos = peek_position(); | 2597 spread_arg.end_pos = peek_position(); |
2597 } | 2598 } |
2598 argument = factory()->NewSpread(argument, start_pos, expr_pos); | 2599 argument = factory()->NewSpread(argument, start_pos, expr_pos); |
2599 } | 2600 } |
2600 result->Add(argument, zone_); | 2601 result->Add(argument, zone_); |
2601 | 2602 |
2602 // unspread_sequences_count is the number of sequences of parameters which | 2603 // unspread_sequences_count is the number of sequences of parameters which |
2603 // are not prefixed with a spread '...' operator. | 2604 // are not prefixed with a spread '...' operator. |
2604 if (is_spread) { | 2605 if (is_spread) { |
2605 was_unspread = false; | 2606 was_unspread = false; |
| 2607 spread_count++; |
2606 } else if (!was_unspread) { | 2608 } else if (!was_unspread) { |
2607 was_unspread = true; | 2609 was_unspread = true; |
2608 unspread_sequences_count++; | 2610 unspread_sequences_count++; |
2609 } | 2611 } |
2610 | 2612 |
2611 if (result->length() > Code::kMaxArguments) { | 2613 if (result->length() > Code::kMaxArguments) { |
2612 ReportMessage(MessageTemplate::kTooManyArguments); | 2614 ReportMessage(MessageTemplate::kTooManyArguments); |
2613 *ok = false; | 2615 *ok = false; |
2614 return impl()->NullExpressionList(); | 2616 return impl()->NullExpressionList(); |
2615 } | 2617 } |
(...skipping 15 matching lines...) Expand all Loading... |
2631 *first_spread_arg_loc = spread_arg; | 2633 *first_spread_arg_loc = spread_arg; |
2632 | 2634 |
2633 if (!maybe_arrow || peek() != Token::ARROW) { | 2635 if (!maybe_arrow || peek() != Token::ARROW) { |
2634 if (maybe_arrow) { | 2636 if (maybe_arrow) { |
2635 impl()->RewriteNonPattern(CHECK_OK_CUSTOM(NullExpressionList)); | 2637 impl()->RewriteNonPattern(CHECK_OK_CUSTOM(NullExpressionList)); |
2636 } | 2638 } |
2637 if (spread_arg.IsValid()) { | 2639 if (spread_arg.IsValid()) { |
2638 // Unspread parameter sequences are translated into array literals in the | 2640 // Unspread parameter sequences are translated into array literals in the |
2639 // parser. Ensure that the number of materialized literals matches between | 2641 // parser. Ensure that the number of materialized literals matches between |
2640 // the parser and preparser | 2642 // the parser and preparser |
2641 impl()->MaterializeUnspreadArgumentsLiterals(unspread_sequences_count); | 2643 if (was_unspread || spread_count > 1) { |
| 2644 // There was more than one spread, or the spread was not the final |
| 2645 // argument, so the parser will materialize literals. |
| 2646 impl()->MaterializeUnspreadArgumentsLiterals(unspread_sequences_count); |
| 2647 } |
2642 } | 2648 } |
2643 } | 2649 } |
2644 | 2650 |
2645 return result; | 2651 return result; |
2646 } | 2652 } |
2647 | 2653 |
2648 // Precedence = 2 | 2654 // Precedence = 2 |
2649 template <typename Impl> | 2655 template <typename Impl> |
2650 typename ParserBase<Impl>::ExpressionT | 2656 typename ParserBase<Impl>::ExpressionT |
2651 ParserBase<Impl>::ParseAssignmentExpression(bool accept_IN, bool* ok) { | 2657 ParserBase<Impl>::ParseAssignmentExpression(bool accept_IN, bool* ok) { |
(...skipping 521 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3173 // The calls that need special treatment are the | 3179 // The calls that need special treatment are the |
3174 // direct eval calls. These calls are all of the form eval(...), with | 3180 // direct eval calls. These calls are all of the form eval(...), with |
3175 // no explicit receiver. | 3181 // no explicit receiver. |
3176 // These calls are marked as potentially direct eval calls. Whether | 3182 // These calls are marked as potentially direct eval calls. Whether |
3177 // they are actually direct calls to eval is determined at run time. | 3183 // they are actually direct calls to eval is determined at run time. |
3178 Call::PossiblyEval is_possibly_eval = | 3184 Call::PossiblyEval is_possibly_eval = |
3179 CheckPossibleEvalCall(result, scope()); | 3185 CheckPossibleEvalCall(result, scope()); |
3180 | 3186 |
3181 bool is_super_call = result->IsSuperCallReference(); | 3187 bool is_super_call = result->IsSuperCallReference(); |
3182 if (spread_pos.IsValid()) { | 3188 if (spread_pos.IsValid()) { |
3183 result = impl()->SpreadCall(result, args, pos); | 3189 result = impl()->SpreadCall(result, args, pos, is_possibly_eval); |
3184 } else { | 3190 } else { |
3185 result = factory()->NewCall(result, args, pos, is_possibly_eval); | 3191 result = factory()->NewCall(result, args, pos, is_possibly_eval); |
3186 } | 3192 } |
3187 | 3193 |
3188 // Explicit calls to the super constructor using super() perform an | 3194 // Explicit calls to the super constructor using super() perform an |
3189 // implicit binding assignment to the 'this' variable. | 3195 // implicit binding assignment to the 'this' variable. |
3190 if (is_super_call) { | 3196 if (is_super_call) { |
3191 ExpressionT this_expr = impl()->ThisExpression(pos); | 3197 ExpressionT this_expr = impl()->ThisExpression(pos); |
3192 result = | 3198 result = |
3193 factory()->NewAssignment(Token::INIT, this_expr, result, pos); | 3199 factory()->NewAssignment(Token::INIT, this_expr, result, pos); |
(...skipping 2335 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5529 has_seen_constructor_ = true; | 5535 has_seen_constructor_ = true; |
5530 return; | 5536 return; |
5531 } | 5537 } |
5532 } | 5538 } |
5533 | 5539 |
5534 | 5540 |
5535 } // namespace internal | 5541 } // namespace internal |
5536 } // namespace v8 | 5542 } // namespace v8 |
5537 | 5543 |
5538 #endif // V8_PARSING_PARSER_BASE_H | 5544 #endif // V8_PARSING_PARSER_BASE_H |
OLD | NEW |