📄 sipdialogvoipserver.cxx
字号:
/* Copyright (C) 2004-2006 the Minisip Team This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA *//* Copyright (C) 2004 * * Authors: Erik Eliasson <eliasson@it.kth.se> * Johan Bilien <jobi@via.ecp.fr> * Joachim Orrblad <joachim[at]orrblad.com>*//* Name * SipDialogVoipServer.cxx * Author * Erik Eliasson, eliasson@it.kth.se * Purpose * */#include<config.h>#include<libminisip/sip/SipDialogVoipServer.h>#include<libmutil/massert.h>//#include<libmsip/SipDialogContainer.h>#include<libmsip/SipTransactionInviteClientUA.h>#include<libmsip/SipTransactionInviteServerUA.h>#include<libmsip/SipTransactionNonInviteClient.h>#include<libmsip/SipTransactionNonInviteServer.h>#include<libmsip/SipTransactionUtils.h>#include<libmsip/SipCommandString.h>#include<libmsip/SipHeaderWarning.h>#include<libmsip/SipHeaderContact.h>#include<libmsip/SipHeaderFrom.h>#include<libmsip/SipHeaderRoute.h>#include<libmsip/SipHeaderRequire.h>#include<libmsip/SipHeaderTo.h>#include<libmsip/SipMIMEContent.h>#include<libmsip/SipMessageContent.h>#include<libmutil/itoa.h>#include<libmcrypto/base64.h>#include<libmutil/Timestamp.h>#include<libmutil/termmanip.h>#include<libmutil/dbg.h>#include<libmsip/SipSMCommand.h>#include <time.h>#include<libminisip/gui/LogEntry.h>#include<libmutil/print_hex.h>#include <iostream>#include<time.h>#ifdef _WIN32_WCE# include"../include/minisip_wce_extra_includes.h"#endifusing namespace std;/* The responsibility of the voip invite server is to accept or reject an incoming call request. It should either end up in the in_call state or be terminated. The super class, SipDialogVoip handles calls after they have been established. This class adds two states, start and ringing. The in_call, termwait and terminated states are inherited from the super-class (they have dotted borders in the diagram below). The "dotted" states are implemented in SipDialogVoip.cxx. +---------------+ | | | start | | | +---------------+ | | INVITE | a3001:transIR; send 180 V +---------------+ | | | ringing |----------+ reject | | | a3005:send40X +---------------+ | | | CANCEL | accept_invite & | a3004:transCancelResp | authok | | a3002: send 200 | BYE V | a3003:transByeResp +. . . . . . . .+ | . . | INVITE & a11 fail . in call . | a3006: send 606 . . | +. . . . . . . .+ | | | | +. . . . . . . .+ | . . | . termwait .<---------+ . . +. . . . . . . .+ +. . . . . . . .+ . . . terminated . . . + . . . . . . . + */bool SipDialogVoipServer::a3001_start_ringing_INVITE( const SipSMCommand &command){ if (transitionMatch("INVITE", command, SipSMCommand::transaction_layer, SipSMCommand::dialog_layer)){ MRef<SipRequest*> inv = (SipRequest *)*command.getCommandPacket(); string branch = inv->getDestinationBranch(); setLastInvite(inv); dialogState.updateState( inv ); //string peerUri = command.getCommandPacket()->getFrom().getString().substr(4); string peerUri = dialogState.remoteUri; getDialogConfig()->inherited->sipIdentity->setSipUri(inv->getHeaderValueTo()->getUri().getUserIpString()); //MRef<SipMessageContent *> Offer = *command.getCommandPacket()->getContent(); if(!sortMIME(*inv->getContent(), peerUri, 10)){ merr << "No MIME match" << end; return false; }#ifdef IPSEC_SUPPORT // Check if IPSEC was required if (ipsecSession->required() && !ipsecSession->offered){ cerr << "I require IPSEC or nothing at all!" << endl; return false; }#endif // cerr << "EEEEEEEE: finding transaction and adding to dialogs set"<<endl;// MRef<SipTransaction*> trans = dispatcher->getLayerTransaction()->findTransaction(branch);// massert(trans);// registerTransactionToDialog(trans); /* MRef<SipHeaderValue*> identity = command.getCommandPacket()->getHeaderValueNo(SIP_HEADER_TYPE_IDENTITY, 0); MRef<SipHeaderValue*> identityinfo = command.getCommandPacket()->getHeaderValueNo(SIP_HEADER_TYPE_IDENTITYINFO, 0); bool identityVerified=false; if (identity && identityinfo){ cerr << "IDENTITY: found identity and identity-info header values"<< endl; assert(dynamic_cast<SipHeaderValueIdentity*>( *identity)); assert(dynamic_cast<SipHeaderValueIdentityInfo*>( *identityinfo)); MRef<SipHeaderValueIdentity*> ident = (SipHeaderValueIdentity*) *identity; MRef<SipHeaderValueIdentity*> identinfo = (SipHeaderValueIdentity*) *identityinfo; cerr << "IDENTITY: algorithm is: <"<< identinfo->getParameter("alg") << ">"<< endl; //downloadCertificate( identinfo->getCertUri() ); identityVerified = verifyIdentityHeader(ident); //TODO: check that the identity is rsa-sha1 if (!identityVerified){#ifdef DEBUG_OUTPUT cerr << "IDENTITY: the verification FAILED!"<< endl;#endif } }else{ cerr << "IDENTITY: did not find identity header value"<< endl; }*/ CommandString cmdstr(dialogState.callId, SipCommandString::incoming_available, dialogState.remoteUri, (getMediaSession()->isSecure()?"secure":"unprotected") ); dispatcher->getCallback()->handleCommand("gui", cmdstr ); bool rel100Supported = inv->supported("100rel"); sendRinging(branch, rel100Supported && getDialogConfig()->inherited->use100Rel ); if( getDialogConfig()->inherited->autoAnswer ){ CommandString accept( dialogState.callId, SipCommandString::accept_invite ); SipSMCommand sipcmd(accept, SipSMCommand::dialog_layer, SipSMCommand::dialog_layer); dispatcher->enqueueCommand(sipcmd,HIGH_PRIO_QUEUE/*, PRIO_LAST_IN_QUEUE*/); } return true; }else{ return false; }}bool SipDialogVoipServer::a3002_ringing_incall_accept( const SipSMCommand &command){ if (transitionMatch(command, SipCommandString::accept_invite, SipSMCommand::dialog_layer, SipSMCommand::dialog_layer)){#ifdef ENABLE_TS ts.save(USER_ACCEPT);#endif CommandString cmdstr(dialogState.callId, SipCommandString::invite_ok,"", (getMediaSession()->isSecure()?"secure":"unprotected") ); dispatcher->getCallback()->handleCommand("gui", cmdstr ); massert( !getLastInvite().isNull() ); sendInviteOk(getLastInvite()->getDestinationBranch() ); getMediaSession()->start(); MRef<LogEntry *> logEntry = new LogEntryIncomingCompletedCall(); logEntry->start = time( NULL ); logEntry->peerSipUri = getLastInvite()->getFrom().getString(); setLogEntry( logEntry ); return true; }else{ return false; }}bool SipDialogVoipServer::a3003_ringing_termwait_BYE( const SipSMCommand &command){ if (transitionMatch("BYE", command, SipSMCommand::transaction_layer, SipSMCommand::dialog_layer) && dialogState.remoteTag != ""){ MRef<SipRequest*> bye = (SipRequest*) *command.getCommandPacket(); //mdbg << "log stuff"<< end; if( getLogEntry() ){ ((LogEntrySuccess *)(*( getLogEntry() )))->duration = time( NULL ) - getLogEntry()->start; getLogEntry()->handle(); }/* MRef<SipTransaction*> byeresp = new SipTransactionNonInviteServer(sipStack, //MRef<SipDialog*>(this), bye->getCSeq(), bye->getCSeqMethod(), bye->getLastViaBranch(), dialogState.callId); //TODO: remove second argument dispatcher->getLayerTransaction()->addTransaction(byeresp); registerTransactionToDialog(byeresp); SipSMCommand cmd(command); cmd.setDestination(SipSMCommand::transaction_layer); cmd.setSource(command.getSource()); dispatcher->enqueueCommand(cmd, HIGH_PRIO_QUEUE);*/ sendByeOk(bye, /*byeresp->getBranch()*/"" ); CommandString cmdstr(dialogState.callId, SipCommandString::remote_hang_up); dispatcher->getCallback()->handleCommand("gui", cmdstr); getMediaSession()->stop(); signalIfNoTransactions(); return true; }else{ return false; }}bool SipDialogVoipServer::a3004_ringing_termwait_CANCEL( const SipSMCommand &command){ if (transitionMatch("CANCEL", command, SipSMCommand::transaction_layer, SipSMCommand::dialog_layer)) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -