kamailio+rtpengine对sdp的处理

kamailio+rtpengine对sdp的处理

 

概述

使用kamailio+rtpengine的过程中,默认会使用rtpengine处理sdp信息,同时又需要对sdp信息定制,就需要对cfg配置流程中做特殊处理才能实现。

环境

CentOS 7.9

kamailio:5.8.3-bullseye docker

rtpengine:mr13.1.1.6-4 docker

需求

kamailio 5.8.3 + rtpengine 13.1.1.6,媒体代理模式。

需求点

1,需要使用rtpengine修改sdp信息中的ip地址为代理ip

2,需要对sdp信息中的“s=CounterPath eyeBeam 1.5”替换为“s=gw001”

3,需要对sdp信息中的“a=alt:1 1 : IvxRyFPx cTd2qu0Q 10.9.0.30 23592”做删除操作

 

方案1,在rtpengine_manage之后对“$avp(sdp)”做处理。

$avp(sdp) = $(avp(sdp){re.subst,/^a=alt:1.*//});

$avp(sdp) = $(avp(sdp){re.subst,/^a=alt:1.*rn//});

$avp(sdp) = $(avp(sdp){re.subst,/^a=alt:1.*r?n?//});

测试结果,处理后的sdp中删除了“a=alt:1”行,但是对于行尾换行符的处理不够充分,rn对应的"0d 0a"会删除“0d”,保留“0a”,造成sngrep和wireshark的抓包信息展示不美观。

 

kamailio+rtpengine对sdp的处理

 

方案2,在rtpengine_manage之前对“原始sdp”做处理,并需要提交修改。

replace_body("^a=alt:1.*rn","");

msg_apply_changes();

测试结果,处理后的sdp正确删除了“a=alt:1”行,换行符的处理也符合预期。

配置

测试结果使用方案2更符合需求预期。

方案2的cfg配置更复杂,也更绕,主要是“replace_body”等函数对sdp的处理并不会直接生效,而是需要调用“msg_apply_changes”提交修改生效。

修改kamailio.cfg文件,主要修改如下。

... loadmodule "textops.so" loadmodule "textopsx.so" ... loadmodule "rtpengine.so" loadmodule "sdpops.so" ... # ----- rtpengine params ----- modparam("rtpengine", "rtpengine_sock", "udp:127.0.0.1:2223") modparam("rtpengine", "read_sdp_pv", "$avp(sdp)") modparam("rtpengine", "write_sdp_pv", "$avp(sdp)") ... 	if (is_method("INVITE|UPDATE|ACK")) {		 		# proxy media  		route(RTPENGINE); 	} ... route[RTPENGINE] { 	xinfo("route[RTPENGINE]n");  	# check if have sdp 	if (!has_body("application/sdp")) 	{ 		xinfo("!has_body(application/sdp)n"); 		return; 	}  	if(ds_is_from_list("3060") || ds_is_from_list("3061")) 	{ 		# xinfo("route[RTPENGINE1], sdp(body)=$sdp(body)n"); 		replace_body("^s=CounterPath.*","s=SBC-GW001"); 		replace_body("^a=alt:1.*rn",""); 		sdp_remove_codecs_by_id("18");  		msg_apply_changes(); 		# xinfo("route[RTPENGINE2], sdp(body)=$sdp(body)n"); 		sdp_get("$avp(sdp)");  		# xinfo("route[RTPENGINE3], avp(sdp)=$avp(sdp)n");  		xinfo("route[RTPENGINE], 3060|3061n"); 		# from pub, to priv 		rtpengine_manage("replace-origin replace-session-connection direction=pub direction=priv ");  		# xinfo("route[RTPENGINE4], avp(sdp)=$avp(sdp)n");  		set_body("$avp(sdp)", "application/sdp"); 	} 	else if(ds_is_from_list("5060")) 	{ 		replace_body("^s=pjmedia.*","s=SBC-GW001"); 		replace_body("^b=AS:84.*rn",""); 		replace_body("^a=X-nat:0rn",""); 		msg_apply_changes(); 		 		sdp_get("$avp(sdp)");  		xinfo("route[RTPENGINE], 5060n"); 		# from priv, to pub 		rtpengine_manage("replace-origin replace-session-connection direction=priv direction=pub ");  		set_body("$avp(sdp)", "application/sdp"); 	}  	return; }

测试

重启kamailio,发起呼叫。

从信令中看到,经过kamailio处理的sdp信息符合预期。

kamailio+rtpengine对sdp的处理

 

总结

kamailio+rtpengine作为媒体代理的方式简单易用,转发效率高,不会修改媒体包的内容,rtp和rtcp都可以正常透传转发。

kamailio的cfg配置实例在网上较少,需要对照官方文档反复测试试验。

 

空空如常

求真得真

 

发表评论

评论已关闭。

相关文章