aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/time/timekeeping.c
diff options
context:
space:
mode:
authorFeng Tang <feng.tang@intel.com>2013-01-15 11:09:47 -0500
committerJohn Stultz <john.stultz@linaro.org>2013-01-15 21:16:07 -0500
commit31ade30692dc9680bfc95700d794818fa3f754ac (patch)
treecb436c839b890d04f589b49f75cb0df59315158e /kernel/time/timekeeping.c
parentf0dbe81f0e7c39783ad25d9084bbcda131508993 (diff)
timekeeping: Add persistent_clock_exist flag
In current kernel, there are several places which need to check whether there is a persistent clock for the platform. Current check is done by calling the read_persistent_clock() and validating its return value. So one optimization is to do the check only once in timekeeping_init(), and use a flag persistent_clock_exist to record it. v2: Add a has_persistent_clock() helper function, as suggested by John. Cc: Thomas Gleixner <tglx@linutronix.de> Cc: John Stultz <john.stultz@linaro.org> Signed-off-by: Feng Tang <feng.tang@intel.com> Signed-off-by: John Stultz <john.stultz@linaro.org>
Diffstat (limited to 'kernel/time/timekeeping.c')
-rw-r--r--kernel/time/timekeeping.c16
1 files changed, 11 insertions, 5 deletions
diff --git a/kernel/time/timekeeping.c b/kernel/time/timekeeping.c
index dfc7f87eb332..b7a584177618 100644
--- a/kernel/time/timekeeping.c
+++ b/kernel/time/timekeeping.c
@@ -28,6 +28,9 @@ static struct timekeeper timekeeper;
28/* flag for if timekeeping is suspended */ 28/* flag for if timekeeping is suspended */
29int __read_mostly timekeeping_suspended; 29int __read_mostly timekeeping_suspended;
30 30
31/* Flag for if there is a persistent clock on this platform */
32bool __read_mostly persistent_clock_exist = false;
33
31static inline void tk_normalize_xtime(struct timekeeper *tk) 34static inline void tk_normalize_xtime(struct timekeeper *tk)
32{ 35{
33 while (tk->xtime_nsec >= ((u64)NSEC_PER_SEC << tk->shift)) { 36 while (tk->xtime_nsec >= ((u64)NSEC_PER_SEC << tk->shift)) {
@@ -609,12 +612,14 @@ void __init timekeeping_init(void)
609 struct timespec now, boot, tmp; 612 struct timespec now, boot, tmp;
610 613
611 read_persistent_clock(&now); 614 read_persistent_clock(&now);
615
612 if (!timespec_valid_strict(&now)) { 616 if (!timespec_valid_strict(&now)) {
613 pr_warn("WARNING: Persistent clock returned invalid value!\n" 617 pr_warn("WARNING: Persistent clock returned invalid value!\n"
614 " Check your CMOS/BIOS settings.\n"); 618 " Check your CMOS/BIOS settings.\n");
615 now.tv_sec = 0; 619 now.tv_sec = 0;
616 now.tv_nsec = 0; 620 now.tv_nsec = 0;
617 } 621 } else if (now.tv_sec || now.tv_nsec)
622 persistent_clock_exist = true;
618 623
619 read_boot_clock(&boot); 624 read_boot_clock(&boot);
620 if (!timespec_valid_strict(&boot)) { 625 if (!timespec_valid_strict(&boot)) {
@@ -687,11 +692,12 @@ void timekeeping_inject_sleeptime(struct timespec *delta)
687{ 692{
688 struct timekeeper *tk = &timekeeper; 693 struct timekeeper *tk = &timekeeper;
689 unsigned long flags; 694 unsigned long flags;
690 struct timespec ts;
691 695
692 /* Make sure we don't set the clock twice */ 696 /*
693 read_persistent_clock(&ts); 697 * Make sure we don't set the clock twice, as timekeeping_resume()
694 if (!(ts.tv_sec == 0 && ts.tv_nsec == 0)) 698 * already did it
699 */
700 if (has_persistent_clock())
695 return; 701 return;
696 702
697 write_seqlock_irqsave(&tk->lock, flags); 703 write_seqlock_irqsave(&tk->lock, flags);