summaryrefslogtreecommitdiffstats
path: root/drivers/rtc/class.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2011-05-19 17:45:08 -0700
committerLinus Torvalds <torvalds@linux-foundation.org>2011-05-19 17:45:08 -0700
commit78c4def67e8eebe602655a3dec9aa08f0e2f7c4b (patch)
tree8c0c756bbff7325f5c2a773f8cc64d8390ebe5b5 /drivers/rtc/class.c
parent7e6628e4bcb3b3546c625ec63ca724f28ab14f0c (diff)
parent942c3c5c329274fa6de5998cb911cf3d0a42d0b1 (diff)
downloadop-kernel-dev-78c4def67e8eebe602655a3dec9aa08f0e2f7c4b.zip
op-kernel-dev-78c4def67e8eebe602655a3dec9aa08f0e2f7c4b.tar.gz
Merge branch 'timers-core-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip
* 'timers-core-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip: hrtimer: Make lookup table const RTC: Disable CONFIG_RTC_CLASS from being built as a module timers: Fix alarmtimer build issues when CONFIG_RTC_CLASS=n timers: Remove delayed irqwork from alarmtimers implementation timers: Improve alarmtimer comments and minor fixes timers: Posix interface for alarm-timers timers: Introduce in-kernel alarm-timer interface timers: Add rb_init_node() to allow for stack allocated rb nodes time: Add timekeeping_inject_sleeptime
Diffstat (limited to 'drivers/rtc/class.c')
-rw-r--r--drivers/rtc/class.c23
1 files changed, 9 insertions, 14 deletions
diff --git a/drivers/rtc/class.c b/drivers/rtc/class.c
index 3901386..4194e59 100644
--- a/drivers/rtc/class.c
+++ b/drivers/rtc/class.c
@@ -41,26 +41,21 @@ static void rtc_device_release(struct device *dev)
* system's wall clock; restore it on resume().
*/
-static struct timespec delta;
static time_t oldtime;
+static struct timespec oldts;
static int rtc_suspend(struct device *dev, pm_message_t mesg)
{
struct rtc_device *rtc = to_rtc_device(dev);
struct rtc_time tm;
- struct timespec ts = current_kernel_time();
if (strcmp(dev_name(&rtc->dev), CONFIG_RTC_HCTOSYS_DEVICE) != 0)
return 0;
rtc_read_time(rtc, &tm);
+ ktime_get_ts(&oldts);
rtc_tm_to_time(&tm, &oldtime);
- /* RTC precision is 1 second; adjust delta for avg 1/2 sec err */
- set_normalized_timespec(&delta,
- ts.tv_sec - oldtime,
- ts.tv_nsec - (NSEC_PER_SEC >> 1));
-
return 0;
}
@@ -70,10 +65,12 @@ static int rtc_resume(struct device *dev)
struct rtc_time tm;
time_t newtime;
struct timespec time;
+ struct timespec newts;
if (strcmp(dev_name(&rtc->dev), CONFIG_RTC_HCTOSYS_DEVICE) != 0)
return 0;
+ ktime_get_ts(&newts);
rtc_read_time(rtc, &tm);
if (rtc_valid_tm(&tm) != 0) {
pr_debug("%s: bogus resume time\n", dev_name(&rtc->dev));
@@ -85,15 +82,13 @@ static int rtc_resume(struct device *dev)
pr_debug("%s: time travel!\n", dev_name(&rtc->dev));
return 0;
}
+ /* calculate the RTC time delta */
+ set_normalized_timespec(&time, newtime - oldtime, 0);
- /* restore wall clock using delta against this RTC;
- * adjust again for avg 1/2 second RTC sampling error
- */
- set_normalized_timespec(&time,
- newtime + delta.tv_sec,
- (NSEC_PER_SEC >> 1) + delta.tv_nsec);
- do_settimeofday(&time);
+ /* subtract kernel time between rtc_suspend to rtc_resume */
+ time = timespec_sub(time, timespec_sub(newts, oldts));
+ timekeeping_inject_sleeptime(&time);
return 0;
}
OpenPOWER on IntegriCloud