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 #include "src/v8.h" | 5 #include "src/v8.h" |
6 | 6 |
7 #include "src/api.h" | 7 #include "src/api.h" |
8 #include "src/ast.h" | 8 #include "src/ast.h" |
9 #include "src/bailout-reason.h" | 9 #include "src/bailout-reason.h" |
10 #include "src/base/platform/platform.h" | 10 #include "src/base/platform/platform.h" |
(...skipping 1127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1138 if (ok) ok = Check(Token::RPAREN); | 1138 if (ok) ok = Check(Token::RPAREN); |
1139 } else { | 1139 } else { |
1140 // BindingIdentifier | 1140 // BindingIdentifier |
1141 ParseFormalParameter(scope, &error_locs, has_rest, &ok); | 1141 ParseFormalParameter(scope, &error_locs, has_rest, &ok); |
1142 } | 1142 } |
1143 | 1143 |
1144 if (ok) { | 1144 if (ok) { |
1145 ExpressionClassifier classifier; | 1145 ExpressionClassifier classifier; |
1146 Expression* expression = ParseArrowFunctionLiteral( | 1146 Expression* expression = ParseArrowFunctionLiteral( |
1147 scope, error_locs, has_rest, &classifier, &ok); | 1147 scope, error_locs, has_rest, &classifier, &ok); |
1148 // TODO(dslomov): report error if not a valid expression. | 1148 ValidateExpression(&classifier, &ok); |
1149 if (ok) { | 1149 if (ok) { |
1150 // Scanning must end at the same position that was recorded | 1150 // Scanning must end at the same position that was recorded |
1151 // previously. If not, parsing has been interrupted due to a stack | 1151 // previously. If not, parsing has been interrupted due to a stack |
1152 // overflow, at which point the partially parsed arrow function | 1152 // overflow, at which point the partially parsed arrow function |
1153 // concise body happens to be a valid expression. This is a problem | 1153 // concise body happens to be a valid expression. This is a problem |
1154 // only for arrow functions with single expression bodies, since there | 1154 // only for arrow functions with single expression bodies, since there |
1155 // is no end token such as "}" for normal functions. | 1155 // is no end token such as "}" for normal functions. |
1156 if (scanner()->location().end_pos == shared_info->end_position()) { | 1156 if (scanner()->location().end_pos == shared_info->end_position()) { |
1157 // The pre-parser saw an arrow function here, so the full parser | 1157 // The pre-parser saw an arrow function here, so the full parser |
1158 // must produce a FunctionLiteral. | 1158 // must produce a FunctionLiteral. |
(...skipping 441 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1600 | 1600 |
1601 case Token::CLASS: | 1601 case Token::CLASS: |
1602 // TODO(ES6): Support parsing anonymous class declarations here. | 1602 // TODO(ES6): Support parsing anonymous class declarations here. |
1603 result = ParseClassDeclaration(&names, CHECK_OK); | 1603 result = ParseClassDeclaration(&names, CHECK_OK); |
1604 break; | 1604 break; |
1605 | 1605 |
1606 default: { | 1606 default: { |
1607 int pos = peek_position(); | 1607 int pos = peek_position(); |
1608 ExpressionClassifier classifier; | 1608 ExpressionClassifier classifier; |
1609 Expression* expr = ParseAssignmentExpression(true, &classifier, CHECK_OK); | 1609 Expression* expr = ParseAssignmentExpression(true, &classifier, CHECK_OK); |
1610 // TODO(dslomov): report error if not a valid expression. | 1610 ValidateExpression(&classifier, CHECK_OK); |
1611 | 1611 |
1612 ExpectSemicolon(CHECK_OK); | 1612 ExpectSemicolon(CHECK_OK); |
1613 result = factory()->NewExpressionStatement(expr, pos); | 1613 result = factory()->NewExpressionStatement(expr, pos); |
1614 break; | 1614 break; |
1615 } | 1615 } |
1616 } | 1616 } |
1617 | 1617 |
1618 const AstRawString* default_string = ast_value_factory()->default_string(); | 1618 const AstRawString* default_string = ast_value_factory()->default_string(); |
1619 | 1619 |
1620 DCHECK_LE(names.length(), 1); | 1620 DCHECK_LE(names.length(), 1); |
(...skipping 735 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2356 int nvars = 0; // the number of variables declared | 2356 int nvars = 0; // the number of variables declared |
2357 int bindings_start = peek_position(); | 2357 int bindings_start = peek_position(); |
2358 const AstRawString* name = NULL; | 2358 const AstRawString* name = NULL; |
2359 const AstRawString* first_name = NULL; | 2359 const AstRawString* first_name = NULL; |
2360 bool is_for_iteration_variable; | 2360 bool is_for_iteration_variable; |
2361 do { | 2361 do { |
2362 if (fni_ != NULL) fni_->Enter(); | 2362 if (fni_ != NULL) fni_->Enter(); |
2363 | 2363 |
2364 // Parse variable name. | 2364 // Parse variable name. |
2365 if (nvars > 0) Consume(Token::COMMA); | 2365 if (nvars > 0) Consume(Token::COMMA); |
2366 name = ParseIdentifier(kDontAllowRestrictedIdentifiers, CHECK_OK); | 2366 |
2367 { | |
2368 ExpressionClassifier pattern_classifier; | |
2369 Token::Value next = peek(); | |
2370 Expression* pattern = | |
2371 ParsePrimaryExpression(&pattern_classifier, CHECK_OK); | |
2372 ValidateBindingPattern(&pattern_classifier, CHECK_OK); | |
2373 if (pattern->IsVariableProxy() && | |
2374 pattern->AsVariableProxy()->IsValidReferenceExpression()) { | |
2375 scope_->RemoveUnresolved(pattern->AsVariableProxy()); | |
Dmitry Lomov (no reviews)
2015/04/23 16:29:24
Here, instead of adding an unresolved proxy and th
arv (Not doing code reviews)
2015/04/23 16:52:52
I like this better. I doubt it matters for perform
| |
2376 name = pattern->AsVariableProxy()->raw_name(); | |
2377 } else { | |
2378 ReportUnexpectedToken(next); | |
2379 *ok = false; | |
2380 return nullptr; | |
2381 } | |
2382 } | |
2383 | |
2367 if (!first_name) first_name = name; | 2384 if (!first_name) first_name = name; |
2368 Scanner::Location variable_loc = scanner()->location(); | 2385 Scanner::Location variable_loc = scanner()->location(); |
2369 if (fni_ != NULL) fni_->PushVariableName(name); | 2386 if (fni_ != NULL) fni_->PushVariableName(name); |
2370 | 2387 |
2371 // Declare variable. | 2388 // Declare variable. |
2372 // Note that we *always* must treat the initial value via a separate init | 2389 // Note that we *always* must treat the initial value via a separate init |
2373 // assignment for variables and constants because the value must be assigned | 2390 // assignment for variables and constants because the value must be assigned |
2374 // when the variable is encountered in the source. But the variable/constant | 2391 // when the variable is encountered in the source. But the variable/constant |
2375 // is declared (and set to 'undefined') upon entering the function within | 2392 // is declared (and set to 'undefined') upon entering the function within |
2376 // which the variable or constant is declared. Only function variables have | 2393 // which the variable or constant is declared. Only function variables have |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2435 Expression* value = NULL; | 2452 Expression* value = NULL; |
2436 int pos = -1; | 2453 int pos = -1; |
2437 // Harmony consts have non-optional initializers. | 2454 // Harmony consts have non-optional initializers. |
2438 if (peek() == Token::ASSIGN || | 2455 if (peek() == Token::ASSIGN || |
2439 (mode == CONST && !is_for_iteration_variable)) { | 2456 (mode == CONST && !is_for_iteration_variable)) { |
2440 Expect(Token::ASSIGN, CHECK_OK); | 2457 Expect(Token::ASSIGN, CHECK_OK); |
2441 pos = position(); | 2458 pos = position(); |
2442 ExpressionClassifier classifier; | 2459 ExpressionClassifier classifier; |
2443 value = ParseAssignmentExpression(var_context != kForStatement, | 2460 value = ParseAssignmentExpression(var_context != kForStatement, |
2444 &classifier, CHECK_OK); | 2461 &classifier, CHECK_OK); |
2445 // TODO(dslomov): check that expression is valid. | 2462 ValidateExpression(&classifier, CHECK_OK); |
2446 variable_loc.end_pos = scanner()->location().end_pos; | 2463 variable_loc.end_pos = scanner()->location().end_pos; |
2447 | 2464 |
2448 if (first_initializer_loc && !first_initializer_loc->IsValid()) { | 2465 if (first_initializer_loc && !first_initializer_loc->IsValid()) { |
2449 *first_initializer_loc = variable_loc; | 2466 *first_initializer_loc = variable_loc; |
2450 } | 2467 } |
2451 | 2468 |
2452 // Don't infer if it is "a = function(){...}();"-like expression. | 2469 // Don't infer if it is "a = function(){...}();"-like expression. |
2453 if (fni_ != NULL && | 2470 if (fni_ != NULL && |
2454 value->AsCall() == NULL && | 2471 value->AsCall() == NULL && |
2455 value->AsCallNew() == NULL) { | 2472 value->AsCallNew() == NULL) { |
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2626 if (is_strong(language_mode()) && | 2643 if (is_strong(language_mode()) && |
2627 i::IsConstructor(function_state_->kind())) { | 2644 i::IsConstructor(function_state_->kind())) { |
2628 bool is_this = peek() == Token::THIS; | 2645 bool is_this = peek() == Token::THIS; |
2629 Expression* expr; | 2646 Expression* expr; |
2630 ExpressionClassifier classifier; | 2647 ExpressionClassifier classifier; |
2631 if (is_this) { | 2648 if (is_this) { |
2632 expr = ParseStrongInitializationExpression(&classifier, CHECK_OK); | 2649 expr = ParseStrongInitializationExpression(&classifier, CHECK_OK); |
2633 } else { | 2650 } else { |
2634 expr = ParseStrongSuperCallExpression(&classifier, CHECK_OK); | 2651 expr = ParseStrongSuperCallExpression(&classifier, CHECK_OK); |
2635 } | 2652 } |
2636 // TODO(dslomov): report error if not a valid expression. | 2653 ValidateExpression(&classifier, CHECK_OK); |
2637 switch (peek()) { | 2654 switch (peek()) { |
2638 case Token::SEMICOLON: | 2655 case Token::SEMICOLON: |
2639 Consume(Token::SEMICOLON); | 2656 Consume(Token::SEMICOLON); |
2640 break; | 2657 break; |
2641 case Token::RBRACE: | 2658 case Token::RBRACE: |
2642 case Token::EOS: | 2659 case Token::EOS: |
2643 break; | 2660 break; |
2644 default: | 2661 default: |
2645 if (!scanner()->HasAnyLineTerminatorBeforeNext()) { | 2662 if (!scanner()->HasAnyLineTerminatorBeforeNext()) { |
2646 ReportMessageAt(function_state_->this_location(), | 2663 ReportMessageAt(function_state_->this_location(), |
(...skipping 1708 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4355 proxy, CONST, block_scope, pos, is_class_declaration, | 4372 proxy, CONST, block_scope, pos, is_class_declaration, |
4356 scope_->class_declaration_group_start()); | 4373 scope_->class_declaration_group_start()); |
4357 Declare(declaration, true, CHECK_OK); | 4374 Declare(declaration, true, CHECK_OK); |
4358 } | 4375 } |
4359 | 4376 |
4360 Expression* extends = NULL; | 4377 Expression* extends = NULL; |
4361 if (Check(Token::EXTENDS)) { | 4378 if (Check(Token::EXTENDS)) { |
4362 block_scope->set_start_position(scanner()->location().end_pos); | 4379 block_scope->set_start_position(scanner()->location().end_pos); |
4363 ExpressionClassifier classifier; | 4380 ExpressionClassifier classifier; |
4364 extends = ParseLeftHandSideExpression(&classifier, CHECK_OK); | 4381 extends = ParseLeftHandSideExpression(&classifier, CHECK_OK); |
4365 // TODO(dslomov): report error if not a valid expression. | 4382 ValidateExpression(&classifier, CHECK_OK); |
4366 } else { | 4383 } else { |
4367 block_scope->set_start_position(scanner()->location().end_pos); | 4384 block_scope->set_start_position(scanner()->location().end_pos); |
4368 } | 4385 } |
4369 | 4386 |
4370 | 4387 |
4371 ClassLiteralChecker checker(this); | 4388 ClassLiteralChecker checker(this); |
4372 ZoneList<ObjectLiteral::Property*>* properties = NewPropertyList(4, zone()); | 4389 ZoneList<ObjectLiteral::Property*>* properties = NewPropertyList(4, zone()); |
4373 FunctionLiteral* constructor = NULL; | 4390 FunctionLiteral* constructor = NULL; |
4374 bool has_seen_constructor = false; | 4391 bool has_seen_constructor = false; |
4375 | 4392 |
4376 Expect(Token::LBRACE, CHECK_OK); | 4393 Expect(Token::LBRACE, CHECK_OK); |
4377 | 4394 |
4378 const bool has_extends = extends != nullptr; | 4395 const bool has_extends = extends != nullptr; |
4379 while (peek() != Token::RBRACE) { | 4396 while (peek() != Token::RBRACE) { |
4380 if (Check(Token::SEMICOLON)) continue; | 4397 if (Check(Token::SEMICOLON)) continue; |
4381 if (fni_ != NULL) fni_->Enter(); | 4398 if (fni_ != NULL) fni_->Enter(); |
4382 const bool in_class = true; | 4399 const bool in_class = true; |
4383 const bool is_static = false; | 4400 const bool is_static = false; |
4384 bool is_computed_name = false; // Classes do not care about computed | 4401 bool is_computed_name = false; // Classes do not care about computed |
4385 // property names here. | 4402 // property names here. |
4386 ExpressionClassifier classifier; | 4403 ExpressionClassifier classifier; |
4387 ObjectLiteral::Property* property = ParsePropertyDefinition( | 4404 ObjectLiteral::Property* property = ParsePropertyDefinition( |
4388 &checker, in_class, has_extends, is_static, &is_computed_name, | 4405 &checker, in_class, has_extends, is_static, &is_computed_name, |
4389 &has_seen_constructor, &classifier, CHECK_OK); | 4406 &has_seen_constructor, &classifier, CHECK_OK); |
4390 // TODO(dslomov): report error if not a valid expression. | 4407 ValidateExpression(&classifier, CHECK_OK); |
4391 | 4408 |
4392 if (has_seen_constructor && constructor == NULL) { | 4409 if (has_seen_constructor && constructor == NULL) { |
4393 constructor = GetPropertyValue(property)->AsFunctionLiteral(); | 4410 constructor = GetPropertyValue(property)->AsFunctionLiteral(); |
4394 DCHECK_NOT_NULL(constructor); | 4411 DCHECK_NOT_NULL(constructor); |
4395 } else { | 4412 } else { |
4396 properties->Add(property, zone()); | 4413 properties->Add(property, zone()); |
4397 } | 4414 } |
4398 | 4415 |
4399 if (fni_ != NULL) { | 4416 if (fni_ != NULL) { |
4400 fni_->Infer(); | 4417 fni_->Infer(); |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4432 | 4449 |
4433 int pos = peek_position(); | 4450 int pos = peek_position(); |
4434 Expect(Token::MOD, CHECK_OK); | 4451 Expect(Token::MOD, CHECK_OK); |
4435 // Allow "eval" or "arguments" for backward compatibility. | 4452 // Allow "eval" or "arguments" for backward compatibility. |
4436 const AstRawString* name = ParseIdentifier(kAllowRestrictedIdentifiers, | 4453 const AstRawString* name = ParseIdentifier(kAllowRestrictedIdentifiers, |
4437 CHECK_OK); | 4454 CHECK_OK); |
4438 Scanner::Location spread_pos; | 4455 Scanner::Location spread_pos; |
4439 ExpressionClassifier classifier; | 4456 ExpressionClassifier classifier; |
4440 ZoneList<Expression*>* args = | 4457 ZoneList<Expression*>* args = |
4441 ParseArguments(&spread_pos, &classifier, CHECK_OK); | 4458 ParseArguments(&spread_pos, &classifier, CHECK_OK); |
4442 // TODO(dslomov): report error if not a valid expression. | 4459 ValidateExpression(&classifier, CHECK_OK); |
4443 | 4460 |
4444 DCHECK(!spread_pos.IsValid()); | 4461 DCHECK(!spread_pos.IsValid()); |
4445 | 4462 |
4446 if (extension_ != NULL) { | 4463 if (extension_ != NULL) { |
4447 // The extension structures are only accessible while parsing the | 4464 // The extension structures are only accessible while parsing the |
4448 // very first time not when reparsing because of lazy compilation. | 4465 // very first time not when reparsing because of lazy compilation. |
4449 scope_->DeclarationScope()->ForceEagerCompilation(); | 4466 scope_->DeclarationScope()->ForceEagerCompilation(); |
4450 } | 4467 } |
4451 | 4468 |
4452 const Runtime::Function* function = Runtime::FunctionForName(name->string()); | 4469 const Runtime::Function* function = Runtime::FunctionForName(name->string()); |
(...skipping 1356 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5809 | 5826 |
5810 Expression* Parser::SpreadCallNew(Expression* function, | 5827 Expression* Parser::SpreadCallNew(Expression* function, |
5811 ZoneList<v8::internal::Expression*>* args, | 5828 ZoneList<v8::internal::Expression*>* args, |
5812 int pos) { | 5829 int pos) { |
5813 args->InsertAt(0, function, zone()); | 5830 args->InsertAt(0, function, zone()); |
5814 | 5831 |
5815 return factory()->NewCallRuntime( | 5832 return factory()->NewCallRuntime( |
5816 ast_value_factory()->reflect_construct_string(), NULL, args, pos); | 5833 ast_value_factory()->reflect_construct_string(), NULL, args, pos); |
5817 } | 5834 } |
5818 } } // namespace v8::internal | 5835 } } // namespace v8::internal |
OLD | NEW |