On Mon, Oct 21, 2019 at 06:41:46PM +0800, Bin.Cheng wrote:
> The overflow check is difficult, IIUC, checks on bit precision in the
> patch is not enough?  Considering an unsigned 64-bit candidate with

I think it can cover some cases, especially on 64-bit targets, but will
leave other cases out.

I guess the first question is what iv->no_overflow means, the IVs
are base + iteration * step, does no_overflow mean that neither iteration *
step, nor base + iteration * step overflows?
For the debug info and division, guess we care primarily if just the
iteration * step part doesn't overflow.

There are still cases where I fear even the precision check might not be
enough.  If ustep is a power of two and so is rat, then I think we should be
fine, or if use->iv->no_overflow, but otherwise I fear of say unsigned char
use and unsigned short candidate, with ustep 3 and cstep 9 (i.e. rat 3).
If the loop has more than 65536 / 9 iterations, the var - cbase
will overflow, so will have values 0, 9, ..., 0xfff0, 0xfff9, 2, 11, ...
and corresponding use computed using division (assuming ubase is 0)
0 + (unsigned char) ((var - cbase) / 3):
0, 3, ..., 0x50, 0x53, 0, 3, ...
which is incorrect.
Simple testcase -O3 -g -fno-tree-dce:

void
foo (unsigned short c, unsigned char *p)
{
  unsigned char a = 0;
  unsigned short b = 0;
  for (; b != c; a += 3, b += 9)
    p[b]++;
}

where I think with the patch it will be wrong-debug on 7282th iteration etc.

So I wonder if for correctness I don't need to add:

  if (!use->iv->no_overflow
      && !cand->iv->no_overflow
      && !integer_pow2p (cstep))
    return NULL_TREE;

with some of the above as comment explaining why.

On the other side, if cand->iv->no_overflow, couldn't we bypass the extra
precision test?

And related to the first question above, perhaps incrementally, couldn't we
track separately whether the whole base + iteration * step overflows (i.e.
what we track right now) and also just whether iteration * step overflows in
a separate bool?  Because when we subtract the base from the value, all we
care about is iteration * step.

        Jakub

Reply via email to