@ -1484,7 +1484,7 @@ static int make_trunk(unsigned short callno, int locked)
*
* \ note Calling this function while holding another pvt lock can cause a deadlock .
*/
static int find_callno( unsigned short callno , unsigned short dcallno , struct sockaddr_in * sin , int new , int sockf d)
static int __ find_callno( unsigned short callno , unsigned short dcallno , struct sockaddr_in * sin , int new , int sockf d, int return_locke d)
{
int res = 0 ;
int x ;
@ -1560,12 +1560,23 @@ static int find_callno(unsigned short callno, unsigned short dcallno, struct soc
ast_mutex_unlock ( & iaxsl [ x ] ) ;
return 0 ;
}
ast_mutex_unlock ( & iaxsl [ x ] ) ;
if ( ! return_locked )
ast_mutex_unlock ( & iaxsl [ x ] ) ;
res = x ;
}
return res ;
}
static int find_callno ( unsigned short callno , unsigned short dcallno , struct sockaddr_in * sin , int new , int sockfd ) {
return __find_callno ( callno , dcallno , sin , new , sockfd , 0 ) ;
}
static int find_callno_locked ( unsigned short callno , unsigned short dcallno , struct sockaddr_in * sin , int new , int sockfd ) {
return __find_callno ( callno , dcallno , sin , new , sockfd , 1 ) ;
}
static void iax2_frame_free ( struct iax_frame * fr )
{
AST_SCHED_DEL ( sched , fr - > retrans ) ;
@ -3888,6 +3899,13 @@ static struct ast_channel *ast_iax2_new(int callno, int state, int capability)
ast_mutex_unlock ( & iaxsl [ callno ] ) ;
tmp = ast_channel_alloc ( 1 , state , i - > cid_num , i - > cid_name , i - > accountcode , i - > exten , i - > context , i - > amaflags , " IAX2/%s-%d " , i - > host , i - > callno ) ;
ast_mutex_lock ( & iaxsl [ callno ] ) ;
if ( ! iaxs [ callno ] ) {
if ( tmp ) {
ast_channel_free ( tmp ) ;
}
ast_mutex_unlock ( & iaxsl [ callno ] ) ;
return NULL ;
}
iax2_ami_channelupdate ( i ) ;
if ( ! tmp )
return NULL ;
@ -7589,12 +7607,10 @@ static int socket_process_meta(int packet_len, struct ast_iax2_meta_hdr *meta, s
/* Stop if we don't have enough data */
if ( len > packet_len )
break ;
fr - > callno = find_callno ( callno & ~ IAX_FLAG_FULL , 0 , sin , NEW_PREVENT , sockfd ) ;
fr - > callno = find_callno _locked ( callno & ~ IAX_FLAG_FULL , 0 , sin , NEW_PREVENT , sockfd ) ;
if ( ! fr - > callno )
continue ;
ast_mutex_lock ( & iaxsl [ fr - > callno ] ) ;
/* If it's a valid call, deliver the contents. If not, we
drop it , since we don ' t have a scallno to use for an INVAL */
/* Process as a mini frame */
@ -7973,7 +7989,9 @@ static int socket_process(struct iax2_thread *thread)
if ( call_to_destroy ) {
if ( iaxdebug )
ast_debug ( 1 , " Really destroying %d, having been acked on final message \n " , call_to_destroy ) ;
ast_mutex_lock ( & iaxsl [ call_to_destroy ] ) ;
iax2_destroy ( call_to_destroy ) ;
ast_mutex_unlock ( & iaxsl [ call_to_destroy ] ) ;
}
}
/* Note how much we've received acknowledgement for */
@ -9389,13 +9407,14 @@ static int iax2_do_register(struct iax2_registry *reg)
if ( ! reg - > callno ) {
ast_debug ( 1 , " Allocate call number \n " ) ;
reg - > callno = find_callno ( 0 , 0 , & reg - > addr , NEW_FORCE , defaultsockfd ) ;
reg - > callno = find_callno _locked ( 0 , 0 , & reg - > addr , NEW_FORCE , defaultsockfd ) ;
if ( reg - > callno < 1 ) {
ast_log ( LOG_WARNING , " Unable to create call for registration \n " ) ;
return - 1 ;
} else
ast_debug ( 1 , " Registration created on call %d \n " , reg - > callno ) ;
iaxs [ reg - > callno ] - > reg = reg ;
ast_mutex_unlock ( & iaxsl [ reg - > callno ] ) ;
}
/* Setup the next registration a little early */
reg - > expire = iax2_sched_replace ( reg - > expire , sched ,
@ -9439,11 +9458,10 @@ static int iax2_provision(struct sockaddr_in *end, int sockfd, char *dest, const
memset ( & ied , 0 , sizeof ( ied ) ) ;
iax_ie_append_raw ( & ied , IAX_IE_PROVISIONING , provdata . buf , provdata . pos ) ;
callno = find_callno ( 0 , 0 , & sin , NEW_FORCE , cai . sockfd ) ;
callno = find_callno _locked ( 0 , 0 , & sin , NEW_FORCE , cai . sockfd ) ;
if ( ! callno )
return - 1 ;
ast_mutex_lock ( & iaxsl [ callno ] ) ;
if ( iaxs [ callno ] ) {
/* Schedule autodestruct in case they don't ever give us anything back */
iaxs [ callno ] - > autoid = iax2_sched_replace ( iaxs [ callno ] - > autoid ,
@ -9675,15 +9693,13 @@ static struct ast_channel *iax2_request(const char *type, int format, void *data
if ( pds . port )
sin . sin_port = htons ( atoi ( pds . port ) ) ;
callno = find_callno ( 0 , 0 , & sin , NEW_FORCE , cai . sockfd ) ;
callno = find_callno _locked ( 0 , 0 , & sin , NEW_FORCE , cai . sockfd ) ;
if ( callno < 1 ) {
ast_log ( LOG_WARNING , " Unable to create call \n " ) ;
* cause = AST_CAUSE_CONGESTION ;
return NULL ;
}
ast_mutex_lock ( & iaxsl [ callno ] ) ;
/* If this is a trunk, update it now */
ast_copy_flags ( iaxs [ callno ] , & cai , IAX_TRUNK | IAX_SENDANI | IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF | IAX_FORCEJITTERBUF ) ;
if ( ast_test_flag ( & cai , IAX_TRUNK ) ) {
@ -11044,13 +11060,12 @@ static int cache_get_callno_locked(const char *data)
ast_debug ( 1 , " peer: %s, username: %s, password: %s, context: %s \n " ,
pds . peer , pds . username , pds . password , pds . context ) ;
callno = find_callno ( 0 , 0 , & sin , NEW_FORCE , cai . sockfd ) ;
callno = find_callno _locked ( 0 , 0 , & sin , NEW_FORCE , cai . sockfd ) ;
if ( callno < 1 ) {
ast_log ( LOG_WARNING , " Unable to create call \n " ) ;
return - 1 ;
}
ast_mutex_lock ( & iaxsl [ callno ] ) ;
ast_string_field_set ( iaxs [ callno ] , dproot , data ) ;
iaxs [ callno ] - > capability = IAX_CAPABILITY_FULLBANDWIDTH ;