summaryrefslogtreecommitdiffstats
path: root/llvm/lib/CodeGen
diff options
context:
space:
mode:
authorEkaterina Romanova <katya_romanova@playstation.sony.com>2014-03-13 18:47:12 +0000
committerEkaterina Romanova <katya_romanova@playstation.sony.com>2014-03-13 18:47:12 +0000
commit8d62008ecb3edd841341789112a0fcab587beff5 (patch)
tree2d4176db3955c65cf9283bbbec535bffea398b39 /llvm/lib/CodeGen
parentc3ec337e4db6ee91db5471cb9e4e479d2f6c1d99 (diff)
downloadbcm5719-llvm-8d62008ecb3edd841341789112a0fcab587beff5.tar.gz
bcm5719-llvm-8d62008ecb3edd841341789112a0fcab587beff5.zip
Fix for http://llvm.org/bugs/show_bug.cgi?id=18590
This patch fixes the bug in peephole optimization that folds a load which defines one vreg into the one and only use of that vreg. With debug info, a DBG_VALUE that referenced the vreg considered to be a use, preventing the optimization. The fix is to ignore DBG_VALUE's during the optimization, and undef a DBG_VALUE that references a vreg that gets removed. Patch by Trevor Smigiel! llvm-svn: 203829
Diffstat (limited to 'llvm/lib/CodeGen')
-rw-r--r--llvm/lib/CodeGen/DeadMachineInstructionElim.cpp12
-rw-r--r--llvm/lib/CodeGen/MachineRegisterInfo.cpp15
-rw-r--r--llvm/lib/CodeGen/PeepholeOptimizer.cpp14
3 files changed, 27 insertions, 14 deletions
diff --git a/llvm/lib/CodeGen/DeadMachineInstructionElim.cpp b/llvm/lib/CodeGen/DeadMachineInstructionElim.cpp
index bbb4da83305..643efc2a4f9 100644
--- a/llvm/lib/CodeGen/DeadMachineInstructionElim.cpp
+++ b/llvm/lib/CodeGen/DeadMachineInstructionElim.cpp
@@ -127,17 +127,7 @@ bool DeadMachineInstructionElim::runOnMachineFunction(MachineFunction &MF) {
unsigned Reg = MO.getReg();
if (!TargetRegisterInfo::isVirtualRegister(Reg))
continue;
- MachineRegisterInfo::use_iterator nextI;
- for (MachineRegisterInfo::use_iterator I = MRI->use_begin(Reg),
- E = MRI->use_end(); I!=E; I=nextI) {
- nextI = std::next(I); // I is invalidated by the setReg
- MachineOperand& Use = I.getOperand();
- MachineInstr *UseMI = Use.getParent();
- if (UseMI==MI)
- continue;
- assert(Use.isDebug());
- UseMI->getOperand(0).setReg(0U);
- }
+ MRI->markUsesInDebugValueAsUndef(Reg);
}
AnyChanges = true;
MI->eraseFromParent();
diff --git a/llvm/lib/CodeGen/MachineRegisterInfo.cpp b/llvm/lib/CodeGen/MachineRegisterInfo.cpp
index 4029f4a2bbc..3dabcbed7fc 100644
--- a/llvm/lib/CodeGen/MachineRegisterInfo.cpp
+++ b/llvm/lib/CodeGen/MachineRegisterInfo.cpp
@@ -414,3 +414,18 @@ bool MachineRegisterInfo::isConstantPhysReg(unsigned PhysReg,
return false;
return true;
}
+
+/// markUsesInDebugValueAsUndef - Mark every DBG_VALUE referencing the
+/// specified register as undefined which causes the DBG_VALUE to be
+/// deleted during LiveDebugVariables analysis.
+void MachineRegisterInfo::markUsesInDebugValueAsUndef(unsigned Reg) const {
+ // Mark any DBG_VALUE that uses Reg as undef (but don't delete it.)
+ MachineRegisterInfo::use_iterator nextI;
+ for (use_iterator I = use_begin(Reg), E = use_end(); I != E; I = nextI) {
+ nextI = std::next(I); // I is invalidated by the setReg
+ MachineOperand& Use = I.getOperand();
+ MachineInstr *UseMI = Use.getParent();
+ if (UseMI->isDebugValue())
+ UseMI->getOperand(0).setReg(0U);
+ }
+}
diff --git a/llvm/lib/CodeGen/PeepholeOptimizer.cpp b/llvm/lib/CodeGen/PeepholeOptimizer.cpp
index 18af9d480c7..8bf2270755e 100644
--- a/llvm/lib/CodeGen/PeepholeOptimizer.cpp
+++ b/llvm/lib/CodeGen/PeepholeOptimizer.cpp
@@ -505,12 +505,12 @@ bool PeepholeOptimizer::isLoadFoldable(MachineInstr *MI,
return false;
unsigned Reg = MI->getOperand(0).getReg();
- // To reduce compilation time, we check MRI->hasOneUse when inserting
+ // To reduce compilation time, we check MRI->hasOneNonDBGUse when inserting
// loads. It should be checked when processing uses of the load, since
// uses can be removed during peephole.
if (!MI->getOperand(0).getSubReg() &&
TargetRegisterInfo::isVirtualRegister(Reg) &&
- MRI->hasOneUse(Reg)) {
+ MRI->hasOneNonDBGUse(Reg)) {
FoldAsLoadDefReg = Reg;
return true;
}
@@ -594,10 +594,14 @@ bool PeepholeOptimizer::runOnMachineFunction(MachineFunction &MF) {
++MII;
LocalMIs.insert(MI);
+ // Skip debug values. They should not affect this peephole optimization.
+ if (MI->isDebugValue())
+ continue;
+
// If there exists an instruction which belongs to the following
// categories, we will discard the load candidate.
if (MI->isPosition() || MI->isPHI() || MI->isImplicitDef() ||
- MI->isKill() || MI->isInlineAsm() || MI->isDebugValue() ||
+ MI->isKill() || MI->isInlineAsm() ||
MI->hasUnmodeledSideEffects()) {
FoldAsLoadDefReg = 0;
continue;
@@ -633,6 +637,9 @@ bool PeepholeOptimizer::runOnMachineFunction(MachineFunction &MF) {
if (!isLoadFoldable(MI, FoldAsLoadDefReg) && FoldAsLoadDefReg) {
// We need to fold load after optimizeCmpInstr, since optimizeCmpInstr
// can enable folding by converting SUB to CMP.
+ // Save FoldAsLoadDefReg because optimizeLoadInstr() resets it and we
+ // need it for markUsesInDebugValueAsUndef().
+ unsigned FoldedReg = FoldAsLoadDefReg;
MachineInstr *DefMI = 0;
MachineInstr *FoldMI = TII->optimizeLoadInstr(MI, MRI,
FoldAsLoadDefReg, DefMI);
@@ -645,6 +652,7 @@ bool PeepholeOptimizer::runOnMachineFunction(MachineFunction &MF) {
LocalMIs.insert(FoldMI);
MI->eraseFromParent();
DefMI->eraseFromParent();
+ MRI->markUsesInDebugValueAsUndef(FoldedReg);
++NumLoadFold;
// MI is replaced with FoldMI.
OpenPOWER on IntegriCloud