1 #include <string.h>
2 #include <stdio.h>
3 #include <stdlib.h>
4 #include <sys/reason.h>
5 #include <dispatch/dispatch.h>
6 #include <dispatch/private.h>
7
8 #define TEST_REASON_CODE 4
9
10 #define countof(x) (sizeof(x) / sizeof(x[0]))
11
12 static bool
_should_spin(char * mode)13 _should_spin(char *mode)
14 {
15 // These tests are signaled by the parent
16 char *spin_modes[] = {
17 "spin",
18 "reason",
19 "reason_signal",
20 "clean",
21 "dirty",
22 };
23 for (size_t i = 0; i < countof(spin_modes); i++) {
24 if (strcmp(mode, spin_modes[i]) == 0) {
25 return true;
26 }
27 }
28 return false;
29 }
30
31 int
main(int argc,char * argv[])32 main(int argc, char *argv[])
33 {
34 if (argc != 2) {
35 printf("Missing arguments\n");
36 exit(1);
37 }
38
39 if (strcmp(argv[1], "crash") == 0) {
40 abort_with_reason(OS_REASON_TEST, TEST_REASON_CODE, "Test forcing crash", OS_REASON_FLAG_CONSISTENT_FAILURE | OS_REASON_FLAG_NO_CRASH_REPORT);
41 } else if (strcmp(argv[1], "success") == 0) {
42 exit(0);
43 } else if (strcmp(argv[1], "exit") == 0) {
44 exit(2);
45 } else if (strcmp(argv[1], "wait") == 0) {
46 signal(SIGUSR1, SIG_IGN);
47 dispatch_source_t source = dispatch_source_create(DISPATCH_SOURCE_TYPE_SIGNAL, SIGUSR1, 0, NULL);
48 dispatch_source_set_event_handler(source, ^{
49 abort_with_reason(OS_REASON_TEST, TEST_REASON_CODE, "Test forcing crash", OS_REASON_FLAG_CONSISTENT_FAILURE | OS_REASON_FLAG_NO_CRASH_REPORT);
50 });
51 dispatch_activate(source);
52 } else if (_should_spin(argv[1])) {
53 while (1) {
54 // Do nothing until the parent kills us
55 continue;
56 }
57 } else {
58 printf("Unknown argument: %s\n", argv[1]);
59 exit(1);
60 }
61 dispatch_main();
62 }
63