ia64/xen-unstable

view linux-2.6-xen-sparse/include/asm-xen/asm-i386/hypercall.h @ 6756:f752e0c873a6

merge?
author cl349@firebug.cl.cam.ac.uk
date Mon Sep 12 12:32:20 2005 +0000 (2005-09-12)
parents dd668f7527cb 939fd35d58da
children 4d899a738d59 8ca0f98ba8e2
line source
1 /******************************************************************************
2 * hypercall.h
3 *
4 * Linux-specific hypervisor handling.
5 *
6 * Copyright (c) 2002-2004, K A Fraser
7 *
8 * This file may be distributed separately from the Linux kernel, or
9 * incorporated into other software packages, subject to the following license:
10 *
11 * Permission is hereby granted, free of charge, to any person obtaining a copy
12 * of this source file (the "Software"), to deal in the Software without
13 * restriction, including without limitation the rights to use, copy, modify,
14 * merge, publish, distribute, sublicense, and/or sell copies of the Software,
15 * and to permit persons to whom the Software is furnished to do so, subject to
16 * the following conditions:
17 *
18 * The above copyright notice and this permission notice shall be included in
19 * all copies or substantial portions of the Software.
20 *
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
22 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
23 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
24 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
25 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
26 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
27 * IN THE SOFTWARE.
28 */
30 #ifndef __HYPERCALL_H__
31 #define __HYPERCALL_H__
33 #include <asm-xen/xen-public/xen.h>
35 #define _hypercall0(type, name) \
36 ({ \
37 long __res; \
38 asm volatile ( \
39 TRAP_INSTR \
40 : "=a" (__res) \
41 : "0" (__HYPERVISOR_##name) \
42 : "memory" ); \
43 (type)__res; \
44 })
46 #define _hypercall1(type, name, a1) \
47 ({ \
48 long __res, __ign1; \
49 asm volatile ( \
50 TRAP_INSTR \
51 : "=a" (__res), "=b" (__ign1) \
52 : "0" (__HYPERVISOR_##name), "1" ((long)(a1)) \
53 : "memory" ); \
54 (type)__res; \
55 })
57 #define _hypercall2(type, name, a1, a2) \
58 ({ \
59 long __res, __ign1, __ign2; \
60 asm volatile ( \
61 TRAP_INSTR \
62 : "=a" (__res), "=b" (__ign1), "=c" (__ign2) \
63 : "0" (__HYPERVISOR_##name), "1" ((long)(a1)), \
64 "2" ((long)(a2)) \
65 : "memory" ); \
66 (type)__res; \
67 })
69 #define _hypercall3(type, name, a1, a2, a3) \
70 ({ \
71 long __res, __ign1, __ign2, __ign3; \
72 asm volatile ( \
73 TRAP_INSTR \
74 : "=a" (__res), "=b" (__ign1), "=c" (__ign2), \
75 "=d" (__ign3) \
76 : "0" (__HYPERVISOR_##name), "1" ((long)(a1)), \
77 "2" ((long)(a2)), "3" ((long)(a3)) \
78 : "memory" ); \
79 (type)__res; \
80 })
82 #define _hypercall4(type, name, a1, a2, a3, a4) \
83 ({ \
84 long __res, __ign1, __ign2, __ign3, __ign4; \
85 asm volatile ( \
86 TRAP_INSTR \
87 : "=a" (__res), "=b" (__ign1), "=c" (__ign2), \
88 "=d" (__ign3), "=S" (__ign4) \
89 : "0" (__HYPERVISOR_##name), "1" ((long)(a1)), \
90 "2" ((long)(a2)), "3" ((long)(a3)), \
91 "4" ((long)(a4)) \
92 : "memory" ); \
93 (type)__res; \
94 })
96 #define _hypercall5(type, name, a1, a2, a3, a4, a5) \
97 ({ \
98 long __res, __ign1, __ign2, __ign3, __ign4, __ign5; \
99 asm volatile ( \
100 TRAP_INSTR \
101 : "=a" (__res), "=b" (__ign1), "=c" (__ign2), \
102 "=d" (__ign3), "=S" (__ign4), "=D" (__ign5) \
103 : "0" (__HYPERVISOR_##name), "1" ((long)(a1)), \
104 "2" ((long)(a2)), "3" ((long)(a3)), \
105 "4" ((long)(a4)), "5" ((long)(a5)) \
106 : "memory" ); \
107 (type)__res; \
108 })
110 static inline int
111 HYPERVISOR_set_trap_table(
112 trap_info_t *table)
113 {
114 return _hypercall1(int, set_trap_table, table);
115 }
117 static inline int
118 HYPERVISOR_mmu_update(
119 mmu_update_t *req, int count, int *success_count, domid_t domid)
120 {
121 return _hypercall4(int, mmu_update, req, count, success_count, domid);
122 }
124 static inline int
125 HYPERVISOR_mmuext_op(
126 struct mmuext_op *op, int count, int *success_count, domid_t domid)
127 {
128 return _hypercall4(int, mmuext_op, op, count, success_count, domid);
129 }
131 static inline int
132 HYPERVISOR_set_gdt(
133 unsigned long *frame_list, int entries)
134 {
135 return _hypercall2(int, set_gdt, frame_list, entries);
136 }
138 static inline int
139 HYPERVISOR_stack_switch(
140 unsigned long ss, unsigned long esp)
141 {
142 return _hypercall2(int, stack_switch, ss, esp);
143 }
145 static inline int
146 HYPERVISOR_set_callbacks(
147 unsigned long event_selector, unsigned long event_address,
148 unsigned long failsafe_selector, unsigned long failsafe_address)
149 {
150 return _hypercall4(int, set_callbacks,
151 event_selector, event_address,
152 failsafe_selector, failsafe_address);
153 }
155 static inline int
156 HYPERVISOR_fpu_taskswitch(
157 int set)
158 {
159 return _hypercall1(int, fpu_taskswitch, set);
160 }
162 static inline int
163 HYPERVISOR_yield(
164 void)
165 {
166 return _hypercall2(int, sched_op, SCHEDOP_yield, 0);
167 }
169 static inline int
170 HYPERVISOR_block(
171 void)
172 {
173 return _hypercall2(int, sched_op, SCHEDOP_block, 0);
174 }
176 static inline int
177 HYPERVISOR_shutdown(
178 void)
179 {
180 return _hypercall2(int, sched_op, SCHEDOP_shutdown |
181 (SHUTDOWN_poweroff << SCHEDOP_reasonshift), 0);
182 }
184 static inline int
185 HYPERVISOR_reboot(
186 void)
187 {
188 return _hypercall2(int, sched_op, SCHEDOP_shutdown |
189 (SHUTDOWN_reboot << SCHEDOP_reasonshift), 0);
190 }
192 static inline int
193 HYPERVISOR_crash(
194 void)
195 {
196 return _hypercall2(int, sched_op, SCHEDOP_shutdown |
197 (SHUTDOWN_crash << SCHEDOP_reasonshift), 0);
198 }
200 static inline long
201 HYPERVISOR_set_timer_op(
202 u64 timeout)
203 {
204 unsigned long timeout_hi = (unsigned long)(timeout>>32);
205 unsigned long timeout_lo = (unsigned long)timeout;
206 return _hypercall2(long, set_timer_op, timeout_lo, timeout_hi);
207 }
209 static inline int
210 HYPERVISOR_dom0_op(
211 dom0_op_t *dom0_op)
212 {
213 dom0_op->interface_version = DOM0_INTERFACE_VERSION;
214 return _hypercall1(int, dom0_op, dom0_op);
215 }
217 static inline int
218 HYPERVISOR_set_debugreg(
219 int reg, unsigned long value)
220 {
221 return _hypercall2(int, set_debugreg, reg, value);
222 }
224 static inline unsigned long
225 HYPERVISOR_get_debugreg(
226 int reg)
227 {
228 return _hypercall1(unsigned long, get_debugreg, reg);
229 }
231 static inline int
232 HYPERVISOR_update_descriptor(
233 u64 ma, u64 desc)
234 {
235 return _hypercall4(int, update_descriptor, ma, ma>>32, desc, desc>>32);
236 }
238 static inline int
239 HYPERVISOR_memory_op(
240 unsigned int cmd, void *arg)
241 {
242 return _hypercall2(int, memory_op, cmd, arg);
243 }
245 static inline int
246 HYPERVISOR_multicall(
247 void *call_list, int nr_calls)
248 {
249 return _hypercall2(int, multicall, call_list, nr_calls);
250 }
252 static inline int
253 HYPERVISOR_update_va_mapping(
254 unsigned long va, pte_t new_val, unsigned long flags)
255 {
256 unsigned long pte_hi = 0;
257 #ifdef CONFIG_X86_PAE
258 pte_hi = new_val.pte_high;
259 #endif
260 return _hypercall4(int, update_va_mapping, va,
261 new_val.pte_low, pte_hi, flags);
262 }
264 static inline int
265 HYPERVISOR_event_channel_op(
266 void *op)
267 {
268 return _hypercall1(int, event_channel_op, op);
269 }
271 static inline int
272 HYPERVISOR_xen_version(
273 int cmd, void *arg)
274 {
275 return _hypercall2(int, xen_version, cmd, arg);
276 }
278 static inline int
279 HYPERVISOR_console_io(
280 int cmd, int count, char *str)
281 {
282 return _hypercall3(int, console_io, cmd, count, str);
283 }
285 static inline int
286 HYPERVISOR_physdev_op(
287 void *physdev_op)
288 {
289 return _hypercall1(int, physdev_op, physdev_op);
290 }
292 static inline int
293 HYPERVISOR_grant_table_op(
294 unsigned int cmd, void *uop, unsigned int count)
295 {
296 return _hypercall3(int, grant_table_op, cmd, uop, count);
297 }
299 static inline int
300 HYPERVISOR_update_va_mapping_otherdomain(
301 unsigned long va, pte_t new_val, unsigned long flags, domid_t domid)
302 {
303 unsigned long pte_hi = 0;
304 #ifdef CONFIG_X86_PAE
305 pte_hi = new_val.pte_high;
306 #endif
307 return _hypercall5(int, update_va_mapping_otherdomain, va,
308 new_val.pte_low, pte_hi, flags, domid);
309 }
311 static inline int
312 HYPERVISOR_vm_assist(
313 unsigned int cmd, unsigned int type)
314 {
315 return _hypercall2(int, vm_assist, cmd, type);
316 }
318 static inline int
319 HYPERVISOR_boot_vcpu(
320 unsigned long vcpu, vcpu_guest_context_t *ctxt)
321 {
322 return _hypercall2(int, boot_vcpu, vcpu, ctxt);
323 }
325 static inline int
326 HYPERVISOR_vcpu_up(
327 int vcpu)
328 {
329 return _hypercall2(int, sched_op, SCHEDOP_vcpu_up |
330 (vcpu << SCHEDOP_vcpushift), 0);
331 }
333 static inline int
334 HYPERVISOR_vcpu_pickle(
335 int vcpu, vcpu_guest_context_t *ctxt)
336 {
337 return _hypercall2(int, sched_op, SCHEDOP_vcpu_pickle |
338 (vcpu << SCHEDOP_vcpushift), ctxt);
339 }
341 static inline int
342 HYPERVISOR_suspend(
343 unsigned long srec)
344 {
345 int ret;
346 unsigned long ign1, ign2;
348 /* On suspend, control software expects a suspend record in %esi. */
349 __asm__ __volatile__ (
350 TRAP_INSTR
351 : "=a" (ret), "=b" (ign1), "=S" (ign2)
352 : "0" (__HYPERVISOR_sched_op),
353 "1" (SCHEDOP_shutdown | (SHUTDOWN_suspend <<
354 SCHEDOP_reasonshift)),
355 "2" (srec) : "memory", "ecx");
357 return ret;
358 }
360 static inline int
361 HYPERVISOR_vcpu_down(
362 int vcpu)
363 {
364 int ret;
365 unsigned long ign1;
366 /* Yes, I really do want to clobber edx here: when we resume a
367 vcpu after unpickling a multi-processor domain, it returns
368 here, but clobbers all of the call clobbered registers. */
369 __asm__ __volatile__ (
370 TRAP_INSTR
371 : "=a" (ret), "=b" (ign1)
372 : "0" (__HYPERVISOR_sched_op),
373 "1" (SCHEDOP_vcpu_down | (vcpu << SCHEDOP_vcpushift))
374 : "memory", "ecx", "edx" );
375 return ret;
376 }
378 #endif /* __HYPERCALL_H__ */
380 /*
381 * Local variables:
382 * c-file-style: "linux"
383 * indent-tabs-mode: t
384 * c-indent-level: 8
385 * c-basic-offset: 8
386 * tab-width: 8
387 * End:
388 */