bool WaitingForInvite::InviteRequest( DialogTracker& impl, SipMessage& request, TransactionDirectionality direction, const char* address, int port ) const { bool bTrackRequestResponse = false; impl.setTransactionDirectionality( direction ); // check is another sipX is already taking care of NAT traversing this session. if( !impl.isRequestAlreadyHandledByOther( request ) ) { bTrackRequestResponse = true; impl.markRequestAsHandledByUs( request ); // check if the INVITE contains an SDP offer if( request.hasSdpBody() ) { // request contains an SDP offer. Check if the SDP or the or the actual // location of the two endpoints impose the use of a media relay. if( impl.doesEndpointsLocationImposeMediaRelay() ) { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Media relay required", impl.name(), impl.GetCurrentState()->name() ); impl.setMediaRelayRequiredFlag(); } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Media relay not required", impl.name(), impl.GetCurrentState()->name() ); impl.clearMediaRelayRequiredFlag(); } impl.ProcessMediaOffer( request, INITIAL_OFFER_ANSWER ); ChangeState( impl, impl.pWaitingForMediaAnswer ); } else { // request does contains an SDP offer. This INVITE may be used to set up a 3PCC // call. Play it safe and impose the use of a media relay to guarantee speechpath impl.setMediaRelayRequiredFlag(); ChangeState( impl, impl.pWaitingForMediaOffer ); } } else { // this particular session is already being handled by another sipX i nthe network. // That sipX is taking care of overcoming the NATs that separate the endpoints involved // in that session. There isn't much value we can add here so just bail on tracking that // session. ChangeState( impl, impl.pMoribund ); } return bTrackRequestResponse; }
void WaitingFor200OkforInvite::SuccessfulResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_INVITE_METHOD ) == 0 ) { // normally we would not be expecting this 200 OK response to carry // an SDP however we have encountered in the field some endpoints // that repeat the SDP answer they already sent in a previous // reliable provisional response (see XECS-2079 for the details). // Given that, if an SDP answer is found, we will reprocess it // to make sure it gets the same transformations that the initial // one got as per XECS-2089. if( response.hasSdpBody() ) { impl.ProcessMediaAnswer( response, INITIAL_OFFER_ANSWER ); } ChangeState( impl, impl.pWaitingForAckForInvite ); } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected successful response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } } }
void Negotiating::FailureResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_INVITE_METHOD ) == 0 ) { // session negotiation failed. Deallocate all the tentative // media relays tentatively allocated to handle the media // sessions that just failed. impl.deallocateAndClearAllMediaRelaySessions( true, true, false ); if( !impl.getDialogEstablishedFlag() ) { // this is a final failure response to a dialog-forming INVITE. That // event marks the end of the dialog hence, we do not need to continue // to track it. ChangeState( impl, impl.pMoribund ); } else { // the renegotiation failed but the dialog is still active. Go back to state where // we wait for an incoming INVITE. ChangeState( impl, impl.pWaitingForInvite ); } } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected successful response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } } }
void ProcessingPrack::SuccessfulResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_INVITE_METHOD ) == 0 ) { // normally we would not be expecting this 200 OK response to carry // an SDP in this state however we have encountered in the field some endpoints // that repeat the SDP answer they already sent in a previous // Successful response (see XECS-2079 for the details). // Given that, if an SDP answer is found, we will reprocess it // to make sure it gets the same transformations that the initial // one got as per XECS-2089. if( response.hasSdpBody() ) { impl.ProcessMediaAnswer( response, INITIAL_OFFER_ANSWER ); } } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected Successful Response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } // We have received a response - although that does // not cause a state machine state change, we need to reset the tick counter // to show that there is still activity in this dialog. impl.resetTimerTickCounter(); } }
void TimeBoundState::CleanUpTimerTick( DialogTracker& impl ) const { if( impl.incrementTimerTickCounter() >= MAX_TIMER_TICK_COUNTS_BEFORE_DIALOG_TRACKER_CLEAN_UP ) { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - cleaning up stale dialog tracker", impl.name(), impl.GetCurrentState()->name() ); ChangeState( impl, impl.pMoribund ); } }
void DialogTrackerState::SuccessfulResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { if( impl.isARetransmittedResponse( response ) ) { impl.restoreSdpBodyOfRetransmittedResponse( response ); } else { OsSysLog::add(FAC_NAT,PRI_WARNING,"'%s': Received unexpected event SuccessfulResponse while in state '%s'", impl.name(), impl.GetCurrentState()->name() ); } }
bool DialogTrackerState::UpdateRequest( DialogTracker& impl, SipMessage& request, TransactionDirectionality direction, const char* address, int port ) const { if( impl.isARetransmittedRequest( request ) ) { impl.restoreSdpBodyOfRetransmittedRequest( request ); } else { OsSysLog::add(FAC_NAT,PRI_WARNING,"'%s': Received unexpected event UpdateRequest while in state '%s'", impl.name(), impl.GetCurrentState()->name() ); } return true; }
void WaitingForInvite::CleanUpTimerTick( DialogTracker& impl ) const { if( impl.getDialogEstablishedFlag() ) { // we have an established dialog - check it see if the media is still flowing if( !impl.wasMediaTrafficSeenInLastNSeconds( IDLE_MEDIA_MAXIMUM_IN_SECONDS ) ) { OsSysLog::add(FAC_NAT,PRI_WARNING,"'%s': Terminating dialog tracker due to excessive media inactivity period", impl.name() ); ChangeState( impl, impl.pMoribund ); } } }
void WaitingFor200OkForPrack::FailureResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_PRACK_METHOD ) == 0 ) { ChangeState( impl, impl.pWaitingForPrack ); } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected successful response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } } }
bool DialogTrackerState::InviteRequest( DialogTracker& impl, SipMessage& request, TransactionDirectionality direction, const char* address, int port ) const { if( !impl.isRequestAlreadyHandledByOther( request ) ) { impl.markRequestAsHandledByUs( request ); } if( impl.isARetransmittedRequest( request ) ) { impl.restoreSdpBodyOfRetransmittedRequest( request ); } else { Os::Logger::instance().log(FAC_NAT,PRI_WARNING,"'%s': Received unexpected event InviteRequest while in state '%s'", impl.name(), impl.GetCurrentState()->name() ); } return true; }
void WaitingFor200OkWithAnswerForPrack::SuccessfulResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_PRACK_METHOD ) == 0 ) { impl.ProcessMediaAnswer( response, NON_INITIAL_OFFER_ANSWER ); impl.modifyNonIntialOfferAnswerExchangeDoneFlag( true ); ChangeState( impl, impl.pWaitingFor200OkforInvite ); } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected successful response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } } }
void WaitingFor200OkForSlowStartPrack::FailureResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_PRACK_METHOD ) == 0 ) { // PRACK was rejected. Keep tentative INVITE media relays in case an // acceptable PRACK gets generated by the UAC. ChangeState( impl, impl.pWaitingForPrackWithMediaAnswer ); } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected failure response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } } }
void WaitingFor200OkWithAnswerForPrack::FailureResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { int seqNum; UtlString seqMethod; if( response.getCSeqField( &seqNum, &seqMethod ) ) { if( seqMethod.compareTo( SIP_PRACK_METHOD ) == 0 ) { // PRACK offer/answer failed. Deallocate any tentative media relays allocation // in preparation for that failed PRACK offer/answer negotiation. impl.deallocateAndClearAllMediaRelaySessions( false, true, false ); ChangeState( impl, impl.pWaitingForPrack ); } else { OsSysLog::add(FAC_NAT,PRI_DEBUG,"'%s:%s' - Received unexpected failure response for %s request", impl.name(), impl.GetCurrentState()->name(), seqMethod.data() ); } } }
void DialogTrackerState::CleanUpTimerTick( DialogTracker& impl ) const { OsSysLog::add(FAC_NAT,PRI_WARNING,"'%s': Received unexpected event CleanUpTimerTick while in state '%s'", impl.name(), impl.GetCurrentState()->name() ); }
void DialogTrackerState::FailureResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { OsSysLog::add(FAC_NAT,PRI_WARNING,"'%s': Received unexpected event FailureResponse while in state '%s'", impl.name(), impl.GetCurrentState()->name() ); }
void DialogTrackerState::RedirectionResponse( DialogTracker& impl, SipMessage& response, const char* address, int port ) const { Os::Logger::instance().log(FAC_NAT,PRI_WARNING,"'%s': Received unexpected event RedirectionResponse while in state '%s'", impl.name(), impl.GetCurrentState()->name() ); }