Here's a proposed patch to 'signbit' to have it use 'copysign' if available.
Normally the 'signbit' implementation relies on undefined behavior, as it accesses the "wrong" member of a union; but when copysign is available the implementation can use copysign's well-defined behavior instead. This is safer for traditional platforms like Solaris 9 that have copysign but not signbit. 2007-04-06 Paul Eggert <[EMAIL PROTECTED]> * lib/signbitd.c (gl_signbitd): Use copysign if available. This avoids relying on undefined behavior. * lib/signbitf.c (gl_signbitf): Use copysignf if available. * lib/signbitl.c (gl_signbitl): Use copysignl if available. * m4/signbit.m4 (gl_SIGNBIT): Test for copysignf, copysign, copysignl. Index: lib/signbitd.c =================================================================== RCS file: /cvsroot/gnulib/gnulib/lib/signbitd.c,v retrieving revision 1.1 diff -u -p -r1.1 signbitd.c --- lib/signbitd.c 6 Apr 2007 20:55:44 -0000 1.1 +++ lib/signbitd.c 7 Apr 2007 05:22:38 -0000 @@ -29,7 +29,9 @@ int gl_signbitd (double arg) { -#if defined DBL_SIGNBIT_WORD && defined DBL_SIGNBIT_BIT +#if HAVE_DECL_COPYSIGN + return copysign (1, arg) < 0; +#elif defined DBL_SIGNBIT_WORD && defined DBL_SIGNBIT_BIT # define NWORDS \ ((sizeof (double) + sizeof (unsigned int) - 1) / sizeof (unsigned int)) union { double value; unsigned int word[NWORDS]; } m; Index: lib/signbitf.c =================================================================== RCS file: /cvsroot/gnulib/gnulib/lib/signbitf.c,v retrieving revision 1.1 diff -u -p -r1.1 signbitf.c --- lib/signbitf.c 6 Apr 2007 20:55:44 -0000 1.1 +++ lib/signbitf.c 7 Apr 2007 05:22:38 -0000 @@ -29,7 +29,9 @@ int gl_signbitf (float arg) { -#if defined FLT_SIGNBIT_WORD && defined FLT_SIGNBIT_BIT +#if HAVE_DECL_COPYSIGNF + return copysignf (1, arg) < 0; +#elif defined FLT_SIGNBIT_WORD && defined FLT_SIGNBIT_BIT # define NWORDS \ ((sizeof (float) + sizeof (unsigned int) - 1) / sizeof (unsigned int)) union { float value; unsigned int word[NWORDS]; } m; Index: lib/signbitl.c =================================================================== RCS file: /cvsroot/gnulib/gnulib/lib/signbitl.c,v retrieving revision 1.1 diff -u -p -r1.1 signbitl.c --- lib/signbitl.c 6 Apr 2007 20:55:44 -0000 1.1 +++ lib/signbitl.c 7 Apr 2007 05:22:38 -0000 @@ -29,7 +29,9 @@ int gl_signbitl (long double arg) { -#if defined LDBL_SIGNBIT_WORD && defined LDBL_SIGNBIT_BIT +#if HAVE_DECL_COPYSIGNL + return copysignl (1, arg) < 0; +#elif defined LDBL_SIGNBIT_WORD && defined LDBL_SIGNBIT_BIT # define NWORDS \ ((sizeof (long double) + sizeof (unsigned int) - 1) / sizeof (unsigned int)) union { long double value; unsigned int word[NWORDS]; } m; Index: m4/signbit.m4 =================================================================== RCS file: /cvsroot/gnulib/gnulib/m4/signbit.m4,v retrieving revision 1.1 diff -u -p -r1.1 signbit.m4 --- m4/signbit.m4 6 Apr 2007 20:55:44 -0000 1.1 +++ m4/signbit.m4 7 Apr 2007 05:22:38 -0000 @@ -62,9 +62,12 @@ int main () AC_LIBOBJ([signbitf]) AC_LIBOBJ([signbitd]) AC_LIBOBJ([signbitl]) - gl_FLOAT_SIGN_LOCATION - gl_DOUBLE_SIGN_LOCATION - gl_LONG_DOUBLE_SIGN_LOCATION + AC_CHECK_DECLS([copysignf], [], [gl_FLOAT_SIGN_LOCATION], + [#include <math.h>]) + AC_CHECK_DECLS([copysign], [], [gl_DOUBLE_SIGN_LOCATION], + [#include <math.h>]) + AC_CHECK_DECLS([copysignl], [], [gl_LONG_DOUBLE_SIGN_LOCATION], + [#include <math.h>]) fi ])