diff -ur asterisk-1.4.2.orig/channels/chan_iax2.c asterisk-1.4.2/channels/chan_iax2.c --- asterisk-1.4.2.orig/channels/chan_iax2.c 2007-03-15 14:13:21.000000000 -0400 +++ asterisk-1.4.2/channels/chan_iax2.c 2007-05-02 16:27:38.000000000 -0400 @@ -1841,8 +1841,12 @@ fr.subclass = AST_CONTROL_HANGUP; iax2_queue_frame(callno, &fr); /* Remember, owner could disappear */ - if (iaxs[callno]->owner) - iaxs[callno]->owner->hangupcause = AST_CAUSE_DESTINATION_OUT_OF_ORDER; + if ( iaxs[callno] ) { + if (iaxs[callno]->owner) + iaxs[callno]->owner->hangupcause = AST_CAUSE_DESTINATION_OUT_OF_ORDER; + } else { + ast_log(LOG_WARNING, "Potential race condition detected in __attempt_transmit\n"); + } } else { if (iaxs[callno]->reg) { memset(&iaxs[callno]->reg->us, 0, sizeof(iaxs[callno]->reg->us)); @@ -2242,6 +2246,14 @@ case JB_OK: fr = frame.data; __do_deliver(fr); + + /* __do_deliver calls iax2_queue_frame,that releases the iaxsl[callno] mutex, so anybody can barge in and ruin the party + * We need to check that we still have the goods */ + if ( !iaxs[callno] ) + { + ast_log(LOG_WARNING, "Potential race condition in __get_from_jb (JB_OK)\n"); + pvt = NULL; + } break; case JB_INTERP: { @@ -2259,6 +2271,14 @@ * which we'd need to malloc, and then it would free it. That seems like a drag */ if (!ast_test_flag(iaxs[callno], IAX_ALREADYGONE)) iax2_queue_frame(callno, &af); + + /* iax2_queue_frame releases the iaxsl[callno] mutex, so anybody can barge in and ruin the party + * We need to check that we still have the goods */ + if ( !iaxs[callno] ) + { + ast_log(LOG_WARNING, "Potential race condition in __get_from_jb (JB_INTERP)\n"); + pvt = NULL; + } } break; case JB_DROP: @@ -2273,7 +2293,8 @@ break; } } - update_jbsched(pvt); + if ( pvt ) + update_jbsched(pvt); ast_mutex_unlock(&iaxsl[callno]); } @@ -2334,13 +2355,17 @@ while(jb_getall(iaxs[fr->callno]->jb,&frame) == JB_OK) __do_deliver(frame.data); - jb_reset(iaxs[fr->callno]->jb); - - if (iaxs[fr->callno]->jbid > -1) - ast_sched_del(sched, iaxs[fr->callno]->jbid); - - iaxs[fr->callno]->jbid = -1; - + if ( iaxs[fr->callno] ) { + jb_reset(iaxs[fr->callno]->jb); + + if (iaxs[fr->callno]->jbid > -1) + ast_sched_del(sched, iaxs[fr->callno]->jbid); + + iaxs[fr->callno]->jbid = -1; + } else { + ast_log(LOG_WARNING, "Potential race condition detected in schedule_delivery\n"); + } + /* deliver this frame now */ if (tsout) *tsout = fr->ts;