re PR middle-end/22429 (-1073741824 <= n && n <= 1073741823 is true where n is 107374...
authorAndrew Pinski <pinskia@physics.uc.edu>
Wed, 2 Nov 2005 21:44:17 +0000 (21:44 +0000)
committerRichard Henderson <rth@gcc.gnu.org>
Wed, 2 Nov 2005 21:44:17 +0000 (13:44 -0800)
        PR 22429
        * fold-const.c (build_range_check): Use unsigned when signed
        overflow is undefined also.  If etype is subtype, make sure that
        the subtraction is in the supertype.

From-SVN: r106400

gcc/ChangeLog
gcc/fold-const.c
gcc/testsuite/gcc.c-torture/execute/pr22429.c [new file with mode: 0644]

index f2b2f54e377249d7cb67073d002a2c01cd5852a9..64a4297da81a9810cf3c78305f6e10a4c9024a9f 100644 (file)
@@ -1,3 +1,10 @@
+2005-11-02  Andrew Pinski  <pinskia@physics.uc.edu>
+
+       PR 22429
+       * fold-const.c (build_range_check): Use unsigned when signed
+       overflow is undefined also.  If etype is subtype, make sure that
+       the subtraction is in the supertype.
+
 2005-11-02  Richard Henderson  <rth@redhat.com>
 
        PR target/24178
index 16e7eb30b307587b576f2dd8b91f9c9a6ba17f62..6f829adfa7714a6772cc49a549c14ece905a5460 100644 (file)
@@ -4014,7 +4014,8 @@ build_range_check (tree type, tree exp, int in_p, tree low, tree high)
     }
 
   value = const_binop (MINUS_EXPR, high, low, 0);
-  if (value != 0 && TREE_OVERFLOW (value) && ! TYPE_UNSIGNED (etype))
+  if (value != 0 && (!flag_wrapv || TREE_OVERFLOW (value))
+      && ! TYPE_UNSIGNED (etype))
     {
       tree utype, minv, maxv;
 
@@ -4025,6 +4026,11 @@ build_range_check (tree type, tree exp, int in_p, tree low, tree high)
        case INTEGER_TYPE:
        case ENUMERAL_TYPE:
        case CHAR_TYPE:
+         /* There is no requirement that LOW be within the range of ETYPE
+            if the latter is a subtype.  It must, however, be within the base
+            type of ETYPE.  So be sure we do the subtraction in that type.  */
+         if (TREE_TYPE (etype))
+           etype = TREE_TYPE (etype);
          utype = lang_hooks.types.unsigned_type (etype);
          maxv = fold_convert (utype, TYPE_MAX_VALUE (etype));
          maxv = range_binop (PLUS_EXPR, NULL_TREE, maxv, 1,
diff --git a/gcc/testsuite/gcc.c-torture/execute/pr22429.c b/gcc/testsuite/gcc.c-torture/execute/pr22429.c
new file mode 100644 (file)
index 0000000..aa55b6e
--- /dev/null
@@ -0,0 +1,17 @@
+extern void abort (void);
+
+#define N      (1 << (sizeof(int) * __CHAR_BIT__ - 2))
+
+int f(int n)
+{
+  if (-N <= n && n <= N-1)
+    return 1;
+  return 0;
+}
+
+int main ()
+{
+  if (f (N))
+    abort ();
+  return 0;
+}