OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 "src/compiler/code-generator.h" | 5 #include "src/compiler/code-generator.h" |
6 | 6 |
7 #include "src/arm/macro-assembler-arm.h" | 7 #include "src/arm/macro-assembler-arm.h" |
8 #include "src/assembler-inl.h" | 8 #include "src/assembler-inl.h" |
9 #include "src/compilation-info.h" | 9 #include "src/compilation-info.h" |
10 #include "src/compiler/code-generator-impl.h" | 10 #include "src/compiler/code-generator-impl.h" |
(...skipping 1594 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1605 } | 1605 } |
1606 DCHECK_EQ(LeaveCC, i.OutputSBit()); | 1606 DCHECK_EQ(LeaveCC, i.OutputSBit()); |
1607 break; | 1607 break; |
1608 case kArmPoke: { | 1608 case kArmPoke: { |
1609 int const slot = MiscField::decode(instr->opcode()); | 1609 int const slot = MiscField::decode(instr->opcode()); |
1610 __ str(i.InputRegister(0), MemOperand(sp, slot * kPointerSize)); | 1610 __ str(i.InputRegister(0), MemOperand(sp, slot * kPointerSize)); |
1611 DCHECK_EQ(LeaveCC, i.OutputSBit()); | 1611 DCHECK_EQ(LeaveCC, i.OutputSBit()); |
1612 break; | 1612 break; |
1613 } | 1613 } |
1614 case kArmF32x4Splat: { | 1614 case kArmF32x4Splat: { |
1615 __ vdup(i.OutputSimd128Register(), i.InputFloatRegister(0)); | 1615 int src_code = i.InputFloatRegister(0).code(); |
| 1616 __ vdup(Neon32, i.OutputSimd128Register(), |
| 1617 DwVfpRegister::from_code(src_code / 2), src_code & 0x1); |
1616 break; | 1618 break; |
1617 } | 1619 } |
1618 case kArmF32x4ExtractLane: { | 1620 case kArmF32x4ExtractLane: { |
1619 __ ExtractLane(i.OutputFloatRegister(), i.InputSimd128Register(0), | 1621 __ ExtractLane(i.OutputFloatRegister(), i.InputSimd128Register(0), |
1620 kScratchReg, i.InputInt8(1)); | 1622 i.InputInt8(1)); |
1621 break; | 1623 break; |
1622 } | 1624 } |
1623 case kArmF32x4ReplaceLane: { | 1625 case kArmF32x4ReplaceLane: { |
1624 __ ReplaceLane(i.OutputSimd128Register(), i.InputSimd128Register(0), | 1626 __ ReplaceLane(i.OutputSimd128Register(), i.InputSimd128Register(0), |
1625 i.InputFloatRegister(2), kScratchReg, i.InputInt8(1)); | 1627 i.InputFloatRegister(2), i.InputInt8(1)); |
1626 break; | 1628 break; |
1627 } | 1629 } |
1628 case kArmF32x4SConvertI32x4: { | 1630 case kArmF32x4SConvertI32x4: { |
1629 __ vcvt_f32_s32(i.OutputSimd128Register(), i.InputSimd128Register(0)); | 1631 __ vcvt_f32_s32(i.OutputSimd128Register(), i.InputSimd128Register(0)); |
1630 break; | 1632 break; |
1631 } | 1633 } |
1632 case kArmF32x4UConvertI32x4: { | 1634 case kArmF32x4UConvertI32x4: { |
1633 __ vcvt_f32_u32(i.OutputSimd128Register(), i.InputSimd128Register(0)); | 1635 __ vcvt_f32_u32(i.OutputSimd128Register(), i.InputSimd128Register(0)); |
1634 break; | 1636 break; |
1635 } | 1637 } |
(...skipping 576 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2212 int src0_code = src0.code() * 4; | 2214 int src0_code = src0.code() * 4; |
2213 int src1_code = src1.code() * 4; | 2215 int src1_code = src1.code() * 4; |
2214 int32_t shuffle = i.InputInt32(2); | 2216 int32_t shuffle = i.InputInt32(2); |
2215 for (int i = 0; i < 4; i++) { | 2217 for (int i = 0; i < 4; i++) { |
2216 int lane = shuffle & 0x7; | 2218 int lane = shuffle & 0x7; |
2217 int src_code = src0_code; | 2219 int src_code = src0_code; |
2218 if (lane >= 4) { | 2220 if (lane >= 4) { |
2219 src_code = src1_code; | 2221 src_code = src1_code; |
2220 lane &= 0x3; | 2222 lane &= 0x3; |
2221 } | 2223 } |
2222 __ VmovExtended(dst_code + i, src_code + lane, kScratchReg); | 2224 __ VmovExtended(dst_code + i, src_code + lane); |
2223 shuffle >>= 8; | 2225 shuffle >>= 8; |
2224 } | 2226 } |
2225 break; | 2227 break; |
2226 } | 2228 } |
2227 case kArmS32x4TransposeRight: { | 2229 case kArmS32x4TransposeRight: { |
2228 Simd128Register dst = i.OutputSimd128Register(), | 2230 Simd128Register dst = i.OutputSimd128Register(), |
2229 src1 = i.InputSimd128Register(1); | 2231 src1 = i.InputSimd128Register(1); |
2230 DCHECK(dst.is(i.InputSimd128Register(0))); | 2232 DCHECK(dst.is(i.InputSimd128Register(0))); |
2231 // src0 = [4, 5, 6, 7], src1 = [0, 1, 2, 3] (flipped from TransposeLeft). | 2233 // src0 = [4, 5, 6, 7], src1 = [0, 1, 2, 3] (flipped from TransposeLeft). |
2232 __ vmov(kScratchQuadReg, src1); | 2234 __ vmov(kScratchQuadReg, src1); |
(...skipping 798 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3031 } else { | 3033 } else { |
3032 DCHECK(destination->IsDoubleStackSlot()); | 3034 DCHECK(destination->IsDoubleStackSlot()); |
3033 __ vstr(src, g.ToMemOperand(destination)); | 3035 __ vstr(src, g.ToMemOperand(destination)); |
3034 } | 3036 } |
3035 } else if (rep == MachineRepresentation::kFloat32) { | 3037 } else if (rep == MachineRepresentation::kFloat32) { |
3036 // GapResolver may give us reg codes that don't map to actual s-registers. | 3038 // GapResolver may give us reg codes that don't map to actual s-registers. |
3037 // Generate code to work around those cases. | 3039 // Generate code to work around those cases. |
3038 int src_code = LocationOperand::cast(source)->register_code(); | 3040 int src_code = LocationOperand::cast(source)->register_code(); |
3039 if (destination->IsFloatRegister()) { | 3041 if (destination->IsFloatRegister()) { |
3040 int dst_code = LocationOperand::cast(destination)->register_code(); | 3042 int dst_code = LocationOperand::cast(destination)->register_code(); |
3041 __ VmovExtended(dst_code, src_code, kScratchReg); | 3043 __ VmovExtended(dst_code, src_code); |
3042 } else { | 3044 } else { |
3043 DCHECK(destination->IsFloatStackSlot()); | 3045 DCHECK(destination->IsFloatStackSlot()); |
3044 __ VmovExtended(g.ToMemOperand(destination), src_code, kScratchReg); | 3046 __ VmovExtended(g.ToMemOperand(destination), src_code); |
3045 } | 3047 } |
3046 } else { | 3048 } else { |
3047 DCHECK_EQ(MachineRepresentation::kSimd128, rep); | 3049 DCHECK_EQ(MachineRepresentation::kSimd128, rep); |
3048 QwNeonRegister src = g.ToSimd128Register(source); | 3050 QwNeonRegister src = g.ToSimd128Register(source); |
3049 if (destination->IsSimd128Register()) { | 3051 if (destination->IsSimd128Register()) { |
3050 QwNeonRegister dst = g.ToSimd128Register(destination); | 3052 QwNeonRegister dst = g.ToSimd128Register(destination); |
3051 __ Move(dst, src); | 3053 __ Move(dst, src); |
3052 } else { | 3054 } else { |
3053 DCHECK(destination->IsSimd128StackSlot()); | 3055 DCHECK(destination->IsSimd128StackSlot()); |
3054 MemOperand dst = g.ToMemOperand(destination); | 3056 MemOperand dst = g.ToMemOperand(destination); |
3055 __ add(kScratchReg, dst.rn(), Operand(dst.offset())); | 3057 __ add(kScratchReg, dst.rn(), Operand(dst.offset())); |
3056 __ vst1(Neon8, NeonListOperand(src.low(), 2), | 3058 __ vst1(Neon8, NeonListOperand(src.low(), 2), |
3057 NeonMemOperand(kScratchReg)); | 3059 NeonMemOperand(kScratchReg)); |
3058 } | 3060 } |
3059 } | 3061 } |
3060 } else if (source->IsFPStackSlot()) { | 3062 } else if (source->IsFPStackSlot()) { |
3061 MemOperand src = g.ToMemOperand(source); | 3063 MemOperand src = g.ToMemOperand(source); |
3062 MachineRepresentation rep = | 3064 MachineRepresentation rep = |
3063 LocationOperand::cast(destination)->representation(); | 3065 LocationOperand::cast(destination)->representation(); |
3064 if (destination->IsFPRegister()) { | 3066 if (destination->IsFPRegister()) { |
3065 if (rep == MachineRepresentation::kFloat64) { | 3067 if (rep == MachineRepresentation::kFloat64) { |
3066 __ vldr(g.ToDoubleRegister(destination), src); | 3068 __ vldr(g.ToDoubleRegister(destination), src); |
3067 } else if (rep == MachineRepresentation::kFloat32) { | 3069 } else if (rep == MachineRepresentation::kFloat32) { |
3068 // GapResolver may give us reg codes that don't map to actual | 3070 // GapResolver may give us reg codes that don't map to actual |
3069 // s-registers. Generate code to work around those cases. | 3071 // s-registers. Generate code to work around those cases. |
3070 int dst_code = LocationOperand::cast(destination)->register_code(); | 3072 int dst_code = LocationOperand::cast(destination)->register_code(); |
3071 __ VmovExtended(dst_code, src, kScratchReg); | 3073 __ VmovExtended(dst_code, src); |
3072 } else { | 3074 } else { |
3073 DCHECK_EQ(MachineRepresentation::kSimd128, rep); | 3075 DCHECK_EQ(MachineRepresentation::kSimd128, rep); |
3074 QwNeonRegister dst = g.ToSimd128Register(destination); | 3076 QwNeonRegister dst = g.ToSimd128Register(destination); |
3075 __ add(kScratchReg, src.rn(), Operand(src.offset())); | 3077 __ add(kScratchReg, src.rn(), Operand(src.offset())); |
3076 __ vld1(Neon8, NeonListOperand(dst.low(), 2), | 3078 __ vld1(Neon8, NeonListOperand(dst.low(), 2), |
3077 NeonMemOperand(kScratchReg)); | 3079 NeonMemOperand(kScratchReg)); |
3078 } | 3080 } |
3079 } else if (rep == MachineRepresentation::kFloat64) { | 3081 } else if (rep == MachineRepresentation::kFloat64) { |
3080 DCHECK(destination->IsFPStackSlot()); | 3082 DCHECK(destination->IsFPStackSlot()); |
3081 if (rep == MachineRepresentation::kFloat64) { | 3083 if (rep == MachineRepresentation::kFloat64) { |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3145 DCHECK(destination->IsFPStackSlot()); | 3147 DCHECK(destination->IsFPStackSlot()); |
3146 MemOperand dst = g.ToMemOperand(destination); | 3148 MemOperand dst = g.ToMemOperand(destination); |
3147 __ Move(temp, src); | 3149 __ Move(temp, src); |
3148 __ vldr(src, dst); | 3150 __ vldr(src, dst); |
3149 __ vstr(temp, dst); | 3151 __ vstr(temp, dst); |
3150 } | 3152 } |
3151 } else if (rep == MachineRepresentation::kFloat32) { | 3153 } else if (rep == MachineRepresentation::kFloat32) { |
3152 int src_code = LocationOperand::cast(source)->register_code(); | 3154 int src_code = LocationOperand::cast(source)->register_code(); |
3153 if (destination->IsFPRegister()) { | 3155 if (destination->IsFPRegister()) { |
3154 int dst_code = LocationOperand::cast(destination)->register_code(); | 3156 int dst_code = LocationOperand::cast(destination)->register_code(); |
3155 __ VmovExtended(temp.low().code(), src_code, kScratchReg); | 3157 __ VmovExtended(temp.low().code(), src_code); |
3156 __ VmovExtended(src_code, dst_code, kScratchReg); | 3158 __ VmovExtended(src_code, dst_code); |
3157 __ VmovExtended(dst_code, temp.low().code(), kScratchReg); | 3159 __ VmovExtended(dst_code, temp.low().code()); |
3158 } else { | 3160 } else { |
3159 DCHECK(destination->IsFPStackSlot()); | 3161 DCHECK(destination->IsFPStackSlot()); |
3160 MemOperand dst = g.ToMemOperand(destination); | 3162 MemOperand dst = g.ToMemOperand(destination); |
3161 __ VmovExtended(temp.low().code(), src_code, kScratchReg); | 3163 __ VmovExtended(temp.low().code(), src_code); |
3162 __ VmovExtended(src_code, dst, kScratchReg); | 3164 __ VmovExtended(src_code, dst); |
3163 __ vstr(temp.low(), dst); | 3165 __ vstr(temp.low(), dst); |
3164 } | 3166 } |
3165 } else { | 3167 } else { |
3166 DCHECK_EQ(MachineRepresentation::kSimd128, rep); | 3168 DCHECK_EQ(MachineRepresentation::kSimd128, rep); |
3167 QwNeonRegister src = g.ToSimd128Register(source); | 3169 QwNeonRegister src = g.ToSimd128Register(source); |
3168 if (destination->IsFPRegister()) { | 3170 if (destination->IsFPRegister()) { |
3169 QwNeonRegister dst = g.ToSimd128Register(destination); | 3171 QwNeonRegister dst = g.ToSimd128Register(destination); |
3170 __ Swap(src, dst); | 3172 __ Swap(src, dst); |
3171 } else { | 3173 } else { |
3172 DCHECK(destination->IsFPStackSlot()); | 3174 DCHECK(destination->IsFPStackSlot()); |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3244 padding_size -= v8::internal::Assembler::kInstrSize; | 3246 padding_size -= v8::internal::Assembler::kInstrSize; |
3245 } | 3247 } |
3246 } | 3248 } |
3247 } | 3249 } |
3248 | 3250 |
3249 #undef __ | 3251 #undef __ |
3250 | 3252 |
3251 } // namespace compiler | 3253 } // namespace compiler |
3252 } // namespace internal | 3254 } // namespace internal |
3253 } // namespace v8 | 3255 } // namespace v8 |
OLD | NEW |