On Wed, Feb 20, 2019 at 06:29:06PM +0000, Joseph Myers wrote: > On Wed, 20 Feb 2019, Jakub Jelinek wrote: > > > + /* mpc_norm assumes it can square a number without bothering with > > + with range scaling, so until that is fixed, double the minimum > > + and maximum exponents, plus add some buffer for arithmetics > > + on the squared numbers. */ > > Note that I think such issues are pervasive in MPC; it's not just that one > function. MPFR is generally careful about using a larger exponent range > internally (there might still be issues with very big exponents where they > aren't handled specially to avoid internal overflow, but the maximum MPFR > exponent range is very large); MPC doesn't generally try to handle > restricted exponent ranges.
I've added E.g. to the comment, is that sufficient, or are you aware of some mpc computation that will misbehave even with those 2 * max_exp + 2 etc. ranges? Bootstrapped/regtested now on x86_64-linux and i686-linux successfully and various people tested it on other targets, ok for trunk? 2019-02-20 Jakub Jelinek <ja...@redhat.com> PR middle-end/88074 PR middle-end/89415 * toplev.c (do_compile): Double the emin/emax exponents to workaround buggy mpc_norm. * gcc.dg/pr88074-2.c: New test. --- gcc/toplev.c.jj 2019-02-20 10:00:49.290492694 +0100 +++ gcc/toplev.c 2019-02-20 14:04:27.037769362 +0100 @@ -2173,8 +2173,12 @@ do_compile () max_exp = fmt->emax; } } - if (mpfr_set_emin (min_exp) - || mpfr_set_emax (max_exp)) + /* E.g. mpc_norm assumes it can square a number without bothering with + with range scaling, so until that is fixed, double the minimum + and maximum exponents, plus add some buffer for arithmetics + on the squared numbers. */ + if (mpfr_set_emin (2 * (min_exp - 1)) + || mpfr_set_emax (2 * (max_exp + 1))) sorry ("mpfr not configured to handle all float modes"); /* Set up the back-end if requested. */ --- gcc/testsuite/gcc.dg/pr88074-2.c.jj 2019-02-20 14:10:07.109140297 +0100 +++ gcc/testsuite/gcc.dg/pr88074-2.c 2019-02-20 14:09:46.696478179 +0100 @@ -0,0 +1,17 @@ +/* PR middle-end/88074 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -fdump-tree-optimized" } */ +/* { dg-add-options float128 } */ +/* { dg-require-effective-target float128 } */ +/* { dg-final { scan-tree-dump-not "link_error " "optimized" } } */ + +extern void link_error (void); +int +main () +{ + if (((__FLT128_MAX__ * 0.5 + __FLT128_MAX__ * 0.5i) + / (__FLT128_MAX__ * 0.25 + __FLT128_MAX__ * 0.25i)) + != (_Complex _Float128) 2) + link_error (); + return 0; +} Jakub