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

Commits to the Asterisk SCF project code repositories asterisk-scf-commits at lists.digium.com
Tue Sep 6 18:40:25 CDT 2011


branch "client-registration" has been updated
       via  431b2770d9d3474a875472bebcca9f94078b1a9d (commit)
       via  98c040dd66ef764138d08a8ffdd9225d41b01e89 (commit)
       via  cd36994c6bec938714967bb1d4f3204657047b43 (commit)
       via  4aaedaa1ec9918bc075f021889b6de9860d69458 (commit)
       via  edac7e1214ff616569b541ba4aa776d6222872ea (commit)
      from  49654083b0cd285e5744419d25b977fd7480abe1 (commit)

Summary of changes:
 config/SipConfigurator.py                          |   42 +++++
 .../SipSessionManager/SipConfigurationIf.ice       |   66 ++++++++
 src/SipClientRegistration.cpp                      |   71 ++++++---
 src/SipClientRegistration.h                        |   18 +-
 src/SipConfiguration.cpp                           |  174 +++++++++++++++++++-
 src/SipEndpoint.cpp                                |   26 +++
 src/SipEndpoint.h                                  |    2 +
 7 files changed, 360 insertions(+), 39 deletions(-)


- Log -----------------------------------------------------------------
commit 431b2770d9d3474a875472bebcca9f94078b1a9d
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 6 18:41:44 2011 -0500

    Allow for multiple client registrations to be added to an endpoint.

diff --git a/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice b/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
index c93aa22..c972cf5 100644
--- a/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
+++ b/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
@@ -550,6 +550,8 @@ class SipClientRegistrationItem extends SipConfigurationItem
     int defaultExpiration;
 };
 
+sequence<SipClientRegistrationItem> SipClientRegistrationItemSeq;
+
 class SipRegistrationGroupRef extends SipConfigurationItem
 {
     string registrationGroupName;
diff --git a/src/SipConfiguration.cpp b/src/SipConfiguration.cpp
index de2b10f..d669f8c 100644
--- a/src/SipConfiguration.cpp
+++ b/src/SipConfiguration.cpp
@@ -428,7 +428,7 @@ public:
             return;
         }
 
-        mEndpoint->updateClientRegistration(item);
+        mClientRegistrations.push_back(item);
     }
 
     void updated(const UpdateCommandList& updates)
@@ -449,6 +449,10 @@ public:
                 UpdateCommand command = *op;
                 command();
             }
+            if (!mClientRegistrations.empty())
+            {
+                mEndpoint->updateClientRegistrations(mClientRegistrations);
+            }
             if (updateSystem)
             {
                 mFactory->generateRoutingDestinations(destinations);
@@ -466,6 +470,7 @@ private:
     boost::shared_ptr<SipEndpointFactory> mFactory;
     LocatorRegistrySmartPrx mRegistry;
     string mRoutingId;
+    SipClientRegistrationItemSeq mClientRegistrations;
 };
 
 /**
diff --git a/src/SipEndpoint.cpp b/src/SipEndpoint.cpp
index d98bb01..128a928 100644
--- a/src/SipEndpoint.cpp
+++ b/src/SipEndpoint.cpp
@@ -37,6 +37,7 @@ using namespace AsteriskSCF::Core::Discovery::V1;
 using namespace AsteriskSCF::SessionCommunications::V1;
 using namespace AsteriskSCF::Replication::SipSessionManager::V1;
 using namespace AsteriskSCF::Discovery;
+using namespace AsteriskSCF::Configuration::SipSessionManager::V1;
 
 namespace
 {
@@ -312,21 +313,25 @@ void SipEndpoint::setDTMFMethod(AsteriskSCF::Configuration::SipSessionManager::V
     mImplPriv->mConfig.sessionConfig.dtmf = dtmf;
 }
 
-void SipEndpoint::updateClientRegistration(AsteriskSCF::Configuration::SipSessionManager::V1::SipClientRegistrationItemPtr& item)
+void SipEndpoint::updateClientRegistrations(SipClientRegistrationItemSeq& items)
 {
-    std::map<std::string, SipRegistrationClientPtr>::iterator iter =
-        mImplPriv->mClientRegistrations.find(item->aor);
-
-    if (iter != mImplPriv->mClientRegistrations.end())
+    for (SipClientRegistrationItemSeq::iterator item = items.begin();
+            item != items.end(); ++item)
     {
-        //Updating one that exists
-        iter->second->addContacts(item->contacts);
-    }
-    else
-    {
-        //New one!
-        mImplPriv->mClientRegistrations[item->aor] =
-            new SipRegistrationClient(item->contacts, mImplPriv->mManager->getEndpoint(), this);
+        std::map<std::string, SipRegistrationClientPtr>::iterator iter =
+            mImplPriv->mClientRegistrations.find((*item)->aor);
+
+        if (iter != mImplPriv->mClientRegistrations.end())
+        {
+            //Updating one that exists
+            iter->second->addContacts((*item)->contacts);
+        }
+        else
+        {
+            //New one!
+            mImplPriv->mClientRegistrations[(*item)->aor] =
+                new SipRegistrationClient((*item)->contacts, mImplPriv->mManager->getEndpoint(), this);
+        }
     }
 }
 
diff --git a/src/SipEndpoint.h b/src/SipEndpoint.h
index f0a3e33..9ee243f 100644
--- a/src/SipEndpoint.h
+++ b/src/SipEndpoint.h
@@ -355,7 +355,7 @@ public:
     AsteriskSCF::Media::V1::StreamInformationDict getStreamTopology();
     void setDTMFMethod(AsteriskSCF::Configuration::SipSessionManager::V1::SipDTMFOption dtmf);
 
-    void updateClientRegistration(AsteriskSCF::Configuration::SipSessionManager::V1::SipClientRegistrationItemPtr& item);
+    void updateClientRegistrations(AsteriskSCF::Configuration::SipSessionManager::V1::SipClientRegistrationItemSeq& items);
 
     void addDefaultSessionCookie(
         const AsteriskSCF::SessionCommunications::V1::SessionCookiePtr& cookie);

commit 98c040dd66ef764138d08a8ffdd9225d41b01e89
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 6 18:15:49 2011 -0500

    Add the rest of the configuration operations.

diff --git a/src/SipConfiguration.cpp b/src/SipConfiguration.cpp
index 7eed40e..de2b10f 100644
--- a/src/SipConfiguration.cpp
+++ b/src/SipConfiguration.cpp
@@ -892,6 +892,7 @@ public:
         mRoutingId(routingId), 
         mRoutingServiceLocatorRegistry(registry) 
     {
+        mRegistrationConfigMap.clear();
     }
 
     /**
@@ -1038,6 +1039,20 @@ public:
         }
     }
 
+    void remove(const SipRegistrationGroupPtr& group)
+    {
+        RegistrationConfigPtr config;
+        {
+            boost::unique_lock<boost::shared_mutex> lock(mLock);
+            RegistrationConfigMap::iterator i = mRegistrationConfigMap.find(group->name);
+            if (i != mRegistrationConfigMap.end())
+            {
+                config = i->second;
+                mRegistrationConfigMap.erase(i);
+            }
+        }
+    }
+
     SipGeneralGroupPtr getGroupFor(const SipGeneralGroupPtr&)
     {
         return mGroup;
@@ -1466,6 +1481,11 @@ ConfigurationGroupSeq ConfigurationServiceImpl::getConfiguration(
             getGeneric<SipEndpointGroupPtr>(mImpl->getData(), group, mGroups);
 	};
 
+    void visitSipRegistrationGroup(const SipRegistrationGroupPtr& group)
+    {
+        getGeneric<SipRegistrationGroupPtr>(mImpl->getData(), group, mGroups);
+    }
+
 	ConfigurationServiceImplPtr mImpl;
 	ConfigurationGroupSeq& mGroups;
     };
@@ -1539,6 +1559,11 @@ ConfigurationGroupSeq ConfigurationServiceImpl::getConfigurationAll(
             genericGetAll<SipEndpointGroupPtr>(mImpl->getData(), group, mGroups);
 	};
 
+    void visitSipRegistrationGroup(const SipRegistrationGroupPtr& group)
+    {
+        genericGetAll<SipRegistrationGroupPtr>(mImpl->getData(), group, mGroups);
+    }
+
 	ConfigurationServiceImplPtr mImpl;
 	ConfigurationGroupSeq& mGroups;
     };
@@ -1686,6 +1711,11 @@ void ConfigurationServiceImpl::removeConfigurationItems(
         {
             mImpl->getData()->removeFromGroup(group);
         };
+
+        void visitSipRegistrationGroup(const SipRegistrationGroupPtr& group)
+        {
+            mImpl->getData()->removeFromGroup(group);
+        }
     private:
 	ConfigurationServiceImplPtr mImpl;
     };
@@ -1742,6 +1772,11 @@ void ConfigurationServiceImpl::removeConfigurationGroups(
             mImpl->getData()->remove(group);
         };
 
+        void visitSipRegistrationGroup(const SipRegistrationGroupPtr& group)
+        {
+            mImpl->getData()->remove(group);
+        }
+
 	ConfigurationServiceImplPtr mImpl;
     };
     

commit cd36994c6bec938714967bb1d4f3204657047b43
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 6 17:59:30 2011 -0500

    Add code to be able to configure new client registrations for an endpoint.
    
    Next step is to add configuration code so things can be removed.

diff --git a/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice b/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
index 3dba430..c93aa22 100644
--- a/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
+++ b/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
@@ -525,7 +525,7 @@ struct ContactInfo
      * Expiration for this contact in seconds
      */
     int expiration;
-}
+};
 
 sequence<ContactInfo> ContactInfoSeq;
 
@@ -550,6 +550,11 @@ class SipClientRegistrationItem extends SipConfigurationItem
     int defaultExpiration;
 };
 
+class SipRegistrationGroupRef extends SipConfigurationItem
+{
+    string registrationGroupName;
+};
+
 }; /* module V1 */
 
 }; /* module SipSessionManager */
diff --git a/src/SipClientRegistration.cpp b/src/SipClientRegistration.cpp
index cadc360..a7b9d83 100644
--- a/src/SipClientRegistration.cpp
+++ b/src/SipClientRegistration.cpp
@@ -21,6 +21,7 @@ namespace
 
 using namespace AsteriskSCF::SipSessionManager;
 using namespace AsteriskSCF::System::Hook::V1;
+using namespace AsteriskSCF::Configuration::SipSessionManager::V1;
 
 void regCallback(struct pjsip_regc_cbparam *param)
 {
@@ -31,14 +32,14 @@ void regCallback(struct pjsip_regc_cbparam *param)
     client->handleRegisterResponse(param);
 }
 
-bool operator< (const RegPair& lhs, const RegPair& rhs)
+bool operator< (const ContactInfo& lhs, const ContactInfo& rhs)
 {
-    return lhs.first < rhs.first;
+    return lhs.contactURI < rhs.contactURI;
 }
 
-bool operator== (const RegPair& lhs, const RegPair& rhs)
+bool operator== (const ContactInfo& lhs, const ContactInfo& rhs)
 {
-    return lhs.first == rhs.first;
+    return lhs.contactURI == rhs.contactURI;
 }
 
 struct EqualContacts
@@ -46,18 +47,18 @@ struct EqualContacts
     EqualContacts(const std::string& str)
         :mContact(str) { }
 
-    bool operator()(const RegPair& pair) 
+    bool operator()(const ContactInfo& info) 
     {
-        return pair.first == mContact;
+        return info.contactURI == mContact;
     }
 
     const std::string mContact;
 };
 
-pj_str_t makeContact(const RegPair& pair)
+pj_str_t makeContact(const ContactInfo& info)
 {
     std::stringstream str;
-    str << pair.first << ";expires=" << pair.second;
+    str << info.contactURI << ";expires=" << info.expiration;
     pj_str_t ret;
     pj_cstr(&ret, str.str().c_str());
     return ret;
@@ -121,7 +122,7 @@ AuthHookSeq SipRegistrationClientManager::getAuthHooks()
 }
 
 SipRegistrationClient::SipRegistrationClient(
-        const RegPairSeq& contacts,
+        const ContactInfoSeq& contacts,
         pjsip_endpoint* pjEndpoint,
         const SipEndpointPtr& sipEndpoint)
     : mEndpointName(sipEndpoint->getName())
@@ -166,7 +167,7 @@ SipRegistrationClient::~SipRegistrationClient()
     pjsip_regc_destroy(mReg);
 }
 
-void SipRegistrationClient::addContacts(const RegPairSeq& contacts)
+void SipRegistrationClient::addContacts(const ContactInfoSeq& contacts)
 {
     unique_add(mContacts, contacts);
 
diff --git a/src/SipClientRegistration.h b/src/SipClientRegistration.h
index 4e40ae1..8c62e44 100644
--- a/src/SipClientRegistration.h
+++ b/src/SipClientRegistration.h
@@ -19,6 +19,8 @@
 #include <boost/thread.hpp>
 #include <pjsip_ua.h>
 
+#include <AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.h>
+
 #include "SipEndpoint.h"
 #include "AuthManager.h"
 
@@ -60,26 +62,22 @@ private:
 
 typedef IceUtil::Handle<SipRegistrationClientManager> SipRegistrationClientManagerPtr;
 
-
-typedef std::pair<std::string, int> RegPair;
-typedef std::vector<RegPair> RegPairSeq;
-
 /**
  * One of these exists per endpoint.
  * This takes care of sending REGISTER
  * to the configured endpoint.
  */
-class SipRegistrationClient
+class SipRegistrationClient : public IceUtil::Shared
 {
 public:
     SipRegistrationClient(
-            const RegPairSeq& contacts,
+            const AsteriskSCF::Configuration::SipSessionManager::V1::ContactInfoSeq& contacts,
             pjsip_endpoint* pjEndpoint,
             const SipEndpointPtr& sipEndpoint);
 
     ~SipRegistrationClient();
 
-    void addContacts(const RegPairSeq& contacts);
+    void addContacts(const AsteriskSCF::Configuration::SipSessionManager::V1::ContactInfoSeq& contacts);
 
     void removeContacts(const Ice::StringSeq& contacts);
 
@@ -92,10 +90,12 @@ private:
     void authenticate(pjsip_rx_data *rdata);
 
     const std::string mEndpointName;
-    RegPairSeq mContacts;
+    AsteriskSCF::Configuration::SipSessionManager::V1::ContactInfoSeq mContacts;
     SipRegistrationClientManagerPtr mManager;
     pjsip_regc* mReg;
 };
 
+typedef IceUtil::Handle<SipRegistrationClient> SipRegistrationClientPtr;
+
 }
 }
diff --git a/src/SipConfiguration.cpp b/src/SipConfiguration.cpp
index d6a342a..7eed40e 100644
--- a/src/SipConfiguration.cpp
+++ b/src/SipConfiguration.cpp
@@ -137,6 +137,72 @@ static void performSerialCheck(const ConfigurationItemDict& changedItems, const
 typedef boost::function<void()> UpdateCommand;
 typedef vector<UpdateCommand> UpdateCommandList;
 
+class ConfigBase
+{
+public:
+    virtual ~ConfigBase() {}
+
+    virtual SipConfigurationItemVisitorPtr getVisitor() { return 0; }
+};
+typedef boost::shared_ptr<ConfigBase> ConfigBasePtr;
+
+class RegistrationConfig : public ConfigBase, public boost::enable_shared_from_this<RegistrationConfig>
+{
+    class Visitor : public SipConfigurationItemVisitor
+    {
+    public:
+        Visitor(const boost::shared_ptr<RegistrationConfig>& config)
+            : mConfig(config) { }
+
+        void visitSipClientRegistrationItem(const SipClientRegistrationItemPtr& item)
+        {
+            mConfig->update(item);
+        }
+    private:
+        boost::shared_ptr<RegistrationConfig> mConfig;
+    };
+
+public:
+
+    RegistrationConfig(const SipRegistrationGroupPtr& group)
+        : mGroup(group) { }
+
+    SipConfigurationItemVisitorPtr getVisitor()
+    {
+        return new Visitor(shared_from_this());
+    }
+
+    void update(const SipClientRegistrationItemPtr& item)
+    {
+        boost::unique_lock<boost::shared_mutex> lock(mLock);
+        mItem = item;
+    }
+
+    SipRegistrationGroupPtr getTypedGroup() const
+    {
+        return mGroup;
+    }
+
+    SipClientRegistrationItemPtr getClientRegistrationItem()
+    {
+        boost::shared_lock<boost::shared_mutex> lock(mLock);
+        return mItem;
+    }
+
+private:
+
+    boost::shared_mutex mLock;
+
+    SipClientRegistrationItemPtr mItem;
+
+    mutable SipRegistrationGroupPtr mGroup;
+};
+
+typedef boost::shared_ptr<RegistrationConfig> RegistrationConfigPtr;
+typedef std::map<std::string, RegistrationConfigPtr> RegistrationConfigMap;
+
+RegistrationConfigMap mRegistrationConfigMap;
+
 /**
  * A helper class and visitor for propogating configuration changes to the SIPEndPoint implementation.
  **/
@@ -228,6 +294,10 @@ class EndpointConfigHelper : public boost::enable_shared_from_this<EndpointConfi
         {
             mUpdates.push_back(boost::bind(&EndpointConfigHelper::updateDTMF, mConfig, dtmf));
         };
+        void visitSipRegistrationGroupRef(const SipRegistrationGroupRefPtr& registration)
+        {
+            mUpdates.push_back(boost::bind(&EndpointConfigHelper::updateRegistration, mConfig, registration));
+        }
 
     private:
 
@@ -333,11 +403,34 @@ public:
     {
         mEndpoint->setSignalingNATOptions(item->stun);
     }
+
     void updateDTMF(const SipDTMFItemPtr& dtmf)
     {
         mEndpoint->setDTMFMethod(dtmf->dtmf);
     }
 
+    void updateRegistration(const SipRegistrationGroupRefPtr& registration)
+    {
+        RegistrationConfigMap::const_iterator entry =
+            mRegistrationConfigMap.find(registration->registrationGroupName);
+
+        if (entry == mRegistrationConfigMap.end())
+        {
+            //Group doesn't exist.
+            return;
+        }
+
+        SipClientRegistrationItemPtr item = entry->second->getClientRegistrationItem();
+
+        if (item == 0)
+        {
+            //Group doesn't have a configuration item.
+            return;
+        }
+
+        mEndpoint->updateClientRegistration(item);
+    }
+
     void updated(const UpdateCommandList& updates)
     {
         //
@@ -375,15 +468,6 @@ private:
     string mRoutingId;
 };
 
-class ConfigBase
-{
-public:
-    virtual ~ConfigBase() {}
-
-    virtual SipConfigurationItemVisitorPtr getVisitor() { return 0; }
-};
-typedef boost::shared_ptr<ConfigBase> ConfigBasePtr;
-
 /**
  * The Transport specializations take care of any transport specific configuration and
  * initialization. The UDP and TCP transports are so similar that they could probably
@@ -1035,6 +1119,16 @@ public:
         return 0;
     }
 
+    const SipRegistrationGroupPtr getGroupFor(const SipRegistrationGroupPtr& group)
+    {
+        RegistrationConfigMap::const_iterator i;
+        if (getItem(mRegistrationConfigMap, i, group->name))
+        {
+            return i->second->getTypedGroup();
+        }
+        return 0;
+    }
+
 private:
 
     boost::shared_mutex mLock;
@@ -1217,6 +1311,23 @@ private:
         return transport->getVisitor();
     }
 
+    SipConfigurationItemVisitorPtr updateGroup(const SipRegistrationGroupPtr& group)
+    {
+        RegistrationConfigMap::const_iterator i;
+        RegistrationConfigPtr registrationConfig;
+        if (!getItem(mRegistrationConfigMap, i, group->name))
+        {
+            registrationConfig.reset(new RegistrationConfig(group));
+            mRegistrationConfigMap.insert(make_pair(group->name, registrationConfig));
+        }
+        else
+        {
+            registrationConfig = i->second;
+        }
+
+        return registrationConfig->getVisitor();
+    }
+
     template <class T>
     void copyTemplates(ConfigurationGroupSeq& groups, const T& items)
     {
@@ -1513,6 +1624,11 @@ void ConfigurationServiceImpl::setConfiguration(const AsteriskSCF::System::Confi
         {
             genericSet<SipEndpointGroupPtr>(mImpl->getData(), group);
         };
+
+        void visitSipRegistrationGroup(const SipRegistrationGroupPtr& group)
+        {
+            genericSet<SipRegistrationGroupPtr>(mImpl->getData(), group);
+        }
 	
 	ConfigurationServiceImplPtr mImpl;
     };
diff --git a/src/SipEndpoint.cpp b/src/SipEndpoint.cpp
index f88691b..d98bb01 100644
--- a/src/SipEndpoint.cpp
+++ b/src/SipEndpoint.cpp
@@ -16,6 +16,7 @@
 #include "PJSipManager.h"
 #include "SipEndpointFactory.h"
 #include "SipSession.h"
+#include "SipClientRegistration.h"
 #include <Ice/Ice.h>
 #include <IceUtil/UUID.h>
 
@@ -238,6 +239,8 @@ public:
     SipReplicationContextPtr mReplicationContext;
     AsteriskSCF::Collections::ProxySet<SessionListenerPrx>::SetPtr mDefaultListeners;
     AsteriskSCF::Collections::HandleSet<SessionCookiePtr>::SetPtr mDefaultSessionCookies;
+
+    std::map<std::string, SipRegistrationClientPtr> mClientRegistrations;
 };
 
 SipEndpoint::SipEndpoint(const Ice::ObjectAdapterPtr& adapter, 
@@ -309,6 +312,24 @@ void SipEndpoint::setDTMFMethod(AsteriskSCF::Configuration::SipSessionManager::V
     mImplPriv->mConfig.sessionConfig.dtmf = dtmf;
 }
 
+void SipEndpoint::updateClientRegistration(AsteriskSCF::Configuration::SipSessionManager::V1::SipClientRegistrationItemPtr& item)
+{
+    std::map<std::string, SipRegistrationClientPtr>::iterator iter =
+        mImplPriv->mClientRegistrations.find(item->aor);
+
+    if (iter != mImplPriv->mClientRegistrations.end())
+    {
+        //Updating one that exists
+        iter->second->addContacts(item->contacts);
+    }
+    else
+    {
+        //New one!
+        mImplPriv->mClientRegistrations[item->aor] =
+            new SipRegistrationClient(item->contacts, mImplPriv->mManager->getEndpoint(), this);
+    }
+}
+
 void SipEndpoint::setRTPOverIPv6(bool enabled)
 {
     mImplPriv->mConfig.sessionConfig.rtpOverIPv6 = enabled;
diff --git a/src/SipEndpoint.h b/src/SipEndpoint.h
index 80b9e2e..f0a3e33 100644
--- a/src/SipEndpoint.h
+++ b/src/SipEndpoint.h
@@ -355,6 +355,8 @@ public:
     AsteriskSCF::Media::V1::StreamInformationDict getStreamTopology();
     void setDTMFMethod(AsteriskSCF::Configuration::SipSessionManager::V1::SipDTMFOption dtmf);
 
+    void updateClientRegistration(AsteriskSCF::Configuration::SipSessionManager::V1::SipClientRegistrationItemPtr& item);
+
     void addDefaultSessionCookie(
         const AsteriskSCF::SessionCommunications::V1::SessionCookiePtr& cookie);
 

commit 4aaedaa1ec9918bc075f021889b6de9860d69458
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 6 15:37:23 2011 -0500

    Add configuration items and configurator code for client registration.

diff --git a/config/SipConfigurator.py b/config/SipConfigurator.py
index 88639a8..12d71ba 100755
--- a/config/SipConfigurator.py
+++ b/config/SipConfigurator.py
@@ -102,6 +102,46 @@ class SipSectionVisitors(Configurator.SectionVisitors):
 
         self.groups.append(group)
 
+    def visit_registration_contacts(self, section, option):
+            
+    def visit_registration(self, config, section):
+
+        class RegistrationContactHandler:
+            def __init__(self, config):
+                self.config = config
+            def get(self, section, option):
+                setting = config.get(section, option)
+                contacts = setting.split(',')
+                ret = []
+
+                for contact in contacts:
+                    uri, slash, expiration = contact.partition('/')
+                    info = AsteriskSCF.Configuration.SipSessionManager.V1.ContactInfo()
+                    info.contactUri = uri
+                    info.expiration = int(expiration)
+                    ret.append(info)
+
+                return ret
+
+        group = AsteriskSCF.Configuration.SipSessionManager.V1.SipRegistrationGroup()
+        group.name = section
+        group.configurationItems = {}
+
+        mapper = Configurator.OptionMapper()
+
+        item = AsteriskSCF.Configuration.SipSessionManager.V1.SipClientRegistrationItem()
+
+        mapper.map('aor', item, 'aor', 'registration', config.get, None)
+        mapper.map('expiration', item, 'defaultExpiration', 'registration', config.getint, None)
+        handler = RegistrationContactHandler(config)
+        mapper.map('contacts', item, 'contacts', 'registration', handler.get, None)
+
+        for option in config.options(section):
+            mapper.execute(group, section, option)
+        mapper.finish(group)
+
+        self.groups.append(group)
+
     def visit_endpoint(self, config, section):
         group = AsteriskSCF.Configuration.SipSessionManager.V1.SipEndpointGroup()
         group.name = section
@@ -254,6 +294,8 @@ class SipSectionVisitors(Configurator.SectionVisitors):
             self.visit_transport_tls(config, section)
         elif config.get(section, 'type') == 'endpoint':
             self.visit_endpoint(config, section)
+        elif config.get(section, 'type') == 'registration':
+            self.visit_registration(config, section)
 
 # In order to do service locator based lookup we need to pass in a params object
 serviceLocatorParams = AsteriskSCF.Core.Discovery.V1.ServiceLocatorParams()
diff --git a/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice b/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
index 6bddae5..3dba430 100644
--- a/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
+++ b/slice/AsteriskSCF/Configuration/SipSessionManager/SipConfigurationIf.ice
@@ -96,6 +96,18 @@ class SipDomainGroup extends SipConfigurationGroup
 };
 
 /**
+ * SIP Client Registration group. Used to configure
+ * parameters relating to client registration
+ */
+class SipRegistrationGroup extends SipConfigurationGroup
+{
+    /**
+     * Name for this registration group
+     */
+    string name;
+};
+
+/**
  * Domain item for bindings
  */
 class SipBindingsItem extends SipConfigurationItem
@@ -491,6 +503,53 @@ class SipDTMFItem extends SipConfigurationItem
     SipDTMFOption dtmf = RFC4733;
 };
 
+/**
+ * Information pertaining to a 
+ * contact bound to a specific AOR
+ */
+struct ContactInfo
+{
+    /**
+     * The URI for the contact. This
+     * will be fed in directly to the
+     * client registration code. This
+     * must be formatted as a SIP or SIPs
+     * URI. It may contain a display name.
+     *
+     * Examples:
+     * "Bob" <sip:bob at example.org>
+     * <sip:alice at example.org>
+     */
+    string contactURI;
+    /**
+     * Expiration for this contact in seconds
+     */
+    int expiration;
+}
+
+sequence<ContactInfo> ContactInfoSeq;
+
+const int DefaultExpiration = 3600;
+
+class SipClientRegistrationItem extends SipConfigurationItem
+{
+    /**
+     * The AOR to which the contacts will
+     * be bound.
+     */
+    string aor;
+    /**
+     * The contacts to bind to the AOR
+     */
+    ContactInfoSeq contacts;
+    /**
+     * The expiration to use for any contacts
+     * with no explicit expiration set. Units
+     * for expiration are seconds.
+     */
+    int defaultExpiration;
+};
+
 }; /* module V1 */
 
 }; /* module SipSessionManager */
diff --git a/src/SipClientRegistration.cpp b/src/SipClientRegistration.cpp
index 9543aa2..cadc360 100644
--- a/src/SipClientRegistration.cpp
+++ b/src/SipClientRegistration.cpp
@@ -282,7 +282,7 @@ void SipRegistrationClient::authenticate(pjsip_rx_data *rdata)
                 pjsip_cred_info info;
                 pj_cstr(&info.realm, authIter->realm.c_str());
                 pj_cstr(&info.scheme, "digest");
-                pj_cstr(&info.username, authIter->user.c_str());
+                pj_cstr(&info.username, authIter->username.c_str());
                 pj_cstr(&info.data, authIter->password.c_str());
                 info.data_type = PJSIP_CRED_DATA_PLAIN_PASSWD;
                 creds.push_back(info);

commit edac7e1214ff616569b541ba4aa776d6222872ea
Author: Mark Michelson <mmichelson at digium.com>
Date:   Tue Sep 6 10:40:37 2011 -0500

    Add authentication support to client registration.
    
    The next step in this mess is to mess with configuration.

diff --git a/src/SipClientRegistration.cpp b/src/SipClientRegistration.cpp
index 0706d0d..9543aa2 100644
--- a/src/SipClientRegistration.cpp
+++ b/src/SipClientRegistration.cpp
@@ -233,19 +233,8 @@ void SipRegistrationClient::handleRegisterResponse(pjsip_regc_cbparam *param)
     case 401:
     case 407:
     {
-        AuthHookSeq hooks = mManager->getAuthHooks();
-        for (AuthHookSeq::iterator iter = hooks.begin();
-                iter != hooks.end(); ++iter)
-        {
-            ClientAuthSeq auths;
-            Ice::StringSeq realms = getRealms(param->rdata);
-            HookResult result = (*iter)->getCredentials(mEndpointName, realms, auths);
-            if (result.status == Succeeded)
-            {
-                //Cool. So now we need to update the auth info on mReg
-            }
-        }
         //We must authenticate!
+        authenticate(param->rdata);
         break;
     }
     default:
@@ -270,5 +259,42 @@ Ice::StringSeq SipRegistrationClient::getRealms(pjsip_rx_data *rdata)
     return realms;
 }
 
+//XXX This function seems like it may fit better into AuthManager
+//or some more central place since it could be useful for authentication
+//responses for any type of request. This is not REGISTER-specific, in
+//other words.
+void SipRegistrationClient::authenticate(pjsip_rx_data *rdata)
+{
+    AuthHookSeq hooks = mManager->getAuthHooks();
+    for (AuthHookSeq::iterator iter = hooks.begin();
+            iter != hooks.end(); ++iter)
+    {
+        ClientAuthSeq auths;
+        Ice::StringSeq realms = getRealms(rdata);
+        HookResult result = (*iter)->getCredentials(mEndpointName, realms, auths);
+        if (result.status == Succeeded)
+        {
+            std::vector<pjsip_cred_info> creds;
+            //Cool. So now we need to update the auth info on mReg
+            for (ClientAuthSeq::iterator authIter = auths.begin();
+                    authIter != auths.end(); ++authIter)
+            {
+                pjsip_cred_info info;
+                pj_cstr(&info.realm, authIter->realm.c_str());
+                pj_cstr(&info.scheme, "digest");
+                pj_cstr(&info.username, authIter->user.c_str());
+                pj_cstr(&info.data, authIter->password.c_str());
+                info.data_type = PJSIP_CRED_DATA_PLAIN_PASSWD;
+                creds.push_back(info);
+            }
+            if (creds.size() != 0)
+            {
+                pjsip_regc_set_credentials(mReg, creds.size(), &creds.front());
+                sendRegister();
+            }
+        }
+    }
+}
+
 }
 }
diff --git a/src/SipClientRegistration.h b/src/SipClientRegistration.h
index 4e68ce5..4e40ae1 100644
--- a/src/SipClientRegistration.h
+++ b/src/SipClientRegistration.h
@@ -89,6 +89,8 @@ private:
 
     Ice::StringSeq getRealms(pjsip_rx_data *rdata);
 
+    void authenticate(pjsip_rx_data *rdata);
+
     const std::string mEndpointName;
     RegPairSeq mContacts;
     SipRegistrationClientManagerPtr mManager;

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


-- 
asterisk-scf/integration/sip.git



More information about the asterisk-scf-commits mailing list