[asterisk-dev] fork or pthread_atfork
Yuan Qin
yuan007qin at gmail.com
Fri Apr 6 08:04:27 MST 2007
Hi, all
I found that code in res_agi.c(version of 1.2.13) called fork() to
create an AGI process,
however, fork() is not a safe function in Linux multi-thread environment
because the child
process only hold one thread that made from a copy of the calling thread but
inherit all the mutex
or conditional variables including their state of the whole process. The
child process doesn't
known the state of any mutex or conditional variable, It may fall into
deadlock If it lock the mutex
before execv, For example, the following code fragment(in res_agi.c):
pid = fork();
if (pid < 0) {
ast_log(LOG_WARNING, "Failed to fork(): %s\n", strerror(errno));
return -1;
}
if (!pid) {
/* Don't run AGI scripts with realtime priority -- it causes audio
stutter */
ast_set_priority(0);
/* Redirect stdin and out, provide enhanced audio channel if desired
*/
dup2(fromast[0], STDIN_FILENO);
dup2(toast[1], STDOUT_FILENO);
if (efd) {
dup2(audio[0], STDERR_FILENO + 1);
} else {
close(STDERR_FILENO + 1);
}
/* unblock important signal handlers */
if (sigfillset(&signal_set) || pthread_sigmask(SIG_UNBLOCK,
&signal_set, NULL)) {
ast_log(LOG_WARNING, "unable to unblock signals for AGI script:
%s\n", strerror(errno));
exit(1);
}
/* Close everything but stdin/out/error */
for (x=STDERR_FILENO + 2;x<1024;x++)
close(x);
/* Execute script */
execv(script, argv);
The ast_log() will lock a mutex if appropriate, but the mutex may be in
locked state already.
Maybe we should use pthread_atfork() instead of fork() or never call some
functions that hold mutex
before execv() in child process.
Is there something that I missed?
--
Regards
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.digium.com/pipermail/asterisk-dev/attachments/20070406/57e8ba8f/attachment-0001.htm
More information about the asterisk-dev
mailing list