]> www.infradead.org Git - users/jedix/linux-maple.git/commitdiff
x86/spec: Always set IBRS to guest value on VMENTER and host on VMEXIT.
authorKonrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Tue, 9 Jan 2018 19:17:30 +0000 (14:17 -0500)
committerKirtikar Kashyap <kirtikar.kashyap@oracle.com>
Fri, 12 Jan 2018 18:22:29 +0000 (10:22 -0800)
The paper says that to "set IBRS even if it was already set".
The Intel drop does not have that (it checks to see if it was enabled, and
if so does not do the WRMSR).

Furtheremore it says that on VM Entry we should restore the guest value.
But the patches from Intel again have that _only_ if they the guest
has the IBRS set to zero.

Xen does it that way (as the PDF).

Red Hat code follows the same way as Intel.

It is confusing. Upstream Arjan says:
 IBRS will ensure that, when set after the ring transition, no earlier
 branch prediction data is used for indirect branches while IBRS is set

What is a ring transition? Upon more clarification it is not
ring transition, but predication mode change. And
VMX non-root transition to VMX root is a prediction mode change and
1 setting in less privilege mode is not sufficient for VMX root mode.

In effect we do want to make a write to the MSR setting IBRS
(even if the value is already set to 1).

Orabug: 27365575
CVE: CVE-2017-5715

Reviewed-by: Boris Ostrovsky <boris.ostrovsky@oracle.com>
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Signed-off-by: Kirtikar Kashyap <kirtikar.kashyap@oracle.com>
arch/x86/kvm/vmx.c

index fe0c299055b8041199c551bf60a40dc0b892f27f..0ce64443f9ef5a7243c1b14c3bc92267033436a6 100644 (file)
@@ -8187,14 +8187,15 @@ static void __noclone vmx_vcpu_run(struct kvm_vcpu *vcpu)
        if (vcpu->guest_debug & KVM_GUESTDBG_SINGLESTEP)
                vmx_set_interrupt_shadow(vcpu, 0);
 
-       if (ibrs_inuse &&
-           vmx->spec_ctrl != SPEC_CTRL_FEATURE_ENABLE_IBRS)
-               wrmsrl(MSR_IA32_SPEC_CTRL, vmx->spec_ctrl);
-
        atomic_switch_perf_msrs(vmx);
        debugctlmsr = get_debugctlmsr();
 
        vmx->__launched = vmx->loaded_vmcs->launched;
+
+       if (ibrs_inuse &&
+           vmx->spec_ctrl != SPEC_CTRL_FEATURE_ENABLE_IBRS)
+               wrmsrl(MSR_IA32_SPEC_CTRL, vmx->spec_ctrl);
+
        asm(
                /* Store host registers */
                "push %%" _ASM_DX "; push %%" _ASM_BP ";"
@@ -8319,8 +8320,7 @@ static void __noclone vmx_vcpu_run(struct kvm_vcpu *vcpu)
 
        if (ibrs_inuse) {
                rdmsrl(MSR_IA32_SPEC_CTRL, vmx->spec_ctrl);
-               if (!vmx->spec_ctrl)
-                       wrmsrl(MSR_IA32_SPEC_CTRL, SPEC_CTRL_FEATURE_ENABLE_IBRS);
+               wrmsrl(MSR_IA32_SPEC_CTRL, SPEC_CTRL_FEATURE_ENABLE_IBRS);
        }
        stuff_RSB();