|
|
@ -0,0 +1,842 @@ |
|
|
|
|
|
## TEMPLATE RENDER CMD: sed "s|{{SIP_IP}}|184.106.171.135|g;s|{{SIP_PORT}}|5060|g;s|{{SIP_TLS_PORT}}|5061|g" opensips.tmp > opensips.cfg |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Core Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# chroot= |
|
|
|
|
|
# group="opensips" |
|
|
|
|
|
# user="opensips" |
|
|
|
|
|
# dbversion_table= |
|
|
|
|
|
disable_core_dump=no |
|
|
|
|
|
max_while_loops=100 |
|
|
|
|
|
maxbuffer=262144 |
|
|
|
|
|
memdump=3 |
|
|
|
|
|
memlog=2 |
|
|
|
|
|
# open_files_limit=2048 |
|
|
|
|
|
server_signature=no |
|
|
|
|
|
server_header="Server: 2600hz" |
|
|
|
|
|
user_agent_header="User-Agent: 2600hz" |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Core Fork Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
fork=yes |
|
|
|
|
|
children=8 |
|
|
|
|
|
tcp_children=8 |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Core Logging Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
debug=3 |
|
|
|
|
|
sip_warning=0 |
|
|
|
|
|
log_stderror=no |
|
|
|
|
|
log_facility=LOG_LOCAL0 |
|
|
|
|
|
log_name="opensips" |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Aliases |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
auto_aliases=yes |
|
|
|
|
|
alias=localhost |
|
|
|
|
|
alias=localhost.localdomain |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Connectivity |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
listen=udp:eth0:{{SIP_PORT}} |
|
|
|
|
|
listen=udp:eth0:7000 |
|
|
|
|
|
listen=tcp:eth0:{{SIP_PORT}} |
|
|
|
|
|
listen=tcp:eth0:7000 |
|
|
|
|
|
tos=IPTOS_LOWDELAY |
|
|
|
|
|
# advertised_address={{SIP_IP}} |
|
|
|
|
|
# advertised_port={{SIP_PORT}} |
|
|
|
|
|
mcast_loopback=no |
|
|
|
|
|
mcast_ttl=1 |
|
|
|
|
|
mhomed=0 |
|
|
|
|
|
# tcp_accept_aliases |
|
|
|
|
|
tcp_connect_timeout=3 |
|
|
|
|
|
tcp_connection_lifetime=120 |
|
|
|
|
|
tcp_max_connections=2048 |
|
|
|
|
|
# tcp_poll_method=select |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## DNS |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
dns=no |
|
|
|
|
|
dns_retr_time=1 |
|
|
|
|
|
dns_retr_no=3 |
|
|
|
|
|
# dns_servers_no=2 |
|
|
|
|
|
dns_try_ipv6=no |
|
|
|
|
|
disable_dns_blacklist=yes |
|
|
|
|
|
disable_dns_failover=no |
|
|
|
|
|
dns_use_search_list=no |
|
|
|
|
|
rev_dns=no |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## SIP |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
check_via=0 |
|
|
|
|
|
#! disable_503_translation=no |
|
|
|
|
|
disable_stateless_fwd=no |
|
|
|
|
|
disable_tcp=no |
|
|
|
|
|
# disable_tls=no |
|
|
|
|
|
#! reply_to_via=1 |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## TLS |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# disable_tls=no |
|
|
|
|
|
# listen=tls:{{SIP_IP}}:{{SIP_TLS_PORT}} |
|
|
|
|
|
# tls_verify_server=1 |
|
|
|
|
|
# tls_verify_client=1 |
|
|
|
|
|
# tls_require_client_certificate=0 |
|
|
|
|
|
# tls_method=TLSv1 |
|
|
|
|
|
# tls_certificate="/usr/local/etc/opensips/tls/user/user-cert.pem" |
|
|
|
|
|
# tls_private_key="/usr/local/etc/opensips/tls/user/user-privkey.pem" |
|
|
|
|
|
# tls_ca_list="/usr/local/etc/opensips/tls/user/user-calist.pem" |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Destination Blacklist |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# dst_blacklist=gw:{( tcp , 192.168.2.100 , 5060 , "" ),( any , 192.168.2.101 , 0 , "" )} |
|
|
|
|
|
# dst_blacklist=net_filter2:{ !( any , 192.168.30.0/255.255.255.0 , 0 , "" )} |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Attribute Value Pairs |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# avp_aliases="uuid=I:660;email=s:email_addr;fwd=i:753" |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Module Loading |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
mpath="/usr/lib64/opensips/modules/" |
|
|
|
|
|
loadmodule "localcache.so" |
|
|
|
|
|
loadmodule "signaling.so" |
|
|
|
|
|
loadmodule "sl.so" |
|
|
|
|
|
loadmodule "tm.so" |
|
|
|
|
|
loadmodule "dialog.so" |
|
|
|
|
|
loadmodule "maxfwd.so" |
|
|
|
|
|
loadmodule "rr.so" |
|
|
|
|
|
loadmodule "path.so" |
|
|
|
|
|
loadmodule "uri.so" |
|
|
|
|
|
loadmodule "textops.so" |
|
|
|
|
|
loadmodule "usrloc.so" |
|
|
|
|
|
loadmodule "nathelper.so" |
|
|
|
|
|
loadmodule "nat_traversal.so" |
|
|
|
|
|
loadmodule "uac_redirect.so" |
|
|
|
|
|
loadmodule "dispatcher.so" |
|
|
|
|
|
loadmodule "mi_fifo.so" |
|
|
|
|
|
# loadmodule "mi_datagram.so" |
|
|
|
|
|
# loadmodule "xlog.so" |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Localcache Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("localcache", "cache_table_size", 10) |
|
|
|
|
|
modparam("localcache", "cache_clean_period", 120) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Stateless UA Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("sl", "enable_stats", 1) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## SIP Transaction UA Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("tm", "fr_timer", 2) |
|
|
|
|
|
modparam("tm", "fr_inv_timer", 120) |
|
|
|
|
|
# modparam("tm", "wt_timer", 5) |
|
|
|
|
|
# modparam("tm", "delete_timer", 2) |
|
|
|
|
|
# modparam("tm", "T1_timer", 500) |
|
|
|
|
|
# modparam("tm", "T2_timer", 4000) |
|
|
|
|
|
# modparam("tm", "ruri_matching", 1) |
|
|
|
|
|
# modparam("tm", "via1_matching", 1) |
|
|
|
|
|
# modparam("tm", "unix_tx_timeout", 2) |
|
|
|
|
|
# modparam("tm", "restart_fr_on_each_reply", 1) |
|
|
|
|
|
modparam("tm", "fr_timer_avp", "$avp(s:final_reply_timer)") |
|
|
|
|
|
# modparam("tm", "fr_inv_timer_avp", "$avp(s:final_reply_prov)") |
|
|
|
|
|
# modparam("tm", "tw_append", |
|
|
|
|
|
# "test: ua=$hdr(User-Agent) ;avp=$avp(i:10);$rb;time=$Ts") |
|
|
|
|
|
modparam("tm", "pass_provisional_replies", 1) |
|
|
|
|
|
# modparam("tm", "syn_branch", 1) |
|
|
|
|
|
# modparam("tm", "onreply_avp_mode", 0) |
|
|
|
|
|
# modparam("tm", "disable_6xx_block", 0) |
|
|
|
|
|
# modparam("tm", "enable_stats", 1) |
|
|
|
|
|
# modparam("tm", "minor_branch_flag", 3) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Max Forward Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("maxfwd", "max_limit", 30) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Record Route Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("rr", "enable_full_lr", 1) |
|
|
|
|
|
modparam("rr", "append_fromtag", 1) |
|
|
|
|
|
modparam("rr", "enable_double_rr", 0) |
|
|
|
|
|
modparam("rr", "add_username", 0) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Path Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("path", "use_received", 1) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## URI Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# modparam("uri", "aaa_url", "radius:/etc/radiusclient-ng/radiusclient.conf") |
|
|
|
|
|
modparam("uri", "use_sip_uri_host", 0) |
|
|
|
|
|
modparam("uri", "use_uri_table", 0) |
|
|
|
|
|
modparam("uri", "service_type", 10) |
|
|
|
|
|
modparam("uri", "use_domain", 1) |
|
|
|
|
|
modparam("uri", "use_uri_table", 0) |
|
|
|
|
|
# modparam("uri", "db_url", "mysql://username:password@localhost/opensips") |
|
|
|
|
|
# modparam("uri", "db_table", "uri") |
|
|
|
|
|
# modparam("uri", "user_column", "username") |
|
|
|
|
|
# modparam("uri", "domain_column", "domain") |
|
|
|
|
|
# modparam("uri", "uriuser_column", "uri_user") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## User Location Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("usrloc", "nat_bflag", 6) |
|
|
|
|
|
modparam("usrloc", "use_domain", 1) |
|
|
|
|
|
modparam("usrloc", "desc_time_order", 0) |
|
|
|
|
|
modparam("usrloc", "timer_interval", 60) |
|
|
|
|
|
modparam("usrloc", "matching_mode", 0) |
|
|
|
|
|
modparam("usrloc", "cseq_delay", 20) |
|
|
|
|
|
modparam("usrloc", "hash_size", 9) |
|
|
|
|
|
modparam("usrloc", "db_mode", 0) |
|
|
|
|
|
# modparam("usrloc", "db_url", "dbdriver://username:password@dbhost/dbname") |
|
|
|
|
|
modparam("usrloc", "fetch_rows", 2000) |
|
|
|
|
|
modparam("usrloc", "user_column", "username") |
|
|
|
|
|
modparam("usrloc", "domain_column", "domain") |
|
|
|
|
|
modparam("usrloc", "contact_column", "contact") |
|
|
|
|
|
modparam("usrloc", "expires_column", "expires") |
|
|
|
|
|
modparam("usrloc", "q_column", "q") |
|
|
|
|
|
modparam("usrloc", "callid_column", "callid") |
|
|
|
|
|
modparam("usrloc", "cseq_column", "cseq") |
|
|
|
|
|
modparam("usrloc", "methods_column", "methods") |
|
|
|
|
|
modparam("usrloc", "flags_column", "flags") |
|
|
|
|
|
modparam("usrloc", "cflags_column", "cflags") |
|
|
|
|
|
modparam("usrloc", "user_agent_column", "user_agent") |
|
|
|
|
|
modparam("usrloc", "received_column", "received") |
|
|
|
|
|
modparam("usrloc", "socket_column", "socket") |
|
|
|
|
|
modparam("usrloc", "path_column", "path") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Nathelper Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# modparam("nathelper", "rtpproxy_sock", "udp:127.0.0.1:7890") |
|
|
|
|
|
# modparam("nathelper", "natping_interval", 30) |
|
|
|
|
|
# modparam("nathelper", "ping_nated_only", 1) |
|
|
|
|
|
# modparam("nathelper", "natping_processes", 3) |
|
|
|
|
|
# modparam("nathelper", "sipping_bflag", 7) |
|
|
|
|
|
# modparam("nathelper", "sipping_from", "sip:sipcheck@{{SIP_IP}}:{{SIP_PORT}}") |
|
|
|
|
|
# modparam("nathelper", "sipping_method", "INFO") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## NAT Traversal Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("nat_traversal", "keepalive_interval", 60) |
|
|
|
|
|
modparam("nat_traversal", "keepalive_method", "OPTIONS") |
|
|
|
|
|
modparam("nat_traversal", "keepalive_from", "sip:keepalive@{{SIP_IP}}:{{SIP_PORT}}") |
|
|
|
|
|
modparam("nat_traversal", "keepalive_state_file", "/tmp/opensips_keepalive_state") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## UAC Redirect Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("uac_redirect", "default_filter", "accept") |
|
|
|
|
|
# modparam("uac_redirect", "deny_filter", NULL) |
|
|
|
|
|
# modparam("uac_redirect", "accept_filter", NULL) |
|
|
|
|
|
# modparam("uac_redirect", "acc_function", "acc_log_request") |
|
|
|
|
|
# modparam("uac_redirect", "acc_db_table", "acc") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Dispatcher Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("dispatcher", "list_file", "/etc/opensips/dispatcher.list") |
|
|
|
|
|
modparam("dispatcher", "flags", 2) |
|
|
|
|
|
modparam("dispatcher", "use_default", 0) |
|
|
|
|
|
modparam("dispatcher", "force_dst", 1) |
|
|
|
|
|
modparam("dispatcher", "dst_avp", "$avp(i:271)") |
|
|
|
|
|
modparam("dispatcher", "attrs_avp", "$avp(i:272)") |
|
|
|
|
|
modparam("dispatcher", "grp_avp", "$avp(i:273)") |
|
|
|
|
|
modparam("dispatcher", "cnt_avp", "$avp(i:274)") |
|
|
|
|
|
modparam("dispatcher", "hash_pvar", "$avp(i:273)") |
|
|
|
|
|
# modparam("dispatcher", "setid_pvar", "$var(setid)") |
|
|
|
|
|
modparam("dispatcher", "ds_ping_method", "OPTIONS") |
|
|
|
|
|
modparam("dispatcher", "ds_ping_from", "sip:sipcheck@{{SIP_IP}}:{{SIP_PORT}}") |
|
|
|
|
|
modparam("dispatcher", "ds_ping_interval", 10) |
|
|
|
|
|
# modparam("dispatcher", "ds_ping_sock", "udp:{{SIP_IP}}:{{SIP_PORT}}") |
|
|
|
|
|
modparam("dispatcher", "ds_probing_threshhold", 3) |
|
|
|
|
|
modparam("dispatcher", "ds_probing_mode", 0) |
|
|
|
|
|
modparam("dispatcher", "options_reply_codes", "501, 403, 404, 400") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## MI-FIFO Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
modparam("mi_fifo", "fifo_name", "/tmp/opensips_fifo") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## MI-Datagram Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# modparam("mi_datagram", "socket_name", "udp:127.0.0.1:8889") |
|
|
|
|
|
# modparam("mi_datagram", "children_count", 1) |
|
|
|
|
|
# modparam("mi_datagram", "unix_socket_mode", 0600) |
|
|
|
|
|
# modparam("mi_datagram", "unix_socket_group", "root") |
|
|
|
|
|
# modparam("mi_datagram", "unix_socket_user", "root") |
|
|
|
|
|
# modparam("mi_datagram", "socket_timeout", 2000) |
|
|
|
|
|
# modparam("mi_datagram", "reply_indent", "\t") |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## XLog Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
# modparam("xlog", "buf_size", 4096) |
|
|
|
|
|
# modparam("xlog", "force_color", 0) |
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Multiple Module Parameters |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
###################################################################### |
|
|
|
|
|
## Main Request Routing |
|
|
|
|
|
###################################################################### |
|
|
|
|
|
route |
|
|
|
|
|
{ |
|
|
|
|
|
# log the basic info regarding this call |
|
|
|
|
|
xlog("L_INFO", "$ci|start|recieved $oP request $rm $ou"); |
|
|
|
|
|
xlog("L_INFO", "$ci|log|source $si:$sp"); |
|
|
|
|
|
xlog("L_INFO", "$ci|log|from $fu"); |
|
|
|
|
|
xlog("L_INFO", "$ci|log|to $tu"); |
|
|
|
|
|
|
|
|
|
|
|
# check that hop cound for this request and make sure it is under 10 |
|
|
|
|
|
# to prevent endless loops |
|
|
|
|
|
if (!mf_process_maxfwd_header("10")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_WARN", "$ci|end|to many hops"); |
|
|
|
|
|
|
|
|
|
|
|
sl_send_reply("483", "We refuse to process this endless imbroglio"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# this check detemines if the opensips has routed the request to itself, |
|
|
|
|
|
# this happens because the server is the destination of the request but |
|
|
|
|
|
# we mangle it to send it else where. When that mangeling fails and we |
|
|
|
|
|
# still relay it then it just comes right back to us... |
|
|
|
|
|
if (src_ip==myself) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_WARN", "$ci|end|sourced from this server"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# currently we dont support subscribe in whistle so to keep the noise down |
|
|
|
|
|
# just end the request here. For options just end the request here as well. |
|
|
|
|
|
if (is_method("OPTIONS|SUBSCRIBE")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_NOTICE", "$ci|end|unsupported method"); |
|
|
|
|
|
|
|
|
|
|
|
sl_send_reply("503", "Rawr!!"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the source IP/port are in one of the server dispatch lists |
|
|
|
|
|
# then this request originated from one of our media servers, mark it |
|
|
|
|
|
# as such by setting flag 26 |
|
|
|
|
|
if (ds_is_in_list("$si", "", "1")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|internal inception (from media server)"); |
|
|
|
|
|
|
|
|
|
|
|
# Flag 26 marks the source as a on-net server |
|
|
|
|
|
setflag(26); |
|
|
|
|
|
|
|
|
|
|
|
setbflag(26); |
|
|
|
|
|
} |
|
|
|
|
|
# if the request source IP/port was not in any dispatcher lists |
|
|
|
|
|
# this this originated outside our equipment (carrier, client, ect) |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|external inception"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the to header has a tag attached then it implies this request |
|
|
|
|
|
# has been processed by us before (IE: a media server has added |
|
|
|
|
|
# its tag on the to header in prior messages) |
|
|
|
|
|
if (has_totag()) |
|
|
|
|
|
{ |
|
|
|
|
|
# sequential request within a dialog should |
|
|
|
|
|
# take the path determined by record-routing |
|
|
|
|
|
if (loose_route()) |
|
|
|
|
|
{ |
|
|
|
|
|
append_hf("P-hint: rr-enforced\r\n"); |
|
|
|
|
|
|
|
|
|
|
|
# if the request is an ACK from our media servers with a IP in the from domain |
|
|
|
|
|
# then bump the association |
|
|
|
|
|
#if ($(fd{ip.isip}) && isflagset(26) && is_method("ACK")) |
|
|
|
|
|
#{ |
|
|
|
|
|
#cache_store("local", "$tU", "$fd", 3600); |
|
|
|
|
|
|
|
|
|
|
|
#xlog("L_INFO", "$ci|log|maintaining contact association to media server $fd"); |
|
|
|
|
|
#} |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|forwarding based on the route set"); |
|
|
|
|
|
|
|
|
|
|
|
route(correct_transmit_and_die); |
|
|
|
|
|
} |
|
|
|
|
|
else if ( is_method("ACK") ) |
|
|
|
|
|
{ |
|
|
|
|
|
if ( t_check_trans() ) |
|
|
|
|
|
{ |
|
|
|
|
|
# non loose-route, but stateful ACK; must be an ACK after |
|
|
|
|
|
# a 487 or e.g. 404 from upstream server |
|
|
|
|
|
xlog("L_INFO", "$ci|log|in dialog request belongs to a known transaction"); |
|
|
|
|
|
|
|
|
|
|
|
route(correct_transmit_and_die); |
|
|
|
|
|
} |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
# ACK without matching transaction -> |
|
|
|
|
|
# ignore and discard |
|
|
|
|
|
xlog("L_NOTICE", "$ci|end|no matching transaction"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# request with a to tag that cant be routed loosly and is not an ACK |
|
|
|
|
|
# ignor eand discard |
|
|
|
|
|
xlog("L_WARN", "$ci|end|could not route in dialog"); |
|
|
|
|
|
|
|
|
|
|
|
sl_send_reply("486", "PC Load Letter"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the request is to cancel a transaction process it now |
|
|
|
|
|
if (is_method("CANCEL")) |
|
|
|
|
|
{ |
|
|
|
|
|
# If this cancel is part of a transaction |
|
|
|
|
|
# then pass it along to concerned parties |
|
|
|
|
|
if (t_check_trans()) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|request belogs to a known transaction"); |
|
|
|
|
|
|
|
|
|
|
|
route(correct_transmit_and_die); |
|
|
|
|
|
} |
|
|
|
|
|
# if the cancel does not belong to a known transaction or a |
|
|
|
|
|
# request that has not progressed outside this server dont relay it |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_NOTICE", "$ci|end|no matching transaction"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# If this is a retransmission it will break/stop the script |
|
|
|
|
|
# and do standard processing of the message |
|
|
|
|
|
t_check_trans(); |
|
|
|
|
|
|
|
|
|
|
|
# Except for an ACK no request should have a route set with no to tag, this would |
|
|
|
|
|
# indicate that the intial request has the Route headers and is likely someone trying |
|
|
|
|
|
# to get us to send the request were they want |
|
|
|
|
|
if (loose_route()) |
|
|
|
|
|
{ |
|
|
|
|
|
if (!is_method("ACK")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_WARN", "$ci|end|initial request contained a preloaded route set"); |
|
|
|
|
|
|
|
|
|
|
|
sl_send_reply("403", "Please leave the routing up to us"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# If the request is a register we will pass it along but we need |
|
|
|
|
|
# to add the path header (along with the received IP/port info) |
|
|
|
|
|
if (is_method("REGISTER")) |
|
|
|
|
|
{ |
|
|
|
|
|
# if we fail to add the path header then dont let it |
|
|
|
|
|
# register because it will cause issues later... |
|
|
|
|
|
if (!add_path_received()) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_ERR", "$ci|end|unable to add path"); |
|
|
|
|
|
|
|
|
|
|
|
sl_send_reply("503", "Internal path befuddlement"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|added path"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the request is not from a media server it must be for one, load a list of |
|
|
|
|
|
# currently active servers |
|
|
|
|
|
if (!isflagset(26)) |
|
|
|
|
|
{ |
|
|
|
|
|
if (ds_select_domain("1", "4")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|loaded media server list"); |
|
|
|
|
|
} |
|
|
|
|
|
# if no media server could be set with ds_select_domain then there are no |
|
|
|
|
|
# active servers, no need to conitnue |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_ERR", "$ci|end|no servers avaliable"); |
|
|
|
|
|
|
|
|
|
|
|
sl_send_reply("503", "The cake is a lie!"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the request is not from our media severs but has a contact uri in localcache |
|
|
|
|
|
# then change the routing to go to the server previously associated with it. |
|
|
|
|
|
if ($ct.fields(uri) && cache_fetch("local", "$(ct.fields(uri){uri.user})", $avp(i:55))) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|contact $(ct.fields(uri){uri.user}) is associated with media server $avp(i:55)"); |
|
|
|
|
|
|
|
|
|
|
|
# if the dispatcher list (in 271) does not start with |
|
|
|
|
|
# the request domain/port that we are sending this call |
|
|
|
|
|
# to, re-order the list so that it does |
|
|
|
|
|
if($(avp(i:271)[0]) != $avp(i:55)) |
|
|
|
|
|
{ |
|
|
|
|
|
# create a index var for our loop (arrays are start at 0 and this is a count) |
|
|
|
|
|
$var(i) = $avp(i:274) - 1; |
|
|
|
|
|
|
|
|
|
|
|
# loop over the dispatcher list |
|
|
|
|
|
while($var(i) > 0) |
|
|
|
|
|
{ |
|
|
|
|
|
# if this element in the dispatch list is the same |
|
|
|
|
|
# as the call destination |
|
|
|
|
|
if($(avp(i:271)[$var(i)]) == $avp(i:55)) |
|
|
|
|
|
{ |
|
|
|
|
|
# replace it with the first element of the list |
|
|
|
|
|
$(avp(i:271)[$(var(i))]) = $(avp(i:271)[0]); |
|
|
|
|
|
|
|
|
|
|
|
# break out of the loop |
|
|
|
|
|
$var(i) = -1; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
$var(i) = $var(i) - 1; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# handles the case were we only have two servers |
|
|
|
|
|
# and the one that we are locked to has failed |
|
|
|
|
|
if ($var(i) >= 0) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|associated media server is inactive, moving to $rd"); |
|
|
|
|
|
|
|
|
|
|
|
# leave the randomly choosen server as the destination and |
|
|
|
|
|
# overwrite the cache |
|
|
|
|
|
cache_store("local", "$(ct.fields(uri){uri.user})", "sip:$rd:$rp", 3600); |
|
|
|
|
|
|
|
|
|
|
|
cache_store("local", "$ci", "sip:$rd:$rp", 3600); |
|
|
|
|
|
} |
|
|
|
|
|
# the server we are locked to is in the active server list from then |
|
|
|
|
|
# dispatcher so re-arrange the list to try it first |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|re-ordering the dispatcher list to keep associated server first"); |
|
|
|
|
|
|
|
|
|
|
|
# set the first element of the list to the destination |
|
|
|
|
|
$(avp(i:271)[0]) = $avp(i:55); |
|
|
|
|
|
|
|
|
|
|
|
# set the domain for this request (server IP to route to) |
|
|
|
|
|
$rd = $(avp(i:55){uri.host}); |
|
|
|
|
|
|
|
|
|
|
|
# set the port for this request (server IP to route to) |
|
|
|
|
|
$rp = $(avp(i:55){uri.port}); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
# if the request is not from our media severs but has a call-id in localcache |
|
|
|
|
|
# then change the routing to go to the server previously associated with it. |
|
|
|
|
|
else if (cache_fetch("local", "$ci", $avp(i:55))) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|call-id is associated with media server $avp(i:55)"); |
|
|
|
|
|
|
|
|
|
|
|
# if the dispatcher list (in 271) does not start with |
|
|
|
|
|
# the request domain/port that we are sending this call |
|
|
|
|
|
# to, re-order the list so that it does |
|
|
|
|
|
if($(avp(i:271)[0]) != $avp(i:55)) |
|
|
|
|
|
{ |
|
|
|
|
|
# create a index var for our loop (arrays are start at 0 and this is a count) |
|
|
|
|
|
$var(i) = $avp(i:274) - 1; |
|
|
|
|
|
|
|
|
|
|
|
# loop over the dispatcher list |
|
|
|
|
|
while($var(i) > 0) |
|
|
|
|
|
{ |
|
|
|
|
|
# if this element in the dispatch list is the same |
|
|
|
|
|
# as the call destination |
|
|
|
|
|
if($(avp(i:271)[$var(i)]) == $avp(i:55)) |
|
|
|
|
|
{ |
|
|
|
|
|
# replace it with the first element of the list |
|
|
|
|
|
$(avp(i:271)[$(var(i))]) = $(avp(i:271)[0]); |
|
|
|
|
|
|
|
|
|
|
|
# break out of the loop |
|
|
|
|
|
$var(i) = -1; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
$var(i) = $var(i) - 1; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# handles the case were we only have two servers |
|
|
|
|
|
# and the one that we are locked to has failed |
|
|
|
|
|
if ($var(i) >= 0) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|associated media server is inactive, moving to $rd"); |
|
|
|
|
|
|
|
|
|
|
|
# leave the randomly choosen server as the destination and |
|
|
|
|
|
# overwrite the cache |
|
|
|
|
|
cache_store("local", "$(ct.fields(uri){uri.user})", "sip:$rd:$rp", 3600); |
|
|
|
|
|
|
|
|
|
|
|
cache_store("local", "$ci", "sip:$rd:$rp", 3600); |
|
|
|
|
|
} |
|
|
|
|
|
# the server we are locked to is in the active server list from then |
|
|
|
|
|
# dispatcher so re-arrange the list to try it first |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|re-ordering the dispatcher list to keep associated server first"); |
|
|
|
|
|
|
|
|
|
|
|
# set the first element of the list to the destination |
|
|
|
|
|
$(avp(i:271)[0]) = $avp(i:55); |
|
|
|
|
|
|
|
|
|
|
|
# set the domain for this request (server IP to route to) |
|
|
|
|
|
$rd = $(avp(i:55){uri.host}); |
|
|
|
|
|
|
|
|
|
|
|
# set the port for this request (server IP to route to) |
|
|
|
|
|
$rp = $(avp(i:55){uri.port}); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
if ($ct.fields(uri) && is_method("INVITE")) |
|
|
|
|
|
{ |
|
|
|
|
|
cache_store("local", "$(ct.fields(uri){uri.user})", "sip:$rd:$rp", 3600); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|associated contact $(ct.fields(uri){uri.user}) with media server sip:$rd:$rp"); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
# if the request is not from our media servers and no associations in localcache |
|
|
|
|
|
# then used the distribute list as is |
|
|
|
|
|
else if (!isflagset(26)) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|routing call to arbitrary media server $rd:$rp"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# for all initial request (not having been processed above in the has_totag) |
|
|
|
|
|
# that are not a register or message add this sever to the route set on the |
|
|
|
|
|
# request so subsequent messages come through this server |
|
|
|
|
|
if (!is_method("REGISTER|MESSAGE")) |
|
|
|
|
|
{ |
|
|
|
|
|
# Record the route that this request has taken |
|
|
|
|
|
# so we remain in the signaling path |
|
|
|
|
|
record_route(); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|added this server to the route set"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
route(correct_transmit_and_die); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
route[correct_transmit_and_die] |
|
|
|
|
|
{ |
|
|
|
|
|
# if the request is from a media server then assume it is going somewhere |
|
|
|
|
|
# outside our control and give that equipment longer to respond. |
|
|
|
|
|
# Also arm a branch to log the replies |
|
|
|
|
|
if (isflagset(26) || isbflagset(26)) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|provisional reply required in 6 seconds"); |
|
|
|
|
|
|
|
|
|
|
|
$avp(s:final_reply_timer) = 6; |
|
|
|
|
|
|
|
|
|
|
|
t_on_reply("external_reply"); |
|
|
|
|
|
} |
|
|
|
|
|
# otherwise the request must be for a media server |
|
|
|
|
|
# 1. remove any X-AUTH-IP headers so we will be the only one to set it |
|
|
|
|
|
# 2. set the X-AUTH-IP header for freeswitch ACLs |
|
|
|
|
|
# 3. set the final reply timer to two seconds, so we failover faster |
|
|
|
|
|
# 4. arm a logging branch for replies |
|
|
|
|
|
# 5. arm a failure branch that will try another one of our media servers when possible |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
route("nat_test_and_correct"); |
|
|
|
|
|
|
|
|
|
|
|
remove_hf("X-AUTH-IP"); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|X-AUTH-IP: $si"); |
|
|
|
|
|
|
|
|
|
|
|
append_hf("X-AUTH-IP: $si\r\n"); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|provisional reply required in 2 seconds"); |
|
|
|
|
|
|
|
|
|
|
|
$avp(s:final_reply_timer) = 2; |
|
|
|
|
|
|
|
|
|
|
|
t_on_reply("internal_reply"); |
|
|
|
|
|
|
|
|
|
|
|
t_on_failure("internal_fault"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
route("logged_relay"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
route[logged_relay] |
|
|
|
|
|
{ |
|
|
|
|
|
# try to send the request on its way, if it fails send back a |
|
|
|
|
|
# stateless error to the requestor |
|
|
|
|
|
if (t_relay()) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|pass|$rd:$rp"); |
|
|
|
|
|
} |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_ERR", "$ci|end|unable to relay message"); |
|
|
|
|
|
|
|
|
|
|
|
sl_reply_error(); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
route[nat_test_and_correct] |
|
|
|
|
|
{ |
|
|
|
|
|
# check if the request is from a client behind NAT, and fix if so... |
|
|
|
|
|
# this check looks at: |
|
|
|
|
|
# 1. if client has a private IP address (as defined by RFC1918) in the Contact field of the SIP message |
|
|
|
|
|
# 2. if client has contacted OpenSIPS from an address that is different from the one in the Via field |
|
|
|
|
|
if (client_nat_test("3")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|via address differs from source or RFC1918 address in contact"); |
|
|
|
|
|
|
|
|
|
|
|
# adds the rport parameter to the first Via header |
|
|
|
|
|
force_rport(); |
|
|
|
|
|
|
|
|
|
|
|
# will replace the IP and port in the Contact header with the IP and port |
|
|
|
|
|
# the SIP message was received from |
|
|
|
|
|
fix_contact(); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the request has a body see if it needs NAT corrections as well, |
|
|
|
|
|
# this check looks at: |
|
|
|
|
|
# 8. SDP is searched for occurrence of RFC1918 addresses |
|
|
|
|
|
if (has_body("application/sdp") && nat_uac_test("8")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|SDP contains a RFC1918 address"); |
|
|
|
|
|
|
|
|
|
|
|
# alters the SDP information in order to facilitate NAT traversal. |
|
|
|
|
|
# 2. rewrite media IP address (c=) with source IP |
|
|
|
|
|
# 8. rewrite IP from origin description (o=) with source IP |
|
|
|
|
|
fix_nated_sdp("10"); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
onreply_route[external_reply] |
|
|
|
|
|
{ |
|
|
|
|
|
# this branch handles replies that are comming from equipment |
|
|
|
|
|
# outside our control, just logging and NAT corrections |
|
|
|
|
|
xlog("L_INFO", "$ci|start|recieved external reply $rs $rr"); |
|
|
|
|
|
xlog("L_INFO", "$ci|log|source $si:$sp"); |
|
|
|
|
|
|
|
|
|
|
|
route("nat_test_and_correct"); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|pass|$(<request>si):$(<request>sp)"); |
|
|
|
|
|
|
|
|
|
|
|
# if the reply is not dropped (only provisional replies can be), |
|
|
|
|
|
# it will be injected and processed by the transaction engine. |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
onreply_route[internal_reply] |
|
|
|
|
|
{ |
|
|
|
|
|
# this branch handles replies that are comming from our |
|
|
|
|
|
# media server, just logging and NAT corrections |
|
|
|
|
|
xlog("L_INFO", "$ci|start|recieved internal reply $rs $rr"); |
|
|
|
|
|
xlog("L_INFO", "$ci|log|source $si:$sp"); |
|
|
|
|
|
|
|
|
|
|
|
# if one of our media servers has replied with a 407 or 401 associate |
|
|
|
|
|
# this call-id with that media server so the next "initial" requests |
|
|
|
|
|
# go to it (IE: the reply to the challenge) |
|
|
|
|
|
if (t_check_status("(407)|(401)") && $(si{ip.isip}) && ds_is_in_list("$si", "", "1")) |
|
|
|
|
|
{ |
|
|
|
|
|
cache_store("local", "$ci", "sip:$si:$sp", 3600); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|associated call-id with media server sip:$si:$sp"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|pass|$(<request>si):$(<request>sp)"); |
|
|
|
|
|
|
|
|
|
|
|
# if the reply is not dropped (only provisional replies can be), |
|
|
|
|
|
# it will be injected and processed by the transaction engine. |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
failure_route[internal_fault] |
|
|
|
|
|
{ |
|
|
|
|
|
# if the failure cause was due to the transaction being |
|
|
|
|
|
# cancelled then we are complete |
|
|
|
|
|
if (t_was_cancelled()) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|end|transaction was cancelled"); |
|
|
|
|
|
|
|
|
|
|
|
exit; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if the failure case was soemthing that we should recover |
|
|
|
|
|
# from then try to find a new media server |
|
|
|
|
|
if (t_check_status("(408)|(5[0-9][0-9])")) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|start|recieved or generated negative reply (>=300)"); |
|
|
|
|
|
xlog("L_INFO", "$ci|log|source $si:$sp"); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_ERR", "$ci|log|moving media server $rd:$rp to probing mode"); |
|
|
|
|
|
|
|
|
|
|
|
# flag the media server that failed and start sending SIP pings |
|
|
|
|
|
# when it begins responding put it back in the lsit |
|
|
|
|
|
ds_mark_dst("p"); |
|
|
|
|
|
|
|
|
|
|
|
# ensure the endpoint is not locked to a failed server |
|
|
|
|
|
cache_remove("local", "$(ct.fields(uri){uri.user})"); |
|
|
|
|
|
cache_remove("local", "$ci"); |
|
|
|
|
|
|
|
|
|
|
|
# try to find a new media server to send the call to |
|
|
|
|
|
if(ds_next_domain()) |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_INFO", "$ci|log|routing call to next media server $rd:$rp"); |
|
|
|
|
|
|
|
|
|
|
|
# store the new callid association |
|
|
|
|
|
cache_store("local", "$ci", "sip:$rd:$rp", 3600); |
|
|
|
|
|
|
|
|
|
|
|
# if the request has a contact and is an INVITE then store the new |
|
|
|
|
|
# association |
|
|
|
|
|
if ($ct.fields(uri) && is_method("INVITE")) |
|
|
|
|
|
{ |
|
|
|
|
|
cache_store("local", "$(ct.fields(uri){uri.user})", "sip:$rd:$rp", 3600); |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|log|associated contact $(ct.fields(uri){uri.user}) with media server sip:$rd:$rp"); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
xlog("L_INFO", "$ci|pass|$rd:$rp"); |
|
|
|
|
|
|
|
|
|
|
|
# reset the final reply timer |
|
|
|
|
|
$avp(s:final_reply_timer) = 2; |
|
|
|
|
|
|
|
|
|
|
|
t_on_reply("internal_reply"); |
|
|
|
|
|
|
|
|
|
|
|
t_on_failure("internal_fault"); |
|
|
|
|
|
|
|
|
|
|
|
# relay the request to the new media server |
|
|
|
|
|
t_relay(); |
|
|
|
|
|
|
|
|
|
|
|
exit(); |
|
|
|
|
|
} |
|
|
|
|
|
else |
|
|
|
|
|
{ |
|
|
|
|
|
xlog("L_ERR", "$ci|end|no other media servers avaliable"); |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
# if no new branch is generated or no reply is forced over, by default, |
|
|
|
|
|
# the winning reply will be sent back to UAC. |
|
|
|
|
|
} |