summaryrefslogtreecommitdiffstats
path: root/llvm/lib/IR/ConstantRange.cpp
diff options
context:
space:
mode:
authorNikita Popov <nikita.ppv@gmail.com>2019-04-28 15:40:56 +0000
committerNikita Popov <nikita.ppv@gmail.com>2019-04-28 15:40:56 +0000
commit7a94795b2b7fb9eb3f9bbfa514f3b28fec59408a (patch)
tree82e3c51412a3b2c73aacb251e45cc72b864830fe /llvm/lib/IR/ConstantRange.cpp
parentd394195221ad1a446e0318b7417abd1076512243 (diff)
downloadbcm5719-llvm-7a94795b2b7fb9eb3f9bbfa514f3b28fec59408a.tar.gz
bcm5719-llvm-7a94795b2b7fb9eb3f9bbfa514f3b28fec59408a.zip
[ConstantRange] Add makeExactNoWrapRegion()
I got confused on the terminology, and the change in D60598 was not correct. I was thinking of "exact" in terms of the result being non-approximate. However, the relevant distinction here is whether the result is * Largest range such that: Forall Y in Other: Forall X in Result: X BinOp Y does not wrap. (makeGuaranteedNoWrapRegion) * Smallest range such that: Forall Y in Other: Forall X not in Result: X BinOp Y wraps. (A hypothetical makeAllowedNoWrapRegion) * Both. (makeExactNoWrapRegion) I'm adding a separate makeExactNoWrapRegion method accepting a single APInt (same as makeExactICmpRegion) and using it in the places where the guarantee is relevant. Differential Revision: https://reviews.llvm.org/D60960 llvm-svn: 359402
Diffstat (limited to 'llvm/lib/IR/ConstantRange.cpp')
-rw-r--r--llvm/lib/IR/ConstantRange.cpp14
1 files changed, 10 insertions, 4 deletions
diff --git a/llvm/lib/IR/ConstantRange.cpp b/llvm/lib/IR/ConstantRange.cpp
index 76e0b0ca5b3..e40bbbb7e9a 100644
--- a/llvm/lib/IR/ConstantRange.cpp
+++ b/llvm/lib/IR/ConstantRange.cpp
@@ -309,6 +309,14 @@ ConstantRange::makeGuaranteedNoWrapRegion(Instruction::BinaryOps BinOp,
}
}
+ConstantRange ConstantRange::makeExactNoWrapRegion(Instruction::BinaryOps BinOp,
+ const APInt &Other,
+ unsigned NoWrapKind) {
+ // makeGuaranteedNoWrapRegion() is exact for single-element ranges, as
+ // "for all" and "for any" coincide in this case.
+ return makeGuaranteedNoWrapRegion(BinOp, ConstantRange(Other), NoWrapKind);
+}
+
bool ConstantRange::isFullSet() const {
return Lower == Upper && Lower.isMaxValue();
}
@@ -843,10 +851,8 @@ ConstantRange::add(const ConstantRange &Other) const {
ConstantRange ConstantRange::addWithNoSignedWrap(const APInt &Other) const {
// Calculate the subset of this range such that "X + Other" is
// guaranteed not to wrap (overflow) for all X in this subset.
- // makeGuaranteedNoWrapRegion will produce an exact NSW range.
- auto NSWRange = ConstantRange::makeGuaranteedNoWrapRegion(BinaryOperator::Add,
- ConstantRange(Other),
- OverflowingBinaryOperator::NoSignedWrap);
+ auto NSWRange = ConstantRange::makeExactNoWrapRegion(
+ BinaryOperator::Add, Other, OverflowingBinaryOperator::NoSignedWrap);
auto NSWConstrainedRange = intersectWith(NSWRange);
return NSWConstrainedRange.add(ConstantRange(Other));
OpenPOWER on IntegriCloud