summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJosh Boyer <jwboyer@fedoraproject.org>2016-05-20 08:23:06 -0400
committerJosh Boyer <jwboyer@fedoraproject.org>2016-05-20 09:01:34 -0400
commite8f3f4f939f4a5f7be4a3b0af4219951cfe61e8d (patch)
tree1406537ce694505c27312a0fa92e56732138fd68
parenta0a9ac914f183c19792b2dbee05f22ac53d548b3 (diff)
downloadkernel-e8f3f4f939f4a5f7be4a3b0af4219951cfe61e8d.tar.gz
kernel-e8f3f4f939f4a5f7be4a3b0af4219951cfe61e8d.tar.xz
kernel-e8f3f4f939f4a5f7be4a3b0af4219951cfe61e8d.zip
CVE-2016-4440 kvm: incorrect state leading to APIC register access (rhbz 1337806 1337807)
-rw-r--r--kernel.spec6
-rw-r--r--kvm-vmx-more-complete-state-update-on-APICv-on-off.patch112
2 files changed, 118 insertions, 0 deletions
diff --git a/kernel.spec b/kernel.spec
index 43588e458..0e0988151 100644
--- a/kernel.spec
+++ b/kernel.spec
@@ -614,6 +614,9 @@ Patch716: ALSA-timer-Fix-leak-in-events-via-snd_timer_user_tin.patch
#CVE-2016-3713 rhbz 1332139 1336410
Patch717: KVM-MTRR-remove-MSR-0x2f8.patch
+#CVE-2016-4440 rhbz 1337806 1337807
+Patch719: kvm-vmx-more-complete-state-update-on-APICv-on-off.patch
+
# END OF PATCH DEFINITIONS
%endif
@@ -2139,6 +2142,9 @@ fi
#
#
%changelog
+* Fri May 20 2016 Josh Boyer <jwboyer@fedoraproject.org>
+- CVE-2016-4440 kvm: incorrect state leading to APIC register access (rhbz 1337806 1337807)
+
* Fri May 20 2016 Peter Robinson <pbrobinson@fedoraproject.org>
- Minor ARM cleanups, enable Tegra USB-3 controller
diff --git a/kvm-vmx-more-complete-state-update-on-APICv-on-off.patch b/kvm-vmx-more-complete-state-update-on-APICv-on-off.patch
new file mode 100644
index 000000000..67043300c
--- /dev/null
+++ b/kvm-vmx-more-complete-state-update-on-APICv-on-off.patch
@@ -0,0 +1,112 @@
+From: Roman Kagan <rkagan@virtuozzo.com>
+Subject: [PATCH v3] kvm:vmx: more complete state update on APICv on/off
+Date: 2016-05-18 14:48:20 GMT (1 day, 21 hours and 23 minutes ago)
+
+The function to update APICv on/off state (in particular, to deactivate
+it when enabling Hyper-V SynIC), used to be incomplete: it didn't adjust
+APICv-related fields among secondary processor-based VM-execution
+controls.
+
+As a result, Windows 2012 guests would get stuck when SynIC-based
+auto-EOI interrupt intersected with e.g. an IPI in the guest.
+
+In addition, the MSR intercept bitmap wasn't updated to correspond to
+whether "virtualize x2APIC mode" was enabled. This path used not to be
+triggered, since Windows didn't use x2APIC but rather their own
+synthetic APIC access MSRs; however it represented a security risk
+because the guest running in a SynIC-enabled VM could switch to x2APIC
+and thus obtain direct access to host APIC MSRs (thanks to Yang Zhang
+<yang.zhang.wz@gmail.com> for spotting this).
+
+The patch fixes those omissions.
+
+Signed-off-by: Roman Kagan <rkagan@virtuozzo.com>
+Cc: Steve Rutherford <srutherford@google.com>
+Cc: Yang Zhang <yang.zhang.wz@gmail.com>
+---
+v2 -> v3:
+ - only switch to x2apic msr bitmap if virtualize x2apic mode is on in vmcs
+
+v1 -> v2:
+ - only update relevant bits in the secondary exec control
+ - update msr intercept bitmap (also make x2apic msr bitmap always
+ correspond to APICv)
+
+ arch/x86/kvm/vmx.c | 48 ++++++++++++++++++++++++++++++------------------
+ 1 file changed, 30 insertions(+), 18 deletions(-)
+
+diff --git a/arch/x86/kvm/vmx.c b/arch/x86/kvm/vmx.c
+index ee1c8a9..cef741a 100644
+--- a/arch/x86/kvm/vmx.c
++++ b/arch/x86/kvm/vmx.c
+@@ -2418,7 +2418,9 @@ static void vmx_set_msr_bitmap(struct kvm_vcpu *vcpu)
+
+ if (is_guest_mode(vcpu))
+ msr_bitmap = vmx_msr_bitmap_nested;
+- else if (vcpu->arch.apic_base & X2APIC_ENABLE) {
++ else if (cpu_has_secondary_exec_ctrls() &&
++ (vmcs_read32(SECONDARY_VM_EXEC_CONTROL) &
++ SECONDARY_EXEC_VIRTUALIZE_X2APIC_MODE)) {
+ if (is_long_mode(vcpu))
+ msr_bitmap = vmx_msr_bitmap_longmode_x2apic;
+ else
+@@ -4783,6 +4785,19 @@ static void vmx_refresh_apicv_exec_ctrl(struct kvm_vcpu *vcpu)
+ struct vcpu_vmx *vmx = to_vmx(vcpu);
+
+ vmcs_write32(PIN_BASED_VM_EXEC_CONTROL, vmx_pin_based_exec_ctrl(vmx));
++ if (cpu_has_secondary_exec_ctrls()) {
++ if (kvm_vcpu_apicv_active(vcpu))
++ vmcs_set_bits(SECONDARY_VM_EXEC_CONTROL,
++ SECONDARY_EXEC_APIC_REGISTER_VIRT |
++ SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY);
++ else
++ vmcs_clear_bits(SECONDARY_VM_EXEC_CONTROL,
++ SECONDARY_EXEC_APIC_REGISTER_VIRT |
++ SECONDARY_EXEC_VIRTUAL_INTR_DELIVERY);
++ }
++
++ if (cpu_has_vmx_msr_bitmap())
++ vmx_set_msr_bitmap(vcpu);
+ }
+
+ static u32 vmx_exec_control(struct vcpu_vmx *vmx)
+@@ -6329,23 +6344,20 @@ static __init int hardware_setup(void)
+
+ set_bit(0, vmx_vpid_bitmap); /* 0 is reserved for host */
+
+- if (enable_apicv) {
+- for (msr = 0x800; msr <= 0x8ff; msr++)
+- vmx_disable_intercept_msr_read_x2apic(msr);
+-
+- /* According SDM, in x2apic mode, the whole id reg is used.
+- * But in KVM, it only use the highest eight bits. Need to
+- * intercept it */
+- vmx_enable_intercept_msr_read_x2apic(0x802);
+- /* TMCCT */
+- vmx_enable_intercept_msr_read_x2apic(0x839);
+- /* TPR */
+- vmx_disable_intercept_msr_write_x2apic(0x808);
+- /* EOI */
+- vmx_disable_intercept_msr_write_x2apic(0x80b);
+- /* SELF-IPI */
+- vmx_disable_intercept_msr_write_x2apic(0x83f);
+- }
++ for (msr = 0x800; msr <= 0x8ff; msr++)
++ vmx_disable_intercept_msr_read_x2apic(msr);
++
++ /* According SDM, in x2apic mode, the whole id reg is used. But in
++ * KVM, it only use the highest eight bits. Need to intercept it */
++ vmx_enable_intercept_msr_read_x2apic(0x802);
++ /* TMCCT */
++ vmx_enable_intercept_msr_read_x2apic(0x839);
++ /* TPR */
++ vmx_disable_intercept_msr_write_x2apic(0x808);
++ /* EOI */
++ vmx_disable_intercept_msr_write_x2apic(0x80b);
++ /* SELF-IPI */
++ vmx_disable_intercept_msr_write_x2apic(0x83f);
+
+ if (enable_ept) {
+ kvm_mmu_set_mask_ptes(0ull,
+--
+2.5.5