diff --git a/lib/Target/PowerPC/PPC32AsmPrinter.cpp b/lib/Target/PowerPC/PPC32AsmPrinter.cpp index b30977b1a19..cadc88a0b91 100644 --- a/lib/Target/PowerPC/PPC32AsmPrinter.cpp +++ b/lib/Target/PowerPC/PPC32AsmPrinter.cpp @@ -102,6 +102,16 @@ namespace { MVT::ValueType VT) { O << (unsigned short)MI->getOperand(OpNo).getImmedValue(); } + void printBranchOperand(const MachineInstr *MI, unsigned OpNo, + MVT::ValueType VT) { + printOp(MI->getOperand(OpNo)); + } + void printPICLabel(const MachineInstr *MI, unsigned OpNo, + MVT::ValueType VT) { + // FIXME: should probably be converted to cout.width and cout.fill + O << "\"L0000" << LabelNumber << "$pb\"\n"; + O << "\"L0000" << LabelNumber << "$pb\":"; + } void printConstantPool(MachineConstantPool *MCP); bool runOnMachineFunction(MachineFunction &F); @@ -293,42 +303,6 @@ void PPC32AsmPrinter::printMachineInstruction(const MachineInstr *MI) { assert(((Desc.TSFlags & PPCII::PPC64) == 0) && "Instruction requires 64 bit support"); - // CALLpcrel and CALLindirect are handled specially here to print only the - // appropriate number of args that the assembler expects. This is because - // may have many arguments appended to record the uses of registers that are - // holding arguments to the called function. - if (Opcode == PPC::COND_BRANCH) { - std::cerr << "Error: untranslated conditional branch psuedo instruction!\n"; - abort(); - } else if (Opcode == PPC::IMPLICIT_DEF) { - --EmittedInsts; // Not an actual machine instruction - O << "; IMPLICIT DEF "; - printOp(MI->getOperand(0)); - O << "\n"; - return; - } else if (Opcode == PPC::CALLpcrel) { - O << TII.getName(Opcode) << " "; - printOp(MI->getOperand(0)); - O << "\n"; - return; - } else if (Opcode == PPC::CALLindirect) { - O << TII.getName(Opcode) << " "; - printImmOp(MI->getOperand(0), ArgType[0]); - O << ", "; - printImmOp(MI->getOperand(1), ArgType[0]); - O << "\n"; - return; - } else if (Opcode == PPC::MovePCtoLR) { - ++EmittedInsts; // Actually two machine instructions - // FIXME: should probably be converted to cout.width and cout.fill - O << "bl \"L0000" << LabelNumber << "$pb\"\n"; - O << "\"L0000" << LabelNumber << "$pb\":\n"; - O << "\tmflr "; - printOp(MI->getOperand(0)); - O << "\n"; - return; - } - O << TII.getName(Opcode) << " "; if (Opcode == PPC::LOADHiAddr) { printOp(MI->getOperand(0)); diff --git a/lib/Target/PowerPC/PPC32ISelSimple.cpp b/lib/Target/PowerPC/PPC32ISelSimple.cpp index 5ba7a5beeb2..2a13bfbd929 100644 --- a/lib/Target/PowerPC/PPC32ISelSimple.cpp +++ b/lib/Target/PowerPC/PPC32ISelSimple.cpp @@ -532,8 +532,8 @@ void ISel::copyGlobalBaseToRegister(MachineBasicBlock *MBB, MachineBasicBlock &FirstMBB = F->front(); MachineBasicBlock::iterator MBBI = FirstMBB.begin(); GlobalBaseReg = makeAnotherReg(Type::IntTy); - BuildMI(FirstMBB, MBBI, PPC::IMPLICIT_DEF, 0, PPC::LR); - BuildMI(FirstMBB, MBBI, PPC::MovePCtoLR, 0, GlobalBaseReg); + BuildMI(FirstMBB, MBBI, PPC::MovePCtoLR, 0, PPC::LR); + BuildMI(FirstMBB, MBBI, PPC::MFLR, 0, GlobalBaseReg).addReg(PPC::LR); GlobalBaseInitialized = true; } // Emit our copy of GlobalBaseReg to the destination register in the diff --git a/lib/Target/PowerPC/PPCAsmPrinter.cpp b/lib/Target/PowerPC/PPCAsmPrinter.cpp index b30977b1a19..cadc88a0b91 100644 --- a/lib/Target/PowerPC/PPCAsmPrinter.cpp +++ b/lib/Target/PowerPC/PPCAsmPrinter.cpp @@ -102,6 +102,16 @@ namespace { MVT::ValueType VT) { O << (unsigned short)MI->getOperand(OpNo).getImmedValue(); } + void printBranchOperand(const MachineInstr *MI, unsigned OpNo, + MVT::ValueType VT) { + printOp(MI->getOperand(OpNo)); + } + void printPICLabel(const MachineInstr *MI, unsigned OpNo, + MVT::ValueType VT) { + // FIXME: should probably be converted to cout.width and cout.fill + O << "\"L0000" << LabelNumber << "$pb\"\n"; + O << "\"L0000" << LabelNumber << "$pb\":"; + } void printConstantPool(MachineConstantPool *MCP); bool runOnMachineFunction(MachineFunction &F); @@ -293,42 +303,6 @@ void PPC32AsmPrinter::printMachineInstruction(const MachineInstr *MI) { assert(((Desc.TSFlags & PPCII::PPC64) == 0) && "Instruction requires 64 bit support"); - // CALLpcrel and CALLindirect are handled specially here to print only the - // appropriate number of args that the assembler expects. This is because - // may have many arguments appended to record the uses of registers that are - // holding arguments to the called function. - if (Opcode == PPC::COND_BRANCH) { - std::cerr << "Error: untranslated conditional branch psuedo instruction!\n"; - abort(); - } else if (Opcode == PPC::IMPLICIT_DEF) { - --EmittedInsts; // Not an actual machine instruction - O << "; IMPLICIT DEF "; - printOp(MI->getOperand(0)); - O << "\n"; - return; - } else if (Opcode == PPC::CALLpcrel) { - O << TII.getName(Opcode) << " "; - printOp(MI->getOperand(0)); - O << "\n"; - return; - } else if (Opcode == PPC::CALLindirect) { - O << TII.getName(Opcode) << " "; - printImmOp(MI->getOperand(0), ArgType[0]); - O << ", "; - printImmOp(MI->getOperand(1), ArgType[0]); - O << "\n"; - return; - } else if (Opcode == PPC::MovePCtoLR) { - ++EmittedInsts; // Actually two machine instructions - // FIXME: should probably be converted to cout.width and cout.fill - O << "bl \"L0000" << LabelNumber << "$pb\"\n"; - O << "\"L0000" << LabelNumber << "$pb\":\n"; - O << "\tmflr "; - printOp(MI->getOperand(0)); - O << "\n"; - return; - } - O << TII.getName(Opcode) << " "; if (Opcode == PPC::LOADHiAddr) { printOp(MI->getOperand(0)); diff --git a/lib/Target/PowerPC/PPCBranchSelector.cpp b/lib/Target/PowerPC/PPCBranchSelector.cpp index 6f7b597da3a..f80237e8989 100644 --- a/lib/Target/PowerPC/PPCBranchSelector.cpp +++ b/lib/Target/PowerPC/PPCBranchSelector.cpp @@ -41,11 +41,6 @@ namespace { // minor pessimization that saves us from having to worry about // keeping the offsets up to date later when we emit long branch glue. return 12; - case PPC::MovePCtoLR: - // MovePCtoLR is actually a combination of a branch-and-link (bl) - // followed by a move from link register to dest reg (mflr) - return 8; - break; case PPC::IMPLICIT_DEF: // no asm emitted return 0; break; diff --git a/lib/Target/PowerPC/PPCInstrFormats.td b/lib/Target/PowerPC/PPCInstrFormats.td index b0fe8da5efc..b5d24fdb8b1 100644 --- a/lib/Target/PowerPC/PPCInstrFormats.td +++ b/lib/Target/PowerPC/PPCInstrFormats.td @@ -60,8 +60,8 @@ class I opcode, bit ppc64, bit vmx> : Instruction { } // 1.7.1 I-Form -class IForm opcode, bit aa, bit lk, bit ppc64, bit vmx> - : I { +class IForm opcode, bit aa, bit lk, bit ppc64, bit vmx, + dag OL, string asmstr> : I<"", opcode, ppc64, vmx> { field bits<24> LI; let ArgCount = 1; @@ -74,6 +74,8 @@ class IForm opcode, bit aa, bit lk, bit ppc64, bit vmx> let Inst{6-29} = LI; let Inst{30} = aa; let Inst{31} = lk; + let OperandList = OL; + let AsmString = asmstr; } // 1.7.2 B-Form @@ -311,8 +313,8 @@ class XForm_11 opcode, bits<10> xo, bit rc, bit ppc64, bit vmx, let B = 0; } -class XForm_16 opcode, bits<10> xo, bit ppc64, bit vmx> - : I { +class XForm_16 opcode, bits<10> xo, bit ppc64, bit vmx, + dag OL, string asmstr> : I<"", opcode, ppc64, vmx> { field bits<3> BF; field bits<1> L; field bits<5> RA; @@ -332,10 +334,17 @@ class XForm_16 opcode, bits<10> xo, bit ppc64, bit vmx> let Inst{16-20} = RB; let Inst{21-30} = xo; let Inst{31} = 0; + let OperandList = OL; + let AsmString = asmstr; } -class XForm_16_ext opcode, bits<10> xo, bit ppc64, bit vmx> - : XForm_16 { +class XForm_16_ext opcode, bits<10> xo, bit ppc64, bit vmx, + dag OL, string asmstr> + : XForm_16 { + let ArgCount = 3; + let Arg1Type = Gpr.Value; + let Arg2Type = Gpr.Value; + let Arg3Type = 0; let L = ppc64; } @@ -395,8 +404,8 @@ class XLForm_1 opcode, bits<10> xo, bit ppc64, bit vmx, let Arg2Type = Imm5.Value; } -class XLForm_2 opcode, bits<10> xo, bit lk, bit ppc64, - bit vmx> : I { +class XLForm_2 opcode, bits<10> xo, bit lk, bit ppc64, bit vmx, + dag OL, string asmstr> : I<"", opcode, ppc64, vmx> { field bits<5> BO; field bits<5> BI; field bits<2> BH; @@ -414,11 +423,14 @@ class XLForm_2 opcode, bits<10> xo, bit lk, bit ppc64, let Inst{19-20} = BH; let Inst{21-30} = xo; let Inst{31} = lk; + let OperandList = OL; + let AsmString = asmstr; } -class XLForm_2_ext opcode, bits<10> xo, bits<5> bo, - bits<5> bi, bit lk, bit ppc64, bit vmx> - : XLForm_2 { +class XLForm_2_ext opcode, bits<10> xo, bits<5> bo, + bits<5> bi, bit lk, bit ppc64, bit vmx, + dag OL, string asmstr> + : XLForm_2 { let ArgCount = 0; let Arg0Type = 0; let Arg1Type = 0; @@ -634,17 +646,18 @@ class MDForm_1 opcode, bits<3> xo, bit rc, bit ppc64, bit vmx, //===----------------------------------------------------------------------===// -class Pseudo : I { - let Name = name; - let ArgCount = 0; - let PPC64 = 0; - let VMX = 0; +class Pseudo : I<"", 0, 0, 0> { + let ArgCount = 0; + let PPC64 = 0; + let VMX = 0; - let Arg0Type = Pseudo.Value; - let Arg1Type = Pseudo.Value; - let Arg2Type = Pseudo.Value; - let Arg3Type = Pseudo.Value; - let Arg4Type = 0; + let Arg0Type = Pseudo.Value; + let Arg1Type = Pseudo.Value; + let Arg2Type = Pseudo.Value; + let Arg3Type = Pseudo.Value; + let Arg4Type = 0; - let Inst{31-0} = 0; + let Inst{31-0} = 0; + let OperandList = OL; + let AsmString = asmstr; } diff --git a/lib/Target/PowerPC/PPCInstrInfo.td b/lib/Target/PowerPC/PPCInstrInfo.td index d692745c98b..3bae51eda7a 100644 --- a/lib/Target/PowerPC/PPCInstrInfo.td +++ b/lib/Target/PowerPC/PPCInstrInfo.td @@ -15,7 +15,7 @@ include "PowerPCInstrFormats.td" let isTerminator = 1, isReturn = 1 in - def BLR : XLForm_2_ext<"blr", 19, 16, 20, 31, 1, 0, 0>; + def BLR : XLForm_2_ext<19, 16, 20, 31, 1, 0, 0, (ops), "blr">; def u5imm : Operand { let PrintMethod = "printU5ImmOperand"; @@ -26,18 +26,23 @@ def u6imm : Operand { def u16imm : Operand { let PrintMethod = "printU16ImmOperand"; } +def target : Operand { + let PrintMethod = "printBranchOperand"; +} +def piclabel: Operand { + let PrintMethod = "printPICLabel"; +} // Pseudo-instructions: -def PHI : Pseudo<"PHI">; -def ADJCALLSTACKDOWN : Pseudo<"ADJCALLSTACKDOWN">; -def ADJCALLSTACKUP : Pseudo<"ADJCALLSTACKUP">; -let Defs = [LR] in - def MovePCtoLR : Pseudo<"MovePCtoLR">; -def IMPLICIT_DEF : Pseudo<"IMPLICIT_DEF">; +def PHI : Pseudo<(ops), "; PHI">; +def ADJCALLSTACKDOWN : Pseudo<(ops), "; ADJCALLSTACKDOWN">; +def ADJCALLSTACKUP : Pseudo<(ops), "; ADJCALLSTACKUP">; +def IMPLICIT_DEF : Pseudo<(ops), "; IMPLICIT_DEF">; +def MovePCtoLR : Pseudo<(ops piclabel:$label), "bl $label">; let isBranch = 1, isTerminator = 1 in { - def COND_BRANCH : Pseudo<"COND_BRANCH">; - def B : IForm<"b", 18, 0, 0, 0, 0>; + def COND_BRANCH : Pseudo<(ops), "; COND_BRANCH">; + def B : IForm<18, 0, 0, 0, 0, (ops target:$func), "b $func">; // FIXME: 4*CR# needs to be added to the BI field! // This will only work for CR0 as it stands now def BLT : BForm_ext<"blt", 16, 0, 0, 12, 0, 0, 0>; @@ -55,8 +60,8 @@ let isBranch = 1, isTerminator = 1, isCall = 1, LR,XER,CTR, CR0,CR1,CR5,CR6,CR7] in { // Convenient aliases for call instructions - def CALLpcrel : IForm<"bl", 18, 0, 1, 0, 0>; - def CALLindirect : XLForm_2_ext<"bctrl", 19, 528, 20, 31, 1, 0, 0>; + def CALLpcrel : IForm<18, 0, 1, 0, 0, (ops target:$func), "bl $func">; + def CALLindirect : XLForm_2_ext<19, 528, 20, 31, 1, 0, 0, (ops), "bctrl">; } def LA : DForm_2<"la", 14, 0, 0>; @@ -96,13 +101,6 @@ def LD : DSForm_2<"ld", 58, 0, 1, 0>; def STD : DSForm_2<"std", 62, 0, 1, 0>; def STDU : DSForm_2<"stdu", 62, 1, 1, 0>; -def CMP : XForm_16<"cmp", 31, 0, 0, 0>; -def CMPL : XForm_16<"cmpl", 31, 32, 0, 0>; -def CMPW : XForm_16_ext<"cmpw", 31, 0, 0, 0>; -def CMPD : XForm_16_ext<"cmpd", 31, 0, 1, 0>; -def CMPLW : XForm_16_ext<"cmplw", 31, 32, 0, 0>; -def CMPLD : XForm_16_ext<"cmpld", 31, 32, 1, 0>; - // D-Form instructions. Most instructions that perform an operation on a // register and an immediate are of this type. // @@ -200,6 +198,24 @@ def EXTSH : XForm_11<31, 922, 0, 0, 0, (ops GPRC:$rA, GPRC:$rS), "extsh $rA, $rS">; def EXTSW : XForm_11<31, 986, 0, 1, 0, (ops GPRC:$rA, GPRC:$rS), "extsw $rA, $rS">; +def CMP : XForm_16<31, 0, 0, 0, + (ops CRRC:$crD, i1imm:$long, GPRC:$rA, GPRC:$rB), + "cmp $crD, $long, $rA, $rB">; +def CMPL : XForm_16<31, 32, 0, 0, + (ops CRRC:$crD, i1imm:$long, GPRC:$rA, GPRC:$rB), + "cmpl $crD, $long, $rA, $rB">; +def CMPW : XForm_16_ext<31, 0, 0, 0, + (ops CRRC:$crD, GPRC:$rA, GPRC:$rB), + "cmpw $crD, $rA, $rB">; +def CMPD : XForm_16_ext<31, 0, 1, 0, + (ops CRRC:$crD, GPRC:$rA, GPRC:$rB), + "cmpd $crD, $rA, $rB">; +def CMPLW : XForm_16_ext<31, 32, 0, 0, + (ops CRRC:$crD, GPRC:$rA, GPRC:$rB), + "cmplw $crD, $rA, $rB">; +def CMPLD : XForm_16_ext<31, 32, 1, 0, + (ops CRRC:$crD, GPRC:$rA, GPRC:$rB), + "cmpld $crD, $rA, $rB">; def FCMPU : XForm_17<63, 0, 0, 0, (ops CRRC:$crD, FPRC:$fA, FPRC:$fB), "fcmpu $crD, $fA, $fB">; def LFSX : XForm_25<31, 535, 0, 0, (ops FPRC:$dst, GPRC:$base, GPRC:$index),