xref: /xnu-10002.61.3/bsd/tests/pmap_test_sysctl.c (revision 0f4c859e951fba394238ab619495c4e1d54d0f34)
1 /*
2  * Copyright (c) 2016 Apple Inc. All rights reserved.
3  *
4  * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
5  *
6  * This file contains Original Code and/or Modifications of Original Code
7  * as defined in and that are subject to the Apple Public Source License
8  * Version 2.0 (the 'License'). You may not use this file except in
9  * compliance with the License. The rights granted to you under the License
10  * may not be used to create, or enable the creation or redistribution of,
11  * unlawful or unlicensed copies of an Apple operating system, or to
12  * circumvent, violate, or enable the circumvention or violation of, any
13  * terms of an Apple operating system software license agreement.
14  *
15  * Please obtain a copy of the License at
16  * http://www.opensource.apple.com/apsl/ and read it before using this file.
17  *
18  * The Original Code and all software distributed under the License are
19  * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
20  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
21  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
22  * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
23  * Please see the License for the specific language governing rights and
24  * limitations under the License.
25  *
26  * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
27  */
28 
29 #include <sys/sysctl.h>
30 
31 extern kern_return_t test_pmap_enter_disconnect(unsigned int);
32 extern kern_return_t test_pmap_compress_remove(unsigned int);
33 extern kern_return_t test_pmap_exec_remove(unsigned int);
34 extern kern_return_t test_pmap_nesting(unsigned int);
35 extern kern_return_t test_pmap_iommu_disconnect(void);
36 extern kern_return_t test_pmap_extended(void);
37 extern void test_pmap_call_overhead(unsigned int);
38 extern uint64_t test_pmap_page_protect_overhead(unsigned int, unsigned int);
39 
40 static int
sysctl_test_pmap_enter_disconnect(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)41 sysctl_test_pmap_enter_disconnect(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
42 {
43 	unsigned int num_loops;
44 	int error, changed;
45 	error = sysctl_io_number(req, 0, sizeof(num_loops), &num_loops, &changed);
46 	if (error || !changed) {
47 		return error;
48 	}
49 	return test_pmap_enter_disconnect(num_loops);
50 }
51 
52 SYSCTL_PROC(_kern, OID_AUTO, pmap_enter_disconnect_test,
53     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
54     0, 0, sysctl_test_pmap_enter_disconnect, "I", "");
55 
56 static int
sysctl_test_pmap_compress_remove(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)57 sysctl_test_pmap_compress_remove(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
58 {
59 	unsigned int num_loops;
60 	int error, changed;
61 	error = sysctl_io_number(req, 0, sizeof(num_loops), &num_loops, &changed);
62 	if (error || !changed) {
63 		return error;
64 	}
65 	return test_pmap_compress_remove(num_loops);
66 }
67 
68 SYSCTL_PROC(_kern, OID_AUTO, pmap_compress_remove_test,
69     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
70     0, 0, sysctl_test_pmap_compress_remove, "I", "");
71 
72 static int
sysctl_test_pmap_exec_remove(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)73 sysctl_test_pmap_exec_remove(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
74 {
75 	unsigned int num_loops;
76 	int error, changed;
77 	error = sysctl_io_number(req, 0, sizeof(num_loops), &num_loops, &changed);
78 	if (error || !changed) {
79 		return error;
80 	}
81 	return test_pmap_exec_remove(num_loops);
82 }
83 
84 SYSCTL_PROC(_kern, OID_AUTO, pmap_exec_remove_test,
85     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
86     0, 0, sysctl_test_pmap_exec_remove, "I", "");
87 
88 static int
sysctl_test_pmap_nesting(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)89 sysctl_test_pmap_nesting(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
90 {
91 	unsigned int num_loops;
92 	int error, changed;
93 	error = sysctl_io_number(req, 0, sizeof(num_loops), &num_loops, &changed);
94 	if (error || !changed) {
95 		return error;
96 	}
97 	return test_pmap_nesting(num_loops);
98 }
99 SYSCTL_PROC(_kern, OID_AUTO, pmap_nesting_test,
100     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
101     0, 0, sysctl_test_pmap_nesting, "I", "");
102 
103 static int
sysctl_test_pmap_iommu_disconnect(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)104 sysctl_test_pmap_iommu_disconnect(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
105 {
106 	unsigned int run = 0;
107 	int error, changed;
108 	error = sysctl_io_number(req, 0, sizeof(run), &run, &changed);
109 	if (error || !changed) {
110 		return error;
111 	}
112 	return test_pmap_iommu_disconnect();
113 }
114 
115 SYSCTL_PROC(_kern, OID_AUTO, pmap_iommu_disconnect_test,
116     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
117     0, 0, sysctl_test_pmap_iommu_disconnect, "I", "");
118 
119 static int
sysctl_test_pmap_extended(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)120 sysctl_test_pmap_extended(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
121 {
122 	unsigned int run = 0;
123 	int error, changed;
124 	error = sysctl_io_number(req, 0, sizeof(run), &run, &changed);
125 	if (error || !changed) {
126 		return error;
127 	}
128 	return test_pmap_extended();
129 }
130 
131 SYSCTL_PROC(_kern, OID_AUTO, pmap_extended_test,
132     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
133     0, 0, sysctl_test_pmap_extended, "I", "");
134 
135 static int
sysctl_test_pmap_call_overhead(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)136 sysctl_test_pmap_call_overhead(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
137 {
138 	unsigned int num_loops;
139 	int error, changed;
140 	error = sysctl_io_number(req, 0, sizeof(num_loops), &num_loops, &changed);
141 	if (error || !changed) {
142 		return error;
143 	}
144 	test_pmap_call_overhead(num_loops);
145 	return 0;
146 }
147 
148 SYSCTL_PROC(_kern, OID_AUTO, pmap_call_overhead_test,
149     CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_LOCKED,
150     0, 0, sysctl_test_pmap_call_overhead, "I", "");
151 
152 static int
sysctl_test_pmap_page_protect_overhead(__unused struct sysctl_oid * oidp,__unused void * arg1,__unused int arg2,struct sysctl_req * req)153 sysctl_test_pmap_page_protect_overhead(__unused struct sysctl_oid *oidp, __unused void *arg1, __unused int arg2, struct sysctl_req *req)
154 {
155 	struct {
156 		unsigned int num_loops;
157 		unsigned int num_aliases;
158 	} ppo_in;
159 
160 	int error;
161 	uint64_t duration;
162 
163 	error = SYSCTL_IN(req, &ppo_in, sizeof(ppo_in));
164 	if (error) {
165 		return error;
166 	}
167 
168 	duration = test_pmap_page_protect_overhead(ppo_in.num_loops, ppo_in.num_aliases);
169 	error = SYSCTL_OUT(req, &duration, sizeof(duration));
170 	return error;
171 }
172 
173 SYSCTL_PROC(_kern, OID_AUTO, pmap_page_protect_overhead_test,
174     CTLTYPE_OPAQUE | CTLFLAG_RW | CTLFLAG_LOCKED, 0, 0, sysctl_test_pmap_page_protect_overhead, "-", "");
175