On Wed, 3 Aug 2016, Richard Biener wrote:
> Couldn't this even be
>
> (cmp (float @0) REAL_CST@1)
> (with
> {
> HOST_WIDE_INT n = real_to_integer (TREE_REAL_CST (@1));
> REAL_VALUE_TYPE cint;
> real_from_integer (&cint, VOIDmode, n, SIGNED);
> }
> (if (real_identical (&c, &cint))
> (cmp @0 { build_int_cst (TREE_TYPE (@0), n); }))))
>
> with some additional type checks to make sure n fits the type of @0
> (and otherwise fold to true/false directly).
Well, real_identical is too strong. Comparisons with -0 can be optimized
just like those with +0.
> Not sure whether we need to restrict it to float types that can
> represent all values of the type of @0 exactly.
I discussed the conditions for this optimization in more detail in PR
57371. For an arbitrary comparison operator, between a converted integer
and an arbitrary real constant: (a) you need -fno-trapping-math unless the
(type, range) information for the integer implies it can be converted
exactly to the floating-point type, (b) if the conversion may not be
exact, you also need -fno-rounding-math unless you know from the value of
the real constant that rounding for the conversion from integer cannot
affect the result of the comparison. Given that, all such floating-point
comparisons could be converted to equivalent integer comparisons, *but*
equality comparisons (== != islessgreater) may need to be converted to a
range test on the integer rather than a comparison with a single integer
value.
--
Joseph S. Myers
[email protected]