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.

296 lines
5.0 KiB

  1. #include "precomp.h"
  2. #include "NacList.h"
  3. template <class T>
  4. NacList<T>::NacList(int nInitialSize, int nGrowthRate) :
  5. m_nSize(0), m_nHeadIndex(0), m_nTotalSize(nInitialSize), m_nGrowthRate(nGrowthRate)
  6. {
  7. ASSERT(nInitialSize > 0);
  8. ASSERT(nGrowthRate > 0);
  9. DBG_SAVE_FILE_LINE
  10. m_aElements = new T[nInitialSize];
  11. if (m_aElements == NULL)
  12. {
  13. ERROR_OUT(("NacList::NacList - Out of memory"));
  14. }
  15. }
  16. template <class T>
  17. NacList<T>::~NacList()
  18. {
  19. Flush();
  20. delete [] m_aElements;
  21. }
  22. template <class T>
  23. void NacList<T>::Flush()
  24. {
  25. m_nHeadIndex = 0;
  26. m_nSize = 0;
  27. }
  28. template <class T>
  29. bool NacList<T>::PeekFront(T *pT)
  30. {
  31. if (m_nSize <= 0)
  32. {
  33. return false;
  34. }
  35. *pT = m_aElements[m_nHeadIndex];
  36. return true;
  37. }
  38. template <class T>
  39. bool NacList<T>::PeekRear(T *pT)
  40. {
  41. int nRearIndex;
  42. if (m_nSize <= 0)
  43. {
  44. return false;
  45. }
  46. nRearIndex = (m_nHeadIndex + m_nSize - 1) % m_nTotalSize;
  47. *pT = m_aElements[nRearIndex];
  48. return true;
  49. }
  50. template <class T>
  51. bool NacList<T>::PushFront(const T &t)
  52. {
  53. int nInsertIndex;
  54. // do we need to grow
  55. if (m_nSize >= m_nTotalSize)
  56. {
  57. Grow();
  58. }
  59. if (m_nHeadIndex == 0)
  60. {
  61. m_nHeadIndex = m_nTotalSize - 1;
  62. }
  63. else
  64. {
  65. --m_nHeadIndex;
  66. }
  67. m_aElements[m_nHeadIndex] = t;
  68. m_nSize++;
  69. return true;
  70. }
  71. template <class T>
  72. bool NacList<T>::PushRear(const T &t)
  73. {
  74. int nInsertIndex;
  75. // do we need to grow
  76. if (m_nSize >= m_nTotalSize)
  77. {
  78. Grow();
  79. }
  80. nInsertIndex = (m_nHeadIndex + m_nSize) % m_nTotalSize;
  81. m_aElements[nInsertIndex] = t;
  82. m_nSize++;
  83. return true;
  84. }
  85. template <class T>
  86. bool NacList<T>::PopFront(T *pT)
  87. {
  88. ASSERT(m_nSize >= 0);
  89. if (m_nSize <= 0)
  90. {
  91. return false;
  92. }
  93. *pT = m_aElements[m_nHeadIndex];
  94. m_nHeadIndex = (m_nHeadIndex + 1) % m_nTotalSize;
  95. m_nSize--;
  96. return true;
  97. }
  98. template <class T>
  99. bool NacList<T>::PopRear(T *pT)
  100. {
  101. int nRearIndex;
  102. ASSERT(m_nSize >= 0);
  103. if (m_nSize <= 0)
  104. {
  105. return false;
  106. }
  107. nRearIndex = (m_nHeadIndex + m_nSize - 1) % m_nTotalSize;
  108. *pT = m_aElements[nRearIndex];
  109. m_nSize--;
  110. return true;
  111. }
  112. template <class T>
  113. int NacList<T>::Grow()
  114. {
  115. T *aNew;
  116. int nTotalSize;
  117. int nIndex, nCopyIndex;
  118. nTotalSize = m_nTotalSize + m_nGrowthRate;
  119. DBG_SAVE_FILE_LINE
  120. aNew = new T[nTotalSize];
  121. if (aNew == NULL)
  122. {
  123. ERROR_OUT(("Out of Memory"));
  124. return 0;
  125. }
  126. for (nIndex = 0; nIndex < m_nSize; nIndex++)
  127. {
  128. nCopyIndex = (nIndex + m_nHeadIndex) % m_nTotalSize;
  129. aNew[nIndex] = m_aElements[nCopyIndex];
  130. }
  131. delete [] m_aElements;
  132. m_aElements = aNew;
  133. m_nTotalSize = nTotalSize;
  134. m_nHeadIndex = 0;
  135. return (nTotalSize);
  136. }
  137. // Thread Safe List
  138. template <class T>
  139. ThreadSafeList<T>::ThreadSafeList(int nInitialSize, int nGrowthRate) :
  140. NacList<T>(nInitialSize, nGrowthRate)
  141. {
  142. InitializeCriticalSection(&m_cs);
  143. }
  144. template <class T>
  145. ThreadSafeList<T>::~ThreadSafeList()
  146. {
  147. DeleteCriticalSection(&m_cs);
  148. }
  149. template <class T>
  150. void ThreadSafeList<T>::Flush()
  151. {
  152. EnterCriticalSection(&m_cs);
  153. NacList<T>::Flush();
  154. LeaveCriticalSection(&m_cs);
  155. }
  156. template <class T>
  157. bool ThreadSafeList<T>::PeekFront(T *pT)
  158. {
  159. bool bRet;
  160. EnterCriticalSection(&m_cs);
  161. bRet = NacList<T>::PeekFront(pT);
  162. LeaveCriticalSection(&m_cs);
  163. return bRet;
  164. }
  165. template <class T>
  166. bool ThreadSafeList<T>::PeekRear(T *pT)
  167. {
  168. bool bRet;
  169. EnterCriticalSection(&m_cs);
  170. bRet = NacList<T>::PeekRear(pT);
  171. LeaveCriticalSection(&m_cs);
  172. return bRet;
  173. }
  174. template <class T>
  175. bool ThreadSafeList<T>::PushFront(const T &t)
  176. {
  177. bool bRet;
  178. EnterCriticalSection(&m_cs);
  179. bRet = NacList<T>::PushFront(t);
  180. LeaveCriticalSection(&m_cs);
  181. return bRet;
  182. }
  183. template <class T>
  184. bool ThreadSafeList<T>::PushRear(const T &t)
  185. {
  186. bool bRet;
  187. EnterCriticalSection(&m_cs);
  188. bRet = NacList<T>::PushRear(t);
  189. LeaveCriticalSection(&m_cs);
  190. return bRet;
  191. }
  192. template <class T>
  193. bool ThreadSafeList<T>::PopFront(T *pT)
  194. {
  195. bool bRet;
  196. EnterCriticalSection(&m_cs);
  197. bRet = NacList<T>::PopFront(pT);
  198. LeaveCriticalSection(&m_cs);
  199. return bRet;
  200. }
  201. template <class T>
  202. bool ThreadSafeList<T>::PopRear(T *pT)
  203. {
  204. bool bRet;
  205. EnterCriticalSection(&m_cs);
  206. bRet = NacList<T>::PopRear(pT);
  207. LeaveCriticalSection(&m_cs);
  208. return bRet;
  209. }
  210. template <class T>
  211. int ThreadSafeList<T>::Size()
  212. {
  213. int nRet;
  214. EnterCriticalSection(&m_cs);
  215. nRet = NacList<T>::Size();
  216. LeaveCriticalSection(&m_cs);
  217. return nRet;
  218. }
  219. // each instance type of the template needs to be declared here
  220. // For example:
  221. // template class NacList<int>; // list of integers
  222. // template class NacList<int*>; // list of pointers to integers
  223. // you have to disable warnings for the following error, else
  224. // the compiler thinks that a second instantiation is occuring
  225. // when it's really only a second declaration
  226. // This generates a warning which becomes an error
  227. #pragma warning(disable:4660)
  228. #include "PacketSender.h"
  229. template class ThreadSafeList<PS_QUEUE_ELEMENT>;