summaryrefslogtreecommitdiff
path: root/src/regress/lib/libc/ieeefp/except/except.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/regress/lib/libc/ieeefp/except/except.c')
-rw-r--r--src/regress/lib/libc/ieeefp/except/except.c100
1 files changed, 100 insertions, 0 deletions
diff --git a/src/regress/lib/libc/ieeefp/except/except.c b/src/regress/lib/libc/ieeefp/except/except.c
new file mode 100644
index 0000000000..4e8c17d427
--- /dev/null
+++ b/src/regress/lib/libc/ieeefp/except/except.c
@@ -0,0 +1,100 @@
1/* $OpenBSD: except.c,v 1.6 2004/04/02 03:06:12 mickey Exp $ */
2
3#include <stdio.h>
4#include <stdlib.h>
5#include <signal.h>
6#include <assert.h>
7#include <ieeefp.h>
8#include <float.h>
9
10volatile sig_atomic_t signal_caught;
11
12volatile const double one = 1.0;
13volatile const double zero = 0.0;
14volatile const double huge = DBL_MAX;
15volatile const double tiny = DBL_MIN;
16
17void
18sigfpe(int sig, siginfo_t *si, void *v)
19{
20 char buf[132];
21
22 if (si) {
23 snprintf(buf, sizeof(buf), "sigfpe: addr=%p, code=%d\n",
24 si->si_addr, si->si_code);
25 write(1, buf, strlen(buf));
26 }
27 signal_caught = 1;
28}
29
30
31int
32main(int argc, char *argv[])
33{
34 struct sigaction sa;
35 volatile double x;
36
37 /*
38 * check to make sure that all exceptions are masked and
39 * that the accumulated exception status is clear.
40 */
41 assert(fpgetmask() == 0);
42 assert(fpgetsticky() == 0);
43
44 memset(&sa, 0, sizeof(sa));
45 sa.sa_sigaction = sigfpe;
46 sa.sa_flags = SA_SIGINFO;
47 sigaction(SIGFPE, &sa, NULL);
48 signal_caught = 0;
49
50 /* trip divide by zero */
51 x = one / zero;
52 assert(fpgetsticky() & FP_X_DZ);
53 assert(signal_caught == 0);
54 fpsetsticky(0);
55
56 /* trip invalid operation */
57 x = zero / zero;
58 assert(fpgetsticky() & FP_X_INV);
59 assert(signal_caught == 0);
60 fpsetsticky(0);
61
62 /* trip overflow */
63 x = huge * huge;
64 assert(fpgetsticky() & FP_X_OFL);
65 assert(signal_caught == 0);
66 fpsetsticky(0);
67
68 /* trip underflow */
69 x = tiny * tiny;
70 assert(fpgetsticky() & FP_X_UFL);
71 assert(signal_caught == 0);
72 fpsetsticky(0);
73
74 /* unmask and then trip divide by zero */
75 fpsetmask(FP_X_DZ);
76 x = one / zero;
77 assert(signal_caught == 1);
78 signal_caught = 0;
79
80 /* unmask and then trip invalid operation */
81 fpsetmask(FP_X_INV);
82 x = zero / zero;
83 assert(signal_caught == 1);
84 signal_caught = 0;
85
86 /* unmask and then trip overflow */
87 fpsetmask(FP_X_OFL);
88 x = huge * huge;
89 assert(signal_caught == 1);
90 signal_caught = 0;
91
92 /* unmask and then trip underflow */
93 fpsetmask(FP_X_UFL);
94 x = tiny * tiny;
95 assert (signal_caught == 1);
96 signal_caught = 0;
97
98 exit(0);
99}
100