Hi On Tue, Aug 24, 2021 at 7:27 PM Peter Xu wrote: > Both dump-guest-memory and live migration caches vm state at the beginning. > Either of them entering the other one will cause race on the vm state, and > even > more severe on that (please refer to the crash report in the bug link). > > Let's block live migration in dump-guest-memory, and that'll also block > dump-guest-memory if it detected that we're during a live migration. > > Side note: migrate_del_blocker() can be called even if the blocker is not > inserted yet, so it's safe to unconditionally delete that blocker in > dump_cleanup (g_slist_remove allows no-entry-found case). > > Suggested-by: Dr. David Alan Gilbert > Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=1996609 > Signed-off-by: Peter Xu > --- > dump/dump.c | 20 +++++++++++++++----- > include/sysemu/dump.h | 1 + > 2 files changed, 16 insertions(+), 5 deletions(-) > > diff --git a/dump/dump.c b/dump/dump.c > index ab625909f3..7996d7a6c5 100644 > --- a/dump/dump.c > +++ b/dump/dump.c > @@ -29,6 +29,7 @@ > #include "qemu/error-report.h" > #include "qemu/main-loop.h" > #include "hw/misc/vmcoreinfo.h" > +#include "migration/blocker.h" > > #ifdef TARGET_X86_64 > #include "win_dump.h" > @@ -101,6 +102,7 @@ static int dump_cleanup(DumpState *s) > qemu_mutex_unlock_iothread(); > } > } > + migrate_del_blocker(s->dump_migration_blocker); > > return 0; > } > @@ -1857,6 +1859,19 @@ static void dump_init(DumpState *s, int fd, bool > has_format, > } > } > > + if (!s->dump_migration_blocker) { > + error_setg(&s->dump_migration_blocker, > + "Live migration disabled: dump-guest-memory in > progress"); > + } > + > + /* > + * Allows even for -only-migratable, but forbid migration during the > + * process of dump guest memory. > + */ > + if (migrate_add_blocker_internal(s->dump_migration_blocker, errp)) { > + goto cleanup; > + } > + > Shouldn't this be placed earlier in the function, before runstate_is_running() and vm_stop() ? return; > > cleanup: > @@ -1927,11 +1942,6 @@ void qmp_dump_guest_memory(bool paging, const char > *file, > Error *local_err = NULL; > bool detach_p = false; > > - if (runstate_check(RUN_STATE_INMIGRATE)) { > - error_setg(errp, "Dump not allowed during incoming migration."); > - return; > - } > - > /* if there is a dump in background, we should wait until the dump > * finished */ > if (dump_in_progress()) { > diff --git a/include/sysemu/dump.h b/include/sysemu/dump.h > index 250143cb5a..7b619c2a43 100644 > --- a/include/sysemu/dump.h > +++ b/include/sysemu/dump.h > @@ -195,6 +195,7 @@ typedef struct DumpState { > * finished. */ > uint8_t *guest_note; /* ELF note content */ > size_t guest_note_size; > + Error *dump_migration_blocker; /* Blocker for live migration */ > } DumpState; > > uint16_t cpu_to_dump16(DumpState *s, uint16_t val); > -- > 2.31.1 > >