X-Git-Url: https://perl5.git.perl.org/perl5.git/blobdiff_plain/99bf9e32fc57a4be2b3d9395384dc7bf2dc9d8e7..5d288d736c2758c27a5943647f4a524f0e93a642:/perl.h diff --git a/perl.h b/perl.h index 55b33de..8e81724 100644 --- a/perl.h +++ b/perl.h @@ -28,7 +28,14 @@ # include "config.h" #endif -#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) || defined(_STDC_C99) +/* NOTE 1: that with gcc -std=c89 the __STDC_VERSION__ is *not* defined + * because the __STDC_VERSION__ became a thing only with C90. Therefore, + * with gcc, HAS_C99 will never become true as long as we use -std=c89. + + * NOTE 2: headers lie. Do not expect that if HAS_C99 gets to be true, + * all the C99 features are there and are correct. */ +#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) || \ + defined(_STDC_C99) # define HAS_C99 1 #endif @@ -1945,7 +1952,9 @@ EXTERN_C long double modfl(long double, long double *); # define Perl_isinf(x) ((x) > LDBL_MAX || (x) < -LDBL_MAX) # endif # endif -# define Perl_isfinite(x) Perl_isfinitel(x) +# ifndef Perl_isfinite +# define Perl_isfinite(x) Perl_isfinitel(x) +# endif #else # define NV_DIG DBL_DIG # ifdef DBL_MANT_DIG @@ -2023,11 +2032,6 @@ EXTERN_C long double modfl(long double, long double *); # define Perl_isfinite(x) isfinite(x) # elif defined(HAS_FINITE) # define Perl_isfinite(x) finite(x) -# else -/* For the infinities the multiplication returns nan, - * for the nan the multiplication also returns nan, - * for everything else (that is, finite) zero should be returned. */ -# define Perl_isfinite(x) ((x) * 0 == 0) # endif # endif #endif @@ -2284,13 +2288,15 @@ int isnan(double d); #ifndef Perl_isfinite # if defined(HAS_ISFINITE) && !defined(isfinite) -# define Perl_isfinite(x) isfinite((double)x) +# define Perl_isfinite(x) isfinite((double)(x)) # elif defined(HAS_FINITE) -# define Perl_isfinite(x) finite((double)x) +# define Perl_isfinite(x) finite((double)(x)) # elif defined(Perl_fp_class_finite) # define Perl_isfinite(x) Perl_fp_class_finite(x) # else -/* NaN*0 is NaN, [+-]Inf*0 is NaN, zero for anything else. */ +/* For the infinities the multiplication returns nan, + * for the nan the multiplication also returns nan, + * for everything else (that is, finite) zero should be returned. */ # define Perl_isfinite(x) (((x) * 0) == 0) # endif #endif @@ -2307,7 +2313,7 @@ int isnan(double d); #if defined(HAS_LONG_DOUBLE) && !defined(Perl_isfinitel) /* If isfinite() is a macro and looks like we have C99, * we assume it's the type-aware C99 isfinite(). */ -# if defined(isfinite) && defined(HAS_C99) +# if defined(HAS_ISFINITE) && defined(isfinite) && defined(HAS_C99) # define Perl_isfinitel(x) isfinite(x) # elif defined(HAS_ISFINITEL) # define Perl_isfinitel(x) isfinitel(x) @@ -4136,9 +4142,8 @@ END_EXTERN_C # if !defined(NV_INF) && defined(HUGE_VAL) # define NV_INF HUGE_VAL # endif -# ifndef NV_NAN -# define NV_NAN (NV_INF-NV_INF) -# endif +/* For WIN32 the best NV_NAN is the __PL_nan_u trick, see below. + * There is no supported way of getting the NAN across all the crts. */ #endif /* If you are thinking of using HUGE_VAL for infinity, or using @@ -4235,6 +4240,9 @@ static const union { unsigned int __i; float __f; } __PL_nan_u = #if !defined(NV_NAN) # define NV_NAN ((NV)0.0/0.0) /* Some compilers will warn. */ #endif +/* Do NOT try doing NV_NAN based on NV_INF and trying (NV_INF-NV_INF). + * Though IEEE-754-logically correct, some compilers (like Visual C 2003) + * falsely misoptimize that to zero (x-x is zero, right?) */ #ifndef __cplusplus # if !defined(WIN32) && !defined(VMS)