These patches generalize the recent improvement on isfinite() to isinf(), isnan(), and signbit().
2026-02-03 Bruno Haible <[email protected]> signbit: Make more C++ safe. * lib/math.in.h (signbit): In C++ mode, define as a template with three instantiations, instead of as a macro. 2026-02-03 Bruno Haible <[email protected]> isnan: Make more C++ safe. * lib/math.in.h (isnan): In C++ mode, define as a template with three instantiations, instead of as a macro. 2026-02-03 Bruno Haible <[email protected]> isinf: Make more C++ safe. * lib/math.in.h (isinf): In C++ mode, define as a template with three instantiations, instead of as a macro.
>From a4ef84e62578dc733482fc945799ce97eb236100 Mon Sep 17 00:00:00 2001 From: Bruno Haible <[email protected]> Date: Tue, 3 Feb 2026 10:46:27 +0100 Subject: [PATCH 1/3] isinf: Make more C++ safe. * lib/math.in.h (isinf): In C++ mode, define as a template with three instantiations, instead of as a macro. --- ChangeLog | 6 ++++++ lib/math.in.h | 17 ++++++++++++----- 2 files changed, 18 insertions(+), 5 deletions(-) diff --git a/ChangeLog b/ChangeLog index 7d9831f49d..f7874afd1f 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2026-02-03 Bruno Haible <[email protected]> + + isinf: Make more C++ safe. + * lib/math.in.h (isinf): In C++ mode, define as a template with three + instantiations, instead of as a macro. + 2026-02-02 Bruno Haible <[email protected]> isinf: Avoid unnecessary override of isinf(). diff --git a/lib/math.in.h b/lib/math.in.h index 210ac99cf3..357b68e31d 100644 --- a/lib/math.in.h +++ b/lib/math.in.h @@ -2508,11 +2508,18 @@ _GL_WARN_REAL_FLOATING_DECL (isfinite); _GL_EXTERN_C int gl_isinff (float x); _GL_EXTERN_C int gl_isinfd (double x); _GL_EXTERN_C int gl_isinfl (long double x); -# undef isinf -# define isinf(x) \ - (sizeof (x) == sizeof (long double) ? gl_isinfl (x) : \ - sizeof (x) == sizeof (double) ? gl_isinfd (x) : \ - gl_isinff (x)) +# ifdef __cplusplus +template <typename T> int isinf (T); +template <> inline int isinf<float> (float x) { return gl_isinff (x); } +template <> inline int isinf<double> (double x) { return gl_isinfd (x); } +template <> inline int isinf<long double> (long double x) { return gl_isinfl (x); } +# else +# undef isinf +# define isinf(x) \ + (sizeof (x) == sizeof (long double) ? gl_isinfl (x) : \ + sizeof (x) == sizeof (double) ? gl_isinfd (x) : \ + gl_isinff (x)) +# endif # endif # if @GNULIB_ISINF@ && defined __cplusplus # if defined isinf || defined GNULIB_NAMESPACE -- 2.52.0
>From 1eb37128b10764afcb2291634f0c32efa94d6e86 Mon Sep 17 00:00:00 2001 From: Bruno Haible <[email protected]> Date: Tue, 3 Feb 2026 10:52:13 +0100 Subject: [PATCH 2/3] isnan: Make more C++ safe. * lib/math.in.h (isnan): In C++ mode, define as a template with three instantiations, instead of as a macro. --- ChangeLog | 6 ++++++ lib/math.in.h | 34 ++++++++++++++++++++++++---------- 2 files changed, 30 insertions(+), 10 deletions(-) diff --git a/ChangeLog b/ChangeLog index f7874afd1f..9b2ba3c49b 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2026-02-03 Bruno Haible <[email protected]> + + isnan: Make more C++ safe. + * lib/math.in.h (isnan): In C++ mode, define as a template with three + instantiations, instead of as a macro. + 2026-02-03 Bruno Haible <[email protected]> isinf: Make more C++ safe. diff --git a/lib/math.in.h b/lib/math.in.h index 357b68e31d..540e7339c3 100644 --- a/lib/math.in.h +++ b/lib/math.in.h @@ -2649,17 +2649,31 @@ _GL_EXTERN_C int rpl_isnand (double x); _GL_EXTERN_C int rpl_isnanl (long double x) _GL_ATTRIBUTE_CONST; # define gl_isnan_l(x) rpl_isnanl (x) # endif -# undef isnan -# define isnan(x) \ - (sizeof (x) == sizeof (long double) ? gl_isnan_l (x) : \ - sizeof (x) == sizeof (double) ? gl_isnan_d (x) : \ - gl_isnan_f (x)) +# ifdef __cplusplus +template <typename T> int isnan (T); +template <> inline int isnan<float> (float x) { return gl_isnan_f (x); } +template <> inline int isnan<double> (double x) { return gl_isnan_d (x); } +template <> inline int isnan<long double> (long double x) { return gl_isnan_l (x); } +# else +# undef isnan +# define isnan(x) \ + (sizeof (x) == sizeof (long double) ? gl_isnan_l (x) : \ + sizeof (x) == sizeof (double) ? gl_isnan_d (x) : \ + gl_isnan_f (x)) +# endif # elif (__GNUC__ >= 4) || (__clang_major__ >= 4) -# undef isnan -# define isnan(x) \ - (sizeof (x) == sizeof (long double) ? __builtin_isnan ((long double)(x)) : \ - sizeof (x) == sizeof (double) ? __builtin_isnan ((double)(x)) : \ - __builtin_isnan ((float)(x))) +# ifdef __cplusplus +template <typename T> int isnan (T); +template <> inline int isnan<float> (float x) { return __builtin_isnan (x); } +template <> inline int isnan<double> (double x) { return __builtin_isnan (x); } +template <> inline int isnan<long double> (long double x) { return __builtin_isnan (x); } +# else +# undef isnan +# define isnan(x) \ + (sizeof (x) == sizeof (long double) ? __builtin_isnan ((long double)(x)) : \ + sizeof (x) == sizeof (double) ? __builtin_isnan ((double)(x)) : \ + __builtin_isnan ((float)(x))) +# endif # endif # if @GNULIB_ISNAN@ && defined __cplusplus # if defined isnan || defined GNULIB_NAMESPACE -- 2.52.0
>From a8febe5c59b341f1daf09e049644e6690a803278 Mon Sep 17 00:00:00 2001 From: Bruno Haible <[email protected]> Date: Tue, 3 Feb 2026 10:58:36 +0100 Subject: [PATCH 3/3] signbit: Make more C++ safe. * lib/math.in.h (signbit): In C++ mode, define as a template with three instantiations, instead of as a macro. --- ChangeLog | 6 ++++++ lib/math.in.h | 30 ++++++++++++++++++++++-------- 2 files changed, 28 insertions(+), 8 deletions(-) diff --git a/ChangeLog b/ChangeLog index 9b2ba3c49b..b563dc4021 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2026-02-03 Bruno Haible <[email protected]> + + signbit: Make more C++ safe. + * lib/math.in.h (signbit): In C++ mode, define as a template with three + instantiations, instead of as a macro. + 2026-02-03 Bruno Haible <[email protected]> isnan: Make more C++ safe. diff --git a/lib/math.in.h b/lib/math.in.h index 540e7339c3..3b33ab4a9e 100644 --- a/lib/math.in.h +++ b/lib/math.in.h @@ -2714,10 +2714,17 @@ _GL_WARN_REAL_FLOATING_DECL (isnan); && (!defined __cplusplus || __cplusplus < 201103)) # undef signbit /* GCC >= 4.0 and clang provide three built-ins for signbit. */ -# define signbit(x) \ - (sizeof (x) == sizeof (long double) ? __builtin_signbitl (x) : \ - sizeof (x) == sizeof (double) ? __builtin_signbit (x) : \ - __builtin_signbitf (x)) +# ifdef __cplusplus +template <typename T> int signbit (T); +template <> inline int signbit<float> (float x) { return __builtin_signbitf (x); } +template <> inline int signbit<double> (double x) { return __builtin_signbit (x); } +template <> inline int signbit<long double> (long double x) { return __builtin_signbitl (x); } +# else +# define signbit(x) \ + (sizeof (x) == sizeof (long double) ? __builtin_signbitl (x) : \ + sizeof (x) == sizeof (double) ? __builtin_signbit (x) : \ + __builtin_signbitf (x)) +# endif # endif # if @REPLACE_SIGNBIT@ && !GNULIB_defined_signbit # undef signbit @@ -2761,10 +2768,17 @@ _GL_EXTERN_C int gl_signbitl (long double arg); }) # endif # endif -# define signbit(x) \ - (sizeof (x) == sizeof (long double) ? gl_signbitl (x) : \ - sizeof (x) == sizeof (double) ? gl_signbitd (x) : \ - gl_signbitf (x)) +# ifdef __cplusplus +template <typename T> int signbit (T); +template <> inline int signbit<float> (float x) { return gl_signbitf (x); } +template <> inline int signbit<double> (double x) { return gl_signbitd (x); } +template <> inline int signbit<long double> (long double x) { return gl_signbitl (x); } +# else +# define signbit(x) \ + (sizeof (x) == sizeof (long double) ? gl_signbitl (x) : \ + sizeof (x) == sizeof (double) ? gl_signbitd (x) : \ + gl_signbitf (x)) +# endif # define GNULIB_defined_signbit 1 # endif # if @GNULIB_SIGNBIT@ && defined __cplusplus -- 2.52.0
