Newer
Older
//===- SCCP.cpp - Sparse Conditional Constant Propogation -----------------===//
//
// This file implements sparse conditional constant propogation and merging:
//
// Specifically, this:
// * Assumes values are constant unless proven otherwise
// * Assumes BasicBlocks are dead unless proven otherwise
// * Proves values to be constant, and replaces them with constants
// . Proves conditional branches constant, and unconditionalizes them
// * Folds multiple identical constants in the constant pool together
//
// Notice that:
// * This pass has a habit of making definitions be dead. It is a good idea
// to to run a DCE pass sometime after running this pass.
//
//===----------------------------------------------------------------------===//
Chris Lattner
committed
#include "llvm/Transforms/Scalar/ConstantProp.h"
#include "llvm/ConstantHandling.h"
#include "llvm/iPHINode.h"
#include "llvm/iMemory.h"
#include "llvm/iTerminators.h"
#include "llvm/iOther.h"
#include "llvm/Pass.h"
#include "llvm/Support/InstVisitor.h"
#include "Support/STLExtras.h"
#include <algorithm>
#include <set>
#include <iostream>
using std::cerr;
// InstVal class - This class represents the different lattice values that an
// instruction may occupy. It is a simple class with value semantics.
namespace {
class InstVal {
enum {
undefined, // This instruction has no known value
constant, // This instruction has a constant value
// Range, // This instruction is known to fall within a range
overdefined // This instruction has an unknown value
} LatticeValue; // The current lattice position
Constant *ConstantVal; // If Constant value, the current value
inline InstVal() : LatticeValue(undefined), ConstantVal(0) {}
// markOverdefined - Return true if this is a new status to be in...
inline bool markOverdefined() {
if (LatticeValue != overdefined) {
LatticeValue = overdefined;
return true;
}
return false;
}
// markConstant - Return true if this is a new status for us...
inline bool markConstant(Constant *V) {
if (LatticeValue != constant) {
LatticeValue = constant;
ConstantVal = V;
return true;
} else {
assert(ConstantVal == V && "Marking constant with different value");
}
return false;
}
inline bool isUndefined() const { return LatticeValue == undefined; }
inline bool isConstant() const { return LatticeValue == constant; }
inline bool isOverdefined() const { return LatticeValue == overdefined; }
inline Constant *getConstant() const { return ConstantVal; }
} // end anonymous namespace
//===----------------------------------------------------------------------===//
// SCCP Class
//
// This class does all of the work of Sparse Conditional Constant Propogation.
//
namespace {
class SCCP : public FunctionPass, public InstVisitor<SCCP> {
std::set<BasicBlock*> BBExecutable;// The basic blocks that are executable
std::map<Value*, InstVal> ValueState; // The state each value is in...
std::vector<Instruction*> InstWorkList;// The instruction work list
std::vector<BasicBlock*> BBWorkList; // The BasicBlock work list
public:
const char *getPassName() const {
return "Sparse Conditional Constant Propogation";
}
// runOnFunction - Run the Sparse Conditional Constant Propogation algorithm,
// and return true if the function was modified.
bool runOnFunction(Function *F);
virtual void getAnalysisUsage(AnalysisUsage &AU) const {
// FIXME: SCCP does not preserve the CFG because it folds terminators!
//AU.preservesCFG();
}
//===--------------------------------------------------------------------===//
// The implementation of this class
//
private:
friend class InstVisitor<SCCP>; // Allow callbacks from visitor
// markValueOverdefined - Make a value be marked as "constant". If the value
// is not already a constant, add it to the instruction work list so that
// the users of the instruction are updated later.
//
inline bool markConstant(Instruction *I, Constant *V) {
//cerr << "markConstant: " << V << " = " << I;
if (ValueState[I].markConstant(V)) {
InstWorkList.push_back(I);
return true;
}
return false;
}
// markValueOverdefined - Make a value be marked as "overdefined". If the
// value is not already overdefined, add it to the instruction work list so
// that the users of the instruction are updated later.
//
inline bool markOverdefined(Value *V) {
if (ValueState[V].markOverdefined()) {
if (Instruction *I = dyn_cast<Instruction>(V)) {
//cerr << "markOverdefined: " << V;
InstWorkList.push_back(I); // Only instructions go on the work list
}
return true;
}
return false;
}
// getValueState - Return the InstVal object that corresponds to the value.
// This function is neccesary because not all values should start out in the
// underdefined state... Argument's should be overdefined, and
// constants should be marked as constants. If a value is not known to be an
// Instruction object, then use this accessor to get its value from the map.
//
inline InstVal &getValueState(Value *V) {
std::map<Value*, InstVal>::iterator I = ValueState.find(V);
if (I != ValueState.end()) return I->second; // Common case, in the map
if (Constant *CPV = dyn_cast<Constant>(V)) { // Constants are constant
ValueState[CPV].markConstant(CPV);
} else if (isa<Argument>(V)) { // Arguments are overdefined
ValueState[V].markOverdefined();
}
// All others are underdefined by default...
return ValueState[V];
}
// markExecutable - Mark a basic block as executable, adding it to the BB
// work list if it is not already executable...
//
void markExecutable(BasicBlock *BB) {
if (BBExecutable.count(BB)) return;
//cerr << "Marking BB Executable: " << BB;
BBExecutable.insert(BB); // Basic block is executable!
BBWorkList.push_back(BB); // Add the block to the work list!
}
// visit implementations - Something changed in this instruction... Either an
// operand made a transition, or the instruction is newly executable. Change
// the value type of I to reflect these changes if appropriate.
//
void visitPHINode(PHINode *I);
// Terminators
void visitReturnInst(ReturnInst *I) { /*does not have an effect*/ }
void visitBranchInst(BranchInst *I);
void visitSwitchInst(SwitchInst *I);
void visitUnaryOperator(Instruction *I);
void visitCastInst(CastInst *I) { visitUnaryOperator(I); }
void visitBinaryOperator(Instruction *I);
void visitShiftInst(ShiftInst *I) { visitBinaryOperator(I); }
// Instructions that cannot be folded away...
void visitMemAccessInst (Instruction *I) { markOverdefined(I); }
void visitCallInst (Instruction *I) { markOverdefined(I); }
void visitInvokeInst (Instruction *I) { markOverdefined(I); }
void visitAllocationInst(Instruction *I) { markOverdefined(I); }
void visitFreeInst (Instruction *I) { markOverdefined(I); }
void visitInstruction(Instruction *I) {
// If a new instruction is added to LLVM that we don't handle...
cerr << "SCCP: Don't know how to handle: " << I;
markOverdefined(I); // Just in case
}
// OperandChangedState - This method is invoked on all of the users of an
// instruction that was just changed state somehow.... Based on this
// information, we need to update the specified user of this instruction.
//
void OperandChangedState(User *U);
};
} // end anonymous namespace
// createSCCPPass - This is the public interface to this file...
//
Pass *createSCCPPass() {
return new SCCP();
}
//===----------------------------------------------------------------------===//
// SCCP Class Implementation
// runOnFunction() - Run the Sparse Conditional Constant Propogation algorithm,
// and return true if the function was modified.
bool SCCP::runOnFunction(Function *F) {
// Mark the first block of the function as being executable...
markExecutable(F->front());
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
// Process the work lists until their are empty!
while (!BBWorkList.empty() || !InstWorkList.empty()) {
// Process the instruction work list...
while (!InstWorkList.empty()) {
Instruction *I = InstWorkList.back();
InstWorkList.pop_back();
//cerr << "\nPopped off I-WL: " << I;
// "I" got into the work list because it either made the transition from
// bottom to constant, or to Overdefined.
//
// Update all of the users of this instruction's value...
//
for_each(I->use_begin(), I->use_end(),
bind_obj(this, &SCCP::OperandChangedState));
}
// Process the basic block work list...
while (!BBWorkList.empty()) {
BasicBlock *BB = BBWorkList.back();
BBWorkList.pop_back();
//cerr << "\nPopped off BBWL: " << BB;
// If this block only has a single successor, mark it as executable as
// well... if not, terminate the do loop.
//
if (BB->getTerminator()->getNumSuccessors() == 1)
// Notify all instructions in this basic block that they are newly
// executable.
visit(BB);
}
}
#if 0
for (Function::iterator BBI = F->begin(), BBEnd = F->end();
if (!BBExecutable.count(*BBI))
cerr << "BasicBlock Dead:" << *BBI;
#endif
// Iterate over all of the instructions in a function, replacing them with
// constants if we have found them to be of constant values.
//
bool MadeChanges = false;
for (Function::iterator FI = F->begin(), FE = F->end(); FI != FE; ++FI) {
BasicBlock *BB = *FI;
for (BasicBlock::iterator BI = BB->begin(); BI != BB->end();) {
Instruction *Inst = *BI;
InstVal &IV = ValueState[Inst];
if (IV.isConstant()) {
Constant *Const = IV.getConstant();
// cerr << "Constant: " << Inst << " is: " << Const;
// Replaces all of the uses of a variable with uses of the constant.
Inst->replaceAllUsesWith(Const);
// Remove the operator from the list of definitions... and delete it.
delete BB->getInstList().remove(BI);
// Hey, we just changed something!
MadeChanges = true;
// Do NOT advance the iterator, skipping the next instruction...
continue;
} else if (TerminatorInst *TI = dyn_cast<TerminatorInst>(Inst)) {
MadeChanges |= ConstantFoldTerminator(BB, BI, TI);
// Reset state so that the next invokation will have empty data structures
BBExecutable.clear();
ValueState.clear();
// Merge identical constants last: this is important because we may have just
// introduced constants that already exist, and we don't want to pollute later
// stages with extraneous constants.
//
// visit Implementations - Something changed in this instruction... Either an
// operand made a transition, or the instruction is newly executable. Change
// the value type of I to reflect these changes if appropriate. This method
// makes sure to do the following actions:
//
// 1. If a phi node merges two constants in, and has conflicting value coming
// from different branches, or if the PHI node merges in an overdefined
// value, then the PHI node becomes overdefined.
// 2. If a phi node merges only constants in, and they all agree on value, the
// PHI node becomes a constant value equal to that.
// 3. If V <- x (op) y && isConstant(x) && isConstant(y) V = Constant
// 4. If V <- x (op) y && (isOverdefined(x) || isOverdefined(y)) V = Overdefined
// 5. If V <- MEM or V <- CALL or V <- (unknown) then V = Overdefined
// 6. If a conditional branch has a value that is constant, make the selected
// destination executable
// 7. If a conditional branch has a value that is overdefined, make all
// successors executable.
//
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
void SCCP::visitPHINode(PHINode *PN) {
unsigned NumValues = PN->getNumIncomingValues(), i;
InstVal *OperandIV = 0;
// Look at all of the executable operands of the PHI node. If any of them
// are overdefined, the PHI becomes overdefined as well. If they are all
// constant, and they agree with each other, the PHI becomes the identical
// constant. If they are constant and don't agree, the PHI is overdefined.
// If there are no executable operands, the PHI remains undefined.
//
for (i = 0; i < NumValues; ++i) {
if (BBExecutable.count(PN->getIncomingBlock(i))) {
InstVal &IV = getValueState(PN->getIncomingValue(i));
if (IV.isUndefined()) continue; // Doesn't influence PHI node.
if (IV.isOverdefined()) { // PHI node becomes overdefined!
markOverdefined(PN);
return;
}
if (OperandIV == 0) { // Grab the first value...
OperandIV = &IV;
} else { // Another value is being merged in!
// There is already a reachable operand. If we conflict with it,
// then the PHI node becomes overdefined. If we agree with it, we
// can continue on.
// Check to see if there are two different constants merging...
if (IV.getConstant() != OperandIV->getConstant()) {
// Yes there is. This means the PHI node is not constant.
// You must be overdefined poor PHI.
//
markOverdefined(PN); // The PHI node now becomes overdefined
return; // I'm done analyzing you
// If we exited the loop, this means that the PHI node only has constant
// arguments that agree with each other(and OperandIV is a pointer to one
// of their InstVal's) or OperandIV is null because there are no defined
// incoming arguments. If this is the case, the PHI remains undefined.
//
if (OperandIV) {
assert(OperandIV->isConstant() && "Should only be here for constants!");
markConstant(PN, OperandIV->getConstant()); // Aquire operand value
void SCCP::visitBranchInst(BranchInst *BI) {
if (BI->isUnconditional())
return; // Unconditional branches are already handled!
InstVal &BCValue = getValueState(BI->getCondition());
if (BCValue.isOverdefined()) {
// Overdefined condition variables mean the branch could go either way.
markExecutable(BI->getSuccessor(0));
markExecutable(BI->getSuccessor(1));
} else if (BCValue.isConstant()) {
// Constant condition variables mean the branch can only go a single way.
if (BCValue.getConstant() == ConstantBool::True)
markExecutable(BI->getSuccessor(0));
else
markExecutable(BI->getSuccessor(1));
}
void SCCP::visitSwitchInst(SwitchInst *SI) {
InstVal &SCValue = getValueState(SI->getCondition());
if (SCValue.isOverdefined()) { // Overdefined condition? All dests are exe
Chris Lattner
committed
for(unsigned i = 0, E = SI->getNumSuccessors(); i != E; ++i)
markExecutable(SI->getSuccessor(i));
} else if (SCValue.isConstant()) {
Constant *CPV = SCValue.getConstant();
// Make sure to skip the "default value" which isn't a value
for (unsigned i = 1, E = SI->getNumSuccessors(); i != E; ++i) {
if (SI->getSuccessorValue(i) == CPV) {// Found the right branch...
markExecutable(SI->getSuccessor(i));
return;
// Constant value not equal to any of the branches... must execute
// default branch then...
markExecutable(SI->getDefaultDest());
void SCCP::visitUnaryOperator(Instruction *I) {
Value *V = I->getOperand(0);
InstVal &VState = getValueState(V);
if (VState.isOverdefined()) { // Inherit overdefinedness of operand
} else if (VState.isConstant()) { // Propogate constant value
Constant *Result = isa<CastInst>(I)
? ConstantFoldCastInstruction(VState.getConstant(), I->getType())
: ConstantFoldUnaryInstruction(I->getOpcode(), VState.getConstant());
if (Result) {
// This instruction constant folds!
markConstant(I, Result);
} else {
markOverdefined(I); // Don't know how to fold this instruction. :(
}
}
}
// Handle BinaryOperators and Shift Instructions...
void SCCP::visitBinaryOperator(Instruction *I) {
InstVal &V1State = getValueState(I->getOperand(0));
InstVal &V2State = getValueState(I->getOperand(1));
if (V1State.isOverdefined() || V2State.isOverdefined()) {
markOverdefined(I);
} else if (V1State.isConstant() && V2State.isConstant()) {
Constant *Result = ConstantFoldBinaryInstruction(I->getOpcode(),
V1State.getConstant(),
V2State.getConstant());
if (Result)
markConstant(I, Result); // This instruction constant folds!
else
markOverdefined(I); // Don't know how to fold this instruction. :(
}
}
// OperandChangedState - This method is invoked on all of the users of an
// instruction that was just changed state somehow.... Based on this
// information, we need to update the specified user of this instruction.
//
void SCCP::OperandChangedState(User *U) {
// Only instructions use other variable values!
if (!BBExecutable.count(I->getParent())) return; // Inst not executable yet!
visit(I);