| OLD | NEW | 
|---|
| 1 // Copyright (c) 1994-2006 Sun Microsystems Inc. | 1 // Copyright (c) 1994-2006 Sun Microsystems Inc. | 
| 2 // All Rights Reserved. | 2 // All Rights Reserved. | 
| 3 // | 3 // | 
| 4 // Redistribution and use in source and binary forms, with or without | 4 // Redistribution and use in source and binary forms, with or without | 
| 5 // modification, are permitted provided that the following conditions | 5 // modification, are permitted provided that the following conditions | 
| 6 // are met: | 6 // are met: | 
| 7 // | 7 // | 
| 8 // - Redistributions of source code must retain the above copyright notice, | 8 // - Redistributions of source code must retain the above copyright notice, | 
| 9 // this list of conditions and the following disclaimer. | 9 // this list of conditions and the following disclaimer. | 
| 10 // | 10 // | 
| (...skipping 2528 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 2539   DCHECK(!base.is(pc)); | 2539   DCHECK(!base.is(pc)); | 
| 2540 | 2540 | 
| 2541   int sd, d; | 2541   int sd, d; | 
| 2542   first.split_code(&sd, &d); | 2542   first.split_code(&sd, &d); | 
| 2543   int count = last.code() - first.code() + 1; | 2543   int count = last.code() - first.code() + 1; | 
| 2544   emit(cond | B27 | B26 | am | d*B22 | base.code()*B16 | sd*B12 | | 2544   emit(cond | B27 | B26 | am | d*B22 | base.code()*B16 | sd*B12 | | 
| 2545        0xA*B8 | count); | 2545        0xA*B8 | count); | 
| 2546 } | 2546 } | 
| 2547 | 2547 | 
| 2548 | 2548 | 
| 2549 void Assembler::vmov(const SwVfpRegister dst, float imm) { |  | 
| 2550   mov(ip, Operand(bit_cast<int32_t>(imm))); |  | 
| 2551   vmov(dst, ip); |  | 
| 2552 } |  | 
| 2553 |  | 
| 2554 |  | 
| 2555 static void DoubleAsTwoUInt32(double d, uint32_t* lo, uint32_t* hi) { | 2549 static void DoubleAsTwoUInt32(double d, uint32_t* lo, uint32_t* hi) { | 
| 2556   uint64_t i; | 2550   uint64_t i; | 
| 2557   memcpy(&i, &d, 8); | 2551   memcpy(&i, &d, 8); | 
| 2558 | 2552 | 
| 2559   *lo = i & 0xffffffff; | 2553   *lo = i & 0xffffffff; | 
| 2560   *hi = i >> 32; | 2554   *hi = i >> 32; | 
| 2561 } | 2555 } | 
| 2562 | 2556 | 
| 2563 | 2557 | 
| 2564 // Only works for little endian floating point formats. | 2558 // Only works for little endian floating point formats. | 
| 2565 // We don't support VFP on the mixed endian floating point platform. | 2559 // We don't support VFP on the mixed endian floating point platform. | 
| 2566 static bool FitsVMOVDoubleImmediate(double d, uint32_t *encoding) { | 2560 static bool FitsVmovFPImmediate(double d, uint32_t* encoding) { | 
| 2567   DCHECK(CpuFeatures::IsSupported(VFP3)); | 2561   DCHECK(CpuFeatures::IsSupported(VFP3)); | 
| 2568 | 2562 | 
| 2569   // VMOV can accept an immediate of the form: | 2563   // VMOV can accept an immediate of the form: | 
| 2570   // | 2564   // | 
| 2571   //  +/- m * 2^(-n) where 16 <= m <= 31 and 0 <= n <= 7 | 2565   //  +/- m * 2^(-n) where 16 <= m <= 31 and 0 <= n <= 7 | 
| 2572   // | 2566   // | 
| 2573   // The immediate is encoded using an 8-bit quantity, comprised of two | 2567   // The immediate is encoded using an 8-bit quantity, comprised of two | 
| 2574   // 4-bit fields. For an 8-bit immediate of the form: | 2568   // 4-bit fields. For an 8-bit immediate of the form: | 
| 2575   // | 2569   // | 
| 2576   //  [abcdefgh] | 2570   //  [abcdefgh] | 
| 2577   // | 2571   // | 
| 2578   // where a is the MSB and h is the LSB, an immediate 64-bit double can be | 2572   // where a is the MSB and h is the LSB, an immediate 64-bit double can be | 
| 2579   // created of the form: | 2573   // created of the form: | 
| 2580   // | 2574   // | 
| 2581   //  [aBbbbbbb,bbcdefgh,00000000,00000000, | 2575   //  [aBbbbbbb,bbcdefgh,00000000,00000000, | 
| 2582   //      00000000,00000000,00000000,00000000] | 2576   //      00000000,00000000,00000000,00000000] | 
| 2583   // | 2577   // | 
| 2584   // where B = ~b. | 2578   // where B = ~b. | 
| 2585   // | 2579   // | 
| 2586 | 2580 | 
| 2587   uint32_t lo, hi; | 2581   uint32_t lo, hi; | 
| 2588   DoubleAsTwoUInt32(d, &lo, &hi); | 2582   DoubleAsTwoUInt32(d, &lo, &hi); | 
| 2589 | 2583 | 
| 2590   // The most obvious constraint is the long block of zeroes. | 2584   // The most obvious constraint is the long block of zeroes. | 
| 2591   if ((lo != 0) || ((hi & 0xffff) != 0)) { | 2585   if ((lo != 0) || ((hi & 0xffff) != 0)) { | 
| 2592     return false; | 2586     return false; | 
| 2593   } | 2587   } | 
| 2594 | 2588 | 
| 2595   // Bits 62:55 must be all clear or all set. | 2589   // Bits 61:54 must be all clear or all set. | 
| 2596   if (((hi & 0x3fc00000) != 0) && ((hi & 0x3fc00000) != 0x3fc00000)) { | 2590   if (((hi & 0x3fc00000) != 0) && ((hi & 0x3fc00000) != 0x3fc00000)) { | 
| 2597     return false; | 2591     return false; | 
| 2598   } | 2592   } | 
| 2599 | 2593 | 
| 2600   // Bit 63 must be NOT bit 62. | 2594   // Bit 62 must be NOT bit 61. | 
| 2601   if (((hi ^ (hi << 1)) & (0x40000000)) == 0) { | 2595   if (((hi ^ (hi << 1)) & (0x40000000)) == 0) { | 
| 2602     return false; | 2596     return false; | 
| 2603   } | 2597   } | 
| 2604 | 2598 | 
| 2605   // Create the encoded immediate in the form: | 2599   // Create the encoded immediate in the form: | 
| 2606   //  [00000000,0000abcd,00000000,0000efgh] | 2600   //  [00000000,0000abcd,00000000,0000efgh] | 
| 2607   *encoding  = (hi >> 16) & 0xf;      // Low nybble. | 2601   *encoding  = (hi >> 16) & 0xf;      // Low nybble. | 
| 2608   *encoding |= (hi >> 4) & 0x70000;   // Low three bits of the high nybble. | 2602   *encoding |= (hi >> 4) & 0x70000;   // Low three bits of the high nybble. | 
| 2609   *encoding |= (hi >> 12) & 0x80000;  // Top bit of the high nybble. | 2603   *encoding |= (hi >> 12) & 0x80000;  // Top bit of the high nybble. | 
| 2610 | 2604 | 
| 2611   return true; | 2605   return true; | 
| 2612 } | 2606 } | 
| 2613 | 2607 | 
| 2614 | 2608 | 
|  | 2609 void Assembler::vmov(const SwVfpRegister dst, float imm) { | 
|  | 2610   uint32_t enc; | 
|  | 2611   if (CpuFeatures::IsSupported(VFP3) && FitsVmovFPImmediate(imm, &enc)) { | 
|  | 2612     // The float can be encoded in the instruction. | 
|  | 2613     // | 
|  | 2614     // Sd = immediate | 
|  | 2615     // Instruction details available in ARM DDI 0406C.b, A8-936. | 
|  | 2616     // cond(31-28) | 11101(27-23) | D(22) | 11(21-20) | imm4H(19-16) | | 
|  | 2617     // Vd(15-12) | 101(11-9) | sz=0(8) | imm4L(3-0) | 
|  | 2618     int vd, d; | 
|  | 2619     dst.split_code(&vd, &d); | 
|  | 2620     emit(al | 0x1D * B23 | d * B22 | 0x3 * B20 | vd * B12 | 0x5 * B9 | enc); | 
|  | 2621   } else { | 
|  | 2622     mov(ip, Operand(bit_cast<int32_t>(imm))); | 
|  | 2623     vmov(dst, ip); | 
|  | 2624   } | 
|  | 2625 } | 
|  | 2626 | 
|  | 2627 | 
| 2615 void Assembler::vmov(const DwVfpRegister dst, | 2628 void Assembler::vmov(const DwVfpRegister dst, | 
| 2616                      double imm, | 2629                      double imm, | 
| 2617                      const Register scratch) { | 2630                      const Register scratch) { | 
| 2618   uint32_t enc; | 2631   uint32_t enc; | 
| 2619   // If the embedded constant pool is disabled, we can use the normal, inline | 2632   // If the embedded constant pool is disabled, we can use the normal, inline | 
| 2620   // constant pool. If the embedded constant pool is enabled (via | 2633   // constant pool. If the embedded constant pool is enabled (via | 
| 2621   // FLAG_enable_embedded_constant_pool), we can only use it where the pool | 2634   // FLAG_enable_embedded_constant_pool), we can only use it where the pool | 
| 2622   // pointer (pp) is valid. | 2635   // pointer (pp) is valid. | 
| 2623   bool can_use_pool = | 2636   bool can_use_pool = | 
| 2624       !FLAG_enable_embedded_constant_pool || is_constant_pool_available(); | 2637       !FLAG_enable_embedded_constant_pool || is_constant_pool_available(); | 
| 2625   if (CpuFeatures::IsSupported(VFP3) && FitsVMOVDoubleImmediate(imm, &enc)) { | 2638   if (CpuFeatures::IsSupported(VFP3) && FitsVmovFPImmediate(imm, &enc)) { | 
| 2626     // The double can be encoded in the instruction. | 2639     // The double can be encoded in the instruction. | 
| 2627     // | 2640     // | 
| 2628     // Dd = immediate | 2641     // Dd = immediate | 
| 2629     // Instruction details available in ARM DDI 0406C.b, A8-936. | 2642     // Instruction details available in ARM DDI 0406C.b, A8-936. | 
| 2630     // cond(31-28) | 11101(27-23) | D(22) | 11(21-20) | imm4H(19-16) | | 2643     // cond(31-28) | 11101(27-23) | D(22) | 11(21-20) | imm4H(19-16) | | 
| 2631     // Vd(15-12) | 101(11-9) | sz=1(8) | imm4L(3-0) | 2644     // Vd(15-12) | 101(11-9) | sz=1(8) | imm4L(3-0) | 
| 2632     int vd, d; | 2645     int vd, d; | 
| 2633     dst.split_code(&vd, &d); | 2646     dst.split_code(&vd, &d); | 
| 2634     emit(al | 0x1D*B23 | d*B22 | 0x3*B20 | vd*B12 | 0x5*B9 | B8 | enc); | 2647     emit(al | 0x1D*B23 | d*B22 | 0x3*B20 | vd*B12 | 0x5*B9 | B8 | enc); | 
| 2635   } else if (FLAG_enable_vldr_imm && can_use_pool) { | 2648   } else if (FLAG_enable_vldr_imm && can_use_pool) { | 
| (...skipping 1512 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 4148     DCHECK(is_uint12(offset)); | 4161     DCHECK(is_uint12(offset)); | 
| 4149     instr_at_put(pc, SetLdrRegisterImmediateOffset(instr, offset)); | 4162     instr_at_put(pc, SetLdrRegisterImmediateOffset(instr, offset)); | 
| 4150   } | 4163   } | 
| 4151 } | 4164 } | 
| 4152 | 4165 | 
| 4153 | 4166 | 
| 4154 }  // namespace internal | 4167 }  // namespace internal | 
| 4155 }  // namespace v8 | 4168 }  // namespace v8 | 
| 4156 | 4169 | 
| 4157 #endif  // V8_TARGET_ARCH_ARM | 4170 #endif  // V8_TARGET_ARCH_ARM | 
| OLD | NEW | 
|---|