[PATCH v3 15/18] KVM: x86/pmu: Mask only OS/USR bits when filtering fixed counters

From: Zide Chen

Date: Thu Nov 05 2026 - 20:57:54 EST


In preparation for supporting AnyThread deprecation and Fixed Counter 3,
mask only INTEL_FIXED_0_KERNEL and INTEL_FIXED_0_USER when updating
fixed_ctr_ctrl_hw in kvm_mediated_pmu_refresh_event_filter().

Masking the full 0xf nibble would cause two issues:

1. AnyThread for Fixed Counters 0-2: When a counter is allowed, copying
the full nibble from guest-visible pmu->fixed_ctr_ctrl back into
hardware-visible pmu->fixed_ctr_ctrl_hw would resurrect AnyThread in
hardware, defeating SMT cross-VM isolation.

2. Metrics Clear for Fixed Counter 3: If an event filter denies Fixed
Counter 3, clearing 0xf inadvertently strips METRICS_CLEAR_EN from
hardware. If the guest sets METRICS_CLEAR_EN and executes native RDPMC,
metrics will remain un-cleared, returning stale data.

This gates hardware counting without clobbering other control bits,
matching general-purpose counter filtering which only masks the event
ENABLE bit.

Signed-off-by: Zide Chen <zide.chen@xxxxxxxxx>
---
v3:
- New patch.
---
arch/x86/kvm/pmu.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/arch/x86/kvm/pmu.c b/arch/x86/kvm/pmu.c
index 2cb5bccc7044..afb3e18a9879 100644
--- a/arch/x86/kvm/pmu.c
+++ b/arch/x86/kvm/pmu.c
@@ -557,7 +557,9 @@ static void kvm_mediated_pmu_refresh_event_filter(struct kvm_pmc *pmc)
pmc->eventsel_hw |= pmc->eventsel &
ARCH_PERFMON_EVENTSEL_ENABLE;
} else {
- u64 mask = intel_fixed_bits_by_idx(pmc->idx - KVM_FIXED_PMC_BASE_IDX, 0xf);
+ u64 mask = intel_fixed_bits_by_idx(pmc->idx - KVM_FIXED_PMC_BASE_IDX,
+ INTEL_FIXED_0_KERNEL |
+ INTEL_FIXED_0_USER);

pmu->fixed_ctr_ctrl_hw &= ~mask;
if (allowed)
--
2.56.0