diff options
author | Eugene Zelenko <eugene.zelenko@gmail.com> | 2017-08-18 23:51:26 +0000 |
---|---|---|
committer | Eugene Zelenko <eugene.zelenko@gmail.com> | 2017-08-18 23:51:26 +0000 |
commit | 89688ce180615f38be048e64a0226b09e689134f (patch) | |
tree | ae112f0e251dabbca04f4c5614eb210d34830ad6 /lib/Analysis/ScalarEvolution.cpp | |
parent | 3c29a5e3d5788757b6b8bae0f2814040f90b8236 (diff) |
[Analysis] Fix some Clang-tidy modernize and Include What You Use warnings; other minor fixes (NFC).
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@311212 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Analysis/ScalarEvolution.cpp')
-rw-r--r-- | lib/Analysis/ScalarEvolution.cpp | 187 |
1 files changed, 105 insertions, 82 deletions
diff --git a/lib/Analysis/ScalarEvolution.cpp b/lib/Analysis/ScalarEvolution.cpp index 0d1c6d16f41..25decab88ed 100644 --- a/lib/Analysis/ScalarEvolution.cpp +++ b/lib/Analysis/ScalarEvolution.cpp @@ -59,12 +59,22 @@ //===----------------------------------------------------------------------===// #include "llvm/Analysis/ScalarEvolution.h" +#include "llvm/ADT/APInt.h" +#include "llvm/ADT/ArrayRef.h" +#include "llvm/ADT/DenseMap.h" +#include "llvm/ADT/DepthFirstIterator.h" +#include "llvm/ADT/FoldingSet.h" +#include "llvm/ADT/None.h" #include "llvm/ADT/Optional.h" #include "llvm/ADT/STLExtras.h" #include "llvm/ADT/ScopeExit.h" #include "llvm/ADT/Sequence.h" +#include "llvm/ADT/SetVector.h" #include "llvm/ADT/SmallPtrSet.h" +#include "llvm/ADT/SmallSet.h" +#include "llvm/ADT/SmallVector.h" #include "llvm/ADT/Statistic.h" +#include "llvm/ADT/StringRef.h" #include "llvm/Analysis/AssumptionCache.h" #include "llvm/Analysis/ConstantFolding.h" #include "llvm/Analysis/InstructionSimplify.h" @@ -72,28 +82,55 @@ #include "llvm/Analysis/ScalarEvolutionExpressions.h" #include "llvm/Analysis/TargetLibraryInfo.h" #include "llvm/Analysis/ValueTracking.h" +#include "llvm/IR/Argument.h" +#include "llvm/IR/BasicBlock.h" +#include "llvm/IR/CFG.h" +#include "llvm/IR/CallSite.h" +#include "llvm/IR/Constant.h" #include "llvm/IR/ConstantRange.h" #include "llvm/IR/Constants.h" #include "llvm/IR/DataLayout.h" #include "llvm/IR/DerivedTypes.h" #include "llvm/IR/Dominators.h" -#include "llvm/IR/GetElementPtrTypeIterator.h" +#include "llvm/IR/Function.h" #include "llvm/IR/GlobalAlias.h" +#include "llvm/IR/GlobalValue.h" #include "llvm/IR/GlobalVariable.h" #include "llvm/IR/InstIterator.h" +#include "llvm/IR/InstrTypes.h" +#include "llvm/IR/Instruction.h" #include "llvm/IR/Instructions.h" +#include "llvm/IR/IntrinsicInst.h" +#include "llvm/IR/Intrinsics.h" #include "llvm/IR/LLVMContext.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/Operator.h" #include "llvm/IR/PatternMatch.h" +#include "llvm/IR/Type.h" +#include "llvm/IR/Use.h" +#include "llvm/IR/User.h" +#include "llvm/IR/Value.h" +#include "llvm/Pass.h" +#include "llvm/Support/Casting.h" #include "llvm/Support/CommandLine.h" +#include "llvm/Support/Compiler.h" #include "llvm/Support/Debug.h" #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/KnownBits.h" -#include "llvm/Support/MathExtras.h" #include "llvm/Support/SaveAndRestore.h" #include "llvm/Support/raw_ostream.h" #include <algorithm> +#include <cassert> +#include <climits> +#include <cstddef> +#include <cstdint> +#include <cstdlib> +#include <map> +#include <memory> +#include <tuple> +#include <utility> +#include <vector> + using namespace llvm; #define DEBUG_TYPE "scalar-evolution" @@ -736,7 +773,6 @@ static int CompareSCEVComplexity( /// results from this routine. In other words, we don't want the results of /// this to depend on where the addresses of various SCEV objects happened to /// land in memory. -/// static void GroupByComplexity(SmallVectorImpl<const SCEV *> &Ops, LoopInfo *LI, DominatorTree &DT) { if (Ops.size() < 2) return; // Noop @@ -782,14 +818,16 @@ static void GroupByComplexity(SmallVectorImpl<const SCEV *> &Ops, // Returns the size of the SCEV S. static inline int sizeOfSCEV(const SCEV *S) { struct FindSCEVSize { - int Size; - FindSCEVSize() : Size(0) {} + int Size = 0; + + FindSCEVSize() = default; bool follow(const SCEV *S) { ++Size; // Keep looking at all operands of S. return true; } + bool isDone() const { return false; } @@ -1029,7 +1067,7 @@ private: const SCEV *Denominator, *Quotient, *Remainder, *Zero, *One; }; -} +} // end anonymous namespace //===----------------------------------------------------------------------===// // Simple SCEV method implementations @@ -1154,7 +1192,6 @@ static const SCEV *BinomialCoefficient(const SCEV *It, unsigned K, /// A*BC(It, 0) + B*BC(It, 1) + C*BC(It, 2) + D*BC(It, 3) /// /// where BC(It, k) stands for binomial coefficient. -/// const SCEV *SCEVAddRecExpr::evaluateAtIteration(const SCEV *It, ScalarEvolution &SE) const { const SCEV *Result = getStart(); @@ -1340,7 +1377,8 @@ struct ExtendOpTraits<SCEVZeroExtendExpr> : public ExtendOpTraitsBase { const ExtendOpTraitsBase::GetExtendExprTy ExtendOpTraits< SCEVZeroExtendExpr>::GetExtendExpr = &ScalarEvolution::getZeroExtendExpr; -} + +} // end anonymous namespace // The recurrence AR has been shown to have no signed/unsigned wrap or something // close to it. Typically, if we can prove NSW/NUW for AR, then we can just as @@ -1470,7 +1508,6 @@ static const SCEV *getExtendAddRecStart(const SCEVAddRecExpr *AR, Type *Ty, // // In the current context, S is `Start`, X is `Step`, Ext is `ExtendOpTy` and T // is `Delta` (defined below). -// template <typename ExtendOpTy> bool ScalarEvolution::proveNoWrapByVaryingStart(const SCEV *Start, const SCEV *Step, @@ -1481,7 +1518,6 @@ bool ScalarEvolution::proveNoWrapByVaryingStart(const SCEV *Start, // time here. It is correct (but more expensive) to continue with a // non-constant `Start` and do a general SCEV subtraction to compute // `PreStart` below. - // const SCEVConstant *StartC = dyn_cast<SCEVConstant>(Start); if (!StartC) return false; @@ -1983,7 +2019,6 @@ ScalarEvolution::getSignExtendExpr(const SCEV *Op, Type *Ty, unsigned Depth) { /// getAnyExtendExpr - Return a SCEV for the given operand extended with /// unspecified bits out to the given type. -/// const SCEV *ScalarEvolution::getAnyExtendExpr(const SCEV *Op, Type *Ty) { assert(getTypeSizeInBits(Op->getType()) < getTypeSizeInBits(Ty) && @@ -2054,7 +2089,6 @@ const SCEV *ScalarEvolution::getAnyExtendExpr(const SCEV *Op, /// may be exposed. This helps getAddRecExpr short-circuit extra work in /// the common case where no interesting opportunities are present, and /// is also used as a check to avoid infinite recursion. -/// static bool CollectAddOperandsWithScales(DenseMap<const SCEV *, APInt> &M, SmallVectorImpl<const SCEV *> &NewOps, @@ -2129,7 +2163,8 @@ StrengthenNoWrapFlags(ScalarEvolution *SE, SCEVTypes Type, const SmallVectorImpl<const SCEV *> &Ops, SCEV::NoWrapFlags Flags) { using namespace std::placeholders; - typedef OverflowingBinaryOperator OBO; + + using OBO = OverflowingBinaryOperator; bool CanAnalyze = Type == scAddExpr || Type == scAddRecExpr || Type == scMulExpr; @@ -2684,6 +2719,7 @@ static bool containsConstantInAddMulChain(const SCEV *StartExpr) { FoundConstant |= isa<SCEVConstant>(S); return isa<SCEVAddExpr>(S) || isa<SCEVMulExpr>(S); } + bool isDone() const { return FoundConstant; } @@ -3718,7 +3754,6 @@ const SCEV *ScalarEvolution::getExistingSCEV(Value *V) { } /// Return a SCEV corresponding to -V = -1*V -/// const SCEV *ScalarEvolution::getNegativeSCEV(const SCEV *V, SCEV::NoWrapFlags Flags) { if (const SCEVConstant *VC = dyn_cast<SCEVConstant>(V)) @@ -3961,8 +3996,12 @@ void ScalarEvolution::forgetSymbolicName(Instruction *PN, const SCEV *SymName) { } namespace { + class SCEVInitRewriter : public SCEVRewriteVisitor<SCEVInitRewriter> { public: + SCEVInitRewriter(const Loop *L, ScalarEvolution &SE) + : SCEVRewriteVisitor(SE), L(L) {} + static const SCEV *rewrite(const SCEV *S, const Loop *L, ScalarEvolution &SE) { SCEVInitRewriter Rewriter(L, SE); @@ -3970,9 +4009,6 @@ public: return Rewriter.isValid() ? Result : SE.getCouldNotCompute(); } - SCEVInitRewriter(const Loop *L, ScalarEvolution &SE) - : SCEVRewriteVisitor(SE), L(L), Valid(true) {} - const SCEV *visitUnknown(const SCEVUnknown *Expr) { if (!SE.isLoopInvariant(Expr, L)) Valid = false; @@ -3991,11 +4027,14 @@ public: private: const Loop *L; - bool Valid; + bool Valid = true; }; class SCEVShiftRewriter : public SCEVRewriteVisitor<SCEVShiftRewriter> { public: + SCEVShiftRewriter(const Loop *L, ScalarEvolution &SE) + : SCEVRewriteVisitor(SE), L(L) {} + static const SCEV *rewrite(const SCEV *S, const Loop *L, ScalarEvolution &SE) { SCEVShiftRewriter Rewriter(L, SE); @@ -4003,9 +4042,6 @@ public: return Rewriter.isValid() ? Result : SE.getCouldNotCompute(); } - SCEVShiftRewriter(const Loop *L, ScalarEvolution &SE) - : SCEVRewriteVisitor(SE), L(L), Valid(true) {} - const SCEV *visitUnknown(const SCEVUnknown *Expr) { // Only allow AddRecExprs for this loop. if (!SE.isLoopInvariant(Expr, L)) @@ -4019,12 +4055,14 @@ public: Valid = false; return Expr; } + bool isValid() { return Valid; } private: const Loop *L; - bool Valid; + bool Valid = true; }; + } // end anonymous namespace SCEV::NoWrapFlags @@ -4032,7 +4070,8 @@ ScalarEvolution::proveNoWrapViaConstantRanges(const SCEVAddRecExpr *AR) { if (!AR->isAffine()) return SCEV::FlagAnyWrap; - typedef OverflowingBinaryOperator OBO; + using OBO = OverflowingBinaryOperator; + SCEV::NoWrapFlags Result = SCEV::FlagAnyWrap; if (!AR->hasNoSignedWrap()) { @@ -4059,6 +4098,7 @@ ScalarEvolution::proveNoWrapViaConstantRanges(const SCEVAddRecExpr *AR) { } namespace { + /// Represents an abstract binary operation. This may exist as a /// normal instruction or constant expression, or may have been /// derived from an expression tree. @@ -4066,16 +4106,16 @@ struct BinaryOp { unsigned Opcode; Value *LHS; Value *RHS; - bool IsNSW; - bool IsNUW; + bool IsNSW = false; + bool IsNUW = false; /// Op is set if this BinaryOp corresponds to a concrete LLVM instruction or /// constant expression. - Operator *Op; + Operator *Op = nullptr; explicit BinaryOp(Operator *Op) : Opcode(Op->getOpcode()), LHS(Op->getOperand(0)), RHS(Op->getOperand(1)), - IsNSW(false), IsNUW(false), Op(Op) { + Op(Op) { if (auto *OBO = dyn_cast<OverflowingBinaryOperator>(Op)) { IsNSW = OBO->hasNoSignedWrap(); IsNUW = OBO->hasNoUnsignedWrap(); @@ -4084,11 +4124,10 @@ struct BinaryOp { explicit BinaryOp(unsigned Opcode, Value *LHS, Value *RHS, bool IsNSW = false, bool IsNUW = false) - : Opcode(Opcode), LHS(LHS), RHS(RHS), IsNSW(IsNSW), IsNUW(IsNUW), - Op(nullptr) {} + : Opcode(Opcode), LHS(LHS), RHS(RHS), IsNSW(IsNSW), IsNUW(IsNUW) {} }; -} +} // end anonymous namespace /// Try to map \p V into a BinaryOp, and return \c None on failure. static Optional<BinaryOp> MatchBinaryOp(Value *V, DominatorTree &DT) { @@ -4149,7 +4188,7 @@ static Optional<BinaryOp> MatchBinaryOp(Value *V, DominatorTree &DT) { if (auto *F = CI->getCalledFunction()) switch (F->getIntrinsicID()) { case Intrinsic::sadd_with_overflow: - case Intrinsic::uadd_with_overflow: { + case Intrinsic::uadd_with_overflow: if (!isOverflowIntrinsicNoWrap(cast<IntrinsicInst>(CI), DT)) return BinaryOp(Instruction::Add, CI->getArgOperand(0), CI->getArgOperand(1)); @@ -4165,10 +4204,8 @@ static Optional<BinaryOp> MatchBinaryOp(Value *V, DominatorTree &DT) { return BinaryOp(Instruction::Add, CI->getArgOperand(0), CI->getArgOperand(1), /* IsNSW = */ false, /* IsNUW*/ true); - } - case Intrinsic::ssub_with_overflow: - case Intrinsic::usub_with_overflow: { + case Intrinsic::usub_with_overflow: if (!isOverflowIntrinsicNoWrap(cast<IntrinsicInst>(CI), DT)) return BinaryOp(Instruction::Sub, CI->getArgOperand(0), CI->getArgOperand(1)); @@ -4182,7 +4219,6 @@ static Optional<BinaryOp> MatchBinaryOp(Value *V, DominatorTree &DT) { return BinaryOp(Instruction::Sub, CI->getArgOperand(0), CI->getArgOperand(1), /* IsNSW = */ false, /* IsNUW = */ true); - } case Intrinsic::smul_with_overflow: case Intrinsic::umul_with_overflow: return BinaryOp(Instruction::Mul, CI->getArgOperand(0), @@ -4212,7 +4248,6 @@ static Optional<BinaryOp> MatchBinaryOp(Value *V, DominatorTree &DT) { /// \p Signed to true/false, respectively. static Type *isSimpleCastedPHI(const SCEV *Op, const SCEVUnknown *SymbolicPHI, bool &Signed, ScalarEvolution &SE) { - // The case where Op == SymbolicPHI (that is, with no type conversions on // the way) is handled by the regular add recurrence creating logic and // would have already been triggered in createAddRecForPHI. Reaching it here @@ -4243,7 +4278,7 @@ static Type *isSimpleCastedPHI(const SCEV *Op, const SCEVUnknown *SymbolicPHI, const SCEV *X = Trunc->getOperand(); if (X != SymbolicPHI) return nullptr; - Signed = SExt ? true : false; + Signed = SExt != nullptr; return Trunc->getType(); } @@ -4309,7 +4344,6 @@ static const Loop *isIntegerLoopHeaderPHI(const PHINode *PN, LoopInfo &LI) { // which correspond to a phi->trunc->add->sext/zext->phi update chain. // // 3) Outline common code with createAddRecFromPHI to avoid duplication. -// Optional<std::pair<const SCEV *, SmallVector<const SCEVPredicate *, 3>>> ScalarEvolution::createAddRecFromPHIWithCastsImpl(const SCEVUnknown *SymbolicPHI) { SmallVector<const SCEVPredicate *, 3> Predicates; @@ -4319,7 +4353,7 @@ ScalarEvolution::createAddRecFromPHIWithCastsImpl(const SCEVUnknown *SymbolicPHI auto *PN = cast<PHINode>(SymbolicPHI->getValue()); const Loop *L = isIntegerLoopHeaderPHI(PN, LI); - assert (L && "Expecting an integer loop header phi"); + assert(L && "Expecting an integer loop header phi"); // The loop may have multiple entrances or multiple exits; we can analyze // this phi as an addrec if it has a unique entry value and a unique @@ -4380,7 +4414,6 @@ ScalarEvolution::createAddRecFromPHIWithCastsImpl(const SCEVUnknown *SymbolicPHI // varying inside the loop. if (!isLoopInvariant(Accum, L)) return None; - // *** Part2: Create the predicates @@ -4447,7 +4480,7 @@ ScalarEvolution::createAddRecFromPHIWithCastsImpl(const SCEVUnknown *SymbolicPHI // Create the Equal Predicates P2,P3: auto AppendPredicate = [&](const SCEV *Expr) -> void { - assert (isLoopInvariant(Expr, L) && "Expr is expected to be invariant"); + assert(isLoopInvariant(Expr, L) && "Expr is expected to be invariant"); const SCEV *TruncatedExpr = getTruncateExpr(Expr, TruncTy); const SCEV *ExtendedExpr = Signed ? getSignExtendExpr(TruncatedExpr, Expr->getType()) @@ -4478,7 +4511,6 @@ ScalarEvolution::createAddRecFromPHIWithCastsImpl(const SCEVUnknown *SymbolicPHI Optional<std::pair<const SCEV *, SmallVector<const SCEVPredicate *, 3>>> ScalarEvolution::createAddRecFromPHIWithCasts(const SCEVUnknown *SymbolicPHI) { - auto *PN = cast<PHINode>(SymbolicPHI->getValue()); const Loop *L = isIntegerLoopHeaderPHI(PN, LI); if (!L) @@ -5614,7 +5646,7 @@ bool ScalarEvolution::isAddRecNeverPoison(const Instruction *I, const Loop *L) { ScalarEvolution::LoopProperties ScalarEvolution::getLoopProperties(const Loop *L) { - typedef ScalarEvolution::LoopProperties LoopProperties; + using LoopProperties = ScalarEvolution::LoopProperties; auto Itr = LoopPropertiesCache.find(L); if (Itr == LoopPropertiesCache.end()) { @@ -5901,7 +5933,7 @@ const SCEV *ScalarEvolution::createSCEV(Value *V) { } break; - case Instruction::AShr: + case Instruction::AShr: { // AShr X, C, where C is a constant. ConstantInt *CI = dyn_cast<ConstantInt>(BO->RHS); if (!CI) @@ -5953,6 +5985,7 @@ const SCEV *ScalarEvolution::createSCEV(Value *V) { } break; } + } } switch (U->getOpcode()) { @@ -6017,8 +6050,6 @@ const SCEV *ScalarEvolution::createSCEV(Value *V) { return getUnknown(V); } - - //===----------------------------------------------------------------------===// // Iteration Count Computation Code // @@ -6413,7 +6444,7 @@ bool ScalarEvolution::BackedgeTakenInfo::hasOperand(const SCEV *S, } ScalarEvolution::ExitLimit::ExitLimit(const SCEV *E) - : ExactNotTaken(E), MaxNotTaken(E), MaxOrZero(false) { + : ExactNotTaken(E), MaxNotTaken(E) { assert((isa<SCEVCouldNotCompute>(MaxNotTaken) || isa<SCEVConstant>(MaxNotTaken)) && "No point in having a non-constant max backedge taken count!"); @@ -6458,7 +6489,8 @@ ScalarEvolution::BackedgeTakenInfo::BackedgeTakenInfo( &&ExitCounts, bool Complete, const SCEV *MaxCount, bool MaxOrZero) : MaxAndComplete(MaxCount, Complete), MaxOrZero(MaxOrZero) { - typedef ScalarEvolution::BackedgeTakenInfo::EdgeExitInfo EdgeExitInfo; + using EdgeExitInfo = ScalarEvolution::BackedgeTakenInfo::EdgeExitInfo; + ExitNotTaken.reserve(ExitCounts.size()); std::transform( ExitCounts.begin(), ExitCounts.end(), std::back_inserter(ExitNotTaken), @@ -6490,7 +6522,7 @@ ScalarEvolution::computeBackedgeTakenCount(const Loop *L, SmallVector<BasicBlock *, 8> ExitingBlocks; L->getExitingBlocks(ExitingBlocks); - typedef ScalarEvolution::BackedgeTakenInfo::EdgeExitInfo EdgeExitInfo; + using EdgeExitInfo = ScalarEvolution::BackedgeTakenInfo::EdgeExitInfo; SmallVector<EdgeExitInfo, 4> ExitCounts; bool CouldComputeBECount = true; @@ -6570,7 +6602,6 @@ ScalarEvolution::computeExitLimit(const Loop *L, BasicBlock *ExitingBlock, ScalarEvolution::ExitLimit ScalarEvolution::computeExitLimitImpl(const Loop *L, BasicBlock *ExitingBlock, bool AllowPredicates) { - // Okay, we've chosen an exiting block. See what condition causes us to exit // at this block and remember the exit block and whether all other targets // lead to the loop header. @@ -6833,7 +6864,6 @@ ScalarEvolution::computeExitLimitFromICmp(const Loop *L, BasicBlock *FBB, bool ControlsExit, bool AllowPredicates) { - // If the condition was exit on true, convert the condition to exit on false ICmpInst::Predicate Cond; if (!L->contains(FBB)) @@ -6968,7 +6998,6 @@ ScalarEvolution::computeLoadConstantCompareExitLimit( Constant *RHS, const Loop *L, ICmpInst::Predicate predicate) { - if (LI->isVolatile()) return getCouldNotCompute(); // Check to see if the loaded pointer is a getelementptr of a global. @@ -7887,7 +7916,6 @@ static const SCEV *SolveLinEquationWithOverflow(const APInt &A, const SCEV *B, /// Find the roots of the quadratic equation for the given quadratic chrec /// {L,+,M,+,N}. This returns either the two roots (which might be the same) or /// two SCEVCouldNotCompute objects. -/// static Optional<std::pair<const SCEVConstant *,const SCEVConstant *>> SolveQuadraticEquation(const SCEVAddRecExpr *AddRec, ScalarEvolution &SE) { assert(AddRec->getNumOperands() == 3 && "This is not a quadratic chrec!"); @@ -8128,7 +8156,6 @@ ScalarEvolution::getPredecessorWithUniqueSuccessorForBB(BasicBlock *BB) { /// expressions are equal, however for the purposes of looking for a condition /// guarding a loop, it can be useful to be a little more general, since a /// front-end may have replicated the controlling expression. -/// static bool HasSameValue(const SCEV *A, const SCEV *B) { // Quick check to see if they are the same SCEV. if (A == B) return true; @@ -8575,7 +8602,6 @@ bool ScalarEvolution::isKnownPredicateViaConstantRanges( bool ScalarEvolution::isKnownPredicateViaNoOverflow(ICmpInst::Predicate Pred, const SCEV *LHS, const SCEV *RHS) { - // Match Result to (X + Y)<ExpectedFlags> where Y is a constant integer. // Return Y via OutY. auto MatchBinaryAddToConst = @@ -8741,7 +8767,6 @@ ScalarEvolution::isLoopBackedgeGuardedByCond(const Loop *L, for (DomTreeNode *DTN = DT[Latch], *HeaderDTN = DT[L->getHeader()]; DTN != HeaderDTN; DTN = DTN->getIDom()) { - assert(DTN && "should reach the loop header before reaching the root!"); BasicBlock *BB = DTN->getBlock(); @@ -9164,7 +9189,6 @@ bool ScalarEvolution::isImpliedCondOperands(ICmpInst::Predicate Pred, getNotSCEV(FoundLHS)); } - /// If Expr computes ~A, return A else return nullptr static const SCEV *MatchNotExpr(const SCEV *Expr) { const SCEVAddExpr *Add = dyn_cast<SCEVAddExpr>(Expr); @@ -9180,7 +9204,6 @@ static const SCEV *MatchNotExpr(const SCEV *Expr) { return AddRHS->getOperand(1); } - /// Is MaybeMaxExpr an SMax or UMax of Candidate and some other values? template<typename MaxExprType> static bool IsMaxConsistingOf(const SCEV *MaybeMaxExpr, @@ -9191,7 +9214,6 @@ static bool IsMaxConsistingOf(const SCEV *MaybeMaxExpr, return find(MaxExpr->operands(), Candidate) != MaxExpr->op_end(); } - /// Is MaybeMinExpr an SMin or UMin of Candidate and some other values? template<typename MaxExprType> static bool IsMinConsistingOf(ScalarEvolution &SE, @@ -9207,7 +9229,6 @@ static bool IsMinConsistingOf(ScalarEvolution &SE, static bool IsKnownPredicateViaAddRecStart(ScalarEvolution &SE, ICmpInst::Predicate Pred, const SCEV *LHS, const SCEV *RHS) { - // If both sides are affine addrecs for the same loop, with equal // steps, and we know the recurrences don't wrap, then we only // need to check the predicate on the starting values. @@ -9343,7 +9364,9 @@ bool ScalarEvolution::isImpliedViaOperations(ICmpInst::Predicate Pred, } else if (auto *LHSUnknownExpr = dyn_cast<SCEVUnknown>(LHS)) { Value *LL, *LR; // FIXME: Once we have SDiv implemented, we can get rid of this matching. + using namespace llvm::PatternMatch; + if (match(LHSUnknownExpr->getValue(), m_SDiv(m_Value(LL), m_Value(LR)))) { // Rules for division. // We are going to perform some comparisons with Denominator and its @@ -9636,7 +9659,6 @@ ScalarEvolution::howManyLessThans(const SCEV *LHS, const SCEV *RHS, if (PredicatedIV || !NoWrap || isKnownNonPositive(Stride) || !loopHasNoSideEffects(L)) return getCouldNotCompute(); - } else if (!Stride->isOne() && doesIVOverflowOnLT(RHS, Stride, IsSigned, NoWrap)) // Avoid proven overflow cases: this will ensure that the backedge taken @@ -9922,6 +9944,7 @@ static inline bool containsUndefs(const SCEV *S) { } namespace { + // Collect all steps of SCEV expressions. struct SCEVCollectStrides { ScalarEvolution &SE; @@ -9935,6 +9958,7 @@ struct SCEVCollectStrides { Strides.push_back(AR->getStepRecurrence(SE)); return true; } + bool isDone() const { return false; } }; @@ -9942,8 +9966,7 @@ struct SCEVCollectStrides { struct SCEVCollectTerms { SmallVectorImpl<const SCEV *> &Terms; - SCEVCollectTerms(SmallVectorImpl<const SCEV *> &T) - : Terms(T) {} + SCEVCollectTerms(SmallVectorImpl<const SCEV *> &T) : Terms(T) {} bool follow(const SCEV *S) { if (isa<SCEVUnknown>(S) || isa<SCEVMulExpr>(S) || @@ -9958,6 +9981,7 @@ struct SCEVCollectTerms { // Keep looking. return true; } + bool isDone() const { return false; } }; @@ -9966,7 +9990,7 @@ struct SCEVHasAddRec { bool &ContainsAddRec; SCEVHasAddRec(bool &ContainsAddRec) : ContainsAddRec(ContainsAddRec) { - ContainsAddRec = false; + ContainsAddRec = false; } bool follow(const SCEV *S) { @@ -9980,6 +10004,7 @@ struct SCEVHasAddRec { // Keep looking. return true; } + bool isDone() const { return false; } }; @@ -10033,9 +10058,11 @@ struct SCEVCollectAddRecMultiplies { // Keep looking. return true; } + bool isDone() const { return false; } }; -} + +} // end anonymous namespace /// Find parametric terms in this SCEVAddRecExpr. We first for parameters in /// two places: @@ -10114,7 +10141,6 @@ static bool findArrayDimensionsRec(ScalarEvolution &SE, return true; } - // Returns true when one of the SCEVs of Terms contains a SCEVUnknown parameter. static inline bool containsParameters(SmallVectorImpl<const SCEV *> &Terms) { for (const SCEV *T : Terms) @@ -10229,7 +10255,6 @@ void ScalarEvolution::findArrayDimensions(SmallVectorImpl<const SCEV *> &Terms, void ScalarEvolution::computeAccessFunctions( const SCEV *Expr, SmallVectorImpl<const SCEV *> &Subscripts, SmallVectorImpl<const SCEV *> &Sizes) { - // Early exit in case this SCEV is not an affine multivariate function. if (Sizes.empty()) return; @@ -10333,7 +10358,6 @@ void ScalarEvolution::computeAccessFunctions( /// DelinearizationPass that walks through all loads and stores of a function /// asking for the SCEV of the memory access with respect to all enclosing /// loops, calling SCEV->delinearize on that and printing the results. - void ScalarEvolution::delinearize(const SCEV *Expr, SmallVectorImpl<const SCEV *> &Subscripts, SmallVectorImpl<const SCEV *> &Sizes, @@ -10422,11 +10446,8 @@ ScalarEvolution::ScalarEvolution(Function &F, TargetLibraryInfo &TLI, AssumptionCache &AC, DominatorTree &DT, LoopInfo &LI) : F(F), TLI(TLI), AC(AC), DT(DT), LI(LI), - CouldNotCompute(new SCEVCouldNotCompute()), - WalkingBEDominatingConds(false), ProvingSplitPredicate(false), - ValuesAtScopes(64), LoopDispositions(64), BlockDispositions(64), - FirstUnknown(nullptr) { - + CouldNotCompute(new SCEVCouldNotCompute()), ValuesAtScopes(64), + LoopDispositions(64), BlockDispositions(64) { // To use guards for proving predicates, we need to scan every instruction in // relevant basic blocks, and not just terminators. Doing this is a waste of // time if the IR does not actually contain any calls to @@ -10447,7 +10468,6 @@ ScalarEvolution::ScalarEvolution(ScalarEvolution &&Arg) LI(Arg.LI), CouldNotCompute(std::move(Arg.CouldNotCompute)), ValueExprMap(std::move(Arg.ValueExprMap)), PendingLoopPredicates(std::move(Arg.PendingLoopPredicates)), - WalkingBEDominatingConds(false), ProvingSplitPredicate(false), MinTrailingZerosCache(std::move(Arg.MinTrailingZerosCache)), BackedgeTakenCounts(std::move(Arg.BackedgeTakenCounts)), PredicatedBackedgeTakenCounts( @@ -10914,9 +10934,12 @@ void ScalarEvolution::verify() const { // Map's SCEV expressions from one ScalarEvolution "universe" to another. struct SCEVMapper : public SCEVRewriteVisitor<SCEVMapper> { + SCEVMapper(ScalarEvolution &SE) : SCEVRewriteVisitor<SCEVMapper>(SE) {} + const SCEV *visitConstant(const SCEVConstant *Constant) { return SE.getConstant(Constant->getAPInt()); } + const SCEV *visitUnknown(const SCEVUnknown *Expr) { return SE.getUnknown(Expr->getValue()); } @@ -10924,7 +10947,6 @@ void ScalarEvolution::verify() const { const SCEV *visitCouldNotCompute(const SCEVCouldNotCompute *Expr) { return SE.getCouldNotCompute(); } - SCEVMapper(ScalarEvolution &SE) : SCEVRewriteVisitor<SCEVMapper>(SE) {} }; SCEVMapper SCM(SE2); @@ -11013,6 +11035,7 @@ INITIALIZE_PASS_DEPENDENCY(DominatorTreeWrapperPass) INITIALIZE_PASS_DEPENDENCY(TargetLibraryInfoWrapperPass) INITIALIZE_PASS_END(ScalarEvolutionWrapperPass, "scalar-evolution", "Scalar Evolution Analysis", false, true) + char ScalarEvolutionWrapperPass::ID = 0; ScalarEvolutionWrapperPass::ScalarEvolutionWrapperPass() : FunctionPass(ID) { @@ -11088,6 +11111,11 @@ namespace { class SCEVPredicateRewriter : public SCEVRewriteVisitor<SCEVPredicateRewriter> { public: + SCEVPredicateRewriter(const Loop *L, ScalarEvolution &SE, + SmallPtrSetImpl<const SCEVPredicate *> *NewPreds, + SCEVUnionPredicate *Pred) + : SCEVRewriteVisitor(SE), NewPreds(NewPreds), Pred(Pred), L(L) {} + /// Rewrites \p S in the context of a loop L and the SCEV predication /// infrastructure. /// @@ -11103,11 +11131,6 @@ public: return Rewriter.visit(S); } - SCEVPredicateRewriter(const Loop *L, ScalarEvolution &SE, - SmallPtrSetImpl<const SCEVPredicate *> *NewPreds, - SCEVUnionPredicate *Pred) - : SCEVRewriteVisitor(SE), NewPreds(NewPreds), Pred(Pred), L(L) {} - const SCEV *visitUnknown(const SCEVUnknown *Expr) { if (Pred) { auto ExprPreds = Pred->getPredicatesForExpr(Expr); @@ -11191,6 +11214,7 @@ private: SCEVUnionPredicate *Pred; const Loop *L; }; + } // end anonymous namespace const SCEV *ScalarEvolution::rewriteUsingPredicate(const SCEV *S, const Loop *L, @@ -11201,7 +11225,6 @@ const SCEV *ScalarEvolution::rewriteUsingPredicate(const SCEV *S, const Loop *L, const SCEVAddRecExpr *ScalarEvolution::convertSCEVToAddRecWithPredicates( const SCEV *S, const Loop *L, SmallPtrSetImpl<const SCEVPredicate *> &Preds) { - SmallPtrSet<const SCEVPredicate *, 4> TransformPreds; S = SCEVPredicateRewriter::rewrite(S, L, *this, &TransformPreds, nullptr); auto *AddRec = dyn_cast<SCEVAddRecExpr>(S); @@ -11357,7 +11380,7 @@ void SCEVUnionPredicate::add(const SCEVPredicate *N) { PredicatedScalarEvolution::PredicatedScalarEvolution(ScalarEvolution &SE, Loop &L) - : SE(SE), L(L), Generation(0), BackedgeCount(nullptr) {} + : SE(SE), L(L) {} const SCEV *PredicatedScalarEvolution::getSCEV(Value *V) { const SCEV *Expr = SE.getSCEV(V); |