OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "v8.h" | 5 #include "v8.h" |
6 | 6 |
7 #include "double.h" | 7 #include "double.h" |
8 #include "factory.h" | 8 #include "factory.h" |
9 #include "hydrogen-infer-representation.h" | 9 #include "hydrogen-infer-representation.h" |
10 #include "property-details-inl.h" | 10 #include "property-details-inl.h" |
(...skipping 1362 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1373 } | 1373 } |
1374 | 1374 |
1375 | 1375 |
1376 void HCheckMapValue::PrintDataTo(StringStream* stream) { | 1376 void HCheckMapValue::PrintDataTo(StringStream* stream) { |
1377 value()->PrintNameTo(stream); | 1377 value()->PrintNameTo(stream); |
1378 stream->Add(" "); | 1378 stream->Add(" "); |
1379 map()->PrintNameTo(stream); | 1379 map()->PrintNameTo(stream); |
1380 } | 1380 } |
1381 | 1381 |
1382 | 1382 |
| 1383 HValue* HCheckMapValue::Canonicalize() { |
| 1384 if (map()->IsConstant()) { |
| 1385 HConstant* c_map = HConstant::cast(map()); |
| 1386 return HCheckMaps::CreateAndInsertAfter( |
| 1387 block()->graph()->zone(), value(), c_map->MapValue(), |
| 1388 c_map->HasStableMapValue(), this); |
| 1389 } |
| 1390 return this; |
| 1391 } |
| 1392 |
| 1393 |
1383 void HForInPrepareMap::PrintDataTo(StringStream* stream) { | 1394 void HForInPrepareMap::PrintDataTo(StringStream* stream) { |
1384 enumerable()->PrintNameTo(stream); | 1395 enumerable()->PrintNameTo(stream); |
1385 } | 1396 } |
1386 | 1397 |
1387 | 1398 |
1388 void HForInCacheArray::PrintDataTo(StringStream* stream) { | 1399 void HForInCacheArray::PrintDataTo(StringStream* stream) { |
1389 enumerable()->PrintNameTo(stream); | 1400 enumerable()->PrintNameTo(stream); |
1390 stream->Add(" "); | 1401 stream->Add(" "); |
1391 map()->PrintNameTo(stream); | 1402 map()->PrintNameTo(stream); |
1392 stream->Add("[%d]", idx_); | 1403 stream->Add("[%d]", idx_); |
(...skipping 282 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1675 for (int i = 1; i < maps()->size(); ++i) { | 1686 for (int i = 1; i < maps()->size(); ++i) { |
1676 stream->Add(",%p", *maps()->at(i).handle()); | 1687 stream->Add(",%p", *maps()->at(i).handle()); |
1677 } | 1688 } |
1678 stream->Add("]%s", IsStabilityCheck() ? "(stability-check)" : ""); | 1689 stream->Add("]%s", IsStabilityCheck() ? "(stability-check)" : ""); |
1679 } | 1690 } |
1680 | 1691 |
1681 | 1692 |
1682 HValue* HCheckMaps::Canonicalize() { | 1693 HValue* HCheckMaps::Canonicalize() { |
1683 if (!IsStabilityCheck() && maps_are_stable() && value()->IsConstant()) { | 1694 if (!IsStabilityCheck() && maps_are_stable() && value()->IsConstant()) { |
1684 HConstant* c_value = HConstant::cast(value()); | 1695 HConstant* c_value = HConstant::cast(value()); |
1685 if (c_value->HasObjectMap() && c_value->ObjectMapIsStable()) { | 1696 if (c_value->HasObjectMap()) { |
1686 for (int i = 0; i < maps()->size(); ++i) { | 1697 for (int i = 0; i < maps()->size(); ++i) { |
1687 if (c_value->ObjectMap() == maps()->at(i)) { | 1698 if (c_value->ObjectMap() == maps()->at(i)) { |
1688 if (maps()->size() > 1) { | 1699 if (maps()->size() > 1) { |
1689 set_maps(new(block()->graph()->zone()) UniqueSet<Map>( | 1700 set_maps(new(block()->graph()->zone()) UniqueSet<Map>( |
1690 maps()->at(i), block()->graph()->zone())); | 1701 maps()->at(i), block()->graph()->zone())); |
1691 } | 1702 } |
1692 MarkAsStabilityCheck(); | 1703 MarkAsStabilityCheck(); |
1693 break; | 1704 break; |
1694 } | 1705 } |
1695 } | 1706 } |
(...skipping 982 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2678 static bool IsInteger32(double value) { | 2689 static bool IsInteger32(double value) { |
2679 double roundtrip_value = static_cast<double>(static_cast<int32_t>(value)); | 2690 double roundtrip_value = static_cast<double>(static_cast<int32_t>(value)); |
2680 return BitCast<int64_t>(roundtrip_value) == BitCast<int64_t>(value); | 2691 return BitCast<int64_t>(roundtrip_value) == BitCast<int64_t>(value); |
2681 } | 2692 } |
2682 | 2693 |
2683 | 2694 |
2684 HConstant::HConstant(Handle<Object> object, Representation r) | 2695 HConstant::HConstant(Handle<Object> object, Representation r) |
2685 : HTemplateInstruction<0>(HType::TypeFromValue(object)), | 2696 : HTemplateInstruction<0>(HType::TypeFromValue(object)), |
2686 object_(Unique<Object>::CreateUninitialized(object)), | 2697 object_(Unique<Object>::CreateUninitialized(object)), |
2687 object_map_(Handle<Map>::null()), | 2698 object_map_(Handle<Map>::null()), |
2688 object_map_is_stable_(false), | 2699 has_stable_map_value_(false), |
2689 has_smi_value_(false), | 2700 has_smi_value_(false), |
2690 has_int32_value_(false), | 2701 has_int32_value_(false), |
2691 has_double_value_(false), | 2702 has_double_value_(false), |
2692 has_external_reference_value_(false), | 2703 has_external_reference_value_(false), |
2693 is_not_in_new_space_(true), | 2704 is_not_in_new_space_(true), |
2694 boolean_value_(object->BooleanValue()), | 2705 boolean_value_(object->BooleanValue()), |
2695 is_undetectable_(false), | 2706 is_undetectable_(false), |
2696 instance_type_(kUnknownInstanceType) { | 2707 instance_type_(kUnknownInstanceType) { |
2697 if (object->IsHeapObject()) { | 2708 if (object->IsHeapObject()) { |
2698 Isolate* isolate = Handle<HeapObject>::cast(object)->GetIsolate(); | 2709 Handle<HeapObject> heap_object = Handle<HeapObject>::cast(object); |
2699 Handle<Map> map(Handle<HeapObject>::cast(object)->map(), isolate); | 2710 Isolate* isolate = heap_object->GetIsolate(); |
| 2711 Handle<Map> map(heap_object->map(), isolate); |
2700 is_not_in_new_space_ = !isolate->heap()->InNewSpace(*object); | 2712 is_not_in_new_space_ = !isolate->heap()->InNewSpace(*object); |
2701 instance_type_ = map->instance_type(); | 2713 instance_type_ = map->instance_type(); |
2702 is_undetectable_ = map->is_undetectable(); | 2714 is_undetectable_ = map->is_undetectable(); |
2703 object_map_ = Unique<Map>::CreateImmovable(map); | 2715 if (map->is_stable()) object_map_ = Unique<Map>::CreateImmovable(map); |
2704 object_map_is_stable_ = map->is_stable(); | 2716 has_stable_map_value_ = (instance_type_ == MAP_TYPE && |
| 2717 Handle<Map>::cast(heap_object)->is_stable()); |
2705 } | 2718 } |
2706 if (object->IsNumber()) { | 2719 if (object->IsNumber()) { |
2707 double n = object->Number(); | 2720 double n = object->Number(); |
2708 has_int32_value_ = IsInteger32(n); | 2721 has_int32_value_ = IsInteger32(n); |
2709 int32_value_ = DoubleToInt32(n); | 2722 int32_value_ = DoubleToInt32(n); |
2710 has_smi_value_ = has_int32_value_ && Smi::IsValid(int32_value_); | 2723 has_smi_value_ = has_int32_value_ && Smi::IsValid(int32_value_); |
2711 double_value_ = n; | 2724 double_value_ = n; |
2712 has_double_value_ = true; | 2725 has_double_value_ = true; |
2713 // TODO(titzer): if this heap number is new space, tenure a new one. | 2726 // TODO(titzer): if this heap number is new space, tenure a new one. |
2714 } | 2727 } |
2715 | 2728 |
2716 Initialize(r); | 2729 Initialize(r); |
2717 } | 2730 } |
2718 | 2731 |
2719 | 2732 |
2720 HConstant::HConstant(Unique<Object> unique, | 2733 HConstant::HConstant(Unique<Object> object, |
| 2734 Unique<Map> object_map, |
| 2735 bool has_stable_map_value, |
2721 Representation r, | 2736 Representation r, |
2722 HType type, | 2737 HType type, |
2723 bool is_not_in_new_space, | 2738 bool is_not_in_new_space, |
2724 bool boolean_value, | 2739 bool boolean_value, |
2725 bool is_undetectable, | 2740 bool is_undetectable, |
2726 InstanceType instance_type) | 2741 InstanceType instance_type) |
2727 : HTemplateInstruction<0>(type), | 2742 : HTemplateInstruction<0>(type), |
2728 object_(unique), | 2743 object_(object), |
2729 object_map_(Handle<Map>::null()), | 2744 object_map_(object_map), |
2730 object_map_is_stable_(false), | 2745 has_stable_map_value_(has_stable_map_value), |
2731 has_smi_value_(false), | 2746 has_smi_value_(false), |
2732 has_int32_value_(false), | 2747 has_int32_value_(false), |
2733 has_double_value_(false), | 2748 has_double_value_(false), |
2734 has_external_reference_value_(false), | 2749 has_external_reference_value_(false), |
2735 is_not_in_new_space_(is_not_in_new_space), | 2750 is_not_in_new_space_(is_not_in_new_space), |
2736 boolean_value_(boolean_value), | 2751 boolean_value_(boolean_value), |
2737 is_undetectable_(is_undetectable), | 2752 is_undetectable_(is_undetectable), |
2738 instance_type_(instance_type) { | 2753 instance_type_(instance_type) { |
2739 ASSERT(!unique.handle().is_null()); | 2754 ASSERT(!object.handle().is_null()); |
2740 ASSERT(!type.IsTaggedNumber()); | 2755 ASSERT(!type.IsTaggedNumber()); |
2741 Initialize(r); | 2756 Initialize(r); |
2742 } | 2757 } |
2743 | 2758 |
2744 | 2759 |
2745 HConstant::HConstant(int32_t integer_value, | 2760 HConstant::HConstant(int32_t integer_value, |
2746 Representation r, | 2761 Representation r, |
2747 bool is_not_in_new_space, | 2762 bool is_not_in_new_space, |
2748 Unique<Object> object) | 2763 Unique<Object> object) |
2749 : object_(object), | 2764 : object_(object), |
2750 object_map_(Handle<Map>::null()), | 2765 object_map_(Handle<Map>::null()), |
2751 object_map_is_stable_(false), | 2766 has_stable_map_value_(false), |
2752 has_smi_value_(Smi::IsValid(integer_value)), | 2767 has_smi_value_(Smi::IsValid(integer_value)), |
2753 has_int32_value_(true), | 2768 has_int32_value_(true), |
2754 has_double_value_(true), | 2769 has_double_value_(true), |
2755 has_external_reference_value_(false), | 2770 has_external_reference_value_(false), |
2756 is_not_in_new_space_(is_not_in_new_space), | 2771 is_not_in_new_space_(is_not_in_new_space), |
2757 boolean_value_(integer_value != 0), | 2772 boolean_value_(integer_value != 0), |
2758 is_undetectable_(false), | 2773 is_undetectable_(false), |
2759 int32_value_(integer_value), | 2774 int32_value_(integer_value), |
2760 double_value_(FastI2D(integer_value)), | 2775 double_value_(FastI2D(integer_value)), |
2761 instance_type_(kUnknownInstanceType) { | 2776 instance_type_(kUnknownInstanceType) { |
2762 // It's possible to create a constant with a value in Smi-range but stored | 2777 // It's possible to create a constant with a value in Smi-range but stored |
2763 // in a (pre-existing) HeapNumber. See crbug.com/349878. | 2778 // in a (pre-existing) HeapNumber. See crbug.com/349878. |
2764 bool could_be_heapobject = r.IsTagged() && !object.handle().is_null(); | 2779 bool could_be_heapobject = r.IsTagged() && !object.handle().is_null(); |
2765 bool is_smi = has_smi_value_ && !could_be_heapobject; | 2780 bool is_smi = has_smi_value_ && !could_be_heapobject; |
2766 set_type(is_smi ? HType::Smi() : HType::TaggedNumber()); | 2781 set_type(is_smi ? HType::Smi() : HType::TaggedNumber()); |
2767 Initialize(r); | 2782 Initialize(r); |
2768 } | 2783 } |
2769 | 2784 |
2770 | 2785 |
2771 HConstant::HConstant(double double_value, | 2786 HConstant::HConstant(double double_value, |
2772 Representation r, | 2787 Representation r, |
2773 bool is_not_in_new_space, | 2788 bool is_not_in_new_space, |
2774 Unique<Object> object) | 2789 Unique<Object> object) |
2775 : object_(object), | 2790 : object_(object), |
2776 object_map_(Handle<Map>::null()), | 2791 object_map_(Handle<Map>::null()), |
2777 object_map_is_stable_(false), | 2792 has_stable_map_value_(false), |
2778 has_int32_value_(IsInteger32(double_value)), | 2793 has_int32_value_(IsInteger32(double_value)), |
2779 has_double_value_(true), | 2794 has_double_value_(true), |
2780 has_external_reference_value_(false), | 2795 has_external_reference_value_(false), |
2781 is_not_in_new_space_(is_not_in_new_space), | 2796 is_not_in_new_space_(is_not_in_new_space), |
2782 boolean_value_(double_value != 0 && !std::isnan(double_value)), | 2797 boolean_value_(double_value != 0 && !std::isnan(double_value)), |
2783 is_undetectable_(false), | 2798 is_undetectable_(false), |
2784 int32_value_(DoubleToInt32(double_value)), | 2799 int32_value_(DoubleToInt32(double_value)), |
2785 double_value_(double_value), | 2800 double_value_(double_value), |
2786 instance_type_(kUnknownInstanceType) { | 2801 instance_type_(kUnknownInstanceType) { |
2787 has_smi_value_ = has_int32_value_ && Smi::IsValid(int32_value_); | 2802 has_smi_value_ = has_int32_value_ && Smi::IsValid(int32_value_); |
2788 // It's possible to create a constant with a value in Smi-range but stored | 2803 // It's possible to create a constant with a value in Smi-range but stored |
2789 // in a (pre-existing) HeapNumber. See crbug.com/349878. | 2804 // in a (pre-existing) HeapNumber. See crbug.com/349878. |
2790 bool could_be_heapobject = r.IsTagged() && !object.handle().is_null(); | 2805 bool could_be_heapobject = r.IsTagged() && !object.handle().is_null(); |
2791 bool is_smi = has_smi_value_ && !could_be_heapobject; | 2806 bool is_smi = has_smi_value_ && !could_be_heapobject; |
2792 set_type(is_smi ? HType::Smi() : HType::TaggedNumber()); | 2807 set_type(is_smi ? HType::Smi() : HType::TaggedNumber()); |
2793 Initialize(r); | 2808 Initialize(r); |
2794 } | 2809 } |
2795 | 2810 |
2796 | 2811 |
2797 HConstant::HConstant(ExternalReference reference) | 2812 HConstant::HConstant(ExternalReference reference) |
2798 : HTemplateInstruction<0>(HType::None()), | 2813 : HTemplateInstruction<0>(HType::None()), |
2799 object_(Unique<Object>(Handle<Object>::null())), | 2814 object_(Unique<Object>(Handle<Object>::null())), |
2800 object_map_(Handle<Map>::null()), | 2815 object_map_(Handle<Map>::null()), |
2801 object_map_is_stable_(false), | 2816 has_stable_map_value_(false), |
2802 has_smi_value_(false), | 2817 has_smi_value_(false), |
2803 has_int32_value_(false), | 2818 has_int32_value_(false), |
2804 has_double_value_(false), | 2819 has_double_value_(false), |
2805 has_external_reference_value_(true), | 2820 has_external_reference_value_(true), |
2806 is_not_in_new_space_(true), | 2821 is_not_in_new_space_(true), |
2807 boolean_value_(true), | 2822 boolean_value_(true), |
2808 is_undetectable_(false), | 2823 is_undetectable_(false), |
2809 external_reference_value_(reference), | 2824 external_reference_value_(reference), |
2810 instance_type_(kUnknownInstanceType) { | 2825 instance_type_(kUnknownInstanceType) { |
2811 Initialize(Representation::External()); | 2826 Initialize(Representation::External()); |
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2897 return new(zone) HConstant(int32_value_, r, is_not_in_new_space_, object_); | 2912 return new(zone) HConstant(int32_value_, r, is_not_in_new_space_, object_); |
2898 } | 2913 } |
2899 if (has_double_value_) { | 2914 if (has_double_value_) { |
2900 return new(zone) HConstant(double_value_, r, is_not_in_new_space_, object_); | 2915 return new(zone) HConstant(double_value_, r, is_not_in_new_space_, object_); |
2901 } | 2916 } |
2902 if (has_external_reference_value_) { | 2917 if (has_external_reference_value_) { |
2903 return new(zone) HConstant(external_reference_value_); | 2918 return new(zone) HConstant(external_reference_value_); |
2904 } | 2919 } |
2905 ASSERT(!object_.handle().is_null()); | 2920 ASSERT(!object_.handle().is_null()); |
2906 return new(zone) HConstant(object_, | 2921 return new(zone) HConstant(object_, |
| 2922 object_map_, |
| 2923 has_stable_map_value_, |
2907 r, | 2924 r, |
2908 type_, | 2925 type_, |
2909 is_not_in_new_space_, | 2926 is_not_in_new_space_, |
2910 boolean_value_, | 2927 boolean_value_, |
2911 is_undetectable_, | 2928 is_undetectable_, |
2912 instance_type_); | 2929 instance_type_); |
2913 } | 2930 } |
2914 | 2931 |
2915 | 2932 |
2916 Maybe<HConstant*> HConstant::CopyToTruncatedInt32(Zone* zone) { | 2933 Maybe<HConstant*> HConstant::CopyToTruncatedInt32(Zone* zone) { |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2948 void HConstant::PrintDataTo(StringStream* stream) { | 2965 void HConstant::PrintDataTo(StringStream* stream) { |
2949 if (has_int32_value_) { | 2966 if (has_int32_value_) { |
2950 stream->Add("%d ", int32_value_); | 2967 stream->Add("%d ", int32_value_); |
2951 } else if (has_double_value_) { | 2968 } else if (has_double_value_) { |
2952 stream->Add("%f ", FmtElm(double_value_)); | 2969 stream->Add("%f ", FmtElm(double_value_)); |
2953 } else if (has_external_reference_value_) { | 2970 } else if (has_external_reference_value_) { |
2954 stream->Add("%p ", reinterpret_cast<void*>( | 2971 stream->Add("%p ", reinterpret_cast<void*>( |
2955 external_reference_value_.address())); | 2972 external_reference_value_.address())); |
2956 } else { | 2973 } else { |
2957 handle(Isolate::Current())->ShortPrint(stream); | 2974 handle(Isolate::Current())->ShortPrint(stream); |
| 2975 stream->Add(" "); |
| 2976 if (HasStableMapValue()) { |
| 2977 stream->Add("[stable-map] "); |
| 2978 } |
| 2979 if (HasObjectMap()) { |
| 2980 stream->Add("[map %p] ", *ObjectMap().handle()); |
| 2981 } |
2958 } | 2982 } |
2959 if (!is_not_in_new_space_) { | 2983 if (!is_not_in_new_space_) { |
2960 stream->Add("[new space] "); | 2984 stream->Add("[new space] "); |
2961 } | 2985 } |
2962 } | 2986 } |
2963 | 2987 |
2964 | 2988 |
2965 void HBinaryOperation::PrintDataTo(StringStream* stream) { | 2989 void HBinaryOperation::PrintDataTo(StringStream* stream) { |
2966 left()->PrintNameTo(stream); | 2990 left()->PrintNameTo(stream); |
2967 stream->Add(" "); | 2991 stream->Add(" "); |
(...skipping 1784 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4752 break; | 4776 break; |
4753 case kExternalMemory: | 4777 case kExternalMemory: |
4754 stream->Add("[external-memory]"); | 4778 stream->Add("[external-memory]"); |
4755 break; | 4779 break; |
4756 } | 4780 } |
4757 | 4781 |
4758 stream->Add("@%d", offset()); | 4782 stream->Add("@%d", offset()); |
4759 } | 4783 } |
4760 | 4784 |
4761 } } // namespace v8::internal | 4785 } } // namespace v8::internal |
OLD | NEW |