diff --git a/include/sysemu/sysemu.h b/include/sysemu/sysemu.h index 05d1982bda..f992494e10 100644 --- a/include/sysemu/sysemu.h +++ b/include/sysemu/sysemu.h @@ -172,6 +172,7 @@ extern int boot_menu; extern bool boot_strict; extern uint8_t *boot_splash_filedata; extern size_t boot_splash_filedata_size; +extern bool enable_mlock; extern uint8_t qemu_extra_params_fw[2]; extern QEMUClockType rtc_clock; extern const char *mem_path; diff --git a/migration/postcopy-ram.c b/migration/postcopy-ram.c index 8e107fe8e9..1a24b0937e 100644 --- a/migration/postcopy-ram.c +++ b/migration/postcopy-ram.c @@ -87,6 +87,11 @@ static bool ufd_version_check(int ufd) return true; } +/* + * Note: This has the side effect of munlock'ing all of RAM, that's + * normally fine since if the postcopy succeeds it gets turned back on at the + * end. + */ bool postcopy_ram_supported_by_host(void) { long pagesize = getpagesize(); @@ -114,6 +119,15 @@ bool postcopy_ram_supported_by_host(void) goto out; } + /* + * userfault and mlock don't go together; we'll put it back later if + * it was enabled. + */ + if (munlockall()) { + error_report("%s: munlockall: %s", __func__, strerror(errno)); + return -1; + } + /* * We need to check that the ops we need are supported on anon memory * To do that we need to register a chunk and see the flags that @@ -294,6 +308,16 @@ int postcopy_ram_incoming_cleanup(MigrationIncomingState *mis) mis->have_fault_thread = false; } + if (enable_mlock) { + if (os_mlock() < 0) { + error_report("mlock: %s", strerror(errno)); + /* + * It doesn't feel right to fail at this point, we have a valid + * VM state. + */ + } + } + postcopy_state_set(POSTCOPY_INCOMING_END); migrate_send_rp_shut(mis, qemu_file_get_error(mis->from_src_file) != 0);