[asterisk-commits] rmudgett: branch rmudgett/bch_shift_v1.8 r311747 - /team/rmudgett/bch_shift_v...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Mon Mar 28 15:38:57 CDT 2011


Author: rmudgett
Date: Mon Mar 28 15:38:53 2011
New Revision: 311747

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=311747
Log:
RESTART and alarm interaction resulting in resetting flag getting stuck.

If the D channel goes down, any channels getting RESTARTed may get lost
because the RESTART ACKNOWLEDGEMENT may never arrive.

* Clear resetting flags when the D channel goes up or down.

* Clear the resetting flag when the channel alarm goes up or down.

* Fixed and documented locking assumption with
sig_pri_chan_alarm_notify().

Modified:
    team/rmudgett/bch_shift_v1.8/channels/chan_dahdi.c
    team/rmudgett/bch_shift_v1.8/channels/sig_pri.c

Modified: team/rmudgett/bch_shift_v1.8/channels/chan_dahdi.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/bch_shift_v1.8/channels/chan_dahdi.c?view=diff&rev=311747&r1=311746&r2=311747
==============================================================================
--- team/rmudgett/bch_shift_v1.8/channels/chan_dahdi.c (original)
+++ team/rmudgett/bch_shift_v1.8/channels/chan_dahdi.c Mon Mar 28 15:38:53 2011
@@ -11260,7 +11260,9 @@
 		switch (i->sig) {
 #if defined(HAVE_PRI)
 		case SIG_PRI_LIB_HANDLE_CASES:
+			ast_mutex_lock(&i->lock);
 			sig_pri_chan_alarm_notify(i->sig_pvt, 1);
+			ast_mutex_unlock(&i->lock);
 			break;
 #endif	/* defined(HAVE_PRI) */
 #if defined(HAVE_SS7)
@@ -11278,7 +11280,9 @@
 		switch (i->sig) {
 #if defined(HAVE_PRI)
 		case SIG_PRI_LIB_HANDLE_CASES:
+			ast_mutex_lock(&i->lock);
 			sig_pri_chan_alarm_notify(i->sig_pvt, 0);
+			ast_mutex_unlock(&i->lock);
 			break;
 #endif	/* defined(HAVE_PRI) */
 #if defined(HAVE_SS7)
@@ -12673,7 +12677,9 @@
 				switch (tmp->sig) {
 #ifdef HAVE_PRI
 				case SIG_PRI_LIB_HANDLE_CASES:
+					ast_mutex_lock(&tmp->lock);
 					sig_pri_chan_alarm_notify(tmp->sig_pvt, si.alarms);
+					ast_mutex_unlock(&tmp->lock);
 					break;
 #endif
 #if defined(HAVE_SS7)

Modified: team/rmudgett/bch_shift_v1.8/channels/sig_pri.c
URL: http://svnview.digium.com/svn/asterisk/team/rmudgett/bch_shift_v1.8/channels/sig_pri.c?view=diff&rev=311747&r1=311746&r2=311747
==============================================================================
--- team/rmudgett/bch_shift_v1.8/channels/sig_pri.c (original)
+++ team/rmudgett/bch_shift_v1.8/channels/sig_pri.c Mon Mar 28 15:38:53 2011
@@ -4691,11 +4691,12 @@
 					pri->lastreset -= pri->resetinterval;
 					pri->lastreset += 5;
 				}
+				/* Take the channels from inalarm condition */
 				pri->resetting = 0;
-				/* Take the channels from inalarm condition */
 				for (i = 0; i < pri->numchans; i++) {
 					if (pri->pvts[i]) {
 						sig_pri_set_alarm(pri->pvts[i], 0);
+						pri->pvts[i]->resetting = 0;
 					}
 				}
 				sig_pri_span_devstate_changed(pri);
@@ -4703,29 +4704,28 @@
 			case PRI_EVENT_DCHAN_DOWN:
 				pri_find_dchan(pri);
 				if (!pri_is_up(pri)) {
-					pri->resetting = 0;
 					if (pri->sig == SIG_BRI_PTMP) {
 						/* For PTMP connections with non persistent layer 2 we want
 						 * to *not* declare inalarm unless there actually is an alarm */
 						break;
 					}
 					/* Hangup active channels and put them in alarm mode */
+					pri->resetting = 0;
 					for (i = 0; i < pri->numchans; i++) {
 						struct sig_pri_chan *p = pri->pvts[i];
+
 						if (p) {
-							if (!p->pri || !p->pri->pri || pri_get_timer(p->pri->pri, PRI_TIMER_T309) < 0) {
+							if (pri_get_timer(p->pri->pri, PRI_TIMER_T309) < 0) {
 								/* T309 is not enabled : destroy calls when alarm occurs */
 								if (p->call) {
-									if (p->pri && p->pri->pri) {
-										pri_destroycall(p->pri->pri, p->call);
-										p->call = NULL;
-									} else
-										ast_log(LOG_WARNING, "The PRI Call have not been destroyed\n");
+									pri_destroycall(p->pri->pri, p->call);
+									p->call = NULL;
 								}
 								if (p->owner)
 									p->owner->_softhangup |= AST_SOFTHANGUP_DEV;
 							}
 							sig_pri_set_alarm(p, 1);
+							p->resetting = 0;
 						}
 					}
 					sig_pri_span_devstate_changed(pri);
@@ -5999,24 +5999,22 @@
 							PRI_CHANNEL(e->restartack.channel));
 					}
 				} else {
-					if (pri->pvts[chanpos]) {
-						sig_pri_lock_private(pri->pvts[chanpos]);
-						if (pri->pvts[chanpos]->owner) {
-							ast_log(LOG_WARNING,
-								"Span %d: Got restart ack on channel %d/%d with owner\n",
-								pri->span, pri->pvts[chanpos]->logicalspan,
-								pri->pvts[chanpos]->prioffset);
-							pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
-						}
-						pri->pvts[chanpos]->resetting = 0;
-						ast_verb(3,
-							"Span %d: Channel %d/%d successfully restarted\n",
+					sig_pri_lock_private(pri->pvts[chanpos]);
+					if (pri->pvts[chanpos]->owner) {
+						ast_log(LOG_WARNING,
+							"Span %d: Got restart ack on channel %d/%d with owner\n",
 							pri->span, pri->pvts[chanpos]->logicalspan,
 							pri->pvts[chanpos]->prioffset);
-						sig_pri_unlock_private(pri->pvts[chanpos]);
-						if (pri->resetting)
-							pri_check_restart(pri);
+						pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
 					}
+					pri->pvts[chanpos]->resetting = 0;
+					ast_verb(3,
+						"Span %d: Channel %d/%d successfully restarted\n",
+						pri->span, pri->pvts[chanpos]->logicalspan,
+						pri->pvts[chanpos]->prioffset);
+					sig_pri_unlock_private(pri->pvts[chanpos]);
+					if (pri->resetting)
+						pri_check_restart(pri);
 				}
 				break;
 			case PRI_EVENT_SETUP_ACK:
@@ -7555,28 +7553,34 @@
 	return 0;
 }
 
+/*!
+ * \brief Notify new alarm status.
+ *
+ * \param p Channel private pointer.
+ * \param noalarm Non-zero if not in alarm mode.
+ * 
+ * \note Assumes the sig_pri_lock_private(p) is already obtained.
+ *
+ * \return Nothing
+ */
 void sig_pri_chan_alarm_notify(struct sig_pri_chan *p, int noalarm)
 {
+	pri_grab(p, p->pri);
+	p->resetting = 0;
 	sig_pri_set_alarm(p, !noalarm);
 	if (!noalarm) {
-		if (!p->pri || !p->pri->pri || (pri_get_timer(p->pri->pri, PRI_TIMER_T309) < 0)) {
+		if (pri_get_timer(p->pri->pri, PRI_TIMER_T309) < 0) {
 			/* T309 is not enabled : destroy calls when alarm occurs */
 			if (p->call) {
-				if (p->pri && p->pri->pri) {
-					if (!pri_grab(p, p->pri)) {
-						pri_destroycall(p->pri->pri, p->call);
-						p->call = NULL;
-						sig_pri_span_devstate_changed(p->pri);
-						pri_rel(p->pri);
-					} else
-						ast_log(LOG_WARNING, "Failed to grab PRI!\n");
-				} else
-					ast_log(LOG_WARNING, "The PRI Call has not been destroyed\n");
+				pri_destroycall(p->pri->pri, p->call);
+				p->call = NULL;
 			}
 			if (p->owner)
 				p->owner->_softhangup |= AST_SOFTHANGUP_DEV;
 		}
 	}
+	sig_pri_span_devstate_changed(p->pri);
+	pri_rel(p->pri);
 }
 
 struct sig_pri_chan *sig_pri_chan_new(void *pvt_data, struct sig_pri_callback *callback, struct sig_pri_span *pri, int logicalspan, int channo, int trunkgroup)




More information about the asterisk-commits mailing list