alder_lake_bios/Lcfc/LfcPkg/Library/BaseLfcLib/BaseLfcLib.c

204 lines
4.8 KiB
C

/*****************************************************************************
*
*
* Copyright (c) 2012 - 2015, Hefei LCFC Information Technology Co.Ltd.
* And/or its affiliates. All rights reserved.
* Hefei LCFC Information Technology Co.Ltd. PROPRIETARY/CONFIDENTIAL.
* Use is subject to license terms.
*
*****************************************************************************/
/*
Data Name Version Description
2014.12.28 dahai.zhou v1.00 Initial release it for EDK2 projects
*/
#include <Library/IoLib.h>
#include <Library/PcdLib.h>
#include <Uefi.h>
#include <Lfc.h>
#include <Library/GpioLib.h>
//[-start-210513-KEBIN00001-modify]//
//#include "Register/PchRegsPcr.h"
#include "Register/PchPcrRegs.h"
//[-end-210513-KEBIN00001-modify]//
#include <Library/PchPcrLib.h>
#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO base address
#define ACPI_TIMER_ADDR (PcdGet16(PcdPerfPkgAcpiIoPortBaseAddress) + 0x08)
#define ACPI_TIMER_MAX_VALUE 0x1000000
EFI_STATUS
EFIAPI
LfcLibLogError (
IN UINT8 Data
)
{
UINT8 ErrorCount;
IoWrite8 (LFC_CMOS_INDEX, LFC_DEBUG_ERROR_COUNT_INDEX);
ErrorCount = IoRead8 (LFC_CMOS_DATA);
ErrorCount++;
IoWrite8 (LFC_CMOS_INDEX, LFC_DEBUG_ERROR_COUNT_INDEX);
IoWrite8 (LFC_CMOS_DATA, ErrorCount);
if (ErrorCount > 3) {
return EFI_SUCCESS;
} else {
IoWrite8 (LFC_CMOS_INDEX, LFC_DEBUG_ERROR1_INDEX + ErrorCount - 1);
IoWrite8 (LFC_CMOS_DATA, Data);
return EFI_SUCCESS;
}
}
//[-start-210722-QINGLIN0002-modify]//
//[-start-210830-GEORGE0001-modify]//
//#ifndef S570_SUPPORT
#if !defined(S570_SUPPORT) && !defined(S77014_SUPPORT) && !defined(S77014IAH_SUPPORT)
//[-end-210830-GEORGE0001-modify]//
EFI_STATUS
EFIAPI
LfcProjectLibSetDGPUPowerEN (
UINT8 Level
)
{
UINT32 Data32;
// DGPU POEWR_EN GPP_C12 offset 0x6C0
// Set Tx to level.
Data32 = MmioRead32 (PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6C0));
Data32 &= ~BIT0;
Data32 |= Level & BIT0;
MmioWrite32(PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6C0), Data32);
return EFI_SUCCESS;
}
EFI_STATUS
EFIAPI
LfcProjectLibSetDGPUPowerRST (
UINT8 Level
)
{
UINT32 Data32;
// DGPU POEWR_RST GPP_C13 offset 0x6D0
// Set Tx to level.
Data32 = MmioRead32 (PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6D0));
Data32 &= ~BIT0;
Data32 |= Level & BIT0;
MmioWrite32(PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6D0), Data32);
return EFI_SUCCESS;
}
//
//disable Gpio's Tx, for power save and HW circuit.
//there have pull up by HW on PXS_PwrEn.
//
EFI_STATUS
EFIAPI
LfcProjectLibDisableGPUPwr (
)
{
UINT32 Data32;
//disable PXS_PwrEn output
Data32 = MmioRead32 (PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6C0));
Data32 |= BIT8;
MmioWrite32(PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6C0), Data32);
return EFI_SUCCESS;
}
EFI_STATUS
EFIAPI
LfcProjectLibGetDGPUPowerGood (
UINT8 *PowerGood
)
{
// DGPU POEWR_RST GPP_C14 offset 0x6E0
// Get Rx to PowerGood.
if(MmioRead32 (PCH_PCR_ADDRESS (PID_GPIOCOM4, 0x6E0)) & BIT1) {
// Power Good equ high
*PowerGood = 1;
}
else {
// Power Good equ low
*PowerGood = 0;
}
return EFI_SUCCESS;
}
#endif
//[-end-210722-QINGLIN0002-modify]//
/**
Waits for at least the given number of microseconds.
@param[in] Microseconds - Desired length of time to wait
@retval EFI_SUCCESS - If the desired amount of time passed.
@retval !EFI_SUCCESS - If error occurs while locating CpuIoPpi.
**/
EFI_STATUS
EFIAPI
LfcProjectLibStall (
IN UINTN Microseconds
)
{
UINT32 CurrentTick;
UINT32 OriginalTick;
UINT32 RemainingTick;
UINTN Counts;
UINTN Ticks;
if (Microseconds == 0) {
return EFI_SUCCESS;
}
OriginalTick = IoRead32 (ACPI_TIMER_ADDR) & 0x00FFFFFF;
CurrentTick = OriginalTick;
//
// The timer frequency is 3.579545 MHz, so 1 ms corresponds 3.58 clocks
//
Ticks = Microseconds * 358 / 100 + OriginalTick + 1;
//
// The loops needed by timer overflow
//
Counts = Ticks / ACPI_TIMER_MAX_VALUE;
//
// remaining clocks within one loop
//
RemainingTick = Ticks % ACPI_TIMER_MAX_VALUE;
//
// not intend to use TMROF_STS bit of register PM1_STS, because this adds extra
// one I/O operation, and maybe generate SMI
//
while (Counts != 0) {
CurrentTick = IoRead32 (ACPI_TIMER_ADDR) & 0x00FFFFFF;
if (CurrentTick <= OriginalTick) {
Counts--;
}
OriginalTick = CurrentTick;
}
while ((RemainingTick > CurrentTick) && (OriginalTick <= CurrentTick)) {
OriginalTick = CurrentTick;
CurrentTick = (IoRead32 (ACPI_TIMER_ADDR) & 0x00FFFFFF);
}
return EFI_SUCCESS;
}