direct-io.hg

view tools/security/secpol_tool.c @ 11330:3e54734e55f3

[IA64] Remove extraneous verbose output to clean up Fedora boot.

Signed-off-by: Aron Griffis <aron@hp.com>
author awilliam@xenbuild.aw
date Wed Aug 23 13:26:46 2006 -0600 (2006-08-23)
parents 21e6625a6c01
children 12f7be674616
line source
1 /****************************************************************
2 * secpol_tool.c
3 *
4 * Copyright (C) 2005 IBM Corporation
5 *
6 * Authors:
7 * Reiner Sailer <sailer@watson.ibm.com>
8 * Stefan Berger <stefanb@watson.ibm.com>
9 *
10 * This program is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU General Public License as
12 * published by the Free Software Foundation, version 2 of the
13 * License.
14 *
15 * sHype policy management tool. This code runs in a domain and
16 * manages the Xen security policy by interacting with the
17 * Xen access control module via the privcmd device,
18 * which is translated into a acm_op hypercall into Xen.
19 *
20 * indent -i4 -kr -nut
21 */
24 #include <unistd.h>
25 #include <stdio.h>
26 #include <errno.h>
27 #include <fcntl.h>
28 #include <getopt.h>
29 #include <sys/mman.h>
30 #include <sys/types.h>
31 #include <sys/stat.h>
32 #include <stdlib.h>
33 #include <sys/ioctl.h>
34 #include <string.h>
35 #include <netinet/in.h>
36 #include <stdint.h>
37 #include <xen/acm.h>
38 #include <xen/acm_ops.h>
40 #include <xenctrl.h>
42 #define PERROR(_m, _a...) \
43 fprintf(stderr, "ERROR: " _m " (%d = %s)\n" , ## _a , \
44 errno, strerror(errno))
46 void usage(char *progname)
47 {
48 printf("Usage: %s ACTION\n"
49 "ACTION is one of:\n"
50 "\t getpolicy\n"
51 "\t dumpstats\n"
52 "\t loadpolicy <binary policy file>\n", progname);
53 exit(-1);
54 }
56 /*************************** DUMPS *******************************/
58 void acm_dump_chinesewall_buffer(void *buf, int buflen)
59 {
61 struct acm_chwall_policy_buffer *cwbuf =
62 (struct acm_chwall_policy_buffer *) buf;
63 domaintype_t *ssids, *conflicts, *running_types, *conflict_aggregate;
64 int i, j;
67 if (htonl(cwbuf->policy_code) != ACM_CHINESE_WALL_POLICY) {
68 printf("CHINESE WALL POLICY CODE not found ERROR!!\n");
69 return;
70 }
71 printf("\n\nChinese Wall policy:\n");
72 printf("====================\n");
73 printf("Policy version= %x.\n", ntohl(cwbuf->policy_version));
74 printf("Max Types = %x.\n", ntohl(cwbuf->chwall_max_types));
75 printf("Max Ssidrefs = %x.\n", ntohl(cwbuf->chwall_max_ssidrefs));
76 printf("Max ConfSets = %x.\n", ntohl(cwbuf->chwall_max_conflictsets));
77 printf("Ssidrefs Off = %x.\n", ntohl(cwbuf->chwall_ssid_offset));
78 printf("Conflicts Off = %x.\n",
79 ntohl(cwbuf->chwall_conflict_sets_offset));
80 printf("Runing T. Off = %x.\n",
81 ntohl(cwbuf->chwall_running_types_offset));
82 printf("C. Agg. Off = %x.\n",
83 ntohl(cwbuf->chwall_conflict_aggregate_offset));
84 printf("\nSSID To CHWALL-Type matrix:\n");
86 ssids = (domaintype_t *) (buf + ntohl(cwbuf->chwall_ssid_offset));
87 for (i = 0; i < ntohl(cwbuf->chwall_max_ssidrefs); i++) {
88 printf("\n ssidref%2x: ", i);
89 for (j = 0; j < ntohl(cwbuf->chwall_max_types); j++)
90 printf("%02x ",
91 ntohs(ssids[i * ntohl(cwbuf->chwall_max_types) + j]));
92 }
93 printf("\n\nConfict Sets:\n");
94 conflicts =
95 (domaintype_t *) (buf + ntohl(cwbuf->chwall_conflict_sets_offset));
96 for (i = 0; i < ntohl(cwbuf->chwall_max_conflictsets); i++) {
97 printf("\n c-set%2x: ", i);
98 for (j = 0; j < ntohl(cwbuf->chwall_max_types); j++)
99 printf("%02x ",
100 ntohs(conflicts
101 [i * ntohl(cwbuf->chwall_max_types) + j]));
102 }
103 printf("\n");
105 printf("\nRunning\nTypes: ");
106 if (ntohl(cwbuf->chwall_running_types_offset)) {
107 running_types =
108 (domaintype_t *) (buf +
109 ntohl(cwbuf->chwall_running_types_offset));
110 for (i = 0; i < ntohl(cwbuf->chwall_max_types); i++) {
111 printf("%02x ", ntohs(running_types[i]));
112 }
113 printf("\n");
114 } else {
115 printf("Not Reported!\n");
116 }
117 printf("\nConflict\nAggregate Set: ");
118 if (ntohl(cwbuf->chwall_conflict_aggregate_offset)) {
119 conflict_aggregate =
120 (domaintype_t *) (buf +
121 ntohl(cwbuf->
122 chwall_conflict_aggregate_offset));
123 for (i = 0; i < ntohl(cwbuf->chwall_max_types); i++) {
124 printf("%02x ", ntohs(conflict_aggregate[i]));
125 }
126 printf("\n\n");
127 } else {
128 printf("Not Reported!\n");
129 }
130 }
132 void acm_dump_ste_buffer(void *buf, int buflen)
133 {
135 struct acm_ste_policy_buffer *stebuf =
136 (struct acm_ste_policy_buffer *) buf;
137 domaintype_t *ssids;
138 int i, j;
141 if (ntohl(stebuf->policy_code) != ACM_SIMPLE_TYPE_ENFORCEMENT_POLICY) {
142 printf("SIMPLE TYPE ENFORCEMENT POLICY CODE not found ERROR!!\n");
143 return;
144 }
145 printf("\nSimple Type Enforcement policy:\n");
146 printf("===============================\n");
147 printf("Policy version= %x.\n", ntohl(stebuf->policy_version));
148 printf("Max Types = %x.\n", ntohl(stebuf->ste_max_types));
149 printf("Max Ssidrefs = %x.\n", ntohl(stebuf->ste_max_ssidrefs));
150 printf("Ssidrefs Off = %x.\n", ntohl(stebuf->ste_ssid_offset));
151 printf("\nSSID To STE-Type matrix:\n");
153 ssids = (domaintype_t *) (buf + ntohl(stebuf->ste_ssid_offset));
154 for (i = 0; i < ntohl(stebuf->ste_max_ssidrefs); i++) {
155 printf("\n ssidref%2x: ", i);
156 for (j = 0; j < ntohl(stebuf->ste_max_types); j++)
157 printf("%02x ",
158 ntohs(ssids[i * ntohl(stebuf->ste_max_types) + j]));
159 }
160 printf("\n\n");
161 }
163 void acm_dump_policy_buffer(void *buf, int buflen)
164 {
165 struct acm_policy_buffer *pol = (struct acm_policy_buffer *) buf;
166 char *policy_reference_name =
167 (buf + ntohl(pol->policy_reference_offset) +
168 sizeof(struct acm_policy_reference_buffer));
169 printf("\nPolicy dump:\n");
170 printf("============\n");
171 printf("POLICY REFERENCE = %s.\n", policy_reference_name);
172 printf("PolicyVer = %x.\n", ntohl(pol->policy_version));
173 printf("Magic = %x.\n", ntohl(pol->magic));
174 printf("Len = %x.\n", ntohl(pol->len));
175 printf("Primary = %s (c=%x, off=%x).\n",
176 ACM_POLICY_NAME(ntohl(pol->primary_policy_code)),
177 ntohl(pol->primary_policy_code),
178 ntohl(pol->primary_buffer_offset));
179 printf("Secondary = %s (c=%x, off=%x).\n",
180 ACM_POLICY_NAME(ntohl(pol->secondary_policy_code)),
181 ntohl(pol->secondary_policy_code),
182 ntohl(pol->secondary_buffer_offset));
183 switch (ntohl(pol->primary_policy_code)) {
184 case ACM_CHINESE_WALL_POLICY:
185 acm_dump_chinesewall_buffer(buf +
186 ntohl(pol->primary_buffer_offset),
187 ntohl(pol->len) -
188 ntohl(pol->primary_buffer_offset));
189 break;
191 case ACM_SIMPLE_TYPE_ENFORCEMENT_POLICY:
192 acm_dump_ste_buffer(buf + ntohl(pol->primary_buffer_offset),
193 ntohl(pol->len) -
194 ntohl(pol->primary_buffer_offset));
195 break;
197 case ACM_NULL_POLICY:
198 printf("Primary policy is NULL Policy (n/a).\n");
199 break;
201 default:
202 printf("UNKNOWN POLICY!\n");
203 }
205 switch (ntohl(pol->secondary_policy_code)) {
206 case ACM_CHINESE_WALL_POLICY:
207 acm_dump_chinesewall_buffer(buf +
208 ntohl(pol->secondary_buffer_offset),
209 ntohl(pol->len) -
210 ntohl(pol->secondary_buffer_offset));
211 break;
213 case ACM_SIMPLE_TYPE_ENFORCEMENT_POLICY:
214 acm_dump_ste_buffer(buf + ntohl(pol->secondary_buffer_offset),
215 ntohl(pol->len) -
216 ntohl(pol->secondary_buffer_offset));
217 break;
219 case ACM_NULL_POLICY:
220 printf("Secondary policy is NULL Policy (n/a).\n");
221 break;
223 default:
224 printf("UNKNOWN POLICY!\n");
225 }
226 }
228 /******************************* get policy ******************************/
230 #define PULL_CACHE_SIZE 8192
231 uint8_t pull_buffer[PULL_CACHE_SIZE];
233 int acm_domain_getpolicy(int xc_handle)
234 {
235 struct acm_getpolicy getpolicy;
236 int ret;
238 memset(pull_buffer, 0x00, sizeof(pull_buffer));
239 getpolicy.interface_version = ACM_INTERFACE_VERSION;
240 set_xen_guest_handle(getpolicy.pullcache, pull_buffer);
241 getpolicy.pullcache_size = sizeof(pull_buffer);
242 ret = xc_acm_op(xc_handle, ACMOP_getpolicy, &getpolicy, sizeof(getpolicy));
244 if (ret < 0) {
245 printf("ACM operation failed: errno=%d\n", errno);
246 if (errno == EACCES)
247 fprintf(stderr, "ACM operation failed -- need to"
248 " rebuild the user-space tool set?\n");
249 }
251 /* dump policy */
252 acm_dump_policy_buffer(pull_buffer, sizeof(pull_buffer));
253 return ret;
254 }
256 /************************ load binary policy ******************************/
258 int acm_domain_loadpolicy(int xc_handle, const char *filename)
259 {
260 struct stat mystat;
261 int ret, fd;
262 off_t len;
263 uint8_t *buffer;
265 if ((ret = stat(filename, &mystat))) {
266 printf("File %s not found.\n", filename);
267 goto out;
268 }
270 len = mystat.st_size;
271 if ((buffer = malloc(len)) == NULL) {
272 ret = -ENOMEM;
273 goto out;
274 }
275 if ((fd = open(filename, O_RDONLY)) <= 0) {
276 ret = -ENOENT;
277 printf("File %s not found.\n", filename);
278 goto free_out;
279 }
280 if (len == read(fd, buffer, len)) {
281 struct acm_setpolicy setpolicy;
282 /* dump it and then push it down into xen/acm */
283 acm_dump_policy_buffer(buffer, len);
284 setpolicy.interface_version = ACM_INTERFACE_VERSION;
285 set_xen_guest_handle(setpolicy.pushcache, buffer);
286 setpolicy.pushcache_size = len;
287 ret = xc_acm_op(xc_handle, ACMOP_setpolicy, &setpolicy, sizeof(setpolicy));
289 if (ret)
290 printf
291 ("ERROR setting policy.\n");
292 else
293 printf("Successfully changed policy.\n");
295 } else {
296 ret = -1;
297 }
298 close(fd);
299 free_out:
300 free(buffer);
301 out:
302 return ret;
303 }
305 /************************ dump hook statistics ******************************/
306 void dump_ste_stats(struct acm_ste_stats_buffer *ste_stats)
307 {
308 printf("STE-Policy Security Hook Statistics:\n");
309 printf("ste: event_channel eval_count = %d\n",
310 ntohl(ste_stats->ec_eval_count));
311 printf("ste: event_channel denied_count = %d\n",
312 ntohl(ste_stats->ec_denied_count));
313 printf("ste: event_channel cache_hit_count = %d\n",
314 ntohl(ste_stats->ec_cachehit_count));
315 printf("ste:\n");
316 printf("ste: grant_table eval_count = %d\n",
317 ntohl(ste_stats->gt_eval_count));
318 printf("ste: grant_table denied_count = %d\n",
319 ntohl(ste_stats->gt_denied_count));
320 printf("ste: grant_table cache_hit_count = %d\n",
321 ntohl(ste_stats->gt_cachehit_count));
322 }
324 #define PULL_STATS_SIZE 8192
325 int acm_domain_dumpstats(int xc_handle)
326 {
327 uint8_t stats_buffer[PULL_STATS_SIZE];
328 struct acm_dumpstats dumpstats;
329 int ret;
330 struct acm_stats_buffer *stats;
332 memset(stats_buffer, 0x00, sizeof(stats_buffer));
333 dumpstats.interface_version = ACM_INTERFACE_VERSION;
334 set_xen_guest_handle(dumpstats.pullcache, stats_buffer);
335 dumpstats.pullcache_size = sizeof(stats_buffer);
336 ret = xc_acm_op(xc_handle, ACMOP_dumpstats, &dumpstats, sizeof(dumpstats));
338 if (ret < 0) {
339 printf
340 ("ERROR dumping policy stats. Try 'xm dmesg' to see details.\n");
341 return ret;
342 }
343 stats = (struct acm_stats_buffer *) stats_buffer;
345 printf("\nPolicy dump:\n");
346 printf("============\n");
347 printf("Magic = %x.\n", ntohl(stats->magic));
348 printf("Len = %x.\n", ntohl(stats->len));
350 switch (ntohl(stats->primary_policy_code)) {
351 case ACM_NULL_POLICY:
352 printf("NULL Policy: No statistics apply.\n");
353 break;
355 case ACM_CHINESE_WALL_POLICY:
356 printf("Chinese Wall Policy: No statistics apply.\n");
357 break;
359 case ACM_SIMPLE_TYPE_ENFORCEMENT_POLICY:
360 dump_ste_stats((struct acm_ste_stats_buffer *) (stats_buffer +
361 ntohl(stats->
362 primary_stats_offset)));
363 break;
365 default:
366 printf("UNKNOWN PRIMARY POLICY ERROR!\n");
367 }
369 switch (ntohl(stats->secondary_policy_code)) {
370 case ACM_NULL_POLICY:
371 printf("NULL Policy: No statistics apply.\n");
372 break;
374 case ACM_CHINESE_WALL_POLICY:
375 printf("Chinese Wall Policy: No statistics apply.\n");
376 break;
378 case ACM_SIMPLE_TYPE_ENFORCEMENT_POLICY:
379 dump_ste_stats((struct acm_ste_stats_buffer *) (stats_buffer +
380 ntohl(stats->
381 secondary_stats_offset)));
382 break;
384 default:
385 printf("UNKNOWN SECONDARY POLICY ERROR!\n");
386 }
387 return ret;
388 }
390 /***************************** main **************************************/
392 int main(int argc, char **argv)
393 {
395 int xc_handle, ret = 0;
397 if (argc < 2)
398 usage(argv[0]);
400 if ((xc_handle = xc_interface_open()) <= 0) {
401 printf("ERROR: Could not open xen privcmd device!\n");
402 exit(-1);
403 }
405 if (!strcmp(argv[1], "getpolicy")) {
406 if (argc != 2)
407 usage(argv[0]);
408 ret = acm_domain_getpolicy(xc_handle);
409 } else if (!strcmp(argv[1], "loadpolicy")) {
410 if (argc != 3)
411 usage(argv[0]);
412 ret = acm_domain_loadpolicy(xc_handle, argv[2]);
413 } else if (!strcmp(argv[1], "dumpstats")) {
414 if (argc != 2)
415 usage(argv[0]);
416 ret = acm_domain_dumpstats(xc_handle);
417 } else
418 usage(argv[0]);
420 xc_interface_close(xc_handle);
421 return ret;
422 }