diff options
author | Xunlei Pang <pang.xunlei@linaro.org> | 2015-04-01 23:34:22 -0400 |
---|---|---|
committer | Ingo Molnar <mingo@kernel.org> | 2015-04-03 02:18:19 -0400 |
commit | 2ee966320028ac846654eba5344540eeb4dc228d (patch) | |
tree | f76ad848dbad24961069e1361821570b00e83ef6 /kernel/time | |
parent | 9a806ddbb9a18c510e4acdcc828b9a87f5fd3aef (diff) |
time: Add y2038 safe read_persistent_clock64()
As part of addressing in-kernel y2038 issues, this patch adds
read_persistent_clock64() and replaces all the call sites of
read_persistent_clock() with this function. This is a __weak
implementation, which simply calls the existing y2038 unsafe
read_persistent_clock().
This allows architecture specific implementations to be
converted independently, and eventually the y2038 unsafe
read_persistent_clock() can be removed after all its
architecture specific implementations have been converted to
read_persistent_clock64().
Suggested-by: Arnd Bergmann <arnd@arndb.de>
Signed-off-by: Xunlei Pang <pang.xunlei@linaro.org>
Signed-off-by: John Stultz <john.stultz@linaro.org>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Thomas Gleixner <tglx@linutronix.de>
Link: http://lkml.kernel.org/r/1427945681-29972-3-git-send-email-john.stultz@linaro.org
Signed-off-by: Ingo Molnar <mingo@kernel.org>
Diffstat (limited to 'kernel/time')
-rw-r--r-- | kernel/time/timekeeping.c | 22 |
1 files changed, 12 insertions, 10 deletions
diff --git a/kernel/time/timekeeping.c b/kernel/time/timekeeping.c index 652e50a9c6ed..b1dbfa573dce 100644 --- a/kernel/time/timekeeping.c +++ b/kernel/time/timekeeping.c | |||
@@ -1173,6 +1173,14 @@ void __weak read_persistent_clock(struct timespec *ts) | |||
1173 | ts->tv_nsec = 0; | 1173 | ts->tv_nsec = 0; |
1174 | } | 1174 | } |
1175 | 1175 | ||
1176 | void __weak read_persistent_clock64(struct timespec64 *ts64) | ||
1177 | { | ||
1178 | struct timespec ts; | ||
1179 | |||
1180 | read_persistent_clock(&ts); | ||
1181 | *ts64 = timespec_to_timespec64(ts); | ||
1182 | } | ||
1183 | |||
1176 | /** | 1184 | /** |
1177 | * read_boot_clock - Return time of the system start. | 1185 | * read_boot_clock - Return time of the system start. |
1178 | * | 1186 | * |
@@ -1205,10 +1213,8 @@ void __init timekeeping_init(void) | |||
1205 | struct clocksource *clock; | 1213 | struct clocksource *clock; |
1206 | unsigned long flags; | 1214 | unsigned long flags; |
1207 | struct timespec64 now, boot, tmp; | 1215 | struct timespec64 now, boot, tmp; |
1208 | struct timespec ts; | ||
1209 | 1216 | ||
1210 | read_persistent_clock(&ts); | 1217 | read_persistent_clock64(&now); |
1211 | now = timespec_to_timespec64(ts); | ||
1212 | if (!timespec64_valid_strict(&now)) { | 1218 | if (!timespec64_valid_strict(&now)) { |
1213 | pr_warn("WARNING: Persistent clock returned invalid value!\n" | 1219 | pr_warn("WARNING: Persistent clock returned invalid value!\n" |
1214 | " Check your CMOS/BIOS settings.\n"); | 1220 | " Check your CMOS/BIOS settings.\n"); |
@@ -1278,7 +1284,7 @@ static void __timekeeping_inject_sleeptime(struct timekeeper *tk, | |||
1278 | * timekeeping_inject_sleeptime64 - Adds suspend interval to timeekeeping values | 1284 | * timekeeping_inject_sleeptime64 - Adds suspend interval to timeekeeping values |
1279 | * @delta: pointer to a timespec64 delta value | 1285 | * @delta: pointer to a timespec64 delta value |
1280 | * | 1286 | * |
1281 | * This hook is for architectures that cannot support read_persistent_clock | 1287 | * This hook is for architectures that cannot support read_persistent_clock64 |
1282 | * because their RTC/persistent clock is only accessible when irqs are enabled. | 1288 | * because their RTC/persistent clock is only accessible when irqs are enabled. |
1283 | * | 1289 | * |
1284 | * This function should only be called by rtc_resume(), and allows | 1290 | * This function should only be called by rtc_resume(), and allows |
@@ -1325,12 +1331,10 @@ void timekeeping_resume(void) | |||
1325 | struct clocksource *clock = tk->tkr_mono.clock; | 1331 | struct clocksource *clock = tk->tkr_mono.clock; |
1326 | unsigned long flags; | 1332 | unsigned long flags; |
1327 | struct timespec64 ts_new, ts_delta; | 1333 | struct timespec64 ts_new, ts_delta; |
1328 | struct timespec tmp; | ||
1329 | cycle_t cycle_now, cycle_delta; | 1334 | cycle_t cycle_now, cycle_delta; |
1330 | bool suspendtime_found = false; | 1335 | bool suspendtime_found = false; |
1331 | 1336 | ||
1332 | read_persistent_clock(&tmp); | 1337 | read_persistent_clock64(&ts_new); |
1333 | ts_new = timespec_to_timespec64(tmp); | ||
1334 | 1338 | ||
1335 | clockevents_resume(); | 1339 | clockevents_resume(); |
1336 | clocksource_resume(); | 1340 | clocksource_resume(); |
@@ -1406,10 +1410,8 @@ int timekeeping_suspend(void) | |||
1406 | unsigned long flags; | 1410 | unsigned long flags; |
1407 | struct timespec64 delta, delta_delta; | 1411 | struct timespec64 delta, delta_delta; |
1408 | static struct timespec64 old_delta; | 1412 | static struct timespec64 old_delta; |
1409 | struct timespec tmp; | ||
1410 | 1413 | ||
1411 | read_persistent_clock(&tmp); | 1414 | read_persistent_clock64(&timekeeping_suspend_time); |
1412 | timekeeping_suspend_time = timespec_to_timespec64(tmp); | ||
1413 | 1415 | ||
1414 | /* | 1416 | /* |
1415 | * On some systems the persistent_clock can not be detected at | 1417 | * On some systems the persistent_clock can not be detected at |