diff --git a/include/hw/i386/pc.h b/include/hw/i386/pc.h index d1f45540a1..ab303c7fee 100644 --- a/include/hw/i386/pc.h +++ b/include/hw/i386/pc.h @@ -623,6 +623,10 @@ bool e820_get_entry(int, uint32_t, uint64_t *, uint64_t *); .driver = "Broadwell-noTSX" "-" TYPE_X86_CPU,\ .property = "xlevel",\ .value = stringify(0x8000000a),\ + },{\ + .driver = TYPE_X86_CPU,\ + .property = "kvm-no-smi-migration",\ + .value = "on",\ }, #define PC_COMPAT_2_2 \ diff --git a/target/i386/cpu.c b/target/i386/cpu.c index aec5d9daf8..fba92125ab 100644 --- a/target/i386/cpu.c +++ b/target/i386/cpu.c @@ -3983,6 +3983,8 @@ static Property x86_cpu_properties[] = { DEFINE_PROP_BOOL("cpuid-0xb", X86CPU, enable_cpuid_0xb, true), DEFINE_PROP_BOOL("lmce", X86CPU, enable_lmce, false), DEFINE_PROP_BOOL("l3-cache", X86CPU, enable_l3_cache, true), + DEFINE_PROP_BOOL("kvm-no-smi-migration", X86CPU, kvm_no_smi_migration, + false), DEFINE_PROP_BOOL("vmware-cpuid-freq", X86CPU, vmware_cpuid_freq, true), DEFINE_PROP_END_OF_LIST() }; diff --git a/target/i386/cpu.h b/target/i386/cpu.h index 12a39d590f..ac2ad6d443 100644 --- a/target/i386/cpu.h +++ b/target/i386/cpu.h @@ -1255,6 +1255,9 @@ struct X86CPU { /* if true override the phys_bits value with a value read from the host */ bool host_phys_bits; + /* Stop SMI delivery for migration compatibility with old machines */ + bool kvm_no_smi_migration; + /* Number of physical address bits supported */ uint32_t phys_bits; diff --git a/target/i386/kvm.c b/target/i386/kvm.c index 7698421ae7..887a81268f 100644 --- a/target/i386/kvm.c +++ b/target/i386/kvm.c @@ -2492,7 +2492,12 @@ static int kvm_put_vcpu_events(X86CPU *cpu, int level) events.smi.pending = 0; events.smi.latched_init = 0; } - events.flags |= KVM_VCPUEVENT_VALID_SMM; + /* Stop SMI delivery on old machine types to avoid a reboot + * on an inward migration of an old VM. + */ + if (!cpu->kvm_no_smi_migration) { + events.flags |= KVM_VCPUEVENT_VALID_SMM; + } } if (level >= KVM_PUT_RESET_STATE) {