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

--- Comment #5 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
It is the foperator_mult::op{1,2}_range and can be seen even on:
double
foo (double x, double y)
{
  double z = x * y;
  if (z == 0.0)
    return x;
  return 42.0;
}
testcase.
2->3  (T) x_2(D) :      [frange] double [-0.0 (-0x0.0p+0), 0.0 (0x0.0p+0)]
2->3  (T) y_3(D) :      [frange] double [-0.0 (-0x0.0p+0), 0.0 (0x0.0p+0)]
2->3  (T) z_4 :         [frange] double [-0.0 (-0x0.0p+0), 0.0 (0x0.0p+0)]
On the true edge of z == 0.0, we have [-0., 0.] range for z_4, that is correct,
but getting from lhs [-0., 0.] and op2 range VARYING to [-0., 0.] is wrong.
We get that because we compute the range in that case as [-0., 0.] / VARYING,
and for division it is actually correct, [-0., 0.] divided by anything non-NAN
non-zero is still [-0., 0.], and [-0., 0.] divided by [-0., 0.] is NAN.
Plus we have the (IMHO still correct) implication that if a result is not NAN,
then neither operand could be NAN.

So I'm afraid back to the drawing board on when we can use division for
multiplication reverse ranges and when we can use multiplication for division
reverse ranges (and whether it is ok to use minus/plus for plus/minus reverse
operations).

Reply via email to