X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FTransforms%2FIPO%2FIPConstantPropagation.cpp;h=af541d1552545b3641426dcb320110e697cf6849;hb=690d7b2a89f76fd450f38564ce4e6732d853eadc;hp=1d65562f58d80bb4ce58651413376633a57d2105;hpb=5ed3b894c913b0d4f4a0f3bd47f3ea1adf6eb52e;p=oota-llvm.git diff --git a/lib/Transforms/IPO/IPConstantPropagation.cpp b/lib/Transforms/IPO/IPConstantPropagation.cpp index 1d65562f58d..af541d15525 100644 --- a/lib/Transforms/IPO/IPConstantPropagation.cpp +++ b/lib/Transforms/IPO/IPConstantPropagation.cpp @@ -15,30 +15,32 @@ // //===----------------------------------------------------------------------===// -#define DEBUG_TYPE "ipconstprop" #include "llvm/Transforms/IPO.h" -#include "llvm/Constants.h" -#include "llvm/Instructions.h" -#include "llvm/Module.h" -#include "llvm/Pass.h" -#include "llvm/Analysis/ValueTracking.h" -#include "llvm/Support/CallSite.h" -#include "llvm/Support/Compiler.h" -#include "llvm/ADT/Statistic.h" #include "llvm/ADT/SmallVector.h" +#include "llvm/ADT/Statistic.h" +#include "llvm/Analysis/ValueTracking.h" +#include "llvm/IR/CallSite.h" +#include "llvm/IR/Constants.h" +#include "llvm/IR/Instructions.h" +#include "llvm/IR/Module.h" +#include "llvm/Pass.h" using namespace llvm; +#define DEBUG_TYPE "ipconstprop" + STATISTIC(NumArgumentsProped, "Number of args turned into constants"); STATISTIC(NumReturnValProped, "Number of return values turned into constants"); namespace { /// IPCP - The interprocedural constant propagation pass /// - struct VISIBILITY_HIDDEN IPCP : public ModulePass { + struct IPCP : public ModulePass { static char ID; // Pass identification, replacement for typeid - IPCP() : ModulePass(&ID) {} + IPCP() : ModulePass(ID) { + initializeIPCPPass(*PassRegistry::getPassRegistry()); + } - bool runOnModule(Module &M); + bool runOnModule(Module &M) override; private: bool PropagateConstantsIntoArguments(Function &F); bool PropagateConstantReturn(Function &F); @@ -46,8 +48,8 @@ namespace { } char IPCP::ID = 0; -static RegisterPass -X("ipconstprop", "Interprocedural constant propagation"); +INITIALIZE_PASS(IPCP, "ipconstprop", + "Interprocedural constant propagation", false, false) ModulePass *llvm::createIPConstantPropagationPass() { return new IPCP(); } @@ -63,7 +65,7 @@ bool IPCP::runOnModule(Module &M) { if (!I->isDeclaration()) { // Delete any klingons. I->removeDeadConstantUsers(); - if (I->hasInternalLinkage()) + if (I->hasLocalLinkage()) LocalChange |= PropagateConstantsIntoArguments(*I); Changed |= PropagateConstantReturn(*I); } @@ -85,14 +87,19 @@ bool IPCP::PropagateConstantsIntoArguments(Function &F) { ArgumentConstants.resize(F.arg_size()); unsigned NumNonconstant = 0; - for (Value::use_iterator UI = F.use_begin(), E = F.use_end(); UI != E; ++UI) { + for (Use &U : F.uses()) { + User *UR = U.getUser(); + // Ignore blockaddress uses. + if (isa(UR)) continue; + // Used by a non-instruction, or not the callee of a function, do not // transform. - if (UI.getOperandNo() != 0 || - (!isa(*UI) && !isa(*UI))) + if (!isa(UR) && !isa(UR)) return false; - CallSite CS = CallSite::get(cast(*UI)); + CallSite CS(cast(UR)); + if (!CS.isCallee(&U)) + return false; // Check out all of the potentially constant arguments. Note that we don't // inspect varargs here. @@ -106,7 +113,7 @@ bool IPCP::PropagateConstantsIntoArguments(Function &F) { continue; Constant *C = dyn_cast(*AI); - if (C && ArgumentConstants[i].first == 0) { + if (C && ArgumentConstants[i].first == nullptr) { ArgumentConstants[i].first = C; // First constant seen. } else if (C && ArgumentConstants[i].first == C) { // Still the constant value we think it is. @@ -128,11 +135,12 @@ bool IPCP::PropagateConstantsIntoArguments(Function &F) { Function::arg_iterator AI = F.arg_begin(); for (unsigned i = 0, e = ArgumentConstants.size(); i != e; ++i, ++AI) { // Do we have a constant argument? - if (ArgumentConstants[i].second || AI->use_empty()) + if (ArgumentConstants[i].second || AI->use_empty() || + AI->hasInAllocaAttr() || (AI->hasByValAttr() && !F.onlyReadsMemory())) continue; Value *V = ArgumentConstants[i].first; - if (V == 0) V = UndefValue::get(AI->getType()); + if (!V) V = UndefValue::get(AI->getType()); AI->replaceAllUsesWith(V); ++NumArgumentsProped; MadeChange = true; @@ -150,17 +158,17 @@ bool IPCP::PropagateConstantsIntoArguments(Function &F) { // callers will be updated to use the value they pass in directly instead of // using the return value. bool IPCP::PropagateConstantReturn(Function &F) { - if (F.getReturnType() == Type::VoidTy) + if (F.getReturnType()->isVoidTy()) return false; // No return value. // If this function could be overridden later in the link stage, we can't // propagate information about its results into callers. if (F.mayBeOverridden()) return false; - + // Check to see if this function returns a constant. SmallVector RetVals; - const StructType *STy = dyn_cast(F.getReturnType()); + StructType *STy = dyn_cast(F.getReturnType()); if (STy) for (unsigned i = 0, e = STy->getNumElements(); i < e; ++i) RetVals.push_back(UndefValue::get(STy->getElementType(i))); @@ -170,10 +178,6 @@ bool IPCP::PropagateConstantReturn(Function &F) { unsigned NumNonConstant = 0; for (Function::iterator BB = F.begin(), E = F.end(); BB != E; ++BB) if (ReturnInst *RI = dyn_cast(BB->getTerminator())) { - // Return type does not match operand type, this is an old style multiple - // return - bool OldReturn = (F.getReturnType() != RI->getOperand(0)->getType()); - for (unsigned i = 0, e = RetVals.size(); i != e; ++i) { // Already found conflicting return values? Value *RV = RetVals[i]; @@ -182,8 +186,8 @@ bool IPCP::PropagateConstantReturn(Function &F) { // Find the returned value Value *V; - if (!STy || OldReturn) - V = RI->getOperand(i); + if (!STy) + V = RI->getOperand(0); else V = FindInsertedValue(RI->getOperand(0), i); @@ -206,8 +210,8 @@ bool IPCP::PropagateConstantReturn(Function &F) { } // Different or no known return value? Don't propagate this return // value. - RetVals[i] = 0; - // All values non constant? Stop looking. + RetVals[i] = nullptr; + // All values non-constant? Stop looking. if (++NumNonConstant == RetVals.size()) return false; } @@ -217,13 +221,13 @@ bool IPCP::PropagateConstantReturn(Function &F) { // over all users, replacing any uses of the return value with the returned // constant. bool MadeChange = false; - for (Value::use_iterator UI = F.use_begin(), E = F.use_end(); UI != E; ++UI) { - CallSite CS = CallSite::get(*UI); + for (Use &U : F.uses()) { + CallSite CS(U.getUser()); Instruction* Call = CS.getInstruction(); // Not a call instruction or a call instruction that's not calling F // directly? - if (!Call || UI.getOperandNo() != 0) + if (!Call || !CS.isCallee(&U)) continue; // Call result not used? @@ -232,7 +236,7 @@ bool IPCP::PropagateConstantReturn(Function &F) { MadeChange = true; - if (STy == 0) { + if (!STy) { Value* New = RetVals[0]; if (Argument *A = dyn_cast(New)) // Was an argument returned? Then find the corresponding argument in @@ -241,18 +245,13 @@ bool IPCP::PropagateConstantReturn(Function &F) { Call->replaceAllUsesWith(New); continue; } - - for (Value::use_iterator I = Call->use_begin(), E = Call->use_end(); - I != E;) { - Instruction *Ins = dyn_cast(*I); + + for (auto I = Call->user_begin(), E = Call->user_end(); I != E;) { + Instruction *Ins = cast(*I); // Increment now, so we can remove the use ++I; - // Not an instruction? Ignore - if (!Ins) - continue; - // Find the index of the retval to replace with int index = -1; if (ExtractValueInst *EV = dyn_cast(Ins))