Re: [PATCH v2 14/16] KVM: x86/pmu: Ignore AnyThread bit if CPUID.0AH:EDX[15] is set

From: Mi, Dapeng

Date: Tue Sep 01 2026 - 04:04:11 EST


Reviewed-by: Dapeng Mi <dapeng1.mi@xxxxxxxxxxxxxxx>


On 8/28/2026 6:37 AM, Zide Chen wrote:
> Intel PerfMon v5 introduces the ANYTHREAD_DEPRECATION capability
> (CPUID.0AH:EDX[15]) to indicate that AnyThread counting is deprecated
> and that writes to the AnyThread bit in IA32_PERFEVTSELx are ignored.
>
> When ANYTHREAD_DEPRECATION is present in the guest CPUID, emulate the
> architectural behavior and silently ignore writes to the AnyThread bit
> instead of injecting #GP.
>
> Continue to inject #GP when ANYTHREAD_DEPRECATION is not present in the
> guest CPUID, e.g. for PerfMon v3/v4 guests or when the capability is
> not configured for a PerfMon v5+ guest.
>
> Advertise CPUID.0AH:EDX[15] only for PMU version 5+ guests, since the
> bit doesn't exist below version 5.
>
> Signed-off-by: Zide Chen <zide.chen@xxxxxxxxx>
> ---
> v2:
> - Advertise anythread_deprecated only if kvm_pmu_cap.version >= 5.
> - Add the missing AnyThr bit handling for IA32_FIXED_CTR_CTRL.
> - Update the comments to be clearer.
> ---
> arch/x86/kvm/cpuid.c | 2 +-
> arch/x86/kvm/vmx/pmu_intel.c | 19 +++++++++++++++++++
> 2 files changed, 20 insertions(+), 1 deletion(-)
>
> diff --git a/arch/x86/kvm/cpuid.c b/arch/x86/kvm/cpuid.c
> index 63201d4ea4a1..ef208906b3ee 100644
> --- a/arch/x86/kvm/cpuid.c
> +++ b/arch/x86/kvm/cpuid.c
> @@ -1542,7 +1542,7 @@ static inline int __do_cpuid_func(struct kvm_cpuid_array *array, u32 function)
> KVM_MAX_NR_FIXED_COUNTERS);
> edx.split.bit_width_fixed = kvm_pmu_cap.bit_width_fixed;
>
> - if (kvm_pmu_cap.version)
> + if (kvm_pmu_cap.version >= 5)
> edx.split.anythread_deprecated = 1;
>
> entry->eax = eax.full;
> diff --git a/arch/x86/kvm/vmx/pmu_intel.c b/arch/x86/kvm/vmx/pmu_intel.c
> index c7472778137a..599c69dfa6e3 100644
> --- a/arch/x86/kvm/vmx/pmu_intel.c
> +++ b/arch/x86/kvm/vmx/pmu_intel.c
> @@ -446,6 +446,12 @@ static int intel_pmu_set_msr(struct kvm_vcpu *vcpu, struct msr_data *msr_info)
> if (data & pmu->fixed_ctr_ctrl_rsvd)
> return 1;
>
> + /*
> + * This is to emulate ANYTHREAD_DEPRECATION. Guests without
> + * support for it would have had the write rejected by
> + * pmu->fixed_ctr_ctrl_rsvd above.
> + */
> + data &= ~intel_pmu_fixed_ctrl_bits(pmu, INTEL_FIXED_0_ANYTHREAD);
> if (pmu->fixed_ctr_ctrl != data)
> reprogram_fixed_counters(pmu, data);
> break;
> @@ -494,6 +500,8 @@ static int intel_pmu_set_msr(struct kvm_vcpu *vcpu, struct msr_data *msr_info)
> if (data & eventsel_rsvd)
> return 1;
>
> + /* See above comments for MSR_CORE_PERF_FIXED_CTR_CTRL. */
> + data &= ~ARCH_PERFMON_EVENTSEL_ANY;
> if (data != pmc->eventsel) {
> pmc->eventsel = data;
> pmc->eventsel_hw = data;
> @@ -603,6 +611,17 @@ static void intel_pmu_refresh(struct kvm_vcpu *vcpu)
> pmu->pmc_exists64 = (BIT_ULL(nr_gp_counters) - 1) &
> kvm_pmu_cap.cntr_mask64;
>
> + /*
> + * AnyThread counting is not supported by KVM due to cross-VM
> + * information leakage concerns on SMT cores. Therefore, AnyThread
> + * remains unavailable for PerfMon v3/v4 guests, where AnyThread
> + * deprecation is not enumerated.
> + */
> + if (pmu->version >= 5 && edx.split.anythread_deprecated) {
> + pmu->eventsel_rsvd &= ~ARCH_PERFMON_EVENTSEL_ANY;
> + fixed_enable_bits |= INTEL_FIXED_0_ANYTHREAD;
> + }
> +
> entry = kvm_find_cpuid_entry_index(vcpu, 7, 0);
> if (entry &&
> (boot_cpu_has(X86_FEATURE_HLE) || boot_cpu_has(X86_FEATURE_RTM)) &&