This patch introduces possibility to reboot domain after core dump
finishes. The new flag VIR_DUMP_REBOOT was added to
virDomainCoreDumpFlags. The new functionality is accessible via virsh
too: virsh dump --reboot <domain>
---
diff to v2:
-issue reset command instead of qemuDomainReboot
include/libvirt/libvirt.h.in | 1 +
src/qemu/qemu_driver.c | 54 +++++++++++++++++++++++++++++++++++++++--
tools/virsh.c | 3 ++
3 files changed, 55 insertions(+), 3 deletions(-)
diff --git a/include/libvirt/libvirt.h.in b/include/libvirt/libvirt.h.in
index 39155a6..8c41f5a 100644
--- a/include/libvirt/libvirt.h.in
+++ b/include/libvirt/libvirt.h.in
@@ -748,6 +748,7 @@ typedef enum {
VIR_DUMP_CRASH = (1 << 0), /* crash after dump */
VIR_DUMP_LIVE = (1 << 1), /* live dump */
VIR_DUMP_BYPASS_CACHE = (1 << 2), /* avoid file system cache pollution */
+ VIR_DUMP_REBOOT = (1 << 3), /* reboot domain after dump finishes */
} virDomainCoreDumpFlags;
/* Domain migration flags. */
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 0d0bea2..3e05e14 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -2860,6 +2860,47 @@ getCompressionType(struct qemud_driver *driver)
return compress;
}
+static int
+doSystemReset(struct qemud_driver *driver,
+ virDomainObjPtr *vm)
+{
+ int ret = -1;
+ qemuDomainObjPrivatePtr priv;
+
+ /* Okay, this should never happen, but doesn't hurt to check. */
+ if (!driver || !vm || !*vm) {
+ qemuReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("invalid argument supplied"));
+ goto cleanup;
+ }
+
+ priv = (*vm)->privateData;
+
+ if (qemuDomainObjBeginJob(driver, *vm, QEMU_JOB_MODIFY) < 0)
+ goto cleanup;
+
+ if (!virDomainObjIsActive(*vm)) {
+ qemuReportError(VIR_ERR_INTERNAL_ERROR, "%s",
+ _("guest unexpectedly quit"));
+ goto endjob;
+ }
+
+ qemuDomainObjEnterMonitorWithDriver(driver, *vm);
+ if (qemuMonitorSystemReset(priv->mon) < 0) {
+ qemuDomainObjExitMonitorWithDriver(driver, *vm);
+ goto endjob;
+ }
+ qemuDomainObjExitMonitorWithDriver(driver, *vm);
+
+ ret = 0;
+
+endjob:
+ if (qemuDomainObjEndJob(driver, *vm) == 0)
+ *vm = NULL;
+cleanup:
+ return ret;
+}
+
static int qemudDomainCoreDump(virDomainPtr dom,
const char *path,
unsigned int flags)
@@ -2870,7 +2911,8 @@ static int qemudDomainCoreDump(virDomainPtr dom,
int ret = -1;
virDomainEventPtr event = NULL;
- virCheckFlags(VIR_DUMP_LIVE | VIR_DUMP_CRASH | VIR_DUMP_BYPASS_CACHE, -1);
+ virCheckFlags(VIR_DUMP_LIVE | VIR_DUMP_CRASH |
+ VIR_DUMP_BYPASS_CACHE | VIR_DUMP_REBOOT, -1);
qemuDriverLock(driver);
vm = virDomainFindByUUID(&driver->domains, dom->uuid);
@@ -2949,11 +2991,17 @@ endjob:
}
cleanup:
- if (vm)
- virDomainObjUnlock(vm);
if (event)
qemuDomainEventQueue(driver, event);
+
+ if ((ret == 0) && (flags & VIR_DUMP_REBOOT) && vm) {
+ ret = doSystemReset(driver, &vm);
+ }
+
+ if (vm)
+ virDomainObjUnlock(vm);
qemuDriverUnlock(driver);
+
return ret;
}
diff --git a/tools/virsh.c b/tools/virsh.c
index e5ea9d7..bdff33c 100644
--- a/tools/virsh.c
+++ b/tools/virsh.c
@@ -2899,6 +2899,7 @@ static const vshCmdOptDef opts_dump[] = {
{"crash", VSH_OT_BOOL, 0, N_("crash the domain after core
dump")},
{"bypass-cache", VSH_OT_BOOL, 0,
N_("avoid file system cache when saving")},
+ {"reboot", VSH_OT_BOOL, 0, N_("reboot the domain after core
dump")},
{"domain", VSH_OT_DATA, VSH_OFLAG_REQ, N_("domain name, id or
uuid")},
{"file", VSH_OT_DATA, VSH_OFLAG_REQ, N_("where to dump the
core")},
{NULL, 0, 0, NULL}
@@ -2928,6 +2929,8 @@ cmdDump(vshControl *ctl, const vshCmd *cmd)
flags |= VIR_DUMP_CRASH;
if (vshCommandOptBool(cmd, "bypass-cache"))
flags |= VIR_DUMP_BYPASS_CACHE;
+ if (vshCommandOptBool(cmd, "reboot"))
+ flags |= VIR_DUMP_REBOOT;
if (virDomainCoreDump(dom, to, flags) < 0) {
vshError(ctl, _("Failed to core dump domain %s to %s"), name, to);
--
1.7.3.4