• Sean Christopherson's avatar
    KVM: x86: Always use 32-bit SMRAM save state for 32-bit kernels · b68f3cc7
    Sean Christopherson authored
    Invoking the 64-bit variation on a 32-bit kenrel will crash the guest,
    trigger a WARN, and/or lead to a buffer overrun in the host, e.g.
    rsm_load_state_64() writes r8-r15 unconditionally, but enum kvm_reg and
    thus x86_emulate_ctxt._regs only define r8-r15 for CONFIG_X86_64.
    
    KVM allows userspace to report long mode support via CPUID, even though
    the guest is all but guaranteed to crash if it actually tries to enable
    long mode.  But, a pure 32-bit guest that is ignorant of long mode will
    happily plod along.
    
    SMM complicates things as 64-bit CPUs use a different SMRAM save state
    area.  KVM handles this correctly for 64-bit kernels, e.g. uses the
    legacy save state map if userspace has hid long mode from the guest,
    but doesn't fare well when userspace reports long mode support on a
    32-bit host kernel (32-bit KVM doesn't support 64-bit guests).
    
    Since the alternative is to crash the guest, e.g. by not loading state
    or explicitly requesting shutdown, unconditionally use the legacy SMRAM
    save state map for 32-bit KVM.  If a guest has managed to get far enough
    to handle SMIs when running under a weird/buggy userspace hypervisor,
    then don't deliberately crash the guest since there are no downsides
    (from KVM's perspective) to allow it to continue running.
    
    Fixes: 660a5d51 ("KVM: x86: save/load state on SMM switch")
    Cc: stable@vger.kernel.org
    Signed-off-by: default avatarSean Christopherson <sean.j.christopherson@intel.com>
    Signed-off-by: default avatarPaolo Bonzini <pbonzini@redhat.com>
    b68f3cc7
emulate.c 150 KB