ia64/xen-unstable

view xen/common/sysctl.c @ 14196:9d36026b1b43

xen: Cleanups and bug fixes after the rcu_lock_domain patch.
Signed-off-by: Keir Fraser <keir@xensource.com>
author kfraser@localhost.localdomain
date Thu Mar 01 11:38:55 2007 +0000 (2007-03-01)
parents 97826d77bd4d
children 7ab04fa25d52
line source
1 /******************************************************************************
2 * sysctl.c
3 *
4 * System management operations. For use by node control stack.
5 *
6 * Copyright (c) 2002-2006, K Fraser
7 */
9 #include <xen/config.h>
10 #include <xen/types.h>
11 #include <xen/lib.h>
12 #include <xen/mm.h>
13 #include <xen/sched.h>
14 #include <xen/domain.h>
15 #include <xen/event.h>
16 #include <xen/domain_page.h>
17 #include <xen/trace.h>
18 #include <xen/console.h>
19 #include <xen/iocap.h>
20 #include <xen/guest_access.h>
21 #include <asm/current.h>
22 #include <public/sysctl.h>
24 extern long arch_do_sysctl(
25 struct xen_sysctl *op, XEN_GUEST_HANDLE(xen_sysctl_t) u_sysctl);
27 long do_sysctl(XEN_GUEST_HANDLE(xen_sysctl_t) u_sysctl)
28 {
29 long ret = 0;
30 struct xen_sysctl curop, *op = &curop;
31 static DEFINE_SPINLOCK(sysctl_lock);
33 if ( !IS_PRIV(current->domain) )
34 return -EPERM;
36 if ( copy_from_guest(op, u_sysctl, 1) )
37 return -EFAULT;
39 if ( op->interface_version != XEN_SYSCTL_INTERFACE_VERSION )
40 return -EACCES;
42 spin_lock(&sysctl_lock);
44 switch ( op->cmd )
45 {
46 case XEN_SYSCTL_readconsole:
47 {
48 ret = read_console_ring(
49 guest_handle_cast(op->u.readconsole.buffer, char),
50 &op->u.readconsole.count,
51 op->u.readconsole.clear);
52 if ( copy_to_guest(u_sysctl, op, 1) )
53 ret = -EFAULT;
54 }
55 break;
57 case XEN_SYSCTL_tbuf_op:
58 {
59 ret = tb_control(&op->u.tbuf_op);
60 if ( copy_to_guest(u_sysctl, op, 1) )
61 ret = -EFAULT;
62 }
63 break;
65 case XEN_SYSCTL_sched_id:
66 {
67 op->u.sched_id.sched_id = sched_id();
68 if ( copy_to_guest(u_sysctl, op, 1) )
69 ret = -EFAULT;
70 else
71 ret = 0;
72 }
73 break;
75 case XEN_SYSCTL_getdomaininfolist:
76 {
77 struct domain *d;
78 struct xen_domctl_getdomaininfo info;
79 u32 num_domains = 0;
81 rcu_read_lock(&domlist_read_lock);
83 for_each_domain ( d )
84 {
85 if ( d->domain_id < op->u.getdomaininfolist.first_domain )
86 continue;
87 if ( num_domains == op->u.getdomaininfolist.max_domains )
88 break;
90 getdomaininfo(d, &info);
92 if ( copy_to_guest_offset(op->u.getdomaininfolist.buffer,
93 num_domains, &info, 1) )
94 {
95 ret = -EFAULT;
96 break;
97 }
99 num_domains++;
100 }
102 rcu_read_unlock(&domlist_read_lock);
104 if ( ret != 0 )
105 break;
107 op->u.getdomaininfolist.num_domains = num_domains;
109 if ( copy_to_guest(u_sysctl, op, 1) )
110 ret = -EFAULT;
111 }
112 break;
114 #ifdef PERF_COUNTERS
115 case XEN_SYSCTL_perfc_op:
116 {
117 ret = perfc_control(&op->u.perfc_op);
118 if ( copy_to_guest(u_sysctl, op, 1) )
119 ret = -EFAULT;
120 }
121 break;
122 #endif
124 default:
125 ret = arch_do_sysctl(op, u_sysctl);
126 break;
127 }
129 spin_unlock(&sysctl_lock);
131 return ret;
132 }
134 /*
135 * Local variables:
136 * mode: C
137 * c-set-style: "BSD"
138 * c-basic-offset: 4
139 * tab-width: 4
140 * indent-tabs-mode: nil
141 * End:
142 */