I'll ping it myself then!
Segher On Thu, Oct 22, 2020 at 06:03:46PM -0400, Michael Meissner wrote: > PowerPC: Map IEEE 128-bit long double built-in functions > > This patch is revised from the first and second versions of the patch posted. > It now uses the names that are not in the user's namespace (i.e. __sinieee128 > instead of sinf128) that Joseph Myers suggested. > > In addition, I added the changes suggested by Segher the last time this patch > was submitted (changing where the default is, fixing the scalbl built-in name, > using strlen and xaprintf). > > I have split all of these patches into separate patches to hopefully get them > into the tree. > > This patch goes through the built-in functions and changes the name of the > math, scanf, and printf built-in functions to use the functions that GLIBC > provides when long double uses the IEEE 128-bit representation. > > In addition, changing the name in GCC allows the Fortran compiler to > automatically use the correct name. > > To map the math functions, typically this patch changes <name>l to > __<name>ieee128. However there are some exceptions that are handled with this > patch. > > To map the printf functions, <name> is mapped to __<name>ieee128. > > To map the scanf functions, <name> is mapped to __isoc99_<name>ieee128. > > I have tested this patch with bootstrap builds on a little endian power9 > system > running Linux. With the other patches, I have built two full bootstrap builds > using this patch and the patches after this patch. One build used the current > default for long double (IBM extended double) and the other build switched the > default to IEEE 128-bit. I used the Advance Toolchain AT 14.0 compiler as the > library used by this compiler. There are no regressions between the tests. > There are 3 fortran benchmarks (ieee/large_2.f90, default_format_2.f90, and > default_format_denormal_2.f90) that now pass. > > Can I install this into the trunk? > > We have gotten some requests to back port these changes to GCC 10.x. At the > moment, I am not planning to do the back port, but I may need to in the > future. > > gcc/ > 2020-10-22 Michael Meissner <meiss...@linux.ibm.com> > > * config/rs6000/rs6000.c (rs6000_mangle_decl_assembler_name): Add > support for mapping built-in function names for long double > built-in functions if long double is IEEE 128-bit. > > gcc/testsuite/ > 2020-10-22 Michael Meissner <meiss...@linux.ibm.com> > > * gcc.target/powerpc/float128-longdouble-math.c: New test. > * gcc.target/powerpc/float128-longdouble-stdio.c: New test. > * gcc.target/powerpc/float128-math.c: Adjust test for new name > being generated. > --- > gcc/config/rs6000/rs6000.c | 135 ++++- > .../powerpc/float128-longdouble-math.c | 567 ++++++++++++++++++ > .../powerpc/float128-longdouble-stdio.c | 37 ++ > .../gcc.target/powerpc/float128-math.c | 6 +- > 4 files changed, 710 insertions(+), 35 deletions(-) > create mode 100644 > gcc/testsuite/gcc.target/powerpc/float128-longdouble-math.c > create mode 100644 > gcc/testsuite/gcc.target/powerpc/float128-longdouble-stdio.c > > diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c > index 141684e3157..8c2544ee88d 100644 > --- a/gcc/config/rs6000/rs6000.c > +++ b/gcc/config/rs6000/rs6000.c > @@ -26893,56 +26893,127 @@ rs6000_globalize_decl_name (FILE * stream, tree > decl) > library before you can switch the real*16 type at compile time. > > We use the TARGET_MANGLE_DECL_ASSEMBLER_NAME hook to change this name. We > - only do this if the default is that long double is IBM extended double, > and > - the user asked for IEEE 128-bit. */ > + only do this transformation if the __float128 type is enabled. This > + prevents us from doing the transformation on older 32-bit ports that might > + have enabled using IEEE 128-bit floating point as the default long double > + type. */ > > static tree > rs6000_mangle_decl_assembler_name (tree decl, tree id) > { > - if (!TARGET_IEEEQUAD_DEFAULT && TARGET_IEEEQUAD && TARGET_LONG_DOUBLE_128 > - && TREE_CODE (decl) == FUNCTION_DECL && DECL_IS_BUILTIN (decl) ) > + if (TARGET_FLOAT128_TYPE && TARGET_IEEEQUAD && TARGET_LONG_DOUBLE_128 > + && TREE_CODE (decl) == FUNCTION_DECL > + && fndecl_built_in_p (decl, BUILT_IN_NORMAL)) > { > size_t len = IDENTIFIER_LENGTH (id); > const char *name = IDENTIFIER_POINTER (id); > + char *newname = NULL; > > - if (name[len - 1] == 'l') > + /* See if it is one of the built-in functions with an unusual name. */ > + switch (DECL_FUNCTION_CODE (decl)) > { > - bool uses_ieee128_p = false; > - tree type = TREE_TYPE (decl); > - machine_mode ret_mode = TYPE_MODE (type); > + case BUILT_IN_DREML: > + newname = xstrdup ("__remainderieee128"); > + break; > > - /* See if the function returns a IEEE 128-bit floating point type or > - complex type. */ > - if (ret_mode == TFmode || ret_mode == TCmode) > - uses_ieee128_p = true; > - else > - { > - function_args_iterator args_iter; > - tree arg; > + case BUILT_IN_GAMMAL: > + newname = xstrdup ("__lgammaieee128"); > + break; > + > + case BUILT_IN_GAMMAL_R: > + case BUILT_IN_LGAMMAL_R: > + newname = xstrdup ("__lgammaieee128_r"); > + break; > + > + case BUILT_IN_NEXTTOWARD: > + newname = xstrdup ("__nexttoward_to_ieee128"); > + break; > + > + case BUILT_IN_NEXTTOWARDF: > + newname = xstrdup ("__nexttowardf_to_ieee128"); > + break; > + > + case BUILT_IN_NEXTTOWARDL: > + newname = xstrdup ("__nexttowardieee128"); > + break; > + > + case BUILT_IN_POW10L: > + newname = xstrdup ("__exp10ieee128"); > + break; > + > + case BUILT_IN_SCALBL: > + newname = xstrdup ("__scalbieee128"); > + break; > + > + case BUILT_IN_SIGNIFICANDL: > + newname = xstrdup ("__significandieee128"); > + break; > + > + case BUILT_IN_SINCOSL: > + newname = xstrdup ("__sincosieee128"); > + break; > > - /* See if the function passes a IEEE 128-bit floating point type > - or complex type. */ > - FOREACH_FUNCTION_ARGS (type, arg, args_iter) > + default: > + break; > + } > + > + /* Update the __builtin_*printf && __builtin_*scanf functions. */ > + if (!newname) > + { > + size_t printf_len = strlen ("printf"); > + size_t scanf_len = strlen ("scanf"); > + > + if (len >= printf_len > + && strcmp (name + len - printf_len, "printf") == 0) > + newname = xasprintf ("__%sieee128", name); > + > + else if (len >= scanf_len > + && strcmp (name + len - scanf_len, "scanf") == 0) > + newname = xasprintf ("__isoc99_%sieee128", name); > + > + else if (name[len - 1] == 'l') > + { > + bool uses_ieee128_p = false; > + tree type = TREE_TYPE (decl); > + machine_mode ret_mode = TYPE_MODE (type); > + > + /* See if the function returns a IEEE 128-bit floating point type > or > + complex type. */ > + if (ret_mode == TFmode || ret_mode == TCmode) > + uses_ieee128_p = true; > + else > { > - machine_mode arg_mode = TYPE_MODE (arg); > - if (arg_mode == TFmode || arg_mode == TCmode) > + function_args_iterator args_iter; > + tree arg; > + > + /* See if the function passes a IEEE 128-bit floating point > type > + or complex type. */ > + FOREACH_FUNCTION_ARGS (type, arg, args_iter) > { > - uses_ieee128_p = true; > - break; > + machine_mode arg_mode = TYPE_MODE (arg); > + if (arg_mode == TFmode || arg_mode == TCmode) > + { > + uses_ieee128_p = true; > + break; > + } > } > } > - } > > - /* If we passed or returned an IEEE 128-bit floating point type, > - change the name. */ > - if (uses_ieee128_p) > - { > - char *name2 = (char *) alloca (len + 4); > - memcpy (name2, name, len - 1); > - strcpy (name2 + len - 1, "f128"); > - id = get_identifier (name2); > + /* If we passed or returned an IEEE 128-bit floating point type, > + change the name. Use __<name>ieee128, instead of <name>l. */ > + if (uses_ieee128_p) > + newname = xasprintf ("__%.*sieee128", (int)(len - 1), name); > } > } > + > + if (newname) > + { > + if (TARGET_DEBUG_BUILTIN) > + fprintf (stderr, "Map %s => %s\n", name, newname); > + > + id = get_identifier (newname); > + free (newname); > + } > } > > return id; > diff --git a/gcc/testsuite/gcc.target/powerpc/float128-longdouble-math.c > b/gcc/testsuite/gcc.target/powerpc/float128-longdouble-math.c > new file mode 100644 > index 00000000000..50d40180fdc > --- /dev/null > +++ b/gcc/testsuite/gcc.target/powerpc/float128-longdouble-math.c > @@ -0,0 +1,567 @@ > +/* { dg-require-effective-target ppc_float128_hw } */ > +/* { dg-require-effective-target power10_ok } */ > +/* { dg-options "-mdejagnu-cpu=power9 -mno-pcrel -O2 -Wno-psabi > -mabi=ieeelongdouble" } */ > + > +/* Test if switching long double to IEEE 128-bit maps all of the math > built-in > + function names correctly. We explicitly turn off PC-relative support to > + make it simpler to compare the call without having a @notoc qualifier. */ > + > +/* Debugging support to use 'name' instead of '__builtin_name'. Note if you > + enable this, you will likely need additional flags to get all of the > + functions defined. */ > +#ifdef DO_FUNC > +#ifndef DO_MATH_H > +#define DO_MATH_H 1 > +#endif > + > +#define BUILTIN0(FUNC) FUNC () > +#define BUILTIN1(FUNC, ARG1) FUNC (ARG1) > +#define BUILTIN2(FUNC, ARG1, ARG2) FUNC (ARG1, ARG2) > +#define BUILTIN3(FUNC, ARG1, ARG2, ARG3) FUNC (ARG1, ARG2, ARG3) > + > +#else > +#define BUILTIN0(FUNC) __builtin_ ## FUNC () > +#define BUILTIN1(FUNC, ARG1) __builtin_ ## FUNC (ARG1) > +#define BUILTIN2(FUNC, ARG1, ARG2) __builtin_ ## FUNC (ARG1, ARG2) > +#define BUILTIN3(FUNC, ARG1, ARG2, ARG3) __builtin_ ## FUNC (ARG1, ARG2, > ARG3) > +#endif > + > +/* Debugging support to compare using math.h with the raw built-in > functions. */ > +#ifdef DO_MATH_H > +#define __STDC_WANT_IEC_60559_TYPES_EXT__ 1 > +#define __STDC_WANT_IEC_60559_FUNCS_EXT__ 1 > +#define _GNU_SOURCE 1 > +#define _XOPEN_SOURCE 1 > + > +#include <math.h> > +#include <complex.h> > +#endif > + > +/* Built-in functions that returns a long double and take one long double > + argument. */ > + > +void > +return_ld_arg_ld (long double *p, > + long double *q) > +{ > + /* { dg-final { scan-assembler {\m__acoshieee128\M} } } */ > + *p++ = BUILTIN1 (acoshl, *q++); > + > + /* { dg-final { scan-assembler {\m__acosieee128\M} } } */ > + *p++ = BUILTIN1 (acosl, *q++); > + > + /* { dg-final { scan-assembler {\m__asinhieee128\M} } } */ > + *p++ = BUILTIN1 (asinhl, *q++); > + > + /* { dg-final { scan-assembler {\m__asinieee128\M} } } */ > + *p++ = BUILTIN1 (asinl, *q++); > + > + /* { dg-final { scan-assembler {\m__atanhieee128\M} } } */ > + *p++ = BUILTIN1 (atanhl, *q++); > + > + /* { dg-final { scan-assembler {\m__atanieee128\M} } } */ > + *p++ = BUILTIN1 (atanl, *q++); > + > + /* { dg-final { scan-assembler {\m__cbrtieee128\M} } } */ > + *p++ = BUILTIN1 (cbrtl, *q++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxsrqpi +[0-9]+,[0-9]+,[0-9]+,2\M} } } */ > + *p++ = BUILTIN1 (ceill, *q++); > + > + /* { dg-final { scan-assembler {\m__coshieee128\M} } } */ > + *p++ = BUILTIN1 (coshl, *q++); > + > + /* { dg-final { scan-assembler {\m__cosieee128\M} } } */ > + *p++ = BUILTIN1 (cosl, *q++); > + > + /* { dg-final { scan-assembler {\m__erfcieee128\M} } } */ > + *p++ = BUILTIN1 (erfcl, *q++); > + > + /* { dg-final { scan-assembler {\m__erfieee128\M} } } */ > + *p++ = BUILTIN1 (erfl, *q++); > + > + /* { dg-final { scan-assembler {\m__exp10ieee128\M} } } */ > + *p++ = BUILTIN1 (exp10l, *q++); > + > + /* { dg-final { scan-assembler {\m__exp2ieee128\M} } } */ > + *p++ = BUILTIN1 (exp2l, *q++); > + > + /* { dg-final { scan-assembler {\m__expieee128\M} } } */ > + *p++ = BUILTIN1 (expl, *q++); > + > + /* { dg-final { scan-assembler {\m__expm1ieee128\M} } } */ > + *p++ = BUILTIN1 (expm1l, *q++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxsabsqp\M} } } */ > + *p++ = BUILTIN1 (fabsl, *q++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxsrqpi +[0-9]+,[0-9]+,[0-9]+,3\M} } } */ > + *p++ = BUILTIN1 (floorl, *q++); > + > + /* { dg-final { scan-assembler {\m__lgammaieee128\M} } } */ > + *p++ = BUILTIN1 (gammal, *q++); > + > + /* { dg-final { scan-assembler {\m__j0ieee128\M} } } */ > + *p++ = BUILTIN1 (j0l, *q++); > + > + /* { dg-final { scan-assembler {\m__j1ieee128\M} } } */ > + *p++ = BUILTIN1 (j1l, *q++); > + > + /* lgammaf128 mentioned previously. */ > + *p++ = BUILTIN1 (lgammal, *q++); > + > + /* { dg-final { scan-assembler {\m__log10ieee128\M} } } */ > + *p++ = BUILTIN1 (log10l, *q++); > + > + /* { dg-final { scan-assembler {\m__log1pieee128\M} } } */ > + *p++ = BUILTIN1 (log1pl, *q++); > + > + /* { dg-final { scan-assembler {\m__log2ieee128\M} } } */ > + *p++ = BUILTIN1 (log2l, *q++); > + > + /* { dg-final { scan-assembler {\m__logbieee128\M} } } */ > + *p++ = BUILTIN1 (logbl, *q++); > + > + /* { dg-final { scan-assembler {\m__logieee128\M} } } */ > + *p++ = BUILTIN1 (logl, *q++); > + > + /* { dg-final { scan-assembler {\m__nearbyintieee128\M} } } */ > + *p++ = BUILTIN1 (nearbyintl, *q++); > + > + /* { dg-final { scan-assembler {\m__exp10ieee128\M} } } */ > + *p++ = BUILTIN1 (pow10l, *q++); > + > + /* { dg-final { scan-assembler {\m__rintieee128\M} } } */ > + *p++ = BUILTIN1 (rintl, *q++); > + > + /* { dg-final { scan-assembler {\m__roundevenieee128\M} } } */ > + *p++ = BUILTIN1 (roundevenl, *q++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxsrqpi +[0-9]+,[0-9]+,[0-9]+,0\M} } } */ > + *p++ = BUILTIN1 (roundl, *q++); > + > + /* { dg-final { scan-assembler {\m__significandieee128\M} } } */ > + *p++ = BUILTIN1 (significandl, *q++); > + > + /* { dg-final { scan-assembler {\m__sinhieee128\M} } } */ > + *p++ = BUILTIN1 (sinhl, *q++); > + > + /* { dg-final { scan-assembler {\m__sinieee128\M} } } */ > + *p++ = BUILTIN1 (sinl, *q++); > + > + /* { dg-final { scan-assembler {\m__sqrtieee128\M} } } */ > + *p++ = BUILTIN1 (sqrtl, *q++); > + > + /* { dg-final { scan-assembler {\m__tanhieee128\M} } } */ > + *p++ = BUILTIN1 (tanhl, *q++); > + > + /* { dg-final { scan-assembler {\m__tanieee128\M} } } */ > + *p++ = BUILTIN1 (tanl, *q++); > + > + /* { dg-final { scan-assembler {\m__tgammaieee128\M} } } */ > + *p++ = BUILTIN1 (tgammal, *q++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxsrqpi +[0-9]+,[0-9]+,[0-9]+,1\M} } } */ > + *p++ = BUILTIN1 (truncl, *q++); > + > + /* { dg-final { scan-assembler {\m__y0ieee128\M} } } */ > + *p++ = BUILTIN1 (y0l, *q++); > + > + /* { dg-final { scan-assembler {\m__y1ieee128\M} } } */ > + *p = BUILTIN1 (y1l, *q); > + > +} > + > +/* Built-in functions that returns a long double and take two long double > + arguments. */ > + > +void > +return_ld_arg_ld_ld (long double *p, > + long double *q, > + long double *r) > +{ > + /* { dg-final { scan-assembler {\m__atan2ieee128\M} } } */ > + *p++ = BUILTIN2 (atan2l, *q++, *r++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxscpsgnqp\M} } } */ > + *p++ = BUILTIN2 (copysignl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__remainderieee128\M} } } */ > + *p++ = BUILTIN2 (dreml, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__fdimieee128\M} } } */ > + *p++ = BUILTIN2 (fdiml, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__fmaxieee128\M} } } */ > + *p++ = BUILTIN2 (fmaxl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__fminieee128\M} } } */ > + *p++ = BUILTIN2 (fminl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__fmodieee128\M} } } */ > + *p++ = BUILTIN2 (fmodl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__hypotieee128\M} } } */ > + *p++ = BUILTIN2 (hypotl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__nextafterieee128\M} } } */ > + *p++ = BUILTIN2 (nextafterl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__nexttowardieee128\M} } } */ > + *p++ = BUILTIN2 (nexttowardl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__powieee128\M} } } */ > + *p++ = BUILTIN2 (powl, *q++, *r++); > + > + /* remainderf128 mentioned previously. */ > + *p++ = BUILTIN2 (remainderl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__scalbnieee128\M} } } */ > + *p = BUILTIN2 (scalbl, *q, *r); > +} > + > +/* Built-in function that returns a long double and take three long double > + arguments. */ > + > +void > +return_ld_arg_ld_ld_ld (long double *p, > + long double *q, > + long double *r, > + long double *s) > +{ > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxsmaddqp\M} } } */ > + *p = BUILTIN3 (fmal, *q, *r, *s); > +} > + > +/* Built-in functions that returns a long double and take one > + _Complex long double argument. */ > + > +void > +return_ld_arg_cld (long double *p, > + _Complex long double *q) > +{ > + /* { dg-final { scan-assembler {\m__cabsieee128\M} } } */ > + *p++ = BUILTIN1 (cabsl, *q++); > + > + /* inline code. */ > + *p++ = BUILTIN1 (cargl, *q++); > + > + /* inline code. */ > + *p++ = BUILTIN1 (cimagl, *q++); > + > + /* inline code. */ > + *p = BUILTIN1 (creall, *q); > +} > + > +/* Built-in functions that returns a _Complex long double and takes one > + _Complex long double argument. */ > + > +void > +return_cld_arg_cld (_Complex long double *p, > + _Complex long double *q) > +{ > + /* { dg-final { scan-assembler {\m__cacoshieee128\M} } } */ > + *p++ = BUILTIN1 (cacoshl, *q++); > + > + /* { dg-final { scan-assembler {\m__cacosieee128\M} } } */ > + *p++ = BUILTIN1 (cacosl, *q++); > + > + /* { dg-final { scan-assembler {\m__casinhieee128\M} } } */ > + *p++ = BUILTIN1 (casinhl, *q++); > + > + /* { dg-final { scan-assembler {\m__casinieee128\M} } } */ > + *p++ = BUILTIN1 (casinl, *q++); > + > + /* { dg-final { scan-assembler {\m__catanhieee128\M} } } */ > + *p++ = BUILTIN1 (catanhl, *q++); > + > + /* { dg-final { scan-assembler {\m__catanieee128\M} } } */ > + *p++ = BUILTIN1 (catanl, *q++); > + > + /* { dg-final { scan-assembler {\m__ccoshieee128\M} } } */ > + *p++ = BUILTIN1 (ccoshl, *q++); > + > + /* { dg-final { scan-assembler {\m__ccosieee128\M} } } */ > + *p++ = BUILTIN1 (ccosl, *q++); > + > + /* { dg-final { scan-assembler {\m__cexpieee128\M} } } */ > + *p++ = BUILTIN1 (cexpl, *q++); > + > + /* { dg-final { scan-assembler {\m__clogieee128\M} } } */ > + *p++ = BUILTIN1 (clogl, *q++); > + > + /* { dg-final { scan-assembler {\m__clog10ieee128\M} } } */ > + *p++ = BUILTIN1 (clog10l, *q++); > + > + /* inline code. */ > + *p++ = BUILTIN1 (conjl, *q++); > + > + /* { dg-final { scan-assembler {\m__cprojieee128\M} } } */ > + *p++ = BUILTIN1 (cprojl, *q++); > + > + /* { dg-final { scan-assembler {\m__csinhieee128\M} } } */ > + *p++ = BUILTIN1 (csinhl, *q++); > + > + /* { dg-final { scan-assembler {\m__csinieee128\M} } } */ > + *p++ = BUILTIN1 (csinl, *q++); > + > + /* { dg-final { scan-assembler {\m__csqrtieee128\M} } } */ > + *p++ = BUILTIN1 (csqrtl, *q++); > + > + /* { dg-final { scan-assembler {\m__ctanhieee128\M} } } */ > + *p++ = BUILTIN1 (ctanhl, *q++); > + > + /* { dg-final { scan-assembler {\m__ctanieee128\M} } } */ > + *p = BUILTIN1 (ctanl, *q); > +} > + > +/* Built-in functions that returns a _Complex long double and takes one > + long double argument. */ > + > +void > +return_cld_arg_ld (_Complex long double *p, > + long double *q) > +{ > + /* { dg-final { scan-assembler {\m__sincosieee128\M} } } */ > + *p = BUILTIN1 (cexpil, *q); > +} > + > +/* Built-in function that returns a _Complex long double and takes two > + _Complex long double arguments. */ > + > +void > +return_cld_arg_cld_cld (_Complex long double *p, > + _Complex long double *q, > + _Complex long double *r) > +{ > + /* { dg-final { scan-assembler {\m__cpowieee128\M} } } */ > + *p = BUILTIN2 (cpowl, *q, *r); > +} > + > +/* Built-in functions that returns a long double and takes a long double and > a > + pointer to an int arguments. */ > + > +void > +return_ld_arg_ld_pi (long double *p, > + long double *q, > + int **r) > +{ > + /* { dg-final { scan-assembler {\m__frexpieee128\M} } } */ > + *p++ = BUILTIN2 (frexpl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__lgammaieee128_r\M} } } */ > + *p++ = BUILTIN2 (gammal_r, *q++, *r++); > + > + /* __lgammaieee128_r mentioned previously. */ > + *p = BUILTIN2 (lgammal_r, *q, *r); > +} > + > +/* Built-in functions that returns a long double and takes a long double and > an > + int arguments. */ > + > +void > +return_ld_arg_ld_i (long double *p, > + long double *q, > + int *r) > +{ > + /* { dg-final { scan-assembler {\m__ldexpieee128\M} } } */ > + *p++ = BUILTIN2 (ldexpl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__powikf2\M} } } */ > + *p++ = BUILTIN2 (powil, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__scalbnieee128\M} } } */ > + *p = BUILTIN2 (scalbnl, *q, *r); > +} > + > +/* Built-in function that returns a long double and takes a long double and a > + long arguments. */ > + > +void > +return_ld_arg_ld_l (long double *p, > + long double *q, > + long *r) > +{ > + /* { dg-final { scan-assembler {\m__scalblnieee128\M} } } */ > + *p = BUILTIN2 (scalblnl, *q, *r); > +} > + > +/* Built-in functions that returns a long double and takes a long double and > a > + long long arguments. */ > + > +void > +return_ld_arg_i_ld (long double *p, > + int *q, > + long double *r) > +{ > + /* { dg-final { scan-assembler {\m__jnieee128\M} } } */ > + *p++ = BUILTIN2 (jnl, *q++, *r++); > + > + /* { dg-final { scan-assembler {\m__ynieee128\M} } } */ > + *p = BUILTIN2 (ynl, *q, *r); > +} > + > +/* Built-in functions that returns a long double and takes a long double and > a > + pointer to a long double arguments. */ > + > +void > +return_ld_arg_ld_pld (long double *p, > + long double *q, > + long double **r) > +{ > + /* { dg-final { scan-assembler {\m__modfieee128\M} } } */ > + *p = BUILTIN2 (modfl, *q, *r); > +} > + > +/* Built-in function that returns a long double and takes two long double > and a > + pointer to an int arguments. */ > + > +void > +return_ld_arg_ld_ld_pi (long double *p, > + long double *q, > + long double *r, > + int **s) > +{ > + /* { dg-final { scan-assembler {\m__remquoieee128\M} } } */ > + *p = BUILTIN3 (remquol, *q, *r, *s); > +} > + > +/* Built-in functions that returns a long double and take no arguments. */ > + > +void > +return_ld_no_arg (long double *p) > +{ > + /* inline code. */ > + *p++ = BUILTIN0 (huge_vall); > + > + /* inline code. */ > + *p = BUILTIN0 (infl); > +} > + > +/* Built-in functions that return san int and takes one long double > argument. */ > + > +void > +return_i_arg_ld (int *p, > + long double *q) > +{ > + /* { dg-final { scan-assembler {\m__ceilieee128\M} } } */ > + *p++ = BUILTIN1 (iceill, *q++); > + > + /* { dg-final { scan-assembler {\m__floorieee128\M} } } */ > + *p++ = BUILTIN1 (ifloorl, *q++); > + > + /* { dg-final { scan-assembler {\m__ilogbieee128\M} } } */ > + *p++ = BUILTIN1 (ilogbl, *q++); > + > + /* { dg-final { scan-assembler {\m__lrintieee128\M} } } */ > + *p++ = BUILTIN1 (irintl, *q++); > + > + /* { dg-final { scan-assembler {\m__lroundieee128\M} } } */ > + *p++ = BUILTIN1 (iroundl, *q++); > + > + /* inline code. */ > + /* { dg-final { scan-assembler {\mxscvqpswz\M} } } */ > + *p++ = BUILTIN1 (signbitl, *q++); > + > + /* inline code. */ > + *p++ = BUILTIN1 (finitel, *q++); > + > + /* inline code. */ > + *p++ = BUILTIN1 (isinfl, *q++); > + > + /* inline code. */ > + *p = BUILTIN1 (isnanl, *q); > +} > + > +/* Built-in functions that returns a long and takes one long double > argument. */ > + > +void > +return_l_arg_ld (long *p, > + long double *q) > +{ > + /* ceilf128 mentioned previouly. */ > + *p++ = BUILTIN1 (lceill, *q++); > + > + /* floorf128 mentioned previously. */ > + *p++ = BUILTIN1 (lfloorl, *q++); > + > + /* lrintf128 mentioned previously. */ > + *p++ = BUILTIN1 (lrintl, *q++); > + > + /* lroundf128 mentioned previously. */ > + *p = BUILTIN1 (lroundl, *q); > +} > + > +/* Built-in functions that returns a long long and takes one long double > + argument. */ > + > +void > +return_ll_arg_ld (long long *p, > + long double *r) > +{ > + /* ceilf128 mentioned previous. */ > + *p++ = BUILTIN1 (llceill, *r++); > + > + /* floorf128 mentioned previously. */ > + *p++ = BUILTIN1 (llfloorl, *r++); > + > + /* llrintf128 mentioned previously. */ > + *p++ = BUILTIN1 (llrintl, *r++); > + > + /* llroundf128 mentioned previously. */ > + *p = BUILTIN1 (llroundl, *r); > +} > + > +/* Built-in function that returns a double and takes one double and one long > + double arguments. */ > + > +void > +return_d_arg_d_ld (double *p, > + double *q, > + long double *r) > +{ > + /* { dg-final { scan-assembler {\m__nexttoward_to_ieee128\M} } } */ > + *p = BUILTIN2 (nexttoward, *q, *r); > +} > + > +/* Built-in function that returns a float and takes one float and one long > + double arguments. */ > + > +void > +return_f_arg_f_ld (float *p, > + float *q, > + long double *r) > +{ > + /* { dg-final { scan-assembler {\m__nexttowardf_to_ieee128\M} } } */ > + *p = BUILTIN2 (nexttowardf, *q, *r); > +} > + > +/* Built-in function that returns void and takes one long double and two > + pointers to long double arguments. */ > + > +void > +return_void_arg_ld_pld_pld (long double *p, > + long double **q, > + long double **r) > +{ > + /* __sincosieee128 mentioned previously. */ > + BUILTIN3 (sincosl, *p, *q, *r); > +} > + > +/* Debug main program to determine if the library has all of the mapped > + external functions. Note, you need a new enough glibc to provide all of > the > + f128 functions. */ > +#ifdef DO_MAIN > +int > +main (void) > +{ > + return 0; > +} > +#endif > diff --git a/gcc/testsuite/gcc.target/powerpc/float128-longdouble-stdio.c > b/gcc/testsuite/gcc.target/powerpc/float128-longdouble-stdio.c > new file mode 100644 > index 00000000000..570f3e071b9 > --- /dev/null > +++ b/gcc/testsuite/gcc.target/powerpc/float128-longdouble-stdio.c > @@ -0,0 +1,37 @@ > +/* { dg-require-effective-target ppc_float128_hw } */ > +/* { dg-require-effective-target power10_ok } */ > +/* { dg-options "-mdejagnu-cpu=power9 -mno-pcrel -O2 -Wno-psabi > -mabi=ieeelongdouble" } */ > + > +/* Test if switching long double to IEEE 128-bit maps the printf and scanf > + function names correctly. We explicitly turn off PC-relative support to > + make it simpler to compare the call without having a @notoc qualifier. */ > + > +#include <stdlib.h> > + > +volatile long double x = 1.0L; > +volatile long double y, z; > + > +int > +main (void) > +{ > + char buffer[100]; > + > + /* { dg-final { scan-assembler {\m__sprintfieee128\M} } } */ > + __builtin_sprintf (buffer, "%Lg", x); > + > + /* { dg-final { scan-assembler {\m__printfieee128\M} } } */ > + __builtin_printf ("x is %Lg [%s]\n", x, buffer); > + > + /* { dg-final { scan-assembler {\m__isoc99_sscanfieee128\M} } } */ > + __builtin_sscanf (buffer, "%Lg", &y); > + > + __builtin_printf ("Type 1.0: "); > + > + /* { dg-final { scan-assembler {\m__isoc99_scanfieee128\M} } } */ > + __builtin_scanf ("%Lg", &z); > + > + if (x != y || x != z) > + abort (); > + > + return 0; > +} > diff --git a/gcc/testsuite/gcc.target/powerpc/float128-math.c > b/gcc/testsuite/gcc.target/powerpc/float128-math.c > index 4ad3b5b8363..ea5cb43bcf1 100644 > --- a/gcc/testsuite/gcc.target/powerpc/float128-math.c > +++ b/gcc/testsuite/gcc.target/powerpc/float128-math.c > @@ -10,11 +10,11 @@ > > extern __float128 sinf128 (__float128); > > -void foo (__float128 *p, long double *q, long double *r) > +void foo (__float128 *p, long double *q) > { > *p = sinf128 (*p); > *q = __builtin_sinl (*q); > } > > -/* { dg-final { scan-assembler-times {\mbl sinf128\M} 2 } } */ > -/* { dg-final { scan-assembler-not {\mbl sinl\M} } } */ > +/* { dg-final { scan-assembler {\mbl __sinieee128\M} } } */ > +/* { dg-final { scan-assembler-not {\mbl sinl\M} } } */ > -- > 2.22.0 > > > -- > Michael Meissner, IBM > IBM, M/S 2506R, 550 King Street, Littleton, MA 01460-6245, USA > email: meiss...@linux.ibm.com, phone: +1 (978) 899-4797