All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2 0/3] Provide VM capability to disable PMU virtualization for individual VMs
@ 2022-01-21  0:29 David Dunn
  2022-01-21  0:29 ` [PATCH v2 1/3] " David Dunn
                   ` (2 more replies)
  0 siblings, 3 replies; 5+ messages in thread
From: David Dunn @ 2022-01-21  0:29 UTC (permalink / raw)
  To: kvm, pbonzini, like.xu.linux, jmattson, cloudliang; +Cc: daviddunn

This patchset adds a new per VM capability for configuring the x86 PMU.
Right now the only configuration is to disable the PMU for an entire VM.

Thanks to Sean and Like for great feedback on v1.

I've incorporated most of the comments.  Unfortunately I wasn't able to
get the AMD version to work by using pmu->version == 0 as a flag.  And
it makes the Intel pmu->refresh() logic complicated.  So this version
stays with the kvm->arch.enable_pmu boolean on each VM.

David Dunn (3):
  Provide VM capability to disable PMU virtualization for individual VMs
  selftests: introduce function to create test VM without vcpus.
  selftests: Verify disabling PMU via KVM_CAP_CONFIG_PMU

 arch/x86/include/asm/kvm_host.h               |  1 +
 arch/x86/kvm/svm/pmu.c                        |  2 +-
 arch/x86/kvm/vmx/pmu_intel.c                  |  2 +-
 arch/x86/kvm/x86.c                            | 12 +++++
 include/uapi/linux/kvm.h                      |  4 ++
 tools/include/uapi/linux/kvm.h                |  4 ++
 .../selftests/kvm/include/kvm_util_base.h     |  3 ++
 tools/testing/selftests/kvm/lib/kvm_util.c    | 48 ++++++++++++++-----
 .../kvm/x86_64/pmu_event_filter_test.c        | 35 ++++++++++++++
 9 files changed, 96 insertions(+), 15 deletions(-)

-- 
2.35.0.rc0.227.g00780c9af4-goog


^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCH v2 1/3] Provide VM capability to disable PMU virtualization for individual VMs
  2022-01-21  0:29 [PATCH v2 0/3] Provide VM capability to disable PMU virtualization for individual VMs David Dunn
@ 2022-01-21  0:29 ` David Dunn
  2022-01-21  6:59   ` Like Xu
  2022-01-21  0:29 ` [PATCH v2 2/3] selftests: introduce function to create test VM without vcpus David Dunn
  2022-01-21  0:29 ` [PATCH v2 3/3] selftests: Verify disabling PMU via KVM_CAP_CONFIG_PMU David Dunn
  2 siblings, 1 reply; 5+ messages in thread
From: David Dunn @ 2022-01-21  0:29 UTC (permalink / raw)
  To: kvm, pbonzini, like.xu.linux, jmattson, cloudliang; +Cc: daviddunn

KVM_PMU_CONFIG_DISABLE can be used to disable PMU virtualization on
individual x86 VMs.  PMU configuration must be done prior to creating
VCPUs.

To enable future extension, KVM_CAP_PMU_CONFIG reports available
settings when queried via check_extension.

Since KVM_GET_SUPPORTED_CPUID reports the maximal CPUID information
based on module parameters, usermode will need to adjust CPUID when
disabling PMU virtualization on individual VMs.

Signed-off-by: David Dunn <daviddunn@google.com>
---
 arch/x86/include/asm/kvm_host.h |  1 +
 arch/x86/kvm/svm/pmu.c          |  2 +-
 arch/x86/kvm/vmx/pmu_intel.c    |  2 +-
 arch/x86/kvm/x86.c              | 12 ++++++++++++
 include/uapi/linux/kvm.h        |  4 ++++
 tools/include/uapi/linux/kvm.h  |  4 ++++
 6 files changed, 23 insertions(+), 2 deletions(-)

diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h
index 682ad02a4e58..5cdcd4a7671b 100644
--- a/arch/x86/include/asm/kvm_host.h
+++ b/arch/x86/include/asm/kvm_host.h
@@ -1232,6 +1232,7 @@ struct kvm_arch {
 	hpa_t	hv_root_tdp;
 	spinlock_t hv_root_tdp_lock;
 #endif
+	bool enable_pmu;
 };
 
 struct kvm_vm_stat {
diff --git a/arch/x86/kvm/svm/pmu.c b/arch/x86/kvm/svm/pmu.c
index 5aa45f13b16d..d4de52409335 100644
--- a/arch/x86/kvm/svm/pmu.c
+++ b/arch/x86/kvm/svm/pmu.c
@@ -101,7 +101,7 @@ static inline struct kvm_pmc *get_gp_pmc_amd(struct kvm_pmu *pmu, u32 msr,
 {
 	struct kvm_vcpu *vcpu = pmu_to_vcpu(pmu);
 
-	if (!enable_pmu)
+	if (!vcpu->kvm->arch.enable_pmu)
 		return NULL;
 
 	switch (msr) {
diff --git a/arch/x86/kvm/vmx/pmu_intel.c b/arch/x86/kvm/vmx/pmu_intel.c
index 466d18fc0c5d..2c5868d77268 100644
--- a/arch/x86/kvm/vmx/pmu_intel.c
+++ b/arch/x86/kvm/vmx/pmu_intel.c
@@ -487,7 +487,7 @@ static void intel_pmu_refresh(struct kvm_vcpu *vcpu)
 	pmu->reserved_bits = 0xffffffff00200000ull;
 
 	entry = kvm_find_cpuid_entry(vcpu, 0xa, 0);
-	if (!entry || !enable_pmu)
+	if (!entry || !vcpu->kvm->arch.enable_pmu)
 		return;
 	eax.full = entry->eax;
 	edx.full = entry->edx;
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 55518b7d3b96..42a98635bea5 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -4326,6 +4326,9 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
 		if (r < sizeof(struct kvm_xsave))
 			r = sizeof(struct kvm_xsave);
 		break;
+	case KVM_CAP_PMU_CONFIG:
+		r = enable_pmu ? KVM_PMU_CONFIG_VALID : 0;
+		break;
 	}
 	default:
 		break;
@@ -5937,6 +5940,14 @@ int kvm_vm_ioctl_enable_cap(struct kvm *kvm,
 		kvm->arch.exit_on_emulation_error = cap->args[0];
 		r = 0;
 		break;
+	case KVM_CAP_PMU_CONFIG:
+		r = -EINVAL;
+		if (!enable_pmu || kvm->created_vcpus > 0 ||
+		    cap->args[0] & ~KVM_PMU_CONFIG_VALID)
+			break;
+		kvm->arch.enable_pmu = !(cap->args[0] & KVM_PMU_CONFIG_DISABLE);
+		r = 0;
+		break;
 	default:
 		r = -EINVAL;
 		break;
@@ -11562,6 +11573,7 @@ int kvm_arch_init_vm(struct kvm *kvm, unsigned long type)
 	raw_spin_unlock_irqrestore(&kvm->arch.tsc_write_lock, flags);
 
 	kvm->arch.guest_can_read_msr_platform_info = true;
+	kvm->arch.enable_pmu = enable_pmu;
 
 #if IS_ENABLED(CONFIG_HYPERV)
 	spin_lock_init(&kvm->arch.hv_root_tdp_lock);
diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h
index 9563d294f181..57a1280fa43b 100644
--- a/include/uapi/linux/kvm.h
+++ b/include/uapi/linux/kvm.h
@@ -1133,6 +1133,7 @@ struct kvm_ppc_resize_hpt {
 #define KVM_CAP_VM_MOVE_ENC_CONTEXT_FROM 206
 #define KVM_CAP_VM_GPA_BITS 207
 #define KVM_CAP_XSAVE2 208
+#define KVM_CAP_PMU_CONFIG 209
 
 #ifdef KVM_CAP_IRQ_ROUTING
 
@@ -1972,6 +1973,9 @@ struct kvm_dirty_gfn {
 #define KVM_BUS_LOCK_DETECTION_OFF             (1 << 0)
 #define KVM_BUS_LOCK_DETECTION_EXIT            (1 << 1)
 
+#define KVM_PMU_CONFIG_DISABLE                 (1 << 0)
+#define KVM_PMU_CONFIG_VALID                   (KVM_PMU_CONFIG_DISABLE)
+
 /**
  * struct kvm_stats_header - Header of per vm/vcpu binary statistics data.
  * @flags: Some extra information for header, always 0 for now.
diff --git a/tools/include/uapi/linux/kvm.h b/tools/include/uapi/linux/kvm.h
index 9563d294f181..57a1280fa43b 100644
--- a/tools/include/uapi/linux/kvm.h
+++ b/tools/include/uapi/linux/kvm.h
@@ -1133,6 +1133,7 @@ struct kvm_ppc_resize_hpt {
 #define KVM_CAP_VM_MOVE_ENC_CONTEXT_FROM 206
 #define KVM_CAP_VM_GPA_BITS 207
 #define KVM_CAP_XSAVE2 208
+#define KVM_CAP_PMU_CONFIG 209
 
 #ifdef KVM_CAP_IRQ_ROUTING
 
@@ -1972,6 +1973,9 @@ struct kvm_dirty_gfn {
 #define KVM_BUS_LOCK_DETECTION_OFF             (1 << 0)
 #define KVM_BUS_LOCK_DETECTION_EXIT            (1 << 1)
 
+#define KVM_PMU_CONFIG_DISABLE                 (1 << 0)
+#define KVM_PMU_CONFIG_VALID                   (KVM_PMU_CONFIG_DISABLE)
+
 /**
  * struct kvm_stats_header - Header of per vm/vcpu binary statistics data.
  * @flags: Some extra information for header, always 0 for now.
-- 
2.35.0.rc0.227.g00780c9af4-goog


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v2 2/3] selftests: introduce function to create test VM without vcpus.
  2022-01-21  0:29 [PATCH v2 0/3] Provide VM capability to disable PMU virtualization for individual VMs David Dunn
  2022-01-21  0:29 ` [PATCH v2 1/3] " David Dunn
@ 2022-01-21  0:29 ` David Dunn
  2022-01-21  0:29 ` [PATCH v2 3/3] selftests: Verify disabling PMU via KVM_CAP_CONFIG_PMU David Dunn
  2 siblings, 0 replies; 5+ messages in thread
From: David Dunn @ 2022-01-21  0:29 UTC (permalink / raw)
  To: kvm, pbonzini, like.xu.linux, jmattson, cloudliang; +Cc: daviddunn

Break out portion of vm_create_with_vcpus so that selftests can modify
the VM prior to creating vcpus.

Signed-off-by: David Dunn <daviddunn@google.com>
---
 .../selftests/kvm/include/kvm_util_base.h     |  3 ++
 tools/testing/selftests/kvm/lib/kvm_util.c    | 48 ++++++++++++++-----
 2 files changed, 38 insertions(+), 13 deletions(-)

diff --git a/tools/testing/selftests/kvm/include/kvm_util_base.h b/tools/testing/selftests/kvm/include/kvm_util_base.h
index 66775de26952..0454027d588d 100644
--- a/tools/testing/selftests/kvm/include/kvm_util_base.h
+++ b/tools/testing/selftests/kvm/include/kvm_util_base.h
@@ -336,6 +336,9 @@ struct kvm_vm *vm_create_with_vcpus(enum vm_guest_mode mode, uint32_t nr_vcpus,
 				    uint32_t num_percpu_pages, void *guest_code,
 				    uint32_t vcpuids[]);
 
+/* First phase of vm_create_with_vcpus, allows customization before vcpu add */
+struct kvm_vm *vm_create_without_vcpus(enum vm_guest_mode mode, uint64_t pages);
+
 /*
  * Adds a vCPU with reasonable defaults (e.g. a stack)
  *
diff --git a/tools/testing/selftests/kvm/lib/kvm_util.c b/tools/testing/selftests/kvm/lib/kvm_util.c
index 8c53f96ab7fe..f44fd2210c66 100644
--- a/tools/testing/selftests/kvm/lib/kvm_util.c
+++ b/tools/testing/selftests/kvm/lib/kvm_util.c
@@ -362,6 +362,40 @@ struct kvm_vm *vm_create(enum vm_guest_mode mode, uint64_t phy_pages, int perm)
 	return vm;
 }
 
+/*
+ * VM Create without creating VCPUs
+ *
+ * Input Args:
+ *   mode - VM Mode (e.g. VM_MODE_P52V48_4K)
+ *   pages - pages of memory required for VM
+ *
+ * Output Args: None
+ *
+ * Return:
+ *   Pointer to opaque structure that describes the created VM.
+ *
+ * Creates a VM with the mode specified by mode (e.g. VM_MODE_P52V48_4K).
+ */
+struct kvm_vm *vm_create_without_vcpus(enum vm_guest_mode mode, uint64_t pages)
+{
+	struct kvm_vm *vm;
+
+#ifdef __x86_64__
+	/*
+	 * Permission needs to be requested before KVM_SET_CPUID2.
+	 */
+	vm_xsave_req_perm();
+#endif
+	vm = vm_create(mode, pages, O_RDWR);
+
+	kvm_vm_elf_load(vm, program_invocation_name);
+
+#ifdef __x86_64__
+	vm_create_irqchip(vm);
+#endif
+	return vm;
+}
+
 /*
  * VM Create with customized parameters
  *
@@ -393,13 +427,6 @@ struct kvm_vm *vm_create_with_vcpus(enum vm_guest_mode mode, uint32_t nr_vcpus,
 	struct kvm_vm *vm;
 	int i;
 
-#ifdef __x86_64__
-	/*
-	 * Permission needs to be requested before KVM_SET_CPUID2.
-	 */
-	vm_xsave_req_perm();
-#endif
-
 	/* Force slot0 memory size not small than DEFAULT_GUEST_PHY_PAGES */
 	if (slot0_mem_pages < DEFAULT_GUEST_PHY_PAGES)
 		slot0_mem_pages = DEFAULT_GUEST_PHY_PAGES;
@@ -419,13 +446,8 @@ struct kvm_vm *vm_create_with_vcpus(enum vm_guest_mode mode, uint32_t nr_vcpus,
 		    nr_vcpus, kvm_check_cap(KVM_CAP_MAX_VCPUS));
 
 	pages = vm_adjust_num_guest_pages(mode, pages);
-	vm = vm_create(mode, pages, O_RDWR);
 
-	kvm_vm_elf_load(vm, program_invocation_name);
-
-#ifdef __x86_64__
-	vm_create_irqchip(vm);
-#endif
+	vm = vm_create_without_vcpus(mode, pages);
 
 	for (i = 0; i < nr_vcpus; ++i) {
 		uint32_t vcpuid = vcpuids ? vcpuids[i] : i;
-- 
2.35.0.rc0.227.g00780c9af4-goog


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH v2 3/3] selftests: Verify disabling PMU via KVM_CAP_CONFIG_PMU
  2022-01-21  0:29 [PATCH v2 0/3] Provide VM capability to disable PMU virtualization for individual VMs David Dunn
  2022-01-21  0:29 ` [PATCH v2 1/3] " David Dunn
  2022-01-21  0:29 ` [PATCH v2 2/3] selftests: introduce function to create test VM without vcpus David Dunn
@ 2022-01-21  0:29 ` David Dunn
  2 siblings, 0 replies; 5+ messages in thread
From: David Dunn @ 2022-01-21  0:29 UTC (permalink / raw)
  To: kvm, pbonzini, like.xu.linux, jmattson, cloudliang; +Cc: daviddunn

On a VM with PMU disabled via KVM_CAP_PMU_CONFIG, the PMU will not be
usable by the guest.  On Intel, this causes a #GP.  And on AMD, the
counters no longer increment.

KVM_CAP_PMU_CONFIG must be invoked on a VM prior to creating VCPUs.

Signed-off-by: David Dunn <daviddunn@google.com>
---
 .../kvm/x86_64/pmu_event_filter_test.c        | 35 +++++++++++++++++++
 1 file changed, 35 insertions(+)

diff --git a/tools/testing/selftests/kvm/x86_64/pmu_event_filter_test.c b/tools/testing/selftests/kvm/x86_64/pmu_event_filter_test.c
index c715adcbd487..40fecaa4ea9f 100644
--- a/tools/testing/selftests/kvm/x86_64/pmu_event_filter_test.c
+++ b/tools/testing/selftests/kvm/x86_64/pmu_event_filter_test.c
@@ -325,6 +325,39 @@ static void test_not_member_allow_list(struct kvm_vm *vm)
 	TEST_ASSERT(!count, "Disallowed PMU Event is counting");
 }
 
+/*
+ * Verify KVM_PMU_CONFIG_DISABLE prevents the use of the PMU.
+ *
+ * Note that KVM_CAP_PMU_CONFIG must be invoked prior to creating VCPUs.
+ */
+static void test_pmu_config_disable(void (*guest_code)(void))
+{
+	int r;
+	struct kvm_vm *vm;
+	struct kvm_enable_cap cap = { 0 };
+	bool sane;
+
+	r = kvm_check_cap(KVM_CAP_PMU_CONFIG);
+	if ((r & KVM_PMU_CONFIG_DISABLE) == 0)
+		return;
+
+	vm = vm_create_without_vcpus(VM_MODE_DEFAULT, DEFAULT_GUEST_PHY_PAGES);
+
+	cap.cap = KVM_CAP_PMU_CONFIG;
+	cap.args[0] = KVM_PMU_CONFIG_DISABLE;
+	r = vm_enable_cap(vm, &cap);
+	TEST_ASSERT(r == 0, "Failed KVM_PMU_CONFIG_DISABLE.");
+
+	vm_vcpu_add_default(vm, VCPU_ID, guest_code);
+	vm_init_descriptor_tables(vm);
+	vcpu_init_descriptor_tables(vm, VCPU_ID);
+
+	sane = sanity_check_pmu(vm);
+	TEST_ASSERT(!sane, "Guest should not see PMU when disabled.");
+
+	kvm_vm_free(vm);
+}
+
 /*
  * Check for a non-zero PMU version, at least one general-purpose
  * counter per logical processor, an EBX bit vector of length greater
@@ -430,5 +463,7 @@ int main(int argc, char *argv[])
 
 	kvm_vm_free(vm);
 
+	test_pmu_config_disable(guest_code);
+
 	return 0;
 }
-- 
2.35.0.rc0.227.g00780c9af4-goog


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [PATCH v2 1/3] Provide VM capability to disable PMU virtualization for individual VMs
  2022-01-21  0:29 ` [PATCH v2 1/3] " David Dunn
@ 2022-01-21  6:59   ` Like Xu
  0 siblings, 0 replies; 5+ messages in thread
From: Like Xu @ 2022-01-21  6:59 UTC (permalink / raw)
  To: David Dunn
  Cc: kvm list,
	Paolo Bonzini - Distinguished Engineer (kernel-recipes.org),
	Jim Mattson, cloudliang(梁金荣)

Hi David,

Please modify the subject of this patch to follow the convention.

On 21/1/2022 8:29 am, David Dunn wrote:
> KVM_PMU_CONFIG_DISABLE can be used to disable PMU virtualization on

How about using:

case KVM_CAP_PMU_CAPABILITY
#define KVM_CAP_PMU_DISABLE	(1 << 0)
#define KVM_CAP_PMU_MASK (KVM_CAP_PMU_DISABLE)

> individual x86 VMs.  PMU configuration must be done prior to creating
> VCPUs.
> 
> To enable future extension, KVM_CAP_PMU_CONFIG reports available
> settings when queried via check_extension.

Please help update the document in the Documentation/virt/kvm/api.rst

> 
> Since KVM_GET_SUPPORTED_CPUID reports the maximal CPUID information
> based on module parameters, usermode will need to adjust CPUID when
> disabling PMU virtualization on individual VMs.

For an irrational user space (set both pmu cpuid bits and KVM_CAP_PMU_DISABLE),
how about we remove the relevant PMU cpuid bits in kvm_pmu_refresh() silently?

> 
> Signed-off-by: David Dunn <daviddunn@google.com>
> ---
>   arch/x86/include/asm/kvm_host.h |  1 +
>   arch/x86/kvm/svm/pmu.c          |  2 +-
>   arch/x86/kvm/vmx/pmu_intel.c    |  2 +-
>   arch/x86/kvm/x86.c              | 12 ++++++++++++
>   include/uapi/linux/kvm.h        |  4 ++++
>   tools/include/uapi/linux/kvm.h  |  4 ++++
>   6 files changed, 23 insertions(+), 2 deletions(-)
> 
> diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h
> index 682ad02a4e58..5cdcd4a7671b 100644
> --- a/arch/x86/include/asm/kvm_host.h
> +++ b/arch/x86/include/asm/kvm_host.h
> @@ -1232,6 +1232,7 @@ struct kvm_arch {
>   	hpa_t	hv_root_tdp;
>   	spinlock_t hv_root_tdp_lock;
>   #endif
> +	bool enable_pmu;
>   };
>   
>   struct kvm_vm_stat {
> diff --git a/arch/x86/kvm/svm/pmu.c b/arch/x86/kvm/svm/pmu.c
> index 5aa45f13b16d..d4de52409335 100644
> --- a/arch/x86/kvm/svm/pmu.c
> +++ b/arch/x86/kvm/svm/pmu.c
> @@ -101,7 +101,7 @@ static inline struct kvm_pmc *get_gp_pmc_amd(struct kvm_pmu *pmu, u32 msr,
>   {
>   	struct kvm_vcpu *vcpu = pmu_to_vcpu(pmu);
>   
> -	if (!enable_pmu)
> +	if (!vcpu->kvm->arch.enable_pmu)

Compared to diff in the v1:

-	if (!enable_pmu)
+	if (!enable_pmu || !vcpu->kvm->arch.enable_pmu)

Now I have come to appreciate the ingenious name.

>   		return NULL;
>   
>   	switch (msr) {
> diff --git a/arch/x86/kvm/vmx/pmu_intel.c b/arch/x86/kvm/vmx/pmu_intel.c
> index 466d18fc0c5d..2c5868d77268 100644
> --- a/arch/x86/kvm/vmx/pmu_intel.c
> +++ b/arch/x86/kvm/vmx/pmu_intel.c
> @@ -487,7 +487,7 @@ static void intel_pmu_refresh(struct kvm_vcpu *vcpu)
>   	pmu->reserved_bits = 0xffffffff00200000ull;
>   
>   	entry = kvm_find_cpuid_entry(vcpu, 0xa, 0);
> -	if (!entry || !enable_pmu)
> +	if (!entry || !vcpu->kvm->arch.enable_pmu)
>   		return;
>   	eax.full = entry->eax;
>   	edx.full = entry->edx;
> diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
> index 55518b7d3b96..42a98635bea5 100644
> --- a/arch/x86/kvm/x86.c
> +++ b/arch/x86/kvm/x86.c
> @@ -4326,6 +4326,9 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
>   		if (r < sizeof(struct kvm_xsave))
>   			r = sizeof(struct kvm_xsave);
>   		break;
> +	case KVM_CAP_PMU_CONFIG:
> +		r = enable_pmu ? KVM_PMU_CONFIG_VALID : 0;
> +		break;

diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 42a98635bea5..94481f92355d 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -4326,10 +4326,10 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
  		if (r < sizeof(struct kvm_xsave))
  			r = sizeof(struct kvm_xsave);
  		break;
+	}
  	case KVM_CAP_PMU_CONFIG:
  		r = enable_pmu ? KVM_CAP_PMU_MASK : 0;
  		break;
-	}
  	default:
  		break;
  	}

>   	}
>   	default:
>   		break;
> @@ -5937,6 +5940,14 @@ int kvm_vm_ioctl_enable_cap(struct kvm *kvm,
>   		kvm->arch.exit_on_emulation_error = cap->args[0];
>   		r = 0;
>   		break;
> +	case KVM_CAP_PMU_CONFIG:
> +		r = -EINVAL;
> +		if (!enable_pmu || kvm->created_vcpus > 0 ||
> +		    cap->args[0] & ~KVM_PMU_CONFIG_VALID)
> +			break;
> +		kvm->arch.enable_pmu = !(cap->args[0] & KVM_PMU_CONFIG_DISABLE);
> +		r = 0;
> +		break;
>   	default:
>   		r = -EINVAL;
>   		break;
> @@ -11562,6 +11573,7 @@ int kvm_arch_init_vm(struct kvm *kvm, unsigned long type)
>   	raw_spin_unlock_irqrestore(&kvm->arch.tsc_write_lock, flags);
>   
>   	kvm->arch.guest_can_read_msr_platform_info = true;
> +	kvm->arch.enable_pmu = enable_pmu;
>   
>   #if IS_ENABLED(CONFIG_HYPERV)
>   	spin_lock_init(&kvm->arch.hv_root_tdp_lock);
> diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h
> index 9563d294f181..57a1280fa43b 100644
> --- a/include/uapi/linux/kvm.h
> +++ b/include/uapi/linux/kvm.h
> @@ -1133,6 +1133,7 @@ struct kvm_ppc_resize_hpt {
>   #define KVM_CAP_VM_MOVE_ENC_CONTEXT_FROM 206
>   #define KVM_CAP_VM_GPA_BITS 207
>   #define KVM_CAP_XSAVE2 208
> +#define KVM_CAP_PMU_CONFIG 209
>   
>   #ifdef KVM_CAP_IRQ_ROUTING
>   
> @@ -1972,6 +1973,9 @@ struct kvm_dirty_gfn {
>   #define KVM_BUS_LOCK_DETECTION_OFF             (1 << 0)
>   #define KVM_BUS_LOCK_DETECTION_EXIT            (1 << 1)
>   
> +#define KVM_PMU_CONFIG_DISABLE                 (1 << 0)
> +#define KVM_PMU_CONFIG_VALID                   (KVM_PMU_CONFIG_DISABLE)
> +
>   /**
>    * struct kvm_stats_header - Header of per vm/vcpu binary statistics data.
>    * @flags: Some extra information for header, always 0 for now.
> diff --git a/tools/include/uapi/linux/kvm.h b/tools/include/uapi/linux/kvm.h
> index 9563d294f181..57a1280fa43b 100644
> --- a/tools/include/uapi/linux/kvm.h
> +++ b/tools/include/uapi/linux/kvm.h
> @@ -1133,6 +1133,7 @@ struct kvm_ppc_resize_hpt {
>   #define KVM_CAP_VM_MOVE_ENC_CONTEXT_FROM 206
>   #define KVM_CAP_VM_GPA_BITS 207
>   #define KVM_CAP_XSAVE2 208
> +#define KVM_CAP_PMU_CONFIG 209
>   
>   #ifdef KVM_CAP_IRQ_ROUTING
>   
> @@ -1972,6 +1973,9 @@ struct kvm_dirty_gfn {
>   #define KVM_BUS_LOCK_DETECTION_OFF             (1 << 0)
>   #define KVM_BUS_LOCK_DETECTION_EXIT            (1 << 1)
>   
> +#define KVM_PMU_CONFIG_DISABLE                 (1 << 0)
> +#define KVM_PMU_CONFIG_VALID                   (KVM_PMU_CONFIG_DISABLE)
> +
>   /**
>    * struct kvm_stats_header - Header of per vm/vcpu binary statistics data.
>    * @flags: Some extra information for header, always 0 for now.

^ permalink raw reply related	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2022-01-21  6:59 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-01-21  0:29 [PATCH v2 0/3] Provide VM capability to disable PMU virtualization for individual VMs David Dunn
2022-01-21  0:29 ` [PATCH v2 1/3] " David Dunn
2022-01-21  6:59   ` Like Xu
2022-01-21  0:29 ` [PATCH v2 2/3] selftests: introduce function to create test VM without vcpus David Dunn
2022-01-21  0:29 ` [PATCH v2 3/3] selftests: Verify disabling PMU via KVM_CAP_CONFIG_PMU David Dunn

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.