Module: sip-router Branch: master Commit: 15f27e65c9bd4ac50c91672d1b355d9e75f8972f URL: http://git.sip-router.org/cgi-bin/gitweb.cgi/sip-router/?a=commit;h=15f27e65...
Author: Richard Good richard.good@smilecoms.com Committer: Richard Good richard.good@smilecoms.com Date: Thu Oct 9 11:48:04 2014 +0200
modules/ims_icscf: Added new module param use_preferred_scscf_uri This allows ICSCF to have a preferred S-CSCF is HSS returns a list Usually ICSCF uses SCSCFs in the order in which HSS provides them This gives another level of priority control to SCSCF selection at the ICSCF
---
modules/ims_icscf/doc/ims_icscf_admin.xml | 45 +++++++++++++++++++++++- modules/ims_icscf/mod.c | 5 +++ modules/ims_icscf/scscf_list.c | 53 ++++++++++++++++++++++++----- 3 files changed, 92 insertions(+), 11 deletions(-)
diff --git a/modules/ims_icscf/doc/ims_icscf_admin.xml b/modules/ims_icscf/doc/ims_icscf_admin.xml index 4712bbb..dfd9a9c 100644 --- a/modules/ims_icscf/doc/ims_icscf_admin.xml +++ b/modules/ims_icscf/doc/ims_icscf_admin.xml @@ -140,7 +140,7 @@ modparam("ims_icscf", "cxdx_forced_peer", "hss.ims.smilecoms.com") <para><emphasis> Default value is "ims.smilecoms.com".</emphasis></para>
<example> - <title><varname>version_table</varname> parameter usage</title> + <title><varname>cxdx_dest_realm</varname> parameter usage</title>
<programlisting format="linespecific"> ... @@ -149,6 +149,47 @@ modparam("ims_icscf", "cxdx_dest_realm", "ims.smilecoms.com") </programlisting> </example> </section> + + <section> + <title><varname>use_preferred_scscf_uri</varname> (int)</title> + + <para>Whether or not this ICSCF has a preferred S-CSCF to use when the + HSS returns a list of SCSCFs. 0 means this I-CSCF has no preferred + SCSCF. 1 means it has a preferred S-CSCF.</para> + + <para><emphasis> Default value is 0.</emphasis></para> + + <example> + <title><varname>use_preferred_scscf_uri</varname> parameter usage</title> + + <programlisting format="linespecific"> +... +modparam("ims_icscf", "use_preferred_scscf_uri", 1) +... + </programlisting> + </example> + </section> + + <section> + <title><varname>preferred_scscf_uri</varname> (string)</title> + + <para>If use_preferred_scscf_uri is set then this is the URI of the preferred + SCSCF.</para> + + <para><emphasis> Default value is "".</emphasis></para> + + <example> + <title><varname>preferred_scscf_uri</varname> parameter usage</title> + + <programlisting format="linespecific"> +... +modparam("ims_icscf", "preferred_scscf_uri", "sip:scscf.ims.smilecoms.com:6060") +... + </programlisting> + </example> + </section> + + </section>
<section> @@ -299,7 +340,7 @@ route[REG_UAR_REPLY] retrieve return value</para>
<example> - <title>I_perform_location_information_request()</title> + <title>I_perform_location_information_request</title>
<programlisting format="linespecific"> ... diff --git a/modules/ims_icscf/mod.c b/modules/ims_icscf/mod.c index ce67903..04ccd19 100644 --- a/modules/ims_icscf/mod.c +++ b/modules/ims_icscf/mod.c @@ -76,6 +76,9 @@ int scscf_entry_expiry = 300; char* cxdx_dest_realm_s = "ims.smilecoms.com"; str cxdx_dest_realm;
+str preferred_scscf_uri = str_init("sip:scscf.ims.smilecoms.com:4060"); +int use_preferred_scscf_uri = 0; + //Only used if we want to force the Rx peer //Usually this is configured at a stack level and the first request uses realm routing char* cxdx_forced_peer_s = ""; @@ -123,6 +126,8 @@ static param_export_t params[] = { {"db_capabilities_table", PARAM_STRING, &ims_icscf_db_capabilities_table}, {"cxdx_forced_peer", PARAM_STR, &cxdx_forced_peer}, {"cxdx_dest_realm", PARAM_STR, &cxdx_dest_realm}, + {"preferred_scscf_uri", PARAM_STR, &preferred_scscf_uri}, + {"use_preferred_scscf_uri", INT_PARAM, &use_preferred_scscf_uri}, {0, 0, 0} };
diff --git a/modules/ims_icscf/scscf_list.c b/modules/ims_icscf/scscf_list.c index f5655c5..1d21ba3 100644 --- a/modules/ims_icscf/scscf_list.c +++ b/modules/ims_icscf/scscf_list.c @@ -56,6 +56,9 @@ extern int scscf_entry_expiry; //time for scscf entries to remain the scscf_list
extern struct tm_binds tmb; //Structure with pointers to tm funcs
+extern int use_preferred_scscf_uri; +extern str preferred_scscf_uri; + int i_hash_size; i_hash_slot *i_hash_table = 0;
@@ -427,19 +430,51 @@ out_of_memory: str take_scscf_entry(str call_id) { str scscf = {0, 0}; scscf_list *l = 0; + scscf_entry *scscf_entry = 0; unsigned int hash = get_call_id_hash(call_id, i_hash_size);
+ LM_DBG("Getting scscf entry from list\n"); + i_lock(hash); l = i_hash_table[hash].head; - while (l) { - if (l->call_id.len == call_id.len && - strncasecmp(l->call_id.s, call_id.s, call_id.len) == 0) { - if (l->list) { - scscf = l->list->scscf_name; - } - break; - } - l = l->next; + + //if use_preferred_scscf_uri then check the table for the preferred scscf set + if(use_preferred_scscf_uri) { + LM_DBG("use_preferred_scscf_uri is set so will check for preferred_scscf_uri first [%.*s]\n", preferred_scscf_uri.len, preferred_scscf_uri.s); + while (l) { + if (l->call_id.len == call_id.len && + strncasecmp(l->call_id.s, call_id.s, call_id.len) == 0) { + scscf_entry = l->list; + while (scscf_entry) { + LM_DBG("scscf_entry [%.*s]\n", scscf_entry->scscf_name.len, scscf_entry->scscf_name.s); + if (strncasecmp(scscf_entry->scscf_name.s, preferred_scscf_uri.s, preferred_scscf_uri.len) == 0) { + LM_DBG("scscf_entry matches\n"); + scscf = scscf_entry->scscf_name; + break; + } + scscf_entry = scscf_entry->next; + } + + break; + } + l = l->next; + } + } + + // if scscf has not yet been set then find the first scscf that matches + if(scscf.len <= 0 ) { + LM_DBG("scscf has not been set so we just look for first match\n"); + while (l) { + if (l->call_id.len == call_id.len && + strncasecmp(l->call_id.s, call_id.s, call_id.len) == 0) { + if (l->list) { + LM_DBG("scscf_entry [%.*s]\n", l->list->scscf_name.len, l->list->scscf_name.s); + scscf = l->list->scscf_name; + } + break; + } + l = l->next; + } } i_unlock(hash); return scscf;