summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--main/channel.c6
1 files changed, 6 insertions, 0 deletions
diff --git a/main/channel.c b/main/channel.c
index c1b3b88ba..bc6041348 100644
--- a/main/channel.c
+++ b/main/channel.c
@@ -929,6 +929,7 @@ static struct ast_channel *channel_find_locked(const struct ast_channel *prev,
const char *msg = prev ? "deadlock" : "initial deadlock";
int retries;
struct ast_channel *c;
+ const struct ast_channel *_prev = prev;
for (retries = 0; retries < 10; retries++) {
int done;
@@ -988,6 +989,11 @@ static struct ast_channel *channel_find_locked(const struct ast_channel *prev,
AST_RWLIST_UNLOCK(&channels);
if (done)
return c;
+ /* If we reach this point we basically tried to lock a channel and failed. Instead of
+ * starting from the beginning of the list we can restore our saved pointer to the previous
+ * channel and start from there.
+ */
+ prev = _prev;
usleep(1); /* give other threads a chance before retrying */
}