⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 michellecti.cpp

📁 利用AVAYA AES的TASPI开发的一套软电话系统,仅供参考,ACTIVEX形式的.
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// MichelleCTI.cpp : Implementation of CMichelleCTI
#include "stdafx.h"
#include "LucentCti.h"
#include "KVPair.h"
#include "KVList.h"
#include "CTIEvent.h"
#include "MichelleCTI.h"

#include <time.h>
#define szLogPath "c:\\LUCENTLOG" // the log file path
#define EVENT_BUF_LEN 800 // the lucent event bufer default length

///////////////////////////////////////////////////////////////////////////////
//Area for global functions
HINSTANCE CMichelleCTI::m_hInstance=NULL;
HWND CMichelleCTI::m_hSynWnd=NULL;
HANDLE CMichelleCTI::m_hPumpTrd=NULL;
UINT CMichelleCTI::m_dwPumpId=0;

DECLARE_CASTER(CDirectoryNumber, IDirectoryNumber)
DECLARE_CREATOR(CCTIEvent, ICTIEvent)
DECLARE_CREATOR(CDirectoryNumber, IDirectoryNumber)

//write log
void WriteLog(char* pData)
{
#ifdef _WRITELOG
	time_t  now;
	time(&now);
	tm nowTime=*localtime(&now);

	char logfile[1024]={0};
	sprintf(logfile,"%s\\LucentCTILog%02d_%02d_%04d.log",szLogPath,nowTime.tm_mon+1,nowTime.tm_mday,nowTime.tm_year+1900);
	HANDLE hLogFile=CreateFile(logfile,GENERIC_WRITE|GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
	if (hLogFile==INVALID_HANDLE_VALUE)
	{
		if (!CreateDirectory(szLogPath,NULL))
			return;
		else
			hLogFile=CreateFile(logfile,GENERIC_WRITE|GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
	}
	if (hLogFile!=INVALID_HANDLE_VALUE)
	{
		SetFilePointer(hLogFile,NULL,NULL,FILE_END);
		sprintf(logfile,"%2d:%2d:%2d Message:%s\r\n",nowTime.tm_hour,nowTime.tm_min,nowTime.tm_sec,pData);
		DWORD dw;
		WriteFile(hLogFile,logfile,strlen(logfile),&dw,NULL);
		
		CloseHandle(hLogFile);
	}

#endif
}

// the pump thread, all lucent api must post message to me at first, then
//		I'll send this message to the synchronic window
DWORD PumpThread (HWND hSynWnd)
{
	CoInitialize(NULL);
	MSG msg;
	while (GetMessage(&msg,NULL,0,0))
	{
		if (IsWindow(hSynWnd))
		if (!SendMessage(hSynWnd,msg.message,msg.wParam,msg.lParam))
			Sleep(100);
	}
	CoUninitialize();
	return 0;
}

//the registried lucent stream monitor function.Get all message here
//void WINAPI monitorStream(CMichelleCTI* pCti)
void WINAPI monitorStream(unsigned long p)
{ // the stream event process event
	CMichelleCTI* pCti=(CMichelleCTI*)p;
	//PostThreadMessage regulation:
	//msg: um_cti or um_dn_csta or um_dn_att or um_apifailed
	//wParam: cti class or dn class
	//lParam: evnet pointer
	if (pCti)
	{
		byte*  eventBuf=new byte[EVENT_BUF_LEN];
		if (eventBuf==NULL)
			return;
		unsigned short nEventBufLen=EVENT_BUF_LEN;
		ATTPrivateData_t* data=new ATTPrivateData_t; // the private data
		if (data)
		{
			
			data->length=ATT_MAX_PRIVATE_DATA;
			CSTAEvent_t* cstaEvent=NULL; // the csta event
			ATTEvent_t* attEvent=NULL; // the att event
			unsigned short nNumEvent=0; // the event queue 's member account

			RetCode_t ret=acsGetEventPoll(pCti->m_serverHandle,eventBuf,&nEventBufLen,
											(PrivateData_t*)data,&nNumEvent);
			if (ret!=0)
			{
				if (ACSERR_NOMESSAGE==ret)
				{//There is no message,ok
					return;
				}else if (ACSERR_UBUFSMALL==ret)
				{//The buffer is too small
					delete eventBuf;
					eventBuf=new byte[ nEventBufLen];
					if (!eventBuf)
					{
						PostThreadMessage(pCti->m_dwPumpId,UM_APIFAILED,(WPARAM)pCti,0);
						WriteLog("event buffer too small, realloc failed.");
					}
					//try to get the event again
					ret=acsGetEventPoll(pCti->m_serverHandle,eventBuf,&nEventBufLen,
											(PrivateData_t*)data,&nNumEvent);
					if (ret!=0)
					{
						PostThreadMessage(pCti->m_dwPumpId,UM_APIFAILED,(WPARAM)pCti,0);
						WriteLog("get event twince, but all failed.");
					}
				}else
				{
					PostThreadMessage(pCti->m_dwPumpId,UM_APIFAILED,(WPARAM)pCti,0);
					WriteLog("get event failed.");
				}
			}else
			{// ok, we get a csta event
				cstaEvent=(CSTAEvent_t*)eventBuf;
			}

			if (cstaEvent)
			{
				dnevent* pEvent=NULL;
				//now process the csta event
				switch(cstaEvent->eventHeader.eventClass)
				{
				case ACSCONFIRMATION:
					// the acs api confirmation
					switch (cstaEvent->eventHeader.eventType)
					{
					case ACS_OPEN_STREAM_CONF:
					case ACS_CLOSE_STREAM_CONF:
						//acs ok
						PostThreadMessage(pCti->m_dwPumpId,UM_CTI,(WPARAM)pCti,cstaEvent->eventHeader.eventType);
						break;
					case ACS_UNIVERSAL_FAILURE_CONF:
						//failure confirm
						if (pCti->m_iDn)
						{// This message must be post to dn if the dn has been registered
							pEvent=new dnevent(cstaEvent,NULL);
							if (pEvent)
							{
								 PostThreadMessage(pCti->m_dwPumpId,UM_DN,(WPARAM)pCti->m_iDn,(LPARAM)pEvent);
								 eventBuf=NULL;
								 cstaEvent=NULL;
							}
						}else
						{
							pCti->m_lErrCode=cstaEvent->event.cstaConfirmation.u.universalFailure.error;
							pCti->m_errType=ET_LUCENT_CONF;
							PostThreadMessage(pCti->m_dwPumpId,UM_CTI,(WPARAM)pCti,UM_APIFAILED);
							char pTemp[100]={0};
							wsprintf(pTemp,"ACS_UNIVERSAL_FAILURE_CONF error code:%d(cti)",pCti->m_lErrCode);
							WriteLog(pTemp);
						}
						break;
					default:
						//PostThreadMessage(pCti->m_dwPumpId,UM_CTI,(WPARAM)pCti,UM_APIFAILED);
						WriteLog("Get an unknown ascconfirmation event.");
						break;
					}
					break;
				case ACSUNSOLICITED:
					if (pCti->m_iDn)
					{// This message must be post to dn if the dn has been registered
						pEvent=new dnevent(cstaEvent,NULL);
						if (pEvent)
						{
							 PostThreadMessage(pCti->m_dwPumpId,UM_DN,(WPARAM)pCti->m_iDn,(LPARAM)pEvent);
							 eventBuf=NULL;
							 cstaEvent=NULL;
						}
					}else 
					{//send to cti object
						pCti->m_lErrCode=cstaEvent->event.acsUnsolicited.u.failureEvent.error;
						pCti->m_errType=ET_LUCENT_CONF;
						pCti->m_ErrMsg="Get an acsunsolicited event.";
						PostThreadMessage(pCti->m_dwPumpId,UM_CTI,(WPARAM)pCti,UM_APIFAILED);
						char pTemp[100]={0};
						wsprintf(pTemp,"ACSUNSOLICITED error code:%d(cti)",pCti->m_lErrCode);
						WriteLog(pTemp);
					}
					break;
				case CSTACONFIRMATION:
					//the csta api confirmation
					pEvent=new dnevent(cstaEvent,NULL);
					if (pEvent)
					{
						 PostThreadMessage(pCti->m_dwPumpId,UM_DN,(WPARAM)pCti->m_iDn,(LPARAM)pEvent);
						 eventBuf=NULL;
						 cstaEvent=NULL;
					}
					break;
				case CSTAUNSOLICITED:
					//post the csta message
					switch (cstaEvent->eventHeader.eventType)
					{
					case CSTA_DELIVERED:
						//post the att event
						if (data->length>0)
						{//contains private data,send ATTEvent
							attEvent=new ATTEvent_t;
							//this buffer will be processed and deleted in future
							if (attEvent)
							{
								ret=attPrivateData(data,attEvent);
								if (ret!=0)
								{
									delete attEvent;
									attEvent=NULL;
								}
							}
						}
						break;
					default:
						break;
					}
					pEvent=new dnevent(cstaEvent,attEvent);
					if (pEvent)
					{
						PostThreadMessage(pCti->m_dwPumpId,UM_DN,(WPARAM)pCti->m_iDn,(LPARAM)pEvent);
						eventBuf=NULL;
						cstaEvent=NULL;
					}else
					{
						delete attEvent;
						attEvent=NULL;
					}
					eventBuf=NULL;
					cstaEvent=NULL;
					break;
				}//switch(cstaEvent->eventHeader.eventClass)
			}
			// before exit, clear buffer
			if (eventBuf)
			{
				delete eventBuf;
				eventBuf=NULL;
				cstaEvent=NULL;
			}
			//call fun again to process event
			if (nNumEvent>1)
				monitorStream((unsigned long)pCti);
		}
	}
	return;
}

// the synchronic window message process function. All message will be processed here
LRESULT CALLBACK SynchronicWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{// the synchronic window message dispatcher
	CCTIEvent *pCEvent;
	ICTIEvent *pIEvent;
	CMichelleCTI* pCti=NULL;
	CDirectoryNumber* pDn=NULL;

	CSTAEvent_t* cstaEvent=NULL;
	dnevent* pEvent=NULL;

	switch(msg)
	{
	case UM_APIFAILED:
		if (wParam!=0)
		{
			pCti=(CMichelleCTI*)wParam;
			if(SUCCEEDED(CreateClass(&pCEvent, &pIEvent))) 
			{
				pCEvent->m_GenesysEvent=EVT_Error;
				pCti->Fire_Event(pIEvent);
				pIEvent->Release();
			} else 
			{
				pCti->Fire_Event(NULL);
			}
		}
		break;
	case UM_CTI:
		if (wParam!=0)
		{
			pCti=(CMichelleCTI*)wParam;
			if (!pCti->DefaultHandler(lParam))//event name
			{
				if(SUCCEEDED(CreateClass(&pCEvent, &pIEvent))) 
				{
					switch(lParam)
					{
					case UM_APIFAILED:
						pCEvent->m_GenesysEvent=EVT_Error;
						break;
					case ACS_OPEN_STREAM_CONF:
						pCEvent->m_GenesysEvent=EVT_LinkConnected;
						break;
/////////////MARK by rick --begin
//					case ACS_CLOSE_STREAM_CONF:
//						pCEvent->m_GenesysEvent=EVT_LinkDisconnected;
//						break;

/////////////MARK --end
					}
					pCti->Fire_Event(pIEvent);
					pIEvent->Release();
				} else 
				{
					pCti->Fire_Event(NULL);
				}
			}
		}
		break;
	case UM_DN:
		if (wParam!=0)
		{
			pDn = I2C((IDirectoryNumber*)wParam);
			pEvent=(dnevent*) lParam;
			if (!pDn->DefaultHandler(pEvent))
			{
				if(SUCCEEDED(CreateClass(&pCEvent, &pIEvent))) 
				{
						pCEvent->SetEvent(pEvent);
						pDn->Fire_Event(pIEvent);
						pIEvent->Release();
				} else 
				{
					pCti->Fire_Event(NULL);
				}
				delete pEvent;
			}
			lParam=0; // the dnevent has been deleted
		}
		if (wParam==0 && lParam!=0) 
			delete ((dnevent*) lParam);
		break;

	default:
		return(DefWindowProc(hwnd, msg, wParam, lParam));
	}
	return (0l);
}

BOOL GlobalStartup(HINSTANCE hInstance)
{
	BOOL ret=FALSE;
	if (hInstance)
	{
		CMichelleCTI::m_hInstance=hInstance;
		//Create the message synchronic window
			WNDCLASS wc;
		wc.style = 0;
		wc.lpfnWndProc = SynchronicWndProc;
		wc.cbClsExtra = wc.cbWndExtra = 0;
		wc.hInstance = hInstance;
		wc.hIcon = NULL;
		wc.hCursor = NULL;
		wc.hbrBackground = NULL;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -