diff options
author | Reed Kotler <rkotler@mips.com> | 2012-10-26 04:46:26 +0000 |
---|---|---|
committer | Reed Kotler <rkotler@mips.com> | 2012-10-26 04:46:26 +0000 |
commit | a81be80b0eabfc8b5e590a10471c66dadf6ded6f (patch) | |
tree | 8514128901c58a6b0de8569dd31ed430a3c477e8 /lib/Target/Mips | |
parent | 4734fe19f6d240a911918a330a786751fe1030d9 (diff) |
Implement carry for subtract/add for mips16
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@166755 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Target/Mips')
-rw-r--r-- | lib/Target/Mips/Mips16InstrInfo.td | 15 | ||||
-rw-r--r-- | lib/Target/Mips/MipsISelDAGToDAG.cpp | 18 |
2 files changed, 29 insertions, 4 deletions
diff --git a/lib/Target/Mips/Mips16InstrInfo.td b/lib/Target/Mips/Mips16InstrInfo.td index 74ddc99e13..3721cc7ba0 100644 --- a/lib/Target/Mips/Mips16InstrInfo.td +++ b/lib/Target/Mips/Mips16InstrInfo.td @@ -194,6 +194,10 @@ class FRR16_ins<bits<5> f, string asmstr, InstrItinClass itin> : !strconcat(asmstr, "\t$rx, $ry"), [], itin> { } +class FRRTR16_ins<bits<5> f, string asmstr, InstrItinClass itin> : + FRR16<f, (outs CPU16Regs:$rz), (ins CPU16Regs:$rx, CPU16Regs:$ry), + !strconcat(asmstr, "\t$rx, $ry\n\tmove\t$rz, $$t8"), [], itin> ; + // // maybe refactor but need a $zero as a dummy first parameter // @@ -816,6 +820,9 @@ def SltCCRxRy16: FCCRR16_ins<0b00010, "slt", IIAlu>; // Purpose: Set on Less Than Unsigned // To record the result of an unsigned less-than comparison. // +def SltuRxRyRz16: FRRTR16_ins<0b00011, "sltu", IIAlu> { + let isCodeGenOnly=1; +} def SltuCCRxRy16: FCCRR16_ins<0b00011, "sltu", IIAlu>; @@ -976,6 +983,14 @@ def : Mips16Pat<(i32 imm:$imm), (OrRxRxRy16 (SllX16 (LiRxImmX16 (HI16 imm:$imm)), 16), (LiRxImmX16 (LO16 imm:$imm)))>; +// Carry MipsPatterns +def : Mips16Pat<(subc CPU16Regs:$lhs, CPU16Regs:$rhs), + (SubuRxRyRz16 CPU16Regs:$lhs, CPU16Regs:$rhs)>; +def : Mips16Pat<(addc CPU16Regs:$lhs, CPU16Regs:$rhs), + (AdduRxRyRz16 CPU16Regs:$lhs, CPU16Regs:$rhs)>; +def : Mips16Pat<(addc CPU16Regs:$src, immSExt16:$imm), + (AddiuRxRxImmX16 CPU16Regs:$src, imm:$imm)>; + // // Some branch conditional patterns are not generated by llvm at this time. // Some are for seemingly arbitrary reasons not used: i.e. with signed number diff --git a/lib/Target/Mips/MipsISelDAGToDAG.cpp b/lib/Target/Mips/MipsISelDAGToDAG.cpp index fceb63a1bc..9a5a712ee7 100644 --- a/lib/Target/Mips/MipsISelDAGToDAG.cpp +++ b/lib/Target/Mips/MipsISelDAGToDAG.cpp @@ -413,6 +413,7 @@ SDNode* MipsDAGToDAGISel::Select(SDNode *Node) { case ISD::SUBE: case ISD::ADDE: { + bool inMips16Mode = Subtarget.inMips16Mode(); SDValue InFlag = Node->getOperand(2), CmpLHS; unsigned Opc = InFlag.getOpcode(); (void)Opc; assert(((Opc == ISD::ADDC || Opc == ISD::ADDE) || @@ -422,10 +423,16 @@ SDNode* MipsDAGToDAGISel::Select(SDNode *Node) { unsigned MOp; if (Opcode == ISD::ADDE) { CmpLHS = InFlag.getValue(0); - MOp = Mips::ADDu; + if (inMips16Mode) + MOp = Mips::AdduRxRyRz16; + else + MOp = Mips::ADDu; } else { CmpLHS = InFlag.getOperand(0); - MOp = Mips::SUBu; + if (inMips16Mode) + MOp = Mips::SubuRxRyRz16; + else + MOp = Mips::SUBu; } SDValue Ops[] = { CmpLHS, InFlag.getOperand(1) }; @@ -434,8 +441,11 @@ SDNode* MipsDAGToDAGISel::Select(SDNode *Node) { SDValue RHS = Node->getOperand(1); EVT VT = LHS.getValueType(); - SDNode *Carry = CurDAG->getMachineNode(Mips::SLTu, dl, VT, Ops, 2); - SDNode *AddCarry = CurDAG->getMachineNode(Mips::ADDu, dl, VT, + + unsigned Sltu_op = inMips16Mode? Mips::SltuRxRyRz16: Mips::SLTu; + SDNode *Carry = CurDAG->getMachineNode(Sltu_op, dl, VT, Ops, 2); + unsigned Addu_op = inMips16Mode? Mips::AdduRxRyRz16 : Mips::ADDu; + SDNode *AddCarry = CurDAG->getMachineNode(Addu_op, dl, VT, SDValue(Carry,0), RHS); return CurDAG->SelectNodeTo(Node, MOp, VT, MVT::Glue, |