Re: [PATCH v3 23/37] KVM: nVMX: Add helper to handle TLB flushes on nested VM-Enter/VM-Exit
From: Lai Jiangshan
Date: Thu Oct 28 2021 - 09:11:26 EST
On Sat, Mar 21, 2020 at 5:29 AM Sean Christopherson
<sean.j.christopherson@xxxxxxxxx> wrote:
> + if (!nested_cpu_has_vpid(vmcs12) || !nested_has_guest_tlb_tag(vcpu)) {
> + kvm_make_request(KVM_REQ_TLB_FLUSH, vcpu);
> + } else if (is_vmenter &&
> + vmcs12->virtual_processor_id != vmx->nested.last_vpid) {
> + vmx->nested.last_vpid = vmcs12->virtual_processor_id;
> + vpid_sync_context(nested_get_vpid02(vcpu));
> + }
> +}
(I'm sorry to pick this old email to reply to, but the problem has
nothing to do with this patch nor 5c614b3583e7 and it exists since
nested vmx is introduced.)
I think kvm_mmu_free_guest_mode_roots() should be called
if (!enable_ept && vmcs12->virtual_processor_id != vmx->nested.last_vpid)
just because prev_roots doesn't cache the vpid12.
(prev_roots caches PCID, which is distinctive)
The problem hardly exists if L1's hypervisor is also kvm, but if
L1's hypervisor is different or is also kvm with some changes
in the way how it manages VPID. (Actually, I planned to
change the way how it manages VPID to svm-like.)
nvcpu0 and nvcpu1 are in the same nested VM and are running the same
application process.
vcpu1: runs nvcpu1 with the same cr3 as nvcpu0
vcpu0: runs nvcpu0, modifies pagetable and L1 sync root, and flush VPID12
but L0 doesn't sync, it just removes the root from vcpu0's prev_roots.
vcpu1: L1 migrates nvcpu0 to here, allocates a *fresh* VPID12 to nvcpu0
like the ways svm allocates a fresh ASID.
vcpu1: runs nvcpu0 without any flush. (vcpu1's prev_roots has already had it
L0 hasn't synced it)
If my understanding is correct, I hope it is a report and somebody fixes it.