diff options
author | Ian Kent <raven@themaw.net> | 2009-09-28 23:47:44 +0800 |
---|---|---|
committer | Jaikumar Ganesh <jaikumar@google.com> | 2011-05-25 11:51:54 -0700 |
commit | b259b11bf5ac5259069d1144cd049e213352ed74 (patch) | |
tree | d3b387f797018beb781f95acfd440fb0aaa55d82 /audio | |
parent | 71d71d08545fdc8f923119dea69f4c274ca60b71 (diff) | |
download | bluez-b259b11bf5ac5259069d1144cd049e213352ed74.tar.gz |
bluez a2dp - fix wait_for_start() spurious wakeup
When waiting on a condition is is possble to receive spurious
wake ups. Deal with this in wait_for_start().
Change-Id: I678e9d7831333d9b8baa31e9b0ec2597ca9263cd
Diffstat (limited to 'audio')
-rwxr-xr-x | audio/liba2dp.c | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/audio/liba2dp.c b/audio/liba2dp.c index 222b188b..b48b954c 100755 --- a/audio/liba2dp.c +++ b/audio/liba2dp.c @@ -917,7 +917,7 @@ static int wait_for_start(struct bluetooth_data *data, int timeout) ts.tv_nsec = (tv.tv_usec + (timeout % 1000) * 1000L ) * 1000L; pthread_mutex_lock(&data->mutex); - while (state != A2DP_STATE_STARTED && !err) { + while (state != A2DP_STATE_STARTED) { if (state == A2DP_STATE_NONE) set_command(data, A2DP_CMD_INIT); else if (state == A2DP_STATE_INITIALIZED) @@ -925,9 +925,22 @@ static int wait_for_start(struct bluetooth_data *data, int timeout) else if (state == A2DP_STATE_CONFIGURED) { __set_command(data, A2DP_CMD_START); } +again: + err = pthread_cond_timedwait(&data->client_wait, &data->mutex, &ts); + if (err) { + /* don't timeout if we're done */ + if (data->state == A2DP_STATE_STARTED) { + err = 0; + break; + } + if (err == ETIMEDOUT) + break; + goto again; + } + + if (state == data->state) + goto again; - while ((err = pthread_cond_timedwait(&data->client_wait, &data->mutex, &ts)) - == EINTR) ; state = data->state; if (state == A2DP_STATE_NONE) { |