mirror of
https://github.com/xen-project/xen.git
synced 2026-10-29 10:40:03 +01:00
[POWERPC] Merge with xen-unstable.hg.
Signed-off-by: Hollis Blanchard <hollisb@us.ibm.com>
This commit is contained in:
commit
8cadd348b3
453 files changed
+41020
-5584
No files matched your search
@@ -26,7 +26,7 @@ platform_serial = ''
|
||||
platform_localtime = False
|
||||
platform_clock_offset = False
|
||||
platform_enable_audio = False
|
||||
builder = ''
|
||||
builder = 'linux'
|
||||
boot_method = '' # this will remove the kernel/initrd ??
|
||||
kernel_kernel = '/boot/vmlinuz-2.6.16.29-xen'
|
||||
kernel_initrd = '/root/initrd-2.6.16.29-xen.img'
|
||||
|
||||
@@ -29,17 +29,20 @@ from getpass import getpass
|
||||
MB = 1024 * 1024
|
||||
|
||||
HOST_INFO_FORMAT = '%-20s: %-50s'
|
||||
VM_LIST_FORMAT = '%(name_label)-18s %(memory_actual)-5s %(vcpus_number)-5s'\
|
||||
VM_LIST_FORMAT = '%(name_label)-18s %(memory_actual)-5s %(VCPUs_number)-5s'\
|
||||
' %(power_state)-10s %(uuid)-36s'
|
||||
SR_LIST_FORMAT = '%(name_label)-18s %(uuid)-36s %(physical_size)-10s' \
|
||||
'%(type)-10s'
|
||||
VDI_LIST_FORMAT = '%(name_label)-18s %(uuid)-36s %(virtual_size)-8s '\
|
||||
'%(sector_size)-8s'
|
||||
VBD_LIST_FORMAT = '%(name_label)-18s %(uuid)-36s %(VDI)-8s '\
|
||||
'%(image)-8s'
|
||||
|
||||
COMMANDS = {
|
||||
'host-info': ('', 'Get Xen Host Info'),
|
||||
'host-set-name': ('', 'Set host name'),
|
||||
'sr-list': ('', 'List all SRs'),
|
||||
'vbd-list': ('', 'List all VBDs'),
|
||||
'vbd-create': ('<domname> <pycfg> [opts]',
|
||||
'Create VBD attached to domname'),
|
||||
'vdi-create': ('<pycfg> [opts]', 'Create a VDI'),
|
||||
@@ -165,6 +168,13 @@ def resolve_vm(server, session, vm_name):
|
||||
else:
|
||||
return vm_uuid[0]
|
||||
|
||||
def resolve_vdi(server, session, vdi_name):
|
||||
vdi_uuid = execute(server.VDI.get_by_name_label, session, vdi_name)
|
||||
if not vdi_uuid:
|
||||
return None
|
||||
else:
|
||||
return vdi_uuid[0]
|
||||
|
||||
#
|
||||
# Actual commands
|
||||
#
|
||||
@@ -216,16 +226,16 @@ def xapi_vm_list(*args):
|
||||
if not is_long:
|
||||
print VM_LIST_FORMAT % {'name_label':'Name',
|
||||
'memory_actual':'Mem',
|
||||
'vcpus_number': 'VCPUs',
|
||||
'VCPUs_number': 'VCPUs',
|
||||
'power_state': 'State',
|
||||
'uuid': 'UUID'}
|
||||
|
||||
for uuid in vm_uuids:
|
||||
vm_info = execute(server.VM.get_record, session, uuid)
|
||||
if is_long:
|
||||
vbds = vm_info['vbds']
|
||||
vifs = vm_info['vifs']
|
||||
vtpms = vm_info['vtpms']
|
||||
vbds = vm_info['VBDs']
|
||||
vifs = vm_info['VIFs']
|
||||
vtpms = vm_info['VTPMs']
|
||||
vif_infos = []
|
||||
vbd_infos = []
|
||||
vtpm_infos = []
|
||||
@@ -238,9 +248,9 @@ def xapi_vm_list(*args):
|
||||
for vtpm in vtpms:
|
||||
vtpm_info = execute(server.VTPM.get_record, session, vtpm)
|
||||
vtpm_infos.append(vtpm_info)
|
||||
vm_info['vbds'] = vbd_infos
|
||||
vm_info['vifs'] = vif_infos
|
||||
vm_info['vtpms'] = vtpm_infos
|
||||
vm_info['VBDs'] = vbd_infos
|
||||
vm_info['VIFs'] = vif_infos
|
||||
vm_info['VTPMs'] = vtpm_infos
|
||||
pprint(vm_info)
|
||||
else:
|
||||
print VM_LIST_FORMAT % _stringify(vm_info)
|
||||
@@ -276,7 +286,7 @@ def xapi_vm_start(*args):
|
||||
server, session = _connect()
|
||||
vm_uuid = resolve_vm(server, session, args[0])
|
||||
print 'Starting VM %s (%s)' % (args[0], vm_uuid)
|
||||
success = execute(server.VM.start, session, vm_uuid)
|
||||
success = execute(server.VM.start, session, vm_uuid, False)
|
||||
print 'Done.'
|
||||
|
||||
def xapi_vm_shutdown(*args):
|
||||
@@ -334,6 +344,22 @@ def xapi_vif_create(*args):
|
||||
vif_uuid = execute(server.VIF.create, session, cfg)
|
||||
print 'Done. (%s)' % vif_uuid
|
||||
|
||||
def xapi_vbd_list(*args):
|
||||
server, session = _connect()
|
||||
domname = args[0]
|
||||
|
||||
dom_uuid = resolve_vm(server, session, domname)
|
||||
vbds = execute(server.VM.get_VBDs, session, dom_uuid)
|
||||
|
||||
print VBD_LIST_FORMAT % {'name_label': 'VDI Label',
|
||||
'uuid' : 'UUID',
|
||||
'VDI': 'VDI',
|
||||
'image': 'Image'}
|
||||
|
||||
for vbd in vbds:
|
||||
vbd_struct = execute(server.VBD.get_record, session, vbd)
|
||||
print VBD_LIST_FORMAT % vbd_struct
|
||||
|
||||
def xapi_vdi_list(*args):
|
||||
server, session = _connect()
|
||||
vdis = execute(server.VDI.get_all, session)
|
||||
@@ -420,8 +446,6 @@ def xapi_vtpm_create(*args):
|
||||
print "Has driver type '%s'" % driver
|
||||
vtpm_rec = execute(server.VTPM.get_record, session, vtpm_uuid)
|
||||
print "Has vtpm record '%s'" % vtpm_rec
|
||||
vm = execute(server.VTPM.get_VM, session, vtpm_uuid)
|
||||
print "Has VM '%s'" % vm
|
||||
|
||||
|
||||
#
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
#define PKG "xen.lowlevel.xc"
|
||||
#define CLS "xc"
|
||||
|
||||
static PyObject *xc_error, *zero;
|
||||
static PyObject *xc_error_obj, *zero;
|
||||
|
||||
typedef struct {
|
||||
PyObject_HEAD;
|
||||
@@ -40,6 +40,26 @@ typedef struct {
|
||||
static PyObject *dom_op(XcObject *self, PyObject *args,
|
||||
int (*fn)(int, uint32_t));
|
||||
|
||||
static PyObject *pyxc_error_to_exception(void)
|
||||
{
|
||||
PyObject *pyerr;
|
||||
const xc_error const *err = xc_get_last_error();
|
||||
const char *desc = xc_error_code_to_desc(err->code);
|
||||
|
||||
if (err->code == XC_ERROR_NONE)
|
||||
return PyErr_SetFromErrno(xc_error_obj);
|
||||
|
||||
if (err->message[0] != '\0')
|
||||
pyerr = Py_BuildValue("(iss)", err->code, desc, err->message);
|
||||
else
|
||||
pyerr = Py_BuildValue("(is)", err->code, desc);
|
||||
|
||||
xc_clear_last_error();
|
||||
|
||||
PyErr_SetObject(xc_error_obj, pyerr);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static PyObject *pyxc_domain_dumpcore(XcObject *self, PyObject *args)
|
||||
{
|
||||
@@ -53,7 +73,7 @@ static PyObject *pyxc_domain_dumpcore(XcObject *self, PyObject *args)
|
||||
return NULL;
|
||||
|
||||
if (xc_domain_dumpcore(self->xc_handle, dom, corefile) != 0)
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -101,13 +121,13 @@ static PyObject *pyxc_domain_create(XcObject *self,
|
||||
|
||||
if ( (ret = xc_domain_create(self->xc_handle, ssidref,
|
||||
handle, flags, &dom)) < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
return PyInt_FromLong(dom);
|
||||
|
||||
out_exception:
|
||||
errno = EINVAL;
|
||||
PyErr_SetFromErrno(xc_error);
|
||||
PyErr_SetFromErrno(xc_error_obj);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -119,7 +139,7 @@ static PyObject *pyxc_domain_max_vcpus(XcObject *self, PyObject *args)
|
||||
return NULL;
|
||||
|
||||
if (xc_domain_max_vcpus(self->xc_handle, dom, max) != 0)
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -164,7 +184,7 @@ static PyObject *pyxc_vcpu_setaffinity(XcObject *self,
|
||||
}
|
||||
|
||||
if ( xc_vcpu_setaffinity(self->xc_handle, dom, vcpu, cpumap) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -184,7 +204,7 @@ static PyObject *pyxc_domain_setcpuweight(XcObject *self,
|
||||
return NULL;
|
||||
|
||||
if ( xc_domain_setcpuweight(self->xc_handle, dom, cpuweight) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -215,14 +235,13 @@ static PyObject *pyxc_domain_sethandle(XcObject *self, PyObject *args)
|
||||
}
|
||||
|
||||
if (xc_domain_sethandle(self->xc_handle, dom, handle) < 0)
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
|
||||
out_exception:
|
||||
errno = EINVAL;
|
||||
PyErr_SetFromErrno(xc_error);
|
||||
PyErr_SetFromErrno(xc_error_obj);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -251,7 +270,7 @@ static PyObject *pyxc_domain_getinfo(XcObject *self,
|
||||
if (nr_doms < 0)
|
||||
{
|
||||
free(info);
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
}
|
||||
|
||||
list = PyList_New(nr_doms);
|
||||
@@ -306,10 +325,10 @@ static PyObject *pyxc_vcpu_getinfo(XcObject *self,
|
||||
|
||||
rc = xc_vcpu_getinfo(self->xc_handle, dom, vcpu, &info);
|
||||
if ( rc < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
rc = xc_vcpu_getaffinity(self->xc_handle, dom, vcpu, &cpumap);
|
||||
if ( rc < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
info_dict = Py_BuildValue("{s:i,s:i,s:i,s:L,s:i}",
|
||||
"online", info.online,
|
||||
@@ -360,9 +379,7 @@ static PyObject *pyxc_linux_build(XcObject *self,
|
||||
ramdisk, cmdline, features, flags,
|
||||
store_evtchn, &store_mfn,
|
||||
console_evtchn, &console_mfn) != 0 ) {
|
||||
if (!errno)
|
||||
errno = EINVAL;
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
}
|
||||
return Py_BuildValue("{s:i,s:i}",
|
||||
"store_mfn", store_mfn,
|
||||
@@ -415,10 +432,13 @@ static PyObject *pyxc_hvm_build(XcObject *self,
|
||||
PyObject *kwds)
|
||||
{
|
||||
uint32_t dom;
|
||||
#if !defined(__ia64__)
|
||||
struct hvm_info_table *va_hvm;
|
||||
uint8_t *va_map, sum;
|
||||
int i;
|
||||
#endif
|
||||
char *image;
|
||||
int i, store_evtchn, memsize, vcpus = 1, pae = 0, acpi = 0, apic = 1;
|
||||
int store_evtchn, memsize, vcpus = 1, pae = 0, acpi = 0, apic = 1;
|
||||
unsigned long store_mfn;
|
||||
|
||||
static char *kwd_list[] = { "domid", "store_evtchn",
|
||||
@@ -429,15 +449,20 @@ static PyObject *pyxc_hvm_build(XcObject *self,
|
||||
&image, &vcpus, &pae, &acpi, &apic) )
|
||||
return NULL;
|
||||
|
||||
#if defined(__ia64__)
|
||||
/* Set vcpus to later be retrieved in setup_guest() */
|
||||
xc_set_hvm_param(self->xc_handle, dom, HVM_PARAM_VCPUS, vcpus);
|
||||
#endif
|
||||
if ( xc_hvm_build(self->xc_handle, dom, memsize, image) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
#if !defined(__ia64__)
|
||||
/* Set up the HVM info table. */
|
||||
va_map = xc_map_foreign_range(self->xc_handle, dom, PAGE_SIZE,
|
||||
va_map = xc_map_foreign_range(self->xc_handle, dom, XC_PAGE_SIZE,
|
||||
PROT_READ | PROT_WRITE,
|
||||
HVM_INFO_PFN);
|
||||
if ( va_map == NULL )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return PyErr_SetFromErrno(xc_error_obj);
|
||||
va_hvm = (struct hvm_info_table *)(va_map + HVM_INFO_OFFSET);
|
||||
memset(va_hvm, 0, sizeof(*va_hvm));
|
||||
strncpy(va_hvm->signature, "HVM INFO", 8);
|
||||
@@ -448,10 +473,13 @@ static PyObject *pyxc_hvm_build(XcObject *self,
|
||||
for ( i = 0, sum = 0; i < va_hvm->length; i++ )
|
||||
sum += ((uint8_t *)va_hvm)[i];
|
||||
va_hvm->checksum = -sum;
|
||||
munmap(va_map, PAGE_SIZE);
|
||||
munmap(va_map, XC_PAGE_SIZE);
|
||||
#endif
|
||||
|
||||
xc_get_hvm_param(self->xc_handle, dom, HVM_PARAM_STORE_PFN, &store_mfn);
|
||||
#if !defined(__ia64__)
|
||||
xc_set_hvm_param(self->xc_handle, dom, HVM_PARAM_PAE_ENABLED, pae);
|
||||
#endif
|
||||
xc_set_hvm_param(self->xc_handle, dom, HVM_PARAM_STORE_EVTCHN,
|
||||
store_evtchn);
|
||||
|
||||
@@ -472,7 +500,7 @@ static PyObject *pyxc_evtchn_alloc_unbound(XcObject *self,
|
||||
return NULL;
|
||||
|
||||
if ( (port = xc_evtchn_alloc_unbound(self->xc_handle, dom, remote_dom)) < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
return PyInt_FromLong(port);
|
||||
}
|
||||
@@ -493,7 +521,7 @@ static PyObject *pyxc_physdev_pci_access_modify(XcObject *self,
|
||||
ret = xc_physdev_pci_access_modify(
|
||||
self->xc_handle, dom, bus, dev, func, enable);
|
||||
if ( ret != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -515,7 +543,7 @@ static PyObject *pyxc_readconsolering(XcObject *self,
|
||||
|
||||
ret = xc_readconsolering(self->xc_handle, &str, &count, clear);
|
||||
if ( ret < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
return PyString_FromStringAndSize(str, count);
|
||||
}
|
||||
@@ -545,7 +573,7 @@ static PyObject *pyxc_physinfo(XcObject *self)
|
||||
int i;
|
||||
|
||||
if ( xc_physinfo(self->xc_handle, &info) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
*q=0;
|
||||
for(i=0;i<sizeof(info.hw_cap)/4;i++)
|
||||
@@ -583,25 +611,25 @@ static PyObject *pyxc_xeninfo(XcObject *self)
|
||||
xen_version = xc_version(self->xc_handle, XENVER_version, NULL);
|
||||
|
||||
if ( xc_version(self->xc_handle, XENVER_extraversion, &xen_extra) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
if ( xc_version(self->xc_handle, XENVER_compile_info, &xen_cc) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
if ( xc_version(self->xc_handle, XENVER_changeset, &xen_chgset) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
if ( xc_version(self->xc_handle, XENVER_capabilities, &xen_caps) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
if ( xc_version(self->xc_handle, XENVER_platform_parameters, &p_parms) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
sprintf(str, "virt_start=0x%lx", p_parms.virt_start);
|
||||
|
||||
xen_pagesize = xc_version(self->xc_handle, XENVER_pagesize, NULL);
|
||||
if (xen_pagesize < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
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}",
|
||||
"xen_major", xen_version >> 16,
|
||||
@@ -634,7 +662,7 @@ static PyObject *pyxc_sedf_domain_set(XcObject *self,
|
||||
return NULL;
|
||||
if ( xc_sedf_domain_set(self->xc_handle, domid, period,
|
||||
slice, latency, extratime,weight) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -651,7 +679,7 @@ static PyObject *pyxc_sedf_domain_get(XcObject *self, PyObject *args)
|
||||
|
||||
if (xc_sedf_domain_get(self->xc_handle, domid, &period,
|
||||
&slice,&latency,&extratime,&weight))
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
return Py_BuildValue("{s:i,s:L,s:L,s:L,s:i,s:i}",
|
||||
"domid", domid,
|
||||
@@ -679,7 +707,7 @@ static PyObject *pyxc_shadow_control(PyObject *self,
|
||||
|
||||
if ( xc_shadow_control(xc->xc_handle, dom, op, NULL, 0, NULL, 0, NULL)
|
||||
< 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -709,7 +737,7 @@ static PyObject *pyxc_shadow_mem_control(PyObject *self,
|
||||
op = XEN_DOMCTL_SHADOW_OP_SET_ALLOCATION;
|
||||
}
|
||||
if ( xc_shadow_control(xc->xc_handle, dom, op, NULL, 0, &mb, 0, NULL) < 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
mbarg = mb;
|
||||
return Py_BuildValue("i", mbarg);
|
||||
@@ -719,7 +747,7 @@ static PyObject *pyxc_sched_id_get(XcObject *self) {
|
||||
|
||||
int sched_id;
|
||||
if (xc_sched_id(self->xc_handle, &sched_id) != 0)
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return PyErr_SetFromErrno(xc_error_obj);
|
||||
|
||||
return Py_BuildValue("i", sched_id);
|
||||
}
|
||||
@@ -745,7 +773,7 @@ static PyObject *pyxc_sched_credit_domain_set(XcObject *self,
|
||||
sdom.cap = cap;
|
||||
|
||||
if ( xc_sched_credit_domain_set(self->xc_handle, domid, &sdom) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -760,7 +788,7 @@ static PyObject *pyxc_sched_credit_domain_get(XcObject *self, PyObject *args)
|
||||
return NULL;
|
||||
|
||||
if ( xc_sched_credit_domain_get(self->xc_handle, domid, &sdom) != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
return Py_BuildValue("{s:H,s:H}",
|
||||
"weight", sdom.weight,
|
||||
@@ -776,7 +804,22 @@ static PyObject *pyxc_domain_setmaxmem(XcObject *self, PyObject *args)
|
||||
return NULL;
|
||||
|
||||
if (xc_domain_setmaxmem(self->xc_handle, dom, maxmem_kb) != 0)
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
}
|
||||
|
||||
static PyObject *pyxc_domain_set_memmap_limit(XcObject *self, PyObject *args)
|
||||
{
|
||||
uint32_t dom;
|
||||
unsigned int maplimit_kb;
|
||||
|
||||
if ( !PyArg_ParseTuple(args, "ii", &dom, &maplimit_kb) )
|
||||
return NULL;
|
||||
|
||||
if ( xc_domain_set_memmap_limit(self->xc_handle, dom, maplimit_kb) != 0 )
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -803,7 +846,7 @@ static PyObject *pyxc_domain_memory_increase_reservation(XcObject *self,
|
||||
if ( xc_domain_memory_increase_reservation(self->xc_handle, dom,
|
||||
nr_extents, extent_order,
|
||||
address_bits, NULL) )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -847,7 +890,7 @@ static PyObject *pyxc_domain_ioport_permission(XcObject *self,
|
||||
ret = xc_domain_ioport_permission(
|
||||
self->xc_handle, dom, first_port, nr_ports, allow_access);
|
||||
if ( ret != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -870,7 +913,7 @@ static PyObject *pyxc_domain_irq_permission(PyObject *self,
|
||||
ret = xc_domain_irq_permission(
|
||||
xc->xc_handle, dom, pirq, allow_access);
|
||||
if ( ret != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -893,7 +936,7 @@ static PyObject *pyxc_domain_iomem_permission(PyObject *self,
|
||||
ret = xc_domain_iomem_permission(
|
||||
xc->xc_handle, dom, first_pfn, nr_pfns, allow_access);
|
||||
if ( ret != 0 )
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -933,7 +976,7 @@ static PyObject *dom_op(XcObject *self, PyObject *args,
|
||||
return NULL;
|
||||
|
||||
if (fn(self->xc_handle, dom) != 0)
|
||||
return PyErr_SetFromErrno(xc_error);
|
||||
return pyxc_error_to_exception();
|
||||
|
||||
Py_INCREF(zero);
|
||||
return zero;
|
||||
@@ -1199,6 +1242,14 @@ static PyMethodDef pyxc_methods[] = {
|
||||
" maxmem_kb [int]: .\n"
|
||||
"Returns: [int] 0 on success; -1 on error.\n" },
|
||||
|
||||
{ "domain_set_memmap_limit",
|
||||
(PyCFunction)pyxc_domain_set_memmap_limit,
|
||||
METH_VARARGS, "\n"
|
||||
"Set a domain's physical memory mappping limit\n"
|
||||
" dom [int]: Identifier of domain.\n"
|
||||
" map_limitkb [int]: .\n"
|
||||
"Returns: [int] 0 on success; -1 on error.\n" },
|
||||
|
||||
{ "domain_memory_increase_reservation",
|
||||
(PyCFunction)pyxc_domain_memory_increase_reservation,
|
||||
METH_VARARGS | METH_KEYWORDS, "\n"
|
||||
@@ -1284,7 +1335,7 @@ static int
|
||||
PyXc_init(XcObject *self, PyObject *args, PyObject *kwds)
|
||||
{
|
||||
if ((self->xc_handle = xc_interface_open()) == -1) {
|
||||
PyErr_SetFromErrno(xc_error);
|
||||
pyxc_error_to_exception();
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1357,7 +1408,7 @@ PyMODINIT_FUNC initxc(void)
|
||||
if (m == NULL)
|
||||
return;
|
||||
|
||||
xc_error = PyErr_NewException(PKG ".Error", PyExc_RuntimeError, NULL);
|
||||
xc_error_obj = PyErr_NewException(PKG ".Error", PyExc_RuntimeError, NULL);
|
||||
zero = PyInt_FromLong(0);
|
||||
|
||||
/* KAF: This ensures that we get debug output in a timely manner. */
|
||||
@@ -1367,8 +1418,8 @@ PyMODINIT_FUNC initxc(void)
|
||||
Py_INCREF(&PyXcType);
|
||||
PyModule_AddObject(m, CLS, (PyObject *)&PyXcType);
|
||||
|
||||
Py_INCREF(xc_error);
|
||||
PyModule_AddObject(m, "Error", xc_error);
|
||||
Py_INCREF(xc_error_obj);
|
||||
PyModule_AddObject(m, "Error", xc_error_obj);
|
||||
|
||||
/* Expose some libxc constants to Python */
|
||||
PyModule_AddIntConstant(m, "XEN_SCHEDULER_SEDF", XEN_SCHEDULER_SEDF);
|
||||
|
||||
@@ -43,8 +43,9 @@ TITLE_RE = re.compile(r'<title>(.*)</title>')
|
||||
|
||||
FILES_TO_SEND = [ '/var/log/' + x for x in
|
||||
[ 'syslog', 'messages', 'debug',
|
||||
'xen/xend.log', 'xen/xend-debug.log', 'xen/xenstored-trace.log',
|
||||
'xen/xen-hotplug.log' ] ]
|
||||
'xen/xend-debug.log', 'xen/xenstored-trace.log',
|
||||
'xen/xen-hotplug.log', 'xen/xend.log' ] +
|
||||
[ 'xen/xend.log.%d' % z for z in range(1,6) ] ]
|
||||
#FILES_TO_SEND = [ ]
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,44 @@
|
||||
#============================================================================
|
||||
# This library is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Lesser General Public License as published by
|
||||
# the Free Software Foundation; either version 2.1 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This library is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Lesser General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Lesser General Public License
|
||||
# along with this library; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
#============================================================================
|
||||
# Copyright (c) 2006 XenSource Inc.
|
||||
#============================================================================
|
||||
|
||||
import errno
|
||||
import os
|
||||
import os.path
|
||||
import stat
|
||||
|
||||
|
||||
def parents(dir, perms, enforcePermissions = False):
|
||||
"""
|
||||
Ensure that the given directory exists, creating it if necessary, but not
|
||||
complaining if it's already there.
|
||||
|
||||
@param dir The directory name.
|
||||
@param perms One of the stat.S_ constants.
|
||||
@param enforcePermissions Enforce our ownership and the given permissions,
|
||||
even if the directory pre-existed with different ones.
|
||||
"""
|
||||
# Catch the exception here, rather than checking for the directory's
|
||||
# existence first, to avoid races.
|
||||
try:
|
||||
os.makedirs(dir, perms)
|
||||
except OSError, exn:
|
||||
if exn.args[0] != errno.EEXIST or not os.path.isdir(dir):
|
||||
raise
|
||||
if enforcePermissions:
|
||||
os.chown(dir, os.geteuid(), os.getegid())
|
||||
os.chmod(dir, stat.S_IRWXU)
|
||||
@@ -30,6 +30,8 @@ from SimpleXMLRPCServer import SimpleXMLRPCServer, SimpleXMLRPCRequestHandler
|
||||
import SocketServer
|
||||
import xmlrpclib, socket, os, stat
|
||||
|
||||
import mkdir
|
||||
|
||||
from xen.web import connection
|
||||
from xen.xend.XendLogging import log
|
||||
|
||||
@@ -234,14 +236,9 @@ class UnixXMLRPCServer(TCPXMLRPCServer):
|
||||
address_family = socket.AF_UNIX
|
||||
|
||||
def __init__(self, addr, allowed, logRequests = 1):
|
||||
parent = os.path.dirname(addr)
|
||||
if os.path.exists(parent):
|
||||
os.chown(parent, os.geteuid(), os.getegid())
|
||||
os.chmod(parent, stat.S_IRWXU)
|
||||
if self.allow_reuse_address and os.path.exists(addr):
|
||||
os.unlink(addr)
|
||||
else:
|
||||
os.makedirs(parent, stat.S_IRWXU)
|
||||
mkdir.parents(os.path.dirname(addr), stat.S_IRWXU, True)
|
||||
if self.allow_reuse_address and os.path.exists(addr):
|
||||
os.unlink(addr)
|
||||
|
||||
TCPXMLRPCServer.__init__(self, addr, allowed,
|
||||
UnixXMLRPCRequestHandler, logRequests)
|
||||
@@ -264,7 +264,32 @@ class HttpServerRequest(http.HttpRequest):
|
||||
s += x + "/"
|
||||
self.write(' <a href="%s">%s</a>/' % (s, x))
|
||||
self.write("</h1>")
|
||||
|
||||
|
||||
class HttpServerClient:
|
||||
|
||||
def __init__(self, server, sock, addr):
|
||||
self.server = server
|
||||
self.sock = sock
|
||||
self.addr = addr
|
||||
|
||||
def process(self):
|
||||
thread = threading.Thread(target=self.doProcess)
|
||||
thread.setDaemon(True)
|
||||
thread.start()
|
||||
|
||||
def doProcess(self):
|
||||
try:
|
||||
rp = RequestProcessor(self.server, self.sock, self.addr)
|
||||
rp.process()
|
||||
except SystemExit:
|
||||
raise
|
||||
except Exception, ex:
|
||||
print 'HttpServer>processRequest> exception: ', ex
|
||||
try:
|
||||
self.sock.close()
|
||||
except:
|
||||
pass
|
||||
|
||||
class HttpServer:
|
||||
|
||||
backlog = 5
|
||||
@@ -286,8 +311,8 @@ class HttpServer:
|
||||
|
||||
while not self.closed:
|
||||
(sock, addr) = self.accept()
|
||||
self.processRequest(sock, addr)
|
||||
|
||||
cl = HttpServerClient(self, sock, addr)
|
||||
cl.process()
|
||||
|
||||
def stop(self):
|
||||
self.close()
|
||||
@@ -314,19 +339,6 @@ class HttpServer:
|
||||
except:
|
||||
pass
|
||||
|
||||
def processRequest(self, sock, addr):
|
||||
try:
|
||||
rp = RequestProcessor(self, sock, addr)
|
||||
rp.process()
|
||||
except SystemExit:
|
||||
raise
|
||||
except Exception, ex:
|
||||
print 'HttpServer>processRequest> exception: ', ex
|
||||
try:
|
||||
sock.close()
|
||||
except:
|
||||
pass
|
||||
|
||||
def getServerAddr(self):
|
||||
return (socket.gethostname(), self.port)
|
||||
|
||||
|
||||
@@ -22,6 +22,8 @@ import os.path
|
||||
import socket
|
||||
import stat
|
||||
|
||||
from xen.util import mkdir
|
||||
|
||||
import connection
|
||||
|
||||
|
||||
@@ -30,13 +32,9 @@ def bind(path):
|
||||
created such that only the current user may access it."""
|
||||
|
||||
parent = os.path.dirname(path)
|
||||
if os.path.exists(parent):
|
||||
os.chown(parent, os.geteuid(), os.getegid())
|
||||
os.chmod(parent, stat.S_IRWXU)
|
||||
if os.path.exists(path):
|
||||
os.unlink(path)
|
||||
else:
|
||||
os.makedirs(parent, stat.S_IRWXU)
|
||||
mkdir.parents(parent, stat.S_IRWXU, True)
|
||||
if os.path.exists(path):
|
||||
os.unlink(path)
|
||||
|
||||
sock = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
|
||||
sock.bind(path)
|
||||
|
||||
+209
-206
@@ -248,8 +248,8 @@ def valid_sr(func):
|
||||
# Bridge to Legacy XM API calls
|
||||
# -----------------------------
|
||||
|
||||
def do_vm_func(fn_name, vm_ref, *args):
|
||||
"""Helper wrapper func to abstract away from repeative code.
|
||||
def do_vm_func(fn_name, vm_ref, *args, **kwargs):
|
||||
"""Helper wrapper func to abstract away from repetitive code.
|
||||
|
||||
@param fn_name: function name for XendDomain instance
|
||||
@type fn_name: string
|
||||
@@ -260,7 +260,7 @@ def do_vm_func(fn_name, vm_ref, *args):
|
||||
"""
|
||||
xendom = XendDomain.instance()
|
||||
fn = getattr(xendom, fn_name)
|
||||
xendom.do_legacy_api_with_uuid(fn, vm_ref, *args)
|
||||
xendom.do_legacy_api_with_uuid(fn, vm_ref, *args, **kwargs)
|
||||
return xen_api_success_void()
|
||||
|
||||
|
||||
@@ -303,8 +303,8 @@ class XendAPI:
|
||||
# all get_by_uuid() methods.
|
||||
|
||||
for cls in classes.keys():
|
||||
get_by_uuid = '%s_get_by_uuid' % cls.lower()
|
||||
get_uuid = '%s_get_uuid' % cls.lower()
|
||||
get_by_uuid = '%s_get_by_uuid' % cls
|
||||
get_uuid = '%s_get_uuid' % cls
|
||||
setattr(XendAPI, get_by_uuid,
|
||||
lambda s, sess, obj_ref: xen_api_success(obj_ref))
|
||||
setattr(XendAPI, get_uuid,
|
||||
@@ -327,7 +327,7 @@ class XendAPI:
|
||||
|
||||
# wrap validators around readable class attributes
|
||||
for attr_name in ro_attrs + rw_attrs + self.Base_attr_ro:
|
||||
getter_name = '%s_get_%s' % (cls.lower(), attr_name.lower())
|
||||
getter_name = '%s_get_%s' % (cls, attr_name)
|
||||
try:
|
||||
getter = getattr(XendAPI, getter_name)
|
||||
for validator in validators:
|
||||
@@ -340,7 +340,7 @@ class XendAPI:
|
||||
|
||||
# wrap validators around writable class attrributes
|
||||
for attr_name in rw_attrs + self.Base_attr_rw:
|
||||
setter_name = '%s_set_%s' % (cls.lower(), attr_name.lower())
|
||||
setter_name = '%s_set_%s' % (cls, attr_name)
|
||||
try:
|
||||
setter = getattr(XendAPI, setter_name)
|
||||
for validator in validators:
|
||||
@@ -353,7 +353,8 @@ class XendAPI:
|
||||
|
||||
# wrap validators around methods
|
||||
for method_name in methods + self.Base_methods:
|
||||
method_full_name = '%s_%s' % (cls.lower(),method_name.lower())
|
||||
method_full_name = '%s_%s' % (cls, method_name)
|
||||
|
||||
try:
|
||||
method = getattr(XendAPI, method_full_name)
|
||||
for validator in validators:
|
||||
@@ -366,7 +367,7 @@ class XendAPI:
|
||||
|
||||
# wrap validators around class functions
|
||||
for func_name in funcs + self.Base_funcs:
|
||||
func_full_name = '%s_%s' % (cls.lower(), func_name.lower())
|
||||
func_full_name = '%s_%s' % (cls, func_name)
|
||||
try:
|
||||
method = getattr(XendAPI, func_full_name)
|
||||
method = session_required(method)
|
||||
@@ -379,7 +380,7 @@ class XendAPI:
|
||||
|
||||
Base_attr_ro = ['uuid']
|
||||
Base_attr_rw = []
|
||||
Base_methods = ['destroy', 'to_XML', 'get_record']
|
||||
Base_methods = ['destroy', 'get_record']
|
||||
Base_funcs = ['create', 'get_by_uuid', 'get_all']
|
||||
|
||||
# Xen API: Class Session
|
||||
@@ -411,8 +412,6 @@ class XendAPI:
|
||||
record = {'this_host': XendNode.instance().uuid,
|
||||
'this_user': auth_manager().get_user(session)}
|
||||
return xen_api_success(record)
|
||||
def session_to_xml(self, session):
|
||||
return xen_api_todo()
|
||||
|
||||
# attributes (ro)
|
||||
def session_get_this_host(self, session):
|
||||
@@ -536,8 +535,6 @@ class XendAPI:
|
||||
'features': node.get_host_cpu_features(host_cpu_ref),
|
||||
'utilisation': node.get_host_cpu_load(host_cpu_ref)}
|
||||
return xen_api_success(record)
|
||||
def host_cpu_to_xml(self, session, host_cpu_ref):
|
||||
return xen_api_todo()
|
||||
|
||||
# class methods
|
||||
def host_cpu_get_all(self, session):
|
||||
@@ -586,7 +583,7 @@ class XendAPI:
|
||||
'VCPUs_policy',
|
||||
'VCPUs_params',
|
||||
'VCPUs_features_force_on',
|
||||
'VCPUS_features_force_off',
|
||||
'VCPUs_features_force_off',
|
||||
'actions_after_shutdown',
|
||||
'actions_after_reboot',
|
||||
'actions_after_suspend',
|
||||
@@ -656,304 +653,302 @@ class XendAPI:
|
||||
'otherConfig']
|
||||
|
||||
# attributes (ro)
|
||||
def vm_get_power_state(self, session, vm_ref):
|
||||
def VM_get_power_state(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.state)
|
||||
|
||||
def vm_get_resident_on(self, session, vm_ref):
|
||||
def VM_get_resident_on(self, session, vm_ref):
|
||||
return xen_api_success(XendNode.instance().uuid)
|
||||
|
||||
def vm_get_memory_actual(self, session, vm_ref):
|
||||
def VM_get_memory_actual(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo() # unsupported by xc
|
||||
|
||||
def vm_get_memory_static_max(self, session, vm_ref):
|
||||
def VM_get_memory_static_max(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_memory_static_max())
|
||||
|
||||
def vm_get_memory_static_min(self, session, vm_ref):
|
||||
def VM_get_memory_static_min(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_memory_static_min())
|
||||
|
||||
def vm_get_VCPUs_number(self, session, vm_ref):
|
||||
def VM_get_VCPUs_number(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.getVCpuCount())
|
||||
|
||||
def vm_get_VCPUs_utilisation(self, session, vm_ref):
|
||||
def VM_get_VCPUs_utilisation(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_vcpus_util())
|
||||
|
||||
def vm_get_VCPUs_features_required(self, session, vm_ref):
|
||||
def VM_get_VCPUs_features_required(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo() # unsupported by xc
|
||||
|
||||
def vm_get_VCPUs_can_use(self, session, vm_ref):
|
||||
def VM_get_VCPUs_can_use(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo() # unsupported by xc
|
||||
|
||||
def vm_get_VIFs(self, session, vm_ref):
|
||||
def VM_get_VIFs(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_vifs())
|
||||
|
||||
def vm_get_VBDs(self, session, vm_ref):
|
||||
def VM_get_VBDs(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_vbds())
|
||||
|
||||
def vm_get_VTPMs(self, session, vm_ref):
|
||||
def VM_get_VTPMs(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_vtpms())
|
||||
|
||||
def vm_get_PCI_bus(self, session, vm_ref):
|
||||
def VM_get_PCI_bus(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo() # unsupported by xc
|
||||
|
||||
def vm_get_tools_version(self, session, vm_ref):
|
||||
def VM_get_tools_version(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
# attributes (rw)
|
||||
def vm_get_name_label(self, session, vm_ref):
|
||||
def VM_get_name_label(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.getName())
|
||||
|
||||
def vm_get_name_description(self, session, vm_ref):
|
||||
def VM_get_name_description(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_user_version(self, session, vm_ref):
|
||||
def VM_get_user_version(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_is_a_template(self, session, vm_ref):
|
||||
def VM_get_is_a_template(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_memory_dynamic_max(self, session, vm_ref):
|
||||
def VM_get_memory_dynamic_max(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
return xen_api_success(dom.get_memory_dynamic_max())
|
||||
|
||||
def vm_get_memory_dynamic_min(self, session, vm_ref):
|
||||
def VM_get_memory_dynamic_min(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
return xen_api_success(dom.get_memory_dynamic_min())
|
||||
|
||||
def vm_get_VCPUs_policy(self, session, vm_ref):
|
||||
def VM_get_VCPUs_policy(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo() # need to access scheduler
|
||||
|
||||
def vm_get_VCPUs_params(self, session, vm_ref):
|
||||
def VM_get_VCPUs_params(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo() # need access to scheduler
|
||||
|
||||
def vm_get_VCPUs_features_force_on(self, session, vm_ref):
|
||||
def VM_get_VCPUs_features_force_on(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_VCPUs_features_force_off(self, session, vm_ref):
|
||||
def VM_get_VCPUs_features_force_off(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_actions_after_shutdown(self, session, vm_ref):
|
||||
def VM_get_actions_after_shutdown(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_on_shutdown())
|
||||
|
||||
def vm_get_actions_after_reboot(self, session, vm_ref):
|
||||
def VM_get_actions_after_reboot(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_on_reboot())
|
||||
|
||||
def vm_get_actions_after_suspend(self, session, vm_ref):
|
||||
def VM_get_actions_after_suspend(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_on_suspend())
|
||||
|
||||
def vm_get_actions_after_crash(self, session, vm_ref):
|
||||
def VM_get_actions_after_crash(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_on_crash())
|
||||
|
||||
def vm_get_bios_boot(self, session, vm_ref):
|
||||
def VM_get_bios_boot(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_bios_boot())
|
||||
|
||||
def vm_get_platform_std_VGA(self, session, vm_ref):
|
||||
def VM_get_platform_std_VGA(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_platform_serial(self, session, vm_ref):
|
||||
def VM_get_platform_serial(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_platform_localtime(self, session, vm_ref):
|
||||
def VM_get_platform_localtime(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_platform_clock_offset(self, session, vm_ref):
|
||||
def VM_get_platform_clock_offset(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_platform_enable_audio(self, session, vm_ref):
|
||||
def VM_get_platform_enable_audio(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_platform_keymap(self, session, vm_ref):
|
||||
def VM_get_platform_keymap(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_builder(self, session, vm_ref):
|
||||
def VM_get_builder(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
return xen_api_success(dom.get_builder())
|
||||
|
||||
def vm_get_boot_method(self, session, vm_ref):
|
||||
def VM_get_boot_method(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success(dom.get_boot_method())
|
||||
|
||||
def VM_get_kernel_kernel(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success('')
|
||||
|
||||
def vm_get_kernel_kernel(self, session, vm_ref):
|
||||
def VM_get_kernel_initrd(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success('')
|
||||
|
||||
def vm_get_kernel_initrd(self, session, vm_ref):
|
||||
def VM_get_kernel_args(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success('')
|
||||
|
||||
def vm_get_kernel_args(self, session, vm_ref):
|
||||
def VM_get_grub_cmdline(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success('')
|
||||
|
||||
def vm_get_grub_cmdline(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success('')
|
||||
|
||||
def vm_get_otherConfig(self, session, vm_ref):
|
||||
def VM_get_otherConfig(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_set_name_label(self, session, vm_ref):
|
||||
def VM_set_name_label(self, session, vm_ref, label):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
dom.setName(label)
|
||||
return xen_api_success_void()
|
||||
|
||||
def VM_set_name_description(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_name_description(self, session, vm_ref):
|
||||
def VM_set_user_version(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_user_version(self, session, vm_ref):
|
||||
def VM_set_is_a_template(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_is_a_template(self, session, vm_ref):
|
||||
def VM_set_memory_dynamic_max(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_memory_dynamic_max(self, session, vm_ref):
|
||||
def VM_set_memory_dynamic_min(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_memory_dynamic_min(self, session, vm_ref):
|
||||
def VM_set_VCPUs_policy(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_vcpus_policy(self, session, vm_ref):
|
||||
def VM_set_VCPUs_params(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_vcpus_params(self, session, vm_ref):
|
||||
def VM_set_VCPUs_features_force_on(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_vcpus_features_force_on(self, session, vm_ref):
|
||||
def VM_set_VCPUs_features_force_off(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_vcpus_features_force_off(self, session, vm_ref):
|
||||
def VM_set_actions_after_shutdown(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_actions_after_shutdown(self, session, vm_ref):
|
||||
def VM_set_actions_after_reboot(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_actions_after_reboot(self, session, vm_ref):
|
||||
def VM_set_actions_after_suspend(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_actions_after_suspend(self, session, vm_ref):
|
||||
def VM_set_actions_after_crash(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_actions_after_crash(self, session, vm_ref):
|
||||
def VM_set_bios_boot(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_bios_boot(self, session, vm_ref):
|
||||
def VM_set_platform_std_VGA(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_platform_std_VGA(self, session, vm_ref):
|
||||
def VM_set_platform_serial(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_platform_serial(self, session, vm_ref):
|
||||
def VM_set_platform_localtime(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_platform_localtime(self, session, vm_ref):
|
||||
def VM_set_platform_clock_offset(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_platform_clock_offset(self, session, vm_ref):
|
||||
def VM_set_platform_enable_audio(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_platform_enable_audio(self, session, vm_ref):
|
||||
def VM_set_builder(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_builder(self, session, vm_ref):
|
||||
def VM_set_boot_method(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_boot_method(self, session, vm_ref):
|
||||
def VM_set_kernel_kernel(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_kernel_kernel(self, session, vm_ref):
|
||||
def VM_set_kernel_initrd(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_kernel_initrd(self, session, vm_ref):
|
||||
def VM_set_kernel_args(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_kernel_args(self, session, vm_ref):
|
||||
def VM_set_grub_cmdline(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_grub_cmdline(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vm_set_otherConfig(self, session, vm_ref):
|
||||
def VM_set_otherConfig(self, session, vm_ref):
|
||||
dom = XendDomain.instance().get_vm_by_uuid(vm_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
# class methods
|
||||
def vm_get_all(self, session):
|
||||
refs = [d.get_uuid() for d in XendDomain.instance().list()]
|
||||
def VM_get_all(self, session):
|
||||
refs = [d.get_uuid() for d in XendDomain.instance().list('all')]
|
||||
return xen_api_success(refs)
|
||||
|
||||
def vm_get_by_name_label(self, session, label):
|
||||
def VM_get_by_name_label(self, session, label):
|
||||
xendom = XendDomain.instance()
|
||||
dom = xendom.domain_lookup_nr(label)
|
||||
if dom:
|
||||
return xen_api_success([dom.get_uuid()])
|
||||
return xen_api_error(XEND_ERROR_VM_INVALID)
|
||||
|
||||
def vm_create(self, session, vm_struct):
|
||||
def VM_create(self, session, vm_struct):
|
||||
xendom = XendDomain.instance()
|
||||
domuuid = xendom.create_domain(vm_struct)
|
||||
return xen_api_success(domuuid)
|
||||
|
||||
# object methods
|
||||
def vm_to_xml(self, session, vm_ref):
|
||||
return xen_api_todo()
|
||||
|
||||
def vm_get_record(self, session, vm_ref):
|
||||
def VM_get_record(self, session, vm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
xeninfo = xendom.get_vm_by_uuid(vm_ref)
|
||||
if not xeninfo:
|
||||
@@ -969,17 +964,17 @@ class XendAPI:
|
||||
'resident_on': XendNode.instance().uuid,
|
||||
'memory_static_min': xeninfo.get_memory_static_min(),
|
||||
'memory_static_max': xeninfo.get_memory_static_max(),
|
||||
'memory_dynamic_min': xeninfo.get_memory_static_min(),
|
||||
'memory_dynamic_max': xeninfo.get_memory_static_max(),
|
||||
'memory_dynamic_min': xeninfo.get_memory_dynamic_min(),
|
||||
'memory_dynamic_max': xeninfo.get_memory_dynamic_max(),
|
||||
'memory_actual': xeninfo.get_memory_static_min(),
|
||||
'vcpus_policy': xeninfo.get_vcpus_policy(),
|
||||
'vcpus_params': xeninfo.get_vcpus_params(),
|
||||
'vcpus_number': xeninfo.getVCpuCount(),
|
||||
'vcpus_utilisation': xeninfo.get_vcpus_util(),
|
||||
'vcpus_features_required': [],
|
||||
'vcpus_features_can_use': [],
|
||||
'vcpus_features_force_on': [],
|
||||
'vcpus_features_force_off': [],
|
||||
'VCPUs_policy': xeninfo.get_vcpus_policy(),
|
||||
'VCPUs_params': xeninfo.get_vcpus_params(),
|
||||
'VCPUs_number': xeninfo.getVCpuCount(),
|
||||
'VCPUs_utilisation': xeninfo.get_vcpus_util(),
|
||||
'VCPUs_features_required': [],
|
||||
'VCPUs_features_can_use': [],
|
||||
'VCPUs_features_force_on': [],
|
||||
'VCPUs_features_force_off': [],
|
||||
'actions_after_shutdown': xeninfo.get_on_shutdown(),
|
||||
'actions_after_reboot': xeninfo.get_on_reboot(),
|
||||
'actions_after_suspend': xeninfo.get_on_suspend(),
|
||||
@@ -1006,45 +1001,43 @@ class XendAPI:
|
||||
}
|
||||
return xen_api_success(record)
|
||||
|
||||
def vm_clean_reboot(self, session, vm_ref):
|
||||
def VM_clean_reboot(self, session, vm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
xeninfo = xendom.get_vm_by_uuid(vm_ref)
|
||||
xeninfo.shutdown("reboot")
|
||||
return xen_api_success_void()
|
||||
def vm_clean_shutdown(self, session, vm_ref):
|
||||
def VM_clean_shutdown(self, session, vm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
xeninfo = xendom.get_vm_by_uuid(vm_ref)
|
||||
xeninfo.shutdown("poweroff")
|
||||
return xen_api_success_void()
|
||||
def vm_clone(self, session, vm_ref):
|
||||
def VM_clone(self, session, vm_ref):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
def vm_destroy(self, session, vm_ref):
|
||||
def VM_destroy(self, session, vm_ref):
|
||||
return do_vm_func("domain_delete", vm_ref)
|
||||
def vm_hard_reboot(self, session, vm_ref):
|
||||
def VM_hard_reboot(self, session, vm_ref):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
def vm_hard_shutdown(self, session, vm_ref):
|
||||
def VM_hard_shutdown(self, session, vm_ref):
|
||||
return do_vm_func("domain_destroy", vm_ref)
|
||||
def vm_pause(self, session, vm_ref):
|
||||
def VM_pause(self, session, vm_ref):
|
||||
return do_vm_func("domain_pause", vm_ref)
|
||||
def vm_resume(self, session, vm_ref, start_paused):
|
||||
return do_vm_func("domain_resume", vm_ref)
|
||||
def vm_start(self, session, vm_ref):
|
||||
return do_vm_func("domain_start", vm_ref)
|
||||
def vm_suspend(self, session, vm_ref):
|
||||
def VM_resume(self, session, vm_ref, start_paused):
|
||||
return do_vm_func("domain_resume", vm_ref, start_paused = start_paused)
|
||||
def VM_start(self, session, vm_ref, start_paused):
|
||||
return do_vm_func("domain_start", vm_ref, start_paused = start_paused)
|
||||
def VM_suspend(self, session, vm_ref):
|
||||
return do_vm_func("domain_suspend", vm_ref)
|
||||
def vm_unpause(self, session, vm_ref):
|
||||
def VM_unpause(self, session, vm_ref):
|
||||
return do_vm_func("domain_unpause", vm_ref)
|
||||
|
||||
# Xen API: Class VDI
|
||||
# ----------------------------------------------------------------
|
||||
# TODO: NOT IMPLEMENTED.
|
||||
|
||||
# Xen API: Class VBD
|
||||
# ----------------------------------------------------------------
|
||||
# Note: accepts a non-API standard 'image' attribute to emulate
|
||||
# regular xm created VBDs
|
||||
|
||||
VBD_attr_ro = ['image',
|
||||
'IO_bandwidth_incoming_kbs',
|
||||
'IO_bandwidth_outgoing_kbs']
|
||||
'io_read_kbs',
|
||||
'io_write_kbs']
|
||||
VBD_attr_rw = ['VM',
|
||||
'VDI',
|
||||
'device',
|
||||
@@ -1053,8 +1046,10 @@ class XendAPI:
|
||||
|
||||
VBD_attr_inst = VBD_attr_rw + ['image']
|
||||
|
||||
VBD_methods = ['media_change']
|
||||
|
||||
# object methods
|
||||
def vbd_get_record(self, session, vbd_ref):
|
||||
def VBD_get_record(self, session, vbd_ref):
|
||||
xendom = XendDomain.instance()
|
||||
vm = xendom.get_vm_with_dev_uuid('vbd', vbd_ref)
|
||||
if not vm:
|
||||
@@ -1062,10 +1057,22 @@ class XendAPI:
|
||||
cfg = vm.get_dev_xenapi_config('vbd', vbd_ref)
|
||||
if not cfg:
|
||||
return xen_api_error(XEND_ERROR_VBD_INVALID)
|
||||
return xen_api_success(cfg)
|
||||
|
||||
|
||||
valid_vbd_keys = self.VBD_attr_ro + self.VBD_attr_rw + \
|
||||
self.Base_attr_ro + self.Base_attr_rw
|
||||
|
||||
return_cfg = {}
|
||||
for k in cfg.keys():
|
||||
if k in valid_vbd_keys:
|
||||
return_cfg[k] = cfg[k]
|
||||
|
||||
return xen_api_success(return_cfg)
|
||||
|
||||
def VBD_media_change(self, session, vbd_ref, vdi_ref):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
|
||||
# class methods
|
||||
def vbd_create(self, session, vbd_struct):
|
||||
def VBD_create(self, session, vbd_struct):
|
||||
xendom = XendDomain.instance()
|
||||
if not xendom.is_valid_vm(vbd_struct['VM']):
|
||||
return xen_api_error(XEND_ERROR_DOMAIN_INVALID)
|
||||
@@ -1092,22 +1099,22 @@ class XendAPI:
|
||||
return xen_api_success(vbd_ref)
|
||||
|
||||
# attributes (rw)
|
||||
def vbd_get_vm(self, session, vbd_ref):
|
||||
def VBD_get_VM(self, session, vbd_ref):
|
||||
xendom = XendDomain.instance()
|
||||
return xen_api_success(xendom.get_dev_property('vbd', vbd_ref, 'VM'))
|
||||
|
||||
def vbd_get_vdi(self, session, vbd_ref):
|
||||
def VBD_get_VDI(self, session, vbd_ref):
|
||||
return xen_api_todo()
|
||||
|
||||
def vbd_get_device(self, session, vbd_ref):
|
||||
def VBD_get_device(self, session, vbd_ref):
|
||||
xendom = XendDomain.instance()
|
||||
return xen_api_success(xendom.get_dev_property('vbd', vbd_ref,
|
||||
'device'))
|
||||
def vbd_get_mode(self, session, vbd_ref):
|
||||
def VBD_get_mode(self, session, vbd_ref):
|
||||
xendom = XendDomain.instance()
|
||||
return xen_api_success(xendom.get_dev_property('vbd', vbd_ref,
|
||||
'mode'))
|
||||
def vbd_get_driver(self, session, vbd_ref):
|
||||
def VBD_get_driver(self, session, vbd_ref):
|
||||
xendom = XendDomain.instance()
|
||||
return xen_api_success(xendom.get_dev_property('vbd', vbd_ref,
|
||||
'driver'))
|
||||
@@ -1115,10 +1122,8 @@ class XendAPI:
|
||||
# Xen API: Class VIF
|
||||
# ----------------------------------------------------------------
|
||||
|
||||
VIF_attr_ro = ['network_read_kbs',
|
||||
'network_write_kbs',
|
||||
'IO_bandwidth_incoming_kbs',
|
||||
'IO_bandwidth_outgoing_kbs']
|
||||
VIF_attr_ro = ['io_read_kbs',
|
||||
'io_write_kbs']
|
||||
VIF_attr_rw = ['name',
|
||||
'type',
|
||||
'device',
|
||||
@@ -1130,7 +1135,7 @@ class XendAPI:
|
||||
VIF_attr_inst = VIF_attr_rw
|
||||
|
||||
# object methods
|
||||
def vif_get_record(self, session, vif_ref):
|
||||
def VIF_get_record(self, session, vif_ref):
|
||||
xendom = XendDomain.instance()
|
||||
vm = xendom.get_vm_with_dev_uuid('vif', vif_ref)
|
||||
if not vm:
|
||||
@@ -1138,16 +1143,19 @@ class XendAPI:
|
||||
cfg = vm.get_dev_xenapi_config('vif', vif_ref)
|
||||
if not cfg:
|
||||
return xen_api_error(XEND_ERROR_VIF_INVALID)
|
||||
|
||||
valid_vif_keys = self.VIF_attr_ro + self.VIF_attr_rw + \
|
||||
self.Base_attr_ro + self.Base_attr_rw
|
||||
|
||||
return_cfg = {}
|
||||
for k in cfg.keys():
|
||||
if k not in valid_vif_keys:
|
||||
del cfg[k]
|
||||
if k in valid_vif_keys:
|
||||
return_cfg[k] = cfg[k]
|
||||
|
||||
return xen_api_success(cfg)
|
||||
return xen_api_success(return_cfg)
|
||||
|
||||
# class methods
|
||||
def vif_create(self, session, vif_struct):
|
||||
def VIF_create(self, session, vif_struct):
|
||||
xendom = XendDomain.instance()
|
||||
if xendom.is_valid_vm(vif_struct['VM']):
|
||||
dom = xendom.get_vm_by_uuid(vif_struct['VM'])
|
||||
@@ -1180,99 +1188,96 @@ class XendAPI:
|
||||
VDI_methods = ['snapshot']
|
||||
VDI_funcs = ['get_by_name_label']
|
||||
|
||||
def vdi_get_VBDs(self, session, vdi_ref):
|
||||
def VDI_get_VBDs(self, session, vdi_ref):
|
||||
return xen_api_todo()
|
||||
|
||||
def vdi_get_physical_utilisation(self, session, vdi_ref):
|
||||
def VDI_get_physical_utilisation(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.get_physical_utilisation())
|
||||
|
||||
def vdi_get_sector_size(self, session, vdi_ref):
|
||||
def VDI_get_sector_size(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.sector_size)
|
||||
|
||||
def vdi_get_type(self, session, vdi_ref):
|
||||
def VDI_get_type(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.type)
|
||||
|
||||
def vdi_get_parent(self, session, vdi_ref):
|
||||
def VDI_get_parent(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.parent)
|
||||
|
||||
def vdi_get_children(self, session, vdi_ref):
|
||||
def VDI_get_children(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.children)
|
||||
|
||||
def vdi_get_name_label(self, session, vdi_ref):
|
||||
def VDI_get_name_label(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.name_label)
|
||||
|
||||
def vdi_get_name_description(self, session, vdi_ref):
|
||||
def VDI_get_name_description(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.name_description)
|
||||
|
||||
def vdi_get_sr(self, session, vdi_ref):
|
||||
def VDI_get_SR(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.uuid)
|
||||
|
||||
def vdi_get_virtual_size(self, session, vdi_ref):
|
||||
def VDI_get_virtual_size(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.virtual_size)
|
||||
|
||||
def vdi_get_sharable(self, session, vdi_ref):
|
||||
def VDI_get_sharable(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.sharable)
|
||||
|
||||
def vdi_get_read_only(self, session, vdi_ref):
|
||||
def VDI_get_read_only(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
return xen_api_success(image.sharable)
|
||||
|
||||
def vdi_set_name_label(self, session, vdi_ref, value):
|
||||
def VDI_set_name_label(self, session, vdi_ref, value):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
image.name_label = value
|
||||
return xen_api_success_void()
|
||||
|
||||
def vdi_set_name_description(self, session, vdi_ref, value):
|
||||
def VDI_set_name_description(self, session, vdi_ref, value):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
image.name_description = value
|
||||
return xen_api_success_void()
|
||||
|
||||
def vdi_set_sr(self, session, vdi_ref, value):
|
||||
def VDI_set_SR(self, session, vdi_ref, value):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
|
||||
def vdi_set_virtual_size(self, session, vdi_ref, value):
|
||||
def VDI_set_virtual_size(self, session, vdi_ref, value):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
|
||||
def vdi_set_sharable(self, session, vdi_ref, value):
|
||||
def VDI_set_sharable(self, session, vdi_ref, value):
|
||||
return xen_api_todo()
|
||||
def vdi_set_read_only(self, session, vdi_ref, value):
|
||||
def VDI_set_read_only(self, session, vdi_ref, value):
|
||||
return xen_api_todo()
|
||||
|
||||
# Object Methods
|
||||
def vdi_snapshot(self, session, vdi_ref):
|
||||
def VDI_snapshot(self, session, vdi_ref):
|
||||
return xen_api_todo()
|
||||
|
||||
def vdi_destroy(self, session, vdi_ref):
|
||||
def VDI_destroy(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
sr.destroy_image(vdi_ref)
|
||||
return xen_api_success_void()
|
||||
|
||||
def vdi_to_xml(self, session, vdi_ref):
|
||||
return xen_api_todo()
|
||||
|
||||
def vdi_get_record(self, session, vdi_ref):
|
||||
def VDI_get_record(self, session, vdi_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image = sr.xen_api_get_by_uuid(vdi_ref)
|
||||
if image:
|
||||
@@ -1295,7 +1300,7 @@ class XendAPI:
|
||||
return xen_api_error(XEND_ERROR_VDI_INVALID)
|
||||
|
||||
# Class Functions
|
||||
def vdi_create(self, session, vdi_struct):
|
||||
def VDI_create(self, session, vdi_struct):
|
||||
sr = XendNode.instance().get_sr()
|
||||
sr_ref = vdi_struct['SR']
|
||||
if sr.uuid != sr_ref:
|
||||
@@ -1304,11 +1309,11 @@ class XendAPI:
|
||||
vdi_uuid = sr.create_image(vdi_struct)
|
||||
return xen_api_success(vdi_uuid)
|
||||
|
||||
def vdi_get_all(self, session):
|
||||
def VDI_get_all(self, session):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.list_images())
|
||||
|
||||
def vdi_get_by_name_label(self, session, name):
|
||||
def VDI_get_by_name_label(self, session, name):
|
||||
sr = XendNode.instance().get_sr()
|
||||
image_uuid = sr.xen_api_get_by_name_label(name)
|
||||
if image_uuid:
|
||||
@@ -1329,7 +1334,7 @@ class XendAPI:
|
||||
VTPM_attr_inst = VTPM_attr_rw
|
||||
|
||||
# object methods
|
||||
def vtpm_get_record(self, session, vtpm_ref):
|
||||
def VTPM_get_record(self, session, vtpm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
vm = xendom.get_vm_with_dev_uuid('vtpm', vtpm_ref)
|
||||
if not vm:
|
||||
@@ -1346,7 +1351,7 @@ class XendAPI:
|
||||
return xen_api_success(cfg)
|
||||
|
||||
# Class Functions
|
||||
def vtpm_get_instance(self, session, vtpm_ref):
|
||||
def VTPM_get_instance(self, session, vtpm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
vm = xendom.get_vm_with_dev_uuid('vtpm', vtpm_ref)
|
||||
if not vm:
|
||||
@@ -1360,7 +1365,7 @@ class XendAPI:
|
||||
instance = -1
|
||||
return xen_api_success(instance)
|
||||
|
||||
def vtpm_get_driver(self, session, vtpm_ref):
|
||||
def VTPM_get_driver(self, session, vtpm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
vm = xendom.get_vm_with_dev_uuid('vtpm', vtpm_ref)
|
||||
if not vm:
|
||||
@@ -1374,7 +1379,7 @@ class XendAPI:
|
||||
driver = "Unknown"
|
||||
return xen_api_success(driver)
|
||||
|
||||
def vtpm_get_backend(self, session, vtpm_ref):
|
||||
def VTPM_get_backend(self, session, vtpm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
vm = xendom.get_vm_with_dev_uuid('vtpm', vtpm_ref)
|
||||
if not vm:
|
||||
@@ -1388,12 +1393,12 @@ class XendAPI:
|
||||
backend = "Domain-0"
|
||||
return xen_api_success(backend)
|
||||
|
||||
def vtpm_get_VM(self, session, vtpm_ref):
|
||||
def VTPM_get_VM(self, session, vtpm_ref):
|
||||
xendom = XendDomain.instance()
|
||||
return xen_api_success(xendom.get_dev_property('vtpm', vtpm_ref, 'VM'))
|
||||
|
||||
# class methods
|
||||
def vtpm_create(self, session, vtpm_struct):
|
||||
def VTPM_create(self, session, vtpm_struct):
|
||||
xendom = XendDomain.instance()
|
||||
if xendom.is_valid_vm(vtpm_struct['VM']):
|
||||
dom = xendom.get_vm_by_uuid(vtpm_struct['VM'])
|
||||
@@ -1429,32 +1434,30 @@ class XendAPI:
|
||||
SR_funcs = ['get_by_name_label']
|
||||
|
||||
# Class Functions
|
||||
def sr_get_all(self, session):
|
||||
def SR_get_all(self, session):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success([sr.uuid])
|
||||
|
||||
def sr_get_by_name_label(self, session, label):
|
||||
def SR_get_by_name_label(self, session, label):
|
||||
sr = XendNode.instance().get_sr()
|
||||
if sr.name_label != label:
|
||||
return xen_api_error(XEND_ERROR_SR_INVALID)
|
||||
return xen_api_success([sr.uuid])
|
||||
|
||||
def sr_create(self, session):
|
||||
def SR_create(self, session):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
|
||||
def sr_get_by_uuid(self, session):
|
||||
def SR_get_by_uuid(self, session):
|
||||
return xen_api_success(XendNode.instance().get_sr().uuid)
|
||||
|
||||
# Class Methods
|
||||
def sr_clone(self, session, sr_ref):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
def sr_destroy(self, session, sr_ref):
|
||||
def SR_clone(self, session, sr_ref):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
|
||||
def sr_to_xml(self, session, sr_ref):
|
||||
return xen_api_todo()
|
||||
def SR_destroy(self, session, sr_ref):
|
||||
return xen_api_error(XEND_ERROR_UNSUPPORTED)
|
||||
|
||||
def sr_get_record(self, session, sr_ref):
|
||||
def SR_get_record(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success({
|
||||
'uuid': sr.uuid,
|
||||
@@ -1469,44 +1472,44 @@ class XendAPI:
|
||||
})
|
||||
|
||||
# Attribute acceess
|
||||
def sr_get_vdis(self, session, sr_ref):
|
||||
def SR_get_VDIs(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.list_images())
|
||||
|
||||
def sr_get_virtual_allocation(self, session, sr_ref):
|
||||
def SR_get_virtual_allocation(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return sr.used_space_bytes()
|
||||
|
||||
def sr_get_physical_utilisation(self, session, sr_ref):
|
||||
def SR_get_physical_utilisation(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return sr.used_space_bytes()
|
||||
|
||||
def sr_get_physical_size(self, session, sr_ref):
|
||||
def SR_get_physical_size(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return sr.total_space_bytes()
|
||||
|
||||
def sr_get_type(self, session, sr_ref):
|
||||
def SR_get_type(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.type)
|
||||
|
||||
def sr_get_location(self, session, sr_ref):
|
||||
def SR_get_location(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.location)
|
||||
|
||||
def sr_get_name_label(self, session, sr_ref):
|
||||
def SR_get_name_label(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.name_label)
|
||||
|
||||
def sr_get_name_description(self, session, sr_ref):
|
||||
def SR_get_name_description(self, session, sr_ref):
|
||||
sr = XendNode.instance().get_sr()
|
||||
return xen_api_success(sr.name_description)
|
||||
|
||||
def sr_set_name_label(self, session, sr_ref, value):
|
||||
def SR_set_name_label(self, session, sr_ref, value):
|
||||
sr = XendNode.instance().get_sr()
|
||||
sr.name_label = value
|
||||
return xen_api_success_void()
|
||||
|
||||
def sr_set_name_description(self, session, sr_ref, value):
|
||||
def SR_set_name_description(self, session, sr_ref, value):
|
||||
sr = XendNode.instance().get_sr()
|
||||
sr.name_description = value
|
||||
return xen_api_success_void()
|
||||
@@ -1525,24 +1528,24 @@ if __name__ == "__main__":
|
||||
methods = getattr(XendAPI, '%s_methods' % cls, [])
|
||||
funcs = getattr(XendAPI, '%s_funcs' % cls, [])
|
||||
|
||||
ref = '%s_ref' % cls.lower()
|
||||
ref = '%s_ref' % cls
|
||||
|
||||
for attr_name in ro_attrs + rw_attrs + XendAPI.Base_attr_ro:
|
||||
getter_name = '%s_get_%s' % (cls.lower(), attr_name.lower())
|
||||
getter_name = '%s_get_%s' % (cls, attr_name)
|
||||
output('def %s(self, session, %s):' % (getter_name, ref))
|
||||
output(' return xen_api_todo()')
|
||||
|
||||
for attr_name in rw_attrs + XendAPI.Base_attr_rw:
|
||||
setter_name = '%s_set_%s' % (cls.lower(), attr_name.lower())
|
||||
setter_name = '%s_set_%s' % (cls, attr_name)
|
||||
output('def %s(self, session, %s, value):' % (setter_name, ref))
|
||||
output(' return xen_api_todo()')
|
||||
|
||||
for method_name in methods + XendAPI.Base_methods:
|
||||
method_full_name = '%s_%s' % (cls.lower(),method_name.lower())
|
||||
method_full_name = '%s_%s' % (cls,method_name)
|
||||
output('def %s(self, session, %s):' % (method_full_name, ref))
|
||||
output(' return xen_api_todo()')
|
||||
|
||||
for func_name in funcs + XendAPI.Base_funcs:
|
||||
func_full_name = '%s_%s' % (cls.lower(), func_name.lower())
|
||||
func_full_name = '%s_%s' % (cls, func_name)
|
||||
output('def %s(self, session):' % func_full_name)
|
||||
output(' return xen_api_todo()')
|
||||
@@ -55,7 +55,7 @@ class XendAuthSessions:
|
||||
@return: Session UUID
|
||||
"""
|
||||
if self.is_authorized(username, password):
|
||||
return login_unconditionally(username)
|
||||
return self.login_unconditionally(username)
|
||||
|
||||
raise XendError("Login failed")
|
||||
|
||||
|
||||
@@ -12,11 +12,12 @@
|
||||
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
#
|
||||
|
||||
import os, select, errno
|
||||
import os, select, errno, stat
|
||||
import random
|
||||
import shlex
|
||||
from xen.xend import sxp
|
||||
|
||||
from xen.util import mkdir
|
||||
from XendLogging import log
|
||||
from XendError import VmError
|
||||
|
||||
@@ -37,11 +38,16 @@ def bootloader(blexec, disk, quiet = 0, blargs = None, imgcfg = None):
|
||||
log.error(msg)
|
||||
raise VmError(msg)
|
||||
|
||||
mkdir.parents("/var/run/xend/boot/", stat.S_IRWXU)
|
||||
|
||||
while True:
|
||||
fifo = "/var/lib/xen/xenbl.%s" % random.randint(0, 32000)
|
||||
if not os.path.exists(fifo):
|
||||
break
|
||||
os.mkfifo(fifo, 0600)
|
||||
fifo = "/var/run/xend/boot/xenbl.%s" %(random.randint(0, 32000),)
|
||||
try:
|
||||
os.mkfifo(fifo, 0600)
|
||||
except OSError, e:
|
||||
if (e.errno != errno.EEXIST):
|
||||
raise
|
||||
break
|
||||
|
||||
child = os.fork()
|
||||
if (not child):
|
||||
|
||||
@@ -18,8 +18,8 @@ import xen.lowlevel.xc
|
||||
from xen.xend import balloon, sxp
|
||||
from xen.xend.XendError import XendError, VmError
|
||||
from xen.xend.XendLogging import log
|
||||
from xen.xend.XendConstants import *
|
||||
from xen.xend.XendConfig import XendConfig
|
||||
from xen.xend.XendConstants import *
|
||||
|
||||
SIGNATURE = "LinuxGuestRecord"
|
||||
XC_SAVE = "xc_save"
|
||||
@@ -137,7 +137,6 @@ def restore(xd, fd, dominfo = None, paused = False):
|
||||
vmconfig = p.get_val()
|
||||
|
||||
if dominfo:
|
||||
dominfo.update(XendConfig(sxp = vmconfig), refresh = False)
|
||||
dominfo.resume()
|
||||
else:
|
||||
dominfo = xd.restore_(vmconfig)
|
||||
|
||||
+776
-567
File diff suppressed because it is too large.
Load diff
@@ -34,6 +34,8 @@ DOMAIN_SHUTDOWN_REASONS = {
|
||||
DOMAIN_CRASH : "crash",
|
||||
DOMAIN_HALT : "halt"
|
||||
}
|
||||
REVERSE_DOMAIN_SHUTDOWN_REASONS = \
|
||||
dict([(y, x) for x, y in DOMAIN_SHUTDOWN_REASONS.items()])
|
||||
|
||||
restart_modes = [
|
||||
"restart",
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
# A collection of DevControllers
|
||||
#
|
||||
|
||||
from xen.xend.server import blkif, netif, tpmif, pciif, iopif, irqif, usbif
|
||||
from xen.xend.server import blkif, netif, tpmif, pciif, iopif, irqif, usbif, vfbif
|
||||
from xen.xend.server.BlktapController import BlktapController
|
||||
|
||||
class XendDevices:
|
||||
@@ -41,6 +41,8 @@ class XendDevices:
|
||||
'irq': irqif.IRQController,
|
||||
'usb': usbif.UsbifController,
|
||||
'tap': BlktapController,
|
||||
'vfb': vfbif.VfbifController,
|
||||
'vkbd': vfbif.VkbdifController,
|
||||
}
|
||||
|
||||
#@classmethod
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
"""
|
||||
|
||||
import os
|
||||
import stat
|
||||
import shutil
|
||||
import socket
|
||||
import threading
|
||||
@@ -44,7 +45,7 @@ from xen.xend.XendDevices import XendDevices
|
||||
|
||||
from xen.xend.xenstore.xstransact import xstransact
|
||||
from xen.xend.xenstore.xswatch import xswatch
|
||||
from xen.util import security
|
||||
from xen.util import mkdir, security
|
||||
from xen.xend import uuid
|
||||
|
||||
xc = xen.lowlevel.xc.xc()
|
||||
@@ -99,11 +100,7 @@ class XendDomain:
|
||||
"""Singleton initialisation function."""
|
||||
|
||||
dom_path = self._managed_path()
|
||||
try:
|
||||
os.stat(dom_path)
|
||||
except OSError:
|
||||
log.info("Making %s", dom_path)
|
||||
os.makedirs(dom_path, 0755)
|
||||
mkdir.parents(dom_path, stat.S_IRWXU)
|
||||
|
||||
xstransact.Mkdir(XS_VMROOT)
|
||||
xstransact.SetPermissions(XS_VMROOT, {'dom': DOM0_ID})
|
||||
@@ -184,7 +181,7 @@ class XendDomain:
|
||||
if not dom_uuid:
|
||||
continue
|
||||
|
||||
dom_name = dom.get('name', 'Domain-%s' % dom_uuid)
|
||||
dom_name = dom.get('name_label', 'Domain-%s' % dom_uuid)
|
||||
try:
|
||||
running_dom = self.domain_lookup_nr(dom_name)
|
||||
if not running_dom:
|
||||
@@ -271,25 +268,17 @@ class XendDomain:
|
||||
domains_dir = self._managed_path()
|
||||
dom_uuid = dominfo.get_uuid()
|
||||
domain_config_dir = self._managed_path(dom_uuid)
|
||||
|
||||
# make sure the domain dir exists
|
||||
if not os.path.exists(domains_dir):
|
||||
os.makedirs(domains_dir, 0755)
|
||||
elif not os.path.isdir(domains_dir):
|
||||
log.error("xend_domain_dir is not a directory.")
|
||||
raise XendError("Unable to save managed configuration "
|
||||
"because %s is not a directory." %
|
||||
domains_dir)
|
||||
|
||||
if not os.path.exists(domain_config_dir):
|
||||
|
||||
def make_or_raise(path):
|
||||
try:
|
||||
os.makedirs(domain_config_dir, 0755)
|
||||
except IOError:
|
||||
log.exception("Failed to create directory: %s" %
|
||||
domain_config_dir)
|
||||
raise XendError("Failed to create directory: %s" %
|
||||
domain_config_dir)
|
||||
|
||||
mkdir.parents(path, stat.S_IRWXU)
|
||||
except:
|
||||
log.exception("%s could not be created." % path)
|
||||
raise XendError("%s could not be created." % path)
|
||||
|
||||
make_or_raise(domains_dir)
|
||||
make_or_raise(domain_config_dir)
|
||||
|
||||
try:
|
||||
sxp_cache_file = open(self._managed_config_path(dom_uuid),'w')
|
||||
prettyprint(dominfo.sxpr(), sxp_cache_file, width = 78)
|
||||
@@ -423,7 +412,6 @@ class XendDomain:
|
||||
self._remove_domain(dom, domid)
|
||||
|
||||
|
||||
|
||||
def _add_domain(self, info):
|
||||
"""Add a domain to the list of running domains
|
||||
|
||||
@@ -433,6 +421,11 @@ class XendDomain:
|
||||
"""
|
||||
log.debug("Adding Domain: %s" % info.getDomid())
|
||||
self.domains[info.getDomid()] = info
|
||||
|
||||
# update the managed domains with a new XendDomainInfo object
|
||||
# if we are keeping track of it.
|
||||
if info.get_uuid() in self.managed_domains:
|
||||
self._managed_domain_register(info)
|
||||
|
||||
def _remove_domain(self, info, domid = None):
|
||||
"""Remove the domain from the list of running domains
|
||||
@@ -647,18 +640,23 @@ class XendDomain:
|
||||
def is_valid_dev(self, klass, dev_uuid):
|
||||
return (self.get_vm_with_dev_uuid(klass, dev_uuid) != None)
|
||||
|
||||
def do_legacy_api_with_uuid(self, fn, vm_uuid, *args):
|
||||
def do_legacy_api_with_uuid(self, fn, vm_uuid, *args, **kwargs):
|
||||
dom = self.uuid_to_dom(vm_uuid)
|
||||
fn(dom, *args, **kwargs)
|
||||
|
||||
def uuid_to_dom(self, vm_uuid):
|
||||
self.domains_lock.acquire()
|
||||
try:
|
||||
for domid, dom in self.domains.items():
|
||||
if dom.get_uuid == vm_uuid:
|
||||
return fn(domid, *args)
|
||||
if dom.get_uuid() == vm_uuid:
|
||||
return domid
|
||||
|
||||
if vm_uuid in self.managed_domains:
|
||||
domid = self.managed_domains[vm_uuid].getDomid()
|
||||
if domid == None:
|
||||
domid = self.managed_domains[vm_uuid].getName()
|
||||
return fn(domid, *args)
|
||||
if domid is None:
|
||||
return self.managed_domains[vm_uuid].getName()
|
||||
else:
|
||||
return domid
|
||||
|
||||
raise XendInvalidDomain("Domain does not exist")
|
||||
finally:
|
||||
@@ -669,7 +667,7 @@ class XendDomain:
|
||||
self.domains_lock.acquire()
|
||||
try:
|
||||
try:
|
||||
xeninfo = XendConfig(xenapi_vm = xenapi_vm)
|
||||
xeninfo = XendConfig(xapi = xenapi_vm)
|
||||
dominfo = XendDomainInfo.createDormant(xeninfo)
|
||||
log.debug("Creating new managed domain: %s: %s" %
|
||||
(dominfo.getName(), dominfo.get_uuid()))
|
||||
@@ -795,7 +793,7 @@ class XendDomain:
|
||||
raise XendError("can't write guest state file %s: %s" %
|
||||
(path, ex[1]))
|
||||
|
||||
def domain_resume(self, domname):
|
||||
def domain_resume(self, domname, start_paused = False):
|
||||
"""Resumes a domain that is persistently managed by Xend.
|
||||
|
||||
@param domname: Domain Name
|
||||
@@ -815,7 +813,7 @@ class XendDomain:
|
||||
raise XendError("Cannot save privileged domain %s" % domname)
|
||||
|
||||
if dominfo.state != DOM_STATE_HALTED:
|
||||
raise XendError("Cannot suspend domain that is not running.")
|
||||
raise XendError("Cannot resume domain that is not halted.")
|
||||
|
||||
dom_uuid = dominfo.get_uuid()
|
||||
chkpath = self._managed_check_point_path(dom_uuid)
|
||||
@@ -827,7 +825,8 @@ class XendDomain:
|
||||
log.debug('Current DomainInfo state: %d' % dominfo.state)
|
||||
XendCheckpoint.restore(self,
|
||||
os.open(chkpath, os.O_RDONLY),
|
||||
dominfo)
|
||||
dominfo,
|
||||
paused = start_paused)
|
||||
self._add_domain(dominfo)
|
||||
os.unlink(chkpath)
|
||||
except OSError, ex:
|
||||
@@ -872,8 +871,8 @@ class XendDomain:
|
||||
self.domains_lock.acquire()
|
||||
try:
|
||||
try:
|
||||
xeninfo = XendConfig(sxp = config)
|
||||
dominfo = XendDomainInfo.createDormant(xeninfo)
|
||||
domconfig = XendConfig(sxp_obj = config)
|
||||
dominfo = XendDomainInfo.createDormant(domconfig)
|
||||
log.debug("Creating new managed domain: %s" %
|
||||
dominfo.getName())
|
||||
self._managed_domain_register(dominfo)
|
||||
@@ -886,7 +885,7 @@ class XendDomain:
|
||||
finally:
|
||||
self.domains_lock.release()
|
||||
|
||||
def domain_start(self, domid):
|
||||
def domain_start(self, domid, start_paused = True):
|
||||
"""Start a managed domain
|
||||
|
||||
@require: Domain must not be running.
|
||||
@@ -911,6 +910,9 @@ class XendDomain:
|
||||
self._add_domain(dominfo)
|
||||
finally:
|
||||
self.domains_lock.release()
|
||||
dominfo.waitForDevices()
|
||||
if not start_paused:
|
||||
dominfo.unpause()
|
||||
|
||||
|
||||
def domain_delete(self, domid):
|
||||
@@ -932,6 +934,9 @@ class XendDomain:
|
||||
if dominfo.state != DOM_STATE_HALTED:
|
||||
raise XendError("Domain is still running")
|
||||
|
||||
log.info("Domain %s (%s) deleted." %
|
||||
(dominfo.getName(), dominfo.info.get('uuid')))
|
||||
|
||||
self._managed_domain_unregister(dominfo)
|
||||
self._remove_domain(dominfo)
|
||||
XendDevices.destroy_device_state(dominfo)
|
||||
|
||||
File diff suppressed because it is too large.
Load diff
@@ -16,13 +16,15 @@
|
||||
# Copyright (C) 2005, 2006 XenSource Ltd.
|
||||
#============================================================================
|
||||
|
||||
|
||||
import os
|
||||
import stat
|
||||
import tempfile
|
||||
import types
|
||||
import logging
|
||||
import logging.handlers
|
||||
import fcntl
|
||||
|
||||
from xen.util import mkdir
|
||||
from xen.xend.server import params
|
||||
|
||||
|
||||
@@ -80,6 +82,7 @@ def init(filename, level):
|
||||
global logfilename
|
||||
|
||||
def openFileHandler(fname):
|
||||
mkdir.parents(os.path.dirname(fname), stat.S_IRWXU)
|
||||
return XendRotatingFileHandler(fname, mode = 'a',
|
||||
maxBytes = MAX_BYTES,
|
||||
backupCount = BACKUP_COUNT)
|
||||
|
||||
@@ -19,10 +19,12 @@
|
||||
# The default QCOW Xen API Storage Repository
|
||||
#
|
||||
|
||||
import os
|
||||
import commands
|
||||
import os
|
||||
import stat
|
||||
import threading
|
||||
|
||||
from xen.util import mkdir
|
||||
from xen.xend import uuid
|
||||
from xen.xend.XendError import XendError
|
||||
from xen.xend.XendVDI import *
|
||||
@@ -98,10 +100,7 @@ class XendStorageRepository:
|
||||
"""
|
||||
self.lock.acquire()
|
||||
try:
|
||||
# create directory if /var/lib/xend/storage does not exist
|
||||
if not os.path.exists(XEND_STORAGE_DIR):
|
||||
os.makedirs(XEND_STORAGE_DIR)
|
||||
os.chmod(XEND_STORAGE_DIR, 0700)
|
||||
mkdir.parents(XEND_STORAGE_DIR, stat.S_IRWXU)
|
||||
|
||||
# scan the directory and populate self.images
|
||||
total_used = 0
|
||||
|
||||
+135
-87
@@ -23,7 +23,7 @@ import math
|
||||
import signal
|
||||
|
||||
import xen.lowlevel.xc
|
||||
from xen.xend import sxp
|
||||
from xen.xend.XendConstants import REVERSE_DOMAIN_SHUTDOWN_REASONS
|
||||
from xen.xend.XendError import VmError, XendError
|
||||
from xen.xend.XendLogging import log
|
||||
from xen.xend.server.netif import randomMAC
|
||||
@@ -31,19 +31,18 @@ from xen.xend.xenstore.xswatch import xswatch
|
||||
from xen.xend import arch
|
||||
from xen.xend import FlatDeviceTree
|
||||
|
||||
|
||||
xc = xen.lowlevel.xc.xc()
|
||||
|
||||
|
||||
MAX_GUEST_CMDLINE = 1024
|
||||
|
||||
|
||||
def create(vm, imageConfig, deviceConfig):
|
||||
def create(vm, vmConfig, imageConfig, deviceConfig):
|
||||
"""Create an image handler for a vm.
|
||||
|
||||
@return ImageHandler instance
|
||||
"""
|
||||
return findImageHandlerClass(imageConfig)(vm, imageConfig, deviceConfig)
|
||||
return findImageHandlerClass(imageConfig)(vm, vmConfig, imageConfig,
|
||||
deviceConfig)
|
||||
|
||||
|
||||
class ImageHandler:
|
||||
@@ -66,34 +65,20 @@ class ImageHandler:
|
||||
ostype = None
|
||||
|
||||
|
||||
def __init__(self, vm, imageConfig, deviceConfig):
|
||||
def __init__(self, vm, vmConfig, imageConfig, deviceConfig):
|
||||
self.vm = vm
|
||||
|
||||
self.kernel = None
|
||||
self.ramdisk = None
|
||||
self.cmdline = None
|
||||
|
||||
self.configure(imageConfig, deviceConfig)
|
||||
self.configure(vmConfig, imageConfig, deviceConfig)
|
||||
|
||||
def configure(self, imageConfig, _):
|
||||
def configure(self, vmConfig, imageConfig, _):
|
||||
"""Config actions common to all unix-like domains."""
|
||||
|
||||
def get_cfg(name, default = None):
|
||||
return sxp.child_value(imageConfig, name, default)
|
||||
|
||||
self.kernel = get_cfg("kernel")
|
||||
self.cmdline = ""
|
||||
ip = get_cfg("ip")
|
||||
if ip:
|
||||
self.cmdline += " ip=" + ip
|
||||
root = get_cfg("root")
|
||||
if root:
|
||||
self.cmdline += " root=" + root
|
||||
args = get_cfg("args")
|
||||
if args:
|
||||
self.cmdline += " " + args
|
||||
self.ramdisk = get_cfg("ramdisk", '')
|
||||
|
||||
self.kernel = vmConfig['kernel_kernel']
|
||||
self.cmdline = vmConfig['kernel_args']
|
||||
self.ramdisk = vmConfig['kernel_initrd']
|
||||
self.vm.storeVm(("image/ostype", self.ostype),
|
||||
("image/kernel", self.kernel),
|
||||
("image/cmdline", self.cmdline),
|
||||
@@ -181,6 +166,10 @@ class ImageHandler:
|
||||
pass
|
||||
|
||||
|
||||
def recreate(self):
|
||||
pass
|
||||
|
||||
|
||||
class LinuxImageHandler(ImageHandler):
|
||||
|
||||
ostype = "linux"
|
||||
@@ -214,8 +203,8 @@ class PPC_LinuxImageHandler(LinuxImageHandler):
|
||||
|
||||
ostype = "linux"
|
||||
|
||||
def configure(self, imageConfig, deviceConfig):
|
||||
LinuxImageHandler.configure(self, imageConfig, deviceConfig)
|
||||
def configure(self, vmConfig, imageConfig, deviceConfig):
|
||||
LinuxImageHandler.configure(self, vmConfig, imageConfig, deviceConfig)
|
||||
self.imageConfig = imageConfig
|
||||
|
||||
def buildDomain(self):
|
||||
@@ -302,37 +291,42 @@ class PPC_ProseImageHandler(LinuxImageHandler):
|
||||
|
||||
class HVMImageHandler(ImageHandler):
|
||||
|
||||
def __init__(self, vm, imageConfig, deviceConfig):
|
||||
ImageHandler.__init__(self, vm, imageConfig, deviceConfig)
|
||||
self.shutdownWatch = None
|
||||
ostype = "hvm"
|
||||
|
||||
def configure(self, imageConfig, deviceConfig):
|
||||
ImageHandler.configure(self, imageConfig, deviceConfig)
|
||||
def __init__(self, vm, vmConfig, imageConfig, deviceConfig):
|
||||
ImageHandler.__init__(self, vm, vmConfig, imageConfig, deviceConfig)
|
||||
self.shutdownWatch = None
|
||||
self.rebootFeatureWatch = None
|
||||
|
||||
def configure(self, vmConfig, imageConfig, deviceConfig):
|
||||
ImageHandler.configure(self, vmConfig, imageConfig, deviceConfig)
|
||||
|
||||
info = xc.xeninfo()
|
||||
if not 'hvm' in info['xen_caps']:
|
||||
if 'hvm' not in info['xen_caps']:
|
||||
raise VmError("HVM guest support is unavailable: is VT/AMD-V "
|
||||
"supported by your CPU and enabled in your BIOS?")
|
||||
|
||||
self.dmargs = self.parseDeviceModelArgs(imageConfig, deviceConfig)
|
||||
self.device_model = sxp.child_value(imageConfig, 'device_model')
|
||||
self.device_model = imageConfig['hvm'].get('device_model')
|
||||
if not self.device_model:
|
||||
raise VmError("hvm: missing device model")
|
||||
self.display = sxp.child_value(imageConfig, 'display')
|
||||
self.xauthority = sxp.child_value(imageConfig, 'xauthority')
|
||||
self.vncconsole = sxp.child_value(imageConfig, 'vncconsole')
|
||||
|
||||
self.display = imageConfig['hvm'].get('display')
|
||||
self.xauthority = imageConfig['hvm'].get('xauthority')
|
||||
self.vncconsole = imageConfig['hvm'].get('vncconsole')
|
||||
|
||||
self.vm.storeVm(("image/dmargs", " ".join(self.dmargs)),
|
||||
("image/device-model", self.device_model),
|
||||
("image/display", self.display))
|
||||
|
||||
self.pid = 0
|
||||
self.pid = None
|
||||
|
||||
self.dmargs += self.configVNC(imageConfig)
|
||||
|
||||
self.pae = int(sxp.child_value(imageConfig, 'pae', 1))
|
||||
self.acpi = int(sxp.child_value(imageConfig, 'acpi', 1))
|
||||
self.apic = int(sxp.child_value(imageConfig, 'apic', 1))
|
||||
self.pae = imageConfig['hvm'].get('pae', 0)
|
||||
self.apic = imageConfig['hvm'].get('apic', 0)
|
||||
self.acpi = imageConfig['hvm']['devices'].get('acpi', 0)
|
||||
|
||||
|
||||
def buildDomain(self):
|
||||
store_evtchn = self.vm.getStorePort()
|
||||
@@ -349,6 +343,7 @@ class HVMImageHandler(ImageHandler):
|
||||
log.debug("apic = %d", self.apic)
|
||||
|
||||
self.register_shutdown_watch()
|
||||
self.register_reboot_feature_watch()
|
||||
|
||||
return xc.hvm_build(domid = self.vm.getDomid(),
|
||||
image = self.kernel,
|
||||
@@ -366,8 +361,10 @@ class HVMImageHandler(ImageHandler):
|
||||
'localtime', 'serial', 'stdvga', 'isa', 'vcpus',
|
||||
'acpi', 'usb', 'usbdevice', 'keymap' ]
|
||||
ret = []
|
||||
hvmDeviceConfig = imageConfig['hvm']['devices']
|
||||
|
||||
for a in dmargs:
|
||||
v = sxp.child_value(imageConfig, a)
|
||||
v = hvmDeviceConfig.get(a)
|
||||
|
||||
# python doesn't allow '-' in variable names
|
||||
if a == 'stdvga': a = 'std-vga'
|
||||
@@ -382,7 +379,7 @@ class HVMImageHandler(ImageHandler):
|
||||
ret.append("-%s" % a)
|
||||
ret.append("%s" % v)
|
||||
|
||||
if a in ['fda', 'fdb' ]:
|
||||
if a in ['fda', 'fdb']:
|
||||
if v:
|
||||
if not os.path.isabs(v):
|
||||
raise VmError("Floppy file %s does not exist." % v)
|
||||
@@ -390,26 +387,27 @@ class HVMImageHandler(ImageHandler):
|
||||
|
||||
# Handle disk/network related options
|
||||
mac = None
|
||||
ret = ret + ["-domain-name", "%s" % self.vm.info['name']]
|
||||
ret = ret + ["-domain-name", str(self.vm.info['name_label'])]
|
||||
nics = 0
|
||||
for (name, info) in deviceConfig:
|
||||
if name == 'vbd':
|
||||
uname = sxp.child_value(info, 'uname')
|
||||
|
||||
for devuuid, (devtype, devinfo) in deviceConfig.items():
|
||||
if devtype == 'vbd':
|
||||
uname = devinfo.get('uname')
|
||||
if uname is not None and 'file:' in uname:
|
||||
(_, vbdparam) = string.split(uname, ':', 1)
|
||||
if not os.path.isfile(vbdparam):
|
||||
raise VmError('Disk image does not exist: %s' %
|
||||
vbdparam)
|
||||
if name == 'vif':
|
||||
type = sxp.child_value(info, 'type')
|
||||
if type != 'ioemu':
|
||||
if devtype == 'vif':
|
||||
dtype = devinfo.get('type', 'ioemu')
|
||||
if dtype != 'ioemu':
|
||||
continue
|
||||
nics += 1
|
||||
mac = sxp.child_value(info, 'mac')
|
||||
mac = devinfo.get('mac')
|
||||
if mac == None:
|
||||
mac = randomMAC()
|
||||
bridge = sxp.child_value(info, 'bridge', 'xenbr0')
|
||||
model = sxp.child_value(info, 'model', 'rtl8139')
|
||||
bridge = devinfo.get('bridge', 'xenbr0')
|
||||
model = devinfo.get('model', 'rtl8139')
|
||||
ret.append("-net")
|
||||
ret.append("nic,vlan=%d,macaddr=%s,model=%s" %
|
||||
(nics, mac, model))
|
||||
@@ -417,31 +415,32 @@ class HVMImageHandler(ImageHandler):
|
||||
ret.append("tap,vlan=%d,bridge=%s" % (nics, bridge))
|
||||
return ret
|
||||
|
||||
def configVNC(self, config):
|
||||
def configVNC(self, imageConfig):
|
||||
# Handle graphics library related options
|
||||
vnc = sxp.child_value(config, 'vnc')
|
||||
sdl = sxp.child_value(config, 'sdl')
|
||||
vnc = imageConfig.get('vnc')
|
||||
sdl = imageConfig.get('sdl')
|
||||
ret = []
|
||||
nographic = sxp.child_value(config, 'nographic')
|
||||
nographic = imageConfig.get('nographic')
|
||||
|
||||
# get password from VM config (if password omitted, None)
|
||||
vncpasswd_vmconfig = sxp.child_value(config, 'vncpasswd')
|
||||
vncpasswd_vmconfig = imageConfig.get('vncpasswd')
|
||||
|
||||
if nographic:
|
||||
ret.append('-nographic')
|
||||
return ret
|
||||
|
||||
if vnc:
|
||||
vncdisplay = int(sxp.child_value(config, 'vncdisplay',
|
||||
self.vm.getDomid()))
|
||||
vncdisplay = imageConfig.get('vncdisplay',
|
||||
int(self.vm.getDomid()))
|
||||
vncunused = imageConfig.get('vncunused')
|
||||
|
||||
vncunused = sxp.child_value(config, 'vncunused')
|
||||
if vncunused:
|
||||
ret += ['-vncunused']
|
||||
else:
|
||||
ret += ['-vnc', '%d' % vncdisplay]
|
||||
|
||||
vnclisten = sxp.child_value(config, 'vnclisten')
|
||||
vnclisten = imageConfig.get('vnclisten')
|
||||
|
||||
if not(vnclisten):
|
||||
vnclisten = (xen.xend.XendRoot.instance().
|
||||
get_vnclisten_address())
|
||||
@@ -477,21 +476,37 @@ class HVMImageHandler(ImageHandler):
|
||||
if self.vncconsole:
|
||||
args = args + ([ "-vncviewer" ])
|
||||
log.info("spawning device models: %s %s", self.device_model, args)
|
||||
# keep track of pid and spawned options to kill it later
|
||||
self.pid = os.spawnve(os.P_NOWAIT, self.device_model, args, env)
|
||||
self.vm.storeDom("image/device-model-pid", self.pid)
|
||||
log.info("device model pid: %d", self.pid)
|
||||
|
||||
def recreate(self):
|
||||
self.register_shutdown_watch()
|
||||
self.register_reboot_feature_watch()
|
||||
self.pid = self.vm.gatherDom(('image/device-model-pid', int))
|
||||
|
||||
def destroy(self):
|
||||
self.unregister_shutdown_watch();
|
||||
if not self.pid:
|
||||
return
|
||||
os.kill(self.pid, signal.SIGKILL)
|
||||
os.waitpid(self.pid, 0)
|
||||
self.pid = 0
|
||||
self.unregister_shutdown_watch()
|
||||
self.unregister_reboot_feature_watch();
|
||||
if self.pid:
|
||||
try:
|
||||
os.kill(self.pid, signal.SIGKILL)
|
||||
except OSError, exn:
|
||||
log.exception(exn)
|
||||
try:
|
||||
os.waitpid(self.pid, 0)
|
||||
except OSError, exn:
|
||||
# This is expected if Xend has been restarted within the
|
||||
# life of this domain. In this case, we can kill the process,
|
||||
# but we can't wait for it because it's not our child.
|
||||
pass
|
||||
self.pid = None
|
||||
|
||||
def register_shutdown_watch(self):
|
||||
""" add xen store watch on control/shutdown """
|
||||
self.shutdownWatch = xswatch(self.vm.dompath + "/control/shutdown", \
|
||||
self.hvm_shutdown)
|
||||
self.shutdownWatch = xswatch(self.vm.dompath + "/control/shutdown",
|
||||
self.hvm_shutdown)
|
||||
log.debug("hvm shutdown watch registered")
|
||||
|
||||
def unregister_shutdown_watch(self):
|
||||
@@ -510,28 +525,55 @@ class HVMImageHandler(ImageHandler):
|
||||
""" watch call back on node control/shutdown,
|
||||
if node changed, this function will be called
|
||||
"""
|
||||
from xen.xend.XendConstants import DOMAIN_SHUTDOWN_REASONS
|
||||
xd = xen.xend.XendDomain.instance()
|
||||
try:
|
||||
vm = xd.domain_lookup( self.vm.getDomid() )
|
||||
except XendError:
|
||||
# domain isn't registered, no need to clean it up.
|
||||
return
|
||||
return False
|
||||
|
||||
reason = vm.getShutdownReason()
|
||||
log.debug("hvm_shutdown fired, shutdown reason=%s", reason)
|
||||
for x in DOMAIN_SHUTDOWN_REASONS.keys():
|
||||
if DOMAIN_SHUTDOWN_REASONS[x] == reason:
|
||||
vm.info['shutdown'] = 1
|
||||
vm.info['shutdown_reason'] = x
|
||||
vm.refreshShutdown(vm.info)
|
||||
if reason in REVERSE_DOMAIN_SHUTDOWN_REASONS:
|
||||
vm.info['shutdown'] = 1
|
||||
vm.info['shutdown_reason'] = \
|
||||
REVERSE_DOMAIN_SHUTDOWN_REASONS[reason]
|
||||
vm.refreshShutdown(vm.info)
|
||||
|
||||
return True # Keep watching
|
||||
|
||||
def register_reboot_feature_watch(self):
|
||||
""" add xen store watch on control/feature-reboot """
|
||||
self.rebootFeatureWatch = xswatch(self.vm.dompath + "/control/feature-reboot", \
|
||||
self.hvm_reboot_feature)
|
||||
log.debug("hvm reboot feature watch registered")
|
||||
|
||||
def unregister_reboot_feature_watch(self):
|
||||
"""Remove the watch on the control/feature-reboot, if any. Nothrow
|
||||
guarantee."""
|
||||
|
||||
try:
|
||||
if self.rebootFeatureWatch:
|
||||
self.rebootFeatureWatch.unwatch()
|
||||
except:
|
||||
log.exception("Unwatching hvm reboot feature watch failed.")
|
||||
self.rebootFeatureWatch = None
|
||||
log.debug("hvm reboot feature watch unregistered")
|
||||
|
||||
def hvm_reboot_feature(self, _):
|
||||
""" watch call back on node control/feature-reboot,
|
||||
if node changed, this function will be called
|
||||
"""
|
||||
status = self.vm.readDom('control/feature-reboot')
|
||||
log.debug("hvm_reboot_feature fired, module status=%s", status)
|
||||
if status == '1':
|
||||
self.unregister_shutdown_watch()
|
||||
|
||||
return True # Keep watching
|
||||
|
||||
return 1 # Keep watching
|
||||
|
||||
class IA64_HVM_ImageHandler(HVMImageHandler):
|
||||
|
||||
ostype = "hvm"
|
||||
|
||||
def getRequiredAvailableMemory(self, mem_kb):
|
||||
page_kb = 16
|
||||
# ROM size for guest firmware, ioreq page and xenstore page
|
||||
@@ -544,8 +586,6 @@ class IA64_HVM_ImageHandler(HVMImageHandler):
|
||||
|
||||
class X86_HVM_ImageHandler(HVMImageHandler):
|
||||
|
||||
ostype = "hvm"
|
||||
|
||||
def getRequiredAvailableMemory(self, mem_kb):
|
||||
# Add 8 MiB overhead for QEMU's video RAM.
|
||||
return mem_kb + 8192
|
||||
@@ -562,6 +602,14 @@ class X86_HVM_ImageHandler(HVMImageHandler):
|
||||
return max(4 * (256 * self.vm.getVCpuCount() + 2 * (maxmem_kb / 1024)),
|
||||
shadow_mem_kb)
|
||||
|
||||
class X86_Linux_ImageHandler(LinuxImageHandler):
|
||||
|
||||
def buildDomain(self):
|
||||
# set physical mapping limit
|
||||
# add an 8MB slack to balance backend allocations.
|
||||
mem_kb = self.getRequiredInitialReservation() + (8 * 1024)
|
||||
xc.domain_set_memmap_limit(self.vm.getDomid(), mem_kb)
|
||||
return LinuxImageHandler.buildDomain(self)
|
||||
|
||||
_handlers = {
|
||||
"powerpc": {
|
||||
@@ -573,7 +621,7 @@ _handlers = {
|
||||
"hvm": IA64_HVM_ImageHandler,
|
||||
},
|
||||
"x86": {
|
||||
"linux": LinuxImageHandler,
|
||||
"linux": X86_Linux_ImageHandler,
|
||||
"hvm": X86_HVM_ImageHandler,
|
||||
},
|
||||
}
|
||||
@@ -584,10 +632,10 @@ def findImageHandlerClass(image):
|
||||
@param image config
|
||||
@return ImageHandler subclass or None
|
||||
"""
|
||||
type = sxp.name(image)
|
||||
if type is None:
|
||||
image_type = image['type']
|
||||
if image_type is None:
|
||||
raise VmError('missing image type')
|
||||
try:
|
||||
return _handlers[arch.type][type]
|
||||
return _handlers[arch.type][image_type]
|
||||
except KeyError:
|
||||
raise VmError('unknown image type: ' + type)
|
||||
raise VmError('unknown image type: ' + image_type)
|
||||
@@ -17,6 +17,7 @@
|
||||
#============================================================================
|
||||
|
||||
from threading import Event
|
||||
import types
|
||||
|
||||
from xen.xend import sxp
|
||||
from xen.xend.XendError import VmError
|
||||
@@ -86,7 +87,7 @@ class DevController:
|
||||
|
||||
import xen.xend.XendDomain
|
||||
xd = xen.xend.XendDomain.instance()
|
||||
backdom_name = sxp.child_value(config, 'backend')
|
||||
backdom_name = config.get('backend')
|
||||
if backdom_name is None:
|
||||
backdom = xen.xend.XendDomain.DOM0_ID
|
||||
else:
|
||||
@@ -223,11 +224,13 @@ class DevController:
|
||||
configDict = self.getDeviceConfiguration(devid)
|
||||
sxpr = [self.deviceClass]
|
||||
for key, val in configDict.items():
|
||||
if type(val) == type(list()):
|
||||
if isinstance(val, (types.ListType, types.TupleType)):
|
||||
for v in val:
|
||||
sxpr.append([key, v])
|
||||
if v != None:
|
||||
sxpr.append([key, v])
|
||||
else:
|
||||
sxpr.append([key, val])
|
||||
if val != None:
|
||||
sxpr.append([key, val])
|
||||
return sxpr
|
||||
|
||||
def sxprs(self):
|
||||
@@ -405,7 +408,7 @@ class DevController:
|
||||
import xen.xend.XendDomain
|
||||
xd = xen.xend.XendDomain.instance()
|
||||
|
||||
backdom_name = sxp.child_value(config, 'backend')
|
||||
backdom_name = config.get('backend')
|
||||
if backdom_name:
|
||||
backdom = xd.domain_lookup_nr(backdom_name)
|
||||
else:
|
||||
|
||||
@@ -6,7 +6,9 @@
|
||||
###########################################################
|
||||
|
||||
import os
|
||||
import os.path
|
||||
import signal
|
||||
import stat
|
||||
import sys
|
||||
import threading
|
||||
import time
|
||||
@@ -19,6 +21,7 @@ import xen.lowlevel.xc
|
||||
|
||||
from xen.xend.XendLogging import log
|
||||
from xen.xend import osdep
|
||||
from xen.util import mkdir
|
||||
|
||||
import relocate
|
||||
import SrvServer
|
||||
@@ -57,6 +60,14 @@ class Daemon:
|
||||
return running
|
||||
|
||||
|
||||
def reloadConfig(self):
|
||||
"""
|
||||
"""
|
||||
pid = read_pid(XEND_PID_FILE)
|
||||
if find_process(pid, XEND_PROCESS_NAME):
|
||||
os.kill(pid, signal.SIGHUP)
|
||||
|
||||
|
||||
def status(self):
|
||||
"""Returns the status of the xend daemon.
|
||||
The return value is defined by the LSB:
|
||||
@@ -102,17 +113,31 @@ class Daemon:
|
||||
|
||||
# Detach from standard file descriptors, and redirect them to
|
||||
# /dev/null or the log as appropriate.
|
||||
# We open the log file first, so that we can diagnose a failure to do
|
||||
# so _before_ we close stderr.
|
||||
try:
|
||||
parent = os.path.dirname(XEND_DEBUG_LOG)
|
||||
mkdir.parents(parent, stat.S_IRWXU)
|
||||
fd = os.open(XEND_DEBUG_LOG, os.O_WRONLY|os.O_CREAT|os.O_APPEND)
|
||||
except Exception, exn:
|
||||
print >>sys.stderr, exn
|
||||
print >>sys.stderr, ("Xend failed to open %s. Exiting!" %
|
||||
XEND_DEBUG_LOG)
|
||||
sys.exit(1)
|
||||
|
||||
os.close(0)
|
||||
os.close(1)
|
||||
os.close(2)
|
||||
if XEND_DEBUG:
|
||||
os.open('/dev/null', os.O_RDONLY)
|
||||
os.open(XEND_DEBUG_LOG, os.O_WRONLY|os.O_CREAT|os.O_APPEND)
|
||||
os.dup(1)
|
||||
os.dup(fd)
|
||||
os.dup(fd)
|
||||
else:
|
||||
os.open('/dev/null', os.O_RDWR)
|
||||
os.dup(0)
|
||||
os.open(XEND_DEBUG_LOG, os.O_WRONLY|os.O_CREAT|os.O_APPEND)
|
||||
os.dup(fd)
|
||||
os.close(fd)
|
||||
|
||||
print >>sys.stderr, ("Xend started at %s." %
|
||||
time.asctime(time.localtime()))
|
||||
|
||||
@@ -253,6 +278,8 @@ class Daemon:
|
||||
modulename = m.group(1)
|
||||
if re.search('sxp.py', modulename):
|
||||
return None
|
||||
if re.search('SrvServer.py', modulename):
|
||||
return None
|
||||
self.traceindent += 1
|
||||
self.print_trace("> %s:%s\n"
|
||||
% (modulename, code.co_name))
|
||||
|
||||
@@ -21,6 +21,7 @@ from xen.web import http
|
||||
from xen.xend import sxp
|
||||
from xen.xend import XendDomain
|
||||
from xen.xend.Args import FormFn
|
||||
from xen.xend.XendLogging import log
|
||||
|
||||
from xen.web.SrvDir import SrvDir
|
||||
|
||||
@@ -63,6 +64,18 @@ class SrvDomain(SrvDir):
|
||||
self.acceptCommand(req)
|
||||
return self.dom.shutdown(req.args['reason'][0])
|
||||
|
||||
def op_delete(self, _, req):
|
||||
self.acceptCommand(req)
|
||||
return self.xd.domain_delete(self.dom.getName())
|
||||
|
||||
def op_start(self, _, req):
|
||||
self.acceptCommand(req)
|
||||
paused = False
|
||||
if 'paused' in req.args and req.args['paused'] == [1]:
|
||||
paused = True
|
||||
log.debug("Starting domain " + self.dom.getName() + " " + str(paused))
|
||||
return self.xd.domain_start(self.dom.getName(), paused)
|
||||
|
||||
def op_sysrq(self, _, req):
|
||||
self.acceptCommand(req)
|
||||
return self.dom.send_sysrq(int(req.args['key'][0]))
|
||||
|
||||
@@ -25,6 +25,8 @@ from xen.xend import XendDomain
|
||||
from xen.xend.XendDomainInfo import XendDomainInfo
|
||||
from xen.xend.Args import FormFn
|
||||
from xen.xend.XendError import XendError
|
||||
from xen.xend.XendLogging import log
|
||||
from xen.xend.XendConstants import DOM_STATE_RUNNING
|
||||
|
||||
from xen.web.SrvDir import SrvDir
|
||||
from SrvDomain import SrvDomain
|
||||
@@ -101,6 +103,35 @@ class SrvDomainDir(SrvDir):
|
||||
out.close()
|
||||
return val
|
||||
|
||||
def op_new(self, _, req):
|
||||
"""Define a new domain.
|
||||
Expects the domain config in request parameter 'config' in SXP format.
|
||||
"""
|
||||
ok = 0
|
||||
errmsg = ''
|
||||
try:
|
||||
configstring = req.args.get('config')[0]
|
||||
#print 'op_create>', 'config:', configstring
|
||||
pin = sxp.Parser()
|
||||
pin.input(configstring)
|
||||
pin.input_eof()
|
||||
config = pin.get_val()
|
||||
ok = 1
|
||||
except sxp.ParseError, ex:
|
||||
errmsg = 'Invalid configuration ' + str(ex)
|
||||
except Exception, ex:
|
||||
print 'op_create> Exception in config', ex
|
||||
traceback.print_exc()
|
||||
errmsg = 'Configuration error ' + str(ex)
|
||||
if not ok:
|
||||
raise XendError(errmsg)
|
||||
try:
|
||||
self.xd.domain_new(config)
|
||||
except Exception, ex:
|
||||
print 'op_create> Exception creating domain:'
|
||||
traceback.print_exc()
|
||||
raise XendError("Error creating domain: " + str(ex))
|
||||
|
||||
def op_restore(self, op, req):
|
||||
"""Restore a domain from file.
|
||||
|
||||
@@ -159,16 +190,19 @@ class SrvDomainDir(SrvDir):
|
||||
if detail:
|
||||
sxp.show(map(XendDomainInfo.sxpr, self.xd.list()), out=req)
|
||||
else:
|
||||
sxp.show(self.xd.list_names(), out=req)
|
||||
state = DOM_STATE_RUNNING
|
||||
if 'state' in req.args and len(req.args['state']) > 0:
|
||||
state = req.args['state'][0]
|
||||
log.debug("Listing domains in state " + str(state))
|
||||
sxp.show(self.xd.list_names(state), out=req)
|
||||
else:
|
||||
domains = self.xd.list_sorted()
|
||||
req.write('<ul>')
|
||||
for d in domains:
|
||||
req.write(
|
||||
'<li><a href="%s%s">Domain %s</a>: id = %s, memory = %d, '
|
||||
'ssidref = %d.'
|
||||
'<li><a href="%s%s">Domain %s</a>: id = %s, memory = %d'
|
||||
% (url, d.getName(), d.getName(), d.getDomid(),
|
||||
d.getMemoryTarget(), d.getSsidref()))
|
||||
d.getMemoryTarget()))
|
||||
req.write('</li>')
|
||||
req.write('</ul>')
|
||||
|
||||
|
||||
@@ -62,9 +62,11 @@ xroot = XendRoot.instance()
|
||||
|
||||
class XendServers:
|
||||
|
||||
def __init__(self):
|
||||
def __init__(self, root):
|
||||
self.servers = []
|
||||
self.root = root
|
||||
self.cleaningUp = False
|
||||
self.reloadingConfig = False
|
||||
|
||||
def add(self, server):
|
||||
self.servers.append(server)
|
||||
@@ -78,6 +80,11 @@ class XendServers:
|
||||
except:
|
||||
pass
|
||||
|
||||
def reloadConfig(self, signum = 0, frame = None):
|
||||
log.debug("SrvServer.reloadConfig()")
|
||||
self.reloadingConfig = True
|
||||
self.cleanup(signum, frame)
|
||||
|
||||
def start(self, status):
|
||||
# Running the network script will spawn another process, which takes
|
||||
# the status fd with it unless we set FD_CLOEXEC. Failing to do this
|
||||
@@ -86,66 +93,90 @@ class XendServers:
|
||||
fcntl.fcntl(status, fcntl.F_SETFD, fcntl.FD_CLOEXEC)
|
||||
|
||||
Vifctl.network('start')
|
||||
threads = []
|
||||
for server in self.servers:
|
||||
thread = Thread(target=server.run, name=server.__class__.__name__)
|
||||
if isinstance(server, HttpServer):
|
||||
thread.setDaemon(True)
|
||||
thread.start()
|
||||
threads.append(thread)
|
||||
|
||||
|
||||
# check for when all threads have initialized themselves and then
|
||||
# close the status pipe
|
||||
|
||||
threads_left = True
|
||||
while threads_left:
|
||||
threads_left = False
|
||||
|
||||
for server in self.servers:
|
||||
if not server.ready:
|
||||
threads_left = True
|
||||
break
|
||||
|
||||
if threads_left:
|
||||
time.sleep(.5)
|
||||
|
||||
if status:
|
||||
status.write('0')
|
||||
status.close()
|
||||
|
||||
# Prepare to catch SIGTERM (received when 'xend stop' is executed)
|
||||
# and call each server's cleanup if possible
|
||||
signal.signal(signal.SIGTERM, self.cleanup)
|
||||
signal.signal(signal.SIGHUP, self.reloadConfig)
|
||||
|
||||
# Interruptible Thread.join - Python Bug #1167930
|
||||
# Replaces: for t in threads: t.join()
|
||||
# Reason: The above will cause python signal handlers to be
|
||||
# blocked so we're not able to catch SIGTERM in any
|
||||
# way for cleanup
|
||||
runningThreads = threads
|
||||
while len(runningThreads) > 0:
|
||||
try:
|
||||
for t in threads:
|
||||
t.join(1.0)
|
||||
runningThreads = [t for t in threads
|
||||
if t.isAlive() and not t.isDaemon()]
|
||||
if self.cleaningUp and len(runningThreads) > 0:
|
||||
log.debug("Waiting for %s." %
|
||||
[x.getName() for x in runningThreads])
|
||||
except:
|
||||
pass
|
||||
while True:
|
||||
threads = []
|
||||
for server in self.servers:
|
||||
if server.ready:
|
||||
continue
|
||||
|
||||
thread = Thread(target=server.run, name=server.__class__.__name__)
|
||||
if isinstance(server, HttpServer):
|
||||
thread.setDaemon(True)
|
||||
thread.start()
|
||||
threads.append(thread)
|
||||
|
||||
|
||||
def create():
|
||||
root = SrvDir()
|
||||
root.putChild('xend', SrvRoot())
|
||||
servers = XendServers()
|
||||
if xroot.get_xend_http_server():
|
||||
# check for when all threads have initialized themselves and then
|
||||
# close the status pipe
|
||||
|
||||
retryCount = 0
|
||||
threads_left = True
|
||||
while threads_left:
|
||||
threads_left = False
|
||||
|
||||
for server in self.servers:
|
||||
if not server.ready:
|
||||
threads_left = True
|
||||
break
|
||||
|
||||
if threads_left:
|
||||
time.sleep(.5)
|
||||
retryCount += 1
|
||||
if retryCount > 60:
|
||||
for server in self.servers:
|
||||
if not server.ready:
|
||||
log.error("Server " +
|
||||
server.__class__.__name__ +
|
||||
" did not initialise!")
|
||||
break
|
||||
|
||||
if status:
|
||||
status.write('0')
|
||||
status.close()
|
||||
status = None
|
||||
|
||||
# Interruptible Thread.join - Python Bug #1167930
|
||||
# Replaces: for t in threads: t.join()
|
||||
# Reason: The above will cause python signal handlers to be
|
||||
# blocked so we're not able to catch SIGTERM in any
|
||||
# way for cleanup
|
||||
runningThreads = threads
|
||||
while len(runningThreads) > 0:
|
||||
try:
|
||||
for t in threads:
|
||||
t.join(1.0)
|
||||
runningThreads = [t for t in threads
|
||||
if t.isAlive() and not t.isDaemon()]
|
||||
if self.cleaningUp and len(runningThreads) > 0:
|
||||
log.debug("Waiting for %s." %
|
||||
[x.getName() for x in runningThreads])
|
||||
except:
|
||||
pass
|
||||
|
||||
if self.reloadingConfig:
|
||||
log.info("Restarting all XML-RPC and Xen-API servers...")
|
||||
self.cleaningUp = False
|
||||
self.reloadingConfig = False
|
||||
xroot.set_config()
|
||||
new_servers = [x for x in self.servers
|
||||
if isinstance(x, HttpServer)]
|
||||
self.servers = new_servers
|
||||
_loadConfig(self, self.root, True)
|
||||
else:
|
||||
break
|
||||
|
||||
def _loadConfig(servers, root, reload):
|
||||
if not reload and xroot.get_xend_http_server():
|
||||
servers.add(HttpServer(root,
|
||||
xroot.get_xend_address(),
|
||||
xroot.get_xend_port()))
|
||||
if xroot.get_xend_unix_server():
|
||||
if not reload and xroot.get_xend_unix_server():
|
||||
path = xroot.get_xend_unix_path()
|
||||
log.info('unix path=' + path)
|
||||
servers.add(UnixHttpServer(root, path))
|
||||
@@ -154,7 +185,7 @@ def create():
|
||||
if api_cfg:
|
||||
try:
|
||||
addrs = [(str(x[0]).split(':'),
|
||||
len(x) > 1 and x[1] or XendAPI.AUTH_NONE,
|
||||
len(x) > 1 and x[1] or XendAPI.AUTH_PAM,
|
||||
len(x) > 2 and x[2] and map(re.compile, x[2].split(" "))
|
||||
or None)
|
||||
for x in api_cfg]
|
||||
@@ -188,4 +219,11 @@ def create():
|
||||
|
||||
if xroot.get_xend_unix_xmlrpc_server():
|
||||
servers.add(XMLRPCServer(XendAPI.AUTH_PAM))
|
||||
|
||||
|
||||
def create():
|
||||
root = SrvDir()
|
||||
root.putChild('xend', SrvRoot())
|
||||
servers = XendServers(root)
|
||||
_loadConfig(servers, root, False)
|
||||
return servers
|
||||
@@ -16,6 +16,8 @@
|
||||
# Copyright (C) 2006 XenSource Ltd.
|
||||
#============================================================================
|
||||
|
||||
import errno
|
||||
import socket
|
||||
import types
|
||||
import xmlrpclib
|
||||
from xen.util.xmlrpclib2 import UnixXMLRPCServer, TCPXMLRPCServer
|
||||
@@ -105,20 +107,25 @@ class XMLRPCServer:
|
||||
"; authentication has been disabled for this server." or
|
||||
".")
|
||||
|
||||
if self.use_tcp:
|
||||
log.info("Opening TCP XML-RPC server on %s%d%s",
|
||||
self.host and '%s:' % self.host or
|
||||
'all interfaces, port ',
|
||||
self.port, authmsg)
|
||||
self.server = TCPXMLRPCServer((self.host, self.port),
|
||||
self.hosts_allowed,
|
||||
logRequests = False)
|
||||
else:
|
||||
log.info("Opening Unix domain socket XML-RPC server on %s%s",
|
||||
self.path, authmsg)
|
||||
self.server = UnixXMLRPCServer(self.path, self.hosts_allowed,
|
||||
logRequests = False)
|
||||
|
||||
try:
|
||||
if self.use_tcp:
|
||||
log.info("Opening TCP XML-RPC server on %s%d%s",
|
||||
self.host and '%s:' % self.host or
|
||||
'all interfaces, port ',
|
||||
self.port, authmsg)
|
||||
self.server = TCPXMLRPCServer((self.host, self.port),
|
||||
self.hosts_allowed,
|
||||
logRequests = False)
|
||||
else:
|
||||
log.info("Opening Unix domain socket XML-RPC server on %s%s",
|
||||
self.path, authmsg)
|
||||
self.server = UnixXMLRPCServer(self.path, self.hosts_allowed,
|
||||
logRequests = False)
|
||||
except socket.error, exn:
|
||||
log.error('Cannot start server: %s!', exn.args[1])
|
||||
ready = True
|
||||
running = False
|
||||
return
|
||||
|
||||
# Register Xen API Functions
|
||||
# -------------------------------------------------------------------
|
||||
@@ -177,6 +184,11 @@ class XMLRPCServer:
|
||||
|
||||
def cleanup(self):
|
||||
log.debug("XMLRPCServer.cleanup()")
|
||||
try:
|
||||
self.server.socket.close()
|
||||
except Exception, exn:
|
||||
log.exception(exn)
|
||||
pass
|
||||
|
||||
def shutdown(self):
|
||||
self.running = False
|
||||
|
||||
@@ -21,7 +21,6 @@ import string
|
||||
|
||||
from xen.util import blkif
|
||||
from xen.util import security
|
||||
from xen.xend import sxp
|
||||
from xen.xend.XendError import VmError
|
||||
from xen.xend.server.DevController import DevController
|
||||
|
||||
@@ -37,9 +36,9 @@ class BlkifController(DevController):
|
||||
|
||||
def getDeviceDetails(self, config):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
uname = sxp.child_value(config, 'uname', '')
|
||||
dev = sxp.child_value(config, 'dev', '')
|
||||
|
||||
uname = config.get('uname', '')
|
||||
dev = config.get('dev', '')
|
||||
|
||||
if 'ioemu:' in dev:
|
||||
(_, dev) = string.split(dev, ':', 1)
|
||||
try:
|
||||
@@ -59,17 +58,17 @@ class BlkifController(DevController):
|
||||
except ValueError:
|
||||
(typ, params) = ("", "")
|
||||
|
||||
mode = sxp.child_value(config, 'mode', 'r')
|
||||
mode = config.get('mode', 'r')
|
||||
if mode not in ('r', 'w', 'w!'):
|
||||
raise VmError('Invalid mode')
|
||||
|
||||
back = { 'dev' : dev,
|
||||
'type' : typ,
|
||||
'params' : params,
|
||||
'mode' : mode
|
||||
}
|
||||
back = {'dev' : dev,
|
||||
'type' : typ,
|
||||
'params' : params,
|
||||
'mode' : mode,
|
||||
}
|
||||
|
||||
uuid = sxp.child_value(config, 'uuid')
|
||||
uuid = config.get('uuid')
|
||||
if uuid:
|
||||
back['uuid'] = uuid
|
||||
|
||||
@@ -125,6 +124,8 @@ class BlkifController(DevController):
|
||||
config['dev'] = dev
|
||||
if typ and params:
|
||||
config['uname'] = typ +':' + params
|
||||
else:
|
||||
config['uname'] = None
|
||||
if mode:
|
||||
config['mode'] = mode
|
||||
if uuid:
|
||||
|
||||
@@ -22,7 +22,6 @@ import types
|
||||
|
||||
import xen.lowlevel.xc
|
||||
|
||||
from xen.xend import sxp
|
||||
from xen.xend.XendError import VmError
|
||||
|
||||
from xen.xend.server.DevController import DevController
|
||||
@@ -49,13 +48,12 @@ class IOPortsController(DevController):
|
||||
def __init__(self, vm):
|
||||
DevController.__init__(self, vm)
|
||||
|
||||
|
||||
def getDeviceDetails(self, config):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
|
||||
def get_param(field):
|
||||
try:
|
||||
val = sxp.child_value(config, field)
|
||||
val = config.get(field)
|
||||
|
||||
if not val:
|
||||
raise VmError('ioports: Missing %s config setting' % field)
|
||||
|
||||
@@ -45,7 +45,7 @@ class IRQController(DevController):
|
||||
|
||||
def get_param(field):
|
||||
try:
|
||||
val = sxp.child_value(config, field)
|
||||
val = config.get(field)
|
||||
|
||||
if not val:
|
||||
raise VmError('irq: Missing %s config setting' % field)
|
||||
|
||||
@@ -24,7 +24,6 @@ import os
|
||||
import random
|
||||
import re
|
||||
|
||||
from xen.xend import sxp
|
||||
from xen.xend import XendRoot
|
||||
from xen.xend.server.DevController import DevController
|
||||
|
||||
@@ -139,22 +138,15 @@ class NetifController(DevController):
|
||||
def getDeviceDetails(self, config):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
|
||||
def _get_config_ipaddr(config):
|
||||
val = []
|
||||
for ipaddr in sxp.children(config, elt='ip'):
|
||||
val.append(sxp.child0(ipaddr))
|
||||
return val
|
||||
|
||||
script = os.path.join(xroot.network_script_dir,
|
||||
sxp.child_value(config, 'script',
|
||||
xroot.get_vif_script()))
|
||||
typ = sxp.child_value(config, 'type')
|
||||
bridge = sxp.child_value(config, 'bridge')
|
||||
mac = sxp.child_value(config, 'mac')
|
||||
vifname = sxp.child_value(config, 'vifname')
|
||||
rate = sxp.child_value(config, 'rate')
|
||||
uuid = sxp.child_value(config, 'uuid')
|
||||
ipaddr = _get_config_ipaddr(config)
|
||||
config.get('script', xroot.get_vif_script()))
|
||||
typ = config.get('type')
|
||||
bridge = config.get('bridge')
|
||||
mac = config.get('mac')
|
||||
vifname = config.get('vifname')
|
||||
rate = config.get('rate')
|
||||
uuid = config.get('uuid')
|
||||
ipaddr = config.get('ip')
|
||||
|
||||
devid = self.allocateDeviceID()
|
||||
|
||||
@@ -172,7 +164,7 @@ class NetifController(DevController):
|
||||
front = { 'handle' : "%i" % devid,
|
||||
'mac' : mac }
|
||||
if ipaddr:
|
||||
back['ip'] = ' '.join(ipaddr)
|
||||
back['ip'] = ipaddr
|
||||
if bridge:
|
||||
back['bridge'] = bridge
|
||||
if vifname:
|
||||
@@ -197,7 +189,7 @@ class NetifController(DevController):
|
||||
network_script_dir = xroot.network_script_dir + os.sep
|
||||
result['script'] = script.replace(network_script_dir, "")
|
||||
if ip:
|
||||
result['ip'] = ip.split(" ")
|
||||
result['ip'] = ip
|
||||
if bridge:
|
||||
result['bridge'] = bridge
|
||||
if mac:
|
||||
|
||||
@@ -53,60 +53,29 @@ class PciController(DevController):
|
||||
|
||||
def getDeviceDetails(self, config):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
#log.debug('pci config='+sxp.to_string(config))
|
||||
|
||||
def get_param(config, field, default=None):
|
||||
def parse_hex(val):
|
||||
try:
|
||||
val = sxp.child_value(config, field)
|
||||
|
||||
if not val:
|
||||
if default==None:
|
||||
raise VmError('pci: Missing %s config setting' % field)
|
||||
else:
|
||||
return default
|
||||
|
||||
if isinstance(val, types.StringTypes):
|
||||
return int(val, 16)
|
||||
else:
|
||||
return val
|
||||
except:
|
||||
if default==None:
|
||||
raise VmError('pci: Invalid config setting %s: %s' %
|
||||
(field, val))
|
||||
else:
|
||||
return default
|
||||
|
||||
back = {}
|
||||
|
||||
val = sxp.child_value(config, 'dev')
|
||||
if isinstance(val, (types.ListType, types.TupleType)):
|
||||
pcidevid = 0
|
||||
for dev_config in sxp.children(config, 'dev'):
|
||||
domain = get_param(dev_config, 'domain', 0)
|
||||
bus = get_param(dev_config,'bus')
|
||||
slot = get_param(dev_config,'slot')
|
||||
func = get_param(dev_config,'func')
|
||||
|
||||
self.setupDevice(domain, bus, slot, func)
|
||||
|
||||
back['dev-%i' % pcidevid]="%04x:%02x:%02x.%02x"% \
|
||||
(domain, bus, slot, func)
|
||||
pcidevid+=1
|
||||
except ValueError:
|
||||
return None
|
||||
|
||||
back['num_devs']=str(pcidevid)
|
||||
|
||||
else:
|
||||
# Xen 2.0 configuration compatibility
|
||||
domain = get_param(config, 'domain', 0)
|
||||
bus = get_param(config, 'bus')
|
||||
slot = get_param(config, 'dev')
|
||||
func = get_param(config, 'func')
|
||||
|
||||
back = {}
|
||||
pcidevid = 0
|
||||
for pci_config in config.get('devs', []):
|
||||
domain = parse_hex(pci_config.get('domain', 0))
|
||||
bus = parse_hex(pci_config.get('bus', 0))
|
||||
slot = parse_hex(pci_config.get('slot', 0))
|
||||
func = parse_hex(pci_config.get('func', 0))
|
||||
self.setupDevice(domain, bus, slot, func)
|
||||
back['dev-%i' % pcidevid] = "%04x:%02x:%02x.%02x" % \
|
||||
(domain, bus, slot, func)
|
||||
pcidevid += 1
|
||||
|
||||
back['dev-0']="%04x:%02x:%02x.%02x"%(domain, bus, slot, func)
|
||||
back['num_devs']=str(1)
|
||||
|
||||
back['num_devs']=str(pcidevid)
|
||||
back['uuid'] = config.get('uuid','')
|
||||
return (0, back, {})
|
||||
|
||||
def getDeviceConfiguration(self, devid):
|
||||
@@ -129,7 +98,8 @@ class PciController(DevController):
|
||||
'slot': '0x%(slot)s' % pci_dev_info,
|
||||
'func': '0x%(func)s' % pci_dev_info})
|
||||
|
||||
result['dev'] = pci_devs
|
||||
result['devs'] = pci_devs
|
||||
result['uuid'] = self.readBackend(devid, 'uuid')
|
||||
return result
|
||||
|
||||
def configuration(self, devid):
|
||||
@@ -142,7 +112,8 @@ class PciController(DevController):
|
||||
sxpr = [self.deviceClass]
|
||||
|
||||
# remove devs
|
||||
devs = configDict.pop('dev', [])
|
||||
devs = configDict.pop('devs', [])
|
||||
|
||||
for dev in devs:
|
||||
dev_sxpr = ['dev']
|
||||
for dev_item in dev.items():
|
||||
|
||||
@@ -15,25 +15,24 @@ class PCIQuirk:
|
||||
self.device = device
|
||||
self.subvendor = subvendor
|
||||
self.subdevice = subdevice
|
||||
self.domain = domain
|
||||
self.bus = bus
|
||||
self.slot = slot
|
||||
self.func = func
|
||||
self.domain = domain
|
||||
self.bus = bus
|
||||
self.slot = slot
|
||||
self.func = func
|
||||
|
||||
self.devid = "%04x:%04x:%04x:%04x" % (vendor, device, subvendor, subdevice)
|
||||
self.pciid = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
|
||||
self.pciid = "%04x:%02x:%02x.%01x" % (domain, bus, slot, func)
|
||||
self.quirks = self.__getQuirksByID()
|
||||
|
||||
self.quirks = self.__getQuirksByID( )
|
||||
|
||||
self.__sendQuirks( )
|
||||
self.__sendPermDevs( )
|
||||
self.__sendQuirks()
|
||||
self.__sendPermDevs()
|
||||
|
||||
def __matchPCIdev( self, list ):
|
||||
ret = False
|
||||
if list == None:
|
||||
return False
|
||||
for id in list:
|
||||
if id.startswith( self.devid[:9] ): # id's vendor and device ID match
|
||||
if id.startswith(self.devid[:9]): # id's vendor and device ID match
|
||||
skey = id.split(':')
|
||||
size = len(skey)
|
||||
if (size == 2): # subvendor/subdevice not suplied
|
||||
@@ -41,13 +40,13 @@ class PCIQuirk:
|
||||
break
|
||||
elif (size == 4): # check subvendor/subdevice
|
||||
# check subvendor
|
||||
subven = '%04x' % self.subvendor
|
||||
subven = '%04x' % self.subvendor
|
||||
if ((skey[2] != 'FFFF') and
|
||||
(skey[2] != 'ffff') and
|
||||
(skey[2] != subven)):
|
||||
continue
|
||||
# check subdevice
|
||||
subdev = '%04x' % self.subdevice
|
||||
subdev = '%04x' % self.subdevice
|
||||
if ((skey[3] != 'FFFF') and
|
||||
(skey[3] != 'ffff') and
|
||||
(skey[3] != subdev)):
|
||||
@@ -101,8 +100,8 @@ class PCIQuirk:
|
||||
self.slot, self.func, quirk) )
|
||||
f.close()
|
||||
except Exception, e:
|
||||
raise VmError("pci: failed to open/write/close quirks sysfs " + \
|
||||
"node - " + str(e))
|
||||
raise VmError("pci: failed to open/write/close quirks " +
|
||||
"sysfs node - " + str(e))
|
||||
|
||||
def __devIsUnconstrained( self ):
|
||||
if os.path.exists(PERMISSIVE_CONFIG_FILE):
|
||||
@@ -126,20 +125,22 @@ class PCIQuirk:
|
||||
|
||||
devices = child_at(child(pci_perm_dev_config, 'unconstrained_dev_ids'),0)
|
||||
if self.__matchPCIdev( devices ):
|
||||
log.debug("Permissive mode enabled for PCI device [%s]" % self.devid)
|
||||
log.debug("Permissive mode enabled for PCI device [%s]" %
|
||||
self.devid)
|
||||
return True
|
||||
log.debug("Permissive mode NOT enabled for PCI device [%s]" % self.devid)
|
||||
log.debug("Permissive mode NOT enabled for PCI device [%s]" %
|
||||
self.devid)
|
||||
return False
|
||||
|
||||
def __sendPermDevs(self):
|
||||
if self.__devIsUnconstrained( ):
|
||||
log.debug("Unconstrained device: %04x:%02x:%02x.%1x" % (self.domain,
|
||||
self.bus, self.slot, self.func))
|
||||
log.debug("Unconstrained device: %04x:%02x:%02x.%1x" %
|
||||
(self.domain, self.bus, self.slot, self.func))
|
||||
try:
|
||||
f = file(PERMISSIVE_SYSFS_NODE ,"w")
|
||||
f.write( "%04x:%02x:%02x.%1x" % (self.domain, self.bus,
|
||||
self.slot, self.func) )
|
||||
self.slot, self.func))
|
||||
f.close()
|
||||
except Exception, e:
|
||||
raise VmError("pci: failed to open/write/close permissive " + \
|
||||
"sysfs node: " + str(e))
|
||||
raise VmError("pci: failed to open/write/close permissive " +
|
||||
"sysfs node: " + str(e))
|
||||
@@ -21,13 +21,13 @@ class test_controllers(unittest.TestCase):
|
||||
def testNetif(self):
|
||||
controller = self.controllerInstance(netif.NetifController)
|
||||
|
||||
self.assertNetif(controller.getDeviceDetails(['vif']), None)
|
||||
self.assertNetif(controller.getDeviceDetails({}), None)
|
||||
self.assertNetif(
|
||||
controller.getDeviceDetails(
|
||||
['vif', ['mac', 'aa:bb:cc:dd:ee:ff']]),
|
||||
controller.getDeviceDetails({'mac': 'aa:bb:cc:dd:ee:ff'}),
|
||||
'aa:bb:cc:dd:ee:ff')
|
||||
|
||||
|
||||
|
||||
def assertNetif(self, results, expectedMac):
|
||||
|
||||
(devid, backdets, frontdets) = results
|
||||
|
||||
@@ -18,10 +18,8 @@
|
||||
# Copyright (C) 2005 XenSource Ltd
|
||||
#============================================================================
|
||||
|
||||
"""Support for virtual TPM interfaces.
|
||||
"""
|
||||
"""Support for virtual TPM interfaces."""
|
||||
|
||||
from xen.xend import sxp
|
||||
from xen.xend import XendRoot
|
||||
from xen.xend.XendLogging import log
|
||||
from xen.xend.XendError import XendError
|
||||
@@ -49,12 +47,12 @@ class TPMifController(DevController):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
|
||||
devid = self.allocateDeviceID()
|
||||
inst = int(sxp.child_value(config, 'pref_instance', '-1'))
|
||||
inst = int(config.get('pref_instance', -1))
|
||||
if inst == -1:
|
||||
inst = int(sxp.child_value(config, 'instance' , '0'))
|
||||
inst = int(config.get('instance', 0))
|
||||
|
||||
typ = sxp.child_value(config, 'type')
|
||||
uuid = sxp.child_value(config, 'uuid')
|
||||
typ = config.get('type')
|
||||
uuid = config.get('uuid')
|
||||
|
||||
log.info("The domain has a TPM with pref. instance %d and devid %d.",
|
||||
inst, devid)
|
||||
|
||||
@@ -0,0 +1,74 @@
|
||||
from xen.xend.server.DevController import DevController
|
||||
|
||||
from xen.xend.XendError import VmError
|
||||
import xen.xend
|
||||
import os
|
||||
|
||||
def spawn_detached(path, args, env):
|
||||
p = os.fork()
|
||||
if p == 0:
|
||||
os.spawnve(os.P_NOWAIT, path, args, env)
|
||||
os._exit(0)
|
||||
else:
|
||||
os.waitpid(p, 0)
|
||||
|
||||
class VfbifController(DevController):
|
||||
"""Virtual frame buffer controller. Handles all vfb devices for a domain.
|
||||
Note that we only support a single vfb per domain at the moment.
|
||||
"""
|
||||
|
||||
def __init__(self, vm):
|
||||
DevController.__init__(self, vm)
|
||||
self.config = {}
|
||||
|
||||
def getDeviceDetails(self, config):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
devid = 0
|
||||
back = {}
|
||||
front = {}
|
||||
return (devid, back, front)
|
||||
|
||||
def getDeviceConfiguration(self, devid):
|
||||
r = DevController.getDeviceConfiguration(self, devid)
|
||||
for (k,v) in self.config.iteritems():
|
||||
r[k] = v
|
||||
return r
|
||||
|
||||
def createDevice(self, config):
|
||||
DevController.createDevice(self, config)
|
||||
self.config = config
|
||||
std_args = [ "--domid", "%d" % self.vm.getDomid(),
|
||||
"--title", self.vm.getName() ]
|
||||
t = config.get("type", None)
|
||||
if t == "vnc":
|
||||
# Try to start the vnc backend
|
||||
args = [xen.util.auxbin.pathTo("xen-vncfb")]
|
||||
if config.has_key("vncunused"):
|
||||
args += ["--unused"]
|
||||
elif config.has_key("vncdisplay"):
|
||||
args += ["--vncport", "%d" % (5900 + config["vncdisplay"])]
|
||||
vnclisten = config.get("vnclisten",
|
||||
xen.xend.XendRoot.instance().get_vnclisten_address())
|
||||
args += [ "--listen", vnclisten ]
|
||||
spawn_detached(args[0], args + std_args, os.environ)
|
||||
elif t == "sdl":
|
||||
args = [xen.util.auxbin.pathTo("xen-sdlfb")]
|
||||
env = dict(os.environ)
|
||||
if config.has_key("display"):
|
||||
env['DISPLAY'] = config["display"]
|
||||
if config.has_key("xauthority"):
|
||||
env['XAUTHORITY'] = config["xauthority"]
|
||||
spawn_detached(args[0], args + std_args, env)
|
||||
else:
|
||||
raise VmError('Unknown vfb type %s (%s)' % (t, repr(config)))
|
||||
|
||||
class VkbdifController(DevController):
|
||||
"""Virtual keyboard controller. Handles all vkbd devices for a domain.
|
||||
"""
|
||||
|
||||
def getDeviceDetails(self, config):
|
||||
"""@see DevController.getDeviceDetails"""
|
||||
devid = 0
|
||||
back = {}
|
||||
front = {}
|
||||
return (devid, back, front)
|
||||
@@ -11,11 +11,12 @@ from xen.xend.xenstore.xsutil import xshandle
|
||||
class xstransact:
|
||||
|
||||
def __init__(self, path = ""):
|
||||
assert path is not None
|
||||
|
||||
self.in_transaction = False # Set this temporarily -- if this
|
||||
# constructor fails, then we need to
|
||||
# protect __del__.
|
||||
|
||||
assert path is not None
|
||||
self.path = path.rstrip("/")
|
||||
self.transaction = xshandle().transaction_start()
|
||||
self.in_transaction = True
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
# Public License. See the file "COPYING" in the main directory of
|
||||
# this archive for more details.
|
||||
|
||||
import errno
|
||||
import threading
|
||||
from xen.xend.xenstore.xsutil import xshandle
|
||||
|
||||
@@ -65,7 +66,15 @@ def watchMain():
|
||||
watch = we[1]
|
||||
res = watch.fn(we[0], *watch.args, **watch.kwargs)
|
||||
if not res:
|
||||
watch.unwatch()
|
||||
try:
|
||||
watch.unwatch()
|
||||
except RuntimeError, exn:
|
||||
if exn.args[0] == errno.ENOENT:
|
||||
# The watch has already been unregistered -- that's
|
||||
# fine.
|
||||
pass
|
||||
else:
|
||||
raise
|
||||
except:
|
||||
log.exception("read_watch failed")
|
||||
# Ignore this exception -- there's no point throwing it
|
||||
|
||||
@@ -0,0 +1,132 @@
|
||||
#============================================================================
|
||||
# This library is free software; you can redistribute it and/or
|
||||
# modify it under the terms of version 2.1 of the GNU Lesser General Public
|
||||
# License as published by the Free Software Foundation.
|
||||
#
|
||||
# This library is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# Lesser General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Lesser General Public
|
||||
# License along with this library; if not, write to the Free Software
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
#============================================================================
|
||||
# Copyright (C) 2006 XenSource Inc.
|
||||
#============================================================================
|
||||
#
|
||||
# Parts of this file are based upon xmlrpclib.py, the XML-RPC client
|
||||
# interface included in the Python distribution.
|
||||
#
|
||||
# Copyright (c) 1999-2002 by Secret Labs AB
|
||||
# Copyright (c) 1999-2002 by Fredrik Lundh
|
||||
#
|
||||
# By obtaining, using, and/or copying this software and/or its
|
||||
# associated documentation, you agree that you have read, understood,
|
||||
# and will comply with the following terms and conditions:
|
||||
#
|
||||
# Permission to use, copy, modify, and distribute this software and
|
||||
# its associated documentation for any purpose and without fee is
|
||||
# hereby granted, provided that the above copyright notice appears in
|
||||
# all copies, and that both that copyright notice and this permission
|
||||
# notice appear in supporting documentation, and that the name of
|
||||
# Secret Labs AB or the author not be used in advertising or publicity
|
||||
# pertaining to distribution of the software without specific, written
|
||||
# prior permission.
|
||||
#
|
||||
# SECRET LABS AB AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD
|
||||
# TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANT-
|
||||
# ABILITY AND FITNESS. IN NO EVENT SHALL SECRET LABS AB OR THE AUTHOR
|
||||
# BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY
|
||||
# DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
|
||||
# WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
|
||||
# ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
|
||||
# OF THIS SOFTWARE.
|
||||
# --------------------------------------------------------------------
|
||||
|
||||
import xmlrpclib
|
||||
|
||||
import xen.util.xmlrpclib2
|
||||
|
||||
|
||||
class Failure(Exception):
|
||||
def __init__(self, details):
|
||||
self.details = details
|
||||
|
||||
def __str__(self):
|
||||
return "Xen-API failure: %s" % str(self.details)
|
||||
|
||||
|
||||
class Session(xen.util.xmlrpclib2.ServerProxy):
|
||||
"""A server proxy and session manager for communicating with Xend using
|
||||
the Xen-API.
|
||||
|
||||
Example:
|
||||
|
||||
session = Session('http://localhost:9363/')
|
||||
session.login_with_password('me', 'mypassword')
|
||||
session.xenapi.VM.start(vm_uuid)
|
||||
session.xenapi.session.logout()
|
||||
|
||||
For now, this class also supports the legacy XML-RPC API, using
|
||||
session.xend.domain('Domain-0') and similar. This support will disappear
|
||||
once there is a working Xen-API replacement for every call in the legacy
|
||||
API.
|
||||
"""
|
||||
|
||||
def __init__(self, uri, transport=None, encoding=None, verbose=0,
|
||||
allow_none=1):
|
||||
xen.util.xmlrpclib2.ServerProxy.__init__(self, uri, transport,
|
||||
encoding, verbose,
|
||||
allow_none)
|
||||
self._session = None
|
||||
|
||||
|
||||
def _xen_request(self, methodname, params):
|
||||
full_params = (self._session,) + params
|
||||
return _parse_result(getattr(self, methodname)(*full_params))
|
||||
|
||||
|
||||
def _login(self, method, username, password):
|
||||
self._session = _parse_result(
|
||||
getattr(self, 'session.%s' % method)(username, password))
|
||||
|
||||
|
||||
def __getattr__(self, name):
|
||||
if name == 'xenapi':
|
||||
return _Dispatcher(self._xen_request, None)
|
||||
elif name.startswith('login'):
|
||||
return lambda u, p: self._login(name, u, p)
|
||||
else:
|
||||
return xen.util.xmlrpclib2.ServerProxy.__getattr__(self, name)
|
||||
|
||||
|
||||
def _parse_result(result):
|
||||
if 'Status' not in result:
|
||||
raise xmlrpclib.Fault(500, 'Missing Status in response from server')
|
||||
if result['Status'] == 'Success':
|
||||
if 'Value' in result:
|
||||
return result['Value']
|
||||
else:
|
||||
raise xmlrpclib.Fault(500,
|
||||
'Missing Value in response from server')
|
||||
else:
|
||||
if 'ErrorDescription' in result:
|
||||
raise Failure(result['ErrorDescription'])
|
||||
else:
|
||||
raise xmlrpclib.Fault(
|
||||
500, 'Missing ErrorDescription in response from server')
|
||||
|
||||
|
||||
# Based upon _Method from xmlrpclib.
|
||||
class _Dispatcher:
|
||||
def __init__(self, send, name):
|
||||
self.__send = send
|
||||
self.__name = name
|
||||
def __getattr__(self, name):
|
||||
if self.__name is None:
|
||||
return _Dispatcher(self.__send, name)
|
||||
else:
|
||||
return _Dispatcher(self.__send, "%s.%s" % (self.__name, name))
|
||||
def __call__(self, *args):
|
||||
return self.__send(self.__name, args)
|
||||
@@ -29,13 +29,13 @@ import xmlrpclib
|
||||
from xen.xend import sxp
|
||||
from xen.xend import PrettyPrint
|
||||
import xen.xend.XendClient
|
||||
from xen.xend.XendClient import server
|
||||
from xen.xend.XendBootloader import bootloader
|
||||
from xen.util import blkif
|
||||
from xen.util import security
|
||||
|
||||
from xen.xm.opts import *
|
||||
|
||||
from main import server
|
||||
import console
|
||||
|
||||
|
||||
@@ -284,6 +284,18 @@ gopts.var('usbport', val='PATH',
|
||||
use="""Add a physical USB port to a domain, as specified by the path
|
||||
to that port. This option may be repeated to add more than one port.""")
|
||||
|
||||
gopts.var('vfb', val="type={vnc,sdl},vncunused=1,vncdisplay=N,vnclisten=ADDR,display=DISPLAY,xauthority=XAUTHORITY",
|
||||
fn=append_value, default=[],
|
||||
use="""Make the domain a framebuffer backend.
|
||||
The backend type should be either sdl or vnc.
|
||||
For type=vnc, connect an external vncviewer. The server will listen
|
||||
on ADDR (default 127.0.0.1) on port N+5900. N defaults to the
|
||||
domain id. If vncunused=1, the server will try to find an arbitrary
|
||||
unused port above 5900.
|
||||
For type=sdl, a viewer will be started automatically using the
|
||||
given DISPLAY and XAUTHORITY, which default to the current user's
|
||||
ones.""")
|
||||
|
||||
gopts.var('vif', val="type=TYPE,mac=MAC,bridge=BRIDGE,ip=IPADDR,script=SCRIPT,backend=DOM,vifname=NAME",
|
||||
fn=append_value, default=[],
|
||||
use="""Add a network interface with the given MAC address and bridge.
|
||||
@@ -512,8 +524,8 @@ def configure_image(vals):
|
||||
config_image.append(['args', vals.extra])
|
||||
|
||||
if vals.builder == 'hvm':
|
||||
configure_hvm(config_image, vals)
|
||||
|
||||
configure_hvm(config_image, vals)
|
||||
|
||||
return config_image
|
||||
|
||||
def configure_disks(config_devs, vals):
|
||||
@@ -564,6 +576,23 @@ def configure_usb(config_devs, vals):
|
||||
config_usb = ['usbport', ['path', path]]
|
||||
config_devs.append(['device', config_usb])
|
||||
|
||||
def configure_vfbs(config_devs, vals):
|
||||
for f in vals.vfb:
|
||||
d = comma_sep_kv_to_dict(f)
|
||||
config = ['vfb']
|
||||
if not d.has_key("type"):
|
||||
d['type'] = 'sdl'
|
||||
for (k,v) in d.iteritems():
|
||||
if not k in [ 'vnclisten', 'vncunused', 'vncdisplay', 'display',
|
||||
'xauthority', 'type' ]:
|
||||
err("configuration option %s unknown to vfbs" % k)
|
||||
config.append([k,v])
|
||||
if not d.has_key("display") and os.environ.has_key("DISPLAY"):
|
||||
config.append(["display", os.environ['DISPLAY']])
|
||||
if not d.has_key("xauthority"):
|
||||
config.append(["xauthority", get_xauthority()])
|
||||
config_devs.append(['device', ['vkbd']])
|
||||
config_devs.append(['device', config])
|
||||
|
||||
def configure_security(config, vals):
|
||||
"""Create the config for ACM security labels.
|
||||
@@ -675,8 +704,10 @@ def configure_hvm(config_image, vals):
|
||||
config_image.append(['vncpasswd', vals.vncpasswd])
|
||||
|
||||
def run_bootloader(vals, config_image):
|
||||
if not os.access(vals.bootloader, os.F_OK):
|
||||
err("Bootloader '%s' does not exist" % vals.bootloader)
|
||||
if not os.access(vals.bootloader, os.X_OK):
|
||||
err("Bootloader isn't executable")
|
||||
err("Bootloader '%s' isn't executable" % vals.bootloader)
|
||||
if len(vals.disk) < 1:
|
||||
err("No disks configured and boot loader requested")
|
||||
(uname, dev, mode, backend) = vals.disk[0]
|
||||
@@ -742,6 +773,7 @@ def make_config(vals):
|
||||
configure_vifs(config_devs, vals)
|
||||
configure_usb(config_devs, vals)
|
||||
configure_vtpm(config_devs, vals)
|
||||
configure_vfbs(config_devs, vals)
|
||||
configure_security(config, vals)
|
||||
config += config_devs
|
||||
|
||||
|
||||
+168
-23
@@ -21,6 +21,7 @@
|
||||
|
||||
"""Grand unified management application for Xen.
|
||||
"""
|
||||
import atexit
|
||||
import os
|
||||
import sys
|
||||
import re
|
||||
@@ -29,8 +30,10 @@ import socket
|
||||
import traceback
|
||||
import xmlrpclib
|
||||
import traceback
|
||||
import time
|
||||
import datetime
|
||||
from select import select
|
||||
import xml.dom.minidom
|
||||
|
||||
import warnings
|
||||
warnings.filterwarnings('ignore', category=FutureWarning)
|
||||
@@ -38,12 +41,14 @@ warnings.filterwarnings('ignore', category=FutureWarning)
|
||||
from xen.xend import PrettyPrint
|
||||
from xen.xend import sxp
|
||||
from xen.xend import XendClient
|
||||
from xen.xend.XendClient import server
|
||||
from xen.xend.XendConstants import *
|
||||
|
||||
from xen.xm.opts import OptionError, Opts, wrap, set_true
|
||||
from xen.xm import console
|
||||
from xen.util import security
|
||||
from xen.util.xmlrpclib2 import ServerProxy
|
||||
|
||||
import XenAPI
|
||||
|
||||
# getopt.gnu_getopt is better, but only exists in Python 2.3+. Use
|
||||
# getopt.getopt if gnu_getopt is not available. This will mean that options
|
||||
@@ -51,6 +56,12 @@ from xen.util import security
|
||||
if not hasattr(getopt, 'gnu_getopt'):
|
||||
getopt.gnu_getopt = getopt.getopt
|
||||
|
||||
XM_CONFIG_FILE = '/etc/xen/xm-config.xml'
|
||||
|
||||
# Supported types of server
|
||||
SERVER_LEGACY_XMLRPC = 'LegacyXMLRPC'
|
||||
SERVER_XEN_API = 'Xen-API'
|
||||
|
||||
# General help message
|
||||
|
||||
USAGE_HELP = "Usage: xm <subcommand> [args]\n\n" \
|
||||
@@ -127,9 +138,9 @@ SUBCOMMAND_HELP = {
|
||||
|
||||
# device commands
|
||||
|
||||
'block-attach' : ('<Domain> <BackDev> <FrontDev> <Mode>',
|
||||
'block-attach' : ('<Domain> <BackDev> <FrontDev> <Mode> [BackDomain]',
|
||||
'Create a new virtual block device.'),
|
||||
'block-configure': ('<Domain> <BackDev> <FrontDev> <Mode> [BackDomId]',
|
||||
'block-configure': ('<Domain> <BackDev> <FrontDev> <Mode> [BackDomain]',
|
||||
'Change block device configuration'),
|
||||
'block-detach' : ('<Domain> <DevId>',
|
||||
'Destroy a domain\'s virtual block device.'),
|
||||
@@ -207,7 +218,13 @@ SUBCOMMAND_OPTIONS = {
|
||||
('-L', '--live', 'Dump core without pausing the domain'),
|
||||
('-C', '--crash', 'Crash domain after dumping core'),
|
||||
),
|
||||
'restore': (
|
||||
'start': (
|
||||
('-p', '--paused', 'Do not unpause domain after starting it'),
|
||||
),
|
||||
'resume': (
|
||||
('-p', '--paused', 'Do not unpause domain after resuming it'),
|
||||
),
|
||||
'restore': (
|
||||
('-p', '--paused', 'Do not unpause domain after restoring it'),
|
||||
),
|
||||
}
|
||||
@@ -313,6 +330,40 @@ acm_commands = [
|
||||
all_commands = (domain_commands + host_commands + scheduler_commands +
|
||||
device_commands + vnet_commands + acm_commands)
|
||||
|
||||
|
||||
##
|
||||
# Configuration File Parsing
|
||||
##
|
||||
|
||||
config = None
|
||||
if os.path.isfile(XM_CONFIG_FILE):
|
||||
try:
|
||||
config = xml.dom.minidom.parse(XM_CONFIG_FILE)
|
||||
except:
|
||||
print >>sys.stderr, ('Ignoring invalid configuration file %s.' %
|
||||
XM_CONFIG_FILE)
|
||||
|
||||
def parseServer():
|
||||
if config:
|
||||
server = config.getElementsByTagName('server')
|
||||
if server:
|
||||
st = server[0].getAttribute('type')
|
||||
if st != SERVER_XEN_API and st != SERVER_LEGACY_XMLRPC:
|
||||
print >>sys.stderr, ('Invalid server type %s; using %s.' %
|
||||
(st, SERVER_LEGACY_XMLRPC))
|
||||
st = SERVER_LEGACY_XMLRPC
|
||||
return (st, server[0].getAttribute('uri'))
|
||||
|
||||
return SERVER_LEGACY_XMLRPC, XendClient.uri
|
||||
|
||||
def parseAuthentication():
|
||||
server = config.getElementsByTagName('server')[0]
|
||||
return (server.getAttribute('username'),
|
||||
server.getAttribute('password'))
|
||||
|
||||
serverType, serverURI = parseServer()
|
||||
|
||||
|
||||
####################################################################
|
||||
#
|
||||
# Help/usage printing functions
|
||||
@@ -463,6 +514,16 @@ def err(msg):
|
||||
print >>sys.stderr, "Error:", msg
|
||||
|
||||
|
||||
def get_single_vm(dom):
|
||||
uuids = server.xenapi.VM.get_by_name_label(dom)
|
||||
n = len(uuids)
|
||||
if n == 1:
|
||||
return uuids[0]
|
||||
else:
|
||||
dominfo = server.xend.domain(dom, False)
|
||||
return dominfo['uuid']
|
||||
|
||||
|
||||
#########################################################################
|
||||
#
|
||||
# Main xm functions
|
||||
@@ -571,15 +632,21 @@ def parse_doms_info(info):
|
||||
|
||||
def get_status(n, t, d):
|
||||
return DOM_STATES[t(sxp.child_value(info, n, d))]
|
||||
|
||||
|
||||
start_time = get_info('start_time', float, -1)
|
||||
if start_time == -1:
|
||||
up_time = float(-1)
|
||||
else:
|
||||
up_time = time.time() - start_time
|
||||
|
||||
return {
|
||||
'domid' : get_info('domid', str, ''),
|
||||
'name' : get_info('name', str, '??'),
|
||||
'mem' : get_info('memory_dynamic_max', int, 0),
|
||||
'vcpus' : get_info('online_vcpus', int, 0),
|
||||
'mem' : get_info('memory_dynamic_min', int, 0),
|
||||
'vcpus' : get_info('online_vcpus', int, 0),
|
||||
'state' : get_info('state', str, ''),
|
||||
'cpu_time' : get_info('cpu_time', float, 0),
|
||||
'up_time' : get_info('up_time', float, -1),
|
||||
'up_time' : up_time,
|
||||
'seclabel' : security.get_security_printlabel(info),
|
||||
}
|
||||
|
||||
@@ -742,24 +809,70 @@ def xm_vcpu_list(args):
|
||||
print format % locals()
|
||||
|
||||
def xm_start(args):
|
||||
arg_check(args, "start", 1)
|
||||
dom = args[0]
|
||||
server.xend.domain.start(dom)
|
||||
arg_check(args, "start", 1, 2)
|
||||
|
||||
try:
|
||||
(options, params) = getopt.gnu_getopt(args, 'p', ['paused'])
|
||||
except getopt.GetoptError, opterr:
|
||||
err(opterr)
|
||||
sys.exit(1)
|
||||
|
||||
paused = False
|
||||
for (k, v) in options:
|
||||
if k in ['-p', '--paused']:
|
||||
paused = True
|
||||
|
||||
if len(params) != 1:
|
||||
err("Wrong number of parameters")
|
||||
usage('start')
|
||||
sys.exit(1)
|
||||
|
||||
dom = params[0]
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.start(get_single_vm(dom), paused)
|
||||
else:
|
||||
server.xend.domain.start(dom, paused)
|
||||
|
||||
def xm_delete(args):
|
||||
arg_check(args, "delete", 1)
|
||||
dom = args[0]
|
||||
server.xend.domain.delete(dom)
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.destroy(get_single_vm(dom))
|
||||
else:
|
||||
server.xend.domain.delete(dom)
|
||||
|
||||
def xm_suspend(args):
|
||||
arg_check(args, "suspend", 1)
|
||||
dom = args[0]
|
||||
server.xend.domain.suspend(dom)
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.suspend(get_single_vm(dom))
|
||||
else:
|
||||
server.xend.domain.suspend(dom)
|
||||
|
||||
def xm_resume(args):
|
||||
arg_check(args, "resume", 1)
|
||||
dom = args[0]
|
||||
server.xend.domain.resume(dom)
|
||||
arg_check(args, "resume", 1, 2)
|
||||
|
||||
try:
|
||||
(options, params) = getopt.gnu_getopt(args, 'p', ['paused'])
|
||||
except getopt.GetoptError, opterr:
|
||||
err(opterr)
|
||||
sys.exit(1)
|
||||
|
||||
paused = False
|
||||
for (k, v) in options:
|
||||
if k in ['-p', '--paused']:
|
||||
paused = True
|
||||
|
||||
if len(params) != 1:
|
||||
err("Wrong number of parameters")
|
||||
usage('resume')
|
||||
sys.exit(1)
|
||||
|
||||
dom = params[0]
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.resume(get_single_vm(dom), paused)
|
||||
else:
|
||||
server.xend.domain.resume(dom, paused)
|
||||
|
||||
def xm_reboot(args):
|
||||
arg_check(args, "reboot", 1, 3)
|
||||
@@ -775,13 +888,19 @@ def xm_pause(args):
|
||||
arg_check(args, "pause", 1)
|
||||
dom = args[0]
|
||||
|
||||
server.xend.domain.pause(dom)
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.pause(get_single_vm(dom))
|
||||
else:
|
||||
server.xend.domain.pause(dom)
|
||||
|
||||
def xm_unpause(args):
|
||||
arg_check(args, "unpause", 1)
|
||||
dom = args[0]
|
||||
|
||||
server.xend.domain.unpause(dom)
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.unpause(get_single_vm(dom))
|
||||
else:
|
||||
server.xend.domain.unpause(dom)
|
||||
|
||||
def xm_dump_core(args):
|
||||
live = False
|
||||
@@ -822,7 +941,10 @@ def xm_dump_core(args):
|
||||
def xm_rename(args):
|
||||
arg_check(args, "rename", 2)
|
||||
|
||||
server.xend.domain.setName(args[0], args[1])
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.set_name_label(get_single_vm(args[0]), args[1])
|
||||
else:
|
||||
server.xend.domain.setName(args[0], args[1])
|
||||
|
||||
def xm_importcommand(command, args):
|
||||
cmd = __import__(command, globals(), locals(), 'xen.xm')
|
||||
@@ -880,7 +1002,12 @@ def xm_vcpu_set(args):
|
||||
|
||||
def xm_destroy(args):
|
||||
arg_check(args, "destroy", 1)
|
||||
server.xend.domain.destroy(args[0])
|
||||
|
||||
dom = args[0]
|
||||
if serverType == SERVER_XEN_API:
|
||||
server.xenapi.VM.hard_shutdown(get_single_vm(dom))
|
||||
else:
|
||||
server.xend.domain.destroy(dom)
|
||||
|
||||
|
||||
def xm_domid(args):
|
||||
@@ -1094,7 +1221,7 @@ def xm_uptime(args):
|
||||
|
||||
for dom in doms:
|
||||
d = parse_doms_info(dom)
|
||||
if d['domid'] > 0:
|
||||
if int(d['domid']) > 0:
|
||||
uptime = int(round(d['up_time']))
|
||||
else:
|
||||
f=open('/proc/uptime', 'r')
|
||||
@@ -1121,10 +1248,10 @@ def xm_uptime(args):
|
||||
if short_mode:
|
||||
now = datetime.datetime.now()
|
||||
upstring = now.strftime(" %H:%M:%S") + " up " + upstring
|
||||
upstring += ", " + d['name'] + " (" + str(d['domid']) + ")"
|
||||
upstring += ", " + d['name'] + " (" + d['domid'] + ")"
|
||||
else:
|
||||
upstring += ':%(seconds)02d' % vars()
|
||||
upstring = ("%(name)-32s %(domid)3d " % d) + upstring
|
||||
upstring = ("%(name)-32s %(domid)3s " % d) + upstring
|
||||
|
||||
print upstring
|
||||
|
||||
@@ -1537,6 +1664,8 @@ def deprecated(old,new):
|
||||
"Command %s is deprecated. Please use xm %s instead." % (old, new))
|
||||
|
||||
def main(argv=sys.argv):
|
||||
global server
|
||||
|
||||
if len(argv) < 2:
|
||||
usage()
|
||||
|
||||
@@ -1555,6 +1684,19 @@ def main(argv=sys.argv):
|
||||
args = argv[2:]
|
||||
if cmd:
|
||||
try:
|
||||
if serverType == SERVER_XEN_API:
|
||||
server = XenAPI.Session(serverURI)
|
||||
username, password = parseAuthentication()
|
||||
server.login_with_password(username, password)
|
||||
def logout():
|
||||
try:
|
||||
server.xenapi.session.logout()
|
||||
except:
|
||||
pass
|
||||
atexit.register(logout)
|
||||
else:
|
||||
server = ServerProxy(serverURI)
|
||||
|
||||
rc = cmd(args)
|
||||
if rc:
|
||||
usage()
|
||||
@@ -1575,6 +1717,9 @@ def main(argv=sys.argv):
|
||||
sys.exit(1)
|
||||
except SystemExit:
|
||||
sys.exit(1)
|
||||
except XenAPI.Failure, exn:
|
||||
err(str(exn))
|
||||
sys.exit(1)
|
||||
except xmlrpclib.Fault, ex:
|
||||
if ex.faultCode == XendClient.ERROR_INVALID_DOMAIN:
|
||||
err("Domain '%s' does not exist." % ex.faultString)
|
||||
|
||||
@@ -21,9 +21,10 @@
|
||||
|
||||
import sys
|
||||
|
||||
from xen.xend.XendClient import server
|
||||
from xen.xm.opts import *
|
||||
|
||||
from main import server
|
||||
|
||||
gopts = Opts(use="""[options] DOM HOST
|
||||
|
||||
Migrate domain DOM to host HOST.
|
||||
|
||||
@@ -21,10 +21,9 @@ import xmlrpclib
|
||||
from xen.xend import PrettyPrint
|
||||
from xen.xend import sxp
|
||||
from xen.xend import XendClient
|
||||
from xen.xend.XendClient import server
|
||||
|
||||
from xen.xm.opts import *
|
||||
from xen.xm.create import *
|
||||
from opts import *
|
||||
from create import *
|
||||
|
||||
def make_unstarted_domain(opts, config):
|
||||
"""Create an unstarted domain.
|
||||
@@ -58,6 +57,12 @@ def main(argv):
|
||||
if not opts:
|
||||
return
|
||||
|
||||
if type(config) == str:
|
||||
try:
|
||||
config = sxp.parse(file(config))[0]
|
||||
except IOError, exn:
|
||||
raise OptionError("Cannot read file %s: %s" % (config, exn[1]))
|
||||
|
||||
if opts.vals.dryrun:
|
||||
PrettyPrint.prettyprint(config)
|
||||
else:
|
||||
|
||||
@@ -19,9 +19,9 @@
|
||||
"""
|
||||
import time
|
||||
|
||||
from xen.xend.XendClient import server
|
||||
from xen.xend import sxp
|
||||
from xen.xm.opts import *
|
||||
from opts import *
|
||||
from main import server
|
||||
|
||||
gopts = Opts(use="""[options] [DOM]
|
||||
|
||||
|
||||