-/*++\r
+/** @file\r
+ Copyright (c) 2006, Intel Corporation \r
+ All rights reserved. This program and the accompanying materials \r
+ are licensed and made available under the terms and conditions of the BSD License \r
+ which accompanies this distribution. The full text of the license may be found at \r
+ http://opensource.org/licenses/bsd-license.php \r
\r
-Copyright (c) 2006, Intel Corporation \r
-All rights reserved. This program and the accompanying materials \r
-are licensed and made available under the terms and conditions of the BSD License \r
-which accompanies this distribution. The full text of the license may be found at \r
-http://opensource.org/licenses/bsd-license.php \r
- \r
-THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, \r
-WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. \r
+ THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, \r
+ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. \r
\r
-Module Name:\r
+**/\r
\r
- atapi.c\r
- \r
-Abstract: \r
- \r
+#include "idebus.h"\r
\r
-Revision History\r
---*/\r
+/**\r
+ This function is used to get the current status of the media residing\r
+ in the LS-120 drive or ZIP drive. The media status is returned in the \r
+ Error Status.\r
\r
-#include "idebus.h"\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @retval EFI_SUCCESS\r
+ The media status is achieved successfully and the media\r
+ can be read/written.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ Get Media Status Command is failed.\r
+ \r
+ @retval EFI_NO_MEDIA\r
+ There is no media in the drive.\r
+ \r
+ @retval EFI_WRITE_PROTECTED\r
+ The media is writing protected.\r
\r
+ @note\r
+ This function must be called after the LS120EnableMediaStatus() \r
+ with second parameter set to TRUE \r
+ (means enable media status notification) is called.\r
+\r
+**/\r
STATIC\r
EFI_STATUS\r
LS120GetMediaStatus (\r
IN IDE_BLK_IO_DEV *IdeDev\r
)\r
-/*++\r
- Name:\r
- LS120GetMediaStatus\r
-\r
- Purpose: \r
- This function is used to get the current status of the media residing\r
- in the LS-120 drive or ZIP drive. The media status is returned in the \r
- Error Status.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- The media status is achieved successfully and the media\r
- can be read/written. \r
- \r
- EFI_DEVICE_ERROR\r
- Get Media Status Command is failed.\r
-\r
- EFI_NO_MEDIA\r
- There is no media in the drive.\r
-\r
- EFI_WRITE_PROTECTED\r
- The media is writing protected. \r
-\r
- Notes: \r
- This function must be called after the LS120EnableMediaStatus() \r
- with second parameter set to TRUE \r
- (means enable media status notification) is called.\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
{\r
UINT8 DeviceSelect;\r
UINT8 StatusValue;\r
}\r
}\r
\r
+/**\r
+ This function is used to send Enable Media Status Notification Command\r
+ or Disable Media Status Notification Command.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[in] Enable\r
+ a flag that indicates whether enable or disable media\r
+ status notification.\r
+\r
+ @retval EFI_SUCCESS\r
+ If command completes successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ If command failed.\r
+\r
+**/\r
STATIC\r
EFI_STATUS\r
LS120EnableMediaStatus (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
IN BOOLEAN Enable\r
)\r
-/*++\r
- Name:\r
- LS120EnableMediaStatus\r
-\r
- Purpose: \r
- This function is used to send Enable Media Status Notification Command\r
- or Disable Media Status Notification Command.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- BOOLEAN IN Enable\r
- a flag that indicates whether enable or disable media\r
- status notification.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- If command completes successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- If command failed.\r
-\r
-\r
- Notes: \r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: Enable - add argument and description to function comment\r
{\r
UINT8 DeviceSelect;\r
EFI_STATUS Status;\r
return EFI_SUCCESS;\r
}\r
\r
+/**\r
+ This function is called by DiscoverIdeDevice() during its device\r
+ identification.\r
+\r
+ Its main purpose is to get enough information for the device media\r
+ to fill in the Media data structure of the Block I/O Protocol interface.\r
+\r
+ There are 5 steps to reach such objective:\r
+\r
+ 1. Sends out the ATAPI Identify Command to the specified device. \r
+ Only ATAPI device responses to this command. If the command succeeds,\r
+ it returns the Identify data structure which filled with information \r
+ about the device. Since the ATAPI device contains removable media, \r
+ the only meaningful information is the device module name.\r
+\r
+ 2. Sends out ATAPI Inquiry Packet Command to the specified device.\r
+ This command will return inquiry data of the device, which contains\r
+ the device type information.\r
+\r
+ 3. Allocate sense data space for future use. We don't detect the media\r
+ presence here to improvement boot performance, especially when CD \r
+ media is present. The media detection will be performed just before\r
+ each BLK_IO read/write\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @retval EFI_SUCCESS\r
+ Identify ATAPI device successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ ATAPI Identify Device Command failed or device type\r
+ is not supported by this IDE driver.\r
+\r
+ @note\r
+ Parameter "IdeDev" will be updated in this function.\r
+\r
+ TODO: EFI_OUT_OF_RESOURCES - add return value to function comment\r
+ TODO: EFI_OUT_OF_RESOURCES - add return value to function comment\r
+**/\r
EFI_STATUS\r
ATAPIIdentify (\r
IN IDE_BLK_IO_DEV *IdeDev\r
)\r
-/*++\r
- Name:\r
- ATAPIIdentify\r
-\r
-\r
- Purpose: \r
- This function is called by DiscoverIdeDevice() during its device\r
- identification.\r
-\r
- Its main purpose is to get enough information for the device media\r
- to fill in the Media data structure of the Block I/O Protocol interface.\r
-\r
- There are 5 steps to reach such objective:\r
-\r
- 1. Sends out the ATAPI Identify Command to the specified device. \r
- Only ATAPI device responses to this command. If the command succeeds,\r
- it returns the Identify data structure which filled with information \r
- about the device. Since the ATAPI device contains removable media, \r
- the only meaningful information is the device module name.\r
-\r
- 2. Sends out ATAPI Inquiry Packet Command to the specified device.\r
- This command will return inquiry data of the device, which contains\r
- the device type information.\r
-\r
- 3. Allocate sense data space for future use. We don't detect the media\r
- presence here to improvement boot performance, especially when CD \r
- media is present. The media detection will be performed just before\r
- each BLK_IO read/write\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- Identify ATAPI device successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- ATAPI Identify Device Command failed or device type \r
- is not supported by this IDE driver.\r
-\r
- Notes:\r
- Parameter "IdeDev" will be updated in this function.\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: EFI_OUT_OF_RESOURCES - add return value to function comment\r
-// TODO: EFI_OUT_OF_RESOURCES - add return value to function comment\r
{\r
EFI_IDENTIFY_DATA *AtapiIdentifyPointer;\r
UINT8 DeviceSelect;\r
return EFI_SUCCESS;\r
}\r
\r
+/**\r
+ Sends out ATAPI Inquiry Packet Command to the specified device.\r
+ This command will return INQUIRY data of the device.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @retval EFI_SUCCESS\r
+ Inquiry command completes successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ Inquiry command failed.\r
+\r
+ @note\r
+ Parameter "IdeDev" will be updated in this function.\r
+\r
+**/\r
EFI_STATUS\r
AtapiInquiry (\r
IN IDE_BLK_IO_DEV *IdeDev\r
)\r
-/*++\r
- Name:\r
- AtapiInquiry\r
-\r
- Purpose: \r
- Sends out ATAPI Inquiry Packet Command to the specified device.\r
- This command will return INQUIRY data of the device.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- Inquiry command completes successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- Inquiry command failed.\r
- Notes:\r
- Parameter "IdeDev" will be updated in this function.\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
{\r
ATAPI_PACKET_COMMAND Packet;\r
EFI_STATUS Status;\r
return EFI_SUCCESS;\r
}\r
\r
+/**\r
+ This function is used to send out ATAPI commands conforms to the \r
+ Packet Command with PIO Data In Protocol.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[in] *Packet\r
+ pointer pointing to ATAPI_PACKET_COMMAND data structure\r
+ which contains the contents of the command. \r
+\r
+ @param[in] *Buffer\r
+ buffer contained data transferred from device to host.\r
+\r
+ @param[in] ByteCount\r
+ data size in byte unit of the buffer.\r
+\r
+ @param[in] TimeOut\r
+ this parameter is used to specify the timeout \r
+ value for the PioReadWriteData() function. \r
+\r
+ @retval EFI_SUCCESS\r
+ send out the ATAPI packet command successfully\r
+ and device sends data successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ the device failed to send data.\r
+\r
+**/\r
EFI_STATUS\r
AtapiPacketCommandIn (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
IN UINT32 ByteCount,\r
IN UINTN TimeOut\r
)\r
-/*++\r
- Name:\r
- AtapiPacketCommandIn\r
-\r
- Purpose: \r
- This function is used to send out ATAPI commands conforms to the \r
- Packet Command with PIO Data In Protocol.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- ATAPI_PACKET_COMMAND IN *Packet\r
- pointer pointing to ATAPI_PACKET_COMMAND data structure\r
- which contains the contents of the command. \r
- \r
- UINT16 IN *Buffer\r
- buffer contained data transferred from device to host.\r
-\r
- UINT32 IN ByteCount\r
- data size in byte unit of the buffer.\r
-\r
- UINTN IN TimeOut\r
- this parameter is used to specify the timeout \r
- value for the PioReadWriteData() function. \r
-\r
- Returns: \r
- EFI_SUCCESS\r
- send out the ATAPI packet command successfully \r
- and device sends data successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- the device failed to send data. \r
-\r
- Notes:\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: Packet - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
-// TODO: ByteCount - add argument and description to function comment\r
-// TODO: TimeOut - add argument and description to function comment\r
{\r
UINT16 *CommandIndex;\r
EFI_STATUS Status;\r
return PioReadWriteData (IdeDev, Buffer, ByteCount, 1, TimeOut);\r
}\r
\r
+/**\r
+ This function is used to send out ATAPI commands conforms to the \r
+ Packet Command with PIO Data Out Protocol.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[in] *Packet\r
+ pointer pointing to ATAPI_PACKET_COMMAND data structure\r
+ which contains the contents of the command.\r
+\r
+ @param[in] *Buffer\r
+ buffer contained data transferred from host to device.\r
+\r
+ @param[in] ByteCount\r
+ data size in byte unit of the buffer.\r
+\r
+ @param[in] TimeOut\r
+ this parameter is used to specify the timeout \r
+ value for the PioReadWriteData() function. \r
+\r
+ @retval EFI_SUCCESS\r
+ send out the ATAPI packet command successfully\r
+ and device received data successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ the device failed to send data.\r
+\r
+**/\r
EFI_STATUS\r
AtapiPacketCommandOut (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
IN UINT32 ByteCount,\r
IN UINTN TimeOut\r
)\r
-/*++\r
- Name:\r
- AtapiPacketCommandOut\r
-\r
- Purpose: \r
- This function is used to send out ATAPI commands conforms to the \r
- Packet Command with PIO Data Out Protocol.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- ATAPI_PACKET_COMMAND IN *Packet\r
- pointer pointing to ATAPI_PACKET_COMMAND data structure\r
- which contains the contents of the command.\r
-\r
- VOID IN *Buffer\r
- buffer contained data transferred from host to device.\r
-\r
- UINT32 IN ByteCount\r
- data size in byte unit of the buffer.\r
-\r
- UINTN IN TimeOut\r
- this parameter is used to specify the timeout \r
- value for the PioReadWriteData() function. \r
-\r
- Returns: \r
- EFI_SUCCESS\r
- send out the ATAPI packet command successfully \r
- and device received data successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- the device failed to send data. \r
-\r
- Notes:\r
- \r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: Packet - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
-// TODO: ByteCount - add argument and description to function comment\r
-// TODO: TimeOut - add argument and description to function comment\r
{\r
UINT16 *CommandIndex;\r
EFI_STATUS Status;\r
return PioReadWriteData (IdeDev, Buffer, ByteCount, 0, TimeOut);\r
}\r
\r
+/**\r
+ This function is called by either AtapiPacketCommandIn() or \r
+ AtapiPacketCommandOut(). It is used to transfer data between\r
+ host and device. The data direction is specified by the fourth\r
+ parameter.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[in] *Buffer\r
+ buffer contained data transferred between host and device.\r
+\r
+ @param[in] ByteCount\r
+ data size in byte unit of the buffer.\r
+\r
+ @param[in] Read\r
+ flag used to determine the data transfer direction.\r
+ Read equals 1, means data transferred from device to host;\r
+ Read equals 0, means data transferred from host to device.\r
+\r
+ @param[in] TimeOut\r
+ timeout value for wait DRQ ready before each data \r
+ stream's transfer.\r
+\r
+ @retval EFI_SUCCESS\r
+ data is transferred successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ the device failed to transfer data.\r
+\r
+**/\r
EFI_STATUS\r
PioReadWriteData (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
IN BOOLEAN Read,\r
IN UINTN TimeOut\r
)\r
-/*++\r
- Name:\r
- PioReadWriteData\r
-\r
- Purpose: \r
- This function is called by either AtapiPacketCommandIn() or \r
- AtapiPacketCommandOut(). It is used to transfer data between\r
- host and device. The data direction is specified by the fourth\r
- parameter.\r
-\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- VOID IN *Buffer\r
- buffer contained data transferred between host and device.\r
-\r
- UINT32 IN ByteCount\r
- data size in byte unit of the buffer.\r
-\r
- BOOLEAN IN Read\r
- flag used to determine the data transfer direction.\r
- Read equals 1, means data transferred from device to host;\r
- Read equals 0, means data transferred from host to device.\r
-\r
- UINTN IN TimeOut\r
- timeout value for wait DRQ ready before each data \r
- stream's transfer.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- data is transferred successfully. \r
-\r
- EFI_DEVICE_ERROR\r
- the device failed to transfer data. \r
-\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
-// TODO: ByteCount - add argument and description to function comment\r
-// TODO: Read - add argument and description to function comment\r
-// TODO: TimeOut - add argument and description to function comment\r
{\r
//\r
// required transfer data in word unit.\r
EFI_STATUS Status;\r
UINT16 *PtrBuffer;\r
\r
- //\r
- // containing status byte read from Status Register.\r
- //\r
- UINT8 StatusRegister;\r
-\r
//\r
// No data transfer is premitted.\r
//\r
//\r
// read Status Register will clear interrupt\r
//\r
- StatusRegister = IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Status);\r
+ IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->Reg.Status);\r
\r
//\r
// get current data transfer size from Cylinder Registers.\r
//\r
- WordCount =\r
- (\r
- (IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->CylinderMsb) << 8) |\r
- IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->CylinderLsb)\r
- ) & 0xffff;\r
+ WordCount = IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->CylinderMsb) << 8;\r
+ WordCount = WordCount | IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->CylinderLsb);\r
+ WordCount = WordCount & 0xffff;\r
WordCount /= 2;\r
\r
WordCount = EFI_MIN (WordCount, (RequiredWordCount - ActualWordCount));\r
PtrBuffer += WordCount;\r
ActualWordCount += WordCount;\r
}\r
+ \r
+ if (Read) {\r
+ //\r
+ // In the case where the drive wants to send more data than we need to read,\r
+ // the DRQ bit will be set and cause delays from DRQClear2().\r
+ // We need to read data from the drive until it clears DRQ so we can move on.\r
+ //\r
+ AtapiReadPendingData (IdeDev);\r
+ }\r
\r
//\r
// After data transfer is completed, normally, DRQ bit should clear.\r
return CheckErrorStatus (IdeDev);\r
}\r
\r
-EFI_STATUS\r
-AtapiTestUnitReady (\r
- IN IDE_BLK_IO_DEV *IdeDev\r
- )\r
-/*++\r
- Name:\r
- AtapiTestUnitReady\r
-\r
- Purpose: \r
- Sends out ATAPI Test Unit Ready Packet Command to the specified device\r
- to find out whether device is accessible.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
+/**\r
+ Sends out ATAPI Test Unit Ready Packet Command to the specified device\r
+ to find out whether device is accessible.\r
\r
- Returns: \r
- EFI_SUCCESS\r
- device is accessible.\r
+ @param[in] *IdeDev Pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+ @param[in] *SenseCount Sense count for this packet command\r
\r
- EFI_DEVICE_ERROR\r
- device is not accessible.\r
+ @retval EFI_SUCCESS Device is accessible.\r
+ @retval EFI_DEVICE_ERROR Device is not accessible.\r
\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
+**/\r
+EFI_STATUS\r
+AtapiTestUnitReady (\r
+ IN IDE_BLK_IO_DEV *IdeDev,\r
+ OUT UINTN *SenseCount\r
+ )\r
{\r
ATAPI_PACKET_COMMAND Packet;\r
EFI_STATUS Status;\r
\r
+ *SenseCount = 0;\r
+\r
//\r
// fill command packet\r
//\r
// send command packet\r
//\r
Status = AtapiPacketCommandIn (IdeDev, &Packet, NULL, 0, ATAPITIMEOUT);\r
- return Status;\r
-}\r
-\r
-EFI_STATUS\r
-AtapiRequestSense (\r
- IN IDE_BLK_IO_DEV *IdeDev,\r
- OUT UINTN *SenseCounts\r
- )\r
-/*++\r
- Name:\r
- AtapiRequestSense\r
+ if (EFI_ERROR (Status)) {\r
+ return Status;\r
+ }\r
\r
- Purpose: \r
- Sends out ATAPI Request Sense Packet Command to the specified device.\r
- This command will return all the current Sense data in the device. \r
- This function will pack all the Sense data in one single buffer.\r
+ Status = AtapiRequestSense (IdeDev, SenseCount);\r
+ if (EFI_ERROR (Status)) {\r
+ *SenseCount = 0;\r
+ return Status;\r
+ }\r
\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
+ return EFI_SUCCESS;\r
+}\r
\r
- UINT16 OUT **SenseBuffers\r
- allocated in this function, and freed by the calling function.\r
- This buffer is used to accommodate all the sense data returned \r
- by the device.\r
+/**\r
+ Sends out ATAPI Request Sense Packet Command to the specified device.\r
+ This command will return all the current Sense data in the device. \r
+ This function will pack all the Sense data in one single buffer.\r
\r
- UINTN OUT *BufUnit\r
- record the unit size of the sense data block in the SenseBuffers,\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
\r
- UINTN OUT *BufNumbers\r
- record the number of units in the SenseBuffers.\r
+ @param[out] **SenseBuffers\r
+ allocated in this function, and freed by the calling function.\r
+ This buffer is used to accommodate all the sense data returned \r
+ by the device.\r
\r
- Returns: \r
- EFI_SUCCESS\r
- Request Sense command completes successfully.\r
+ @param[out] *BufUnit\r
+ record the unit size of the sense data block in the SenseBuffers,\r
\r
- EFI_DEVICE_ERROR\r
- Request Sense command failed.\r
+ @param[out] *BufNumbers\r
+ record the number of units in the SenseBuffers.\r
\r
- Notes:\r
+ @retval EFI_SUCCESS\r
+ Request Sense command completes successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ Request Sense command failed.\r
\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: SenseCounts - add argument and description to function comment\r
+**/\r
+EFI_STATUS\r
+AtapiRequestSense (\r
+ IN IDE_BLK_IO_DEV *IdeDev,\r
+ OUT UINTN *SenseCounts\r
+ )\r
{\r
EFI_STATUS Status;\r
REQUEST_SENSE_DATA *Sense;\r
//\r
// Ptr is word-based pointer\r
//\r
- Ptr += sizeof (REQUEST_SENSE_DATA) / 2;\r
+ Ptr += (sizeof (REQUEST_SENSE_DATA) + 1) >> 1;\r
\r
} else {\r
//\r
return EFI_SUCCESS;\r
}\r
\r
+/**\r
+ Sends out ATAPI Read Capacity Packet Command to the specified device.\r
+ This command will return the information regarding the capacity of the\r
+ media in the device.\r
+\r
+ Current device status will impact device's response to the Read Capacity\r
+ Command. For example, if the device once reset, the Read Capacity\r
+ Command will fail. The Sense data record the current device status, so \r
+ if the Read Capacity Command failed, the Sense data must be requested\r
+ and be analyzed to determine if the Read Capacity Command should retry.\r
+\r
+ @param[in] *IdeDev Pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+ @param[in] SenseCount Sense count for this packet command\r
+\r
+ @retval EFI_SUCCESS Read Capacity Command finally completes successfully.\r
+ @retval EFI_DEVICE_ERROR Read Capacity Command failed because of device error.\r
+\r
+ @note Parameter "IdeDev" will be updated in this function.\r
+\r
+ TODO: EFI_NOT_READY - add return value to function comment\r
+**/\r
EFI_STATUS\r
AtapiReadCapacity (\r
- IN IDE_BLK_IO_DEV *IdeDev\r
+ IN IDE_BLK_IO_DEV *IdeDev,\r
+ OUT UINTN *SenseCount\r
)\r
-/*++\r
- Name:\r
- AtapiReadCapacity\r
-\r
- Purpose: \r
- Sends out ATAPI Read Capacity Packet Command to the specified device.\r
- This command will return the information regarding the capacity of the\r
- media in the device.\r
-\r
- Current device status will impact device's response to the Read Capacity\r
- Command. For example, if the device once reset, the Read Capacity\r
- Command will fail. The Sense data record the current device status, so \r
- if the Read Capacity Command failed, the Sense data must be requested\r
- and be analyzed to determine if the Read Capacity Command should retry.\r
-\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- Read Capacity Command finally completes successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- Read Capacity Command failed because of device error.\r
-\r
- Notes:\r
- parameter "IdeDev" will be updated in this function.\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: EFI_NOT_READY - add return value to function comment\r
{\r
//\r
// status returned by Read Capacity Packet Command\r
//\r
EFI_STATUS Status;\r
+ EFI_STATUS SenseStatus;\r
ATAPI_PACKET_COMMAND Packet;\r
\r
//\r
READ_CAPACITY_DATA Data;\r
READ_FORMAT_CAPACITY_DATA FormatData;\r
\r
+ *SenseCount = 0;\r
+\r
ZeroMem (&Data, sizeof (Data));\r
ZeroMem (&FormatData, sizeof (FormatData));\r
\r
ZeroMem (&Packet, sizeof (ATAPI_PACKET_COMMAND));\r
Packet.Inquiry.opcode = READ_CAPACITY;\r
Status = AtapiPacketCommandIn (\r
- IdeDev,\r
- &Packet,\r
- (UINT16 *) &Data,\r
- sizeof (READ_CAPACITY_DATA),\r
- ATAPITIMEOUT\r
- );\r
+ IdeDev,\r
+ &Packet,\r
+ (UINT16 *) &Data,\r
+ sizeof (READ_CAPACITY_DATA),\r
+ ATAPITIMEOUT\r
+ );\r
\r
} else {\r
//\r
Packet.ReadFormatCapacity.opcode = READ_FORMAT_CAPACITY;\r
Packet.ReadFormatCapacity.allocation_length_lo = 12;\r
Status = AtapiPacketCommandIn (\r
- IdeDev,\r
- &Packet,\r
- (UINT16 *) &FormatData,\r
- sizeof (READ_FORMAT_CAPACITY_DATA),\r
- ATAPITIMEOUT\r
- );\r
+ IdeDev,\r
+ &Packet,\r
+ (UINT16 *) &FormatData,\r
+ sizeof (READ_FORMAT_CAPACITY_DATA),\r
+ ATAPITIMEOUT\r
+ );\r
}\r
\r
- if (!EFI_ERROR (Status)) {\r
-\r
- if (IdeDev->Type == IdeCdRom) {\r
-\r
- IdeDev->BlkIo.Media->LastBlock = (Data.LastLba3 << 24) |\r
- (Data.LastLba2 << 16) |\r
- (Data.LastLba1 << 8) |\r
- Data.LastLba0;\r
-\r
- if (IdeDev->BlkIo.Media->LastBlock != 0) {\r
-\r
- IdeDev->BlkIo.Media->BlockSize = (Data.BlockSize3 << 24) |\r
- (Data.BlockSize2 << 16) |\r
- (Data.BlockSize1 << 8) |\r
- Data.BlockSize0;\r
+ if (Status == EFI_TIMEOUT) {\r
+ *SenseCount = 0;\r
+ return Status;\r
+ }\r
\r
- IdeDev->BlkIo.Media->MediaPresent = TRUE;\r
- } else {\r
- IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
- return EFI_DEVICE_ERROR;\r
- }\r
+ SenseStatus = AtapiRequestSense (IdeDev, SenseCount);\r
\r
- IdeDev->BlkIo.Media->ReadOnly = TRUE;\r
+ if (!EFI_ERROR (SenseStatus)) {\r
\r
- //\r
- // Because the user data portion in the sector of the Data CD supported\r
- // is always 0x800\r
- //\r
- IdeDev->BlkIo.Media->BlockSize = 0x800;\r
- }\r
+ if (!EFI_ERROR (Status)) {\r
\r
- if (IdeDev->Type == IdeMagnetic) {\r
+ if (IdeDev->Type == IdeCdRom) {\r
\r
- if (FormatData.DesCode == 3) {\r
- IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
- IdeDev->BlkIo.Media->LastBlock = 0;\r
- } else {\r
+ IdeDev->BlkIo.Media->LastBlock = (Data.LastLba3 << 24) |\r
+ (Data.LastLba2 << 16) |\r
+ (Data.LastLba1 << 8) |\r
+ Data.LastLba0;\r
\r
- IdeDev->BlkIo.Media->LastBlock = (FormatData.LastLba3 << 24) |\r
- (FormatData.LastLba2 << 16) | \r
- (FormatData.LastLba1 << 8) |\r
- FormatData.LastLba0;\r
if (IdeDev->BlkIo.Media->LastBlock != 0) {\r
- IdeDev->BlkIo.Media->LastBlock--;\r
\r
- IdeDev->BlkIo.Media->BlockSize = (FormatData.BlockSize2 << 16) |\r
- (FormatData.BlockSize1 << 8) |\r
- FormatData.BlockSize0;\r
+ IdeDev->BlkIo.Media->BlockSize = (Data.BlockSize3 << 24) |\r
+ (Data.BlockSize2 << 16) |\r
+ (Data.BlockSize1 << 8) |\r
+ Data.BlockSize0;\r
\r
IdeDev->BlkIo.Media->MediaPresent = TRUE;\r
} else {\r
IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
- //\r
- // Return EFI_NOT_READY operation succeeds but returned capacity is 0\r
- //\r
- return EFI_NOT_READY;\r
+ return EFI_DEVICE_ERROR;\r
}\r
\r
- IdeDev->BlkIo.Media->BlockSize = 0x200;\r
+ IdeDev->BlkIo.Media->ReadOnly = TRUE;\r
+\r
+ //\r
+ // Because the user data portion in the sector of the Data CD supported\r
+ // is always 0x800\r
+ //\r
+ IdeDev->BlkIo.Media->BlockSize = 0x800;\r
+ }\r
+\r
+ if (IdeDev->Type == IdeMagnetic) {\r
+\r
+ if (FormatData.DesCode == 3) {\r
+ IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
+ IdeDev->BlkIo.Media->LastBlock = 0;\r
+ } else {\r
+\r
+ IdeDev->BlkIo.Media->LastBlock = (FormatData.LastLba3 << 24) |\r
+ (FormatData.LastLba2 << 16) | \r
+ (FormatData.LastLba1 << 8) |\r
+ FormatData.LastLba0;\r
+ if (IdeDev->BlkIo.Media->LastBlock != 0) {\r
+ IdeDev->BlkIo.Media->LastBlock--;\r
+\r
+ IdeDev->BlkIo.Media->BlockSize = (FormatData.BlockSize2 << 16) |\r
+ (FormatData.BlockSize1 << 8) |\r
+ FormatData.BlockSize0;\r
+\r
+ IdeDev->BlkIo.Media->MediaPresent = TRUE;\r
+ } else {\r
+ IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
+ //\r
+ // Return EFI_NOT_READY operation succeeds but returned capacity is 0\r
+ //\r
+ return EFI_NOT_READY;\r
+ }\r
\r
+ IdeDev->BlkIo.Media->BlockSize = 0x200;\r
+\r
+ }\r
}\r
}\r
\r
return EFI_SUCCESS;\r
\r
} else {\r
-\r
+ *SenseCount = 0;\r
return EFI_DEVICE_ERROR;\r
}\r
}\r
\r
+/**\r
+ Used before read/write blocks from/to ATAPI device media. \r
+ Since ATAPI device media is removable, it is necessary to detect\r
+ whether media is present and get current present media's\r
+ information, and if media has been changed, Block I/O Protocol\r
+ need to be reinstalled.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[out] *MediaChange\r
+ return value that indicates if the media of the device has been\r
+ changed.\r
+\r
+ @retval EFI_SUCCESS\r
+ media found successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ any error encounters during media detection.\r
+ \r
+ @retval EFI_NO_MEDIA\r
+ media not found.\r
+\r
+ @note\r
+ parameter IdeDev may be updated in this function.\r
+\r
+**/\r
EFI_STATUS\r
AtapiDetectMedia (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
OUT BOOLEAN *MediaChange\r
)\r
-/*++\r
- Name:\r
- AtapiDetectMedia\r
-\r
- Purpose: \r
- Used before read/write blocks from/to ATAPI device media. \r
- Since ATAPI device media is removable, it is necessary to detect\r
- whether media is present and get current present media's\r
- information, and if media has been changed, Block I/O Protocol\r
- need to be reinstalled.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- BOOLEAN OUT *MediaChange\r
- return value that indicates if the media of the device has been\r
- changed.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- media found successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- any error encounters during media detection.\r
- \r
- EFI_NO_MEDIA\r
- media not found.\r
-\r
- Notes:\r
- parameter IdeDev may be updated in this function.\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: MediaChange - add argument and description to function comment\r
{\r
- EFI_STATUS Status;\r
- EFI_STATUS ReadCapacityStatus;\r
- EFI_BLOCK_IO_MEDIA OldMediaInfo;\r
- UINTN SenseCounts;\r
- UINTN RetryIndex;\r
- UINTN RetryTimes;\r
- UINTN MaximumRetryTimes;\r
- UINTN ReadyWaitFactor;\r
- BOOLEAN NeedRetry;\r
- //\r
- // a flag used to determine whether need to perform Read Capacity command.\r
- //\r
- BOOLEAN NeedReadCapacity;\r
- BOOLEAN WriteProtected;\r
+ EFI_STATUS Status;\r
+ EFI_STATUS CleanStateStatus;\r
+ EFI_BLOCK_IO_MEDIA OldMediaInfo;\r
+ UINTN RetryTimes;\r
+ UINTN RetryNotReady;\r
+ UINTN SenseCount;\r
+ SENSE_RESULT SResult;\r
+ BOOLEAN WriteProtected;\r
\r
+ CopyMem (&OldMediaInfo, IdeDev->BlkIo.Media, sizeof (EFI_BLOCK_IO_MEDIA));\r
+ *MediaChange = FALSE;\r
//\r
- // init\r
+ // Retry for SenseDeviceNotReadyNeedRetry.\r
+ // Each retry takes 1s and we limit the upper boundary to\r
+ // 120 times about 2 min.\r
//\r
- CopyMem (&OldMediaInfo, IdeDev->BlkIo.Media, sizeof (OldMediaInfo));\r
- // OldMediaInfo = *(IdeDev->BlkIo.Media);\r
- *MediaChange = FALSE;\r
- ReadCapacityStatus = EFI_DEVICE_ERROR;\r
+ RetryNotReady = 120;\r
\r
//\r
- // if there is no media, or media is not changed,\r
- // the request sense command will detect faster than read capacity command.\r
- // read capacity command can be bypassed, thus improve performance.\r
+ // Do Test Unit Ready\r
//\r
-\r
+ DoTUR:\r
//\r
- // Test Unit Ready command is used to detect whether device is accessible,\r
- // the device will produce corresponding Sense data.\r
+ // Retry 5 times\r
//\r
- for (RetryIndex = 0; RetryIndex < 2; RetryIndex++) {\r
-\r
- Status = AtapiTestUnitReady (IdeDev);\r
- if (!EFI_ERROR (Status)) {\r
- //\r
- // skip the loop if test unit command succeeds.\r
- //\r
- break;\r
- }\r
+ RetryTimes = 5;\r
+ while (RetryTimes != 0) {\r
\r
- Status = AtapiSoftReset (IdeDev);\r
+ Status = AtapiTestUnitReady (IdeDev, &SenseCount);\r
\r
if (EFI_ERROR (Status)) {\r
- AtaSoftReset (IdeDev);\r
- }\r
- }\r
-\r
- SenseCounts = 0;\r
- NeedReadCapacity = TRUE;\r
-\r
- //\r
- // at most retry 5 times\r
- //\r
- MaximumRetryTimes = 5;\r
- RetryTimes = 1;\r
-\r
- for (RetryIndex = 0; \r
- (RetryIndex < RetryTimes) && (RetryIndex < MaximumRetryTimes);\r
- RetryIndex++) {\r
-\r
- Status = AtapiRequestSense (IdeDev, &SenseCounts);\r
-\r
- if (!EFI_ERROR (Status)) {\r
//\r
- // if first time there is no Sense Key, no need to read capacity any more\r
+ // Test Unit Ready error without sense data.\r
+ // For some devices, this means there's extra data\r
+ // that has not been read, so we read these extra\r
+ // data out before going on.\r
//\r
- if (!HaveSenseKey (IdeDev->SenseData, SenseCounts) &&\r
- (IdeDev->BlkIo.Media->MediaPresent)) {\r
-\r
- if (RetryIndex == 0) {\r
- NeedReadCapacity = FALSE;\r
- }\r
-\r
- } else {\r
+ CleanStateStatus = AtapiReadPendingData (IdeDev);\r
+ if (EFI_ERROR (CleanStateStatus)) {\r
//\r
- // No Media\r
+ // Busy wait failed, try again\r
//\r
- if (IsNoMedia (IdeDev->SenseData, SenseCounts)) {\r
- NeedReadCapacity = FALSE;\r
- IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
- IdeDev->BlkIo.Media->LastBlock = 0;\r
+ RetryTimes--;\r
+ }\r
+ //\r
+ // Try again without counting down RetryTimes\r
+ //\r
+ continue;\r
+ } else {\r
+\r
+ ParseSenseData (IdeDev, SenseCount, &SResult);\r
+\r
+ switch (SResult) {\r
+ case SenseNoSenseKey:\r
+ if (IdeDev->BlkIo.Media->MediaPresent) {\r
+ goto Done;\r
} else {\r
//\r
- // Media Changed\r
- //\r
- if (IsMediaChange (IdeDev->SenseData, SenseCounts)) {\r
- NeedReadCapacity = TRUE;\r
- IdeDev->BlkIo.Media->MediaId++;\r
- }\r
- //\r
- // Media Error\r
+ // Media present but the internal structure need refreshed.\r
+ // Try Read Capacity\r
//\r
- if (IsMediaError (IdeDev->SenseData, SenseCounts)) {\r
- return EFI_DEVICE_ERROR;\r
- }\r
+ goto DoRC;\r
+ }\r
+ break;\r
+\r
+ case SenseDeviceNotReadyNeedRetry:\r
+ if (--RetryNotReady == 0) {\r
+ return EFI_DEVICE_ERROR;\r
}\r
+ gBS->Stall (1000 * STALL_1_MILLI_SECOND);\r
+ continue;\r
+ break;\r
+\r
+ case SenseNoMedia:\r
+ IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
+ IdeDev->BlkIo.Media->LastBlock = 0;\r
+ goto Done;\r
+ break;\r
+\r
+ case SenseDeviceNotReadyNoRetry:\r
+ case SenseMediaError:\r
+ return EFI_DEVICE_ERROR;\r
+\r
+ case SenseMediaChange:\r
+ IdeDev->BlkIo.Media->MediaId++;\r
+ goto DoRC;\r
+ break;\r
+\r
+ default:\r
+ RetryTimes--;\r
+ break;\r
}\r
- } else {\r
- //\r
- // retry once more, if request sense command met errors.\r
- //\r
- RetryTimes++;\r
}\r
}\r
\r
- if (NeedReadCapacity) {\r
- //\r
- // at most retry 5 times\r
- //\r
- MaximumRetryTimes = 5;\r
- //\r
- // initial retry twice\r
- //\r
- RetryTimes = 2;\r
- ReadyWaitFactor = 2;\r
-\r
- for (RetryIndex = 0;\r
- (RetryIndex < RetryTimes) && (RetryIndex < MaximumRetryTimes);\r
- RetryIndex++) {\r
+ return EFI_DEVICE_ERROR;\r
\r
- ReadCapacityStatus = AtapiReadCapacity (IdeDev);\r
+ //\r
+ // Do Read Capacity\r
+ //\r
+ DoRC:\r
+ RetryTimes = 5;\r
\r
- SenseCounts = 0;\r
+ while (RetryTimes != 0) {\r
\r
- if (!EFI_ERROR (ReadCapacityStatus)) {\r
- //\r
- // Read Capacity succeeded\r
- //\r
- break;\r
+ Status = AtapiReadCapacity (IdeDev, &SenseCount);\r
\r
+ if (EFI_ERROR (Status)) {\r
+ RetryTimes--;\r
+ continue;\r
} else {\r
\r
- if (ReadCapacityStatus == EFI_NOT_READY) {\r
- //\r
- // If device not ready, wait here... waiting time increases by retry\r
- // times.\r
- //\r
- gBS->Stall (ReadyWaitFactor * 2000 * STALL_1_MILLI_SECOND);\r
- ReadyWaitFactor++;\r
- //\r
- // retry once more\r
- //\r
- RetryTimes++;\r
- continue;\r
- }\r
- \r
- //\r
- // Other errors returned, requery sense data\r
- //\r
- Status = AtapiRequestSense (IdeDev, &SenseCounts);\r
+ ParseSenseData (IdeDev, SenseCount, &SResult);\r
\r
- //\r
- // If Request Sense data failed, reset the device and retry.\r
- //\r
- if (EFI_ERROR (Status)) {\r
-\r
- Status = AtapiSoftReset (IdeDev);\r
+ switch (SResult) {\r
+ case SenseNoSenseKey:\r
+ goto Done;\r
+ break;\r
\r
+ case SenseDeviceNotReadyNeedRetry:\r
//\r
- // if ATAPI soft reset fail,\r
- // use stronger reset mechanism -- ATA soft reset.\r
+ // We use Test Unit Ready to retry which\r
+ // is faster.\r
//\r
- if (EFI_ERROR (Status)) {\r
- AtaSoftReset (IdeDev);\r
- }\r
- //\r
- // retry once more\r
- //\r
- RetryTimes++;\r
- continue;\r
- }\r
- \r
- //\r
- // No Media\r
- //\r
- if (IsNoMedia (IdeDev->SenseData, SenseCounts)) {\r
+ goto DoTUR;\r
+ break;\r
\r
+ case SenseNoMedia:\r
IdeDev->BlkIo.Media->MediaPresent = FALSE;\r
IdeDev->BlkIo.Media->LastBlock = 0;\r
- return EFI_NO_MEDIA;\r
- }\r
+ goto Done;\r
+ break;\r
\r
- if (IsMediaError (IdeDev->SenseData, SenseCounts)) {\r
+ case SenseDeviceNotReadyNoRetry:\r
+ case SenseMediaError:\r
return EFI_DEVICE_ERROR;\r
- }\r
- \r
- //\r
- // Media Changed\r
- //\r
- if (IsMediaChange (IdeDev->SenseData, SenseCounts)) {\r
+\r
+ case SenseMediaChange:\r
IdeDev->BlkIo.Media->MediaId++;\r
- }\r
+ continue;\r
+ break;\r
\r
- if (!IsDriveReady (IdeDev->SenseData, SenseCounts, &NeedRetry)) {\r
- \r
- //\r
- // Drive not ready: if NeedRetry, then retry once more;\r
- // else return error\r
- //\r
- if (NeedRetry) {\r
- //\r
- // Stall 1 second to wait for drive becoming ready\r
- //\r
- gBS->Stall (1000 * STALL_1_MILLI_SECOND);\r
- //\r
- // reset retry variable to zero,\r
- // to make it retry for "drive in progress of becoming ready".\r
- //\r
- RetryIndex = 0;\r
- continue;\r
- } else {\r
- AtapiSoftReset (IdeDev);\r
- return EFI_DEVICE_ERROR;\r
- }\r
+ default:\r
+ RetryTimes--;\r
+ break;\r
}\r
- //\r
- // if read capacity fail not for above reasons, retry once more\r
- //\r
- RetryTimes++;\r
}\r
-\r
- }\r
- \r
- //\r
- // tell whether the readcapacity process is successful or not in the end\r
- //\r
- if (EFI_ERROR (ReadCapacityStatus)) {\r
- return EFI_DEVICE_ERROR;\r
}\r
- }\r
\r
+ return EFI_DEVICE_ERROR;\r
+\r
+ Done:\r
//\r
// the following code is to check the write-protected for LS120 media\r
//\r
);\r
}\r
\r
- return EFI_SUCCESS;\r
-\r
+ if (IdeDev->BlkIo.Media->MediaPresent) {\r
+ return EFI_SUCCESS;\r
+ } else {\r
+ return EFI_NO_MEDIA;\r
+ }\r
}\r
\r
+/**\r
+ This function is called by the AtapiBlkIoReadBlocks() to perform\r
+ read from media in block unit.\r
+\r
+ The main command used to access media here is READ(10) Command. \r
+ READ(10) Command requests that the ATAPI device media transfer \r
+ specified data to the host. Data is transferred in block(sector) \r
+ unit. The maximum number of blocks that can be transferred once is\r
+ 65536. This is the main difference between READ(10) and READ(12) \r
+ Command. The maximum number of blocks in READ(12) is 2 power 32.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[in] *Buffer\r
+ A pointer to the destination buffer for the data. \r
+\r
+ @param[in] Lba\r
+ The starting logical block address to read from \r
+ on the device media.\r
+\r
+ @param[in] NumberOfBlocks\r
+ The number of transfer data blocks.\r
+\r
+ @return status is fully dependent on the return status\r
+ of AtapiPacketCommandIn() function.\r
+\r
+**/\r
EFI_STATUS\r
AtapiReadSectors (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
IN EFI_LBA Lba,\r
IN UINTN NumberOfBlocks\r
)\r
-/*++\r
- Name:\r
- AtapiReadSectors\r
-\r
- Purpose: \r
- This function is called by the AtapiBlkIoReadBlocks() to perform\r
- read from media in block unit.\r
-\r
- The main command used to access media here is READ(10) Command. \r
- READ(10) Command requests that the ATAPI device media transfer \r
- specified data to the host. Data is transferred in block(sector) \r
- unit. The maximum number of blocks that can be transferred once is\r
- 65536. This is the main difference between READ(10) and READ(12) \r
- Command. The maximum number of blocks in READ(12) is 2 power 32.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- VOID IN *Buffer\r
- A pointer to the destination buffer for the data. \r
-\r
- EFI_LBA IN Lba\r
- The starting logical block address to read from \r
- on the device media.\r
-\r
- UINTN IN NumberOfBlocks\r
- The number of transfer data blocks.\r
-\r
- Returns: \r
- return status is fully dependent on the return status\r
- of AtapiPacketCommandIn() function.\r
-\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
-// TODO: Lba - add argument and description to function comment\r
-// TODO: NumberOfBlocks - add argument and description to function comment\r
{\r
\r
ATAPI_PACKET_COMMAND Packet;\r
//\r
// limit the data bytes that can be transferred by one Read(10) Command\r
//\r
- MaxBlock = (UINT16) (65536 / BlockSize);\r
+ MaxBlock = 65535;\r
\r
BlocksRemaining = NumberOfBlocks;\r
\r
return Status;\r
}\r
\r
+/**\r
+ This function is called by the AtapiBlkIoWriteBlocks() to perform\r
+ write onto media in block unit.\r
+ The main command used to access media here is Write(10) Command. \r
+ Write(10) Command requests that the ATAPI device media transfer \r
+ specified data to the host. Data is transferred in block (sector) \r
+ unit. The maximum number of blocks that can be transferred once is\r
+ 65536. \r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @param[in] *Buffer\r
+ A pointer to the source buffer for the data. \r
+\r
+ @param[in] Lba\r
+ The starting logical block address to write onto \r
+ the device media.\r
+\r
+ @param[in] NumberOfBlocks\r
+ The number of transfer data blocks.\r
+\r
+ @return status is fully dependent on the return status\r
+ of AtapiPacketCommandOut() function.\r
+\r
+**/\r
EFI_STATUS\r
AtapiWriteSectors (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
IN EFI_LBA Lba,\r
IN UINTN NumberOfBlocks\r
)\r
-/*++\r
- Name:\r
- AtapiWriteSectors\r
-\r
- Purpose: \r
- This function is called by the AtapiBlkIoWriteBlocks() to perform\r
- write onto media in block unit.\r
- The main command used to access media here is Write(10) Command. \r
- Write(10) Command requests that the ATAPI device media transfer \r
- specified data to the host. Data is transferred in block (sector) \r
- unit. The maximum number of blocks that can be transferred once is\r
- 65536. \r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- VOID IN *Buffer\r
- A pointer to the source buffer for the data. \r
-\r
- EFI_LBA IN Lba\r
- The starting logical block address to write onto \r
- the device media.\r
-\r
- UINTN IN NumberOfBlocks\r
- The number of transfer data blocks.\r
-\r
- Returns: \r
- return status is fully dependent on the return status\r
- of AtapiPacketCommandOut() function.\r
-\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
-// TODO: Lba - add argument and description to function comment\r
-// TODO: NumberOfBlocks - add argument and description to function comment\r
{\r
\r
ATAPI_PACKET_COMMAND Packet;\r
return Status;\r
}\r
\r
+/**\r
+ This function is used to implement the Soft Reset on the specified\r
+ ATAPI device. Different from the AtaSoftReset(), here reset is a ATA\r
+ Soft Reset Command special for ATAPI device, and it only take effects\r
+ on the specified ATAPI device, not on the whole IDE bus.\r
+ Since the ATAPI soft reset is needed when device is in exceptional\r
+ condition (such as BSY bit is always set ), I think the Soft Reset\r
+ command should be sent without waiting for the BSY clear and DRDY\r
+ set.\r
+ This function is called by IdeBlkIoReset(), \r
+ a interface function of Block I/O protocol.\r
+\r
+ @param[in] *IdeDev\r
+ pointer pointing to IDE_BLK_IO_DEV data structure, used\r
+ to record all the information of the IDE device.\r
+\r
+ @retval EFI_SUCCESS\r
+ Soft reset completes successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ Any step during the reset process is failed.\r
+\r
+**/\r
EFI_STATUS\r
AtapiSoftReset (\r
IN IDE_BLK_IO_DEV *IdeDev\r
)\r
-/*++\r
- Name:\r
- AtapiSoftReset\r
-\r
- Purpose: \r
- This function is used to implement the Soft Reset on the specified\r
- ATAPI device. Different from the AtaSoftReset(), here reset is a ATA\r
- Soft Reset Command special for ATAPI device, and it only take effects\r
- on the specified ATAPI device, not on the whole IDE bus.\r
- Since the ATAPI soft reset is needed when device is in exceptional\r
- condition (such as BSY bit is always set ), I think the Soft Reset\r
- command should be sent without waiting for the BSY clear and DRDY\r
- set.\r
- This function is called by IdeBlkIoReset(), \r
- a interface function of Block I/O protocol.\r
-\r
- \r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeDev\r
- pointer pointing to IDE_BLK_IO_DEV data structure, used\r
- to record all the information of the IDE device.\r
-\r
- Returns: \r
- EFI_SUCCESS\r
- Soft reset completes successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- Any step during the reset process is failed.\r
-\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeDev - add argument and description to function comment\r
{\r
UINT8 Command;\r
UINT8 DeviceSelect;\r
return EFI_SUCCESS;\r
}\r
\r
+/**\r
+ This function is the ATAPI implementation for ReadBlocks in the\r
+ Block I/O Protocol interface.\r
+\r
+ @param[in] *IdeBlkIoDev\r
+ Indicates the calling context.\r
+\r
+ @param[in] MediaId\r
+ The media id that the read request is for.\r
+\r
+ @param[in] LBA\r
+ The starting logical block address to read from \r
+ on the device.\r
+\r
+ @param[in] BufferSize\r
+ The size of the Buffer in bytes. This must be a\r
+ multiple of the intrinsic block size of the device.\r
+\r
+ @param[out] *Buffer\r
+ A pointer to the destination buffer for the data. \r
+ The caller is responsible for either having implicit\r
+ or explicit ownership of the memory that data is read into.\r
+\r
+ @retval EFI_SUCCESS\r
+ Read Blocks successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ Read Blocks failed.\r
+ \r
+ @retval EFI_NO_MEDIA\r
+ There is no media in the device.\r
+ \r
+ @retval EFI_MEDIA_CHANGED\r
+ The MediaId is not for the current media.\r
+ \r
+ @retval EFI_BAD_BUFFER_SIZE\r
+ The BufferSize parameter is not a multiple of the\r
+ intrinsic block size of the device.\r
+ \r
+ @retval EFI_INVALID_PARAMETER\r
+ The read request contains LBAs that are not valid,\r
+ or the data buffer is not valid.\r
+\r
+**/\r
EFI_STATUS\r
AtapiBlkIoReadBlocks (\r
IN IDE_BLK_IO_DEV *IdeBlkIoDevice,\r
IN UINTN BufferSize,\r
OUT VOID *Buffer\r
)\r
-/*++\r
- Name:\r
- AtapiBlkIoReadBlocks\r
-\r
- Purpose: \r
- This function is the ATAPI implementation for ReadBlocks in the\r
- Block I/O Protocol interface.\r
-\r
- Parameters:\r
- IDE_BLK_IO_DEV IN *IdeBlkIoDev\r
- Indicates the calling context.\r
-\r
- UINT32 IN MediaId\r
- The media id that the read request is for.\r
-\r
- EFI_LBA IN LBA\r
- The starting logical block address to read from \r
- on the device.\r
-\r
- UINTN IN BufferSize\r
- The size of the Buffer in bytes. This must be a\r
- multiple of the intrinsic block size of the device.\r
-\r
- VOID OUT *Buffer\r
- A pointer to the destination buffer for the data. \r
- The caller is responsible for either having implicit\r
- or explicit ownership of the memory that data is read into.\r
-\r
- Returns: \r
- EFI_SUCCESS \r
- Read Blocks successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- Read Blocks failed.\r
-\r
- EFI_NO_MEDIA\r
- There is no media in the device.\r
-\r
- EFI_MEDIA_CHANGED\r
- The MediaId is not for the current media.\r
-\r
- EFI_BAD_BUFFER_SIZE\r
- The BufferSize parameter is not a multiple of the \r
- intrinsic block size of the device.\r
-\r
- EFI_INVALID_PARAMETER\r
- The read request contains LBAs that are not valid,\r
- or the data buffer is not valid.\r
-\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeBlkIoDevice - add argument and description to function comment\r
-// TODO: MediaId - add argument and description to function comment\r
-// TODO: LBA - add argument and description to function comment\r
-// TODO: BufferSize - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
{\r
EFI_BLOCK_IO_MEDIA *Media;\r
UINTN BlockSize;\r
\r
}\r
\r
+/**\r
+ This function is the ATAPI implementation for WriteBlocks in the\r
+ Block I/O Protocol interface.\r
+\r
+ @param[in] *This\r
+ Indicates the calling context.\r
+\r
+ @param[in] MediaId\r
+ The media id that the write request is for.\r
+\r
+ @param[in] LBA\r
+ The starting logical block address to write onto \r
+ the device.\r
+\r
+ @param[in] BufferSize\r
+ The size of the Buffer in bytes. This must be a\r
+ multiple of the intrinsic block size of the device.\r
+\r
+ @param[out] *Buffer\r
+ A pointer to the source buffer for the data. \r
+ The caller is responsible for either having implicit\r
+ or explicit ownership of the memory that data is \r
+ written from.\r
+\r
+ @retval EFI_SUCCESS\r
+ Write Blocks successfully.\r
+ \r
+ @retval EFI_DEVICE_ERROR\r
+ Write Blocks failed.\r
+ \r
+ @retval EFI_NO_MEDIA\r
+ There is no media in the device.\r
+ \r
+ @retval EFI_MEDIA_CHANGE\r
+ The MediaId is not for the current media.\r
+ \r
+ @retval EFI_BAD_BUFFER_SIZE\r
+ The BufferSize parameter is not a multiple of the\r
+ intrinsic block size of the device.\r
+ \r
+ @retval EFI_INVALID_PARAMETER\r
+ The write request contains LBAs that are not valid,\r
+ or the data buffer is not valid.\r
+\r
+ TODO: EFI_MEDIA_CHANGED - add return value to function comment\r
+ TODO: EFI_WRITE_PROTECTED - add return value to function comment\r
+**/\r
EFI_STATUS\r
AtapiBlkIoWriteBlocks (\r
IN IDE_BLK_IO_DEV *IdeBlkIoDevice,\r
IN UINTN BufferSize,\r
OUT VOID *Buffer\r
)\r
-/*++\r
- Name:\r
- AtapiBlkIoWriteBlocks\r
-\r
- Purpose: \r
- This function is the ATAPI implementation for WriteBlocks in the\r
- Block I/O Protocol interface.\r
-\r
- Parameters:\r
- EFI_BLOCK_IO IN *This\r
- Indicates the calling context.\r
-\r
- UINT32 IN MediaId\r
- The media id that the write request is for.\r
-\r
- EFI_LBA IN LBA\r
- The starting logical block address to write onto \r
- the device.\r
-\r
- UINTN IN BufferSize\r
- The size of the Buffer in bytes. This must be a\r
- multiple of the intrinsic block size of the device.\r
-\r
- VOID OUT *Buffer\r
- A pointer to the source buffer for the data. \r
- The caller is responsible for either having implicit\r
- or explicit ownership of the memory that data is \r
- written from.\r
-\r
- Returns: \r
- EFI_SUCCESS \r
- Write Blocks successfully.\r
-\r
- EFI_DEVICE_ERROR\r
- Write Blocks failed.\r
-\r
- EFI_NO_MEDIA\r
- There is no media in the device.\r
-\r
- EFI_MEDIA_CHANGE\r
- The MediaId is not for the current media.\r
-\r
- EFI_BAD_BUFFER_SIZE\r
- The BufferSize parameter is not a multiple of the \r
- intrinsic block size of the device.\r
-\r
- EFI_INVALID_PARAMETER\r
- The write request contains LBAs that are not valid,\r
- or the data buffer is not valid. \r
-\r
- Notes:\r
-\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: IdeBlkIoDevice - add argument and description to function comment\r
-// TODO: MediaId - add argument and description to function comment\r
-// TODO: LBA - add argument and description to function comment\r
-// TODO: BufferSize - add argument and description to function comment\r
-// TODO: Buffer - add argument and description to function comment\r
-// TODO: EFI_MEDIA_CHANGED - add return value to function comment\r
-// TODO: EFI_WRITE_PROTECTED - add return value to function comment\r
{\r
\r
EFI_BLOCK_IO_MEDIA *Media;\r
\r
}\r
\r
-//\r
-// The following functions are a set of helper functions,\r
-// which are used to parse sense key returned by the device.\r
-//\r
-\r
-BOOLEAN\r
-IsNoMedia (\r
- IN REQUEST_SENSE_DATA *SenseData,\r
- IN UINTN SenseCounts\r
- )\r
-/*++\r
-\r
-Routine Description:\r
-\r
- TODO: Add function description\r
-\r
-Arguments:\r
+/**\r
+ This function is used to parse sense data. Only the first\r
+ sense data is honoured.\r
\r
- SenseData - TODO: add argument description\r
- SenseCounts - TODO: add argument description\r
+ @param[in] IdeDev Indicates the calling context.\r
+ @param[in] SenseCount Count of sense data.\r
+ @param[out] Result The parsed result.\r
\r
-Returns:\r
-\r
- TODO: add return values\r
-\r
---*/\r
-{\r
- REQUEST_SENSE_DATA *SensePointer;\r
- UINTN Index;\r
- BOOLEAN NoMedia;\r
-\r
- NoMedia = FALSE;\r
- SensePointer = SenseData;\r
-\r
- for (Index = 0; Index < SenseCounts; Index++) {\r
- //\r
- // Sense Key is SK_NOT_READY (0x2),\r
- // Additional Sense Code is ASC_NO_MEDIA (0x3A)\r
- //\r
- if ((SensePointer->sense_key == SK_NOT_READY) &&\r
- (SensePointer->addnl_sense_code == ASC_NO_MEDIA)) {\r
+ @retval EFI_SUCCESS Successfully parsed.\r
+ @retval EFI_INVALID_PARAMETER Count of sense data is zero.\r
\r
- NoMedia = TRUE;\r
- }\r
-\r
- SensePointer++;\r
- }\r
-\r
- return NoMedia;\r
-}\r
-\r
-BOOLEAN\r
-IsMediaError (\r
- IN REQUEST_SENSE_DATA *SenseData,\r
- IN UINTN SenseCounts\r
+**/\r
+EFI_STATUS\r
+ParseSenseData (\r
+ IN IDE_BLK_IO_DEV *IdeDev,\r
+ IN UINTN SenseCount,\r
+ OUT SENSE_RESULT *Result\r
)\r
-/*++\r
- Name:\r
- IsMediaError\r
-\r
- Purpose: \r
- Test if the device meets a media error after media changed\r
-\r
- Parameters:\r
- EQUEST_SENSE_DATA IN *SenseData\r
- pointer pointing to ATAPI device sense data list.\r
- UINTN IN SenseCounts\r
- sense data number of the list \r
-\r
- Returns: \r
- TRUE\r
- Device meets a media error\r
-\r
- FALSE\r
- No media error\r
---*/\r
-// TODO: function comment is missing 'Routine Description:'\r
-// TODO: function comment is missing 'Arguments:'\r
-// TODO: SenseData - add argument and description to function comment\r
-// TODO: SenseCounts - add argument and description to function comment\r
{\r
- REQUEST_SENSE_DATA *SensePointer;\r
- UINTN Index;\r
- BOOLEAN IsError;\r
-\r
- IsError = FALSE;\r
- SensePointer = SenseData;\r
+ REQUEST_SENSE_DATA *SenseData;\r
\r
- for (Index = 0; Index < SenseCounts; Index++) {\r
-\r
- switch (SensePointer->sense_key) {\r
-\r
- case SK_MEDIUM_ERROR:\r
- //\r
- // Sense Key is SK_MEDIUM_ERROR (0x3)\r
- //\r
- switch (SensePointer->addnl_sense_code) {\r
- case ASC_MEDIA_ERR1:\r
- case ASC_MEDIA_ERR2:\r
- case ASC_MEDIA_ERR3:\r
- case ASC_MEDIA_ERR4:\r
- IsError = TRUE;\r
- break;\r
+ if (SenseCount == 0) {\r
+ return EFI_INVALID_PARAMETER;\r
+ }\r
\r
- default:\r
- break;\r
- }\r
+ //\r
+ // Only use the first sense data\r
+ //\r
+ SenseData = IdeDev->SenseData;\r
+ *Result = SenseOtherSense;\r
\r
+ switch (SenseData->sense_key) {\r
+ case SK_NO_SENSE:\r
+ *Result = SenseNoSenseKey;\r
+ break;\r
+ case SK_NOT_READY:\r
+ switch (SenseData->addnl_sense_code) {\r
+ case ASC_NO_MEDIA:\r
+ *Result = SenseNoMedia;\r
break;\r
-\r
- case SK_NOT_READY:\r
- //\r
- // Sense Key is SK_NOT_READY (0x2)\r
- //\r
- switch (SensePointer->addnl_sense_code) {\r
- //\r
- // Additional Sense Code is ASC_MEDIA_UPSIDE_DOWN (0x6)\r
- //\r
- case ASC_MEDIA_UPSIDE_DOWN:\r
- IsError = TRUE;\r
- break;\r
-\r
- default:\r
- break;\r
+ case ASC_MEDIA_UPSIDE_DOWN:\r
+ *Result = SenseMediaError;\r
+ break;\r
+ case ASC_NOT_READY:\r
+ if (SenseData->addnl_sense_code_qualifier == ASCQ_IN_PROGRESS) {\r
+ *Result = SenseDeviceNotReadyNeedRetry;\r
+ } else {\r
+ *Result = SenseDeviceNotReadyNoRetry;\r
}\r
break;\r
-\r
- default:\r
+ }\r
+ break;\r
+ case SK_UNIT_ATTENTION:\r
+ if (SenseData->addnl_sense_code == ASC_MEDIA_CHANGE) {\r
+ *Result = SenseMediaChange;\r
+ }\r
+ break;\r
+ case SK_MEDIUM_ERROR:\r
+ switch (SenseData->addnl_sense_code) {\r
+ case ASC_MEDIA_ERR1:\r
+ case ASC_MEDIA_ERR2:\r
+ case ASC_MEDIA_ERR3:\r
+ case ASC_MEDIA_ERR4:\r
+ *Result = SenseMediaError;\r
break;\r
}\r
-\r
- SensePointer++;\r
+ break;\r
+ default:\r
+ break;\r
}\r
\r
- return IsError;\r
+ return EFI_SUCCESS;\r
}\r
\r
-BOOLEAN\r
-IsMediaChange (\r
- IN REQUEST_SENSE_DATA *SenseData,\r
- IN UINTN SenseCounts\r
- )\r
-/*++\r
-\r
-Routine Description:\r
-\r
- TODO: Add function description\r
-\r
-Arguments:\r
-\r
- SenseData - TODO: add argument description\r
- SenseCounts - TODO: add argument description\r
-\r
-Returns:\r
+/**\r
+ This function reads the pending data in the device.\r
\r
- TODO: add return values\r
+ @param[in] IdeDev Indicates the calling context.\r
\r
---*/\r
-{\r
- REQUEST_SENSE_DATA *SensePointer;\r
- UINTN Index;\r
- BOOLEAN IsMediaChange;\r
-\r
- IsMediaChange = FALSE;\r
- SensePointer = SenseData;\r
-\r
- for (Index = 0; Index < SenseCounts; Index++) {\r
- //\r
- // Sense Key is SK_UNIT_ATTENTION (0x6)\r
- //\r
- if ((SensePointer->sense_key == SK_UNIT_ATTENTION) &&\r
- (SensePointer->addnl_sense_code == ASC_MEDIA_CHANGE)) {\r
-\r
- IsMediaChange = TRUE;\r
- }\r
-\r
- SensePointer++;\r
- }\r
-\r
- return IsMediaChange;\r
-}\r
+ @retval EFI_SUCCESS Successfully read.\r
+ @retval EFI_NOT_READY The BSY is set avoiding reading.\r
\r
-BOOLEAN\r
-IsDriveReady (\r
- IN REQUEST_SENSE_DATA *SenseData,\r
- IN UINTN SenseCounts,\r
- OUT BOOLEAN *NeedRetry\r
+**/\r
+EFI_STATUS\r
+AtapiReadPendingData (\r
+ IN IDE_BLK_IO_DEV *IdeDev\r
)\r
-/*++\r
-\r
-Routine Description:\r
-\r
- TODO: Add function description\r
-\r
-Arguments:\r
-\r
- SenseData - TODO: add argument description\r
- SenseCounts - TODO: add argument description\r
- NeedRetry - TODO: add argument description\r
-\r
-Returns:\r
-\r
- TODO: add return values\r
-\r
---*/\r
{\r
- REQUEST_SENSE_DATA *SensePointer;\r
- UINTN Index;\r
- BOOLEAN IsReady;\r
-\r
- IsReady = TRUE;\r
- *NeedRetry = FALSE;\r
- SensePointer = SenseData;\r
-\r
- for (Index = 0; Index < SenseCounts; Index++) {\r
-\r
- switch (SensePointer->sense_key) {\r
-\r
- case SK_NOT_READY:\r
- //\r
- // Sense Key is SK_NOT_READY (0x2)\r
- //\r
- switch (SensePointer->addnl_sense_code) {\r
- case ASC_NOT_READY:\r
- //\r
- // Additional Sense Code is ASC_NOT_READY (0x4)\r
- //\r
- switch (SensePointer->addnl_sense_code_qualifier) {\r
- case ASCQ_IN_PROGRESS:\r
- //\r
- // Additional Sense Code Qualifier is ASCQ_IN_PROGRESS (0x1)\r
- //\r
- IsReady = FALSE;\r
- *NeedRetry = TRUE;\r
- break;\r
-\r
- default:\r
- IsReady = FALSE;\r
- *NeedRetry = FALSE;\r
- break;\r
- }\r
- break;\r
-\r
- default:\r
- break;\r
- }\r
- break;\r
+ UINT8 AltRegister;\r
+ UINT16 TempWordBuffer;\r
\r
- default:\r
- break;\r
+ AltRegister = IDEReadPortB (IdeDev->PciIo, IdeDev->IoPort->Alt.AltStatus);\r
+ if ((AltRegister & BSY) == BSY) {\r
+ return EFI_NOT_READY;\r
+ }\r
+ if ((AltRegister & (BSY | DRQ)) == DRQ) {\r
+ TempWordBuffer = IDEReadPortB (IdeDev->PciIo,IdeDev->IoPort->Alt.AltStatus);\r
+ while ((TempWordBuffer & (BSY | DRQ)) == DRQ) {\r
+ IDEReadPortWMultiple (\r
+ IdeDev->PciIo,\r
+ IdeDev->IoPort->Data, \r
+ 1, \r
+ &TempWordBuffer\r
+ );\r
+ TempWordBuffer = IDEReadPortB (IdeDev->PciIo,IdeDev->IoPort->Alt.AltStatus);\r
}\r
-\r
- SensePointer++;\r
}\r
-\r
- return IsReady;\r
+ return EFI_SUCCESS;\r
}\r
\r
-BOOLEAN\r
-HaveSenseKey (\r
- IN REQUEST_SENSE_DATA *SenseData,\r
- IN UINTN SenseCounts\r
- )\r
-/*++\r
-\r
-Routine Description:\r
-\r
+/**\r
TODO: Add function description\r
\r
-Arguments:\r
-\r
- SenseData - TODO: add argument description\r
- SenseCounts - TODO: add argument description\r
-\r
-Returns:\r
-\r
- TODO: add return values\r
-\r
---*/\r
-{\r
- BOOLEAN Have;\r
-\r
- Have = TRUE;\r
-\r
- //\r
- // if first sense key in the Sense Data Array is SK_NO_SENSE,\r
- // it indicates there is no more sense key in the Sense Data Array.\r
- //\r
- if (SenseData->sense_key == SK_NO_SENSE) {\r
- Have = FALSE;\r
- }\r
+ @param IdeDev TODO: add argument description\r
+ @param WriteProtected TODO: add argument description\r
\r
- return Have;\r
-}\r
+ @retval EFI_DEVICE_ERROR TODO: Add description for return value\r
+ @retval EFI_DEVICE_ERROR TODO: Add description for return value\r
+ @retval EFI_SUCCESS TODO: Add description for return value\r
\r
+**/\r
EFI_STATUS\r
IsLS120orZipWriteProtected (\r
IN IDE_BLK_IO_DEV *IdeDev,\r
OUT BOOLEAN *WriteProtected\r
)\r
-/*++\r
-\r
-Routine Description:\r
-\r
- TODO: Add function description\r
-\r
-Arguments:\r
-\r
- IdeDev - TODO: add argument description\r
- WriteProtected - TODO: add argument description\r
-\r
-Returns:\r
-\r
- EFI_DEVICE_ERROR - TODO: Add description for return value\r
- EFI_DEVICE_ERROR - TODO: Add description for return value\r
- EFI_SUCCESS - TODO: Add description for return value\r
-\r
---*/\r
{\r
EFI_STATUS Status;\r
\r