mirror of
https://github.com/asterisk/asterisk.git
synced 2025-09-02 11:06:31 +00:00
app_dial.c: Moved channel lock to prevent deadlock
It's reproducible with pbx_lua, not regular dialplan. deadlock description: 1. asterisk locks a channel 2. calls function onedigit_goto 3. calls ast_goto_if_exists funciton 4. checks ast_exists_extension -> pbx_extension_helper 5. pbx_extension_helper calls pbx_find_extension 6. Then asterisk starts autoservice in a new thread 7. autoservice run tries to lock the channel again Because our channel is locked already, autoservice can't lock. Autoservice can't lock -> autoservice stop is waiting forever. onedigit_goto waits for autoservice stop. Resolves: https://github.com/asterisk/asterisk/issues/1335
This commit is contained in:
@@ -1808,7 +1808,10 @@ static struct ast_channel *wait_for_answer(struct ast_channel *in,
|
||||
if (ast_test_flag64(peerflags, OPT_DTMF_EXIT)) {
|
||||
const char *context;
|
||||
ast_channel_lock(in);
|
||||
context = pbx_builtin_getvar_helper(in, "EXITCONTEXT");
|
||||
if ((context = pbx_builtin_getvar_helper(in, "EXITCONTEXT"))) {
|
||||
context = ast_strdupa(context);
|
||||
}
|
||||
ast_channel_unlock(in);
|
||||
if (onedigit_goto(in, context, (char) f->subclass.integer, 1)) {
|
||||
ast_verb(3, "User hit %c to disconnect call.\n", f->subclass.integer);
|
||||
*to_answer = 0;
|
||||
@@ -1817,14 +1820,12 @@ static struct ast_channel *wait_for_answer(struct ast_channel *in,
|
||||
pa->canceled = 1;
|
||||
publish_dial_end_event(in, out_chans, NULL, pa->status);
|
||||
ast_frfree(f);
|
||||
ast_channel_unlock(in);
|
||||
if (is_cc_recall) {
|
||||
ast_cc_completed(in, "CC completed, but the caller used DTMF to exit");
|
||||
}
|
||||
SCOPE_EXIT_RTN_VALUE(NULL, "%s: Caller pressed %c to end call\n",
|
||||
ast_channel_name(in), f->subclass.integer);
|
||||
}
|
||||
ast_channel_unlock(in);
|
||||
}
|
||||
|
||||
if (ast_test_flag64(peerflags, OPT_CALLER_HANGUP) &&
|
||||
|
Reference in New Issue
Block a user