[ConstantRange] Rename a method and add more doc
authorSanjoy Das <sanjoy@playingwithpointers.com>
Mon, 22 Feb 2016 16:13:02 +0000 (16:13 +0000)
committerSanjoy Das <sanjoy@playingwithpointers.com>
Mon, 22 Feb 2016 16:13:02 +0000 (16:13 +0000)
Rename makeNoWrapRegion to a more obvious makeGuaranteedNoWrapRegion,
and add a comment about the counter-intuitive aspects of the function.
This is to help prevent cases like PR26628.

llvm-svn: 261532

llvm/include/llvm/IR/ConstantRange.h
llvm/lib/Analysis/ScalarEvolution.cpp
llvm/lib/IR/ConstantRange.cpp
llvm/unittests/IR/ConstantRangeTest.cpp

index fb596a3..f2a7776 100644 (file)
@@ -82,16 +82,25 @@ public:
   static ConstantRange makeSatisfyingICmpRegion(CmpInst::Predicate Pred,
                                                 const ConstantRange &Other);
 
-  /// Return the largest range containing all X such that "X BinOpC C" does not
-  /// wrap (overflow).
+  /// Return the largest range containing all X such that "X BinOpC C" is
+  /// guaranteed not to wrap (overflow).
+  ///
+  /// NB! The returned set does *not* contain **all** possible values of X for
+  /// which "X BinOpC C" does not wrap -- some viable values of X may be
+  /// missing, so you cannot use this to contrain X's range.  E.g. in the last
+  /// example, "(-2) + 1" is both nsw and nuw (so the "X" could be -2), but (-2)
+  /// is not in the set returned.
   ///
   /// Example:
   ///  typedef OverflowingBinaryOperator OBO;
   ///  makeNoWrapRegion(Add, i8 1, OBO::NoSignedWrap) == [-128, 127)
   ///  makeNoWrapRegion(Add, i8 1, OBO::NoUnsignedWrap) == [0, -1)
   ///  makeNoWrapRegion(Add, i8 0, OBO::NoUnsignedWrap) == Full Set
-  static ConstantRange makeNoWrapRegion(Instruction::BinaryOps BinOp,
-                                        const APInt &C, unsigned NoWrapKind);
+  ///  makeNoWrapRegion(Add, i8 1, OBO::NoUnsignedWrap | OBO::NoSignedWrap) ==
+  ///    [0,INT_MAX)
+  static ConstantRange makeGuaranteedNoWrapRegion(Instruction::BinaryOps BinOp,
+                                                  const APInt &C,
+                                                  unsigned NoWrapKind);
 
   /// Return the lower value for this range.
   ///
index 07d72f5..f1f57c6 100644 (file)
@@ -1969,15 +1969,14 @@ StrengthenNoWrapFlags(ScalarEvolution *SE, SCEVTypes Type,
 
     const APInt &C = cast<SCEVConstant>(Ops[0])->getAPInt();
     if (!(SignOrUnsignWrap & SCEV::FlagNSW)) {
-      auto NSWRegion =
-        ConstantRange::makeNoWrapRegion(Instruction::Add, C, OBO::NoSignedWrap);
+      auto NSWRegion = ConstantRange::makeGuaranteedNoWrapRegion(
+          Instruction::Add, C, OBO::NoSignedWrap);
       if (NSWRegion.contains(SE->getSignedRange(Ops[1])))
         Flags = ScalarEvolution::setFlags(Flags, SCEV::FlagNSW);
     }
     if (!(SignOrUnsignWrap & SCEV::FlagNUW)) {
-      auto NUWRegion =
-        ConstantRange::makeNoWrapRegion(Instruction::Add, C,
-                                        OBO::NoUnsignedWrap);
+      auto NUWRegion = ConstantRange::makeGuaranteedNoWrapRegion(
+          Instruction::Add, C, OBO::NoUnsignedWrap);
       if (NUWRegion.contains(SE->getUnsignedRange(Ops[1])))
         Flags = ScalarEvolution::setFlags(Flags, SCEV::FlagNUW);
     }
index 460b778..9bea98c 100644 (file)
@@ -127,9 +127,9 @@ ConstantRange ConstantRange::makeSatisfyingICmpRegion(CmpInst::Predicate Pred,
       .inverse();
 }
 
-ConstantRange ConstantRange::makeNoWrapRegion(Instruction::BinaryOps BinOp,
-                                              const APInt &C,
-                                              unsigned NoWrapKind) {
+ConstantRange
+ConstantRange::makeGuaranteedNoWrapRegion(Instruction::BinaryOps BinOp,
+                                          const APInt &C, unsigned NoWrapKind) {
   typedef OverflowingBinaryOperator OBO;
 
   // Computes the intersection of CR0 and CR1.  It is different from
index 1f32eea..af2f133 100644 (file)
@@ -577,17 +577,17 @@ TEST(ConstantRange, MakeOverflowingRegion) {
   for (int Const : {0, -1, -2, 1, 2, IntMin4Bits, IntMax4Bits}) {
     APInt C(4, Const, true /* = isSigned */);
 
-    auto NUWRegion =
-      ConstantRange::makeNoWrapRegion(Instruction::Add, C, OBO::NoUnsignedWrap);
+    auto NUWRegion = ConstantRange::makeGuaranteedNoWrapRegion(
+        Instruction::Add, C, OBO::NoUnsignedWrap);
 
     EXPECT_FALSE(NUWRegion.isEmptySet());
 
-    auto NSWRegion =
-      ConstantRange::makeNoWrapRegion(Instruction::Add, C, OBO::NoSignedWrap);
+    auto NSWRegion = ConstantRange::makeGuaranteedNoWrapRegion(
+        Instruction::Add, C, OBO::NoSignedWrap);
 
     EXPECT_FALSE(NSWRegion.isEmptySet());
 
-    auto NoWrapRegion = ConstantRange::makeNoWrapRegion(
+    auto NoWrapRegion = ConstantRange::makeGuaranteedNoWrapRegion(
         Instruction::Add, C, OBO::NoSignedWrap | OBO::NoUnsignedWrap);
 
     EXPECT_FALSE(NoWrapRegion.isEmptySet());