[sr-dev] git:master: modules_k/pua, modules_k/rls: Prevent RLS from performing multiple back-end subscriptions to a presentity for a single RLS subscription

Peter Dunkley peter.dunkley at crocodile-rcs.com
Fri Apr 6 00:30:20 CEST 2012


Module: sip-router
Branch: master
Commit: 9cb078da8ff7cba9d2642d949e4e5a10bd851d82
URL:    http://git.sip-router.org/cgi-bin/gitweb.cgi/sip-router/?a=commit;h=9cb078da8ff7cba9d2642d949e4e5a10bd851d82

Author: Peter Dunkley <peter.dunkley at crocodile-rcs.com>
Committer: Peter Dunkley <peter.dunkley at crocodile-rcs.com>
Date:   Thu Apr  5 23:21:39 2012 +0100

modules_k/pua, modules_k/rls: Prevent RLS from performing multiple back-end subscriptions to a presentity for a single RLS subscription

---

 modules_k/pua/hash.c           |    2 +-
 modules_k/pua/pua_db.c         |    2 +-
 modules_k/pua/send_subscribe.c |    9 +----
 modules_k/rls/list.h           |   13 +++++++-
 modules_k/rls/subscribe.c      |   70 +++++++++++++++++++++++-----------------
 5 files changed, 56 insertions(+), 40 deletions(-)

diff --git a/modules_k/pua/hash.c b/modules_k/pua/hash.c
index fe6d82b..1fa6149 100644
--- a/modules_k/pua/hash.c
+++ b/modules_k/pua/hash.c
@@ -687,7 +687,7 @@ list_entry_t *get_subs_list(str *did)
 				tmp_str->len = dialog->pres_uri->len;
 				tmp_str->s[tmp_str->len] = '\0';
 
-				list = list_insert(tmp_str, list);
+				list = list_insert(tmp_str, list, NULL);
 			}
 			dialog = dialog->next;
 		}
diff --git a/modules_k/pua/pua_db.c b/modules_k/pua/pua_db.c
index c9846d0..2bc9e88 100644
--- a/modules_k/pua/pua_db.c
+++ b/modules_k/pua/pua_db.c
@@ -1560,7 +1560,7 @@ list_entry_t *get_subs_list_puadb(str *did)
 			tmp_str->len = strng.len;
 			tmp_str->s[tmp_str->len] = '\0';
 
-			list = list_insert(tmp_str, list);
+			list = list_insert(tmp_str, list, NULL);
 		}
 	} while ((db_fetch_next(&pua_dbf, pua_fetch_rows, pua_db, &res)==1)
 			&& (RES_ROWS(res)>0));
diff --git a/modules_k/pua/send_subscribe.c b/modules_k/pua/send_subscribe.c
index c88db69..a62ba7c 100644
--- a/modules_k/pua/send_subscribe.c
+++ b/modules_k/pua/send_subscribe.c
@@ -1091,15 +1091,10 @@ insert:
 		if (presentity->to_tag.len == 0)
 		{
 			if (subs->expires > 0)
-			{
-				LM_WARN("attempting to re-SUBSCRIBE to temporary (non-established) dialog - skipping\n");
-				LM_WARN("  is %.*s in %.*s's contact list more than once?\n",
-					presentity->pres_uri->len, presentity->pres_uri->s,
-					presentity->watcher_uri->len, presentity->watcher_uri->s);
-			}
+				LM_WARN("attempting to re-SUBSCRIBE to a temporary (non-established) dialog - skipping\n");
 			else
 			{
-				LM_WARN("attempting to un-SUBSCRIBE to temporary (non-established) dialog - skipping and deleting dialog\n");
+				LM_WARN("attempting to un-SUBSCRIBE from a temporary (non-established) dialog - skipping and deleting dialog\n");
 				if (dbmode==PUA_DB_ONLY)
 					delete_dialog_puadb(presentity);
 				else
diff --git a/modules_k/rls/list.h b/modules_k/rls/list.h
index e8580da..c9904aa 100644
--- a/modules_k/rls/list.h
+++ b/modules_k/rls/list.h
@@ -11,11 +11,14 @@ typedef struct list_entry
 	struct list_entry *next;
 } list_entry_t;
 
-static inline list_entry_t *list_insert(str *strng, list_entry_t *list)
+static inline list_entry_t *list_insert(str *strng, list_entry_t *list, int *duplicate)
 {
 	int cmp;
 	list_entry_t *p, *q;
 
+	if (duplicate != NULL)
+		*duplicate = 0;
+
 	if (strng == NULL || strng->s == NULL || strng->len == 0)
 	{
 		LM_ERR("bad string\n");
@@ -36,7 +39,11 @@ static inline list_entry_t *list_insert(str *strng, list_entry_t *list)
 	cmp = strncmp(list->strng->s, strng->s, strng->len);
 
 	if (cmp == 0)
+	{
+		if (duplicate != NULL)
+			*duplicate = 1;
 		return list;
+	}
 	if (cmp > 0)
 	{
 		p->next = list;
@@ -49,7 +56,11 @@ static inline list_entry_t *list_insert(str *strng, list_entry_t *list)
 			q = q->next;
 
 		if (cmp == 0)
+		{
+			if (duplicate != NULL)
+				*duplicate = 1;
 			return list;
+		}
 
 		p->next = q->next;
 		q->next = p;
diff --git a/modules_k/rls/subscribe.c b/modules_k/rls/subscribe.c
index c3dc4a2..eadef7a 100644
--- a/modules_k/rls/subscribe.c
+++ b/modules_k/rls/subscribe.c
@@ -861,8 +861,10 @@ error:
 
 int send_resource_subs(char* uri, void* param)
 {
-	str pres_uri;
+	str pres_uri, *tmp_str;
 	struct sip_uri parsed_pres_uri;
+	int duplicate = 0;
+	subs_info_t *s = (subs_info_t *) param;
 
 	pres_uri.s = uri;
 	pres_uri.len = strlen(uri);
@@ -877,8 +879,8 @@ int send_resource_subs(char* uri, void* param)
 	{
 		LM_WARN("Unable to subscribe to remote contact %.*s for watcher %.*s\n",
 				pres_uri.len, pres_uri.s,
-				((subs_info_t*)param)->watcher_uri->len,
-				((subs_info_t*)param)->watcher_uri->s);
+				s->watcher_uri->len,
+				s->watcher_uri->s);
 		return 1;
 	}
 
@@ -887,31 +889,33 @@ int send_resource_subs(char* uri, void* param)
 	if (rls_max_backend_subs > 0 && ++counter > rls_max_backend_subs)
 		return 1;
 
-	((subs_info_t*)param)->pres_uri = &pres_uri;
-	((subs_info_t*)param)->remote_target = &pres_uri;
+	s->pres_uri = &pres_uri;
+	s->remote_target = &pres_uri;
 
-	if (((subs_info_t*)param)->internal_update_flag == INTERNAL_UPDATE_TRUE)
+	/* Build list of contacts... checking each contact exists only once */
+	if ((tmp_str = (str *)pkg_malloc(sizeof(str))) == NULL)
 	{
-		str *tmp_str;
-
-		if ((tmp_str = (str *)pkg_malloc(sizeof(str))) == NULL)
-		{
-			LM_ERR("out of private memory\n");
-			return -1;
-		}
-		if ((tmp_str->s = (char *)pkg_malloc(sizeof(char) * pres_uri.len)) == NULL)
-		{
-			pkg_free(tmp_str);
-			LM_ERR("out of private memory\n");
-			return -1;
-		}
-		memcpy(tmp_str->s, pres_uri.s, pres_uri.len);
-		tmp_str->len = pres_uri.len;
-
-		rls_contact_list = list_insert(tmp_str, rls_contact_list);
+		LM_ERR("out of private memory\n");
+		return -1;
+	}
+	if ((tmp_str->s = (char *)pkg_malloc(sizeof(char) * pres_uri.len)) == NULL)
+	{
+		pkg_free(tmp_str);
+		LM_ERR("out of private memory\n");
+		return -1;
+	}
+	memcpy(tmp_str->s, pres_uri.s, pres_uri.len);
+	tmp_str->len = pres_uri.len;
+	rls_contact_list = list_insert(tmp_str, rls_contact_list, &duplicate);
+	if (duplicate != 0)
+	{
+		LM_WARN("%.*s has %.*s multiple times in the same resource list\n",
+			s->watcher_uri->len, s->watcher_uri->s,
+			s->pres_uri->len, s->pres_uri->s);
+		return 1;
 	}
 
-	return pua_send_subscribe((subs_info_t*)param);
+	return pua_send_subscribe(s);
 }
 
 /**
@@ -964,14 +968,14 @@ int resource_subscriptions(subs_t* subs, xmlNodePtr xmlnode)
 
 	s.internal_update_flag = subs->internal_update_flag;
 
-	if (subs->internal_update_flag == INTERNAL_UPDATE_TRUE)
+	if (rls_contact_list != NULL)
 	{
-		if (rls_contact_list != NULL)
-		{
-			LM_WARN("contact list is not empty\n");
-			list_free(&rls_contact_list);
-		}
+		LM_WARN("contact list is not empty\n");
+		list_free(&rls_contact_list);
+	}
 
+	if (subs->internal_update_flag == INTERNAL_UPDATE_TRUE)
+	{
 		if (rls_subs_list != NULL)
 		{
 			LM_WARN("subscriber list is not empty\n");
@@ -1016,6 +1020,10 @@ int resource_subscriptions(subs_t* subs, xmlNodePtr xmlnode)
 			pkg_free(tmp_str);
 		}
 	}
+	else
+	{
+		list_free(&rls_contact_list);
+	}
 
 	pkg_free(wuri.s);
 	pkg_free(did_str.s);
@@ -1027,6 +1035,8 @@ error:
 		pkg_free(wuri.s);
 	if(did_str.s)
 		pkg_free(did_str.s);
+	if(rls_contact_list)
+		list_free(&rls_contact_list);
 	return -1;
 
 }




More information about the sr-dev mailing list