OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/flow_graph_builder.h" | 5 #include "vm/flow_graph_builder.h" |
6 | 6 |
7 #include "vm/ast_printer.h" | 7 #include "vm/ast_printer.h" |
8 #include "vm/bit_vector.h" | 8 #include "vm/bit_vector.h" |
9 #include "vm/code_descriptors.h" | 9 #include "vm/code_descriptors.h" |
10 #include "vm/dart_entry.h" | 10 #include "vm/dart_entry.h" |
(...skipping 203 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
214 DoInstr* store_context = | 214 DoInstr* store_context = |
215 new DoInstr(new StoreContextComp(new UseVal(load_saved_context))); | 215 new DoInstr(new StoreContextComp(new UseVal(load_saved_context))); |
216 AddInstruction(store_context); | 216 AddInstruction(store_context); |
217 } | 217 } |
218 | 218 |
219 | 219 |
220 | 220 |
221 void TestGraphVisitor::ReturnValue(Value* value) { | 221 void TestGraphVisitor::ReturnValue(Value* value) { |
222 if (FLAG_enable_type_checks) { | 222 if (FLAG_enable_type_checks) { |
223 BindInstr* assert_boolean = | 223 BindInstr* assert_boolean = |
224 new BindInstr(new AssertBooleanComp(condition_token_index(), | 224 new BindInstr(new AssertBooleanComp(condition_token_pos(), |
225 owner()->try_index(), | 225 owner()->try_index(), |
226 value)); | 226 value)); |
227 AddInstruction(assert_boolean); | 227 AddInstruction(assert_boolean); |
228 value = new UseVal(assert_boolean); | 228 value = new UseVal(assert_boolean); |
229 } | 229 } |
230 BranchInstr* branch = new BranchInstr(value); | 230 BranchInstr* branch = new BranchInstr(value); |
231 AddInstruction(branch); | 231 AddInstruction(branch); |
232 CloseFragment(); | 232 CloseFragment(); |
233 true_successor_address_ = branch->true_successor_address(); | 233 true_successor_address_ = branch->true_successor_address(); |
234 false_successor_address_ = branch->false_successor_address(); | 234 false_successor_address_ = branch->false_successor_address(); |
(...skipping 27 matching lines...) Expand all Loading... |
262 (kind == RawFunction::kConstImplicitGetter); | 262 (kind == RawFunction::kConstImplicitGetter); |
263 const bool is_static = owner()->parsed_function().function().is_static(); | 263 const bool is_static = owner()->parsed_function().function().is_static(); |
264 // Implicit getters do not need a type check at return, unless they compute | 264 // Implicit getters do not need a type check at return, unless they compute |
265 // the initial value of a static field. | 265 // the initial value of a static field. |
266 if (is_static || !is_implicit_getter) { | 266 if (is_static || !is_implicit_getter) { |
267 const AbstractType& dst_type = | 267 const AbstractType& dst_type = |
268 AbstractType::ZoneHandle( | 268 AbstractType::ZoneHandle( |
269 owner()->parsed_function().function().result_type()); | 269 owner()->parsed_function().function().result_type()); |
270 const String& dst_name = | 270 const String& dst_name = |
271 String::ZoneHandle(String::NewSymbol("function result")); | 271 String::ZoneHandle(String::NewSymbol("function result")); |
272 return_value = BuildAssignableValue(node->value()->token_index(), | 272 return_value = BuildAssignableValue(node->value()->token_pos(), |
273 return_value, | 273 return_value, |
274 dst_type, | 274 dst_type, |
275 dst_name); | 275 dst_name); |
276 } | 276 } |
277 } | 277 } |
278 | 278 |
279 intptr_t current_context_level = owner()->context_level(); | 279 intptr_t current_context_level = owner()->context_level(); |
280 ASSERT(current_context_level >= 0); | 280 ASSERT(current_context_level >= 0); |
281 if (owner()->parsed_function().saved_context_var() != NULL) { | 281 if (owner()->parsed_function().saved_context_var() != NULL) { |
282 // CTX on entry was saved, but not linked as context parent. | 282 // CTX on entry was saved, but not linked as context parent. |
283 BuildLoadContext(*owner()->parsed_function().saved_context_var()); | 283 BuildLoadContext(*owner()->parsed_function().saved_context_var()); |
284 } else { | 284 } else { |
285 while (current_context_level-- > 0) { | 285 while (current_context_level-- > 0) { |
286 UnchainContext(); | 286 UnchainContext(); |
287 } | 287 } |
288 } | 288 } |
289 | 289 |
290 AddInstruction( | 290 AddInstruction( |
291 new ReturnInstr(node->token_index(), return_value)); | 291 new ReturnInstr(node->token_pos(), return_value)); |
292 CloseFragment(); | 292 CloseFragment(); |
293 } | 293 } |
294 | 294 |
295 | 295 |
296 // <Expression> ::= Literal { literal: Instance } | 296 // <Expression> ::= Literal { literal: Instance } |
297 void EffectGraphVisitor::VisitLiteralNode(LiteralNode* node) { | 297 void EffectGraphVisitor::VisitLiteralNode(LiteralNode* node) { |
298 return; | 298 return; |
299 } | 299 } |
300 | 300 |
301 void ValueGraphVisitor::VisitLiteralNode(LiteralNode* node) { | 301 void ValueGraphVisitor::VisitLiteralNode(LiteralNode* node) { |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
387 // dst_name: String } | 387 // dst_name: String } |
388 void EffectGraphVisitor::VisitAssignableNode(AssignableNode* node) { | 388 void EffectGraphVisitor::VisitAssignableNode(AssignableNode* node) { |
389 UNREACHABLE(); | 389 UNREACHABLE(); |
390 } | 390 } |
391 | 391 |
392 | 392 |
393 void ValueGraphVisitor::VisitAssignableNode(AssignableNode* node) { | 393 void ValueGraphVisitor::VisitAssignableNode(AssignableNode* node) { |
394 ValueGraphVisitor for_value(owner(), temp_index()); | 394 ValueGraphVisitor for_value(owner(), temp_index()); |
395 node->expr()->Visit(&for_value); | 395 node->expr()->Visit(&for_value); |
396 Append(for_value); | 396 Append(for_value); |
397 ReturnValue(BuildAssignableValue(node->expr()->token_index(), | 397 ReturnValue(BuildAssignableValue(node->expr()->token_pos(), |
398 for_value.value(), | 398 for_value.value(), |
399 node->type(), | 399 node->type(), |
400 node->dst_name())); | 400 node->dst_name())); |
401 } | 401 } |
402 | 402 |
403 | 403 |
404 // <Expression> :: BinaryOp { kind: Token::Kind | 404 // <Expression> :: BinaryOp { kind: Token::Kind |
405 // left: <Expression> | 405 // left: <Expression> |
406 // right: <Expression> } | 406 // right: <Expression> } |
407 void EffectGraphVisitor::VisitBinaryOpNode(BinaryOpNode* node) { | 407 void EffectGraphVisitor::VisitBinaryOpNode(BinaryOpNode* node) { |
408 // Operators "&&" and "||" cannot be overloaded therefore do not call | 408 // Operators "&&" and "||" cannot be overloaded therefore do not call |
409 // operator. | 409 // operator. |
410 if ((node->kind() == Token::kAND) || (node->kind() == Token::kOR)) { | 410 if ((node->kind() == Token::kAND) || (node->kind() == Token::kOR)) { |
411 // See ValueGraphVisitor::VisitBinaryOpNode. | 411 // See ValueGraphVisitor::VisitBinaryOpNode. |
412 TestGraphVisitor for_left(owner(), | 412 TestGraphVisitor for_left(owner(), |
413 temp_index(), | 413 temp_index(), |
414 node->left()->token_index()); | 414 node->left()->token_pos()); |
415 node->left()->Visit(&for_left); | 415 node->left()->Visit(&for_left); |
416 EffectGraphVisitor for_right(owner(), temp_index()); | 416 EffectGraphVisitor for_right(owner(), temp_index()); |
417 node->right()->Visit(&for_right); | 417 node->right()->Visit(&for_right); |
418 EffectGraphVisitor empty(owner(), temp_index()); | 418 EffectGraphVisitor empty(owner(), temp_index()); |
419 if (node->kind() == Token::kAND) { | 419 if (node->kind() == Token::kAND) { |
420 Join(for_left, for_right, empty); | 420 Join(for_left, for_right, empty); |
421 } else { | 421 } else { |
422 Join(for_left, empty, for_right); | 422 Join(for_left, empty, for_right); |
423 } | 423 } |
424 return; | 424 return; |
425 } | 425 } |
426 ValueGraphVisitor for_left_value(owner(), temp_index()); | 426 ValueGraphVisitor for_left_value(owner(), temp_index()); |
427 node->left()->Visit(&for_left_value); | 427 node->left()->Visit(&for_left_value); |
428 Append(for_left_value); | 428 Append(for_left_value); |
429 ValueGraphVisitor for_right_value(owner(), temp_index()); | 429 ValueGraphVisitor for_right_value(owner(), temp_index()); |
430 node->right()->Visit(&for_right_value); | 430 node->right()->Visit(&for_right_value); |
431 Append(for_right_value); | 431 Append(for_right_value); |
432 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(2); | 432 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(2); |
433 arguments->Add(for_left_value.value()); | 433 arguments->Add(for_left_value.value()); |
434 arguments->Add(for_right_value.value()); | 434 arguments->Add(for_right_value.value()); |
435 const String& name = String::ZoneHandle(String::NewSymbol(node->Name())); | 435 const String& name = String::ZoneHandle(String::NewSymbol(node->Name())); |
436 InstanceCallComp* call = new InstanceCallComp(node->token_index(), | 436 InstanceCallComp* call = new InstanceCallComp(node->token_pos(), |
437 owner()->try_index(), | 437 owner()->try_index(), |
438 name, | 438 name, |
439 node->kind(), | 439 node->kind(), |
440 arguments, | 440 arguments, |
441 Array::ZoneHandle(), | 441 Array::ZoneHandle(), |
442 2); | 442 2); |
443 ReturnComputation(call); | 443 ReturnComputation(call); |
444 } | 444 } |
445 | 445 |
446 | 446 |
447 // Special handling for AND/OR. | 447 // Special handling for AND/OR. |
448 void ValueGraphVisitor::VisitBinaryOpNode(BinaryOpNode* node) { | 448 void ValueGraphVisitor::VisitBinaryOpNode(BinaryOpNode* node) { |
449 // Operators "&&" and "||" cannot be overloaded therefore do not call | 449 // Operators "&&" and "||" cannot be overloaded therefore do not call |
450 // operator. | 450 // operator. |
451 if ((node->kind() == Token::kAND) || (node->kind() == Token::kOR)) { | 451 if ((node->kind() == Token::kAND) || (node->kind() == Token::kOR)) { |
452 // Implement short-circuit logic: do not evaluate right if evaluation | 452 // Implement short-circuit logic: do not evaluate right if evaluation |
453 // of left is sufficient. | 453 // of left is sufficient. |
454 // AND: left ? right === true : false; | 454 // AND: left ? right === true : false; |
455 // OR: left ? true : right === true; | 455 // OR: left ? true : right === true; |
456 const Bool& bool_true = Bool::ZoneHandle(Bool::True()); | 456 const Bool& bool_true = Bool::ZoneHandle(Bool::True()); |
457 const Bool& bool_false = Bool::ZoneHandle(Bool::False()); | 457 const Bool& bool_false = Bool::ZoneHandle(Bool::False()); |
458 | 458 |
459 TestGraphVisitor for_test(owner(), | 459 TestGraphVisitor for_test(owner(), |
460 temp_index(), | 460 temp_index(), |
461 node->left()->token_index()); | 461 node->left()->token_pos()); |
462 node->left()->Visit(&for_test); | 462 node->left()->Visit(&for_test); |
463 | 463 |
464 ValueGraphVisitor for_right(owner(), temp_index()); | 464 ValueGraphVisitor for_right(owner(), temp_index()); |
465 node->right()->Visit(&for_right); | 465 node->right()->Visit(&for_right); |
466 Value* right_value = for_right.value(); | 466 Value* right_value = for_right.value(); |
467 if (FLAG_enable_type_checks) { | 467 if (FLAG_enable_type_checks) { |
468 BindInstr* assert_boolean = | 468 BindInstr* assert_boolean = |
469 new BindInstr(new AssertBooleanComp(node->right()->token_index(), | 469 new BindInstr(new AssertBooleanComp(node->right()->token_pos(), |
470 owner()->try_index(), | 470 owner()->try_index(), |
471 right_value)); | 471 right_value)); |
472 for_right.AddInstruction(assert_boolean); | 472 for_right.AddInstruction(assert_boolean); |
473 right_value = new UseVal(assert_boolean); | 473 right_value = new UseVal(assert_boolean); |
474 } | 474 } |
475 BindInstr* constant_true = new BindInstr(new ConstantVal(bool_true)); | 475 BindInstr* constant_true = new BindInstr(new ConstantVal(bool_true)); |
476 for_right.AddInstruction(constant_true); | 476 for_right.AddInstruction(constant_true); |
477 BindInstr* comp = | 477 BindInstr* comp = |
478 new BindInstr(new StrictCompareComp(Token::kEQ_STRICT, | 478 new BindInstr(new StrictCompareComp(Token::kEQ_STRICT, |
479 right_value, | 479 right_value, |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
569 break; | 569 break; |
570 } | 570 } |
571 } | 571 } |
572 if (compile_time_interpolation) { | 572 if (compile_time_interpolation) { |
573 // Not needed for effect, only for value | 573 // Not needed for effect, only for value |
574 CompiletimeStringInterpolation(interpol_func, literals); | 574 CompiletimeStringInterpolation(interpol_func, literals); |
575 return; | 575 return; |
576 } | 576 } |
577 // Runtime string interpolation. | 577 // Runtime string interpolation. |
578 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(); | 578 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(); |
579 ArgumentListNode* interpol_arg = new ArgumentListNode(node->token_index()); | 579 ArgumentListNode* interpol_arg = new ArgumentListNode(node->token_pos()); |
580 interpol_arg->Add(node->values()); | 580 interpol_arg->Add(node->values()); |
581 TranslateArgumentList(*interpol_arg, values); | 581 TranslateArgumentList(*interpol_arg, values); |
582 StaticCallComp* call = | 582 StaticCallComp* call = |
583 new StaticCallComp(node->token_index(), | 583 new StaticCallComp(node->token_pos(), |
584 owner()->try_index(), | 584 owner()->try_index(), |
585 interpol_func, | 585 interpol_func, |
586 interpol_arg->names(), | 586 interpol_arg->names(), |
587 values); | 587 values); |
588 ReturnComputation(call); | 588 ReturnComputation(call); |
589 } | 589 } |
590 | 590 |
591 | 591 |
592 void EffectGraphVisitor::BuildTypecheckArguments( | 592 void EffectGraphVisitor::BuildTypecheckArguments( |
593 intptr_t token_index, | 593 intptr_t token_pos, |
594 Value** instantiator_result, | 594 Value** instantiator_result, |
595 Value** instantiator_type_arguments_result) { | 595 Value** instantiator_type_arguments_result) { |
596 Value* instantiator = NULL; | 596 Value* instantiator = NULL; |
597 Value* instantiator_type_arguments = NULL; | 597 Value* instantiator_type_arguments = NULL; |
598 const Class& instantiator_class = Class::Handle( | 598 const Class& instantiator_class = Class::Handle( |
599 owner()->parsed_function().function().owner()); | 599 owner()->parsed_function().function().owner()); |
600 // Since called only when type tested against is not instantiated. | 600 // Since called only when type tested against is not instantiated. |
601 ASSERT(instantiator_class.NumTypeParameters() > 0); | 601 ASSERT(instantiator_class.NumTypeParameters() > 0); |
602 instantiator = BuildInstantiator(); | 602 instantiator = BuildInstantiator(); |
603 if (instantiator == NULL) { | 603 if (instantiator == NULL) { |
604 // No instantiator when inside factory. | 604 // No instantiator when inside factory. |
605 instantiator = BuildNullValue(); | 605 instantiator = BuildNullValue(); |
606 instantiator_type_arguments = | 606 instantiator_type_arguments = |
607 BuildInstantiatorTypeArguments(token_index, NULL); | 607 BuildInstantiatorTypeArguments(token_pos, NULL); |
608 } else { | 608 } else { |
609 // Preserve instantiator. | 609 // Preserve instantiator. |
610 const LocalVariable& expr_temp = | 610 const LocalVariable& expr_temp = |
611 *owner()->parsed_function().expression_temp_var(); | 611 *owner()->parsed_function().expression_temp_var(); |
612 BindInstr* saved = | 612 BindInstr* saved = |
613 new BindInstr(BuildStoreLocal(expr_temp, instantiator)); | 613 new BindInstr(BuildStoreLocal(expr_temp, instantiator)); |
614 AddInstruction(saved); | 614 AddInstruction(saved); |
615 instantiator = new UseVal(saved); | 615 instantiator = new UseVal(saved); |
616 BindInstr* loaded = new BindInstr(BuildLoadLocal(expr_temp)); | 616 BindInstr* loaded = new BindInstr(BuildLoadLocal(expr_temp)); |
617 AddInstruction(loaded); | 617 AddInstruction(loaded); |
618 instantiator_type_arguments = | 618 instantiator_type_arguments = |
619 BuildInstantiatorTypeArguments(token_index, new UseVal(loaded)); | 619 BuildInstantiatorTypeArguments(token_pos, new UseVal(loaded)); |
620 } | 620 } |
621 *instantiator_result = instantiator; | 621 *instantiator_result = instantiator; |
622 *instantiator_type_arguments_result = instantiator_type_arguments; | 622 *instantiator_type_arguments_result = instantiator_type_arguments; |
623 } | 623 } |
624 | 624 |
625 | 625 |
626 Value* EffectGraphVisitor::BuildNullValue() { | 626 Value* EffectGraphVisitor::BuildNullValue() { |
627 BindInstr* instr = new BindInstr(new ConstantVal(Object::ZoneHandle())); | 627 BindInstr* instr = new BindInstr(new ConstantVal(Object::ZoneHandle())); |
628 AddInstruction(instr); | 628 AddInstruction(instr); |
629 return new UseVal(instr); | 629 return new UseVal(instr); |
630 } | 630 } |
631 | 631 |
632 | 632 |
633 // Used for testing incoming arguments. | 633 // Used for testing incoming arguments. |
634 AssertAssignableComp* EffectGraphVisitor::BuildAssertAssignable( | 634 AssertAssignableComp* EffectGraphVisitor::BuildAssertAssignable( |
635 intptr_t token_index, | 635 intptr_t token_pos, |
636 Value* value, | 636 Value* value, |
637 const AbstractType& dst_type, | 637 const AbstractType& dst_type, |
638 const String& dst_name) { | 638 const String& dst_name) { |
639 // Build the type check computation. | 639 // Build the type check computation. |
640 Value* instantiator = NULL; | 640 Value* instantiator = NULL; |
641 Value* instantiator_type_arguments = NULL; | 641 Value* instantiator_type_arguments = NULL; |
642 if (dst_type.IsInstantiated()) { | 642 if (dst_type.IsInstantiated()) { |
643 instantiator = BuildNullValue(); | 643 instantiator = BuildNullValue(); |
644 instantiator_type_arguments = BuildNullValue(); | 644 instantiator_type_arguments = BuildNullValue(); |
645 } else { | 645 } else { |
646 BuildTypecheckArguments(token_index, | 646 BuildTypecheckArguments(token_pos, |
647 &instantiator, | 647 &instantiator, |
648 &instantiator_type_arguments); | 648 &instantiator_type_arguments); |
649 } | 649 } |
650 return new AssertAssignableComp(token_index, | 650 return new AssertAssignableComp(token_pos, |
651 owner()->try_index(), | 651 owner()->try_index(), |
652 value, | 652 value, |
653 instantiator, | 653 instantiator, |
654 instantiator_type_arguments, | 654 instantiator_type_arguments, |
655 dst_type, | 655 dst_type, |
656 dst_name); | 656 dst_name); |
657 } | 657 } |
658 | 658 |
659 | 659 |
660 // Used to to test assignments. | 660 // Used to to test assignments. |
661 Value* EffectGraphVisitor::BuildAssignableValue(intptr_t token_index, | 661 Value* EffectGraphVisitor::BuildAssignableValue(intptr_t token_pos, |
662 Value* value, | 662 Value* value, |
663 const AbstractType& dst_type, | 663 const AbstractType& dst_type, |
664 const String& dst_name) { | 664 const String& dst_name) { |
665 if (CanSkipTypeCheck(value, dst_type)) { | 665 if (CanSkipTypeCheck(value, dst_type)) { |
666 return value; | 666 return value; |
667 } | 667 } |
668 AssertAssignableComp* comp = BuildAssertAssignable(token_index, | 668 AssertAssignableComp* comp = BuildAssertAssignable(token_pos, |
669 value, | 669 value, |
670 dst_type, | 670 dst_type, |
671 dst_name); | 671 dst_name); |
672 BindInstr* assert_assignable = new BindInstr(comp); | 672 BindInstr* assert_assignable = new BindInstr(comp); |
673 AddInstruction(assert_assignable); | 673 AddInstruction(assert_assignable); |
674 return new UseVal(assert_assignable); | 674 return new UseVal(assert_assignable); |
675 } | 675 } |
676 | 676 |
677 | 677 |
678 void EffectGraphVisitor::BuildInstanceOf(ComparisonNode* node) { | 678 void EffectGraphVisitor::BuildInstanceOf(ComparisonNode* node) { |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
734 | 734 |
735 ValueGraphVisitor for_left_value(owner(), temp_index()); | 735 ValueGraphVisitor for_left_value(owner(), temp_index()); |
736 node->left()->Visit(&for_left_value); | 736 node->left()->Visit(&for_left_value); |
737 Append(for_left_value); | 737 Append(for_left_value); |
738 Value* instantiator = NULL; | 738 Value* instantiator = NULL; |
739 Value* instantiator_type_arguments = NULL; | 739 Value* instantiator_type_arguments = NULL; |
740 if (type.IsInstantiated()) { | 740 if (type.IsInstantiated()) { |
741 instantiator = BuildNullValue(); | 741 instantiator = BuildNullValue(); |
742 instantiator_type_arguments = BuildNullValue(); | 742 instantiator_type_arguments = BuildNullValue(); |
743 } else { | 743 } else { |
744 BuildTypecheckArguments(node->token_index(), | 744 BuildTypecheckArguments(node->token_pos(), |
745 &instantiator, | 745 &instantiator, |
746 &instantiator_type_arguments); | 746 &instantiator_type_arguments); |
747 } | 747 } |
748 InstanceOfComp* instance_of = | 748 InstanceOfComp* instance_of = |
749 new InstanceOfComp(node->token_index(), | 749 new InstanceOfComp(node->token_pos(), |
750 owner()->try_index(), | 750 owner()->try_index(), |
751 for_left_value.value(), | 751 for_left_value.value(), |
752 instantiator, | 752 instantiator, |
753 instantiator_type_arguments, | 753 instantiator_type_arguments, |
754 node->right()->AsTypeNode()->type(), | 754 node->right()->AsTypeNode()->type(), |
755 (node->kind() == Token::kISNOT)); | 755 (node->kind() == Token::kISNOT)); |
756 ReturnComputation(instance_of); | 756 ReturnComputation(instance_of); |
757 } | 757 } |
758 | 758 |
759 | 759 |
(...skipping 21 matching lines...) Expand all Loading... |
781 } | 781 } |
782 | 782 |
783 if ((node->kind() == Token::kEQ) || (node->kind() == Token::kNE)) { | 783 if ((node->kind() == Token::kEQ) || (node->kind() == Token::kNE)) { |
784 ValueGraphVisitor for_left_value(owner(), temp_index()); | 784 ValueGraphVisitor for_left_value(owner(), temp_index()); |
785 node->left()->Visit(&for_left_value); | 785 node->left()->Visit(&for_left_value); |
786 Append(for_left_value); | 786 Append(for_left_value); |
787 ValueGraphVisitor for_right_value(owner(), temp_index()); | 787 ValueGraphVisitor for_right_value(owner(), temp_index()); |
788 node->right()->Visit(&for_right_value); | 788 node->right()->Visit(&for_right_value); |
789 Append(for_right_value); | 789 Append(for_right_value); |
790 EqualityCompareComp* comp = new EqualityCompareComp( | 790 EqualityCompareComp* comp = new EqualityCompareComp( |
791 node->token_index(), owner()->try_index(), | 791 node->token_pos(), owner()->try_index(), |
792 for_left_value.value(), for_right_value.value()); | 792 for_left_value.value(), for_right_value.value()); |
793 if (node->kind() == Token::kEQ) { | 793 if (node->kind() == Token::kEQ) { |
794 ReturnComputation(comp); | 794 ReturnComputation(comp); |
795 } else { | 795 } else { |
796 BindInstr* eq_result = new BindInstr(comp); | 796 BindInstr* eq_result = new BindInstr(comp); |
797 AddInstruction(eq_result); | 797 AddInstruction(eq_result); |
798 if (FLAG_enable_type_checks) { | 798 if (FLAG_enable_type_checks) { |
799 eq_result = | 799 eq_result = |
800 new BindInstr(new AssertBooleanComp(node->token_index(), | 800 new BindInstr(new AssertBooleanComp(node->token_pos(), |
801 owner()->try_index(), | 801 owner()->try_index(), |
802 new UseVal(eq_result))); | 802 new UseVal(eq_result))); |
803 AddInstruction(eq_result); | 803 AddInstruction(eq_result); |
804 } | 804 } |
805 BooleanNegateComp* negate = new BooleanNegateComp(new UseVal(eq_result)); | 805 BooleanNegateComp* negate = new BooleanNegateComp(new UseVal(eq_result)); |
806 ReturnComputation(negate); | 806 ReturnComputation(negate); |
807 } | 807 } |
808 return; | 808 return; |
809 } | 809 } |
810 | 810 |
811 ValueGraphVisitor for_left_value(owner(), temp_index()); | 811 ValueGraphVisitor for_left_value(owner(), temp_index()); |
812 node->left()->Visit(&for_left_value); | 812 node->left()->Visit(&for_left_value); |
813 Append(for_left_value); | 813 Append(for_left_value); |
814 ValueGraphVisitor for_right_value(owner(), temp_index()); | 814 ValueGraphVisitor for_right_value(owner(), temp_index()); |
815 node->right()->Visit(&for_right_value); | 815 node->right()->Visit(&for_right_value); |
816 Append(for_right_value); | 816 Append(for_right_value); |
817 RelationalOpComp* comp = new RelationalOpComp(node->token_index(), | 817 RelationalOpComp* comp = new RelationalOpComp(node->token_pos(), |
818 owner()->try_index(), | 818 owner()->try_index(), |
819 node->kind(), | 819 node->kind(), |
820 for_left_value.value(), | 820 for_left_value.value(), |
821 for_right_value.value()); | 821 for_right_value.value()); |
822 ReturnComputation(comp); | 822 ReturnComputation(comp); |
823 } | 823 } |
824 | 824 |
825 | 825 |
826 void EffectGraphVisitor::VisitUnaryOpNode(UnaryOpNode* node) { | 826 void EffectGraphVisitor::VisitUnaryOpNode(UnaryOpNode* node) { |
827 // "!" cannot be overloaded, therefore do not call operator. | 827 // "!" cannot be overloaded, therefore do not call operator. |
828 if (node->kind() == Token::kNOT) { | 828 if (node->kind() == Token::kNOT) { |
829 ValueGraphVisitor for_value(owner(), temp_index()); | 829 ValueGraphVisitor for_value(owner(), temp_index()); |
830 node->operand()->Visit(&for_value); | 830 node->operand()->Visit(&for_value); |
831 Append(for_value); | 831 Append(for_value); |
832 Value* value = for_value.value(); | 832 Value* value = for_value.value(); |
833 if (FLAG_enable_type_checks) { | 833 if (FLAG_enable_type_checks) { |
834 BindInstr* assert_boolean = | 834 BindInstr* assert_boolean = |
835 new BindInstr(new AssertBooleanComp(node->operand()->token_index(), | 835 new BindInstr(new AssertBooleanComp(node->operand()->token_pos(), |
836 owner()->try_index(), | 836 owner()->try_index(), |
837 value)); | 837 value)); |
838 AddInstruction(assert_boolean); | 838 AddInstruction(assert_boolean); |
839 value = new UseVal(assert_boolean); | 839 value = new UseVal(assert_boolean); |
840 } | 840 } |
841 BooleanNegateComp* negate = new BooleanNegateComp(value); | 841 BooleanNegateComp* negate = new BooleanNegateComp(value); |
842 ReturnComputation(negate); | 842 ReturnComputation(negate); |
843 return; | 843 return; |
844 } | 844 } |
845 ValueGraphVisitor for_value(owner(), temp_index()); | 845 ValueGraphVisitor for_value(owner(), temp_index()); |
846 node->operand()->Visit(&for_value); | 846 node->operand()->Visit(&for_value); |
847 Append(for_value); | 847 Append(for_value); |
848 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(1); | 848 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(1); |
849 arguments->Add(for_value.value()); | 849 arguments->Add(for_value.value()); |
850 Token::Kind token_kind = | 850 Token::Kind token_kind = |
851 (node->kind() == Token::kSUB) ? Token::kNEGATE : node->kind(); | 851 (node->kind() == Token::kSUB) ? Token::kNEGATE : node->kind(); |
852 | 852 |
853 const String& name = | 853 const String& name = |
854 String::ZoneHandle(String::NewSymbol(Token::Str(token_kind))); | 854 String::ZoneHandle(String::NewSymbol(Token::Str(token_kind))); |
855 InstanceCallComp* call = new InstanceCallComp( | 855 InstanceCallComp* call = new InstanceCallComp( |
856 node->token_index(), owner()->try_index(), name, token_kind, | 856 node->token_pos(), owner()->try_index(), name, token_kind, |
857 arguments, Array::ZoneHandle(), 1); | 857 arguments, Array::ZoneHandle(), 1); |
858 ReturnComputation(call); | 858 ReturnComputation(call); |
859 } | 859 } |
860 | 860 |
861 | 861 |
862 void EffectGraphVisitor::VisitConditionalExprNode(ConditionalExprNode* node) { | 862 void EffectGraphVisitor::VisitConditionalExprNode(ConditionalExprNode* node) { |
863 TestGraphVisitor for_test(owner(), | 863 TestGraphVisitor for_test(owner(), |
864 temp_index(), | 864 temp_index(), |
865 node->condition()->token_index()); | 865 node->condition()->token_pos()); |
866 node->condition()->Visit(&for_test); | 866 node->condition()->Visit(&for_test); |
867 | 867 |
868 // Translate the subexpressions for their effects. | 868 // Translate the subexpressions for their effects. |
869 EffectGraphVisitor for_true(owner(), temp_index()); | 869 EffectGraphVisitor for_true(owner(), temp_index()); |
870 node->true_expr()->Visit(&for_true); | 870 node->true_expr()->Visit(&for_true); |
871 EffectGraphVisitor for_false(owner(), temp_index()); | 871 EffectGraphVisitor for_false(owner(), temp_index()); |
872 node->false_expr()->Visit(&for_false); | 872 node->false_expr()->Visit(&for_false); |
873 | 873 |
874 Join(for_test, for_true, for_false); | 874 Join(for_test, for_true, for_false); |
875 } | 875 } |
876 | 876 |
877 | 877 |
878 void ValueGraphVisitor::VisitConditionalExprNode(ConditionalExprNode* node) { | 878 void ValueGraphVisitor::VisitConditionalExprNode(ConditionalExprNode* node) { |
879 TestGraphVisitor for_test(owner(), | 879 TestGraphVisitor for_test(owner(), |
880 temp_index(), | 880 temp_index(), |
881 node->condition()->token_index()); | 881 node->condition()->token_pos()); |
882 node->condition()->Visit(&for_test); | 882 node->condition()->Visit(&for_test); |
883 | 883 |
884 ValueGraphVisitor for_true(owner(), temp_index()); | 884 ValueGraphVisitor for_true(owner(), temp_index()); |
885 node->true_expr()->Visit(&for_true); | 885 node->true_expr()->Visit(&for_true); |
886 ASSERT(for_true.is_open()); | 886 ASSERT(for_true.is_open()); |
887 for_true.AddInstruction(new DoInstr(BuildStoreLocal( | 887 for_true.AddInstruction(new DoInstr(BuildStoreLocal( |
888 *owner()->parsed_function().expression_temp_var(), for_true.value()))); | 888 *owner()->parsed_function().expression_temp_var(), for_true.value()))); |
889 | 889 |
890 ValueGraphVisitor for_false(owner(), temp_index()); | 890 ValueGraphVisitor for_false(owner(), temp_index()); |
891 node->false_expr()->Visit(&for_false); | 891 node->false_expr()->Visit(&for_false); |
892 ASSERT(for_false.is_open()); | 892 ASSERT(for_false.is_open()); |
893 for_false.AddInstruction(new DoInstr(BuildStoreLocal( | 893 for_false.AddInstruction(new DoInstr(BuildStoreLocal( |
894 *owner()->parsed_function().expression_temp_var(), for_false.value()))); | 894 *owner()->parsed_function().expression_temp_var(), for_false.value()))); |
895 | 895 |
896 Join(for_test, for_true, for_false); | 896 Join(for_test, for_true, for_false); |
897 ReturnComputation( | 897 ReturnComputation( |
898 BuildLoadLocal(*owner()->parsed_function().expression_temp_var())); | 898 BuildLoadLocal(*owner()->parsed_function().expression_temp_var())); |
899 } | 899 } |
900 | 900 |
901 | 901 |
902 // <Statement> ::= If { condition: <Expression> | 902 // <Statement> ::= If { condition: <Expression> |
903 // true_branch: <Sequence> | 903 // true_branch: <Sequence> |
904 // false_branch: <Sequence> } | 904 // false_branch: <Sequence> } |
905 void EffectGraphVisitor::VisitIfNode(IfNode* node) { | 905 void EffectGraphVisitor::VisitIfNode(IfNode* node) { |
906 TestGraphVisitor for_test(owner(), | 906 TestGraphVisitor for_test(owner(), |
907 temp_index(), | 907 temp_index(), |
908 node->condition()->token_index()); | 908 node->condition()->token_pos()); |
909 node->condition()->Visit(&for_test); | 909 node->condition()->Visit(&for_test); |
910 | 910 |
911 EffectGraphVisitor for_true(owner(), temp_index()); | 911 EffectGraphVisitor for_true(owner(), temp_index()); |
912 EffectGraphVisitor for_false(owner(), temp_index()); | 912 EffectGraphVisitor for_false(owner(), temp_index()); |
913 | 913 |
914 node->true_branch()->Visit(&for_true); | 914 node->true_branch()->Visit(&for_true); |
915 // The for_false graph fragment will be empty (default graph fragment) if | 915 // The for_false graph fragment will be empty (default graph fragment) if |
916 // we do not call Visit. | 916 // we do not call Visit. |
917 if (node->false_branch() != NULL) node->false_branch()->Visit(&for_false); | 917 if (node->false_branch() != NULL) node->false_branch()->Visit(&for_false); |
918 Join(for_test, for_true, for_false); | 918 Join(for_test, for_true, for_false); |
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
988 | 988 |
989 // Generate instructions for all case expressions and collect data to | 989 // Generate instructions for all case expressions and collect data to |
990 // connect them. | 990 // connect them. |
991 GrowableArray<TargetEntryInstr**> case_true_addresses; | 991 GrowableArray<TargetEntryInstr**> case_true_addresses; |
992 GrowableArray<TargetEntryInstr**> case_false_addresses; | 992 GrowableArray<TargetEntryInstr**> case_false_addresses; |
993 GrowableArray<TargetEntryInstr*> case_entries; | 993 GrowableArray<TargetEntryInstr*> case_entries; |
994 for (intptr_t i = 0; i < len; i++) { | 994 for (intptr_t i = 0; i < len; i++) { |
995 AstNode* case_expr = node->case_expressions()->NodeAt(i); | 995 AstNode* case_expr = node->case_expressions()->NodeAt(i); |
996 TestGraphVisitor for_case_expression(owner(), | 996 TestGraphVisitor for_case_expression(owner(), |
997 temp_index(), | 997 temp_index(), |
998 case_expr->token_index()); | 998 case_expr->token_pos()); |
999 if (i == 0) { | 999 if (i == 0) { |
1000 case_entries.Add(NULL); // Not to be used | 1000 case_entries.Add(NULL); // Not to be used |
1001 case_expr->Visit(&for_case_expression); | 1001 case_expr->Visit(&for_case_expression); |
1002 // Append only the first one, everything else is connected from it. | 1002 // Append only the first one, everything else is connected from it. |
1003 Append(for_case_expression); | 1003 Append(for_case_expression); |
1004 } else { | 1004 } else { |
1005 TargetEntryInstr* case_entry_target = new TargetEntryInstr(); | 1005 TargetEntryInstr* case_entry_target = new TargetEntryInstr(); |
1006 case_entries.Add(case_entry_target); | 1006 case_entries.Add(case_entry_target); |
1007 for_case_expression.AddInstruction(case_entry_target); | 1007 for_case_expression.AddInstruction(case_entry_target); |
1008 case_expr->Visit(&for_case_expression); | 1008 case_expr->Visit(&for_case_expression); |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1070 // a) continue-join (optional) | 1070 // a) continue-join (optional) |
1071 // b) loop-join | 1071 // b) loop-join |
1072 // c) [ test ] -> (body-entry-target, loop-exit-target) | 1072 // c) [ test ] -> (body-entry-target, loop-exit-target) |
1073 // d) body-entry-target | 1073 // d) body-entry-target |
1074 // e) [ body ] -> (loop-join) | 1074 // e) [ body ] -> (loop-join) |
1075 // f) loop-exit-target | 1075 // f) loop-exit-target |
1076 // g) break-join (optional) | 1076 // g) break-join (optional) |
1077 void EffectGraphVisitor::VisitWhileNode(WhileNode* node) { | 1077 void EffectGraphVisitor::VisitWhileNode(WhileNode* node) { |
1078 TestGraphVisitor for_test(owner(), | 1078 TestGraphVisitor for_test(owner(), |
1079 temp_index(), | 1079 temp_index(), |
1080 node->condition()->token_index()); | 1080 node->condition()->token_pos()); |
1081 node->condition()->Visit(&for_test); | 1081 node->condition()->Visit(&for_test); |
1082 ASSERT(!for_test.is_empty()); // Language spec. | 1082 ASSERT(!for_test.is_empty()); // Language spec. |
1083 | 1083 |
1084 EffectGraphVisitor for_body(owner(), temp_index()); | 1084 EffectGraphVisitor for_body(owner(), temp_index()); |
1085 CheckStackOverflowComp* comp = | 1085 CheckStackOverflowComp* comp = |
1086 new CheckStackOverflowComp(node->token_index(), owner()->try_index()); | 1086 new CheckStackOverflowComp(node->token_pos(), owner()->try_index()); |
1087 for_body.AddInstruction(new DoInstr(comp)); | 1087 for_body.AddInstruction(new DoInstr(comp)); |
1088 node->body()->Visit(&for_body); | 1088 node->body()->Visit(&for_body); |
1089 | 1089 |
1090 // Labels are set after body traversal. | 1090 // Labels are set after body traversal. |
1091 SourceLabel* lbl = node->label(); | 1091 SourceLabel* lbl = node->label(); |
1092 ASSERT(lbl != NULL); | 1092 ASSERT(lbl != NULL); |
1093 if (lbl->join_for_continue() != NULL) { | 1093 if (lbl->join_for_continue() != NULL) { |
1094 AddInstruction(lbl->join_for_continue()); | 1094 AddInstruction(lbl->join_for_continue()); |
1095 } | 1095 } |
1096 TieLoop(for_test, for_body); | 1096 TieLoop(for_test, for_body); |
1097 if (lbl->join_for_break() != NULL) { | 1097 if (lbl->join_for_break() != NULL) { |
1098 AddInstruction(lbl->join_for_break()); | 1098 AddInstruction(lbl->join_for_break()); |
1099 } | 1099 } |
1100 } | 1100 } |
1101 | 1101 |
1102 | 1102 |
1103 // The fragment is composed as follows: | 1103 // The fragment is composed as follows: |
1104 // a) body-entry-join | 1104 // a) body-entry-join |
1105 // b) [ body ] | 1105 // b) [ body ] |
1106 // c) test-entry (continue-join or body-exit-target) | 1106 // c) test-entry (continue-join or body-exit-target) |
1107 // d) [ test-entry ] -> (back-target, loop-exit-target) | 1107 // d) [ test-entry ] -> (back-target, loop-exit-target) |
1108 // e) back-target -> (body-entry-join) | 1108 // e) back-target -> (body-entry-join) |
1109 // f) loop-exit-target | 1109 // f) loop-exit-target |
1110 // g) break-join | 1110 // g) break-join |
1111 void EffectGraphVisitor::VisitDoWhileNode(DoWhileNode* node) { | 1111 void EffectGraphVisitor::VisitDoWhileNode(DoWhileNode* node) { |
1112 // Traverse body first in order to generate continue and break labels. | 1112 // Traverse body first in order to generate continue and break labels. |
1113 EffectGraphVisitor for_body(owner(), temp_index()); | 1113 EffectGraphVisitor for_body(owner(), temp_index()); |
1114 CheckStackOverflowComp* comp = | 1114 CheckStackOverflowComp* comp = |
1115 new CheckStackOverflowComp(node->token_index(), owner()->try_index()); | 1115 new CheckStackOverflowComp(node->token_pos(), owner()->try_index()); |
1116 for_body.AddInstruction(new DoInstr(comp)); | 1116 for_body.AddInstruction(new DoInstr(comp)); |
1117 node->body()->Visit(&for_body); | 1117 node->body()->Visit(&for_body); |
1118 | 1118 |
1119 TestGraphVisitor for_test(owner(), | 1119 TestGraphVisitor for_test(owner(), |
1120 temp_index(), | 1120 temp_index(), |
1121 node->condition()->token_index()); | 1121 node->condition()->token_pos()); |
1122 node->condition()->Visit(&for_test); | 1122 node->condition()->Visit(&for_test); |
1123 ASSERT(is_open()); | 1123 ASSERT(is_open()); |
1124 | 1124 |
1125 // Tie do-while loop (test is after the body). | 1125 // Tie do-while loop (test is after the body). |
1126 JoinEntryInstr* body_entry_join = new JoinEntryInstr(); | 1126 JoinEntryInstr* body_entry_join = new JoinEntryInstr(); |
1127 AddInstruction(body_entry_join); | 1127 AddInstruction(body_entry_join); |
1128 body_entry_join->SetSuccessor(for_body.entry()); | 1128 body_entry_join->SetSuccessor(for_body.entry()); |
1129 Instruction* body_exit = | 1129 Instruction* body_exit = |
1130 for_body.is_empty() ? body_entry_join : for_body.exit(); | 1130 for_body.is_empty() ? body_entry_join : for_body.exit(); |
1131 | 1131 |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1172 EffectGraphVisitor for_initializer(owner(), temp_index()); | 1172 EffectGraphVisitor for_initializer(owner(), temp_index()); |
1173 node->initializer()->Visit(&for_initializer); | 1173 node->initializer()->Visit(&for_initializer); |
1174 Append(for_initializer); | 1174 Append(for_initializer); |
1175 ASSERT(is_open()); | 1175 ASSERT(is_open()); |
1176 | 1176 |
1177 // Compose body to set any jump labels. | 1177 // Compose body to set any jump labels. |
1178 EffectGraphVisitor for_body(owner(), temp_index()); | 1178 EffectGraphVisitor for_body(owner(), temp_index()); |
1179 TargetEntryInstr* body_entry = new TargetEntryInstr(); | 1179 TargetEntryInstr* body_entry = new TargetEntryInstr(); |
1180 for_body.AddInstruction(body_entry); | 1180 for_body.AddInstruction(body_entry); |
1181 CheckStackOverflowComp* comp = | 1181 CheckStackOverflowComp* comp = |
1182 new CheckStackOverflowComp(node->token_index(), owner()->try_index()); | 1182 new CheckStackOverflowComp(node->token_pos(), owner()->try_index()); |
1183 for_body.AddInstruction(new DoInstr(comp)); | 1183 for_body.AddInstruction(new DoInstr(comp)); |
1184 node->body()->Visit(&for_body); | 1184 node->body()->Visit(&for_body); |
1185 | 1185 |
1186 // Join loop body, increment and compute their end instruction. | 1186 // Join loop body, increment and compute their end instruction. |
1187 ASSERT(!for_body.is_empty()); | 1187 ASSERT(!for_body.is_empty()); |
1188 Instruction* loop_increment_end = NULL; | 1188 Instruction* loop_increment_end = NULL; |
1189 EffectGraphVisitor for_increment(owner(), temp_index()); | 1189 EffectGraphVisitor for_increment(owner(), temp_index()); |
1190 if ((node->label()->join_for_continue() == NULL) && for_body.is_open()) { | 1190 if ((node->label()->join_for_continue() == NULL) && for_body.is_open()) { |
1191 // Do not insert an extra basic block. | 1191 // Do not insert an extra basic block. |
1192 node->increment()->Visit(&for_increment); | 1192 node->increment()->Visit(&for_increment); |
(...skipping 29 matching lines...) Expand all Loading... |
1222 if (node->label()->join_for_break() == NULL) { | 1222 if (node->label()->join_for_break() == NULL) { |
1223 CloseFragment(); | 1223 CloseFragment(); |
1224 } else { | 1224 } else { |
1225 // Control flow of ForLoop continues into join_for_break. | 1225 // Control flow of ForLoop continues into join_for_break. |
1226 exit_ = node->label()->join_for_break(); | 1226 exit_ = node->label()->join_for_break(); |
1227 } | 1227 } |
1228 } else { | 1228 } else { |
1229 TargetEntryInstr* loop_exit = new TargetEntryInstr(); | 1229 TargetEntryInstr* loop_exit = new TargetEntryInstr(); |
1230 TestGraphVisitor for_test(owner(), | 1230 TestGraphVisitor for_test(owner(), |
1231 temp_index(), | 1231 temp_index(), |
1232 node->condition()->token_index()); | 1232 node->condition()->token_pos()); |
1233 node->condition()->Visit(&for_test); | 1233 node->condition()->Visit(&for_test); |
1234 Append(for_test); | 1234 Append(for_test); |
1235 *for_test.true_successor_address() = body_entry; | 1235 *for_test.true_successor_address() = body_entry; |
1236 *for_test.false_successor_address() = loop_exit; | 1236 *for_test.false_successor_address() = loop_exit; |
1237 if (node->label()->join_for_break() == NULL) { | 1237 if (node->label()->join_for_break() == NULL) { |
1238 exit_ = loop_exit; | 1238 exit_ = loop_exit; |
1239 } else { | 1239 } else { |
1240 loop_exit->SetSuccessor(node->label()->join_for_break()); | 1240 loop_exit->SetSuccessor(node->label()->join_for_break()); |
1241 exit_ = node->label()->join_for_break(); | 1241 exit_ = node->label()->join_for_break(); |
1242 } | 1242 } |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1306 // Translate the array elements and collect their values. | 1306 // Translate the array elements and collect their values. |
1307 ZoneGrowableArray<Value*>* values = | 1307 ZoneGrowableArray<Value*>* values = |
1308 new ZoneGrowableArray<Value*>(node->length()); | 1308 new ZoneGrowableArray<Value*>(node->length()); |
1309 for (int i = 0; i < node->length(); ++i) { | 1309 for (int i = 0; i < node->length(); ++i) { |
1310 ValueGraphVisitor for_value(owner(), temp_index()); | 1310 ValueGraphVisitor for_value(owner(), temp_index()); |
1311 node->ElementAt(i)->Visit(&for_value); | 1311 node->ElementAt(i)->Visit(&for_value); |
1312 Append(for_value); | 1312 Append(for_value); |
1313 values->Add(for_value.value()); | 1313 values->Add(for_value.value()); |
1314 } | 1314 } |
1315 Value* element_type = new UseVal( | 1315 Value* element_type = new UseVal( |
1316 BuildInstantiatedTypeArguments(node->token_index(), | 1316 BuildInstantiatedTypeArguments(node->token_pos(), |
1317 node->type_arguments())); | 1317 node->type_arguments())); |
1318 CreateArrayComp* create = new CreateArrayComp(node->token_index(), | 1318 CreateArrayComp* create = new CreateArrayComp(node->token_pos(), |
1319 owner()->try_index(), | 1319 owner()->try_index(), |
1320 values, | 1320 values, |
1321 element_type); | 1321 element_type); |
1322 ReturnComputation(create); | 1322 ReturnComputation(create); |
1323 } | 1323 } |
1324 | 1324 |
1325 | 1325 |
1326 void EffectGraphVisitor::VisitClosureNode(ClosureNode* node) { | 1326 void EffectGraphVisitor::VisitClosureNode(ClosureNode* node) { |
1327 const Function& function = node->function(); | 1327 const Function& function = node->function(); |
1328 | 1328 |
(...skipping 20 matching lines...) Expand all Loading... |
1349 ASSERT(function.context_scope() != ContextScope::null()); | 1349 ASSERT(function.context_scope() != ContextScope::null()); |
1350 | 1350 |
1351 // The function type of a closure may have type arguments. In that case, pass | 1351 // The function type of a closure may have type arguments. In that case, pass |
1352 // the type arguments of the instantiator. Otherwise, pass null object. | 1352 // the type arguments of the instantiator. Otherwise, pass null object. |
1353 const Class& cls = Class::Handle(function.signature_class()); | 1353 const Class& cls = Class::Handle(function.signature_class()); |
1354 ASSERT(!cls.IsNull()); | 1354 ASSERT(!cls.IsNull()); |
1355 const bool requires_type_arguments = cls.HasTypeArguments(); | 1355 const bool requires_type_arguments = cls.HasTypeArguments(); |
1356 Value* type_arguments = NULL; | 1356 Value* type_arguments = NULL; |
1357 if (requires_type_arguments) { | 1357 if (requires_type_arguments) { |
1358 ASSERT(!function.IsImplicitStaticClosureFunction()); | 1358 ASSERT(!function.IsImplicitStaticClosureFunction()); |
1359 type_arguments = BuildInstantiatorTypeArguments(node->token_index(), NULL); | 1359 type_arguments = BuildInstantiatorTypeArguments(node->token_pos(), NULL); |
1360 } else { | 1360 } else { |
1361 type_arguments = BuildNullValue(); | 1361 type_arguments = BuildNullValue(); |
1362 } | 1362 } |
1363 | 1363 |
1364 CreateClosureComp* create = new CreateClosureComp( | 1364 CreateClosureComp* create = new CreateClosureComp( |
1365 node, owner()->try_index(), type_arguments, receiver); | 1365 node, owner()->try_index(), type_arguments, receiver); |
1366 ReturnComputation(create); | 1366 ReturnComputation(create); |
1367 } | 1367 } |
1368 | 1368 |
1369 | 1369 |
(...skipping 13 matching lines...) Expand all Loading... |
1383 int length = arguments->length(); | 1383 int length = arguments->length(); |
1384 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(length + 1); | 1384 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(length + 1); |
1385 | 1385 |
1386 ValueGraphVisitor for_receiver(owner(), temp_index()); | 1386 ValueGraphVisitor for_receiver(owner(), temp_index()); |
1387 node->receiver()->Visit(&for_receiver); | 1387 node->receiver()->Visit(&for_receiver); |
1388 Append(for_receiver); | 1388 Append(for_receiver); |
1389 values->Add(for_receiver.value()); | 1389 values->Add(for_receiver.value()); |
1390 | 1390 |
1391 TranslateArgumentList(*arguments, values); | 1391 TranslateArgumentList(*arguments, values); |
1392 InstanceCallComp* call = new InstanceCallComp( | 1392 InstanceCallComp* call = new InstanceCallComp( |
1393 node->token_index(), owner()->try_index(), | 1393 node->token_pos(), owner()->try_index(), |
1394 node->function_name(), Token::kILLEGAL, values, | 1394 node->function_name(), Token::kILLEGAL, values, |
1395 arguments->names(), 1); | 1395 arguments->names(), 1); |
1396 ReturnComputation(call); | 1396 ReturnComputation(call); |
1397 } | 1397 } |
1398 | 1398 |
1399 | 1399 |
1400 // <Expression> ::= StaticCall { function: Function | 1400 // <Expression> ::= StaticCall { function: Function |
1401 // arguments: <ArgumentList> } | 1401 // arguments: <ArgumentList> } |
1402 void EffectGraphVisitor::VisitStaticCallNode(StaticCallNode* node) { | 1402 void EffectGraphVisitor::VisitStaticCallNode(StaticCallNode* node) { |
1403 int length = node->arguments()->length(); | 1403 int length = node->arguments()->length(); |
1404 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(length); | 1404 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(length); |
1405 TranslateArgumentList(*node->arguments(), values); | 1405 TranslateArgumentList(*node->arguments(), values); |
1406 StaticCallComp* call = | 1406 StaticCallComp* call = |
1407 new StaticCallComp(node->token_index(), | 1407 new StaticCallComp(node->token_pos(), |
1408 owner()->try_index(), | 1408 owner()->try_index(), |
1409 node->function(), | 1409 node->function(), |
1410 node->arguments()->names(), | 1410 node->arguments()->names(), |
1411 values); | 1411 values); |
1412 ReturnComputation(call); | 1412 ReturnComputation(call); |
1413 } | 1413 } |
1414 | 1414 |
1415 | 1415 |
1416 ClosureCallComp* EffectGraphVisitor::BuildClosureCall( | 1416 ClosureCallComp* EffectGraphVisitor::BuildClosureCall( |
1417 ClosureCallNode* node) { | 1417 ClosureCallNode* node) { |
(...skipping 30 matching lines...) Expand all Loading... |
1448 BuildLoadContext(*owner()->parsed_function().expression_temp_var()); | 1448 BuildLoadContext(*owner()->parsed_function().expression_temp_var()); |
1449 | 1449 |
1450 ReturnValue(new UseVal(result)); | 1450 ReturnValue(new UseVal(result)); |
1451 } | 1451 } |
1452 | 1452 |
1453 | 1453 |
1454 void EffectGraphVisitor::VisitCloneContextNode(CloneContextNode* node) { | 1454 void EffectGraphVisitor::VisitCloneContextNode(CloneContextNode* node) { |
1455 BindInstr* context = new BindInstr(new CurrentContextComp()); | 1455 BindInstr* context = new BindInstr(new CurrentContextComp()); |
1456 AddInstruction(context); | 1456 AddInstruction(context); |
1457 BindInstr* clone = | 1457 BindInstr* clone = |
1458 new BindInstr(new CloneContextComp(node->token_index(), | 1458 new BindInstr(new CloneContextComp(node->token_pos(), |
1459 owner()->try_index(), | 1459 owner()->try_index(), |
1460 new UseVal(context))); | 1460 new UseVal(context))); |
1461 AddInstruction(clone); | 1461 AddInstruction(clone); |
1462 ReturnComputation(new StoreContextComp(new UseVal(clone))); | 1462 ReturnComputation(new StoreContextComp(new UseVal(clone))); |
1463 } | 1463 } |
1464 | 1464 |
1465 | 1465 |
1466 BindInstr* EffectGraphVisitor::BuildObjectAllocation( | 1466 BindInstr* EffectGraphVisitor::BuildObjectAllocation( |
1467 ConstructorCallNode* node) { | 1467 ConstructorCallNode* node) { |
1468 const Class& cls = Class::ZoneHandle(node->constructor().owner()); | 1468 const Class& cls = Class::ZoneHandle(node->constructor().owner()); |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1509 new BindInstr(new ConstantVal( | 1509 new BindInstr(new ConstantVal( |
1510 Smi::ZoneHandle(Smi::New(Function::kCtorPhaseAll)))); | 1510 Smi::ZoneHandle(Smi::New(Function::kCtorPhaseAll)))); |
1511 AddInstruction(ctor_arg); | 1511 AddInstruction(ctor_arg); |
1512 | 1512 |
1513 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(); | 1513 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(); |
1514 values->Add(alloc_value); | 1514 values->Add(alloc_value); |
1515 values->Add(new UseVal(ctor_arg)); | 1515 values->Add(new UseVal(ctor_arg)); |
1516 | 1516 |
1517 TranslateArgumentList(*node->arguments(), values); | 1517 TranslateArgumentList(*node->arguments(), values); |
1518 StaticCallComp* call = | 1518 StaticCallComp* call = |
1519 new StaticCallComp(node->token_index(), | 1519 new StaticCallComp(node->token_pos(), |
1520 owner()->try_index(), | 1520 owner()->try_index(), |
1521 node->constructor(), | 1521 node->constructor(), |
1522 node->arguments()->names(), | 1522 node->arguments()->names(), |
1523 values); | 1523 values); |
1524 AddInstruction(new DoInstr(call)); | 1524 AddInstruction(new DoInstr(call)); |
1525 } | 1525 } |
1526 | 1526 |
1527 | 1527 |
1528 void EffectGraphVisitor::VisitConstructorCallNode(ConstructorCallNode* node) { | 1528 void EffectGraphVisitor::VisitConstructorCallNode(ConstructorCallNode* node) { |
1529 if (node->constructor().IsFactory()) { | 1529 if (node->constructor().IsFactory()) { |
1530 ZoneGrowableArray<Value*>* factory_arguments = | 1530 ZoneGrowableArray<Value*>* factory_arguments = |
1531 new ZoneGrowableArray<Value*>(); | 1531 new ZoneGrowableArray<Value*>(); |
1532 factory_arguments->Add( | 1532 factory_arguments->Add( |
1533 new UseVal(BuildInstantiatedTypeArguments(node->token_index(), | 1533 new UseVal(BuildInstantiatedTypeArguments(node->token_pos(), |
1534 node->type_arguments()))); | 1534 node->type_arguments()))); |
1535 ASSERT(factory_arguments->length() == 1); | 1535 ASSERT(factory_arguments->length() == 1); |
1536 TranslateArgumentList(*node->arguments(), factory_arguments); | 1536 TranslateArgumentList(*node->arguments(), factory_arguments); |
1537 StaticCallComp* call = | 1537 StaticCallComp* call = |
1538 new StaticCallComp(node->token_index(), | 1538 new StaticCallComp(node->token_pos(), |
1539 owner()->try_index(), | 1539 owner()->try_index(), |
1540 node->constructor(), | 1540 node->constructor(), |
1541 node->arguments()->names(), | 1541 node->arguments()->names(), |
1542 factory_arguments); | 1542 factory_arguments); |
1543 ReturnComputation(call); | 1543 ReturnComputation(call); |
1544 return; | 1544 return; |
1545 } | 1545 } |
1546 // t_n contains the allocated and initialized object. | 1546 // t_n contains the allocated and initialized object. |
1547 // t_n <- AllocateObject(class) | 1547 // t_n <- AllocateObject(class) |
1548 // t_n+1 <- ctor-arg | 1548 // t_n+1 <- ctor-arg |
(...skipping 24 matching lines...) Expand all Loading... |
1573 ValueGraphVisitor for_instantiator(owner(), temp_index()); | 1573 ValueGraphVisitor for_instantiator(owner(), temp_index()); |
1574 owner()->parsed_function().instantiator()->Visit(&for_instantiator); | 1574 owner()->parsed_function().instantiator()->Visit(&for_instantiator); |
1575 Append(for_instantiator); | 1575 Append(for_instantiator); |
1576 return for_instantiator.value(); | 1576 return for_instantiator.value(); |
1577 } | 1577 } |
1578 | 1578 |
1579 | 1579 |
1580 // 'expression_temp_var' may not be used inside this method if 'instantiator' | 1580 // 'expression_temp_var' may not be used inside this method if 'instantiator' |
1581 // is not NULL. | 1581 // is not NULL. |
1582 Value* EffectGraphVisitor::BuildInstantiatorTypeArguments( | 1582 Value* EffectGraphVisitor::BuildInstantiatorTypeArguments( |
1583 intptr_t token_index, Value* instantiator) { | 1583 intptr_t token_pos, Value* instantiator) { |
1584 const Class& instantiator_class = Class::Handle( | 1584 const Class& instantiator_class = Class::Handle( |
1585 owner()->parsed_function().function().owner()); | 1585 owner()->parsed_function().function().owner()); |
1586 if (instantiator_class.NumTypeParameters() == 0) { | 1586 if (instantiator_class.NumTypeParameters() == 0) { |
1587 // The type arguments are compile time constants. | 1587 // The type arguments are compile time constants. |
1588 AbstractTypeArguments& type_arguments = AbstractTypeArguments::ZoneHandle(); | 1588 AbstractTypeArguments& type_arguments = AbstractTypeArguments::ZoneHandle(); |
1589 // TODO(regis): Temporary type should be allocated in new gen heap. | 1589 // TODO(regis): Temporary type should be allocated in new gen heap. |
1590 Type& type = Type::Handle( | 1590 Type& type = Type::Handle( |
1591 Type::New(instantiator_class, type_arguments, token_index)); | 1591 Type::New(instantiator_class, type_arguments, token_pos)); |
1592 type ^= ClassFinalizer::FinalizeType( | 1592 type ^= ClassFinalizer::FinalizeType( |
1593 instantiator_class, type, ClassFinalizer::kFinalizeWellFormed); | 1593 instantiator_class, type, ClassFinalizer::kFinalizeWellFormed); |
1594 type_arguments = type.arguments(); | 1594 type_arguments = type.arguments(); |
1595 BindInstr* args = new BindInstr(new ConstantVal(type_arguments)); | 1595 BindInstr* args = new BindInstr(new ConstantVal(type_arguments)); |
1596 AddInstruction(args); | 1596 AddInstruction(args); |
1597 return new UseVal(args); | 1597 return new UseVal(args); |
1598 } | 1598 } |
1599 Function& outer_function = | 1599 Function& outer_function = |
1600 Function::Handle(owner()->parsed_function().function().raw()); | 1600 Function::Handle(owner()->parsed_function().function().raw()); |
1601 while (outer_function.IsLocalFunction()) { | 1601 while (outer_function.IsLocalFunction()) { |
(...skipping 23 matching lines...) Expand all Loading... |
1625 new BindInstr(new LoadVMFieldComp( | 1625 new BindInstr(new LoadVMFieldComp( |
1626 instantiator, | 1626 instantiator, |
1627 type_arguments_instance_field_offset, | 1627 type_arguments_instance_field_offset, |
1628 Type::ZoneHandle())); // Not an instance, no type. | 1628 Type::ZoneHandle())); // Not an instance, no type. |
1629 AddInstruction(load); | 1629 AddInstruction(load); |
1630 return new UseVal(load); | 1630 return new UseVal(load); |
1631 } | 1631 } |
1632 | 1632 |
1633 | 1633 |
1634 BindInstr* EffectGraphVisitor::BuildInstantiatedTypeArguments( | 1634 BindInstr* EffectGraphVisitor::BuildInstantiatedTypeArguments( |
1635 intptr_t token_index, | 1635 intptr_t token_pos, |
1636 const AbstractTypeArguments& type_arguments) { | 1636 const AbstractTypeArguments& type_arguments) { |
1637 if (type_arguments.IsNull() || type_arguments.IsInstantiated()) { | 1637 if (type_arguments.IsNull() || type_arguments.IsInstantiated()) { |
1638 BindInstr* type_args = | 1638 BindInstr* type_args = |
1639 new BindInstr(new ConstantVal(type_arguments)); | 1639 new BindInstr(new ConstantVal(type_arguments)); |
1640 AddInstruction(type_args); | 1640 AddInstruction(type_args); |
1641 return type_args; | 1641 return type_args; |
1642 } | 1642 } |
1643 // The type arguments are uninstantiated. | 1643 // The type arguments are uninstantiated. |
1644 Value* instantiator_value = | 1644 Value* instantiator_value = |
1645 BuildInstantiatorTypeArguments(token_index, NULL); | 1645 BuildInstantiatorTypeArguments(token_pos, NULL); |
1646 BindInstr* instantiate = | 1646 BindInstr* instantiate = |
1647 new BindInstr(new InstantiateTypeArgumentsComp(token_index, | 1647 new BindInstr(new InstantiateTypeArgumentsComp(token_pos, |
1648 owner()->try_index(), | 1648 owner()->try_index(), |
1649 type_arguments, | 1649 type_arguments, |
1650 instantiator_value)); | 1650 instantiator_value)); |
1651 AddInstruction(instantiate); | 1651 AddInstruction(instantiate); |
1652 return instantiate; | 1652 return instantiate; |
1653 } | 1653 } |
1654 | 1654 |
1655 | 1655 |
1656 void EffectGraphVisitor::BuildConstructorTypeArguments( | 1656 void EffectGraphVisitor::BuildConstructorTypeArguments( |
1657 ConstructorCallNode* node, | 1657 ConstructorCallNode* node, |
(...skipping 20 matching lines...) Expand all Loading... |
1678 // t2 = ExtractConstructorTypeArguments(t1); | 1678 // t2 = ExtractConstructorTypeArguments(t1); |
1679 // t1 = ExtractConstructorInstantiator(t1); | 1679 // t1 = ExtractConstructorInstantiator(t1); |
1680 // t_n <- t2 | 1680 // t_n <- t2 |
1681 // t_n+1 <- t1 | 1681 // t_n+1 <- t1 |
1682 // Use expression_temp_var and node->allocated_object_var() locals to keep | 1682 // Use expression_temp_var and node->allocated_object_var() locals to keep |
1683 // intermediate results around (t1 and t2 above). | 1683 // intermediate results around (t1 and t2 above). |
1684 ASSERT(owner()->parsed_function().expression_temp_var() != NULL); | 1684 ASSERT(owner()->parsed_function().expression_temp_var() != NULL); |
1685 const LocalVariable& t1 = *owner()->parsed_function().expression_temp_var(); | 1685 const LocalVariable& t1 = *owner()->parsed_function().expression_temp_var(); |
1686 const LocalVariable& t2 = node->allocated_object_var(); | 1686 const LocalVariable& t2 = node->allocated_object_var(); |
1687 Value* instantiator_type_arguments = BuildInstantiatorTypeArguments( | 1687 Value* instantiator_type_arguments = BuildInstantiatorTypeArguments( |
1688 node->token_index(), NULL); | 1688 node->token_pos(), NULL); |
1689 ASSERT(instantiator_type_arguments->IsUse()); | 1689 ASSERT(instantiator_type_arguments->IsUse()); |
1690 BindInstr* stored_instantiator = new BindInstr( | 1690 BindInstr* stored_instantiator = new BindInstr( |
1691 BuildStoreLocal(t1, instantiator_type_arguments)); | 1691 BuildStoreLocal(t1, instantiator_type_arguments)); |
1692 AddInstruction(stored_instantiator); | 1692 AddInstruction(stored_instantiator); |
1693 // t1: instantiator type arguments. | 1693 // t1: instantiator type arguments. |
1694 | 1694 |
1695 BindInstr* extract_type_arguments = new BindInstr( | 1695 BindInstr* extract_type_arguments = new BindInstr( |
1696 new ExtractConstructorTypeArgumentsComp( | 1696 new ExtractConstructorTypeArgumentsComp( |
1697 node->token_index(), | 1697 node->token_pos(), |
1698 owner()->try_index(), | 1698 owner()->try_index(), |
1699 node->type_arguments(), | 1699 node->type_arguments(), |
1700 new UseVal(stored_instantiator))); | 1700 new UseVal(stored_instantiator))); |
1701 AddInstruction(extract_type_arguments); | 1701 AddInstruction(extract_type_arguments); |
1702 | 1702 |
1703 Instruction* stored_type_arguments = new DoInstr( | 1703 Instruction* stored_type_arguments = new DoInstr( |
1704 BuildStoreLocal(t2, new UseVal(extract_type_arguments))); | 1704 BuildStoreLocal(t2, new UseVal(extract_type_arguments))); |
1705 AddInstruction(stored_type_arguments); | 1705 AddInstruction(stored_type_arguments); |
1706 // t2: extracted constructor type arguments. | 1706 // t2: extracted constructor type arguments. |
1707 BindInstr* load_instantiator = new BindInstr(BuildLoadLocal(t1)); | 1707 BindInstr* load_instantiator = new BindInstr(BuildLoadLocal(t1)); |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1756 | 1756 |
1757 void EffectGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) { | 1757 void EffectGraphVisitor::VisitInstanceGetterNode(InstanceGetterNode* node) { |
1758 ValueGraphVisitor for_receiver(owner(), temp_index()); | 1758 ValueGraphVisitor for_receiver(owner(), temp_index()); |
1759 node->receiver()->Visit(&for_receiver); | 1759 node->receiver()->Visit(&for_receiver); |
1760 Append(for_receiver); | 1760 Append(for_receiver); |
1761 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(1); | 1761 ZoneGrowableArray<Value*>* arguments = new ZoneGrowableArray<Value*>(1); |
1762 arguments->Add(for_receiver.value()); | 1762 arguments->Add(for_receiver.value()); |
1763 const String& name = | 1763 const String& name = |
1764 String::ZoneHandle(Field::GetterSymbol(node->field_name())); | 1764 String::ZoneHandle(Field::GetterSymbol(node->field_name())); |
1765 InstanceCallComp* call = new InstanceCallComp( | 1765 InstanceCallComp* call = new InstanceCallComp( |
1766 node->token_index(), owner()->try_index(), name, Token::kGET, | 1766 node->token_pos(), owner()->try_index(), name, Token::kGET, |
1767 arguments, Array::ZoneHandle(), 1); | 1767 arguments, Array::ZoneHandle(), 1); |
1768 ReturnComputation(call); | 1768 ReturnComputation(call); |
1769 } | 1769 } |
1770 | 1770 |
1771 | 1771 |
1772 void EffectGraphVisitor::BuildInstanceSetterValues( | 1772 void EffectGraphVisitor::BuildInstanceSetterValues( |
1773 InstanceSetterNode* node, Value** receiver, Value** value) { | 1773 InstanceSetterNode* node, Value** receiver, Value** value) { |
1774 ValueGraphVisitor for_receiver(owner(), temp_index()); | 1774 ValueGraphVisitor for_receiver(owner(), temp_index()); |
1775 node->receiver()->Visit(&for_receiver); | 1775 node->receiver()->Visit(&for_receiver); |
1776 Append(for_receiver); | 1776 Append(for_receiver); |
1777 ValueGraphVisitor for_value(owner(), for_receiver.temp_index()); | 1777 ValueGraphVisitor for_value(owner(), for_receiver.temp_index()); |
1778 node->value()->Visit(&for_value); | 1778 node->value()->Visit(&for_value); |
1779 Append(for_value); | 1779 Append(for_value); |
1780 *receiver = for_receiver.value(); | 1780 *receiver = for_receiver.value(); |
1781 *value = for_value.value(); | 1781 *value = for_value.value(); |
1782 } | 1782 } |
1783 | 1783 |
1784 | 1784 |
1785 void EffectGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) { | 1785 void EffectGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) { |
1786 Value *receiver, *value; | 1786 Value *receiver, *value; |
1787 BuildInstanceSetterValues(node, &receiver, &value); | 1787 BuildInstanceSetterValues(node, &receiver, &value); |
1788 InstanceSetterComp* setter = | 1788 InstanceSetterComp* setter = |
1789 new InstanceSetterComp(node->token_index(), | 1789 new InstanceSetterComp(node->token_pos(), |
1790 owner()->try_index(), | 1790 owner()->try_index(), |
1791 node->field_name(), | 1791 node->field_name(), |
1792 receiver, | 1792 receiver, |
1793 value); | 1793 value); |
1794 ReturnComputation(setter); | 1794 ReturnComputation(setter); |
1795 } | 1795 } |
1796 | 1796 |
1797 | 1797 |
1798 void ValueGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) { | 1798 void ValueGraphVisitor::VisitInstanceSetterNode(InstanceSetterNode* node) { |
1799 Value *receiver, *value; | 1799 Value *receiver, *value; |
1800 BuildInstanceSetterValues(node, &receiver, &value); | 1800 BuildInstanceSetterValues(node, &receiver, &value); |
1801 BindInstr* store_local_instr = new BindInstr( | 1801 BindInstr* store_local_instr = new BindInstr( |
1802 BuildStoreLocal(*owner()->parsed_function().expression_temp_var(), | 1802 BuildStoreLocal(*owner()->parsed_function().expression_temp_var(), |
1803 value)); | 1803 value)); |
1804 AddInstruction(store_local_instr); | 1804 AddInstruction(store_local_instr); |
1805 UseVal* saved_value = new UseVal(store_local_instr); | 1805 UseVal* saved_value = new UseVal(store_local_instr); |
1806 InstanceSetterComp* setter = | 1806 InstanceSetterComp* setter = |
1807 new InstanceSetterComp(node->token_index(), | 1807 new InstanceSetterComp(node->token_pos(), |
1808 owner()->try_index(), | 1808 owner()->try_index(), |
1809 node->field_name(), | 1809 node->field_name(), |
1810 receiver, | 1810 receiver, |
1811 saved_value); | 1811 saved_value); |
1812 AddInstruction(new DoInstr(setter)); | 1812 AddInstruction(new DoInstr(setter)); |
1813 ReturnComputation( | 1813 ReturnComputation( |
1814 BuildLoadLocal(*owner()->parsed_function().expression_temp_var())); | 1814 BuildLoadLocal(*owner()->parsed_function().expression_temp_var())); |
1815 } | 1815 } |
1816 | 1816 |
1817 | 1817 |
1818 void EffectGraphVisitor::VisitStaticGetterNode(StaticGetterNode* node) { | 1818 void EffectGraphVisitor::VisitStaticGetterNode(StaticGetterNode* node) { |
1819 const String& getter_name = | 1819 const String& getter_name = |
1820 String::Handle(Field::GetterName(node->field_name())); | 1820 String::Handle(Field::GetterName(node->field_name())); |
1821 const Function& getter_function = | 1821 const Function& getter_function = |
1822 Function::ZoneHandle(node->cls().LookupStaticFunction(getter_name)); | 1822 Function::ZoneHandle(node->cls().LookupStaticFunction(getter_name)); |
1823 ASSERT(!getter_function.IsNull()); | 1823 ASSERT(!getter_function.IsNull()); |
1824 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(); | 1824 ZoneGrowableArray<Value*>* values = new ZoneGrowableArray<Value*>(); |
1825 StaticCallComp* call = new StaticCallComp(node->token_index(), | 1825 StaticCallComp* call = new StaticCallComp(node->token_pos(), |
1826 owner()->try_index(), | 1826 owner()->try_index(), |
1827 getter_function, | 1827 getter_function, |
1828 Array::ZoneHandle(), // No names. | 1828 Array::ZoneHandle(), // No names. |
1829 values); | 1829 values); |
1830 ReturnComputation(call); | 1830 ReturnComputation(call); |
1831 } | 1831 } |
1832 | 1832 |
1833 | 1833 |
1834 void EffectGraphVisitor::VisitStaticSetterNode(StaticSetterNode* node) { | 1834 void EffectGraphVisitor::VisitStaticSetterNode(StaticSetterNode* node) { |
1835 const String& setter_name = | 1835 const String& setter_name = |
1836 String::Handle(Field::SetterName(node->field_name())); | 1836 String::Handle(Field::SetterName(node->field_name())); |
1837 const Function& setter_function = | 1837 const Function& setter_function = |
1838 Function::ZoneHandle(node->cls().LookupStaticFunction(setter_name)); | 1838 Function::ZoneHandle(node->cls().LookupStaticFunction(setter_name)); |
1839 ASSERT(!setter_function.IsNull()); | 1839 ASSERT(!setter_function.IsNull()); |
1840 ValueGraphVisitor for_value(owner(), temp_index()); | 1840 ValueGraphVisitor for_value(owner(), temp_index()); |
1841 node->value()->Visit(&for_value); | 1841 node->value()->Visit(&for_value); |
1842 Append(for_value); | 1842 Append(for_value); |
1843 StaticSetterComp* call = new StaticSetterComp(node->token_index(), | 1843 StaticSetterComp* call = new StaticSetterComp(node->token_pos(), |
1844 owner()->try_index(), | 1844 owner()->try_index(), |
1845 setter_function, | 1845 setter_function, |
1846 for_value.value()); | 1846 for_value.value()); |
1847 ReturnComputation(call); | 1847 ReturnComputation(call); |
1848 } | 1848 } |
1849 | 1849 |
1850 | 1850 |
1851 void EffectGraphVisitor::VisitNativeBodyNode(NativeBodyNode* node) { | 1851 void EffectGraphVisitor::VisitNativeBodyNode(NativeBodyNode* node) { |
1852 NativeCallComp* native_call = | 1852 NativeCallComp* native_call = |
1853 new NativeCallComp(node, owner()->try_index()); | 1853 new NativeCallComp(node, owner()->try_index()); |
(...skipping 25 matching lines...) Expand all Loading... |
1879 | 1879 |
1880 | 1880 |
1881 // <Expression> ::= StoreLocal { local: LocalVariable | 1881 // <Expression> ::= StoreLocal { local: LocalVariable |
1882 // value: <Expression> } | 1882 // value: <Expression> } |
1883 void EffectGraphVisitor::VisitStoreLocalNode(StoreLocalNode* node) { | 1883 void EffectGraphVisitor::VisitStoreLocalNode(StoreLocalNode* node) { |
1884 ValueGraphVisitor for_value(owner(), temp_index()); | 1884 ValueGraphVisitor for_value(owner(), temp_index()); |
1885 node->value()->Visit(&for_value); | 1885 node->value()->Visit(&for_value); |
1886 Append(for_value); | 1886 Append(for_value); |
1887 Value* store_value = for_value.value(); | 1887 Value* store_value = for_value.value(); |
1888 if (FLAG_enable_type_checks) { | 1888 if (FLAG_enable_type_checks) { |
1889 store_value = BuildAssignableValue(node->value()->token_index(), | 1889 store_value = BuildAssignableValue(node->value()->token_pos(), |
1890 store_value, | 1890 store_value, |
1891 node->local().type(), | 1891 node->local().type(), |
1892 node->local().name()); | 1892 node->local().name()); |
1893 } | 1893 } |
1894 Computation* store = BuildStoreLocal(node->local(), store_value); | 1894 Computation* store = BuildStoreLocal(node->local(), store_value); |
1895 ReturnComputation(store); | 1895 ReturnComputation(store); |
1896 } | 1896 } |
1897 | 1897 |
1898 | 1898 |
1899 void EffectGraphVisitor::VisitLoadInstanceFieldNode( | 1899 void EffectGraphVisitor::VisitLoadInstanceFieldNode( |
(...skipping 12 matching lines...) Expand all Loading... |
1912 ValueGraphVisitor for_instance(owner(), temp_index()); | 1912 ValueGraphVisitor for_instance(owner(), temp_index()); |
1913 node->instance()->Visit(&for_instance); | 1913 node->instance()->Visit(&for_instance); |
1914 Append(for_instance); | 1914 Append(for_instance); |
1915 ValueGraphVisitor for_value(owner(), for_instance.temp_index()); | 1915 ValueGraphVisitor for_value(owner(), for_instance.temp_index()); |
1916 node->value()->Visit(&for_value); | 1916 node->value()->Visit(&for_value); |
1917 Append(for_value); | 1917 Append(for_value); |
1918 Value* store_value = for_value.value(); | 1918 Value* store_value = for_value.value(); |
1919 if (FLAG_enable_type_checks) { | 1919 if (FLAG_enable_type_checks) { |
1920 const AbstractType& type = AbstractType::ZoneHandle(node->field().type()); | 1920 const AbstractType& type = AbstractType::ZoneHandle(node->field().type()); |
1921 const String& dst_name = String::ZoneHandle(node->field().name()); | 1921 const String& dst_name = String::ZoneHandle(node->field().name()); |
1922 store_value = BuildAssignableValue(node->value()->token_index(), | 1922 store_value = BuildAssignableValue(node->value()->token_pos(), |
1923 store_value, | 1923 store_value, |
1924 type, | 1924 type, |
1925 dst_name); | 1925 dst_name); |
1926 } | 1926 } |
1927 StoreInstanceFieldComp* store = new StoreInstanceFieldComp( | 1927 StoreInstanceFieldComp* store = new StoreInstanceFieldComp( |
1928 node->field(), for_instance.value(), store_value, NULL); | 1928 node->field(), for_instance.value(), store_value, NULL); |
1929 ReturnComputation(store); | 1929 ReturnComputation(store); |
1930 } | 1930 } |
1931 | 1931 |
1932 | 1932 |
(...skipping 11 matching lines...) Expand all Loading... |
1944 | 1944 |
1945 | 1945 |
1946 void EffectGraphVisitor::VisitStoreStaticFieldNode(StoreStaticFieldNode* node) { | 1946 void EffectGraphVisitor::VisitStoreStaticFieldNode(StoreStaticFieldNode* node) { |
1947 ValueGraphVisitor for_value(owner(), temp_index()); | 1947 ValueGraphVisitor for_value(owner(), temp_index()); |
1948 node->value()->Visit(&for_value); | 1948 node->value()->Visit(&for_value); |
1949 Append(for_value); | 1949 Append(for_value); |
1950 Value* store_value = for_value.value(); | 1950 Value* store_value = for_value.value(); |
1951 if (FLAG_enable_type_checks) { | 1951 if (FLAG_enable_type_checks) { |
1952 const AbstractType& type = AbstractType::ZoneHandle(node->field().type()); | 1952 const AbstractType& type = AbstractType::ZoneHandle(node->field().type()); |
1953 const String& dst_name = String::ZoneHandle(node->field().name()); | 1953 const String& dst_name = String::ZoneHandle(node->field().name()); |
1954 store_value = BuildAssignableValue(node->value()->token_index(), | 1954 store_value = BuildAssignableValue(node->value()->token_pos(), |
1955 store_value, | 1955 store_value, |
1956 type, | 1956 type, |
1957 dst_name); | 1957 dst_name); |
1958 } | 1958 } |
1959 StoreStaticFieldComp* store = | 1959 StoreStaticFieldComp* store = |
1960 new StoreStaticFieldComp(node->field(), store_value); | 1960 new StoreStaticFieldComp(node->field(), store_value); |
1961 ReturnComputation(store); | 1961 ReturnComputation(store); |
1962 } | 1962 } |
1963 | 1963 |
1964 | 1964 |
1965 void EffectGraphVisitor::VisitLoadIndexedNode(LoadIndexedNode* node) { | 1965 void EffectGraphVisitor::VisitLoadIndexedNode(LoadIndexedNode* node) { |
1966 ValueGraphVisitor for_array(owner(), temp_index()); | 1966 ValueGraphVisitor for_array(owner(), temp_index()); |
1967 node->array()->Visit(&for_array); | 1967 node->array()->Visit(&for_array); |
1968 Append(for_array); | 1968 Append(for_array); |
1969 ValueGraphVisitor for_index(owner(), for_array.temp_index()); | 1969 ValueGraphVisitor for_index(owner(), for_array.temp_index()); |
1970 node->index_expr()->Visit(&for_index); | 1970 node->index_expr()->Visit(&for_index); |
1971 Append(for_index); | 1971 Append(for_index); |
1972 | 1972 |
1973 LoadIndexedComp* load = new LoadIndexedComp( | 1973 LoadIndexedComp* load = new LoadIndexedComp( |
1974 node->token_index(), | 1974 node->token_pos(), |
1975 owner()->try_index(), | 1975 owner()->try_index(), |
1976 for_array.value(), | 1976 for_array.value(), |
1977 for_index.value()); | 1977 for_index.value()); |
1978 ReturnComputation(load); | 1978 ReturnComputation(load); |
1979 } | 1979 } |
1980 | 1980 |
1981 | 1981 |
1982 void EffectGraphVisitor::BuildStoreIndexedValues( | 1982 void EffectGraphVisitor::BuildStoreIndexedValues( |
1983 StoreIndexedNode* node, Value** array, Value** index, Value** value) { | 1983 StoreIndexedNode* node, Value** array, Value** index, Value** value) { |
1984 ValueGraphVisitor for_array(owner(), temp_index()); | 1984 ValueGraphVisitor for_array(owner(), temp_index()); |
1985 node->array()->Visit(&for_array); | 1985 node->array()->Visit(&for_array); |
1986 Append(for_array); | 1986 Append(for_array); |
1987 ValueGraphVisitor for_index(owner(), for_array.temp_index()); | 1987 ValueGraphVisitor for_index(owner(), for_array.temp_index()); |
1988 node->index_expr()->Visit(&for_index); | 1988 node->index_expr()->Visit(&for_index); |
1989 Append(for_index); | 1989 Append(for_index); |
1990 ValueGraphVisitor for_value(owner(), for_index.temp_index()); | 1990 ValueGraphVisitor for_value(owner(), for_index.temp_index()); |
1991 node->value()->Visit(&for_value); | 1991 node->value()->Visit(&for_value); |
1992 Append(for_value); | 1992 Append(for_value); |
1993 *array = for_array.value(); | 1993 *array = for_array.value(); |
1994 *index = for_index.value(); | 1994 *index = for_index.value(); |
1995 *value = for_value.value(); | 1995 *value = for_value.value(); |
1996 } | 1996 } |
1997 | 1997 |
1998 | 1998 |
1999 void EffectGraphVisitor::VisitStoreIndexedNode(StoreIndexedNode* node) { | 1999 void EffectGraphVisitor::VisitStoreIndexedNode(StoreIndexedNode* node) { |
2000 Value *array, *index, *value; | 2000 Value *array, *index, *value; |
2001 BuildStoreIndexedValues(node, &array, &index, &value); | 2001 BuildStoreIndexedValues(node, &array, &index, &value); |
2002 StoreIndexedComp* store = new StoreIndexedComp(node->token_index(), | 2002 StoreIndexedComp* store = new StoreIndexedComp(node->token_pos(), |
2003 owner()->try_index(), | 2003 owner()->try_index(), |
2004 array, | 2004 array, |
2005 index, | 2005 index, |
2006 value); | 2006 value); |
2007 ReturnComputation(store); | 2007 ReturnComputation(store); |
2008 } | 2008 } |
2009 | 2009 |
2010 | 2010 |
2011 void ValueGraphVisitor::VisitStoreIndexedNode(StoreIndexedNode* node) { | 2011 void ValueGraphVisitor::VisitStoreIndexedNode(StoreIndexedNode* node) { |
2012 Value *array, *index, *value; | 2012 Value *array, *index, *value; |
2013 BuildStoreIndexedValues(node, &array, &index, &value); | 2013 BuildStoreIndexedValues(node, &array, &index, &value); |
2014 BindInstr* store_local_instr = new BindInstr( | 2014 BindInstr* store_local_instr = new BindInstr( |
2015 BuildStoreLocal(*owner()->parsed_function().expression_temp_var(), | 2015 BuildStoreLocal(*owner()->parsed_function().expression_temp_var(), |
2016 value)); | 2016 value)); |
2017 AddInstruction(store_local_instr); | 2017 AddInstruction(store_local_instr); |
2018 UseVal* saved_value = new UseVal(store_local_instr); | 2018 UseVal* saved_value = new UseVal(store_local_instr); |
2019 StoreIndexedComp* store = new StoreIndexedComp(node->token_index(), | 2019 StoreIndexedComp* store = new StoreIndexedComp(node->token_pos(), |
2020 owner()->try_index(), | 2020 owner()->try_index(), |
2021 array, | 2021 array, |
2022 index, | 2022 index, |
2023 saved_value); | 2023 saved_value); |
2024 AddInstruction(new DoInstr(store)); | 2024 AddInstruction(new DoInstr(store)); |
2025 ReturnComputation( | 2025 ReturnComputation( |
2026 BuildLoadLocal(*owner()->parsed_function().expression_temp_var())); | 2026 BuildLoadLocal(*owner()->parsed_function().expression_temp_var())); |
2027 } | 2027 } |
2028 | 2028 |
2029 | 2029 |
(...skipping 23 matching lines...) Expand all Loading... |
2053 void EffectGraphVisitor::VisitSequenceNode(SequenceNode* node) { | 2053 void EffectGraphVisitor::VisitSequenceNode(SequenceNode* node) { |
2054 LocalScope* scope = node->scope(); | 2054 LocalScope* scope = node->scope(); |
2055 const intptr_t num_context_variables = | 2055 const intptr_t num_context_variables = |
2056 (scope != NULL) ? scope->num_context_variables() : 0; | 2056 (scope != NULL) ? scope->num_context_variables() : 0; |
2057 int previous_context_level = owner()->context_level(); | 2057 int previous_context_level = owner()->context_level(); |
2058 if (num_context_variables > 0) { | 2058 if (num_context_variables > 0) { |
2059 // The loop local scope declares variables that are captured. | 2059 // The loop local scope declares variables that are captured. |
2060 // Allocate and chain a new context. | 2060 // Allocate and chain a new context. |
2061 // Allocate context computation (uses current CTX) | 2061 // Allocate context computation (uses current CTX) |
2062 BindInstr* allocated_context = | 2062 BindInstr* allocated_context = |
2063 new BindInstr(new AllocateContextComp(node->token_index(), | 2063 new BindInstr(new AllocateContextComp(node->token_pos(), |
2064 owner()->try_index(), | 2064 owner()->try_index(), |
2065 num_context_variables)); | 2065 num_context_variables)); |
2066 AddInstruction(allocated_context); | 2066 AddInstruction(allocated_context); |
2067 | 2067 |
2068 // If this node_sequence is the body of the function being compiled, and if | 2068 // If this node_sequence is the body of the function being compiled, and if |
2069 // this function is not a closure, do not link the current context as the | 2069 // this function is not a closure, do not link the current context as the |
2070 // parent of the newly allocated context, as it is not accessible. Instead, | 2070 // parent of the newly allocated context, as it is not accessible. Instead, |
2071 // save it in a pre-allocated variable and restore it on exit. | 2071 // save it in a pre-allocated variable and restore it on exit. |
2072 if (MustSaveRestoreContext(node)) { | 2072 if (MustSaveRestoreContext(node)) { |
2073 BindInstr* current_context = new BindInstr(new CurrentContextComp()); | 2073 BindInstr* current_context = new BindInstr(new CurrentContextComp()); |
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2143 // Skip type checking of receiver for instance functions. | 2143 // Skip type checking of receiver for instance functions. |
2144 pos = 1; | 2144 pos = 1; |
2145 } | 2145 } |
2146 while (pos < num_params) { | 2146 while (pos < num_params) { |
2147 const LocalVariable& parameter = *scope->VariableAt(pos); | 2147 const LocalVariable& parameter = *scope->VariableAt(pos); |
2148 ASSERT(parameter.owner() == scope); | 2148 ASSERT(parameter.owner() == scope); |
2149 if (!CanSkipTypeCheck(NULL, parameter.type())) { | 2149 if (!CanSkipTypeCheck(NULL, parameter.type())) { |
2150 BindInstr* load = new BindInstr(BuildLoadLocal(parameter)); | 2150 BindInstr* load = new BindInstr(BuildLoadLocal(parameter)); |
2151 AddInstruction(load); | 2151 AddInstruction(load); |
2152 AssertAssignableComp* assert_assignable = | 2152 AssertAssignableComp* assert_assignable = |
2153 BuildAssertAssignable(parameter.token_index(), | 2153 BuildAssertAssignable(parameter.token_pos(), |
2154 new UseVal(load), | 2154 new UseVal(load), |
2155 parameter.type(), | 2155 parameter.type(), |
2156 parameter.name()); | 2156 parameter.name()); |
2157 AddInstruction(new DoInstr(assert_assignable)); | 2157 AddInstruction(new DoInstr(assert_assignable)); |
2158 } | 2158 } |
2159 pos++; | 2159 pos++; |
2160 } | 2160 } |
2161 } | 2161 } |
2162 | 2162 |
2163 intptr_t i = 0; | 2163 intptr_t i = 0; |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2261 } | 2261 } |
2262 } | 2262 } |
2263 | 2263 |
2264 | 2264 |
2265 void EffectGraphVisitor::BuildThrowNode(ThrowNode* node) { | 2265 void EffectGraphVisitor::BuildThrowNode(ThrowNode* node) { |
2266 ValueGraphVisitor for_exception(owner(), temp_index()); | 2266 ValueGraphVisitor for_exception(owner(), temp_index()); |
2267 node->exception()->Visit(&for_exception); | 2267 node->exception()->Visit(&for_exception); |
2268 Append(for_exception); | 2268 Append(for_exception); |
2269 Instruction* instr = NULL; | 2269 Instruction* instr = NULL; |
2270 if (node->stacktrace() == NULL) { | 2270 if (node->stacktrace() == NULL) { |
2271 instr = new ThrowInstr(node->token_index(), | 2271 instr = new ThrowInstr(node->token_pos(), |
2272 owner()->try_index(), | 2272 owner()->try_index(), |
2273 for_exception.value()); | 2273 for_exception.value()); |
2274 } else { | 2274 } else { |
2275 ValueGraphVisitor for_stack_trace(owner(), temp_index()); | 2275 ValueGraphVisitor for_stack_trace(owner(), temp_index()); |
2276 node->stacktrace()->Visit(&for_stack_trace); | 2276 node->stacktrace()->Visit(&for_stack_trace); |
2277 Append(for_stack_trace); | 2277 Append(for_stack_trace); |
2278 instr = new ReThrowInstr(node->token_index(), | 2278 instr = new ReThrowInstr(node->token_pos(), |
2279 owner()->try_index(), | 2279 owner()->try_index(), |
2280 for_exception.value(), | 2280 for_exception.value(), |
2281 for_stack_trace.value()); | 2281 for_stack_trace.value()); |
2282 } | 2282 } |
2283 AddInstruction(instr); | 2283 AddInstruction(instr); |
2284 } | 2284 } |
2285 | 2285 |
2286 | 2286 |
2287 void EffectGraphVisitor::VisitThrowNode(ThrowNode* node) { | 2287 void EffectGraphVisitor::VisitThrowNode(ThrowNode* node) { |
2288 BuildThrowNode(node); | 2288 BuildThrowNode(node); |
(...skipping 440 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2729 char* chars = reinterpret_cast<char*>( | 2729 char* chars = reinterpret_cast<char*>( |
2730 Isolate::Current()->current_zone()->Allocate(len)); | 2730 Isolate::Current()->current_zone()->Allocate(len)); |
2731 OS::SNPrint(chars, len, kFormat, function_name, reason); | 2731 OS::SNPrint(chars, len, kFormat, function_name, reason); |
2732 const Error& error = Error::Handle( | 2732 const Error& error = Error::Handle( |
2733 LanguageError::New(String::Handle(String::New(chars)))); | 2733 LanguageError::New(String::Handle(String::New(chars)))); |
2734 Isolate::Current()->long_jump_base()->Jump(1, error); | 2734 Isolate::Current()->long_jump_base()->Jump(1, error); |
2735 } | 2735 } |
2736 | 2736 |
2737 | 2737 |
2738 } // namespace dart | 2738 } // namespace dart |
OLD | NEW |