[turbofan] Recognize sign extension of 8-bit and 16-bit values on arm64.
R=bmeurer@chromium.org Review URL: https://codereview.chromium.org/730183005 Cr-Commit-Position: refs/heads/master@{#25475}
This commit is contained in:
parent
be0fcaa2bc
commit
9b5c279b9f
@ -416,6 +416,12 @@ void CodeGenerator::AssembleArchInstruction(Instruction* instr) {
|
||||
case kArm64Mov32:
|
||||
__ Mov(i.OutputRegister32(), i.InputRegister32(0));
|
||||
break;
|
||||
case kArm64Sxtb32:
|
||||
__ Sxtb(i.OutputRegister32(), i.InputRegister32(0));
|
||||
break;
|
||||
case kArm64Sxth32:
|
||||
__ Sxth(i.OutputRegister32(), i.InputRegister32(0));
|
||||
break;
|
||||
case kArm64Sxtw:
|
||||
__ Sxtw(i.OutputRegister(), i.InputRegister32(0));
|
||||
break;
|
||||
|
@ -65,6 +65,8 @@ namespace compiler {
|
||||
V(Arm64Ror) \
|
||||
V(Arm64Ror32) \
|
||||
V(Arm64Mov32) \
|
||||
V(Arm64Sxtb32) \
|
||||
V(Arm64Sxth32) \
|
||||
V(Arm64Sxtw) \
|
||||
V(Arm64Ubfx) \
|
||||
V(Arm64Ubfx32) \
|
||||
|
@ -608,6 +608,21 @@ void InstructionSelector::VisitWord64Shr(Node* node) {
|
||||
|
||||
|
||||
void InstructionSelector::VisitWord32Sar(Node* node) {
|
||||
Arm64OperandGenerator g(this);
|
||||
Int32BinopMatcher m(node);
|
||||
// Select Sxth/Sxtb for (x << K) >> K where K is 16 or 24.
|
||||
if (CanCover(node, m.left().node()) && m.left().IsWord32Shl()) {
|
||||
Int32BinopMatcher mleft(m.left().node());
|
||||
if (mleft.right().Is(16) && m.right().Is(16)) {
|
||||
Emit(kArm64Sxth32, g.DefineAsRegister(node),
|
||||
g.UseRegister(mleft.left().node()));
|
||||
return;
|
||||
} else if (mleft.right().Is(24) && m.right().Is(24)) {
|
||||
Emit(kArm64Sxtb32, g.DefineAsRegister(node),
|
||||
g.UseRegister(mleft.left().node()));
|
||||
return;
|
||||
}
|
||||
}
|
||||
VisitRRO(this, kArm64Asr32, node, kShift32Imm);
|
||||
}
|
||||
|
||||
|
@ -2129,6 +2129,38 @@ TEST_F(InstructionSelectorTest, Int32MulHighWithParameters) {
|
||||
EXPECT_EQ(s.ToVreg(n), s.ToVreg(s[1]->Output()));
|
||||
}
|
||||
|
||||
|
||||
TEST_F(InstructionSelectorTest, Word32SarWithWord32Shl) {
|
||||
{
|
||||
StreamBuilder m(this, kMachInt32, kMachInt32);
|
||||
Node* const p0 = m.Parameter(0);
|
||||
Node* const r =
|
||||
m.Word32Sar(m.Word32Shl(p0, m.Int32Constant(24)), m.Int32Constant(24));
|
||||
m.Return(r);
|
||||
Stream s = m.Build();
|
||||
ASSERT_EQ(1U, s.size());
|
||||
EXPECT_EQ(kArm64Sxtb32, s[0]->arch_opcode());
|
||||
ASSERT_EQ(1U, s[0]->InputCount());
|
||||
EXPECT_EQ(s.ToVreg(p0), s.ToVreg(s[0]->InputAt(0)));
|
||||
ASSERT_EQ(1U, s[0]->OutputCount());
|
||||
EXPECT_EQ(s.ToVreg(r), s.ToVreg(s[0]->Output()));
|
||||
}
|
||||
{
|
||||
StreamBuilder m(this, kMachInt32, kMachInt32);
|
||||
Node* const p0 = m.Parameter(0);
|
||||
Node* const r =
|
||||
m.Word32Sar(m.Word32Shl(p0, m.Int32Constant(16)), m.Int32Constant(16));
|
||||
m.Return(r);
|
||||
Stream s = m.Build();
|
||||
ASSERT_EQ(1U, s.size());
|
||||
EXPECT_EQ(kArm64Sxth32, s[0]->arch_opcode());
|
||||
ASSERT_EQ(1U, s[0]->InputCount());
|
||||
EXPECT_EQ(s.ToVreg(p0), s.ToVreg(s[0]->InputAt(0)));
|
||||
ASSERT_EQ(1U, s[0]->OutputCount());
|
||||
EXPECT_EQ(s.ToVreg(r), s.ToVreg(s[0]->Output()));
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace compiler
|
||||
} // namespace internal
|
||||
} // namespace v8
|
||||
|
Loading…
Reference in New Issue
Block a user