[reSIProcate] Target refresh in the wrong invitesession state causes abort
Scott Godin
sgodin at sipspectrum.com
Wed Apr 20 14:49:16 CDT 2016
Hi Robert,
It appears there are actually more states we don't handle this properly
in. I took a different approach and put in "catch all" like handling for
inbound INVITEs and UPDATEs in dispatchOthers. If an INVITE or UPDATE
makes it here, we will respond with a 491.
Can you try out the following code and see if it works for you?
void
InviteSession::dispatchOthers(const SipMessage& msg)
{
// handle OnGeneralFailure
// handle OnRedirect
switch (msg.header(h_CSeq).method())
{
case INVITE:
case UPDATE:
if (msg.isRequest())
{
SharedPtr<SipMessage> response(new SipMessage);
mDialog.makeResponse(*response, msg, 491);
send(response);
break;
}
case PRACK:
dispatchPrack(msg);
break;
case CANCEL:
dispatchCancel(msg);
break;
case BYE:
dispatchBye(msg);
break;
case INFO:
dispatchInfo(msg);
break;
case MESSAGE:
dispatchMessage(msg);
break;
case ACK:
// Ignore duplicate ACKs from 2xx reTransmissions
break;
default:
// handled in Dialog
WarningLog (<< "DUM delivered a "
<< msg.header(h_CSeq).unknownMethodName()
<< " to the InviteSession in state: " << toData(mState)
<< endl
<< msg);
resip_assert(0);
break;
}
}
Best Regards,
Scott
On Thu, Apr 14, 2016 at 9:18 AM, Szokovacs Robert <
robert.szokovacs at gamma.co.uk> wrote:
> Hi,
>
> We have experienced a crash (abort) in our resiprocate-based B2BUA, in
> this scenario:
> we use rtpproxy, but when it turns out to be unnecessary, we drop it
> using a pair of reinvites:
> 1, SDP-less invite to C
> 2, OK from C with SDP offer
> 3, pass on the SDP offer in invite to A,
> 4, OK from A with SDP answer
> 5, pass on the SDP answer in ACK to C,
> 6, ACK to A
>
> we also have an upstream SBC, which have multiple instances with
> fail-over capabilities. When one of the instances fail, the fail-over
> sends "target refresh" INVITEs to our B2BUA. When these two happen
> simultaneously (the reinvite being between step 2 and 5), the B2BUA will
> crash in resiprocate:
>
> 3 0x00007f7880eb4e42 in __assert_fail () from
> /lib/x86_64-linux-gnu/libc.so.6
> #4 0x00000000007eb9e6 in resip::InviteSession::dispatchOthers
> (this=0x7f784da84a50, msg=
> ...) at InviteSession.cxx:2039
> #5 0x00000000007eaee8 in
> resip::InviteSession::dispatchSentReinviteAnswered (
> this=0x7f784da84a50, msg=...) at InviteSession.cxx:1892
> #6 0x00000000007e7209 in resip::InviteSession::dispatch
> (this=0x7f784da84a50, msg=...)
> at InviteSession.cxx:1160
> #7 0x000000000082fedd in resip::ClientInviteSession::dispatch
> (this=0x7f784da84a50,
> msg=...) at ClientInviteSession.cxx:450
> #8 0x00000000007a5426 in resip::Dialog::dispatch (this=0x7f784cdf4520,
> msg=...)
> at Dialog.cxx:427
> #9 0x00000000007b56e7 in resip::DialogSet::dispatch
> (this=0x7f783f04e200, msg=...)
> at DialogSet.cxx:895
> #10 0x00000000007c7fe6 in resip::DialogUsageManager::processRequest (
> this=0x7f7882f16fd8, request=...) at DialogUsageManager.cxx:1985
> #11 0x00000000007c549f in resip::DialogUsageManager::incomingProcess (
> this=0x7f7882f16fd8, msg=...) at DialogUsageManager.cxx:1622
> #12 0x00000000007c4595 in resip::DialogUsageManager::internalProcess (
> this=0x7f7882f16fd8, msg=...) at DialogUsageManager.cxx:1446
> #13 0x00000000007c57cf in resip::DialogUsageManager::process
> (this=0x7f7882f16fd8,
> mutex=0x0) at DialogUsageManager.cxx:1656
>
> (the line numbers may vary, this trace is from an older resiprocate, but
> the crash is reproducible with the latest, too).
> We have a proposed patch, but we'd like to have a discussion about it,
> so I post it here instead of creating the pull request right away:
>
> Index: InviteSession.cxx
> ===================================================================
> --- InviteSession.cxx (revision 33950)
> +++ InviteSession.cxx (working copy)
> @@ -299,6 +299,29 @@
> }
>
> bool
> +InviteSession::isUpdating() const
> +{
> + switch (mState)
> + {
> + case SentUpdate:
> + case SentUpdateGlare:
> + case SentReinvite:
> + case SentReinviteGlare:
> + case SentReinviteNoOffer:
> + case SentReinviteAnswered:
> + case SentReinviteNoOfferGlare:
> + case ReceivedUpdate:
> + case ReceivedReinvite:
> + case ReceivedReinviteNoOffer:
> + case ReceivedReinviteSentOffer:
> + return true;
> +
> + default:
> + return false;
> + }
> +}
> +
> +bool
> InviteSession::isEarly() const
> {
> switch (mState)
> Index: InviteSession.hxx
> ===================================================================
> --- InviteSession.hxx (revision 33950)
> +++ InviteSession.hxx (working copy)
> @@ -152,6 +152,7 @@
> const SdpContents& getProposedRemoteSdp() const;
>
> bool isConnected() const;
> + bool isUpdating() const;
> bool isTerminated() const;
> bool isEarly() const; // UAC Early states
> bool isAccepted() const; // UAS States after accept is called
> Index: Dialog.cxx
> ===================================================================
> --- Dialog.cxx (revision 33950)
> +++ Dialog.cxx (working copy)
> @@ -426,6 +426,14 @@
> }
> }
>
> + if(msg.isRequest() && INVITE == msg.header(h_CSeq).method() &&
> + mInviteSession != 0 && mInviteSession->isUpdating())
> + {
> + SipMessage failure;
> + makeResponse(failure, msg, 491);
> + mDum.sendResponse(failure);
> + return;
> + }
> handleTargetRefresh(msg);
> if (msg.isRequest())
> {
>
>
> please comment
>
> br
>
> Szo
> _______________________________________________
> resiprocate-devel mailing list
> resiprocate-devel at resiprocate.org
> https://list.resiprocate.org/mailman/listinfo/resiprocate-devel
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://list.resiprocate.org/pipermail/resiprocate-devel/attachments/20160420/a43cf90f/attachment.htm>
More information about the resiprocate-devel
mailing list