summaryrefslogtreecommitdiff
path: root/lib/CodeGen/MachineLICM.cpp
diff options
context:
space:
mode:
authorEvan Cheng <evan.cheng@apple.com>2010-04-13 20:21:05 +0000
committerEvan Cheng <evan.cheng@apple.com>2010-04-13 20:21:05 +0000
commitaeb2f4aa462949ce067125f2f56dc34df64b25db (patch)
tree4ab458ba863bcf6df8af350163a3ce3b5bf448fa /lib/CodeGen/MachineLICM.cpp
parent8d17160e2cf9a1645b4b06b0cd575aef6195b108 (diff)
downloadllvm-aeb2f4aa462949ce067125f2f56dc34df64b25db.tar.gz
llvm-aeb2f4aa462949ce067125f2f56dc34df64b25db.tar.bz2
llvm-aeb2f4aa462949ce067125f2f56dc34df64b25db.tar.xz
Expand postra machine licm's capability a little more. If an instruction's register operands are all loop invariants, then it's safe to hoist it.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@101167 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/MachineLICM.cpp')
-rw-r--r--lib/CodeGen/MachineLICM.cpp32
1 files changed, 24 insertions, 8 deletions
diff --git a/lib/CodeGen/MachineLICM.cpp b/lib/CodeGen/MachineLICM.cpp
index f99aa25e10..1db30d8c4e 100644
--- a/lib/CodeGen/MachineLICM.cpp
+++ b/lib/CodeGen/MachineLICM.cpp
@@ -276,7 +276,7 @@ void MachineLICM::ProcessMI(MachineInstr *MI,
SmallSet<int, 32> &StoredFIs,
SmallVector<CandidateInfo, 32> &Candidates) {
bool RuledOut = false;
- bool HasRegFIUse = false;
+ bool HasNonInvariantUse = false;
unsigned Def = 0;
for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
const MachineOperand &MO = MI->getOperand(i);
@@ -287,7 +287,7 @@ void MachineLICM::ProcessMI(MachineInstr *MI,
MFI->isSpillSlotObjectIndex(FI) &&
InstructionStoresToFI(MI, FI))
StoredFIs.insert(FI);
- HasRegFIUse = true;
+ HasNonInvariantUse = true;
continue;
}
@@ -300,7 +300,10 @@ void MachineLICM::ProcessMI(MachineInstr *MI,
"Not expecting virtual register!");
if (!MO.isDef()) {
- HasRegFIUse = true;
+ if (PhysRegDefs[Reg])
+ // If it's using a non-loop-invariant register, then it's obviously not
+ // safe to hoist.
+ HasNonInvariantUse = true;
continue;
}
@@ -338,9 +341,7 @@ void MachineLICM::ProcessMI(MachineInstr *MI,
// operands. FIXME: Consider unfold load folding instructions.
if (Def && !RuledOut) {
int FI = INT_MIN;
- // FIXME: Also hoist instructions if all source operands are live in
- // to the loop.
- if ((!HasRegFIUse && IsLICMCandidate(*MI)) ||
+ if ((!HasNonInvariantUse && IsLICMCandidate(*MI)) ||
(TII->isLoadFromStackSlot(MI, FI) && MFI->isSpillSlotObjectIndex(FI)))
Candidates.push_back(CandidateInfo(MI, Def, FI));
}
@@ -400,8 +401,23 @@ void MachineLICM::HoistRegionPostRA(MachineDomTreeNode *N) {
StoredFIs.count(Candidates[i].FI))
continue;
- if (PhysRegDefs[Candidates[i].Def] == 1)
- HoistPostRA(Candidates[i].MI, Candidates[i].Def);
+ if (PhysRegDefs[Candidates[i].Def] == 1) {
+ bool Safe = true;
+ MachineInstr *MI = Candidates[i].MI;
+ for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
+ const MachineOperand &MO = MI->getOperand(i);
+ if (!MO.isReg() || MO.isDef())
+ continue;
+ if (PhysRegDefs[MO.getReg()]) {
+ // If it's using a non-loop-invariant register, then it's obviously
+ // not safe to hoist.
+ Safe = false;
+ break;
+ }
+ }
+ if (Safe)
+ HoistPostRA(MI, Candidates[i].Def);
+ }
}
delete[] PhysRegDefs;