debuggers.hg

view tools/python/xen/lowlevel/xc/xc.c @ 20871:49a2c1069e14

xend: Properly interpret vcpu_avail Long Integer in xc.hvm_build().

Signed-off-by: Keir Fraser <keir.fraser@citrix.com>
author Keir Fraser <keir.fraser@citrix.com>
date Wed Jan 20 09:33:59 2010 +0000 (2010-01-20)
parents b600a7e8acfe
children b0b41e735575
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/elfnote.h>
22 #include <xen/tmem.h>
23 #include "xc_dom.h"
24 #include <xen/hvm/hvm_info_table.h>
25 #include <xen/hvm/params.h>
27 #define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
29 /* Needed for Python versions earlier than 2.3. */
30 #ifndef PyMODINIT_FUNC
31 #define PyMODINIT_FUNC DL_EXPORT(void)
32 #endif
34 #define PKG "xen.lowlevel.xc"
35 #define CLS "xc"
37 static PyObject *xc_error_obj, *zero;
39 typedef struct {
40 PyObject_HEAD;
41 int xc_handle;
42 } XcObject;
45 static PyObject *dom_op(XcObject *self, PyObject *args,
46 int (*fn)(int, uint32_t));
48 static PyObject *pyxc_error_to_exception(void)
49 {
50 PyObject *pyerr;
51 const xc_error *err = xc_get_last_error();
52 const char *desc = xc_error_code_to_desc(err->code);
54 if ( err->code == XC_ERROR_NONE )
55 return PyErr_SetFromErrno(xc_error_obj);
57 if ( err->message[0] != '\0' )
58 pyerr = Py_BuildValue("(iss)", err->code, desc, err->message);
59 else
60 pyerr = Py_BuildValue("(is)", err->code, desc);
62 xc_clear_last_error();
64 if ( pyerr != NULL )
65 {
66 PyErr_SetObject(xc_error_obj, pyerr);
67 Py_DECREF(pyerr);
68 }
70 return NULL;
71 }
73 static PyObject *pyxc_domain_dumpcore(XcObject *self, PyObject *args)
74 {
75 uint32_t dom;
76 char *corefile;
78 if ( !PyArg_ParseTuple(args, "is", &dom, &corefile) )
79 return NULL;
81 if ( (corefile == NULL) || (corefile[0] == '\0') )
82 return NULL;
84 if ( xc_domain_dumpcore(self->xc_handle, dom, corefile) != 0 )
85 return pyxc_error_to_exception();
87 Py_INCREF(zero);
88 return zero;
89 }
91 static PyObject *pyxc_handle(XcObject *self)
92 {
93 return PyInt_FromLong(self->xc_handle);
94 }
96 static PyObject *pyxc_domain_create(XcObject *self,
97 PyObject *args,
98 PyObject *kwds)
99 {
100 uint32_t dom = 0, ssidref = 0, flags = 0, target = 0;
101 int ret, i;
102 PyObject *pyhandle = NULL;
103 xen_domain_handle_t handle = {
104 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef,
105 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef };
107 static char *kwd_list[] = { "domid", "ssidref", "handle", "flags", "target", NULL };
109 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|iiOii", kwd_list,
110 &dom, &ssidref, &pyhandle, &flags, &target))
111 return NULL;
112 if ( pyhandle != NULL )
113 {
114 if ( !PyList_Check(pyhandle) ||
115 (PyList_Size(pyhandle) != sizeof(xen_domain_handle_t)) )
116 goto out_exception;
118 for ( i = 0; i < sizeof(xen_domain_handle_t); i++ )
119 {
120 PyObject *p = PyList_GetItem(pyhandle, i);
121 if ( !PyInt_Check(p) )
122 goto out_exception;
123 handle[i] = (uint8_t)PyInt_AsLong(p);
124 }
125 }
127 if ( (ret = xc_domain_create(self->xc_handle, ssidref,
128 handle, flags, &dom)) < 0 )
129 return pyxc_error_to_exception();
131 if ( target )
132 if ( (ret = xc_domain_set_target(self->xc_handle, dom, target)) < 0 )
133 return pyxc_error_to_exception();
136 return PyInt_FromLong(dom);
138 out_exception:
139 errno = EINVAL;
140 PyErr_SetFromErrno(xc_error_obj);
141 return NULL;
142 }
144 static PyObject *pyxc_domain_max_vcpus(XcObject *self, PyObject *args)
145 {
146 uint32_t dom, max;
148 if (!PyArg_ParseTuple(args, "ii", &dom, &max))
149 return NULL;
151 if (xc_domain_max_vcpus(self->xc_handle, dom, max) != 0)
152 return pyxc_error_to_exception();
154 Py_INCREF(zero);
155 return zero;
156 }
158 static PyObject *pyxc_domain_pause(XcObject *self, PyObject *args)
159 {
160 return dom_op(self, args, xc_domain_pause);
161 }
163 static PyObject *pyxc_domain_unpause(XcObject *self, PyObject *args)
164 {
165 return dom_op(self, args, xc_domain_unpause);
166 }
168 static PyObject *pyxc_domain_destroy_hook(XcObject *self, PyObject *args)
169 {
170 #ifdef __ia64__
171 dom_op(self, args, xc_ia64_save_to_nvram);
172 #endif
174 Py_INCREF(zero);
175 return zero;
176 }
178 static PyObject *pyxc_domain_destroy(XcObject *self, PyObject *args)
179 {
180 return dom_op(self, args, xc_domain_destroy);
181 }
183 static PyObject *pyxc_domain_shutdown(XcObject *self, PyObject *args)
184 {
185 uint32_t dom, reason;
187 if ( !PyArg_ParseTuple(args, "ii", &dom, &reason) )
188 return NULL;
190 if ( xc_domain_shutdown(self->xc_handle, dom, reason) != 0 )
191 return pyxc_error_to_exception();
193 Py_INCREF(zero);
194 return zero;
195 }
197 static PyObject *pyxc_domain_resume(XcObject *self, PyObject *args)
198 {
199 uint32_t dom;
200 int fast;
202 if ( !PyArg_ParseTuple(args, "ii", &dom, &fast) )
203 return NULL;
205 if ( xc_domain_resume(self->xc_handle, dom, fast) != 0 )
206 return pyxc_error_to_exception();
208 Py_INCREF(zero);
209 return zero;
210 }
212 static PyObject *pyxc_vcpu_setaffinity(XcObject *self,
213 PyObject *args,
214 PyObject *kwds)
215 {
216 uint32_t dom;
217 int vcpu = 0, i;
218 uint64_t cpumap = ~0ULL;
219 PyObject *cpulist = NULL;
221 static char *kwd_list[] = { "domid", "vcpu", "cpumap", NULL };
223 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|iO", kwd_list,
224 &dom, &vcpu, &cpulist) )
225 return NULL;
227 if ( (cpulist != NULL) && PyList_Check(cpulist) )
228 {
229 cpumap = 0ULL;
230 for ( i = 0; i < PyList_Size(cpulist); i++ )
231 {
232 long cpu = PyInt_AsLong(PyList_GetItem(cpulist, i));
233 if ( cpu >= 64 )
234 {
235 errno = EINVAL;
236 PyErr_SetFromErrno(xc_error_obj);
237 return NULL;
238 }
239 cpumap |= (uint64_t)1 << cpu;
240 }
241 }
243 if ( xc_vcpu_setaffinity(self->xc_handle, dom, vcpu, cpumap) != 0 )
244 return pyxc_error_to_exception();
246 Py_INCREF(zero);
247 return zero;
248 }
250 static PyObject *pyxc_domain_sethandle(XcObject *self, PyObject *args)
251 {
252 int i;
253 uint32_t dom;
254 PyObject *pyhandle;
255 xen_domain_handle_t handle;
257 if (!PyArg_ParseTuple(args, "iO", &dom, &pyhandle))
258 return NULL;
260 if ( !PyList_Check(pyhandle) ||
261 (PyList_Size(pyhandle) != sizeof(xen_domain_handle_t)) )
262 {
263 goto out_exception;
264 }
266 for ( i = 0; i < sizeof(xen_domain_handle_t); i++ )
267 {
268 PyObject *p = PyList_GetItem(pyhandle, i);
269 if ( !PyInt_Check(p) )
270 goto out_exception;
271 handle[i] = (uint8_t)PyInt_AsLong(p);
272 }
274 if (xc_domain_sethandle(self->xc_handle, dom, handle) < 0)
275 return pyxc_error_to_exception();
277 Py_INCREF(zero);
278 return zero;
280 out_exception:
281 PyErr_SetFromErrno(xc_error_obj);
282 return NULL;
283 }
286 static PyObject *pyxc_domain_getinfo(XcObject *self,
287 PyObject *args,
288 PyObject *kwds)
289 {
290 PyObject *list, *info_dict, *pyhandle;
292 uint32_t first_dom = 0;
293 int max_doms = 1024, nr_doms, i, j;
294 xc_dominfo_t *info;
296 static char *kwd_list[] = { "first_dom", "max_doms", NULL };
298 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|ii", kwd_list,
299 &first_dom, &max_doms) )
300 return NULL;
302 info = calloc(max_doms, sizeof(xc_dominfo_t));
303 if (info == NULL)
304 return PyErr_NoMemory();
306 nr_doms = xc_domain_getinfo(self->xc_handle, first_dom, max_doms, info);
308 if (nr_doms < 0)
309 {
310 free(info);
311 return pyxc_error_to_exception();
312 }
314 list = PyList_New(nr_doms);
315 for ( i = 0 ; i < nr_doms; i++ )
316 {
317 info_dict = Py_BuildValue(
318 "{s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i,s:i"
319 ",s:L,s:L,s:L,s:i,s:i}",
320 "domid", (int)info[i].domid,
321 "online_vcpus", info[i].nr_online_vcpus,
322 "max_vcpu_id", info[i].max_vcpu_id,
323 "hvm", info[i].hvm,
324 "dying", info[i].dying,
325 "crashed", info[i].crashed,
326 "shutdown", info[i].shutdown,
327 "paused", info[i].paused,
328 "blocked", info[i].blocked,
329 "running", info[i].running,
330 "mem_kb", (long long)info[i].nr_pages*(XC_PAGE_SIZE/1024),
331 "cpu_time", (long long)info[i].cpu_time,
332 "maxmem_kb", (long long)info[i].max_memkb,
333 "ssidref", (int)info[i].ssidref,
334 "shutdown_reason", info[i].shutdown_reason);
335 pyhandle = PyList_New(sizeof(xen_domain_handle_t));
336 if ( (pyhandle == NULL) || (info_dict == NULL) )
337 {
338 Py_DECREF(list);
339 if ( pyhandle != NULL ) { Py_DECREF(pyhandle); }
340 if ( info_dict != NULL ) { Py_DECREF(info_dict); }
341 free(info);
342 return NULL;
343 }
344 for ( j = 0; j < sizeof(xen_domain_handle_t); j++ )
345 PyList_SetItem(pyhandle, j, PyInt_FromLong(info[i].handle[j]));
346 PyDict_SetItemString(info_dict, "handle", pyhandle);
347 Py_DECREF(pyhandle);
348 PyList_SetItem(list, i, info_dict);
349 }
351 free(info);
353 return list;
354 }
356 static PyObject *pyxc_vcpu_getinfo(XcObject *self,
357 PyObject *args,
358 PyObject *kwds)
359 {
360 PyObject *info_dict, *cpulist;
362 uint32_t dom, vcpu = 0;
363 xc_vcpuinfo_t info;
364 int rc, i;
365 uint64_t cpumap;
367 static char *kwd_list[] = { "domid", "vcpu", NULL };
369 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list,
370 &dom, &vcpu) )
371 return NULL;
373 rc = xc_vcpu_getinfo(self->xc_handle, dom, vcpu, &info);
374 if ( rc < 0 )
375 return pyxc_error_to_exception();
376 rc = xc_vcpu_getaffinity(self->xc_handle, dom, vcpu, &cpumap);
377 if ( rc < 0 )
378 return pyxc_error_to_exception();
380 info_dict = Py_BuildValue("{s:i,s:i,s:i,s:L,s:i}",
381 "online", info.online,
382 "blocked", info.blocked,
383 "running", info.running,
384 "cpu_time", info.cpu_time,
385 "cpu", info.cpu);
387 cpulist = PyList_New(0);
388 for ( i = 0; cpumap != 0; i++ )
389 {
390 if ( cpumap & 1 ) {
391 PyObject *pyint = PyInt_FromLong(i);
392 PyList_Append(cpulist, pyint);
393 Py_DECREF(pyint);
394 }
395 cpumap >>= 1;
396 }
397 PyDict_SetItemString(info_dict, "cpumap", cpulist);
398 Py_DECREF(cpulist);
399 return info_dict;
400 }
402 static PyObject *pyxc_getBitSize(XcObject *self,
403 PyObject *args,
404 PyObject *kwds)
405 {
406 PyObject *info_type;
407 char *image = NULL, *cmdline = "", *features = NULL;
408 int type = 0;
409 static char *kwd_list[] = { "image", "cmdline", "features", NULL };
410 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "sss", kwd_list,
411 &image, &cmdline, &features) )
412 return NULL;
413 xc_get_bit_size(image, cmdline, features, &type);
414 if (type < 0)
415 return pyxc_error_to_exception();
416 info_type = Py_BuildValue("{s:i}",
417 "type", type);
418 return info_type;
419 }
421 static PyObject *pyxc_linux_build(XcObject *self,
422 PyObject *args,
423 PyObject *kwds)
424 {
425 uint32_t domid;
426 struct xc_dom_image *dom;
427 char *image, *ramdisk = NULL, *cmdline = "", *features = NULL;
428 int flags = 0;
429 int store_evtchn, console_evtchn;
430 int vhpt = 0;
431 int superpages = 0;
432 unsigned int mem_mb;
433 unsigned long store_mfn = 0;
434 unsigned long console_mfn = 0;
435 PyObject* elfnote_dict;
436 PyObject* elfnote = NULL;
437 PyObject* ret;
438 int i;
440 static char *kwd_list[] = { "domid", "store_evtchn", "memsize",
441 "console_evtchn", "image",
442 /* optional */
443 "ramdisk", "cmdline", "flags",
444 "features", "vhpt", "superpages", NULL };
446 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiis|ssisii", kwd_list,
447 &domid, &store_evtchn, &mem_mb,
448 &console_evtchn, &image,
449 /* optional */
450 &ramdisk, &cmdline, &flags,
451 &features, &vhpt, &superpages) )
452 return NULL;
454 xc_dom_loginit();
455 if (!(dom = xc_dom_allocate(cmdline, features)))
456 return pyxc_error_to_exception();
458 /* for IA64 */
459 dom->vhpt_size_log2 = vhpt;
461 dom->superpages = superpages;
463 if ( xc_dom_linux_build(self->xc_handle, dom, domid, mem_mb, image,
464 ramdisk, flags, store_evtchn, &store_mfn,
465 console_evtchn, &console_mfn) != 0 ) {
466 goto out;
467 }
469 if ( !(elfnote_dict = PyDict_New()) )
470 goto out;
472 for ( i = 0; i < ARRAY_SIZE(dom->parms.elf_notes); i++ )
473 {
474 switch ( dom->parms.elf_notes[i].type )
475 {
476 case XEN_ENT_NONE:
477 continue;
478 case XEN_ENT_LONG:
479 elfnote = Py_BuildValue("k", dom->parms.elf_notes[i].data.num);
480 break;
481 case XEN_ENT_STR:
482 elfnote = Py_BuildValue("s", dom->parms.elf_notes[i].data.str);
483 break;
484 }
485 PyDict_SetItemString(elfnote_dict,
486 dom->parms.elf_notes[i].name,
487 elfnote);
488 Py_DECREF(elfnote);
489 }
491 ret = Py_BuildValue("{s:i,s:i,s:N}",
492 "store_mfn", store_mfn,
493 "console_mfn", console_mfn,
494 "notes", elfnote_dict);
496 if ( dom->arch_hooks->native_protocol )
497 {
498 PyObject *native_protocol =
499 Py_BuildValue("s", dom->arch_hooks->native_protocol);
500 PyDict_SetItemString(ret, "native_protocol", native_protocol);
501 Py_DECREF(native_protocol);
502 }
504 xc_dom_release(dom);
506 return ret;
508 out:
509 xc_dom_release(dom);
510 return pyxc_error_to_exception();
511 }
513 static PyObject *pyxc_get_hvm_param(XcObject *self,
514 PyObject *args,
515 PyObject *kwds)
516 {
517 uint32_t dom;
518 int param;
519 unsigned long value;
521 static char *kwd_list[] = { "domid", "param", NULL };
522 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "ii", kwd_list,
523 &dom, &param) )
524 return NULL;
526 if ( xc_get_hvm_param(self->xc_handle, dom, param, &value) != 0 )
527 return pyxc_error_to_exception();
529 return PyLong_FromUnsignedLong(value);
531 }
533 static PyObject *pyxc_set_hvm_param(XcObject *self,
534 PyObject *args,
535 PyObject *kwds)
536 {
537 uint32_t dom;
538 int param;
539 uint64_t value;
541 static char *kwd_list[] = { "domid", "param", "value", NULL };
542 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiL", kwd_list,
543 &dom, &param, &value) )
544 return NULL;
546 if ( xc_set_hvm_param(self->xc_handle, dom, param, value) != 0 )
547 return pyxc_error_to_exception();
549 Py_INCREF(zero);
550 return zero;
551 }
553 static int token_value(char *token)
554 {
555 token = strchr(token, 'x') + 1;
556 return strtol(token, NULL, 16);
557 }
559 static int next_bdf(char **str, int *seg, int *bus, int *dev, int *func)
560 {
561 char *token;
563 if ( !(*str) || !strchr(*str, ',') )
564 return 0;
566 token = *str;
567 *seg = token_value(token);
568 token = strchr(token, ',') + 1;
569 *bus = token_value(token);
570 token = strchr(token, ',') + 1;
571 *dev = token_value(token);
572 token = strchr(token, ',') + 1;
573 *func = token_value(token);
574 token = strchr(token, ',');
575 *str = token ? token + 1 : NULL;
577 return 1;
578 }
580 static PyObject *pyxc_test_assign_device(XcObject *self,
581 PyObject *args,
582 PyObject *kwds)
583 {
584 uint32_t dom;
585 char *pci_str;
586 int32_t bdf = 0;
587 int seg, bus, dev, func;
589 static char *kwd_list[] = { "domid", "pci", NULL };
590 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "is", kwd_list,
591 &dom, &pci_str) )
592 return NULL;
594 while ( next_bdf(&pci_str, &seg, &bus, &dev, &func) )
595 {
596 bdf |= (bus & 0xff) << 16;
597 bdf |= (dev & 0x1f) << 11;
598 bdf |= (func & 0x7) << 8;
600 if ( xc_test_assign_device(self->xc_handle, dom, bdf) != 0 )
601 {
602 if (errno == ENOSYS)
603 bdf = -1;
604 break;
605 }
606 bdf = 0;
607 }
609 return Py_BuildValue("i", bdf);
610 }
612 static PyObject *pyxc_assign_device(XcObject *self,
613 PyObject *args,
614 PyObject *kwds)
615 {
616 uint32_t dom;
617 char *pci_str;
618 int32_t bdf = 0;
619 int seg, bus, dev, func;
621 static char *kwd_list[] = { "domid", "pci", NULL };
622 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "is", kwd_list,
623 &dom, &pci_str) )
624 return NULL;
626 while ( next_bdf(&pci_str, &seg, &bus, &dev, &func) )
627 {
628 bdf |= (bus & 0xff) << 16;
629 bdf |= (dev & 0x1f) << 11;
630 bdf |= (func & 0x7) << 8;
632 if ( xc_assign_device(self->xc_handle, dom, bdf) != 0 )
633 {
634 if (errno == ENOSYS)
635 bdf = -1;
636 break;
637 }
638 bdf = 0;
639 }
641 return Py_BuildValue("i", bdf);
642 }
644 static PyObject *pyxc_deassign_device(XcObject *self,
645 PyObject *args,
646 PyObject *kwds)
647 {
648 uint32_t dom;
649 char *pci_str;
650 int32_t bdf = 0;
651 int seg, bus, dev, func;
653 static char *kwd_list[] = { "domid", "pci", NULL };
654 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "is", kwd_list,
655 &dom, &pci_str) )
656 return NULL;
658 while ( next_bdf(&pci_str, &seg, &bus, &dev, &func) )
659 {
660 bdf |= (bus & 0xff) << 16;
661 bdf |= (dev & 0x1f) << 11;
662 bdf |= (func & 0x7) << 8;
664 if ( xc_deassign_device(self->xc_handle, dom, bdf) != 0 )
665 {
666 if (errno == ENOSYS)
667 bdf = -1;
668 break;
669 }
670 bdf = 0;
671 }
673 return Py_BuildValue("i", bdf);
674 }
676 static PyObject *pyxc_get_device_group(XcObject *self,
677 PyObject *args)
678 {
679 uint32_t bdf = 0;
680 uint32_t max_sdevs, num_sdevs;
681 int domid, seg, bus, dev, func, rc, i;
682 PyObject *Pystr;
683 char *group_str;
684 char dev_str[9];
685 uint32_t *sdev_array;
687 if ( !PyArg_ParseTuple(args, "iiiii", &domid, &seg, &bus, &dev, &func) )
688 return NULL;
690 /* Maximum allowed siblings device number per group */
691 max_sdevs = 1024;
693 sdev_array = calloc(max_sdevs, sizeof(*sdev_array));
694 if (sdev_array == NULL)
695 return PyErr_NoMemory();
697 bdf |= (bus & 0xff) << 16;
698 bdf |= (dev & 0x1f) << 11;
699 bdf |= (func & 0x7) << 8;
701 rc = xc_get_device_group(self->xc_handle,
702 domid, bdf, max_sdevs, &num_sdevs, sdev_array);
704 if ( rc < 0 )
705 {
706 free(sdev_array);
707 return pyxc_error_to_exception();
708 }
710 if ( !num_sdevs )
711 {
712 free(sdev_array);
713 return Py_BuildValue("s", "");
714 }
716 group_str = calloc(num_sdevs, sizeof(dev_str));
717 if (group_str == NULL)
718 {
719 free(sdev_array);
720 return PyErr_NoMemory();
721 }
723 for ( i = 0; i < num_sdevs; i++ )
724 {
725 bus = (sdev_array[i] >> 16) & 0xff;
726 dev = (sdev_array[i] >> 11) & 0x1f;
727 func = (sdev_array[i] >> 8) & 0x7;
728 snprintf(dev_str, sizeof(dev_str), "%02x:%02x.%x,", bus, dev, func);
729 strcat(group_str, dev_str);
730 }
732 Pystr = Py_BuildValue("s", group_str);
734 free(sdev_array);
735 free(group_str);
737 return Pystr;
738 }
740 #ifdef __ia64__
741 static PyObject *pyxc_nvram_init(XcObject *self,
742 PyObject *args)
743 {
744 char *dom_name;
745 uint32_t dom;
747 if ( !PyArg_ParseTuple(args, "si", &dom_name, &dom) )
748 return NULL;
750 xc_ia64_nvram_init(self->xc_handle, dom_name, dom);
752 Py_INCREF(zero);
753 return zero;
754 }
756 static PyObject *pyxc_set_os_type(XcObject *self,
757 PyObject *args)
758 {
759 char *os_type;
760 uint32_t dom;
762 if ( !PyArg_ParseTuple(args, "si", &os_type, &dom) )
763 return NULL;
765 xc_ia64_set_os_type(self->xc_handle, os_type, dom);
767 Py_INCREF(zero);
768 return zero;
769 }
770 #endif /* __ia64__ */
773 #if defined(__i386__) || defined(__x86_64__)
774 static void pyxc_dom_extract_cpuid(PyObject *config,
775 char **regs)
776 {
777 const char *regs_extract[4] = { "eax", "ebx", "ecx", "edx" };
778 PyObject *obj;
779 int i;
781 memset(regs, 0, 4*sizeof(*regs));
783 if ( !PyDict_Check(config) )
784 return;
786 for ( i = 0; i < 4; i++ )
787 if ( (obj = PyDict_GetItemString(config, regs_extract[i])) != NULL )
788 regs[i] = PyString_AS_STRING(obj);
789 }
791 static PyObject *pyxc_create_cpuid_dict(char **regs)
792 {
793 const char *regs_extract[4] = { "eax", "ebx", "ecx", "edx" };
794 PyObject *dict;
795 int i;
797 dict = PyDict_New();
798 for ( i = 0; i < 4; i++ )
799 {
800 if ( regs[i] == NULL )
801 continue;
802 PyDict_SetItemString(dict, regs_extract[i],
803 PyString_FromString(regs[i]));
804 free(regs[i]);
805 regs[i] = NULL;
806 }
807 return dict;
808 }
810 static PyObject *pyxc_dom_check_cpuid(XcObject *self,
811 PyObject *args)
812 {
813 PyObject *sub_input, *config;
814 unsigned int input[2];
815 char *regs[4], *regs_transform[4];
817 if ( !PyArg_ParseTuple(args, "iOO", &input[0], &sub_input, &config) )
818 return NULL;
820 pyxc_dom_extract_cpuid(config, regs);
822 input[1] = XEN_CPUID_INPUT_UNUSED;
823 if ( PyLong_Check(sub_input) )
824 input[1] = PyLong_AsUnsignedLong(sub_input);
826 if ( xc_cpuid_check(self->xc_handle, input,
827 (const char **)regs, regs_transform) )
828 return pyxc_error_to_exception();
830 return pyxc_create_cpuid_dict(regs_transform);
831 }
833 static PyObject *pyxc_dom_set_policy_cpuid(XcObject *self,
834 PyObject *args)
835 {
836 int domid;
838 if ( !PyArg_ParseTuple(args, "i", &domid) )
839 return NULL;
841 if ( xc_cpuid_apply_policy(self->xc_handle, domid) )
842 return pyxc_error_to_exception();
844 Py_INCREF(zero);
845 return zero;
846 }
849 static PyObject *pyxc_dom_set_cpuid(XcObject *self,
850 PyObject *args)
851 {
852 PyObject *sub_input, *config;
853 unsigned int domid, input[2];
854 char *regs[4], *regs_transform[4];
856 if ( !PyArg_ParseTuple(args, "IIOO", &domid,
857 &input[0], &sub_input, &config) )
858 return NULL;
860 pyxc_dom_extract_cpuid(config, regs);
862 input[1] = XEN_CPUID_INPUT_UNUSED;
863 if ( PyLong_Check(sub_input) )
864 input[1] = PyLong_AsUnsignedLong(sub_input);
866 if ( xc_cpuid_set(self->xc_handle, domid, input, (const char **)regs,
867 regs_transform) )
868 return pyxc_error_to_exception();
870 return pyxc_create_cpuid_dict(regs_transform);
871 }
873 static PyObject *pyxc_dom_set_machine_address_size(XcObject *self,
874 PyObject *args,
875 PyObject *kwds)
876 {
877 uint32_t dom, width;
879 if (!PyArg_ParseTuple(args, "ii", &dom, &width))
880 return NULL;
882 if (xc_domain_set_machine_address_size(self->xc_handle, dom, width) != 0)
883 return pyxc_error_to_exception();
885 Py_INCREF(zero);
886 return zero;
887 }
889 static PyObject *pyxc_dom_suppress_spurious_page_faults(XcObject *self,
890 PyObject *args,
891 PyObject *kwds)
892 {
893 uint32_t dom;
895 if (!PyArg_ParseTuple(args, "i", &dom))
896 return NULL;
898 if (xc_domain_suppress_spurious_page_faults(self->xc_handle, dom) != 0)
899 return pyxc_error_to_exception();
901 Py_INCREF(zero);
902 return zero;
903 }
904 #endif /* __i386__ || __x86_64__ */
906 static PyObject *pyxc_hvm_build(XcObject *self,
907 PyObject *args,
908 PyObject *kwds)
909 {
910 uint32_t dom;
911 #if !defined(__ia64__)
912 struct hvm_info_table *va_hvm;
913 uint8_t *va_map, sum;
914 #endif
915 int i;
916 char *image;
917 int memsize, target=-1, vcpus = 1, acpi = 0, apic = 1;
918 PyObject *vcpu_avail_handle = NULL;
919 uint8_t vcpu_avail[HVM_MAX_VCPUS/8];
921 static char *kwd_list[] = { "domid",
922 "memsize", "image", "target", "vcpus",
923 "vcpu_avail", "acpi", "apic", NULL };
924 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iis|iiOii", kwd_list,
925 &dom, &memsize, &image, &target, &vcpus,
926 &vcpu_avail_handle, &acpi, &apic) )
927 return NULL;
929 memset(vcpu_avail, 0, sizeof(vcpu_avail));
930 vcpu_avail[0] = 1;
931 if ( vcpu_avail_handle != NULL )
932 {
933 if ( PyInt_Check(vcpu_avail_handle) )
934 {
935 unsigned long v = PyInt_AsLong(vcpu_avail_handle);
936 for ( i = 0; i < sizeof(long)/8; i++ )
937 vcpu_avail[i] = (uint8_t)(v>>(i*8));
938 }
939 else if ( PyLong_Check(vcpu_avail_handle) )
940 {
941 if ( _PyLong_AsByteArray((PyLongObject *)vcpu_avail_handle,
942 (unsigned char *)vcpu_avail,
943 sizeof(vcpu_avail), 1, 0) )
944 return NULL;
945 }
946 else
947 {
948 errno = EINVAL;
949 PyErr_SetFromErrno(xc_error_obj);
950 return NULL;
951 }
952 }
954 if ( target == -1 )
955 target = memsize;
957 if ( xc_hvm_build_target_mem(self->xc_handle, dom, memsize,
958 target, image) != 0 )
959 return pyxc_error_to_exception();
961 #if !defined(__ia64__)
962 /* Fix up the HVM info table. */
963 va_map = xc_map_foreign_range(self->xc_handle, dom, XC_PAGE_SIZE,
964 PROT_READ | PROT_WRITE,
965 HVM_INFO_PFN);
966 if ( va_map == NULL )
967 return PyErr_SetFromErrno(xc_error_obj);
968 va_hvm = (struct hvm_info_table *)(va_map + HVM_INFO_OFFSET);
969 va_hvm->acpi_enabled = acpi;
970 va_hvm->apic_mode = apic;
971 va_hvm->nr_vcpus = vcpus;
972 memcpy(va_hvm->vcpu_online, vcpu_avail, sizeof(vcpu_avail));
973 for ( i = 0, sum = 0; i < va_hvm->length; i++ )
974 sum += ((uint8_t *)va_hvm)[i];
975 va_hvm->checksum -= sum;
976 munmap(va_map, XC_PAGE_SIZE);
977 #endif
979 return Py_BuildValue("{}");
980 }
982 static PyObject *pyxc_evtchn_alloc_unbound(XcObject *self,
983 PyObject *args,
984 PyObject *kwds)
985 {
986 uint32_t dom, remote_dom;
987 int port;
989 static char *kwd_list[] = { "domid", "remote_dom", NULL };
991 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "ii", kwd_list,
992 &dom, &remote_dom) )
993 return NULL;
995 if ( (port = xc_evtchn_alloc_unbound(self->xc_handle, dom, remote_dom)) < 0 )
996 return pyxc_error_to_exception();
998 return PyInt_FromLong(port);
999 }
1001 static PyObject *pyxc_evtchn_reset(XcObject *self,
1002 PyObject *args,
1003 PyObject *kwds)
1005 uint32_t dom;
1007 static char *kwd_list[] = { "dom", NULL };
1009 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i", kwd_list, &dom) )
1010 return NULL;
1012 if ( xc_evtchn_reset(self->xc_handle, dom) < 0 )
1013 return pyxc_error_to_exception();
1015 Py_INCREF(zero);
1016 return zero;
1019 static PyObject *pyxc_physdev_map_pirq(PyObject *self,
1020 PyObject *args,
1021 PyObject *kwds)
1023 XcObject *xc = (XcObject *)self;
1024 uint32_t dom;
1025 int index, pirq, ret;
1027 static char *kwd_list[] = {"domid", "index", "pirq", NULL};
1029 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iii", kwd_list,
1030 &dom, &index, &pirq) )
1031 return NULL;
1032 ret = xc_physdev_map_pirq(xc->xc_handle, dom, index, &pirq);
1033 if ( ret != 0 )
1034 return pyxc_error_to_exception();
1035 return PyLong_FromUnsignedLong(pirq);
1038 static PyObject *pyxc_physdev_pci_access_modify(XcObject *self,
1039 PyObject *args,
1040 PyObject *kwds)
1042 uint32_t dom;
1043 int bus, dev, func, enable, ret;
1045 static char *kwd_list[] = { "domid", "bus", "dev", "func", "enable", NULL };
1047 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiii", kwd_list,
1048 &dom, &bus, &dev, &func, &enable) )
1049 return NULL;
1051 ret = xc_physdev_pci_access_modify(
1052 self->xc_handle, dom, bus, dev, func, enable);
1053 if ( ret != 0 )
1054 return pyxc_error_to_exception();
1056 Py_INCREF(zero);
1057 return zero;
1060 static PyObject *pyxc_readconsolering(XcObject *self,
1061 PyObject *args,
1062 PyObject *kwds)
1064 unsigned int clear = 0, index = 0, incremental = 0;
1065 char _str[32768], *str = _str;
1066 unsigned int count = 32768;
1067 int ret;
1069 static char *kwd_list[] = { "clear", "index", "incremental", NULL };
1071 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "|iii", kwd_list,
1072 &clear, &index, &incremental) )
1073 return NULL;
1075 ret = xc_readconsolering(self->xc_handle, &str, &count, clear,
1076 incremental, &index);
1077 if ( ret < 0 )
1078 return pyxc_error_to_exception();
1080 return PyString_FromStringAndSize(str, count);
1084 static unsigned long pages_to_kib(unsigned long pages)
1086 return pages * (XC_PAGE_SIZE / 1024);
1090 static PyObject *pyxc_pages_to_kib(XcObject *self, PyObject *args)
1092 unsigned long pages;
1094 if (!PyArg_ParseTuple(args, "l", &pages))
1095 return NULL;
1097 return PyLong_FromUnsignedLong(pages_to_kib(pages));
1101 static PyObject *pyxc_physinfo(XcObject *self)
1103 #define MAX_CPU_ID 255
1104 xc_physinfo_t info;
1105 char cpu_cap[128], virt_caps[128], *p;
1106 int i, j, max_cpu_id, nr_nodes = 0;
1107 uint64_t free_heap;
1108 PyObject *ret_obj, *node_to_cpu_obj, *node_to_memory_obj;
1109 PyObject *node_to_dma32_mem_obj;
1110 xc_cpu_to_node_t map[MAX_CPU_ID + 1];
1111 const char *virtcap_names[] = { "hvm", "hvm_directio" };
1113 set_xen_guest_handle(info.cpu_to_node, map);
1114 info.max_cpu_id = MAX_CPU_ID;
1116 if ( xc_physinfo(self->xc_handle, &info) != 0 )
1117 return pyxc_error_to_exception();
1119 p = cpu_cap;
1120 *p = '\0';
1121 for ( i = 0; i < sizeof(info.hw_cap)/4; i++ )
1122 p += sprintf(p, "%08x:", info.hw_cap[i]);
1123 *(p-1) = 0;
1125 p = virt_caps;
1126 *p = '\0';
1127 for ( i = 0; i < 2; i++ )
1128 if ( (info.capabilities >> i) & 1 )
1129 p += sprintf(p, "%s ", virtcap_names[i]);
1130 if ( p != virt_caps )
1131 *(p-1) = '\0';
1133 max_cpu_id = info.max_cpu_id;
1134 if ( max_cpu_id > MAX_CPU_ID )
1135 max_cpu_id = MAX_CPU_ID;
1137 /* Construct node-to-* lists. */
1138 node_to_cpu_obj = PyList_New(0);
1139 node_to_memory_obj = PyList_New(0);
1140 node_to_dma32_mem_obj = PyList_New(0);
1141 for ( i = 0; i <= info.max_node_id; i++ )
1143 int node_exists = 0;
1144 PyObject *pyint;
1146 /* CPUs. */
1147 PyObject *cpus = PyList_New(0);
1148 for ( j = 0; j <= max_cpu_id; j++ )
1150 if ( i != map[j] )
1151 continue;
1152 pyint = PyInt_FromLong(j);
1153 PyList_Append(cpus, pyint);
1154 Py_DECREF(pyint);
1155 node_exists = 1;
1157 PyList_Append(node_to_cpu_obj, cpus);
1158 Py_DECREF(cpus);
1160 /* Memory. */
1161 xc_availheap(self->xc_handle, 0, 0, i, &free_heap);
1162 node_exists = node_exists || (free_heap != 0);
1163 pyint = PyInt_FromLong(free_heap / 1024);
1164 PyList_Append(node_to_memory_obj, pyint);
1165 Py_DECREF(pyint);
1167 /* DMA memory. */
1168 xc_availheap(self->xc_handle, 0, 32, i, &free_heap);
1169 pyint = PyInt_FromLong(free_heap / 1024);
1170 PyList_Append(node_to_dma32_mem_obj, pyint);
1171 Py_DECREF(pyint);
1173 if ( node_exists )
1174 nr_nodes++;
1177 ret_obj = Py_BuildValue("{s:i,s:i,s:i,s:i,s:i,s:i,s:l,s:l,s:l,s:i,s:s:s:s}",
1178 "nr_nodes", nr_nodes,
1179 "max_node_id", info.max_node_id,
1180 "max_cpu_id", info.max_cpu_id,
1181 "threads_per_core", info.threads_per_core,
1182 "cores_per_socket", info.cores_per_socket,
1183 "nr_cpus", info.nr_cpus,
1184 "total_memory", pages_to_kib(info.total_pages),
1185 "free_memory", pages_to_kib(info.free_pages),
1186 "scrub_memory", pages_to_kib(info.scrub_pages),
1187 "cpu_khz", info.cpu_khz,
1188 "hw_caps", cpu_cap,
1189 "virt_caps", virt_caps);
1190 PyDict_SetItemString(ret_obj, "node_to_cpu", node_to_cpu_obj);
1191 Py_DECREF(node_to_cpu_obj);
1192 PyDict_SetItemString(ret_obj, "node_to_memory", node_to_memory_obj);
1193 Py_DECREF(node_to_memory_obj);
1194 PyDict_SetItemString(ret_obj, "node_to_dma32_mem", node_to_dma32_mem_obj);
1195 Py_DECREF(node_to_dma32_mem_obj);
1197 return ret_obj;
1198 #undef MAX_CPU_ID
1201 static PyObject *pyxc_xeninfo(XcObject *self)
1203 xen_extraversion_t xen_extra;
1204 xen_compile_info_t xen_cc;
1205 xen_changeset_info_t xen_chgset;
1206 xen_capabilities_info_t xen_caps;
1207 xen_platform_parameters_t p_parms;
1208 xen_commandline_t xen_commandline;
1209 long xen_version;
1210 long xen_pagesize;
1211 char str[128];
1213 xen_version = xc_version(self->xc_handle, XENVER_version, NULL);
1215 if ( xc_version(self->xc_handle, XENVER_extraversion, &xen_extra) != 0 )
1216 return pyxc_error_to_exception();
1218 if ( xc_version(self->xc_handle, XENVER_compile_info, &xen_cc) != 0 )
1219 return pyxc_error_to_exception();
1221 if ( xc_version(self->xc_handle, XENVER_changeset, &xen_chgset) != 0 )
1222 return pyxc_error_to_exception();
1224 if ( xc_version(self->xc_handle, XENVER_capabilities, &xen_caps) != 0 )
1225 return pyxc_error_to_exception();
1227 if ( xc_version(self->xc_handle, XENVER_platform_parameters, &p_parms) != 0 )
1228 return pyxc_error_to_exception();
1230 if ( xc_version(self->xc_handle, XENVER_commandline, &xen_commandline) != 0 )
1231 return pyxc_error_to_exception();
1233 snprintf(str, sizeof(str), "virt_start=0x%lx", p_parms.virt_start);
1235 xen_pagesize = xc_version(self->xc_handle, XENVER_pagesize, NULL);
1236 if (xen_pagesize < 0 )
1237 return pyxc_error_to_exception();
1239 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,s:s}",
1240 "xen_major", xen_version >> 16,
1241 "xen_minor", (xen_version & 0xffff),
1242 "xen_extra", xen_extra,
1243 "xen_caps", xen_caps,
1244 "xen_pagesize", xen_pagesize,
1245 "platform_params", str,
1246 "xen_changeset", xen_chgset,
1247 "xen_commandline", xen_commandline,
1248 "cc_compiler", xen_cc.compiler,
1249 "cc_compile_by", xen_cc.compile_by,
1250 "cc_compile_domain", xen_cc.compile_domain,
1251 "cc_compile_date", xen_cc.compile_date);
1255 static PyObject *pyxc_sedf_domain_set(XcObject *self,
1256 PyObject *args,
1257 PyObject *kwds)
1259 uint32_t domid;
1260 uint64_t period, slice, latency;
1261 uint16_t extratime, weight;
1262 static char *kwd_list[] = { "domid", "period", "slice",
1263 "latency", "extratime", "weight",NULL };
1265 if( !PyArg_ParseTupleAndKeywords(args, kwds, "iLLLhh", kwd_list,
1266 &domid, &period, &slice,
1267 &latency, &extratime, &weight) )
1268 return NULL;
1269 if ( xc_sedf_domain_set(self->xc_handle, domid, period,
1270 slice, latency, extratime,weight) != 0 )
1271 return pyxc_error_to_exception();
1273 Py_INCREF(zero);
1274 return zero;
1277 static PyObject *pyxc_sedf_domain_get(XcObject *self, PyObject *args)
1279 uint32_t domid;
1280 uint64_t period, slice,latency;
1281 uint16_t weight, extratime;
1283 if(!PyArg_ParseTuple(args, "i", &domid))
1284 return NULL;
1286 if (xc_sedf_domain_get(self->xc_handle, domid, &period,
1287 &slice,&latency,&extratime,&weight))
1288 return pyxc_error_to_exception();
1290 return Py_BuildValue("{s:i,s:L,s:L,s:L,s:i,s:i}",
1291 "domid", domid,
1292 "period", period,
1293 "slice", slice,
1294 "latency", latency,
1295 "extratime", extratime,
1296 "weight", weight);
1299 static PyObject *pyxc_shadow_control(PyObject *self,
1300 PyObject *args,
1301 PyObject *kwds)
1303 XcObject *xc = (XcObject *)self;
1305 uint32_t dom;
1306 int op=0;
1308 static char *kwd_list[] = { "dom", "op", NULL };
1310 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list,
1311 &dom, &op) )
1312 return NULL;
1314 if ( xc_shadow_control(xc->xc_handle, dom, op, NULL, 0, NULL, 0, NULL)
1315 < 0 )
1316 return pyxc_error_to_exception();
1318 Py_INCREF(zero);
1319 return zero;
1322 static PyObject *pyxc_shadow_mem_control(PyObject *self,
1323 PyObject *args,
1324 PyObject *kwds)
1326 XcObject *xc = (XcObject *)self;
1327 int op;
1328 uint32_t dom;
1329 int mbarg = -1;
1330 unsigned long mb;
1332 static char *kwd_list[] = { "dom", "mb", NULL };
1334 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "i|i", kwd_list,
1335 &dom, &mbarg) )
1336 return NULL;
1338 if ( mbarg < 0 )
1339 op = XEN_DOMCTL_SHADOW_OP_GET_ALLOCATION;
1340 else
1342 mb = mbarg;
1343 op = XEN_DOMCTL_SHADOW_OP_SET_ALLOCATION;
1345 if ( xc_shadow_control(xc->xc_handle, dom, op, NULL, 0, &mb, 0, NULL) < 0 )
1346 return pyxc_error_to_exception();
1348 mbarg = mb;
1349 return Py_BuildValue("i", mbarg);
1352 static PyObject *pyxc_sched_id_get(XcObject *self) {
1354 int sched_id;
1355 if (xc_sched_id(self->xc_handle, &sched_id) != 0)
1356 return PyErr_SetFromErrno(xc_error_obj);
1358 return Py_BuildValue("i", sched_id);
1361 static PyObject *pyxc_sched_credit_domain_set(XcObject *self,
1362 PyObject *args,
1363 PyObject *kwds)
1365 uint32_t domid;
1366 uint16_t weight;
1367 uint16_t cap;
1368 static char *kwd_list[] = { "domid", "weight", "cap", NULL };
1369 static char kwd_type[] = "I|HH";
1370 struct xen_domctl_sched_credit sdom;
1372 weight = 0;
1373 cap = (uint16_t)~0U;
1374 if( !PyArg_ParseTupleAndKeywords(args, kwds, kwd_type, kwd_list,
1375 &domid, &weight, &cap) )
1376 return NULL;
1378 sdom.weight = weight;
1379 sdom.cap = cap;
1381 if ( xc_sched_credit_domain_set(self->xc_handle, domid, &sdom) != 0 )
1382 return pyxc_error_to_exception();
1384 Py_INCREF(zero);
1385 return zero;
1388 static PyObject *pyxc_sched_credit_domain_get(XcObject *self, PyObject *args)
1390 uint32_t domid;
1391 struct xen_domctl_sched_credit sdom;
1393 if( !PyArg_ParseTuple(args, "I", &domid) )
1394 return NULL;
1396 if ( xc_sched_credit_domain_get(self->xc_handle, domid, &sdom) != 0 )
1397 return pyxc_error_to_exception();
1399 return Py_BuildValue("{s:H,s:H}",
1400 "weight", sdom.weight,
1401 "cap", sdom.cap);
1404 static PyObject *pyxc_domain_setmaxmem(XcObject *self, PyObject *args)
1406 uint32_t dom;
1407 unsigned int maxmem_kb;
1409 if (!PyArg_ParseTuple(args, "ii", &dom, &maxmem_kb))
1410 return NULL;
1412 if (xc_domain_setmaxmem(self->xc_handle, dom, maxmem_kb) != 0)
1413 return pyxc_error_to_exception();
1415 Py_INCREF(zero);
1416 return zero;
1419 static PyObject *pyxc_domain_set_target_mem(XcObject *self, PyObject *args)
1421 uint32_t dom;
1422 unsigned int mem_kb, mem_pages;
1424 if (!PyArg_ParseTuple(args, "ii", &dom, &mem_kb))
1425 return NULL;
1427 mem_pages = mem_kb / 4;
1429 if (xc_domain_memory_set_pod_target(self->xc_handle, dom, mem_pages,
1430 NULL, NULL, NULL) != 0)
1431 return pyxc_error_to_exception();
1433 Py_INCREF(zero);
1434 return zero;
1437 static PyObject *pyxc_domain_set_memmap_limit(XcObject *self, PyObject *args)
1439 uint32_t dom;
1440 unsigned int maplimit_kb;
1442 if ( !PyArg_ParseTuple(args, "ii", &dom, &maplimit_kb) )
1443 return NULL;
1445 if ( xc_domain_set_memmap_limit(self->xc_handle, dom, maplimit_kb) != 0 )
1446 return pyxc_error_to_exception();
1448 Py_INCREF(zero);
1449 return zero;
1452 static PyObject *pyxc_domain_ioport_permission(XcObject *self,
1453 PyObject *args,
1454 PyObject *kwds)
1456 uint32_t dom;
1457 int first_port, nr_ports, allow_access, ret;
1459 static char *kwd_list[] = { "domid", "first_port", "nr_ports", "allow_access", NULL };
1461 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiii", kwd_list,
1462 &dom, &first_port, &nr_ports, &allow_access) )
1463 return NULL;
1465 ret = xc_domain_ioport_permission(
1466 self->xc_handle, dom, first_port, nr_ports, allow_access);
1467 if ( ret != 0 )
1468 return pyxc_error_to_exception();
1470 Py_INCREF(zero);
1471 return zero;
1474 static PyObject *pyxc_domain_irq_permission(PyObject *self,
1475 PyObject *args,
1476 PyObject *kwds)
1478 XcObject *xc = (XcObject *)self;
1479 uint32_t dom;
1480 int pirq, allow_access, ret;
1482 static char *kwd_list[] = { "domid", "pirq", "allow_access", NULL };
1484 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iii", kwd_list,
1485 &dom, &pirq, &allow_access) )
1486 return NULL;
1488 ret = xc_domain_irq_permission(
1489 xc->xc_handle, dom, pirq, allow_access);
1490 if ( ret != 0 )
1491 return pyxc_error_to_exception();
1493 Py_INCREF(zero);
1494 return zero;
1497 static PyObject *pyxc_domain_iomem_permission(PyObject *self,
1498 PyObject *args,
1499 PyObject *kwds)
1501 XcObject *xc = (XcObject *)self;
1502 uint32_t dom;
1503 unsigned long first_pfn, nr_pfns, allow_access, ret;
1505 static char *kwd_list[] = { "domid", "first_pfn", "nr_pfns", "allow_access", NULL };
1507 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "illi", kwd_list,
1508 &dom, &first_pfn, &nr_pfns, &allow_access) )
1509 return NULL;
1511 ret = xc_domain_iomem_permission(
1512 xc->xc_handle, dom, first_pfn, nr_pfns, allow_access);
1513 if ( ret != 0 )
1514 return pyxc_error_to_exception();
1516 Py_INCREF(zero);
1517 return zero;
1520 static PyObject *pyxc_domain_set_time_offset(XcObject *self, PyObject *args)
1522 uint32_t dom;
1523 int32_t offset;
1525 if (!PyArg_ParseTuple(args, "ii", &dom, &offset))
1526 return NULL;
1528 if (xc_domain_set_time_offset(self->xc_handle, dom, offset) != 0)
1529 return pyxc_error_to_exception();
1531 Py_INCREF(zero);
1532 return zero;
1535 static PyObject *pyxc_domain_set_tsc_info(XcObject *self, PyObject *args)
1537 uint32_t dom, tsc_mode;
1539 if (!PyArg_ParseTuple(args, "ii", &dom, &tsc_mode))
1540 return NULL;
1542 if (xc_domain_set_tsc_info(self->xc_handle, dom, tsc_mode, 0, 0, 0) != 0)
1543 return pyxc_error_to_exception();
1545 Py_INCREF(zero);
1546 return zero;
1549 static PyObject *pyxc_domain_disable_migrate(XcObject *self, PyObject *args)
1551 uint32_t dom;
1553 if (!PyArg_ParseTuple(args, "i", &dom))
1554 return NULL;
1556 if (xc_domain_disable_migrate(self->xc_handle, dom) != 0)
1557 return pyxc_error_to_exception();
1559 Py_INCREF(zero);
1560 return zero;
1563 static PyObject *pyxc_domain_send_trigger(XcObject *self,
1564 PyObject *args,
1565 PyObject *kwds)
1567 uint32_t dom;
1568 int trigger, vcpu = 0;
1570 static char *kwd_list[] = { "domid", "trigger", "vcpu", NULL };
1572 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "ii|i", kwd_list,
1573 &dom, &trigger, &vcpu) )
1574 return NULL;
1576 if (xc_domain_send_trigger(self->xc_handle, dom, trigger, vcpu) != 0)
1577 return pyxc_error_to_exception();
1579 Py_INCREF(zero);
1580 return zero;
1583 static PyObject *pyxc_send_debug_keys(XcObject *self,
1584 PyObject *args,
1585 PyObject *kwds)
1587 char *keys;
1589 static char *kwd_list[] = { "keys", NULL };
1591 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "s", kwd_list, &keys) )
1592 return NULL;
1594 if ( xc_send_debug_keys(self->xc_handle, keys) != 0 )
1595 return pyxc_error_to_exception();
1597 Py_INCREF(zero);
1598 return zero;
1601 static PyObject *dom_op(XcObject *self, PyObject *args,
1602 int (*fn)(int, uint32_t))
1604 uint32_t dom;
1606 if (!PyArg_ParseTuple(args, "i", &dom))
1607 return NULL;
1609 if (fn(self->xc_handle, dom) != 0)
1610 return pyxc_error_to_exception();
1612 Py_INCREF(zero);
1613 return zero;
1616 static PyObject *pyxc_tmem_control(XcObject *self,
1617 PyObject *args,
1618 PyObject *kwds)
1620 int32_t pool_id;
1621 uint32_t subop;
1622 uint32_t cli_id;
1623 uint32_t arg1;
1624 uint32_t arg2;
1625 uint64_t arg3;
1626 char *buf;
1627 char _buffer[32768], *buffer = _buffer;
1628 int rc;
1630 static char *kwd_list[] = { "pool_id", "subop", "cli_id", "arg1", "arg2", "arg3", "buf", NULL };
1632 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "iiiiiis", kwd_list,
1633 &pool_id, &subop, &cli_id, &arg1, &arg2, &arg3, &buf) )
1634 return NULL;
1636 if ( (subop == TMEMC_LIST) && (arg1 > 32768) )
1637 arg1 = 32768;
1639 if ( (rc = xc_tmem_control(self->xc_handle, pool_id, subop, cli_id, arg1, arg2, arg3, buffer)) < 0 )
1640 return Py_BuildValue("i", rc);
1642 switch (subop) {
1643 case TMEMC_LIST:
1644 return Py_BuildValue("s", buffer);
1645 case TMEMC_FLUSH:
1646 return Py_BuildValue("i", rc);
1647 case TMEMC_QUERY_FREEABLE_MB:
1648 return Py_BuildValue("i", rc);
1649 case TMEMC_THAW:
1650 case TMEMC_FREEZE:
1651 case TMEMC_DESTROY:
1652 case TMEMC_SET_WEIGHT:
1653 case TMEMC_SET_CAP:
1654 case TMEMC_SET_COMPRESS:
1655 default:
1656 break;
1659 Py_INCREF(zero);
1660 return zero;
1663 static PyObject *pyxc_tmem_shared_auth(XcObject *self,
1664 PyObject *args,
1665 PyObject *kwds)
1667 uint32_t cli_id;
1668 uint32_t arg1;
1669 char *uuid_str;
1670 int rc;
1672 static char *kwd_list[] = { "cli_id", "uuid_str", "arg1", NULL };
1674 if ( !PyArg_ParseTupleAndKeywords(args, kwds, "isi", kwd_list,
1675 &cli_id, &uuid_str, &arg1) )
1676 return NULL;
1678 if ( (rc = xc_tmem_auth(self->xc_handle, cli_id, uuid_str, arg1)) < 0 )
1679 return Py_BuildValue("i", rc);
1681 Py_INCREF(zero);
1682 return zero;
1685 static PyObject *pyxc_dom_set_memshr(XcObject *self, PyObject *args)
1687 uint32_t dom;
1688 int enable;
1690 if (!PyArg_ParseTuple(args, "ii", &dom, &enable))
1691 return NULL;
1693 if (xc_memshr_control(self->xc_handle, dom, enable) != 0)
1694 return pyxc_error_to_exception();
1696 Py_INCREF(zero);
1697 return zero;
1701 static PyMethodDef pyxc_methods[] = {
1702 { "handle",
1703 (PyCFunction)pyxc_handle,
1704 METH_NOARGS, "\n"
1705 "Query the xc control interface file descriptor.\n\n"
1706 "Returns: [int] file descriptor\n" },
1708 { "domain_create",
1709 (PyCFunction)pyxc_domain_create,
1710 METH_VARARGS | METH_KEYWORDS, "\n"
1711 "Create a new domain.\n"
1712 " dom [int, 0]: Domain identifier to use (allocated if zero).\n"
1713 "Returns: [int] new domain identifier; -1 on error.\n" },
1715 { "domain_max_vcpus",
1716 (PyCFunction)pyxc_domain_max_vcpus,
1717 METH_VARARGS, "\n"
1718 "Set the maximum number of VCPUs a domain may create.\n"
1719 " dom [int, 0]: Domain identifier to use.\n"
1720 " max [int, 0]: New maximum number of VCPUs in domain.\n"
1721 "Returns: [int] 0 on success; -1 on error.\n" },
1723 { "domain_dumpcore",
1724 (PyCFunction)pyxc_domain_dumpcore,
1725 METH_VARARGS, "\n"
1726 "Dump core of a domain.\n"
1727 " dom [int]: Identifier of domain to dump core of.\n"
1728 " corefile [string]: Name of corefile to be created.\n\n"
1729 "Returns: [int] 0 on success; -1 on error.\n" },
1731 { "domain_pause",
1732 (PyCFunction)pyxc_domain_pause,
1733 METH_VARARGS, "\n"
1734 "Temporarily pause execution of a domain.\n"
1735 " dom [int]: Identifier of domain to be paused.\n\n"
1736 "Returns: [int] 0 on success; -1 on error.\n" },
1738 { "domain_unpause",
1739 (PyCFunction)pyxc_domain_unpause,
1740 METH_VARARGS, "\n"
1741 "(Re)start execution of a domain.\n"
1742 " dom [int]: Identifier of domain to be unpaused.\n\n"
1743 "Returns: [int] 0 on success; -1 on error.\n" },
1745 { "domain_destroy",
1746 (PyCFunction)pyxc_domain_destroy,
1747 METH_VARARGS, "\n"
1748 "Destroy a domain.\n"
1749 " dom [int]: Identifier of domain to be destroyed.\n\n"
1750 "Returns: [int] 0 on success; -1 on error.\n" },
1752 { "domain_destroy_hook",
1753 (PyCFunction)pyxc_domain_destroy_hook,
1754 METH_VARARGS, "\n"
1755 "Add a hook for arch stuff before destroy a domain.\n"
1756 " dom [int]: Identifier of domain to be destroyed.\n\n"
1757 "Returns: [int] 0 on success; -1 on error.\n" },
1759 { "domain_resume",
1760 (PyCFunction)pyxc_domain_resume,
1761 METH_VARARGS, "\n"
1762 "Resume execution of a suspended domain.\n"
1763 " dom [int]: Identifier of domain to be resumed.\n"
1764 " fast [int]: Use cooperative resume.\n\n"
1765 "Returns: [int] 0 on success; -1 on error.\n" },
1767 { "domain_shutdown",
1768 (PyCFunction)pyxc_domain_shutdown,
1769 METH_VARARGS, "\n"
1770 "Shutdown a domain.\n"
1771 " dom [int, 0]: Domain identifier to use.\n"
1772 " reason [int, 0]: Reason for shutdown.\n"
1773 "Returns: [int] 0 on success; -1 on error.\n" },
1775 { "vcpu_setaffinity",
1776 (PyCFunction)pyxc_vcpu_setaffinity,
1777 METH_VARARGS | METH_KEYWORDS, "\n"
1778 "Pin a VCPU to a specified set CPUs.\n"
1779 " dom [int]: Identifier of domain to which VCPU belongs.\n"
1780 " vcpu [int, 0]: VCPU being pinned.\n"
1781 " cpumap [list, []]: list of usable CPUs.\n\n"
1782 "Returns: [int] 0 on success; -1 on error.\n" },
1784 { "domain_sethandle",
1785 (PyCFunction)pyxc_domain_sethandle,
1786 METH_VARARGS, "\n"
1787 "Set domain's opaque handle.\n"
1788 " dom [int]: Identifier of domain.\n"
1789 " handle [list of 16 ints]: New opaque handle.\n"
1790 "Returns: [int] 0 on success; -1 on error.\n" },
1792 { "domain_getinfo",
1793 (PyCFunction)pyxc_domain_getinfo,
1794 METH_VARARGS | METH_KEYWORDS, "\n"
1795 "Get information regarding a set of domains, in increasing id order.\n"
1796 " first_dom [int, 0]: First domain to retrieve info about.\n"
1797 " max_doms [int, 1024]: Maximum number of domains to retrieve info"
1798 " about.\n\n"
1799 "Returns: [list of dicts] if list length is less than 'max_doms'\n"
1800 " parameter then there was an error, or the end of the\n"
1801 " domain-id space was reached.\n"
1802 " dom [int]: Identifier of domain to which this info pertains\n"
1803 " cpu [int]: CPU to which this domain is bound\n"
1804 " vcpus [int]: Number of Virtual CPUS in this domain\n"
1805 " dying [int]: Bool - is the domain dying?\n"
1806 " crashed [int]: Bool - has the domain crashed?\n"
1807 " shutdown [int]: Bool - has the domain shut itself down?\n"
1808 " paused [int]: Bool - is the domain paused by control software?\n"
1809 " blocked [int]: Bool - is the domain blocked waiting for an event?\n"
1810 " running [int]: Bool - is the domain currently running?\n"
1811 " mem_kb [int]: Memory reservation, in kilobytes\n"
1812 " maxmem_kb [int]: Maximum memory limit, in kilobytes\n"
1813 " cpu_time [long]: CPU time consumed, in nanoseconds\n"
1814 " shutdown_reason [int]: Numeric code from guest OS, explaining "
1815 "reason why it shut itself down.\n" },
1817 { "vcpu_getinfo",
1818 (PyCFunction)pyxc_vcpu_getinfo,
1819 METH_VARARGS | METH_KEYWORDS, "\n"
1820 "Get information regarding a VCPU.\n"
1821 " dom [int]: Domain to retrieve info about.\n"
1822 " vcpu [int, 0]: VCPU to retrieve info about.\n\n"
1823 "Returns: [dict]\n"
1824 " online [int]: Bool - Is this VCPU currently online?\n"
1825 " blocked [int]: Bool - Is this VCPU blocked waiting for an event?\n"
1826 " running [int]: Bool - Is this VCPU currently running on a CPU?\n"
1827 " cpu_time [long]: CPU time consumed, in nanoseconds\n"
1828 " cpumap [int]: Bitmap of CPUs this VCPU can run on\n"
1829 " cpu [int]: CPU that this VCPU is currently bound to\n" },
1831 { "linux_build",
1832 (PyCFunction)pyxc_linux_build,
1833 METH_VARARGS | METH_KEYWORDS, "\n"
1834 "Build a new Linux guest OS.\n"
1835 " dom [int]: Identifier of domain to build into.\n"
1836 " image [str]: Name of kernel image file. May be gzipped.\n"
1837 " ramdisk [str, n/a]: Name of ramdisk file, if any.\n"
1838 " cmdline [str, n/a]: Kernel parameters, if any.\n\n"
1839 " vcpus [int, 1]: Number of Virtual CPUS in domain.\n\n"
1840 "Returns: [int] 0 on success; -1 on error.\n" },
1842 {"getBitSize",
1843 (PyCFunction)pyxc_getBitSize,
1844 METH_VARARGS | METH_KEYWORDS, "\n"
1845 "Get the bitsize of a guest OS.\n"
1846 " image [str]: Name of kernel image file. May be gzipped.\n"
1847 " cmdline [str, n/a]: Kernel parameters, if any.\n\n"},
1849 { "hvm_build",
1850 (PyCFunction)pyxc_hvm_build,
1851 METH_VARARGS | METH_KEYWORDS, "\n"
1852 "Build a new HVM guest OS.\n"
1853 " dom [int]: Identifier of domain to build into.\n"
1854 " image [str]: Name of HVM loader image file.\n"
1855 " vcpus [int, 1]: Number of Virtual CPUS in domain.\n\n"
1856 " vcpu_avail [long, 1]: Which Virtual CPUS available.\n\n"
1857 "Returns: [int] 0 on success; -1 on error.\n" },
1859 { "hvm_get_param",
1860 (PyCFunction)pyxc_get_hvm_param,
1861 METH_VARARGS | METH_KEYWORDS, "\n"
1862 "get a parameter of HVM guest OS.\n"
1863 " dom [int]: Identifier of domain to build into.\n"
1864 " param [int]: No. of HVM param.\n"
1865 "Returns: [long] value of the param.\n" },
1867 { "hvm_set_param",
1868 (PyCFunction)pyxc_set_hvm_param,
1869 METH_VARARGS | METH_KEYWORDS, "\n"
1870 "set a parameter of HVM guest OS.\n"
1871 " dom [int]: Identifier of domain to build into.\n"
1872 " param [int]: No. of HVM param.\n"
1873 " value [long]: Value of param.\n"
1874 "Returns: [int] 0 on success.\n" },
1876 { "get_device_group",
1877 (PyCFunction)pyxc_get_device_group,
1878 METH_VARARGS, "\n"
1879 "get sibling devices infomation.\n"
1880 " dom [int]: Domain to assign device to.\n"
1881 " seg [int]: PCI segment.\n"
1882 " bus [int]: PCI bus.\n"
1883 " dev [int]: PCI dev.\n"
1884 " func [int]: PCI func.\n"
1885 "Returns: [string]: Sibling devices \n" },
1887 { "test_assign_device",
1888 (PyCFunction)pyxc_test_assign_device,
1889 METH_VARARGS | METH_KEYWORDS, "\n"
1890 "test device assignment with VT-d.\n"
1891 " dom [int]: Identifier of domain to build into.\n"
1892 " pci_str [str]: PCI devices.\n"
1893 "Returns: [int] 0 on success, or device bdf that can't be assigned.\n" },
1895 { "assign_device",
1896 (PyCFunction)pyxc_assign_device,
1897 METH_VARARGS | METH_KEYWORDS, "\n"
1898 "Assign device to IOMMU domain.\n"
1899 " dom [int]: Domain to assign device to.\n"
1900 " pci_str [str]: PCI devices.\n"
1901 "Returns: [int] 0 on success, or device bdf that can't be assigned.\n" },
1903 { "deassign_device",
1904 (PyCFunction)pyxc_deassign_device,
1905 METH_VARARGS | METH_KEYWORDS, "\n"
1906 "Deassign device from IOMMU domain.\n"
1907 " dom [int]: Domain to deassign device from.\n"
1908 " pci_str [str]: PCI devices.\n"
1909 "Returns: [int] 0 on success, or device bdf that can't be deassigned.\n" },
1911 { "sched_id_get",
1912 (PyCFunction)pyxc_sched_id_get,
1913 METH_NOARGS, "\n"
1914 "Get the current scheduler type in use.\n"
1915 "Returns: [int] sched_id.\n" },
1917 { "sedf_domain_set",
1918 (PyCFunction)pyxc_sedf_domain_set,
1919 METH_KEYWORDS, "\n"
1920 "Set the scheduling parameters for a domain when running with Atropos.\n"
1921 " dom [int]: domain to set\n"
1922 " period [long]: domain's scheduling period\n"
1923 " slice [long]: domain's slice per period\n"
1924 " latency [long]: domain's wakeup latency hint\n"
1925 " extratime [int]: domain aware of extratime?\n"
1926 "Returns: [int] 0 on success; -1 on error.\n" },
1928 { "sedf_domain_get",
1929 (PyCFunction)pyxc_sedf_domain_get,
1930 METH_VARARGS, "\n"
1931 "Get the current scheduling parameters for a domain when running with\n"
1932 "the Atropos scheduler."
1933 " dom [int]: domain to query\n"
1934 "Returns: [dict]\n"
1935 " domain [int]: domain ID\n"
1936 " period [long]: scheduler period\n"
1937 " slice [long]: CPU reservation per period\n"
1938 " latency [long]: domain's wakeup latency hint\n"
1939 " extratime [int]: domain aware of extratime?\n"},
1941 { "sched_credit_domain_set",
1942 (PyCFunction)pyxc_sched_credit_domain_set,
1943 METH_KEYWORDS, "\n"
1944 "Set the scheduling parameters for a domain when running with the\n"
1945 "SMP credit scheduler.\n"
1946 " domid [int]: domain id to set\n"
1947 " weight [short]: domain's scheduling weight\n"
1948 "Returns: [int] 0 on success; -1 on error.\n" },
1950 { "sched_credit_domain_get",
1951 (PyCFunction)pyxc_sched_credit_domain_get,
1952 METH_VARARGS, "\n"
1953 "Get the scheduling parameters for a domain when running with the\n"
1954 "SMP credit scheduler.\n"
1955 " domid [int]: domain id to get\n"
1956 "Returns: [dict]\n"
1957 " weight [short]: domain's scheduling weight\n"},
1959 { "evtchn_alloc_unbound",
1960 (PyCFunction)pyxc_evtchn_alloc_unbound,
1961 METH_VARARGS | METH_KEYWORDS, "\n"
1962 "Allocate an unbound port that will await a remote connection.\n"
1963 " dom [int]: Domain whose port space to allocate from.\n"
1964 " remote_dom [int]: Remote domain to accept connections from.\n\n"
1965 "Returns: [int] Unbound event-channel port.\n" },
1967 { "evtchn_reset",
1968 (PyCFunction)pyxc_evtchn_reset,
1969 METH_VARARGS | METH_KEYWORDS, "\n"
1970 "Reset all connections.\n"
1971 " dom [int]: Domain to reset.\n" },
1973 { "physdev_map_pirq",
1974 (PyCFunction)pyxc_physdev_map_pirq,
1975 METH_VARARGS | METH_KEYWORDS, "\n"
1976 "map physical irq to guest pirq.\n"
1977 " dom [int]: Identifier of domain to map for.\n"
1978 " index [int]: physical irq.\n"
1979 " pirq [int]: guest pirq.\n"
1980 "Returns: [long] value of the param.\n" },
1982 { "physdev_pci_access_modify",
1983 (PyCFunction)pyxc_physdev_pci_access_modify,
1984 METH_VARARGS | METH_KEYWORDS, "\n"
1985 "Allow a domain access to a PCI device\n"
1986 " dom [int]: Identifier of domain to be allowed access.\n"
1987 " bus [int]: PCI bus\n"
1988 " dev [int]: PCI slot\n"
1989 " func [int]: PCI function\n"
1990 " enable [int]: Non-zero means enable access; else disable access\n\n"
1991 "Returns: [int] 0 on success; -1 on error.\n" },
1993 { "readconsolering",
1994 (PyCFunction)pyxc_readconsolering,
1995 METH_VARARGS | METH_KEYWORDS, "\n"
1996 "Read Xen's console ring.\n"
1997 " clear [int, 0]: Bool - clear the ring after reading from it?\n\n"
1998 "Returns: [str] string is empty on failure.\n" },
2000 { "physinfo",
2001 (PyCFunction)pyxc_physinfo,
2002 METH_NOARGS, "\n"
2003 "Get information about the physical host machine\n"
2004 "Returns [dict]: information about the hardware"
2005 " [None]: on failure.\n" },
2007 { "xeninfo",
2008 (PyCFunction)pyxc_xeninfo,
2009 METH_NOARGS, "\n"
2010 "Get information about the Xen host\n"
2011 "Returns [dict]: information about Xen"
2012 " [None]: on failure.\n" },
2014 { "shadow_control",
2015 (PyCFunction)pyxc_shadow_control,
2016 METH_VARARGS | METH_KEYWORDS, "\n"
2017 "Set parameter for shadow pagetable interface\n"
2018 " dom [int]: Identifier of domain.\n"
2019 " op [int, 0]: operation\n\n"
2020 "Returns: [int] 0 on success; -1 on error.\n" },
2022 { "shadow_mem_control",
2023 (PyCFunction)pyxc_shadow_mem_control,
2024 METH_VARARGS | METH_KEYWORDS, "\n"
2025 "Set or read shadow pagetable memory use\n"
2026 " dom [int]: Identifier of domain.\n"
2027 " mb [int, -1]: MB of shadow memory this domain should have.\n\n"
2028 "Returns: [int] MB of shadow memory in use by this domain.\n" },
2030 { "domain_setmaxmem",
2031 (PyCFunction)pyxc_domain_setmaxmem,
2032 METH_VARARGS, "\n"
2033 "Set a domain's memory limit\n"
2034 " dom [int]: Identifier of domain.\n"
2035 " maxmem_kb [int]: .\n"
2036 "Returns: [int] 0 on success; -1 on error.\n" },
2038 { "domain_set_target_mem",
2039 (PyCFunction)pyxc_domain_set_target_mem,
2040 METH_VARARGS, "\n"
2041 "Set a domain's memory target\n"
2042 " dom [int]: Identifier of domain.\n"
2043 " mem_kb [int]: .\n"
2044 "Returns: [int] 0 on success; -1 on error.\n" },
2046 { "domain_set_memmap_limit",
2047 (PyCFunction)pyxc_domain_set_memmap_limit,
2048 METH_VARARGS, "\n"
2049 "Set a domain's physical memory mappping limit\n"
2050 " dom [int]: Identifier of domain.\n"
2051 " map_limitkb [int]: .\n"
2052 "Returns: [int] 0 on success; -1 on error.\n" },
2054 #ifdef __ia64__
2055 { "nvram_init",
2056 (PyCFunction)pyxc_nvram_init,
2057 METH_VARARGS, "\n"
2058 "Init nvram in IA64 platform\n"
2059 "Returns: [int] 0 on success; -1 on error.\n" },
2060 { "set_os_type",
2061 (PyCFunction)pyxc_set_os_type,
2062 METH_VARARGS, "\n"
2063 "Set guest OS type on IA64 platform\n"
2064 "Returns: [int] 0 on success; -1 on error.\n" },
2065 #endif /* __ia64__ */
2066 { "domain_ioport_permission",
2067 (PyCFunction)pyxc_domain_ioport_permission,
2068 METH_VARARGS | METH_KEYWORDS, "\n"
2069 "Allow a domain access to a range of IO ports\n"
2070 " dom [int]: Identifier of domain to be allowed access.\n"
2071 " first_port [int]: First IO port\n"
2072 " nr_ports [int]: Number of IO ports\n"
2073 " allow_access [int]: Non-zero means enable access; else disable access\n\n"
2074 "Returns: [int] 0 on success; -1 on error.\n" },
2076 { "domain_irq_permission",
2077 (PyCFunction)pyxc_domain_irq_permission,
2078 METH_VARARGS | METH_KEYWORDS, "\n"
2079 "Allow a domain access to a physical IRQ\n"
2080 " dom [int]: Identifier of domain to be allowed access.\n"
2081 " pirq [int]: The Physical IRQ\n"
2082 " allow_access [int]: Non-zero means enable access; else disable access\n\n"
2083 "Returns: [int] 0 on success; -1 on error.\n" },
2085 { "domain_iomem_permission",
2086 (PyCFunction)pyxc_domain_iomem_permission,
2087 METH_VARARGS | METH_KEYWORDS, "\n"
2088 "Allow a domain access to a range of IO memory pages\n"
2089 " dom [int]: Identifier of domain to be allowed access.\n"
2090 " first_pfn [long]: First page of I/O Memory\n"
2091 " nr_pfns [long]: Number of pages of I/O Memory (>0)\n"
2092 " allow_access [int]: Non-zero means enable access; else disable access\n\n"
2093 "Returns: [int] 0 on success; -1 on error.\n" },
2095 { "pages_to_kib",
2096 (PyCFunction)pyxc_pages_to_kib,
2097 METH_VARARGS, "\n"
2098 "Returns: [int]: The size in KiB of memory spanning the given number "
2099 "of pages.\n" },
2101 { "domain_set_time_offset",
2102 (PyCFunction)pyxc_domain_set_time_offset,
2103 METH_VARARGS, "\n"
2104 "Set a domain's time offset to Dom0's localtime\n"
2105 " dom [int]: Domain whose time offset is being set.\n"
2106 " offset [int]: Time offset from UTC in seconds.\n"
2107 "Returns: [int] 0 on success; -1 on error.\n" },
2109 { "domain_set_tsc_info",
2110 (PyCFunction)pyxc_domain_set_tsc_info,
2111 METH_VARARGS, "\n"
2112 "Set a domain's TSC mode\n"
2113 " dom [int]: Domain whose TSC mode is being set.\n"
2114 " tsc_mode [int]: 0=default (monotonic, but native where possible)\n"
2115 " 1=always emulate 2=never emulate 3=pvrdtscp\n"
2116 "Returns: [int] 0 on success; -1 on error.\n" },
2118 { "domain_disable_migrate",
2119 (PyCFunction)pyxc_domain_disable_migrate,
2120 METH_VARARGS, "\n"
2121 "Marks domain as non-migratable AND non-restoreable\n"
2122 " dom [int]: Domain whose TSC mode is being set.\n"
2123 "Returns: [int] 0 on success; -1 on error.\n" },
2125 { "domain_send_trigger",
2126 (PyCFunction)pyxc_domain_send_trigger,
2127 METH_VARARGS | METH_KEYWORDS, "\n"
2128 "Send trigger to a domain.\n"
2129 " dom [int]: Identifier of domain to be sent trigger.\n"
2130 " trigger [int]: Trigger type number.\n"
2131 " vcpu [int]: VCPU to be sent trigger.\n"
2132 "Returns: [int] 0 on success; -1 on error.\n" },
2134 { "send_debug_keys",
2135 (PyCFunction)pyxc_send_debug_keys,
2136 METH_VARARGS | METH_KEYWORDS, "\n"
2137 "Inject debug keys into Xen.\n"
2138 " keys [str]: String of keys to inject.\n" },
2140 #if defined(__i386__) || defined(__x86_64__)
2141 { "domain_check_cpuid",
2142 (PyCFunction)pyxc_dom_check_cpuid,
2143 METH_VARARGS, "\n"
2144 "Apply checks to host CPUID.\n"
2145 " input [long]: Input for cpuid instruction (eax)\n"
2146 " sub_input [long]: Second input (optional, may be None) for cpuid "
2147 " instruction (ecx)\n"
2148 " config [dict]: Dictionary of register\n"
2149 " config [dict]: Dictionary of register, use for checking\n\n"
2150 "Returns: [int] 0 on success; exception on error.\n" },
2152 { "domain_set_cpuid",
2153 (PyCFunction)pyxc_dom_set_cpuid,
2154 METH_VARARGS, "\n"
2155 "Set cpuid response for an input and a domain.\n"
2156 " dom [int]: Identifier of domain.\n"
2157 " input [long]: Input for cpuid instruction (eax)\n"
2158 " sub_input [long]: Second input (optional, may be None) for cpuid "
2159 " instruction (ecx)\n"
2160 " config [dict]: Dictionary of register\n\n"
2161 "Returns: [int] 0 on success; exception on error.\n" },
2163 { "domain_set_policy_cpuid",
2164 (PyCFunction)pyxc_dom_set_policy_cpuid,
2165 METH_VARARGS, "\n"
2166 "Set the default cpuid policy for a domain.\n"
2167 " dom [int]: Identifier of domain.\n\n"
2168 "Returns: [int] 0 on success; exception on error.\n" },
2170 { "domain_set_machine_address_size",
2171 (PyCFunction)pyxc_dom_set_machine_address_size,
2172 METH_VARARGS, "\n"
2173 "Set maximum machine address size for this domain.\n"
2174 " dom [int]: Identifier of domain.\n"
2175 " width [int]: Maximum machine address width.\n" },
2177 { "domain_suppress_spurious_page_faults",
2178 (PyCFunction)pyxc_dom_suppress_spurious_page_faults,
2179 METH_VARARGS, "\n"
2180 "Do not propagate spurious page faults to this guest.\n"
2181 " dom [int]: Identifier of domain.\n" },
2182 #endif
2184 { "tmem_control",
2185 (PyCFunction)pyxc_tmem_control,
2186 METH_VARARGS | METH_KEYWORDS, "\n"
2187 "Do various control on a tmem pool.\n"
2188 " pool_id [int]: Identifier of the tmem pool (-1 == all).\n"
2189 " subop [int]: Supplementary Operation.\n"
2190 " cli_id [int]: Client identifier (-1 == all).\n"
2191 " arg1 [int]: Argument.\n"
2192 " arg2 [int]: Argument.\n"
2193 " buf [str]: Buffer.\n\n"
2194 "Returns: [int] 0 or [str] tmem info on success; exception on error.\n" },
2196 { "tmem_shared_auth",
2197 (PyCFunction)pyxc_tmem_shared_auth,
2198 METH_VARARGS | METH_KEYWORDS, "\n"
2199 "De/authenticate a shared tmem pool.\n"
2200 " cli_id [int]: Client identifier (-1 == all).\n"
2201 " uuid_str [str]: uuid.\n"
2202 " auth [int]: 0|1 .\n"
2203 "Returns: [int] 0 on success; exception on error.\n" },
2205 { "dom_set_memshr",
2206 (PyCFunction)pyxc_dom_set_memshr,
2207 METH_VARARGS, "\n"
2208 "Enable/disable memory sharing for the domain.\n"
2209 " dom [int]: Domain identifier.\n"
2210 " enable [int,0|1]: Disable or enable?\n"
2211 "Returns: [int] 0 on success; -1 on error.\n" },
2213 { NULL, NULL, 0, NULL }
2214 };
2217 static PyObject *PyXc_getattr(PyObject *obj, char *name)
2219 return Py_FindMethod(pyxc_methods, obj, name);
2222 static PyObject *PyXc_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2224 XcObject *self = (XcObject *)type->tp_alloc(type, 0);
2226 if (self == NULL)
2227 return NULL;
2229 self->xc_handle = -1;
2231 return (PyObject *)self;
2234 static int
2235 PyXc_init(XcObject *self, PyObject *args, PyObject *kwds)
2237 if ((self->xc_handle = xc_interface_open()) == -1) {
2238 pyxc_error_to_exception();
2239 return -1;
2242 return 0;
2245 static void PyXc_dealloc(XcObject *self)
2247 if (self->xc_handle != -1) {
2248 xc_interface_close(self->xc_handle);
2249 self->xc_handle = -1;
2252 self->ob_type->tp_free((PyObject *)self);
2255 static PyTypeObject PyXcType = {
2256 PyObject_HEAD_INIT(NULL)
2257 0,
2258 PKG "." CLS,
2259 sizeof(XcObject),
2260 0,
2261 (destructor)PyXc_dealloc, /* tp_dealloc */
2262 NULL, /* tp_print */
2263 PyXc_getattr, /* tp_getattr */
2264 NULL, /* tp_setattr */
2265 NULL, /* tp_compare */
2266 NULL, /* tp_repr */
2267 NULL, /* tp_as_number */
2268 NULL, /* tp_as_sequence */
2269 NULL, /* tp_as_mapping */
2270 NULL, /* tp_hash */
2271 NULL, /* tp_call */
2272 NULL, /* tp_str */
2273 NULL, /* tp_getattro */
2274 NULL, /* tp_setattro */
2275 NULL, /* tp_as_buffer */
2276 Py_TPFLAGS_DEFAULT, /* tp_flags */
2277 "Xen client connections", /* tp_doc */
2278 NULL, /* tp_traverse */
2279 NULL, /* tp_clear */
2280 NULL, /* tp_richcompare */
2281 0, /* tp_weaklistoffset */
2282 NULL, /* tp_iter */
2283 NULL, /* tp_iternext */
2284 pyxc_methods, /* tp_methods */
2285 NULL, /* tp_members */
2286 NULL, /* tp_getset */
2287 NULL, /* tp_base */
2288 NULL, /* tp_dict */
2289 NULL, /* tp_descr_get */
2290 NULL, /* tp_descr_set */
2291 0, /* tp_dictoffset */
2292 (initproc)PyXc_init, /* tp_init */
2293 NULL, /* tp_alloc */
2294 PyXc_new, /* tp_new */
2295 };
2297 static PyMethodDef xc_methods[] = { { NULL } };
2299 PyMODINIT_FUNC initxc(void)
2301 PyObject *m;
2303 if (PyType_Ready(&PyXcType) < 0)
2304 return;
2306 m = Py_InitModule(PKG, xc_methods);
2308 if (m == NULL)
2309 return;
2311 xc_error_obj = PyErr_NewException(PKG ".Error", PyExc_RuntimeError, NULL);
2312 zero = PyInt_FromLong(0);
2314 /* KAF: This ensures that we get debug output in a timely manner. */
2315 setbuf(stdout, NULL);
2316 setbuf(stderr, NULL);
2318 Py_INCREF(&PyXcType);
2319 PyModule_AddObject(m, CLS, (PyObject *)&PyXcType);
2321 Py_INCREF(xc_error_obj);
2322 PyModule_AddObject(m, "Error", xc_error_obj);
2324 /* Expose some libxc constants to Python */
2325 PyModule_AddIntConstant(m, "XEN_SCHEDULER_SEDF", XEN_SCHEDULER_SEDF);
2326 PyModule_AddIntConstant(m, "XEN_SCHEDULER_CREDIT", XEN_SCHEDULER_CREDIT);
2331 /*
2332 * Local variables:
2333 * c-indent-level: 4
2334 * c-basic-offset: 4
2335 * End:
2336 */