diff options
| author | Roman Divacky <rdivacky@FreeBSD.org> | 2010-03-16 16:51:38 +0000 | 
|---|---|---|
| committer | Roman Divacky <rdivacky@FreeBSD.org> | 2010-03-16 16:51:38 +0000 | 
| commit | c69102774f9739c81ae1285ed9ae62405071c63c (patch) | |
| tree | 458dd25677a43aef6390ecadb4423817f00e08b0 /lib/Transforms/Scalar/CodeGenPrepare.cpp | |
| parent | ea5b2dd11c0526581803e7eb58224a2eabf191e6 (diff) | |
Notes
Diffstat (limited to 'lib/Transforms/Scalar/CodeGenPrepare.cpp')
| -rw-r--r-- | lib/Transforms/Scalar/CodeGenPrepare.cpp | 48 | 
1 files changed, 48 insertions, 0 deletions
diff --git a/lib/Transforms/Scalar/CodeGenPrepare.cpp b/lib/Transforms/Scalar/CodeGenPrepare.cpp index 7ceda1fa1f2c..50c96304db09 100644 --- a/lib/Transforms/Scalar/CodeGenPrepare.cpp +++ b/lib/Transforms/Scalar/CodeGenPrepare.cpp @@ -28,6 +28,7 @@  #include "llvm/Transforms/Utils/AddrModeMatcher.h"  #include "llvm/Transforms/Utils/BasicBlockUtils.h"  #include "llvm/Transforms/Utils/Local.h" +#include "llvm/Transforms/Utils/BuildLibCalls.h"  #include "llvm/ADT/DenseMap.h"  #include "llvm/ADT/SmallSet.h"  #include "llvm/Assembly/Writer.h" @@ -36,6 +37,7 @@  #include "llvm/Support/GetElementPtrTypeIterator.h"  #include "llvm/Support/PatternMatch.h"  #include "llvm/Support/raw_ostream.h" +#include "llvm/Support/IRBuilder.h"  using namespace llvm;  using namespace llvm::PatternMatch; @@ -72,6 +74,7 @@ namespace {                              DenseMap<Value*,Value*> &SunkAddrs);      bool OptimizeInlineAsmInst(Instruction *I, CallSite CS,                                 DenseMap<Value*,Value*> &SunkAddrs); +    bool OptimizeCallInst(CallInst *CI);      bool MoveExtToFormExtLoad(Instruction *I);      bool OptimizeExtUses(Instruction *I);      void findLoopBackEdges(const Function &F); @@ -537,6 +540,47 @@ static bool OptimizeCmpExpression(CmpInst *CI) {    return MadeChange;  } +namespace { +class CodeGenPrepareFortifiedLibCalls : public SimplifyFortifiedLibCalls { +protected: +  void replaceCall(Value *With) { +    CI->replaceAllUsesWith(With); +    CI->eraseFromParent(); +  } +  bool isFoldable(unsigned SizeCIOp, unsigned, bool) const { +    if (ConstantInt *SizeCI = dyn_cast<ConstantInt>(CI->getOperand(SizeCIOp))) +      return SizeCI->isAllOnesValue(); +    return false; +  } +}; +} // end anonymous namespace + +bool CodeGenPrepare::OptimizeCallInst(CallInst *CI) { +  // Lower all uses of llvm.objectsize.* +  IntrinsicInst *II = dyn_cast<IntrinsicInst>(CI); +  if (II && II->getIntrinsicID() == Intrinsic::objectsize) { +    bool Min = (cast<ConstantInt>(II->getOperand(2))->getZExtValue() == 1); +    const Type *ReturnTy = CI->getType(); +    Constant *RetVal = ConstantInt::get(ReturnTy, Min ? 0 : -1ULL);     +    CI->replaceAllUsesWith(RetVal); +    CI->eraseFromParent(); +    return true; +  } + +  // From here on out we're working with named functions. +  if (CI->getCalledFunction() == 0) return false; +   +  // We'll need TargetData from here on out. +  const TargetData *TD = TLI ? TLI->getTargetData() : 0; +  if (!TD) return false; +   +  // Lower all default uses of _chk calls.  This is very similar +  // to what InstCombineCalls does, but here we are only lowering calls +  // that have the default "don't know" as the objectsize.  Anything else +  // should be left alone. +  CodeGenPrepareFortifiedLibCalls Simplifier; +  return Simplifier.fold(CI, TD); +}  //===----------------------------------------------------------------------===//  // Memory Optimization  //===----------------------------------------------------------------------===// @@ -913,6 +957,10 @@ bool CodeGenPrepare::OptimizeBlock(BasicBlock &BB) {          } else            // Sink address computing for memory operands into the block.            MadeChange |= OptimizeInlineAsmInst(I, &(*CI), SunkAddrs); +      } else { +        // Other CallInst optimizations that don't need to muck with the +        // enclosing iterator here. +        MadeChange |= OptimizeCallInst(CI);        }      }    }  | 
