[mips] Move initGlobalBaseReg to MipsFunctionInfo. NFC

Move initGlobalBaseReg from MipsSEDAGToDAGISel to MipsFunctionInfo.
This way functions used for handling position independent code during
instruction selection, getGlobalBaseReg and initGlobalBaseReg,
end up in same class.

Differential Revision: https://reviews.llvm.org/D62586

llvm-svn: 362206
This commit is contained in:
Petar Avramovic 2019-05-31 08:15:28 +00:00
parent b457e430f3
commit 9058b50fb2
4 changed files with 93 additions and 94 deletions

View File

@ -51,6 +51,94 @@ unsigned MipsFunctionInfo::getGlobalBaseReg() {
return GlobalBaseReg;
}
void MipsFunctionInfo::initGlobalBaseReg() {
if (!GlobalBaseReg)
return;
MachineBasicBlock &MBB = MF.front();
MachineBasicBlock::iterator I = MBB.begin();
MachineRegisterInfo &RegInfo = MF.getRegInfo();
const TargetInstrInfo &TII = *MF.getSubtarget().getInstrInfo();
DebugLoc DL;
unsigned V0, V1;
const TargetRegisterClass *RC;
const MipsABIInfo &ABI =
static_cast<const MipsTargetMachine &>(MF.getTarget()).getABI();
RC = (ABI.IsN64()) ? &Mips::GPR64RegClass : &Mips::GPR32RegClass;
V0 = RegInfo.createVirtualRegister(RC);
V1 = RegInfo.createVirtualRegister(RC);
if (ABI.IsN64()) {
MF.getRegInfo().addLiveIn(Mips::T9_64);
MBB.addLiveIn(Mips::T9_64);
// lui $v0, %hi(%neg(%gp_rel(fname)))
// daddu $v1, $v0, $t9
// daddiu $globalbasereg, $v1, %lo(%neg(%gp_rel(fname)))
const GlobalValue *FName = &MF.getFunction();
BuildMI(MBB, I, DL, TII.get(Mips::LUi64), V0)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_HI);
BuildMI(MBB, I, DL, TII.get(Mips::DADDu), V1).addReg(V0)
.addReg(Mips::T9_64);
BuildMI(MBB, I, DL, TII.get(Mips::DADDiu), GlobalBaseReg).addReg(V1)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_LO);
return;
}
if (!MF.getTarget().isPositionIndependent()) {
// Set global register to __gnu_local_gp.
//
// lui $v0, %hi(__gnu_local_gp)
// addiu $globalbasereg, $v0, %lo(__gnu_local_gp)
BuildMI(MBB, I, DL, TII.get(Mips::LUi), V0)
.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);
return;
}
MF.getRegInfo().addLiveIn(Mips::T9);
MBB.addLiveIn(Mips::T9);
if (ABI.IsN32()) {
// lui $v0, %hi(%neg(%gp_rel(fname)))
// addu $v1, $v0, $t9
// addiu $globalbasereg, $v1, %lo(%neg(%gp_rel(fname)))
const GlobalValue *FName = &MF.getFunction();
BuildMI(MBB, I, DL, TII.get(Mips::LUi), V0)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_HI);
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);
return;
}
assert(ABI.IsO32());
// For O32 ABI, the following instruction sequence is emitted to initialize
// the global base register:
//
// 0. lui $2, %hi(_gp_disp)
// 1. addiu $2, $2, %lo(_gp_disp)
// 2. addu $globalbasereg, $2, $t9
//
// We emit only the last instruction here.
//
// GNU linker requires that the first two instructions appear at the beginning
// of a function and no instructions be inserted before or between them.
// The two instructions are emitted during lowering to MC layer in order to
// avoid any reordering.
//
// Register $2 (Mips::V0) is added to the list of live-in registers to ensure
// the value instruction 1 (addiu) defines is valid when instruction 2 (addu)
// reads it.
MF.getRegInfo().addLiveIn(Mips::V0);
MBB.addLiveIn(Mips::V0);
BuildMI(MBB, I, DL, TII.get(Mips::ADDu), GlobalBaseReg)
.addReg(Mips::V0).addReg(Mips::T9);
}
void MipsFunctionInfo::createEhDataRegsFI() {
const TargetRegisterInfo &TRI = *MF.getSubtarget().getRegisterInfo();
for (int I = 0; I < 4; ++I) {

View File

@ -34,6 +34,10 @@ public:
bool globalBaseRegSet() const;
unsigned getGlobalBaseReg();
// Insert instructions to initialize the global base register in the
// first MBB of the function.
void initGlobalBaseReg();
int getVarArgsFrameIndex() const { return VarArgsFrameIndex; }
void setVarArgsFrameIndex(int Index) { VarArgsFrameIndex = Index; }

View File

@ -134,97 +134,8 @@ bool MipsSEDAGToDAGISel::replaceUsesWithZeroReg(MachineRegisterInfo *MRI,
return true;
}
void MipsSEDAGToDAGISel::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 TargetInstrInfo &TII = *Subtarget->getInstrInfo();
DebugLoc DL;
unsigned V0, V1, GlobalBaseReg = MipsFI->getGlobalBaseReg();
const TargetRegisterClass *RC;
const MipsABIInfo &ABI = static_cast<const MipsTargetMachine &>(TM).getABI();
RC = (ABI.IsN64()) ? &Mips::GPR64RegClass : &Mips::GPR32RegClass;
V0 = RegInfo.createVirtualRegister(RC);
V1 = RegInfo.createVirtualRegister(RC);
if (ABI.IsN64()) {
MF.getRegInfo().addLiveIn(Mips::T9_64);
MBB.addLiveIn(Mips::T9_64);
// lui $v0, %hi(%neg(%gp_rel(fname)))
// daddu $v1, $v0, $t9
// daddiu $globalbasereg, $v1, %lo(%neg(%gp_rel(fname)))
const GlobalValue *FName = &MF.getFunction();
BuildMI(MBB, I, DL, TII.get(Mips::LUi64), V0)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_HI);
BuildMI(MBB, I, DL, TII.get(Mips::DADDu), V1).addReg(V0)
.addReg(Mips::T9_64);
BuildMI(MBB, I, DL, TII.get(Mips::DADDiu), GlobalBaseReg).addReg(V1)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_LO);
return;
}
if (!MF.getTarget().isPositionIndependent()) {
// Set global register to __gnu_local_gp.
//
// lui $v0, %hi(__gnu_local_gp)
// addiu $globalbasereg, $v0, %lo(__gnu_local_gp)
BuildMI(MBB, I, DL, TII.get(Mips::LUi), V0)
.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);
return;
}
MF.getRegInfo().addLiveIn(Mips::T9);
MBB.addLiveIn(Mips::T9);
if (ABI.IsN32()) {
// lui $v0, %hi(%neg(%gp_rel(fname)))
// addu $v1, $v0, $t9
// addiu $globalbasereg, $v1, %lo(%neg(%gp_rel(fname)))
const GlobalValue *FName = &MF.getFunction();
BuildMI(MBB, I, DL, TII.get(Mips::LUi), V0)
.addGlobalAddress(FName, 0, MipsII::MO_GPOFF_HI);
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);
return;
}
assert(ABI.IsO32());
// For O32 ABI, the following instruction sequence is emitted to initialize
// the global base register:
//
// 0. lui $2, %hi(_gp_disp)
// 1. addiu $2, $2, %lo(_gp_disp)
// 2. addu $globalbasereg, $2, $t9
//
// We emit only the last instruction here.
//
// GNU linker requires that the first two instructions appear at the beginning
// of a function and no instructions be inserted before or between them.
// The two instructions are emitted during lowering to MC layer in order to
// avoid any reordering.
//
// Register $2 (Mips::V0) is added to the list of live-in registers to ensure
// the value instruction 1 (addiu) defines is valid when instruction 2 (addu)
// reads it.
MF.getRegInfo().addLiveIn(Mips::V0);
MBB.addLiveIn(Mips::V0);
BuildMI(MBB, I, DL, TII.get(Mips::ADDu), GlobalBaseReg)
.addReg(Mips::V0).addReg(Mips::T9);
}
void MipsSEDAGToDAGISel::processFunctionAfterISel(MachineFunction &MF) {
initGlobalBaseReg(MF);
MF.getInfo<MipsFunctionInfo>()->initGlobalBaseReg();
MachineRegisterInfo *MRI = &MF.getRegInfo();

View File

@ -130,10 +130,6 @@ private:
void processFunctionAfterISel(MachineFunction &MF) override;
// Insert instructions to initialize the global base register in the
// first MBB of the function.
void initGlobalBaseReg(MachineFunction &MF);
bool SelectInlineAsmMemoryOperand(const SDValue &Op,
unsigned ConstraintID,
std::vector<SDValue> &OutOps) override;