[asterisk-scf-commits] asterisk-scf/integration/sip.git branch "master" updated.

Commits to the Asterisk SCF project code repositories asterisk-scf-commits at lists.digium.com
Tue Sep 14 17:50:23 CDT 2010


branch "master" has been updated
       via  40408d535a5cc2797127bb0df0f96071c5a6783a (commit)
       via  3075cbaea7770996b971bfc3054a3ee5d6f5d91c (commit)
       via  fb521666e3b325386edc63bd7a15523bf46d0756 (commit)
      from  3b8ed438ff28ba3f347157df2fc57264f2f69d33 (commit)

Summary of changes:
 local-slice/SipStateReplicationIf.ice |    2 +-
 src/PJSipSessionModule.cpp            |  152 +++++++++++++++++++++++++++++++-
 2 files changed, 148 insertions(+), 6 deletions(-)


- Log -----------------------------------------------------------------
commit 40408d535a5cc2797127bb0df0f96071c5a6783a
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 14 17:50:31 2010 -0500

    Add TransactionState item for PJSipSessionModule to use.
    
    Also changed the name of the transaction state item in the slice to
    be more in line with the dialog state item name.

diff --git a/local-slice/SipStateReplicationIf.ice b/local-slice/SipStateReplicationIf.ice
index e6cf259..bab37db 100644
--- a/local-slice/SipStateReplicationIf.ice
+++ b/local-slice/SipStateReplicationIf.ice
@@ -71,7 +71,7 @@ module V1
 	  TransactionStateDestroyed
    };
 
-   class TransactionStateItem extends SipStateItem
+   class SipTransactionStateItem extends SipStateItem
    {
       string mBranch;
 	  TransactionState mCurrentState;
diff --git a/src/PJSipSessionModule.cpp b/src/PJSipSessionModule.cpp
index 47178d0..ca8bfce 100644
--- a/src/PJSipSessionModule.cpp
+++ b/src/PJSipSessionModule.cpp
@@ -105,7 +105,6 @@ public:
 	  mDialogState->mTransport = "UDP";
 	  mNeedsUpdate = true;
    }
-
    /**
 	* The associated dialog information. Used for state replication
 	*/
@@ -118,6 +117,60 @@ public:
    bool mNeedsUpdate;
 };
 
+class PJSipTransactionModInfo
+{
+   PJSipTransactionModInfo(pjsip_transaction *transaction) : mTransactionState(new SipTransactionStateItem), mNeedsUpdate(true)
+   {
+      mTransactionState->mId = IceUtil::generateUUID();
+	  updateTransactionState(transaction);
+   }
+   void updateTransactionState(pjsip_transaction *transaction)
+   {
+      mTransactionState->mBranch = std::string(pj_strbuf(&transaction->branch), pj_strlen(&transaction->branch));
+	  mTransactionState->mIsClient = (transaction->role == PJSIP_ROLE_UAC || transaction->role == PJSIP_UAC_ROLE) ? true : false;
+	  mTransactionState->mCurrentState = transactionStateTranslate(transaction->state);
+   }
+private:
+   TransactionState transactionStateTranslate(pjsip_tsx_state_e state)
+   {
+      TransactionState retState;
+      switch (state)
+	  {
+	  case PJSIP_TSX_STATE_NULL:
+	     retState = TransactionStateNull;
+		 break;
+	  case PJSIP_TSX_STATE_CALLING:
+	     retState = TransactionStateCalling;
+		 break;
+	  case PJSIP_TSX_STATE_TRYING:
+	     retState = TransactionStateTrying;
+		 break;
+	  case PJSIP_TSX_STATE_PROCEEDING:
+	     retState = TransactionStateProceeding;
+		 break;
+	  case PJSIP_TSX_STATE_COMPLETED:
+	     retState = TransactionStateCompleted;
+		 break;
+	  case PJSIP_TSX_STATE_CONFIRMED:
+	     retState = TransactionStateConfirmed;
+		 break;
+	  case PJSIP_TSX_STATE_TERMINATED:
+	     retState = TransactionStateTerminated;
+		 break;
+	  case PJSIP_TSX_STATE_DESTROYED:
+	     retState = TransactionStateDestroyed;
+		 break;
+	  default:
+	     std::cerr << "[ERROR] Unknown PJSIP Transaction state encountered: " << state << std::endl;
+		 retState = TransactionStateNull;
+		 break;
+	  }
+	  return retState;
+   }
+   SipTransactionStateItemPtr mTransactionState;
+   bool mNeedsUpdate;
+};
+
 static pj_status_t sessionLoad(pjsip_endpoint *endpt)
 {
 	//stub

commit 3075cbaea7770996b971bfc3054a3ee5d6f5d91c
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 14 16:12:08 2010 -0500

    Use the new PJSipDialogModData structure for dialog mod_data and move the
    session into the inv_session's mod_data.

diff --git a/src/PJSipSessionModule.cpp b/src/PJSipSessionModule.cpp
index 9e1f40b..47178d0 100644
--- a/src/PJSipSessionModule.cpp
+++ b/src/PJSipSessionModule.cpp
@@ -172,6 +172,7 @@ static void handle_new_invite(pjsip_rx_data *rdata)
 	//on the To header of the incoming Invite.
 	pjsip_module *module = pjsip_ua_instance();
 	pj_status_t status = pjsip_dlg_create_uas(module, rdata, NULL, &dlg);
+	PJSipDialogModInfo *dlg_mod_info = new PJSipDialogModInfo(dlg);
 
 	if (status != PJ_SUCCESS)
 	{
@@ -243,9 +244,10 @@ static void handle_new_invite(pjsip_rx_data *rdata)
 	(*session)->setInviteSession(inv_session);
 	(*session)->setDialog(dlg);
 
-	//Adding the SipEndpoint to the dialog's mod_data makes it easy to
+	//Adding the SipEndpoint to the inv_session's mod_data makes it easy to
 	//retrieve during signal callbacks.
-	dlg->mod_data[module->id] = (void *)session;
+	inv_session->mod_data[module->id] = (void *)session;
+	dlg->mod_data[module->id] = (void *)dlg_mod_info;
 
 	AsteriskSCF::SessionCommunications::V1::SessionRouterPrx router = dataModel.getSessionRouter();
 	router->routeSession((*session)->getSessionProxy(), destination);
@@ -324,7 +326,7 @@ static pj_bool_t sessionOnReceiveRequest(pjsip_rx_data *rdata)
 static void handle_invite_response(pjsip_inv_session *inv, pjsip_rx_data *rdata, pjsip_dialog *dlg)
 {
 	int respCode = rdata->msg_info.msg->line.status.code;
-	SipSessionPtr *session = (SipSessionPtr*)dlg->mod_data[pjsip_ua_instance()->id];
+	SipSessionPtr *session = (SipSessionPtr*)inv->mod_data[pjsip_ua_instance()->id];
 	//Commented because they are currently unused. They
 	//will be once the individual cases are mapped out.
 	//pjsip_dialog *dlg = pjsip_rdata_get_dlg(rdata);
@@ -441,7 +443,7 @@ static void invOnStateChanged(pjsip_inv_session *inv, pjsip_event *event)
 {
    if (inv->state == PJSIP_INV_STATE_DISCONNECTED)
    {
-      SipSessionPtr *session = (SipSessionPtr*)inv->dlg->mod_data[pjsip_ua_instance()->id];
+      SipSessionPtr *session = (SipSessionPtr*)inv->mod_data[pjsip_ua_instance()->id];
       if (session == 0)
       {
 	 return;
@@ -513,7 +515,7 @@ static void invOnMediaUpdate(pjsip_inv_session *inv, pj_status_t status)
 
    const pjmedia_sdp_conn *remote_conn = remote_sdp->media[0]->conn ? remote_sdp->media[0]->conn : remote_sdp->conn;
 
-   SipSessionPtr *session = (SipSessionPtr*)inv->dlg->mod_data[pjsip_ua_instance()->id];
+   SipSessionPtr *session = (SipSessionPtr*)inv->mod_data[pjsip_ua_instance()->id];
    (*session)->setRemoteDetails(pj_strbuf(&remote_conn->addr), remote_sdp->media[0]->desc.port);
 
    // Each stream has its own set of formats, so go to that granularity

commit fb521666e3b325386edc63bd7a15523bf46d0756
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 14 15:44:33 2010 -0500

    Add a class for maintaining dialog state.

diff --git a/src/PJSipSessionModule.cpp b/src/PJSipSessionModule.cpp
index d4da67f..9e1f40b 100644
--- a/src/PJSipSessionModule.cpp
+++ b/src/PJSipSessionModule.cpp
@@ -5,6 +5,7 @@
  *
  * All rights reserved.
  */
+#include <IceUtil/UUID.h>
 
 #include <Core/Endpoint/EndpointIf.h>
 #include <Core/Routing/RoutingIf.h>
@@ -18,6 +19,7 @@
 #include "SipEndpointFactory.h"
 #include "SipSession.h"
 #include "PJSipManager.h"
+#include "SipStateReplicator.h"
 
 namespace AsteriskSCF
 {
@@ -30,6 +32,91 @@ using namespace AsteriskSCF::SessionCommunications::Bridging::V1;
 using namespace AsteriskSCF::Core::Endpoint::V1;
 using namespace AsteriskSCF::SessionCommunications::V1;
 using namespace AsteriskSCF::Media::V1;
+using namespace AsteriskSCF::SIP::V1;
+
+//Arbitrarily chosen URI size. Used for times when I need
+//to retrieve PJSIP URI strings.
+const int URI_SIZE = 64;
+
+/**
+ * This is the data we stash in a pjsip_dialog's mod_info
+ * array so we can have all the dialog info we need. This
+ * is mostly used for state replication.
+ *
+ * XXX It may be necessary to put this class in a .h file
+ * in case SipEndpoint.cpp needs to use this.
+ */
+class PJSipDialogModInfo
+{
+public:
+   PJSipDialogModInfo(pjsip_dialog *dialog) : mDialogState(new SipDialogStateItem) , mNeedsUpdate(true)
+   {
+      //XXX Is there a way to tell ICE to make the default
+	  //constructor for SipStateItem set mId?
+      mDialogState->mId = IceUtil::generateUUID();
+	  updateDialogState(dialog);
+   }
+   /**
+	* Copies data from the pjsip_dialog structure into
+	* our state data.
+	*
+	* XXX This could likely be optimized to only update
+	* stuff that needs updating. Important first step
+	* is to get it working.
+	*/
+   void updateDialogState(pjsip_dialog *dialog)
+   {
+      mDialogState->mCallId = std::string(pj_strbuf(&dialog->call_id->id), pj_strlen(&dialog->call_id->id));
+	  mDialogState->mIsDialogEstablished = dialog->state == PJSIP_DIALOG_STATE_ESTABLISHED ? true : false;
+	  mDialogState->mIsSecure = dialog->secure == PJ_TRUE ? true : false;
+
+      mDialogState->mLocalCSeq = dialog->local.cseq;
+	  mDialogState->mLocalTag = std::string(pj_strbuf(&dialog->local.info->tag), pj_strlen(&dialog->local.info->tag));
+	  char localUri[URI_SIZE];
+	  pjsip_uri_print(PJSIP_URI_IN_FROMTO_HDR, dialog->local.info->uri, localUri, sizeof(localUri));
+	  mDialogState->mLocalUri = localUri;
+
+      mDialogState->mRemoteCSeq = dialog->remote.cseq;
+	  mDialogState->mRemoteTag = std::string(pj_strbuf(&dialog->remote.info->tag), pj_strlen(&dialog->remote.info->tag));
+	  char remoteUri[URI_SIZE];
+	  pjsip_uri_print(PJSIP_URI_IN_FROMTO_HDR, dialog->remote.info->uri, remoteUri, sizeof(remoteUri));
+	  mDialogState->mRemoteUri = remoteUri;
+      
+	  //This is a place where the whole "only change what you need" optimization
+      //will come in super-handy since we have to erase and rebuild the route set
+	  //every time. My recollection is that the route set can only be established
+	  //in the first transaction of a dialog so this is purdy wasteful.
+	  mDialogState->mRouteSet.erase(mDialogState->mRouteSet.begin(), mDialogState->mRouteSet.end());
+	  for (pjsip_route_hdr *hdr_iter = dialog->route_set.next; hdr_iter != &dialog->route_set; hdr_iter = hdr_iter->next)
+	  {
+		 char routeUri[URI_SIZE];
+		 pjsip_uri_print(PJSIP_URI_IN_ROUTING_HDR, hdr_iter->name_addr.uri, routeUri, sizeof(routeUri));
+
+	     //XXX I need to see the order in which the route set is represented
+		 //in a pjsip dialog. push_back could be completely incorrect here,
+		 //or it may only be correct depending on whether we're the UAC or UAS.
+		 //Also, for now we're ignoring the optional display name portion of URIs
+		 //in the route set. They're not strictly necessary for routing calls correctly.
+		 mDialogState->mRouteSet.push_back(routeUri);
+	  }
+	  //XXX I'm not 100% sure how to get the transport from a pjsip_dialog, so for now,
+	  //I'll just hardcode this as UDP until we start wanting to actually implement
+	  //other transports.
+	  mDialogState->mTransport = "UDP";
+	  mNeedsUpdate = true;
+   }
+
+   /**
+	* The associated dialog information. Used for state replication
+	*/
+   SipDialogStateItemPtr mDialogState;
+   /**
+	* An indicator of whether there are pending updates to the dialogState.
+	* This is in place so we don't send needless updates to the state replicator
+	* if nothing has actually changed for the dialog.
+	*/
+   bool mNeedsUpdate;
+};
 
 static pj_status_t sessionLoad(pjsip_endpoint *endpt)
 {

-----------------------------------------------------------------------


-- 
asterisk-scf/integration/sip.git



More information about the asterisk-scf-commits mailing list