aboutsummaryrefslogtreecommitdiffstats
path: root/kernel
diff options
context:
space:
mode:
Diffstat (limited to 'kernel')
-rw-r--r--kernel/hrtimer.c53
1 files changed, 35 insertions, 18 deletions
diff --git a/kernel/hrtimer.c b/kernel/hrtimer.c
index e2f91ecc01a8..1363c1aac158 100644
--- a/kernel/hrtimer.c
+++ b/kernel/hrtimer.c
@@ -486,13 +486,14 @@ static inline int hrtimer_hres_active(void)
486 * next event 486 * next event
487 * Called with interrupts disabled and base->lock held 487 * Called with interrupts disabled and base->lock held
488 */ 488 */
489static void hrtimer_force_reprogram(struct hrtimer_cpu_base *cpu_base) 489static void
490hrtimer_force_reprogram(struct hrtimer_cpu_base *cpu_base, int skip_equal)
490{ 491{
491 int i; 492 int i;
492 struct hrtimer_clock_base *base = cpu_base->clock_base; 493 struct hrtimer_clock_base *base = cpu_base->clock_base;
493 ktime_t expires; 494 ktime_t expires, expires_next;
494 495
495 cpu_base->expires_next.tv64 = KTIME_MAX; 496 expires_next.tv64 = KTIME_MAX;
496 497
497 for (i = 0; i < HRTIMER_MAX_CLOCK_BASES; i++, base++) { 498 for (i = 0; i < HRTIMER_MAX_CLOCK_BASES; i++, base++) {
498 struct hrtimer *timer; 499 struct hrtimer *timer;
@@ -508,10 +509,15 @@ static void hrtimer_force_reprogram(struct hrtimer_cpu_base *cpu_base)
508 */ 509 */
509 if (expires.tv64 < 0) 510 if (expires.tv64 < 0)
510 expires.tv64 = 0; 511 expires.tv64 = 0;
511 if (expires.tv64 < cpu_base->expires_next.tv64) 512 if (expires.tv64 < expires_next.tv64)
512 cpu_base->expires_next = expires; 513 expires_next = expires;
513 } 514 }
514 515
516 if (skip_equal && expires_next.tv64 == cpu_base->expires_next.tv64)
517 return;
518
519 cpu_base->expires_next.tv64 = expires_next.tv64;
520
515 if (cpu_base->expires_next.tv64 != KTIME_MAX) 521 if (cpu_base->expires_next.tv64 != KTIME_MAX)
516 tick_program_event(cpu_base->expires_next, 1); 522 tick_program_event(cpu_base->expires_next, 1);
517} 523}
@@ -594,7 +600,7 @@ static void retrigger_next_event(void *arg)
594 base->clock_base[CLOCK_REALTIME].offset = 600 base->clock_base[CLOCK_REALTIME].offset =
595 timespec_to_ktime(realtime_offset); 601 timespec_to_ktime(realtime_offset);
596 602
597 hrtimer_force_reprogram(base); 603 hrtimer_force_reprogram(base, 0);
598 spin_unlock(&base->lock); 604 spin_unlock(&base->lock);
599} 605}
600 606
@@ -707,7 +713,8 @@ static int hrtimer_switch_to_hres(void)
707static inline int hrtimer_hres_active(void) { return 0; } 713static inline int hrtimer_hres_active(void) { return 0; }
708static inline int hrtimer_is_hres_enabled(void) { return 0; } 714static inline int hrtimer_is_hres_enabled(void) { return 0; }
709static inline int hrtimer_switch_to_hres(void) { return 0; } 715static inline int hrtimer_switch_to_hres(void) { return 0; }
710static inline void hrtimer_force_reprogram(struct hrtimer_cpu_base *base) { } 716static inline void
717hrtimer_force_reprogram(struct hrtimer_cpu_base *base, int skip_equal) { }
711static inline int hrtimer_enqueue_reprogram(struct hrtimer *timer, 718static inline int hrtimer_enqueue_reprogram(struct hrtimer *timer,
712 struct hrtimer_clock_base *base, 719 struct hrtimer_clock_base *base,
713 int wakeup) 720 int wakeup)
@@ -850,19 +857,29 @@ static void __remove_hrtimer(struct hrtimer *timer,
850 struct hrtimer_clock_base *base, 857 struct hrtimer_clock_base *base,
851 unsigned long newstate, int reprogram) 858 unsigned long newstate, int reprogram)
852{ 859{
853 if (timer->state & HRTIMER_STATE_ENQUEUED) { 860 if (!(timer->state & HRTIMER_STATE_ENQUEUED))
854 /* 861 goto out;
855 * Remove the timer from the rbtree and replace the 862
856 * first entry pointer if necessary. 863 /*
857 */ 864 * Remove the timer from the rbtree and replace the first
858 if (base->first == &timer->node) { 865 * entry pointer if necessary.
859 base->first = rb_next(&timer->node); 866 */
860 /* Reprogram the clock event device. if enabled */ 867 if (base->first == &timer->node) {
861 if (reprogram && hrtimer_hres_active()) 868 base->first = rb_next(&timer->node);
862 hrtimer_force_reprogram(base->cpu_base); 869#ifdef CONFIG_HIGH_RES_TIMERS
870 /* Reprogram the clock event device. if enabled */
871 if (reprogram && hrtimer_hres_active()) {
872 ktime_t expires;
873
874 expires = ktime_sub(hrtimer_get_expires(timer),
875 base->offset);
876 if (base->cpu_base->expires_next.tv64 == expires.tv64)
877 hrtimer_force_reprogram(base->cpu_base, 1);
863 } 878 }
864 rb_erase(&timer->node, &base->active); 879#endif
865 } 880 }
881 rb_erase(&timer->node, &base->active);
882out:
866 timer->state = newstate; 883 timer->state = newstate;
867} 884}
868 885