On 02/19/2018 12:47 PM, Richard Sandiford wrote: > Yuri Gribov <tetra2...@gmail.com> writes: >> Hi all, >> >> This is a second iteration of patch which gets rid of float casts in >> comparisons when all values of casted integral type are exactly >> representable by the float type >> (https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81376). The new version >> addresses Richard's review >> (https://gcc.gnu.org/ml/gcc-patches/2017-10/msg00481.html). >> >> Bootstrapped and regtested on x64_64. Ok to commit? >> >> -Y >> >> From 1ea62f7bf4394142e0c473a69de8a0e9b1718a69 Mon Sep 17 00:00:00 2001 >> From: Yury Gribov <tetra2...@gmail.com> >> Date: Fri, 29 Sep 2017 07:34:54 +0200 >> Subject: [PATCH] Add pattern to remove useless float casts in comparison. >> >> 2018-02-17 Yury Gribov <tetra2...@gmail.com> >> >> PR middle-end/81376 >> >> gcc/ >> * real.c (format_helper::can_represent_integral_type_p): New function >> * real.h (format_helper::can_represent_integral_type_p): Ditto. >> * match.pd: New pattern. >> >> gcc/testsuite/ >> * c-c++-common/pr81376.c: New test. >> --- >> gcc/match.pd | 30 ++++++++++++++++++++------- >> gcc/real.c | 13 ++++++++++++ >> gcc/real.h | 1 + >> gcc/testsuite/c-c++-common/pr81376.c | 39 >> ++++++++++++++++++++++++++++++++++++ >> 4 files changed, 76 insertions(+), 7 deletions(-) >> create mode 100644 gcc/testsuite/c-c++-common/pr81376.c >> >> diff --git a/gcc/match.pd b/gcc/match.pd >> index 4452b58..33a5f36 100644 >> --- a/gcc/match.pd >> +++ b/gcc/match.pd >> @@ -3252,6 +3252,27 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT) >> (if (! HONOR_NANS (@0)) >> (cmp @0 @1)))))) >> >> +/* Optimize various special cases of (FTYPE) N CMP (FTYPE) M. */ >> +(for cmp (tcc_comparison) >> + (simplify >> + (cmp (float@0 @1) (float @2)) >> + (if (SCALAR_FLOAT_TYPE_P (TREE_TYPE (@0)) >> + && ! DECIMAL_FLOAT_TYPE_P (TREE_TYPE (@0))) >> + (with >> + { >> + format_helper fmt (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (@0)))); >> + tree type1 = TREE_TYPE (@1); >> + tree type2 = TREE_TYPE (@2); >> + } >> + (if (fmt.can_represent_integral_type_p (type1) >> + && fmt.can_represent_integral_type_p (type2)) >> + (if (TYPE_PRECISION (type1) > TYPE_PRECISION (type2)) >> + (cmp @1 (convert @2)) >> + (if (TYPE_PRECISION (type1) < TYPE_PRECISION (type2)) >> + (cmp (convert:type2 @1) @2) >> + (if (TYPE_SIGN (type1) == TYPE_SIGN (type2)) >> + (cmp @1 @2))))))))) > > I think this would mishandle combinations in which the wider type > is unsigned and the narrower type is signed, like @1:short @2:unsigned int. I think you're right. I suspect most of the cases where this is going to apply in the real world will have @1 and @2 of the same type. So just rejecting those cases seems quite reasonable to me. With that fixed and a testcase for that situation this should be OK.
jeff