libxl: move libxlVmStart to libxl_domain

Move libxlVmStart from libxl_driver to libxl_domain for
use by other libxl modules.  For consistency, rename to
libxlDomainStart.

Signed-off-by: Jim Fehlig <jfehlig@suse.com>
This commit is contained in:
Jim Fehlig 2014-02-26 14:11:30 -07:00
parent 024e4bb400
commit 3182448f4c
3 changed files with 192 additions and 191 deletions

View File

@ -893,3 +893,184 @@ libxlDomainFreeMem(libxlDomainObjPrivatePtr priv, libxl_domain_config *d_config)
return ret;
}
/*
* Start a domain through libxenlight.
*
* virDomainObjPtr must be locked on invocation
*/
int
libxlDomainStart(libxlDriverPrivatePtr driver, virDomainObjPtr vm,
bool start_paused, int restore_fd)
{
libxl_domain_config d_config;
virDomainDefPtr def = NULL;
virObjectEventPtr event = NULL;
libxlSavefileHeader hdr;
int ret = -1;
uint32_t domid = 0;
char *dom_xml = NULL;
char *managed_save_path = NULL;
int managed_save_fd = -1;
libxlDomainObjPrivatePtr priv = vm->privateData;
libxlDriverConfigPtr cfg;
#ifdef LIBXL_HAVE_DOMAIN_CREATE_RESTORE_PARAMS
libxl_domain_restore_params params;
#endif
virHostdevManagerPtr hostdev_mgr = driver->hostdevMgr;
if (libxlDomainObjPrivateInitCtx(vm) < 0)
return ret;
if (libxlDomainObjBeginJob(driver, vm, LIBXL_JOB_MODIFY) < 0)
return ret;
cfg = libxlDriverConfigGet(driver);
/* If there is a managed saved state restore it instead of starting
* from scratch. The old state is removed once the restoring succeeded. */
if (restore_fd < 0) {
managed_save_path = libxlDomainManagedSavePath(driver, vm);
if (managed_save_path == NULL)
goto endjob;
if (virFileExists(managed_save_path)) {
managed_save_fd = libxlDomainSaveImageOpen(driver, cfg,
managed_save_path,
&def, &hdr);
if (managed_save_fd < 0)
goto endjob;
restore_fd = managed_save_fd;
if (STRNEQ(vm->def->name, def->name) ||
memcmp(vm->def->uuid, def->uuid, VIR_UUID_BUFLEN)) {
char vm_uuidstr[VIR_UUID_STRING_BUFLEN];
char def_uuidstr[VIR_UUID_STRING_BUFLEN];
virUUIDFormat(vm->def->uuid, vm_uuidstr);
virUUIDFormat(def->uuid, def_uuidstr);
virReportError(VIR_ERR_OPERATION_FAILED,
_("cannot restore domain '%s' uuid %s from a file"
" which belongs to domain '%s' uuid %s"),
vm->def->name, vm_uuidstr, def->name, def_uuidstr);
goto endjob;
}
virDomainObjAssignDef(vm, def, true, NULL);
def = NULL;
if (unlink(managed_save_path) < 0)
VIR_WARN("Failed to remove the managed state %s",
managed_save_path);
vm->hasManagedSave = false;
}
VIR_FREE(managed_save_path);
}
libxl_domain_config_init(&d_config);
if (libxlBuildDomainConfig(driver, vm, &d_config) < 0)
goto endjob;
if (cfg->autoballoon && libxlDomainFreeMem(priv, &d_config) < 0) {
virReportError(VIR_ERR_INTERNAL_ERROR,
_("libxenlight failed to get free memory for domain '%s'"),
d_config.c_info.name);
goto endjob;
}
if (virHostdevPrepareDomainDevices(hostdev_mgr, LIBXL_DRIVER_NAME,
vm->def, VIR_HOSTDEV_SP_PCI) < 0)
goto endjob;
/* Unlock virDomainObj while creating the domain */
virObjectUnlock(vm);
if (restore_fd < 0) {
ret = libxl_domain_create_new(priv->ctx, &d_config,
&domid, NULL, NULL);
} else {
#ifdef LIBXL_HAVE_DOMAIN_CREATE_RESTORE_PARAMS
params.checkpointed_stream = 0;
ret = libxl_domain_create_restore(priv->ctx, &d_config, &domid,
restore_fd, &params, NULL, NULL);
#else
ret = libxl_domain_create_restore(priv->ctx, &d_config, &domid,
restore_fd, NULL, NULL);
#endif
}
virObjectLock(vm);
if (ret) {
if (restore_fd < 0)
virReportError(VIR_ERR_INTERNAL_ERROR,
_("libxenlight failed to create new domain '%s'"),
d_config.c_info.name);
else
virReportError(VIR_ERR_INTERNAL_ERROR,
_("libxenlight failed to restore domain '%s'"),
d_config.c_info.name);
goto endjob;
}
/*
* The domain has been successfully created with libxl, so it should
* be cleaned up if there are any subsequent failures.
*/
vm->def->id = domid;
if (libxlDomainEventsRegister(vm) < 0)
goto cleanup_dom;
if ((dom_xml = virDomainDefFormat(vm->def, 0)) == NULL)
goto cleanup_dom;
if (libxl_userdata_store(priv->ctx, domid, "libvirt-xml",
(uint8_t *)dom_xml, strlen(dom_xml) + 1)) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
_("libxenlight failed to store userdata"));
goto cleanup_dom;
}
if (libxlDomainSetVcpuAffinities(driver, vm) < 0)
goto cleanup_dom;
if (!start_paused) {
libxl_domain_unpause(priv->ctx, domid);
virDomainObjSetState(vm, VIR_DOMAIN_RUNNING, VIR_DOMAIN_RUNNING_BOOTED);
} else {
virDomainObjSetState(vm, VIR_DOMAIN_PAUSED, VIR_DOMAIN_PAUSED_USER);
}
if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm) < 0)
goto cleanup_dom;
if (virAtomicIntInc(&driver->nactive) == 1 && driver->inhibitCallback)
driver->inhibitCallback(true, driver->inhibitOpaque);
event = virDomainEventLifecycleNewFromObj(vm, VIR_DOMAIN_EVENT_STARTED,
restore_fd < 0 ?
VIR_DOMAIN_EVENT_STARTED_BOOTED :
VIR_DOMAIN_EVENT_STARTED_RESTORED);
if (event)
libxlDomainEventQueue(driver, event);
ret = 0;
goto endjob;
cleanup_dom:
libxl_domain_destroy(priv->ctx, domid, NULL);
vm->def->id = -1;
virDomainObjSetState(vm, VIR_DOMAIN_SHUTOFF, VIR_DOMAIN_SHUTOFF_FAILED);
endjob:
if (!libxlDomainObjEndJob(driver, vm))
vm = NULL;
libxl_domain_config_dispose(&d_config);
VIR_FREE(dom_xml);
VIR_FREE(managed_save_path);
virDomainDefFree(def);
VIR_FORCE_CLOSE(managed_save_fd);
virObjectUnref(cfg);
return ret;
}

View File

@ -131,4 +131,10 @@ int
libxlDomainFreeMem(libxlDomainObjPrivatePtr priv,
libxl_domain_config *d_config);
int
libxlDomainStart(libxlDriverPrivatePtr driver,
virDomainObjPtr vm,
bool start_paused,
int restore_fd);
#endif /* LIBXL_DOMAIN_H */

View File

@ -81,10 +81,6 @@ static int
libxlDomainManagedSaveLoad(virDomainObjPtr vm,
void *opaque);
static int
libxlVmStart(libxlDriverPrivatePtr driver, virDomainObjPtr vm,
bool start_paused, int restore_fd);
/* Function definitions */
static virDomainObjPtr
@ -118,7 +114,7 @@ libxlAutostartDomain(virDomainObjPtr vm,
virResetLastError();
if (vm->autostart && !virDomainObjIsActive(vm) &&
libxlVmStart(driver, vm, false, -1) < 0) {
libxlDomainStart(driver, vm, false, -1) < 0) {
err = virGetLastError();
VIR_ERROR(_("Failed to autostart VM '%s': %s"),
vm->def->name,
@ -245,7 +241,7 @@ restart:
}
libxl_domain_destroy(ctx, vm->def->id, NULL);
libxlDomainCleanupJob(driver, vm, VIR_DOMAIN_SHUTOFF_SHUTDOWN);
libxlVmStart(driver, vm, 0, -1);
libxlDomainStart(driver, vm, 0, -1);
cleanup:
if (vm)
@ -311,188 +307,6 @@ const struct libxl_event_hooks ev_hooks = {
.disaster = NULL,
};
/*
* Start a domain through libxenlight.
*
* virDomainObjPtr should be locked on invocation
*/
static int
libxlVmStart(libxlDriverPrivatePtr driver, virDomainObjPtr vm,
bool start_paused, int restore_fd)
{
libxl_domain_config d_config;
virDomainDefPtr def = NULL;
virObjectEventPtr event = NULL;
libxlSavefileHeader hdr;
int ret = -1;
uint32_t domid = 0;
char *dom_xml = NULL;
char *managed_save_path = NULL;
int managed_save_fd = -1;
libxlDomainObjPrivatePtr priv = vm->privateData;
libxlDriverConfigPtr cfg;
#ifdef LIBXL_HAVE_DOMAIN_CREATE_RESTORE_PARAMS
libxl_domain_restore_params params;
#endif
virHostdevManagerPtr hostdev_mgr = driver->hostdevMgr;
if (libxlDomainObjPrivateInitCtx(vm) < 0)
return ret;
if (libxlDomainObjBeginJob(driver, vm, LIBXL_JOB_MODIFY) < 0)
return ret;
cfg = libxlDriverConfigGet(driver);
/* If there is a managed saved state restore it instead of starting
* from scratch. The old state is removed once the restoring succeeded. */
if (restore_fd < 0) {
managed_save_path = libxlDomainManagedSavePath(driver, vm);
if (managed_save_path == NULL)
goto endjob;
if (virFileExists(managed_save_path)) {
managed_save_fd = libxlDomainSaveImageOpen(driver, cfg,
managed_save_path,
&def, &hdr);
if (managed_save_fd < 0)
goto endjob;
restore_fd = managed_save_fd;
if (STRNEQ(vm->def->name, def->name) ||
memcmp(vm->def->uuid, def->uuid, VIR_UUID_BUFLEN)) {
char vm_uuidstr[VIR_UUID_STRING_BUFLEN];
char def_uuidstr[VIR_UUID_STRING_BUFLEN];
virUUIDFormat(vm->def->uuid, vm_uuidstr);
virUUIDFormat(def->uuid, def_uuidstr);
virReportError(VIR_ERR_OPERATION_FAILED,
_("cannot restore domain '%s' uuid %s from a file"
" which belongs to domain '%s' uuid %s"),
vm->def->name, vm_uuidstr, def->name, def_uuidstr);
goto endjob;
}
virDomainObjAssignDef(vm, def, true, NULL);
def = NULL;
if (unlink(managed_save_path) < 0)
VIR_WARN("Failed to remove the managed state %s",
managed_save_path);
vm->hasManagedSave = false;
}
VIR_FREE(managed_save_path);
}
libxl_domain_config_init(&d_config);
if (libxlBuildDomainConfig(driver, vm, &d_config) < 0)
goto endjob;
if (cfg->autoballoon && libxlDomainFreeMem(priv, &d_config) < 0) {
virReportError(VIR_ERR_INTERNAL_ERROR,
_("libxenlight failed to get free memory for domain '%s'"),
d_config.c_info.name);
goto endjob;
}
if (virHostdevPrepareDomainDevices(hostdev_mgr, LIBXL_DRIVER_NAME,
vm->def, VIR_HOSTDEV_SP_PCI) < 0)
goto endjob;
/* Unlock virDomainObj while creating the domain */
virObjectUnlock(vm);
if (restore_fd < 0) {
ret = libxl_domain_create_new(priv->ctx, &d_config,
&domid, NULL, NULL);
} else {
#ifdef LIBXL_HAVE_DOMAIN_CREATE_RESTORE_PARAMS
params.checkpointed_stream = 0;
ret = libxl_domain_create_restore(priv->ctx, &d_config, &domid,
restore_fd, &params, NULL, NULL);
#else
ret = libxl_domain_create_restore(priv->ctx, &d_config, &domid,
restore_fd, NULL, NULL);
#endif
}
virObjectLock(vm);
if (ret) {
if (restore_fd < 0)
virReportError(VIR_ERR_INTERNAL_ERROR,
_("libxenlight failed to create new domain '%s'"),
d_config.c_info.name);
else
virReportError(VIR_ERR_INTERNAL_ERROR,
_("libxenlight failed to restore domain '%s'"),
d_config.c_info.name);
goto endjob;
}
/*
* The domain has been successfully created with libxl, so it should
* be cleaned up if there are any subsequent failures.
*/
vm->def->id = domid;
if (libxlDomainEventsRegister(vm) < 0)
goto cleanup_dom;
if ((dom_xml = virDomainDefFormat(vm->def, 0)) == NULL)
goto cleanup_dom;
if (libxl_userdata_store(priv->ctx, domid, "libvirt-xml",
(uint8_t *)dom_xml, strlen(dom_xml) + 1)) {
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
_("libxenlight failed to store userdata"));
goto cleanup_dom;
}
if (libxlDomainSetVcpuAffinities(driver, vm) < 0)
goto cleanup_dom;
if (!start_paused) {
libxl_domain_unpause(priv->ctx, domid);
virDomainObjSetState(vm, VIR_DOMAIN_RUNNING, VIR_DOMAIN_RUNNING_BOOTED);
} else {
virDomainObjSetState(vm, VIR_DOMAIN_PAUSED, VIR_DOMAIN_PAUSED_USER);
}
if (virDomainSaveStatus(driver->xmlopt, cfg->stateDir, vm) < 0)
goto cleanup_dom;
if (virAtomicIntInc(&driver->nactive) == 1 && driver->inhibitCallback)
driver->inhibitCallback(true, driver->inhibitOpaque);
event = virDomainEventLifecycleNewFromObj(vm, VIR_DOMAIN_EVENT_STARTED,
restore_fd < 0 ?
VIR_DOMAIN_EVENT_STARTED_BOOTED :
VIR_DOMAIN_EVENT_STARTED_RESTORED);
if (event)
libxlDomainEventQueue(driver, event);
ret = 0;
goto endjob;
cleanup_dom:
libxl_domain_destroy(priv->ctx, domid, NULL);
vm->def->id = -1;
virDomainObjSetState(vm, VIR_DOMAIN_SHUTOFF, VIR_DOMAIN_SHUTOFF_FAILED);
endjob:
if (!libxlDomainObjEndJob(driver, vm))
vm = NULL;
libxl_domain_config_dispose(&d_config);
VIR_FREE(dom_xml);
VIR_FREE(managed_save_path);
virDomainDefFree(def);
VIR_FORCE_CLOSE(managed_save_fd);
virObjectUnref(cfg);
return ret;
}
/*
* Reconnect to running domains that were previously started/created
* with libxenlight driver.
@ -1018,7 +832,7 @@ libxlDomainCreateXML(virConnectPtr conn, const char *xml,
goto cleanup;
def = NULL;
if (libxlVmStart(driver, vm, (flags & VIR_DOMAIN_START_PAUSED) != 0,
if (libxlDomainStart(driver, vm, (flags & VIR_DOMAIN_START_PAUSED) != 0,
-1) < 0) {
virDomainObjListRemove(driver->domains, vm);
vm = NULL;
@ -1798,7 +1612,7 @@ libxlDomainRestoreFlags(virConnectPtr conn, const char *from,
def = NULL;
ret = libxlVmStart(driver, vm, (flags & VIR_DOMAIN_SAVE_PAUSED) != 0, fd);
ret = libxlDomainStart(driver, vm, (flags & VIR_DOMAIN_SAVE_PAUSED) != 0, fd);
if (ret < 0 && !vm->persistent) {
virDomainObjListRemove(driver->domains, vm);
vm = NULL;
@ -2687,7 +2501,7 @@ libxlDomainCreateWithFlags(virDomainPtr dom,
goto cleanup;
}
ret = libxlVmStart(driver, vm, (flags & VIR_DOMAIN_START_PAUSED) != 0, -1);
ret = libxlDomainStart(driver, vm, (flags & VIR_DOMAIN_START_PAUSED) != 0, -1);
cleanup:
if (vm)