Steve,
Here is my ser.cfg. If you find any potential problems or errors with it then please let me know. The general setup here is ser-0.9 is the sip router, asterisk 1.0.1 is the voicemail server and we use a third party for PSTN access.
Click-2-Dial is not handled with FIFO commands, but rather with sipp from sourceforge because this lets us seperate the web console from the sip proxy. We do not use serweb, so we have our own web frontend replacement for serweb.
This ser.cfg makes use of the avpops module for call forwarding features and some voice mail stuff. The call forwarding stuff got rather complex because we had to make sure the number a user keyed in to their call forwarding settings was "valid". For example, if they did not have international dialing permissions then they wouldn't be allowed to have an international number in their call forwarding settings. The other complex part for the call forwarding section is the fact that you have to know in the reply_route which call forwarding number to use under different conditions, (ie forward busy versus forward no answer).
The final note is that we have our own custom ser module called xdz_tools which exposes the is_caller_blocked() and is_did_unassigned() functions.
The is_did_unassigned() function is needed so we can determine if a DID is assigned to our PRI but not allocated to a subscriber. This prevents infinite loops between our SIP proxy and the PSTN gateway.
The is_caller_blocked() function is used to determine if the callee has a line block on the caller.
Hope this helps.
Regards, Paul
# IP Legend # 99.99.99.100 - Asterisk Voicemail Server # 99.99.99.101 - Domestic US PSTN Gateway # 99.99.99.102 - International PSTN Gateway
# ------------- Initial global variables
debug=3 fork=yes log_stderror=no
listen=99.99.99.99 port=5060 children=4 server_signature=yes
# hostname matching an alias will satisfy the condition uri==myself" alias=mycompany1.com alias=mycompany2.com
# dns - Uses dns to check if it is necessary to add a "received=" field # to a via. Default is no. # rev_dns - Same as dns but use reverse DNS. dns=no rev_dns=no
# check_via - Turn on or off Via host checking when forwarding replies. # Default is no. arcane. looks for discrepancy between name and # ip address when forwarding replies. check_via=no
# syn_branch - Shall the server use stateful synonym branches? It is # faster but not reboot-safe. Default is yes. syn_branch=yes
# memlog - Debugging level for final memory statistics report. Default # is L_DBG -- memory statistics are dumped only if debug is set high. memlog=1000
# sip_warning - Should replies include extensive warnings? # By default yes, it is good for trouble-shooting. sip_warning=no
# fifo - FIFO special file pathname fifo_mode=0666 fifo="/tmp/ser_fifo" fifo_db_url="mysql://ser:number4@localhost/ser"
# reply_to_via - A hint to reply modules whether they should send reply # to IP advertised in Via. Turned off by default, which means that # replies are sent to IP address from which requests came. reply_to_via=no
# user | uid - uid to be used by the server. 99 = nobody. #uid="nobody"
# group | gid - gid to be used by the server. 99 = nobody. #gid="nobody"
# mhomed -- enable calculation of outbound interface. # useful on multihomed servers. mhomed=0
# ------------- external module loading loadmodule "/usr/local/lib/ser/modules/mysql.so" loadmodule "/usr/local/lib/ser/modules/sl.so" loadmodule "/usr/local/lib/ser/modules/tm.so" loadmodule "/usr/local/lib/ser/modules/rr.so" loadmodule "/usr/local/lib/ser/modules/maxfwd.so" loadmodule "/usr/local/lib/ser/modules/usrloc.so" loadmodule "/usr/local/lib/ser/modules/registrar.so" loadmodule "/usr/local/lib/ser/modules/auth.so" loadmodule "/usr/local/lib/ser/modules/auth_db.so" loadmodule "/usr/local/lib/ser/modules/acc.so" loadmodule "/usr/local/lib/ser/modules/exec.so" loadmodule "/usr/local/lib/ser/modules/group.so" loadmodule "/usr/local/lib/ser/modules/print.so" loadmodule "/usr/local/lib/ser/modules/textops.so" loadmodule "/usr/local/lib/ser/modules/mediaproxy.so" loadmodule "/usr/local/lib/ser/modules/uri.so" loadmodule "/usr/local/lib/ser/modules/uri_db.so" loadmodule "/usr/local/lib/ser/modules/domain.so" loadmodule "/usr/local/lib/ser/modules/xlog.so" loadmodule "/usr/local/lib/ser/modules/speeddial.so" loadmodule "/usr/local/lib/ser/modules/options.so" loadmodule "/usr/local/lib/ser/modules/avpops.so" loadmodule "/usr/local/lib/ser/modules/permissions.so" loadmodule "/usr/local/lib/ser/modules/xdz_tools.so"
# ------------ media proxy settings modparam("mediaproxy", "natping_interval", 30) modparam("mediaproxy", "sip_asymmetrics", "/usr/local/etc/ser/sip-asymmetric-clients") modparam("mediaproxy", "rtp_asymmetrics", "/usr/local/etc/ser/rtp-asymmetric-clients")
# ------------- db_url setting modparam("acc|auth_db|domain|group|permissions|speeddial|uri_db|usrloc|xdz_tools", "db_url", "mysql://ser:heslo@localhost/ser")
# ------------- use_domain setting modparam("auth_db|group|registrar|speeddial|uri_db|usrloc", "use_domain", 0)
# ------------- permissions settings modparam("permissions", "db_mode", 1) modparam("permissions", "trusted_table", "trusted")
# ------------- accounting parameters modparam("acc", "db_flag", 1) modparam("acc", "db_missed_flag", 1) modparam("acc", "log_fmt", "cdfimorstup") modparam("acc", "log_level", 1) modparam("acc", "failed_transactions", 1) modparam("acc", "report_cancels", 1) modparam("acc", "report_ack", 0)
# ------------- auth parameters # allows clear text passwords in the mysql database modparam("auth_db", "calculate_ha1", yes) modparam("auth_db", "password_column", "password") modparam("auth_db", "avps_column_int", "domn") modparam("auth_db", "avps_column_str", "uuid|rpid") modparam("auth", "rpid_prefix", "<sip:") modparam("auth", "rpid_suffix", ";user=phone>;party=calling;screen=yes;id-type=subscriber;privacy=full")
# ------------- domain parameters modparam("domain", "db_mode", 1)
# ------------- exec parameters modparam("exec", "setvars", 1) modparam("exec", "time_to_kill", 10)
# ------------- registration parameters modparam("registrar", "nat_flag", 2) modparam("registrar", "min_expires", 60) modparam("registrar", "max_expires", 86400) modparam("registrar", "default_expires", 3600) modparam("registrar", "desc_time_order", 1) modparam("registrar", "append_branches", 1)
# ------------- rr parameters # set ";lr" tag to lr=true modparam("rr", "enable_full_lr", 1)
# ------------- tm parameters modparam("tm", "fr_timer", 15) modparam("tm", "fr_inv_timer", 22) modparam("tm", "wt_timer", 5) modparam("tm", "fr_inv_timer_avp", "inv_timeout")
# ------------- usrloc parameters # 0 = disable # 1 = write-through # 2 = write-back modparam("usrloc", "db_mode", 2) modparam("usrloc", "timer_interval", 60) modparam("usrloc", "desc_time_order", 1)
#-------------- AVPOPS parameters modparam("avpops", "avp_url", "mysql://ser:heslo@localhost/ser") modparam("avpops", "avp_table", "usr_preferences") modparam("avpops", "avp_aliases", "voicemail=i:500;calltype=i:700;fwd_no_answer_type=i:701;fwd_busy_type=i:702")
# ------------- logging parameters modparam("xlog", "buf_size", 8192)
route {
# ------------------------------------------------------------------------ # Sanity Check Section # ------------------------------------------------------------------------ if (!mf_process_maxfwd_header("10")) { sl_send_reply("483", "Too Many Hops"); break; };
if (msg:len > max_len) { sl_send_reply("513", "Message Overflow"); break; };
# ------------------------------------------------------------------------ # NOTIFY Keep-Alive Section # ------------------------------------------------------------------------ if ((method=="NOTIFY") && search("^Event: keep-alive")) { sl_send_reply("200", "OK"); break; };
if ((method=="NOTIFY") && (uri=~"^sip:700@")) { sl_send_reply("200", "OK"); break; };
# ------------------------------------------------------------------------ # NOTIFY Message-Summary Section # # Event: Message-Summary is used to control the message waiting indicator # ------------------------------------------------------------------------ if ((method=="NOTIFY") && (src_ip=="99.99.99.100") && search("^Event: message-summary")) { if (lookup("location")) { t_relay(); }; break; };
# ------------------------------------------------------------------------ # OPTIONS Section # ------------------------------------------------------------------------ if (method=="OPTIONS") { options_reply(); break; };
# ------------------------------------------------------------------------ # NAT Test Section #1 # ------------------------------------------------------------------------ if (method=="REGISTER" && client_nat_test("3")) {
fix_contact(); force_rport(); setflag(2); };
# ------------------------------------------------------------------------ # Click2Dial Section # ------------------------------------------------------------------------ if (src_ip=="99.99.99.99" && (search("^From: <sip:700@") || search("^To: <sip:700@"))) { setflag(14); };
# ------------------------------------------------------------------------ # Registration Section # ------------------------------------------------------------------------ if (method=="REGISTER") {
# allow all requests from user 700 - the Click2Dial controller if (!isflagset(14)) {
if (!is_from_local()) {
sl_send_reply("403", "Unknown Domain"); break; };
if (!www_authorize("", "subscriber")) {
www_challenge("", "0"); break; };
if (!check_to()) {
sl_send_reply("401", "Unauthorized"); break; };
if (is_user_in("To", "demo-disabled")) {
sl_send_reply("403", "Your evaluation period has expired"); break; };
if (is_user_in("To", "disabled")) {
sl_send_reply("403", "Your account has been disabled"); break; }; };
# snom sip phones use this header to start their # keep-alive mechanism for NAT bindings append_to_reply("P-NAT-Refresh: 15\r\n");
if (!save("location")) {
sl_reply_error(); };
break; };
# ------------------------------------------------------------------------ # Accounting Section # # NOTE: We test for flag 14 because we do not want to record Click2Dial # entries # ------------------------------------------------------------------------ if ((method=="INVITE" || method=="BYE") && !isflagset(14)) { setflag(1); };
# ------------------------------------------------------------------------ # NAT Tear-Down Section # ------------------------------------------------------------------------ if ((method == "BYE" || method == "CANCEL")) { end_media_session(); };
# ------------------------------------------------------------------------ # Record Route Section # # we record-route all messages -- to make sure that subsequent messages # will go through our proxy; that's particularly good if upstream and # downstream entities use different transport protocol # ------------------------------------------------------------------------ if (!method=="REGISTER") { record_route(); };
# ------------------------------------------------------------------------ # Loose Route Section # # Grant route routing if route headers present # ------------------------------------------------------------------------ if (loose_route()) { route(2); break; };
# ------------------------------------------------------------------------ # Message Waiting Indicator SUBSCRIBE Section # # Make sure all SUBSCRIBE messages with header "Event: message-summary" # are sent to the voicemail server # ------------------------------------------------------------------------ if ((method=="SUBSCRIBE") && search("^Event: message-summary")) { rewritehostport("99.99.99.100:5060"); t_relay(); break; };
# ------------------------------------------------------------------------ # NAT Test Section #1 # ------------------------------------------------------------------------ if (client_nat_test("3") && !search("^Record-Route:")) { force_rport(); fix_contact(); };
# ------------------------------------------------------------------------ # Enhanced Voicemail Applications Section # # Access additional Asterisk applications at extension 701 and 702 # ------------------------------------------------------------------------ if (uri=~"^sip:70[1|2]@") { route(5); break; };
# ------------------------------------------------------------------------ # PSTN Section # # ------------------------------------------------------------------------ if (method=="INVITE") {
if (uri=~"^sip:1[0-9]{10}@") { strip(1); };
if ((uri=~"^sip:911@.*") || (uri=~"^sip:900[0-9]{7}@") || (uri=~"^sip:976[0-9]{7}@")) {
sl_send_reply("503", "Service Unavailable"); break; }; };
# ------------------------------------------------------------------------ # Alias Routing Section # ------------------------------------------------------------------------ lookup("aliases"); if (!uri==myself) { route(2); break; };
# ------------------------------------------------------------------------ # Load ACL Section # ------------------------------------------------------------------------ if (method=="INVITE" && !isflagset(14)) {
if (is_user_in("Request-URI", "voicemail")) { setflag(31); };
if (is_from_local() || is_uri_host_local()) {
if (is_user_in("From", "411")) { setflag(30); };
if (is_user_in("From", "int")) { setflag(29); };
if (is_user_in("From", "free-pstn")) { setflag(28); };
if (avp_db_load("$from/username", "s:callidblock")) { if (avp_check("s:callidblock", "eq/y/i")) { setflag(25); }; }; };
if (avp_db_load("$ruri/username", "s:anoncallrej")) { if (avp_check("s:anoncallrej", "eq/y/i")) { setflag(24); }; }; };
# ------------------------------------------------------------------------ # Anonymous Call Rejection Section # ------------------------------------------------------------------------ if (isflagset(24) && (method=="INVITE") && search("^(f|F)rom:.*(a|A)nonymous")) { route(8); break; };
# ------------------------------------------------------------------------ # 411 Directory Assistance Section # ------------------------------------------------------------------------ if (method=="INVITE" && uri=~"^sip:411@.*") {
if (isflagset(30)) {
avp_write("$from", "i:34"); avp_pushto("$ruri", "i:34"); strip_tail(7); subst_uri('/^sip:([0-9]+)@(.*)$/sip:\15551212@\2/i'); avp_delete("i:34");
route(3); break; };
sl_send_reply("503", "Service Unavailable"); break; };
# ------------------------------------------------------------------------ # Speed Dialing Section # ------------------------------------------------------------------------ if ((method=="INVITE") && (uri=~"^sip:[0-9]{2}@.*")) { sd_lookup("speed_dial"); };
# ------------------------------------------------------------------------ # 011 International Call Section # ------------------------------------------------------------------------ if (method=="INVITE" && uri=~"^sip:011[0-9]*@") { if (isflagset(29)) { route(6); } else { sl_send_reply("503", "Service Unavailable"); }; break; };
# ------------------------------------------------------------------------ # URI Compare Section # # Here we compare the "from" and "to" to see if the caller is dialing # their own extension. If so then we route to voicemail if needed # ------------------------------------------------------------------------ if (method=="INVITE") { avp_write("$from", "i:34"); if (avp_check("i:34", "eq/$ruri/i")) {
if (isflagset(31)) { route(5); break; } else { sl_send_reply("486", "Busy"); break; }; }; };
# ------------------------------------------------------------------------ # Call Block Section # ------------------------------------------------------------------------ if (is_caller_blocked()) { route(7); break; };
# ------------------------------------------------------------------------ # Do Not Disturb Section # ------------------------------------------------------------------------ if (avp_db_load("$ruri/username", "s:donotdisturb")) { if (avp_check("s:donotdisturb", "eq/y/i")) { route(5); break; }; };
# ------------------------------------------------------------------------ # Blind Call Forwarding Section # ------------------------------------------------------------------------ if (method=="INVITE") {
# here we must store the current (aka original) R-URI because if # we set call forwarding and the forwarded number is busy then we # need to use this original R-URI to determine which voicemail # box we should go to if (isflagset(31)) { avp_write("$ruri", "$voicemail"); };
if (avp_db_load("$ruri/username", "s:callfwd")) {
avp_pushto("$ruri", "s:callfwd");
# lookup the call fowarding number to see if it is a served # sip number or a PSTN number
# check forwarding number rules route(1);
if (avp_check("$calltype", "eq/-/i")) { sl_send_reply("503", "Service Unavailable"); break; };
# test for domestic PSTN gateway if (avp_check("$calltype", "eq/dom/i")) { route(3); break; };
# test for international PSTN gateway if (avp_check("$calltype", "eq/int/i")) { route(6); break; }; }; };
# ------------------------------------------------------------------------ # Call Routing Section # ------------------------------------------------------------------------ if (!lookup("location")) {
# if flag 31 (ie voicemail) is set and we made it here this means # the user's phone is not registered anywhere. We'll forward to # voicemail after this block because we need to check the call # forward settings first if (isflagset(31)) {
# flag 19 means the user has voicemail but is not online # so we need to remember to send to voicemail if call # forwarding is not enabled setflag(19); };
if (method=="INVITE") {
if (does_uri_exist()) { # subscriber record found, but they're offline sl_send_reply("480", "Temporarily Unavailable"); break; };
if (is_did_unassigned()) { # User Does Not Exist, but the DID is ours sl_send_reply("404", "User Not Found"); break; };
if (uri=~"^sip:[0-9]{10}@") {
# Send to PSTN Gateway if (isflagset(28)) { route(3); } else { sl_send_reply("503", "Service Unavailable"); };
break; }; sl_send_reply("404", "User Not Found"); break; }; };
# ------------------------------------------------------------------------ # Call Forwarding Section # ------------------------------------------------------------------------ if (method=="INVITE") {
# save R-URI in a temp AVP for later use avp_write("$ruri", "i:99");
# only load the forward no answer option if voice mail is not enabled if (!isflagset(31)) {
if (avp_db_load("$ruri/username", "s:fwdnoanswer")) {
route(1);
if (!avp_check("$calltype", "eq/-/i")) {
if (avp_check("$calltype", "eq/dom/i")) { avp_write("dom", "$fwd_no_answer_type"); } else if (avp_check("$calltype", "eq/int/i")) { avp_write("int", "$fwd_no_answer_type"); } else { avp_write("sip", "$fwd_no_answer_type"); }
setflag(27); }; }; };
if (avp_db_load("$ruri/username", "s:fwdbusy")) {
route(1);
if (!avp_check("$calltype", "eq/-/i")) {
if (avp_check("$calltype", "eq/dom/i")) { avp_write("dom", "$fwd_busy_type"); } else if (avp_check("$calltype", "eq/int/i")) { avp_write("int", "$fwd_busy_type"); } else { avp_write("sip", "$fwd_busy_type"); }
setflag(26); }; };
avp_pushto("$ruri", "i:99"); };
if (isflagset(19)) {
# send to voicemail route(5);
} else {
route(2); }; }
route[1] {
# Here we have route checks for all the call forwarding stuff. The return # values are passed as AVP $calltype as follows: # # "-" = R-URI is not allowed # "dom" = R-RURI is a domestic call # "int" = R-RURI is an international call # "sip" = R-RURI is a sip call
avp_write("-", "$calltype");
if (uri=~"^sip:1[0-9]{10}@") { strip(1); };
if ((uri=~"^sip:70[1|2]@") || (uri=~"^sip:411@.*") || (uri=~"^sip:911@.*") || (uri=~"^sip:900[0-9]{7}@") || (uri=~"^sip:976[0-9]{7}@")) { break; };
lookup("aliases"); if (!lookup("location")) {
if (uri=~"^sip:[0-9]{10}@") {
# test for domestic PSTN number
if (isflagset(28)) { avp_write("dom", "$calltype"); };
} else if (uri=~"^sip:011[0-9]*@") {
# test for international PSTN number
if (isflagset(29)) { avp_write("int", "$calltype"); }; };
break; };
avp_write("sip", "$calltype"); }
route[2] {
if ((method=="INVITE") && !allow_trusted()) {
if (!proxy_authorize("", "subscriber")) {
proxy_challenge("", "0"); break;
} else if (!check_from()) {
log(1, "Spoofed SIP call attempt"); sl_send_reply("403", "Use From=ID"); break;
} else if (!(is_from_local() || is_uri_host_local())) {
sl_send_reply("403", "Please register to use our service"); break; }; };
if (uri=~"[@:](192.168.|10.|172.(1[6-9]|2[0-9]|3[0-1]).)" && !search("^Route:")){ sl_send_reply("479", "We don't forward to private IP addresses"); break; };
if (isflagset(25)) { replace("^From:(.*)>" , "From: "Anonymous" sip:someone@anonymous.invalid"); };
if (method=="INVITE" || method=="ACK") { use_media_proxy(); };
t_on_failure("1"); t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
route[3] {
if (method=="INVITE") {
if (!proxy_authorize("", "subscriber")) {
proxy_challenge("", "0"); break;
} else if (!check_from()) {
log(1, "Spoofed SIP call attempt"); sl_send_reply("403", "Use From=ID"); break;
} else if (!(is_from_local() || is_uri_host_local())) {
sl_send_reply("403", "Please register to use our service"); break; };
# enable caller id blocking for PSTN calls if (isflagset(25)) { append_rpid_hf(); }; };
# SIP->PSTN calls get 45 seconds to timeout avp_write("i:45", "inv_timeout");
rewritehost("99.99.99.101");
if (uri=~"[@:](192.168.|10.|172.(1[6-9]|2[0-9]|3[0-1]).)" && !search("^Route:")){ sl_send_reply("479", "We don't forward to private IP addresses"); break; };
if (method=="INVITE" || method=="ACK") { use_media_proxy(); };
if (isflagset(31)) { t_on_failure("1"); };
t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
route[4] {
# voicemail route #1 # # this path this executed during these conditions: # # cond 1) the called number is in the location table # but the callee did not answer the phone # (ie, failover to voicemail)
if (isflagset(25)) { replace("^From:(.*)>" , "From: "Anonymous" sip:someone@anonymous.invalid"); };
rewritehostport("99.99.99.100:5060"); append_branch();
t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
route[5] {
# voicemail route #2 # # this path this executed during these conditions: # # cond 1) the called number is not in the location table # cond 2) the from_uri == to_uri (ie, caller==callee)
if (method=="INVITE" || method=="ACK") { use_media_proxy(); };
rewritehostport("99.99.99.100:5060");
t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
route[6] {
# All International Calls Go To BroadVox
if (method=="INVITE") {
if (!proxy_authorize("", "subscriber")) {
proxy_challenge("", "0"); break;
} else if (!check_from()) {
log(1, "Spoofed SIP call attempt"); sl_send_reply("403", "Use From=ID"); break;
} else if (!(is_from_local() || is_uri_host_local())) {
sl_send_reply("403", "Please register to use our service"); break; };
# enable caller id blocking for PSTN calls if (isflagset(25)) { append_rpid_hf(); }; };
# SIP->PSTN calls get 45 seconds to timeout avp_write("i:45", "inv_timeout");
rewritehost("99.99.99.102");
if (uri=~"[@:](192.168.|10.|172.(1[6-9]|2[0-9]|3[0-1]).)" && !search("^Route:")){ sl_send_reply("479", "We don't forward to private IP addresses"); break; };
if (method=="INVITE" || method=="ACK") { use_media_proxy(); };
t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
route[7] {
# caller blocked announcment # # this path this executed if a caller has been blocked if (method=="INVITE" || method=="ACK") { use_media_proxy(); };
rewriteuri("sip:699@99.99.99.100:5060");
t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
route[8] {
# anonymous call rejection announcment # # this path this executed for anonymous callers
if (method=="INVITE" || method=="ACK") { use_media_proxy(); };
rewriteuri("sip:698@99.99.99.100:5060");
t_on_reply("1");
if (!t_relay()) {
if (method=="INVITE" || method=="ACK") { end_media_session(); };
sl_reply_error(); }; }
onreply_route[1] {
# Not all 2xx messages have a content body so here we # make sure our Content-Length > 0 to avoid a parse error if (status=~"(180)|(183)|2[0-9][0-9]") {
if (!search("^Content-Length:\ 0")) { use_media_proxy(); }; };
if (client_nat_test("1")) { fix_contact(); }; }
failure_route[1] {
# if caller hung up then don't sent to voicemail if (t_check_status("487")) { break; };
if (isflagset(26) && t_check_status("486")) {
# forward busy is flag 26 if (avp_pushto("$ruri", "s:fwdbusy")) { avp_delete("s:fwdbusy"); append_branch(); resetflag(26);
# test for domestic PSTN gateway if (avp_check("$fwd_busy_type", "eq/dom/i")) { # test for domestic PSTN gateway route(3); } else if (avp_check("$fwd_busy_type", "eq/int/i")) { # test for international PSTN gateway route(6); } else { # default to sip call route(2); };
break; }; };
# here we can have either voicemail __OR__ forward no answer if (isflagset(27) && t_check_status("408")) {
# forward no answer is flag 27
if (avp_pushto("$ruri", "s:fwdnoanswer")) { avp_delete("s:fwdnoanswer"); append_branch(); resetflag(27);
if (avp_check("$fwd_no_answer_type", "eq/dom/i")) { # test for domestic PSTN gateway route(3); } else if (avp_check("$fwd_no_answer_type", "eq/int/i")) { # test for international PSTN gateway route(6); } else { # default to sip call route(2); };
break; };
} else if (isflagset(31) && avp_pushto("$ruri", "$voicemail")) {
avp_delete("$voicemail"); route(4); break; }; }
--- Steve Blair blairs@isc.upenn.edu wrote:
Does anyone have a working example of a config file for ser 0.9 that they can share. My 0.8.14 config keeps failing. The line numbers in the debug output indicate the problem is on a line that is blank. The NEWS file is no help.
Thanks
--
ISC Network Engineering The University of Pennsylvania 3401 Walnut Street, Suite 221A Philadelphia, PA 19104
voice: 215-573-8396
215-746-8001
fax: 215-898-9348
sip:blairs@upenn.edu
Serusers mailing list serusers@lists.iptel.org http://lists.iptel.org/mailman/listinfo/serusers
__________________________________ Do you Yahoo!? Yahoo! Mail - Helps protect you from nasty viruses. http://promotions.yahoo.com/new_mail