aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorThomas Gleixner <tglx@linutronix.de>2006-01-12 05:25:54 -0500
committerThomas Gleixner <tglx@linutronix.de>2006-01-12 05:25:54 -0500
commit288867ec5c377db82933b64460ce050e5c998ee9 (patch)
treed1c0c2e89cb7ffa2ac613e9b1740b81a813965a7
parent593195f9b2309693f27b402f34573f7920b82c3e (diff)
[hrtimer] Remove listhead from hrtimer struct
The list_head in the hrtimer structure was introduced for easy access to the first timer with the further extensions of real high resolution timers in mind, but it turned out in the course of development that it is not necessary for the standard use case. Remove the list head and access the first expiry timer by a datafield in the timer base. Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
-rw-r--r--include/linux/hrtimer.h7
-rw-r--r--kernel/hrtimer.c26
2 files changed, 16 insertions, 17 deletions
diff --git a/include/linux/hrtimer.h b/include/linux/hrtimer.h
index cf5cfdf8d613..abb674c9b764 100644
--- a/include/linux/hrtimer.h
+++ b/include/linux/hrtimer.h
@@ -49,8 +49,6 @@ struct hrtimer_base;
49 * struct hrtimer - the basic hrtimer structure 49 * struct hrtimer - the basic hrtimer structure
50 * 50 *
51 * @node: red black tree node for time ordered insertion 51 * @node: red black tree node for time ordered insertion
52 * @list: list head for easier access to the time ordered list,
53 * without walking the red black tree.
54 * @expires: the absolute expiry time in the hrtimers internal 52 * @expires: the absolute expiry time in the hrtimers internal
55 * representation. The time is related to the clock on 53 * representation. The time is related to the clock on
56 * which the timer is based. 54 * which the timer is based.
@@ -63,7 +61,6 @@ struct hrtimer_base;
63 */ 61 */
64struct hrtimer { 62struct hrtimer {
65 struct rb_node node; 63 struct rb_node node;
66 struct list_head list;
67 ktime_t expires; 64 ktime_t expires;
68 enum hrtimer_state state; 65 enum hrtimer_state state;
69 int (*function)(void *); 66 int (*function)(void *);
@@ -78,7 +75,7 @@ struct hrtimer {
78 * to a base on another cpu. 75 * to a base on another cpu.
79 * @lock: lock protecting the base and associated timers 76 * @lock: lock protecting the base and associated timers
80 * @active: red black tree root node for the active timers 77 * @active: red black tree root node for the active timers
81 * @pending: list of pending timers for simple time ordered access 78 * @first: pointer to the timer node which expires first
82 * @resolution: the resolution of the clock, in nanoseconds 79 * @resolution: the resolution of the clock, in nanoseconds
83 * @get_time: function to retrieve the current time of the clock 80 * @get_time: function to retrieve the current time of the clock
84 * @curr_timer: the timer which is executing a callback right now 81 * @curr_timer: the timer which is executing a callback right now
@@ -87,7 +84,7 @@ struct hrtimer_base {
87 clockid_t index; 84 clockid_t index;
88 spinlock_t lock; 85 spinlock_t lock;
89 struct rb_root active; 86 struct rb_root active;
90 struct list_head pending; 87 struct rb_node *first;
91 unsigned long resolution; 88 unsigned long resolution;
92 ktime_t (*get_time)(void); 89 ktime_t (*get_time)(void);
93 struct hrtimer *curr_timer; 90 struct hrtimer *curr_timer;
diff --git a/kernel/hrtimer.c b/kernel/hrtimer.c
index f073a2461faa..e6e8278bcb18 100644
--- a/kernel/hrtimer.c
+++ b/kernel/hrtimer.c
@@ -314,7 +314,6 @@ hrtimer_forward(struct hrtimer *timer, const ktime_t interval)
314static void enqueue_hrtimer(struct hrtimer *timer, struct hrtimer_base *base) 314static void enqueue_hrtimer(struct hrtimer *timer, struct hrtimer_base *base)
315{ 315{
316 struct rb_node **link = &base->active.rb_node; 316 struct rb_node **link = &base->active.rb_node;
317 struct list_head *prev = &base->pending;
318 struct rb_node *parent = NULL; 317 struct rb_node *parent = NULL;
319 struct hrtimer *entry; 318 struct hrtimer *entry;
320 319
@@ -330,22 +329,23 @@ static void enqueue_hrtimer(struct hrtimer *timer, struct hrtimer_base *base)
330 */ 329 */
331 if (timer->expires.tv64 < entry->expires.tv64) 330 if (timer->expires.tv64 < entry->expires.tv64)
332 link = &(*link)->rb_left; 331 link = &(*link)->rb_left;
333 else { 332 else
334 link = &(*link)->rb_right; 333 link = &(*link)->rb_right;
335 prev = &entry->list;
336 }
337 } 334 }
338 335
339 /* 336 /*
340 * Insert the timer to the rbtree and to the sorted list: 337 * Insert the timer to the rbtree and check whether it
338 * replaces the first pending timer
341 */ 339 */
342 rb_link_node(&timer->node, parent, link); 340 rb_link_node(&timer->node, parent, link);
343 rb_insert_color(&timer->node, &base->active); 341 rb_insert_color(&timer->node, &base->active);
344 list_add(&timer->list, prev);
345 342
346 timer->state = HRTIMER_PENDING; 343 timer->state = HRTIMER_PENDING;
347}
348 344
345 if (!base->first || timer->expires.tv64 <
346 rb_entry(base->first, struct hrtimer, node)->expires.tv64)
347 base->first = &timer->node;
348}
349 349
350/* 350/*
351 * __remove_hrtimer - internal function to remove a timer 351 * __remove_hrtimer - internal function to remove a timer
@@ -355,9 +355,11 @@ static void enqueue_hrtimer(struct hrtimer *timer, struct hrtimer_base *base)
355static void __remove_hrtimer(struct hrtimer *timer, struct hrtimer_base *base) 355static void __remove_hrtimer(struct hrtimer *timer, struct hrtimer_base *base)
356{ 356{
357 /* 357 /*
358 * Remove the timer from the sorted list and from the rbtree: 358 * Remove the timer from the rbtree and replace the
359 * first entry pointer if necessary.
359 */ 360 */
360 list_del(&timer->list); 361 if (base->first == &timer->node)
362 base->first = rb_next(&timer->node);
361 rb_erase(&timer->node, &base->active); 363 rb_erase(&timer->node, &base->active);
362} 364}
363 365
@@ -529,16 +531,17 @@ int hrtimer_get_res(const clockid_t which_clock, struct timespec *tp)
529static inline void run_hrtimer_queue(struct hrtimer_base *base) 531static inline void run_hrtimer_queue(struct hrtimer_base *base)
530{ 532{
531 ktime_t now = base->get_time(); 533 ktime_t now = base->get_time();
534 struct rb_node *node;
532 535
533 spin_lock_irq(&base->lock); 536 spin_lock_irq(&base->lock);
534 537
535 while (!list_empty(&base->pending)) { 538 while ((node = base->first)) {
536 struct hrtimer *timer; 539 struct hrtimer *timer;
537 int (*fn)(void *); 540 int (*fn)(void *);
538 int restart; 541 int restart;
539 void *data; 542 void *data;
540 543
541 timer = list_entry(base->pending.next, struct hrtimer, list); 544 timer = rb_entry(node, struct hrtimer, node);
542 if (now.tv64 <= timer->expires.tv64) 545 if (now.tv64 <= timer->expires.tv64)
543 break; 546 break;
544 547
@@ -732,7 +735,6 @@ static void __devinit init_hrtimers_cpu(int cpu)
732 735
733 for (i = 0; i < MAX_HRTIMER_BASES; i++) { 736 for (i = 0; i < MAX_HRTIMER_BASES; i++) {
734 spin_lock_init(&base->lock); 737 spin_lock_init(&base->lock);
735 INIT_LIST_HEAD(&base->pending);
736 base++; 738 base++;
737 } 739 }
738} 740}