Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

vdso/treewide: Add vdso_data pointer argument to __arch_get_hw_counter()

MIPS already uses and S390 will need the vdso data pointer in
__arch_get_hw_counter().

This works nicely as long as the architecture does not support time
namespaces in the VDSO. With time namespaces enabled the regular
accessor to the vdso data pointer __arch_get_vdso_data() will return the
namespace specific VDSO data page for tasks which are part of a
non-root time namespace. This would cause the architectures which need
the vdso data pointer in __arch_get_hw_counter() to access the wrong
vdso data page.

Add a vdso_data pointer argument to __arch_get_hw_counter() and hand it in
from the call sites in the core code. For architectures which do not need
the data pointer in their counter accessor function the compiler will just
optimize it out.

Fix up all existing architecture implementations and make MIPS utilize the
pointer instead of invoking the accessor function.

No functional change and no change in the resulting object code (except
MIPS).

Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Link: https://lkml.kernel.org/r/draft-87wo2ekuzn.fsf@nanos.tec.linutronix.de

+15 -9
+2 -1
arch/arm/include/asm/vdso/gettimeofday.h
··· 113 113 } 114 114 #define __arch_vdso_hres_capable arm_vdso_hres_capable 115 115 116 - static __always_inline u64 __arch_get_hw_counter(int clock_mode) 116 + static __always_inline u64 __arch_get_hw_counter(int clock_mode, 117 + const struct vdso_data *vd) 117 118 { 118 119 #ifdef CONFIG_ARM_ARCH_TIMER 119 120 u64 cycle_now;
+2 -1
arch/arm64/include/asm/vdso/compat_gettimeofday.h
··· 103 103 return ret; 104 104 } 105 105 106 - 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) 107 108 { 108 109 u64 res; 109 110
+2 -1
arch/arm64/include/asm/vdso/gettimeofday.h
··· 64 64 return ret; 65 65 } 66 66 67 - static __always_inline u64 __arch_get_hw_counter(s32 clock_mode) 67 + static __always_inline u64 __arch_get_hw_counter(s32 clock_mode, 68 + const struct vdso_data *vd) 68 69 { 69 70 u64 res; 70 71
+3 -2
arch/mips/include/asm/vdso/gettimeofday.h
··· 167 167 168 168 #endif 169 169 170 - static __always_inline u64 __arch_get_hw_counter(s32 clock_mode) 170 + static __always_inline u64 __arch_get_hw_counter(s32 clock_mode, 171 + const struct vdso_data *vd) 171 172 { 172 173 #ifdef CONFIG_CSRC_R4K 173 174 if (clock_mode == VDSO_CLOCKMODE_R4K) ··· 176 175 #endif 177 176 #ifdef CONFIG_CLKSRC_MIPS_GIC 178 177 if (clock_mode == VDSO_CLOCKMODE_GIC) 179 - return read_gic_count(get_vdso_data()); 178 + return read_gic_count(vd); 180 179 #endif 181 180 /* 182 181 * Core checks mode already. So this raced against a concurrent
+2 -1
arch/riscv/include/asm/vdso/gettimeofday.h
··· 60 60 return ret; 61 61 } 62 62 63 - static __always_inline u64 __arch_get_hw_counter(s32 clock_mode) 63 + static __always_inline u64 __arch_get_hw_counter(s32 clock_mode, 64 + const struct vdso_data *vd) 64 65 { 65 66 /* 66 67 * The purpose of csr_read(CSR_TIME) is to trap the system into
+2 -1
arch/x86/include/asm/vdso/gettimeofday.h
··· 241 241 } 242 242 #endif 243 243 244 - static inline u64 __arch_get_hw_counter(s32 clock_mode) 244 + static inline u64 __arch_get_hw_counter(s32 clock_mode, 245 + const struct vdso_data *vd) 245 246 { 246 247 if (likely(clock_mode == VDSO_CLOCKMODE_TSC)) 247 248 return (u64)rdtsc_ordered();
+2 -2
lib/vdso/gettimeofday.c
··· 68 68 if (unlikely(!vdso_clocksource_ok(vd))) 69 69 return -1; 70 70 71 - cycles = __arch_get_hw_counter(vd->clock_mode); 71 + cycles = __arch_get_hw_counter(vd->clock_mode, vd); 72 72 if (unlikely(!vdso_cycles_ok(cycles))) 73 73 return -1; 74 74 ns = vdso_ts->nsec; ··· 138 138 if (unlikely(!vdso_clocksource_ok(vd))) 139 139 return -1; 140 140 141 - cycles = __arch_get_hw_counter(vd->clock_mode); 141 + cycles = __arch_get_hw_counter(vd->clock_mode, vd); 142 142 if (unlikely(!vdso_cycles_ok(cycles))) 143 143 return -1; 144 144 ns = vdso_ts->nsec;