1 /** @file
2 Header file for AHCI mode of ATA host controller.
3
4 Copyright (c) 2010 - 2015, Intel Corporation. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
9
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12
13 **/
14
15 #include "AtaAtapiPassThru.h"
16
17 /**
18 read a one-byte data from a IDE port.
19
20 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure
21 @param Port The IDE Port number
22
23 @return the one-byte data read from IDE port
24 **/
25 UINT8
26 EFIAPI
IdeReadPortB(IN EFI_PCI_IO_PROTOCOL * PciIo,IN UINT16 Port)27 IdeReadPortB (
28 IN EFI_PCI_IO_PROTOCOL *PciIo,
29 IN UINT16 Port
30 )
31 {
32 UINT8 Data;
33
34 ASSERT (PciIo != NULL);
35
36 Data = 0;
37 //
38 // perform 1-byte data read from register
39 //
40 PciIo->Io.Read (
41 PciIo,
42 EfiPciIoWidthUint8,
43 EFI_PCI_IO_PASS_THROUGH_BAR,
44 (UINT64) Port,
45 1,
46 &Data
47 );
48 return Data;
49 }
50
51 /**
52 write a 1-byte data to a specific IDE port.
53
54 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure
55 @param Port The IDE port to be writen
56 @param Data The data to write to the port
57 **/
58 VOID
59 EFIAPI
IdeWritePortB(IN EFI_PCI_IO_PROTOCOL * PciIo,IN UINT16 Port,IN UINT8 Data)60 IdeWritePortB (
61 IN EFI_PCI_IO_PROTOCOL *PciIo,
62 IN UINT16 Port,
63 IN UINT8 Data
64 )
65 {
66 ASSERT (PciIo != NULL);
67
68 //
69 // perform 1-byte data write to register
70 //
71 PciIo->Io.Write (
72 PciIo,
73 EfiPciIoWidthUint8,
74 EFI_PCI_IO_PASS_THROUGH_BAR,
75 (UINT64) Port,
76 1,
77 &Data
78 );
79 }
80
81 /**
82 write a 1-word data to a specific IDE port.
83
84 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure
85 @param Port The IDE port to be writen
86 @param Data The data to write to the port
87 **/
88 VOID
89 EFIAPI
IdeWritePortW(IN EFI_PCI_IO_PROTOCOL * PciIo,IN UINT16 Port,IN UINT16 Data)90 IdeWritePortW (
91 IN EFI_PCI_IO_PROTOCOL *PciIo,
92 IN UINT16 Port,
93 IN UINT16 Data
94 )
95 {
96 ASSERT (PciIo != NULL);
97
98 //
99 // perform 1-word data write to register
100 //
101 PciIo->Io.Write (
102 PciIo,
103 EfiPciIoWidthUint16,
104 EFI_PCI_IO_PASS_THROUGH_BAR,
105 (UINT64) Port,
106 1,
107 &Data
108 );
109 }
110
111 /**
112 write a 2-word data to a specific IDE port.
113
114 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure
115 @param Port The IDE port to be writen
116 @param Data The data to write to the port
117 **/
118 VOID
119 EFIAPI
IdeWritePortDW(IN EFI_PCI_IO_PROTOCOL * PciIo,IN UINT16 Port,IN UINT32 Data)120 IdeWritePortDW (
121 IN EFI_PCI_IO_PROTOCOL *PciIo,
122 IN UINT16 Port,
123 IN UINT32 Data
124 )
125 {
126 ASSERT (PciIo != NULL);
127
128 //
129 // perform 2-word data write to register
130 //
131 PciIo->Io.Write (
132 PciIo,
133 EfiPciIoWidthUint32,
134 EFI_PCI_IO_PASS_THROUGH_BAR,
135 (UINT64) Port,
136 1,
137 &Data
138 );
139 }
140
141 /**
142 Write multiple words of data to the IDE data port.
143 Call the IO abstraction once to do the complete read,
144 not one word at a time
145
146 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure
147 @param Port IO port to read
148 @param Count No. of UINT16's to read
149 @param Buffer Pointer to the data buffer for read
150
151 **/
152 VOID
153 EFIAPI
IdeWritePortWMultiple(IN EFI_PCI_IO_PROTOCOL * PciIo,IN UINT16 Port,IN UINTN Count,IN VOID * Buffer)154 IdeWritePortWMultiple (
155 IN EFI_PCI_IO_PROTOCOL *PciIo,
156 IN UINT16 Port,
157 IN UINTN Count,
158 IN VOID *Buffer
159 )
160 {
161 ASSERT (PciIo != NULL);
162 ASSERT (Buffer != NULL);
163
164 //
165 // perform UINT16 data write to the FIFO
166 //
167 PciIo->Io.Write (
168 PciIo,
169 EfiPciIoWidthFifoUint16,
170 EFI_PCI_IO_PASS_THROUGH_BAR,
171 (UINT64) Port,
172 Count,
173 (UINT16 *) Buffer
174 );
175
176 }
177
178 /**
179 Reads multiple words of data from the IDE data port.
180 Call the IO abstraction once to do the complete read,
181 not one word at a time
182
183 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure
184 @param Port IO port to read
185 @param Count Number of UINT16's to read
186 @param Buffer Pointer to the data buffer for read
187
188 **/
189 VOID
190 EFIAPI
IdeReadPortWMultiple(IN EFI_PCI_IO_PROTOCOL * PciIo,IN UINT16 Port,IN UINTN Count,IN VOID * Buffer)191 IdeReadPortWMultiple (
192 IN EFI_PCI_IO_PROTOCOL *PciIo,
193 IN UINT16 Port,
194 IN UINTN Count,
195 IN VOID *Buffer
196 )
197 {
198 ASSERT (PciIo != NULL);
199 ASSERT (Buffer != NULL);
200
201 //
202 // Perform UINT16 data read from FIFO
203 //
204 PciIo->Io.Read (
205 PciIo,
206 EfiPciIoWidthFifoUint16,
207 EFI_PCI_IO_PASS_THROUGH_BAR,
208 (UINT64) Port,
209 Count,
210 (UINT16 *) Buffer
211 );
212
213 }
214
215 /**
216 This function is used to analyze the Status Register and print out
217 some debug information and if there is ERR bit set in the Status
218 Register, the Error Register's value is also be parsed and print out.
219
220 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
221 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
222 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
223
224 **/
225 VOID
226 EFIAPI
DumpAllIdeRegisters(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)227 DumpAllIdeRegisters (
228 IN EFI_PCI_IO_PROTOCOL *PciIo,
229 IN EFI_IDE_REGISTERS *IdeRegisters,
230 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
231 )
232 {
233 EFI_ATA_STATUS_BLOCK StatusBlock;
234
235 ASSERT (PciIo != NULL);
236 ASSERT (IdeRegisters != NULL);
237
238 ZeroMem (&StatusBlock, sizeof (EFI_ATA_STATUS_BLOCK));
239
240 StatusBlock.AtaStatus = IdeReadPortB (PciIo, IdeRegisters->CmdOrStatus);
241 StatusBlock.AtaError = IdeReadPortB (PciIo, IdeRegisters->ErrOrFeature);
242 StatusBlock.AtaSectorCount = IdeReadPortB (PciIo, IdeRegisters->SectorCount);
243 StatusBlock.AtaSectorCountExp = IdeReadPortB (PciIo, IdeRegisters->SectorCount);
244 StatusBlock.AtaSectorNumber = IdeReadPortB (PciIo, IdeRegisters->SectorNumber);
245 StatusBlock.AtaSectorNumberExp = IdeReadPortB (PciIo, IdeRegisters->SectorNumber);
246 StatusBlock.AtaCylinderLow = IdeReadPortB (PciIo, IdeRegisters->CylinderLsb);
247 StatusBlock.AtaCylinderLowExp = IdeReadPortB (PciIo, IdeRegisters->CylinderLsb);
248 StatusBlock.AtaCylinderHigh = IdeReadPortB (PciIo, IdeRegisters->CylinderMsb);
249 StatusBlock.AtaCylinderHighExp = IdeReadPortB (PciIo, IdeRegisters->CylinderMsb);
250 StatusBlock.AtaDeviceHead = IdeReadPortB (PciIo, IdeRegisters->Head);
251
252 if (AtaStatusBlock != NULL) {
253 //
254 // Dump the content of all ATA registers.
255 //
256 CopyMem (AtaStatusBlock, &StatusBlock, sizeof (EFI_ATA_STATUS_BLOCK));
257 }
258
259 DEBUG_CODE_BEGIN ();
260 if ((StatusBlock.AtaStatus & ATA_STSREG_DWF) != 0) {
261 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Write Fault\n", StatusBlock.AtaStatus));
262 }
263
264 if ((StatusBlock.AtaStatus & ATA_STSREG_CORR) != 0) {
265 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Corrected Data\n", StatusBlock.AtaStatus));
266 }
267
268 if ((StatusBlock.AtaStatus & ATA_STSREG_ERR) != 0) {
269 if ((StatusBlock.AtaError & ATA_ERRREG_BBK) != 0) {
270 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Bad Block Detected\n", StatusBlock.AtaError));
271 }
272
273 if ((StatusBlock.AtaError & ATA_ERRREG_UNC) != 0) {
274 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Uncorrectable Data\n", StatusBlock.AtaError));
275 }
276
277 if ((StatusBlock.AtaError & ATA_ERRREG_MC) != 0) {
278 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Media Change\n", StatusBlock.AtaError));
279 }
280
281 if ((StatusBlock.AtaError & ATA_ERRREG_ABRT) != 0) {
282 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Abort\n", StatusBlock.AtaError));
283 }
284
285 if ((StatusBlock.AtaError & ATA_ERRREG_TK0NF) != 0) {
286 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Track 0 Not Found\n", StatusBlock.AtaError));
287 }
288
289 if ((StatusBlock.AtaError & ATA_ERRREG_AMNF) != 0) {
290 DEBUG ((EFI_D_ERROR, "CheckRegisterStatus()-- %02x : Error : Address Mark Not Found\n", StatusBlock.AtaError));
291 }
292 }
293 DEBUG_CODE_END ();
294 }
295
296 /**
297 This function is used to analyze the Status Register at the condition that BSY is zero.
298 if there is ERR bit set in the Status Register, then return error.
299
300 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
301 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
302
303 @retval EFI_SUCCESS No err information in the Status Register.
304 @retval EFI_DEVICE_ERROR Any err information in the Status Register.
305
306 **/
307 EFI_STATUS
308 EFIAPI
CheckStatusRegister(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters)309 CheckStatusRegister (
310 IN EFI_PCI_IO_PROTOCOL *PciIo,
311 IN EFI_IDE_REGISTERS *IdeRegisters
312 )
313 {
314 UINT8 StatusRegister;
315
316 ASSERT (PciIo != NULL);
317 ASSERT (IdeRegisters != NULL);
318
319 StatusRegister = IdeReadPortB (PciIo, IdeRegisters->CmdOrStatus);
320
321 if ((StatusRegister & ATA_STSREG_BSY) == 0) {
322 if ((StatusRegister & (ATA_STSREG_ERR | ATA_STSREG_DWF | ATA_STSREG_CORR)) == 0) {
323 return EFI_SUCCESS;
324 } else {
325 return EFI_DEVICE_ERROR;
326 }
327 }
328 return EFI_SUCCESS;
329 }
330
331 /**
332 This function is used to poll for the DRQ bit clear in the Status
333 Register. DRQ is cleared when the device is finished transferring data.
334 So this function is called after data transfer is finished.
335
336 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
337 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
338 @param Timeout The time to complete the command, uses 100ns as a unit.
339
340 @retval EFI_SUCCESS DRQ bit clear within the time out.
341
342 @retval EFI_TIMEOUT DRQ bit not clear within the time out.
343
344 @note
345 Read Status Register will clear interrupt status.
346
347 **/
348 EFI_STATUS
349 EFIAPI
DRQClear(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)350 DRQClear (
351 IN EFI_PCI_IO_PROTOCOL *PciIo,
352 IN EFI_IDE_REGISTERS *IdeRegisters,
353 IN UINT64 Timeout
354 )
355 {
356 UINT64 Delay;
357 UINT8 StatusRegister;
358 BOOLEAN InfiniteWait;
359
360 ASSERT (PciIo != NULL);
361 ASSERT (IdeRegisters != NULL);
362
363 if (Timeout == 0) {
364 InfiniteWait = TRUE;
365 } else {
366 InfiniteWait = FALSE;
367 }
368
369 Delay = DivU64x32(Timeout, 1000) + 1;
370 do {
371 StatusRegister = IdeReadPortB (PciIo, IdeRegisters->CmdOrStatus);
372
373 //
374 // Wait for BSY == 0, then judge if DRQ is clear
375 //
376 if ((StatusRegister & ATA_STSREG_BSY) == 0) {
377 if ((StatusRegister & ATA_STSREG_DRQ) == ATA_STSREG_DRQ) {
378 return EFI_DEVICE_ERROR;
379 } else {
380 return EFI_SUCCESS;
381 }
382 }
383
384 //
385 // Stall for 100 microseconds.
386 //
387 MicroSecondDelay (100);
388
389 Delay--;
390
391 } while (InfiniteWait || (Delay > 0));
392
393 return EFI_TIMEOUT;
394 }
395 /**
396 This function is used to poll for the DRQ bit clear in the Alternate
397 Status Register. DRQ is cleared when the device is finished
398 transferring data. So this function is called after data transfer
399 is finished.
400
401 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
402 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
403 @param Timeout The time to complete the command, uses 100ns as a unit.
404
405 @retval EFI_SUCCESS DRQ bit clear within the time out.
406
407 @retval EFI_TIMEOUT DRQ bit not clear within the time out.
408 @note Read Alternate Status Register will not clear interrupt status.
409
410 **/
411 EFI_STATUS
412 EFIAPI
DRQClear2(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)413 DRQClear2 (
414 IN EFI_PCI_IO_PROTOCOL *PciIo,
415 IN EFI_IDE_REGISTERS *IdeRegisters,
416 IN UINT64 Timeout
417 )
418 {
419 UINT64 Delay;
420 UINT8 AltRegister;
421 BOOLEAN InfiniteWait;
422
423 ASSERT (PciIo != NULL);
424 ASSERT (IdeRegisters != NULL);
425
426 if (Timeout == 0) {
427 InfiniteWait = TRUE;
428 } else {
429 InfiniteWait = FALSE;
430 }
431
432 Delay = DivU64x32(Timeout, 1000) + 1;
433 do {
434 AltRegister = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
435
436 //
437 // Wait for BSY == 0, then judge if DRQ is clear
438 //
439 if ((AltRegister & ATA_STSREG_BSY) == 0) {
440 if ((AltRegister & ATA_STSREG_DRQ) == ATA_STSREG_DRQ) {
441 return EFI_DEVICE_ERROR;
442 } else {
443 return EFI_SUCCESS;
444 }
445 }
446
447 //
448 // Stall for 100 microseconds.
449 //
450 MicroSecondDelay (100);
451
452 Delay--;
453
454 } while (InfiniteWait || (Delay > 0));
455
456 return EFI_TIMEOUT;
457 }
458
459 /**
460 This function is used to poll for the DRQ bit set in the
461 Status Register.
462 DRQ is set when the device is ready to transfer data. So this function
463 is called after the command is sent to the device and before required
464 data is transferred.
465
466 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
467 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
468 @param Timeout The time to complete the command, uses 100ns as a unit.
469
470 @retval EFI_SUCCESS DRQ bit set within the time out.
471 @retval EFI_TIMEOUT DRQ bit not set within the time out.
472 @retval EFI_ABORTED DRQ bit not set caused by the command abort.
473
474 @note Read Status Register will clear interrupt status.
475
476 **/
477 EFI_STATUS
478 EFIAPI
DRQReady(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)479 DRQReady (
480 IN EFI_PCI_IO_PROTOCOL *PciIo,
481 IN EFI_IDE_REGISTERS *IdeRegisters,
482 IN UINT64 Timeout
483 )
484 {
485 UINT64 Delay;
486 UINT8 StatusRegister;
487 UINT8 ErrorRegister;
488 BOOLEAN InfiniteWait;
489
490 ASSERT (PciIo != NULL);
491 ASSERT (IdeRegisters != NULL);
492
493 if (Timeout == 0) {
494 InfiniteWait = TRUE;
495 } else {
496 InfiniteWait = FALSE;
497 }
498
499 Delay = DivU64x32(Timeout, 1000) + 1;
500 do {
501 //
502 // Read Status Register will clear interrupt
503 //
504 StatusRegister = IdeReadPortB (PciIo, IdeRegisters->CmdOrStatus);
505
506 //
507 // Wait for BSY == 0, then judge if DRQ is clear or ERR is set
508 //
509 if ((StatusRegister & ATA_STSREG_BSY) == 0) {
510 if ((StatusRegister & ATA_STSREG_ERR) == ATA_STSREG_ERR) {
511 ErrorRegister = IdeReadPortB (PciIo, IdeRegisters->ErrOrFeature);
512
513 if ((ErrorRegister & ATA_ERRREG_ABRT) == ATA_ERRREG_ABRT) {
514 return EFI_ABORTED;
515 }
516 return EFI_DEVICE_ERROR;
517 }
518
519 if ((StatusRegister & ATA_STSREG_DRQ) == ATA_STSREG_DRQ) {
520 return EFI_SUCCESS;
521 } else {
522 return EFI_NOT_READY;
523 }
524 }
525
526 //
527 // Stall for 100 microseconds.
528 //
529 MicroSecondDelay (100);
530
531 Delay--;
532 } while (InfiniteWait || (Delay > 0));
533
534 return EFI_TIMEOUT;
535 }
536 /**
537 This function is used to poll for the DRQ bit set in the Alternate Status Register.
538 DRQ is set when the device is ready to transfer data. So this function is called after
539 the command is sent to the device and before required data is transferred.
540
541 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
542 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
543 @param Timeout The time to complete the command, uses 100ns as a unit.
544
545 @retval EFI_SUCCESS DRQ bit set within the time out.
546 @retval EFI_TIMEOUT DRQ bit not set within the time out.
547 @retval EFI_ABORTED DRQ bit not set caused by the command abort.
548 @note Read Alternate Status Register will not clear interrupt status.
549
550 **/
551 EFI_STATUS
552 EFIAPI
DRQReady2(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)553 DRQReady2 (
554 IN EFI_PCI_IO_PROTOCOL *PciIo,
555 IN EFI_IDE_REGISTERS *IdeRegisters,
556 IN UINT64 Timeout
557 )
558 {
559 UINT64 Delay;
560 UINT8 AltRegister;
561 UINT8 ErrorRegister;
562 BOOLEAN InfiniteWait;
563
564 ASSERT (PciIo != NULL);
565 ASSERT (IdeRegisters != NULL);
566
567 if (Timeout == 0) {
568 InfiniteWait = TRUE;
569 } else {
570 InfiniteWait = FALSE;
571 }
572
573 Delay = DivU64x32(Timeout, 1000) + 1;
574
575 do {
576 //
577 // Read Alternate Status Register will not clear interrupt status
578 //
579 AltRegister = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
580 //
581 // Wait for BSY == 0, then judge if DRQ is clear or ERR is set
582 //
583 if ((AltRegister & ATA_STSREG_BSY) == 0) {
584 if ((AltRegister & ATA_STSREG_ERR) == ATA_STSREG_ERR) {
585 ErrorRegister = IdeReadPortB (PciIo, IdeRegisters->ErrOrFeature);
586
587 if ((ErrorRegister & ATA_ERRREG_ABRT) == ATA_ERRREG_ABRT) {
588 return EFI_ABORTED;
589 }
590 return EFI_DEVICE_ERROR;
591 }
592
593 if ((AltRegister & ATA_STSREG_DRQ) == ATA_STSREG_DRQ) {
594 return EFI_SUCCESS;
595 } else {
596 return EFI_NOT_READY;
597 }
598 }
599
600 //
601 // Stall for 100 microseconds.
602 //
603 MicroSecondDelay (100);
604
605 Delay--;
606 } while (InfiniteWait || (Delay > 0));
607
608 return EFI_TIMEOUT;
609 }
610
611 /**
612 This function is used to poll for the DRDY bit set in the Status Register. DRDY
613 bit is set when the device is ready to accept command. Most ATA commands must be
614 sent after DRDY set except the ATAPI Packet Command.
615
616 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
617 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
618 @param Timeout The time to complete the command, uses 100ns as a unit.
619
620 @retval EFI_SUCCESS DRDY bit set within the time out.
621 @retval EFI_TIMEOUT DRDY bit not set within the time out.
622
623 @note Read Status Register will clear interrupt status.
624 **/
625 EFI_STATUS
626 EFIAPI
DRDYReady(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)627 DRDYReady (
628 IN EFI_PCI_IO_PROTOCOL *PciIo,
629 IN EFI_IDE_REGISTERS *IdeRegisters,
630 IN UINT64 Timeout
631 )
632 {
633 UINT64 Delay;
634 UINT8 StatusRegister;
635 UINT8 ErrorRegister;
636 BOOLEAN InfiniteWait;
637
638 ASSERT (PciIo != NULL);
639 ASSERT (IdeRegisters != NULL);
640
641 if (Timeout == 0) {
642 InfiniteWait = TRUE;
643 } else {
644 InfiniteWait = FALSE;
645 }
646
647 Delay = DivU64x32(Timeout, 1000) + 1;
648 do {
649 StatusRegister = IdeReadPortB (PciIo, IdeRegisters->CmdOrStatus);
650 //
651 // Wait for BSY == 0, then judge if DRDY is set or ERR is set
652 //
653 if ((StatusRegister & ATA_STSREG_BSY) == 0) {
654 if ((StatusRegister & ATA_STSREG_ERR) == ATA_STSREG_ERR) {
655 ErrorRegister = IdeReadPortB (PciIo, IdeRegisters->ErrOrFeature);
656
657 if ((ErrorRegister & ATA_ERRREG_ABRT) == ATA_ERRREG_ABRT) {
658 return EFI_ABORTED;
659 }
660 return EFI_DEVICE_ERROR;
661 }
662
663 if ((StatusRegister & ATA_STSREG_DRDY) == ATA_STSREG_DRDY) {
664 return EFI_SUCCESS;
665 } else {
666 return EFI_DEVICE_ERROR;
667 }
668 }
669
670 //
671 // Stall for 100 microseconds.
672 //
673 MicroSecondDelay (100);
674
675 Delay--;
676 } while (InfiniteWait || (Delay > 0));
677
678 return EFI_TIMEOUT;
679 }
680
681 /**
682 This function is used to poll for the DRDY bit set in the Alternate Status Register.
683 DRDY bit is set when the device is ready to accept command. Most ATA commands must
684 be sent after DRDY set except the ATAPI Packet Command.
685
686 @param PciIo A pointer to EFI_PCI_IO_PROTOCOL data structure.
687 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
688 @param Timeout The time to complete the command, uses 100ns as a unit.
689
690 @retval EFI_SUCCESS DRDY bit set within the time out.
691 @retval EFI_TIMEOUT DRDY bit not set within the time out.
692
693 @note Read Alternate Status Register will clear interrupt status.
694
695 **/
696 EFI_STATUS
697 EFIAPI
DRDYReady2(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)698 DRDYReady2 (
699 IN EFI_PCI_IO_PROTOCOL *PciIo,
700 IN EFI_IDE_REGISTERS *IdeRegisters,
701 IN UINT64 Timeout
702 )
703 {
704 UINT64 Delay;
705 UINT8 AltRegister;
706 UINT8 ErrorRegister;
707 BOOLEAN InfiniteWait;
708
709 ASSERT (PciIo != NULL);
710 ASSERT (IdeRegisters != NULL);
711
712 if (Timeout == 0) {
713 InfiniteWait = TRUE;
714 } else {
715 InfiniteWait = FALSE;
716 }
717
718 Delay = DivU64x32(Timeout, 1000) + 1;
719 do {
720 AltRegister = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
721 //
722 // Wait for BSY == 0, then judge if DRDY is set or ERR is set
723 //
724 if ((AltRegister & ATA_STSREG_BSY) == 0) {
725 if ((AltRegister & ATA_STSREG_ERR) == ATA_STSREG_ERR) {
726 ErrorRegister = IdeReadPortB (PciIo, IdeRegisters->ErrOrFeature);
727
728 if ((ErrorRegister & ATA_ERRREG_ABRT) == ATA_ERRREG_ABRT) {
729 return EFI_ABORTED;
730 }
731 return EFI_DEVICE_ERROR;
732 }
733
734 if ((AltRegister & ATA_STSREG_DRDY) == ATA_STSREG_DRDY) {
735 return EFI_SUCCESS;
736 } else {
737 return EFI_DEVICE_ERROR;
738 }
739 }
740
741 //
742 // Stall for 100 microseconds.
743 //
744 MicroSecondDelay (100);
745
746 Delay--;
747 } while (InfiniteWait || (Delay > 0));
748
749 return EFI_TIMEOUT;
750 }
751
752 /**
753 This function is used to poll for the BSY bit clear in the Status Register. BSY
754 is clear when the device is not busy. Every command must be sent after device is not busy.
755
756 @param PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
757 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
758 @param Timeout The time to complete the command, uses 100ns as a unit.
759
760 @retval EFI_SUCCESS BSY bit clear within the time out.
761 @retval EFI_TIMEOUT BSY bit not clear within the time out.
762
763 @note Read Status Register will clear interrupt status.
764 **/
765 EFI_STATUS
766 EFIAPI
WaitForBSYClear(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)767 WaitForBSYClear (
768 IN EFI_PCI_IO_PROTOCOL *PciIo,
769 IN EFI_IDE_REGISTERS *IdeRegisters,
770 IN UINT64 Timeout
771 )
772 {
773 UINT64 Delay;
774 UINT8 StatusRegister;
775 BOOLEAN InfiniteWait;
776
777 ASSERT (PciIo != NULL);
778 ASSERT (IdeRegisters != NULL);
779
780 if (Timeout == 0) {
781 InfiniteWait = TRUE;
782 } else {
783 InfiniteWait = FALSE;
784 }
785
786 Delay = DivU64x32(Timeout, 1000) + 1;
787 do {
788 StatusRegister = IdeReadPortB (PciIo, IdeRegisters->CmdOrStatus);
789
790 if ((StatusRegister & ATA_STSREG_BSY) == 0x00) {
791 return EFI_SUCCESS;
792 }
793
794 //
795 // Stall for 100 microseconds.
796 //
797 MicroSecondDelay (100);
798
799 Delay--;
800
801 } while (InfiniteWait || (Delay > 0));
802
803 return EFI_TIMEOUT;
804 }
805
806 /**
807 This function is used to poll for the BSY bit clear in the Status Register. BSY
808 is clear when the device is not busy. Every command must be sent after device is not busy.
809
810 @param PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
811 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
812 @param Timeout The time to complete the command, uses 100ns as a unit.
813
814 @retval EFI_SUCCESS BSY bit clear within the time out.
815 @retval EFI_TIMEOUT BSY bit not clear within the time out.
816
817 @note Read Status Register will clear interrupt status.
818 **/
819 EFI_STATUS
820 EFIAPI
WaitForBSYClear2(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)821 WaitForBSYClear2 (
822 IN EFI_PCI_IO_PROTOCOL *PciIo,
823 IN EFI_IDE_REGISTERS *IdeRegisters,
824 IN UINT64 Timeout
825 )
826 {
827 UINT64 Delay;
828 UINT8 AltStatusRegister;
829 BOOLEAN InfiniteWait;
830
831 ASSERT (PciIo != NULL);
832 ASSERT (IdeRegisters != NULL);
833
834 if (Timeout == 0) {
835 InfiniteWait = TRUE;
836 } else {
837 InfiniteWait = FALSE;
838 }
839
840 Delay = DivU64x32(Timeout, 1000) + 1;
841 do {
842 AltStatusRegister = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
843
844 if ((AltStatusRegister & ATA_STSREG_BSY) == 0x00) {
845 return EFI_SUCCESS;
846 }
847
848 //
849 // Stall for 100 microseconds.
850 //
851 MicroSecondDelay (100);
852
853 Delay--;
854
855 } while (InfiniteWait || (Delay > 0));
856
857 return EFI_TIMEOUT;
858 }
859
860 /**
861 Get IDE i/o port registers' base addresses by mode.
862
863 In 'Compatibility' mode, use fixed addresses.
864 In Native-PCI mode, get base addresses from BARs in the PCI IDE controller's
865 Configuration Space.
866
867 The steps to get IDE i/o port registers' base addresses for each channel
868 as follows:
869
870 1. Examine the Programming Interface byte of the Class Code fields in PCI IDE
871 controller's Configuration Space to determine the operating mode.
872
873 2. a) In 'Compatibility' mode, use fixed addresses shown in the Table 1 below.
874 ___________________________________________
875 | | Command Block | Control Block |
876 | Channel | Registers | Registers |
877 |___________|_______________|_______________|
878 | Primary | 1F0h - 1F7h | 3F6h - 3F7h |
879 |___________|_______________|_______________|
880 | Secondary | 170h - 177h | 376h - 377h |
881 |___________|_______________|_______________|
882
883 Table 1. Compatibility resource mappings
884
885 b) In Native-PCI mode, IDE registers are mapped into IO space using the BARs
886 in IDE controller's PCI Configuration Space, shown in the Table 2 below.
887 ___________________________________________________
888 | | Command Block | Control Block |
889 | Channel | Registers | Registers |
890 |___________|___________________|___________________|
891 | Primary | BAR at offset 0x10| BAR at offset 0x14|
892 |___________|___________________|___________________|
893 | Secondary | BAR at offset 0x18| BAR at offset 0x1C|
894 |___________|___________________|___________________|
895
896 Table 2. BARs for Register Mapping
897
898 @param[in] PciIo Pointer to the EFI_PCI_IO_PROTOCOL instance
899 @param[in, out] IdeRegisters Pointer to EFI_IDE_REGISTERS which is used to
900 store the IDE i/o port registers' base addresses
901
902 @retval EFI_UNSUPPORTED Return this value when the BARs is not IO type
903 @retval EFI_SUCCESS Get the Base address successfully
904 @retval Other Read the pci configureation data error
905
906 **/
907 EFI_STATUS
908 EFIAPI
GetIdeRegisterIoAddr(IN EFI_PCI_IO_PROTOCOL * PciIo,IN OUT EFI_IDE_REGISTERS * IdeRegisters)909 GetIdeRegisterIoAddr (
910 IN EFI_PCI_IO_PROTOCOL *PciIo,
911 IN OUT EFI_IDE_REGISTERS *IdeRegisters
912 )
913 {
914 EFI_STATUS Status;
915 PCI_TYPE00 PciData;
916 UINT16 CommandBlockBaseAddr;
917 UINT16 ControlBlockBaseAddr;
918 UINT16 BusMasterBaseAddr;
919
920 if ((PciIo == NULL) || (IdeRegisters == NULL)) {
921 return EFI_INVALID_PARAMETER;
922 }
923
924 Status = PciIo->Pci.Read (
925 PciIo,
926 EfiPciIoWidthUint8,
927 0,
928 sizeof (PciData),
929 &PciData
930 );
931
932 if (EFI_ERROR (Status)) {
933 return Status;
934 }
935
936 BusMasterBaseAddr = (UINT16) ((PciData.Device.Bar[4] & 0x0000fff0));
937
938 if ((PciData.Hdr.ClassCode[0] & IDE_PRIMARY_OPERATING_MODE) == 0) {
939 CommandBlockBaseAddr = 0x1f0;
940 ControlBlockBaseAddr = 0x3f6;
941 } else {
942 //
943 // The BARs should be of IO type
944 //
945 if ((PciData.Device.Bar[0] & BIT0) == 0 ||
946 (PciData.Device.Bar[1] & BIT0) == 0) {
947 return EFI_UNSUPPORTED;
948 }
949
950 CommandBlockBaseAddr = (UINT16) (PciData.Device.Bar[0] & 0x0000fff8);
951 ControlBlockBaseAddr = (UINT16) ((PciData.Device.Bar[1] & 0x0000fffc) + 2);
952 }
953
954 //
955 // Calculate IDE primary channel I/O register base address.
956 //
957 IdeRegisters[EfiIdePrimary].Data = CommandBlockBaseAddr;
958 IdeRegisters[EfiIdePrimary].ErrOrFeature = (UINT16) (CommandBlockBaseAddr + 0x01);
959 IdeRegisters[EfiIdePrimary].SectorCount = (UINT16) (CommandBlockBaseAddr + 0x02);
960 IdeRegisters[EfiIdePrimary].SectorNumber = (UINT16) (CommandBlockBaseAddr + 0x03);
961 IdeRegisters[EfiIdePrimary].CylinderLsb = (UINT16) (CommandBlockBaseAddr + 0x04);
962 IdeRegisters[EfiIdePrimary].CylinderMsb = (UINT16) (CommandBlockBaseAddr + 0x05);
963 IdeRegisters[EfiIdePrimary].Head = (UINT16) (CommandBlockBaseAddr + 0x06);
964 IdeRegisters[EfiIdePrimary].CmdOrStatus = (UINT16) (CommandBlockBaseAddr + 0x07);
965 IdeRegisters[EfiIdePrimary].AltOrDev = ControlBlockBaseAddr;
966 IdeRegisters[EfiIdePrimary].BusMasterBaseAddr = BusMasterBaseAddr;
967
968 if ((PciData.Hdr.ClassCode[0] & IDE_SECONDARY_OPERATING_MODE) == 0) {
969 CommandBlockBaseAddr = 0x170;
970 ControlBlockBaseAddr = 0x376;
971 } else {
972 //
973 // The BARs should be of IO type
974 //
975 if ((PciData.Device.Bar[2] & BIT0) == 0 ||
976 (PciData.Device.Bar[3] & BIT0) == 0) {
977 return EFI_UNSUPPORTED;
978 }
979
980 CommandBlockBaseAddr = (UINT16) (PciData.Device.Bar[2] & 0x0000fff8);
981 ControlBlockBaseAddr = (UINT16) ((PciData.Device.Bar[3] & 0x0000fffc) + 2);
982 }
983
984 //
985 // Calculate IDE secondary channel I/O register base address.
986 //
987 IdeRegisters[EfiIdeSecondary].Data = CommandBlockBaseAddr;
988 IdeRegisters[EfiIdeSecondary].ErrOrFeature = (UINT16) (CommandBlockBaseAddr + 0x01);
989 IdeRegisters[EfiIdeSecondary].SectorCount = (UINT16) (CommandBlockBaseAddr + 0x02);
990 IdeRegisters[EfiIdeSecondary].SectorNumber = (UINT16) (CommandBlockBaseAddr + 0x03);
991 IdeRegisters[EfiIdeSecondary].CylinderLsb = (UINT16) (CommandBlockBaseAddr + 0x04);
992 IdeRegisters[EfiIdeSecondary].CylinderMsb = (UINT16) (CommandBlockBaseAddr + 0x05);
993 IdeRegisters[EfiIdeSecondary].Head = (UINT16) (CommandBlockBaseAddr + 0x06);
994 IdeRegisters[EfiIdeSecondary].CmdOrStatus = (UINT16) (CommandBlockBaseAddr + 0x07);
995 IdeRegisters[EfiIdeSecondary].AltOrDev = ControlBlockBaseAddr;
996 IdeRegisters[EfiIdeSecondary].BusMasterBaseAddr = (UINT16) (BusMasterBaseAddr + 0x8);
997
998 return EFI_SUCCESS;
999 }
1000
1001 /**
1002 This function is used to implement the Soft Reset on the specified device. But,
1003 the ATA Soft Reset mechanism is so strong a reset method that it will force
1004 resetting on both devices connected to the same cable.
1005
1006 It is called by IdeBlkIoReset(), a interface function of Block
1007 I/O protocol.
1008
1009 This function can also be used by the ATAPI device to perform reset when
1010 ATAPI Reset command is failed.
1011
1012 @param PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
1013 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1014 @param Timeout The time to complete the command, uses 100ns as a unit.
1015
1016 @retval EFI_SUCCESS Soft reset completes successfully.
1017 @retval EFI_DEVICE_ERROR Any step during the reset process is failed.
1018
1019 @note The registers initial values after ATA soft reset are different
1020 to the ATA device and ATAPI device.
1021 **/
1022 EFI_STATUS
1023 EFIAPI
AtaSoftReset(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)1024 AtaSoftReset (
1025 IN EFI_PCI_IO_PROTOCOL *PciIo,
1026 IN EFI_IDE_REGISTERS *IdeRegisters,
1027 IN UINT64 Timeout
1028 )
1029 {
1030 UINT8 DeviceControl;
1031
1032 DeviceControl = 0;
1033 //
1034 // disable Interrupt and set SRST bit to initiate soft reset
1035 //
1036 DeviceControl = ATA_CTLREG_SRST | ATA_CTLREG_IEN_L;
1037
1038 IdeWritePortB (PciIo, IdeRegisters->AltOrDev, DeviceControl);
1039
1040 //
1041 // SRST should assert for at least 5 us, we use 10 us for
1042 // better compatibility
1043 //
1044 MicroSecondDelay (10);
1045
1046 //
1047 // Enable interrupt to support UDMA, and clear SRST bit
1048 //
1049 DeviceControl = 0;
1050 IdeWritePortB (PciIo, IdeRegisters->AltOrDev, DeviceControl);
1051
1052 //
1053 // Wait for at least 10 ms to check BSY status, we use 10 ms
1054 // for better compatibility
1055 //
1056 MicroSecondDelay (10000);
1057
1058 //
1059 // slave device needs at most 31ms to clear BSY
1060 //
1061 if (WaitForBSYClear (PciIo, IdeRegisters, Timeout) == EFI_TIMEOUT) {
1062 return EFI_DEVICE_ERROR;
1063 }
1064
1065 return EFI_SUCCESS;
1066 }
1067
1068 /**
1069 Send ATA Ext command into device with NON_DATA protocol.
1070
1071 @param PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
1072 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1073 @param AtaCommandBlock A pointer to EFI_ATA_COMMAND_BLOCK data structure.
1074 @param Timeout The time to complete the command, uses 100ns as a unit.
1075
1076 @retval EFI_SUCCESS Reading succeed
1077 @retval EFI_DEVICE_ERROR Error executing commands on this device.
1078
1079 **/
1080 EFI_STATUS
1081 EFIAPI
AtaIssueCommand(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN EFI_ATA_COMMAND_BLOCK * AtaCommandBlock,IN UINT64 Timeout)1082 AtaIssueCommand (
1083 IN EFI_PCI_IO_PROTOCOL *PciIo,
1084 IN EFI_IDE_REGISTERS *IdeRegisters,
1085 IN EFI_ATA_COMMAND_BLOCK *AtaCommandBlock,
1086 IN UINT64 Timeout
1087 )
1088 {
1089 EFI_STATUS Status;
1090 UINT8 DeviceHead;
1091 UINT8 AtaCommand;
1092
1093 ASSERT (PciIo != NULL);
1094 ASSERT (IdeRegisters != NULL);
1095 ASSERT (AtaCommandBlock != NULL);
1096
1097 DeviceHead = AtaCommandBlock->AtaDeviceHead;
1098 AtaCommand = AtaCommandBlock->AtaCommand;
1099
1100 Status = WaitForBSYClear (PciIo, IdeRegisters, Timeout);
1101 if (EFI_ERROR (Status)) {
1102 return EFI_DEVICE_ERROR;
1103 }
1104
1105 //
1106 // Select device (bit4), set LBA mode(bit6) (use 0xe0 for compatibility)
1107 //
1108 IdeWritePortB (PciIo, IdeRegisters->Head, (UINT8) (0xe0 | DeviceHead));
1109
1110 //
1111 // set all the command parameters
1112 // Before write to all the following registers, BSY and DRQ must be 0.
1113 //
1114 Status = DRQClear2 (PciIo, IdeRegisters, Timeout);
1115 if (EFI_ERROR (Status)) {
1116 return EFI_DEVICE_ERROR;
1117 }
1118
1119 //
1120 // Fill the feature register, which is a two-byte FIFO. Need write twice.
1121 //
1122 IdeWritePortB (PciIo, IdeRegisters->ErrOrFeature, AtaCommandBlock->AtaFeaturesExp);
1123 IdeWritePortB (PciIo, IdeRegisters->ErrOrFeature, AtaCommandBlock->AtaFeatures);
1124
1125 //
1126 // Fill the sector count register, which is a two-byte FIFO. Need write twice.
1127 //
1128 IdeWritePortB (PciIo, IdeRegisters->SectorCount, AtaCommandBlock->AtaSectorCountExp);
1129 IdeWritePortB (PciIo, IdeRegisters->SectorCount, AtaCommandBlock->AtaSectorCount);
1130
1131 //
1132 // Fill the start LBA registers, which are also two-byte FIFO
1133 //
1134 IdeWritePortB (PciIo, IdeRegisters->SectorNumber, AtaCommandBlock->AtaSectorNumberExp);
1135 IdeWritePortB (PciIo, IdeRegisters->SectorNumber, AtaCommandBlock->AtaSectorNumber);
1136
1137 IdeWritePortB (PciIo, IdeRegisters->CylinderLsb, AtaCommandBlock->AtaCylinderLowExp);
1138 IdeWritePortB (PciIo, IdeRegisters->CylinderLsb, AtaCommandBlock->AtaCylinderLow);
1139
1140 IdeWritePortB (PciIo, IdeRegisters->CylinderMsb, AtaCommandBlock->AtaCylinderHighExp);
1141 IdeWritePortB (PciIo, IdeRegisters->CylinderMsb, AtaCommandBlock->AtaCylinderHigh);
1142
1143 //
1144 // Send command via Command Register
1145 //
1146 IdeWritePortB (PciIo, IdeRegisters->CmdOrStatus, AtaCommand);
1147
1148 //
1149 // Stall at least 400 microseconds.
1150 //
1151 MicroSecondDelay (400);
1152
1153 return EFI_SUCCESS;
1154 }
1155
1156 /**
1157 This function is used to send out ATA commands conforms to the PIO Data In Protocol.
1158
1159 @param[in] PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data
1160 structure.
1161 @param[in] IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1162 @param[in, out] Buffer A pointer to the source buffer for the data.
1163 @param[in] ByteCount The length of the data.
1164 @param[in] Read Flag used to determine the data transfer direction.
1165 Read equals 1, means data transferred from device
1166 to host;Read equals 0, means data transferred
1167 from host to device.
1168 @param[in] AtaCommandBlock A pointer to EFI_ATA_COMMAND_BLOCK data structure.
1169 @param[in, out] AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
1170 @param[in] Timeout The time to complete the command, uses 100ns as a unit.
1171 @param[in] Task Optional. Pointer to the ATA_NONBLOCK_TASK
1172 used by non-blocking mode.
1173
1174 @retval EFI_SUCCESS send out the ATA command and device send required data successfully.
1175 @retval EFI_DEVICE_ERROR command sent failed.
1176
1177 **/
1178 EFI_STATUS
1179 EFIAPI
AtaPioDataInOut(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN OUT VOID * Buffer,IN UINT64 ByteCount,IN BOOLEAN Read,IN EFI_ATA_COMMAND_BLOCK * AtaCommandBlock,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock,IN UINT64 Timeout,IN ATA_NONBLOCK_TASK * Task)1180 AtaPioDataInOut (
1181 IN EFI_PCI_IO_PROTOCOL *PciIo,
1182 IN EFI_IDE_REGISTERS *IdeRegisters,
1183 IN OUT VOID *Buffer,
1184 IN UINT64 ByteCount,
1185 IN BOOLEAN Read,
1186 IN EFI_ATA_COMMAND_BLOCK *AtaCommandBlock,
1187 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock,
1188 IN UINT64 Timeout,
1189 IN ATA_NONBLOCK_TASK *Task
1190 )
1191 {
1192 UINTN WordCount;
1193 UINTN Increment;
1194 UINT16 *Buffer16;
1195 EFI_STATUS Status;
1196
1197 if ((PciIo == NULL) || (IdeRegisters == NULL) || (Buffer == NULL) || (AtaCommandBlock == NULL)) {
1198 return EFI_INVALID_PARAMETER;
1199 }
1200
1201 //
1202 // Issue ATA command
1203 //
1204 Status = AtaIssueCommand (PciIo, IdeRegisters, AtaCommandBlock, Timeout);
1205 if (EFI_ERROR (Status)) {
1206 Status = EFI_DEVICE_ERROR;
1207 goto Exit;
1208 }
1209
1210 Buffer16 = (UINT16 *) Buffer;
1211
1212 //
1213 // According to PIO data in protocol, host can perform a series of reads to
1214 // the data register after each time device set DRQ ready;
1215 // The data size of "a series of read" is command specific.
1216 // For most ATA command, data size received from device will not exceed
1217 // 1 sector, hence the data size for "a series of read" can be the whole data
1218 // size of one command request.
1219 // For ATA command such as Read Sector command, the data size of one ATA
1220 // command request is often larger than 1 sector, according to the
1221 // Read Sector command, the data size of "a series of read" is exactly 1
1222 // sector.
1223 // Here for simplification reason, we specify the data size for
1224 // "a series of read" to 1 sector (256 words) if data size of one ATA command
1225 // request is larger than 256 words.
1226 //
1227 Increment = 256;
1228
1229 //
1230 // used to record bytes of currently transfered data
1231 //
1232 WordCount = 0;
1233
1234 while (WordCount < RShiftU64(ByteCount, 1)) {
1235 //
1236 // Poll DRQ bit set, data transfer can be performed only when DRQ is ready
1237 //
1238 Status = DRQReady2 (PciIo, IdeRegisters, Timeout);
1239 if (EFI_ERROR (Status)) {
1240 Status = EFI_DEVICE_ERROR;
1241 goto Exit;
1242 }
1243
1244 //
1245 // Get the byte count for one series of read
1246 //
1247 if ((WordCount + Increment) > RShiftU64(ByteCount, 1)) {
1248 Increment = (UINTN)(RShiftU64(ByteCount, 1) - WordCount);
1249 }
1250
1251 if (Read) {
1252 IdeReadPortWMultiple (
1253 PciIo,
1254 IdeRegisters->Data,
1255 Increment,
1256 Buffer16
1257 );
1258 } else {
1259 IdeWritePortWMultiple (
1260 PciIo,
1261 IdeRegisters->Data,
1262 Increment,
1263 Buffer16
1264 );
1265 }
1266
1267 Status = CheckStatusRegister (PciIo, IdeRegisters);
1268 if (EFI_ERROR (Status)) {
1269 Status = EFI_DEVICE_ERROR;
1270 goto Exit;
1271 }
1272
1273 WordCount += Increment;
1274 Buffer16 += Increment;
1275 }
1276
1277 Status = DRQClear (PciIo, IdeRegisters, Timeout);
1278 if (EFI_ERROR (Status)) {
1279 Status = EFI_DEVICE_ERROR;
1280 goto Exit;
1281 }
1282
1283 Exit:
1284 //
1285 // Dump All Ide registers to ATA_STATUS_BLOCK
1286 //
1287 DumpAllIdeRegisters (PciIo, IdeRegisters, AtaStatusBlock);
1288
1289 //
1290 // Not support the Non-blocking now,just do the blocking process.
1291 //
1292 return Status;
1293 }
1294
1295 /**
1296 Send ATA command into device with NON_DATA protocol
1297
1298 @param[in] PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE
1299 data structure.
1300 @param[in] IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1301 @param[in] AtaCommandBlock A pointer to EFI_ATA_COMMAND_BLOCK data
1302 structure.
1303 @param[in, out] AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
1304 @param[in] Timeout The time to complete the command, uses 100ns as a unit.
1305 @param[in] Task Optional. Pointer to the ATA_NONBLOCK_TASK
1306 used by non-blocking mode.
1307
1308 @retval EFI_SUCCESS Reading succeed
1309 @retval EFI_ABORTED Command failed
1310 @retval EFI_DEVICE_ERROR Device status error.
1311
1312 **/
1313 EFI_STATUS
1314 EFIAPI
AtaNonDataCommandIn(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN EFI_ATA_COMMAND_BLOCK * AtaCommandBlock,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock,IN UINT64 Timeout,IN ATA_NONBLOCK_TASK * Task)1315 AtaNonDataCommandIn (
1316 IN EFI_PCI_IO_PROTOCOL *PciIo,
1317 IN EFI_IDE_REGISTERS *IdeRegisters,
1318 IN EFI_ATA_COMMAND_BLOCK *AtaCommandBlock,
1319 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock,
1320 IN UINT64 Timeout,
1321 IN ATA_NONBLOCK_TASK *Task
1322 )
1323 {
1324 EFI_STATUS Status;
1325
1326 if ((PciIo == NULL) || (IdeRegisters == NULL) || (AtaCommandBlock == NULL)) {
1327 return EFI_INVALID_PARAMETER;
1328 }
1329
1330 //
1331 // Issue ATA command
1332 //
1333 Status = AtaIssueCommand (PciIo, IdeRegisters, AtaCommandBlock, Timeout);
1334 if (EFI_ERROR (Status)) {
1335 Status = EFI_DEVICE_ERROR;
1336 goto Exit;
1337 }
1338
1339 //
1340 // Wait for command completion
1341 //
1342 Status = WaitForBSYClear (PciIo, IdeRegisters, Timeout);
1343 if (EFI_ERROR (Status)) {
1344 Status = EFI_DEVICE_ERROR;
1345 goto Exit;
1346 }
1347
1348 Status = CheckStatusRegister (PciIo, IdeRegisters);
1349 if (EFI_ERROR (Status)) {
1350 Status = EFI_DEVICE_ERROR;
1351 goto Exit;
1352 }
1353
1354 Exit:
1355 //
1356 // Dump All Ide registers to ATA_STATUS_BLOCK
1357 //
1358 DumpAllIdeRegisters (PciIo, IdeRegisters, AtaStatusBlock);
1359
1360 //
1361 // Not support the Non-blocking now,just do the blocking process.
1362 //
1363 return Status;
1364 }
1365
1366 /**
1367 Wait for memory to be set.
1368
1369 @param[in] PciIo The PCI IO protocol instance.
1370 @param[in] IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1371 @param[in] Timeout The time to complete the command, uses 100ns as a unit.
1372
1373 @retval EFI_DEVICE_ERROR The memory is not set.
1374 @retval EFI_TIMEOUT The memory setting is time out.
1375 @retval EFI_SUCCESS The memory is correct set.
1376
1377 **/
1378 EFI_STATUS
AtaUdmStatusWait(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT64 Timeout)1379 AtaUdmStatusWait (
1380 IN EFI_PCI_IO_PROTOCOL *PciIo,
1381 IN EFI_IDE_REGISTERS *IdeRegisters,
1382 IN UINT64 Timeout
1383 )
1384 {
1385 UINT8 RegisterValue;
1386 EFI_STATUS Status;
1387 UINT16 IoPortForBmis;
1388 UINT64 Delay;
1389 BOOLEAN InfiniteWait;
1390
1391 if (Timeout == 0) {
1392 InfiniteWait = TRUE;
1393 } else {
1394 InfiniteWait = FALSE;
1395 }
1396
1397 Delay = DivU64x32 (Timeout, 1000) + 1;
1398
1399 do {
1400 Status = CheckStatusRegister (PciIo, IdeRegisters);
1401 if (EFI_ERROR (Status)) {
1402 Status = EFI_DEVICE_ERROR;
1403 break;
1404 }
1405
1406 IoPortForBmis = (UINT16) (IdeRegisters->BusMasterBaseAddr + BMIS_OFFSET);
1407 RegisterValue = IdeReadPortB (PciIo, IoPortForBmis);
1408 if (((RegisterValue & BMIS_ERROR) != 0) || (Timeout == 0)) {
1409 DEBUG ((EFI_D_ERROR, "ATA UDMA operation fails\n"));
1410 Status = EFI_DEVICE_ERROR;
1411 break;
1412 }
1413
1414 if ((RegisterValue & BMIS_INTERRUPT) != 0) {
1415 Status = EFI_SUCCESS;
1416 break;
1417 }
1418 //
1419 // Stall for 100 microseconds.
1420 //
1421 MicroSecondDelay (100);
1422 Delay--;
1423 } while (InfiniteWait || (Delay > 0));
1424
1425 return Status;
1426 }
1427
1428 /**
1429 Check if the memory to be set.
1430
1431 @param[in] PciIo The PCI IO protocol instance.
1432 @param[in] Task Optional. Pointer to the ATA_NONBLOCK_TASK
1433 used by non-blocking mode.
1434 @param[in] IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1435
1436 @retval EFI_DEVICE_ERROR The memory setting met a issue.
1437 @retval EFI_NOT_READY The memory is not set.
1438 @retval EFI_TIMEOUT The memory setting is time out.
1439 @retval EFI_SUCCESS The memory is correct set.
1440
1441 **/
1442 EFI_STATUS
AtaUdmStatusCheck(IN EFI_PCI_IO_PROTOCOL * PciIo,IN ATA_NONBLOCK_TASK * Task,IN EFI_IDE_REGISTERS * IdeRegisters)1443 AtaUdmStatusCheck (
1444 IN EFI_PCI_IO_PROTOCOL *PciIo,
1445 IN ATA_NONBLOCK_TASK *Task,
1446 IN EFI_IDE_REGISTERS *IdeRegisters
1447 )
1448 {
1449 UINT8 RegisterValue;
1450 UINT16 IoPortForBmis;
1451 EFI_STATUS Status;
1452
1453 Task->RetryTimes--;
1454
1455 Status = CheckStatusRegister (PciIo, IdeRegisters);
1456 if (EFI_ERROR (Status)) {
1457 return EFI_DEVICE_ERROR;
1458 }
1459
1460 IoPortForBmis = (UINT16) (IdeRegisters->BusMasterBaseAddr + BMIS_OFFSET);
1461 RegisterValue = IdeReadPortB (PciIo, IoPortForBmis);
1462
1463 if ((RegisterValue & BMIS_ERROR) != 0) {
1464 DEBUG ((EFI_D_ERROR, "ATA UDMA operation fails\n"));
1465 return EFI_DEVICE_ERROR;
1466 }
1467
1468 if ((RegisterValue & BMIS_INTERRUPT) != 0) {
1469 return EFI_SUCCESS;
1470 }
1471
1472 if (!Task->InfiniteWait && (Task->RetryTimes == 0)) {
1473 return EFI_TIMEOUT;
1474 } else {
1475 //
1476 // The memory is not set.
1477 //
1478 return EFI_NOT_READY;
1479 }
1480 }
1481
1482 /**
1483 Perform an ATA Udma operation (Read, ReadExt, Write, WriteExt).
1484
1485 @param[in] Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data
1486 structure.
1487 @param[in] IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1488 @param[in] Read Flag used to determine the data transfer
1489 direction. Read equals 1, means data transferred
1490 from device to host;Read equals 0, means data
1491 transferred from host to device.
1492 @param[in] DataBuffer A pointer to the source buffer for the data.
1493 @param[in] DataLength The length of the data.
1494 @param[in] AtaCommandBlock A pointer to EFI_ATA_COMMAND_BLOCK data structure.
1495 @param[in, out] AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
1496 @param[in] Timeout The time to complete the command, uses 100ns as a unit.
1497 @param[in] Task Optional. Pointer to the ATA_NONBLOCK_TASK
1498 used by non-blocking mode.
1499
1500 @retval EFI_SUCCESS the operation is successful.
1501 @retval EFI_OUT_OF_RESOURCES Build PRD table failed
1502 @retval EFI_UNSUPPORTED Unknown channel or operations command
1503 @retval EFI_DEVICE_ERROR Ata command execute failed
1504
1505 **/
1506 EFI_STATUS
1507 EFIAPI
AtaUdmaInOut(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN EFI_IDE_REGISTERS * IdeRegisters,IN BOOLEAN Read,IN VOID * DataBuffer,IN UINT64 DataLength,IN EFI_ATA_COMMAND_BLOCK * AtaCommandBlock,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock,IN UINT64 Timeout,IN ATA_NONBLOCK_TASK * Task)1508 AtaUdmaInOut (
1509 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
1510 IN EFI_IDE_REGISTERS *IdeRegisters,
1511 IN BOOLEAN Read,
1512 IN VOID *DataBuffer,
1513 IN UINT64 DataLength,
1514 IN EFI_ATA_COMMAND_BLOCK *AtaCommandBlock,
1515 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock,
1516 IN UINT64 Timeout,
1517 IN ATA_NONBLOCK_TASK *Task
1518 )
1519 {
1520 EFI_STATUS Status;
1521 UINT16 IoPortForBmic;
1522 UINT16 IoPortForBmis;
1523 UINT16 IoPortForBmid;
1524
1525 UINTN PrdTableSize;
1526 EFI_PHYSICAL_ADDRESS PrdTableMapAddr;
1527 VOID *PrdTableMap;
1528 EFI_PHYSICAL_ADDRESS PrdTableBaseAddr;
1529 EFI_ATA_DMA_PRD *TempPrdBaseAddr;
1530 UINTN PrdTableNum;
1531
1532 UINT8 RegisterValue;
1533 UINTN PageCount;
1534 UINTN ByteCount;
1535 UINTN ByteRemaining;
1536 UINT8 DeviceControl;
1537
1538 VOID *BufferMap;
1539 EFI_PHYSICAL_ADDRESS BufferMapAddress;
1540 EFI_PCI_IO_PROTOCOL_OPERATION PciIoOperation;
1541
1542 UINT8 DeviceHead;
1543 EFI_PCI_IO_PROTOCOL *PciIo;
1544 EFI_TPL OldTpl;
1545
1546 UINTN AlignmentMask;
1547 UINTN RealPageCount;
1548 EFI_PHYSICAL_ADDRESS BaseAddr;
1549 EFI_PHYSICAL_ADDRESS BaseMapAddr;
1550
1551 Status = EFI_SUCCESS;
1552 PrdTableMap = NULL;
1553 BufferMap = NULL;
1554 PageCount = 0;
1555 RealPageCount = 0;
1556 BaseAddr = 0;
1557 PciIo = Instance->PciIo;
1558
1559 if ((PciIo == NULL) || (IdeRegisters == NULL) || (DataBuffer == NULL) || (AtaCommandBlock == NULL)) {
1560 return EFI_INVALID_PARAMETER;
1561 }
1562
1563 //
1564 // Before starting the Blocking BlockIO operation, push to finish all non-blocking
1565 // BlockIO tasks.
1566 // Delay 1ms to simulate the blocking time out checking.
1567 //
1568 OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
1569 while ((Task == NULL) && (!IsListEmpty (&Instance->NonBlockingTaskList))) {
1570 AsyncNonBlockingTransferRoutine (NULL, Instance);
1571 //
1572 // Stall for 1 milliseconds.
1573 //
1574 MicroSecondDelay (1000);
1575 }
1576 gBS->RestoreTPL (OldTpl);
1577
1578 //
1579 // The data buffer should be even alignment
1580 //
1581 if (((UINTN)DataBuffer & 0x1) != 0) {
1582 return EFI_INVALID_PARAMETER;
1583 }
1584
1585 //
1586 // Set relevant IO Port address.
1587 //
1588 IoPortForBmic = (UINT16) (IdeRegisters->BusMasterBaseAddr + BMIC_OFFSET);
1589 IoPortForBmis = (UINT16) (IdeRegisters->BusMasterBaseAddr + BMIS_OFFSET);
1590 IoPortForBmid = (UINT16) (IdeRegisters->BusMasterBaseAddr + BMID_OFFSET);
1591
1592 //
1593 // For Blocking mode, start the command.
1594 // For non-blocking mode, when the command is not started, start it, otherwise
1595 // go to check the status.
1596 //
1597 if (((Task != NULL) && (!Task->IsStart)) || (Task == NULL)) {
1598 //
1599 // Calculate the number of PRD entry.
1600 // Every entry in PRD table can specify a 64K memory region.
1601 //
1602 PrdTableNum = (UINTN)(RShiftU64(DataLength, 16) + 1);
1603
1604 //
1605 // Make sure that the memory region of PRD table is not cross 64K boundary
1606 //
1607 PrdTableSize = PrdTableNum * sizeof (EFI_ATA_DMA_PRD);
1608 if (PrdTableSize > 0x10000) {
1609 return EFI_INVALID_PARAMETER;
1610 }
1611
1612 //
1613 // Allocate buffer for PRD table initialization.
1614 // Note Ide Bus Master spec said the descriptor table must be aligned on a 4 byte
1615 // boundary and the table cannot cross a 64K boundary in memory.
1616 //
1617 PageCount = EFI_SIZE_TO_PAGES (PrdTableSize);
1618 RealPageCount = PageCount + EFI_SIZE_TO_PAGES (SIZE_64KB);
1619
1620 //
1621 // Make sure that PageCount plus EFI_SIZE_TO_PAGES (SIZE_64KB) does not overflow.
1622 //
1623 ASSERT (RealPageCount > PageCount);
1624
1625 Status = PciIo->AllocateBuffer (
1626 PciIo,
1627 AllocateAnyPages,
1628 EfiBootServicesData,
1629 RealPageCount,
1630 (VOID **)&BaseAddr,
1631 0
1632 );
1633 if (EFI_ERROR (Status)) {
1634 return EFI_OUT_OF_RESOURCES;
1635 }
1636
1637 ByteCount = EFI_PAGES_TO_SIZE (RealPageCount);
1638 Status = PciIo->Map (
1639 PciIo,
1640 EfiPciIoOperationBusMasterCommonBuffer,
1641 (VOID*)(UINTN)BaseAddr,
1642 &ByteCount,
1643 &BaseMapAddr,
1644 &PrdTableMap
1645 );
1646 if (EFI_ERROR (Status) || (ByteCount != EFI_PAGES_TO_SIZE (RealPageCount))) {
1647 //
1648 // If the data length actually mapped is not equal to the requested amount,
1649 // it means the DMA operation may be broken into several discontinuous smaller chunks.
1650 // Can't handle this case.
1651 //
1652 PciIo->FreeBuffer (PciIo, RealPageCount, (VOID*)(UINTN)BaseAddr);
1653 return EFI_OUT_OF_RESOURCES;
1654 }
1655
1656 ZeroMem ((VOID *) ((UINTN) BaseAddr), ByteCount);
1657
1658 //
1659 // Calculate the 64K align address as PRD Table base address.
1660 //
1661 AlignmentMask = SIZE_64KB - 1;
1662 PrdTableBaseAddr = ((UINTN) BaseAddr + AlignmentMask) & ~AlignmentMask;
1663 PrdTableMapAddr = ((UINTN) BaseMapAddr + AlignmentMask) & ~AlignmentMask;
1664
1665 //
1666 // Map the host address of DataBuffer to DMA master address.
1667 //
1668 if (Read) {
1669 PciIoOperation = EfiPciIoOperationBusMasterWrite;
1670 } else {
1671 PciIoOperation = EfiPciIoOperationBusMasterRead;
1672 }
1673
1674 ByteCount = (UINTN)DataLength;
1675 Status = PciIo->Map (
1676 PciIo,
1677 PciIoOperation,
1678 DataBuffer,
1679 &ByteCount,
1680 &BufferMapAddress,
1681 &BufferMap
1682 );
1683 if (EFI_ERROR (Status) || (ByteCount != DataLength)) {
1684 PciIo->Unmap (PciIo, PrdTableMap);
1685 PciIo->FreeBuffer (PciIo, RealPageCount, (VOID*)(UINTN)BaseAddr);
1686 return EFI_OUT_OF_RESOURCES;
1687 }
1688
1689 //
1690 // According to Ata spec, it requires the buffer address and size to be even.
1691 //
1692 ASSERT ((BufferMapAddress & 0x1) == 0);
1693 ASSERT ((ByteCount & 0x1) == 0);
1694
1695 //
1696 // Fill the PRD table with appropriate bus master address of data buffer and data length.
1697 //
1698 ByteRemaining = ByteCount;
1699 TempPrdBaseAddr = (EFI_ATA_DMA_PRD*)(UINTN)PrdTableBaseAddr;
1700 while (ByteRemaining != 0) {
1701 if (ByteRemaining <= 0x10000) {
1702 TempPrdBaseAddr->RegionBaseAddr = (UINT32) ((UINTN) BufferMapAddress);
1703 TempPrdBaseAddr->ByteCount = (UINT16) ByteRemaining;
1704 TempPrdBaseAddr->EndOfTable = 0x8000;
1705 break;
1706 }
1707
1708 TempPrdBaseAddr->RegionBaseAddr = (UINT32) ((UINTN) BufferMapAddress);
1709 TempPrdBaseAddr->ByteCount = (UINT16) 0x0;
1710
1711 ByteRemaining -= 0x10000;
1712 BufferMapAddress += 0x10000;
1713 TempPrdBaseAddr++;
1714 }
1715
1716 //
1717 // Start to enable the DMA operation
1718 //
1719 DeviceHead = AtaCommandBlock->AtaDeviceHead;
1720
1721 IdeWritePortB (PciIo, IdeRegisters->Head, (UINT8)(0xe0 | DeviceHead));
1722
1723 //
1724 // Enable interrupt to support UDMA
1725 //
1726 DeviceControl = 0;
1727 IdeWritePortB (PciIo, IdeRegisters->AltOrDev, DeviceControl);
1728
1729 //
1730 // Read BMIS register and clear ERROR and INTR bit
1731 //
1732 RegisterValue = IdeReadPortB(PciIo, IoPortForBmis);
1733 RegisterValue |= (BMIS_INTERRUPT | BMIS_ERROR);
1734 IdeWritePortB (PciIo, IoPortForBmis, RegisterValue);
1735
1736 //
1737 // Set the base address to BMID register
1738 //
1739 IdeWritePortDW (PciIo, IoPortForBmid, (UINT32)PrdTableMapAddr);
1740
1741 //
1742 // Set BMIC register to identify the operation direction
1743 //
1744 RegisterValue = IdeReadPortB(PciIo, IoPortForBmic);
1745 if (Read) {
1746 RegisterValue |= BMIC_NREAD;
1747 } else {
1748 RegisterValue &= ~((UINT8) BMIC_NREAD);
1749 }
1750 IdeWritePortB (PciIo, IoPortForBmic, RegisterValue);
1751
1752 if (Task != NULL) {
1753 Task->Map = BufferMap;
1754 Task->TableMap = PrdTableMap;
1755 Task->MapBaseAddress = (EFI_ATA_DMA_PRD*)(UINTN)BaseAddr;
1756 Task->PageCount = RealPageCount;
1757 Task->IsStart = TRUE;
1758 }
1759
1760 //
1761 // Issue ATA command
1762 //
1763 Status = AtaIssueCommand (PciIo, IdeRegisters, AtaCommandBlock, Timeout);
1764
1765 if (EFI_ERROR (Status)) {
1766 Status = EFI_DEVICE_ERROR;
1767 goto Exit;
1768 }
1769
1770 Status = CheckStatusRegister (PciIo, IdeRegisters);
1771 if (EFI_ERROR (Status)) {
1772 Status = EFI_DEVICE_ERROR;
1773 goto Exit;
1774 }
1775 //
1776 // Set START bit of BMIC register
1777 //
1778 RegisterValue = IdeReadPortB(PciIo, IoPortForBmic);
1779 RegisterValue |= BMIC_START;
1780 IdeWritePortB(PciIo, IoPortForBmic, RegisterValue);
1781
1782 }
1783
1784 //
1785 // Check the INTERRUPT and ERROR bit of BMIS
1786 //
1787 if (Task != NULL) {
1788 Status = AtaUdmStatusCheck (PciIo, Task, IdeRegisters);
1789 } else {
1790 Status = AtaUdmStatusWait (PciIo, IdeRegisters, Timeout);
1791 }
1792
1793 //
1794 // For blocking mode, clear registers and free buffers.
1795 // For non blocking mode, when the related registers have been set or time
1796 // out, or a error has been happened, it needs to clear the register and free
1797 // buffer.
1798 //
1799 if ((Task == NULL) || Status != EFI_NOT_READY) {
1800 //
1801 // Read BMIS register and clear ERROR and INTR bit
1802 //
1803 RegisterValue = IdeReadPortB (PciIo, IoPortForBmis);
1804 RegisterValue |= (BMIS_INTERRUPT | BMIS_ERROR);
1805 IdeWritePortB (PciIo, IoPortForBmis, RegisterValue);
1806
1807 //
1808 // Read Status Register of IDE device to clear interrupt
1809 //
1810 RegisterValue = IdeReadPortB(PciIo, IdeRegisters->CmdOrStatus);
1811
1812 //
1813 // Clear START bit of BMIC register
1814 //
1815 RegisterValue = IdeReadPortB(PciIo, IoPortForBmic);
1816 RegisterValue &= ~((UINT8) BMIC_START);
1817 IdeWritePortB (PciIo, IoPortForBmic, RegisterValue);
1818
1819 //
1820 // Disable interrupt of Select device
1821 //
1822 DeviceControl = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
1823 DeviceControl |= ATA_CTLREG_IEN_L;
1824 IdeWritePortB (PciIo, IdeRegisters->AltOrDev, DeviceControl);
1825 //
1826 // Stall for 10 milliseconds.
1827 //
1828 MicroSecondDelay (10000);
1829
1830 }
1831
1832 Exit:
1833 //
1834 // Free all allocated resource
1835 //
1836 if ((Task == NULL) || Status != EFI_NOT_READY) {
1837 if (Task != NULL) {
1838 PciIo->Unmap (PciIo, Task->TableMap);
1839 PciIo->FreeBuffer (PciIo, Task->PageCount, Task->MapBaseAddress);
1840 PciIo->Unmap (PciIo, Task->Map);
1841 } else {
1842 PciIo->Unmap (PciIo, PrdTableMap);
1843 PciIo->FreeBuffer (PciIo, RealPageCount, (VOID*)(UINTN)BaseAddr);
1844 PciIo->Unmap (PciIo, BufferMap);
1845 }
1846
1847 //
1848 // Dump All Ide registers to ATA_STATUS_BLOCK
1849 //
1850 DumpAllIdeRegisters (PciIo, IdeRegisters, AtaStatusBlock);
1851 }
1852
1853 return Status;
1854 }
1855
1856 /**
1857 This function reads the pending data in the device.
1858
1859 @param PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
1860 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1861
1862 @retval EFI_SUCCESS Successfully read.
1863 @retval EFI_NOT_READY The BSY is set avoiding reading.
1864
1865 **/
1866 EFI_STATUS
1867 EFIAPI
AtaPacketReadPendingData(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters)1868 AtaPacketReadPendingData (
1869 IN EFI_PCI_IO_PROTOCOL *PciIo,
1870 IN EFI_IDE_REGISTERS *IdeRegisters
1871 )
1872 {
1873 UINT8 AltRegister;
1874 UINT16 TempWordBuffer;
1875
1876 AltRegister = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
1877 if ((AltRegister & ATA_STSREG_BSY) == ATA_STSREG_BSY) {
1878 return EFI_NOT_READY;
1879 }
1880
1881 if ((AltRegister & (ATA_STSREG_BSY | ATA_STSREG_DRQ)) == ATA_STSREG_DRQ) {
1882 TempWordBuffer = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
1883 while ((TempWordBuffer & (ATA_STSREG_BSY | ATA_STSREG_DRQ)) == ATA_STSREG_DRQ) {
1884 IdeReadPortWMultiple (
1885 PciIo,
1886 IdeRegisters->Data,
1887 1,
1888 &TempWordBuffer
1889 );
1890 TempWordBuffer = IdeReadPortB (PciIo, IdeRegisters->AltOrDev);
1891 }
1892 }
1893 return EFI_SUCCESS;
1894 }
1895
1896 /**
1897 This function is called by AtaPacketCommandExecute().
1898 It is used to transfer data between host and device. The data direction is specified
1899 by the fourth parameter.
1900
1901 @param PciIo A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
1902 @param IdeRegisters A pointer to EFI_IDE_REGISTERS data structure.
1903 @param Buffer Buffer contained data transferred between host and device.
1904 @param ByteCount Data size in byte unit of the buffer.
1905 @param Read Flag used to determine the data transfer direction.
1906 Read equals 1, means data transferred from device to host;
1907 Read equals 0, means data transferred from host to device.
1908 @param Timeout Timeout value for wait DRQ ready before each data stream's transfer
1909 , uses 100ns as a unit.
1910
1911 @retval EFI_SUCCESS data is transferred successfully.
1912 @retval EFI_DEVICE_ERROR the device failed to transfer data.
1913 **/
1914 EFI_STATUS
1915 EFIAPI
AtaPacketReadWrite(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN OUT VOID * Buffer,IN UINT64 ByteCount,IN BOOLEAN Read,IN UINT64 Timeout)1916 AtaPacketReadWrite (
1917 IN EFI_PCI_IO_PROTOCOL *PciIo,
1918 IN EFI_IDE_REGISTERS *IdeRegisters,
1919 IN OUT VOID *Buffer,
1920 IN UINT64 ByteCount,
1921 IN BOOLEAN Read,
1922 IN UINT64 Timeout
1923 )
1924 {
1925 UINT32 RequiredWordCount;
1926 UINT32 ActualWordCount;
1927 UINT32 WordCount;
1928 EFI_STATUS Status;
1929 UINT16 *PtrBuffer;
1930
1931 //
1932 // No data transfer is premitted.
1933 //
1934 if (ByteCount == 0) {
1935 return EFI_SUCCESS;
1936 }
1937
1938 PtrBuffer = Buffer;
1939 RequiredWordCount = (UINT32)RShiftU64(ByteCount, 1);
1940 //
1941 // ActuralWordCount means the word count of data really transferred.
1942 //
1943 ActualWordCount = 0;
1944
1945 while (ActualWordCount < RequiredWordCount) {
1946 //
1947 // before each data transfer stream, the host should poll DRQ bit ready,
1948 // to see whether indicates device is ready to transfer data.
1949 //
1950 Status = DRQReady2 (PciIo, IdeRegisters, Timeout);
1951 if (EFI_ERROR (Status)) {
1952 return Status;
1953 }
1954
1955 //
1956 // get current data transfer size from Cylinder Registers.
1957 //
1958 WordCount = IdeReadPortB (PciIo, IdeRegisters->CylinderMsb) << 8;
1959 WordCount = WordCount | IdeReadPortB (PciIo, IdeRegisters->CylinderLsb);
1960 WordCount = WordCount & 0xffff;
1961 WordCount /= 2;
1962
1963 WordCount = MIN (WordCount, (RequiredWordCount - ActualWordCount));
1964
1965 if (Read) {
1966 IdeReadPortWMultiple (
1967 PciIo,
1968 IdeRegisters->Data,
1969 WordCount,
1970 PtrBuffer
1971 );
1972 } else {
1973 IdeWritePortWMultiple (
1974 PciIo,
1975 IdeRegisters->Data,
1976 WordCount,
1977 PtrBuffer
1978 );
1979 }
1980
1981 //
1982 // read status register to check whether error happens.
1983 //
1984 Status = CheckStatusRegister (PciIo, IdeRegisters);
1985 if (EFI_ERROR (Status)) {
1986 return EFI_DEVICE_ERROR;
1987 }
1988
1989 PtrBuffer += WordCount;
1990 ActualWordCount += WordCount;
1991 }
1992
1993 if (Read) {
1994 //
1995 // In the case where the drive wants to send more data than we need to read,
1996 // the DRQ bit will be set and cause delays from DRQClear2().
1997 // We need to read data from the drive until it clears DRQ so we can move on.
1998 //
1999 AtaPacketReadPendingData (PciIo, IdeRegisters);
2000 }
2001
2002 //
2003 // read status register to check whether error happens.
2004 //
2005 Status = CheckStatusRegister (PciIo, IdeRegisters);
2006 if (EFI_ERROR (Status)) {
2007 return EFI_DEVICE_ERROR;
2008 }
2009
2010 //
2011 // After data transfer is completed, normally, DRQ bit should clear.
2012 //
2013 Status = DRQClear (PciIo, IdeRegisters, Timeout);
2014 if (EFI_ERROR (Status)) {
2015 return EFI_DEVICE_ERROR;
2016 }
2017
2018 return Status;
2019 }
2020
2021 /**
2022 This function is used to send out ATAPI commands conforms to the Packet Command
2023 with PIO Data In Protocol.
2024
2025 @param[in] PciIo Pointer to the EFI_PCI_IO_PROTOCOL instance
2026 @param[in] IdeRegisters Pointer to EFI_IDE_REGISTERS which is used to
2027 store the IDE i/o port registers' base addresses
2028 @param[in] Channel The channel number of device.
2029 @param[in] Device The device number of device.
2030 @param[in] Packet A pointer to EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET data structure.
2031
2032 @retval EFI_SUCCESS send out the ATAPI packet command successfully
2033 and device sends data successfully.
2034 @retval EFI_DEVICE_ERROR the device failed to send data.
2035
2036 **/
2037 EFI_STATUS
2038 EFIAPI
AtaPacketCommandExecute(IN EFI_PCI_IO_PROTOCOL * PciIo,IN EFI_IDE_REGISTERS * IdeRegisters,IN UINT8 Channel,IN UINT8 Device,IN EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET * Packet)2039 AtaPacketCommandExecute (
2040 IN EFI_PCI_IO_PROTOCOL *PciIo,
2041 IN EFI_IDE_REGISTERS *IdeRegisters,
2042 IN UINT8 Channel,
2043 IN UINT8 Device,
2044 IN EFI_EXT_SCSI_PASS_THRU_SCSI_REQUEST_PACKET *Packet
2045 )
2046 {
2047 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2048 EFI_STATUS Status;
2049 UINT8 Count;
2050 UINT8 PacketCommand[12];
2051
2052 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2053
2054 //
2055 // Fill ATAPI Command Packet according to CDB.
2056 // For Atapi cmd, its length should be less than or equal to 12 bytes.
2057 //
2058 if (Packet->CdbLength > 12) {
2059 return EFI_INVALID_PARAMETER;
2060 }
2061
2062 ZeroMem (PacketCommand, 12);
2063 CopyMem (PacketCommand, Packet->Cdb, Packet->CdbLength);
2064
2065 //
2066 // No OVL; No DMA
2067 //
2068 AtaCommandBlock.AtaFeatures = 0x00;
2069 //
2070 // set the transfersize to ATAPI_MAX_BYTE_COUNT to let the device
2071 // determine how many data should be transferred.
2072 //
2073 AtaCommandBlock.AtaCylinderLow = (UINT8) (ATAPI_MAX_BYTE_COUNT & 0x00ff);
2074 AtaCommandBlock.AtaCylinderHigh = (UINT8) (ATAPI_MAX_BYTE_COUNT >> 8);
2075 AtaCommandBlock.AtaDeviceHead = (UINT8) (Device << 0x4);
2076 AtaCommandBlock.AtaCommand = ATA_CMD_PACKET;
2077
2078 IdeWritePortB (PciIo, IdeRegisters->Head, (UINT8)(0xe0 | (Device << 0x4)));
2079 //
2080 // Disable interrupt
2081 //
2082 IdeWritePortB (PciIo, IdeRegisters->AltOrDev, ATA_DEFAULT_CTL);
2083
2084 //
2085 // Issue ATA PACKET command firstly
2086 //
2087 Status = AtaIssueCommand (PciIo, IdeRegisters, &AtaCommandBlock, Packet->Timeout);
2088 if (EFI_ERROR (Status)) {
2089 return Status;
2090 }
2091
2092 Status = DRQReady (PciIo, IdeRegisters, Packet->Timeout);
2093 if (EFI_ERROR (Status)) {
2094 return Status;
2095 }
2096
2097 //
2098 // Send out ATAPI command packet
2099 //
2100 for (Count = 0; Count < 6; Count++) {
2101 IdeWritePortW (PciIo, IdeRegisters->Data, *((UINT16*)PacketCommand + Count));
2102 //
2103 // Stall for 10 microseconds.
2104 //
2105 MicroSecondDelay (10);
2106 }
2107
2108 //
2109 // Read/Write the data of ATAPI Command
2110 //
2111 if (Packet->DataDirection == EFI_EXT_SCSI_DATA_DIRECTION_READ) {
2112 Status = AtaPacketReadWrite (
2113 PciIo,
2114 IdeRegisters,
2115 Packet->InDataBuffer,
2116 Packet->InTransferLength,
2117 TRUE,
2118 Packet->Timeout
2119 );
2120 } else {
2121 Status = AtaPacketReadWrite (
2122 PciIo,
2123 IdeRegisters,
2124 Packet->OutDataBuffer,
2125 Packet->OutTransferLength,
2126 FALSE,
2127 Packet->Timeout
2128 );
2129 }
2130
2131 return Status;
2132 }
2133
2134
2135 /**
2136 Set the calculated Best transfer mode to a detected device.
2137
2138 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2139 @param Channel The channel number of device.
2140 @param Device The device number of device.
2141 @param TransferMode A pointer to EFI_ATA_TRANSFER_MODE data structure.
2142 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
2143
2144 @retval EFI_SUCCESS Set transfer mode successfully.
2145 @retval EFI_DEVICE_ERROR Set transfer mode failed.
2146 @retval EFI_OUT_OF_RESOURCES Allocate memory failed.
2147
2148 **/
2149 EFI_STATUS
2150 EFIAPI
SetDeviceTransferMode(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 Channel,IN UINT8 Device,IN EFI_ATA_TRANSFER_MODE * TransferMode,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)2151 SetDeviceTransferMode (
2152 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2153 IN UINT8 Channel,
2154 IN UINT8 Device,
2155 IN EFI_ATA_TRANSFER_MODE *TransferMode,
2156 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
2157 )
2158 {
2159 EFI_STATUS Status;
2160 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2161
2162 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2163
2164 AtaCommandBlock.AtaCommand = ATA_CMD_SET_FEATURES;
2165 AtaCommandBlock.AtaDeviceHead = (UINT8)(Device << 0x4);
2166 AtaCommandBlock.AtaFeatures = 0x03;
2167 AtaCommandBlock.AtaSectorCount = *((UINT8 *)TransferMode);
2168
2169 //
2170 // Send SET FEATURE command (sub command 0x03) to set pio mode.
2171 //
2172 Status = AtaNonDataCommandIn (
2173 Instance->PciIo,
2174 &Instance->IdeRegisters[Channel],
2175 &AtaCommandBlock,
2176 AtaStatusBlock,
2177 ATA_ATAPI_TIMEOUT,
2178 NULL
2179 );
2180
2181 return Status;
2182 }
2183
2184 /**
2185 Set drive parameters for devices not support PACKETS command.
2186
2187 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2188 @param Channel The channel number of device.
2189 @param Device The device number of device.
2190 @param DriveParameters A pointer to EFI_ATA_DRIVE_PARMS data structure.
2191 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
2192
2193 @retval EFI_SUCCESS Set drive parameter successfully.
2194 @retval EFI_DEVICE_ERROR Set drive parameter failed.
2195 @retval EFI_OUT_OF_RESOURCES Allocate memory failed.
2196
2197 **/
2198 EFI_STATUS
2199 EFIAPI
SetDriveParameters(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 Channel,IN UINT8 Device,IN EFI_ATA_DRIVE_PARMS * DriveParameters,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)2200 SetDriveParameters (
2201 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2202 IN UINT8 Channel,
2203 IN UINT8 Device,
2204 IN EFI_ATA_DRIVE_PARMS *DriveParameters,
2205 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
2206 )
2207 {
2208 EFI_STATUS Status;
2209 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2210
2211 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2212
2213 AtaCommandBlock.AtaCommand = ATA_CMD_INIT_DRIVE_PARAM;
2214 AtaCommandBlock.AtaSectorCount = DriveParameters->Sector;
2215 AtaCommandBlock.AtaDeviceHead = (UINT8) ((Device << 0x4) + DriveParameters->Heads);
2216
2217 //
2218 // Send Init drive parameters
2219 //
2220 Status = AtaNonDataCommandIn (
2221 Instance->PciIo,
2222 &Instance->IdeRegisters[Channel],
2223 &AtaCommandBlock,
2224 AtaStatusBlock,
2225 ATA_ATAPI_TIMEOUT,
2226 NULL
2227 );
2228
2229 //
2230 // Send Set Multiple parameters
2231 //
2232 AtaCommandBlock.AtaCommand = ATA_CMD_SET_MULTIPLE_MODE;
2233 AtaCommandBlock.AtaSectorCount = DriveParameters->MultipleSector;
2234 AtaCommandBlock.AtaDeviceHead = (UINT8)(Device << 0x4);
2235
2236 Status = AtaNonDataCommandIn (
2237 Instance->PciIo,
2238 &Instance->IdeRegisters[Channel],
2239 &AtaCommandBlock,
2240 AtaStatusBlock,
2241 ATA_ATAPI_TIMEOUT,
2242 NULL
2243 );
2244
2245 return Status;
2246 }
2247
2248 /**
2249 Send SMART Return Status command to check if the execution of SMART cmd is successful or not.
2250
2251 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2252 @param Channel The channel number of device.
2253 @param Device The device number of device.
2254 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
2255
2256 @retval EFI_SUCCESS Successfully get the return status of S.M.A.R.T command execution.
2257 @retval Others Fail to get return status data.
2258
2259 **/
2260 EFI_STATUS
2261 EFIAPI
IdeAtaSmartReturnStatusCheck(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 Channel,IN UINT8 Device,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)2262 IdeAtaSmartReturnStatusCheck (
2263 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2264 IN UINT8 Channel,
2265 IN UINT8 Device,
2266 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
2267 )
2268 {
2269 EFI_STATUS Status;
2270 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2271 UINT8 LBAMid;
2272 UINT8 LBAHigh;
2273
2274 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2275
2276 AtaCommandBlock.AtaCommand = ATA_CMD_SMART;
2277 AtaCommandBlock.AtaFeatures = ATA_SMART_RETURN_STATUS;
2278 AtaCommandBlock.AtaCylinderLow = ATA_CONSTANT_4F;
2279 AtaCommandBlock.AtaCylinderHigh = ATA_CONSTANT_C2;
2280 AtaCommandBlock.AtaDeviceHead = (UINT8) ((Device << 0x4) | 0xe0);
2281
2282 //
2283 // Send S.M.A.R.T Read Return Status command to device
2284 //
2285 Status = AtaNonDataCommandIn (
2286 Instance->PciIo,
2287 &Instance->IdeRegisters[Channel],
2288 &AtaCommandBlock,
2289 AtaStatusBlock,
2290 ATA_ATAPI_TIMEOUT,
2291 NULL
2292 );
2293
2294 if (EFI_ERROR (Status)) {
2295 REPORT_STATUS_CODE (
2296 EFI_ERROR_CODE | EFI_ERROR_MINOR,
2297 (EFI_IO_BUS_ATA_ATAPI | EFI_IOB_ATA_BUS_SMART_DISABLED)
2298 );
2299 return EFI_DEVICE_ERROR;
2300 }
2301
2302 REPORT_STATUS_CODE (
2303 EFI_PROGRESS_CODE,
2304 (EFI_IO_BUS_ATA_ATAPI | EFI_IOB_ATA_BUS_SMART_ENABLE)
2305 );
2306
2307 LBAMid = IdeReadPortB (Instance->PciIo, Instance->IdeRegisters[Channel].CylinderLsb);
2308 LBAHigh = IdeReadPortB (Instance->PciIo, Instance->IdeRegisters[Channel].CylinderMsb);
2309
2310 if ((LBAMid == 0x4f) && (LBAHigh == 0xc2)) {
2311 //
2312 // The threshold exceeded condition is not detected by the device
2313 //
2314 DEBUG ((EFI_D_INFO, "The S.M.A.R.T threshold exceeded condition is not detected\n"));
2315 REPORT_STATUS_CODE (
2316 EFI_PROGRESS_CODE,
2317 (EFI_IO_BUS_ATA_ATAPI | EFI_IOB_ATA_BUS_SMART_UNDERTHRESHOLD)
2318 );
2319 } else if ((LBAMid == 0xf4) && (LBAHigh == 0x2c)) {
2320 //
2321 // The threshold exceeded condition is detected by the device
2322 //
2323 DEBUG ((EFI_D_INFO, "The S.M.A.R.T threshold exceeded condition is detected\n"));
2324 REPORT_STATUS_CODE (
2325 EFI_PROGRESS_CODE,
2326 (EFI_IO_BUS_ATA_ATAPI | EFI_IOB_ATA_BUS_SMART_OVERTHRESHOLD)
2327 );
2328 }
2329
2330 return EFI_SUCCESS;
2331 }
2332
2333 /**
2334 Enable SMART command of the disk if supported.
2335
2336 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2337 @param Channel The channel number of device.
2338 @param Device The device number of device.
2339 @param IdentifyData A pointer to data buffer which is used to contain IDENTIFY data.
2340 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
2341
2342 **/
2343 VOID
2344 EFIAPI
IdeAtaSmartSupport(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 Channel,IN UINT8 Device,IN EFI_IDENTIFY_DATA * IdentifyData,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)2345 IdeAtaSmartSupport (
2346 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2347 IN UINT8 Channel,
2348 IN UINT8 Device,
2349 IN EFI_IDENTIFY_DATA *IdentifyData,
2350 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
2351 )
2352 {
2353 EFI_STATUS Status;
2354 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2355
2356 //
2357 // Detect if the device supports S.M.A.R.T.
2358 //
2359 if ((IdentifyData->AtaData.command_set_supported_82 & 0x0001) != 0x0001) {
2360 //
2361 // S.M.A.R.T is not supported by the device
2362 //
2363 DEBUG ((EFI_D_INFO, "S.M.A.R.T feature is not supported at [%a] channel [%a] device!\n",
2364 (Channel == 1) ? "secondary" : "primary", (Device == 1) ? "slave" : "master"));
2365 REPORT_STATUS_CODE (
2366 EFI_ERROR_CODE | EFI_ERROR_MINOR,
2367 (EFI_IO_BUS_ATA_ATAPI | EFI_IOB_ATA_BUS_SMART_NOTSUPPORTED)
2368 );
2369 } else {
2370 //
2371 // Check if the feature is enabled. If not, then enable S.M.A.R.T.
2372 //
2373 if ((IdentifyData->AtaData.command_set_feature_enb_85 & 0x0001) != 0x0001) {
2374
2375 REPORT_STATUS_CODE (
2376 EFI_PROGRESS_CODE,
2377 (EFI_IO_BUS_ATA_ATAPI | EFI_IOB_ATA_BUS_SMART_DISABLE)
2378 );
2379
2380 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2381
2382 AtaCommandBlock.AtaCommand = ATA_CMD_SMART;
2383 AtaCommandBlock.AtaFeatures = ATA_SMART_ENABLE_OPERATION;
2384 AtaCommandBlock.AtaCylinderLow = ATA_CONSTANT_4F;
2385 AtaCommandBlock.AtaCylinderHigh = ATA_CONSTANT_C2;
2386 AtaCommandBlock.AtaDeviceHead = (UINT8) ((Device << 0x4) | 0xe0);
2387
2388 //
2389 // Send S.M.A.R.T Enable command to device
2390 //
2391 Status = AtaNonDataCommandIn (
2392 Instance->PciIo,
2393 &Instance->IdeRegisters[Channel],
2394 &AtaCommandBlock,
2395 AtaStatusBlock,
2396 ATA_ATAPI_TIMEOUT,
2397 NULL
2398 );
2399
2400 if (!EFI_ERROR (Status)) {
2401 //
2402 // Send S.M.A.R.T AutoSave command to device
2403 //
2404 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2405
2406 AtaCommandBlock.AtaCommand = ATA_CMD_SMART;
2407 AtaCommandBlock.AtaFeatures = 0xD2;
2408 AtaCommandBlock.AtaSectorCount = 0xF1;
2409 AtaCommandBlock.AtaCylinderLow = ATA_CONSTANT_4F;
2410 AtaCommandBlock.AtaCylinderHigh = ATA_CONSTANT_C2;
2411 AtaCommandBlock.AtaDeviceHead = (UINT8) ((Device << 0x4) | 0xe0);
2412
2413 Status = AtaNonDataCommandIn (
2414 Instance->PciIo,
2415 &Instance->IdeRegisters[Channel],
2416 &AtaCommandBlock,
2417 AtaStatusBlock,
2418 ATA_ATAPI_TIMEOUT,
2419 NULL
2420 );
2421 if (!EFI_ERROR (Status)) {
2422 Status = IdeAtaSmartReturnStatusCheck (
2423 Instance,
2424 Channel,
2425 Device,
2426 AtaStatusBlock
2427 );
2428 }
2429 }
2430 }
2431
2432 DEBUG ((EFI_D_INFO, "Enabled S.M.A.R.T feature at [%a] channel [%a] device!\n",
2433 (Channel == 1) ? "secondary" : "primary", (Device == 1) ? "slave" : "master"));
2434
2435 }
2436
2437 return ;
2438 }
2439
2440
2441 /**
2442 Sends out an ATA Identify Command to the specified device.
2443
2444 This function is called by DiscoverIdeDevice() during its device
2445 identification. It sends out the ATA Identify Command to the
2446 specified device. Only ATA device responses to this command. If
2447 the command succeeds, it returns the Identify data structure which
2448 contains information about the device. This function extracts the
2449 information it needs to fill the IDE_BLK_IO_DEV data structure,
2450 including device type, media block size, media capacity, and etc.
2451
2452 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2453 @param Channel The channel number of device.
2454 @param Device The device number of device.
2455 @param Buffer A pointer to data buffer which is used to contain IDENTIFY data.
2456 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
2457
2458 @retval EFI_SUCCESS Identify ATA device successfully.
2459 @retval EFI_DEVICE_ERROR ATA Identify Device Command failed or device is not ATA device.
2460 @retval EFI_OUT_OF_RESOURCES Allocate memory failed.
2461
2462 **/
2463 EFI_STATUS
2464 EFIAPI
AtaIdentify(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 Channel,IN UINT8 Device,IN OUT EFI_IDENTIFY_DATA * Buffer,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)2465 AtaIdentify (
2466 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2467 IN UINT8 Channel,
2468 IN UINT8 Device,
2469 IN OUT EFI_IDENTIFY_DATA *Buffer,
2470 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
2471 )
2472 {
2473 EFI_STATUS Status;
2474 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2475
2476 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2477
2478 AtaCommandBlock.AtaCommand = ATA_CMD_IDENTIFY_DRIVE;
2479 AtaCommandBlock.AtaDeviceHead = (UINT8)(Device << 0x4);
2480
2481 Status = AtaPioDataInOut (
2482 Instance->PciIo,
2483 &Instance->IdeRegisters[Channel],
2484 Buffer,
2485 sizeof (EFI_IDENTIFY_DATA),
2486 TRUE,
2487 &AtaCommandBlock,
2488 AtaStatusBlock,
2489 ATA_ATAPI_TIMEOUT,
2490 NULL
2491 );
2492
2493 return Status;
2494 }
2495
2496 /**
2497 This function is called by DiscoverIdeDevice() during its device
2498 identification.
2499 Its main purpose is to get enough information for the device media
2500 to fill in the Media data structure of the Block I/O Protocol interface.
2501
2502 There are 5 steps to reach such objective:
2503 1. Sends out the ATAPI Identify Command to the specified device.
2504 Only ATAPI device responses to this command. If the command succeeds,
2505 it returns the Identify data structure which filled with information
2506 about the device. Since the ATAPI device contains removable media,
2507 the only meaningful information is the device module name.
2508 2. Sends out ATAPI Inquiry Packet Command to the specified device.
2509 This command will return inquiry data of the device, which contains
2510 the device type information.
2511 3. Allocate sense data space for future use. We don't detect the media
2512 presence here to improvement boot performance, especially when CD
2513 media is present. The media detection will be performed just before
2514 each BLK_IO read/write
2515
2516 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2517 @param Channel The channel number of device.
2518 @param Device The device number of device.
2519 @param Buffer A pointer to data buffer which is used to contain IDENTIFY data.
2520 @param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
2521
2522 @retval EFI_SUCCESS Identify ATAPI device successfully.
2523 @retval EFI_DEVICE_ERROR ATA Identify Packet Device Command failed or device type
2524 is not supported by this IDE driver.
2525 @retval EFI_OUT_OF_RESOURCES Allocate memory failed.
2526
2527 **/
2528 EFI_STATUS
2529 EFIAPI
AtaIdentifyPacket(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 Channel,IN UINT8 Device,IN OUT EFI_IDENTIFY_DATA * Buffer,IN OUT EFI_ATA_STATUS_BLOCK * AtaStatusBlock)2530 AtaIdentifyPacket (
2531 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2532 IN UINT8 Channel,
2533 IN UINT8 Device,
2534 IN OUT EFI_IDENTIFY_DATA *Buffer,
2535 IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
2536 )
2537 {
2538 EFI_STATUS Status;
2539 EFI_ATA_COMMAND_BLOCK AtaCommandBlock;
2540
2541 ZeroMem (&AtaCommandBlock, sizeof (EFI_ATA_COMMAND_BLOCK));
2542
2543 AtaCommandBlock.AtaCommand = ATA_CMD_IDENTIFY_DEVICE;
2544 AtaCommandBlock.AtaDeviceHead = (UINT8)(Device << 0x4);
2545
2546 //
2547 // Send ATAPI Identify Command to get IDENTIFY data.
2548 //
2549 Status = AtaPioDataInOut (
2550 Instance->PciIo,
2551 &Instance->IdeRegisters[Channel],
2552 (VOID *) Buffer,
2553 sizeof (EFI_IDENTIFY_DATA),
2554 TRUE,
2555 &AtaCommandBlock,
2556 AtaStatusBlock,
2557 ATA_ATAPI_TIMEOUT,
2558 NULL
2559 );
2560
2561 return Status;
2562 }
2563
2564
2565 /**
2566 This function is used for detect whether the IDE device exists in the
2567 specified Channel as the specified Device Number.
2568
2569 There is two IDE channels: one is Primary Channel, the other is
2570 Secondary Channel.(Channel is the logical name for the physical "Cable".)
2571 Different channel has different register group.
2572
2573 On each IDE channel, at most two IDE devices attach,
2574 one is called Device 0 (Master device), the other is called Device 1
2575 (Slave device). The devices on the same channel co-use the same register
2576 group, so before sending out a command for a specified device via command
2577 register, it is a must to select the current device to accept the command
2578 by set the device number in the Head/Device Register.
2579
2580 @param Instance A pointer to ATA_ATAPI_PASS_THRU_INSTANCE data structure.
2581 @param IdeChannel The channel number of device.
2582
2583 @retval EFI_SUCCESS successfully detects device.
2584 @retval other any failure during detection process will return this value.
2585
2586 **/
2587 EFI_STATUS
2588 EFIAPI
DetectAndConfigIdeDevice(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance,IN UINT8 IdeChannel)2589 DetectAndConfigIdeDevice (
2590 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance,
2591 IN UINT8 IdeChannel
2592 )
2593 {
2594 EFI_STATUS Status;
2595 UINT8 SectorCountReg;
2596 UINT8 LBALowReg;
2597 UINT8 LBAMidReg;
2598 UINT8 LBAHighReg;
2599 EFI_ATA_DEVICE_TYPE DeviceType;
2600 UINT8 IdeDevice;
2601 EFI_IDE_REGISTERS *IdeRegisters;
2602 EFI_IDENTIFY_DATA Buffer;
2603
2604 EFI_IDE_CONTROLLER_INIT_PROTOCOL *IdeInit;
2605 EFI_PCI_IO_PROTOCOL *PciIo;
2606
2607 EFI_ATA_COLLECTIVE_MODE *SupportedModes;
2608 EFI_ATA_TRANSFER_MODE TransferMode;
2609 EFI_ATA_DRIVE_PARMS DriveParameters;
2610
2611 IdeRegisters = &Instance->IdeRegisters[IdeChannel];
2612 IdeInit = Instance->IdeControllerInit;
2613 PciIo = Instance->PciIo;
2614
2615 for (IdeDevice = 0; IdeDevice < EfiIdeMaxDevice; IdeDevice++) {
2616 //
2617 // Select Master or Slave device to get the return signature for ATA DEVICE DIAGNOSTIC cmd.
2618 //
2619 IdeWritePortB (PciIo, IdeRegisters->Head, (UINT8)((IdeDevice << 4) | 0xe0));
2620
2621 //
2622 // Send ATA Device Execut Diagnostic command.
2623 // This command should work no matter DRDY is ready or not
2624 //
2625 IdeWritePortB (PciIo, IdeRegisters->CmdOrStatus, ATA_CMD_EXEC_DRIVE_DIAG);
2626
2627 Status = WaitForBSYClear (PciIo, IdeRegisters, 350000000);
2628 if (EFI_ERROR (Status)) {
2629 DEBUG((EFI_D_ERROR, "New detecting method: Send Execute Diagnostic Command: WaitForBSYClear: Status: %d\n", Status));
2630 continue;
2631 }
2632
2633 //
2634 // Select Master or Slave device to get the return signature for ATA DEVICE DIAGNOSTIC cmd.
2635 //
2636 IdeWritePortB (PciIo, IdeRegisters->Head, (UINT8)((IdeDevice << 4) | 0xe0));
2637 //
2638 // Stall for 1 milliseconds.
2639 //
2640 MicroSecondDelay (1000);
2641
2642 SectorCountReg = IdeReadPortB (PciIo, IdeRegisters->SectorCount);
2643 LBALowReg = IdeReadPortB (PciIo, IdeRegisters->SectorNumber);
2644 LBAMidReg = IdeReadPortB (PciIo, IdeRegisters->CylinderLsb);
2645 LBAHighReg = IdeReadPortB (PciIo, IdeRegisters->CylinderMsb);
2646
2647 //
2648 // Refer to ATA/ATAPI 4 Spec, section 9.1
2649 //
2650 if ((SectorCountReg == 0x1) && (LBALowReg == 0x1) && (LBAMidReg == 0x0) && (LBAHighReg == 0x0)) {
2651 DeviceType = EfiIdeHarddisk;
2652 } else if ((LBAMidReg == 0x14) && (LBAHighReg == 0xeb)) {
2653 DeviceType = EfiIdeCdrom;
2654 } else {
2655 continue;
2656 }
2657
2658 //
2659 // Send IDENTIFY cmd to the device to test if it is really attached.
2660 //
2661 if (DeviceType == EfiIdeHarddisk) {
2662 Status = AtaIdentify (Instance, IdeChannel, IdeDevice, &Buffer, NULL);
2663 //
2664 // if identifying ata device is failure, then try to send identify packet cmd.
2665 //
2666 if (EFI_ERROR (Status)) {
2667 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, (EFI_PERIPHERAL_FIXED_MEDIA | EFI_P_EC_NOT_DETECTED));
2668
2669 DeviceType = EfiIdeCdrom;
2670 Status = AtaIdentifyPacket (Instance, IdeChannel, IdeDevice, &Buffer, NULL);
2671 }
2672 } else {
2673 Status = AtaIdentifyPacket (Instance, IdeChannel, IdeDevice, &Buffer, NULL);
2674 //
2675 // if identifying atapi device is failure, then try to send identify cmd.
2676 //
2677 if (EFI_ERROR (Status)) {
2678 DeviceType = EfiIdeHarddisk;
2679 Status = AtaIdentify (Instance, IdeChannel, IdeDevice, &Buffer, NULL);
2680 }
2681 }
2682
2683 if (EFI_ERROR (Status)) {
2684 //
2685 // No device is found at this port
2686 //
2687 continue;
2688 }
2689
2690 DEBUG ((EFI_D_INFO, "[%a] channel [%a] [%a] device\n",
2691 (IdeChannel == 1) ? "secondary" : "primary ", (IdeDevice == 1) ? "slave " : "master",
2692 DeviceType == EfiIdeCdrom ? "cdrom " : "harddisk"));
2693 //
2694 // If the device is a hard disk, then try to enable S.M.A.R.T feature
2695 //
2696 if ((DeviceType == EfiIdeHarddisk) && PcdGetBool (PcdAtaSmartEnable)) {
2697 IdeAtaSmartSupport (
2698 Instance,
2699 IdeChannel,
2700 IdeDevice,
2701 &Buffer,
2702 NULL
2703 );
2704 }
2705
2706 //
2707 // Submit identify data to IDE controller init driver
2708 //
2709 IdeInit->SubmitData (IdeInit, IdeChannel, IdeDevice, &Buffer);
2710
2711 //
2712 // Now start to config ide device parameter and transfer mode.
2713 //
2714 Status = IdeInit->CalculateMode (
2715 IdeInit,
2716 IdeChannel,
2717 IdeDevice,
2718 &SupportedModes
2719 );
2720 if (EFI_ERROR (Status)) {
2721 DEBUG ((EFI_D_ERROR, "Calculate Mode Fail, Status = %r\n", Status));
2722 continue;
2723 }
2724
2725 //
2726 // Set best supported PIO mode on this IDE device
2727 //
2728 if (SupportedModes->PioMode.Mode <= EfiAtaPioMode2) {
2729 TransferMode.ModeCategory = EFI_ATA_MODE_DEFAULT_PIO;
2730 } else {
2731 TransferMode.ModeCategory = EFI_ATA_MODE_FLOW_PIO;
2732 }
2733
2734 TransferMode.ModeNumber = (UINT8) (SupportedModes->PioMode.Mode);
2735
2736 if (SupportedModes->ExtModeCount == 0){
2737 Status = SetDeviceTransferMode (Instance, IdeChannel, IdeDevice, &TransferMode, NULL);
2738
2739 if (EFI_ERROR (Status)) {
2740 DEBUG ((EFI_D_ERROR, "Set transfer Mode Fail, Status = %r\n", Status));
2741 continue;
2742 }
2743 }
2744
2745 //
2746 // Set supported DMA mode on this IDE device. Note that UDMA & MDMA cann't
2747 // be set together. Only one DMA mode can be set to a device. If setting
2748 // DMA mode operation fails, we can continue moving on because we only use
2749 // PIO mode at boot time. DMA modes are used by certain kind of OS booting
2750 //
2751 if (SupportedModes->UdmaMode.Valid) {
2752 TransferMode.ModeCategory = EFI_ATA_MODE_UDMA;
2753 TransferMode.ModeNumber = (UINT8) (SupportedModes->UdmaMode.Mode);
2754 Status = SetDeviceTransferMode (Instance, IdeChannel, IdeDevice, &TransferMode, NULL);
2755
2756 if (EFI_ERROR (Status)) {
2757 DEBUG ((EFI_D_ERROR, "Set transfer Mode Fail, Status = %r\n", Status));
2758 continue;
2759 }
2760 } else if (SupportedModes->MultiWordDmaMode.Valid) {
2761 TransferMode.ModeCategory = EFI_ATA_MODE_MDMA;
2762 TransferMode.ModeNumber = (UINT8) SupportedModes->MultiWordDmaMode.Mode;
2763 Status = SetDeviceTransferMode (Instance, IdeChannel, IdeDevice, &TransferMode, NULL);
2764
2765 if (EFI_ERROR (Status)) {
2766 DEBUG ((EFI_D_ERROR, "Set transfer Mode Fail, Status = %r\n", Status));
2767 continue;
2768 }
2769 }
2770
2771 //
2772 // Set Parameters for the device:
2773 // 1) Init
2774 // 2) Establish the block count for READ/WRITE MULTIPLE (EXT) command
2775 //
2776 if (DeviceType == EfiIdeHarddisk) {
2777 //
2778 // Init driver parameters
2779 //
2780 DriveParameters.Sector = (UINT8) ((ATA5_IDENTIFY_DATA *)(&Buffer.AtaData))->sectors_per_track;
2781 DriveParameters.Heads = (UINT8) (((ATA5_IDENTIFY_DATA *)(&Buffer.AtaData))->heads - 1);
2782 DriveParameters.MultipleSector = (UINT8) ((ATA5_IDENTIFY_DATA *)(&Buffer.AtaData))->multi_sector_cmd_max_sct_cnt;
2783
2784 Status = SetDriveParameters (Instance, IdeChannel, IdeDevice, &DriveParameters, NULL);
2785 }
2786
2787 //
2788 // Set IDE controller Timing Blocks in the PCI Configuration Space
2789 //
2790 IdeInit->SetTiming (IdeInit, IdeChannel, IdeDevice, SupportedModes);
2791
2792 //
2793 // IDE controller and IDE device timing is configured successfully.
2794 // Now insert the device into device list.
2795 //
2796 Status = CreateNewDeviceInfo (Instance, IdeChannel, IdeDevice, DeviceType, &Buffer);
2797 if (EFI_ERROR (Status)) {
2798 continue;
2799 }
2800
2801 if (DeviceType == EfiIdeHarddisk) {
2802 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, (EFI_PERIPHERAL_FIXED_MEDIA | EFI_P_PC_ENABLE));
2803 }
2804 }
2805 return EFI_SUCCESS;
2806 }
2807
2808
2809 /**
2810 Initialize ATA host controller at IDE mode.
2811
2812 The function is designed to initialize ATA host controller.
2813
2814 @param[in] Instance A pointer to the ATA_ATAPI_PASS_THRU_INSTANCE instance.
2815
2816 **/
2817 EFI_STATUS
2818 EFIAPI
IdeModeInitialization(IN ATA_ATAPI_PASS_THRU_INSTANCE * Instance)2819 IdeModeInitialization (
2820 IN ATA_ATAPI_PASS_THRU_INSTANCE *Instance
2821 )
2822 {
2823 EFI_STATUS Status;
2824 EFI_IDE_CONTROLLER_INIT_PROTOCOL *IdeInit;
2825 EFI_PCI_IO_PROTOCOL *PciIo;
2826 UINT8 Channel;
2827 UINT8 IdeChannel;
2828 BOOLEAN ChannelEnabled;
2829 UINT8 MaxDevices;
2830
2831 IdeInit = Instance->IdeControllerInit;
2832 PciIo = Instance->PciIo;
2833 Channel = IdeInit->ChannelCount;
2834
2835 //
2836 // Obtain IDE IO port registers' base addresses
2837 //
2838 Status = GetIdeRegisterIoAddr (PciIo, Instance->IdeRegisters);
2839 if (EFI_ERROR (Status)) {
2840 goto ErrorExit;
2841 }
2842
2843 for (IdeChannel = 0; IdeChannel < Channel; IdeChannel++) {
2844 IdeInit->NotifyPhase (IdeInit, EfiIdeBeforeChannelEnumeration, IdeChannel);
2845
2846 //
2847 // now obtain channel information fron IdeControllerInit protocol.
2848 //
2849 Status = IdeInit->GetChannelInfo (
2850 IdeInit,
2851 IdeChannel,
2852 &ChannelEnabled,
2853 &MaxDevices
2854 );
2855 if (EFI_ERROR (Status)) {
2856 DEBUG ((EFI_D_ERROR, "[GetChannel, Status=%x]", Status));
2857 continue;
2858 }
2859
2860 if (!ChannelEnabled) {
2861 continue;
2862 }
2863
2864 ASSERT (MaxDevices <= 2);
2865 //
2866 // Now inform the IDE Controller Init Module.
2867 //
2868 IdeInit->NotifyPhase (IdeInit, EfiIdeBeforeChannelReset, IdeChannel);
2869
2870 //
2871 // No reset channel function implemented.
2872 //
2873 IdeInit->NotifyPhase (IdeInit, EfiIdeAfterChannelReset, IdeChannel);
2874
2875 //
2876 // Now inform the IDE Controller Init Module.
2877 //
2878 IdeInit->NotifyPhase (IdeInit, EfiIdeBusBeforeDevicePresenceDetection, IdeChannel);
2879
2880 //
2881 // Detect all attached ATA devices and set the transfer mode for each device.
2882 //
2883 DetectAndConfigIdeDevice (Instance, IdeChannel);
2884 }
2885
2886 //
2887 // All configurations done! Notify IdeController to do post initialization
2888 // work such as saving IDE controller PCI settings for S3 resume
2889 //
2890 IdeInit->NotifyPhase (IdeInit, EfiIdeBusPhaseMaximum, 0);
2891
2892 ErrorExit:
2893 return Status;
2894 }
2895
2896