OSDN Git Service

PR 23604
authordnovillo <dnovillo@138bc75d-0d04-0410-961f-82ee72b054a4>
Sat, 1 Oct 2005 13:57:29 +0000 (13:57 +0000)
committerdnovillo <dnovillo@138bc75d-0d04-0410-961f-82ee72b054a4>
Sat, 1 Oct 2005 13:57:29 +0000 (13:57 +0000)
* tree-vrp.c (extract_range_from_assert): For !=
assertions, only build an anti-range if LIMIT is a
single-valued range.

testsuite/

PR 23604
* gcc.c-torture/execute/pr23604.c: New test.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@104858 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/ChangeLog
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.c-torture/execute/pr23604.c [new file with mode: 0644]
gcc/tree-vrp.c

index 34561df..95db709 100644 (file)
@@ -1,3 +1,11 @@
+2005-10-01  James A. Morrison  <phython@gcc.gnu.org>
+           Diego Novillo  <dnovillo@redhat.com>
+
+       PR 23604
+       * tree-vrp.c (extract_range_from_assert): For !=
+       assertions, only build an anti-range if LIMIT is a
+       single-valued range.
+
 2005-09-30  Richard Earnshaw  <richard.earnshaw@arm.com>
 
        * arm.md (movqi): On thumb when optimizing, handle loading from 
index 00b067a..aff2b8d 100644 (file)
@@ -1,3 +1,9 @@
+2005-10-01  James A. Morrison  <phython@gcc.gnu.org>
+           Diego Novillo  <dnovillo@redhat.com>
+
+       PR 23604
+       * gcc.c-torture/execute/pr23604.c: New test.
+
 2005-10-01  Paul Thomas  <pault@gcc.gnu.org>
 
        PR fortran/16404
diff --git a/gcc/testsuite/gcc.c-torture/execute/pr23604.c b/gcc/testsuite/gcc.c-torture/execute/pr23604.c
new file mode 100644 (file)
index 0000000..4c2b80d
--- /dev/null
@@ -0,0 +1,22 @@
+extern void abort (void);
+
+int g(int i, int j)
+{
+  if (i>-1)
+    if (i<2)
+     {
+        if (i != j)
+          {
+            if (j != 0)
+                return 0;
+          }
+     }
+  return 1;
+}
+
+int main(void)
+{
+  if (!g(1, 0))
+   abort ();
+  return 0;
+}
index 4aec9fc..21e6cf6 100644 (file)
@@ -774,17 +774,32 @@ extract_range_from_assert (value_range_t *vr_p, tree expr)
         LIMIT's range was ~[0, 0], the assertion 'VAR != LIMIT' does
         not imply that VAR's range is [0, 0].  So, in the case of
         anti-ranges, we just assert the inequality using LIMIT and
-        not its anti-range.  */
-      if (limit_vr == NULL
-         || limit_vr->type == VR_ANTI_RANGE)
+        not its anti-range.
+
+        If LIMIT_VR is a range, we can only use it to build a new
+        anti-range if LIMIT_VR is a single-valued range.  For
+        instance, if LIMIT_VR is [0, 1], the predicate
+        VAR != [0, 1] does not mean that VAR's range is ~[0, 1].
+        Rather, it means that for value 0 VAR should be ~[0, 0]
+        and for value 1, VAR should be ~[1, 1].  We cannot
+        represent these ranges.
+
+        The only situation in which we can build a valid
+        anti-range is when LIMIT_VR is a single-valued range
+        (i.e., LIMIT_VR->MIN == LIMIT_VR->MAX).  In that case, 
+        build the anti-range ~[LIMIT_VR->MIN, LIMIT_VR->MAX].  */
+      if (limit_vr
+         && limit_vr->type == VR_RANGE
+         && compare_values (limit_vr->min, limit_vr->max) == 0)
        {
-         min = limit;
-         max = limit;
+         min = limit_vr->min;
+         max = limit_vr->max;
        }
       else
        {
-         min = limit_vr->min;
-         max = limit_vr->max;
+         /* In any other case, we cannot use LIMIT's range to build a
+            valid anti-range.  */
+         min = max = limit;
        }
 
       /* If MIN and MAX cover the whole range for their type, then