Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(122)

Side by Side Diff: src/preparser.h

Issue 915563003: super is only allowed in methods, accessors and constructor (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Use i:: to qualify function name Created 5 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | test/cctest/test-parsing.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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_PREPARSER_H 5 #ifndef V8_PREPARSER_H
6 #define V8_PREPARSER_H 6 #define V8_PREPARSER_H
7 7
8 #include "src/v8.h" 8 #include "src/v8.h"
9 9
10 #include "src/bailout-reason.h" 10 #include "src/bailout-reason.h"
(...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after
210 210
211 int NextHandlerIndex() { return next_handler_index_++; } 211 int NextHandlerIndex() { return next_handler_index_++; }
212 int handler_count() { return next_handler_index_; } 212 int handler_count() { return next_handler_index_; }
213 213
214 void AddProperty() { expected_property_count_++; } 214 void AddProperty() { expected_property_count_++; }
215 int expected_property_count() { return expected_property_count_; } 215 int expected_property_count() { return expected_property_count_; }
216 216
217 bool is_generator() const { return IsGeneratorFunction(kind_); } 217 bool is_generator() const { return IsGeneratorFunction(kind_); }
218 218
219 FunctionKind kind() const { return kind_; } 219 FunctionKind kind() const { return kind_; }
220 FunctionState* outer() const { return outer_function_state_; }
220 221
221 void set_generator_object_variable( 222 void set_generator_object_variable(
222 typename Traits::Type::GeneratorVariable* variable) { 223 typename Traits::Type::GeneratorVariable* variable) {
223 DCHECK(variable != NULL); 224 DCHECK(variable != NULL);
224 DCHECK(is_generator()); 225 DCHECK(is_generator());
225 generator_object_variable_ = variable; 226 generator_object_variable_ = variable;
226 } 227 }
227 typename Traits::Type::GeneratorVariable* generator_object_variable() 228 typename Traits::Type::GeneratorVariable* generator_object_variable()
228 const { 229 const {
229 return generator_object_variable_; 230 return generator_object_variable_;
(...skipping 12 matching lines...) Expand all
242 243
243 // Properties count estimation. 244 // Properties count estimation.
244 int expected_property_count_; 245 int expected_property_count_;
245 246
246 FunctionKind kind_; 247 FunctionKind kind_;
247 // For generators, this variable may hold the generator object. It variable 248 // For generators, this variable may hold the generator object. It variable
248 // is used by yield expressions and return statements. It is not necessary 249 // is used by yield expressions and return statements. It is not necessary
249 // for generator functions to have this variable set. 250 // for generator functions to have this variable set.
250 Variable* generator_object_variable_; 251 Variable* generator_object_variable_;
251 252
252
253 FunctionState** function_state_stack_; 253 FunctionState** function_state_stack_;
254 FunctionState* outer_function_state_; 254 FunctionState* outer_function_state_;
255 Scope** scope_stack_; 255 Scope** scope_stack_;
256 Scope* outer_scope_; 256 Scope* outer_scope_;
257 typename Traits::Type::Factory* factory_; 257 typename Traits::Type::Factory* factory_;
258 258
259 friend class ParserTraits; 259 friend class ParserTraits;
260 friend class Checkpoint; 260 friend class Checkpoint;
261 }; 261 };
262 262
(...skipping 299 matching lines...) Expand 10 before | Expand all | Expand 10 after
562 ExpressionT ParsePostfixExpression(bool* ok); 562 ExpressionT ParsePostfixExpression(bool* ok);
563 ExpressionT ParseLeftHandSideExpression(bool* ok); 563 ExpressionT ParseLeftHandSideExpression(bool* ok);
564 ExpressionT ParseMemberWithNewPrefixesExpression(bool* ok); 564 ExpressionT ParseMemberWithNewPrefixesExpression(bool* ok);
565 ExpressionT ParseMemberExpression(bool* ok); 565 ExpressionT ParseMemberExpression(bool* ok);
566 ExpressionT ParseMemberExpressionContinuation(ExpressionT expression, 566 ExpressionT ParseMemberExpressionContinuation(ExpressionT expression,
567 bool* ok); 567 bool* ok);
568 ExpressionT ParseArrowFunctionLiteral(int start_pos, ExpressionT params_ast, 568 ExpressionT ParseArrowFunctionLiteral(int start_pos, ExpressionT params_ast,
569 bool* ok); 569 bool* ok);
570 ExpressionT ParseTemplateLiteral(ExpressionT tag, int start, bool* ok); 570 ExpressionT ParseTemplateLiteral(ExpressionT tag, int start, bool* ok);
571 void AddTemplateExpression(ExpressionT); 571 void AddTemplateExpression(ExpressionT);
572 ExpressionT ParseSuperExpression(bool is_new, bool* ok);
572 573
573 // Checks if the expression is a valid reference expression (e.g., on the 574 // Checks if the expression is a valid reference expression (e.g., on the
574 // left-hand side of assignments). Although ruled out by ECMA as early errors, 575 // left-hand side of assignments). Although ruled out by ECMA as early errors,
575 // we allow calls for web compatibility and rewrite them to a runtime throw. 576 // we allow calls for web compatibility and rewrite them to a runtime throw.
576 ExpressionT CheckAndRewriteReferenceExpression( 577 ExpressionT CheckAndRewriteReferenceExpression(
577 ExpressionT expression, 578 ExpressionT expression,
578 Scanner::Location location, const char* message, bool* ok); 579 Scanner::Location location, const char* message, bool* ok);
579 580
580 // Used to validate property names in object literals and class literals 581 // Used to validate property names in object literals and class literals
581 enum PropertyKind { 582 enum PropertyKind {
(...skipping 2077 matching lines...) Expand 10 before | Expand all | Expand 10 after
2659 // new foo()() means (new foo())() 2660 // new foo()() means (new foo())()
2660 // new new foo()() means (new (new foo())()) 2661 // new new foo()() means (new (new foo())())
2661 // new new foo means new (new foo) 2662 // new new foo means new (new foo)
2662 // new new foo() means new (new foo()) 2663 // new new foo() means new (new foo())
2663 // new new foo().bar().baz means (new (new foo()).bar()).baz 2664 // new new foo().bar().baz means (new (new foo()).bar()).baz
2664 2665
2665 if (peek() == Token::NEW) { 2666 if (peek() == Token::NEW) {
2666 Consume(Token::NEW); 2667 Consume(Token::NEW);
2667 int new_pos = position(); 2668 int new_pos = position();
2668 ExpressionT result = this->EmptyExpression(); 2669 ExpressionT result = this->EmptyExpression();
2669 if (Check(Token::SUPER)) { 2670 if (peek() == Token::SUPER) {
2670 result = this->SuperReference(scope_, factory()); 2671 const bool is_new = true;
2672 result = ParseSuperExpression(is_new, CHECK_OK);
2671 } else { 2673 } else {
2672 result = this->ParseMemberWithNewPrefixesExpression(CHECK_OK); 2674 result = this->ParseMemberWithNewPrefixesExpression(CHECK_OK);
2673 } 2675 }
2674 if (peek() == Token::LPAREN) { 2676 if (peek() == Token::LPAREN) {
2675 // NewExpression with arguments. 2677 // NewExpression with arguments.
2676 typename Traits::Type::ExpressionList args = 2678 typename Traits::Type::ExpressionList args =
2677 this->ParseArguments(CHECK_OK); 2679 this->ParseArguments(CHECK_OK);
2678 result = factory()->NewCallNew(result, args, new_pos); 2680 result = factory()->NewCallNew(result, args, new_pos);
2679 // The expression can still continue with . or [ after the arguments. 2681 // The expression can still continue with . or [ after the arguments.
2680 result = this->ParseMemberExpressionContinuation(result, CHECK_OK); 2682 result = this->ParseMemberExpressionContinuation(result, CHECK_OK);
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
2717 function_name_location = scanner()->location(); 2719 function_name_location = scanner()->location();
2718 function_type = FunctionLiteral::NAMED_EXPRESSION; 2720 function_type = FunctionLiteral::NAMED_EXPRESSION;
2719 } 2721 }
2720 result = this->ParseFunctionLiteral( 2722 result = this->ParseFunctionLiteral(
2721 name, function_name_location, is_strict_reserved_name, 2723 name, function_name_location, is_strict_reserved_name,
2722 is_generator ? FunctionKind::kGeneratorFunction 2724 is_generator ? FunctionKind::kGeneratorFunction
2723 : FunctionKind::kNormalFunction, 2725 : FunctionKind::kNormalFunction,
2724 function_token_position, function_type, FunctionLiteral::NORMAL_ARITY, 2726 function_token_position, function_type, FunctionLiteral::NORMAL_ARITY,
2725 CHECK_OK); 2727 CHECK_OK);
2726 } else if (peek() == Token::SUPER) { 2728 } else if (peek() == Token::SUPER) {
2727 int beg_pos = position(); 2729 const bool is_new = false;
2728 Consume(Token::SUPER); 2730 result = ParseSuperExpression(is_new, CHECK_OK);
2729 Token::Value next = peek();
2730 if (next == Token::PERIOD || next == Token::LBRACK) {
2731 scope_->RecordSuperPropertyUsage();
2732 result = this->SuperReference(scope_, factory());
2733 } else if (next == Token::LPAREN) {
2734 scope_->RecordSuperConstructorCallUsage();
2735 result = this->SuperReference(scope_, factory());
2736 } else {
2737 ReportMessageAt(Scanner::Location(beg_pos, position()),
2738 "unexpected_super");
2739 *ok = false;
2740 return this->EmptyExpression();
2741 }
2742 } else { 2731 } else {
2743 result = ParsePrimaryExpression(CHECK_OK); 2732 result = ParsePrimaryExpression(CHECK_OK);
2744 } 2733 }
2745 2734
2746 result = ParseMemberExpressionContinuation(result, CHECK_OK); 2735 result = ParseMemberExpressionContinuation(result, CHECK_OK);
2747 return result; 2736 return result;
2748 } 2737 }
2749 2738
2750 2739
2751 template <class Traits> 2740 template <class Traits>
2752 typename ParserBase<Traits>::ExpressionT 2741 typename ParserBase<Traits>::ExpressionT
2742 ParserBase<Traits>::ParseSuperExpression(bool is_new, bool* ok) {
2743 int beg_pos = position();
2744 Expect(Token::SUPER, CHECK_OK);
2745
2746 FunctionState* function_state = function_state_;
2747 while (IsArrowFunction(function_state->kind())) {
2748 function_state = function_state->outer();
2749 }
2750 // TODO(arv): Handle eval scopes similarly.
2751
2752 FunctionKind kind = function_state->kind();
2753 if (IsConciseMethod(kind) || IsAccessorFunction(kind) ||
2754 i::IsConstructor(kind)) {
2755 if (peek() == Token::PERIOD || peek() == Token::LBRACK) {
2756 scope_->RecordSuperPropertyUsage();
2757 return this->SuperReference(scope_, factory());
2758 }
2759 // new super() is never allowed.
2760 // super() is only allowed in constructor
2761 if (!is_new && peek() == Token::LPAREN && i::IsConstructor(kind)) {
2762 scope_->RecordSuperConstructorCallUsage();
2763 return this->SuperReference(scope_, factory());
2764 }
2765 }
2766
2767 ReportMessageAt(Scanner::Location(beg_pos, position()), "unexpected_super");
2768 *ok = false;
2769 return this->EmptyExpression();
2770 }
2771
2772
2773 template <class Traits>
2774 typename ParserBase<Traits>::ExpressionT
2753 ParserBase<Traits>::ParseMemberExpressionContinuation(ExpressionT expression, 2775 ParserBase<Traits>::ParseMemberExpressionContinuation(ExpressionT expression,
2754 bool* ok) { 2776 bool* ok) {
2755 // Parses this part of MemberExpression: 2777 // Parses this part of MemberExpression:
2756 // ('[' Expression ']' | '.' Identifier)* 2778 // ('[' Expression ']' | '.' Identifier)*
2757 while (true) { 2779 while (true) {
2758 switch (peek()) { 2780 switch (peek()) {
2759 case Token::LBRACK: { 2781 case Token::LBRACK: {
2760 Consume(Token::LBRACK); 2782 Consume(Token::LBRACK);
2761 int pos = position(); 2783 int pos = position();
2762 ExpressionT index = this->ParseExpression(true, CHECK_OK); 2784 ExpressionT index = this->ParseExpression(true, CHECK_OK);
(...skipping 297 matching lines...) Expand 10 before | Expand all | Expand 10 after
3060 *ok = false; 3082 *ok = false;
3061 return; 3083 return;
3062 } 3084 }
3063 has_seen_constructor_ = true; 3085 has_seen_constructor_ = true;
3064 return; 3086 return;
3065 } 3087 }
3066 } 3088 }
3067 } } // v8::internal 3089 } } // v8::internal
3068 3090
3069 #endif // V8_PREPARSER_H 3091 #endif // V8_PREPARSER_H
OLDNEW
« no previous file with comments | « no previous file | test/cctest/test-parsing.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698