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 835 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
846 "HeapNumberMap register clobbered."); | 846 "HeapNumberMap register clobbered."); |
847 __ JumpIfNotHeapNumber(object, heap_number_map, scratch1, not_int32); | 847 __ JumpIfNotHeapNumber(object, heap_number_map, scratch1, not_int32); |
848 | 848 |
849 // Load the number. | 849 // Load the number. |
850 if (CpuFeatures::IsSupported(VFP2)) { | 850 if (CpuFeatures::IsSupported(VFP2)) { |
851 CpuFeatures::Scope scope(VFP2); | 851 CpuFeatures::Scope scope(VFP2); |
852 // Load the double value. | 852 // Load the double value. |
853 __ sub(scratch1, object, Operand(kHeapObjectTag)); | 853 __ sub(scratch1, object, Operand(kHeapObjectTag)); |
854 __ vldr(double_dst, scratch1, HeapNumber::kValueOffset); | 854 __ vldr(double_dst, scratch1, HeapNumber::kValueOffset); |
855 | 855 |
856 __ EmitVFPTruncate(kRoundToZero, | 856 __ TestDoubleIsInt32(double_dst, double_scratch); |
857 scratch1, | |
858 double_dst, | |
859 scratch2, | |
860 double_scratch, | |
861 kCheckForInexactConversion); | |
862 | |
863 // Jump to not_int32 if the operation did not succeed. | 857 // Jump to not_int32 if the operation did not succeed. |
864 __ b(ne, not_int32); | 858 __ b(ne, not_int32); |
865 | 859 |
866 if (destination == kCoreRegisters) { | 860 if (destination == kCoreRegisters) { |
867 __ vmov(dst_mantissa, dst_exponent, double_dst); | 861 __ vmov(dst_mantissa, dst_exponent, double_dst); |
868 } | 862 } |
869 | 863 |
870 } else { | 864 } else { |
871 ASSERT(!scratch1.is(object) && !scratch2.is(object)); | 865 ASSERT(!scratch1.is(object) && !scratch2.is(object)); |
872 // Load the double value in the destination registers. | 866 // Load the double value in the destination registers. |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
944 | 938 |
945 // Object is a heap number. | 939 // Object is a heap number. |
946 // Convert the floating point value to a 32-bit integer. | 940 // Convert the floating point value to a 32-bit integer. |
947 if (CpuFeatures::IsSupported(VFP2)) { | 941 if (CpuFeatures::IsSupported(VFP2)) { |
948 CpuFeatures::Scope scope(VFP2); | 942 CpuFeatures::Scope scope(VFP2); |
949 | 943 |
950 // Load the double value. | 944 // Load the double value. |
951 __ sub(scratch1, object, Operand(kHeapObjectTag)); | 945 __ sub(scratch1, object, Operand(kHeapObjectTag)); |
952 __ vldr(double_scratch0, scratch1, HeapNumber::kValueOffset); | 946 __ vldr(double_scratch0, scratch1, HeapNumber::kValueOffset); |
953 | 947 |
954 __ EmitVFPTruncate(kRoundToZero, | 948 __ TryDoubleToInt32Exact(dst, double_scratch0, double_scratch1); |
955 dst, | |
956 double_scratch0, | |
957 scratch1, | |
958 double_scratch1, | |
959 kCheckForInexactConversion); | |
960 | |
961 // Jump to not_int32 if the operation did not succeed. | 949 // Jump to not_int32 if the operation did not succeed. |
962 __ b(ne, not_int32); | 950 __ b(ne, not_int32); |
963 } else { | 951 } else { |
964 // Load the double value in the destination registers. | 952 // Load the double value in the destination registers. |
965 __ ldr(scratch1, FieldMemOperand(object, HeapNumber::kExponentOffset)); | 953 __ ldr(scratch1, FieldMemOperand(object, HeapNumber::kExponentOffset)); |
966 __ ldr(scratch2, FieldMemOperand(object, HeapNumber::kMantissaOffset)); | 954 __ ldr(scratch2, FieldMemOperand(object, HeapNumber::kMantissaOffset)); |
967 | 955 |
968 // Check for 0 and -0. | 956 // Check for 0 and -0. |
969 __ bic(dst, scratch1, Operand(HeapNumber::kSignMask)); | 957 __ bic(dst, scratch1, Operand(HeapNumber::kSignMask)); |
970 __ orr(dst, scratch2, Operand(dst)); | 958 __ orr(dst, scratch2, Operand(dst)); |
(...skipping 2078 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3049 default: | 3037 default: |
3050 UNREACHABLE(); | 3038 UNREACHABLE(); |
3051 } | 3039 } |
3052 | 3040 |
3053 if (op_ != Token::DIV) { | 3041 if (op_ != Token::DIV) { |
3054 // These operations produce an integer result. | 3042 // These operations produce an integer result. |
3055 // Try to return a smi if we can. | 3043 // Try to return a smi if we can. |
3056 // Otherwise return a heap number if allowed, or jump to type | 3044 // Otherwise return a heap number if allowed, or jump to type |
3057 // transition. | 3045 // transition. |
3058 | 3046 |
3059 __ EmitVFPTruncate(kRoundToZero, | |
3060 scratch1, | |
3061 d5, | |
3062 scratch2, | |
3063 d8); | |
3064 | |
3065 if (result_type_ <= BinaryOpIC::INT32) { | 3047 if (result_type_ <= BinaryOpIC::INT32) { |
| 3048 __ TryDoubleToInt32Exact(scratch1, d5, d8); |
3066 // If the ne condition is set, result does | 3049 // If the ne condition is set, result does |
3067 // not fit in a 32-bit integer. | 3050 // not fit in a 32-bit integer. |
3068 __ b(ne, &transition); | 3051 __ b(ne, &transition); |
| 3052 } else { |
| 3053 __ vcvt_s32_f64(s8, d5); |
| 3054 __ vmov(scratch1, s8); |
3069 } | 3055 } |
3070 | 3056 |
3071 // Check if the result fits in a smi. | 3057 // Check if the result fits in a smi. |
3072 __ add(scratch2, scratch1, Operand(0x40000000), SetCC); | 3058 __ add(scratch2, scratch1, Operand(0x40000000), SetCC); |
3073 // If not try to return a heap number. | 3059 // If not try to return a heap number. |
3074 __ b(mi, &return_heap_number); | 3060 __ b(mi, &return_heap_number); |
3075 // Check for minus zero. Return heap number for minus zero. | 3061 // Check for minus zero. Return heap number for minus zero. |
3076 Label not_zero; | 3062 Label not_zero; |
3077 __ cmp(scratch1, Operand::Zero()); | 3063 __ cmp(scratch1, Operand::Zero()); |
3078 __ b(ne, ¬_zero); | 3064 __ b(ne, ¬_zero); |
(...skipping 4839 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7918 | 7904 |
7919 __ Pop(lr, r5, r1); | 7905 __ Pop(lr, r5, r1); |
7920 __ Ret(); | 7906 __ Ret(); |
7921 } | 7907 } |
7922 | 7908 |
7923 #undef __ | 7909 #undef __ |
7924 | 7910 |
7925 } } // namespace v8::internal | 7911 } } // namespace v8::internal |
7926 | 7912 |
7927 #endif // V8_TARGET_ARCH_ARM | 7913 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |