📄 scoverio.hxx
字号:
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
//
// Use of this source code is subject to the terms of the Microsoft shared
// source or premium shared source license agreement under which you licensed
// this source code. If you did not accept the terms of the license agreement,
// you are not authorized to use this source code. For the terms of the license,
// please see the license agreement between you and Microsoft or, if applicable,
// see the SOURCE.RTF on your install media or the root of your tools installation.
// THE SOURCE CODE IS PROVIDED "AS IS", WITH NO WARRANTIES.
//
/*++
Module Name:
scoverio.hxx
Abstract:
Small client overlapped I/O support
--*/
#if ! defined (__scoverio_HXX__)
#define __scoverio_HXX__ 1
#include <svsutil.hxx>
#include <mq.h>
#define SC_OVER_THREAD_TIMEOUT 5000
class ScIoRequest : public SVSAllocClass {
private:
HANDLE hEvent;
HANDLE hCallerProc;
CMarshalOverlapped *pOverlapped;
DWORD *pdwStatus;
SCHANDLE hQueue;
SCHANDLE hCursor;
DWORD tExpirationTicks;
unsigned int tExpirationS;
unsigned int tExpirationMS;
DWORD dwTimeout;
DWORD dwAction;
ce::copy_in<SCPROPVAR*> *pMsgProps;
SVSTNode *pNode;
ScIoRequest *pNext;
int iNdx;
ScIoRequest (HANDLE a_hWaitEvent,
HANDLE a_hCallerProc,
DWORD *a_pdwStatus,
CMarshalOverlapped *a_pOverlapped,
SCHANDLE a_hQueue,
SCHANDLE a_hCursor,
DWORD a_dwTimeout,
DWORD a_dwAction,
ce::copy_in<SCPROPVAR*> *a_pMsgProps) {
hEvent = a_hWaitEvent;
hCallerProc = a_hCallerProc;
pdwStatus = a_pdwStatus;
pOverlapped = a_pOverlapped;
hQueue = a_hQueue;
hCursor = a_hCursor;
dwTimeout = a_dwTimeout;
if (dwTimeout == INFINITE) {
tExpirationTicks = tExpirationS = 0xffffffff;
tExpirationMS = 999;
} else {
svsutil_GetAbsTime (&tExpirationS, &tExpirationMS);
tExpirationMS += dwTimeout;
tExpirationS += tExpirationMS / 1000;
tExpirationMS %= 1000;
tExpirationTicks = GetTickCount () + a_dwTimeout;
}
dwAction = a_dwAction;
pMsgProps = a_pMsgProps;
pNode = NULL;
pNext = NULL;
iNdx = -1;
}
// Set status code and event to alert application that request is over.
void SetStatusAndEvent(HRESULT hr) {
// Either we should be using overlapped structure from app OR params
// specified by MSMQ PSL thread itself (exclusive OR)
SVSUTIL_ASSERT((pOverlapped && (NULL==pdwStatus) && (NULL==hEvent)) ||
(!pOverlapped && pdwStatus && hEvent));
if (pdwStatus)
*pdwStatus = hr;
if (hEvent)
SetEvent(hEvent);
if (pOverlapped) {
pOverlapped->SetOverlappedEvent();
pOverlapped->SetStatus(hr);
delete pOverlapped;
pOverlapped = NULL;
// We delete pMsgProps only if pOverlapped was set, because
// this indicates that scapi_MQReceiveMessage has returned and
// is relying on the worker thread here to take care of deallocation.
delete pMsgProps;
pMsgProps = NULL;
}
}
friend class ScOverlappedSupport;
friend static HRESULT scapi_MQReceiveMessageI (ScIoRequest *pReq);
friend static ScIoRequest *scapi_ReverseReqList (ScIoRequest *pReqList);
friend DWORD WINAPI scapi_UserControlThread (LPVOID lpParameter);
};
class ScOverlappedSupport : public SVSAllocClass {
private:
HANDLE hThread;
SVSTree *pTimeTree;
int fInitialized;
int iNumPendingRequests;
HANDLE ahQueueEvents[MAXIMUM_WAIT_OBJECTS];
HANDLE *pahQueueEvents;
ScIoRequest *apPendingRequests[MAXIMUM_WAIT_OBJECTS - 1];
void SpinThread (void) {
SVSUTIL_ASSERT (iNumPendingRequests > 0);
if (! hThread) {
DWORD dwTID;
hThread = CreateThread (NULL, 0, OverlappedSupportThread_s, this, 0, &dwTID);
}
if (hThread)
SetEvent (ahQueueEvents[0]);
}
void CompressIndex (int iNdx);
void Deregister (ScIoRequest *pRequest, HRESULT hr);
void OverlappedSupportThread (void);
void SelfDestruct (void);
static DWORD WINAPI OverlappedSupportThread_s (void *pvParam);
public:
int fBusy;
ScOverlappedSupport (void) {
iNumPendingRequests = 0;
pahQueueEvents = &ahQueueEvents[1];
hThread = NULL;
ahQueueEvents[0] = CreateEvent (NULL, FALSE, FALSE, NULL);
pTimeTree = SVSNewTree(gMem->pTreeNodeMem);
fInitialized = pTimeTree && ahQueueEvents[0];
fBusy = 0;
}
~ScOverlappedSupport (void) {
SelfDestruct ();
}
HRESULT EnterOverlappedReceive(
HANDLE hQueueEvent,
HANDLE hWaitEvent,
HANDLE hCallerProc,
DWORD *pdwStatus,
CMarshalOverlapped *pOverlapped,
SCHANDLE hQueue,
SCHANDLE hCursor,
DWORD dwTimeout,
DWORD dwAction,
ce::copy_in<SCPROPVAR*> *pMsgProps);
HRESULT EnterOverlappedReceive(
HANDLE hQueueEvent,
ScIoRequest *pIO);
void CloseHandle (SCHANDLE h);
friend DWORD WINAPI scapi_UserControlThread (LPVOID lpParameter);
};
#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -