[PATCH 00/11] KVM: arm64: Add NV timer support

Marc Zyngier
2024-12-02T17:22:18Z

Here's another batch of NV-related patches, this time bringing in most
of the timer support for EL2 as well as nested guests.

The code is pretty convoluted for a bunch of reasons:

- FEAT_NV2 breaks the timer semantics by redirecting HW controls to
memory, meaning that a guest could setup a timer and never see it
firing until the next exit

- We go try hard to reflect the timer state in memory, but that's not
great.

- With FEAT_ECV, we can finally correctly emulate the virtual timer,
but this emulation is pretty costly

- As a way to make things suck less, we handle timer reads as early as
possible, and only defer writes to the normal trap handling

- Finally, some implementations are badly broken, and require some
hand-holding, irrespective of NV support. So we try and reuse the NV
infrastructure to make them usable. This could be further optimised,
but I'm running out of patience for this sort of HW.

What this is not implementing is support for CNTPOFF_EL2. It appears
that the architecture doesn't let you correctly emulate it, so I guess
this will be trap/emulate for the foreseeable future.

This series is on top of v6.13-rc1, and has been tested on my usual M2
setup, but also on a Snapdragon X1 Elite devkit. I would like to thank
Qualcomm for the free hardware with no strings (nor support) attached!

If you are feeling brave, you can run the whole thing from [1].

[1] https://git.kernel.org/pub/scm/linux/kernel/git/maz/arm-platforms.git/log/?h=kvm-arm64/nv-next

Marc Zyngier (11):
KVM: arm64: nv: Add handling of EL2-specific timer registers
KVM: arm64: nv: Sync nested timer state with FEAT_NV2
KVM: arm64: nv: Publish emulated timer interrupt state in the
in-memory state
KVM: arm64: nv: Use FEAT_ECV to trap access to EL0 timers
KVM: arm64: nv: Accelerate EL0 timer read accesses when FEAT_ECV in
use
KVM: arm64: nv: Acceletate EL0 counter accesses from hypervisor
context
KVM: arm64: Handle counter access early in non-HYP context
KVM: arm64: nv: Add trap routing for
CNTHCTL_EL2.EL1{NVPCT,NVVCT,TVT,TVCT}
KVM: arm64: nv: Propagate CNTHCTL_EL2.EL1NV{P,V}CT bits
KVM: arm64: nv: Sanitise CNTHCTL_EL2
KVM: arm64: Work around x1e's CNTVOFF_EL2 bogosity

arch/arm64/include/asm/cputype.h | 2 +
arch/arm64/include/asm/kvm_host.h | 2 +-
arch/arm64/include/asm/sysreg.h | 4 +
arch/arm64/kernel/cpu_errata.c | 8 ++
arch/arm64/kernel/image-vars.h | 3 +
arch/arm64/kvm/arch_timer.c | 177 +++++++++++++++++++++---
arch/arm64/kvm/arm.c | 3 +
arch/arm64/kvm/emulate-nested.c | 58 +++++++-
arch/arm64/kvm/hyp/include/hyp/switch.h | 39 ++++--
arch/arm64/kvm/hyp/nvhe/timer-sr.c | 16 ++-
arch/arm64/kvm/hyp/vhe/switch.c | 84 +++++++++++
arch/arm64/kvm/nested.c | 15 ++
arch/arm64/kvm/sys_regs.c | 146 ++++++++++++++++++-
arch/arm64/tools/cpucaps | 1 +
include/clocksource/arm_arch_timer.h | 6 +
include/kvm/arm_arch_timer.h | 23 +++
16 files changed, 546 insertions(+), 41 deletions(-)

--
2.39.2