Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

634 lines
14 KiB

  1. /*==========================================================================
  2. *
  3. * Copyright (C) 2000 Microsoft Corporation. All Rights Reserved.
  4. *
  5. * File: AsyncOp.h
  6. * Content: Async Operation Object Header File
  7. *@@BEGIN_MSINTERNAL
  8. * History:
  9. * Date By Reason
  10. * ==== == ======
  11. * 04/08/00 mjn Created
  12. * 04/11/00 mjn Added DIRECTNETOBJECT bilink for CAsyncOps
  13. * 04/16/00 mjn Added ASYNC_OP_SEND and ASYNC_OP_USER_HANDLE
  14. * mjn Added SetStartTime() and GetStartTime()
  15. * 04/20/00 mjn Added ASYNC_OP_RECEIVE_BUFFER
  16. * 04/22/00 mjn Added ASYNC_OP_REQUEST
  17. * 05/02/00 mjn Added m_pConnection to track Connection over life of AsyncOp
  18. * 07/08/00 mjn Added m_bilinkParent
  19. * 07/17/00 mjn Added signature to CAsyncOp
  20. * 07/27/00 mjn Added m_dwReserved and changed locking for parent/child bilinks
  21. * 08/05/00 mjn Added ASYNC_OP_COMPLETE,ASYNC_OP_CANCELLED,ASYNC_OP_INTERNAL flags
  22. * mjn Added m_bilinkActiveList
  23. * 01/09/01 mjn Added ASYNC_OP_CANNOT_CANCEL,SetCannotCancel(),IsCannotCancel()
  24. * 02/08/01 mjn Added m_pCancelEvent,m_dwCancelThreadID
  25. * 05/23/01 mjn Added ClearCannotCancel()
  26. *@@END_MSINTERNAL
  27. *
  28. ***************************************************************************/
  29. #ifndef __ASYNC_OP_H__
  30. #define __ASYNC_OP_H__
  31. #undef DPF_SUBCOMP
  32. #define DPF_SUBCOMP DN_SUBCOMP_CORE
  33. //**********************************************************************
  34. // Constant definitions
  35. //**********************************************************************
  36. #define ASYNC_OP_CHILD 0x0001
  37. #define ASYNC_OP_PARENT 0x0002
  38. #define ASYNC_OP_USE_PARENT_OP_DATA 0x0004
  39. #define ASYNC_OP_CANNOT_CANCEL 0x0010
  40. #define ASYNC_OP_COMPLETE 0x0100
  41. #define ASYNC_OP_CANCELLED 0x0200
  42. #define ASYNC_OP_INTERNAL 0x8000
  43. //**********************************************************************
  44. // Macro definitions
  45. //**********************************************************************
  46. //**********************************************************************
  47. // Structure definitions
  48. //**********************************************************************
  49. typedef enum
  50. {
  51. ASYNC_OP_CONNECT,
  52. ASYNC_OP_DISCONNECT,
  53. ASYNC_OP_ENUM_QUERY,
  54. ASYNC_OP_ENUM_RESPONSE,
  55. ASYNC_OP_LISTEN,
  56. ASYNC_OP_SEND,
  57. ASYNC_OP_RECEIVE_BUFFER,
  58. ASYNC_OP_REQUEST,
  59. ASYNC_OP_UNKNOWN,
  60. ASYNC_OP_USER_HANDLE,
  61. #ifndef DPNBUILD_NOMULTICAST
  62. ASYNC_OP_LISTEN_MULTICAST,
  63. ASYNC_OP_CONNECT_MULTICAST_SEND,
  64. ASYNC_OP_CONNECT_MULTICAST_RECEIVE,
  65. #endif // ! DPNBUILD_NOMULTICAST
  66. } ASYNC_OP_TYPE;
  67. class CAsyncOp;
  68. class CConnection;
  69. class CRefCountBuffer;
  70. class CServiceProvider;
  71. class CSyncEvent;
  72. typedef struct _DIRECTNETOBJECT DIRECTNETOBJECT;
  73. typedef void (*PFNASYNCOP_COMPLETE)(DIRECTNETOBJECT *const,CAsyncOp *const);
  74. typedef union
  75. {
  76. DN_SEND_OP_DATA SendOpData;
  77. #ifndef DPNBUILD_ONLYONEADAPTER
  78. DN_LISTEN_OP_DATA ListenOpData;
  79. DN_CONNECT_OP_DATA ConnectOpData;
  80. #endif // ! DPNBUILD_ONLYONEADAPTER
  81. DN_ENUM_QUERY_OP_DATA EnumQueryOpData;
  82. DN_ENUM_RESPONSE_OP_DATA EnumResponseOpData;
  83. } DN_OP_DATA;
  84. //**********************************************************************
  85. // Variable definitions
  86. //**********************************************************************
  87. //**********************************************************************
  88. // Function prototypes
  89. //**********************************************************************
  90. //**********************************************************************
  91. // Class prototypes
  92. //**********************************************************************
  93. // class for Async Operations
  94. class CAsyncOp
  95. {
  96. public:
  97. #undef DPF_MODNAME
  98. #define DPF_MODNAME "CAsyncOp::FPMAlloc"
  99. static BOOL FPMAlloc( void* pvItem, void* pvContext )
  100. {
  101. CAsyncOp* pAsyncOp = (CAsyncOp*)pvItem;
  102. pAsyncOp->m_Sig[0] = 'A';
  103. pAsyncOp->m_Sig[1] = 'S';
  104. pAsyncOp->m_Sig[2] = 'Y';
  105. pAsyncOp->m_Sig[3] = 'N';
  106. pAsyncOp->m_dwReserved = 0;
  107. if (!DNInitializeCriticalSection(&pAsyncOp->m_cs))
  108. {
  109. return(FALSE);
  110. }
  111. #ifdef DBG
  112. pAsyncOp->m_bilinkAsyncOps.Initialize();
  113. #endif // DBG
  114. pAsyncOp->m_bilinkActiveList.Initialize();
  115. pAsyncOp->m_bilinkParent.Initialize();
  116. pAsyncOp->m_bilinkChildren.Initialize();
  117. memset( &pAsyncOp->m_OpData,0x00,sizeof(DN_OP_DATA) );
  118. return(TRUE);
  119. };
  120. #undef DPF_MODNAME
  121. #define DPF_MODNAME "CAsyncOp::FPMInitialize"
  122. static void FPMInitialize( void* pvItem, void* pvContext )
  123. {
  124. CAsyncOp* pAsyncOp = (CAsyncOp*)pvItem;
  125. pAsyncOp->m_pdnObject = static_cast<DIRECTNETOBJECT*>(pvContext);
  126. pAsyncOp->m_dwFlags = 0;
  127. pAsyncOp->m_lRefCount = 1;
  128. pAsyncOp->m_OpType = ASYNC_OP_UNKNOWN;
  129. pAsyncOp->m_pParent = NULL;
  130. pAsyncOp->m_handle = 0;
  131. pAsyncOp->m_dwOpFlags = 0;
  132. pAsyncOp->m_pvContext = NULL;
  133. pAsyncOp->m_hProtocol = NULL;
  134. pAsyncOp->m_pvOpData = NULL;
  135. pAsyncOp->m_dwStartTime = 0;
  136. pAsyncOp->m_dpnid = 0;
  137. pAsyncOp->m_hr = DPNERR_GENERIC;
  138. pAsyncOp->m_phr = NULL;
  139. pAsyncOp->m_pConnection = NULL;
  140. pAsyncOp->m_pSP = NULL;
  141. pAsyncOp->m_pRefCountBuffer = NULL;
  142. pAsyncOp->m_pSyncEvent = NULL;
  143. pAsyncOp->m_pCancelEvent = NULL;
  144. pAsyncOp->m_dwCancelThreadID = 0;
  145. pAsyncOp->m_pfnCompletion = NULL;
  146. pAsyncOp->m_dwFirstFrameRTT = -1;
  147. pAsyncOp->m_dwFirstFrameRetryCount = -1;
  148. // pAsyncOp->m_dwReserved = 0;
  149. #ifdef DBG
  150. DNASSERT(pAsyncOp->m_bilinkAsyncOps.IsEmpty());
  151. #endif // DBG
  152. DNASSERT(pAsyncOp->m_bilinkActiveList.IsEmpty());
  153. DNASSERT(pAsyncOp->m_bilinkParent.IsEmpty());
  154. DNASSERT(pAsyncOp->m_bilinkChildren.IsEmpty());
  155. };
  156. #undef DPF_MODNAME
  157. #define DPF_MODNAME "CAsyncOp::FPMRelease"
  158. static void FPMRelease( void* pvItem )
  159. {
  160. CAsyncOp* pAsyncOp = (CAsyncOp*)pvItem;
  161. pAsyncOp->m_dwFlags |= 0xffff0000;
  162. #ifdef DBG
  163. DNASSERT(pAsyncOp->m_bilinkAsyncOps.IsEmpty());
  164. #endif // DBG
  165. DNASSERT(pAsyncOp->m_bilinkActiveList.IsEmpty());
  166. DNASSERT(pAsyncOp->m_bilinkParent.IsEmpty());
  167. DNASSERT(pAsyncOp->m_bilinkChildren.IsEmpty());
  168. DNASSERT(pAsyncOp->m_pvOpData == NULL);
  169. };
  170. #undef DPF_MODNAME
  171. #define DPF_MODNAME "CAsyncOp::FPMDealloc"
  172. static void FPMDealloc( void* pvItem )
  173. {
  174. CAsyncOp* pAsyncOp = (CAsyncOp*)pvItem;
  175. DNDeleteCriticalSection(&pAsyncOp->m_cs);
  176. };
  177. void ReturnSelfToPool( void );
  178. #undef DPF_MODNAME
  179. #define DPF_MODNAME "CAsyncOp::AddRef"
  180. void AddRef(void)
  181. {
  182. LONG lRefCount;
  183. DNASSERT(m_lRefCount > 0);
  184. lRefCount = DNInterlockedIncrement(const_cast<LONG*>(&m_lRefCount));
  185. DPFX(DPFPREP, 3,"CAsyncOp::AddRef [0x%lx] RefCount [0x%lx]",this,lRefCount);
  186. };
  187. void CAsyncOp::Release( void );
  188. void Lock( void )
  189. {
  190. DNEnterCriticalSection( &m_cs );
  191. };
  192. void Unlock( void )
  193. {
  194. DNLeaveCriticalSection( &m_cs );
  195. };
  196. void SetOpType( const ASYNC_OP_TYPE OpType )
  197. {
  198. m_OpType = OpType;
  199. };
  200. ASYNC_OP_TYPE GetOpType( void ) const
  201. {
  202. return( m_OpType );
  203. };
  204. void MakeParent( void )
  205. {
  206. m_dwFlags |= ASYNC_OP_PARENT;
  207. };
  208. BOOL IsParent( void ) const
  209. {
  210. if (m_dwFlags & ASYNC_OP_PARENT)
  211. return(TRUE);
  212. return(FALSE);
  213. };
  214. #undef DPF_MODNAME
  215. #define DPF_MODNAME "CAsyncOp::MakeChild"
  216. void MakeChild( CAsyncOp *const pParent )
  217. {
  218. DNASSERT(pParent != NULL);
  219. pParent->AddRef();
  220. m_pParent = pParent;
  221. m_bilinkChildren.InsertBefore(&m_pParent->m_bilinkParent);
  222. m_dwFlags |= ASYNC_OP_CHILD;
  223. };
  224. BOOL IsChild( void ) const
  225. {
  226. if (m_dwFlags & ASYNC_OP_CHILD)
  227. return(TRUE);
  228. return(FALSE);
  229. };
  230. CAsyncOp *GetParent( void ) const
  231. {
  232. return( m_pParent );
  233. };
  234. void CAsyncOp::Orphan( void );
  235. void SetHandle( const DPNHANDLE handle )
  236. {
  237. m_handle = handle;
  238. };
  239. DPNHANDLE GetHandle( void ) const
  240. {
  241. return( m_handle );
  242. };
  243. void SetOpFlags( const DWORD dwOpFlags )
  244. {
  245. m_dwOpFlags = dwOpFlags;
  246. };
  247. DWORD GetOpFlags( void ) const
  248. {
  249. return( m_dwOpFlags );
  250. };
  251. void SetContext( void *const pvContext )
  252. {
  253. m_pvContext = pvContext;
  254. };
  255. void *GetContext( void ) const
  256. {
  257. return( m_pvContext );
  258. };
  259. void SetProtocolHandle( const HANDLE hProtocol )
  260. {
  261. m_hProtocol = hProtocol;
  262. };
  263. HANDLE GetProtocolHandle( void ) const
  264. {
  265. return( m_hProtocol );
  266. };
  267. void SetOpData( void *const pvOpData )
  268. {
  269. m_pvOpData = pvOpData;
  270. };
  271. void *GetOpData( void ) const
  272. {
  273. return( m_pvOpData );
  274. };
  275. void SetStartTime( const DWORD dwStartTime )
  276. {
  277. m_dwStartTime = dwStartTime;
  278. };
  279. DWORD GetStartTime( void ) const
  280. {
  281. return( m_dwStartTime );
  282. };
  283. void SetDPNID( const DPNID dpnid )
  284. {
  285. m_dpnid = dpnid;
  286. };
  287. DPNID GetDPNID( void ) const
  288. {
  289. return( m_dpnid );
  290. };
  291. void SetResult( const HRESULT hr )
  292. {
  293. m_hr = hr;
  294. };
  295. HRESULT GetResult( void ) const
  296. {
  297. return( m_hr );
  298. };
  299. void SetFirstFrameRTT( const DWORD dwFirstFrameRTT )
  300. {
  301. m_dwFirstFrameRTT = dwFirstFrameRTT;
  302. };
  303. DWORD GetFirstFrameRTT( void ) const
  304. {
  305. return ( m_dwFirstFrameRTT );
  306. };
  307. void SetFirstFrameRetryCount( const DWORD dwFirstFrameRetryCount )
  308. {
  309. m_dwFirstFrameRetryCount = dwFirstFrameRetryCount;
  310. };
  311. DWORD GetFirstFrameRetryCount( void ) const
  312. {
  313. return ( m_dwFirstFrameRetryCount );
  314. };
  315. void SetResultPointer( volatile HRESULT *const phr )
  316. {
  317. m_phr = phr;
  318. };
  319. volatile HRESULT *GetResultPointer( void ) const
  320. {
  321. return( m_phr );
  322. };
  323. void CAsyncOp::SetConnection( CConnection *const pConnection );
  324. CConnection *GetConnection (void ) const
  325. {
  326. return( m_pConnection );
  327. };
  328. void CAsyncOp::SetSP( CServiceProvider *const pSP );
  329. CServiceProvider *GetSP( void ) const
  330. {
  331. return( m_pSP );
  332. };
  333. void CAsyncOp::SetRefCountBuffer( CRefCountBuffer *const pRefCountBuffer );
  334. CRefCountBuffer *GetRefCountBuffer( void ) const
  335. {
  336. return( m_pRefCountBuffer );
  337. };
  338. void SetSyncEvent( CSyncEvent *const pSyncEvent )
  339. {
  340. m_pSyncEvent = pSyncEvent;
  341. };
  342. CSyncEvent *GetSyncEvent( void ) const
  343. {
  344. return( m_pSyncEvent );
  345. };
  346. void SetCancelEvent( CSyncEvent *const pSyncEvent )
  347. {
  348. m_pCancelEvent = pSyncEvent;
  349. };
  350. CSyncEvent *GetCancelEvent( void ) const
  351. {
  352. return( m_pCancelEvent );
  353. };
  354. void SetCancelThreadID( const DWORD dwCancelThreadID )
  355. {
  356. m_dwCancelThreadID = dwCancelThreadID;
  357. };
  358. DWORD GetCancelThreadID( void ) const
  359. {
  360. return( m_dwCancelThreadID );
  361. };
  362. void SetCompletion( PFNASYNCOP_COMPLETE pfn )
  363. {
  364. m_pfnCompletion = pfn;
  365. };
  366. void SetReserved( const DWORD dw )
  367. {
  368. m_dwReserved = dw;
  369. };
  370. void SetComplete( void )
  371. {
  372. m_dwFlags |= ASYNC_OP_COMPLETE;
  373. };
  374. BOOL IsComplete( void ) const
  375. {
  376. if (m_dwFlags & ASYNC_OP_COMPLETE)
  377. {
  378. return( TRUE );
  379. }
  380. return( FALSE );
  381. };
  382. void SetCancelled( void )
  383. {
  384. m_dwFlags |= ASYNC_OP_CANCELLED;
  385. };
  386. BOOL IsCancelled( void ) const
  387. {
  388. if (m_dwFlags & ASYNC_OP_CANCELLED)
  389. {
  390. return( TRUE );
  391. }
  392. return( FALSE );
  393. };
  394. void SetInternal( void )
  395. {
  396. m_dwFlags |= ASYNC_OP_INTERNAL;
  397. };
  398. BOOL IsInternal( void ) const
  399. {
  400. if (m_dwFlags & ASYNC_OP_INTERNAL)
  401. {
  402. return( TRUE );
  403. }
  404. return( FALSE );
  405. };
  406. void ClearCannotCancel( void )
  407. {
  408. m_dwFlags &= (~ASYNC_OP_CANNOT_CANCEL);
  409. };
  410. void SetCannotCancel( void )
  411. {
  412. m_dwFlags |= ASYNC_OP_CANNOT_CANCEL;
  413. };
  414. BOOL IsCannotCancel( void ) const
  415. {
  416. if (m_dwFlags & ASYNC_OP_CANNOT_CANCEL)
  417. {
  418. return( TRUE );
  419. }
  420. return( FALSE );
  421. };
  422. void ClearUseParentOpData( void )
  423. {
  424. m_dwFlags &= (~ASYNC_OP_USE_PARENT_OP_DATA);
  425. };
  426. void SetUseParentOpData( void )
  427. {
  428. m_dwFlags |= ASYNC_OP_USE_PARENT_OP_DATA;
  429. };
  430. BOOL IsUseParentOpData( void ) const
  431. {
  432. if (m_dwFlags & ASYNC_OP_USE_PARENT_OP_DATA)
  433. {
  434. return( TRUE );
  435. }
  436. return( FALSE );
  437. };
  438. DN_SEND_OP_DATA *GetLocalSendOpData( void )
  439. {
  440. return( &m_OpData.SendOpData );
  441. };
  442. #ifndef DPNBUILD_ONLYONEADAPTER
  443. DN_CONNECT_OP_DATA *GetLocalConnectOpData( void )
  444. {
  445. return( &m_OpData.ConnectOpData );
  446. };
  447. DN_LISTEN_OP_DATA *GetLocalListenOpData( void )
  448. {
  449. return( &m_OpData.ListenOpData );
  450. };
  451. #endif // ! DPNBUILD_ONLYONEADAPTER
  452. DN_ENUM_QUERY_OP_DATA *GetLocalEnumQueryOpData( void )
  453. {
  454. return( &m_OpData.EnumQueryOpData );
  455. };
  456. DN_ENUM_RESPONSE_OP_DATA *GetLocalEnumResponseOpData( void )
  457. {
  458. return( &m_OpData.EnumResponseOpData );
  459. };
  460. #ifdef DBG
  461. CBilink m_bilinkAsyncOps;
  462. #endif // DBG
  463. CBilink m_bilinkActiveList; // Active AsyncOps
  464. CBilink m_bilinkParent; // Starting point for children
  465. CBilink m_bilinkChildren; // Other children sharing this parent
  466. private:
  467. BYTE m_Sig[4]; // Signature
  468. DWORD volatile m_dwFlags;
  469. LONG volatile m_lRefCount;
  470. ASYNC_OP_TYPE m_OpType; // Operation Type
  471. CAsyncOp *m_pParent; // Parent Async Operation
  472. DPNHANDLE m_handle; // Async Operation Handle
  473. DWORD m_dwOpFlags;
  474. void *m_pvContext;
  475. HANDLE m_hProtocol; // Protocol Operation Handle
  476. void *m_pvOpData; // Operation specific data
  477. DWORD m_dwStartTime;
  478. DPNID m_dpnid;
  479. HRESULT volatile m_hr;
  480. volatile HRESULT *m_phr;
  481. CConnection *m_pConnection; // Send Target connection - released
  482. CServiceProvider *m_pSP; // Service Provider - released
  483. CRefCountBuffer *m_pRefCountBuffer; // Refernce Count Buffer - released
  484. CSyncEvent *m_pSyncEvent; // Sync Event - set at release
  485. CSyncEvent *m_pCancelEvent; // Cancel event - prevent completion from returning
  486. DWORD m_dwCancelThreadID; // Cancelling thread's ID (prevent deadlocking)
  487. PFNASYNCOP_COMPLETE m_pfnCompletion; // Completion function - called
  488. #ifndef DPNBUILD_ONLYONETHREAD
  489. DNCRITICAL_SECTION m_cs;
  490. #endif // !DPNBUILD_ONLYONETHREAD
  491. DIRECTNETOBJECT *m_pdnObject;
  492. DWORD m_dwFirstFrameRTT;
  493. DWORD m_dwFirstFrameRetryCount;
  494. DN_OP_DATA m_OpData;
  495. DWORD m_dwReserved; // INTERNAL - RESERVED FOR DEBUG !
  496. };
  497. #undef DPF_MODNAME
  498. #endif // __ASYNC_OP_H__