1 /* Test for fenv inline implementations.
2 Copyright (C) 2015-2017 Free Software Foundation, Inc.
3 This file is part of the GNU C Library.
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.
10 The GNU C Library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public
16 License along with the GNU C Library; if not, see
17 <http://www.gnu.org/licenses/>. */
23 /* To make sure the fenv inline function are used. */
24 #undef __NO_MATH_INLINES
28 #include <math-tests.h>
31 Since not all architectures might define all exceptions, we define
32 a private set and map accordingly.
35 #define INEXACT_EXC 0x1
36 #define DIVBYZERO_EXC 0x2
37 #define UNDERFLOW_EXC 0x04
38 #define OVERFLOW_EXC 0x08
39 #define INVALID_EXC 0x10
41 (INEXACT_EXC | DIVBYZERO_EXC | UNDERFLOW_EXC | OVERFLOW_EXC | \
43 static int count_errors
;
47 test_single_exception_fp_int (int exception
,
50 const char *flag_name
)
52 if (exception
& exc_flag
)
54 if (fetestexcept (fe_flag
))
55 printf (" Pass: Exception \"%s\" is set\n", flag_name
);
58 printf (" Fail: Exception \"%s\" is not set\n", flag_name
);
64 if (fetestexcept (fe_flag
))
66 printf (" Fail: Exception \"%s\" is set\n", flag_name
);
70 printf (" Pass: Exception \"%s\" is not set\n", flag_name
);
73 /* Test whether a given exception was raised. */
75 test_single_exception_fp_double (int exception
,
78 const char *flag_name
)
80 if (exception
& exc_flag
)
82 if (fetestexcept (fe_flag
))
83 printf (" Pass: Exception \"%s\" is set\n", flag_name
);
86 printf (" Fail: Exception \"%s\" is not set\n", flag_name
);
92 if (fetestexcept (fe_flag
))
94 printf (" Fail: Exception \"%s\" is set\n", flag_name
);
98 printf (" Pass: Exception \"%s\" is not set\n", flag_name
);
104 test_exceptions (const char *test_name
, int exception
)
106 printf ("Test: %s\n", test_name
);
108 test_single_exception_fp_double (exception
, DIVBYZERO_EXC
, FE_DIVBYZERO
,
112 test_single_exception_fp_double (exception
, INVALID_EXC
, FE_INVALID
,
116 test_single_exception_fp_double (exception
, INEXACT_EXC
, FE_INEXACT
,
120 test_single_exception_fp_double (exception
, UNDERFLOW_EXC
, FE_UNDERFLOW
,
124 test_single_exception_fp_double (exception
, OVERFLOW_EXC
, FE_OVERFLOW
,
130 test_exceptionflag (void)
132 printf ("Test: fegetexceptionflag (FE_ALL_EXCEPT)\n");
136 feclearexcept (FE_ALL_EXCEPT
);
138 feraiseexcept (FE_INVALID
);
139 fegetexceptflag (&excepts
, FE_ALL_EXCEPT
);
141 feclearexcept (FE_ALL_EXCEPT
);
142 feraiseexcept (FE_OVERFLOW
| FE_INEXACT
);
144 fesetexceptflag (&excepts
, FE_ALL_EXCEPT
);
146 test_single_exception_fp_int (INVALID_EXC
, INVALID_EXC
, FE_INVALID
,
148 test_single_exception_fp_int (INVALID_EXC
, OVERFLOW_EXC
, FE_OVERFLOW
,
150 test_single_exception_fp_int (INVALID_EXC
, INEXACT_EXC
, FE_INEXACT
,
153 /* Same test, but using double as argument */
154 feclearexcept (FE_ALL_EXCEPT
);
156 feraiseexcept (FE_INVALID
);
157 fegetexceptflag (&excepts
, (double)FE_ALL_EXCEPT
);
159 feclearexcept (FE_ALL_EXCEPT
);
160 feraiseexcept (FE_OVERFLOW
| FE_INEXACT
);
162 fesetexceptflag (&excepts
, (double)FE_ALL_EXCEPT
);
164 test_single_exception_fp_double (INVALID_EXC
, INVALID_EXC
, FE_INVALID
,
166 test_single_exception_fp_double (INVALID_EXC
, OVERFLOW_EXC
, FE_OVERFLOW
,
167 "OVERFLOW (double)");
168 test_single_exception_fp_double (INVALID_EXC
, INEXACT_EXC
, FE_INEXACT
,
174 test_fesetround (void)
176 #if defined FE_TONEAREST && defined FE_TOWARDZERO
180 printf ("Tests for fesetround\n");
182 /* The fesetround should not itself cause the test to fail, however it
183 should either succeed for both 'int' and 'double' argument, or fail
185 res1
= fesetround ((int) FE_TOWARDZERO
);
186 res2
= fesetround ((double) FE_TOWARDZERO
);
189 printf ("fesetround (FE_TOWARDZERO) failed: %d, %d\n", res1
, res2
);
193 res1
= fesetround ((int) FE_TONEAREST
);
194 res2
= fesetround ((double) FE_TONEAREST
);
197 printf ("fesetround (FE_TONEAREST) failed: %d, %d\n", res1
, res2
);
204 /* Tests for feenableexcept/fedisableexcept. */
206 feenable_test (const char *flag_name
, fexcept_t fe_exc
)
208 int fe_exci
= fe_exc
;
209 double fe_excd
= fe_exc
;
212 /* First disable all exceptions. */
213 if (fedisableexcept (FE_ALL_EXCEPT
) == -1)
215 printf ("Test: fedisableexcept (FE_ALL_EXCEPT) failed\n");
217 /* If this fails, the other tests don't make sense. */
221 /* Test for inline macros using integer argument. */
222 excepts
= feenableexcept (fe_exci
);
223 if (!EXCEPTION_ENABLE_SUPPORTED (fe_exci
) && excepts
== -1)
225 printf ("Test: not testing feenableexcept, it isn't implemented.\n");
230 printf ("Test: feenableexcept (%s) failed\n", flag_name
);
236 printf ("Test: feenableexcept (%s) failed, return should be 0, is %x\n",
241 /* And now disable the exception again. */
242 excepts
= fedisableexcept (fe_exc
);
245 printf ("Test: fedisableexcept (%s) failed\n", flag_name
);
249 if (excepts
!= fe_exc
)
251 printf ("Test: fedisableexcept (%s) failed, return should be 0x%x, is 0x%x\n",
252 flag_name
, (unsigned int)fe_exc
, excepts
);
256 /* Test for inline macros using double argument. */
257 excepts
= feenableexcept (fe_excd
);
258 if (!EXCEPTION_ENABLE_SUPPORTED (fe_excd
) && excepts
== -1)
260 printf ("Test: not testing feenableexcept, it isn't implemented.\n");
265 printf ("Test: feenableexcept (%s) failed\n", flag_name
);
271 printf ("Test: feenableexcept (%s) failed, return should be 0, is %x\n",
276 /* And now disable the exception again. */
277 excepts
= fedisableexcept (fe_exc
);
280 printf ("Test: fedisableexcept (%s) failed\n", flag_name
);
284 if (excepts
!= fe_exc
)
286 printf ("Test: fedisableexcept (%s) failed, return should be 0x%x, is 0x%x\n",
287 flag_name
, (unsigned int)fe_exc
, excepts
);
294 test_feenabledisable (void)
296 printf ("Tests for feenableexcepts/fedisableexcept\n");
298 /* We might have some exceptions still set. */
299 feclearexcept (FE_ALL_EXCEPT
);
302 feenable_test ("FE_DIVBYZERO", FE_DIVBYZERO
);
305 feenable_test ("FE_INVALID", FE_INVALID
);
308 feenable_test ("FE_INEXACT", FE_INEXACT
);
311 feenable_test ("FE_UNDERFLOW", FE_UNDERFLOW
);
314 feenable_test ("FE_OVERFLOW", FE_OVERFLOW
);
316 fesetenv (FE_DFL_ENV
);
322 /* clear all exceptions and test if all are cleared */
323 feclearexcept (FE_ALL_EXCEPT
);
324 test_exceptions ("feclearexcept (FE_ALL_EXCEPT) clears all exceptions",
327 /* raise all exceptions and test if all are raised */
328 feraiseexcept (FE_ALL_EXCEPT
);
329 if (EXCEPTION_TESTS (float))
330 test_exceptions ("feraiseexcept (FE_ALL_EXCEPT) raises all exceptions",
333 /* Same test, but using double as argument */
334 feclearexcept ((double)FE_ALL_EXCEPT
);
335 test_exceptions ("feclearexcept ((double)FE_ALL_EXCEPT) clears all exceptions",
338 feraiseexcept ((double)FE_ALL_EXCEPT
);
339 if (EXCEPTION_TESTS (float))
340 test_exceptions ("feraiseexcept ((double)FE_ALL_EXCEPT) raises all exceptions",
343 if (EXCEPTION_TESTS (float))
344 test_exceptionflag ();
348 test_feenabledisable ();
353 #define TEST_FUNCTION do_test ()
354 #include "../test-skeleton.c"