summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Target/PowerPC
diff options
context:
space:
mode:
authorZaara Syeda <syzaara@ca.ibm.com>2018-03-19 14:52:25 +0000
committerZaara Syeda <syzaara@ca.ibm.com>2018-03-19 14:52:25 +0000
commitff05e2b0e609a10ac7ab1db445ffdba24319d50d (patch)
treeaa43bbdf11411c98ab7670b00081e4db4dad32c6 /llvm/lib/Target/PowerPC
parent30c38c38497763d5660fde146e1185c0dbb082d5 (diff)
downloadbcm5719-llvm-ff05e2b0e609a10ac7ab1db445ffdba24319d50d.tar.gz
bcm5719-llvm-ff05e2b0e609a10ac7ab1db445ffdba24319d50d.zip
[MachineLICM] Add functions to MachineLICM to hoist invariant stores
This patch adds functions to allow MachineLICM to hoist invariant stores. Currently, MachineLICM does not hoist any store instructions, however when storing the same value to a constant spot on the stack, the store instruction should be considered invariant and be hoisted. The function isInvariantStore iterates each operand of the store instruction and checks that each register operand satisfies isCallerPreservedPhysReg. The store may be fed by a copy, which is hoisted by isCopyFeedingInvariantStore. This patch also adds the PowerPC changes needed to consider the stack register as caller preserved. Differential Revision: https://reviews.llvm.org/D40196 llvm-svn: 327856
Diffstat (limited to 'llvm/lib/Target/PowerPC')
-rw-r--r--llvm/lib/Target/PowerPC/PPCInstrInfo.cpp25
-rw-r--r--llvm/lib/Target/PowerPC/PPCInstrInfo.h7
-rw-r--r--llvm/lib/Target/PowerPC/PPCMIPeephole.cpp20
-rw-r--r--llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp25
4 files changed, 33 insertions, 44 deletions
diff --git a/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp b/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp
index 4e0dd9d5e5e..8e92316e75e 100644
--- a/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp
+++ b/llvm/lib/Target/PowerPC/PPCInstrInfo.cpp
@@ -2178,28 +2178,6 @@ bool PPCInstrInfo::expandPostRAPseudo(MachineInstr &MI) const {
return false;
}
-unsigned PPCInstrInfo::lookThruCopyLike(unsigned SrcReg,
- const MachineRegisterInfo *MRI) {
- while (true) {
- MachineInstr *MI = MRI->getVRegDef(SrcReg);
- if (!MI->isCopyLike())
- return SrcReg;
-
- unsigned CopySrcReg;
- if (MI->isCopy())
- CopySrcReg = MI->getOperand(1).getReg();
- else {
- assert(MI->isSubregToReg() && "Bad opcode for lookThruCopyLike");
- CopySrcReg = MI->getOperand(2).getReg();
- }
-
- if (!TargetRegisterInfo::isVirtualRegister(CopySrcReg))
- return CopySrcReg;
-
- SrcReg = CopySrcReg;
- }
-}
-
// Essentially a compile-time implementation of a compare->isel sequence.
// It takes two constants to compare, along with the true/false registers
// and the comparison type (as a subreg to a CR field) and returns one
@@ -2265,6 +2243,7 @@ MachineInstr *PPCInstrInfo::getConstantDefMI(MachineInstr &MI,
ConstOp = ~0U;
MachineInstr *DefMI = nullptr;
MachineRegisterInfo *MRI = &MI.getParent()->getParent()->getRegInfo();
+ const TargetRegisterInfo *TRI = &getRegisterInfo();
// If we'ere in SSA, get the defs through the MRI. Otherwise, only look
// within the basic block to see if the register is defined using an LI/LI8.
if (MRI->isSSA()) {
@@ -2274,7 +2253,7 @@ MachineInstr *PPCInstrInfo::getConstantDefMI(MachineInstr &MI,
unsigned Reg = MI.getOperand(i).getReg();
if (!TargetRegisterInfo::isVirtualRegister(Reg))
continue;
- unsigned TrueReg = lookThruCopyLike(Reg, MRI);
+ unsigned TrueReg = TRI->lookThruCopyLike(Reg, MRI);
if (TargetRegisterInfo::isVirtualRegister(TrueReg)) {
DefMI = MRI->getVRegDef(TrueReg);
if (DefMI->getOpcode() == PPC::LI || DefMI->getOpcode() == PPC::LI8) {
diff --git a/llvm/lib/Target/PowerPC/PPCInstrInfo.h b/llvm/lib/Target/PowerPC/PPCInstrInfo.h
index 8bfb8bc8809..3eba41f7df6 100644
--- a/llvm/lib/Target/PowerPC/PPCInstrInfo.h
+++ b/llvm/lib/Target/PowerPC/PPCInstrInfo.h
@@ -359,13 +359,6 @@ public:
MachineInstr **KilledDef = nullptr) const;
void replaceInstrWithLI(MachineInstr &MI, const LoadImmediateInfo &LII) const;
- // This is used to find the "true" source register for n
- // Machine instruction. Returns the original SrcReg unless it is the target
- // of a copy-like operation, in which case we chain backwards through all
- // such operations to the ultimate source register. If a
- // physical register is encountered, we stop the search.
- static unsigned lookThruCopyLike(unsigned SrcReg,
- const MachineRegisterInfo *MRI);
bool instrHasImmForm(const MachineInstr &MI, ImmInstrInfo &III) const;
};
diff --git a/llvm/lib/Target/PowerPC/PPCMIPeephole.cpp b/llvm/lib/Target/PowerPC/PPCMIPeephole.cpp
index 246770f02a8..8151e433d6a 100644
--- a/llvm/lib/Target/PowerPC/PPCMIPeephole.cpp
+++ b/llvm/lib/Target/PowerPC/PPCMIPeephole.cpp
@@ -220,7 +220,7 @@ bool PPCMIPeephole::simplifyCode(void) {
bool Simplified = false;
MachineInstr* ToErase = nullptr;
std::map<MachineInstr *, bool> TOCSaves;
-
+ const TargetRegisterInfo *TRI = &TII->getRegisterInfo();
NumFunctionsEnteredInMIPeephole++;
if (ConvertRegReg) {
// Fixed-point conversion of reg/reg instructions fed by load-immediate
@@ -297,9 +297,9 @@ bool PPCMIPeephole::simplifyCode(void) {
// We have to look through chains of COPY and SUBREG_TO_REG
// to find the real source values for comparison.
unsigned TrueReg1 =
- TII->lookThruCopyLike(MI.getOperand(1).getReg(), MRI);
+ TRI->lookThruCopyLike(MI.getOperand(1).getReg(), MRI);
unsigned TrueReg2 =
- TII->lookThruCopyLike(MI.getOperand(2).getReg(), MRI);
+ TRI->lookThruCopyLike(MI.getOperand(2).getReg(), MRI);
if (TrueReg1 == TrueReg2
&& TargetRegisterInfo::isVirtualRegister(TrueReg1)) {
@@ -314,7 +314,7 @@ bool PPCMIPeephole::simplifyCode(void) {
if (DefOpc != PPC::XVCVDPSXDS && DefOpc != PPC::XVCVDPUXDS)
return false;
unsigned DefReg =
- TII->lookThruCopyLike(DefMI->getOperand(1).getReg(), MRI);
+ TRI->lookThruCopyLike(DefMI->getOperand(1).getReg(), MRI);
if (TargetRegisterInfo::isVirtualRegister(DefReg)) {
MachineInstr *LoadMI = MRI->getVRegDef(DefReg);
if (LoadMI && LoadMI->getOpcode() == PPC::LXVDSX)
@@ -341,9 +341,9 @@ bool PPCMIPeephole::simplifyCode(void) {
if (DefOpc == PPC::XXPERMDI) {
unsigned FeedImmed = DefMI->getOperand(3).getImm();
unsigned FeedReg1 =
- TII->lookThruCopyLike(DefMI->getOperand(1).getReg(), MRI);
+ TRI->lookThruCopyLike(DefMI->getOperand(1).getReg(), MRI);
unsigned FeedReg2 =
- TII->lookThruCopyLike(DefMI->getOperand(2).getReg(), MRI);
+ TRI->lookThruCopyLike(DefMI->getOperand(2).getReg(), MRI);
if ((FeedImmed == 0 || FeedImmed == 3) && FeedReg1 == FeedReg2) {
DEBUG(dbgs()
@@ -402,7 +402,7 @@ bool PPCMIPeephole::simplifyCode(void) {
unsigned MyOpcode = MI.getOpcode();
unsigned OpNo = MyOpcode == PPC::XXSPLTW ? 1 : 2;
unsigned TrueReg =
- TII->lookThruCopyLike(MI.getOperand(OpNo).getReg(), MRI);
+ TRI->lookThruCopyLike(MI.getOperand(OpNo).getReg(), MRI);
if (!TargetRegisterInfo::isVirtualRegister(TrueReg))
break;
MachineInstr *DefMI = MRI->getVRegDef(TrueReg);
@@ -465,7 +465,7 @@ bool PPCMIPeephole::simplifyCode(void) {
case PPC::XVCVDPSP: {
// If this is a DP->SP conversion fed by an FRSP, the FRSP is redundant.
unsigned TrueReg =
- TII->lookThruCopyLike(MI.getOperand(1).getReg(), MRI);
+ TRI->lookThruCopyLike(MI.getOperand(1).getReg(), MRI);
if (!TargetRegisterInfo::isVirtualRegister(TrueReg))
break;
MachineInstr *DefMI = MRI->getVRegDef(TrueReg);
@@ -474,9 +474,9 @@ bool PPCMIPeephole::simplifyCode(void) {
// values.
if (DefMI && DefMI->getOpcode() == PPC::XXPERMDI) {
unsigned DefsReg1 =
- TII->lookThruCopyLike(DefMI->getOperand(1).getReg(), MRI);
+ TRI->lookThruCopyLike(DefMI->getOperand(1).getReg(), MRI);
unsigned DefsReg2 =
- TII->lookThruCopyLike(DefMI->getOperand(2).getReg(), MRI);
+ TRI->lookThruCopyLike(DefMI->getOperand(2).getReg(), MRI);
if (!TargetRegisterInfo::isVirtualRegister(DefsReg1) ||
!TargetRegisterInfo::isVirtualRegister(DefsReg2))
break;
diff --git a/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp b/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp
index a938bb98ce1..bc9dfb1292c 100644
--- a/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp
+++ b/llvm/lib/Target/PowerPC/PPCRegisterInfo.cpp
@@ -65,6 +65,12 @@ static cl::opt<bool>
EnableGPRToVecSpills("ppc-enable-gpr-to-vsr-spills", cl::Hidden, cl::init(false),
cl::desc("Enable spills from gpr to vsr rather than stack"));
+static cl::opt<bool>
+StackPtrConst("ppc-stack-ptr-caller-preserved",
+ cl::desc("Consider R1 caller preserved so stack saves of "
+ "caller preserved registers can be LICM candidates"),
+ cl::init(true), cl::Hidden);
+
PPCRegisterInfo::PPCRegisterInfo(const PPCTargetMachine &TM)
: PPCGenRegisterInfo(TM.isPPC64() ? PPC::LR8 : PPC::LR,
TM.isPPC64() ? 0 : 1,
@@ -304,15 +310,26 @@ BitVector PPCRegisterInfo::getReservedRegs(const MachineFunction &MF) const {
bool PPCRegisterInfo::isCallerPreservedPhysReg(unsigned PhysReg,
const MachineFunction &MF) const {
assert(TargetRegisterInfo::isPhysicalRegister(PhysReg));
- if (TM.isELFv2ABI() && PhysReg == PPC::X2) {
+ const PPCSubtarget &Subtarget = MF.getSubtarget<PPCSubtarget>();
+ const MachineFrameInfo &MFI = MF.getFrameInfo();
+ if (!TM.isPPC64())
+ return false;
+
+ if (!Subtarget.isSVR4ABI())
+ return false;
+ if (PhysReg == PPC::X2)
// X2 is guaranteed to be preserved within a function if it is reserved.
// The reason it's reserved is that it's the TOC pointer (and the function
// uses the TOC). In functions where it isn't reserved (i.e. leaf functions
// with no TOC access), we can't claim that it is preserved.
return (getReservedRegs(MF).test(PPC::X2));
- } else {
- return false;
- }
+ if (StackPtrConst && (PhysReg == PPC::X1) && !MFI.hasVarSizedObjects()
+ && !MFI.hasOpaqueSPAdjustment())
+ // The value of the stack pointer does not change within a function after
+ // the prologue and before the epilogue if there are no dynamic allocations
+ // and no inline asm which clobbers X1.
+ return true;
+ return false;
}
unsigned PPCRegisterInfo::getRegPressureLimit(const TargetRegisterClass *RC,
OpenPOWER on IntegriCloud