ia64/xen-unstable

view tools/security/get_decision.c @ 7778:0b4596caf761

nloopbacks default is now 8. So vifnum of greater than 7 requires
an adjustment to nloopbacks. Warning comment updated.

Signed-off-by: Nivedita Singhvi (niv@us.ibm.com)
author kaf24@firebug.cl.cam.ac.uk
date Fri Nov 11 10:46:36 2005 +0100 (2005-11-11)
parents 1e40bed176d4
children
line source
1 /****************************************************************
2 * get_decision.c
3 *
4 * Copyright (C) 2005 IBM Corporation
5 *
6 * Authors:
7 * Reiner Sailer <sailer@watson.ibm.com>
8 *
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License as
11 * published by the Free Software Foundation, version 2 of the
12 * License.
13 *
14 * An example program that shows how to retrieve an access control
15 * decision from the hypervisor ACM based on the currently active policy.
16 *
17 */
19 #include <unistd.h>
20 #include <stdio.h>
21 #include <errno.h>
22 #include <fcntl.h>
23 #include <getopt.h>
24 #include <sys/mman.h>
25 #include <sys/types.h>
26 #include <sys/stat.h>
27 #include <stdlib.h>
28 #include <sys/ioctl.h>
29 #include <string.h>
30 #include <netinet/in.h>
31 #include <xen/acm.h>
32 #include <xen/acm_ops.h>
33 #include <xen/linux/privcmd.h>
35 #define PERROR(_m, _a...) \
36 fprintf(stderr, "ERROR: " _m " (%d = %s)\n" , ## _a , \
37 errno, strerror(errno))
39 void usage(char *progname)
40 {
41 printf("Use: %s \n", progname);
42 printf(" Test program illustrating the retrieval of\n");
43 printf(" access control decisions from xen. At this time,\n");
44 printf(" only sharing (STE) policy decisions are supported.\n");
45 printf(" parameter options:\n");
46 printf("\t -i domid -i domid\n");
47 printf("\t -i domid -s ssidref\n");
48 printf("\t -s ssidref -s ssidref\n\n");
49 exit(-1);
50 }
52 static inline int do_policycmd(int xc_handle, unsigned int cmd,
53 unsigned long data)
54 {
55 return ioctl(xc_handle, cmd, data);
56 }
58 static inline int do_xen_hypercall(int xc_handle,
59 privcmd_hypercall_t * hypercall)
60 {
61 return do_policycmd(xc_handle,
62 IOCTL_PRIVCMD_HYPERCALL,
63 (unsigned long) hypercall);
64 }
66 static inline int do_acm_op(int xc_handle, struct acm_op *op)
67 {
68 int ret = -1;
69 privcmd_hypercall_t hypercall;
71 op->interface_version = ACM_INTERFACE_VERSION;
73 hypercall.op = __HYPERVISOR_acm_op;
74 hypercall.arg[0] = (unsigned long) op;
76 if (mlock(op, sizeof(*op)) != 0) {
77 PERROR("Could not lock memory for Xen policy hypercall");
78 goto out1;
79 }
81 if ((ret = do_xen_hypercall(xc_handle, &hypercall)) < 0) {
82 if (errno == EACCES)
83 fprintf(stderr, "ACM operation failed -- need to"
84 " rebuild the user-space tool set?\n");
85 goto out2;
86 }
88 out2:(void) munlock(op, sizeof(*op));
89 out1:return ret;
90 }
93 /************************ get decision ******************************/
95 /* this example uses two domain ids and retrieves the decision if these domains
96 * can share information (useful, i.e., to enforce policy onto network traffic in dom0
97 */
98 int acm_get_decision(int xc_handle, int argc, char *const argv[])
99 {
100 struct acm_op op;
101 int ret;
103 op.cmd = ACM_GETDECISION;
104 op.interface_version = ACM_INTERFACE_VERSION;
105 op.u.getdecision.get_decision_by1 = UNSET;
106 op.u.getdecision.get_decision_by2 = UNSET;
107 op.u.getdecision.hook = SHARING;
109 while (1) {
110 int c = getopt(argc, argv, "i:s:");
111 if (c == -1)
112 break;
114 if (c == 'i') {
115 if (op.u.getdecision.get_decision_by1 == UNSET) {
116 op.u.getdecision.get_decision_by1 = DOMAINID;
117 op.u.getdecision.id1.domainid = strtoul(optarg, NULL, 0);
118 } else if (op.u.getdecision.get_decision_by2 == UNSET) {
119 op.u.getdecision.get_decision_by2 = DOMAINID;
120 op.u.getdecision.id2.domainid = strtoul(optarg, NULL, 0);
121 } else
122 usage(argv[0]);
123 } else if (c == 's') {
124 if (op.u.getdecision.get_decision_by1 == UNSET) {
125 op.u.getdecision.get_decision_by1 = SSIDREF;
126 op.u.getdecision.id1.ssidref = strtoul(optarg, NULL, 0);
127 } else if (op.u.getdecision.get_decision_by2 == UNSET) {
128 op.u.getdecision.get_decision_by2 = SSIDREF;
129 op.u.getdecision.id2.ssidref = strtoul(optarg, NULL, 0);
130 } else
131 usage(argv[0]);
132 } else
133 usage(argv[0]);
134 }
135 if ((op.u.getdecision.get_decision_by1 == UNSET) ||
136 (op.u.getdecision.get_decision_by2 == UNSET))
137 usage(argv[0]);
139 if ((ret = do_acm_op(xc_handle, &op))) {
140 printf("%s: Error getting decision (%d).\n", __func__, ret);
141 printf("%s: decision = %s.\n", __func__,
142 (op.u.getdecision.acm_decision ==
143 ACM_ACCESS_PERMITTED) ? "PERMITTED" : ((op.u.getdecision.
144 acm_decision ==
145 ACM_ACCESS_DENIED)
146 ? "DENIED" :
147 "ERROR"));
148 return ret;
149 }
150 return op.u.getdecision.acm_decision;
151 }
153 /***************************** main **************************************/
155 int main(int argc, char **argv)
156 {
158 int acm_cmd_fd, ret = 0;
160 if (argc < 5)
161 usage(argv[0]);
163 if ((acm_cmd_fd = open("/proc/xen/privcmd", O_RDONLY)) <= 0) {
164 printf("ERROR: Could not open xen privcmd device!\n");
165 exit(-1);
166 }
168 ret = acm_get_decision(acm_cmd_fd, argc, argv);
170 printf("Decision: %s (%d)\n",
171 (ret == ACM_ACCESS_PERMITTED) ? "PERMITTED" :
172 ((ret == ACM_ACCESS_DENIED) ? "DENIED" : "ERROR"), ret);
174 close(acm_cmd_fd);
175 return ret;
176 }