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.

304 lines
10 KiB

  1. #ifndef _HEAP_HPP_
  2. #define _HEAP_HPP_
  3. // Ruler
  4. // 1 2 3 4 5 6 7 8
  5. //345678901234567890123456789012345678901234567890123456789012345678901234567890
  6. /********************************************************************/
  7. /* */
  8. /* The standard layout. */
  9. /* */
  10. /* The standard layout for 'hpp' files for this code is as */
  11. /* follows: */
  12. /* */
  13. /* 1. Include files. */
  14. /* 2. Constants exported from the class. */
  15. /* 3. Data structures exported from the class. */
  16. /* 4. Forward references to other data structures. */
  17. /* 5. Class specifications (including inline functions). */
  18. /* 6. Additional large inline functions. */
  19. /* */
  20. /* Any portion that is not required is simply omitted. */
  21. /* */
  22. /********************************************************************/
  23. #include "Global.hpp"
  24. #include "Environment.hpp"
  25. #include "Common.hpp"
  26. #include "Find.hpp"
  27. #include "NewPage.hpp"
  28. #include "Prefetch.hpp"
  29. #include "Rockall.hpp"
  30. /********************************************************************/
  31. /* */
  32. /* Class forward references. */
  33. /* */
  34. /* We need to refer to the following classes before they are */
  35. /* fully specified so here we list them as forward references. */
  36. /* */
  37. /********************************************************************/
  38. class BUCKET;
  39. class CACHE;
  40. /********************************************************************/
  41. /* */
  42. /* The heap interface. */
  43. /* */
  44. /* The traditional memory allocation interface only supports */
  45. /* a single allocation heap. This memory allocator supports */
  46. /* multiple allocation heaps. However, the interface nicely */
  47. /* hides this so at this point we are back to the traditional */
  48. /* single heap interface. */
  49. /* */
  50. /********************************************************************/
  51. class HEAP : public ENVIRONMENT, public COMMON
  52. {
  53. //
  54. // Private data.
  55. //
  56. // The heap is the top level container of all the
  57. // functionality in the other classes. The 'Active'
  58. // flag indicates if the heap has been initialized.
  59. // The 'MaxFreePages' controls the amount of free
  60. // space the heap will slave before it starts to
  61. // return it the the external allocator. The
  62. // 'SmallestParentMask' is mask that shows which
  63. // parts of an address can be safely masked off
  64. // and still ensure a hit in the find lookaside
  65. // cache. The 'ThreadSafe' flag indicates whether
  66. // locking being used.
  67. //
  68. BOOLEAN Active;
  69. SBIT32 MaxFreePages;
  70. BIT32 SmallestParentMask;
  71. BOOLEAN ThreadSafe;
  72. //
  73. // A heap is merely a collection of fixed sized
  74. // allocation buckets (each with an optional cache).
  75. // The 'CachesSize' is the total number of buckets.
  76. // The 'MinCacheSize' is the allocation size of the
  77. // smallest bucket. The 'MidCacheSize' is the size
  78. // of the bucket where the stride changes. The
  79. // 'MaxCacheSize' is the allocation size of the
  80. // largest bucket externally visable.
  81. //
  82. SBIT32 CachesSize;
  83. SBIT32 MinCacheSize;
  84. SBIT32 MidCacheSize;
  85. SBIT32 MaxCacheSize;
  86. //
  87. // A key function of the heap is to convert the
  88. // requested allocation size into a pointer to
  89. // the appropriate bucket (and cache). This has
  90. // to be very fast and is achieved using a direct
  91. // lookup (i.e. an array). The lookup array
  92. // consists of two sections (i.e. for small sizes
  93. // and large sizes) to minimize space. The
  94. // 'MaxTable1' and 'MaxTable2' variables contain
  95. // the size of each section of the array. The
  96. // 'ShiftSize1' and 'ShiftSize2' variables contain
  97. // the shift that should be applied to the size to
  98. // obtain the appropriate index. The 'SizeToCache1'
  99. // and 'SizeToCache2' pointers refer to the direct
  100. // lookup tables.
  101. //
  102. SBIT32 MaxTable1;
  103. SBIT32 MaxTable2;
  104. SBIT32 ShiftSize1;
  105. SBIT32 ShiftSize2;
  106. CACHE **SizeToCache1;
  107. CACHE **SizeToCache2;
  108. //
  109. // The heap needs to have access to most of the
  110. // other classes. The 'Caches' class sits on
  111. // top of an allocation bucket which owns all
  112. // the allocated memory for a given size. The
  113. // 'ExternalCache' is a special bucket that
  114. // contains weird sized pages. The 'Find' class
  115. // translates allocation addresses to page
  116. // descriptions. The 'Rockall' class is needed
  117. // to gain access to the external allocation APIs.
  118. // The 'NewPage' class owns all page descriptions
  119. // and plays a significant role in whole heap
  120. // operations. The 'TopCache' is the largest
  121. // bucket size and owns almost all the externally
  122. // allocated memory.
  123. //
  124. CACHE **Caches;
  125. CACHE *ExternalCache;
  126. FIND *Find;
  127. NEW_PAGE *NewPage;
  128. PREFETCH Prefetch;
  129. ROCKALL *Rockall;
  130. CACHE *TopCache;
  131. #ifdef ENABLE_HEAP_STATISTICS
  132. //
  133. // Statistics data.
  134. //
  135. // A key feature of this heap is its ability to be
  136. // significantly reconfigured at run time. A great
  137. // deal of complexity could have been removed if
  138. // certain static choices had been made. Although
  139. // this flexibility is nice the support of statistics
  140. // here allows precise information to be collected so
  141. // to enable the value of this to be maximized.
  142. //
  143. //
  144. SBIT32 CopyMisses;
  145. SBIT32 MaxCopySize;
  146. SBIT32 MaxNewSize;
  147. SBIT32 NewMisses;
  148. SBIT32 Reallocations;
  149. SBIT32 *Statistics;
  150. SBIT32 TotalCopySize;
  151. SBIT32 TotalNewSize;
  152. #endif
  153. public:
  154. //
  155. // Public functions.
  156. //
  157. // The heap exports the high level interface
  158. // out to the world. Any request a developer
  159. // can make must come through one of these
  160. // functions.
  161. //
  162. HEAP
  163. (
  164. CACHE *Caches1[],
  165. CACHE *Caches2[],
  166. SBIT32 MaxFreeSpace,
  167. FIND *NewFind,
  168. NEW_PAGE *NewPages,
  169. ROCKALL *NewRockall,
  170. SBIT32 Size1,
  171. SBIT32 Size2,
  172. SBIT32 Stride1,
  173. SBIT32 Stride2,
  174. BOOLEAN NewThredSafe
  175. );
  176. BOOLEAN Delete( VOID *Address,SBIT32 Size = NoSize );
  177. VOID DeleteAll( BOOLEAN Recycle = True );
  178. BOOLEAN Details( VOID *Address,SBIT32 *Size = NULL );
  179. VOID LockAll( VOID );
  180. BOOLEAN MultipleDelete
  181. (
  182. SBIT32 Actual,
  183. VOID *Array[],
  184. SBIT32 Size = NoSize
  185. );
  186. BOOLEAN MultipleNew
  187. (
  188. SBIT32 *Actual,
  189. VOID *Array[],
  190. SBIT32 Requested,
  191. SBIT32 Size,
  192. SBIT32 *Space = NULL,
  193. BOOLEAN Zero = False
  194. );
  195. VOID *New
  196. (
  197. SBIT32 Size,
  198. SBIT32 *Space = NULL,
  199. BOOLEAN Zero = False
  200. );
  201. VOID *Resize
  202. (
  203. VOID *Address,
  204. SBIT32 NewSize,
  205. SBIT32 Move = 1,
  206. SBIT32 *Space = NULL,
  207. BOOLEAN NoDelete = False,
  208. BOOLEAN Zero = False
  209. );
  210. BOOLEAN Truncate( SBIT32 MaxFreeSpace = 0 );
  211. VOID UnlockAll( BOOLEAN Partial = False );
  212. BOOLEAN Verify( VOID *Address,SBIT32 *Size = NULL );
  213. BOOLEAN Walk
  214. (
  215. BOOLEAN *Active,
  216. VOID **Address,
  217. SBIT32 *Size
  218. );
  219. ~HEAP( VOID );
  220. //
  221. // Public inline functions.
  222. //
  223. // Although these functions are public they mostly
  224. // intended for internal consumption and are not
  225. // to be called externally.
  226. //
  227. INLINE SBIT32 GetMaxFreePages( VOID )
  228. { return MaxFreePages; }
  229. INLINE BOOLEAN KnownArea( VOID *Address )
  230. { return (Find -> KnownArea( Address,TopCache )); }
  231. INLINE VOID *SpecialNew( SBIT32 Size )
  232. { return NewPage -> NewCacheStack( Size ); }
  233. private:
  234. //
  235. // Private functions.
  236. //
  237. // All of the statistical information is
  238. // generated and output when the heaps
  239. // destructor executes.
  240. //
  241. CACHE *FindCache( SBIT32 Size );
  242. #ifdef ENABLE_HEAP_STATISTICS
  243. VOID PrintDebugStatistics( VOID );
  244. #endif
  245. //
  246. // Private inline functions.
  247. //
  248. // The notion that resizing an allocation is
  249. // cheap has worked its way into the minds of
  250. // a large number of developers. As a result
  251. // parameter has been added to the function to
  252. // allow the actual behavior to be controlled.
  253. //
  254. INLINE BOOLEAN ResizeTest( SBIT32 Delta,SBIT32 Move )
  255. {
  256. return
  257. (
  258. ((Move > 0) && ((((Delta >= 0) ? Delta : -Delta) >= Move)))
  259. ||
  260. ((Move < 0) && ((Delta > 0) || (Delta <= Move)))
  261. );
  262. }
  263. //
  264. // Disabled operations.
  265. //
  266. // All copy constructors and class assignment
  267. // operations are disabled.
  268. //
  269. HEAP( CONST HEAP & Copy );
  270. VOID operator=( CONST HEAP & Copy );
  271. };
  272. #endif