| OLD | NEW |
| 1 // Copyright 2011 the V8 project authors. All rights reserved. | 1 // Copyright 2011 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 217 result = HType::Boolean(); | 217 result = HType::Boolean(); |
| 218 } else if (value->IsJSObject()) { | 218 } else if (value->IsJSObject()) { |
| 219 result = HType::JSObject(); | 219 result = HType::JSObject(); |
| 220 } else if (value->IsJSArray()) { | 220 } else if (value->IsJSArray()) { |
| 221 result = HType::JSArray(); | 221 result = HType::JSArray(); |
| 222 } | 222 } |
| 223 return result; | 223 return result; |
| 224 } | 224 } |
| 225 | 225 |
| 226 | 226 |
| 227 int HValue::LookupOperandIndex(int occurrence_index, HValue* op) const { | 227 int HValue::LookupOperandIndex(int occurrence_index, HValue* op) { |
| 228 for (int i = 0; i < OperandCount(); ++i) { | 228 for (int i = 0; i < OperandCount(); ++i) { |
| 229 if (OperandAt(i) == op) { | 229 if (OperandAt(i) == op) { |
| 230 if (occurrence_index == 0) return i; | 230 if (occurrence_index == 0) return i; |
| 231 --occurrence_index; | 231 --occurrence_index; |
| 232 } | 232 } |
| 233 } | 233 } |
| 234 return -1; | 234 return -1; |
| 235 } | 235 } |
| 236 | 236 |
| 237 | 237 |
| 238 bool HValue::IsDefinedAfter(HBasicBlock* other) const { | 238 bool HValue::IsDefinedAfter(HBasicBlock* other) const { |
| 239 return block()->block_id() > other->block_id(); | 239 return block()->block_id() > other->block_id(); |
| 240 } | 240 } |
| 241 | 241 |
| 242 | 242 |
| 243 bool HValue::UsesMultipleTimes(HValue* op) const { | 243 bool HValue::UsesMultipleTimes(HValue* op) { |
| 244 bool seen = false; | 244 bool seen = false; |
| 245 for (int i = 0; i < OperandCount(); ++i) { | 245 for (int i = 0; i < OperandCount(); ++i) { |
| 246 if (OperandAt(i) == op) { | 246 if (OperandAt(i) == op) { |
| 247 if (seen) return true; | 247 if (seen) return true; |
| 248 seen = true; | 248 seen = true; |
| 249 } | 249 } |
| 250 } | 250 } |
| 251 return false; | 251 return false; |
| 252 } | 252 } |
| 253 | 253 |
| 254 | 254 |
| 255 bool HValue::Equals(HValue* other) const { | 255 bool HValue::Equals(HValue* other) { |
| 256 if (other->opcode() != opcode()) return false; | 256 if (other->opcode() != opcode()) return false; |
| 257 if (!other->representation().Equals(representation())) return false; | 257 if (!other->representation().Equals(representation())) return false; |
| 258 if (!other->type_.Equals(type_)) return false; | 258 if (!other->type_.Equals(type_)) return false; |
| 259 if (other->flags() != flags()) return false; | 259 if (other->flags() != flags()) return false; |
| 260 if (OperandCount() != other->OperandCount()) return false; | 260 if (OperandCount() != other->OperandCount()) return false; |
| 261 for (int i = 0; i < OperandCount(); ++i) { | 261 for (int i = 0; i < OperandCount(); ++i) { |
| 262 if (OperandAt(i)->id() != other->OperandAt(i)->id()) return false; | 262 if (OperandAt(i)->id() != other->OperandAt(i)->id()) return false; |
| 263 } | 263 } |
| 264 bool result = DataEquals(other); | 264 bool result = DataEquals(other); |
| 265 ASSERT(!result || Hashcode() == other->Hashcode()); | 265 ASSERT(!result || Hashcode() == other->Hashcode()); |
| 266 return result; | 266 return result; |
| 267 } | 267 } |
| 268 | 268 |
| 269 | 269 |
| 270 intptr_t HValue::Hashcode() const { | 270 intptr_t HValue::Hashcode() { |
| 271 intptr_t result = opcode(); | 271 intptr_t result = opcode(); |
| 272 int count = OperandCount(); | 272 int count = OperandCount(); |
| 273 for (int i = 0; i < count; ++i) { | 273 for (int i = 0; i < count; ++i) { |
| 274 result = result * 19 + OperandAt(i)->id() + (result >> 7); | 274 result = result * 19 + OperandAt(i)->id() + (result >> 7); |
| 275 } | 275 } |
| 276 return result; | 276 return result; |
| 277 } | 277 } |
| 278 | 278 |
| 279 | 279 |
| 280 void HValue::SetOperandAt(int index, HValue* value) { | 280 void HValue::SetOperandAt(int index, HValue* value) { |
| (...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 434 } | 434 } |
| 435 | 435 |
| 436 | 436 |
| 437 void HValue::ComputeInitialRange() { | 437 void HValue::ComputeInitialRange() { |
| 438 ASSERT(!HasRange()); | 438 ASSERT(!HasRange()); |
| 439 range_ = InferRange(); | 439 range_ = InferRange(); |
| 440 ASSERT(HasRange()); | 440 ASSERT(HasRange()); |
| 441 } | 441 } |
| 442 | 442 |
| 443 | 443 |
| 444 void HInstruction::PrintTo(StringStream* stream) const { | 444 void HInstruction::PrintTo(StringStream* stream) { |
| 445 stream->Add("%s", Mnemonic()); | 445 stream->Add("%s", Mnemonic()); |
| 446 if (HasSideEffects()) stream->Add("*"); | 446 if (HasSideEffects()) stream->Add("*"); |
| 447 stream->Add(" "); | 447 stream->Add(" "); |
| 448 PrintDataTo(stream); | 448 PrintDataTo(stream); |
| 449 | 449 |
| 450 if (range() != NULL) { | 450 if (range() != NULL) { |
| 451 stream->Add(" range[%d,%d,m0=%d]", | 451 stream->Add(" range[%d,%d,m0=%d]", |
| 452 range()->lower(), | 452 range()->lower(), |
| 453 range()->upper(), | 453 range()->upper(), |
| 454 static_cast<int>(range()->CanBeMinusZero())); | 454 static_cast<int>(range()->CanBeMinusZero())); |
| (...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 557 } | 557 } |
| 558 | 558 |
| 559 // Verify that instructions that can be eliminated by GVN have overridden | 559 // Verify that instructions that can be eliminated by GVN have overridden |
| 560 // HValue::DataEquals. The default implementation is UNREACHABLE. We | 560 // HValue::DataEquals. The default implementation is UNREACHABLE. We |
| 561 // don't actually care whether DataEquals returns true or false here. | 561 // don't actually care whether DataEquals returns true or false here. |
| 562 if (CheckFlag(kUseGVN)) DataEquals(this); | 562 if (CheckFlag(kUseGVN)) DataEquals(this); |
| 563 } | 563 } |
| 564 #endif | 564 #endif |
| 565 | 565 |
| 566 | 566 |
| 567 void HCall::PrintDataTo(StringStream* stream) const { | 567 void HCall::PrintDataTo(StringStream* stream) { |
| 568 stream->Add("#%d", argument_count()); | 568 stream->Add("#%d", argument_count()); |
| 569 } | 569 } |
| 570 | 570 |
| 571 | 571 |
| 572 void HUnaryCall::PrintDataTo(StringStream* stream) const { | 572 void HUnaryCall::PrintDataTo(StringStream* stream) { |
| 573 value()->PrintNameTo(stream); | 573 value()->PrintNameTo(stream); |
| 574 stream->Add(" "); | 574 stream->Add(" "); |
| 575 HCall::PrintDataTo(stream); | 575 HCall::PrintDataTo(stream); |
| 576 } | 576 } |
| 577 | 577 |
| 578 | 578 |
| 579 void HBinaryCall::PrintDataTo(StringStream* stream) const { | 579 void HBinaryCall::PrintDataTo(StringStream* stream) { |
| 580 first()->PrintNameTo(stream); | 580 first()->PrintNameTo(stream); |
| 581 stream->Add(" "); | 581 stream->Add(" "); |
| 582 second()->PrintNameTo(stream); | 582 second()->PrintNameTo(stream); |
| 583 stream->Add(" "); | 583 stream->Add(" "); |
| 584 HCall::PrintDataTo(stream); | 584 HCall::PrintDataTo(stream); |
| 585 } | 585 } |
| 586 | 586 |
| 587 | 587 |
| 588 void HCallConstantFunction::PrintDataTo(StringStream* stream) const { | 588 void HCallConstantFunction::PrintDataTo(StringStream* stream) { |
| 589 if (IsApplyFunction()) { | 589 if (IsApplyFunction()) { |
| 590 stream->Add("optimized apply "); | 590 stream->Add("optimized apply "); |
| 591 } else { | 591 } else { |
| 592 stream->Add("%o ", function()->shared()->DebugName()); | 592 stream->Add("%o ", function()->shared()->DebugName()); |
| 593 } | 593 } |
| 594 HCall::PrintDataTo(stream); | 594 HCall::PrintDataTo(stream); |
| 595 } | 595 } |
| 596 | 596 |
| 597 | 597 |
| 598 void HCallNamed::PrintDataTo(StringStream* stream) const { | 598 void HCallNamed::PrintDataTo(StringStream* stream) { |
| 599 stream->Add("%o ", *name()); | 599 stream->Add("%o ", *name()); |
| 600 HUnaryCall::PrintDataTo(stream); | 600 HUnaryCall::PrintDataTo(stream); |
| 601 } | 601 } |
| 602 | 602 |
| 603 | 603 |
| 604 void HCallGlobal::PrintDataTo(StringStream* stream) const { | 604 void HCallGlobal::PrintDataTo(StringStream* stream) { |
| 605 stream->Add("%o ", *name()); | 605 stream->Add("%o ", *name()); |
| 606 HUnaryCall::PrintDataTo(stream); | 606 HUnaryCall::PrintDataTo(stream); |
| 607 } | 607 } |
| 608 | 608 |
| 609 | 609 |
| 610 void HCallKnownGlobal::PrintDataTo(StringStream* stream) const { | 610 void HCallKnownGlobal::PrintDataTo(StringStream* stream) { |
| 611 stream->Add("o ", target()->shared()->DebugName()); | 611 stream->Add("o ", target()->shared()->DebugName()); |
| 612 HCall::PrintDataTo(stream); | 612 HCall::PrintDataTo(stream); |
| 613 } | 613 } |
| 614 | 614 |
| 615 | 615 |
| 616 void HCallRuntime::PrintDataTo(StringStream* stream) const { | 616 void HCallRuntime::PrintDataTo(StringStream* stream) { |
| 617 stream->Add("%o ", *name()); | 617 stream->Add("%o ", *name()); |
| 618 HCall::PrintDataTo(stream); | 618 HCall::PrintDataTo(stream); |
| 619 } | 619 } |
| 620 | 620 |
| 621 | 621 |
| 622 void HClassOfTest::PrintDataTo(StringStream* stream) const { | 622 void HClassOfTest::PrintDataTo(StringStream* stream) { |
| 623 stream->Add("class_of_test("); | 623 stream->Add("class_of_test("); |
| 624 value()->PrintNameTo(stream); | 624 value()->PrintNameTo(stream); |
| 625 stream->Add(", \"%o\")", *class_name()); | 625 stream->Add(", \"%o\")", *class_name()); |
| 626 } | 626 } |
| 627 | 627 |
| 628 | 628 |
| 629 void HAccessArgumentsAt::PrintDataTo(StringStream* stream) const { | 629 void HAccessArgumentsAt::PrintDataTo(StringStream* stream) { |
| 630 arguments()->PrintNameTo(stream); | 630 arguments()->PrintNameTo(stream); |
| 631 stream->Add("["); | 631 stream->Add("["); |
| 632 index()->PrintNameTo(stream); | 632 index()->PrintNameTo(stream); |
| 633 stream->Add("], length "); | 633 stream->Add("], length "); |
| 634 length()->PrintNameTo(stream); | 634 length()->PrintNameTo(stream); |
| 635 } | 635 } |
| 636 | 636 |
| 637 | 637 |
| 638 void HControlInstruction::PrintDataTo(StringStream* stream) const { | 638 void HControlInstruction::PrintDataTo(StringStream* stream) { |
| 639 if (FirstSuccessor() != NULL) { | 639 if (FirstSuccessor() != NULL) { |
| 640 int first_id = FirstSuccessor()->block_id(); | 640 int first_id = FirstSuccessor()->block_id(); |
| 641 if (SecondSuccessor() == NULL) { | 641 if (SecondSuccessor() == NULL) { |
| 642 stream->Add(" B%d", first_id); | 642 stream->Add(" B%d", first_id); |
| 643 } else { | 643 } else { |
| 644 int second_id = SecondSuccessor()->block_id(); | 644 int second_id = SecondSuccessor()->block_id(); |
| 645 stream->Add(" goto (B%d, B%d)", first_id, second_id); | 645 stream->Add(" goto (B%d, B%d)", first_id, second_id); |
| 646 } | 646 } |
| 647 } | 647 } |
| 648 } | 648 } |
| 649 | 649 |
| 650 | 650 |
| 651 void HUnaryControlInstruction::PrintDataTo(StringStream* stream) const { | 651 void HUnaryControlInstruction::PrintDataTo(StringStream* stream) { |
| 652 value()->PrintNameTo(stream); | 652 value()->PrintNameTo(stream); |
| 653 HControlInstruction::PrintDataTo(stream); | 653 HControlInstruction::PrintDataTo(stream); |
| 654 } | 654 } |
| 655 | 655 |
| 656 | 656 |
| 657 void HCompareMap::PrintDataTo(StringStream* stream) const { | 657 void HCompareMap::PrintDataTo(StringStream* stream) { |
| 658 value()->PrintNameTo(stream); | 658 value()->PrintNameTo(stream); |
| 659 stream->Add(" (%p)", *map()); | 659 stream->Add(" (%p)", *map()); |
| 660 HControlInstruction::PrintDataTo(stream); | 660 HControlInstruction::PrintDataTo(stream); |
| 661 } | 661 } |
| 662 | 662 |
| 663 | 663 |
| 664 const char* HUnaryMathOperation::OpName() const { | 664 const char* HUnaryMathOperation::OpName() const { |
| 665 switch (op()) { | 665 switch (op()) { |
| 666 case kMathFloor: return "floor"; | 666 case kMathFloor: return "floor"; |
| 667 case kMathRound: return "round"; | 667 case kMathRound: return "round"; |
| 668 case kMathCeil: return "ceil"; | 668 case kMathCeil: return "ceil"; |
| 669 case kMathAbs: return "abs"; | 669 case kMathAbs: return "abs"; |
| 670 case kMathLog: return "log"; | 670 case kMathLog: return "log"; |
| 671 case kMathSin: return "sin"; | 671 case kMathSin: return "sin"; |
| 672 case kMathCos: return "cos"; | 672 case kMathCos: return "cos"; |
| 673 case kMathTan: return "tan"; | 673 case kMathTan: return "tan"; |
| 674 case kMathASin: return "asin"; | 674 case kMathASin: return "asin"; |
| 675 case kMathACos: return "acos"; | 675 case kMathACos: return "acos"; |
| 676 case kMathATan: return "atan"; | 676 case kMathATan: return "atan"; |
| 677 case kMathExp: return "exp"; | 677 case kMathExp: return "exp"; |
| 678 case kMathSqrt: return "sqrt"; | 678 case kMathSqrt: return "sqrt"; |
| 679 default: break; | 679 default: break; |
| 680 } | 680 } |
| 681 return "(unknown operation)"; | 681 return "(unknown operation)"; |
| 682 } | 682 } |
| 683 | 683 |
| 684 | 684 |
| 685 void HUnaryMathOperation::PrintDataTo(StringStream* stream) const { | 685 void HUnaryMathOperation::PrintDataTo(StringStream* stream) { |
| 686 const char* name = OpName(); | 686 const char* name = OpName(); |
| 687 stream->Add("%s ", name); | 687 stream->Add("%s ", name); |
| 688 value()->PrintNameTo(stream); | 688 value()->PrintNameTo(stream); |
| 689 } | 689 } |
| 690 | 690 |
| 691 | 691 |
| 692 void HUnaryOperation::PrintDataTo(StringStream* stream) const { | 692 void HUnaryOperation::PrintDataTo(StringStream* stream) { |
| 693 value()->PrintNameTo(stream); | 693 value()->PrintNameTo(stream); |
| 694 } | 694 } |
| 695 | 695 |
| 696 | 696 |
| 697 void HHasInstanceType::PrintDataTo(StringStream* stream) const { | 697 void HHasInstanceType::PrintDataTo(StringStream* stream) { |
| 698 value()->PrintNameTo(stream); | 698 value()->PrintNameTo(stream); |
| 699 switch (from_) { | 699 switch (from_) { |
| 700 case FIRST_JS_OBJECT_TYPE: | 700 case FIRST_JS_OBJECT_TYPE: |
| 701 if (to_ == LAST_TYPE) stream->Add(" spec_object"); | 701 if (to_ == LAST_TYPE) stream->Add(" spec_object"); |
| 702 break; | 702 break; |
| 703 case JS_REGEXP_TYPE: | 703 case JS_REGEXP_TYPE: |
| 704 if (to_ == JS_REGEXP_TYPE) stream->Add(" reg_exp"); | 704 if (to_ == JS_REGEXP_TYPE) stream->Add(" reg_exp"); |
| 705 break; | 705 break; |
| 706 case JS_ARRAY_TYPE: | 706 case JS_ARRAY_TYPE: |
| 707 if (to_ == JS_ARRAY_TYPE) stream->Add(" array"); | 707 if (to_ == JS_ARRAY_TYPE) stream->Add(" array"); |
| 708 break; | 708 break; |
| 709 case JS_FUNCTION_TYPE: | 709 case JS_FUNCTION_TYPE: |
| 710 if (to_ == JS_FUNCTION_TYPE) stream->Add(" function"); | 710 if (to_ == JS_FUNCTION_TYPE) stream->Add(" function"); |
| 711 break; | 711 break; |
| 712 default: | 712 default: |
| 713 break; | 713 break; |
| 714 } | 714 } |
| 715 } | 715 } |
| 716 | 716 |
| 717 | 717 |
| 718 void HTypeofIs::PrintDataTo(StringStream* stream) const { | 718 void HTypeofIs::PrintDataTo(StringStream* stream) { |
| 719 value()->PrintNameTo(stream); | 719 value()->PrintNameTo(stream); |
| 720 stream->Add(" == "); | 720 stream->Add(" == "); |
| 721 stream->Add(type_literal_->ToAsciiVector()); | 721 stream->Add(type_literal_->ToAsciiVector()); |
| 722 } | 722 } |
| 723 | 723 |
| 724 | 724 |
| 725 void HChange::PrintDataTo(StringStream* stream) const { | 725 void HChange::PrintDataTo(StringStream* stream) { |
| 726 HUnaryOperation::PrintDataTo(stream); | 726 HUnaryOperation::PrintDataTo(stream); |
| 727 stream->Add(" %s to %s", from_.Mnemonic(), to_.Mnemonic()); | 727 stream->Add(" %s to %s", from_.Mnemonic(), to_.Mnemonic()); |
| 728 | 728 |
| 729 if (CanTruncateToInt32()) stream->Add(" truncating-int32"); | 729 if (CanTruncateToInt32()) stream->Add(" truncating-int32"); |
| 730 if (CheckFlag(kBailoutOnMinusZero)) stream->Add(" -0?"); | 730 if (CheckFlag(kBailoutOnMinusZero)) stream->Add(" -0?"); |
| 731 } | 731 } |
| 732 | 732 |
| 733 | 733 |
| 734 HCheckInstanceType* HCheckInstanceType::NewIsJSObjectOrJSFunction( | 734 HCheckInstanceType* HCheckInstanceType::NewIsJSObjectOrJSFunction( |
| 735 HValue* value) { | 735 HValue* value) { |
| 736 STATIC_ASSERT((LAST_JS_OBJECT_TYPE + 1) == JS_FUNCTION_TYPE); | 736 STATIC_ASSERT((LAST_JS_OBJECT_TYPE + 1) == JS_FUNCTION_TYPE); |
| 737 return new HCheckInstanceType(value, FIRST_JS_OBJECT_TYPE, JS_FUNCTION_TYPE); | 737 return new HCheckInstanceType(value, FIRST_JS_OBJECT_TYPE, JS_FUNCTION_TYPE); |
| 738 } | 738 } |
| 739 | 739 |
| 740 | 740 |
| 741 void HCheckMap::PrintDataTo(StringStream* stream) const { | 741 void HCheckMap::PrintDataTo(StringStream* stream) { |
| 742 value()->PrintNameTo(stream); | 742 value()->PrintNameTo(stream); |
| 743 stream->Add(" %p", *map()); | 743 stream->Add(" %p", *map()); |
| 744 } | 744 } |
| 745 | 745 |
| 746 | 746 |
| 747 void HCheckFunction::PrintDataTo(StringStream* stream) const { | 747 void HCheckFunction::PrintDataTo(StringStream* stream) { |
| 748 value()->PrintNameTo(stream); | 748 value()->PrintNameTo(stream); |
| 749 stream->Add(" %p", *target()); | 749 stream->Add(" %p", *target()); |
| 750 } | 750 } |
| 751 | 751 |
| 752 | 752 |
| 753 void HCallStub::PrintDataTo(StringStream* stream) const { | 753 void HCallStub::PrintDataTo(StringStream* stream) { |
| 754 stream->Add("%s ", | 754 stream->Add("%s ", |
| 755 CodeStub::MajorName(major_key_, false)); | 755 CodeStub::MajorName(major_key_, false)); |
| 756 HUnaryCall::PrintDataTo(stream); | 756 HUnaryCall::PrintDataTo(stream); |
| 757 } | 757 } |
| 758 | 758 |
| 759 | 759 |
| 760 void HInstanceOf::PrintDataTo(StringStream* stream) const { | 760 void HInstanceOf::PrintDataTo(StringStream* stream) { |
| 761 left()->PrintNameTo(stream); | 761 left()->PrintNameTo(stream); |
| 762 stream->Add(" "); | 762 stream->Add(" "); |
| 763 right()->PrintNameTo(stream); | 763 right()->PrintNameTo(stream); |
| 764 stream->Add(" "); | 764 stream->Add(" "); |
| 765 context()->PrintNameTo(stream); | 765 context()->PrintNameTo(stream); |
| 766 } | 766 } |
| 767 | 767 |
| 768 | 768 |
| 769 Range* HValue::InferRange() { | 769 Range* HValue::InferRange() { |
| 770 if (representation().IsTagged()) { | 770 if (representation().IsTagged()) { |
| (...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 895 if (!right()->range()->CanBeZero()) { | 895 if (!right()->range()->CanBeZero()) { |
| 896 ClearFlag(HValue::kCanBeDivByZero); | 896 ClearFlag(HValue::kCanBeDivByZero); |
| 897 } | 897 } |
| 898 return result; | 898 return result; |
| 899 } else { | 899 } else { |
| 900 return HArithmeticBinaryOperation::InferRange(); | 900 return HArithmeticBinaryOperation::InferRange(); |
| 901 } | 901 } |
| 902 } | 902 } |
| 903 | 903 |
| 904 | 904 |
| 905 void HPhi::PrintTo(StringStream* stream) const { | 905 void HPhi::PrintTo(StringStream* stream) { |
| 906 stream->Add("["); | 906 stream->Add("["); |
| 907 for (int i = 0; i < OperandCount(); ++i) { | 907 for (int i = 0; i < OperandCount(); ++i) { |
| 908 HValue* value = OperandAt(i); | 908 HValue* value = OperandAt(i); |
| 909 stream->Add(" "); | 909 stream->Add(" "); |
| 910 value->PrintNameTo(stream); | 910 value->PrintNameTo(stream); |
| 911 stream->Add(" "); | 911 stream->Add(" "); |
| 912 } | 912 } |
| 913 stream->Add(" uses%d_%di_%dd_%dt]", | 913 stream->Add(" uses%d_%di_%dd_%dt]", |
| 914 uses()->length(), | 914 uses()->length(), |
| 915 int32_non_phi_uses() + int32_indirect_uses(), | 915 int32_non_phi_uses() + int32_indirect_uses(), |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 973 } | 973 } |
| 974 | 974 |
| 975 | 975 |
| 976 void HPhi::AddIndirectUsesTo(int* dest) { | 976 void HPhi::AddIndirectUsesTo(int* dest) { |
| 977 for (int i = 0; i < Representation::kNumRepresentations; i++) { | 977 for (int i = 0; i < Representation::kNumRepresentations; i++) { |
| 978 dest[i] += indirect_uses_[i]; | 978 dest[i] += indirect_uses_[i]; |
| 979 } | 979 } |
| 980 } | 980 } |
| 981 | 981 |
| 982 | 982 |
| 983 void HSimulate::PrintDataTo(StringStream* stream) const { | 983 void HSimulate::PrintDataTo(StringStream* stream) { |
| 984 stream->Add("id=%d ", ast_id()); | 984 stream->Add("id=%d ", ast_id()); |
| 985 if (pop_count_ > 0) stream->Add("pop %d", pop_count_); | 985 if (pop_count_ > 0) stream->Add("pop %d", pop_count_); |
| 986 if (values_.length() > 0) { | 986 if (values_.length() > 0) { |
| 987 if (pop_count_ > 0) stream->Add(" /"); | 987 if (pop_count_ > 0) stream->Add(" /"); |
| 988 for (int i = 0; i < values_.length(); ++i) { | 988 for (int i = 0; i < values_.length(); ++i) { |
| 989 if (!HasAssignedIndexAt(i)) { | 989 if (!HasAssignedIndexAt(i)) { |
| 990 stream->Add(" push "); | 990 stream->Add(" push "); |
| 991 } else { | 991 } else { |
| 992 stream->Add(" var[%d] = ", GetAssignedIndexAt(i)); | 992 stream->Add(" var[%d] = ", GetAssignedIndexAt(i)); |
| 993 } | 993 } |
| 994 values_[i]->PrintNameTo(stream); | 994 values_[i]->PrintNameTo(stream); |
| 995 } | 995 } |
| 996 } | 996 } |
| 997 } | 997 } |
| 998 | 998 |
| 999 | 999 |
| 1000 void HEnterInlined::PrintDataTo(StringStream* stream) const { | 1000 void HEnterInlined::PrintDataTo(StringStream* stream) { |
| 1001 SmartPointer<char> name = function()->debug_name()->ToCString(); | 1001 SmartPointer<char> name = function()->debug_name()->ToCString(); |
| 1002 stream->Add("%s, id=%d", *name, function()->id()); | 1002 stream->Add("%s, id=%d", *name, function()->id()); |
| 1003 } | 1003 } |
| 1004 | 1004 |
| 1005 | 1005 |
| 1006 HConstant::HConstant(Handle<Object> handle, Representation r) | 1006 HConstant::HConstant(Handle<Object> handle, Representation r) |
| 1007 : handle_(handle), | 1007 : handle_(handle), |
| 1008 constant_type_(HType::TypeFromValue(handle)), | 1008 constant_type_(HType::TypeFromValue(handle)), |
| 1009 has_int32_value_(false), | 1009 has_int32_value_(false), |
| 1010 int32_value_(0), | 1010 int32_value_(0), |
| (...skipping 20 matching lines...) Expand all Loading... |
| 1031 | 1031 |
| 1032 | 1032 |
| 1033 HConstant* HConstant::CopyToTruncatedInt32() const { | 1033 HConstant* HConstant::CopyToTruncatedInt32() const { |
| 1034 if (!has_double_value_) return NULL; | 1034 if (!has_double_value_) return NULL; |
| 1035 int32_t truncated = NumberToInt32(*handle_); | 1035 int32_t truncated = NumberToInt32(*handle_); |
| 1036 return new HConstant(Factory::NewNumberFromInt(truncated), | 1036 return new HConstant(Factory::NewNumberFromInt(truncated), |
| 1037 Representation::Integer32()); | 1037 Representation::Integer32()); |
| 1038 } | 1038 } |
| 1039 | 1039 |
| 1040 | 1040 |
| 1041 void HConstant::PrintDataTo(StringStream* stream) const { | 1041 void HConstant::PrintDataTo(StringStream* stream) { |
| 1042 handle()->ShortPrint(stream); | 1042 handle()->ShortPrint(stream); |
| 1043 } | 1043 } |
| 1044 | 1044 |
| 1045 | 1045 |
| 1046 bool HArrayLiteral::IsCopyOnWrite() const { | 1046 bool HArrayLiteral::IsCopyOnWrite() const { |
| 1047 return constant_elements()->map() == Heap::fixed_cow_array_map(); | 1047 return constant_elements()->map() == Heap::fixed_cow_array_map(); |
| 1048 } | 1048 } |
| 1049 | 1049 |
| 1050 | 1050 |
| 1051 void HBinaryOperation::PrintDataTo(StringStream* stream) const { | 1051 void HBinaryOperation::PrintDataTo(StringStream* stream) { |
| 1052 left()->PrintNameTo(stream); | 1052 left()->PrintNameTo(stream); |
| 1053 stream->Add(" "); | 1053 stream->Add(" "); |
| 1054 right()->PrintNameTo(stream); | 1054 right()->PrintNameTo(stream); |
| 1055 if (CheckFlag(kCanOverflow)) stream->Add(" !"); | 1055 if (CheckFlag(kCanOverflow)) stream->Add(" !"); |
| 1056 if (CheckFlag(kBailoutOnMinusZero)) stream->Add(" -0?"); | 1056 if (CheckFlag(kBailoutOnMinusZero)) stream->Add(" -0?"); |
| 1057 } | 1057 } |
| 1058 | 1058 |
| 1059 | 1059 |
| 1060 Range* HBitAnd::InferRange() { | 1060 Range* HBitAnd::InferRange() { |
| 1061 Range* a = left()->range(); | 1061 Range* a = left()->range(); |
| (...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1125 result->Shl(val); | 1125 result->Shl(val); |
| 1126 return result; | 1126 return result; |
| 1127 } | 1127 } |
| 1128 } | 1128 } |
| 1129 | 1129 |
| 1130 return HBinaryOperation::InferRange(); | 1130 return HBinaryOperation::InferRange(); |
| 1131 } | 1131 } |
| 1132 | 1132 |
| 1133 | 1133 |
| 1134 | 1134 |
| 1135 void HCompare::PrintDataTo(StringStream* stream) const { | 1135 void HCompare::PrintDataTo(StringStream* stream) { |
| 1136 stream->Add(Token::Name(token())); | 1136 stream->Add(Token::Name(token())); |
| 1137 stream->Add(" "); | 1137 stream->Add(" "); |
| 1138 HBinaryOperation::PrintDataTo(stream); | 1138 HBinaryOperation::PrintDataTo(stream); |
| 1139 } | 1139 } |
| 1140 | 1140 |
| 1141 | 1141 |
| 1142 void HCompare::SetInputRepresentation(Representation r) { | 1142 void HCompare::SetInputRepresentation(Representation r) { |
| 1143 input_representation_ = r; | 1143 input_representation_ = r; |
| 1144 if (r.IsTagged()) { | 1144 if (r.IsTagged()) { |
| 1145 SetAllSideEffects(); | 1145 SetAllSideEffects(); |
| 1146 ClearFlag(kUseGVN); | 1146 ClearFlag(kUseGVN); |
| 1147 } else { | 1147 } else { |
| 1148 ClearAllSideEffects(); | 1148 ClearAllSideEffects(); |
| 1149 SetFlag(kUseGVN); | 1149 SetFlag(kUseGVN); |
| 1150 } | 1150 } |
| 1151 } | 1151 } |
| 1152 | 1152 |
| 1153 | 1153 |
| 1154 void HParameter::PrintDataTo(StringStream* stream) const { | 1154 void HParameter::PrintDataTo(StringStream* stream) { |
| 1155 stream->Add("%u", index()); | 1155 stream->Add("%u", index()); |
| 1156 } | 1156 } |
| 1157 | 1157 |
| 1158 | 1158 |
| 1159 void HLoadNamedField::PrintDataTo(StringStream* stream) const { | 1159 void HLoadNamedField::PrintDataTo(StringStream* stream) { |
| 1160 object()->PrintNameTo(stream); | 1160 object()->PrintNameTo(stream); |
| 1161 stream->Add(" @%d%s", offset(), is_in_object() ? "[in-object]" : ""); | 1161 stream->Add(" @%d%s", offset(), is_in_object() ? "[in-object]" : ""); |
| 1162 } | 1162 } |
| 1163 | 1163 |
| 1164 | 1164 |
| 1165 void HLoadKeyed::PrintDataTo(StringStream* stream) const { | 1165 void HLoadKeyed::PrintDataTo(StringStream* stream) { |
| 1166 object()->PrintNameTo(stream); | 1166 object()->PrintNameTo(stream); |
| 1167 stream->Add("["); | 1167 stream->Add("["); |
| 1168 key()->PrintNameTo(stream); | 1168 key()->PrintNameTo(stream); |
| 1169 stream->Add("]"); | 1169 stream->Add("]"); |
| 1170 } | 1170 } |
| 1171 | 1171 |
| 1172 | 1172 |
| 1173 void HLoadPixelArrayElement::PrintDataTo(StringStream* stream) const { | 1173 void HLoadPixelArrayElement::PrintDataTo(StringStream* stream) { |
| 1174 external_pointer()->PrintNameTo(stream); | 1174 external_pointer()->PrintNameTo(stream); |
| 1175 stream->Add("["); | 1175 stream->Add("["); |
| 1176 key()->PrintNameTo(stream); | 1176 key()->PrintNameTo(stream); |
| 1177 stream->Add("]"); | 1177 stream->Add("]"); |
| 1178 } | 1178 } |
| 1179 | 1179 |
| 1180 | 1180 |
| 1181 void HStoreNamed::PrintDataTo(StringStream* stream) const { | 1181 void HStoreNamed::PrintDataTo(StringStream* stream) { |
| 1182 object()->PrintNameTo(stream); | 1182 object()->PrintNameTo(stream); |
| 1183 stream->Add("."); | 1183 stream->Add("."); |
| 1184 ASSERT(name()->IsString()); | 1184 ASSERT(name()->IsString()); |
| 1185 stream->Add(*String::cast(*name())->ToCString()); | 1185 stream->Add(*String::cast(*name())->ToCString()); |
| 1186 stream->Add(" = "); | 1186 stream->Add(" = "); |
| 1187 value()->PrintNameTo(stream); | 1187 value()->PrintNameTo(stream); |
| 1188 } | 1188 } |
| 1189 | 1189 |
| 1190 | 1190 |
| 1191 void HStoreNamedField::PrintDataTo(StringStream* stream) const { | 1191 void HStoreNamedField::PrintDataTo(StringStream* stream) { |
| 1192 HStoreNamed::PrintDataTo(stream); | 1192 HStoreNamed::PrintDataTo(stream); |
| 1193 if (!transition().is_null()) { | 1193 if (!transition().is_null()) { |
| 1194 stream->Add(" (transition map %p)", *transition()); | 1194 stream->Add(" (transition map %p)", *transition()); |
| 1195 } | 1195 } |
| 1196 } | 1196 } |
| 1197 | 1197 |
| 1198 | 1198 |
| 1199 void HStoreKeyed::PrintDataTo(StringStream* stream) const { | 1199 void HStoreKeyed::PrintDataTo(StringStream* stream) { |
| 1200 object()->PrintNameTo(stream); | 1200 object()->PrintNameTo(stream); |
| 1201 stream->Add("["); | 1201 stream->Add("["); |
| 1202 key()->PrintNameTo(stream); | 1202 key()->PrintNameTo(stream); |
| 1203 stream->Add("] = "); | 1203 stream->Add("] = "); |
| 1204 value()->PrintNameTo(stream); | 1204 value()->PrintNameTo(stream); |
| 1205 } | 1205 } |
| 1206 | 1206 |
| 1207 | 1207 |
| 1208 void HStorePixelArrayElement::PrintDataTo(StringStream* stream) const { | 1208 void HStorePixelArrayElement::PrintDataTo(StringStream* stream) { |
| 1209 external_pointer()->PrintNameTo(stream); | 1209 external_pointer()->PrintNameTo(stream); |
| 1210 stream->Add("["); | 1210 stream->Add("["); |
| 1211 key()->PrintNameTo(stream); | 1211 key()->PrintNameTo(stream); |
| 1212 stream->Add("] = "); | 1212 stream->Add("] = "); |
| 1213 value()->PrintNameTo(stream); | 1213 value()->PrintNameTo(stream); |
| 1214 } | 1214 } |
| 1215 | 1215 |
| 1216 | 1216 |
| 1217 void HLoadGlobal::PrintDataTo(StringStream* stream) const { | 1217 void HLoadGlobal::PrintDataTo(StringStream* stream) { |
| 1218 stream->Add("[%p]", *cell()); | 1218 stream->Add("[%p]", *cell()); |
| 1219 if (check_hole_value()) stream->Add(" (deleteable/read-only)"); | 1219 if (check_hole_value()) stream->Add(" (deleteable/read-only)"); |
| 1220 } | 1220 } |
| 1221 | 1221 |
| 1222 | 1222 |
| 1223 void HStoreGlobal::PrintDataTo(StringStream* stream) const { | 1223 void HStoreGlobal::PrintDataTo(StringStream* stream) { |
| 1224 stream->Add("[%p] = ", *cell()); | 1224 stream->Add("[%p] = ", *cell()); |
| 1225 value()->PrintNameTo(stream); | 1225 value()->PrintNameTo(stream); |
| 1226 } | 1226 } |
| 1227 | 1227 |
| 1228 | 1228 |
| 1229 void HLoadContextSlot::PrintDataTo(StringStream* stream) const { | 1229 void HLoadContextSlot::PrintDataTo(StringStream* stream) { |
| 1230 value()->PrintNameTo(stream); | 1230 value()->PrintNameTo(stream); |
| 1231 stream->Add("[%d]", slot_index()); | 1231 stream->Add("[%d]", slot_index()); |
| 1232 } | 1232 } |
| 1233 | 1233 |
| 1234 | 1234 |
| 1235 void HStoreContextSlot::PrintDataTo(StringStream* stream) const { | 1235 void HStoreContextSlot::PrintDataTo(StringStream* stream) { |
| 1236 context()->PrintNameTo(stream); | 1236 context()->PrintNameTo(stream); |
| 1237 stream->Add("[%d] = ", slot_index()); | 1237 stream->Add("[%d] = ", slot_index()); |
| 1238 value()->PrintNameTo(stream); | 1238 value()->PrintNameTo(stream); |
| 1239 } | 1239 } |
| 1240 | 1240 |
| 1241 | 1241 |
| 1242 // Implementation of type inference and type conversions. Calculates | 1242 // Implementation of type inference and type conversions. Calculates |
| 1243 // the inferred type of this instruction based on the input operands. | 1243 // the inferred type of this instruction based on the input operands. |
| 1244 | 1244 |
| 1245 HType HValue::CalculateInferredType() const { | 1245 HType HValue::CalculateInferredType() { |
| 1246 return type_; | 1246 return type_; |
| 1247 } | 1247 } |
| 1248 | 1248 |
| 1249 | 1249 |
| 1250 HType HCheckMap::CalculateInferredType() const { | 1250 HType HCheckMap::CalculateInferredType() { |
| 1251 return value()->type(); | 1251 return value()->type(); |
| 1252 } | 1252 } |
| 1253 | 1253 |
| 1254 | 1254 |
| 1255 HType HCheckFunction::CalculateInferredType() const { | 1255 HType HCheckFunction::CalculateInferredType() { |
| 1256 return value()->type(); | 1256 return value()->type(); |
| 1257 } | 1257 } |
| 1258 | 1258 |
| 1259 | 1259 |
| 1260 HType HCheckNonSmi::CalculateInferredType() const { | 1260 HType HCheckNonSmi::CalculateInferredType() { |
| 1261 // TODO(kasperl): Is there any way to signal that this isn't a smi? | 1261 // TODO(kasperl): Is there any way to signal that this isn't a smi? |
| 1262 return HType::Tagged(); | 1262 return HType::Tagged(); |
| 1263 } | 1263 } |
| 1264 | 1264 |
| 1265 | 1265 |
| 1266 HType HCheckSmi::CalculateInferredType() const { | 1266 HType HCheckSmi::CalculateInferredType() { |
| 1267 return HType::Smi(); | 1267 return HType::Smi(); |
| 1268 } | 1268 } |
| 1269 | 1269 |
| 1270 | 1270 |
| 1271 HType HPhi::CalculateInferredType() const { | 1271 HType HPhi::CalculateInferredType() { |
| 1272 HType result = HType::Uninitialized(); | 1272 HType result = HType::Uninitialized(); |
| 1273 for (int i = 0; i < OperandCount(); ++i) { | 1273 for (int i = 0; i < OperandCount(); ++i) { |
| 1274 HType current = OperandAt(i)->type(); | 1274 HType current = OperandAt(i)->type(); |
| 1275 result = result.Combine(current); | 1275 result = result.Combine(current); |
| 1276 } | 1276 } |
| 1277 return result; | 1277 return result; |
| 1278 } | 1278 } |
| 1279 | 1279 |
| 1280 | 1280 |
| 1281 HType HConstant::CalculateInferredType() const { | 1281 HType HConstant::CalculateInferredType() { |
| 1282 return constant_type_; | 1282 return constant_type_; |
| 1283 } | 1283 } |
| 1284 | 1284 |
| 1285 | 1285 |
| 1286 HType HCompare::CalculateInferredType() const { | 1286 HType HCompare::CalculateInferredType() { |
| 1287 return HType::Boolean(); | 1287 return HType::Boolean(); |
| 1288 } | 1288 } |
| 1289 | 1289 |
| 1290 | 1290 |
| 1291 HType HCompareJSObjectEq::CalculateInferredType() const { | 1291 HType HCompareJSObjectEq::CalculateInferredType() { |
| 1292 return HType::Boolean(); | 1292 return HType::Boolean(); |
| 1293 } | 1293 } |
| 1294 | 1294 |
| 1295 | 1295 |
| 1296 HType HUnaryPredicate::CalculateInferredType() const { | 1296 HType HUnaryPredicate::CalculateInferredType() { |
| 1297 return HType::Boolean(); | 1297 return HType::Boolean(); |
| 1298 } | 1298 } |
| 1299 | 1299 |
| 1300 | 1300 |
| 1301 HType HBitwiseBinaryOperation::CalculateInferredType() const { | 1301 HType HBitwiseBinaryOperation::CalculateInferredType() { |
| 1302 return HType::TaggedNumber(); | 1302 return HType::TaggedNumber(); |
| 1303 } | 1303 } |
| 1304 | 1304 |
| 1305 | 1305 |
| 1306 HType HArithmeticBinaryOperation::CalculateInferredType() const { | 1306 HType HArithmeticBinaryOperation::CalculateInferredType() { |
| 1307 return HType::TaggedNumber(); | 1307 return HType::TaggedNumber(); |
| 1308 } | 1308 } |
| 1309 | 1309 |
| 1310 | 1310 |
| 1311 HType HAdd::CalculateInferredType() const { | 1311 HType HAdd::CalculateInferredType() { |
| 1312 return HType::Tagged(); | 1312 return HType::Tagged(); |
| 1313 } | 1313 } |
| 1314 | 1314 |
| 1315 | 1315 |
| 1316 HType HBitAnd::CalculateInferredType() const { | 1316 HType HBitAnd::CalculateInferredType() { |
| 1317 return HType::TaggedNumber(); | 1317 return HType::TaggedNumber(); |
| 1318 } | 1318 } |
| 1319 | 1319 |
| 1320 | 1320 |
| 1321 HType HBitXor::CalculateInferredType() const { | 1321 HType HBitXor::CalculateInferredType() { |
| 1322 return HType::TaggedNumber(); | 1322 return HType::TaggedNumber(); |
| 1323 } | 1323 } |
| 1324 | 1324 |
| 1325 | 1325 |
| 1326 HType HBitOr::CalculateInferredType() const { | 1326 HType HBitOr::CalculateInferredType() { |
| 1327 return HType::TaggedNumber(); | 1327 return HType::TaggedNumber(); |
| 1328 } | 1328 } |
| 1329 | 1329 |
| 1330 | 1330 |
| 1331 HType HBitNot::CalculateInferredType() const { | 1331 HType HBitNot::CalculateInferredType() { |
| 1332 return HType::TaggedNumber(); | 1332 return HType::TaggedNumber(); |
| 1333 } | 1333 } |
| 1334 | 1334 |
| 1335 | 1335 |
| 1336 HType HUnaryMathOperation::CalculateInferredType() const { | 1336 HType HUnaryMathOperation::CalculateInferredType() { |
| 1337 return HType::TaggedNumber(); | 1337 return HType::TaggedNumber(); |
| 1338 } | 1338 } |
| 1339 | 1339 |
| 1340 | 1340 |
| 1341 HType HShl::CalculateInferredType() const { | 1341 HType HShl::CalculateInferredType() { |
| 1342 return HType::TaggedNumber(); | 1342 return HType::TaggedNumber(); |
| 1343 } | 1343 } |
| 1344 | 1344 |
| 1345 | 1345 |
| 1346 HType HShr::CalculateInferredType() const { | 1346 HType HShr::CalculateInferredType() { |
| 1347 return HType::TaggedNumber(); | 1347 return HType::TaggedNumber(); |
| 1348 } | 1348 } |
| 1349 | 1349 |
| 1350 | 1350 |
| 1351 HType HSar::CalculateInferredType() const { | 1351 HType HSar::CalculateInferredType() { |
| 1352 return HType::TaggedNumber(); | 1352 return HType::TaggedNumber(); |
| 1353 } | 1353 } |
| 1354 | 1354 |
| 1355 | 1355 |
| 1356 HValue* HUnaryMathOperation::EnsureAndPropagateNotMinusZero( | 1356 HValue* HUnaryMathOperation::EnsureAndPropagateNotMinusZero( |
| 1357 BitVector* visited) { | 1357 BitVector* visited) { |
| 1358 visited->Add(id()); | 1358 visited->Add(id()); |
| 1359 if (representation().IsInteger32() && | 1359 if (representation().IsInteger32() && |
| 1360 !value()->representation().IsInteger32()) { | 1360 !value()->representation().IsInteger32()) { |
| 1361 if (value()->range() == NULL || value()->range()->CanBeMinusZero()) { | 1361 if (value()->range() == NULL || value()->range()->CanBeMinusZero()) { |
| (...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1491 | 1491 |
| 1492 | 1492 |
| 1493 void HCheckPrototypeMaps::Verify() { | 1493 void HCheckPrototypeMaps::Verify() { |
| 1494 HInstruction::Verify(); | 1494 HInstruction::Verify(); |
| 1495 ASSERT(HasNoUses()); | 1495 ASSERT(HasNoUses()); |
| 1496 } | 1496 } |
| 1497 | 1497 |
| 1498 #endif | 1498 #endif |
| 1499 | 1499 |
| 1500 } } // namespace v8::internal | 1500 } } // namespace v8::internal |
| OLD | NEW |