test-snan.c 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153
  1. /* Test signaling NaNs in issignaling, isnan, isinf, and similar functions.
  2. Copyright (C) 2008-2016 Free Software Foundation, Inc.
  3. This file is part of the GNU C Library.
  4. Contributed by Andreas Jaeger <aj@suse.de>, 2005.
  5. The GNU C Library is free software; you can redistribute it and/or
  6. modify it under the terms of the GNU Lesser General Public
  7. License as published by the Free Software Foundation; either
  8. version 2.1 of the License, or (at your option) any later version.
  9. The GNU C Library is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  12. Lesser General Public License for more details.
  13. You should have received a copy of the GNU Lesser General Public
  14. License along with the GNU C Library; if not, see
  15. <http://www.gnu.org/licenses/>. */
  16. #define _GNU_SOURCE 1
  17. #include <stdio.h>
  18. #include <math.h>
  19. #include <float.h>
  20. #if __UCLIBC_HAS_FENV__
  21. #include <fenv.h>
  22. #endif
  23. #include <signal.h>
  24. #include <setjmp.h>
  25. #include "math-tests.h"
  26. #if __UCLIBC_HAS_FENV__
  27. static sigjmp_buf sigfpe_buf;
  28. static void
  29. myFPsighandler (int signal)
  30. {
  31. siglongjmp (sigfpe_buf, 1);
  32. }
  33. static int errors = 0;
  34. #define CHECK(testname, expr) \
  35. do { \
  36. feclearexcept (FE_ALL_EXCEPT); \
  37. feenableexcept (FE_ALL_EXCEPT); \
  38. if (sigsetjmp (sigfpe_buf, 0)) \
  39. { \
  40. printf ("%s raised SIGFPE\n", testname); \
  41. ++errors; \
  42. } \
  43. else if (!(expr)) \
  44. { \
  45. printf ("Failure: %s\n", testname); \
  46. ++errors; \
  47. } \
  48. } while (0)
  49. #define TEST_FUNC(NAME, FLOAT, SUFFIX) \
  50. static void \
  51. NAME (void) \
  52. { \
  53. /* Variables are declared volatile to forbid some compiler \
  54. optimizations. */ \
  55. volatile FLOAT Inf_var, qNaN_var, zero_var, one_var; \
  56. /* A sNaN is only guaranteed to be representable in variables with */ \
  57. /* static (or thread-local) storage duration. */ \
  58. static volatile FLOAT sNaN_var = __builtin_nans ## SUFFIX (""); \
  59. static volatile FLOAT minus_sNaN_var = -__builtin_nans ## SUFFIX (""); \
  60. fenv_t saved_fenv; \
  61. \
  62. zero_var = 0.0; \
  63. one_var = 1.0; \
  64. qNaN_var = __builtin_nan ## SUFFIX (""); \
  65. Inf_var = one_var / zero_var; \
  66. \
  67. (void) &zero_var; \
  68. (void) &one_var; \
  69. (void) &qNaN_var; \
  70. (void) &sNaN_var; \
  71. (void) &minus_sNaN_var; \
  72. (void) &Inf_var; \
  73. \
  74. fegetenv (&saved_fenv); \
  75. \
  76. CHECK (#FLOAT " issignaling (qNaN)", !issignaling (qNaN_var)); \
  77. CHECK (#FLOAT " issignaling (-qNaN)", !issignaling (-qNaN_var)); \
  78. CHECK (#FLOAT " issignaling (sNaN)", \
  79. SNAN_TESTS (FLOAT) ? issignaling (sNaN_var) : 1); \
  80. CHECK (#FLOAT " issignaling (-sNaN)", \
  81. SNAN_TESTS (FLOAT) ? issignaling (minus_sNaN_var) : 1); \
  82. CHECK (#FLOAT " isnan (qNaN)", isnan (qNaN_var)); \
  83. CHECK (#FLOAT " isnan (-qNaN)", isnan (-qNaN_var)); \
  84. CHECK (#FLOAT " isnan (sNaN)", \
  85. SNAN_TESTS (FLOAT) ? isnan (sNaN_var) : 1); \
  86. CHECK (#FLOAT " isnan (-sNaN)", \
  87. SNAN_TESTS (FLOAT) ? isnan (minus_sNaN_var) : 1); \
  88. CHECK (#FLOAT " isinf (qNaN)", !isinf (qNaN_var)); \
  89. CHECK (#FLOAT " isinf (-qNaN)", !isinf (-qNaN_var)); \
  90. CHECK (#FLOAT " isinf (sNaN)", \
  91. SNAN_TESTS (FLOAT) ? !isinf (sNaN_var) : 1); \
  92. CHECK (#FLOAT " isinf (-sNaN)", \
  93. SNAN_TESTS (FLOAT) ? !isinf (minus_sNaN_var) : 1); \
  94. CHECK (#FLOAT " isfinite (qNaN)", !isfinite (qNaN_var)); \
  95. CHECK (#FLOAT " isfinite (-qNaN)", !isfinite (-qNaN_var)); \
  96. CHECK (#FLOAT " isfinite (sNaN)", \
  97. SNAN_TESTS (FLOAT) ? !isfinite (sNaN_var) : 1); \
  98. CHECK (#FLOAT " isfinite (-sNaN)", \
  99. SNAN_TESTS (FLOAT) ? !isfinite (minus_sNaN_var) : 1); \
  100. CHECK (#FLOAT " isnormal (qNaN)", !isnormal (qNaN_var)); \
  101. CHECK (#FLOAT " isnormal (-qNaN)", !isnormal (-qNaN_var)); \
  102. CHECK (#FLOAT " isnormal (sNaN)", \
  103. SNAN_TESTS (FLOAT) ? !isnormal (sNaN_var) : 1); \
  104. CHECK (#FLOAT " isnormal (-sNaN)", \
  105. SNAN_TESTS (FLOAT) ? !isnormal (minus_sNaN_var) : 1); \
  106. CHECK (#FLOAT " fpclassify (qNaN)", (fpclassify (qNaN_var)==FP_NAN)); \
  107. CHECK (#FLOAT " fpclassify (-qNaN)", (fpclassify (-qNaN_var)==FP_NAN)); \
  108. CHECK (#FLOAT " fpclassify (sNaN)", \
  109. SNAN_TESTS (FLOAT) ? fpclassify (sNaN_var) == FP_NAN : 1); \
  110. CHECK (#FLOAT " fpclassify (-sNaN)", \
  111. SNAN_TESTS (FLOAT) ? fpclassify (minus_sNaN_var) == FP_NAN : 1); \
  112. \
  113. fesetenv (&saved_fenv); /* restore saved fenv */ \
  114. } \
  115. TEST_FUNC (float_test, float, f)
  116. TEST_FUNC (double_test, double, )
  117. #ifndef NO_LONG_DOUBLE
  118. TEST_FUNC (ldouble_test, long double, l)
  119. #endif
  120. #endif
  121. static int
  122. do_test (void)
  123. {
  124. #if __UCLIBC_HAS_FENV__
  125. signal (SIGFPE, &myFPsighandler);
  126. float_test ();
  127. double_test ();
  128. #ifndef NO_LONG_DOUBLE
  129. ldouble_test ();
  130. #endif
  131. return errors != 0;
  132. #else
  133. return 23;
  134. #endif
  135. }
  136. #define TEST_FUNCTION do_test ()
  137. #include "../test-skeleton.c"