2
0
Эх сурвалжийг харах

ims_usrloc_pcscf: added a reverse searchin get_pcontact

- added a new parameter for reverse search in get_pcontact.
Aleksandar Yosifov 5 жил өмнө
parent
commit
71b590f446

+ 11 - 9
src/modules/ims_usrloc_pcscf/udomain.c

@@ -444,9 +444,10 @@ error:
  * @udomain_t* _d - domain to search in
  * @str* _contact - contact to search for - should be a SIP URI
  * @struct pontact** _c - contact to return to if found (null if not found)
+ * @int reverse_search - reverse search for a contact in the memory
  * @return 0 if found <>0 if not
  */
-int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact** _c) {
+int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact** _c, int reverse_search) {
 	unsigned int sl, i, j, aorhash, params_len, has_rinstance=0;
 	struct pcontact* c;
 	struct sip_uri needle_uri;
@@ -454,9 +455,10 @@ int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact**
 	char *params, *sep;
 	str rinstance = {0, 0};
         
-	LM_DBG("Searching for contact with AOR [%.*s] in P-CSCF usrloc based on VIA [%d://%.*s:%d] Received [%d://%.*s:%d], Search flag is %d\n",
+	LM_DBG("Searching for contact with AOR [%.*s] in P-CSCF usrloc based on VIA [%d://%.*s:%d] Received [%d://%.*s:%d], Search flag is %d, reverse_search %d\n",
 		contact_info->aor.len, contact_info->aor.s, contact_info->via_prot, contact_info->via_host.len, contact_info->via_host.s, contact_info->via_port,
-		contact_info->received_proto, contact_info->received_host.len, contact_info->received_host.s, contact_info->received_port, contact_info->searchflag);
+		contact_info->received_proto, contact_info->received_host.len, contact_info->received_host.s, contact_info->received_port, contact_info->searchflag,
+		reverse_search);
 
 	/* parse the uri in the NOTIFY */
 	if (contact_info->aor.len>0 && contact_info->aor.s){
@@ -501,7 +503,7 @@ int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact**
 	sl = aorhash & (_d->size - 1);
         
 	LM_DBG("get_pcontact slot is [%d]\n", sl);
-	c = _d->table[sl].first;
+	c = reverse_search ? _d->table[sl].last : _d->table[sl].first;
 
 	for (i = 0; i < _d->table[sl].n; i++) {
 		LM_DBG("comparing contact with aorhash [%u], aor [%.*s]\n", c->aorhash, c->aor.len, c->aor.s);
@@ -563,7 +565,7 @@ int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact**
 							c->rinstance.len, c->rinstance.s);
 					if ((rinstance.len == c->rinstance.len) && memcmp(rinstance.s, c->rinstance.s, rinstance.len) != 0) {
 						LM_DBG("rinstance does not match - no match here...\n");
-						c = c->next;
+						c = reverse_search ? c->prev : c->next;
 						continue;
 					}
 				}
@@ -571,7 +573,7 @@ int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact**
 				if ((contact_info->extra_search_criteria & SEARCH_SERVICE_ROUTES) && contact_info->num_service_routes > 0) {
 					LM_DBG("have %d service routes to search for\n", contact_info->num_service_routes);
 					if (contact_info->num_service_routes != c->num_service_routes) {
-						c = c->next;
+						c = reverse_search ? c->prev : c->next;
 						LM_DBG("number of service routes do not match - failing\n");
 						continue;
 					} 
@@ -588,7 +590,7 @@ int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact**
 						}
 					}
 					if (serviceroutematch == 0) {
-						c = c->next;
+						c = reverse_search ? c->prev : c->next;
 						continue;
 					}
 				}
@@ -596,14 +598,14 @@ int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact**
 				//finally check state being searched for
 				if ( (contact_info->reg_state != PCONTACT_ANY) && ((contact_info->reg_state & c->reg_state) == 0)) {
 					LM_DBG("can't find contact for requested reg state [%d] - (have [%d])\n", contact_info->reg_state, c->reg_state);
-					c = c->next;
+					c = reverse_search ? c->prev : c->next;
 					continue;
 				}
 				*_c = c;
 				return 0;
 			}
 		}
-		c = c->next;
+		c = reverse_search ? c->prev : c->next;
 	}
         
 	LM_DBG("contact not found in memory\n");

+ 1 - 1
src/modules/ims_usrloc_pcscf/udomain.h

@@ -74,7 +74,7 @@ void unlock_ulslot(udomain_t* _d, int i);
 int update_rx_regsession(struct udomain* _d, str* session_id, struct pcontact* _c);
 int update_pcontact(struct udomain* _d, struct pcontact_info* _ci, struct pcontact* _c);
 int insert_pcontact(struct udomain* _d, str* _contact, struct pcontact_info* _ci, struct pcontact** _r);
-int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact** _r);
+int get_pcontact(udomain_t* _d, pcontact_info_t* contact_info, struct pcontact** _c, int reverse_search);
 int assert_identity(udomain_t* _d, str * _host, unsigned short _port, unsigned short _proto, str * _identity);
 int delete_pcontact(udomain_t* _d, struct pcontact* _r);
 int unreg_pending_contacts_cb(udomain_t* _d, pcontact_t* _c, int type);

+ 1 - 1
src/modules/ims_usrloc_pcscf/usrloc.h

@@ -237,7 +237,7 @@ typedef struct pcontact {
     struct pcontact* next; /*!< Previous item in the hash entry */
 } pcontact_t;
 
-typedef int (*get_pcontact_t)(struct udomain* _d, pcontact_info_t* contact_info, struct pcontact** _c);
+typedef int (*get_pcontact_t)(struct udomain* _d, pcontact_info_t* contact_info, struct pcontact** _c, int reverse_search);
 
 typedef int (*assert_identity_t)(struct udomain* _d, str * _host, unsigned short _port, unsigned short _proto, str * _identity);