aboutsummaryrefslogtreecommitdiffstats
path: root/lib/CodeGen
diff options
context:
space:
mode:
authorEvan Cheng <evan.cheng@apple.com>2009-09-04 07:47:40 +0000
committerEvan Cheng <evan.cheng@apple.com>2009-09-04 07:47:40 +0000
commit030a0a0cdb38924e55773a8e0b5fe7347aa664aa (patch)
tree7dffa62ef1bf0eb250d871fdc39d25cf5f776924 /lib/CodeGen
parente93909185fb61ae1b2fd045572d7d51209a39d1c (diff)
downloadexternal_llvm-030a0a0cdb38924e55773a8e0b5fe7347aa664aa.zip
external_llvm-030a0a0cdb38924e55773a8e0b5fe7347aa664aa.tar.gz
external_llvm-030a0a0cdb38924e55773a8e0b5fe7347aa664aa.tar.bz2
Run branch folding if if-converter make some transformations.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@80994 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen')
-rw-r--r--lib/CodeGen/BranchFolding.cpp147
-rw-r--r--lib/CodeGen/BranchFolding.h84
-rw-r--r--lib/CodeGen/IfConversion.cpp8
3 files changed, 155 insertions, 84 deletions
diff --git a/lib/CodeGen/BranchFolding.cpp b/lib/CodeGen/BranchFolding.cpp
index dd51d5f..f9abeac 100644
--- a/lib/CodeGen/BranchFolding.cpp
+++ b/lib/CodeGen/BranchFolding.cpp
@@ -17,6 +17,7 @@
//===----------------------------------------------------------------------===//
#define DEBUG_TYPE "branchfolding"
+#include "BranchFolding.h"
#include "llvm/CodeGen/Passes.h"
#include "llvm/CodeGen/MachineModuleInfo.h"
#include "llvm/CodeGen/MachineFunctionPass.h"
@@ -46,64 +47,28 @@ TailMergeThreshold("tail-merge-threshold",
cl::desc("Max number of predecessors to consider tail merging"),
cl::init(150), cl::Hidden);
-namespace {
- struct VISIBILITY_HIDDEN BranchFolder : public MachineFunctionPass {
- static char ID;
- explicit BranchFolder(bool defaultEnableTailMerge) :
- MachineFunctionPass(&ID) {
- switch (FlagEnableTailMerge) {
- case cl::BOU_UNSET: EnableTailMerge = defaultEnableTailMerge; break;
- case cl::BOU_TRUE: EnableTailMerge = true; break;
- case cl::BOU_FALSE: EnableTailMerge = false; break;
- }
- }
- virtual bool runOnMachineFunction(MachineFunction &MF);
- virtual const char *getPassName() const { return "Control Flow Optimizer"; }
- const TargetInstrInfo *TII;
- MachineModuleInfo *MMI;
- bool MadeChange;
- private:
- // Tail Merging.
- bool EnableTailMerge;
- bool TailMergeBlocks(MachineFunction &MF);
- bool TryMergeBlocks(MachineBasicBlock* SuccBB,
- MachineBasicBlock* PredBB);
- void ReplaceTailWithBranchTo(MachineBasicBlock::iterator OldInst,
- MachineBasicBlock *NewDest);
- MachineBasicBlock *SplitMBBAt(MachineBasicBlock &CurMBB,
- MachineBasicBlock::iterator BBI1);
- unsigned ComputeSameTails(unsigned CurHash, unsigned minCommonTailLength);
- void RemoveBlocksWithHash(unsigned CurHash, MachineBasicBlock* SuccBB,
- MachineBasicBlock* PredBB);
- unsigned CreateCommonTailOnlyBlock(MachineBasicBlock *&PredBB,
- unsigned maxCommonTailLength);
-
- typedef std::pair<unsigned,MachineBasicBlock*> MergePotentialsElt;
- typedef std::vector<MergePotentialsElt>::iterator MPIterator;
- std::vector<MergePotentialsElt> MergePotentials;
-
- typedef std::pair<MPIterator, MachineBasicBlock::iterator> SameTailElt;
- std::vector<SameTailElt> SameTails;
-
- const TargetRegisterInfo *RegInfo;
- RegScavenger *RS;
- // Branch optzn.
- bool OptimizeBranches(MachineFunction &MF);
- void OptimizeBlock(MachineBasicBlock *MBB);
- void RemoveDeadBlock(MachineBasicBlock *MBB);
- bool OptimizeImpDefsBlock(MachineBasicBlock *MBB);
-
- bool CanFallThrough(MachineBasicBlock *CurBB);
- bool CanFallThrough(MachineBasicBlock *CurBB, bool BranchUnAnalyzable,
- MachineBasicBlock *TBB, MachineBasicBlock *FBB,
- const SmallVectorImpl<MachineOperand> &Cond);
- };
- char BranchFolder::ID = 0;
-}
+char BranchFolderPass::ID = 0;
FunctionPass *llvm::createBranchFoldingPass(bool DefaultEnableTailMerge) {
- return new BranchFolder(DefaultEnableTailMerge);
+ return new BranchFolderPass(DefaultEnableTailMerge);
+}
+
+bool BranchFolderPass::runOnMachineFunction(MachineFunction &MF) {
+ return OptimizeFunction(MF,
+ MF.getTarget().getInstrInfo(),
+ MF.getTarget().getRegisterInfo(),
+ getAnalysisIfAvailable<MachineModuleInfo>());
+}
+
+
+
+BranchFolder::BranchFolder(bool defaultEnableTailMerge) {
+ switch (FlagEnableTailMerge) {
+ case cl::BOU_UNSET: EnableTailMerge = defaultEnableTailMerge; break;
+ case cl::BOU_TRUE: EnableTailMerge = true; break;
+ case cl::BOU_FALSE: EnableTailMerge = false; break;
+ }
}
/// RemoveDeadBlock - Remove the specified dead machine basic block from the
@@ -149,7 +114,7 @@ bool BranchFolder::OptimizeImpDefsBlock(MachineBasicBlock *MBB) {
break;
unsigned Reg = I->getOperand(0).getReg();
ImpDefRegs.insert(Reg);
- for (const unsigned *SubRegs = RegInfo->getSubRegisters(Reg);
+ for (const unsigned *SubRegs = TRI->getSubRegisters(Reg);
unsigned SubReg = *SubRegs; ++SubRegs)
ImpDefRegs.insert(SubReg);
++I;
@@ -183,32 +148,37 @@ bool BranchFolder::OptimizeImpDefsBlock(MachineBasicBlock *MBB) {
return true;
}
-bool BranchFolder::runOnMachineFunction(MachineFunction &MF) {
- TII = MF.getTarget().getInstrInfo();
- if (!TII) return false;
+/// OptimizeFunction - Perhaps branch folding, tail merging and other
+/// CFG optimizations on the given function.
+bool BranchFolder::OptimizeFunction(MachineFunction &MF,
+ const TargetInstrInfo *tii,
+ const TargetRegisterInfo *tri,
+ MachineModuleInfo *mmi) {
+ if (!tii) return false;
+
+ TII = tii;
+ TRI = tri;
+ MMI = mmi;
- RegInfo = MF.getTarget().getRegisterInfo();
+ RS = TRI->requiresRegisterScavenging(MF) ? new RegScavenger() : NULL;
// Fix CFG. The later algorithms expect it to be right.
- bool EverMadeChange = false;
+ bool MadeChange = false;
for (MachineFunction::iterator I = MF.begin(), E = MF.end(); I != E; I++) {
MachineBasicBlock *MBB = I, *TBB = 0, *FBB = 0;
SmallVector<MachineOperand, 4> Cond;
if (!TII->AnalyzeBranch(*MBB, TBB, FBB, Cond, true))
- EverMadeChange |= MBB->CorrectExtraCFGEdges(TBB, FBB, !Cond.empty());
- EverMadeChange |= OptimizeImpDefsBlock(MBB);
+ MadeChange |= MBB->CorrectExtraCFGEdges(TBB, FBB, !Cond.empty());
+ MadeChange |= OptimizeImpDefsBlock(MBB);
}
- RS = RegInfo->requiresRegisterScavenging(MF) ? new RegScavenger() : NULL;
-
- MMI = getAnalysisIfAvailable<MachineModuleInfo>();
bool MadeChangeThisIteration = true;
while (MadeChangeThisIteration) {
MadeChangeThisIteration = false;
MadeChangeThisIteration |= TailMergeBlocks(MF);
MadeChangeThisIteration |= OptimizeBranches(MF);
- EverMadeChange |= MadeChangeThisIteration;
+ MadeChange |= MadeChangeThisIteration;
}
// See if any jump tables have become mergable or dead as the code generator
@@ -225,8 +195,12 @@ bool BranchFolder::runOnMachineFunction(MachineFunction &MF) {
// Scan the jump tables, seeing if there are any duplicates. Note that this
// is N^2, which should be fixed someday.
- for (unsigned i = 1, e = JTs.size(); i != e; ++i)
- JTMapping.push_back(JTI->getJumpTableIndex(JTs[i].MBBs));
+ for (unsigned i = 1, e = JTs.size(); i != e; ++i) {
+ if (JTs[i].MBBs.empty())
+ JTMapping.push_back(i);
+ else
+ JTMapping.push_back(JTI->getJumpTableIndex(JTs[i].MBBs));
+ }
// If a jump table was merge with another one, walk the function rewriting
// references to jump tables to reference the new JT ID's. Keep track of
@@ -253,12 +227,12 @@ bool BranchFolder::runOnMachineFunction(MachineFunction &MF) {
for (unsigned i = 0, e = JTIsLive.size(); i != e; ++i)
if (!JTIsLive.test(i)) {
JTI->RemoveJumpTable(i);
- EverMadeChange = true;
+ MadeChange = true;
}
}
-
+
delete RS;
- return EverMadeChange;
+ return MadeChange;
}
//===----------------------------------------------------------------------===//
@@ -398,9 +372,9 @@ MachineBasicBlock *BranchFolder::SplitMBBAt(MachineBasicBlock &CurMBB,
RS->enterBasicBlock(&CurMBB);
if (!CurMBB.empty())
RS->forward(prior(CurMBB.end()));
- BitVector RegsLiveAtExit(RegInfo->getNumRegs());
+ BitVector RegsLiveAtExit(TRI->getNumRegs());
RS->getRegsUsed(RegsLiveAtExit, false);
- for (unsigned int i=0, e=RegInfo->getNumRegs(); i!=e; i++)
+ for (unsigned int i=0, e=TRI->getNumRegs(); i!=e; i++)
if (RegsLiveAtExit[i])
NewMBB->addLiveIn(i);
}
@@ -593,11 +567,12 @@ unsigned BranchFolder::CreateCommonTailOnlyBlock(MachineBasicBlock *&PredBB,
bool BranchFolder::TryMergeBlocks(MachineBasicBlock *SuccBB,
MachineBasicBlock* PredBB) {
+ bool MadeChange = false;
+
// It doesn't make sense to save a single instruction since tail merging
// will add a jump.
// FIXME: Ask the target to provide the threshold?
unsigned minCommonTailLength = (SuccBB ? 1 : 2) + 1;
- MadeChange = false;
DEBUG(errs() << "\nTryMergeBlocks " << MergePotentials.size() << '\n');
@@ -668,7 +643,7 @@ bool BranchFolder::TailMergeBlocks(MachineFunction &MF) {
if (!EnableTailMerge) return false;
- MadeChange = false;
+ bool MadeChange = false;
// First find blocks with no successors.
MergePotentials.clear();
@@ -779,14 +754,14 @@ bool BranchFolder::TailMergeBlocks(MachineFunction &MF) {
//===----------------------------------------------------------------------===//
bool BranchFolder::OptimizeBranches(MachineFunction &MF) {
- MadeChange = false;
+ bool MadeChange = false;
// Make sure blocks are numbered in order
MF.RenumberBlocks();
for (MachineFunction::iterator I = ++MF.begin(), E = MF.end(); I != E; ) {
MachineBasicBlock *MBB = I++;
- OptimizeBlock(MBB);
+ MadeChange |= OptimizeBlock(MBB);
// If it is dead, remove it.
if (MBB->pred_empty()) {
@@ -880,7 +855,9 @@ static bool IsBetterFallthrough(MachineBasicBlock *MBB1,
/// OptimizeBlock - Analyze and optimize control flow related to the specified
/// block. This is never called on the entry block.
-void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
+bool BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
+ bool MadeChange = false;
+
MachineFunction::iterator FallThrough = MBB;
++FallThrough;
@@ -889,7 +866,7 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
// points to this block.
if (MBB->empty() && !MBB->isLandingPad()) {
// Dead block? Leave for cleanup later.
- if (MBB->pred_empty()) return;
+ if (MBB->pred_empty()) return MadeChange;
if (FallThrough == MBB->getParent()->end()) {
// TODO: Simplify preds to not branch here if possible!
@@ -906,7 +883,7 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
ReplaceMBBInJumpTables(MBB, FallThrough);
MadeChange = true;
}
- return;
+ return MadeChange;
}
// Check to see if we can simplify the terminator of the block before this
@@ -1020,7 +997,7 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
MBB->moveAfter(--MBB->getParent()->end());
MadeChange = true;
++NumBranchOpts;
- return;
+ return MadeChange;
}
}
}
@@ -1122,7 +1099,7 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
if (DidChange) {
++NumBranchOpts;
MadeChange = true;
- if (!HasBranchToSelf) return;
+ if (!HasBranchToSelf) return MadeChange;
}
}
}
@@ -1203,8 +1180,10 @@ void BranchFolder::OptimizeBlock(MachineBasicBlock *MBB) {
PrevBB.isSuccessor(FallThrough)) {
MBB->moveAfter(--MBB->getParent()->end());
MadeChange = true;
- return;
+ return MadeChange;
}
}
}
+
+ return MadeChange;
}
diff --git a/lib/CodeGen/BranchFolding.h b/lib/CodeGen/BranchFolding.h
new file mode 100644
index 0000000..9763e33
--- /dev/null
+++ b/lib/CodeGen/BranchFolding.h
@@ -0,0 +1,84 @@
+//===-- BranchFolding.h - Fold machine code branch instructions --*- C++ -*===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CODEGEN_BRANCHFOLDING_HPP
+#define LLVM_CODEGEN_BRANCHFOLDING_HPP
+
+#include "llvm/CodeGen/MachineBasicBlock.h"
+#include "llvm/CodeGen/MachineFunctionPass.h"
+#include <vector>
+
+namespace llvm {
+ class MachineFunction;
+ class MachineModuleInfo;
+ class RegScavenger;
+ class TargetInstrInfo;
+ class TargetRegisterInfo;
+
+ class BranchFolder {
+ public:
+ explicit BranchFolder(bool defaultEnableTailMerge);
+
+ bool OptimizeFunction(MachineFunction &MF,
+ const TargetInstrInfo *tii,
+ const TargetRegisterInfo *tri,
+ MachineModuleInfo *mmi);
+ private:
+ typedef std::pair<unsigned,MachineBasicBlock*> MergePotentialsElt;
+ typedef std::vector<MergePotentialsElt>::iterator MPIterator;
+ std::vector<MergePotentialsElt> MergePotentials;
+
+ typedef std::pair<MPIterator, MachineBasicBlock::iterator> SameTailElt;
+ std::vector<SameTailElt> SameTails;
+
+ bool EnableTailMerge;
+ const TargetInstrInfo *TII;
+ const TargetRegisterInfo *TRI;
+ MachineModuleInfo *MMI;
+ RegScavenger *RS;
+
+ bool TailMergeBlocks(MachineFunction &MF);
+ bool TryMergeBlocks(MachineBasicBlock* SuccBB,
+ MachineBasicBlock* PredBB);
+ void ReplaceTailWithBranchTo(MachineBasicBlock::iterator OldInst,
+ MachineBasicBlock *NewDest);
+ MachineBasicBlock *SplitMBBAt(MachineBasicBlock &CurMBB,
+ MachineBasicBlock::iterator BBI1);
+ unsigned ComputeSameTails(unsigned CurHash, unsigned minCommonTailLength);
+ void RemoveBlocksWithHash(unsigned CurHash, MachineBasicBlock* SuccBB,
+ MachineBasicBlock* PredBB);
+ unsigned CreateCommonTailOnlyBlock(MachineBasicBlock *&PredBB,
+ unsigned maxCommonTailLength);
+
+ bool OptimizeBranches(MachineFunction &MF);
+ bool OptimizeBlock(MachineBasicBlock *MBB);
+ void RemoveDeadBlock(MachineBasicBlock *MBB);
+ bool OptimizeImpDefsBlock(MachineBasicBlock *MBB);
+
+ bool CanFallThrough(MachineBasicBlock *CurBB);
+ bool CanFallThrough(MachineBasicBlock *CurBB, bool BranchUnAnalyzable,
+ MachineBasicBlock *TBB, MachineBasicBlock *FBB,
+ const SmallVectorImpl<MachineOperand> &Cond);
+ };
+
+
+ /// BranchFolderPass - Wrap branch folder in a machine function pass.
+ class BranchFolderPass : public MachineFunctionPass,
+ public BranchFolder {
+ public:
+ static char ID;
+ explicit BranchFolderPass(bool defaultEnableTailMerge)
+ : MachineFunctionPass(&ID), BranchFolder(defaultEnableTailMerge) {}
+
+ virtual bool runOnMachineFunction(MachineFunction &MF);
+ virtual const char *getPassName() const { return "Control Flow Optimizer"; }
+ };
+}
+
+#endif /* LLVM_CODEGEN_BRANCHFOLDING_HPP */
diff --git a/lib/CodeGen/IfConversion.cpp b/lib/CodeGen/IfConversion.cpp
index 62bde60..7b613ff 100644
--- a/lib/CodeGen/IfConversion.cpp
+++ b/lib/CodeGen/IfConversion.cpp
@@ -12,6 +12,7 @@
//===----------------------------------------------------------------------===//
#define DEBUG_TYPE "ifcvt"
+#include "BranchFolding.h"
#include "llvm/Function.h"
#include "llvm/CodeGen/Passes.h"
#include "llvm/CodeGen/MachineModuleInfo.h"
@@ -360,6 +361,13 @@ bool IfConverter::runOnMachineFunction(MachineFunction &MF) {
Roots.clear();
BBAnalysis.clear();
+ if (MadeChange) {
+ BranchFolder BF(false);
+ BF.OptimizeFunction(MF, TII,
+ MF.getTarget().getRegisterInfo(),
+ getAnalysisIfAvailable<MachineModuleInfo>());
+ }
+
return MadeChange;
}