OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 772 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
783 // implement DataEquals(), which will be used to determine if other | 783 // implement DataEquals(), which will be used to determine if other |
784 // occurrences of the instruction are indeed the same. | 784 // occurrences of the instruction are indeed the same. |
785 kUseGVN, | 785 kUseGVN, |
786 // Track instructions that are dominating side effects. If an instruction | 786 // Track instructions that are dominating side effects. If an instruction |
787 // sets this flag, it must implement SetSideEffectDominator() and should | 787 // sets this flag, it must implement SetSideEffectDominator() and should |
788 // indicate which side effects to track by setting GVN flags. | 788 // indicate which side effects to track by setting GVN flags. |
789 kTrackSideEffectDominators, | 789 kTrackSideEffectDominators, |
790 kCanOverflow, | 790 kCanOverflow, |
791 kBailoutOnMinusZero, | 791 kBailoutOnMinusZero, |
792 kCanBeDivByZero, | 792 kCanBeDivByZero, |
793 kDeoptimizeOnUndefined, | 793 kAllowUndefinedAsNaN, |
794 kIsArguments, | 794 kIsArguments, |
795 kTruncatingToInt32, | 795 kTruncatingToInt32, |
796 // Set after an instruction is killed. | 796 // Set after an instruction is killed. |
797 kIsDead, | 797 kIsDead, |
798 // Instructions that are allowed to produce full range unsigned integer | 798 // Instructions that are allowed to produce full range unsigned integer |
799 // values are marked with kUint32 flag. If arithmetic shift or a load from | 799 // values are marked with kUint32 flag. If arithmetic shift or a load from |
800 // EXTERNAL_UNSIGNED_INT_ELEMENTS array is not marked with this flag | 800 // EXTERNAL_UNSIGNED_INT_ELEMENTS array is not marked with this flag |
801 // it will deoptimize if result does not fit into signed integer range. | 801 // it will deoptimize if result does not fit into signed integer range. |
802 // HGraph::ComputeSafeUint32Operations is responsible for setting this | 802 // HGraph::ComputeSafeUint32Operations is responsible for setting this |
803 // flag. | 803 // flag. |
(...skipping 901 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1705 | 1705 |
1706 DECLARE_CONCRETE_INSTRUCTION(ForceRepresentation) | 1706 DECLARE_CONCRETE_INSTRUCTION(ForceRepresentation) |
1707 }; | 1707 }; |
1708 | 1708 |
1709 | 1709 |
1710 class HChange: public HUnaryOperation { | 1710 class HChange: public HUnaryOperation { |
1711 public: | 1711 public: |
1712 HChange(HValue* value, | 1712 HChange(HValue* value, |
1713 Representation to, | 1713 Representation to, |
1714 bool is_truncating, | 1714 bool is_truncating, |
1715 bool deoptimize_on_undefined) | 1715 bool allow_undefined_as_nan) |
1716 : HUnaryOperation(value) { | 1716 : HUnaryOperation(value) { |
1717 ASSERT(!value->representation().IsNone()); | 1717 ASSERT(!value->representation().IsNone()); |
1718 ASSERT(!to.IsNone()); | 1718 ASSERT(!to.IsNone()); |
1719 ASSERT(!value->representation().Equals(to)); | 1719 ASSERT(!value->representation().Equals(to)); |
1720 set_representation(to); | 1720 set_representation(to); |
1721 SetFlag(kUseGVN); | 1721 SetFlag(kUseGVN); |
1722 if (deoptimize_on_undefined) SetFlag(kDeoptimizeOnUndefined); | 1722 if (allow_undefined_as_nan) SetFlag(kAllowUndefinedAsNaN); |
1723 if (is_truncating) SetFlag(kTruncatingToInt32); | 1723 if (is_truncating) SetFlag(kTruncatingToInt32); |
1724 if (value->representation().IsSmi() || value->type().IsSmi()) { | 1724 if (value->representation().IsSmi() || value->type().IsSmi()) { |
1725 set_type(HType::Smi()); | 1725 set_type(HType::Smi()); |
1726 } else { | 1726 } else { |
1727 set_type(HType::TaggedNumber()); | 1727 set_type(HType::TaggedNumber()); |
1728 if (to.IsTagged()) SetGVNFlag(kChangesNewSpacePromotion); | 1728 if (to.IsTagged()) SetGVNFlag(kChangesNewSpacePromotion); |
1729 } | 1729 } |
1730 } | 1730 } |
1731 | 1731 |
1732 virtual HValue* EnsureAndPropagateNotMinusZero(BitVector* visited); | 1732 virtual HValue* EnsureAndPropagateNotMinusZero(BitVector* visited); |
1733 virtual HType CalculateInferredType(); | 1733 virtual HType CalculateInferredType(); |
1734 virtual HValue* Canonicalize(); | 1734 virtual HValue* Canonicalize(); |
1735 | 1735 |
1736 Representation from() const { return value()->representation(); } | 1736 Representation from() const { return value()->representation(); } |
1737 Representation to() const { return representation(); } | 1737 Representation to() const { return representation(); } |
1738 bool deoptimize_on_undefined() const { | 1738 bool allow_undefined_as_nan() const { |
1739 return CheckFlag(kDeoptimizeOnUndefined); | 1739 return CheckFlag(kAllowUndefinedAsNaN); |
1740 } | 1740 } |
1741 bool deoptimize_on_minus_zero() const { | 1741 bool deoptimize_on_minus_zero() const { |
1742 return CheckFlag(kBailoutOnMinusZero); | 1742 return CheckFlag(kBailoutOnMinusZero); |
1743 } | 1743 } |
1744 virtual Representation RequiredInputRepresentation(int index) { | 1744 virtual Representation RequiredInputRepresentation(int index) { |
1745 return from(); | 1745 return from(); |
1746 } | 1746 } |
1747 | 1747 |
1748 virtual Range* InferRange(Zone* zone); | 1748 virtual Range* InferRange(Zone* zone); |
1749 | 1749 |
1750 virtual void PrintDataTo(StringStream* stream); | 1750 virtual void PrintDataTo(StringStream* stream); |
1751 | 1751 |
1752 DECLARE_CONCRETE_INSTRUCTION(Change) | 1752 DECLARE_CONCRETE_INSTRUCTION(Change) |
1753 | 1753 |
1754 protected: | 1754 protected: |
1755 virtual bool DataEquals(HValue* other) { return true; } | 1755 virtual bool DataEquals(HValue* other) { return true; } |
1756 | 1756 |
1757 private: | 1757 private: |
1758 virtual bool IsDeletable() const { | 1758 virtual bool IsDeletable() const { |
1759 return !from().IsTagged() || value()->type().IsSmi(); | 1759 return !from().IsTagged() || value()->type().IsSmi(); |
1760 } | 1760 } |
1761 }; | 1761 }; |
1762 | 1762 |
1763 | 1763 |
1764 class HClampToUint8: public HUnaryOperation { | 1764 class HClampToUint8: public HUnaryOperation { |
1765 public: | 1765 public: |
1766 explicit HClampToUint8(HValue* value) | 1766 explicit HClampToUint8(HValue* value) |
1767 : HUnaryOperation(value) { | 1767 : HUnaryOperation(value) { |
1768 set_representation(Representation::Integer32()); | 1768 set_representation(Representation::Integer32()); |
| 1769 SetFlag(kAllowUndefinedAsNaN); |
1769 SetFlag(kUseGVN); | 1770 SetFlag(kUseGVN); |
1770 } | 1771 } |
1771 | 1772 |
1772 virtual Representation RequiredInputRepresentation(int index) { | 1773 virtual Representation RequiredInputRepresentation(int index) { |
1773 return Representation::None(); | 1774 return Representation::None(); |
1774 } | 1775 } |
1775 | 1776 |
1776 DECLARE_CONCRETE_INSTRUCTION(ClampToUint8) | 1777 DECLARE_CONCRETE_INSTRUCTION(ClampToUint8) |
1777 | 1778 |
1778 protected: | 1779 protected: |
(...skipping 706 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2485 virtual bool IsDeletable() const { return true; } | 2486 virtual bool IsDeletable() const { return true; } |
2486 }; | 2487 }; |
2487 | 2488 |
2488 | 2489 |
2489 class HBitNot: public HUnaryOperation { | 2490 class HBitNot: public HUnaryOperation { |
2490 public: | 2491 public: |
2491 explicit HBitNot(HValue* value) : HUnaryOperation(value) { | 2492 explicit HBitNot(HValue* value) : HUnaryOperation(value) { |
2492 set_representation(Representation::Integer32()); | 2493 set_representation(Representation::Integer32()); |
2493 SetFlag(kUseGVN); | 2494 SetFlag(kUseGVN); |
2494 SetFlag(kTruncatingToInt32); | 2495 SetFlag(kTruncatingToInt32); |
| 2496 SetFlag(kAllowUndefinedAsNaN); |
2495 } | 2497 } |
2496 | 2498 |
2497 virtual Representation RequiredInputRepresentation(int index) { | 2499 virtual Representation RequiredInputRepresentation(int index) { |
2498 return Representation::Integer32(); | 2500 return Representation::Integer32(); |
2499 } | 2501 } |
2500 virtual Representation observed_input_representation(int index) { | 2502 virtual Representation observed_input_representation(int index) { |
2501 return Representation::Integer32(); | 2503 return Representation::Integer32(); |
2502 } | 2504 } |
2503 virtual HType CalculateInferredType(); | 2505 virtual HType CalculateInferredType(); |
2504 | 2506 |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2594 break; | 2596 break; |
2595 case kMathExp: | 2597 case kMathExp: |
2596 case kMathSqrt: | 2598 case kMathSqrt: |
2597 case kMathPowHalf: | 2599 case kMathPowHalf: |
2598 set_representation(Representation::Double()); | 2600 set_representation(Representation::Double()); |
2599 break; | 2601 break; |
2600 default: | 2602 default: |
2601 UNREACHABLE(); | 2603 UNREACHABLE(); |
2602 } | 2604 } |
2603 SetFlag(kUseGVN); | 2605 SetFlag(kUseGVN); |
| 2606 SetFlag(kAllowUndefinedAsNaN); |
2604 } | 2607 } |
2605 | 2608 |
2606 virtual bool IsDeletable() const { return true; } | 2609 virtual bool IsDeletable() const { return true; } |
2607 | 2610 |
2608 BuiltinFunctionId op_; | 2611 BuiltinFunctionId op_; |
2609 }; | 2612 }; |
2610 | 2613 |
2611 | 2614 |
2612 class HLoadExternalArrayPointer: public HUnaryOperation { | 2615 class HLoadExternalArrayPointer: public HUnaryOperation { |
2613 public: | 2616 public: |
(...skipping 321 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2935 : inputs_(2, zone), | 2938 : inputs_(2, zone), |
2936 merged_index_(merged_index), | 2939 merged_index_(merged_index), |
2937 phi_id_(-1), | 2940 phi_id_(-1), |
2938 is_convertible_to_integer_(true) { | 2941 is_convertible_to_integer_(true) { |
2939 for (int i = 0; i < Representation::kNumRepresentations; i++) { | 2942 for (int i = 0; i < Representation::kNumRepresentations; i++) { |
2940 non_phi_uses_[i] = 0; | 2943 non_phi_uses_[i] = 0; |
2941 indirect_uses_[i] = 0; | 2944 indirect_uses_[i] = 0; |
2942 } | 2945 } |
2943 ASSERT(merged_index >= 0); | 2946 ASSERT(merged_index >= 0); |
2944 SetFlag(kFlexibleRepresentation); | 2947 SetFlag(kFlexibleRepresentation); |
| 2948 SetFlag(kAllowUndefinedAsNaN); |
2945 } | 2949 } |
2946 | 2950 |
2947 virtual Representation RepresentationFromInputs(); | 2951 virtual Representation RepresentationFromInputs(); |
2948 | 2952 |
2949 virtual Range* InferRange(Zone* zone); | 2953 virtual Range* InferRange(Zone* zone); |
2950 virtual void InferRepresentation(HInferRepresentation* h_infer); | 2954 virtual void InferRepresentation(HInferRepresentation* h_infer); |
2951 Representation RepresentationFromUseRequirements(); | 2955 Representation RepresentationFromUseRequirements(); |
2952 virtual Representation RequiredInputRepresentation(int index) { | 2956 virtual Representation RequiredInputRepresentation(int index) { |
2953 return representation(); | 2957 return representation(); |
2954 } | 2958 } |
(...skipping 703 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3658 } | 3662 } |
3659 }; | 3663 }; |
3660 | 3664 |
3661 | 3665 |
3662 class HBitwiseBinaryOperation: public HBinaryOperation { | 3666 class HBitwiseBinaryOperation: public HBinaryOperation { |
3663 public: | 3667 public: |
3664 HBitwiseBinaryOperation(HValue* context, HValue* left, HValue* right) | 3668 HBitwiseBinaryOperation(HValue* context, HValue* left, HValue* right) |
3665 : HBinaryOperation(context, left, right) { | 3669 : HBinaryOperation(context, left, right) { |
3666 SetFlag(kFlexibleRepresentation); | 3670 SetFlag(kFlexibleRepresentation); |
3667 SetFlag(kTruncatingToInt32); | 3671 SetFlag(kTruncatingToInt32); |
| 3672 SetFlag(kAllowUndefinedAsNaN); |
3668 SetAllSideEffects(); | 3673 SetAllSideEffects(); |
3669 } | 3674 } |
3670 | 3675 |
3671 virtual Representation RequiredInputRepresentation(int index) { | 3676 virtual Representation RequiredInputRepresentation(int index) { |
3672 return index == 0 | 3677 return index == 0 |
3673 ? Representation::Tagged() | 3678 ? Representation::Tagged() |
3674 : representation(); | 3679 : representation(); |
3675 } | 3680 } |
3676 | 3681 |
3677 virtual void RepresentationChanged(Representation to) { | 3682 virtual void RepresentationChanged(Representation to) { |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3712 class HMathFloorOfDiv: public HBinaryOperation { | 3717 class HMathFloorOfDiv: public HBinaryOperation { |
3713 public: | 3718 public: |
3714 HMathFloorOfDiv(HValue* context, HValue* left, HValue* right) | 3719 HMathFloorOfDiv(HValue* context, HValue* left, HValue* right) |
3715 : HBinaryOperation(context, left, right) { | 3720 : HBinaryOperation(context, left, right) { |
3716 set_representation(Representation::Integer32()); | 3721 set_representation(Representation::Integer32()); |
3717 SetFlag(kUseGVN); | 3722 SetFlag(kUseGVN); |
3718 SetFlag(kCanOverflow); | 3723 SetFlag(kCanOverflow); |
3719 if (!right->IsConstant()) { | 3724 if (!right->IsConstant()) { |
3720 SetFlag(kCanBeDivByZero); | 3725 SetFlag(kCanBeDivByZero); |
3721 } | 3726 } |
| 3727 SetFlag(kAllowUndefinedAsNaN); |
3722 } | 3728 } |
3723 | 3729 |
3724 virtual HValue* EnsureAndPropagateNotMinusZero(BitVector* visited); | 3730 virtual HValue* EnsureAndPropagateNotMinusZero(BitVector* visited); |
3725 | 3731 |
3726 virtual Representation RequiredInputRepresentation(int index) { | 3732 virtual Representation RequiredInputRepresentation(int index) { |
3727 return Representation::Integer32(); | 3733 return Representation::Integer32(); |
3728 } | 3734 } |
3729 | 3735 |
3730 DECLARE_CONCRETE_INSTRUCTION(MathFloorOfDiv) | 3736 DECLARE_CONCRETE_INSTRUCTION(MathFloorOfDiv) |
3731 | 3737 |
3732 protected: | 3738 protected: |
3733 virtual bool DataEquals(HValue* other) { return true; } | 3739 virtual bool DataEquals(HValue* other) { return true; } |
3734 | 3740 |
3735 private: | 3741 private: |
3736 virtual bool IsDeletable() const { return true; } | 3742 virtual bool IsDeletable() const { return true; } |
3737 }; | 3743 }; |
3738 | 3744 |
3739 | 3745 |
3740 class HArithmeticBinaryOperation: public HBinaryOperation { | 3746 class HArithmeticBinaryOperation: public HBinaryOperation { |
3741 public: | 3747 public: |
3742 HArithmeticBinaryOperation(HValue* context, HValue* left, HValue* right) | 3748 HArithmeticBinaryOperation(HValue* context, HValue* left, HValue* right) |
3743 : HBinaryOperation(context, left, right) { | 3749 : HBinaryOperation(context, left, right) { |
3744 SetAllSideEffects(); | 3750 SetAllSideEffects(); |
3745 SetFlag(kFlexibleRepresentation); | 3751 SetFlag(kFlexibleRepresentation); |
| 3752 SetFlag(kAllowUndefinedAsNaN); |
3746 } | 3753 } |
3747 | 3754 |
3748 virtual void RepresentationChanged(Representation to) { | 3755 virtual void RepresentationChanged(Representation to) { |
3749 if (to.IsTagged()) { | 3756 if (to.IsTagged()) { |
3750 SetAllSideEffects(); | 3757 SetAllSideEffects(); |
3751 ClearFlag(kUseGVN); | 3758 ClearFlag(kUseGVN); |
3752 } else { | 3759 } else { |
3753 ClearAllSideEffects(); | 3760 ClearAllSideEffects(); |
3754 SetFlag(kUseGVN); | 3761 SetFlag(kUseGVN); |
3755 } | 3762 } |
(...skipping 1965 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5721 SetOperandAt(0, obj); | 5728 SetOperandAt(0, obj); |
5722 SetOperandAt(1, key); | 5729 SetOperandAt(1, key); |
5723 SetOperandAt(2, val); | 5730 SetOperandAt(2, val); |
5724 | 5731 |
5725 if (IsFastObjectElementsKind(elements_kind)) { | 5732 if (IsFastObjectElementsKind(elements_kind)) { |
5726 SetFlag(kTrackSideEffectDominators); | 5733 SetFlag(kTrackSideEffectDominators); |
5727 SetGVNFlag(kDependsOnNewSpacePromotion); | 5734 SetGVNFlag(kDependsOnNewSpacePromotion); |
5728 } | 5735 } |
5729 if (is_external()) { | 5736 if (is_external()) { |
5730 SetGVNFlag(kChangesSpecializedArrayElements); | 5737 SetGVNFlag(kChangesSpecializedArrayElements); |
| 5738 SetFlag(kAllowUndefinedAsNaN); |
5731 } else if (IsFastDoubleElementsKind(elements_kind)) { | 5739 } else if (IsFastDoubleElementsKind(elements_kind)) { |
5732 SetGVNFlag(kChangesDoubleArrayElements); | 5740 SetGVNFlag(kChangesDoubleArrayElements); |
5733 SetFlag(kDeoptimizeOnUndefined); | |
5734 } else if (IsFastSmiElementsKind(elements_kind)) { | 5741 } else if (IsFastSmiElementsKind(elements_kind)) { |
5735 SetGVNFlag(kChangesArrayElements); | 5742 SetGVNFlag(kChangesArrayElements); |
5736 SetFlag(kDeoptimizeOnUndefined); | |
5737 } else { | 5743 } else { |
5738 SetGVNFlag(kChangesArrayElements); | 5744 SetGVNFlag(kChangesArrayElements); |
5739 } | 5745 } |
5740 | 5746 |
5741 // EXTERNAL_{UNSIGNED_,}{BYTE,SHORT,INT}_ELEMENTS are truncating. | 5747 // EXTERNAL_{UNSIGNED_,}{BYTE,SHORT,INT}_ELEMENTS are truncating. |
5742 if (elements_kind >= EXTERNAL_BYTE_ELEMENTS && | 5748 if (elements_kind >= EXTERNAL_BYTE_ELEMENTS && |
5743 elements_kind <= EXTERNAL_UNSIGNED_INT_ELEMENTS) { | 5749 elements_kind <= EXTERNAL_UNSIGNED_INT_ELEMENTS) { |
5744 SetFlag(kTruncatingToInt32); | 5750 SetFlag(kTruncatingToInt32); |
5745 } | 5751 } |
5746 } | 5752 } |
(...skipping 744 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6491 virtual bool IsDeletable() const { return true; } | 6497 virtual bool IsDeletable() const { return true; } |
6492 }; | 6498 }; |
6493 | 6499 |
6494 | 6500 |
6495 #undef DECLARE_INSTRUCTION | 6501 #undef DECLARE_INSTRUCTION |
6496 #undef DECLARE_CONCRETE_INSTRUCTION | 6502 #undef DECLARE_CONCRETE_INSTRUCTION |
6497 | 6503 |
6498 } } // namespace v8::internal | 6504 } } // namespace v8::internal |
6499 | 6505 |
6500 #endif // V8_HYDROGEN_INSTRUCTIONS_H_ | 6506 #endif // V8_HYDROGEN_INSTRUCTIONS_H_ |
OLD | NEW |