Hi!
Up to now I could avoid Kamailio setups with Kamailio behind NAt. But this time I have to deal with it. That's why I want to ask what others did as best practice.
The scenario is:
Asterisk 1----\ Kamailio+RTPPROXY \ |10.10.0.2 Asterisk n------\ | --------|------------- FW --SIP-trunk--- ITSP Freeswitch 1----/ 10.10.0.1 public-IP / Freeswitch n--/ 10.10.0.x
Kamailio and rtpproxy have a private IP. Internal communication uses private IPs, external communication uses a public IP which is NATed 1:1 to Kamailio's IP address. No registrations, just forwarding of messages.
Using the global "advertised_address" setting with the public IP does not work, as there is also internal communication. Using set_advertised_address() is also cumbersome.
So it seems, the easiest solution would be to use 2 sockets on Kamailio, e.g. port 5050 and port 5060. Then I could use the listen with dedicated advertised addresses: listen=udp:10.10.0.2:5050 listen=udp:10.10.0.2:5060 advertise pu.bl.ic.ip:5060
If I understand it correctly, this should solve all issues with Record-Routing and Via-headers.
For RTP-Proxy it seems necessary to detect the direction of each message and set the IP address in rtpproxy_manage("","ip.add.re.ss") manually.
Thus, it seems straight forward - or do I miss something? Any comments and practical experience?
Thanks Klaus
Hello Klauss,
I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2).
I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip
Regards, Ovidiu Sas
Before we start, know this: I am a total Kamailio/SER noob. There. I admitted it. This is my first attempt. I seek wisdom from you experienced, all-knowing wise ones!
I've searched many hours about this problem, read thru the docs about the modules, etc. etc.
Here's the setup.
Centos 5.x Kamailio 3.3.3 Asterisk 1.6.x
We have one Asterisk based PBX. We have two trunk sip accounts. Both to the same voip provider machine. Their system is such that the two accounts are billed separately, but they need to have them at two different ip/port combinations.
Asterisk can only listen for SIP on one port, and it for sure can only send responses from one port.
The voip provider only listens on one port: 5060. Pretty normal, actually, right?
So, I create the first sip account, going directly to the voip provider, just like normal, from/to Asterisk.
But, on Asterisk, the second sip account is pointed to port 25061 on localhost.
On the same system as Asterisk, I have installed kamailio. It will listen on localhost:25061.
It also listens on the network address, port 45061.
And for that second account, the voip provider is set up to talk to our machine at port 45061.
And I programmed kamailio to shuttle incoming packets from Asterisk on 25061 to the voip provider via the 45061 port.
And, the incoming packets from the Voip provider on port 45061 are shuttled to Asterisk via the 25061 port.
At least, that's the intention!
But it's not working that way.
In the following config stuff, 100.100.100.100 is the IP of my asterisk box. 200.200.200.200 is the IP of the voip provider.
I'm using a stock kamailio.cfg file, with some changes.
disable_tcp = yes ## I don't think I need tcp...
listen=udp:127.0.0.1:25061 # primary Asterisk port listen=udp:100.100.100.100:45061 # My boxes external IP address on the internet.
port=25060 ## do I really need this?
request_route {
# per request initial checks route(REQINIT);
if (src_ip=="127.0.0.1") { # outgoing SIP from Asterisk if(dst_port==25061) { #realm 3 if( !t_relay("200.200.200.200",5060) ) # The IP of the voip provider { sl_reply_error(); break; } force_send_socket(udp:100.100.100.100:45061); #This machine's IP } } else { # incoming SIP from voip provider if(dst_port==45061) { # voip provider trunk if(!t_relay("127.0.0.1",5060) ) # The realm primary IP { sl_reply_error(); break; } force_send_socket(udp:127.0.0.1:25061); #This machine's IP } } }
The only other route block I kept from the original was the route[REQINIT] stuff.
Nothing fancy. Could easily be, that I took out too much.
When I try to make an outgoing call from the Asterisk server, out to the voip provider, I see this:
0(3150) ERROR: <core> [udp_server.c:598]: ERROR: udp_send: sendto(sock,0xb5d2a870,1007,0,200.200.200.200:5060,16): Invalid argument(22) 0(3150) : <core> [udp_server.c:603]: CRITICAL: invalid sendtoparameters one possible reason is the server is bound to localhost and attempts to send to the net 0(3150) ERROR: tm [../../forward.h:150]: msg_send: ERROR: udp_send failed 0(3150) DEBUG: tm [t_fwd.c:1365]: t_send_branch: send to 200.200.200.200:5060 (1) failed 0(3150) ERROR: tm [t_fwd.c:1383]: ERROR: t_send_branch: sending request on branch 0 failed 0(3150) DEBUG: tm [t_funcs.c:361]: ERROR:tm:t_relay_to: t_forward_nonack returned error 0(3150) DEBUG: tm [t_funcs.c:369]: -477 error reply generation delayed 0(3150) DEBUG: <core> [msg_translator.c:206]: check_via_address(127.0.0.1, 100.100.100.100, 0) 0(3150) ERROR: sl [sl_funcs.c:371]: ERROR: sl_reply_error used: Unfortunately error on sending to next hop occurred (477/SL) 0(3150) DEBUG: tm [t_lookup.c:1532]: t_unref: delayed error reply generation(-477) 0(3150) DEBUG: <core> [msg_translator.c:206]: check_via_address(127.0.0.1, 100.100.100.100, 0) 0(3150) DEBUG: tm [t_reply.c:1543]: DEBUG: cleanup_uac_timers: RETR/FR timers reset 0(3150) DEBUG: tm [t_reply.c:703]: DEBUG: reply sent out. buf=0xb7b96d78: SIP/2.0 477 Unfortun..., shmem=0xb5d2a648: SIP/2.0 477 Unfortun 0(3150) DEBUG: tm [t_reply.c:713]: DEBUG: _reply_light: finished
So, is the above a reasonable approach? Is there a better way to handle things?
What's the deal with 127.0.0.1 traffic not being OK? why is sendto having problems?
If I were to want to do this for several trunks, why can't I use switch (dst_port) {} ?
I'm probably pretty off-track on all this; any help you folks can provide will surely be appreciated.
murf
Hey Klaus
The way you described works for me (on EC2) and I think is a good solution.
Be sure to set mhomed=1 in your config.
Richard
On 4 January 2013 17:57, Ovidiu Sas osas@voipembedded.com wrote:
Hello Klauss,
I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2).
I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip
Regards, Ovidiu Sas
-- VoIP Embedded, Inc. http://www.voipembedded.com
On Thu, Jan 3, 2013 at 5:11 AM, Klaus Darilion klaus.mailinglists@pernau.at wrote:
Hi!
Up to now I could avoid Kamailio setups with Kamailio behind NAt. But
this
time I have to deal with it. That's why I want to ask what others did as best practice.
The scenario is:
Asterisk 1----\ Kamailio+RTPPROXY \ |10.10.0.2 Asterisk n------\ | --------|------------- FW --SIP-trunk--- ITSP Freeswitch 1----/ 10.10.0.1 public-IP / Freeswitch n--/ 10.10.0.x
Kamailio and rtpproxy have a private IP. Internal communication uses
private
IPs, external communication uses a public IP which is NATed 1:1 to Kamailio's IP address. No registrations, just forwarding of messages.
Using the global "advertised_address" setting with the public IP does not work, as there is also internal communication. Using set_advertised_address() is also cumbersome.
So it seems, the easiest solution would be to use 2 sockets on Kamailio, e.g. port 5050 and port 5060. Then I could use the listen with dedicated advertised addresses: listen=udp:10.10.0.2:5050 listen=udp:10.10.0.2:5060 advertise pu.bl.ic.ip:5060
If I understand it correctly, this should solve all issues with Record-Routing and Via-headers.
For RTP-Proxy it seems necessary to detect the direction of each message
and
set the IP address in rtpproxy_manage("","ip.add.re.ss") manually.
Thus, it seems straight forward - or do I miss something? Any comments
and
practical experience?
Thanks Klaus
SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
Hi Richard!
I wonder why I have to set mhomed. In the scenario I described both sockets are in the same network segment and I would guess that automatic socket selection will not work and always chooses the same socket. I think I have to set the proper outgoing socket manually with force_send_socket(), regardless if mhomed is on or off.
regards Klaus
On 07.01.2013 02:20, Richard Brady wrote:
Hey Klaus
The way you described works for me (on EC2) and I think is a good solution.
Be sure to set mhomed=1 in your config.
Richard
On 4 January 2013 17:57, Ovidiu Sas <osas@voipembedded.com mailto:osas@voipembedded.com> wrote:
Hello Klauss, I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2). I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip Regards, Ovidiu Sas -- VoIP Embedded, Inc. http://www.voipembedded.com On Thu, Jan 3, 2013 at 5:11 AM, Klaus Darilion <klaus.mailinglists@pernau.at <mailto:klaus.mailinglists@pernau.at>> wrote: > Hi! > > Up to now I could avoid Kamailio setups with Kamailio behind NAt. But this > time I have to deal with it. That's why I want to ask what others did as > best practice. > > The scenario is: > > > Asterisk 1----\ Kamailio+RTPPROXY > \ |10.10.0.2 > Asterisk n------\ | > --------|------------- FW --SIP-trunk--- ITSP > Freeswitch 1----/ 10.10.0.1 public-IP > / > Freeswitch n--/ > 10.10.0.x > > Kamailio and rtpproxy have a private IP. Internal communication uses private > IPs, external communication uses a public IP which is NATed 1:1 to > Kamailio's IP address. No registrations, just forwarding of messages. > > Using the global "advertised_address" setting with the public IP does not > work, as there is also internal communication. Using > set_advertised_address() is also cumbersome. > > So it seems, the easiest solution would be to use 2 sockets on Kamailio, > e.g. port 5050 and port 5060. Then I could use the listen with dedicated > advertised addresses: > listen=udp:10.10.0.2:5050 <http://10.10.0.2:5050> > listen=udp:10.10.0.2:5060 <http://10.10.0.2:5060> advertise pu.bl.ic.ip:5060 > > If I understand it correctly, this should solve all issues with > Record-Routing and Via-headers. > > For RTP-Proxy it seems necessary to detect the direction of each message and > set the IP address in rtpproxy_manage("","ip.add.re.ss") manually. > > Thus, it seems straight forward - or do I miss something? Any comments and > practical experience? > > Thanks > Klaus _______________________________________________ SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org <mailto:sr-users@lists.sip-router.org> http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
Hi all!
On 04.01.2013 18:57, Ovidiu Sas wrote:
Hello Klauss,
I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2).
I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip
I did some basic tests (incoming, outgoing, on/off-hold). The service provider's SIP trunk was an Asterisk with NAT traversal disabled. Kamailio was NATed 1:1 to the public IP address (exclusively, without port translation). I tested Kamailio only doing near-end NAT-traversal (taking care of its own NAT).
I used two IP addresses for the two sockets, but I must works also with a single IP address and different ports.
Conclusion: works :-)
Following is the setup how I tested it (if you need to add far-end NAT traversal (SIP clients behind another NAT) then it will more complex).
regards Klaus
# Service Provider for SIP Trunk: 5.5.5.5 # public IP address of Kamailio/rtpproxy: 3.3.3.3 # rtpproxy binds to 10.10.0.3 listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise 3.3.3.3:5060 mhomed=0
route[RELAY] { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2"); rtpproxy_manage("","10.10.0.3"); } else { force_send_socket("10.10.0.3"); rtpproxy_manage("","3.3.3.3"); } ... t_relay(); }
onreply_route { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2"); rtpproxy_manage("","10.10.0.3"); } else { force_send_socket("10.10.0.3"); rtpproxy_manage("","3.3.3.3"); } }
Hi Klaus
Thanks for posting the working solution.
You are right that mhomed=1 won't help if the sockets both have same IP address. Though I think if you used it with two different IPs and the correct routing tables on the OS then it would work.
In any case your solution is a good one.
Richard
On 7 January 2013 15:45, Klaus Darilion klaus.mailinglists@pernau.atwrote:
Hi all!
On 04.01.2013 18:57, Ovidiu Sas wrote:
Hello Klauss,
I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/**modules/3.3.x/modules_k/rr.**html#id2550086http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2).
I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip
I did some basic tests (incoming, outgoing, on/off-hold). The service provider's SIP trunk was an Asterisk with NAT traversal disabled. Kamailio was NATed 1:1 to the public IP address (exclusively, without port translation). I tested Kamailio only doing near-end NAT-traversal (taking care of its own NAT).
I used two IP addresses for the two sockets, but I must works also with a single IP address and different ports.
Conclusion: works :-)
Following is the setup how I tested it (if you need to add far-end NAT traversal (SIP clients behind another NAT) then it will more complex).
regards Klaus
# Service Provider for SIP Trunk: 5.5.5.5 # public IP address of Kamailio/rtpproxy: 3.3.3.3 # rtpproxy binds to 10.10.0.3 listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise 3.3.3.3:5060 mhomed=0
route[RELAY] { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2")**; rtpproxy_manage("","10.10.0.3"**); } else { force_send_socket("10.10.0.3")**; rtpproxy_manage("","3.3.3.3"); } ... t_relay(); }
onreply_route { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2")**; rtpproxy_manage("","10.10.0.3"**); } else { force_send_socket("10.10.0.3")**; rtpproxy_manage("","3.3.3.3");
}
}
______________________________**_________________ SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org http://lists.sip-router.org/**cgi-bin/mailman/listinfo/sr-**usershttp://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
Am 11.01.2013 02:12, schrieb Richard Brady:
Hi Klaus
Thanks for posting the working solution.
You are right that mhomed=1 won't help if the sockets both have same IP address.
That's true.
Though I think if you used it with two different IPs and the correct routing tables on the OS then it would work.
I have not tried it, but I think it depends on the actual setup.
If both IP addresses are in the same subnet, then it might work if Linux uses the "local" IP address for local calls and the "external" IP address for external call (i think this can be done with having the local as eth0 and the external as eth0.1 and specyfing the default gateway for eth0.1 instead for eth0.)
If the two IP addresses are in different subnets, then mhomed=1 should indeed work and the force_send_socket() calls could be removed.
regards Klaus
In any case your solution is a good one.
Richard
On 7 January 2013 15:45, Klaus Darilion <klaus.mailinglists@pernau.at mailto:klaus.mailinglists@pernau.at> wrote:
Hi all! On 04.01.2013 18:57, Ovidiu Sas wrote: Hello Klauss, I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2). I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip I did some basic tests (incoming, outgoing, on/off-hold). The service provider's SIP trunk was an Asterisk with NAT traversal disabled. Kamailio was NATed 1:1 to the public IP address (exclusively, without port translation). I tested Kamailio only doing near-end NAT-traversal (taking care of its own NAT). I used two IP addresses for the two sockets, but I must works also with a single IP address and different ports. Conclusion: works :-) Following is the setup how I tested it (if you need to add far-end NAT traversal (SIP clients behind another NAT) then it will more complex). regards Klaus # Service Provider for SIP Trunk: 5.5.5.5 # public IP address of Kamailio/rtpproxy: 3.3.3.3 # rtpproxy binds to 10.10.0.3 listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise 3.3.3.3:5060 <http://3.3.3.3:5060> mhomed=0 route[RELAY] { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2"); rtpproxy_manage("","10.10.0.3"); } else { force_send_socket("10.10.0.3"); rtpproxy_manage("","3.3.3.3"); } ... t_relay(); } onreply_route { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2"); rtpproxy_manage("","10.10.0.3"); } else { force_send_socket("10.10.0.3"); rtpproxy_manage("","3.3.3.3"); } } _______________________________________________ SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org <mailto:sr-users@lists.sip-router.org> http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
+1 Klaus - I used your tips and Kamailio is working great behind NAT. I'll try to test different types of NATs and see if SIP and RTP works perfectly for all scenarios.
Thanks and cheers Sammy
On Fri, Jan 11, 2013 at 1:42 PM, Klaus Darilion < klaus.mailinglists@pernau.at> wrote:
Am 11.01.2013 02:12, schrieb Richard Brady:
Hi Klaus
Thanks for posting the working solution.
You are right that mhomed=1 won't help if the sockets both have same IP address.
That's true.
Though I think if you used it with two different IPs and the correct routing tables on the OS then it would work.
I have not tried it, but I think it depends on the actual setup.
If both IP addresses are in the same subnet, then it might work if Linux uses the "local" IP address for local calls and the "external" IP address for external call (i think this can be done with having the local as eth0 and the external as eth0.1 and specyfing the default gateway for eth0.1 instead for eth0.)
If the two IP addresses are in different subnets, then mhomed=1 should indeed work and the force_send_socket() calls could be removed.
regards Klaus
In any case your solution is a good one.
Richard
On 7 January 2013 15:45, Klaus Darilion klaus.mailinglists@pernau.atwrote:
Hi all!
On 04.01.2013 18:57, Ovidiu Sas wrote:
Hello Klauss,
I use record_route_preset for this kind of scenarios: http://kamailio.org/docs/modules/3.3.x/modules_k/rr.html#id2550086 That was the main reason that I enhanced record_route_preset with the second parameter (see the Note on string2).
I haven't tried your idea with two sockets. Let us know if it's working. If you need to use the same port on the internal and external interface, you could add a new IP to the host and listen on two sockets on the same port and force the socket when sending a request out. listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise pu.bl.ic.ip
I did some basic tests (incoming, outgoing, on/off-hold). The service provider's SIP trunk was an Asterisk with NAT traversal disabled. Kamailio was NATed 1:1 to the public IP address (exclusively, without port translation). I tested Kamailio only doing near-end NAT-traversal (taking care of its own NAT).
I used two IP addresses for the two sockets, but I must works also with a single IP address and different ports.
Conclusion: works :-)
Following is the setup how I tested it (if you need to add far-end NAT traversal (SIP clients behind another NAT) then it will more complex).
regards Klaus
# Service Provider for SIP Trunk: 5.5.5.5 # public IP address of Kamailio/rtpproxy: 3.3.3.3 # rtpproxy binds to 10.10.0.3 listen=udp:10.10.0.2 listen=udp:10.10.0.3 advertise 3.3.3.3:5060 mhomed=0
route[RELAY] { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2"); rtpproxy_manage("","10.10.0.3"); } else { force_send_socket("10.10.0.3"); rtpproxy_manage("","3.3.3.3"); } ... t_relay(); }
onreply_route { if (src_ip == 5.5.5.5) { force_send_socket("10.10.0.2"); rtpproxy_manage("","10.10.0.3"); } else { force_send_socket("10.10.0.3"); rtpproxy_manage("","3.3.3.3");
}
}
SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing listsr-users@lists.sip-router.orghttp://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users
SIP Express Router (SER) and Kamailio (OpenSER) - sr-users mailing list sr-users@lists.sip-router.org http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-users