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 247 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
258 | 258 |
259 | 259 |
260 void MacroAssembler::Move(Register dst, Register src, Condition cond) { | 260 void MacroAssembler::Move(Register dst, Register src, Condition cond) { |
261 if (!dst.is(src)) { | 261 if (!dst.is(src)) { |
262 mov(dst, src, LeaveCC, cond); | 262 mov(dst, src, LeaveCC, cond); |
263 } | 263 } |
264 } | 264 } |
265 | 265 |
266 | 266 |
267 void MacroAssembler::Move(DoubleRegister dst, DoubleRegister src) { | 267 void MacroAssembler::Move(DoubleRegister dst, DoubleRegister src) { |
268 ASSERT(CpuFeatures::IsSupported(VFP3)); | 268 ASSERT(CpuFeatures::IsSupported(VFP2)); |
269 CpuFeatures::Scope scope(VFP3); | 269 CpuFeatures::Scope scope(VFP2); |
270 if (!dst.is(src)) { | 270 if (!dst.is(src)) { |
271 vmov(dst, src); | 271 vmov(dst, src); |
272 } | 272 } |
273 } | 273 } |
274 | 274 |
275 | 275 |
276 void MacroAssembler::And(Register dst, Register src1, const Operand& src2, | 276 void MacroAssembler::And(Register dst, Register src1, const Operand& src2, |
277 Condition cond) { | 277 Condition cond) { |
278 if (!src2.is_reg() && | 278 if (!src2.is_reg() && |
279 !src2.must_use_constant_pool() && | 279 !src2.must_use_constant_pool() && |
(...skipping 491 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
771 const Register fpscr_flags, | 771 const Register fpscr_flags, |
772 const Condition cond) { | 772 const Condition cond) { |
773 // Compare and load FPSCR. | 773 // Compare and load FPSCR. |
774 vcmp(src1, src2, cond); | 774 vcmp(src1, src2, cond); |
775 vmrs(fpscr_flags, cond); | 775 vmrs(fpscr_flags, cond); |
776 } | 776 } |
777 | 777 |
778 void MacroAssembler::Vmov(const DwVfpRegister dst, | 778 void MacroAssembler::Vmov(const DwVfpRegister dst, |
779 const double imm, | 779 const double imm, |
780 const Condition cond) { | 780 const Condition cond) { |
781 ASSERT(CpuFeatures::IsEnabled(VFP3)); | 781 ASSERT(CpuFeatures::IsEnabled(VFP2)); |
782 static const DoubleRepresentation minus_zero(-0.0); | 782 static const DoubleRepresentation minus_zero(-0.0); |
783 static const DoubleRepresentation zero(0.0); | 783 static const DoubleRepresentation zero(0.0); |
784 DoubleRepresentation value(imm); | 784 DoubleRepresentation value(imm); |
785 // Handle special values first. | 785 // Handle special values first. |
786 if (value.bits == zero.bits) { | 786 if (value.bits == zero.bits) { |
787 vmov(dst, kDoubleRegZero, cond); | 787 vmov(dst, kDoubleRegZero, cond); |
788 } else if (value.bits == minus_zero.bits) { | 788 } else if (value.bits == minus_zero.bits) { |
789 vneg(dst, kDoubleRegZero, cond); | 789 vneg(dst, kDoubleRegZero, cond); |
790 } else if (false && CpuFeatures::IsSupported(VFP3)) { | |
Sven Panne
2012/07/25 07:49:06
As discussed offline, this duplicates some fallbac
| |
791 CpuFeatures::Scope scope(VFP3); | |
792 vmov(dst, imm, cond); | |
790 } else { | 793 } else { |
791 vmov(dst, imm, cond); | 794 union conversion { |
795 double d; | |
796 int32_t u[2]; | |
797 } c; | |
798 Label done; | |
799 if (cond != al) { | |
800 b(&done, NegateCondition(cond)); | |
801 } | |
802 c.d = imm; | |
803 mov(ip, Operand(c.u[0])); | |
804 vmov(dst.low(), ip); | |
805 mov(ip, Operand(c.u[1])); | |
806 vmov(dst.high(), ip); | |
807 bind(&done); | |
792 } | 808 } |
793 } | 809 } |
794 | 810 |
795 | 811 |
796 void MacroAssembler::EnterFrame(StackFrame::Type type) { | 812 void MacroAssembler::EnterFrame(StackFrame::Type type) { |
797 // r0-r3: preserved | 813 // r0-r3: preserved |
798 stm(db_w, sp, cp.bit() | fp.bit() | lr.bit()); | 814 stm(db_w, sp, cp.bit() | fp.bit() | lr.bit()); |
799 mov(ip, Operand(Smi::FromInt(type))); | 815 mov(ip, Operand(Smi::FromInt(type))); |
800 push(ip); | 816 push(ip); |
801 mov(ip, Operand(CodeObject())); | 817 mov(ip, Operand(CodeObject())); |
(...skipping 121 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
923 | 939 |
924 // Tear down the exit frame, pop the arguments, and return. | 940 // Tear down the exit frame, pop the arguments, and return. |
925 mov(sp, Operand(fp)); | 941 mov(sp, Operand(fp)); |
926 ldm(ia_w, sp, fp.bit() | lr.bit()); | 942 ldm(ia_w, sp, fp.bit() | lr.bit()); |
927 if (argument_count.is_valid()) { | 943 if (argument_count.is_valid()) { |
928 add(sp, sp, Operand(argument_count, LSL, kPointerSizeLog2)); | 944 add(sp, sp, Operand(argument_count, LSL, kPointerSizeLog2)); |
929 } | 945 } |
930 } | 946 } |
931 | 947 |
932 void MacroAssembler::GetCFunctionDoubleResult(const DoubleRegister dst) { | 948 void MacroAssembler::GetCFunctionDoubleResult(const DoubleRegister dst) { |
949 ASSERT(CpuFeatures::IsSupported(VFP2)); | |
933 if (use_eabi_hardfloat()) { | 950 if (use_eabi_hardfloat()) { |
934 Move(dst, d0); | 951 Move(dst, d0); |
935 } else { | 952 } else { |
936 vmov(dst, r0, r1); | 953 vmov(dst, r0, r1); |
937 } | 954 } |
938 } | 955 } |
939 | 956 |
940 | 957 |
941 void MacroAssembler::SetCallKind(Register dst, CallKind call_kind) { | 958 void MacroAssembler::SetCallKind(Register dst, CallKind call_kind) { |
942 // This macro takes the dst register to make the code more readable | 959 // This macro takes the dst register to make the code more readable |
(...skipping 1017 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1960 jmp(&have_double_value); | 1977 jmp(&have_double_value); |
1961 | 1978 |
1962 bind(&smi_value); | 1979 bind(&smi_value); |
1963 add(scratch1, elements_reg, | 1980 add(scratch1, elements_reg, |
1964 Operand(FixedDoubleArray::kHeaderSize - kHeapObjectTag)); | 1981 Operand(FixedDoubleArray::kHeaderSize - kHeapObjectTag)); |
1965 add(scratch1, scratch1, | 1982 add(scratch1, scratch1, |
1966 Operand(key_reg, LSL, kDoubleSizeLog2 - kSmiTagSize)); | 1983 Operand(key_reg, LSL, kDoubleSizeLog2 - kSmiTagSize)); |
1967 // scratch1 is now effective address of the double element | 1984 // scratch1 is now effective address of the double element |
1968 | 1985 |
1969 FloatingPointHelper::Destination destination; | 1986 FloatingPointHelper::Destination destination; |
1970 if (CpuFeatures::IsSupported(VFP3)) { | 1987 if (CpuFeatures::IsSupported(VFP2)) { |
1971 destination = FloatingPointHelper::kVFPRegisters; | 1988 destination = FloatingPointHelper::kVFPRegisters; |
1972 } else { | 1989 } else { |
1973 destination = FloatingPointHelper::kCoreRegisters; | 1990 destination = FloatingPointHelper::kCoreRegisters; |
1974 } | 1991 } |
1975 | 1992 |
1976 Register untagged_value = receiver_reg; | 1993 Register untagged_value = receiver_reg; |
1977 SmiUntag(untagged_value, value_reg); | 1994 SmiUntag(untagged_value, value_reg); |
1978 FloatingPointHelper::ConvertIntToDouble(this, | 1995 FloatingPointHelper::ConvertIntToDouble(this, |
1979 untagged_value, | 1996 untagged_value, |
1980 destination, | 1997 destination, |
1981 d0, | 1998 d0, |
1982 mantissa_reg, | 1999 mantissa_reg, |
1983 exponent_reg, | 2000 exponent_reg, |
1984 scratch4, | 2001 scratch4, |
1985 s2); | 2002 s2); |
1986 if (destination == FloatingPointHelper::kVFPRegisters) { | 2003 if (destination == FloatingPointHelper::kVFPRegisters) { |
1987 CpuFeatures::Scope scope(VFP3); | 2004 CpuFeatures::Scope scope(VFP2); |
1988 vstr(d0, scratch1, 0); | 2005 vstr(d0, scratch1, 0); |
1989 } else { | 2006 } else { |
1990 str(mantissa_reg, MemOperand(scratch1, 0)); | 2007 str(mantissa_reg, MemOperand(scratch1, 0)); |
1991 str(exponent_reg, MemOperand(scratch1, Register::kSizeInBytes)); | 2008 str(exponent_reg, MemOperand(scratch1, Register::kSizeInBytes)); |
1992 } | 2009 } |
1993 bind(&done); | 2010 bind(&done); |
1994 } | 2011 } |
1995 | 2012 |
1996 | 2013 |
1997 void MacroAssembler::CompareMap(Register obj, | 2014 void MacroAssembler::CompareMap(Register obj, |
(...skipping 326 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2324 | 2341 |
2325 // Tries to get a signed int32 out of a double precision floating point heap | 2342 // Tries to get a signed int32 out of a double precision floating point heap |
2326 // number. Rounds towards 0. Branch to 'not_int32' if the double is out of the | 2343 // number. Rounds towards 0. Branch to 'not_int32' if the double is out of the |
2327 // 32bits signed integer range. | 2344 // 32bits signed integer range. |
2328 void MacroAssembler::ConvertToInt32(Register source, | 2345 void MacroAssembler::ConvertToInt32(Register source, |
2329 Register dest, | 2346 Register dest, |
2330 Register scratch, | 2347 Register scratch, |
2331 Register scratch2, | 2348 Register scratch2, |
2332 DwVfpRegister double_scratch, | 2349 DwVfpRegister double_scratch, |
2333 Label *not_int32) { | 2350 Label *not_int32) { |
2334 if (CpuFeatures::IsSupported(VFP3)) { | 2351 if (CpuFeatures::IsSupported(VFP2)) { |
2335 CpuFeatures::Scope scope(VFP3); | 2352 CpuFeatures::Scope scope(VFP2); |
2336 sub(scratch, source, Operand(kHeapObjectTag)); | 2353 sub(scratch, source, Operand(kHeapObjectTag)); |
2337 vldr(double_scratch, scratch, HeapNumber::kValueOffset); | 2354 vldr(double_scratch, scratch, HeapNumber::kValueOffset); |
2338 vcvt_s32_f64(double_scratch.low(), double_scratch); | 2355 vcvt_s32_f64(double_scratch.low(), double_scratch); |
2339 vmov(dest, double_scratch.low()); | 2356 vmov(dest, double_scratch.low()); |
2340 // Signed vcvt instruction will saturate to the minimum (0x80000000) or | 2357 // Signed vcvt instruction will saturate to the minimum (0x80000000) or |
2341 // maximun (0x7fffffff) signed 32bits integer when the double is out of | 2358 // maximun (0x7fffffff) signed 32bits integer when the double is out of |
2342 // range. When substracting one, the minimum signed integer becomes the | 2359 // range. When substracting one, the minimum signed integer becomes the |
2343 // maximun signed integer. | 2360 // maximun signed integer. |
2344 sub(scratch, dest, Operand(1)); | 2361 sub(scratch, dest, Operand(1)); |
2345 cmp(scratch, Operand(LONG_MAX - 1)); | 2362 cmp(scratch, Operand(LONG_MAX - 1)); |
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2420 } | 2437 } |
2421 } | 2438 } |
2422 | 2439 |
2423 | 2440 |
2424 void MacroAssembler::EmitVFPTruncate(VFPRoundingMode rounding_mode, | 2441 void MacroAssembler::EmitVFPTruncate(VFPRoundingMode rounding_mode, |
2425 SwVfpRegister result, | 2442 SwVfpRegister result, |
2426 DwVfpRegister double_input, | 2443 DwVfpRegister double_input, |
2427 Register scratch1, | 2444 Register scratch1, |
2428 Register scratch2, | 2445 Register scratch2, |
2429 CheckForInexactConversion check_inexact) { | 2446 CheckForInexactConversion check_inexact) { |
2430 ASSERT(CpuFeatures::IsSupported(VFP3)); | 2447 ASSERT(CpuFeatures::IsSupported(VFP2)); |
2431 CpuFeatures::Scope scope(VFP3); | 2448 CpuFeatures::Scope scope(VFP2); |
2432 Register prev_fpscr = scratch1; | 2449 Register prev_fpscr = scratch1; |
2433 Register scratch = scratch2; | 2450 Register scratch = scratch2; |
2434 | 2451 |
2435 int32_t check_inexact_conversion = | 2452 int32_t check_inexact_conversion = |
2436 (check_inexact == kCheckForInexactConversion) ? kVFPInexactExceptionBit : 0; | 2453 (check_inexact == kCheckForInexactConversion) ? kVFPInexactExceptionBit : 0; |
2437 | 2454 |
2438 // Set custom FPCSR: | 2455 // Set custom FPCSR: |
2439 // - Set rounding mode. | 2456 // - Set rounding mode. |
2440 // - Clear vfp cumulative exception flags. | 2457 // - Clear vfp cumulative exception flags. |
2441 // - Make sure Flush-to-zero mode control bit is unset. | 2458 // - Make sure Flush-to-zero mode control bit is unset. |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2539 bind(&done); | 2556 bind(&done); |
2540 } | 2557 } |
2541 | 2558 |
2542 | 2559 |
2543 void MacroAssembler::EmitECMATruncate(Register result, | 2560 void MacroAssembler::EmitECMATruncate(Register result, |
2544 DwVfpRegister double_input, | 2561 DwVfpRegister double_input, |
2545 SwVfpRegister single_scratch, | 2562 SwVfpRegister single_scratch, |
2546 Register scratch, | 2563 Register scratch, |
2547 Register input_high, | 2564 Register input_high, |
2548 Register input_low) { | 2565 Register input_low) { |
2549 CpuFeatures::Scope scope(VFP3); | 2566 CpuFeatures::Scope scope(VFP2); |
2550 ASSERT(!input_high.is(result)); | 2567 ASSERT(!input_high.is(result)); |
2551 ASSERT(!input_low.is(result)); | 2568 ASSERT(!input_low.is(result)); |
2552 ASSERT(!input_low.is(input_high)); | 2569 ASSERT(!input_low.is(input_high)); |
2553 ASSERT(!scratch.is(result) && | 2570 ASSERT(!scratch.is(result) && |
2554 !scratch.is(input_high) && | 2571 !scratch.is(input_high) && |
2555 !scratch.is(input_low)); | 2572 !scratch.is(input_low)); |
2556 ASSERT(!single_scratch.is(double_input.low()) && | 2573 ASSERT(!single_scratch.is(double_input.low()) && |
2557 !single_scratch.is(double_input.high())); | 2574 !single_scratch.is(double_input.high())); |
2558 | 2575 |
2559 Label done; | 2576 Label done; |
(...skipping 765 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3325 } | 3342 } |
3326 | 3343 |
3327 | 3344 |
3328 void MacroAssembler::PrepareCallCFunction(int num_reg_arguments, | 3345 void MacroAssembler::PrepareCallCFunction(int num_reg_arguments, |
3329 Register scratch) { | 3346 Register scratch) { |
3330 PrepareCallCFunction(num_reg_arguments, 0, scratch); | 3347 PrepareCallCFunction(num_reg_arguments, 0, scratch); |
3331 } | 3348 } |
3332 | 3349 |
3333 | 3350 |
3334 void MacroAssembler::SetCallCDoubleArguments(DoubleRegister dreg) { | 3351 void MacroAssembler::SetCallCDoubleArguments(DoubleRegister dreg) { |
3352 ASSERT(CpuFeatures::IsSupported(VFP2)); | |
3335 if (use_eabi_hardfloat()) { | 3353 if (use_eabi_hardfloat()) { |
3336 Move(d0, dreg); | 3354 Move(d0, dreg); |
3337 } else { | 3355 } else { |
3338 vmov(r0, r1, dreg); | 3356 vmov(r0, r1, dreg); |
3339 } | 3357 } |
3340 } | 3358 } |
3341 | 3359 |
3342 | 3360 |
3343 void MacroAssembler::SetCallCDoubleArguments(DoubleRegister dreg1, | 3361 void MacroAssembler::SetCallCDoubleArguments(DoubleRegister dreg1, |
3344 DoubleRegister dreg2) { | 3362 DoubleRegister dreg2) { |
3363 ASSERT(CpuFeatures::IsSupported(VFP2)); | |
3345 if (use_eabi_hardfloat()) { | 3364 if (use_eabi_hardfloat()) { |
3346 if (dreg2.is(d0)) { | 3365 if (dreg2.is(d0)) { |
3347 ASSERT(!dreg1.is(d1)); | 3366 ASSERT(!dreg1.is(d1)); |
3348 Move(d1, dreg2); | 3367 Move(d1, dreg2); |
3349 Move(d0, dreg1); | 3368 Move(d0, dreg1); |
3350 } else { | 3369 } else { |
3351 Move(d0, dreg1); | 3370 Move(d0, dreg1); |
3352 Move(d1, dreg2); | 3371 Move(d1, dreg2); |
3353 } | 3372 } |
3354 } else { | 3373 } else { |
3355 vmov(r0, r1, dreg1); | 3374 vmov(r0, r1, dreg1); |
3356 vmov(r2, r3, dreg2); | 3375 vmov(r2, r3, dreg2); |
3357 } | 3376 } |
3358 } | 3377 } |
3359 | 3378 |
3360 | 3379 |
3361 void MacroAssembler::SetCallCDoubleArguments(DoubleRegister dreg, | 3380 void MacroAssembler::SetCallCDoubleArguments(DoubleRegister dreg, |
3362 Register reg) { | 3381 Register reg) { |
3382 ASSERT(CpuFeatures::IsSupported(VFP2)); | |
3363 if (use_eabi_hardfloat()) { | 3383 if (use_eabi_hardfloat()) { |
3364 Move(d0, dreg); | 3384 Move(d0, dreg); |
3365 Move(r0, reg); | 3385 Move(r0, reg); |
3366 } else { | 3386 } else { |
3367 Move(r2, reg); | 3387 Move(r2, reg); |
3368 vmov(r0, r1, dreg); | 3388 vmov(r0, r1, dreg); |
3369 } | 3389 } |
3370 } | 3390 } |
3371 | 3391 |
3372 | 3392 |
(...skipping 428 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3801 void CodePatcher::EmitCondition(Condition cond) { | 3821 void CodePatcher::EmitCondition(Condition cond) { |
3802 Instr instr = Assembler::instr_at(masm_.pc_); | 3822 Instr instr = Assembler::instr_at(masm_.pc_); |
3803 instr = (instr & ~kCondMask) | cond; | 3823 instr = (instr & ~kCondMask) | cond; |
3804 masm_.emit(instr); | 3824 masm_.emit(instr); |
3805 } | 3825 } |
3806 | 3826 |
3807 | 3827 |
3808 } } // namespace v8::internal | 3828 } } // namespace v8::internal |
3809 | 3829 |
3810 #endif // V8_TARGET_ARCH_ARM | 3830 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |