public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug tree-optimization/58686] New: [BUG] vect_get_loop_niters() cound not get the correct result for some loops.
@ 2013-10-11  1:10 congh at google dot com
  2013-10-11  7:51 ` [Bug tree-optimization/58686] vect_get_loop_niters() fails " rguenth at gcc dot gnu.org
                   ` (4 more replies)
  0 siblings, 5 replies; 6+ messages in thread
From: congh at google dot com @ 2013-10-11  1:10 UTC (permalink / raw)
  To: gcc-bugs

http://gcc.gnu.org/bugzilla/show_bug.cgi?id=58686

            Bug ID: 58686
           Summary: [BUG] vect_get_loop_niters() cound not get the correct
                    result for some loops.
           Product: gcc
           Version: 4.9.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: tree-optimization
          Assignee: unassigned at gcc dot gnu.org
          Reporter: congh at google dot com

Look at the following loop:


  unsigned int t = ...;
  do {
    ...
    t -= 4;
  } while (t >= 5);


When I tried to get the iteration number of this loop as an expression using
vect_get_loop_niters(), it gave me the result "scev_not_known". If I changed
the type of t into signed int, then I can get the result as below: 


t > 4 ? ((unsigned int) t + 4294967291) / 4 : 0


But even when t is unsigned, we should still get the result as:


t != 4 ? (t + 4294967291) / 4 : 0


I spent some time on tracking the reason why it failed to do so, and then
reached the function assert_loop_rolls_lt(), in which the assumptions are built
to make sure we can get the iteration number from the following formula:


(iv1->base - iv0->base + step - 1) / step


In the example above, iv1->base is t-4, iv0->base is 4 (t>=5 is t>4), and step
is 4. This formula works only if


-step + 1 <= (iv1->base - iv0->base) <= MAX - step + 1

(MAX is the maximum value of the unsigned variant of type of t, and in this
formula we don't have to take care of overflow.)


I think when (iv1->base - iv0->base) < -step + 1, then we can assume the number
of times the back edge is taken is 0, and that is how niter->may_be_zero is
built in this function. And niter->assumptions is built based on (iv1->base -
iv0->base) <= MAX - step + 1. Note that we can only get the iteration number of
the loop if niter->assumptions is always evaluated as true.

However, I found that the build of niter->assumptions does not involve both
iv1->base and iv0->base, but only one of them. I think this is possibly a
potential bug.

Further, the reason why we can get the iteration number if t is of unsigned int
type is that niter->assumptions built here t-4 < MAX-3 is evaluated to true, by
taking advantage of the fact that the overflow on signed int is undefined (so
t-4 < MAX-3 can be converted to t < MAX+1, where MAX+1 is assumed to not
overflow). But this is not working for unsigned int.

One more problem is the way how niter->may_be_zero is built. For the loop
above, niter->may_be_zero I got is 4 > t - 4 - (-4 + 1), but we should make
sure t-4 here does not overflow. Otherwise niter->may_be_zero is invalid. I
think the function assert_loop_rolls_lt() should take care more of unsigned int
types.

With this issue we cannot vectorize this loop as its iteration number is
unknown.


Thank you!

Cong


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

end of thread, other threads:[~2021-12-12 10:21 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2013-10-11  1:10 [Bug tree-optimization/58686] New: [BUG] vect_get_loop_niters() cound not get the correct result for some loops congh at google dot com
2013-10-11  7:51 ` [Bug tree-optimization/58686] vect_get_loop_niters() fails " rguenth at gcc dot gnu.org
2013-10-12  0:21 ` congh at google dot com
2013-10-13  8:22 ` rguenther at suse dot de
2021-12-12 10:21 ` pinskia at gcc dot gnu.org
2021-12-12 10:21 ` pinskia 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).