Reviewed-by: Giri P Mudusuru <[email protected]> > -----Original Message----- > From: Chan, Amy > Sent: Monday, July 25, 2016 8:14 PM > To: Tian, Feng <[email protected]>; Kinney, Michael D > <[email protected]>; Mudusuru, Giri P <[email protected]> > Cc: [email protected] > Subject: RE: [patch] MdeModulePkg: add generic SataController driver. > > Reviewed-by: Chan, Amy <[email protected]> > > Thanks > Amy > > > -----Original Message----- > > From: Tian, Feng > > Sent: Wednesday, July 20, 2016 1:07 PM > > To: Kinney, Michael D <[email protected]>; Mudusuru, Giri P > > <[email protected]>; Chan, Amy <[email protected]> > > Cc: [email protected] > > Subject: [patch] MdeModulePkg: add generic SataController driver. > > > > This SataController driver is used to provide a generic solution > > for those IDE/SATA/AHCI spec compliance host controllers. > > > > If there is special reqirement on timing setting or something else, > > user could override this driver to customize a specific one. > > > > Cc: Michael Kinney <[email protected]> > > Cc: Amy Chan <[email protected]> > > Cc: Giri P Mudusuru <[email protected]> > > Contributed-under: TianoCore Contribution Agreement 1.0 > > Signed-off-by: Feng Tian <[email protected]> > > --- > > .../Bus/Pci/SataControllerDxe/ComponentName.c | 177 ++++ > > .../Bus/Pci/SataControllerDxe/SataController.c | 1021 > > ++++++++++++++++++++ > > .../Bus/Pci/SataControllerDxe/SataController.h | 536 ++++++++++ > > .../Pci/SataControllerDxe/SataControllerDxe.inf | 58 ++ > > .../Pci/SataControllerDxe/SataControllerDxe.uni | 22 + > > .../SataControllerDxe/SataControllerDxeExtra.uni | 20 + > > MdeModulePkg/MdeModulePkg.dsc | 1 + > > 7 files changed, 1835 insertions(+) > > create mode 100644 > > MdeModulePkg/Bus/Pci/SataControllerDxe/ComponentName.c > > create mode 100644 > > MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.c > > create mode 100644 > > MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.h > > create mode 100644 > > MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf > > create mode 100644 > > MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.uni > > create mode 100644 > > MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxeExtra.uni > > > > diff --git a/MdeModulePkg/Bus/Pci/SataControllerDxe/ComponentName.c > > b/MdeModulePkg/Bus/Pci/SataControllerDxe/ComponentName.c > > new file mode 100644 > > index 0000000..467ad11 > > --- /dev/null > > +++ b/MdeModulePkg/Bus/Pci/SataControllerDxe/ComponentName.c > > @@ -0,0 +1,177 @@ > > +/** @file > > + UEFI Component Name(2) protocol implementation for Sata Controller > > driver. > > + > > + Copyright (c) 2011 - 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 > > + 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/MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.c > > b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.c > > new file mode 100644 > > index 0000000..a6d55c1 > > --- /dev/null > > +++ b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.c > > @@ -0,0 +1,1021 @@ > > +/** @file > > + This driver module produces IDE_CONTROLLER_INIT protocol for Sata > > Controllers. > > + > > + Copyright (c) 2011 - 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 > > + 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; > > +} > > + > > +/** > > + 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 *Private; > > + UINT32 Data32; > > + UINTN TotalCount; > > + > > + DEBUG ((EFI_D_INFO, "SataControllerStart start\n")); > > + > > + Private = 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 > > + // > > + Private = AllocateZeroPool (sizeof > (EFI_SATA_CONTROLLER_PRIVATE_DATA)); > > + if (Private == NULL) { > > + Status = EFI_OUT_OF_RESOURCES; > > + goto Done; > > + } > > + > > + // > > + // Initialize Sata Private Data > > + // > > + Private->Signature = SATA_CONTROLLER_SIGNATURE; > > + Private->PciIo = PciIo; > > + Private->IdeInit.GetChannelInfo = IdeInitGetChannelInfo; > > + Private->IdeInit.NotifyPhase = IdeInitNotifyPhase; > > + Private->IdeInit.SubmitData = IdeInitSubmitData; > > + Private->IdeInit.DisqualifyMode = IdeInitDisqualifyMode; > > + Private->IdeInit.CalculateMode = IdeInitCalculateMode; > > + Private->IdeInit.SetTiming = IdeInitSetTiming; > > + Private->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)) { > > + Private->IdeInit.ChannelCount = IDE_MAX_CHANNEL; > > + Private->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); > > + Private->IdeInit.ChannelCount = (UINT8) ((Data32 & B_AHCI_CAP_NPS) + > 1); > > + Private->DeviceCount = AHCI_MAX_DEVICES; > > + if ((Data32 & B_AHCI_CAP_SPM) == B_AHCI_CAP_SPM) { > > + Private->DeviceCount = AHCI_MULTI_MAX_DEVICES; > > + } > > + } > > + > > + TotalCount = (UINTN) (Private->IdeInit.ChannelCount) * (UINTN) (Private- > > >DeviceCount); > > + Private->DisqualifiedModes = AllocateZeroPool ((sizeof > > (EFI_ATA_COLLECTIVE_MODE)) * TotalCount); > > + if (Private->DisqualifiedModes == NULL) { > > + Status = EFI_OUT_OF_RESOURCES; > > + goto Done; > > + } > > + > > + Private->IdentifyData = AllocateZeroPool ((sizeof (EFI_IDENTIFY_DATA)) * > > TotalCount); > > + if (Private->IdentifyData == NULL) { > > + Status = EFI_OUT_OF_RESOURCES; > > + goto Done; > > + } > > + > > + Private->IdentifyValid = AllocateZeroPool ((sizeof (BOOLEAN)) * > TotalCount); > > + if (Private->IdentifyValid == NULL) { > > + Status = EFI_OUT_OF_RESOURCES; > > + goto Done; > > + } > > + > > + // > > + // Install IDE Controller Init Protocol to this instance > > + // > > + Status = gBS->InstallMultipleProtocolInterfaces ( > > + &Controller, > > + &gEfiIdeControllerInitProtocolGuid, > > + &(Private->IdeInit), > > + NULL > > + ); > > + > > +Done: > > + if (EFI_ERROR (Status)) { > > + > > + gBS->CloseProtocol ( > > + Controller, > > + &gEfiPciIoProtocolGuid, > > + This->DriverBindingHandle, > > + Controller > > + ); > > + if (Private != NULL) { > > + if (Private->DisqualifiedModes != NULL) { > > + FreePool (Private->DisqualifiedModes); > > + } > > + if (Private->IdentifyData != NULL) { > > + FreePool (Private->IdentifyData); > > + } > > + if (Private->IdentifyValid != NULL) { > > + FreePool (Private->IdentifyValid); > > + } > > + FreePool (Private); > > + } > > + } > > + > > + DEBUG ((EFI_D_INFO, "SataControllerStart end with %r\n", Status)); > > + > > + return Status; > > +} > > + > > +/** > > + Stop this driver on ControllerHandle. > > + > > + @param This A pointer to the EFI_DRIVER_BINDING_PROTOCOL > > instance. > > + @param Controller A handle to the device being stopped. > > + @param NumberOfChildren The number of child device handles in > > ChildHandleBuffer. > > + @param ChildHandleBuffer An array of child handles to be freed. > > + > > + @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 *Private; > > + > > + // > > + // 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; > > + } > > + > > + Private = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (IdeInit); > > + ASSERT (Private != NULL); > > + > > + // > > + // Uninstall the IDE Controller Init Protocol from this instance > > + // > > + Status = gBS->UninstallMultipleProtocolInterfaces ( > > + Controller, > > + &gEfiIdeControllerInitProtocolGuid, > > + &(Private->IdeInit), > > + NULL > > + ); > > + if (EFI_ERROR (Status)) { > > + return Status; > > + } > > + > > + if (Private != NULL) { > > + if (Private->DisqualifiedModes != NULL) { > > + FreePool (Private->DisqualifiedModes); > > + } > > + if (Private->IdentifyData != NULL) { > > + FreePool (Private->IdentifyData); > > + } > > + if (Private->IdentifyValid != NULL) { > > + FreePool (Private->IdentifyValid); > > + } > > + FreePool (Private); > > + } > > + > > + // > > + // Close protocols opened by Sata Controller driver > > + // > > + return gBS->CloseProtocol ( > > + Controller, > > + &gEfiPciIoProtocolGuid, > > + This->DriverBindingHandle, > > + Controller > > + ); > > +} > > + > > +/** > > + Calculate the flat array subscript of a (Channel, Device) pair. > > + > > + @param[in] Private The private data structure corresponding to the > > + SATA controller that attaches the device for > > + which the flat array subscript is being > > + calculated. > > + > > + @param[in] Channel The channel (ie. port) number on the SATA > > + controller that the device is attached to. > > + > > + @param[in] Device The device number on the channel. > > + > > + @return The flat array subscript suitable for indexing > > DisqualifiedModes, > > + IdentifyData, and IdentifyValid. > > +**/ > > +STATIC > > +UINTN > > +FlatDeviceIndex ( > > + IN CONST EFI_SATA_CONTROLLER_PRIVATE_DATA *Private, > > + IN UINTN Channel, > > + IN UINTN Device > > + ) > > +{ > > + ASSERT (Private != NULL); > > + ASSERT (Channel < Private->IdeInit.ChannelCount); > > + ASSERT (Device < Private->DeviceCount); > > + > > + return Channel * Private->DeviceCount + Device; > > +} > > + > > +// > > +// Interface functions of IDE_CONTROLLER_INIT protocol > > +// > > +/** > > + Returns the information about the specified IDE channel. > > + > > + This function can be used to obtain information about a particular IDE > > channel. > > + The driver entity uses this information during the enumeration process. > > + > > + If Enabled is set to FALSE, the driver entity will not scan the channel. > > Note > > + that it will not prevent an operating system driver from scanning the > > channel. > > + > > + For most of today's controllers, MaxDevices will either be 1 or 2. For > > SATA > > + controllers, this value will always be 1. SATA configurations can contain > > SATA > > + port multipliers. SATA port multipliers behave like SATA bridges and can > > support > > + up to 16 devices on the other side. If a SATA port out of the IDE > > controller > > + is connected to a port multiplier, MaxDevices will be set to the number > > of > > SATA > > + devices that the port multiplier supports. Because today's port > > multipliers > > + support up to fifteen SATA devices, this number can be as large as > > fifteen. > > The IDE > > + bus driver is required to scan for the presence of port multipliers > > behind an > > SATA > > + controller and enumerate up to MaxDevices number of devices behind the > > port > > + multiplier. > > + > > + In this context, the devices behind a port multiplier constitute a > > channel. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel Zero-based channel number. > > + @param[out] Enabled TRUE if this channel is enabled. > > Disabled > > channels > > + are not scanned to see if any devices > > are present. > > + @param[out] MaxDevices The maximum number of IDE devices that > > the bus driver > > + can expect on this channel. For the > > ATA/ATAPI > > + specification, version 6, this number > > will either be > > + one or two. For Serial ATA (SATA) > > configurations with a > > + port multiplier, this number can be as > > large as fifteen. > > + > > + @retval EFI_SUCCESS Information was returned without any > > errors. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + > > +**/ > > +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 *Private; > > + Private = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); > > + ASSERT (Private != NULL); > > + > > + if (Channel < This->ChannelCount) { > > + *Enabled = TRUE; > > + *MaxDevices = Private->DeviceCount; > > + return EFI_SUCCESS; > > + } > > + > > + *Enabled = FALSE; > > + return EFI_INVALID_PARAMETER; > > +} > > + > > +/** > > + The notifications from the driver entity that it is about to enter a > > certain > > + phase of the IDE channel enumeration process. > > + > > + This function can be used to notify the IDE controller driver to perform > > + specific actions, including any chipset-specific initialization, so that > > the > > + chipset is ready to enter the next phase. Seven notification points are > > defined > > + at this time. > > + > > + More synchronization points may be added as required in the future. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL > > + instance. > > + @param[in] Phase The phase during enumeration. > > + @param[in] Channel Zero-based channel number. > > + > > + @retval EFI_SUCCESS The notification was accepted without any > > errors. > > + @retval EFI_UNSUPPORTED Phase is not supported. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_NOT_READY This phase cannot be entered at this > > time; > > for > > + example, an attempt was made to enter a > > Phase > > + without having entered one or more > > previous > > + Phase. > > + > > +**/ > > +EFI_STATUS > > +EFIAPI > > +IdeInitNotifyPhase ( > > + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, > > + IN EFI_IDE_CONTROLLER_ENUM_PHASE Phase, > > + IN UINT8 Channel > > + ) > > +{ > > + return EFI_SUCCESS; > > +} > > + > > +/** > > + Submits the device information to the IDE controller driver. > > + > > + This function is used by the driver entity to pass detailed information > > about > > + a particular device to the IDE controller driver. The driver entity > > obtains > > + this information by issuing an ATA or ATAPI IDENTIFY_DEVICE command. > > IdentifyData > > + is the pointer to the response data buffer. The IdentifyData buffer is > > owned > > + by the driver entity, and the IDE controller driver must make a local > > copy > > + of the entire buffer or parts of the buffer as needed. The original > > IdentifyData > > + buffer pointer may not be valid when > > + > > + - EFI_IDE_CONTROLLER_INIT_PROTOCOL.CalculateMode() or > > + - EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode() is called at a > > later point. > > + > > + The IDE controller driver may consult various fields of EFI_IDENTIFY_DATA > > to > > + compute the optimum mode for the device. These fields are not limited to > > the > > + timing information. For example, an implementation of the IDE controller > > driver > > + may examine the vendor and type/mode field to match known bad drives. > > + > > + The driver entity may submit drive information in any order, as long as > > it > > + submits information for all the devices belonging to the enumeration > > group > > + before EFI_IDE_CONTROLLER_INIT_PROTOCOL.CalculateMode() is called > for > > any device > > + in that enumeration group. If a device is absent, > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + should be called with IdentifyData set to NULL. The IDE controller > > driver > > may > > + not have any other mechanism to know whether a device is present or not. > > Therefore, > > + setting IdentifyData to NULL does not constitute an error condition. > > + EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() can be called only > once > > for a > > + given (Channel, Device) pair. > > + > > + @param[in] This A pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel Zero-based channel number. > > + @param[in] Device Zero-based device number on the Channel. > > + @param[in] IdentifyData The device's response to the ATA > > IDENTIFY_DEVICE command. > > + > > + @retval EFI_SUCCESS The information was accepted without any > > errors. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + > > +**/ > > +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 *Private; > > + UINTN DeviceIndex; > > + > > + Private = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); > > + ASSERT (Private != NULL); > > + > > + if ((Channel >= This->ChannelCount) || (Device >= Private->DeviceCount)) > > { > > + return EFI_INVALID_PARAMETER; > > + } > > + > > + DeviceIndex = FlatDeviceIndex (Private, Channel, Device); > > + > > + // > > + // Make a local copy of device's IdentifyData and mark the valid flag > > + // > > + if (IdentifyData != NULL) { > > + CopyMem ( > > + &(Private->IdentifyData[DeviceIndex]), > > + IdentifyData, > > + sizeof (EFI_IDENTIFY_DATA) > > + ); > > + > > + Private->IdentifyValid[DeviceIndex] = TRUE; > > + } else { > > + Private->IdentifyValid[DeviceIndex] = FALSE; > > + } > > + > > + return EFI_SUCCESS; > > +} > > + > > +/** > > + Disqualifies specific modes for an IDE device. > > + > > + This function allows the driver entity or other drivers (such as platform > > + drivers) to reject certain timing modes and request the IDE controller > > driver > > + to recalculate modes. This function allows the driver entity and the IDE > > + controller driver to negotiate the timings on a per-device basis. This > > function > > + is useful in the case of drives that lie about their capabilities. An > > example > > + is when the IDE device fails to accept the timing modes that are > > calculated > > + by the IDE controller driver based on the response to the Identify Drive > > command. > > + > > + If the driver entity does not want to limit the ATA timing modes and > > leave > > that > > + decision to the IDE controller driver, it can either not call this > > function for > > + the given device or call this function and set the Valid flag to FALSE > > for all > > + modes that are listed in EFI_ATA_COLLECTIVE_MODE. > > + > > + The driver entity may disqualify modes for a device in any order and any > > number > > + of times. > > + > > + This function can be called multiple times to invalidate multiple modes > > of > > the > > + same type (e.g., Programmed Input/Output [PIO] modes 3 and 4). See the > > ATA/ATAPI > > + specification for more information on PIO modes. > > + > > + For Serial ATA (SATA) controllers, this member function can be used to > > disqualify > > + a higher transfer rate mode on a given channel. For example, a platform > > driver > > + may inform the IDE controller driver to not use second-generation (Gen2) > > speeds > > + for a certain SATA drive. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel The zero-based channel number. > > + @param[in] Device The zero-based device number on the > > Channel. > > + @param[in] 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 Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + @retval EFI_INVALID_PARAMETER IdentifyData is NULL. > > + > > +**/ > > +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 *Private; > > + UINTN DeviceIndex; > > + > > + Private = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); > > + ASSERT (Private != NULL); > > + > > + if ((Channel >= This->ChannelCount) || (BadModes == NULL) || (Device >= > > Private->DeviceCount)) { > > + return EFI_INVALID_PARAMETER; > > + } > > + > > + DeviceIndex = FlatDeviceIndex (Private, Channel, Device); > > + > > + // > > + // 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 ( > > + &(Private->DisqualifiedModes[DeviceIndex]), > > + BadModes, > > + sizeof (EFI_ATA_COLLECTIVE_MODE) > > + ); > > + > > + return EFI_SUCCESS; > > +} > > + > > +/** > > + Returns the information about the optimum modes for the specified IDE > > device. > > + > > + This function is used by the driver entity to obtain the optimum ATA > > modes > > for > > + a specific device. The IDE controller driver takes into account the > > following > > + while calculating the mode: > > + - The IdentifyData inputs to > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + - The BadModes inputs to > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode() > > + > > + The driver entity is required to call > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + for all the devices that belong to an enumeration group before calling > > + EFI_IDE_CONTROLLER_INIT_PROTOCOL.CalculateMode() for any device in > > the same group. > > + > > + The IDE controller driver will use controller- and possibly > > platform-specific > > + algorithms to arrive at SupportedModes. The IDE controller may base its > > + decision on user preferences and other considerations as well. This > > function > > + may be called multiple times because the driver entity may renegotiate > > the > > mode > > + with the IDE controller driver using > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode(). > > + > > + The driver entity may collect timing information for various devices in > > any > > + order. The driver entity is responsible for making sure that all the > > dependencies > > + are satisfied. For example, the SupportedModes information for device A > > that > > + was previously returned may become stale after a call to > > + EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode() for device B. > > + > > + The buffer SupportedModes is allocated by the callee because the caller > > does > > + not necessarily know the size of the buffer. The type > > EFI_ATA_COLLECTIVE_MODE > > + is defined in a way that allows for future extensibility and can be of > > variable > > + length. This memory pool should be deallocated by the caller when it is > > no > > + longer necessary. > > + > > + The IDE controller driver for a Serial ATA (SATA) controller can use this > > + member function to force a lower speed (first-generation [Gen1] speeds on > > a > > + second-generation [Gen2]-capable hardware). The IDE controller driver > > can > > + also allow the driver entity to stay with the speed that has been > > negotiated > > + by the physical layer. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel A zero-based channel number. > > + @param[in] Device A zero-based device number on the > > Channel. > > + @param[out] SupportedModes The optimum modes for the device. > > + > > + @retval EFI_SUCCESS SupportedModes was returned. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + @retval EFI_INVALID_PARAMETER SupportedModes is NULL. > > + @retval EFI_NOT_READY Modes cannot be calculated due to a lack > > of > > + data. This error may happen if > > + > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + and > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyData() > > + were not called for at least one drive > > in the > > + same enumeration group. > > + > > +**/ > > +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 *Private; > > + EFI_IDENTIFY_DATA *IdentifyData; > > + BOOLEAN IdentifyValid; > > + EFI_ATA_COLLECTIVE_MODE *DisqualifiedModes; > > + UINT16 SelectedMode; > > + EFI_STATUS Status; > > + UINTN DeviceIndex; > > + > > + Private = SATA_CONTROLLER_PRIVATE_DATA_FROM_THIS (This); > > + ASSERT (Private != NULL); > > + > > + if ((Channel >= This->ChannelCount) || (SupportedModes == NULL) || > > (Device >= Private->DeviceCount)) { > > + return EFI_INVALID_PARAMETER; > > + } > > + > > + *SupportedModes = AllocateZeroPool (sizeof > (EFI_ATA_COLLECTIVE_MODE)); > > + if (*SupportedModes == NULL) { > > + ASSERT (*SupportedModes != NULL); > > + return EFI_OUT_OF_RESOURCES; > > + } > > + > > + DeviceIndex = FlatDeviceIndex (Private, Channel, Device); > > + > > + IdentifyData = &(Private->IdentifyData[DeviceIndex]); > > + IdentifyValid = Private->IdentifyValid[DeviceIndex]; > > + DisqualifiedModes = &(Private->DisqualifiedModes[DeviceIndex]); > > + > > + // > > + // Make sure we've got the valid identify data of the device from > > SubmitData() > > + // > > + if (!IdentifyValid) { > > + FreePool (*SupportedModes); > > + return EFI_NOT_READY; > > + } > > + > > + Status = CalculateBestPioMode ( > > + IdentifyData, > > + (DisqualifiedModes->PioMode.Valid ? ((UINT16 *) > > &(DisqualifiedModes->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, > > + (DisqualifiedModes->UdmaMode.Valid ? ((UINT16 *) > > &(DisqualifiedModes->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; > > +} > > + > > +/** > > + Commands the IDE controller driver to program the IDE controller hardware > > + so that the specified device can operate at the specified mode. > > + > > + This function is used by the driver entity to instruct the IDE controller > > + driver to program the IDE controller hardware to the specified modes. > > This > > + function can be called only once for a particular device. For a Serial > > ATA > > + (SATA) Advanced Host Controller Interface (AHCI) controller, no > > controller- > > + specific programming may be required. > > + > > + @param[in] This Pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel Zero-based channel number. > > + @param[in] Device Zero-based device number on the Channel. > > + @param[in] Modes The modes to set. > > + > > + @retval EFI_SUCCESS The command was accepted without any > > errors. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + @retval EFI_NOT_READY Modes cannot be set at this time due to > > lack > > of data. > > + @retval EFI_DEVICE_ERROR Modes cannot be set due to hardware > > failure. > > + The driver entity should not use this > > device. > > + > > +**/ > > +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/MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.h > > b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.h > > new file mode 100644 > > index 0000000..f7db3b8 > > --- /dev/null > > +++ b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataController.h > > @@ -0,0 +1,536 @@ > > +/** @file > > + Header file for Sata Controller driver. > > + > > + Copyright (c) 2011 - 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 > > + 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 <Uefi.h> > > + > > +#include <IndustryStandard/Pci.h> > > + > > +#include <Protocol/ComponentName.h> > > +#include <Protocol/DriverBinding.h> > > +#include <Protocol/PciIo.h> > > +#include <Protocol/IdeControllerInit.h> > > + > > +#include <Library/BaseLib.h> > > +#include <Library/BaseMemoryLib.h> > > +#include <Library/DebugLib.h> > > +#include <Library/UefiLib.h> > > +#include <Library/UefiDriverEntryPoint.h> > > +#include <Library/MemoryAllocationLib.h> > > +#include <Library/UefiBootServicesTableLib.h> > > + > > +// > > +// 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 *DisqualifiedModes; > > + > > + // > > + // 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 A pointer to the EFI_DRIVER_BINDING_PROTOCOL > > instance. > > + @param Controller A handle to the device being stopped. > > + @param NumberOfChildren The number of child device handles in > > ChildHandleBuffer. > > + @param ChildHandleBuffer An array of child handles to be freed. > > + > > + @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 > > +// > > +/** > > + Returns the information about the specified IDE channel. > > + > > + This function can be used to obtain information about a particular IDE > > channel. > > + The driver entity uses this information during the enumeration process. > > + > > + If Enabled is set to FALSE, the driver entity will not scan the channel. > > Note > > + that it will not prevent an operating system driver from scanning the > > channel. > > + > > + For most of today's controllers, MaxDevices will either be 1 or 2. For > > SATA > > + controllers, this value will always be 1. SATA configurations can contain > > SATA > > + port multipliers. SATA port multipliers behave like SATA bridges and can > > support > > + up to 16 devices on the other side. If a SATA port out of the IDE > > controller > > + is connected to a port multiplier, MaxDevices will be set to the number > > of > > SATA > > + devices that the port multiplier supports. Because today's port > > multipliers > > + support up to fifteen SATA devices, this number can be as large as > > fifteen. > > The IDE > > + bus driver is required to scan for the presence of port multipliers > > behind an > > SATA > > + controller and enumerate up to MaxDevices number of devices behind the > > port > > + multiplier. > > + > > + In this context, the devices behind a port multiplier constitute a > > channel. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel Zero-based channel number. > > + @param[out] Enabled TRUE if this channel is enabled. > > Disabled > > channels > > + are not scanned to see if any devices > > are present. > > + @param[out] MaxDevices The maximum number of IDE devices that > > the bus driver > > + can expect on this channel. For the > > ATA/ATAPI > > + specification, version 6, this number > > will either be > > + one or two. For Serial ATA (SATA) > > configurations with a > > + port multiplier, this number can be as > > large as fifteen. > > + > > + > > + @retval EFI_SUCCESS Information was returned without any > > errors. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + > > +**/ > > +EFI_STATUS > > +EFIAPI > > +IdeInitGetChannelInfo ( > > + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, > > + IN UINT8 Channel, > > + OUT BOOLEAN *Enabled, > > + OUT UINT8 *MaxDevices > > + ); > > + > > +/** > > + The notifications from the driver entity that it is about to enter a > > certain > > + phase of the IDE channel enumeration process. > > + > > + This function can be used to notify the IDE controller driver to perform > > + specific actions, including any chipset-specific initialization, so that > > the > > + chipset is ready to enter the next phase. Seven notification points are > > defined > > + at this time. > > + > > + More synchronization points may be added as required in the future. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL > > + instance. > > + @param[in] Phase The phase during enumeration. > > + @param[in] Channel Zero-based channel number. > > + > > + @retval EFI_SUCCESS The notification was accepted without any > > errors. > > + @retval EFI_UNSUPPORTED Phase is not supported. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_NOT_READY This phase cannot be entered at this > > time; > > for > > + example, an attempt was made to enter a > > Phase > > + without having entered one or more > > previous > > + Phase. > > + > > +**/ > > +EFI_STATUS > > +EFIAPI > > +IdeInitNotifyPhase ( > > + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, > > + IN EFI_IDE_CONTROLLER_ENUM_PHASE Phase, > > + IN UINT8 Channel > > + ); > > + > > +/** > > + Submits the device information to the IDE controller driver. > > + > > + This function is used by the driver entity to pass detailed information > > about > > + a particular device to the IDE controller driver. The driver entity > > obtains > > + this information by issuing an ATA or ATAPI IDENTIFY_DEVICE command. > > IdentifyData > > + is the pointer to the response data buffer. The IdentifyData buffer is > > owned > > + by the driver entity, and the IDE controller driver must make a local > > copy > > + of the entire buffer or parts of the buffer as needed. The original > > IdentifyData > > + buffer pointer may not be valid when > > + > > + - EFI_IDE_CONTROLLER_INIT_PROTOCOL.CalculateMode() or > > + - EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode() is called at a > > later point. > > + > > + The IDE controller driver may consult various fields of EFI_IDENTIFY_DATA > > to > > + compute the optimum mode for the device. These fields are not limited to > > the > > + timing information. For example, an implementation of the IDE controller > > driver > > + may examine the vendor and type/mode field to match known bad drives. > > + > > + The driver entity may submit drive information in any order, as long as > > it > > + submits information for all the devices belonging to the enumeration > > group > > + before EFI_IDE_CONTROLLER_INIT_PROTOCOL.CalculateMode() is called > for > > any device > > + in that enumeration group. If a device is absent, > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + should be called with IdentifyData set to NULL. The IDE controller > > driver > > may > > + not have any other mechanism to know whether a device is present or not. > > Therefore, > > + setting IdentifyData to NULL does not constitute an error condition. > > + EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() can be called only > once > > for a > > + given (Channel, Device) pair. > > + > > + @param[in] This A pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel Zero-based channel number. > > + @param[in] Device Zero-based device number on the Channel. > > + @param[in] IdentifyData The device's response to the ATA > > IDENTIFY_DEVICE command. > > + > > + @retval EFI_SUCCESS The information was accepted without any > > errors. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + > > +**/ > > +EFI_STATUS > > +EFIAPI > > +IdeInitSubmitData ( > > + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, > > + IN UINT8 Channel, > > + IN UINT8 Device, > > + IN EFI_IDENTIFY_DATA *IdentifyData > > + ); > > + > > +/** > > + Disqualifies specific modes for an IDE device. > > + > > + This function allows the driver entity or other drivers (such as platform > > + drivers) to reject certain timing modes and request the IDE controller > > driver > > + to recalculate modes. This function allows the driver entity and the IDE > > + controller driver to negotiate the timings on a per-device basis. This > > function > > + is useful in the case of drives that lie about their capabilities. An > > example > > + is when the IDE device fails to accept the timing modes that are > > calculated > > + by the IDE controller driver based on the response to the Identify Drive > > command. > > + > > + If the driver entity does not want to limit the ATA timing modes and > > leave > > that > > + decision to the IDE controller driver, it can either not call this > > function for > > + the given device or call this function and set the Valid flag to FALSE > > for all > > + modes that are listed in EFI_ATA_COLLECTIVE_MODE. > > + > > + The driver entity may disqualify modes for a device in any order and any > > number > > + of times. > > + > > + This function can be called multiple times to invalidate multiple modes > > of > > the > > + same type (e.g., Programmed Input/Output [PIO] modes 3 and 4). See the > > ATA/ATAPI > > + specification for more information on PIO modes. > > + > > + For Serial ATA (SATA) controllers, this member function can be used to > > disqualify > > + a higher transfer rate mode on a given channel. For example, a platform > > driver > > + may inform the IDE controller driver to not use second-generation (Gen2) > > speeds > > + for a certain SATA drive. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel The zero-based channel number. > > + @param[in] Device The zero-based device number on the > > Channel. > > + @param[in] 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 Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + @retval EFI_INVALID_PARAMETER IdentifyData is NULL. > > + > > +**/ > > +EFI_STATUS > > +EFIAPI > > +IdeInitDisqualifyMode ( > > + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, > > + IN UINT8 Channel, > > + IN UINT8 Device, > > + IN EFI_ATA_COLLECTIVE_MODE *BadModes > > + ); > > + > > +/** > > + Returns the information about the optimum modes for the specified IDE > > device. > > + > > + This function is used by the driver entity to obtain the optimum ATA > > modes > > for > > + a specific device. The IDE controller driver takes into account the > > following > > + while calculating the mode: > > + - The IdentifyData inputs to > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + - The BadModes inputs to > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode() > > + > > + The driver entity is required to call > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + for all the devices that belong to an enumeration group before calling > > + EFI_IDE_CONTROLLER_INIT_PROTOCOL.CalculateMode() for any device in > > the same group. > > + > > + The IDE controller driver will use controller- and possibly > > platform-specific > > + algorithms to arrive at SupportedModes. The IDE controller may base its > > + decision on user preferences and other considerations as well. This > > function > > + may be called multiple times because the driver entity may renegotiate > > the > > mode > > + with the IDE controller driver using > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode(). > > + > > + The driver entity may collect timing information for various devices in > > any > > + order. The driver entity is responsible for making sure that all the > > dependencies > > + are satisfied. For example, the SupportedModes information for device A > > that > > + was previously returned may become stale after a call to > > + EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyMode() for device B. > > + > > + The buffer SupportedModes is allocated by the callee because the caller > > does > > + not necessarily know the size of the buffer. The type > > EFI_ATA_COLLECTIVE_MODE > > + is defined in a way that allows for future extensibility and can be of > > variable > > + length. This memory pool should be deallocated by the caller when it is > > no > > + longer necessary. > > + > > + The IDE controller driver for a Serial ATA (SATA) controller can use this > > + member function to force a lower speed (first-generation [Gen1] speeds on > > a > > + second-generation [Gen2]-capable hardware). The IDE controller driver > > can > > + also allow the driver entity to stay with the speed that has been > > negotiated > > + by the physical layer. > > + > > + @param[in] This The pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel A zero-based channel number. > > + @param[in] Device A zero-based device number on the > > Channel. > > + @param[out] SupportedModes The optimum modes for the device. > > + > > + @retval EFI_SUCCESS SupportedModes was returned. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + @retval EFI_INVALID_PARAMETER SupportedModes is NULL. > > + @retval EFI_NOT_READY Modes cannot be calculated due to a lack > > of > > + data. This error may happen if > > + > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.SubmitData() > > + and > > EFI_IDE_CONTROLLER_INIT_PROTOCOL.DisqualifyData() > > + were not called for at least one drive > > in the > > + same enumeration group. > > + > > +**/ > > +EFI_STATUS > > +EFIAPI > > +IdeInitCalculateMode ( > > + IN EFI_IDE_CONTROLLER_INIT_PROTOCOL *This, > > + IN UINT8 Channel, > > + IN UINT8 Device, > > + OUT EFI_ATA_COLLECTIVE_MODE **SupportedModes > > + ); > > + > > +/** > > + Commands the IDE controller driver to program the IDE controller hardware > > + so that the specified device can operate at the specified mode. > > + > > + This function is used by the driver entity to instruct the IDE controller > > + driver to program the IDE controller hardware to the specified modes. > > This > > + function can be called only once for a particular device. For a Serial > > ATA > > + (SATA) Advanced Host Controller Interface (AHCI) controller, no > > controller- > > + specific programming may be required. > > + > > + @param[in] This Pointer to the > > EFI_IDE_CONTROLLER_INIT_PROTOCOL instance. > > + @param[in] Channel Zero-based channel number. > > + @param[in] Device Zero-based device number on the Channel. > > + @param[in] Modes The modes to set. > > + > > + @retval EFI_SUCCESS The command was accepted without any > > errors. > > + @retval EFI_INVALID_PARAMETER Channel is invalid (Channel >= > > ChannelCount). > > + @retval EFI_INVALID_PARAMETER Device is invalid. > > + @retval EFI_NOT_READY Modes cannot be set at this time due to > > lack > > of data. > > + @retval EFI_DEVICE_ERROR Modes cannot be set due to hardware > > failure. > > + The driver entity should not use this > > device. > > + > > +**/ > > +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/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf > > b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf > > new file mode 100644 > > index 0000000..e24b2a0 > > --- /dev/null > > +++ b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf > > @@ -0,0 +1,58 @@ > > +## @file > > +# > > +# Component description file for the Sata Controller driver. > > +# > > +# Copyright (c) 2011 - 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 > > +# 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 > > + MODULE_UNI_FILE = SataControllerDxe.uni > > + FILE_GUID = 820C59BB-274C-43B2-83EA-DAC673035A59 > > + 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 ARM AARCH64 > > +# > > +# DRIVER_BINDING = gSataControllerDriverBinding > > +# COMPONENT_NAME = gSataControllerComponentName > > +# COMPONENT_NAME2 = gSataControllerComponentName2 > > +# > > + > > +[Sources] > > + ComponentName.c > > + SataController.c > > + SataController.h > > + > > +[Packages] > > + MdePkg/MdePkg.dec > > + > > +[LibraryClasses] > > + UefiDriverEntryPoint > > + DebugLib > > + UefiLib > > + BaseLib > > + BaseMemoryLib > > + MemoryAllocationLib > > + UefiBootServicesTableLib > > + > > +[Protocols] > > + gEfiPciIoProtocolGuid ## TO_START > > + gEfiIdeControllerInitProtocolGuid ## BY_START > > + > > +[UserExtensions.TianoCore."ExtraFiles"] > > + SataControllerDxeExtra.uni > > + > > diff --git a/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.uni > > b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.uni > > new file mode 100644 > > index 0000000..a956327 > > --- /dev/null > > +++ b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.uni > > @@ -0,0 +1,22 @@ > > +// /** @file > > +// The SataControllerDxe driver is responsible for managing the standard > > SATA controller. > > +// > > +// It consumes PciIo protocol and produces IdeControllerInit protocol for > > upper layer use. > > +// > > +// Copyright (c) 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 > > +// 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. > > +// > > +// **/ > > + > > + > > +#string STR_MODULE_ABSTRACT #language en-US "Responsible for > > managing the standard SATA controller" > > + > > +#string STR_MODULE_DESCRIPTION #language en-US "Implements the > > IdeControllerInit protocol interface for upper layer use\n" > > + > > \ No newline at end of file > > diff --git > > a/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxeExtra.uni > > b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxeExtra.uni > > new file mode 100644 > > index 0000000..ed25611 > > --- /dev/null > > +++ b/MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxeExtra.uni > > @@ -0,0 +1,20 @@ > > +// /** @file > > +// SataControllerDxe Localized Strings and Content > > +// > > +// Copyright (c) 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 > > +// 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. > > +// > > +// **/ > > + > > +#string STR_PROPERTIES_MODULE_NAME > > +#language en-US > > +"SATA Controller DXE Driver" > > + > > + > > diff --git a/MdeModulePkg/MdeModulePkg.dsc > > b/MdeModulePkg/MdeModulePkg.dsc > > index 1e57389..daad736 100644 > > --- a/MdeModulePkg/MdeModulePkg.dsc > > +++ b/MdeModulePkg/MdeModulePkg.dsc > > @@ -234,6 +234,7 @@ > > MdeModulePkg/Bus/Pci/IdeBusPei/IdeBusPei.inf > > MdeModulePkg/Bus/Usb/UsbBusPei/UsbBusPei.inf > > MdeModulePkg/Bus/Usb/UsbBotPei/UsbBotPei.inf > > + MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf > > MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf > > MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf > > MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf > > -- > > 2.7.1.windows.2
_______________________________________________ edk2-devel mailing list [email protected] https://lists.01.org/mailman/listinfo/edk2-devel

