void MipsDAGToDAGISel::InitGlobalBaseReg(MachineFunction &MF) {
MipsFunctionInfo *MipsFI = MF.getInfo<MipsFunctionInfo>();
+ if (!MipsFI->globalBaseRegSet())
+ return;
+
MachineBasicBlock &MBB = MF.front();
MachineBasicBlock::iterator I = MBB.begin();
MachineRegisterInfo &RegInfo = MF.getRegInfo();
- const MipsRegisterInfo *TargetRegInfo = TM.getRegisterInfo();
- const MipsInstrInfo *MII = TM.getInstrInfo();
const TargetInstrInfo &TII = *MF.getTarget().getInstrInfo();
DebugLoc DL = I != MBB.end() ? I->getDebugLoc() : DebugLoc();
- unsigned V0, V1, GlobalBaseReg = MipsFI->getGlobalBaseReg();
- int FI; // should initialize this to some kind of null
+ unsigned V0, V1, V2, GlobalBaseReg = MipsFI->getGlobalBaseReg();
+ const TargetRegisterClass *RC;
- if (!Subtarget.inMips16Mode())
- FI= MipsFI->initGlobalRegFI();
-
- const TargetRegisterClass *RC = Subtarget.isABI_N64() ?
- (const TargetRegisterClass*)&Mips::CPU64RegsRegClass :
- (const TargetRegisterClass*)&Mips::CPURegsRegClass;
+ if (Subtarget.isABI_N64())
+ RC = (const TargetRegisterClass*)&Mips::CPU64RegsRegClass;
+ else if (Subtarget.inMips16Mode())
+ RC = (const TargetRegisterClass*)&Mips::CPU16RegsRegClass;
+ else
+ RC = (const TargetRegisterClass*)&Mips::CPURegsRegClass;
V0 = RegInfo.createVirtualRegister(RC);
V1 = RegInfo.createVirtualRegister(RC);
+ V2 = RegInfo.createVirtualRegister(RC);
if (Subtarget.isABI_N64()) {
MF.getRegInfo().addLiveIn(Mips::T9_64);
.addReg(Mips::T9_64);
BuildMI(MBB, I, DL, TII.get(Mips::DADDiu), GlobalBaseReg).addReg(V1)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_LO);
- MII->storeRegToStackSlot(MBB, I, GlobalBaseReg, false, FI, RC,
- TargetRegInfo);
+ return;
+ }
+
+ if (Subtarget.inMips16Mode()) {
+ BuildMI(MBB, I, DL, TII.get(Mips::LiRxImmX16), V0)
+ .addExternalSymbol("_gp_disp", MipsII::MO_ABS_HI);
+ BuildMI(MBB, I, DL, TII.get(Mips::AddiuRxPcImmX16), V1)
+ .addExternalSymbol("_gp_disp", MipsII::MO_ABS_LO);
+ BuildMI(MBB, I, DL, TII.get(Mips::SllX16), V2).addReg(V0).addImm(16);
+ BuildMI(MBB, I, DL, TII.get(Mips::AdduRxRyRz16), GlobalBaseReg)
+ .addReg(V1).addReg(V2);
return;
}
.addExternalSymbol("__gnu_local_gp", MipsII::MO_ABS_HI);
BuildMI(MBB, I, DL, TII.get(Mips::ADDiu), GlobalBaseReg).addReg(V0)
.addExternalSymbol("__gnu_local_gp", MipsII::MO_ABS_LO);
- MII->storeRegToStackSlot(MBB, I, GlobalBaseReg, false, FI, RC,
- TargetRegInfo);
return;
}
BuildMI(MBB, I, DL, TII.get(Mips::ADDu), V1).addReg(V0).addReg(Mips::T9);
BuildMI(MBB, I, DL, TII.get(Mips::ADDiu), GlobalBaseReg).addReg(V1)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_LO);
- MII->storeRegToStackSlot(MBB, I, GlobalBaseReg, false, FI, RC,
- TargetRegInfo);
return;
}
assert(Subtarget.isABI_O32());
- if (Subtarget.inMips16Mode())
- return; // no need to load GP. It can be calculated anywhere
-
-
// For O32 ABI, the following instruction sequence is emitted to initialize
// the global base register:
//
MBB.addLiveIn(Mips::V0);
BuildMI(MBB, I, DL, TII.get(Mips::ADDu), GlobalBaseReg)
.addReg(Mips::V0).addReg(Mips::T9);
- MII->storeRegToStackSlot(MBB, I, GlobalBaseReg, false, FI, RC, TargetRegInfo);
}
bool MipsDAGToDAGISel::ReplaceUsesWithZeroReg(MachineRegisterInfo *MRI,
// Replace uses with ZeroReg.
for (MachineRegisterInfo::use_iterator U = MRI->use_begin(DstReg),
- E = MRI->use_end(); U != E; ++U) {
+ E = MRI->use_end(); U != E;) {
MachineOperand &MO = U.getOperand();
+ unsigned OpNo = U.getOperandNo();
MachineInstr *MI = MO.getParent();
+ ++U;
// Do not replace if it is a phi's operand or is tied to def operand.
- if (MI->isPHI() || MI->isRegTiedToDefOperand(U.getOperandNo()) ||
- MI->isPseudo())
+ if (MI->isPHI() || MI->isRegTiedToDefOperand(OpNo) || MI->isPseudo())
continue;
MO.setReg(ZeroReg);
SelectAddr(SDNode *Parent, SDValue Addr, SDValue &Base, SDValue &Offset) {
EVT ValTy = Addr.getValueType();
- // If Parent is an unaligned f32 load or store, select a (base + index)
- // floating point load/store instruction (luxc1 or suxc1).
- const LSBaseSDNode *LS = 0;
-
- if (Parent && (LS = dyn_cast<LSBaseSDNode>(Parent))) {
- EVT VT = LS->getMemoryVT();
-
- if (VT.getSizeInBits() / 8 > LS->getAlignment()) {
- assert(TLI.allowsUnalignedMemoryAccesses(VT) &&
- "Unaligned loads/stores not supported for this type.");
- if (VT == MVT::f32)
- return false;
- }
- }
-
// if Address is FI, get the TargetFrameIndex.
if (FrameIndexSDNode *FIN = dyn_cast<FrameIndexSDNode>(Addr)) {
Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), ValTy);
}
// If an indexed floating point load/store can be emitted, return false.
+ const LSBaseSDNode *LS = dyn_cast<LSBaseSDNode>(Parent);
+
if (LS &&
(LS->getMemoryVT() == MVT::f32 || LS->getMemoryVT() == MVT::f64) &&
Subtarget.hasMips32r2Or64())