1 //===- llvm/Analysis/ScalarEvolutionExpressions.h - SCEV Exprs --*- C++ -*-===//
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
9 // This file defines the classes used to represent and build scalar expressions.
11 //===----------------------------------------------------------------------===//
13 #ifndef LLVM_ANALYSIS_SCALAREVOLUTIONEXPRESSIONS_H
14 #define LLVM_ANALYSIS_SCALAREVOLUTIONEXPRESSIONS_H
16 #include "llvm/ADT/DenseMap.h"
17 #include "llvm/ADT/FoldingSet.h"
18 #include "llvm/ADT/SmallPtrSet.h"
19 #include "llvm/ADT/SmallVector.h"
20 #include "llvm/ADT/iterator_range.h"
21 #include "llvm/Analysis/ScalarEvolution.h"
22 #include "llvm/IR/Constants.h"
23 #include "llvm/IR/Value.h"
24 #include "llvm/IR/ValueHandle.h"
25 #include "llvm/Support/Casting.h"
26 #include "llvm/Support/ErrorHandling.h"
39 // These should be ordered in terms of increasing complexity to make the
41 scConstant
, scTruncate
, scZeroExtend
, scSignExtend
, scAddExpr
, scMulExpr
,
42 scUDivExpr
, scAddRecExpr
, scUMaxExpr
, scSMaxExpr
, scUMinExpr
, scSMinExpr
,
43 scUnknown
, scCouldNotCompute
46 /// This class represents a constant integer value.
47 class SCEVConstant
: public SCEV
{
48 friend class ScalarEvolution
;
52 SCEVConstant(const FoldingSetNodeIDRef ID
, ConstantInt
*v
) :
53 SCEV(ID
, scConstant
, 1), V(v
) {}
56 ConstantInt
*getValue() const { return V
; }
57 const APInt
&getAPInt() const { return getValue()->getValue(); }
59 Type
*getType() const { return V
->getType(); }
61 /// Methods for support type inquiry through isa, cast, and dyn_cast:
62 static bool classof(const SCEV
*S
) {
63 return S
->getSCEVType() == scConstant
;
67 static unsigned short computeExpressionSize(ArrayRef
<const SCEV
*> Args
) {
69 for (auto *Arg
: Args
)
70 Size
= Size
.uadd_sat(APInt(16, Arg
->getExpressionSize()));
71 return (unsigned short)Size
.getZExtValue();
74 /// This is the base class for unary cast operator classes.
75 class SCEVCastExpr
: public SCEV
{
80 SCEVCastExpr(const FoldingSetNodeIDRef ID
,
81 unsigned SCEVTy
, const SCEV
*op
, Type
*ty
);
84 const SCEV
*getOperand() const { return Op
; }
85 Type
*getType() const { return Ty
; }
87 /// Methods for support type inquiry through isa, cast, and dyn_cast:
88 static bool classof(const SCEV
*S
) {
89 return S
->getSCEVType() == scTruncate
||
90 S
->getSCEVType() == scZeroExtend
||
91 S
->getSCEVType() == scSignExtend
;
95 /// This class represents a truncation of an integer value to a
96 /// smaller integer value.
97 class SCEVTruncateExpr
: public SCEVCastExpr
{
98 friend class ScalarEvolution
;
100 SCEVTruncateExpr(const FoldingSetNodeIDRef ID
,
101 const SCEV
*op
, Type
*ty
);
104 /// Methods for support type inquiry through isa, cast, and dyn_cast:
105 static bool classof(const SCEV
*S
) {
106 return S
->getSCEVType() == scTruncate
;
110 /// This class represents a zero extension of a small integer value
111 /// to a larger integer value.
112 class SCEVZeroExtendExpr
: public SCEVCastExpr
{
113 friend class ScalarEvolution
;
115 SCEVZeroExtendExpr(const FoldingSetNodeIDRef ID
,
116 const SCEV
*op
, Type
*ty
);
119 /// Methods for support type inquiry through isa, cast, and dyn_cast:
120 static bool classof(const SCEV
*S
) {
121 return S
->getSCEVType() == scZeroExtend
;
125 /// This class represents a sign extension of a small integer value
126 /// to a larger integer value.
127 class SCEVSignExtendExpr
: public SCEVCastExpr
{
128 friend class ScalarEvolution
;
130 SCEVSignExtendExpr(const FoldingSetNodeIDRef ID
,
131 const SCEV
*op
, Type
*ty
);
134 /// Methods for support type inquiry through isa, cast, and dyn_cast:
135 static bool classof(const SCEV
*S
) {
136 return S
->getSCEVType() == scSignExtend
;
140 /// This node is a base class providing common functionality for
142 class SCEVNAryExpr
: public SCEV
{
144 // Since SCEVs are immutable, ScalarEvolution allocates operand
145 // arrays with its SCEVAllocator, so this class just needs a simple
146 // pointer rather than a more elaborate vector-like data structure.
147 // This also avoids the need for a non-trivial destructor.
148 const SCEV
*const *Operands
;
151 SCEVNAryExpr(const FoldingSetNodeIDRef ID
, enum SCEVTypes T
,
152 const SCEV
*const *O
, size_t N
)
153 : SCEV(ID
, T
, computeExpressionSize(makeArrayRef(O
, N
))), Operands(O
),
157 size_t getNumOperands() const { return NumOperands
; }
159 const SCEV
*getOperand(unsigned i
) const {
160 assert(i
< NumOperands
&& "Operand index out of range!");
164 using op_iterator
= const SCEV
*const *;
165 using op_range
= iterator_range
<op_iterator
>;
167 op_iterator
op_begin() const { return Operands
; }
168 op_iterator
op_end() const { return Operands
+ NumOperands
; }
169 op_range
operands() const {
170 return make_range(op_begin(), op_end());
173 Type
*getType() const { return getOperand(0)->getType(); }
175 NoWrapFlags
getNoWrapFlags(NoWrapFlags Mask
= NoWrapMask
) const {
176 return (NoWrapFlags
)(SubclassData
& Mask
);
179 bool hasNoUnsignedWrap() const {
180 return getNoWrapFlags(FlagNUW
) != FlagAnyWrap
;
183 bool hasNoSignedWrap() const {
184 return getNoWrapFlags(FlagNSW
) != FlagAnyWrap
;
187 bool hasNoSelfWrap() const {
188 return getNoWrapFlags(FlagNW
) != FlagAnyWrap
;
191 /// Methods for support type inquiry through isa, cast, and dyn_cast:
192 static bool classof(const SCEV
*S
) {
193 return S
->getSCEVType() == scAddExpr
|| S
->getSCEVType() == scMulExpr
||
194 S
->getSCEVType() == scSMaxExpr
|| S
->getSCEVType() == scUMaxExpr
||
195 S
->getSCEVType() == scSMinExpr
|| S
->getSCEVType() == scUMinExpr
||
196 S
->getSCEVType() == scAddRecExpr
;
200 /// This node is the base class for n'ary commutative operators.
201 class SCEVCommutativeExpr
: public SCEVNAryExpr
{
203 SCEVCommutativeExpr(const FoldingSetNodeIDRef ID
,
204 enum SCEVTypes T
, const SCEV
*const *O
, size_t N
)
205 : SCEVNAryExpr(ID
, T
, O
, N
) {}
208 /// Methods for support type inquiry through isa, cast, and dyn_cast:
209 static bool classof(const SCEV
*S
) {
210 return S
->getSCEVType() == scAddExpr
|| S
->getSCEVType() == scMulExpr
||
211 S
->getSCEVType() == scSMaxExpr
|| S
->getSCEVType() == scUMaxExpr
||
212 S
->getSCEVType() == scSMinExpr
|| S
->getSCEVType() == scUMinExpr
;
215 /// Set flags for a non-recurrence without clearing previously set flags.
216 void setNoWrapFlags(NoWrapFlags Flags
) {
217 SubclassData
|= Flags
;
221 /// This node represents an addition of some number of SCEVs.
222 class SCEVAddExpr
: public SCEVCommutativeExpr
{
223 friend class ScalarEvolution
;
225 SCEVAddExpr(const FoldingSetNodeIDRef ID
,
226 const SCEV
*const *O
, size_t N
)
227 : SCEVCommutativeExpr(ID
, scAddExpr
, O
, N
) {}
230 Type
*getType() const {
231 // Use the type of the last operand, which is likely to be a pointer
232 // type, if there is one. This doesn't usually matter, but it can help
233 // reduce casts when the expressions are expanded.
234 return getOperand(getNumOperands() - 1)->getType();
237 /// Methods for support type inquiry through isa, cast, and dyn_cast:
238 static bool classof(const SCEV
*S
) {
239 return S
->getSCEVType() == scAddExpr
;
243 /// This node represents multiplication of some number of SCEVs.
244 class SCEVMulExpr
: public SCEVCommutativeExpr
{
245 friend class ScalarEvolution
;
247 SCEVMulExpr(const FoldingSetNodeIDRef ID
,
248 const SCEV
*const *O
, size_t N
)
249 : SCEVCommutativeExpr(ID
, scMulExpr
, O
, N
) {}
252 /// Methods for support type inquiry through isa, cast, and dyn_cast:
253 static bool classof(const SCEV
*S
) {
254 return S
->getSCEVType() == scMulExpr
;
258 /// This class represents a binary unsigned division operation.
259 class SCEVUDivExpr
: public SCEV
{
260 friend class ScalarEvolution
;
265 SCEVUDivExpr(const FoldingSetNodeIDRef ID
, const SCEV
*lhs
, const SCEV
*rhs
)
266 : SCEV(ID
, scUDivExpr
, computeExpressionSize({lhs
, rhs
})), LHS(lhs
),
270 const SCEV
*getLHS() const { return LHS
; }
271 const SCEV
*getRHS() const { return RHS
; }
273 Type
*getType() const {
274 // In most cases the types of LHS and RHS will be the same, but in some
275 // crazy cases one or the other may be a pointer. ScalarEvolution doesn't
276 // depend on the type for correctness, but handling types carefully can
277 // avoid extra casts in the SCEVExpander. The LHS is more likely to be
278 // a pointer type than the RHS, so use the RHS' type here.
279 return getRHS()->getType();
282 /// Methods for support type inquiry through isa, cast, and dyn_cast:
283 static bool classof(const SCEV
*S
) {
284 return S
->getSCEVType() == scUDivExpr
;
288 /// This node represents a polynomial recurrence on the trip count
289 /// of the specified loop. This is the primary focus of the
290 /// ScalarEvolution framework; all the other SCEV subclasses are
291 /// mostly just supporting infrastructure to allow SCEVAddRecExpr
292 /// expressions to be created and analyzed.
294 /// All operands of an AddRec are required to be loop invariant.
296 class SCEVAddRecExpr
: public SCEVNAryExpr
{
297 friend class ScalarEvolution
;
301 SCEVAddRecExpr(const FoldingSetNodeIDRef ID
,
302 const SCEV
*const *O
, size_t N
, const Loop
*l
)
303 : SCEVNAryExpr(ID
, scAddRecExpr
, O
, N
), L(l
) {}
306 const SCEV
*getStart() const { return Operands
[0]; }
307 const Loop
*getLoop() const { return L
; }
309 /// Constructs and returns the recurrence indicating how much this
310 /// expression steps by. If this is a polynomial of degree N, it
311 /// returns a chrec of degree N-1. We cannot determine whether
312 /// the step recurrence has self-wraparound.
313 const SCEV
*getStepRecurrence(ScalarEvolution
&SE
) const {
314 if (isAffine()) return getOperand(1);
315 return SE
.getAddRecExpr(SmallVector
<const SCEV
*, 3>(op_begin()+1,
317 getLoop(), FlagAnyWrap
);
320 /// Return true if this represents an expression A + B*x where A
321 /// and B are loop invariant values.
322 bool isAffine() const {
323 // We know that the start value is invariant. This expression is thus
324 // affine iff the step is also invariant.
325 return getNumOperands() == 2;
328 /// Return true if this represents an expression A + B*x + C*x^2
329 /// where A, B and C are loop invariant values. This corresponds
330 /// to an addrec of the form {L,+,M,+,N}
331 bool isQuadratic() const {
332 return getNumOperands() == 3;
335 /// Set flags for a recurrence without clearing any previously set flags.
336 /// For AddRec, either NUW or NSW implies NW. Keep track of this fact here
337 /// to make it easier to propagate flags.
338 void setNoWrapFlags(NoWrapFlags Flags
) {
339 if (Flags
& (FlagNUW
| FlagNSW
))
340 Flags
= ScalarEvolution::setFlags(Flags
, FlagNW
);
341 SubclassData
|= Flags
;
344 /// Return the value of this chain of recurrences at the specified
345 /// iteration number.
346 const SCEV
*evaluateAtIteration(const SCEV
*It
, ScalarEvolution
&SE
) const;
348 /// Return the number of iterations of this loop that produce
349 /// values in the specified constant range. Another way of
350 /// looking at this is that it returns the first iteration number
351 /// where the value is not in the condition, thus computing the
352 /// exit count. If the iteration count can't be computed, an
353 /// instance of SCEVCouldNotCompute is returned.
354 const SCEV
*getNumIterationsInRange(const ConstantRange
&Range
,
355 ScalarEvolution
&SE
) const;
357 /// Return an expression representing the value of this expression
358 /// one iteration of the loop ahead.
359 const SCEVAddRecExpr
*getPostIncExpr(ScalarEvolution
&SE
) const;
361 /// Methods for support type inquiry through isa, cast, and dyn_cast:
362 static bool classof(const SCEV
*S
) {
363 return S
->getSCEVType() == scAddRecExpr
;
367 /// This node is the base class min/max selections.
368 class SCEVMinMaxExpr
: public SCEVCommutativeExpr
{
369 friend class ScalarEvolution
;
371 static bool isMinMaxType(enum SCEVTypes T
) {
372 return T
== scSMaxExpr
|| T
== scUMaxExpr
|| T
== scSMinExpr
||
377 /// Note: Constructing subclasses via this constructor is allowed
378 SCEVMinMaxExpr(const FoldingSetNodeIDRef ID
, enum SCEVTypes T
,
379 const SCEV
*const *O
, size_t N
)
380 : SCEVCommutativeExpr(ID
, T
, O
, N
) {
381 assert(isMinMaxType(T
));
382 // Min and max never overflow
383 setNoWrapFlags((NoWrapFlags
)(FlagNUW
| FlagNSW
));
387 static bool classof(const SCEV
*S
) {
388 return isMinMaxType(static_cast<SCEVTypes
>(S
->getSCEVType()));
391 static enum SCEVTypes
negate(enum SCEVTypes T
) {
402 llvm_unreachable("Not a min or max SCEV type!");
407 /// This class represents a signed maximum selection.
408 class SCEVSMaxExpr
: public SCEVMinMaxExpr
{
409 friend class ScalarEvolution
;
411 SCEVSMaxExpr(const FoldingSetNodeIDRef ID
, const SCEV
*const *O
, size_t N
)
412 : SCEVMinMaxExpr(ID
, scSMaxExpr
, O
, N
) {}
415 /// Methods for support type inquiry through isa, cast, and dyn_cast:
416 static bool classof(const SCEV
*S
) {
417 return S
->getSCEVType() == scSMaxExpr
;
421 /// This class represents an unsigned maximum selection.
422 class SCEVUMaxExpr
: public SCEVMinMaxExpr
{
423 friend class ScalarEvolution
;
425 SCEVUMaxExpr(const FoldingSetNodeIDRef ID
, const SCEV
*const *O
, size_t N
)
426 : SCEVMinMaxExpr(ID
, scUMaxExpr
, O
, N
) {}
429 /// Methods for support type inquiry through isa, cast, and dyn_cast:
430 static bool classof(const SCEV
*S
) {
431 return S
->getSCEVType() == scUMaxExpr
;
435 /// This class represents a signed minimum selection.
436 class SCEVSMinExpr
: public SCEVMinMaxExpr
{
437 friend class ScalarEvolution
;
439 SCEVSMinExpr(const FoldingSetNodeIDRef ID
, const SCEV
*const *O
, size_t N
)
440 : SCEVMinMaxExpr(ID
, scSMinExpr
, O
, N
) {}
443 /// Methods for support type inquiry through isa, cast, and dyn_cast:
444 static bool classof(const SCEV
*S
) {
445 return S
->getSCEVType() == scSMinExpr
;
449 /// This class represents an unsigned minimum selection.
450 class SCEVUMinExpr
: public SCEVMinMaxExpr
{
451 friend class ScalarEvolution
;
453 SCEVUMinExpr(const FoldingSetNodeIDRef ID
, const SCEV
*const *O
, size_t N
)
454 : SCEVMinMaxExpr(ID
, scUMinExpr
, O
, N
) {}
457 /// Methods for support type inquiry through isa, cast, and dyn_cast:
458 static bool classof(const SCEV
*S
) {
459 return S
->getSCEVType() == scUMinExpr
;
463 /// This means that we are dealing with an entirely unknown SCEV
464 /// value, and only represent it as its LLVM Value. This is the
465 /// "bottom" value for the analysis.
466 class SCEVUnknown final
: public SCEV
, private CallbackVH
{
467 friend class ScalarEvolution
;
469 /// The parent ScalarEvolution value. This is used to update the
470 /// parent's maps when the value associated with a SCEVUnknown is
471 /// deleted or RAUW'd.
474 /// The next pointer in the linked list of all SCEVUnknown
475 /// instances owned by a ScalarEvolution.
478 SCEVUnknown(const FoldingSetNodeIDRef ID
, Value
*V
,
479 ScalarEvolution
*se
, SCEVUnknown
*next
) :
480 SCEV(ID
, scUnknown
, 1), CallbackVH(V
), SE(se
), Next(next
) {}
482 // Implement CallbackVH.
483 void deleted() override
;
484 void allUsesReplacedWith(Value
*New
) override
;
487 Value
*getValue() const { return getValPtr(); }
490 /// Test whether this is a special constant representing a type
491 /// size, alignment, or field offset in a target-independent
492 /// manner, and hasn't happened to have been folded with other
493 /// operations into something unrecognizable. This is mainly only
494 /// useful for pretty-printing and other situations where it isn't
495 /// absolutely required for these to succeed.
496 bool isSizeOf(Type
*&AllocTy
) const;
497 bool isAlignOf(Type
*&AllocTy
) const;
498 bool isOffsetOf(Type
*&STy
, Constant
*&FieldNo
) const;
501 Type
*getType() const { return getValPtr()->getType(); }
503 /// Methods for support type inquiry through isa, cast, and dyn_cast:
504 static bool classof(const SCEV
*S
) {
505 return S
->getSCEVType() == scUnknown
;
509 /// This class defines a simple visitor class that may be used for
510 /// various SCEV analysis purposes.
511 template<typename SC
, typename RetVal
=void>
513 RetVal
visit(const SCEV
*S
) {
514 switch (S
->getSCEVType()) {
516 return ((SC
*)this)->visitConstant((const SCEVConstant
*)S
);
518 return ((SC
*)this)->visitTruncateExpr((const SCEVTruncateExpr
*)S
);
520 return ((SC
*)this)->visitZeroExtendExpr((const SCEVZeroExtendExpr
*)S
);
522 return ((SC
*)this)->visitSignExtendExpr((const SCEVSignExtendExpr
*)S
);
524 return ((SC
*)this)->visitAddExpr((const SCEVAddExpr
*)S
);
526 return ((SC
*)this)->visitMulExpr((const SCEVMulExpr
*)S
);
528 return ((SC
*)this)->visitUDivExpr((const SCEVUDivExpr
*)S
);
530 return ((SC
*)this)->visitAddRecExpr((const SCEVAddRecExpr
*)S
);
532 return ((SC
*)this)->visitSMaxExpr((const SCEVSMaxExpr
*)S
);
534 return ((SC
*)this)->visitUMaxExpr((const SCEVUMaxExpr
*)S
);
536 return ((SC
*)this)->visitSMinExpr((const SCEVSMinExpr
*)S
);
538 return ((SC
*)this)->visitUMinExpr((const SCEVUMinExpr
*)S
);
540 return ((SC
*)this)->visitUnknown((const SCEVUnknown
*)S
);
541 case scCouldNotCompute
:
542 return ((SC
*)this)->visitCouldNotCompute((const SCEVCouldNotCompute
*)S
);
544 llvm_unreachable("Unknown SCEV type!");
548 RetVal
visitCouldNotCompute(const SCEVCouldNotCompute
*S
) {
549 llvm_unreachable("Invalid use of SCEVCouldNotCompute!");
553 /// Visit all nodes in the expression tree using worklist traversal.
555 /// Visitor implements:
556 /// // return true to follow this node.
557 /// bool follow(const SCEV *S);
558 /// // return true to terminate the search.
560 template<typename SV
>
561 class SCEVTraversal
{
563 SmallVector
<const SCEV
*, 8> Worklist
;
564 SmallPtrSet
<const SCEV
*, 8> Visited
;
566 void push(const SCEV
*S
) {
567 if (Visited
.insert(S
).second
&& Visitor
.follow(S
))
568 Worklist
.push_back(S
);
572 SCEVTraversal(SV
& V
): Visitor(V
) {}
574 void visitAll(const SCEV
*Root
) {
576 while (!Worklist
.empty() && !Visitor
.isDone()) {
577 const SCEV
*S
= Worklist
.pop_back_val();
579 switch (S
->getSCEVType()) {
586 push(cast
<SCEVCastExpr
>(S
)->getOperand());
595 for (const auto *Op
: cast
<SCEVNAryExpr
>(S
)->operands())
599 const SCEVUDivExpr
*UDiv
= cast
<SCEVUDivExpr
>(S
);
600 push(UDiv
->getLHS());
601 push(UDiv
->getRHS());
604 case scCouldNotCompute
:
605 llvm_unreachable("Attempt to use a SCEVCouldNotCompute object!");
607 llvm_unreachable("Unknown SCEV kind!");
613 /// Use SCEVTraversal to visit all nodes in the given expression tree.
614 template<typename SV
>
615 void visitAll(const SCEV
*Root
, SV
& Visitor
) {
616 SCEVTraversal
<SV
> T(Visitor
);
620 /// Return true if any node in \p Root satisfies the predicate \p Pred.
621 template <typename PredTy
>
622 bool SCEVExprContains(const SCEV
*Root
, PredTy Pred
) {
627 FindClosure(PredTy Pred
) : Pred(Pred
) {}
629 bool follow(const SCEV
*S
) {
637 bool isDone() const { return Found
; }
640 FindClosure
FC(Pred
);
645 /// This visitor recursively visits a SCEV expression and re-writes it.
646 /// The result from each visit is cached, so it will return the same
647 /// SCEV for the same input.
648 template<typename SC
>
649 class SCEVRewriteVisitor
: public SCEVVisitor
<SC
, const SCEV
*> {
652 // Memoize the result of each visit so that we only compute once for
653 // the same input SCEV. This is to avoid redundant computations when
654 // a SCEV is referenced by multiple SCEVs. Without memoization, this
655 // visit algorithm would have exponential time complexity in the worst
656 // case, causing the compiler to hang on certain tests.
657 DenseMap
<const SCEV
*, const SCEV
*> RewriteResults
;
660 SCEVRewriteVisitor(ScalarEvolution
&SE
) : SE(SE
) {}
662 const SCEV
*visit(const SCEV
*S
) {
663 auto It
= RewriteResults
.find(S
);
664 if (It
!= RewriteResults
.end())
666 auto* Visited
= SCEVVisitor
<SC
, const SCEV
*>::visit(S
);
667 auto Result
= RewriteResults
.try_emplace(S
, Visited
);
668 assert(Result
.second
&& "Should insert a new entry");
669 return Result
.first
->second
;
672 const SCEV
*visitConstant(const SCEVConstant
*Constant
) {
676 const SCEV
*visitTruncateExpr(const SCEVTruncateExpr
*Expr
) {
677 const SCEV
*Operand
= ((SC
*)this)->visit(Expr
->getOperand());
678 return Operand
== Expr
->getOperand()
680 : SE
.getTruncateExpr(Operand
, Expr
->getType());
683 const SCEV
*visitZeroExtendExpr(const SCEVZeroExtendExpr
*Expr
) {
684 const SCEV
*Operand
= ((SC
*)this)->visit(Expr
->getOperand());
685 return Operand
== Expr
->getOperand()
687 : SE
.getZeroExtendExpr(Operand
, Expr
->getType());
690 const SCEV
*visitSignExtendExpr(const SCEVSignExtendExpr
*Expr
) {
691 const SCEV
*Operand
= ((SC
*)this)->visit(Expr
->getOperand());
692 return Operand
== Expr
->getOperand()
694 : SE
.getSignExtendExpr(Operand
, Expr
->getType());
697 const SCEV
*visitAddExpr(const SCEVAddExpr
*Expr
) {
698 SmallVector
<const SCEV
*, 2> Operands
;
699 bool Changed
= false;
700 for (auto *Op
: Expr
->operands()) {
701 Operands
.push_back(((SC
*)this)->visit(Op
));
702 Changed
|= Op
!= Operands
.back();
704 return !Changed
? Expr
: SE
.getAddExpr(Operands
);
707 const SCEV
*visitMulExpr(const SCEVMulExpr
*Expr
) {
708 SmallVector
<const SCEV
*, 2> Operands
;
709 bool Changed
= false;
710 for (auto *Op
: Expr
->operands()) {
711 Operands
.push_back(((SC
*)this)->visit(Op
));
712 Changed
|= Op
!= Operands
.back();
714 return !Changed
? Expr
: SE
.getMulExpr(Operands
);
717 const SCEV
*visitUDivExpr(const SCEVUDivExpr
*Expr
) {
718 auto *LHS
= ((SC
*)this)->visit(Expr
->getLHS());
719 auto *RHS
= ((SC
*)this)->visit(Expr
->getRHS());
720 bool Changed
= LHS
!= Expr
->getLHS() || RHS
!= Expr
->getRHS();
721 return !Changed
? Expr
: SE
.getUDivExpr(LHS
, RHS
);
724 const SCEV
*visitAddRecExpr(const SCEVAddRecExpr
*Expr
) {
725 SmallVector
<const SCEV
*, 2> Operands
;
726 bool Changed
= false;
727 for (auto *Op
: Expr
->operands()) {
728 Operands
.push_back(((SC
*)this)->visit(Op
));
729 Changed
|= Op
!= Operands
.back();
731 return !Changed
? Expr
732 : SE
.getAddRecExpr(Operands
, Expr
->getLoop(),
733 Expr
->getNoWrapFlags());
736 const SCEV
*visitSMaxExpr(const SCEVSMaxExpr
*Expr
) {
737 SmallVector
<const SCEV
*, 2> Operands
;
738 bool Changed
= false;
739 for (auto *Op
: Expr
->operands()) {
740 Operands
.push_back(((SC
*)this)->visit(Op
));
741 Changed
|= Op
!= Operands
.back();
743 return !Changed
? Expr
: SE
.getSMaxExpr(Operands
);
746 const SCEV
*visitUMaxExpr(const SCEVUMaxExpr
*Expr
) {
747 SmallVector
<const SCEV
*, 2> Operands
;
748 bool Changed
= false;
749 for (auto *Op
: Expr
->operands()) {
750 Operands
.push_back(((SC
*)this)->visit(Op
));
751 Changed
|= Op
!= Operands
.back();
753 return !Changed
? Expr
: SE
.getUMaxExpr(Operands
);
756 const SCEV
*visitSMinExpr(const SCEVSMinExpr
*Expr
) {
757 SmallVector
<const SCEV
*, 2> Operands
;
758 bool Changed
= false;
759 for (auto *Op
: Expr
->operands()) {
760 Operands
.push_back(((SC
*)this)->visit(Op
));
761 Changed
|= Op
!= Operands
.back();
763 return !Changed
? Expr
: SE
.getSMinExpr(Operands
);
766 const SCEV
*visitUMinExpr(const SCEVUMinExpr
*Expr
) {
767 SmallVector
<const SCEV
*, 2> Operands
;
768 bool Changed
= false;
769 for (auto *Op
: Expr
->operands()) {
770 Operands
.push_back(((SC
*)this)->visit(Op
));
771 Changed
|= Op
!= Operands
.back();
773 return !Changed
? Expr
: SE
.getUMinExpr(Operands
);
776 const SCEV
*visitUnknown(const SCEVUnknown
*Expr
) {
780 const SCEV
*visitCouldNotCompute(const SCEVCouldNotCompute
*Expr
) {
785 using ValueToValueMap
= DenseMap
<const Value
*, Value
*>;
787 /// The SCEVParameterRewriter takes a scalar evolution expression and updates
788 /// the SCEVUnknown components following the Map (Value -> Value).
789 class SCEVParameterRewriter
: public SCEVRewriteVisitor
<SCEVParameterRewriter
> {
791 static const SCEV
*rewrite(const SCEV
*Scev
, ScalarEvolution
&SE
,
792 ValueToValueMap
&Map
,
793 bool InterpretConsts
= false) {
794 SCEVParameterRewriter
Rewriter(SE
, Map
, InterpretConsts
);
795 return Rewriter
.visit(Scev
);
798 SCEVParameterRewriter(ScalarEvolution
&SE
, ValueToValueMap
&M
, bool C
)
799 : SCEVRewriteVisitor(SE
), Map(M
), InterpretConsts(C
) {}
801 const SCEV
*visitUnknown(const SCEVUnknown
*Expr
) {
802 Value
*V
= Expr
->getValue();
805 if (InterpretConsts
&& isa
<ConstantInt
>(NV
))
806 return SE
.getConstant(cast
<ConstantInt
>(NV
));
807 return SE
.getUnknown(NV
);
813 ValueToValueMap
&Map
;
814 bool InterpretConsts
;
817 using LoopToScevMapT
= DenseMap
<const Loop
*, const SCEV
*>;
819 /// The SCEVLoopAddRecRewriter takes a scalar evolution expression and applies
820 /// the Map (Loop -> SCEV) to all AddRecExprs.
821 class SCEVLoopAddRecRewriter
822 : public SCEVRewriteVisitor
<SCEVLoopAddRecRewriter
> {
824 SCEVLoopAddRecRewriter(ScalarEvolution
&SE
, LoopToScevMapT
&M
)
825 : SCEVRewriteVisitor(SE
), Map(M
) {}
827 static const SCEV
*rewrite(const SCEV
*Scev
, LoopToScevMapT
&Map
,
828 ScalarEvolution
&SE
) {
829 SCEVLoopAddRecRewriter
Rewriter(SE
, Map
);
830 return Rewriter
.visit(Scev
);
833 const SCEV
*visitAddRecExpr(const SCEVAddRecExpr
*Expr
) {
834 SmallVector
<const SCEV
*, 2> Operands
;
835 for (const SCEV
*Op
: Expr
->operands())
836 Operands
.push_back(visit(Op
));
838 const Loop
*L
= Expr
->getLoop();
839 const SCEV
*Res
= SE
.getAddRecExpr(Operands
, L
, Expr
->getNoWrapFlags());
841 if (0 == Map
.count(L
))
844 const SCEVAddRecExpr
*Rec
= cast
<SCEVAddRecExpr
>(Res
);
845 return Rec
->evaluateAtIteration(Map
[L
], SE
);
852 } // end namespace llvm
854 #endif // LLVM_ANALYSIS_SCALAREVOLUTIONEXPRESSIONS_H