From 27f3015903bf30b9ca0e72c0174e9ef787d79659 Mon Sep 17 00:00:00 2001 From: lzeng14 Date: Tue, 8 Mar 2011 05:42:37 +0000 Subject: [PATCH] Add AHCI support for DUET. git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@11353 6f19259b-4bc3-4df7-8a09-765794883524 --- DuetPkg/DuetPkg.fdf | 11 +- DuetPkg/DuetPkgIa32.dsc | 11 +- DuetPkg/DuetPkgX64.dsc | 11 +- DuetPkg/SataControllerDxe/ComponentName.c | 176 ++++ DuetPkg/SataControllerDxe/SataController.c | 867 ++++++++++++++++++ DuetPkg/SataControllerDxe/SataController.h | 402 ++++++++ .../SataControllerDxe/SataControllerDxe.inf | 49 + 7 files changed, 1515 insertions(+), 12 deletions(-) create mode 100644 DuetPkg/SataControllerDxe/ComponentName.c create mode 100644 DuetPkg/SataControllerDxe/SataController.c create mode 100644 DuetPkg/SataControllerDxe/SataController.h create mode 100644 DuetPkg/SataControllerDxe/SataControllerDxe.inf diff --git a/DuetPkg/DuetPkg.fdf b/DuetPkg/DuetPkg.fdf index ca7d2be203..ef4b5fee0b 100644 --- a/DuetPkg/DuetPkg.fdf +++ b/DuetPkg/DuetPkg.fdf @@ -1,7 +1,7 @@ ## @file # This is DUET FDF file with UEFI HII features enabled # -# Copyright (c) 2007 - 2010, Intel Corporation. All rights reserved.
+# Copyright (c) 2007 - 2011, Intel Corporation. All rights reserved.
# # This program and the accompanying materials # are licensed and made available under the terms and conditions of the BSD License @@ -82,9 +82,12 @@ INF DuetPkg/PciBusNoEnumerationDxe/PciBusNoEnumeration.inf INF IntelFrameworkModulePkg/Bus/Pci/VgaMiniPortDxe/VgaMiniPortDxe.inf INF IntelFrameworkModulePkg/Universal/Console/VgaClassDxe/VgaClassDxe.inf - # IDE Support -INF IntelFrameworkModulePkg/Bus/Pci/IdeBusDxe/IdeBusDxe.inf -INF PcAtChipsetPkg/Bus/Pci/IdeControllerDxe/IdeControllerDxe.inf + # IDE/AHCI Support +INF DuetPkg/SataControllerDxe/SataControllerDxe.inf +INF MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf +INF MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf +INF MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf +INF MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf # Usb Support INF MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf diff --git a/DuetPkg/DuetPkgIa32.dsc b/DuetPkg/DuetPkgIa32.dsc index 83d5688b66..825e0feeb8 100644 --- a/DuetPkg/DuetPkgIa32.dsc +++ b/DuetPkg/DuetPkgIa32.dsc @@ -4,7 +4,7 @@ # Developer's UEFI Emulation. DUET provides an EFI/UEFI IA32/X64 environment on legacy BIOS, # to help developing and debugging native EFI/UEFI drivers. # -# Copyright (c) 2010 - 2010, Intel Corporation. All rights reserved.
+# Copyright (c) 2010 - 2011, Intel Corporation. All rights reserved.
# # This program and the accompanying materials # are licensed and made available under the terms and conditions of the BSD License @@ -218,9 +218,12 @@ IntelFrameworkModulePkg/Bus/Pci/VgaMiniPortDxe/VgaMiniPortDxe.inf IntelFrameworkModulePkg/Universal/Console/VgaClassDxe/VgaClassDxe.inf - # IDE Support - IntelFrameworkModulePkg/Bus/Pci/IdeBusDxe/IdeBusDxe.inf - PcAtChipsetPkg/Bus/Pci/IdeControllerDxe/IdeControllerDxe.inf + # IDE/AHCI Support + DuetPkg/SataControllerDxe/SataControllerDxe.inf + MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf + MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf + MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf + MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf # Usb Support MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf diff --git a/DuetPkg/DuetPkgX64.dsc b/DuetPkg/DuetPkgX64.dsc index 142af252ec..5ccf2a3675 100644 --- a/DuetPkg/DuetPkgX64.dsc +++ b/DuetPkg/DuetPkgX64.dsc @@ -4,7 +4,7 @@ # Developer's UEFI Emulation. DUET provides an EFI/UEFI IA32/X64 environment on legacy BIOS, # to help developing and debugging native EFI/UEFI drivers. # -# Copyright (c) 2010 - 2010, Intel Corporation. All rights reserved.
+# Copyright (c) 2010 - 2011, Intel Corporation. All rights reserved.
# # This program and the accompanying materials # are licensed and made available under the terms and conditions of the BSD License @@ -218,9 +218,12 @@ IntelFrameworkModulePkg/Bus/Pci/VgaMiniPortDxe/VgaMiniPortDxe.inf IntelFrameworkModulePkg/Universal/Console/VgaClassDxe/VgaClassDxe.inf - # IDE Support - IntelFrameworkModulePkg/Bus/Pci/IdeBusDxe/IdeBusDxe.inf - PcAtChipsetPkg/Bus/Pci/IdeControllerDxe/IdeControllerDxe.inf + # IDE/AHCI Support + DuetPkg/SataControllerDxe/SataControllerDxe.inf + MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf + MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf + MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf + MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf # Usb Support MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf diff --git a/DuetPkg/SataControllerDxe/ComponentName.c b/DuetPkg/SataControllerDxe/ComponentName.c new file mode 100644 index 0000000000..57cd3c88d3 --- /dev/null +++ b/DuetPkg/SataControllerDxe/ComponentName.c @@ -0,0 +1,176 @@ +/** @file + UEFI Component Name(2) protocol implementation for Sata Controller driver. + + Copyright (c) 2011, Intel Corporation. All rights reserved.
+ 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 + http://opensource.org/licenses/bsd-license.php. + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +**/ + +#include "SataController.h" + +// +/// EFI Component Name Protocol +/// +GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME_PROTOCOL gSataControllerComponentName = { + SataControllerComponentNameGetDriverName, + SataControllerComponentNameGetControllerName, + "eng" +}; + +// +/// EFI Component Name 2 Protocol +/// +GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME2_PROTOCOL gSataControllerComponentName2 = { + (EFI_COMPONENT_NAME2_GET_DRIVER_NAME) SataControllerComponentNameGetDriverName, + (EFI_COMPONENT_NAME2_GET_CONTROLLER_NAME) SataControllerComponentNameGetControllerName, + "en" +}; + +// +/// Driver Name Strings +/// +GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE mSataControllerDriverNameTable[] = { + { + "eng;en", + (CHAR16 *)L"Sata Controller Init Driver" + }, + { + NULL, + NULL + } +}; + +/// +/// Controller Name Strings +/// +GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE mSataControllerControllerNameTable[] = { + { + "eng;en", + (CHAR16 *)L"Sata Controller" + }, + { + NULL, + NULL + } +}; + +/** + Retrieves a Unicode string that is the user readable name of the UEFI Driver. + + @param This A pointer to the EFI_COMPONENT_NAME_PROTOCOL instance. + @param Language A pointer to a three character ISO 639-2 language identifier. + This is the language of the driver name that that the caller + is requesting, and it must match one of the languages specified + in SupportedLanguages. The number of languages supported by a + driver is up to the driver writer. + @param DriverName A pointer to the Unicode string to return. This Unicode string + is the name of the driver specified by This in the language + specified by Language. + + @retval EFI_SUCCESS The Unicode string for the Driver specified by This + and the language specified by Language was returned + in DriverName. + @retval EFI_INVALID_PARAMETER Language is NULL. + @retval EFI_INVALID_PARAMETER DriverName is NULL. + @retval EFI_UNSUPPORTED The driver specified by This does not support the + language specified by Language. +**/ +EFI_STATUS +EFIAPI +SataControllerComponentNameGetDriverName ( + IN EFI_COMPONENT_NAME_PROTOCOL *This, + IN CHAR8 *Language, + OUT CHAR16 **DriverName + ) +{ + return LookupUnicodeString2 ( + Language, + This->SupportedLanguages, + mSataControllerDriverNameTable, + DriverName, + (BOOLEAN)(This == &gSataControllerComponentName) + ); +} + +/** + Retrieves a Unicode string that is the user readable name of the controller + that is being managed by an UEFI Driver. + + @param This A pointer to the EFI_COMPONENT_NAME_PROTOCOL instance. + @param ControllerHandle The handle of a controller that the driver specified by + This is managing. This handle specifies the controller + whose name is to be returned. + @param ChildHandle OPTIONAL The handle of the child controller to retrieve the name + of. This is an optional parameter that may be NULL. It + will be NULL for device drivers. It will also be NULL + for a bus drivers that wish to retrieve the name of the + bus controller. It will not be NULL for a bus driver + that wishes to retrieve the name of a child controller. + @param Language A pointer to a three character ISO 639-2 language + identifier. This is the language of the controller name + that that the caller is requesting, and it must match one + of the languages specified in SupportedLanguages. The + number of languages supported by a driver is up to the + driver writer. + @param ControllerName A pointer to the Unicode string to return. This Unicode + string is the name of the controller specified by + ControllerHandle and ChildHandle in the language + specified by Language from the point of view of the + driver specified by This. + + @retval EFI_SUCCESS The Unicode string for the user readable name in the + language specified by Language for the driver + specified by This was returned in DriverName. + @retval EFI_INVALID_PARAMETER ControllerHandle is not a valid EFI_HANDLE. + @retval EFI_INVALID_PARAMETER ChildHandle is not NULL and it is not a valid + EFI_HANDLE. + @retval EFI_INVALID_PARAMETER Language is NULL. + @retval EFI_INVALID_PARAMETER ControllerName is NULL. + @retval EFI_UNSUPPORTED The driver specified by This is not currently + managing the controller specified by + ControllerHandle and ChildHandle. + @retval EFI_UNSUPPORTED The driver specified by This does not support the + language specified by Language. +**/ +EFI_STATUS +EFIAPI +SataControllerComponentNameGetControllerName ( + IN EFI_COMPONENT_NAME_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN EFI_HANDLE ChildHandle OPTIONAL, + IN CHAR8 *Language, + OUT CHAR16 **ControllerName + ) +{ + EFI_STATUS Status; + + // + // Make sure this driver is currently managing ControllHandle + // + Status = EfiTestManagedDevice ( + ControllerHandle, + gSataControllerDriverBinding.DriverBindingHandle, + &gEfiPciIoProtocolGuid + ); + if (EFI_ERROR (Status)) { + return Status; + } + + if (ChildHandle != NULL) { + return EFI_UNSUPPORTED; + } + + return LookupUnicodeString2 ( + Language, + This->SupportedLanguages, + mSataControllerControllerNameTable, + ControllerName, + (BOOLEAN)(This == &gSataControllerComponentName) + ); +} diff --git a/DuetPkg/SataControllerDxe/SataController.c b/DuetPkg/SataControllerDxe/SataController.c new file mode 100644 index 0000000000..f00abcebb9 --- /dev/null +++ b/DuetPkg/SataControllerDxe/SataController.c @@ -0,0 +1,867 @@ +/** @file + This driver module produces IDE_CONTROLLER_INIT protocol for Sata Controllers. + + Copyright (c) 2011, Intel Corporation. All rights reserved.
+ 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 + http://opensource.org/licenses/bsd-license.php + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +**/ + +#include "SataController.h" + +/// +/// EFI_DRIVER_BINDING_PROTOCOL instance +/// +EFI_DRIVER_BINDING_PROTOCOL gSataControllerDriverBinding = { + SataControllerSupported, + SataControllerStart, + SataControllerStop, + 0xa, + NULL, + NULL +}; + +/** + Read AHCI Operation register. + + @param PciIo The PCI IO protocol instance. + @param Offset The operation register offset. + + @return The register content read. + +**/ +UINT32 +EFIAPI +AhciReadReg ( + IN EFI_PCI_IO_PROTOCOL *PciIo, + IN UINT32 Offset + ) +{ + UINT32 Data; + + ASSERT (PciIo != NULL); + + Data = 0; + + PciIo->Mem.Read ( + PciIo, + EfiPciIoWidthUint32, + AHCI_BAR_INDEX, + (UINT64) Offset, + 1, + &Data + ); + + return Data; +} + +/** + Write AHCI Operation register. + + @param PciIo The PCI IO protocol instance. + @param Offset The operation register offset. + @param Data The data used to write down. + +**/ +VOID +EFIAPI +AhciWriteReg ( + IN EFI_PCI_IO_PROTOCOL *PciIo, + IN UINT32 Offset, + IN UINT32 Data + ) +{ + ASSERT (PciIo != NULL); + + PciIo->Mem.Write ( + PciIo, + EfiPciIoWidthUint32, + AHCI_BAR_INDEX, + (UINT64) Offset, + 1, + &Data + ); + + return; +} + +/** + This function is used to calculate the best PIO mode supported by specific IDE device + + @param IdentifyData The identify data of specific IDE device. + @param DisPioMode Disqualified PIO modes collection. + @param SelectedMode Available PIO modes collection. + + @retval EFI_SUCCESS Best PIO modes are returned. + @retval EFI_UNSUPPORTED The device doesn't support PIO mode, + or all supported modes have been disqualified. +**/ +EFI_STATUS +CalculateBestPioMode ( + IN EFI_IDENTIFY_DATA *IdentifyData, + IN UINT16 *DisPioMode OPTIONAL, + OUT UINT16 *SelectedMode + ) +{ + UINT16 PioMode; + UINT16 AdvancedPioMode; + UINT16 Temp; + UINT16 Index; + UINT16 MinimumPioCycleTime; + + Temp = 0xff; + + PioMode = (UINT8) (((ATA5_IDENTIFY_DATA *) (&(IdentifyData->AtaData)))->pio_cycle_timing >> 8); + + // + // See whether Identify Data word 64 - 70 are valid + // + if ((IdentifyData->AtaData.field_validity & 0x02) == 0x02) { + + AdvancedPioMode = IdentifyData->AtaData.advanced_pio_modes; + DEBUG ((EFI_D_INFO, "CalculateBestPioMode: AdvancedPioMode = %x\n", AdvancedPioMode)); + + for (Index = 0; Index < 8; Index++) { + if ((AdvancedPioMode & 0x01) != 0) { + Temp = Index; + } + + AdvancedPioMode >>= 1; + } + + // + // If Temp is modified, mean the advanced_pio_modes is not zero; + // if Temp is not modified, mean there is no advanced PIO mode supported, + // the best PIO Mode is the value in pio_cycle_timing. + // + if (Temp != 0xff) { + AdvancedPioMode = (UINT16) (Temp + 3); + } else { + AdvancedPioMode = PioMode; + } + + // + // Limit the PIO mode to at most PIO4. + // + PioMode = (UINT16) MIN (AdvancedPioMode, 4); + + MinimumPioCycleTime = IdentifyData->AtaData.min_pio_cycle_time_with_flow_control; + + if (MinimumPioCycleTime <= 120) { + PioMode = (UINT16) MIN (4, PioMode); + } else if (MinimumPioCycleTime <= 180) { + PioMode = (UINT16) MIN (3, PioMode); + } else if (MinimumPioCycleTime <= 240) { + PioMode = (UINT16) MIN (2, PioMode); + } else { + PioMode = 0; + } + + // + // Degrade the PIO mode if the mode has been disqualified + // + if (DisPioMode != NULL) { + if (*DisPioMode < 2) { + return EFI_UNSUPPORTED; // no mode below ATA_PIO_MODE_BELOW_2 + } + + if (PioMode >= *DisPioMode) { + PioMode = (UINT16) (*DisPioMode - 1); + } + } + + if (PioMode < 2) { + *SelectedMode = 1; // ATA_PIO_MODE_BELOW_2; + } else { + *SelectedMode = PioMode; // ATA_PIO_MODE_2 to ATA_PIO_MODE_4; + } + + } else { + // + // Identify Data word 64 - 70 are not valid + // Degrade the PIO mode if the mode has been disqualified + // + if (DisPioMode != NULL) { + if (*DisPioMode < 2) { + return EFI_UNSUPPORTED; // no mode below ATA_PIO_MODE_BELOW_2 + } + + if (PioMode == *DisPioMode) { + PioMode--; + } + } + + if (PioMode < 2) { + *SelectedMode = 1; // ATA_PIO_MODE_BELOW_2; + } else { + *SelectedMode = 2; // ATA_PIO_MODE_2; + } + + } + + return EFI_SUCCESS; +} + +/** + This function is used to calculate the best UDMA mode supported by specific IDE device + + @param IdentifyData The identify data of specific IDE device. + @param DisUDmaMode Disqualified UDMA modes collection. + @param SelectedMode Available UDMA modes collection. + + @retval EFI_SUCCESS Best UDMA modes are returned. + @retval EFI_UNSUPPORTED The device doesn't support UDMA mode, + or all supported modes have been disqualified. +**/ +EFI_STATUS +CalculateBestUdmaMode ( + IN EFI_IDENTIFY_DATA *IdentifyData, + IN UINT16 *DisUDmaMode OPTIONAL, + OUT UINT16 *SelectedMode + ) +{ + UINT16 TempMode; + UINT16 DeviceUDmaMode; + + DeviceUDmaMode = 0; + + // + // Check whether the WORD 88 (supported UltraDMA by drive) is valid + // + if ((IdentifyData->AtaData.field_validity & 0x04) == 0x00) { + return EFI_UNSUPPORTED; + } + + DeviceUDmaMode = IdentifyData->AtaData.ultra_dma_mode; + DEBUG ((EFI_D_INFO, "CalculateBestUdmaMode: DeviceUDmaMode = %x\n", DeviceUDmaMode)); + DeviceUDmaMode &= 0x3f; + TempMode = 0; // initialize it to UDMA-0 + + while ((DeviceUDmaMode >>= 1) != 0) { + TempMode++; + } + + // + // Degrade the UDMA mode if the mode has been disqualified + // + if (DisUDmaMode != NULL) { + if (*DisUDmaMode == 0) { + *SelectedMode = 0; + return EFI_UNSUPPORTED; // no mode below ATA_UDMA_MODE_0 + } + + if (TempMode >= *DisUDmaMode) { + TempMode = (UINT16) (*DisUDmaMode - 1); + } + } + + // + // Possible returned mode is between ATA_UDMA_MODE_0 and ATA_UDMA_MODE_5 + // + *SelectedMode = TempMode; + + return EFI_SUCCESS; +} + +/** + The Entry Point of module. It follows the standard UEFI driver model. + + @param[in] ImageHandle The firmware allocated handle for the EFI image. + @param[in] SystemTable A pointer to the EFI System Table. + + @retval EFI_SUCCESS The entry point is executed successfully. + @retval other Some error occurs when executing this entry point. + +**/ +EFI_STATUS +EFIAPI +InitializeSataControllerDriver ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + + // + // Install driver model protocol(s). + // + Status = EfiLibInstallDriverBindingComponentName2 ( + ImageHandle, + SystemTable, + &gSataControllerDriverBinding, + ImageHandle, + &gSataControllerComponentName, + &gSataControllerComponentName2 + ); + ASSERT_EFI_ERROR (Status); + + return Status; +} + +/** + Supported function of Driver Binding protocol for this driver. + Test to see if this driver supports ControllerHandle. + + @param This Protocol instance pointer. + @param Controller Handle of device to test. + @param RemainingDevicePath A pointer to the device path. + it should be ignored by device driver. + + @retval EFI_SUCCESS This driver supports this device. + @retval EFI_ALREADY_STARTED This driver is already running on this device. + @retval other This driver does not support this device. + +**/ +EFI_STATUS +EFIAPI +SataControllerSupported ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE Controller, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath + ) +{ + EFI_STATUS Status; + EFI_PCI_IO_PROTOCOL *PciIo; + PCI_TYPE00 PciData; + + // + // Attempt to open PCI I/O Protocol + // + Status = gBS->OpenProtocol ( + Controller, + &gEfiPciIoProtocolGuid, + (VOID **) &PciIo, + This->DriverBindingHandle, + Controller, + EFI_OPEN_PROTOCOL_GET_PROTOCOL + ); + if (EFI_ERROR (Status)) { + return Status; + } + + // + // Now further check the PCI header: Base Class (offset 0x0B) and + // Sub Class (offset 0x0A). This controller should be an SATA controller + // + Status = PciIo->Pci.Read ( + PciIo, + EfiPciIoWidthUint8, + PCI_CLASSCODE_OFFSET, + sizeof (PciData.Hdr.ClassCode), + PciData.Hdr.ClassCode + ); + if (EFI_ERROR (Status)) { + return EFI_UNSUPPORTED; + } + + if (IS_PCI_IDE (&PciData) || IS_PCI_SATADPA (&PciData)) { + return EFI_SUCCESS; + } + + return EFI_UNSUPPORTED; +} + +/** + This routine is called right after the .Supported() called and + Start this driver on ControllerHandle. + + @param This Protocol instance pointer. + @param Controller Handle of device to bind driver to. + @param RemainingDevicePath A pointer to the device path. + it should be ignored by device driver. + + @retval EFI_SUCCESS This driver is added to this device. + @retval EFI_ALREADY_STARTED This driver is already running on this device. + @retval other Some error occurs when binding this driver to this device. + +**/ +EFI_STATUS +EFIAPI +SataControllerStart ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE Controller, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath + ) +{ + EFI_STATUS Status; + EFI_PCI_IO_PROTOCOL *PciIo; + PCI_TYPE00 PciData; + EFI_SATA_CONTROLLER_PRIVATE_DATA *SataPrivateData; + UINT32 Data32; + UINTN ChannelDeviceCount; + + DEBUG ((EFI_D_INFO, "SataControllerStart START\n")); + + SataPrivateData = NULL; + + // + // Now test and open PCI I/O Protocol + // + Status = gBS->OpenProtocol ( + Controller, + &gEfiPciIoProtocolGuid, + (VOID **) &PciIo, + This->DriverBindingHandle, + Controller, + EFI_OPEN_PROTOCOL_BY_DRIVER + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "SataControllerStart error return status = %r\n", Status)); + return Status; + } + + // + // Allocate Sata Private Data structure + // + SataPrivateData = AllocateZeroPool (sizeof (EFI_SATA_CONTROLLER_PRIVATE_DATA)); + if (SataPrivateData == NULL) { + Status = EFI_OUT_OF_RESOURCES; + goto Done; + } + + // + // Initialize Sata Private Data + // + SataPrivateData->Signature = SATA_CONTROLLER_SIGNATURE; + SataPrivateData->PciIo = PciIo; + SataPrivateData->IdeInit.GetChannelInfo = IdeInitGetChannelInfo; + SataPrivateData->IdeInit.NotifyPhase = IdeInitNotifyPhase; + SataPrivateData->IdeInit.SubmitData = IdeInitSubmitData; + SataPrivateData->IdeInit.DisqualifyMode = IdeInitDisqualifyMode; + SataPrivateData->IdeInit.CalculateMode = IdeInitCalculateMode; + SataPrivateData->IdeInit.SetTiming = IdeInitSetTiming; + SataPrivateData->IdeInit.EnumAll = SATA_ENUMER_ALL; + + Status = PciIo->Pci.Read ( + PciIo, + EfiPciIoWidthUint8, + PCI_CLASSCODE_OFFSET, + sizeof (PciData.Hdr.ClassCode), + PciData.Hdr.ClassCode + ); + ASSERT_EFI_ERROR (Status); + + if (IS_PCI_IDE (&PciData)) { + SataPrivateData->IdeInit.ChannelCount = IDE_MAX_CHANNEL; + SataPrivateData->DeviceCount = IDE_MAX_DEVICES; + } else if (IS_PCI_SATADPA (&PciData)) { + // + // Read Host Capability Register(CAP) to get Number of Ports(NPS) and Supports Port Multiplier(SPM) + // NPS is 0's based value indicating the maximum number of ports supported by the HBA silicon. + // A maximum of 32 ports can be supported. A value of '0h', indicating one port, is the minimum requirement. + // + Data32 = AhciReadReg (PciIo, R_AHCI_CAP); + SataPrivateData->IdeInit.ChannelCount = (UINT8) (Data32 & B_AHCI_CAP_NPS) + 1; + SataPrivateData->DeviceCount = AHCI_MAX_DEVICES; + if ((Data32 & B_AHCI_CAP_SPM) == B_AHCI_CAP_SPM) { + SataPrivateData->DeviceCount = AHCI_MULTI_MAX_DEVICES; + } + } + + ChannelDeviceCount = (UINTN) (SataPrivateData->IdeInit.ChannelCount) * (UINTN) (SataPrivateData->DeviceCount); + SataPrivateData->DisqulifiedModes = AllocateZeroPool ((sizeof (EFI_ATA_COLLECTIVE_MODE)) * ChannelDeviceCount); + if (SataPrivateData->DisqulifiedModes == NULL) { + Status = EFI_OUT_OF_RESOURCES; + goto Done; + } + + SataPrivateData->IdentifyData = AllocateZeroPool ((sizeof (EFI_IDENTIFY_DATA)) * ChannelDeviceCount); + if (SataPrivateData->IdentifyData == NULL) { + Status = EFI_OUT_OF_RESOURCES; + goto Done; + } + + SataPrivateData->IdentifyValid = AllocateZeroPool ((sizeof (BOOLEAN)) * ChannelDeviceCount); + if (SataPrivateData->IdentifyValid == NULL) { + Status = EFI_OUT_OF_RESOURCES; + goto Done; + } + + // + // Install IDE Controller Init Protocol to this instance + // + Status = gBS->InstallMultipleProtocolInterfaces ( + &Controller, + &gEfiIdeControllerInitProtocolGuid, + &(SataPrivateData->IdeInit), + NULL + ); + +Done: + if (EFI_ERROR (Status)) { + + gBS->CloseProtocol ( + Controller, + &gEfiPciIoProtocolGuid, + This->DriverBindingHandle, + Controller + ); + if (SataPrivateData != NULL) { + if (SataPrivateData->DisqulifiedModes != NULL) { + FreePool (SataPrivateData->DisqulifiedModes); + } + if (SataPrivateData->IdentifyData != NULL) { + FreePool (SataPrivateData->IdentifyData); + } + if (SataPrivateData->IdentifyValid != NULL) { + FreePool (SataPrivateData->IdentifyValid); + } + FreePool (SataPrivateData); + } + } + + DEBUG ((EFI_D_INFO, "SataControllerStart END status = %r\n", Status)); + + return Status; +} + +/** + Stop this driver on ControllerHandle. + + @param This Protocol instance pointer. + @param Controller Handle of device to stop driver on. + @param NumberOfChildren Not used. + @param ChildHandleBuffer Not used. + + @retval EFI_SUCCESS This driver is removed from this device. + @retval other Some error occurs when removing this driver from this device. + +**/ +EFI_STATUS +EFIAPI +SataControllerStop ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE Controller, + IN UINTN NumberOfChildren, + IN EFI_HANDLE *ChildHandleBuffer + ) +{ + EFI_STATUS Status; + EFI_IDE_CONTROLLER_INIT_PROTOCOL *IdeInit; + EFI_SATA_CONTROLLER_PRIVATE_DATA *SataPrivateData; + + // + // Open the produced protocol + // + Status = gBS->OpenProtocol ( + Controller, + &gEfiIdeControllerInitProtocolGuid, + (VOID **) &IdeInit, + This->DriverBindingHandle, + Controller, + EFI_OPEN_PROTOCOL_GET_PROTOCOL + ); + if (EFI_ERROR (Status)) { + return EFI_UNSUPPORTED; + } + + SataPrivateData = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (IdeInit); + ASSERT (SataPrivateData != NULL); + + // + // Uninstall the IDE Controller Init Protocol from this instance + // + Status = gBS->UninstallMultipleProtocolInterfaces ( + Controller, + &gEfiIdeControllerInitProtocolGuid, + &(SataPrivateData->IdeInit), + NULL + ); + if (EFI_ERROR (Status)) { + return Status; + } + + if (SataPrivateData != NULL) { + if (SataPrivateData->DisqulifiedModes != NULL) { + FreePool (SataPrivateData->DisqulifiedModes); + } + if (SataPrivateData->IdentifyData != NULL) { + FreePool (SataPrivateData->IdentifyData); + } + if (SataPrivateData->IdentifyValid != NULL) { + FreePool (SataPrivateData->IdentifyValid); + } + FreePool (SataPrivateData); + } + + // + // Close protocols opened by Sata Controller driver + // + return gBS->CloseProtocol ( + Controller, + &gEfiPciIoProtocolGuid, + This->DriverBindingHandle, + Controller + ); +} + +// +// Interface functions of IDE_CONTROLLER_INIT protocol +// +/** + This function can be used to obtain information about a specified channel. + It's usually used by IDE Bus driver during enumeration process. + + @param This the EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. Parallel ATA (PATA) controllers can support up to two channels. + Advanced Host Controller Interface (AHCI) Serial ATA (SATA) controllers + can support up to 32 channels, each of which can have up to 1 device. + In the presence of a multiplier, each channel can have 15 devices. + @param Enabled TRUE if the channel is enabled. If the channel is disabled, + then it will no be enumerated. + @param MaxDevices For Parallel ATA (PATA) controllers, this number will either be 1 or 2. + For Serial ATA (SATA) controllers, it always be 1, + but with a port multiplier, this number can be as large as 15. + + @retval EFI_SUCCESS Success to get channel information. + @retval EFI_INVALID_PARAMETER Invalid channel id. +**/ +EFI_STATUS +EFIAPI +IdeInitGetChannelInfo ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + OUT BOOLEAN *Enabled, + OUT UINT8 *MaxDevices + ) +{ + EFI_SATA_CONTROLLER_PRIVATE_DATA *SataPrivateData; + SataPrivateData = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); + ASSERT (SataPrivateData != NULL); + + if (Channel < This->ChannelCount) { + *Enabled = TRUE; + *MaxDevices = SataPrivateData->DeviceCount; + return EFI_SUCCESS; + } + + *Enabled = FALSE; + return EFI_INVALID_PARAMETER; +} + +/** + This function is called by IdeBus driver before executing certain actions. + This allows IDE Controller Init to prepare for each action. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Phase Phase indicator defined by IDE_CONTROLLER_INIT protocol. + @param Channel Channel number. + + @retval EFI_SUCCESS Success operation. +**/ +EFI_STATUS +EFIAPI +IdeInitNotifyPhase ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN EFI_IDE_CONTROLLER_ENUM_PHASE Phase, + IN UINT8 Channel + ) +{ + return EFI_SUCCESS; +} + +/** + This function is called by IdeBus driver to submit EFI_IDENTIFY_DATA data structure + obtained from IDE deivce. This structure is used to set IDE timing. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param IdentifyData A pointer to EFI_IDENTIFY_DATA data structure. + + @retval EFI_SUCCESS The information is accepted without any errors. + @retval EFI_INVALID_PARAMETER Invalid channel id or device id. +**/ +EFI_STATUS +EFIAPI +IdeInitSubmitData ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + IN EFI_IDENTIFY_DATA *IdentifyData + ) +{ + EFI_SATA_CONTROLLER_PRIVATE_DATA *SataPrivateData; + SataPrivateData = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); + ASSERT (SataPrivateData != NULL); + + if ((Channel >= This->ChannelCount) || (Device >= SataPrivateData->DeviceCount)) { + return EFI_INVALID_PARAMETER; + } + + // + // Make a local copy of device's IdentifyData and mark the valid flag + // + if (IdentifyData != NULL) { + CopyMem ( + &(SataPrivateData->IdentifyData[Channel * Device]), + IdentifyData, + sizeof (EFI_IDENTIFY_DATA) + ); + + SataPrivateData->IdentifyValid[Channel * Device] = TRUE; + } else { + SataPrivateData->IdentifyValid[Channel * Device] = FALSE; + } + + return EFI_SUCCESS; +} + +/** + This function is called by IdeBus driver to disqualify unsupported operation + mode on specfic IDE device. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param BadModes The modes that the device does not support and that + should be disqualified. + + @retval EFI_SUCCESS The modes were accepted without any errors. + @retval EFI_INVALID_PARAMETER Invalid channel id or device id. +**/ +EFI_STATUS +EFIAPI +IdeInitDisqualifyMode ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + IN EFI_ATA_COLLECTIVE_MODE *BadModes + ) +{ + EFI_SATA_CONTROLLER_PRIVATE_DATA *SataPrivateData; + SataPrivateData = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); + ASSERT (SataPrivateData != NULL); + + if ((Channel >= This->ChannelCount) || (BadModes == NULL) || (Device >= SataPrivateData->DeviceCount)) { + return EFI_INVALID_PARAMETER; + } + + // + // Record the disqualified modes per channel per device. From ATA/ATAPI spec, + // if a mode is not supported, the modes higher than it is also not supported. + // + CopyMem ( + &(SataPrivateData->DisqulifiedModes[Channel * Device]), + BadModes, + sizeof (EFI_ATA_COLLECTIVE_MODE) + ); + + return EFI_SUCCESS; +} + +/** + This function is called by IdeBus driver to calculate the best operation mode + supported by specific IDE device. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param SupportedModes The optimum modes for the device. + + @retval EFI_SUCCESS Supported modes are returned. + @retval EFI_INVALID_PARAMETER Invalid channel id or device id. + @retval EFI_OUT_OF_RESOURCES Fail to allocate pool. + @retval EFI_NOT_READY Identify data of the device is not ready. +**/ +EFI_STATUS +EFIAPI +IdeInitCalculateMode ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + OUT EFI_ATA_COLLECTIVE_MODE **SupportedModes + ) +{ + EFI_SATA_CONTROLLER_PRIVATE_DATA *SataPrivateData; + EFI_IDENTIFY_DATA *IdentifyData; + BOOLEAN IdentifyValid; + EFI_ATA_COLLECTIVE_MODE *DisqulifiedModes; + UINT16 SelectedMode; + EFI_STATUS Status; + + SataPrivateData = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); + ASSERT (SataPrivateData != NULL); + + if ((Channel >= This->ChannelCount) || (SupportedModes == NULL) || (Device >= SataPrivateData->DeviceCount)) { + return EFI_INVALID_PARAMETER; + } + + *SupportedModes = AllocateZeroPool (sizeof (EFI_ATA_COLLECTIVE_MODE)); + if (*SupportedModes == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + IdentifyData = &(SataPrivateData->IdentifyData[Channel * Device]); + IdentifyValid = SataPrivateData->IdentifyValid[Channel * Device]; + DisqulifiedModes = &(SataPrivateData->DisqulifiedModes[Channel * Device]); + + // + // Make sure we've got the valid identify data of the device from SubmitData() + // + if (!IdentifyValid) { + return EFI_NOT_READY; + } + + Status = CalculateBestPioMode ( + IdentifyData, + (DisqulifiedModes->PioMode.Valid ? ((UINT16 *) &(DisqulifiedModes->PioMode.Mode)) : NULL), + &SelectedMode + ); + if (!EFI_ERROR (Status)) { + (*SupportedModes)->PioMode.Valid = TRUE; + (*SupportedModes)->PioMode.Mode = SelectedMode; + + } else { + (*SupportedModes)->PioMode.Valid = FALSE; + } + DEBUG ((EFI_D_INFO, "IdeInitCalculateMode: PioMode = %x\n", (*SupportedModes)->PioMode.Mode)); + + Status = CalculateBestUdmaMode ( + IdentifyData, + (DisqulifiedModes->UdmaMode.Valid ? ((UINT16 *) &(DisqulifiedModes->UdmaMode.Mode)) : NULL), + &SelectedMode + ); + + if (!EFI_ERROR (Status)) { + (*SupportedModes)->UdmaMode.Valid = TRUE; + (*SupportedModes)->UdmaMode.Mode = SelectedMode; + + } else { + (*SupportedModes)->UdmaMode.Valid = FALSE; + } + DEBUG ((EFI_D_INFO, "IdeInitCalculateMode: UdmaMode = %x\n", (*SupportedModes)->UdmaMode.Mode)); + + // + // The modes other than PIO and UDMA are not supported + // + return EFI_SUCCESS; +} + +/** + This function is called by IdeBus driver to set appropriate timing on IDE + controller according supported operation mode. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param Modes The modes to set. + + @retval EFI_SUCCESS Sucess operation. +**/ +EFI_STATUS +EFIAPI +IdeInitSetTiming ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + IN EFI_ATA_COLLECTIVE_MODE *Modes + ) +{ + return EFI_SUCCESS; +} diff --git a/DuetPkg/SataControllerDxe/SataController.h b/DuetPkg/SataControllerDxe/SataController.h new file mode 100644 index 0000000000..0352178bab --- /dev/null +++ b/DuetPkg/SataControllerDxe/SataController.h @@ -0,0 +1,402 @@ +/** @file + Header file for Sata Controller driver. + + Copyright (c) 2011, Intel Corporation. All rights reserved.
+ 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 + http://opensource.org/licenses/bsd-license.php + + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. + +**/ + +#ifndef _SATA_CONTROLLER_H_ +#define _SATA_CONTROLLER_H_ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +// +// Global Variables definitions +// +extern EFI_DRIVER_BINDING_PROTOCOL gSataControllerDriverBinding; +extern EFI_COMPONENT_NAME_PROTOCOL gSataControllerComponentName; +extern EFI_COMPONENT_NAME2_PROTOCOL gSataControllerComponentName2; + +#define AHCI_BAR_INDEX 0x05 +#define R_AHCI_CAP 0x0 +#define B_AHCI_CAP_NPS (BIT4 | BIT3 | BIT2 | BIT1 | BIT0) // Number of Ports +#define B_AHCI_CAP_SPM BIT17 // Supports Port Multiplier + +/// +/// AHCI each channel can have up to 1 device +/// +#define AHCI_MAX_DEVICES 0x01 + +/// +/// AHCI each channel can have 15 devices in the presence of a multiplier +/// +#define AHCI_MULTI_MAX_DEVICES 0x0F + +/// +/// IDE supports 2 channel max +/// +#define IDE_MAX_CHANNEL 0x02 + +/// +/// IDE supports 2 devices max +/// +#define IDE_MAX_DEVICES 0x02 + +#define SATA_ENUMER_ALL FALSE + +// +// Sata Controller driver private data structure +// + +#define SATA_CONTROLLER_SIGNATURE SIGNATURE_32('S','A','T','A') + +typedef struct _EFI_SATA_CONTROLLER_PRIVATE_DATA { + // + // Standard signature used to identify Sata Controller private data + // + UINT32 Signature; + + // + // Protocol instance of IDE_CONTROLLER_INIT produced by this driver + // + EFI_IDE_CONTROLLER_INIT_PROTOCOL IdeInit; + + // + // Copy of protocol pointers used by this driver + // + EFI_PCI_IO_PROTOCOL *PciIo; + + // + // The number of devices that are supported by this channel + // + UINT8 DeviceCount; + + // + // The highest disqulified mode for each attached device, + // From ATA/ATAPI spec, if a mode is not supported, + // the modes higher than it is also not supported + // + EFI_ATA_COLLECTIVE_MODE *DisqulifiedModes; + + // + // A copy of EFI_IDENTIFY_DATA data for each attached SATA device and its flag + // + EFI_IDENTIFY_DATA *IdentifyData; + BOOLEAN *IdentifyValid; +} EFI_SATA_CONTROLLER_PRIVATE_DATA; + +#define SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS(a) CR(a, EFI_SATA_CONTROLLER_PRIVATE_DATA, IdeInit, SATA_CONTROLLER_SIGNATURE) + +// +// Driver binding functions declaration +// +/** + Supported function of Driver Binding protocol for this driver. + Test to see if this driver supports ControllerHandle. + + @param This Protocol instance pointer. + @param Controller Handle of device to test. + @param RemainingDevicePath A pointer to the device path. Should be ignored by + device driver. + + @retval EFI_SUCCESS This driver supports this device. + @retval EFI_ALREADY_STARTED This driver is already running on this device. + @retval other This driver does not support this device. + +**/ +EFI_STATUS +EFIAPI +SataControllerSupported ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE Controller, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath + ) +; + +/** + This routine is called right after the .Supported() called and + Start this driver on ControllerHandle. + + @param This Protocol instance pointer. + @param Controller Handle of device to bind driver to. + @param RemainingDevicePath A pointer to the device path. Should be ignored by + device driver. + + @retval EFI_SUCCESS This driver is added to this device. + @retval EFI_ALREADY_STARTED This driver is already running on this device. + @retval other Some error occurs when binding this driver to this device. + +**/ +EFI_STATUS +EFIAPI +SataControllerStart ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE Controller, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath + ) +; + +/** + Stop this driver on ControllerHandle. + + @param This Protocol instance pointer. + @param Controller Handle of device to stop driver on. + @param NumberOfChildren Not used. + @param ChildHandleBuffer Not used. + + @retval EFI_SUCCESS This driver is removed from this device. + @retval other Some error occurs when removing this driver from this device. + +**/ +EFI_STATUS +EFIAPI +SataControllerStop ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE Controller, + IN UINTN NumberOfChildren, + IN EFI_HANDLE *ChildHandleBuffer + ) +; + +// +// IDE controller init functions declaration +// +/** + This function can be used to obtain information about a specified channel. + It's usually used by IDE Bus driver during enumeration process. + + @param This the EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. Parallel ATA (PATA) controllers can support up to two channels. + Advanced Host Controller Interface (AHCI) Serial ATA (SATA) controllers + can support up to 32 channels, each of which can have up to one device. + In the presence of a multiplier, each channel can have 15 devices. + @param Enabled TRUE if the channel is enabled. If the channel is disabled, + then it will no be enumerated. + @param MaxDevices For Parallel ATA (PATA) controllers, this number will either be 1 or 2. + For Serial ATA (SATA) controllers with a port multiplier, this number can be as large as 15. + + @retval EFI_SUCCESS Success to get channel information. + @retval EFI_INVALID_PARAMETER Invalid channel id. +**/ +EFI_STATUS +EFIAPI +IdeInitGetChannelInfo ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + OUT BOOLEAN *Enabled, + OUT UINT8 *MaxDevices + ) +; + +/** + This function is called by IdeBus driver before executing certain actions. + This allows IDE Controller Init to prepare for each action. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Phase Phase indicator defined by IDE_CONTROLLER_INIT protocol. + @param Channel Channel number. + + @retval EFI_SUCCESS Success operation. +**/ +EFI_STATUS +EFIAPI +IdeInitNotifyPhase ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN EFI_IDE_CONTROLLER_ENUM_PHASE Phase, + IN UINT8 Channel + ) +; + +/** + This function is called by IdeBus driver to submit EFI_IDENTIFY_DATA data structure + obtained from IDE deivce. This structure is used to set IDE timing. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param IdentifyData A pointer to EFI_IDENTIFY_DATA data structure. + + @retval EFI_SUCCESS The information was accepted without any errors. + @retval EFI_INVALID_PARAMETER Invalid channel id or device id. +**/ +EFI_STATUS +EFIAPI +IdeInitSubmitData ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + IN EFI_IDENTIFY_DATA *IdentifyData + ) +; + +/** + This function is called by IdeBus driver to disqualify unsupported operation + mode on specfic IDE device. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param BadModes The modes that the device does not support and that + should be disqualified. + + @retval EFI_SUCCESS The modes were accepted without any errors. + @retval EFI_INVALID_PARAMETER Invalid channel id or device id. +**/ +EFI_STATUS +EFIAPI +IdeInitDisqualifyMode ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + IN EFI_ATA_COLLECTIVE_MODE *BadModes + ) +; + +/** + This function is called by IdeBus driver to calculate the best operation mode + supported by specific IDE device. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param SupportedModes The optimum modes for the device. + + @retval EFI_SUCCESS SupportedModes was returned. + @retval EFI_OUT_OF_RESOURCES Fail to allocate pool. + @retval EFI_INVALID_PARAMETER Invalid channel id or device id. +**/ +EFI_STATUS +EFIAPI +IdeInitCalculateMode ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + OUT EFI_ATA_COLLECTIVE_MODE **SupportedModes + ) +; + +/** + This function is called by IdeBus driver to set appropriate timing on IDE + controller according supported operation mode. + + @param This The EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. + @param Channel Channel number. + @param Device Device number. + @param Modes The modes to set. + + @retval EFI_SUCCESS Sucess operation. +**/ +EFI_STATUS +EFIAPI +IdeInitSetTiming ( + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, + IN UINT8 Channel, + IN UINT8 Device, + IN EFI_ATA_COLLECTIVE_MODE *Modes + ) +; + +// +// Forward reference declaration +// +/** + Retrieves a Unicode string that is the user readable name of the UEFI Driver. + + @param This A pointer to the EFI_COMPONENT_NAME_PROTOCOL instance. + @param Language A pointer to a three character ISO 639-2 language identifier. + This is the language of the driver name that that the caller + is requesting, and it must match one of the languages specified + in SupportedLanguages. The number of languages supported by a + driver is up to the driver writer. + @param DriverName A pointer to the Unicode string to return. This Unicode string + is the name of the driver specified by This in the language + specified by Language. + + @retval EFI_SUCCESS The Unicode string for the Driver specified by This + and the language specified by Language was returned + in DriverName. + @retval EFI_INVALID_PARAMETER Language is NULL. + @retval EFI_INVALID_PARAMETER DriverName is NULL. + @retval EFI_UNSUPPORTED The driver specified by This does not support the + language specified by Language. +**/ +EFI_STATUS +EFIAPI +SataControllerComponentNameGetDriverName ( + IN EFI_COMPONENT_NAME_PROTOCOL *This, + IN CHAR8 *Language, + OUT CHAR16 **DriverName + ) +; + +/** + Retrieves a Unicode string that is the user readable name of the controller + that is being managed by an UEFI Driver. + + @param This A pointer to the EFI_COMPONENT_NAME_PROTOCOL instance. + @param ControllerHandle The handle of a controller that the driver specified by + This is managing. This handle specifies the controller + whose name is to be returned. + @param OPTIONAL ChildHandle The handle of the child controller to retrieve the name + of. This is an optional parameter that may be NULL. It + will be NULL for device drivers. It will also be NULL + for a bus drivers that wish to retrieve the name of the + bus controller. It will not be NULL for a bus driver + that wishes to retrieve the name of a child controller. + @param Language A pointer to a three character ISO 639-2 language + identifier. This is the language of the controller name + that that the caller is requesting, and it must match one + of the languages specified in SupportedLanguages. The + number of languages supported by a driver is up to the + driver writer. + @param ControllerName A pointer to the Unicode string to return. This Unicode + string is the name of the controller specified by + ControllerHandle and ChildHandle in the language + specified by Language from the point of view of the + driver specified by This. + + @retval EFI_SUCCESS The Unicode string for the user readable name in the + language specified by Language for the driver + specified by This was returned in DriverName. + @retval EFI_INVALID_PARAMETER ControllerHandle is not a valid EFI_HANDLE. + @retval EFI_INVALID_PARAMETER ChildHandle is not NULL and it is not a valid + EFI_HANDLE. + @retval EFI_INVALID_PARAMETER Language is NULL. + @retval EFI_INVALID_PARAMETER ControllerName is NULL. + @retval EFI_UNSUPPORTED The driver specified by This is not currently + managing the controller specified by + ControllerHandle and ChildHandle. + @retval EFI_UNSUPPORTED The driver specified by This does not support the + language specified by Language. +**/ +EFI_STATUS +EFIAPI +SataControllerComponentNameGetControllerName ( + IN EFI_COMPONENT_NAME_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN EFI_HANDLE ChildHandle OPTIONAL, + IN CHAR8 *Language, + OUT CHAR16 **ControllerName + ) +; + +#endif diff --git a/DuetPkg/SataControllerDxe/SataControllerDxe.inf b/DuetPkg/SataControllerDxe/SataControllerDxe.inf new file mode 100644 index 0000000000..b3b37ddd0e --- /dev/null +++ b/DuetPkg/SataControllerDxe/SataControllerDxe.inf @@ -0,0 +1,49 @@ +## @file +# +# Component description file for the Sata Controller driver. +# +# Copyright (c) 2011, Intel Corporation. All rights reserved.
+# 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 +# http://opensource.org/licenses/bsd-license.php +# +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. +# +## + +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = SataController + FILE_GUID = 8F4CD826-A5A0-4e93-9522-CFB0AB72926C + MODULE_TYPE = UEFI_DRIVER + VERSION_STRING = 1.0 + ENTRY_POINT = InitializeSataControllerDriver + +# +# The following information is for reference only and not required by the build tools. +# +# VALID_ARCHITECTURES = IA32 X64 IPF EBC +# + +[Sources] + ComponentName.c + SataController.c + SataController.h + +[Packages] + MdePkg/MdePkg.dec + +[LibraryClasses] + UefiDriverEntryPoint + DebugLib + UefiLib + BaseLib + BaseMemoryLib + MemoryAllocationLib + UefiBootServicesTableLib + +[Protocols] + gEfiPciIoProtocolGuid + gEfiIdeControllerInitProtocolGuid -- 2.39.2