[RFC/PATCH] ARM: vDSO gettimeofday using generic timer architecture
Nathan Lynch
Nathan_Lynch at mentor.com
Tue Jan 28 16:48:43 EST 2014
On 01/28/2014 03:22 PM, Russell King - ARM Linux wrote:
> On Tue, Jan 28, 2014 at 03:06:53PM -0600, Nathan Lynch wrote:
>> +static union {
>> + struct vdso_data data;
>> + u8 page[PAGE_SIZE];
>> +} vdso_data_store __page_aligned_data;
>> +struct vdso_data *vdso_data = &vdso_data_store.data;
>
> So this is in the kernel data segment.
>
>> +void update_vsyscall(struct timekeeper *tk)
>> +{
>> + struct timespec xtime_coarse;
>> + struct timespec wall_time = tk_xtime(tk);
>> + struct timespec *wtm = &tk->wall_to_monotonic;
>> + u32 use_syscall = strcmp(tk->clock->name, "arch_sys_counter");
>> +
>> + ++vdso_data->tb_seq_count;
>> + smp_wmb();
>> +
>> + xtime_coarse = __current_kernel_time();
>> + vdso_data->use_syscall = use_syscall;
>> + vdso_data->xtime_coarse_sec = xtime_coarse.tv_sec;
>> + vdso_data->xtime_coarse_nsec = xtime_coarse.tv_nsec;
>> +
>> + if (!use_syscall) {
>> + vdso_data->cs_cycle_last = tk->clock->cycle_last;
>> + vdso_data->xtime_clock_sec = wall_time.tv_sec;
>> + vdso_data->xtime_clock_nsec = wall_time.tv_nsec;
>> + vdso_data->cs_mult = tk->mult;
>> + vdso_data->cs_shift = tk->shift;
>> + vdso_data->wtm_clock_sec = wtm->tv_sec;
>> + vdso_data->wtm_clock_nsec = wtm->tv_nsec;
>> + }
>> +
>> + smp_wmb();
>> + ++vdso_data->tb_seq_count;
>> +}
>> +
>> +void update_vsyscall_tz(void)
>> +{
>> + vdso_data->tz_minuteswest = sys_tz.tz_minuteswest;
>> + vdso_data->tz_dsttime = sys_tz.tz_dsttime;
>> +}
>
> which gets written to directly, and read from userspace. This won't work
> with aliasing caches, of which we have VIVT caches on all ARMv4 and ARMv5
> CPUs, and VIPT caches on some ARMv6.
>
> Either this needs to be limited to just VIPT nonaliasing caches, or it
> needs cache handling.
Thanks, I will address this.
>
> The above also looks rather unsafe from the SMP perspective - how does
> vdso_data->tb_seq_count protect this data between CPUs?
It doesn't -- it merely provides a mechanism for signaling the
consistency of the data userspace reads from the page. It's basically a
seqlock.
Looks like timekeeper_lock in kernel/time/timekeeping.c prevents
concurrent calls to update_vsyscall. I could document that dependency...
More information about the linux-arm-kernel
mailing list