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.

288 lines
7.0 KiB

  1. /*++
  2. Copyright (c) 1999-2002 Microsoft Corporation
  3. Module Name:
  4. debugp.h
  5. Abstract:
  6. This module contains definitions private to the debug support.
  7. These declarations are placed in a separate .H file to make it
  8. easier to access them from within the kernel debugger extension DLL.
  9. Author:
  10. Keith Moore (keithmo) 07-Apr-1999
  11. Revision History:
  12. --*/
  13. #ifndef _DEBUGP_H_
  14. #define _DEBUGP_H_
  15. //
  16. // MDL tracker
  17. //
  18. typedef struct _UL_DEBUG_MDL_TRACKER
  19. {
  20. PMDL pMdl;
  21. PCSTR pFileName;
  22. USHORT LineNumber;
  23. LIST_ENTRY Linkage;
  24. } UL_DEBUG_MDL_TRACKER, *PUL_DEBUG_MDL_TRACKER;
  25. //
  26. // Per-thread data.
  27. //
  28. typedef struct _UL_DEBUG_THREAD_DATA
  29. {
  30. //
  31. // Links onto the global list.
  32. //
  33. LIST_ENTRY ThreadDataListEntry;
  34. //
  35. // The thread.
  36. //
  37. PETHREAD pThread;
  38. //
  39. // Reference count.
  40. //
  41. LONG ReferenceCount;
  42. //
  43. // Total number of resources held.
  44. //
  45. LONG ResourceCount;
  46. //
  47. // Total number of resources held.
  48. //
  49. LONG PushLockCount;
  50. //
  51. // If we call another driver they may call our
  52. // completion routine in-line. Remember that
  53. // we are inside an external call to avoid
  54. // getting confused.
  55. //
  56. LONG ExternalCallCount;
  57. } UL_DEBUG_THREAD_DATA, *PUL_DEBUG_THREAD_DATA;
  58. //
  59. // Header and trailer structs for Pool allocations
  60. //
  61. #define ENABLE_POOL_HEADER
  62. #define ENABLE_POOL_TRAILER
  63. #define ENABLE_POOL_TRAILER_BYTE_SIGNATURE
  64. #if !defined(ENABLE_POOL_HEADER) && defined(ENABLE_POOL_TRAILER)
  65. #error UL_POOL_TRAILER depends on UL_POOL_HEADER
  66. #endif
  67. #if !defined(_WIN64)
  68. # define UL_POOL_HEADER_PADDING
  69. #endif
  70. #ifdef ENABLE_POOL_HEADER
  71. typedef struct _UL_POOL_HEADER
  72. {
  73. PCSTR pFileName;
  74. PEPROCESS pProcess;
  75. SIZE_T Size;
  76. ULONG Tag;
  77. USHORT LineNumber;
  78. USHORT TrailerPadSize;
  79. #ifdef UL_POOL_HEADER_PADDING
  80. ULONG_PTR Padding;
  81. #endif
  82. } UL_POOL_HEADER, *PUL_POOL_HEADER;
  83. // sizeof(UL_POOL_HEADER) must be a multiple of MEMORY_ALLOCATION_ALIGNMENT
  84. C_ASSERT((sizeof(UL_POOL_HEADER) & (MEMORY_ALLOCATION_ALIGNMENT - 1)) == 0);
  85. __inline
  86. ULONG_PTR
  87. UlpPoolHeaderChecksum(
  88. PUL_POOL_HEADER pHeader
  89. )
  90. {
  91. ULONG_PTR Checksum;
  92. Checksum = ((ULONG_PTR) pHeader
  93. + ((ULONG_PTR) pHeader->pFileName >> 12)
  94. + (ULONG_PTR) pHeader->Size
  95. + (((ULONG_PTR) pHeader->LineNumber << 19)
  96. - pHeader->LineNumber) // 2^19-1 is prime
  97. + pHeader->TrailerPadSize);
  98. Checksum ^= ~ ((ULONG_PTR) pHeader->Tag << 8);
  99. return Checksum;
  100. } // UlpPoolHeaderChecksum
  101. #endif // ENABLE_POOL_HEADER
  102. #ifdef ENABLE_POOL_TRAILER
  103. typedef struct _UL_POOL_TRAILER
  104. {
  105. PUL_POOL_HEADER pHeader;
  106. ULONG_PTR CheckSum;
  107. } UL_POOL_TRAILER, *PUL_POOL_TRAILER;
  108. // sizeof(UL_POOL_TRAILER) must be a multiple of MEMORY_ALLOCATION_ALIGNMENT
  109. C_ASSERT((sizeof(UL_POOL_TRAILER) & (MEMORY_ALLOCATION_ALIGNMENT - 1)) == 0);
  110. #endif // ENABLE_POOL_TRAILER
  111. #ifdef ENABLE_POOL_TRAILER_BYTE_SIGNATURE
  112. __inline
  113. UCHAR
  114. UlpAddressToByteSignature(
  115. PVOID pAddress
  116. )
  117. {
  118. ULONG_PTR Address = (ULONG_PTR) pAddress;
  119. UCHAR Byte = (UCHAR) (~Address & 0xFF);
  120. // Don't want to return 0 as it may inadvertently terminate otherwise
  121. // unterminated strings
  122. return (Byte == 0) ? 0x5A : Byte;
  123. } // UlpAddressToByteSignature
  124. #endif // ENABLE_POOL_TRAILER_BYTE_SIGNATURE
  125. //
  126. // Keep track of UL_DEBUG_THREAD_DATA for each thread
  127. //
  128. typedef struct _UL_THREAD_HASH_BUCKET
  129. {
  130. union
  131. {
  132. struct
  133. {
  134. #if 0
  135. // Have to use a custom spinlock instead of a regular KSPIN_LOCK.
  136. // If the driver verifier's IRQL checking is enabled, every
  137. // spinlock acquisition has to trim all system pagable memory---a
  138. // hugely time-consuming process that radically changes
  139. // timing. Every workitem in the threadpool requires acquiring
  140. // this lock at least twice. Can't use an ERESOURCE or a
  141. // FAST_MUTEX because they cannot be acquired at DISPATCH_LEVEL.
  142. #endif
  143. KSPIN_LOCK BucketSpinLock;
  144. LONG Count;
  145. LONG Max;
  146. LIST_ENTRY BucketListHead;
  147. };
  148. UCHAR CacheAlignment[UL_CACHE_LINE];
  149. };
  150. } UL_THREAD_HASH_BUCKET, *PUL_THREAD_HASH_BUCKET;
  151. //
  152. // Private prototypes.
  153. //
  154. VOID
  155. UlpDbgUpdatePoolCounter(
  156. IN OUT PLARGE_INTEGER pAddend,
  157. IN SIZE_T Increment
  158. );
  159. PUL_DEBUG_THREAD_DATA
  160. UlpDbgFindThread(
  161. BOOLEAN OkToCreate,
  162. PCSTR pFileName,
  163. USHORT LineNumber
  164. );
  165. VOID
  166. UlpDbgDereferenceThread(
  167. IN PUL_DEBUG_THREAD_DATA pData
  168. REFERENCE_DEBUG_FORMAL_PARAMS
  169. );
  170. //
  171. // Private macros.
  172. //
  173. #define ULP_DBG_FIND_THREAD() \
  174. UlpDbgFindThread(FALSE, (PCSTR)__FILE__, (USHORT)__LINE__)
  175. #define ULP_DBG_FIND_OR_CREATE_THREAD() \
  176. UlpDbgFindThread(TRUE, (PCSTR)__FILE__, (USHORT)__LINE__)
  177. #define ULP_DBG_DEREFERENCE_THREAD(pData) \
  178. UlpDbgDereferenceThread((pData) REFERENCE_DEBUG_ACTUAL_PARAMS)
  179. #define SET_RESOURCE_OWNED_EXCLUSIVE( pLock ) \
  180. (pLock)->pExclusiveOwner = PsGetCurrentThread()
  181. #define SET_RESOURCE_NOT_OWNED_EXCLUSIVE( pLock ) \
  182. (pLock)->pPreviousOwner = (pLock)->pExclusiveOwner; \
  183. (pLock)->pExclusiveOwner = NULL
  184. #define SET_PUSH_LOCK_OWNED_EXCLUSIVE( pLock ) \
  185. (pLock)->pExclusiveOwner = PsGetCurrentThread()
  186. #define SET_PUSH_LOCK_NOT_OWNED_EXCLUSIVE( pLock ) \
  187. (pLock)->pPreviousOwner = (pLock)->pExclusiveOwner; \
  188. (pLock)->pExclusiveOwner = NULL
  189. #define SET_SPIN_LOCK_OWNED( pLock ) \
  190. do { \
  191. (pLock)->pOwnerThread = PsGetCurrentThread(); \
  192. (pLock)->OwnerProcessor = (ULONG)KeGetCurrentProcessorNumber(); \
  193. } while (FALSE)
  194. #define SET_SPIN_LOCK_NOT_OWNED( pLock ) \
  195. do { \
  196. (pLock)->pOwnerThread = NULL; \
  197. (pLock)->OwnerProcessor = (ULONG)-1L; \
  198. } while (FALSE)
  199. //
  200. // Private constants.
  201. //
  202. #define NUM_THREAD_HASH_BUCKETS 64
  203. #define NUM_THREAD_HASH_MASK (NUM_THREAD_HASH_BUCKETS - 1)
  204. // power of 2 required
  205. C_ASSERT((NUM_THREAD_HASH_BUCKETS & NUM_THREAD_HASH_MASK) == 0);
  206. // 8191 = 2^13 - 1 is prime. Grab the middle 6 bits after multiplying by 8191.
  207. #define HASH_FROM_THREAD(thrd) \
  208. ((ULONG) ((((ULONG_PTR)(thrd)) - ((ULONG_PTR) (thrd) >> 13)) \
  209. & NUM_THREAD_HASH_MASK))
  210. #endif // _DEBUGP_H_