1 /** @file 2 This file contains all helper functions on the ATAPI command 3 4 Copyright (c) 2006 - 2010, 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 "IdeBus.h" 16 17 /** 18 This function is used to get the current status of the media residing 19 in the LS-120 drive or ZIP drive. The media status is returned in the 20 Error Status. 21 22 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 23 to record all the information of the IDE device. 24 25 @retval EFI_SUCCESS The media status is achieved successfully and the media 26 can be read/written. 27 @retval EFI_DEVICE_ERROR Get Media Status Command is failed. 28 @retval EFI_NO_MEDIA There is no media in the drive. 29 @retval EFI_WRITE_PROTECTED The media is writing protected. 30 31 @note This function must be called after the LS120EnableMediaStatus() 32 with second parameter set to TRUE 33 (means enable media status notification) is called. 34 **/ 35 EFI_STATUS 36 LS120GetMediaStatus ( 37 IN IDE_BLK_IO_DEV *IdeDev 38 ) 39 { 40 UINT8 DeviceSelect; 41 UINT8 StatusValue; 42 EFI_STATUS EfiStatus; 43 // 44 // Poll Alternate Register for BSY clear within timeout. 45 // 46 EfiStatus = WaitForBSYClear2 (IdeDev, ATATIMEOUT); 47 if (EFI_ERROR (EfiStatus)) { 48 return EFI_DEVICE_ERROR; 49 } 50 51 // 52 // Select device via Device/Head Register. 53 // 54 DeviceSelect = (UINT8) ((IdeDev->Device) << 4 | 0xe0); 55 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Head, DeviceSelect); 56 57 // 58 // Poll Alternate Register for DRDY set within timeout. 59 // After device is selected, DRDY set indicates the device is ready to 60 // accept command. 61 // 62 EfiStatus = DRDYReady2 (IdeDev, ATATIMEOUT); 63 if (EFI_ERROR (EfiStatus)) { 64 return EFI_DEVICE_ERROR; 65 } 66 67 // 68 // Get Media Status Command is sent 69 // 70 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Command, 0xDA); 71 72 // 73 // BSY bit will clear after command is complete. 74 // 75 EfiStatus = WaitForBSYClear2 (IdeDev, ATATIMEOUT); 76 if (EFI_ERROR (EfiStatus)) { 77 return EFI_DEVICE_ERROR; 78 } 79 80 // 81 // the media status is returned by the command in the ERROR register 82 // 83 StatusValue = IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->Reg1.Error); 84 85 if ((StatusValue & BIT1) != 0) { 86 return EFI_NO_MEDIA; 87 } 88 89 if ((StatusValue & BIT6) != 0) { 90 return EFI_WRITE_PROTECTED; 91 } else { 92 return EFI_SUCCESS; 93 } 94 } 95 /** 96 This function is used to send Enable Media Status Notification Command 97 or Disable Media Status Notification Command. 98 99 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 100 to record all the information of the IDE device. 101 102 @param Enable a flag that indicates whether enable or disable media 103 status notification. 104 @retval EFI_SUCCESS If command completes successfully. 105 @retval EFI_DEVICE_ERROR If command failed. 106 **/ 107 EFI_STATUS 108 LS120EnableMediaStatus ( 109 IN IDE_BLK_IO_DEV *IdeDev, 110 IN BOOLEAN Enable 111 ) 112 { 113 UINT8 DeviceSelect; 114 EFI_STATUS Status; 115 116 // 117 // Poll Alternate Register for BSY clear within timeout. 118 // 119 Status = WaitForBSYClear2 (IdeDev, ATATIMEOUT); 120 if (EFI_ERROR (Status)) { 121 return EFI_DEVICE_ERROR; 122 } 123 124 // 125 // Select device via Device/Head Register. 126 // 127 DeviceSelect = (UINT8) ((IdeDev->Device) << 4 | 0xe0); 128 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Head, DeviceSelect); 129 130 // 131 // Poll Alternate Register for DRDY set within timeout. 132 // After device is selected, DRDY set indicates the device is ready to 133 // accept command. 134 // 135 Status = DRDYReady2 (IdeDev, ATATIMEOUT); 136 if (EFI_ERROR (Status)) { 137 return EFI_DEVICE_ERROR; 138 } 139 140 if (Enable) { 141 // 142 // 0x95: Enable media status notification 143 // 144 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg1.Feature, 0x95); 145 } else { 146 // 147 // 0x31: Disable media status notification 148 // 149 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg1.Feature, 0x31); 150 } 151 // 152 // Set Feature Command is sent 153 // 154 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Command, 0xEF); 155 156 // 157 // BSY bit will clear after command is complete. 158 // 159 Status = WaitForBSYClear (IdeDev, ATATIMEOUT); 160 if (EFI_ERROR (Status)) { 161 return EFI_DEVICE_ERROR; 162 } 163 164 return EFI_SUCCESS; 165 } 166 /** 167 This function reads the pending data in the device. 168 169 @param IdeDev Indicates the calling context. 170 171 @retval EFI_SUCCESS Successfully read. 172 @retval EFI_NOT_READY The BSY is set avoiding reading. 173 174 **/ 175 EFI_STATUS 176 AtapiReadPendingData ( 177 IN IDE_BLK_IO_DEV *IdeDev 178 ) 179 { 180 UINT8 AltRegister; 181 UINT16 TempWordBuffer; 182 183 AltRegister = IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->Alt.AltStatus); 184 if ((AltRegister & ATA_STSREG_BSY) == ATA_STSREG_BSY) { 185 return EFI_NOT_READY; 186 } 187 if ((AltRegister & (ATA_STSREG_BSY | ATA_STSREG_DRQ)) == ATA_STSREG_DRQ) { 188 TempWordBuffer = IDEReadPortB (IdeDev->PciIo,IdeDev->IoPort->Alt.AltStatus); 189 while ((TempWordBuffer & (ATA_STSREG_BSY | ATA_STSREG_DRQ)) == ATA_STSREG_DRQ) { 190 IDEReadPortWMultiple ( 191 IdeDev->PciIo, 192 IdeDev->IoPort->Data, 193 1, 194 &TempWordBuffer 195 ); 196 TempWordBuffer = IDEReadPortB (IdeDev->PciIo,IdeDev->IoPort->Alt.AltStatus); 197 } 198 } 199 return EFI_SUCCESS; 200 } 201 202 /** 203 This function is called by either AtapiPacketCommandIn() or AtapiPacketCommandOut(). 204 It is used to transfer data between host and device. The data direction is specified 205 by the fourth parameter. 206 207 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used to record 208 all the information of the IDE device. 209 @param Buffer buffer contained data transferred between host and device. 210 @param ByteCount data size in byte unit of the buffer. 211 @param Read flag used to determine the data transfer direction. 212 Read equals 1, means data transferred from device to host; 213 Read equals 0, means data transferred from host to device. 214 @param TimeOut timeout value for wait DRQ ready before each data stream's transfer. 215 216 @retval EFI_SUCCESS data is transferred successfully. 217 @retval EFI_DEVICE_ERROR the device failed to transfer data. 218 **/ 219 EFI_STATUS 220 PioReadWriteData ( 221 IN IDE_BLK_IO_DEV *IdeDev, 222 IN UINT16 *Buffer, 223 IN UINT32 ByteCount, 224 IN BOOLEAN Read, 225 IN UINTN TimeOut 226 ) 227 { 228 // 229 // required transfer data in word unit. 230 // 231 UINT32 RequiredWordCount; 232 233 // 234 // actual transfer data in word unit. 235 // 236 UINT32 ActualWordCount; 237 UINT32 WordCount; 238 EFI_STATUS Status; 239 UINT16 *PtrBuffer; 240 241 // 242 // No data transfer is premitted. 243 // 244 if (ByteCount == 0) { 245 return EFI_SUCCESS; 246 } 247 // 248 // for performance, we assert the ByteCount is an even number 249 // which is actually a resonable assumption 250 ASSERT((ByteCount%2) == 0); 251 252 PtrBuffer = Buffer; 253 RequiredWordCount = ByteCount / 2; 254 // 255 // ActuralWordCount means the word count of data really transferred. 256 // 257 ActualWordCount = 0; 258 259 while (ActualWordCount < RequiredWordCount) { 260 261 // 262 // before each data transfer stream, the host should poll DRQ bit ready, 263 // to see whether indicates device is ready to transfer data. 264 // 265 Status = DRQReady2 (IdeDev, TimeOut); 266 if (EFI_ERROR (Status)) { 267 return CheckErrorStatus (IdeDev); 268 } 269 270 // 271 // read Status Register will clear interrupt 272 // 273 IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Status); 274 275 // 276 // get current data transfer size from Cylinder Registers. 277 // 278 WordCount = IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->CylinderMsb) << 8; 279 WordCount = WordCount | IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->CylinderLsb); 280 WordCount = WordCount & 0xffff; 281 WordCount /= 2; 282 283 WordCount = MIN (WordCount, (RequiredWordCount - ActualWordCount)); 284 285 if (Read) { 286 IDEReadPortWMultiple ( 287 IdeDev->PciIo, 288 IdeDev->IoPort->Data, 289 WordCount, 290 PtrBuffer 291 ); 292 } else { 293 IDEWritePortWMultiple ( 294 IdeDev->PciIo, 295 IdeDev->IoPort->Data, 296 WordCount, 297 PtrBuffer 298 ); 299 } 300 301 PtrBuffer += WordCount; 302 ActualWordCount += WordCount; 303 } 304 305 if (Read) { 306 // 307 // In the case where the drive wants to send more data than we need to read, 308 // the DRQ bit will be set and cause delays from DRQClear2(). 309 // We need to read data from the drive until it clears DRQ so we can move on. 310 // 311 AtapiReadPendingData (IdeDev); 312 } 313 314 // 315 // After data transfer is completed, normally, DRQ bit should clear. 316 // 317 Status = DRQClear2 (IdeDev, ATAPITIMEOUT); 318 if (EFI_ERROR (Status)) { 319 return EFI_DEVICE_ERROR; 320 } 321 322 // 323 // read status register to check whether error happens. 324 // 325 return CheckErrorStatus (IdeDev); 326 } 327 328 /** 329 This function is used to send out ATAPI commands conforms to the Packet Command 330 with PIO Data In Protocol. 331 332 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 333 to record all the information of the IDE device. 334 @param Packet pointer pointing to ATAPI_PACKET_COMMAND data structure 335 which contains the contents of the command. 336 @param Buffer buffer contained data transferred from device to host. 337 @param ByteCount data size in byte unit of the buffer. 338 @param TimeOut this parameter is used to specify the timeout value for the 339 PioReadWriteData() function. 340 341 @retval EFI_SUCCESS send out the ATAPI packet command successfully 342 and device sends data successfully. 343 @retval EFI_DEVICE_ERROR the device failed to send data. 344 345 **/ 346 EFI_STATUS 347 AtapiPacketCommandIn ( 348 IN IDE_BLK_IO_DEV *IdeDev, 349 IN ATAPI_PACKET_COMMAND *Packet, 350 IN UINT16 *Buffer, 351 IN UINT32 ByteCount, 352 IN UINTN TimeOut 353 ) 354 { 355 UINT16 *CommandIndex; 356 EFI_STATUS Status; 357 UINT32 Count; 358 359 // 360 // Set all the command parameters by fill related registers. 361 // Before write to all the following registers, BSY and DRQ must be 0. 362 // 363 Status = DRQClear2 (IdeDev, ATAPITIMEOUT); 364 if (EFI_ERROR (Status)) { 365 return Status; 366 } 367 368 // 369 // Select device via Device/Head Register. 370 // 371 IDEWritePortB ( 372 IdeDev->PciIo, 373 IdeDev->IoPort->Head, 374 (UINT8) ((IdeDev->Device << 4) | ATA_DEFAULT_CMD) // DEFAULT_CMD: 0xa0 (1010,0000) 375 ); 376 377 // 378 // No OVL; No DMA 379 // 380 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg1.Feature, 0x00); 381 382 // 383 // set the transfersize to ATAPI_MAX_BYTE_COUNT to let the device 384 // determine how many data should be transferred. 385 // 386 IDEWritePortB ( 387 IdeDev->PciIo, 388 IdeDev->IoPort->CylinderLsb, 389 (UINT8) (ATAPI_MAX_BYTE_COUNT & 0x00ff) 390 ); 391 IDEWritePortB ( 392 IdeDev->PciIo, 393 IdeDev->IoPort->CylinderMsb, 394 (UINT8) (ATAPI_MAX_BYTE_COUNT >> 8) 395 ); 396 397 // 398 // ATA_DEFAULT_CTL:0x0a (0000,1010) 399 // Disable interrupt 400 // 401 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Alt.DeviceControl, ATA_DEFAULT_CTL); 402 403 // 404 // Send Packet command to inform device 405 // that the following data bytes are command packet. 406 // 407 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Command, ATA_CMD_PACKET); 408 409 Status = DRQReady (IdeDev, ATAPITIMEOUT); 410 if (EFI_ERROR (Status)) { 411 return Status; 412 } 413 414 // 415 // Send out command packet 416 // 417 CommandIndex = Packet->Data16; 418 for (Count = 0; Count < 6; Count++, CommandIndex++) { 419 420 IDEWritePortW (IdeDev->PciIo, IdeDev->IoPort->Data, *CommandIndex); 421 gBS->Stall (10); 422 } 423 424 // 425 // call PioReadWriteData() function to get 426 // requested transfer data form device. 427 // 428 return PioReadWriteData (IdeDev, Buffer, ByteCount, 1, TimeOut); 429 } 430 /** 431 This function is used to send out ATAPI commands conforms to the Packet Command 432 with PIO Data Out Protocol. 433 434 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 435 to record all the information of the IDE device. 436 @param Packet pointer pointing to ATAPI_PACKET_COMMAND data structure 437 which contains the contents of the command. 438 @param Buffer buffer contained data transferred from host to device. 439 @param ByteCount data size in byte unit of the buffer. 440 @param TimeOut this parameter is used to specify the timeout value 441 for the PioReadWriteData() function. 442 @retval EFI_SUCCESS send out the ATAPI packet command successfully 443 and device received data successfully. 444 @retval EFI_DEVICE_ERROR the device failed to send data. 445 446 **/ 447 EFI_STATUS 448 AtapiPacketCommandOut ( 449 IN IDE_BLK_IO_DEV *IdeDev, 450 IN ATAPI_PACKET_COMMAND *Packet, 451 IN UINT16 *Buffer, 452 IN UINT32 ByteCount, 453 IN UINTN TimeOut 454 ) 455 { 456 UINT16 *CommandIndex; 457 EFI_STATUS Status; 458 UINT32 Count; 459 460 // 461 // set all the command parameters 462 // Before write to all the following registers, BSY and DRQ must be 0. 463 // 464 Status = DRQClear2 (IdeDev, ATAPITIMEOUT); 465 if (EFI_ERROR (Status)) { 466 return Status; 467 } 468 469 // 470 // Select device via Device/Head Register. 471 // 472 IDEWritePortB ( 473 IdeDev->PciIo, 474 IdeDev->IoPort->Head, 475 (UINT8) ((IdeDev->Device << 4) | ATA_DEFAULT_CMD) // ATA_DEFAULT_CMD: 0xa0 (1010,0000) 476 ); 477 478 // 479 // No OVL; No DMA 480 // 481 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg1.Feature, 0x00); 482 483 // 484 // set the transfersize to ATAPI_MAX_BYTE_COUNT to 485 // let the device determine how many data should be transferred. 486 // 487 IDEWritePortB ( 488 IdeDev->PciIo, 489 IdeDev->IoPort->CylinderLsb, 490 (UINT8) (ATAPI_MAX_BYTE_COUNT & 0x00ff) 491 ); 492 IDEWritePortB ( 493 IdeDev->PciIo, 494 IdeDev->IoPort->CylinderMsb, 495 (UINT8) (ATAPI_MAX_BYTE_COUNT >> 8) 496 ); 497 498 // 499 // DEFAULT_CTL:0x0a (0000,1010) 500 // Disable interrupt 501 // 502 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Alt.DeviceControl, ATA_DEFAULT_CTL); 503 504 // 505 // Send Packet command to inform device 506 // that the following data bytes are command packet. 507 // 508 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Command, ATA_CMD_PACKET); 509 510 Status = DRQReady2 (IdeDev, ATAPITIMEOUT); 511 if (EFI_ERROR (Status)) { 512 return Status; 513 } 514 515 // 516 // Send out command packet 517 // 518 CommandIndex = Packet->Data16; 519 for (Count = 0; Count < 6; Count++, CommandIndex++) { 520 IDEWritePortW (IdeDev->PciIo, IdeDev->IoPort->Data, *CommandIndex); 521 gBS->Stall (10); 522 } 523 524 // 525 // call PioReadWriteData() function to send requested transfer data to device. 526 // 527 return PioReadWriteData (IdeDev, Buffer, ByteCount, 0, TimeOut); 528 } 529 /** 530 Sends out ATAPI Inquiry Packet Command to the specified device. This command will 531 return INQUIRY data of the device. 532 533 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 534 to record all the information of the IDE device. 535 536 @retval EFI_SUCCESS Inquiry command completes successfully. 537 @retval EFI_DEVICE_ERROR Inquiry command failed. 538 539 @note Parameter "IdeDev" will be updated in this function. 540 541 **/ 542 EFI_STATUS 543 AtapiInquiry ( 544 IN IDE_BLK_IO_DEV *IdeDev 545 ) 546 { 547 ATAPI_PACKET_COMMAND Packet; 548 EFI_STATUS Status; 549 ATAPI_INQUIRY_DATA *InquiryData; 550 551 // 552 // prepare command packet for the ATAPI Inquiry Packet Command. 553 // 554 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 555 Packet.Inquiry.opcode = ATA_CMD_INQUIRY; 556 Packet.Inquiry.page_code = 0; 557 Packet.Inquiry.allocation_length = (UINT8) sizeof (ATAPI_INQUIRY_DATA); 558 559 InquiryData = AllocatePool (sizeof (ATAPI_INQUIRY_DATA)); 560 if (InquiryData == NULL) { 561 return EFI_DEVICE_ERROR; 562 } 563 564 // 565 // Send command packet and get requested Inquiry data. 566 // 567 Status = AtapiPacketCommandIn ( 568 IdeDev, 569 &Packet, 570 (UINT16 *) InquiryData, 571 sizeof (ATAPI_INQUIRY_DATA), 572 ATAPITIMEOUT 573 ); 574 if (EFI_ERROR (Status)) { 575 gBS->FreePool (InquiryData); 576 return EFI_DEVICE_ERROR; 577 } 578 579 IdeDev->InquiryData = InquiryData; 580 581 return EFI_SUCCESS; 582 } 583 /** 584 This function is called by DiscoverIdeDevice() during its device 585 identification. 586 Its main purpose is to get enough information for the device media 587 to fill in the Media data structure of the Block I/O Protocol interface. 588 589 There are 5 steps to reach such objective: 590 1. Sends out the ATAPI Identify Command to the specified device. 591 Only ATAPI device responses to this command. If the command succeeds, 592 it returns the Identify data structure which filled with information 593 about the device. Since the ATAPI device contains removable media, 594 the only meaningful information is the device module name. 595 2. Sends out ATAPI Inquiry Packet Command to the specified device. 596 This command will return inquiry data of the device, which contains 597 the device type information. 598 3. Allocate sense data space for future use. We don't detect the media 599 presence here to improvement boot performance, especially when CD 600 media is present. The media detection will be performed just before 601 each BLK_IO read/write 602 603 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 604 to record all the information of the IDE device. 605 606 @retval EFI_SUCCESS Identify ATAPI device successfully. 607 @retval EFI_DEVICE_ERROR ATAPI Identify Device Command failed or device type 608 is not supported by this IDE driver. 609 @retval EFI_OUT_OF_RESOURCES Allocate memory for sense data failed 610 611 @note Parameter "IdeDev" will be updated in this function. 612 **/ 613 EFI_STATUS 614 ATAPIIdentify ( 615 IN IDE_BLK_IO_DEV *IdeDev 616 ) 617 { 618 EFI_IDENTIFY_DATA *AtapiIdentifyPointer; 619 UINT8 DeviceSelect; 620 EFI_STATUS Status; 621 622 // 623 // device select bit 624 // 625 DeviceSelect = (UINT8) ((IdeDev->Device) << 4); 626 627 AtapiIdentifyPointer = AllocatePool (sizeof (EFI_IDENTIFY_DATA)); 628 if (AtapiIdentifyPointer == NULL) { 629 return EFI_OUT_OF_RESOURCES; 630 } 631 // 632 // Send ATAPI Identify Command to get IDENTIFY data. 633 // 634 Status = AtaPioDataIn ( 635 IdeDev, 636 (VOID *) AtapiIdentifyPointer, 637 sizeof (EFI_IDENTIFY_DATA), 638 ATA_CMD_IDENTIFY_DEVICE, 639 DeviceSelect, 640 0, 641 0, 642 0, 643 0 644 ); 645 646 if (EFI_ERROR (Status)) { 647 gBS->FreePool (AtapiIdentifyPointer); 648 return EFI_DEVICE_ERROR; 649 } 650 651 IdeDev->IdData = AtapiIdentifyPointer; 652 PrintAtaModuleName (IdeDev); 653 654 // 655 // Send ATAPI Inquiry Packet Command to get INQUIRY data. 656 // 657 Status = AtapiInquiry (IdeDev); 658 if (EFI_ERROR (Status)) { 659 gBS->FreePool (IdeDev->IdData); 660 // 661 // Make sure the pIdData will not be freed again. 662 // 663 IdeDev->IdData = NULL; 664 return EFI_DEVICE_ERROR; 665 } 666 // 667 // Get media removable info from INQUIRY data. 668 // 669 IdeDev->BlkIo.Media->RemovableMedia = (UINT8) ((IdeDev->InquiryData->RMB & 0x80) == 0x80); 670 671 // 672 // Identify device type via INQUIRY data. 673 // 674 switch (IdeDev->InquiryData->peripheral_type & 0x1f) { 675 676 // 677 // Magnetic Disk 678 // 679 case 0x00: 680 681 // 682 // device is LS120 or ZIP drive. 683 // 684 IdeDev->Type = IdeMagnetic; 685 686 IdeDev->BlkIo.Media->MediaId = 0; 687 // 688 // Give initial value 689 // 690 IdeDev->BlkIo.Media->MediaPresent = FALSE; 691 692 IdeDev->BlkIo.Media->LastBlock = 0; 693 IdeDev->BlkIo.Media->BlockSize = 0x200; 694 break; 695 696 // 697 // CD-ROM 698 // 699 case 0x05: 700 701 IdeDev->Type = IdeCdRom; 702 IdeDev->BlkIo.Media->MediaId = 0; 703 // 704 // Give initial value 705 // 706 IdeDev->BlkIo.Media->MediaPresent = FALSE; 707 708 IdeDev->BlkIo.Media->LastBlock = 0; 709 IdeDev->BlkIo.Media->BlockSize = 0x800; 710 IdeDev->BlkIo.Media->ReadOnly = TRUE; 711 break; 712 713 // 714 // Tape 715 // 716 case 0x01: 717 718 // 719 // WORM 720 // 721 case 0x04: 722 723 // 724 // Optical 725 // 726 case 0x07: 727 728 default: 729 IdeDev->Type = IdeUnknown; 730 gBS->FreePool (IdeDev->IdData); 731 gBS->FreePool (IdeDev->InquiryData); 732 // 733 // Make sure the pIdData and pInquiryData will not be freed again. 734 // 735 IdeDev->IdData = NULL; 736 IdeDev->InquiryData = NULL; 737 return EFI_DEVICE_ERROR; 738 } 739 740 // 741 // original sense data numbers 742 // 743 IdeDev->SenseDataNumber = 20; 744 745 IdeDev->SenseData = AllocatePool (IdeDev->SenseDataNumber * sizeof (ATAPI_REQUEST_SENSE_DATA)); 746 if (IdeDev->SenseData == NULL) { 747 gBS->FreePool (IdeDev->IdData); 748 gBS->FreePool (IdeDev->InquiryData); 749 // 750 // Make sure the pIdData and pInquiryData will not be freed again. 751 // 752 IdeDev->IdData = NULL; 753 IdeDev->InquiryData = NULL; 754 return EFI_OUT_OF_RESOURCES; 755 } 756 757 return EFI_SUCCESS; 758 } 759 /** 760 Sends out ATAPI Request Sense Packet Command to the specified device. This command 761 will return all the current Sense data in the device. This function will pack 762 all the Sense data in one single buffer. 763 764 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 765 to record all the information of the IDE device. 766 @param SenseCounts allocated in this function, and freed by the calling function. 767 This buffer is used to accommodate all the sense data returned 768 by the device. 769 770 @retval EFI_SUCCESS Request Sense command completes successfully. 771 @retval EFI_DEVICE_ERROR Request Sense command failed. 772 **/ 773 EFI_STATUS 774 AtapiRequestSense ( 775 IN IDE_BLK_IO_DEV *IdeDev, 776 OUT UINTN *SenseCounts 777 ) 778 { 779 EFI_STATUS Status; 780 ATAPI_REQUEST_SENSE_DATA *Sense; 781 UINT16 *Ptr; 782 BOOLEAN FetchSenseData; 783 ATAPI_PACKET_COMMAND Packet; 784 785 *SenseCounts = 0; 786 787 ZeroMem (IdeDev->SenseData, sizeof (ATAPI_REQUEST_SENSE_DATA) * (IdeDev->SenseDataNumber)); 788 // 789 // fill command packet for Request Sense Packet Command 790 // 791 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 792 Packet.RequestSence.opcode = ATA_CMD_REQUEST_SENSE; 793 Packet.RequestSence.allocation_length = (UINT8) sizeof (ATAPI_REQUEST_SENSE_DATA); 794 795 // 796 // initialize pointer 797 // 798 Ptr = (UINT16 *) IdeDev->SenseData; 799 // 800 // request sense data from device continuously until no sense data 801 // exists in the device. 802 // 803 for (FetchSenseData = TRUE; FetchSenseData;) { 804 805 Sense = (ATAPI_REQUEST_SENSE_DATA *) Ptr; 806 807 // 808 // send out Request Sense Packet Command and get one Sense data form device 809 // 810 Status = AtapiPacketCommandIn ( 811 IdeDev, 812 &Packet, 813 Ptr, 814 sizeof (ATAPI_REQUEST_SENSE_DATA), 815 ATAPITIMEOUT 816 ); 817 // 818 // failed to get Sense data 819 // 820 if (EFI_ERROR (Status)) { 821 if (*SenseCounts == 0) { 822 return EFI_DEVICE_ERROR; 823 } else { 824 return EFI_SUCCESS; 825 } 826 } 827 828 (*SenseCounts)++; 829 // 830 // We limit MAX sense data count to 20 in order to avoid dead loop. Some 831 // incompatible ATAPI devices don't retrive NO_SENSE when there is no media. 832 // In this case, dead loop occurs if we don't have a gatekeeper. 20 is 833 // supposed to be large enough for any ATAPI device. 834 // 835 if ((Sense->sense_key != ATA_SK_NO_SENSE) && ((*SenseCounts) < 20)) { 836 // 837 // Ptr is word-based pointer 838 // 839 Ptr += (sizeof (ATAPI_REQUEST_SENSE_DATA) + 1) >> 1; 840 841 } else { 842 // 843 // when no sense key, skip out the loop 844 // 845 FetchSenseData = FALSE; 846 } 847 } 848 849 return EFI_SUCCESS; 850 } 851 /** 852 This function is used to parse sense data. Only the first sense data is honoured 853 854 @param IdeDev Indicates the calling context. 855 @param SenseCount Count of sense data. 856 @param Result The parsed result. 857 858 @retval EFI_SUCCESS Successfully parsed. 859 @retval EFI_INVALID_PARAMETER Count of sense data is zero. 860 861 **/ 862 EFI_STATUS 863 ParseSenseData ( 864 IN IDE_BLK_IO_DEV *IdeDev, 865 IN UINTN SenseCount, 866 OUT SENSE_RESULT *Result 867 ) 868 { 869 ATAPI_REQUEST_SENSE_DATA *SenseData; 870 871 if (SenseCount == 0) { 872 return EFI_INVALID_PARAMETER; 873 } 874 875 // 876 // Only use the first sense data 877 // 878 SenseData = IdeDev->SenseData; 879 *Result = SenseOtherSense; 880 881 switch (SenseData->sense_key) { 882 case ATA_SK_NO_SENSE: 883 *Result = SenseNoSenseKey; 884 break; 885 case ATA_SK_NOT_READY: 886 switch (SenseData->addnl_sense_code) { 887 case ATA_ASC_NO_MEDIA: 888 *Result = SenseNoMedia; 889 break; 890 case ATA_ASC_MEDIA_UPSIDE_DOWN: 891 *Result = SenseMediaError; 892 break; 893 case ATA_ASC_NOT_READY: 894 if (SenseData->addnl_sense_code_qualifier == ATA_ASCQ_IN_PROGRESS) { 895 *Result = SenseDeviceNotReadyNeedRetry; 896 } else { 897 *Result = SenseDeviceNotReadyNoRetry; 898 } 899 break; 900 } 901 break; 902 case ATA_SK_UNIT_ATTENTION: 903 if (SenseData->addnl_sense_code == ATA_ASC_MEDIA_CHANGE) { 904 *Result = SenseMediaChange; 905 } 906 break; 907 case ATA_SK_MEDIUM_ERROR: 908 switch (SenseData->addnl_sense_code) { 909 case ATA_ASC_MEDIA_ERR1: 910 case ATA_ASC_MEDIA_ERR2: 911 case ATA_ASC_MEDIA_ERR3: 912 case ATA_ASC_MEDIA_ERR4: 913 *Result = SenseMediaError; 914 break; 915 } 916 break; 917 default: 918 break; 919 } 920 921 return EFI_SUCCESS; 922 } 923 924 /** 925 Sends out ATAPI Test Unit Ready Packet Command to the specified device 926 to find out whether device is accessible. 927 928 @param IdeDev Pointer pointing to IDE_BLK_IO_DEV data structure, used 929 to record all the information of the IDE device. 930 @param SResult Sense result for this packet command. 931 932 @retval EFI_SUCCESS Device is accessible. 933 @retval EFI_DEVICE_ERROR Device is not accessible. 934 935 **/ 936 EFI_STATUS 937 AtapiTestUnitReady ( 938 IN IDE_BLK_IO_DEV *IdeDev, 939 OUT SENSE_RESULT *SResult 940 ) 941 { 942 ATAPI_PACKET_COMMAND Packet; 943 EFI_STATUS Status; 944 UINTN SenseCount; 945 946 // 947 // fill command packet 948 // 949 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 950 Packet.TestUnitReady.opcode = ATA_CMD_TEST_UNIT_READY; 951 952 // 953 // send command packet 954 // 955 Status = AtapiPacketCommandIn (IdeDev, &Packet, NULL, 0, ATAPITIMEOUT); 956 if (EFI_ERROR (Status)) { 957 return Status; 958 } 959 960 Status = AtapiRequestSense (IdeDev, &SenseCount); 961 if (EFI_ERROR (Status)) { 962 return Status; 963 } 964 965 ParseSenseData (IdeDev, SenseCount, SResult); 966 return EFI_SUCCESS; 967 } 968 969 970 /** 971 Sends out ATAPI Read Capacity Packet Command to the specified device. 972 This command will return the information regarding the capacity of the 973 media in the device. 974 975 Current device status will impact device's response to the Read Capacity 976 Command. For example, if the device once reset, the Read Capacity 977 Command will fail. The Sense data record the current device status, so 978 if the Read Capacity Command failed, the Sense data must be requested 979 and be analyzed to determine if the Read Capacity Command should retry. 980 981 @param IdeDev Pointer pointing to IDE_BLK_IO_DEV data structure, used 982 to record all the information of the IDE device. 983 @param SResult Sense result for this packet command 984 985 @retval EFI_SUCCESS Read Capacity Command finally completes successfully. 986 @retval EFI_DEVICE_ERROR Read Capacity Command failed because of device error. 987 @retval EFI_NOT_READY Operation succeeds but returned capacity is 0 988 989 @note Parameter "IdeDev" will be updated in this function. 990 991 992 **/ 993 EFI_STATUS 994 AtapiReadCapacity ( 995 IN IDE_BLK_IO_DEV *IdeDev, 996 OUT SENSE_RESULT *SResult 997 ) 998 { 999 // 1000 // status returned by Read Capacity Packet Command 1001 // 1002 EFI_STATUS Status; 1003 EFI_STATUS SenseStatus; 1004 ATAPI_PACKET_COMMAND Packet; 1005 UINTN SenseCount; 1006 1007 // 1008 // used for capacity data returned from ATAPI device 1009 // 1010 ATAPI_READ_CAPACITY_DATA Data; 1011 ATAPI_READ_FORMAT_CAPACITY_DATA FormatData; 1012 1013 ZeroMem (&Data, sizeof (Data)); 1014 ZeroMem (&FormatData, sizeof (FormatData)); 1015 1016 if (IdeDev->Type == IdeCdRom) { 1017 1018 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 1019 Packet.Inquiry.opcode = ATA_CMD_READ_CAPACITY; 1020 Status = AtapiPacketCommandIn ( 1021 IdeDev, 1022 &Packet, 1023 (UINT16 *) &Data, 1024 sizeof (ATAPI_READ_CAPACITY_DATA), 1025 ATAPITIMEOUT 1026 ); 1027 1028 } else { 1029 // 1030 // Type == IdeMagnetic 1031 // 1032 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 1033 Packet.ReadFormatCapacity.opcode = ATA_CMD_READ_FORMAT_CAPACITY; 1034 Packet.ReadFormatCapacity.allocation_length_lo = 12; 1035 Status = AtapiPacketCommandIn ( 1036 IdeDev, 1037 &Packet, 1038 (UINT16 *) &FormatData, 1039 sizeof (ATAPI_READ_FORMAT_CAPACITY_DATA), 1040 ATAPITIMEOUT 1041 ); 1042 } 1043 1044 if (Status == EFI_TIMEOUT) { 1045 return Status; 1046 } 1047 1048 SenseStatus = AtapiRequestSense (IdeDev, &SenseCount); 1049 1050 if (!EFI_ERROR (SenseStatus)) { 1051 ParseSenseData (IdeDev, SenseCount, SResult); 1052 1053 if (!EFI_ERROR (Status) && *SResult == SenseNoSenseKey) { 1054 if (IdeDev->Type == IdeCdRom) { 1055 1056 IdeDev->BlkIo.Media->LastBlock = (Data.LastLba3 << 24) | 1057 (Data.LastLba2 << 16) | 1058 (Data.LastLba1 << 8) | 1059 Data.LastLba0; 1060 1061 IdeDev->BlkIo.Media->MediaPresent = TRUE; 1062 1063 IdeDev->BlkIo.Media->ReadOnly = TRUE; 1064 1065 // 1066 // Because the user data portion in the sector of the Data CD supported 1067 // is always 0x800 1068 // 1069 IdeDev->BlkIo.Media->BlockSize = 0x800; 1070 } 1071 1072 if (IdeDev->Type == IdeMagnetic) { 1073 1074 if (FormatData.DesCode == 3) { 1075 IdeDev->BlkIo.Media->MediaPresent = FALSE; 1076 IdeDev->BlkIo.Media->LastBlock = 0; 1077 } else { 1078 1079 IdeDev->BlkIo.Media->LastBlock = (FormatData.LastLba3 << 24) | 1080 (FormatData.LastLba2 << 16) | 1081 (FormatData.LastLba1 << 8) | 1082 FormatData.LastLba0; 1083 if (IdeDev->BlkIo.Media->LastBlock != 0) { 1084 IdeDev->BlkIo.Media->LastBlock--; 1085 1086 IdeDev->BlkIo.Media->BlockSize = (FormatData.BlockSize2 << 16) | 1087 (FormatData.BlockSize1 << 8) | 1088 FormatData.BlockSize0; 1089 1090 IdeDev->BlkIo.Media->MediaPresent = TRUE; 1091 } else { 1092 IdeDev->BlkIo.Media->MediaPresent = FALSE; 1093 // 1094 // Return EFI_NOT_READY operation succeeds but returned capacity is 0 1095 // 1096 return EFI_NOT_READY; 1097 } 1098 1099 IdeDev->BlkIo.Media->BlockSize = 0x200; 1100 1101 } 1102 } 1103 } 1104 1105 return EFI_SUCCESS; 1106 1107 } else { 1108 return EFI_DEVICE_ERROR; 1109 } 1110 } 1111 /** 1112 This function is used to test the current media write-protected or not residing 1113 in the LS-120 drive or ZIP drive. 1114 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 1115 to record all the information of the IDE device. 1116 @param WriteProtected if True, current media is write protected. 1117 if FALSE, current media is writable 1118 1119 @retval EFI_SUCCESS The media write-protected status is achieved successfully 1120 @retval EFI_DEVICE_ERROR Get Media Status Command is failed. 1121 **/ 1122 EFI_STATUS 1123 IsLS120orZipWriteProtected ( 1124 IN IDE_BLK_IO_DEV *IdeDev, 1125 OUT BOOLEAN *WriteProtected 1126 ) 1127 { 1128 EFI_STATUS Status; 1129 1130 *WriteProtected = FALSE; 1131 1132 Status = LS120EnableMediaStatus (IdeDev, TRUE); 1133 if (EFI_ERROR (Status)) { 1134 return EFI_DEVICE_ERROR; 1135 } 1136 1137 // 1138 // the Get Media Status Command is only valid 1139 // if a Set Features/Enable Media Status Command has been priviously issued. 1140 // 1141 if (LS120GetMediaStatus (IdeDev) == EFI_WRITE_PROTECTED) { 1142 1143 *WriteProtected = TRUE; 1144 } else { 1145 1146 *WriteProtected = FALSE; 1147 } 1148 1149 // 1150 // After Get Media Status Command completes, 1151 // Set Features/Disable Media Command should be sent. 1152 // 1153 Status = LS120EnableMediaStatus (IdeDev, FALSE); 1154 if (EFI_ERROR (Status)) { 1155 return EFI_DEVICE_ERROR; 1156 } 1157 1158 return EFI_SUCCESS; 1159 } 1160 1161 /** 1162 Used before read/write blocks from/to ATAPI device media. Since ATAPI device 1163 media is removable, it is necessary to detect whether media is present and 1164 get current present media's information, and if media has been changed, Block 1165 I/O Protocol need to be reinstalled. 1166 1167 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 1168 to record all the information of the IDE device. 1169 @param MediaChange return value that indicates if the media of the device has been 1170 changed. 1171 1172 @retval EFI_SUCCESS media found successfully. 1173 @retval EFI_DEVICE_ERROR any error encounters during media detection. 1174 @retval EFI_NO_MEDIA media not found. 1175 1176 @note 1177 parameter IdeDev may be updated in this function. 1178 1179 **/ 1180 EFI_STATUS 1181 AtapiDetectMedia ( 1182 IN IDE_BLK_IO_DEV *IdeDev, 1183 OUT BOOLEAN *MediaChange 1184 ) 1185 { 1186 EFI_STATUS Status; 1187 EFI_STATUS CleanStateStatus; 1188 EFI_BLOCK_IO_MEDIA OldMediaInfo; 1189 UINTN RetryTimes; 1190 UINTN RetryNotReady; 1191 SENSE_RESULT SResult; 1192 BOOLEAN WriteProtected; 1193 1194 CopyMem (&OldMediaInfo, IdeDev->BlkIo.Media, sizeof (EFI_BLOCK_IO_MEDIA)); 1195 *MediaChange = FALSE; 1196 // 1197 // Retry for SenseDeviceNotReadyNeedRetry. 1198 // Each retry takes 1s and we limit the upper boundary to 1199 // 120 times about 2 min. 1200 // 1201 RetryNotReady = 120; 1202 1203 // 1204 // Do Test Unit Ready 1205 // 1206 DoTUR: 1207 // 1208 // Retry 5 times 1209 // 1210 RetryTimes = 5; 1211 while (RetryTimes != 0) { 1212 1213 Status = AtapiTestUnitReady (IdeDev, &SResult); 1214 1215 if (EFI_ERROR (Status)) { 1216 // 1217 // Test Unit Ready error without sense data. 1218 // For some devices, this means there's extra data 1219 // that has not been read, so we read these extra 1220 // data out before going on. 1221 // 1222 CleanStateStatus = AtapiReadPendingData (IdeDev); 1223 if (EFI_ERROR (CleanStateStatus)) { 1224 // 1225 // Busy wait failed, try again 1226 // 1227 RetryTimes--; 1228 } 1229 // 1230 // Try again without counting down RetryTimes 1231 // 1232 continue; 1233 } else { 1234 switch (SResult) { 1235 case SenseNoSenseKey: 1236 if (IdeDev->BlkIo.Media->MediaPresent) { 1237 goto Done; 1238 } else { 1239 // 1240 // Media present but the internal structure need refreshed. 1241 // Try Read Capacity 1242 // 1243 goto DoRC; 1244 } 1245 break; 1246 1247 case SenseDeviceNotReadyNeedRetry: 1248 if (--RetryNotReady == 0) { 1249 return EFI_DEVICE_ERROR; 1250 } 1251 gBS->Stall (1000 * STALL_1_MILLI_SECOND); 1252 continue; 1253 break; 1254 1255 case SenseNoMedia: 1256 IdeDev->BlkIo.Media->MediaPresent = FALSE; 1257 IdeDev->BlkIo.Media->LastBlock = 0; 1258 goto Done; 1259 break; 1260 1261 case SenseDeviceNotReadyNoRetry: 1262 case SenseMediaError: 1263 return EFI_DEVICE_ERROR; 1264 1265 case SenseMediaChange: 1266 IdeDev->BlkIo.Media->MediaId++; 1267 goto DoRC; 1268 break; 1269 1270 default: 1271 RetryTimes--; 1272 break; 1273 } 1274 } 1275 } 1276 1277 return EFI_DEVICE_ERROR; 1278 1279 // 1280 // Do Read Capacity 1281 // 1282 DoRC: 1283 RetryTimes = 5; 1284 1285 while (RetryTimes != 0) { 1286 1287 Status = AtapiReadCapacity (IdeDev, &SResult); 1288 1289 if (EFI_ERROR (Status)) { 1290 RetryTimes--; 1291 continue; 1292 } else { 1293 switch (SResult) { 1294 case SenseNoSenseKey: 1295 goto Done; 1296 break; 1297 1298 case SenseDeviceNotReadyNeedRetry: 1299 // 1300 // We use Test Unit Ready to retry which 1301 // is faster. 1302 // 1303 goto DoTUR; 1304 break; 1305 1306 case SenseNoMedia: 1307 IdeDev->BlkIo.Media->MediaPresent = FALSE; 1308 IdeDev->BlkIo.Media->LastBlock = 0; 1309 goto Done; 1310 break; 1311 1312 case SenseDeviceNotReadyNoRetry: 1313 case SenseMediaError: 1314 return EFI_DEVICE_ERROR; 1315 1316 case SenseMediaChange: 1317 IdeDev->BlkIo.Media->MediaId++; 1318 continue; 1319 break; 1320 1321 default: 1322 RetryTimes--; 1323 break; 1324 } 1325 } 1326 } 1327 1328 return EFI_DEVICE_ERROR; 1329 1330 Done: 1331 // 1332 // the following code is to check the write-protected for LS120 media 1333 // 1334 if ((IdeDev->BlkIo.Media->MediaPresent) && (IdeDev->Type == IdeMagnetic)) { 1335 1336 Status = IsLS120orZipWriteProtected (IdeDev, &WriteProtected); 1337 if (!EFI_ERROR (Status)) { 1338 1339 if (WriteProtected) { 1340 1341 IdeDev->BlkIo.Media->ReadOnly = TRUE; 1342 } else { 1343 1344 IdeDev->BlkIo.Media->ReadOnly = FALSE; 1345 } 1346 1347 } 1348 } 1349 1350 if (IdeDev->BlkIo.Media->MediaId != OldMediaInfo.MediaId) { 1351 // 1352 // Media change information got from the device 1353 // 1354 *MediaChange = TRUE; 1355 } 1356 1357 if (IdeDev->BlkIo.Media->ReadOnly != OldMediaInfo.ReadOnly) { 1358 *MediaChange = TRUE; 1359 IdeDev->BlkIo.Media->MediaId += 1; 1360 } 1361 1362 if (IdeDev->BlkIo.Media->BlockSize != OldMediaInfo.BlockSize) { 1363 *MediaChange = TRUE; 1364 IdeDev->BlkIo.Media->MediaId += 1; 1365 } 1366 1367 if (IdeDev->BlkIo.Media->LastBlock != OldMediaInfo.LastBlock) { 1368 *MediaChange = TRUE; 1369 IdeDev->BlkIo.Media->MediaId += 1; 1370 } 1371 1372 if (IdeDev->BlkIo.Media->MediaPresent != OldMediaInfo.MediaPresent) { 1373 if (IdeDev->BlkIo.Media->MediaPresent) { 1374 // 1375 // when change from no media to media present, reset the MediaId to 1. 1376 // 1377 IdeDev->BlkIo.Media->MediaId = 1; 1378 } else { 1379 // 1380 // when no media, reset the MediaId to zero. 1381 // 1382 IdeDev->BlkIo.Media->MediaId = 0; 1383 } 1384 1385 *MediaChange = TRUE; 1386 } 1387 1388 // 1389 // if any change on current existing media, 1390 // the Block I/O protocol need to be reinstalled. 1391 // 1392 if (*MediaChange) { 1393 gBS->ReinstallProtocolInterface ( 1394 IdeDev->Handle, 1395 &gEfiBlockIoProtocolGuid, 1396 &IdeDev->BlkIo, 1397 &IdeDev->BlkIo 1398 ); 1399 } 1400 1401 if (IdeDev->BlkIo.Media->MediaPresent) { 1402 return EFI_SUCCESS; 1403 } else { 1404 return EFI_NO_MEDIA; 1405 } 1406 } 1407 1408 /** 1409 This function is called by the AtapiBlkIoReadBlocks() to perform 1410 read from media in block unit. 1411 1412 The main command used to access media here is READ(10) Command. 1413 READ(10) Command requests that the ATAPI device media transfer 1414 specified data to the host. Data is transferred in block(sector) 1415 unit. The maximum number of blocks that can be transferred once is 1416 65536. This is the main difference between READ(10) and READ(12) 1417 Command. The maximum number of blocks in READ(12) is 2 power 32. 1418 1419 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 1420 to record all the information of the IDE device. 1421 @param Buffer A pointer to the destination buffer for the data. 1422 @param Lba The starting logical block address to read from on the 1423 device media. 1424 @param NumberOfBlocks The number of transfer data blocks. 1425 1426 @return status is fully dependent on the return status of AtapiPacketCommandIn() function. 1427 1428 **/ 1429 EFI_STATUS 1430 AtapiReadSectors ( 1431 IN IDE_BLK_IO_DEV *IdeDev, 1432 IN VOID *Buffer, 1433 IN EFI_LBA Lba, 1434 IN UINTN NumberOfBlocks 1435 ) 1436 { 1437 1438 ATAPI_PACKET_COMMAND Packet; 1439 ATAPI_READ10_CMD *Read10Packet; 1440 EFI_STATUS Status; 1441 UINTN BlocksRemaining; 1442 UINT32 Lba32; 1443 UINT32 BlockSize; 1444 UINT32 ByteCount; 1445 UINT16 SectorCount; 1446 VOID *PtrBuffer; 1447 UINT16 MaxBlock; 1448 UINTN TimeOut; 1449 1450 // 1451 // fill command packet for Read(10) command 1452 // 1453 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 1454 Read10Packet = &Packet.Read10; 1455 Lba32 = (UINT32) Lba; 1456 PtrBuffer = Buffer; 1457 1458 BlockSize = IdeDev->BlkIo.Media->BlockSize; 1459 1460 // 1461 // limit the data bytes that can be transferred by one Read(10) Command 1462 // 1463 MaxBlock = 65535; 1464 1465 BlocksRemaining = NumberOfBlocks; 1466 1467 Status = EFI_SUCCESS; 1468 while (BlocksRemaining > 0) { 1469 1470 if (BlocksRemaining <= MaxBlock) { 1471 1472 SectorCount = (UINT16) BlocksRemaining; 1473 } else { 1474 1475 SectorCount = MaxBlock; 1476 } 1477 1478 // 1479 // fill the Packet data structure 1480 // 1481 1482 Read10Packet->opcode = ATA_CMD_READ_10; 1483 1484 // 1485 // Lba0 ~ Lba3 specify the start logical block address of the data transfer. 1486 // Lba0 is MSB, Lba3 is LSB 1487 // 1488 Read10Packet->Lba3 = (UINT8) (Lba32 & 0xff); 1489 Read10Packet->Lba2 = (UINT8) (Lba32 >> 8); 1490 Read10Packet->Lba1 = (UINT8) (Lba32 >> 16); 1491 Read10Packet->Lba0 = (UINT8) (Lba32 >> 24); 1492 1493 // 1494 // TranLen0 ~ TranLen1 specify the transfer length in block unit. 1495 // TranLen0 is MSB, TranLen is LSB 1496 // 1497 Read10Packet->TranLen1 = (UINT8) (SectorCount & 0xff); 1498 Read10Packet->TranLen0 = (UINT8) (SectorCount >> 8); 1499 1500 ByteCount = SectorCount * BlockSize; 1501 1502 if (IdeDev->Type == IdeCdRom) { 1503 TimeOut = CDROMLONGTIMEOUT; 1504 } else { 1505 TimeOut = ATAPILONGTIMEOUT; 1506 } 1507 1508 Status = AtapiPacketCommandIn ( 1509 IdeDev, 1510 &Packet, 1511 (UINT16 *) PtrBuffer, 1512 ByteCount, 1513 TimeOut 1514 ); 1515 if (EFI_ERROR (Status)) { 1516 return Status; 1517 } 1518 1519 Lba32 += SectorCount; 1520 PtrBuffer = (UINT8 *) PtrBuffer + SectorCount * BlockSize; 1521 BlocksRemaining -= SectorCount; 1522 } 1523 1524 return Status; 1525 } 1526 1527 /** 1528 This function is called by the AtapiBlkIoWriteBlocks() to perform 1529 write onto media in block unit. 1530 The main command used to access media here is Write(10) Command. 1531 Write(10) Command requests that the ATAPI device media transfer 1532 specified data to the host. Data is transferred in block (sector) 1533 unit. The maximum number of blocks that can be transferred once is 1534 65536. 1535 1536 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 1537 to record all the information of the IDE device. 1538 @param Buffer A pointer to the source buffer for the data. 1539 @param Lba The starting logical block address to write onto 1540 the device media. 1541 @param NumberOfBlocks The number of transfer data blocks. 1542 1543 @return status is fully dependent on the return status of AtapiPacketCommandOut() function. 1544 1545 **/ 1546 EFI_STATUS 1547 AtapiWriteSectors ( 1548 IN IDE_BLK_IO_DEV *IdeDev, 1549 IN VOID *Buffer, 1550 IN EFI_LBA Lba, 1551 IN UINTN NumberOfBlocks 1552 ) 1553 { 1554 1555 ATAPI_PACKET_COMMAND Packet; 1556 ATAPI_READ10_CMD *Read10Packet; 1557 1558 EFI_STATUS Status; 1559 UINTN BlocksRemaining; 1560 UINT32 Lba32; 1561 UINT32 BlockSize; 1562 UINT32 ByteCount; 1563 UINT16 SectorCount; 1564 VOID *PtrBuffer; 1565 UINT16 MaxBlock; 1566 1567 // 1568 // fill command packet for Write(10) command 1569 // Write(10) command packet has the same data structure as 1570 // Read(10) command packet, 1571 // so here use the Read10Packet data structure 1572 // for the Write(10) command packet. 1573 // 1574 ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND)); 1575 Read10Packet = &Packet.Read10; 1576 1577 Lba32 = (UINT32) Lba; 1578 PtrBuffer = Buffer; 1579 1580 BlockSize = IdeDev->BlkIo.Media->BlockSize; 1581 1582 // 1583 // limit the data bytes that can be transferred by one Read(10) Command 1584 // 1585 MaxBlock = (UINT16) (65536 / BlockSize); 1586 1587 BlocksRemaining = NumberOfBlocks; 1588 1589 Status = EFI_SUCCESS; 1590 while (BlocksRemaining > 0) { 1591 1592 if (BlocksRemaining >= MaxBlock) { 1593 SectorCount = MaxBlock; 1594 } else { 1595 SectorCount = (UINT16) BlocksRemaining; 1596 } 1597 1598 // 1599 // Command code is WRITE_10. 1600 // 1601 Read10Packet->opcode = ATA_CMD_WRITE_10; 1602 1603 // 1604 // Lba0 ~ Lba3 specify the start logical block address of the data transfer. 1605 // Lba0 is MSB, Lba3 is LSB 1606 // 1607 Read10Packet->Lba3 = (UINT8) (Lba32 & 0xff); 1608 Read10Packet->Lba2 = (UINT8) (Lba32 >> 8); 1609 Read10Packet->Lba1 = (UINT8) (Lba32 >> 16); 1610 Read10Packet->Lba0 = (UINT8) (Lba32 >> 24); 1611 1612 // 1613 // TranLen0 ~ TranLen1 specify the transfer length in block unit. 1614 // TranLen0 is MSB, TranLen is LSB 1615 // 1616 Read10Packet->TranLen1 = (UINT8) (SectorCount & 0xff); 1617 Read10Packet->TranLen0 = (UINT8) (SectorCount >> 8); 1618 1619 ByteCount = SectorCount * BlockSize; 1620 1621 Status = AtapiPacketCommandOut ( 1622 IdeDev, 1623 &Packet, 1624 (UINT16 *) PtrBuffer, 1625 ByteCount, 1626 ATAPILONGTIMEOUT 1627 ); 1628 if (EFI_ERROR (Status)) { 1629 return Status; 1630 } 1631 1632 Lba32 += SectorCount; 1633 PtrBuffer = ((UINT8 *) PtrBuffer + SectorCount * BlockSize); 1634 BlocksRemaining -= SectorCount; 1635 } 1636 1637 return Status; 1638 } 1639 /** 1640 This function is used to implement the Soft Reset on the specified 1641 ATAPI device. Different from the AtaSoftReset(), here reset is a ATA 1642 Soft Reset Command special for ATAPI device, and it only take effects 1643 on the specified ATAPI device, not on the whole IDE bus. 1644 Since the ATAPI soft reset is needed when device is in exceptional 1645 condition (such as BSY bit is always set ), I think the Soft Reset 1646 command should be sent without waiting for the BSY clear and DRDY 1647 set. 1648 This function is called by IdeBlkIoReset(), 1649 a interface function of Block I/O protocol. 1650 1651 @param IdeDev pointer pointing to IDE_BLK_IO_DEV data structure, used 1652 to record all the information of the IDE device. 1653 1654 @retval EFI_SUCCESS Soft reset completes successfully. 1655 @retval EFI_DEVICE_ERROR Any step during the reset process is failed. 1656 1657 **/ 1658 EFI_STATUS 1659 AtapiSoftReset ( 1660 IN IDE_BLK_IO_DEV *IdeDev 1661 ) 1662 { 1663 UINT8 Command; 1664 UINT8 DeviceSelect; 1665 EFI_STATUS Status; 1666 1667 // 1668 // for ATAPI device, no need to wait DRDY ready after device selecting. 1669 // (bit7 and bit5 are both set to 1 for backward compatibility) 1670 // 1671 DeviceSelect = (UINT8) (((BIT7 | BIT5) | (IdeDev->Device << 4))); 1672 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Head, DeviceSelect); 1673 1674 Command = ATA_CMD_SOFT_RESET; 1675 IDEWritePortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Command, Command); 1676 1677 // 1678 // BSY cleared is the only status return to the host by the device 1679 // when reset is completed. 1680 // slave device needs at most 31s to clear BSY 1681 // 1682 Status = WaitForBSYClear (IdeDev, 31000); 1683 if (EFI_ERROR (Status)) { 1684 return EFI_DEVICE_ERROR; 1685 } 1686 1687 // 1688 // stall 5 seconds to make the device status stable 1689 // 1690 gBS->Stall (5000000); 1691 1692 return EFI_SUCCESS; 1693 } 1694 1695 /** 1696 This function is the ATAPI implementation for ReadBlocks in the 1697 Block I/O Protocol interface. 1698 1699 @param IdeBlkIoDevice Indicates the calling context. 1700 @param MediaId The media id that the read request is for. 1701 @param Lba The starting logical block address to read from on the device. 1702 @param BufferSize The size of the Buffer in bytes. This must be a multiple 1703 of the intrinsic block size of the device. 1704 @param Buffer A pointer to the destination buffer for the data. The caller 1705 is responsible for either having implicit or explicit 1706 ownership of the memory that data is read into. 1707 1708 @retval EFI_SUCCESS Read Blocks successfully. 1709 @retval EFI_DEVICE_ERROR Read Blocks failed. 1710 @retval EFI_NO_MEDIA There is no media in the device. 1711 @retval EFI_MEDIA_CHANGED The MediaId is not for the current media. 1712 @retval EFI_BAD_BUFFER_SIZE The BufferSize parameter is not a multiple of the 1713 intrinsic block size of the device. 1714 @retval EFI_INVALID_PARAMETER The read request contains LBAs that are not valid, 1715 or the data buffer is not valid. 1716 **/ 1717 EFI_STATUS 1718 AtapiBlkIoReadBlocks ( 1719 IN IDE_BLK_IO_DEV *IdeBlkIoDevice, 1720 IN UINT32 MediaId, 1721 IN EFI_LBA Lba, 1722 IN UINTN BufferSize, 1723 OUT VOID *Buffer 1724 ) 1725 { 1726 EFI_BLOCK_IO_MEDIA *Media; 1727 UINTN BlockSize; 1728 UINTN NumberOfBlocks; 1729 EFI_STATUS Status; 1730 1731 BOOLEAN MediaChange; 1732 1733 if (Buffer == NULL) { 1734 return EFI_INVALID_PARAMETER; 1735 } 1736 1737 if (BufferSize == 0) { 1738 return EFI_SUCCESS; 1739 } 1740 1741 // 1742 // ATAPI device media is removable, so it is a must 1743 // to detect media first before read operation 1744 // 1745 MediaChange = FALSE; 1746 Status = AtapiDetectMedia (IdeBlkIoDevice, &MediaChange); 1747 if (EFI_ERROR (Status)) { 1748 1749 if (IdeBlkIoDevice->Cache != NULL) { 1750 gBS->FreePool (IdeBlkIoDevice->Cache); 1751 IdeBlkIoDevice->Cache = NULL; 1752 } 1753 1754 return Status; 1755 } 1756 // 1757 // Get the intrinsic block size 1758 // 1759 Media = IdeBlkIoDevice->BlkIo.Media; 1760 BlockSize = Media->BlockSize; 1761 1762 NumberOfBlocks = BufferSize / BlockSize; 1763 1764 if (!(Media->MediaPresent)) { 1765 1766 if (IdeBlkIoDevice->Cache != NULL) { 1767 gBS->FreePool (IdeBlkIoDevice->Cache); 1768 IdeBlkIoDevice->Cache = NULL; 1769 } 1770 return EFI_NO_MEDIA; 1771 1772 } 1773 1774 if ((MediaId != Media->MediaId) || MediaChange) { 1775 1776 if (IdeBlkIoDevice->Cache != NULL) { 1777 gBS->FreePool (IdeBlkIoDevice->Cache); 1778 IdeBlkIoDevice->Cache = NULL; 1779 } 1780 return EFI_MEDIA_CHANGED; 1781 } 1782 1783 if (BufferSize % BlockSize != 0) { 1784 return EFI_BAD_BUFFER_SIZE; 1785 } 1786 1787 if (Lba > Media->LastBlock) { 1788 return EFI_INVALID_PARAMETER; 1789 } 1790 1791 if ((Lba + NumberOfBlocks - 1) > Media->LastBlock) { 1792 return EFI_INVALID_PARAMETER; 1793 } 1794 1795 if ((Media->IoAlign > 1) && (((UINTN) Buffer & (Media->IoAlign - 1)) != 0)) { 1796 return EFI_INVALID_PARAMETER; 1797 } 1798 1799 // 1800 // if all the parameters are valid, then perform read sectors command 1801 // to transfer data from device to host. 1802 // 1803 Status = AtapiReadSectors (IdeBlkIoDevice, Buffer, Lba, NumberOfBlocks); 1804 if (EFI_ERROR (Status)) { 1805 return EFI_DEVICE_ERROR; 1806 } 1807 1808 // 1809 // Read blocks succeeded 1810 // 1811 1812 // 1813 // save the first block to the cache for performance 1814 // 1815 if (Lba == 0 && (IdeBlkIoDevice->Cache == NULL)) { 1816 IdeBlkIoDevice->Cache = AllocatePool (BlockSize); 1817 if (IdeBlkIoDevice->Cache!= NULL) { 1818 CopyMem ((UINT8 *) IdeBlkIoDevice->Cache, (UINT8 *) Buffer, BlockSize); 1819 } 1820 } 1821 1822 return EFI_SUCCESS; 1823 1824 } 1825 /** 1826 This function is the ATAPI implementation for WriteBlocks in the 1827 Block I/O Protocol interface. 1828 1829 @param IdeBlkIoDevice Indicates the calling context. 1830 @param MediaId The media id that the write request is for. 1831 @param Lba The starting logical block address to write onto the device. 1832 @param BufferSize The size of the Buffer in bytes. This must be a multiple 1833 of the intrinsic block size of the device. 1834 @param Buffer A pointer to the source buffer for the data. The caller 1835 is responsible for either having implicit or explicit ownership 1836 of the memory that data is written from. 1837 1838 @retval EFI_SUCCESS Write Blocks successfully. 1839 @retval EFI_DEVICE_ERROR Write Blocks failed. 1840 @retval EFI_NO_MEDIA There is no media in the device. 1841 @retval EFI_MEDIA_CHANGE The MediaId is not for the current media. 1842 @retval EFI_BAD_BUFFER_SIZE The BufferSize parameter is not a multiple of the 1843 intrinsic block size of the device. 1844 @retval EFI_INVALID_PARAMETER The write request contains LBAs that are not valid, 1845 or the data buffer is not valid. 1846 1847 @retval EFI_WRITE_PROTECTED The write protected is enabled or the media does not support write 1848 **/ 1849 EFI_STATUS 1850 AtapiBlkIoWriteBlocks ( 1851 IN IDE_BLK_IO_DEV *IdeBlkIoDevice, 1852 IN UINT32 MediaId, 1853 IN EFI_LBA Lba, 1854 IN UINTN BufferSize, 1855 OUT VOID *Buffer 1856 ) 1857 { 1858 1859 EFI_BLOCK_IO_MEDIA *Media; 1860 UINTN BlockSize; 1861 UINTN NumberOfBlocks; 1862 EFI_STATUS Status; 1863 BOOLEAN MediaChange; 1864 1865 if (Lba == 0 && IdeBlkIoDevice->Cache != NULL) { 1866 gBS->FreePool (IdeBlkIoDevice->Cache); 1867 IdeBlkIoDevice->Cache = NULL; 1868 } 1869 1870 if (Buffer == NULL) { 1871 return EFI_INVALID_PARAMETER; 1872 } 1873 1874 if (BufferSize == 0) { 1875 return EFI_SUCCESS; 1876 } 1877 1878 // 1879 // ATAPI device media is removable, 1880 // so it is a must to detect media first before write operation 1881 // 1882 MediaChange = FALSE; 1883 Status = AtapiDetectMedia (IdeBlkIoDevice, &MediaChange); 1884 if (EFI_ERROR (Status)) { 1885 1886 if (Lba == 0 && IdeBlkIoDevice->Cache != NULL) { 1887 gBS->FreePool (IdeBlkIoDevice->Cache); 1888 IdeBlkIoDevice->Cache = NULL; 1889 } 1890 return Status; 1891 } 1892 1893 // 1894 // Get the intrinsic block size 1895 // 1896 Media = IdeBlkIoDevice->BlkIo.Media; 1897 BlockSize = Media->BlockSize; 1898 NumberOfBlocks = BufferSize / BlockSize; 1899 1900 if (!(Media->MediaPresent)) { 1901 1902 if (Lba == 0 && IdeBlkIoDevice->Cache != NULL) { 1903 gBS->FreePool (IdeBlkIoDevice->Cache); 1904 IdeBlkIoDevice->Cache = NULL; 1905 } 1906 return EFI_NO_MEDIA; 1907 } 1908 1909 if ((MediaId != Media->MediaId) || MediaChange) { 1910 1911 if (Lba == 0 && IdeBlkIoDevice->Cache != NULL) { 1912 gBS->FreePool (IdeBlkIoDevice->Cache); 1913 IdeBlkIoDevice->Cache = NULL; 1914 } 1915 return EFI_MEDIA_CHANGED; 1916 } 1917 1918 if (Media->ReadOnly) { 1919 return EFI_WRITE_PROTECTED; 1920 } 1921 1922 if (BufferSize % BlockSize != 0) { 1923 return EFI_BAD_BUFFER_SIZE; 1924 } 1925 1926 if (Lba > Media->LastBlock) { 1927 return EFI_INVALID_PARAMETER; 1928 } 1929 1930 if ((Lba + NumberOfBlocks - 1) > Media->LastBlock) { 1931 return EFI_INVALID_PARAMETER; 1932 } 1933 1934 if ((Media->IoAlign > 1) && (((UINTN) Buffer & (Media->IoAlign - 1)) != 0)) { 1935 return EFI_INVALID_PARAMETER; 1936 } 1937 1938 // 1939 // if all the parameters are valid, 1940 // then perform write sectors command to transfer data from host to device. 1941 // 1942 Status = AtapiWriteSectors (IdeBlkIoDevice, Buffer, Lba, NumberOfBlocks); 1943 if (EFI_ERROR (Status)) { 1944 return EFI_DEVICE_ERROR; 1945 } 1946 1947 return EFI_SUCCESS; 1948 1949 } 1950 1951 1952 1953