]> git.proxmox.com Git - qemu-server.git/commitdiff
migrate: resume initially running VM when failing after convergence
authorFabian Ebner <f.ebner@proxmox.com>
Mon, 25 Apr 2022 12:31:12 +0000 (14:31 +0200)
committerFabian Grünbichler <f.gruenbichler@proxmox.com>
Tue, 26 Apr 2022 09:42:25 +0000 (11:42 +0200)
When phase2() is aborted after the migration already converged, then
after migrate_cancel, the VM might be in POSTMIGRATE state.

(There also is a conditional for SHUTDOWN state in QEMU's
migration_iteration_finish(), so it's likely possible to end up there
if the VM is shut down at the right time during migration, but no need
to resume then).

Detect the POSTMIGRATE state and resume the VM if it wasn't paused at
the beginning of the migration. There is no direct way to go to
PAUSED, so just print an error if the VM was paused at the beginning
of the migration.

Reported-by: Fabian Grünbichler <f.gruenbichler@proxmox.com>
Signed-off-by: Fabian Ebner <f.ebner@proxmox.com>
PVE/QemuMigrate.pm

index c293e2948bc1f8ab23ad0dc1636169fafd3f2d12..dfe923251219720aa76ff95295db12bb7f86fb21 100644 (file)
@@ -1056,6 +1056,22 @@ sub phase2_cleanup {
     };
     $self->log('info', "migrate_cancel error: $@") if $@;
 
+    my $vm_status = eval {
+       mon_cmd($vmid, 'query-status')->{status} or die "no 'status' in result\n";
+    };
+    $self->log('err', "query-status error: $@") if $@;
+
+    # Can end up in POSTMIGRATE state if failure occurred after convergence. Try going back to
+    # original state. Unfortunately, direct transition from POSTMIGRATE to PAUSED is not possible.
+    if ($vm_status && $vm_status eq 'postmigrate') {
+       if (!$self->{vm_was_paused}) {
+           eval { mon_cmd($vmid, 'cont'); };
+           $self->log('err', "resuming VM failed: $@") if $@;
+       } else {
+           $self->log('err', "VM was paused, but ended in postmigrate state");
+       }
+    }
+
     my $conf = $self->{vmconf};
     delete $conf->{lock};
     eval { PVE::QemuConfig->write_config($vmid, $conf) };