public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero.
@ 2014-11-30 20:40 andi-gcc at firstfloor dot org
  2014-11-30 20:47 ` [Bug tree-optimization/64130] " glisse at gcc dot gnu.org
                   ` (9 more replies)
  0 siblings, 10 replies; 11+ messages in thread
From: andi-gcc at firstfloor dot org @ 2014-11-30 20:40 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

            Bug ID: 64130
           Summary: vrp: handle non zero constant divided by range cannot
                    be zero.
           Product: gcc
           Version: 5.0
            Status: UNCONFIRMED
          Severity: enhancement
          Priority: P3
         Component: tree-optimization
          Assignee: unassigned at gcc dot gnu.org
          Reporter: andi-gcc at firstfloor dot org

The following two functions should always be optimized to return 0
because x > 0, x / a cannot be 0. But VRP misses this case for unknown 
reasons, even though it has some code for it in ranges_from_anti_range()

int fsigned(int a)
{
        return 100 / a == 0;
}

int funsigned(unsigned a)
{
        return 100 / a == 0;
}

gcc50 -fno-non-call-exceptions -O2 -S tvrpdiv.c

gcc version 5.0.0 20141111 (experimental) (GCC) 

        movl    $100, %eax
        cltd
        idivl   %edi
        testl   %eax, %eax
        sete    %al
        movzbl  %al, %eax
        ret

        xorl    %edx, %edx
        movl    $100, %eax
        divl    %edi
        testl   %eax, %eax
        sete    %al
        movzbl  %al, %eax


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
@ 2014-11-30 20:47 ` glisse at gcc dot gnu.org
  2014-11-30 20:49 ` pinskia at gcc dot gnu.org
                   ` (8 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: glisse at gcc dot gnu.org @ 2014-11-30 20:47 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #1 from Marc Glisse <glisse at gcc dot gnu.org> ---
Uh? 100/1000==0, I don't understand your point.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
  2014-11-30 20:47 ` [Bug tree-optimization/64130] " glisse at gcc dot gnu.org
@ 2014-11-30 20:49 ` pinskia at gcc dot gnu.org
  2014-11-30 20:57 ` andi-gcc at firstfloor dot org
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: pinskia at gcc dot gnu.org @ 2014-11-30 20:49 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #2 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
So this should be optimized to a > 100 instead.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
  2014-11-30 20:47 ` [Bug tree-optimization/64130] " glisse at gcc dot gnu.org
  2014-11-30 20:49 ` pinskia at gcc dot gnu.org
@ 2014-11-30 20:57 ` andi-gcc at firstfloor dot org
  2014-12-01  9:30 ` rguenth at gcc dot gnu.org
                   ` (6 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: andi-gcc at firstfloor dot org @ 2014-11-30 20:57 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #3 from Andi Kleen <andi-gcc at firstfloor dot org> ---
You're right. I actually meant

x >= maxval(typeof(a)), x / a   cannot be 0.

Corrected test case (assuming 64bit target):

#include <limits.h>

int fsigned(int a)
{
        return 0x1fffffffL / a == 0;
}

int funsigned(unsigned a)
{
        return 0x1fffffffL / a == 0;
}

>So this should be optimized to a > 100 instead.

Yes this would make sense too.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (2 preceding siblings ...)
  2014-11-30 20:57 ` andi-gcc at firstfloor dot org
@ 2014-12-01  9:30 ` rguenth at gcc dot gnu.org
  2015-06-18 23:38 ` kugan at gcc dot gnu.org
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: rguenth at gcc dot gnu.org @ 2014-12-01  9:30 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

Richard Biener <rguenth at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
           Keywords|                            |missed-optimization
             Status|UNCONFIRMED                 |NEW
   Last reconfirmed|                            |2014-12-01
     Ever confirmed|0                           |1

--- Comment #4 from Richard Biener <rguenth at gcc dot gnu.org> ---
(In reply to Andi Kleen from comment #3)
> You're right. I actually meant
> 
> x >= maxval(typeof(a)), x / a   cannot be 0.
> 
> Corrected test case (assuming 64bit target):
> 
> #include <limits.h>
> 
> int fsigned(int a)
> {
>         return 0x1fffffffL / a == 0;
> }

0x1fffffffL / 0x20000000 == 0

Maybe you meant 0x1fffffffffffffffL / a == 0?

> int funsigned(unsigned a)
> {
>         return 0x1fffffffL / a == 0;
> }
> 
> >So this should be optimized to a > 100 instead.
> 
> Yes this would make sense too.

Yes.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (3 preceding siblings ...)
  2014-12-01  9:30 ` rguenth at gcc dot gnu.org
@ 2015-06-18 23:38 ` kugan at gcc dot gnu.org
  2015-06-19  7:13 ` pinskia at gcc dot gnu.org
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: kugan at gcc dot gnu.org @ 2015-06-18 23:38 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

kugan at gcc dot gnu.org changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |kugan at gcc dot gnu.org

--- Comment #5 from kugan at gcc dot gnu.org ---
I think it should be in from front-end? 

Tried fixing it in VRP like:

--- a/gcc/tree-vrp.c
+++ b/gcc/tree-vrp.c
@@ -9943,12 +9943,43 @@ simplify_stmt_using_ranges (gimple_stmt_iterator *gsi)
     {
       enum tree_code rhs_code = gimple_assign_rhs_code (stmt);
       tree rhs1 = gimple_assign_rhs1 (stmt);
+      tree rhs2 = gimple_assign_rhs2 (stmt);

       switch (rhs_code)
        {
        case EQ_EXPR:
        case NE_EXPR:
-          /* Transform EQ_EXPR, NE_EXPR into BIT_XOR_EXPR or identity
+
+         /* PR64130.  If there is a statement (integer_cst / var == 0) and
+            integer_cst >= TYPE_MAX (TREE_TYPE (var))
+            then (integer_cst / var) cannot be 0. Hence this condition will
+            be always false.  */
+         if (rhs_code == EQ_EXPR
+             && TREE_CODE (rhs1) == SSA_NAME
+             && integer_zerop (rhs2))
+           {
+             gimple g = SSA_NAME_DEF_STMT (rhs1);
+
+             if (is_gimple_assign (g)
+                 && INTEGRAL_TYPE_P (TREE_TYPE (gimple_assign_rhs1 (g)))
+                 && TREE_CODE (gimple_assign_rhs1 (g)) == INTEGER_CST
+                 && TREE_CODE (gimple_assign_rhs2 (g)) == SSA_NAME
+                 && gimple_assign_rhs_code (g) == TRUNC_DIV_EXPR)
+               {
+                 tree r1 = gimple_assign_rhs1 (g);
+                 tree r2 = gimple_assign_rhs2 (g);
+                 tree max = TYPE_MAX_VALUE (TREE_TYPE (r2));
+                 if (compare_values (r1, max) == -1
+                     || compare_values (r1, max) == 0)
+                   {
+                     gimple_assign_set_rhs_with_ops (gsi, NOP_EXPR, rhs2);
+                     update_stmt (stmt);
+                     return true;
+                   }
+               }
+           }
+
+         /* Transform EQ_EXPR, NE_EXPR into BIT_XOR_EXPR or identity
             if the RHS is zero or one, and the LHS are known to be boolean
             values.  */
          if (INTEGRAL_TYPE_P (TREE_TYPE (rhs1)))


But by the time we are in VRP, variable "a" is already promoted to that fits
the constant.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (4 preceding siblings ...)
  2015-06-18 23:38 ` kugan at gcc dot gnu.org
@ 2015-06-19  7:13 ` pinskia at gcc dot gnu.org
  2015-06-19  8:05 ` glisse at gcc dot gnu.org
                   ` (3 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: pinskia at gcc dot gnu.org @ 2015-06-19  7:13 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #7 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Marc Glisse from comment #6)
> (In reply to kugan from comment #5)
> > I think it should be in from front-end? 
> 
> ?

Yes this is really not a good comment to make.  This is not even front-end
specific optimization and can happen in Fortran, Ada, etc.
Basically when a > 100, 100/a is 0 so 100/a == 0 is the same as a > 100.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (5 preceding siblings ...)
  2015-06-19  7:13 ` pinskia at gcc dot gnu.org
@ 2015-06-19  8:05 ` glisse at gcc dot gnu.org
  2015-06-19 11:36 ` kugan at gcc dot gnu.org
                   ` (2 subsequent siblings)
  9 siblings, 0 replies; 11+ messages in thread
From: glisse at gcc dot gnu.org @ 2015-06-19  8:05 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #9 from Marc Glisse <glisse at gcc dot gnu.org> ---
Forget comment #8, it can introduce abs(INT_MIN) which would be bad.


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (6 preceding siblings ...)
  2015-06-19  8:05 ` glisse at gcc dot gnu.org
@ 2015-06-19 11:36 ` kugan at gcc dot gnu.org
  2015-06-29  0:16 ` kugan at gcc dot gnu.org
  2015-06-29  8:39 ` rguenth at gcc dot gnu.org
  9 siblings, 0 replies; 11+ messages in thread
From: kugan at gcc dot gnu.org @ 2015-06-19 11:36 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #10 from kugan at gcc dot gnu.org ---
(In reply to Marc Glisse from comment #6)
> (In reply to kugan from comment #5)
> > I think it should be in from front-end? 
> 
> ?

Sorry for the confusing terminology.

for the case
int fsigned(int a)
{
  return 0xffffffffffffffL / a == 0;
}

004t.gimple has:

  int D.4228;
  long long int D.4229;
  long long int D.4230;
  _Bool D.4231;

  D.4229 = (long long int) a;
  D.4230 = 72057594037927935 / D.4229;
  D.4231 = D.4230 == 0;


So based on the "x >= maxval(typeof(a)), x / a   cannot be 0" the
maxval(typeof(a)) is now maxval(long long int) in the case of ARM. Thats why I
was asking if it is to be done before gimple is generated. As I see, the above
statement does not rely on value ranges.


> 
> > Tried fixing it in VRP like:
> 
> You don't seem to use ranges at all. This might be the right place to
> implement the suggestion from comment #2 (though if it does not use ranges,
> match.pd would be better), but for the original optimization, what you want
> to improve is the computation of the range of a division. When a has range
> [0, 4294967295] we compute for 2305843009213693951 / a the range [0,
> 2305843009213693951] which is not optimal, the left bound should be
> 536870912 not 0. If the good interval is computed, VRP will automatically
> fold == 0 to false without extra code. We already get this right when a has
> range [1, 4294967295].

How about something like this:

--- a/gcc/tree-vrp.c
+++ b/gcc/tree-vrp.c
@@ -3158,7 +3158,14 @@ extract_range_from_binary_expr_1 (value_range_t *vr,
                type = VR_VARYING;
              cmp = compare_values (vr0.min, zero);
              if (cmp == 1)
-               min = zero;
+               {
+                 if (vr1.type == VR_RANGE
+                     && !symbolic_range_p (&vr0)
+                     && !symbolic_range_p (&vr1))
+                   min = int_const_binop (code, vr0.min, vr1.max);
+                 else
+                   min = zero;
+               }
              else if (cmp == 0 || cmp == -1)
                min = vr0.min;
              else


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (7 preceding siblings ...)
  2015-06-19 11:36 ` kugan at gcc dot gnu.org
@ 2015-06-29  0:16 ` kugan at gcc dot gnu.org
  2015-06-29  8:39 ` rguenth at gcc dot gnu.org
  9 siblings, 0 replies; 11+ messages in thread
From: kugan at gcc dot gnu.org @ 2015-06-29  0:16 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

--- Comment #11 from kugan at gcc dot gnu.org ---
Author: kugan
Date: Mon Jun 29 00:15:41 2015
New Revision: 225108

URL: https://gcc.gnu.org/viewcvs?rev=225108&root=gcc&view=rev
Log:
gcc/ChangeLog:

2015-06-29  Kugan Vivekanandarajah  <kuganv@linaro.org>

        PR middle-end/64130
        * tree-vrp.c (extract_range_from_binary_expr_1): For unsigned
        division, compute max and min when value ranges for dividend and
        divisor are available.


gcc/testsuite/ChangeLog:

2015-06-29  Kugan Vivekanandarajah  <kuganv@linaro.org>

        PR middle-end/64130
        * gcc.dg/tree-ssa/pr64130.c: New test.


Added:
    trunk/gcc/testsuite/gcc.dg/tree-ssa/pr64130.c
Modified:
    trunk/gcc/ChangeLog
    trunk/gcc/testsuite/ChangeLog
    trunk/gcc/tree-vrp.c


^ permalink raw reply	[flat|nested] 11+ messages in thread

* [Bug tree-optimization/64130] vrp: handle non zero constant divided by range cannot be zero.
  2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
                   ` (8 preceding siblings ...)
  2015-06-29  0:16 ` kugan at gcc dot gnu.org
@ 2015-06-29  8:39 ` rguenth at gcc dot gnu.org
  9 siblings, 0 replies; 11+ messages in thread
From: rguenth at gcc dot gnu.org @ 2015-06-29  8:39 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64130

Richard Biener <rguenth at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|NEW                         |RESOLVED
         Resolution|---                         |FIXED

--- Comment #12 from Richard Biener <rguenth at gcc dot gnu.org> ---
Fixed on trunk.


^ permalink raw reply	[flat|nested] 11+ messages in thread

end of thread, other threads:[~2015-06-29  8:39 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2014-11-30 20:40 [Bug tree-optimization/64130] New: vrp: handle non zero constant divided by range cannot be zero andi-gcc at firstfloor dot org
2014-11-30 20:47 ` [Bug tree-optimization/64130] " glisse at gcc dot gnu.org
2014-11-30 20:49 ` pinskia at gcc dot gnu.org
2014-11-30 20:57 ` andi-gcc at firstfloor dot org
2014-12-01  9:30 ` rguenth at gcc dot gnu.org
2015-06-18 23:38 ` kugan at gcc dot gnu.org
2015-06-19  7:13 ` pinskia at gcc dot gnu.org
2015-06-19  8:05 ` glisse at gcc dot gnu.org
2015-06-19 11:36 ` kugan at gcc dot gnu.org
2015-06-29  0:16 ` kugan at gcc dot gnu.org
2015-06-29  8:39 ` rguenth at gcc dot gnu.org

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).