📄 cmctrl.c
字号:
/***********************************************************************
Copyright (c) 2002 RADVISION Ltd.
************************************************************************
NOTICE:
This document contains information that is confidential and proprietary
to RADVISION Ltd.. No part of this document may be reproduced in any
form whatsoever without written prior approval by RADVISION Ltd..
RADVISION Ltd. reserve the right to revise this publication and make
changes without obligation to notify any person of such revisions or
changes.
***********************************************************************/
#include "rvinternal.h"
#include "rvh323timer.h"
#include "cm.h"
#include "cmictrl.h"
#include "cmintr.h"
#include "cmCall.h"
#include "cmConf.h"
#include "caputils.h"
#include "cmutils.h"
#include "strutils.h"
#include "prnutils.h"
#include "cmchan.h"
#include "oidutils.h"
#include "h245.h"
#include "cmCtrlCap.h"
#include "cmCtrlMSD.h"
#include "cmCtrlRTD.h"
#include "cmCtrlMMode.h"
#include "cmCtrlRMode.h"
#include "cmCtrlMPoint.h"
#include "cmChanOperations.h"
#include "cmdebprn.h"
#include "pvaltree.h"
#ifdef __cplusplus
extern "C" {
#endif
int userInput(H245Control*ctrl, int message);
/* General __________________________________________________________________________________*/
void notifyControlState(HCALL hsCall);
int cmiReportControl(IN HCALL hsCall,
IN cmControlState state,
IN cmControlStateMode stateMode)
{
callElem*call=(callElem*)hsCall;
cmElem* app;
int nesting;
app = (cmElem*)emaGetInstance((EMAElement)hsCall);
if (app->cmMySessionEvent.cmEvCallControlStateChanged != NULL)
{
#if (RV_LOGMASK_COMPILEMASK & RV_LOGLEVEL_ENTER)
static char *stateModes[]=
{ (char*)"cmControlStateModeNull",(char*)""};
static char *states[]=
{
(char*)"cmControlStateConnected",
(char*)"cmControlStateConference",
(char*)"cmControlStateTransportConnected",
(char*)"cmControlStateTransportDisconnected",
(char*)"cmControlStateFastStart",
(char*)"cmControlStateFastStartComplete"
};
cmiCBEnter((HAPP)app,(char*)"cmEvCallControlStateChanged(haCall=0x%p,hsCall=0x%p,state=%s,stateMode=%s)",emaGetApplicationHandle((EMAElement)hsCall),hsCall,nprn(states[state]),nprn(stateModes[stateMode+1]));
#endif
nesting=emaPrepareForCallback((EMAElement)hsCall);
app->cmMySessionEvent.cmEvCallControlStateChanged((HAPPCALL)emaGetApplicationHandle((EMAElement)hsCall),hsCall,state,stateMode);
emaReturnFromCallback((EMAElement)hsCall,nesting);
#if (RV_LOGMASK_COMPILEMASK & RV_LOGLEVEL_LEAVE)
cmiCBExit((HAPP)app,(char*)"cmEvCallControlStateChanged");
#endif
}
if (call->state == cmCallStateConnected)
notifyControlState(hsCall);
if ((app->mibEvent.h341AddControl != NULL) && ((state == cmControlStateConnected) || (state == cmControlStateFastStart)))
app->mibEvent.h341AddControl(app->mibHandle, hsCall);
return 0;
}
RVAPI int RVCALLCONV
cmSetSessionEventHandler(
/* Set user callbacks functions for control session. */
IN HAPP hApp,
IN CMSESSIONEVENT cmSessionEvent,
IN int size)
{
cmElem *app = (cmElem *)hApp;
if (!app) return RV_ERROR_UNKNOWN;
cmiAPIEnter((HAPP)app, "cmSetSessionEventHandler: hApp=0x%p, cmSessionEvent=0x%p, size=%d.",
hApp, cmSessionEvent, size);
app->dynamicPayloadNumber = 0;
memset(&(app->cmMySessionEvent), 0, sizeof(app->cmMySessionEvent));
memcpy(&(app->cmMySessionEvent), cmSessionEvent, (RvSize_t)RvMin((int)sizeof(app->cmMySessionEvent), size));
cmiAPIExit((HAPP)app, "cmSetSessionEventHandler: [0].");
return 0;
}
RVAPI int RVCALLCONV
cmGetControlEventHandler(
/* Set user callbacks functions for control session. */
IN HAPP hApp,
OUT CMSESSIONEVENT cmSessionEvent,
IN int size)
{
cmElem *app = (cmElem *)hApp;
if (!app) return RV_ERROR_UNKNOWN;
cmiAPIEnter((HAPP)app, "cmGetControlEventHandler: hApp=0x%p, cmSessionEvent=0x%p, size=%d.",
hApp, cmSessionEvent, size);
memset(cmSessionEvent, 0, (RvSize_t)size);
memcpy(cmSessionEvent,&(app->cmMySessionEvent), (RvSize_t)RvMin((int)sizeof(app->cmMySessionEvent), size));
cmiAPIExit((HAPP)app, "cmGetControlEventHandler: [0].");
return 0;
}
/* returns the value-tree node id of h245 configuration root node */
RVAPI
RvInt32 RVCALLCONV cmGetH245ConfigurationHandle(
IN HAPP hApp)
{
cmElem *app = (cmElem *)hApp;
if (!app) return RV_ERROR_UNKNOWN;
cmiAPIEnter((HAPP)app, "cmGetH245ConfigurationHandle: hApp=0x%p.", hApp);
cmiAPIExit((HAPP)app, "cmGetH245ConfigurationHandle: [%d].", app->h245Conf);
return app->h245Conf;
}
int
cmcReadyEvent(
/* Check if session reached ready state and if so inform application. */
H245Control* ctrl
)
{
callElem *call=(callElem *)cmiGetByControl((HCONTROL)ctrl);
cmElem* app=(cmElem*)emaGetInstance((EMAElement)call);
if (!app) return RV_ERROR_UNKNOWN;
if ((ctrl->eOutCapStatus == CapStatusAcknowledged) && (ctrl->eInCapStatus == CapStatusAcknowledged) &&
ctrl->bIsMasterSlave && ctrl->eState==ctrlInitialized)
{
if ((!cmTransIsParallel(call->hsTransSession) || m_callget(call,fastStartFinished)))
{
ctrl->eState=ctrlConnected;
cmiReportControl(cmiGetByControl((HCONTROL)ctrl), cmControlStateConnected,(cmControlStateMode)0);
if (RV_PVT_NODEID_IS_VALID(ctrl->incomingOLCs[0]))
{
openLogicalChannel(ctrl, ctrl->incomingOLCs[0]);
pvtDelete(app->hVal, ctrl->incomingOLCs[0]);
ctrl->incomingOLCs[0] = RV_PVT_INVALID_NODEID;
}
if (RV_PVT_NODEID_IS_VALID(ctrl->incomingOLCs[1]))
{
openLogicalChannel(ctrl, ctrl->incomingOLCs[1]);
pvtDelete(app->hVal, ctrl->incomingOLCs[1]);
ctrl->incomingOLCs[1] = RV_PVT_INVALID_NODEID;
}
}
}
return RV_TRUE;
}
void cmH245Start(HAPP hApp)
{
cmElem *app = (cmElem *)hApp;
/* Encode the protocol identifier that we'll use in future TCS messages */
app->h245protocolIDLen =
oidEncodeOID(sizeof(app->h245protocolID), app->h245protocolID, H245_PROTOCOL_IDENTIFIER);
}
void cmH245Stop(HAPP hApp)
{
cmElem *app = (cmElem *)hApp;
if (app);
}
void initControl(HCONTROL ctrl, int lcnOut)
{
H245Control*ctrlE=(H245Control*)ctrl;
memset((void *)ctrl,0,sizeof(H245Control));
ctrlE->logicalChannelOut=lcnOut;
ctrlE->eOutCapStatus=CapStatusReleased;
ctrlE->eInCapStatus=CapStatusReleased;
ctrlE->bIsMasterSlave=0;
ctrlE->bIsMaster=0;
ctrlE->conflictChannels=0;
ctrlE->myTerminalLabel.mcuNumber=255;
ctrlE->myTerminalLabel.terminalNumber=255;
capInit(ctrlE);
msdInit(ctrlE);
rtdInit(ctrlE);
ctrlE->multiPointMode=0;
ctrlE->eState=ctrlInitialized;
ctrlE->outRequestMode.timer = NULL;
ctrlE->incomingOLCs[0] = RV_PVT_INVALID_NODEID;
ctrlE->incomingOLCs[1] = RV_PVT_INVALID_NODEID;
}
void startControl(HCONTROL ctrl)
{
H245Control*ctrlE=(H245Control*)ctrl;
cmElem* app=(cmElem*)emaGetInstance((EMAElement)cmiGetByControl(ctrl));
HPVT hVal=app->hVal;
int capNodeId, res = 0;
if (pvtGetChild2(hVal,app->h245Conf,__h245(capabilities),__h245(manualOperation))<0 &&
(capNodeId=(pvtGetChild2(hVal,app->h245Conf,__h245(capabilities),__h245(terminalCapabilitySet)))))
{
int nodeId=pvtAddRoot(hVal,app->synProtH245,0,NULL);
int tcsNodeId=pvtAddBranch2(hVal,nodeId,__h245(request),__h245(terminalCapabilitySet));
res = pvtSetTree(hVal,tcsNodeId,hVal,capNodeId);
if (res >= 0)
res = outCapTransferRequest(ctrlE, nodeId);
pvtDelete(hVal,nodeId);
}
if ((res >= 0) && (pvtGetChild2(hVal,app->h245Conf,__h245(masterSlave),__h245(manualOperation))<0))
msdDetermineRequest(ctrlE, -1, -1);
}
/************************************************************************
* stopControl
* purpose: Stop the H245 Control connection for a call.
* input : ctrl - Control object
* output : none
* return : Non-negative value on success
* Negative value on failure
************************************************************************/
void stopControl(IN HCONTROL ctrl)
{
H245Control*ctrlE=(H245Control*)ctrl;
cmElem* app=(cmElem*)emaGetInstance((EMAElement)cmiGetByControl(ctrl));
int nodeId, message;
HPVT hVal=app->hVal;
/* Make sure we close all the channels */
closeChannels(ctrl);
/* Send an endSession message if we have to */
if (ctrlE->eState==ctrlConnected || ctrlE->eState==ctrlConference || ctrlE->eState==ctrlInitialized)
{
/* Create an endSession command message */
message=pvtAddRoot(hVal,app->synProtH245,0,NULL);
nodeId=pvtAddBranch2(hVal,message,__h245(command), __h245(endSessionCommand) );
pvtAddBranch(hVal,nodeId,__h245(disconnect));
/* Send the endSession message */
sendMessageH245(ctrl, message);
/* Kill the created message */
pvtDelete(app->hVal,message);
/* Finish with the capabilities , MSD and RTD procedures */
capEnd(ctrlE);
msdEnd(ctrlE);
rtdEnd(ctrlE);
if (RV_PVT_NODEID_IS_VALID(ctrlE->incomingOLCs[0]))
{
pvtDelete(hVal, ctrlE->incomingOLCs[0]);
ctrlE->incomingOLCs[0] = RV_PVT_INVALID_NODEID;
}
if (RV_PVT_NODEID_IS_VALID(ctrlE->incomingOLCs[1]))
{
pvtDelete(hVal, ctrlE->incomingOLCs[1]);
ctrlE->incomingOLCs[1] = RV_PVT_INVALID_NODEID;
}
/* Make sure we're in the endSession state */
ctrlE->eState=ctrlEndSession;
}
/* report that the control has disconnected */
cmiReportControl(cmiGetByControl((HCONTROL)ctrl),cmControlStateTransportDisconnected,(cmControlStateMode)0);
}
controlState controlGetState(HCONTROL ctrl)
{
H245Control*ctrlE=(H245Control*)ctrl;
return ctrlE->eState;
}
/************************************************************************
* endSessionCommand
* purpose: Handle an incoming endSessionCommand message.
* This should stop the control of the call.
* input : ctrl - Control object
* message - endSessionCommand message received
* output : none
* return : Non-negative value on success
* Negative value on failure
************************************************************************/
int endSessionCommand(IN H245Control* ctrl, IN int message)
{
callElem* call=(callElem*)cmiGetByControl((HCONTROL)ctrl);
RV_UNUSED_ARG(message);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -