Source code of Windows XP (NT5)
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.

1113 lines
27 KiB

  1. /**************************************************************************************************************************
  2. * IRCOMMON.H SigmaTel STIR4200 common USB/IR definitions
  3. **************************************************************************************************************************
  4. * (C) Unpublished Copyright of Sigmatel, Inc. All Rights Reserved.
  5. *
  6. *
  7. * Created: 04/06/2000
  8. * Version 0.9
  9. * Edited: 04/24/2000
  10. * Version 0.91
  11. * Edited: 04/27/2000
  12. * Version 0.92
  13. * Edited: 05/03/2000
  14. * Version 0.93
  15. * Edited: 05/12/2000
  16. * Version 0.94
  17. * Edited: 05/19/2000
  18. * Version 0.95
  19. * Edited: 07/27/2000
  20. * Version 1.01
  21. * Edited: 09/16/2000
  22. * Version 1.03
  23. * Edited: 09/25/2000
  24. * Version 1.10
  25. * Edited: 11/09/2000
  26. * Version 1.12
  27. * Edited: 02/20/2001
  28. * Version 1.15
  29. *
  30. **************************************************************************************************************************/
  31. #ifndef _IRCOM_H
  32. #define _IRCOM_H
  33. #include "stir4200.h"
  34. //
  35. // This is for use by check-for-hang handler and is just a reasonable guess;
  36. // Total # of USBD control errors, read aerrors and write errors;
  37. // Used by check-for-hang handler to decide if we need a reset
  38. //
  39. #define IRUSB_100ns_PER_ms 10000
  40. #define IRUSB_100ns_PER_us 10
  41. #define IRUSB_ms_PER_SEC 1000
  42. #define IRUSB_100ns_PER_SEC ( IRUSB_100ns_PER_ms * IRUSB_ms_PER_SEC )
  43. #define MAX_QUERY_TIME_100ns ( 8 * IRUSB_100ns_PER_SEC ) //8 sec
  44. #define MAX_SET_TIME_100ns MAX_QUERY_TIME_100ns
  45. #define MAX_SEND_TIME_100ns ( 20 * IRUSB_100ns_PER_SEC ) //20 sec
  46. #define MAX_TURNAROUND_usec 10000
  47. #define DEFAULT_TURNAROUND_usec 1000
  48. #define MIN(a,b) (((a) <= (b)) ? (a) : (b))
  49. #define MAX(a,b) (((a) >= (b)) ? (a) : (b))
  50. //
  51. // A receive buffer is either FREE (not holding anything) FULL
  52. // (holding undelivered data) or PENDING (holding data delivered
  53. // asynchronously)
  54. //
  55. typedef enum
  56. {
  57. RCV_STATE_FREE,
  58. RCV_STATE_FULL,
  59. RCV_STATE_PENDING
  60. } RCV_BUFFER_STATE, FIFO_BUFFER_STATE;
  61. //
  62. // Structure to keep track of receive packets and buffers to indicate
  63. // receive data to the protocol.
  64. //
  65. typedef struct
  66. {
  67. PVOID pPacket;
  68. UINT DataLen;
  69. PUCHAR pDataBuf;
  70. PVOID pThisDev;
  71. ULONG fInRcvDpc;
  72. RCV_BUFFER_STATE BufferState;
  73. #if defined(DIAGS)
  74. LIST_ENTRY ListEntry; // This will be used to do the diags queueing
  75. #endif
  76. #if defined(WORKAROUND_MISSING_C1)
  77. BOOLEAN MissingC1Detected;
  78. #endif
  79. } RCV_BUFFER, *PRCV_BUFFER;
  80. //
  81. // Structure to read data from the FIFO
  82. //
  83. typedef struct
  84. {
  85. UINT DataLen;
  86. PUCHAR pDataBuf;
  87. PVOID pThisDev;
  88. PVOID pIrp;
  89. FIFO_BUFFER_STATE BufferState;
  90. } FIFO_BUFFER, *PFIFO_BUFFER;
  91. //
  92. // All different sizes for data
  93. //
  94. #define IRDA_ADDRESS_FIELD_SIZE 1
  95. #define IRDA_CONTROL_FIELD_SIZE 1
  96. #define IRDA_A_C_TOTAL_SIZE ( IRDA_ADDRESS_FIELD_SIZE + IRDA_CONTROL_FIELD_SIZE )
  97. #define USB_IRDA_TOTAL_NON_DATA_SIZE ( IRDA_ADDRESS_FIELD_SIZE + IRDA_CONTROL_FIELD_SIZE )
  98. #define IRDA_MAX_DATAONLY_SIZE 2048
  99. #define MAX_TOTAL_SIZE_WITH_ALL_HEADERS ( IRDA_MAX_DATAONLY_SIZE + USB_IRDA_TOTAL_NON_DATA_SIZE )
  100. #define MAX_NUM_EXTRA_BOFS 48
  101. #define MAX_POSSIBLE_IR_PACKET_SIZE_FOR_DATA(dataLen) ( \
  102. (dataLen) * 2 + (MAX_NUM_EXTRA_BOFS + 1) * \
  103. SLOW_IR_BOF_SIZE + IRDA_ADDRESS_FIELD_SIZE + IRDA_CONTROL_FIELD_SIZE + \
  104. SLOW_IR_FCS_SIZE + SLOW_IR_EOF_SIZE) + sizeof(STIR4200_FRAME_HEADER)
  105. //
  106. // Note that the receive size needs to be incremented to account for
  107. // the way the decoding can use one more byte
  108. //
  109. #define MAX_RCV_DATA_SIZE (MAX_TOTAL_SIZE_WITH_ALL_HEADERS + FAST_IR_FCS_SIZE + 1)
  110. #define MAX_IRDA_DATA_SIZE MAX_POSSIBLE_IR_PACKET_SIZE_FOR_DATA(IRDA_MAX_DATAONLY_SIZE)
  111. //
  112. // Possible speeds
  113. //
  114. typedef enum _BAUD_RATE
  115. {
  116. //
  117. // Slow IR
  118. //
  119. BAUDRATE_2400 = 0,
  120. BAUDRATE_9600,
  121. BAUDRATE_19200,
  122. BAUDRATE_38400,
  123. BAUDRATE_57600,
  124. BAUDRATE_115200,
  125. //
  126. // Medium IR
  127. //
  128. #if !defined(DWORKAROUND_BROKEN_MIR)
  129. BAUDRATE_576000,
  130. BAUDRATE_1152000,
  131. #endif
  132. //
  133. // Fast IR
  134. //
  135. BAUDRATE_4000000,
  136. //
  137. // must be last
  138. //
  139. NUM_BAUDRATES
  140. } BAUD_RATE;
  141. typedef enum _IR_MODE
  142. {
  143. IR_MODE_SIR = 0,
  144. IR_MODE_MIR,
  145. IR_MODE_FIR,
  146. NUM_IR_MODES
  147. } IR_MODE;
  148. //
  149. // Speeds
  150. //
  151. #define SPEED_2400 2400
  152. #define SPEED_9600 9600
  153. #define SPEED_19200 19200
  154. #define SPEED_38400 38400
  155. #define SPEED_57600 57600
  156. #define SPEED_115200 115200
  157. #define SPEED_576000 576000
  158. #define SPEED_1152000 1152000
  159. #define SPEED_4000000 4000000
  160. #define DEFAULT_BAUD_RATE SPEED_9600
  161. #define MAX_SIR_SPEED SPEED_115200
  162. #define MAX_MIR_SPEED SPEED_1152000
  163. //
  164. // Sizes of IrLAP frame fields:
  165. // Beginning Of Frame (BOF)
  166. // End Of Frame (EOF)
  167. // Address
  168. // Control
  169. //
  170. #define SLOW_IR_BOF_TYPE UCHAR
  171. #define SLOW_IR_BOF_SIZE sizeof(SLOW_IR_BOF_TYPE)
  172. #define SLOW_IR_EOF_TYPE UCHAR
  173. #define SLOW_IR_EOF_SIZE sizeof(SLOW_IR_EOF_TYPE)
  174. #define SLOW_IR_FCS_TYPE USHORT
  175. #define SLOW_IR_FCS_SIZE sizeof(SLOW_IR_FCS_TYPE)
  176. #define SLOW_IR_BOF 0xC0
  177. #define SLOW_IR_EOF 0xC1
  178. #define SLOW_IR_ESC 0x7D
  179. #define SLOW_IR_ESC_COMP 0x20
  180. #define SLOW_IR_EXTRA_BOF_TYPE UCHAR
  181. #define SLOW_IR_EXTRA_BOF_SIZE sizeof(SLOW_IR_EXTRA_BOF_TYPE)
  182. #define SLOW_IR_EXTRA_BOF 0xC0
  183. #define MEDIUM_IR_BOF 0x7E
  184. #define MEDIUM_IR_EOF 0x7E
  185. #define MEDIUM_IR_FCS_TYPE USHORT
  186. #define MEDIUM_IR_FCS_SIZE sizeof(MEDIUM_IR_FCS_TYPE)
  187. #define FAST_IR_FCS_TYPE ULONG
  188. #define FAST_IR_FCS_SIZE sizeof(FAST_IR_FCS_TYPE)
  189. #define FAST_IR_EOF_TYPE ULONG
  190. #define FAST_IR_EOF_SIZE sizeof(FAST_IR_EOF_TYPE)
  191. //
  192. // Definition for speed masks
  193. //
  194. #define NDIS_IRDA_SPEED_MASK_2400 0x001 // SLOW IR ...
  195. #define NDIS_IRDA_SPEED_MASK_9600 0x003
  196. #define NDIS_IRDA_SPEED_MASK_19200 0x007
  197. #define NDIS_IRDA_SPEED_MASK_38400 0x00f
  198. #define NDIS_IRDA_SPEED_MASK_57600 0x01f
  199. #define NDIS_IRDA_SPEED_MASK_115200 0x03f
  200. #define NDIS_IRDA_SPEED_MASK_576K 0x07f // MEDIUM IR ...
  201. #define NDIS_IRDA_SPEED_MASK_1152K 0x0ff
  202. #define NDIS_IRDA_SPEED_MASK_4M 0x1ff // FAST IR
  203. #define GOOD_FCS ((USHORT) ~0xf0b8)
  204. #define FIR_GOOD_FCS ((ULONG) ~0xdebb20e3)
  205. typedef struct
  206. {
  207. BAUD_RATE TableIndex;
  208. UINT BitsPerSec;
  209. IR_MODE IrMode;
  210. UINT NdisCode; // bitmask element as used by ndis and in class-specific descriptor
  211. UCHAR Stir4200Divisor;
  212. } BAUDRATE_INFO;
  213. //
  214. // Struct to hold the IR USB dongle's USB Class-Specific Descriptor as per
  215. // "Universal Serial Bus IrDA Bridge Device Definition" doc, section 7.2
  216. // This is the struct returned by USBD as the result of a request with an urb
  217. // of type _URB_CONTROL_VENDOR_OR_CLASS_REQUEST, function URB_FUNCTION_CLASS_DEVICE
  218. //
  219. // Enable 1-byte alignment in the below struct
  220. #pragma pack (push,1)
  221. typedef struct _IRUSB_CLASS_SPECIFIC_DESCRIPTOR
  222. {
  223. BOOLEAN ClassConfigured;
  224. UCHAR bmDataSize; // max bytes allowed in any frame as per IrLAP spec, where:
  225. #define BM_DATA_SIZE_2048 (1 << 5)
  226. #define BM_DATA_SIZE_1024 (1 << 4)
  227. #define BM_DATA_SIZE_512 (1 << 3)
  228. #define BM_DATA_SIZE_256 (1 << 2)
  229. #define BM_DATA_SIZE_128 (1 << 1)
  230. #define BM_DATA_SIZE_64 (1 << 0)
  231. UCHAR bmWindowSize; // max un-acked frames that can be received
  232. // before an ack is sent, where:
  233. #define BM_WINDOW_SIZE_7 (1 << 6)
  234. #define BM_WINDOW_SIZE_6 (1 << 5)
  235. #define BM_WINDOW_SIZE_5 (1 << 4)
  236. #define BM_WINDOW_SIZE_4 (1 << 3)
  237. #define BM_WINDOW_SIZE_3 (1 << 2)
  238. #define BM_WINDOW_SIZE_2 (1 << 1)
  239. #define BM_WINDOW_SIZE_1 (1 << 0)
  240. UCHAR bmMinTurnaroundTime; // min millisecs required for recovery between
  241. // end of last xmission and can receive again, where:
  242. #define BM_TURNAROUND_TIME_0ms (1 << 7) // 0 ms
  243. #define BM_TURNAROUND_TIME_0p01ms (1 << 6) // 0.01 ms
  244. #define BM_TURNAROUND_TIME_0p05ms (1 << 5) // 0.05 ms
  245. #define BM_TURNAROUND_TIME_0p1ms (1 << 4) // 0.1 ms
  246. #define BM_TURNAROUND_TIME_0p5ms (1 << 3) // 0.5 ms
  247. #define BM_TURNAROUND_TIME_1ms (1 << 2) // 1 ms
  248. #define BM_TURNAROUND_TIME_5ms (1 << 1) // 5 ms
  249. #define BM_TURNAROUND_TIME_10ms (1 << 0) // 10 ms
  250. USHORT wBaudRate;
  251. //
  252. // ir speed masks as used both by NDIS and as formatted in USB class-specfic descriptor
  253. //
  254. #define NDIS_IRDA_SPEED_2400 (1 << 0) // SLOW IR ...
  255. #define NDIS_IRDA_SPEED_9600 (1 << 1)
  256. #define NDIS_IRDA_SPEED_19200 (1 << 2)
  257. #define NDIS_IRDA_SPEED_38400 (1 << 3)
  258. #define NDIS_IRDA_SPEED_57600 (1 << 4)
  259. #define NDIS_IRDA_SPEED_115200 (1 << 5)
  260. #define NDIS_IRDA_SPEED_576K (1 << 6) // MEDIUM IR ...
  261. #define NDIS_IRDA_SPEED_1152K (1 << 7)
  262. #define NDIS_IRDA_SPEED_4M (1 << 8) // FAST IR
  263. UCHAR bmExtraBofs; // #BOFS required at 115200; 0 if slow speeds <=115200 not supported
  264. #define BM_EXTRA_BOFS_0 (1 << 7)
  265. #define BM_EXTRA_BOFS_1 (1 << 6)
  266. #define BM_EXTRA_BOFS_2 (1 << 5)
  267. #define BM_EXTRA_BOFS_3 (1 << 4)
  268. #define BM_EXTRA_BOFS_6 (1 << 3)
  269. #define BM_EXTRA_BOFS_12 (1 << 2)
  270. #define BM_EXTRA_BOFS_24 (1 << 1)
  271. #define BM_EXTRA_BOFS_48 (1 << 0)
  272. } IRUSB_CLASS_SPECIFIC_DESCRIPTOR, *PIRUSB_CLASS_SPECIFIC_DESCRIPTOR;
  273. #pragma pack (pop) //disable 1-byte alignment
  274. typedef struct _DONGLE_CAPABILITIES
  275. {
  276. //
  277. // Time (in microseconds) that must transpire between
  278. // a transmit and the next receive.
  279. //
  280. LONG turnAroundTime_usec; // gotten from class-specific descriptor
  281. //
  282. // Max un-acked frames that can be received
  283. // before an ack is sent
  284. //
  285. UINT windowSize; // gotten from class-specific descriptor
  286. //
  287. // #BOFS required at 115200; 0 if slow speeds <=115200 are not supported
  288. //
  289. UINT extraBOFS; // gotten from class-specific descriptor
  290. //
  291. // max bytes allowed in any frame as per IrLAP spec
  292. //
  293. UINT dataSize; // gotten from class-specific descriptor
  294. } DONGLE_CAPABILITIES, *PDONGLE_CAPABILITIES;
  295. //
  296. // Enum of context types for SendPacket
  297. //
  298. typedef enum _CONTEXT_TYPE
  299. {
  300. CONTEXT_NDIS_PACKET,
  301. CONTEXT_SET_SPEED,
  302. CONTEXT_READ_WRITE_REGISTER,
  303. CONTEXT_DIAGS_ENABLE,
  304. CONTEXT_DIAGS_DISABLE,
  305. CONTEXT_DIAGS_READ_REGISTERS,
  306. CONTEXT_DIAGS_WRITE_REGISTER,
  307. CONTEXT_DIAGS_BULK_OUT,
  308. CONTEXT_DIAGS_BULK_IN,
  309. CONTEXT_DIAGS_SEND
  310. } CONTEXT_TYPE;
  311. typedef VOID (*WORK_PROC)(struct _IR_WORK_ITEM *);
  312. typedef struct _IR_WORK_ITEM
  313. {
  314. PVOID pIrDevice;
  315. WORK_PROC Callback;
  316. PUCHAR pInfoBuf;
  317. ULONG InfoBufLen;
  318. ULONG fInUse; // declared as ulong for use with interlockedexchange
  319. } IR_WORK_ITEM, *PIR_WORK_ITEM;
  320. //
  321. // Transceiver type definition
  322. //
  323. typedef enum _TRANSCEIVER_TYPE
  324. {
  325. TRANSCEIVER_4012 = 0,
  326. TRANSCEIVER_4000,
  327. TRANSCEIVER_VISHAY,
  328. TRANSCEIVER_INFINEON
  329. } TRANSCEIVER_TYPE;
  330. //
  331. // Chip revision definition
  332. //
  333. typedef enum _CHIP_REVISION
  334. {
  335. CHIP_REVISION_6 = 5,
  336. CHIP_REVISION_7,
  337. CHIP_REVISION_8
  338. } CHIP_REVISION;
  339. typedef struct _IR_DEVICE
  340. {
  341. //
  342. // Keep track of various device objects.
  343. //
  344. PDEVICE_OBJECT pUsbDevObj; //'Next Device Object'
  345. PDEVICE_OBJECT pPhysDevObj; // Physical Device Object
  346. //
  347. // This is the handle that the NDIS wrapper associates with a connection.
  348. // (The handle that the miniport driver associates with the connection
  349. // is just an index into the devStates array).
  350. //
  351. HANDLE hNdisAdapter;
  352. //
  353. // The dongle interface allows us to check the tranceiver type once
  354. // and then set up the interface to allow us to init, set speed,
  355. // and deinit the dongle.
  356. //
  357. // We also want the dongle capabilities.
  358. //
  359. DONGLE_CAPABILITIES dongleCaps;
  360. //
  361. // Type of transceiver installed
  362. //
  363. TRANSCEIVER_TYPE TransceiverType;
  364. //
  365. // Revision of the installed 4200
  366. //
  367. CHIP_REVISION ChipRevision;
  368. //
  369. // Current speed setting, in bits/sec.
  370. // Note: This is updated when we ACTUALLY change the speed,
  371. // not when we get the request to change speed via
  372. // irusbSetInformation.
  373. //
  374. //
  375. // When speed is changed, we have to clear the send queue before
  376. // setting the new speed on the hardware.
  377. // These vars let us remember to do it.
  378. //
  379. UINT currentSpeed;
  380. //
  381. // Current link speed information. This also will maintain the
  382. // chosen speed if the protocol requests a speed change.
  383. //
  384. BAUDRATE_INFO *linkSpeedInfo;
  385. //
  386. // Maintain statistical debug info.
  387. //
  388. ULONG packetsReceived;
  389. ULONG packetsReceivedDropped;
  390. ULONG packetsReceivedOverflow;
  391. ULONG packetsReceivedChecksum;
  392. ULONG packetsReceivedRunt;
  393. ULONG packetsReceivedNoBuffer;
  394. ULONG packetsSent;
  395. ULONG packetsSentDropped;
  396. ULONG packetsSentRejected;
  397. ULONG packetsSentInvalid;
  398. #if DBG
  399. ULONG packetsHeldByProtocol;
  400. ULONG MaxPacketsHeldByProtocol;
  401. ULONG TotalBytesReceived;
  402. ULONG TotalBytesSent;
  403. ULONG NumYesQueryMediaBusyOids;
  404. ULONG NumNoQueryMediaBusyOids;
  405. ULONG NumSetMediaBusyOids;
  406. ULONG NumMediaBusyIndications;
  407. ULONG NumPacketsSentRequiringTurnaroundTime;
  408. ULONG NumPacketsSentNotRequiringTurnaroundTime;
  409. #endif
  410. //
  411. // used by check hang handler to track Query, Set, and Send times
  412. //
  413. LARGE_INTEGER LastQueryTime;
  414. LARGE_INTEGER LastSetTime;
  415. BOOLEAN fSetpending;
  416. BOOLEAN fQuerypending;
  417. //
  418. // Set when device has been started; use for safe cleanup after failed initialization
  419. //
  420. BOOLEAN fDeviceStarted;
  421. //
  422. // Indicates that we have received an OID_GEN_CURRENT_PACKET_FILTER
  423. // indication from the protocol. We can deliver received packets to the
  424. // protocol.
  425. //
  426. BOOLEAN fGotFilterIndication;
  427. //
  428. // NDIS calls most of the MiniportXxx function with IRQL DISPATCH_LEVEL.
  429. // There are a number of instances where the ir device must send
  430. // requests to the device which may be synchronous and
  431. // we can't block in DISPATCH_LEVEL. Therefore, we set up a thread to deal
  432. // with request which require PASSIVE_LEVEL. An event is used to signal
  433. // the thread that work is required.
  434. //
  435. HANDLE hPassiveThread;
  436. BOOLEAN fKillPassiveLevelThread;
  437. KEVENT EventPassiveThread;
  438. /*
  439. According to W2000 ddk doc:
  440. The IrDA protocol driver sets this OID to zero to request the miniport to
  441. start monitoring for a media busy condition. The IrDA protocol
  442. can then query this OID to determine whether the media is busy.
  443. If the media is not busy, the miniport returns a zero for this
  444. OID when queried. If the media is busy,that is, if the miniport
  445. has detected some traffic since the IrDA protocol driver last
  446. set OID_IRDA_MEDIA_BUSY to zero the miniport returns a non-zero
  447. value for this OID when queried. On detecting the media busy
  448. condition. the miniport must also call NdisMIndicateStatus to
  449. indicate NDIS_STATUS_MEDIA_BUSY. When the media is busy,
  450. the IrDA protocol driver will not send packets to the miniport
  451. for transmission. After the miniport has detected a busy state,
  452. it does not have to monitor for a media busy condition until
  453. the IrDA protocol driver again sets OID_IRDA_MEDIA_BUSY to zero.
  454. According to USB IrDA Bridge Device Definition Doc sec 5.4.1.2:
  455. The bmStatus field indicators shall be set by the Device as follows:
  456. Media_Busy
  457. Media_Busy shall indicate zero (0) if the Device:
  458. . has not received a Check Media Busy class-specific request
  459. . has detected no traffic on the infrared media since receiving a Check Media Busy
  460. . class-specific request
  461. . Has returned a header with Media_Busy set to one (1) since receiving a Check
  462. Media Busy class-specific request.
  463. Media_Busy shall indicate one (1) if the Device has detected traffic on the infrared
  464. media since receiving a Check Media Busy class-specific request. Note that
  465. Media_Busy shall indicate one (1) in exactly one header following receipt of each
  466. Check Media Busy class-specific request.
  467. According to USB IrDA Bridge Device Definition Doc sec 6.2.2:
  468. Check Media Busy
  469. This class-specific request instructs the Device to look for a media busy condition. If infrared
  470. traffic of any kind is detected by this Device, the Device shall set the Media_Busy field in the
  471. bmStatus field in the next Data-In packet header sent to the host. In the case where a Check
  472. Media Busy command has been received, a media busy condition detected, and no IrLAP frame
  473. traffic is ready to transmit to the host, the Device shall set the Media_Busy field and send it in a
  474. Data-In packet with no IrLAP frame following the header.
  475. bmRequestType bRequest wValue wIndex wLength Data
  476. 00100001B 3 Zero Interface Zero [None]
  477. */
  478. ULONG fMediaBusy; // declare as ULONGS for use with InterlockedExchange
  479. ULONG fIndicatedMediaBusy;
  480. //
  481. // The variable fProcessing is used to indicate that the ir device
  482. // object has an active polling thread,
  483. //
  484. // Under normal circumstances fReceiving should always be TRUE.
  485. // However sometimes the processing has to be stopped
  486. // and this variable is used to synchronize
  487. //
  488. ULONG fProcessing;
  489. //
  490. // To be set to true when really receiving packets
  491. //
  492. ULONG fCurrentlyReceiving;
  493. //
  494. // The variables fPendingHalt and fPendingReset allow the send and receive
  495. // completion routines to complete the current pending irp and
  496. // then cleanup and stop sending irps to the USB driver.
  497. //
  498. BOOLEAN fPendingHalt;
  499. BOOLEAN fPendingReset;
  500. ULONG fPendingReadClearStall;
  501. ULONG fPendingWriteClearStall;
  502. //
  503. // This is required when the part gets into a complete USB hang and a reset is required
  504. //
  505. ULONG fPendingClearTotalStall;
  506. //
  507. // We keep an array of receive buffers so that we don't continually
  508. // need to allocate buffers to indicate packets to the protocol.
  509. // Since the protocol can retain ownership of up to eight packets
  510. // and we can be receiving up to WindowSize ( 7 ) packets while the protocol has
  511. // ownership of eight packets, we will allocate 16 packets for
  512. // receiving.
  513. //
  514. #define NUM_RCV_BUFS 16
  515. RCV_BUFFER rcvBufs[NUM_RCV_BUFS];
  516. PRCV_BUFFER pCurrentRecBuf;
  517. FIFO_BUFFER PreReadBuffer;
  518. //
  519. // Can have max of NUM_RCV_BUFS packets pending + one set and one query
  520. //
  521. #define NUM_WORK_ITEMS (NUM_RCV_BUFS+3)
  522. IR_WORK_ITEM WorkItems[NUM_WORK_ITEMS];
  523. //
  524. // Since we can have multiple write irps pending with the USB driver,
  525. // we track the irp contexts for each one so we have all the info we need at each
  526. // invokation of the USB write completion routine. See the IRUSB_CONTEXT definition below
  527. // There are 128 contexts for sending, one for read/write operations, one for setting the speed
  528. // and one for diagnostic operations
  529. //
  530. #define NUM_SEND_CONTEXTS 131
  531. PVOID pSendContexts;
  532. //
  533. // Handles to the NDIS packet pool and NDIS buffer pool
  534. // for allocating the receive buffers.
  535. //
  536. HANDLE hPacketPool;
  537. HANDLE hBufferPool;
  538. BOOLEAN BufferPoolAllocated;
  539. KEVENT EventSyncUrb;
  540. KEVENT EventAsyncUrb;
  541. NTSTATUS StatusControl;
  542. NTSTATUS StatusReadWrite;
  543. NTSTATUS StatusSendReceive;
  544. //
  545. // track pending IRPS; this should be zero at halt time
  546. //
  547. UINT PendingIrpCount;
  548. ULONG NumReads;
  549. ULONG NumWrites;
  550. ULONG NumReadWrites;
  551. //
  552. // various USB errors
  553. //
  554. ULONG NumDataErrors;
  555. ULONG NumReadWriteErrors;
  556. HANDLE BulkInPipeHandle;
  557. HANDLE BulkOutPipeHandle;
  558. HANDLE hPollingThread;
  559. BOOLEAN fKillPollingThread;
  560. //
  561. // The IR USB dongle's USB Class-Specific Descriptor as per
  562. // "Universal Serial Bus IrDA Bridge Device Definition" doc, section 7.2
  563. // This is the struct returned by USBD as the result of a request with an urb
  564. // of type _URB_CONTROL_VENDOR_OR_CLASS_REQUEST, function URB_FUNCTION_CLASS_DEVICE.
  565. // Note this struct is in-line, not a pointer
  566. //
  567. IRUSB_CLASS_SPECIFIC_DESCRIPTOR ClassDesc;
  568. UINT IdVendor; // USB vendor Id read from dongle
  569. //
  570. // We don't define it here because we need to isolate USB stuff so we
  571. // can build things referencing NDIS with the BINARY_COMPATIBLE flag for win9x
  572. //
  573. PUCHAR pUsbInfo;
  574. //
  575. // Optional registry entry for debugging; limit baud rate.
  576. // The mask is set up as per the USB Class-Specific descriptor 'wBaudRate'
  577. // This is 'and'ed with value from Class descriptor to possibly limit baud rate;
  578. // It defaults to 0xffff
  579. //
  580. UINT BaudRateMask;
  581. //
  582. // Necessary to read the registry fields
  583. //
  584. NDIS_HANDLE WrapperConfigurationContext;
  585. //
  586. // IR Tranceiver Model
  587. //
  588. STIR4200_TRANCEIVER StIrTranceiver;
  589. //
  590. // Send buffers (works only if sending is serialied)
  591. //
  592. PUCHAR pBuffer;
  593. UINT BufLen;
  594. PUCHAR pStagingBuffer;
  595. //
  596. // Send FIFO count
  597. //
  598. ULONG SendFifoCount;
  599. //
  600. // Receive adaptive delay
  601. //
  602. ULONG ReceiveAdaptiveDelay;
  603. ULONG ReceiveAdaptiveDelayBoost;
  604. //
  605. // Send URB (works only if sending is serialied)
  606. //
  607. PURB pUrb;
  608. UINT UrbLen;
  609. //
  610. // Receive buffer and positions
  611. //
  612. UCHAR pRawBuf[STIR4200_FIFO_SIZE];
  613. ULONG rawCleanupBytesRead;
  614. PORT_RCV_STATE rcvState;
  615. ULONG readBufPos;
  616. BOOLEAN fReadHoldingReg;
  617. ULONG PreFifoCount;
  618. //
  619. // Send lists and lock
  620. //
  621. LIST_ENTRY SendAvailableQueue;
  622. LIST_ENTRY SendBuiltQueue;
  623. LIST_ENTRY SendPendingQueue;
  624. ULONG SendAvailableCount;
  625. ULONG SendBuiltCount;
  626. ULONG SendPendingCount;
  627. KSPIN_LOCK SendLock;
  628. //
  629. // Read and write register list, shares the other send queues
  630. //
  631. LIST_ENTRY ReadWritePendingQueue;
  632. ULONG ReadWritePendingCount;
  633. //
  634. // Diagnostics
  635. //
  636. #if defined(DIAGS)
  637. ULONG DiagsActive;
  638. ULONG DiagsPendingActivation;
  639. PVOID pIOCTL;
  640. NTSTATUS IOCTLStatus;
  641. NDIS_HANDLE NdisDeviceHandle;
  642. KEVENT EventDiags;
  643. LIST_ENTRY DiagsReceiveQueue;
  644. KSPIN_LOCK DiagsReceiveLock;
  645. #endif
  646. //
  647. // Logging
  648. //
  649. #if defined(RECEIVE_LOGGING)
  650. HANDLE ReceiveFileHandle;
  651. __int64 ReceiveFilePosition;
  652. #endif
  653. #if defined(RECEIVE_ERROR_LOGGING)
  654. HANDLE ReceiveErrorFileHandle;
  655. __int64 ReceiveErrorFilePosition;
  656. #endif
  657. #if defined(SEND_LOGGING)
  658. HANDLE SendFileHandle;
  659. __int64 SendFilePosition;
  660. #endif
  661. #if !defined(WORKAROUND_BROKEN_MIR)
  662. //
  663. // Mir in software
  664. //
  665. UCHAR pRawUnstuffedBuf[STIR4200_FIFO_SIZE];
  666. UCHAR MirIncompleteByte;
  667. ULONG MirIncompleteBitCount;
  668. ULONG MirOneBitCount;
  669. ULONG MirFlagCount;
  670. #endif
  671. //
  672. // Dummy send fix
  673. //
  674. BOOLEAN GearedDown;
  675. //
  676. // temporary Fix!
  677. //
  678. //ULONG SirDpll;
  679. //ULONG FirDpll;
  680. //ULONG SirSensitivity;
  681. //ULONG FirSensitivity;
  682. } IR_DEVICE, *PIR_DEVICE;
  683. //
  684. // We use a pointer to the IR_DEVICE structure as the miniport's device context.
  685. //
  686. #define CONTEXT_TO_DEV(__deviceContext) ((PIR_DEVICE)(__deviceContext))
  687. #define DEV_TO_CONTEXT(__irdev) ((HANDLE)(__irdev))
  688. #define IRUSB_TAG 'RITS'
  689. VOID
  690. MyNdisMSetInformationComplete(
  691. IN PIR_DEVICE pThisDev,
  692. IN NDIS_STATUS Status
  693. );
  694. VOID
  695. MyNdisMQueryInformationComplete(
  696. IN PIR_DEVICE pThisDev,
  697. IN NDIS_STATUS Status
  698. );
  699. USHORT
  700. ComputeFCS16(
  701. IN PUCHAR pData,
  702. UINT DataLen
  703. );
  704. ULONG
  705. ComputeFCS32(
  706. IN PUCHAR pData,
  707. ULONG DataLen
  708. );
  709. BOOLEAN
  710. NdisToFirPacket(
  711. IN PIR_DEVICE pIrDev,
  712. IN PNDIS_PACKET pPacket,
  713. OUT PUCHAR pIrPacketBuf,
  714. ULONG IrPacketBufLen,
  715. IN PUCHAR pContigPacketBuf,
  716. OUT PULONG pIrPacketLen
  717. );
  718. BOOLEAN
  719. NdisToMirPacket(
  720. IN PIR_DEVICE pIrDev,
  721. IN PNDIS_PACKET pPacket,
  722. OUT PUCHAR pIrPacketBuf,
  723. ULONG IrPacketBufLen,
  724. IN PUCHAR pContigPacketBuf,
  725. OUT PULONG pIrPacketLen
  726. );
  727. BOOLEAN
  728. NdisToSirPacket(
  729. IN PIR_DEVICE pIrDev,
  730. IN PNDIS_PACKET pPacket,
  731. OUT PUCHAR pIrPacketBuf,
  732. ULONG IrPacketBufLen,
  733. IN PUCHAR pContigPacketBuf,
  734. OUT PULONG pIrPacketLen
  735. );
  736. BOOLEAN
  737. ReceiveFirStepFSM(
  738. IN OUT PIR_DEVICE pIrDev,
  739. OUT PULONG pBytesProcessed
  740. );
  741. BOOLEAN
  742. ReceiveMirStepFSM(
  743. IN OUT PIR_DEVICE pIrDev,
  744. OUT PULONG pBytesProcessed
  745. );
  746. #if !defined(WORKAROUND_BROKEN_MIR)
  747. BOOLEAN
  748. ReceiveMirUnstuff(
  749. IN OUT PIR_DEVICE pIrDev,
  750. IN PUCHAR pInputBuffer,
  751. ULONG InputBufferSize,
  752. OUT PUCHAR pOutputBuffer,
  753. OUT PULONG pOutputBufferSize
  754. );
  755. #endif
  756. BOOLEAN
  757. ReceiveSirStepFSM(
  758. IN OUT PIR_DEVICE pIrDev,
  759. OUT PULONG pBytesProcessed
  760. );
  761. VOID
  762. ReceiveProcessFifoData(
  763. IN OUT PIR_DEVICE pThisDev
  764. );
  765. VOID
  766. ReceiveResetPointers(
  767. IN OUT PIR_DEVICE pThisDev
  768. );
  769. NTSTATUS
  770. ReceivePreprocessFifo(
  771. IN OUT PIR_DEVICE pThisDev,
  772. OUT PULONG pFifoCount
  773. );
  774. NTSTATUS
  775. ReceiveGetFifoData(
  776. IN OUT PIR_DEVICE pThisDev,
  777. OUT PUCHAR pData,
  778. OUT PULONG pBytesRead,
  779. ULONG BytesToRead
  780. );
  781. VOID
  782. ReceiveProcessReturnPacket(
  783. OUT PIR_DEVICE pThisDev,
  784. OUT PRCV_BUFFER pReceiveBuffer
  785. );
  786. NTSTATUS
  787. ReceivePacketRead(
  788. IN PIR_DEVICE pThisDev,
  789. OUT PFIFO_BUFFER pRecBuf
  790. );
  791. NTSTATUS
  792. ReceiveCompletePacketRead(
  793. IN PDEVICE_OBJECT pUsbDevObj,
  794. IN PIRP pIrp,
  795. IN PVOID Context
  796. );
  797. VOID
  798. IndicateMediaBusy(
  799. IN PIR_DEVICE pThisDev
  800. );
  801. VOID
  802. IrUsb_IncIoCount(
  803. IN OUT PIR_DEVICE pThisDev
  804. );
  805. VOID
  806. IrUsb_DecIoCount(
  807. IN OUT PIR_DEVICE pThisDev
  808. );
  809. NTSTATUS
  810. IrUsb_GetDongleCaps(
  811. IN OUT PIR_DEVICE pThisDev
  812. );
  813. VOID
  814. IrUsb_SetDongleCaps(
  815. IN OUT PIR_DEVICE pThisDev
  816. );
  817. VOID
  818. MyMemFree(
  819. IN PVOID pMem,
  820. IN UINT size
  821. );
  822. PVOID
  823. MyMemAlloc(
  824. UINT size
  825. );
  826. BOOLEAN
  827. AllocUsbInfo(
  828. IN OUT PIR_DEVICE pThisDev
  829. );
  830. VOID
  831. FreeUsbInfo(
  832. IN OUT PIR_DEVICE pThisDev
  833. );
  834. VOID
  835. PollingThread(
  836. IN OUT PVOID Context
  837. );
  838. extern BAUDRATE_INFO supportedBaudRateTable[NUM_BAUDRATES];
  839. VOID
  840. ReceiveDeliverBuffer(
  841. IN OUT PIR_DEVICE pThisDev,
  842. IN PRCV_BUFFER pRecBuf
  843. );
  844. NTSTATUS
  845. InitializeProcessing(
  846. IN OUT PIR_DEVICE pThisDev,
  847. IN BOOLEAN InitPassiveThread
  848. );
  849. NTSTATUS
  850. IrUsb_ResetPipe (
  851. IN PIR_DEVICE pThisDev,
  852. IN HANDLE Pipe
  853. );
  854. BOOLEAN
  855. IrUsb_InitSendStructures(
  856. IN OUT PIR_DEVICE pThisDev
  857. );
  858. VOID
  859. IrUsb_FreeSendStructures(
  860. IN OUT PIR_DEVICE pThisDev
  861. );
  862. NDIS_STATUS
  863. SendPacketPreprocess(
  864. IN OUT PIR_DEVICE pThisDev,
  865. IN PVOID pPacketToSend
  866. );
  867. NDIS_STATUS
  868. SendPreprocessedPacketSend(
  869. IN OUT PIR_DEVICE pThisDev,
  870. IN PVOID pContext
  871. );
  872. NTSTATUS
  873. SendWaitCompletion(
  874. IN OUT PIR_DEVICE pThisDev
  875. );
  876. NTSTATUS
  877. SendCheckForOverflow(
  878. IN OUT PIR_DEVICE pThisDev
  879. );
  880. NTSTATUS
  881. SendCompletePacketSend(
  882. IN PDEVICE_OBJECT pUsbDevObj,
  883. IN PIRP pIrp,
  884. IN PVOID Context
  885. );
  886. PRCV_BUFFER
  887. ReceiveGetBuf(
  888. PIR_DEVICE pThisDev,
  889. OUT PUINT pIndex,
  890. IN RCV_BUFFER_STATE BufferState
  891. );
  892. VOID
  893. PassiveLevelThread(
  894. IN PVOID Context
  895. );
  896. BOOLEAN
  897. ScheduleWorkItem(
  898. IN OUT PIR_DEVICE pThisDev,
  899. WORK_PROC Callback,
  900. IN PVOID pInfoBuf,
  901. ULONG InfoBufLen
  902. );
  903. VOID
  904. FreeWorkItem(
  905. IN OUT PIR_WORK_ITEM pItem
  906. );
  907. VOID
  908. IrUsb_PrepareSetSpeed(
  909. IN OUT PIR_DEVICE pThisDev
  910. );
  911. VOID
  912. ResetPipeCallback (
  913. IN PIR_WORK_ITEM pWorkItem
  914. );
  915. PVOID
  916. AllocXferUrb (
  917. VOID
  918. );
  919. VOID
  920. FreeXferUrb(
  921. IN OUT PVOID pUrb
  922. );
  923. BOOLEAN
  924. IrUsb_CancelPendingReadIo(
  925. IN OUT PIR_DEVICE pThisDev,
  926. BOOLEAN fWaitCancelComplete
  927. );
  928. BOOLEAN
  929. IrUsb_CancelPendingWriteIo(
  930. IN OUT PIR_DEVICE pThisDev
  931. );
  932. BOOLEAN
  933. IrUsb_CancelPendingReadWriteIo(
  934. IN OUT PIR_DEVICE pThisDev
  935. );
  936. #endif // _IRCOM_H