[asterisk-dev] SIP Timers and "100 Trying" on a Re-INVITE. Resource leak.

Steve Davies davies147 at gmail.com
Wed Jun 13 10:27:11 CDT 2012


On 13 June 2012 15:34, Kevin P. Fleming <kpfleming at digium.com> wrote:
> On 06/13/2012 07:41 AM, Steve Davies wrote:
>>
>> Hi,
>>
>>  From my Google searches, this is a much asked but little answered
>> question that the SIP RFCs do not appear to handle. I've been using
>> the Asterisk 1.8.11.0 code to determine how Asterisk behaves, so
>> apologies if version 10 already answers this.
>>
>> In a "normal" INVITE, we have a global timeout that is specified by
>> the Dial command's ring duration, such that it all else fails,
>> app_dial or equivalent will stop the channel from existing beyond its
>> natural lifespan. With a Re-INVITE, this is not the case, and I have a
>> scenario where Asterisk leaks RTP ports:
>>
>> - Inbound call (any channel tech) to SIP endpoint A.
>> - Original call on-hold by SIP A
>> - SIP A calls SIP B, and direct-media call is set up.
>> - SIP A 'REFER's the call to bridge the inbound call to SIP B.
>> - As part of this, it Re-INVITEs the SIP A and SIP B audio back to
>> Asterisk
>
>
> By 'it' I believe you mean Asterisk, right?

I cannot believe I missed that. Yes. Asterisk sends a media-update
INVITE (Re-INVITE) to both SIP A and SIP B devices to put itself
(Asterisk) back into the Audio path. I believe this occurs as part of
the Masquerade process.

>> - SIP A has a bug that means it responds "100 Trying" to the
>> Re-INVITE, but then nothing more.
>
> Ugly.

Agreed, I am assuming that SIP A's SIP stack is internally destroying
the session state as part of completing the transfer, and "forgets" to
close it down cleanly with Asterisk first.

>> I completely appreciate that this is not Asterisk's problem, BUT it
>> leaves a potential DoS where the original SIP A RTP ports are leaked,
>> and over a period of time can prevent Asterisk and/or the host from
>> working.
>>
>> My Thoughts:
>>
>> If we know we are a Re-INVITE, set a new destroy timer on the pvt
>> after a 1xx or 18x response. I assume that we can identify a Re-INVITE
>> as an invite that it in progress on a channel that is in state
>> AST_STATE_UP ?
>
> I'm not sure what you mean by 'we are a Re-INVITE' but that could just be a
> lack of common language, since you don't speak the same English I do :-)

Pavement/Sidewalk, Trousers/Pants :) Apologies. I've had my head in
C-source files, and am not switching back to even UK English properly.

What I meant was that if the SIP A channel receives a 1xx or 18x
response to a Re-INVITE packet (A media update or COLP update INVITE,
or any other non-initial update), then perhaps we should reset the PVT
destroy timer rather than clearing it in handle_response_invite() ? A
non-initial INVITE ought to be completed in sub-1 second, so I think
allowing the default Timer B 32 seconds would be plenty?

> You have found a legitimate issue; because the other UA (SIP A) sent a
> response within the interval allowed by Timer B, Asterisk will stop
> re-transmitting the INVITE request. More importantly, there is *no*
> RFC-specified timer that will later cause the INVITE transaction to enter
> the 'Terminated' state if SIP A never sends a final response.
>
> This a somewhat convoluted, but legitimate, attack vector. If you setup a
> call with Asterisk and somehow convince *it* to send you a re-INVITE, then
> respond with 100 Trying and disappear, that dialog will never be terminated
> (except possibly via Session-Timer or RTP timeouts, but the fact that it is
> in a 'pending re-INVITE' states causes me to believe that even those won't
> get triggered).

I agree it is convoluted, but we found and caused it by using any
Aastra handset with sufficiently old firmware installed. I have not
yet established whether newer Aastra handset firmware behaves better.

RTP timeouts do not clean up the ports either. I have them configured
already, but I think they are defeated by the direct-media nature of
the call. Session-Timers may help, but the fact that the SIP channel
is mid-INVITE may even defeat that? I also believe that Session timers
require co-operation of both parties?

Should I raise this as a JIRA ticket (with the cleaned-up grammar)?

Regards,
Steve



More information about the asterisk-dev mailing list