| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182 |
- /* SPDX-License-Identifier: GPL-2.0 */
- /*
- * ARM Generic Timer specific interface
- */
- #ifndef SELFTEST_KVM_ARCH_TIMER_H
- #define SELFTEST_KVM_ARCH_TIMER_H
- #include "processor.h"
- enum arch_timer {
- VIRTUAL,
- PHYSICAL,
- };
- #define CTL_ENABLE (1 << 0)
- #define CTL_IMASK (1 << 1)
- #define CTL_ISTATUS (1 << 2)
- #define msec_to_cycles(msec) \
- (timer_get_cntfrq() * (uint64_t)(msec) / 1000)
- #define usec_to_cycles(usec) \
- (timer_get_cntfrq() * (uint64_t)(usec) / 1000000)
- #define cycles_to_usec(cycles) \
- ((uint64_t)(cycles) * 1000000 / timer_get_cntfrq())
- static inline uint32_t timer_get_cntfrq(void)
- {
- return read_sysreg(cntfrq_el0);
- }
- static inline uint64_t timer_get_cntct(enum arch_timer timer)
- {
- isb();
- switch (timer) {
- case VIRTUAL:
- return read_sysreg(cntvct_el0);
- case PHYSICAL:
- return read_sysreg(cntpct_el0);
- default:
- GUEST_FAIL("Unexpected timer type = %u", timer);
- }
- /* We should not reach here */
- return 0;
- }
- static inline void timer_set_cval(enum arch_timer timer, uint64_t cval)
- {
- switch (timer) {
- case VIRTUAL:
- write_sysreg(cval, cntv_cval_el0);
- break;
- case PHYSICAL:
- write_sysreg(cval, cntp_cval_el0);
- break;
- default:
- GUEST_FAIL("Unexpected timer type = %u", timer);
- }
- isb();
- }
- static inline uint64_t timer_get_cval(enum arch_timer timer)
- {
- switch (timer) {
- case VIRTUAL:
- return read_sysreg(cntv_cval_el0);
- case PHYSICAL:
- return read_sysreg(cntp_cval_el0);
- default:
- GUEST_FAIL("Unexpected timer type = %u", timer);
- }
- /* We should not reach here */
- return 0;
- }
- static inline void timer_set_tval(enum arch_timer timer, int32_t tval)
- {
- switch (timer) {
- case VIRTUAL:
- write_sysreg(tval, cntv_tval_el0);
- break;
- case PHYSICAL:
- write_sysreg(tval, cntp_tval_el0);
- break;
- default:
- GUEST_FAIL("Unexpected timer type = %u", timer);
- }
- isb();
- }
- static inline int32_t timer_get_tval(enum arch_timer timer)
- {
- isb();
- switch (timer) {
- case VIRTUAL:
- return read_sysreg(cntv_tval_el0);
- case PHYSICAL:
- return read_sysreg(cntp_tval_el0);
- default:
- GUEST_FAIL("Could not get timer %d\n", timer);
- }
- /* We should not reach here */
- return 0;
- }
- static inline void timer_set_ctl(enum arch_timer timer, uint32_t ctl)
- {
- switch (timer) {
- case VIRTUAL:
- write_sysreg(ctl, cntv_ctl_el0);
- break;
- case PHYSICAL:
- write_sysreg(ctl, cntp_ctl_el0);
- break;
- default:
- GUEST_FAIL("Unexpected timer type = %u", timer);
- }
- isb();
- }
- static inline uint32_t timer_get_ctl(enum arch_timer timer)
- {
- switch (timer) {
- case VIRTUAL:
- return read_sysreg(cntv_ctl_el0);
- case PHYSICAL:
- return read_sysreg(cntp_ctl_el0);
- default:
- GUEST_FAIL("Unexpected timer type = %u", timer);
- }
- /* We should not reach here */
- return 0;
- }
- static inline void timer_set_next_cval_ms(enum arch_timer timer, uint32_t msec)
- {
- uint64_t now_ct = timer_get_cntct(timer);
- uint64_t next_ct = now_ct + msec_to_cycles(msec);
- timer_set_cval(timer, next_ct);
- }
- static inline void timer_set_next_tval_ms(enum arch_timer timer, uint32_t msec)
- {
- timer_set_tval(timer, msec_to_cycles(msec));
- }
- static inline u32 vcpu_get_vtimer_irq(struct kvm_vcpu *vcpu)
- {
- u32 intid;
- u64 attr;
- attr = vcpu_has_el2(vcpu) ? KVM_ARM_VCPU_TIMER_IRQ_HVTIMER :
- KVM_ARM_VCPU_TIMER_IRQ_VTIMER;
- vcpu_device_attr_get(vcpu, KVM_ARM_VCPU_TIMER_CTRL, attr, &intid);
- return intid;
- }
- static inline u32 vcpu_get_ptimer_irq(struct kvm_vcpu *vcpu)
- {
- u32 intid;
- u64 attr;
- attr = vcpu_has_el2(vcpu) ? KVM_ARM_VCPU_TIMER_IRQ_HPTIMER :
- KVM_ARM_VCPU_TIMER_IRQ_PTIMER;
- vcpu_device_attr_get(vcpu, KVM_ARM_VCPU_TIMER_CTRL, attr, &intid);
- return intid;
- }
- #endif /* SELFTEST_KVM_ARCH_TIMER_H */
|