Message ID | 5499DA84.3010205@ezchip.com |
---|---|
State | New |
Headers | show |
On Tue, Dec 23, 2014 at 1:11 PM, Chris Metcalf <cmetcalf@ezchip.com> wrote: > On 12/23/2014 3:47 PM, Chris Metcalf wrote: >> >> On 12/23/2014 3:06 PM, Joseph Myers wrote: >>> >>> I take it that the ABI on tilegx32 allows the lround alias to llround >> >> >> No, it doesn't - I missed this possibility. I assume the best fix is to >> provide an lround override in sysdeps/tile/tilegx/tilegx32/s_lround.c >> that invokes llround() and then sign-extends the result? >> >> But, why doesn't MIPS itself use this approach? >> >> Thanks for catching this! > > > Actually, it is, of course, a little trickier than that, since > we have to prevent s_llround.c from setting up the alias for > lround() as well. But I think it may make sense to use global > conditional logic to do this. The current users of dbl-64/wordsize-64 > are aarch64, alpha, sparc64, and x86_64. So as far as I know, the > question is whether the forthcoming ILP32 version of aarch64 would > benefit from this hack (probably yes) and whether the existing x32 > version of x86_64 would (not clear to me, but plausibly better to clean > up the high bits of the returned value). If it's OK to just add > ILP32-conditional logic, we can do use the appended diff. > > If not, the simplest thing for me to do would be to just add s_lround.c > and s_llround.c in sysdeps/tile/tilegx/tilegx32 that use the default > versions of dbl-64 and not worry about the slight performance > improvement from using the full 64-bit register size. Or, we could > come up with some way to use a conditional in this code: for example, > just add a random #ifdef, #define it in a tilegx-specific override > of s_llround.c, and #include the standard version explicitly. But > this runs counter to the glibc rule of avoiding #ifdef. I'm not sure what > the cleanest path would be if the use of "#ifdef _LP64" isn't OK. > > --- a/sysdeps/ieee754/dbl-64/wordsize-64/s_llround.c > +++ b/sysdeps/ieee754/dbl-64/wordsize-64/s_llround.c > @@ -64,16 +64,31 @@ __llround (double x) > > weak_alias (__llround, llround) > #ifdef NO_LONG_DOUBLE > -strong_alias (__llround, __lroundl) > -weak_alias (__llround, lroundl) > +strong_alias (__llround, __llroundl) > +weak_alias (__llround, llroundl) > #endif > > -/* long has the same width as long long on 64-bit machines. */ > +/* long has the same width as long long on 64-bit machines. > + If building for ILP32 on a machine with 64-bit registers, however, > + do an explicit cast on the return value instead. */ > #undef lround > #undef __lround > +#ifdef _LP64 > strong_alias (__llround, __lround) > weak_alias (__llround, lround) > -#ifdef NO_LONG_DOUBLE > -strong_alias (__llround, __llroundl) > -weak_alias (__llround, llroundl) > +# ifdef NO_LONG_DOUBLE > +strong_alias (__llround, __lroundl) > +weak_alias (__llround, lroundl) > +# endif > +#else > +long int > +__lround (double x) > +{ > + return __llround (x); > +} > +weak_alias (__lround, lround) > +# ifdef NO_LONG_DOUBLE > +strong_alias (__lround, __lroundl) > +weak_alias (__lround, lroundl) > +# endif > #endif > Please make sure that x32 version is unchanged where lround is an alias of llround.
--- a/sysdeps/ieee754/dbl-64/wordsize-64/s_llround.c +++ b/sysdeps/ieee754/dbl-64/wordsize-64/s_llround.c @@ -64,16 +64,31 @@ __llround (double x) weak_alias (__llround, llround) #ifdef NO_LONG_DOUBLE -strong_alias (__llround, __lroundl) -weak_alias (__llround, lroundl) +strong_alias (__llround, __llroundl) +weak_alias (__llround, llroundl) #endif -/* long has the same width as long long on 64-bit machines. */ +/* long has the same width as long long on 64-bit machines. + If building for ILP32 on a machine with 64-bit registers, however, + do an explicit cast on the return value instead. */ #undef lround #undef __lround +#ifdef _LP64 strong_alias (__llround, __lround) weak_alias (__llround, lround) -#ifdef NO_LONG_DOUBLE -strong_alias (__llround, __llroundl) -weak_alias (__llround, llroundl) +# ifdef NO_LONG_DOUBLE +strong_alias (__llround, __lroundl) +weak_alias (__llround, lroundl) +# endif +#else +long int +__lround (double x) +{ + return __llround (x); +} +weak_alias (__lround, lround) +# ifdef NO_LONG_DOUBLE +strong_alias (__lround, __lroundl) +weak_alias (__lround, lroundl) +# endif #endif