#include "llvm/Type.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/Statistic.h"
+#include "llvm/Support/Compiler.h"
#include "llvm/Support/Streams.h"
using namespace llvm;
STATISTIC(NumSwThread, "Number of CFG edges threaded through switches");
namespace {
- struct CondProp : public FunctionPass {
+ struct VISIBILITY_HIDDEN CondProp : public FunctionPass {
+ static char ID; // Pass identification, replacement for typeid
+ CondProp() : FunctionPass((intptr_t)&ID) {}
+
virtual bool runOnFunction(Function &F);
virtual void getAnalysisUsage(AnalysisUsage &AU) const {
void SimplifyPredecessors(SwitchInst *SI);
void RevectorBlockTo(BasicBlock *FromBB, BasicBlock *ToBB);
};
+
+ char CondProp::ID = 0;
RegisterPass<CondProp> X("condprop", "Conditional Propagation");
}
MadeChange = false;
for (Function::iterator BB = F.begin(), E = F.end(); BB != E; ++BB)
SimplifyBlock(BB);
- EverMadeChange = MadeChange;
+ EverMadeChange = EverMadeChange || MadeChange;
} while (MadeChange);
return EverMadeChange;
}
// possible, and to avoid invalidating "i".
for (unsigned i = PN->getNumIncomingValues(); i != 0; --i)
if (ConstantInt *CB = dyn_cast<ConstantInt>(PN->getIncomingValue(i-1))) {
- if (CB->getType() != Type::BoolTy) continue;
// If we have a constant, forward the edge from its current to its
// ultimate destination.
- bool PHIGone = PN->getNumIncomingValues() == 2;
RevectorBlockTo(PN->getIncomingBlock(i-1),
- BI->getSuccessor(CB->getBoolValue() == 0));
+ BI->getSuccessor(CB->isZero()));
++NumBrThread;
- // If there were two predecessors before this simplification, the PHI node
- // will be deleted. Don't iterate through it the last time.
- if (PHIGone) return;
+ // If there were two predecessors before this simplification, or if the
+ // PHI node contained all the same value except for the one we just
+ // substituted, the PHI node may be deleted. Don't iterate through it the
+ // last time.
+ if (BI->getCondition() != PN) return;
}
}
if (ConstantInt *CI = dyn_cast<ConstantInt>(PN->getIncomingValue(i-1))) {
// If we have a constant, forward the edge from its current to its
// ultimate destination.
- bool PHIGone = PN->getNumIncomingValues() == 2;
unsigned DestCase = SI->findCaseValue(CI);
RevectorBlockTo(PN->getIncomingBlock(i-1),
SI->getSuccessor(DestCase));
++NumSwThread;
RemovedPreds = true;
- // If there were two predecessors before this simplification, the PHI node
- // will be deleted. Don't iterate through it the last time.
- if (PHIGone) return;
+ // If there were two predecessors before this simplification, or if the
+ // PHI node contained all the same value except for the one we just
+ // substituted, the PHI node may be deleted. Don't iterate through it the
+ // last time.
+ if (SI->getCondition() != PN) return;
}
}