xref: /xnu-12377.81.4/tests/ecc_test_helper.c (revision 043036a2b3718f7f0be807e2870f8f47d3fa0796)
1*043036a2SApple OSS Distributions #include <errno.h>
2*043036a2SApple OSS Distributions #include <stdio.h>
3*043036a2SApple OSS Distributions #include <stdlib.h>
4*043036a2SApple OSS Distributions #include <math.h>
5*043036a2SApple OSS Distributions #include <ptrauth.h>
6*043036a2SApple OSS Distributions #include <string.h>
7*043036a2SApple OSS Distributions #include <sys/mman.h>
8*043036a2SApple OSS Distributions #include <sys/sysctl.h>
9*043036a2SApple OSS Distributions #include <unistd.h>
10*043036a2SApple OSS Distributions 
11*043036a2SApple OSS Distributions #include <mach/mach_vm.h>
12*043036a2SApple OSS Distributions 
13*043036a2SApple OSS Distributions /*
14*043036a2SApple OSS Distributions  * ecc_test_helper is a convenience binary to induce various ECC errors
15*043036a2SApple OSS Distributions  * it's used by ECC-related tests: XNU unit tests and end-2-end coreos-tests
16*043036a2SApple OSS Distributions  */
17*043036a2SApple OSS Distributions 
18*043036a2SApple OSS Distributions 
19*043036a2SApple OSS Distributions int verbose = 0;
20*043036a2SApple OSS Distributions #define PRINTF(...) \
21*043036a2SApple OSS Distributions 	if (verbose) { \
22*043036a2SApple OSS Distributions 	        printf(__VA_ARGS__); \
23*043036a2SApple OSS Distributions 	}
24*043036a2SApple OSS Distributions 
25*043036a2SApple OSS Distributions __attribute__((noinline))
26*043036a2SApple OSS Distributions static void
foo(void)27*043036a2SApple OSS Distributions foo(void)
28*043036a2SApple OSS Distributions {
29*043036a2SApple OSS Distributions 	PRINTF("In foo()\n");
30*043036a2SApple OSS Distributions 	fflush(stdout);
31*043036a2SApple OSS Distributions }
32*043036a2SApple OSS Distributions 
33*043036a2SApple OSS Distributions volatile struct data {
34*043036a2SApple OSS Distributions 	char buffer1[16 * 1024];
35*043036a2SApple OSS Distributions 	int big_data[16 * 1024];
36*043036a2SApple OSS Distributions 	char buffer2[16 * 1024];
37*043036a2SApple OSS Distributions } x = {
38*043036a2SApple OSS Distributions 	.big_data = {
39*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
40*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
41*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
42*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
43*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
44*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
45*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
46*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
47*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
48*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
49*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
50*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
51*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
52*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
53*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
54*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
55*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
56*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
57*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
58*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
59*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
60*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
61*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
62*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
63*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
64*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
65*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
66*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
67*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
68*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
69*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
70*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
71*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
72*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
73*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
74*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
75*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
76*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
77*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
78*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
79*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
80*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
81*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
82*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
83*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
84*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
85*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
86*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
87*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
88*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
89*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
90*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
91*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
92*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
93*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
94*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
95*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
96*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
97*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
98*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
99*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
100*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
101*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
102*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
103*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
104*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
105*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
106*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
107*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
108*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
109*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
110*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
111*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
112*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
113*043036a2SApple OSS Distributions 		1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,
114*043036a2SApple OSS Distributions 	}
115*043036a2SApple OSS Distributions };
116*043036a2SApple OSS Distributions 
117*043036a2SApple OSS Distributions /*
118*043036a2SApple OSS Distributions  * volatile to stop the compiler from optimizing away calls to atan()
119*043036a2SApple OSS Distributions  */
120*043036a2SApple OSS Distributions volatile double zero = 0.0;
121*043036a2SApple OSS Distributions 
122*043036a2SApple OSS Distributions 
123*043036a2SApple OSS Distributions typedef enum TestCase {
124*043036a2SApple OSS Distributions 	Yfoo,
125*043036a2SApple OSS Distributions 	Xfoo,
126*043036a2SApple OSS Distributions 	Yatan,
127*043036a2SApple OSS Distributions 	Xatan,
128*043036a2SApple OSS Distributions 	Xclean,
129*043036a2SApple OSS Distributions 	Xdirty,
130*043036a2SApple OSS Distributions 	Xcopyout,
131*043036a2SApple OSS Distributions 	Xmmap_clean,
132*043036a2SApple OSS Distributions 	Xmmap_dirty,
133*043036a2SApple OSS Distributions 	Xwired,
134*043036a2SApple OSS Distributions 	kernel,
135*043036a2SApple OSS Distributions 	Xmte_active,
136*043036a2SApple OSS Distributions 
137*043036a2SApple OSS Distributions 	BAD_TEST_CASE
138*043036a2SApple OSS Distributions } TestCase;
139*043036a2SApple OSS Distributions 
140*043036a2SApple OSS Distributions typedef struct{
141*043036a2SApple OSS Distributions 	char *key;
142*043036a2SApple OSS Distributions 	enum TestCase val;
143*043036a2SApple OSS Distributions } testcase_t;
144*043036a2SApple OSS Distributions 
145*043036a2SApple OSS Distributions #define testCase(name) {#name, name}
146*043036a2SApple OSS Distributions 
147*043036a2SApple OSS Distributions static testcase_t testcases[] = {
148*043036a2SApple OSS Distributions 	testCase(Yfoo),
149*043036a2SApple OSS Distributions 	testCase(Xfoo),
150*043036a2SApple OSS Distributions 	testCase(Yatan),
151*043036a2SApple OSS Distributions 	testCase(Xatan),
152*043036a2SApple OSS Distributions 	testCase(Xclean),
153*043036a2SApple OSS Distributions 	testCase(Xdirty),
154*043036a2SApple OSS Distributions 	testCase(Xmmap_clean),
155*043036a2SApple OSS Distributions 	testCase(Xmmap_dirty),
156*043036a2SApple OSS Distributions 	testCase(Xcopyout),
157*043036a2SApple OSS Distributions 	testCase(kernel),
158*043036a2SApple OSS Distributions 	testCase(Xwired),
159*043036a2SApple OSS Distributions 	testCase(Xmte_active)
160*043036a2SApple OSS Distributions };
161*043036a2SApple OSS Distributions 
162*043036a2SApple OSS Distributions TestCase
get_testcase(char * key)163*043036a2SApple OSS Distributions get_testcase(char *key)
164*043036a2SApple OSS Distributions {
165*043036a2SApple OSS Distributions 	int i;
166*043036a2SApple OSS Distributions 	for (i = 0; i < sizeof(testcases) / sizeof(testcase_t); i++) {
167*043036a2SApple OSS Distributions 		testcase_t elem = testcases[i];
168*043036a2SApple OSS Distributions 		if (strcmp(elem.key, key) == 0) {
169*043036a2SApple OSS Distributions 			return elem.val;
170*043036a2SApple OSS Distributions 		}
171*043036a2SApple OSS Distributions 	}
172*043036a2SApple OSS Distributions 	return BAD_TEST_CASE;
173*043036a2SApple OSS Distributions }
174*043036a2SApple OSS Distributions 
175*043036a2SApple OSS Distributions int
main(int argc,char ** argv)176*043036a2SApple OSS Distributions main(int argc, char **argv)
177*043036a2SApple OSS Distributions {
178*043036a2SApple OSS Distributions 	void *addr;
179*043036a2SApple OSS Distributions 	int *page;
180*043036a2SApple OSS Distributions 	size_t s = sizeof(addr);
181*043036a2SApple OSS Distributions 	int err;
182*043036a2SApple OSS Distributions 	static volatile int readval;
183*043036a2SApple OSS Distributions 	static volatile double readval_d;
184*043036a2SApple OSS Distributions 
185*043036a2SApple OSS Distributions 	/*
186*043036a2SApple OSS Distributions 	 * check for -v for verbose output
187*043036a2SApple OSS Distributions 	 */
188*043036a2SApple OSS Distributions 	if (argc > 1 && strcmp(argv[1], "-v") == 0) {
189*043036a2SApple OSS Distributions 		verbose = 1;
190*043036a2SApple OSS Distributions 	}
191*043036a2SApple OSS Distributions 
192*043036a2SApple OSS Distributions 	/*
193*043036a2SApple OSS Distributions 	 * needs to run as root for sysctl
194*043036a2SApple OSS Distributions 	 */
195*043036a2SApple OSS Distributions 	if (geteuid() != 0) {
196*043036a2SApple OSS Distributions 		printf("Test not running as root, exiting\n");
197*043036a2SApple OSS Distributions 		exit(-1);
198*043036a2SApple OSS Distributions 	}
199*043036a2SApple OSS Distributions 
200*043036a2SApple OSS Distributions 	/*
201*043036a2SApple OSS Distributions 	 * The argument determines what test to try.
202*043036a2SApple OSS Distributions 	 * "Y{name}" is a test, "X{name}" does the test after injecting an ECC error
203*043036a2SApple OSS Distributions 	 *
204*043036a2SApple OSS Distributions 	 * Tests:
205*043036a2SApple OSS Distributions 	 * "foo" - invoke a local TEXT function.
206*043036a2SApple OSS Distributions 	 * "atan" - invoke a shared library TEXT function.
207*043036a2SApple OSS Distributions 	 * "clean" - read from a clean DATA page
208*043036a2SApple OSS Distributions 	 * "dirty" - read from a dirty DATA page
209*043036a2SApple OSS Distributions 	 * "mmap_clean" - read from a clean mmap'd page
210*043036a2SApple OSS Distributions 	 * "mmap_dirty" - read from a dirty mmap'd page
211*043036a2SApple OSS Distributions 	 */
212*043036a2SApple OSS Distributions 	switch (get_testcase(argv[argc - 1])) {
213*043036a2SApple OSS Distributions 	case Yfoo:
214*043036a2SApple OSS Distributions 		foo();
215*043036a2SApple OSS Distributions 		break;
216*043036a2SApple OSS Distributions 	case Xfoo:
217*043036a2SApple OSS Distributions 		PRINTF("Warm up call to foo()\n");
218*043036a2SApple OSS Distributions 		foo();
219*043036a2SApple OSS Distributions 
220*043036a2SApple OSS Distributions 		addr = (void *)ptrauth_strip(&foo, ptrauth_key_function_pointer);
221*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &addr, s);
222*043036a2SApple OSS Distributions 
223*043036a2SApple OSS Distributions 		PRINTF("Calling foo() after injection\n");
224*043036a2SApple OSS Distributions 		foo();
225*043036a2SApple OSS Distributions 
226*043036a2SApple OSS Distributions 		break;
227*043036a2SApple OSS Distributions 	case Yatan:
228*043036a2SApple OSS Distributions 		readval_d = atan(zero);
229*043036a2SApple OSS Distributions 		PRINTF("atan(0) is %g\n", readval_d);
230*043036a2SApple OSS Distributions 		break;
231*043036a2SApple OSS Distributions 	case Xatan:
232*043036a2SApple OSS Distributions 		readval_d = atan(zero);
233*043036a2SApple OSS Distributions 		PRINTF("Warmup call to atan(0) is %g\n", readval_d);
234*043036a2SApple OSS Distributions 
235*043036a2SApple OSS Distributions 		addr = (void *)ptrauth_strip(&atan, ptrauth_key_function_pointer);
236*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &addr, s);
237*043036a2SApple OSS Distributions 
238*043036a2SApple OSS Distributions 		readval_d = atan(zero);
239*043036a2SApple OSS Distributions 		PRINTF("After injection, atan(0) is %g\n", readval_d);
240*043036a2SApple OSS Distributions 		break;
241*043036a2SApple OSS Distributions 	case Xclean:
242*043036a2SApple OSS Distributions 		readval = x.big_data[35];
243*043036a2SApple OSS Distributions 		PRINTF("initial read of clean x.big_data[35] is %d\n", readval);
244*043036a2SApple OSS Distributions 
245*043036a2SApple OSS Distributions 		addr = (void *)&x.big_data[35];
246*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &addr, s);
247*043036a2SApple OSS Distributions 
248*043036a2SApple OSS Distributions 		readval = x.big_data[35];
249*043036a2SApple OSS Distributions 		PRINTF("After injection, read of x.big_data[35] is %d\n", readval);
250*043036a2SApple OSS Distributions 		break;
251*043036a2SApple OSS Distributions 	case Xdirty:
252*043036a2SApple OSS Distributions 		x.big_data[36] = (int)random();
253*043036a2SApple OSS Distributions 		PRINTF("initial read of dirty x.big_data[36] is %d\n", x.big_data[36]);
254*043036a2SApple OSS Distributions 
255*043036a2SApple OSS Distributions 		addr = (void *)&x.big_data[36];
256*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &addr, s);
257*043036a2SApple OSS Distributions 
258*043036a2SApple OSS Distributions 		readval = x.big_data[36];
259*043036a2SApple OSS Distributions 		PRINTF("After injection, read of x.big_data[36] is %d\n", readval);
260*043036a2SApple OSS Distributions 		break;
261*043036a2SApple OSS Distributions 	case Xmmap_clean:
262*043036a2SApple OSS Distributions 		page = (int *)mmap(NULL, PAGE_SIZE * 3, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, 0, 0);
263*043036a2SApple OSS Distributions 		page = (int *)((char *)page + PAGE_SIZE);
264*043036a2SApple OSS Distributions 
265*043036a2SApple OSS Distributions 		readval = *page;
266*043036a2SApple OSS Distributions 		PRINTF("initial read of clean page %p is %d\n", page, readval);
267*043036a2SApple OSS Distributions 
268*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &page, s);
269*043036a2SApple OSS Distributions 
270*043036a2SApple OSS Distributions 		readval = *page;
271*043036a2SApple OSS Distributions 		PRINTF("second read of page is %d\n", readval);
272*043036a2SApple OSS Distributions 		break;
273*043036a2SApple OSS Distributions 	case Xmmap_dirty:
274*043036a2SApple OSS Distributions 		page = (int *) mmap(NULL, PAGE_SIZE * 3, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, 0, 0);
275*043036a2SApple OSS Distributions 		page = (int *)((char *)page + PAGE_SIZE);
276*043036a2SApple OSS Distributions 
277*043036a2SApple OSS Distributions 		*page = 0xFFFF;
278*043036a2SApple OSS Distributions 		PRINTF("initial read of dirty page %p is %d (after write)\n", page, *page);
279*043036a2SApple OSS Distributions 
280*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &page, s);
281*043036a2SApple OSS Distributions 
282*043036a2SApple OSS Distributions 		readval = *page;
283*043036a2SApple OSS Distributions 		PRINTF("second read of page is %d\n", readval);
284*043036a2SApple OSS Distributions 		break;
285*043036a2SApple OSS Distributions 	case Xcopyout:
286*043036a2SApple OSS Distributions 		x.big_data[37] = (int)random();
287*043036a2SApple OSS Distributions 		PRINTF("initial read of dirty x.big_data[37] is %d\n", x.big_data[37]);
288*043036a2SApple OSS Distributions 
289*043036a2SApple OSS Distributions 		addr = (void *)&x.big_data[37];
290*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc_copyout", NULL, NULL, &addr, s);
291*043036a2SApple OSS Distributions 		if (err) {
292*043036a2SApple OSS Distributions 			PRINTF("copyout return %d\n", err);
293*043036a2SApple OSS Distributions 			exit(err);
294*043036a2SApple OSS Distributions 		}
295*043036a2SApple OSS Distributions 
296*043036a2SApple OSS Distributions 		readval = x.big_data[37];
297*043036a2SApple OSS Distributions 		PRINTF("After injection, read of dirty x.big_data[37] is %d\n", readval);
298*043036a2SApple OSS Distributions 		break;
299*043036a2SApple OSS Distributions 	case Xwired:
300*043036a2SApple OSS Distributions 		page = (int *) mmap(NULL, PAGE_SIZE * 3, PROT_READ | PROT_WRITE, MAP_ANON | MAP_PRIVATE, 0, 0);
301*043036a2SApple OSS Distributions 		page = (int *)((char *)page + PAGE_SIZE);
302*043036a2SApple OSS Distributions 		PRINTF("page addr %p\n", page);
303*043036a2SApple OSS Distributions 		if (mlock(page, PAGE_SIZE)) {
304*043036a2SApple OSS Distributions 			printf("Failed to wire, errno: %d", errno);
305*043036a2SApple OSS Distributions 			exit(0);
306*043036a2SApple OSS Distributions 		}
307*043036a2SApple OSS Distributions 
308*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &page, s);
309*043036a2SApple OSS Distributions 
310*043036a2SApple OSS Distributions 		readval = *page;
311*043036a2SApple OSS Distributions 		PRINTF("wire trigger value: %d", readval);
312*043036a2SApple OSS Distributions 
313*043036a2SApple OSS Distributions 		break;
314*043036a2SApple OSS Distributions 	case kernel:
315*043036a2SApple OSS Distributions 		PRINTF("Inducing ECC on kernel page\n");
316*043036a2SApple OSS Distributions 
317*043036a2SApple OSS Distributions 		addr = (void *)1;         /* used to flag some kernel page */
318*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc", NULL, NULL, &addr, s);
319*043036a2SApple OSS Distributions 		exit(0);
320*043036a2SApple OSS Distributions 	case Xmte_active:
321*043036a2SApple OSS Distributions 		PRINTF("Inducing ECC on MTE active storage page\n");
322*043036a2SApple OSS Distributions 		err = sysctlbyname("vm.inject_ecc_mte_active", NULL, NULL, NULL, 0);
323*043036a2SApple OSS Distributions 		if (err) {
324*043036a2SApple OSS Distributions 			printf("Failed to call sysctl vm.inject_ecc_mte_active: (%d) %s\n",
325*043036a2SApple OSS Distributions 			    errno, strerror(errno));
326*043036a2SApple OSS Distributions 			exit(errno);
327*043036a2SApple OSS Distributions 		}
328*043036a2SApple OSS Distributions 		exit(0);
329*043036a2SApple OSS Distributions 
330*043036a2SApple OSS Distributions 		break;
331*043036a2SApple OSS Distributions 	case BAD_TEST_CASE:
332*043036a2SApple OSS Distributions 		printf("Unknown test case\n\n");
333*043036a2SApple OSS Distributions 		printf("Valid tests:\n");
334*043036a2SApple OSS Distributions 		for (int i = 0; i < sizeof(testcases) / sizeof(testcase_t); i++) {
335*043036a2SApple OSS Distributions 			testcase_t elem = testcases[i];
336*043036a2SApple OSS Distributions 			printf("%d. %s\n", i + 1, elem.key);
337*043036a2SApple OSS Distributions 		}
338*043036a2SApple OSS Distributions 		printf("\nY{name} is a test, X{name} does the test after injecting an ECC error\n");
339*043036a2SApple OSS Distributions 
340*043036a2SApple OSS Distributions 		exit(1);
341*043036a2SApple OSS Distributions 
342*043036a2SApple OSS Distributions 		break;
343*043036a2SApple OSS Distributions 	}
344*043036a2SApple OSS Distributions 
345*043036a2SApple OSS Distributions 	exit(0);
346*043036a2SApple OSS Distributions }
347