[libvirt PATCH 35/80] qemu: Introduce qemuMigrationDstFinishActive

Jiri Denemark jdenemar at redhat.com
Tue May 10 15:20:56 UTC 2022


Refactors qemuMigrationDstFinish by moving some parts to a dedicated
function for easier introduction of postcopy resume code without
duplicating common parts of the Finish phase. The goal is to have the
following call graph:

    - qemuMigrationDstFinish
        - qemuMigrationDstFinishOffline
        - qemuMigrationDstFinishActive
            - qemuMigrationDstFinishFresh
            - qemuMigrationDstFinishResume

Signed-off-by: Jiri Denemark <jdenemar at redhat.com>
---
 src/qemu/qemu_migration.c | 173 +++++++++++++++++++++++---------------
 1 file changed, 103 insertions(+), 70 deletions(-)

diff --git a/src/qemu/qemu_migration.c b/src/qemu/qemu_migration.c
index 170d99d789..d02e8132e4 100644
--- a/src/qemu/qemu_migration.c
+++ b/src/qemu/qemu_migration.c
@@ -6004,71 +6004,32 @@ qemuMigrationDstFinishFresh(virQEMUDriver *driver,
 }
 
 
-virDomainPtr
-qemuMigrationDstFinish(virQEMUDriver *driver,
-                       virConnectPtr dconn,
-                       virDomainObj *vm,
-                       const char *cookiein,
-                       int cookieinlen,
-                       char **cookieout,
-                       int *cookieoutlen,
-                       unsigned long flags,
-                       int retcode,
-                       bool v3proto)
+static virDomainPtr
+qemuMigrationDstFinishActive(virQEMUDriver *driver,
+                             virConnectPtr dconn,
+                             virDomainObj *vm,
+                             int cookie_flags,
+                             const char *cookiein,
+                             int cookieinlen,
+                             char **cookieout,
+                             int *cookieoutlen,
+                             unsigned long flags,
+                             int retcode,
+                             bool v3proto,
+                             unsigned long long timeReceived,
+                             virErrorPtr *orig_err)
 {
     virDomainPtr dom = NULL;
     g_autoptr(qemuMigrationCookie) mig = NULL;
-    virErrorPtr orig_err = NULL;
-    int cookie_flags = 0;
     qemuDomainObjPrivate *priv = vm->privateData;
     qemuDomainJobPrivate *jobPriv = priv->job.privateData;
-    unsigned short port;
-    unsigned long long timeReceived = 0;
     virObjectEvent *event;
     bool inPostCopy = false;
     bool doKill = true;
     int rc;
 
-    VIR_DEBUG("driver=%p, dconn=%p, vm=%p, cookiein=%s, cookieinlen=%d, "
-              "cookieout=%p, cookieoutlen=%p, flags=0x%lx, retcode=%d",
-              driver, dconn, vm, NULLSTR(cookiein), cookieinlen,
-              cookieout, cookieoutlen, flags, retcode);
-
-    port = priv->migrationPort;
-    priv->migrationPort = 0;
-
-    if (!qemuMigrationJobIsActive(vm, VIR_ASYNC_JOB_MIGRATION_IN)) {
-        qemuMigrationDstErrorReport(driver, vm->def->name);
-        goto cleanup;
-    }
-
-    ignore_value(virTimeMillisNow(&timeReceived));
-
-    qemuMigrationJobStartPhase(vm,
-                               v3proto ? QEMU_MIGRATION_PHASE_FINISH3
-                                       : QEMU_MIGRATION_PHASE_FINISH2);
-
-    qemuDomainCleanupRemove(vm, qemuMigrationDstPrepareCleanup);
-    g_clear_pointer(&priv->job.completed, virDomainJobDataFree);
-
-    cookie_flags = QEMU_MIGRATION_COOKIE_NETWORK |
-                   QEMU_MIGRATION_COOKIE_STATS |
-                   QEMU_MIGRATION_COOKIE_NBD;
-    /* Some older versions of libvirt always send persistent XML in the cookie
-     * even though VIR_MIGRATE_PERSIST_DEST was not used. */
-    cookie_flags |= QEMU_MIGRATION_COOKIE_PERSISTENT;
-
-    if (flags & VIR_MIGRATE_OFFLINE) {
-        if (retcode == 0) {
-            dom = qemuMigrationDstFinishOffline(driver, dconn, vm,
-                                                cookie_flags,
-                                                cookiein, cookieinlen,
-                                                cookieout, cookieoutlen);
-        }
-
-        qemuMigrationJobFinish(vm);
-        goto cleanup;
-    }
+    VIR_DEBUG("vm=%p, flags=0x%lx, retcode=%d",
+              vm, flags, retcode);
 
     if (!(mig = qemuMigrationCookieParse(driver, vm->def, priv->origname, priv,
                                          cookiein, cookieinlen, cookie_flags)))
@@ -6106,25 +6067,12 @@ qemuMigrationDstFinish(virQEMUDriver *driver,
 
     qemuMigrationJobFinish(vm);
 
- cleanup:
-    virPortAllocatorRelease(port);
-    if (priv->mon)
-        qemuMonitorSetDomainLog(priv->mon, NULL, NULL, NULL);
-    VIR_FREE(priv->origname);
-    virDomainObjEndAPI(&vm);
-    virErrorRestore(&orig_err);
-
-    /* Set a special error if Finish is expected to return NULL as a result of
-     * successful call with retcode != 0
-     */
-    if (retcode != 0 && !dom && virGetLastErrorCode() == VIR_ERR_OK)
-        virReportError(VIR_ERR_MIGRATE_FINISH_OK, NULL);
     return dom;
 
  error:
     /* Need to save the current error, in case shutting down the process
      * overwrites it. */
-    virErrorPreserveLast(&orig_err);
+    virErrorPreserveLast(orig_err);
 
     if (virDomainObjIsActive(vm)) {
         if (doKill) {
@@ -6155,7 +6103,92 @@ qemuMigrationDstFinish(virQEMUDriver *driver,
     if (!virDomainObjIsActive(vm))
         qemuDomainRemoveInactive(driver, vm);
 
-    goto cleanup;
+    return NULL;
+}
+
+
+virDomainPtr
+qemuMigrationDstFinish(virQEMUDriver *driver,
+                       virConnectPtr dconn,
+                       virDomainObj *vm,
+                       const char *cookiein,
+                       int cookieinlen,
+                       char **cookieout,
+                       int *cookieoutlen,
+                       unsigned long flags,
+                       int retcode,
+                       bool v3proto)
+{
+    virDomainPtr dom = NULL;
+    virErrorPtr orig_err = NULL;
+    int cookie_flags = 0;
+    qemuDomainObjPrivate *priv = vm->privateData;
+    unsigned short port;
+    unsigned long long timeReceived = 0;
+
+    VIR_DEBUG("driver=%p, dconn=%p, vm=%p, cookiein=%s, cookieinlen=%d, "
+              "cookieout=%p, cookieoutlen=%p, flags=0x%lx, retcode=%d",
+              driver, dconn, vm, NULLSTR(cookiein), cookieinlen,
+              cookieout, cookieoutlen, flags, retcode);
+
+    port = priv->migrationPort;
+    priv->migrationPort = 0;
+
+    if (!qemuMigrationJobIsActive(vm, VIR_ASYNC_JOB_MIGRATION_IN)) {
+        qemuMigrationDstErrorReport(driver, vm->def->name);
+        goto cleanup;
+    }
+
+    ignore_value(virTimeMillisNow(&timeReceived));
+
+    qemuMigrationJobStartPhase(vm,
+                               v3proto ? QEMU_MIGRATION_PHASE_FINISH3
+                                       : QEMU_MIGRATION_PHASE_FINISH2);
+
+    qemuDomainCleanupRemove(vm, qemuMigrationDstPrepareCleanup);
+    g_clear_pointer(&priv->job.completed, virDomainJobDataFree);
+
+    cookie_flags = QEMU_MIGRATION_COOKIE_NETWORK |
+                   QEMU_MIGRATION_COOKIE_STATS |
+                   QEMU_MIGRATION_COOKIE_NBD;
+    /* Some older versions of libvirt always send persistent XML in the cookie
+     * even though VIR_MIGRATE_PERSIST_DEST was not used. */
+    cookie_flags |= QEMU_MIGRATION_COOKIE_PERSISTENT;
+
+    if (flags & VIR_MIGRATE_OFFLINE) {
+        if (retcode == 0) {
+            dom = qemuMigrationDstFinishOffline(driver, dconn, vm,
+                                                cookie_flags,
+                                                cookiein, cookieinlen,
+                                                cookieout, cookieoutlen);
+        }
+
+        qemuMigrationJobFinish(vm);
+        goto cleanup;
+    }
+
+    dom = qemuMigrationDstFinishActive(driver, dconn, vm, cookie_flags,
+                                       cookiein, cookieinlen,
+                                       cookieout, cookieoutlen,
+                                       flags, retcode, v3proto, timeReceived,
+                                       &orig_err);
+    if (!dom)
+        goto cleanup;
+
+ cleanup:
+    virPortAllocatorRelease(port);
+    if (priv->mon)
+        qemuMonitorSetDomainLog(priv->mon, NULL, NULL, NULL);
+    VIR_FREE(priv->origname);
+    virDomainObjEndAPI(&vm);
+    virErrorRestore(&orig_err);
+
+    /* Set a special error if Finish is expected to return NULL as a result of
+     * successful call with retcode != 0
+     */
+    if (retcode != 0 && !dom && virGetLastErrorCode() == VIR_ERR_OK)
+        virReportError(VIR_ERR_MIGRATE_FINISH_OK, NULL);
+    return dom;
 }
 
 
-- 
2.35.1



More information about the libvir-list mailing list