* [PATCH] rtc: Fix some bugs that allowed accumulating time drift in suspend/resume
@ 2011-11-23 2:24 Arve Hjønnevåg
2011-11-23 2:49 ` John Stultz
0 siblings, 1 reply; 2+ messages in thread
From: Arve Hjønnevåg @ 2011-11-23 2:24 UTC (permalink / raw)
To: linux-kernel
Cc: John Stultz, Arve Hjønnevåg, Alessandro Zummo,
rtc-linux
The current code checks if abs(delta_delta.tv_sec) is greater or
equal to two before it discards the old delta value, but this can
trigger at close to -1 seconds since -1.000000001 seconds is stored
as tv_sec -2 and tv_nsec 999999999 in a normalized timespec.
rtc_resume had an early return check if the rtc value had not changed
since rtc_suspend. This effectivly stops time for the duration of the
short sleep. Check if sleep_time is positive after all the adjustments
have been applied instead since this allows the old_system adjustment
in rtc_suspend to have an effect even for short sleep cycles.
Signed-off-by: Arve Hjønnevåg <arve@android.com>
---
drivers/rtc/class.c | 10 +++++-----
1 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/drivers/rtc/class.c b/drivers/rtc/class.c
index 01a7df5..b82a155 100644
--- a/drivers/rtc/class.c
+++ b/drivers/rtc/class.c
@@ -66,7 +66,7 @@ static int rtc_suspend(struct device *dev, pm_message_t mesg)
*/
delta = timespec_sub(old_system, old_rtc);
delta_delta = timespec_sub(delta, old_delta);
- if (abs(delta_delta.tv_sec) >= 2) {
+ if (delta_delta.tv_sec < -2 || delta_delta.tv_sec >= 2) {
/*
* if delta_delta is too large, assume time correction
* has occured and set old_delta to the current delta.
@@ -100,9 +100,8 @@ static int rtc_resume(struct device *dev)
rtc_tm_to_time(&tm, &new_rtc.tv_sec);
new_rtc.tv_nsec = 0;
- if (new_rtc.tv_sec <= old_rtc.tv_sec) {
- if (new_rtc.tv_sec < old_rtc.tv_sec)
- pr_debug("%s: time travel!\n", dev_name(&rtc->dev));
+ if (new_rtc.tv_sec < old_rtc.tv_sec) {
+ pr_debug("%s: time travel!\n", dev_name(&rtc->dev));
return 0;
}
@@ -119,7 +118,8 @@ static int rtc_resume(struct device *dev)
sleep_time = timespec_sub(sleep_time,
timespec_sub(new_system, old_system));
- timekeeping_inject_sleeptime(&sleep_time);
+ if (sleep_time.tv_sec >= 0)
+ timekeeping_inject_sleeptime(&sleep_time);
return 0;
}
--
1.7.3.1
^ permalink raw reply related [flat|nested] 2+ messages in thread
* Re: [PATCH] rtc: Fix some bugs that allowed accumulating time drift in suspend/resume
2011-11-23 2:24 [PATCH] rtc: Fix some bugs that allowed accumulating time drift in suspend/resume Arve Hjønnevåg
@ 2011-11-23 2:49 ` John Stultz
0 siblings, 0 replies; 2+ messages in thread
From: John Stultz @ 2011-11-23 2:49 UTC (permalink / raw)
To: Arve Hjønnevåg; +Cc: linux-kernel, Alessandro Zummo, rtc-linux
On Tue, 2011-11-22 at 18:24 -0800, Arve Hjønnevåg wrote:
> The current code checks if abs(delta_delta.tv_sec) is greater or
> equal to two before it discards the old delta value, but this can
> trigger at close to -1 seconds since -1.000000001 seconds is stored
> as tv_sec -2 and tv_nsec 999999999 in a normalized timespec.
>
> rtc_resume had an early return check if the rtc value had not changed
> since rtc_suspend. This effectivly stops time for the duration of the
> short sleep. Check if sleep_time is positive after all the adjustments
> have been applied instead since this allows the old_system adjustment
> in rtc_suspend to have an effect even for short sleep cycles.
>
> Signed-off-by: Arve Hjønnevåg <arve@android.com>
Looks good to me! Thanks for fixing and sending this in!
I'll queue it for upstream.
thanks
-john
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2011-11-23 2:49 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2011-11-23 2:24 [PATCH] rtc: Fix some bugs that allowed accumulating time drift in suspend/resume Arve Hjønnevåg
2011-11-23 2:49 ` John Stultz
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox