1 /*************************************************************************
3 * $Id: trionan.c,v 1.33 2005/05/29 11:57:25 breese Exp $
5 * Copyright (C) 2001 Bjorn Reese <breese@users.sourceforge.net>
7 * Permission to use, copy, modify, and distribute this software for any
8 * purpose with or without fee is hereby granted, provided that the above
9 * copyright notice and this permission notice appear in all copies.
11 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
12 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
13 * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE AUTHORS AND
14 * CONTRIBUTORS ACCEPT NO RESPONSIBILITY IN ANY CONCEIVABLE MANNER.
16 ************************************************************************
18 * Functions to handle special quantities in floating-point numbers
19 * (that is, NaNs and infinity). They provide the capability to detect
20 * and fabricate special quantities.
22 * Although written to be as portable as possible, it can never be
23 * guaranteed to work on all platforms, as not all hardware supports
26 * The approach used here (approximately) is to:
28 * 1. Use C99 functionality when available.
29 * 2. Use IEEE 754 bit-patterns if possible.
30 * 3. Use platform-specific techniques.
32 ************************************************************************/
34 /*************************************************************************
43 #if !defined(TRIO_PLATFORM_SYMBIAN)
46 #if defined(TRIO_PLATFORM_UNIX)
49 #if defined(TRIO_COMPILER_DECC)
50 # include <fp_class.h>
54 #if defined(TRIO_DOCUMENTATION)
55 # include "doc/doc_nan.h"
57 /** @addtogroup SpecialQuantities
61 /*************************************************************************
65 #if !defined(TRIO_PUBLIC_NAN)
66 # define TRIO_PUBLIC_NAN TRIO_PUBLIC
68 #if !defined(TRIO_PRIVATE_NAN)
69 # define TRIO_PRIVATE_NAN TRIO_PRIVATE
72 #define TRIO_TRUE (1 == 1)
73 #define TRIO_FALSE (0 == 1)
76 * We must enable IEEE floating-point on Alpha
78 #if defined(__alpha) && !defined(_IEEE_FP)
79 # if defined(TRIO_COMPILER_DECC)
80 # if defined(TRIO_PLATFORM_VMS)
81 # error "Must be compiled with option /IEEE_MODE=UNDERFLOW_TO_ZERO/FLOAT=IEEE"
84 # error "Must be compiled with option -ieee"
88 # if defined(TRIO_COMPILER_GCC)
89 # error "Must be compiled with option -mieee"
92 #endif /* __alpha && ! _IEEE_FP */
95 * In ANSI/IEEE 754-1985 64-bits double format numbers have the
96 * following properties (amoungst others)
98 * o FLT_RADIX == 2: binary encoding
99 * o DBL_MAX_EXP == 1024: 11 bits exponent, where one bit is used
100 * to indicate special numbers (e.g. NaN and Infinity), so the
101 * maximum exponent is 10 bits wide (2^10 == 1024).
102 * o DBL_MANT_DIG == 53: The mantissa is 52 bits wide, but because
103 * numbers are normalized the initial binary 1 is represented
104 * implicitly (the so-called "hidden bit"), which leaves us with
105 * the ability to represent 53 bits wide mantissa.
107 #if defined(__STDC_IEC_559__)
108 # define TRIO_IEEE_754
110 # if (FLT_RADIX - 0 == 2) && (DBL_MAX_EXP - 0 == 1024) && (DBL_MANT_DIG - 0 == 53)
111 # define TRIO_IEEE_754
116 * Determine which fpclassify_and_sign() function to use.
118 #if defined(TRIO_FUNC_FPCLASSIFY_AND_SIGNBIT)
119 # if defined(PREDEF_STANDARD_C99) && defined(fpclassify)
120 # define TRIO_FUNC_C99_FPCLASSIFY_AND_SIGNBIT
122 # if defined(TRIO_COMPILER_DECC)
123 # define TRIO_FUNC_DECC_FPCLASSIFY_AND_SIGNBIT
125 # if defined(TRIO_COMPILER_VISUALC) || defined(TRIO_COMPILER_BORLAND)
126 # define TRIO_FUNC_MS_FPCLASSIFY_AND_SIGNBIT
128 # if defined(TRIO_COMPILER_HP) && defined(FP_PLUS_NORM)
129 # define TRIO_FUNC_HP_FPCLASSIFY_AND_SIGNBIT
131 # if defined(TRIO_COMPILER_XLC) && defined(FP_PLUS_NORM)
132 # define TRIO_FUNC_XLC_FPCLASSIFY_AND_SIGNBIT
134 # define TRIO_FUNC_INTERNAL_FPCLASSIFY_AND_SIGNBIT
143 * Determine how to generate negative zero.
145 #if defined(TRIO_FUNC_NZERO)
146 # if defined(TRIO_IEEE_754)
147 # define TRIO_NZERO_IEEE_754
149 # define TRIO_NZERO_FALLBACK
154 * Determine how to generate positive infinity.
156 #if defined(TRIO_FUNC_PINF)
157 # if defined(INFINITY) && defined(__STDC_IEC_559__)
158 # define TRIO_PINF_C99_MACRO
160 # if defined(TRIO_IEEE_754)
161 # define TRIO_PINF_IEEE_754
163 # define TRIO_PINF_FALLBACK
169 * Determine how to generate NaN.
171 #if defined(TRIO_FUNC_NAN)
172 # if defined(PREDEF_STANDARD_C99) && !defined(TRIO_COMPILER_DECC)
173 # define TRIO_NAN_C99_FUNCTION
175 # if defined(NAN) && defined(__STDC_IEC_559__)
176 # define TRIO_NAN_C99_MACRO
178 # if defined(TRIO_IEEE_754)
179 # define TRIO_NAN_IEEE_754
181 # define TRIO_NAN_FALLBACK
188 * Resolve internal dependencies.
190 #if defined(TRIO_FUNC_INTERNAL_FPCLASSIFY_AND_SIGNBIT)
191 # define TRIO_FUNC_INTERNAL_ISNAN
192 # define TRIO_FUNC_INTERNAL_ISINF
193 # if defined(TRIO_IEEE_754)
194 # define TRIO_FUNC_INTERNAL_IS_SPECIAL_QUANTITY
195 # define TRIO_FUNC_INTERNAL_IS_NEGATIVE
199 #if defined(TRIO_NZERO_IEEE_754) \
200 || defined(TRIO_PINF_IEEE_754) \
201 || defined(TRIO_NAN_IEEE_754)
202 # define TRIO_FUNC_INTERNAL_MAKE_DOUBLE
205 #if defined(TRIO_FUNC_INTERNAL_ISNAN)
206 # if defined(PREDEF_STANDARD_XPG3)
207 # define TRIO_INTERNAL_ISNAN_XPG3
209 # if defined(TRIO_IEEE_754)
210 # define TRIO_INTERNAL_ISNAN_IEEE_754
212 # define TRIO_INTERNAL_ISNAN_FALLBACK
217 #if defined(TRIO_FUNC_INTERNAL_ISINF)
218 # if defined(TRIO_IEEE_754)
219 # define TRIO_INTERNAL_ISINF_IEEE_754
221 # define TRIO_INTERNAL_ISINF_FALLBACK
225 /*************************************************************************
229 #if !defined(TRIO_EMBED_NAN)
230 static TRIO_CONST char rcsid[] = "@(#)$Id: trionan.c,v 1.33 2005/05/29 11:57:25 breese Exp $";
233 #if defined(TRIO_FUNC_INTERNAL_MAKE_DOUBLE) \
234 || defined(TRIO_FUNC_INTERNAL_IS_SPECIAL_QUANTITY) \
235 || defined(TRIO_FUNC_INTERNAL_IS_NEGATIVE)
237 * Endian-agnostic indexing macro.
239 * The value of internalEndianMagic, when converted into a 64-bit
240 * integer, becomes 0x0706050403020100 (we could have used a 64-bit
241 * integer value instead of a double, but not all platforms supports
242 * that type). The value is automatically encoded with the correct
243 * endianess by the compiler, which means that we can support any
244 * kind of endianess. The individual bytes are then used as an index
245 * for the IEEE 754 bit-patterns and masks.
247 #define TRIO_DOUBLE_INDEX(x) (((unsigned char *)&internalEndianMagic)[7-(x)])
248 static TRIO_CONST double internalEndianMagic = 7.949928895127363e-275;
251 #if defined(TRIO_FUNC_INTERNAL_IS_SPECIAL_QUANTITY)
252 /* Mask for the exponent */
253 static TRIO_CONST unsigned char ieee_754_exponent_mask[] = {
254 0x7F, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
257 /* Mask for the mantissa */
258 static TRIO_CONST unsigned char ieee_754_mantissa_mask[] = {
259 0x00, 0x0F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF
263 #if defined(TRIO_FUNC_INTERNAL_IS_NEGATIVE)
264 /* Mask for the sign bit */
265 static TRIO_CONST unsigned char ieee_754_sign_mask[] = {
266 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
270 #if defined(TRIO_NZERO_IEEE_754)
271 /* Bit-pattern for negative zero */
272 static TRIO_CONST unsigned char ieee_754_negzero_array[] = {
273 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
277 #if defined(TRIO_PINF_IEEE_754)
278 /* Bit-pattern for infinity */
279 static TRIO_CONST unsigned char ieee_754_infinity_array[] = {
280 0x7F, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
284 #if defined(TRIO_NAN_IEEE_754)
285 /* Bit-pattern for quiet NaN */
286 static TRIO_CONST unsigned char ieee_754_qnan_array[] = {
287 0x7F, 0xF8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
292 /*************************************************************************
297 * internal_make_double
299 #if defined(TRIO_FUNC_INTERNAL_MAKE_DOUBLE)
301 TRIO_PRIVATE_NAN double
304 TRIO_CONST unsigned char *values)
306 TRIO_VOLATILE double result;
309 for (i = 0; i < (int)sizeof(double); i++) {
310 ((TRIO_VOLATILE unsigned char *)&result)[TRIO_DOUBLE_INDEX(i)] = values[i];
318 * internal_is_special_quantity
320 #if defined(TRIO_FUNC_INTERNAL_IS_SPECIAL_QUANTITY)
323 internal_is_special_quantity
324 TRIO_ARGS2((number, has_mantissa),
329 unsigned char current;
330 int is_special_quantity = TRIO_TRUE;
334 for (i = 0; i < (unsigned int)sizeof(double); i++) {
335 current = ((unsigned char *)&number)[TRIO_DOUBLE_INDEX(i)];
337 &= ((current & ieee_754_exponent_mask[i]) == ieee_754_exponent_mask[i]);
338 *has_mantissa |= (current & ieee_754_mantissa_mask[i]);
340 return is_special_quantity;
346 * internal_is_negative
348 #if defined(TRIO_FUNC_INTERNAL_IS_NEGATIVE)
356 int is_negative = TRIO_FALSE;
358 for (i = 0; i < (unsigned int)sizeof(double); i++) {
359 is_negative |= (((unsigned char *)&number)[TRIO_DOUBLE_INDEX(i)]
360 & ieee_754_sign_mask[i]);
367 #if defined(TRIO_FUNC_C99_FPCLASSIFY_AND_SIGNBIT)
369 TRIO_PRIVATE_NAN TRIO_INLINE int
370 c99_fpclassify_and_signbit
371 TRIO_ARGS2((number, is_negative),
375 *is_negative = signbit(number);
376 switch (fpclassify(number)) {
380 return TRIO_FP_INFINITE;
382 return TRIO_FP_SUBNORMAL;
386 return TRIO_FP_NORMAL;
390 #endif /* TRIO_FUNC_C99_FPCLASSIFY_AND_SIGNBIT */
392 #if defined(TRIO_FUNC_DECC_FPCLASSIFY_AND_SIGNBIT)
394 TRIO_PRIVATE_NAN TRIO_INLINE int
395 decc_fpclassify_and_signbit
396 TRIO_ARGS2((number, is_negative),
400 switch (fp_class(number)) {
403 *is_negative = TRIO_FALSE; /* NaN has no sign */
406 *is_negative = TRIO_FALSE;
407 return TRIO_FP_INFINITE;
409 *is_negative = TRIO_TRUE;
410 return TRIO_FP_INFINITE;
412 *is_negative = TRIO_FALSE;
413 return TRIO_FP_SUBNORMAL;
415 *is_negative = TRIO_TRUE;
416 return TRIO_FP_SUBNORMAL;
418 *is_negative = TRIO_FALSE;
421 *is_negative = TRIO_TRUE;
424 *is_negative = TRIO_FALSE;
425 return TRIO_FP_NORMAL;
427 *is_negative = TRIO_TRUE;
428 return TRIO_FP_NORMAL;
430 *is_negative = (number < 0.0);
431 return TRIO_FP_NORMAL;
435 #endif /* TRIO_FUNC_DECC_FPCLASSIFY_AND_SIGNBIT */
437 #if defined(TRIO_FUNC_MS_FPCLASSIFY_AND_SIGNBIT)
440 ms_fpclassify_and_signbit
441 TRIO_ARGS2((number, is_negative),
446 # if defined(TRIO_COMPILER_BORLAND)
448 * The floating-point precision may be changed by the Borland _fpclass()
449 * function, so we have to save and restore the floating-point control mask.
452 /* Remember the old mask */
453 mask = _control87(0, 0);
456 switch (_fpclass(number)) {
459 *is_negative = TRIO_FALSE; /* NaN has no sign */
460 result = TRIO_FP_NAN;
463 *is_negative = TRIO_FALSE;
464 result = TRIO_FP_INFINITE;
467 *is_negative = TRIO_TRUE;
468 result = TRIO_FP_INFINITE;
471 *is_negative = TRIO_FALSE;
472 result = TRIO_FP_SUBNORMAL;
475 *is_negative = TRIO_TRUE;
476 result = TRIO_FP_SUBNORMAL;
479 *is_negative = TRIO_FALSE;
480 result = TRIO_FP_ZERO;
483 *is_negative = TRIO_TRUE;
484 result = TRIO_FP_ZERO;
487 *is_negative = TRIO_FALSE;
488 result = TRIO_FP_NORMAL;
491 *is_negative = TRIO_TRUE;
492 result = TRIO_FP_NORMAL;
495 *is_negative = (number < 0.0);
496 result = TRIO_FP_NORMAL;
500 # if defined(TRIO_COMPILER_BORLAND)
501 /* Restore the old precision */
502 (void)_control87(mask, MCW_PC);
508 #endif /* TRIO_FUNC_MS_FPCLASSIFY_AND_SIGNBIT */
510 #if defined(TRIO_FUNC_HP_FPCLASSIFY_AND_SIGNBIT)
512 TRIO_PRIVATE_NAN TRIO_INLINE int
513 hp_fpclassify_and_signbit
514 TRIO_ARGS2((number, is_negative),
519 * HP-UX 9.x and 10.x have an fpclassify() function, that is different
520 * from the C99 fpclassify() macro supported on HP-UX 11.x.
522 switch (fpclassify(number)) {
525 *is_negative = TRIO_FALSE; /* NaN has no sign */
528 *is_negative = TRIO_FALSE;
529 return TRIO_FP_INFINITE;
531 *is_negative = TRIO_TRUE;
532 return TRIO_FP_INFINITE;
534 *is_negative = TRIO_FALSE;
535 return TRIO_FP_SUBNORMAL;
536 case FP_MINUS_DENORM:
537 *is_negative = TRIO_TRUE;
538 return TRIO_FP_SUBNORMAL;
540 *is_negative = TRIO_FALSE;
543 *is_negative = TRIO_TRUE;
546 *is_negative = TRIO_FALSE;
547 return TRIO_FP_NORMAL;
549 *is_negative = TRIO_TRUE;
550 return TRIO_FP_NORMAL;
552 *is_negative = (number < 0.0);
553 return TRIO_FP_NORMAL;
557 #endif /* TRIO_FUNC_HP_FPCLASSIFY_AND_SIGNBIT */
559 #if defined(TRIO_FUNC_XLC_FPCLASSIFY_AND_SIGNBIT)
561 TRIO_PRIVATE_NAN TRIO_INLINE int
562 xlc_fpclassify_and_signbit
563 TRIO_ARGS2((number, is_negative),
568 * AIX has class() for C, and _class() for C++
570 # if defined(__cplusplus)
571 # define AIX_CLASS(n) _class(n)
573 # define AIX_CLASS(n) class(n)
576 switch (AIX_CLASS(number)) {
579 *is_negative = TRIO_FALSE; /* NaN has no sign */
582 *is_negative = TRIO_FALSE;
583 return TRIO_FP_INFINITE;
585 *is_negative = TRIO_TRUE;
586 return TRIO_FP_INFINITE;
588 *is_negative = TRIO_FALSE;
589 return TRIO_FP_SUBNORMAL;
590 case FP_MINUS_DENORM:
591 *is_negative = TRIO_TRUE;
592 return TRIO_FP_SUBNORMAL;
594 *is_negative = TRIO_FALSE;
597 *is_negative = TRIO_TRUE;
600 *is_negative = TRIO_FALSE;
601 return TRIO_FP_NORMAL;
603 *is_negative = TRIO_TRUE;
604 return TRIO_FP_NORMAL;
606 *is_negative = (number < 0.0);
607 return TRIO_FP_NORMAL;
611 #endif /* TRIO_FUNC_XLC_FPCLASSIFY_AND_SIGNBIT */
613 #if defined(TRIO_FUNC_INTERNAL_ISNAN)
615 TRIO_PRIVATE_NAN TRIO_INLINE int
620 # if defined(TRIO_INTERNAL_ISNAN_XPG3) || defined(TRIO_PLATFORM_SYMBIAN)
622 * XPG3 defines isnan() as a function.
624 return isnan(number);
628 # if defined(TRIO_INTERNAL_ISNAN_IEEE_754)
631 * Examine IEEE 754 bit-pattern. A NaN must have a special exponent
632 * pattern, and a non-empty mantissa.
635 int is_special_quantity;
637 is_special_quantity = internal_is_special_quantity(number, &has_mantissa);
639 return (is_special_quantity && has_mantissa);
643 # if defined(TRIO_INTERNAL_ISNAN_FALLBACK)
649 double integral, fraction;
651 # if defined(TRIO_PLATFORM_UNIX)
652 void (*signal_handler)(int) = signal(SIGFPE, SIG_IGN);
656 * NaN is the only number which does not compare to itself
658 ((TRIO_VOLATILE double)number != (TRIO_VOLATILE double)number) ||
660 * Fallback solution if NaN compares to NaN
663 (fraction = modf(number, &integral),
664 integral == fraction)));
666 # if defined(TRIO_PLATFORM_UNIX)
667 signal(SIGFPE, signal_handler);
675 #endif /* TRIO_FUNC_INTERNAL_ISNAN */
677 #if defined(TRIO_FUNC_INTERNAL_ISINF)
679 TRIO_PRIVATE_NAN TRIO_INLINE int
684 # if defined(TRIO_PLATFORM_SYMBIAN)
686 return isinf(number);
690 # if defined(TRIO_INTERNAL_ISINF_IEEE_754)
692 * Examine IEEE 754 bit-pattern. Infinity must have a special exponent
693 * pattern, and an empty mantissa.
696 int is_special_quantity;
698 is_special_quantity = internal_is_special_quantity(number, &has_mantissa);
700 return (is_special_quantity && !has_mantissa)
701 ? ((number < 0.0) ? -1 : 1)
706 # if defined(TRIO_INTERNAL_ISINF_FALLBACK)
713 # if defined(TRIO_PLATFORM_UNIX)
714 void (*signal_handler)(int) = signal(SIGFPE, SIG_IGN);
717 double infinity = trio_pinf();
719 status = ((number == infinity)
721 : ((number == -infinity) ? -1 : 0));
723 # if defined(TRIO_PLATFORM_UNIX)
724 signal(SIGFPE, signal_handler);
732 #endif /* TRIO_FUNC_INTERNAL_ISINF */
734 /*************************************************************************
738 #if defined(TRIO_FUNC_FPCLASSIFY_AND_SIGNBIT)
741 trio_fpclassify_and_signbit
742 TRIO_ARGS2((number, is_negative),
746 /* The TRIO_FUNC_xxx_FPCLASSIFY_AND_SIGNBIT macros are mutually exclusive */
748 #if defined(TRIO_FUNC_C99_FPCLASSIFY_AND_SIGNBIT)
750 return c99_fpclassify_and_signbit(number, is_negative);
754 #if defined(TRIO_FUNC_DECC_FPCLASSIFY_AND_SIGNBIT)
756 return decc_fpclassify_and_signbit(number, is_negative);
760 #if defined(TRIO_FUNC_MS_FPCLASSIFY_AND_SIGNBIT)
762 return ms_fpclassify_and_signbit(number, is_negative);
766 #if defined(TRIO_FUNC_HP_FPCLASSIFY_AND_SIGNBIT)
768 return hp_fpclassify_and_signbit(number, is_negative);
772 #if defined(TRIO_FUNC_XLC_FPCLASSIFY_AND_SIGNBIT)
774 return xlc_fpclassify_and_signbit(number, is_negative);
778 #if defined(TRIO_FUNC_INTERNAL_FPCLASSIFY_AND_SIGNBIT)
787 * In IEEE 754 the sign of zero is ignored in comparisons, so we
788 * have to handle this as a special case by examining the sign bit
791 # if defined(TRIO_IEEE_754)
792 *is_negative = internal_is_negative(number);
794 *is_negative = TRIO_FALSE; /* FIXME */
798 if (internal_isnan(number)) {
799 *is_negative = TRIO_FALSE;
802 rc = internal_isinf(number);
804 *is_negative = (rc == -1);
805 return TRIO_FP_INFINITE;
807 if ((number > 0.0) && (number < DBL_MIN)) {
808 *is_negative = TRIO_FALSE;
809 return TRIO_FP_SUBNORMAL;
811 if ((number < 0.0) && (number > -DBL_MIN)) {
812 *is_negative = TRIO_TRUE;
813 return TRIO_FP_SUBNORMAL;
815 *is_negative = (number < 0.0);
816 return TRIO_FP_NORMAL;
826 @param number An arbitrary floating-point number.
827 @return Boolean value indicating whether or not the number is a NaN.
829 #if defined(TRIO_FUNC_ISNAN)
838 return (trio_fpclassify_and_signbit(number, &dummy) == TRIO_FP_NAN);
846 @param number An arbitrary floating-point number.
847 @return 1 if positive infinity, -1 if negative infinity, 0 otherwise.
849 #if defined(TRIO_FUNC_ISINF)
858 if (trio_fpclassify_and_signbit(number, &is_negative) == TRIO_FP_INFINITE)
860 return (is_negative) ? -1 : 1;
873 @param number An arbitrary floating-point number.
874 @return Boolean value indicating whether or not the number is a finite.
876 #if defined(TRIO_FUNC_ISFINITE)
885 switch (trio_fpclassify_and_signbit(number, &dummy))
887 case TRIO_FP_INFINITE:
898 Examine the sign of a number.
900 @param number An arbitrary floating-point number.
901 @return Boolean value indicating whether or not the number has the
902 sign bit set (i.e. is negative).
904 #if defined(TRIO_FUNC_SIGNBIT)
913 (void)trio_fpclassify_and_signbit(number, &is_negative);
920 Examine the class of a number.
922 @param number An arbitrary floating-point number.
923 @return Enumerable value indicating the class of @p number
925 #if defined(TRIO_FUNC_FPCLASSIFY)
934 return trio_fpclassify_and_signbit(number, &dummy);
940 Generate negative zero.
942 @return Floating-point representation of negative zero.
944 #if defined(TRIO_FUNC_NZERO)
946 TRIO_PUBLIC_NAN double
947 trio_nzero(TRIO_NOARGS)
949 # if defined(TRIO_NZERO_IEEE_754)
951 return internal_make_double(ieee_754_negzero_array);
955 # if defined(TRIO_NZERO_FALLBACK)
957 TRIO_VOLATILE double zero = 0.0;
967 Generate positive infinity.
969 @return Floating-point representation of positive infinity.
971 #if defined(TRIO_FUNC_PINF)
973 TRIO_PUBLIC_NAN double
974 trio_pinf(TRIO_NOARGS)
976 /* Cache the result */
977 static double pinf_value = 0.0;
979 if (pinf_value == 0.0) {
981 # if defined(TRIO_PINF_C99_MACRO)
983 pinf_value = (double)INFINITY;
987 # if defined(TRIO_PINF_IEEE_754)
989 pinf_value = internal_make_double(ieee_754_infinity_array);
993 # if defined(TRIO_PINF_FALLBACK)
995 * If HUGE_VAL is different from DBL_MAX, then HUGE_VAL is used
996 * as infinity. Otherwise we have to resort to an overflow
997 * operation to generate infinity.
999 # if defined(TRIO_PLATFORM_UNIX)
1000 void (*signal_handler)(int) = signal(SIGFPE, SIG_IGN);
1003 pinf_value = HUGE_VAL;
1004 if (HUGE_VAL == DBL_MAX) {
1005 /* Force overflow */
1006 pinf_value += HUGE_VAL;
1009 # if defined(TRIO_PLATFORM_UNIX)
1010 signal(SIGFPE, signal_handler);
1021 Generate negative infinity.
1023 @return Floating-point value of negative infinity.
1025 #if defined(TRIO_FUNC_NINF)
1027 TRIO_PUBLIC_NAN double
1028 trio_ninf(TRIO_NOARGS)
1030 static double ninf_value = 0.0;
1032 if (ninf_value == 0.0) {
1034 * Negative infinity is calculated by negating positive infinity,
1035 * which can be done because it is legal to do calculations on
1036 * infinity (for example, 1 / infinity == 0).
1038 ninf_value = -trio_pinf();
1048 @return Floating-point representation of NaN.
1050 #if defined(TRIO_FUNC_NAN)
1052 TRIO_PUBLIC_NAN double
1053 trio_nan(TRIO_NOARGS)
1055 /* Cache the result */
1056 static double nan_value = 0.0;
1058 if (nan_value == 0.0) {
1060 # if defined(TRIO_NAN_C99_FUNCTION) || defined(TRIO_PLATFORM_SYMBIAN)
1062 nan_value = nan("");
1066 # if defined(TRIO_NAN_C99_MACRO)
1068 nan_value = (double)NAN;
1072 # if defined(TRIO_NAN_IEEE_754)
1074 nan_value = internal_make_double(ieee_754_qnan_array);
1078 # if defined(TRIO_NAN_FALLBACK)
1080 * There are several ways to generate NaN. The one used here is
1081 * to divide infinity by infinity. I would have preferred to add
1082 * negative infinity to positive infinity, but that yields wrong
1083 * result (infinity) on FreeBSD.
1085 * This may fail if the hardware does not support NaN, or if
1086 * the Invalid Operation floating-point exception is unmasked.
1088 # if defined(TRIO_PLATFORM_UNIX)
1089 void (*signal_handler)(int) = signal(SIGFPE, SIG_IGN);
1092 nan_value = trio_pinf() / trio_pinf();
1094 # if defined(TRIO_PLATFORM_UNIX)
1095 signal(SIGFPE, signal_handler);
1105 /** @} SpecialQuantities */
1107 /*************************************************************************
1108 * For test purposes.
1110 * Add the following compiler option to include this test code.
1112 * Unix : -DSTANDALONE
1113 * VMS : /DEFINE=(STANDALONE)
1115 #if defined(STANDALONE)
1118 static TRIO_CONST char *
1124 case TRIO_FP_INFINITE:
1125 return "FP_INFINITE";
1128 case TRIO_FP_NORMAL:
1130 case TRIO_FP_SUBNORMAL:
1131 return "FP_SUBNORMAL";
1135 return "FP_UNKNOWN";
1141 TRIO_ARGS2((prefix, number),
1142 TRIO_CONST char *prefix,
1145 printf("%-6s: %s %-15s %g\n",
1147 trio_signbit(number) ? "-" : "+",
1148 getClassification(trio_fpclassify(number)),
1152 int main(TRIO_NOARGS)
1157 # if defined(TRIO_PLATFORM_UNIX)
1158 void (*signal_handler) TRIO_PROTO((int));
1161 my_nan = trio_nan();
1162 my_pinf = trio_pinf();
1163 my_ninf = trio_ninf();
1165 print_class("Nan", my_nan);
1166 print_class("PInf", my_pinf);
1167 print_class("NInf", my_ninf);
1168 print_class("PZero", 0.0);
1169 print_class("NZero", -0.0);
1170 print_class("PNorm", 1.0);
1171 print_class("NNorm", -1.0);
1172 print_class("PSub", 1.01e-307 - 1.00e-307);
1173 print_class("NSub", 1.00e-307 - 1.01e-307);
1175 printf("NaN : %4g 0x%02x%02x%02x%02x%02x%02x%02x%02x (%2d, %2d, %2d)\n",
1177 ((unsigned char *)&my_nan)[0],
1178 ((unsigned char *)&my_nan)[1],
1179 ((unsigned char *)&my_nan)[2],
1180 ((unsigned char *)&my_nan)[3],
1181 ((unsigned char *)&my_nan)[4],
1182 ((unsigned char *)&my_nan)[5],
1183 ((unsigned char *)&my_nan)[6],
1184 ((unsigned char *)&my_nan)[7],
1185 trio_isnan(my_nan), trio_isinf(my_nan), trio_isfinite(my_nan));
1186 printf("PInf: %4g 0x%02x%02x%02x%02x%02x%02x%02x%02x (%2d, %2d, %2d)\n",
1188 ((unsigned char *)&my_pinf)[0],
1189 ((unsigned char *)&my_pinf)[1],
1190 ((unsigned char *)&my_pinf)[2],
1191 ((unsigned char *)&my_pinf)[3],
1192 ((unsigned char *)&my_pinf)[4],
1193 ((unsigned char *)&my_pinf)[5],
1194 ((unsigned char *)&my_pinf)[6],
1195 ((unsigned char *)&my_pinf)[7],
1196 trio_isnan(my_pinf), trio_isinf(my_pinf), trio_isfinite(my_pinf));
1197 printf("NInf: %4g 0x%02x%02x%02x%02x%02x%02x%02x%02x (%2d, %2d, %2d)\n",
1199 ((unsigned char *)&my_ninf)[0],
1200 ((unsigned char *)&my_ninf)[1],
1201 ((unsigned char *)&my_ninf)[2],
1202 ((unsigned char *)&my_ninf)[3],
1203 ((unsigned char *)&my_ninf)[4],
1204 ((unsigned char *)&my_ninf)[5],
1205 ((unsigned char *)&my_ninf)[6],
1206 ((unsigned char *)&my_ninf)[7],
1207 trio_isnan(my_ninf), trio_isinf(my_ninf), trio_isfinite(my_ninf));
1209 # if defined(TRIO_PLATFORM_UNIX)
1210 signal_handler = signal(SIGFPE, SIG_IGN);
1213 my_pinf = DBL_MAX + DBL_MAX;
1215 my_nan = my_pinf / my_pinf;
1217 # if defined(TRIO_PLATFORM_UNIX)
1218 signal(SIGFPE, signal_handler);
1221 printf("NaN : %4g 0x%02x%02x%02x%02x%02x%02x%02x%02x (%2d, %2d, %2d)\n",
1223 ((unsigned char *)&my_nan)[0],
1224 ((unsigned char *)&my_nan)[1],
1225 ((unsigned char *)&my_nan)[2],
1226 ((unsigned char *)&my_nan)[3],
1227 ((unsigned char *)&my_nan)[4],
1228 ((unsigned char *)&my_nan)[5],
1229 ((unsigned char *)&my_nan)[6],
1230 ((unsigned char *)&my_nan)[7],
1231 trio_isnan(my_nan), trio_isinf(my_nan), trio_isfinite(my_nan));
1232 printf("PInf: %4g 0x%02x%02x%02x%02x%02x%02x%02x%02x (%2d, %2d, %2d)\n",
1234 ((unsigned char *)&my_pinf)[0],
1235 ((unsigned char *)&my_pinf)[1],
1236 ((unsigned char *)&my_pinf)[2],
1237 ((unsigned char *)&my_pinf)[3],
1238 ((unsigned char *)&my_pinf)[4],
1239 ((unsigned char *)&my_pinf)[5],
1240 ((unsigned char *)&my_pinf)[6],
1241 ((unsigned char *)&my_pinf)[7],
1242 trio_isnan(my_pinf), trio_isinf(my_pinf), trio_isfinite(my_pinf));
1243 printf("NInf: %4g 0x%02x%02x%02x%02x%02x%02x%02x%02x (%2d, %2d, %2d)\n",
1245 ((unsigned char *)&my_ninf)[0],
1246 ((unsigned char *)&my_ninf)[1],
1247 ((unsigned char *)&my_ninf)[2],
1248 ((unsigned char *)&my_ninf)[3],
1249 ((unsigned char *)&my_ninf)[4],
1250 ((unsigned char *)&my_ninf)[5],
1251 ((unsigned char *)&my_ninf)[6],
1252 ((unsigned char *)&my_ninf)[7],
1253 trio_isnan(my_ninf), trio_isinf(my_ninf), trio_isfinite(my_ninf));