diff options
Diffstat (limited to 'lib/Transforms')
24 files changed, 249 insertions, 233 deletions
diff --git a/lib/Transforms/Hello/Makefile b/lib/Transforms/Hello/Makefile index c5e75d4..46f8098 100644 --- a/lib/Transforms/Hello/Makefile +++ b/lib/Transforms/Hello/Makefile @@ -11,6 +11,7 @@ LEVEL = ../../.. LIBRARYNAME = LLVMHello LOADABLE_MODULE = 1 USEDLIBS = +CXXFLAGS = -fno-rtti include $(LEVEL)/Makefile.common diff --git a/lib/Transforms/IPO/Inliner.cpp b/lib/Transforms/IPO/Inliner.cpp index 5725db1..0990278 100644 --- a/lib/Transforms/IPO/Inliner.cpp +++ b/lib/Transforms/IPO/Inliner.cpp @@ -171,7 +171,16 @@ static bool InlineCallIfPossible(CallSite CS, CallGraph &CG, return true; } - + +unsigned Inliner::getInlineThreshold(Function* Caller) const { + if (Caller && !Caller->isDeclaration() && + Caller->hasFnAttr(Attribute::OptimizeForSize) && + InlineLimit.getNumOccurrences() == 0) + return 50; + else + return InlineThreshold; +} + /// shouldInline - Return true if the inliner should attempt to inline /// at the given CallSite. bool Inliner::shouldInline(CallSite CS) { @@ -190,14 +199,8 @@ bool Inliner::shouldInline(CallSite CS) { } int Cost = IC.getValue(); - int CurrentThreshold = InlineThreshold; Function *Caller = CS.getCaller(); - if (Caller && !Caller->isDeclaration() && - Caller->hasFnAttr(Attribute::OptimizeForSize) && - InlineLimit.getNumOccurrences() == 0 && - InlineThreshold != 50) - CurrentThreshold = 50; - + int CurrentThreshold = getInlineThreshold(Caller); float FudgeFactor = getInlineFudgeFactor(CS); if (Cost >= (int)(CurrentThreshold * FudgeFactor)) { DEBUG(dbgs() << " NOT Inlining: cost=" << Cost @@ -233,13 +236,8 @@ bool Inliner::shouldInline(CallSite CS) { outerCallsFound = true; int Cost2 = IC2.getValue(); - int CurrentThreshold2 = InlineThreshold; Function *Caller2 = CS2.getCaller(); - if (Caller2 && !Caller2->isDeclaration() && - Caller2->hasFnAttr(Attribute::OptimizeForSize) && - InlineThreshold != 50) - CurrentThreshold2 = 50; - + int CurrentThreshold2 = getInlineThreshold(Caller2); float FudgeFactor2 = getInlineFudgeFactor(CS2); if (Cost2 >= (int)(CurrentThreshold2 * FudgeFactor2)) diff --git a/lib/Transforms/IPO/Makefile b/lib/Transforms/IPO/Makefile index 5c42374..fd018c4 100644 --- a/lib/Transforms/IPO/Makefile +++ b/lib/Transforms/IPO/Makefile @@ -10,6 +10,7 @@ LEVEL = ../../.. LIBRARYNAME = LLVMipo BUILD_ARCHIVE = 1 +CXXFLAGS = -fno-rtti include $(LEVEL)/Makefile.common diff --git a/lib/Transforms/IPO/StripSymbols.cpp b/lib/Transforms/IPO/StripSymbols.cpp index ae88d9e..0e0d83a 100644 --- a/lib/Transforms/IPO/StripSymbols.cpp +++ b/lib/Transforms/IPO/StripSymbols.cpp @@ -147,7 +147,7 @@ static void StripSymtab(ValueSymbolTable &ST, bool PreserveDbgInfo) { // Strip the symbol table of its names. static void StripTypeSymtab(TypeSymbolTable &ST, bool PreserveDbgInfo) { for (TypeSymbolTable::iterator TI = ST.begin(), E = ST.end(); TI != E; ) { - if (PreserveDbgInfo && strncmp(TI->first.c_str(), "llvm.dbg", 8) == 0) + if (PreserveDbgInfo && StringRef(TI->first).startswith("llvm.dbg")) ++TI; else ST.remove(TI++); diff --git a/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp b/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp index af300fc..fa7bb12 100644 --- a/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp +++ b/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp @@ -1751,6 +1751,11 @@ Instruction *InstCombiner::visitXor(BinaryOperator &I) { return BinaryOperator::CreateOr(NotX, NotY); return BinaryOperator::CreateAnd(NotX, NotY); } + + } else if (Op0I->getOpcode() == Instruction::AShr) { + // ~(~X >>s Y) --> (X >>s Y) + if (Value *Op0NotVal = dyn_castNotVal(Op0I->getOperand(0))) + return BinaryOperator::CreateAShr(Op0NotVal, Op0I->getOperand(1)); } } } diff --git a/lib/Transforms/InstCombine/InstCombineCasts.cpp b/lib/Transforms/InstCombine/InstCombineCasts.cpp index e018b35..f25dd35 100644 --- a/lib/Transforms/InstCombine/InstCombineCasts.cpp +++ b/lib/Transforms/InstCombine/InstCombineCasts.cpp @@ -955,6 +955,19 @@ Instruction *InstCombiner::visitSExt(SExtInst &CI) { ShAmt); } + // If this input is a trunc from our destination, then turn sext(trunc(x)) + // into shifts. + if (TruncInst *TI = dyn_cast<TruncInst>(Src)) + if (TI->hasOneUse() && TI->getOperand(0)->getType() == DestTy) { + uint32_t SrcBitSize = SrcTy->getScalarSizeInBits(); + uint32_t DestBitSize = DestTy->getScalarSizeInBits(); + + // We need to emit a shl + ashr to do the sign extend. + Value *ShAmt = ConstantInt::get(DestTy, DestBitSize-SrcBitSize); + Value *Res = Builder->CreateShl(TI->getOperand(0), ShAmt, "sext"); + return BinaryOperator::CreateAShr(Res, ShAmt); + } + // If the input is a shl/ashr pair of a same constant, then this is a sign // extension from a smaller value. If we could trust arbitrary bitwidth // integers, we could turn this into a truncate to the smaller bit and then diff --git a/lib/Transforms/InstCombine/InstCombineLoadStoreAlloca.cpp b/lib/Transforms/InstCombine/InstCombineLoadStoreAlloca.cpp index 6c0ecc9..ae728dd 100644 --- a/lib/Transforms/InstCombine/InstCombineLoadStoreAlloca.cpp +++ b/lib/Transforms/InstCombine/InstCombineLoadStoreAlloca.cpp @@ -366,7 +366,7 @@ Instruction *InstCombiner::visitStoreInst(StoreInst &SI) { // alloca dead. // If the RHS is an alloca with a two uses, the other one being a // llvm.dbg.declare, zapify the store and the declare, making the - // alloca dead. We must do this to prevent declare's from affecting + // alloca dead. We must do this to prevent declares from affecting // codegen. if (!SI.isVolatile()) { if (Ptr->hasOneUse()) { @@ -408,8 +408,6 @@ Instruction *InstCombiner::visitStoreInst(StoreInst &SI) { --BBI; // Don't count debug info directives, lest they affect codegen, // and we skip pointer-to-pointer bitcasts, which are NOPs. - // It is necessary for correctness to skip those that feed into a - // llvm.dbg.declare, as these are not present when debugging is off. if (isa<DbgInfoIntrinsic>(BBI) || (isa<BitCastInst>(BBI) && isa<PointerType>(BBI->getType()))) { ScanInsts++; @@ -475,9 +473,8 @@ Instruction *InstCombiner::visitStoreInst(StoreInst &SI) { // If this store is the last instruction in the basic block (possibly - // excepting debug info instructions and the pointer bitcasts that feed - // into them), and if the block ends with an unconditional branch, try - // to move it to the successor block. + // excepting debug info instructions), and if the block ends with an + // unconditional branch, try to move it to the successor block. BBI = &SI; do { ++BBI; diff --git a/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp b/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp index 6afc0cd..2e26a75 100644 --- a/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp +++ b/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp @@ -407,7 +407,7 @@ Instruction *InstCombiner::visitUDiv(BinaryOperator &I) { return Common; if (ConstantInt *C = dyn_cast<ConstantInt>(Op1)) { - // X udiv C^2 -> X >> C + // X udiv 2^C -> X >> C // Check to see if this is an unsigned division with an exact power of 2, // if so, convert to a right shift. if (C->getValue().isPowerOf2()) // 0 not included in isPowerOf2 diff --git a/lib/Transforms/InstCombine/InstCombineShifts.cpp b/lib/Transforms/InstCombine/InstCombineShifts.cpp index fe91da1..321c91d 100644 --- a/lib/Transforms/InstCombine/InstCombineShifts.cpp +++ b/lib/Transforms/InstCombine/InstCombineShifts.cpp @@ -404,12 +404,26 @@ Instruction *InstCombiner::visitAShr(BinaryOperator &I) { if (ConstantInt *Op1C = dyn_cast<ConstantInt>(Op1)) { // If the input is a SHL by the same constant (ashr (shl X, C), C), then we - // have a sign-extend idiom. If the input value is known to already be sign - // extended enough, delete the extension. + // have a sign-extend idiom. Value *X; - if (match(Op0, m_Shl(m_Value(X), m_Specific(Op1))) && - ComputeNumSignBits(X) > Op1C->getZExtValue()) - return ReplaceInstUsesWith(I, X); + if (match(Op0, m_Shl(m_Value(X), m_Specific(Op1)))) { + // If the input value is known to already be sign extended enough, delete + // the extension. + if (ComputeNumSignBits(X) > Op1C->getZExtValue()) + return ReplaceInstUsesWith(I, X); + + // If the input is an extension from the shifted amount value, e.g. + // %x = zext i8 %A to i32 + // %y = shl i32 %x, 24 + // %z = ashr %y, 24 + // then turn this into "z = sext i8 A to i32". + if (ZExtInst *ZI = dyn_cast<ZExtInst>(X)) { + uint32_t SrcBits = ZI->getOperand(0)->getType()->getScalarSizeInBits(); + uint32_t DestBits = ZI->getType()->getScalarSizeInBits(); + if (Op1C->getZExtValue() == DestBits-SrcBits) + return new SExtInst(ZI->getOperand(0), ZI->getType()); + } + } } // See if we can turn a signed shr into an unsigned shr. diff --git a/lib/Transforms/InstCombine/Makefile b/lib/Transforms/InstCombine/Makefile index 0c488e78..f9de42a 100644 --- a/lib/Transforms/InstCombine/Makefile +++ b/lib/Transforms/InstCombine/Makefile @@ -10,6 +10,7 @@ LEVEL = ../../.. LIBRARYNAME = LLVMInstCombine BUILD_ARCHIVE = 1 +CXXFLAGS = -fno-rtti include $(LEVEL)/Makefile.common diff --git a/lib/Transforms/Instrumentation/Makefile b/lib/Transforms/Instrumentation/Makefile index 6cbc7a9..1238896 100644 --- a/lib/Transforms/Instrumentation/Makefile +++ b/lib/Transforms/Instrumentation/Makefile @@ -10,6 +10,7 @@ LEVEL = ../../.. LIBRARYNAME = LLVMInstrumentation BUILD_ARCHIVE = 1 +CXXFLAGS = -fno-rtti include $(LEVEL)/Makefile.common diff --git a/lib/Transforms/Instrumentation/OptimalEdgeProfiling.cpp b/lib/Transforms/Instrumentation/OptimalEdgeProfiling.cpp index 94b0671..5650150 100644 --- a/lib/Transforms/Instrumentation/OptimalEdgeProfiling.cpp +++ b/lib/Transforms/Instrumentation/OptimalEdgeProfiling.cpp @@ -130,7 +130,7 @@ bool OptimalEdgeProfiler::runOnModule(Module &M) { // actual MST is returned but the edges _not_ in the MST. ProfileInfo::EdgeWeights ECs = - getAnalysisID<ProfileInfo>(ProfileEstimatorPassID, *F).getEdgeWeights(F); + getAnalysis<ProfileInfo>(*F).getEdgeWeights(F); std::vector<ProfileInfo::EdgeWeight> EdgeVector(ECs.begin(), ECs.end()); MaximumSpanningTree<BasicBlock> MST (EdgeVector); std::stable_sort(MST.begin(),MST.end()); diff --git a/lib/Transforms/Scalar/CodeGenPrepare.cpp b/lib/Transforms/Scalar/CodeGenPrepare.cpp index 9c1b440..c3139a5 100644 --- a/lib/Transforms/Scalar/CodeGenPrepare.cpp +++ b/lib/Transforms/Scalar/CodeGenPrepare.cpp @@ -617,7 +617,23 @@ bool CodeGenPrepare::OptimizeMemoryInst(Instruction *MemoryInst, Value *Addr, TLI->getTargetData()->getIntPtrType(AccessTy->getContext()); Value *Result = 0; - // Start with the scale value. + + // Start with the base register. Do this first so that subsequent address + // matching finds it last, which will prevent it from trying to match it + // as the scaled value in case it happens to be a mul. That would be + // problematic if we've sunk a different mul for the scale, because then + // we'd end up sinking both muls. + if (AddrMode.BaseReg) { + Value *V = AddrMode.BaseReg; + if (isa<PointerType>(V->getType())) + V = new PtrToIntInst(V, IntPtrTy, "sunkaddr", InsertPt); + if (V->getType() != IntPtrTy) + V = CastInst::CreateIntegerCast(V, IntPtrTy, /*isSigned=*/true, + "sunkaddr", InsertPt); + Result = V; + } + + // Add the scale value. if (AddrMode.Scale) { Value *V = AddrMode.ScaledReg; if (V->getType() == IntPtrTy) { @@ -634,17 +650,6 @@ bool CodeGenPrepare::OptimizeMemoryInst(Instruction *MemoryInst, Value *Addr, V = BinaryOperator::CreateMul(V, ConstantInt::get(IntPtrTy, AddrMode.Scale), "sunkaddr", InsertPt); - Result = V; - } - - // Add in the base register. - if (AddrMode.BaseReg) { - Value *V = AddrMode.BaseReg; - if (isa<PointerType>(V->getType())) - V = new PtrToIntInst(V, IntPtrTy, "sunkaddr", InsertPt); - if (V->getType() != IntPtrTy) - V = CastInst::CreateIntegerCast(V, IntPtrTy, /*isSigned=*/true, - "sunkaddr", InsertPt); if (Result) Result = BinaryOperator::CreateAdd(Result, V, "sunkaddr", InsertPt); else diff --git a/lib/Transforms/Scalar/GVN.cpp b/lib/Transforms/Scalar/GVN.cpp index ac0d850..b29fe74 100644 --- a/lib/Transforms/Scalar/GVN.cpp +++ b/lib/Transforms/Scalar/GVN.cpp @@ -70,18 +70,44 @@ static cl::opt<bool> EnableLoadPRE("enable-load-pre", cl::init(true)); /// two values. namespace { struct Expression { - enum ExpressionOpcode { ADD, FADD, SUB, FSUB, MUL, FMUL, - UDIV, SDIV, FDIV, UREM, SREM, - FREM, SHL, LSHR, ASHR, AND, OR, XOR, ICMPEQ, - ICMPNE, ICMPUGT, ICMPUGE, ICMPULT, ICMPULE, - ICMPSGT, ICMPSGE, ICMPSLT, ICMPSLE, FCMPOEQ, - FCMPOGT, FCMPOGE, FCMPOLT, FCMPOLE, FCMPONE, - FCMPORD, FCMPUNO, FCMPUEQ, FCMPUGT, FCMPUGE, - FCMPULT, FCMPULE, FCMPUNE, EXTRACT, INSERT, - SHUFFLE, SELECT, TRUNC, ZEXT, SEXT, FPTOUI, - FPTOSI, UITOFP, SITOFP, FPTRUNC, FPEXT, - PTRTOINT, INTTOPTR, BITCAST, GEP, CALL, CONSTANT, - INSERTVALUE, EXTRACTVALUE, EMPTY, TOMBSTONE }; + enum ExpressionOpcode { + ADD = Instruction::Add, + FADD = Instruction::FAdd, + SUB = Instruction::Sub, + FSUB = Instruction::FSub, + MUL = Instruction::Mul, + FMUL = Instruction::FMul, + UDIV = Instruction::UDiv, + SDIV = Instruction::SDiv, + FDIV = Instruction::FDiv, + UREM = Instruction::URem, + SREM = Instruction::SRem, + FREM = Instruction::FRem, + SHL = Instruction::Shl, + LSHR = Instruction::LShr, + ASHR = Instruction::AShr, + AND = Instruction::And, + OR = Instruction::Or, + XOR = Instruction::Xor, + TRUNC = Instruction::Trunc, + ZEXT = Instruction::ZExt, + SEXT = Instruction::SExt, + FPTOUI = Instruction::FPToUI, + FPTOSI = Instruction::FPToSI, + UITOFP = Instruction::UIToFP, + SITOFP = Instruction::SIToFP, + FPTRUNC = Instruction::FPTrunc, + FPEXT = Instruction::FPExt, + PTRTOINT = Instruction::PtrToInt, + INTTOPTR = Instruction::IntToPtr, + BITCAST = Instruction::BitCast, + ICMPEQ, ICMPNE, ICMPUGT, ICMPUGE, ICMPULT, ICMPULE, + ICMPSGT, ICMPSGE, ICMPSLT, ICMPSLE, FCMPOEQ, + FCMPOGT, FCMPOGE, FCMPOLT, FCMPOLE, FCMPONE, + FCMPORD, FCMPUNO, FCMPUEQ, FCMPUGT, FCMPUGE, + FCMPULT, FCMPULE, FCMPUNE, EXTRACT, INSERT, + SHUFFLE, SELECT, GEP, CALL, CONSTANT, + INSERTVALUE, EXTRACTVALUE, EMPTY, TOMBSTONE }; ExpressionOpcode opcode; const Type* type; @@ -127,9 +153,7 @@ namespace { uint32_t nextValueNumber; - Expression::ExpressionOpcode getOpcode(BinaryOperator* BO); Expression::ExpressionOpcode getOpcode(CmpInst* C); - Expression::ExpressionOpcode getOpcode(CastInst* C); Expression create_expression(BinaryOperator* BO); Expression create_expression(CmpInst* C); Expression create_expression(ShuffleVectorInst* V); @@ -200,30 +224,6 @@ struct isPodLike<Expression> { static const bool value = true; }; //===----------------------------------------------------------------------===// // ValueTable Internal Functions //===----------------------------------------------------------------------===// -Expression::ExpressionOpcode ValueTable::getOpcode(BinaryOperator* BO) { - switch(BO->getOpcode()) { - default: // THIS SHOULD NEVER HAPPEN - llvm_unreachable("Binary operator with unknown opcode?"); - case Instruction::Add: return Expression::ADD; - case Instruction::FAdd: return Expression::FADD; - case Instruction::Sub: return Expression::SUB; - case Instruction::FSub: return Expression::FSUB; - case Instruction::Mul: return Expression::MUL; - case Instruction::FMul: return Expression::FMUL; - case Instruction::UDiv: return Expression::UDIV; - case Instruction::SDiv: return Expression::SDIV; - case Instruction::FDiv: return Expression::FDIV; - case Instruction::URem: return Expression::UREM; - case Instruction::SRem: return Expression::SREM; - case Instruction::FRem: return Expression::FREM; - case Instruction::Shl: return Expression::SHL; - case Instruction::LShr: return Expression::LSHR; - case Instruction::AShr: return Expression::ASHR; - case Instruction::And: return Expression::AND; - case Instruction::Or: return Expression::OR; - case Instruction::Xor: return Expression::XOR; - } -} Expression::ExpressionOpcode ValueTable::getOpcode(CmpInst* C) { if (isa<ICmpInst>(C)) { @@ -263,25 +263,6 @@ Expression::ExpressionOpcode ValueTable::getOpcode(CmpInst* C) { } } -Expression::ExpressionOpcode ValueTable::getOpcode(CastInst* C) { - switch(C->getOpcode()) { - default: // THIS SHOULD NEVER HAPPEN - llvm_unreachable("Cast operator with unknown opcode?"); - case Instruction::Trunc: return Expression::TRUNC; - case Instruction::ZExt: return Expression::ZEXT; - case Instruction::SExt: return Expression::SEXT; - case Instruction::FPToUI: return Expression::FPTOUI; - case Instruction::FPToSI: return Expression::FPTOSI; - case Instruction::UIToFP: return Expression::UITOFP; - case Instruction::SIToFP: return Expression::SITOFP; - case Instruction::FPTrunc: return Expression::FPTRUNC; - case Instruction::FPExt: return Expression::FPEXT; - case Instruction::PtrToInt: return Expression::PTRTOINT; - case Instruction::IntToPtr: return Expression::INTTOPTR; - case Instruction::BitCast: return Expression::BITCAST; - } -} - Expression ValueTable::create_expression(CallInst* C) { Expression e; @@ -302,7 +283,7 @@ Expression ValueTable::create_expression(BinaryOperator* BO) { e.varargs.push_back(lookup_or_add(BO->getOperand(1))); e.function = 0; e.type = BO->getType(); - e.opcode = getOpcode(BO); + e.opcode = static_cast<Expression::ExpressionOpcode>(BO->getOpcode()); return e; } @@ -325,7 +306,7 @@ Expression ValueTable::create_expression(CastInst* C) { e.varargs.push_back(lookup_or_add(C->getOperand(0))); e.function = 0; e.type = C->getType(); - e.opcode = getOpcode(C); + e.opcode = static_cast<Expression::ExpressionOpcode>(C->getOpcode()); return e; } diff --git a/lib/Transforms/Scalar/IndVarSimplify.cpp b/lib/Transforms/Scalar/IndVarSimplify.cpp index ce1307c..17f7d98 100644 --- a/lib/Transforms/Scalar/IndVarSimplify.cpp +++ b/lib/Transforms/Scalar/IndVarSimplify.cpp @@ -471,6 +471,13 @@ void IndVarSimplify::RewriteIVExpressions(Loop *L, const Type *LargestType, // Compute the final addrec to expand into code. const SCEV *AR = IU->getReplacementExpr(*UI); + // Evaluate the expression out of the loop, if possible. + if (!L->contains(UI->getUser())) { + const SCEV *ExitVal = SE->getSCEVAtScope(AR, L->getParentLoop()); + if (ExitVal->isLoopInvariant(L)) + AR = ExitVal; + } + // FIXME: It is an extremely bad idea to indvar substitute anything more // complex than affine induction variables. Doing so will put expensive // polynomial evaluations inside of the loop, and the str reduction pass @@ -522,11 +529,10 @@ void IndVarSimplify::RewriteIVExpressions(Loop *L, const Type *LargestType, Rewriter.clear(); // Now that we're done iterating through lists, clean up any instructions // which are now dead. - while (!DeadInsts.empty()) { - Instruction *Inst = dyn_cast_or_null<Instruction>(DeadInsts.pop_back_val()); - if (Inst) + while (!DeadInsts.empty()) + if (Instruction *Inst = + dyn_cast_or_null<Instruction>(DeadInsts.pop_back_val())) RecursivelyDeleteTriviallyDeadInstructions(Inst); - } } /// If there's a single exit block, sink any loop-invariant values that diff --git a/lib/Transforms/Scalar/Makefile b/lib/Transforms/Scalar/Makefile index cc42fd0..e18f30f 100644 --- a/lib/Transforms/Scalar/Makefile +++ b/lib/Transforms/Scalar/Makefile @@ -10,6 +10,7 @@ LEVEL = ../../.. LIBRARYNAME = LLVMScalarOpts BUILD_ARCHIVE = 1 +CXXFLAGS = -fno-rtti include $(LEVEL)/Makefile.common diff --git a/lib/Transforms/Scalar/ScalarReplAggregates.cpp b/lib/Transforms/Scalar/ScalarReplAggregates.cpp index 9e1e79a..f473480 100644 --- a/lib/Transforms/Scalar/ScalarReplAggregates.cpp +++ b/lib/Transforms/Scalar/ScalarReplAggregates.cpp @@ -85,10 +85,6 @@ namespace { /// isUnsafe - This is set to true if the alloca cannot be SROA'd. bool isUnsafe : 1; - /// needsCleanup - This is set to true if there is some use of the alloca - /// that requires cleanup. - bool needsCleanup : 1; - /// isMemCpySrc - This is true if this aggregate is memcpy'd from. bool isMemCpySrc : 1; @@ -96,15 +92,14 @@ namespace { bool isMemCpyDst : 1; AllocaInfo() - : isUnsafe(false), needsCleanup(false), - isMemCpySrc(false), isMemCpyDst(false) {} + : isUnsafe(false), isMemCpySrc(false), isMemCpyDst(false) {} }; unsigned SRThreshold; void MarkUnsafe(AllocaInfo &I) { I.isUnsafe = true; } - int isSafeAllocaToScalarRepl(AllocaInst *AI); + bool isSafeAllocaToScalarRepl(AllocaInst *AI); void isSafeForScalarRepl(Instruction *I, AllocaInst *AI, uint64_t Offset, AllocaInfo &Info); @@ -119,7 +114,6 @@ namespace { void DoScalarReplacement(AllocaInst *AI, std::vector<AllocaInst*> &WorkList); void DeleteDeadInstructions(); - void CleanupAllocaUsers(Value *V); AllocaInst *AddNewAlloca(Function &F, const Type *Ty, AllocaInst *Base); void RewriteForScalarRepl(Instruction *I, AllocaInst *AI, uint64_t Offset, @@ -281,14 +275,7 @@ bool SROA::performScalarRepl(Function &F) { getNumSAElements(AI->getAllocatedType()) <= SRThreshold/4) { // Check that all of the users of the allocation are capable of being // transformed. - switch (isSafeAllocaToScalarRepl(AI)) { - default: llvm_unreachable("Unexpected value!"); - case 0: // Not safe to scalar replace. - break; - case 1: // Safe, but requires cleanup/canonicalizations first - CleanupAllocaUsers(AI); - // FALL THROUGH. - case 3: // Safe to scalar replace. + if (isSafeAllocaToScalarRepl(AI)) { DoScalarReplacement(AI, WorkList); Changed = true; continue; @@ -437,14 +424,6 @@ void SROA::isSafeForScalarRepl(Instruction *I, AllocaInst *AI, uint64_t Offset, SIType, true, Info); } else MarkUnsafe(Info); - } else if (isa<DbgInfoIntrinsic>(UI)) { - // If one user is DbgInfoIntrinsic then check if all users are - // DbgInfoIntrinsics. - if (OnlyUsedByDbgInfoIntrinsics(I)) { - Info.needsCleanup = true; - return; - } - MarkUnsafe(Info); } else { DEBUG(errs() << " Transformation preventing inst: " << *User << '\n'); MarkUnsafe(Info); @@ -752,9 +731,16 @@ void SROA::RewriteMemIntrinUserOfAlloca(MemIntrinsic *MI, Instruction *Inst, } break; } - // If OtherPtr has already been rewritten, this intrinsic will be dead. - if (OtherPtr == NewElts[0]) + // Copying the alloca to itself is a no-op: just delete it. + if (OtherPtr == AI || OtherPtr == NewElts[0]) { + // This code will run twice for a no-op memcpy -- once for each operand. + // Put only one reference to MI on the DeadInsts list. + for (SmallVector<Value*, 32>::const_iterator I = DeadInsts.begin(), + E = DeadInsts.end(); I != E; ++I) + if (*I == MI) return; + DeadInsts.push_back(MI); return; + } if (ConstantExpr *BCE = dyn_cast<ConstantExpr>(OtherPtr)) if (BCE->getOpcode() == Instruction::BitCast) @@ -779,10 +765,7 @@ void SROA::RewriteMemIntrinUserOfAlloca(MemIntrinsic *MI, Instruction *Inst, Value *OtherElt = 0; unsigned OtherEltAlign = MemAlignment; - if (OtherPtr == AI) { - OtherElt = NewElts[i]; - OtherEltAlign = 0; - } else if (OtherPtr) { + if (OtherPtr) { Value *Idx[2] = { Zero, ConstantInt::get(Type::getInt32Ty(MI->getContext()), i) }; OtherElt = GetElementPtrInst::CreateInBounds(OtherPtr, Idx, Idx + 2, @@ -1146,7 +1129,7 @@ static bool HasPadding(const Type *Ty, const TargetData &TD) { /// isSafeStructAllocaToScalarRepl - Check to see if the specified allocation of /// an aggregate can be broken down into elements. Return 0 if not, 3 if safe, /// or 1 if safe after canonicalization has been performed. -int SROA::isSafeAllocaToScalarRepl(AllocaInst *AI) { +bool SROA::isSafeAllocaToScalarRepl(AllocaInst *AI) { // Loop over the use list of the alloca. We can only transform it if all of // the users are safe to transform. AllocaInfo Info; @@ -1154,7 +1137,7 @@ int SROA::isSafeAllocaToScalarRepl(AllocaInst *AI) { isSafeForScalarRepl(AI, AI, 0, Info); if (Info.isUnsafe) { DEBUG(dbgs() << "Cannot transform: " << *AI << '\n'); - return 0; + return false; } // Okay, we know all the users are promotable. If the aggregate is a memcpy @@ -1164,29 +1147,9 @@ int SROA::isSafeAllocaToScalarRepl(AllocaInst *AI) { // struct. if (Info.isMemCpySrc && Info.isMemCpyDst && HasPadding(AI->getAllocatedType(), *TD)) - return 0; - - // If we require cleanup, return 1, otherwise return 3. - return Info.needsCleanup ? 1 : 3; -} + return false; -/// CleanupAllocaUsers - If SROA reported that it can promote the specified -/// allocation, but only if cleaned up, perform the cleanups required. -void SROA::CleanupAllocaUsers(Value *V) { - for (Value::use_iterator UI = V->use_begin(), E = V->use_end(); - UI != E; ) { - User *U = *UI++; - Instruction *I = cast<Instruction>(U); - SmallVector<DbgInfoIntrinsic *, 2> DbgInUses; - if (!isa<StoreInst>(I) && OnlyUsedByDbgInfoIntrinsics(I, &DbgInUses)) { - // Safe to remove debug info uses. - while (!DbgInUses.empty()) { - DbgInfoIntrinsic *DI = DbgInUses.pop_back_val(); - DI->eraseFromParent(); - } - I->eraseFromParent(); - } - } + return true; } /// MergeInType - Add the 'In' type to the accumulated type (Accum) so far at @@ -1321,10 +1284,6 @@ bool SROA::CanConvertToScalar(Value *V, bool &IsNotTrivial, const Type *&VecTy, } } - // Ignore dbg intrinsic. - if (isa<DbgInfoIntrinsic>(User)) - continue; - // Otherwise, we cannot handle this! return false; } @@ -1449,18 +1408,11 @@ void SROA::ConvertUsesToScalar(Value *Ptr, AllocaInst *NewAI, uint64_t Offset) { } else { // Noop transfer. Src == Dst } - MTI->eraseFromParent(); continue; } - // If user is a dbg info intrinsic then it is safe to remove it. - if (isa<DbgInfoIntrinsic>(User)) { - User->eraseFromParent(); - continue; - } - llvm_unreachable("Unsupported operation!"); } } diff --git a/lib/Transforms/Scalar/SimplifyLibCalls.cpp b/lib/Transforms/Scalar/SimplifyLibCalls.cpp index 9183f3a..a49da9c 100644 --- a/lib/Transforms/Scalar/SimplifyLibCalls.cpp +++ b/lib/Transforms/Scalar/SimplifyLibCalls.cpp @@ -81,6 +81,10 @@ public: /// and the return value has 'i8*' type. Value *EmitStrChr(Value *Ptr, char C, IRBuilder<> &B); + /// EmitStrCpy - Emit a call to the strcpy function to the builder, for the + /// specified pointer arguments. + Value *EmitStrCpy(Value *Dst, Value *Src, IRBuilder<> &B); + /// EmitMemCpy - Emit a call to the memcpy function to the builder. This /// always expects that the size has type 'intptr_t' and Dst/Src are pointers. Value *EmitMemCpy(Value *Dst, Value *Src, Value *Len, @@ -176,6 +180,22 @@ Value *LibCallOptimization::EmitStrChr(Value *Ptr, char C, IRBuilder<> &B) { return CI; } +/// EmitStrCpy - Emit a call to the strcpy function to the builder, for the +/// specified pointer arguments. +Value *LibCallOptimization::EmitStrCpy(Value *Dst, Value *Src, IRBuilder<> &B) { + Module *M = Caller->getParent(); + AttributeWithIndex AWI[2]; + AWI[0] = AttributeWithIndex::get(2, Attribute::NoCapture); + AWI[1] = AttributeWithIndex::get(~0u, Attribute::NoUnwind); + const Type *I8Ptr = Type::getInt8PtrTy(*Context); + Value *StrCpy = M->getOrInsertFunction("strcpy", AttrListPtr::get(AWI, 2), + I8Ptr, I8Ptr, I8Ptr, NULL); + CallInst *CI = B.CreateCall2(StrCpy, CastToCStr(Dst, B), CastToCStr(Src, B), + "strcpy"); + if (const Function *F = dyn_cast<Function>(StrCpy->stripPointerCasts())) + CI->setCallingConv(F->getCallingConv()); + return CI; +} /// EmitMemCpy - Emit a call to the memcpy function to the builder. This always /// expects that the size has type 'intptr_t' and Dst/Src are pointers. @@ -1181,6 +1201,31 @@ struct MemMoveChkOpt : public LibCallOptimization { } }; +struct StrCpyChkOpt : public LibCallOptimization { + virtual Value *CallOptimizer(Function *Callee, CallInst *CI, IRBuilder<> &B) { + // These optimizations require TargetData. + if (!TD) return 0; + + const FunctionType *FT = Callee->getFunctionType(); + if (FT->getNumParams() != 3 || FT->getReturnType() != FT->getParamType(0) || + !isa<PointerType>(FT->getParamType(0)) || + !isa<PointerType>(FT->getParamType(1)) || + !isa<IntegerType>(FT->getParamType(2))) + return 0; + + ConstantInt *SizeCI = dyn_cast<ConstantInt>(CI->getOperand(3)); + if (!SizeCI) + return 0; + + // We don't have any length information, just lower to a plain strcpy. + if (SizeCI->isAllOnesValue()) + return EmitStrCpy(CI->getOperand(1), CI->getOperand(2), B); + + return 0; + } +}; + + //===----------------------------------------------------------------------===// // Math Library Optimizations //===----------------------------------------------------------------------===// @@ -1725,6 +1770,7 @@ namespace { // Object Size Checking MemCpyChkOpt MemCpyChk; MemSetChkOpt MemSetChk; MemMoveChkOpt MemMoveChk; + StrCpyChkOpt StrCpyChk; bool Modified; // This is only used by doInitialization. public: @@ -1836,6 +1882,7 @@ void SimplifyLibCalls::InitOptimizations() { Optimizations["__memcpy_chk"] = &MemCpyChk; Optimizations["__memset_chk"] = &MemSetChk; Optimizations["__memmove_chk"] = &MemMoveChk; + Optimizations["__strcpy_chk"] = &StrCpyChk; } diff --git a/lib/Transforms/Utils/BasicBlockUtils.cpp b/lib/Transforms/Utils/BasicBlockUtils.cpp index e902688..7bc4fcd 100644 --- a/lib/Transforms/Utils/BasicBlockUtils.cpp +++ b/lib/Transforms/Utils/BasicBlockUtils.cpp @@ -615,11 +615,6 @@ Value *llvm::FindAvailableLoadedValue(Value *Ptr, BasicBlock *ScanBB, Instruction *Inst = --ScanFrom; if (isa<DbgInfoIntrinsic>(Inst)) continue; - // We skip pointer-to-pointer bitcasts, which are NOPs. - // It is necessary for correctness to skip those that feed into a - // llvm.dbg.declare, as these are not present when debugging is off. - if (isa<BitCastInst>(Inst) && isa<PointerType>(Inst->getType())) - continue; // Restore ScanFrom to expected value in case next test succeeds ScanFrom++; diff --git a/lib/Transforms/Utils/Local.cpp b/lib/Transforms/Utils/Local.cpp index 90e929e..92bdf2d 100644 --- a/lib/Transforms/Utils/Local.cpp +++ b/lib/Transforms/Utils/Local.cpp @@ -609,30 +609,6 @@ bool llvm::TryToSimplifyUncondBranchFromEmptyBlock(BasicBlock *BB) { return true; } - - -/// OnlyUsedByDbgIntrinsics - Return true if the instruction I is only used -/// by DbgIntrinsics. If DbgInUses is specified then the vector is filled -/// with the DbgInfoIntrinsic that use the instruction I. -bool llvm::OnlyUsedByDbgInfoIntrinsics(Instruction *I, - SmallVectorImpl<DbgInfoIntrinsic *> *DbgInUses) { - if (DbgInUses) - DbgInUses->clear(); - - for (Value::use_iterator UI = I->use_begin(), UE = I->use_end(); UI != UE; - ++UI) { - if (DbgInfoIntrinsic *DI = dyn_cast<DbgInfoIntrinsic>(*UI)) { - if (DbgInUses) - DbgInUses->push_back(DI); - } else { - if (DbgInUses) - DbgInUses->clear(); - return false; - } - } - return true; -} - /// EliminateDuplicatePHINodes - Check for and eliminate duplicate PHI /// nodes in this block. This doesn't try to be clever about PHI nodes /// which differ only in the order of the incoming values, but instcombine diff --git a/lib/Transforms/Utils/LoopSimplify.cpp b/lib/Transforms/Utils/LoopSimplify.cpp index 7fcc5f7..e81b779 100644 --- a/lib/Transforms/Utils/LoopSimplify.cpp +++ b/lib/Transforms/Utils/LoopSimplify.cpp @@ -232,7 +232,7 @@ ReprocessLoop: PN->eraseFromParent(); } - // If this loop has muliple exits and the exits all go to the same + // If this loop has multiple exits and the exits all go to the same // block, attempt to merge the exits. This helps several passes, such // as LoopRotation, which do not support loops with multiple exits. // SimplifyCFG also does this (and this code uses the same utility diff --git a/lib/Transforms/Utils/Makefile b/lib/Transforms/Utils/Makefile index d1e9336..b9761df 100644 --- a/lib/Transforms/Utils/Makefile +++ b/lib/Transforms/Utils/Makefile @@ -10,6 +10,7 @@ LEVEL = ../../.. LIBRARYNAME = LLVMTransformUtils BUILD_ARCHIVE = 1 +CXXFLAGS = -fno-rtti include $(LEVEL)/Makefile.common diff --git a/lib/Transforms/Utils/PromoteMemoryToRegister.cpp b/lib/Transforms/Utils/PromoteMemoryToRegister.cpp index baaa130..d9261ac 100644 --- a/lib/Transforms/Utils/PromoteMemoryToRegister.cpp +++ b/lib/Transforms/Utils/PromoteMemoryToRegister.cpp @@ -23,6 +23,7 @@ #include "llvm/Function.h" #include "llvm/Instructions.h" #include "llvm/IntrinsicInst.h" +#include "llvm/Analysis/DebugInfo.h" #include "llvm/Analysis/Dominators.h" #include "llvm/Analysis/AliasSetTracker.h" #include "llvm/ADT/DenseMap.h" @@ -76,16 +77,6 @@ bool llvm::isAllocaPromotable(const AllocaInst *AI) { return false; // Don't allow a store OF the AI, only INTO the AI. if (SI->isVolatile()) return false; - } else if (const BitCastInst *BC = dyn_cast<BitCastInst>(*UI)) { - // A bitcast that does not feed into debug info inhibits promotion. - if (!BC->hasOneUse() || !isa<DbgInfoIntrinsic>(*BC->use_begin())) - return false; - // If the only use is by debug info, this alloca will not exist in - // non-debug code, so don't try to promote; this ensures the same - // codegen with debug info. Otherwise, debug info should not - // inhibit promotion (but we must examine other uses). - if (AI->hasOneUse()) - return false; } else { return false; } @@ -173,6 +164,7 @@ namespace { std::vector<AllocaInst*> Allocas; DominatorTree &DT; DominanceFrontier &DF; + DIFactory *DIF; /// AST - An AliasSetTracker object to update. If null, don't update it. /// @@ -209,7 +201,7 @@ namespace { public: PromoteMem2Reg(const std::vector<AllocaInst*> &A, DominatorTree &dt, DominanceFrontier &df, AliasSetTracker *ast) - : Allocas(A), DT(dt), DF(df), AST(ast) {} + : Allocas(A), DT(dt), DF(df), DIF(0), AST(ast) {} void run(); @@ -251,8 +243,9 @@ namespace { LargeBlockInfo &LBI); void PromoteSingleBlockAlloca(AllocaInst *AI, AllocaInfo &Info, LargeBlockInfo &LBI); - - + void ConvertDebugDeclareToDebugValue(DbgDeclareInst *DDI, StoreInst* SI, + uint64_t Offset); + void RenamePass(BasicBlock *BB, BasicBlock *Pred, RenamePassData::ValVector &IncVals, std::vector<RenamePassData> &Worklist); @@ -290,15 +283,7 @@ namespace { for (Value::use_iterator UI = AI->use_begin(), E = AI->use_end(); UI != E;) { Instruction *User = cast<Instruction>(*UI++); - if (BitCastInst *BC = dyn_cast<BitCastInst>(User)) { - // Remove any uses of this alloca in DbgInfoInstrinsics. - assert(BC->hasOneUse() && "Unexpected alloca uses!"); - DbgInfoIntrinsic *DI = cast<DbgInfoIntrinsic>(*BC->use_begin()); - DI->eraseFromParent(); - BC->eraseFromParent(); - continue; - } - + if (StoreInst *SI = dyn_cast<StoreInst>(User)) { // Remember the basic blocks which define new values for the alloca DefiningBlocks.push_back(SI->getParent()); @@ -324,6 +309,19 @@ namespace { } // end of anonymous namespace +/// Finds the llvm.dbg.declare intrinsic corresponding to an alloca if any. +static DbgDeclareInst *findDbgDeclare(AllocaInst *AI) { + Function *F = AI->getParent()->getParent(); + for (Function::iterator FI = F->begin(), FE = F->end(); FI != FE; ++FI) + for (BasicBlock::iterator BI = (*FI).begin(), BE = (*FI).end(); + BI != BE; ++BI) + if (DbgDeclareInst *DDI = dyn_cast<DbgDeclareInst>(BI)) + if (DDI->getAddress() == AI) + return DDI; + + return 0; +} + void PromoteMem2Reg::run() { Function &F = *DF.getRoot()->getParent(); @@ -362,6 +360,8 @@ void PromoteMem2Reg::run() { // Finally, after the scan, check to see if the store is all that is left. if (Info.UsingBlocks.empty()) { + // Record debuginfo for the store before removing it. + ConvertDebugDeclareToDebugValue(findDbgDeclare(AI), Info.OnlyStore, 0); // Remove the (now dead) store and alloca. Info.OnlyStore->eraseFromParent(); LBI.deleteValue(Info.OnlyStore); @@ -388,8 +388,11 @@ void PromoteMem2Reg::run() { if (Info.UsingBlocks.empty()) { // Remove the (now dead) stores and alloca. + DbgDeclareInst *DDI = findDbgDeclare(AI); while (!AI->use_empty()) { StoreInst *SI = cast<StoreInst>(AI->use_back()); + // Record debuginfo for the store before removing it. + ConvertDebugDeclareToDebugValue(DDI, SI, 0); SI->eraseFromParent(); LBI.deleteValue(SI); } @@ -851,6 +854,18 @@ void PromoteMem2Reg::PromoteSingleBlockAlloca(AllocaInst *AI, AllocaInfo &Info, } } +// Inserts a llvm.dbg.value instrinsic before the stores to an alloca'd value +// that has an associated llvm.dbg.decl intrinsic. +void PromoteMem2Reg::ConvertDebugDeclareToDebugValue(DbgDeclareInst *DDI, + StoreInst* SI, + uint64_t Offset) { + if (!DDI) return; + + if (!DIF) + DIF = new DIFactory(*SI->getParent()->getParent()->getParent()); + DIF->InsertDbgValueIntrinsic(SI->getOperand(0), Offset, + DIVariable(DDI->getVariable()), SI); +} // QueuePhiNode - queues a phi-node to be added to a basic-block for a specific // Alloca returns true if there wasn't already a phi-node for that variable @@ -964,6 +979,8 @@ NextIteration: // what value were we writing? IncomingVals[ai->second] = SI->getOperand(0); + // Record debuginfo for the store before removing it. + ConvertDebugDeclareToDebugValue(findDbgDeclare(Dest), SI, 0); BB->getInstList().erase(SI); } } diff --git a/lib/Transforms/Utils/ValueMapper.cpp b/lib/Transforms/Utils/ValueMapper.cpp index 39331d7..a6e6701 100644 --- a/lib/Transforms/Utils/ValueMapper.cpp +++ b/lib/Transforms/Utils/ValueMapper.cpp @@ -13,12 +13,11 @@ //===----------------------------------------------------------------------===// #include "llvm/Transforms/Utils/ValueMapper.h" -#include "llvm/DerivedTypes.h" // For getNullValue(Type::Int32Ty) +#include "llvm/Type.h" #include "llvm/Constants.h" #include "llvm/Function.h" #include "llvm/Metadata.h" #include "llvm/ADT/SmallVector.h" -#include "llvm/Support/ErrorHandling.h" using namespace llvm; Value *llvm::MapValue(const Value *V, ValueMapTy &VM) { @@ -28,11 +27,19 @@ Value *llvm::MapValue(const Value *V, ValueMapTy &VM) { // NOTE: VMSlot can be invalidated by any reference to VM, which can grow the // DenseMap. This includes any recursive calls to MapValue. - // Global values and metadata do not need to be seeded into the ValueMap if - // they are using the identity mapping. - if (isa<GlobalValue>(V) || isa<InlineAsm>(V) || isa<MetadataBase>(V)) + // Global values and non-function-local metadata do not need to be seeded into + // the ValueMap if they are using the identity mapping. + if (isa<GlobalValue>(V) || isa<InlineAsm>(V) || isa<MDString>(V) || + (isa<MDNode>(V) && !cast<MDNode>(V)->isFunctionLocal())) return VMSlot = const_cast<Value*>(V); + if (const MDNode *MD = dyn_cast<MDNode>(V)) { + SmallVector<Value*, 4> Elts; + for (unsigned i = 0; i != MD->getNumOperands(); i++) + Elts.push_back(MD->getOperand(i) ? MapValue(MD->getOperand(i), VM) : 0); + return VM[V] = MDNode::get(V->getContext(), Elts.data(), Elts.size()); + } + Constant *C = const_cast<Constant*>(dyn_cast<Constant>(V)); if (C == 0) return 0; @@ -111,14 +118,10 @@ Value *llvm::MapValue(const Value *V, ValueMapTy &VM) { return VM[V] = C; } - if (BlockAddress *BA = dyn_cast<BlockAddress>(C)) { - Function *F = cast<Function>(MapValue(BA->getFunction(), VM)); - BasicBlock *BB = cast_or_null<BasicBlock>(MapValue(BA->getBasicBlock(),VM)); - return VM[V] = BlockAddress::get(F, BB ? BB : BA->getBasicBlock()); - } - - llvm_unreachable("Unknown type of constant!"); - return 0; + BlockAddress *BA = cast<BlockAddress>(C); + Function *F = cast<Function>(MapValue(BA->getFunction(), VM)); + BasicBlock *BB = cast_or_null<BasicBlock>(MapValue(BA->getBasicBlock(),VM)); + return VM[V] = BlockAddress::get(F, BB ? BB : BA->getBasicBlock()); } /// RemapInstruction - Convert the instruction operands from referencing the @@ -131,3 +134,4 @@ void llvm::RemapInstruction(Instruction *I, ValueMapTy &ValueMap) { *op = V; } } + |