| 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 |