[asterisk-commits] russell: trunk r94252 - in /trunk: ./	channels/chan_zap.c
    SVN commits to the Asterisk project 
    asterisk-commits at lists.digium.com
       
    Thu Dec 20 14:16:22 CST 2007
    
    
  
Author: russell
Date: Thu Dec 20 14:16:21 2007
New Revision: 94252
URL: http://svn.digium.com/view/asterisk?view=rev&rev=94252
Log:
Merged revisions 94251 via svnmerge from 
https://origsvn.digium.com/svn/asterisk/branches/1.4
........
r94251 | russell | 2007-12-20 14:08:42 -0600 (Thu, 20 Dec 2007) | 10 lines
Fix a deadlock in d-channel handling in chan_zap.
This deadlock was introduced by the fix to ensure that channels are properly
locked when handling channel variables.  There were sections of this code where
the channel pvt was locked before the channel lock, when in fact it _must_ be
the other way around.
(closes issue #11582)
Reported by: bugi
........
Modified:
    trunk/   (props changed)
    trunk/channels/chan_zap.c
Propchange: trunk/
------------------------------------------------------------------------------
Binary property 'branch-1.4-merged' - no diff available.
Modified: trunk/channels/chan_zap.c
URL: http://svn.digium.com/view/asterisk/trunk/channels/chan_zap.c?view=diff&rev=94252&r1=94251&r2=94252
==============================================================================
--- trunk/channels/chan_zap.c (original)
+++ trunk/channels/chan_zap.c Thu Dec 20 14:16:21 2007
@@ -10206,6 +10206,9 @@
 							} else {
 								c = zt_new(pri->pvts[chanpos], AST_STATE_RESERVED, 0, SUB_REAL, law, e->ring.ctype);
 							}
+
+							ast_mutex_unlock(&pri->pvts[chanpos]->lock);
+
 							if (!ast_strlen_zero(e->ring.callingsubaddr)) {
 								pbx_builtin_setvar_helper(c, "CALLINGSUBADDR", e->ring.callingsubaddr);
 							}
@@ -10225,7 +10228,8 @@
 							pbx_builtin_setvar_helper(c, "CALLEDTON", calledtonstr);
 							if (e->ring.redirectingreason >= 0)
 								pbx_builtin_setvar_helper(c, "PRIREDIRECTREASON", redirectingreason2str(e->ring.redirectingreason));
-							
+						
+							ast_mutex_lock(&pri->pvts[chanpos]->lock);
 							ast_mutex_lock(&pri->lock);
 							if (c && !ast_pthread_create_detached(&threadid, NULL, ss_thread, c)) {
 								ast_verb(3, "Accepting overlap call from '%s' to '%s' on channel %d/%d, span %d\n",
@@ -10245,9 +10249,11 @@
 							ast_mutex_unlock(&pri->lock);
 							/* Release PRI lock while we create the channel */
 							c = zt_new(pri->pvts[chanpos], AST_STATE_RING, 1, SUB_REAL, law, e->ring.ctype);
-							ast_mutex_lock(&pri->lock);
 							if (c) {
 								char calledtonstr[10];
+
+								ast_mutex_unlock(&pri->pvts[chanpos]->lock);
+
 								if (e->ring.ani2 >= 0) {
 									snprintf(ani2str, 5, "%d", e->ring.ani2);
 									pbx_builtin_setvar_helper(c, "ANI2", ani2str);
@@ -10265,11 +10271,19 @@
 							
 								snprintf(calledtonstr, sizeof(calledtonstr)-1, "%d", e->ring.calledplan);
 								pbx_builtin_setvar_helper(c, "CALLEDTON", calledtonstr);
+
+								ast_mutex_lock(&pri->pvts[chanpos]->lock);
+								ast_mutex_lock(&pri->lock);
+
 								ast_verb(3, "Accepting call from '%s' to '%s' on channel %d/%d, span %d\n",
 										plancallingnum, pri->pvts[chanpos]->exten, 
-											pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
+										pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
+
 								zt_enable_ec(pri->pvts[chanpos]);
 							} else {
+
+								ast_mutex_lock(&pri->lock);
+
 								ast_log(LOG_WARNING, "Unable to start PBX on channel %d/%d, span %d\n", 
 									pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
 								pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_SWITCH_CONGESTION);
@@ -10328,7 +10342,10 @@
 
 #ifdef SUPPORT_USERUSER
 						if (!ast_strlen_zero(e->ringing.useruserinfo)) {
+							struct ast_channel *owner = pri->pvts[chanpos]->owner;
+							ast_mutex_unlock(&pri->pvts[chanpos]->lock);
 							pbx_builtin_setvar_helper(pri->pvts[chanpos]->owner, "USERUSERINFO", e->ringing.useruserinfo);
+							ast_mutex_lock(&pri->pvts[chanpos]->lock);
 						}
 #endif
 
@@ -10482,7 +10499,10 @@
 
 #ifdef SUPPORT_USERUSER
 						if (!ast_strlen_zero(e->answer.useruserinfo)) {
+							struct ast_channel *owner = pri->pvts[chanpos]->owner;
+							ast_mutex_unlock(&pri->pvts[chanpos]->lock);
 							pbx_builtin_setvar_helper(pri->pvts[chanpos]->owner, "USERUSERINFO", e->answer.useruserinfo);
+							ast_mutex_lock(&pri->pvts[chanpos]->lock);
 						}
 #endif
 
@@ -10545,7 +10565,10 @@
 
 #ifdef SUPPORT_USERUSER
 						if (pri->pvts[chanpos]->owner && !ast_strlen_zero(e->hangup.useruserinfo)) {
+							struct ast_channel *owner = pri->pvts[chanpos]->owner;
+							ast_mutex_unlock(&pri->pvts[chanpos]->lock);
 							pbx_builtin_setvar_helper(pri->pvts[chanpos]->owner, "USERUSERINFO", e->hangup.useruserinfo);
+							ast_mutex_lock(&pri->pvts[chanpos]->lock);
 						}
 #endif
 
@@ -10608,7 +10631,10 @@
 
 #ifdef SUPPORT_USERUSER
 						if (!ast_strlen_zero(e->hangup.useruserinfo)) {
+							struct ast_channel *owner = pri->pvts[chanpos]->owner;
+							ast_mutex_unlock(&pri->pvts[chanpos]->lock);
 							pbx_builtin_setvar_helper(pri->pvts[chanpos]->owner, "USERUSERINFO", e->hangup.useruserinfo);
+							ast_mutex_lock(&pri->pvts[chanpos]->lock);
 						}
 #endif
 
@@ -10635,7 +10661,10 @@
 
 #ifdef SUPPORT_USERUSER
 						if (!ast_strlen_zero(e->hangup.useruserinfo)) {
+							struct ast_channel *owner = pri->pvts[chanpos]->owner;
+							ast_mutex_unlock(&pri->pvts[chanpos]->lock);
 							pbx_builtin_setvar_helper(pri->pvts[chanpos]->owner, "USERUSERINFO", e->hangup.useruserinfo);
+							ast_mutex_lock(&pri->pvts[chanpos]->lock);
 						}
 #endif
 
    
    
More information about the asterisk-commits
mailing list