Fixed deadlock in conference when starting sound device in Linux

git-svn-id: https://svn.pjsip.org/repos/pjproject/trunk@246 74dad513-b988-da41-8d7b-12977e46ad98
This commit is contained in:
Benny Prijono 2006-02-27 23:53:34 +00:00
parent fa994facfb
commit 09e265014a
1 changed files with 16 additions and 7 deletions

View File

@ -30,7 +30,7 @@
//#define CONF_DEBUG //#define CONF_DEBUG
#ifdef CONF_DEBUG #ifdef CONF_DEBUG
# include <stdio.h> # include <stdio.h>
# define TRACE_(x) printf x # define TRACE_(x) {printf x; fflush(stdout); }
#else #else
# define TRACE_(x) # define TRACE_(x)
#endif #endif
@ -266,7 +266,7 @@ PJ_DEF(pj_status_t) pjmedia_conf_create( pj_pool_t *pool,
sizeof(conf->uns_buf[0])); sizeof(conf->uns_buf[0]));
/* Create mutex. */ /* Create mutex. */
status = pj_mutex_create_simple(pool, "conf", &conf->mutex); status = pj_mutex_create_recursive(pool, "conf", &conf->mutex);
if (status != PJ_SUCCESS) if (status != PJ_SUCCESS)
return status; return status;
@ -460,6 +460,7 @@ PJ_DEF(pj_status_t) pjmedia_conf_connect_port( pjmedia_conf *conf,
unsigned sink_slot ) unsigned sink_slot )
{ {
struct conf_port *src_port, *dst_port; struct conf_port *src_port, *dst_port;
pj_bool_t start_sound = PJ_FALSE;
/* Check arguments */ /* Check arguments */
PJ_ASSERT_RETURN(conf && src_slot<conf->max_ports && PJ_ASSERT_RETURN(conf && src_slot<conf->max_ports &&
@ -480,7 +481,7 @@ PJ_DEF(pj_status_t) pjmedia_conf_connect_port( pjmedia_conf *conf,
++src_port->listener_cnt; ++src_port->listener_cnt;
if (conf->connect_cnt == 1) if (conf->connect_cnt == 1)
resume_sound(conf); start_sound = 1;
PJ_LOG(4,(THIS_FILE,"Port %.*s transmitting to port %.*s", PJ_LOG(4,(THIS_FILE,"Port %.*s transmitting to port %.*s",
(int)src_port->name.slen, (int)src_port->name.slen,
@ -491,6 +492,12 @@ PJ_DEF(pj_status_t) pjmedia_conf_connect_port( pjmedia_conf *conf,
pj_mutex_unlock(conf->mutex); pj_mutex_unlock(conf->mutex);
/* Sound device must be started without mutex, otherwise the
* sound thread will deadlock (?)
*/
if (start_sound)
resume_sound(conf);
return PJ_SUCCESS; return PJ_SUCCESS;
} }
@ -680,10 +687,10 @@ static pj_status_t play_cb( /* in */ void *user_data,
PJ_UNUSED_ARG(timestamp); PJ_UNUSED_ARG(timestamp);
PJ_UNUSED_ARG(size); PJ_UNUSED_ARG(size);
TRACE_(("p"));
pj_mutex_lock(conf->mutex); pj_mutex_lock(conf->mutex);
TRACE_(("p"));
/* Zero all port's temporary buffers. */ /* Zero all port's temporary buffers. */
for (i=0, ci=0; i<conf->max_ports && ci < conf->port_cnt; ++i) { for (i=0, ci=0; i<conf->max_ports && ci < conf->port_cnt; ++i) {
struct conf_port *conf_port = conf->ports[i]; struct conf_port *conf_port = conf->ports[i];
@ -913,12 +920,14 @@ static pj_status_t rec_cb( /* in */ void *user_data,
} }
/* Skip if this port is muted/disabled. */ /* Skip if this port is muted/disabled. */
if (snd_port->rx_setting != PJMEDIA_PORT_ENABLE) if (snd_port->rx_setting != PJMEDIA_PORT_ENABLE) {
return PJ_SUCCESS; return PJ_SUCCESS;
}
/* Skip if no port is listening to the microphone */ /* Skip if no port is listening to the microphone */
if (snd_port->listener_cnt == 0) if (snd_port->listener_cnt == 0) {
return PJ_SUCCESS; return PJ_SUCCESS;
}
/* Determine which rx_buffer to fill in */ /* Determine which rx_buffer to fill in */