From f945d6d201901b204eceae0b8ee7d6a8d0912402 Mon Sep 17 00:00:00 2001 From: Michael Brown Date: Sun, 12 Oct 2008 15:04:37 +0100 Subject: [PATCH] [retry] Use a separate flag to indicate that a retry timer is running Using start==0 to indicate a stopped timer is dangerous, because 0 is a valid value for the current tick counter. --- src/include/gpxe/retry.h | 9 ++++----- src/net/retry.c | 12 ++++++++---- 2 files changed, 12 insertions(+), 9 deletions(-) diff --git a/src/include/gpxe/retry.h b/src/include/gpxe/retry.h index ec57db9e..1e7fde4c 100644 --- a/src/include/gpxe/retry.h +++ b/src/include/gpxe/retry.h @@ -19,6 +19,8 @@ struct retry_timer { /** List of active timers */ struct list_head list; + /** Timer is currently running */ + unsigned int running; /** Timeout value (in ticks) */ unsigned long timeout; /** Minimum timeout value (in ticks) @@ -31,10 +33,7 @@ struct retry_timer { * A value of zero means "use default timeout." */ unsigned long max_timeout; - /** Start time (in ticks) - * - * A start time of zero indicates a stopped timer. - */ + /** Start time (in ticks) */ unsigned long start; /** Retry count */ unsigned int count; @@ -74,7 +73,7 @@ static inline void start_timer_nodelay ( struct retry_timer *timer ) { */ static inline __attribute__ (( always_inline )) unsigned long timer_running ( struct retry_timer *timer ) { - return ( timer->start ); + return ( timer->running ); } #endif /* _GPXE_RETRY_H */ diff --git a/src/net/retry.c b/src/net/retry.c index 2a645c97..cd793a7f 100644 --- a/src/net/retry.c +++ b/src/net/retry.c @@ -55,9 +55,10 @@ static LIST_HEAD ( timers ); * be stopped and the timer's callback function will be called. */ void start_timer ( struct retry_timer *timer ) { - if ( ! timer_running ( timer ) ) + if ( ! timer->running ) list_add ( &timer->list, &timers ); timer->start = currticks(); + timer->running = 1; /* 0 means "use default timeout" */ if ( timer->min_timeout == 0 ) @@ -82,6 +83,8 @@ void start_timer ( struct retry_timer *timer ) { void start_timer_fixed ( struct retry_timer *timer, unsigned long timeout ) { start_timer ( timer ); timer->timeout = timeout; + DBG2 ( "Timer %p expiry time changed to %ld\n", + timer, ( timer->start + timer->timeout ) ); } /** @@ -97,12 +100,12 @@ void stop_timer ( struct retry_timer *timer ) { unsigned long runtime; /* If timer was already stopped, do nothing */ - if ( ! timer_running ( timer ) ) + if ( ! timer->running ) return; list_del ( &timer->list ); runtime = ( now - timer->start ); - timer->start = 0; + timer->running = 0; DBG2 ( "Timer %p stopped at time %ld (ran for %ld)\n", timer, now, runtime ); @@ -144,8 +147,9 @@ static void timer_expired ( struct retry_timer *timer ) { /* Stop timer without performing RTT calculations */ DBG2 ( "Timer %p stopped at time %ld on expiry\n", timer, currticks() ); + assert ( timer->running ); list_del ( &timer->list ); - timer->start = 0; + timer->running = 0; timer->count++; /* Back off the timeout value */