Skip to content

Commit c927013

Browse files
paulusmackmpe
authored andcommitted
KVM: PPC: Book3S HV: Add userspace interfaces for POWER9 MMU
This adds two capabilities and two ioctls to allow userspace to find out about and configure the POWER9 MMU in a guest. The two capabilities tell userspace whether KVM can support a guest using the radix MMU, or using the hashed page table (HPT) MMU with a process table and segment tables. (Note that the MMUs in the POWER9 processor cores do not use the process and segment tables when in HPT mode, but the nest MMU does). The KVM_PPC_CONFIGURE_V3_MMU ioctl allows userspace to specify whether a guest will use the radix MMU or the HPT MMU, and to specify the size and location (in guest space) of the process table. The KVM_PPC_GET_RMMU_INFO ioctl gives userspace information about the radix MMU. It returns a list of supported radix tree geometries (base page size and number of bits indexed at each level of the radix tree) and the encoding used to specify the various page sizes for the TLB invalidate entry instruction. Initially, both capabilities return 0 and the ioctls return -EINVAL, until the necessary infrastructure for them to operate correctly is added. Signed-off-by: Paul Mackerras <paulus@ozlabs.org> Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
1 parent bc35512 commit c927013

File tree

6 files changed

+156
-0
lines changed

6 files changed

+156
-0
lines changed

Documentation/virtual/kvm/api.txt

Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3201,6 +3201,71 @@ struct kvm_reinject_control {
32013201
pit_reinject = 0 (!reinject mode) is recommended, unless running an old
32023202
operating system that uses the PIT for timing (e.g. Linux 2.4.x).
32033203

3204+
4.99 KVM_PPC_CONFIGURE_V3_MMU
3205+
3206+
Capability: KVM_CAP_PPC_RADIX_MMU or KVM_CAP_PPC_HASH_MMU_V3
3207+
Architectures: ppc
3208+
Type: vm ioctl
3209+
Parameters: struct kvm_ppc_mmuv3_cfg (in)
3210+
Returns: 0 on success,
3211+
-EFAULT if struct kvm_ppc_mmuv3_cfg cannot be read,
3212+
-EINVAL if the configuration is invalid
3213+
3214+
This ioctl controls whether the guest will use radix or HPT (hashed
3215+
page table) translation, and sets the pointer to the process table for
3216+
the guest.
3217+
3218+
struct kvm_ppc_mmuv3_cfg {
3219+
__u64 flags;
3220+
__u64 process_table;
3221+
};
3222+
3223+
There are two bits that can be set in flags; KVM_PPC_MMUV3_RADIX and
3224+
KVM_PPC_MMUV3_GTSE. KVM_PPC_MMUV3_RADIX, if set, configures the guest
3225+
to use radix tree translation, and if clear, to use HPT translation.
3226+
KVM_PPC_MMUV3_GTSE, if set and if KVM permits it, configures the guest
3227+
to be able to use the global TLB and SLB invalidation instructions;
3228+
if clear, the guest may not use these instructions.
3229+
3230+
The process_table field specifies the address and size of the guest
3231+
process table, which is in the guest's space. This field is formatted
3232+
as the second doubleword of the partition table entry, as defined in
3233+
the Power ISA V3.00, Book III section 5.7.6.1.
3234+
3235+
4.100 KVM_PPC_GET_RMMU_INFO
3236+
3237+
Capability: KVM_CAP_PPC_RADIX_MMU
3238+
Architectures: ppc
3239+
Type: vm ioctl
3240+
Parameters: struct kvm_ppc_rmmu_info (out)
3241+
Returns: 0 on success,
3242+
-EFAULT if struct kvm_ppc_rmmu_info cannot be written,
3243+
-EINVAL if no useful information can be returned
3244+
3245+
This ioctl returns a structure containing two things: (a) a list
3246+
containing supported radix tree geometries, and (b) a list that maps
3247+
page sizes to put in the "AP" (actual page size) field for the tlbie
3248+
(TLB invalidate entry) instruction.
3249+
3250+
struct kvm_ppc_rmmu_info {
3251+
struct kvm_ppc_radix_geom {
3252+
__u8 page_shift;
3253+
__u8 level_bits[4];
3254+
__u8 pad[3];
3255+
} geometries[8];
3256+
__u32 ap_encodings[8];
3257+
};
3258+
3259+
The geometries[] field gives up to 8 supported geometries for the
3260+
radix page table, in terms of the log base 2 of the smallest page
3261+
size, and the number of bits indexed at each level of the tree, from
3262+
the PTE level up to the PGD level in that order. Any unused entries
3263+
will have 0 in the page_shift field.
3264+
3265+
The ap_encodings gives the supported page sizes and their AP field
3266+
encodings, encoded with the AP value in the top 3 bits and the log
3267+
base 2 of the page size in the bottom 6 bits.
3268+
32043269
5. The kvm_run structure
32053270
------------------------
32063271

@@ -3942,3 +4007,21 @@ In order to use SynIC, it has to be activated by setting this
39424007
capability via KVM_ENABLE_CAP ioctl on the vcpu fd. Note that this
39434008
will disable the use of APIC hardware virtualization even if supported
39444009
by the CPU, as it's incompatible with SynIC auto-EOI behavior.
4010+
4011+
8.3 KVM_CAP_PPC_RADIX_MMU
4012+
4013+
Architectures: ppc
4014+
4015+
This capability, if KVM_CHECK_EXTENSION indicates that it is
4016+
available, means that that the kernel can support guests using the
4017+
radix MMU defined in Power ISA V3.00 (as implemented in the POWER9
4018+
processor).
4019+
4020+
8.4 KVM_CAP_PPC_HASH_MMU_V3
4021+
4022+
Architectures: ppc
4023+
4024+
This capability, if KVM_CHECK_EXTENSION indicates that it is
4025+
available, means that that the kernel can support guests using the
4026+
hashed page table MMU defined in Power ISA V3.00 (as implemented in
4027+
the POWER9 processor), including in-memory segment tables.

arch/powerpc/include/asm/kvm_ppc.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -291,6 +291,8 @@ struct kvmppc_ops {
291291
struct irq_bypass_producer *);
292292
void (*irq_bypass_del_producer)(struct irq_bypass_consumer *,
293293
struct irq_bypass_producer *);
294+
int (*configure_mmu)(struct kvm *kvm, struct kvm_ppc_mmuv3_cfg *cfg);
295+
int (*get_rmmu_info)(struct kvm *kvm, struct kvm_ppc_rmmu_info *info);
294296
};
295297

296298
extern struct kvmppc_ops *kvmppc_hv_ops;

arch/powerpc/include/uapi/asm/kvm.h

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -413,6 +413,26 @@ struct kvm_get_htab_header {
413413
__u16 n_invalid;
414414
};
415415

416+
/* For KVM_PPC_CONFIGURE_V3_MMU */
417+
struct kvm_ppc_mmuv3_cfg {
418+
__u64 flags;
419+
__u64 process_table; /* second doubleword of partition table entry */
420+
};
421+
422+
/* Flag values for KVM_PPC_CONFIGURE_V3_MMU */
423+
#define KVM_PPC_MMUV3_RADIX 1 /* 1 = radix mode, 0 = HPT */
424+
#define KVM_PPC_MMUV3_GTSE 2 /* global translation shootdown enb. */
425+
426+
/* For KVM_PPC_GET_RMMU_INFO */
427+
struct kvm_ppc_rmmu_info {
428+
struct kvm_ppc_radix_geom {
429+
__u8 page_shift;
430+
__u8 level_bits[4];
431+
__u8 pad[3];
432+
} geometries[8];
433+
__u32 ap_encodings[8];
434+
};
435+
416436
/* Per-vcpu XICS interrupt controller state */
417437
#define KVM_REG_PPC_ICP_STATE (KVM_REG_PPC | KVM_REG_SIZE_U64 | 0x8c)
418438

arch/powerpc/kvm/book3s_hv.c

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3657,6 +3657,17 @@ static void init_default_hcalls(void)
36573657
}
36583658
}
36593659

3660+
/* dummy implementations for now */
3661+
static int kvmhv_configure_mmu(struct kvm *kvm, struct kvm_ppc_mmuv3_cfg *cfg)
3662+
{
3663+
return -EINVAL;
3664+
}
3665+
3666+
static int kvmhv_get_rmmu_info(struct kvm *kvm, struct kvm_ppc_rmmu_info *info)
3667+
{
3668+
return -EINVAL;
3669+
}
3670+
36603671
static struct kvmppc_ops kvm_ops_hv = {
36613672
.get_sregs = kvm_arch_vcpu_ioctl_get_sregs_hv,
36623673
.set_sregs = kvm_arch_vcpu_ioctl_set_sregs_hv,
@@ -3694,6 +3705,8 @@ static struct kvmppc_ops kvm_ops_hv = {
36943705
.irq_bypass_add_producer = kvmppc_irq_bypass_add_producer_hv,
36953706
.irq_bypass_del_producer = kvmppc_irq_bypass_del_producer_hv,
36963707
#endif
3708+
.configure_mmu = kvmhv_configure_mmu,
3709+
.get_rmmu_info = kvmhv_get_rmmu_info,
36973710
};
36983711

36993712
static int kvm_init_subcore_bitmap(void)

arch/powerpc/kvm/powerpc.c

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -565,6 +565,13 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
565565
case KVM_CAP_PPC_HWRNG:
566566
r = kvmppc_hwrng_present();
567567
break;
568+
case KVM_CAP_PPC_MMU_RADIX:
569+
r = !!(0 && hv_enabled && radix_enabled());
570+
break;
571+
case KVM_CAP_PPC_MMU_HASH_V3:
572+
r = !!(0 && hv_enabled && !radix_enabled() &&
573+
cpu_has_feature(CPU_FTR_ARCH_300));
574+
break;
568575
#endif
569576
case KVM_CAP_SYNC_MMU:
570577
#ifdef CONFIG_KVM_BOOK3S_HV_POSSIBLE
@@ -1468,6 +1475,31 @@ long kvm_arch_vm_ioctl(struct file *filp,
14681475
r = kvm_vm_ioctl_rtas_define_token(kvm, argp);
14691476
break;
14701477
}
1478+
case KVM_PPC_CONFIGURE_V3_MMU: {
1479+
struct kvm *kvm = filp->private_data;
1480+
struct kvm_ppc_mmuv3_cfg cfg;
1481+
1482+
r = -EINVAL;
1483+
if (!kvm->arch.kvm_ops->configure_mmu)
1484+
goto out;
1485+
r = -EFAULT;
1486+
if (copy_from_user(&cfg, argp, sizeof(cfg)))
1487+
goto out;
1488+
r = kvm->arch.kvm_ops->configure_mmu(kvm, &cfg);
1489+
break;
1490+
}
1491+
case KVM_PPC_GET_RMMU_INFO: {
1492+
struct kvm *kvm = filp->private_data;
1493+
struct kvm_ppc_rmmu_info info;
1494+
1495+
r = -EINVAL;
1496+
if (!kvm->arch.kvm_ops->get_rmmu_info)
1497+
goto out;
1498+
r = kvm->arch.kvm_ops->get_rmmu_info(kvm, &info);
1499+
if (r >= 0 && copy_to_user(argp, &info, sizeof(info)))
1500+
r = -EFAULT;
1501+
break;
1502+
}
14711503
default: {
14721504
struct kvm *kvm = filp->private_data;
14731505
r = kvm->arch.kvm_ops->arch_vm_ioctl(filp, ioctl, arg);

include/uapi/linux/kvm.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -871,6 +871,8 @@ struct kvm_ppc_smmu_info {
871871
#define KVM_CAP_S390_USER_INSTR0 130
872872
#define KVM_CAP_MSI_DEVID 131
873873
#define KVM_CAP_PPC_HTM 132
874+
#define KVM_CAP_PPC_MMU_RADIX 134
875+
#define KVM_CAP_PPC_MMU_HASH_V3 135
874876

875877
#ifdef KVM_CAP_IRQ_ROUTING
876878

@@ -1187,6 +1189,10 @@ struct kvm_s390_ucas_mapping {
11871189
#define KVM_ARM_SET_DEVICE_ADDR _IOW(KVMIO, 0xab, struct kvm_arm_device_addr)
11881190
/* Available with KVM_CAP_PPC_RTAS */
11891191
#define KVM_PPC_RTAS_DEFINE_TOKEN _IOW(KVMIO, 0xac, struct kvm_rtas_token_args)
1192+
/* Available with KVM_CAP_PPC_RADIX_MMU or KVM_CAP_PPC_HASH_MMU_V3 */
1193+
#define KVM_PPC_CONFIGURE_V3_MMU _IOW(KVMIO, 0xaf, struct kvm_ppc_mmuv3_cfg)
1194+
/* Available with KVM_CAP_PPC_RADIX_MMU */
1195+
#define KVM_PPC_GET_RMMU_INFO _IOW(KVMIO, 0xb0, struct kvm_ppc_rmmu_info)
11901196

11911197
/* ioctl for vm fd */
11921198
#define KVM_CREATE_DEVICE _IOWR(KVMIO, 0xe0, struct kvm_create_device)

0 commit comments

Comments
 (0)