diff --git a/daemon/t38.c b/daemon/t38.c index 1162db55a..2117ff800 100644 --- a/daemon/t38.c +++ b/daemon/t38.c @@ -283,12 +283,17 @@ static void t38_pcm_player(struct media_player *mp) { ilog(LOG_DEBUG, "Generated %i T.38 PCM samples", num); - // this reschedules our player as well - media_player_add_packet(tg->pcm_player, (char *) smp, num * 2, num * 1000000 / 8000, tg->pts); - + // release gateway lock as the media player may trigger a lock on the SSRC objects + // and this is the wrong lock order + struct media_player *pcm_player = media_player_get(tg->pcm_player); + unsigned long long pts = tg->pts; tg->pts += num; mutex_unlock(&tg->lock); + + // this reschedules our player as well + media_player_add_packet(pcm_player, (char *) smp, num * 2, num * 1000000 / 8000, pts); + media_player_put(&pcm_player); } diff --git a/include/media_player.h b/include/media_player.h index 517dc4154..3f9da1a95 100644 --- a/include/media_player.h +++ b/include/media_player.h @@ -60,11 +60,20 @@ INLINE void media_player_put(struct media_player **mp) { obj_put(&(*mp)->tt_obj); *mp = NULL; } +INLINE struct media_player *media_player_get(struct media_player *mp) { + if (!mp) + return NULL; + obj_hold(&mp->tt_obj); + return mp; +} #else INLINE void media_player_put(struct media_player **mp) { } +INLINE struct media_player *media_player_get(struct media_player *mp) { + return NULL; +} #endif