Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm

Pull KVM fixes from Paolo Bonzini:
"The important fixes are for two bugs introduced by the merge window.

On top of this, add a couple of WARN_ONs and stop spamming dmesg on
pretty much every boot of a virtual machine"

* tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm:
kvm: warn on more invariant breakage
kvm: fix sorting of memslots with base_gfn == 0
kvm: x86: drop severity of "generation wraparound" message
kvm: x86: vmx: reorder some msr writing

+65 -51
+1 -1
arch/x86/kvm/mmu.c
··· 4448 4448 * zap all shadow pages. 4449 4449 */ 4450 4450 if (unlikely(kvm_current_mmio_generation(kvm) == 0)) { 4451 - printk_ratelimited(KERN_INFO "kvm: zapping shadow pages for mmio generation wraparound\n"); 4451 + printk_ratelimited(KERN_DEBUG "kvm: zapping shadow pages for mmio generation wraparound\n"); 4452 4452 kvm_mmu_invalidate_zap_all_pages(kvm); 4453 4453 } 4454 4454 }
+44 -44
arch/x86/kvm/vmx.c
··· 5840 5840 memset(vmx_msr_bitmap_legacy, 0xff, PAGE_SIZE); 5841 5841 memset(vmx_msr_bitmap_longmode, 0xff, PAGE_SIZE); 5842 5842 5843 - vmx_disable_intercept_for_msr(MSR_FS_BASE, false); 5844 - vmx_disable_intercept_for_msr(MSR_GS_BASE, false); 5845 - vmx_disable_intercept_for_msr(MSR_KERNEL_GS_BASE, true); 5846 - vmx_disable_intercept_for_msr(MSR_IA32_SYSENTER_CS, false); 5847 - vmx_disable_intercept_for_msr(MSR_IA32_SYSENTER_ESP, false); 5848 - vmx_disable_intercept_for_msr(MSR_IA32_SYSENTER_EIP, false); 5849 - vmx_disable_intercept_for_msr(MSR_IA32_BNDCFGS, true); 5850 - 5851 - memcpy(vmx_msr_bitmap_legacy_x2apic, 5852 - vmx_msr_bitmap_legacy, PAGE_SIZE); 5853 - memcpy(vmx_msr_bitmap_longmode_x2apic, 5854 - vmx_msr_bitmap_longmode, PAGE_SIZE); 5855 - 5856 - if (enable_apicv) { 5857 - for (msr = 0x800; msr <= 0x8ff; msr++) 5858 - vmx_disable_intercept_msr_read_x2apic(msr); 5859 - 5860 - /* According SDM, in x2apic mode, the whole id reg is used. 5861 - * But in KVM, it only use the highest eight bits. Need to 5862 - * intercept it */ 5863 - vmx_enable_intercept_msr_read_x2apic(0x802); 5864 - /* TMCCT */ 5865 - vmx_enable_intercept_msr_read_x2apic(0x839); 5866 - /* TPR */ 5867 - vmx_disable_intercept_msr_write_x2apic(0x808); 5868 - /* EOI */ 5869 - vmx_disable_intercept_msr_write_x2apic(0x80b); 5870 - /* SELF-IPI */ 5871 - vmx_disable_intercept_msr_write_x2apic(0x83f); 5872 - } 5873 - 5874 - if (enable_ept) { 5875 - kvm_mmu_set_mask_ptes(0ull, 5876 - (enable_ept_ad_bits) ? VMX_EPT_ACCESS_BIT : 0ull, 5877 - (enable_ept_ad_bits) ? VMX_EPT_DIRTY_BIT : 0ull, 5878 - 0ull, VMX_EPT_EXECUTABLE_MASK); 5879 - ept_set_mmio_spte_mask(); 5880 - kvm_enable_tdp(); 5881 - } else 5882 - kvm_disable_tdp(); 5883 - 5884 - update_ple_window_actual_max(); 5885 - 5886 5843 if (setup_vmcs_config(&vmcs_config) < 0) { 5887 5844 r = -EIO; 5888 5845 goto out7; 5889 - } 5846 + } 5890 5847 5891 5848 if (boot_cpu_has(X86_FEATURE_NX)) 5892 5849 kvm_enable_efer_bits(EFER_NX); ··· 5901 5944 5902 5945 if (nested) 5903 5946 nested_vmx_setup_ctls_msrs(); 5947 + 5948 + vmx_disable_intercept_for_msr(MSR_FS_BASE, false); 5949 + vmx_disable_intercept_for_msr(MSR_GS_BASE, false); 5950 + vmx_disable_intercept_for_msr(MSR_KERNEL_GS_BASE, true); 5951 + vmx_disable_intercept_for_msr(MSR_IA32_SYSENTER_CS, false); 5952 + vmx_disable_intercept_for_msr(MSR_IA32_SYSENTER_ESP, false); 5953 + vmx_disable_intercept_for_msr(MSR_IA32_SYSENTER_EIP, false); 5954 + vmx_disable_intercept_for_msr(MSR_IA32_BNDCFGS, true); 5955 + 5956 + memcpy(vmx_msr_bitmap_legacy_x2apic, 5957 + vmx_msr_bitmap_legacy, PAGE_SIZE); 5958 + memcpy(vmx_msr_bitmap_longmode_x2apic, 5959 + vmx_msr_bitmap_longmode, PAGE_SIZE); 5960 + 5961 + if (enable_apicv) { 5962 + for (msr = 0x800; msr <= 0x8ff; msr++) 5963 + vmx_disable_intercept_msr_read_x2apic(msr); 5964 + 5965 + /* According SDM, in x2apic mode, the whole id reg is used. 5966 + * But in KVM, it only use the highest eight bits. Need to 5967 + * intercept it */ 5968 + vmx_enable_intercept_msr_read_x2apic(0x802); 5969 + /* TMCCT */ 5970 + vmx_enable_intercept_msr_read_x2apic(0x839); 5971 + /* TPR */ 5972 + vmx_disable_intercept_msr_write_x2apic(0x808); 5973 + /* EOI */ 5974 + vmx_disable_intercept_msr_write_x2apic(0x80b); 5975 + /* SELF-IPI */ 5976 + vmx_disable_intercept_msr_write_x2apic(0x83f); 5977 + } 5978 + 5979 + if (enable_ept) { 5980 + kvm_mmu_set_mask_ptes(0ull, 5981 + (enable_ept_ad_bits) ? VMX_EPT_ACCESS_BIT : 0ull, 5982 + (enable_ept_ad_bits) ? VMX_EPT_DIRTY_BIT : 0ull, 5983 + 0ull, VMX_EPT_EXECUTABLE_MASK); 5984 + ept_set_mmio_spte_mask(); 5985 + kvm_enable_tdp(); 5986 + } else 5987 + kvm_disable_tdp(); 5988 + 5989 + update_ple_window_actual_max(); 5904 5990 5905 5991 return alloc_kvm_area(); 5906 5992
+20 -6
virt/kvm/kvm_main.c
··· 671 671 672 672 WARN_ON(mslots[i].id != id); 673 673 if (!new->npages) { 674 + WARN_ON(!mslots[i].npages); 674 675 new->base_gfn = 0; 675 676 if (mslots[i].npages) 676 677 slots->used_slots--; ··· 688 687 slots->id_to_index[mslots[i].id] = i; 689 688 i++; 690 689 } 691 - while (i > 0 && 692 - new->base_gfn > mslots[i - 1].base_gfn) { 693 - mslots[i] = mslots[i - 1]; 694 - slots->id_to_index[mslots[i].id] = i; 695 - i--; 696 - } 690 + 691 + /* 692 + * The ">=" is needed when creating a slot with base_gfn == 0, 693 + * so that it moves before all those with base_gfn == npages == 0. 694 + * 695 + * On the other hand, if new->npages is zero, the above loop has 696 + * already left i pointing to the beginning of the empty part of 697 + * mslots, and the ">=" would move the hole backwards in this 698 + * case---which is wrong. So skip the loop when deleting a slot. 699 + */ 700 + if (new->npages) { 701 + while (i > 0 && 702 + new->base_gfn >= mslots[i - 1].base_gfn) { 703 + mslots[i] = mslots[i - 1]; 704 + slots->id_to_index[mslots[i].id] = i; 705 + i--; 706 + } 707 + } else 708 + WARN_ON_ONCE(i != slots->used_slots); 697 709 698 710 mslots[i] = *new; 699 711 slots->id_to_index[mslots[i].id] = i;