VirtualBox

Changeset 80842 in vbox


Ignore:
Timestamp:
Sep 17, 2019 6:28:09 AM (5 years ago)
Author:
vboxsync
Message:

VMM/HMVMXR0: Nested VMX: bugref:9180 Tighten up the CR4 guest/host mask to include reserved/unknown bits in CR4.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMR0/HMVMXR0.cpp

    r80840 r80842  
    839839
    840840/**
    841  * Get the CR0 guest/host mask that does not change through the lifetime of a VM.
    842  *
    843  * Any bit set in this mask is owned by the host/hypervisor and would cause a
    844  * VM-exit when modified by the guest.
    845  *
    846  * @returns The static CR0 guest/host mask.
     841 * Gets the CR0 guest/host mask.
     842 *
     843 * These bits typically does not change through the lifetime of a VM. Any bit set in
     844 * this mask is owned by the host/hypervisor and would cause a VM-exit when modified
     845 * by the guest.
     846 *
     847 * @returns The CR0 guest/host mask.
    847848 * @param   pVCpu   The cross context virtual CPU structure.
    848849 */
    849 DECL_FORCE_INLINE(uint64_t) hmR0VmxGetFixedCr0Mask(PCVMCPUCC pVCpu)
     850static uint64_t hmR0VmxGetFixedCr0Mask(PCVMCPUCC pVCpu)
    850851{
    851852    /*
     
    870871
    871872/**
    872  * Gets the CR4 guest/host mask that does not change through the lifetime of a VM.
    873  *
    874  * Any bit set in this mask is owned by the host/hypervisor and would cause a
    875  * VM-exit when modified by the guest.
    876  *
    877  * @returns The static CR4 guest/host mask.
     873 * Gets the CR4 guest/host mask.
     874 *
     875 * These bits typically does not change through the lifetime of a VM. Any bit set in
     876 * this mask is owned by the host/hypervisor and would cause a VM-exit when modified
     877 * by the guest.
     878 *
     879 * @returns The CR4 guest/host mask.
    878880 * @param   pVCpu   The cross context virtual CPU structure.
    879881 */
    880 DECL_FORCE_INLINE(uint64_t) hmR0VmxGetFixedCr4Mask(PCVMCPUCC pVCpu)
    881 {
    882     /*
    883      * We need to look at the host features here (for e.g. OSXSAVE, PCID) because
    884      * these bits are reserved on hardware that does not support them. Since the
    885      * CPU cannot refer to our virtual CPUID, we need to intercept CR4 changes to
    886      * these  bits and handle it depending on whether we expose them to the guest.
    887      */
    888     PVMCC pVM = pVCpu->CTX_SUFF(pVM);
    889     bool const fXSaveRstor = pVM->cpum.ro.HostFeatures.fXSaveRstor;
    890     bool const fPcid       = pVM->cpum.ro.HostFeatures.fPcid;
    891     return (  X86_CR4_VMXE
    892             | X86_CR4_VME
    893             | X86_CR4_PAE
    894             | X86_CR4_PGE
    895             | X86_CR4_PSE
    896             | (fXSaveRstor ? X86_CR4_OSXSAVE : 0)
    897             | (fPcid       ? X86_CR4_PCIDE   : 0));
     882static uint64_t hmR0VmxGetFixedCr4Mask(PCVMCPUCC pVCpu)
     883{
     884    /*
     885     * We construct a mask of all CR4 bits that the guest can modify without causing
     886     * a VM-exit. Then invert this mask to obtain all CR4 bits that should cause
     887     * a VM-exit when the guest attempts to modify them when executing using
     888     * hardware-assisted VMX.
     889     *
     890     * When a feature is not exposed to the guest (and may be present on the host),
     891     * we want to intercept guest modifications to the bit so we can emulate proper
     892     * behavior (e.g., #GP).
     893     *
     894     * Furthermore, only modifications to those bits that don't require immediate
     895     * emulation is allowed. For e.g., PCIDE is excluded because the behavior
     896     * depends on CR3 which might not always be the guest value while executing
     897     * using hardware-assisted VMX.
     898     */
     899    PCVMCC pVM = pVCpu->CTX_SUFF(pVM);
     900    bool const fFsGsBase    = pVM->cpum.ro.GuestFeatures.fFsGsBase;
     901    bool const fXSaveRstor  = pVM->cpum.ro.GuestFeatures.fXSaveRstor;
     902    bool const fFxSaveRstor = pVM->cpum.ro.GuestFeatures.fFxSaveRstor;
     903
     904    /*
     905     * Paranoia.
     906     * Ensure features exposed to the guest are present on the host.
     907     */
     908    Assert(!fFsGsBase    || pVM->cpum.ro.HostFeatures.fFsGsBase);
     909    Assert(!fXSaveRstor  || pVM->cpum.ro.HostFeatures.fXSaveRstor);
     910    Assert(!fFxSaveRstor || pVM->cpum.ro.HostFeatures.fFxSaveRstor);
     911
     912    uint64_t const fGstMask = (  X86_CR4_PVI
     913                               | X86_CR4_TSD
     914                               | X86_CR4_DE
     915                               | X86_CR4_MCE
     916                               | X86_CR4_PCE
     917                               | X86_CR4_OSXMMEEXCPT
     918                               | (fFsGsBase    ? X86_CR4_FSGSBASE : 0)
     919                               | (fXSaveRstor  ? X86_CR4_OSXSAVE  : 0)
     920                               | (fFxSaveRstor ? X86_CR4_OSFXSR   : 0));
     921    return ~fGstMask;
    898922}
    899923
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette