]>
Commit | Line | Data |
---|---|---|
5f125488 A |
1 | #include <stdlib.h> |
2 | #include <unistd.h> | |
974e3884 A |
3 | #include <signal.h> |
4 | #include <setjmp.h> | |
5f125488 | 5 | |
974e3884 | 6 | #include <darwintest.h> |
5f125488 | 7 | |
974e3884 A |
8 | static char *heap; |
9 | static volatile int pass; | |
10 | static sigjmp_buf jbuf; | |
11 | ||
12 | static void __dead2 | |
5f125488 A |
13 | action(int signo, struct __siginfo *info, void *uap __attribute__((unused))) |
14 | { | |
15 | if (info) { | |
16 | pass = (signo == SIGBUS && info->si_addr == heap); | |
17 | } | |
974e3884 | 18 | siglongjmp(jbuf, 0); |
5f125488 A |
19 | } |
20 | ||
e07eda1a | 21 | T_DECL(nxheap, "Non-executable heap", T_META_CHECK_LEAKS(false), T_META_ASROOT(true)) |
5f125488 | 22 | { |
5f125488 A |
23 | struct sigaction sa = { |
24 | .__sigaction_u.__sa_sigaction = action, | |
25 | .sa_flags = SA_SIGINFO, | |
26 | }; | |
27 | ||
974e3884 | 28 | T_ASSERT_POSIX_ZERO(sigaction(SIGBUS, &sa, NULL), NULL); |
e07eda1a | 29 | |
5f125488 | 30 | if (sigsetjmp(jbuf, 0)) { |
974e3884 A |
31 | T_PASS("SIGBUS"); |
32 | T_END; | |
5f125488 A |
33 | } |
34 | ||
974e3884 | 35 | T_QUIET; T_ASSERT_NOTNULL((heap = malloc(1)), NULL); |
5f125488 | 36 | |
974e3884 | 37 | *heap = (char)0xc3; // retq |
5f125488 A |
38 | ((void (*)(void))heap)(); // call *%eax |
39 | ||
974e3884 | 40 | T_FAIL("SIGBUS"); |
5f125488 | 41 | } |