Skip to content

Commit 3064cee

Browse files
author
Marc Zyngier
committed
Merge branch kvm-arm64/pkvm_vm_handle into kvmarm-master/next
* kvm-arm64/pkvm_vm_handle: : pKVM VM handle allocation fixes, courtesy of Fuad Tabba. : : From the cover letter (20250909072437.4110547-1-tabba@google.com): : : "In pKVM, this handle is allocated when the VM is initialized at the : hypervisor, which is on the first vCPU run. However, the host starts : initializing the VM and setting up its data structures earlier. MMU : notifiers for the VMs are also registered before VM initialization at : the hypervisor, and rely on the handle to identify the VM. : : Therefore, there is a potential gap between when the VM is (partially) : setup at the host, but still without a valid pKVM handle to identify it : when communicating with the hypervisor." KVM: arm64: Reserve pKVM handle during pkvm_init_host_vm() KVM: arm64: Introduce separate hypercalls for pKVM VM reservation and initialization KVM: arm64: Consolidate pKVM hypervisor VM initialization logic KVM: arm64: Separate allocation and insertion of pKVM VM table entries KVM: arm64: Decouple hyp VM creation state from its handle KVM: arm64: Clarify comments to distinguish pKVM mode from protected VMs KVM: arm64: Rename 'host_kvm' to 'kvm' in pKVM host code KVM: arm64: Rename pkvm.enabled to pkvm.is_protected KVM: arm64: Add build-time check for duplicate DECLARE_REG use Signed-off-by: Marc Zyngier <maz@kernel.org>
2 parents ebdda44 + 07aeb70 commit 3064cee

9 files changed

Lines changed: 221 additions & 75 deletions

File tree

arch/arm64/include/asm/kvm_asm.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,8 @@ enum __kvm_host_smccc_func {
8181
__KVM_HOST_SMCCC_FUNC___kvm_timer_set_cntvoff,
8282
__KVM_HOST_SMCCC_FUNC___vgic_v3_save_vmcr_aprs,
8383
__KVM_HOST_SMCCC_FUNC___vgic_v3_restore_vmcr_aprs,
84+
__KVM_HOST_SMCCC_FUNC___pkvm_reserve_vm,
85+
__KVM_HOST_SMCCC_FUNC___pkvm_unreserve_vm,
8486
__KVM_HOST_SMCCC_FUNC___pkvm_init_vm,
8587
__KVM_HOST_SMCCC_FUNC___pkvm_init_vcpu,
8688
__KVM_HOST_SMCCC_FUNC___pkvm_teardown_vm,

arch/arm64/include/asm/kvm_host.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -252,7 +252,8 @@ struct kvm_protected_vm {
252252
pkvm_handle_t handle;
253253
struct kvm_hyp_memcache teardown_mc;
254254
struct kvm_hyp_memcache stage2_teardown_mc;
255-
bool enabled;
255+
bool is_protected;
256+
bool is_created;
256257
};
257258

258259
struct kvm_mpidr_data {
@@ -1441,7 +1442,7 @@ struct kvm *kvm_arch_alloc_vm(void);
14411442

14421443
#define __KVM_HAVE_ARCH_FLUSH_REMOTE_TLBS_RANGE
14431444

1444-
#define kvm_vm_is_protected(kvm) (is_protected_kvm_enabled() && (kvm)->arch.pkvm.enabled)
1445+
#define kvm_vm_is_protected(kvm) (is_protected_kvm_enabled() && (kvm)->arch.pkvm.is_protected)
14451446

14461447
#define vcpu_is_protected(vcpu) kvm_vm_is_protected((vcpu)->kvm)
14471448

arch/arm64/include/asm/kvm_pkvm.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818

1919
int pkvm_init_host_vm(struct kvm *kvm);
2020
int pkvm_create_hyp_vm(struct kvm *kvm);
21+
bool pkvm_hyp_vm_is_created(struct kvm *kvm);
2122
void pkvm_destroy_hyp_vm(struct kvm *kvm);
2223
int pkvm_create_hyp_vcpu(struct kvm_vcpu *vcpu);
2324

arch/arm64/kvm/arm.c

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -170,10 +170,6 @@ int kvm_arch_init_vm(struct kvm *kvm, unsigned long type)
170170
if (ret)
171171
return ret;
172172

173-
ret = pkvm_init_host_vm(kvm);
174-
if (ret)
175-
goto err_unshare_kvm;
176-
177173
if (!zalloc_cpumask_var(&kvm->arch.supported_cpus, GFP_KERNEL_ACCOUNT)) {
178174
ret = -ENOMEM;
179175
goto err_unshare_kvm;
@@ -184,6 +180,16 @@ int kvm_arch_init_vm(struct kvm *kvm, unsigned long type)
184180
if (ret)
185181
goto err_free_cpumask;
186182

183+
if (is_protected_kvm_enabled()) {
184+
/*
185+
* If any failures occur after this is successful, make sure to
186+
* call __pkvm_unreserve_vm to unreserve the VM in hyp.
187+
*/
188+
ret = pkvm_init_host_vm(kvm);
189+
if (ret)
190+
goto err_free_cpumask;
191+
}
192+
187193
kvm_vgic_early_init(kvm);
188194

189195
kvm_timer_init_vm(kvm);

arch/arm64/kvm/hyp/include/nvhe/pkvm.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ struct pkvm_hyp_vcpu {
2929
};
3030

3131
/*
32-
* Holds the relevant data for running a protected vm.
32+
* Holds the relevant data for running a vm in protected mode.
3333
*/
3434
struct pkvm_hyp_vm {
3535
struct kvm kvm;
@@ -67,6 +67,8 @@ static inline bool pkvm_hyp_vm_is_protected(struct pkvm_hyp_vm *hyp_vm)
6767

6868
void pkvm_hyp_vm_table_init(void *tbl);
6969

70+
int __pkvm_reserve_vm(void);
71+
void __pkvm_unreserve_vm(pkvm_handle_t handle);
7072
int __pkvm_init_vm(struct kvm *host_kvm, unsigned long vm_hva,
7173
unsigned long pgd_hva);
7274
int __pkvm_init_vcpu(pkvm_handle_t handle, struct kvm_vcpu *host_vcpu,

arch/arm64/kvm/hyp/include/nvhe/trap_handler.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,8 @@
1212
#include <asm/kvm_host.h>
1313

1414
#define cpu_reg(ctxt, r) (ctxt)->regs.regs[r]
15-
#define DECLARE_REG(type, name, ctxt, reg) \
15+
#define DECLARE_REG(type, name, ctxt, reg) \
16+
__always_unused int ___check_reg_ ## reg; \
1617
type name = (type)cpu_reg(ctxt, (reg))
1718

1819
#endif /* __ARM64_KVM_NVHE_TRAP_HANDLER_H__ */

arch/arm64/kvm/hyp/nvhe/hyp-main.c

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -546,6 +546,18 @@ static void handle___pkvm_prot_finalize(struct kvm_cpu_context *host_ctxt)
546546
cpu_reg(host_ctxt, 1) = __pkvm_prot_finalize();
547547
}
548548

549+
static void handle___pkvm_reserve_vm(struct kvm_cpu_context *host_ctxt)
550+
{
551+
cpu_reg(host_ctxt, 1) = __pkvm_reserve_vm();
552+
}
553+
554+
static void handle___pkvm_unreserve_vm(struct kvm_cpu_context *host_ctxt)
555+
{
556+
DECLARE_REG(pkvm_handle_t, handle, host_ctxt, 1);
557+
558+
__pkvm_unreserve_vm(handle);
559+
}
560+
549561
static void handle___pkvm_init_vm(struct kvm_cpu_context *host_ctxt)
550562
{
551563
DECLARE_REG(struct kvm *, host_kvm, host_ctxt, 1);
@@ -606,6 +618,8 @@ static const hcall_t host_hcall[] = {
606618
HANDLE_FUNC(__kvm_timer_set_cntvoff),
607619
HANDLE_FUNC(__vgic_v3_save_vmcr_aprs),
608620
HANDLE_FUNC(__vgic_v3_restore_vmcr_aprs),
621+
HANDLE_FUNC(__pkvm_reserve_vm),
622+
HANDLE_FUNC(__pkvm_unreserve_vm),
609623
HANDLE_FUNC(__pkvm_init_vm),
610624
HANDLE_FUNC(__pkvm_init_vcpu),
611625
HANDLE_FUNC(__pkvm_teardown_vm),

0 commit comments

Comments
 (0)