summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Analysis/ScalarEvolution.cpp
diff options
context:
space:
mode:
authorTim Shen <timshen91@gmail.com>2018-07-02 20:01:54 +0000
committerTim Shen <timshen91@gmail.com>2018-07-02 20:01:54 +0000
commitc7cef4bcc4400673ffb86be04c006790577f7f56 (patch)
tree022bdc0f4bbbd8ba8c449d7e09b10ce282886a0c /llvm/lib/Analysis/ScalarEvolution.cpp
parent4bc7f3d4d635c05a874c180c03e7a0c130f07cd2 (diff)
downloadbcm5719-llvm-c7cef4bcc4400673ffb86be04c006790577f7f56.tar.gz
bcm5719-llvm-c7cef4bcc4400673ffb86be04c006790577f7f56.zip
[SCEV] Strengthen StrengthenNoWrapFlags (reapply r334428).
Summary: Comment on Transforms/LoopVersioning/incorrect-phi.ll: With the change SCEV is able to prove that the loop doesn't wrap-self (due to zext i16 to i64), disabling the entire loop versioning pass. Removed the zext and just use i64. Reviewers: sanjoy Subscribers: jlebar, hiraditya, javed.absar, bixia, llvm-commits Differential Revision: https://reviews.llvm.org/D48409 llvm-svn: 336140
Diffstat (limited to 'llvm/lib/Analysis/ScalarEvolution.cpp')
-rw-r--r--llvm/lib/Analysis/ScalarEvolution.cpp27
1 files changed, 20 insertions, 7 deletions
diff --git a/llvm/lib/Analysis/ScalarEvolution.cpp b/llvm/lib/Analysis/ScalarEvolution.cpp
index d52c5b0276a..a39ac9b9fb9 100644
--- a/llvm/lib/Analysis/ScalarEvolution.cpp
+++ b/llvm/lib/Analysis/ScalarEvolution.cpp
@@ -2247,22 +2247,35 @@ StrengthenNoWrapFlags(ScalarEvolution *SE, SCEVTypes Type,
SignOrUnsignWrap = ScalarEvolution::maskFlags(Flags, SignOrUnsignMask);
- if (SignOrUnsignWrap != SignOrUnsignMask && Type == scAddExpr &&
- Ops.size() == 2 && isa<SCEVConstant>(Ops[0])) {
-
- // (A + C) --> (A + C)<nsw> if the addition does not sign overflow
- // (A + C) --> (A + C)<nuw> if the addition does not unsign overflow
+ if (SignOrUnsignWrap != SignOrUnsignMask &&
+ (Type == scAddExpr || Type == scMulExpr) && Ops.size() == 2 &&
+ isa<SCEVConstant>(Ops[0])) {
+
+ auto Opcode = [&] {
+ switch (Type) {
+ case scAddExpr:
+ return Instruction::Add;
+ case scMulExpr:
+ return Instruction::Mul;
+ default:
+ llvm_unreachable("Unexpected SCEV op.");
+ }
+ }();
const APInt &C = cast<SCEVConstant>(Ops[0])->getAPInt();
+
+ // (A <opcode> C) --> (A <opcode> C)<nsw> if the op doesn't sign overflow.
if (!(SignOrUnsignWrap & SCEV::FlagNSW)) {
auto NSWRegion = ConstantRange::makeGuaranteedNoWrapRegion(
- Instruction::Add, C, OBO::NoSignedWrap);
+ Opcode, C, OBO::NoSignedWrap);
if (NSWRegion.contains(SE->getSignedRange(Ops[1])))
Flags = ScalarEvolution::setFlags(Flags, SCEV::FlagNSW);
}
+
+ // (A <opcode> C) --> (A <opcode> C)<nuw> if the op doesn't unsign overflow.
if (!(SignOrUnsignWrap & SCEV::FlagNUW)) {
auto NUWRegion = ConstantRange::makeGuaranteedNoWrapRegion(
- Instruction::Add, C, OBO::NoUnsignedWrap);
+ Opcode, C, OBO::NoUnsignedWrap);
if (NUWRegion.contains(SE->getUnsignedRange(Ops[1])))
Flags = ScalarEvolution::setFlags(Flags, SCEV::FlagNUW);
}
OpenPOWER on IntegriCloud