设为首页 收藏本站
开启辅助访问 切换到宽版
注册会员 找回密码

VoIP88

toasterisk 发表于 2011-6-13 22:10 | 显示全部楼层 |阅读模式
注:以下文章如需转载,请注明所属作者,转载地址,谢谢!
实验——使用LCR特性(Lab——using the LCR Feature


让我们使用LCR来执行一个简单的实验。对于这个实验,我们需要一个OpenSER服务器,两个网关和一个IP电话。你可以使用asterisk作为网关和虚拟机很容易的模拟这个实验环境。
步骤1:使用网关构建LAB。配置一台名为usa1的网关来接收以+1作为前缀的通话,另配置一台名为br1的网关来接收以+55作为前缀的通话。在网关中,你可以在将通话发送到PSTN之前添加前缀或删除一个数字。可以使用strip()和prefix()核心函数来加前缀和删除数字。要了解更多的细节,请登录www.openser.org
cd /etc/openser
cp openser.lcr openser.cfg
The script can be seen below with the modifications highlighted.
# ------------------ module loading ----------------------------------
#set module path
mpath="//lib/openser/modules/"
loadmodule "mysql.so"
loadmodule "sl.so"
loadmodule "tm.so"
loadmodule "rr.so"
loadmodule "maxfwd.so"
loadmodule "usrloc.so"
loadmodule "registrar.so"
loadmodule "textops.so"
loadmodule "uri.so"
loadmodule "uri_db.so"
loadmodule "domain.so"
loadmodule "permissions.so"
loadmodule "group.so"
loadmodule "mi_fifo.so"
loadmodule "lcr.so"
# Uncomment this if you want digest authentication
# mysql.so must be loaded !
loadmodule "auth.so"
loadmodule "auth_db.so"
# ----------------- setting module-specific parameters ---------------
modparam("mi_fifo", "fifo_name", "/tmp/openser_fifo")
modparam("usrloc", "db_mode", 2)
modparam("auth_db", "calculate_ha1", yes)
modparam("auth_db", "password_column", "password")
modparam("rr", "enable_full_lr", 1)
modparam("auth_db|permissions|uri_db|usrloc","db_url","mysql://openserpenserrw@localhost/openser")
modparam("permissions", "db_mode", 1)
modparam("permissions", "trusted_table", "trusted")
# ------------------------- request routing logic -------------------
# main routing logic
route{
#
# -- 1 -- Request Validation
#
if (!mf_process_maxfwd_header("10")) {
sl_send_reply("483","Too Many Hops");
exit;
};
if (msg:len >= 2048 ) {
sl_send_reply("513", "Message too big");
exit;
};
#
# -- 2 -- Routing Preprocessing
#
## Record-route all except Register
if (!method=="REGISTER") record_route();
##Loose_route packets
if (loose_route()) {
# marca a logica de roteamento no pedido
append_hf("-hint: roteado por loose_route\r\n");
route(1);
};

#
# -- 3 -- Determine Request Target
#
if (method=="REGISTER") {
route(2);
} else {
route(3);
};
}

route[1] {
#
# -- 4 -- Forward request to target
#
## Forward statefully
t_on_failure("1");
if (!t_relay()) {
sl_reply_error();
};
exit;
}
route[2] {
## Register request handler
if (is_uri_host_local()) {
if (!www_authorize("", "subscriber")) {
www_challenge("", "1");
exit;
};
if (!check_to()) {
sl_send_reply("403", "Forbidden");
exit;
};

save("location");
exit;
} else if {
sl_send_reply("403", "Forbidden");
};
}

route[3] {
## INVITE request handler
if (is_from_local()){
# From an internal domain -> check the credentials and the FROM
if(!allow_trusted()){
if (!proxy_authorize("","subscriber")) {
proxy_challenge("","1");
exit;
} else if (!check_from()) {
sl_send_reply("403", "Forbidden, use From=ID");
exit;
};
} else {
log("Request bypassed the auth.using allow_trusted");
};
consume_credentials();
#Verify aliases, if found replace R-URI.
lookup("aliases");
if (is_uri_host_local()) {
# -- Inbound to Inbound
route(10);
} else {
# -- Inbound to outbound
route(11);
};
} else {
#From an external domain ->do not check credentials
#Verify aliases, if found replace R-URI.
lookup("aliases");

if (is_uri_host_local()) {
#-- Outbound to inbound
route(12);
} else {
# -- Outbound to outbound
route(13);
};
};
}

route[4] {
# routing to the public network
if (!load_gws()) {
sl_send_reply("503", "Unable to load gateways");
exit;
}

if(!next_gw()){
sl_send_reply("503", "Unable to find a gateway");
exit;
}
route(1);
exit;
}

route[10] {
#from an internal domain -> inbound
#Native SIP destinations are handled using the location table
#Gateway destinations are handled by regular expressions
#In our example we will normalize the number to e164 +1305XXXXXX
#to facilitate the posterior billing.
append_hf("-hint: inbound->inbound \r\n");
if (uri=~"^sip:[2-9][0-9]{6}@") {
if (is_user_in("credentials","local")) {
# Assuming your country is USA (+1) and area code (305)
prefix("+1305");
route(4);
exit;
} else {
sl_send_reply("403", "No permissions for local calls");
exit;
};
};
if (uri=~"^sip:1[2-9][0-9]{9}@") {
if (is_user_in("credentials","ld")) {
prefix("+");
route(4);
exit;
} else {
sl_send_reply("403", "No permissions for long distance");
exit;
};
};
if (uri=~"^sip:011[0-9]*@") {
if (is_user_in("credentials","int")) {
strip(2);
prefix("+");
route(4);
exit;
} else {
sl_send_reply("403", "No permissions for international calls");
};
};

if (!lookup("location")) {
sl_send_reply("404", "Not Found");
exit;
};
route(1);
}


route[11] {
# from an internal domain -> outbound
# Simply route the call outbound using DNS search
append_hf("-hint: inbound->outbound \r\n");
route(1);
}
route[12] {
# From an external domain -> inbound
# Verify aliases, if found replace R-URI.
lookup("aliases");
if (!lookup("location")) {
sl_send_reply("404", "Not Found");
exit;
};
route(1);
}
route[13] {
#From an external domain outbound
#we are not accepting these calls
append_hf("-hint: outbound->inbound \r\n");
sl_send_reply("403", "Forbidden");
exit;
}
failure_route[1] {
if(!next_gw()) {
t_reply("503", "Service not available, no more gateways");
exit;
}
t_on_failure("1");
t_relay();
步骤3:使用ngrep抓包并确保包都能够到达正确的目的地。
步骤4:按照下面的表,使用openserctl lcr命令添加路由和网关
lcr 网关组(lcr Gateway Groups


你可以使用SerMyAdmin来插入网关组。


Lcr 网关(lcr Gateways




Lcr 路由(lcr Routes





步骤5:对任何以+1+55开头的号码进行测试
步骤6:关闭网关br1,并在此测试+55的通话。通话此时应该走另一个可供选择的网关,因为现在的br1已经关闭了。
保证re-INVITES的安全(Securing re-INVITES
既然我们连上了PSTN,那么对于安全性的考虑就很重要了。Re-INVITES在松散路由区段中被处理。这些re-INVITES不会被要求他们的凭据。为了增强安全性,需要添加下面脚本的内容到你的loose_route区段中。如果是接续请求(has_totag()),需要其拥有ROUTE头。如果它没有该头(由函数loose_route()检查得到),我们将丢弃请求并给出错误“404not here”。如果你有疑问,请查看文件openser.章节7-3
if (has_totag()) {
# sequential request withing a dialog should
# take the path determined by record-routing
if (loose_route()) {
#Check authentication of re-invites
if(method=="INVITE" && (!allow_trusted())) {
if (!proxy_authorize("","subscriber")) {
proxy_challenge("","1");
exit;
} else if (!check_from()) {
sl_send_reply("403", "Forbidden, use From=ID");
exit;
};
};
route(1);
} else {
sl_send_reply("404","Not here");
}
exit;
}
黑名单和“473/Filtered Destination”消息(Blacklists and “473/Filtered Destination messages”
DNS黑名单是用来进行DNS故障转移的特性。如果你发送一通通话给一个网关,并且这个网关不能被访问或是返回5××或6××错误码,OpenSER使用了一个叫做“dns blacklist”的资源,并将你的网关插入黑名单。在能够继续发送前,你的网关在此黑名单将持续4分钟(这个数字可以在编译时在blacklists.h中被修改)。当网关在黑名单中时,如果你试图继续向该网关发送通话,那么你将收到“473/Filtered Destination”消息。要关闭该特性(默认是打开的),可以使用下面的语句:
disable_dns_blacklist=yes
你也可以创建你自己的永久的网关黑名单或暂时的服务之外的名单。
概要(Summary
在本章中,你已经学会如何配置OpenSER来将通话前转到网关。注意安全性是很重要的。使用permissions模块你能够允许网关避开摘要认证(digest authentication)并允许他们只验证IP地址。组模块对于控制由UAC到来的访问尤其重要。确认re-INVITES的凭据也是很有趣的工作。从你连上PSTN的那一刻起,就要特别注意通行欺骗(toll fraud)。我建议你找一个安全专家定期检查你的环境。还要经常的对你的通话记录进行分析以检查出不正常的通话活动。


您需要登录后才可以回帖 登录 | 注册会员

本版积分规则

关闭

站长推荐上一条 /1 下一条

手机版|VoIP88 ( 粤ICP备11095982号   填写您的邮件地址,订阅我们的精彩内容:

GMT+8, 2017-9-24 18:32 , Processed in 0.349126 second(s), 22 queries .

Powered by VoIP88

© 2001-2017 VoIP88

快速回复 返回顶部 返回列表