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.

346 lines
7.5 KiB

  1. #include "precomp.h"
  2. //
  3. // OA.CPP
  4. // Order Accumulation, both cpi32 and display driver sides
  5. //
  6. // Copyright(c) Microsoft 1997-
  7. //
  8. #define MLZ_FILE_ZONE ZONE_ORDER
  9. //
  10. //
  11. // FUNCTION: OA_ResetOrderList
  12. //
  13. //
  14. // DESCRIPTION:
  15. //
  16. // Frees all Orders and Additional Order Data in the Order List.
  17. // Frees up the Order Heap memory.
  18. //
  19. //
  20. // PARAMETERS:
  21. //
  22. // None.
  23. //
  24. //
  25. // RETURNS:
  26. //
  27. // Nothing.
  28. //
  29. //
  30. void ASHost::OA_ResetOrderList(void)
  31. {
  32. LPOA_SHARED_DATA lpoaShared;
  33. DebugEntry(ASHost::OA_ResetOrderList);
  34. TRACE_OUT(("Free order list"));
  35. lpoaShared = OA_SHM_START_WRITING;
  36. //
  37. // First free all the orders on the list.
  38. //
  39. OAFreeAllOrders(lpoaShared);
  40. //
  41. // Ensure that the list pointers are NULL.
  42. //
  43. if ((lpoaShared->orderListHead.next != 0) || (lpoaShared->orderListHead.prev != 0))
  44. {
  45. ERROR_OUT(("Non-NULL list pointers (%lx)(%lx)",
  46. lpoaShared->orderListHead.next,
  47. lpoaShared->orderListHead.prev));
  48. COM_BasedListInit(&lpoaShared->orderListHead);
  49. }
  50. OA_SHM_STOP_WRITING;
  51. DebugExitVOID(ASHost::OA_ResetOrderList);
  52. }
  53. //
  54. // OA_SyncOutgoing()
  55. // Called when a share starts or somebody new joins the share.
  56. // Resets currently accumulated orders, which were based on old obsolete
  57. // caps and data.
  58. //
  59. void ASHost::OA_SyncOutgoing(void)
  60. {
  61. OAFreeAllOrders(g_poaData[1 - g_asSharedMemory->displayToCore.newBuffer]);
  62. }
  63. //
  64. //
  65. // OA_GetFirstListOrder()
  66. //
  67. // Returns:
  68. // Pointer to the first order in the Order List.
  69. //
  70. //
  71. LPINT_ORDER ASHost::OA_GetFirstListOrder(void)
  72. {
  73. LPOA_SHARED_DATA lpoaShared;
  74. LPINT_ORDER retOrder = NULL;
  75. DebugEntry(ASHost::OA_GetFirstListOrder);
  76. lpoaShared = OA_SHM_START_READING;
  77. //
  78. // Get the first entry from the linked list.
  79. //
  80. retOrder = (LPINT_ORDER)COM_BasedListFirst(&lpoaShared->orderListHead,
  81. FIELD_OFFSET(INT_ORDER, OrderHeader.list));
  82. OA_SHM_STOP_READING;
  83. TRACE_OUT(("First order = 0x%08x", retOrder));
  84. DebugExitVOID(ASHost::OA_GetFirstListOrder);
  85. return(retOrder);
  86. }
  87. //
  88. //
  89. // OA_RemoveListOrder(..)
  90. //
  91. // Removes the specified order from the Order List by marking it as spoilt.
  92. //
  93. // Returns:
  94. // Pointer to the order following the removed order.
  95. //
  96. //
  97. LPINT_ORDER ASHost::OA_RemoveListOrder(LPINT_ORDER pCondemnedOrder)
  98. {
  99. LPOA_SHARED_DATA lpoaShared;
  100. LPINT_ORDER pSaveOrder;
  101. // DebugEntry(ASHost::OA_RemoveListOrder);
  102. TRACE_OUT(("Remove list order 0x%08x", pCondemnedOrder));
  103. lpoaShared = OA_SHM_START_WRITING;
  104. //
  105. // Check for a valid order.
  106. //
  107. if (pCondemnedOrder->OrderHeader.Common.fOrderFlags & OF_SPOILT)
  108. {
  109. TRACE_OUT(("Invalid order"));
  110. DC_QUIT;
  111. }
  112. //
  113. // Mark the order as spoilt.
  114. //
  115. pCondemnedOrder->OrderHeader.Common.fOrderFlags |= OF_SPOILT;
  116. //
  117. // Update the count of bytes currently in the Order List.
  118. //
  119. lpoaShared->totalOrderBytes -= (UINT)MAX_ORDER_SIZE(pCondemnedOrder);
  120. //
  121. // SAve the order so we can remove it from the linked list after having
  122. // got the next element in the chain.
  123. //
  124. pSaveOrder = pCondemnedOrder;
  125. pCondemnedOrder = (LPINT_ORDER)COM_BasedListNext(&(lpoaShared->orderListHead),
  126. pCondemnedOrder, FIELD_OFFSET(INT_ORDER, OrderHeader.list));
  127. ASSERT(pCondemnedOrder != pSaveOrder);
  128. //
  129. // Delete the unwanted order from the linked list.
  130. //
  131. COM_BasedListRemove(&pSaveOrder->OrderHeader.list);
  132. //
  133. // Check that the list is still consistent with the total number of
  134. // order bytes.
  135. //
  136. if ( (lpoaShared->orderListHead.next != 0) &&
  137. (lpoaShared->orderListHead.prev != 0) &&
  138. (lpoaShared->totalOrderBytes == 0) )
  139. {
  140. ERROR_OUT(("List head wrong: %ld %ld", lpoaShared->orderListHead.next,
  141. lpoaShared->orderListHead.prev));
  142. COM_BasedListInit(&lpoaShared->orderListHead);
  143. pCondemnedOrder = NULL;
  144. }
  145. DC_EXIT_POINT:
  146. OA_SHM_STOP_WRITING;
  147. // DebugExitPVOID(ASHost::OA_RemoveListOrder, pCondemnedOrder);
  148. return(pCondemnedOrder);
  149. }
  150. //
  151. //
  152. // OA_GetTotalOrderListBytes(..)
  153. //
  154. // Returns:
  155. // The total number of bytes in the orders currently stored in the Order
  156. // List.
  157. //
  158. //
  159. UINT ASHost::OA_GetTotalOrderListBytes(void)
  160. {
  161. LPOA_SHARED_DATA lpoaShared;
  162. UINT rc;
  163. DebugEntry(ASHost::OA_GetTotalOrderListBytes);
  164. lpoaShared = OA_SHM_START_READING;
  165. rc = lpoaShared->totalOrderBytes;
  166. OA_SHM_STOP_READING;
  167. DebugExitDWORD(ASHost::OA_GetTotalOrderListBytes, rc);
  168. return(rc);
  169. }
  170. //
  171. // OA_LocalHostReset()
  172. //
  173. void ASHost::OA_LocalHostReset(void)
  174. {
  175. OA_FLOW_CONTROL oaFlowEsc;
  176. DebugEntry(ASHost::OA_LocalHostReset);
  177. m_oaFlow = OAFLOW_FAST;
  178. oaFlowEsc.oaFlow = m_oaFlow;
  179. OSI_FunctionRequest(OA_ESC_FLOW_CONTROL, (LPOSI_ESCAPE_HEADER)&oaFlowEsc, sizeof(oaFlowEsc));
  180. DebugExitVOID(ASHost::OA_LocalHostReset);
  181. }
  182. //
  183. // OA_FlowControl()
  184. // Sees if we've changed between fast and slow throughput, and adjusts some
  185. // accumulation variables accordingly.
  186. //
  187. void ASHost::OA_FlowControl(UINT newSize)
  188. {
  189. OA_FLOW_CONTROL oaFlowEsc;
  190. DebugEntry(ASHost::OA_FlowControl);
  191. //
  192. // Work out the new parameters.
  193. //
  194. if (newSize < OA_FAST_THRESHOLD)
  195. {
  196. //
  197. // Throughput is slow
  198. //
  199. if (m_oaFlow == OAFLOW_FAST)
  200. {
  201. m_oaFlow = OAFLOW_SLOW;
  202. TRACE_OUT(("OA_FlowControl: SLOW; spoil more orders and spoil by SDA"));
  203. }
  204. else
  205. {
  206. // No change
  207. DC_QUIT;
  208. }
  209. }
  210. else
  211. {
  212. //
  213. // Throughput is fast
  214. //
  215. if (m_oaFlow == OAFLOW_SLOW)
  216. {
  217. m_oaFlow = OAFLOW_FAST;
  218. TRACE_OUT(("OA_FlowControl: FAST; spoil fewer orders and don't spoil by SDA"));
  219. }
  220. else
  221. {
  222. // No change
  223. DC_QUIT;
  224. }
  225. }
  226. //
  227. // Tell the display driver about the new state
  228. //
  229. oaFlowEsc.oaFlow = m_oaFlow;
  230. OSI_FunctionRequest(OA_ESC_FLOW_CONTROL, (LPOSI_ESCAPE_HEADER)&oaFlowEsc, sizeof(oaFlowEsc));
  231. DC_EXIT_POINT:
  232. DebugExitVOID(ASHost::OA_FlowControl);
  233. }
  234. //
  235. // OA_QueryOrderAccum - see oa.h
  236. //
  237. UINT ASHost::OA_QueryOrderAccum(void)
  238. {
  239. LPOA_FAST_DATA lpoaFast;
  240. UINT rc = 0;
  241. DebugEntry(ASHost::OA_QueryOrderAccum);
  242. lpoaFast = OA_FST_START_WRITING;
  243. //
  244. // Get the current value.
  245. //
  246. rc = lpoaFast->ordersAccumulated;
  247. //
  248. // Clear the value for next time we swap the buffers.
  249. //
  250. lpoaFast->ordersAccumulated = 0;
  251. OA_FST_STOP_WRITING;
  252. DebugExitDWORD(ASHost::OA_QueryOrderAccum, rc);
  253. return(rc);
  254. }
  255. //
  256. // OAFreeAllOrders
  257. //
  258. // Free the all the individual orders on the orders list, without
  259. // discarding the list itself.
  260. //
  261. void ASHost::OAFreeAllOrders(LPOA_SHARED_DATA lpoaShared)
  262. {
  263. DebugEntry(ASHost::OAFreeAllOrders);
  264. //
  265. // Simply clear the list head.
  266. //
  267. COM_BasedListInit(&lpoaShared->orderListHead);
  268. lpoaShared->totalHeapOrderBytes = 0;
  269. lpoaShared->totalOrderBytes = 0;
  270. lpoaShared->totalAdditionalOrderBytes = 0;
  271. lpoaShared->nextOrder = 0;
  272. DebugExitVOID(ASHost::OAFreeAllOrders);
  273. }
  274.