X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FTarget%2FMips%2FMips16InstrInfo.td;h=10fff03b7240f118685569ad7f6dedb429408321;hb=872808e946f3f8be1b30a6672697c2ba8e12f9e1;hp=4415ccb7df4e0cd0b2d3a85bbdd46a45768067aa;hpb=c6d4d667a8a56b341fac949153ec5939857445df;p=oota-llvm.git diff --git a/lib/Target/Mips/Mips16InstrInfo.td b/lib/Target/Mips/Mips16InstrInfo.td index 4415ccb7df4..10fff03b724 100644 --- a/lib/Target/Mips/Mips16InstrInfo.td +++ b/lib/Target/Mips/Mips16InstrInfo.td @@ -51,7 +51,10 @@ class FI816_ins_base _func, string asmstr, FI816<_func, (outs), (ins simm16:$imm), !strconcat(asmstr, asmstr2), [], itin>; - +class FI816_ins _func, string asmstr, + InstrItinClass itin>: + FI816_ins_base<_func, asmstr, "\t$imm # 16 bit inst", itin>; + class FI816_SP_ins _func, string asmstr, InstrItinClass itin>: FI816_ins_base<_func, asmstr, "\t$$sp, $imm # 16 bit inst", itin>; @@ -116,7 +119,18 @@ class FJAL16_ins _X, string asmstr, !strconcat(asmstr, "\t$imm\n\tnop"),[], itin> { let isCodeGenOnly=1; + let Size=6; +} + +class FJALB16_ins _X, string asmstr, + InstrItinClass itin>: + FJAL16<_X, (outs), (ins simm20:$imm), + !strconcat(asmstr, "\t$imm\t# branch\n\tnop"),[], + itin> { + let isCodeGenOnly=1; + let Size=6; } + // // EXT-I instruction format // @@ -286,7 +300,7 @@ class FI8_MOV32R16_ins: // // This are pseudo formats for multiply -// This first one can be changed to non pseudo now. +// This first one can be changed to non-pseudo now. // // MULT // @@ -488,7 +502,7 @@ class ArithLogic16Defs { bits<5> shamt = 0; bit isCommutable = isCom; bit isReMaterializable = 1; - bit neverHasSideEffects = 1; + bit hasSideEffects = 0; } class branch16 { @@ -627,6 +641,10 @@ def Break16: FRRBreakNull16_ins<"break 0", NoItinerary>; // Purpose: Branch on T Equal to Zero (Extended) // To test special register T then do a PC-relative conditional branch. // +def Bteqz16: FI816_ins<0b000, "bteqz", IIAlu>, cbranch16 { + let Uses = [T8]; +} + def BteqzX16: FEXT_I816_ins<0b000, "bteqz", IIAlu>, cbranch16 { let Uses = [T8]; } @@ -650,6 +668,11 @@ def BteqzT8SltiuX16: FEXT_T8I8I16_ins<"bteqz", "sltiu">, // Purpose: Branch on T Not Equal to Zero (Extended) // To test special register T then do a PC-relative conditional branch. // + +def Btnez16: FI816_ins<0b001, "btnez", IIAlu>, cbranch16 { + let Uses = [T8]; +} + def BtnezX16: FEXT_I816_ins<0b001, "btnez", IIAlu> ,cbranch16 { let Uses = [T8]; } @@ -722,6 +745,13 @@ def DivuRxRy16: FRR16_div_ins<0b11011, "divu", IIAlu> { def Jal16 : FJAL16_ins<0b0, "jal", IIAlu> { let hasDelaySlot = 0; // not true, but we add the nop for now let isCall=1; + let Defs = [RA]; +} + +def JalB16 : FJALB16_ins<0b0, "jal", IIAlu>, branch16 { + let hasDelaySlot = 0; // not true, but we add the nop for now + let isBranch=1; + let Defs = [RA]; } // @@ -757,7 +787,7 @@ def JrcRx16: FRR16_JALRC_ins<1, 1, 0, "jrc", IIAlu> { // Purpose: Load Byte (Extended) // To load a byte from memory as a signed value. // -def LbRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10011, "lb", mem16, IILoad>, MayLoad{ +def LbRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10011, "lb", mem16, II_LB>, MayLoad{ let isCodeGenOnly = 1; } @@ -767,7 +797,7 @@ def LbRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10011, "lb", mem16, IILoad>, MayLoad{ // To load a byte from memory as a unsigned value. // def LbuRxRyOffMemX16: - FEXT_RRI16_mem_ins<0b10100, "lbu", mem16, IILoad>, MayLoad { + FEXT_RRI16_mem_ins<0b10100, "lbu", mem16, II_LBU>, MayLoad { let isCodeGenOnly = 1; } @@ -776,7 +806,7 @@ def LbuRxRyOffMemX16: // Purpose: Load Halfword signed (Extended) // To load a halfword from memory as a signed value. // -def LhRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10100, "lh", mem16, IILoad>, MayLoad{ +def LhRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10100, "lh", mem16, II_LH>, MayLoad{ let isCodeGenOnly = 1; } @@ -786,7 +816,7 @@ def LhRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10100, "lh", mem16, IILoad>, MayLoad{ // To load a halfword from memory as an unsigned value. // def LhuRxRyOffMemX16: - FEXT_RRI16_mem_ins<0b10100, "lhu", mem16, IILoad>, MayLoad { + FEXT_RRI16_mem_ins<0b10100, "lhu", mem16, II_LHU>, MayLoad { let isCodeGenOnly = 1; } @@ -813,7 +843,7 @@ def LiRxImmAlignX16: FEXT_RI16_ins<0b01101, ".align 2\n\tli", IIAlu> { // Purpose: Load Word (Extended) // To load a word from memory as a signed value. // -def LwRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10011, "lw", mem16, IILoad>, MayLoad{ +def LwRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10011, "lw", mem16, II_LW>, MayLoad{ let isCodeGenOnly = 1; } @@ -821,13 +851,13 @@ def LwRxRyOffMemX16: FEXT_RRI16_mem_ins<0b10011, "lw", mem16, IILoad>, MayLoad{ // Purpose: Load Word (SP-Relative, Extended) // To load an SP-relative word from memory as a signed value. // -def LwRxSpImmX16: FEXT_RI16_SP_explicit_ins<0b10010, "lw", IILoad>, MayLoad{ +def LwRxSpImmX16: FEXT_RI16_SP_explicit_ins<0b10010, "lw", II_LW>, MayLoad{ let Uses = [SP]; } -def LwRxPcTcp16: FRI16_TCP_ins<0b10110, "lw", IILoad>, MayLoad; +def LwRxPcTcp16: FRI16_TCP_ins<0b10110, "lw", II_LW>, MayLoad; -def LwRxPcTcpX16: FEXT_RI16_TCP_ins<0b10110, "lw", IILoad>, MayLoad; +def LwRxPcTcpX16: FEXT_RI16_TCP_ins<0b10110, "lw", II_LW>, MayLoad; // // Format: MOVE r32, rz MIPS16e // Purpose: Move @@ -849,7 +879,7 @@ def MoveR3216: FI8_MOVR3216_ins<"move", IIAlu>; // def Mfhi16: FRR16_M_ins<0b10000, "mfhi", IIAlu> { let Uses = [HI0]; - let neverHasSideEffects = 1; + let hasSideEffects = 0; } // @@ -859,7 +889,7 @@ def Mfhi16: FRR16_M_ins<0b10000, "mfhi", IIAlu> { // def Mflo16: FRR16_M_ins<0b10010, "mflo", IIAlu> { let Uses = [LO0]; - let neverHasSideEffects = 1; + let hasSideEffects = 0; } // @@ -867,13 +897,13 @@ def Mflo16: FRR16_M_ins<0b10010, "mflo", IIAlu> { // def MultRxRy16: FMULT16_ins<"mult", IIAlu> { let isCommutable = 1; - let neverHasSideEffects = 1; + let hasSideEffects = 0; let Defs = [HI0, LO0]; } def MultuRxRy16: FMULT16_ins<"multu", IIAlu> { let isCommutable = 1; - let neverHasSideEffects = 1; + let hasSideEffects = 0; let Defs = [HI0, LO0]; } @@ -884,7 +914,7 @@ def MultuRxRy16: FMULT16_ins<"multu", IIAlu> { // def MultRxRyRz16: FMULT16_LO_ins<"mult", IIAlu> { let isCommutable = 1; - let neverHasSideEffects = 1; + let hasSideEffects = 0; let Defs = [HI0, LO0]; } @@ -895,7 +925,7 @@ def MultRxRyRz16: FMULT16_LO_ins<"mult", IIAlu> { // def MultuRxRyRz16: FMULT16_LO_ins<"multu", IIAlu> { let isCommutable = 1; - let neverHasSideEffects = 1; + let hasSideEffects = 0; let Defs = [HI0, LO0]; } @@ -929,26 +959,18 @@ def OrRxRxRy16: FRxRxRy16_ins<0b01101, "or", IIAlu>, ArithLogic16Defs<1>; // stack // -// fixed form for restoring RA and the frame -// for direct object emitter, encoding needs to be adjusted for the -// frame size -// -let ra=1, s=0,s0=1,s1=1 in -def RestoreRaF16: - FI8_SVRS16<0b1, (outs), (ins uimm16:$frame_size), - "restore\t$$ra, $$s0, $$s1, $$s2, $frame_size", [], IILoad >, MayLoad { +def Restore16: + FI8_SVRS16<0b1, (outs), (ins variable_ops), + "", [], II_RESTORE >, MayLoad { let isCodeGenOnly = 1; - let Defs = [S0, S1, S2, RA, SP]; + let Defs = [SP]; let Uses = [SP]; } -// Use Restore to increment SP since SP is not a Mip 16 register, this -// is an easy way to do that which does not require a register. -// -let ra=0, s=0,s0=0,s1=0 in -def RestoreIncSpF16: - FI8_SVRS16<0b1, (outs), (ins uimm16:$frame_size), - "restore\t$frame_size", [], IILoad >, MayLoad { + +def RestoreX16: + FI8_SVRS16<0b1, (outs), (ins variable_ops), + "", [], II_RESTORE >, MayLoad { let isCodeGenOnly = 1; let Defs = [SP]; let Uses = [SP]; @@ -961,23 +983,17 @@ def RestoreIncSpF16: // To set up a stack frame on entry to a subroutine, // saving return address and static registers, and adjusting stack // -let ra=1, s=1,s0=1,s1=1 in -def SaveRaF16: - FI8_SVRS16<0b1, (outs), (ins uimm16:$frame_size), - "save\t$$ra, $$s0, $$s1, $$s2, $frame_size", [], IIStore >, MayStore { +def Save16: + FI8_SVRS16<0b1, (outs), (ins variable_ops), + "", [], II_SAVE >, MayStore { let isCodeGenOnly = 1; - let Uses = [RA, SP, S0, S1, S2]; + let Uses = [SP]; let Defs = [SP]; } -// -// Use Save to decrement the SP by a constant since SP is not -// a Mips16 register. -// -let ra=0, s=0,s0=0,s1=0 in -def SaveDecSpF16: - FI8_SVRS16<0b1, (outs), (ins uimm16:$frame_size), - "save\t$frame_size", [], IIStore >, MayStore { +def SaveX16: + FI8_SVRS16<0b1, (outs), (ins variable_ops), + "", [], II_SAVE >, MayStore { let isCodeGenOnly = 1; let Uses = [SP]; let Defs = [SP]; @@ -988,7 +1004,7 @@ def SaveDecSpF16: // To store a byte to memory. // def SbRxRyOffMemX16: - FEXT_RRI16_mem2_ins<0b11000, "sb", mem16, IIStore>, MayStore; + FEXT_RRI16_mem2_ins<0b11000, "sb", mem16, II_SB>, MayStore; // // Format: SEB rx MIPS16e @@ -1126,7 +1142,7 @@ def SelTBtneZSltiu: SeliT<"btnez", "sltiu">; // To store a halfword to memory. // def ShRxRyOffMemX16: - FEXT_RRI16_mem2_ins<0b11001, "sh", mem16, IIStore>, MayStore; + FEXT_RRI16_mem2_ins<0b11001, "sh", mem16, II_SH>, MayStore; // // Format: SLL rx, ry, sa MIPS16e @@ -1262,7 +1278,7 @@ def SubuRxRyRz16: FRRR16_ins<0b11, "subu", IIAlu>, ArithLogic16Defs<0>; // To store a word to memory. // def SwRxRyOffMemX16: - FEXT_RRI16_mem2_ins<0b11011, "sw", mem16, IIStore>, MayStore; + FEXT_RRI16_mem2_ins<0b11011, "sw", mem16, II_SW>, MayStore; // // Format: SW rx, offset(sp) MIPS16e @@ -1270,7 +1286,7 @@ def SwRxRyOffMemX16: // To store an SP-relative word to memory. // def SwRxSpImmX16: FEXT_RI16_SP_Store_explicit_ins - <0b11010, "sw", IIStore>, MayStore; + <0b11010, "sw", II_SW>, MayStore; // // @@ -1354,15 +1370,19 @@ def : Mips16Pat<(MipsJmpLink (i32 texternalsym:$dst)), (Jal16 texternalsym:$dst)>; // Indirect branch -def: Mips16Pat< - (brind CPU16Regs:$rs), - (JrcRx16 CPU16Regs:$rs)>; +def: Mips16Pat<(brind CPU16Regs:$rs), (JrcRx16 CPU16Regs:$rs)> { + // Ensure that the addition of MIPS32r6/MIPS64r6 support does not change + // MIPS16's behaviour. + let AddedComplexity = 1; +} // Jump and Link (Call) let isCall=1, hasDelaySlot=0 in def JumpLinkReg16: FRR16_JALRC<0, 0, 0, (outs), (ins CPU16Regs:$rs), - "jalrc \t$rs", [(MipsJmpLink CPU16Regs:$rs)], IIBranch>; + "jalrc \t$rs", [(MipsJmpLink CPU16Regs:$rs)], IIBranch> { + let Defs = [RA]; +} // Mips16 pseudos let isReturn=1, isTerminator=1, hasDelaySlot=1, isBarrier=1, hasCtrlDep=1, @@ -1427,7 +1447,7 @@ def: Mips16Pat def: Mips16Pat <(brcond (i32 (seteq CPU16Regs:$rx, 0)), bb:$targ16), - (BeqzRxImmX16 CPU16Regs:$rx, bb:$targ16) + (BeqzRxImm16 CPU16Regs:$rx, bb:$targ16) >; // @@ -1489,7 +1509,7 @@ def: Mips16Pat def: Mips16Pat <(brcond (i32 (setne CPU16Regs:$rx, 0)), bb:$targ16), - (BnezRxImmX16 CPU16Regs:$rx, bb:$targ16) + (BnezRxImm16 CPU16Regs:$rx, bb:$targ16) >; // @@ -1497,7 +1517,7 @@ def: Mips16Pat // def: Mips16Pat <(brcond CPU16Regs:$rx, bb:$targ16), - (BnezRxImmX16 CPU16Regs:$rx, bb:$targ16) + (BnezRxImm16 CPU16Regs:$rx, bb:$targ16) >; // @@ -1751,9 +1771,9 @@ def: Mips16Pat // // For constants, llvm transforms this to: -// x > (k -1) and then reverses the operands to use setlt. So this pattern +// x > (k - 1) and then reverses the operands to use setlt. So this pattern // is not used now by the compiler. (Presumably checking that k-1 does not -// overflow). The compiler never uses this at a the current time, due to +// overflow). The compiler never uses this at the current time, due to // other optimizations. // //def: Mips16Pat @@ -1878,7 +1898,7 @@ def GotPrologue16: MipsPseudo16< (outs CPU16Regs:$rh, CPU16Regs:$rl), (ins simm16:$immHi, simm16:$immLo), - ".align 2\n\tli\t$rh, $immHi\n\taddiu\t$rl, $$pc, $immLo\n ",[]> ; + "li\t$rh, $immHi\n\taddiu\t$rl, $$pc, $immLo\n ",[]> ; // An operand for the CONSTPOOL_ENTRY pseudo-instruction. def cpinst_operand : Operand { @@ -1890,7 +1910,7 @@ def cpinst_operand : Operand { // is the index into the MachineConstantPool that this is, the third is the // size in bytes of this constant pool entry. // -let neverHasSideEffects = 1, isNotDuplicable = 1 in +let hasSideEffects = 0, isNotDuplicable = 1 in def CONSTPOOL_ENTRY : MipsPseudo16<(outs), (ins cpinst_operand:$instid, cpinst_operand:$cpidx, i32imm:$size), "foo", []>;