[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [PATCH][QEMU] Make active-timers thread-safe
Protect active_timers[] lists with mutexes so timers can be safely used from different threads. Signed-off-by: Ben Guthro <bguthro@xxxxxxxxxxxxxx> Signed-off-by: Gary Grebus <ggrebus@xxxxxxxxxxxxxxx> diff -r 475eda44cd99 tools/ioemu/vl.c --- a/tools/ioemu/vl.c Mon Aug 27 14:14:56 2007 -0400 +++ b/tools/ioemu/vl.c Mon Aug 27 14:14:56 2007 -0400 @@ -759,6 +759,7 @@ QEMUClock *vm_clock; QEMUClock *vm_clock; static QEMUTimer *active_timers[2]; +static pthread_mutex_t active_timers_lock[2]; #ifdef _WIN32 static MMRESULT timerID; static HANDLE host_alarm = NULL; @@ -795,7 +796,7 @@ void qemu_free_timer(QEMUTimer *ts) } /* stop a timer, but do not dealloc it */ -void qemu_del_timer(QEMUTimer *ts) +static void qemu_del_timer_nolock(QEMUTimer *ts) { QEMUTimer **pt, *t; @@ -808,10 +809,18 @@ void qemu_del_timer(QEMUTimer *ts) break; if (t == ts) { *pt = t->next; + t->next = NULL; break; } pt = &t->next; } +} + +void qemu_del_timer(QEMUTimer *ts) +{ + pthread_mutex_lock(&active_timers_lock[ts->clock->type]); + qemu_del_timer_nolock(ts); + pthread_mutex_unlock(&active_timers_lock[ts->clock->type]); } void qemu_advance_timer(QEMUTimer *ts, int64_t expire_time) @@ -826,11 +835,13 @@ void qemu_mod_timer(QEMUTimer *ts, int64 { QEMUTimer **pt, *t; - qemu_del_timer(ts); - - /* add the timer in the sorted list */ /* NOTE: this code must be signal safe because qemu_timer_expired() can be called from a signal. */ + pthread_mutex_lock(&active_timers_lock[ts->clock->type]); + + qemu_del_timer_nolock(ts); + + /* add the timer in the sorted list */ pt = &active_timers[ts->clock->type]; for(;;) { t = *pt; @@ -843,16 +854,20 @@ void qemu_mod_timer(QEMUTimer *ts, int64 ts->expire_time = expire_time; ts->next = *pt; *pt = ts; + pthread_mutex_unlock(&active_timers_lock[ts->clock->type]); } int qemu_timer_pending(QEMUTimer *ts) { QEMUTimer *t; + pthread_mutex_lock(&active_timers_lock[ts->clock->type]); for(t = active_timers[ts->clock->type]; t != NULL; t = t->next) { if (t == ts) - return 1; - } - return 0; + break; + } + pthread_mutex_unlock(&active_timers_lock[ts->clock->type]); + return !!t; + } static inline int qemu_timer_expired(QEMUTimer *timer_head, int64_t current_time) @@ -865,7 +880,12 @@ static void qemu_run_timers(QEMUTimer ** static void qemu_run_timers(QEMUTimer **ptimer_head, int64_t current_time) { QEMUTimer *ts; + int clock_type; + if (*ptimer_head == NULL) + return; + clock_type = (*ptimer_head)->clock->type; + pthread_mutex_lock(&active_timers_lock[clock_type]); for(;;) { ts = *ptimer_head; if (!ts || ts->expire_time > current_time) @@ -875,8 +895,11 @@ static void qemu_run_timers(QEMUTimer ** ts->next = NULL; /* run the callback (the timer list can be modified) */ + pthread_mutex_unlock(&active_timers_lock[clock_type]); ts->cb(ts->opaque); - } + pthread_mutex_lock(&active_timers_lock[clock_type]); + } + pthread_mutex_unlock(&active_timers_lock[clock_type]); } int64_t qemu_get_clock(QEMUClock *clock) _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |