Jakub Jelinek <ja...@redhat.com> wrote:
>Hi!
>
>It is not safe to always handle a = ~b; for bool a and b as
>in_p = !in_p; exp = arg0.  If the current range is say
>+[-,-] or -[-,-] or similar (i.e. unconditional false or true),
>then the value of exp doesn't matter and thus the fact that exp
>has been negated is irrelevant.
>
>Fixed by just making sure that the range either has 0 as high limit
>or 1 as low limit.  In fold-const.c we actually are even more
>conservative
>and just do test for 0:
>    case TRUTH_NOT_EXPR:
>      /* We can only do something if the range is testing for zero.  */
>      if (low == NULL_TREE || high == NULL_TREE
>          || ! integer_zerop (low) || ! integer_zerop (high))
>        return NULL_TREE;
>      *p_in_p = ! in_p;
>      return arg0;
>
>Bootstrapped/regtested on x86_64-linux and i686-linux, ok for
>trunk/4.8?
>

Ok.

Thanks,
Richard.

>2013-09-09  Jakub Jelinek  <ja...@redhat.com>
>
>       PR tree-optimization/58364
>       * tree-ssa-reassoc.c (init_range_entry): For BIT_NOT_EXPR on
>       BOOLEAN_TYPE, only invert in_p and continue with arg0 if
>       the current range can't be an unconditional true or false.
>
>       * gcc.c-torture/execute/pr58364.c: New test.
>
>--- gcc/tree-ssa-reassoc.c.jj  2013-08-13 12:20:45.000000000 +0200
>+++ gcc/tree-ssa-reassoc.c     2013-09-09 11:30:07.416312027 +0200
>@@ -1797,7 +1797,14 @@ init_range_entry (struct range_entry *r,
>       switch (code)
>       {
>       case BIT_NOT_EXPR:
>-        if (TREE_CODE (TREE_TYPE (exp)) == BOOLEAN_TYPE)
>+        if (TREE_CODE (TREE_TYPE (exp)) == BOOLEAN_TYPE
>+            /* Ensure the range is either +[-,0], +[0,0],
>+               -[-,0], -[0,0] or +[1,-], +[1,1], -[1,-] or
>+               -[1,1].  If it is e.g. +[-,-] or -[-,-]
>+               or similar expression of unconditional true or
>+               false, it should not be negated.  */
>+            && ((high && integer_zerop (high))
>+                || (low && integer_onep (low))))
>           {
>             in_p = !in_p;
>             exp = arg0;
>--- gcc/testsuite/gcc.c-torture/execute/pr58364.c.jj   2013-09-09
>11:28:59.917681919 +0200
>+++ gcc/testsuite/gcc.c-torture/execute/pr58364.c      2013-09-09
>11:28:40.000000000 +0200
>@@ -0,0 +1,17 @@
>+/* PR tree-optimization/58364 */
>+
>+int a = 1, b, c;
>+
>+int
>+foo (int x)
>+{
>+  return x < 0 ? 1 : x;
>+}
>+
>+int
>+main ()
>+{
>+  if (foo (a > c == (b = 0)))
>+    __builtin_abort ();
>+  return 0;
>+}
>
>       Jakub


Reply via email to