ia64/xen-unstable

view tools/python/xen/lowlevel/xc/xc.c @ 13945:978ff6fad81f

[POWERPC][XEN] Merge with xen-unstable.hg.
Signed-off-by: Hollis Blanchard <hollisb@us.ibm.com>
author Hollis Blanchard <hollisb@us.ibm.com>
date Tue Feb 06 15:03:52 2007 -0600 (2007-02-06)
parents 09b3fd488726 207523704fb1
children 6c938630de54
line source
1 /******************************************************************************
2 * Xc.c
3 *
4 * Copyright (c) 2003-2004, K A Fraser (University of Cambridge)
5 */
7 #include <Python.h>
8 #include <xenctrl.h>
9 #include <xenguest.h>
10 #include <zlib.h>
11 #include <fcntl.h>
12 #include <netinet/in.h>
13 #include <netinet/tcp.h>
14 #include <sys/types.h>
15 #include <sys/socket.h>
16 #include <sys/mman.h>
17 #include <netdb.h>
18 #include <arpa/inet.h>
20 #include "xenctrl.h"
21 #include <xen/hvm/hvm_info_table.h>
22 #include <xen/hvm/params.h>
24 /* Needed for Python versions earlier than 2.3. */
25 #ifndef PyMODINIT_FUNC
26 #define PyMODINIT_FUNC DL_EXPORT(void)
27 #endif
29 #define PKG "xen.lowlevel.xc"
30 #define CLS "xc"
32 static PyObject *xc_error_obj, *zero;
34 typedef struct {
35 PyObject_HEAD;
36 int xc_handle;
37 } XcObject;
40 static PyObject *dom_op(XcObject *self, PyObject *args,
41 int (*fn)(int, uint32_t));
43 static PyObject *pyxc_error_to_exception(void)
44 {
45 PyObject *pyerr;
46 const xc_error const *err = xc_get_last_error();
47 const char *desc = xc_error_code_to_desc(err->code);
49 if (err->code == XC_ERROR_NONE)
50 return PyErr_SetFromErrno(xc_error_obj);
52 if (err->message[0] != '\0')
53 pyerr = Py_BuildValue("(iss)", err->code, desc, err->message);
54 else
55 pyerr = Py_BuildValue("(is)", err->code, desc);
57 xc_clear_last_error();
59 PyErr_SetObject(xc_error_obj, pyerr);
61 return NULL;
62 }
64 static PyObject *pyxc_domain_dumpcore(XcObject *self, PyObject *args)
65 {
66 uint32_t dom;
67 char *corefile;
69 if (!PyArg_ParseTuple(args, "is", &dom, &corefile))
70 return NULL;
72 if ( (corefile == NULL) || (corefile[0] == '\0') )
73 return NULL;
75 if (xc_domain_dumpcore(self->xc_handle, dom, corefile) != 0)
76 return pyxc_error_to_exception();
78 Py_INCREF(zero);
79 return zero;
80 }
82 static PyObject *pyxc_handle(XcObject *self)
83 {
84 return PyInt_FromLong(self->xc_handle);
85 }
87 static PyObject *pyxc_domain_create(XcObject *self,
88 PyObject *args,
89 PyObject *kwds)
90 {
91 uint32_t dom = 0, ssidref = 0, flags = 0;
92 int ret, i, hvm = 0;
93 PyObject *pyhandle = NULL;
94 xen_domain_handle_t handle = {
95 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef,
96 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef };
98 static char *kwd_list[] = { "domid", "ssidref", "handle", "hvm", NULL };
100 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|iiOi", kwd_list,
101 &dom, &ssidref, &pyhandle, &hvm))
102 return NULL;
104 if ( pyhandle != NULL )
105 {
106 if ( !PyList_Check(pyhandle) ||
107 (PyList_Size(pyhandle) != sizeof(xen_domain_handle_t)) )
108 goto out_exception;
110 for ( i = 0; i < sizeof(xen_domain_handle_t); i++ )
111 {
112 PyObject *p = PyList_GetItem(pyhandle, i);
113 if ( !PyInt_Check(p) )
114 goto out_exception;
115 handle[i] = (uint8_t)PyInt_AsLong(p);
116 }
117 }
119 if ( hvm )
120 flags |= XEN_DOMCTL_CDF_hvm_guest;
122 if ( (ret = xc_domain_create(self->xc_handle, ssidref,
123 handle, flags, &dom)) < 0 )
124 return pyxc_error_to_exception();
126 return PyInt_FromLong(dom);
128 out_exception:
129 errno = EINVAL;
130 PyErr_SetFromErrno(xc_error_obj);
131 return NULL;
132 }
134 static PyObject *pyxc_domain_max_vcpus(XcObject *self, PyObject *args)
135 {
136 uint32_t dom, max;
138 if (!PyArg_ParseTuple(args, "ii", &dom, &max))
139 return NULL;
141 if (xc_domain_max_vcpus(self->xc_handle, dom, max) != 0)
142 return pyxc_error_to_exception();
144 Py_INCREF(zero);
145 return zero;
146 }
148 static PyObject *pyxc_domain_pause(XcObject *self, PyObject *args)
149 {
150 return dom_op(self, args, xc_domain_pause);
151 }
153 static PyObject *pyxc_domain_unpause(XcObject *self, PyObject *args)
154 {
155 return dom_op(self, args, xc_domain_unpause);
156 }
158 static PyObject *pyxc_domain_destroy(XcObject *self, PyObject *args)
159 {
160 return dom_op(self, args, xc_domain_destroy);
161 }
163 static PyObject *pyxc_domain_shutdown(XcObject *self, PyObject *args)
164 {
165 uint32_t dom, reason;
167 if (!PyArg_ParseTuple(args, "ii", &dom, &reason))
168 return NULL;
170 if (xc_domain_shutdown(self->xc_handle, dom, reason) != 0)
171 return pyxc_error_to_exception();
173 Py_INCREF(zero);
174 return zero;
175 }
177 static PyObject *pyxc_domain_resume(XcObject *self, PyObject *args)
178 {
179 return dom_op(self, args, xc_domain_resume);
180 }
182 static PyObject *pyxc_vcpu_setaffinity(XcObject *self,
183 PyObject *args,
184 PyObject *kwds)
185 {
186 uint32_t dom;
187 int vcpu = 0, i;
188 uint64_t cpumap = ~0ULL;
189 PyObject *cpulist = NULL;
191 static char *kwd_list[] = { "domid", "vcpu", "cpumap", NULL };
193 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|iO", kwd_list,
194 &dom, &vcpu, &cpulist) )
195 return NULL;
197 if ( (cpulist != NULL) && PyList_Check(cpulist) )
198 {
199 cpumap = 0ULL;
200 for ( i = 0; i < PyList_Size(cpulist); i++ )
201 cpumap |= (uint64_t)1 << PyInt_AsLong(PyList_GetItem(cpulist, i));
202 }
204 if ( xc_vcpu_setaffinity(self->xc_handle, dom, vcpu, cpumap) != 0 )
205 return pyxc_error_to_exception();
207 Py_INCREF(zero);
208 return zero;
209 }
211 static PyObject *pyxc_domain_setcpuweight(XcObject *self,
212 PyObject *args,
213 PyObject *kwds)
214 {
215 uint32_t dom;
216 float cpuweight = 1;
218 static char *kwd_list[] = { "domid", "cpuweight", NULL };
220 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|f", kwd_list,
221 &dom, &cpuweight) )
222 return NULL;
224 if ( xc_domain_setcpuweight(self->xc_handle, dom, cpuweight) != 0 )
225 return pyxc_error_to_exception();
227 Py_INCREF(zero);
228 return zero;
229 }
231 static PyObject *pyxc_domain_sethandle(XcObject *self, PyObject *args)
232 {
233 int i;
234 uint32_t dom;
235 PyObject *pyhandle;
236 xen_domain_handle_t handle;
238 if (!PyArg_ParseTuple(args, "iO", &dom, &pyhandle))
239 return NULL;
241 if ( !PyList_Check(pyhandle) ||
242 (PyList_Size(pyhandle) != sizeof(xen_domain_handle_t)) )
243 {
244 goto out_exception;
245 }
247 for ( i = 0; i < sizeof(xen_domain_handle_t); i++ )
248 {
249 PyObject *p = PyList_GetItem(pyhandle, i);
250 if ( !PyInt_Check(p) )
251 goto out_exception;
252 handle[i] = (uint8_t)PyInt_AsLong(p);
253 }
255 if (xc_domain_sethandle(self->xc_handle, dom, handle) < 0)
256 return pyxc_error_to_exception();
258 Py_INCREF(zero);
259 return zero;
261 out_exception:
262 PyErr_SetFromErrno(xc_error_obj);
263 return NULL;
264 }
267 static PyObject *pyxc_domain_getinfo(XcObject *self,
268 PyObject *args,
269 PyObject *kwds)
270 {
271 PyObject *list, *info_dict;
273 uint32_t first_dom = 0;
274 int max_doms = 1024, nr_doms, i, j;
275 xc_dominfo_t *info;
277 static char *kwd_list[] = { "first_dom", "max_doms", NULL };
279 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|ii", kwd_list,
280 &first_dom, &max_doms) )
281 return NULL;
283 if ( (info = malloc(max_doms * sizeof(xc_dominfo_t))) == NULL )
284 return PyErr_NoMemory();
286 nr_doms = xc_domain_getinfo(self->xc_handle, first_dom, max_doms, info);
288 if (nr_doms < 0)
289 {
290 free(info);
291 return pyxc_error_to_exception();
292 }
294 list = PyList_New(nr_doms);
295 for ( i = 0 ; i < nr_doms; i++ )
296 {
297 PyObject *pyhandle = PyList_New(sizeof(xen_domain_handle_t));
298 for ( j = 0; j < sizeof(xen_domain_handle_t); j++ )
299 PyList_SetItem(pyhandle, j, PyInt_FromLong(info[i].handle[j]));
300 info_dict = Py_BuildValue("{s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i"
301 ",s:l,s:L,s:l,s:i,s:i}",
302 "domid", info[i].domid,
303 "online_vcpus", info[i].nr_online_vcpus,
304 "max_vcpu_id", info[i].max_vcpu_id,
305 "hvm", info[i].hvm,
306 "dying", info[i].dying,
307 "crashed", info[i].crashed,
308 "shutdown", info[i].shutdown,
309 "paused", info[i].paused,
310 "blocked", info[i].blocked,
311 "running", info[i].running,
312 "mem_kb", info[i].nr_pages*(XC_PAGE_SIZE/1024),
313 "cpu_time", info[i].cpu_time,
314 "maxmem_kb", info[i].max_memkb,
315 "ssidref", info[i].ssidref,
316 "shutdown_reason", info[i].shutdown_reason);
317 PyDict_SetItemString(info_dict, "handle", pyhandle);
318 Py_DECREF(pyhandle);
319 PyList_SetItem(list, i, info_dict);
320 }
322 free(info);
324 return list;
325 }
327 static PyObject *pyxc_vcpu_getinfo(XcObject *self,
328 PyObject *args,
329 PyObject *kwds)
330 {
331 PyObject *info_dict, *cpulist;
333 uint32_t dom, vcpu = 0;
334 xc_vcpuinfo_t info;
335 int rc, i;
336 uint64_t cpumap;
338 static char *kwd_list[] = { "domid", "vcpu", NULL };
340 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list,
341 &dom, &vcpu) )
342 return NULL;
344 rc = xc_vcpu_getinfo(self->xc_handle, dom, vcpu, &info);
345 if ( rc < 0 )
346 return pyxc_error_to_exception();
347 rc = xc_vcpu_getaffinity(self->xc_handle, dom, vcpu, &cpumap);
348 if ( rc < 0 )
349 return pyxc_error_to_exception();
351 info_dict = Py_BuildValue("{s:i,s:i,s:i,s:L,s:i}",
352 "online", info.online,
353 "blocked", info.blocked,
354 "running", info.running,
355 "cpu_time", info.cpu_time,
356 "cpu", info.cpu);
358 cpulist = PyList_New(0);
359 for ( i = 0; cpumap != 0; i++ )
360 {
361 if ( cpumap & 1 )
362 PyList_Append(cpulist, PyInt_FromLong(i));
363 cpumap >>= 1;
364 }
365 PyDict_SetItemString(info_dict, "cpumap", cpulist);
366 Py_DECREF(cpulist);
367 return info_dict;
368 }
370 static PyObject *pyxc_linux_build(XcObject *self,
371 PyObject *args,
372 PyObject *kwds)
373 {
374 uint32_t dom;
375 char *image, *ramdisk = NULL, *cmdline = "", *features = NULL;
376 int flags = 0;
377 int store_evtchn, console_evtchn;
378 unsigned int mem_mb;
379 unsigned long store_mfn = 0;
380 unsigned long console_mfn = 0;
382 static char *kwd_list[] = { "domid", "store_evtchn", "memsize",
383 "console_evtchn", "image",
384 /* optional */
385 "ramdisk", "cmdline", "flags",
386 "features", NULL };
388 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiis|ssis", kwd_list,
389 &dom, &store_evtchn, &mem_mb,
390 &console_evtchn, &image,
391 /* optional */
392 &ramdisk, &cmdline, &flags,
393 &features) )
394 return NULL;
396 if ( xc_linux_build(self->xc_handle, dom, mem_mb, image,
397 ramdisk, cmdline, features, flags,
398 store_evtchn, &store_mfn,
399 console_evtchn, &console_mfn) != 0 ) {
400 return pyxc_error_to_exception();
401 }
402 return Py_BuildValue("{s:i,s:i}",
403 "store_mfn", store_mfn,
404 "console_mfn", console_mfn);
405 }
407 static PyObject *pyxc_hvm_build(XcObject *self,
408 PyObject *args,
409 PyObject *kwds)
410 {
411 uint32_t dom;
412 #if !defined(__ia64__)
413 struct hvm_info_table *va_hvm;
414 uint8_t *va_map, sum;
415 int i;
416 #endif
417 char *image;
418 int store_evtchn, memsize, vcpus = 1, pae = 0, acpi = 0, apic = 1;
419 unsigned long store_mfn;
421 static char *kwd_list[] = { "domid", "store_evtchn",
422 "memsize", "image", "vcpus", "pae", "acpi",
423 "apic", NULL };
424 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiis|iiii", kwd_list,
425 &dom, &store_evtchn, &memsize,
426 &image, &vcpus, &pae, &acpi, &apic) )
427 return NULL;
429 if ( xc_hvm_build(self->xc_handle, dom, memsize, image) != 0 )
430 return pyxc_error_to_exception();
432 #if !defined(__ia64__)
433 /* Set up the HVM info table. */
434 va_map = xc_map_foreign_range(self->xc_handle, dom, XC_PAGE_SIZE,
435 PROT_READ | PROT_WRITE,
436 HVM_INFO_PFN);
437 if ( va_map == NULL )
438 return PyErr_SetFromErrno(xc_error_obj);
439 va_hvm = (struct hvm_info_table *)(va_map + HVM_INFO_OFFSET);
440 memset(va_hvm, 0, sizeof(*va_hvm));
441 strncpy(va_hvm->signature, "HVM INFO", 8);
442 va_hvm->length = sizeof(struct hvm_info_table);
443 va_hvm->acpi_enabled = acpi;
444 va_hvm->apic_mode = apic;
445 va_hvm->nr_vcpus = vcpus;
446 for ( i = 0, sum = 0; i < va_hvm->length; i++ )
447 sum += ((uint8_t *)va_hvm)[i];
448 va_hvm->checksum = -sum;
449 munmap(va_map, XC_PAGE_SIZE);
450 #endif
452 xc_get_hvm_param(self->xc_handle, dom, HVM_PARAM_STORE_PFN, &store_mfn);
453 #if !defined(__ia64__)
454 xc_set_hvm_param(self->xc_handle, dom, HVM_PARAM_PAE_ENABLED, pae);
455 #endif
456 xc_set_hvm_param(self->xc_handle, dom, HVM_PARAM_STORE_EVTCHN,
457 store_evtchn);
459 return Py_BuildValue("{s:i}", "store_mfn", store_mfn);
460 }
462 static PyObject *pyxc_evtchn_alloc_unbound(XcObject *self,
463 PyObject *args,
464 PyObject *kwds)
465 {
466 uint32_t dom, remote_dom;
467 int port;
469 static char *kwd_list[] = { "domid", "remote_dom", NULL };
471 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "ii", kwd_list,
472 &dom, &remote_dom) )
473 return NULL;
475 if ( (port = xc_evtchn_alloc_unbound(self->xc_handle, dom, remote_dom)) < 0 )
476 return pyxc_error_to_exception();
478 return PyInt_FromLong(port);
479 }
481 static PyObject *pyxc_evtchn_reset(XcObject *self,
482 PyObject *args,
483 PyObject *kwds)
484 {
485 uint32_t dom;
487 static char *kwd_list[] = { "dom", NULL };
489 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i", kwd_list, &dom) )
490 return NULL;
492 if ( xc_evtchn_reset(self->xc_handle, dom) < 0 )
493 return pyxc_error_to_exception();
495 Py_INCREF(zero);
496 return zero;
497 }
499 static PyObject *pyxc_physdev_pci_access_modify(XcObject *self,
500 PyObject *args,
501 PyObject *kwds)
502 {
503 uint32_t dom;
504 int bus, dev, func, enable, ret;
506 static char *kwd_list[] = { "domid", "bus", "dev", "func", "enable", NULL };
508 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiii", kwd_list,
509 &dom, &bus, &dev, &func, &enable) )
510 return NULL;
512 ret = xc_physdev_pci_access_modify(
513 self->xc_handle, dom, bus, dev, func, enable);
514 if ( ret != 0 )
515 return pyxc_error_to_exception();
517 Py_INCREF(zero);
518 return zero;
519 }
521 static PyObject *pyxc_readconsolering(XcObject *self,
522 PyObject *args,
523 PyObject *kwds)
524 {
525 unsigned int clear = 0;
526 char _str[32768], *str = _str;
527 unsigned int count = 32768;
528 int ret;
530 static char *kwd_list[] = { "clear", NULL };
532 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|i", kwd_list, &clear) )
533 return NULL;
535 ret = xc_readconsolering(self->xc_handle, &str, &count, clear);
536 if ( ret < 0 )
537 return pyxc_error_to_exception();
539 return PyString_FromStringAndSize(str, count);
540 }
543 static unsigned long pages_to_kib(unsigned long pages)
544 {
545 return pages * (XC_PAGE_SIZE / 1024);
546 }
549 static PyObject *pyxc_pages_to_kib(XcObject *self, PyObject *args)
550 {
551 unsigned long pages;
553 if (!PyArg_ParseTuple(args, "l", &pages))
554 return NULL;
556 return PyLong_FromUnsignedLong(pages_to_kib(pages));
557 }
560 static PyObject *pyxc_physinfo(XcObject *self)
561 {
562 xc_physinfo_t info;
563 char cpu_cap[128], *p=cpu_cap, *q=cpu_cap;
564 int i;
566 if ( xc_physinfo(self->xc_handle, &info) != 0 )
567 return pyxc_error_to_exception();
569 *q=0;
570 for(i=0;i<sizeof(info.hw_cap)/4;i++)
571 {
572 p+=sprintf(p,"%08x:",info.hw_cap[i]);
573 if(info.hw_cap[i])
574 q=p;
575 }
576 if(q>cpu_cap)
577 *(q-1)=0;
579 return Py_BuildValue("{s:i,s:i,s:i,s:i,s:l,s:l,s:l,s:i,s:s}",
580 "threads_per_core", info.threads_per_core,
581 "cores_per_socket", info.cores_per_socket,
582 "sockets_per_node", info.sockets_per_node,
583 "nr_nodes", info.nr_nodes,
584 "total_memory", pages_to_kib(info.total_pages),
585 "free_memory", pages_to_kib(info.free_pages),
586 "scrub_memory", pages_to_kib(info.scrub_pages),
587 "cpu_khz", info.cpu_khz,
588 "hw_caps", cpu_cap);
589 }
591 static PyObject *pyxc_xeninfo(XcObject *self)
592 {
593 xen_extraversion_t xen_extra;
594 xen_compile_info_t xen_cc;
595 xen_changeset_info_t xen_chgset;
596 xen_capabilities_info_t xen_caps;
597 xen_platform_parameters_t p_parms;
598 long xen_version;
599 long xen_pagesize;
600 char str[128];
602 xen_version = xc_version(self->xc_handle, XENVER_version, NULL);
604 if ( xc_version(self->xc_handle, XENVER_extraversion, &xen_extra) != 0 )
605 return pyxc_error_to_exception();
607 if ( xc_version(self->xc_handle, XENVER_compile_info, &xen_cc) != 0 )
608 return pyxc_error_to_exception();
610 if ( xc_version(self->xc_handle, XENVER_changeset, &xen_chgset) != 0 )
611 return pyxc_error_to_exception();
613 if ( xc_version(self->xc_handle, XENVER_capabilities, &xen_caps) != 0 )
614 return pyxc_error_to_exception();
616 if ( xc_version(self->xc_handle, XENVER_platform_parameters, &p_parms) != 0 )
617 return pyxc_error_to_exception();
619 sprintf(str, "virt_start=0x%lx", p_parms.virt_start);
621 xen_pagesize = xc_version(self->xc_handle, XENVER_pagesize, NULL);
622 if (xen_pagesize < 0 )
623 return pyxc_error_to_exception();
625 return Py_BuildValue("{s:i,s:i,s:s,s:s,s:i,s:s,s:s,s:s,s:s,s:s,s:s}",
626 "xen_major", xen_version >> 16,
627 "xen_minor", (xen_version & 0xffff),
628 "xen_extra", xen_extra,
629 "xen_caps", xen_caps,
630 "xen_pagesize", xen_pagesize,
631 "platform_params", str,
632 "xen_changeset", xen_chgset,
633 "cc_compiler", xen_cc.compiler,
634 "cc_compile_by", xen_cc.compile_by,
635 "cc_compile_domain", xen_cc.compile_domain,
636 "cc_compile_date", xen_cc.compile_date);
637 }
640 static PyObject *pyxc_sedf_domain_set(XcObject *self,
641 PyObject *args,
642 PyObject *kwds)
643 {
644 uint32_t domid;
645 uint64_t period, slice, latency;
646 uint16_t extratime, weight;
647 static char *kwd_list[] = { "domid", "period", "slice",
648 "latency", "extratime", "weight",NULL };
650 if( !PyArg_ParseTupleAndKeywords(args, kwds, "iLLLhh", kwd_list,
651 &domid, &period, &slice,
652 &latency, &extratime, &weight) )
653 return NULL;
654 if ( xc_sedf_domain_set(self->xc_handle, domid, period,
655 slice, latency, extratime,weight) != 0 )
656 return pyxc_error_to_exception();
658 Py_INCREF(zero);
659 return zero;
660 }
662 static PyObject *pyxc_sedf_domain_get(XcObject *self, PyObject *args)
663 {
664 uint32_t domid;
665 uint64_t period, slice,latency;
666 uint16_t weight, extratime;
668 if(!PyArg_ParseTuple(args, "i", &domid))
669 return NULL;
671 if (xc_sedf_domain_get(self->xc_handle, domid, &period,
672 &slice,&latency,&extratime,&weight))
673 return pyxc_error_to_exception();
675 return Py_BuildValue("{s:i,s:L,s:L,s:L,s:i,s:i}",
676 "domid", domid,
677 "period", period,
678 "slice", slice,
679 "latency", latency,
680 "extratime", extratime,
681 "weight", weight);
682 }
684 static PyObject *pyxc_shadow_control(PyObject *self,
685 PyObject *args,
686 PyObject *kwds)
687 {
688 XcObject *xc = (XcObject *)self;
690 uint32_t dom;
691 int op=0;
693 static char *kwd_list[] = { "dom", "op", NULL };
695 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list,
696 &dom, &op) )
697 return NULL;
699 if ( xc_shadow_control(xc->xc_handle, dom, op, NULL, 0, NULL, 0, NULL)
700 < 0 )
701 return pyxc_error_to_exception();
703 Py_INCREF(zero);
704 return zero;
705 }
707 static PyObject *pyxc_shadow_mem_control(PyObject *self,
708 PyObject *args,
709 PyObject *kwds)
710 {
711 XcObject *xc = (XcObject *)self;
712 int op;
713 uint32_t dom;
714 int mbarg = -1;
715 unsigned long mb;
717 static char *kwd_list[] = { "dom", "mb", NULL };
719 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list,
720 &dom, &mbarg) )
721 return NULL;
723 if ( mbarg < 0 )
724 op = XEN_DOMCTL_SHADOW_OP_GET_ALLOCATION;
725 else
726 {
727 mb = mbarg;
728 op = XEN_DOMCTL_SHADOW_OP_SET_ALLOCATION;
729 }
730 if ( xc_shadow_control(xc->xc_handle, dom, op, NULL, 0, &mb, 0, NULL) < 0 )
731 return pyxc_error_to_exception();
733 mbarg = mb;
734 return Py_BuildValue("i", mbarg);
735 }
737 static PyObject *pyxc_sched_id_get(XcObject *self) {
739 int sched_id;
740 if (xc_sched_id(self->xc_handle, &sched_id) != 0)
741 return PyErr_SetFromErrno(xc_error_obj);
743 return Py_BuildValue("i", sched_id);
744 }
746 static PyObject *pyxc_sched_credit_domain_set(XcObject *self,
747 PyObject *args,
748 PyObject *kwds)
749 {
750 uint32_t domid;
751 uint16_t weight;
752 uint16_t cap;
753 static char *kwd_list[] = { "domid", "weight", "cap", NULL };
754 static char kwd_type[] = "I|HH";
755 struct xen_domctl_sched_credit sdom;
757 weight = 0;
758 cap = (uint16_t)~0U;
759 if( !PyArg_ParseTupleAndKeywords(args, kwds, kwd_type, kwd_list,
760 &domid, &weight, &cap) )
761 return NULL;
763 sdom.weight = weight;
764 sdom.cap = cap;
766 if ( xc_sched_credit_domain_set(self->xc_handle, domid, &sdom) != 0 )
767 return pyxc_error_to_exception();
769 Py_INCREF(zero);
770 return zero;
771 }
773 static PyObject *pyxc_sched_credit_domain_get(XcObject *self, PyObject *args)
774 {
775 uint32_t domid;
776 struct xen_domctl_sched_credit sdom;
778 if( !PyArg_ParseTuple(args, "I", &domid) )
779 return NULL;
781 if ( xc_sched_credit_domain_get(self->xc_handle, domid, &sdom) != 0 )
782 return pyxc_error_to_exception();
784 return Py_BuildValue("{s:H,s:H}",
785 "weight", sdom.weight,
786 "cap", sdom.cap);
787 }
789 static PyObject *pyxc_domain_setmaxmem(XcObject *self, PyObject *args)
790 {
791 uint32_t dom;
792 unsigned int maxmem_kb;
794 if (!PyArg_ParseTuple(args, "ii", &dom, &maxmem_kb))
795 return NULL;
797 if (xc_domain_setmaxmem(self->xc_handle, dom, maxmem_kb) != 0)
798 return pyxc_error_to_exception();
800 Py_INCREF(zero);
801 return zero;
802 }
804 static PyObject *pyxc_domain_set_memmap_limit(XcObject *self, PyObject *args)
805 {
806 uint32_t dom;
807 unsigned int maplimit_kb;
809 if ( !PyArg_ParseTuple(args, "ii", &dom, &maplimit_kb) )
810 return NULL;
812 if ( xc_domain_set_memmap_limit(self->xc_handle, dom, maplimit_kb) != 0 )
813 return pyxc_error_to_exception();
815 Py_INCREF(zero);
816 return zero;
817 }
819 static PyObject *pyxc_domain_memory_increase_reservation(XcObject *self,
820 PyObject *args,
821 PyObject *kwds)
822 {
823 uint32_t dom;
824 unsigned long mem_kb;
825 unsigned int extent_order = 0 , address_bits = 0;
826 unsigned long nr_extents;
828 static char *kwd_list[] = { "domid", "mem_kb", "extent_order", "address_bits", NULL };
830 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "il|ii", kwd_list,
831 &dom, &mem_kb, &extent_order, &address_bits) )
832 return NULL;
834 /* round down to nearest power of 2. Assume callers using extent_order>0
835 know what they are doing */
836 nr_extents = (mem_kb / (XC_PAGE_SIZE/1024)) >> extent_order;
837 if ( xc_domain_memory_increase_reservation(self->xc_handle, dom,
838 nr_extents, extent_order,
839 address_bits, NULL) )
840 return pyxc_error_to_exception();
842 Py_INCREF(zero);
843 return zero;
844 }
846 static PyObject *pyxc_domain_ioport_permission(XcObject *self,
847 PyObject *args,
848 PyObject *kwds)
849 {
850 uint32_t dom;
851 int first_port, nr_ports, allow_access, ret;
853 static char *kwd_list[] = { "domid", "first_port", "nr_ports", "allow_access", NULL };
855 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiii", kwd_list,
856 &dom, &first_port, &nr_ports, &allow_access) )
857 return NULL;
859 ret = xc_domain_ioport_permission(
860 self->xc_handle, dom, first_port, nr_ports, allow_access);
861 if ( ret != 0 )
862 return pyxc_error_to_exception();
864 Py_INCREF(zero);
865 return zero;
866 }
868 static PyObject *pyxc_domain_irq_permission(PyObject *self,
869 PyObject *args,
870 PyObject *kwds)
871 {
872 XcObject *xc = (XcObject *)self;
873 uint32_t dom;
874 int pirq, allow_access, ret;
876 static char *kwd_list[] = { "domid", "pirq", "allow_access", NULL };
878 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iii", kwd_list,
879 &dom, &pirq, &allow_access) )
880 return NULL;
882 ret = xc_domain_irq_permission(
883 xc->xc_handle, dom, pirq, allow_access);
884 if ( ret != 0 )
885 return pyxc_error_to_exception();
887 Py_INCREF(zero);
888 return zero;
889 }
891 static PyObject *pyxc_domain_iomem_permission(PyObject *self,
892 PyObject *args,
893 PyObject *kwds)
894 {
895 XcObject *xc = (XcObject *)self;
896 uint32_t dom;
897 unsigned long first_pfn, nr_pfns, allow_access, ret;
899 static char *kwd_list[] = { "domid", "first_pfn", "nr_pfns", "allow_access", NULL };
901 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "illi", kwd_list,
902 &dom, &first_pfn, &nr_pfns, &allow_access) )
903 return NULL;
905 ret = xc_domain_iomem_permission(
906 xc->xc_handle, dom, first_pfn, nr_pfns, allow_access);
907 if ( ret != 0 )
908 return pyxc_error_to_exception();
910 Py_INCREF(zero);
911 return zero;
912 }
914 static PyObject *pyxc_domain_set_time_offset(XcObject *self, PyObject *args)
915 {
916 uint32_t dom;
917 int32_t time_offset_seconds;
918 time_t calendar_time;
919 struct tm local_time;
920 struct tm utc_time;
922 if (!PyArg_ParseTuple(args, "i", &dom))
923 return NULL;
925 calendar_time = time(NULL);
926 localtime_r(&calendar_time, &local_time);
927 gmtime_r(&calendar_time, &utc_time);
928 /* set up to get calendar time based on utc_time, with local dst setting */
929 utc_time.tm_isdst = local_time.tm_isdst;
930 time_offset_seconds = (int32_t)difftime(calendar_time, mktime(&utc_time));
932 if (xc_domain_set_time_offset(self->xc_handle, dom, time_offset_seconds) != 0)
933 return NULL;
935 Py_INCREF(zero);
936 return zero;
937 }
939 static PyObject *dom_op(XcObject *self, PyObject *args,
940 int (*fn)(int, uint32_t))
941 {
942 uint32_t dom;
944 if (!PyArg_ParseTuple(args, "i", &dom))
945 return NULL;
947 if (fn(self->xc_handle, dom) != 0)
948 return pyxc_error_to_exception();
950 Py_INCREF(zero);
951 return zero;
952 }
954 #ifdef __powerpc__
955 static PyObject *pyxc_alloc_real_mode_area(XcObject *self,
956 PyObject *args,
957 PyObject *kwds)
958 {
959 uint32_t dom;
960 unsigned int log;
962 static char *kwd_list[] = { "dom", "log", NULL };
964 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "ii", kwd_list,
965 &dom, &log) )
966 return NULL;
968 if ( xc_alloc_real_mode_area(self->xc_handle, dom, log) )
969 return pyxc_error_to_exception();
971 Py_INCREF(zero);
972 return zero;
973 }
975 static PyObject *pyxc_prose_build(XcObject *self,
976 PyObject *args,
977 PyObject *kwds)
978 {
979 uint32_t dom;
980 char *image, *ramdisk = NULL, *cmdline = "", *features = NULL;
981 int flags = 0;
982 int store_evtchn, console_evtchn;
983 unsigned int mem_mb;
984 unsigned long store_mfn = 0;
985 unsigned long console_mfn = 0;
986 int unused;
988 static char *kwd_list[] = { "dom", "store_evtchn",
989 "console_evtchn", "image", "memsize",
990 /* optional */
991 "ramdisk", "cmdline", "flags",
992 "features", NULL };
994 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiis|ssis#", kwd_list,
995 &dom, &store_evtchn, &mem_mb,
996 &console_evtchn, &image,
997 /* optional */
998 &ramdisk, &cmdline, &flags,
999 &features, &unused) )
1000 return NULL;
1002 if ( xc_prose_build(self->xc_handle, dom, mem_mb, image,
1003 ramdisk, cmdline, features, flags,
1004 store_evtchn, &store_mfn,
1005 console_evtchn, &console_mfn) != 0 ) {
1006 if (!errno)
1007 errno = EINVAL;
1008 return pyxc_error_to_exception();
1010 return Py_BuildValue("{s:i,s:i}",
1011 "store_mfn", store_mfn,
1012 "console_mfn", console_mfn);
1014 #endif /* powerpc */
1016 static PyMethodDef pyxc_methods[] = {
1017 { "handle",
1018 (PyCFunction)pyxc_handle,
1019 METH_NOARGS, "\n"
1020 "Query the xc control interface file descriptor.\n\n"
1021 "Returns: [int] file descriptor\n" },
1023 { "domain_create",
1024 (PyCFunction)pyxc_domain_create,
1025 METH_VARARGS | METH_KEYWORDS, "\n"
1026 "Create a new domain.\n"
1027 " dom [int, 0]: Domain identifier to use (allocated if zero).\n"
1028 "Returns: [int] new domain identifier; -1 on error.\n" },
1030 { "domain_max_vcpus",
1031 (PyCFunction)pyxc_domain_max_vcpus,
1032 METH_VARARGS, "\n"
1033 "Set the maximum number of VCPUs a domain may create.\n"
1034 " dom [int, 0]: Domain identifier to use.\n"
1035 " max [int, 0]: New maximum number of VCPUs in domain.\n"
1036 "Returns: [int] 0 on success; -1 on error.\n" },
1038 { "domain_dumpcore",
1039 (PyCFunction)pyxc_domain_dumpcore,
1040 METH_VARARGS, "\n"
1041 "Dump core of a domain.\n"
1042 " dom [int]: Identifier of domain to dump core of.\n"
1043 " corefile [string]: Name of corefile to be created.\n\n"
1044 "Returns: [int] 0 on success; -1 on error.\n" },
1046 { "domain_pause",
1047 (PyCFunction)pyxc_domain_pause,
1048 METH_VARARGS, "\n"
1049 "Temporarily pause execution of a domain.\n"
1050 " dom [int]: Identifier of domain to be paused.\n\n"
1051 "Returns: [int] 0 on success; -1 on error.\n" },
1053 { "domain_unpause",
1054 (PyCFunction)pyxc_domain_unpause,
1055 METH_VARARGS, "\n"
1056 "(Re)start execution of a domain.\n"
1057 " dom [int]: Identifier of domain to be unpaused.\n\n"
1058 "Returns: [int] 0 on success; -1 on error.\n" },
1060 { "domain_destroy",
1061 (PyCFunction)pyxc_domain_destroy,
1062 METH_VARARGS, "\n"
1063 "Destroy a domain.\n"
1064 " dom [int]: Identifier of domain to be destroyed.\n\n"
1065 "Returns: [int] 0 on success; -1 on error.\n" },
1067 { "domain_resume",
1068 (PyCFunction)pyxc_domain_resume,
1069 METH_VARARGS, "\n"
1070 "Resume execution of a suspended domain.\n"
1071 " dom [int]: Identifier of domain to be resumed.\n\n"
1072 "Returns: [int] 0 on success; -1 on error.\n" },
1074 { "domain_shutdown",
1075 (PyCFunction)pyxc_domain_shutdown,
1076 METH_VARARGS, "\n"
1077 "Shutdown a domain.\n"
1078 " dom [int, 0]: Domain identifier to use.\n"
1079 " reason [int, 0]: Reason for shutdown.\n"
1080 "Returns: [int] 0 on success; -1 on error.\n" },
1082 { "vcpu_setaffinity",
1083 (PyCFunction)pyxc_vcpu_setaffinity,
1084 METH_VARARGS | METH_KEYWORDS, "\n"
1085 "Pin a VCPU to a specified set CPUs.\n"
1086 " dom [int]: Identifier of domain to which VCPU belongs.\n"
1087 " vcpu [int, 0]: VCPU being pinned.\n"
1088 " cpumap [list, []]: list of usable CPUs.\n\n"
1089 "Returns: [int] 0 on success; -1 on error.\n" },
1091 { "domain_setcpuweight",
1092 (PyCFunction)pyxc_domain_setcpuweight,
1093 METH_VARARGS | METH_KEYWORDS, "\n"
1094 "Set cpuweight scheduler parameter for domain.\n"
1095 " dom [int]: Identifier of domain to be changed.\n"
1096 " cpuweight [float, 1]: VCPU being pinned.\n"
1097 "Returns: [int] 0 on success; -1 on error.\n" },
1099 { "domain_sethandle",
1100 (PyCFunction)pyxc_domain_sethandle,
1101 METH_VARARGS, "\n"
1102 "Set domain's opaque handle.\n"
1103 " dom [int]: Identifier of domain.\n"
1104 " handle [list of 16 ints]: New opaque handle.\n"
1105 "Returns: [int] 0 on success; -1 on error.\n" },
1107 { "domain_getinfo",
1108 (PyCFunction)pyxc_domain_getinfo,
1109 METH_VARARGS | METH_KEYWORDS, "\n"
1110 "Get information regarding a set of domains, in increasing id order.\n"
1111 " first_dom [int, 0]: First domain to retrieve info about.\n"
1112 " max_doms [int, 1024]: Maximum number of domains to retrieve info"
1113 " about.\n\n"
1114 "Returns: [list of dicts] if list length is less than 'max_doms'\n"
1115 " parameter then there was an error, or the end of the\n"
1116 " domain-id space was reached.\n"
1117 " dom [int]: Identifier of domain to which this info pertains\n"
1118 " cpu [int]: CPU to which this domain is bound\n"
1119 " vcpus [int]: Number of Virtual CPUS in this domain\n"
1120 " dying [int]: Bool - is the domain dying?\n"
1121 " crashed [int]: Bool - has the domain crashed?\n"
1122 " shutdown [int]: Bool - has the domain shut itself down?\n"
1123 " paused [int]: Bool - is the domain paused by control software?\n"
1124 " blocked [int]: Bool - is the domain blocked waiting for an event?\n"
1125 " running [int]: Bool - is the domain currently running?\n"
1126 " mem_kb [int]: Memory reservation, in kilobytes\n"
1127 " maxmem_kb [int]: Maximum memory limit, in kilobytes\n"
1128 " cpu_time [long]: CPU time consumed, in nanoseconds\n"
1129 " shutdown_reason [int]: Numeric code from guest OS, explaining "
1130 "reason why it shut itself down.\n" },
1132 { "vcpu_getinfo",
1133 (PyCFunction)pyxc_vcpu_getinfo,
1134 METH_VARARGS | METH_KEYWORDS, "\n"
1135 "Get information regarding a VCPU.\n"
1136 " dom [int]: Domain to retrieve info about.\n"
1137 " vcpu [int, 0]: VCPU to retrieve info about.\n\n"
1138 "Returns: [dict]\n"
1139 " online [int]: Bool - Is this VCPU currently online?\n"
1140 " blocked [int]: Bool - Is this VCPU blocked waiting for an event?\n"
1141 " running [int]: Bool - Is this VCPU currently running on a CPU?\n"
1142 " cpu_time [long]: CPU time consumed, in nanoseconds\n"
1143 " cpumap [int]: Bitmap of CPUs this VCPU can run on\n"
1144 " cpu [int]: CPU that this VCPU is currently bound to\n" },
1146 { "linux_build",
1147 (PyCFunction)pyxc_linux_build,
1148 METH_VARARGS | METH_KEYWORDS, "\n"
1149 "Build a new Linux guest OS.\n"
1150 " dom [int]: Identifier of domain to build into.\n"
1151 " image [str]: Name of kernel image file. May be gzipped.\n"
1152 " ramdisk [str, n/a]: Name of ramdisk file, if any.\n"
1153 " cmdline [str, n/a]: Kernel parameters, if any.\n\n"
1154 " vcpus [int, 1]: Number of Virtual CPUS in domain.\n\n"
1155 "Returns: [int] 0 on success; -1 on error.\n" },
1157 { "hvm_build",
1158 (PyCFunction)pyxc_hvm_build,
1159 METH_VARARGS | METH_KEYWORDS, "\n"
1160 "Build a new HVM guest OS.\n"
1161 " dom [int]: Identifier of domain to build into.\n"
1162 " image [str]: Name of HVM loader image file.\n"
1163 " vcpus [int, 1]: Number of Virtual CPUS in domain.\n\n"
1164 "Returns: [int] 0 on success; -1 on error.\n" },
1166 { "sched_id_get",
1167 (PyCFunction)pyxc_sched_id_get,
1168 METH_NOARGS, "\n"
1169 "Get the current scheduler type in use.\n"
1170 "Returns: [int] sched_id.\n" },
1172 { "sedf_domain_set",
1173 (PyCFunction)pyxc_sedf_domain_set,
1174 METH_KEYWORDS, "\n"
1175 "Set the scheduling parameters for a domain when running with Atropos.\n"
1176 " dom [int]: domain to set\n"
1177 " period [long]: domain's scheduling period\n"
1178 " slice [long]: domain's slice per period\n"
1179 " latency [long]: domain's wakeup latency hint\n"
1180 " extratime [int]: domain aware of extratime?\n"
1181 "Returns: [int] 0 on success; -1 on error.\n" },
1183 { "sedf_domain_get",
1184 (PyCFunction)pyxc_sedf_domain_get,
1185 METH_VARARGS, "\n"
1186 "Get the current scheduling parameters for a domain when running with\n"
1187 "the Atropos scheduler."
1188 " dom [int]: domain to query\n"
1189 "Returns: [dict]\n"
1190 " domain [int]: domain ID\n"
1191 " period [long]: scheduler period\n"
1192 " slice [long]: CPU reservation per period\n"
1193 " latency [long]: domain's wakeup latency hint\n"
1194 " extratime [int]: domain aware of extratime?\n"},
1196 { "sched_credit_domain_set",
1197 (PyCFunction)pyxc_sched_credit_domain_set,
1198 METH_KEYWORDS, "\n"
1199 "Set the scheduling parameters for a domain when running with the\n"
1200 "SMP credit scheduler.\n"
1201 " domid [int]: domain id to set\n"
1202 " weight [short]: domain's scheduling weight\n"
1203 "Returns: [int] 0 on success; -1 on error.\n" },
1205 { "sched_credit_domain_get",
1206 (PyCFunction)pyxc_sched_credit_domain_get,
1207 METH_VARARGS, "\n"
1208 "Get the scheduling parameters for a domain when running with the\n"
1209 "SMP credit scheduler.\n"
1210 " domid [int]: domain id to get\n"
1211 "Returns: [dict]\n"
1212 " weight [short]: domain's scheduling weight\n"},
1214 { "evtchn_alloc_unbound",
1215 (PyCFunction)pyxc_evtchn_alloc_unbound,
1216 METH_VARARGS | METH_KEYWORDS, "\n"
1217 "Allocate an unbound port that will await a remote connection.\n"
1218 " dom [int]: Domain whose port space to allocate from.\n"
1219 " remote_dom [int]: Remote domain to accept connections from.\n\n"
1220 "Returns: [int] Unbound event-channel port.\n" },
1222 { "evtchn_reset",
1223 (PyCFunction)pyxc_evtchn_reset,
1224 METH_VARARGS | METH_KEYWORDS, "\n"
1225 "Reset all connections.\n"
1226 " dom [int]: Domain to reset.\n" },
1228 { "physdev_pci_access_modify",
1229 (PyCFunction)pyxc_physdev_pci_access_modify,
1230 METH_VARARGS | METH_KEYWORDS, "\n"
1231 "Allow a domain access to a PCI device\n"
1232 " dom [int]: Identifier of domain to be allowed access.\n"
1233 " bus [int]: PCI bus\n"
1234 " dev [int]: PCI slot\n"
1235 " func [int]: PCI function\n"
1236 " enable [int]: Non-zero means enable access; else disable access\n\n"
1237 "Returns: [int] 0 on success; -1 on error.\n" },
1239 { "readconsolering",
1240 (PyCFunction)pyxc_readconsolering,
1241 METH_VARARGS | METH_KEYWORDS, "\n"
1242 "Read Xen's console ring.\n"
1243 " clear [int, 0]: Bool - clear the ring after reading from it?\n\n"
1244 "Returns: [str] string is empty on failure.\n" },
1246 { "physinfo",
1247 (PyCFunction)pyxc_physinfo,
1248 METH_NOARGS, "\n"
1249 "Get information about the physical host machine\n"
1250 "Returns [dict]: information about the hardware"
1251 " [None]: on failure.\n" },
1253 { "xeninfo",
1254 (PyCFunction)pyxc_xeninfo,
1255 METH_NOARGS, "\n"
1256 "Get information about the Xen host\n"
1257 "Returns [dict]: information about Xen"
1258 " [None]: on failure.\n" },
1260 { "shadow_control",
1261 (PyCFunction)pyxc_shadow_control,
1262 METH_VARARGS | METH_KEYWORDS, "\n"
1263 "Set parameter for shadow pagetable interface\n"
1264 " dom [int]: Identifier of domain.\n"
1265 " op [int, 0]: operation\n\n"
1266 "Returns: [int] 0 on success; -1 on error.\n" },
1268 { "shadow_mem_control",
1269 (PyCFunction)pyxc_shadow_mem_control,
1270 METH_VARARGS | METH_KEYWORDS, "\n"
1271 "Set or read shadow pagetable memory use\n"
1272 " dom [int]: Identifier of domain.\n"
1273 " mb [int, -1]: MB of shadow memory this domain should have.\n\n"
1274 "Returns: [int] MB of shadow memory in use by this domain.\n" },
1276 { "domain_setmaxmem",
1277 (PyCFunction)pyxc_domain_setmaxmem,
1278 METH_VARARGS, "\n"
1279 "Set a domain's memory limit\n"
1280 " dom [int]: Identifier of domain.\n"
1281 " maxmem_kb [int]: .\n"
1282 "Returns: [int] 0 on success; -1 on error.\n" },
1284 { "domain_set_memmap_limit",
1285 (PyCFunction)pyxc_domain_set_memmap_limit,
1286 METH_VARARGS, "\n"
1287 "Set a domain's physical memory mappping limit\n"
1288 " dom [int]: Identifier of domain.\n"
1289 " map_limitkb [int]: .\n"
1290 "Returns: [int] 0 on success; -1 on error.\n" },
1292 { "domain_memory_increase_reservation",
1293 (PyCFunction)pyxc_domain_memory_increase_reservation,
1294 METH_VARARGS | METH_KEYWORDS, "\n"
1295 "Increase a domain's memory reservation\n"
1296 " dom [int]: Identifier of domain.\n"
1297 " mem_kb [long]: .\n"
1298 "Returns: [int] 0 on success; -1 on error.\n" },
1300 { "domain_ioport_permission",
1301 (PyCFunction)pyxc_domain_ioport_permission,
1302 METH_VARARGS | METH_KEYWORDS, "\n"
1303 "Allow a domain access to a range of IO ports\n"
1304 " dom [int]: Identifier of domain to be allowed access.\n"
1305 " first_port [int]: First IO port\n"
1306 " nr_ports [int]: Number of IO ports\n"
1307 " allow_access [int]: Non-zero means enable access; else disable access\n\n"
1308 "Returns: [int] 0 on success; -1 on error.\n" },
1310 { "domain_irq_permission",
1311 (PyCFunction)pyxc_domain_irq_permission,
1312 METH_VARARGS | METH_KEYWORDS, "\n"
1313 "Allow a domain access to a physical IRQ\n"
1314 " dom [int]: Identifier of domain to be allowed access.\n"
1315 " pirq [int]: The Physical IRQ\n"
1316 " allow_access [int]: Non-zero means enable access; else disable access\n\n"
1317 "Returns: [int] 0 on success; -1 on error.\n" },
1319 { "domain_iomem_permission",
1320 (PyCFunction)pyxc_domain_iomem_permission,
1321 METH_VARARGS | METH_KEYWORDS, "\n"
1322 "Allow a domain access to a range of IO memory pages\n"
1323 " dom [int]: Identifier of domain to be allowed access.\n"
1324 " first_pfn [long]: First page of I/O Memory\n"
1325 " nr_pfns [long]: Number of pages of I/O Memory (>0)\n"
1326 " allow_access [int]: Non-zero means enable access; else disable access\n\n"
1327 "Returns: [int] 0 on success; -1 on error.\n" },
1329 { "pages_to_kib",
1330 (PyCFunction)pyxc_pages_to_kib,
1331 METH_VARARGS, "\n"
1332 "Returns: [int]: The size in KiB of memory spanning the given number "
1333 "of pages.\n" },
1335 { "domain_set_time_offset",
1336 (PyCFunction)pyxc_domain_set_time_offset,
1337 METH_VARARGS, "\n"
1338 "Set a domain's time offset to Dom0's localtime\n"
1339 " dom [int]: Domain whose time offset is being set.\n"
1340 "Returns: [int] 0 on success; -1 on error.\n" },
1342 #ifdef __powerpc__
1343 { "arch_alloc_real_mode_area",
1344 (PyCFunction)pyxc_alloc_real_mode_area,
1345 METH_VARARGS | METH_KEYWORDS, "\n"
1346 "Allocate a domain's real mode area.\n"
1347 " dom [int]: Identifier of domain.\n"
1348 " log [int]: Specifies the area's size.\n"
1349 "Returns: [int] 0 on success; -1 on error.\n" },
1351 { "arch_prose_build",
1352 (PyCFunction)pyxc_prose_build,
1353 METH_VARARGS | METH_KEYWORDS, "\n"
1354 "Build a new Linux guest OS.\n"
1355 " dom [int]: Identifier of domain to build into.\n"
1356 " image [str]: Name of kernel image file. May be gzipped.\n"
1357 " ramdisk [str, n/a]: Name of ramdisk file, if any.\n"
1358 " cmdline [str, n/a]: Kernel parameters, if any.\n\n"
1359 " vcpus [int, 1]: Number of Virtual CPUS in domain.\n\n"
1360 "Returns: [int] 0 on success; -1 on error.\n" },
1361 #endif /* __powerpc */
1363 { NULL, NULL, 0, NULL }
1364 };
1367 static PyObject *PyXc_getattr(PyObject *obj, char *name)
1369 return Py_FindMethod(pyxc_methods, obj, name);
1372 static PyObject *PyXc_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1374 XcObject *self = (XcObject *)type->tp_alloc(type, 0);
1376 if (self == NULL)
1377 return NULL;
1379 self->xc_handle = -1;
1381 return (PyObject *)self;
1384 static int
1385 PyXc_init(XcObject *self, PyObject *args, PyObject *kwds)
1387 if ((self->xc_handle = xc_interface_open()) == -1) {
1388 pyxc_error_to_exception();
1389 return -1;
1392 return 0;
1395 static void PyXc_dealloc(XcObject *self)
1397 if (self->xc_handle != -1) {
1398 xc_interface_close(self->xc_handle);
1399 self->xc_handle = -1;
1402 self->ob_type->tp_free((PyObject *)self);
1405 static PyTypeObject PyXcType = {
1406 PyObject_HEAD_INIT(NULL)
1407 0,
1408 PKG "." CLS,
1409 sizeof(XcObject),
1410 0,
1411 (destructor)PyXc_dealloc, /* tp_dealloc */
1412 NULL, /* tp_print */
1413 PyXc_getattr, /* tp_getattr */
1414 NULL, /* tp_setattr */
1415 NULL, /* tp_compare */
1416 NULL, /* tp_repr */
1417 NULL, /* tp_as_number */
1418 NULL, /* tp_as_sequence */
1419 NULL, /* tp_as_mapping */
1420 NULL, /* tp_hash */
1421 NULL, /* tp_call */
1422 NULL, /* tp_str */
1423 NULL, /* tp_getattro */
1424 NULL, /* tp_setattro */
1425 NULL, /* tp_as_buffer */
1426 Py_TPFLAGS_DEFAULT, /* tp_flags */
1427 "Xen client connections", /* tp_doc */
1428 NULL, /* tp_traverse */
1429 NULL, /* tp_clear */
1430 NULL, /* tp_richcompare */
1431 0, /* tp_weaklistoffset */
1432 NULL, /* tp_iter */
1433 NULL, /* tp_iternext */
1434 pyxc_methods, /* tp_methods */
1435 NULL, /* tp_members */
1436 NULL, /* tp_getset */
1437 NULL, /* tp_base */
1438 NULL, /* tp_dict */
1439 NULL, /* tp_descr_get */
1440 NULL, /* tp_descr_set */
1441 0, /* tp_dictoffset */
1442 (initproc)PyXc_init, /* tp_init */
1443 NULL, /* tp_alloc */
1444 PyXc_new, /* tp_new */
1445 };
1447 static PyMethodDef xc_methods[] = { { NULL } };
1449 PyMODINIT_FUNC initxc(void)
1451 PyObject *m;
1453 if (PyType_Ready(&PyXcType) < 0)
1454 return;
1456 m = Py_InitModule(PKG, xc_methods);
1458 if (m == NULL)
1459 return;
1461 xc_error_obj = PyErr_NewException(PKG ".Error", PyExc_RuntimeError, NULL);
1462 zero = PyInt_FromLong(0);
1464 /* KAF: This ensures that we get debug output in a timely manner. */
1465 setbuf(stdout, NULL);
1466 setbuf(stderr, NULL);
1468 Py_INCREF(&PyXcType);
1469 PyModule_AddObject(m, CLS, (PyObject *)&PyXcType);
1471 Py_INCREF(xc_error_obj);
1472 PyModule_AddObject(m, "Error", xc_error_obj);
1474 /* Expose some libxc constants to Python */
1475 PyModule_AddIntConstant(m, "XEN_SCHEDULER_SEDF", XEN_SCHEDULER_SEDF);
1476 PyModule_AddIntConstant(m, "XEN_SCHEDULER_CREDIT", XEN_SCHEDULER_CREDIT);
1481 /*
1482 * Local variables:
1483 * c-indent-level: 4
1484 * c-basic-offset: 4
1485 * End:
1486 */