From: Mingwei Zhang Cache the unadulterated snapshot of perf_capabilities so that KVM can compare guest vPMU capabilities against raw hardware capabilities. For example, if the host supports PERF_METRICS but it is not configured for the guest, KVM can use it to determine that RDPMC accesses must be intercepted. Signed-off-by: Mingwei Zhang Signed-off-by: Zide Chen Reviewed-by: Dapeng Mi Reviewed-by: Jim Mattson --- v5: new patch. --- arch/x86/include/asm/kvm_host.h | 1 + arch/x86/kvm/vmx/vmx.c | 8 ++------ arch/x86/kvm/x86.c | 4 ++++ 3 files changed, 7 insertions(+), 6 deletions(-) diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h index 8a4e542218a7..d893fa5be838 100644 --- a/arch/x86/include/asm/kvm_host.h +++ b/arch/x86/include/asm/kvm_host.h @@ -294,6 +294,7 @@ struct kvm_host_values { u64 xss; u64 s_cet; u64 arch_capabilities; + u64 perf_capabilities; }; extern struct kvm_host_values kvm_host; diff --git a/arch/x86/kvm/vmx/vmx.c b/arch/x86/kvm/vmx/vmx.c index e3bfe6aca1a0..6e9d197982b7 100644 --- a/arch/x86/kvm/vmx/vmx.c +++ b/arch/x86/kvm/vmx/vmx.c @@ -8023,14 +8023,10 @@ void vmx_vcpu_after_set_cpuid(struct kvm_vcpu *vcpu) static __init u64 vmx_get_perf_capabilities(void) { u64 perf_cap = PERF_CAP_FW_WRITES; - u64 host_perf_cap = 0; if (!enable_pmu) return 0; - if (boot_cpu_has(X86_FEATURE_PDCM)) - rdmsrq(MSR_IA32_PERF_CAPABILITIES, host_perf_cap); - if (!cpu_feature_enabled(X86_FEATURE_ARCH_LBR) && !enable_mediated_pmu) { x86_perf_get_lbr(&vmx_lbr_caps); @@ -8043,11 +8039,11 @@ static __init u64 vmx_get_perf_capabilities(void) if (!vmx_lbr_caps.has_callstack) memset(&vmx_lbr_caps, 0, sizeof(vmx_lbr_caps)); else if (vmx_lbr_caps.nr) - perf_cap |= host_perf_cap & PERF_CAP_LBR_FMT; + perf_cap |= kvm_host.perf_capabilities & PERF_CAP_LBR_FMT; } if (vmx_pebs_supported()) { - perf_cap |= host_perf_cap & PERF_CAP_PEBS_MASK; + perf_cap |= kvm_host.perf_capabilities & PERF_CAP_PEBS_MASK; /* * Disallow adaptive PEBS as it is functionally broken, can be diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index d94b59140c45..d349224d2734 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -7083,6 +7083,10 @@ int kvm_x86_vendor_init(struct kvm_x86_init_ops *ops) if (boot_cpu_has(X86_FEATURE_ARCH_CAPABILITIES)) rdmsrq(MSR_IA32_ARCH_CAPABILITIES, kvm_host.arch_capabilities); + if (boot_cpu_has(X86_FEATURE_PDCM)) + rdmsrq_safe(MSR_IA32_PERF_CAPABILITIES, + &kvm_host.perf_capabilities); + WARN_ON_ONCE(kvm_nr_uret_msrs); r = ops->hardware_setup(); -- 2.55.0