xref: /aosp_15_r20/external/llvm/lib/Transforms/Utils/SimplifyIndVar.cpp (revision 9880d6810fe72a1726cb53787c6711e909410d58)
1*9880d681SAndroid Build Coastguard Worker //===-- SimplifyIndVar.cpp - Induction variable simplification ------------===//
2*9880d681SAndroid Build Coastguard Worker //
3*9880d681SAndroid Build Coastguard Worker //                     The LLVM Compiler Infrastructure
4*9880d681SAndroid Build Coastguard Worker //
5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source
6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details.
7*9880d681SAndroid Build Coastguard Worker //
8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
9*9880d681SAndroid Build Coastguard Worker //
10*9880d681SAndroid Build Coastguard Worker // This file implements induction variable simplification. It does
11*9880d681SAndroid Build Coastguard Worker // not define any actual pass or policy, but provides a single function to
12*9880d681SAndroid Build Coastguard Worker // simplify a loop's induction variables based on ScalarEvolution.
13*9880d681SAndroid Build Coastguard Worker //
14*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
15*9880d681SAndroid Build Coastguard Worker 
16*9880d681SAndroid Build Coastguard Worker #include "llvm/Transforms/Utils/SimplifyIndVar.h"
17*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/STLExtras.h"
18*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/SmallVector.h"
19*9880d681SAndroid Build Coastguard Worker #include "llvm/ADT/Statistic.h"
20*9880d681SAndroid Build Coastguard Worker #include "llvm/Analysis/LoopInfo.h"
21*9880d681SAndroid Build Coastguard Worker #include "llvm/Analysis/LoopPass.h"
22*9880d681SAndroid Build Coastguard Worker #include "llvm/Analysis/ScalarEvolutionExpressions.h"
23*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/DataLayout.h"
24*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/Dominators.h"
25*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/IRBuilder.h"
26*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/Instructions.h"
27*9880d681SAndroid Build Coastguard Worker #include "llvm/IR/IntrinsicInst.h"
28*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/Debug.h"
29*9880d681SAndroid Build Coastguard Worker #include "llvm/Support/raw_ostream.h"
30*9880d681SAndroid Build Coastguard Worker 
31*9880d681SAndroid Build Coastguard Worker using namespace llvm;
32*9880d681SAndroid Build Coastguard Worker 
33*9880d681SAndroid Build Coastguard Worker #define DEBUG_TYPE "indvars"
34*9880d681SAndroid Build Coastguard Worker 
35*9880d681SAndroid Build Coastguard Worker STATISTIC(NumElimIdentity, "Number of IV identities eliminated");
36*9880d681SAndroid Build Coastguard Worker STATISTIC(NumElimOperand,  "Number of IV operands folded into a use");
37*9880d681SAndroid Build Coastguard Worker STATISTIC(NumElimRem     , "Number of IV remainder operations eliminated");
38*9880d681SAndroid Build Coastguard Worker STATISTIC(NumElimCmp     , "Number of IV comparisons eliminated");
39*9880d681SAndroid Build Coastguard Worker 
40*9880d681SAndroid Build Coastguard Worker namespace {
41*9880d681SAndroid Build Coastguard Worker   /// This is a utility for simplifying induction variables
42*9880d681SAndroid Build Coastguard Worker   /// based on ScalarEvolution. It is the primary instrument of the
43*9880d681SAndroid Build Coastguard Worker   /// IndvarSimplify pass, but it may also be directly invoked to cleanup after
44*9880d681SAndroid Build Coastguard Worker   /// other loop passes that preserve SCEV.
45*9880d681SAndroid Build Coastguard Worker   class SimplifyIndvar {
46*9880d681SAndroid Build Coastguard Worker     Loop             *L;
47*9880d681SAndroid Build Coastguard Worker     LoopInfo         *LI;
48*9880d681SAndroid Build Coastguard Worker     ScalarEvolution  *SE;
49*9880d681SAndroid Build Coastguard Worker     DominatorTree    *DT;
50*9880d681SAndroid Build Coastguard Worker 
51*9880d681SAndroid Build Coastguard Worker     SmallVectorImpl<WeakVH> &DeadInsts;
52*9880d681SAndroid Build Coastguard Worker 
53*9880d681SAndroid Build Coastguard Worker     bool Changed;
54*9880d681SAndroid Build Coastguard Worker 
55*9880d681SAndroid Build Coastguard Worker   public:
SimplifyIndvar(Loop * Loop,ScalarEvolution * SE,DominatorTree * DT,LoopInfo * LI,SmallVectorImpl<WeakVH> & Dead)56*9880d681SAndroid Build Coastguard Worker     SimplifyIndvar(Loop *Loop, ScalarEvolution *SE, DominatorTree *DT,
57*9880d681SAndroid Build Coastguard Worker                    LoopInfo *LI,SmallVectorImpl<WeakVH> &Dead)
58*9880d681SAndroid Build Coastguard Worker         : L(Loop), LI(LI), SE(SE), DT(DT), DeadInsts(Dead), Changed(false) {
59*9880d681SAndroid Build Coastguard Worker       assert(LI && "IV simplification requires LoopInfo");
60*9880d681SAndroid Build Coastguard Worker     }
61*9880d681SAndroid Build Coastguard Worker 
hasChanged() const62*9880d681SAndroid Build Coastguard Worker     bool hasChanged() const { return Changed; }
63*9880d681SAndroid Build Coastguard Worker 
64*9880d681SAndroid Build Coastguard Worker     /// Iteratively perform simplification on a worklist of users of the
65*9880d681SAndroid Build Coastguard Worker     /// specified induction variable. This is the top-level driver that applies
66*9880d681SAndroid Build Coastguard Worker     /// all simplifications to users of an IV.
67*9880d681SAndroid Build Coastguard Worker     void simplifyUsers(PHINode *CurrIV, IVVisitor *V = nullptr);
68*9880d681SAndroid Build Coastguard Worker 
69*9880d681SAndroid Build Coastguard Worker     Value *foldIVUser(Instruction *UseInst, Instruction *IVOperand);
70*9880d681SAndroid Build Coastguard Worker 
71*9880d681SAndroid Build Coastguard Worker     bool eliminateIdentitySCEV(Instruction *UseInst, Instruction *IVOperand);
72*9880d681SAndroid Build Coastguard Worker 
73*9880d681SAndroid Build Coastguard Worker     bool eliminateOverflowIntrinsic(CallInst *CI);
74*9880d681SAndroid Build Coastguard Worker     bool eliminateIVUser(Instruction *UseInst, Instruction *IVOperand);
75*9880d681SAndroid Build Coastguard Worker     void eliminateIVComparison(ICmpInst *ICmp, Value *IVOperand);
76*9880d681SAndroid Build Coastguard Worker     void eliminateIVRemainder(BinaryOperator *Rem, Value *IVOperand,
77*9880d681SAndroid Build Coastguard Worker                               bool IsSigned);
78*9880d681SAndroid Build Coastguard Worker     bool strengthenOverflowingOperation(BinaryOperator *OBO, Value *IVOperand);
79*9880d681SAndroid Build Coastguard Worker   };
80*9880d681SAndroid Build Coastguard Worker }
81*9880d681SAndroid Build Coastguard Worker 
82*9880d681SAndroid Build Coastguard Worker /// Fold an IV operand into its use.  This removes increments of an
83*9880d681SAndroid Build Coastguard Worker /// aligned IV when used by a instruction that ignores the low bits.
84*9880d681SAndroid Build Coastguard Worker ///
85*9880d681SAndroid Build Coastguard Worker /// IVOperand is guaranteed SCEVable, but UseInst may not be.
86*9880d681SAndroid Build Coastguard Worker ///
87*9880d681SAndroid Build Coastguard Worker /// Return the operand of IVOperand for this induction variable if IVOperand can
88*9880d681SAndroid Build Coastguard Worker /// be folded (in case more folding opportunities have been exposed).
89*9880d681SAndroid Build Coastguard Worker /// Otherwise return null.
foldIVUser(Instruction * UseInst,Instruction * IVOperand)90*9880d681SAndroid Build Coastguard Worker Value *SimplifyIndvar::foldIVUser(Instruction *UseInst, Instruction *IVOperand) {
91*9880d681SAndroid Build Coastguard Worker   Value *IVSrc = nullptr;
92*9880d681SAndroid Build Coastguard Worker   unsigned OperIdx = 0;
93*9880d681SAndroid Build Coastguard Worker   const SCEV *FoldedExpr = nullptr;
94*9880d681SAndroid Build Coastguard Worker   switch (UseInst->getOpcode()) {
95*9880d681SAndroid Build Coastguard Worker   default:
96*9880d681SAndroid Build Coastguard Worker     return nullptr;
97*9880d681SAndroid Build Coastguard Worker   case Instruction::UDiv:
98*9880d681SAndroid Build Coastguard Worker   case Instruction::LShr:
99*9880d681SAndroid Build Coastguard Worker     // We're only interested in the case where we know something about
100*9880d681SAndroid Build Coastguard Worker     // the numerator and have a constant denominator.
101*9880d681SAndroid Build Coastguard Worker     if (IVOperand != UseInst->getOperand(OperIdx) ||
102*9880d681SAndroid Build Coastguard Worker         !isa<ConstantInt>(UseInst->getOperand(1)))
103*9880d681SAndroid Build Coastguard Worker       return nullptr;
104*9880d681SAndroid Build Coastguard Worker 
105*9880d681SAndroid Build Coastguard Worker     // Attempt to fold a binary operator with constant operand.
106*9880d681SAndroid Build Coastguard Worker     // e.g. ((I + 1) >> 2) => I >> 2
107*9880d681SAndroid Build Coastguard Worker     if (!isa<BinaryOperator>(IVOperand)
108*9880d681SAndroid Build Coastguard Worker         || !isa<ConstantInt>(IVOperand->getOperand(1)))
109*9880d681SAndroid Build Coastguard Worker       return nullptr;
110*9880d681SAndroid Build Coastguard Worker 
111*9880d681SAndroid Build Coastguard Worker     IVSrc = IVOperand->getOperand(0);
112*9880d681SAndroid Build Coastguard Worker     // IVSrc must be the (SCEVable) IV, since the other operand is const.
113*9880d681SAndroid Build Coastguard Worker     assert(SE->isSCEVable(IVSrc->getType()) && "Expect SCEVable IV operand");
114*9880d681SAndroid Build Coastguard Worker 
115*9880d681SAndroid Build Coastguard Worker     ConstantInt *D = cast<ConstantInt>(UseInst->getOperand(1));
116*9880d681SAndroid Build Coastguard Worker     if (UseInst->getOpcode() == Instruction::LShr) {
117*9880d681SAndroid Build Coastguard Worker       // Get a constant for the divisor. See createSCEV.
118*9880d681SAndroid Build Coastguard Worker       uint32_t BitWidth = cast<IntegerType>(UseInst->getType())->getBitWidth();
119*9880d681SAndroid Build Coastguard Worker       if (D->getValue().uge(BitWidth))
120*9880d681SAndroid Build Coastguard Worker         return nullptr;
121*9880d681SAndroid Build Coastguard Worker 
122*9880d681SAndroid Build Coastguard Worker       D = ConstantInt::get(UseInst->getContext(),
123*9880d681SAndroid Build Coastguard Worker                            APInt::getOneBitSet(BitWidth, D->getZExtValue()));
124*9880d681SAndroid Build Coastguard Worker     }
125*9880d681SAndroid Build Coastguard Worker     FoldedExpr = SE->getUDivExpr(SE->getSCEV(IVSrc), SE->getSCEV(D));
126*9880d681SAndroid Build Coastguard Worker   }
127*9880d681SAndroid Build Coastguard Worker   // We have something that might fold it's operand. Compare SCEVs.
128*9880d681SAndroid Build Coastguard Worker   if (!SE->isSCEVable(UseInst->getType()))
129*9880d681SAndroid Build Coastguard Worker     return nullptr;
130*9880d681SAndroid Build Coastguard Worker 
131*9880d681SAndroid Build Coastguard Worker   // Bypass the operand if SCEV can prove it has no effect.
132*9880d681SAndroid Build Coastguard Worker   if (SE->getSCEV(UseInst) != FoldedExpr)
133*9880d681SAndroid Build Coastguard Worker     return nullptr;
134*9880d681SAndroid Build Coastguard Worker 
135*9880d681SAndroid Build Coastguard Worker   DEBUG(dbgs() << "INDVARS: Eliminated IV operand: " << *IVOperand
136*9880d681SAndroid Build Coastguard Worker         << " -> " << *UseInst << '\n');
137*9880d681SAndroid Build Coastguard Worker 
138*9880d681SAndroid Build Coastguard Worker   UseInst->setOperand(OperIdx, IVSrc);
139*9880d681SAndroid Build Coastguard Worker   assert(SE->getSCEV(UseInst) == FoldedExpr && "bad SCEV with folded oper");
140*9880d681SAndroid Build Coastguard Worker 
141*9880d681SAndroid Build Coastguard Worker   ++NumElimOperand;
142*9880d681SAndroid Build Coastguard Worker   Changed = true;
143*9880d681SAndroid Build Coastguard Worker   if (IVOperand->use_empty())
144*9880d681SAndroid Build Coastguard Worker     DeadInsts.emplace_back(IVOperand);
145*9880d681SAndroid Build Coastguard Worker   return IVSrc;
146*9880d681SAndroid Build Coastguard Worker }
147*9880d681SAndroid Build Coastguard Worker 
148*9880d681SAndroid Build Coastguard Worker /// SimplifyIVUsers helper for eliminating useless
149*9880d681SAndroid Build Coastguard Worker /// comparisons against an induction variable.
eliminateIVComparison(ICmpInst * ICmp,Value * IVOperand)150*9880d681SAndroid Build Coastguard Worker void SimplifyIndvar::eliminateIVComparison(ICmpInst *ICmp, Value *IVOperand) {
151*9880d681SAndroid Build Coastguard Worker   unsigned IVOperIdx = 0;
152*9880d681SAndroid Build Coastguard Worker   ICmpInst::Predicate Pred = ICmp->getPredicate();
153*9880d681SAndroid Build Coastguard Worker   if (IVOperand != ICmp->getOperand(0)) {
154*9880d681SAndroid Build Coastguard Worker     // Swapped
155*9880d681SAndroid Build Coastguard Worker     assert(IVOperand == ICmp->getOperand(1) && "Can't find IVOperand");
156*9880d681SAndroid Build Coastguard Worker     IVOperIdx = 1;
157*9880d681SAndroid Build Coastguard Worker     Pred = ICmpInst::getSwappedPredicate(Pred);
158*9880d681SAndroid Build Coastguard Worker   }
159*9880d681SAndroid Build Coastguard Worker 
160*9880d681SAndroid Build Coastguard Worker   // Get the SCEVs for the ICmp operands.
161*9880d681SAndroid Build Coastguard Worker   const SCEV *S = SE->getSCEV(ICmp->getOperand(IVOperIdx));
162*9880d681SAndroid Build Coastguard Worker   const SCEV *X = SE->getSCEV(ICmp->getOperand(1 - IVOperIdx));
163*9880d681SAndroid Build Coastguard Worker 
164*9880d681SAndroid Build Coastguard Worker   // Simplify unnecessary loops away.
165*9880d681SAndroid Build Coastguard Worker   const Loop *ICmpLoop = LI->getLoopFor(ICmp->getParent());
166*9880d681SAndroid Build Coastguard Worker   S = SE->getSCEVAtScope(S, ICmpLoop);
167*9880d681SAndroid Build Coastguard Worker   X = SE->getSCEVAtScope(X, ICmpLoop);
168*9880d681SAndroid Build Coastguard Worker 
169*9880d681SAndroid Build Coastguard Worker   ICmpInst::Predicate InvariantPredicate;
170*9880d681SAndroid Build Coastguard Worker   const SCEV *InvariantLHS, *InvariantRHS;
171*9880d681SAndroid Build Coastguard Worker 
172*9880d681SAndroid Build Coastguard Worker   // If the condition is always true or always false, replace it with
173*9880d681SAndroid Build Coastguard Worker   // a constant value.
174*9880d681SAndroid Build Coastguard Worker   if (SE->isKnownPredicate(Pred, S, X)) {
175*9880d681SAndroid Build Coastguard Worker     ICmp->replaceAllUsesWith(ConstantInt::getTrue(ICmp->getContext()));
176*9880d681SAndroid Build Coastguard Worker     DeadInsts.emplace_back(ICmp);
177*9880d681SAndroid Build Coastguard Worker     DEBUG(dbgs() << "INDVARS: Eliminated comparison: " << *ICmp << '\n');
178*9880d681SAndroid Build Coastguard Worker   } else if (SE->isKnownPredicate(ICmpInst::getInversePredicate(Pred), S, X)) {
179*9880d681SAndroid Build Coastguard Worker     ICmp->replaceAllUsesWith(ConstantInt::getFalse(ICmp->getContext()));
180*9880d681SAndroid Build Coastguard Worker     DeadInsts.emplace_back(ICmp);
181*9880d681SAndroid Build Coastguard Worker     DEBUG(dbgs() << "INDVARS: Eliminated comparison: " << *ICmp << '\n');
182*9880d681SAndroid Build Coastguard Worker   } else if (isa<PHINode>(IVOperand) &&
183*9880d681SAndroid Build Coastguard Worker              SE->isLoopInvariantPredicate(Pred, S, X, L, InvariantPredicate,
184*9880d681SAndroid Build Coastguard Worker                                           InvariantLHS, InvariantRHS)) {
185*9880d681SAndroid Build Coastguard Worker 
186*9880d681SAndroid Build Coastguard Worker     // Rewrite the comparison to a loop invariant comparison if it can be done
187*9880d681SAndroid Build Coastguard Worker     // cheaply, where cheaply means "we don't need to emit any new
188*9880d681SAndroid Build Coastguard Worker     // instructions".
189*9880d681SAndroid Build Coastguard Worker 
190*9880d681SAndroid Build Coastguard Worker     Value *NewLHS = nullptr, *NewRHS = nullptr;
191*9880d681SAndroid Build Coastguard Worker 
192*9880d681SAndroid Build Coastguard Worker     if (S == InvariantLHS || X == InvariantLHS)
193*9880d681SAndroid Build Coastguard Worker       NewLHS =
194*9880d681SAndroid Build Coastguard Worker           ICmp->getOperand(S == InvariantLHS ? IVOperIdx : (1 - IVOperIdx));
195*9880d681SAndroid Build Coastguard Worker 
196*9880d681SAndroid Build Coastguard Worker     if (S == InvariantRHS || X == InvariantRHS)
197*9880d681SAndroid Build Coastguard Worker       NewRHS =
198*9880d681SAndroid Build Coastguard Worker           ICmp->getOperand(S == InvariantRHS ? IVOperIdx : (1 - IVOperIdx));
199*9880d681SAndroid Build Coastguard Worker 
200*9880d681SAndroid Build Coastguard Worker     auto *PN = cast<PHINode>(IVOperand);
201*9880d681SAndroid Build Coastguard Worker     for (unsigned i = 0, e = PN->getNumIncomingValues();
202*9880d681SAndroid Build Coastguard Worker          i != e && (!NewLHS || !NewRHS);
203*9880d681SAndroid Build Coastguard Worker          ++i) {
204*9880d681SAndroid Build Coastguard Worker 
205*9880d681SAndroid Build Coastguard Worker       // If this is a value incoming from the backedge, then it cannot be a loop
206*9880d681SAndroid Build Coastguard Worker       // invariant value (since we know that IVOperand is an induction variable).
207*9880d681SAndroid Build Coastguard Worker       if (L->contains(PN->getIncomingBlock(i)))
208*9880d681SAndroid Build Coastguard Worker         continue;
209*9880d681SAndroid Build Coastguard Worker 
210*9880d681SAndroid Build Coastguard Worker       // NB! This following assert does not fundamentally have to be true, but
211*9880d681SAndroid Build Coastguard Worker       // it is true today given how SCEV analyzes induction variables.
212*9880d681SAndroid Build Coastguard Worker       // Specifically, today SCEV will *not* recognize %iv as an induction
213*9880d681SAndroid Build Coastguard Worker       // variable in the following case:
214*9880d681SAndroid Build Coastguard Worker       //
215*9880d681SAndroid Build Coastguard Worker       // define void @f(i32 %k) {
216*9880d681SAndroid Build Coastguard Worker       // entry:
217*9880d681SAndroid Build Coastguard Worker       //   br i1 undef, label %r, label %l
218*9880d681SAndroid Build Coastguard Worker       //
219*9880d681SAndroid Build Coastguard Worker       // l:
220*9880d681SAndroid Build Coastguard Worker       //   %k.inc.l = add i32 %k, 1
221*9880d681SAndroid Build Coastguard Worker       //   br label %loop
222*9880d681SAndroid Build Coastguard Worker       //
223*9880d681SAndroid Build Coastguard Worker       // r:
224*9880d681SAndroid Build Coastguard Worker       //   %k.inc.r = add i32 %k, 1
225*9880d681SAndroid Build Coastguard Worker       //   br label %loop
226*9880d681SAndroid Build Coastguard Worker       //
227*9880d681SAndroid Build Coastguard Worker       // loop:
228*9880d681SAndroid Build Coastguard Worker       //   %iv = phi i32 [ %k.inc.l, %l ], [ %k.inc.r, %r ], [ %iv.inc, %loop ]
229*9880d681SAndroid Build Coastguard Worker       //   %iv.inc = add i32 %iv, 1
230*9880d681SAndroid Build Coastguard Worker       //   br label %loop
231*9880d681SAndroid Build Coastguard Worker       // }
232*9880d681SAndroid Build Coastguard Worker       //
233*9880d681SAndroid Build Coastguard Worker       // but if it starts to, at some point, then the assertion below will have
234*9880d681SAndroid Build Coastguard Worker       // to be changed to a runtime check.
235*9880d681SAndroid Build Coastguard Worker 
236*9880d681SAndroid Build Coastguard Worker       Value *Incoming = PN->getIncomingValue(i);
237*9880d681SAndroid Build Coastguard Worker 
238*9880d681SAndroid Build Coastguard Worker #ifndef NDEBUG
239*9880d681SAndroid Build Coastguard Worker       if (auto *I = dyn_cast<Instruction>(Incoming))
240*9880d681SAndroid Build Coastguard Worker         assert(DT->dominates(I, ICmp) && "Should be a unique loop dominating value!");
241*9880d681SAndroid Build Coastguard Worker #endif
242*9880d681SAndroid Build Coastguard Worker 
243*9880d681SAndroid Build Coastguard Worker       const SCEV *IncomingS = SE->getSCEV(Incoming);
244*9880d681SAndroid Build Coastguard Worker 
245*9880d681SAndroid Build Coastguard Worker       if (!NewLHS && IncomingS == InvariantLHS)
246*9880d681SAndroid Build Coastguard Worker         NewLHS = Incoming;
247*9880d681SAndroid Build Coastguard Worker       if (!NewRHS && IncomingS == InvariantRHS)
248*9880d681SAndroid Build Coastguard Worker         NewRHS = Incoming;
249*9880d681SAndroid Build Coastguard Worker     }
250*9880d681SAndroid Build Coastguard Worker 
251*9880d681SAndroid Build Coastguard Worker     if (!NewLHS || !NewRHS)
252*9880d681SAndroid Build Coastguard Worker       // We could not find an existing value to replace either LHS or RHS.
253*9880d681SAndroid Build Coastguard Worker       // Generating new instructions has subtler tradeoffs, so avoid doing that
254*9880d681SAndroid Build Coastguard Worker       // for now.
255*9880d681SAndroid Build Coastguard Worker       return;
256*9880d681SAndroid Build Coastguard Worker 
257*9880d681SAndroid Build Coastguard Worker     DEBUG(dbgs() << "INDVARS: Simplified comparison: " << *ICmp << '\n');
258*9880d681SAndroid Build Coastguard Worker     ICmp->setPredicate(InvariantPredicate);
259*9880d681SAndroid Build Coastguard Worker     ICmp->setOperand(0, NewLHS);
260*9880d681SAndroid Build Coastguard Worker     ICmp->setOperand(1, NewRHS);
261*9880d681SAndroid Build Coastguard Worker   } else
262*9880d681SAndroid Build Coastguard Worker     return;
263*9880d681SAndroid Build Coastguard Worker 
264*9880d681SAndroid Build Coastguard Worker   ++NumElimCmp;
265*9880d681SAndroid Build Coastguard Worker   Changed = true;
266*9880d681SAndroid Build Coastguard Worker }
267*9880d681SAndroid Build Coastguard Worker 
268*9880d681SAndroid Build Coastguard Worker /// SimplifyIVUsers helper for eliminating useless
269*9880d681SAndroid Build Coastguard Worker /// remainder operations operating on an induction variable.
eliminateIVRemainder(BinaryOperator * Rem,Value * IVOperand,bool IsSigned)270*9880d681SAndroid Build Coastguard Worker void SimplifyIndvar::eliminateIVRemainder(BinaryOperator *Rem,
271*9880d681SAndroid Build Coastguard Worker                                       Value *IVOperand,
272*9880d681SAndroid Build Coastguard Worker                                       bool IsSigned) {
273*9880d681SAndroid Build Coastguard Worker   // We're only interested in the case where we know something about
274*9880d681SAndroid Build Coastguard Worker   // the numerator.
275*9880d681SAndroid Build Coastguard Worker   if (IVOperand != Rem->getOperand(0))
276*9880d681SAndroid Build Coastguard Worker     return;
277*9880d681SAndroid Build Coastguard Worker 
278*9880d681SAndroid Build Coastguard Worker   // Get the SCEVs for the ICmp operands.
279*9880d681SAndroid Build Coastguard Worker   const SCEV *S = SE->getSCEV(Rem->getOperand(0));
280*9880d681SAndroid Build Coastguard Worker   const SCEV *X = SE->getSCEV(Rem->getOperand(1));
281*9880d681SAndroid Build Coastguard Worker 
282*9880d681SAndroid Build Coastguard Worker   // Simplify unnecessary loops away.
283*9880d681SAndroid Build Coastguard Worker   const Loop *ICmpLoop = LI->getLoopFor(Rem->getParent());
284*9880d681SAndroid Build Coastguard Worker   S = SE->getSCEVAtScope(S, ICmpLoop);
285*9880d681SAndroid Build Coastguard Worker   X = SE->getSCEVAtScope(X, ICmpLoop);
286*9880d681SAndroid Build Coastguard Worker 
287*9880d681SAndroid Build Coastguard Worker   // i % n  -->  i  if i is in [0,n).
288*9880d681SAndroid Build Coastguard Worker   if ((!IsSigned || SE->isKnownNonNegative(S)) &&
289*9880d681SAndroid Build Coastguard Worker       SE->isKnownPredicate(IsSigned ? ICmpInst::ICMP_SLT : ICmpInst::ICMP_ULT,
290*9880d681SAndroid Build Coastguard Worker                            S, X))
291*9880d681SAndroid Build Coastguard Worker     Rem->replaceAllUsesWith(Rem->getOperand(0));
292*9880d681SAndroid Build Coastguard Worker   else {
293*9880d681SAndroid Build Coastguard Worker     // (i+1) % n  -->  (i+1)==n?0:(i+1)  if i is in [0,n).
294*9880d681SAndroid Build Coastguard Worker     const SCEV *LessOne = SE->getMinusSCEV(S, SE->getOne(S->getType()));
295*9880d681SAndroid Build Coastguard Worker     if (IsSigned && !SE->isKnownNonNegative(LessOne))
296*9880d681SAndroid Build Coastguard Worker       return;
297*9880d681SAndroid Build Coastguard Worker 
298*9880d681SAndroid Build Coastguard Worker     if (!SE->isKnownPredicate(IsSigned ?
299*9880d681SAndroid Build Coastguard Worker                               ICmpInst::ICMP_SLT : ICmpInst::ICMP_ULT,
300*9880d681SAndroid Build Coastguard Worker                               LessOne, X))
301*9880d681SAndroid Build Coastguard Worker       return;
302*9880d681SAndroid Build Coastguard Worker 
303*9880d681SAndroid Build Coastguard Worker     ICmpInst *ICmp = new ICmpInst(Rem, ICmpInst::ICMP_EQ,
304*9880d681SAndroid Build Coastguard Worker                                   Rem->getOperand(0), Rem->getOperand(1));
305*9880d681SAndroid Build Coastguard Worker     SelectInst *Sel =
306*9880d681SAndroid Build Coastguard Worker       SelectInst::Create(ICmp,
307*9880d681SAndroid Build Coastguard Worker                          ConstantInt::get(Rem->getType(), 0),
308*9880d681SAndroid Build Coastguard Worker                          Rem->getOperand(0), "tmp", Rem);
309*9880d681SAndroid Build Coastguard Worker     Rem->replaceAllUsesWith(Sel);
310*9880d681SAndroid Build Coastguard Worker   }
311*9880d681SAndroid Build Coastguard Worker 
312*9880d681SAndroid Build Coastguard Worker   DEBUG(dbgs() << "INDVARS: Simplified rem: " << *Rem << '\n');
313*9880d681SAndroid Build Coastguard Worker   ++NumElimRem;
314*9880d681SAndroid Build Coastguard Worker   Changed = true;
315*9880d681SAndroid Build Coastguard Worker   DeadInsts.emplace_back(Rem);
316*9880d681SAndroid Build Coastguard Worker }
317*9880d681SAndroid Build Coastguard Worker 
eliminateOverflowIntrinsic(CallInst * CI)318*9880d681SAndroid Build Coastguard Worker bool SimplifyIndvar::eliminateOverflowIntrinsic(CallInst *CI) {
319*9880d681SAndroid Build Coastguard Worker   auto *F = CI->getCalledFunction();
320*9880d681SAndroid Build Coastguard Worker   if (!F)
321*9880d681SAndroid Build Coastguard Worker     return false;
322*9880d681SAndroid Build Coastguard Worker 
323*9880d681SAndroid Build Coastguard Worker   typedef const SCEV *(ScalarEvolution::*OperationFunctionTy)(
324*9880d681SAndroid Build Coastguard Worker       const SCEV *, const SCEV *, SCEV::NoWrapFlags);
325*9880d681SAndroid Build Coastguard Worker   typedef const SCEV *(ScalarEvolution::*ExtensionFunctionTy)(
326*9880d681SAndroid Build Coastguard Worker       const SCEV *, Type *);
327*9880d681SAndroid Build Coastguard Worker 
328*9880d681SAndroid Build Coastguard Worker   OperationFunctionTy Operation;
329*9880d681SAndroid Build Coastguard Worker   ExtensionFunctionTy Extension;
330*9880d681SAndroid Build Coastguard Worker 
331*9880d681SAndroid Build Coastguard Worker   Instruction::BinaryOps RawOp;
332*9880d681SAndroid Build Coastguard Worker 
333*9880d681SAndroid Build Coastguard Worker   // We always have exactly one of nsw or nuw.  If NoSignedOverflow is false, we
334*9880d681SAndroid Build Coastguard Worker   // have nuw.
335*9880d681SAndroid Build Coastguard Worker   bool NoSignedOverflow;
336*9880d681SAndroid Build Coastguard Worker 
337*9880d681SAndroid Build Coastguard Worker   switch (F->getIntrinsicID()) {
338*9880d681SAndroid Build Coastguard Worker   default:
339*9880d681SAndroid Build Coastguard Worker     return false;
340*9880d681SAndroid Build Coastguard Worker 
341*9880d681SAndroid Build Coastguard Worker   case Intrinsic::sadd_with_overflow:
342*9880d681SAndroid Build Coastguard Worker     Operation = &ScalarEvolution::getAddExpr;
343*9880d681SAndroid Build Coastguard Worker     Extension = &ScalarEvolution::getSignExtendExpr;
344*9880d681SAndroid Build Coastguard Worker     RawOp = Instruction::Add;
345*9880d681SAndroid Build Coastguard Worker     NoSignedOverflow = true;
346*9880d681SAndroid Build Coastguard Worker     break;
347*9880d681SAndroid Build Coastguard Worker 
348*9880d681SAndroid Build Coastguard Worker   case Intrinsic::uadd_with_overflow:
349*9880d681SAndroid Build Coastguard Worker     Operation = &ScalarEvolution::getAddExpr;
350*9880d681SAndroid Build Coastguard Worker     Extension = &ScalarEvolution::getZeroExtendExpr;
351*9880d681SAndroid Build Coastguard Worker     RawOp = Instruction::Add;
352*9880d681SAndroid Build Coastguard Worker     NoSignedOverflow = false;
353*9880d681SAndroid Build Coastguard Worker     break;
354*9880d681SAndroid Build Coastguard Worker 
355*9880d681SAndroid Build Coastguard Worker   case Intrinsic::ssub_with_overflow:
356*9880d681SAndroid Build Coastguard Worker     Operation = &ScalarEvolution::getMinusSCEV;
357*9880d681SAndroid Build Coastguard Worker     Extension = &ScalarEvolution::getSignExtendExpr;
358*9880d681SAndroid Build Coastguard Worker     RawOp = Instruction::Sub;
359*9880d681SAndroid Build Coastguard Worker     NoSignedOverflow = true;
360*9880d681SAndroid Build Coastguard Worker     break;
361*9880d681SAndroid Build Coastguard Worker 
362*9880d681SAndroid Build Coastguard Worker   case Intrinsic::usub_with_overflow:
363*9880d681SAndroid Build Coastguard Worker     Operation = &ScalarEvolution::getMinusSCEV;
364*9880d681SAndroid Build Coastguard Worker     Extension = &ScalarEvolution::getZeroExtendExpr;
365*9880d681SAndroid Build Coastguard Worker     RawOp = Instruction::Sub;
366*9880d681SAndroid Build Coastguard Worker     NoSignedOverflow = false;
367*9880d681SAndroid Build Coastguard Worker     break;
368*9880d681SAndroid Build Coastguard Worker   }
369*9880d681SAndroid Build Coastguard Worker 
370*9880d681SAndroid Build Coastguard Worker   const SCEV *LHS = SE->getSCEV(CI->getArgOperand(0));
371*9880d681SAndroid Build Coastguard Worker   const SCEV *RHS = SE->getSCEV(CI->getArgOperand(1));
372*9880d681SAndroid Build Coastguard Worker 
373*9880d681SAndroid Build Coastguard Worker   auto *NarrowTy = cast<IntegerType>(LHS->getType());
374*9880d681SAndroid Build Coastguard Worker   auto *WideTy =
375*9880d681SAndroid Build Coastguard Worker     IntegerType::get(NarrowTy->getContext(), NarrowTy->getBitWidth() * 2);
376*9880d681SAndroid Build Coastguard Worker 
377*9880d681SAndroid Build Coastguard Worker   const SCEV *A =
378*9880d681SAndroid Build Coastguard Worker       (SE->*Extension)((SE->*Operation)(LHS, RHS, SCEV::FlagAnyWrap), WideTy);
379*9880d681SAndroid Build Coastguard Worker   const SCEV *B =
380*9880d681SAndroid Build Coastguard Worker       (SE->*Operation)((SE->*Extension)(LHS, WideTy),
381*9880d681SAndroid Build Coastguard Worker                        (SE->*Extension)(RHS, WideTy), SCEV::FlagAnyWrap);
382*9880d681SAndroid Build Coastguard Worker 
383*9880d681SAndroid Build Coastguard Worker   if (A != B)
384*9880d681SAndroid Build Coastguard Worker     return false;
385*9880d681SAndroid Build Coastguard Worker 
386*9880d681SAndroid Build Coastguard Worker   // Proved no overflow, nuke the overflow check and, if possible, the overflow
387*9880d681SAndroid Build Coastguard Worker   // intrinsic as well.
388*9880d681SAndroid Build Coastguard Worker 
389*9880d681SAndroid Build Coastguard Worker   BinaryOperator *NewResult = BinaryOperator::Create(
390*9880d681SAndroid Build Coastguard Worker       RawOp, CI->getArgOperand(0), CI->getArgOperand(1), "", CI);
391*9880d681SAndroid Build Coastguard Worker 
392*9880d681SAndroid Build Coastguard Worker   if (NoSignedOverflow)
393*9880d681SAndroid Build Coastguard Worker     NewResult->setHasNoSignedWrap(true);
394*9880d681SAndroid Build Coastguard Worker   else
395*9880d681SAndroid Build Coastguard Worker     NewResult->setHasNoUnsignedWrap(true);
396*9880d681SAndroid Build Coastguard Worker 
397*9880d681SAndroid Build Coastguard Worker   SmallVector<ExtractValueInst *, 4> ToDelete;
398*9880d681SAndroid Build Coastguard Worker 
399*9880d681SAndroid Build Coastguard Worker   for (auto *U : CI->users()) {
400*9880d681SAndroid Build Coastguard Worker     if (auto *EVI = dyn_cast<ExtractValueInst>(U)) {
401*9880d681SAndroid Build Coastguard Worker       if (EVI->getIndices()[0] == 1)
402*9880d681SAndroid Build Coastguard Worker         EVI->replaceAllUsesWith(ConstantInt::getFalse(CI->getContext()));
403*9880d681SAndroid Build Coastguard Worker       else {
404*9880d681SAndroid Build Coastguard Worker         assert(EVI->getIndices()[0] == 0 && "Only two possibilities!");
405*9880d681SAndroid Build Coastguard Worker         EVI->replaceAllUsesWith(NewResult);
406*9880d681SAndroid Build Coastguard Worker       }
407*9880d681SAndroid Build Coastguard Worker       ToDelete.push_back(EVI);
408*9880d681SAndroid Build Coastguard Worker     }
409*9880d681SAndroid Build Coastguard Worker   }
410*9880d681SAndroid Build Coastguard Worker 
411*9880d681SAndroid Build Coastguard Worker   for (auto *EVI : ToDelete)
412*9880d681SAndroid Build Coastguard Worker     EVI->eraseFromParent();
413*9880d681SAndroid Build Coastguard Worker 
414*9880d681SAndroid Build Coastguard Worker   if (CI->use_empty())
415*9880d681SAndroid Build Coastguard Worker     CI->eraseFromParent();
416*9880d681SAndroid Build Coastguard Worker 
417*9880d681SAndroid Build Coastguard Worker   return true;
418*9880d681SAndroid Build Coastguard Worker }
419*9880d681SAndroid Build Coastguard Worker 
420*9880d681SAndroid Build Coastguard Worker /// Eliminate an operation that consumes a simple IV and has no observable
421*9880d681SAndroid Build Coastguard Worker /// side-effect given the range of IV values.  IVOperand is guaranteed SCEVable,
422*9880d681SAndroid Build Coastguard Worker /// but UseInst may not be.
eliminateIVUser(Instruction * UseInst,Instruction * IVOperand)423*9880d681SAndroid Build Coastguard Worker bool SimplifyIndvar::eliminateIVUser(Instruction *UseInst,
424*9880d681SAndroid Build Coastguard Worker                                      Instruction *IVOperand) {
425*9880d681SAndroid Build Coastguard Worker   if (ICmpInst *ICmp = dyn_cast<ICmpInst>(UseInst)) {
426*9880d681SAndroid Build Coastguard Worker     eliminateIVComparison(ICmp, IVOperand);
427*9880d681SAndroid Build Coastguard Worker     return true;
428*9880d681SAndroid Build Coastguard Worker   }
429*9880d681SAndroid Build Coastguard Worker   if (BinaryOperator *Rem = dyn_cast<BinaryOperator>(UseInst)) {
430*9880d681SAndroid Build Coastguard Worker     bool IsSigned = Rem->getOpcode() == Instruction::SRem;
431*9880d681SAndroid Build Coastguard Worker     if (IsSigned || Rem->getOpcode() == Instruction::URem) {
432*9880d681SAndroid Build Coastguard Worker       eliminateIVRemainder(Rem, IVOperand, IsSigned);
433*9880d681SAndroid Build Coastguard Worker       return true;
434*9880d681SAndroid Build Coastguard Worker     }
435*9880d681SAndroid Build Coastguard Worker   }
436*9880d681SAndroid Build Coastguard Worker 
437*9880d681SAndroid Build Coastguard Worker   if (auto *CI = dyn_cast<CallInst>(UseInst))
438*9880d681SAndroid Build Coastguard Worker     if (eliminateOverflowIntrinsic(CI))
439*9880d681SAndroid Build Coastguard Worker       return true;
440*9880d681SAndroid Build Coastguard Worker 
441*9880d681SAndroid Build Coastguard Worker   if (eliminateIdentitySCEV(UseInst, IVOperand))
442*9880d681SAndroid Build Coastguard Worker     return true;
443*9880d681SAndroid Build Coastguard Worker 
444*9880d681SAndroid Build Coastguard Worker   return false;
445*9880d681SAndroid Build Coastguard Worker }
446*9880d681SAndroid Build Coastguard Worker 
447*9880d681SAndroid Build Coastguard Worker /// Eliminate any operation that SCEV can prove is an identity function.
eliminateIdentitySCEV(Instruction * UseInst,Instruction * IVOperand)448*9880d681SAndroid Build Coastguard Worker bool SimplifyIndvar::eliminateIdentitySCEV(Instruction *UseInst,
449*9880d681SAndroid Build Coastguard Worker                                            Instruction *IVOperand) {
450*9880d681SAndroid Build Coastguard Worker   if (!SE->isSCEVable(UseInst->getType()) ||
451*9880d681SAndroid Build Coastguard Worker       (UseInst->getType() != IVOperand->getType()) ||
452*9880d681SAndroid Build Coastguard Worker       (SE->getSCEV(UseInst) != SE->getSCEV(IVOperand)))
453*9880d681SAndroid Build Coastguard Worker     return false;
454*9880d681SAndroid Build Coastguard Worker 
455*9880d681SAndroid Build Coastguard Worker   // getSCEV(X) == getSCEV(Y) does not guarantee that X and Y are related in the
456*9880d681SAndroid Build Coastguard Worker   // dominator tree, even if X is an operand to Y.  For instance, in
457*9880d681SAndroid Build Coastguard Worker   //
458*9880d681SAndroid Build Coastguard Worker   //     %iv = phi i32 {0,+,1}
459*9880d681SAndroid Build Coastguard Worker   //     br %cond, label %left, label %merge
460*9880d681SAndroid Build Coastguard Worker   //
461*9880d681SAndroid Build Coastguard Worker   //   left:
462*9880d681SAndroid Build Coastguard Worker   //     %X = add i32 %iv, 0
463*9880d681SAndroid Build Coastguard Worker   //     br label %merge
464*9880d681SAndroid Build Coastguard Worker   //
465*9880d681SAndroid Build Coastguard Worker   //   merge:
466*9880d681SAndroid Build Coastguard Worker   //     %M = phi (%X, %iv)
467*9880d681SAndroid Build Coastguard Worker   //
468*9880d681SAndroid Build Coastguard Worker   // getSCEV(%M) == getSCEV(%X) == {0,+,1}, but %X does not dominate %M, and
469*9880d681SAndroid Build Coastguard Worker   // %M.replaceAllUsesWith(%X) would be incorrect.
470*9880d681SAndroid Build Coastguard Worker 
471*9880d681SAndroid Build Coastguard Worker   if (isa<PHINode>(UseInst))
472*9880d681SAndroid Build Coastguard Worker     // If UseInst is not a PHI node then we know that IVOperand dominates
473*9880d681SAndroid Build Coastguard Worker     // UseInst directly from the legality of SSA.
474*9880d681SAndroid Build Coastguard Worker     if (!DT || !DT->dominates(IVOperand, UseInst))
475*9880d681SAndroid Build Coastguard Worker       return false;
476*9880d681SAndroid Build Coastguard Worker 
477*9880d681SAndroid Build Coastguard Worker   if (!LI->replacementPreservesLCSSAForm(UseInst, IVOperand))
478*9880d681SAndroid Build Coastguard Worker     return false;
479*9880d681SAndroid Build Coastguard Worker 
480*9880d681SAndroid Build Coastguard Worker   DEBUG(dbgs() << "INDVARS: Eliminated identity: " << *UseInst << '\n');
481*9880d681SAndroid Build Coastguard Worker 
482*9880d681SAndroid Build Coastguard Worker   UseInst->replaceAllUsesWith(IVOperand);
483*9880d681SAndroid Build Coastguard Worker   ++NumElimIdentity;
484*9880d681SAndroid Build Coastguard Worker   Changed = true;
485*9880d681SAndroid Build Coastguard Worker   DeadInsts.emplace_back(UseInst);
486*9880d681SAndroid Build Coastguard Worker   return true;
487*9880d681SAndroid Build Coastguard Worker }
488*9880d681SAndroid Build Coastguard Worker 
489*9880d681SAndroid Build Coastguard Worker /// Annotate BO with nsw / nuw if it provably does not signed-overflow /
490*9880d681SAndroid Build Coastguard Worker /// unsigned-overflow.  Returns true if anything changed, false otherwise.
strengthenOverflowingOperation(BinaryOperator * BO,Value * IVOperand)491*9880d681SAndroid Build Coastguard Worker bool SimplifyIndvar::strengthenOverflowingOperation(BinaryOperator *BO,
492*9880d681SAndroid Build Coastguard Worker                                                     Value *IVOperand) {
493*9880d681SAndroid Build Coastguard Worker 
494*9880d681SAndroid Build Coastguard Worker   // Fastpath: we don't have any work to do if `BO` is `nuw` and `nsw`.
495*9880d681SAndroid Build Coastguard Worker   if (BO->hasNoUnsignedWrap() && BO->hasNoSignedWrap())
496*9880d681SAndroid Build Coastguard Worker     return false;
497*9880d681SAndroid Build Coastguard Worker 
498*9880d681SAndroid Build Coastguard Worker   const SCEV *(ScalarEvolution::*GetExprForBO)(const SCEV *, const SCEV *,
499*9880d681SAndroid Build Coastguard Worker                                                SCEV::NoWrapFlags);
500*9880d681SAndroid Build Coastguard Worker 
501*9880d681SAndroid Build Coastguard Worker   switch (BO->getOpcode()) {
502*9880d681SAndroid Build Coastguard Worker   default:
503*9880d681SAndroid Build Coastguard Worker     return false;
504*9880d681SAndroid Build Coastguard Worker 
505*9880d681SAndroid Build Coastguard Worker   case Instruction::Add:
506*9880d681SAndroid Build Coastguard Worker     GetExprForBO = &ScalarEvolution::getAddExpr;
507*9880d681SAndroid Build Coastguard Worker     break;
508*9880d681SAndroid Build Coastguard Worker 
509*9880d681SAndroid Build Coastguard Worker   case Instruction::Sub:
510*9880d681SAndroid Build Coastguard Worker     GetExprForBO = &ScalarEvolution::getMinusSCEV;
511*9880d681SAndroid Build Coastguard Worker     break;
512*9880d681SAndroid Build Coastguard Worker 
513*9880d681SAndroid Build Coastguard Worker   case Instruction::Mul:
514*9880d681SAndroid Build Coastguard Worker     GetExprForBO = &ScalarEvolution::getMulExpr;
515*9880d681SAndroid Build Coastguard Worker     break;
516*9880d681SAndroid Build Coastguard Worker   }
517*9880d681SAndroid Build Coastguard Worker 
518*9880d681SAndroid Build Coastguard Worker   unsigned BitWidth = cast<IntegerType>(BO->getType())->getBitWidth();
519*9880d681SAndroid Build Coastguard Worker   Type *WideTy = IntegerType::get(BO->getContext(), BitWidth * 2);
520*9880d681SAndroid Build Coastguard Worker   const SCEV *LHS = SE->getSCEV(BO->getOperand(0));
521*9880d681SAndroid Build Coastguard Worker   const SCEV *RHS = SE->getSCEV(BO->getOperand(1));
522*9880d681SAndroid Build Coastguard Worker 
523*9880d681SAndroid Build Coastguard Worker   bool Changed = false;
524*9880d681SAndroid Build Coastguard Worker 
525*9880d681SAndroid Build Coastguard Worker   if (!BO->hasNoUnsignedWrap()) {
526*9880d681SAndroid Build Coastguard Worker     const SCEV *ExtendAfterOp = SE->getZeroExtendExpr(SE->getSCEV(BO), WideTy);
527*9880d681SAndroid Build Coastguard Worker     const SCEV *OpAfterExtend = (SE->*GetExprForBO)(
528*9880d681SAndroid Build Coastguard Worker       SE->getZeroExtendExpr(LHS, WideTy), SE->getZeroExtendExpr(RHS, WideTy),
529*9880d681SAndroid Build Coastguard Worker       SCEV::FlagAnyWrap);
530*9880d681SAndroid Build Coastguard Worker     if (ExtendAfterOp == OpAfterExtend) {
531*9880d681SAndroid Build Coastguard Worker       BO->setHasNoUnsignedWrap();
532*9880d681SAndroid Build Coastguard Worker       SE->forgetValue(BO);
533*9880d681SAndroid Build Coastguard Worker       Changed = true;
534*9880d681SAndroid Build Coastguard Worker     }
535*9880d681SAndroid Build Coastguard Worker   }
536*9880d681SAndroid Build Coastguard Worker 
537*9880d681SAndroid Build Coastguard Worker   if (!BO->hasNoSignedWrap()) {
538*9880d681SAndroid Build Coastguard Worker     const SCEV *ExtendAfterOp = SE->getSignExtendExpr(SE->getSCEV(BO), WideTy);
539*9880d681SAndroid Build Coastguard Worker     const SCEV *OpAfterExtend = (SE->*GetExprForBO)(
540*9880d681SAndroid Build Coastguard Worker       SE->getSignExtendExpr(LHS, WideTy), SE->getSignExtendExpr(RHS, WideTy),
541*9880d681SAndroid Build Coastguard Worker       SCEV::FlagAnyWrap);
542*9880d681SAndroid Build Coastguard Worker     if (ExtendAfterOp == OpAfterExtend) {
543*9880d681SAndroid Build Coastguard Worker       BO->setHasNoSignedWrap();
544*9880d681SAndroid Build Coastguard Worker       SE->forgetValue(BO);
545*9880d681SAndroid Build Coastguard Worker       Changed = true;
546*9880d681SAndroid Build Coastguard Worker     }
547*9880d681SAndroid Build Coastguard Worker   }
548*9880d681SAndroid Build Coastguard Worker 
549*9880d681SAndroid Build Coastguard Worker   return Changed;
550*9880d681SAndroid Build Coastguard Worker }
551*9880d681SAndroid Build Coastguard Worker 
552*9880d681SAndroid Build Coastguard Worker /// Add all uses of Def to the current IV's worklist.
pushIVUsers(Instruction * Def,SmallPtrSet<Instruction *,16> & Simplified,SmallVectorImpl<std::pair<Instruction *,Instruction * >> & SimpleIVUsers)553*9880d681SAndroid Build Coastguard Worker static void pushIVUsers(
554*9880d681SAndroid Build Coastguard Worker   Instruction *Def,
555*9880d681SAndroid Build Coastguard Worker   SmallPtrSet<Instruction*,16> &Simplified,
556*9880d681SAndroid Build Coastguard Worker   SmallVectorImpl< std::pair<Instruction*,Instruction*> > &SimpleIVUsers) {
557*9880d681SAndroid Build Coastguard Worker 
558*9880d681SAndroid Build Coastguard Worker   for (User *U : Def->users()) {
559*9880d681SAndroid Build Coastguard Worker     Instruction *UI = cast<Instruction>(U);
560*9880d681SAndroid Build Coastguard Worker 
561*9880d681SAndroid Build Coastguard Worker     // Avoid infinite or exponential worklist processing.
562*9880d681SAndroid Build Coastguard Worker     // Also ensure unique worklist users.
563*9880d681SAndroid Build Coastguard Worker     // If Def is a LoopPhi, it may not be in the Simplified set, so check for
564*9880d681SAndroid Build Coastguard Worker     // self edges first.
565*9880d681SAndroid Build Coastguard Worker     if (UI != Def && Simplified.insert(UI).second)
566*9880d681SAndroid Build Coastguard Worker       SimpleIVUsers.push_back(std::make_pair(UI, Def));
567*9880d681SAndroid Build Coastguard Worker   }
568*9880d681SAndroid Build Coastguard Worker }
569*9880d681SAndroid Build Coastguard Worker 
570*9880d681SAndroid Build Coastguard Worker /// Return true if this instruction generates a simple SCEV
571*9880d681SAndroid Build Coastguard Worker /// expression in terms of that IV.
572*9880d681SAndroid Build Coastguard Worker ///
573*9880d681SAndroid Build Coastguard Worker /// This is similar to IVUsers' isInteresting() but processes each instruction
574*9880d681SAndroid Build Coastguard Worker /// non-recursively when the operand is already known to be a simpleIVUser.
575*9880d681SAndroid Build Coastguard Worker ///
isSimpleIVUser(Instruction * I,const Loop * L,ScalarEvolution * SE)576*9880d681SAndroid Build Coastguard Worker static bool isSimpleIVUser(Instruction *I, const Loop *L, ScalarEvolution *SE) {
577*9880d681SAndroid Build Coastguard Worker   if (!SE->isSCEVable(I->getType()))
578*9880d681SAndroid Build Coastguard Worker     return false;
579*9880d681SAndroid Build Coastguard Worker 
580*9880d681SAndroid Build Coastguard Worker   // Get the symbolic expression for this instruction.
581*9880d681SAndroid Build Coastguard Worker   const SCEV *S = SE->getSCEV(I);
582*9880d681SAndroid Build Coastguard Worker 
583*9880d681SAndroid Build Coastguard Worker   // Only consider affine recurrences.
584*9880d681SAndroid Build Coastguard Worker   const SCEVAddRecExpr *AR = dyn_cast<SCEVAddRecExpr>(S);
585*9880d681SAndroid Build Coastguard Worker   if (AR && AR->getLoop() == L)
586*9880d681SAndroid Build Coastguard Worker     return true;
587*9880d681SAndroid Build Coastguard Worker 
588*9880d681SAndroid Build Coastguard Worker   return false;
589*9880d681SAndroid Build Coastguard Worker }
590*9880d681SAndroid Build Coastguard Worker 
591*9880d681SAndroid Build Coastguard Worker /// Iteratively perform simplification on a worklist of users
592*9880d681SAndroid Build Coastguard Worker /// of the specified induction variable. Each successive simplification may push
593*9880d681SAndroid Build Coastguard Worker /// more users which may themselves be candidates for simplification.
594*9880d681SAndroid Build Coastguard Worker ///
595*9880d681SAndroid Build Coastguard Worker /// This algorithm does not require IVUsers analysis. Instead, it simplifies
596*9880d681SAndroid Build Coastguard Worker /// instructions in-place during analysis. Rather than rewriting induction
597*9880d681SAndroid Build Coastguard Worker /// variables bottom-up from their users, it transforms a chain of IVUsers
598*9880d681SAndroid Build Coastguard Worker /// top-down, updating the IR only when it encounters a clear optimization
599*9880d681SAndroid Build Coastguard Worker /// opportunity.
600*9880d681SAndroid Build Coastguard Worker ///
601*9880d681SAndroid Build Coastguard Worker /// Once DisableIVRewrite is default, LSR will be the only client of IVUsers.
602*9880d681SAndroid Build Coastguard Worker ///
simplifyUsers(PHINode * CurrIV,IVVisitor * V)603*9880d681SAndroid Build Coastguard Worker void SimplifyIndvar::simplifyUsers(PHINode *CurrIV, IVVisitor *V) {
604*9880d681SAndroid Build Coastguard Worker   if (!SE->isSCEVable(CurrIV->getType()))
605*9880d681SAndroid Build Coastguard Worker     return;
606*9880d681SAndroid Build Coastguard Worker 
607*9880d681SAndroid Build Coastguard Worker   // Instructions processed by SimplifyIndvar for CurrIV.
608*9880d681SAndroid Build Coastguard Worker   SmallPtrSet<Instruction*,16> Simplified;
609*9880d681SAndroid Build Coastguard Worker 
610*9880d681SAndroid Build Coastguard Worker   // Use-def pairs if IV users waiting to be processed for CurrIV.
611*9880d681SAndroid Build Coastguard Worker   SmallVector<std::pair<Instruction*, Instruction*>, 8> SimpleIVUsers;
612*9880d681SAndroid Build Coastguard Worker 
613*9880d681SAndroid Build Coastguard Worker   // Push users of the current LoopPhi. In rare cases, pushIVUsers may be
614*9880d681SAndroid Build Coastguard Worker   // called multiple times for the same LoopPhi. This is the proper thing to
615*9880d681SAndroid Build Coastguard Worker   // do for loop header phis that use each other.
616*9880d681SAndroid Build Coastguard Worker   pushIVUsers(CurrIV, Simplified, SimpleIVUsers);
617*9880d681SAndroid Build Coastguard Worker 
618*9880d681SAndroid Build Coastguard Worker   while (!SimpleIVUsers.empty()) {
619*9880d681SAndroid Build Coastguard Worker     std::pair<Instruction*, Instruction*> UseOper =
620*9880d681SAndroid Build Coastguard Worker       SimpleIVUsers.pop_back_val();
621*9880d681SAndroid Build Coastguard Worker     Instruction *UseInst = UseOper.first;
622*9880d681SAndroid Build Coastguard Worker 
623*9880d681SAndroid Build Coastguard Worker     // Bypass back edges to avoid extra work.
624*9880d681SAndroid Build Coastguard Worker     if (UseInst == CurrIV) continue;
625*9880d681SAndroid Build Coastguard Worker 
626*9880d681SAndroid Build Coastguard Worker     Instruction *IVOperand = UseOper.second;
627*9880d681SAndroid Build Coastguard Worker     for (unsigned N = 0; IVOperand; ++N) {
628*9880d681SAndroid Build Coastguard Worker       assert(N <= Simplified.size() && "runaway iteration");
629*9880d681SAndroid Build Coastguard Worker 
630*9880d681SAndroid Build Coastguard Worker       Value *NewOper = foldIVUser(UseOper.first, IVOperand);
631*9880d681SAndroid Build Coastguard Worker       if (!NewOper)
632*9880d681SAndroid Build Coastguard Worker         break; // done folding
633*9880d681SAndroid Build Coastguard Worker       IVOperand = dyn_cast<Instruction>(NewOper);
634*9880d681SAndroid Build Coastguard Worker     }
635*9880d681SAndroid Build Coastguard Worker     if (!IVOperand)
636*9880d681SAndroid Build Coastguard Worker       continue;
637*9880d681SAndroid Build Coastguard Worker 
638*9880d681SAndroid Build Coastguard Worker     if (eliminateIVUser(UseOper.first, IVOperand)) {
639*9880d681SAndroid Build Coastguard Worker       pushIVUsers(IVOperand, Simplified, SimpleIVUsers);
640*9880d681SAndroid Build Coastguard Worker       continue;
641*9880d681SAndroid Build Coastguard Worker     }
642*9880d681SAndroid Build Coastguard Worker 
643*9880d681SAndroid Build Coastguard Worker     if (BinaryOperator *BO = dyn_cast<BinaryOperator>(UseOper.first)) {
644*9880d681SAndroid Build Coastguard Worker       if (isa<OverflowingBinaryOperator>(BO) &&
645*9880d681SAndroid Build Coastguard Worker           strengthenOverflowingOperation(BO, IVOperand)) {
646*9880d681SAndroid Build Coastguard Worker         // re-queue uses of the now modified binary operator and fall
647*9880d681SAndroid Build Coastguard Worker         // through to the checks that remain.
648*9880d681SAndroid Build Coastguard Worker         pushIVUsers(IVOperand, Simplified, SimpleIVUsers);
649*9880d681SAndroid Build Coastguard Worker       }
650*9880d681SAndroid Build Coastguard Worker     }
651*9880d681SAndroid Build Coastguard Worker 
652*9880d681SAndroid Build Coastguard Worker     CastInst *Cast = dyn_cast<CastInst>(UseOper.first);
653*9880d681SAndroid Build Coastguard Worker     if (V && Cast) {
654*9880d681SAndroid Build Coastguard Worker       V->visitCast(Cast);
655*9880d681SAndroid Build Coastguard Worker       continue;
656*9880d681SAndroid Build Coastguard Worker     }
657*9880d681SAndroid Build Coastguard Worker     if (isSimpleIVUser(UseOper.first, L, SE)) {
658*9880d681SAndroid Build Coastguard Worker       pushIVUsers(UseOper.first, Simplified, SimpleIVUsers);
659*9880d681SAndroid Build Coastguard Worker     }
660*9880d681SAndroid Build Coastguard Worker   }
661*9880d681SAndroid Build Coastguard Worker }
662*9880d681SAndroid Build Coastguard Worker 
663*9880d681SAndroid Build Coastguard Worker namespace llvm {
664*9880d681SAndroid Build Coastguard Worker 
anchor()665*9880d681SAndroid Build Coastguard Worker void IVVisitor::anchor() { }
666*9880d681SAndroid Build Coastguard Worker 
667*9880d681SAndroid Build Coastguard Worker /// Simplify instructions that use this induction variable
668*9880d681SAndroid Build Coastguard Worker /// by using ScalarEvolution to analyze the IV's recurrence.
simplifyUsersOfIV(PHINode * CurrIV,ScalarEvolution * SE,DominatorTree * DT,LoopInfo * LI,SmallVectorImpl<WeakVH> & Dead,IVVisitor * V)669*9880d681SAndroid Build Coastguard Worker bool simplifyUsersOfIV(PHINode *CurrIV, ScalarEvolution *SE, DominatorTree *DT,
670*9880d681SAndroid Build Coastguard Worker                        LoopInfo *LI, SmallVectorImpl<WeakVH> &Dead,
671*9880d681SAndroid Build Coastguard Worker                        IVVisitor *V) {
672*9880d681SAndroid Build Coastguard Worker   SimplifyIndvar SIV(LI->getLoopFor(CurrIV->getParent()), SE, DT, LI, Dead);
673*9880d681SAndroid Build Coastguard Worker   SIV.simplifyUsers(CurrIV, V);
674*9880d681SAndroid Build Coastguard Worker   return SIV.hasChanged();
675*9880d681SAndroid Build Coastguard Worker }
676*9880d681SAndroid Build Coastguard Worker 
677*9880d681SAndroid Build Coastguard Worker /// Simplify users of induction variables within this
678*9880d681SAndroid Build Coastguard Worker /// loop. This does not actually change or add IVs.
simplifyLoopIVs(Loop * L,ScalarEvolution * SE,DominatorTree * DT,LoopInfo * LI,SmallVectorImpl<WeakVH> & Dead)679*9880d681SAndroid Build Coastguard Worker bool simplifyLoopIVs(Loop *L, ScalarEvolution *SE, DominatorTree *DT,
680*9880d681SAndroid Build Coastguard Worker                      LoopInfo *LI, SmallVectorImpl<WeakVH> &Dead) {
681*9880d681SAndroid Build Coastguard Worker   bool Changed = false;
682*9880d681SAndroid Build Coastguard Worker   for (BasicBlock::iterator I = L->getHeader()->begin(); isa<PHINode>(I); ++I) {
683*9880d681SAndroid Build Coastguard Worker     Changed |= simplifyUsersOfIV(cast<PHINode>(I), SE, DT, LI, Dead);
684*9880d681SAndroid Build Coastguard Worker   }
685*9880d681SAndroid Build Coastguard Worker   return Changed;
686*9880d681SAndroid Build Coastguard Worker }
687*9880d681SAndroid Build Coastguard Worker 
688*9880d681SAndroid Build Coastguard Worker } // namespace llvm
689