diff options
author | Nikita Popov <npopov@redhat.com> | 2022-12-06 16:35:24 +0100 |
---|---|---|
committer | Nikita Popov <npopov@redhat.com> | 2022-12-06 16:37:43 +0100 |
commit | b04fc99c347058111cfb9313546df95e10c26132 (patch) | |
tree | 77fa8d66d7ac9b1d957c04ba430d84d347b6a4ef /llvm/lib/IR/ConstantRange.cpp | |
parent | 5cd900ce3c6edd9e0d9b163c9d6cf7f38688d2ee (diff) | |
download | llvm-b04fc99c347058111cfb9313546df95e10c26132.zip llvm-b04fc99c347058111cfb9313546df95e10c26132.tar.gz llvm-b04fc99c347058111cfb9313546df95e10c26132.tar.bz2 |
[ConstantRange] Fix nsw nowrap region for 1 bit integers (PR59301)
The special case for V=1 was incorrect for one bit types, where
1 is also -1. Remove it, and use getNonEmpty() to handle the full
range case instead.
Adjust the exhaustive nowrap tests to test both 5 bit and 1 bit
types.
Fixes https://github.com/llvm/llvm-project/issues/59301.
Diffstat (limited to 'llvm/lib/IR/ConstantRange.cpp')
-rw-r--r-- | llvm/lib/IR/ConstantRange.cpp | 10 |
1 files changed, 3 insertions, 7 deletions
diff --git a/llvm/lib/IR/ConstantRange.cpp b/llvm/lib/IR/ConstantRange.cpp index 553e565..bae1e55 100644 --- a/llvm/lib/IR/ConstantRange.cpp +++ b/llvm/lib/IR/ConstantRange.cpp @@ -258,10 +258,9 @@ static ConstantRange makeExactMulNUWRegion(const APInt &V) { /// Exact mul nsw region for single element RHS. static ConstantRange makeExactMulNSWRegion(const APInt &V) { - // Handle special case for 0, -1 and 1. See the last for reason why we - // specialize -1 and 1. + // Handle 0 and -1 separately to avoid division by zero or overflow. unsigned BitWidth = V.getBitWidth(); - if (V == 0 || V.isOne()) + if (V == 0) return ConstantRange::getFull(BitWidth); APInt MinValue = APInt::getSignedMinValue(BitWidth); @@ -278,10 +277,7 @@ static ConstantRange makeExactMulNSWRegion(const APInt &V) { Lower = APIntOps::RoundingSDiv(MinValue, V, APInt::Rounding::UP); Upper = APIntOps::RoundingSDiv(MaxValue, V, APInt::Rounding::DOWN); } - // ConstantRange ctor take a half inclusive interval [Lower, Upper + 1). - // Upper + 1 is guaranteed not to overflow, because |divisor| > 1. 0, -1, - // and 1 are already handled as special cases. - return ConstantRange(Lower, Upper + 1); + return ConstantRange::getNonEmpty(Lower, Upper + 1); } ConstantRange |