switch ((qemuMonitorMigrationStatus) priv->stats.mig.status) {
case QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY:
+ case QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY_RECOVER:
jobData->status = VIR_DOMAIN_JOB_STATUS_POSTCOPY;
break;
"inactive", "setup",
"active", "pre-switchover",
"device", "postcopy-active",
- "postcopy-paused",
+ "postcopy-paused", "postcopy-recover",
"completed", "failed",
"cancelling", "cancelled",
"wait-unplug",
QEMU_MONITOR_MIGRATION_STATUS_DEVICE,
QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY,
QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY_PAUSED,
+ QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY_RECOVER,
QEMU_MONITOR_MIGRATION_STATUS_COMPLETED,
QEMU_MONITOR_MIGRATION_STATUS_ERROR,
QEMU_MONITOR_MIGRATION_STATUS_CANCELLING,
case QEMU_MONITOR_MIGRATION_STATUS_ACTIVE:
case QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY:
case QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY_PAUSED:
+ case QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY_RECOVER:
case QEMU_MONITOR_MIGRATION_STATUS_COMPLETED:
case QEMU_MONITOR_MIGRATION_STATUS_CANCELLING:
case QEMU_MONITOR_MIGRATION_STATUS_PRE_SWITCHOVER:
}
break;
+ case QEMU_MONITOR_MIGRATION_STATUS_POSTCOPY_RECOVER:
+ if (virDomainObjIsFailedPostcopy(vm)) {
+ int eventType = -1;
+ int eventDetail = -1;
+
+ if (state == VIR_DOMAIN_PAUSED) {
+ reason = VIR_DOMAIN_PAUSED_POSTCOPY;
+ eventType = VIR_DOMAIN_EVENT_SUSPENDED;
+ eventDetail = qemuDomainPausedReasonToSuspendedEvent(reason);
+ } else {
+ reason = VIR_DOMAIN_RUNNING_POSTCOPY;
+ eventType = VIR_DOMAIN_EVENT_RESUMED;
+ eventDetail = qemuDomainRunningReasonToResumeEvent(reason);
+ }
+
+ VIR_DEBUG("Post-copy migration recovered; correcting state for domain '%s' to %s/%s",
+ vm->def->name,
+ virDomainStateTypeToString(state),
+ NULLSTR(virDomainStateReasonToString(state, reason)));
+ virDomainObjSetState(vm, state, reason);
+ event = virDomainEventLifecycleNewFromObj(vm, eventType, eventDetail);
+ qemuDomainSaveStatus(vm);
+ }
+ break;
+
case QEMU_MONITOR_MIGRATION_STATUS_INACTIVE:
case QEMU_MONITOR_MIGRATION_STATUS_SETUP:
case QEMU_MONITOR_MIGRATION_STATUS_ACTIVE: