| .. | .. |
|---|
| 7 | 7 | |
|---|
| 8 | 8 | #ifndef __ASSEMBLY__ |
|---|
| 9 | 9 | |
|---|
| 10 | +#include <asm/barrier.h> |
|---|
| 10 | 11 | #include <asm/unistd.h> |
|---|
| 11 | 12 | #include <asm/errno.h> |
|---|
| 12 | 13 | |
|---|
| 13 | 14 | #include <asm/vdso/compat_barrier.h> |
|---|
| 14 | 15 | |
|---|
| 15 | | -#define __VDSO_USE_SYSCALL ULLONG_MAX |
|---|
| 16 | | - |
|---|
| 17 | 16 | #define VDSO_HAS_CLOCK_GETRES 1 |
|---|
| 18 | | - |
|---|
| 19 | | -#define VDSO_HAS_TIME 1 |
|---|
| 20 | 17 | |
|---|
| 21 | 18 | #define BUILD_VDSO32 1 |
|---|
| 22 | 19 | |
|---|
| .. | .. |
|---|
| 44 | 41 | register struct __kernel_timespec *ts asm("r1") = _ts; |
|---|
| 45 | 42 | register clockid_t clkid asm("r0") = _clkid; |
|---|
| 46 | 43 | register long ret asm ("r0"); |
|---|
| 44 | + register long nr asm("r7") = __NR_compat_clock_gettime64; |
|---|
| 45 | + |
|---|
| 46 | + asm volatile( |
|---|
| 47 | + " swi #0\n" |
|---|
| 48 | + : "=r" (ret) |
|---|
| 49 | + : "r" (clkid), "r" (ts), "r" (nr) |
|---|
| 50 | + : "memory"); |
|---|
| 51 | + |
|---|
| 52 | + return ret; |
|---|
| 53 | +} |
|---|
| 54 | + |
|---|
| 55 | +static __always_inline |
|---|
| 56 | +long clock_gettime32_fallback(clockid_t _clkid, struct old_timespec32 *_ts) |
|---|
| 57 | +{ |
|---|
| 58 | + register struct old_timespec32 *ts asm("r1") = _ts; |
|---|
| 59 | + register clockid_t clkid asm("r0") = _clkid; |
|---|
| 60 | + register long ret asm ("r0"); |
|---|
| 47 | 61 | register long nr asm("r7") = __NR_compat_clock_gettime; |
|---|
| 48 | 62 | |
|---|
| 49 | 63 | asm volatile( |
|---|
| .. | .. |
|---|
| 61 | 75 | register struct __kernel_timespec *ts asm("r1") = _ts; |
|---|
| 62 | 76 | register clockid_t clkid asm("r0") = _clkid; |
|---|
| 63 | 77 | register long ret asm ("r0"); |
|---|
| 78 | + register long nr asm("r7") = __NR_compat_clock_getres_time64; |
|---|
| 79 | + |
|---|
| 80 | + asm volatile( |
|---|
| 81 | + " swi #0\n" |
|---|
| 82 | + : "=r" (ret) |
|---|
| 83 | + : "r" (clkid), "r" (ts), "r" (nr) |
|---|
| 84 | + : "memory"); |
|---|
| 85 | + |
|---|
| 86 | + return ret; |
|---|
| 87 | +} |
|---|
| 88 | + |
|---|
| 89 | +static __always_inline |
|---|
| 90 | +int clock_getres32_fallback(clockid_t _clkid, struct old_timespec32 *_ts) |
|---|
| 91 | +{ |
|---|
| 92 | + register struct old_timespec32 *ts asm("r1") = _ts; |
|---|
| 93 | + register clockid_t clkid asm("r0") = _clkid; |
|---|
| 94 | + register long ret asm ("r0"); |
|---|
| 64 | 95 | register long nr asm("r7") = __NR_compat_clock_getres; |
|---|
| 65 | 96 | |
|---|
| 66 | 97 | asm volatile( |
|---|
| .. | .. |
|---|
| 72 | 103 | return ret; |
|---|
| 73 | 104 | } |
|---|
| 74 | 105 | |
|---|
| 75 | | -static __always_inline u64 __arch_get_hw_counter(s32 clock_mode) |
|---|
| 106 | +static __always_inline u64 __arch_get_hw_counter(s32 clock_mode, |
|---|
| 107 | + const struct vdso_data *vd) |
|---|
| 76 | 108 | { |
|---|
| 77 | 109 | u64 res; |
|---|
| 78 | 110 | |
|---|
| 79 | 111 | /* |
|---|
| 80 | | - * clock_mode == 0 implies that vDSO are enabled otherwise |
|---|
| 81 | | - * fallback on syscall. |
|---|
| 112 | + * Core checks for mode already, so this raced against a concurrent |
|---|
| 113 | + * update. Return something. Core will do another round and then |
|---|
| 114 | + * see the mode change and fallback to the syscall. |
|---|
| 82 | 115 | */ |
|---|
| 83 | | - if (clock_mode) |
|---|
| 84 | | - return __VDSO_USE_SYSCALL; |
|---|
| 116 | + if (clock_mode != VDSO_CLOCKMODE_ARCHTIMER) |
|---|
| 117 | + return 0; |
|---|
| 85 | 118 | |
|---|
| 86 | 119 | /* |
|---|
| 87 | 120 | * This isb() is required to prevent that the counter value |
|---|
| .. | .. |
|---|
| 121 | 154 | return ret; |
|---|
| 122 | 155 | } |
|---|
| 123 | 156 | |
|---|
| 157 | +#ifdef CONFIG_TIME_NS |
|---|
| 158 | +static __always_inline const struct vdso_data *__arch_get_timens_vdso_data(void) |
|---|
| 159 | +{ |
|---|
| 160 | + const struct vdso_data *ret; |
|---|
| 161 | + |
|---|
| 162 | + /* See __arch_get_vdso_data(). */ |
|---|
| 163 | + asm volatile("mov %0, %1" : "=r"(ret) : "r"(_timens_data)); |
|---|
| 164 | + |
|---|
| 165 | + return ret; |
|---|
| 166 | +} |
|---|
| 167 | +#endif |
|---|
| 168 | + |
|---|
| 169 | +static inline bool vdso_clocksource_ok(const struct vdso_data *vd) |
|---|
| 170 | +{ |
|---|
| 171 | + return vd->clock_mode == VDSO_CLOCKMODE_ARCHTIMER; |
|---|
| 172 | +} |
|---|
| 173 | +#define vdso_clocksource_ok vdso_clocksource_ok |
|---|
| 174 | + |
|---|
| 124 | 175 | #endif /* !__ASSEMBLY__ */ |
|---|
| 125 | 176 | |
|---|
| 126 | 177 | #endif /* __ASM_VDSO_GETTIMEOFDAY_H */ |
|---|