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.

179 lines
3.8 KiB

  1. #include "precomp.h"
  2. #define MAXPORTS 128
  3. struct _ObjLink {
  4. struct _ObjLink * sNext;
  5. PMOXA_DEVICE_EXTENSION extension;
  6. };
  7. typedef struct _ObjLink ObjLink;
  8. static ObjLink openDevice[MAXPORTS];
  9. static ObjLink *pFree;
  10. static ObjLink *pHeader;
  11. static ObjLink *pTailer;
  12. static KTIMER pollTimer;
  13. static KDPC pollDpc;
  14. void MoxaTimeOutProcIsr(
  15. IN PKDPC Dpc,
  16. IN PVOID DeferredContext,
  17. IN PVOID SystemContext1,
  18. IN PVOID SystemContext2
  19. );
  20. static void MoxaResetTimeOutProc(void);
  21. void MoxaInitTimeOutProc()
  22. {
  23. int i;
  24. pHeader = NULL;
  25. pTailer = NULL;
  26. pFree = &openDevice[0];
  27. for ( i=0; i<MAXPORTS; i++ )
  28. openDevice[i].sNext = &openDevice[i + 1];
  29. openDevice[MAXPORTS - 1].sNext = NULL;
  30. KeInitializeDpc(
  31. &pollDpc,
  32. MoxaTimeOutProcIsr,
  33. NULL
  34. );
  35. KeInitializeTimer(&pollTimer);
  36. }
  37. void MoxaStopTimeOutProc()
  38. {
  39. KeRemoveQueueDpc(&pollDpc);
  40. KeCancelTimer(&pollTimer);
  41. }
  42. BOOLEAN MoxaAddTimeOutProc(
  43. PMOXA_DEVICE_EXTENSION extension
  44. )
  45. {
  46. ObjLink *pTmp;
  47. if ( pFree == NULL )
  48. return(FALSE);
  49. pTmp = pFree;
  50. pFree = pFree->sNext;
  51. pTmp->sNext = NULL;
  52. pTmp->extension = extension;
  53. if ( pHeader == NULL )
  54. pHeader = pTmp;
  55. else
  56. pTailer->sNext = pTmp;
  57. pTailer = pTmp;
  58. if ( pHeader == pTailer )
  59. MoxaResetTimeOutProc();
  60. return(TRUE);
  61. }
  62. BOOLEAN MoxaDelTimeOutProc(
  63. PMOXA_DEVICE_EXTENSION extension
  64. )
  65. {
  66. ObjLink *next;
  67. ObjLink *prev;
  68. next = pHeader;
  69. prev = NULL;
  70. while ( next ) {
  71. if ( next->extension == extension )
  72. break;
  73. prev = next;
  74. next = prev->sNext;
  75. }
  76. if ( next == NULL )
  77. return(FALSE);
  78. if ( prev ) {
  79. prev->sNext = next->sNext;
  80. if ( prev->sNext == NULL )
  81. pTailer = prev;
  82. } else {
  83. pHeader = next->sNext;
  84. }
  85. next->sNext = pFree;
  86. pFree = next;
  87. return(TRUE);
  88. }
  89. void MoxaTimeOutProcIsr(
  90. IN PKDPC Dpc,
  91. IN PVOID DeferredContext,
  92. IN PVOID SystemContext1,
  93. IN PVOID SystemContext2
  94. )
  95. {
  96. ObjLink *next;
  97. KIRQL oldIrql;
  98. PMOXA_DEVICE_EXTENSION extension;
  99. if ( (next = pHeader) == NULL )
  100. return;
  101. while ( next ) {
  102. if ((extension = next->extension) == NULL) {
  103. next = next->sNext;
  104. continue;
  105. }
  106. if ((extension->ReadLength > 0) &&
  107. (*(PSHORT)(extension->PortOfs + HostStat) &WakeupRxTrigger) ) {
  108. PUCHAR ofs;
  109. PUSHORT rptr, wptr;
  110. USHORT lenMask, count;
  111. IoAcquireCancelSpinLock(&oldIrql);
  112. ofs = extension->PortOfs;
  113. rptr = (PUSHORT)(ofs + RXrptr);
  114. wptr = (PUSHORT)(ofs + RXwptr);
  115. lenMask = *(PUSHORT)(ofs + RX_mask);
  116. count = (*wptr >= *rptr) ? (*wptr - *rptr)
  117. : (*wptr - *rptr + lenMask + 1);
  118. if (count >= *(PUSHORT)(ofs + Rx_trigger)) {
  119. if (extension->Interrupt) {
  120. KeSynchronizeExecution(
  121. extension->Interrupt,
  122. MoxaIsrGetData,
  123. extension
  124. );
  125. }
  126. else {
  127. MoxaIsrGetData(extension);
  128. }
  129. }
  130. IoReleaseCancelSpinLock(oldIrql);
  131. }
  132. next = next->sNext;
  133. }
  134. MoxaResetTimeOutProc();
  135. }
  136. static void MoxaResetTimeOutProc()
  137. {
  138. LARGE_INTEGER time;
  139. //
  140. // Add time out process routine.
  141. //
  142. time.QuadPart = -1000000; /* 100 msec */
  143. KeSetTimer(
  144. &pollTimer,
  145. time,
  146. &pollDpc
  147. );
  148. }