Source code of Windows XP (NT5)
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.

366 lines
10 KiB

  1. /*+r
  2. Copyright (c) 1989 Microsoft Corporation
  3. Module Name:
  4. afd.h
  5. Abstract:
  6. This is the local header file for AFD. It includes all other
  7. necessary header files for AFD.
  8. Author:
  9. David Treadwell (davidtr) 21-Feb-1992
  10. Revision History:
  11. --*/
  12. #ifndef _AFDP_
  13. #define _AFDP_
  14. #include <ntosp.h>
  15. #include <zwapi.h>
  16. #include <tdikrnl.h>
  17. #ifndef _AFDKDP_H_
  18. extern POBJECT_TYPE *ExEventObjectType;
  19. #endif // _AFDKDP_H_
  20. #if DBG
  21. #ifndef AFD_PERF_DBG
  22. #define AFD_PERF_DBG 1
  23. #endif
  24. #ifndef AFD_KEEP_STATS
  25. #define AFD_KEEP_STATS 1
  26. #endif
  27. #else
  28. #ifndef AFD_PERF_DBG
  29. #define AFD_PERF_DBG 0
  30. #endif
  31. #ifndef AFD_KEEP_STATS
  32. #define AFD_KEEP_STATS 0
  33. #endif
  34. #endif // DBG
  35. //
  36. // Hack-O-Rama. TDI has a fundamental flaw in that it is often impossible
  37. // to determine exactly when a TDI protocol is "done" with a connection
  38. // object. The biggest problem here is that AFD may get a suprious TDI
  39. // indication *after* an abort request has completed. As a temporary work-
  40. // around, whenever an abort request completes, we'll start a timer. AFD
  41. // will defer further processing on the connection until that timer fires.
  42. //
  43. // If the following symbol is defined, then our timer hack is enabled.
  44. // Afd now uses InterlockedCompareExchange to protect itself
  45. //
  46. // #define ENABLE_ABORT_TIMER_HACK 0
  47. //
  48. // The following constant defines the relative time interval (in seconds)
  49. // for the "post abort request complete" timer.
  50. //
  51. // #define AFD_ABORT_TIMER_TIMEOUT_VALUE 5 // seconds
  52. //
  53. // Goodies stolen from other header files.
  54. //
  55. #ifndef FAR
  56. #define FAR
  57. #endif
  58. #ifndef max
  59. #define max(a,b) (((a) > (b)) ? (a) : (b))
  60. #endif
  61. #ifndef min
  62. #define min(a,b) (((a) < (b)) ? (a) : (b))
  63. #endif
  64. typedef unsigned short u_short;
  65. #ifndef SG_UNCONSTRAINED_GROUP
  66. #define SG_UNCONSTRAINED_GROUP 0x01
  67. #endif
  68. #ifndef SG_CONSTRAINED_GROUP
  69. #define SG_CONSTRAINED_GROUP 0x02
  70. #endif
  71. #include <afd.h>
  72. #include "afdstr.h"
  73. #include "afddata.h"
  74. #include "afdprocs.h"
  75. #define AFD_EA_POOL_TAG ( (ULONG)'AdfA' | PROTECTED_POOL )
  76. #define AFD_DATA_BUFFER_POOL_TAG ( (ULONG)'BdfA' | PROTECTED_POOL )
  77. #define AFD_CONNECTION_POOL_TAG ( (ULONG)'CdfA' | PROTECTED_POOL )
  78. #define AFD_CONNECT_DATA_POOL_TAG ( (ULONG)'cdfA' | PROTECTED_POOL )
  79. #define AFD_DEBUG_POOL_TAG ( (ULONG)'DdfA' | PROTECTED_POOL )
  80. #define AFD_ENDPOINT_POOL_TAG ( (ULONG)'EdfA' | PROTECTED_POOL )
  81. #define AFD_TRANSMIT_INFO_POOL_TAG ( (ULONG)'FdfA' | PROTECTED_POOL )
  82. #define AFD_GROUP_POOL_TAG ( (ULONG)'GdfA' | PROTECTED_POOL )
  83. #define AFD_ADDRESS_CHANGE_POOL_TAG ( (ULONG)'hdfA' | PROTECTED_POOL )
  84. #define AFD_TDI_POOL_TAG ( (ULONG)'IdfA' | PROTECTED_POOL )
  85. #define AFD_LOCAL_ADDRESS_POOL_TAG ( (ULONG)'LdfA' | PROTECTED_POOL )
  86. #define AFD_POLL_POOL_TAG ( (ULONG)'PdfA' | PROTECTED_POOL )
  87. #define AFD_TRANSPORT_IRP_POOL_TAG ( (ULONG)'pdfA' | PROTECTED_POOL )
  88. #define AFD_ROUTING_QUERY_POOL_TAG ( (ULONG)'qdfA' | PROTECTED_POOL )
  89. #define AFD_REMOTE_ADDRESS_POOL_TAG ( (ULONG)'RdfA' | PROTECTED_POOL )
  90. #define AFD_RESOURCE_POOL_TAG ( (ULONG)'rdfA' | PROTECTED_POOL )
  91. // Can't be protected - freed by kernel.
  92. #define AFD_SECURITY_POOL_TAG ( (ULONG)'SdfA' )
  93. #define AFD_TRANSPORT_ADDRESS_POOL_TAG ( (ULONG)'tdfA' | PROTECTED_POOL )
  94. #define AFD_TRANSPORT_INFO_POOL_TAG ( (ULONG)'TdfA' | PROTECTED_POOL )
  95. // Can't be protected - freed by kernel.
  96. #define AFD_TEMPORARY_POOL_TAG ( (ULONG)' dfA' )
  97. #define AFD_CONTEXT_POOL_TAG ( (ULONG)'XdfA' | PROTECTED_POOL )
  98. #define AFD_SAN_CONTEXT_POOL_TAG ( (ULONG)'xdfA' | PROTECTED_POOL )
  99. #define MyFreePoolWithTag(a,t) ExFreePoolWithTag(a,t)
  100. #if DBG
  101. //
  102. // N.B. This structure MUST be quadword aligned!
  103. //
  104. typedef struct DECLSPEC_ALIGN(MEMORY_ALLOCATION_ALIGNMENT) _AFD_POOL_HEADER {
  105. SIZE_T Size;
  106. PCHAR FileName;
  107. ULONG LineNumber;
  108. ULONG InUse;
  109. } AFD_POOL_HEADER, *PAFD_POOL_HEADER;
  110. #define AFD_POOL_OVERHEAD (sizeof(AFD_POOL_HEADER))
  111. #else
  112. #define AFD_POOL_OVERHEAD 0
  113. #endif
  114. #if DBG
  115. extern ULONG AfdDebug;
  116. extern ULONG AfdLocksAcquired;
  117. #undef IF_DEBUG
  118. #define IF_DEBUG(a) if ( (AFD_DEBUG_ ## a & AfdDebug) != 0 )
  119. #define AFD_DEBUG_OPEN_CLOSE 0x00000001
  120. #define AFD_DEBUG_ENDPOINT 0x00000002
  121. #define AFD_DEBUG_CONNECTION 0x00000004
  122. #define AFD_DEBUG_EVENT_SELECT 0x00000008
  123. #define AFD_DEBUG_BIND 0x00000010
  124. #define AFD_DEBUG_CONNECT 0x00000020
  125. #define AFD_DEBUG_LISTEN 0x00000040
  126. #define AFD_DEBUG_ACCEPT 0x00000080
  127. #define AFD_DEBUG_SEND 0x00000100
  128. #define AFD_DEBUG_QUOTA 0x00000200
  129. #define AFD_DEBUG_RECEIVE 0x00000400
  130. #define AFD_DEBUG_11 0x00000800
  131. #define AFD_DEBUG_POLL 0x00001000
  132. #define AFD_DEBUG_FAST_IO 0x00002000
  133. #define AFD_DEBUG_ROUTING_QUERY 0x00010000
  134. #define AFD_DEBUG_ADDRESS_LIST 0x00020000
  135. #define AFD_DEBUG_TRANSMIT 0x00100000
  136. #define AFD_DEBUG_SAN_SWITCH 0x00200000
  137. #define DEBUG
  138. #define AFD_ALLOCATE_POOL(a,b,t) AfdAllocatePool( a,b,t,__FILE__,__LINE__,FALSE,LowPoolPriority )
  139. #define AFD_ALLOCATE_POOL_WITH_QUOTA(a,b,t) AfdAllocatePool( (a)|POOL_RAISE_IF_ALLOCATION_FAILURE,b,t,__FILE__,__LINE__,TRUE,LowPoolPriority )
  140. #define AFD_ALLOCATE_POOL_PRIORITY(a,b,t,p) AfdAllocatePool( a,b,t,__FILE__,__LINE__,FALSE,p )
  141. PVOID
  142. AfdAllocatePool (
  143. IN POOL_TYPE PoolType,
  144. IN SIZE_T NumberOfBytes,
  145. IN ULONG Tag,
  146. IN PCHAR FileName,
  147. IN ULONG LineNumber,
  148. IN BOOLEAN WithQuota,
  149. IN EX_POOL_PRIORITY Priority
  150. );
  151. #define AFD_FREE_POOL(a,t) AfdFreePool(a,t)
  152. VOID
  153. AfdFreePool (
  154. IN PVOID Pointer,
  155. IN ULONG Tag
  156. );
  157. #define AfdRecordOutstandingIrp(a,b,c) \
  158. AfdRecordOutstandingIrpDebug(a,b,c,__FILE__,__LINE__)
  159. BOOLEAN
  160. AfdRecordOutstandingIrpDebug (
  161. IN PAFD_ENDPOINT Endpoint,
  162. IN PDEVICE_OBJECT DeviceObject,
  163. IN PIRP Irp,
  164. IN PCHAR FileName,
  165. IN ULONG LineNumber
  166. );
  167. #define AfdIoCallDriver(a,b,c) \
  168. (AfdRecordOutstandingIrp(a,b,c) \
  169. ? IoCallDriver (b,c) \
  170. : STATUS_INSUFFICIENT_RESOURCES \
  171. )
  172. #define AfdCompleteOutstandingIrp(a,b) \
  173. AfdCompleteOutstandingIrpDebug(a,b)
  174. VOID
  175. AfdCompleteOutstandingIrpDebug (
  176. IN PAFD_ENDPOINT Endpoint,
  177. IN PIRP Irp
  178. );
  179. #ifdef AFDDBG_QUOTA
  180. VOID
  181. AfdRecordQuotaHistory(
  182. IN PEPROCESS Process,
  183. IN LONG Bytes,
  184. IN PSZ Type,
  185. IN PVOID Block
  186. );
  187. #else
  188. #define AfdRecordQuotaHistory(a,b,c,d)
  189. #endif
  190. //
  191. // Queued spinlock wrappers - perform basic validation
  192. //
  193. #define AfdAcquireSpinLock(a,b) \
  194. ASSERT(AfdLoaded); (b)->SpinLock=(a); KeAcquireInStackQueuedSpinLock(&(a)->ActualSpinLock,&((b)->LockHandle)); AfdLocksAcquired++
  195. #define AfdReleaseSpinLock(a,b) \
  196. AfdLocksAcquired--; ASSERT ((b)->SpinLock==(a)); ASSERT( AfdLoaded ); KeReleaseInStackQueuedSpinLock(&((b)->LockHandle));
  197. #define AfdAcquireSpinLockAtDpcLevel(a,b) \
  198. ASSERT( AfdLoaded ); (b)->SpinLock=(a); KeAcquireInStackQueuedSpinLockAtDpcLevel(&(a)->ActualSpinLock,&((b)->LockHandle)); AfdLocksAcquired++
  199. #define AfdReleaseSpinLockFromDpcLevel(a,b) \
  200. AfdLocksAcquired--; ASSERT ((b)->SpinLock==(a)); ASSERT( AfdLoaded ); KeReleaseInStackQueuedSpinLockFromDpcLevel(&((b)->LockHandle))
  201. #define AfdInitializeSpinLock(a) \
  202. KeInitializeSpinLock(&(a)->ActualSpinLock)
  203. //
  204. // Define our own assert so that we can actually catch assertion failures
  205. // when running a checked AFD on a free kernel.
  206. //
  207. VOID
  208. AfdAssert(
  209. PVOID FailedAssertion,
  210. PVOID FileName,
  211. ULONG LineNumber,
  212. PCHAR Message
  213. );
  214. #undef ASSERT
  215. #define ASSERT( exp ) \
  216. if (!(exp)) \
  217. AfdAssert( #exp, __FILE__, __LINE__, NULL )
  218. #undef ASSERTMSG
  219. #define ASSERTMSG( msg, exp ) \
  220. if (!(exp)) \
  221. AfdAssert( #exp, __FILE__, __LINE__, msg )
  222. #define AFD_EXCEPTION_FILTER(_s) \
  223. AfdExceptionFilter( \
  224. (LPSTR)__FILE__, \
  225. (LONG)__LINE__, \
  226. GetExceptionInformation(), \
  227. _s \
  228. )
  229. #else // !DBG
  230. #undef IF_DEBUG
  231. #define IF_DEBUG(a) if (FALSE)
  232. #define DEBUG if ( FALSE )
  233. #define AFD_ALLOCATE_POOL(a,b,t) ExAllocatePoolWithTagPriority(a,b,t,LowPoolPriority)
  234. #define AFD_ALLOCATE_POOL_WITH_QUOTA(a,b,t) ExAllocatePoolWithQuotaTag((a)|POOL_RAISE_IF_ALLOCATION_FAILURE,b,t)
  235. #define AFD_ALLOCATE_POOL_PRIORITY(a,b,t,p) ExAllocatePoolWithTagPriority(a,b,t,p)
  236. #define AFD_FREE_POOL(a,t) MyFreePoolWithTag(a,t)
  237. #define AfdRecordOutstandingIrp(a,b,c) \
  238. (InterlockedIncrement(&((a)->OutstandingIrpCount)), TRUE)
  239. #define AfdIoCallDriver(a,b,c) \
  240. (AfdRecordOutstandingIrp(a,b,c), IoCallDriver(b,c))
  241. #define AfdCompleteOutstandingIrp(a,b) \
  242. InterlockedDecrement(&((a)->OutstandingIrpCount))
  243. NTSTATUS
  244. AfdIoCallDriverFree (
  245. IN PAFD_ENDPOINT Endpoint,
  246. IN PDEVICE_OBJECT DeviceObject,
  247. IN PIRP Irp
  248. );
  249. VOID
  250. AfdCompleteOutstandingIrpFree (
  251. IN PAFD_ENDPOINT Endpoint,
  252. IN PIRP Irp
  253. );
  254. #define AfdRecordQuotaHistory(a,b,c,d)
  255. #define AfdAcquireSpinLock(a,b) KeAcquireInStackQueuedSpinLock(&(a)->ActualSpinLock,(b))
  256. #define AfdReleaseSpinLock(a,b) KeReleaseInStackQueuedSpinLock((b))
  257. #define AfdAcquireSpinLockAtDpcLevel(a,b) KeAcquireInStackQueuedSpinLockAtDpcLevel(&(a)->ActualSpinLock,(b))
  258. #define AfdReleaseSpinLockFromDpcLevel(a,b) KeReleaseInStackQueuedSpinLockFromDpcLevel((b))
  259. #define AfdInitializeSpinLock(a) \
  260. KeInitializeSpinLock(&(a)->ActualSpinLock)
  261. #define AFD_EXCEPTION_FILTER(_s) \
  262. AfdExceptionFilter( \
  263. GetExceptionInformation(), \
  264. _s \
  265. )
  266. #endif // def DBG
  267. #if DBG || REFERENCE_DEBUG
  268. VOID
  269. AfdInitializeDebugData(
  270. VOID
  271. );
  272. VOID
  273. AfdFreeDebugData (
  274. VOID
  275. );
  276. #endif
  277. //
  278. // Make some of the receive code a bit prettier.
  279. //
  280. #define TDI_RECEIVE_EITHER ( TDI_RECEIVE_NORMAL | TDI_RECEIVE_EXPEDITED )
  281. #endif // ndef _AFDP_