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.

672 lines
22 KiB

  1. /*++
  2. Copyright (C) Microsoft Corporation, 1993 - 1999
  3. Module Name:
  4. nibble.c
  5. Abstract:
  6. This module contains the code to do nibble mode reads.
  7. Author:
  8. Anthony V. Ercolano 1-Aug-1992
  9. Norbert P. Kusters 22-Oct-1993
  10. Environment:
  11. Kernel mode
  12. Revision History :
  13. --*/
  14. #include "pch.h"
  15. BOOLEAN
  16. ParIsNibbleSupported(
  17. IN PPDO_EXTENSION Pdx
  18. );
  19. BOOLEAN
  20. ParIsChannelizedNibbleSupported(
  21. IN PPDO_EXTENSION Pdx
  22. );
  23. NTSTATUS
  24. ParEnterNibbleMode(
  25. IN PPDO_EXTENSION Pdx,
  26. IN BOOLEAN DeviceIdRequest
  27. );
  28. NTSTATUS
  29. ParEnterChannelizedNibbleMode(
  30. IN PPDO_EXTENSION Pdx,
  31. IN BOOLEAN DeviceIdRequest
  32. );
  33. VOID
  34. ParTerminateNibbleMode(
  35. IN PPDO_EXTENSION Pdx
  36. );
  37. NTSTATUS
  38. ParNibbleModeRead(
  39. IN PPDO_EXTENSION Pdx,
  40. IN PVOID Buffer,
  41. IN ULONG BufferSize,
  42. OUT PULONG BytesTransferred
  43. );
  44. BOOLEAN
  45. ParIsNibbleSupported(
  46. IN PPDO_EXTENSION Pdx
  47. )
  48. /*++
  49. Routine Description:
  50. This routine determines whether or not nibble mode is suported
  51. by trying to negotiate when asked.
  52. Arguments:
  53. Pdx - The device extension.
  54. Return Value:
  55. BOOLEAN.
  56. --*/
  57. {
  58. NTSTATUS Status;
  59. if (Pdx->BadProtocolModes & NIBBLE) {
  60. DD((PCE)Pdx,DDT,"ParIsNibbleSupported: BAD PROTOCOL Leaving\n");
  61. return FALSE;
  62. }
  63. if (Pdx->ProtocolModesSupported & NIBBLE) {
  64. DD((PCE)Pdx,DDT,"ParIsNibbleSupported: Already Checked YES Leaving\n");
  65. return TRUE;
  66. }
  67. Status = ParEnterNibbleMode (Pdx, FALSE);
  68. ParTerminateNibbleMode (Pdx);
  69. if (NT_SUCCESS(Status)) {
  70. DD((PCE)Pdx,DDT,"ParIsNibbleSupported: SUCCESS Leaving\n");
  71. Pdx->ProtocolModesSupported |= NIBBLE;
  72. return TRUE;
  73. }
  74. DD((PCE)Pdx,DDT,"ParIsNibbleSupported: UNSUCCESSFUL Leaving\n");
  75. return FALSE;
  76. }
  77. BOOLEAN
  78. ParIsChannelizedNibbleSupported(
  79. IN PPDO_EXTENSION Pdx
  80. )
  81. /*++
  82. Routine Description:
  83. This routine determines whether or not channelized nibble mode is suported (1284.3)
  84. by trying to negotiate when asked.
  85. Arguments:
  86. Pdx - The device extension.
  87. Return Value:
  88. BOOLEAN.
  89. --*/
  90. {
  91. NTSTATUS Status;
  92. if (Pdx->BadProtocolModes & CHANNEL_NIBBLE) {
  93. DD((PCE)Pdx,DDT,"ParIsChannelizedNibbleSupported: BAD PROTOCOL Leaving\n");
  94. return FALSE;
  95. }
  96. if (Pdx->ProtocolModesSupported & CHANNEL_NIBBLE) {
  97. DD((PCE)Pdx,DDT,"ParIsChannelizedNibbleSupported: Already Checked YES Leaving\n");
  98. return TRUE;
  99. }
  100. Status = ParEnterChannelizedNibbleMode (Pdx, FALSE);
  101. ParTerminateNibbleMode (Pdx);
  102. if (NT_SUCCESS(Status)) {
  103. DD((PCE)Pdx,DDT,"ParIsChannelizedNibbleSupported: SUCCESS Leaving\n");
  104. Pdx->ProtocolModesSupported |= CHANNEL_NIBBLE;
  105. return TRUE;
  106. }
  107. DD((PCE)Pdx,DDT,"ParIsChannelizedNibbleSupported: UNSUCCESSFUL Leaving\n");
  108. return FALSE;
  109. }
  110. NTSTATUS
  111. ParEnterNibbleMode(
  112. IN PPDO_EXTENSION Pdx,
  113. IN BOOLEAN DeviceIdRequest
  114. )
  115. /*++
  116. Routine Description:
  117. This routine performs 1284 negotiation with the peripheral to the
  118. nibble mode protocol.
  119. Arguments:
  120. Controller - Supplies the port address.
  121. DeviceIdRequest - Supplies whether or not this is a request for a device
  122. id.
  123. Return Value:
  124. STATUS_SUCCESS - Successful negotiation.
  125. otherwise - Unsuccessful negotiation.
  126. --*/
  127. {
  128. NTSTATUS Status = STATUS_SUCCESS;
  129. DD((PCE)Pdx,DDT,"ParEnterNibbleMode: Start\n");
  130. if ( Pdx->ModeSafety == SAFE_MODE ) {
  131. if (DeviceIdRequest) {
  132. Status = IeeeEnter1284Mode (Pdx, NIBBLE_EXTENSIBILITY | DEVICE_ID_REQ);
  133. } else {
  134. Status = IeeeEnter1284Mode (Pdx, NIBBLE_EXTENSIBILITY);
  135. }
  136. } else {
  137. DD((PCE)Pdx,DDT,"ParEnterNibbleMode: In UNSAFE_MODE.\n");
  138. Pdx->Connected = TRUE;
  139. }
  140. // dvdr
  141. if (NT_SUCCESS(Status)) {
  142. DD((PCE)Pdx,DDT,"ParEnterNibbleMode: IeeeEnter1284Mode returned success\n");
  143. Pdx->CurrentEvent = 6;
  144. P5SetPhase( Pdx, PHASE_NEGOTIATION );
  145. Pdx->IsIeeeTerminateOk = TRUE;
  146. } else {
  147. DD((PCE)Pdx,DDT,"ParEnterNibbleMode: IeeeEnter1284Mode returned unsuccessful\n");
  148. ParTerminateNibbleMode ( Pdx );
  149. P5SetPhase( Pdx, PHASE_UNKNOWN );
  150. Pdx->IsIeeeTerminateOk = FALSE;
  151. }
  152. DD((PCE)Pdx,DDT,"ParEnterNibbleMode: Leaving with Status : %x \n", Status);
  153. return Status;
  154. }
  155. NTSTATUS
  156. ParEnterChannelizedNibbleMode(
  157. IN PPDO_EXTENSION Pdx,
  158. IN BOOLEAN DeviceIdRequest
  159. )
  160. /*++
  161. Routine Description:
  162. This routine performs 1284 negotiation with the peripheral to the
  163. nibble mode protocol.
  164. Arguments:
  165. Controller - Supplies the port address.
  166. DeviceIdRequest - Supplies whether or not this is a request for a device
  167. id.
  168. Return Value:
  169. STATUS_SUCCESS - Successful negotiation.
  170. otherwise - Unsuccessful negotiation.
  171. --*/
  172. {
  173. NTSTATUS Status = STATUS_SUCCESS;
  174. DD((PCE)Pdx,DDT,"ParEnterChannelizedNibbleMode: Start\n");
  175. if ( Pdx->ModeSafety == SAFE_MODE ) {
  176. if (DeviceIdRequest) {
  177. Status = IeeeEnter1284Mode (Pdx, CHANNELIZED_EXTENSIBILITY | DEVICE_ID_REQ);
  178. } else {
  179. Status = IeeeEnter1284Mode (Pdx, CHANNELIZED_EXTENSIBILITY);
  180. }
  181. } else {
  182. DD((PCE)Pdx,DDT,"ParEnterChannelizedNibbleMode: In UNSAFE_MODE.\n");
  183. Pdx->Connected = TRUE;
  184. }
  185. // dvdr
  186. if (NT_SUCCESS(Status)) {
  187. DD((PCE)Pdx,DDT,"ParEnterChannelizedNibbleMode: IeeeEnter1284Mode returned success\n");
  188. Pdx->CurrentEvent = 6;
  189. P5SetPhase( Pdx, PHASE_NEGOTIATION );
  190. Pdx->IsIeeeTerminateOk = TRUE;
  191. } else {
  192. DD((PCE)Pdx,DDT,"ParEnterChannelizedNibbleMode: IeeeEnter1284Mode returned unsuccessful\n");
  193. ParTerminateNibbleMode ( Pdx );
  194. P5SetPhase( Pdx, PHASE_UNKNOWN );
  195. Pdx->IsIeeeTerminateOk = FALSE;
  196. }
  197. DD((PCE)Pdx,DDT,"ParEnterChannelizedNibbleMode: Leaving with Status : %x \n", Status);
  198. return Status;
  199. }
  200. VOID
  201. ParTerminateNibbleMode(
  202. IN PPDO_EXTENSION Pdx
  203. )
  204. /*++
  205. Routine Description:
  206. This routine terminates the interface back to compatibility mode.
  207. Arguments:
  208. Controller - Supplies the parallel port's controller address.
  209. Return Value:
  210. None.
  211. --*/
  212. {
  213. DD((PCE)Pdx,DDT,"ParTerminateNibbleMode: Enter.\n");
  214. if ( Pdx->ModeSafety == SAFE_MODE ) {
  215. IeeeTerminate1284Mode (Pdx);
  216. } else {
  217. DD((PCE)Pdx,DDT,"ParTerminateNibbleMode: In UNSAFE_MODE.\n");
  218. Pdx->Connected = FALSE;
  219. }
  220. DD((PCE)Pdx,DDT,"ParTerminateNibbleMode: Exit.\n");
  221. }
  222. NTSTATUS
  223. ParNibbleModeRead(
  224. IN PPDO_EXTENSION Pdx,
  225. IN PVOID Buffer,
  226. IN ULONG BufferSize,
  227. OUT PULONG BytesTransferred
  228. )
  229. /*++
  230. Routine Description:
  231. This routine performs a 1284 nibble mode read into the given
  232. buffer for no more than 'BufferSize' bytes.
  233. Arguments:
  234. Pdx - Supplies the device extension.
  235. Buffer - Supplies the buffer to read into.
  236. BufferSize - Supplies the number of bytes in the buffer.
  237. BytesTransferred - Returns the number of bytes transferred.
  238. --*/
  239. {
  240. PUCHAR Controller;
  241. PUCHAR wPortDCR;
  242. PUCHAR wPortDSR;
  243. NTSTATUS Status = STATUS_SUCCESS;
  244. PUCHAR p = (PUCHAR)Buffer;
  245. UCHAR dsr, dcr;
  246. UCHAR nibble[2];
  247. ULONG i, j;
  248. Controller = Pdx->Controller;
  249. wPortDCR = Controller + OFFSET_DCR;
  250. wPortDSR = Controller + OFFSET_DSR;
  251. // Read nibbles according to 1284 spec.
  252. DD((PCE)Pdx,DDT,"ParNibbleModeRead - enter\n");
  253. dcr = P5ReadPortUchar(wPortDCR);
  254. switch (Pdx->CurrentPhase) {
  255. case PHASE_NEGOTIATION:
  256. DD((PCE)Pdx,DDT,"ParNibbleModeRead - case PHASE_NEGOTIATION\n");
  257. // Starting in state 6 - where do we go from here?
  258. // To Reverse Idle or Reverse Data Transfer Phase depending if
  259. // data is available.
  260. dsr = P5ReadPortUchar(wPortDSR);
  261. // =============== Periph State 6 ===============8
  262. // PeriphAck/PtrBusy = Don't Care
  263. // PeriphClk/PtrClk = Don't Care (should be high
  264. // and the nego. proc already
  265. // checked this)
  266. // nAckReverse/AckDataReq = Don't Care (should be high)
  267. // XFlag = Don't Care (should be low)
  268. // nPeriphReq/nDataAvail = High/Low (line status determines
  269. // which state we move to)
  270. Pdx->CurrentEvent = 6;
  271. #if (0 == DVRH_USE_NIBBLE_MACROS)
  272. if (dsr & DSR_NOT_DATA_AVAIL)
  273. #else
  274. if (TEST_DSR(dsr, DONT_CARE, DONT_CARE, DONT_CARE, DONT_CARE, ACTIVE ))
  275. #endif
  276. {
  277. // Data is NOT available - go to Reverse Idle
  278. DD((PCE)Pdx,DDT,"ParNibbleModeRead - now in PHASE_REVERSE_IDLE\n");
  279. // Host enters state 7 - officially in Reverse Idle now
  280. // Must stall for at least .5 microseconds before this state.
  281. KeStallExecutionProcessor(1);
  282. /* =============== Host State 7 Nibble Reverse Idle ===============8
  283. DIR = Don't Care
  284. IRQEN = Don't Care
  285. 1284/SelectIn = High
  286. nReverseReq/ (ECP only)= Don't Care
  287. HostAck/HostBusy = Low (signals State 7)
  288. HostClk/nStrobe = High
  289. ============================================================ */
  290. Pdx->CurrentEvent = 7;
  291. #if (0 == DVRH_USE_NIBBLE_MACROS)
  292. dcr |= DCR_NOT_HOST_BUSY;
  293. #else
  294. dcr = UPDATE_DCR(dcr, DONT_CARE, DONT_CARE, ACTIVE, DONT_CARE, INACTIVE, ACTIVE);
  295. #endif
  296. P5WritePortUchar(wPortDCR, dcr);
  297. P5SetPhase( Pdx, PHASE_REVERSE_IDLE );
  298. // FALL THRU TO reverse idle
  299. } else {
  300. // Data is available, go to Reverse Transfer Phase
  301. P5SetPhase( Pdx, PHASE_REVERSE_XFER );
  302. // DO NOT fall thru
  303. goto PhaseReverseXfer; // please save me from my sins!
  304. }
  305. case PHASE_REVERSE_IDLE:
  306. // Check to see if the peripheral has indicated Interrupt Phase and if so,
  307. // get us ready to reverse transfer.
  308. // See if data is available (looking for state 19)
  309. dsr = P5ReadPortUchar(Controller + OFFSET_DSR);
  310. if (!(dsr & DSR_NOT_DATA_AVAIL)) {
  311. dcr = P5ReadPortUchar(wPortDCR);
  312. // =========== Host State 20 Interrupt Phase ===========8
  313. // DIR = Don't Care
  314. // IRQEN = Don't Care
  315. // 1284/SelectIn = High
  316. // nReverseReq/ (ECP only) = Don't Care
  317. // HostAck/HostBusy = High (Signals state 20)
  318. // HostClk/nStrobe = High
  319. //
  320. // Data is available, get us to Reverse Transfer Phase
  321. Pdx->CurrentEvent = 20;
  322. dcr = UPDATE_DCR(dcr, DONT_CARE, DONT_CARE, ACTIVE, DONT_CARE, ACTIVE, ACTIVE);
  323. P5WritePortUchar(wPortDCR, dcr);
  324. // =============== Periph State 21 HBDA ===============8
  325. // PeriphAck/PtrBusy = Don't Care
  326. // PeriphClk/PtrClk = Don't Care (should be high)
  327. // nAckReverse/AckDataReq = low (signals state 21)
  328. // XFlag = Don't Care (should be low)
  329. // nPeriphReq/nDataAvail = Don't Care (should be low)
  330. Pdx->CurrentEvent = 21;
  331. if (CHECK_DSR(Controller,
  332. DONT_CARE, DONT_CARE, INACTIVE,
  333. DONT_CARE, DONT_CARE,
  334. IEEE_MAXTIME_TL)) {
  335. // Got state 21
  336. // Let's jump to Reverse Xfer and get the data
  337. P5SetPhase( Pdx, PHASE_REVERSE_XFER );
  338. goto PhaseReverseXfer;
  339. } else {
  340. // Timeout on state 21
  341. Pdx->IsIeeeTerminateOk = TRUE;
  342. Status = STATUS_IO_DEVICE_ERROR;
  343. P5SetPhase( Pdx, PHASE_UNKNOWN );
  344. DD((PCE)Pdx,DDT,"ParNibbleModeRead - Failed State 21: Controller %x dcr %x\n", Controller, dcr);
  345. // NOTE: Don't ASSERT Here. An Assert here can bite you if you are in
  346. // Nibble Rev and you device is off/offline.
  347. // dvrh 2/25/97
  348. goto NibbleReadExit;
  349. }
  350. } else {
  351. // Data is NOT available - do nothing
  352. // The device doesn't report any data, it still looks like it is
  353. // in ReverseIdle. Just to make sure it hasn't powered off or somehow
  354. // jumped out of Nibble mode, test also for AckDataReq high and XFlag low
  355. // and nDataAvaul high.
  356. Pdx->CurrentEvent = 18;
  357. dsr = P5ReadPortUchar(Controller + OFFSET_DSR);
  358. if(( dsr & DSR_NIBBLE_VALIDATION )== DSR_NIBBLE_TEST_RESULT ) {
  359. P5SetPhase( Pdx, PHASE_REVERSE_IDLE );
  360. } else {
  361. #if DVRH_BUS_RESET_ON_ERROR
  362. BusReset(wPortDCR); // Pass in the dcr address
  363. #endif
  364. // Appears we failed state 19.
  365. Pdx->IsIeeeTerminateOk = TRUE;
  366. Status = STATUS_IO_DEVICE_ERROR;
  367. P5SetPhase( Pdx, PHASE_UNKNOWN );
  368. DD((PCE)Pdx,DDT,"ParNibbleModeRead - Failed State 19: Controller %x dcr %x\n", Controller, dcr);
  369. }
  370. goto NibbleReadExit;
  371. }
  372. PhaseReverseXfer:
  373. case PHASE_REVERSE_XFER:
  374. DD((PCE)Pdx,DDT,"ParNibbleModeRead - case PHASE_REVERSE_IDLE\n");
  375. for (i = 0; i < BufferSize; i++) {
  376. for (j = 0; j < 2; j++) {
  377. // Host enters state 7 or 12 depending if nibble 1 or 2
  378. // StoreControl (Controller, HDReady);
  379. dcr |= DCR_NOT_HOST_BUSY;
  380. P5WritePortUchar(wPortDCR, dcr);
  381. // =============== Periph State 9 ===============8
  382. // PeriphAck/PtrBusy = Don't Care (Bit 3 of Nibble)
  383. // PeriphClk/PtrClk = low (signals state 9)
  384. // nAckReverse/AckDataReq = Don't Care (Bit 2 of Nibble)
  385. // XFlag = Don't Care (Bit 1 of Nibble)
  386. // nPeriphReq/nDataAvail = Don't Care (Bit 0 of Nibble)
  387. Pdx->CurrentEvent = 9;
  388. if (!CHECK_DSR(Controller,
  389. DONT_CARE, INACTIVE, DONT_CARE,
  390. DONT_CARE, DONT_CARE,
  391. IEEE_MAXTIME_TL)) {
  392. // Time out.
  393. // Bad things happened - timed out on this state,
  394. // Mark Status as bad and let our mgr kill current mode.
  395. Pdx->IsIeeeTerminateOk = FALSE;
  396. Status = STATUS_IO_DEVICE_ERROR;
  397. DD((PCE)Pdx,DDT,"ParNibbleModeRead - Failed State 9: Controller %x dcr %x\n", Controller, dcr);
  398. P5SetPhase( Pdx, PHASE_UNKNOWN );
  399. goto NibbleReadExit;
  400. }
  401. // Read Nibble
  402. nibble[j] = P5ReadPortUchar(wPortDSR);
  403. /* ============== Host State 10 Nibble Read ===============8
  404. DIR = Don't Care
  405. IRQEN = Don't Care
  406. 1284/SelectIn = High
  407. HostAck/HostBusy = High (signals State 10)
  408. HostClk/nStrobe = High
  409. ============================================================ */
  410. Pdx->CurrentEvent = 10;
  411. dcr &= ~DCR_NOT_HOST_BUSY;
  412. P5WritePortUchar(wPortDCR, dcr);
  413. // =============== Periph State 11 ===============8
  414. // PeriphAck/PtrBusy = Don't Care (Bit 3 of Nibble)
  415. // PeriphClk/PtrClk = High (signals state 11)
  416. // nAckReverse/AckDataReq = Don't Care (Bit 2 of Nibble)
  417. // XFlag = Don't Care (Bit 1 of Nibble)
  418. // nPeriphReq/nDataAvail = Don't Care (Bit 0 of Nibble)
  419. Pdx->CurrentEvent = 11;
  420. if (!CHECK_DSR(Controller,
  421. DONT_CARE, ACTIVE, DONT_CARE,
  422. DONT_CARE, DONT_CARE,
  423. IEEE_MAXTIME_TL)) {
  424. // Time out.
  425. // Bad things happened - timed out on this state,
  426. // Mark Status as bad and let our mgr kill current mode.
  427. Status = STATUS_IO_DEVICE_ERROR;
  428. Pdx->IsIeeeTerminateOk = FALSE;
  429. DD((PCE)Pdx,DDT,"ParNibbleModeRead - Failed State 11: Controller %x dcr %x\n", Controller, dcr);
  430. P5SetPhase( Pdx, PHASE_UNKNOWN );
  431. goto NibbleReadExit;
  432. }
  433. }
  434. // Read two nibbles - make them into one byte.
  435. p[i] = (((nibble[0]&0x38)>>3)&0x07) | ((nibble[0]&0x80) ? 0x00 : 0x08);
  436. p[i] |= (((nibble[1]&0x38)<<1)&0x70) | ((nibble[1]&0x80) ? 0x00 : 0x80);
  437. // RMT - put this back in if needed - DD((PCE)Pdx,DDT,"ParNibbleModeRead:%x:%c\n", p[i], p[i]);
  438. // At this point, we've either received the number of bytes we
  439. // were looking for, or the peripheral has no more data to
  440. // send, or there was an error of some sort (of course, in the
  441. // error case we shouldn't get to this comment). Set the
  442. // phase to indicate reverse idle if no data available or
  443. // reverse data transfer if there's some waiting for us
  444. // to get next time.
  445. dsr = P5ReadPortUchar(wPortDSR);
  446. if (dsr & DSR_NOT_DATA_AVAIL) {
  447. // Data is NOT available - go to Reverse Idle
  448. // Really we are going to HBDNA, but if we set
  449. // current phase to reverse idle, the next time
  450. // we get into this function all we have to do
  451. // is set hostbusy low to indicate idle and
  452. // we have infinite time to do that.
  453. // Break out of the loop so we don't try to read
  454. // data that isn't there.
  455. // NOTE - this is a successful case even if we
  456. // didn't read all that the caller requested
  457. P5SetPhase( Pdx, PHASE_REVERSE_IDLE );
  458. i++; // account for this last byte transferred
  459. break;
  460. } else {
  461. // Data is available, go to (remain in ) Reverse Transfer Phase
  462. P5SetPhase( Pdx, PHASE_REVERSE_XFER );
  463. }
  464. } // end for i loop
  465. *BytesTransferred = i;
  466. // DON'T FALL THRU THIS ONE
  467. break;
  468. default:
  469. // I'm gonna mark this as false. There is not a correct answer here.
  470. // The peripheral and the host are out of sync. I'm gonna reset myself
  471. // and the peripheral.
  472. Pdx->IsIeeeTerminateOk = FALSE;
  473. Status = STATUS_IO_DEVICE_ERROR;
  474. P5SetPhase( Pdx, PHASE_UNKNOWN );
  475. DD((PCE)Pdx,DDT,"ParNibbleModeRead - Failed State 9: Unknown Phase. Controller %x dcr %x\n", Controller, dcr);
  476. DD((PCE)Pdx,DDT, "ParNibbleModeRead: You're hosed man.\n" );
  477. DD((PCE)Pdx,DDT, "ParNibbleModeRead: If you are here, you've got a bug somewhere else.\n" );
  478. DD((PCE)Pdx,DDT, "ParNibbleModeRead: Go fix it!\n" );
  479. goto NibbleReadExit;
  480. break;
  481. } // end switch
  482. NibbleReadExit:
  483. if( Pdx->CurrentPhase == PHASE_REVERSE_IDLE ) {
  484. // Host enters state 7 - officially in Reverse Idle now
  485. DD((PCE)Pdx,DDT,"ParNibbleModeRead - PHASE_REVERSE_IDLE\n");
  486. dcr |= DCR_NOT_HOST_BUSY;
  487. P5WritePortUchar (wPortDCR, dcr);
  488. }
  489. DD((PCE)Pdx,DDT,"ParNibbleModeRead:End [%d] bytes read = %d\n", NT_SUCCESS(Status), *BytesTransferred);
  490. Pdx->log.NibbleReadCount += *BytesTransferred;
  491. #if 1 == DBG_SHOW_BYTES
  492. if( DbgShowBytes ) {
  493. if( NT_SUCCESS( Status ) && (*BytesTransferred > 0) ) {
  494. const ULONG maxBytes = 32;
  495. ULONG i;
  496. PUCHAR bytePtr = (PUCHAR)Buffer;
  497. DbgPrint("n: ");
  498. for( i=0 ; (i < *BytesTransferred) && (i < maxBytes ) ; ++i ) {
  499. DbgPrint("%02x ",*bytePtr++);
  500. }
  501. if( *BytesTransferred > maxBytes ) {
  502. DbgPrint("... ");
  503. }
  504. DbgPrint("zz\n");
  505. }
  506. }
  507. #endif
  508. return Status;
  509. }