www.pudn.com > TsapiCallRouting.rar > Tsapi.cpp


// Tsapi.cpp : interface to TSAPI Tserver. 
// 
// This file handles the hidden TSAPI window 
// 
 
#include "stdafx.h" 
#include "windowsx.h" 
#include "Tsapi.h" 
#include "utilities.h" 
#include "global.h" 
 
#ifdef _DEBUG 
#define new DEBUG_NEW 
#undef THIS_FILE 
static char THIS_FILE[] = __FILE__; 
#endif 
 
// First, there are the CTsapiDevice methods. 
//  
// This class is referenced by the TSAPI window class (CTsapiWnd). 
// It handles: 
//	1. tracking of the window that handles the TSAPI events for each device known 
//		by the CTsapiWnd 
//	3. tracking of the monitor cross reference ID for the current monitoring session 
//		for each device known by the CTsapiWnd 
//	2. tracking of all of the calls and connections for each device known by the 
//		CTsapiWnd 
// 
// Note that this sample only implements 1 device tracking. The CTsapiWnd here can 
//  only track a single device and this memory is hard-coded. 
// Note that this sample hard-codes the number of calls and connections that the 
//  device can support. 
 
CTsapiDevice::CTsapiDevice() 
{ 
	 
	m_MonitorCrossRefID = 0; 
	m_pWnd = 0; 
	for(int i=0; i 0), then post ourselves another 
//  WM_TSAPIMSG.  This is done instead of a while(numEvents >0) loop to allow for 
//  processing of other windows events and to allow for the TSAPI event to process-to- 
//  completion 
LRESULT CTsapiWnd::OnTsapiMsg(WPARAM wParam, LPARAM lParam) 
{ 
 
	static char func[]="CTsapiWnd::OnTsapiMsg"; 
	RetCode_t rc; 
	unsigned short numEvents; 
	//AfxMessageBox("Event received"); 
	// free any previously allocated memory before continuing             
	 
	if(m_EventBufPtr && (m_EventBufPtr != (CSTAEvent_t*)&m_EventBuf)) 
	{  
		GlobalFreePtr(m_EventBufPtr); 
		m_EventBufPtr = (CSTAEvent_t*)&m_EventBuf; 
	} 
	// attempt to retrieve the event from the CSTA DLL	 
	m_EventBufSize = sizeof(m_EventBuf); 
//	rc = acsGetEventPoll(m_AcsHandle, &m_EventBuf, &m_EventBufSize, 0, &numEvents); 
	 
	 
	m_AttPrivateData.length = 0; 
 
	rc = acsGetEventPoll( 
		m_AcsHandle,   // the handle returned by acsOpenStream() 
		m_EventBufPtr,					// a pointer to the event buffer which will be filled by this call 
		&m_EventBufSize,				// a pointer to the size of the above event buffer 
		(PrivateData_t*) &m_AttPrivateData, // a pointer to the private data buffer which will be filled by this call 
		&numEvents						// a pointer to the number of events left in the queue 
		); 
		 
	if(rc != 0) 
	{ 
		// check if rc indicates no messages to get - that is ok 
		if(rc == ACSERR_NOMESSAGE) 
		{ 
			return 0; 
		} 
		else if(rc == ACSERR_UBUFSMALL)	// static buffer too small - allocate larger one 
		{  
			// space required is in the return parameter 
		    m_EventBufPtr = (CSTAEvent_t*)GlobalAllocPtr(GHND, m_EventBufSize); 
			if(!m_EventBufPtr) 
			{ 
				m_TsapiController->PostMessage(WM_TSAPIFAILURE, rc, 0); 
				return (LRESULT)rc; 
			} 
			CString reqStr; 
			reqStr.Format( "acsGetEventPoll(acsHandle=%d eventBufSize=%d) 2", m_AcsHandle, m_EventBufSize ); 
			// try to get the event out of the queue again, into the newly allocated memory                      
			rc = acsGetEventPoll(m_AcsHandle, m_EventBufPtr, &m_EventBufSize, (PrivateData_t*) &m_AttPrivateData, &numEvents); 
			DBG1_OUT( func, "%s rc=%d numEvents=%d eventBufSize=%d", reqStr.GetString(), rc, ( rc == 0 ? numEvents : 0 ), ( rc == ACSERR_UBUFSMALL ? m_EventBufSize : 0 ) ); 
 
			if(rc != 0) 
			{ 
				// not you can do here... 
				// free the allocated memory 
				GlobalFreePtr(m_EventBufPtr); 
				m_EventBufPtr = 0;    
				m_TsapiController->PostMessage(WM_TSAPIFAILURE, rc, 0); 
				return (LRESULT)rc; 
			}                                        
		} 
		else  
		{ 
			// not much you can do here... 
			m_TsapiController->PostMessage(WM_TSAPIFAILURE, rc, 0); 
			return (LRESULT)rc; 
		} 
	} 
	else 
	{ 
		m_EventBufPtr = (CSTAEvent_t*)&m_EventBuf; 
	} 
// at this point acsGetEventPoll() got an event 
	// now lets figure out what to do with the event 
 
	// until we determine otherwise, lets assume that this event does NOT contain private data 
	m_AttEvent.eventType = 0; 
	// handle each class of events slightly differently		 
	switch(m_EventBufPtr->eventHeader.eventClass) 
	{ 
	 case ACSUNSOLICITED: 
	{ 
		// ACS Unsolicited events are all handled by the TSAPI controller - the 
		//  window that wants to be responsible for memory clean-up and stream failure 
		//  handling. Forward all of these events to the controller. 
 
		// this is a sendmessage(), not a postmessage() because the operation has to 
		//  process to completion - or at least until the event buffer is not needed 
		CWnd* pWnd = (CWnd*)m_EventBufPtr->event.acsConfirmation.invokeID; 
		if(::IsWindow(pWnd->m_hWnd)) 
		{ 
			pWnd->SendMessage(WM_TSAPIACSUNSOLICITED, 0, 0); 
		// m_TsapiController->SendMessage(WM_TSAPIACSUNSOLICITED, 0, 0); 
		} 
		break; 
	} 
	 case ACSCONFIRMATION: 
	 { 
		// ACS Confirmation events are all handled by the window that is passed in via 
		//  the invoke ID. Forward all of these events to that window. 
 
		// get CWnd pointer out of invokeID, send message 
		CWnd* pWnd = (CWnd*)m_EventBufPtr->event.acsConfirmation.invokeID; 
		if(::IsWindow(pWnd->m_hWnd)) 
		{ 
			// this is a sendmessage(), not a postmessage() because the operation has to 
			//  process to completion - or at least until the event buffer is not needed 
			pWnd->SendMessage(WM_TSAPIACSCONFIRMATION, 0, 0); 
		} 
		break; 
	 } 
	 case CSTACONFIRMATION: 
	 { 
	    CWnd* pWnd = (CWnd*)m_EventBufPtr->event.acsConfirmation.invokeID; 
		if(::IsWindow(pWnd->m_hWnd)) 
		{ 
			if(m_AttPrivateData.length > 0) 
			{	 
				if (attPrivateData( &m_AttPrivateData, &m_AttEvent ) != ACSPOSITIVE_ACK) { 
					// we are unable to get private data. still send confirmation 
					m_TsapiController->SendMessage(WM_TSAPICSTACONFIRMATION, 0, 0); 
				} else  
					m_TsapiController->SendMessage(WM_TSAPICSTACONFIRMATION, 0, 0); 
			 
			} else 
				m_TsapiController->SendMessage(WM_TSAPICSTACONFIRMATION, 0, 0); 
		} 
		break; 
	 } 
	 case CSTAUNSOLICITED: 
	 { 
		// CSTA Unsolicited events are all handled by the window that is associated with 
		//  the device whose monitor cross reference ID matches the one received in this 
		//  event. Forward all of these events to that window. 
 
		// get CTsapiDevice pointer by looking for a matching monitor cross reference ID 
		//m_EventBufPtr->event.cstaUnsolicited.monitorCrossRefId; 
		// get the CWnd pointer out of CTsapiDevice and make sure the window is still there 
		 CWnd* pWnd = (CWnd*)m_EventBufPtr->event.acsConfirmation.invokeID; 
		 // pWnd->SendMessage(WM_TSAPICSTAUNSOLICITED, 0, 0); 
		 m_TsapiController->SendMessage(WM_TSAPICSTAUNSOLICITED, 0, 0); 
		break; 
	 } 
	 case CSTAREQUEST: 
		if (attPrivateData( &m_AttPrivateData, &m_AttEvent ) != ACSPOSITIVE_ACK) { 
			/* Decoding error */ 
			printf(" Decoding failed\n"); 
		} else { 
			printf("Decoding successful\n"); 
			m_TsapiController->SendMessage(WM_TSAPICSTAREQUEST, 0, 0); 
		} 
 
		 break; 
	 default: 
		break; 
	} 
 
	// If there are additional TSAPI events to process, post ourselves another message. 
	if(numEvents > 0) 
	{ 
		PostMessage(WM_TSAPIMSG, 0, 0); 
	}                               
 
	return 0; 
}