[sr-dev] git:kamailio_3.0: tm: added t_relay_to(proxy, flags)

Daniel-Constantin Mierla miconda at gmail.com
Wed Jan 6 15:40:15 CET 2010


Module: sip-router
Branch: kamailio_3.0
Commit: fc59de27f87772df40a4408485a34344acbec950
URL:    http://git.sip-router.org/cgi-bin/gitweb.cgi/sip-router/?a=commit;h=fc59de27f87772df40a4408485a34344acbec950

Author: Daniel-Constantin Mierla <miconda at gmail.com>
Committer: Daniel-Constantin Mierla <miconda at gmail.com>
Date:   Wed Jan  6 14:36:55 2010 +0100

tm: added t_relay_to(proxy, flags)

- parameters compatible with t_relay() in K old version
- proxy value can be: [proto:]host[:port]
- flgas can be 0x01, 0x04 or 0x05, 0x02 flag not supported
- all or any of the parameters can be omitted

---

 modules/tm/tm.c |  168 +++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 168 insertions(+), 0 deletions(-)

diff --git a/modules/tm/tm.c b/modules/tm/tm.c
index dcd9f83..a935755 100644
--- a/modules/tm/tm.c
+++ b/modules/tm/tm.c
@@ -146,6 +146,7 @@ static int fixup_on_reply(void** param, int param_no);
 static int fixup_on_branch(void** param, int param_no);
 static int fixup_t_reply(void** param, int param_no);
 static int fixup_on_sl_reply(modparam_t type, void* val);
+static int fixup_t_relay_to(void** param, int param_no);
 
 /* init functions */
 static int mod_init(void);
@@ -181,6 +182,7 @@ inline static int w_t_relay_to_sctp( struct sip_msg  *p_msg , char *proxy,
 inline static int w_t_relay_to_sctp_uri( struct sip_msg*, char*, char*);
 #endif
 inline static int w_t_relay_to_avp(struct sip_msg* msg, char* str,char*);
+inline static int w_t_relay_to(struct sip_msg* msg, char* str,char*);
 inline static int w_t_replicate_uri( struct sip_msg  *p_msg ,
 				char *uri,       /* sip uri as string or variable */
 				char *_foo       /* nothing expected */ );
@@ -319,6 +321,12 @@ static cmd_export_t cmds[]={
 			REQUEST_ROUTE | FAILURE_ROUTE },
 	{"t_relay_to_avp", w_t_relay_to_avp,  		2, fixup_proto_hostport2proxy,
 			REQUEST_ROUTE},
+	{"t_relay_to",			w_t_relay_to,           0, 0,
+			REQUEST_ROUTE | FAILURE_ROUTE },
+	{"t_relay_to",			w_t_relay_to,           1, fixup_t_relay_to,
+			REQUEST_ROUTE | FAILURE_ROUTE },
+	{"t_relay_to",			w_t_relay_to,           2, fixup_t_relay_to,
+			REQUEST_ROUTE | FAILURE_ROUTE },
 	{T_FORWARD_NONACK,     w_t_forward_nonack,      2, fixup_hostport2proxy,
 			REQUEST_ROUTE},
 	{T_FORWARD_NONACK_URI, w_t_forward_nonack_uri,  0, 0,
@@ -1880,3 +1888,163 @@ static int t_check_trans(struct sip_msg* msg, char* foo, char* bar)
 	}
 	return -1;
 }
+
+static int hexatoi(str *s, unsigned int* result)
+{
+	int i, xv, fact;
+
+	/* more than 32bit hexa? */
+	if (s->len>8)
+		return -1;
+
+	*result = 0;
+	fact = 1;
+
+	for(i=s->len-1; i>=0 ;i--)
+	{
+		xv = hex2int(s->s[i]);
+		if(xv<0)
+			return -1;
+
+		*result += (xv * fact);
+		fact *= 16;
+	}
+	return 0;
+}
+
+static int fixup_t_relay_to(void** param, int param_no)
+{
+
+	int port;
+	int proto;
+	unsigned int flags;
+	struct proxy_l *proxy;
+	action_u_t *a;
+	str s;
+	str host;
+
+	s.s = (char*)*param;
+	s.len = strlen(s.s);
+	LM_DBG("fixing (%s, %d)\n", s.s, param_no);
+	if (param_no==1){
+		a = fixup_get_param(param, param_no, 2);
+		if(a==NULL)
+		{
+			LM_CRIT("server error for parameter <%s>\n",s.s);
+			return E_UNSPEC;
+		}
+		if(a->u.string!=NULL) {
+			/* second parameter set, first should be proxy addr */
+			if (parse_phostport(s.s, &host.s, &host.len, &port, &proto)!=0){
+				LM_CRIT("invalid proxy addr parameter <%s>\n",s.s);
+				return E_UNSPEC;
+			}
+
+			proxy = mk_proxy(&host, port, proto);
+			if (proxy==0) {
+				LM_ERR("failed to build proxy structure for <%.*s>\n", host.len, host.s );
+				return E_UNSPEC;
+			}
+			*(param)=proxy;
+			return 0;
+		} else {
+			/* no second parameter, then is proxy addr or flags */
+			flags = 0;
+			if (s.len>2 && s.s[0]=='0' && s.s[1]=='x') {
+				s.s += 2;
+				s.len -= 2;
+				if(hexatoi(&s, &flags)<0)
+				{
+					LM_CRIT("invalid hexa flags <%s>\n", s.s);
+					return E_UNSPEC;
+				}
+				a->u.data = (void*)(unsigned long int)flags;
+				*(param)= 0;
+				return 0;
+			} else {
+				if(str2int(&s, &flags)==0)
+				{
+					a->u.data = (void*)(unsigned long int)flags;
+					*(param)= 0;
+					return 0;
+				} else {
+					/* try proxy */
+					if (parse_phostport(s.s, &host.s, &host.len, &port, &proto)!=0){
+						LM_CRIT("invalid proxy addr parameter <%s>\n",s.s);
+						return E_UNSPEC;
+					}
+
+					proxy = mk_proxy(&host, port, proto);
+					if (proxy==0) {
+						LM_ERR("failed to build proxy structure for <%.*s>\n", host.len, host.s );
+						return E_UNSPEC;
+					}
+					*(param)=proxy;
+					return 0;
+				}
+			}
+		}
+	} else if (param_no==2) {
+		/* flags */
+		flags = 0;
+		if (s.len>2 && s.s[0]=='0' && s.s[1]=='x') {
+			s.s += 2;
+			s.len -= 2;
+			if(hexatoi(&s, &flags)<0)
+			{
+				LM_CRIT("invalid hexa flags <%s>\n", s.s);
+				return E_UNSPEC;
+			}
+			*(param) = (void*)(unsigned long int)flags;
+			return 0;
+		} else {
+			if(str2int(&s, &flags)==0)
+			{
+				*(param) = (void*)(unsigned long int)flags;
+				return 0;
+			} else {
+				LM_CRIT("invalid flags <%s>\n", s.s);
+				return E_UNSPEC;
+			}
+		}
+	} else {
+		LM_ERR("invalid parameter number %d\n", param_no);
+		return E_BUG;
+	}
+}
+
+
+inline static int w_t_relay_to(struct sip_msg *msg, char *proxy, char *flags)
+{
+	unsigned int fl;
+	struct proxy_l *px;
+	fparam_t param;
+
+	fl = (unsigned int)(long)(void*)flags;
+	px = (struct proxy_l*)proxy;
+
+	if(flags!=0)
+	{
+		memset(&param, 0, sizeof(fparam_t));
+		param.type = FPARAM_INT;
+		/* no auto 100 trying */
+		if(fl&1) {
+			param.v.i = 0;
+			t_set_auto_inv_100(msg, (char*)(&param), 0);
+		}
+		/* no auto negative reply - not implemented */
+		/*
+		if(fl&2) {
+			param.v.i = 1;
+			t_set_disable_internal_reply(msg, (char*)param, 0);
+		}
+		*/
+		/* no dns failover */
+		if(fl&4) {
+			param.v.i = 1;
+			t_set_disable_failover(msg, (char*)(&param), 0);
+		}
+	}
+	return _w_t_relay_to(msg, px, PROTO_NONE);
+}
+




More information about the sr-dev mailing list