diff options
Diffstat (limited to 'src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family')
3 files changed, 1184 insertions, 0 deletions
diff --git a/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataEnvService.c b/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataEnvService.c new file mode 100644 index 0000000000..a90771f04b --- /dev/null +++ b/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataEnvService.c @@ -0,0 +1,307 @@ +/* $NoKeywords:$ */ +/** + * @file + * + * Graphics Controller family specific service procedure + * + * + * + * @xrefitem bom "File Content Label" "Release Content" + * @e project: AGESA + * @e sub-project: FCH + * @e \$Revision: 63460 $ @e \$Date: 2011-12-22 19:04:22 -0600 (Thu, 22 Dec 2011) $ + * + */ + +/* +***************************************************************************** +* +* Copyright 2008 - 2012 ADVANCED MICRO DEVICES, INC. All Rights Reserved. +* +* AMD is granting you permission to use this software (the Materials) +* pursuant to the terms and conditions of your Software License Agreement +* with AMD. This header does *NOT* give you permission to use the Materials +* or any rights under AMD's intellectual property. Your use of any portion +* of these Materials shall constitute your acceptance of those terms and +* conditions. If you do not agree to the terms and conditions of the Software +* License Agreement, please do not use any portion of these Materials. +* +* CONFIDENTIALITY: The Materials and all other information, identified as +* confidential and provided to you by AMD shall be kept confidential in +* accordance with the terms and conditions of the Software License Agreement. +* +* LIMITATION OF LIABILITY: THE MATERIALS AND ANY OTHER RELATED INFORMATION +* PROVIDED TO YOU BY AMD ARE PROVIDED "AS IS" WITHOUT ANY EXPRESS OR IMPLIED +* WARRANTY OF ANY KIND, INCLUDING BUT NOT LIMITED TO WARRANTIES OF +* MERCHANTABILITY, NONINFRINGEMENT, TITLE, FITNESS FOR ANY PARTICULAR PURPOSE, +* OR WARRANTIES ARISING FROM CONDUCT, COURSE OF DEALING, OR USAGE OF TRADE. +* IN NO EVENT SHALL AMD OR ITS LICENSORS BE LIABLE FOR ANY DAMAGES WHATSOEVER +* (INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF PROFITS, BUSINESS +* INTERRUPTION, OR LOSS OF INFORMATION) ARISING OUT OF AMD'S NEGLIGENCE, +* GROSS NEGLIGENCE, THE USE OF OR INABILITY TO USE THE MATERIALS OR ANY OTHER +* RELATED INFORMATION PROVIDED TO YOU BY AMD, EVEN IF AMD HAS BEEN ADVISED OF +* THE POSSIBILITY OF SUCH DAMAGES. BECAUSE SOME JURISDICTIONS PROHIBIT THE +* EXCLUSION OR LIMITATION OF LIABILITY FOR CONSEQUENTIAL OR INCIDENTAL DAMAGES, +* THE ABOVE LIMITATION MAY NOT APPLY TO YOU. +* +* AMD does not assume any responsibility for any errors which may appear in +* the Materials or any other related information provided to you by AMD, or +* result from use of the Materials or any related information. +* +* You agree that you will not reverse engineer or decompile the Materials. +* +* NO SUPPORT OBLIGATION: AMD is not obligated to furnish, support, or make any +* further information, software, technical information, know-how, or show-how +* available to you. Additionally, AMD retains the right to modify the +* Materials at any time, without notice, and is not obligated to provide such +* modified Materials to you. +* +* U.S. GOVERNMENT RESTRICTED RIGHTS: The Materials are provided with +* "RESTRICTED RIGHTS." Use, duplication, or disclosure by the Government is +* subject to the restrictions as set forth in FAR 52.227-14 and +* DFAR252.227-7013, et seq., or its successor. Use of the Materials by the +* Government constitutes acknowledgement of AMD's proprietary rights in them. +* +* EXPORT ASSURANCE: You agree and certify that neither the Materials, nor any +* direct product thereof will be exported directly or indirectly, into any +* country prohibited by the United States Export Administration Act and the +* regulations thereunder, without the required authorization from the U.S. +* government nor will be used for any purpose prohibited by the same. +* *************************************************************************** +*/ + + +/*---------------------------------------------------------------------------------------- + * M O D U L E S U S E D + *---------------------------------------------------------------------------------------- + */ +#include "FchPlatform.h" +#include "Filecode.h" +#define FILECODE PROC_FCH_SATA_FAMILY_HUDSON2_HUDSON2SATAENVSERVICE_FILECODE + +/*---------------------------------------------------------------------------------------- + * D E F I N I T I O N S A N D M A C R O S + *---------------------------------------------------------------------------------------- + */ +// +// Local Routine +// +VOID FchSataCombineControlDataByte (IN UINT8 *ControlReg); +VOID FchSataCombineControlDataWord (IN UINT16 *ControlReg); + +SATA_PHY_SETTING SataPhyTable[] = +{ + //Gen3 + {0x0030, 0x0057A607}, + {0x0031, 0x0057A607}, + {0x0032, 0x0057A407}, + {0x0033, 0x0057A407}, + {0x0034, 0x0057A607}, + {0x0035, 0x0057A607}, + {0x0036, 0x0057A403}, + {0x0037, 0x0057A403}, + + //Gen2 + {0x0120, 0x00071302}, + + //Gen1 + {0x0110, 0x00174101} +}; + +/** + * FchInitEnvProgramSataPciRegs - Sata Pci Configuration Space + * register setting + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchInitEnvProgramSataPciRegs ( + IN VOID *FchDataPtr + ) +{ + UINT8 *PortRegByte; + UINT16 *PortRegWord; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + // + // Caculate SataPortReg for SATA_ESP_PORT + // + PortRegByte = &(LocalCfgPtr->Sata.SataEspPort.SataPortReg); + FchSataCombineControlDataByte (PortRegByte); + PortRegByte = &(LocalCfgPtr->Sata.SataPortPower.SataPortReg); + FchSataCombineControlDataByte (PortRegByte); + PortRegWord = &(LocalCfgPtr->Sata.SataPortMd.SataPortMode); + FchSataCombineControlDataWord (PortRegWord); + PortRegByte = &(LocalCfgPtr->Sata.SataHotRemovalEnhPort.SataPortReg); + FchSataCombineControlDataByte (PortRegByte); + + // + // Set Sata PCI Configuration Space Write enable + // + SataEnableWriteAccess (StdHeader); + + // + // Enables the SATA watchdog timer register prior to the SATA BIOS post + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x44), AccessWidth8, 0xff, BIT0, StdHeader); + + // + // SATA PCI Watchdog timer setting + // Set timer out to 0x20 to fix IDE to SATA Bridge dropping drive issue. + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x44 + 2), AccessWidth8, 0, 0x20, StdHeader); + + // + // BIT4:disable fast boot + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x040 ), AccessWidth8, 0xff, BIT4, StdHeader); + + // + // Enable IDE DMA read enhancement + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x48 + 3), AccessWidth8, 0xff, BIT7, StdHeader); + + // + // Unused SATA Ports Disabled + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x040 + 2), AccessWidth8, 0, LocalCfgPtr->Sata.SataPortPower.SataPortReg, StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x48), AccessWidth32, (UINT32) (~ (0x01 << 11)), (UINT32) (0x01 << 11), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x084 ), AccessWidth32, (UINT32) (~ (0x01 << 31)), (UINT32) (0x00 << 31), StdHeader); + //RPR 9.22 Design Enhancement + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x1 << 18)), (UINT32) (0x1 << 18), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x1 << 20)), (UINT32) (0x1 << 20), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x1 << 21)), (UINT32) (0x1 << 21), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x7 << 26)), (UINT32) (0x7 << 26), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x3 << 30)), (UINT32) (0x3 << 30), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x48), AccessWidth32, (UINT32) (~ (0x1 << 30)), (UINT32) (0x1 << 30), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x1 << 29)), (UINT32) (0x1 << 29), StdHeader); +} + +/** + * FchSataCombineControlDataByte - Combine port control options + * to one control byte. + * + * + * @param[in] *ControlReg - Data pointer for control byte. + * + */ +VOID +FchSataCombineControlDataByte ( + IN UINT8 *ControlReg + ) +{ + UINT8 Index; + UINT8 PortControl; + + *ControlReg = 0; + for ( Index = 0; Index < 8; Index++ ) { + PortControl = *( ControlReg + 1 + Index ); + *ControlReg |= PortControl << Index; + } +} +/** + * FchSataCombineControlDataWord - Combine port control options + * to one control Word. + * + * + * @param[in] *ControlReg - Data pointer for control byte. + * + */ +VOID +FchSataCombineControlDataWord ( + IN UINT16 *ControlReg + ) +{ + UINT8 Index; + UINT8 PortControl; + + *ControlReg = 0; + for ( Index = 0; Index < 8; Index++ ) { + PortControl = *( (UINT8 *)ControlReg + 2 + Index ); + *ControlReg |= PortControl << (Index * 2); + } +} + + +VOID +FchProgramSataPhy ( + IN AMD_CONFIG_PARAMS *StdHeader + ) +{ + SATA_PHY_SETTING *PhyTablePtr; + UINT16 Index; + + PhyTablePtr = &SataPhyTable[0]; + + for (Index = 0; Index < (sizeof (SataPhyTable) / sizeof (SATA_PHY_SETTING)); Index++) { + RwPci ((SATA_BUS_DEV_FUN << 16) + 0x80, AccessWidth16, 0x00, PhyTablePtr->PhyCoreControlWord, StdHeader); + RwPci ((SATA_BUS_DEV_FUN << 16) + 0x98, AccessWidth32, 0x00, PhyTablePtr->PhyFineTuneDword, StdHeader); + ++PhyTablePtr; + } + + + RwPci ((SATA_BUS_DEV_FUN << 16) + 0x80, AccessWidth16, 0x00, 0x110, StdHeader); + RwPci ((SATA_BUS_DEV_FUN << 16) + 0x09C , AccessWidth32, (UINT32) (~(0x7 << 4)), (UINT32) (0x2 << 4), StdHeader); + RwPci ((SATA_BUS_DEV_FUN << 16) + 0x80, AccessWidth16, 0x00, 0x10, StdHeader); +} + +/** + * FchInitEnvSataRaidProgram - Configuration SATA Raid + * controller + * + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchInitEnvSataRaidProgram ( + IN VOID *FchDataPtr + ) +{ + UINT32 SataSSIDValue; + UINT32 DeviceId; + UINT8 EfuseValue; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + // + // Class code + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x08), AccessWidth32, 0, 0x01040040, StdHeader); + // + // Device ID + // + SataSSIDValue = 0; + if (LocalCfgPtr->Sata.SataRaid5Ssid != 0 ) { + SataSSIDValue = LocalCfgPtr->Sata.SataRaid5Ssid; + } + + DeviceId = FCH_SATA_RAID5_DID; + EfuseValue = SATA_EFUSE_LOCATION; + GetEfuseStatus (&EfuseValue, StdHeader); + + if (( EfuseValue & SATA_EFUSE_BIT ) || ( LocalCfgPtr->Sata.SataForceRaid == 1 )) { + DeviceId = FCH_SATA_RAID_DID; + if (LocalCfgPtr->Sata.SataRaidSsid != 0 ) { + SataSSIDValue = LocalCfgPtr->Sata.SataRaidSsid; + } + } + + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x02), AccessWidth16, 0, DeviceId, StdHeader); + // + // SSID + // + if (SataSSIDValue != 0 ) { + RwPci ((SATA_BUS_DEV_FUN << 16) + 0x2C, AccessWidth32, 0, SataSSIDValue, StdHeader); + } +} + diff --git a/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataResetService.c b/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataResetService.c new file mode 100644 index 0000000000..be32489094 --- /dev/null +++ b/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataResetService.c @@ -0,0 +1,166 @@ +/* $NoKeywords:$ */ +/** + * @file + * + * Config Fch Sata controller + * + * Init Sata Controller features (PEI phase). + * + * @xrefitem bom "File Content Label" "Release Content" + * @e project: AGESA + * @e sub-project: FCH + * @e \$Revision: 63425 $ @e \$Date: 2011-12-22 11:24:10 -0600 (Thu, 22 Dec 2011) $ + * + */ +/* +***************************************************************************** +* +* Copyright 2008 - 2012 ADVANCED MICRO DEVICES, INC. All Rights Reserved. +* +* AMD is granting you permission to use this software (the Materials) +* pursuant to the terms and conditions of your Software License Agreement +* with AMD. This header does *NOT* give you permission to use the Materials +* or any rights under AMD's intellectual property. Your use of any portion +* of these Materials shall constitute your acceptance of those terms and +* conditions. If you do not agree to the terms and conditions of the Software +* License Agreement, please do not use any portion of these Materials. +* +* CONFIDENTIALITY: The Materials and all other information, identified as +* confidential and provided to you by AMD shall be kept confidential in +* accordance with the terms and conditions of the Software License Agreement. +* +* LIMITATION OF LIABILITY: THE MATERIALS AND ANY OTHER RELATED INFORMATION +* PROVIDED TO YOU BY AMD ARE PROVIDED "AS IS" WITHOUT ANY EXPRESS OR IMPLIED +* WARRANTY OF ANY KIND, INCLUDING BUT NOT LIMITED TO WARRANTIES OF +* MERCHANTABILITY, NONINFRINGEMENT, TITLE, FITNESS FOR ANY PARTICULAR PURPOSE, +* OR WARRANTIES ARISING FROM CONDUCT, COURSE OF DEALING, OR USAGE OF TRADE. +* IN NO EVENT SHALL AMD OR ITS LICENSORS BE LIABLE FOR ANY DAMAGES WHATSOEVER +* (INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF PROFITS, BUSINESS +* INTERRUPTION, OR LOSS OF INFORMATION) ARISING OUT OF AMD'S NEGLIGENCE, +* GROSS NEGLIGENCE, THE USE OF OR INABILITY TO USE THE MATERIALS OR ANY OTHER +* RELATED INFORMATION PROVIDED TO YOU BY AMD, EVEN IF AMD HAS BEEN ADVISED OF +* THE POSSIBILITY OF SUCH DAMAGES. BECAUSE SOME JURISDICTIONS PROHIBIT THE +* EXCLUSION OR LIMITATION OF LIABILITY FOR CONSEQUENTIAL OR INCIDENTAL DAMAGES, +* THE ABOVE LIMITATION MAY NOT APPLY TO YOU. +* +* AMD does not assume any responsibility for any errors which may appear in +* the Materials or any other related information provided to you by AMD, or +* result from use of the Materials or any related information. +* +* You agree that you will not reverse engineer or decompile the Materials. +* +* NO SUPPORT OBLIGATION: AMD is not obligated to furnish, support, or make any +* further information, software, technical information, know-how, or show-how +* available to you. Additionally, AMD retains the right to modify the +* Materials at any time, without notice, and is not obligated to provide such +* modified Materials to you. +* +* U.S. GOVERNMENT RESTRICTED RIGHTS: The Materials are provided with +* "RESTRICTED RIGHTS." Use, duplication, or disclosure by the Government is +* subject to the restrictions as set forth in FAR 52.227-14 and +* DFAR252.227-7013, et seq., or its successor. Use of the Materials by the +* Government constitutes acknowledgement of AMD's proprietary rights in them. +* +* EXPORT ASSURANCE: You agree and certify that neither the Materials, nor any +* direct product thereof will be exported directly or indirectly, into any +* country prohibited by the United States Export Administration Act and the +* regulations thereunder, without the required authorization from the U.S. +* government nor will be used for any purpose prohibited by the same. +**************************************************************************** +*/ +#include "FchPlatform.h" +#include "Filecode.h" +#define FILECODE PROC_FCH_SATA_FAMILY_HUDSON2_HUDSON2SATARESETSERVICE_FILECODE + +/** + * FchInitResetSataProgram - Config Sata controller during + * Power-On + * + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchInitResetSataProgram ( + IN VOID *FchDataPtr + ) +{ + UINT8 SataPortNum; + UINT8 PortStatusByte; + UINT8 EfuseByte; + UINT8 FchSataMode; + UINT8 FchSataInternal100Spread; + FCH_RESET_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_RESET_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + // + //FchSataMode = LocalCfgPtr->Sata.SATA_MODE.SataMode.SataModeReg; + //New structure need calculate Sata Register value + // + FchSataMode = 0; + if ( LocalCfgPtr->FchReset.SataEnable ) { + FchSataMode |= 0x01; + } + if ( LocalCfgPtr->Sata6AhciCap ) { + FchSataMode |= 0x02; + } + if ( LocalCfgPtr->SataSetMaxGen2 ) { + FchSataMode |= 0x04; + } + if ( LocalCfgPtr->FchReset.IdeEnable ) { + FchSataMode |= 0x08; + } + + FchSataMode |= (( LocalCfgPtr->SataClkMode ) << 4 ) ; + LocalCfgPtr->SataModeReg = FchSataMode; ///Save Back to Structure + + FchSataInternal100Spread = ( UINT8 ) LocalCfgPtr->SataInternal100Spread; + SataPortNum = 0; + + // + // Sata Workaround + // + for ( SataPortNum = 0; SataPortNum < 0x08; SataPortNum++ ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x040 + 2), AccessWidth8, 0xFF, 1 << SataPortNum, StdHeader); + FchStall (2, StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x040 + 2), AccessWidth8, (0xFF ^ (1 << SataPortNum)) , 0x00, StdHeader); + FchStall (2, StdHeader); + } + + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x084 + 3), AccessWidth8, (UINT32)~BIT2, 0, StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x0A0 ), AccessWidth8, (UINT32)~(BIT2 + BIT3 + BIT4 + BIT5 + BIT6), BIT2 + BIT3 + BIT4 + BIT5, StdHeader); + + // + // Sata Setting for clock mode only + // + RwMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth8, 0, FchSataMode); + + if ( FchSataInternal100Spread ) { + RwMem (ACPI_MMIO_BASE + MISC_BASE + 0x1E, AccessWidth8, 0xFF, BIT4); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x084 ), AccessWidth32, 0xFFFFFFFB, 0x00, StdHeader); + } else { + RwMem (ACPI_MMIO_BASE + MISC_BASE + 0x1E, AccessWidth8, (UINT32)~BIT4, 0x00); + } + + EfuseByte = SATA_FIS_BASE_EFUSE_LOC; + GetEfuseStatus (&EfuseByte, StdHeader); + + if (EfuseByte & BIT0) { + RwMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth8, 0xFB, 0x04); + } + + ReadMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth8, &PortStatusByte); + if ( ((PortStatusByte & 0xF0) == 0x10) ) { + RwMem (ACPI_MMIO_BASE + MISC_BASE + FCH_PMIOA_REG08, AccessWidth8, 0, BIT5); + } + + if ( FchSataInternal100Spread ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x084 ), AccessWidth32, 0xFFFFFFFF, 0x04, StdHeader); + } +} + + diff --git a/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataService.c b/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataService.c new file mode 100644 index 0000000000..d3eb26308d --- /dev/null +++ b/src/vendorcode/amd/agesa/f15tn/Proc/Fch/Sata/Family/Hudson2/Hudson2SataService.c @@ -0,0 +1,711 @@ +/* $NoKeywords:$ */ +/** + * @file + * + * Graphics Controller family specific service procedure + * + * + * + * @xrefitem bom "File Content Label" "Release Content" + * @e project: AGESA + * @e sub-project: FCH + * @e \$Revision: 63425 $ @e \$Date: 2011-12-22 11:24:10 -0600 (Thu, 22 Dec 2011) $ + * + */ + +/* +***************************************************************************** +* +* Copyright 2008 - 2012 ADVANCED MICRO DEVICES, INC. All Rights Reserved. +* +* AMD is granting you permission to use this software (the Materials) +* pursuant to the terms and conditions of your Software License Agreement +* with AMD. This header does *NOT* give you permission to use the Materials +* or any rights under AMD's intellectual property. Your use of any portion +* of these Materials shall constitute your acceptance of those terms and +* conditions. If you do not agree to the terms and conditions of the Software +* License Agreement, please do not use any portion of these Materials. +* +* CONFIDENTIALITY: The Materials and all other information, identified as +* confidential and provided to you by AMD shall be kept confidential in +* accordance with the terms and conditions of the Software License Agreement. +* +* LIMITATION OF LIABILITY: THE MATERIALS AND ANY OTHER RELATED INFORMATION +* PROVIDED TO YOU BY AMD ARE PROVIDED "AS IS" WITHOUT ANY EXPRESS OR IMPLIED +* WARRANTY OF ANY KIND, INCLUDING BUT NOT LIMITED TO WARRANTIES OF +* MERCHANTABILITY, NONINFRINGEMENT, TITLE, FITNESS FOR ANY PARTICULAR PURPOSE, +* OR WARRANTIES ARISING FROM CONDUCT, COURSE OF DEALING, OR USAGE OF TRADE. +* IN NO EVENT SHALL AMD OR ITS LICENSORS BE LIABLE FOR ANY DAMAGES WHATSOEVER +* (INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF PROFITS, BUSINESS +* INTERRUPTION, OR LOSS OF INFORMATION) ARISING OUT OF AMD'S NEGLIGENCE, +* GROSS NEGLIGENCE, THE USE OF OR INABILITY TO USE THE MATERIALS OR ANY OTHER +* RELATED INFORMATION PROVIDED TO YOU BY AMD, EVEN IF AMD HAS BEEN ADVISED OF +* THE POSSIBILITY OF SUCH DAMAGES. BECAUSE SOME JURISDICTIONS PROHIBIT THE +* EXCLUSION OR LIMITATION OF LIABILITY FOR CONSEQUENTIAL OR INCIDENTAL DAMAGES, +* THE ABOVE LIMITATION MAY NOT APPLY TO YOU. +* +* AMD does not assume any responsibility for any errors which may appear in +* the Materials or any other related information provided to you by AMD, or +* result from use of the Materials or any related information. +* +* You agree that you will not reverse engineer or decompile the Materials. +* +* NO SUPPORT OBLIGATION: AMD is not obligated to furnish, support, or make any +* further information, software, technical information, know-how, or show-how +* available to you. Additionally, AMD retains the right to modify the +* Materials at any time, without notice, and is not obligated to provide such +* modified Materials to you. +* +* U.S. GOVERNMENT RESTRICTED RIGHTS: The Materials are provided with +* "RESTRICTED RIGHTS." Use, duplication, or disclosure by the Government is +* subject to the restrictions as set forth in FAR 52.227-14 and +* DFAR252.227-7013, et seq., or its successor. Use of the Materials by the +* Government constitutes acknowledgement of AMD's proprietary rights in them. +* +* EXPORT ASSURANCE: You agree and certify that neither the Materials, nor any +* direct product thereof will be exported directly or indirectly, into any +* country prohibited by the United States Export Administration Act and the +* regulations thereunder, without the required authorization from the U.S. +* government nor will be used for any purpose prohibited by the same. +* *************************************************************************** +*/ + + +/*---------------------------------------------------------------------------------------- + * M O D U L E S U S E D + *---------------------------------------------------------------------------------------- + */ +#include "FchPlatform.h" +#include "Filecode.h" +#define FILECODE PROC_FCH_SATA_FAMILY_HUDSON2_HUDSON2SATASERVICE_FILECODE + +/*---------------------------------------------------------------------------------------- + * D E F I N I T I O N S A N D M A C R O S + *---------------------------------------------------------------------------------------- + */ +UINT8 NumOfSataPorts = 8; + +/** + * FchSataGpioInitial - Sata GPIO function Procedure + * + * - Private function + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchSataGpioInitial ( + IN VOID *FchDataPtr + ) +{ + UINT32 Bar5; + UINT32 FchSataBarRegDword; + UINT32 EMb; + UINT32 SataGpioVariableDword; + UINT8 FchSataSgpio0; + FCH_DATA_BLOCK *LocalCfgPtr; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + + Bar5 = 0; + EMb = 0; + FchSataSgpio0 = (UINT8) LocalCfgPtr->Sata.SataSgpio0; + + SataBar5setting (LocalCfgPtr, &Bar5); + ReadMem (Bar5 + 0x1C , AccessWidth32, &FchSataBarRegDword); + EMb = (Bar5 + (( FchSataBarRegDword & 0xFFFF0000) >> 14)); + + if ( EMb ) { + SataGpioVariableDword = 0x03040C00; + WriteMem ( Bar5 + EMb, AccessWidth32, &SataGpioVariableDword); + SataGpioVariableDword = 0x00C08240; + WriteMem ( Bar5 + EMb + 4, AccessWidth32, &SataGpioVariableDword); + SataGpioVariableDword = 0x00000001; + WriteMem ( Bar5 + EMb + 8, AccessWidth32, &SataGpioVariableDword); + + if ( FchSataSgpio0 ) { + SataGpioVariableDword = 0x00000060; + } else { + SataGpioVariableDword = 0x00000061; + } + + WriteMem ( Bar5 + EMb + 0x0C, AccessWidth32, &SataGpioVariableDword); + RwMem ((Bar5 + 0x20), AccessWidth16, (UINT32)~(BIT8), BIT8); + + do { + ReadMem (Bar5 + 0x20 , AccessWidth32, &FchSataBarRegDword); + FchSataBarRegDword = FchSataBarRegDword & BIT8; + } while ( FchSataBarRegDword != 0 ); + + SataGpioVariableDword = 0x03040F00; + WriteMem ( Bar5 + EMb, AccessWidth32, &SataGpioVariableDword); + SataGpioVariableDword = 0x00008240; + WriteMem ( Bar5 + EMb + 4, AccessWidth32, &SataGpioVariableDword); + SataGpioVariableDword = 0x00000002; + WriteMem ( Bar5 + EMb + 8, AccessWidth32, &SataGpioVariableDword); + SataGpioVariableDword = 0x00800000; + WriteMem ( Bar5 + EMb + 0x0C, AccessWidth32, &SataGpioVariableDword); + SataGpioVariableDword = 0x0F003700; + WriteMem ( Bar5 + EMb + 0x0C, AccessWidth32, &SataGpioVariableDword); + RwMem ((Bar5 + 0x20), AccessWidth16, (UINT32)~(BIT8), BIT8); + + do { + ReadMem (Bar5 + 0x20 , AccessWidth32, &FchSataBarRegDword); + FchSataBarRegDword = FchSataBarRegDword & BIT8; + } while ( FchSataBarRegDword != 0 ); + } +} + +/** + * FchInitMidProgramSataRegs - Sata Pci Configuration Space + * register setting + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchInitMidProgramSataRegs ( + IN VOID *FchDataPtr + ) +{ + UINT8 FchSataMsiCapability; + UINT8 FchSataTargetSupport8Device; + UINT8 FchSataDisableGenericMode; + UINT8 FchSataSgpio0; + UINT8 FchSataSgpio1; + UINT8 FchSataPhyPllShutDown; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + FchSataMsiCapability = (UINT8) LocalCfgPtr->Sata.SataMsiCapability; + FchSataTargetSupport8Device = (UINT8) LocalCfgPtr->Sata.SataTargetSupport8Device; + FchSataDisableGenericMode = (UINT8) LocalCfgPtr->Sata.SataDisableGenericMode; + FchSataSgpio0 = (UINT8) LocalCfgPtr->Sata.SataSgpio0; + FchSataSgpio1 = (UINT8) LocalCfgPtr->Sata.SataSgpio1; + FchSataPhyPllShutDown = (UINT8) LocalCfgPtr->Sata.SataPhyPllShutDown; + + if ((LocalCfgPtr->Sata.SataClass == SataNativeIde) || (LocalCfgPtr->Sata.SataClass == SataLegacyIde)) { + FchSataMsiCapability = 0; + } + // + // Enabled SATA MSI capability + // SATA MSI and D3 Power State Capability + // + if ( FchSataMsiCapability ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x34), AccessWidth8, 0, 0x50, StdHeader); + } else { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x34), AccessWidth8, 0, 0x70, StdHeader); + } + + // + // Disable SATA FLR Capability + // + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x70), AccessWidth16, 0x00FF, 0x00, StdHeader); + + // + // Sata Target Support 8 devices function + // + if ( FchSataTargetSupport8Device ) { + RwMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth16, (UINT32)~BIT12, BIT12); + } else { + RwMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth16, (UINT32)~BIT12, 0x00); + } + + // + // Sata Generic Mode setting + // + if ( FchSataDisableGenericMode ) { + RwMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth16, (UINT32)~BIT13, BIT13); + } else { + RwMem (ACPI_MMIO_BASE + PMIO_BASE + 0xDA , AccessWidth16, (UINT32)~BIT13, 0x00); + } + + // + // Sata GPIO Initial + // + if ( FchSataSgpio0 ) { + FchSataGpioInitial ( LocalCfgPtr ); + } + + if ( FchSataSgpio1 ) { + FchSataGpioInitial ( LocalCfgPtr ); + } + + // + // Sata Phy Pll Shutdown setting + // + if ( FchSataPhyPllShutDown ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x87), AccessWidth8, (UINT32)~(BIT6), BIT6, StdHeader); + } else { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x87), AccessWidth8, (UINT32)~(BIT6), 0x00, StdHeader); + } + + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x04C ), AccessWidth32, (UINT32) (~ (0x3f << 26)), (UINT32) (0x3f << 26), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x48), AccessWidth32, (UINT32) (~ (0x01 << 11)), (UINT32) (0x01 << 11), StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x084 ), AccessWidth32, (UINT32) (~ (0x01 << 31)), (UINT32) (0x00 << 31), StdHeader); +} + + +/** + * FchInitLateProgramSataRegs - Sata Pci Configuration Space + * register setting + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchInitLateProgramSataRegs ( + IN VOID *FchDataPtr + ) +{ + UINT8 PortNumByte; + UINT32 Bar5; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + SataBar5setting (LocalCfgPtr, &Bar5); + // + //Clear error status + // + RwMem ((Bar5 + FCH_SATA_BAR5_REG130), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + FCH_SATA_BAR5_REG1B0), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + FCH_SATA_BAR5_REG230), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + FCH_SATA_BAR5_REG2B0), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + FCH_SATA_BAR5_REG330), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + FCH_SATA_BAR5_REG3B0), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + 0x0430 ), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + RwMem ((Bar5 + 0x04B0 ), AccessWidth32, 0xFFFFFFFF, 0xFFFFFFFF); + + for ( PortNumByte = 0; PortNumByte < MAX_SATA_PORTS; PortNumByte++ ) { + RwMem ((Bar5 + 0x110 + (PortNumByte * 0x80)), AccessWidth32, 0xFFFFFFFF, 0x00); + } +} + +/** + * sataBar5RegSet - Sata Bar5 register setting + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +SataBar5RegSet ( + IN VOID *FchDataPtr + ) +{ + UINT32 AndMaskDword; + UINT32 OrMaskDword; + UINT32 Bar5; + UINT8 EfuseByte; + UINT8 FchSataAggrLinkPmCap; + UINT8 FchSataPortMultCap; + UINT8 FchSataPscCap; + UINT8 FchSataSscCap; + UINT8 FchSataFisBasedSwitching; + UINT8 FchSataCccSupport; + UINT8 FchSataAhciEnclosureManagement; + FCH_DATA_BLOCK *LocalCfgPtr; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + + FchSataAggrLinkPmCap = (UINT8) LocalCfgPtr->Sata.SataAggrLinkPmCap; + FchSataPortMultCap = (UINT8) LocalCfgPtr->Sata.SataPortMultCap; + FchSataPscCap = (UINT8) LocalCfgPtr->Sata.SataPscCap; + FchSataSscCap = (UINT8) LocalCfgPtr->Sata.SataSscCap; + FchSataFisBasedSwitching = (UINT8) LocalCfgPtr->Sata.SataFisBasedSwitching; + FchSataCccSupport = (UINT8) LocalCfgPtr->Sata.SataCccSupport; + FchSataAhciEnclosureManagement = (UINT8) LocalCfgPtr->Sata.SataAhciEnclosureManagement; + + AndMaskDword = 0; + OrMaskDword = 0; + Bar5 = 0; + + SataBar5setting (LocalCfgPtr, &Bar5); + EfuseByte = SATA_FIS_BASE_EFUSE_LOC; + GetEfuseStatus (&EfuseByte, LocalCfgPtr->StdHeader); + + if ( !FchSataPortMultCap ) { + AndMaskDword |= BIT12; + } + + if ( FchSataAggrLinkPmCap ) { + OrMaskDword |= BIT11; + } else { + AndMaskDword |= BIT11; + } + + if ( FchSataPscCap ) { + OrMaskDword |= BIT1; + } else { + AndMaskDword |= BIT1; + } + + if ( FchSataSscCap ) { + OrMaskDword |= BIT26; + } else { + AndMaskDword |= BIT26; + } + + if ( FchSataFisBasedSwitching ) { + if (EfuseByte & BIT1) { + AndMaskDword |= BIT10; + } else { + OrMaskDword |= BIT10; + } + } else { + AndMaskDword |= BIT10; + } + + // + // Disabling CCC (Command Completion Coalescing) support. + // + if ( FchSataCccSupport ) { + OrMaskDword |= BIT19; + } else { + AndMaskDword |= BIT19; + } + + if ( FchSataAhciEnclosureManagement ) { + OrMaskDword |= BIT27; + } else { + AndMaskDword |= BIT27; + } + + RwMem ((Bar5 + 0xFC), AccessWidth32, ~AndMaskDword, OrMaskDword); + + // + // SATA ESP port setting + // These config bits are set for SATA driver to identify which ports are external SATA ports and need to + // support hotplug. If a port is set as an external SATA port and need to support hotplug, then driver will + // not enable power management (HIPM & DIPM) for these ports. + // + if ( LocalCfgPtr->Sata.SataEspPort.SataPortReg != 0 ) { + RwMem ((Bar5 + 0xF8), AccessWidth32, ~(LocalCfgPtr->Sata.SataEspPort.SataPortReg), 0); + RwMem ((Bar5 + 0xF8), AccessWidth32, 0xFF00FF00, (LocalCfgPtr->Sata.SataEspPort.SataPortReg << 16)); + // + // External SATA Port Indication Registers + // If any of the ports was programmed as an external port, HCAP.SXS should also be set + // + RwMem ((Bar5 + 0xFC), AccessWidth32, (UINT32)~(BIT20), BIT20); + } else { + // + // External SATA Port Indication Registers + // If any of the ports was programmed as an external port, HCAP.SXS should also be set (Clear for no ESP port) + // + RwMem ((Bar5 + 0xF8), AccessWidth32, 0xFF00FF00, 0x00); + RwMem ((Bar5 + 0xFC), AccessWidth32, (UINT32)~(BIT20), 0x00); + } + + if ( FchSataFisBasedSwitching ) { + if (EfuseByte & BIT1) { + RwMem ((Bar5 + 0xF8), AccessWidth32, 0x00FFFFFF, 0x00); + } else { + RwMem ((Bar5 + 0xF8), AccessWidth32, 0x00FFFFFF, 0xFF000000); + } + } else { + RwMem ((Bar5 + 0xF8), AccessWidth32, 0x00FFFFFF, 0x00); + } + + if ( LocalCfgPtr->Sata.BiosOsHandOff == 1 ) { + RwMem ((Bar5 + 0x24), AccessWidth8, (UINT32)~BIT0, BIT0); + } else { + RwMem ((Bar5 + 0x24), AccessWidth8, (UINT32)~BIT0, 0x00); + } +} + +/** + * FchSataSetDeviceNumMsi - Program Sata controller support + * device number cap & MSI cap + * + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchSataSetDeviceNumMsi ( + IN VOID *FchDataPtr + ) +{ + UINT32 Bar5; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + Bar5 = 0; + SataBar5setting (LocalCfgPtr, &Bar5); + // + // RAID or AHCI + // + if (LocalCfgPtr->Sata.SataMode.IdeEnable == DISABLED) { + // + // IDE2 Controller is enabled + // + if (LocalCfgPtr->Sata.SataMode.Sata6AhciCap == ENABLED) { + // + // 6 AHCI mode + // + RwMem ((Bar5 + 0x0C), AccessWidth8, 0x00, 0x3F); + RwMem ((Bar5 + 0x00), AccessWidth8, (UINT32)~(BIT2 + BIT1 + BIT0), BIT2 + BIT0); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x50 + 2), AccessWidth8, (UINT32)~(BIT3 + BIT2 + BIT1), BIT2 + BIT1, StdHeader); + RwMem ((Bar5 + 0xFC), AccessWidth8, 0x07, 0x30); + } else { + RwMem ((Bar5 + 0x0C), AccessWidth8, 0x00, 0x0F); + if ( LocalCfgPtr->Sata.SataCccSupport ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x50 + 2), AccessWidth8, (UINT32)~(BIT3 + BIT2 + BIT1), BIT2 + BIT1, StdHeader); + RwMem ((Bar5 + 0xFC), AccessWidth8, 0x07, 0x20); + } else { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x50 + 2), AccessWidth8, (UINT32)~(BIT3 + BIT2 + BIT1), BIT2, StdHeader); + } + } + } else { + // + // IDE2 Controller is disabled + // + RwMem ((Bar5 + 0x00), AccessWidth8, (UINT32)~(BIT2 + BIT1 + BIT0), BIT2 + BIT1 + BIT0); + RwMem ((Bar5 + 0x0C), AccessWidth8, 0x00, 0xFF); + if ( LocalCfgPtr->Sata.SataCccSupport ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x50 + 2), AccessWidth8, (UINT32)~(BIT3 + BIT2 + BIT1), BIT3, StdHeader); + RwMem ((Bar5 + 0xFC), AccessWidth8, 0x07, 0x40); + } else { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x50 + 2), AccessWidth8, (UINT32)~(BIT3 + BIT2 + BIT1), BIT2 + BIT1, StdHeader); + } + } +} + + +/** + * FchSataDriveDetection - Sata drive detection + * + * - Sata Ide & Sata Ide to Ahci only + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * @param[in] *Bar5Ptr Sata BAR5 base address. + * + */ +VOID +FchSataDriveDetection ( + IN VOID *FchDataPtr, + IN UINT32 *Bar5Ptr + ) +{ + UINT32 SataBarInfo; + UINT8 PortNumByte; + UINT8 SataPortType; + UINT16 IoBaseWord; + UINT32 SataLoopVarDWord; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + for ( PortNumByte = 0; PortNumByte < 4; PortNumByte++ ) { + + ReadMem (*Bar5Ptr + FCH_SATA_BAR5_REG128 + PortNumByte * 0x80, AccessWidth32, &SataBarInfo); + + if ( ( SataBarInfo & 0x0F ) == 0x03 ) { + if ( PortNumByte & BIT0 ) { + // + //this port belongs to secondary channel + // + ReadPci (((UINT32) (SATA_BUS_DEV_FUN << 16) + 0x18), AccessWidth16, &IoBaseWord, StdHeader); + } else { + // + //this port belongs to primary channel + // + ReadPci (((UINT32) (SATA_BUS_DEV_FUN << 16) + 0x10), AccessWidth16, &IoBaseWord, StdHeader); + } + + // + //if legacy ide mode, then the bar registers don't contain the correct values. So we need to hardcode them + // + if ( LocalCfgPtr->Sata.SataClass == SataLegacyIde ) { + IoBaseWord = ( (0x170) | ((UINT16) ( (~((UINT8) (PortNumByte & BIT0) << 7)) & 0x80 )) ); + } + + if ( PortNumByte & BIT1 ) { + // + //this port is slave + // + SataPortType = 0xB0; + } else { + // + //this port is master + // + SataPortType = 0xA0; + } + + IoBaseWord &= 0xFFF8; + LibAmdIoWrite (AccessWidth8, IoBaseWord + 6, &SataPortType, StdHeader); + + // + //Wait in loop for 30s for the drive to become ready + // + for ( SataLoopVarDWord = 0; SataLoopVarDWord < 300000; SataLoopVarDWord++ ) { + LibAmdIoRead (AccessWidth8, IoBaseWord + 7, &SataPortType, StdHeader); + if ( (SataPortType & 0x88) == 0 ) { + break; + } + FchStall (100, StdHeader); + } + } + } +} + +/** + * FchShutdownUnconnectedSataPortClock - Shutdown unconnected + * Sata port clock + * + * - Sata Ide & Sata Ide to Ahci only + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * @param[in] Bar5 Sata BAR5 base address. + * + */ +VOID +FchShutdownUnconnectedSataPortClock ( + IN VOID *FchDataPtr, + IN UINT32 Bar5 + ) +{ + UINT8 PortNumByte; + UINT8 PortSataStatusByte; + UINT8 NumOfPorts; + UINT8 FchSataClkAutoOff; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + FchSataClkAutoOff = (UINT8) LocalCfgPtr->Sata.SataClkAutoOff; + + NumOfPorts = 0; + // + // Enable SATA auto clock control by default + // + for ( PortNumByte = 0; PortNumByte < MAX_SATA_PORTS; PortNumByte++ ) { + ReadMem (Bar5 + FCH_SATA_BAR5_REG128 + (PortNumByte * 0x80), AccessWidth8, &PortSataStatusByte); + // + // Shutdown the clock for the port and do the necessary port reporting changes. + // Error port status should be 1 not 3 + // + if ( ((PortSataStatusByte & 0x0F) != 0x03) && (! ((LocalCfgPtr->Sata.SataEspPort.SataPortReg) & (1 << PortNumByte))) ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x040 + 2), AccessWidth8, 0xFF, (1 << PortNumByte), StdHeader); + RwMem (Bar5 + 0x0C, AccessWidth8, ~(1 << PortNumByte), 00); + } + } ///end of for (PortNumByte=0;PortNumByte<6;PortNumByte++) + + ReadMem (Bar5 + 0x0C, AccessWidth8, &PortSataStatusByte); + + // + //if all ports are in disabled state, report at least one port + // + if ( (PortSataStatusByte & 0xFF) == 0) { + RwMem (Bar5 + 0x0C, AccessWidth8, (UINT32) ~(0xFF), 01); + } + + ReadMem (Bar5 + 0x0C, AccessWidth8, &PortSataStatusByte); + + for (PortNumByte = 0; PortNumByte < MAX_SATA_PORTS; PortNumByte ++) { + if (PortSataStatusByte & (1 << PortNumByte)) { + NumOfPorts++; + } + } + + if ( NumOfPorts == 0) { + NumOfPorts = 0x01; + } + + RwMem (Bar5 + 0x00, AccessWidth8, 0xE0, NumOfPorts - 1); +} + +/** + * FchSataSetPortGenMode - Set Sata port mode (each) for + * Gen1/Gen2/Gen3 + * + * + * @param[in] FchDataPtr Fch configuration structure pointer. + * + */ +VOID +FchSataSetPortGenMode ( + IN VOID *FchDataPtr + ) +{ + UINT32 Bar5; + UINT8 PortNumByte; + UINT8 PortModeByte; + UINT16 SataPortMode; + BOOLEAN FchSataHotRemovalEnh; + FCH_DATA_BLOCK *LocalCfgPtr; + AMD_CONFIG_PARAMS *StdHeader; + + LocalCfgPtr = (FCH_DATA_BLOCK *) FchDataPtr; + StdHeader = LocalCfgPtr->StdHeader; + + FchSataHotRemovalEnh = LocalCfgPtr->Sata.SataHotRemovalEnh; + + SataBar5setting (LocalCfgPtr, &Bar5); + SataPortMode = (UINT16)LocalCfgPtr->Sata.SataPortMd.SataPortMode; + PortNumByte = 0; + + while ( PortNumByte < 8 ) { + PortModeByte = (UINT8) (SataPortMode & 3); + if ( (PortModeByte == BIT0) || (PortModeByte == BIT1) ) { + if ( PortModeByte == BIT0 ) { + // + // set GEN 1 + // + RwMem (Bar5 + FCH_SATA_BAR5_REG12C + PortNumByte * 0x80, AccessWidth8, 0x0F, 0x10); + } + + if ( PortModeByte == BIT1 ) { + // + // set GEN2 (default is GEN3) + // + RwMem (Bar5 + FCH_SATA_BAR5_REG12C + PortNumByte * 0x80, AccessWidth8, 0x0F, 0x20); + } + + RwMem (Bar5 + FCH_SATA_BAR5_REG12C + PortNumByte * 0x80, AccessWidth8, 0xFF, 0x01); + } + + SataPortMode >>= 2; + PortNumByte ++; + } + + FchStall (1000, StdHeader); + SataPortMode = (UINT16)LocalCfgPtr->Sata.SataPortMd.SataPortMode; + PortNumByte = 0; + + while ( PortNumByte < 8 ) { + PortModeByte = (UINT8) (SataPortMode & 3); + + if ( (PortModeByte == BIT0) || (PortModeByte == BIT1) ) { + RwMem (Bar5 + FCH_SATA_BAR5_REG12C + PortNumByte * 0x80, AccessWidth8, 0xFE, 0x00); + } + + PortNumByte ++; + SataPortMode >>= 2; + } + + // + // Sata Hot Removal Enhance setting + // + if ( FchSataHotRemovalEnh ) { + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x80), AccessWidth16, (UINT32)~BIT8, BIT8, StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x0A8 ), AccessWidth16, (UINT32)~BIT0, BIT0, StdHeader); + RwPci (((SATA_BUS_DEV_FUN << 16) + 0x80), AccessWidth16, (UINT32)~BIT8, 0, StdHeader); + } +} + |