mirror of https://github.com/acidanthera/audk.git
MdeModulePkg Ata: Use the new (incompatible) PortMultiplierPort semantics
The Mantis ticket 1353 <https://mantis.uefi.org/mantis/view.php?id=1353> and Mantis ticket 1472 <https://mantis.uefi.org/mantis/view.php?id=1472> updated the description of the port multiplier port number parameter in SATA Device Path Node and ATA Pass-Through Protocol. Now, this parameter should be set to 0xFFFF instead of 0 to indicate that an ATA device is directly attached on the controller port. Please note that this is an incompatible change. The consumer of SATA device path or ATA_PASS_THRU needs to re-examine its usage to follow UEFI 2.5 mantis 1353 and 1472. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Hao Wu <hao.a.wu@intel.com> Reviewed-by: Feng Tian <feng.tian@intel.com>
This commit is contained in:
parent
cc4036509e
commit
23a596db1b
|
@ -2513,7 +2513,7 @@ AhciModeInitialization (
|
|||
//
|
||||
// Found a ATA or ATAPI device, add it into the device list.
|
||||
//
|
||||
CreateNewDeviceInfo (Instance, Port, 0, DeviceType, &Buffer);
|
||||
CreateNewDeviceInfo (Instance, Port, 0xFFFF, DeviceType, &Buffer);
|
||||
if (DeviceType == EfiIdeHarddisk) {
|
||||
REPORT_STATUS_CODE (EFI_PROGRESS_CODE, (EFI_PERIPHERAL_FIXED_MEDIA | EFI_P_PC_ENABLE));
|
||||
}
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
This file implements ATA_PASSTHRU_PROCTOCOL and EXT_SCSI_PASSTHRU_PROTOCOL interfaces
|
||||
for managed ATA controllers.
|
||||
|
||||
Copyright (c) 2010 - 2015, Intel Corporation. All rights reserved.<BR>
|
||||
Copyright (c) 2010 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
This program and the accompanying materials
|
||||
are licensed and made available under the terms and conditions of the BSD License
|
||||
which accompanies this distribution. The full text of the license may be found at
|
||||
|
@ -148,7 +148,7 @@ UINT8 mScsiId[TARGET_MAX_BYTES] = {
|
|||
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in, out] Packet A pointer to the ATA command to send to the ATA device specified by Port
|
||||
and PortMultiplierPort.
|
||||
@param[in] Instance Pointer to the ATA_ATAPI_PASS_THRU_INSTANCE.
|
||||
|
@ -272,6 +272,14 @@ AtaPassThruPassThruExecute (
|
|||
}
|
||||
break;
|
||||
case EfiAtaAhciMode :
|
||||
if (PortMultiplierPort == 0xFFFF) {
|
||||
//
|
||||
// If there is no port multiplier, PortMultiplierPort will be 0xFFFF
|
||||
// according to UEFI spec. Here, we convert its value to 0 to follow
|
||||
// AHCI spec.
|
||||
//
|
||||
PortMultiplierPort = 0;
|
||||
}
|
||||
switch (Protocol) {
|
||||
case EFI_ATA_PASS_THRU_PROTOCOL_ATA_NON_DATA:
|
||||
Status = AhciNonDataTransfer (
|
||||
|
@ -982,7 +990,7 @@ AtaAtapiPassThruStop (
|
|||
@param[in] Instance A pointer to the ATA_ATAPI_PASS_THRU_INSTANCE instance.
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in] DeviceType The device type of the ATA device.
|
||||
|
||||
@retval The pointer to the data structure of the device info to access.
|
||||
|
@ -1004,6 +1012,18 @@ SearchDeviceInfoList (
|
|||
while (!IsNull (&Instance->DeviceList, Node)) {
|
||||
DeviceInfo = ATA_ATAPI_DEVICE_INFO_FROM_THIS (Node);
|
||||
|
||||
//
|
||||
// For CD-ROM working in the AHCI mode, only 8 bits are used to record
|
||||
// the PortMultiplier information. If the CD-ROM is directly attached
|
||||
// on a SATA port, the PortMultiplier should be translated from 0xFF
|
||||
// to 0xFFFF according to the UEFI spec.
|
||||
//
|
||||
if ((Instance->Mode == EfiAtaAhciMode) &&
|
||||
(DeviceInfo->Type == EfiIdeCdrom) &&
|
||||
(PortMultiplier == 0xFF)) {
|
||||
PortMultiplier = 0xFFFF;
|
||||
}
|
||||
|
||||
if ((DeviceInfo->Type == DeviceType) &&
|
||||
(Port == DeviceInfo->Port) &&
|
||||
(PortMultiplier == DeviceInfo->PortMultiplier)) {
|
||||
|
@ -1023,7 +1043,7 @@ SearchDeviceInfoList (
|
|||
@param[in] Instance A pointer to the ATA_ATAPI_PASS_THRU_INSTANCE instance.
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in] DeviceType The device type of the ATA device.
|
||||
@param[in] IdentifyData The data buffer to store the output of the IDENTIFY cmd.
|
||||
|
||||
|
@ -1216,7 +1236,7 @@ Done:
|
|||
@param[in] This A pointer to the EFI_ATA_PASS_THRU_PROTOCOL instance.
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in, out] Packet A pointer to the ATA command to send to the ATA device specified by Port
|
||||
and PortMultiplierPort.
|
||||
@param[in] Event If non-blocking I/O is not supported then Event is ignored, and blocking
|
||||
|
@ -1531,7 +1551,34 @@ AtaPassThruGetNextDevice (
|
|||
return EFI_INVALID_PARAMETER;
|
||||
}
|
||||
|
||||
if (*PortMultiplierPort == 0xFFFF) {
|
||||
if (Instance->PreviousPortMultiplier == 0xFFFF) {
|
||||
//
|
||||
// If a device is directly attached on a port, previous call to this
|
||||
// function will return the value 0xFFFF for PortMultiplierPort. In
|
||||
// this case, there should be no more device on the port multiplier.
|
||||
//
|
||||
Instance->PreviousPortMultiplier = 0;
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
|
||||
if (*PortMultiplierPort == Instance->PreviousPortMultiplier) {
|
||||
Node = GetFirstNode (&Instance->DeviceList);
|
||||
|
||||
while (!IsNull (&Instance->DeviceList, Node)) {
|
||||
DeviceInfo = ATA_ATAPI_DEVICE_INFO_FROM_THIS (Node);
|
||||
|
||||
if ((DeviceInfo->Type == EfiIdeHarddisk) &&
|
||||
(DeviceInfo->Port == Port) &&
|
||||
(DeviceInfo->PortMultiplier > *PortMultiplierPort)){
|
||||
*PortMultiplierPort = DeviceInfo->PortMultiplier;
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
Node = GetNextNode (&Instance->DeviceList, Node);
|
||||
}
|
||||
|
||||
return EFI_NOT_FOUND;
|
||||
} else if (*PortMultiplierPort == 0xFFFF) {
|
||||
//
|
||||
// If the PortMultiplierPort is all 0xFF's, start to traverse the device list from the beginning
|
||||
//
|
||||
|
@ -1549,23 +1596,6 @@ AtaPassThruGetNextDevice (
|
|||
Node = GetNextNode (&Instance->DeviceList, Node);
|
||||
}
|
||||
|
||||
return EFI_NOT_FOUND;
|
||||
} else if (*PortMultiplierPort == Instance->PreviousPortMultiplier) {
|
||||
Node = GetFirstNode (&Instance->DeviceList);
|
||||
|
||||
while (!IsNull (&Instance->DeviceList, Node)) {
|
||||
DeviceInfo = ATA_ATAPI_DEVICE_INFO_FROM_THIS (Node);
|
||||
|
||||
if ((DeviceInfo->Type == EfiIdeHarddisk) &&
|
||||
(DeviceInfo->Port == Port) &&
|
||||
(DeviceInfo->PortMultiplier > *PortMultiplierPort)){
|
||||
*PortMultiplierPort = DeviceInfo->PortMultiplier;
|
||||
goto Exit;
|
||||
}
|
||||
|
||||
Node = GetNextNode (&Instance->DeviceList, Node);
|
||||
}
|
||||
|
||||
return EFI_NOT_FOUND;
|
||||
} else {
|
||||
//
|
||||
|
@ -1601,7 +1631,7 @@ Exit:
|
|||
device path node is to be allocated and built.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device for which a
|
||||
device path node is to be allocated and built. If there is no
|
||||
port multiplier, then specify 0.
|
||||
port multiplier, then specify 0xFFFF.
|
||||
@param[in, out] DevicePath A pointer to a single device path node that describes the ATA
|
||||
device specified by Port and PortMultiplierPort. This function
|
||||
is responsible for allocating the buffer DevicePath with the
|
||||
|
@ -1812,7 +1842,7 @@ AtaPassThruResetPort (
|
|||
@param[in] This A pointer to the EFI_ATA_PASS_THRU_PROTOCOL instance.
|
||||
@param[in] Port Port represents the port number of the ATA device to be reset.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to reset.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@retval EFI_SUCCESS The ATA device specified by Port and PortMultiplierPort was reset.
|
||||
@retval EFI_UNSUPPORTED The ATA controller does not support a device reset operation.
|
||||
@retval EFI_INVALID_PARAMETER Port or PortMultiplierPort are invalid.
|
||||
|
@ -2049,6 +2079,13 @@ ExtScsiPassThruPassThru (
|
|||
Status = AtaPacketCommandExecute (Instance->PciIo, &Instance->IdeRegisters[Port], Port, PortMultiplier, Packet);
|
||||
break;
|
||||
case EfiAtaAhciMode:
|
||||
if (PortMultiplier == 0xFF) {
|
||||
//
|
||||
// If there is no port multiplier, the PortMultiplier will be 0xFF
|
||||
// Here, we convert its value to 0 to follow the AHCI spec.
|
||||
//
|
||||
PortMultiplier = 0;
|
||||
}
|
||||
Status = AhciPacketCommandExecute (Instance->PciIo, &Instance->AhciRegisters, Port, PortMultiplier, Packet);
|
||||
break;
|
||||
default :
|
||||
|
@ -2186,7 +2223,7 @@ ExtScsiPassThruGetNextTargetLun (
|
|||
if ((DeviceInfo->Type == EfiIdeCdrom) &&
|
||||
((Target8[0] < DeviceInfo->Port) ||
|
||||
((Target8[0] == DeviceInfo->Port) &&
|
||||
(Target8[1] < DeviceInfo->PortMultiplier)))) {
|
||||
(Target8[1] < (UINT8)DeviceInfo->PortMultiplier)))) {
|
||||
Target8[0] = (UINT8)DeviceInfo->Port;
|
||||
Target8[1] = (UINT8)DeviceInfo->PortMultiplier;
|
||||
goto Exit;
|
||||
|
@ -2308,7 +2345,13 @@ ExtScsiPassThruBuildDevicePath (
|
|||
}
|
||||
|
||||
DevicePathNode->Sata.HBAPortNumber = Port;
|
||||
DevicePathNode->Sata.PortMultiplierPortNumber = PortMultiplier;
|
||||
//
|
||||
// For CD-ROM working in the AHCI mode, only 8 bits are used to record
|
||||
// the PortMultiplier information. If the CD-ROM is directly attached
|
||||
// on a SATA port, the PortMultiplier should be translated from 0xFF
|
||||
// to 0xFFFF according to the UEFI spec.
|
||||
//
|
||||
DevicePathNode->Sata.PortMultiplierPortNumber = PortMultiplier == 0xFF ? 0xFFFF : PortMultiplier;
|
||||
DevicePathNode->Sata.Lun = (UINT16) Lun;
|
||||
}
|
||||
|
||||
|
@ -2562,7 +2605,7 @@ ExtScsiPassThruGetNextTarget (
|
|||
if ((DeviceInfo->Type == EfiIdeCdrom) &&
|
||||
((Target8[0] < DeviceInfo->Port) ||
|
||||
((Target8[0] == DeviceInfo->Port) &&
|
||||
(Target8[1] < DeviceInfo->PortMultiplier)))) {
|
||||
(Target8[1] < (UINT8)DeviceInfo->PortMultiplier)))) {
|
||||
Target8[0] = (UINT8)DeviceInfo->Port;
|
||||
Target8[1] = (UINT8)DeviceInfo->PortMultiplier;
|
||||
goto Exit;
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
/** @file
|
||||
Header file for ATA/ATAPI PASS THRU driver.
|
||||
|
||||
Copyright (c) 2010 - 2012, Intel Corporation. All rights reserved.<BR>
|
||||
Copyright (c) 2010 - 2016, Intel Corporation. All rights reserved.<BR>
|
||||
This program and the accompanying materials
|
||||
are licensed and made available under the terms and conditions of the BSD License
|
||||
which accompanies this distribution. The full text of the license may be found at
|
||||
|
@ -437,7 +437,7 @@ AtaAtapiPassThruStop (
|
|||
@param[in] Instance A pointer to the ATA_ATAPI_PASS_THRU_INSTANCE instance.
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in] DeviceType The device type of the ATA device.
|
||||
|
||||
@retval The pointer to the data structure of the device info to access.
|
||||
|
@ -459,7 +459,7 @@ SearchDeviceInfoList (
|
|||
@param[in] Instance A pointer to the ATA_ATAPI_PASS_THRU_INSTANCE instance.
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in] DeviceType The device type of the ATA device.
|
||||
@param[in] IdentifyData The data buffer to store the output of the IDENTIFY cmd.
|
||||
|
||||
|
@ -544,7 +544,7 @@ AsyncNonBlockingTransferRoutine (
|
|||
@param[in] This A pointer to the EFI_ATA_PASS_THRU_PROTOCOL instance.
|
||||
@param[in] Port The port number of the ATA device to send the command.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to send the command.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@param[in, out] Packet A pointer to the ATA command to send to the ATA device specified by Port
|
||||
and PortMultiplierPort.
|
||||
@param[in] Event If non-blocking I/O is not supported then Event is ignored, and blocking
|
||||
|
@ -681,7 +681,7 @@ AtaPassThruGetNextDevice (
|
|||
device path node is to be allocated and built.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device for which a
|
||||
device path node is to be allocated and built. If there is no
|
||||
port multiplier, then specify 0.
|
||||
port multiplier, then specify 0xFFFF.
|
||||
@param[in, out] DevicePath A pointer to a single device path node that describes the ATA
|
||||
device specified by Port and PortMultiplierPort. This function
|
||||
is responsible for allocating the buffer DevicePath with the
|
||||
|
@ -802,7 +802,7 @@ AtaPassThruResetPort (
|
|||
@param[in] This A pointer to the EFI_ATA_PASS_THRU_PROTOCOL instance.
|
||||
@param[in] Port Port represents the port number of the ATA device to be reset.
|
||||
@param[in] PortMultiplierPort The port multiplier port number of the ATA device to reset.
|
||||
If there is no port multiplier, then specify 0.
|
||||
If there is no port multiplier, then specify 0xFFFF.
|
||||
@retval EFI_SUCCESS The ATA device specified by Port and PortMultiplierPort was reset.
|
||||
@retval EFI_UNSUPPORTED The ATA controller does not support a device reset operation.
|
||||
@retval EFI_INVALID_PARAMETER Port or PortMultiplierPort are invalid.
|
||||
|
|
Loading…
Reference in New Issue