[asterisk-commits] rizzo: branch rizzo/astobj2 r77649 - /team/rizzo/astobj2/channels/chan_sip.c

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Sat Jul 28 12:06:48 CDT 2007


Author: rizzo
Date: Sat Jul 28 12:06:44 2007
New Revision: 77649

URL: http://svn.digium.com/view/asterisk?view=rev&rev=77649
Log:
mostly merge from trunk (rename a field from "register_pvt" to "call"),
but also cleanup the logic in __sip_autodestruct() and add a missing
dialog_unref()


Modified:
    team/rizzo/astobj2/channels/chan_sip.c

Modified: team/rizzo/astobj2/channels/chan_sip.c
URL: http://svn.digium.com/view/asterisk/team/rizzo/astobj2/channels/chan_sip.c?view=diff&rev=77649&r1=77648&r2=77649
==============================================================================
--- team/rizzo/astobj2/channels/chan_sip.c (original)
+++ team/rizzo/astobj2/channels/chan_sip.c Sat Jul 28 12:06:44 2007
@@ -1369,7 +1369,7 @@
 	int regattempts;		/*!< Number of attempts (since the last success) */
 	int timeout; 			/*!< sched id of next event */
 	int refresh;			/*!< How often to refresh */
-	struct sip_pvt *register_pvt;		/*!< create a sip_pvt structure for each outbound "registration dialog" in progress */
+	struct sip_pvt *call;		/*!< create a sip_pvt structure for each outbound "registration dialog" in progress */
 	enum sipregistrystate regstate;	/*!< Registration state (see above) */
 	struct timeval regtime;			/*!< Last successful registration time */
 	int callid_valid;		/*!< 0 means we haven't chosen callid for this registry yet. */
@@ -1936,12 +1936,12 @@
 	/* Really delete */
 	ast_debug(3, "Destroying registry entry for %s@%s\n", reg->username, reg->hostname);
 
-	if (reg->register_pvt) {
+	if (reg->call) {
 		/* Clear registry before destroying to ensure
 		   we don't get reentered trying to grab the registry lock */
-		reg->register_pvt->registry = NULL;	/* XXX cannot be different or we would not be here! */
+		reg->call->registry = NULL;	/* XXX cannot be different or we would not be here! */
 		ast_debug(3, "Destroying active SIP dialog for registry %s@%s\n", reg->username, reg->hostname);
-		reg->register_pvt = sip_destroy(reg->register_pvt);
+		reg->call = sip_destroy(reg->call);
 	}
 	if (reg->timeout > -1)
 		ast_sched_del(sched, reg->timeout);
@@ -2467,7 +2467,9 @@
 }
 
 /*! \brief Kill a SIP dialog (called by scheduler)
- * We have a reference to the pvt, so we need to release it when done
+ * The scheduler has a reference to this dialog when p->autokillid != -1,
+ * and we are called using that reference. So if the event is not
+ * rescheduled, we need to call dialog_unref().
  */
 static int __sip_autodestruct(void *data)
 {
@@ -2492,6 +2494,7 @@
 	if (p->owner) {
 		ast_log(LOG_WARNING, "Autodestruct on dialog '%s' with owner in place (Method: %s)\n", p->callid, sip_methods[p->method].text);
 		ast_queue_hangup(p->owner);
+		dialog_unref(p);
 	} else if (p->refer) {
 		ast_debug(3, "Finally hanging up channel after transfer: %s\n", p->callid);
 		transmit_request_with_auth(p, SIP_BYE, 0, XMIT_RELIABLE, 1);
@@ -2507,7 +2510,9 @@
 	return 0;
 }
 
-/*! \brief Schedule destruction of SIP dialog */
+/*! \brief Schedule destruction of SIP dialog.
+ * This function does not consume any reference to p.
+ */
 static void sip_scheddestroy(struct sip_pvt *p, int ms)
 {
 	if (ms < 0) {
@@ -2517,14 +2522,10 @@
 	}
 	if (sip_debug_test_pvt(p))
 		ast_verbose("Scheduling destruction of SIP dialog '%s' in %d ms (Method: %s)\n", p->callid, ms, sip_methods[p->method].text);
+	sip_cancel_destroy(p);
 	if (p->do_history)
 		append_history(p, "SchedDestroy", "%d ms", ms);
-
-	if (p->autokillid > -1)	/* cancel previous schedule, but keep the reference */
-		ast_sched_del(sched, p->autokillid);
-	else
-		dialog_ref(p);	/* create a new reference */
-	p->autokillid = ast_sched_add(sched, ms, __sip_autodestruct, p);
+	p->autokillid = ast_sched_add(sched, ms, __sip_autodestruct, dialog_ref(p));
 }
 
 /*! \brief Cancel destruction of SIP dialog */
@@ -3620,8 +3621,8 @@
 		 * in any case, if it is for ourselves, the destructor
 		 * would not be called in astobj2
 		 */
-		if (p->registry->register_pvt == p)
-			p->registry->register_pvt = dialog_unref(p->registry->register_pvt);
+		if (p->registry->call == p)
+			p->registry->call = dialog_unref(p->registry->call);
 		p->registry = registry_unref(p->registry);
 	}
 
@@ -8089,10 +8090,10 @@
 	struct sip_registry *r = data;
 
 	r->timeout = -1;	/* old event, now gone */
-	if (r->register_pvt) {
+	if (r->call) {
 		ast_log(LOG_WARNING, "-- sip_reregister should not have a pvt %p (%s@%s)\n",
-			r->register_pvt, r->username, r->hostname);
-		r->register_pvt = dialog_unref(r->register_pvt);
+			r->call, r->username, r->hostname);
+		r->call = dialog_unref(r->call);
 	}
 
 	/* Since registry's are only added/removed by the the monitor thread, this
@@ -8120,14 +8121,14 @@
 	r->timeout = -1;	/* reset event reference */
 	ast_log(LOG_NOTICE, "   -- Registration for '%s@%s' timed out, trying again (Attempt #%d)\n", r->username, r->hostname, r->regattempts); 
 	/* if the initial tranmission failed, we may not have an existing dialog,
-	 * so it is possible that r->register_pvt == NULL.
+	 * so it is possible that r->call == NULL.
 	 * In any case we have a timeout so we don't want it.
 	 */
-	if (r->register_pvt) {
+	if (r->call) {
 		/* Unlink us, destroy old call.  Locking is not relevant here because all this happens
 		   in the single SIP manager thread. */
 		/* XXX p->registry == r so and r has 2 refs, so the unref won't take the object away */
-		p = r->register_pvt;
+		p = r->call;
 		p->needdestroy = 1;	/* XXX why do that if we are going to kill it in a moment ? */
 		/* Pretend to ACK anything just in case */
 		__sip_pretend_ack(p); /* XXX we need p locked, not sure we have */
@@ -8135,7 +8136,7 @@
 		/* decouple the two objects */
 		if (p->registry)
 			p->registry = registry_unref(p->registry);
-		r->register_pvt = dialog_unref(r->register_pvt);	/* reference goes away */
+		r->call = dialog_unref(r->call);	/* reference goes away */
 	}
 
 	/* If we have a limit, stop registration and give up */
@@ -8179,12 +8180,12 @@
 	}
 
 	r->regattempts++;
-	if (r->register_pvt) {	/* We have a registration */
+	if (r->call) {	/* We have a registration */
 		if (!auth) {
 			ast_log(LOG_WARNING, "Already have a REGISTER going on to %s@%s?? \n", r->username, r->hostname);
 			return 0;
 		} else {
-			p = dialog_ref(r->register_pvt);	/* grab a reference */
+			p = dialog_ref(r->call);	/* grab a reference */
 			make_our_tag(p->tag, sizeof(p->tag));	/* create a new local tag for every register attempt */
 			ast_string_field_free(p, theirtag);	/* forget their old tag, so we don't match tags when getting response */
 		}
@@ -8219,7 +8220,7 @@
 		else 	/* Set registry port to the port set from the peer definition/srv or default */
 			r->portno = ntohs(p->sa.sin_port);
 		ast_set_flag(&p->flags[0], SIP_OUTGOING);	/* Registration is outgoing call */
-		r->register_pvt = dialog_ref(p);			/* Save pointer to SIP dialog */
+		r->call = dialog_ref(p);			/* Save pointer to SIP dialog */
 		p->registry = registry_addref(r);	/* Add pointer to registry in dialog */
 		if (!ast_strlen_zero(r->secret))	/* Secret (password) */
 			ast_string_field_set(p, secret, r->secret);
@@ -13376,14 +13377,14 @@
 {
 	struct sip_registry *r = p->registry;
 
-	r->register_pvt = dialog_unref(r->register_pvt);
+	r->call = dialog_unref(r->call);
 	p->registry = registry_unref(r);
 	p->needdestroy = 1;
 }
 
 /*! \brief Handle responses on REGISTER to services.
  * In principle, we should have p->registry != NULL,
- * and p->registry->register_pvt == p, otherwise there is
+ * and p->registry->call == p, otherwise there is
  * something bogus.
  */
 static int handle_response_register(struct sip_pvt *p, int resp, char *rest, struct sip_request *req, int seqno)
@@ -13391,11 +13392,11 @@
 	int expires, expires_ms;
 	struct sip_registry *r = p->registry;
 
-	if (r == NULL || r->register_pvt != p) {
+	if (r == NULL || r->call != p) {
 		if (r == NULL)
 			ast_log(LOG_WARNING, "Got %d on REGISTER but we have no sip_registry entry", resp);
 		else
-			ast_log(LOG_WARNING, "Got %d on REGISTER, but mismatched link p %p reg->p %p", resp, p, r->register_pvt);
+			ast_log(LOG_WARNING, "Got %d on REGISTER, but mismatched link p %p reg->p %p", resp, p, r->call);
 		p->needdestroy = 1;
 		return 1;
 	}
@@ -18694,10 +18695,10 @@
 	/* This is needed, since otherwise active registry entries will not be destroyed */
 	ASTOBJ_CONTAINER_TRAVERSE(&regl, 1, do {
 		ASTOBJ_RDLOCK(iterator);
-		if (iterator->register_pvt) {
+		if (iterator->call) {
 			ast_debug(3, "Destroying active SIP dialog for registry %s@%s\n", iterator->username, iterator->hostname);
 			/* This will also remove references to the registry */
-			iterator->register_pvt = sip_destroy(iterator->register_pvt);
+			iterator->call = sip_destroy(iterator->call);
 		}
 		ASTOBJ_UNLOCK(iterator);
 	} while(0));




More information about the asterisk-commits mailing list