@@ -1740,6 +1740,10 @@ static void *migration_thread(void *opaque)
static void *snapshot_thread(void *opaque)
{
+ MigrationState *ms = opaque;;
+ bool old_vm_running = false;
+ int ret;
+
rcu_register_thread();
/* Fix me: Remove this if we support snapshot for KVM */
if (strcmp(current_machine->accel, "tcg")) {
@@ -1747,8 +1751,38 @@ static void *snapshot_thread(void *opaque)
goto error;
}
- /* TODO: create memory snapshot */
+ qemu_savevm_state_header(ms->file);
+ qemu_savevm_state_begin(ms->file, &ms->params);
+
+ qemu_mutex_lock_iothread();
+ qemu_system_wakeup_request(QEMU_WAKEUP_REASON_OTHER);
+ old_vm_running = runstate_is_running();
+ ret = global_state_store();
+ if (!ret) {
+ ret = vm_stop_force_state(RUN_STATE_SAVE_VM);
+ if (ret < 0) {
+ error_report("Failed to stop VM");
+ goto error;
+ }
+ }
+
+ /* TODO: other setup work */
+ if (old_vm_running) {
+ vm_start();
+ }
+ qemu_mutex_unlock_iothread();
+
+ migrate_set_state(ms, MIGRATION_STATUS_SETUP, MIGRATION_STATUS_ACTIVE);
+
+ trace_snapshot_thread_setup_complete();
+
+ /* Save VM's state */
+
+ qemu_mutex_lock_iothread();
+ qemu_savevm_state_cleanup();
+ qemu_bh_schedule(ms->cleanup_bh);
+ qemu_mutex_unlock_iothread();
error:
rcu_unregister_thread();
return NULL;
@@ -1935,9 +1935,11 @@ static int ram_save_setup(QEMUFile *f, void *opaque)
* gaps due to alignment or unplugs.
*/
migration_dirty_pages = ram_bytes_total() >> TARGET_PAGE_BITS;
-
- memory_global_dirty_log_start();
- migration_bitmap_sync();
+ /* For snapshot, we don't need to enable global dirty log */
+ if (!migration_in_snapshot(migrate_get_current())) {
+ memory_global_dirty_log_start();
+ migration_bitmap_sync();
+ }
qemu_mutex_unlock_ramlist();
qemu_mutex_unlock_iothread();
@@ -1495,6 +1495,7 @@ migrate_state_too_big(void) ""
migrate_transferred(uint64_t tranferred, uint64_t time_spent, double bandwidth, uint64_t size) "transferred %" PRIu64 " time_spent %" PRIu64 " bandwidth %g max_size %" PRId64
process_incoming_migration_co_end(int ret, int ps) "ret=%d postcopy-state=%d"
process_incoming_migration_co_postcopy_end_main(void) ""
+snapshot_thread_setup_complete(void) ""
# migration/rdma.c
qemu_rdma_accept_incoming_migration(void) ""
We re-use some migration helper fucntions to realize setup work for snapshot, besides, we need to do some initialization work (for example, save VM's device state) with VM pausing. Signed-off-by: zhanghailiang <zhang.zhanghailiang@huawei.com> --- migration/migration.c | 36 +++++++++++++++++++++++++++++++++++- migration/ram.c | 8 +++++--- trace-events | 1 + 3 files changed, 41 insertions(+), 4 deletions(-)