Where QEMU_CAPS_WIN_DMP_GUEST_AWARE is present, QEMU reports win-dmp
as available only for a guest that has published a vmcoreinfo dump
header. In that case prefer it over the elf default: converting an
elf dump into a Windows-debuggable format afterwards is possible but
complicated and unreliable.

Add qemuDomainGetAutoDumpFormat(), which probes win-dmp support
right before an auto-triggered dump and falls back to elf
otherwise. Use it from both doCoreDumpToAutoDumpPath() (on_crash)
and processWatchdogEvent() (watchdog dump). virDomainCoreDump() and
virDomainCoreDumpWithFormat() are left untouched, since RAW there
is a documented part of their API contract, standing in for an
explicit caller request rather than an internal default.

The probe is best-effort: reset any error left by a failed monitor
call or QMP command, so it cannot leak past a dump that otherwise
succeeds.

Without the capability the probe is skipped: older QEMU offers win-dmp
on any x86 machine, where the resulting dump is useless.

Signed-off-by: Denis V. Lunev <[email protected]>
---
 NEWS.rst               |  7 +++++++
 src/qemu/qemu_driver.c | 33 +++++++++++++++++++++++++++++++--
 2 files changed, 38 insertions(+), 2 deletions(-)

diff --git a/NEWS.rst b/NEWS.rst
index ae4d8c18a5..3dadb6d4f3 100644
--- a/NEWS.rst
+++ b/NEWS.rst
@@ -19,6 +19,13 @@ v12.7.0 (unreleased)
 
 * **Improvements**
 
+  * qemu: Select the win-dmp format for Windows guest crash dumps
+
+    Dumps triggered by ``<on_crash>`` and by watchdog handling used QEMU's elf
+    default, which WinDbg cannot load. Where QEMU reports the format as
+    available only to a guest that can use it, such dumps are now written in
+    win-dmp format instead.
+
 * **Bug fixes**
 
 
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
index 44b41726fb..cfabaf0746 100644
--- a/src/qemu/qemu_driver.c
+++ b/src/qemu/qemu_driver.c
@@ -3532,6 +3532,34 @@ getAutoDumpPath(virQEMUDriver *driver,
     return g_strdup_printf("%s/%s-%s", cfg->autoDumpPath, domname, nowstr);
 }
 
+/* Older QEMU offers win-dmp on any x86 machine, so trust the capability
+ * query only where QEMU says the answer depends on the guest. */
+static unsigned int
+qemuDomainGetAutoDumpFormat(virDomainObj *vm)
+{
+    qemuDomainObjPrivate *priv = vm->privateData;
+    unsigned int dumpformat = VIR_DOMAIN_CORE_DUMP_FORMAT_RAW;
+    int rc;
+
+    if (!virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_WIN_DMP_GUEST_AWARE))
+        return dumpformat;
+
+    if (qemuDomainObjEnterMonitorAsync(vm, VIR_ASYNC_JOB_DUMP) < 0) {
+        virResetLastError();
+        return dumpformat;
+    }
+
+    rc = qemuMonitorGetDumpGuestMemoryCapability(priv->mon, "win-dmp");
+    if (rc < 0)
+        virResetLastError();
+    else if (rc > 0)
+        dumpformat = VIR_DOMAIN_CORE_DUMP_FORMAT_WIN_DMP;
+
+    qemuDomainObjExitMonitor(vm);
+    return dumpformat;
+}
+
+
 static void
 processWatchdogEvent(virQEMUDriver *driver,
                      virDomainObj *vm,
@@ -3558,7 +3586,7 @@ processWatchdogEvent(virQEMUDriver *driver,
 
         flags |= cfg->autoDumpBypassCache ? VIR_DUMP_BYPASS_CACHE: 0;
         if ((ret = doCoreDump(driver, vm, dumpfile, flags,
-                              VIR_DOMAIN_CORE_DUMP_FORMAT_RAW)) < 0)
+                              qemuDomainGetAutoDumpFormat(vm))) < 0)
             virReportError(VIR_ERR_OPERATION_FAILED,
                            "%s", _("Dump failed"));
 
@@ -3578,6 +3606,7 @@ processWatchdogEvent(virQEMUDriver *driver,
     virDomainObjEndAsyncJob(vm);
 }
 
+
 static int
 doCoreDumpToAutoDumpPath(virQEMUDriver *driver,
                          virDomainObj *vm,
@@ -3592,7 +3621,7 @@ doCoreDumpToAutoDumpPath(virQEMUDriver *driver,
 
     flags |= cfg->autoDumpBypassCache ? VIR_DUMP_BYPASS_CACHE: 0;
     if ((ret = doCoreDump(driver, vm, dumpfile, flags,
-                          VIR_DOMAIN_CORE_DUMP_FORMAT_RAW)) < 0)
+                          qemuDomainGetAutoDumpFormat(vm))) < 0)
         virReportError(VIR_ERR_OPERATION_FAILED,
                        "%s", _("Dump failed"));
     return ret;
-- 
2.53.0

Reply via email to