📄 tmclnt.c
字号:
/*
tmclnt.c
960615 TR Created
960617 TR Added all the functions
*/
/*----------------------------------------------------------------------------
SYSTEM INCLUDE FILES
----------------------------------------------------------------------------*/
#define WANTVXDWRAPS
#include <basedef.h>
#include <vmm.h>
#include <vxdwraps.h>
#include <vwin32.h>
/*----------------------------------------------------------------------------
DRIVER SPECIFIC INCLUDE FILES
----------------------------------------------------------------------------*/
#include "vxstd.h"
#include "vxwin.h"
#include "vxdbg.h"
#include "tmwincom.h"
#include "tmshare.h"
#include "tmman32.h"
#include "tmif.h"
#include "tmclnt.h"
#include "cqueue.h"
STATUS clntmCreate ( PVOID *ppvObject, PVOID pContainer )
{
PTMCLNT_MGR_OBJECT this;
DWORD dwIdx;
if ( *((PTMCLNT_MGR_OBJECT *)ppvObject) )
{
this = *((PTMCLNT_MGR_OBJECT *)ppvObject);
}
else
{
if ( ( this = vxdMalloc ( sizeof ( TMCLNT_MGR_OBJECT ) ) ) == NULL )
{
DP(0,"TM:clntmCreate:vxdMalloc:CLNT_MGR_OBJECT:FAIL\n");
return TM_STATUS ( TMCLNT_ERR_OUTOFMEMORY );
}
FlagSet ( this->dwFlags, TMCLNT_MGR_FLAGDYNAMICALLOC );
}
this->dwSize = sizeof ( TMCLNT_MGR_OBJECT );
FlagSet ( this->dwFlags, TMCLNT_MGR_FLAGINITIALIZED );
// initialize all the client objects
for ( dwIdx = 0 ; dwIdx < TMCLNT_CLIENT_COUNT ;dwIdx ++ )
{
this->Client[dwIdx].dwFlags = 0;
this->Client[dwIdx].dwSize = sizeof ( TMCLNT_OBJECT );
FlagSet ( this->Client[dwIdx].dwFlags, TMCLNT_FLAGINITIALIZED );
}
*((PTMCLNT_MGR_OBJECT *)ppvObject) = this;
return TMOK;
}
/*
clntmOpen
This calls crates a new instance of client object. The structure
PTMCLNT_CLIENT is filled up the caller with the attributes about the
client, whcih can be a VxD, 16 bit DLL or 32 bit DLL. Depending upon the
type of client this call allocates data structures and returns the object
and handles in the TMCLNT_CLIENT data structure.
*/
STATUS clntmCreateClnt ( PVOID pvObject, PVOID pvClientInfo, PDWORD pdwHandle )
{
PTMCLNT_MGR_OBJECT this = (PTMCLNT_MGR_OBJECT)pvObject;
PTMCLNT_CLIENT pClientInfo = (PTMCLNT_CLIENT)pvClientInfo;
PTMCLNT_OBJECT pClient;
DWORD dwIdx;
// initialize all the client objects
for ( pClient = NULL, dwIdx = 0 ; dwIdx < TMCLNT_CLIENT_COUNT; dwIdx ++ )
{
if ( ! FlagGet ( this->Client[dwIdx].dwFlags, TMCLNT_FLAGALLOCATED ) )
{
pClient = &this->Client[dwIdx];
break;
}
}
if ( ! pClient )
{
return (TM_STATUS ( TMCLNT_ERR_OUTOFMEMORY ) );
}
FlagSet ( pClient->dwFlags, TMCLNT_FLAGALLOCATED );
// don't use any other field of pClient until we have copied all the
// data there
switch ( pClientInfo->dwType )
{
case TMCLNT_CLIENT_TYPEDLL32 :
if ( ( pClientInfo->Client.DLL32.pvOverlappedObject =
vxdMalloc ( sizeof ( OVERLAPPED ) ) ) == NULL )
{
DP(0,"TM:clntmOpen:vxdMalloc:pvOverlappedObject:FAIL\n");
return TM_STATUS( TMCLNT_ERR_OVERLAPPEDALLCOATIONFAIL );
}
DP(0,"TM:clntmCreateClnt:pClient[%x]:Idx[%x]:pvOverlappedObject[%x]\n",
pClient,
dwIdx,
pClientInfo->Client.DLL32.pvOverlappedObject);
// we want the cqueue object to be allocated dynamically
pClientInfo->Client.DLL32.pvAdvisoryQueue = NULL;
// create the advisory request in Ring 0, this queue can be acccessed
// form ring 0 also.
if ( cqueueCreate ( TMIF_ADVISORY_REQUEST_COUNT,
sizeof ( TMIF_ADVISORY_REQUEST ), NULL,
&pClientInfo->Client.DLL32.pvAdvisoryQueue ) != TRUE )
{
DP(0,"TM:clntmOpen:vxdMalloc:pvAdvisoryQueue:FAIL\n");
return TM_STATUS( TMCLNT_ERR_ADVISORYQCREATEFAIL );
}
break;
case TMCLNT_CLIENT_TYPEDLL16 :
break;
case TMCLNT_CLIENT_TYPEVXD :
break;
}
// copy the client info object into the client object
pClient->Client = *pClientInfo;
pClient->fRing3ThreadActive = FALSE;
pClient->dwReferenceCount = 0;
*pdwHandle = (DWORD)pClient;
return TMOK;
}
STATUS clntDestroy ( DWORD dwHandle )
{
PTMCLNT_OBJECT this = ( PTMCLNT_OBJECT)dwHandle;
DP(13,"TM:clntDestroy:pClient[%x]:VMHandle[%x]:pvOverlappedObject[%x]\n",
this,
this->Client.Client.DLL32.dwVMHandle,
this->Client.Client.DLL32.pvOverlappedObject);
if ( ! FlagGet ( this->dwFlags, TMCLNT_FLAGALLOCATED ) )
{
DP(0,"TM:clntDestroy:pClient[%x]:INVALID\n", this );
return TM_STATUS ( TMCLNT_ERR_INVALIDCLIENT );
}
if ( this->dwReferenceCount-- )
{
DP(0,"TM:clntDestroy:pClient[%x]:CANNOT FREE RESOURCES:ReferenceCount[%x]\n",
this,
this->dwReferenceCount );
return TM_STATUS (TMCLNT_ERR_REFERENCESEXIST );
}
switch ( this->Client.dwType )
{
case TMCLNT_CLIENT_TYPEDLL32 :
vxdFree ( this->Client.Client.DLL32.pvOverlappedObject );
cqueueDestroy ( this->Client.Client.DLL32.pvAdvisoryQueue );
break;
case TMCLNT_CLIENT_TYPEDLL16 :
break;
case TMCLNT_CLIENT_TYPEVXD :
break;
}
FlagClr( this->dwFlags, TMCLNT_FLAGALLOCATED );
return TMOK;
}
STATUS clntIncrementReference ( DWORD dwHandle )
{
PTMCLNT_OBJECT this = ( PTMCLNT_OBJECT)dwHandle;
this->dwReferenceCount++;
return TMOK;
}
STATUS clntDecrementReference ( DWORD dwHandle )
{
PTMCLNT_OBJECT this = ( PTMCLNT_OBJECT)dwHandle;
if ( this->dwReferenceCount ) this->dwReferenceCount--;
return TMOK;
}
STATUS clntAdvise ( DWORD dwHandle , PVOID pvAdvisoryObject )
{
PTMCLNT_OBJECT this = ( PTMCLNT_OBJECT)dwHandle;
PTMIF_ADVISORY_REQUEST pAdvisoryObject =
(PTMIF_ADVISORY_REQUEST)pvAdvisoryObject;
DWORD QueueLength;
switch ( this->Client.dwType )
{
case TMCLNT_CLIENT_TYPEDLL32 :
QueueLength = cqueueLength(this->Client.Client.DLL32.pvAdvisoryQueue);
if ( QueueLength > 10 )
{
DP ( 0,"[UK:%x]", QueueLength );
}
if ( cqueueInsert (
this->Client.Client.DLL32.pvAdvisoryQueue,
pAdvisoryObject ) != TRUE )
{
return TM_STATUS ( TMCLNT_ERR_ADVISORYQFULL );
}
if ( ! this->fRing3ThreadActive )
{
this->fRing3ThreadActive = TRUE;
winVWIN32_DIOCCompletionRoutine (
((OVERLAPPED *)this->Client.Client.DLL32.pvOverlappedObject)->O_Internal );
}
break;
case TMCLNT_CLIENT_TYPEDLL16 :
/*
( this->Client.Client.DLL16.CallbackFunc ) ( pAdvisoryObject,
this->Client.dwContext );
*/
break;
case TMCLNT_CLIENT_TYPEVXD :
((TMMAN_ADVISORY_NOTIFICATION)pAdvisoryObject->dwCallback )(
pAdvisoryObject->dwMessage,
pAdvisoryObject->dwObjHandle,
pAdvisoryObject->pContext,
&pAdvisoryObject->Packet );
break;
}
return TMOK;
}
/*
clntWaitForAdvise
called by TMIF_BLOCKONADVISE.
This devioctl is passed only by 32 bit clients that have a worker thread
processing requests out of the advisory request queue. The client makes
this call when he thinks that there are no more requests in the queue. At
this call the clients thread blocks on the overlapped event. So from this
point onwards it is ready to process more requests. To be on the safe side
this function rechecks the request queue and resignals the event if there
are requests to be processed.
*/
STATUS clntWaitForAdvise ( DWORD dwHandle )
{
PTMCLNT_OBJECT this = ( PTMCLNT_OBJECT)dwHandle;
// verify that client is of the right type
switch ( this->Client.dwType )
{
case TMCLNT_CLIENT_TYPEDLL32 :
this->fRing3ThreadActive = FALSE;
if ( ! cqueueIsEmpty ( this->Client.Client.DLL32.pvAdvisoryQueue ) )
{
this->fRing3ThreadActive = TRUE;
winVWIN32_DIOCCompletionRoutine (
((OVERLAPPED *)this->Client.Client.DLL32.pvOverlappedObject)->O_Internal );
}
break;
default :
return ( TM_STATUS ( TMCLNT_ERR_INVALIDCLIENT ) );
break;
}
}
STATUS clntmDestroy ( PVOID pvObject )
{
PTMCLNT_MGR_OBJECT this = (PTMCLNT_MGR_OBJECT)pvObject;
this->dwSize = 0;
if ( FlagGet ( this->dwFlags, TMCLNT_MGR_FLAGDYNAMICALLOC ) )
{
this->dwFlags = 0;
vxdFree ( this );
}
else
{
this->dwFlags = 0;
}
return TMOK;
}
STATUS clntmVMHandleToClnt ( PVOID pObject, DWORD VMHandle,
PDWORD pClientHandle )
{
PTMCLNT_MGR_OBJECT this = (PTMCLNT_MGR_OBJECT)pObject;
DWORD Idx;
PTMCLNT_OBJECT pClient;
for ( Idx = 0 ; Idx < TMCLNT_CLIENT_COUNT ;Idx ++ )
{
pClient = &this->Client[Idx];
DP(13,"TM:clntmVMHandleToClnt:pClient[%x]:Idx[%x]:VMHandle[%x]\n",
pClient,
Idx,
VMHandle);
if ( ! FlagGet ( pClient->dwFlags, TMCLNT_FLAGALLOCATED ) )
continue;
if ( pClient->Client.dwType != TMCLNT_CLIENT_TYPEDLL32 )
continue;
switch ( pClient->Client.dwType )
{
case TMCLNT_CLIENT_TYPEDLL32 :
if ( pClient->Client.Client.DLL32.dwVMHandle == VMHandle )
{
*pClientHandle = (DWORD)pClient;
return TMOK;
}
break;
case TMCLNT_CLIENT_TYPEDLL16 :
case TMCLNT_CLIENT_TYPEVXD :
return TMCLNT_ERR_CLIENTSYSVM;
break;
}
}
return TMCLNT_ERR_VMNOTREGISTERED;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -