Index: runtime/vm/intermediate_language_arm64.cc |
=================================================================== |
--- runtime/vm/intermediate_language_arm64.cc (revision 36576) |
+++ runtime/vm/intermediate_language_arm64.cc (working copy) |
@@ -3426,37 +3426,125 @@ |
LocationSummary* Simd32x4ShuffleInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Simd32x4ShuffleInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister value = locs()->in(0).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ switch (op_kind()) { |
+ case MethodRecognizer::kFloat32x4ShuffleX: |
+ __ vinss(result, 0, value, 0); |
+ __ fcvtds(result, result); |
+ break; |
+ case MethodRecognizer::kFloat32x4ShuffleY: |
+ __ vinss(result, 0, value, 1); |
+ __ fcvtds(result, result); |
+ break; |
+ case MethodRecognizer::kFloat32x4ShuffleZ: |
+ __ vinss(result, 0, value, 2); |
+ __ fcvtds(result, result); |
+ break; |
+ case MethodRecognizer::kFloat32x4ShuffleW: |
+ __ vinss(result, 0, value, 3); |
+ __ fcvtds(result, result); |
+ break; |
+ case MethodRecognizer::kInt32x4Shuffle: |
+ case MethodRecognizer::kFloat32x4Shuffle: |
+ if (mask_ == 0x00) { |
+ __ vdups(result, value, 0); |
+ } else if (mask_ == 0x55) { |
+ __ vdups(result, value, 1); |
+ } else if (mask_ == 0xAA) { |
+ __ vdups(result, value, 2); |
+ } else if (mask_ == 0xFF) { |
+ __ vdups(result, value, 3); |
+ } else { |
+ __ vinss(result, 0, value, mask_ & 0x3); |
+ __ vinss(result, 1, value, (mask_ >> 2) & 0x3); |
+ __ vinss(result, 2, value, (mask_ >> 4) & 0x3); |
+ __ vinss(result, 3, value, (mask_ >> 6) & 0x3); |
+ } |
+ break; |
+ default: UNREACHABLE(); |
+ } |
} |
LocationSummary* Simd32x4ShuffleMixInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 2; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_in(1, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Simd32x4ShuffleMixInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister left = locs()->in(0).fpu_reg(); |
+ const VRegister right = locs()->in(1).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ switch (op_kind()) { |
+ case MethodRecognizer::kFloat32x4ShuffleMix: |
+ case MethodRecognizer::kInt32x4ShuffleMix: |
+ __ vinss(result, 0, left, mask_ & 0x3); |
+ __ vinss(result, 1, left, (mask_ >> 2) & 0x3); |
+ __ vinss(result, 2, right, (mask_ >> 4) & 0x3); |
+ __ vinss(result, 3, right, (mask_ >> 6) & 0x3); |
+ break; |
+ default: UNREACHABLE(); |
+ } |
} |
LocationSummary* Simd32x4GetSignMaskInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 1; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_temp(0, Location::RequiresRegister()); |
+ summary->set_out(0, Location::RequiresRegister()); |
+ return summary; |
} |
void Simd32x4GetSignMaskInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister value = locs()->in(0).fpu_reg(); |
+ const Register out = locs()->out(0).reg(); |
+ const Register temp = locs()->temp(0).reg(); |
+ |
+ // X lane. |
+ __ vmovrs(out, value, 0); |
+ __ Lsr(out, out, 31); |
+ // Y lane. |
+ __ vmovrs(temp, value, 1); |
+ __ Lsr(temp, temp, 31); |
+ __ orr(out, out, Operand(temp, LSL, 1)); |
+ // Z lane. |
+ __ vmovrs(temp, value, 2); |
+ __ Lsr(temp, temp, 31); |
+ __ orr(out, out, Operand(temp, LSL, 2)); |
+ // W lane. |
+ __ vmovrs(temp, value, 3); |
+ __ Lsr(temp, temp, 31); |
+ __ orr(out, out, Operand(temp, LSL, 3)); |
+ // Tag. |
+ __ SmiTag(out); |
} |
@@ -3482,14 +3570,14 @@ |
const VRegister v3 = locs()->in(3).fpu_reg(); |
const VRegister r = locs()->out(0).fpu_reg(); |
- __ fcvtsd(v0, v0); |
- __ vinss(r, 0, v0, 0); |
- __ fcvtsd(v1, v1); |
- __ vinss(r, 1, v1, 1); |
- __ fcvtsd(v2, v2); |
- __ vinss(r, 2, v2, 2); |
- __ fcvtsd(v3, v3); |
- __ vinss(r, 3, v3, 3); |
+ __ fcvtsd(VTMP, v0); |
+ __ vinss(r, 0, VTMP, 0); |
+ __ fcvtsd(VTMP, v1); |
+ __ vinss(r, 1, VTMP, 0); |
+ __ fcvtsd(VTMP, v2); |
+ __ vinss(r, 2, VTMP, 0); |
+ __ fcvtsd(VTMP, v3); |
+ __ vinss(r, 3, VTMP, 0); |
} |
@@ -3506,7 +3594,7 @@ |
void Float32x4ZeroInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
const VRegister v = locs()->out(0).fpu_reg(); |
- __ LoadDImmediate(v, 0.0, PP); |
+ __ veor(v, v, v); |
} |
@@ -3601,13 +3689,29 @@ |
LocationSummary* Float32x4ZeroArgInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Float32x4ZeroArgInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister left = locs()->in(0).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ switch (op_kind()) { |
+ case MethodRecognizer::kFloat32x4Negate: |
+ __ vnegs(result, left); |
+ break; |
+ case MethodRecognizer::kFloat32x4Absolute: |
+ __ vabss(result, left); |
+ break; |
+ default: UNREACHABLE(); |
+ } |
} |
@@ -3625,25 +3729,64 @@ |
LocationSummary* Float32x4WithInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 2; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_in(1, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Float32x4WithInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister replacement = locs()->in(0).fpu_reg(); |
+ const VRegister value = locs()->in(1).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ __ fcvtsd(VTMP, replacement); |
+ if (result != value) { |
+ __ vmov(result, value); |
+ } |
+ |
+ switch (op_kind()) { |
+ case MethodRecognizer::kFloat32x4WithX: |
+ __ vinss(result, 0, VTMP, 0); |
+ break; |
+ case MethodRecognizer::kFloat32x4WithY: |
+ __ vinss(result, 1, VTMP, 0); |
+ break; |
+ case MethodRecognizer::kFloat32x4WithZ: |
+ __ vinss(result, 2, VTMP, 0); |
+ break; |
+ case MethodRecognizer::kFloat32x4WithW: |
+ __ vinss(result, 3, VTMP, 0); |
+ break; |
+ default: UNREACHABLE(); |
+ } |
} |
LocationSummary* Float32x4ToInt32x4Instr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Float32x4ToInt32x4Instr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister value = locs()->in(0).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ if (value != result) { |
+ __ vmov(result, value); |
+ } |
} |
@@ -3688,7 +3831,7 @@ |
void Float64x2ZeroInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
const VRegister v = locs()->out(0).fpu_reg(); |
- __ LoadDImmediate(v, 0.0, PP); |
+ __ veor(v, v, v); |
} |
@@ -3735,25 +3878,57 @@ |
LocationSummary* Float64x2ToFloat32x4Instr::MakeLocationSummary( |
Isolate* isolate, bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Float64x2ToFloat32x4Instr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister q = locs()->in(0).fpu_reg(); |
+ const VRegister r = locs()->out(0).fpu_reg(); |
+ |
+ // Zero register. |
+ __ veor(r, r, r); |
+ // Set X lane. |
+ __ vinsd(VTMP, 0, q, 0); |
+ __ fcvtsd(VTMP, VTMP); |
+ __ vinss(r, 0, VTMP, 0); |
+ // Set Y lane. |
+ __ vinsd(VTMP, 0, q, 1); |
+ __ fcvtsd(VTMP, VTMP); |
+ __ vinss(r, 1, VTMP, 0); |
} |
LocationSummary* Float32x4ToFloat64x2Instr::MakeLocationSummary( |
Isolate* isolate, bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Float32x4ToFloat64x2Instr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister q = locs()->in(0).fpu_reg(); |
+ const VRegister r = locs()->out(0).fpu_reg(); |
+ |
+ // Set X. |
+ __ vinss(VTMP, 0, q, 0); |
+ __ fcvtds(VTMP, VTMP); |
+ __ vinsd(r, 0, VTMP, 0); |
+ // Set Y. |
+ __ vinss(VTMP, 0, q, 1); |
+ __ fcvtds(VTMP, VTMP); |
+ __ vinsd(r, 1, VTMP, 0); |
} |
@@ -3771,85 +3946,260 @@ |
LocationSummary* Float64x2OneArgInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 2; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_in(1, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::SameAsFirstInput()); |
+ return summary; |
} |
void Float64x2OneArgInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister left = locs()->in(0).fpu_reg(); |
+ const VRegister right = locs()->in(1).fpu_reg(); |
+ const VRegister out = locs()->out(0).fpu_reg(); |
+ ASSERT(left == out); |
+ |
+ switch (op_kind()) { |
+ case MethodRecognizer::kFloat64x2Scale: |
+ __ vmuld(out, left, right); |
+ break; |
+ case MethodRecognizer::kFloat64x2WithX: |
+ __ vinsd(out, 0, right, 0); |
+ break; |
+ case MethodRecognizer::kFloat64x2WithY: |
+ __ vinsd(out, 1, right, 0); |
+ break; |
+ case MethodRecognizer::kFloat64x2Min: { |
+ UNIMPLEMENTED(); |
+ break; |
+ } |
+ case MethodRecognizer::kFloat64x2Max: { |
+ UNIMPLEMENTED(); |
+ break; |
+ } |
+ default: UNREACHABLE(); |
+ } |
} |
LocationSummary* Int32x4BoolConstructorInstr::MakeLocationSummary( |
Isolate* isolate, bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 4; |
+ const intptr_t kNumTemps = 1; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresRegister()); |
+ summary->set_in(1, Location::RequiresRegister()); |
+ summary->set_in(2, Location::RequiresRegister()); |
+ summary->set_in(3, Location::RequiresRegister()); |
+ summary->set_temp(0, Location::RequiresRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Int32x4BoolConstructorInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const Register v0 = locs()->in(0).reg(); |
+ const Register v1 = locs()->in(1).reg(); |
+ const Register v2 = locs()->in(2).reg(); |
+ const Register v3 = locs()->in(3).reg(); |
+ const Register temp = locs()->temp(0).reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ __ veor(result, result, result); |
+ __ LoadImmediate(temp, 0xffffffff, PP); |
+ __ LoadObject(TMP2, Bool::True(), PP); |
+ |
+ // __ CompareObject(v0, Bool::True(), PP); |
+ __ CompareRegisters(v0, TMP2); |
+ __ csel(TMP, temp, ZR, EQ); |
+ __ vinsw(result, 0, TMP); |
+ |
+ // __ CompareObject(v1, Bool::True(), PP); |
+ __ CompareRegisters(v1, TMP2); |
+ __ csel(TMP, temp, ZR, EQ); |
+ __ vinsw(result, 1, TMP); |
+ |
+ // __ CompareObject(v2, Bool::True(), PP); |
+ __ CompareRegisters(v2, TMP2); |
+ __ csel(TMP, temp, ZR, EQ); |
+ __ vinsw(result, 2, TMP); |
+ |
+ // __ CompareObject(v3, Bool::True(), PP); |
+ __ CompareRegisters(v3, TMP2); |
+ __ csel(TMP, temp, ZR, EQ); |
+ __ vinsw(result, 3, TMP); |
} |
LocationSummary* Int32x4GetFlagInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresRegister()); |
+ return summary; |
} |
void Int32x4GetFlagInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister value = locs()->in(0).fpu_reg(); |
+ const Register result = locs()->out(0).reg(); |
+ |
+ switch (op_kind()) { |
+ case MethodRecognizer::kInt32x4GetFlagX: |
+ __ vmovrs(result, value, 0); |
+ break; |
+ case MethodRecognizer::kInt32x4GetFlagY: |
+ __ vmovrs(result, value, 1); |
+ break; |
+ case MethodRecognizer::kInt32x4GetFlagZ: |
+ __ vmovrs(result, value, 2); |
+ break; |
+ case MethodRecognizer::kInt32x4GetFlagW: |
+ __ vmovrs(result, value, 3); |
+ break; |
+ default: UNREACHABLE(); |
+ } |
+ |
+ __ tst(result, Operand(result)); |
+ __ LoadObject(result, Bool::True(), PP); |
+ __ LoadObject(TMP, Bool::False(), PP); |
+ __ csel(result, TMP, result, EQ); |
} |
LocationSummary* Int32x4SelectInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 3; |
+ const intptr_t kNumTemps = 1; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_in(1, Location::RequiresFpuRegister()); |
+ summary->set_in(2, Location::RequiresFpuRegister()); |
+ summary->set_temp(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Int32x4SelectInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister mask = locs()->in(0).fpu_reg(); |
+ const VRegister trueValue = locs()->in(1).fpu_reg(); |
+ const VRegister falseValue = locs()->in(2).fpu_reg(); |
+ const VRegister out = locs()->out(0).fpu_reg(); |
+ const VRegister temp = locs()->temp(0).fpu_reg(); |
+ |
+ // Copy mask. |
+ __ vmov(temp, mask); |
+ // Invert it. |
+ __ vnot(temp, temp); |
+ // mask = mask & trueValue. |
+ __ vand(mask, mask, trueValue); |
+ // temp = temp & falseValue. |
+ __ vand(temp, temp, falseValue); |
+ // out = mask | temp. |
+ __ vorr(out, mask, temp); |
} |
LocationSummary* Int32x4SetFlagInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 2; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_in(1, Location::RequiresRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Int32x4SetFlagInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister mask = locs()->in(0).fpu_reg(); |
+ const Register flag = locs()->in(1).reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ if (result != mask) { |
+ __ vmov(result, mask); |
+ } |
+ |
+ __ CompareObject(flag, Bool::True(), PP); |
+ __ LoadImmediate(TMP, 0xffffffff, PP); |
+ __ csel(TMP, TMP, ZR, EQ); |
+ switch (op_kind()) { |
+ case MethodRecognizer::kInt32x4WithFlagX: |
+ __ vinsw(result, 0, TMP); |
+ break; |
+ case MethodRecognizer::kInt32x4WithFlagY: |
+ __ vinsw(result, 1, TMP); |
+ break; |
+ case MethodRecognizer::kInt32x4WithFlagZ: |
+ __ vinsw(result, 2, TMP); |
+ break; |
+ case MethodRecognizer::kInt32x4WithFlagW: |
+ __ vinsw(result, 3, TMP); |
+ break; |
+ default: UNREACHABLE(); |
+ } |
} |
LocationSummary* Int32x4ToFloat32x4Instr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 1; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void Int32x4ToFloat32x4Instr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister value = locs()->in(0).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ |
+ if (value != result) { |
+ __ vmov(result, value); |
+ } |
} |
LocationSummary* BinaryInt32x4OpInstr::MakeLocationSummary(Isolate* isolate, |
bool opt) const { |
- UNIMPLEMENTED(); |
- return NULL; |
+ const intptr_t kNumInputs = 2; |
+ const intptr_t kNumTemps = 0; |
+ LocationSummary* summary = new LocationSummary( |
+ isolate, kNumInputs, kNumTemps, LocationSummary::kNoCall); |
+ summary->set_in(0, Location::RequiresFpuRegister()); |
+ summary->set_in(1, Location::RequiresFpuRegister()); |
+ summary->set_out(0, Location::RequiresFpuRegister()); |
+ return summary; |
} |
void BinaryInt32x4OpInstr::EmitNativeCode(FlowGraphCompiler* compiler) { |
- UNIMPLEMENTED(); |
+ const VRegister left = locs()->in(0).fpu_reg(); |
+ const VRegister right = locs()->in(1).fpu_reg(); |
+ const VRegister result = locs()->out(0).fpu_reg(); |
+ switch (op_kind()) { |
+ case Token::kBIT_AND: __ vand(result, left, right); break; |
+ case Token::kBIT_OR: __ vorr(result, left, right); break; |
+ case Token::kBIT_XOR: __ veor(result, left, right); break; |
+ case Token::kADD: __ vaddw(result, left, right); break; |
+ case Token::kSUB: __ vsubw(result, left, right); break; |
+ default: UNREACHABLE(); |
+ } |
} |