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

Side by Side Diff: src/parser.cc

Issue 13179002: Add parser support for generators. (Closed) Base URL: git://github.com/v8/v8.git@master
Patch Set: added additional syntax tests Created 7 years, 8 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 | « src/parser.h ('k') | src/preparser.h » ('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 // 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 662 matching lines...) Expand 10 before | Expand all | Expand 10 after
673 body, 673 body,
674 function_state.materialized_literal_count(), 674 function_state.materialized_literal_count(),
675 function_state.expected_property_count(), 675 function_state.expected_property_count(),
676 function_state.handler_count(), 676 function_state.handler_count(),
677 function_state.only_simple_this_property_assignments(), 677 function_state.only_simple_this_property_assignments(),
678 function_state.this_property_assignments(), 678 function_state.this_property_assignments(),
679 0, 679 0,
680 FunctionLiteral::kNoDuplicateParameters, 680 FunctionLiteral::kNoDuplicateParameters,
681 FunctionLiteral::ANONYMOUS_EXPRESSION, 681 FunctionLiteral::ANONYMOUS_EXPRESSION,
682 FunctionLiteral::kGlobalOrEval, 682 FunctionLiteral::kGlobalOrEval,
683 FunctionLiteral::kNotParenthesized); 683 FunctionLiteral::kNotParenthesized,
684 FunctionLiteral::kNotGenerator);
684 result->set_ast_properties(factory()->visitor()->ast_properties()); 685 result->set_ast_properties(factory()->visitor()->ast_properties());
685 } else if (stack_overflow_) { 686 } else if (stack_overflow_) {
686 isolate()->StackOverflow(); 687 isolate()->StackOverflow();
687 } 688 }
688 } 689 }
689 690
690 // Make sure the target stack is empty. 691 // Make sure the target stack is empty.
691 ASSERT(target_stack_ == NULL); 692 ASSERT(target_stack_ == NULL);
692 693
693 // If there was a syntax error we have to get rid of the AST 694 // If there was a syntax error we have to get rid of the AST
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
761 ASSERT(info()->language_mode() == shared_info->language_mode()); 762 ASSERT(info()->language_mode() == shared_info->language_mode());
762 scope->SetLanguageMode(shared_info->language_mode()); 763 scope->SetLanguageMode(shared_info->language_mode());
763 FunctionLiteral::Type type = shared_info->is_expression() 764 FunctionLiteral::Type type = shared_info->is_expression()
764 ? (shared_info->is_anonymous() 765 ? (shared_info->is_anonymous()
765 ? FunctionLiteral::ANONYMOUS_EXPRESSION 766 ? FunctionLiteral::ANONYMOUS_EXPRESSION
766 : FunctionLiteral::NAMED_EXPRESSION) 767 : FunctionLiteral::NAMED_EXPRESSION)
767 : FunctionLiteral::DECLARATION; 768 : FunctionLiteral::DECLARATION;
768 bool ok = true; 769 bool ok = true;
769 result = ParseFunctionLiteral(name, 770 result = ParseFunctionLiteral(name,
770 false, // Strict mode name already checked. 771 false, // Strict mode name already checked.
772 shared_info->is_generator(),
771 RelocInfo::kNoPosition, 773 RelocInfo::kNoPosition,
772 type, 774 type,
773 &ok); 775 &ok);
774 // Make sure the results agree. 776 // Make sure the results agree.
775 ASSERT(ok == (result != NULL)); 777 ASSERT(ok == (result != NULL));
776 } 778 }
777 779
778 // Make sure the target stack is empty. 780 // Make sure the target stack is empty.
779 ASSERT(target_stack_ == NULL); 781 ASSERT(target_stack_ == NULL);
780 782
(...skipping 344 matching lines...) Expand 10 before | Expand all | Expand 10 after
1125 // Statement 1127 // Statement
1126 // FunctionDeclaration 1128 // FunctionDeclaration
1127 // 1129 //
1128 // In harmony mode we allow additionally the following productions 1130 // In harmony mode we allow additionally the following productions
1129 // ModuleElement: 1131 // ModuleElement:
1130 // LetDeclaration 1132 // LetDeclaration
1131 // ConstDeclaration 1133 // ConstDeclaration
1132 // ModuleDeclaration 1134 // ModuleDeclaration
1133 // ImportDeclaration 1135 // ImportDeclaration
1134 // ExportDeclaration 1136 // ExportDeclaration
1137 // GeneratorDeclaration
1135 1138
1136 switch (peek()) { 1139 switch (peek()) {
1137 case Token::FUNCTION: 1140 case Token::FUNCTION:
1138 return ParseFunctionDeclaration(NULL, ok); 1141 return ParseFunctionDeclaration(NULL, ok);
1139 case Token::LET: 1142 case Token::LET:
1140 case Token::CONST: 1143 case Token::CONST:
1141 return ParseVariableStatement(kModuleElement, NULL, ok); 1144 return ParseVariableStatement(kModuleElement, NULL, ok);
1142 case Token::IMPORT: 1145 case Token::IMPORT:
1143 return ParseImportDeclaration(ok); 1146 return ParseImportDeclaration(ok);
1144 case Token::EXPORT: 1147 case Token::EXPORT:
(...skipping 278 matching lines...) Expand 10 before | Expand all | Expand 10 after
1423 1426
1424 return block; 1427 return block;
1425 } 1428 }
1426 1429
1427 1430
1428 Statement* Parser::ParseExportDeclaration(bool* ok) { 1431 Statement* Parser::ParseExportDeclaration(bool* ok) {
1429 // ExportDeclaration: 1432 // ExportDeclaration:
1430 // 'export' Identifier (',' Identifier)* ';' 1433 // 'export' Identifier (',' Identifier)* ';'
1431 // 'export' VariableDeclaration 1434 // 'export' VariableDeclaration
1432 // 'export' FunctionDeclaration 1435 // 'export' FunctionDeclaration
1436 // 'export' GeneratorDeclaration
1433 // 'export' ModuleDeclaration 1437 // 'export' ModuleDeclaration
1434 // 1438 //
1435 // TODO(ES6): implement structuring ExportSpecifiers 1439 // TODO(ES6): implement structuring ExportSpecifiers
1436 1440
1437 Expect(Token::EXPORT, CHECK_OK); 1441 Expect(Token::EXPORT, CHECK_OK);
1438 1442
1439 Statement* result = NULL; 1443 Statement* result = NULL;
1440 ZoneStringList names(1, zone()); 1444 ZoneStringList names(1, zone());
1441 switch (peek()) { 1445 switch (peek()) {
1442 case Token::IDENTIFIER: { 1446 case Token::IDENTIFIER: {
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after
1502 bool* ok) { 1506 bool* ok) {
1503 // (Ecma 262 5th Edition, clause 14): 1507 // (Ecma 262 5th Edition, clause 14):
1504 // SourceElement: 1508 // SourceElement:
1505 // Statement 1509 // Statement
1506 // FunctionDeclaration 1510 // FunctionDeclaration
1507 // 1511 //
1508 // In harmony mode we allow additionally the following productions 1512 // In harmony mode we allow additionally the following productions
1509 // BlockElement (aka SourceElement): 1513 // BlockElement (aka SourceElement):
1510 // LetDeclaration 1514 // LetDeclaration
1511 // ConstDeclaration 1515 // ConstDeclaration
1516 // GeneratorDeclaration
1512 1517
1513 switch (peek()) { 1518 switch (peek()) {
1514 case Token::FUNCTION: 1519 case Token::FUNCTION:
1515 return ParseFunctionDeclaration(NULL, ok); 1520 return ParseFunctionDeclaration(NULL, ok);
1516 case Token::LET: 1521 case Token::LET:
1517 case Token::CONST: 1522 case Token::CONST:
1518 return ParseVariableStatement(kModuleElement, NULL, ok); 1523 return ParseVariableStatement(kModuleElement, NULL, ok);
1519 default: 1524 default:
1520 return ParseStatement(labels, ok); 1525 return ParseStatement(labels, ok);
1521 } 1526 }
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after
1621 } 1626 }
1622 1627
1623 case Token::FUNCTION: { 1628 case Token::FUNCTION: {
1624 // FunctionDeclaration is only allowed in the context of SourceElements 1629 // FunctionDeclaration is only allowed in the context of SourceElements
1625 // (Ecma 262 5th Edition, clause 14): 1630 // (Ecma 262 5th Edition, clause 14):
1626 // SourceElement: 1631 // SourceElement:
1627 // Statement 1632 // Statement
1628 // FunctionDeclaration 1633 // FunctionDeclaration
1629 // Common language extension is to allow function declaration in place 1634 // Common language extension is to allow function declaration in place
1630 // of any statement. This language extension is disabled in strict mode. 1635 // of any statement. This language extension is disabled in strict mode.
1636 //
1637 // In Harmony mode, this case also handles the extension:
1638 // Statement:
1639 // GeneratorDeclaration
1631 if (!top_scope_->is_classic_mode()) { 1640 if (!top_scope_->is_classic_mode()) {
1632 ReportMessageAt(scanner().peek_location(), "strict_function", 1641 ReportMessageAt(scanner().peek_location(), "strict_function",
1633 Vector<const char*>::empty()); 1642 Vector<const char*>::empty());
1634 *ok = false; 1643 *ok = false;
1635 return NULL; 1644 return NULL;
1636 } 1645 }
1637 return ParseFunctionDeclaration(NULL, ok); 1646 return ParseFunctionDeclaration(NULL, ok);
1638 } 1647 }
1639 1648
1640 case Token::DEBUGGER: 1649 case Token::DEBUGGER:
(...skipping 244 matching lines...) Expand 10 before | Expand all | Expand 10 after
1885 factory()->NewAssignment( 1894 factory()->NewAssignment(
1886 Token::INIT_VAR, proxy, lit, RelocInfo::kNoPosition)); 1895 Token::INIT_VAR, proxy, lit, RelocInfo::kNoPosition));
1887 } 1896 }
1888 1897
1889 1898
1890 Statement* Parser::ParseFunctionDeclaration(ZoneStringList* names, bool* ok) { 1899 Statement* Parser::ParseFunctionDeclaration(ZoneStringList* names, bool* ok) {
1891 // FunctionDeclaration :: 1900 // FunctionDeclaration ::
1892 // 'function' Identifier '(' FormalParameterListopt ')' '{' FunctionBody '}' 1901 // 'function' Identifier '(' FormalParameterListopt ')' '{' FunctionBody '}'
1893 Expect(Token::FUNCTION, CHECK_OK); 1902 Expect(Token::FUNCTION, CHECK_OK);
1894 int function_token_position = scanner().location().beg_pos; 1903 int function_token_position = scanner().location().beg_pos;
1904 bool is_generator = FLAG_harmony_generators && Check(Token::MUL);
1895 bool is_strict_reserved = false; 1905 bool is_strict_reserved = false;
1896 Handle<String> name = ParseIdentifierOrStrictReservedWord( 1906 Handle<String> name = ParseIdentifierOrStrictReservedWord(
1897 &is_strict_reserved, CHECK_OK); 1907 &is_strict_reserved, CHECK_OK);
1898 FunctionLiteral* fun = ParseFunctionLiteral(name, 1908 FunctionLiteral* fun = ParseFunctionLiteral(name,
1899 is_strict_reserved, 1909 is_strict_reserved,
1910 is_generator,
1900 function_token_position, 1911 function_token_position,
1901 FunctionLiteral::DECLARATION, 1912 FunctionLiteral::DECLARATION,
1902 CHECK_OK); 1913 CHECK_OK);
1903 // Even if we're not at the top-level of the global or a function 1914 // Even if we're not at the top-level of the global or a function
1904 // scope, we treat it as such and introduce the function with its 1915 // scope, we treat it as such and introduce the function with its
1905 // initial value upon entering the corresponding scope. 1916 // initial value upon entering the corresponding scope.
1906 // In extended mode, a function behaves as a lexical binding, except in the 1917 // In extended mode, a function behaves as a lexical binding, except in the
1907 // global scope. 1918 // global scope.
1908 VariableMode mode = 1919 VariableMode mode =
1909 is_extended_mode() && !top_scope_->is_global_scope() ? LET : VAR; 1920 is_extended_mode() && !top_scope_->is_global_scope() ? LET : VAR;
(...skipping 1087 matching lines...) Expand 10 before | Expand all | Expand 10 after
2997 factory()->NewBinaryOperation(Token::COMMA, result, right, position); 3008 factory()->NewBinaryOperation(Token::COMMA, result, right, position);
2998 } 3009 }
2999 return result; 3010 return result;
3000 } 3011 }
3001 3012
3002 3013
3003 // Precedence = 2 3014 // Precedence = 2
3004 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) { 3015 Expression* Parser::ParseAssignmentExpression(bool accept_IN, bool* ok) {
3005 // AssignmentExpression :: 3016 // AssignmentExpression ::
3006 // ConditionalExpression 3017 // ConditionalExpression
3018 // YieldExpression
3007 // LeftHandSideExpression AssignmentOperator AssignmentExpression 3019 // LeftHandSideExpression AssignmentOperator AssignmentExpression
3008 3020
3021 if (peek() == Token::YIELD && inside_generator()) {
3022 return ParseYieldExpression(ok);
3023 }
3024
3009 if (fni_ != NULL) fni_->Enter(); 3025 if (fni_ != NULL) fni_->Enter();
3010 Expression* expression = ParseConditionalExpression(accept_IN, CHECK_OK); 3026 Expression* expression = ParseConditionalExpression(accept_IN, CHECK_OK);
3011 3027
3012 if (!Token::IsAssignmentOp(peek())) { 3028 if (!Token::IsAssignmentOp(peek())) {
3013 if (fni_ != NULL) fni_->Leave(); 3029 if (fni_ != NULL) fni_->Leave();
3014 // Parsed conditional expression only (no assignment). 3030 // Parsed conditional expression only (no assignment).
3015 return expression; 3031 return expression;
3016 } 3032 }
3017 3033
3018 // Signal a reference error if the expression is an invalid left-hand 3034 // Signal a reference error if the expression is an invalid left-hand
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
3067 } else { 3083 } else {
3068 fni_->RemoveLastFunction(); 3084 fni_->RemoveLastFunction();
3069 } 3085 }
3070 fni_->Leave(); 3086 fni_->Leave();
3071 } 3087 }
3072 3088
3073 return factory()->NewAssignment(op, expression, right, pos); 3089 return factory()->NewAssignment(op, expression, right, pos);
3074 } 3090 }
3075 3091
3076 3092
3093 Expression* Parser::ParseYieldExpression(bool* ok) {
3094 // YieldExpression ::
3095 // 'yield' '*'? AssignmentExpression
3096 int position = scanner().peek_location().beg_pos;
3097 Expect(Token::YIELD, CHECK_OK);
3098 bool is_yield_star = Check(Token::MUL);
3099 Expression* expression = ParseAssignmentExpression(false, CHECK_OK);
3100 return factory()->NewYield(expression, is_yield_star, position);
3101 }
3102
3103
3077 // Precedence = 3 3104 // Precedence = 3
3078 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) { 3105 Expression* Parser::ParseConditionalExpression(bool accept_IN, bool* ok) {
3079 // ConditionalExpression :: 3106 // ConditionalExpression ::
3080 // LogicalOrExpression 3107 // LogicalOrExpression
3081 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression 3108 // LogicalOrExpression '?' AssignmentExpression ':' AssignmentExpression
3082 3109
3083 // We start using the binary expression parser for prec >= 4 only! 3110 // We start using the binary expression parser for prec >= 4 only!
3084 Expression* expression = ParseBinaryExpression(4, accept_IN, CHECK_OK); 3111 Expression* expression = ParseBinaryExpression(4, accept_IN, CHECK_OK);
3085 if (peek() != Token::CONDITIONAL) return expression; 3112 if (peek() != Token::CONDITIONAL) return expression;
3086 Consume(Token::CONDITIONAL); 3113 Consume(Token::CONDITIONAL);
(...skipping 356 matching lines...) Expand 10 before | Expand all | Expand 10 after
3443 bool* ok) { 3470 bool* ok) {
3444 // MemberExpression :: 3471 // MemberExpression ::
3445 // (PrimaryExpression | FunctionLiteral) 3472 // (PrimaryExpression | FunctionLiteral)
3446 // ('[' Expression ']' | '.' Identifier | Arguments)* 3473 // ('[' Expression ']' | '.' Identifier | Arguments)*
3447 3474
3448 // Parse the initial primary or function expression. 3475 // Parse the initial primary or function expression.
3449 Expression* result = NULL; 3476 Expression* result = NULL;
3450 if (peek() == Token::FUNCTION) { 3477 if (peek() == Token::FUNCTION) {
3451 Expect(Token::FUNCTION, CHECK_OK); 3478 Expect(Token::FUNCTION, CHECK_OK);
3452 int function_token_position = scanner().location().beg_pos; 3479 int function_token_position = scanner().location().beg_pos;
3480 bool is_generator = FLAG_harmony_generators && Check(Token::MUL);
3453 Handle<String> name; 3481 Handle<String> name;
3454 bool is_strict_reserved_name = false; 3482 bool is_strict_reserved_name = false;
3455 if (peek_any_identifier()) { 3483 if (peek_any_identifier()) {
3456 name = ParseIdentifierOrStrictReservedWord(&is_strict_reserved_name, 3484 name = ParseIdentifierOrStrictReservedWord(&is_strict_reserved_name,
3457 CHECK_OK); 3485 CHECK_OK);
3458 } 3486 }
3459 FunctionLiteral::Type type = name.is_null() 3487 FunctionLiteral::Type type = name.is_null()
3460 ? FunctionLiteral::ANONYMOUS_EXPRESSION 3488 ? FunctionLiteral::ANONYMOUS_EXPRESSION
3461 : FunctionLiteral::NAMED_EXPRESSION; 3489 : FunctionLiteral::NAMED_EXPRESSION;
3462 result = ParseFunctionLiteral(name, 3490 result = ParseFunctionLiteral(name,
3463 is_strict_reserved_name, 3491 is_strict_reserved_name,
3492 is_generator,
3464 function_token_position, 3493 function_token_position,
3465 type, 3494 type,
3466 CHECK_OK); 3495 CHECK_OK);
3467 } else { 3496 } else {
3468 result = ParsePrimaryExpression(CHECK_OK); 3497 result = ParsePrimaryExpression(CHECK_OK);
3469 } 3498 }
3470 3499
3471 while (true) { 3500 while (true) {
3472 switch (peek()) { 3501 switch (peek()) {
3473 case Token::LBRACK: { 3502 case Token::LBRACK: {
(...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after
3597 Consume(Token::TRUE_LITERAL); 3626 Consume(Token::TRUE_LITERAL);
3598 result = factory()->NewLiteral(isolate()->factory()->true_value()); 3627 result = factory()->NewLiteral(isolate()->factory()->true_value());
3599 break; 3628 break;
3600 3629
3601 case Token::FALSE_LITERAL: 3630 case Token::FALSE_LITERAL:
3602 Consume(Token::FALSE_LITERAL); 3631 Consume(Token::FALSE_LITERAL);
3603 result = factory()->NewLiteral(isolate()->factory()->false_value()); 3632 result = factory()->NewLiteral(isolate()->factory()->false_value());
3604 break; 3633 break;
3605 3634
3606 case Token::IDENTIFIER: 3635 case Token::IDENTIFIER:
3636 case Token::YIELD:
3607 case Token::FUTURE_STRICT_RESERVED_WORD: { 3637 case Token::FUTURE_STRICT_RESERVED_WORD: {
3608 Handle<String> name = ParseIdentifier(CHECK_OK); 3638 Handle<String> name = ParseIdentifier(CHECK_OK);
3609 if (fni_ != NULL) fni_->PushVariableName(name); 3639 if (fni_ != NULL) fni_->PushVariableName(name);
3610 // The name may refer to a module instance object, so its type is unknown. 3640 // The name may refer to a module instance object, so its type is unknown.
3611 #ifdef DEBUG 3641 #ifdef DEBUG
3612 if (FLAG_print_interface_details) 3642 if (FLAG_print_interface_details)
3613 PrintF("# Variable %s ", name->ToAsciiArray()); 3643 PrintF("# Variable %s ", name->ToAsciiArray());
3614 #endif 3644 #endif
3615 Interface* interface = Interface::NewUnknown(zone()); 3645 Interface* interface = Interface::NewUnknown(zone());
3616 result = top_scope_->NewUnresolved( 3646 result = top_scope_->NewUnresolved(
(...skipping 385 matching lines...) Expand 10 before | Expand all | Expand 10 after
4002 next == Token::STRING || is_keyword) { 4032 next == Token::STRING || is_keyword) {
4003 Handle<String> name; 4033 Handle<String> name;
4004 if (is_keyword) { 4034 if (is_keyword) {
4005 name = isolate_->factory()->InternalizeUtf8String(Token::String(next)); 4035 name = isolate_->factory()->InternalizeUtf8String(Token::String(next));
4006 } else { 4036 } else {
4007 name = GetSymbol(CHECK_OK); 4037 name = GetSymbol(CHECK_OK);
4008 } 4038 }
4009 FunctionLiteral* value = 4039 FunctionLiteral* value =
4010 ParseFunctionLiteral(name, 4040 ParseFunctionLiteral(name,
4011 false, // reserved words are allowed here 4041 false, // reserved words are allowed here
4042 false, // not a generator
4012 RelocInfo::kNoPosition, 4043 RelocInfo::kNoPosition,
4013 FunctionLiteral::ANONYMOUS_EXPRESSION, 4044 FunctionLiteral::ANONYMOUS_EXPRESSION,
4014 CHECK_OK); 4045 CHECK_OK);
4015 // Allow any number of parameters for compatibilty with JSC. 4046 // Allow any number of parameters for compatibilty with JSC.
4016 // Specification only allows zero parameters for get and one for set. 4047 // Specification only allows zero parameters for get and one for set.
4017 return factory()->NewObjectLiteralProperty(is_getter, value); 4048 return factory()->NewObjectLiteralProperty(is_getter, value);
4018 } else { 4049 } else {
4019 ReportUnexpectedToken(next); 4050 ReportUnexpectedToken(next);
4020 *ok = false; 4051 *ok = false;
4021 return NULL; 4052 return NULL;
(...skipping 281 matching lines...) Expand 10 before | Expand all | Expand 10 after
4303 int properties_; 4334 int properties_;
4304 LanguageMode mode_; 4335 LanguageMode mode_;
4305 // For error messages. 4336 // For error messages.
4306 const char* message_; 4337 const char* message_;
4307 const char* argument_opt_; 4338 const char* argument_opt_;
4308 }; 4339 };
4309 4340
4310 4341
4311 FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> function_name, 4342 FunctionLiteral* Parser::ParseFunctionLiteral(Handle<String> function_name,
4312 bool name_is_strict_reserved, 4343 bool name_is_strict_reserved,
4344 bool is_generator,
4313 int function_token_position, 4345 int function_token_position,
4314 FunctionLiteral::Type type, 4346 FunctionLiteral::Type type,
4315 bool* ok) { 4347 bool* ok) {
4316 // Function :: 4348 // Function ::
4317 // '(' FormalParameterList? ')' '{' FunctionBody '}' 4349 // '(' FormalParameterList? ')' '{' FunctionBody '}'
4318 4350
4319 // Anonymous functions were passed either the empty symbol or a null 4351 // Anonymous functions were passed either the empty symbol or a null
4320 // handle as the function name. Remember if we were passed a non-empty 4352 // handle as the function name. Remember if we were passed a non-empty
4321 // handle to decide whether to invoke function name inference. 4353 // handle to decide whether to invoke function name inference.
4322 bool should_infer_name = function_name.is_null(); 4354 bool should_infer_name = function_name.is_null();
4323 4355
4324 // We want a non-null handle as the function name. 4356 // We want a non-null handle as the function name.
4325 if (should_infer_name) { 4357 if (should_infer_name) {
4326 function_name = isolate()->factory()->empty_string(); 4358 function_name = isolate()->factory()->empty_string();
4327 } 4359 }
4328 4360
4329 int num_parameters = 0; 4361 int num_parameters = 0;
4330 // Function declarations are function scoped in normal mode, so they are 4362 // Function declarations are function scoped in normal mode, so they are
4331 // hoisted. In harmony block scoping mode they are block scoped, so they 4363 // hoisted. In harmony block scoping mode they are block scoped, so they
4332 // are not hoisted. 4364 // are not hoisted.
4333 Scope* scope = (type == FunctionLiteral::DECLARATION && !is_extended_mode()) 4365 Scope* scope = (type == FunctionLiteral::DECLARATION && !is_extended_mode())
4334 ? NewScope(top_scope_->DeclarationScope(), FUNCTION_SCOPE) 4366 ? NewScope(top_scope_->DeclarationScope(), FUNCTION_SCOPE)
4335 : NewScope(top_scope_, FUNCTION_SCOPE); 4367 : NewScope(top_scope_, FUNCTION_SCOPE);
4368 scope->set_inside_generator(is_generator);
4336 ZoneList<Statement*>* body = NULL; 4369 ZoneList<Statement*>* body = NULL;
4337 int materialized_literal_count = -1; 4370 int materialized_literal_count = -1;
4338 int expected_property_count = -1; 4371 int expected_property_count = -1;
4339 int handler_count = 0; 4372 int handler_count = 0;
4340 bool only_simple_this_property_assignments; 4373 bool only_simple_this_property_assignments;
4341 Handle<FixedArray> this_property_assignments; 4374 Handle<FixedArray> this_property_assignments;
4342 FunctionLiteral::ParameterFlag duplicate_parameters = 4375 FunctionLiteral::ParameterFlag duplicate_parameters =
4343 FunctionLiteral::kNoDuplicateParameters; 4376 FunctionLiteral::kNoDuplicateParameters;
4344 FunctionLiteral::IsParenthesizedFlag parenthesized = parenthesized_function_ 4377 FunctionLiteral::IsParenthesizedFlag parenthesized = parenthesized_function_
4345 ? FunctionLiteral::kIsParenthesized 4378 ? FunctionLiteral::kIsParenthesized
4346 : FunctionLiteral::kNotParenthesized; 4379 : FunctionLiteral::kNotParenthesized;
4380 FunctionLiteral::IsGeneratorFlag generator = is_generator
4381 ? FunctionLiteral::kIsGenerator
4382 : FunctionLiteral::kNotGenerator;
4347 AstProperties ast_properties; 4383 AstProperties ast_properties;
4348 // Parse function body. 4384 // Parse function body.
4349 { FunctionState function_state(this, scope, isolate()); 4385 { FunctionState function_state(this, scope, isolate());
4350 top_scope_->SetScopeName(function_name); 4386 top_scope_->SetScopeName(function_name);
4351 4387
4352 // FormalParameterList :: 4388 // FormalParameterList ::
4353 // '(' (Identifier)*[','] ')' 4389 // '(' (Identifier)*[','] ')'
4354 Expect(Token::LPAREN, CHECK_OK); 4390 Expect(Token::LPAREN, CHECK_OK);
4355 scope->set_start_position(scanner().location().beg_pos); 4391 scope->set_start_position(scanner().location().beg_pos);
4356 Scanner::Location name_loc = Scanner::Location::invalid(); 4392 Scanner::Location name_loc = Scanner::Location::invalid();
(...skipping 220 matching lines...) Expand 10 before | Expand all | Expand 10 after
4577 body, 4613 body,
4578 materialized_literal_count, 4614 materialized_literal_count,
4579 expected_property_count, 4615 expected_property_count,
4580 handler_count, 4616 handler_count,
4581 only_simple_this_property_assignments, 4617 only_simple_this_property_assignments,
4582 this_property_assignments, 4618 this_property_assignments,
4583 num_parameters, 4619 num_parameters,
4584 duplicate_parameters, 4620 duplicate_parameters,
4585 type, 4621 type,
4586 FunctionLiteral::kIsFunction, 4622 FunctionLiteral::kIsFunction,
4587 parenthesized); 4623 parenthesized,
4624 generator);
4588 function_literal->set_function_token_position(function_token_position); 4625 function_literal->set_function_token_position(function_token_position);
4589 function_literal->set_ast_properties(&ast_properties); 4626 function_literal->set_ast_properties(&ast_properties);
4590 4627
4591 if (fni_ != NULL && should_infer_name) fni_->AddFunction(function_literal); 4628 if (fni_ != NULL && should_infer_name) fni_->AddFunction(function_literal);
4592 return function_literal; 4629 return function_literal;
4593 } 4630 }
4594 4631
4595 4632
4596 preparser::PreParser::PreParseResult Parser::LazyParseFunctionLiteral( 4633 preparser::PreParser::PreParseResult Parser::LazyParseFunctionLiteral(
4597 SingletonLogger* logger) { 4634 SingletonLogger* logger) {
4598 HistogramTimerScope preparse_scope(isolate()->counters()->pre_parse()); 4635 HistogramTimerScope preparse_scope(isolate()->counters()->pre_parse());
4599 ASSERT_EQ(Token::LBRACE, scanner().current_token()); 4636 ASSERT_EQ(Token::LBRACE, scanner().current_token());
4600 4637
4601 if (reusable_preparser_ == NULL) { 4638 if (reusable_preparser_ == NULL) {
4602 intptr_t stack_limit = isolate()->stack_guard()->real_climit(); 4639 intptr_t stack_limit = isolate()->stack_guard()->real_climit();
4603 bool do_allow_lazy = true; 4640 bool do_allow_lazy = true;
4604 reusable_preparser_ = new preparser::PreParser(&scanner_, 4641 reusable_preparser_ = new preparser::PreParser(&scanner_,
4605 NULL, 4642 NULL,
4606 stack_limit, 4643 stack_limit,
4607 do_allow_lazy, 4644 do_allow_lazy,
4608 allow_natives_syntax_, 4645 allow_natives_syntax_,
4609 allow_modules_); 4646 allow_modules_);
4610 } 4647 }
4611 preparser::PreParser::PreParseResult result = 4648 preparser::PreParser::PreParseResult result =
4612 reusable_preparser_->PreParseLazyFunction(top_scope_->language_mode(), 4649 reusable_preparser_->PreParseLazyFunction(top_scope_->language_mode(),
4650 top_scope_->inside_generator(),
4613 logger); 4651 logger);
4614 return result; 4652 return result;
4615 } 4653 }
4616 4654
4617 4655
4618 Expression* Parser::ParseV8Intrinsic(bool* ok) { 4656 Expression* Parser::ParseV8Intrinsic(bool* ok) {
4619 // CallRuntime :: 4657 // CallRuntime ::
4620 // '%' Identifier Arguments 4658 // '%' Identifier Arguments
4621 4659
4622 Expect(Token::MOD, CHECK_OK); 4660 Expect(Token::MOD, CHECK_OK);
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
4665 4703
4666 // We have a valid intrinsics call or a call to a builtin. 4704 // We have a valid intrinsics call or a call to a builtin.
4667 return factory()->NewCallRuntime(name, function, args); 4705 return factory()->NewCallRuntime(name, function, args);
4668 } 4706 }
4669 4707
4670 4708
4671 bool Parser::peek_any_identifier() { 4709 bool Parser::peek_any_identifier() {
4672 Token::Value next = peek(); 4710 Token::Value next = peek();
4673 return next == Token::IDENTIFIER || 4711 return next == Token::IDENTIFIER ||
4674 next == Token::FUTURE_RESERVED_WORD || 4712 next == Token::FUTURE_RESERVED_WORD ||
4675 next == Token::FUTURE_STRICT_RESERVED_WORD; 4713 next == Token::FUTURE_STRICT_RESERVED_WORD ||
4714 next == Token::YIELD;
4676 } 4715 }
4677 4716
4678 4717
4679 void Parser::Consume(Token::Value token) { 4718 void Parser::Consume(Token::Value token) {
4680 Token::Value next = Next(); 4719 Token::Value next = Next();
4681 USE(next); 4720 USE(next);
4682 USE(token); 4721 USE(token);
4683 ASSERT(next == token); 4722 ASSERT(next == token);
4684 } 4723 }
4685 4724
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after
4737 4776
4738 4777
4739 Literal* Parser::GetLiteralTheHole() { 4778 Literal* Parser::GetLiteralTheHole() {
4740 return factory()->NewLiteral(isolate()->factory()->the_hole_value()); 4779 return factory()->NewLiteral(isolate()->factory()->the_hole_value());
4741 } 4780 }
4742 4781
4743 4782
4744 // Parses an identifier that is valid for the current scope, in particular it 4783 // Parses an identifier that is valid for the current scope, in particular it
4745 // fails on strict mode future reserved keywords in a strict scope. 4784 // fails on strict mode future reserved keywords in a strict scope.
4746 Handle<String> Parser::ParseIdentifier(bool* ok) { 4785 Handle<String> Parser::ParseIdentifier(bool* ok) {
4747 if (!top_scope_->is_classic_mode()) { 4786 Token::Value next = Next();
4748 Expect(Token::IDENTIFIER, ok); 4787 if (next == Token::IDENTIFIER ||
4749 } else if (!Check(Token::IDENTIFIER)) { 4788 (top_scope_->is_classic_mode() &&
4750 Expect(Token::FUTURE_STRICT_RESERVED_WORD, ok); 4789 (next == Token::FUTURE_STRICT_RESERVED_WORD ||
4790 (next == Token::YIELD && !inside_generator())))) {
4791 return GetSymbol(ok);
4792 } else {
4793 ReportUnexpectedToken(next);
4794 *ok = false;
4795 return Handle<String>();
4751 } 4796 }
4752 if (!*ok) return Handle<String>();
4753 return GetSymbol(ok);
4754 } 4797 }
4755 4798
4756 4799
4757 // Parses and identifier or a strict mode future reserved word, and indicate 4800 // Parses and identifier or a strict mode future reserved word, and indicate
4758 // whether it is strict mode future reserved. 4801 // whether it is strict mode future reserved.
4759 Handle<String> Parser::ParseIdentifierOrStrictReservedWord( 4802 Handle<String> Parser::ParseIdentifierOrStrictReservedWord(
4760 bool* is_strict_reserved, bool* ok) { 4803 bool* is_strict_reserved, bool* ok) {
4761 *is_strict_reserved = false; 4804 Token::Value next = Next();
4762 if (!Check(Token::IDENTIFIER)) { 4805 if (next == Token::IDENTIFIER) {
4763 Expect(Token::FUTURE_STRICT_RESERVED_WORD, ok); 4806 *is_strict_reserved = false;
4807 } else if (next == Token::FUTURE_STRICT_RESERVED_WORD ||
4808 (next == Token::YIELD && !inside_generator())) {
4764 *is_strict_reserved = true; 4809 *is_strict_reserved = true;
4810 } else {
4811 ReportUnexpectedToken(next);
4812 *ok = false;
4813 return Handle<String>();
4765 } 4814 }
4766 if (!*ok) return Handle<String>();
4767 return GetSymbol(ok); 4815 return GetSymbol(ok);
4768 } 4816 }
4769 4817
4770 4818
4771 Handle<String> Parser::ParseIdentifierName(bool* ok) { 4819 Handle<String> Parser::ParseIdentifierName(bool* ok) {
4772 Token::Value next = Next(); 4820 Token::Value next = Next();
4773 if (next != Token::IDENTIFIER && 4821 if (next != Token::IDENTIFIER &&
4774 next != Token::FUTURE_RESERVED_WORD && 4822 next != Token::FUTURE_RESERVED_WORD &&
4775 next != Token::FUTURE_STRICT_RESERVED_WORD && 4823 next != Token::FUTURE_STRICT_RESERVED_WORD &&
4776 !Token::IsKeyword(next)) { 4824 !Token::IsKeyword(next)) {
(...skipping 1165 matching lines...) Expand 10 before | Expand all | Expand 10 after
5942 ASSERT(info->isolate()->has_pending_exception()); 5990 ASSERT(info->isolate()->has_pending_exception());
5943 } else { 5991 } else {
5944 result = parser.ParseProgram(); 5992 result = parser.ParseProgram();
5945 } 5993 }
5946 } 5994 }
5947 info->SetFunction(result); 5995 info->SetFunction(result);
5948 return (result != NULL); 5996 return (result != NULL);
5949 } 5997 }
5950 5998
5951 } } // namespace v8::internal 5999 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/parser.h ('k') | src/preparser.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698