[Devel] [PATCH RHEL7 COMMIT] ms/kvm: x86: vmx: fix vpid leak

Konstantin Khorenko khorenko at virtuozzo.com
Mon Aug 13 14:28:37 MSK 2018


The commit is pushed to "branch-rh7-3.10.0-862.9.1.vz7.70.x-ovz" and will appear at https://src.openvz.org/scm/ovz/vzkernel.git
after rh7-3.10.0-862.9.1.vz7.70.2
------>
commit 3abde379141387695f46bb2dea28caddee7e1293
Author: Roman Kagan <rkagan at virtuozzo.com>
Date:   Mon Aug 13 14:28:37 2018 +0300

    ms/kvm: x86: vmx: fix vpid leak
    
    commit 63aff65573d73eb8dda4732ad4ef222dd35e4862 upstream.
    
    VPID for the nested vcpu is allocated at vmx_create_vcpu whenever nested
    vmx is turned on with the module parameter.
    
    However, it's only freed if the L1 guest has executed VMXON which is not
    a given.
    
    As a result, on a system with nested==on every creation+deletion of an
    L1 vcpu without running an L2 guest results in leaking one vpid.  Since
    the total number of vpids is limited to 64k, they can eventually get
    exhausted, preventing L2 from starting.
    
    Delay allocation of the L2 vpid until VMXON emulation, thus matching its
    freeing.
    
    mFixes: 5c614b3583e7 ("KVM: nVMX: nested VPID emulation")
    Cc: stable at vger.kernel.org
    Signed-off-by: Roman Kagan <rkagan at virtuozzo.com>
    Signed-off-by: Paolo Bonzini <pbonzini at redhat.com>
    Signed-off-by: Greg Kroah-Hartman <gregkh at linuxfoundation.org>
    
    (cherry picked from commit 020a90f653dd02dbbae389da91f510d5f33984dc
    on stable/linux-4.9.y)
    
    https://jira.sw.ru/browse/PSBM-86479
    
    Signed-off-by: Roman Kagan <rkagan at virtuozzo.com>
---
 arch/x86/kvm/vmx.c | 7 +++----
 1 file changed, 3 insertions(+), 4 deletions(-)

diff --git a/arch/x86/kvm/vmx.c b/arch/x86/kvm/vmx.c
index f3fc84960df1..e1ad90f6d209 100644
--- a/arch/x86/kvm/vmx.c
+++ b/arch/x86/kvm/vmx.c
@@ -7123,6 +7123,8 @@ static int handle_vmon(struct kvm_vcpu *vcpu)
 		     HRTIMER_MODE_REL);
 	vmx->nested.preemption_timer.function = vmx_preemption_timer_fn;
 
+	vmx->nested.vpid02 = allocate_vpid();
+
 	vmx->nested.vmxon = true;
 
 	skip_emulated_instruction(vcpu);
@@ -9355,10 +9357,8 @@ static struct kvm_vcpu *vmx_create_vcpu(struct kvm *kvm, unsigned int id)
 			goto free_vmcs;
 	}
 
-	if (nested) {
+	if (nested)
 		nested_vmx_setup_ctls_msrs(vmx);
-		vmx->nested.vpid02 = allocate_vpid();
-	}
 
 	vmx->nested.posted_intr_nv = -1;
 	vmx->nested.current_vmptr = -1ull;
@@ -9375,7 +9375,6 @@ static struct kvm_vcpu *vmx_create_vcpu(struct kvm *kvm, unsigned int id)
 	return &vmx->vcpu;
 
 free_vmcs:
-	free_vpid(vmx->nested.vpid02);
 	free_loaded_vmcs(vmx->loaded_vmcs);
 free_msrs:
 	kfree(vmx->guest_msrs);


More information about the Devel mailing list