On October 27, 2021 4:44:53 PM GMT+02:00, Jakub Jelinek <ja...@redhat.com> wrote: >On Wed, Oct 27, 2021 at 04:29:38PM +0200, Richard Biener wrote: >> So something like the following below? Note I have to fix >> simplify_const_unary_operation to not perform the invalid constant >> folding with (not worrying about the exact conversion case - I doubt >> any of the constant folding is really relevant on RTL these days, >> maybe we should simply punt for all unary float-float ops when either >> mode has sign dependent rounding modes) >> >> diff --git a/gcc/simplify-rtx.c b/gcc/simplify-rtx.c >> index bbbd6b74942..9522a31570e 100644 >> --- a/gcc/simplify-rtx.c >> +++ b/gcc/simplify-rtx.c >> @@ -2068,6 +2073,9 @@ simplify_const_unary_operation (enum rtx_code code, >> machine_mode mode, >> and the operand is a signaling NaN. */ >> if (HONOR_SNANS (mode) && REAL_VALUE_ISSIGNALING_NAN (d)) >> return NULL_RTX; >> + /* Or if flag_rounding_math is on. */ >> + if (HONOR_SIGN_DEPENDENT_ROUNDING (mode)) >> + return NULL_RTX; >> d = real_value_truncate (mode, d); >> break; > >Won't this stop folding of truncations that are never a problem? >I mean at least if the wider float mode constant is exactly representable >in the narrower float mode, no matter what rounding mode is used the value >will be always the same... >And people use > float f = 1.0; >or > float f = 1.25; >etc. a lot.
Yes, but I do expect any such opportunities to be realized on GENERIC/GIMPLE? >So perhaps again > if (HONOR_SIGN_DEPENDENT_ROUNDING (mode) > && !exact_real_truncate (mode, &d)) > return NULL_RTX; >? Sure, for this case it's short and straight forward. > >> /* PR57245 */ >> /* { dg-do run } */ >> /* { dg-require-effective-target fenv } */ >> /* { dg-additional-options "-frounding-math" } */ >> >> #include <fenv.h> >> #include <stdlib.h> >> >> int >> main () >> { > >Roughly yes. Some tests also do #ifdef FE_*, so in your case >> #if __DBL_MANT_DIG__ == 53 && __FLT_MANT_DIG__ == 24 >+#ifdef FE_UPWARD Ah, OK. Will fix. Richard. >> fesetround (FE_UPWARD); >> float f = 1.3; >> if (f != 0x1.4ccccep+0f) >> __builtin_abort (); >+#endif >+#ifdef FE_TONEAREST >etc. >> fesetround (FE_TONEAREST); >> /* Use different actual values so the bogus CSE we perform does not >> break things. */ >> f = 1.33; >> if (f != 0x1.547ae2p+0f) >> abort (); >> fesetround (FE_DOWNWARD); >> f = 1.333; >> if (f != 0x1.553f7cp+0f) >> abort (); >> fesetround (FE_TOWARDZERO); >> f = 1.3333; >> if (f != 0x1.555326p+0f) >> abort (); >> #endif >> return 0; >> } > > Jakub >