[asterisk-dev] Symmetric RTP behaviour and 'nat' peer option.
Alex Balashov
abalashov at evaristesys.com
Tue Apr 21 19:51:37 CDT 2009
My interpretation seems to be supported by main/rtp.c:ast_rtp_read():
/* Send to whoever send to us if NAT is turned on */
if (rtp->nat) {
if ((rtp->them.sin_addr.s_addr != sin.sin_addr.s_addr) ||
(rtp->them.sin_port != sin.sin_port)) {
rtp->them = sin;
if (rtp->rtcp) {
memcpy(&rtp->rtcp->them, &sin,
sizeof(rtp->rtcp->them));
rtp->rtcp->them.sin_port =
htons(ntohs(rtp->them.sin_port)+1);
}
rtp->rxseqno = 0;
ast_set_flag(rtp, FLAG_NAT_ACTIVE);
if (option_debug || rtpdebug)
ast_log(LOG_DEBUG, "RTP NAT: Got audio
from other end. Now sending to address %s:%d\n",
ast_inet_ntoa(rtp->them.sin_addr), ntohs(rtp->them.sin_port));
}
}
Yet, with nat=no, I would expect that NAT would not be "turned on."
I would expect the behaviour under nat=no to follow strict protocol
mechanics and ignore any received Layer 3 / Layer 4 characteristics, yet
that is clearly not the case.
Perhaps I am missing something about how Packet2Packet bridging works?
Thanks!
Alex Balashov wrote:
> Greetings,
>
> I am running Asterisk 1.4.21.2 and seeing some counterintuitive
> behaviour with regard to RTP and far-end NAT traversal and could use a
> little perspective.
>
> The topology looks like this:
>
> endpoint <--NAT GW--> NAT traversal fixup proxy <--> Asterisk
>
> The NAT traversal fixup proxy uses the usual far-end traversal
> techniques - mangling the Contact header to the received IP, forcing the
> use of the received port for replies, and SDP received IP endpoint
> mangling.
>
> There is a SIP peer built out to the proxy from Asterisk.
>
> Anyway, when I initiate a call from the phone to a PSTN gateway through
> this chain (Asterisk bridges the call to a PSTN gateway via SIP), I am
> seeing the following behaviour. Here is the scenario:
>
> 1) Endpoint sends INVITE to proxy;
>
> 2) Proxy does NAT traversal fixups including substitution of received
> IP in the m= line of the SDP payload.
>
> 3) Proxy statefully forwards call to Asterisk.
>
> 4) When the endpoint starts sending RTP toward Asterisk after the
> call is established, the source port of the RTP packets is
> different from the destination port announced in the endpoint's
> initial INVITE's SDP payload. This is typical of SIP NAT gateways
> without SIP-aware ALGs.
>
> And here is what I am experiencing:
>
> 1) With nat=no on the peer, Asterisk sends RTP toward the endpoint at
> the destination port specified in the SDP payload of its INVITE *until*
> it receives its first RTP packet from the endpoint. The first RTP
> packet has a different source port than what was advertised in the
> endpoint's SDP offer, and from that moment, Asterisk starts sending RTP
> to the source port of that first media packet *instead* of what is in
> the SDP.
>
> 2) With nat=yes, Asterisk ignores the source ports of incoming RTP from
> the endpoint and continues sending media to the destination port
> specified in the received SDP.
>
> ...
>
> This seems counterintuitive to me. I had always thought that nat=yes is
> what enables symmetric RTP, but it seems that the opposite is true in
> this implementation; with nat=yes, the received source port of
> subsequent RTP is ignored and the SDP is used, while with nat=no,
> attention is paid to the actual received source port.
>
> What am I missing?
>
> Thanks!
>
--
Alex Balashov
Evariste Systems
Web : http://www.evaristesys.com/
Tel : (+1) (678) 954-0670
Direct : (+1) (678) 954-0671
Mobile : (+1) (678) 237-1775
More information about the asterisk-dev
mailing list