[sr-dev] why new tcp connection?

Iñaki Baz Castillo ibc at aliax.net
Fri Nov 6 12:16:37 CET 2009

El Viernes, 6 de Noviembre de 2009, Andrei Pelinescu-Onciul escribió:
> On Nov 06, 2009 at 08:12, Juha Heinanen <jh at tutpro.com> wrote:
> > twinkle is registered over tcp to sr using source port 59056 destination
> > port 5060.  in contact uri twinkle has put port 5074 (i need to configure
> > some fixed port there).
> >
> > when another ua calls twinkle and i see this in syslog:
> >
> > Nov  6 07:16:21 localhost /usr/sbin/sip-proxy[30133]: INFO: Routing first
> > INVITE to <sip:jh_test_fi at;transport=tcp> and <<null>>
> > Nov  6 07:16:21 localhost /usr/sbin/sip-proxy[30133]: INFO: <core>
> > [tcp_main.c:1928]: tcp_send: quick connect for 0xb54f3e60
> >
> > when i look wireshark output, i see that sr has created a new tcp
> > connection to twinkle at port 5074 even when there is already is one, but
> > not to that port.
> >
> > is this twinkle's fault, i.e., should it put in contact uri port 59056
> > instead?
> Yes, it should do either that,

Hi, I don't agree with it. When a UA uses TCP for registration the following 
occurs (no NAT between UA and proxy):

- UA listens for *incoming* requests on a predefined port (i.e: 5060 UDP/TCP).
- UA sends a TCP REGISTER from a ramdom port (i.e: 12345 TCP).
- The "Via" port of the REGISTER MUST be "5060" (the port in which UA 
- The "Contact" port of the REGISTER MUST be "5060" (the port in which UA 
listens). Yes, this is what RFC 3261 states.
- The proxy must send the response of the REGISTER using the existing TCP 
connection (as per RFC 3261 18.2.2).
- If the connection is no longer open, the proxy must open a new connection to 
the IP address in the "received" parameter, if present, and port in "Via" 
"sent-by", and send there the response of the REGISTER.

I think this is totally clear. The problem arises when the proxy must route an 
incoming request to the location of this UA. In this case:

- A request arrives to the proxy.
- The proxy must route it to UA's location so it inspects the location 
database and fetches the "Contact" value of the UA's REGISTER. The port 
retrieved is 5060 rather than 12345.
- So the proxy routes the request there, to UA's port 5060.  Since there is no 
TCP connection open it must open a new one. It would work as there is no NAT 
and UA is listening in port 5060 TCP.

NOTE: Must of the UA's accept incoming requests arriving to the port from 
which they sent the REGISTER, but this is not specified in RFC 3261 at all. Of 
course, if NAT exists the only solution is using the connection established by 
the registration process as the proxy couldn't open a new connection with 
natted UA.

So answering to this question:

> is this twinkle's fault, i.e., should it put in contact uri port 59056
> instead?

Not at all per RFC 3261. Perhaps the hyper-complex draft-outbound states that 
the TCP UA must bind on the source port from which the REGISTER is sent, no 
idea. But for sure RFC 3261 doesn't say that.

> or add an alias parameter to its Via
> (assuming that the port in Via _is_ 5074).
> If it does add "alias" to the Via, make sure you have
> tcp_accept_aliases=yes in the config.

What is an "alias" parameter in the Via header?

> > or should sr figure out that twinkle in fact is behind the tcp
> > connection it created when it registered itself no matter what the port
> > in contact uri is?
> You can force that, using force_tcp_alias() (adds src_ip:port_in_via as
> an alias for src_ip:src_port).
> If the port in Via is not 5074 then you can work around that too, using
> force_tcp_alias(5074) (based maybe on looking at the contact?), but in
> this case it's better to reconfigure/fix twinkle.

Please, explain it again as I don't understand what you mean with "adds 
src_ip:port_in_via as an alias for src_ip:src_port".
However I ensure that Twinkle behaviour is totally correct when using SIP TCP 
and there is nothing to fix here. In short:

- Twinkle binds on port 5060 TCP (and UDP).
- It sends a REGISTER from random port (12345). "Via" and "Contact" contains 
port 5060.
- Twinkle would accept incoming requests to both ports 5060 and 12345. 
Allowing incoming request to port 12345 helps with NAT, of course, but it's 
not specified in RFC 3261 at all, and Twinkle (or any UA) could refuse a 
request incoming from a port different than 5060 (the port it has announced as 
listening port).

An example of Twinkle TCP REGISTER:

T 2009/11/06 12:13:26.472917 -> XX.XX.XX.XX:5062
REGISTER sip:mydomain.net SIP/2.0                                            
Via: SIP/2.0/TCP;rport;branch=z9hG4bKsswrheos           
Contact: <sip:ibc_aliax_net at;transport=tcp>;expires=600  

> In general, especially if you have NATed UACs, it's better to always have
> force_tcp_alias() in the config. It will cause problems only if you have
>  non-NATed broken UACs that don't expect/support symmetric signalling
>  over TCP (e.g. open a new connection for each new request and expect
>  only replies to that request on the connection).

Symmetric signalling is about using the same src_ip:src_port - dst_ip:dst_port 
within a transaction, which involves requests and its replies. It's not about 
different transactions in both ways. For that there is a draft/RFC about TCP 
reuse and so, but it requires a "Via" parameter and some stuff...
RFC 3261 doesn't state that a UA should accept incoming requests to a port 
different than the binding port.

> OTOH if you  don't force_tcp_alias() and the UACs don't add alias to the
> Via, it's a very slim chance that NATed UACs will work over tcp.

I again ask what "add alias to the Via" means :)


Iñaki Baz Castillo <ibc at aliax.net>

More information about the sr-dev mailing list