mirror of https://github.com/acidanthera/audk.git
1. fix AtaPassThru.PassThru() sct failure
2. avoid reenumerate existing device to reduce boot time at AtaBus. git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@11232 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
parent
f877f3006e
commit
e519983a6c
|
@ -1,7 +1,7 @@
|
|||
/** @file
|
||||
The file for AHCI mode of ATA host controller.
|
||||
|
||||
Copyright (c) 2010, Intel Corporation. All rights reserved.<BR>
|
||||
Copyright (c) 2010 - 2011, 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
|
||||
|
@ -256,6 +256,42 @@ AhciClearPortStatus (
|
|||
AhciWriteReg (PciIo, EFI_AHCI_IS_OFFSET, AhciReadReg (PciIo, EFI_AHCI_IS_OFFSET));
|
||||
}
|
||||
|
||||
/**
|
||||
This function is used to dump the Status Registers and if there is ERR bit set
|
||||
in the Status Register, the Error Register's value is also be dumped.
|
||||
|
||||
@param PciIo The PCI IO protocol instance.
|
||||
@param Port The number of port.
|
||||
@param AtaStatusBlock A pointer to EFI_ATA_STATUS_BLOCK data structure.
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
AhciDumpPortStatus (
|
||||
IN EFI_PCI_IO_PROTOCOL *PciIo,
|
||||
IN UINT8 Port,
|
||||
IN OUT EFI_ATA_STATUS_BLOCK *AtaStatusBlock
|
||||
)
|
||||
{
|
||||
UINT32 Offset;
|
||||
UINT32 Data;
|
||||
|
||||
ASSERT (PciIo != NULL);
|
||||
|
||||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_TFD;
|
||||
Data = AhciReadReg (PciIo, Offset);
|
||||
|
||||
if (AtaStatusBlock != NULL) {
|
||||
ZeroMem (AtaStatusBlock, sizeof (EFI_ATA_STATUS_BLOCK));
|
||||
|
||||
AtaStatusBlock->AtaStatus = (UINT8)Data;
|
||||
if ((AtaStatusBlock->AtaStatus & BIT0) != 0) {
|
||||
AtaStatusBlock->AtaError = (UINT8)(Data >> 8);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
Enable the FIS running for giving port.
|
||||
|
||||
|
@ -621,7 +657,7 @@ AhciPioTransfer (
|
|||
//
|
||||
Delay = (UINT32) (DivU64x32(Timeout, 1000) + 1);
|
||||
do {
|
||||
Value = *(UINT32 *) (FisBaseAddr + EFI_AHCI_PIO_FIS_OFFSET);
|
||||
Value = *(volatile UINT32 *) (FisBaseAddr + EFI_AHCI_PIO_FIS_OFFSET);
|
||||
|
||||
if ((Value & EFI_AHCI_FIS_TYPE_MASK) == EFI_AHCI_FIS_PIO_SETUP) {
|
||||
break;
|
||||
|
@ -686,6 +722,8 @@ Exit:
|
|||
Map
|
||||
);
|
||||
|
||||
AhciDumpPortStatus (PciIo, Port, AtaStatusBlock);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
@ -855,6 +893,8 @@ Exit:
|
|||
Map
|
||||
);
|
||||
|
||||
AhciDumpPortStatus (PciIo, Port, AtaStatusBlock);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
@ -942,7 +982,7 @@ AhciNonDataTransfer (
|
|||
//
|
||||
Delay = (UINT32) (DivU64x32(Timeout, 1000) + 1);
|
||||
do {
|
||||
Value = *(UINT32 *) (FisBaseAddr + EFI_AHCI_D2H_FIS_OFFSET);
|
||||
Value = *(volatile UINT32 *) (FisBaseAddr + EFI_AHCI_D2H_FIS_OFFSET);
|
||||
|
||||
if ((Value & EFI_AHCI_FIS_TYPE_MASK) == EFI_AHCI_FIS_REGISTER_D2H) {
|
||||
break;
|
||||
|
@ -984,6 +1024,8 @@ Exit:
|
|||
Timeout
|
||||
);
|
||||
|
||||
AhciDumpPortStatus (PciIo, Port, AtaStatusBlock);
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
|
@ -1082,17 +1124,6 @@ AhciStartCommand (
|
|||
return Status;
|
||||
}
|
||||
|
||||
//
|
||||
// Setting the command
|
||||
//
|
||||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_SACT;
|
||||
AhciAndReg (PciIo, Offset, 0);
|
||||
AhciOrReg (PciIo, Offset, CmdSlotBit);
|
||||
|
||||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_CI;
|
||||
AhciAndReg (PciIo, Offset, 0);
|
||||
AhciOrReg (PciIo, Offset, CmdSlotBit);
|
||||
|
||||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_CMD;
|
||||
PortStatus = AhciReadReg (PciIo, Offset);
|
||||
|
||||
|
@ -1124,6 +1155,17 @@ AhciStartCommand (
|
|||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_CMD;
|
||||
AhciOrReg (PciIo, Offset, EFI_AHCI_PORT_CMD_ST | StartCmd);
|
||||
|
||||
//
|
||||
// Setting the command
|
||||
//
|
||||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_SACT;
|
||||
AhciAndReg (PciIo, Offset, 0);
|
||||
AhciOrReg (PciIo, Offset, CmdSlotBit);
|
||||
|
||||
Offset = EFI_AHCI_PORT_START + Port * EFI_AHCI_PORT_REG_WIDTH + EFI_AHCI_PORT_CI;
|
||||
AhciAndReg (PciIo, Offset, 0);
|
||||
AhciOrReg (PciIo, Offset, CmdSlotBit);
|
||||
|
||||
return EFI_SUCCESS;
|
||||
}
|
||||
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
This file implements protocol interfaces: Driver Binding protocol,
|
||||
Block IO protocol and DiskInfo protocol.
|
||||
|
||||
Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
|
||||
Copyright (c) 2009 - 2011, 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
|
||||
|
@ -173,15 +173,43 @@ RegisterAtaDevice (
|
|||
ATA_DEVICE *AtaDevice;
|
||||
EFI_ATA_PASS_THRU_PROTOCOL *AtaPassThru;
|
||||
EFI_DEVICE_PATH_PROTOCOL *NewDevicePathNode;
|
||||
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
|
||||
EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath;
|
||||
EFI_HANDLE DeviceHandle;
|
||||
|
||||
AtaDevice = NULL;
|
||||
NewDevicePathNode = NULL;
|
||||
DevicePath = NULL;
|
||||
RemainingDevicePath = NULL;
|
||||
|
||||
//
|
||||
// Build device path
|
||||
//
|
||||
AtaPassThru = AtaBusDriverData->AtaPassThru;
|
||||
Status = AtaPassThru->BuildDevicePath (AtaPassThru, Port, PortMultiplierPort, &NewDevicePathNode);
|
||||
if (EFI_ERROR (Status)) {
|
||||
goto Done;
|
||||
}
|
||||
|
||||
DevicePath = AppendDevicePathNode (AtaBusDriverData->ParentDevicePath, NewDevicePathNode);
|
||||
if (DevicePath == NULL) {
|
||||
goto Done;
|
||||
}
|
||||
|
||||
DeviceHandle = NULL;
|
||||
Status = gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &RemainingDevicePath, &DeviceHandle);
|
||||
if (!EFI_ERROR (Status) && (DeviceHandle != NULL) && IsDevicePathEnd(RemainingDevicePath)) {
|
||||
Status = EFI_ALREADY_STARTED;
|
||||
goto Done;
|
||||
}
|
||||
|
||||
//
|
||||
// Allocate ATA device from the template.
|
||||
//
|
||||
AtaDevice = AllocateCopyPool (sizeof (gAtaDeviceTemplate), &gAtaDeviceTemplate);
|
||||
if (AtaDevice == NULL) {
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
Status = EFI_OUT_OF_RESOURCES;
|
||||
goto Done;
|
||||
}
|
||||
|
||||
//
|
||||
|
@ -189,6 +217,7 @@ RegisterAtaDevice (
|
|||
//
|
||||
AtaDevice->BlockIo.Media = &AtaDevice->BlockMedia;
|
||||
AtaDevice->AtaBusDriverData = AtaBusDriverData;
|
||||
AtaDevice->DevicePath = DevicePath;
|
||||
AtaDevice->Port = Port;
|
||||
AtaDevice->PortMultiplierPort = PortMultiplierPort;
|
||||
AtaDevice->Asb = AllocateAlignedBuffer (AtaDevice, sizeof (*AtaDevice->Asb));
|
||||
|
@ -235,15 +264,6 @@ RegisterAtaDevice (
|
|||
goto Done;
|
||||
}
|
||||
|
||||
//
|
||||
// Build device path
|
||||
//
|
||||
AtaPassThru = AtaBusDriverData->AtaPassThru;
|
||||
Status = AtaPassThru->BuildDevicePath (AtaPassThru, Port, PortMultiplierPort, &NewDevicePathNode);
|
||||
if (EFI_ERROR (Status)) {
|
||||
goto Done;
|
||||
}
|
||||
|
||||
//
|
||||
// Update to AHCI interface GUID based on device path node. The default one
|
||||
// is IDE interface GUID copied from template.
|
||||
|
@ -252,11 +272,6 @@ RegisterAtaDevice (
|
|||
CopyGuid (&AtaDevice->DiskInfo.Interface, &gEfiDiskInfoAhciInterfaceGuid);
|
||||
}
|
||||
|
||||
AtaDevice->DevicePath = AppendDevicePathNode (AtaBusDriverData->ParentDevicePath, NewDevicePathNode);
|
||||
if (AtaDevice->DevicePath == NULL) {
|
||||
goto Done;
|
||||
}
|
||||
|
||||
Status = gBS->InstallMultipleProtocolInterfaces (
|
||||
&AtaDevice->Handle,
|
||||
&gEfiDevicePathProtocolGuid,
|
||||
|
@ -285,7 +300,7 @@ Done:
|
|||
FreePool (NewDevicePathNode);
|
||||
}
|
||||
|
||||
if (EFI_ERROR (Status)) {
|
||||
if (EFI_ERROR (Status) && (AtaDevice != NULL)) {
|
||||
ReleaseAtaResources (AtaDevice);
|
||||
DEBUG ((DEBUG_ERROR | DEBUG_INIT, "Failed to initialize Port %x PortMultiplierPort %x, status = %r\n", Port, PortMultiplierPort, Status));
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
This file defines common data structures, macro definitions and some module
|
||||
internal function header files.
|
||||
|
||||
Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
|
||||
Copyright (c) 2009 - 2011, 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
|
||||
|
@ -39,7 +39,7 @@
|
|||
//
|
||||
// Time out value for ATA pass through protocol
|
||||
//
|
||||
#define ATA_TIMEOUT EFI_TIMER_PERIOD_SECONDS (1)
|
||||
#define ATA_TIMEOUT EFI_TIMER_PERIOD_SECONDS (3)
|
||||
|
||||
//
|
||||
// Maximum number of times to retry ATA command
|
||||
|
|
Loading…
Reference in New Issue