From bdfbb74d34dafba3c5638fdddd561043823ebdd2 Mon Sep 17 00:00:00 2001 From: Bruno Cardoso Lopes Date: Sat, 21 Mar 2009 00:05:07 +0000 Subject: [PATCH] Removed AFGR32 register class Handle odd registers allocation in FGR32. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@67422 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/Mips/MipsISelLowering.cpp | 29 ++----- lib/Target/Mips/MipsInstrFPU.td | 124 ++++++++------------------- lib/Target/Mips/MipsInstrInfo.cpp | 52 ++++------- lib/Target/Mips/MipsRegisterInfo.cpp | 10 ++- lib/Target/Mips/MipsRegisterInfo.td | 71 ++++++++------- 5 files changed, 110 insertions(+), 176 deletions(-) diff --git a/lib/Target/Mips/MipsISelLowering.cpp b/lib/Target/Mips/MipsISelLowering.cpp index bec6cf7fa26..e50c0421543 100644 --- a/lib/Target/Mips/MipsISelLowering.cpp +++ b/lib/Target/Mips/MipsISelLowering.cpp @@ -66,14 +66,12 @@ MipsTargetLowering(MipsTargetMachine &TM): TargetLowering(TM) // Set up the register classes addRegisterClass(MVT::i32, Mips::CPURegsRegisterClass); + addRegisterClass(MVT::f32, Mips::FGR32RegisterClass); // When dealing with single precision only, use libcalls - if (!Subtarget->isSingleFloat()) { - addRegisterClass(MVT::f32, Mips::AFGR32RegisterClass); + if (!Subtarget->isSingleFloat()) if (!Subtarget->isFP64bit()) addRegisterClass(MVT::f64, Mips::AFGR64RegisterClass); - } else - addRegisterClass(MVT::f32, Mips::FGR32RegisterClass); // Legal fp constants addLegalFPImmediate(APFloat(+0.0f)); @@ -284,13 +282,11 @@ MipsTargetLowering::EmitInstrWithCustomInserter(MachineInstr *MI, switch (MI->getOpcode()) { default: assert(false && "Unexpected instr type to insert"); case Mips::Select_FCC: - case Mips::Select_FCC_SO32: - case Mips::Select_FCC_AS32: + case Mips::Select_FCC_S32: case Mips::Select_FCC_D32: isFPCmp = true; // FALL THROUGH case Mips::Select_CC: - case Mips::Select_CC_SO32: - case Mips::Select_CC_AS32: + case Mips::Select_CC_S32: case Mips::Select_CC_D32: { // To "insert" a SELECT_CC instruction, we actually have to insert the // diamond control-flow pattern. The incoming instruction knows the @@ -935,12 +931,9 @@ LowerFORMAL_ARGUMENTS(SDValue Op, SelectionDAG &DAG) if (RegVT == MVT::i32) RC = Mips::CPURegsRegisterClass; - else if (RegVT == MVT::f32) { - if (Subtarget->isSingleFloat()) - RC = Mips::FGR32RegisterClass; - else - RC = Mips::AFGR32RegisterClass; - } else if (RegVT == MVT::f64) { + else if (RegVT == MVT::f32) + RC = Mips::FGR32RegisterClass; + else if (RegVT == MVT::f64) { if (!Subtarget->isSingleFloat()) RC = Mips::AFGR64RegisterClass; } else @@ -1162,12 +1155,8 @@ getRegForInlineAsmConstraint(const std::string &Constraint, MVT VT) const case 'r': return std::make_pair(0U, Mips::CPURegsRegisterClass); case 'f': - if (VT == MVT::f32) { - if (Subtarget->isSingleFloat()) - return std::make_pair(0U, Mips::FGR32RegisterClass); - else - return std::make_pair(0U, Mips::AFGR32RegisterClass); - } + if (VT == MVT::f32) + return std::make_pair(0U, Mips::FGR32RegisterClass); if (VT == MVT::f64) if ((!Subtarget->isSingleFloat()) && (!Subtarget->isFP64bit())) return std::make_pair(0U, Mips::AFGR64RegisterClass); diff --git a/lib/Target/Mips/MipsInstrFPU.td b/lib/Target/Mips/MipsInstrFPU.td index 8e05ac50a9a..b734a7ccf9b 100644 --- a/lib/Target/Mips/MipsInstrFPU.td +++ b/lib/Target/Mips/MipsInstrFPU.td @@ -44,36 +44,27 @@ let PrintMethod = "printFCCOperand" in //===----------------------------------------------------------------------===// def In32BitMode : Predicate<"!Subtarget.isFP64bit()">; -def In64BitMode : Predicate<"Subtarget.isFP64bit()">; def IsSingleFloat : Predicate<"Subtarget.isSingleFloat()">; def IsNotSingleFloat : Predicate<"!Subtarget.isSingleFloat()">; //===----------------------------------------------------------------------===// // Instruction Class Templates // -// A set of multiclasses is used to address this in one shot. -// SO32 - single precision only, uses all 32 32-bit fp registers -// require FGR32 Register Class and IsSingleFloat -// AS32 - 16 even fp registers are used for single precision -// require AFGR32 Register Class and In32BitMode -// S64 - 32 64 bit registers are used to hold 32-bit single precision values. -// require FGR64 Register Class and In64BitMode -// D32 - 16 even fp registers are used for double precision -// require AFGR64 Register Class and In32BitMode -// D64 - 32 64 bit registers are used to hold 64-bit double precision values. -// require FGR64 Register Class and In64BitMode +// A set of multiclasses is used to address the register usage. // -// Only SO32, AS32 and D32 are supported right now. +// S32 - single precision in 16 32bit even fp registers +// single precision in 32 32bit fp registers in SingleOnly mode +// S64 - single precision in 32 64bit fp registers (In64BitMode) +// D32 - double precision in 16 32bit even fp registers +// D64 - double precision in 32 64bit fp registers (In64BitMode) // +// Only S32 and D32 are supported right now. //===----------------------------------------------------------------------===// multiclass FFR1_1 funct, string asmstr> { - def _SO32 : FFR<0x11, funct, 0x0, (outs FGR32:$fd), (ins FGR32:$fs), - !strconcat(asmstr, ".s $fd, $fs"), []>, Requires<[IsSingleFloat]>; - - def _AS32 : FFR<0x11, funct, 0x0, (outs AFGR32:$fd), (ins AFGR32:$fs), - !strconcat(asmstr, ".s $fd, $fs"), []>, Requires<[In32BitMode]>; + def _S32 : FFR<0x11, funct, 0x0, (outs FGR32:$fd), (ins FGR32:$fs), + !strconcat(asmstr, ".s $fd, $fs"), []>; def _D32 : FFR<0x11, funct, 0x1, (outs AFGR64:$fd), (ins AFGR64:$fs), !strconcat(asmstr, ".d $fd, $fs"), []>, Requires<[In32BitMode]>; @@ -81,13 +72,9 @@ multiclass FFR1_1 funct, string asmstr> multiclass FFR1_2 funct, string asmstr, SDNode FOp> { - def _SO32 : FFR<0x11, funct, 0x0, (outs FGR32:$fd), (ins FGR32:$fs), - !strconcat(asmstr, ".s $fd, $fs"), - [(set FGR32:$fd, (FOp FGR32:$fs))]>, Requires<[IsSingleFloat]>; - - def _AS32 : FFR<0x11, funct, 0x0, (outs AFGR32:$fd), (ins AFGR32:$fs), + def _S32 : FFR<0x11, funct, 0x0, (outs FGR32:$fd), (ins FGR32:$fs), !strconcat(asmstr, ".s $fd, $fs"), - [(set AFGR32:$fd, (FOp AFGR32:$fs))]>, Requires<[In32BitMode]>; + [(set FGR32:$fd, (FOp FGR32:$fs))]>; def _D32 : FFR<0x11, funct, 0x1, (outs AFGR64:$fd), (ins AFGR64:$fs), !strconcat(asmstr, ".d $fd, $fs"), @@ -101,19 +88,12 @@ class FFR1_3 funct, bits<5> fmt, RegisterClass RcSrc, multiclass FFR1_4 funct, string asmstr, SDNode FOp> { - def _SO32 : FFR<0x11, funct, 0x0, (outs FGR32:$fd), + def _S32 : FFR<0x11, funct, 0x0, (outs FGR32:$fd), (ins FGR32:$fs, FGR32:$ft), !strconcat(asmstr, ".s $fd, $fs, $ft"), - [(set FGR32:$fd, (FOp FGR32:$fs, FGR32:$ft))]>, - Requires<[IsSingleFloat]>; - - def _AS32 : FFR<0x11, funct, 0x0, (outs AFGR32:$fd), - (ins AFGR32:$fs, AFGR32:$ft), - !strconcat(asmstr, ".s $fd, $fs, $ft"), - [(set AFGR32:$fd, (FOp AFGR32:$fs, AFGR32:$ft))]>, - Requires<[In32BitMode]>; + [(set FGR32:$fd, (FOp FGR32:$fs, FGR32:$ft))]>; - def _D32 : FFR<0x11, funct, 0x1, (outs AFGR64:$fd), + def _D32 : FFR<0x11, funct, 0x1, (outs AFGR64:$fd), (ins AFGR64:$fs, AFGR64:$ft), !strconcat(asmstr, ".d $fd, $fs, $ft"), [(set AFGR64:$fd, (FOp AFGR64:$fs, AFGR64:$ft))]>, @@ -136,25 +116,28 @@ let ft = 0 in { defm FNEG : FFR1_2<0b000111, "neg", fneg>; defm FSQRT : FFR1_2<0b000100, "sqrt", fsqrt>; + /// Convert to Single Precison + def CVTS_W32 : FFR1_3<0b100000, 0x2, FGR32, FGR32, "cvt.s.w">; + let Predicates = [IsNotSingleFloat] in { /// Ceil to long signed integer - def CEIL_LS : FFR1_3<0b001010, 0x0, AFGR32, AFGR32, "ceil.l">; + def CEIL_LS : FFR1_3<0b001010, 0x0, FGR32, FGR32, "ceil.l">; def CEIL_LD : FFR1_3<0b001010, 0x1, AFGR64, AFGR64, "ceil.l">; /// Round to long signed integer - def ROUND_LS : FFR1_3<0b001000, 0x0, AFGR32, AFGR32, "round.l">; + def ROUND_LS : FFR1_3<0b001000, 0x0, FGR32, FGR32, "round.l">; def ROUND_LD : FFR1_3<0b001000, 0x1, AFGR64, AFGR64, "round.l">; /// Floor to long signed integer - def FLOOR_LS : FFR1_3<0b001011, 0x0, AFGR32, AFGR32, "floor.l">; + def FLOOR_LS : FFR1_3<0b001011, 0x0, FGR32, FGR32, "floor.l">; def FLOOR_LD : FFR1_3<0b001011, 0x1, AFGR64, AFGR64, "floor.l">; /// Trunc to long signed integer - def TRUNC_LS : FFR1_3<0b001001, 0x0, AFGR32, AFGR32, "trunc.l">; + def TRUNC_LS : FFR1_3<0b001001, 0x0, FGR32, FGR32, "trunc.l">; def TRUNC_LD : FFR1_3<0b001001, 0x1, AFGR64, AFGR64, "trunc.l">; /// Convert to long signed integer - def CVTL_S : FFR1_3<0b100101, 0x0, AFGR32, AFGR32, "cvt.l">; + def CVTL_S : FFR1_3<0b100101, 0x0, FGR32, FGR32, "cvt.l">; def CVTL_D : FFR1_3<0b100101, 0x1, AFGR64, AFGR64, "cvt.l">; /// Convert to Double Precison @@ -166,10 +149,6 @@ let ft = 0 in { def CVTS_D32 : FFR1_3<0b100000, 0x1, FGR32, AFGR64, "cvt.s.d">; def CVTS_L32 : FFR1_3<0b100000, 0x3, FGR32, AFGR64, "cvt.s.l">; } - - /// Convert to Single Precison - def CVTS_W32 : FFR1_3<0b100000, 0x2, FGR32, FGR32, "cvt.s.w">, - Requires<[IsSingleFloat]>; } // The odd-numbered registers are only referenced when doing loads, @@ -184,23 +163,11 @@ let fd = 0 in { ///def CTC1 : FFR<0x11, 0x0, 0x6, (outs CPURegs:$rt), (ins FGR32:$fs), /// "ctc1 $rt, $fs", []>; /// - ///def CFC1A : FFR<0x11, 0x0, 0x2, (outs CPURegs:$rt), (ins AFGR32:$fs), - /// "cfc1 $rt, $fs", []>; - - ///def CTC1A : FFR<0x11, 0x0, 0x6, (outs CPURegs:$rt), (ins AFGR32:$fs), - /// "ctc1 $rt, $fs", []>; - def MFC1 : FFR<0x11, 0x00, 0x00, (outs CPURegs:$rt), (ins FGR32:$fs), "mfc1 $rt, $fs", []>; def MTC1 : FFR<0x11, 0x00, 0x04, (outs FGR32:$fs), (ins CPURegs:$rt), "mtc1 $rt, $fs", []>; - - def MFC1A : FFR<0x11, 0x00, 0x00, (outs CPURegs:$rt), (ins AFGR32:$fs), - "mfc1 $rt, $fs", []>; - - def MTC1A : FFR<0x11, 0x00, 0x04, (outs AFGR32:$fs), (ins CPURegs:$rt), - "mtc1 $rt, $fs", []>; } /// Floating Point Memory Instructions @@ -218,11 +185,6 @@ def LWC1 : FFI<0b110001, (outs FGR32:$ft), (ins mem:$addr), "lwc1 $ft, $addr", def SWC1 : FFI<0b111001, (outs), (ins FGR32:$ft, mem:$addr), "swc1 $ft, $addr", [(store FGR32:$ft, addr:$addr)]>; -def LWC1A : FFI<0b110001, (outs AFGR32:$ft), (ins mem:$addr), "lwc1 $ft, $addr", - [(set AFGR32:$ft, (load addr:$addr))]>; -def SWC1A : FFI<0b111001, (outs), (ins AFGR32:$ft, mem:$addr), - "swc1 $ft, $addr", [(store AFGR32:$ft, addr:$addr)]>; - /// Floating-point Aritmetic defm FADD : FFR1_4<0x10, "add", fadd>; defm FDIV : FFR1_4<0x03, "div", fdiv>; @@ -274,14 +236,10 @@ def MIPS_FCOND_NGT : PatLeaf<(i32 15)>; /// Floating Point Compare let hasDelaySlot = 1, Defs=[FCR31] in { - def FCMP_SO32 : FCC<0x0, (outs), (ins FGR32:$fs, FGR32:$ft, condcode:$cc), + def FCMP_S32 : FCC<0x0, (outs), (ins FGR32:$fs, FGR32:$ft, condcode:$cc), "c.$cc.s $fs, $ft", [(MipsFPCmp FGR32:$fs, FGR32:$ft, imm:$cc), - (implicit FCR31)]>, Requires<[IsSingleFloat]>; + (implicit FCR31)]>; - def FCMP_AS32 : FCC<0x0, (outs), (ins AFGR32:$fs, AFGR32:$ft, condcode:$cc), - "c.$cc.s $fs, $ft", [(MipsFPCmp AFGR32:$fs, AFGR32:$ft, imm:$cc), - (implicit FCR31)]>, Requires<[In32BitMode]>; - def FCMP_D32 : FCC<0x1, (outs), (ins AFGR64:$fs, AFGR64:$ft, condcode:$cc), "c.$cc.d $fs, $ft", [(MipsFPCmp AFGR64:$fs, AFGR64:$ft, imm:$cc), (implicit FCR31)]>, Requires<[In32BitMode]>; @@ -302,24 +260,17 @@ let usesCustomDAGSchedInserter = 1, Uses=[FCR31] in { } // The values to be selected are fp but the condition test is with integers. -def Select_CC_SO32 : PseudoSelCC, - Requires<[IsSingleFloat]>; -def Select_CC_AS32 : PseudoSelCC, - Requires<[In32BitMode]>; -def Select_CC_D32 : PseudoSelCC, - Requires<[In32BitMode]>; +def Select_CC_S32 : PseudoSelCC; +def Select_CC_D32 : PseudoSelCC, + Requires<[In32BitMode]>; // The values to be selected are int but the condition test is done with fp. -def Select_FCC : PseudoFPSelCC; +def Select_FCC : PseudoFPSelCC; // The values to be selected and the condition test is done with fp. -def Select_FCC_SO32 : PseudoFPSelCC, - Requires<[IsSingleFloat]>; -def Select_FCC_AS32 : PseudoFPSelCC, - Requires<[In32BitMode]>; -def Select_FCC_D32 : PseudoFPSelCC, - Requires<[In32BitMode]>; - +def Select_FCC_S32 : PseudoFPSelCC; +def Select_FCC_D32 : PseudoFPSelCC, + Requires<[In32BitMode]>; //===----------------------------------------------------------------------===// // Floating Point Patterns @@ -328,19 +279,12 @@ def fpimm0 : PatLeaf<(fpimm), [{ return N->isExactlyValue(+0.0); }]>; -def : Pat<(f32 fpimm0), (MTC1 ZERO)>, Requires<[IsSingleFloat]>; -def : Pat<(f32 fpimm0), (MTC1A ZERO)>, Requires<[In32BitMode]>; +def : Pat<(f32 fpimm0), (MTC1 ZERO)>; def : Pat<(f32 (sint_to_fp CPURegs:$src)), (CVTS_W32 (MTC1 CPURegs:$src))>; def : Pat<(f64 (sint_to_fp CPURegs:$src)), (CVTD_W32 (MTC1 CPURegs:$src))>; -def : Pat<(i32 (fp_to_sint FGR32:$src)), (MFC1 (TRUNC_W_SO32 FGR32:$src))>; -def : Pat<(i32 (fp_to_sint AFGR32:$src)), (MFC1A (TRUNC_W_AS32 AFGR32:$src))>; +def : Pat<(i32 (fp_to_sint FGR32:$src)), (MFC1 (TRUNC_W_S32 FGR32:$src))>; def : Pat<(i32 (bitconvert FGR32:$src)), (MFC1 FGR32:$src)>; -def : Pat<(i32 (bitconvert AFGR32:$src)), (MFC1A AFGR32:$src)>; - -def : Pat<(f32 (bitconvert CPURegs:$src)), (MTC1 CPURegs:$src)>, - Requires<[IsSingleFloat]>; -def : Pat<(f32 (bitconvert CPURegs:$src)), (MTC1A CPURegs:$src)>, - Requires<[In32BitMode]>; +def : Pat<(f32 (bitconvert CPURegs:$src)), (MTC1 CPURegs:$src)>; diff --git a/lib/Target/Mips/MipsInstrInfo.cpp b/lib/Target/Mips/MipsInstrInfo.cpp index f2232b1c697..a672d3ef7e1 100644 --- a/lib/Target/Mips/MipsInstrInfo.cpp +++ b/lib/Target/Mips/MipsInstrInfo.cpp @@ -35,8 +35,8 @@ isMoveInstr(const MachineInstr &MI, unsigned &SrcReg, unsigned &DstReg, { SrcSubIdx = DstSubIdx = 0; // No sub-registers. - // addu $dst, $src, $zero || addu $dst, $zero, $src - // or $dst, $src, $zero || or $dst, $zero, $src + // addu $dst, $src, $zero || addu $dst, $zero, $src + // or $dst, $src, $zero || or $dst, $zero, $src if ((MI.getOpcode() == Mips::ADDu) || (MI.getOpcode() == Mips::OR)) { if (MI.getOperand(1).getReg() == Mips::ZERO) { DstReg = MI.getOperand(0).getReg(); @@ -52,16 +52,16 @@ isMoveInstr(const MachineInstr &MI, unsigned &SrcReg, unsigned &DstReg, // mov $fpDst, $fpSrc // mfc $gpDst, $fpSrc // mtc $fpDst, $gpSrc - if (MI.getOpcode() == Mips::FMOV_SO32 || MI.getOpcode() == Mips::FMOV_AS32 || - MI.getOpcode() == Mips::FMOV_D32 || MI.getOpcode() == Mips::MFC1A || - MI.getOpcode() == Mips::MFC1 || MI.getOpcode() == Mips::MTC1A || + if (MI.getOpcode() == Mips::FMOV_S32 || + MI.getOpcode() == Mips::FMOV_D32 || + MI.getOpcode() == Mips::MFC1 || MI.getOpcode() == Mips::MTC1 ) { DstReg = MI.getOperand(0).getReg(); SrcReg = MI.getOperand(1).getReg(); return true; } - // addiu $dst, $src, 0 + // addiu $dst, $src, 0 if (MI.getOpcode() == Mips::ADDiu) { if ((MI.getOperand(1).isReg()) && (isZeroImm(MI.getOperand(2)))) { DstReg = MI.getOperand(0).getReg(); @@ -81,7 +81,7 @@ unsigned MipsInstrInfo:: isLoadFromStackSlot(const MachineInstr *MI, int &FrameIndex) const { if ((MI->getOpcode() == Mips::LW) || (MI->getOpcode() == Mips::LWC1) || - (MI->getOpcode() == Mips::LWC1A) || (MI->getOpcode() == Mips::LDC1)) { + (MI->getOpcode() == Mips::LDC1)) { if ((MI->getOperand(2).isFI()) && // is a stack slot (MI->getOperand(1).isImm()) && // the imm is zero (isZeroImm(MI->getOperand(1)))) { @@ -102,7 +102,7 @@ unsigned MipsInstrInfo:: isStoreToStackSlot(const MachineInstr *MI, int &FrameIndex) const { if ((MI->getOpcode() == Mips::SW) || (MI->getOpcode() == Mips::SWC1) || - (MI->getOpcode() == Mips::SWC1A) || (MI->getOpcode() == Mips::SDC1)) { + (MI->getOpcode() == Mips::SDC1)) { if ((MI->getOperand(2).isFI()) && // is a stack slot (MI->getOperand(1).isImm()) && // the imm is zero (isZeroImm(MI->getOperand(1)))) { @@ -132,27 +132,23 @@ copyRegToReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, if (I != MBB.end()) DL = I->getDebugLoc(); if (DestRC != SrcRC) { + // Moves between coprocessors and cpu if ((DestRC == Mips::CPURegsRegisterClass) && (SrcRC == Mips::FGR32RegisterClass)) BuildMI(MBB, I, DL, get(Mips::MFC1), DestReg).addReg(SrcReg); - else if ((DestRC == Mips::CPURegsRegisterClass) && - (SrcRC == Mips::AFGR32RegisterClass)) - BuildMI(MBB, I, DL, get(Mips::MFC1A), DestReg).addReg(SrcReg); else if ((DestRC == Mips::FGR32RegisterClass) && (SrcRC == Mips::CPURegsRegisterClass)) BuildMI(MBB, I, DL, get(Mips::MTC1), DestReg).addReg(SrcReg); - else if ((DestRC == Mips::AFGR32RegisterClass) && - (SrcRC == Mips::CPURegsRegisterClass)) - BuildMI(MBB, I, DL, get(Mips::MTC1A), DestReg).addReg(SrcReg); - else if ((DestRC == Mips::AFGR32RegisterClass) && - (SrcRC == Mips::CPURegsRegisterClass)) - BuildMI(MBB, I, DL, get(Mips::MTC1A), DestReg).addReg(SrcReg); + + // Condition registers else if ((SrcRC == Mips::CCRRegisterClass) && (SrcReg == Mips::FCR31)) return true; // This register is used implicitly, no copy needed. else if ((DestRC == Mips::CCRRegisterClass) && (DestReg == Mips::FCR31)) return true; // This register is used implicitly, no copy needed. + + // Move from/to Hi/Lo registers else if ((DestRC == Mips::HILORegisterClass) && (SrcRC == Mips::CPURegsRegisterClass)) { unsigned Opc = (DestReg == Mips::HI) ? Mips::MTHI : Mips::MTLO; @@ -161,9 +157,10 @@ copyRegToReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, (DestRC == Mips::CPURegsRegisterClass)) { unsigned Opc = (SrcReg == Mips::HI) ? Mips::MFHI : Mips::MFLO; BuildMI(MBB, I, DL, get(Opc), DestReg); + + // Can't copy this register } else - // DestRC != SrcRC, Can't copy this register - return false; + return false; return true; } @@ -172,9 +169,7 @@ copyRegToReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, BuildMI(MBB, I, DL, get(Mips::ADDu), DestReg).addReg(Mips::ZERO) .addReg(SrcReg); else if (DestRC == Mips::FGR32RegisterClass) - BuildMI(MBB, I, DL, get(Mips::FMOV_SO32), DestReg).addReg(SrcReg); - else if (DestRC == Mips::AFGR32RegisterClass) - BuildMI(MBB, I, DL, get(Mips::FMOV_AS32), DestReg).addReg(SrcReg); + BuildMI(MBB, I, DL, get(Mips::FMOV_S32), DestReg).addReg(SrcReg); else if (DestRC == Mips::AFGR64RegisterClass) BuildMI(MBB, I, DL, get(Mips::FMOV_D32), DestReg).addReg(SrcReg); else @@ -198,8 +193,6 @@ storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, Opc = Mips::SW; else if (RC == Mips::FGR32RegisterClass) Opc = Mips::SWC1; - else if (RC == Mips::AFGR32RegisterClass) - Opc = Mips::SWC1A; else if (RC == Mips::AFGR64RegisterClass) Opc = Mips::SDC1; else @@ -218,8 +211,6 @@ void MipsInstrInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, Opc = Mips::SW; else if (RC == Mips::FGR32RegisterClass) Opc = Mips::SWC1; - else if (RC == Mips::AFGR32RegisterClass) - Opc = Mips::SWC1A; else if (RC == Mips::AFGR64RegisterClass) Opc = Mips::SDC1; else @@ -244,8 +235,6 @@ loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, Opc = Mips::LW; else if (RC == Mips::FGR32RegisterClass) Opc = Mips::LWC1; - else if (RC == Mips::AFGR32RegisterClass) - Opc = Mips::LWC1A; else if (RC == Mips::AFGR64RegisterClass) Opc = Mips::LDC1; else @@ -265,8 +254,6 @@ void MipsInstrInfo::loadRegFromAddr(MachineFunction &MF, unsigned DestReg, Opc = Mips::LW; else if (RC == Mips::FGR32RegisterClass) Opc = Mips::LWC1; - else if (RC == Mips::AFGR32RegisterClass) - Opc = Mips::LWC1A; else if (RC == Mips::AFGR64RegisterClass) Opc = Mips::LDC1; else @@ -310,8 +297,7 @@ foldMemoryOperandImpl(MachineFunction &MF, } } break; - case Mips::FMOV_SO32: - case Mips::FMOV_AS32: + case Mips::FMOV_S32: case Mips::FMOV_D32: if ((MI->getOperand(0).isReg()) && (MI->getOperand(1).isReg())) { @@ -321,8 +307,6 @@ foldMemoryOperandImpl(MachineFunction &MF, if (RC == Mips::FGR32RegisterClass) { LoadOpc = Mips::LWC1; StoreOpc = Mips::SWC1; - } else if (RC == Mips::AFGR32RegisterClass) { - LoadOpc = Mips::LWC1A; StoreOpc = Mips::SWC1A; } else if (RC == Mips::AFGR64RegisterClass) { LoadOpc = Mips::LDC1; StoreOpc = Mips::SDC1; } else diff --git a/lib/Target/Mips/MipsRegisterInfo.cpp b/lib/Target/Mips/MipsRegisterInfo.cpp index a33e2c2c563..115bb929719 100644 --- a/lib/Target/Mips/MipsRegisterInfo.cpp +++ b/lib/Target/Mips/MipsRegisterInfo.cpp @@ -133,8 +133,8 @@ MipsRegisterInfo::getCalleeSavedRegClasses(const MachineFunction *MF) const &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, &Mips::CPURegsRegClass, - &Mips::AFGR32RegClass, &Mips::AFGR32RegClass, &Mips::AFGR32RegClass, - &Mips::AFGR32RegClass, &Mips::AFGR32RegClass, &Mips::AFGR32RegClass, + &Mips::FGR32RegClass, &Mips::FGR32RegClass, &Mips::FGR32RegClass, + &Mips::FGR32RegClass, &Mips::FGR32RegClass, &Mips::FGR32RegClass, &Mips::AFGR64RegClass, &Mips::AFGR64RegClass, &Mips::AFGR64RegClass, &Mips::AFGR64RegClass, &Mips::AFGR64RegClass, &Mips::AFGR64RegClass, 0 }; @@ -157,6 +157,12 @@ getReservedRegs(const MachineFunction &MF) const Reserved.set(Mips::SP); Reserved.set(Mips::FP); Reserved.set(Mips::RA); + + // SRV4 requires that odd register can't be used. + if (!Subtarget.isSingleFloat()) + for (unsigned FReg=(Mips::F0)+1; FReg < Mips::F30; FReg+=2) + Reserved.set(FReg); + return Reserved; } diff --git a/lib/Target/Mips/MipsRegisterInfo.td b/lib/Target/Mips/MipsRegisterInfo.td index 10956aa7413..aa942696572 100644 --- a/lib/Target/Mips/MipsRegisterInfo.td +++ b/lib/Target/Mips/MipsRegisterInfo.td @@ -160,13 +160,13 @@ def CPURegs : RegisterClass<"Mips", [i32], 32, }]; } -// * 64bit fp: -// - FGR64 = 32 64-bit registers (default mode) -// - AFGR32/AFGR64 = 16 even 32-bit registers (32-bit compatible mode) for -// single and double access. -// * 32bit fp: -// - AFGR32/AFGR64 = 16 even 32-bit registers - single and double -// - FGR32 = 32 32-bit registers (within single-only mode) +// 64bit fp: +// * FGR64 - 32 64-bit registers +// * AFGR64 - 16 32-bit even registers (32-bit FP Mode) +// +// 32bit fp: +// * FGR32 - 16 32-bit even registers +// * FGR32 - 32 32-bit registers (single float only mode) def FGR32 : RegisterClass<"Mips", [f32], 32, // Return Values and Arguments [F0, F1, F2, F3, F12, F13, F14, F15, @@ -178,35 +178,46 @@ def FGR32 : RegisterClass<"Mips", [f32], 32, F31]> { let MethodProtos = [{ + iterator allocation_order_begin(const MachineFunction &MF) const; iterator allocation_order_end(const MachineFunction &MF) const; }]; let MethodBodies = [{ + + static const unsigned MIPS_FGR32[] = { + Mips::F0, Mips::F1, Mips::F2, Mips::F3, Mips::F12, Mips::F13, + Mips::F14, Mips::F15, Mips::F4, Mips::F5, Mips::F6, Mips::F7, + Mips::F8, Mips::F9, Mips::F10, Mips::F11, Mips::F16, Mips::F17, + Mips::F18, Mips::F19, Mips::F20, Mips::F21, Mips::F22, Mips::F23, + Mips::F24, Mips::F25, Mips::F26, Mips::F27, Mips::F28, Mips::F29, + Mips::F30 + }; + + static const unsigned MIPS_SVR4_FGR32[] = { + Mips::F0, Mips::F2, Mips::F12, Mips::F14, Mips::F4, + Mips::F6, Mips::F8, Mips::F10, Mips::F16, Mips::F18, + Mips::F20, Mips::F22, Mips::F24, Mips::F26, Mips::F28, Mips::F30, + }; + FGR32Class::iterator - FGR32Class::allocation_order_end(const MachineFunction &MF) const { - // The last register on the list above is reserved - return end()-1; + FGR32Class::allocation_order_begin(const MachineFunction &MF) const { + const TargetMachine &TM = MF.getTarget(); + const MipsSubtarget &Subtarget = TM.getSubtarget(); + + if (Subtarget.isSingleFloat()) + return MIPS_FGR32; + else + return MIPS_SVR4_FGR32; } - }]; -} -def AFGR32 : RegisterClass<"Mips", [f32], 32, - // Return Values and Arguments - [F0, F2, F12, F14, - // Not preserved across procedure calls - F4, F6, F8, F10, F16, F18, - // Callee save - F20, F22, F24, F26, F28, F30, - // Reserved - F31]> -{ - let MethodProtos = [{ - iterator allocation_order_end(const MachineFunction &MF) const; - }]; - let MethodBodies = [{ - AFGR32Class::iterator - AFGR32Class::allocation_order_end(const MachineFunction &MF) const { - // The last register on the list above is reserved - return end()-1; + FGR32Class::iterator + FGR32Class::allocation_order_end(const MachineFunction &MF) const { + const TargetMachine &TM = MF.getTarget(); + const MipsSubtarget &Subtarget = TM.getSubtarget(); + + if (Subtarget.isSingleFloat()) + return MIPS_FGR32 + (sizeof(MIPS_FGR32) / sizeof(unsigned)); + else + return MIPS_SVR4_FGR32 + (sizeof(MIPS_SVR4_FGR32) / sizeof(unsigned)); } }]; } -- 2.34.1