[13/13] Use GCC builtins for copysign functions if desired.
Commit Message
On 12/4/19 2:20 PM, Joseph Myers wrote:
> On Wed, 4 Dec 2019, Stefan Liebler wrote:
>
>>> I think they can all be 1, given that IBM long double has its own
>>> implementation. Except that you shouldn't need the indirection through
>>> these macros at all. Just use __builtin_copysign etc. directly in the
>>> implementations (other than IBM long double), unconditionally, the same
>>> way that sysdeps/ieee754/dbl-64/s_fabs.c uses __builtin_fabs directly
>>> without such macros being needed.
>>>
>>
>> Okay. I've set them to 1 and also used build-many-glibcs.py and had a look
>> into the s_copysign*.os files. There is no function call to copysign* itself.
>
> I think we should handle this like fabs and not have the macros at all,
> just call __builtin_copysign etc. unconditionally.
>
Okay. Then I've removed the macros for float and double and call the
builtins unconditionally.
But I still need the long double version as the f128 builtin is not
available with every GCC version.
Bye,
Stefan
Comments
On Wed, 4 Dec 2019, Stefan Liebler wrote:
> Okay. Then I've removed the macros for float and double and call the builtins
> unconditionally.
> But I still need the long double version as the f128 builtin is not available
> with every GCC version.
I think the _Float128 version could be defined to 1 for GCC 7 and later
(so both long double and _Float128 versions could be removed once we
require GCC 7 or later to build glibc).
commit 105b38cfc6d03772b4fe913dc1db9f56b4045bfb
Author: Stefan Liebler <stli@linux.ibm.com>
Date: Mon Dec 2 15:32:44 2019 +0100
Use GCC builtins for copysign functions if desired.
This patch is always using the corresponding GCC builtin for copysignf, copysign,
and is using the builtin for copysignl, copysignf128 if the USE_FUNCTION_BUILTIN
macros are defined to one in math-use-builtins.h.
Altough the long double version is enabled by default we still need
the macro and the alternative implementation as the _Float128 version
of the builtin is not available with all supported GCC versions.
@@ -51,4 +51,7 @@
#define USE_ROUNDL_BUILTIN 0
#define USE_ROUNDF128_BUILTIN 0
+#define USE_COPYSIGNL_BUILTIN 1
+#define USE_COPYSIGNF128_BUILTIN 0
+
#endif /* math-use-builtins.h */
@@ -10,7 +10,7 @@
* ====================================================
*/
-#if defined(LIBM_SCCS) && !defined(lint)
+#if defined (LIBM_SCCS) && ! defined (lint)
static char rcsid[] = "$NetBSD: s_copysign.c,v 1.8 1995/05/10 20:46:57 jtc Exp $";
#endif
@@ -22,16 +22,11 @@ static char rcsid[] = "$NetBSD: s_copysign.c,v 1.8 1995/05/10 20:46:57 jtc Exp $
#define NO_MATH_REDIRECT
#include <math.h>
-#include <math_private.h>
#include <libm-alias-double.h>
double
__copysign (double x, double y)
{
- uint32_t hx, hy;
- GET_HIGH_WORD (hx, x);
- GET_HIGH_WORD (hy, y);
- SET_HIGH_WORD (x, (hx & 0x7fffffff) | (hy & 0x80000000));
- return x;
+ return __builtin_copysign (x, y);
}
libm_alias_double (__copysign, copysign)
@@ -152,6 +152,8 @@
#define USE_TRUNCL_BUILTIN USE_TRUNCF128_BUILTIN
#undef USE_ROUNDL_BUILTIN
#define USE_ROUNDL_BUILTIN USE_ROUNDF128_BUILTIN
+#undef USE_COPYSIGNL_BUILTIN
+#define USE_COPYSIGNL_BUILTIN USE_COPYSIGNF128_BUILTIN
/* IEEE function renames. */
#define __ieee754_acoshl __ieee754_acoshf128
@@ -361,6 +363,7 @@
#define __builtin_ceill __builtin_ceilf128
#define __builtin_truncl __builtin_truncf128
#define __builtin_roundl __builtin_roundf128
+#define __builtin_copysignl __builtin_copysignf128
/* Get the constant suffix from bits/floatn-compat.h. */
#define L(x) __f128 (x)
@@ -13,7 +13,7 @@
* ====================================================
*/
-#if defined(LIBM_SCCS) && !defined(lint)
+#if defined (LIBM_SCCS) && ! defined (lint)
static char rcsid[] = "$NetBSD: s_copysignf.c,v 1.4 1995/05/10 20:46:59 jtc Exp $";
#endif
@@ -25,15 +25,11 @@ static char rcsid[] = "$NetBSD: s_copysignf.c,v 1.4 1995/05/10 20:46:59 jtc Exp
#define NO_MATH_REDIRECT
#include <math.h>
-#include <math_private.h>
#include <libm-alias-float.h>
-float __copysignf(float x, float y)
+float
+__copysignf (float x, float y)
{
- uint32_t ix,iy;
- GET_FLOAT_WORD(ix,x);
- GET_FLOAT_WORD(iy,y);
- SET_FLOAT_WORD(x,(ix&0x7fffffff)|(iy&0x80000000));
- return x;
+ return __builtin_copysignf (x, y);
}
libm_alias_float (__copysign, copysign)
@@ -13,7 +13,9 @@
* ====================================================
*/
-#if defined(LIBM_SCCS) && !defined(lint)
+#include <math-use-builtins.h>
+
+#if ! USE_COPYSIGNL_BUILTIN && defined (LIBM_SCCS) && ! defined (lint)
static char rcsid[] = "$NetBSD: $";
#endif
@@ -28,13 +30,18 @@ static char rcsid[] = "$NetBSD: $";
#include <math_private.h>
#include <libm-alias-ldouble.h>
-_Float128 __copysignl(_Float128 x, _Float128 y)
+_Float128
+__copysignl (_Float128 x, _Float128 y)
{
- uint64_t hx,hy;
- GET_LDOUBLE_MSW64(hx,x);
- GET_LDOUBLE_MSW64(hy,y);
- SET_LDOUBLE_MSW64(x,(hx&0x7fffffffffffffffULL)
- |(hy&0x8000000000000000ULL));
- return x;
+#if USE_COPYSIGNL_BUILTIN
+ return __builtin_copysignl (x, y);
+#else
+ uint64_t hx, hy;
+ GET_LDOUBLE_MSW64 (hx, x);
+ GET_LDOUBLE_MSW64 (hy, y);
+ SET_LDOUBLE_MSW64 (x, (hx & 0x7fffffffffffffffULL)
+ | (hy & 0x8000000000000000ULL));
+ return x;
+#endif
}
libm_alias_ldouble (__copysign, copysign)
@@ -50,6 +50,11 @@
# define USE_ROUNDF_BUILTIN 1
# define USE_ROUNDL_BUILTIN 1
+/* GCC emits the z9-ec zarch "copy sign" instruction for these
+ builtins if build with at least --march=z196 -mzarch.
+ Note: z196 is no typo but a bug in GCC! */
+# define USE_COPYSIGNL_BUILTIN 1
+
# if __GNUC_PREREQ (8, 1)
# define USE_NEARBYINTF128_BUILTIN 1
# define USE_RINTF128_BUILTIN 1
@@ -57,6 +62,7 @@
# define USE_CEILF128_BUILTIN 1
# define USE_TRUNCF128_BUILTIN 1
# define USE_ROUNDF128_BUILTIN 1
+# define USE_COPYSIGNF128_BUILTIN 1
# else
# define USE_NEARBYINTF128_BUILTIN 0
# define USE_RINTF128_BUILTIN 0
@@ -64,6 +70,7 @@
# define USE_CEILF128_BUILTIN 0
# define USE_TRUNCF128_BUILTIN 0
# define USE_ROUNDF128_BUILTIN 0
+# define USE_COPYSIGNF128_BUILTIN 0
# endif
#else