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/parsing/parser.h" | 5 #include "src/parsing/parser.h" |
6 | 6 |
7 #include "src/api.h" | 7 #include "src/api.h" |
8 #include "src/ast/ast.h" | 8 #include "src/ast/ast.h" |
9 #include "src/ast/ast-expression-rewriter.h" | 9 #include "src/ast/ast-expression-rewriter.h" |
10 #include "src/ast/ast-expression-visitor.h" | 10 #include "src/ast/ast-expression-visitor.h" |
(...skipping 6403 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6414 | 6414 |
6415 void ParserTraits::BuildIteratorClose(ZoneList<Statement*>* statements, | 6415 void ParserTraits::BuildIteratorClose(ZoneList<Statement*>* statements, |
6416 Variable* iterator, | 6416 Variable* iterator, |
6417 Maybe<Variable*> input, | 6417 Maybe<Variable*> input, |
6418 Variable* var_output) { | 6418 Variable* var_output) { |
6419 // | 6419 // |
6420 // This function adds four statements to [statements], corresponding to the | 6420 // This function adds four statements to [statements], corresponding to the |
6421 // following code: | 6421 // following code: |
6422 // | 6422 // |
6423 // let iteratorReturn = iterator.return; | 6423 // let iteratorReturn = iterator.return; |
6424 // if (IS_NULL_OR_UNDEFINED(iteratorReturn) return |input|; | 6424 // if (IS_NULL_OR_UNDEFINED(iteratorReturn) { |
6425 // output = %_Call(iteratorReturn, iterator|, input|); | 6425 // return {value: input, done: true}; |
| 6426 // } |
| 6427 // output = %_Call(iteratorReturn, iterator, input); |
6426 // if (!IS_RECEIVER(output)) %ThrowIterResultNotAnObject(output); | 6428 // if (!IS_RECEIVER(output)) %ThrowIterResultNotAnObject(output); |
6427 // | 6429 // |
6428 // Here, |...| denotes optional parts, depending on the presence of the | 6430 // When the input variable is not given, the return statement becomes |
6429 // input variable. The reason for allowing input is that BuildIteratorClose | 6431 // return {value: undefined, done: true}; |
| 6432 // and %_Call has only two arguments: |
| 6433 // output = %_Call(iteratorReturn, iterator); |
| 6434 // |
| 6435 // The reason for allowing input is that BuildIteratorClose |
6430 // can then be reused to handle the return case in yield*. | 6436 // can then be reused to handle the return case in yield*. |
6431 // | 6437 // |
6432 | 6438 |
6433 const int nopos = RelocInfo::kNoPosition; | 6439 const int nopos = RelocInfo::kNoPosition; |
6434 auto factory = parser_->factory(); | 6440 auto factory = parser_->factory(); |
6435 auto avfactory = parser_->ast_value_factory(); | 6441 auto avfactory = parser_->ast_value_factory(); |
6436 auto zone = parser_->zone(); | 6442 auto zone = parser_->zone(); |
6437 | 6443 |
6438 // let iteratorReturn = iterator.return; | 6444 // let iteratorReturn = iterator.return; |
6439 Variable* var_return = var_output; // Reusing the output variable. | 6445 Variable* var_return = var_output; // Reusing the output variable. |
6440 Statement* get_return; | 6446 Statement* get_return; |
6441 { | 6447 { |
6442 Expression* iterator_proxy = factory->NewVariableProxy(iterator); | 6448 Expression* iterator_proxy = factory->NewVariableProxy(iterator); |
6443 Expression* literal = | 6449 Expression* literal = |
6444 factory->NewStringLiteral(avfactory->return_string(), nopos); | 6450 factory->NewStringLiteral(avfactory->return_string(), nopos); |
6445 Expression* property = | 6451 Expression* property = |
6446 factory->NewProperty(iterator_proxy, literal, nopos); | 6452 factory->NewProperty(iterator_proxy, literal, nopos); |
6447 Expression* return_proxy = factory->NewVariableProxy(var_return); | 6453 Expression* return_proxy = factory->NewVariableProxy(var_return); |
6448 Expression* assignment = factory->NewAssignment( | 6454 Expression* assignment = factory->NewAssignment( |
6449 Token::ASSIGN, return_proxy, property, nopos); | 6455 Token::ASSIGN, return_proxy, property, nopos); |
6450 get_return = factory->NewExpressionStatement(assignment, nopos); | 6456 get_return = factory->NewExpressionStatement(assignment, nopos); |
6451 } | 6457 } |
6452 | 6458 |
6453 // if (IS_NULL_OR_UNDEFINED(iteratorReturn) return |input|; | 6459 // if (IS_NULL_OR_UNDEFINED(iteratorReturn) { |
| 6460 // return {value: input, done: true}; |
| 6461 // } |
6454 Statement* check_return; | 6462 Statement* check_return; |
6455 { | 6463 { |
6456 Expression* condition = factory->NewCompareOperation( | 6464 Expression* condition = factory->NewCompareOperation( |
6457 Token::EQ, factory->NewVariableProxy(var_return), | 6465 Token::EQ, factory->NewVariableProxy(var_return), |
6458 factory->NewNullLiteral(nopos), nopos); | 6466 factory->NewNullLiteral(nopos), nopos); |
6459 | 6467 |
6460 Expression* value = input.IsJust() | 6468 Expression* value = input.IsJust() |
6461 ? static_cast<Expression*>( | 6469 ? static_cast<Expression*>( |
6462 factory->NewVariableProxy(input.FromJust())) | 6470 factory->NewVariableProxy(input.FromJust())) |
6463 : factory->NewUndefinedLiteral(nopos); | 6471 : factory->NewUndefinedLiteral(nopos); |
6464 | 6472 |
6465 Statement* return_input = factory->NewReturnStatement(value, nopos); | 6473 Statement* return_input = |
| 6474 factory->NewReturnStatement(BuildIteratorResult(value, true), nopos); |
6466 | 6475 |
6467 check_return = factory->NewIfStatement( | 6476 check_return = factory->NewIfStatement( |
6468 condition, return_input, factory->NewEmptyStatement(nopos), nopos); | 6477 condition, return_input, factory->NewEmptyStatement(nopos), nopos); |
6469 } | 6478 } |
6470 | 6479 |
6471 // output = %_Call(iteratorReturn, iterator, |input|); | 6480 // output = %_Call(iteratorReturn, iterator, input); |
6472 Statement* call_return; | 6481 Statement* call_return; |
6473 { | 6482 { |
6474 auto args = new (zone) ZoneList<Expression*>(3, zone); | 6483 auto args = new (zone) ZoneList<Expression*>(3, zone); |
6475 args->Add(factory->NewVariableProxy(var_return), zone); | 6484 args->Add(factory->NewVariableProxy(var_return), zone); |
6476 args->Add(factory->NewVariableProxy(iterator), zone); | 6485 args->Add(factory->NewVariableProxy(iterator), zone); |
6477 if (input.IsJust()) { | 6486 if (input.IsJust()) { |
6478 args->Add(factory->NewVariableProxy(input.FromJust()), zone); | 6487 args->Add(factory->NewVariableProxy(input.FromJust()), zone); |
6479 } | 6488 } |
6480 | 6489 |
6481 Expression* call = | 6490 Expression* call = |
(...skipping 451 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6933 try_block, target); | 6942 try_block, target); |
6934 final_loop = target; | 6943 final_loop = target; |
6935 } | 6944 } |
6936 | 6945 |
6937 return final_loop; | 6946 return final_loop; |
6938 } | 6947 } |
6939 | 6948 |
6940 | 6949 |
6941 } // namespace internal | 6950 } // namespace internal |
6942 } // namespace v8 | 6951 } // namespace v8 |
OLD | NEW |