From: George Anzinger Date: Mon, 14 Nov 2005 00:07:44 +0000 (-0800) Subject: [PATCH] timespec: normalize off by one errors X-Git-Tag: v2.6.15-rc2~144 X-Git-Url: https://err.no/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=3f39894d1b5c253b10fcb8fbbbcf65a330f6cdc7;p=linux-2.6 [PATCH] timespec: normalize off by one errors It would appear that the timespec normalize code has an off by one error. Found in three places. Thanks to Ben for spotting. Signed-off-by: George Anzinger Cc: Benjamin Herrenschmidt Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- diff --git a/include/linux/time.h b/include/linux/time.h index 8e83f4e778..bfbe92d076 100644 --- a/include/linux/time.h +++ b/include/linux/time.h @@ -101,7 +101,7 @@ extern struct timespec timespec_trunc(struct timespec t, unsigned gran); static inline void set_normalized_timespec (struct timespec *ts, time_t sec, long nsec) { - while (nsec > NSEC_PER_SEC) { + while (nsec >= NSEC_PER_SEC) { nsec -= NSEC_PER_SEC; ++sec; } diff --git a/kernel/posix-timers.c b/kernel/posix-timers.c index ea55c7a1cd..5870efb3e2 100644 --- a/kernel/posix-timers.c +++ b/kernel/posix-timers.c @@ -270,7 +270,7 @@ static void tstojiffie(struct timespec *tp, int res, u64 *jiff) long sec = tp->tv_sec; long nsec = tp->tv_nsec + res - 1; - if (nsec > NSEC_PER_SEC) { + if (nsec >= NSEC_PER_SEC) { sec++; nsec -= NSEC_PER_SEC; } @@ -1209,13 +1209,9 @@ static int do_posix_clock_monotonic_get(clockid_t clock, struct timespec *tp) do_posix_clock_monotonic_gettime_parts(tp, &wall_to_mono); - tp->tv_sec += wall_to_mono.tv_sec; - tp->tv_nsec += wall_to_mono.tv_nsec; + set_normalized_timespec(tp, tp->tv_sec + wall_to_mono.tv_sec, + tp->tv_nsec + wall_to_mono.tv_nsec); - if ((tp->tv_nsec - NSEC_PER_SEC) > 0) { - tp->tv_nsec -= NSEC_PER_SEC; - tp->tv_sec++; - } return 0; }