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.

199 lines
7.1 KiB

  1. // Ruler
  2. // 1 2 3 4 5 6 7 8
  3. //345678901234567890123456789012345678901234567890123456789012345678901234567890
  4. /********************************************************************/
  5. /* */
  6. /* The standard layout. */
  7. /* */
  8. /* The standard layout for 'cpp' files in this code is as */
  9. /* follows: */
  10. /* */
  11. /* 1. Include files. */
  12. /* 2. Constants local to the class. */
  13. /* 3. Data structures local to the class. */
  14. /* 4. Data initializations. */
  15. /* 5. Static functions. */
  16. /* 6. Class functions. */
  17. /* */
  18. /* The constructor is typically the first function, class */
  19. /* member functions appear in alphabetical order with the */
  20. /* destructor appearing at the end of the file. Any section */
  21. /* or function this is not required is simply omitted. */
  22. /* */
  23. /********************************************************************/
  24. #include "LibraryPCH.hpp"
  25. #include "SList.hpp"
  26. #ifdef ASSEMBLY_X86
  27. /********************************************************************/
  28. /* */
  29. /* Class constructor. */
  30. /* */
  31. /* Create a new slist and initialize it. This call is not */
  32. /* thread safe and should only be made in a single thread */
  33. /* environment. */
  34. /* */
  35. /********************************************************************/
  36. SLIST::SLIST( VOID )
  37. {
  38. //
  39. // Zero the list head.
  40. //
  41. Header = 0;
  42. }
  43. /********************************************************************/
  44. /* */
  45. /* Pop an element. */
  46. /* */
  47. /* Pop an element from the list. */
  48. /* */
  49. /********************************************************************/
  50. BOOLEAN SLIST::Pop( SLIST **Element )
  51. {
  52. AUTO SBIT64 Original;
  53. AUTO SBIT64 Update;
  54. REGISTER SLIST_HEADER *NewElement;
  55. REGISTER SLIST_HEADER *NewHeader = ((SLIST_HEADER*) & Update);
  56. //
  57. // We repeatedly try to update the list until
  58. // we are sucessful.
  59. //
  60. do
  61. {
  62. //
  63. // Clone the current head of the list.
  64. //
  65. Original = Header;
  66. Update = Original;
  67. //
  68. // We need to be sure that there is an element
  69. // to extract. If not we exit.
  70. //
  71. if ( (NewElement = ((SLIST_HEADER*) NewHeader -> Address)) != NULL )
  72. {
  73. //
  74. // Create a new list head.
  75. //
  76. NewHeader -> Address = NewElement -> Address;
  77. NewHeader -> Size --;
  78. NewHeader -> Version ++;
  79. }
  80. else
  81. { return False; }
  82. }
  83. while
  84. ( AtomicCompareExchange64( & Header,Update,Original ) != Original );
  85. //
  86. // Update the parameter and exit.
  87. //
  88. (*Element) = ((SLIST*) NewElement);
  89. return True;
  90. }
  91. /********************************************************************/
  92. /* */
  93. /* Pop all elements. */
  94. /* */
  95. /* Pop all the elements from the list. */
  96. /* */
  97. /********************************************************************/
  98. VOID SLIST::PopAll( SLIST **List )
  99. {
  100. AUTO SBIT64 Original;
  101. AUTO SBIT64 Update = NULL;
  102. REGISTER SLIST_HEADER *OldHeader = ((SLIST_HEADER*) & Original);
  103. //
  104. // We repeatedly try to update the list until
  105. // we are sucessful.
  106. //
  107. do
  108. {
  109. //
  110. // Clone the current head of the list.
  111. //
  112. Original = Header;
  113. }
  114. while
  115. ( AtomicCompareExchange64( & Header,Update,Original ) != Original );
  116. //
  117. // Update the parameter and exit.
  118. //
  119. (*List) = ((SLIST*) OldHeader -> Address);
  120. }
  121. /********************************************************************/
  122. /* */
  123. /* Push an element. */
  124. /* */
  125. /* Push an element onto the list. */
  126. /* */
  127. /********************************************************************/
  128. VOID SLIST::Push( SLIST *Element )
  129. {
  130. AUTO SBIT64 Original;
  131. AUTO SBIT64 Update;
  132. REGISTER SLIST_HEADER *NewElement = ((SLIST_HEADER*) Element);
  133. REGISTER SLIST_HEADER *NewHeader = ((SLIST_HEADER*) & Update);
  134. //
  135. // We repeatedly try to update the list until
  136. // we are sucessful.
  137. //
  138. do
  139. {
  140. //
  141. // Clone the current head of the list.
  142. //
  143. Original = Header;
  144. Update = Original;
  145. //
  146. // The current list head is copied to
  147. // the new element pointer.
  148. //
  149. NewElement -> Address = NewHeader -> Address;
  150. //
  151. // Update the list head.
  152. //
  153. NewHeader -> Address = Element;
  154. NewHeader -> Size ++;
  155. NewHeader -> Version ++;
  156. }
  157. while
  158. ( AtomicCompareExchange64( & Header,Update,Original ) != Original );
  159. }
  160. /********************************************************************/
  161. /* */
  162. /* Class destructor. */
  163. /* */
  164. /* Destory a SList. This call is not thread safe and should */
  165. /* only be made in a single thread environment. */
  166. /* */
  167. /********************************************************************/
  168. SLIST::~SLIST( VOID )
  169. {
  170. //
  171. // The list should be empty.
  172. //
  173. if ( Header != 0 )
  174. { Failure( "Non-empty list in destructor for SLIST" ); }
  175. }
  176. #endif