Skip to contentSkip to conversation

KVM: arm64: Tentative fixes for page-table lifetime issues

PATCH Applied Will Deacon 2 participants 4 messages Mar 27 – Apr 2

Subsystems (2)
lore
Share & tools
lore

Will Deacon

author maintainer
#0 lore raw

cover KVM: arm64: Tentative fixes for page-table lifetime issues

Hi all,

Sashiko highlighted a couple of potential page-table lifetime issues in the upstream code while it was reviewing the pKVM protected memory series. They make sense to me so I've had a crack at fixing them and writing a better description of the problem in the commit message.

For the second issue, I've tested it by forcing the notifier registration to fail and then watching the SecPageTables line in /proc/meminfo after attempting to create VMs.

Cheers,

Will

Cc Marc Zyngier <[email protected]>
Cc Oliver Upton <[email protected]>
Cc Joey Gouly <[email protected]>
Cc Suzuki K Poulose <[email protected]>
Cc Zenghui Yu <[email protected]>

--->8

Will Deacon (2):
KVM: arm64: Don't leave mmu->pgt dangling on kvm_init_stage2_mmu()
error
KVM: arm64: Destroy stage-2 page-table in kvm_arch_destroy_vm()

 arch/arm64/kvm/arm.c | 1 +
 arch/arm64/kvm/mmu.c | 1 +
 2 files changed, 2 insertions(+)
Signature · 1 line
2.53.0.1018.g2bb0e51243-goog
author maintainer
#1 lore raw

PATCH 1/2 KVM: arm64: Don't leave mmu->pgt dangling on kvm_init_stage2_mmu() error

If kvm_init_stage2_mmu() fails to allocate 'mmu->last_vcpu_ran', it destroys the newly allocated stage-2 page-table before returning ENOMEM.

Unfortunately, it also leaves a dangling pointer in 'mmu->pgt' which points at the freed 'kvm_pgtable' structure. This is likely to confuse the kvm_vcpu_init_nested() failure path which can double-free the structure if it finds it via kvm_free_stage2_pgd().

Ensure that the dangling 'mmu->pgt' pointer is cleared when returning an error from kvm_init_stage2_mmu().

---
 arch/arm64/kvm/mmu.c | 1 +
 1 file changed, 1 insertion(+)
arch/arm64/kvm/mmu.c +1 -0
index 17d64a1e11e5..34e9d897d08b 100644
@@ -1013,6 +1013,7 @@ int kvm_init_stage2_mmu(struct kvm *kvm, struct kvm_s2_mmu *mmu, unsigned long t
 
 out_destroy_pgtable:
 	kvm_stage2_destroy(pgt);
+	mmu->pgt = NULL;
 out_free_pgtable:
 	kfree(pgt);
 	return err;
Signature · 1 line
2.53.0.1018.g2bb0e51243-goog
author maintainer
#2 lore raw

PATCH 2/2 KVM: arm64: Destroy stage-2 page-table in kvm_arch_destroy_vm()

In reply to Will Deacon

kvm_arch_destroy_vm() can be called on the kvm_create_vm() error path after we have failed to register the MMU notifiers for the new VM. In this case, we cannot rely on the MMU ->release() notifier to call kvm_arch_flush_shadow_all() and so the stage-2 page-table allocated in kvm_arch_init_vm() will be leaked.

Explicitly destroy the stage-2 page-table in kvm_arch_destroy_vm(), so that we clean up after kvm_arch_destroy_vm() without relying on the MMU notifiers.

---
 arch/arm64/kvm/arm.c | 1 +
 1 file changed, 1 insertion(+)
arch/arm64/kvm/arm.c +1 -0
index 410ffd41fd73..29bfa79555b2 100644
@@ -301,6 +301,7 @@ void kvm_arch_destroy_vm(struct kvm *kvm)
 	if (is_protected_kvm_enabled())
 		pkvm_destroy_hyp_vm(kvm);
 
+	kvm_uninit_stage2_mmu(kvm);
 	kvm_destroy_mpidr_data(kvm);
 
 	kfree(kvm->arch.sysreg_masks);
Signature · 1 line
2.53.0.1018.g2bb0e51243-goog
maintainer Applied
#3 lore raw
In reply to Will Deacon
Quoted 10 lines · Will Deacon

Sashiko highlighted a couple of potential page-table lifetime issues in the upstream code while it was reviewing the pKVM protected memory series. They make sense to me so I've had a crack at fixing them and writing a better description of the problem in the commit message.

For the second issue, I've tested it by forcing the notifier registration to fail and then watching the SecPageTables line in /proc/meminfo after attempting to create VMs.

[...]

Applied to next, thanks!

[1/2] KVM: arm64: Don't leave mmu->pgt dangling on kvm_init_stage2_mmu() error

      commit: 2fc0f3e2b9a9f397554ffe86e8f6eb0e2507ec6e
[2/2] KVM: arm64: Destroy stage-2 page-table in kvm_arch_destroy_vm()
      commit: a3ca3bfd01b7ee9f54ed85718a6d553cdd87050e

Cheers,

	M.
Signature · 1 line
Without deviation from the norm, progress is not possible.