Skip to content

Commit

Permalink
Postcopy+spice: Pass spice migration data earlier
Browse files Browse the repository at this point in the history
Spice hooks the migration status changes to figure out when to
transmit information to the new spice server; but the migration
status in postcopy doesn't quite fit - the destination starts
running before the end of the source migration.

It's not a case of hanging off the migration status change to
postcopy-active either, since that happens before we stop the
guest CPU.

Fix it by sending a notify just after sending the device state,
and adding a flag that can be tested by the notify receiver.

Symptom:
   spice handover doesn't work with the error:
   red_worker.c:11540:display_channel_wait_for_migrate_data: timeout

Signed-off-by: Dr. David Alan Gilbert <dgilbert@redhat.com>
Reviewed-by: Amit Shah <amit.shah@redhat.com>
Message-id: 1456161452-25318-1-git-send-email-dgilbert@redhat.com
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
  • Loading branch information
dagrh authored and kraxel committed Feb 23, 2016
1 parent 22672a3 commit b82fc32
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 1 deletion.
4 changes: 4 additions & 0 deletions include/migration/migration.h
Expand Up @@ -159,6 +159,8 @@ struct MigrationState

/* Flag set once the migration has been asked to enter postcopy */
bool start_postcopy;
/* Flag set after postcopy has sent the device state */
bool postcopy_after_devices;

/* Flag set once the migration thread is running (and needs joining) */
bool migration_thread_running;
Expand Down Expand Up @@ -212,6 +214,8 @@ bool migration_has_finished(MigrationState *);
bool migration_has_failed(MigrationState *);
/* True if outgoing migration has entered postcopy phase */
bool migration_in_postcopy(MigrationState *);
/* ...and after the device transmission */
bool migration_in_postcopy_after_devices(MigrationState *);
MigrationState *migrate_get_current(void);

void migrate_compress_threads_create(void);
Expand Down
14 changes: 14 additions & 0 deletions migration/migration.c
Expand Up @@ -905,6 +905,11 @@ bool migration_in_postcopy(MigrationState *s)
return (s->state == MIGRATION_STATUS_POSTCOPY_ACTIVE);
}

bool migration_in_postcopy_after_devices(MigrationState *s)
{
return migration_in_postcopy(s) && s->postcopy_after_devices;
}

MigrationState *migrate_init(const MigrationParams *params)
{
MigrationState *s = migrate_get_current();
Expand All @@ -930,6 +935,7 @@ MigrationState *migrate_init(const MigrationParams *params)
s->setup_time = 0;
s->dirty_sync_count = 0;
s->start_postcopy = false;
s->postcopy_after_devices = false;
s->migration_thread_running = false;
s->last_req_rb = NULL;

Expand Down Expand Up @@ -1489,6 +1495,14 @@ static int postcopy_start(MigrationState *ms, bool *old_vm_running)
goto fail_closefb;
}
qemu_fclose(fb);

/* Send a notify to give a chance for anything that needs to happen
* at the transition to postcopy and after the device state; in particular
* spice needs to trigger a transition now
*/
ms->postcopy_after_devices = true;
notifier_list_notify(&migration_state_notifiers, ms);

ms->downtime = qemu_clock_get_ms(QEMU_CLOCK_REALTIME) - time_at_stop;

qemu_mutex_unlock_iothread();
Expand Down
3 changes: 2 additions & 1 deletion ui/spice-core.c
Expand Up @@ -573,7 +573,8 @@ static void migration_state_notifier(Notifier *notifier, void *data)

if (migration_in_setup(s)) {
spice_server_migrate_start(spice_server);
} else if (migration_has_finished(s)) {
} else if (migration_has_finished(s) ||
migration_in_postcopy_after_devices(s)) {
spice_server_migrate_end(spice_server, true);
spice_have_target_host = false;
} else if (migration_has_failed(s)) {
Expand Down

0 comments on commit b82fc32

Please sign in to comment.