Add PCH Pkg for SimicsICH10. It is added for simics QSP project support
Cc: Hao Wu <hao.a.wu@intel.com>
Cc: Liming Gao <liming.gao@intel.com>
Cc: Ankit Sinha <ankit.sinha@intel.com>
Cc: Agyeman Prince <prince.agyeman@intel.com>
Cc: Kubacki Michael A <michael.a.kubacki@intel.com>
Cc: Nate DeSimone <nathaniel.l.desimone@intel.com>
Cc: Michael D Kinney <michael.d.kinney@intel.com>
Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: David Wei <david.y.wei@intel.com>
---
.../Library/ResetSystemLib/ResetSystemLib.c | 137 +++
.../Library/SmmSpiFlashCommonLib/SpiFlashCommon.c | 194 +++++
.../SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c | 54 ++
.../LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c | 935 +++++++++++++++++++++
.../SmmControl/RuntimeDxe/SmmControl2Dxe.c | 410 +++++++++
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c | 175 ++++
Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec | 22 +
.../Include/Library/SpiFlashCommonLib.h | 98 +++
Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h | 43 +
Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h | 94 +++
.../SimicsICH10Pkg/Include/PchReservedResources.h | 60 ++
.../Intel/SimicsICH10Pkg/Include/Protocol/Spi.h | 295 +++++++
.../SimicsICH10Pkg/Include/Register/PchRegsPmc.h | 647 ++++++++++++++
.../SimicsICH10Pkg/Include/Register/PchRegsSpi.h | 304 +++++++
.../IncludePrivate/Library/PchSpiCommonLib.h | 396 +++++++++
.../Library/ResetSystemLib/ResetSystemLib.inf | 34 +
.../SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf | 52 ++
.../BasePchSpiCommonLib/BasePchSpiCommonLib.inf | 33 +
Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc | 12 +
.../Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf | 9 +
.../Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf | 9 +
.../Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf | 13 +
.../SmmControl/RuntimeDxe/SmmControl2Dxe.inf | 59 ++
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h | 23 +
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf | 44 +
25 files changed, 4152 insertions(+)
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
new file mode 100644
index 0000000000..46355e191c
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
@@ -0,0 +1,137 @@
+/** @file
+ Reset System Library functions for OVMF
+
+ Copyright (c) 2006 - 2016 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Base.h>
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/TimerLib.h>
+#include <IndustryStandard/X58Ich10.h>
+
+
+VOID
+AcpiPmControl (
+ UINTN SuspendType
+ )
+{
+ ASSERT (SuspendType < 6);
+ DEBUG((EFI_D_ERROR, "SuspendType = 0x%x\n", SuspendType));
+
+ IoBitFieldWrite16 (ICH10_PMBASE_IO + 4, 10, 13, (UINT16) SuspendType);
+ IoOr16 (ICH10_PMBASE_IO + 0x04, BIT13);
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes a system-wide reset. This sets
+ all circuitry within the system to its initial state. This type of reset
+ is asynchronous to system operation and operates without regard to
+ cycle boundaries.
+
+ System reset should not return, if it returns, it means the system does
+ not support cold reset.
+**/
+VOID
+EFIAPI
+ResetCold (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetCold_CF9\n"));
+ IoWrite8 (0xCF9, BIT3 | BIT2 | BIT1); // 1st choice: PIIX3 RCR, RCPU|SRST
+ MicroSecondDelay (50);
+
+ DEBUG((EFI_D_ERROR, "ResetCold_Port64\n"));
+ IoWrite8 (0x64, 0xfe); // 2nd choice: keyboard controller
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes a system-wide initialization. The processors
+ are set to their initial state, and pending cycles are not corrupted.
+
+ System reset should not return, if it returns, it means the system does
+ not support warm reset.
+**/
+VOID
+EFIAPI
+ResetWarm (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetWarm\n"));
+ //
+ //BUGBUG workaround for warm reset
+ //
+ IoWrite8(0xCF9, BIT2 | BIT1);
+ MicroSecondDelay(50);
+
+ IoWrite8 (0x64, 0xfe);
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes the system to enter a power state equivalent
+ to the ACPI G2/S5 or G3 states.
+
+ System shutdown should not return, if it returns, it means the system does
+ not support shut down reset.
+**/
+VOID
+EFIAPI
+ResetShutdown (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetShutdown\n"));
+ AcpiPmControl (0);
+ ASSERT (FALSE);
+}
+
+
+/**
+ Calling this function causes the system to enter a power state for capsule
+ update.
+
+ Reset update should not return, if it returns, it means the system does
+ not support capsule update.
+
+**/
+VOID
+EFIAPI
+EnterS3WithImmediateWake (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "EnterS3WithImmediateWake\n"));
+ AcpiPmControl (1);
+ ASSERT (FALSE);
+}
+
+/**
+ This function causes a systemwide reset. The exact type of the reset is
+ defined by the EFI_GUID that follows the Null-terminated Unicode string passed
+ into ResetData. If the platform does not recognize the EFI_GUID in ResetData
+ the platform must pick a supported reset type to perform.The platform may
+ optionally log the parameters from any non-normal reset that occurs.
+
+ @param[in] DataSize The size, in bytes, of ResetData.
+ @param[in] ResetData The data buffer starts with a Null-terminated string,
+ followed by the EFI_GUID.
+**/
+VOID
+EFIAPI
+ResetPlatformSpecific (
+ IN UINTN DataSize,
+ IN VOID *ResetData
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetPlatformSpecific\n"));
+ ResetCold ();
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
new file mode 100644
index 0000000000..3d4e24eac6
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
@@ -0,0 +1,194 @@
+/** @file
+ Wrap EFI_SPI_PROTOCOL to provide some library level interfaces
+ for module use.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/SpiFlashCommonLib.h>
+#include <Library/IoLib.h>
+#include <Library/PciLib.h>
+#include <Protocol/Spi.h>
+
+
+EFI_SPI_PROTOCOL *mSpiProtocol;
+
+//
+// FlashAreaBaseAddress and Size for boottime and runtime usage.
+//
+UINTN mFlashAreaBaseAddress = 0;
+UINTN mFlashAreaSize = 0;
+
+/**
+ Enable block protection on the Serial Flash device.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashLock (
+ VOID
+ )
+{
+ return EFI_SUCCESS;
+}
+
+/**
+ Read NumBytes bytes of data from the address specified by
+ PAddress into Buffer.
+
+ @param[in] Address The starting physical address of the read.
+ @param[in,out] NumBytes On input, the number of bytes to read. On output, the number
+ of bytes actually read.
+ @param[out] Buffer The destination data buffer for the read.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashRead (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ OUT UINT8 *Buffer
+ )
+{
+ ASSERT ((NumBytes != NULL) && (Buffer != NULL));
+ if ((NumBytes == NULL) || (Buffer == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // This function is implemented specifically for those platforms
+ // at which the SPI device is memory mapped for read. So this
+ // function just do a memory copy for Spi Flash Read.
+ //
+ CopyMem (Buffer, (VOID *) Address, *NumBytes);
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Write NumBytes bytes of data from Buffer to the address specified by
+ PAddresss.
+
+ @param[in] Address The starting physical address of the write.
+ @param[in,out] NumBytes On input, the number of bytes to write. On output,
+ the actual number of bytes written.
+ @param[in] Buffer The source data buffer for the write.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashWrite (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ IN UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINTN Offset;
+ UINT32 Length;
+ UINT32 RemainingBytes;
+
+ ASSERT ((NumBytes != NULL) && (Buffer != NULL));
+ if ((NumBytes == NULL) || (Buffer == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ ASSERT (Address >= mFlashAreaBaseAddress);
+
+ Offset = Address - mFlashAreaBaseAddress;
+
+ ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
+
+ Status = EFI_SUCCESS;
+ RemainingBytes = *NumBytes;
+
+
+ while (RemainingBytes > 0) {
+ if (RemainingBytes > SECTOR_SIZE_4KB) {
+ Length = SECTOR_SIZE_4KB;
+ } else {
+ Length = RemainingBytes;
+ }
+ Status = mSpiProtocol->FlashWrite (
+ mSpiProtocol,
+ FlashRegionBios,
+ (UINT32) Offset,
+ Length,
+ Buffer
+ );
+ if (EFI_ERROR (Status)) {
+ break;
+ }
+ RemainingBytes -= Length;
+ Offset += Length;
+ Buffer += Length;
+ }
+
+ //
+ // Actual number of bytes written
+ //
+ *NumBytes -= RemainingBytes;
+
+ return Status;
+}
+
+/**
+ Erase the block starting at Address.
+
+ @param[in] Address The starting physical address of the block to be erased.
+ This library assume that caller garantee that the PAddress
+ is at the starting address of this block.
+ @param[in] NumBytes On input, the number of bytes of the logical block to be erased.
+ On output, the actual number of bytes erased.
+
+ @retval EFI_SUCCESS. Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashBlockErase (
+ IN UINTN Address,
+ IN UINTN *NumBytes
+ )
+{
+ EFI_STATUS Status;
+ UINTN Offset;
+ UINTN RemainingBytes;
+
+ ASSERT (NumBytes != NULL);
+ if (NumBytes == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ ASSERT (Address >= mFlashAreaBaseAddress);
+
+ Offset = Address - mFlashAreaBaseAddress;
+
+ ASSERT ((*NumBytes % SECTOR_SIZE_4KB) == 0);
+ ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
+
+ Status = EFI_SUCCESS;
+ RemainingBytes = *NumBytes;
+
+
+ Status = mSpiProtocol->FlashErase (
+ mSpiProtocol,
+ FlashRegionBios,
+ (UINT32) Offset,
+ (UINT32) RemainingBytes
+ );
+ return Status;
+}
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
new file mode 100644
index 0000000000..1e5cd0d744
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
@@ -0,0 +1,54 @@
+/** @file
+ SMM Library instance of SPI Flash Common Library Class
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/SpiFlashCommonLib.h>
+#include <Library/SmmServicesTableLib.h>
+#include <Protocol/Spi.h>
+
+extern EFI_SPI_PROTOCOL *mSpiProtocol;
+
+extern UINTN mFlashAreaBaseAddress;
+extern UINTN mFlashAreaSize;
+
+/**
+ The library constructuor.
+
+ The function does the necessary initialization work for this library
+ instance.
+
+ @param[in] ImageHandle The firmware allocated handle for the UEFI image.
+ @param[in] SystemTable A pointer to the EFI system table.
+
+ @retval EFI_SUCCESS The function always return EFI_SUCCESS for now.
+ It will ASSERT on error for debug version.
+ @retval EFI_ERROR Please reference LocateProtocol for error code details.
+**/
+EFI_STATUS
+EFIAPI
+SmmSpiFlashCommonLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ mFlashAreaBaseAddress = (UINTN)PcdGet32 (PcdFlashAreaBaseAddress);
+ mFlashAreaSize = (UINTN)PcdGet32 (PcdFlashAreaSize);
+
+ //
+ // Locate the SMM SPI protocol.
+ //
+ Status = gSmst->SmmLocateProtocol (
+ &gEfiSmmSpiProtocolGuid,
+ NULL,
+ (VOID **) &mSpiProtocol
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
new file mode 100644
index 0000000000..77fb76d7cd
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
@@ -0,0 +1,935 @@
+/** @file
+ PCH SPI Common Driver implements the SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Uefi/UefiBaseType.h>
+#include <Library/IoLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <IndustryStandard/Pci30.h>
+#include <PchAccess.h>
+#include <Protocol/Spi.h>
+#include <IncludePrivate/Library/PchSpiCommonLib.h>
+#include <IndustryStandard/X58Ich10.h>
+
+/**
+ Initialize an SPI protocol instance.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @exception EFI_UNSUPPORTED The PCH is not supported by this module
+**/
+EFI_STATUS
+SpiProtocolConstructor (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+ UINTN PchSpiBar0;
+
+ //
+ // Initialize the SPI protocol instance
+ //
+ SpiInstance->Signature = PCH_SPI_PRIVATE_DATA_SIGNATURE;
+ SpiInstance->Handle = NULL;
+ SpiInstance->SpiProtocol.Revision = PCH_SPI_SERVICES_REVISION;
+ SpiInstance->SpiProtocol.FlashRead = SpiProtocolFlashRead;
+ SpiInstance->SpiProtocol.FlashWrite = SpiProtocolFlashWrite;
+ SpiInstance->SpiProtocol.FlashErase = SpiProtocolFlashErase;
+ SpiInstance->SpiProtocol.FlashReadSfdp = SpiProtocolFlashReadSfdp;
+ SpiInstance->SpiProtocol.FlashReadJedecId = SpiProtocolFlashReadJedecId;
+ SpiInstance->SpiProtocol.FlashWriteStatus = SpiProtocolFlashWriteStatus;
+ SpiInstance->SpiProtocol.FlashReadStatus = SpiProtocolFlashReadStatus;
+ SpiInstance->SpiProtocol.GetRegionAddress = SpiProtocolGetRegionAddress;
+ SpiInstance->SpiProtocol.ReadPchSoftStrap = SpiProtocolReadPchSoftStrap;
+ SpiInstance->SpiProtocol.ReadCpuSoftStrap = SpiProtocolReadCpuSoftStrap;
+
+ SpiInstance->PchAcpiBase = ICH10_PMBASE_IO;
+ ASSERT (SpiInstance->PchAcpiBase != 0);
+
+ PchSpiBar0 = RCRB + SPIBAR;
+
+ if (PchSpiBar0 == 0) {
+ DEBUG ((DEBUG_ERROR, "ERROR : PchSpiBar0 is invalid!\n"));
+ ASSERT (FALSE);
+ }
+
+ if ((MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC) & B_PCH_SPI_HSFSC_FDV) == 0) {
+ DEBUG ((DEBUG_ERROR, "ERROR : SPI Flash Signature invalid, cannot use the Hardware Sequencing registers!\n"));
+ ASSERT (FALSE);
+ }
+ SpiInstance->ReadPermission = 0xffff;
+ SpiInstance->WritePermission = 0xffff;
+ DEBUG ((DEBUG_INFO, "Flash Region Permission: Read- 0x%04x; Write= 0x%04x\n",
+ SpiInstance->ReadPermission,
+ SpiInstance->WritePermission));
+
+ //
+ SpiInstance->TotalFlashSize = PcdGet32(PcdFlashAreaSize);
+ DEBUG ((DEBUG_INFO, "Total Flash Size : %0x\n", SpiInstance->TotalFlashSize));
+ return EFI_SUCCESS;
+}
+
+/**
+ Delay for at least the request number of microseconds for Runtime usage.
+
+ @param[in] ABase Acpi base address
+ @param[in] Microseconds Number of microseconds to delay.
+
+**/
+VOID
+EFIAPI
+PchPmTimerStallRuntimeSafe (
+ IN UINT16 ABase,
+ IN UINTN Microseconds
+ )
+{
+ UINTN Ticks;
+ UINTN Counts;
+ UINTN CurrentTick;
+ UINTN OriginalTick;
+ UINTN RemainingTick;
+
+ if (Microseconds == 0) {
+ return;
+ }
+
+ OriginalTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) & B_PCH_ACPI_PM1_TMR_VAL;
+ 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 / V_PCH_ACPI_PM1_TMR_MAX_VAL;
+
+ //
+ // Remaining clocks within one loop
+ //
+ RemainingTick = Ticks % V_PCH_ACPI_PM1_TMR_MAX_VAL;
+
+ //
+ // 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) || (RemainingTick > CurrentTick)) {
+ CurrentTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) & B_PCH_ACPI_PM1_TMR_VAL;
+ //
+ // Check if timer overflow
+ //
+ if ((CurrentTick < OriginalTick)) {
+ if (Counts != 0) {
+ Counts--;
+ } else {
+ //
+ // If timer overflow and Counts equ to 0, that means we already stalled more than
+ // RemainingTick, break the loop here
+ //
+ break;
+ }
+ }
+
+ OriginalTick = CurrentTick;
+ }
+}
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashRead (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleRead,
+ Address,
+ ByteCount,
+ Buffer
+ );
+ return Status;
+}
+
+/**
+ Write data to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWrite (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleWrite,
+ Address,
+ ByteCount,
+ Buffer
+ );
+ return Status;
+}
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashErase (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleErase,
+ Address,
+ ByteCount,
+ NULL
+ );
+ return Status;
+}
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadSfdp (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ EFI_STATUS Status;
+ UINT32 FlashAddress;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ Status = EFI_SUCCESS;
+
+ if (ComponentNumber > SpiInstance->NumberOfComponents) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ FlashAddress = 0;
+ if (ComponentNumber == FlashComponent1) {
+ FlashAddress = SpiInstance->Component1StartAddr;
+ }
+ FlashAddress += Address;
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadSfdp,
+ FlashAddress,
+ ByteCount,
+ SfdpData
+ );
+ return Status;
+}
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadJedecId (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ EFI_STATUS Status;
+ UINT32 Address;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ Status = EFI_SUCCESS;
+
+ if (ComponentNumber > SpiInstance->NumberOfComponents) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Address = 0;
+ if (ComponentNumber == FlashComponent1) {
+ Address = SpiInstance->Component1StartAddr;
+ }
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadJedecId,
+ Address,
+ ByteCount,
+ JedecId
+ );
+ return Status;
+}
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWriteStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleWriteStatus,
+ 0,
+ ByteCount,
+ StatusValue
+ );
+ return Status;
+}
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadStatus,
+ 0,
+ ByteCount,
+ StatusValue
+ );
+ return Status;
+}
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolGetRegionAddress (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINTN PchSpiBar0;
+ UINT32 ReadValue;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (FlashRegionType >= FlashRegionMax) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ if (FlashRegionType == FlashRegionAll) {
+ *BaseAddress = 0;
+ *RegionSize = SpiInstance->TotalFlashSize;
+ return EFI_SUCCESS;
+ }
+
+ PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
+ ReadValue = MmioRead32 (PchSpiBar0 + (R_PCH_SPI_FREG0_FLASHD + (S_PCH_SPI_FREGX * ((UINT32) FlashRegionType))));
+ ReleaseSpiBar0 (SpiInstance);
+
+ //
+ // If the region is not used, the Region Base is 7FFFh and Region Limit is 0000h
+ //
+ if (ReadValue == B_PCH_SPI_FREGX_BASE_MASK) {
+ return EFI_DEVICE_ERROR;
+ }
+ *BaseAddress = ((ReadValue & B_PCH_SPI_FREGX_BASE_MASK) >> N_PCH_SPI_FREGX_BASE) <<
+ N_PCH_SPI_FREGX_BASE_REPR;
+ //
+ // Region limit address Bits[11:0] are assumed to be FFFh
+ //
+ *RegionSize = ((((ReadValue & B_PCH_SPI_FREGX_LIMIT_MASK) >> N_PCH_SPI_FREGX_LIMIT) + 1) <<
+ N_PCH_SPI_FREGX_LIMIT_REPR) - *BaseAddress;
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadPchSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINT32 StrapFlashAddr;
+ EFI_STATUS Status;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (ByteCount == 0) {
+ *(UINT16 *) SoftStrapValue = SpiInstance->PchStrapSize;
+ return EFI_SUCCESS;
+ }
+
+ if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->PchStrapSize) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // PCH Strap Flash Address = FPSBA + RamAddr
+ //
+ StrapFlashAddr = SpiInstance->PchStrapBaseAddr + SoftStrapAddr;
+
+ //
+ // Read PCH Soft straps from using execute command
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionDescriptor,
+ FlashCycleRead,
+ StrapFlashAddr,
+ ByteCount,
+ SoftStrapValue
+ );
+ return Status;
+}
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadCpuSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINT32 StrapFlashAddr;
+ EFI_STATUS Status;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (ByteCount == 0) {
+ *(UINT16 *) SoftStrapValue = SpiInstance->CpuStrapSize;
+ return EFI_SUCCESS;
+ }
+
+ if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->CpuStrapSize) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // CPU Strap Flash Address = FCPUSBA + RamAddr
+ //
+ StrapFlashAddr = SpiInstance->CpuStrapBaseAddr + SoftStrapAddr;
+
+ //
+ // Read Cpu Soft straps from using execute command
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionDescriptor,
+ FlashCycleRead,
+ StrapFlashAddr,
+ ByteCount,
+ SoftStrapValue
+ );
+ return Status;
+}
+
+/**
+ This function sends the programmed SPI command to the slave device.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SpiRegionType The SPI Region type for flash cycle which is listed in the Descriptor
+ @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware Sequencing Flash Control Register) register
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in,out] Buffer Pointer to caller-allocated buffer containing the dada received or sent during the SPI cycle.
+
+ @retval EFI_SUCCESS SPI command completes successfully.
+ @retval EFI_DEVICE_ERROR Device error, the command aborts abnormally.
+ @retval EFI_ACCESS_DENIED Some unrecognized command encountered in hardware sequencing mode
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+**/
+EFI_STATUS
+SendSpiCmd (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN FLASH_CYCLE_TYPE FlashCycleType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN OUT UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Index;
+ SPI_INSTANCE *SpiInstance;
+ UINTN SpiBaseAddress;
+ UINTN PchSpiBar0;
+ UINT32 HardwareSpiAddr;
+ UINT32 FlashRegionSize;
+ UINT32 SpiDataCount;
+ UINT32 FlashCycle;
+ UINT32 SmiEnSave;
+ UINT16 ABase;
+
+ Status = EFI_SUCCESS;
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ SpiBaseAddress = SpiInstance->PchSpiBase;
+ PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
+ SpiBaseAddress = SpiInstance->PchSpiBase;
+ ABase = SpiInstance->PchAcpiBase;
+
+ //
+ // Disable SMIs to make sure normal mode flash access is not interrupted by an SMI
+ // whose SMI handler accesses flash (e.g. for error logging)
+ //
+ // *** NOTE: if the SMI_LOCK bit is set (i.e., PMC PCI Offset A0h [4]='1'),
+ // clearing B_GBL_SMI_EN will not have effect. In this situation, some other
+ // synchronization methods must be applied here or in the consumer of the
+ // SendSpiCmd. An example method is disabling the specific SMI sources
+ // whose SMI handlers access flash before flash cycle and re-enabling the SMI
+ // sources after the flash cycle .
+ //
+ SmiEnSave = IoRead32 ((UINTN) (ABase + R_PCH_SMI_EN));
+ IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave & (UINT32) (~B_PCH_SMI_EN_GBL_SMI));
+
+ //
+ // If it's write cycle, disable Prefetching, Caching and disable BIOS Write Protect
+ //
+ if ((FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleErase)) {
+ Status = DisableBiosWriteProtect ();
+ if (EFI_ERROR (Status)) {
+ goto SendSpiCmdEnd;
+ }
+ }
+ //
+ // Make sure it's safe to program the command.
+ //
+ if (!WaitForSpiCycleComplete (This, PchSpiBar0, FALSE)) {
+ Status = EFI_DEVICE_ERROR;
+ goto SendSpiCmdEnd;
+ }
+
+ Status = SpiProtocolGetRegionAddress (This, FlashRegionType, &HardwareSpiAddr, &FlashRegionSize);
+ if (EFI_ERROR (Status)) {
+ goto SendSpiCmdEnd;
+ }
+ HardwareSpiAddr += Address;
+ if ((Address + ByteCount) > FlashRegionSize) {
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ }
+
+ //
+ // Check for PCH SPI hardware sequencing required commands
+ //
+ FlashCycle = 0;
+ switch (FlashCycleType) {
+ case FlashCycleRead:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleWrite:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleErase:
+ if (((ByteCount % SIZE_4KB) != 0) ||
+ ((HardwareSpiAddr % SIZE_4KB) != 0)) {
+ ASSERT (FALSE);
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ }
+ break;
+ case FlashCycleReadSfdp:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_SFDP << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleReadJedecId:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleWriteStatus:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleReadStatus:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_STATUS << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ default:
+ //
+ // Unrecognized Operation
+ //
+ ASSERT (FALSE);
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ break;
+ }
+
+ do {
+ SpiDataCount = ByteCount;
+ if ((FlashCycleType == FlashCycleRead) ||
+ (FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleReadSfdp)) {
+ //
+ // Trim at 256 byte boundary per operation,
+ // - PCH SPI controller requires trimming at 4KB boundary
+ // - Some SPI chips require trimming at 256 byte boundary for write operation
+ // - Trimming has limited performance impact as we can read / write atmost 64 byte
+ // per operation
+ //
+ if (HardwareSpiAddr + ByteCount > ((HardwareSpiAddr + BIT8) &~(BIT8 - 1))) {
+ SpiDataCount = (((UINT32) (HardwareSpiAddr) + BIT8) &~(BIT8 - 1)) - (UINT32) (HardwareSpiAddr);
+ }
+ //
+ // Calculate the number of bytes to shift in/out during the SPI data cycle.
+ // Valid settings for the number of bytes duing each data portion of the
+ // PCH SPI cycles are: 0, 1, 2, 3, 4, 5, 6, 7, 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ if (SpiDataCount >= 64) {
+ SpiDataCount = 64;
+ } else if ((SpiDataCount &~0x07) != 0) {
+ SpiDataCount = SpiDataCount &~0x07;
+ }
+ }
+ if (FlashCycleType == FlashCycleErase) {
+ if (((ByteCount / SIZE_64KB) != 0) &&
+ ((ByteCount % SIZE_64KB) == 0) &&
+ ((HardwareSpiAddr % SIZE_64KB) == 0)) {
+ if (HardwareSpiAddr < SpiInstance->Component1StartAddr) {
+ //
+ // Check whether Component0 support 64k Erase
+ //
+ if ((SpiInstance->SfdpVscc0Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K) != 0) {
+ SpiDataCount = SIZE_64KB;
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ } else {
+ //
+ // Check whether Component1 support 64k Erase
+ //
+ if ((SpiInstance->SfdpVscc1Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K) != 0) {
+ SpiDataCount = SIZE_64KB;
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ }
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ if (SpiDataCount == SIZE_4KB) {
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_4K_ERASE << N_PCH_SPI_HSFSC_CYCLE);
+ } else {
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_64K_ERASE << N_PCH_SPI_HSFSC_CYCLE);
+ }
+ }
+ //
+ // If it's write cycle, load data into the SPI data buffer.
+ //
+ if ((FlashCycleType == FlashCycleWrite) || (FlashCycleType == FlashCycleWriteStatus)) {
+ if ((SpiDataCount & 0x07) != 0) {
+ //
+ // Use Byte write if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
+ //
+ for (Index = 0; Index < SpiDataCount; Index++) {
+ MmioWrite8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, Buffer[Index]);
+ }
+ } else {
+ //
+ // Use Dword write if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
+ MmioWrite32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, *(UINT32 *) (Buffer + Index));
+ }
+ }
+ }
+
+ //
+ // Set the Flash Address
+ //
+ MmioWrite32 (
+ (PchSpiBar0 + R_PCH_SPI_FADDR),
+ (UINT32) (HardwareSpiAddr & B_PCH_SPI_FADDR_MASK)
+ );
+
+ //
+ // Set Data count, Flash cycle, and Set Go bit to start a cycle
+ //
+ MmioAndThenOr32 (
+ PchSpiBar0 + R_PCH_SPI_HSFSC,
+ (UINT32) (~(B_PCH_SPI_HSFSC_FDBC_MASK | B_PCH_SPI_HSFSC_CYCLE_MASK)),
+ (UINT32) ((((SpiDataCount - 1) << N_PCH_SPI_HSFSC_FDBC) & B_PCH_SPI_HSFSC_FDBC_MASK) | FlashCycle | B_PCH_SPI_HSFSC_CYCLE_FGO)
+ );
+ //
+ // end of command execution
+ //
+ // Wait the SPI cycle to complete.
+ //
+ if (!WaitForSpiCycleComplete (This, PchSpiBar0, TRUE)) {
+ ASSERT (FALSE);
+ Status = EFI_DEVICE_ERROR;
+ goto SendSpiCmdEnd;
+ }
+ //
+ // If it's read cycle, load data into the call's buffer.
+ //
+ if ((FlashCycleType == FlashCycleRead) ||
+ (FlashCycleType == FlashCycleReadSfdp) ||
+ (FlashCycleType == FlashCycleReadJedecId) ||
+ (FlashCycleType == FlashCycleReadStatus)) {
+ if ((SpiDataCount & 0x07) != 0) {
+ //
+ // Use Byte read if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
+ //
+ for (Index = 0; Index < SpiDataCount; Index++) {
+ Buffer[Index] = MmioRead8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index);
+ }
+ } else {
+ //
+ // Use Dword read if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
+ *(UINT32 *) (Buffer + Index) = MmioRead32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index);
+ }
+ }
+ }
+
+ HardwareSpiAddr += SpiDataCount;
+ Buffer += SpiDataCount;
+ ByteCount -= SpiDataCount;
+ } while (ByteCount > 0);
+
+SendSpiCmdEnd:
+ //
+ // Restore the settings for SPI Prefetching and Caching and enable BIOS Write Protect
+ //
+ if ((FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleErase)) {
+ EnableBiosWriteProtect ();
+ }
+ //
+ // Restore SMIs.
+ //
+ IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave);
+
+ ReleaseSpiBar0 (SpiInstance);
+ return Status;
+}
+
+/**
+ Wait execution cycle to complete on the SPI interface.
+
+ @param[in] This The SPI protocol instance
+ @param[in] PchSpiBar0 Spi MMIO base address
+ @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
+
+ @retval TRUE SPI cycle completed on the interface.
+ @retval FALSE Time out while waiting the SPI cycle to complete.
+ It's not safe to program the next command on the SPI interface.
+**/
+BOOLEAN
+WaitForSpiCycleComplete (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINTN PchSpiBar0,
+ IN BOOLEAN ErrorCheck
+ )
+{
+ UINT64 WaitTicks;
+ UINT64 WaitCount;
+ UINT32 Data32;
+ SPI_INSTANCE *SpiInstance;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ //
+ // Convert the wait period allowed into to tick count
+ //
+ WaitCount = SPI_WAIT_TIME / SPI_WAIT_PERIOD;
+ //
+ // Wait for the SPI cycle to complete.
+ //
+ for (WaitTicks = 0; WaitTicks < WaitCount; WaitTicks++) {
+ Data32 = MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC);
+ if ((Data32 & B_PCH_SPI_HSFSC_SCIP) == 0) {
+ MmioWrite32 (PchSpiBar0 + R_PCH_SPI_HSFSC, B_PCH_SPI_HSFSC_FCERR | B_PCH_SPI_HSFSC_FDONE);
+ if (((Data32 & B_PCH_SPI_HSFSC_FCERR) != 0) && (ErrorCheck == TRUE)) {
+ return FALSE;
+ } else {
+ return TRUE;
+ }
+ }
+ PchPmTimerStallRuntimeSafe (SpiInstance->PchAcpiBase, SPI_WAIT_PERIOD);
+ }
+ return FALSE;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
new file mode 100644
index 0000000000..8fb4947b1a
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
@@ -0,0 +1,410 @@
+/** @file
+ A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
+ EFI_SMM_CONTROL2_PROTOCOL.
+
+ We expect the PEI phase to have covered the following:
+ - ensure that the underlying QEMU machine type be X58
+ (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
+ - ensure that the ACPI PM IO space be configured
+ (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
+
+ Our own entry point is responsible for confirming the SMI feature and for
+ configuring it.
+
+ Copyright (C) 2013, 2015, Red Hat, Inc.<BR>
+ Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <IndustryStandard/X58Ich10.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/PcdLib.h>
+#include <Library/PciLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Protocol/S3SaveState.h>
+#include <Protocol/SmmControl2.h>
+
+//
+// Forward declaration.
+//
+STATIC
+VOID
+EFIAPI
+OnS3SaveStateInstalled (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ );
+
+//
+// The absolute IO port address of the SMI Control and Enable Register. It is
+// only used to carry information from the entry point function to the
+// S3SaveState protocol installation callback, strictly before the runtime
+// phase.
+//
+STATIC UINTN mSmiEnable;
+
+//
+// Event signaled when an S3SaveState protocol interface is installed.
+//
+STATIC EFI_EVENT mS3SaveStateInstalled;
+
+/**
+ Clear the SMI status
+
+ @retval EFI_SUCCESS The function completes successfully
+ @retval EFI_DEVICE_ERROR Something error occurred
+
+**/
+EFI_STATUS
+EFIAPI
+SmmClear(
+ VOID
+)
+{
+ EFI_STATUS Status;
+ UINT32 OutputData;
+ UINT32 OutputPort;
+ UINT32 PmBase;
+
+ Status = EFI_SUCCESS;
+ PmBase = ICH10_PMBASE_IO;
+
+ OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_STS;
+ OutputData = ICH10_SMI_STS_APM;
+ IoWrite32(
+ (UINTN)OutputPort,
+ (UINT32)(OutputData)
+ );
+
+ ///
+ /// Set the EOS Bit
+ ///
+ OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_EN;
+ OutputData = IoRead32((UINTN)OutputPort);
+ OutputData |= ICH10_SMI_EN_EOS;
+ IoWrite32(
+ (UINTN)OutputPort,
+ (UINT32)(OutputData)
+ );
+
+ ///
+ /// There is no need to read EOS back and check if it is set.
+ /// This can lead to a reading of zero if an SMI occurs right after the SMI_EN port read
+ /// but before the data is returned to the CPU.
+ /// SMM Dispatcher should make sure that EOS is set after all SMI sources are processed.
+ ///
+ return Status;
+}
+
+/**
+ Invokes SMI activation from either the preboot or runtime environment.
+
+ This function generates an SMI.
+
+ @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
+ @param[in,out] CommandPort The value written to the command port.
+ @param[in,out] DataPort The value written to the data port.
+ @param[in] Periodic Optional mechanism to engender a periodic
+ stream.
+ @param[in] ActivationInterval Optional parameter to repeat at this
+ period one time or, if the Periodic
+ Boolean is set, periodically.
+
+ @retval EFI_SUCCESS The SMI/PMI has been engendered.
+ @retval EFI_DEVICE_ERROR The timing is unsupported.
+ @retval EFI_INVALID_PARAMETER The activation period is unsupported.
+ @retval EFI_INVALID_PARAMETER The last periodic activation has not been
+ cleared.
+ @retval EFI_NOT_STARTED The SMM base service has not been initialized.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+SmmControl2DxeTrigger (
+ IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
+ IN OUT UINT8 *CommandPort OPTIONAL,
+ IN OUT UINT8 *DataPort OPTIONAL,
+ IN BOOLEAN Periodic OPTIONAL,
+ IN UINTN ActivationInterval OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ //
+ // No support for queued or periodic activation.
+ //
+ if (Periodic || ActivationInterval > 0) {
+ return EFI_DEVICE_ERROR;
+ }
+ ///
+ /// Clear any pending the APM SMI
+ ///
+ Status = SmmClear();
+ //
+ // The so-called "Advanced Power Management Status Port Register" is in fact
+ // a generic data passing register, between the caller and the SMI
+ // dispatcher. The ICH9 spec calls it "scratchpad register" -- calling it
+ // "status" elsewhere seems quite the misnomer. Status registers usually
+ // report about hardware status, while this register is fully governed by
+ // software.
+ //
+ // Write to the status register first, as this won't trigger the SMI just
+ // yet. Then write to the control register.
+ //
+ IoWrite8 (ICH10_APM_STS, DataPort == NULL ? 0 : *DataPort);
+ IoWrite8 (ICH10_APM_CNT, CommandPort == NULL ? 0 : *CommandPort);
+ return EFI_SUCCESS;
+}
+
+/**
+ Clears any system state that was created in response to the Trigger() call.
+
+ This function acknowledges and causes the deassertion of the SMI activation
+ source.
+
+ @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
+ @param[in] Periodic Optional parameter to repeat at this period
+ one time
+
+ @retval EFI_SUCCESS The SMI/PMI has been engendered.
+ @retval EFI_DEVICE_ERROR The source could not be cleared.
+ @retval EFI_INVALID_PARAMETER The service did not support the Periodic input
+ argument.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+SmmControl2DxeClear (
+ IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
+ IN BOOLEAN Periodic OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ if (Periodic) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // The PI spec v1.4 explains that Clear() is only supposed to clear software
+ // status; it is not in fact responsible for deasserting the SMI. It gives
+ // two reasons for this: (a) many boards clear the SMI automatically when
+ // entering SMM, (b) if Clear() actually deasserted the SMI, then it could
+ // incorrectly suppress an SMI that was asynchronously asserted between the
+ // last return of the SMI handler and the call made to Clear().
+ //
+ // In fact QEMU automatically deasserts CPU_INTERRUPT_SMI in:
+ // - x86_cpu_exec_interrupt() [target-i386/seg_helper.c], and
+ // - kvm_arch_pre_run() [target-i386/kvm.c].
+ //
+ // So, nothing to do here.
+ //
+ Status = SmmClear();
+
+ return EFI_SUCCESS;
+}
+
+STATIC EFI_SMM_CONTROL2_PROTOCOL mControl2 = {
+ &SmmControl2DxeTrigger,
+ &SmmControl2DxeClear,
+ MAX_UINTN // MinimumTriggerPeriod -- we don't support periodic SMIs
+};
+
+//
+// Entry point of this driver.
+//
+EFI_STATUS
+EFIAPI
+SmmControl2DxeEntryPoint (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ UINT32 PmBase;
+ UINT32 SmiEnableVal;
+ EFI_STATUS Status;
+
+ //
+ // This module should only be included if SMRAM support is required.
+ //
+ ASSERT (FeaturePcdGet (PcdSmmSmramRequire));
+
+ //
+ // Calculate the absolute IO port address of the SMI Control and Enable
+ // Register. (As noted at the top, the PEI phase has left us with a working
+ // ACPI PM IO space.)
+ //
+ PmBase = PciRead32 (POWER_MGMT_REGISTER_ICH10 (ICH10_PMBASE)) &
+ ICH10_PMBASE_MASK;
+ mSmiEnable = PmBase + ICH10_PMBASE_OFS_SMI_EN;
+
+ //
+ // If APMC_EN is pre-set in SMI_EN, that's QEMU's way to tell us that SMI
+ // support is not available. (For example due to KVM lacking it.) Otherwise,
+ // this bit is clear after each reset.
+ //
+ SmiEnableVal = IoRead32 (mSmiEnable);
+ if ((SmiEnableVal & ICH10_SMI_EN_APMC_EN) != 0) {
+ DEBUG ((EFI_D_ERROR, "%a: this X58 implementation lacks SMI\n",
+ __FUNCTION__));
+ }
+
+ //
+ // Otherwise, configure the board to inject an SMI when ICH10_APM_CNT is
+ // written to. (See the Trigger() method above.)
+ //
+ SmiEnableVal |= ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
+ IoWrite32 (mSmiEnable, SmiEnableVal);
+
+ //
+ // Prevent software from undoing the above (until platform reset).
+ //
+ PciOr16 (POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
+ ICH10_GEN_PMCON_1_SMI_LOCK);
+
+ //
+ // If we can clear GBL_SMI_EN now, that means QEMU's SMI support is not
+ // appropriate.
+ //
+ IoWrite32 (mSmiEnable, SmiEnableVal & ~(UINT32)ICH10_SMI_EN_GBL_SMI_EN);
+ if (IoRead32 (mSmiEnable) != SmiEnableVal) {
+ DEBUG ((EFI_D_ERROR, "%a: failed to lock down GBL_SMI_EN\n",
+ __FUNCTION__));
+ goto FatalError;
+ }
+
+ VOID *Registration;
+
+ //
+ // On S3 resume the above register settings have to be repeated. Register a
+ // protocol notify callback that, when boot script saving becomes
+ // available, saves operations equivalent to the above to the boot script.
+ //
+ Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK,
+ OnS3SaveStateInstalled, NULL /* Context */,
+ &mS3SaveStateInstalled);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: CreateEvent: %r\n", __FUNCTION__, Status));
+ goto FatalError;
+ }
+
+ Status = gBS->RegisterProtocolNotify (&gEfiS3SaveStateProtocolGuid,
+ mS3SaveStateInstalled, &Registration);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: RegisterProtocolNotify: %r\n", __FUNCTION__,
+ Status));
+ goto ReleaseEvent;
+ }
+
+ //
+ // Kick the event right now -- maybe the boot script is already saveable.
+ //
+ Status = gBS->SignalEvent (mS3SaveStateInstalled);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: SignalEvent: %r\n", __FUNCTION__, Status));
+ goto ReleaseEvent;
+ }
+
+ //
+ // We have no pointers to convert to virtual addresses. The handle itself
+ // doesn't matter, as protocol services are not accessible at runtime.
+ //
+ Status = gBS->InstallMultipleProtocolInterfaces (&ImageHandle,
+ &gEfiSmmControl2ProtocolGuid, &mControl2,
+ NULL);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: InstallMultipleProtocolInterfaces: %r\n",
+ __FUNCTION__, Status));
+ goto ReleaseEvent;
+ }
+
+ return EFI_SUCCESS;
+
+ReleaseEvent:
+ if (mS3SaveStateInstalled != NULL) {
+ gBS->CloseEvent (mS3SaveStateInstalled);
+ }
+
+FatalError:
+ //
+ // We really don't want to continue in this case.
+ //
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ return EFI_UNSUPPORTED;
+}
+
+/**
+ Notification callback for S3SaveState installation.
+
+ @param[in] Event Event whose notification function is being invoked.
+
+ @param[in] Context The pointer to the notification function's context, which
+ is implementation-dependent.
+**/
+STATIC
+VOID
+EFIAPI
+OnS3SaveStateInstalled (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+{
+ EFI_STATUS Status;
+ EFI_S3_SAVE_STATE_PROTOCOL *S3SaveState;
+ UINT32 SmiEnOrMask, SmiEnAndMask;
+ UINT16 GenPmCon1OrMask, GenPmCon1AndMask;
+
+ ASSERT (Event == mS3SaveStateInstalled);
+
+ Status = gBS->LocateProtocol (&gEfiS3SaveStateProtocolGuid,
+ NULL /* Registration */, (VOID **)&S3SaveState);
+ if (EFI_ERROR (Status)) {
+ return;
+ }
+
+ //
+ // These operations were originally done, verified and explained in the entry
+ // point function of the driver.
+ //
+ SmiEnOrMask = ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
+ SmiEnAndMask = MAX_UINT32;
+ Status = S3SaveState->Write (
+ S3SaveState,
+ EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE,
+ EfiBootScriptWidthUint32,
+ (UINT64)mSmiEnable,
+ &SmiEnOrMask,
+ &SmiEnAndMask
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE: %r\n",
+ __FUNCTION__, Status));
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ }
+
+ GenPmCon1OrMask = ICH10_GEN_PMCON_1_SMI_LOCK;
+ GenPmCon1AndMask = MAX_UINT16;
+ Status = S3SaveState->Write (
+ S3SaveState,
+ EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE,
+ EfiBootScriptWidthUint16,
+ (UINT64)POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
+ &GenPmCon1OrMask,
+ &GenPmCon1AndMask
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR,
+ "%a: EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE: %r\n", __FUNCTION__,
+ Status));
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ }
+
+ DEBUG ((EFI_D_VERBOSE, "%a: boot script fragment saved\n", __FUNCTION__));
+ gBS->CloseEvent (Event);
+ mS3SaveStateInstalled = NULL;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
new file mode 100644
index 0000000000..19eb469657
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
@@ -0,0 +1,175 @@
+/** @file
+ PCH SPI SMM Driver implements the SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include "PchSpi.h"
+
+//
+// Global variables
+//
+GLOBAL_REMOVE_IF_UNREFERENCED SPI_INSTANCE *mSpiInstance;
+//
+// mPchSpiResvMmioAddr keeps the reserved MMIO range assiged to SPI.
+// In SMM it always set back the reserved MMIO address to SPI BAR0 to ensure the MMIO range
+// won't overlap with SMRAM range, and trusted.
+//
+GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mSpiResvMmioAddr;
+
+/**
+ <b>SPI Runtime SMM Module Entry Point</b>\n
+ - <b>Introduction</b>\n
+ The SPI SMM module provide a standard way for other modules to use the PCH SPI Interface in SMM.
+
+ - @pre
+ - EFI_SMM_BASE2_PROTOCOL
+ - Documented in System Management Mode Core Interface Specification .
+
+ - @result
+ The SPI SMM driver produces @link _PCH_SPI_PROTOCOL PCH_SPI_PROTOCOL @endlink with GUID
+ gPchSmmSpiProtocolGuid which is different from SPI RUNTIME driver.
+
+ - <b>Integration Check List</b>\n
+ - This driver supports Descriptor Mode only.
+ - This driver supports Hardware Sequence only.
+ - When using SMM SPI Protocol to perform flash access in an SMI handler,
+ and the SMI occurrence is asynchronous to normal mode code execution,
+ proper synchronization mechanism must be applied, e.g. disable SMI before
+ the normal mode SendSpiCmd() starts and re-enable SMI after
+ the normal mode SendSpiCmd() completes.
+ @note The implementation of SendSpiCmd() uses GBL_SMI_EN in
+ SMI_EN register (ABase + 30h) to disable and enable SMIs. But this may
+ not be effective as platform may well set the SMI_LOCK bit (i.e., PMC PCI Offset A0h [4]).
+ So the synchronization at caller level is likely needed.
+
+ @param[in] ImageHandle Image handle of this driver.
+ @param[in] SystemTable Global system service table.
+
+ @retval EFI_SUCCESS Initialization complete.
+ @exception EFI_UNSUPPORTED The chipset is unsupported by this driver.
+ @retval EFI_OUT_OF_RESOURCES Do not have enough resources to initialize the driver.
+ @retval EFI_DEVICE_ERROR Device error, driver exits abnormally.
+**/
+EFI_STATUS
+EFIAPI
+InstallPchSpi (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Init PCH spi reserved MMIO address.
+ //
+ mSpiResvMmioAddr = PCH_SPI_BASE_ADDRESS;
+
+ ///
+ /// Allocate pool for SPI protocol instance
+ ///
+ Status = gSmst->SmmAllocatePool (
+ EfiRuntimeServicesData, /// MemoryType don't care
+ sizeof (SPI_INSTANCE),
+ (VOID **) &mSpiInstance
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (mSpiInstance == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ ZeroMem ((VOID *) mSpiInstance, sizeof (SPI_INSTANCE));
+ ///
+ /// Initialize the SPI protocol instance
+ ///
+ Status = SpiProtocolConstructor (mSpiInstance);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+ //
+ // Install the SMM EFI_SPI_PROTOCOL interface
+ //
+ Status = gSmst->SmmInstallProtocolInterface (
+ &(mSpiInstance->Handle),
+ &gEfiSmmSpiProtocolGuid,
+ EFI_NATIVE_INTERFACE,
+ &(mSpiInstance->SpiProtocol)
+ );
+ if (EFI_ERROR (Status)) {
+ gSmst->SmmFreePool (mSpiInstance);
+ return EFI_DEVICE_ERROR;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Acquire PCH spi mmio address.
+ It is not expected for this BAR0 to change because the SPI device is hidden
+ from the OS for SKL PCH LP/H B stepping and above (refer to section 3.5.1),
+ but if it is ever different from the preallocated address, reassign it back.
+ In SMM, it always override the BAR0 and returns the reserved MMIO range for SPI.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval PchSpiBar0 return SPI MMIO address
+**/
+UINTN
+AcquireSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+ //
+ // SPIBAR0 will be different before and after PCI enum so need to get it from SPI BAR0 reg.
+ //
+ return mSpiResvMmioAddr;
+}
+
+/**
+ Release pch spi mmio address. Do nothing.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval None
+**/
+VOID
+ReleaseSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+}
+
+/**
+ This function is a hook for Spi to disable BIOS Write Protect
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in SMM phase
+
+**/
+EFI_STATUS
+EFIAPI
+DisableBiosWriteProtect (
+ VOID
+ )
+{
+
+ return EFI_SUCCESS;
+}
+
+/**
+ This function is a hook for Spi to enable BIOS Write Protect
+
+
+**/
+VOID
+EFIAPI
+EnableBiosWriteProtect (
+ VOID
+ )
+{
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
new file mode 100644
index 0000000000..f9d340d6df
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
@@ -0,0 +1,22 @@
+## @file
+# Copyright (c) 2014 - 2016 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ DEC_SPECIFICATION = 0x00010005
+ PACKAGE_NAME = ICH10Pkg
+ PACKAGE_GUID = 4E97AC4B-F64C-4008-BBDE-01CC3B0BAA6B
+ PACKAGE_VERSION = 0.91
+
+[Includes]
+ Include
+
+[Ppis]
+
+[Guids]
+ gEfiPchTokenSpaceGuid = { 0x89a1b278, 0xa1a1, 0x4df7, { 0xb1, 0x37, 0xde, 0x5a, 0xd7, 0xc4, 0x79, 0x13 } }
+[Protocols]
+ gEfiSmmSpiProtocolGuid = {0xbd75fe35, 0xfdce, 0x49d7, {0xa9, 0xdd, 0xb2, 0x6f, 0x1f, 0xc6, 0xb4, 0x37}}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
new file mode 100644
index 0000000000..c36360bcb0
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
@@ -0,0 +1,98 @@
+/** @file
+ The header file includes the common header files, defines
+ internal structure and functions used by SpiFlashCommonLib.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef __SPI_FLASH_COMMON_LIB_H__
+#define __SPI_FLASH_COMMON_LIB_H__
+
+#include <Uefi.h>
+#include <Library/BaseLib.h>
+#include <Library/PcdLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+
+#define SECTOR_SIZE_4KB 0x1000 // Common 4kBytes sector size
+/**
+ Enable block protection on the Serial Flash device.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashLock (
+ VOID
+ );
+
+/**
+ Read NumBytes bytes of data from the address specified by
+ PAddress into Buffer.
+
+ @param[in] Address The starting physical address of the read.
+ @param[in,out] NumBytes On input, the number of bytes to read. On output, the number
+ of bytes actually read.
+ @param[out] Buffer The destination data buffer for the read.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashRead (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write NumBytes bytes of data from Buffer to the address specified by
+ PAddresss.
+
+ @param[in] Address The starting physical address of the write.
+ @param[in,out] NumBytes On input, the number of bytes to write. On output,
+ the actual number of bytes written.
+ @param[in] Buffer The source data buffer for the write.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashWrite (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase the block starting at Address.
+
+ @param[in] Address The starting physical address of the block to be erased.
+ This library assume that caller garantee that the PAddress
+ is at the starting address of this block.
+ @param[in] NumBytes On input, the number of bytes of the logical block to be erased.
+ On output, the actual number of bytes erased.
+
+ @retval EFI_SUCCESS. Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashBlockErase (
+ IN UINTN Address,
+ IN UINTN *NumBytes
+ );
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
new file mode 100644
index 0000000000..552ce28d8c
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
@@ -0,0 +1,43 @@
+/** @file
+ Macros that simplify accessing PCH devices's PCI registers.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_ACCESS_H_
+#define _PCH_ACCESS_H_
+
+#include "PchReservedResources.h"
+
+#ifndef STALL_ONE_MICRO_SECOND
+#define STALL_ONE_MICRO_SECOND 1
+#endif
+#ifndef STALL_ONE_SECOND
+#define STALL_ONE_SECOND 1000000
+#endif
+
+
+///
+/// The default PCH PCI bus number
+///
+#define DEFAULT_PCI_BUS_NUMBER_PCH 0
+
+//
+// Default Vendor ID and Subsystem ID
+//
+#define V_PCH_INTEL_VENDOR_ID 0x8086 ///< Default Intel PCH Vendor ID
+#define V_PCH_DEFAULT_SID 0x7270 ///< Default Intel PCH Subsystem ID
+#define V_PCH_DEFAULT_SVID_SID (V_INTEL_VENDOR_ID + (V_PCH_DEFAULT_SID << 16)) ///< Default INTEL PCH Vendor ID and Subsystem ID
+
+//
+// Include device register definitions
+//
+
+#include "Register/PchRegsPmc.h"
+
+#include "Register/PchRegsSpi.h"
+
+#endif
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
new file mode 100644
index 0000000000..d503d130c8
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
@@ -0,0 +1,94 @@
+/** @file
+ Build time limits of PCH resources.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_LIMITS_H_
+#define _PCH_LIMITS_H_
+
+//
+// PCIe limits
+//
+#define PCH_MAX_PCIE_ROOT_PORTS PCH_H_PCIE_MAX_ROOT_PORTS
+#define PCH_H_PCIE_MAX_ROOT_PORTS 20
+#define PCH_LP_PCIE_MAX_ROOT_PORTS 12
+
+#define PCH_MAX_PCIE_CONTROLLERS PCH_H_PCIE_MAX_CONTROLLERS
+#define PCH_PCIE_CONTROLLER_PORTS 4
+#define PCH_H_PCIE_MAX_CONTROLLERS (PCH_H_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
+#define PCH_LP_PCIE_MAX_CONTROLLERS (PCH_LP_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
+
+//
+// PCIe clocks limits
+//
+#define PCH_LP_PCIE_MAX_CLK_REQ 6
+#define PCH_H_PCIE_MAX_CLK_REQ 16
+
+//
+// RST PCIe Storage Cycle Router limits
+//
+#define PCH_MAX_RST_PCIE_STORAGE_CR 3
+
+//
+// SATA limits
+//
+#define PCH_MAX_SATA_PORTS PCH_H_AHCI_MAX_PORTS
+#define PCH_H_AHCI_MAX_PORTS 8 ///< Max number of sata ports in SKL PCH H
+#define PCH_LP_AHCI_MAX_PORTS 3 ///< Max number of sata ports in SKL PCH LP
+#define PCH_SATA_MAX_DEVICES_PER_PORT 1 ///< Max support device numner per port, Port Multiplier is not support.
+
+//
+// USB limits
+//
+#define PCH_MAX_USB2_PORTS PCH_H_XHCI_MAX_USB2_PORTS
+
+#define PCH_H_XHCI_MAX_USB2_PHYSICAL_PORTS 14 ///< Max Physical Connector XHCI, not counting virtual ports like USB-R.
+#define PCH_LP_XHCI_MAX_USB2_PHYSICAL_PORTS 10 ///< Max Physical Connector XHCI, not counting virtual ports like USB-R.
+
+#define PCH_H_XHCI_MAX_USB2_PORTS 16 ///< 14 High Speed lanes + Including two ports reserved for USBr
+#define PCH_LP_XHCI_MAX_USB2_PORTS 12 ///< 10 High Speed lanes + Including two ports reserved for USBr
+
+#define PCH_MAX_USB3_PORTS PCH_H_XHCI_MAX_USB3_PORTS
+
+#define PCH_H_XHCI_MAX_USB3_PORTS 10 ///< 10 Super Speed lanes
+#define PCH_LP_XHCI_MAX_USB3_PORTS 6 ///< 6 Super Speed lanes
+
+#define PCH_XHCI_MAX_SSIC_PORT_COUNT 2 ///< 2 SSIC ports in SKL PCH-LP and SKL PCH-H
+
+//
+// SerialIo limits
+//
+#define PCH_SERIALIO_MAX_CONTROLLERS 11 ///< Number of SerialIo controllers, this includes I2C, SPI and UART
+#define PCH_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo I2C controllers
+#define PCH_LP_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo I2C controllers for PCH-LP
+#define PCH_H_SERIALIO_MAX_I2C_CONTROLLERS 4 ///< Number of SerialIo I2C controllers for PCH-H
+#define PCH_SERIALIO_MAX_SPI_CONTROLLERS 2 ///< Number of SerialIo SPI controllers
+#define PCH_SERIALIO_MAX_UART_CONTROLLERS 3 ///< Number of SerialIo UART controllers
+
+//
+// ISH limits
+//
+#define PCH_ISH_MAX_GP_PINS 8
+#define PCH_ISH_MAX_UART_CONTROLLERS 2
+#define PCH_ISH_MAX_I2C_CONTROLLERS 3
+#define PCH_ISH_MAX_SPI_CONTROLLERS 1
+
+//
+// SCS limits
+//
+#define PCH_SCS_MAX_CONTROLLERS 3 ///< Number of Storage and Communication Subsystem controllers, this includes eMMC, SDIO, SDCARD
+
+//
+// Flash Protection Range Register
+//
+#define PCH_FLASH_PROTECTED_RANGES 5
+
+//
+// Number of eSPI slaves
+//
+#define PCH_ESPI_MAX_SLAVE_ID 2
+#endif // _PCH_LIMITS_H_
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
new file mode 100644
index 0000000000..00139fc230
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
@@ -0,0 +1,60 @@
+/** @file
+ PCH preserved MMIO resource definitions.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_PRESERVED_RESOURCES_H_
+#define _PCH_PRESERVED_RESOURCES_H_
+
+/**
+ PCH preserved MMIO range, 24 MB, from 0xFD000000 to 0xFE7FFFFF
+
+ Detailed recommended static allocation
+ +-------------------------------------------------------------------------+
+ | Size | Start | End | Usage |
+ | 16 MB | 0xFD000000 | 0xFDFFFFFF | SBREG |
+ | 64 KB | 0xFE000000 | 0xFE00FFFF | PMC MBAR |
+ | 4 KB | 0xFE010000 | 0xFE010FFF | SPI BAR0 |
+ | 88 KB | 0xFE020000 | 0xFE035FFF | SerialIo BAR in ACPI mode |
+ | 24 KB | 0xFE036000 | 0xFE03BFFF | Unused |
+ | 4 KB | 0xFE03C000 | 0xFE03CFFF | Thermal Device in ACPI mode |
+ | 524 KB | 0xFE03D000 | 0xFE0BFFFF | Unused |
+ | 256 KB | 0xFE0C0000 | 0xFE0FFFFF | TraceHub FW BAR |
+ | 1 MB | 0xFE100000 | 0xFE1FFFFF | TraceHub MTB BAR |
+ | 2 MB | 0xFE200000 | 0xFE3FFFFF | TraceHub SW BAR |
+ | 64 KB | 0xFE400000 | 0xFE40FFFF | CIO2 MMIO BAR in ACPI mode |
+ | 2 MB - 64KB | 0xFE410000 | 0xFE5FFFFF | Unused |
+ | 2 MB | 0xFE600000 | 0xFE7FFFFF | Temp address |
+ +-------------------------------------------------------------------------+
+**/
+#define PCH_PRESERVED_BASE_ADDRESS 0xFD000000 ///< Pch preserved MMIO base address
+#define PCH_PRESERVED_MMIO_SIZE 0x01800000 ///< 24MB
+#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO base address
+#define PCH_PCR_MMIO_SIZE 0x01000000 ///< 16MB
+#define PCH_PWRM_BASE_ADDRESS 0xFE000000 ///< PMC MBAR MMIO base address
+#define PCH_PWRM_MMIO_SIZE 0x00010000 ///< 64KB
+#define PCH_SPI_BASE_ADDRESS 0xFED1C000 + 0x3800 ///< SPI MBAR MMIO base address
+#define PCH_SPI_MMIO_SIZE 0x00001000 ///< 4KB
+#define PCH_SERIAL_IO_BASE_ADDRESS 0xFE020000 ///< SerialIo MMIO base address
+#define PCH_SERIAL_IO_MMIO_SIZE 0x00016000 ///< 88KB
+#define PCH_THERMAL_BASE_ADDRESS 0xFE03C000 ///< Thermal Device in ACPI mode
+#define PCH_THERMAL_MMIO_SIZE 0x00001000 ///< 4KB
+#define PCH_TRACE_HUB_FW_BASE_ADDRESS 0xFE0C0000 ///< TraceHub FW MMIO base address
+#define PCH_TRACE_HUB_FW_MMIO_SIZE 0x00040000 ///< 256KB
+#define PCH_TRACE_HUB_MTB_BASE_ADDRESS 0xFE100000 ///< TraceHub MTB MMIO base address
+#define PCH_TRACE_HUB_MTB_MMIO_SIZE 0x00100000 ///< 1MB
+#define PCH_TRACE_HUB_SW_BASE_ADDRESS 0xFE200000 ///< TraceHub SW MMIO base address
+#define PCH_TRACE_HUB_SW_MMIO_SIZE 0x00200000 ///< 2MB
+#define PCH_CIO2_BASE_ADDRESS 0xFE400000 ///< CIO2 MMIO BAR in ACPI mode
+#define PCH_CIO2_MMIO_SIZE 0x00010000 ///< 64KB
+#define PCH_TEMP_BASE_ADDRESS 0xFE600000 ///< preserved temp address for misc usage
+#define PCH_TEMP_MMIO_SIZE 0x00200000 ///< 2MB
+
+#define RCRB 0xFED1C000
+#define SPIBAR 0x3800
+
+#endif // _PCH_PRESERVED_RESOURCES_H_
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
new file mode 100644
index 0000000000..cb5f26c47b
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
@@ -0,0 +1,295 @@
+/** @file
+ This file defines the PCH SPI Protocol which implements the
+ Intel(R) PCH SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_PROTOCOL_H_
+#define _PCH_SPI_PROTOCOL_H_
+
+//
+// Extern the GUID for protocol users.
+//
+extern EFI_GUID gEfiSpiProtocolGuid;
+extern EFI_GUID gEfiSmmSpiProtocolGuid;
+
+//
+// Forward reference for ANSI C compatibility
+//
+typedef struct _PCH_SPI_PROTOCOL EFI_SPI_PROTOCOL;
+
+//
+// SPI protocol data structures and definitions
+//
+
+/**
+ Flash Region Type
+**/
+typedef enum {
+ FlashRegionDescriptor,
+ FlashRegionBios,
+ FlashRegionMe,
+ FlashRegionGbE,
+ FlashRegionPlatformData,
+ FlashRegionDer,
+ FlashRegionAll,
+ FlashRegionMax
+} FLASH_REGION_TYPE;
+
+
+//
+// Protocol member functions
+//
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write data to the flash part. Remark: Erase may be needed before write to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_WRITE) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_ERASE) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ );
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_SFDP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ );
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_JEDEC_ID) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ );
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_WRITE_STATUS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ );
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_STATUS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ );
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_GET_REGION_ADDRESS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ );
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_READ_PCH_SOFTSTRAP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_READ_CPU_SOFTSTRAP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ These protocols/PPI allows a platform module to perform SPI operations through the
+ Intel PCH SPI Host Controller Interface.
+**/
+struct _PCH_SPI_PROTOCOL {
+ /**
+ This member specifies the revision of this structure. This field is used to
+ indicate backwards compatible changes to the protocol.
+ **/
+ UINT8 Revision;
+ PCH_SPI_FLASH_READ FlashRead; ///< Read data from the flash part.
+ PCH_SPI_FLASH_WRITE FlashWrite; ///< Write data to the flash part. Remark: Erase may be needed before write to the flash part.
+ PCH_SPI_FLASH_ERASE FlashErase; ///< Erase some area on the flash part.
+ PCH_SPI_FLASH_READ_SFDP FlashReadSfdp; ///< Read SFDP data from the flash part.
+ PCH_SPI_FLASH_READ_JEDEC_ID FlashReadJedecId; ///< Read Jedec Id from the flash part.
+ PCH_SPI_FLASH_WRITE_STATUS FlashWriteStatus; ///< Write the status register in the flash part.
+ PCH_SPI_FLASH_READ_STATUS FlashReadStatus; ///< Read status register in the flash part.
+ PCH_SPI_GET_REGION_ADDRESS GetRegionAddress; ///< Get the SPI region base and size
+ PCH_SPI_READ_PCH_SOFTSTRAP ReadPchSoftStrap; ///< Read PCH Soft Strap Values
+ PCH_SPI_READ_CPU_SOFTSTRAP ReadCpuSoftStrap; ///< Read CPU Soft Strap Values
+};
+
+/**
+ PCH SPI PPI/PROTOCOL revision number
+
+ Revision 1: Initial version
+**/
+#define PCH_SPI_SERVICES_REVISION 1
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
new file mode 100644
index 0000000000..e08721f405
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
@@ -0,0 +1,647 @@
+/** @file
+ Register names for PCH PMC device
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values within the bits
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, PCH registers are denoted by "_PCH_" in register names
+ - Registers / bits that are different between PCH generations are denoted by
+ "_PCH_[generation_name]_" in register/bit names.
+ - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit names.
+ Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit names.
+ e.g., "_PCH_H_", "_PCH_LP_"
+ Registers / bits names without _H_ or _LP_ apply for both H and LP.
+ - Registers / bits that are different between SKUs are denoted by "_[SKU_name]"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a PCH generation will be just named
+ as "_PCH_" without [generation_name] inserted.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_REGS_PMC_H_
+#define _PCH_REGS_PMC_H_
+
+//
+// PMC Registers (D31:F2)
+//
+#define PCI_DEVICE_NUMBER_PCH_PMC 31
+#define PCI_FUNCTION_NUMBER_PCH_PMC 2
+
+#define R_PCH_PMC_PM_DATA_BAR 0x10
+#define B_PCH_PMC_PM_DATA_BAR 0xFFFFC000
+#define R_PCH_PMC_ACPI_BASE 0x40
+#define B_PCH_PMC_ACPI_BASE_BAR 0xFFFC
+#define R_PCH_PMC_ACPI_CNT 0x44
+#define B_PCH_PMC_ACPI_CNT_PWRM_EN BIT8 ///< PWRM enable
+#define B_PCH_PMC_ACPI_CNT_ACPI_EN BIT7 ///< ACPI eanble
+#define B_PCH_PMC_ACPI_CNT_SCIS (BIT2 | BIT1 | BIT0) ///< SCI IRQ select
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ9 0
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ10 1
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ11 2
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ20 4
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ21 5
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ22 6
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ23 7
+#define R_PCH_PMC_PWRM_BASE 0x48
+#define B_PCH_PMC_PWRM_BASE_BAR 0xFFFF0000 ///< PWRM must be 64KB alignment to align the source decode.
+#define R_PCH_PMC_GEN_PMCON_A 0xA0
+#define B_PCH_PMC_GEN_PMCON_A_DC_PP_DIS BIT30
+#define B_PCH_PMC_GEN_PMCON_A_DSX_PP_DIS BIT29
+#define B_PCH_PMC_GEN_PMCON_A_AG3_PP_EN BIT28
+#define B_PCH_PMC_GEN_PMCON_A_SX_PP_EN BIT27
+#define B_PCH_PMC_GEN_PMCON_A_DISB BIT23
+#define B_PCH_PMC_GEN_PMCON_A_MEM_SR BIT21
+#define B_PCH_PMC_GEN_PMCON_A_MS4V BIT18
+#define B_PCH_PMC_GEN_PMCON_A_GBL_RST_STS BIT16
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_OPI_PLL_SD_INC0 BIT13
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_SPXB_CG_INC0 BIT12
+#define B_PCH_PMC_GEN_PMCON_A_BIOS_PCI_EXP_EN BIT10
+#define B_PCH_PMC_GEN_PMCON_A_PWRBTN_LVL BIT9
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_C0 BIT7
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_OPI_ON BIT6
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_BCLKREQ_ON BIT5
+#define B_PCH_PMC_GEN_PMCON_A_SMI_LOCK BIT4
+#define B_PCH_PMC_GEN_PMCON_A_ESPI_SMI_LOCK BIT3 ///< ESPI SMI lock
+#define B_PCH_PMC_GEN_PMCON_A_PER_SMI_SEL 0x0003
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_64S 0x0000
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_32S 0x0001
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_16S 0x0002
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_8S 0x0003
+#define R_PCH_PMC_GEN_PMCON_B 0xA4
+#define B_PCH_PMC_GEN_PMCON_B_SLPSX_STR_POL_LOCK BIT18 ///< Lock down SLP_S3/SLP_S4 Minimum Assertion width
+#define B_PCH_PMC_GEN_PMCON_B_ACPI_BASE_LOCK BIT17 ///< Lock ACPI BASE at 0x40, only cleared by reset when set
+#define B_PCH_PMC_GEN_PMCON_B_PM_DATA_BAR_DIS BIT16
+#define B_PCH_PMC_GEN_PMCON_B_PME_B0_S5_DIS BIT15
+#define B_PCH_PMC_GEN_PMCON_B_SUS_PWR_FLR BIT14
+#define B_PCH_PMC_GEN_PMCON_B_WOL_EN_OVRD BIT13
+#define B_PCH_PMC_GEN_PMCON_B_DISABLE_SX_STRETCH BIT12
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW 0xC00
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_60US 0x000
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_1MS 0x400
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_50MS 0x800
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_2S 0xC00
+#define B_PCH_PMC_GEN_PMCON_B_HOST_RST_STS BIT9
+#define B_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL 0xC0
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_64MS 0xC0
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_32MS 0x80
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_16MS 0x40
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_1_5MS 0x00
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW 0x30
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_1S 0x30
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_2S 0x20
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_3S 0x10
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_4S 0x00
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_ASE BIT3
+#define B_PCH_PMC_GEN_PMCON_B_RTC_PWR_STS BIT2
+#define B_PCH_PMC_GEN_PMCON_B_PWR_FLR BIT1
+#define B_PCH_PMC_GEN_PMCON_B_AFTERG3_EN BIT0
+#define R_PCH_PMC_BM_CX_CNF 0xA8
+#define B_PCH_PMC_BM_CX_CNF_STORAGE_BREAK_EN BIT31
+#define B_PCH_PMC_BM_CX_CNF_PCIE_BREAK_EN BIT30
+#define B_PCH_PMC_BM_CX_CNF_AZ_BREAK_EN BIT24
+#define B_PCH_PMC_BM_CX_CNF_DPSN_BREAK_EN BIT19
+#define B_PCH_PMC_BM_CX_CNF_XHCI_BREAK_EN BIT17
+#define B_PCH_PMC_BM_CX_CNF_SATA3_BREAK_EN BIT16
+#define B_PCH_PMC_BM_CX_CNF_SCRATCHPAD BIT15
+#define B_PCH_PMC_BM_CX_CNF_PHOLD_BM_STS_BLOCK BIT14
+#define B_PCH_PMC_BM_CX_CNF_MASK_CF BIT11
+#define B_PCH_PMC_BM_CX_CNF_BM_STS_ZERO_EN BIT10
+#define B_PCH_PMC_BM_CX_CNF_PM_SYNC_MSG_MODE BIT9
+#define R_PCH_PMC_ETR3 0xAC
+#define B_PCH_PMC_ETR3_CF9LOCK BIT31 ///< CF9h Lockdown
+#define B_PCH_PMC_ETR3_USB_CACHE_DIS BIT21
+#define B_PCH_PMC_ETR3_CF9GR BIT20 ///< CF9h Global Reset
+#define B_PCH_PMC_ETR3_SKIP_HOST_RST_HS BIT19
+#define B_PCH_PMC_ETR3_CWORWRE BIT18
+
+//
+// ACPI and legacy I/O register offsets from ACPIBASE
+//
+#define R_PCH_ACPI_PM1_STS 0x00
+#define S_PCH_ACPI_PM1_STS 2
+#define B_PCH_ACPI_PM1_STS_WAK BIT15
+#define B_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS BIT14
+#define B_PCH_ACPI_PM1_STS_PRBTNOR BIT11
+#define B_PCH_ACPI_PM1_STS_RTC BIT10
+#define B_PCH_ACPI_PM1_STS_PWRBTN BIT8
+#define B_PCH_ACPI_PM1_STS_GBL BIT5
+#define B_PCH_ACPI_PM1_STS_BM BIT4
+#define B_PCH_ACPI_PM1_STS_TMROF BIT0
+#define N_PCH_ACPI_PM1_STS_WAK 15
+#define N_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS 14
+#define N_PCH_ACPI_PM1_STS_PRBTNOR 11
+#define N_PCH_ACPI_PM1_STS_RTC 10
+#define N_PCH_ACPI_PM1_STS_PWRBTN 8
+#define N_PCH_ACPI_PM1_STS_GBL 5
+#define N_PCH_ACPI_PM1_STS_BM 4
+#define N_PCH_ACPI_PM1_STS_TMROF 0
+
+#define R_PCH_ACPI_PM1_EN 0x02
+#define S_PCH_ACPI_PM1_EN 2
+#define B_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS BIT14
+#define B_PCH_ACPI_PM1_EN_RTC BIT10
+#define B_PCH_ACPI_PM1_EN_PWRBTN BIT8
+#define B_PCH_ACPI_PM1_EN_GBL BIT5
+#define B_PCH_ACPI_PM1_EN_TMROF BIT0
+#define N_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS 14
+#define N_PCH_ACPI_PM1_EN_RTC 10
+#define N_PCH_ACPI_PM1_EN_PWRBTN 8
+#define N_PCH_ACPI_PM1_EN_GBL 5
+#define N_PCH_ACPI_PM1_EN_TMROF 0
+
+#define R_PCH_ACPI_PM1_CNT 0x04
+#define S_PCH_ACPI_PM1_CNT 4
+#define B_PCH_ACPI_PM1_CNT_SLP_EN BIT13
+#define B_PCH_ACPI_PM1_CNT_SLP_TYP (BIT12 | BIT11 | BIT10)
+#define V_PCH_ACPI_PM1_CNT_S0 0
+#define V_PCH_ACPI_PM1_CNT_S1 BIT10
+#define V_PCH_ACPI_PM1_CNT_S3 (BIT12 | BIT10)
+#define V_PCH_ACPI_PM1_CNT_S4 (BIT12 | BIT11)
+#define V_PCH_ACPI_PM1_CNT_S5 (BIT12 | BIT11 | BIT10)
+#define B_PCH_ACPI_PM1_CNT_GBL_RLS BIT2
+#define B_PCH_ACPI_PM1_CNT_BM_RLD BIT1
+#define B_PCH_ACPI_PM1_CNT_SCI_EN BIT0
+
+#define R_PCH_ACPI_PM1_TMR 0x08
+#define V_PCH_ACPI_TMR_FREQUENCY 3579545
+#define B_PCH_ACPI_PM1_TMR_VAL 0xFFFFFF
+#define V_PCH_ACPI_PM1_TMR_MAX_VAL 0x1000000 ///< The timer is 24 bit overflow
+
+#define R_PCH_SMI_EN 0x30
+#define S_PCH_SMI_EN 4
+#define B_PCH_SMI_EN_LEGACY_USB3 BIT31
+#define B_PCH_SMI_EN_GPIO_UNLOCK_SMI BIT27
+#define B_PCH_SMI_EN_LEGACY_USB2 BIT17
+#define B_PCH_SMI_EN_PERIODIC BIT14
+#define B_PCH_SMI_EN_TCO BIT13
+#define B_PCH_SMI_EN_MCSMI BIT11
+#define B_PCH_SMI_EN_BIOS_RLS BIT7
+#define B_PCH_SMI_EN_SWSMI_TMR BIT6
+#define B_PCH_SMI_EN_APMC BIT5
+#define B_PCH_SMI_EN_ON_SLP_EN BIT4
+#define B_PCH_SMI_EN_LEGACY_USB BIT3
+#define B_PCH_SMI_EN_BIOS BIT2
+#define B_PCH_SMI_EN_EOS BIT1
+#define B_PCH_SMI_EN_GBL_SMI BIT0
+#define N_PCH_SMI_EN_LEGACY_USB3 31
+#define N_PCH_SMI_EN_ESPI 28
+#define N_PCH_SMI_EN_GPIO_UNLOCK 27
+#define N_PCH_SMI_EN_INTEL_USB2 18
+#define N_PCH_SMI_EN_LEGACY_USB2 17
+#define N_PCH_SMI_EN_PERIODIC 14
+#define N_PCH_SMI_EN_TCO 13
+#define N_PCH_SMI_EN_MCSMI 11
+#define N_PCH_SMI_EN_BIOS_RLS 7
+#define N_PCH_SMI_EN_SWSMI_TMR 6
+#define N_PCH_SMI_EN_APMC 5
+#define N_PCH_SMI_EN_ON_SLP_EN 4
+#define N_PCH_SMI_EN_LEGACY_USB 3
+#define N_PCH_SMI_EN_BIOS 2
+#define N_PCH_SMI_EN_EOS 1
+#define N_PCH_SMI_EN_GBL_SMI 0
+
+#define R_PCH_SMI_STS 0x34
+#define S_PCH_SMI_STS 4
+#define B_PCH_SMI_STS_LEGACY_USB3 BIT31
+#define B_PCH_SMI_STS_GPIO_UNLOCK BIT27
+#define B_PCH_SMI_STS_SPI BIT26
+#define B_PCH_SMI_STS_MONITOR BIT21
+#define B_PCH_SMI_STS_PCI_EXP BIT20
+#define B_PCH_SMI_STS_PATCH BIT19
+#define B_PCH_SMI_STS_INTEL_USB2 BIT18
+#define B_PCH_SMI_STS_LEGACY_USB2 BIT17
+#define B_PCH_SMI_STS_SMBUS BIT16
+#define B_PCH_SMI_STS_SERIRQ BIT15
+#define B_PCH_SMI_STS_PERIODIC BIT14
+#define B_PCH_SMI_STS_TCO BIT13
+#define B_PCH_SMI_STS_DEVMON BIT12
+#define B_PCH_SMI_STS_MCSMI BIT11
+#define B_PCH_SMI_STS_GPIO_SMI BIT10
+#define B_PCH_SMI_STS_GPE0 BIT9
+#define B_PCH_SMI_STS_PM1_STS_REG BIT8
+#define B_PCH_SMI_STS_SWSMI_TMR BIT6
+#define B_PCH_SMI_STS_APM BIT5
+#define B_PCH_SMI_STS_ON_SLP_EN BIT4
+#define B_PCH_SMI_STS_LEGACY_USB BIT3
+#define B_PCH_SMI_STS_BIOS BIT2
+#define N_PCH_SMI_STS_LEGACY_USB3 31
+#define N_PCH_SMI_STS_ESPI 28
+#define N_PCH_SMI_STS_GPIO_UNLOCK 27
+#define N_PCH_SMI_STS_SPI 26
+#define N_PCH_SMI_STS_MONITOR 21
+#define N_PCH_SMI_STS_PCI_EXP 20
+#define N_PCH_SMI_STS_PATCH 19
+#define N_PCH_SMI_STS_INTEL_USB2 18
+#define N_PCH_SMI_STS_LEGACY_USB2 17
+#define N_PCH_SMI_STS_SMBUS 16
+#define N_PCH_SMI_STS_SERIRQ 15
+#define N_PCH_SMI_STS_PERIODIC 14
+#define N_PCH_SMI_STS_TCO 13
+#define N_PCH_SMI_STS_DEVMON 12
+#define N_PCH_SMI_STS_MCSMI 11
+#define N_PCH_SMI_STS_GPIO_SMI 10
+#define N_PCH_SMI_STS_GPE0 9
+#define N_PCH_SMI_STS_PM1_STS_REG 8
+#define N_PCH_SMI_STS_SWSMI_TMR 6
+#define N_PCH_SMI_STS_APM 5
+#define N_PCH_SMI_STS_ON_SLP_EN 4
+#define N_PCH_SMI_STS_LEGACY_USB 3
+#define N_PCH_SMI_STS_BIOS 2
+
+#define R_PCH_ACPI_GPE_CNTL 0x40
+#define B_PCH_ACPI_GPE_CNTL_SWGPE_CTRL BIT17
+
+#define R_PCH_DEVACT_STS 0x44
+#define S_PCH_DEVACT_STS 2
+#define B_PCH_DEVACT_STS_MASK 0x13E1
+#define B_PCH_DEVACT_STS_KBC BIT12
+#define B_PCH_DEVACT_STS_PIRQDH BIT9
+#define B_PCH_DEVACT_STS_PIRQCG BIT8
+#define B_PCH_DEVACT_STS_PIRQBF BIT7
+#define B_PCH_DEVACT_STS_PIRQAE BIT6
+#define B_PCH_DEVACT_STS_D0_TRP BIT0
+#define N_PCH_DEVACT_STS_KBC 12
+#define N_PCH_DEVACT_STS_PIRQDH 9
+#define N_PCH_DEVACT_STS_PIRQCG 8
+#define N_PCH_DEVACT_STS_PIRQBF 7
+#define N_PCH_DEVACT_STS_PIRQAE 6
+
+#define R_PCH_ACPI_PM2_CNT 0x50
+#define B_PCH_ACPI_PM2_CNT_ARB_DIS BIT0
+
+#define R_PCH_OC_WDT_CTL 0x54
+#define B_PCH_OC_WDT_CTL_RLD BIT31
+#define B_PCH_OC_WDT_CTL_ICCSURV_STS BIT25
+#define B_PCH_OC_WDT_CTL_NO_ICCSURV_STS BIT24
+#define B_PCH_OC_WDT_CTL_FORCE_ALL BIT15
+#define B_PCH_OC_WDT_CTL_EN BIT14
+#define B_PCH_OC_WDT_CTL_ICCSURV BIT13
+#define B_PCH_OC_WDT_CTL_LCK BIT12
+#define B_PCH_OC_WDT_CTL_TOV_MASK 0x3FF
+#define B_PCH_OC_WDT_CTL_FAILURE_STS BIT23
+#define B_PCH_OC_WDT_CTL_UNXP_RESET_STS BIT22
+#define B_PCH_OC_WDT_CTL_AFTER_POST 0x3F0000
+#define V_PCH_OC_WDT_CTL_STATUS_FAILURE 1
+#define V_PCH_OC_WDT_CTL_STATUS_OK 0
+
+#define R_PCH_ACPI_GPE0_STS_31_0 0x80
+#define R_PCH_ACPI_GPE0_STS_63_32 0x84
+#define R_PCH_ACPI_GPE0_STS_95_64 0x88
+#define R_PCH_ACPI_GPE0_STS_127_96 0x8C
+#define S_PCH_ACPI_GPE0_STS_127_96 4
+#define B_PCH_ACPI_GPE0_STS_127_96_WADT BIT18
+#define B_PCH_ACPI_GPE0_STS_127_96_LAN_WAKE BIT16
+#define B_PCH_ACPI_GPE0_STS_127_96_PME_B0 BIT13
+#define B_PCH_ACPI_GPE0_STS_127_96_ME_SCI BIT12
+#define B_PCH_ACPI_GPE0_STS_127_96_PME BIT11
+#define B_PCH_ACPI_GPE0_STS_127_96_BATLOW BIT10
+#define B_PCH_ACPI_GPE0_STS_127_96_PCI_EXP BIT9
+#define B_PCH_ACPI_GPE0_STS_127_96_RI BIT8
+#define B_PCH_ACPI_GPE0_STS_127_96_SMB_WAK BIT7
+#define B_PCH_ACPI_GPE0_STS_127_96_TC0SCI BIT6
+#define B_PCH_ACPI_GPE0_STS_127_96_SWGPE BIT2
+#define B_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG BIT1
+#define N_PCH_ACPI_GPE0_STS_127_96_PME_B0 13
+#define N_PCH_ACPI_GPE0_STS_127_96_PME 11
+#define N_PCH_ACPI_GPE0_STS_127_96_BATLOW 10
+#define N_PCH_ACPI_GPE0_STS_127_96_PCI_EXP 9
+#define N_PCH_ACPI_GPE0_STS_127_96_RI 8
+#define N_PCH_ACPI_GPE0_STS_127_96_SMB_WAK 7
+#define N_PCH_ACPI_GPE0_STS_127_96_TC0SCI 6
+#define N_PCH_ACPI_GPE0_STS_127_96_SWGPE 2
+#define N_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG 1
+
+#define R_PCH_ACPI_GPE0_EN_31_0 0x90
+#define R_PCH_ACPI_GPE0_EN_63_32 0x94
+#define R_PCH_ACPI_GPE0_EN_95_64 0x98
+#define R_PCH_ACPI_GPE0_EN_127_96 0x9C
+#define S_PCH_ACPI_GPE0_EN_127_96 4
+#define B_PCH_ACPI_GPE0_EN_127_96_WADT BIT18
+#define B_PCH_ACPI_GPE0_EN_127_96_LAN_WAKE BIT16
+#define B_PCH_ACPI_GPE0_EN_127_96_PME_B0 BIT13
+#define B_PCH_ACPI_GPE0_EN_127_96_ME_SCI BIT12
+#define B_PCH_ACPI_GPE0_EN_127_96_PME BIT11
+#define B_PCH_ACPI_GPE0_EN_127_96_BATLOW BIT10
+#define B_PCH_ACPI_GPE0_EN_127_96_PCI_EXP BIT9
+#define B_PCH_ACPI_GPE0_EN_127_96_RI BIT8
+#define B_PCH_ACPI_GPE0_EN_127_96_TC0SCI BIT6
+#define B_PCH_ACPI_GPE0_EN_127_96_SWGPE BIT2
+#define B_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG BIT1
+#define N_PCH_ACPI_GPE0_EN_127_96_PME_B0 13
+#define N_PCH_ACPI_GPE0_EN_127_96_USB3 12
+#define N_PCH_ACPI_GPE0_EN_127_96_PME 11
+#define N_PCH_ACPI_GPE0_EN_127_96_BATLOW 10
+#define N_PCH_ACPI_GPE0_EN_127_96_PCI_EXP 9
+#define N_PCH_ACPI_GPE0_EN_127_96_RI 8
+#define N_PCH_ACPI_GPE0_EN_127_96_TC0SCI 6
+#define N_PCH_ACPI_GPE0_EN_127_96_SWGPE 2
+#define N_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG 1
+
+
+//
+// TCO register I/O map
+//
+#define R_PCH_TCO_RLD 0x0
+#define R_PCH_TCO_DAT_IN 0x2
+#define R_PCH_TCO_DAT_OUT 0x3
+#define R_PCH_TCO1_STS 0x04
+#define S_PCH_TCO1_STS 2
+#define B_PCH_TCO1_STS_DMISERR BIT12
+#define B_PCH_TCO1_STS_DMISMI BIT10
+#define B_PCH_TCO1_STS_DMISCI BIT9
+#define B_PCH_TCO1_STS_BIOSWR BIT8
+#define B_PCH_TCO1_STS_NEWCENTURY BIT7
+#define B_PCH_TCO1_STS_TIMEOUT BIT3
+#define B_PCH_TCO1_STS_TCO_INT BIT2
+#define B_PCH_TCO1_STS_SW_TCO_SMI BIT1
+#define B_PCH_TCO1_STS_NMI2SMI BIT0
+#define N_PCH_TCO1_STS_DMISMI 10
+#define N_PCH_TCO1_STS_BIOSWR 8
+#define N_PCH_TCO1_STS_NEWCENTURY 7
+#define N_PCH_TCO1_STS_TIMEOUT 3
+#define N_PCH_TCO1_STS_SW_TCO_SMI 1
+#define N_PCH_TCO1_STS_NMI2SMI 0
+
+#define R_PCH_TCO2_STS 0x06
+#define S_PCH_TCO2_STS 2
+#define B_PCH_TCO2_STS_SMLINK_SLV_SMI BIT4
+#define B_PCH_TCO2_STS_BAD_BIOS BIT3
+#define B_PCH_TCO2_STS_BOOT BIT2
+#define B_PCH_TCO2_STS_SECOND_TO BIT1
+#define B_PCH_TCO2_STS_INTRD_DET BIT0
+#define N_PCH_TCO2_STS_INTRD_DET 0
+
+#define R_PCH_TCO1_CNT 0x08
+#define S_PCH_TCO1_CNT 2
+#define B_PCH_TCO_CNT_LOCK BIT12
+#define B_PCH_TCO_CNT_TMR_HLT BIT11
+#define B_PCH_TCO_CNT_NMI2SMI_EN BIT9
+#define B_PCH_TCO_CNT_NMI_NOW BIT8
+#define N_PCH_TCO_CNT_NMI2SMI_EN 9
+
+#define R_PCH_TCO2_CNT 0x0A
+#define S_PCH_TCO2_CNT 2
+#define B_PCH_TCO2_CNT_OS_POLICY 0x0030
+#define B_PCH_TCO2_CNT_GPI11_ALERT_DISABLE 0x0008
+#define B_PCH_TCO2_CNT_INTRD_SEL 0x0006
+#define N_PCH_TCO2_CNT_INTRD_SEL 2
+
+#define R_PCH_TCO_MESSAGE1 0x0C
+#define R_PCH_TCO_MESSAGE2 0x0D
+#define R_PCH_TCO_WDCNT 0x0E
+#define R_PCH_TCO_SW_IRQ_GEN 0x10
+#define B_PCH_TCO_IRQ12_CAUSE BIT1
+#define B_PCH_TCO_IRQ1_CAUSE BIT0
+#define R_PCH_TCO_TMR 0x12
+
+//
+// PWRM Registers
+//
+#define R_PCH_WADT_AC 0x0 ///< Wake Alarm Device Timer: AC
+#define R_PCH_WADT_DC 0x4 ///< Wake Alarm Device Timer: DC
+#define R_PCH_WADT_EXP_AC 0x8 ///< Wake Alarm Device Expired Timer: AC
+#define R_PCH_WADT_EXP_DC 0xC ///< Wake Alarm Device Expired Timer: DC
+#define R_PCH_PWRM_PRSTS 0x10 ///< Power and Reset Status
+#define B_PCH_PWRM_PRSTS_VE_WD_TMR_STS BIT7 ///< VE Watchdog Timer Status
+#define B_PCH_PWRM_PRSTS_WOL_OVR_WK_STS BIT5
+#define B_PCH_PWRM_PRSTS_FIELD_1 BIT4
+#define B_PCH_PWRM_PRSTS_ME_WAKE_STS BIT0
+#define R_PCH_PWRM_14 0x14
+#define R_PCH_PWRM_CFG 0x18 ///< Power Management Configuration
+#define B_PCH_PWRM_CFG_ALLOW_24_OSC_SD BIT29 ///< Allow 24MHz Crystal Oscillator Shutdown
+#define B_PCH_PWRM_CFG_ALLOW_USB2_CORE_PG BIT25 ///< Allow USB2 Core Power Gating
+#define B_PCH_PWRM_CFG_RTC_DS_WAKE_DIS BIT21 ///< RTC Wake from Deep S4/S5 Disable
+#define B_PCH_PWRM_CFG_SSMAW_MASK (BIT19 | BIT18) ///< SLP_SUS# Min Assertion Width
+#define V_PCH_PWRM_CFG_SSMAW_4S (BIT19 | BIT18) ///< 4 seconds
+#define V_PCH_PWRM_CFG_SSMAW_1S BIT19 ///< 1 second
+#define V_PCH_PWRM_CFG_SSMAW_0_5S BIT18 ///< 0.5 second (500ms)
+#define V_PCH_PWRM_CFG_SSMAW_0S 0 ///< 0 second
+#define B_PCH_PWRM_CFG_SAMAW_MASK (BIT17 | BIT16) ///< SLP_A# Min Assertion Width
+#define V_PCH_PWRM_CFG_SAMAW_2S (BIT17 | BIT16) ///< 2 seconds
+#define V_PCH_PWRM_CFG_SAMAW_98ms BIT17 ///< 98ms
+#define V_PCH_PWRM_CFG_SAMAW_4S BIT16 ///< 4 seconds
+#define V_PCH_PWRM_CFG_SAMAW_0S 0 ///< 0 second
+#define B_PCH_PWRM_CFG_RPCD_MASK (BIT9 | BIT8) ///< Reset Power Cycle Duration
+#define V_PCH_PWRM_CFG_RPCD_1S (BIT9 | BIT8) ///< 1-2 seconds
+#define V_PCH_PWRM_CFG_RPCD_2S BIT9 ///< 2-3 seconds
+#define V_PCH_PWRM_CFG_RPCD_3S BIT8 ///< 3-4 seconds
+#define V_PCH_PWRM_CFG_RPCD_4S 0 ///< 4-5 seconds (Default)
+#define R_PCH_PWRM_PCH_PM_STS 0x1C ///< Contains misc. fields used to record PCH power management events
+#define B_PCH_PWRM_PCH_PM_STS_PMC_MSG_FULL_STS BIT24 ///< MTPMC transport mechanism full indication
+#define R_PCH_PWRM_MTPMC 0x20 ///< Message to PMC
+#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_0_15 0xE ///< Command to override lanes 0-15 power gating
+#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_16_31 0xF ///< Command to override lanes 16-31 power gating
+#define B_PCH_PWRM_MTPMC_PG_CMD_DATA 0xFFFF0000 ///< Data part of PowerGate Message to PMC
+#define N_PCH_PWRM_MTPMC_PG_CMD_DATA 16
+#define R_PCH_PWRM_PCH_PM_STS2 0x24 ///< PCH Power Management Status
+#define R_PCH_PWRM_S3_PWRGATE_POL 0x28 ///< S3 Power Gating Policies
+#define B_PCH_PWRM_S3DC_GATE_SUS BIT1 ///< Deep S3 Enable in DC Mode
+#define B_PCH_PWRM_S3AC_GATE_SUS BIT0 ///< Deep S3 Enable in AC Mode
+#define R_PCH_PWRM_S4_PWRGATE_POL 0x2C ///< Deep S4 Power Policies
+#define B_PCH_PWRM_S4DC_GATE_SUS BIT1 ///< Deep S4 Enable in DC Mode
+#define B_PCH_PWRM_S4AC_GATE_SUS BIT0 ///< Deep S4 Enable in AC Mode
+#define R_PCH_PWRM_S5_PWRGATE_POL 0x30 ///< Deep S5 Power Policies
+#define B_PCH_PWRM_S5DC_GATE_SUS BIT15 ///< Deep S5 Enable in DC Mode
+#define B_PCH_PWRM_S5AC_GATE_SUS BIT14 ///< Deep S5 Enable in AC Mode
+#define R_PCH_PWRM_DSX_CFG 0x34 ///< Deep SX Configuration
+#define B_PCH_PWRM_DSX_CFG_WAKE_PIN_DSX_EN BIT2 ///< WAKE# Pin DeepSx Enable
+#define B_PCH_PWRM_DSX_CFG_ACPRES_PD_DSX_DIS BIT1 ///< AC_PRESENT pin pulldown in DeepSx disable
+#define B_PCH_PWRM_DSX_CFG_LAN_WAKE_EN BIT0 ///< LAN_WAKE Pin DeepSx Enable
+#define R_PCH_PWRM_CFG2 0x3C ///< Power Management Configuration Reg 2
+#define B_PCH_PWRM_CFG2_PBOP (BIT31 | BIT30 | BIT29) ///< Power Button Override Period (PBOP)
+#define N_PCH_PWRM_CFG2_PBOP 29 ///< Power Button Override Period (PBOP)
+#define B_PCH_PWRM_CFG2_PB_DIS BIT28 ///< Power Button Native Mode Disable (PB_DIS)
+#define B_PCH_PWRM_CFG2_DRAM_RESET_CTL BIT26 ///< DRAM RESET# control
+#define R_PCH_PWRM_EN_SN_SLOW_RING 0x48 ///< Enable Snoop Request to SLOW_RING
+#define R_PCH_PWRM_EN_SN_SLOW_RING2 0x4C ///< Enable Snoop Request to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_SN_SA 0x50 ///< Enable Snoop Request to SA
+#define R_PCH_PWRM_EN_SN_SA2 0x54 ///< Enable Snoop Request to SA 2nd Reg
+#define R_PCH_PWRM_EN_SN_SLOW_RING_CF 0x58 ///< Enable Snoop Request to SLOW_RING_CF
+#define R_PCH_PWRM_EN_NS_SA 0x68 ///< Enable Non-Snoop Request to SA
+#define R_PCH_PWRM_EN_CW_SLOW_RING 0x80 ///< Enable Clock Wake to SLOW_RING
+#define R_PCH_PWRM_EN_CW_SLOW_RING2 0x84 ///< Enable Clock Wake to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_CW_SA 0x88 ///< Enable Clock Wake to SA
+#define R_PCH_PWRM_EN_CW_SA2 0x8C ///< Enable Clock Wake to SA 2nd Reg
+#define R_PCH_PWRM_EN_CW_SLOW_RING_CF 0x98 ///< Enable Clock Wake to SLOW_RING_CF
+#define R_PCH_PWRM_EN_PA_SLOW_RING 0xA8 ///< Enable Pegged Active to SLOW_RING
+#define R_PCH_PWRM_EN_PA_SLOW_RING2 0xAC ///< Enable Pegged Active to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_PA_SA 0xB0 ///< Enable Pegged Active to SA
+#define R_PCH_PWRM_EN_PA_SA2 0xB4 ///< Enable Pegged Active to SA 2nd Reg
+#define R_PCH_PWRM_EN_MISC_EVENT 0xC0 ///< Enable Misc PM_SYNC Events
+#define R_PCH_PWRM_PMSYNC_TPR_CONFIG 0xC4
+#define B_PCH_PWRM_PMSYNC_TPR_CONFIG_LOCK BIT31
+#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_EN BIT26
+#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE (BIT25 | BIT24)
+#define N_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE 24
+#define V_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE_1 1
+#define R_PCH_PWRM_PMSYNC_MISC_CFG 0xC8
+#define B_PCH_PWRM_PMSYNC_PM_SYNC_LOCK BIT15 ///< PM_SYNC Configuration Lock
+#define B_PCH_PWRM_PMSYNC_GPIO_D_SEL BIT11
+#define B_PCH_PWRM_PMSYNC_GPIO_C_SEL BIT10
+#define R_PCH_PWRM_PM_SYNC_STATE_HYS 0xD0 ///< PM_SYNC State Hysteresis
+#define R_PCH_PWRM_PM_SYNC_MODE 0xD4 ///< PM_SYNC Pin Mode
+#define R_PCH_PWRM_CFG3 0xE0 ///< Power Management Configuration Reg 3
+#define B_PCH_PWRM_CFG3_DSX_WLAN_PP_EN BIT16 ///< Deep-Sx WLAN Phy Power Enable
+#define B_PCH_PWRM_CFG3_HOST_WLAN_PP_EN BIT17 ///< Host Wireless LAN Phy Power Enable
+#define B_PCH_PWRM_CFG3_PWRG_LOCK BIT2 ///< Lock power gating override messages
+#define R_PCH_PWRM_PM_DOWN_PPB_CFG 0xE4 ///< PM_DOWN PCH_POWER_BUDGET CONFIGURATION
+#define R_PCH_PWRM_CFG4 0xE8 ///< Power Management Configuration Reg 4
+#define B_PCH_PWRM_CFG4_U2_PHY_PG_EN BIT30 ///< USB2 PHY SUS Well Power Gating Enable
+#define B_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR (0x000001FF) ///< CPU I/O VR Ramp Duration, [8:0]
+#define N_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR 0
+#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_70US 0x007
+#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_240US 0x018
+#define R_PCH_PWRM_CPU_EPOC 0xEC
+#define R_PCH_PWRM_VR_MISC_CTL 0x100
+#define B_PCH_PWRM_VR_MISC_CTL_VIDSOVEN BIT3
+#define R_PCH_PWRM_GPIO_CFG 0x120
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW2 (BIT11 | BIT10 | BIT9 | BIT8)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW2 8
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW1 (BIT7 | BIT6 | BIT5 | BIT4)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW1 4
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW0 (BIT3 | BIT2 | BIT1 | BIT0)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW0 0
+#define R_PCH_PWRM_PM_SYNC_MODE_C0 0xF4 ///< PM_SYNC Pin Mode in C0
+#define R_PCH_PWRM_ACPI_TMR_CTL 0xFC
+#define B_PCH_PWRM_ACPI_TMR_DIS BIT1
+#define R_PCH_PWRM_124 0x124
+#define R_PCH_PWRM_SLP_S0_RESIDENCY_COUNTER 0x13C
+#define R_PCH_PWRM_MODPHY_PM_CFG1 0x200
+#define R_PCH_PWRM_MODPHY_PM_CFG1_MLSXSWPGP 0xFFFF
+#define R_PCH_PWRM_MODPHY_PM_CFG2 0x204 ///< ModPHY Power Management Configuration Reg 2
+#define B_PCH_PWRM_MODPHY_PM_CFG2_MLSPDDGE BIT30 ///< ModPHY Lane SUS Power Domain Dynamic Gating Enable
+#define B_PCH_PWRM_MODPHY_PM_CFG2_EMFC BIT29 ///< Enable ModPHY FET Control
+#define B_PCH_PWRM_MODPHY_PM_CFG2_EFRT (BIT28 | BIT27 | BIT26 | BIT25 | BIT24) ///< External FET Ramp Time
+#define N_PCH_PWRM_MODPHY_PM_CFG2_EFRT 24
+#define V_PCH_PWRM_MODPHY_PM_CFG2_EFRT_200US 0x0A
+#define B_PCH_PWRM_MODPHY_PM_CFG2_ASLOR_UFS BIT16 ///< UFS ModPHY SPD SPD Override
+#define R_PCH_PWRM_MODPHY_PM_CFG3 0x208 ///< ModPHY Power Management Configuration Reg 3
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_UFS BIT16 ///< UFS ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XDCI BIT15 ///< xDCI ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XHCI BIT14 ///< xHCI ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_GBE BIT13 ///< GbE ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_SATA BIT12 ///< SATA ModPHY SPD RT Request
+#define R_PCH_PWRM_30C 0x30C
+#define R_PCH_PWRM_OBFF_CFG 0x314 ///< OBFF Configuration
+#define R_PCH_PWRM_31C 0x31C
+#define R_PCH_PWRM_CPPM_MISC_CFG 0x320 ///< CPPM Miscellaneous Configuration
+#define R_PCH_PWRM_CPPM_CG_POL1A 0x324 ///< CPPM Clock Gating Policy Reg 1
+#define R_PCH_PWRM_CPPM_CG_POL2A 0x340 ///< CPPM Clock Gating Policy Reg 3
+#define R_PCH_PWRM_34C 0x34C
+#define R_PCH_PWRM_CPPM_CG_POL3A 0x3A8 ///< CPPM Clock Gating Policy Reg 5
+#define B_PCH_PWRM_CPPM_CG_POLXA_CPPM_GX_QUAL BIT30 ///< CPPM Shutdown Qualifier Enable for Clock Source Group X
+#define B_PCH_PWRM_CPPM_CG_POLXA_LTR_GX_THRESH (0x000001FF) ///< LTR Threshold for Clock Source Group X, [8:0]
+#define R_PCH_PWRM_3D0 0x3D0
+#define R_PCH_PWRM_CPPM_MPG_POL1A 0x3E0 ///< CPPM ModPHY Gating Policy Reg 1A
+#define B_PCH_PWRM_CPPM_MPG_POL1A_CPPM_MODPHY_QUAL BIT30 ///< CPPM Shutdown Qualifier Enable for ModPHY
+#define B_PCH_PWRM_CPPM_MPG_POL1A_LT_MODPHY_SEL BIT29 ///< ASLT/PLT Selection for ModPHY
+#define B_PCH_PWRM_CPPM_MPG_POL1A_LTR_MODPHY_THRESH (0x000001FF) ///< LTR Threshold for ModPHY, [8:0]
+#define R_PCH_PWRM_CS_SD_CTL1 0x3E8 ///< Clock Source Shutdown Control Reg 1
+#define B_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG (BIT22 | BIT21 | BIT20) ///< Clock Source 5 Control Configuration
+#define N_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG 20
+#define B_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG (BIT2 | BIT1 | BIT0) ///< Clock Source 1 Control Configuration
+#define N_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG 0
+#define R_PCH_PWRM_CS_SD_CTL2 0x3EC ///< Clock Source Shutdown Control Reg 2
+#define R_PCH_PWRM_HSWPGCR1 0x5D0
+#define B_PCH_PWRM_SW_PG_CTRL_LOCK BIT31
+#define B_PCH_PWRM_DFX_SW_PG_CTRL BIT0
+#define R_PCH_PWRM_600 0x600
+#define R_PCH_PWRM_604 0x604
+#define R_PCH_PWRM_ST_PG_FDIS_PMC_1 0x620 ///< Static PG Related Function Disable Register 1
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ST_FDIS_LK BIT31 ///< Static Function Disable Lock (ST_FDIS_LK)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_CAM_FDIS_PMC BIT6 ///< Camera Function Disable (PMC Version) (CAM_FDIS_PMC)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ISH_FDIS_PMC BIT5 ///< SH Function Disable (PMC Version) (ISH_FDIS_PMC)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_GBE_FDIS_PMC BIT0 ///< GBE Function Disable (PMC Version) (GBE_FDIS_PMC)
+#define R_PCH_PWRM_ST_PG_FDIS_PMC_2 0x624 ///< Static Function Disable Control Register 2
+#define V_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_FDIS_PMC 0x7FF ///< Static Function Disable Control Register 2
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI1_FDIS_PMC BIT10 ///< SerialIo Controller GSPI Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI0_FDIS_PMC BIT9 ///< SerialIo Controller GSPI Device 0 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART2_FDIS_PMC BIT8 ///< SerialIo Controller UART Device 2 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART1_FDIS_PMC BIT7 ///< SerialIo Controller UART Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART0_FDIS_PMC BIT6 ///< SerialIo Controller UART Device 0 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C5_FDIS_PMC BIT5 ///< SerialIo Controller I2C Device 5 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C4_FDIS_PMC BIT4 ///< SerialIo Controller I2C Device 4 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C3_FDIS_PMC BIT3 ///< SerialIo Controller I2C Device 3 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C2_FDIS_PMC BIT2 ///< SerialIo Controller I2C Device 2 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C1_FDIS_PMC BIT1 ///< SerialIo Controller I2C Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C0_FDIS_PMC BIT0 ///< SerialIo Controller I2C Device 0 Function Disable
+#define R_PCH_PWRM_NST_PG_FDIS_1 0x628
+#define B_PCH_PWRM_NST_PG_FDIS_1_SCC_FDIS_PMC BIT25 ///< SCC Function Disable. This is only avaiable in B0 onward.
+#define B_PCH_PWRM_NST_PG_FDIS_1_XDCI_FDIS_PMC BIT24 ///< XDCI Function Disable. This is only avaiable in B0 onward.
+#define B_PCH_PWRM_NST_PG_FDIS_1_ADSP_FDIS_PMC BIT23 ///< ADSP Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_SATA_FDIS_PMC BIT22 ///< SATA Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C3_FDIS_PMC BIT13 ///< PCIe Controller C Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C2_FDIS_PMC BIT12 ///< PCIe Controller C Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C1_FDIS_PMC BIT11 ///< PCIe Controller C Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C0_FDIS_PMC BIT10 ///< PCIe Controller C Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B3_FDIS_PMC BIT9 ///< PCIe Controller B Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B2_FDIS_PMC BIT8 ///< PCIe Controller B Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B1_FDIS_PMC BIT7 ///< PCIe Controller B Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B0_FDIS_PMC BIT6 ///< PCIe Controller B Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A3_FDIS_PMC BIT5 ///< PCIe Controller A Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A2_FDIS_PMC BIT4 ///< PCIe Controller A Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A1_FDIS_PMC BIT3 ///< PCIe Controller A Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A0_FDIS_PMC BIT2 ///< PCIe Controller A Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_XHCI_FDIS_PMC BIT0 ///< XHCI Function Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_1 0x640 ///< Fuse Disable Read 1 Register
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E3_FUSE_DIS BIT21 ///< PCIe Controller E Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E2_FUSE_DIS BIT20 ///< PCIe Controller E Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E1_FUSE_DIS BIT19 ///< PCIe Controller E Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E0_FUSE_DIS BIT18 ///< PCIe Controller E Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D3_FUSE_DIS BIT17 ///< PCIe Controller D Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D2_FUSE_DIS BIT16 ///< PCIe Controller D Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D1_FUSE_DIS BIT15 ///< PCIe Controller D Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D0_FUSE_DIS BIT14 ///< PCIe Controller D Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C3_FUSE_DIS BIT13 ///< PCIe Controller C Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C2_FUSE_DIS BIT12 ///< PCIe Controller C Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C1_FUSE_DIS BIT11 ///< PCIe Controller C Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C0_FUSE_DIS BIT10 ///< PCIe Controller C Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B3_FUSE_DIS BIT9 ///< PCIe Controller B Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B2_FUSE_DIS BIT8 ///< PCIe Controller B Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B1_FUSE_DIS BIT7 ///< PCIe Controller B Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B0_FUSE_DIS BIT6 ///< PCIe Controller B Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A3_FUSE_DIS BIT5 ///< PCIe Controller A Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A2_FUSE_DIS BIT4 ///< PCIe Controller A Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A1_FUSE_DIS BIT3 ///< PCIe Controller A Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A0_FUSE_DIS BIT2 ///< PCIe Controller A Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_XHCI_FUSE_DIS BIT0 ///< XHCI Fuse Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_2 0x644 ///< Fuse Disable Read 2 Register
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPC_SS_DIS BIT25 ///< SPC Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPB_SS_DIS BIT24 ///< SPB Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPA_SS_DIS BIT23 ///< SPA Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_PSTH_FUSE_SS_DIS BIT21 ///< PSTH Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_DMI_FUSE_SS_DIS BIT20 ///< DMI Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_OTG_FUSE_SS_DIS BIT19 ///< OTG Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_XHCI_SS_DIS BIT18 ///< XHCI Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_FIA_FUSE_SS_DIS BIT17 ///< FIA Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_DSP_FUSE_SS_DIS BIT16 ///< DSP Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SATA_FUSE_SS_DIS BIT15 ///< SATA Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ICC_FUSE_SS_DIS BIT14 ///< ICC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_LPC_FUSE_SS_DIS BIT13 ///< LPC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_RTC_FUSE_SS_DIS BIT12 ///< RTC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_P2S_FUSE_SS_DIS BIT11 ///< P2S Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_TRSB_FUSE_SS_DIS BIT10 ///< TRSB Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SMB_FUSE_SS_DIS BIT9 ///< SMB Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ITSS_FUSE_SS_DIS BIT8 ///< ITSS Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SERIALIO_FUSE_SS_DIS BIT6 ///< SerialIo Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SCC_FUSE_SS_DIS BIT4 ///< SCC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_P2D_FUSE_SS_DIS BIT3 ///< P2D Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_CAM_FUSE_SS_DIS BIT2 ///< Camera Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ISH_FUSE_SS_DIS BIT1 ///< ISH Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_GBE_FUSE_SS_DIS BIT0 ///< GBE Fuse or Soft Strap Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_3 0x648 ///< Static PG Fuse and Soft Strap Disable Read Register 3
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA3_FUSE_SS_DIS BIT3 ///< PNCRA3 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA2_FUSE_SS_DIS BIT2 ///< PNCRA2 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA1_FUSE_SS_DIS BIT1 ///< PNCRA1 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA_FUSE_SS_DIS BIT0 ///< PNCRA Fuse or Soft Strap Disable
+
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
new file mode 100644
index 0000000000..a727aae927
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
@@ -0,0 +1,304 @@
+/** @file
+ Register names for PCH SPI device.
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values within the bits
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, PCH registers are denoted by "_PCH_" in register names
+ - Registers / bits that are different between PCH generations are denoted by
+ "_PCH_[generation_name]_" in register/bit names.
+ - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit names.
+ Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit names.
+ e.g., "_PCH_H_", "_PCH_LP_"
+ Registers / bits names without _H_ or _LP_ apply for both H and LP.
+ - Registers / bits that are different between SKUs are denoted by "_[SKU_name]"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a PCH generation will be just named
+ as "_PCH_" without [generation_name] inserted.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_REGS_SPI_H_
+#define _PCH_REGS_SPI_H_
+
+//
+// SPI Registers (D31:F5)
+//
+
+#define PCI_DEVICE_NUMBER_PCH_SPI 31
+#define PCI_FUNCTION_NUMBER_PCH_SPI 5
+
+#define R_PCH_SPI_BAR0 0x10
+#define B_PCH_SPI_BAR0_MASK 0x0FFF
+
+#define R_PCH_SPI_BDE 0xD8
+#define B_PCH_SPI_BDE_F8 0x8000
+#define B_PCH_SPI_BDE_F0 0x4000
+#define B_PCH_SPI_BDE_E8 0x2000
+#define B_PCH_SPI_BDE_E0 0x1000
+#define B_PCH_SPI_BDE_D8 0x0800
+#define B_PCH_SPI_BDE_D0 0x0400
+#define B_PCH_SPI_BDE_C8 0x0200
+#define B_PCH_SPI_BDE_C0 0x0100
+#define B_PCH_SPI_BDE_LEG_F 0x0080
+#define B_PCH_SPI_BDE_LEG_E 0x0040
+#define B_PCH_SPI_BDE_70 0x0008
+#define B_PCH_SPI_BDE_60 0x0004
+#define B_PCH_SPI_BDE_50 0x0002
+#define B_PCH_SPI_BDE_40 0x0001
+
+#define R_PCH_SPI_BC 0xDC
+#define S_PCH_SPI_BC 4
+#define N_PCH_SPI_BC_ASE_BWP 11
+#define B_PCH_SPI_BC_ASE_BWP BIT11
+#define N_PCH_SPI_BC_ASYNC_SS 10
+#define B_PCH_SPI_BC_ASYNC_SS BIT10
+#define B_PCH_SPI_BC_OSFH BIT9 ///< OS Function Hide
+#define N_PCH_SPI_BC_SYNC_SS 8
+#define B_PCH_SPI_BC_SYNC_SS BIT8
+#define B_PCH_SPI_BC_BILD BIT7
+#define B_PCH_SPI_BC_BBS BIT6 ///< Boot BIOS strap
+#define N_PCH_SPI_BC_BBS 6
+#define V_PCH_SPI_BC_BBS_SPI 0 ///< Boot BIOS strapped to SPI
+#define V_PCH_SPI_BC_BBS_LPC 1 ///< Boot BIOS strapped to LPC
+#define B_PCH_SPI_BC_EISS BIT5 ///< Enable InSMM.STS
+#define B_PCH_SPI_BC_TSS BIT4
+#define B_PCH_SPI_BC_SRC (BIT3 | BIT2)
+#define N_PCH_SPI_BC_SRC 2
+#define V_PCH_SPI_BC_SRC_PREF_EN_CACHE_EN 0x02 ///< Prefetching and Caching enabled
+#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_DIS 0x01 ///< No prefetching and no caching
+#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_EN 0x00 ///< No prefetching, but caching enabled
+#define B_PCH_SPI_BC_LE BIT1 ///< Lock Enable
+#define N_PCH_SPI_BC_BLE 1
+#define B_PCH_SPI_BC_WPD BIT0 ///< Write Protect Disable
+
+//
+// BIOS Flash Program Registers (based on SPI_BAR0)
+//
+#define R_PCH_SPI_BFPR 0x00 ///< BIOS Flash Primary Region Register(32bits), which is RO and contains the same value from FREG1
+#define B_PCH_SPI_BFPR_PRL 0x7FFF0000 ///< BIOS Flash Primary Region Limit mask
+#define N_PCH_SPI_BFPR_PRL 16 ///< BIOS Flash Primary Region Limit bit position
+#define B_PCH_SPI_BFPR_PRB 0x00007FFF ///< BIOS Flash Primary Region Base mask
+#define N_PCH_SPI_BFPR_PRB 0 ///< BIOS Flash Primary Region Base bit position
+#define R_PCH_SPI_HSFSC 0x04 ///< Hardware Sequencing Flash Status and Control Register(32bits)
+#define B_PCH_SPI_HSFSC_FSMIE BIT31 ///< Flash SPI SMI# Enable
+#define B_PCH_SPI_HSFSC_FDBC_MASK 0x3F000000 ///< Flash Data Byte Count ( <= 64), Count = (Value in this field) + 1.
+#define N_PCH_SPI_HSFSC_FDBC 24
+#define B_PCH_SPI_HSFSC_CYCLE_MASK 0x001E0000 ///< Flash Cycle.
+#define N_PCH_SPI_HSFSC_CYCLE 17
+#define V_PCH_SPI_HSFSC_CYCLE_READ 0 ///< Flash Cycle Read
+#define V_PCH_SPI_HSFSC_CYCLE_WRITE 2 ///< Flash Cycle Write
+#define V_PCH_SPI_HSFSC_CYCLE_4K_ERASE 3 ///< Flash Cycle 4K Block Erase
+#define V_PCH_SPI_HSFSC_CYCLE_64K_ERASE 4 ///< Flash Cycle 64K Sector Erase
+#define V_PCH_SPI_HSFSC_CYCLE_READ_SFDP 5 ///< Flash Cycle Read SFDP
+#define V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID 6 ///< Flash Cycle Read JEDEC ID
+#define V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS 7 ///< Flash Cycle Write Status
+#define V_PCH_SPI_HSFSC_CYCLE_READ_STATUS 8 ///< Flash Cycle Read Status
+#define B_PCH_SPI_HSFSC_CYCLE_FGO BIT16 ///< Flash Cycle Go.
+#define B_PCH_SPI_HSFSC_FLOCKDN BIT15 ///< Flash Configuration Lock-Down
+#define B_PCH_SPI_HSFSC_FDV BIT14 ///< Flash Descriptor Valid, once valid software can use hareware sequencing regs
+#define B_PCH_SPI_HSFSC_FDOPSS BIT13 ///< Flash Descriptor Override Pin-Strap Status
+#define B_PCH_SPI_HSFSC_PRR34_LOCKDN BIT12 ///< PRR3 PRR4 Lock-Down
+#define B_PCH_SPI_HSFSC_SAF_CE BIT8 ///< SAF ctype error
+#define B_PCH_SPI_HSFSC_SAF_MODE_ACTIVE BIT7 ///< Indicates flash is attached either directly to the PCH via the SPI bus or EC/BMC
+#define B_PCH_SPI_HSFSC_SAF_LE BIT6 ///< SAF link error
+#define B_PCH_SPI_HSFSC_SCIP BIT5 ///< SPI cycle in progress
+#define B_PCH_SPI_HSFSC_SAF_DLE BIT4 ///< SAF Data length error
+#define B_PCH_SPI_HSFSC_SAF_ERROR BIT3 ///< SAF Error
+#define B_PCH_SPI_HSFSC_AEL BIT2 ///< Access Error Log
+#define B_PCH_SPI_HSFSC_FCERR BIT1 ///< Flash Cycle Error
+#define B_PCH_SPI_HSFSC_FDONE BIT0 ///< Flash Cycle Done
+#define R_PCH_SPI_FADDR 0x08 ///< SPI Flash Address
+#define B_PCH_SPI_FADDR_MASK 0x01FFFFFF ///< SPI Flash Address Mask (0~24bit)
+#define R_PCH_SPI_DLOCK 0x0C ///< Discrete Lock Bits
+#define B_PCH_SPI_DLOCK_PR0LOCKDN BIT8 ///< PR0LOCKDN
+#define R_PCH_SPI_FDATA00 0x10 ///< SPI Data 00 (32 bits)
+#define R_PCH_SPI_FDATA01 0x14 ///< SPI Data 01
+#define R_PCH_SPI_FDATA02 0x18 ///< SPI Data 02
+#define R_PCH_SPI_FDATA03 0x1C ///< SPI Data 03
+#define R_PCH_SPI_FDATA04 0x20 ///< SPI Data 04
+#define R_PCH_SPI_FDATA05 0x24 ///< SPI Data 05
+#define R_PCH_SPI_FDATA06 0x28 ///< SPI Data 06
+#define R_PCH_SPI_FDATA07 0x2C ///< SPI Data 07
+#define R_PCH_SPI_FDATA08 0x30 ///< SPI Data 08
+#define R_PCH_SPI_FDATA09 0x34 ///< SPI Data 09
+#define R_PCH_SPI_FDATA10 0x38 ///< SPI Data 10
+#define R_PCH_SPI_FDATA11 0x3C ///< SPI Data 11
+#define R_PCH_SPI_FDATA12 0x40 ///< SPI Data 12
+#define R_PCH_SPI_FDATA13 0x44 ///< SPI Data 13
+#define R_PCH_SPI_FDATA14 0x48 ///< SPI Data 14
+#define R_PCH_SPI_FDATA15 0x4C ///< SPI Data 15
+#define R_PCH_SPI_FRAP 0x50 ///< Flash Region Access Permisions Register
+#define B_PCH_SPI_FRAP_BRWA_MASK 0x0000FF00 ///< BIOS Region Write Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3: GbE; 4: PlatformData
+#define N_PCH_SPI_FRAP_BRWA 8 ///< BIOS Region Write Access bit position
+#define B_PCH_SPI_FRAP_BRRA_MASK 0x000000FF ///< BIOS Region Read Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3: GbE; 4: PlatformData
+#define B_PCH_SPI_FRAP_BMRAG_MASK 0x00FF0000 ///< BIOS Master Read Access Grant
+#define B_PCH_SPI_FRAP_BMWAG_MASK 0xFF000000 ///< BIOS Master Write Access Grant
+#define R_PCH_SPI_FREG0_FLASHD 0x54 ///< Flash Region 0(Flash Descriptor)(32bits)
+#define R_PCH_SPI_FREG1_BIOS 0x58 ///< Flash Region 1(BIOS)(32bits)
+#define R_PCH_SPI_FREG2_ME 0x5C ///< Flash Region 2(ME)(32bits)
+#define R_PCH_SPI_FREG3_GBE 0x60 ///< Flash Region 3(GbE)(32bits)
+#define R_PCH_SPI_FREG4_PLATFORM_DATA 0x64 ///< Flash Region 4(Platform Data)(32bits)
+#define R_PCH_SPI_FREG5_DER 0x68 ///< Flash Region 5(Device Expansion Region)(32bits)
+#define S_PCH_SPI_FREGX 4 ///< Size of Flash Region register
+#define B_PCH_SPI_FREGX_LIMIT_MASK 0x7FFF0000 ///< Flash Region Limit [30:16] represents [26:12], [11:0] are assumed to be FFFh
+#define N_PCH_SPI_FREGX_LIMIT 16 ///< Region limit bit position
+#define N_PCH_SPI_FREGX_LIMIT_REPR 12 ///< Region limit bit represents position
+#define B_PCH_SPI_FREGX_BASE_MASK 0x00007FFF ///< Flash Region Base, [14:0] represents [26:12]
+#define N_PCH_SPI_FREGX_BASE 0 ///< Region base bit position
+#define N_PCH_SPI_FREGX_BASE_REPR 12 ///< Region base bit represents position
+#define R_PCH_SPI_PR0 0x84 ///< Protected Region 0 Register
+#define R_PCH_SPI_PR1 0x88 ///< Protected Region 1 Register
+#define R_PCH_SPI_PR2 0x8C ///< Protected Region 2 Register
+#define R_PCH_SPI_PR3 0x90 ///< Protected Region 3 Register
+#define R_PCH_SPI_PR4 0x94 ///< Protected Region 4 Register
+#define S_PCH_SPI_PRX 4 ///< Protected Region X Register size
+#define B_PCH_SPI_PRX_WPE BIT31 ///< Write Protection Enable
+#define B_PCH_SPI_PRX_PRL_MASK 0x7FFF0000 ///< Protected Range Limit Mask, [30:16] here represents upper limit of address [26:12]
+#define N_PCH_SPI_PRX_PRL 16 ///< Protected Range Limit bit position
+#define B_PCH_SPI_PRX_RPE BIT15 ///< Read Protection Enable
+#define B_PCH_SPI_PRX_PRB_MASK 0x00007FFF ///< Protected Range Base Mask, [14:0] here represents base limit of address [26:12]
+#define N_PCH_SPI_PRX_PRB 0 ///< Protected Range Base bit position
+#define R_PCH_SPI_SFRAP 0xB0 ///< Secondary Flash Regions Access Permisions Register
+#define R_PCH_SPI_FDOC 0xB4 ///< Flash Descriptor Observability Control Register(32 bits)
+#define B_PCH_SPI_FDOC_FDSS_MASK (BIT14 | BIT13 | BIT12) ///< Flash Descritor Section Select
+#define V_PCH_SPI_FDOC_FDSS_FSDM 0x0000 ///< Flash Signature and Descriptor Map
+#define V_PCH_SPI_FDOC_FDSS_COMP 0x1000 ///< Component
+#define V_PCH_SPI_FDOC_FDSS_REGN 0x2000 ///< Region
+#define V_PCH_SPI_FDOC_FDSS_MSTR 0x3000 ///< Master
+#define V_PCH_SPI_FDOC_FDSS_PCHS 0x4000 ///< PCH soft straps
+#define V_PCH_SPI_FDOC_FDSS_SFDP 0x5000 ///< SFDP Parameter Table
+#define B_PCH_SPI_FDOC_FDSI_MASK 0x0FFC ///< Flash Descriptor Section Index
+#define R_PCH_SPI_FDOD 0xB8 ///< Flash Descriptor Observability Data Register(32 bits)
+#define R_PCH_SPI_SFDP0_VSCC0 0xC4 ///< Vendor Specific Component Capabilities Register(32 bits)
+#define B_PCH_SPI_SFDPX_VSCCX_CPPTV BIT31 ///< Component Property Parameter Table Valid
+#define B_PCH_SPI_SFDP0_VSCC0_VCL BIT30 ///< Vendor Component Lock
+#define B_PCH_SPI_SFDPX_VSCCX_EO_64K BIT29 ///< 64k Erase valid (EO_64k_valid)
+#define B_PCH_SPI_SFDPX_VSCCX_EO_4K BIT28 ///< 4k Erase valid (EO_4k_valid)
+#define B_PCH_SPI_SFDPX_VSCCX_RPMC BIT27 ///< RPMC Supported
+#define B_PCH_SPI_SFDPX_VSCCX_DPD BIT26 ///< Deep Powerdown Supported
+#define B_PCH_SPI_SFDPX_VSCCX_SUSRES BIT25 ///< Suspend/Resume Supported
+#define B_PCH_SPI_SFDPX_VSCCX_SOFTRES BIT24 ///< Soft Reset Supported
+#define B_PCH_SPI_SFDPX_VSCCX_64k_EO_MASK 0x00FF0000 ///< 64k Erase Opcode (EO_64k)
+#define B_PCH_SPI_SFDPX_VSCCX_4k_EO_MASK 0x0000FF00 ///< 4k Erase Opcode (EO_4k)
+#define B_PCH_SPI_SFDPX_VSCCX_QER (BIT7 | BIT6 | BIT5) ///< Quad Enable Requirements
+#define B_PCH_SPI_SFDPX_VSCCX_WEWS BIT4 ///< Write Enable on Write Status
+#define B_PCH_SPI_SFDPX_VSCCX_WSR BIT3 ///< Write Status Required
+#define B_PCH_SPI_SFDPX_VSCCX_WG_64B BIT2 ///< Write Granularity, 0: 1 Byte; 1: 64 Bytes
+#define R_PCH_SPI_SFDP1_VSCC1 0xC8 ///< Vendor Specific Component Capabilities Register(32 bits)
+#define R_PCH_SPI_PINTX 0xCC ///< Parameter Table Index
+#define N_PCH_SPI_PINTX_SPT 14
+#define V_PCH_SPI_PINTX_SPT_CPT0 0x0 ///< Component 0 Property Parameter Table
+#define V_PCH_SPI_PINTX_SPT_CPT1 0x1 ///< Component 1 Property Parameter Table
+#define N_PCH_SPI_PINTX_HORD 12
+#define V_PCH_SPI_PINTX_HORD_SFDP 0x0 ///< SFDP Header
+#define V_PCH_SPI_PINTX_HORD_PT 0x1 ///< Parameter Table Header
+#define V_PCH_SPI_PINTX_HORD_DATA 0x2 ///< Data
+#define R_PCH_SPI_PTDATA 0xD0 ///< Parameter Table Data
+#define R_PCH_SPI_SBRS 0xD4 ///< SPI Bus Requester Status
+#define R_PCH_SPI_SSML 0xF0 ///< Set Strap Msg Lock
+#define B_PCH_SPI_SSML_SSL BIT0 ///< Set_Strap Lock
+#define R_PCH_SPI_SSMC 0xF4 ///< Set Strap Msg Control
+#define B_PCH_SPI_SSMC_SSMS BIT0 ///< Set_Strap Mux Select
+#define R_PCH_SPI_SSMD 0xF8 ///< Set Strap Msg Data
+//
+// @todo Follow up with EDS owner if it should be 3FFF or FFFF.
+//
+#define B_PCH_SPI_SRD_SSD 0x0000FFFF ///< Set_Strap Data
+//
+// Flash Descriptor Base Address Region (FDBAR) from Flash Region 0
+//
+#define R_PCH_SPI_FDBAR_FLVALSIG 0x00 ///< Flash Valid Signature
+#define V_PCH_SPI_FDBAR_FLVALSIG 0x0FF0A55A
+#define R_PCH_SPI_FDBAR_FLASH_MAP0 0x04
+#define B_PCH_SPI_FDBAR_FCBA 0x000000FF ///< Flash Component Base Address
+#define B_PCH_SPI_FDBAR_NC 0x00000300 ///< Number Of Components
+#define N_PCH_SPI_FDBAR_NC 8 ///< Number Of Components
+#define V_PCH_SPI_FDBAR_NC_1 0x00000000
+#define V_PCH_SPI_FDBAR_NC_2 0x00000100
+#define B_PCH_SPI_FDBAR_FRBA 0x00FF0000 ///< Flash Region Base Address
+#define B_PCH_SPI_FDBAR_NR 0x07000000 ///< Number Of Regions
+#define R_PCH_SPI_FDBAR_FLASH_MAP1 0x08
+#define B_PCH_SPI_FDBAR_FMBA 0x000000FF ///< Flash Master Base Address
+#define B_PCH_SPI_FDBAR_NM 0x00000700 ///< Number Of Masters
+#define B_PCH_SPI_FDBAR_FPSBA 0x00FF0000 ///< PCH Strap Base Address, [23:16] represents [11:4]
+#define N_PCH_SPI_FDBAR_FPSBA 16 ///< PCH Strap base Address bit position
+#define N_PCH_SPI_FDBAR_FPSBA_REPR 4 ///< PCH Strap base Address bit represents position
+#define B_PCH_SPI_FDBAR_PCHSL 0xFF000000 ///< PCH Strap Length, [31:24] represents number of Dwords
+#define N_PCH_SPI_FDBAR_PCHSL 24 ///< PCH Strap Length bit position
+#define R_PCH_SPI_FDBAR_FLASH_MAP2 0x0C
+#define B_PCH_SPI_FDBAR_FCPUSBA 0x000000FF ///< CPU Strap Base Address, [7:0] represents [11:4]
+#define N_PCH_SPI_FDBAR_FCPUSBA 0 ///< CPU Strap Base Address bit position
+#define N_PCH_SPI_FDBAR_FCPUSBA_REPR 4 ///< CPU Strap Base Address bit represents position
+#define B_PCH_SPI_FDBAR_CPUSL 0x0000FF00 ///< CPU Strap Length, [15:8] represents number of Dwords
+#define N_PCH_SPI_FDBAR_CPUSL 8 ///< CPU Strap Length bit position
+//
+// Flash Component Base Address (FCBA) from Flash Region 0
+//
+#define R_PCH_SPI_FCBA_FLCOMP 0x00 ///< Flash Components Register
+#define B_PCH_SPI_FLCOMP_RIDS_FREQ (BIT29 | BIT28 | BIT27) ///< Read ID and Read Status Clock Frequency
+#define B_PCH_SPI_FLCOMP_WE_FREQ (BIT26 | BIT25 | BIT24) ///< Write and Erase Clock Frequency
+#define B_PCH_SPI_FLCOMP_FRCF_FREQ (BIT23 | BIT22 | BIT21) ///< Fast Read Clock Frequency
+#define B_PCH_SPI_FLCOMP_FR_SUP BIT20 ///< Fast Read Support.
+#define B_PCH_SPI_FLCOMP_RC_FREQ (BIT19 | BIT18 | BIT17) ///< Read Clock Frequency.
+#define V_PCH_SPI_FLCOMP_FREQ_48MHZ 0x02
+#define V_PCH_SPI_FLCOMP_FREQ_30MHZ 0x04
+#define V_PCH_SPI_FLCOMP_FREQ_17MHZ 0x06
+#define B_PCH_SPI_FLCOMP_COMP1_MASK 0xF0 ///< Flash Component 1 Size MASK
+#define N_PCH_SPI_FLCOMP_COMP1 4 ///< Flash Component 1 Size bit position
+#define B_PCH_SPI_FLCOMP_COMP0_MASK 0x0F ///< Flash Component 0 Size MASK
+#define V_PCH_SPI_FLCOMP_COMP_512KB 0x80000
+//
+// Descriptor Upper Map Section from Flash Region 0
+//
+#define R_PCH_SPI_FLASH_UMAP1 0xEFC ///< Flash Upper Map 1
+#define B_PCH_SPI_FLASH_UMAP1_VTBA 0x000000FF ///< VSCC Table Base Address
+#define B_PCH_SPI_FLASH_UMAP1_VTL 0x0000FF00 ///< VSCC Table Length
+
+#define R_PCH_SPI_VTBA_JID0 0x00 ///< JEDEC-ID 0 Register
+#define S_PCH_SPI_VTBA_JID0 0x04
+#define B_PCH_SPI_VTBA_JID0_VID 0x000000FF
+#define B_PCH_SPI_VTBA_JID0_DID0 0x0000FF00
+#define B_PCH_SPI_VTBA_JID0_DID1 0x00FF0000
+#define N_PCH_SPI_VTBA_JID0_DID0 0x08
+#define N_PCH_SPI_VTBA_JID0_DID1 0x10
+#define R_PCH_SPI_VTBA_VSCC0 0x04
+#define S_PCH_SPI_VTBA_VSCC0 0x04
+
+
+//
+// SPI Private Configuration Space Registers
+//
+#define R_PCH_PCR_SPI_CLK_CTL 0xC004
+#define R_PCH_PCR_SPI_PWR_CTL 0xC008
+#define R_PCH_PCR_SPI_ESPI_SOFTSTRAPS 0xC210
+#define B_PCH_PCR_SPI_ESPI_SOFTSTRAPS_SLAVE BIT12
+
+//
+// MMP0
+//
+#define R_PCH_SPI_STRP_MMP0 0xC4 ///< MMP0 Soft strap offset
+#define B_PCH_SPI_STRP_MMP0 0x10 ///< MMP0 Soft strap bit
+
+
+#define R_PCH_SPI_STRP_SFDP 0xF0 ///< PCH Soft Strap SFDP
+#define B_PCH_SPI_STRP_SFDP_QIORE BIT3 ///< Quad IO Read Enable
+#define B_PCH_SPI_STRP_SFDP_QORE BIT2 ///< Quad Output Read Enable
+#define B_PCH_SPI_STRP_SFDP_DIORE BIT1 ///< Dual IO Read Enable
+#define B_PCH_SPI_STRP_SFDP_DORE BIT0 ///< Dual Output Read Enable
+
+//
+// Descriptor Record 0
+//
+#define R_PCH_SPI_STRP_DSCR_0 0x00 ///< PCH Soft Strap 0
+#define B_PCH_SPI_STRP_DSCR_0_PTT_SUPP BIT22 ///< PTT Supported
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
new file mode 100644
index 0000000000..5bdec96197
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
@@ -0,0 +1,396 @@
+/** @file
+ Header file for the PCH SPI Common Driver.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_COMMON_LIB_H_
+#define _PCH_SPI_COMMON_LIB_H_
+
+//
+// Maximum time allowed while waiting the SPI cycle to complete
+// Wait Time = 6 seconds = 6000000 microseconds
+// Wait Period = 10 microseconds
+//
+#define SPI_WAIT_TIME 6000000 ///< Wait Time = 6 seconds = 6000000 microseconds
+#define SPI_WAIT_PERIOD 10 ///< Wait Period = 10 microseconds
+
+///
+/// Flash cycle Type
+///
+typedef enum {
+ FlashCycleRead,
+ FlashCycleWrite,
+ FlashCycleErase,
+ FlashCycleReadSfdp,
+ FlashCycleReadJedecId,
+ FlashCycleWriteStatus,
+ FlashCycleReadStatus,
+ FlashCycleMax
+} FLASH_CYCLE_TYPE;
+
+///
+/// Flash Component Number
+///
+typedef enum {
+ FlashComponent0,
+ FlashComponent1,
+ FlashComponentMax
+} FLASH_COMPONENT_NUM;
+
+///
+/// Private data structure definitions for the driver
+///
+#define PCH_SPI_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('P', 'S', 'P', 'I')
+
+typedef struct {
+ UINT32 Signature;
+ EFI_HANDLE Handle;
+ EFI_SPI_PROTOCOL SpiProtocol;
+ UINT16 PchAcpiBase;
+ UINTN PchSpiBase;
+ UINT16 ReadPermission;
+ UINT16 WritePermission;
+ UINT32 SfdpVscc0Value;
+ UINT32 SfdpVscc1Value;
+ UINT16 PchStrapBaseAddr;
+ UINT16 PchStrapSize;
+ UINT16 CpuStrapBaseAddr;
+ UINT16 CpuStrapSize;
+ UINT8 NumberOfComponents;
+ UINT32 Component1StartAddr;
+ UINT32 TotalFlashSize;
+} SPI_INSTANCE;
+
+#define SPI_INSTANCE_FROM_SPIPROTOCOL(a) CR (a, SPI_INSTANCE, SpiProtocol, PCH_SPI_PRIVATE_DATA_SIGNATURE)
+
+//
+// Function prototypes used by the SPI protocol.
+//
+
+/**
+ Initialize an SPI protocol instance.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @exception EFI_UNSUPPORTED The PCH is not supported by this module
+**/
+EFI_STATUS
+SpiProtocolConstructor (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ This function is a hook for Spi to disable BIOS Write Protect
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in SMM phase
+
+**/
+EFI_STATUS
+EFIAPI
+DisableBiosWriteProtect (
+ VOID
+ );
+
+/**
+ This function is a hook for Spi to enable BIOS Write Protect
+
+
+**/
+VOID
+EFIAPI
+EnableBiosWriteProtect (
+ VOID
+ );
+
+/**
+ Acquire pch spi mmio address.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval PchSpiBar0 return SPI MMIO address
+**/
+UINTN
+AcquireSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ Release pch spi mmio address.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval None
+**/
+VOID
+ReleaseSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashRead (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write data to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWrite (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashErase (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ );
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadSfdp (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ );
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadJedecId (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ );
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWriteStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ );
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ );
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolGetRegionAddress (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ );
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadPchSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadCpuSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ This function sends the programmed SPI command to the slave device.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SpiRegionType The SPI Region type for flash cycle which is listed in the Descriptor
+ @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware Sequencing Flash Control Register) register
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in,out] Buffer Pointer to caller-allocated buffer containing the dada received or sent during the SPI cycle.
+
+ @retval EFI_SUCCESS SPI command completes successfully.
+ @retval EFI_DEVICE_ERROR Device error, the command aborts abnormally.
+ @retval EFI_ACCESS_DENIED Some unrecognized command encountered in hardware sequencing mode
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+**/
+EFI_STATUS
+SendSpiCmd (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN FLASH_CYCLE_TYPE FlashCycleType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN OUT UINT8 *Buffer
+ );
+
+/**
+ Wait execution cycle to complete on the SPI interface.
+
+ @param[in] This The SPI protocol instance
+ @param[in] PchSpiBar0 Spi MMIO base address
+ @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
+
+ @retval TRUE SPI cycle completed on the interface.
+ @retval FALSE Time out while waiting the SPI cycle to complete.
+ It's not safe to program the next command on the SPI interface.
+**/
+BOOLEAN
+WaitForSpiCycleComplete (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINTN PchSpiBar0,
+ IN BOOLEAN ErrorCheck
+ );
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
new file mode 100644
index 0000000000..4af462da47
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
@@ -0,0 +1,34 @@
+## @file
+# Library instance for ResetSystem library class for OVMF
+#
+# Copyright (c) 2006 - 2018 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = ResetSystemLib
+ FILE_GUID = 66564872-21d4-4d2a-a68b-1e844f980820
+ MODULE_TYPE = BASE
+ VERSION_STRING = 1.0
+ LIBRARY_CLASS = ResetSystemLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[Sources]
+ ResetSystemLib.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+
+[LibraryClasses]
+ DebugLib
+ IoLib
+ TimerLib
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
new file mode 100644
index 0000000000..b5c97f1930
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
@@ -0,0 +1,52 @@
+## @file
+# SMM Library instance of Spi Flash Common Library Class
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010017
+ BASE_NAME = SmmSpiFlashCommonLib
+ FILE_GUID = 9632D96E-E849-4217-9217-DC500B8AAE47
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_SMM_DRIVER
+ LIBRARY_CLASS = SpiFlashCommonLib|DXE_SMM_DRIVER
+ CONSTRUCTOR = SmmSpiFlashCommonLibConstructor
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[LibraryClasses]
+ PciLib
+ IoLib
+ MemoryAllocationLib
+ BaseLib
+ UefiLib
+ SmmServicesTableLib
+ BaseMemoryLib
+ DebugLib
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+ MinPlatformPkg/MinPlatformPkg.dec
+
+
+[Pcd]
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
+
+[Sources]
+ SpiFlashCommonSmmLib.c
+ SpiFlashCommon.c
+
+[Protocols]
+ gEfiSmmSpiProtocolGuid ## CONSUMES
+
+[Depex.X64.DXE_SMM_DRIVER]
+ gEfiSmmSpiProtocolGuid
diff --git a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
new file mode 100644
index 0000000000..11c832e487
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
@@ -0,0 +1,33 @@
+## @file
+# Component description file for the PchSpiCommonLib
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = BasePchSpiCommonLib
+ FILE_GUID = A37CB67E-7D85-45B3-B07E-BF65BDB603E8
+ MODULE_TYPE = BASE
+ VERSION_STRING = 1.0
+ LIBRARY_CLASS = PchSpiCommonLib
+
+[Sources]
+ SpiCommon.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+ MinPlatformPkg/MinPlatformPkg.dec
+
+[LibraryClasses]
+ IoLib
+ DebugLib
+
+[Pcd]
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
new file mode 100644
index 0000000000..a2d006ee35
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
@@ -0,0 +1,12 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE libraries.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[LibraryClasses.common]
+ ResetSystemLib|$(PCH_PKG)/Library/ResetSystemLib/ResetSystemLib.inf
+ PchSpiCommonLib|$(PCH_PKG)/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
new file mode 100644
index 0000000000..78eca21a43
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
@@ -0,0 +1,9 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
new file mode 100644
index 0000000000..2d3a127c20
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
@@ -0,0 +1,9 @@
+## @file
+# Component description file for the SkyLake SiPkg PEI drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
new file mode 100644
index 0000000000..d079c593d9
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
@@ -0,0 +1,13 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+!if gMinPlatformPkgTokenSpaceGuid.PcdBootToShellOnly == FALSE
+ INF $(PCH_PKG)/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
+ INF $(PCH_PKG)/Spi/Smm/PchSpiSmm.inf
+!endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
new file mode 100644
index 0000000000..e23dd9f2fe
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
@@ -0,0 +1,59 @@
+## @file
+# A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
+# EFI_SMM_CONTROL2_PROTOCOL.
+#
+# We expect the PEI phase to have covered the following:
+# - ensure that the underlying QEMU machine type be X58
+# (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
+# - ensure that the ACPI PM IO space be configured
+# (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
+#
+# Our own entry point is responsible for confirming the SMI feature and for
+# configuring it.
+#
+# Copyright (C) 2013, 2015, Red Hat, Inc.
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = SmmControl2Dxe
+ FILE_GUID = 1206F7CA-A475-4624-A83E-E6FC9BB38E49
+ MODULE_TYPE = DXE_RUNTIME_DRIVER
+ VERSION_STRING = 1.0
+ PI_SPECIFICATION_VERSION = 0x00010400
+ ENTRY_POINT = SmmControl2DxeEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[Sources]
+ SmmControl2Dxe.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+
+[LibraryClasses]
+ BaseLib
+ DebugLib
+ IoLib
+ PcdLib
+ PciLib
+ UefiBootServicesTableLib
+ UefiDriverEntryPoint
+
+[Protocols]
+ gEfiS3SaveStateProtocolGuid ## SOMETIMES_CONSUMES
+ gEfiSmmControl2ProtocolGuid ## PRODUCES
+
+[FeaturePcd]
+ gSimicsX58PkgTokenSpaceGuid.PcdSmmSmramRequire
+
+[Depex]
+ TRUE
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
new file mode 100644
index 0000000000..f7fdd3abbe
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
@@ -0,0 +1,23 @@
+/** @file
+ Header file for the PCH SPI SMM Driver.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_H_
+#define _PCH_SPI_H_
+
+#include <Library/IoLib.h>
+#include <Library/DebugLib.h>
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/SmmServicesTableLib.h>
+#include <PchAccess.h>
+#include <Protocol/Spi.h>
+#include <IncludePrivate/Library/PchSpiCommonLib.h>
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
new file mode 100644
index 0000000000..265af00ac0
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
@@ -0,0 +1,44 @@
+## @file
+# Component description file for the SPI SMM driver.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010017
+ BASE_NAME = PchSpiSmm
+ FILE_GUID = 27F4917B-A707-4aad-9676-26DF168CBF0D
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_SMM_DRIVER
+ PI_SPECIFICATION_VERSION = 1.10
+ ENTRY_POINT = InstallPchSpi
+
+
+ [LibraryClasses]
+ DebugLib
+ IoLib
+ UefiDriverEntryPoint
+ UefiBootServicesTableLib
+ BaseLib
+ SmmServicesTableLib
+ PchSpiCommonLib
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+
+[Sources]
+ PchSpi.h
+ PchSpi.c
+
+
+[Protocols]
+ gEfiSmmSpiProtocolGuid # PRODUCES #SERVER_BIOS
+
+
+[Depex]
+ gEfiSmmBase2ProtocolGuid #This is for SmmServicesTableLib
+ AND gEfiSmmCpuProtocolGuid # This is for CpuSmmDisableBiosWriteProtect()
--
2.16.2.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#45303): https://edk2.groups.io/g/devel/message/45303
Mute This Topic: https://groups.io/mt/32816096/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
Hi David,
I would prefer if we follow Pascal casing and rename this package to SimicsIch10Pkg (instead of SimicsICH10Pkg).
Also, I think it would be good if we can also add owners for the new packages to the Maintainers.txt file. (SimicsIch10SiliconBinPkg, SimicsX58SktPkg, SimicsIch10Pkg, and SimicsOpenBoardPkg).
Thanks,
Nate
-----Original Message-----
From: Wei, David Y
Sent: Friday, August 9, 2019 3:47 PM
To: devel@edk2.groups.io
Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>; Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince <prince.agyeman@intel.com>; Kubacki, Michael A <michael.a.kubacki@intel.com>; Desimone, Nathaniel L <nathaniel.l.desimone@intel.com>; Kinney, Michael D <michael.d.kinney@intel.com>
Subject: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for SimicsICH10
Add PCH Pkg for SimicsICH10. It is added for simics QSP project support
Cc: Hao Wu <hao.a.wu@intel.com>
Cc: Liming Gao <liming.gao@intel.com>
Cc: Ankit Sinha <ankit.sinha@intel.com>
Cc: Agyeman Prince <prince.agyeman@intel.com>
Cc: Kubacki Michael A <michael.a.kubacki@intel.com>
Cc: Nate DeSimone <nathaniel.l.desimone@intel.com>
Cc: Michael D Kinney <michael.d.kinney@intel.com>
Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: David Wei <david.y.wei@intel.com>
---
.../Library/ResetSystemLib/ResetSystemLib.c | 137 +++
.../Library/SmmSpiFlashCommonLib/SpiFlashCommon.c | 194 +++++
.../SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c | 54 ++
.../LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c | 935 +++++++++++++++++++++
.../SmmControl/RuntimeDxe/SmmControl2Dxe.c | 410 +++++++++
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c | 175 ++++
Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec | 22 +
.../Include/Library/SpiFlashCommonLib.h | 98 +++
Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h | 43 +
Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h | 94 +++
.../SimicsICH10Pkg/Include/PchReservedResources.h | 60 ++
.../Intel/SimicsICH10Pkg/Include/Protocol/Spi.h | 295 +++++++
.../SimicsICH10Pkg/Include/Register/PchRegsPmc.h | 647 ++++++++++++++
.../SimicsICH10Pkg/Include/Register/PchRegsSpi.h | 304 +++++++
.../IncludePrivate/Library/PchSpiCommonLib.h | 396 +++++++++
.../Library/ResetSystemLib/ResetSystemLib.inf | 34 +
.../SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf | 52 ++
.../BasePchSpiCommonLib/BasePchSpiCommonLib.inf | 33 +
Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc | 12 +
.../Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf | 9 +
.../Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf | 9 +
.../Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf | 13 +
.../SmmControl/RuntimeDxe/SmmControl2Dxe.inf | 59 ++
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h | 23 +
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf | 44 +
25 files changed, 4152 insertions(+)
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
new file mode 100644
index 0000000000..46355e191c
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
@@ -0,0 +1,137 @@
+/** @file
+ Reset System Library functions for OVMF
+
+ Copyright (c) 2006 - 2016 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Base.h>
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/TimerLib.h>
+#include <IndustryStandard/X58Ich10.h>
+
+
+VOID
+AcpiPmControl (
+ UINTN SuspendType
+ )
+{
+ ASSERT (SuspendType < 6);
+ DEBUG((EFI_D_ERROR, "SuspendType = 0x%x\n", SuspendType));
+
+ IoBitFieldWrite16 (ICH10_PMBASE_IO + 4, 10, 13, (UINT16) SuspendType);
+ IoOr16 (ICH10_PMBASE_IO + 0x04, BIT13);
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes a system-wide reset. This sets
+ all circuitry within the system to its initial state. This type of reset
+ is asynchronous to system operation and operates without regard to
+ cycle boundaries.
+
+ System reset should not return, if it returns, it means the system does
+ not support cold reset.
+**/
+VOID
+EFIAPI
+ResetCold (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetCold_CF9\n"));
+ IoWrite8 (0xCF9, BIT3 | BIT2 | BIT1); // 1st choice: PIIX3 RCR, RCPU|SRST
+ MicroSecondDelay (50);
+
+ DEBUG((EFI_D_ERROR, "ResetCold_Port64\n"));
+ IoWrite8 (0x64, 0xfe); // 2nd choice: keyboard controller
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes a system-wide initialization. The processors
+ are set to their initial state, and pending cycles are not corrupted.
+
+ System reset should not return, if it returns, it means the system does
+ not support warm reset.
+**/
+VOID
+EFIAPI
+ResetWarm (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetWarm\n"));
+ //
+ //BUGBUG workaround for warm reset
+ //
+ IoWrite8(0xCF9, BIT2 | BIT1);
+ MicroSecondDelay(50);
+
+ IoWrite8 (0x64, 0xfe);
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes the system to enter a power state equivalent
+ to the ACPI G2/S5 or G3 states.
+
+ System shutdown should not return, if it returns, it means the system does
+ not support shut down reset.
+**/
+VOID
+EFIAPI
+ResetShutdown (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetShutdown\n"));
+ AcpiPmControl (0);
+ ASSERT (FALSE);
+}
+
+
+/**
+ Calling this function causes the system to enter a power state for capsule
+ update.
+
+ Reset update should not return, if it returns, it means the system does
+ not support capsule update.
+
+**/
+VOID
+EFIAPI
+EnterS3WithImmediateWake (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "EnterS3WithImmediateWake\n"));
+ AcpiPmControl (1);
+ ASSERT (FALSE);
+}
+
+/**
+ This function causes a systemwide reset. The exact type of the reset is
+ defined by the EFI_GUID that follows the Null-terminated Unicode string passed
+ into ResetData. If the platform does not recognize the EFI_GUID in ResetData
+ the platform must pick a supported reset type to perform.The platform may
+ optionally log the parameters from any non-normal reset that occurs.
+
+ @param[in] DataSize The size, in bytes, of ResetData.
+ @param[in] ResetData The data buffer starts with a Null-terminated string,
+ followed by the EFI_GUID.
+**/
+VOID
+EFIAPI
+ResetPlatformSpecific (
+ IN UINTN DataSize,
+ IN VOID *ResetData
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetPlatformSpecific\n"));
+ ResetCold ();
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
new file mode 100644
index 0000000000..3d4e24eac6
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
@@ -0,0 +1,194 @@
+/** @file
+ Wrap EFI_SPI_PROTOCOL to provide some library level interfaces
+ for module use.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/SpiFlashCommonLib.h>
+#include <Library/IoLib.h>
+#include <Library/PciLib.h>
+#include <Protocol/Spi.h>
+
+
+EFI_SPI_PROTOCOL *mSpiProtocol;
+
+//
+// FlashAreaBaseAddress and Size for boottime and runtime usage.
+//
+UINTN mFlashAreaBaseAddress = 0;
+UINTN mFlashAreaSize = 0;
+
+/**
+ Enable block protection on the Serial Flash device.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashLock (
+ VOID
+ )
+{
+ return EFI_SUCCESS;
+}
+
+/**
+ Read NumBytes bytes of data from the address specified by
+ PAddress into Buffer.
+
+ @param[in] Address The starting physical address of the read.
+ @param[in,out] NumBytes On input, the number of bytes to read. On output, the number
+ of bytes actually read.
+ @param[out] Buffer The destination data buffer for the read.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashRead (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ OUT UINT8 *Buffer
+ )
+{
+ ASSERT ((NumBytes != NULL) && (Buffer != NULL));
+ if ((NumBytes == NULL) || (Buffer == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // This function is implemented specifically for those platforms
+ // at which the SPI device is memory mapped for read. So this
+ // function just do a memory copy for Spi Flash Read.
+ //
+ CopyMem (Buffer, (VOID *) Address, *NumBytes);
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Write NumBytes bytes of data from Buffer to the address specified by
+ PAddresss.
+
+ @param[in] Address The starting physical address of the write.
+ @param[in,out] NumBytes On input, the number of bytes to write. On output,
+ the actual number of bytes written.
+ @param[in] Buffer The source data buffer for the write.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashWrite (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ IN UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINTN Offset;
+ UINT32 Length;
+ UINT32 RemainingBytes;
+
+ ASSERT ((NumBytes != NULL) && (Buffer != NULL));
+ if ((NumBytes == NULL) || (Buffer == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ ASSERT (Address >= mFlashAreaBaseAddress);
+
+ Offset = Address - mFlashAreaBaseAddress;
+
+ ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
+
+ Status = EFI_SUCCESS;
+ RemainingBytes = *NumBytes;
+
+
+ while (RemainingBytes > 0) {
+ if (RemainingBytes > SECTOR_SIZE_4KB) {
+ Length = SECTOR_SIZE_4KB;
+ } else {
+ Length = RemainingBytes;
+ }
+ Status = mSpiProtocol->FlashWrite (
+ mSpiProtocol,
+ FlashRegionBios,
+ (UINT32) Offset,
+ Length,
+ Buffer
+ );
+ if (EFI_ERROR (Status)) {
+ break;
+ }
+ RemainingBytes -= Length;
+ Offset += Length;
+ Buffer += Length;
+ }
+
+ //
+ // Actual number of bytes written
+ //
+ *NumBytes -= RemainingBytes;
+
+ return Status;
+}
+
+/**
+ Erase the block starting at Address.
+
+ @param[in] Address The starting physical address of the block to be erased.
+ This library assume that caller garantee that the PAddress
+ is at the starting address of this block.
+ @param[in] NumBytes On input, the number of bytes of the logical block to be erased.
+ On output, the actual number of bytes erased.
+
+ @retval EFI_SUCCESS. Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashBlockErase (
+ IN UINTN Address,
+ IN UINTN *NumBytes
+ )
+{
+ EFI_STATUS Status;
+ UINTN Offset;
+ UINTN RemainingBytes;
+
+ ASSERT (NumBytes != NULL);
+ if (NumBytes == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ ASSERT (Address >= mFlashAreaBaseAddress);
+
+ Offset = Address - mFlashAreaBaseAddress;
+
+ ASSERT ((*NumBytes % SECTOR_SIZE_4KB) == 0);
+ ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
+
+ Status = EFI_SUCCESS;
+ RemainingBytes = *NumBytes;
+
+
+ Status = mSpiProtocol->FlashErase (
+ mSpiProtocol,
+ FlashRegionBios,
+ (UINT32) Offset,
+ (UINT32) RemainingBytes
+ );
+ return Status;
+}
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
new file mode 100644
index 0000000000..1e5cd0d744
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
@@ -0,0 +1,54 @@
+/** @file
+ SMM Library instance of SPI Flash Common Library Class
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/SpiFlashCommonLib.h>
+#include <Library/SmmServicesTableLib.h>
+#include <Protocol/Spi.h>
+
+extern EFI_SPI_PROTOCOL *mSpiProtocol;
+
+extern UINTN mFlashAreaBaseAddress;
+extern UINTN mFlashAreaSize;
+
+/**
+ The library constructuor.
+
+ The function does the necessary initialization work for this library
+ instance.
+
+ @param[in] ImageHandle The firmware allocated handle for the UEFI image.
+ @param[in] SystemTable A pointer to the EFI system table.
+
+ @retval EFI_SUCCESS The function always return EFI_SUCCESS for now.
+ It will ASSERT on error for debug version.
+ @retval EFI_ERROR Please reference LocateProtocol for error code details.
+**/
+EFI_STATUS
+EFIAPI
+SmmSpiFlashCommonLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ mFlashAreaBaseAddress = (UINTN)PcdGet32 (PcdFlashAreaBaseAddress);
+ mFlashAreaSize = (UINTN)PcdGet32 (PcdFlashAreaSize);
+
+ //
+ // Locate the SMM SPI protocol.
+ //
+ Status = gSmst->SmmLocateProtocol (
+ &gEfiSmmSpiProtocolGuid,
+ NULL,
+ (VOID **) &mSpiProtocol
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
new file mode 100644
index 0000000000..77fb76d7cd
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
@@ -0,0 +1,935 @@
+/** @file
+ PCH SPI Common Driver implements the SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Uefi/UefiBaseType.h>
+#include <Library/IoLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <IndustryStandard/Pci30.h>
+#include <PchAccess.h>
+#include <Protocol/Spi.h>
+#include <IncludePrivate/Library/PchSpiCommonLib.h>
+#include <IndustryStandard/X58Ich10.h>
+
+/**
+ Initialize an SPI protocol instance.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @exception EFI_UNSUPPORTED The PCH is not supported by this module
+**/
+EFI_STATUS
+SpiProtocolConstructor (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+ UINTN PchSpiBar0;
+
+ //
+ // Initialize the SPI protocol instance
+ //
+ SpiInstance->Signature = PCH_SPI_PRIVATE_DATA_SIGNATURE;
+ SpiInstance->Handle = NULL;
+ SpiInstance->SpiProtocol.Revision = PCH_SPI_SERVICES_REVISION;
+ SpiInstance->SpiProtocol.FlashRead = SpiProtocolFlashRead;
+ SpiInstance->SpiProtocol.FlashWrite = SpiProtocolFlashWrite;
+ SpiInstance->SpiProtocol.FlashErase = SpiProtocolFlashErase;
+ SpiInstance->SpiProtocol.FlashReadSfdp = SpiProtocolFlashReadSfdp;
+ SpiInstance->SpiProtocol.FlashReadJedecId = SpiProtocolFlashReadJedecId;
+ SpiInstance->SpiProtocol.FlashWriteStatus = SpiProtocolFlashWriteStatus;
+ SpiInstance->SpiProtocol.FlashReadStatus = SpiProtocolFlashReadStatus;
+ SpiInstance->SpiProtocol.GetRegionAddress = SpiProtocolGetRegionAddress;
+ SpiInstance->SpiProtocol.ReadPchSoftStrap = SpiProtocolReadPchSoftStrap;
+ SpiInstance->SpiProtocol.ReadCpuSoftStrap = SpiProtocolReadCpuSoftStrap;
+
+ SpiInstance->PchAcpiBase = ICH10_PMBASE_IO;
+ ASSERT (SpiInstance->PchAcpiBase != 0);
+
+ PchSpiBar0 = RCRB + SPIBAR;
+
+ if (PchSpiBar0 == 0) {
+ DEBUG ((DEBUG_ERROR, "ERROR : PchSpiBar0 is invalid!\n"));
+ ASSERT (FALSE);
+ }
+
+ if ((MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC) & B_PCH_SPI_HSFSC_FDV) == 0) {
+ DEBUG ((DEBUG_ERROR, "ERROR : SPI Flash Signature invalid, cannot use the Hardware Sequencing registers!\n"));
+ ASSERT (FALSE);
+ }
+ SpiInstance->ReadPermission = 0xffff;
+ SpiInstance->WritePermission = 0xffff;
+ DEBUG ((DEBUG_INFO, "Flash Region Permission: Read- 0x%04x; Write= 0x%04x\n",
+ SpiInstance->ReadPermission,
+ SpiInstance->WritePermission));
+
+ //
+ SpiInstance->TotalFlashSize = PcdGet32(PcdFlashAreaSize);
+ DEBUG ((DEBUG_INFO, "Total Flash Size : %0x\n", SpiInstance->TotalFlashSize));
+ return EFI_SUCCESS;
+}
+
+/**
+ Delay for at least the request number of microseconds for Runtime usage.
+
+ @param[in] ABase Acpi base address
+ @param[in] Microseconds Number of microseconds to delay.
+
+**/
+VOID
+EFIAPI
+PchPmTimerStallRuntimeSafe (
+ IN UINT16 ABase,
+ IN UINTN Microseconds
+ )
+{
+ UINTN Ticks;
+ UINTN Counts;
+ UINTN CurrentTick;
+ UINTN OriginalTick;
+ UINTN RemainingTick;
+
+ if (Microseconds == 0) {
+ return;
+ }
+
+ OriginalTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) & B_PCH_ACPI_PM1_TMR_VAL;
+ 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 / V_PCH_ACPI_PM1_TMR_MAX_VAL;
+
+ //
+ // Remaining clocks within one loop
+ //
+ RemainingTick = Ticks % V_PCH_ACPI_PM1_TMR_MAX_VAL;
+
+ //
+ // 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) || (RemainingTick > CurrentTick)) {
+ CurrentTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) & B_PCH_ACPI_PM1_TMR_VAL;
+ //
+ // Check if timer overflow
+ //
+ if ((CurrentTick < OriginalTick)) {
+ if (Counts != 0) {
+ Counts--;
+ } else {
+ //
+ // If timer overflow and Counts equ to 0, that means we already stalled more than
+ // RemainingTick, break the loop here
+ //
+ break;
+ }
+ }
+
+ OriginalTick = CurrentTick;
+ }
+}
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashRead (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleRead,
+ Address,
+ ByteCount,
+ Buffer
+ );
+ return Status;
+}
+
+/**
+ Write data to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWrite (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleWrite,
+ Address,
+ ByteCount,
+ Buffer
+ );
+ return Status;
+}
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashErase (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleErase,
+ Address,
+ ByteCount,
+ NULL
+ );
+ return Status;
+}
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadSfdp (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ EFI_STATUS Status;
+ UINT32 FlashAddress;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ Status = EFI_SUCCESS;
+
+ if (ComponentNumber > SpiInstance->NumberOfComponents) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ FlashAddress = 0;
+ if (ComponentNumber == FlashComponent1) {
+ FlashAddress = SpiInstance->Component1StartAddr;
+ }
+ FlashAddress += Address;
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadSfdp,
+ FlashAddress,
+ ByteCount,
+ SfdpData
+ );
+ return Status;
+}
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadJedecId (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ EFI_STATUS Status;
+ UINT32 Address;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ Status = EFI_SUCCESS;
+
+ if (ComponentNumber > SpiInstance->NumberOfComponents) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Address = 0;
+ if (ComponentNumber == FlashComponent1) {
+ Address = SpiInstance->Component1StartAddr;
+ }
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadJedecId,
+ Address,
+ ByteCount,
+ JedecId
+ );
+ return Status;
+}
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWriteStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleWriteStatus,
+ 0,
+ ByteCount,
+ StatusValue
+ );
+ return Status;
+}
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadStatus,
+ 0,
+ ByteCount,
+ StatusValue
+ );
+ return Status;
+}
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolGetRegionAddress (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINTN PchSpiBar0;
+ UINT32 ReadValue;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (FlashRegionType >= FlashRegionMax) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ if (FlashRegionType == FlashRegionAll) {
+ *BaseAddress = 0;
+ *RegionSize = SpiInstance->TotalFlashSize;
+ return EFI_SUCCESS;
+ }
+
+ PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
+ ReadValue = MmioRead32 (PchSpiBar0 + (R_PCH_SPI_FREG0_FLASHD + (S_PCH_SPI_FREGX * ((UINT32) FlashRegionType))));
+ ReleaseSpiBar0 (SpiInstance);
+
+ //
+ // If the region is not used, the Region Base is 7FFFh and Region Limit is 0000h
+ //
+ if (ReadValue == B_PCH_SPI_FREGX_BASE_MASK) {
+ return EFI_DEVICE_ERROR;
+ }
+ *BaseAddress = ((ReadValue & B_PCH_SPI_FREGX_BASE_MASK) >> N_PCH_SPI_FREGX_BASE) <<
+ N_PCH_SPI_FREGX_BASE_REPR;
+ //
+ // Region limit address Bits[11:0] are assumed to be FFFh
+ //
+ *RegionSize = ((((ReadValue & B_PCH_SPI_FREGX_LIMIT_MASK) >> N_PCH_SPI_FREGX_LIMIT) + 1) <<
+ N_PCH_SPI_FREGX_LIMIT_REPR) - *BaseAddress;
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadPchSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINT32 StrapFlashAddr;
+ EFI_STATUS Status;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (ByteCount == 0) {
+ *(UINT16 *) SoftStrapValue = SpiInstance->PchStrapSize;
+ return EFI_SUCCESS;
+ }
+
+ if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->PchStrapSize) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // PCH Strap Flash Address = FPSBA + RamAddr
+ //
+ StrapFlashAddr = SpiInstance->PchStrapBaseAddr + SoftStrapAddr;
+
+ //
+ // Read PCH Soft straps from using execute command
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionDescriptor,
+ FlashCycleRead,
+ StrapFlashAddr,
+ ByteCount,
+ SoftStrapValue
+ );
+ return Status;
+}
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadCpuSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINT32 StrapFlashAddr;
+ EFI_STATUS Status;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (ByteCount == 0) {
+ *(UINT16 *) SoftStrapValue = SpiInstance->CpuStrapSize;
+ return EFI_SUCCESS;
+ }
+
+ if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->CpuStrapSize) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // CPU Strap Flash Address = FCPUSBA + RamAddr
+ //
+ StrapFlashAddr = SpiInstance->CpuStrapBaseAddr + SoftStrapAddr;
+
+ //
+ // Read Cpu Soft straps from using execute command
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionDescriptor,
+ FlashCycleRead,
+ StrapFlashAddr,
+ ByteCount,
+ SoftStrapValue
+ );
+ return Status;
+}
+
+/**
+ This function sends the programmed SPI command to the slave device.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SpiRegionType The SPI Region type for flash cycle which is listed in the Descriptor
+ @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware Sequencing Flash Control Register) register
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in,out] Buffer Pointer to caller-allocated buffer containing the dada received or sent during the SPI cycle.
+
+ @retval EFI_SUCCESS SPI command completes successfully.
+ @retval EFI_DEVICE_ERROR Device error, the command aborts abnormally.
+ @retval EFI_ACCESS_DENIED Some unrecognized command encountered in hardware sequencing mode
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+**/
+EFI_STATUS
+SendSpiCmd (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN FLASH_CYCLE_TYPE FlashCycleType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN OUT UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Index;
+ SPI_INSTANCE *SpiInstance;
+ UINTN SpiBaseAddress;
+ UINTN PchSpiBar0;
+ UINT32 HardwareSpiAddr;
+ UINT32 FlashRegionSize;
+ UINT32 SpiDataCount;
+ UINT32 FlashCycle;
+ UINT32 SmiEnSave;
+ UINT16 ABase;
+
+ Status = EFI_SUCCESS;
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ SpiBaseAddress = SpiInstance->PchSpiBase;
+ PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
+ SpiBaseAddress = SpiInstance->PchSpiBase;
+ ABase = SpiInstance->PchAcpiBase;
+
+ //
+ // Disable SMIs to make sure normal mode flash access is not interrupted by an SMI
+ // whose SMI handler accesses flash (e.g. for error logging)
+ //
+ // *** NOTE: if the SMI_LOCK bit is set (i.e., PMC PCI Offset A0h [4]='1'),
+ // clearing B_GBL_SMI_EN will not have effect. In this situation, some other
+ // synchronization methods must be applied here or in the consumer of the
+ // SendSpiCmd. An example method is disabling the specific SMI sources
+ // whose SMI handlers access flash before flash cycle and re-enabling the SMI
+ // sources after the flash cycle .
+ //
+ SmiEnSave = IoRead32 ((UINTN) (ABase + R_PCH_SMI_EN));
+ IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave & (UINT32) (~B_PCH_SMI_EN_GBL_SMI));
+
+ //
+ // If it's write cycle, disable Prefetching, Caching and disable BIOS Write Protect
+ //
+ if ((FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleErase)) {
+ Status = DisableBiosWriteProtect ();
+ if (EFI_ERROR (Status)) {
+ goto SendSpiCmdEnd;
+ }
+ }
+ //
+ // Make sure it's safe to program the command.
+ //
+ if (!WaitForSpiCycleComplete (This, PchSpiBar0, FALSE)) {
+ Status = EFI_DEVICE_ERROR;
+ goto SendSpiCmdEnd;
+ }
+
+ Status = SpiProtocolGetRegionAddress (This, FlashRegionType, &HardwareSpiAddr, &FlashRegionSize);
+ if (EFI_ERROR (Status)) {
+ goto SendSpiCmdEnd;
+ }
+ HardwareSpiAddr += Address;
+ if ((Address + ByteCount) > FlashRegionSize) {
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ }
+
+ //
+ // Check for PCH SPI hardware sequencing required commands
+ //
+ FlashCycle = 0;
+ switch (FlashCycleType) {
+ case FlashCycleRead:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleWrite:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleErase:
+ if (((ByteCount % SIZE_4KB) != 0) ||
+ ((HardwareSpiAddr % SIZE_4KB) != 0)) {
+ ASSERT (FALSE);
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ }
+ break;
+ case FlashCycleReadSfdp:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_SFDP << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleReadJedecId:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleWriteStatus:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleReadStatus:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_STATUS << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ default:
+ //
+ // Unrecognized Operation
+ //
+ ASSERT (FALSE);
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ break;
+ }
+
+ do {
+ SpiDataCount = ByteCount;
+ if ((FlashCycleType == FlashCycleRead) ||
+ (FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleReadSfdp)) {
+ //
+ // Trim at 256 byte boundary per operation,
+ // - PCH SPI controller requires trimming at 4KB boundary
+ // - Some SPI chips require trimming at 256 byte boundary for write operation
+ // - Trimming has limited performance impact as we can read / write atmost 64 byte
+ // per operation
+ //
+ if (HardwareSpiAddr + ByteCount > ((HardwareSpiAddr + BIT8) &~(BIT8 - 1))) {
+ SpiDataCount = (((UINT32) (HardwareSpiAddr) + BIT8) &~(BIT8 - 1)) - (UINT32) (HardwareSpiAddr);
+ }
+ //
+ // Calculate the number of bytes to shift in/out during the SPI data cycle.
+ // Valid settings for the number of bytes duing each data portion of the
+ // PCH SPI cycles are: 0, 1, 2, 3, 4, 5, 6, 7, 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ if (SpiDataCount >= 64) {
+ SpiDataCount = 64;
+ } else if ((SpiDataCount &~0x07) != 0) {
+ SpiDataCount = SpiDataCount &~0x07;
+ }
+ }
+ if (FlashCycleType == FlashCycleErase) {
+ if (((ByteCount / SIZE_64KB) != 0) &&
+ ((ByteCount % SIZE_64KB) == 0) &&
+ ((HardwareSpiAddr % SIZE_64KB) == 0)) {
+ if (HardwareSpiAddr < SpiInstance->Component1StartAddr) {
+ //
+ // Check whether Component0 support 64k Erase
+ //
+ if ((SpiInstance->SfdpVscc0Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K) != 0) {
+ SpiDataCount = SIZE_64KB;
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ } else {
+ //
+ // Check whether Component1 support 64k Erase
+ //
+ if ((SpiInstance->SfdpVscc1Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K) != 0) {
+ SpiDataCount = SIZE_64KB;
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ }
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ if (SpiDataCount == SIZE_4KB) {
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_4K_ERASE << N_PCH_SPI_HSFSC_CYCLE);
+ } else {
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_64K_ERASE << N_PCH_SPI_HSFSC_CYCLE);
+ }
+ }
+ //
+ // If it's write cycle, load data into the SPI data buffer.
+ //
+ if ((FlashCycleType == FlashCycleWrite) || (FlashCycleType == FlashCycleWriteStatus)) {
+ if ((SpiDataCount & 0x07) != 0) {
+ //
+ // Use Byte write if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
+ //
+ for (Index = 0; Index < SpiDataCount; Index++) {
+ MmioWrite8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, Buffer[Index]);
+ }
+ } else {
+ //
+ // Use Dword write if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
+ MmioWrite32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, *(UINT32 *) (Buffer + Index));
+ }
+ }
+ }
+
+ //
+ // Set the Flash Address
+ //
+ MmioWrite32 (
+ (PchSpiBar0 + R_PCH_SPI_FADDR),
+ (UINT32) (HardwareSpiAddr & B_PCH_SPI_FADDR_MASK)
+ );
+
+ //
+ // Set Data count, Flash cycle, and Set Go bit to start a cycle
+ //
+ MmioAndThenOr32 (
+ PchSpiBar0 + R_PCH_SPI_HSFSC,
+ (UINT32) (~(B_PCH_SPI_HSFSC_FDBC_MASK | B_PCH_SPI_HSFSC_CYCLE_MASK)),
+ (UINT32) ((((SpiDataCount - 1) << N_PCH_SPI_HSFSC_FDBC) & B_PCH_SPI_HSFSC_FDBC_MASK) | FlashCycle | B_PCH_SPI_HSFSC_CYCLE_FGO)
+ );
+ //
+ // end of command execution
+ //
+ // Wait the SPI cycle to complete.
+ //
+ if (!WaitForSpiCycleComplete (This, PchSpiBar0, TRUE)) {
+ ASSERT (FALSE);
+ Status = EFI_DEVICE_ERROR;
+ goto SendSpiCmdEnd;
+ }
+ //
+ // If it's read cycle, load data into the call's buffer.
+ //
+ if ((FlashCycleType == FlashCycleRead) ||
+ (FlashCycleType == FlashCycleReadSfdp) ||
+ (FlashCycleType == FlashCycleReadJedecId) ||
+ (FlashCycleType == FlashCycleReadStatus)) {
+ if ((SpiDataCount & 0x07) != 0) {
+ //
+ // Use Byte read if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
+ //
+ for (Index = 0; Index < SpiDataCount; Index++) {
+ Buffer[Index] = MmioRead8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index);
+ }
+ } else {
+ //
+ // Use Dword read if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
+ *(UINT32 *) (Buffer + Index) = MmioRead32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index);
+ }
+ }
+ }
+
+ HardwareSpiAddr += SpiDataCount;
+ Buffer += SpiDataCount;
+ ByteCount -= SpiDataCount;
+ } while (ByteCount > 0);
+
+SendSpiCmdEnd:
+ //
+ // Restore the settings for SPI Prefetching and Caching and enable BIOS Write Protect
+ //
+ if ((FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleErase)) {
+ EnableBiosWriteProtect ();
+ }
+ //
+ // Restore SMIs.
+ //
+ IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave);
+
+ ReleaseSpiBar0 (SpiInstance);
+ return Status;
+}
+
+/**
+ Wait execution cycle to complete on the SPI interface.
+
+ @param[in] This The SPI protocol instance
+ @param[in] PchSpiBar0 Spi MMIO base address
+ @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
+
+ @retval TRUE SPI cycle completed on the interface.
+ @retval FALSE Time out while waiting the SPI cycle to complete.
+ It's not safe to program the next command on the SPI interface.
+**/
+BOOLEAN
+WaitForSpiCycleComplete (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINTN PchSpiBar0,
+ IN BOOLEAN ErrorCheck
+ )
+{
+ UINT64 WaitTicks;
+ UINT64 WaitCount;
+ UINT32 Data32;
+ SPI_INSTANCE *SpiInstance;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ //
+ // Convert the wait period allowed into to tick count
+ //
+ WaitCount = SPI_WAIT_TIME / SPI_WAIT_PERIOD;
+ //
+ // Wait for the SPI cycle to complete.
+ //
+ for (WaitTicks = 0; WaitTicks < WaitCount; WaitTicks++) {
+ Data32 = MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC);
+ if ((Data32 & B_PCH_SPI_HSFSC_SCIP) == 0) {
+ MmioWrite32 (PchSpiBar0 + R_PCH_SPI_HSFSC, B_PCH_SPI_HSFSC_FCERR | B_PCH_SPI_HSFSC_FDONE);
+ if (((Data32 & B_PCH_SPI_HSFSC_FCERR) != 0) && (ErrorCheck == TRUE)) {
+ return FALSE;
+ } else {
+ return TRUE;
+ }
+ }
+ PchPmTimerStallRuntimeSafe (SpiInstance->PchAcpiBase, SPI_WAIT_PERIOD);
+ }
+ return FALSE;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
new file mode 100644
index 0000000000..8fb4947b1a
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
@@ -0,0 +1,410 @@
+/** @file
+ A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
+ EFI_SMM_CONTROL2_PROTOCOL.
+
+ We expect the PEI phase to have covered the following:
+ - ensure that the underlying QEMU machine type be X58
+ (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
+ - ensure that the ACPI PM IO space be configured
+ (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
+
+ Our own entry point is responsible for confirming the SMI feature and for
+ configuring it.
+
+ Copyright (C) 2013, 2015, Red Hat, Inc.<BR>
+ Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <IndustryStandard/X58Ich10.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/PcdLib.h>
+#include <Library/PciLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Protocol/S3SaveState.h>
+#include <Protocol/SmmControl2.h>
+
+//
+// Forward declaration.
+//
+STATIC
+VOID
+EFIAPI
+OnS3SaveStateInstalled (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ );
+
+//
+// The absolute IO port address of the SMI Control and Enable Register. It is
+// only used to carry information from the entry point function to the
+// S3SaveState protocol installation callback, strictly before the runtime
+// phase.
+//
+STATIC UINTN mSmiEnable;
+
+//
+// Event signaled when an S3SaveState protocol interface is installed.
+//
+STATIC EFI_EVENT mS3SaveStateInstalled;
+
+/**
+ Clear the SMI status
+
+ @retval EFI_SUCCESS The function completes successfully
+ @retval EFI_DEVICE_ERROR Something error occurred
+
+**/
+EFI_STATUS
+EFIAPI
+SmmClear(
+ VOID
+)
+{
+ EFI_STATUS Status;
+ UINT32 OutputData;
+ UINT32 OutputPort;
+ UINT32 PmBase;
+
+ Status = EFI_SUCCESS;
+ PmBase = ICH10_PMBASE_IO;
+
+ OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_STS;
+ OutputData = ICH10_SMI_STS_APM;
+ IoWrite32(
+ (UINTN)OutputPort,
+ (UINT32)(OutputData)
+ );
+
+ ///
+ /// Set the EOS Bit
+ ///
+ OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_EN;
+ OutputData = IoRead32((UINTN)OutputPort);
+ OutputData |= ICH10_SMI_EN_EOS;
+ IoWrite32(
+ (UINTN)OutputPort,
+ (UINT32)(OutputData)
+ );
+
+ ///
+ /// There is no need to read EOS back and check if it is set.
+ /// This can lead to a reading of zero if an SMI occurs right after the SMI_EN port read
+ /// but before the data is returned to the CPU.
+ /// SMM Dispatcher should make sure that EOS is set after all SMI sources are processed.
+ ///
+ return Status;
+}
+
+/**
+ Invokes SMI activation from either the preboot or runtime environment.
+
+ This function generates an SMI.
+
+ @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
+ @param[in,out] CommandPort The value written to the command port.
+ @param[in,out] DataPort The value written to the data port.
+ @param[in] Periodic Optional mechanism to engender a periodic
+ stream.
+ @param[in] ActivationInterval Optional parameter to repeat at this
+ period one time or, if the Periodic
+ Boolean is set, periodically.
+
+ @retval EFI_SUCCESS The SMI/PMI has been engendered.
+ @retval EFI_DEVICE_ERROR The timing is unsupported.
+ @retval EFI_INVALID_PARAMETER The activation period is unsupported.
+ @retval EFI_INVALID_PARAMETER The last periodic activation has not been
+ cleared.
+ @retval EFI_NOT_STARTED The SMM base service has not been initialized.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+SmmControl2DxeTrigger (
+ IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
+ IN OUT UINT8 *CommandPort OPTIONAL,
+ IN OUT UINT8 *DataPort OPTIONAL,
+ IN BOOLEAN Periodic OPTIONAL,
+ IN UINTN ActivationInterval OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ //
+ // No support for queued or periodic activation.
+ //
+ if (Periodic || ActivationInterval > 0) {
+ return EFI_DEVICE_ERROR;
+ }
+ ///
+ /// Clear any pending the APM SMI
+ ///
+ Status = SmmClear();
+ //
+ // The so-called "Advanced Power Management Status Port Register" is in fact
+ // a generic data passing register, between the caller and the SMI
+ // dispatcher. The ICH9 spec calls it "scratchpad register" -- calling it
+ // "status" elsewhere seems quite the misnomer. Status registers usually
+ // report about hardware status, while this register is fully governed by
+ // software.
+ //
+ // Write to the status register first, as this won't trigger the SMI just
+ // yet. Then write to the control register.
+ //
+ IoWrite8 (ICH10_APM_STS, DataPort == NULL ? 0 : *DataPort);
+ IoWrite8 (ICH10_APM_CNT, CommandPort == NULL ? 0 : *CommandPort);
+ return EFI_SUCCESS;
+}
+
+/**
+ Clears any system state that was created in response to the Trigger() call.
+
+ This function acknowledges and causes the deassertion of the SMI activation
+ source.
+
+ @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
+ @param[in] Periodic Optional parameter to repeat at this period
+ one time
+
+ @retval EFI_SUCCESS The SMI/PMI has been engendered.
+ @retval EFI_DEVICE_ERROR The source could not be cleared.
+ @retval EFI_INVALID_PARAMETER The service did not support the Periodic input
+ argument.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+SmmControl2DxeClear (
+ IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
+ IN BOOLEAN Periodic OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ if (Periodic) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // The PI spec v1.4 explains that Clear() is only supposed to clear software
+ // status; it is not in fact responsible for deasserting the SMI. It gives
+ // two reasons for this: (a) many boards clear the SMI automatically when
+ // entering SMM, (b) if Clear() actually deasserted the SMI, then it could
+ // incorrectly suppress an SMI that was asynchronously asserted between the
+ // last return of the SMI handler and the call made to Clear().
+ //
+ // In fact QEMU automatically deasserts CPU_INTERRUPT_SMI in:
+ // - x86_cpu_exec_interrupt() [target-i386/seg_helper.c], and
+ // - kvm_arch_pre_run() [target-i386/kvm.c].
+ //
+ // So, nothing to do here.
+ //
+ Status = SmmClear();
+
+ return EFI_SUCCESS;
+}
+
+STATIC EFI_SMM_CONTROL2_PROTOCOL mControl2 = {
+ &SmmControl2DxeTrigger,
+ &SmmControl2DxeClear,
+ MAX_UINTN // MinimumTriggerPeriod -- we don't support periodic SMIs
+};
+
+//
+// Entry point of this driver.
+//
+EFI_STATUS
+EFIAPI
+SmmControl2DxeEntryPoint (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ UINT32 PmBase;
+ UINT32 SmiEnableVal;
+ EFI_STATUS Status;
+
+ //
+ // This module should only be included if SMRAM support is required.
+ //
+ ASSERT (FeaturePcdGet (PcdSmmSmramRequire));
+
+ //
+ // Calculate the absolute IO port address of the SMI Control and Enable
+ // Register. (As noted at the top, the PEI phase has left us with a working
+ // ACPI PM IO space.)
+ //
+ PmBase = PciRead32 (POWER_MGMT_REGISTER_ICH10 (ICH10_PMBASE)) &
+ ICH10_PMBASE_MASK;
+ mSmiEnable = PmBase + ICH10_PMBASE_OFS_SMI_EN;
+
+ //
+ // If APMC_EN is pre-set in SMI_EN, that's QEMU's way to tell us that SMI
+ // support is not available. (For example due to KVM lacking it.) Otherwise,
+ // this bit is clear after each reset.
+ //
+ SmiEnableVal = IoRead32 (mSmiEnable);
+ if ((SmiEnableVal & ICH10_SMI_EN_APMC_EN) != 0) {
+ DEBUG ((EFI_D_ERROR, "%a: this X58 implementation lacks SMI\n",
+ __FUNCTION__));
+ }
+
+ //
+ // Otherwise, configure the board to inject an SMI when ICH10_APM_CNT is
+ // written to. (See the Trigger() method above.)
+ //
+ SmiEnableVal |= ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
+ IoWrite32 (mSmiEnable, SmiEnableVal);
+
+ //
+ // Prevent software from undoing the above (until platform reset).
+ //
+ PciOr16 (POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
+ ICH10_GEN_PMCON_1_SMI_LOCK);
+
+ //
+ // If we can clear GBL_SMI_EN now, that means QEMU's SMI support is not
+ // appropriate.
+ //
+ IoWrite32 (mSmiEnable, SmiEnableVal & ~(UINT32)ICH10_SMI_EN_GBL_SMI_EN);
+ if (IoRead32 (mSmiEnable) != SmiEnableVal) {
+ DEBUG ((EFI_D_ERROR, "%a: failed to lock down GBL_SMI_EN\n",
+ __FUNCTION__));
+ goto FatalError;
+ }
+
+ VOID *Registration;
+
+ //
+ // On S3 resume the above register settings have to be repeated. Register a
+ // protocol notify callback that, when boot script saving becomes
+ // available, saves operations equivalent to the above to the boot script.
+ //
+ Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK,
+ OnS3SaveStateInstalled, NULL /* Context */,
+ &mS3SaveStateInstalled);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: CreateEvent: %r\n", __FUNCTION__, Status));
+ goto FatalError;
+ }
+
+ Status = gBS->RegisterProtocolNotify (&gEfiS3SaveStateProtocolGuid,
+ mS3SaveStateInstalled, &Registration);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: RegisterProtocolNotify: %r\n", __FUNCTION__,
+ Status));
+ goto ReleaseEvent;
+ }
+
+ //
+ // Kick the event right now -- maybe the boot script is already saveable.
+ //
+ Status = gBS->SignalEvent (mS3SaveStateInstalled);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: SignalEvent: %r\n", __FUNCTION__, Status));
+ goto ReleaseEvent;
+ }
+
+ //
+ // We have no pointers to convert to virtual addresses. The handle itself
+ // doesn't matter, as protocol services are not accessible at runtime.
+ //
+ Status = gBS->InstallMultipleProtocolInterfaces (&ImageHandle,
+ &gEfiSmmControl2ProtocolGuid, &mControl2,
+ NULL);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: InstallMultipleProtocolInterfaces: %r\n",
+ __FUNCTION__, Status));
+ goto ReleaseEvent;
+ }
+
+ return EFI_SUCCESS;
+
+ReleaseEvent:
+ if (mS3SaveStateInstalled != NULL) {
+ gBS->CloseEvent (mS3SaveStateInstalled);
+ }
+
+FatalError:
+ //
+ // We really don't want to continue in this case.
+ //
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ return EFI_UNSUPPORTED;
+}
+
+/**
+ Notification callback for S3SaveState installation.
+
+ @param[in] Event Event whose notification function is being invoked.
+
+ @param[in] Context The pointer to the notification function's context, which
+ is implementation-dependent.
+**/
+STATIC
+VOID
+EFIAPI
+OnS3SaveStateInstalled (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+{
+ EFI_STATUS Status;
+ EFI_S3_SAVE_STATE_PROTOCOL *S3SaveState;
+ UINT32 SmiEnOrMask, SmiEnAndMask;
+ UINT16 GenPmCon1OrMask, GenPmCon1AndMask;
+
+ ASSERT (Event == mS3SaveStateInstalled);
+
+ Status = gBS->LocateProtocol (&gEfiS3SaveStateProtocolGuid,
+ NULL /* Registration */, (VOID **)&S3SaveState);
+ if (EFI_ERROR (Status)) {
+ return;
+ }
+
+ //
+ // These operations were originally done, verified and explained in the entry
+ // point function of the driver.
+ //
+ SmiEnOrMask = ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
+ SmiEnAndMask = MAX_UINT32;
+ Status = S3SaveState->Write (
+ S3SaveState,
+ EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE,
+ EfiBootScriptWidthUint32,
+ (UINT64)mSmiEnable,
+ &SmiEnOrMask,
+ &SmiEnAndMask
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE: %r\n",
+ __FUNCTION__, Status));
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ }
+
+ GenPmCon1OrMask = ICH10_GEN_PMCON_1_SMI_LOCK;
+ GenPmCon1AndMask = MAX_UINT16;
+ Status = S3SaveState->Write (
+ S3SaveState,
+ EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE,
+ EfiBootScriptWidthUint16,
+ (UINT64)POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
+ &GenPmCon1OrMask,
+ &GenPmCon1AndMask
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR,
+ "%a: EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE: %r\n", __FUNCTION__,
+ Status));
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ }
+
+ DEBUG ((EFI_D_VERBOSE, "%a: boot script fragment saved\n", __FUNCTION__));
+ gBS->CloseEvent (Event);
+ mS3SaveStateInstalled = NULL;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
new file mode 100644
index 0000000000..19eb469657
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
@@ -0,0 +1,175 @@
+/** @file
+ PCH SPI SMM Driver implements the SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include "PchSpi.h"
+
+//
+// Global variables
+//
+GLOBAL_REMOVE_IF_UNREFERENCED SPI_INSTANCE *mSpiInstance;
+//
+// mPchSpiResvMmioAddr keeps the reserved MMIO range assiged to SPI.
+// In SMM it always set back the reserved MMIO address to SPI BAR0 to ensure the MMIO range
+// won't overlap with SMRAM range, and trusted.
+//
+GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mSpiResvMmioAddr;
+
+/**
+ <b>SPI Runtime SMM Module Entry Point</b>\n
+ - <b>Introduction</b>\n
+ The SPI SMM module provide a standard way for other modules to use the PCH SPI Interface in SMM.
+
+ - @pre
+ - EFI_SMM_BASE2_PROTOCOL
+ - Documented in System Management Mode Core Interface Specification .
+
+ - @result
+ The SPI SMM driver produces @link _PCH_SPI_PROTOCOL PCH_SPI_PROTOCOL @endlink with GUID
+ gPchSmmSpiProtocolGuid which is different from SPI RUNTIME driver.
+
+ - <b>Integration Check List</b>\n
+ - This driver supports Descriptor Mode only.
+ - This driver supports Hardware Sequence only.
+ - When using SMM SPI Protocol to perform flash access in an SMI handler,
+ and the SMI occurrence is asynchronous to normal mode code execution,
+ proper synchronization mechanism must be applied, e.g. disable SMI before
+ the normal mode SendSpiCmd() starts and re-enable SMI after
+ the normal mode SendSpiCmd() completes.
+ @note The implementation of SendSpiCmd() uses GBL_SMI_EN in
+ SMI_EN register (ABase + 30h) to disable and enable SMIs. But this may
+ not be effective as platform may well set the SMI_LOCK bit (i.e., PMC PCI Offset A0h [4]).
+ So the synchronization at caller level is likely needed.
+
+ @param[in] ImageHandle Image handle of this driver.
+ @param[in] SystemTable Global system service table.
+
+ @retval EFI_SUCCESS Initialization complete.
+ @exception EFI_UNSUPPORTED The chipset is unsupported by this driver.
+ @retval EFI_OUT_OF_RESOURCES Do not have enough resources to initialize the driver.
+ @retval EFI_DEVICE_ERROR Device error, driver exits abnormally.
+**/
+EFI_STATUS
+EFIAPI
+InstallPchSpi (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Init PCH spi reserved MMIO address.
+ //
+ mSpiResvMmioAddr = PCH_SPI_BASE_ADDRESS;
+
+ ///
+ /// Allocate pool for SPI protocol instance
+ ///
+ Status = gSmst->SmmAllocatePool (
+ EfiRuntimeServicesData, /// MemoryType don't care
+ sizeof (SPI_INSTANCE),
+ (VOID **) &mSpiInstance
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (mSpiInstance == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ ZeroMem ((VOID *) mSpiInstance, sizeof (SPI_INSTANCE));
+ ///
+ /// Initialize the SPI protocol instance
+ ///
+ Status = SpiProtocolConstructor (mSpiInstance);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+ //
+ // Install the SMM EFI_SPI_PROTOCOL interface
+ //
+ Status = gSmst->SmmInstallProtocolInterface (
+ &(mSpiInstance->Handle),
+ &gEfiSmmSpiProtocolGuid,
+ EFI_NATIVE_INTERFACE,
+ &(mSpiInstance->SpiProtocol)
+ );
+ if (EFI_ERROR (Status)) {
+ gSmst->SmmFreePool (mSpiInstance);
+ return EFI_DEVICE_ERROR;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Acquire PCH spi mmio address.
+ It is not expected for this BAR0 to change because the SPI device is hidden
+ from the OS for SKL PCH LP/H B stepping and above (refer to section 3.5.1),
+ but if it is ever different from the preallocated address, reassign it back.
+ In SMM, it always override the BAR0 and returns the reserved MMIO range for SPI.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval PchSpiBar0 return SPI MMIO address
+**/
+UINTN
+AcquireSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+ //
+ // SPIBAR0 will be different before and after PCI enum so need to get it from SPI BAR0 reg.
+ //
+ return mSpiResvMmioAddr;
+}
+
+/**
+ Release pch spi mmio address. Do nothing.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval None
+**/
+VOID
+ReleaseSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+}
+
+/**
+ This function is a hook for Spi to disable BIOS Write Protect
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in SMM phase
+
+**/
+EFI_STATUS
+EFIAPI
+DisableBiosWriteProtect (
+ VOID
+ )
+{
+
+ return EFI_SUCCESS;
+}
+
+/**
+ This function is a hook for Spi to enable BIOS Write Protect
+
+
+**/
+VOID
+EFIAPI
+EnableBiosWriteProtect (
+ VOID
+ )
+{
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
new file mode 100644
index 0000000000..f9d340d6df
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
@@ -0,0 +1,22 @@
+## @file
+# Copyright (c) 2014 - 2016 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ DEC_SPECIFICATION = 0x00010005
+ PACKAGE_NAME = ICH10Pkg
+ PACKAGE_GUID = 4E97AC4B-F64C-4008-BBDE-01CC3B0BAA6B
+ PACKAGE_VERSION = 0.91
+
+[Includes]
+ Include
+
+[Ppis]
+
+[Guids]
+ gEfiPchTokenSpaceGuid = { 0x89a1b278, 0xa1a1, 0x4df7, { 0xb1, 0x37, 0xde, 0x5a, 0xd7, 0xc4, 0x79, 0x13 } }
+[Protocols]
+ gEfiSmmSpiProtocolGuid = {0xbd75fe35, 0xfdce, 0x49d7, {0xa9, 0xdd, 0xb2, 0x6f, 0x1f, 0xc6, 0xb4, 0x37}}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
new file mode 100644
index 0000000000..c36360bcb0
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
@@ -0,0 +1,98 @@
+/** @file
+ The header file includes the common header files, defines
+ internal structure and functions used by SpiFlashCommonLib.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef __SPI_FLASH_COMMON_LIB_H__
+#define __SPI_FLASH_COMMON_LIB_H__
+
+#include <Uefi.h>
+#include <Library/BaseLib.h>
+#include <Library/PcdLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+
+#define SECTOR_SIZE_4KB 0x1000 // Common 4kBytes sector size
+/**
+ Enable block protection on the Serial Flash device.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashLock (
+ VOID
+ );
+
+/**
+ Read NumBytes bytes of data from the address specified by
+ PAddress into Buffer.
+
+ @param[in] Address The starting physical address of the read.
+ @param[in,out] NumBytes On input, the number of bytes to read. On output, the number
+ of bytes actually read.
+ @param[out] Buffer The destination data buffer for the read.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashRead (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write NumBytes bytes of data from Buffer to the address specified by
+ PAddresss.
+
+ @param[in] Address The starting physical address of the write.
+ @param[in,out] NumBytes On input, the number of bytes to write. On output,
+ the actual number of bytes written.
+ @param[in] Buffer The source data buffer for the write.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashWrite (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase the block starting at Address.
+
+ @param[in] Address The starting physical address of the block to be erased.
+ This library assume that caller garantee that the PAddress
+ is at the starting address of this block.
+ @param[in] NumBytes On input, the number of bytes of the logical block to be erased.
+ On output, the actual number of bytes erased.
+
+ @retval EFI_SUCCESS. Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashBlockErase (
+ IN UINTN Address,
+ IN UINTN *NumBytes
+ );
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
new file mode 100644
index 0000000000..552ce28d8c
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
@@ -0,0 +1,43 @@
+/** @file
+ Macros that simplify accessing PCH devices's PCI registers.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_ACCESS_H_
+#define _PCH_ACCESS_H_
+
+#include "PchReservedResources.h"
+
+#ifndef STALL_ONE_MICRO_SECOND
+#define STALL_ONE_MICRO_SECOND 1
+#endif
+#ifndef STALL_ONE_SECOND
+#define STALL_ONE_SECOND 1000000
+#endif
+
+
+///
+/// The default PCH PCI bus number
+///
+#define DEFAULT_PCI_BUS_NUMBER_PCH 0
+
+//
+// Default Vendor ID and Subsystem ID
+//
+#define V_PCH_INTEL_VENDOR_ID 0x8086 ///< Default Intel PCH Vendor ID
+#define V_PCH_DEFAULT_SID 0x7270 ///< Default Intel PCH Subsystem ID
+#define V_PCH_DEFAULT_SVID_SID (V_INTEL_VENDOR_ID + (V_PCH_DEFAULT_SID << 16)) ///< Default INTEL PCH Vendor ID and Subsystem ID
+
+//
+// Include device register definitions
+//
+
+#include "Register/PchRegsPmc.h"
+
+#include "Register/PchRegsSpi.h"
+
+#endif
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
new file mode 100644
index 0000000000..d503d130c8
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
@@ -0,0 +1,94 @@
+/** @file
+ Build time limits of PCH resources.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_LIMITS_H_
+#define _PCH_LIMITS_H_
+
+//
+// PCIe limits
+//
+#define PCH_MAX_PCIE_ROOT_PORTS PCH_H_PCIE_MAX_ROOT_PORTS
+#define PCH_H_PCIE_MAX_ROOT_PORTS 20
+#define PCH_LP_PCIE_MAX_ROOT_PORTS 12
+
+#define PCH_MAX_PCIE_CONTROLLERS PCH_H_PCIE_MAX_CONTROLLERS
+#define PCH_PCIE_CONTROLLER_PORTS 4
+#define PCH_H_PCIE_MAX_CONTROLLERS (PCH_H_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
+#define PCH_LP_PCIE_MAX_CONTROLLERS (PCH_LP_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
+
+//
+// PCIe clocks limits
+//
+#define PCH_LP_PCIE_MAX_CLK_REQ 6
+#define PCH_H_PCIE_MAX_CLK_REQ 16
+
+//
+// RST PCIe Storage Cycle Router limits
+//
+#define PCH_MAX_RST_PCIE_STORAGE_CR 3
+
+//
+// SATA limits
+//
+#define PCH_MAX_SATA_PORTS PCH_H_AHCI_MAX_PORTS
+#define PCH_H_AHCI_MAX_PORTS 8 ///< Max number of sata ports in SKL PCH H
+#define PCH_LP_AHCI_MAX_PORTS 3 ///< Max number of sata ports in SKL PCH LP
+#define PCH_SATA_MAX_DEVICES_PER_PORT 1 ///< Max support device numner per port, Port Multiplier is not support.
+
+//
+// USB limits
+//
+#define PCH_MAX_USB2_PORTS PCH_H_XHCI_MAX_USB2_PORTS
+
+#define PCH_H_XHCI_MAX_USB2_PHYSICAL_PORTS 14 ///< Max Physical Connector XHCI, not counting virtual ports like USB-R.
+#define PCH_LP_XHCI_MAX_USB2_PHYSICAL_PORTS 10 ///< Max Physical Connector XHCI, not counting virtual ports like USB-R.
+
+#define PCH_H_XHCI_MAX_USB2_PORTS 16 ///< 14 High Speed lanes + Including two ports reserved for USBr
+#define PCH_LP_XHCI_MAX_USB2_PORTS 12 ///< 10 High Speed lanes + Including two ports reserved for USBr
+
+#define PCH_MAX_USB3_PORTS PCH_H_XHCI_MAX_USB3_PORTS
+
+#define PCH_H_XHCI_MAX_USB3_PORTS 10 ///< 10 Super Speed lanes
+#define PCH_LP_XHCI_MAX_USB3_PORTS 6 ///< 6 Super Speed lanes
+
+#define PCH_XHCI_MAX_SSIC_PORT_COUNT 2 ///< 2 SSIC ports in SKL PCH-LP and SKL PCH-H
+
+//
+// SerialIo limits
+//
+#define PCH_SERIALIO_MAX_CONTROLLERS 11 ///< Number of SerialIo controllers, this includes I2C, SPI and UART
+#define PCH_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo I2C controllers
+#define PCH_LP_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo I2C controllers for PCH-LP
+#define PCH_H_SERIALIO_MAX_I2C_CONTROLLERS 4 ///< Number of SerialIo I2C controllers for PCH-H
+#define PCH_SERIALIO_MAX_SPI_CONTROLLERS 2 ///< Number of SerialIo SPI controllers
+#define PCH_SERIALIO_MAX_UART_CONTROLLERS 3 ///< Number of SerialIo UART controllers
+
+//
+// ISH limits
+//
+#define PCH_ISH_MAX_GP_PINS 8
+#define PCH_ISH_MAX_UART_CONTROLLERS 2
+#define PCH_ISH_MAX_I2C_CONTROLLERS 3
+#define PCH_ISH_MAX_SPI_CONTROLLERS 1
+
+//
+// SCS limits
+//
+#define PCH_SCS_MAX_CONTROLLERS 3 ///< Number of Storage and Communication Subsystem controllers, this includes eMMC, SDIO, SDCARD
+
+//
+// Flash Protection Range Register
+//
+#define PCH_FLASH_PROTECTED_RANGES 5
+
+//
+// Number of eSPI slaves
+//
+#define PCH_ESPI_MAX_SLAVE_ID 2
+#endif // _PCH_LIMITS_H_
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
new file mode 100644
index 0000000000..00139fc230
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
@@ -0,0 +1,60 @@
+/** @file
+ PCH preserved MMIO resource definitions.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_PRESERVED_RESOURCES_H_
+#define _PCH_PRESERVED_RESOURCES_H_
+
+/**
+ PCH preserved MMIO range, 24 MB, from 0xFD000000 to 0xFE7FFFFF
+
+ Detailed recommended static allocation
+ +-------------------------------------------------------------------------+
+ | Size | Start | End | Usage |
+ | 16 MB | 0xFD000000 | 0xFDFFFFFF | SBREG |
+ | 64 KB | 0xFE000000 | 0xFE00FFFF | PMC MBAR |
+ | 4 KB | 0xFE010000 | 0xFE010FFF | SPI BAR0 |
+ | 88 KB | 0xFE020000 | 0xFE035FFF | SerialIo BAR in ACPI mode |
+ | 24 KB | 0xFE036000 | 0xFE03BFFF | Unused |
+ | 4 KB | 0xFE03C000 | 0xFE03CFFF | Thermal Device in ACPI mode |
+ | 524 KB | 0xFE03D000 | 0xFE0BFFFF | Unused |
+ | 256 KB | 0xFE0C0000 | 0xFE0FFFFF | TraceHub FW BAR |
+ | 1 MB | 0xFE100000 | 0xFE1FFFFF | TraceHub MTB BAR |
+ | 2 MB | 0xFE200000 | 0xFE3FFFFF | TraceHub SW BAR |
+ | 64 KB | 0xFE400000 | 0xFE40FFFF | CIO2 MMIO BAR in ACPI mode |
+ | 2 MB - 64KB | 0xFE410000 | 0xFE5FFFFF | Unused |
+ | 2 MB | 0xFE600000 | 0xFE7FFFFF | Temp address |
+ +-------------------------------------------------------------------------+
+**/
+#define PCH_PRESERVED_BASE_ADDRESS 0xFD000000 ///< Pch preserved MMIO base address
+#define PCH_PRESERVED_MMIO_SIZE 0x01800000 ///< 24MB
+#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO base address
+#define PCH_PCR_MMIO_SIZE 0x01000000 ///< 16MB
+#define PCH_PWRM_BASE_ADDRESS 0xFE000000 ///< PMC MBAR MMIO base address
+#define PCH_PWRM_MMIO_SIZE 0x00010000 ///< 64KB
+#define PCH_SPI_BASE_ADDRESS 0xFED1C000 + 0x3800 ///< SPI MBAR MMIO base address
+#define PCH_SPI_MMIO_SIZE 0x00001000 ///< 4KB
+#define PCH_SERIAL_IO_BASE_ADDRESS 0xFE020000 ///< SerialIo MMIO base address
+#define PCH_SERIAL_IO_MMIO_SIZE 0x00016000 ///< 88KB
+#define PCH_THERMAL_BASE_ADDRESS 0xFE03C000 ///< Thermal Device in ACPI mode
+#define PCH_THERMAL_MMIO_SIZE 0x00001000 ///< 4KB
+#define PCH_TRACE_HUB_FW_BASE_ADDRESS 0xFE0C0000 ///< TraceHub FW MMIO base address
+#define PCH_TRACE_HUB_FW_MMIO_SIZE 0x00040000 ///< 256KB
+#define PCH_TRACE_HUB_MTB_BASE_ADDRESS 0xFE100000 ///< TraceHub MTB MMIO base address
+#define PCH_TRACE_HUB_MTB_MMIO_SIZE 0x00100000 ///< 1MB
+#define PCH_TRACE_HUB_SW_BASE_ADDRESS 0xFE200000 ///< TraceHub SW MMIO base address
+#define PCH_TRACE_HUB_SW_MMIO_SIZE 0x00200000 ///< 2MB
+#define PCH_CIO2_BASE_ADDRESS 0xFE400000 ///< CIO2 MMIO BAR in ACPI mode
+#define PCH_CIO2_MMIO_SIZE 0x00010000 ///< 64KB
+#define PCH_TEMP_BASE_ADDRESS 0xFE600000 ///< preserved temp address for misc usage
+#define PCH_TEMP_MMIO_SIZE 0x00200000 ///< 2MB
+
+#define RCRB 0xFED1C000
+#define SPIBAR 0x3800
+
+#endif // _PCH_PRESERVED_RESOURCES_H_
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
new file mode 100644
index 0000000000..cb5f26c47b
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
@@ -0,0 +1,295 @@
+/** @file
+ This file defines the PCH SPI Protocol which implements the
+ Intel(R) PCH SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_PROTOCOL_H_
+#define _PCH_SPI_PROTOCOL_H_
+
+//
+// Extern the GUID for protocol users.
+//
+extern EFI_GUID gEfiSpiProtocolGuid;
+extern EFI_GUID gEfiSmmSpiProtocolGuid;
+
+//
+// Forward reference for ANSI C compatibility
+//
+typedef struct _PCH_SPI_PROTOCOL EFI_SPI_PROTOCOL;
+
+//
+// SPI protocol data structures and definitions
+//
+
+/**
+ Flash Region Type
+**/
+typedef enum {
+ FlashRegionDescriptor,
+ FlashRegionBios,
+ FlashRegionMe,
+ FlashRegionGbE,
+ FlashRegionPlatformData,
+ FlashRegionDer,
+ FlashRegionAll,
+ FlashRegionMax
+} FLASH_REGION_TYPE;
+
+
+//
+// Protocol member functions
+//
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write data to the flash part. Remark: Erase may be needed before write to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_WRITE) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_ERASE) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ );
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_SFDP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ );
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_JEDEC_ID) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ );
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_WRITE_STATUS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ );
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_STATUS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ );
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_GET_REGION_ADDRESS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ );
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_READ_PCH_SOFTSTRAP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_READ_CPU_SOFTSTRAP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ These protocols/PPI allows a platform module to perform SPI operations through the
+ Intel PCH SPI Host Controller Interface.
+**/
+struct _PCH_SPI_PROTOCOL {
+ /**
+ This member specifies the revision of this structure. This field is used to
+ indicate backwards compatible changes to the protocol.
+ **/
+ UINT8 Revision;
+ PCH_SPI_FLASH_READ FlashRead; ///< Read data from the flash part.
+ PCH_SPI_FLASH_WRITE FlashWrite; ///< Write data to the flash part. Remark: Erase may be needed before write to the flash part.
+ PCH_SPI_FLASH_ERASE FlashErase; ///< Erase some area on the flash part.
+ PCH_SPI_FLASH_READ_SFDP FlashReadSfdp; ///< Read SFDP data from the flash part.
+ PCH_SPI_FLASH_READ_JEDEC_ID FlashReadJedecId; ///< Read Jedec Id from the flash part.
+ PCH_SPI_FLASH_WRITE_STATUS FlashWriteStatus; ///< Write the status register in the flash part.
+ PCH_SPI_FLASH_READ_STATUS FlashReadStatus; ///< Read status register in the flash part.
+ PCH_SPI_GET_REGION_ADDRESS GetRegionAddress; ///< Get the SPI region base and size
+ PCH_SPI_READ_PCH_SOFTSTRAP ReadPchSoftStrap; ///< Read PCH Soft Strap Values
+ PCH_SPI_READ_CPU_SOFTSTRAP ReadCpuSoftStrap; ///< Read CPU Soft Strap Values
+};
+
+/**
+ PCH SPI PPI/PROTOCOL revision number
+
+ Revision 1: Initial version
+**/
+#define PCH_SPI_SERVICES_REVISION 1
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
new file mode 100644
index 0000000000..e08721f405
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
@@ -0,0 +1,647 @@
+/** @file
+ Register names for PCH PMC device
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values within the bits
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, PCH registers are denoted by "_PCH_" in register names
+ - Registers / bits that are different between PCH generations are denoted by
+ "_PCH_[generation_name]_" in register/bit names.
+ - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit names.
+ Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit names.
+ e.g., "_PCH_H_", "_PCH_LP_"
+ Registers / bits names without _H_ or _LP_ apply for both H and LP.
+ - Registers / bits that are different between SKUs are denoted by "_[SKU_name]"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a PCH generation will be just named
+ as "_PCH_" without [generation_name] inserted.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_REGS_PMC_H_
+#define _PCH_REGS_PMC_H_
+
+//
+// PMC Registers (D31:F2)
+//
+#define PCI_DEVICE_NUMBER_PCH_PMC 31
+#define PCI_FUNCTION_NUMBER_PCH_PMC 2
+
+#define R_PCH_PMC_PM_DATA_BAR 0x10
+#define B_PCH_PMC_PM_DATA_BAR 0xFFFFC000
+#define R_PCH_PMC_ACPI_BASE 0x40
+#define B_PCH_PMC_ACPI_BASE_BAR 0xFFFC
+#define R_PCH_PMC_ACPI_CNT 0x44
+#define B_PCH_PMC_ACPI_CNT_PWRM_EN BIT8 ///< PWRM enable
+#define B_PCH_PMC_ACPI_CNT_ACPI_EN BIT7 ///< ACPI eanble
+#define B_PCH_PMC_ACPI_CNT_SCIS (BIT2 | BIT1 | BIT0) ///< SCI IRQ select
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ9 0
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ10 1
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ11 2
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ20 4
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ21 5
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ22 6
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ23 7
+#define R_PCH_PMC_PWRM_BASE 0x48
+#define B_PCH_PMC_PWRM_BASE_BAR 0xFFFF0000 ///< PWRM must be 64KB alignment to align the source decode.
+#define R_PCH_PMC_GEN_PMCON_A 0xA0
+#define B_PCH_PMC_GEN_PMCON_A_DC_PP_DIS BIT30
+#define B_PCH_PMC_GEN_PMCON_A_DSX_PP_DIS BIT29
+#define B_PCH_PMC_GEN_PMCON_A_AG3_PP_EN BIT28
+#define B_PCH_PMC_GEN_PMCON_A_SX_PP_EN BIT27
+#define B_PCH_PMC_GEN_PMCON_A_DISB BIT23
+#define B_PCH_PMC_GEN_PMCON_A_MEM_SR BIT21
+#define B_PCH_PMC_GEN_PMCON_A_MS4V BIT18
+#define B_PCH_PMC_GEN_PMCON_A_GBL_RST_STS BIT16
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_OPI_PLL_SD_INC0 BIT13
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_SPXB_CG_INC0 BIT12
+#define B_PCH_PMC_GEN_PMCON_A_BIOS_PCI_EXP_EN BIT10
+#define B_PCH_PMC_GEN_PMCON_A_PWRBTN_LVL BIT9
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_C0 BIT7
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_OPI_ON BIT6
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_BCLKREQ_ON BIT5
+#define B_PCH_PMC_GEN_PMCON_A_SMI_LOCK BIT4
+#define B_PCH_PMC_GEN_PMCON_A_ESPI_SMI_LOCK BIT3 ///< ESPI SMI lock
+#define B_PCH_PMC_GEN_PMCON_A_PER_SMI_SEL 0x0003
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_64S 0x0000
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_32S 0x0001
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_16S 0x0002
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_8S 0x0003
+#define R_PCH_PMC_GEN_PMCON_B 0xA4
+#define B_PCH_PMC_GEN_PMCON_B_SLPSX_STR_POL_LOCK BIT18 ///< Lock down SLP_S3/SLP_S4 Minimum Assertion width
+#define B_PCH_PMC_GEN_PMCON_B_ACPI_BASE_LOCK BIT17 ///< Lock ACPI BASE at 0x40, only cleared by reset when set
+#define B_PCH_PMC_GEN_PMCON_B_PM_DATA_BAR_DIS BIT16
+#define B_PCH_PMC_GEN_PMCON_B_PME_B0_S5_DIS BIT15
+#define B_PCH_PMC_GEN_PMCON_B_SUS_PWR_FLR BIT14
+#define B_PCH_PMC_GEN_PMCON_B_WOL_EN_OVRD BIT13
+#define B_PCH_PMC_GEN_PMCON_B_DISABLE_SX_STRETCH BIT12
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW 0xC00
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_60US 0x000
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_1MS 0x400
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_50MS 0x800
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_2S 0xC00
+#define B_PCH_PMC_GEN_PMCON_B_HOST_RST_STS BIT9
+#define B_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL 0xC0
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_64MS 0xC0
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_32MS 0x80
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_16MS 0x40
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_1_5MS 0x00
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW 0x30
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_1S 0x30
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_2S 0x20
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_3S 0x10
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_4S 0x00
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_ASE BIT3
+#define B_PCH_PMC_GEN_PMCON_B_RTC_PWR_STS BIT2
+#define B_PCH_PMC_GEN_PMCON_B_PWR_FLR BIT1
+#define B_PCH_PMC_GEN_PMCON_B_AFTERG3_EN BIT0
+#define R_PCH_PMC_BM_CX_CNF 0xA8
+#define B_PCH_PMC_BM_CX_CNF_STORAGE_BREAK_EN BIT31
+#define B_PCH_PMC_BM_CX_CNF_PCIE_BREAK_EN BIT30
+#define B_PCH_PMC_BM_CX_CNF_AZ_BREAK_EN BIT24
+#define B_PCH_PMC_BM_CX_CNF_DPSN_BREAK_EN BIT19
+#define B_PCH_PMC_BM_CX_CNF_XHCI_BREAK_EN BIT17
+#define B_PCH_PMC_BM_CX_CNF_SATA3_BREAK_EN BIT16
+#define B_PCH_PMC_BM_CX_CNF_SCRATCHPAD BIT15
+#define B_PCH_PMC_BM_CX_CNF_PHOLD_BM_STS_BLOCK BIT14
+#define B_PCH_PMC_BM_CX_CNF_MASK_CF BIT11
+#define B_PCH_PMC_BM_CX_CNF_BM_STS_ZERO_EN BIT10
+#define B_PCH_PMC_BM_CX_CNF_PM_SYNC_MSG_MODE BIT9
+#define R_PCH_PMC_ETR3 0xAC
+#define B_PCH_PMC_ETR3_CF9LOCK BIT31 ///< CF9h Lockdown
+#define B_PCH_PMC_ETR3_USB_CACHE_DIS BIT21
+#define B_PCH_PMC_ETR3_CF9GR BIT20 ///< CF9h Global Reset
+#define B_PCH_PMC_ETR3_SKIP_HOST_RST_HS BIT19
+#define B_PCH_PMC_ETR3_CWORWRE BIT18
+
+//
+// ACPI and legacy I/O register offsets from ACPIBASE
+//
+#define R_PCH_ACPI_PM1_STS 0x00
+#define S_PCH_ACPI_PM1_STS 2
+#define B_PCH_ACPI_PM1_STS_WAK BIT15
+#define B_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS BIT14
+#define B_PCH_ACPI_PM1_STS_PRBTNOR BIT11
+#define B_PCH_ACPI_PM1_STS_RTC BIT10
+#define B_PCH_ACPI_PM1_STS_PWRBTN BIT8
+#define B_PCH_ACPI_PM1_STS_GBL BIT5
+#define B_PCH_ACPI_PM1_STS_BM BIT4
+#define B_PCH_ACPI_PM1_STS_TMROF BIT0
+#define N_PCH_ACPI_PM1_STS_WAK 15
+#define N_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS 14
+#define N_PCH_ACPI_PM1_STS_PRBTNOR 11
+#define N_PCH_ACPI_PM1_STS_RTC 10
+#define N_PCH_ACPI_PM1_STS_PWRBTN 8
+#define N_PCH_ACPI_PM1_STS_GBL 5
+#define N_PCH_ACPI_PM1_STS_BM 4
+#define N_PCH_ACPI_PM1_STS_TMROF 0
+
+#define R_PCH_ACPI_PM1_EN 0x02
+#define S_PCH_ACPI_PM1_EN 2
+#define B_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS BIT14
+#define B_PCH_ACPI_PM1_EN_RTC BIT10
+#define B_PCH_ACPI_PM1_EN_PWRBTN BIT8
+#define B_PCH_ACPI_PM1_EN_GBL BIT5
+#define B_PCH_ACPI_PM1_EN_TMROF BIT0
+#define N_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS 14
+#define N_PCH_ACPI_PM1_EN_RTC 10
+#define N_PCH_ACPI_PM1_EN_PWRBTN 8
+#define N_PCH_ACPI_PM1_EN_GBL 5
+#define N_PCH_ACPI_PM1_EN_TMROF 0
+
+#define R_PCH_ACPI_PM1_CNT 0x04
+#define S_PCH_ACPI_PM1_CNT 4
+#define B_PCH_ACPI_PM1_CNT_SLP_EN BIT13
+#define B_PCH_ACPI_PM1_CNT_SLP_TYP (BIT12 | BIT11 | BIT10)
+#define V_PCH_ACPI_PM1_CNT_S0 0
+#define V_PCH_ACPI_PM1_CNT_S1 BIT10
+#define V_PCH_ACPI_PM1_CNT_S3 (BIT12 | BIT10)
+#define V_PCH_ACPI_PM1_CNT_S4 (BIT12 | BIT11)
+#define V_PCH_ACPI_PM1_CNT_S5 (BIT12 | BIT11 | BIT10)
+#define B_PCH_ACPI_PM1_CNT_GBL_RLS BIT2
+#define B_PCH_ACPI_PM1_CNT_BM_RLD BIT1
+#define B_PCH_ACPI_PM1_CNT_SCI_EN BIT0
+
+#define R_PCH_ACPI_PM1_TMR 0x08
+#define V_PCH_ACPI_TMR_FREQUENCY 3579545
+#define B_PCH_ACPI_PM1_TMR_VAL 0xFFFFFF
+#define V_PCH_ACPI_PM1_TMR_MAX_VAL 0x1000000 ///< The timer is 24 bit overflow
+
+#define R_PCH_SMI_EN 0x30
+#define S_PCH_SMI_EN 4
+#define B_PCH_SMI_EN_LEGACY_USB3 BIT31
+#define B_PCH_SMI_EN_GPIO_UNLOCK_SMI BIT27
+#define B_PCH_SMI_EN_LEGACY_USB2 BIT17
+#define B_PCH_SMI_EN_PERIODIC BIT14
+#define B_PCH_SMI_EN_TCO BIT13
+#define B_PCH_SMI_EN_MCSMI BIT11
+#define B_PCH_SMI_EN_BIOS_RLS BIT7
+#define B_PCH_SMI_EN_SWSMI_TMR BIT6
+#define B_PCH_SMI_EN_APMC BIT5
+#define B_PCH_SMI_EN_ON_SLP_EN BIT4
+#define B_PCH_SMI_EN_LEGACY_USB BIT3
+#define B_PCH_SMI_EN_BIOS BIT2
+#define B_PCH_SMI_EN_EOS BIT1
+#define B_PCH_SMI_EN_GBL_SMI BIT0
+#define N_PCH_SMI_EN_LEGACY_USB3 31
+#define N_PCH_SMI_EN_ESPI 28
+#define N_PCH_SMI_EN_GPIO_UNLOCK 27
+#define N_PCH_SMI_EN_INTEL_USB2 18
+#define N_PCH_SMI_EN_LEGACY_USB2 17
+#define N_PCH_SMI_EN_PERIODIC 14
+#define N_PCH_SMI_EN_TCO 13
+#define N_PCH_SMI_EN_MCSMI 11
+#define N_PCH_SMI_EN_BIOS_RLS 7
+#define N_PCH_SMI_EN_SWSMI_TMR 6
+#define N_PCH_SMI_EN_APMC 5
+#define N_PCH_SMI_EN_ON_SLP_EN 4
+#define N_PCH_SMI_EN_LEGACY_USB 3
+#define N_PCH_SMI_EN_BIOS 2
+#define N_PCH_SMI_EN_EOS 1
+#define N_PCH_SMI_EN_GBL_SMI 0
+
+#define R_PCH_SMI_STS 0x34
+#define S_PCH_SMI_STS 4
+#define B_PCH_SMI_STS_LEGACY_USB3 BIT31
+#define B_PCH_SMI_STS_GPIO_UNLOCK BIT27
+#define B_PCH_SMI_STS_SPI BIT26
+#define B_PCH_SMI_STS_MONITOR BIT21
+#define B_PCH_SMI_STS_PCI_EXP BIT20
+#define B_PCH_SMI_STS_PATCH BIT19
+#define B_PCH_SMI_STS_INTEL_USB2 BIT18
+#define B_PCH_SMI_STS_LEGACY_USB2 BIT17
+#define B_PCH_SMI_STS_SMBUS BIT16
+#define B_PCH_SMI_STS_SERIRQ BIT15
+#define B_PCH_SMI_STS_PERIODIC BIT14
+#define B_PCH_SMI_STS_TCO BIT13
+#define B_PCH_SMI_STS_DEVMON BIT12
+#define B_PCH_SMI_STS_MCSMI BIT11
+#define B_PCH_SMI_STS_GPIO_SMI BIT10
+#define B_PCH_SMI_STS_GPE0 BIT9
+#define B_PCH_SMI_STS_PM1_STS_REG BIT8
+#define B_PCH_SMI_STS_SWSMI_TMR BIT6
+#define B_PCH_SMI_STS_APM BIT5
+#define B_PCH_SMI_STS_ON_SLP_EN BIT4
+#define B_PCH_SMI_STS_LEGACY_USB BIT3
+#define B_PCH_SMI_STS_BIOS BIT2
+#define N_PCH_SMI_STS_LEGACY_USB3 31
+#define N_PCH_SMI_STS_ESPI 28
+#define N_PCH_SMI_STS_GPIO_UNLOCK 27
+#define N_PCH_SMI_STS_SPI 26
+#define N_PCH_SMI_STS_MONITOR 21
+#define N_PCH_SMI_STS_PCI_EXP 20
+#define N_PCH_SMI_STS_PATCH 19
+#define N_PCH_SMI_STS_INTEL_USB2 18
+#define N_PCH_SMI_STS_LEGACY_USB2 17
+#define N_PCH_SMI_STS_SMBUS 16
+#define N_PCH_SMI_STS_SERIRQ 15
+#define N_PCH_SMI_STS_PERIODIC 14
+#define N_PCH_SMI_STS_TCO 13
+#define N_PCH_SMI_STS_DEVMON 12
+#define N_PCH_SMI_STS_MCSMI 11
+#define N_PCH_SMI_STS_GPIO_SMI 10
+#define N_PCH_SMI_STS_GPE0 9
+#define N_PCH_SMI_STS_PM1_STS_REG 8
+#define N_PCH_SMI_STS_SWSMI_TMR 6
+#define N_PCH_SMI_STS_APM 5
+#define N_PCH_SMI_STS_ON_SLP_EN 4
+#define N_PCH_SMI_STS_LEGACY_USB 3
+#define N_PCH_SMI_STS_BIOS 2
+
+#define R_PCH_ACPI_GPE_CNTL 0x40
+#define B_PCH_ACPI_GPE_CNTL_SWGPE_CTRL BIT17
+
+#define R_PCH_DEVACT_STS 0x44
+#define S_PCH_DEVACT_STS 2
+#define B_PCH_DEVACT_STS_MASK 0x13E1
+#define B_PCH_DEVACT_STS_KBC BIT12
+#define B_PCH_DEVACT_STS_PIRQDH BIT9
+#define B_PCH_DEVACT_STS_PIRQCG BIT8
+#define B_PCH_DEVACT_STS_PIRQBF BIT7
+#define B_PCH_DEVACT_STS_PIRQAE BIT6
+#define B_PCH_DEVACT_STS_D0_TRP BIT0
+#define N_PCH_DEVACT_STS_KBC 12
+#define N_PCH_DEVACT_STS_PIRQDH 9
+#define N_PCH_DEVACT_STS_PIRQCG 8
+#define N_PCH_DEVACT_STS_PIRQBF 7
+#define N_PCH_DEVACT_STS_PIRQAE 6
+
+#define R_PCH_ACPI_PM2_CNT 0x50
+#define B_PCH_ACPI_PM2_CNT_ARB_DIS BIT0
+
+#define R_PCH_OC_WDT_CTL 0x54
+#define B_PCH_OC_WDT_CTL_RLD BIT31
+#define B_PCH_OC_WDT_CTL_ICCSURV_STS BIT25
+#define B_PCH_OC_WDT_CTL_NO_ICCSURV_STS BIT24
+#define B_PCH_OC_WDT_CTL_FORCE_ALL BIT15
+#define B_PCH_OC_WDT_CTL_EN BIT14
+#define B_PCH_OC_WDT_CTL_ICCSURV BIT13
+#define B_PCH_OC_WDT_CTL_LCK BIT12
+#define B_PCH_OC_WDT_CTL_TOV_MASK 0x3FF
+#define B_PCH_OC_WDT_CTL_FAILURE_STS BIT23
+#define B_PCH_OC_WDT_CTL_UNXP_RESET_STS BIT22
+#define B_PCH_OC_WDT_CTL_AFTER_POST 0x3F0000
+#define V_PCH_OC_WDT_CTL_STATUS_FAILURE 1
+#define V_PCH_OC_WDT_CTL_STATUS_OK 0
+
+#define R_PCH_ACPI_GPE0_STS_31_0 0x80
+#define R_PCH_ACPI_GPE0_STS_63_32 0x84
+#define R_PCH_ACPI_GPE0_STS_95_64 0x88
+#define R_PCH_ACPI_GPE0_STS_127_96 0x8C
+#define S_PCH_ACPI_GPE0_STS_127_96 4
+#define B_PCH_ACPI_GPE0_STS_127_96_WADT BIT18
+#define B_PCH_ACPI_GPE0_STS_127_96_LAN_WAKE BIT16
+#define B_PCH_ACPI_GPE0_STS_127_96_PME_B0 BIT13
+#define B_PCH_ACPI_GPE0_STS_127_96_ME_SCI BIT12
+#define B_PCH_ACPI_GPE0_STS_127_96_PME BIT11
+#define B_PCH_ACPI_GPE0_STS_127_96_BATLOW BIT10
+#define B_PCH_ACPI_GPE0_STS_127_96_PCI_EXP BIT9
+#define B_PCH_ACPI_GPE0_STS_127_96_RI BIT8
+#define B_PCH_ACPI_GPE0_STS_127_96_SMB_WAK BIT7
+#define B_PCH_ACPI_GPE0_STS_127_96_TC0SCI BIT6
+#define B_PCH_ACPI_GPE0_STS_127_96_SWGPE BIT2
+#define B_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG BIT1
+#define N_PCH_ACPI_GPE0_STS_127_96_PME_B0 13
+#define N_PCH_ACPI_GPE0_STS_127_96_PME 11
+#define N_PCH_ACPI_GPE0_STS_127_96_BATLOW 10
+#define N_PCH_ACPI_GPE0_STS_127_96_PCI_EXP 9
+#define N_PCH_ACPI_GPE0_STS_127_96_RI 8
+#define N_PCH_ACPI_GPE0_STS_127_96_SMB_WAK 7
+#define N_PCH_ACPI_GPE0_STS_127_96_TC0SCI 6
+#define N_PCH_ACPI_GPE0_STS_127_96_SWGPE 2
+#define N_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG 1
+
+#define R_PCH_ACPI_GPE0_EN_31_0 0x90
+#define R_PCH_ACPI_GPE0_EN_63_32 0x94
+#define R_PCH_ACPI_GPE0_EN_95_64 0x98
+#define R_PCH_ACPI_GPE0_EN_127_96 0x9C
+#define S_PCH_ACPI_GPE0_EN_127_96 4
+#define B_PCH_ACPI_GPE0_EN_127_96_WADT BIT18
+#define B_PCH_ACPI_GPE0_EN_127_96_LAN_WAKE BIT16
+#define B_PCH_ACPI_GPE0_EN_127_96_PME_B0 BIT13
+#define B_PCH_ACPI_GPE0_EN_127_96_ME_SCI BIT12
+#define B_PCH_ACPI_GPE0_EN_127_96_PME BIT11
+#define B_PCH_ACPI_GPE0_EN_127_96_BATLOW BIT10
+#define B_PCH_ACPI_GPE0_EN_127_96_PCI_EXP BIT9
+#define B_PCH_ACPI_GPE0_EN_127_96_RI BIT8
+#define B_PCH_ACPI_GPE0_EN_127_96_TC0SCI BIT6
+#define B_PCH_ACPI_GPE0_EN_127_96_SWGPE BIT2
+#define B_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG BIT1
+#define N_PCH_ACPI_GPE0_EN_127_96_PME_B0 13
+#define N_PCH_ACPI_GPE0_EN_127_96_USB3 12
+#define N_PCH_ACPI_GPE0_EN_127_96_PME 11
+#define N_PCH_ACPI_GPE0_EN_127_96_BATLOW 10
+#define N_PCH_ACPI_GPE0_EN_127_96_PCI_EXP 9
+#define N_PCH_ACPI_GPE0_EN_127_96_RI 8
+#define N_PCH_ACPI_GPE0_EN_127_96_TC0SCI 6
+#define N_PCH_ACPI_GPE0_EN_127_96_SWGPE 2
+#define N_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG 1
+
+
+//
+// TCO register I/O map
+//
+#define R_PCH_TCO_RLD 0x0
+#define R_PCH_TCO_DAT_IN 0x2
+#define R_PCH_TCO_DAT_OUT 0x3
+#define R_PCH_TCO1_STS 0x04
+#define S_PCH_TCO1_STS 2
+#define B_PCH_TCO1_STS_DMISERR BIT12
+#define B_PCH_TCO1_STS_DMISMI BIT10
+#define B_PCH_TCO1_STS_DMISCI BIT9
+#define B_PCH_TCO1_STS_BIOSWR BIT8
+#define B_PCH_TCO1_STS_NEWCENTURY BIT7
+#define B_PCH_TCO1_STS_TIMEOUT BIT3
+#define B_PCH_TCO1_STS_TCO_INT BIT2
+#define B_PCH_TCO1_STS_SW_TCO_SMI BIT1
+#define B_PCH_TCO1_STS_NMI2SMI BIT0
+#define N_PCH_TCO1_STS_DMISMI 10
+#define N_PCH_TCO1_STS_BIOSWR 8
+#define N_PCH_TCO1_STS_NEWCENTURY 7
+#define N_PCH_TCO1_STS_TIMEOUT 3
+#define N_PCH_TCO1_STS_SW_TCO_SMI 1
+#define N_PCH_TCO1_STS_NMI2SMI 0
+
+#define R_PCH_TCO2_STS 0x06
+#define S_PCH_TCO2_STS 2
+#define B_PCH_TCO2_STS_SMLINK_SLV_SMI BIT4
+#define B_PCH_TCO2_STS_BAD_BIOS BIT3
+#define B_PCH_TCO2_STS_BOOT BIT2
+#define B_PCH_TCO2_STS_SECOND_TO BIT1
+#define B_PCH_TCO2_STS_INTRD_DET BIT0
+#define N_PCH_TCO2_STS_INTRD_DET 0
+
+#define R_PCH_TCO1_CNT 0x08
+#define S_PCH_TCO1_CNT 2
+#define B_PCH_TCO_CNT_LOCK BIT12
+#define B_PCH_TCO_CNT_TMR_HLT BIT11
+#define B_PCH_TCO_CNT_NMI2SMI_EN BIT9
+#define B_PCH_TCO_CNT_NMI_NOW BIT8
+#define N_PCH_TCO_CNT_NMI2SMI_EN 9
+
+#define R_PCH_TCO2_CNT 0x0A
+#define S_PCH_TCO2_CNT 2
+#define B_PCH_TCO2_CNT_OS_POLICY 0x0030
+#define B_PCH_TCO2_CNT_GPI11_ALERT_DISABLE 0x0008
+#define B_PCH_TCO2_CNT_INTRD_SEL 0x0006
+#define N_PCH_TCO2_CNT_INTRD_SEL 2
+
+#define R_PCH_TCO_MESSAGE1 0x0C
+#define R_PCH_TCO_MESSAGE2 0x0D
+#define R_PCH_TCO_WDCNT 0x0E
+#define R_PCH_TCO_SW_IRQ_GEN 0x10
+#define B_PCH_TCO_IRQ12_CAUSE BIT1
+#define B_PCH_TCO_IRQ1_CAUSE BIT0
+#define R_PCH_TCO_TMR 0x12
+
+//
+// PWRM Registers
+//
+#define R_PCH_WADT_AC 0x0 ///< Wake Alarm Device Timer: AC
+#define R_PCH_WADT_DC 0x4 ///< Wake Alarm Device Timer: DC
+#define R_PCH_WADT_EXP_AC 0x8 ///< Wake Alarm Device Expired Timer: AC
+#define R_PCH_WADT_EXP_DC 0xC ///< Wake Alarm Device Expired Timer: DC
+#define R_PCH_PWRM_PRSTS 0x10 ///< Power and Reset Status
+#define B_PCH_PWRM_PRSTS_VE_WD_TMR_STS BIT7 ///< VE Watchdog Timer Status
+#define B_PCH_PWRM_PRSTS_WOL_OVR_WK_STS BIT5
+#define B_PCH_PWRM_PRSTS_FIELD_1 BIT4
+#define B_PCH_PWRM_PRSTS_ME_WAKE_STS BIT0
+#define R_PCH_PWRM_14 0x14
+#define R_PCH_PWRM_CFG 0x18 ///< Power Management Configuration
+#define B_PCH_PWRM_CFG_ALLOW_24_OSC_SD BIT29 ///< Allow 24MHz Crystal Oscillator Shutdown
+#define B_PCH_PWRM_CFG_ALLOW_USB2_CORE_PG BIT25 ///< Allow USB2 Core Power Gating
+#define B_PCH_PWRM_CFG_RTC_DS_WAKE_DIS BIT21 ///< RTC Wake from Deep S4/S5 Disable
+#define B_PCH_PWRM_CFG_SSMAW_MASK (BIT19 | BIT18) ///< SLP_SUS# Min Assertion Width
+#define V_PCH_PWRM_CFG_SSMAW_4S (BIT19 | BIT18) ///< 4 seconds
+#define V_PCH_PWRM_CFG_SSMAW_1S BIT19 ///< 1 second
+#define V_PCH_PWRM_CFG_SSMAW_0_5S BIT18 ///< 0.5 second (500ms)
+#define V_PCH_PWRM_CFG_SSMAW_0S 0 ///< 0 second
+#define B_PCH_PWRM_CFG_SAMAW_MASK (BIT17 | BIT16) ///< SLP_A# Min Assertion Width
+#define V_PCH_PWRM_CFG_SAMAW_2S (BIT17 | BIT16) ///< 2 seconds
+#define V_PCH_PWRM_CFG_SAMAW_98ms BIT17 ///< 98ms
+#define V_PCH_PWRM_CFG_SAMAW_4S BIT16 ///< 4 seconds
+#define V_PCH_PWRM_CFG_SAMAW_0S 0 ///< 0 second
+#define B_PCH_PWRM_CFG_RPCD_MASK (BIT9 | BIT8) ///< Reset Power Cycle Duration
+#define V_PCH_PWRM_CFG_RPCD_1S (BIT9 | BIT8) ///< 1-2 seconds
+#define V_PCH_PWRM_CFG_RPCD_2S BIT9 ///< 2-3 seconds
+#define V_PCH_PWRM_CFG_RPCD_3S BIT8 ///< 3-4 seconds
+#define V_PCH_PWRM_CFG_RPCD_4S 0 ///< 4-5 seconds (Default)
+#define R_PCH_PWRM_PCH_PM_STS 0x1C ///< Contains misc. fields used to record PCH power management events
+#define B_PCH_PWRM_PCH_PM_STS_PMC_MSG_FULL_STS BIT24 ///< MTPMC transport mechanism full indication
+#define R_PCH_PWRM_MTPMC 0x20 ///< Message to PMC
+#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_0_15 0xE ///< Command to override lanes 0-15 power gating
+#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_16_31 0xF ///< Command to override lanes 16-31 power gating
+#define B_PCH_PWRM_MTPMC_PG_CMD_DATA 0xFFFF0000 ///< Data part of PowerGate Message to PMC
+#define N_PCH_PWRM_MTPMC_PG_CMD_DATA 16
+#define R_PCH_PWRM_PCH_PM_STS2 0x24 ///< PCH Power Management Status
+#define R_PCH_PWRM_S3_PWRGATE_POL 0x28 ///< S3 Power Gating Policies
+#define B_PCH_PWRM_S3DC_GATE_SUS BIT1 ///< Deep S3 Enable in DC Mode
+#define B_PCH_PWRM_S3AC_GATE_SUS BIT0 ///< Deep S3 Enable in AC Mode
+#define R_PCH_PWRM_S4_PWRGATE_POL 0x2C ///< Deep S4 Power Policies
+#define B_PCH_PWRM_S4DC_GATE_SUS BIT1 ///< Deep S4 Enable in DC Mode
+#define B_PCH_PWRM_S4AC_GATE_SUS BIT0 ///< Deep S4 Enable in AC Mode
+#define R_PCH_PWRM_S5_PWRGATE_POL 0x30 ///< Deep S5 Power Policies
+#define B_PCH_PWRM_S5DC_GATE_SUS BIT15 ///< Deep S5 Enable in DC Mode
+#define B_PCH_PWRM_S5AC_GATE_SUS BIT14 ///< Deep S5 Enable in AC Mode
+#define R_PCH_PWRM_DSX_CFG 0x34 ///< Deep SX Configuration
+#define B_PCH_PWRM_DSX_CFG_WAKE_PIN_DSX_EN BIT2 ///< WAKE# Pin DeepSx Enable
+#define B_PCH_PWRM_DSX_CFG_ACPRES_PD_DSX_DIS BIT1 ///< AC_PRESENT pin pulldown in DeepSx disable
+#define B_PCH_PWRM_DSX_CFG_LAN_WAKE_EN BIT0 ///< LAN_WAKE Pin DeepSx Enable
+#define R_PCH_PWRM_CFG2 0x3C ///< Power Management Configuration Reg 2
+#define B_PCH_PWRM_CFG2_PBOP (BIT31 | BIT30 | BIT29) ///< Power Button Override Period (PBOP)
+#define N_PCH_PWRM_CFG2_PBOP 29 ///< Power Button Override Period (PBOP)
+#define B_PCH_PWRM_CFG2_PB_DIS BIT28 ///< Power Button Native Mode Disable (PB_DIS)
+#define B_PCH_PWRM_CFG2_DRAM_RESET_CTL BIT26 ///< DRAM RESET# control
+#define R_PCH_PWRM_EN_SN_SLOW_RING 0x48 ///< Enable Snoop Request to SLOW_RING
+#define R_PCH_PWRM_EN_SN_SLOW_RING2 0x4C ///< Enable Snoop Request to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_SN_SA 0x50 ///< Enable Snoop Request to SA
+#define R_PCH_PWRM_EN_SN_SA2 0x54 ///< Enable Snoop Request to SA 2nd Reg
+#define R_PCH_PWRM_EN_SN_SLOW_RING_CF 0x58 ///< Enable Snoop Request to SLOW_RING_CF
+#define R_PCH_PWRM_EN_NS_SA 0x68 ///< Enable Non-Snoop Request to SA
+#define R_PCH_PWRM_EN_CW_SLOW_RING 0x80 ///< Enable Clock Wake to SLOW_RING
+#define R_PCH_PWRM_EN_CW_SLOW_RING2 0x84 ///< Enable Clock Wake to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_CW_SA 0x88 ///< Enable Clock Wake to SA
+#define R_PCH_PWRM_EN_CW_SA2 0x8C ///< Enable Clock Wake to SA 2nd Reg
+#define R_PCH_PWRM_EN_CW_SLOW_RING_CF 0x98 ///< Enable Clock Wake to SLOW_RING_CF
+#define R_PCH_PWRM_EN_PA_SLOW_RING 0xA8 ///< Enable Pegged Active to SLOW_RING
+#define R_PCH_PWRM_EN_PA_SLOW_RING2 0xAC ///< Enable Pegged Active to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_PA_SA 0xB0 ///< Enable Pegged Active to SA
+#define R_PCH_PWRM_EN_PA_SA2 0xB4 ///< Enable Pegged Active to SA 2nd Reg
+#define R_PCH_PWRM_EN_MISC_EVENT 0xC0 ///< Enable Misc PM_SYNC Events
+#define R_PCH_PWRM_PMSYNC_TPR_CONFIG 0xC4
+#define B_PCH_PWRM_PMSYNC_TPR_CONFIG_LOCK BIT31
+#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_EN BIT26
+#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE (BIT25 | BIT24)
+#define N_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE 24
+#define V_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE_1 1
+#define R_PCH_PWRM_PMSYNC_MISC_CFG 0xC8
+#define B_PCH_PWRM_PMSYNC_PM_SYNC_LOCK BIT15 ///< PM_SYNC Configuration Lock
+#define B_PCH_PWRM_PMSYNC_GPIO_D_SEL BIT11
+#define B_PCH_PWRM_PMSYNC_GPIO_C_SEL BIT10
+#define R_PCH_PWRM_PM_SYNC_STATE_HYS 0xD0 ///< PM_SYNC State Hysteresis
+#define R_PCH_PWRM_PM_SYNC_MODE 0xD4 ///< PM_SYNC Pin Mode
+#define R_PCH_PWRM_CFG3 0xE0 ///< Power Management Configuration Reg 3
+#define B_PCH_PWRM_CFG3_DSX_WLAN_PP_EN BIT16 ///< Deep-Sx WLAN Phy Power Enable
+#define B_PCH_PWRM_CFG3_HOST_WLAN_PP_EN BIT17 ///< Host Wireless LAN Phy Power Enable
+#define B_PCH_PWRM_CFG3_PWRG_LOCK BIT2 ///< Lock power gating override messages
+#define R_PCH_PWRM_PM_DOWN_PPB_CFG 0xE4 ///< PM_DOWN PCH_POWER_BUDGET CONFIGURATION
+#define R_PCH_PWRM_CFG4 0xE8 ///< Power Management Configuration Reg 4
+#define B_PCH_PWRM_CFG4_U2_PHY_PG_EN BIT30 ///< USB2 PHY SUS Well Power Gating Enable
+#define B_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR (0x000001FF) ///< CPU I/O VR Ramp Duration, [8:0]
+#define N_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR 0
+#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_70US 0x007
+#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_240US 0x018
+#define R_PCH_PWRM_CPU_EPOC 0xEC
+#define R_PCH_PWRM_VR_MISC_CTL 0x100
+#define B_PCH_PWRM_VR_MISC_CTL_VIDSOVEN BIT3
+#define R_PCH_PWRM_GPIO_CFG 0x120
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW2 (BIT11 | BIT10 | BIT9 | BIT8)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW2 8
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW1 (BIT7 | BIT6 | BIT5 | BIT4)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW1 4
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW0 (BIT3 | BIT2 | BIT1 | BIT0)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW0 0
+#define R_PCH_PWRM_PM_SYNC_MODE_C0 0xF4 ///< PM_SYNC Pin Mode in C0
+#define R_PCH_PWRM_ACPI_TMR_CTL 0xFC
+#define B_PCH_PWRM_ACPI_TMR_DIS BIT1
+#define R_PCH_PWRM_124 0x124
+#define R_PCH_PWRM_SLP_S0_RESIDENCY_COUNTER 0x13C
+#define R_PCH_PWRM_MODPHY_PM_CFG1 0x200
+#define R_PCH_PWRM_MODPHY_PM_CFG1_MLSXSWPGP 0xFFFF
+#define R_PCH_PWRM_MODPHY_PM_CFG2 0x204 ///< ModPHY Power Management Configuration Reg 2
+#define B_PCH_PWRM_MODPHY_PM_CFG2_MLSPDDGE BIT30 ///< ModPHY Lane SUS Power Domain Dynamic Gating Enable
+#define B_PCH_PWRM_MODPHY_PM_CFG2_EMFC BIT29 ///< Enable ModPHY FET Control
+#define B_PCH_PWRM_MODPHY_PM_CFG2_EFRT (BIT28 | BIT27 | BIT26 | BIT25 | BIT24) ///< External FET Ramp Time
+#define N_PCH_PWRM_MODPHY_PM_CFG2_EFRT 24
+#define V_PCH_PWRM_MODPHY_PM_CFG2_EFRT_200US 0x0A
+#define B_PCH_PWRM_MODPHY_PM_CFG2_ASLOR_UFS BIT16 ///< UFS ModPHY SPD SPD Override
+#define R_PCH_PWRM_MODPHY_PM_CFG3 0x208 ///< ModPHY Power Management Configuration Reg 3
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_UFS BIT16 ///< UFS ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XDCI BIT15 ///< xDCI ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XHCI BIT14 ///< xHCI ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_GBE BIT13 ///< GbE ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_SATA BIT12 ///< SATA ModPHY SPD RT Request
+#define R_PCH_PWRM_30C 0x30C
+#define R_PCH_PWRM_OBFF_CFG 0x314 ///< OBFF Configuration
+#define R_PCH_PWRM_31C 0x31C
+#define R_PCH_PWRM_CPPM_MISC_CFG 0x320 ///< CPPM Miscellaneous Configuration
+#define R_PCH_PWRM_CPPM_CG_POL1A 0x324 ///< CPPM Clock Gating Policy Reg 1
+#define R_PCH_PWRM_CPPM_CG_POL2A 0x340 ///< CPPM Clock Gating Policy Reg 3
+#define R_PCH_PWRM_34C 0x34C
+#define R_PCH_PWRM_CPPM_CG_POL3A 0x3A8 ///< CPPM Clock Gating Policy Reg 5
+#define B_PCH_PWRM_CPPM_CG_POLXA_CPPM_GX_QUAL BIT30 ///< CPPM Shutdown Qualifier Enable for Clock Source Group X
+#define B_PCH_PWRM_CPPM_CG_POLXA_LTR_GX_THRESH (0x000001FF) ///< LTR Threshold for Clock Source Group X, [8:0]
+#define R_PCH_PWRM_3D0 0x3D0
+#define R_PCH_PWRM_CPPM_MPG_POL1A 0x3E0 ///< CPPM ModPHY Gating Policy Reg 1A
+#define B_PCH_PWRM_CPPM_MPG_POL1A_CPPM_MODPHY_QUAL BIT30 ///< CPPM Shutdown Qualifier Enable for ModPHY
+#define B_PCH_PWRM_CPPM_MPG_POL1A_LT_MODPHY_SEL BIT29 ///< ASLT/PLT Selection for ModPHY
+#define B_PCH_PWRM_CPPM_MPG_POL1A_LTR_MODPHY_THRESH (0x000001FF) ///< LTR Threshold for ModPHY, [8:0]
+#define R_PCH_PWRM_CS_SD_CTL1 0x3E8 ///< Clock Source Shutdown Control Reg 1
+#define B_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG (BIT22 | BIT21 | BIT20) ///< Clock Source 5 Control Configuration
+#define N_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG 20
+#define B_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG (BIT2 | BIT1 | BIT0) ///< Clock Source 1 Control Configuration
+#define N_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG 0
+#define R_PCH_PWRM_CS_SD_CTL2 0x3EC ///< Clock Source Shutdown Control Reg 2
+#define R_PCH_PWRM_HSWPGCR1 0x5D0
+#define B_PCH_PWRM_SW_PG_CTRL_LOCK BIT31
+#define B_PCH_PWRM_DFX_SW_PG_CTRL BIT0
+#define R_PCH_PWRM_600 0x600
+#define R_PCH_PWRM_604 0x604
+#define R_PCH_PWRM_ST_PG_FDIS_PMC_1 0x620 ///< Static PG Related Function Disable Register 1
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ST_FDIS_LK BIT31 ///< Static Function Disable Lock (ST_FDIS_LK)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_CAM_FDIS_PMC BIT6 ///< Camera Function Disable (PMC Version) (CAM_FDIS_PMC)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ISH_FDIS_PMC BIT5 ///< SH Function Disable (PMC Version) (ISH_FDIS_PMC)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_GBE_FDIS_PMC BIT0 ///< GBE Function Disable (PMC Version) (GBE_FDIS_PMC)
+#define R_PCH_PWRM_ST_PG_FDIS_PMC_2 0x624 ///< Static Function Disable Control Register 2
+#define V_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_FDIS_PMC 0x7FF ///< Static Function Disable Control Register 2
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI1_FDIS_PMC BIT10 ///< SerialIo Controller GSPI Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI0_FDIS_PMC BIT9 ///< SerialIo Controller GSPI Device 0 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART2_FDIS_PMC BIT8 ///< SerialIo Controller UART Device 2 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART1_FDIS_PMC BIT7 ///< SerialIo Controller UART Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART0_FDIS_PMC BIT6 ///< SerialIo Controller UART Device 0 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C5_FDIS_PMC BIT5 ///< SerialIo Controller I2C Device 5 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C4_FDIS_PMC BIT4 ///< SerialIo Controller I2C Device 4 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C3_FDIS_PMC BIT3 ///< SerialIo Controller I2C Device 3 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C2_FDIS_PMC BIT2 ///< SerialIo Controller I2C Device 2 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C1_FDIS_PMC BIT1 ///< SerialIo Controller I2C Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C0_FDIS_PMC BIT0 ///< SerialIo Controller I2C Device 0 Function Disable
+#define R_PCH_PWRM_NST_PG_FDIS_1 0x628
+#define B_PCH_PWRM_NST_PG_FDIS_1_SCC_FDIS_PMC BIT25 ///< SCC Function Disable. This is only avaiable in B0 onward.
+#define B_PCH_PWRM_NST_PG_FDIS_1_XDCI_FDIS_PMC BIT24 ///< XDCI Function Disable. This is only avaiable in B0 onward.
+#define B_PCH_PWRM_NST_PG_FDIS_1_ADSP_FDIS_PMC BIT23 ///< ADSP Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_SATA_FDIS_PMC BIT22 ///< SATA Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C3_FDIS_PMC BIT13 ///< PCIe Controller C Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C2_FDIS_PMC BIT12 ///< PCIe Controller C Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C1_FDIS_PMC BIT11 ///< PCIe Controller C Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C0_FDIS_PMC BIT10 ///< PCIe Controller C Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B3_FDIS_PMC BIT9 ///< PCIe Controller B Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B2_FDIS_PMC BIT8 ///< PCIe Controller B Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B1_FDIS_PMC BIT7 ///< PCIe Controller B Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B0_FDIS_PMC BIT6 ///< PCIe Controller B Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A3_FDIS_PMC BIT5 ///< PCIe Controller A Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A2_FDIS_PMC BIT4 ///< PCIe Controller A Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A1_FDIS_PMC BIT3 ///< PCIe Controller A Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A0_FDIS_PMC BIT2 ///< PCIe Controller A Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_XHCI_FDIS_PMC BIT0 ///< XHCI Function Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_1 0x640 ///< Fuse Disable Read 1 Register
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E3_FUSE_DIS BIT21 ///< PCIe Controller E Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E2_FUSE_DIS BIT20 ///< PCIe Controller E Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E1_FUSE_DIS BIT19 ///< PCIe Controller E Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E0_FUSE_DIS BIT18 ///< PCIe Controller E Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D3_FUSE_DIS BIT17 ///< PCIe Controller D Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D2_FUSE_DIS BIT16 ///< PCIe Controller D Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D1_FUSE_DIS BIT15 ///< PCIe Controller D Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D0_FUSE_DIS BIT14 ///< PCIe Controller D Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C3_FUSE_DIS BIT13 ///< PCIe Controller C Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C2_FUSE_DIS BIT12 ///< PCIe Controller C Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C1_FUSE_DIS BIT11 ///< PCIe Controller C Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C0_FUSE_DIS BIT10 ///< PCIe Controller C Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B3_FUSE_DIS BIT9 ///< PCIe Controller B Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B2_FUSE_DIS BIT8 ///< PCIe Controller B Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B1_FUSE_DIS BIT7 ///< PCIe Controller B Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B0_FUSE_DIS BIT6 ///< PCIe Controller B Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A3_FUSE_DIS BIT5 ///< PCIe Controller A Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A2_FUSE_DIS BIT4 ///< PCIe Controller A Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A1_FUSE_DIS BIT3 ///< PCIe Controller A Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A0_FUSE_DIS BIT2 ///< PCIe Controller A Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_XHCI_FUSE_DIS BIT0 ///< XHCI Fuse Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_2 0x644 ///< Fuse Disable Read 2 Register
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPC_SS_DIS BIT25 ///< SPC Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPB_SS_DIS BIT24 ///< SPB Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPA_SS_DIS BIT23 ///< SPA Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_PSTH_FUSE_SS_DIS BIT21 ///< PSTH Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_DMI_FUSE_SS_DIS BIT20 ///< DMI Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_OTG_FUSE_SS_DIS BIT19 ///< OTG Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_XHCI_SS_DIS BIT18 ///< XHCI Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_FIA_FUSE_SS_DIS BIT17 ///< FIA Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_DSP_FUSE_SS_DIS BIT16 ///< DSP Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SATA_FUSE_SS_DIS BIT15 ///< SATA Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ICC_FUSE_SS_DIS BIT14 ///< ICC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_LPC_FUSE_SS_DIS BIT13 ///< LPC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_RTC_FUSE_SS_DIS BIT12 ///< RTC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_P2S_FUSE_SS_DIS BIT11 ///< P2S Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_TRSB_FUSE_SS_DIS BIT10 ///< TRSB Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SMB_FUSE_SS_DIS BIT9 ///< SMB Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ITSS_FUSE_SS_DIS BIT8 ///< ITSS Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SERIALIO_FUSE_SS_DIS BIT6 ///< SerialIo Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SCC_FUSE_SS_DIS BIT4 ///< SCC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_P2D_FUSE_SS_DIS BIT3 ///< P2D Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_CAM_FUSE_SS_DIS BIT2 ///< Camera Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ISH_FUSE_SS_DIS BIT1 ///< ISH Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_GBE_FUSE_SS_DIS BIT0 ///< GBE Fuse or Soft Strap Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_3 0x648 ///< Static PG Fuse and Soft Strap Disable Read Register 3
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA3_FUSE_SS_DIS BIT3 ///< PNCRA3 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA2_FUSE_SS_DIS BIT2 ///< PNCRA2 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA1_FUSE_SS_DIS BIT1 ///< PNCRA1 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA_FUSE_SS_DIS BIT0 ///< PNCRA Fuse or Soft Strap Disable
+
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
new file mode 100644
index 0000000000..a727aae927
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
@@ -0,0 +1,304 @@
+/** @file
+ Register names for PCH SPI device.
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values within the bits
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, PCH registers are denoted by "_PCH_" in register names
+ - Registers / bits that are different between PCH generations are denoted by
+ "_PCH_[generation_name]_" in register/bit names.
+ - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit names.
+ Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit names.
+ e.g., "_PCH_H_", "_PCH_LP_"
+ Registers / bits names without _H_ or _LP_ apply for both H and LP.
+ - Registers / bits that are different between SKUs are denoted by "_[SKU_name]"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a PCH generation will be just named
+ as "_PCH_" without [generation_name] inserted.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_REGS_SPI_H_
+#define _PCH_REGS_SPI_H_
+
+//
+// SPI Registers (D31:F5)
+//
+
+#define PCI_DEVICE_NUMBER_PCH_SPI 31
+#define PCI_FUNCTION_NUMBER_PCH_SPI 5
+
+#define R_PCH_SPI_BAR0 0x10
+#define B_PCH_SPI_BAR0_MASK 0x0FFF
+
+#define R_PCH_SPI_BDE 0xD8
+#define B_PCH_SPI_BDE_F8 0x8000
+#define B_PCH_SPI_BDE_F0 0x4000
+#define B_PCH_SPI_BDE_E8 0x2000
+#define B_PCH_SPI_BDE_E0 0x1000
+#define B_PCH_SPI_BDE_D8 0x0800
+#define B_PCH_SPI_BDE_D0 0x0400
+#define B_PCH_SPI_BDE_C8 0x0200
+#define B_PCH_SPI_BDE_C0 0x0100
+#define B_PCH_SPI_BDE_LEG_F 0x0080
+#define B_PCH_SPI_BDE_LEG_E 0x0040
+#define B_PCH_SPI_BDE_70 0x0008
+#define B_PCH_SPI_BDE_60 0x0004
+#define B_PCH_SPI_BDE_50 0x0002
+#define B_PCH_SPI_BDE_40 0x0001
+
+#define R_PCH_SPI_BC 0xDC
+#define S_PCH_SPI_BC 4
+#define N_PCH_SPI_BC_ASE_BWP 11
+#define B_PCH_SPI_BC_ASE_BWP BIT11
+#define N_PCH_SPI_BC_ASYNC_SS 10
+#define B_PCH_SPI_BC_ASYNC_SS BIT10
+#define B_PCH_SPI_BC_OSFH BIT9 ///< OS Function Hide
+#define N_PCH_SPI_BC_SYNC_SS 8
+#define B_PCH_SPI_BC_SYNC_SS BIT8
+#define B_PCH_SPI_BC_BILD BIT7
+#define B_PCH_SPI_BC_BBS BIT6 ///< Boot BIOS strap
+#define N_PCH_SPI_BC_BBS 6
+#define V_PCH_SPI_BC_BBS_SPI 0 ///< Boot BIOS strapped to SPI
+#define V_PCH_SPI_BC_BBS_LPC 1 ///< Boot BIOS strapped to LPC
+#define B_PCH_SPI_BC_EISS BIT5 ///< Enable InSMM.STS
+#define B_PCH_SPI_BC_TSS BIT4
+#define B_PCH_SPI_BC_SRC (BIT3 | BIT2)
+#define N_PCH_SPI_BC_SRC 2
+#define V_PCH_SPI_BC_SRC_PREF_EN_CACHE_EN 0x02 ///< Prefetching and Caching enabled
+#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_DIS 0x01 ///< No prefetching and no caching
+#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_EN 0x00 ///< No prefetching, but caching enabled
+#define B_PCH_SPI_BC_LE BIT1 ///< Lock Enable
+#define N_PCH_SPI_BC_BLE 1
+#define B_PCH_SPI_BC_WPD BIT0 ///< Write Protect Disable
+
+//
+// BIOS Flash Program Registers (based on SPI_BAR0)
+//
+#define R_PCH_SPI_BFPR 0x00 ///< BIOS Flash Primary Region Register(32bits), which is RO and contains the same value from FREG1
+#define B_PCH_SPI_BFPR_PRL 0x7FFF0000 ///< BIOS Flash Primary Region Limit mask
+#define N_PCH_SPI_BFPR_PRL 16 ///< BIOS Flash Primary Region Limit bit position
+#define B_PCH_SPI_BFPR_PRB 0x00007FFF ///< BIOS Flash Primary Region Base mask
+#define N_PCH_SPI_BFPR_PRB 0 ///< BIOS Flash Primary Region Base bit position
+#define R_PCH_SPI_HSFSC 0x04 ///< Hardware Sequencing Flash Status and Control Register(32bits)
+#define B_PCH_SPI_HSFSC_FSMIE BIT31 ///< Flash SPI SMI# Enable
+#define B_PCH_SPI_HSFSC_FDBC_MASK 0x3F000000 ///< Flash Data Byte Count ( <= 64), Count = (Value in this field) + 1.
+#define N_PCH_SPI_HSFSC_FDBC 24
+#define B_PCH_SPI_HSFSC_CYCLE_MASK 0x001E0000 ///< Flash Cycle.
+#define N_PCH_SPI_HSFSC_CYCLE 17
+#define V_PCH_SPI_HSFSC_CYCLE_READ 0 ///< Flash Cycle Read
+#define V_PCH_SPI_HSFSC_CYCLE_WRITE 2 ///< Flash Cycle Write
+#define V_PCH_SPI_HSFSC_CYCLE_4K_ERASE 3 ///< Flash Cycle 4K Block Erase
+#define V_PCH_SPI_HSFSC_CYCLE_64K_ERASE 4 ///< Flash Cycle 64K Sector Erase
+#define V_PCH_SPI_HSFSC_CYCLE_READ_SFDP 5 ///< Flash Cycle Read SFDP
+#define V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID 6 ///< Flash Cycle Read JEDEC ID
+#define V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS 7 ///< Flash Cycle Write Status
+#define V_PCH_SPI_HSFSC_CYCLE_READ_STATUS 8 ///< Flash Cycle Read Status
+#define B_PCH_SPI_HSFSC_CYCLE_FGO BIT16 ///< Flash Cycle Go.
+#define B_PCH_SPI_HSFSC_FLOCKDN BIT15 ///< Flash Configuration Lock-Down
+#define B_PCH_SPI_HSFSC_FDV BIT14 ///< Flash Descriptor Valid, once valid software can use hareware sequencing regs
+#define B_PCH_SPI_HSFSC_FDOPSS BIT13 ///< Flash Descriptor Override Pin-Strap Status
+#define B_PCH_SPI_HSFSC_PRR34_LOCKDN BIT12 ///< PRR3 PRR4 Lock-Down
+#define B_PCH_SPI_HSFSC_SAF_CE BIT8 ///< SAF ctype error
+#define B_PCH_SPI_HSFSC_SAF_MODE_ACTIVE BIT7 ///< Indicates flash is attached either directly to the PCH via the SPI bus or EC/BMC
+#define B_PCH_SPI_HSFSC_SAF_LE BIT6 ///< SAF link error
+#define B_PCH_SPI_HSFSC_SCIP BIT5 ///< SPI cycle in progress
+#define B_PCH_SPI_HSFSC_SAF_DLE BIT4 ///< SAF Data length error
+#define B_PCH_SPI_HSFSC_SAF_ERROR BIT3 ///< SAF Error
+#define B_PCH_SPI_HSFSC_AEL BIT2 ///< Access Error Log
+#define B_PCH_SPI_HSFSC_FCERR BIT1 ///< Flash Cycle Error
+#define B_PCH_SPI_HSFSC_FDONE BIT0 ///< Flash Cycle Done
+#define R_PCH_SPI_FADDR 0x08 ///< SPI Flash Address
+#define B_PCH_SPI_FADDR_MASK 0x01FFFFFF ///< SPI Flash Address Mask (0~24bit)
+#define R_PCH_SPI_DLOCK 0x0C ///< Discrete Lock Bits
+#define B_PCH_SPI_DLOCK_PR0LOCKDN BIT8 ///< PR0LOCKDN
+#define R_PCH_SPI_FDATA00 0x10 ///< SPI Data 00 (32 bits)
+#define R_PCH_SPI_FDATA01 0x14 ///< SPI Data 01
+#define R_PCH_SPI_FDATA02 0x18 ///< SPI Data 02
+#define R_PCH_SPI_FDATA03 0x1C ///< SPI Data 03
+#define R_PCH_SPI_FDATA04 0x20 ///< SPI Data 04
+#define R_PCH_SPI_FDATA05 0x24 ///< SPI Data 05
+#define R_PCH_SPI_FDATA06 0x28 ///< SPI Data 06
+#define R_PCH_SPI_FDATA07 0x2C ///< SPI Data 07
+#define R_PCH_SPI_FDATA08 0x30 ///< SPI Data 08
+#define R_PCH_SPI_FDATA09 0x34 ///< SPI Data 09
+#define R_PCH_SPI_FDATA10 0x38 ///< SPI Data 10
+#define R_PCH_SPI_FDATA11 0x3C ///< SPI Data 11
+#define R_PCH_SPI_FDATA12 0x40 ///< SPI Data 12
+#define R_PCH_SPI_FDATA13 0x44 ///< SPI Data 13
+#define R_PCH_SPI_FDATA14 0x48 ///< SPI Data 14
+#define R_PCH_SPI_FDATA15 0x4C ///< SPI Data 15
+#define R_PCH_SPI_FRAP 0x50 ///< Flash Region Access Permisions Register
+#define B_PCH_SPI_FRAP_BRWA_MASK 0x0000FF00 ///< BIOS Region Write Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3: GbE; 4: PlatformData
+#define N_PCH_SPI_FRAP_BRWA 8 ///< BIOS Region Write Access bit position
+#define B_PCH_SPI_FRAP_BRRA_MASK 0x000000FF ///< BIOS Region Read Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3: GbE; 4: PlatformData
+#define B_PCH_SPI_FRAP_BMRAG_MASK 0x00FF0000 ///< BIOS Master Read Access Grant
+#define B_PCH_SPI_FRAP_BMWAG_MASK 0xFF000000 ///< BIOS Master Write Access Grant
+#define R_PCH_SPI_FREG0_FLASHD 0x54 ///< Flash Region 0(Flash Descriptor)(32bits)
+#define R_PCH_SPI_FREG1_BIOS 0x58 ///< Flash Region 1(BIOS)(32bits)
+#define R_PCH_SPI_FREG2_ME 0x5C ///< Flash Region 2(ME)(32bits)
+#define R_PCH_SPI_FREG3_GBE 0x60 ///< Flash Region 3(GbE)(32bits)
+#define R_PCH_SPI_FREG4_PLATFORM_DATA 0x64 ///< Flash Region 4(Platform Data)(32bits)
+#define R_PCH_SPI_FREG5_DER 0x68 ///< Flash Region 5(Device Expansion Region)(32bits)
+#define S_PCH_SPI_FREGX 4 ///< Size of Flash Region register
+#define B_PCH_SPI_FREGX_LIMIT_MASK 0x7FFF0000 ///< Flash Region Limit [30:16] represents [26:12], [11:0] are assumed to be FFFh
+#define N_PCH_SPI_FREGX_LIMIT 16 ///< Region limit bit position
+#define N_PCH_SPI_FREGX_LIMIT_REPR 12 ///< Region limit bit represents position
+#define B_PCH_SPI_FREGX_BASE_MASK 0x00007FFF ///< Flash Region Base, [14:0] represents [26:12]
+#define N_PCH_SPI_FREGX_BASE 0 ///< Region base bit position
+#define N_PCH_SPI_FREGX_BASE_REPR 12 ///< Region base bit represents position
+#define R_PCH_SPI_PR0 0x84 ///< Protected Region 0 Register
+#define R_PCH_SPI_PR1 0x88 ///< Protected Region 1 Register
+#define R_PCH_SPI_PR2 0x8C ///< Protected Region 2 Register
+#define R_PCH_SPI_PR3 0x90 ///< Protected Region 3 Register
+#define R_PCH_SPI_PR4 0x94 ///< Protected Region 4 Register
+#define S_PCH_SPI_PRX 4 ///< Protected Region X Register size
+#define B_PCH_SPI_PRX_WPE BIT31 ///< Write Protection Enable
+#define B_PCH_SPI_PRX_PRL_MASK 0x7FFF0000 ///< Protected Range Limit Mask, [30:16] here represents upper limit of address [26:12]
+#define N_PCH_SPI_PRX_PRL 16 ///< Protected Range Limit bit position
+#define B_PCH_SPI_PRX_RPE BIT15 ///< Read Protection Enable
+#define B_PCH_SPI_PRX_PRB_MASK 0x00007FFF ///< Protected Range Base Mask, [14:0] here represents base limit of address [26:12]
+#define N_PCH_SPI_PRX_PRB 0 ///< Protected Range Base bit position
+#define R_PCH_SPI_SFRAP 0xB0 ///< Secondary Flash Regions Access Permisions Register
+#define R_PCH_SPI_FDOC 0xB4 ///< Flash Descriptor Observability Control Register(32 bits)
+#define B_PCH_SPI_FDOC_FDSS_MASK (BIT14 | BIT13 | BIT12) ///< Flash Descritor Section Select
+#define V_PCH_SPI_FDOC_FDSS_FSDM 0x0000 ///< Flash Signature and Descriptor Map
+#define V_PCH_SPI_FDOC_FDSS_COMP 0x1000 ///< Component
+#define V_PCH_SPI_FDOC_FDSS_REGN 0x2000 ///< Region
+#define V_PCH_SPI_FDOC_FDSS_MSTR 0x3000 ///< Master
+#define V_PCH_SPI_FDOC_FDSS_PCHS 0x4000 ///< PCH soft straps
+#define V_PCH_SPI_FDOC_FDSS_SFDP 0x5000 ///< SFDP Parameter Table
+#define B_PCH_SPI_FDOC_FDSI_MASK 0x0FFC ///< Flash Descriptor Section Index
+#define R_PCH_SPI_FDOD 0xB8 ///< Flash Descriptor Observability Data Register(32 bits)
+#define R_PCH_SPI_SFDP0_VSCC0 0xC4 ///< Vendor Specific Component Capabilities Register(32 bits)
+#define B_PCH_SPI_SFDPX_VSCCX_CPPTV BIT31 ///< Component Property Parameter Table Valid
+#define B_PCH_SPI_SFDP0_VSCC0_VCL BIT30 ///< Vendor Component Lock
+#define B_PCH_SPI_SFDPX_VSCCX_EO_64K BIT29 ///< 64k Erase valid (EO_64k_valid)
+#define B_PCH_SPI_SFDPX_VSCCX_EO_4K BIT28 ///< 4k Erase valid (EO_4k_valid)
+#define B_PCH_SPI_SFDPX_VSCCX_RPMC BIT27 ///< RPMC Supported
+#define B_PCH_SPI_SFDPX_VSCCX_DPD BIT26 ///< Deep Powerdown Supported
+#define B_PCH_SPI_SFDPX_VSCCX_SUSRES BIT25 ///< Suspend/Resume Supported
+#define B_PCH_SPI_SFDPX_VSCCX_SOFTRES BIT24 ///< Soft Reset Supported
+#define B_PCH_SPI_SFDPX_VSCCX_64k_EO_MASK 0x00FF0000 ///< 64k Erase Opcode (EO_64k)
+#define B_PCH_SPI_SFDPX_VSCCX_4k_EO_MASK 0x0000FF00 ///< 4k Erase Opcode (EO_4k)
+#define B_PCH_SPI_SFDPX_VSCCX_QER (BIT7 | BIT6 | BIT5) ///< Quad Enable Requirements
+#define B_PCH_SPI_SFDPX_VSCCX_WEWS BIT4 ///< Write Enable on Write Status
+#define B_PCH_SPI_SFDPX_VSCCX_WSR BIT3 ///< Write Status Required
+#define B_PCH_SPI_SFDPX_VSCCX_WG_64B BIT2 ///< Write Granularity, 0: 1 Byte; 1: 64 Bytes
+#define R_PCH_SPI_SFDP1_VSCC1 0xC8 ///< Vendor Specific Component Capabilities Register(32 bits)
+#define R_PCH_SPI_PINTX 0xCC ///< Parameter Table Index
+#define N_PCH_SPI_PINTX_SPT 14
+#define V_PCH_SPI_PINTX_SPT_CPT0 0x0 ///< Component 0 Property Parameter Table
+#define V_PCH_SPI_PINTX_SPT_CPT1 0x1 ///< Component 1 Property Parameter Table
+#define N_PCH_SPI_PINTX_HORD 12
+#define V_PCH_SPI_PINTX_HORD_SFDP 0x0 ///< SFDP Header
+#define V_PCH_SPI_PINTX_HORD_PT 0x1 ///< Parameter Table Header
+#define V_PCH_SPI_PINTX_HORD_DATA 0x2 ///< Data
+#define R_PCH_SPI_PTDATA 0xD0 ///< Parameter Table Data
+#define R_PCH_SPI_SBRS 0xD4 ///< SPI Bus Requester Status
+#define R_PCH_SPI_SSML 0xF0 ///< Set Strap Msg Lock
+#define B_PCH_SPI_SSML_SSL BIT0 ///< Set_Strap Lock
+#define R_PCH_SPI_SSMC 0xF4 ///< Set Strap Msg Control
+#define B_PCH_SPI_SSMC_SSMS BIT0 ///< Set_Strap Mux Select
+#define R_PCH_SPI_SSMD 0xF8 ///< Set Strap Msg Data
+//
+// @todo Follow up with EDS owner if it should be 3FFF or FFFF.
+//
+#define B_PCH_SPI_SRD_SSD 0x0000FFFF ///< Set_Strap Data
+//
+// Flash Descriptor Base Address Region (FDBAR) from Flash Region 0
+//
+#define R_PCH_SPI_FDBAR_FLVALSIG 0x00 ///< Flash Valid Signature
+#define V_PCH_SPI_FDBAR_FLVALSIG 0x0FF0A55A
+#define R_PCH_SPI_FDBAR_FLASH_MAP0 0x04
+#define B_PCH_SPI_FDBAR_FCBA 0x000000FF ///< Flash Component Base Address
+#define B_PCH_SPI_FDBAR_NC 0x00000300 ///< Number Of Components
+#define N_PCH_SPI_FDBAR_NC 8 ///< Number Of Components
+#define V_PCH_SPI_FDBAR_NC_1 0x00000000
+#define V_PCH_SPI_FDBAR_NC_2 0x00000100
+#define B_PCH_SPI_FDBAR_FRBA 0x00FF0000 ///< Flash Region Base Address
+#define B_PCH_SPI_FDBAR_NR 0x07000000 ///< Number Of Regions
+#define R_PCH_SPI_FDBAR_FLASH_MAP1 0x08
+#define B_PCH_SPI_FDBAR_FMBA 0x000000FF ///< Flash Master Base Address
+#define B_PCH_SPI_FDBAR_NM 0x00000700 ///< Number Of Masters
+#define B_PCH_SPI_FDBAR_FPSBA 0x00FF0000 ///< PCH Strap Base Address, [23:16] represents [11:4]
+#define N_PCH_SPI_FDBAR_FPSBA 16 ///< PCH Strap base Address bit position
+#define N_PCH_SPI_FDBAR_FPSBA_REPR 4 ///< PCH Strap base Address bit represents position
+#define B_PCH_SPI_FDBAR_PCHSL 0xFF000000 ///< PCH Strap Length, [31:24] represents number of Dwords
+#define N_PCH_SPI_FDBAR_PCHSL 24 ///< PCH Strap Length bit position
+#define R_PCH_SPI_FDBAR_FLASH_MAP2 0x0C
+#define B_PCH_SPI_FDBAR_FCPUSBA 0x000000FF ///< CPU Strap Base Address, [7:0] represents [11:4]
+#define N_PCH_SPI_FDBAR_FCPUSBA 0 ///< CPU Strap Base Address bit position
+#define N_PCH_SPI_FDBAR_FCPUSBA_REPR 4 ///< CPU Strap Base Address bit represents position
+#define B_PCH_SPI_FDBAR_CPUSL 0x0000FF00 ///< CPU Strap Length, [15:8] represents number of Dwords
+#define N_PCH_SPI_FDBAR_CPUSL 8 ///< CPU Strap Length bit position
+//
+// Flash Component Base Address (FCBA) from Flash Region 0
+//
+#define R_PCH_SPI_FCBA_FLCOMP 0x00 ///< Flash Components Register
+#define B_PCH_SPI_FLCOMP_RIDS_FREQ (BIT29 | BIT28 | BIT27) ///< Read ID and Read Status Clock Frequency
+#define B_PCH_SPI_FLCOMP_WE_FREQ (BIT26 | BIT25 | BIT24) ///< Write and Erase Clock Frequency
+#define B_PCH_SPI_FLCOMP_FRCF_FREQ (BIT23 | BIT22 | BIT21) ///< Fast Read Clock Frequency
+#define B_PCH_SPI_FLCOMP_FR_SUP BIT20 ///< Fast Read Support.
+#define B_PCH_SPI_FLCOMP_RC_FREQ (BIT19 | BIT18 | BIT17) ///< Read Clock Frequency.
+#define V_PCH_SPI_FLCOMP_FREQ_48MHZ 0x02
+#define V_PCH_SPI_FLCOMP_FREQ_30MHZ 0x04
+#define V_PCH_SPI_FLCOMP_FREQ_17MHZ 0x06
+#define B_PCH_SPI_FLCOMP_COMP1_MASK 0xF0 ///< Flash Component 1 Size MASK
+#define N_PCH_SPI_FLCOMP_COMP1 4 ///< Flash Component 1 Size bit position
+#define B_PCH_SPI_FLCOMP_COMP0_MASK 0x0F ///< Flash Component 0 Size MASK
+#define V_PCH_SPI_FLCOMP_COMP_512KB 0x80000
+//
+// Descriptor Upper Map Section from Flash Region 0
+//
+#define R_PCH_SPI_FLASH_UMAP1 0xEFC ///< Flash Upper Map 1
+#define B_PCH_SPI_FLASH_UMAP1_VTBA 0x000000FF ///< VSCC Table Base Address
+#define B_PCH_SPI_FLASH_UMAP1_VTL 0x0000FF00 ///< VSCC Table Length
+
+#define R_PCH_SPI_VTBA_JID0 0x00 ///< JEDEC-ID 0 Register
+#define S_PCH_SPI_VTBA_JID0 0x04
+#define B_PCH_SPI_VTBA_JID0_VID 0x000000FF
+#define B_PCH_SPI_VTBA_JID0_DID0 0x0000FF00
+#define B_PCH_SPI_VTBA_JID0_DID1 0x00FF0000
+#define N_PCH_SPI_VTBA_JID0_DID0 0x08
+#define N_PCH_SPI_VTBA_JID0_DID1 0x10
+#define R_PCH_SPI_VTBA_VSCC0 0x04
+#define S_PCH_SPI_VTBA_VSCC0 0x04
+
+
+//
+// SPI Private Configuration Space Registers
+//
+#define R_PCH_PCR_SPI_CLK_CTL 0xC004
+#define R_PCH_PCR_SPI_PWR_CTL 0xC008
+#define R_PCH_PCR_SPI_ESPI_SOFTSTRAPS 0xC210
+#define B_PCH_PCR_SPI_ESPI_SOFTSTRAPS_SLAVE BIT12
+
+//
+// MMP0
+//
+#define R_PCH_SPI_STRP_MMP0 0xC4 ///< MMP0 Soft strap offset
+#define B_PCH_SPI_STRP_MMP0 0x10 ///< MMP0 Soft strap bit
+
+
+#define R_PCH_SPI_STRP_SFDP 0xF0 ///< PCH Soft Strap SFDP
+#define B_PCH_SPI_STRP_SFDP_QIORE BIT3 ///< Quad IO Read Enable
+#define B_PCH_SPI_STRP_SFDP_QORE BIT2 ///< Quad Output Read Enable
+#define B_PCH_SPI_STRP_SFDP_DIORE BIT1 ///< Dual IO Read Enable
+#define B_PCH_SPI_STRP_SFDP_DORE BIT0 ///< Dual Output Read Enable
+
+//
+// Descriptor Record 0
+//
+#define R_PCH_SPI_STRP_DSCR_0 0x00 ///< PCH Soft Strap 0
+#define B_PCH_SPI_STRP_DSCR_0_PTT_SUPP BIT22 ///< PTT Supported
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
new file mode 100644
index 0000000000..5bdec96197
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
@@ -0,0 +1,396 @@
+/** @file
+ Header file for the PCH SPI Common Driver.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_COMMON_LIB_H_
+#define _PCH_SPI_COMMON_LIB_H_
+
+//
+// Maximum time allowed while waiting the SPI cycle to complete
+// Wait Time = 6 seconds = 6000000 microseconds
+// Wait Period = 10 microseconds
+//
+#define SPI_WAIT_TIME 6000000 ///< Wait Time = 6 seconds = 6000000 microseconds
+#define SPI_WAIT_PERIOD 10 ///< Wait Period = 10 microseconds
+
+///
+/// Flash cycle Type
+///
+typedef enum {
+ FlashCycleRead,
+ FlashCycleWrite,
+ FlashCycleErase,
+ FlashCycleReadSfdp,
+ FlashCycleReadJedecId,
+ FlashCycleWriteStatus,
+ FlashCycleReadStatus,
+ FlashCycleMax
+} FLASH_CYCLE_TYPE;
+
+///
+/// Flash Component Number
+///
+typedef enum {
+ FlashComponent0,
+ FlashComponent1,
+ FlashComponentMax
+} FLASH_COMPONENT_NUM;
+
+///
+/// Private data structure definitions for the driver
+///
+#define PCH_SPI_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('P', 'S', 'P', 'I')
+
+typedef struct {
+ UINT32 Signature;
+ EFI_HANDLE Handle;
+ EFI_SPI_PROTOCOL SpiProtocol;
+ UINT16 PchAcpiBase;
+ UINTN PchSpiBase;
+ UINT16 ReadPermission;
+ UINT16 WritePermission;
+ UINT32 SfdpVscc0Value;
+ UINT32 SfdpVscc1Value;
+ UINT16 PchStrapBaseAddr;
+ UINT16 PchStrapSize;
+ UINT16 CpuStrapBaseAddr;
+ UINT16 CpuStrapSize;
+ UINT8 NumberOfComponents;
+ UINT32 Component1StartAddr;
+ UINT32 TotalFlashSize;
+} SPI_INSTANCE;
+
+#define SPI_INSTANCE_FROM_SPIPROTOCOL(a) CR (a, SPI_INSTANCE, SpiProtocol, PCH_SPI_PRIVATE_DATA_SIGNATURE)
+
+//
+// Function prototypes used by the SPI protocol.
+//
+
+/**
+ Initialize an SPI protocol instance.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @exception EFI_UNSUPPORTED The PCH is not supported by this module
+**/
+EFI_STATUS
+SpiProtocolConstructor (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ This function is a hook for Spi to disable BIOS Write Protect
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in SMM phase
+
+**/
+EFI_STATUS
+EFIAPI
+DisableBiosWriteProtect (
+ VOID
+ );
+
+/**
+ This function is a hook for Spi to enable BIOS Write Protect
+
+
+**/
+VOID
+EFIAPI
+EnableBiosWriteProtect (
+ VOID
+ );
+
+/**
+ Acquire pch spi mmio address.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval PchSpiBar0 return SPI MMIO address
+**/
+UINTN
+AcquireSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ Release pch spi mmio address.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval None
+**/
+VOID
+ReleaseSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashRead (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write data to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWrite (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashErase (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ );
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadSfdp (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ );
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadJedecId (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ );
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWriteStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ );
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ );
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolGetRegionAddress (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ );
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadPchSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadCpuSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ This function sends the programmed SPI command to the slave device.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SpiRegionType The SPI Region type for flash cycle which is listed in the Descriptor
+ @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware Sequencing Flash Control Register) register
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in,out] Buffer Pointer to caller-allocated buffer containing the dada received or sent during the SPI cycle.
+
+ @retval EFI_SUCCESS SPI command completes successfully.
+ @retval EFI_DEVICE_ERROR Device error, the command aborts abnormally.
+ @retval EFI_ACCESS_DENIED Some unrecognized command encountered in hardware sequencing mode
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+**/
+EFI_STATUS
+SendSpiCmd (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN FLASH_CYCLE_TYPE FlashCycleType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN OUT UINT8 *Buffer
+ );
+
+/**
+ Wait execution cycle to complete on the SPI interface.
+
+ @param[in] This The SPI protocol instance
+ @param[in] PchSpiBar0 Spi MMIO base address
+ @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
+
+ @retval TRUE SPI cycle completed on the interface.
+ @retval FALSE Time out while waiting the SPI cycle to complete.
+ It's not safe to program the next command on the SPI interface.
+**/
+BOOLEAN
+WaitForSpiCycleComplete (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINTN PchSpiBar0,
+ IN BOOLEAN ErrorCheck
+ );
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
new file mode 100644
index 0000000000..4af462da47
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
@@ -0,0 +1,34 @@
+## @file
+# Library instance for ResetSystem library class for OVMF
+#
+# Copyright (c) 2006 - 2018 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = ResetSystemLib
+ FILE_GUID = 66564872-21d4-4d2a-a68b-1e844f980820
+ MODULE_TYPE = BASE
+ VERSION_STRING = 1.0
+ LIBRARY_CLASS = ResetSystemLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[Sources]
+ ResetSystemLib.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+
+[LibraryClasses]
+ DebugLib
+ IoLib
+ TimerLib
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
new file mode 100644
index 0000000000..b5c97f1930
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
@@ -0,0 +1,52 @@
+## @file
+# SMM Library instance of Spi Flash Common Library Class
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010017
+ BASE_NAME = SmmSpiFlashCommonLib
+ FILE_GUID = 9632D96E-E849-4217-9217-DC500B8AAE47
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_SMM_DRIVER
+ LIBRARY_CLASS = SpiFlashCommonLib|DXE_SMM_DRIVER
+ CONSTRUCTOR = SmmSpiFlashCommonLibConstructor
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[LibraryClasses]
+ PciLib
+ IoLib
+ MemoryAllocationLib
+ BaseLib
+ UefiLib
+ SmmServicesTableLib
+ BaseMemoryLib
+ DebugLib
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+ MinPlatformPkg/MinPlatformPkg.dec
+
+
+[Pcd]
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
+
+[Sources]
+ SpiFlashCommonSmmLib.c
+ SpiFlashCommon.c
+
+[Protocols]
+ gEfiSmmSpiProtocolGuid ## CONSUMES
+
+[Depex.X64.DXE_SMM_DRIVER]
+ gEfiSmmSpiProtocolGuid
diff --git a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
new file mode 100644
index 0000000000..11c832e487
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
@@ -0,0 +1,33 @@
+## @file
+# Component description file for the PchSpiCommonLib
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = BasePchSpiCommonLib
+ FILE_GUID = A37CB67E-7D85-45B3-B07E-BF65BDB603E8
+ MODULE_TYPE = BASE
+ VERSION_STRING = 1.0
+ LIBRARY_CLASS = PchSpiCommonLib
+
+[Sources]
+ SpiCommon.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+ MinPlatformPkg/MinPlatformPkg.dec
+
+[LibraryClasses]
+ IoLib
+ DebugLib
+
+[Pcd]
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
new file mode 100644
index 0000000000..a2d006ee35
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
@@ -0,0 +1,12 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE libraries.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[LibraryClasses.common]
+ ResetSystemLib|$(PCH_PKG)/Library/ResetSystemLib/ResetSystemLib.inf
+ PchSpiCommonLib|$(PCH_PKG)/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
new file mode 100644
index 0000000000..78eca21a43
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
@@ -0,0 +1,9 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
new file mode 100644
index 0000000000..2d3a127c20
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
@@ -0,0 +1,9 @@
+## @file
+# Component description file for the SkyLake SiPkg PEI drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
new file mode 100644
index 0000000000..d079c593d9
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
@@ -0,0 +1,13 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+!if gMinPlatformPkgTokenSpaceGuid.PcdBootToShellOnly == FALSE
+ INF $(PCH_PKG)/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
+ INF $(PCH_PKG)/Spi/Smm/PchSpiSmm.inf
+!endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
new file mode 100644
index 0000000000..e23dd9f2fe
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
@@ -0,0 +1,59 @@
+## @file
+# A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
+# EFI_SMM_CONTROL2_PROTOCOL.
+#
+# We expect the PEI phase to have covered the following:
+# - ensure that the underlying QEMU machine type be X58
+# (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
+# - ensure that the ACPI PM IO space be configured
+# (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
+#
+# Our own entry point is responsible for confirming the SMI feature and for
+# configuring it.
+#
+# Copyright (C) 2013, 2015, Red Hat, Inc.
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = SmmControl2Dxe
+ FILE_GUID = 1206F7CA-A475-4624-A83E-E6FC9BB38E49
+ MODULE_TYPE = DXE_RUNTIME_DRIVER
+ VERSION_STRING = 1.0
+ PI_SPECIFICATION_VERSION = 0x00010400
+ ENTRY_POINT = SmmControl2DxeEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[Sources]
+ SmmControl2Dxe.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+
+[LibraryClasses]
+ BaseLib
+ DebugLib
+ IoLib
+ PcdLib
+ PciLib
+ UefiBootServicesTableLib
+ UefiDriverEntryPoint
+
+[Protocols]
+ gEfiS3SaveStateProtocolGuid ## SOMETIMES_CONSUMES
+ gEfiSmmControl2ProtocolGuid ## PRODUCES
+
+[FeaturePcd]
+ gSimicsX58PkgTokenSpaceGuid.PcdSmmSmramRequire
+
+[Depex]
+ TRUE
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
new file mode 100644
index 0000000000..f7fdd3abbe
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
@@ -0,0 +1,23 @@
+/** @file
+ Header file for the PCH SPI SMM Driver.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_H_
+#define _PCH_SPI_H_
+
+#include <Library/IoLib.h>
+#include <Library/DebugLib.h>
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/SmmServicesTableLib.h>
+#include <PchAccess.h>
+#include <Protocol/Spi.h>
+#include <IncludePrivate/Library/PchSpiCommonLib.h>
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
new file mode 100644
index 0000000000..265af00ac0
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
@@ -0,0 +1,44 @@
+## @file
+# Component description file for the SPI SMM driver.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010017
+ BASE_NAME = PchSpiSmm
+ FILE_GUID = 27F4917B-A707-4aad-9676-26DF168CBF0D
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_SMM_DRIVER
+ PI_SPECIFICATION_VERSION = 1.10
+ ENTRY_POINT = InstallPchSpi
+
+
+ [LibraryClasses]
+ DebugLib
+ IoLib
+ UefiDriverEntryPoint
+ UefiBootServicesTableLib
+ BaseLib
+ SmmServicesTableLib
+ PchSpiCommonLib
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+
+[Sources]
+ PchSpi.h
+ PchSpi.c
+
+
+[Protocols]
+ gEfiSmmSpiProtocolGuid # PRODUCES #SERVER_BIOS
+
+
+[Depex]
+ gEfiSmmBase2ProtocolGuid #This is for SmmServicesTableLib
+ AND gEfiSmmCpuProtocolGuid # This is for CpuSmmDisableBiosWriteProtect()
--
2.16.2.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#45484): https://edk2.groups.io/g/devel/message/45484
Mute This Topic: https://groups.io/mt/32816096/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
Feedback I could not find already noted elsewhere:
1. /Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf:
This silicon package should not have a dependency on MinPlatformPkg.dec.
2. /Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf:
This silicon package should not have a dependency on SimicsOpenBoardPkg.dec.
3. Although noted elsewhere: I also prefer Pascal naming as well so SimicsIch10Pkg.
4. /Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c:
"Reset System Library functions for OVMF" - replace OVMF with Simics ICH10.
5. /Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf:
This silicon package INF should not have a dependency on MinPlatformPkg.dec.
6. /Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
This silicon package INF should not have a dependency on MinPlatformPkg.dec.
7. /Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonib/SmmSpiFlashCommonLib:
This silicon package INF should not have a dependency on MinPlatformPkg.dec.
> -----Original Message-----
> From: Wei, David Y
> Sent: Friday, August 9, 2019 3:47 PM
> To: devel@edk2.groups.io
> Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>;
> Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince
> <prince.agyeman@intel.com>; Kubacki, Michael A
> <michael.a.kubacki@intel.com>; Desimone, Nathaniel L
> <nathaniel.l.desimone@intel.com>; Kinney, Michael D
> <michael.d.kinney@intel.com>
> Subject: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for
> SimicsICH10
>
> Add PCH Pkg for SimicsICH10. It is added for simics QSP project support
>
> Cc: Hao Wu <hao.a.wu@intel.com>
> Cc: Liming Gao <liming.gao@intel.com>
> Cc: Ankit Sinha <ankit.sinha@intel.com>
> Cc: Agyeman Prince <prince.agyeman@intel.com>
> Cc: Kubacki Michael A <michael.a.kubacki@intel.com>
> Cc: Nate DeSimone <nathaniel.l.desimone@intel.com>
> Cc: Michael D Kinney <michael.d.kinney@intel.com>
> Contributed-under: TianoCore Contribution Agreement 1.0
>
> Signed-off-by: David Wei <david.y.wei@intel.com>
> ---
> .../Library/ResetSystemLib/ResetSystemLib.c | 137 +++
> .../Library/SmmSpiFlashCommonLib/SpiFlashCommon.c | 194 +++++
> .../SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c | 54 ++
> .../LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c | 935
> +++++++++++++++++++++
> .../SmmControl/RuntimeDxe/SmmControl2Dxe.c | 410 +++++++++
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c | 175 ++++
> Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec | 22 +
> .../Include/Library/SpiFlashCommonLib.h | 98 +++
> Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h | 43 +
> Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h | 94 +++
> .../SimicsICH10Pkg/Include/PchReservedResources.h | 60 ++
> .../Intel/SimicsICH10Pkg/Include/Protocol/Spi.h | 295 +++++++
> .../SimicsICH10Pkg/Include/Register/PchRegsPmc.h | 647 ++++++++++++++
> .../SimicsICH10Pkg/Include/Register/PchRegsSpi.h | 304 +++++++
> .../IncludePrivate/Library/PchSpiCommonLib.h | 396 +++++++++
> .../Library/ResetSystemLib/ResetSystemLib.inf | 34 +
> .../SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf | 52 ++
> .../BasePchSpiCommonLib/BasePchSpiCommonLib.inf | 33 +
> Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc | 12 +
> .../Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf | 9 +
> .../Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf | 9 +
> .../Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf | 13 +
> .../SmmControl/RuntimeDxe/SmmControl2Dxe.inf | 59 ++
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h | 23 +
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf | 44 +
> 25 files changed, 4152 insertions(+)
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommo
> n.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommo
> nSmmLib.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommo
> n.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCo
> mmonLib.inf
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpi
> CommonLib.inf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
>
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> new file mode 100644
> index 0000000000..46355e191c
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> @@ -0,0 +1,137 @@
> +/** @file
> + Reset System Library functions for OVMF
> +
> + Copyright (c) 2006 - 2016 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Base.h>
> +
> +#include <Library/BaseLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/IoLib.h>
> +#include <Library/TimerLib.h>
> +#include <IndustryStandard/X58Ich10.h>
> +
> +
> +VOID
> +AcpiPmControl (
> + UINTN SuspendType
> + )
> +{
> + ASSERT (SuspendType < 6);
> + DEBUG((EFI_D_ERROR, "SuspendType = 0x%x\n", SuspendType));
> +
> + IoBitFieldWrite16 (ICH10_PMBASE_IO + 4, 10, 13, (UINT16) SuspendType);
> + IoOr16 (ICH10_PMBASE_IO + 0x04, BIT13);
> + CpuDeadLoop ();
> +}
> +
> +/**
> + Calling this function causes a system-wide reset. This sets
> + all circuitry within the system to its initial state. This type of reset
> + is asynchronous to system operation and operates without regard to
> + cycle boundaries.
> +
> + System reset should not return, if it returns, it means the system does
> + not support cold reset.
> +**/
> +VOID
> +EFIAPI
> +ResetCold (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetCold_CF9\n"));
> + IoWrite8 (0xCF9, BIT3 | BIT2 | BIT1); // 1st choice: PIIX3 RCR, RCPU|SRST
> + MicroSecondDelay (50);
> +
> + DEBUG((EFI_D_ERROR, "ResetCold_Port64\n"));
> + IoWrite8 (0x64, 0xfe); // 2nd choice: keyboard controller
> + CpuDeadLoop ();
> +}
> +
> +/**
> + Calling this function causes a system-wide initialization. The processors
> + are set to their initial state, and pending cycles are not corrupted.
> +
> + System reset should not return, if it returns, it means the system does
> + not support warm reset.
> +**/
> +VOID
> +EFIAPI
> +ResetWarm (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetWarm\n"));
> + //
> + //BUGBUG workaround for warm reset
> + //
> + IoWrite8(0xCF9, BIT2 | BIT1);
> + MicroSecondDelay(50);
> +
> + IoWrite8 (0x64, 0xfe);
> + CpuDeadLoop ();
> +}
> +
> +/**
> + Calling this function causes the system to enter a power state equivalent
> + to the ACPI G2/S5 or G3 states.
> +
> + System shutdown should not return, if it returns, it means the system does
> + not support shut down reset.
> +**/
> +VOID
> +EFIAPI
> +ResetShutdown (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetShutdown\n"));
> + AcpiPmControl (0);
> + ASSERT (FALSE);
> +}
> +
> +
> +/**
> + Calling this function causes the system to enter a power state for capsule
> + update.
> +
> + Reset update should not return, if it returns, it means the system does
> + not support capsule update.
> +
> +**/
> +VOID
> +EFIAPI
> +EnterS3WithImmediateWake (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "EnterS3WithImmediateWake\n"));
> + AcpiPmControl (1);
> + ASSERT (FALSE);
> +}
> +
> +/**
> + This function causes a systemwide reset. The exact type of the reset is
> + defined by the EFI_GUID that follows the Null-terminated Unicode string
> passed
> + into ResetData. If the platform does not recognize the EFI_GUID in ResetData
> + the platform must pick a supported reset type to perform.The platform may
> + optionally log the parameters from any non-normal reset that occurs.
> +
> + @param[in] DataSize The size, in bytes, of ResetData.
> + @param[in] ResetData The data buffer starts with a Null-terminated string,
> + followed by the EFI_GUID.
> +**/
> +VOID
> +EFIAPI
> +ResetPlatformSpecific (
> + IN UINTN DataSize,
> + IN VOID *ResetData
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetPlatformSpecific\n"));
> + ResetCold ();
> +}
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mon.c
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mon.c
> new file mode 100644
> index 0000000000..3d4e24eac6
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mon.c
> @@ -0,0 +1,194 @@
> +/** @file
> + Wrap EFI_SPI_PROTOCOL to provide some library level interfaces
> + for module use.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Library/SpiFlashCommonLib.h>
> +#include <Library/IoLib.h>
> +#include <Library/PciLib.h>
> +#include <Protocol/Spi.h>
> +
> +
> +EFI_SPI_PROTOCOL *mSpiProtocol;
> +
> +//
> +// FlashAreaBaseAddress and Size for boottime and runtime usage.
> +//
> +UINTN mFlashAreaBaseAddress = 0;
> +UINTN mFlashAreaSize = 0;
> +
> +/**
> + Enable block protection on the Serial Flash device.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashLock (
> + VOID
> + )
> +{
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Read NumBytes bytes of data from the address specified by
> + PAddress into Buffer.
> +
> + @param[in] Address The starting physical address of the read.
> + @param[in,out] NumBytes On input, the number of bytes to read. On
> output, the number
> + of bytes actually read.
> + @param[out] Buffer The destination data buffer for the read.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashRead (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + OUT UINT8 *Buffer
> + )
> +{
> + ASSERT ((NumBytes != NULL) && (Buffer != NULL));
> + if ((NumBytes == NULL) || (Buffer == NULL)) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // This function is implemented specifically for those platforms
> + // at which the SPI device is memory mapped for read. So this
> + // function just do a memory copy for Spi Flash Read.
> + //
> + CopyMem (Buffer, (VOID *) Address, *NumBytes);
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Write NumBytes bytes of data from Buffer to the address specified by
> + PAddresss.
> +
> + @param[in] Address The starting physical address of the write.
> + @param[in,out] NumBytes On input, the number of bytes to write. On
> output,
> + the actual number of bytes written.
> + @param[in] Buffer The source data buffer for the write.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashWrite (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + IN UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> + UINTN Offset;
> + UINT32 Length;
> + UINT32 RemainingBytes;
> +
> + ASSERT ((NumBytes != NULL) && (Buffer != NULL));
> + if ((NumBytes == NULL) || (Buffer == NULL)) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + ASSERT (Address >= mFlashAreaBaseAddress);
> +
> + Offset = Address - mFlashAreaBaseAddress;
> +
> + ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
> +
> + Status = EFI_SUCCESS;
> + RemainingBytes = *NumBytes;
> +
> +
> + while (RemainingBytes > 0) {
> + if (RemainingBytes > SECTOR_SIZE_4KB) {
> + Length = SECTOR_SIZE_4KB;
> + } else {
> + Length = RemainingBytes;
> + }
> + Status = mSpiProtocol->FlashWrite (
> + mSpiProtocol,
> + FlashRegionBios,
> + (UINT32) Offset,
> + Length,
> + Buffer
> + );
> + if (EFI_ERROR (Status)) {
> + break;
> + }
> + RemainingBytes -= Length;
> + Offset += Length;
> + Buffer += Length;
> + }
> +
> + //
> + // Actual number of bytes written
> + //
> + *NumBytes -= RemainingBytes;
> +
> + return Status;
> +}
> +
> +/**
> + Erase the block starting at Address.
> +
> + @param[in] Address The starting physical address of the block to be
> erased.
> + This library assume that caller garantee that the PAddress
> + is at the starting address of this block.
> + @param[in] NumBytes On input, the number of bytes of the logical block
> to be erased.
> + On output, the actual number of bytes erased.
> +
> + @retval EFI_SUCCESS. Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashBlockErase (
> + IN UINTN Address,
> + IN UINTN *NumBytes
> + )
> +{
> + EFI_STATUS Status;
> + UINTN Offset;
> + UINTN RemainingBytes;
> +
> + ASSERT (NumBytes != NULL);
> + if (NumBytes == NULL) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + ASSERT (Address >= mFlashAreaBaseAddress);
> +
> + Offset = Address - mFlashAreaBaseAddress;
> +
> + ASSERT ((*NumBytes % SECTOR_SIZE_4KB) == 0);
> + ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
> +
> + Status = EFI_SUCCESS;
> + RemainingBytes = *NumBytes;
> +
> +
> + Status = mSpiProtocol->FlashErase (
> + mSpiProtocol,
> + FlashRegionBios,
> + (UINT32) Offset,
> + (UINT32) RemainingBytes
> + );
> + return Status;
> +}
> +
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> monSmmLib.c
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> monSmmLib.c
> new file mode 100644
> index 0000000000..1e5cd0d744
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> monSmmLib.c
> @@ -0,0 +1,54 @@
> +/** @file
> + SMM Library instance of SPI Flash Common Library Class
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Library/SpiFlashCommonLib.h>
> +#include <Library/SmmServicesTableLib.h>
> +#include <Protocol/Spi.h>
> +
> +extern EFI_SPI_PROTOCOL *mSpiProtocol;
> +
> +extern UINTN mFlashAreaBaseAddress;
> +extern UINTN mFlashAreaSize;
> +
> +/**
> + The library constructuor.
> +
> + The function does the necessary initialization work for this library
> + instance.
> +
> + @param[in] ImageHandle The firmware allocated handle for the UEFI
> image.
> + @param[in] SystemTable A pointer to the EFI system table.
> +
> + @retval EFI_SUCCESS The function always return EFI_SUCCESS for now.
> + It will ASSERT on error for debug version.
> + @retval EFI_ERROR Please reference LocateProtocol for error code
> details.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SmmSpiFlashCommonLibConstructor (
> + IN EFI_HANDLE ImageHandle,
> + IN EFI_SYSTEM_TABLE *SystemTable
> + )
> +{
> + EFI_STATUS Status;
> +
> + mFlashAreaBaseAddress = (UINTN)PcdGet32 (PcdFlashAreaBaseAddress);
> + mFlashAreaSize = (UINTN)PcdGet32 (PcdFlashAreaSize);
> +
> + //
> + // Locate the SMM SPI protocol.
> + //
> + Status = gSmst->SmmLocateProtocol (
> + &gEfiSmmSpiProtocolGuid,
> + NULL,
> + (VOID **) &mSpiProtocol
> + );
> + ASSERT_EFI_ERROR (Status);
> +
> + return Status;
> +}
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mon.c
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mon.c
> new file mode 100644
> index 0000000000..77fb76d7cd
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mon.c
> @@ -0,0 +1,935 @@
> +/** @file
> + PCH SPI Common Driver implements the SPI Host Controller Compatibility
> Interface.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Uefi/UefiBaseType.h>
> +#include <Library/IoLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <IndustryStandard/Pci30.h>
> +#include <PchAccess.h>
> +#include <Protocol/Spi.h>
> +#include <IncludePrivate/Library/PchSpiCommonLib.h>
> +#include <IndustryStandard/X58Ich10.h>
> +
> +/**
> + Initialize an SPI protocol instance.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @exception EFI_UNSUPPORTED The PCH is not supported by this module
> +**/
> +EFI_STATUS
> +SpiProtocolConstructor (
> + IN SPI_INSTANCE *SpiInstance
> + )
> +{
> + UINTN PchSpiBar0;
> +
> + //
> + // Initialize the SPI protocol instance
> + //
> + SpiInstance->Signature = PCH_SPI_PRIVATE_DATA_SIGNATURE;
> + SpiInstance->Handle = NULL;
> + SpiInstance->SpiProtocol.Revision = PCH_SPI_SERVICES_REVISION;
> + SpiInstance->SpiProtocol.FlashRead = SpiProtocolFlashRead;
> + SpiInstance->SpiProtocol.FlashWrite = SpiProtocolFlashWrite;
> + SpiInstance->SpiProtocol.FlashErase = SpiProtocolFlashErase;
> + SpiInstance->SpiProtocol.FlashReadSfdp = SpiProtocolFlashReadSfdp;
> + SpiInstance->SpiProtocol.FlashReadJedecId = SpiProtocolFlashReadJedecId;
> + SpiInstance->SpiProtocol.FlashWriteStatus = SpiProtocolFlashWriteStatus;
> + SpiInstance->SpiProtocol.FlashReadStatus = SpiProtocolFlashReadStatus;
> + SpiInstance->SpiProtocol.GetRegionAddress = SpiProtocolGetRegionAddress;
> + SpiInstance->SpiProtocol.ReadPchSoftStrap = SpiProtocolReadPchSoftStrap;
> + SpiInstance->SpiProtocol.ReadCpuSoftStrap = SpiProtocolReadCpuSoftStrap;
> +
> + SpiInstance->PchAcpiBase = ICH10_PMBASE_IO;
> + ASSERT (SpiInstance->PchAcpiBase != 0);
> +
> + PchSpiBar0 = RCRB + SPIBAR;
> +
> + if (PchSpiBar0 == 0) {
> + DEBUG ((DEBUG_ERROR, "ERROR : PchSpiBar0 is invalid!\n"));
> + ASSERT (FALSE);
> + }
> +
> + if ((MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC) &
> B_PCH_SPI_HSFSC_FDV) == 0) {
> + DEBUG ((DEBUG_ERROR, "ERROR : SPI Flash Signature invalid, cannot use
> the Hardware Sequencing registers!\n"));
> + ASSERT (FALSE);
> + }
> + SpiInstance->ReadPermission = 0xffff;
> + SpiInstance->WritePermission = 0xffff;
> + DEBUG ((DEBUG_INFO, "Flash Region Permission: Read- 0x%04x; Write=
> 0x%04x\n",
> + SpiInstance->ReadPermission,
> + SpiInstance->WritePermission));
> +
> + //
> + SpiInstance->TotalFlashSize = PcdGet32(PcdFlashAreaSize);
> + DEBUG ((DEBUG_INFO, "Total Flash Size : %0x\n", SpiInstance-
> >TotalFlashSize));
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Delay for at least the request number of microseconds for Runtime usage.
> +
> + @param[in] ABase Acpi base address
> + @param[in] Microseconds Number of microseconds to delay.
> +
> +**/
> +VOID
> +EFIAPI
> +PchPmTimerStallRuntimeSafe (
> + IN UINT16 ABase,
> + IN UINTN Microseconds
> + )
> +{
> + UINTN Ticks;
> + UINTN Counts;
> + UINTN CurrentTick;
> + UINTN OriginalTick;
> + UINTN RemainingTick;
> +
> + if (Microseconds == 0) {
> + return;
> + }
> +
> + OriginalTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) &
> B_PCH_ACPI_PM1_TMR_VAL;
> + 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 / V_PCH_ACPI_PM1_TMR_MAX_VAL;
> +
> + //
> + // Remaining clocks within one loop
> + //
> + RemainingTick = Ticks % V_PCH_ACPI_PM1_TMR_MAX_VAL;
> +
> + //
> + // 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) || (RemainingTick > CurrentTick)) {
> + CurrentTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) &
> B_PCH_ACPI_PM1_TMR_VAL;
> + //
> + // Check if timer overflow
> + //
> + if ((CurrentTick < OriginalTick)) {
> + if (Counts != 0) {
> + Counts--;
> + } else {
> + //
> + // If timer overflow and Counts equ to 0, that means we already stalled
> more than
> + // RemainingTick, break the loop here
> + //
> + break;
> + }
> + }
> +
> + OriginalTick = CurrentTick;
> + }
> +}
> +
> +/**
> + Read data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[out] Buffer The Pointer to caller-allocated buffer containing
> the dada received.
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashRead (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionType,
> + FlashCycleRead,
> + Address,
> + ByteCount,
> + Buffer
> + );
> + return Status;
> +}
> +
> +/**
> + Write data to the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in] Buffer Pointer to caller-allocated buffer containing the
> data sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWrite (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionType,
> + FlashCycleWrite,
> + Address,
> + ByteCount,
> + Buffer
> + );
> + return Status;
> +}
> +
> +/**
> + Erase some area on the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashErase (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionType,
> + FlashCycleErase,
> + Address,
> + ByteCount,
> + NULL
> + );
> + return Status;
> +}
> +
> +/**
> + Read SFDP data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] Address The starting byte address for SFDP data read.
> + @param[in] ByteCount Number of bytes in SFDP data portion of the SPI
> cycle
> + @param[out] SfdpData The Pointer to caller-allocated buffer containing
> the SFDP data received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadSfdp (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *SfdpData
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + EFI_STATUS Status;
> + UINT32 FlashAddress;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> + Status = EFI_SUCCESS;
> +
> + if (ComponentNumber > SpiInstance->NumberOfComponents) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + FlashAddress = 0;
> + if (ComponentNumber == FlashComponent1) {
> + FlashAddress = SpiInstance->Component1StartAddr;
> + }
> + FlashAddress += Address;
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleReadSfdp,
> + FlashAddress,
> + ByteCount,
> + SfdpData
> + );
> + return Status;
> +}
> +
> +/**
> + Read Jedec Id from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] ByteCount Number of bytes in JedecId data portion of the
> SPI cycle, the data size is 3 typically
> + @param[out] JedecId The Pointer to caller-allocated buffer containing
> JEDEC ID received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadJedecId (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 ByteCount,
> + OUT UINT8 *JedecId
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + EFI_STATUS Status;
> + UINT32 Address;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> + Status = EFI_SUCCESS;
> +
> + if (ComponentNumber > SpiInstance->NumberOfComponents) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + Address = 0;
> + if (ComponentNumber == FlashComponent1) {
> + Address = SpiInstance->Component1StartAddr;
> + }
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleReadJedecId,
> + Address,
> + ByteCount,
> + JedecId
> + );
> + return Status;
> +}
> +
> +/**
> + Write the status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[in] StatusValue The Pointer to caller-allocated buffer containing
> the value of Status register writing
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWriteStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + IN UINT8 *StatusValue
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleWriteStatus,
> + 0,
> + ByteCount,
> + StatusValue
> + );
> + return Status;
> +}
> +
> +/**
> + Read status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[out] StatusValue The Pointer to caller-allocated buffer
> containing the value of Status register received.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + OUT UINT8 *StatusValue
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleReadStatus,
> + 0,
> + ByteCount,
> + StatusValue
> + );
> + return Status;
> +}
> +
> +/**
> + Get the SPI region base and size, based on the enum type
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for for the base
> address which is listed in the Descriptor.
> + @param[out] BaseAddress The Flash Linear Address for the Region 'n'
> Base
> + @param[out] RegionSize The size for the Region 'n'
> +
> + @retval EFI_SUCCESS Read success
> + @retval EFI_INVALID_PARAMETER Invalid region type given
> + @retval EFI_DEVICE_ERROR The region is not used
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolGetRegionAddress (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + OUT UINT32 *BaseAddress,
> + OUT UINT32 *RegionSize
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + UINTN PchSpiBar0;
> + UINT32 ReadValue;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + if (FlashRegionType >= FlashRegionMax) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + if (FlashRegionType == FlashRegionAll) {
> + *BaseAddress = 0;
> + *RegionSize = SpiInstance->TotalFlashSize;
> + return EFI_SUCCESS;
> + }
> +
> + PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
> + ReadValue = MmioRead32 (PchSpiBar0 + (R_PCH_SPI_FREG0_FLASHD +
> (S_PCH_SPI_FREGX * ((UINT32) FlashRegionType))));
> + ReleaseSpiBar0 (SpiInstance);
> +
> + //
> + // If the region is not used, the Region Base is 7FFFh and Region Limit is 0000h
> + //
> + if (ReadValue == B_PCH_SPI_FREGX_BASE_MASK) {
> + return EFI_DEVICE_ERROR;
> + }
> + *BaseAddress = ((ReadValue & B_PCH_SPI_FREGX_BASE_MASK) >>
> N_PCH_SPI_FREGX_BASE) <<
> + N_PCH_SPI_FREGX_BASE_REPR;
> + //
> + // Region limit address Bits[11:0] are assumed to be FFFh
> + //
> + *RegionSize = ((((ReadValue & B_PCH_SPI_FREGX_LIMIT_MASK) >>
> N_PCH_SPI_FREGX_LIMIT) + 1) <<
> + N_PCH_SPI_FREGX_LIMIT_REPR) - *BaseAddress;
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Read PCH Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing PCH Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadPchSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + UINT32 StrapFlashAddr;
> + EFI_STATUS Status;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + if (ByteCount == 0) {
> + *(UINT16 *) SoftStrapValue = SpiInstance->PchStrapSize;
> + return EFI_SUCCESS;
> + }
> +
> + if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->PchStrapSize) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // PCH Strap Flash Address = FPSBA + RamAddr
> + //
> + StrapFlashAddr = SpiInstance->PchStrapBaseAddr + SoftStrapAddr;
> +
> + //
> + // Read PCH Soft straps from using execute command
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionDescriptor,
> + FlashCycleRead,
> + StrapFlashAddr,
> + ByteCount,
> + SoftStrapValue
> + );
> + return Status;
> +}
> +
> +/**
> + Read CPU Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle.
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing CPU Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadCpuSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + UINT32 StrapFlashAddr;
> + EFI_STATUS Status;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + if (ByteCount == 0) {
> + *(UINT16 *) SoftStrapValue = SpiInstance->CpuStrapSize;
> + return EFI_SUCCESS;
> + }
> +
> + if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->CpuStrapSize) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // CPU Strap Flash Address = FCPUSBA + RamAddr
> + //
> + StrapFlashAddr = SpiInstance->CpuStrapBaseAddr + SoftStrapAddr;
> +
> + //
> + // Read Cpu Soft straps from using execute command
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionDescriptor,
> + FlashCycleRead,
> + StrapFlashAddr,
> + ByteCount,
> + SoftStrapValue
> + );
> + return Status;
> +}
> +
> +/**
> + This function sends the programmed SPI command to the slave device.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SpiRegionType The SPI Region type for flash cycle which is
> listed in the Descriptor
> + @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware
> Sequencing Flash Control Register) register
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in,out] Buffer Pointer to caller-allocated buffer containing the
> dada received or sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS SPI command completes successfully.
> + @retval EFI_DEVICE_ERROR Device error, the command aborts
> abnormally.
> + @retval EFI_ACCESS_DENIED Some unrecognized command encountered
> in hardware sequencing mode
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> +**/
> +EFI_STATUS
> +SendSpiCmd (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN FLASH_CYCLE_TYPE FlashCycleType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN OUT UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> + UINT32 Index;
> + SPI_INSTANCE *SpiInstance;
> + UINTN SpiBaseAddress;
> + UINTN PchSpiBar0;
> + UINT32 HardwareSpiAddr;
> + UINT32 FlashRegionSize;
> + UINT32 SpiDataCount;
> + UINT32 FlashCycle;
> + UINT32 SmiEnSave;
> + UINT16 ABase;
> +
> + Status = EFI_SUCCESS;
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> + SpiBaseAddress = SpiInstance->PchSpiBase;
> + PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
> + SpiBaseAddress = SpiInstance->PchSpiBase;
> + ABase = SpiInstance->PchAcpiBase;
> +
> + //
> + // Disable SMIs to make sure normal mode flash access is not interrupted by
> an SMI
> + // whose SMI handler accesses flash (e.g. for error logging)
> + //
> + // *** NOTE: if the SMI_LOCK bit is set (i.e., PMC PCI Offset A0h [4]='1'),
> + // clearing B_GBL_SMI_EN will not have effect. In this situation, some other
> + // synchronization methods must be applied here or in the consumer of the
> + // SendSpiCmd. An example method is disabling the specific SMI sources
> + // whose SMI handlers access flash before flash cycle and re-enabling the SMI
> + // sources after the flash cycle .
> + //
> + SmiEnSave = IoRead32 ((UINTN) (ABase + R_PCH_SMI_EN));
> + IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave & (UINT32)
> (~B_PCH_SMI_EN_GBL_SMI));
> +
> + //
> + // If it's write cycle, disable Prefetching, Caching and disable BIOS Write
> Protect
> + //
> + if ((FlashCycleType == FlashCycleWrite) ||
> + (FlashCycleType == FlashCycleErase)) {
> + Status = DisableBiosWriteProtect ();
> + if (EFI_ERROR (Status)) {
> + goto SendSpiCmdEnd;
> + }
> + }
> + //
> + // Make sure it's safe to program the command.
> + //
> + if (!WaitForSpiCycleComplete (This, PchSpiBar0, FALSE)) {
> + Status = EFI_DEVICE_ERROR;
> + goto SendSpiCmdEnd;
> + }
> +
> + Status = SpiProtocolGetRegionAddress (This, FlashRegionType,
> &HardwareSpiAddr, &FlashRegionSize);
> + if (EFI_ERROR (Status)) {
> + goto SendSpiCmdEnd;
> + }
> + HardwareSpiAddr += Address;
> + if ((Address + ByteCount) > FlashRegionSize) {
> + Status = EFI_INVALID_PARAMETER;
> + goto SendSpiCmdEnd;
> + }
> +
> + //
> + // Check for PCH SPI hardware sequencing required commands
> + //
> + FlashCycle = 0;
> + switch (FlashCycleType) {
> + case FlashCycleRead:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleWrite:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleErase:
> + if (((ByteCount % SIZE_4KB) != 0) ||
> + ((HardwareSpiAddr % SIZE_4KB) != 0)) {
> + ASSERT (FALSE);
> + Status = EFI_INVALID_PARAMETER;
> + goto SendSpiCmdEnd;
> + }
> + break;
> + case FlashCycleReadSfdp:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_SFDP <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleReadJedecId:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleWriteStatus:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleReadStatus:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_STATUS <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + default:
> + //
> + // Unrecognized Operation
> + //
> + ASSERT (FALSE);
> + Status = EFI_INVALID_PARAMETER;
> + goto SendSpiCmdEnd;
> + break;
> + }
> +
> + do {
> + SpiDataCount = ByteCount;
> + if ((FlashCycleType == FlashCycleRead) ||
> + (FlashCycleType == FlashCycleWrite) ||
> + (FlashCycleType == FlashCycleReadSfdp)) {
> + //
> + // Trim at 256 byte boundary per operation,
> + // - PCH SPI controller requires trimming at 4KB boundary
> + // - Some SPI chips require trimming at 256 byte boundary for write
> operation
> + // - Trimming has limited performance impact as we can read / write atmost
> 64 byte
> + // per operation
> + //
> + if (HardwareSpiAddr + ByteCount > ((HardwareSpiAddr + BIT8) &~(BIT8 -
> 1))) {
> + SpiDataCount = (((UINT32) (HardwareSpiAddr) + BIT8) &~(BIT8 - 1)) -
> (UINT32) (HardwareSpiAddr);
> + }
> + //
> + // Calculate the number of bytes to shift in/out during the SPI data cycle.
> + // Valid settings for the number of bytes duing each data portion of the
> + // PCH SPI cycles are: 0, 1, 2, 3, 4, 5, 6, 7, 8, 16, 24, 32, 40, 48, 56, 64
> + //
> + if (SpiDataCount >= 64) {
> + SpiDataCount = 64;
> + } else if ((SpiDataCount &~0x07) != 0) {
> + SpiDataCount = SpiDataCount &~0x07;
> + }
> + }
> + if (FlashCycleType == FlashCycleErase) {
> + if (((ByteCount / SIZE_64KB) != 0) &&
> + ((ByteCount % SIZE_64KB) == 0) &&
> + ((HardwareSpiAddr % SIZE_64KB) == 0)) {
> + if (HardwareSpiAddr < SpiInstance->Component1StartAddr) {
> + //
> + // Check whether Component0 support 64k Erase
> + //
> + if ((SpiInstance->SfdpVscc0Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K)
> != 0) {
> + SpiDataCount = SIZE_64KB;
> + } else {
> + SpiDataCount = SIZE_4KB;
> + }
> + } else {
> + //
> + // Check whether Component1 support 64k Erase
> + //
> + if ((SpiInstance->SfdpVscc1Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K)
> != 0) {
> + SpiDataCount = SIZE_64KB;
> + } else {
> + SpiDataCount = SIZE_4KB;
> + }
> + }
> + } else {
> + SpiDataCount = SIZE_4KB;
> + }
> + if (SpiDataCount == SIZE_4KB) {
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_4K_ERASE <<
> N_PCH_SPI_HSFSC_CYCLE);
> + } else {
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_64K_ERASE <<
> N_PCH_SPI_HSFSC_CYCLE);
> + }
> + }
> + //
> + // If it's write cycle, load data into the SPI data buffer.
> + //
> + if ((FlashCycleType == FlashCycleWrite) || (FlashCycleType ==
> FlashCycleWriteStatus)) {
> + if ((SpiDataCount & 0x07) != 0) {
> + //
> + // Use Byte write if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
> + //
> + for (Index = 0; Index < SpiDataCount; Index++) {
> + MmioWrite8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index,
> Buffer[Index]);
> + }
> + } else {
> + //
> + // Use Dword write if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
> + //
> + for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
> + MmioWrite32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, *(UINT32 *)
> (Buffer + Index));
> + }
> + }
> + }
> +
> + //
> + // Set the Flash Address
> + //
> + MmioWrite32 (
> + (PchSpiBar0 + R_PCH_SPI_FADDR),
> + (UINT32) (HardwareSpiAddr & B_PCH_SPI_FADDR_MASK)
> + );
> +
> + //
> + // Set Data count, Flash cycle, and Set Go bit to start a cycle
> + //
> + MmioAndThenOr32 (
> + PchSpiBar0 + R_PCH_SPI_HSFSC,
> + (UINT32) (~(B_PCH_SPI_HSFSC_FDBC_MASK |
> B_PCH_SPI_HSFSC_CYCLE_MASK)),
> + (UINT32) ((((SpiDataCount - 1) << N_PCH_SPI_HSFSC_FDBC) &
> B_PCH_SPI_HSFSC_FDBC_MASK) | FlashCycle |
> B_PCH_SPI_HSFSC_CYCLE_FGO)
> + );
> + //
> + // end of command execution
> + //
> + // Wait the SPI cycle to complete.
> + //
> + if (!WaitForSpiCycleComplete (This, PchSpiBar0, TRUE)) {
> + ASSERT (FALSE);
> + Status = EFI_DEVICE_ERROR;
> + goto SendSpiCmdEnd;
> + }
> + //
> + // If it's read cycle, load data into the call's buffer.
> + //
> + if ((FlashCycleType == FlashCycleRead) ||
> + (FlashCycleType == FlashCycleReadSfdp) ||
> + (FlashCycleType == FlashCycleReadJedecId) ||
> + (FlashCycleType == FlashCycleReadStatus)) {
> + if ((SpiDataCount & 0x07) != 0) {
> + //
> + // Use Byte read if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
> + //
> + for (Index = 0; Index < SpiDataCount; Index++) {
> + Buffer[Index] = MmioRead8 (PchSpiBar0 + R_PCH_SPI_FDATA00 +
> Index);
> + }
> + } else {
> + //
> + // Use Dword read if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
> + //
> + for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
> + *(UINT32 *) (Buffer + Index) = MmioRead32 (PchSpiBar0 +
> R_PCH_SPI_FDATA00 + Index);
> + }
> + }
> + }
> +
> + HardwareSpiAddr += SpiDataCount;
> + Buffer += SpiDataCount;
> + ByteCount -= SpiDataCount;
> + } while (ByteCount > 0);
> +
> +SendSpiCmdEnd:
> + //
> + // Restore the settings for SPI Prefetching and Caching and enable BIOS Write
> Protect
> + //
> + if ((FlashCycleType == FlashCycleWrite) ||
> + (FlashCycleType == FlashCycleErase)) {
> + EnableBiosWriteProtect ();
> + }
> + //
> + // Restore SMIs.
> + //
> + IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave);
> +
> + ReleaseSpiBar0 (SpiInstance);
> + return Status;
> +}
> +
> +/**
> + Wait execution cycle to complete on the SPI interface.
> +
> + @param[in] This The SPI protocol instance
> + @param[in] PchSpiBar0 Spi MMIO base address
> + @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
> +
> + @retval TRUE SPI cycle completed on the interface.
> + @retval FALSE Time out while waiting the SPI cycle to complete.
> + It's not safe to program the next command on the SPI
> interface.
> +**/
> +BOOLEAN
> +WaitForSpiCycleComplete (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINTN PchSpiBar0,
> + IN BOOLEAN ErrorCheck
> + )
> +{
> + UINT64 WaitTicks;
> + UINT64 WaitCount;
> + UINT32 Data32;
> + SPI_INSTANCE *SpiInstance;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + //
> + // Convert the wait period allowed into to tick count
> + //
> + WaitCount = SPI_WAIT_TIME / SPI_WAIT_PERIOD;
> + //
> + // Wait for the SPI cycle to complete.
> + //
> + for (WaitTicks = 0; WaitTicks < WaitCount; WaitTicks++) {
> + Data32 = MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC);
> + if ((Data32 & B_PCH_SPI_HSFSC_SCIP) == 0) {
> + MmioWrite32 (PchSpiBar0 + R_PCH_SPI_HSFSC,
> B_PCH_SPI_HSFSC_FCERR | B_PCH_SPI_HSFSC_FDONE);
> + if (((Data32 & B_PCH_SPI_HSFSC_FCERR) != 0) && (ErrorCheck == TRUE)) {
> + return FALSE;
> + } else {
> + return TRUE;
> + }
> + }
> + PchPmTimerStallRuntimeSafe (SpiInstance->PchAcpiBase,
> SPI_WAIT_PERIOD);
> + }
> + return FALSE;
> +}
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> new file mode 100644
> index 0000000000..8fb4947b1a
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> @@ -0,0 +1,410 @@
> +/** @file
> + A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
> + EFI_SMM_CONTROL2_PROTOCOL.
> +
> + We expect the PEI phase to have covered the following:
> + - ensure that the underlying QEMU machine type be X58
> + (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
> + - ensure that the ACPI PM IO space be configured
> + (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
> +
> + Our own entry point is responsible for confirming the SMI feature and for
> + configuring it.
> +
> + Copyright (C) 2013, 2015, Red Hat, Inc.<BR>
> + Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <IndustryStandard/X58Ich10.h>
> +#include <Library/BaseLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/IoLib.h>
> +#include <Library/PcdLib.h>
> +#include <Library/PciLib.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +#include <Protocol/S3SaveState.h>
> +#include <Protocol/SmmControl2.h>
> +
> +//
> +// Forward declaration.
> +//
> +STATIC
> +VOID
> +EFIAPI
> +OnS3SaveStateInstalled (
> + IN EFI_EVENT Event,
> + IN VOID *Context
> + );
> +
> +//
> +// The absolute IO port address of the SMI Control and Enable Register. It is
> +// only used to carry information from the entry point function to the
> +// S3SaveState protocol installation callback, strictly before the runtime
> +// phase.
> +//
> +STATIC UINTN mSmiEnable;
> +
> +//
> +// Event signaled when an S3SaveState protocol interface is installed.
> +//
> +STATIC EFI_EVENT mS3SaveStateInstalled;
> +
> +/**
> + Clear the SMI status
> +
> + @retval EFI_SUCCESS The function completes successfully
> + @retval EFI_DEVICE_ERROR Something error occurred
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SmmClear(
> + VOID
> +)
> +{
> + EFI_STATUS Status;
> + UINT32 OutputData;
> + UINT32 OutputPort;
> + UINT32 PmBase;
> +
> + Status = EFI_SUCCESS;
> + PmBase = ICH10_PMBASE_IO;
> +
> + OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_STS;
> + OutputData = ICH10_SMI_STS_APM;
> + IoWrite32(
> + (UINTN)OutputPort,
> + (UINT32)(OutputData)
> + );
> +
> + ///
> + /// Set the EOS Bit
> + ///
> + OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_EN;
> + OutputData = IoRead32((UINTN)OutputPort);
> + OutputData |= ICH10_SMI_EN_EOS;
> + IoWrite32(
> + (UINTN)OutputPort,
> + (UINT32)(OutputData)
> + );
> +
> + ///
> + /// There is no need to read EOS back and check if it is set.
> + /// This can lead to a reading of zero if an SMI occurs right after the SMI_EN
> port read
> + /// but before the data is returned to the CPU.
> + /// SMM Dispatcher should make sure that EOS is set after all SMI sources are
> processed.
> + ///
> + return Status;
> +}
> +
> +/**
> + Invokes SMI activation from either the preboot or runtime environment.
> +
> + This function generates an SMI.
> +
> + @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
> + @param[in,out] CommandPort The value written to the command port.
> + @param[in,out] DataPort The value written to the data port.
> + @param[in] Periodic Optional mechanism to engender a periodic
> + stream.
> + @param[in] ActivationInterval Optional parameter to repeat at this
> + period one time or, if the Periodic
> + Boolean is set, periodically.
> +
> + @retval EFI_SUCCESS The SMI/PMI has been engendered.
> + @retval EFI_DEVICE_ERROR The timing is unsupported.
> + @retval EFI_INVALID_PARAMETER The activation period is unsupported.
> + @retval EFI_INVALID_PARAMETER The last periodic activation has not been
> + cleared.
> + @retval EFI_NOT_STARTED The SMM base service has not been
> initialized.
> +**/
> +STATIC
> +EFI_STATUS
> +EFIAPI
> +SmmControl2DxeTrigger (
> + IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
> + IN OUT UINT8 *CommandPort OPTIONAL,
> + IN OUT UINT8 *DataPort OPTIONAL,
> + IN BOOLEAN Periodic OPTIONAL,
> + IN UINTN ActivationInterval OPTIONAL
> + )
> +{
> + EFI_STATUS Status;
> + //
> + // No support for queued or periodic activation.
> + //
> + if (Periodic || ActivationInterval > 0) {
> + return EFI_DEVICE_ERROR;
> + }
> + ///
> + /// Clear any pending the APM SMI
> + ///
> + Status = SmmClear();
> + //
> + // The so-called "Advanced Power Management Status Port Register" is in fact
> + // a generic data passing register, between the caller and the SMI
> + // dispatcher. The ICH9 spec calls it "scratchpad register" -- calling it
> + // "status" elsewhere seems quite the misnomer. Status registers usually
> + // report about hardware status, while this register is fully governed by
> + // software.
> + //
> + // Write to the status register first, as this won't trigger the SMI just
> + // yet. Then write to the control register.
> + //
> + IoWrite8 (ICH10_APM_STS, DataPort == NULL ? 0 : *DataPort);
> + IoWrite8 (ICH10_APM_CNT, CommandPort == NULL ? 0 : *CommandPort);
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Clears any system state that was created in response to the Trigger() call.
> +
> + This function acknowledges and causes the deassertion of the SMI activation
> + source.
> +
> + @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
> + @param[in] Periodic Optional parameter to repeat at this period
> + one time
> +
> + @retval EFI_SUCCESS The SMI/PMI has been engendered.
> + @retval EFI_DEVICE_ERROR The source could not be cleared.
> + @retval EFI_INVALID_PARAMETER The service did not support the Periodic
> input
> + argument.
> +**/
> +STATIC
> +EFI_STATUS
> +EFIAPI
> +SmmControl2DxeClear (
> + IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
> + IN BOOLEAN Periodic OPTIONAL
> + )
> +{
> + EFI_STATUS Status;
> +
> + if (Periodic) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // The PI spec v1.4 explains that Clear() is only supposed to clear software
> + // status; it is not in fact responsible for deasserting the SMI. It gives
> + // two reasons for this: (a) many boards clear the SMI automatically when
> + // entering SMM, (b) if Clear() actually deasserted the SMI, then it could
> + // incorrectly suppress an SMI that was asynchronously asserted between the
> + // last return of the SMI handler and the call made to Clear().
> + //
> + // In fact QEMU automatically deasserts CPU_INTERRUPT_SMI in:
> + // - x86_cpu_exec_interrupt() [target-i386/seg_helper.c], and
> + // - kvm_arch_pre_run() [target-i386/kvm.c].
> + //
> + // So, nothing to do here.
> + //
> + Status = SmmClear();
> +
> + return EFI_SUCCESS;
> +}
> +
> +STATIC EFI_SMM_CONTROL2_PROTOCOL mControl2 = {
> + &SmmControl2DxeTrigger,
> + &SmmControl2DxeClear,
> + MAX_UINTN // MinimumTriggerPeriod -- we don't support periodic SMIs
> +};
> +
> +//
> +// Entry point of this driver.
> +//
> +EFI_STATUS
> +EFIAPI
> +SmmControl2DxeEntryPoint (
> + IN EFI_HANDLE ImageHandle,
> + IN EFI_SYSTEM_TABLE *SystemTable
> + )
> +{
> + UINT32 PmBase;
> + UINT32 SmiEnableVal;
> + EFI_STATUS Status;
> +
> + //
> + // This module should only be included if SMRAM support is required.
> + //
> + ASSERT (FeaturePcdGet (PcdSmmSmramRequire));
> +
> + //
> + // Calculate the absolute IO port address of the SMI Control and Enable
> + // Register. (As noted at the top, the PEI phase has left us with a working
> + // ACPI PM IO space.)
> + //
> + PmBase = PciRead32 (POWER_MGMT_REGISTER_ICH10 (ICH10_PMBASE)) &
> + ICH10_PMBASE_MASK;
> + mSmiEnable = PmBase + ICH10_PMBASE_OFS_SMI_EN;
> +
> + //
> + // If APMC_EN is pre-set in SMI_EN, that's QEMU's way to tell us that SMI
> + // support is not available. (For example due to KVM lacking it.) Otherwise,
> + // this bit is clear after each reset.
> + //
> + SmiEnableVal = IoRead32 (mSmiEnable);
> + if ((SmiEnableVal & ICH10_SMI_EN_APMC_EN) != 0) {
> + DEBUG ((EFI_D_ERROR, "%a: this X58 implementation lacks SMI\n",
> + __FUNCTION__));
> + }
> +
> + //
> + // Otherwise, configure the board to inject an SMI when ICH10_APM_CNT is
> + // written to. (See the Trigger() method above.)
> + //
> + SmiEnableVal |= ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
> + IoWrite32 (mSmiEnable, SmiEnableVal);
> +
> + //
> + // Prevent software from undoing the above (until platform reset).
> + //
> + PciOr16 (POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
> + ICH10_GEN_PMCON_1_SMI_LOCK);
> +
> + //
> + // If we can clear GBL_SMI_EN now, that means QEMU's SMI support is not
> + // appropriate.
> + //
> + IoWrite32 (mSmiEnable, SmiEnableVal &
> ~(UINT32)ICH10_SMI_EN_GBL_SMI_EN);
> + if (IoRead32 (mSmiEnable) != SmiEnableVal) {
> + DEBUG ((EFI_D_ERROR, "%a: failed to lock down GBL_SMI_EN\n",
> + __FUNCTION__));
> + goto FatalError;
> + }
> +
> + VOID *Registration;
> +
> + //
> + // On S3 resume the above register settings have to be repeated. Register a
> + // protocol notify callback that, when boot script saving becomes
> + // available, saves operations equivalent to the above to the boot script.
> + //
> + Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK,
> + OnS3SaveStateInstalled, NULL /* Context */,
> + &mS3SaveStateInstalled);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: CreateEvent: %r\n", __FUNCTION__, Status));
> + goto FatalError;
> + }
> +
> + Status = gBS->RegisterProtocolNotify (&gEfiS3SaveStateProtocolGuid,
> + mS3SaveStateInstalled, &Registration);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: RegisterProtocolNotify: %r\n",
> __FUNCTION__,
> + Status));
> + goto ReleaseEvent;
> + }
> +
> + //
> + // Kick the event right now -- maybe the boot script is already saveable.
> + //
> + Status = gBS->SignalEvent (mS3SaveStateInstalled);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: SignalEvent: %r\n", __FUNCTION__, Status));
> + goto ReleaseEvent;
> + }
> +
> + //
> + // We have no pointers to convert to virtual addresses. The handle itself
> + // doesn't matter, as protocol services are not accessible at runtime.
> + //
> + Status = gBS->InstallMultipleProtocolInterfaces (&ImageHandle,
> + &gEfiSmmControl2ProtocolGuid, &mControl2,
> + NULL);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: InstallMultipleProtocolInterfaces: %r\n",
> + __FUNCTION__, Status));
> + goto ReleaseEvent;
> + }
> +
> + return EFI_SUCCESS;
> +
> +ReleaseEvent:
> + if (mS3SaveStateInstalled != NULL) {
> + gBS->CloseEvent (mS3SaveStateInstalled);
> + }
> +
> +FatalError:
> + //
> + // We really don't want to continue in this case.
> + //
> + ASSERT (FALSE);
> + CpuDeadLoop ();
> + return EFI_UNSUPPORTED;
> +}
> +
> +/**
> + Notification callback for S3SaveState installation.
> +
> + @param[in] Event Event whose notification function is being invoked.
> +
> + @param[in] Context The pointer to the notification function's context, which
> + is implementation-dependent.
> +**/
> +STATIC
> +VOID
> +EFIAPI
> +OnS3SaveStateInstalled (
> + IN EFI_EVENT Event,
> + IN VOID *Context
> + )
> +{
> + EFI_STATUS Status;
> + EFI_S3_SAVE_STATE_PROTOCOL *S3SaveState;
> + UINT32 SmiEnOrMask, SmiEnAndMask;
> + UINT16 GenPmCon1OrMask, GenPmCon1AndMask;
> +
> + ASSERT (Event == mS3SaveStateInstalled);
> +
> + Status = gBS->LocateProtocol (&gEfiS3SaveStateProtocolGuid,
> + NULL /* Registration */, (VOID **)&S3SaveState);
> + if (EFI_ERROR (Status)) {
> + return;
> + }
> +
> + //
> + // These operations were originally done, verified and explained in the entry
> + // point function of the driver.
> + //
> + SmiEnOrMask = ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
> + SmiEnAndMask = MAX_UINT32;
> + Status = S3SaveState->Write (
> + S3SaveState,
> + EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE,
> + EfiBootScriptWidthUint32,
> + (UINT64)mSmiEnable,
> + &SmiEnOrMask,
> + &SmiEnAndMask
> + );
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a:
> EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE: %r\n",
> + __FUNCTION__, Status));
> + ASSERT (FALSE);
> + CpuDeadLoop ();
> + }
> +
> + GenPmCon1OrMask = ICH10_GEN_PMCON_1_SMI_LOCK;
> + GenPmCon1AndMask = MAX_UINT16;
> + Status = S3SaveState->Write (
> + S3SaveState,
> + EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE,
> + EfiBootScriptWidthUint16,
> + (UINT64)POWER_MGMT_REGISTER_ICH10
> (ICH10_GEN_PMCON_1),
> + &GenPmCon1OrMask,
> + &GenPmCon1AndMask
> + );
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR,
> + "%a: EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE: %r\n",
> __FUNCTION__,
> + Status));
> + ASSERT (FALSE);
> + CpuDeadLoop ();
> + }
> +
> + DEBUG ((EFI_D_VERBOSE, "%a: boot script fragment saved\n",
> __FUNCTION__));
> + gBS->CloseEvent (Event);
> + mS3SaveStateInstalled = NULL;
> +}
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> new file mode 100644
> index 0000000000..19eb469657
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> @@ -0,0 +1,175 @@
> +/** @file
> + PCH SPI SMM Driver implements the SPI Host Controller Compatibility
> Interface.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include "PchSpi.h"
> +
> +//
> +// Global variables
> +//
> +GLOBAL_REMOVE_IF_UNREFERENCED SPI_INSTANCE *mSpiInstance;
> +//
> +// mPchSpiResvMmioAddr keeps the reserved MMIO range assiged to SPI.
> +// In SMM it always set back the reserved MMIO address to SPI BAR0 to ensure
> the MMIO range
> +// won't overlap with SMRAM range, and trusted.
> +//
> +GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mSpiResvMmioAddr;
> +
> +/**
> + <b>SPI Runtime SMM Module Entry Point</b>\n
> + - <b>Introduction</b>\n
> + The SPI SMM module provide a standard way for other modules to use the
> PCH SPI Interface in SMM.
> +
> + - @pre
> + - EFI_SMM_BASE2_PROTOCOL
> + - Documented in System Management Mode Core Interface Specification .
> +
> + - @result
> + The SPI SMM driver produces @link _PCH_SPI_PROTOCOL
> PCH_SPI_PROTOCOL @endlink with GUID
> + gPchSmmSpiProtocolGuid which is different from SPI RUNTIME driver.
> +
> + - <b>Integration Check List</b>\n
> + - This driver supports Descriptor Mode only.
> + - This driver supports Hardware Sequence only.
> + - When using SMM SPI Protocol to perform flash access in an SMI handler,
> + and the SMI occurrence is asynchronous to normal mode code execution,
> + proper synchronization mechanism must be applied, e.g. disable SMI before
> + the normal mode SendSpiCmd() starts and re-enable SMI after
> + the normal mode SendSpiCmd() completes.
> + @note The implementation of SendSpiCmd() uses GBL_SMI_EN in
> + SMI_EN register (ABase + 30h) to disable and enable SMIs. But this may
> + not be effective as platform may well set the SMI_LOCK bit (i.e., PMC PCI
> Offset A0h [4]).
> + So the synchronization at caller level is likely needed.
> +
> + @param[in] ImageHandle Image handle of this driver.
> + @param[in] SystemTable Global system service table.
> +
> + @retval EFI_SUCCESS Initialization complete.
> + @exception EFI_UNSUPPORTED The chipset is unsupported by this driver.
> + @retval EFI_OUT_OF_RESOURCES Do not have enough resources to
> initialize the driver.
> + @retval EFI_DEVICE_ERROR Device error, driver exits abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +InstallPchSpi (
> + IN EFI_HANDLE ImageHandle,
> + IN EFI_SYSTEM_TABLE *SystemTable
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Init PCH spi reserved MMIO address.
> + //
> + mSpiResvMmioAddr = PCH_SPI_BASE_ADDRESS;
> +
> + ///
> + /// Allocate pool for SPI protocol instance
> + ///
> + Status = gSmst->SmmAllocatePool (
> + EfiRuntimeServicesData, /// MemoryType don't care
> + sizeof (SPI_INSTANCE),
> + (VOID **) &mSpiInstance
> + );
> + if (EFI_ERROR (Status)) {
> + return Status;
> + }
> +
> + if (mSpiInstance == NULL) {
> + return EFI_OUT_OF_RESOURCES;
> + }
> +
> + ZeroMem ((VOID *) mSpiInstance, sizeof (SPI_INSTANCE));
> + ///
> + /// Initialize the SPI protocol instance
> + ///
> + Status = SpiProtocolConstructor (mSpiInstance);
> + if (EFI_ERROR (Status)) {
> + return Status;
> + }
> + //
> + // Install the SMM EFI_SPI_PROTOCOL interface
> + //
> + Status = gSmst->SmmInstallProtocolInterface (
> + &(mSpiInstance->Handle),
> + &gEfiSmmSpiProtocolGuid,
> + EFI_NATIVE_INTERFACE,
> + &(mSpiInstance->SpiProtocol)
> + );
> + if (EFI_ERROR (Status)) {
> + gSmst->SmmFreePool (mSpiInstance);
> + return EFI_DEVICE_ERROR;
> + }
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Acquire PCH spi mmio address.
> + It is not expected for this BAR0 to change because the SPI device is hidden
> + from the OS for SKL PCH LP/H B stepping and above (refer to section 3.5.1),
> + but if it is ever different from the preallocated address, reassign it back.
> + In SMM, it always override the BAR0 and returns the reserved MMIO range
> for SPI.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval PchSpiBar0 return SPI MMIO address
> +**/
> +UINTN
> +AcquireSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + )
> +{
> + //
> + // SPIBAR0 will be different before and after PCI enum so need to get it from
> SPI BAR0 reg.
> + //
> + return mSpiResvMmioAddr;
> +}
> +
> +/**
> + Release pch spi mmio address. Do nothing.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval None
> +**/
> +VOID
> +ReleaseSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + )
> +{
> +}
> +
> +/**
> + This function is a hook for Spi to disable BIOS Write Protect
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in
> SMM phase
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +DisableBiosWriteProtect (
> + VOID
> + )
> +{
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + This function is a hook for Spi to enable BIOS Write Protect
> +
> +
> +**/
> +VOID
> +EFIAPI
> +EnableBiosWriteProtect (
> + VOID
> + )
> +{
> +}
> diff --git a/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> new file mode 100644
> index 0000000000..f9d340d6df
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> @@ -0,0 +1,22 @@
> +## @file
> +# Copyright (c) 2014 - 2016 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + DEC_SPECIFICATION = 0x00010005
> + PACKAGE_NAME = ICH10Pkg
> + PACKAGE_GUID = 4E97AC4B-F64C-4008-BBDE-01CC3B0BAA6B
> + PACKAGE_VERSION = 0.91
> +
> +[Includes]
> + Include
> +
> +[Ppis]
> +
> +[Guids]
> + gEfiPchTokenSpaceGuid = { 0x89a1b278, 0xa1a1, 0x4df7, { 0xb1, 0x37, 0xde,
> 0x5a, 0xd7, 0xc4, 0x79, 0x13 } }
> +[Protocols]
> + gEfiSmmSpiProtocolGuid = {0xbd75fe35, 0xfdce, 0x49d7, {0xa9, 0xdd, 0xb2,
> 0x6f, 0x1f, 0xc6, 0xb4, 0x37}}
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> new file mode 100644
> index 0000000000..c36360bcb0
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> @@ -0,0 +1,98 @@
> +/** @file
> + The header file includes the common header files, defines
> + internal structure and functions used by SpiFlashCommonLib.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef __SPI_FLASH_COMMON_LIB_H__
> +#define __SPI_FLASH_COMMON_LIB_H__
> +
> +#include <Uefi.h>
> +#include <Library/BaseLib.h>
> +#include <Library/PcdLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <Library/MemoryAllocationLib.h>
> +#include <Library/UefiDriverEntryPoint.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +
> +#define SECTOR_SIZE_4KB 0x1000 // Common 4kBytes sector size
> +/**
> + Enable block protection on the Serial Flash device.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashLock (
> + VOID
> + );
> +
> +/**
> + Read NumBytes bytes of data from the address specified by
> + PAddress into Buffer.
> +
> + @param[in] Address The starting physical address of the read.
> + @param[in,out] NumBytes On input, the number of bytes to read. On
> output, the number
> + of bytes actually read.
> + @param[out] Buffer The destination data buffer for the read.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashRead (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + OUT UINT8 *Buffer
> + );
> +
> +/**
> + Write NumBytes bytes of data from Buffer to the address specified by
> + PAddresss.
> +
> + @param[in] Address The starting physical address of the write.
> + @param[in,out] NumBytes On input, the number of bytes to write. On
> output,
> + the actual number of bytes written.
> + @param[in] Buffer The source data buffer for the write.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashWrite (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + IN UINT8 *Buffer
> + );
> +
> +/**
> + Erase the block starting at Address.
> +
> + @param[in] Address The starting physical address of the block to be
> erased.
> + This library assume that caller garantee that the PAddress
> + is at the starting address of this block.
> + @param[in] NumBytes On input, the number of bytes of the logical block
> to be erased.
> + On output, the actual number of bytes erased.
> +
> + @retval EFI_SUCCESS. Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashBlockErase (
> + IN UINTN Address,
> + IN UINTN *NumBytes
> + );
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> new file mode 100644
> index 0000000000..552ce28d8c
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> @@ -0,0 +1,43 @@
> +/** @file
> + Macros that simplify accessing PCH devices's PCI registers.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_ACCESS_H_
> +#define _PCH_ACCESS_H_
> +
> +#include "PchReservedResources.h"
> +
> +#ifndef STALL_ONE_MICRO_SECOND
> +#define STALL_ONE_MICRO_SECOND 1
> +#endif
> +#ifndef STALL_ONE_SECOND
> +#define STALL_ONE_SECOND 1000000
> +#endif
> +
> +
> +///
> +/// The default PCH PCI bus number
> +///
> +#define DEFAULT_PCI_BUS_NUMBER_PCH 0
> +
> +//
> +// Default Vendor ID and Subsystem ID
> +//
> +#define V_PCH_INTEL_VENDOR_ID 0x8086 ///< Default Intel PCH Vendor
> ID
> +#define V_PCH_DEFAULT_SID 0x7270 ///< Default Intel PCH Subsystem
> ID
> +#define V_PCH_DEFAULT_SVID_SID (V_INTEL_VENDOR_ID +
> (V_PCH_DEFAULT_SID << 16)) ///< Default INTEL PCH Vendor ID and
> Subsystem ID
> +
> +//
> +// Include device register definitions
> +//
> +
> +#include "Register/PchRegsPmc.h"
> +
> +#include "Register/PchRegsSpi.h"
> +
> +#endif
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> new file mode 100644
> index 0000000000..d503d130c8
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> @@ -0,0 +1,94 @@
> +/** @file
> + Build time limits of PCH resources.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_LIMITS_H_
> +#define _PCH_LIMITS_H_
> +
> +//
> +// PCIe limits
> +//
> +#define PCH_MAX_PCIE_ROOT_PORTS
> PCH_H_PCIE_MAX_ROOT_PORTS
> +#define PCH_H_PCIE_MAX_ROOT_PORTS 20
> +#define PCH_LP_PCIE_MAX_ROOT_PORTS 12
> +
> +#define PCH_MAX_PCIE_CONTROLLERS
> PCH_H_PCIE_MAX_CONTROLLERS
> +#define PCH_PCIE_CONTROLLER_PORTS 4
> +#define PCH_H_PCIE_MAX_CONTROLLERS
> (PCH_H_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
> +#define PCH_LP_PCIE_MAX_CONTROLLERS
> (PCH_LP_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
> +
> +//
> +// PCIe clocks limits
> +//
> +#define PCH_LP_PCIE_MAX_CLK_REQ 6
> +#define PCH_H_PCIE_MAX_CLK_REQ 16
> +
> +//
> +// RST PCIe Storage Cycle Router limits
> +//
> +#define PCH_MAX_RST_PCIE_STORAGE_CR 3
> +
> +//
> +// SATA limits
> +//
> +#define PCH_MAX_SATA_PORTS PCH_H_AHCI_MAX_PORTS
> +#define PCH_H_AHCI_MAX_PORTS 8 ///< Max number of sata
> ports in SKL PCH H
> +#define PCH_LP_AHCI_MAX_PORTS 3 ///< Max number of sata
> ports in SKL PCH LP
> +#define PCH_SATA_MAX_DEVICES_PER_PORT 1 ///< Max support
> device numner per port, Port Multiplier is not support.
> +
> +//
> +// USB limits
> +//
> +#define PCH_MAX_USB2_PORTS PCH_H_XHCI_MAX_USB2_PORTS
> +
> +#define PCH_H_XHCI_MAX_USB2_PHYSICAL_PORTS 14 ///< Max Physical
> Connector XHCI, not counting virtual ports like USB-R.
> +#define PCH_LP_XHCI_MAX_USB2_PHYSICAL_PORTS 10 ///< Max Physical
> Connector XHCI, not counting virtual ports like USB-R.
> +
> +#define PCH_H_XHCI_MAX_USB2_PORTS 16 ///< 14 High Speed lanes
> + Including two ports reserved for USBr
> +#define PCH_LP_XHCI_MAX_USB2_PORTS 12 ///< 10 High Speed lanes
> + Including two ports reserved for USBr
> +
> +#define PCH_MAX_USB3_PORTS PCH_H_XHCI_MAX_USB3_PORTS
> +
> +#define PCH_H_XHCI_MAX_USB3_PORTS 10 ///< 10 Super Speed
> lanes
> +#define PCH_LP_XHCI_MAX_USB3_PORTS 6 ///< 6 Super Speed lanes
> +
> +#define PCH_XHCI_MAX_SSIC_PORT_COUNT 2 ///< 2 SSIC ports in SKL
> PCH-LP and SKL PCH-H
> +
> +//
> +// SerialIo limits
> +//
> +#define PCH_SERIALIO_MAX_CONTROLLERS 11 ///< Number of SerialIo
> controllers, this includes I2C, SPI and UART
> +#define PCH_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo
> I2C controllers
> +#define PCH_LP_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of
> SerialIo I2C controllers for PCH-LP
> +#define PCH_H_SERIALIO_MAX_I2C_CONTROLLERS 4 ///< Number of
> SerialIo I2C controllers for PCH-H
> +#define PCH_SERIALIO_MAX_SPI_CONTROLLERS 2 ///< Number of SerialIo
> SPI controllers
> +#define PCH_SERIALIO_MAX_UART_CONTROLLERS 3 ///< Number of
> SerialIo UART controllers
> +
> +//
> +// ISH limits
> +//
> +#define PCH_ISH_MAX_GP_PINS 8
> +#define PCH_ISH_MAX_UART_CONTROLLERS 2
> +#define PCH_ISH_MAX_I2C_CONTROLLERS 3
> +#define PCH_ISH_MAX_SPI_CONTROLLERS 1
> +
> +//
> +// SCS limits
> +//
> +#define PCH_SCS_MAX_CONTROLLERS 3 ///< Number of Storage and
> Communication Subsystem controllers, this includes eMMC, SDIO, SDCARD
> +
> +//
> +// Flash Protection Range Register
> +//
> +#define PCH_FLASH_PROTECTED_RANGES 5
> +
> +//
> +// Number of eSPI slaves
> +//
> +#define PCH_ESPI_MAX_SLAVE_ID 2
> +#endif // _PCH_LIMITS_H_
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> new file mode 100644
> index 0000000000..00139fc230
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> @@ -0,0 +1,60 @@
> +/** @file
> + PCH preserved MMIO resource definitions.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_PRESERVED_RESOURCES_H_
> +#define _PCH_PRESERVED_RESOURCES_H_
> +
> +/**
> + PCH preserved MMIO range, 24 MB, from 0xFD000000 to 0xFE7FFFFF
> +
> + Detailed recommended static allocation
> + +-------------------------------------------------------------------------+
> + | Size | Start | End | Usage |
> + | 16 MB | 0xFD000000 | 0xFDFFFFFF | SBREG |
> + | 64 KB | 0xFE000000 | 0xFE00FFFF | PMC MBAR |
> + | 4 KB | 0xFE010000 | 0xFE010FFF | SPI BAR0 |
> + | 88 KB | 0xFE020000 | 0xFE035FFF | SerialIo BAR in ACPI mode |
> + | 24 KB | 0xFE036000 | 0xFE03BFFF | Unused |
> + | 4 KB | 0xFE03C000 | 0xFE03CFFF | Thermal Device in ACPI mode |
> + | 524 KB | 0xFE03D000 | 0xFE0BFFFF | Unused |
> + | 256 KB | 0xFE0C0000 | 0xFE0FFFFF | TraceHub FW BAR |
> + | 1 MB | 0xFE100000 | 0xFE1FFFFF | TraceHub MTB BAR |
> + | 2 MB | 0xFE200000 | 0xFE3FFFFF | TraceHub SW BAR |
> + | 64 KB | 0xFE400000 | 0xFE40FFFF | CIO2 MMIO BAR in ACPI mode |
> + | 2 MB - 64KB | 0xFE410000 | 0xFE5FFFFF | Unused |
> + | 2 MB | 0xFE600000 | 0xFE7FFFFF | Temp address |
> + +-------------------------------------------------------------------------+
> +**/
> +#define PCH_PRESERVED_BASE_ADDRESS 0xFD000000 ///< Pch
> preserved MMIO base address
> +#define PCH_PRESERVED_MMIO_SIZE 0x01800000 ///< 24MB
> +#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO
> base address
> +#define PCH_PCR_MMIO_SIZE 0x01000000 ///< 16MB
> +#define PCH_PWRM_BASE_ADDRESS 0xFE000000 ///< PMC MBAR
> MMIO base address
> +#define PCH_PWRM_MMIO_SIZE 0x00010000 ///< 64KB
> +#define PCH_SPI_BASE_ADDRESS 0xFED1C000 + 0x3800 ///< SPI
> MBAR MMIO base address
> +#define PCH_SPI_MMIO_SIZE 0x00001000 ///< 4KB
> +#define PCH_SERIAL_IO_BASE_ADDRESS 0xFE020000 ///< SerialIo MMIO
> base address
> +#define PCH_SERIAL_IO_MMIO_SIZE 0x00016000 ///< 88KB
> +#define PCH_THERMAL_BASE_ADDRESS 0xFE03C000 ///< Thermal
> Device in ACPI mode
> +#define PCH_THERMAL_MMIO_SIZE 0x00001000 ///< 4KB
> +#define PCH_TRACE_HUB_FW_BASE_ADDRESS 0xFE0C0000 ///< TraceHub
> FW MMIO base address
> +#define PCH_TRACE_HUB_FW_MMIO_SIZE 0x00040000 ///< 256KB
> +#define PCH_TRACE_HUB_MTB_BASE_ADDRESS 0xFE100000 ///<
> TraceHub MTB MMIO base address
> +#define PCH_TRACE_HUB_MTB_MMIO_SIZE 0x00100000 ///< 1MB
> +#define PCH_TRACE_HUB_SW_BASE_ADDRESS 0xFE200000 ///< TraceHub
> SW MMIO base address
> +#define PCH_TRACE_HUB_SW_MMIO_SIZE 0x00200000 ///< 2MB
> +#define PCH_CIO2_BASE_ADDRESS 0xFE400000 ///< CIO2 MMIO BAR
> in ACPI mode
> +#define PCH_CIO2_MMIO_SIZE 0x00010000 ///< 64KB
> +#define PCH_TEMP_BASE_ADDRESS 0xFE600000 ///< preserved temp
> address for misc usage
> +#define PCH_TEMP_MMIO_SIZE 0x00200000 ///< 2MB
> +
> +#define RCRB 0xFED1C000
> +#define SPIBAR 0x3800
> +
> +#endif // _PCH_PRESERVED_RESOURCES_H_
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> new file mode 100644
> index 0000000000..cb5f26c47b
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> @@ -0,0 +1,295 @@
> +/** @file
> + This file defines the PCH SPI Protocol which implements the
> + Intel(R) PCH SPI Host Controller Compatibility Interface.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_SPI_PROTOCOL_H_
> +#define _PCH_SPI_PROTOCOL_H_
> +
> +//
> +// Extern the GUID for protocol users.
> +//
> +extern EFI_GUID gEfiSpiProtocolGuid;
> +extern EFI_GUID gEfiSmmSpiProtocolGuid;
> +
> +//
> +// Forward reference for ANSI C compatibility
> +//
> +typedef struct _PCH_SPI_PROTOCOL EFI_SPI_PROTOCOL;
> +
> +//
> +// SPI protocol data structures and definitions
> +//
> +
> +/**
> + Flash Region Type
> +**/
> +typedef enum {
> + FlashRegionDescriptor,
> + FlashRegionBios,
> + FlashRegionMe,
> + FlashRegionGbE,
> + FlashRegionPlatformData,
> + FlashRegionDer,
> + FlashRegionAll,
> + FlashRegionMax
> +} FLASH_REGION_TYPE;
> +
> +
> +//
> +// Protocol member functions
> +//
> +
> +/**
> + Read data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[out] Buffer The Pointer to caller-allocated buffer containing
> the dada received.
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *Buffer
> + );
> +
> +/**
> + Write data to the flash part. Remark: Erase may be needed before write to the
> flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in] Buffer Pointer to caller-allocated buffer containing the
> data sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_WRITE) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN UINT8 *Buffer
> + );
> +
> +/**
> + Erase some area on the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_ERASE) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount
> + );
> +
> +/**
> + Read SFDP data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] Address The starting byte address for SFDP data read.
> + @param[in] ByteCount Number of bytes in SFDP data portion of the SPI
> cycle
> + @param[out] SfdpData The Pointer to caller-allocated buffer containing
> the SFDP data received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ_SFDP) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *SfdpData
> + );
> +
> +/**
> + Read Jedec Id from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] ByteCount Number of bytes in JedecId data portion of the
> SPI cycle, the data size is 3 typically
> + @param[out] JedecId The Pointer to caller-allocated buffer containing
> JEDEC ID received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ_JEDEC_ID) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 ByteCount,
> + OUT UINT8 *JedecId
> + );
> +
> +/**
> + Write the status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[in] StatusValue The Pointer to caller-allocated buffer containing
> the value of Status register writing
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_WRITE_STATUS) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + IN UINT8 *StatusValue
> + );
> +
> +/**
> + Read status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[out] StatusValue The Pointer to caller-allocated buffer
> containing the value of Status register received.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ_STATUS) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + OUT UINT8 *StatusValue
> + );
> +
> +/**
> + Get the SPI region base and size, based on the enum type
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for for the base
> address which is listed in the Descriptor.
> + @param[out] BaseAddress The Flash Linear Address for the Region 'n'
> Base
> + @param[out] RegionSize The size for the Region 'n'
> +
> + @retval EFI_SUCCESS Read success
> + @retval EFI_INVALID_PARAMETER Invalid region type given
> + @retval EFI_DEVICE_ERROR The region is not used
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_GET_REGION_ADDRESS) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + OUT UINT32 *BaseAddress,
> + OUT UINT32 *RegionSize
> + );
> +
> +/**
> + Read PCH Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing PCH Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_READ_PCH_SOFTSTRAP) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + Read CPU Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle.
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing CPU Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_READ_CPU_SOFTSTRAP) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + These protocols/PPI allows a platform module to perform SPI operations
> through the
> + Intel PCH SPI Host Controller Interface.
> +**/
> +struct _PCH_SPI_PROTOCOL {
> + /**
> + This member specifies the revision of this structure. This field is used to
> + indicate backwards compatible changes to the protocol.
> + **/
> + UINT8 Revision;
> + PCH_SPI_FLASH_READ FlashRead; ///< Read data from the flash
> part.
> + PCH_SPI_FLASH_WRITE FlashWrite; ///< Write data to the flash
> part. Remark: Erase may be needed before write to the flash part.
> + PCH_SPI_FLASH_ERASE FlashErase; ///< Erase some area on the
> flash part.
> + PCH_SPI_FLASH_READ_SFDP FlashReadSfdp; ///< Read SFDP data
> from the flash part.
> + PCH_SPI_FLASH_READ_JEDEC_ID FlashReadJedecId; ///< Read Jedec Id
> from the flash part.
> + PCH_SPI_FLASH_WRITE_STATUS FlashWriteStatus; ///< Write the status
> register in the flash part.
> + PCH_SPI_FLASH_READ_STATUS FlashReadStatus; ///< Read status
> register in the flash part.
> + PCH_SPI_GET_REGION_ADDRESS GetRegionAddress; ///< Get the SPI
> region base and size
> + PCH_SPI_READ_PCH_SOFTSTRAP ReadPchSoftStrap; ///< Read PCH Soft
> Strap Values
> + PCH_SPI_READ_CPU_SOFTSTRAP ReadCpuSoftStrap; ///< Read CPU Soft
> Strap Values
> +};
> +
> +/**
> + PCH SPI PPI/PROTOCOL revision number
> +
> + Revision 1: Initial version
> +**/
> +#define PCH_SPI_SERVICES_REVISION 1
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> new file mode 100644
> index 0000000000..e08721f405
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> @@ -0,0 +1,647 @@
> +/** @file
> + Register names for PCH PMC device
> +
> + Conventions:
> +
> + - Prefixes:
> + Definitions beginning with "R_" are registers
> + Definitions beginning with "B_" are bits within registers
> + Definitions beginning with "V_" are meaningful values within the bits
> + Definitions beginning with "S_" are register sizes
> + Definitions beginning with "N_" are the bit position
> + - In general, PCH registers are denoted by "_PCH_" in register names
> + - Registers / bits that are different between PCH generations are denoted by
> + "_PCH_[generation_name]_" in register/bit names.
> + - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit
> names.
> + Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit
> names.
> + e.g., "_PCH_H_", "_PCH_LP_"
> + Registers / bits names without _H_ or _LP_ apply for both H and LP.
> + - Registers / bits that are different between SKUs are denoted by
> "_[SKU_name]"
> + at the end of the register/bit names
> + - Registers / bits of new devices introduced in a PCH generation will be just
> named
> + as "_PCH_" without [generation_name] inserted.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_REGS_PMC_H_
> +#define _PCH_REGS_PMC_H_
> +
> +//
> +// PMC Registers (D31:F2)
> +//
> +#define PCI_DEVICE_NUMBER_PCH_PMC 31
> +#define PCI_FUNCTION_NUMBER_PCH_PMC 2
> +
> +#define R_PCH_PMC_PM_DATA_BAR 0x10
> +#define B_PCH_PMC_PM_DATA_BAR 0xFFFFC000
> +#define R_PCH_PMC_ACPI_BASE 0x40
> +#define B_PCH_PMC_ACPI_BASE_BAR 0xFFFC
> +#define R_PCH_PMC_ACPI_CNT 0x44
> +#define B_PCH_PMC_ACPI_CNT_PWRM_EN BIT8
> ///< PWRM enable
> +#define B_PCH_PMC_ACPI_CNT_ACPI_EN BIT7 ///<
> ACPI eanble
> +#define B_PCH_PMC_ACPI_CNT_SCIS (BIT2 | BIT1 | BIT0)
> ///< SCI IRQ select
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ9 0
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ10 1
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ11 2
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ20 4
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ21 5
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ22 6
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ23 7
> +#define R_PCH_PMC_PWRM_BASE 0x48
> +#define B_PCH_PMC_PWRM_BASE_BAR 0xFFFF0000
> ///< PWRM must be 64KB alignment to align the source decode.
> +#define R_PCH_PMC_GEN_PMCON_A 0xA0
> +#define B_PCH_PMC_GEN_PMCON_A_DC_PP_DIS BIT30
> +#define B_PCH_PMC_GEN_PMCON_A_DSX_PP_DIS BIT29
> +#define B_PCH_PMC_GEN_PMCON_A_AG3_PP_EN BIT28
> +#define B_PCH_PMC_GEN_PMCON_A_SX_PP_EN BIT27
> +#define B_PCH_PMC_GEN_PMCON_A_DISB BIT23
> +#define B_PCH_PMC_GEN_PMCON_A_MEM_SR BIT21
> +#define B_PCH_PMC_GEN_PMCON_A_MS4V BIT18
> +#define B_PCH_PMC_GEN_PMCON_A_GBL_RST_STS BIT16
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_OPI_PLL_SD_INC0 BIT13
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_SPXB_CG_INC0 BIT12
> +#define B_PCH_PMC_GEN_PMCON_A_BIOS_PCI_EXP_EN BIT10
> +#define B_PCH_PMC_GEN_PMCON_A_PWRBTN_LVL BIT9
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_C0 BIT7
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_OPI_ON BIT6
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_BCLKREQ_ON
> BIT5
> +#define B_PCH_PMC_GEN_PMCON_A_SMI_LOCK BIT4
> +#define B_PCH_PMC_GEN_PMCON_A_ESPI_SMI_LOCK BIT3
> ///< ESPI SMI lock
> +#define B_PCH_PMC_GEN_PMCON_A_PER_SMI_SEL 0x0003
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_64S 0x0000
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_32S 0x0001
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_16S 0x0002
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_8S 0x0003
> +#define R_PCH_PMC_GEN_PMCON_B 0xA4
> +#define B_PCH_PMC_GEN_PMCON_B_SLPSX_STR_POL_LOCK BIT18
> ///< Lock down SLP_S3/SLP_S4 Minimum Assertion width
> +#define B_PCH_PMC_GEN_PMCON_B_ACPI_BASE_LOCK BIT17
> ///< Lock ACPI BASE at 0x40, only cleared by reset when set
> +#define B_PCH_PMC_GEN_PMCON_B_PM_DATA_BAR_DIS BIT16
> +#define B_PCH_PMC_GEN_PMCON_B_PME_B0_S5_DIS BIT15
> +#define B_PCH_PMC_GEN_PMCON_B_SUS_PWR_FLR BIT14
> +#define B_PCH_PMC_GEN_PMCON_B_WOL_EN_OVRD BIT13
> +#define B_PCH_PMC_GEN_PMCON_B_DISABLE_SX_STRETCH BIT12
> +#define B_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW 0xC00
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_60US 0x000
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_1MS 0x400
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_50MS 0x800
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_2S 0xC00
> +#define B_PCH_PMC_GEN_PMCON_B_HOST_RST_STS BIT9
> +#define B_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL 0xC0
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_64MS 0xC0
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_32MS 0x80
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_16MS 0x40
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_1_5MS 0x00
> +#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW 0x30
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_1S 0x30
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_2S 0x20
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_3S 0x10
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_4S 0x00
> +#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_ASE BIT3
> +#define B_PCH_PMC_GEN_PMCON_B_RTC_PWR_STS BIT2
> +#define B_PCH_PMC_GEN_PMCON_B_PWR_FLR BIT1
> +#define B_PCH_PMC_GEN_PMCON_B_AFTERG3_EN BIT0
> +#define R_PCH_PMC_BM_CX_CNF 0xA8
> +#define B_PCH_PMC_BM_CX_CNF_STORAGE_BREAK_EN BIT31
> +#define B_PCH_PMC_BM_CX_CNF_PCIE_BREAK_EN BIT30
> +#define B_PCH_PMC_BM_CX_CNF_AZ_BREAK_EN BIT24
> +#define B_PCH_PMC_BM_CX_CNF_DPSN_BREAK_EN BIT19
> +#define B_PCH_PMC_BM_CX_CNF_XHCI_BREAK_EN BIT17
> +#define B_PCH_PMC_BM_CX_CNF_SATA3_BREAK_EN BIT16
> +#define B_PCH_PMC_BM_CX_CNF_SCRATCHPAD BIT15
> +#define B_PCH_PMC_BM_CX_CNF_PHOLD_BM_STS_BLOCK BIT14
> +#define B_PCH_PMC_BM_CX_CNF_MASK_CF BIT11
> +#define B_PCH_PMC_BM_CX_CNF_BM_STS_ZERO_EN BIT10
> +#define B_PCH_PMC_BM_CX_CNF_PM_SYNC_MSG_MODE BIT9
> +#define R_PCH_PMC_ETR3 0xAC
> +#define B_PCH_PMC_ETR3_CF9LOCK BIT31 ///< CF9h
> Lockdown
> +#define B_PCH_PMC_ETR3_USB_CACHE_DIS BIT21
> +#define B_PCH_PMC_ETR3_CF9GR BIT20 ///< CF9h
> Global Reset
> +#define B_PCH_PMC_ETR3_SKIP_HOST_RST_HS BIT19
> +#define B_PCH_PMC_ETR3_CWORWRE BIT18
> +
> +//
> +// ACPI and legacy I/O register offsets from ACPIBASE
> +//
> +#define R_PCH_ACPI_PM1_STS 0x00
> +#define S_PCH_ACPI_PM1_STS 2
> +#define B_PCH_ACPI_PM1_STS_WAK BIT15
> +#define B_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS BIT14
> +#define B_PCH_ACPI_PM1_STS_PRBTNOR BIT11
> +#define B_PCH_ACPI_PM1_STS_RTC BIT10
> +#define B_PCH_ACPI_PM1_STS_PWRBTN BIT8
> +#define B_PCH_ACPI_PM1_STS_GBL BIT5
> +#define B_PCH_ACPI_PM1_STS_BM BIT4
> +#define B_PCH_ACPI_PM1_STS_TMROF BIT0
> +#define N_PCH_ACPI_PM1_STS_WAK 15
> +#define N_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS 14
> +#define N_PCH_ACPI_PM1_STS_PRBTNOR 11
> +#define N_PCH_ACPI_PM1_STS_RTC 10
> +#define N_PCH_ACPI_PM1_STS_PWRBTN 8
> +#define N_PCH_ACPI_PM1_STS_GBL 5
> +#define N_PCH_ACPI_PM1_STS_BM 4
> +#define N_PCH_ACPI_PM1_STS_TMROF 0
> +
> +#define R_PCH_ACPI_PM1_EN 0x02
> +#define S_PCH_ACPI_PM1_EN 2
> +#define B_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS BIT14
> +#define B_PCH_ACPI_PM1_EN_RTC BIT10
> +#define B_PCH_ACPI_PM1_EN_PWRBTN BIT8
> +#define B_PCH_ACPI_PM1_EN_GBL BIT5
> +#define B_PCH_ACPI_PM1_EN_TMROF BIT0
> +#define N_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS 14
> +#define N_PCH_ACPI_PM1_EN_RTC 10
> +#define N_PCH_ACPI_PM1_EN_PWRBTN 8
> +#define N_PCH_ACPI_PM1_EN_GBL 5
> +#define N_PCH_ACPI_PM1_EN_TMROF 0
> +
> +#define R_PCH_ACPI_PM1_CNT 0x04
> +#define S_PCH_ACPI_PM1_CNT 4
> +#define B_PCH_ACPI_PM1_CNT_SLP_EN BIT13
> +#define B_PCH_ACPI_PM1_CNT_SLP_TYP (BIT12 | BIT11 | BIT10)
> +#define V_PCH_ACPI_PM1_CNT_S0 0
> +#define V_PCH_ACPI_PM1_CNT_S1 BIT10
> +#define V_PCH_ACPI_PM1_CNT_S3 (BIT12 | BIT10)
> +#define V_PCH_ACPI_PM1_CNT_S4 (BIT12 | BIT11)
> +#define V_PCH_ACPI_PM1_CNT_S5 (BIT12 | BIT11 | BIT10)
> +#define B_PCH_ACPI_PM1_CNT_GBL_RLS BIT2
> +#define B_PCH_ACPI_PM1_CNT_BM_RLD BIT1
> +#define B_PCH_ACPI_PM1_CNT_SCI_EN BIT0
> +
> +#define R_PCH_ACPI_PM1_TMR 0x08
> +#define V_PCH_ACPI_TMR_FREQUENCY 3579545
> +#define B_PCH_ACPI_PM1_TMR_VAL 0xFFFFFF
> +#define V_PCH_ACPI_PM1_TMR_MAX_VAL 0x1000000 ///< The
> timer is 24 bit overflow
> +
> +#define R_PCH_SMI_EN 0x30
> +#define S_PCH_SMI_EN 4
> +#define B_PCH_SMI_EN_LEGACY_USB3 BIT31
> +#define B_PCH_SMI_EN_GPIO_UNLOCK_SMI BIT27
> +#define B_PCH_SMI_EN_LEGACY_USB2 BIT17
> +#define B_PCH_SMI_EN_PERIODIC BIT14
> +#define B_PCH_SMI_EN_TCO BIT13
> +#define B_PCH_SMI_EN_MCSMI BIT11
> +#define B_PCH_SMI_EN_BIOS_RLS BIT7
> +#define B_PCH_SMI_EN_SWSMI_TMR BIT6
> +#define B_PCH_SMI_EN_APMC BIT5
> +#define B_PCH_SMI_EN_ON_SLP_EN BIT4
> +#define B_PCH_SMI_EN_LEGACY_USB BIT3
> +#define B_PCH_SMI_EN_BIOS BIT2
> +#define B_PCH_SMI_EN_EOS BIT1
> +#define B_PCH_SMI_EN_GBL_SMI BIT0
> +#define N_PCH_SMI_EN_LEGACY_USB3 31
> +#define N_PCH_SMI_EN_ESPI 28
> +#define N_PCH_SMI_EN_GPIO_UNLOCK 27
> +#define N_PCH_SMI_EN_INTEL_USB2 18
> +#define N_PCH_SMI_EN_LEGACY_USB2 17
> +#define N_PCH_SMI_EN_PERIODIC 14
> +#define N_PCH_SMI_EN_TCO 13
> +#define N_PCH_SMI_EN_MCSMI 11
> +#define N_PCH_SMI_EN_BIOS_RLS 7
> +#define N_PCH_SMI_EN_SWSMI_TMR 6
> +#define N_PCH_SMI_EN_APMC 5
> +#define N_PCH_SMI_EN_ON_SLP_EN 4
> +#define N_PCH_SMI_EN_LEGACY_USB 3
> +#define N_PCH_SMI_EN_BIOS 2
> +#define N_PCH_SMI_EN_EOS 1
> +#define N_PCH_SMI_EN_GBL_SMI 0
> +
> +#define R_PCH_SMI_STS 0x34
> +#define S_PCH_SMI_STS 4
> +#define B_PCH_SMI_STS_LEGACY_USB3 BIT31
> +#define B_PCH_SMI_STS_GPIO_UNLOCK BIT27
> +#define B_PCH_SMI_STS_SPI BIT26
> +#define B_PCH_SMI_STS_MONITOR BIT21
> +#define B_PCH_SMI_STS_PCI_EXP BIT20
> +#define B_PCH_SMI_STS_PATCH BIT19
> +#define B_PCH_SMI_STS_INTEL_USB2 BIT18
> +#define B_PCH_SMI_STS_LEGACY_USB2 BIT17
> +#define B_PCH_SMI_STS_SMBUS BIT16
> +#define B_PCH_SMI_STS_SERIRQ BIT15
> +#define B_PCH_SMI_STS_PERIODIC BIT14
> +#define B_PCH_SMI_STS_TCO BIT13
> +#define B_PCH_SMI_STS_DEVMON BIT12
> +#define B_PCH_SMI_STS_MCSMI BIT11
> +#define B_PCH_SMI_STS_GPIO_SMI BIT10
> +#define B_PCH_SMI_STS_GPE0 BIT9
> +#define B_PCH_SMI_STS_PM1_STS_REG BIT8
> +#define B_PCH_SMI_STS_SWSMI_TMR BIT6
> +#define B_PCH_SMI_STS_APM BIT5
> +#define B_PCH_SMI_STS_ON_SLP_EN BIT4
> +#define B_PCH_SMI_STS_LEGACY_USB BIT3
> +#define B_PCH_SMI_STS_BIOS BIT2
> +#define N_PCH_SMI_STS_LEGACY_USB3 31
> +#define N_PCH_SMI_STS_ESPI 28
> +#define N_PCH_SMI_STS_GPIO_UNLOCK 27
> +#define N_PCH_SMI_STS_SPI 26
> +#define N_PCH_SMI_STS_MONITOR 21
> +#define N_PCH_SMI_STS_PCI_EXP 20
> +#define N_PCH_SMI_STS_PATCH 19
> +#define N_PCH_SMI_STS_INTEL_USB2 18
> +#define N_PCH_SMI_STS_LEGACY_USB2 17
> +#define N_PCH_SMI_STS_SMBUS 16
> +#define N_PCH_SMI_STS_SERIRQ 15
> +#define N_PCH_SMI_STS_PERIODIC 14
> +#define N_PCH_SMI_STS_TCO 13
> +#define N_PCH_SMI_STS_DEVMON 12
> +#define N_PCH_SMI_STS_MCSMI 11
> +#define N_PCH_SMI_STS_GPIO_SMI 10
> +#define N_PCH_SMI_STS_GPE0 9
> +#define N_PCH_SMI_STS_PM1_STS_REG 8
> +#define N_PCH_SMI_STS_SWSMI_TMR 6
> +#define N_PCH_SMI_STS_APM 5
> +#define N_PCH_SMI_STS_ON_SLP_EN 4
> +#define N_PCH_SMI_STS_LEGACY_USB 3
> +#define N_PCH_SMI_STS_BIOS 2
> +
> +#define R_PCH_ACPI_GPE_CNTL 0x40
> +#define B_PCH_ACPI_GPE_CNTL_SWGPE_CTRL BIT17
> +
> +#define R_PCH_DEVACT_STS 0x44
> +#define S_PCH_DEVACT_STS 2
> +#define B_PCH_DEVACT_STS_MASK 0x13E1
> +#define B_PCH_DEVACT_STS_KBC BIT12
> +#define B_PCH_DEVACT_STS_PIRQDH BIT9
> +#define B_PCH_DEVACT_STS_PIRQCG BIT8
> +#define B_PCH_DEVACT_STS_PIRQBF BIT7
> +#define B_PCH_DEVACT_STS_PIRQAE BIT6
> +#define B_PCH_DEVACT_STS_D0_TRP BIT0
> +#define N_PCH_DEVACT_STS_KBC 12
> +#define N_PCH_DEVACT_STS_PIRQDH 9
> +#define N_PCH_DEVACT_STS_PIRQCG 8
> +#define N_PCH_DEVACT_STS_PIRQBF 7
> +#define N_PCH_DEVACT_STS_PIRQAE 6
> +
> +#define R_PCH_ACPI_PM2_CNT 0x50
> +#define B_PCH_ACPI_PM2_CNT_ARB_DIS BIT0
> +
> +#define R_PCH_OC_WDT_CTL 0x54
> +#define B_PCH_OC_WDT_CTL_RLD BIT31
> +#define B_PCH_OC_WDT_CTL_ICCSURV_STS BIT25
> +#define B_PCH_OC_WDT_CTL_NO_ICCSURV_STS BIT24
> +#define B_PCH_OC_WDT_CTL_FORCE_ALL BIT15
> +#define B_PCH_OC_WDT_CTL_EN BIT14
> +#define B_PCH_OC_WDT_CTL_ICCSURV BIT13
> +#define B_PCH_OC_WDT_CTL_LCK BIT12
> +#define B_PCH_OC_WDT_CTL_TOV_MASK 0x3FF
> +#define B_PCH_OC_WDT_CTL_FAILURE_STS BIT23
> +#define B_PCH_OC_WDT_CTL_UNXP_RESET_STS BIT22
> +#define B_PCH_OC_WDT_CTL_AFTER_POST 0x3F0000
> +#define V_PCH_OC_WDT_CTL_STATUS_FAILURE 1
> +#define V_PCH_OC_WDT_CTL_STATUS_OK 0
> +
> +#define R_PCH_ACPI_GPE0_STS_31_0 0x80
> +#define R_PCH_ACPI_GPE0_STS_63_32 0x84
> +#define R_PCH_ACPI_GPE0_STS_95_64 0x88
> +#define R_PCH_ACPI_GPE0_STS_127_96 0x8C
> +#define S_PCH_ACPI_GPE0_STS_127_96 4
> +#define B_PCH_ACPI_GPE0_STS_127_96_WADT BIT18
> +#define B_PCH_ACPI_GPE0_STS_127_96_LAN_WAKE BIT16
> +#define B_PCH_ACPI_GPE0_STS_127_96_PME_B0 BIT13
> +#define B_PCH_ACPI_GPE0_STS_127_96_ME_SCI BIT12
> +#define B_PCH_ACPI_GPE0_STS_127_96_PME BIT11
> +#define B_PCH_ACPI_GPE0_STS_127_96_BATLOW BIT10
> +#define B_PCH_ACPI_GPE0_STS_127_96_PCI_EXP BIT9
> +#define B_PCH_ACPI_GPE0_STS_127_96_RI BIT8
> +#define B_PCH_ACPI_GPE0_STS_127_96_SMB_WAK BIT7
> +#define B_PCH_ACPI_GPE0_STS_127_96_TC0SCI BIT6
> +#define B_PCH_ACPI_GPE0_STS_127_96_SWGPE BIT2
> +#define B_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG BIT1
> +#define N_PCH_ACPI_GPE0_STS_127_96_PME_B0 13
> +#define N_PCH_ACPI_GPE0_STS_127_96_PME 11
> +#define N_PCH_ACPI_GPE0_STS_127_96_BATLOW 10
> +#define N_PCH_ACPI_GPE0_STS_127_96_PCI_EXP 9
> +#define N_PCH_ACPI_GPE0_STS_127_96_RI 8
> +#define N_PCH_ACPI_GPE0_STS_127_96_SMB_WAK 7
> +#define N_PCH_ACPI_GPE0_STS_127_96_TC0SCI 6
> +#define N_PCH_ACPI_GPE0_STS_127_96_SWGPE 2
> +#define N_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG 1
> +
> +#define R_PCH_ACPI_GPE0_EN_31_0 0x90
> +#define R_PCH_ACPI_GPE0_EN_63_32 0x94
> +#define R_PCH_ACPI_GPE0_EN_95_64 0x98
> +#define R_PCH_ACPI_GPE0_EN_127_96 0x9C
> +#define S_PCH_ACPI_GPE0_EN_127_96 4
> +#define B_PCH_ACPI_GPE0_EN_127_96_WADT BIT18
> +#define B_PCH_ACPI_GPE0_EN_127_96_LAN_WAKE BIT16
> +#define B_PCH_ACPI_GPE0_EN_127_96_PME_B0 BIT13
> +#define B_PCH_ACPI_GPE0_EN_127_96_ME_SCI BIT12
> +#define B_PCH_ACPI_GPE0_EN_127_96_PME BIT11
> +#define B_PCH_ACPI_GPE0_EN_127_96_BATLOW BIT10
> +#define B_PCH_ACPI_GPE0_EN_127_96_PCI_EXP BIT9
> +#define B_PCH_ACPI_GPE0_EN_127_96_RI BIT8
> +#define B_PCH_ACPI_GPE0_EN_127_96_TC0SCI BIT6
> +#define B_PCH_ACPI_GPE0_EN_127_96_SWGPE BIT2
> +#define B_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG BIT1
> +#define N_PCH_ACPI_GPE0_EN_127_96_PME_B0 13
> +#define N_PCH_ACPI_GPE0_EN_127_96_USB3 12
> +#define N_PCH_ACPI_GPE0_EN_127_96_PME 11
> +#define N_PCH_ACPI_GPE0_EN_127_96_BATLOW 10
> +#define N_PCH_ACPI_GPE0_EN_127_96_PCI_EXP 9
> +#define N_PCH_ACPI_GPE0_EN_127_96_RI 8
> +#define N_PCH_ACPI_GPE0_EN_127_96_TC0SCI 6
> +#define N_PCH_ACPI_GPE0_EN_127_96_SWGPE 2
> +#define N_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG 1
> +
> +
> +//
> +// TCO register I/O map
> +//
> +#define R_PCH_TCO_RLD 0x0
> +#define R_PCH_TCO_DAT_IN 0x2
> +#define R_PCH_TCO_DAT_OUT 0x3
> +#define R_PCH_TCO1_STS 0x04
> +#define S_PCH_TCO1_STS 2
> +#define B_PCH_TCO1_STS_DMISERR BIT12
> +#define B_PCH_TCO1_STS_DMISMI BIT10
> +#define B_PCH_TCO1_STS_DMISCI BIT9
> +#define B_PCH_TCO1_STS_BIOSWR BIT8
> +#define B_PCH_TCO1_STS_NEWCENTURY BIT7
> +#define B_PCH_TCO1_STS_TIMEOUT BIT3
> +#define B_PCH_TCO1_STS_TCO_INT BIT2
> +#define B_PCH_TCO1_STS_SW_TCO_SMI BIT1
> +#define B_PCH_TCO1_STS_NMI2SMI BIT0
> +#define N_PCH_TCO1_STS_DMISMI 10
> +#define N_PCH_TCO1_STS_BIOSWR 8
> +#define N_PCH_TCO1_STS_NEWCENTURY 7
> +#define N_PCH_TCO1_STS_TIMEOUT 3
> +#define N_PCH_TCO1_STS_SW_TCO_SMI 1
> +#define N_PCH_TCO1_STS_NMI2SMI 0
> +
> +#define R_PCH_TCO2_STS 0x06
> +#define S_PCH_TCO2_STS 2
> +#define B_PCH_TCO2_STS_SMLINK_SLV_SMI BIT4
> +#define B_PCH_TCO2_STS_BAD_BIOS BIT3
> +#define B_PCH_TCO2_STS_BOOT BIT2
> +#define B_PCH_TCO2_STS_SECOND_TO BIT1
> +#define B_PCH_TCO2_STS_INTRD_DET BIT0
> +#define N_PCH_TCO2_STS_INTRD_DET 0
> +
> +#define R_PCH_TCO1_CNT 0x08
> +#define S_PCH_TCO1_CNT 2
> +#define B_PCH_TCO_CNT_LOCK BIT12
> +#define B_PCH_TCO_CNT_TMR_HLT BIT11
> +#define B_PCH_TCO_CNT_NMI2SMI_EN BIT9
> +#define B_PCH_TCO_CNT_NMI_NOW BIT8
> +#define N_PCH_TCO_CNT_NMI2SMI_EN 9
> +
> +#define R_PCH_TCO2_CNT 0x0A
> +#define S_PCH_TCO2_CNT 2
> +#define B_PCH_TCO2_CNT_OS_POLICY 0x0030
> +#define B_PCH_TCO2_CNT_GPI11_ALERT_DISABLE 0x0008
> +#define B_PCH_TCO2_CNT_INTRD_SEL 0x0006
> +#define N_PCH_TCO2_CNT_INTRD_SEL 2
> +
> +#define R_PCH_TCO_MESSAGE1 0x0C
> +#define R_PCH_TCO_MESSAGE2 0x0D
> +#define R_PCH_TCO_WDCNT 0x0E
> +#define R_PCH_TCO_SW_IRQ_GEN 0x10
> +#define B_PCH_TCO_IRQ12_CAUSE BIT1
> +#define B_PCH_TCO_IRQ1_CAUSE BIT0
> +#define R_PCH_TCO_TMR 0x12
> +
> +//
> +// PWRM Registers
> +//
> +#define R_PCH_WADT_AC 0x0 ///< Wake
> Alarm Device Timer: AC
> +#define R_PCH_WADT_DC 0x4 ///< Wake
> Alarm Device Timer: DC
> +#define R_PCH_WADT_EXP_AC 0x8 ///< Wake
> Alarm Device Expired Timer: AC
> +#define R_PCH_WADT_EXP_DC 0xC ///< Wake
> Alarm Device Expired Timer: DC
> +#define R_PCH_PWRM_PRSTS 0x10 ///< Power
> and Reset Status
> +#define B_PCH_PWRM_PRSTS_VE_WD_TMR_STS BIT7
> ///< VE Watchdog Timer Status
> +#define B_PCH_PWRM_PRSTS_WOL_OVR_WK_STS BIT5
> +#define B_PCH_PWRM_PRSTS_FIELD_1 BIT4
> +#define B_PCH_PWRM_PRSTS_ME_WAKE_STS BIT0
> +#define R_PCH_PWRM_14 0x14
> +#define R_PCH_PWRM_CFG 0x18 ///< Power
> Management Configuration
> +#define B_PCH_PWRM_CFG_ALLOW_24_OSC_SD BIT29
> ///< Allow 24MHz Crystal Oscillator Shutdown
> +#define B_PCH_PWRM_CFG_ALLOW_USB2_CORE_PG BIT25
> ///< Allow USB2 Core Power Gating
> +#define B_PCH_PWRM_CFG_RTC_DS_WAKE_DIS BIT21
> ///< RTC Wake from Deep S4/S5 Disable
> +#define B_PCH_PWRM_CFG_SSMAW_MASK (BIT19 | BIT18)
> ///< SLP_SUS# Min Assertion Width
> +#define V_PCH_PWRM_CFG_SSMAW_4S (BIT19 | BIT18)
> ///< 4 seconds
> +#define V_PCH_PWRM_CFG_SSMAW_1S BIT19
> ///< 1 second
> +#define V_PCH_PWRM_CFG_SSMAW_0_5S BIT18
> ///< 0.5 second (500ms)
> +#define V_PCH_PWRM_CFG_SSMAW_0S 0 ///< 0
> second
> +#define B_PCH_PWRM_CFG_SAMAW_MASK (BIT17 | BIT16)
> ///< SLP_A# Min Assertion Width
> +#define V_PCH_PWRM_CFG_SAMAW_2S (BIT17 | BIT16)
> ///< 2 seconds
> +#define V_PCH_PWRM_CFG_SAMAW_98ms BIT17
> ///< 98ms
> +#define V_PCH_PWRM_CFG_SAMAW_4S BIT16
> ///< 4 seconds
> +#define V_PCH_PWRM_CFG_SAMAW_0S 0 ///< 0
> second
> +#define B_PCH_PWRM_CFG_RPCD_MASK (BIT9 | BIT8)
> ///< Reset Power Cycle Duration
> +#define V_PCH_PWRM_CFG_RPCD_1S (BIT9 | BIT8)
> ///< 1-2 seconds
> +#define V_PCH_PWRM_CFG_RPCD_2S BIT9 ///< 2-
> 3 seconds
> +#define V_PCH_PWRM_CFG_RPCD_3S BIT8 ///< 3-
> 4 seconds
> +#define V_PCH_PWRM_CFG_RPCD_4S 0 ///< 4-5
> seconds (Default)
> +#define R_PCH_PWRM_PCH_PM_STS 0x1C ///<
> Contains misc. fields used to record PCH power management events
> +#define B_PCH_PWRM_PCH_PM_STS_PMC_MSG_FULL_STS BIT24
> ///< MTPMC transport mechanism full indication
> +#define R_PCH_PWRM_MTPMC 0x20 ///<
> Message to PMC
> +#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_0_15 0xE
> ///< Command to override lanes 0-15 power gating
> +#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_16_31 0xF
> ///< Command to override lanes 16-31 power gating
> +#define B_PCH_PWRM_MTPMC_PG_CMD_DATA 0xFFFF0000
> ///< Data part of PowerGate Message to PMC
> +#define N_PCH_PWRM_MTPMC_PG_CMD_DATA 16
> +#define R_PCH_PWRM_PCH_PM_STS2 0x24 ///<
> PCH Power Management Status
> +#define R_PCH_PWRM_S3_PWRGATE_POL 0x28
> ///< S3 Power Gating Policies
> +#define B_PCH_PWRM_S3DC_GATE_SUS BIT1 ///<
> Deep S3 Enable in DC Mode
> +#define B_PCH_PWRM_S3AC_GATE_SUS BIT0 ///<
> Deep S3 Enable in AC Mode
> +#define R_PCH_PWRM_S4_PWRGATE_POL 0x2C
> ///< Deep S4 Power Policies
> +#define B_PCH_PWRM_S4DC_GATE_SUS BIT1 ///<
> Deep S4 Enable in DC Mode
> +#define B_PCH_PWRM_S4AC_GATE_SUS BIT0 ///<
> Deep S4 Enable in AC Mode
> +#define R_PCH_PWRM_S5_PWRGATE_POL 0x30
> ///< Deep S5 Power Policies
> +#define B_PCH_PWRM_S5DC_GATE_SUS BIT15 ///<
> Deep S5 Enable in DC Mode
> +#define B_PCH_PWRM_S5AC_GATE_SUS BIT14 ///<
> Deep S5 Enable in AC Mode
> +#define R_PCH_PWRM_DSX_CFG 0x34 ///<
> Deep SX Configuration
> +#define B_PCH_PWRM_DSX_CFG_WAKE_PIN_DSX_EN BIT2
> ///< WAKE# Pin DeepSx Enable
> +#define B_PCH_PWRM_DSX_CFG_ACPRES_PD_DSX_DIS BIT1
> ///< AC_PRESENT pin pulldown in DeepSx disable
> +#define B_PCH_PWRM_DSX_CFG_LAN_WAKE_EN BIT0
> ///< LAN_WAKE Pin DeepSx Enable
> +#define R_PCH_PWRM_CFG2 0x3C ///< Power
> Management Configuration Reg 2
> +#define B_PCH_PWRM_CFG2_PBOP (BIT31 | BIT30 | BIT29)
> ///< Power Button Override Period (PBOP)
> +#define N_PCH_PWRM_CFG2_PBOP 29 ///<
> Power Button Override Period (PBOP)
> +#define B_PCH_PWRM_CFG2_PB_DIS BIT28 ///<
> Power Button Native Mode Disable (PB_DIS)
> +#define B_PCH_PWRM_CFG2_DRAM_RESET_CTL BIT26
> ///< DRAM RESET# control
> +#define R_PCH_PWRM_EN_SN_SLOW_RING 0x48
> ///< Enable Snoop Request to SLOW_RING
> +#define R_PCH_PWRM_EN_SN_SLOW_RING2 0x4C
> ///< Enable Snoop Request to SLOW_RING 2nd Reg
> +#define R_PCH_PWRM_EN_SN_SA 0x50 ///<
> Enable Snoop Request to SA
> +#define R_PCH_PWRM_EN_SN_SA2 0x54 ///<
> Enable Snoop Request to SA 2nd Reg
> +#define R_PCH_PWRM_EN_SN_SLOW_RING_CF 0x58
> ///< Enable Snoop Request to SLOW_RING_CF
> +#define R_PCH_PWRM_EN_NS_SA 0x68 ///<
> Enable Non-Snoop Request to SA
> +#define R_PCH_PWRM_EN_CW_SLOW_RING 0x80
> ///< Enable Clock Wake to SLOW_RING
> +#define R_PCH_PWRM_EN_CW_SLOW_RING2 0x84
> ///< Enable Clock Wake to SLOW_RING 2nd Reg
> +#define R_PCH_PWRM_EN_CW_SA 0x88 ///<
> Enable Clock Wake to SA
> +#define R_PCH_PWRM_EN_CW_SA2 0x8C ///<
> Enable Clock Wake to SA 2nd Reg
> +#define R_PCH_PWRM_EN_CW_SLOW_RING_CF 0x98
> ///< Enable Clock Wake to SLOW_RING_CF
> +#define R_PCH_PWRM_EN_PA_SLOW_RING 0xA8
> ///< Enable Pegged Active to SLOW_RING
> +#define R_PCH_PWRM_EN_PA_SLOW_RING2 0xAC
> ///< Enable Pegged Active to SLOW_RING 2nd Reg
> +#define R_PCH_PWRM_EN_PA_SA 0xB0 ///<
> Enable Pegged Active to SA
> +#define R_PCH_PWRM_EN_PA_SA2 0xB4 ///<
> Enable Pegged Active to SA 2nd Reg
> +#define R_PCH_PWRM_EN_MISC_EVENT 0xC0 ///<
> Enable Misc PM_SYNC Events
> +#define R_PCH_PWRM_PMSYNC_TPR_CONFIG 0xC4
> +#define B_PCH_PWRM_PMSYNC_TPR_CONFIG_LOCK BIT31
> +#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_EN BIT26
> +#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE (BIT25 |
> BIT24)
> +#define N_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE 24
> +#define V_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE_1 1
> +#define R_PCH_PWRM_PMSYNC_MISC_CFG 0xC8
> +#define B_PCH_PWRM_PMSYNC_PM_SYNC_LOCK BIT15
> ///< PM_SYNC Configuration Lock
> +#define B_PCH_PWRM_PMSYNC_GPIO_D_SEL BIT11
> +#define B_PCH_PWRM_PMSYNC_GPIO_C_SEL BIT10
> +#define R_PCH_PWRM_PM_SYNC_STATE_HYS 0xD0
> ///< PM_SYNC State Hysteresis
> +#define R_PCH_PWRM_PM_SYNC_MODE 0xD4
> ///< PM_SYNC Pin Mode
> +#define R_PCH_PWRM_CFG3 0xE0 ///< Power
> Management Configuration Reg 3
> +#define B_PCH_PWRM_CFG3_DSX_WLAN_PP_EN BIT16
> ///< Deep-Sx WLAN Phy Power Enable
> +#define B_PCH_PWRM_CFG3_HOST_WLAN_PP_EN BIT17
> ///< Host Wireless LAN Phy Power Enable
> +#define B_PCH_PWRM_CFG3_PWRG_LOCK BIT2
> ///< Lock power gating override messages
> +#define R_PCH_PWRM_PM_DOWN_PPB_CFG 0xE4
> ///< PM_DOWN PCH_POWER_BUDGET CONFIGURATION
> +#define R_PCH_PWRM_CFG4 0xE8 ///< Power
> Management Configuration Reg 4
> +#define B_PCH_PWRM_CFG4_U2_PHY_PG_EN BIT30
> ///< USB2 PHY SUS Well Power Gating Enable
> +#define B_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR
> (0x000001FF) ///< CPU I/O VR Ramp Duration, [8:0]
> +#define N_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR 0
> +#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_70US 0x007
> +#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_240US 0x018
> +#define R_PCH_PWRM_CPU_EPOC 0xEC
> +#define R_PCH_PWRM_VR_MISC_CTL 0x100
> +#define B_PCH_PWRM_VR_MISC_CTL_VIDSOVEN BIT3
> +#define R_PCH_PWRM_GPIO_CFG 0x120
> +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW2 (BIT11 | BIT10 |
> BIT9 | BIT8)
> +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW2 8
> +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW1 (BIT7 | BIT6 |
> BIT5 | BIT4)
> +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW1 4
> +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW0 (BIT3 | BIT2 |
> BIT1 | BIT0)
> +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW0 0
> +#define R_PCH_PWRM_PM_SYNC_MODE_C0 0xF4
> ///< PM_SYNC Pin Mode in C0
> +#define R_PCH_PWRM_ACPI_TMR_CTL 0xFC
> +#define B_PCH_PWRM_ACPI_TMR_DIS BIT1
> +#define R_PCH_PWRM_124 0x124
> +#define R_PCH_PWRM_SLP_S0_RESIDENCY_COUNTER 0x13C
> +#define R_PCH_PWRM_MODPHY_PM_CFG1 0x200
> +#define R_PCH_PWRM_MODPHY_PM_CFG1_MLSXSWPGP 0xFFFF
> +#define R_PCH_PWRM_MODPHY_PM_CFG2 0x204 ///<
> ModPHY Power Management Configuration Reg 2
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_MLSPDDGE BIT30
> ///< ModPHY Lane SUS Power Domain Dynamic Gating Enable
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_EMFC BIT29 ///<
> Enable ModPHY FET Control
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_EFRT (BIT28 | BIT27
> | BIT26 | BIT25 | BIT24) ///< External FET Ramp Time
> +#define N_PCH_PWRM_MODPHY_PM_CFG2_EFRT 24
> +#define V_PCH_PWRM_MODPHY_PM_CFG2_EFRT_200US 0x0A
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_ASLOR_UFS BIT16
> ///< UFS ModPHY SPD SPD Override
> +#define R_PCH_PWRM_MODPHY_PM_CFG3 0x208 ///<
> ModPHY Power Management Configuration Reg 3
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_UFS BIT16
> ///< UFS ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XDCI BIT15
> ///< xDCI ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XHCI BIT14
> ///< xHCI ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_GBE BIT13
> ///< GbE ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_SATA BIT12
> ///< SATA ModPHY SPD RT Request
> +#define R_PCH_PWRM_30C 0x30C
> +#define R_PCH_PWRM_OBFF_CFG 0x314 ///< OBFF
> Configuration
> +#define R_PCH_PWRM_31C 0x31C
> +#define R_PCH_PWRM_CPPM_MISC_CFG 0x320 ///<
> CPPM Miscellaneous Configuration
> +#define R_PCH_PWRM_CPPM_CG_POL1A 0x324 ///<
> CPPM Clock Gating Policy Reg 1
> +#define R_PCH_PWRM_CPPM_CG_POL2A 0x340 ///<
> CPPM Clock Gating Policy Reg 3
> +#define R_PCH_PWRM_34C 0x34C
> +#define R_PCH_PWRM_CPPM_CG_POL3A 0x3A8 ///<
> CPPM Clock Gating Policy Reg 5
> +#define B_PCH_PWRM_CPPM_CG_POLXA_CPPM_GX_QUAL BIT30
> ///< CPPM Shutdown Qualifier Enable for Clock Source Group X
> +#define B_PCH_PWRM_CPPM_CG_POLXA_LTR_GX_THRESH
> (0x000001FF) ///< LTR Threshold for Clock Source Group X, [8:0]
> +#define R_PCH_PWRM_3D0 0x3D0
> +#define R_PCH_PWRM_CPPM_MPG_POL1A 0x3E0 ///<
> CPPM ModPHY Gating Policy Reg 1A
> +#define B_PCH_PWRM_CPPM_MPG_POL1A_CPPM_MODPHY_QUAL
> BIT30 ///< CPPM Shutdown Qualifier Enable for ModPHY
> +#define B_PCH_PWRM_CPPM_MPG_POL1A_LT_MODPHY_SEL BIT29
> ///< ASLT/PLT Selection for ModPHY
> +#define B_PCH_PWRM_CPPM_MPG_POL1A_LTR_MODPHY_THRESH
> (0x000001FF) ///< LTR Threshold for ModPHY, [8:0]
> +#define R_PCH_PWRM_CS_SD_CTL1 0x3E8 ///< Clock
> Source Shutdown Control Reg 1
> +#define B_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG (BIT22 | BIT21 |
> BIT20) ///< Clock Source 5 Control Configuration
> +#define N_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG 20
> +#define B_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG (BIT2 | BIT1 |
> BIT0) ///< Clock Source 1 Control Configuration
> +#define N_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG 0
> +#define R_PCH_PWRM_CS_SD_CTL2 0x3EC ///< Clock
> Source Shutdown Control Reg 2
> +#define R_PCH_PWRM_HSWPGCR1 0x5D0
> +#define B_PCH_PWRM_SW_PG_CTRL_LOCK BIT31
> +#define B_PCH_PWRM_DFX_SW_PG_CTRL BIT0
> +#define R_PCH_PWRM_600 0x600
> +#define R_PCH_PWRM_604 0x604
> +#define R_PCH_PWRM_ST_PG_FDIS_PMC_1 0x620 ///< Static
> PG Related Function Disable Register 1
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ST_FDIS_LK BIT31 ///<
> Static Function Disable Lock (ST_FDIS_LK)
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_CAM_FDIS_PMC BIT6
> ///< Camera Function Disable (PMC Version) (CAM_FDIS_PMC)
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ISH_FDIS_PMC BIT5 ///<
> SH Function Disable (PMC Version) (ISH_FDIS_PMC)
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_GBE_FDIS_PMC BIT0 ///<
> GBE Function Disable (PMC Version) (GBE_FDIS_PMC)
> +#define R_PCH_PWRM_ST_PG_FDIS_PMC_2 0x624 ///< Static
> Function Disable Control Register 2
> +#define V_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_FDIS_PMC 0x7FF
> ///< Static Function Disable Control Register 2
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI1_FDIS_PMC
> BIT10 ///< SerialIo Controller GSPI Device 1 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI0_FDIS_PMC
> BIT9 ///< SerialIo Controller GSPI Device 0 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART2_FDIS_PMC
> BIT8 ///< SerialIo Controller UART Device 2 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART1_FDIS_PMC
> BIT7 ///< SerialIo Controller UART Device 1 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART0_FDIS_PMC
> BIT6 ///< SerialIo Controller UART Device 0 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C5_FDIS_PMC
> BIT5 ///< SerialIo Controller I2C Device 5 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C4_FDIS_PMC
> BIT4 ///< SerialIo Controller I2C Device 4 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C3_FDIS_PMC
> BIT3 ///< SerialIo Controller I2C Device 3 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C2_FDIS_PMC
> BIT2 ///< SerialIo Controller I2C Device 2 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C1_FDIS_PMC
> BIT1 ///< SerialIo Controller I2C Device 1 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C0_FDIS_PMC
> BIT0 ///< SerialIo Controller I2C Device 0 Function Disable
> +#define R_PCH_PWRM_NST_PG_FDIS_1 0x628
> +#define B_PCH_PWRM_NST_PG_FDIS_1_SCC_FDIS_PMC BIT25 ///<
> SCC Function Disable. This is only avaiable in B0 onward.
> +#define B_PCH_PWRM_NST_PG_FDIS_1_XDCI_FDIS_PMC BIT24 ///<
> XDCI Function Disable. This is only avaiable in B0 onward.
> +#define B_PCH_PWRM_NST_PG_FDIS_1_ADSP_FDIS_PMC BIT23 ///<
> ADSP Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_SATA_FDIS_PMC BIT22 ///<
> SATA Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C3_FDIS_PMC BIT13 ///<
> PCIe Controller C Port 3 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C2_FDIS_PMC BIT12 ///<
> PCIe Controller C Port 2 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C1_FDIS_PMC BIT11 ///<
> PCIe Controller C Port 1 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C0_FDIS_PMC BIT10 ///<
> PCIe Controller C Port 0 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B3_FDIS_PMC BIT9 ///<
> PCIe Controller B Port 3 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B2_FDIS_PMC BIT8 ///<
> PCIe Controller B Port 2 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B1_FDIS_PMC BIT7 ///<
> PCIe Controller B Port 1 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B0_FDIS_PMC BIT6 ///<
> PCIe Controller B Port 0 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A3_FDIS_PMC BIT5 ///<
> PCIe Controller A Port 3 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A2_FDIS_PMC BIT4 ///<
> PCIe Controller A Port 2 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A1_FDIS_PMC BIT3 ///<
> PCIe Controller A Port 1 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A0_FDIS_PMC BIT2 ///<
> PCIe Controller A Port 0 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_XHCI_FDIS_PMC BIT0 ///<
> XHCI Function Disable
> +#define R_PCH_PWRM_FUSE_DIS_RD_1 0x640 ///< Fuse
> Disable Read 1 Register
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E3_FUSE_DIS BIT21 ///<
> PCIe Controller E Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E2_FUSE_DIS BIT20 ///<
> PCIe Controller E Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E1_FUSE_DIS BIT19 ///<
> PCIe Controller E Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E0_FUSE_DIS BIT18 ///<
> PCIe Controller E Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D3_FUSE_DIS BIT17 ///<
> PCIe Controller D Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D2_FUSE_DIS BIT16 ///<
> PCIe Controller D Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D1_FUSE_DIS BIT15 ///<
> PCIe Controller D Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D0_FUSE_DIS BIT14 ///<
> PCIe Controller D Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C3_FUSE_DIS BIT13 ///<
> PCIe Controller C Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C2_FUSE_DIS BIT12 ///<
> PCIe Controller C Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C1_FUSE_DIS BIT11 ///<
> PCIe Controller C Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C0_FUSE_DIS BIT10 ///<
> PCIe Controller C Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B3_FUSE_DIS BIT9 ///<
> PCIe Controller B Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B2_FUSE_DIS BIT8 ///<
> PCIe Controller B Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B1_FUSE_DIS BIT7 ///<
> PCIe Controller B Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B0_FUSE_DIS BIT6 ///<
> PCIe Controller B Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A3_FUSE_DIS BIT5 ///<
> PCIe Controller A Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A2_FUSE_DIS BIT4 ///<
> PCIe Controller A Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A1_FUSE_DIS BIT3 ///<
> PCIe Controller A Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A0_FUSE_DIS BIT2 ///<
> PCIe Controller A Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_XHCI_FUSE_DIS BIT0 ///<
> XHCI Fuse Disable
> +#define R_PCH_PWRM_FUSE_DIS_RD_2 0x644 ///< Fuse
> Disable Read 2 Register
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPC_SS_DIS BIT25 ///< SPC
> Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPB_SS_DIS BIT24 ///< SPB
> Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPA_SS_DIS BIT23 ///< SPA
> Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_PSTH_FUSE_SS_DIS BIT21 ///<
> PSTH Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_DMI_FUSE_SS_DIS BIT20 ///<
> DMI Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_OTG_FUSE_SS_DIS BIT19 ///<
> OTG Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_XHCI_SS_DIS BIT18 ///<
> XHCI Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_FIA_FUSE_SS_DIS BIT17 ///<
> FIA Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_DSP_FUSE_SS_DIS BIT16 ///<
> DSP Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SATA_FUSE_SS_DIS BIT15 ///<
> SATA Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_ICC_FUSE_SS_DIS BIT14 ///<
> ICC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_LPC_FUSE_SS_DIS BIT13 ///<
> LPC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_RTC_FUSE_SS_DIS BIT12 ///<
> RTC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_P2S_FUSE_SS_DIS BIT11 ///<
> P2S Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_TRSB_FUSE_SS_DIS BIT10 ///<
> TRSB Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SMB_FUSE_SS_DIS BIT9 ///<
> SMB Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_ITSS_FUSE_SS_DIS BIT8 ///<
> ITSS Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SERIALIO_FUSE_SS_DIS BIT6
> ///< SerialIo Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SCC_FUSE_SS_DIS BIT4 ///<
> SCC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_P2D_FUSE_SS_DIS BIT3 ///<
> P2D Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_CAM_FUSE_SS_DIS BIT2 ///<
> Camera Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_ISH_FUSE_SS_DIS BIT1 ///<
> ISH Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_GBE_FUSE_SS_DIS BIT0 ///<
> GBE Fuse or Soft Strap Disable
> +#define R_PCH_PWRM_FUSE_DIS_RD_3 0x648 ///< Static PG
> Fuse and Soft Strap Disable Read Register 3
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA3_FUSE_SS_DIS BIT3
> ///< PNCRA3 Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA2_FUSE_SS_DIS BIT2
> ///< PNCRA2 Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA1_FUSE_SS_DIS BIT1
> ///< PNCRA1 Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA_FUSE_SS_DIS BIT0
> ///< PNCRA Fuse or Soft Strap Disable
> +
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> new file mode 100644
> index 0000000000..a727aae927
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> @@ -0,0 +1,304 @@
> +/** @file
> + Register names for PCH SPI device.
> +
> + Conventions:
> +
> + - Prefixes:
> + Definitions beginning with "R_" are registers
> + Definitions beginning with "B_" are bits within registers
> + Definitions beginning with "V_" are meaningful values within the bits
> + Definitions beginning with "S_" are register sizes
> + Definitions beginning with "N_" are the bit position
> + - In general, PCH registers are denoted by "_PCH_" in register names
> + - Registers / bits that are different between PCH generations are denoted by
> + "_PCH_[generation_name]_" in register/bit names.
> + - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit
> names.
> + Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit
> names.
> + e.g., "_PCH_H_", "_PCH_LP_"
> + Registers / bits names without _H_ or _LP_ apply for both H and LP.
> + - Registers / bits that are different between SKUs are denoted by
> "_[SKU_name]"
> + at the end of the register/bit names
> + - Registers / bits of new devices introduced in a PCH generation will be just
> named
> + as "_PCH_" without [generation_name] inserted.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_REGS_SPI_H_
> +#define _PCH_REGS_SPI_H_
> +
> +//
> +// SPI Registers (D31:F5)
> +//
> +
> +#define PCI_DEVICE_NUMBER_PCH_SPI 31
> +#define PCI_FUNCTION_NUMBER_PCH_SPI 5
> +
> +#define R_PCH_SPI_BAR0 0x10
> +#define B_PCH_SPI_BAR0_MASK 0x0FFF
> +
> +#define R_PCH_SPI_BDE 0xD8
> +#define B_PCH_SPI_BDE_F8 0x8000
> +#define B_PCH_SPI_BDE_F0 0x4000
> +#define B_PCH_SPI_BDE_E8 0x2000
> +#define B_PCH_SPI_BDE_E0 0x1000
> +#define B_PCH_SPI_BDE_D8 0x0800
> +#define B_PCH_SPI_BDE_D0 0x0400
> +#define B_PCH_SPI_BDE_C8 0x0200
> +#define B_PCH_SPI_BDE_C0 0x0100
> +#define B_PCH_SPI_BDE_LEG_F 0x0080
> +#define B_PCH_SPI_BDE_LEG_E 0x0040
> +#define B_PCH_SPI_BDE_70 0x0008
> +#define B_PCH_SPI_BDE_60 0x0004
> +#define B_PCH_SPI_BDE_50 0x0002
> +#define B_PCH_SPI_BDE_40 0x0001
> +
> +#define R_PCH_SPI_BC 0xDC
> +#define S_PCH_SPI_BC 4
> +#define N_PCH_SPI_BC_ASE_BWP 11
> +#define B_PCH_SPI_BC_ASE_BWP BIT11
> +#define N_PCH_SPI_BC_ASYNC_SS 10
> +#define B_PCH_SPI_BC_ASYNC_SS BIT10
> +#define B_PCH_SPI_BC_OSFH BIT9 ///< OS Function Hide
> +#define N_PCH_SPI_BC_SYNC_SS 8
> +#define B_PCH_SPI_BC_SYNC_SS BIT8
> +#define B_PCH_SPI_BC_BILD BIT7
> +#define B_PCH_SPI_BC_BBS BIT6 ///< Boot BIOS strap
> +#define N_PCH_SPI_BC_BBS 6
> +#define V_PCH_SPI_BC_BBS_SPI 0 ///< Boot BIOS strapped to
> SPI
> +#define V_PCH_SPI_BC_BBS_LPC 1 ///< Boot BIOS strapped to
> LPC
> +#define B_PCH_SPI_BC_EISS BIT5 ///< Enable InSMM.STS
> +#define B_PCH_SPI_BC_TSS BIT4
> +#define B_PCH_SPI_BC_SRC (BIT3 | BIT2)
> +#define N_PCH_SPI_BC_SRC 2
> +#define V_PCH_SPI_BC_SRC_PREF_EN_CACHE_EN 0x02 ///<
> Prefetching and Caching enabled
> +#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_DIS 0x01 ///< No
> prefetching and no caching
> +#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_EN 0x00 ///< No
> prefetching, but caching enabled
> +#define B_PCH_SPI_BC_LE BIT1 ///< Lock Enable
> +#define N_PCH_SPI_BC_BLE 1
> +#define B_PCH_SPI_BC_WPD BIT0 ///< Write Protect Disable
> +
> +//
> +// BIOS Flash Program Registers (based on SPI_BAR0)
> +//
> +#define R_PCH_SPI_BFPR 0x00 ///< BIOS Flash
> Primary Region Register(32bits), which is RO and contains the same value from
> FREG1
> +#define B_PCH_SPI_BFPR_PRL 0x7FFF0000 ///< BIOS Flash
> Primary Region Limit mask
> +#define N_PCH_SPI_BFPR_PRL 16 ///< BIOS Flash
> Primary Region Limit bit position
> +#define B_PCH_SPI_BFPR_PRB 0x00007FFF ///< BIOS Flash
> Primary Region Base mask
> +#define N_PCH_SPI_BFPR_PRB 0 ///< BIOS Flash
> Primary Region Base bit position
> +#define R_PCH_SPI_HSFSC 0x04 ///< Hardware
> Sequencing Flash Status and Control Register(32bits)
> +#define B_PCH_SPI_HSFSC_FSMIE BIT31 ///< Flash SPI
> SMI# Enable
> +#define B_PCH_SPI_HSFSC_FDBC_MASK 0x3F000000 ///<
> Flash Data Byte Count ( <= 64), Count = (Value in this field) + 1.
> +#define N_PCH_SPI_HSFSC_FDBC 24
> +#define B_PCH_SPI_HSFSC_CYCLE_MASK 0x001E0000 ///<
> Flash Cycle.
> +#define N_PCH_SPI_HSFSC_CYCLE 17
> +#define V_PCH_SPI_HSFSC_CYCLE_READ 0 ///< Flash Cycle
> Read
> +#define V_PCH_SPI_HSFSC_CYCLE_WRITE 2 ///< Flash
> Cycle Write
> +#define V_PCH_SPI_HSFSC_CYCLE_4K_ERASE 3 ///< Flash
> Cycle 4K Block Erase
> +#define V_PCH_SPI_HSFSC_CYCLE_64K_ERASE 4 ///< Flash
> Cycle 64K Sector Erase
> +#define V_PCH_SPI_HSFSC_CYCLE_READ_SFDP 5 ///< Flash
> Cycle Read SFDP
> +#define V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID 6 ///<
> Flash Cycle Read JEDEC ID
> +#define V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS 7 ///< Flash
> Cycle Write Status
> +#define V_PCH_SPI_HSFSC_CYCLE_READ_STATUS 8 ///< Flash
> Cycle Read Status
> +#define B_PCH_SPI_HSFSC_CYCLE_FGO BIT16 ///< Flash
> Cycle Go.
> +#define B_PCH_SPI_HSFSC_FLOCKDN BIT15 ///< Flash
> Configuration Lock-Down
> +#define B_PCH_SPI_HSFSC_FDV BIT14 ///< Flash
> Descriptor Valid, once valid software can use hareware sequencing regs
> +#define B_PCH_SPI_HSFSC_FDOPSS BIT13 ///< Flash
> Descriptor Override Pin-Strap Status
> +#define B_PCH_SPI_HSFSC_PRR34_LOCKDN BIT12 ///< PRR3
> PRR4 Lock-Down
> +#define B_PCH_SPI_HSFSC_SAF_CE BIT8 ///< SAF ctype
> error
> +#define B_PCH_SPI_HSFSC_SAF_MODE_ACTIVE BIT7 ///<
> Indicates flash is attached either directly to the PCH via the SPI bus or EC/BMC
> +#define B_PCH_SPI_HSFSC_SAF_LE BIT6 ///< SAF link
> error
> +#define B_PCH_SPI_HSFSC_SCIP BIT5 ///< SPI cycle in
> progress
> +#define B_PCH_SPI_HSFSC_SAF_DLE BIT4 ///< SAF Data
> length error
> +#define B_PCH_SPI_HSFSC_SAF_ERROR BIT3 ///< SAF Error
> +#define B_PCH_SPI_HSFSC_AEL BIT2 ///< Access Error
> Log
> +#define B_PCH_SPI_HSFSC_FCERR BIT1 ///< Flash Cycle
> Error
> +#define B_PCH_SPI_HSFSC_FDONE BIT0 ///< Flash Cycle
> Done
> +#define R_PCH_SPI_FADDR 0x08 ///< SPI Flash
> Address
> +#define B_PCH_SPI_FADDR_MASK 0x01FFFFFF ///< SPI
> Flash Address Mask (0~24bit)
> +#define R_PCH_SPI_DLOCK 0x0C ///< Discrete Lock
> Bits
> +#define B_PCH_SPI_DLOCK_PR0LOCKDN BIT8 ///<
> PR0LOCKDN
> +#define R_PCH_SPI_FDATA00 0x10 ///< SPI Data 00 (32
> bits)
> +#define R_PCH_SPI_FDATA01 0x14 ///< SPI Data 01
> +#define R_PCH_SPI_FDATA02 0x18 ///< SPI Data 02
> +#define R_PCH_SPI_FDATA03 0x1C ///< SPI Data 03
> +#define R_PCH_SPI_FDATA04 0x20 ///< SPI Data 04
> +#define R_PCH_SPI_FDATA05 0x24 ///< SPI Data 05
> +#define R_PCH_SPI_FDATA06 0x28 ///< SPI Data 06
> +#define R_PCH_SPI_FDATA07 0x2C ///< SPI Data 07
> +#define R_PCH_SPI_FDATA08 0x30 ///< SPI Data 08
> +#define R_PCH_SPI_FDATA09 0x34 ///< SPI Data 09
> +#define R_PCH_SPI_FDATA10 0x38 ///< SPI Data 10
> +#define R_PCH_SPI_FDATA11 0x3C ///< SPI Data 11
> +#define R_PCH_SPI_FDATA12 0x40 ///< SPI Data 12
> +#define R_PCH_SPI_FDATA13 0x44 ///< SPI Data 13
> +#define R_PCH_SPI_FDATA14 0x48 ///< SPI Data 14
> +#define R_PCH_SPI_FDATA15 0x4C ///< SPI Data 15
> +#define R_PCH_SPI_FRAP 0x50 ///< Flash Region
> Access Permisions Register
> +#define B_PCH_SPI_FRAP_BRWA_MASK 0x0000FF00 ///<
> BIOS Region Write Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2:
> ME; 3: GbE; 4: PlatformData
> +#define N_PCH_SPI_FRAP_BRWA 8 ///< BIOS Region
> Write Access bit position
> +#define B_PCH_SPI_FRAP_BRRA_MASK 0x000000FF ///< BIOS
> Region Read Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3:
> GbE; 4: PlatformData
> +#define B_PCH_SPI_FRAP_BMRAG_MASK 0x00FF0000 ///<
> BIOS Master Read Access Grant
> +#define B_PCH_SPI_FRAP_BMWAG_MASK 0xFF000000 ///<
> BIOS Master Write Access Grant
> +#define R_PCH_SPI_FREG0_FLASHD 0x54 ///< Flash
> Region 0(Flash Descriptor)(32bits)
> +#define R_PCH_SPI_FREG1_BIOS 0x58 ///< Flash Region
> 1(BIOS)(32bits)
> +#define R_PCH_SPI_FREG2_ME 0x5C ///< Flash Region
> 2(ME)(32bits)
> +#define R_PCH_SPI_FREG3_GBE 0x60 ///< Flash Region
> 3(GbE)(32bits)
> +#define R_PCH_SPI_FREG4_PLATFORM_DATA 0x64 ///< Flash
> Region 4(Platform Data)(32bits)
> +#define R_PCH_SPI_FREG5_DER 0x68 ///< Flash Region
> 5(Device Expansion Region)(32bits)
> +#define S_PCH_SPI_FREGX 4 ///< Size of Flash Region
> register
> +#define B_PCH_SPI_FREGX_LIMIT_MASK 0x7FFF0000 ///<
> Flash Region Limit [30:16] represents [26:12], [11:0] are assumed to be FFFh
> +#define N_PCH_SPI_FREGX_LIMIT 16 ///< Region limit
> bit position
> +#define N_PCH_SPI_FREGX_LIMIT_REPR 12 ///< Region
> limit bit represents position
> +#define B_PCH_SPI_FREGX_BASE_MASK 0x00007FFF ///<
> Flash Region Base, [14:0] represents [26:12]
> +#define N_PCH_SPI_FREGX_BASE 0 ///< Region base bit
> position
> +#define N_PCH_SPI_FREGX_BASE_REPR 12 ///< Region
> base bit represents position
> +#define R_PCH_SPI_PR0 0x84 ///< Protected Region 0
> Register
> +#define R_PCH_SPI_PR1 0x88 ///< Protected Region 1
> Register
> +#define R_PCH_SPI_PR2 0x8C ///< Protected Region 2
> Register
> +#define R_PCH_SPI_PR3 0x90 ///< Protected Region 3
> Register
> +#define R_PCH_SPI_PR4 0x94 ///< Protected Region 4
> Register
> +#define S_PCH_SPI_PRX 4 ///< Protected Region X
> Register size
> +#define B_PCH_SPI_PRX_WPE BIT31 ///< Write
> Protection Enable
> +#define B_PCH_SPI_PRX_PRL_MASK 0x7FFF0000 ///<
> Protected Range Limit Mask, [30:16] here represents upper limit of address
> [26:12]
> +#define N_PCH_SPI_PRX_PRL 16 ///< Protected Range
> Limit bit position
> +#define B_PCH_SPI_PRX_RPE BIT15 ///< Read
> Protection Enable
> +#define B_PCH_SPI_PRX_PRB_MASK 0x00007FFF ///<
> Protected Range Base Mask, [14:0] here represents base limit of address [26:12]
> +#define N_PCH_SPI_PRX_PRB 0 ///< Protected Range
> Base bit position
> +#define R_PCH_SPI_SFRAP 0xB0 ///< Secondary Flash
> Regions Access Permisions Register
> +#define R_PCH_SPI_FDOC 0xB4 ///< Flash Descriptor
> Observability Control Register(32 bits)
> +#define B_PCH_SPI_FDOC_FDSS_MASK (BIT14 | BIT13 | BIT12) ///<
> Flash Descritor Section Select
> +#define V_PCH_SPI_FDOC_FDSS_FSDM 0x0000 ///< Flash
> Signature and Descriptor Map
> +#define V_PCH_SPI_FDOC_FDSS_COMP 0x1000 ///<
> Component
> +#define V_PCH_SPI_FDOC_FDSS_REGN 0x2000 ///< Region
> +#define V_PCH_SPI_FDOC_FDSS_MSTR 0x3000 ///< Master
> +#define V_PCH_SPI_FDOC_FDSS_PCHS 0x4000 ///< PCH
> soft straps
> +#define V_PCH_SPI_FDOC_FDSS_SFDP 0x5000 ///< SFDP
> Parameter Table
> +#define B_PCH_SPI_FDOC_FDSI_MASK 0x0FFC ///< Flash
> Descriptor Section Index
> +#define R_PCH_SPI_FDOD 0xB8 ///< Flash Descriptor
> Observability Data Register(32 bits)
> +#define R_PCH_SPI_SFDP0_VSCC0 0xC4 ///< Vendor
> Specific Component Capabilities Register(32 bits)
> +#define B_PCH_SPI_SFDPX_VSCCX_CPPTV BIT31 ///<
> Component Property Parameter Table Valid
> +#define B_PCH_SPI_SFDP0_VSCC0_VCL BIT30 ///< Vendor
> Component Lock
> +#define B_PCH_SPI_SFDPX_VSCCX_EO_64K BIT29 ///< 64k
> Erase valid (EO_64k_valid)
> +#define B_PCH_SPI_SFDPX_VSCCX_EO_4K BIT28 ///< 4k
> Erase valid (EO_4k_valid)
> +#define B_PCH_SPI_SFDPX_VSCCX_RPMC BIT27 ///< RPMC
> Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_DPD BIT26 ///< Deep
> Powerdown Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_SUSRES BIT25 ///<
> Suspend/Resume Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_SOFTRES BIT24 ///< Soft
> Reset Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_64k_EO_MASK 0x00FF0000
> ///< 64k Erase Opcode (EO_64k)
> +#define B_PCH_SPI_SFDPX_VSCCX_4k_EO_MASK 0x0000FF00
> ///< 4k Erase Opcode (EO_4k)
> +#define B_PCH_SPI_SFDPX_VSCCX_QER (BIT7 | BIT6 | BIT5) ///<
> Quad Enable Requirements
> +#define B_PCH_SPI_SFDPX_VSCCX_WEWS BIT4 ///< Write
> Enable on Write Status
> +#define B_PCH_SPI_SFDPX_VSCCX_WSR BIT3 ///< Write
> Status Required
> +#define B_PCH_SPI_SFDPX_VSCCX_WG_64B BIT2 ///< Write
> Granularity, 0: 1 Byte; 1: 64 Bytes
> +#define R_PCH_SPI_SFDP1_VSCC1 0xC8 ///< Vendor
> Specific Component Capabilities Register(32 bits)
> +#define R_PCH_SPI_PINTX 0xCC ///< Parameter Table
> Index
> +#define N_PCH_SPI_PINTX_SPT 14
> +#define V_PCH_SPI_PINTX_SPT_CPT0 0x0 ///< Component
> 0 Property Parameter Table
> +#define V_PCH_SPI_PINTX_SPT_CPT1 0x1 ///< Component
> 1 Property Parameter Table
> +#define N_PCH_SPI_PINTX_HORD 12
> +#define V_PCH_SPI_PINTX_HORD_SFDP 0x0 ///< SFDP
> Header
> +#define V_PCH_SPI_PINTX_HORD_PT 0x1 ///< Parameter
> Table Header
> +#define V_PCH_SPI_PINTX_HORD_DATA 0x2 ///< Data
> +#define R_PCH_SPI_PTDATA 0xD0 ///< Parameter
> Table Data
> +#define R_PCH_SPI_SBRS 0xD4 ///< SPI Bus Requester
> Status
> +#define R_PCH_SPI_SSML 0xF0 ///< Set Strap Msg
> Lock
> +#define B_PCH_SPI_SSML_SSL BIT0 ///< Set_Strap Lock
> +#define R_PCH_SPI_SSMC 0xF4 ///< Set Strap Msg
> Control
> +#define B_PCH_SPI_SSMC_SSMS BIT0 ///< Set_Strap
> Mux Select
> +#define R_PCH_SPI_SSMD 0xF8 ///< Set Strap Msg
> Data
> +//
> +// @todo Follow up with EDS owner if it should be 3FFF or FFFF.
> +//
> +#define B_PCH_SPI_SRD_SSD 0x0000FFFF ///< Set_Strap
> Data
> +//
> +// Flash Descriptor Base Address Region (FDBAR) from Flash Region 0
> +//
> +#define R_PCH_SPI_FDBAR_FLVALSIG 0x00 ///< Flash Valid
> Signature
> +#define V_PCH_SPI_FDBAR_FLVALSIG 0x0FF0A55A
> +#define R_PCH_SPI_FDBAR_FLASH_MAP0 0x04
> +#define B_PCH_SPI_FDBAR_FCBA 0x000000FF ///< Flash
> Component Base Address
> +#define B_PCH_SPI_FDBAR_NC 0x00000300 ///< Number
> Of Components
> +#define N_PCH_SPI_FDBAR_NC 8 ///< Number Of
> Components
> +#define V_PCH_SPI_FDBAR_NC_1 0x00000000
> +#define V_PCH_SPI_FDBAR_NC_2 0x00000100
> +#define B_PCH_SPI_FDBAR_FRBA 0x00FF0000 ///< Flash
> Region Base Address
> +#define B_PCH_SPI_FDBAR_NR 0x07000000 ///< Number
> Of Regions
> +#define R_PCH_SPI_FDBAR_FLASH_MAP1 0x08
> +#define B_PCH_SPI_FDBAR_FMBA 0x000000FF ///< Flash
> Master Base Address
> +#define B_PCH_SPI_FDBAR_NM 0x00000700 ///< Number
> Of Masters
> +#define B_PCH_SPI_FDBAR_FPSBA 0x00FF0000 ///< PCH
> Strap Base Address, [23:16] represents [11:4]
> +#define N_PCH_SPI_FDBAR_FPSBA 16 ///< PCH Strap
> base Address bit position
> +#define N_PCH_SPI_FDBAR_FPSBA_REPR 4 ///< PCH Strap
> base Address bit represents position
> +#define B_PCH_SPI_FDBAR_PCHSL 0xFF000000 ///< PCH
> Strap Length, [31:24] represents number of Dwords
> +#define N_PCH_SPI_FDBAR_PCHSL 24 ///< PCH Strap
> Length bit position
> +#define R_PCH_SPI_FDBAR_FLASH_MAP2 0x0C
> +#define B_PCH_SPI_FDBAR_FCPUSBA 0x000000FF ///< CPU
> Strap Base Address, [7:0] represents [11:4]
> +#define N_PCH_SPI_FDBAR_FCPUSBA 0 ///< CPU Strap
> Base Address bit position
> +#define N_PCH_SPI_FDBAR_FCPUSBA_REPR 4 ///< CPU
> Strap Base Address bit represents position
> +#define B_PCH_SPI_FDBAR_CPUSL 0x0000FF00 ///< CPU
> Strap Length, [15:8] represents number of Dwords
> +#define N_PCH_SPI_FDBAR_CPUSL 8 ///< CPU Strap
> Length bit position
> +//
> +// Flash Component Base Address (FCBA) from Flash Region 0
> +//
> +#define R_PCH_SPI_FCBA_FLCOMP 0x00 ///< Flash
> Components Register
> +#define B_PCH_SPI_FLCOMP_RIDS_FREQ (BIT29 | BIT28 | BIT27) ///<
> Read ID and Read Status Clock Frequency
> +#define B_PCH_SPI_FLCOMP_WE_FREQ (BIT26 | BIT25 | BIT24) ///<
> Write and Erase Clock Frequency
> +#define B_PCH_SPI_FLCOMP_FRCF_FREQ (BIT23 | BIT22 | BIT21) ///<
> Fast Read Clock Frequency
> +#define B_PCH_SPI_FLCOMP_FR_SUP BIT20 ///< Fast Read
> Support.
> +#define B_PCH_SPI_FLCOMP_RC_FREQ (BIT19 | BIT18 | BIT17) ///<
> Read Clock Frequency.
> +#define V_PCH_SPI_FLCOMP_FREQ_48MHZ 0x02
> +#define V_PCH_SPI_FLCOMP_FREQ_30MHZ 0x04
> +#define V_PCH_SPI_FLCOMP_FREQ_17MHZ 0x06
> +#define B_PCH_SPI_FLCOMP_COMP1_MASK 0xF0 ///< Flash
> Component 1 Size MASK
> +#define N_PCH_SPI_FLCOMP_COMP1 4 ///< Flash
> Component 1 Size bit position
> +#define B_PCH_SPI_FLCOMP_COMP0_MASK 0x0F ///< Flash
> Component 0 Size MASK
> +#define V_PCH_SPI_FLCOMP_COMP_512KB 0x80000
> +//
> +// Descriptor Upper Map Section from Flash Region 0
> +//
> +#define R_PCH_SPI_FLASH_UMAP1 0xEFC ///< Flash
> Upper Map 1
> +#define B_PCH_SPI_FLASH_UMAP1_VTBA 0x000000FF ///<
> VSCC Table Base Address
> +#define B_PCH_SPI_FLASH_UMAP1_VTL 0x0000FF00 ///<
> VSCC Table Length
> +
> +#define R_PCH_SPI_VTBA_JID0 0x00 ///< JEDEC-ID 0
> Register
> +#define S_PCH_SPI_VTBA_JID0 0x04
> +#define B_PCH_SPI_VTBA_JID0_VID 0x000000FF
> +#define B_PCH_SPI_VTBA_JID0_DID0 0x0000FF00
> +#define B_PCH_SPI_VTBA_JID0_DID1 0x00FF0000
> +#define N_PCH_SPI_VTBA_JID0_DID0 0x08
> +#define N_PCH_SPI_VTBA_JID0_DID1 0x10
> +#define R_PCH_SPI_VTBA_VSCC0 0x04
> +#define S_PCH_SPI_VTBA_VSCC0 0x04
> +
> +
> +//
> +// SPI Private Configuration Space Registers
> +//
> +#define R_PCH_PCR_SPI_CLK_CTL 0xC004
> +#define R_PCH_PCR_SPI_PWR_CTL 0xC008
> +#define R_PCH_PCR_SPI_ESPI_SOFTSTRAPS 0xC210
> +#define B_PCH_PCR_SPI_ESPI_SOFTSTRAPS_SLAVE BIT12
> +
> +//
> +// MMP0
> +//
> +#define R_PCH_SPI_STRP_MMP0 0xC4 ///< MMP0 Soft strap offset
> +#define B_PCH_SPI_STRP_MMP0 0x10 ///< MMP0 Soft strap bit
> +
> +
> +#define R_PCH_SPI_STRP_SFDP 0xF0 ///< PCH Soft Strap SFDP
> +#define B_PCH_SPI_STRP_SFDP_QIORE BIT3 ///< Quad IO Read Enable
> +#define B_PCH_SPI_STRP_SFDP_QORE BIT2 ///< Quad Output Read
> Enable
> +#define B_PCH_SPI_STRP_SFDP_DIORE BIT1 ///< Dual IO Read Enable
> +#define B_PCH_SPI_STRP_SFDP_DORE BIT0 ///< Dual Output Read
> Enable
> +
> +//
> +// Descriptor Record 0
> +//
> +#define R_PCH_SPI_STRP_DSCR_0 0x00 ///< PCH Soft Strap 0
> +#define B_PCH_SPI_STRP_DSCR_0_PTT_SUPP BIT22 ///< PTT Supported
> +
> +#endif
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> new file mode 100644
> index 0000000000..5bdec96197
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> @@ -0,0 +1,396 @@
> +/** @file
> + Header file for the PCH SPI Common Driver.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_SPI_COMMON_LIB_H_
> +#define _PCH_SPI_COMMON_LIB_H_
> +
> +//
> +// Maximum time allowed while waiting the SPI cycle to complete
> +// Wait Time = 6 seconds = 6000000 microseconds
> +// Wait Period = 10 microseconds
> +//
> +#define SPI_WAIT_TIME 6000000 ///< Wait Time = 6 seconds = 6000000
> microseconds
> +#define SPI_WAIT_PERIOD 10 ///< Wait Period = 10 microseconds
> +
> +///
> +/// Flash cycle Type
> +///
> +typedef enum {
> + FlashCycleRead,
> + FlashCycleWrite,
> + FlashCycleErase,
> + FlashCycleReadSfdp,
> + FlashCycleReadJedecId,
> + FlashCycleWriteStatus,
> + FlashCycleReadStatus,
> + FlashCycleMax
> +} FLASH_CYCLE_TYPE;
> +
> +///
> +/// Flash Component Number
> +///
> +typedef enum {
> + FlashComponent0,
> + FlashComponent1,
> + FlashComponentMax
> +} FLASH_COMPONENT_NUM;
> +
> +///
> +/// Private data structure definitions for the driver
> +///
> +#define PCH_SPI_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('P', 'S', 'P', 'I')
> +
> +typedef struct {
> + UINT32 Signature;
> + EFI_HANDLE Handle;
> + EFI_SPI_PROTOCOL SpiProtocol;
> + UINT16 PchAcpiBase;
> + UINTN PchSpiBase;
> + UINT16 ReadPermission;
> + UINT16 WritePermission;
> + UINT32 SfdpVscc0Value;
> + UINT32 SfdpVscc1Value;
> + UINT16 PchStrapBaseAddr;
> + UINT16 PchStrapSize;
> + UINT16 CpuStrapBaseAddr;
> + UINT16 CpuStrapSize;
> + UINT8 NumberOfComponents;
> + UINT32 Component1StartAddr;
> + UINT32 TotalFlashSize;
> +} SPI_INSTANCE;
> +
> +#define SPI_INSTANCE_FROM_SPIPROTOCOL(a) CR (a, SPI_INSTANCE,
> SpiProtocol, PCH_SPI_PRIVATE_DATA_SIGNATURE)
> +
> +//
> +// Function prototypes used by the SPI protocol.
> +//
> +
> +/**
> + Initialize an SPI protocol instance.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @exception EFI_UNSUPPORTED The PCH is not supported by this module
> +**/
> +EFI_STATUS
> +SpiProtocolConstructor (
> + IN SPI_INSTANCE *SpiInstance
> + );
> +
> +/**
> + This function is a hook for Spi to disable BIOS Write Protect
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in
> SMM phase
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +DisableBiosWriteProtect (
> + VOID
> + );
> +
> +/**
> + This function is a hook for Spi to enable BIOS Write Protect
> +
> +
> +**/
> +VOID
> +EFIAPI
> +EnableBiosWriteProtect (
> + VOID
> + );
> +
> +/**
> + Acquire pch spi mmio address.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval PchSpiBar0 return SPI MMIO address
> +**/
> +UINTN
> +AcquireSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + );
> +
> +/**
> + Release pch spi mmio address.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval None
> +**/
> +VOID
> +ReleaseSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + );
> +
> +/**
> + Read data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[out] Buffer The Pointer to caller-allocated buffer containing
> the dada received.
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashRead (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *Buffer
> + );
> +
> +/**
> + Write data to the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in] Buffer Pointer to caller-allocated buffer containing the
> data sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWrite (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN UINT8 *Buffer
> + );
> +
> +/**
> + Erase some area on the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashErase (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount
> + );
> +
> +/**
> + Read SFDP data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] Address The starting byte address for SFDP data read.
> + @param[in] ByteCount Number of bytes in SFDP data portion of the SPI
> cycle
> + @param[out] SfdpData The Pointer to caller-allocated buffer containing
> the SFDP data received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadSfdp (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *SfdpData
> + );
> +
> +/**
> + Read Jedec Id from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] ByteCount Number of bytes in JedecId data portion of the
> SPI cycle, the data size is 3 typically
> + @param[out] JedecId The Pointer to caller-allocated buffer containing
> JEDEC ID received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadJedecId (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 ByteCount,
> + OUT UINT8 *JedecId
> + );
> +
> +/**
> + Write the status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[in] StatusValue The Pointer to caller-allocated buffer containing
> the value of Status register writing
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWriteStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + IN UINT8 *StatusValue
> + );
> +
> +/**
> + Read status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[out] StatusValue The Pointer to caller-allocated buffer
> containing the value of Status register received.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + OUT UINT8 *StatusValue
> + );
> +
> +/**
> + Get the SPI region base and size, based on the enum type
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for for the base
> address which is listed in the Descriptor.
> + @param[out] BaseAddress The Flash Linear Address for the Region 'n'
> Base
> + @param[out] RegionSize The size for the Region 'n'
> +
> + @retval EFI_SUCCESS Read success
> + @retval EFI_INVALID_PARAMETER Invalid region type given
> + @retval EFI_DEVICE_ERROR The region is not used
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolGetRegionAddress (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + OUT UINT32 *BaseAddress,
> + OUT UINT32 *RegionSize
> + );
> +
> +/**
> + Read PCH Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing PCH Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadPchSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + Read CPU Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle.
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing CPU Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadCpuSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + This function sends the programmed SPI command to the slave device.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SpiRegionType The SPI Region type for flash cycle which is
> listed in the Descriptor
> + @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware
> Sequencing Flash Control Register) register
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in,out] Buffer Pointer to caller-allocated buffer containing the
> dada received or sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS SPI command completes successfully.
> + @retval EFI_DEVICE_ERROR Device error, the command aborts
> abnormally.
> + @retval EFI_ACCESS_DENIED Some unrecognized command encountered
> in hardware sequencing mode
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> +**/
> +EFI_STATUS
> +SendSpiCmd (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN FLASH_CYCLE_TYPE FlashCycleType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN OUT UINT8 *Buffer
> + );
> +
> +/**
> + Wait execution cycle to complete on the SPI interface.
> +
> + @param[in] This The SPI protocol instance
> + @param[in] PchSpiBar0 Spi MMIO base address
> + @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
> +
> + @retval TRUE SPI cycle completed on the interface.
> + @retval FALSE Time out while waiting the SPI cycle to complete.
> + It's not safe to program the next command on the SPI
> interface.
> +**/
> +BOOLEAN
> +WaitForSpiCycleComplete (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINTN PchSpiBar0,
> + IN BOOLEAN ErrorCheck
> + );
> +
> +#endif
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> new file mode 100644
> index 0000000000..4af462da47
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> @@ -0,0 +1,34 @@
> +## @file
> +# Library instance for ResetSystem library class for OVMF
> +#
> +# Copyright (c) 2006 - 2018 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010005
> + BASE_NAME = ResetSystemLib
> + FILE_GUID = 66564872-21d4-4d2a-a68b-1e844f980820
> + MODULE_TYPE = BASE
> + VERSION_STRING = 1.0
> + LIBRARY_CLASS = ResetSystemLib
> +
> +#
> +# The following information is for reference only and not required by the build
> tools.
> +#
> +# VALID_ARCHITECTURES = IA32 X64
> +#
> +
> +[Sources]
> + ResetSystemLib.c
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> +
> +[LibraryClasses]
> + DebugLib
> + IoLib
> + TimerLib
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> CommonLib.inf
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> CommonLib.inf
> new file mode 100644
> index 0000000000..b5c97f1930
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> CommonLib.inf
> @@ -0,0 +1,52 @@
> +## @file
> +# SMM Library instance of Spi Flash Common Library Class
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010017
> + BASE_NAME = SmmSpiFlashCommonLib
> + FILE_GUID = 9632D96E-E849-4217-9217-DC500B8AAE47
> + VERSION_STRING = 1.0
> + MODULE_TYPE = DXE_SMM_DRIVER
> + LIBRARY_CLASS = SpiFlashCommonLib|DXE_SMM_DRIVER
> + CONSTRUCTOR = SmmSpiFlashCommonLibConstructor
> +#
> +# The following information is for reference only and not required by the build
> tools.
> +#
> +# VALID_ARCHITECTURES = IA32 X64
> +#
> +
> +[LibraryClasses]
> + PciLib
> + IoLib
> + MemoryAllocationLib
> + BaseLib
> + UefiLib
> + SmmServicesTableLib
> + BaseMemoryLib
> + DebugLib
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsICH10Pkg/ICH10Pkg.dec
> + MinPlatformPkg/MinPlatformPkg.dec
> +
> +
> +[Pcd]
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
> +
> +[Sources]
> + SpiFlashCommonSmmLib.c
> + SpiFlashCommon.c
> +
> +[Protocols]
> + gEfiSmmSpiProtocolGuid ## CONSUMES
> +
> +[Depex.X64.DXE_SMM_DRIVER]
> + gEfiSmmSpiProtocolGuid
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> SpiCommonLib.inf
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> SpiCommonLib.inf
> new file mode 100644
> index 0000000000..11c832e487
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> SpiCommonLib.inf
> @@ -0,0 +1,33 @@
> +## @file
> +# Component description file for the PchSpiCommonLib
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010005
> + BASE_NAME = BasePchSpiCommonLib
> + FILE_GUID = A37CB67E-7D85-45B3-B07E-BF65BDB603E8
> + MODULE_TYPE = BASE
> + VERSION_STRING = 1.0
> + LIBRARY_CLASS = PchSpiCommonLib
> +
> +[Sources]
> + SpiCommon.c
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsICH10Pkg/ICH10Pkg.dec
> + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> + MinPlatformPkg/MinPlatformPkg.dec
> +
> +[LibraryClasses]
> + IoLib
> + DebugLib
> +
> +[Pcd]
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> new file mode 100644
> index 0000000000..a2d006ee35
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> @@ -0,0 +1,12 @@
> +## @file
> +# Component description file for the SkyLake SiPkg DXE libraries.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[LibraryClasses.common]
> + ResetSystemLib|$(PCH_PKG)/Library/ResetSystemLib/ResetSystemLib.inf
> +
> PchSpiCommonLib|$(PCH_PKG)/LibraryPrivate/BasePchSpiCommonLib/BasePc
> hSpiCommonLib.inf
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> new file mode 100644
> index 0000000000..78eca21a43
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> @@ -0,0 +1,9 @@
> +## @file
> +# Component description file for the SkyLake SiPkg DXE drivers.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> new file mode 100644
> index 0000000000..2d3a127c20
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> @@ -0,0 +1,9 @@
> +## @file
> +# Component description file for the SkyLake SiPkg PEI drivers.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> new file mode 100644
> index 0000000000..d079c593d9
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> @@ -0,0 +1,13 @@
> +## @file
> +# Component description file for the SkyLake SiPkg DXE drivers.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +!if gMinPlatformPkgTokenSpaceGuid.PcdBootToShellOnly == FALSE
> + INF $(PCH_PKG)/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> + INF $(PCH_PKG)/Spi/Smm/PchSpiSmm.inf
> +!endif
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> new file mode 100644
> index 0000000000..e23dd9f2fe
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> @@ -0,0 +1,59 @@
> +## @file
> +# A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
> +# EFI_SMM_CONTROL2_PROTOCOL.
> +#
> +# We expect the PEI phase to have covered the following:
> +# - ensure that the underlying QEMU machine type be X58
> +# (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
> +# - ensure that the ACPI PM IO space be configured
> +# (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
> +#
> +# Our own entry point is responsible for confirming the SMI feature and for
> +# configuring it.
> +#
> +# Copyright (C) 2013, 2015, Red Hat, Inc.
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010005
> + BASE_NAME = SmmControl2Dxe
> + FILE_GUID = 1206F7CA-A475-4624-A83E-E6FC9BB38E49
> + MODULE_TYPE = DXE_RUNTIME_DRIVER
> + VERSION_STRING = 1.0
> + PI_SPECIFICATION_VERSION = 0x00010400
> + ENTRY_POINT = SmmControl2DxeEntryPoint
> +
> +#
> +# The following information is for reference only and not required by the build
> tools.
> +#
> +# VALID_ARCHITECTURES = IA32 X64
> +#
> +
> +[Sources]
> + SmmControl2Dxe.c
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> +
> +[LibraryClasses]
> + BaseLib
> + DebugLib
> + IoLib
> + PcdLib
> + PciLib
> + UefiBootServicesTableLib
> + UefiDriverEntryPoint
> +
> +[Protocols]
> + gEfiS3SaveStateProtocolGuid ## SOMETIMES_CONSUMES
> + gEfiSmmControl2ProtocolGuid ## PRODUCES
> +
> +[FeaturePcd]
> + gSimicsX58PkgTokenSpaceGuid.PcdSmmSmramRequire
> +
> +[Depex]
> + TRUE
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> new file mode 100644
> index 0000000000..f7fdd3abbe
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> @@ -0,0 +1,23 @@
> +/** @file
> + Header file for the PCH SPI SMM Driver.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_SPI_H_
> +#define _PCH_SPI_H_
> +
> +#include <Library/IoLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/UefiDriverEntryPoint.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +#include <Library/BaseLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <Library/SmmServicesTableLib.h>
> +#include <PchAccess.h>
> +#include <Protocol/Spi.h>
> +#include <IncludePrivate/Library/PchSpiCommonLib.h>
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> new file mode 100644
> index 0000000000..265af00ac0
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> @@ -0,0 +1,44 @@
> +## @file
> +# Component description file for the SPI SMM driver.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010017
> + BASE_NAME = PchSpiSmm
> + FILE_GUID = 27F4917B-A707-4aad-9676-26DF168CBF0D
> + VERSION_STRING = 1.0
> + MODULE_TYPE = DXE_SMM_DRIVER
> + PI_SPECIFICATION_VERSION = 1.10
> + ENTRY_POINT = InstallPchSpi
> +
> +
> + [LibraryClasses]
> + DebugLib
> + IoLib
> + UefiDriverEntryPoint
> + UefiBootServicesTableLib
> + BaseLib
> + SmmServicesTableLib
> + PchSpiCommonLib
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsICH10Pkg/ICH10Pkg.dec
> +
> +[Sources]
> + PchSpi.h
> + PchSpi.c
> +
> +
> +[Protocols]
> + gEfiSmmSpiProtocolGuid # PRODUCES #SERVER_BIOS
> +
> +
> +[Depex]
> + gEfiSmmBase2ProtocolGuid #This is for SmmServicesTableLib
> + AND gEfiSmmCpuProtocolGuid # This is for
> CpuSmmDisableBiosWriteProtect()
> --
> 2.16.2.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#46065): https://edk2.groups.io/g/devel/message/46065
Mute This Topic: https://groups.io/mt/32816096/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
Hi Mike,
Please see the updates online below. Please let me know if you have any more comments.
Thanks
David
-----Original Message-----
From: Kubacki, Michael A
Sent: Monday, August 19, 2019 6:04 PM
To: Wei, David Y <david.y.wei@intel.com>; devel@edk2.groups.io
Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>; Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince <prince.agyeman@intel.com>; Desimone, Nathaniel L <nathaniel.l.desimone@intel.com>; Kinney, Michael D <michael.d.kinney@intel.com>
Subject: RE: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for SimicsICH10
Feedback I could not find already noted elsewhere:
1. /Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf:
This silicon package should not have a dependency on MinPlatformPkg.dec.
Ydwei: done
2. /Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf:
This silicon package should not have a dependency on SimicsOpenBoardPkg.dec.
Ydwei: done
3. Although noted elsewhere: I also prefer Pascal naming as well so SimicsIch10Pkg.
Ydwei: done
4. /Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c:
"Reset System Library functions for OVMF" - replace OVMF with Simics ICH10.
Ydwei: done
5. /Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf:
This silicon package INF should not have a dependency on MinPlatformPkg.dec.
Ydwei: done
6. /Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
This silicon package INF should not have a dependency on MinPlatformPkg.dec.
Ydwei: done
7. /Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonib/SmmSpiFlashCommonLib:
This silicon package INF should not have a dependency on MinPlatformPkg.dec.
Ydwei: done
> -----Original Message-----
> From: Wei, David Y
> Sent: Friday, August 9, 2019 3:47 PM
> To: devel@edk2.groups.io
> Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>;
> Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince
> <prince.agyeman@intel.com>; Kubacki, Michael A
> <michael.a.kubacki@intel.com>; Desimone, Nathaniel L
> <nathaniel.l.desimone@intel.com>; Kinney, Michael D
> <michael.d.kinney@intel.com>
> Subject: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for
> SimicsICH10
>
> Add PCH Pkg for SimicsICH10. It is added for simics QSP project support
>
> Cc: Hao Wu <hao.a.wu@intel.com>
> Cc: Liming Gao <liming.gao@intel.com>
> Cc: Ankit Sinha <ankit.sinha@intel.com>
> Cc: Agyeman Prince <prince.agyeman@intel.com>
> Cc: Kubacki Michael A <michael.a.kubacki@intel.com>
> Cc: Nate DeSimone <nathaniel.l.desimone@intel.com>
> Cc: Michael D Kinney <michael.d.kinney@intel.com>
> Contributed-under: TianoCore Contribution Agreement 1.0
>
> Signed-off-by: David Wei <david.y.wei@intel.com>
> ---
> .../Library/ResetSystemLib/ResetSystemLib.c | 137 +++
> .../Library/SmmSpiFlashCommonLib/SpiFlashCommon.c | 194 +++++
> .../SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c | 54 ++
> .../LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c | 935
> +++++++++++++++++++++
> .../SmmControl/RuntimeDxe/SmmControl2Dxe.c | 410 +++++++++
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c | 175 ++++
> Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec | 22 +
> .../Include/Library/SpiFlashCommonLib.h | 98 +++
> Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h | 43 +
> Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h | 94 +++
> .../SimicsICH10Pkg/Include/PchReservedResources.h | 60 ++
> .../Intel/SimicsICH10Pkg/Include/Protocol/Spi.h | 295 +++++++
> .../SimicsICH10Pkg/Include/Register/PchRegsPmc.h | 647 ++++++++++++++
> .../SimicsICH10Pkg/Include/Register/PchRegsSpi.h | 304 +++++++
> .../IncludePrivate/Library/PchSpiCommonLib.h | 396 +++++++++
> .../Library/ResetSystemLib/ResetSystemLib.inf | 34 +
> .../SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf | 52 ++
> .../BasePchSpiCommonLib/BasePchSpiCommonLib.inf | 33 +
> Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc | 12 +
> .../Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf | 9 +
> .../Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf | 9 +
> .../Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf | 13 +
> .../SmmControl/RuntimeDxe/SmmControl2Dxe.inf | 59 ++
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h | 23 +
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf | 44 +
> 25 files changed, 4152 insertions(+)
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommo
> n.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommo
> nSmmLib.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommo
> n.c
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCo
> mmonLib.inf
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpi
> CommonLib.inf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> create mode 100644
> Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
>
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> new file mode 100644
> index 0000000000..46355e191c
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> @@ -0,0 +1,137 @@
> +/** @file
> + Reset System Library functions for OVMF
> +
> + Copyright (c) 2006 - 2016 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Base.h>
> +
> +#include <Library/BaseLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/IoLib.h>
> +#include <Library/TimerLib.h>
> +#include <IndustryStandard/X58Ich10.h>
> +
> +
> +VOID
> +AcpiPmControl (
> + UINTN SuspendType
> + )
> +{
> + ASSERT (SuspendType < 6);
> + DEBUG((EFI_D_ERROR, "SuspendType = 0x%x\n", SuspendType));
> +
> + IoBitFieldWrite16 (ICH10_PMBASE_IO + 4, 10, 13, (UINT16) SuspendType);
> + IoOr16 (ICH10_PMBASE_IO + 0x04, BIT13);
> + CpuDeadLoop ();
> +}
> +
> +/**
> + Calling this function causes a system-wide reset. This sets
> + all circuitry within the system to its initial state. This type of reset
> + is asynchronous to system operation and operates without regard to
> + cycle boundaries.
> +
> + System reset should not return, if it returns, it means the system does
> + not support cold reset.
> +**/
> +VOID
> +EFIAPI
> +ResetCold (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetCold_CF9\n"));
> + IoWrite8 (0xCF9, BIT3 | BIT2 | BIT1); // 1st choice: PIIX3 RCR, RCPU|SRST
> + MicroSecondDelay (50);
> +
> + DEBUG((EFI_D_ERROR, "ResetCold_Port64\n"));
> + IoWrite8 (0x64, 0xfe); // 2nd choice: keyboard controller
> + CpuDeadLoop ();
> +}
> +
> +/**
> + Calling this function causes a system-wide initialization. The processors
> + are set to their initial state, and pending cycles are not corrupted.
> +
> + System reset should not return, if it returns, it means the system does
> + not support warm reset.
> +**/
> +VOID
> +EFIAPI
> +ResetWarm (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetWarm\n"));
> + //
> + //BUGBUG workaround for warm reset
> + //
> + IoWrite8(0xCF9, BIT2 | BIT1);
> + MicroSecondDelay(50);
> +
> + IoWrite8 (0x64, 0xfe);
> + CpuDeadLoop ();
> +}
> +
> +/**
> + Calling this function causes the system to enter a power state equivalent
> + to the ACPI G2/S5 or G3 states.
> +
> + System shutdown should not return, if it returns, it means the system does
> + not support shut down reset.
> +**/
> +VOID
> +EFIAPI
> +ResetShutdown (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetShutdown\n"));
> + AcpiPmControl (0);
> + ASSERT (FALSE);
> +}
> +
> +
> +/**
> + Calling this function causes the system to enter a power state for capsule
> + update.
> +
> + Reset update should not return, if it returns, it means the system does
> + not support capsule update.
> +
> +**/
> +VOID
> +EFIAPI
> +EnterS3WithImmediateWake (
> + VOID
> + )
> +{
> + DEBUG((EFI_D_ERROR, "EnterS3WithImmediateWake\n"));
> + AcpiPmControl (1);
> + ASSERT (FALSE);
> +}
> +
> +/**
> + This function causes a systemwide reset. The exact type of the reset is
> + defined by the EFI_GUID that follows the Null-terminated Unicode string
> passed
> + into ResetData. If the platform does not recognize the EFI_GUID in ResetData
> + the platform must pick a supported reset type to perform.The platform may
> + optionally log the parameters from any non-normal reset that occurs.
> +
> + @param[in] DataSize The size, in bytes, of ResetData.
> + @param[in] ResetData The data buffer starts with a Null-terminated string,
> + followed by the EFI_GUID.
> +**/
> +VOID
> +EFIAPI
> +ResetPlatformSpecific (
> + IN UINTN DataSize,
> + IN VOID *ResetData
> + )
> +{
> + DEBUG((EFI_D_ERROR, "ResetPlatformSpecific\n"));
> + ResetCold ();
> +}
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mon.c
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mon.c
> new file mode 100644
> index 0000000000..3d4e24eac6
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mon.c
> @@ -0,0 +1,194 @@
> +/** @file
> + Wrap EFI_SPI_PROTOCOL to provide some library level interfaces
> + for module use.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Library/SpiFlashCommonLib.h>
> +#include <Library/IoLib.h>
> +#include <Library/PciLib.h>
> +#include <Protocol/Spi.h>
> +
> +
> +EFI_SPI_PROTOCOL *mSpiProtocol;
> +
> +//
> +// FlashAreaBaseAddress and Size for boottime and runtime usage.
> +//
> +UINTN mFlashAreaBaseAddress = 0;
> +UINTN mFlashAreaSize = 0;
> +
> +/**
> + Enable block protection on the Serial Flash device.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashLock (
> + VOID
> + )
> +{
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Read NumBytes bytes of data from the address specified by
> + PAddress into Buffer.
> +
> + @param[in] Address The starting physical address of the read.
> + @param[in,out] NumBytes On input, the number of bytes to read. On
> output, the number
> + of bytes actually read.
> + @param[out] Buffer The destination data buffer for the read.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashRead (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + OUT UINT8 *Buffer
> + )
> +{
> + ASSERT ((NumBytes != NULL) && (Buffer != NULL));
> + if ((NumBytes == NULL) || (Buffer == NULL)) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // This function is implemented specifically for those platforms
> + // at which the SPI device is memory mapped for read. So this
> + // function just do a memory copy for Spi Flash Read.
> + //
> + CopyMem (Buffer, (VOID *) Address, *NumBytes);
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Write NumBytes bytes of data from Buffer to the address specified by
> + PAddresss.
> +
> + @param[in] Address The starting physical address of the write.
> + @param[in,out] NumBytes On input, the number of bytes to write. On
> output,
> + the actual number of bytes written.
> + @param[in] Buffer The source data buffer for the write.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashWrite (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + IN UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> + UINTN Offset;
> + UINT32 Length;
> + UINT32 RemainingBytes;
> +
> + ASSERT ((NumBytes != NULL) && (Buffer != NULL));
> + if ((NumBytes == NULL) || (Buffer == NULL)) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + ASSERT (Address >= mFlashAreaBaseAddress);
> +
> + Offset = Address - mFlashAreaBaseAddress;
> +
> + ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
> +
> + Status = EFI_SUCCESS;
> + RemainingBytes = *NumBytes;
> +
> +
> + while (RemainingBytes > 0) {
> + if (RemainingBytes > SECTOR_SIZE_4KB) {
> + Length = SECTOR_SIZE_4KB;
> + } else {
> + Length = RemainingBytes;
> + }
> + Status = mSpiProtocol->FlashWrite (
> + mSpiProtocol,
> + FlashRegionBios,
> + (UINT32) Offset,
> + Length,
> + Buffer
> + );
> + if (EFI_ERROR (Status)) {
> + break;
> + }
> + RemainingBytes -= Length;
> + Offset += Length;
> + Buffer += Length;
> + }
> +
> + //
> + // Actual number of bytes written
> + //
> + *NumBytes -= RemainingBytes;
> +
> + return Status;
> +}
> +
> +/**
> + Erase the block starting at Address.
> +
> + @param[in] Address The starting physical address of the block to be
> erased.
> + This library assume that caller garantee that the PAddress
> + is at the starting address of this block.
> + @param[in] NumBytes On input, the number of bytes of the logical block
> to be erased.
> + On output, the actual number of bytes erased.
> +
> + @retval EFI_SUCCESS. Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashBlockErase (
> + IN UINTN Address,
> + IN UINTN *NumBytes
> + )
> +{
> + EFI_STATUS Status;
> + UINTN Offset;
> + UINTN RemainingBytes;
> +
> + ASSERT (NumBytes != NULL);
> + if (NumBytes == NULL) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + ASSERT (Address >= mFlashAreaBaseAddress);
> +
> + Offset = Address - mFlashAreaBaseAddress;
> +
> + ASSERT ((*NumBytes % SECTOR_SIZE_4KB) == 0);
> + ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
> +
> + Status = EFI_SUCCESS;
> + RemainingBytes = *NumBytes;
> +
> +
> + Status = mSpiProtocol->FlashErase (
> + mSpiProtocol,
> + FlashRegionBios,
> + (UINT32) Offset,
> + (UINT32) RemainingBytes
> + );
> + return Status;
> +}
> +
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> monSmmLib.c
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> monSmmLib.c
> new file mode 100644
> index 0000000000..1e5cd0d744
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> monSmmLib.c
> @@ -0,0 +1,54 @@
> +/** @file
> + SMM Library instance of SPI Flash Common Library Class
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Library/SpiFlashCommonLib.h>
> +#include <Library/SmmServicesTableLib.h>
> +#include <Protocol/Spi.h>
> +
> +extern EFI_SPI_PROTOCOL *mSpiProtocol;
> +
> +extern UINTN mFlashAreaBaseAddress;
> +extern UINTN mFlashAreaSize;
> +
> +/**
> + The library constructuor.
> +
> + The function does the necessary initialization work for this library
> + instance.
> +
> + @param[in] ImageHandle The firmware allocated handle for the UEFI
> image.
> + @param[in] SystemTable A pointer to the EFI system table.
> +
> + @retval EFI_SUCCESS The function always return EFI_SUCCESS for now.
> + It will ASSERT on error for debug version.
> + @retval EFI_ERROR Please reference LocateProtocol for error code
> details.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SmmSpiFlashCommonLibConstructor (
> + IN EFI_HANDLE ImageHandle,
> + IN EFI_SYSTEM_TABLE *SystemTable
> + )
> +{
> + EFI_STATUS Status;
> +
> + mFlashAreaBaseAddress = (UINTN)PcdGet32 (PcdFlashAreaBaseAddress);
> + mFlashAreaSize = (UINTN)PcdGet32 (PcdFlashAreaSize);
> +
> + //
> + // Locate the SMM SPI protocol.
> + //
> + Status = gSmst->SmmLocateProtocol (
> + &gEfiSmmSpiProtocolGuid,
> + NULL,
> + (VOID **) &mSpiProtocol
> + );
> + ASSERT_EFI_ERROR (Status);
> +
> + return Status;
> +}
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mon.c
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mon.c
> new file mode 100644
> index 0000000000..77fb76d7cd
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mon.c
> @@ -0,0 +1,935 @@
> +/** @file
> + PCH SPI Common Driver implements the SPI Host Controller Compatibility
> Interface.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <Uefi/UefiBaseType.h>
> +#include <Library/IoLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <IndustryStandard/Pci30.h>
> +#include <PchAccess.h>
> +#include <Protocol/Spi.h>
> +#include <IncludePrivate/Library/PchSpiCommonLib.h>
> +#include <IndustryStandard/X58Ich10.h>
> +
> +/**
> + Initialize an SPI protocol instance.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @exception EFI_UNSUPPORTED The PCH is not supported by this module
> +**/
> +EFI_STATUS
> +SpiProtocolConstructor (
> + IN SPI_INSTANCE *SpiInstance
> + )
> +{
> + UINTN PchSpiBar0;
> +
> + //
> + // Initialize the SPI protocol instance
> + //
> + SpiInstance->Signature = PCH_SPI_PRIVATE_DATA_SIGNATURE;
> + SpiInstance->Handle = NULL;
> + SpiInstance->SpiProtocol.Revision = PCH_SPI_SERVICES_REVISION;
> + SpiInstance->SpiProtocol.FlashRead = SpiProtocolFlashRead;
> + SpiInstance->SpiProtocol.FlashWrite = SpiProtocolFlashWrite;
> + SpiInstance->SpiProtocol.FlashErase = SpiProtocolFlashErase;
> + SpiInstance->SpiProtocol.FlashReadSfdp = SpiProtocolFlashReadSfdp;
> + SpiInstance->SpiProtocol.FlashReadJedecId = SpiProtocolFlashReadJedecId;
> + SpiInstance->SpiProtocol.FlashWriteStatus = SpiProtocolFlashWriteStatus;
> + SpiInstance->SpiProtocol.FlashReadStatus = SpiProtocolFlashReadStatus;
> + SpiInstance->SpiProtocol.GetRegionAddress = SpiProtocolGetRegionAddress;
> + SpiInstance->SpiProtocol.ReadPchSoftStrap = SpiProtocolReadPchSoftStrap;
> + SpiInstance->SpiProtocol.ReadCpuSoftStrap = SpiProtocolReadCpuSoftStrap;
> +
> + SpiInstance->PchAcpiBase = ICH10_PMBASE_IO;
> + ASSERT (SpiInstance->PchAcpiBase != 0);
> +
> + PchSpiBar0 = RCRB + SPIBAR;
> +
> + if (PchSpiBar0 == 0) {
> + DEBUG ((DEBUG_ERROR, "ERROR : PchSpiBar0 is invalid!\n"));
> + ASSERT (FALSE);
> + }
> +
> + if ((MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC) &
> B_PCH_SPI_HSFSC_FDV) == 0) {
> + DEBUG ((DEBUG_ERROR, "ERROR : SPI Flash Signature invalid, cannot use
> the Hardware Sequencing registers!\n"));
> + ASSERT (FALSE);
> + }
> + SpiInstance->ReadPermission = 0xffff;
> + SpiInstance->WritePermission = 0xffff;
> + DEBUG ((DEBUG_INFO, "Flash Region Permission: Read- 0x%04x; Write=
> 0x%04x\n",
> + SpiInstance->ReadPermission,
> + SpiInstance->WritePermission));
> +
> + //
> + SpiInstance->TotalFlashSize = PcdGet32(PcdFlashAreaSize);
> + DEBUG ((DEBUG_INFO, "Total Flash Size : %0x\n", SpiInstance-
> >TotalFlashSize));
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Delay for at least the request number of microseconds for Runtime usage.
> +
> + @param[in] ABase Acpi base address
> + @param[in] Microseconds Number of microseconds to delay.
> +
> +**/
> +VOID
> +EFIAPI
> +PchPmTimerStallRuntimeSafe (
> + IN UINT16 ABase,
> + IN UINTN Microseconds
> + )
> +{
> + UINTN Ticks;
> + UINTN Counts;
> + UINTN CurrentTick;
> + UINTN OriginalTick;
> + UINTN RemainingTick;
> +
> + if (Microseconds == 0) {
> + return;
> + }
> +
> + OriginalTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) &
> B_PCH_ACPI_PM1_TMR_VAL;
> + 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 / V_PCH_ACPI_PM1_TMR_MAX_VAL;
> +
> + //
> + // Remaining clocks within one loop
> + //
> + RemainingTick = Ticks % V_PCH_ACPI_PM1_TMR_MAX_VAL;
> +
> + //
> + // 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) || (RemainingTick > CurrentTick)) {
> + CurrentTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) &
> B_PCH_ACPI_PM1_TMR_VAL;
> + //
> + // Check if timer overflow
> + //
> + if ((CurrentTick < OriginalTick)) {
> + if (Counts != 0) {
> + Counts--;
> + } else {
> + //
> + // If timer overflow and Counts equ to 0, that means we already stalled
> more than
> + // RemainingTick, break the loop here
> + //
> + break;
> + }
> + }
> +
> + OriginalTick = CurrentTick;
> + }
> +}
> +
> +/**
> + Read data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[out] Buffer The Pointer to caller-allocated buffer containing
> the dada received.
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashRead (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionType,
> + FlashCycleRead,
> + Address,
> + ByteCount,
> + Buffer
> + );
> + return Status;
> +}
> +
> +/**
> + Write data to the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in] Buffer Pointer to caller-allocated buffer containing the
> data sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWrite (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionType,
> + FlashCycleWrite,
> + Address,
> + ByteCount,
> + Buffer
> + );
> + return Status;
> +}
> +
> +/**
> + Erase some area on the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashErase (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionType,
> + FlashCycleErase,
> + Address,
> + ByteCount,
> + NULL
> + );
> + return Status;
> +}
> +
> +/**
> + Read SFDP data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] Address The starting byte address for SFDP data read.
> + @param[in] ByteCount Number of bytes in SFDP data portion of the SPI
> cycle
> + @param[out] SfdpData The Pointer to caller-allocated buffer containing
> the SFDP data received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadSfdp (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *SfdpData
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + EFI_STATUS Status;
> + UINT32 FlashAddress;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> + Status = EFI_SUCCESS;
> +
> + if (ComponentNumber > SpiInstance->NumberOfComponents) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + FlashAddress = 0;
> + if (ComponentNumber == FlashComponent1) {
> + FlashAddress = SpiInstance->Component1StartAddr;
> + }
> + FlashAddress += Address;
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleReadSfdp,
> + FlashAddress,
> + ByteCount,
> + SfdpData
> + );
> + return Status;
> +}
> +
> +/**
> + Read Jedec Id from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] ByteCount Number of bytes in JedecId data portion of the
> SPI cycle, the data size is 3 typically
> + @param[out] JedecId The Pointer to caller-allocated buffer containing
> JEDEC ID received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadJedecId (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 ByteCount,
> + OUT UINT8 *JedecId
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + EFI_STATUS Status;
> + UINT32 Address;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> + Status = EFI_SUCCESS;
> +
> + if (ComponentNumber > SpiInstance->NumberOfComponents) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + Address = 0;
> + if (ComponentNumber == FlashComponent1) {
> + Address = SpiInstance->Component1StartAddr;
> + }
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleReadJedecId,
> + Address,
> + ByteCount,
> + JedecId
> + );
> + return Status;
> +}
> +
> +/**
> + Write the status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[in] StatusValue The Pointer to caller-allocated buffer containing
> the value of Status register writing
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWriteStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + IN UINT8 *StatusValue
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleWriteStatus,
> + 0,
> + ByteCount,
> + StatusValue
> + );
> + return Status;
> +}
> +
> +/**
> + Read status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[out] StatusValue The Pointer to caller-allocated buffer
> containing the value of Status register received.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + OUT UINT8 *StatusValue
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Sends the command to the SPI interface to execute.
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionAll,
> + FlashCycleReadStatus,
> + 0,
> + ByteCount,
> + StatusValue
> + );
> + return Status;
> +}
> +
> +/**
> + Get the SPI region base and size, based on the enum type
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for for the base
> address which is listed in the Descriptor.
> + @param[out] BaseAddress The Flash Linear Address for the Region 'n'
> Base
> + @param[out] RegionSize The size for the Region 'n'
> +
> + @retval EFI_SUCCESS Read success
> + @retval EFI_INVALID_PARAMETER Invalid region type given
> + @retval EFI_DEVICE_ERROR The region is not used
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolGetRegionAddress (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + OUT UINT32 *BaseAddress,
> + OUT UINT32 *RegionSize
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + UINTN PchSpiBar0;
> + UINT32 ReadValue;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + if (FlashRegionType >= FlashRegionMax) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + if (FlashRegionType == FlashRegionAll) {
> + *BaseAddress = 0;
> + *RegionSize = SpiInstance->TotalFlashSize;
> + return EFI_SUCCESS;
> + }
> +
> + PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
> + ReadValue = MmioRead32 (PchSpiBar0 + (R_PCH_SPI_FREG0_FLASHD +
> (S_PCH_SPI_FREGX * ((UINT32) FlashRegionType))));
> + ReleaseSpiBar0 (SpiInstance);
> +
> + //
> + // If the region is not used, the Region Base is 7FFFh and Region Limit is 0000h
> + //
> + if (ReadValue == B_PCH_SPI_FREGX_BASE_MASK) {
> + return EFI_DEVICE_ERROR;
> + }
> + *BaseAddress = ((ReadValue & B_PCH_SPI_FREGX_BASE_MASK) >>
> N_PCH_SPI_FREGX_BASE) <<
> + N_PCH_SPI_FREGX_BASE_REPR;
> + //
> + // Region limit address Bits[11:0] are assumed to be FFFh
> + //
> + *RegionSize = ((((ReadValue & B_PCH_SPI_FREGX_LIMIT_MASK) >>
> N_PCH_SPI_FREGX_LIMIT) + 1) <<
> + N_PCH_SPI_FREGX_LIMIT_REPR) - *BaseAddress;
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Read PCH Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing PCH Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadPchSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + UINT32 StrapFlashAddr;
> + EFI_STATUS Status;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + if (ByteCount == 0) {
> + *(UINT16 *) SoftStrapValue = SpiInstance->PchStrapSize;
> + return EFI_SUCCESS;
> + }
> +
> + if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->PchStrapSize) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // PCH Strap Flash Address = FPSBA + RamAddr
> + //
> + StrapFlashAddr = SpiInstance->PchStrapBaseAddr + SoftStrapAddr;
> +
> + //
> + // Read PCH Soft straps from using execute command
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionDescriptor,
> + FlashCycleRead,
> + StrapFlashAddr,
> + ByteCount,
> + SoftStrapValue
> + );
> + return Status;
> +}
> +
> +/**
> + Read CPU Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle.
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing CPU Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadCpuSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + )
> +{
> + SPI_INSTANCE *SpiInstance;
> + UINT32 StrapFlashAddr;
> + EFI_STATUS Status;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + if (ByteCount == 0) {
> + *(UINT16 *) SoftStrapValue = SpiInstance->CpuStrapSize;
> + return EFI_SUCCESS;
> + }
> +
> + if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->CpuStrapSize) {
> + ASSERT (FALSE);
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // CPU Strap Flash Address = FCPUSBA + RamAddr
> + //
> + StrapFlashAddr = SpiInstance->CpuStrapBaseAddr + SoftStrapAddr;
> +
> + //
> + // Read Cpu Soft straps from using execute command
> + //
> + Status = SendSpiCmd (
> + This,
> + FlashRegionDescriptor,
> + FlashCycleRead,
> + StrapFlashAddr,
> + ByteCount,
> + SoftStrapValue
> + );
> + return Status;
> +}
> +
> +/**
> + This function sends the programmed SPI command to the slave device.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SpiRegionType The SPI Region type for flash cycle which is
> listed in the Descriptor
> + @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware
> Sequencing Flash Control Register) register
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in,out] Buffer Pointer to caller-allocated buffer containing the
> dada received or sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS SPI command completes successfully.
> + @retval EFI_DEVICE_ERROR Device error, the command aborts
> abnormally.
> + @retval EFI_ACCESS_DENIED Some unrecognized command encountered
> in hardware sequencing mode
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> +**/
> +EFI_STATUS
> +SendSpiCmd (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN FLASH_CYCLE_TYPE FlashCycleType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN OUT UINT8 *Buffer
> + )
> +{
> + EFI_STATUS Status;
> + UINT32 Index;
> + SPI_INSTANCE *SpiInstance;
> + UINTN SpiBaseAddress;
> + UINTN PchSpiBar0;
> + UINT32 HardwareSpiAddr;
> + UINT32 FlashRegionSize;
> + UINT32 SpiDataCount;
> + UINT32 FlashCycle;
> + UINT32 SmiEnSave;
> + UINT16 ABase;
> +
> + Status = EFI_SUCCESS;
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> + SpiBaseAddress = SpiInstance->PchSpiBase;
> + PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
> + SpiBaseAddress = SpiInstance->PchSpiBase;
> + ABase = SpiInstance->PchAcpiBase;
> +
> + //
> + // Disable SMIs to make sure normal mode flash access is not interrupted by
> an SMI
> + // whose SMI handler accesses flash (e.g. for error logging)
> + //
> + // *** NOTE: if the SMI_LOCK bit is set (i.e., PMC PCI Offset A0h [4]='1'),
> + // clearing B_GBL_SMI_EN will not have effect. In this situation, some other
> + // synchronization methods must be applied here or in the consumer of the
> + // SendSpiCmd. An example method is disabling the specific SMI sources
> + // whose SMI handlers access flash before flash cycle and re-enabling the SMI
> + // sources after the flash cycle .
> + //
> + SmiEnSave = IoRead32 ((UINTN) (ABase + R_PCH_SMI_EN));
> + IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave & (UINT32)
> (~B_PCH_SMI_EN_GBL_SMI));
> +
> + //
> + // If it's write cycle, disable Prefetching, Caching and disable BIOS Write
> Protect
> + //
> + if ((FlashCycleType == FlashCycleWrite) ||
> + (FlashCycleType == FlashCycleErase)) {
> + Status = DisableBiosWriteProtect ();
> + if (EFI_ERROR (Status)) {
> + goto SendSpiCmdEnd;
> + }
> + }
> + //
> + // Make sure it's safe to program the command.
> + //
> + if (!WaitForSpiCycleComplete (This, PchSpiBar0, FALSE)) {
> + Status = EFI_DEVICE_ERROR;
> + goto SendSpiCmdEnd;
> + }
> +
> + Status = SpiProtocolGetRegionAddress (This, FlashRegionType,
> &HardwareSpiAddr, &FlashRegionSize);
> + if (EFI_ERROR (Status)) {
> + goto SendSpiCmdEnd;
> + }
> + HardwareSpiAddr += Address;
> + if ((Address + ByteCount) > FlashRegionSize) {
> + Status = EFI_INVALID_PARAMETER;
> + goto SendSpiCmdEnd;
> + }
> +
> + //
> + // Check for PCH SPI hardware sequencing required commands
> + //
> + FlashCycle = 0;
> + switch (FlashCycleType) {
> + case FlashCycleRead:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleWrite:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleErase:
> + if (((ByteCount % SIZE_4KB) != 0) ||
> + ((HardwareSpiAddr % SIZE_4KB) != 0)) {
> + ASSERT (FALSE);
> + Status = EFI_INVALID_PARAMETER;
> + goto SendSpiCmdEnd;
> + }
> + break;
> + case FlashCycleReadSfdp:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_SFDP <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleReadJedecId:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleWriteStatus:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + case FlashCycleReadStatus:
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_STATUS <<
> N_PCH_SPI_HSFSC_CYCLE);
> + break;
> + default:
> + //
> + // Unrecognized Operation
> + //
> + ASSERT (FALSE);
> + Status = EFI_INVALID_PARAMETER;
> + goto SendSpiCmdEnd;
> + break;
> + }
> +
> + do {
> + SpiDataCount = ByteCount;
> + if ((FlashCycleType == FlashCycleRead) ||
> + (FlashCycleType == FlashCycleWrite) ||
> + (FlashCycleType == FlashCycleReadSfdp)) {
> + //
> + // Trim at 256 byte boundary per operation,
> + // - PCH SPI controller requires trimming at 4KB boundary
> + // - Some SPI chips require trimming at 256 byte boundary for write
> operation
> + // - Trimming has limited performance impact as we can read / write atmost
> 64 byte
> + // per operation
> + //
> + if (HardwareSpiAddr + ByteCount > ((HardwareSpiAddr + BIT8) &~(BIT8 -
> 1))) {
> + SpiDataCount = (((UINT32) (HardwareSpiAddr) + BIT8) &~(BIT8 - 1)) -
> (UINT32) (HardwareSpiAddr);
> + }
> + //
> + // Calculate the number of bytes to shift in/out during the SPI data cycle.
> + // Valid settings for the number of bytes duing each data portion of the
> + // PCH SPI cycles are: 0, 1, 2, 3, 4, 5, 6, 7, 8, 16, 24, 32, 40, 48, 56, 64
> + //
> + if (SpiDataCount >= 64) {
> + SpiDataCount = 64;
> + } else if ((SpiDataCount &~0x07) != 0) {
> + SpiDataCount = SpiDataCount &~0x07;
> + }
> + }
> + if (FlashCycleType == FlashCycleErase) {
> + if (((ByteCount / SIZE_64KB) != 0) &&
> + ((ByteCount % SIZE_64KB) == 0) &&
> + ((HardwareSpiAddr % SIZE_64KB) == 0)) {
> + if (HardwareSpiAddr < SpiInstance->Component1StartAddr) {
> + //
> + // Check whether Component0 support 64k Erase
> + //
> + if ((SpiInstance->SfdpVscc0Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K)
> != 0) {
> + SpiDataCount = SIZE_64KB;
> + } else {
> + SpiDataCount = SIZE_4KB;
> + }
> + } else {
> + //
> + // Check whether Component1 support 64k Erase
> + //
> + if ((SpiInstance->SfdpVscc1Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K)
> != 0) {
> + SpiDataCount = SIZE_64KB;
> + } else {
> + SpiDataCount = SIZE_4KB;
> + }
> + }
> + } else {
> + SpiDataCount = SIZE_4KB;
> + }
> + if (SpiDataCount == SIZE_4KB) {
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_4K_ERASE <<
> N_PCH_SPI_HSFSC_CYCLE);
> + } else {
> + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_64K_ERASE <<
> N_PCH_SPI_HSFSC_CYCLE);
> + }
> + }
> + //
> + // If it's write cycle, load data into the SPI data buffer.
> + //
> + if ((FlashCycleType == FlashCycleWrite) || (FlashCycleType ==
> FlashCycleWriteStatus)) {
> + if ((SpiDataCount & 0x07) != 0) {
> + //
> + // Use Byte write if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
> + //
> + for (Index = 0; Index < SpiDataCount; Index++) {
> + MmioWrite8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index,
> Buffer[Index]);
> + }
> + } else {
> + //
> + // Use Dword write if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
> + //
> + for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
> + MmioWrite32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, *(UINT32 *)
> (Buffer + Index));
> + }
> + }
> + }
> +
> + //
> + // Set the Flash Address
> + //
> + MmioWrite32 (
> + (PchSpiBar0 + R_PCH_SPI_FADDR),
> + (UINT32) (HardwareSpiAddr & B_PCH_SPI_FADDR_MASK)
> + );
> +
> + //
> + // Set Data count, Flash cycle, and Set Go bit to start a cycle
> + //
> + MmioAndThenOr32 (
> + PchSpiBar0 + R_PCH_SPI_HSFSC,
> + (UINT32) (~(B_PCH_SPI_HSFSC_FDBC_MASK |
> B_PCH_SPI_HSFSC_CYCLE_MASK)),
> + (UINT32) ((((SpiDataCount - 1) << N_PCH_SPI_HSFSC_FDBC) &
> B_PCH_SPI_HSFSC_FDBC_MASK) | FlashCycle |
> B_PCH_SPI_HSFSC_CYCLE_FGO)
> + );
> + //
> + // end of command execution
> + //
> + // Wait the SPI cycle to complete.
> + //
> + if (!WaitForSpiCycleComplete (This, PchSpiBar0, TRUE)) {
> + ASSERT (FALSE);
> + Status = EFI_DEVICE_ERROR;
> + goto SendSpiCmdEnd;
> + }
> + //
> + // If it's read cycle, load data into the call's buffer.
> + //
> + if ((FlashCycleType == FlashCycleRead) ||
> + (FlashCycleType == FlashCycleReadSfdp) ||
> + (FlashCycleType == FlashCycleReadJedecId) ||
> + (FlashCycleType == FlashCycleReadStatus)) {
> + if ((SpiDataCount & 0x07) != 0) {
> + //
> + // Use Byte read if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
> + //
> + for (Index = 0; Index < SpiDataCount; Index++) {
> + Buffer[Index] = MmioRead8 (PchSpiBar0 + R_PCH_SPI_FDATA00 +
> Index);
> + }
> + } else {
> + //
> + // Use Dword read if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
> + //
> + for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
> + *(UINT32 *) (Buffer + Index) = MmioRead32 (PchSpiBar0 +
> R_PCH_SPI_FDATA00 + Index);
> + }
> + }
> + }
> +
> + HardwareSpiAddr += SpiDataCount;
> + Buffer += SpiDataCount;
> + ByteCount -= SpiDataCount;
> + } while (ByteCount > 0);
> +
> +SendSpiCmdEnd:
> + //
> + // Restore the settings for SPI Prefetching and Caching and enable BIOS Write
> Protect
> + //
> + if ((FlashCycleType == FlashCycleWrite) ||
> + (FlashCycleType == FlashCycleErase)) {
> + EnableBiosWriteProtect ();
> + }
> + //
> + // Restore SMIs.
> + //
> + IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave);
> +
> + ReleaseSpiBar0 (SpiInstance);
> + return Status;
> +}
> +
> +/**
> + Wait execution cycle to complete on the SPI interface.
> +
> + @param[in] This The SPI protocol instance
> + @param[in] PchSpiBar0 Spi MMIO base address
> + @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
> +
> + @retval TRUE SPI cycle completed on the interface.
> + @retval FALSE Time out while waiting the SPI cycle to complete.
> + It's not safe to program the next command on the SPI
> interface.
> +**/
> +BOOLEAN
> +WaitForSpiCycleComplete (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINTN PchSpiBar0,
> + IN BOOLEAN ErrorCheck
> + )
> +{
> + UINT64 WaitTicks;
> + UINT64 WaitCount;
> + UINT32 Data32;
> + SPI_INSTANCE *SpiInstance;
> +
> + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> +
> + //
> + // Convert the wait period allowed into to tick count
> + //
> + WaitCount = SPI_WAIT_TIME / SPI_WAIT_PERIOD;
> + //
> + // Wait for the SPI cycle to complete.
> + //
> + for (WaitTicks = 0; WaitTicks < WaitCount; WaitTicks++) {
> + Data32 = MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC);
> + if ((Data32 & B_PCH_SPI_HSFSC_SCIP) == 0) {
> + MmioWrite32 (PchSpiBar0 + R_PCH_SPI_HSFSC,
> B_PCH_SPI_HSFSC_FCERR | B_PCH_SPI_HSFSC_FDONE);
> + if (((Data32 & B_PCH_SPI_HSFSC_FCERR) != 0) && (ErrorCheck == TRUE)) {
> + return FALSE;
> + } else {
> + return TRUE;
> + }
> + }
> + PchPmTimerStallRuntimeSafe (SpiInstance->PchAcpiBase,
> SPI_WAIT_PERIOD);
> + }
> + return FALSE;
> +}
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> new file mode 100644
> index 0000000000..8fb4947b1a
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> @@ -0,0 +1,410 @@
> +/** @file
> + A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
> + EFI_SMM_CONTROL2_PROTOCOL.
> +
> + We expect the PEI phase to have covered the following:
> + - ensure that the underlying QEMU machine type be X58
> + (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
> + - ensure that the ACPI PM IO space be configured
> + (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
> +
> + Our own entry point is responsible for confirming the SMI feature and for
> + configuring it.
> +
> + Copyright (C) 2013, 2015, Red Hat, Inc.<BR>
> + Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include <IndustryStandard/X58Ich10.h>
> +#include <Library/BaseLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/IoLib.h>
> +#include <Library/PcdLib.h>
> +#include <Library/PciLib.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +#include <Protocol/S3SaveState.h>
> +#include <Protocol/SmmControl2.h>
> +
> +//
> +// Forward declaration.
> +//
> +STATIC
> +VOID
> +EFIAPI
> +OnS3SaveStateInstalled (
> + IN EFI_EVENT Event,
> + IN VOID *Context
> + );
> +
> +//
> +// The absolute IO port address of the SMI Control and Enable Register. It is
> +// only used to carry information from the entry point function to the
> +// S3SaveState protocol installation callback, strictly before the runtime
> +// phase.
> +//
> +STATIC UINTN mSmiEnable;
> +
> +//
> +// Event signaled when an S3SaveState protocol interface is installed.
> +//
> +STATIC EFI_EVENT mS3SaveStateInstalled;
> +
> +/**
> + Clear the SMI status
> +
> + @retval EFI_SUCCESS The function completes successfully
> + @retval EFI_DEVICE_ERROR Something error occurred
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SmmClear(
> + VOID
> +)
> +{
> + EFI_STATUS Status;
> + UINT32 OutputData;
> + UINT32 OutputPort;
> + UINT32 PmBase;
> +
> + Status = EFI_SUCCESS;
> + PmBase = ICH10_PMBASE_IO;
> +
> + OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_STS;
> + OutputData = ICH10_SMI_STS_APM;
> + IoWrite32(
> + (UINTN)OutputPort,
> + (UINT32)(OutputData)
> + );
> +
> + ///
> + /// Set the EOS Bit
> + ///
> + OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_EN;
> + OutputData = IoRead32((UINTN)OutputPort);
> + OutputData |= ICH10_SMI_EN_EOS;
> + IoWrite32(
> + (UINTN)OutputPort,
> + (UINT32)(OutputData)
> + );
> +
> + ///
> + /// There is no need to read EOS back and check if it is set.
> + /// This can lead to a reading of zero if an SMI occurs right after the SMI_EN
> port read
> + /// but before the data is returned to the CPU.
> + /// SMM Dispatcher should make sure that EOS is set after all SMI sources are
> processed.
> + ///
> + return Status;
> +}
> +
> +/**
> + Invokes SMI activation from either the preboot or runtime environment.
> +
> + This function generates an SMI.
> +
> + @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
> + @param[in,out] CommandPort The value written to the command port.
> + @param[in,out] DataPort The value written to the data port.
> + @param[in] Periodic Optional mechanism to engender a periodic
> + stream.
> + @param[in] ActivationInterval Optional parameter to repeat at this
> + period one time or, if the Periodic
> + Boolean is set, periodically.
> +
> + @retval EFI_SUCCESS The SMI/PMI has been engendered.
> + @retval EFI_DEVICE_ERROR The timing is unsupported.
> + @retval EFI_INVALID_PARAMETER The activation period is unsupported.
> + @retval EFI_INVALID_PARAMETER The last periodic activation has not been
> + cleared.
> + @retval EFI_NOT_STARTED The SMM base service has not been
> initialized.
> +**/
> +STATIC
> +EFI_STATUS
> +EFIAPI
> +SmmControl2DxeTrigger (
> + IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
> + IN OUT UINT8 *CommandPort OPTIONAL,
> + IN OUT UINT8 *DataPort OPTIONAL,
> + IN BOOLEAN Periodic OPTIONAL,
> + IN UINTN ActivationInterval OPTIONAL
> + )
> +{
> + EFI_STATUS Status;
> + //
> + // No support for queued or periodic activation.
> + //
> + if (Periodic || ActivationInterval > 0) {
> + return EFI_DEVICE_ERROR;
> + }
> + ///
> + /// Clear any pending the APM SMI
> + ///
> + Status = SmmClear();
> + //
> + // The so-called "Advanced Power Management Status Port Register" is in fact
> + // a generic data passing register, between the caller and the SMI
> + // dispatcher. The ICH9 spec calls it "scratchpad register" -- calling it
> + // "status" elsewhere seems quite the misnomer. Status registers usually
> + // report about hardware status, while this register is fully governed by
> + // software.
> + //
> + // Write to the status register first, as this won't trigger the SMI just
> + // yet. Then write to the control register.
> + //
> + IoWrite8 (ICH10_APM_STS, DataPort == NULL ? 0 : *DataPort);
> + IoWrite8 (ICH10_APM_CNT, CommandPort == NULL ? 0 : *CommandPort);
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Clears any system state that was created in response to the Trigger() call.
> +
> + This function acknowledges and causes the deassertion of the SMI activation
> + source.
> +
> + @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
> + @param[in] Periodic Optional parameter to repeat at this period
> + one time
> +
> + @retval EFI_SUCCESS The SMI/PMI has been engendered.
> + @retval EFI_DEVICE_ERROR The source could not be cleared.
> + @retval EFI_INVALID_PARAMETER The service did not support the Periodic
> input
> + argument.
> +**/
> +STATIC
> +EFI_STATUS
> +EFIAPI
> +SmmControl2DxeClear (
> + IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
> + IN BOOLEAN Periodic OPTIONAL
> + )
> +{
> + EFI_STATUS Status;
> +
> + if (Periodic) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + //
> + // The PI spec v1.4 explains that Clear() is only supposed to clear software
> + // status; it is not in fact responsible for deasserting the SMI. It gives
> + // two reasons for this: (a) many boards clear the SMI automatically when
> + // entering SMM, (b) if Clear() actually deasserted the SMI, then it could
> + // incorrectly suppress an SMI that was asynchronously asserted between the
> + // last return of the SMI handler and the call made to Clear().
> + //
> + // In fact QEMU automatically deasserts CPU_INTERRUPT_SMI in:
> + // - x86_cpu_exec_interrupt() [target-i386/seg_helper.c], and
> + // - kvm_arch_pre_run() [target-i386/kvm.c].
> + //
> + // So, nothing to do here.
> + //
> + Status = SmmClear();
> +
> + return EFI_SUCCESS;
> +}
> +
> +STATIC EFI_SMM_CONTROL2_PROTOCOL mControl2 = {
> + &SmmControl2DxeTrigger,
> + &SmmControl2DxeClear,
> + MAX_UINTN // MinimumTriggerPeriod -- we don't support periodic SMIs
> +};
> +
> +//
> +// Entry point of this driver.
> +//
> +EFI_STATUS
> +EFIAPI
> +SmmControl2DxeEntryPoint (
> + IN EFI_HANDLE ImageHandle,
> + IN EFI_SYSTEM_TABLE *SystemTable
> + )
> +{
> + UINT32 PmBase;
> + UINT32 SmiEnableVal;
> + EFI_STATUS Status;
> +
> + //
> + // This module should only be included if SMRAM support is required.
> + //
> + ASSERT (FeaturePcdGet (PcdSmmSmramRequire));
> +
> + //
> + // Calculate the absolute IO port address of the SMI Control and Enable
> + // Register. (As noted at the top, the PEI phase has left us with a working
> + // ACPI PM IO space.)
> + //
> + PmBase = PciRead32 (POWER_MGMT_REGISTER_ICH10 (ICH10_PMBASE)) &
> + ICH10_PMBASE_MASK;
> + mSmiEnable = PmBase + ICH10_PMBASE_OFS_SMI_EN;
> +
> + //
> + // If APMC_EN is pre-set in SMI_EN, that's QEMU's way to tell us that SMI
> + // support is not available. (For example due to KVM lacking it.) Otherwise,
> + // this bit is clear after each reset.
> + //
> + SmiEnableVal = IoRead32 (mSmiEnable);
> + if ((SmiEnableVal & ICH10_SMI_EN_APMC_EN) != 0) {
> + DEBUG ((EFI_D_ERROR, "%a: this X58 implementation lacks SMI\n",
> + __FUNCTION__));
> + }
> +
> + //
> + // Otherwise, configure the board to inject an SMI when ICH10_APM_CNT is
> + // written to. (See the Trigger() method above.)
> + //
> + SmiEnableVal |= ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
> + IoWrite32 (mSmiEnable, SmiEnableVal);
> +
> + //
> + // Prevent software from undoing the above (until platform reset).
> + //
> + PciOr16 (POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
> + ICH10_GEN_PMCON_1_SMI_LOCK);
> +
> + //
> + // If we can clear GBL_SMI_EN now, that means QEMU's SMI support is not
> + // appropriate.
> + //
> + IoWrite32 (mSmiEnable, SmiEnableVal &
> ~(UINT32)ICH10_SMI_EN_GBL_SMI_EN);
> + if (IoRead32 (mSmiEnable) != SmiEnableVal) {
> + DEBUG ((EFI_D_ERROR, "%a: failed to lock down GBL_SMI_EN\n",
> + __FUNCTION__));
> + goto FatalError;
> + }
> +
> + VOID *Registration;
> +
> + //
> + // On S3 resume the above register settings have to be repeated. Register a
> + // protocol notify callback that, when boot script saving becomes
> + // available, saves operations equivalent to the above to the boot script.
> + //
> + Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK,
> + OnS3SaveStateInstalled, NULL /* Context */,
> + &mS3SaveStateInstalled);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: CreateEvent: %r\n", __FUNCTION__, Status));
> + goto FatalError;
> + }
> +
> + Status = gBS->RegisterProtocolNotify (&gEfiS3SaveStateProtocolGuid,
> + mS3SaveStateInstalled, &Registration);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: RegisterProtocolNotify: %r\n",
> __FUNCTION__,
> + Status));
> + goto ReleaseEvent;
> + }
> +
> + //
> + // Kick the event right now -- maybe the boot script is already saveable.
> + //
> + Status = gBS->SignalEvent (mS3SaveStateInstalled);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: SignalEvent: %r\n", __FUNCTION__, Status));
> + goto ReleaseEvent;
> + }
> +
> + //
> + // We have no pointers to convert to virtual addresses. The handle itself
> + // doesn't matter, as protocol services are not accessible at runtime.
> + //
> + Status = gBS->InstallMultipleProtocolInterfaces (&ImageHandle,
> + &gEfiSmmControl2ProtocolGuid, &mControl2,
> + NULL);
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a: InstallMultipleProtocolInterfaces: %r\n",
> + __FUNCTION__, Status));
> + goto ReleaseEvent;
> + }
> +
> + return EFI_SUCCESS;
> +
> +ReleaseEvent:
> + if (mS3SaveStateInstalled != NULL) {
> + gBS->CloseEvent (mS3SaveStateInstalled);
> + }
> +
> +FatalError:
> + //
> + // We really don't want to continue in this case.
> + //
> + ASSERT (FALSE);
> + CpuDeadLoop ();
> + return EFI_UNSUPPORTED;
> +}
> +
> +/**
> + Notification callback for S3SaveState installation.
> +
> + @param[in] Event Event whose notification function is being invoked.
> +
> + @param[in] Context The pointer to the notification function's context, which
> + is implementation-dependent.
> +**/
> +STATIC
> +VOID
> +EFIAPI
> +OnS3SaveStateInstalled (
> + IN EFI_EVENT Event,
> + IN VOID *Context
> + )
> +{
> + EFI_STATUS Status;
> + EFI_S3_SAVE_STATE_PROTOCOL *S3SaveState;
> + UINT32 SmiEnOrMask, SmiEnAndMask;
> + UINT16 GenPmCon1OrMask, GenPmCon1AndMask;
> +
> + ASSERT (Event == mS3SaveStateInstalled);
> +
> + Status = gBS->LocateProtocol (&gEfiS3SaveStateProtocolGuid,
> + NULL /* Registration */, (VOID **)&S3SaveState);
> + if (EFI_ERROR (Status)) {
> + return;
> + }
> +
> + //
> + // These operations were originally done, verified and explained in the entry
> + // point function of the driver.
> + //
> + SmiEnOrMask = ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
> + SmiEnAndMask = MAX_UINT32;
> + Status = S3SaveState->Write (
> + S3SaveState,
> + EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE,
> + EfiBootScriptWidthUint32,
> + (UINT64)mSmiEnable,
> + &SmiEnOrMask,
> + &SmiEnAndMask
> + );
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR, "%a:
> EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE: %r\n",
> + __FUNCTION__, Status));
> + ASSERT (FALSE);
> + CpuDeadLoop ();
> + }
> +
> + GenPmCon1OrMask = ICH10_GEN_PMCON_1_SMI_LOCK;
> + GenPmCon1AndMask = MAX_UINT16;
> + Status = S3SaveState->Write (
> + S3SaveState,
> + EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE,
> + EfiBootScriptWidthUint16,
> + (UINT64)POWER_MGMT_REGISTER_ICH10
> (ICH10_GEN_PMCON_1),
> + &GenPmCon1OrMask,
> + &GenPmCon1AndMask
> + );
> + if (EFI_ERROR (Status)) {
> + DEBUG ((EFI_D_ERROR,
> + "%a: EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE: %r\n",
> __FUNCTION__,
> + Status));
> + ASSERT (FALSE);
> + CpuDeadLoop ();
> + }
> +
> + DEBUG ((EFI_D_VERBOSE, "%a: boot script fragment saved\n",
> __FUNCTION__));
> + gBS->CloseEvent (Event);
> + mS3SaveStateInstalled = NULL;
> +}
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> new file mode 100644
> index 0000000000..19eb469657
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> @@ -0,0 +1,175 @@
> +/** @file
> + PCH SPI SMM Driver implements the SPI Host Controller Compatibility
> Interface.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#include "PchSpi.h"
> +
> +//
> +// Global variables
> +//
> +GLOBAL_REMOVE_IF_UNREFERENCED SPI_INSTANCE *mSpiInstance;
> +//
> +// mPchSpiResvMmioAddr keeps the reserved MMIO range assiged to SPI.
> +// In SMM it always set back the reserved MMIO address to SPI BAR0 to ensure
> the MMIO range
> +// won't overlap with SMRAM range, and trusted.
> +//
> +GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mSpiResvMmioAddr;
> +
> +/**
> + <b>SPI Runtime SMM Module Entry Point</b>\n
> + - <b>Introduction</b>\n
> + The SPI SMM module provide a standard way for other modules to use the
> PCH SPI Interface in SMM.
> +
> + - @pre
> + - EFI_SMM_BASE2_PROTOCOL
> + - Documented in System Management Mode Core Interface Specification .
> +
> + - @result
> + The SPI SMM driver produces @link _PCH_SPI_PROTOCOL
> PCH_SPI_PROTOCOL @endlink with GUID
> + gPchSmmSpiProtocolGuid which is different from SPI RUNTIME driver.
> +
> + - <b>Integration Check List</b>\n
> + - This driver supports Descriptor Mode only.
> + - This driver supports Hardware Sequence only.
> + - When using SMM SPI Protocol to perform flash access in an SMI handler,
> + and the SMI occurrence is asynchronous to normal mode code execution,
> + proper synchronization mechanism must be applied, e.g. disable SMI before
> + the normal mode SendSpiCmd() starts and re-enable SMI after
> + the normal mode SendSpiCmd() completes.
> + @note The implementation of SendSpiCmd() uses GBL_SMI_EN in
> + SMI_EN register (ABase + 30h) to disable and enable SMIs. But this may
> + not be effective as platform may well set the SMI_LOCK bit (i.e., PMC PCI
> Offset A0h [4]).
> + So the synchronization at caller level is likely needed.
> +
> + @param[in] ImageHandle Image handle of this driver.
> + @param[in] SystemTable Global system service table.
> +
> + @retval EFI_SUCCESS Initialization complete.
> + @exception EFI_UNSUPPORTED The chipset is unsupported by this driver.
> + @retval EFI_OUT_OF_RESOURCES Do not have enough resources to
> initialize the driver.
> + @retval EFI_DEVICE_ERROR Device error, driver exits abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +InstallPchSpi (
> + IN EFI_HANDLE ImageHandle,
> + IN EFI_SYSTEM_TABLE *SystemTable
> + )
> +{
> + EFI_STATUS Status;
> +
> + //
> + // Init PCH spi reserved MMIO address.
> + //
> + mSpiResvMmioAddr = PCH_SPI_BASE_ADDRESS;
> +
> + ///
> + /// Allocate pool for SPI protocol instance
> + ///
> + Status = gSmst->SmmAllocatePool (
> + EfiRuntimeServicesData, /// MemoryType don't care
> + sizeof (SPI_INSTANCE),
> + (VOID **) &mSpiInstance
> + );
> + if (EFI_ERROR (Status)) {
> + return Status;
> + }
> +
> + if (mSpiInstance == NULL) {
> + return EFI_OUT_OF_RESOURCES;
> + }
> +
> + ZeroMem ((VOID *) mSpiInstance, sizeof (SPI_INSTANCE));
> + ///
> + /// Initialize the SPI protocol instance
> + ///
> + Status = SpiProtocolConstructor (mSpiInstance);
> + if (EFI_ERROR (Status)) {
> + return Status;
> + }
> + //
> + // Install the SMM EFI_SPI_PROTOCOL interface
> + //
> + Status = gSmst->SmmInstallProtocolInterface (
> + &(mSpiInstance->Handle),
> + &gEfiSmmSpiProtocolGuid,
> + EFI_NATIVE_INTERFACE,
> + &(mSpiInstance->SpiProtocol)
> + );
> + if (EFI_ERROR (Status)) {
> + gSmst->SmmFreePool (mSpiInstance);
> + return EFI_DEVICE_ERROR;
> + }
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + Acquire PCH spi mmio address.
> + It is not expected for this BAR0 to change because the SPI device is hidden
> + from the OS for SKL PCH LP/H B stepping and above (refer to section 3.5.1),
> + but if it is ever different from the preallocated address, reassign it back.
> + In SMM, it always override the BAR0 and returns the reserved MMIO range
> for SPI.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval PchSpiBar0 return SPI MMIO address
> +**/
> +UINTN
> +AcquireSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + )
> +{
> + //
> + // SPIBAR0 will be different before and after PCI enum so need to get it from
> SPI BAR0 reg.
> + //
> + return mSpiResvMmioAddr;
> +}
> +
> +/**
> + Release pch spi mmio address. Do nothing.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval None
> +**/
> +VOID
> +ReleaseSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + )
> +{
> +}
> +
> +/**
> + This function is a hook for Spi to disable BIOS Write Protect
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in
> SMM phase
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +DisableBiosWriteProtect (
> + VOID
> + )
> +{
> +
> + return EFI_SUCCESS;
> +}
> +
> +/**
> + This function is a hook for Spi to enable BIOS Write Protect
> +
> +
> +**/
> +VOID
> +EFIAPI
> +EnableBiosWriteProtect (
> + VOID
> + )
> +{
> +}
> diff --git a/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> new file mode 100644
> index 0000000000..f9d340d6df
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> @@ -0,0 +1,22 @@
> +## @file
> +# Copyright (c) 2014 - 2016 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + DEC_SPECIFICATION = 0x00010005
> + PACKAGE_NAME = ICH10Pkg
> + PACKAGE_GUID = 4E97AC4B-F64C-4008-BBDE-01CC3B0BAA6B
> + PACKAGE_VERSION = 0.91
> +
> +[Includes]
> + Include
> +
> +[Ppis]
> +
> +[Guids]
> + gEfiPchTokenSpaceGuid = { 0x89a1b278, 0xa1a1, 0x4df7, { 0xb1, 0x37, 0xde,
> 0x5a, 0xd7, 0xc4, 0x79, 0x13 } }
> +[Protocols]
> + gEfiSmmSpiProtocolGuid = {0xbd75fe35, 0xfdce, 0x49d7, {0xa9, 0xdd, 0xb2,
> 0x6f, 0x1f, 0xc6, 0xb4, 0x37}}
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> new file mode 100644
> index 0000000000..c36360bcb0
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> @@ -0,0 +1,98 @@
> +/** @file
> + The header file includes the common header files, defines
> + internal structure and functions used by SpiFlashCommonLib.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef __SPI_FLASH_COMMON_LIB_H__
> +#define __SPI_FLASH_COMMON_LIB_H__
> +
> +#include <Uefi.h>
> +#include <Library/BaseLib.h>
> +#include <Library/PcdLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <Library/MemoryAllocationLib.h>
> +#include <Library/UefiDriverEntryPoint.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +
> +#define SECTOR_SIZE_4KB 0x1000 // Common 4kBytes sector size
> +/**
> + Enable block protection on the Serial Flash device.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashLock (
> + VOID
> + );
> +
> +/**
> + Read NumBytes bytes of data from the address specified by
> + PAddress into Buffer.
> +
> + @param[in] Address The starting physical address of the read.
> + @param[in,out] NumBytes On input, the number of bytes to read. On
> output, the number
> + of bytes actually read.
> + @param[out] Buffer The destination data buffer for the read.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashRead (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + OUT UINT8 *Buffer
> + );
> +
> +/**
> + Write NumBytes bytes of data from Buffer to the address specified by
> + PAddresss.
> +
> + @param[in] Address The starting physical address of the write.
> + @param[in,out] NumBytes On input, the number of bytes to write. On
> output,
> + the actual number of bytes written.
> + @param[in] Buffer The source data buffer for the write.
> +
> + @retval EFI_SUCCESS Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashWrite (
> + IN UINTN Address,
> + IN OUT UINT32 *NumBytes,
> + IN UINT8 *Buffer
> + );
> +
> +/**
> + Erase the block starting at Address.
> +
> + @param[in] Address The starting physical address of the block to be
> erased.
> + This library assume that caller garantee that the PAddress
> + is at the starting address of this block.
> + @param[in] NumBytes On input, the number of bytes of the logical block
> to be erased.
> + On output, the actual number of bytes erased.
> +
> + @retval EFI_SUCCESS. Opertion is successful.
> + @retval EFI_DEVICE_ERROR If there is any device errors.
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiFlashBlockErase (
> + IN UINTN Address,
> + IN UINTN *NumBytes
> + );
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> new file mode 100644
> index 0000000000..552ce28d8c
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> @@ -0,0 +1,43 @@
> +/** @file
> + Macros that simplify accessing PCH devices's PCI registers.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_ACCESS_H_
> +#define _PCH_ACCESS_H_
> +
> +#include "PchReservedResources.h"
> +
> +#ifndef STALL_ONE_MICRO_SECOND
> +#define STALL_ONE_MICRO_SECOND 1
> +#endif
> +#ifndef STALL_ONE_SECOND
> +#define STALL_ONE_SECOND 1000000
> +#endif
> +
> +
> +///
> +/// The default PCH PCI bus number
> +///
> +#define DEFAULT_PCI_BUS_NUMBER_PCH 0
> +
> +//
> +// Default Vendor ID and Subsystem ID
> +//
> +#define V_PCH_INTEL_VENDOR_ID 0x8086 ///< Default Intel PCH Vendor
> ID
> +#define V_PCH_DEFAULT_SID 0x7270 ///< Default Intel PCH Subsystem
> ID
> +#define V_PCH_DEFAULT_SVID_SID (V_INTEL_VENDOR_ID +
> (V_PCH_DEFAULT_SID << 16)) ///< Default INTEL PCH Vendor ID and
> Subsystem ID
> +
> +//
> +// Include device register definitions
> +//
> +
> +#include "Register/PchRegsPmc.h"
> +
> +#include "Register/PchRegsSpi.h"
> +
> +#endif
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> new file mode 100644
> index 0000000000..d503d130c8
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> @@ -0,0 +1,94 @@
> +/** @file
> + Build time limits of PCH resources.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_LIMITS_H_
> +#define _PCH_LIMITS_H_
> +
> +//
> +// PCIe limits
> +//
> +#define PCH_MAX_PCIE_ROOT_PORTS
> PCH_H_PCIE_MAX_ROOT_PORTS
> +#define PCH_H_PCIE_MAX_ROOT_PORTS 20
> +#define PCH_LP_PCIE_MAX_ROOT_PORTS 12
> +
> +#define PCH_MAX_PCIE_CONTROLLERS
> PCH_H_PCIE_MAX_CONTROLLERS
> +#define PCH_PCIE_CONTROLLER_PORTS 4
> +#define PCH_H_PCIE_MAX_CONTROLLERS
> (PCH_H_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
> +#define PCH_LP_PCIE_MAX_CONTROLLERS
> (PCH_LP_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
> +
> +//
> +// PCIe clocks limits
> +//
> +#define PCH_LP_PCIE_MAX_CLK_REQ 6
> +#define PCH_H_PCIE_MAX_CLK_REQ 16
> +
> +//
> +// RST PCIe Storage Cycle Router limits
> +//
> +#define PCH_MAX_RST_PCIE_STORAGE_CR 3
> +
> +//
> +// SATA limits
> +//
> +#define PCH_MAX_SATA_PORTS PCH_H_AHCI_MAX_PORTS
> +#define PCH_H_AHCI_MAX_PORTS 8 ///< Max number of sata
> ports in SKL PCH H
> +#define PCH_LP_AHCI_MAX_PORTS 3 ///< Max number of sata
> ports in SKL PCH LP
> +#define PCH_SATA_MAX_DEVICES_PER_PORT 1 ///< Max support
> device numner per port, Port Multiplier is not support.
> +
> +//
> +// USB limits
> +//
> +#define PCH_MAX_USB2_PORTS PCH_H_XHCI_MAX_USB2_PORTS
> +
> +#define PCH_H_XHCI_MAX_USB2_PHYSICAL_PORTS 14 ///< Max Physical
> Connector XHCI, not counting virtual ports like USB-R.
> +#define PCH_LP_XHCI_MAX_USB2_PHYSICAL_PORTS 10 ///< Max Physical
> Connector XHCI, not counting virtual ports like USB-R.
> +
> +#define PCH_H_XHCI_MAX_USB2_PORTS 16 ///< 14 High Speed lanes
> + Including two ports reserved for USBr
> +#define PCH_LP_XHCI_MAX_USB2_PORTS 12 ///< 10 High Speed lanes
> + Including two ports reserved for USBr
> +
> +#define PCH_MAX_USB3_PORTS PCH_H_XHCI_MAX_USB3_PORTS
> +
> +#define PCH_H_XHCI_MAX_USB3_PORTS 10 ///< 10 Super Speed
> lanes
> +#define PCH_LP_XHCI_MAX_USB3_PORTS 6 ///< 6 Super Speed lanes
> +
> +#define PCH_XHCI_MAX_SSIC_PORT_COUNT 2 ///< 2 SSIC ports in SKL
> PCH-LP and SKL PCH-H
> +
> +//
> +// SerialIo limits
> +//
> +#define PCH_SERIALIO_MAX_CONTROLLERS 11 ///< Number of SerialIo
> controllers, this includes I2C, SPI and UART
> +#define PCH_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo
> I2C controllers
> +#define PCH_LP_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of
> SerialIo I2C controllers for PCH-LP
> +#define PCH_H_SERIALIO_MAX_I2C_CONTROLLERS 4 ///< Number of
> SerialIo I2C controllers for PCH-H
> +#define PCH_SERIALIO_MAX_SPI_CONTROLLERS 2 ///< Number of SerialIo
> SPI controllers
> +#define PCH_SERIALIO_MAX_UART_CONTROLLERS 3 ///< Number of
> SerialIo UART controllers
> +
> +//
> +// ISH limits
> +//
> +#define PCH_ISH_MAX_GP_PINS 8
> +#define PCH_ISH_MAX_UART_CONTROLLERS 2
> +#define PCH_ISH_MAX_I2C_CONTROLLERS 3
> +#define PCH_ISH_MAX_SPI_CONTROLLERS 1
> +
> +//
> +// SCS limits
> +//
> +#define PCH_SCS_MAX_CONTROLLERS 3 ///< Number of Storage and
> Communication Subsystem controllers, this includes eMMC, SDIO, SDCARD
> +
> +//
> +// Flash Protection Range Register
> +//
> +#define PCH_FLASH_PROTECTED_RANGES 5
> +
> +//
> +// Number of eSPI slaves
> +//
> +#define PCH_ESPI_MAX_SLAVE_ID 2
> +#endif // _PCH_LIMITS_H_
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> new file mode 100644
> index 0000000000..00139fc230
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> @@ -0,0 +1,60 @@
> +/** @file
> + PCH preserved MMIO resource definitions.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_PRESERVED_RESOURCES_H_
> +#define _PCH_PRESERVED_RESOURCES_H_
> +
> +/**
> + PCH preserved MMIO range, 24 MB, from 0xFD000000 to 0xFE7FFFFF
> +
> + Detailed recommended static allocation
> + +-------------------------------------------------------------------------+
> + | Size | Start | End | Usage |
> + | 16 MB | 0xFD000000 | 0xFDFFFFFF | SBREG |
> + | 64 KB | 0xFE000000 | 0xFE00FFFF | PMC MBAR |
> + | 4 KB | 0xFE010000 | 0xFE010FFF | SPI BAR0 |
> + | 88 KB | 0xFE020000 | 0xFE035FFF | SerialIo BAR in ACPI mode |
> + | 24 KB | 0xFE036000 | 0xFE03BFFF | Unused |
> + | 4 KB | 0xFE03C000 | 0xFE03CFFF | Thermal Device in ACPI mode |
> + | 524 KB | 0xFE03D000 | 0xFE0BFFFF | Unused |
> + | 256 KB | 0xFE0C0000 | 0xFE0FFFFF | TraceHub FW BAR |
> + | 1 MB | 0xFE100000 | 0xFE1FFFFF | TraceHub MTB BAR |
> + | 2 MB | 0xFE200000 | 0xFE3FFFFF | TraceHub SW BAR |
> + | 64 KB | 0xFE400000 | 0xFE40FFFF | CIO2 MMIO BAR in ACPI mode |
> + | 2 MB - 64KB | 0xFE410000 | 0xFE5FFFFF | Unused |
> + | 2 MB | 0xFE600000 | 0xFE7FFFFF | Temp address |
> + +-------------------------------------------------------------------------+
> +**/
> +#define PCH_PRESERVED_BASE_ADDRESS 0xFD000000 ///< Pch
> preserved MMIO base address
> +#define PCH_PRESERVED_MMIO_SIZE 0x01800000 ///< 24MB
> +#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO
> base address
> +#define PCH_PCR_MMIO_SIZE 0x01000000 ///< 16MB
> +#define PCH_PWRM_BASE_ADDRESS 0xFE000000 ///< PMC MBAR
> MMIO base address
> +#define PCH_PWRM_MMIO_SIZE 0x00010000 ///< 64KB
> +#define PCH_SPI_BASE_ADDRESS 0xFED1C000 + 0x3800 ///< SPI
> MBAR MMIO base address
> +#define PCH_SPI_MMIO_SIZE 0x00001000 ///< 4KB
> +#define PCH_SERIAL_IO_BASE_ADDRESS 0xFE020000 ///< SerialIo MMIO
> base address
> +#define PCH_SERIAL_IO_MMIO_SIZE 0x00016000 ///< 88KB
> +#define PCH_THERMAL_BASE_ADDRESS 0xFE03C000 ///< Thermal
> Device in ACPI mode
> +#define PCH_THERMAL_MMIO_SIZE 0x00001000 ///< 4KB
> +#define PCH_TRACE_HUB_FW_BASE_ADDRESS 0xFE0C0000 ///< TraceHub
> FW MMIO base address
> +#define PCH_TRACE_HUB_FW_MMIO_SIZE 0x00040000 ///< 256KB
> +#define PCH_TRACE_HUB_MTB_BASE_ADDRESS 0xFE100000 ///<
> TraceHub MTB MMIO base address
> +#define PCH_TRACE_HUB_MTB_MMIO_SIZE 0x00100000 ///< 1MB
> +#define PCH_TRACE_HUB_SW_BASE_ADDRESS 0xFE200000 ///< TraceHub
> SW MMIO base address
> +#define PCH_TRACE_HUB_SW_MMIO_SIZE 0x00200000 ///< 2MB
> +#define PCH_CIO2_BASE_ADDRESS 0xFE400000 ///< CIO2 MMIO BAR
> in ACPI mode
> +#define PCH_CIO2_MMIO_SIZE 0x00010000 ///< 64KB
> +#define PCH_TEMP_BASE_ADDRESS 0xFE600000 ///< preserved temp
> address for misc usage
> +#define PCH_TEMP_MMIO_SIZE 0x00200000 ///< 2MB
> +
> +#define RCRB 0xFED1C000
> +#define SPIBAR 0x3800
> +
> +#endif // _PCH_PRESERVED_RESOURCES_H_
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> new file mode 100644
> index 0000000000..cb5f26c47b
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> @@ -0,0 +1,295 @@
> +/** @file
> + This file defines the PCH SPI Protocol which implements the
> + Intel(R) PCH SPI Host Controller Compatibility Interface.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_SPI_PROTOCOL_H_
> +#define _PCH_SPI_PROTOCOL_H_
> +
> +//
> +// Extern the GUID for protocol users.
> +//
> +extern EFI_GUID gEfiSpiProtocolGuid;
> +extern EFI_GUID gEfiSmmSpiProtocolGuid;
> +
> +//
> +// Forward reference for ANSI C compatibility
> +//
> +typedef struct _PCH_SPI_PROTOCOL EFI_SPI_PROTOCOL;
> +
> +//
> +// SPI protocol data structures and definitions
> +//
> +
> +/**
> + Flash Region Type
> +**/
> +typedef enum {
> + FlashRegionDescriptor,
> + FlashRegionBios,
> + FlashRegionMe,
> + FlashRegionGbE,
> + FlashRegionPlatformData,
> + FlashRegionDer,
> + FlashRegionAll,
> + FlashRegionMax
> +} FLASH_REGION_TYPE;
> +
> +
> +//
> +// Protocol member functions
> +//
> +
> +/**
> + Read data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[out] Buffer The Pointer to caller-allocated buffer containing
> the dada received.
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *Buffer
> + );
> +
> +/**
> + Write data to the flash part. Remark: Erase may be needed before write to the
> flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in] Buffer Pointer to caller-allocated buffer containing the
> data sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_WRITE) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN UINT8 *Buffer
> + );
> +
> +/**
> + Erase some area on the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_ERASE) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount
> + );
> +
> +/**
> + Read SFDP data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] Address The starting byte address for SFDP data read.
> + @param[in] ByteCount Number of bytes in SFDP data portion of the SPI
> cycle
> + @param[out] SfdpData The Pointer to caller-allocated buffer containing
> the SFDP data received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ_SFDP) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *SfdpData
> + );
> +
> +/**
> + Read Jedec Id from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] ByteCount Number of bytes in JedecId data portion of the
> SPI cycle, the data size is 3 typically
> + @param[out] JedecId The Pointer to caller-allocated buffer containing
> JEDEC ID received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ_JEDEC_ID) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 ByteCount,
> + OUT UINT8 *JedecId
> + );
> +
> +/**
> + Write the status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[in] StatusValue The Pointer to caller-allocated buffer containing
> the value of Status register writing
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_WRITE_STATUS) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + IN UINT8 *StatusValue
> + );
> +
> +/**
> + Read status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[out] StatusValue The Pointer to caller-allocated buffer
> containing the value of Status register received.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_FLASH_READ_STATUS) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + OUT UINT8 *StatusValue
> + );
> +
> +/**
> + Get the SPI region base and size, based on the enum type
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for for the base
> address which is listed in the Descriptor.
> + @param[out] BaseAddress The Flash Linear Address for the Region 'n'
> Base
> + @param[out] RegionSize The size for the Region 'n'
> +
> + @retval EFI_SUCCESS Read success
> + @retval EFI_INVALID_PARAMETER Invalid region type given
> + @retval EFI_DEVICE_ERROR The region is not used
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_GET_REGION_ADDRESS) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + OUT UINT32 *BaseAddress,
> + OUT UINT32 *RegionSize
> + );
> +
> +/**
> + Read PCH Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing PCH Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_READ_PCH_SOFTSTRAP) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + Read CPU Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle.
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing CPU Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +typedef
> +EFI_STATUS
> +(EFIAPI *PCH_SPI_READ_CPU_SOFTSTRAP) (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + These protocols/PPI allows a platform module to perform SPI operations
> through the
> + Intel PCH SPI Host Controller Interface.
> +**/
> +struct _PCH_SPI_PROTOCOL {
> + /**
> + This member specifies the revision of this structure. This field is used to
> + indicate backwards compatible changes to the protocol.
> + **/
> + UINT8 Revision;
> + PCH_SPI_FLASH_READ FlashRead; ///< Read data from the flash
> part.
> + PCH_SPI_FLASH_WRITE FlashWrite; ///< Write data to the flash
> part. Remark: Erase may be needed before write to the flash part.
> + PCH_SPI_FLASH_ERASE FlashErase; ///< Erase some area on the
> flash part.
> + PCH_SPI_FLASH_READ_SFDP FlashReadSfdp; ///< Read SFDP data
> from the flash part.
> + PCH_SPI_FLASH_READ_JEDEC_ID FlashReadJedecId; ///< Read Jedec Id
> from the flash part.
> + PCH_SPI_FLASH_WRITE_STATUS FlashWriteStatus; ///< Write the status
> register in the flash part.
> + PCH_SPI_FLASH_READ_STATUS FlashReadStatus; ///< Read status
> register in the flash part.
> + PCH_SPI_GET_REGION_ADDRESS GetRegionAddress; ///< Get the SPI
> region base and size
> + PCH_SPI_READ_PCH_SOFTSTRAP ReadPchSoftStrap; ///< Read PCH Soft
> Strap Values
> + PCH_SPI_READ_CPU_SOFTSTRAP ReadCpuSoftStrap; ///< Read CPU Soft
> Strap Values
> +};
> +
> +/**
> + PCH SPI PPI/PROTOCOL revision number
> +
> + Revision 1: Initial version
> +**/
> +#define PCH_SPI_SERVICES_REVISION 1
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> new file mode 100644
> index 0000000000..e08721f405
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> @@ -0,0 +1,647 @@
> +/** @file
> + Register names for PCH PMC device
> +
> + Conventions:
> +
> + - Prefixes:
> + Definitions beginning with "R_" are registers
> + Definitions beginning with "B_" are bits within registers
> + Definitions beginning with "V_" are meaningful values within the bits
> + Definitions beginning with "S_" are register sizes
> + Definitions beginning with "N_" are the bit position
> + - In general, PCH registers are denoted by "_PCH_" in register names
> + - Registers / bits that are different between PCH generations are denoted by
> + "_PCH_[generation_name]_" in register/bit names.
> + - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit
> names.
> + Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit
> names.
> + e.g., "_PCH_H_", "_PCH_LP_"
> + Registers / bits names without _H_ or _LP_ apply for both H and LP.
> + - Registers / bits that are different between SKUs are denoted by
> "_[SKU_name]"
> + at the end of the register/bit names
> + - Registers / bits of new devices introduced in a PCH generation will be just
> named
> + as "_PCH_" without [generation_name] inserted.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_REGS_PMC_H_
> +#define _PCH_REGS_PMC_H_
> +
> +//
> +// PMC Registers (D31:F2)
> +//
> +#define PCI_DEVICE_NUMBER_PCH_PMC 31
> +#define PCI_FUNCTION_NUMBER_PCH_PMC 2
> +
> +#define R_PCH_PMC_PM_DATA_BAR 0x10
> +#define B_PCH_PMC_PM_DATA_BAR 0xFFFFC000
> +#define R_PCH_PMC_ACPI_BASE 0x40
> +#define B_PCH_PMC_ACPI_BASE_BAR 0xFFFC
> +#define R_PCH_PMC_ACPI_CNT 0x44
> +#define B_PCH_PMC_ACPI_CNT_PWRM_EN BIT8
> ///< PWRM enable
> +#define B_PCH_PMC_ACPI_CNT_ACPI_EN BIT7 ///<
> ACPI eanble
> +#define B_PCH_PMC_ACPI_CNT_SCIS (BIT2 | BIT1 | BIT0)
> ///< SCI IRQ select
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ9 0
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ10 1
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ11 2
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ20 4
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ21 5
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ22 6
> +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ23 7
> +#define R_PCH_PMC_PWRM_BASE 0x48
> +#define B_PCH_PMC_PWRM_BASE_BAR 0xFFFF0000
> ///< PWRM must be 64KB alignment to align the source decode.
> +#define R_PCH_PMC_GEN_PMCON_A 0xA0
> +#define B_PCH_PMC_GEN_PMCON_A_DC_PP_DIS BIT30
> +#define B_PCH_PMC_GEN_PMCON_A_DSX_PP_DIS BIT29
> +#define B_PCH_PMC_GEN_PMCON_A_AG3_PP_EN BIT28
> +#define B_PCH_PMC_GEN_PMCON_A_SX_PP_EN BIT27
> +#define B_PCH_PMC_GEN_PMCON_A_DISB BIT23
> +#define B_PCH_PMC_GEN_PMCON_A_MEM_SR BIT21
> +#define B_PCH_PMC_GEN_PMCON_A_MS4V BIT18
> +#define B_PCH_PMC_GEN_PMCON_A_GBL_RST_STS BIT16
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_OPI_PLL_SD_INC0 BIT13
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_SPXB_CG_INC0 BIT12
> +#define B_PCH_PMC_GEN_PMCON_A_BIOS_PCI_EXP_EN BIT10
> +#define B_PCH_PMC_GEN_PMCON_A_PWRBTN_LVL BIT9
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_C0 BIT7
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_OPI_ON BIT6
> +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_BCLKREQ_ON
> BIT5
> +#define B_PCH_PMC_GEN_PMCON_A_SMI_LOCK BIT4
> +#define B_PCH_PMC_GEN_PMCON_A_ESPI_SMI_LOCK BIT3
> ///< ESPI SMI lock
> +#define B_PCH_PMC_GEN_PMCON_A_PER_SMI_SEL 0x0003
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_64S 0x0000
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_32S 0x0001
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_16S 0x0002
> +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_8S 0x0003
> +#define R_PCH_PMC_GEN_PMCON_B 0xA4
> +#define B_PCH_PMC_GEN_PMCON_B_SLPSX_STR_POL_LOCK BIT18
> ///< Lock down SLP_S3/SLP_S4 Minimum Assertion width
> +#define B_PCH_PMC_GEN_PMCON_B_ACPI_BASE_LOCK BIT17
> ///< Lock ACPI BASE at 0x40, only cleared by reset when set
> +#define B_PCH_PMC_GEN_PMCON_B_PM_DATA_BAR_DIS BIT16
> +#define B_PCH_PMC_GEN_PMCON_B_PME_B0_S5_DIS BIT15
> +#define B_PCH_PMC_GEN_PMCON_B_SUS_PWR_FLR BIT14
> +#define B_PCH_PMC_GEN_PMCON_B_WOL_EN_OVRD BIT13
> +#define B_PCH_PMC_GEN_PMCON_B_DISABLE_SX_STRETCH BIT12
> +#define B_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW 0xC00
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_60US 0x000
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_1MS 0x400
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_50MS 0x800
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_2S 0xC00
> +#define B_PCH_PMC_GEN_PMCON_B_HOST_RST_STS BIT9
> +#define B_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL 0xC0
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_64MS 0xC0
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_32MS 0x80
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_16MS 0x40
> +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_1_5MS 0x00
> +#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW 0x30
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_1S 0x30
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_2S 0x20
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_3S 0x10
> +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_4S 0x00
> +#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_ASE BIT3
> +#define B_PCH_PMC_GEN_PMCON_B_RTC_PWR_STS BIT2
> +#define B_PCH_PMC_GEN_PMCON_B_PWR_FLR BIT1
> +#define B_PCH_PMC_GEN_PMCON_B_AFTERG3_EN BIT0
> +#define R_PCH_PMC_BM_CX_CNF 0xA8
> +#define B_PCH_PMC_BM_CX_CNF_STORAGE_BREAK_EN BIT31
> +#define B_PCH_PMC_BM_CX_CNF_PCIE_BREAK_EN BIT30
> +#define B_PCH_PMC_BM_CX_CNF_AZ_BREAK_EN BIT24
> +#define B_PCH_PMC_BM_CX_CNF_DPSN_BREAK_EN BIT19
> +#define B_PCH_PMC_BM_CX_CNF_XHCI_BREAK_EN BIT17
> +#define B_PCH_PMC_BM_CX_CNF_SATA3_BREAK_EN BIT16
> +#define B_PCH_PMC_BM_CX_CNF_SCRATCHPAD BIT15
> +#define B_PCH_PMC_BM_CX_CNF_PHOLD_BM_STS_BLOCK BIT14
> +#define B_PCH_PMC_BM_CX_CNF_MASK_CF BIT11
> +#define B_PCH_PMC_BM_CX_CNF_BM_STS_ZERO_EN BIT10
> +#define B_PCH_PMC_BM_CX_CNF_PM_SYNC_MSG_MODE BIT9
> +#define R_PCH_PMC_ETR3 0xAC
> +#define B_PCH_PMC_ETR3_CF9LOCK BIT31 ///< CF9h
> Lockdown
> +#define B_PCH_PMC_ETR3_USB_CACHE_DIS BIT21
> +#define B_PCH_PMC_ETR3_CF9GR BIT20 ///< CF9h
> Global Reset
> +#define B_PCH_PMC_ETR3_SKIP_HOST_RST_HS BIT19
> +#define B_PCH_PMC_ETR3_CWORWRE BIT18
> +
> +//
> +// ACPI and legacy I/O register offsets from ACPIBASE
> +//
> +#define R_PCH_ACPI_PM1_STS 0x00
> +#define S_PCH_ACPI_PM1_STS 2
> +#define B_PCH_ACPI_PM1_STS_WAK BIT15
> +#define B_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS BIT14
> +#define B_PCH_ACPI_PM1_STS_PRBTNOR BIT11
> +#define B_PCH_ACPI_PM1_STS_RTC BIT10
> +#define B_PCH_ACPI_PM1_STS_PWRBTN BIT8
> +#define B_PCH_ACPI_PM1_STS_GBL BIT5
> +#define B_PCH_ACPI_PM1_STS_BM BIT4
> +#define B_PCH_ACPI_PM1_STS_TMROF BIT0
> +#define N_PCH_ACPI_PM1_STS_WAK 15
> +#define N_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS 14
> +#define N_PCH_ACPI_PM1_STS_PRBTNOR 11
> +#define N_PCH_ACPI_PM1_STS_RTC 10
> +#define N_PCH_ACPI_PM1_STS_PWRBTN 8
> +#define N_PCH_ACPI_PM1_STS_GBL 5
> +#define N_PCH_ACPI_PM1_STS_BM 4
> +#define N_PCH_ACPI_PM1_STS_TMROF 0
> +
> +#define R_PCH_ACPI_PM1_EN 0x02
> +#define S_PCH_ACPI_PM1_EN 2
> +#define B_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS BIT14
> +#define B_PCH_ACPI_PM1_EN_RTC BIT10
> +#define B_PCH_ACPI_PM1_EN_PWRBTN BIT8
> +#define B_PCH_ACPI_PM1_EN_GBL BIT5
> +#define B_PCH_ACPI_PM1_EN_TMROF BIT0
> +#define N_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS 14
> +#define N_PCH_ACPI_PM1_EN_RTC 10
> +#define N_PCH_ACPI_PM1_EN_PWRBTN 8
> +#define N_PCH_ACPI_PM1_EN_GBL 5
> +#define N_PCH_ACPI_PM1_EN_TMROF 0
> +
> +#define R_PCH_ACPI_PM1_CNT 0x04
> +#define S_PCH_ACPI_PM1_CNT 4
> +#define B_PCH_ACPI_PM1_CNT_SLP_EN BIT13
> +#define B_PCH_ACPI_PM1_CNT_SLP_TYP (BIT12 | BIT11 | BIT10)
> +#define V_PCH_ACPI_PM1_CNT_S0 0
> +#define V_PCH_ACPI_PM1_CNT_S1 BIT10
> +#define V_PCH_ACPI_PM1_CNT_S3 (BIT12 | BIT10)
> +#define V_PCH_ACPI_PM1_CNT_S4 (BIT12 | BIT11)
> +#define V_PCH_ACPI_PM1_CNT_S5 (BIT12 | BIT11 | BIT10)
> +#define B_PCH_ACPI_PM1_CNT_GBL_RLS BIT2
> +#define B_PCH_ACPI_PM1_CNT_BM_RLD BIT1
> +#define B_PCH_ACPI_PM1_CNT_SCI_EN BIT0
> +
> +#define R_PCH_ACPI_PM1_TMR 0x08
> +#define V_PCH_ACPI_TMR_FREQUENCY 3579545
> +#define B_PCH_ACPI_PM1_TMR_VAL 0xFFFFFF
> +#define V_PCH_ACPI_PM1_TMR_MAX_VAL 0x1000000 ///< The
> timer is 24 bit overflow
> +
> +#define R_PCH_SMI_EN 0x30
> +#define S_PCH_SMI_EN 4
> +#define B_PCH_SMI_EN_LEGACY_USB3 BIT31
> +#define B_PCH_SMI_EN_GPIO_UNLOCK_SMI BIT27
> +#define B_PCH_SMI_EN_LEGACY_USB2 BIT17
> +#define B_PCH_SMI_EN_PERIODIC BIT14
> +#define B_PCH_SMI_EN_TCO BIT13
> +#define B_PCH_SMI_EN_MCSMI BIT11
> +#define B_PCH_SMI_EN_BIOS_RLS BIT7
> +#define B_PCH_SMI_EN_SWSMI_TMR BIT6
> +#define B_PCH_SMI_EN_APMC BIT5
> +#define B_PCH_SMI_EN_ON_SLP_EN BIT4
> +#define B_PCH_SMI_EN_LEGACY_USB BIT3
> +#define B_PCH_SMI_EN_BIOS BIT2
> +#define B_PCH_SMI_EN_EOS BIT1
> +#define B_PCH_SMI_EN_GBL_SMI BIT0
> +#define N_PCH_SMI_EN_LEGACY_USB3 31
> +#define N_PCH_SMI_EN_ESPI 28
> +#define N_PCH_SMI_EN_GPIO_UNLOCK 27
> +#define N_PCH_SMI_EN_INTEL_USB2 18
> +#define N_PCH_SMI_EN_LEGACY_USB2 17
> +#define N_PCH_SMI_EN_PERIODIC 14
> +#define N_PCH_SMI_EN_TCO 13
> +#define N_PCH_SMI_EN_MCSMI 11
> +#define N_PCH_SMI_EN_BIOS_RLS 7
> +#define N_PCH_SMI_EN_SWSMI_TMR 6
> +#define N_PCH_SMI_EN_APMC 5
> +#define N_PCH_SMI_EN_ON_SLP_EN 4
> +#define N_PCH_SMI_EN_LEGACY_USB 3
> +#define N_PCH_SMI_EN_BIOS 2
> +#define N_PCH_SMI_EN_EOS 1
> +#define N_PCH_SMI_EN_GBL_SMI 0
> +
> +#define R_PCH_SMI_STS 0x34
> +#define S_PCH_SMI_STS 4
> +#define B_PCH_SMI_STS_LEGACY_USB3 BIT31
> +#define B_PCH_SMI_STS_GPIO_UNLOCK BIT27
> +#define B_PCH_SMI_STS_SPI BIT26
> +#define B_PCH_SMI_STS_MONITOR BIT21
> +#define B_PCH_SMI_STS_PCI_EXP BIT20
> +#define B_PCH_SMI_STS_PATCH BIT19
> +#define B_PCH_SMI_STS_INTEL_USB2 BIT18
> +#define B_PCH_SMI_STS_LEGACY_USB2 BIT17
> +#define B_PCH_SMI_STS_SMBUS BIT16
> +#define B_PCH_SMI_STS_SERIRQ BIT15
> +#define B_PCH_SMI_STS_PERIODIC BIT14
> +#define B_PCH_SMI_STS_TCO BIT13
> +#define B_PCH_SMI_STS_DEVMON BIT12
> +#define B_PCH_SMI_STS_MCSMI BIT11
> +#define B_PCH_SMI_STS_GPIO_SMI BIT10
> +#define B_PCH_SMI_STS_GPE0 BIT9
> +#define B_PCH_SMI_STS_PM1_STS_REG BIT8
> +#define B_PCH_SMI_STS_SWSMI_TMR BIT6
> +#define B_PCH_SMI_STS_APM BIT5
> +#define B_PCH_SMI_STS_ON_SLP_EN BIT4
> +#define B_PCH_SMI_STS_LEGACY_USB BIT3
> +#define B_PCH_SMI_STS_BIOS BIT2
> +#define N_PCH_SMI_STS_LEGACY_USB3 31
> +#define N_PCH_SMI_STS_ESPI 28
> +#define N_PCH_SMI_STS_GPIO_UNLOCK 27
> +#define N_PCH_SMI_STS_SPI 26
> +#define N_PCH_SMI_STS_MONITOR 21
> +#define N_PCH_SMI_STS_PCI_EXP 20
> +#define N_PCH_SMI_STS_PATCH 19
> +#define N_PCH_SMI_STS_INTEL_USB2 18
> +#define N_PCH_SMI_STS_LEGACY_USB2 17
> +#define N_PCH_SMI_STS_SMBUS 16
> +#define N_PCH_SMI_STS_SERIRQ 15
> +#define N_PCH_SMI_STS_PERIODIC 14
> +#define N_PCH_SMI_STS_TCO 13
> +#define N_PCH_SMI_STS_DEVMON 12
> +#define N_PCH_SMI_STS_MCSMI 11
> +#define N_PCH_SMI_STS_GPIO_SMI 10
> +#define N_PCH_SMI_STS_GPE0 9
> +#define N_PCH_SMI_STS_PM1_STS_REG 8
> +#define N_PCH_SMI_STS_SWSMI_TMR 6
> +#define N_PCH_SMI_STS_APM 5
> +#define N_PCH_SMI_STS_ON_SLP_EN 4
> +#define N_PCH_SMI_STS_LEGACY_USB 3
> +#define N_PCH_SMI_STS_BIOS 2
> +
> +#define R_PCH_ACPI_GPE_CNTL 0x40
> +#define B_PCH_ACPI_GPE_CNTL_SWGPE_CTRL BIT17
> +
> +#define R_PCH_DEVACT_STS 0x44
> +#define S_PCH_DEVACT_STS 2
> +#define B_PCH_DEVACT_STS_MASK 0x13E1
> +#define B_PCH_DEVACT_STS_KBC BIT12
> +#define B_PCH_DEVACT_STS_PIRQDH BIT9
> +#define B_PCH_DEVACT_STS_PIRQCG BIT8
> +#define B_PCH_DEVACT_STS_PIRQBF BIT7
> +#define B_PCH_DEVACT_STS_PIRQAE BIT6
> +#define B_PCH_DEVACT_STS_D0_TRP BIT0
> +#define N_PCH_DEVACT_STS_KBC 12
> +#define N_PCH_DEVACT_STS_PIRQDH 9
> +#define N_PCH_DEVACT_STS_PIRQCG 8
> +#define N_PCH_DEVACT_STS_PIRQBF 7
> +#define N_PCH_DEVACT_STS_PIRQAE 6
> +
> +#define R_PCH_ACPI_PM2_CNT 0x50
> +#define B_PCH_ACPI_PM2_CNT_ARB_DIS BIT0
> +
> +#define R_PCH_OC_WDT_CTL 0x54
> +#define B_PCH_OC_WDT_CTL_RLD BIT31
> +#define B_PCH_OC_WDT_CTL_ICCSURV_STS BIT25
> +#define B_PCH_OC_WDT_CTL_NO_ICCSURV_STS BIT24
> +#define B_PCH_OC_WDT_CTL_FORCE_ALL BIT15
> +#define B_PCH_OC_WDT_CTL_EN BIT14
> +#define B_PCH_OC_WDT_CTL_ICCSURV BIT13
> +#define B_PCH_OC_WDT_CTL_LCK BIT12
> +#define B_PCH_OC_WDT_CTL_TOV_MASK 0x3FF
> +#define B_PCH_OC_WDT_CTL_FAILURE_STS BIT23
> +#define B_PCH_OC_WDT_CTL_UNXP_RESET_STS BIT22
> +#define B_PCH_OC_WDT_CTL_AFTER_POST 0x3F0000
> +#define V_PCH_OC_WDT_CTL_STATUS_FAILURE 1
> +#define V_PCH_OC_WDT_CTL_STATUS_OK 0
> +
> +#define R_PCH_ACPI_GPE0_STS_31_0 0x80
> +#define R_PCH_ACPI_GPE0_STS_63_32 0x84
> +#define R_PCH_ACPI_GPE0_STS_95_64 0x88
> +#define R_PCH_ACPI_GPE0_STS_127_96 0x8C
> +#define S_PCH_ACPI_GPE0_STS_127_96 4
> +#define B_PCH_ACPI_GPE0_STS_127_96_WADT BIT18
> +#define B_PCH_ACPI_GPE0_STS_127_96_LAN_WAKE BIT16
> +#define B_PCH_ACPI_GPE0_STS_127_96_PME_B0 BIT13
> +#define B_PCH_ACPI_GPE0_STS_127_96_ME_SCI BIT12
> +#define B_PCH_ACPI_GPE0_STS_127_96_PME BIT11
> +#define B_PCH_ACPI_GPE0_STS_127_96_BATLOW BIT10
> +#define B_PCH_ACPI_GPE0_STS_127_96_PCI_EXP BIT9
> +#define B_PCH_ACPI_GPE0_STS_127_96_RI BIT8
> +#define B_PCH_ACPI_GPE0_STS_127_96_SMB_WAK BIT7
> +#define B_PCH_ACPI_GPE0_STS_127_96_TC0SCI BIT6
> +#define B_PCH_ACPI_GPE0_STS_127_96_SWGPE BIT2
> +#define B_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG BIT1
> +#define N_PCH_ACPI_GPE0_STS_127_96_PME_B0 13
> +#define N_PCH_ACPI_GPE0_STS_127_96_PME 11
> +#define N_PCH_ACPI_GPE0_STS_127_96_BATLOW 10
> +#define N_PCH_ACPI_GPE0_STS_127_96_PCI_EXP 9
> +#define N_PCH_ACPI_GPE0_STS_127_96_RI 8
> +#define N_PCH_ACPI_GPE0_STS_127_96_SMB_WAK 7
> +#define N_PCH_ACPI_GPE0_STS_127_96_TC0SCI 6
> +#define N_PCH_ACPI_GPE0_STS_127_96_SWGPE 2
> +#define N_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG 1
> +
> +#define R_PCH_ACPI_GPE0_EN_31_0 0x90
> +#define R_PCH_ACPI_GPE0_EN_63_32 0x94
> +#define R_PCH_ACPI_GPE0_EN_95_64 0x98
> +#define R_PCH_ACPI_GPE0_EN_127_96 0x9C
> +#define S_PCH_ACPI_GPE0_EN_127_96 4
> +#define B_PCH_ACPI_GPE0_EN_127_96_WADT BIT18
> +#define B_PCH_ACPI_GPE0_EN_127_96_LAN_WAKE BIT16
> +#define B_PCH_ACPI_GPE0_EN_127_96_PME_B0 BIT13
> +#define B_PCH_ACPI_GPE0_EN_127_96_ME_SCI BIT12
> +#define B_PCH_ACPI_GPE0_EN_127_96_PME BIT11
> +#define B_PCH_ACPI_GPE0_EN_127_96_BATLOW BIT10
> +#define B_PCH_ACPI_GPE0_EN_127_96_PCI_EXP BIT9
> +#define B_PCH_ACPI_GPE0_EN_127_96_RI BIT8
> +#define B_PCH_ACPI_GPE0_EN_127_96_TC0SCI BIT6
> +#define B_PCH_ACPI_GPE0_EN_127_96_SWGPE BIT2
> +#define B_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG BIT1
> +#define N_PCH_ACPI_GPE0_EN_127_96_PME_B0 13
> +#define N_PCH_ACPI_GPE0_EN_127_96_USB3 12
> +#define N_PCH_ACPI_GPE0_EN_127_96_PME 11
> +#define N_PCH_ACPI_GPE0_EN_127_96_BATLOW 10
> +#define N_PCH_ACPI_GPE0_EN_127_96_PCI_EXP 9
> +#define N_PCH_ACPI_GPE0_EN_127_96_RI 8
> +#define N_PCH_ACPI_GPE0_EN_127_96_TC0SCI 6
> +#define N_PCH_ACPI_GPE0_EN_127_96_SWGPE 2
> +#define N_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG 1
> +
> +
> +//
> +// TCO register I/O map
> +//
> +#define R_PCH_TCO_RLD 0x0
> +#define R_PCH_TCO_DAT_IN 0x2
> +#define R_PCH_TCO_DAT_OUT 0x3
> +#define R_PCH_TCO1_STS 0x04
> +#define S_PCH_TCO1_STS 2
> +#define B_PCH_TCO1_STS_DMISERR BIT12
> +#define B_PCH_TCO1_STS_DMISMI BIT10
> +#define B_PCH_TCO1_STS_DMISCI BIT9
> +#define B_PCH_TCO1_STS_BIOSWR BIT8
> +#define B_PCH_TCO1_STS_NEWCENTURY BIT7
> +#define B_PCH_TCO1_STS_TIMEOUT BIT3
> +#define B_PCH_TCO1_STS_TCO_INT BIT2
> +#define B_PCH_TCO1_STS_SW_TCO_SMI BIT1
> +#define B_PCH_TCO1_STS_NMI2SMI BIT0
> +#define N_PCH_TCO1_STS_DMISMI 10
> +#define N_PCH_TCO1_STS_BIOSWR 8
> +#define N_PCH_TCO1_STS_NEWCENTURY 7
> +#define N_PCH_TCO1_STS_TIMEOUT 3
> +#define N_PCH_TCO1_STS_SW_TCO_SMI 1
> +#define N_PCH_TCO1_STS_NMI2SMI 0
> +
> +#define R_PCH_TCO2_STS 0x06
> +#define S_PCH_TCO2_STS 2
> +#define B_PCH_TCO2_STS_SMLINK_SLV_SMI BIT4
> +#define B_PCH_TCO2_STS_BAD_BIOS BIT3
> +#define B_PCH_TCO2_STS_BOOT BIT2
> +#define B_PCH_TCO2_STS_SECOND_TO BIT1
> +#define B_PCH_TCO2_STS_INTRD_DET BIT0
> +#define N_PCH_TCO2_STS_INTRD_DET 0
> +
> +#define R_PCH_TCO1_CNT 0x08
> +#define S_PCH_TCO1_CNT 2
> +#define B_PCH_TCO_CNT_LOCK BIT12
> +#define B_PCH_TCO_CNT_TMR_HLT BIT11
> +#define B_PCH_TCO_CNT_NMI2SMI_EN BIT9
> +#define B_PCH_TCO_CNT_NMI_NOW BIT8
> +#define N_PCH_TCO_CNT_NMI2SMI_EN 9
> +
> +#define R_PCH_TCO2_CNT 0x0A
> +#define S_PCH_TCO2_CNT 2
> +#define B_PCH_TCO2_CNT_OS_POLICY 0x0030
> +#define B_PCH_TCO2_CNT_GPI11_ALERT_DISABLE 0x0008
> +#define B_PCH_TCO2_CNT_INTRD_SEL 0x0006
> +#define N_PCH_TCO2_CNT_INTRD_SEL 2
> +
> +#define R_PCH_TCO_MESSAGE1 0x0C
> +#define R_PCH_TCO_MESSAGE2 0x0D
> +#define R_PCH_TCO_WDCNT 0x0E
> +#define R_PCH_TCO_SW_IRQ_GEN 0x10
> +#define B_PCH_TCO_IRQ12_CAUSE BIT1
> +#define B_PCH_TCO_IRQ1_CAUSE BIT0
> +#define R_PCH_TCO_TMR 0x12
> +
> +//
> +// PWRM Registers
> +//
> +#define R_PCH_WADT_AC 0x0 ///< Wake
> Alarm Device Timer: AC
> +#define R_PCH_WADT_DC 0x4 ///< Wake
> Alarm Device Timer: DC
> +#define R_PCH_WADT_EXP_AC 0x8 ///< Wake
> Alarm Device Expired Timer: AC
> +#define R_PCH_WADT_EXP_DC 0xC ///< Wake
> Alarm Device Expired Timer: DC
> +#define R_PCH_PWRM_PRSTS 0x10 ///< Power
> and Reset Status
> +#define B_PCH_PWRM_PRSTS_VE_WD_TMR_STS BIT7
> ///< VE Watchdog Timer Status
> +#define B_PCH_PWRM_PRSTS_WOL_OVR_WK_STS BIT5
> +#define B_PCH_PWRM_PRSTS_FIELD_1 BIT4
> +#define B_PCH_PWRM_PRSTS_ME_WAKE_STS BIT0
> +#define R_PCH_PWRM_14 0x14
> +#define R_PCH_PWRM_CFG 0x18 ///< Power
> Management Configuration
> +#define B_PCH_PWRM_CFG_ALLOW_24_OSC_SD BIT29
> ///< Allow 24MHz Crystal Oscillator Shutdown
> +#define B_PCH_PWRM_CFG_ALLOW_USB2_CORE_PG BIT25
> ///< Allow USB2 Core Power Gating
> +#define B_PCH_PWRM_CFG_RTC_DS_WAKE_DIS BIT21
> ///< RTC Wake from Deep S4/S5 Disable
> +#define B_PCH_PWRM_CFG_SSMAW_MASK (BIT19 | BIT18)
> ///< SLP_SUS# Min Assertion Width
> +#define V_PCH_PWRM_CFG_SSMAW_4S (BIT19 | BIT18)
> ///< 4 seconds
> +#define V_PCH_PWRM_CFG_SSMAW_1S BIT19
> ///< 1 second
> +#define V_PCH_PWRM_CFG_SSMAW_0_5S BIT18
> ///< 0.5 second (500ms)
> +#define V_PCH_PWRM_CFG_SSMAW_0S 0 ///< 0
> second
> +#define B_PCH_PWRM_CFG_SAMAW_MASK (BIT17 | BIT16)
> ///< SLP_A# Min Assertion Width
> +#define V_PCH_PWRM_CFG_SAMAW_2S (BIT17 | BIT16)
> ///< 2 seconds
> +#define V_PCH_PWRM_CFG_SAMAW_98ms BIT17
> ///< 98ms
> +#define V_PCH_PWRM_CFG_SAMAW_4S BIT16
> ///< 4 seconds
> +#define V_PCH_PWRM_CFG_SAMAW_0S 0 ///< 0
> second
> +#define B_PCH_PWRM_CFG_RPCD_MASK (BIT9 | BIT8)
> ///< Reset Power Cycle Duration
> +#define V_PCH_PWRM_CFG_RPCD_1S (BIT9 | BIT8)
> ///< 1-2 seconds
> +#define V_PCH_PWRM_CFG_RPCD_2S BIT9 ///< 2-
> 3 seconds
> +#define V_PCH_PWRM_CFG_RPCD_3S BIT8 ///< 3-
> 4 seconds
> +#define V_PCH_PWRM_CFG_RPCD_4S 0 ///< 4-5
> seconds (Default)
> +#define R_PCH_PWRM_PCH_PM_STS 0x1C ///<
> Contains misc. fields used to record PCH power management events
> +#define B_PCH_PWRM_PCH_PM_STS_PMC_MSG_FULL_STS BIT24
> ///< MTPMC transport mechanism full indication
> +#define R_PCH_PWRM_MTPMC 0x20 ///<
> Message to PMC
> +#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_0_15 0xE
> ///< Command to override lanes 0-15 power gating
> +#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_16_31 0xF
> ///< Command to override lanes 16-31 power gating
> +#define B_PCH_PWRM_MTPMC_PG_CMD_DATA 0xFFFF0000
> ///< Data part of PowerGate Message to PMC
> +#define N_PCH_PWRM_MTPMC_PG_CMD_DATA 16
> +#define R_PCH_PWRM_PCH_PM_STS2 0x24 ///<
> PCH Power Management Status
> +#define R_PCH_PWRM_S3_PWRGATE_POL 0x28
> ///< S3 Power Gating Policies
> +#define B_PCH_PWRM_S3DC_GATE_SUS BIT1 ///<
> Deep S3 Enable in DC Mode
> +#define B_PCH_PWRM_S3AC_GATE_SUS BIT0 ///<
> Deep S3 Enable in AC Mode
> +#define R_PCH_PWRM_S4_PWRGATE_POL 0x2C
> ///< Deep S4 Power Policies
> +#define B_PCH_PWRM_S4DC_GATE_SUS BIT1 ///<
> Deep S4 Enable in DC Mode
> +#define B_PCH_PWRM_S4AC_GATE_SUS BIT0 ///<
> Deep S4 Enable in AC Mode
> +#define R_PCH_PWRM_S5_PWRGATE_POL 0x30
> ///< Deep S5 Power Policies
> +#define B_PCH_PWRM_S5DC_GATE_SUS BIT15 ///<
> Deep S5 Enable in DC Mode
> +#define B_PCH_PWRM_S5AC_GATE_SUS BIT14 ///<
> Deep S5 Enable in AC Mode
> +#define R_PCH_PWRM_DSX_CFG 0x34 ///<
> Deep SX Configuration
> +#define B_PCH_PWRM_DSX_CFG_WAKE_PIN_DSX_EN BIT2
> ///< WAKE# Pin DeepSx Enable
> +#define B_PCH_PWRM_DSX_CFG_ACPRES_PD_DSX_DIS BIT1
> ///< AC_PRESENT pin pulldown in DeepSx disable
> +#define B_PCH_PWRM_DSX_CFG_LAN_WAKE_EN BIT0
> ///< LAN_WAKE Pin DeepSx Enable
> +#define R_PCH_PWRM_CFG2 0x3C ///< Power
> Management Configuration Reg 2
> +#define B_PCH_PWRM_CFG2_PBOP (BIT31 | BIT30 | BIT29)
> ///< Power Button Override Period (PBOP)
> +#define N_PCH_PWRM_CFG2_PBOP 29 ///<
> Power Button Override Period (PBOP)
> +#define B_PCH_PWRM_CFG2_PB_DIS BIT28 ///<
> Power Button Native Mode Disable (PB_DIS)
> +#define B_PCH_PWRM_CFG2_DRAM_RESET_CTL BIT26
> ///< DRAM RESET# control
> +#define R_PCH_PWRM_EN_SN_SLOW_RING 0x48
> ///< Enable Snoop Request to SLOW_RING
> +#define R_PCH_PWRM_EN_SN_SLOW_RING2 0x4C
> ///< Enable Snoop Request to SLOW_RING 2nd Reg
> +#define R_PCH_PWRM_EN_SN_SA 0x50 ///<
> Enable Snoop Request to SA
> +#define R_PCH_PWRM_EN_SN_SA2 0x54 ///<
> Enable Snoop Request to SA 2nd Reg
> +#define R_PCH_PWRM_EN_SN_SLOW_RING_CF 0x58
> ///< Enable Snoop Request to SLOW_RING_CF
> +#define R_PCH_PWRM_EN_NS_SA 0x68 ///<
> Enable Non-Snoop Request to SA
> +#define R_PCH_PWRM_EN_CW_SLOW_RING 0x80
> ///< Enable Clock Wake to SLOW_RING
> +#define R_PCH_PWRM_EN_CW_SLOW_RING2 0x84
> ///< Enable Clock Wake to SLOW_RING 2nd Reg
> +#define R_PCH_PWRM_EN_CW_SA 0x88 ///<
> Enable Clock Wake to SA
> +#define R_PCH_PWRM_EN_CW_SA2 0x8C ///<
> Enable Clock Wake to SA 2nd Reg
> +#define R_PCH_PWRM_EN_CW_SLOW_RING_CF 0x98
> ///< Enable Clock Wake to SLOW_RING_CF
> +#define R_PCH_PWRM_EN_PA_SLOW_RING 0xA8
> ///< Enable Pegged Active to SLOW_RING
> +#define R_PCH_PWRM_EN_PA_SLOW_RING2 0xAC
> ///< Enable Pegged Active to SLOW_RING 2nd Reg
> +#define R_PCH_PWRM_EN_PA_SA 0xB0 ///<
> Enable Pegged Active to SA
> +#define R_PCH_PWRM_EN_PA_SA2 0xB4 ///<
> Enable Pegged Active to SA 2nd Reg
> +#define R_PCH_PWRM_EN_MISC_EVENT 0xC0 ///<
> Enable Misc PM_SYNC Events
> +#define R_PCH_PWRM_PMSYNC_TPR_CONFIG 0xC4
> +#define B_PCH_PWRM_PMSYNC_TPR_CONFIG_LOCK BIT31
> +#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_EN BIT26
> +#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE (BIT25 |
> BIT24)
> +#define N_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE 24
> +#define V_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE_1 1
> +#define R_PCH_PWRM_PMSYNC_MISC_CFG 0xC8
> +#define B_PCH_PWRM_PMSYNC_PM_SYNC_LOCK BIT15
> ///< PM_SYNC Configuration Lock
> +#define B_PCH_PWRM_PMSYNC_GPIO_D_SEL BIT11
> +#define B_PCH_PWRM_PMSYNC_GPIO_C_SEL BIT10
> +#define R_PCH_PWRM_PM_SYNC_STATE_HYS 0xD0
> ///< PM_SYNC State Hysteresis
> +#define R_PCH_PWRM_PM_SYNC_MODE 0xD4
> ///< PM_SYNC Pin Mode
> +#define R_PCH_PWRM_CFG3 0xE0 ///< Power
> Management Configuration Reg 3
> +#define B_PCH_PWRM_CFG3_DSX_WLAN_PP_EN BIT16
> ///< Deep-Sx WLAN Phy Power Enable
> +#define B_PCH_PWRM_CFG3_HOST_WLAN_PP_EN BIT17
> ///< Host Wireless LAN Phy Power Enable
> +#define B_PCH_PWRM_CFG3_PWRG_LOCK BIT2
> ///< Lock power gating override messages
> +#define R_PCH_PWRM_PM_DOWN_PPB_CFG 0xE4
> ///< PM_DOWN PCH_POWER_BUDGET CONFIGURATION
> +#define R_PCH_PWRM_CFG4 0xE8 ///< Power
> Management Configuration Reg 4
> +#define B_PCH_PWRM_CFG4_U2_PHY_PG_EN BIT30
> ///< USB2 PHY SUS Well Power Gating Enable
> +#define B_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR
> (0x000001FF) ///< CPU I/O VR Ramp Duration, [8:0]
> +#define N_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR 0
> +#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_70US 0x007
> +#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_240US 0x018
> +#define R_PCH_PWRM_CPU_EPOC 0xEC
> +#define R_PCH_PWRM_VR_MISC_CTL 0x100
> +#define B_PCH_PWRM_VR_MISC_CTL_VIDSOVEN BIT3
> +#define R_PCH_PWRM_GPIO_CFG 0x120
> +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW2 (BIT11 | BIT10 |
> BIT9 | BIT8)
> +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW2 8
> +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW1 (BIT7 | BIT6 |
> BIT5 | BIT4)
> +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW1 4
> +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW0 (BIT3 | BIT2 |
> BIT1 | BIT0)
> +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW0 0
> +#define R_PCH_PWRM_PM_SYNC_MODE_C0 0xF4
> ///< PM_SYNC Pin Mode in C0
> +#define R_PCH_PWRM_ACPI_TMR_CTL 0xFC
> +#define B_PCH_PWRM_ACPI_TMR_DIS BIT1
> +#define R_PCH_PWRM_124 0x124
> +#define R_PCH_PWRM_SLP_S0_RESIDENCY_COUNTER 0x13C
> +#define R_PCH_PWRM_MODPHY_PM_CFG1 0x200
> +#define R_PCH_PWRM_MODPHY_PM_CFG1_MLSXSWPGP 0xFFFF
> +#define R_PCH_PWRM_MODPHY_PM_CFG2 0x204 ///<
> ModPHY Power Management Configuration Reg 2
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_MLSPDDGE BIT30
> ///< ModPHY Lane SUS Power Domain Dynamic Gating Enable
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_EMFC BIT29 ///<
> Enable ModPHY FET Control
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_EFRT (BIT28 | BIT27
> | BIT26 | BIT25 | BIT24) ///< External FET Ramp Time
> +#define N_PCH_PWRM_MODPHY_PM_CFG2_EFRT 24
> +#define V_PCH_PWRM_MODPHY_PM_CFG2_EFRT_200US 0x0A
> +#define B_PCH_PWRM_MODPHY_PM_CFG2_ASLOR_UFS BIT16
> ///< UFS ModPHY SPD SPD Override
> +#define R_PCH_PWRM_MODPHY_PM_CFG3 0x208 ///<
> ModPHY Power Management Configuration Reg 3
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_UFS BIT16
> ///< UFS ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XDCI BIT15
> ///< xDCI ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XHCI BIT14
> ///< xHCI ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_GBE BIT13
> ///< GbE ModPHY SPD RT Request
> +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_SATA BIT12
> ///< SATA ModPHY SPD RT Request
> +#define R_PCH_PWRM_30C 0x30C
> +#define R_PCH_PWRM_OBFF_CFG 0x314 ///< OBFF
> Configuration
> +#define R_PCH_PWRM_31C 0x31C
> +#define R_PCH_PWRM_CPPM_MISC_CFG 0x320 ///<
> CPPM Miscellaneous Configuration
> +#define R_PCH_PWRM_CPPM_CG_POL1A 0x324 ///<
> CPPM Clock Gating Policy Reg 1
> +#define R_PCH_PWRM_CPPM_CG_POL2A 0x340 ///<
> CPPM Clock Gating Policy Reg 3
> +#define R_PCH_PWRM_34C 0x34C
> +#define R_PCH_PWRM_CPPM_CG_POL3A 0x3A8 ///<
> CPPM Clock Gating Policy Reg 5
> +#define B_PCH_PWRM_CPPM_CG_POLXA_CPPM_GX_QUAL BIT30
> ///< CPPM Shutdown Qualifier Enable for Clock Source Group X
> +#define B_PCH_PWRM_CPPM_CG_POLXA_LTR_GX_THRESH
> (0x000001FF) ///< LTR Threshold for Clock Source Group X, [8:0]
> +#define R_PCH_PWRM_3D0 0x3D0
> +#define R_PCH_PWRM_CPPM_MPG_POL1A 0x3E0 ///<
> CPPM ModPHY Gating Policy Reg 1A
> +#define B_PCH_PWRM_CPPM_MPG_POL1A_CPPM_MODPHY_QUAL
> BIT30 ///< CPPM Shutdown Qualifier Enable for ModPHY
> +#define B_PCH_PWRM_CPPM_MPG_POL1A_LT_MODPHY_SEL BIT29
> ///< ASLT/PLT Selection for ModPHY
> +#define B_PCH_PWRM_CPPM_MPG_POL1A_LTR_MODPHY_THRESH
> (0x000001FF) ///< LTR Threshold for ModPHY, [8:0]
> +#define R_PCH_PWRM_CS_SD_CTL1 0x3E8 ///< Clock
> Source Shutdown Control Reg 1
> +#define B_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG (BIT22 | BIT21 |
> BIT20) ///< Clock Source 5 Control Configuration
> +#define N_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG 20
> +#define B_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG (BIT2 | BIT1 |
> BIT0) ///< Clock Source 1 Control Configuration
> +#define N_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG 0
> +#define R_PCH_PWRM_CS_SD_CTL2 0x3EC ///< Clock
> Source Shutdown Control Reg 2
> +#define R_PCH_PWRM_HSWPGCR1 0x5D0
> +#define B_PCH_PWRM_SW_PG_CTRL_LOCK BIT31
> +#define B_PCH_PWRM_DFX_SW_PG_CTRL BIT0
> +#define R_PCH_PWRM_600 0x600
> +#define R_PCH_PWRM_604 0x604
> +#define R_PCH_PWRM_ST_PG_FDIS_PMC_1 0x620 ///< Static
> PG Related Function Disable Register 1
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ST_FDIS_LK BIT31 ///<
> Static Function Disable Lock (ST_FDIS_LK)
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_CAM_FDIS_PMC BIT6
> ///< Camera Function Disable (PMC Version) (CAM_FDIS_PMC)
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ISH_FDIS_PMC BIT5 ///<
> SH Function Disable (PMC Version) (ISH_FDIS_PMC)
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_GBE_FDIS_PMC BIT0 ///<
> GBE Function Disable (PMC Version) (GBE_FDIS_PMC)
> +#define R_PCH_PWRM_ST_PG_FDIS_PMC_2 0x624 ///< Static
> Function Disable Control Register 2
> +#define V_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_FDIS_PMC 0x7FF
> ///< Static Function Disable Control Register 2
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI1_FDIS_PMC
> BIT10 ///< SerialIo Controller GSPI Device 1 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI0_FDIS_PMC
> BIT9 ///< SerialIo Controller GSPI Device 0 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART2_FDIS_PMC
> BIT8 ///< SerialIo Controller UART Device 2 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART1_FDIS_PMC
> BIT7 ///< SerialIo Controller UART Device 1 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART0_FDIS_PMC
> BIT6 ///< SerialIo Controller UART Device 0 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C5_FDIS_PMC
> BIT5 ///< SerialIo Controller I2C Device 5 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C4_FDIS_PMC
> BIT4 ///< SerialIo Controller I2C Device 4 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C3_FDIS_PMC
> BIT3 ///< SerialIo Controller I2C Device 3 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C2_FDIS_PMC
> BIT2 ///< SerialIo Controller I2C Device 2 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C1_FDIS_PMC
> BIT1 ///< SerialIo Controller I2C Device 1 Function Disable
> +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C0_FDIS_PMC
> BIT0 ///< SerialIo Controller I2C Device 0 Function Disable
> +#define R_PCH_PWRM_NST_PG_FDIS_1 0x628
> +#define B_PCH_PWRM_NST_PG_FDIS_1_SCC_FDIS_PMC BIT25 ///<
> SCC Function Disable. This is only avaiable in B0 onward.
> +#define B_PCH_PWRM_NST_PG_FDIS_1_XDCI_FDIS_PMC BIT24 ///<
> XDCI Function Disable. This is only avaiable in B0 onward.
> +#define B_PCH_PWRM_NST_PG_FDIS_1_ADSP_FDIS_PMC BIT23 ///<
> ADSP Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_SATA_FDIS_PMC BIT22 ///<
> SATA Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C3_FDIS_PMC BIT13 ///<
> PCIe Controller C Port 3 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C2_FDIS_PMC BIT12 ///<
> PCIe Controller C Port 2 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C1_FDIS_PMC BIT11 ///<
> PCIe Controller C Port 1 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C0_FDIS_PMC BIT10 ///<
> PCIe Controller C Port 0 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B3_FDIS_PMC BIT9 ///<
> PCIe Controller B Port 3 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B2_FDIS_PMC BIT8 ///<
> PCIe Controller B Port 2 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B1_FDIS_PMC BIT7 ///<
> PCIe Controller B Port 1 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B0_FDIS_PMC BIT6 ///<
> PCIe Controller B Port 0 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A3_FDIS_PMC BIT5 ///<
> PCIe Controller A Port 3 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A2_FDIS_PMC BIT4 ///<
> PCIe Controller A Port 2 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A1_FDIS_PMC BIT3 ///<
> PCIe Controller A Port 1 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A0_FDIS_PMC BIT2 ///<
> PCIe Controller A Port 0 Function Disable
> +#define B_PCH_PWRM_NST_PG_FDIS_1_XHCI_FDIS_PMC BIT0 ///<
> XHCI Function Disable
> +#define R_PCH_PWRM_FUSE_DIS_RD_1 0x640 ///< Fuse
> Disable Read 1 Register
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E3_FUSE_DIS BIT21 ///<
> PCIe Controller E Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E2_FUSE_DIS BIT20 ///<
> PCIe Controller E Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E1_FUSE_DIS BIT19 ///<
> PCIe Controller E Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E0_FUSE_DIS BIT18 ///<
> PCIe Controller E Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D3_FUSE_DIS BIT17 ///<
> PCIe Controller D Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D2_FUSE_DIS BIT16 ///<
> PCIe Controller D Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D1_FUSE_DIS BIT15 ///<
> PCIe Controller D Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D0_FUSE_DIS BIT14 ///<
> PCIe Controller D Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C3_FUSE_DIS BIT13 ///<
> PCIe Controller C Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C2_FUSE_DIS BIT12 ///<
> PCIe Controller C Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C1_FUSE_DIS BIT11 ///<
> PCIe Controller C Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C0_FUSE_DIS BIT10 ///<
> PCIe Controller C Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B3_FUSE_DIS BIT9 ///<
> PCIe Controller B Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B2_FUSE_DIS BIT8 ///<
> PCIe Controller B Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B1_FUSE_DIS BIT7 ///<
> PCIe Controller B Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B0_FUSE_DIS BIT6 ///<
> PCIe Controller B Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A3_FUSE_DIS BIT5 ///<
> PCIe Controller A Port 3 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A2_FUSE_DIS BIT4 ///<
> PCIe Controller A Port 2 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A1_FUSE_DIS BIT3 ///<
> PCIe Controller A Port 1 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A0_FUSE_DIS BIT2 ///<
> PCIe Controller A Port 0 Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_1_XHCI_FUSE_DIS BIT0 ///<
> XHCI Fuse Disable
> +#define R_PCH_PWRM_FUSE_DIS_RD_2 0x644 ///< Fuse
> Disable Read 2 Register
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPC_SS_DIS BIT25 ///< SPC
> Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPB_SS_DIS BIT24 ///< SPB
> Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPA_SS_DIS BIT23 ///< SPA
> Fuse Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_PSTH_FUSE_SS_DIS BIT21 ///<
> PSTH Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_DMI_FUSE_SS_DIS BIT20 ///<
> DMI Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_OTG_FUSE_SS_DIS BIT19 ///<
> OTG Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_XHCI_SS_DIS BIT18 ///<
> XHCI Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_FIA_FUSE_SS_DIS BIT17 ///<
> FIA Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_DSP_FUSE_SS_DIS BIT16 ///<
> DSP Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SATA_FUSE_SS_DIS BIT15 ///<
> SATA Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_ICC_FUSE_SS_DIS BIT14 ///<
> ICC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_LPC_FUSE_SS_DIS BIT13 ///<
> LPC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_RTC_FUSE_SS_DIS BIT12 ///<
> RTC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_P2S_FUSE_SS_DIS BIT11 ///<
> P2S Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_TRSB_FUSE_SS_DIS BIT10 ///<
> TRSB Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SMB_FUSE_SS_DIS BIT9 ///<
> SMB Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_ITSS_FUSE_SS_DIS BIT8 ///<
> ITSS Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SERIALIO_FUSE_SS_DIS BIT6
> ///< SerialIo Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_SCC_FUSE_SS_DIS BIT4 ///<
> SCC Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_P2D_FUSE_SS_DIS BIT3 ///<
> P2D Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_CAM_FUSE_SS_DIS BIT2 ///<
> Camera Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_ISH_FUSE_SS_DIS BIT1 ///<
> ISH Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_2_GBE_FUSE_SS_DIS BIT0 ///<
> GBE Fuse or Soft Strap Disable
> +#define R_PCH_PWRM_FUSE_DIS_RD_3 0x648 ///< Static PG
> Fuse and Soft Strap Disable Read Register 3
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA3_FUSE_SS_DIS BIT3
> ///< PNCRA3 Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA2_FUSE_SS_DIS BIT2
> ///< PNCRA2 Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA1_FUSE_SS_DIS BIT1
> ///< PNCRA1 Fuse or Soft Strap Disable
> +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA_FUSE_SS_DIS BIT0
> ///< PNCRA Fuse or Soft Strap Disable
> +
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> new file mode 100644
> index 0000000000..a727aae927
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> @@ -0,0 +1,304 @@
> +/** @file
> + Register names for PCH SPI device.
> +
> + Conventions:
> +
> + - Prefixes:
> + Definitions beginning with "R_" are registers
> + Definitions beginning with "B_" are bits within registers
> + Definitions beginning with "V_" are meaningful values within the bits
> + Definitions beginning with "S_" are register sizes
> + Definitions beginning with "N_" are the bit position
> + - In general, PCH registers are denoted by "_PCH_" in register names
> + - Registers / bits that are different between PCH generations are denoted by
> + "_PCH_[generation_name]_" in register/bit names.
> + - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit
> names.
> + Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit
> names.
> + e.g., "_PCH_H_", "_PCH_LP_"
> + Registers / bits names without _H_ or _LP_ apply for both H and LP.
> + - Registers / bits that are different between SKUs are denoted by
> "_[SKU_name]"
> + at the end of the register/bit names
> + - Registers / bits of new devices introduced in a PCH generation will be just
> named
> + as "_PCH_" without [generation_name] inserted.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_REGS_SPI_H_
> +#define _PCH_REGS_SPI_H_
> +
> +//
> +// SPI Registers (D31:F5)
> +//
> +
> +#define PCI_DEVICE_NUMBER_PCH_SPI 31
> +#define PCI_FUNCTION_NUMBER_PCH_SPI 5
> +
> +#define R_PCH_SPI_BAR0 0x10
> +#define B_PCH_SPI_BAR0_MASK 0x0FFF
> +
> +#define R_PCH_SPI_BDE 0xD8
> +#define B_PCH_SPI_BDE_F8 0x8000
> +#define B_PCH_SPI_BDE_F0 0x4000
> +#define B_PCH_SPI_BDE_E8 0x2000
> +#define B_PCH_SPI_BDE_E0 0x1000
> +#define B_PCH_SPI_BDE_D8 0x0800
> +#define B_PCH_SPI_BDE_D0 0x0400
> +#define B_PCH_SPI_BDE_C8 0x0200
> +#define B_PCH_SPI_BDE_C0 0x0100
> +#define B_PCH_SPI_BDE_LEG_F 0x0080
> +#define B_PCH_SPI_BDE_LEG_E 0x0040
> +#define B_PCH_SPI_BDE_70 0x0008
> +#define B_PCH_SPI_BDE_60 0x0004
> +#define B_PCH_SPI_BDE_50 0x0002
> +#define B_PCH_SPI_BDE_40 0x0001
> +
> +#define R_PCH_SPI_BC 0xDC
> +#define S_PCH_SPI_BC 4
> +#define N_PCH_SPI_BC_ASE_BWP 11
> +#define B_PCH_SPI_BC_ASE_BWP BIT11
> +#define N_PCH_SPI_BC_ASYNC_SS 10
> +#define B_PCH_SPI_BC_ASYNC_SS BIT10
> +#define B_PCH_SPI_BC_OSFH BIT9 ///< OS Function Hide
> +#define N_PCH_SPI_BC_SYNC_SS 8
> +#define B_PCH_SPI_BC_SYNC_SS BIT8
> +#define B_PCH_SPI_BC_BILD BIT7
> +#define B_PCH_SPI_BC_BBS BIT6 ///< Boot BIOS strap
> +#define N_PCH_SPI_BC_BBS 6
> +#define V_PCH_SPI_BC_BBS_SPI 0 ///< Boot BIOS strapped to
> SPI
> +#define V_PCH_SPI_BC_BBS_LPC 1 ///< Boot BIOS strapped to
> LPC
> +#define B_PCH_SPI_BC_EISS BIT5 ///< Enable InSMM.STS
> +#define B_PCH_SPI_BC_TSS BIT4
> +#define B_PCH_SPI_BC_SRC (BIT3 | BIT2)
> +#define N_PCH_SPI_BC_SRC 2
> +#define V_PCH_SPI_BC_SRC_PREF_EN_CACHE_EN 0x02 ///<
> Prefetching and Caching enabled
> +#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_DIS 0x01 ///< No
> prefetching and no caching
> +#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_EN 0x00 ///< No
> prefetching, but caching enabled
> +#define B_PCH_SPI_BC_LE BIT1 ///< Lock Enable
> +#define N_PCH_SPI_BC_BLE 1
> +#define B_PCH_SPI_BC_WPD BIT0 ///< Write Protect Disable
> +
> +//
> +// BIOS Flash Program Registers (based on SPI_BAR0)
> +//
> +#define R_PCH_SPI_BFPR 0x00 ///< BIOS Flash
> Primary Region Register(32bits), which is RO and contains the same value from
> FREG1
> +#define B_PCH_SPI_BFPR_PRL 0x7FFF0000 ///< BIOS Flash
> Primary Region Limit mask
> +#define N_PCH_SPI_BFPR_PRL 16 ///< BIOS Flash
> Primary Region Limit bit position
> +#define B_PCH_SPI_BFPR_PRB 0x00007FFF ///< BIOS Flash
> Primary Region Base mask
> +#define N_PCH_SPI_BFPR_PRB 0 ///< BIOS Flash
> Primary Region Base bit position
> +#define R_PCH_SPI_HSFSC 0x04 ///< Hardware
> Sequencing Flash Status and Control Register(32bits)
> +#define B_PCH_SPI_HSFSC_FSMIE BIT31 ///< Flash SPI
> SMI# Enable
> +#define B_PCH_SPI_HSFSC_FDBC_MASK 0x3F000000 ///<
> Flash Data Byte Count ( <= 64), Count = (Value in this field) + 1.
> +#define N_PCH_SPI_HSFSC_FDBC 24
> +#define B_PCH_SPI_HSFSC_CYCLE_MASK 0x001E0000 ///<
> Flash Cycle.
> +#define N_PCH_SPI_HSFSC_CYCLE 17
> +#define V_PCH_SPI_HSFSC_CYCLE_READ 0 ///< Flash Cycle
> Read
> +#define V_PCH_SPI_HSFSC_CYCLE_WRITE 2 ///< Flash
> Cycle Write
> +#define V_PCH_SPI_HSFSC_CYCLE_4K_ERASE 3 ///< Flash
> Cycle 4K Block Erase
> +#define V_PCH_SPI_HSFSC_CYCLE_64K_ERASE 4 ///< Flash
> Cycle 64K Sector Erase
> +#define V_PCH_SPI_HSFSC_CYCLE_READ_SFDP 5 ///< Flash
> Cycle Read SFDP
> +#define V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID 6 ///<
> Flash Cycle Read JEDEC ID
> +#define V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS 7 ///< Flash
> Cycle Write Status
> +#define V_PCH_SPI_HSFSC_CYCLE_READ_STATUS 8 ///< Flash
> Cycle Read Status
> +#define B_PCH_SPI_HSFSC_CYCLE_FGO BIT16 ///< Flash
> Cycle Go.
> +#define B_PCH_SPI_HSFSC_FLOCKDN BIT15 ///< Flash
> Configuration Lock-Down
> +#define B_PCH_SPI_HSFSC_FDV BIT14 ///< Flash
> Descriptor Valid, once valid software can use hareware sequencing regs
> +#define B_PCH_SPI_HSFSC_FDOPSS BIT13 ///< Flash
> Descriptor Override Pin-Strap Status
> +#define B_PCH_SPI_HSFSC_PRR34_LOCKDN BIT12 ///< PRR3
> PRR4 Lock-Down
> +#define B_PCH_SPI_HSFSC_SAF_CE BIT8 ///< SAF ctype
> error
> +#define B_PCH_SPI_HSFSC_SAF_MODE_ACTIVE BIT7 ///<
> Indicates flash is attached either directly to the PCH via the SPI bus or EC/BMC
> +#define B_PCH_SPI_HSFSC_SAF_LE BIT6 ///< SAF link
> error
> +#define B_PCH_SPI_HSFSC_SCIP BIT5 ///< SPI cycle in
> progress
> +#define B_PCH_SPI_HSFSC_SAF_DLE BIT4 ///< SAF Data
> length error
> +#define B_PCH_SPI_HSFSC_SAF_ERROR BIT3 ///< SAF Error
> +#define B_PCH_SPI_HSFSC_AEL BIT2 ///< Access Error
> Log
> +#define B_PCH_SPI_HSFSC_FCERR BIT1 ///< Flash Cycle
> Error
> +#define B_PCH_SPI_HSFSC_FDONE BIT0 ///< Flash Cycle
> Done
> +#define R_PCH_SPI_FADDR 0x08 ///< SPI Flash
> Address
> +#define B_PCH_SPI_FADDR_MASK 0x01FFFFFF ///< SPI
> Flash Address Mask (0~24bit)
> +#define R_PCH_SPI_DLOCK 0x0C ///< Discrete Lock
> Bits
> +#define B_PCH_SPI_DLOCK_PR0LOCKDN BIT8 ///<
> PR0LOCKDN
> +#define R_PCH_SPI_FDATA00 0x10 ///< SPI Data 00 (32
> bits)
> +#define R_PCH_SPI_FDATA01 0x14 ///< SPI Data 01
> +#define R_PCH_SPI_FDATA02 0x18 ///< SPI Data 02
> +#define R_PCH_SPI_FDATA03 0x1C ///< SPI Data 03
> +#define R_PCH_SPI_FDATA04 0x20 ///< SPI Data 04
> +#define R_PCH_SPI_FDATA05 0x24 ///< SPI Data 05
> +#define R_PCH_SPI_FDATA06 0x28 ///< SPI Data 06
> +#define R_PCH_SPI_FDATA07 0x2C ///< SPI Data 07
> +#define R_PCH_SPI_FDATA08 0x30 ///< SPI Data 08
> +#define R_PCH_SPI_FDATA09 0x34 ///< SPI Data 09
> +#define R_PCH_SPI_FDATA10 0x38 ///< SPI Data 10
> +#define R_PCH_SPI_FDATA11 0x3C ///< SPI Data 11
> +#define R_PCH_SPI_FDATA12 0x40 ///< SPI Data 12
> +#define R_PCH_SPI_FDATA13 0x44 ///< SPI Data 13
> +#define R_PCH_SPI_FDATA14 0x48 ///< SPI Data 14
> +#define R_PCH_SPI_FDATA15 0x4C ///< SPI Data 15
> +#define R_PCH_SPI_FRAP 0x50 ///< Flash Region
> Access Permisions Register
> +#define B_PCH_SPI_FRAP_BRWA_MASK 0x0000FF00 ///<
> BIOS Region Write Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2:
> ME; 3: GbE; 4: PlatformData
> +#define N_PCH_SPI_FRAP_BRWA 8 ///< BIOS Region
> Write Access bit position
> +#define B_PCH_SPI_FRAP_BRRA_MASK 0x000000FF ///< BIOS
> Region Read Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3:
> GbE; 4: PlatformData
> +#define B_PCH_SPI_FRAP_BMRAG_MASK 0x00FF0000 ///<
> BIOS Master Read Access Grant
> +#define B_PCH_SPI_FRAP_BMWAG_MASK 0xFF000000 ///<
> BIOS Master Write Access Grant
> +#define R_PCH_SPI_FREG0_FLASHD 0x54 ///< Flash
> Region 0(Flash Descriptor)(32bits)
> +#define R_PCH_SPI_FREG1_BIOS 0x58 ///< Flash Region
> 1(BIOS)(32bits)
> +#define R_PCH_SPI_FREG2_ME 0x5C ///< Flash Region
> 2(ME)(32bits)
> +#define R_PCH_SPI_FREG3_GBE 0x60 ///< Flash Region
> 3(GbE)(32bits)
> +#define R_PCH_SPI_FREG4_PLATFORM_DATA 0x64 ///< Flash
> Region 4(Platform Data)(32bits)
> +#define R_PCH_SPI_FREG5_DER 0x68 ///< Flash Region
> 5(Device Expansion Region)(32bits)
> +#define S_PCH_SPI_FREGX 4 ///< Size of Flash Region
> register
> +#define B_PCH_SPI_FREGX_LIMIT_MASK 0x7FFF0000 ///<
> Flash Region Limit [30:16] represents [26:12], [11:0] are assumed to be FFFh
> +#define N_PCH_SPI_FREGX_LIMIT 16 ///< Region limit
> bit position
> +#define N_PCH_SPI_FREGX_LIMIT_REPR 12 ///< Region
> limit bit represents position
> +#define B_PCH_SPI_FREGX_BASE_MASK 0x00007FFF ///<
> Flash Region Base, [14:0] represents [26:12]
> +#define N_PCH_SPI_FREGX_BASE 0 ///< Region base bit
> position
> +#define N_PCH_SPI_FREGX_BASE_REPR 12 ///< Region
> base bit represents position
> +#define R_PCH_SPI_PR0 0x84 ///< Protected Region 0
> Register
> +#define R_PCH_SPI_PR1 0x88 ///< Protected Region 1
> Register
> +#define R_PCH_SPI_PR2 0x8C ///< Protected Region 2
> Register
> +#define R_PCH_SPI_PR3 0x90 ///< Protected Region 3
> Register
> +#define R_PCH_SPI_PR4 0x94 ///< Protected Region 4
> Register
> +#define S_PCH_SPI_PRX 4 ///< Protected Region X
> Register size
> +#define B_PCH_SPI_PRX_WPE BIT31 ///< Write
> Protection Enable
> +#define B_PCH_SPI_PRX_PRL_MASK 0x7FFF0000 ///<
> Protected Range Limit Mask, [30:16] here represents upper limit of address
> [26:12]
> +#define N_PCH_SPI_PRX_PRL 16 ///< Protected Range
> Limit bit position
> +#define B_PCH_SPI_PRX_RPE BIT15 ///< Read
> Protection Enable
> +#define B_PCH_SPI_PRX_PRB_MASK 0x00007FFF ///<
> Protected Range Base Mask, [14:0] here represents base limit of address [26:12]
> +#define N_PCH_SPI_PRX_PRB 0 ///< Protected Range
> Base bit position
> +#define R_PCH_SPI_SFRAP 0xB0 ///< Secondary Flash
> Regions Access Permisions Register
> +#define R_PCH_SPI_FDOC 0xB4 ///< Flash Descriptor
> Observability Control Register(32 bits)
> +#define B_PCH_SPI_FDOC_FDSS_MASK (BIT14 | BIT13 | BIT12) ///<
> Flash Descritor Section Select
> +#define V_PCH_SPI_FDOC_FDSS_FSDM 0x0000 ///< Flash
> Signature and Descriptor Map
> +#define V_PCH_SPI_FDOC_FDSS_COMP 0x1000 ///<
> Component
> +#define V_PCH_SPI_FDOC_FDSS_REGN 0x2000 ///< Region
> +#define V_PCH_SPI_FDOC_FDSS_MSTR 0x3000 ///< Master
> +#define V_PCH_SPI_FDOC_FDSS_PCHS 0x4000 ///< PCH
> soft straps
> +#define V_PCH_SPI_FDOC_FDSS_SFDP 0x5000 ///< SFDP
> Parameter Table
> +#define B_PCH_SPI_FDOC_FDSI_MASK 0x0FFC ///< Flash
> Descriptor Section Index
> +#define R_PCH_SPI_FDOD 0xB8 ///< Flash Descriptor
> Observability Data Register(32 bits)
> +#define R_PCH_SPI_SFDP0_VSCC0 0xC4 ///< Vendor
> Specific Component Capabilities Register(32 bits)
> +#define B_PCH_SPI_SFDPX_VSCCX_CPPTV BIT31 ///<
> Component Property Parameter Table Valid
> +#define B_PCH_SPI_SFDP0_VSCC0_VCL BIT30 ///< Vendor
> Component Lock
> +#define B_PCH_SPI_SFDPX_VSCCX_EO_64K BIT29 ///< 64k
> Erase valid (EO_64k_valid)
> +#define B_PCH_SPI_SFDPX_VSCCX_EO_4K BIT28 ///< 4k
> Erase valid (EO_4k_valid)
> +#define B_PCH_SPI_SFDPX_VSCCX_RPMC BIT27 ///< RPMC
> Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_DPD BIT26 ///< Deep
> Powerdown Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_SUSRES BIT25 ///<
> Suspend/Resume Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_SOFTRES BIT24 ///< Soft
> Reset Supported
> +#define B_PCH_SPI_SFDPX_VSCCX_64k_EO_MASK 0x00FF0000
> ///< 64k Erase Opcode (EO_64k)
> +#define B_PCH_SPI_SFDPX_VSCCX_4k_EO_MASK 0x0000FF00
> ///< 4k Erase Opcode (EO_4k)
> +#define B_PCH_SPI_SFDPX_VSCCX_QER (BIT7 | BIT6 | BIT5) ///<
> Quad Enable Requirements
> +#define B_PCH_SPI_SFDPX_VSCCX_WEWS BIT4 ///< Write
> Enable on Write Status
> +#define B_PCH_SPI_SFDPX_VSCCX_WSR BIT3 ///< Write
> Status Required
> +#define B_PCH_SPI_SFDPX_VSCCX_WG_64B BIT2 ///< Write
> Granularity, 0: 1 Byte; 1: 64 Bytes
> +#define R_PCH_SPI_SFDP1_VSCC1 0xC8 ///< Vendor
> Specific Component Capabilities Register(32 bits)
> +#define R_PCH_SPI_PINTX 0xCC ///< Parameter Table
> Index
> +#define N_PCH_SPI_PINTX_SPT 14
> +#define V_PCH_SPI_PINTX_SPT_CPT0 0x0 ///< Component
> 0 Property Parameter Table
> +#define V_PCH_SPI_PINTX_SPT_CPT1 0x1 ///< Component
> 1 Property Parameter Table
> +#define N_PCH_SPI_PINTX_HORD 12
> +#define V_PCH_SPI_PINTX_HORD_SFDP 0x0 ///< SFDP
> Header
> +#define V_PCH_SPI_PINTX_HORD_PT 0x1 ///< Parameter
> Table Header
> +#define V_PCH_SPI_PINTX_HORD_DATA 0x2 ///< Data
> +#define R_PCH_SPI_PTDATA 0xD0 ///< Parameter
> Table Data
> +#define R_PCH_SPI_SBRS 0xD4 ///< SPI Bus Requester
> Status
> +#define R_PCH_SPI_SSML 0xF0 ///< Set Strap Msg
> Lock
> +#define B_PCH_SPI_SSML_SSL BIT0 ///< Set_Strap Lock
> +#define R_PCH_SPI_SSMC 0xF4 ///< Set Strap Msg
> Control
> +#define B_PCH_SPI_SSMC_SSMS BIT0 ///< Set_Strap
> Mux Select
> +#define R_PCH_SPI_SSMD 0xF8 ///< Set Strap Msg
> Data
> +//
> +// @todo Follow up with EDS owner if it should be 3FFF or FFFF.
> +//
> +#define B_PCH_SPI_SRD_SSD 0x0000FFFF ///< Set_Strap
> Data
> +//
> +// Flash Descriptor Base Address Region (FDBAR) from Flash Region 0
> +//
> +#define R_PCH_SPI_FDBAR_FLVALSIG 0x00 ///< Flash Valid
> Signature
> +#define V_PCH_SPI_FDBAR_FLVALSIG 0x0FF0A55A
> +#define R_PCH_SPI_FDBAR_FLASH_MAP0 0x04
> +#define B_PCH_SPI_FDBAR_FCBA 0x000000FF ///< Flash
> Component Base Address
> +#define B_PCH_SPI_FDBAR_NC 0x00000300 ///< Number
> Of Components
> +#define N_PCH_SPI_FDBAR_NC 8 ///< Number Of
> Components
> +#define V_PCH_SPI_FDBAR_NC_1 0x00000000
> +#define V_PCH_SPI_FDBAR_NC_2 0x00000100
> +#define B_PCH_SPI_FDBAR_FRBA 0x00FF0000 ///< Flash
> Region Base Address
> +#define B_PCH_SPI_FDBAR_NR 0x07000000 ///< Number
> Of Regions
> +#define R_PCH_SPI_FDBAR_FLASH_MAP1 0x08
> +#define B_PCH_SPI_FDBAR_FMBA 0x000000FF ///< Flash
> Master Base Address
> +#define B_PCH_SPI_FDBAR_NM 0x00000700 ///< Number
> Of Masters
> +#define B_PCH_SPI_FDBAR_FPSBA 0x00FF0000 ///< PCH
> Strap Base Address, [23:16] represents [11:4]
> +#define N_PCH_SPI_FDBAR_FPSBA 16 ///< PCH Strap
> base Address bit position
> +#define N_PCH_SPI_FDBAR_FPSBA_REPR 4 ///< PCH Strap
> base Address bit represents position
> +#define B_PCH_SPI_FDBAR_PCHSL 0xFF000000 ///< PCH
> Strap Length, [31:24] represents number of Dwords
> +#define N_PCH_SPI_FDBAR_PCHSL 24 ///< PCH Strap
> Length bit position
> +#define R_PCH_SPI_FDBAR_FLASH_MAP2 0x0C
> +#define B_PCH_SPI_FDBAR_FCPUSBA 0x000000FF ///< CPU
> Strap Base Address, [7:0] represents [11:4]
> +#define N_PCH_SPI_FDBAR_FCPUSBA 0 ///< CPU Strap
> Base Address bit position
> +#define N_PCH_SPI_FDBAR_FCPUSBA_REPR 4 ///< CPU
> Strap Base Address bit represents position
> +#define B_PCH_SPI_FDBAR_CPUSL 0x0000FF00 ///< CPU
> Strap Length, [15:8] represents number of Dwords
> +#define N_PCH_SPI_FDBAR_CPUSL 8 ///< CPU Strap
> Length bit position
> +//
> +// Flash Component Base Address (FCBA) from Flash Region 0
> +//
> +#define R_PCH_SPI_FCBA_FLCOMP 0x00 ///< Flash
> Components Register
> +#define B_PCH_SPI_FLCOMP_RIDS_FREQ (BIT29 | BIT28 | BIT27) ///<
> Read ID and Read Status Clock Frequency
> +#define B_PCH_SPI_FLCOMP_WE_FREQ (BIT26 | BIT25 | BIT24) ///<
> Write and Erase Clock Frequency
> +#define B_PCH_SPI_FLCOMP_FRCF_FREQ (BIT23 | BIT22 | BIT21) ///<
> Fast Read Clock Frequency
> +#define B_PCH_SPI_FLCOMP_FR_SUP BIT20 ///< Fast Read
> Support.
> +#define B_PCH_SPI_FLCOMP_RC_FREQ (BIT19 | BIT18 | BIT17) ///<
> Read Clock Frequency.
> +#define V_PCH_SPI_FLCOMP_FREQ_48MHZ 0x02
> +#define V_PCH_SPI_FLCOMP_FREQ_30MHZ 0x04
> +#define V_PCH_SPI_FLCOMP_FREQ_17MHZ 0x06
> +#define B_PCH_SPI_FLCOMP_COMP1_MASK 0xF0 ///< Flash
> Component 1 Size MASK
> +#define N_PCH_SPI_FLCOMP_COMP1 4 ///< Flash
> Component 1 Size bit position
> +#define B_PCH_SPI_FLCOMP_COMP0_MASK 0x0F ///< Flash
> Component 0 Size MASK
> +#define V_PCH_SPI_FLCOMP_COMP_512KB 0x80000
> +//
> +// Descriptor Upper Map Section from Flash Region 0
> +//
> +#define R_PCH_SPI_FLASH_UMAP1 0xEFC ///< Flash
> Upper Map 1
> +#define B_PCH_SPI_FLASH_UMAP1_VTBA 0x000000FF ///<
> VSCC Table Base Address
> +#define B_PCH_SPI_FLASH_UMAP1_VTL 0x0000FF00 ///<
> VSCC Table Length
> +
> +#define R_PCH_SPI_VTBA_JID0 0x00 ///< JEDEC-ID 0
> Register
> +#define S_PCH_SPI_VTBA_JID0 0x04
> +#define B_PCH_SPI_VTBA_JID0_VID 0x000000FF
> +#define B_PCH_SPI_VTBA_JID0_DID0 0x0000FF00
> +#define B_PCH_SPI_VTBA_JID0_DID1 0x00FF0000
> +#define N_PCH_SPI_VTBA_JID0_DID0 0x08
> +#define N_PCH_SPI_VTBA_JID0_DID1 0x10
> +#define R_PCH_SPI_VTBA_VSCC0 0x04
> +#define S_PCH_SPI_VTBA_VSCC0 0x04
> +
> +
> +//
> +// SPI Private Configuration Space Registers
> +//
> +#define R_PCH_PCR_SPI_CLK_CTL 0xC004
> +#define R_PCH_PCR_SPI_PWR_CTL 0xC008
> +#define R_PCH_PCR_SPI_ESPI_SOFTSTRAPS 0xC210
> +#define B_PCH_PCR_SPI_ESPI_SOFTSTRAPS_SLAVE BIT12
> +
> +//
> +// MMP0
> +//
> +#define R_PCH_SPI_STRP_MMP0 0xC4 ///< MMP0 Soft strap offset
> +#define B_PCH_SPI_STRP_MMP0 0x10 ///< MMP0 Soft strap bit
> +
> +
> +#define R_PCH_SPI_STRP_SFDP 0xF0 ///< PCH Soft Strap SFDP
> +#define B_PCH_SPI_STRP_SFDP_QIORE BIT3 ///< Quad IO Read Enable
> +#define B_PCH_SPI_STRP_SFDP_QORE BIT2 ///< Quad Output Read
> Enable
> +#define B_PCH_SPI_STRP_SFDP_DIORE BIT1 ///< Dual IO Read Enable
> +#define B_PCH_SPI_STRP_SFDP_DORE BIT0 ///< Dual Output Read
> Enable
> +
> +//
> +// Descriptor Record 0
> +//
> +#define R_PCH_SPI_STRP_DSCR_0 0x00 ///< PCH Soft Strap 0
> +#define B_PCH_SPI_STRP_DSCR_0_PTT_SUPP BIT22 ///< PTT Supported
> +
> +#endif
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> new file mode 100644
> index 0000000000..5bdec96197
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> @@ -0,0 +1,396 @@
> +/** @file
> + Header file for the PCH SPI Common Driver.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_SPI_COMMON_LIB_H_
> +#define _PCH_SPI_COMMON_LIB_H_
> +
> +//
> +// Maximum time allowed while waiting the SPI cycle to complete
> +// Wait Time = 6 seconds = 6000000 microseconds
> +// Wait Period = 10 microseconds
> +//
> +#define SPI_WAIT_TIME 6000000 ///< Wait Time = 6 seconds = 6000000
> microseconds
> +#define SPI_WAIT_PERIOD 10 ///< Wait Period = 10 microseconds
> +
> +///
> +/// Flash cycle Type
> +///
> +typedef enum {
> + FlashCycleRead,
> + FlashCycleWrite,
> + FlashCycleErase,
> + FlashCycleReadSfdp,
> + FlashCycleReadJedecId,
> + FlashCycleWriteStatus,
> + FlashCycleReadStatus,
> + FlashCycleMax
> +} FLASH_CYCLE_TYPE;
> +
> +///
> +/// Flash Component Number
> +///
> +typedef enum {
> + FlashComponent0,
> + FlashComponent1,
> + FlashComponentMax
> +} FLASH_COMPONENT_NUM;
> +
> +///
> +/// Private data structure definitions for the driver
> +///
> +#define PCH_SPI_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('P', 'S', 'P', 'I')
> +
> +typedef struct {
> + UINT32 Signature;
> + EFI_HANDLE Handle;
> + EFI_SPI_PROTOCOL SpiProtocol;
> + UINT16 PchAcpiBase;
> + UINTN PchSpiBase;
> + UINT16 ReadPermission;
> + UINT16 WritePermission;
> + UINT32 SfdpVscc0Value;
> + UINT32 SfdpVscc1Value;
> + UINT16 PchStrapBaseAddr;
> + UINT16 PchStrapSize;
> + UINT16 CpuStrapBaseAddr;
> + UINT16 CpuStrapSize;
> + UINT8 NumberOfComponents;
> + UINT32 Component1StartAddr;
> + UINT32 TotalFlashSize;
> +} SPI_INSTANCE;
> +
> +#define SPI_INSTANCE_FROM_SPIPROTOCOL(a) CR (a, SPI_INSTANCE,
> SpiProtocol, PCH_SPI_PRIVATE_DATA_SIGNATURE)
> +
> +//
> +// Function prototypes used by the SPI protocol.
> +//
> +
> +/**
> + Initialize an SPI protocol instance.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @exception EFI_UNSUPPORTED The PCH is not supported by this module
> +**/
> +EFI_STATUS
> +SpiProtocolConstructor (
> + IN SPI_INSTANCE *SpiInstance
> + );
> +
> +/**
> + This function is a hook for Spi to disable BIOS Write Protect
> +
> + @retval EFI_SUCCESS The protocol instance was properly initialized
> + @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in
> SMM phase
> +
> +**/
> +EFI_STATUS
> +EFIAPI
> +DisableBiosWriteProtect (
> + VOID
> + );
> +
> +/**
> + This function is a hook for Spi to enable BIOS Write Protect
> +
> +
> +**/
> +VOID
> +EFIAPI
> +EnableBiosWriteProtect (
> + VOID
> + );
> +
> +/**
> + Acquire pch spi mmio address.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval PchSpiBar0 return SPI MMIO address
> +**/
> +UINTN
> +AcquireSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + );
> +
> +/**
> + Release pch spi mmio address.
> +
> + @param[in] SpiInstance Pointer to SpiInstance to initialize
> +
> + @retval None
> +**/
> +VOID
> +ReleaseSpiBar0 (
> + IN SPI_INSTANCE *SpiInstance
> + );
> +
> +/**
> + Read data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[out] Buffer The Pointer to caller-allocated buffer containing
> the dada received.
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashRead (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *Buffer
> + );
> +
> +/**
> + Write data to the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in] Buffer Pointer to caller-allocated buffer containing the
> data sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWrite (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN UINT8 *Buffer
> + );
> +
> +/**
> + Erase some area on the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for flash cycle which is
> listed in the Descriptor.
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashErase (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount
> + );
> +
> +/**
> + Read SFDP data from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] Address The starting byte address for SFDP data read.
> + @param[in] ByteCount Number of bytes in SFDP data portion of the SPI
> cycle
> + @param[out] SfdpData The Pointer to caller-allocated buffer containing
> the SFDP data received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadSfdp (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + OUT UINT8 *SfdpData
> + );
> +
> +/**
> + Read Jedec Id from the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ComponentNumber The Componen Number for chip select
> + @param[in] ByteCount Number of bytes in JedecId data portion of the
> SPI cycle, the data size is 3 typically
> + @param[out] JedecId The Pointer to caller-allocated buffer containing
> JEDEC ID received
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadJedecId (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT8 ComponentNumber,
> + IN UINT32 ByteCount,
> + OUT UINT8 *JedecId
> + );
> +
> +/**
> + Write the status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[in] StatusValue The Pointer to caller-allocated buffer containing
> the value of Status register writing
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashWriteStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + IN UINT8 *StatusValue
> + );
> +
> +/**
> + Read status register in the flash part.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] ByteCount Number of bytes in Status data portion of the
> SPI cycle, the data size is 1 typically
> + @param[out] StatusValue The Pointer to caller-allocated buffer
> containing the value of Status register received.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolFlashReadStatus (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 ByteCount,
> + OUT UINT8 *StatusValue
> + );
> +
> +/**
> + Get the SPI region base and size, based on the enum type
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] FlashRegionType The Flash Region type for for the base
> address which is listed in the Descriptor.
> + @param[out] BaseAddress The Flash Linear Address for the Region 'n'
> Base
> + @param[out] RegionSize The size for the Region 'n'
> +
> + @retval EFI_SUCCESS Read success
> + @retval EFI_INVALID_PARAMETER Invalid region type given
> + @retval EFI_DEVICE_ERROR The region is not used
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolGetRegionAddress (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + OUT UINT32 *BaseAddress,
> + OUT UINT32 *RegionSize
> + );
> +
> +/**
> + Read PCH Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing PCH Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadPchSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + Read CPU Soft Strap Values
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
> + @param[in] ByteCount Number of bytes in SoftStrap data portion of
> the SPI cycle.
> + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> containing CPU Soft Strap Value.
> + If the value of ByteCount is 0, the data type of
> SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> Length
> + It is the caller's responsibility to make sure Buffer is large
> enough for the total number of bytes read.
> +
> + @retval EFI_SUCCESS Command succeed.
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> + @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
> +**/
> +EFI_STATUS
> +EFIAPI
> +SpiProtocolReadCpuSoftStrap (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINT32 SoftStrapAddr,
> + IN UINT32 ByteCount,
> + OUT VOID *SoftStrapValue
> + );
> +
> +/**
> + This function sends the programmed SPI command to the slave device.
> +
> + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> + @param[in] SpiRegionType The SPI Region type for flash cycle which is
> listed in the Descriptor
> + @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware
> Sequencing Flash Control Register) register
> + @param[in] Address The Flash Linear Address must fall within a region
> for which BIOS has access permissions.
> + @param[in] ByteCount Number of bytes in the data portion of the SPI
> cycle.
> + @param[in,out] Buffer Pointer to caller-allocated buffer containing the
> dada received or sent during the SPI cycle.
> +
> + @retval EFI_SUCCESS SPI command completes successfully.
> + @retval EFI_DEVICE_ERROR Device error, the command aborts
> abnormally.
> + @retval EFI_ACCESS_DENIED Some unrecognized command encountered
> in hardware sequencing mode
> + @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
> +**/
> +EFI_STATUS
> +SendSpiCmd (
> + IN EFI_SPI_PROTOCOL *This,
> + IN FLASH_REGION_TYPE FlashRegionType,
> + IN FLASH_CYCLE_TYPE FlashCycleType,
> + IN UINT32 Address,
> + IN UINT32 ByteCount,
> + IN OUT UINT8 *Buffer
> + );
> +
> +/**
> + Wait execution cycle to complete on the SPI interface.
> +
> + @param[in] This The SPI protocol instance
> + @param[in] PchSpiBar0 Spi MMIO base address
> + @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
> +
> + @retval TRUE SPI cycle completed on the interface.
> + @retval FALSE Time out while waiting the SPI cycle to complete.
> + It's not safe to program the next command on the SPI
> interface.
> +**/
> +BOOLEAN
> +WaitForSpiCycleComplete (
> + IN EFI_SPI_PROTOCOL *This,
> + IN UINTN PchSpiBar0,
> + IN BOOLEAN ErrorCheck
> + );
> +
> +#endif
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> new file mode 100644
> index 0000000000..4af462da47
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> @@ -0,0 +1,34 @@
> +## @file
> +# Library instance for ResetSystem library class for OVMF
> +#
> +# Copyright (c) 2006 - 2018 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010005
> + BASE_NAME = ResetSystemLib
> + FILE_GUID = 66564872-21d4-4d2a-a68b-1e844f980820
> + MODULE_TYPE = BASE
> + VERSION_STRING = 1.0
> + LIBRARY_CLASS = ResetSystemLib
> +
> +#
> +# The following information is for reference only and not required by the build
> tools.
> +#
> +# VALID_ARCHITECTURES = IA32 X64
> +#
> +
> +[Sources]
> + ResetSystemLib.c
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> +
> +[LibraryClasses]
> + DebugLib
> + IoLib
> + TimerLib
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> CommonLib.inf
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> CommonLib.inf
> new file mode 100644
> index 0000000000..b5c97f1930
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> CommonLib.inf
> @@ -0,0 +1,52 @@
> +## @file
> +# SMM Library instance of Spi Flash Common Library Class
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010017
> + BASE_NAME = SmmSpiFlashCommonLib
> + FILE_GUID = 9632D96E-E849-4217-9217-DC500B8AAE47
> + VERSION_STRING = 1.0
> + MODULE_TYPE = DXE_SMM_DRIVER
> + LIBRARY_CLASS = SpiFlashCommonLib|DXE_SMM_DRIVER
> + CONSTRUCTOR = SmmSpiFlashCommonLibConstructor
> +#
> +# The following information is for reference only and not required by the build
> tools.
> +#
> +# VALID_ARCHITECTURES = IA32 X64
> +#
> +
> +[LibraryClasses]
> + PciLib
> + IoLib
> + MemoryAllocationLib
> + BaseLib
> + UefiLib
> + SmmServicesTableLib
> + BaseMemoryLib
> + DebugLib
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsICH10Pkg/ICH10Pkg.dec
> + MinPlatformPkg/MinPlatformPkg.dec
> +
> +
> +[Pcd]
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
> +
> +[Sources]
> + SpiFlashCommonSmmLib.c
> + SpiFlashCommon.c
> +
> +[Protocols]
> + gEfiSmmSpiProtocolGuid ## CONSUMES
> +
> +[Depex.X64.DXE_SMM_DRIVER]
> + gEfiSmmSpiProtocolGuid
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> SpiCommonLib.inf
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> SpiCommonLib.inf
> new file mode 100644
> index 0000000000..11c832e487
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> SpiCommonLib.inf
> @@ -0,0 +1,33 @@
> +## @file
> +# Component description file for the PchSpiCommonLib
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010005
> + BASE_NAME = BasePchSpiCommonLib
> + FILE_GUID = A37CB67E-7D85-45B3-B07E-BF65BDB603E8
> + MODULE_TYPE = BASE
> + VERSION_STRING = 1.0
> + LIBRARY_CLASS = PchSpiCommonLib
> +
> +[Sources]
> + SpiCommon.c
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsICH10Pkg/ICH10Pkg.dec
> + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> + MinPlatformPkg/MinPlatformPkg.dec
> +
> +[LibraryClasses]
> + IoLib
> + DebugLib
> +
> +[Pcd]
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
> + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> new file mode 100644
> index 0000000000..a2d006ee35
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> @@ -0,0 +1,12 @@
> +## @file
> +# Component description file for the SkyLake SiPkg DXE libraries.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[LibraryClasses.common]
> + ResetSystemLib|$(PCH_PKG)/Library/ResetSystemLib/ResetSystemLib.inf
> +
> PchSpiCommonLib|$(PCH_PKG)/LibraryPrivate/BasePchSpiCommonLib/BasePc
> hSpiCommonLib.inf
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> new file mode 100644
> index 0000000000..78eca21a43
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> @@ -0,0 +1,9 @@
> +## @file
> +# Component description file for the SkyLake SiPkg DXE drivers.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> new file mode 100644
> index 0000000000..2d3a127c20
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> @@ -0,0 +1,9 @@
> +## @file
> +# Component description file for the SkyLake SiPkg PEI drivers.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> diff --git a/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> new file mode 100644
> index 0000000000..d079c593d9
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> @@ -0,0 +1,13 @@
> +## @file
> +# Component description file for the SkyLake SiPkg DXE drivers.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +!if gMinPlatformPkgTokenSpaceGuid.PcdBootToShellOnly == FALSE
> + INF $(PCH_PKG)/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> + INF $(PCH_PKG)/Spi/Smm/PchSpiSmm.inf
> +!endif
> diff --git
> a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> new file mode 100644
> index 0000000000..e23dd9f2fe
> --- /dev/null
> +++
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> @@ -0,0 +1,59 @@
> +## @file
> +# A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
> +# EFI_SMM_CONTROL2_PROTOCOL.
> +#
> +# We expect the PEI phase to have covered the following:
> +# - ensure that the underlying QEMU machine type be X58
> +# (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
> +# - ensure that the ACPI PM IO space be configured
> +# (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
> +#
> +# Our own entry point is responsible for confirming the SMI feature and for
> +# configuring it.
> +#
> +# Copyright (C) 2013, 2015, Red Hat, Inc.
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010005
> + BASE_NAME = SmmControl2Dxe
> + FILE_GUID = 1206F7CA-A475-4624-A83E-E6FC9BB38E49
> + MODULE_TYPE = DXE_RUNTIME_DRIVER
> + VERSION_STRING = 1.0
> + PI_SPECIFICATION_VERSION = 0x00010400
> + ENTRY_POINT = SmmControl2DxeEntryPoint
> +
> +#
> +# The following information is for reference only and not required by the build
> tools.
> +#
> +# VALID_ARCHITECTURES = IA32 X64
> +#
> +
> +[Sources]
> + SmmControl2Dxe.c
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> +
> +[LibraryClasses]
> + BaseLib
> + DebugLib
> + IoLib
> + PcdLib
> + PciLib
> + UefiBootServicesTableLib
> + UefiDriverEntryPoint
> +
> +[Protocols]
> + gEfiS3SaveStateProtocolGuid ## SOMETIMES_CONSUMES
> + gEfiSmmControl2ProtocolGuid ## PRODUCES
> +
> +[FeaturePcd]
> + gSimicsX58PkgTokenSpaceGuid.PcdSmmSmramRequire
> +
> +[Depex]
> + TRUE
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> new file mode 100644
> index 0000000000..f7fdd3abbe
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> @@ -0,0 +1,23 @@
> +/** @file
> + Header file for the PCH SPI SMM Driver.
> +
> + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +
> + SPDX-License-Identifier: BSD-2-Clause-Patent
> +**/
> +
> +#ifndef _PCH_SPI_H_
> +#define _PCH_SPI_H_
> +
> +#include <Library/IoLib.h>
> +#include <Library/DebugLib.h>
> +#include <Library/UefiDriverEntryPoint.h>
> +#include <Library/UefiBootServicesTableLib.h>
> +#include <Library/BaseLib.h>
> +#include <Library/BaseMemoryLib.h>
> +#include <Library/SmmServicesTableLib.h>
> +#include <PchAccess.h>
> +#include <Protocol/Spi.h>
> +#include <IncludePrivate/Library/PchSpiCommonLib.h>
> +
> +#endif
> diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> new file mode 100644
> index 0000000000..265af00ac0
> --- /dev/null
> +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> @@ -0,0 +1,44 @@
> +## @file
> +# Component description file for the SPI SMM driver.
> +#
> +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> +#
> +# SPDX-License-Identifier: BSD-2-Clause-Patent
> +#
> +##
> +
> +[Defines]
> + INF_VERSION = 0x00010017
> + BASE_NAME = PchSpiSmm
> + FILE_GUID = 27F4917B-A707-4aad-9676-26DF168CBF0D
> + VERSION_STRING = 1.0
> + MODULE_TYPE = DXE_SMM_DRIVER
> + PI_SPECIFICATION_VERSION = 1.10
> + ENTRY_POINT = InstallPchSpi
> +
> +
> + [LibraryClasses]
> + DebugLib
> + IoLib
> + UefiDriverEntryPoint
> + UefiBootServicesTableLib
> + BaseLib
> + SmmServicesTableLib
> + PchSpiCommonLib
> +
> +[Packages]
> + MdePkg/MdePkg.dec
> + SimicsICH10Pkg/ICH10Pkg.dec
> +
> +[Sources]
> + PchSpi.h
> + PchSpi.c
> +
> +
> +[Protocols]
> + gEfiSmmSpiProtocolGuid # PRODUCES #SERVER_BIOS
> +
> +
> +[Depex]
> + gEfiSmmBase2ProtocolGuid #This is for SmmServicesTableLib
> + AND gEfiSmmCpuProtocolGuid # This is for
> CpuSmmDisableBiosWriteProtect()
> --
> 2.16.2.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#46309): https://edk2.groups.io/g/devel/message/46309
Mute This Topic: https://groups.io/mt/32816096/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
Thanks David. No more comments for this patch.
> -----Original Message-----
> From: Wei, David Y
> Sent: Friday, August 23, 2019 9:40 AM
> To: Kubacki, Michael A <michael.a.kubacki@intel.com>; devel@edk2.groups.io
> Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>;
> Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince
> <prince.agyeman@intel.com>; Desimone, Nathaniel L
> <nathaniel.l.desimone@intel.com>; Kinney, Michael D
> <michael.d.kinney@intel.com>
> Subject: RE: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for
> SimicsICH10
>
> Hi Mike,
> Please see the updates online below. Please let me know if you have any more
> comments.
>
> Thanks
> David
>
> -----Original Message-----
> From: Kubacki, Michael A
> Sent: Monday, August 19, 2019 6:04 PM
> To: Wei, David Y <david.y.wei@intel.com>; devel@edk2.groups.io
> Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>;
> Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince
> <prince.agyeman@intel.com>; Desimone, Nathaniel L
> <nathaniel.l.desimone@intel.com>; Kinney, Michael D
> <michael.d.kinney@intel.com>
> Subject: RE: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for
> SimicsICH10
>
> Feedback I could not find already noted elsewhere:
>
> 1.
> /Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePc
> hSpiCommonLib.inf:
> This silicon package should not have a dependency on MinPlatformPkg.dec.
> Ydwei: done
> 2.
> /Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePc
> hSpiCommonLib.inf:
> This silicon package should not have a dependency on
> SimicsOpenBoardPkg.dec.
> Ydwei: done
> 3. Although noted elsewhere: I also prefer Pascal naming as well so
> SimicsIch10Pkg.
> Ydwei: done
> 4. /Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c:
> "Reset System Library functions for OVMF" - replace OVMF with Simics
> ICH10.
> Ydwei: done
> 5. /Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf:
> This silicon package INF should not have a dependency on
> MinPlatformPkg.dec.
> Ydwei: done
> 6.
> /Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> This silicon package INF should not have a dependency on
> MinPlatformPkg.dec.
> Ydwei: done
> 7.
> /Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonib/SmmSpiFlash
> CommonLib:
> This silicon package INF should not have a dependency on
> MinPlatformPkg.dec.
> Ydwei: done
> > -----Original Message-----
> > From: Wei, David Y
> > Sent: Friday, August 9, 2019 3:47 PM
> > To: devel@edk2.groups.io
> > Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>;
> > Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince
> > <prince.agyeman@intel.com>; Kubacki, Michael A
> > <michael.a.kubacki@intel.com>; Desimone, Nathaniel L
> > <nathaniel.l.desimone@intel.com>; Kinney, Michael D
> > <michael.d.kinney@intel.com>
> > Subject: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for
> > SimicsICH10
> >
> > Add PCH Pkg for SimicsICH10. It is added for simics QSP project support
> >
> > Cc: Hao Wu <hao.a.wu@intel.com>
> > Cc: Liming Gao <liming.gao@intel.com>
> > Cc: Ankit Sinha <ankit.sinha@intel.com>
> > Cc: Agyeman Prince <prince.agyeman@intel.com>
> > Cc: Kubacki Michael A <michael.a.kubacki@intel.com>
> > Cc: Nate DeSimone <nathaniel.l.desimone@intel.com>
> > Cc: Michael D Kinney <michael.d.kinney@intel.com>
> > Contributed-under: TianoCore Contribution Agreement 1.0
> >
> > Signed-off-by: David Wei <david.y.wei@intel.com>
> > ---
> > .../Library/ResetSystemLib/ResetSystemLib.c | 137 +++
> > .../Library/SmmSpiFlashCommonLib/SpiFlashCommon.c | 194 +++++
> > .../SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c | 54 ++
> > .../LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c | 935
> > +++++++++++++++++++++
> > .../SmmControl/RuntimeDxe/SmmControl2Dxe.c | 410 +++++++++
> > Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c | 175 ++++
> > Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec | 22 +
> > .../Include/Library/SpiFlashCommonLib.h | 98 +++
> > Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h | 43 +
> > Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h | 94 +++
> > .../SimicsICH10Pkg/Include/PchReservedResources.h | 60 ++
> > .../Intel/SimicsICH10Pkg/Include/Protocol/Spi.h | 295 +++++++
> > .../SimicsICH10Pkg/Include/Register/PchRegsPmc.h | 647 ++++++++++++++
> > .../SimicsICH10Pkg/Include/Register/PchRegsSpi.h | 304 +++++++
> > .../IncludePrivate/Library/PchSpiCommonLib.h | 396 +++++++++
> > .../Library/ResetSystemLib/ResetSystemLib.inf | 34 +
> > .../SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf | 52 ++
> > .../BasePchSpiCommonLib/BasePchSpiCommonLib.inf | 33 +
> > Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc | 12 +
> > .../Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf | 9 +
> > .../Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf | 9 +
> > .../Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf | 13 +
> > .../SmmControl/RuntimeDxe/SmmControl2Dxe.inf | 59 ++
> > Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h | 23 +
> > Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf | 44 +
> > 25 files changed, 4152 insertions(+)
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> > create mode 100644
> >
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mo
> > n.c
> > create mode 100644
> >
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCom
> mo
> > nSmmLib.c
> > create mode 100644
> >
> Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCom
> mo
> > n.c
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> > create mode 100644
> > Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> > create mode 100644
> >
> Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlash
> Co
> > mmonLib.inf
> > create mode 100644
> >
> Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePch
> Spi
> > CommonLib.inf
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> > create mode 100644
> Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> > create mode 100644
> Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> > create mode 100644
> >
> Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> > create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> > create mode 100644
> Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> >
> > diff --git
> > a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> > b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> > new file mode 100644
> > index 0000000000..46355e191c
> > --- /dev/null
> > +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
> > @@ -0,0 +1,137 @@
> > +/** @file
> > + Reset System Library functions for OVMF
> > +
> > + Copyright (c) 2006 - 2016 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#include <Base.h>
> > +
> > +#include <Library/BaseLib.h>
> > +#include <Library/DebugLib.h>
> > +#include <Library/IoLib.h>
> > +#include <Library/TimerLib.h>
> > +#include <IndustryStandard/X58Ich10.h>
> > +
> > +
> > +VOID
> > +AcpiPmControl (
> > + UINTN SuspendType
> > + )
> > +{
> > + ASSERT (SuspendType < 6);
> > + DEBUG((EFI_D_ERROR, "SuspendType = 0x%x\n", SuspendType));
> > +
> > + IoBitFieldWrite16 (ICH10_PMBASE_IO + 4, 10, 13, (UINT16)
> SuspendType);
> > + IoOr16 (ICH10_PMBASE_IO + 0x04, BIT13);
> > + CpuDeadLoop ();
> > +}
> > +
> > +/**
> > + Calling this function causes a system-wide reset. This sets
> > + all circuitry within the system to its initial state. This type of reset
> > + is asynchronous to system operation and operates without regard to
> > + cycle boundaries.
> > +
> > + System reset should not return, if it returns, it means the system does
> > + not support cold reset.
> > +**/
> > +VOID
> > +EFIAPI
> > +ResetCold (
> > + VOID
> > + )
> > +{
> > + DEBUG((EFI_D_ERROR, "ResetCold_CF9\n"));
> > + IoWrite8 (0xCF9, BIT3 | BIT2 | BIT1); // 1st choice: PIIX3 RCR, RCPU|SRST
> > + MicroSecondDelay (50);
> > +
> > + DEBUG((EFI_D_ERROR, "ResetCold_Port64\n"));
> > + IoWrite8 (0x64, 0xfe); // 2nd choice: keyboard controller
> > + CpuDeadLoop ();
> > +}
> > +
> > +/**
> > + Calling this function causes a system-wide initialization. The processors
> > + are set to their initial state, and pending cycles are not corrupted.
> > +
> > + System reset should not return, if it returns, it means the system does
> > + not support warm reset.
> > +**/
> > +VOID
> > +EFIAPI
> > +ResetWarm (
> > + VOID
> > + )
> > +{
> > + DEBUG((EFI_D_ERROR, "ResetWarm\n"));
> > + //
> > + //BUGBUG workaround for warm reset
> > + //
> > + IoWrite8(0xCF9, BIT2 | BIT1);
> > + MicroSecondDelay(50);
> > +
> > + IoWrite8 (0x64, 0xfe);
> > + CpuDeadLoop ();
> > +}
> > +
> > +/**
> > + Calling this function causes the system to enter a power state equivalent
> > + to the ACPI G2/S5 or G3 states.
> > +
> > + System shutdown should not return, if it returns, it means the system
> does
> > + not support shut down reset.
> > +**/
> > +VOID
> > +EFIAPI
> > +ResetShutdown (
> > + VOID
> > + )
> > +{
> > + DEBUG((EFI_D_ERROR, "ResetShutdown\n"));
> > + AcpiPmControl (0);
> > + ASSERT (FALSE);
> > +}
> > +
> > +
> > +/**
> > + Calling this function causes the system to enter a power state for capsule
> > + update.
> > +
> > + Reset update should not return, if it returns, it means the system does
> > + not support capsule update.
> > +
> > +**/
> > +VOID
> > +EFIAPI
> > +EnterS3WithImmediateWake (
> > + VOID
> > + )
> > +{
> > + DEBUG((EFI_D_ERROR, "EnterS3WithImmediateWake\n"));
> > + AcpiPmControl (1);
> > + ASSERT (FALSE);
> > +}
> > +
> > +/**
> > + This function causes a systemwide reset. The exact type of the reset is
> > + defined by the EFI_GUID that follows the Null-terminated Unicode string
> > passed
> > + into ResetData. If the platform does not recognize the EFI_GUID in
> ResetData
> > + the platform must pick a supported reset type to perform.The platform
> may
> > + optionally log the parameters from any non-normal reset that occurs.
> > +
> > + @param[in] DataSize The size, in bytes, of ResetData.
> > + @param[in] ResetData The data buffer starts with a Null-terminated
> string,
> > + followed by the EFI_GUID.
> > +**/
> > +VOID
> > +EFIAPI
> > +ResetPlatformSpecific (
> > + IN UINTN DataSize,
> > + IN VOID *ResetData
> > + )
> > +{
> > + DEBUG((EFI_D_ERROR, "ResetPlatformSpecific\n"));
> > + ResetCold ();
> > +}
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCo
> m
> > mon.c
> >
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCo
> m
> > mon.c
> > new file mode 100644
> > index 0000000000..3d4e24eac6
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCo
> m
> > mon.c
> > @@ -0,0 +1,194 @@
> > +/** @file
> > + Wrap EFI_SPI_PROTOCOL to provide some library level interfaces
> > + for module use.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#include <Library/SpiFlashCommonLib.h>
> > +#include <Library/IoLib.h>
> > +#include <Library/PciLib.h>
> > +#include <Protocol/Spi.h>
> > +
> > +
> > +EFI_SPI_PROTOCOL *mSpiProtocol;
> > +
> > +//
> > +// FlashAreaBaseAddress and Size for boottime and runtime usage.
> > +//
> > +UINTN mFlashAreaBaseAddress = 0;
> > +UINTN mFlashAreaSize = 0;
> > +
> > +/**
> > + Enable block protection on the Serial Flash device.
> > +
> > + @retval EFI_SUCCESS Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashLock (
> > + VOID
> > + )
> > +{
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + Read NumBytes bytes of data from the address specified by
> > + PAddress into Buffer.
> > +
> > + @param[in] Address The starting physical address of the read.
> > + @param[in,out] NumBytes On input, the number of bytes to read. On
> > output, the number
> > + of bytes actually read.
> > + @param[out] Buffer The destination data buffer for the read.
> > +
> > + @retval EFI_SUCCESS Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashRead (
> > + IN UINTN Address,
> > + IN OUT UINT32 *NumBytes,
> > + OUT UINT8 *Buffer
> > + )
> > +{
> > + ASSERT ((NumBytes != NULL) && (Buffer != NULL));
> > + if ((NumBytes == NULL) || (Buffer == NULL)) {
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + //
> > + // This function is implemented specifically for those platforms
> > + // at which the SPI device is memory mapped for read. So this
> > + // function just do a memory copy for Spi Flash Read.
> > + //
> > + CopyMem (Buffer, (VOID *) Address, *NumBytes);
> > +
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + Write NumBytes bytes of data from Buffer to the address specified by
> > + PAddresss.
> > +
> > + @param[in] Address The starting physical address of the write.
> > + @param[in,out] NumBytes On input, the number of bytes to write.
> On
> > output,
> > + the actual number of bytes written.
> > + @param[in] Buffer The source data buffer for the write.
> > +
> > + @retval EFI_SUCCESS Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashWrite (
> > + IN UINTN Address,
> > + IN OUT UINT32 *NumBytes,
> > + IN UINT8 *Buffer
> > + )
> > +{
> > + EFI_STATUS Status;
> > + UINTN Offset;
> > + UINT32 Length;
> > + UINT32 RemainingBytes;
> > +
> > + ASSERT ((NumBytes != NULL) && (Buffer != NULL));
> > + if ((NumBytes == NULL) || (Buffer == NULL)) {
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + ASSERT (Address >= mFlashAreaBaseAddress);
> > +
> > + Offset = Address - mFlashAreaBaseAddress;
> > +
> > + ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
> > +
> > + Status = EFI_SUCCESS;
> > + RemainingBytes = *NumBytes;
> > +
> > +
> > + while (RemainingBytes > 0) {
> > + if (RemainingBytes > SECTOR_SIZE_4KB) {
> > + Length = SECTOR_SIZE_4KB;
> > + } else {
> > + Length = RemainingBytes;
> > + }
> > + Status = mSpiProtocol->FlashWrite (
> > + mSpiProtocol,
> > + FlashRegionBios,
> > + (UINT32) Offset,
> > + Length,
> > + Buffer
> > + );
> > + if (EFI_ERROR (Status)) {
> > + break;
> > + }
> > + RemainingBytes -= Length;
> > + Offset += Length;
> > + Buffer += Length;
> > + }
> > +
> > + //
> > + // Actual number of bytes written
> > + //
> > + *NumBytes -= RemainingBytes;
> > +
> > + return Status;
> > +}
> > +
> > +/**
> > + Erase the block starting at Address.
> > +
> > + @param[in] Address The starting physical address of the block to be
> > erased.
> > + This library assume that caller garantee that the PAddress
> > + is at the starting address of this block.
> > + @param[in] NumBytes On input, the number of bytes of the logical
> block
> > to be erased.
> > + On output, the actual number of bytes erased.
> > +
> > + @retval EFI_SUCCESS. Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashBlockErase (
> > + IN UINTN Address,
> > + IN UINTN *NumBytes
> > + )
> > +{
> > + EFI_STATUS Status;
> > + UINTN Offset;
> > + UINTN RemainingBytes;
> > +
> > + ASSERT (NumBytes != NULL);
> > + if (NumBytes == NULL) {
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + ASSERT (Address >= mFlashAreaBaseAddress);
> > +
> > + Offset = Address - mFlashAreaBaseAddress;
> > +
> > + ASSERT ((*NumBytes % SECTOR_SIZE_4KB) == 0);
> > + ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
> > +
> > + Status = EFI_SUCCESS;
> > + RemainingBytes = *NumBytes;
> > +
> > +
> > + Status = mSpiProtocol->FlashErase (
> > + mSpiProtocol,
> > + FlashRegionBios,
> > + (UINT32) Offset,
> > + (UINT32) RemainingBytes
> > + );
> > + return Status;
> > +}
> > +
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCo
> m
> > monSmmLib.c
> >
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCo
> m
> > monSmmLib.c
> > new file mode 100644
> > index 0000000000..1e5cd0d744
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCo
> m
> > monSmmLib.c
> > @@ -0,0 +1,54 @@
> > +/** @file
> > + SMM Library instance of SPI Flash Common Library Class
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#include <Library/SpiFlashCommonLib.h>
> > +#include <Library/SmmServicesTableLib.h>
> > +#include <Protocol/Spi.h>
> > +
> > +extern EFI_SPI_PROTOCOL *mSpiProtocol;
> > +
> > +extern UINTN mFlashAreaBaseAddress;
> > +extern UINTN mFlashAreaSize;
> > +
> > +/**
> > + The library constructuor.
> > +
> > + The function does the necessary initialization work for this library
> > + instance.
> > +
> > + @param[in] ImageHandle The firmware allocated handle for the UEFI
> > image.
> > + @param[in] SystemTable A pointer to the EFI system table.
> > +
> > + @retval EFI_SUCCESS The function always return EFI_SUCCESS for
> now.
> > + It will ASSERT on error for debug version.
> > + @retval EFI_ERROR Please reference LocateProtocol for error code
> > details.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SmmSpiFlashCommonLibConstructor (
> > + IN EFI_HANDLE ImageHandle,
> > + IN EFI_SYSTEM_TABLE *SystemTable
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + mFlashAreaBaseAddress = (UINTN)PcdGet32 (PcdFlashAreaBaseAddress);
> > + mFlashAreaSize = (UINTN)PcdGet32 (PcdFlashAreaSize);
> > +
> > + //
> > + // Locate the SMM SPI protocol.
> > + //
> > + Status = gSmst->SmmLocateProtocol (
> > + &gEfiSmmSpiProtocolGuid,
> > + NULL,
> > + (VOID **) &mSpiProtocol
> > + );
> > + ASSERT_EFI_ERROR (Status);
> > +
> > + return Status;
> > +}
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCo
> m
> > mon.c
> >
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCo
> m
> > mon.c
> > new file mode 100644
> > index 0000000000..77fb76d7cd
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCo
> m
> > mon.c
> > @@ -0,0 +1,935 @@
> > +/** @file
> > + PCH SPI Common Driver implements the SPI Host Controller Compatibility
> > Interface.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#include <Uefi/UefiBaseType.h>
> > +#include <Library/IoLib.h>
> > +#include <Library/DebugLib.h>
> > +#include <Library/BaseMemoryLib.h>
> > +#include <IndustryStandard/Pci30.h>
> > +#include <PchAccess.h>
> > +#include <Protocol/Spi.h>
> > +#include <IncludePrivate/Library/PchSpiCommonLib.h>
> > +#include <IndustryStandard/X58Ich10.h>
> > +
> > +/**
> > + Initialize an SPI protocol instance.
> > +
> > + @param[in] SpiInstance Pointer to SpiInstance to initialize
> > +
> > + @retval EFI_SUCCESS The protocol instance was properly
> initialized
> > + @exception EFI_UNSUPPORTED The PCH is not supported by this
> module
> > +**/
> > +EFI_STATUS
> > +SpiProtocolConstructor (
> > + IN SPI_INSTANCE *SpiInstance
> > + )
> > +{
> > + UINTN PchSpiBar0;
> > +
> > + //
> > + // Initialize the SPI protocol instance
> > + //
> > + SpiInstance->Signature =
> PCH_SPI_PRIVATE_DATA_SIGNATURE;
> > + SpiInstance->Handle = NULL;
> > + SpiInstance->SpiProtocol.Revision = PCH_SPI_SERVICES_REVISION;
> > + SpiInstance->SpiProtocol.FlashRead = SpiProtocolFlashRead;
> > + SpiInstance->SpiProtocol.FlashWrite = SpiProtocolFlashWrite;
> > + SpiInstance->SpiProtocol.FlashErase = SpiProtocolFlashErase;
> > + SpiInstance->SpiProtocol.FlashReadSfdp = SpiProtocolFlashReadSfdp;
> > + SpiInstance->SpiProtocol.FlashReadJedecId =
> SpiProtocolFlashReadJedecId;
> > + SpiInstance->SpiProtocol.FlashWriteStatus = SpiProtocolFlashWriteStatus;
> > + SpiInstance->SpiProtocol.FlashReadStatus = SpiProtocolFlashReadStatus;
> > + SpiInstance->SpiProtocol.GetRegionAddress =
> SpiProtocolGetRegionAddress;
> > + SpiInstance->SpiProtocol.ReadPchSoftStrap =
> SpiProtocolReadPchSoftStrap;
> > + SpiInstance->SpiProtocol.ReadCpuSoftStrap =
> SpiProtocolReadCpuSoftStrap;
> > +
> > + SpiInstance->PchAcpiBase = ICH10_PMBASE_IO;
> > + ASSERT (SpiInstance->PchAcpiBase != 0);
> > +
> > + PchSpiBar0 = RCRB + SPIBAR;
> > +
> > + if (PchSpiBar0 == 0) {
> > + DEBUG ((DEBUG_ERROR, "ERROR : PchSpiBar0 is invalid!\n"));
> > + ASSERT (FALSE);
> > + }
> > +
> > + if ((MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC) &
> > B_PCH_SPI_HSFSC_FDV) == 0) {
> > + DEBUG ((DEBUG_ERROR, "ERROR : SPI Flash Signature invalid, cannot
> use
> > the Hardware Sequencing registers!\n"));
> > + ASSERT (FALSE);
> > + }
> > + SpiInstance->ReadPermission = 0xffff;
> > + SpiInstance->WritePermission = 0xffff;
> > + DEBUG ((DEBUG_INFO, "Flash Region Permission: Read- 0x%04x; Write=
> > 0x%04x\n",
> > + SpiInstance->ReadPermission,
> > + SpiInstance->WritePermission));
> > +
> > + //
> > + SpiInstance->TotalFlashSize = PcdGet32(PcdFlashAreaSize);
> > + DEBUG ((DEBUG_INFO, "Total Flash Size : %0x\n", SpiInstance-
> > >TotalFlashSize));
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + Delay for at least the request number of microseconds for Runtime usage.
> > +
> > + @param[in] ABase Acpi base address
> > + @param[in] Microseconds Number of microseconds to delay.
> > +
> > +**/
> > +VOID
> > +EFIAPI
> > +PchPmTimerStallRuntimeSafe (
> > + IN UINT16 ABase,
> > + IN UINTN Microseconds
> > + )
> > +{
> > + UINTN Ticks;
> > + UINTN Counts;
> > + UINTN CurrentTick;
> > + UINTN OriginalTick;
> > + UINTN RemainingTick;
> > +
> > + if (Microseconds == 0) {
> > + return;
> > + }
> > +
> > + OriginalTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) &
> > B_PCH_ACPI_PM1_TMR_VAL;
> > + 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 / V_PCH_ACPI_PM1_TMR_MAX_VAL;
> > +
> > + //
> > + // Remaining clocks within one loop
> > + //
> > + RemainingTick = Ticks % V_PCH_ACPI_PM1_TMR_MAX_VAL;
> > +
> > + //
> > + // 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) || (RemainingTick > CurrentTick)) {
> > + CurrentTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) &
> > B_PCH_ACPI_PM1_TMR_VAL;
> > + //
> > + // Check if timer overflow
> > + //
> > + if ((CurrentTick < OriginalTick)) {
> > + if (Counts != 0) {
> > + Counts--;
> > + } else {
> > + //
> > + // If timer overflow and Counts equ to 0, that means we already
> stalled
> > more than
> > + // RemainingTick, break the loop here
> > + //
> > + break;
> > + }
> > + }
> > +
> > + OriginalTick = CurrentTick;
> > + }
> > +}
> > +
> > +/**
> > + Read data from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[out] Buffer The Pointer to caller-allocated buffer
> containing
> > the dada received.
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashRead (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *Buffer
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionType,
> > + FlashCycleRead,
> > + Address,
> > + ByteCount,
> > + Buffer
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Write data to the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[in] Buffer Pointer to caller-allocated buffer containing
> the
> > data sent during the SPI cycle.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashWrite (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + IN UINT8 *Buffer
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionType,
> > + FlashCycleWrite,
> > + Address,
> > + ByteCount,
> > + Buffer
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Erase some area on the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashErase (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionType,
> > + FlashCycleErase,
> > + Address,
> > + ByteCount,
> > + NULL
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Read SFDP data from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ComponentNumber The Componen Number for chip
> select
> > + @param[in] Address The starting byte address for SFDP data read.
> > + @param[in] ByteCount Number of bytes in SFDP data portion of
> the SPI
> > cycle
> > + @param[out] SfdpData The Pointer to caller-allocated buffer
> containing
> > the SFDP data received
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashReadSfdp (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT8 ComponentNumber,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *SfdpData
> > + )
> > +{
> > + SPI_INSTANCE *SpiInstance;
> > + EFI_STATUS Status;
> > + UINT32 FlashAddress;
> > +
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > + Status = EFI_SUCCESS;
> > +
> > + if (ComponentNumber > SpiInstance->NumberOfComponents) {
> > + ASSERT (FALSE);
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + FlashAddress = 0;
> > + if (ComponentNumber == FlashComponent1) {
> > + FlashAddress = SpiInstance->Component1StartAddr;
> > + }
> > + FlashAddress += Address;
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionAll,
> > + FlashCycleReadSfdp,
> > + FlashAddress,
> > + ByteCount,
> > + SfdpData
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Read Jedec Id from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ComponentNumber The Componen Number for chip
> select
> > + @param[in] ByteCount Number of bytes in JedecId data portion of
> the
> > SPI cycle, the data size is 3 typically
> > + @param[out] JedecId The Pointer to caller-allocated buffer
> containing
> > JEDEC ID received
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashReadJedecId (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT8 ComponentNumber,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *JedecId
> > + )
> > +{
> > + SPI_INSTANCE *SpiInstance;
> > + EFI_STATUS Status;
> > + UINT32 Address;
> > +
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > + Status = EFI_SUCCESS;
> > +
> > + if (ComponentNumber > SpiInstance->NumberOfComponents) {
> > + ASSERT (FALSE);
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + Address = 0;
> > + if (ComponentNumber == FlashComponent1) {
> > + Address = SpiInstance->Component1StartAddr;
> > + }
> > +
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionAll,
> > + FlashCycleReadJedecId,
> > + Address,
> > + ByteCount,
> > + JedecId
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Write the status register in the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ByteCount Number of bytes in Status data portion of
> the
> > SPI cycle, the data size is 1 typically
> > + @param[in] StatusValue The Pointer to caller-allocated buffer
> containing
> > the value of Status register writing
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashWriteStatus (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 ByteCount,
> > + IN UINT8 *StatusValue
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionAll,
> > + FlashCycleWriteStatus,
> > + 0,
> > + ByteCount,
> > + StatusValue
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Read status register in the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ByteCount Number of bytes in Status data portion of
> the
> > SPI cycle, the data size is 1 typically
> > + @param[out] StatusValue The Pointer to caller-allocated buffer
> > containing the value of Status register received.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashReadStatus (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *StatusValue
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + //
> > + // Sends the command to the SPI interface to execute.
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionAll,
> > + FlashCycleReadStatus,
> > + 0,
> > + ByteCount,
> > + StatusValue
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Get the SPI region base and size, based on the enum type
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for for the base
> > address which is listed in the Descriptor.
> > + @param[out] BaseAddress The Flash Linear Address for the Region
> 'n'
> > Base
> > + @param[out] RegionSize The size for the Region 'n'
> > +
> > + @retval EFI_SUCCESS Read success
> > + @retval EFI_INVALID_PARAMETER Invalid region type given
> > + @retval EFI_DEVICE_ERROR The region is not used
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolGetRegionAddress (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + OUT UINT32 *BaseAddress,
> > + OUT UINT32 *RegionSize
> > + )
> > +{
> > + SPI_INSTANCE *SpiInstance;
> > + UINTN PchSpiBar0;
> > + UINT32 ReadValue;
> > +
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > +
> > + if (FlashRegionType >= FlashRegionMax) {
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + if (FlashRegionType == FlashRegionAll) {
> > + *BaseAddress = 0;
> > + *RegionSize = SpiInstance->TotalFlashSize;
> > + return EFI_SUCCESS;
> > + }
> > +
> > + PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
> > + ReadValue = MmioRead32 (PchSpiBar0 + (R_PCH_SPI_FREG0_FLASHD +
> > (S_PCH_SPI_FREGX * ((UINT32) FlashRegionType))));
> > + ReleaseSpiBar0 (SpiInstance);
> > +
> > + //
> > + // If the region is not used, the Region Base is 7FFFh and Region Limit is
> 0000h
> > + //
> > + if (ReadValue == B_PCH_SPI_FREGX_BASE_MASK) {
> > + return EFI_DEVICE_ERROR;
> > + }
> > + *BaseAddress = ((ReadValue & B_PCH_SPI_FREGX_BASE_MASK) >>
> > N_PCH_SPI_FREGX_BASE) <<
> > + N_PCH_SPI_FREGX_BASE_REPR;
> > + //
> > + // Region limit address Bits[11:0] are assumed to be FFFh
> > + //
> > + *RegionSize = ((((ReadValue & B_PCH_SPI_FREGX_LIMIT_MASK) >>
> > N_PCH_SPI_FREGX_LIMIT) + 1) <<
> > + N_PCH_SPI_FREGX_LIMIT_REPR) - *BaseAddress;
> > +
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + Read PCH Soft Strap Values
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> > + @param[in] ByteCount Number of bytes in SoftStrap data portion
> of
> > the SPI cycle
> > + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> > containing PCH Soft Strap Value.
> > + If the value of ByteCount is 0, the data type of
> > SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> > Length
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolReadPchSoftStrap (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 SoftStrapAddr,
> > + IN UINT32 ByteCount,
> > + OUT VOID *SoftStrapValue
> > + )
> > +{
> > + SPI_INSTANCE *SpiInstance;
> > + UINT32 StrapFlashAddr;
> > + EFI_STATUS Status;
> > +
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > +
> > + if (ByteCount == 0) {
> > + *(UINT16 *) SoftStrapValue = SpiInstance->PchStrapSize;
> > + return EFI_SUCCESS;
> > + }
> > +
> > + if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->PchStrapSize) {
> > + ASSERT (FALSE);
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + //
> > + // PCH Strap Flash Address = FPSBA + RamAddr
> > + //
> > + StrapFlashAddr = SpiInstance->PchStrapBaseAddr + SoftStrapAddr;
> > +
> > + //
> > + // Read PCH Soft straps from using execute command
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionDescriptor,
> > + FlashCycleRead,
> > + StrapFlashAddr,
> > + ByteCount,
> > + SoftStrapValue
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + Read CPU Soft Strap Values
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SoftStrapAddr CPU Soft Strap address offset from
> FCPUSBA.
> > + @param[in] ByteCount Number of bytes in SoftStrap data portion
> of
> > the SPI cycle.
> > + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> > containing CPU Soft Strap Value.
> > + If the value of ByteCount is 0, the data type of
> > SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> > Length
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolReadCpuSoftStrap (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 SoftStrapAddr,
> > + IN UINT32 ByteCount,
> > + OUT VOID *SoftStrapValue
> > + )
> > +{
> > + SPI_INSTANCE *SpiInstance;
> > + UINT32 StrapFlashAddr;
> > + EFI_STATUS Status;
> > +
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > +
> > + if (ByteCount == 0) {
> > + *(UINT16 *) SoftStrapValue = SpiInstance->CpuStrapSize;
> > + return EFI_SUCCESS;
> > + }
> > +
> > + if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->CpuStrapSize) {
> > + ASSERT (FALSE);
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + //
> > + // CPU Strap Flash Address = FCPUSBA + RamAddr
> > + //
> > + StrapFlashAddr = SpiInstance->CpuStrapBaseAddr + SoftStrapAddr;
> > +
> > + //
> > + // Read Cpu Soft straps from using execute command
> > + //
> > + Status = SendSpiCmd (
> > + This,
> > + FlashRegionDescriptor,
> > + FlashCycleRead,
> > + StrapFlashAddr,
> > + ByteCount,
> > + SoftStrapValue
> > + );
> > + return Status;
> > +}
> > +
> > +/**
> > + This function sends the programmed SPI command to the slave device.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SpiRegionType The SPI Region type for flash cycle which
> is
> > listed in the Descriptor
> > + @param[in] FlashCycleType The Flash SPI cycle type list in HSFC
> (Hardware
> > Sequencing Flash Control Register) register
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[in,out] Buffer Pointer to caller-allocated buffer containing
> the
> > dada received or sent during the SPI cycle.
> > +
> > + @retval EFI_SUCCESS SPI command completes successfully.
> > + @retval EFI_DEVICE_ERROR Device error, the command aborts
> > abnormally.
> > + @retval EFI_ACCESS_DENIED Some unrecognized command
> encountered
> > in hardware sequencing mode
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > +**/
> > +EFI_STATUS
> > +SendSpiCmd (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN FLASH_CYCLE_TYPE FlashCycleType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + IN OUT UINT8 *Buffer
> > + )
> > +{
> > + EFI_STATUS Status;
> > + UINT32 Index;
> > + SPI_INSTANCE *SpiInstance;
> > + UINTN SpiBaseAddress;
> > + UINTN PchSpiBar0;
> > + UINT32 HardwareSpiAddr;
> > + UINT32 FlashRegionSize;
> > + UINT32 SpiDataCount;
> > + UINT32 FlashCycle;
> > + UINT32 SmiEnSave;
> > + UINT16 ABase;
> > +
> > + Status = EFI_SUCCESS;
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > + SpiBaseAddress = SpiInstance->PchSpiBase;
> > + PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
> > + SpiBaseAddress = SpiInstance->PchSpiBase;
> > + ABase = SpiInstance->PchAcpiBase;
> > +
> > + //
> > + // Disable SMIs to make sure normal mode flash access is not interrupted
> by
> > an SMI
> > + // whose SMI handler accesses flash (e.g. for error logging)
> > + //
> > + // *** NOTE: if the SMI_LOCK bit is set (i.e., PMC PCI Offset A0h [4]='1'),
> > + // clearing B_GBL_SMI_EN will not have effect. In this situation, some
> other
> > + // synchronization methods must be applied here or in the consumer of
> the
> > + // SendSpiCmd. An example method is disabling the specific SMI sources
> > + // whose SMI handlers access flash before flash cycle and re-enabling the
> SMI
> > + // sources after the flash cycle .
> > + //
> > + SmiEnSave = IoRead32 ((UINTN) (ABase + R_PCH_SMI_EN));
> > + IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave & (UINT32)
> > (~B_PCH_SMI_EN_GBL_SMI));
> > +
> > + //
> > + // If it's write cycle, disable Prefetching, Caching and disable BIOS Write
> > Protect
> > + //
> > + if ((FlashCycleType == FlashCycleWrite) ||
> > + (FlashCycleType == FlashCycleErase)) {
> > + Status = DisableBiosWriteProtect ();
> > + if (EFI_ERROR (Status)) {
> > + goto SendSpiCmdEnd;
> > + }
> > + }
> > + //
> > + // Make sure it's safe to program the command.
> > + //
> > + if (!WaitForSpiCycleComplete (This, PchSpiBar0, FALSE)) {
> > + Status = EFI_DEVICE_ERROR;
> > + goto SendSpiCmdEnd;
> > + }
> > +
> > + Status = SpiProtocolGetRegionAddress (This, FlashRegionType,
> > &HardwareSpiAddr, &FlashRegionSize);
> > + if (EFI_ERROR (Status)) {
> > + goto SendSpiCmdEnd;
> > + }
> > + HardwareSpiAddr += Address;
> > + if ((Address + ByteCount) > FlashRegionSize) {
> > + Status = EFI_INVALID_PARAMETER;
> > + goto SendSpiCmdEnd;
> > + }
> > +
> > + //
> > + // Check for PCH SPI hardware sequencing required commands
> > + //
> > + FlashCycle = 0;
> > + switch (FlashCycleType) {
> > + case FlashCycleRead:
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + break;
> > + case FlashCycleWrite:
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + break;
> > + case FlashCycleErase:
> > + if (((ByteCount % SIZE_4KB) != 0) ||
> > + ((HardwareSpiAddr % SIZE_4KB) != 0)) {
> > + ASSERT (FALSE);
> > + Status = EFI_INVALID_PARAMETER;
> > + goto SendSpiCmdEnd;
> > + }
> > + break;
> > + case FlashCycleReadSfdp:
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_SFDP <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + break;
> > + case FlashCycleReadJedecId:
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + break;
> > + case FlashCycleWriteStatus:
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + break;
> > + case FlashCycleReadStatus:
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_STATUS <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + break;
> > + default:
> > + //
> > + // Unrecognized Operation
> > + //
> > + ASSERT (FALSE);
> > + Status = EFI_INVALID_PARAMETER;
> > + goto SendSpiCmdEnd;
> > + break;
> > + }
> > +
> > + do {
> > + SpiDataCount = ByteCount;
> > + if ((FlashCycleType == FlashCycleRead) ||
> > + (FlashCycleType == FlashCycleWrite) ||
> > + (FlashCycleType == FlashCycleReadSfdp)) {
> > + //
> > + // Trim at 256 byte boundary per operation,
> > + // - PCH SPI controller requires trimming at 4KB boundary
> > + // - Some SPI chips require trimming at 256 byte boundary for write
> > operation
> > + // - Trimming has limited performance impact as we can read / write
> atmost
> > 64 byte
> > + // per operation
> > + //
> > + if (HardwareSpiAddr + ByteCount > ((HardwareSpiAddr + BIT8) &~(BIT8
> -
> > 1))) {
> > + SpiDataCount = (((UINT32) (HardwareSpiAddr) + BIT8) &~(BIT8 - 1)) -
> > (UINT32) (HardwareSpiAddr);
> > + }
> > + //
> > + // Calculate the number of bytes to shift in/out during the SPI data
> cycle.
> > + // Valid settings for the number of bytes duing each data portion of the
> > + // PCH SPI cycles are: 0, 1, 2, 3, 4, 5, 6, 7, 8, 16, 24, 32, 40, 48, 56, 64
> > + //
> > + if (SpiDataCount >= 64) {
> > + SpiDataCount = 64;
> > + } else if ((SpiDataCount &~0x07) != 0) {
> > + SpiDataCount = SpiDataCount &~0x07;
> > + }
> > + }
> > + if (FlashCycleType == FlashCycleErase) {
> > + if (((ByteCount / SIZE_64KB) != 0) &&
> > + ((ByteCount % SIZE_64KB) == 0) &&
> > + ((HardwareSpiAddr % SIZE_64KB) == 0)) {
> > + if (HardwareSpiAddr < SpiInstance->Component1StartAddr) {
> > + //
> > + // Check whether Component0 support 64k Erase
> > + //
> > + if ((SpiInstance->SfdpVscc0Value &
> B_PCH_SPI_SFDPX_VSCCX_EO_64K)
> > != 0) {
> > + SpiDataCount = SIZE_64KB;
> > + } else {
> > + SpiDataCount = SIZE_4KB;
> > + }
> > + } else {
> > + //
> > + // Check whether Component1 support 64k Erase
> > + //
> > + if ((SpiInstance->SfdpVscc1Value &
> B_PCH_SPI_SFDPX_VSCCX_EO_64K)
> > != 0) {
> > + SpiDataCount = SIZE_64KB;
> > + } else {
> > + SpiDataCount = SIZE_4KB;
> > + }
> > + }
> > + } else {
> > + SpiDataCount = SIZE_4KB;
> > + }
> > + if (SpiDataCount == SIZE_4KB) {
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_4K_ERASE <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + } else {
> > + FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_64K_ERASE <<
> > N_PCH_SPI_HSFSC_CYCLE);
> > + }
> > + }
> > + //
> > + // If it's write cycle, load data into the SPI data buffer.
> > + //
> > + if ((FlashCycleType == FlashCycleWrite) || (FlashCycleType ==
> > FlashCycleWriteStatus)) {
> > + if ((SpiDataCount & 0x07) != 0) {
> > + //
> > + // Use Byte write if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
> > + //
> > + for (Index = 0; Index < SpiDataCount; Index++) {
> > + MmioWrite8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index,
> > Buffer[Index]);
> > + }
> > + } else {
> > + //
> > + // Use Dword write if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
> > + //
> > + for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
> > + MmioWrite32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, *(UINT32
> *)
> > (Buffer + Index));
> > + }
> > + }
> > + }
> > +
> > + //
> > + // Set the Flash Address
> > + //
> > + MmioWrite32 (
> > + (PchSpiBar0 + R_PCH_SPI_FADDR),
> > + (UINT32) (HardwareSpiAddr & B_PCH_SPI_FADDR_MASK)
> > + );
> > +
> > + //
> > + // Set Data count, Flash cycle, and Set Go bit to start a cycle
> > + //
> > + MmioAndThenOr32 (
> > + PchSpiBar0 + R_PCH_SPI_HSFSC,
> > + (UINT32) (~(B_PCH_SPI_HSFSC_FDBC_MASK |
> > B_PCH_SPI_HSFSC_CYCLE_MASK)),
> > + (UINT32) ((((SpiDataCount - 1) << N_PCH_SPI_HSFSC_FDBC) &
> > B_PCH_SPI_HSFSC_FDBC_MASK) | FlashCycle |
> > B_PCH_SPI_HSFSC_CYCLE_FGO)
> > + );
> > + //
> > + // end of command execution
> > + //
> > + // Wait the SPI cycle to complete.
> > + //
> > + if (!WaitForSpiCycleComplete (This, PchSpiBar0, TRUE)) {
> > + ASSERT (FALSE);
> > + Status = EFI_DEVICE_ERROR;
> > + goto SendSpiCmdEnd;
> > + }
> > + //
> > + // If it's read cycle, load data into the call's buffer.
> > + //
> > + if ((FlashCycleType == FlashCycleRead) ||
> > + (FlashCycleType == FlashCycleReadSfdp) ||
> > + (FlashCycleType == FlashCycleReadJedecId) ||
> > + (FlashCycleType == FlashCycleReadStatus)) {
> > + if ((SpiDataCount & 0x07) != 0) {
> > + //
> > + // Use Byte read if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
> > + //
> > + for (Index = 0; Index < SpiDataCount; Index++) {
> > + Buffer[Index] = MmioRead8 (PchSpiBar0 + R_PCH_SPI_FDATA00 +
> > Index);
> > + }
> > + } else {
> > + //
> > + // Use Dword read if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
> > + //
> > + for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
> > + *(UINT32 *) (Buffer + Index) = MmioRead32 (PchSpiBar0 +
> > R_PCH_SPI_FDATA00 + Index);
> > + }
> > + }
> > + }
> > +
> > + HardwareSpiAddr += SpiDataCount;
> > + Buffer += SpiDataCount;
> > + ByteCount -= SpiDataCount;
> > + } while (ByteCount > 0);
> > +
> > +SendSpiCmdEnd:
> > + //
> > + // Restore the settings for SPI Prefetching and Caching and enable BIOS
> Write
> > Protect
> > + //
> > + if ((FlashCycleType == FlashCycleWrite) ||
> > + (FlashCycleType == FlashCycleErase)) {
> > + EnableBiosWriteProtect ();
> > + }
> > + //
> > + // Restore SMIs.
> > + //
> > + IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave);
> > +
> > + ReleaseSpiBar0 (SpiInstance);
> > + return Status;
> > +}
> > +
> > +/**
> > + Wait execution cycle to complete on the SPI interface.
> > +
> > + @param[in] This The SPI protocol instance
> > + @param[in] PchSpiBar0 Spi MMIO base address
> > + @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error
> check
> > +
> > + @retval TRUE SPI cycle completed on the interface.
> > + @retval FALSE Time out while waiting the SPI cycle to
> complete.
> > + It's not safe to program the next command on the SPI
> > interface.
> > +**/
> > +BOOLEAN
> > +WaitForSpiCycleComplete (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINTN PchSpiBar0,
> > + IN BOOLEAN ErrorCheck
> > + )
> > +{
> > + UINT64 WaitTicks;
> > + UINT64 WaitCount;
> > + UINT32 Data32;
> > + SPI_INSTANCE *SpiInstance;
> > +
> > + SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
> > +
> > + //
> > + // Convert the wait period allowed into to tick count
> > + //
> > + WaitCount = SPI_WAIT_TIME / SPI_WAIT_PERIOD;
> > + //
> > + // Wait for the SPI cycle to complete.
> > + //
> > + for (WaitTicks = 0; WaitTicks < WaitCount; WaitTicks++) {
> > + Data32 = MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC);
> > + if ((Data32 & B_PCH_SPI_HSFSC_SCIP) == 0) {
> > + MmioWrite32 (PchSpiBar0 + R_PCH_SPI_HSFSC,
> > B_PCH_SPI_HSFSC_FCERR | B_PCH_SPI_HSFSC_FDONE);
> > + if (((Data32 & B_PCH_SPI_HSFSC_FCERR) != 0) && (ErrorCheck ==
> TRUE)) {
> > + return FALSE;
> > + } else {
> > + return TRUE;
> > + }
> > + }
> > + PchPmTimerStallRuntimeSafe (SpiInstance->PchAcpiBase,
> > SPI_WAIT_PERIOD);
> > + }
> > + return FALSE;
> > +}
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> >
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> > new file mode 100644
> > index 0000000000..8fb4947b1a
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
> > @@ -0,0 +1,410 @@
> > +/** @file
> > + A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
> > + EFI_SMM_CONTROL2_PROTOCOL.
> > +
> > + We expect the PEI phase to have covered the following:
> > + - ensure that the underlying QEMU machine type be X58
> > + (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
> > + - ensure that the ACPI PM IO space be configured
> > + (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
> > +
> > + Our own entry point is responsible for confirming the SMI feature and for
> > + configuring it.
> > +
> > + Copyright (C) 2013, 2015, Red Hat, Inc.<BR>
> > + Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#include <IndustryStandard/X58Ich10.h>
> > +#include <Library/BaseLib.h>
> > +#include <Library/DebugLib.h>
> > +#include <Library/IoLib.h>
> > +#include <Library/PcdLib.h>
> > +#include <Library/PciLib.h>
> > +#include <Library/UefiBootServicesTableLib.h>
> > +#include <Protocol/S3SaveState.h>
> > +#include <Protocol/SmmControl2.h>
> > +
> > +//
> > +// Forward declaration.
> > +//
> > +STATIC
> > +VOID
> > +EFIAPI
> > +OnS3SaveStateInstalled (
> > + IN EFI_EVENT Event,
> > + IN VOID *Context
> > + );
> > +
> > +//
> > +// The absolute IO port address of the SMI Control and Enable Register. It is
> > +// only used to carry information from the entry point function to the
> > +// S3SaveState protocol installation callback, strictly before the runtime
> > +// phase.
> > +//
> > +STATIC UINTN mSmiEnable;
> > +
> > +//
> > +// Event signaled when an S3SaveState protocol interface is installed.
> > +//
> > +STATIC EFI_EVENT mS3SaveStateInstalled;
> > +
> > +/**
> > + Clear the SMI status
> > +
> > + @retval EFI_SUCCESS The function completes successfully
> > + @retval EFI_DEVICE_ERROR Something error occurred
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SmmClear(
> > + VOID
> > +)
> > +{
> > + EFI_STATUS Status;
> > + UINT32 OutputData;
> > + UINT32 OutputPort;
> > + UINT32 PmBase;
> > +
> > + Status = EFI_SUCCESS;
> > + PmBase = ICH10_PMBASE_IO;
> > +
> > + OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_STS;
> > + OutputData = ICH10_SMI_STS_APM;
> > + IoWrite32(
> > + (UINTN)OutputPort,
> > + (UINT32)(OutputData)
> > + );
> > +
> > + ///
> > + /// Set the EOS Bit
> > + ///
> > + OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_EN;
> > + OutputData = IoRead32((UINTN)OutputPort);
> > + OutputData |= ICH10_SMI_EN_EOS;
> > + IoWrite32(
> > + (UINTN)OutputPort,
> > + (UINT32)(OutputData)
> > + );
> > +
> > + ///
> > + /// There is no need to read EOS back and check if it is set.
> > + /// This can lead to a reading of zero if an SMI occurs right after the
> SMI_EN
> > port read
> > + /// but before the data is returned to the CPU.
> > + /// SMM Dispatcher should make sure that EOS is set after all SMI sources
> are
> > processed.
> > + ///
> > + return Status;
> > +}
> > +
> > +/**
> > + Invokes SMI activation from either the preboot or runtime environment.
> > +
> > + This function generates an SMI.
> > +
> > + @param[in] This The EFI_SMM_CONTROL2_PROTOCOL
> instance.
> > + @param[in,out] CommandPort The value written to the command
> port.
> > + @param[in,out] DataPort The value written to the data port.
> > + @param[in] Periodic Optional mechanism to engender a periodic
> > + stream.
> > + @param[in] ActivationInterval Optional parameter to repeat at this
> > + period one time or, if the Periodic
> > + Boolean is set, periodically.
> > +
> > + @retval EFI_SUCCESS The SMI/PMI has been engendered.
> > + @retval EFI_DEVICE_ERROR The timing is unsupported.
> > + @retval EFI_INVALID_PARAMETER The activation period is unsupported.
> > + @retval EFI_INVALID_PARAMETER The last periodic activation has not
> been
> > + cleared.
> > + @retval EFI_NOT_STARTED The SMM base service has not been
> > initialized.
> > +**/
> > +STATIC
> > +EFI_STATUS
> > +EFIAPI
> > +SmmControl2DxeTrigger (
> > + IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
> > + IN OUT UINT8 *CommandPort OPTIONAL,
> > + IN OUT UINT8 *DataPort OPTIONAL,
> > + IN BOOLEAN Periodic OPTIONAL,
> > + IN UINTN ActivationInterval OPTIONAL
> > + )
> > +{
> > + EFI_STATUS Status;
> > + //
> > + // No support for queued or periodic activation.
> > + //
> > + if (Periodic || ActivationInterval > 0) {
> > + return EFI_DEVICE_ERROR;
> > + }
> > + ///
> > + /// Clear any pending the APM SMI
> > + ///
> > + Status = SmmClear();
> > + //
> > + // The so-called "Advanced Power Management Status Port Register" is in
> fact
> > + // a generic data passing register, between the caller and the SMI
> > + // dispatcher. The ICH9 spec calls it "scratchpad register" -- calling it
> > + // "status" elsewhere seems quite the misnomer. Status registers usually
> > + // report about hardware status, while this register is fully governed by
> > + // software.
> > + //
> > + // Write to the status register first, as this won't trigger the SMI just
> > + // yet. Then write to the control register.
> > + //
> > + IoWrite8 (ICH10_APM_STS, DataPort == NULL ? 0 : *DataPort);
> > + IoWrite8 (ICH10_APM_CNT, CommandPort == NULL ? 0 :
> *CommandPort);
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + Clears any system state that was created in response to the Trigger() call.
> > +
> > + This function acknowledges and causes the deassertion of the SMI
> activation
> > + source.
> > +
> > + @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
> > + @param[in] Periodic Optional parameter to repeat at this period
> > + one time
> > +
> > + @retval EFI_SUCCESS The SMI/PMI has been engendered.
> > + @retval EFI_DEVICE_ERROR The source could not be cleared.
> > + @retval EFI_INVALID_PARAMETER The service did not support the
> Periodic
> > input
> > + argument.
> > +**/
> > +STATIC
> > +EFI_STATUS
> > +EFIAPI
> > +SmmControl2DxeClear (
> > + IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
> > + IN BOOLEAN Periodic OPTIONAL
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + if (Periodic) {
> > + return EFI_INVALID_PARAMETER;
> > + }
> > +
> > + //
> > + // The PI spec v1.4 explains that Clear() is only supposed to clear software
> > + // status; it is not in fact responsible for deasserting the SMI. It gives
> > + // two reasons for this: (a) many boards clear the SMI automatically when
> > + // entering SMM, (b) if Clear() actually deasserted the SMI, then it could
> > + // incorrectly suppress an SMI that was asynchronously asserted between
> the
> > + // last return of the SMI handler and the call made to Clear().
> > + //
> > + // In fact QEMU automatically deasserts CPU_INTERRUPT_SMI in:
> > + // - x86_cpu_exec_interrupt() [target-i386/seg_helper.c], and
> > + // - kvm_arch_pre_run() [target-i386/kvm.c].
> > + //
> > + // So, nothing to do here.
> > + //
> > + Status = SmmClear();
> > +
> > + return EFI_SUCCESS;
> > +}
> > +
> > +STATIC EFI_SMM_CONTROL2_PROTOCOL mControl2 = {
> > + &SmmControl2DxeTrigger,
> > + &SmmControl2DxeClear,
> > + MAX_UINTN // MinimumTriggerPeriod -- we don't support periodic SMIs
> > +};
> > +
> > +//
> > +// Entry point of this driver.
> > +//
> > +EFI_STATUS
> > +EFIAPI
> > +SmmControl2DxeEntryPoint (
> > + IN EFI_HANDLE ImageHandle,
> > + IN EFI_SYSTEM_TABLE *SystemTable
> > + )
> > +{
> > + UINT32 PmBase;
> > + UINT32 SmiEnableVal;
> > + EFI_STATUS Status;
> > +
> > + //
> > + // This module should only be included if SMRAM support is required.
> > + //
> > + ASSERT (FeaturePcdGet (PcdSmmSmramRequire));
> > +
> > + //
> > + // Calculate the absolute IO port address of the SMI Control and Enable
> > + // Register. (As noted at the top, the PEI phase has left us with a working
> > + // ACPI PM IO space.)
> > + //
> > + PmBase = PciRead32 (POWER_MGMT_REGISTER_ICH10
> (ICH10_PMBASE)) &
> > + ICH10_PMBASE_MASK;
> > + mSmiEnable = PmBase + ICH10_PMBASE_OFS_SMI_EN;
> > +
> > + //
> > + // If APMC_EN is pre-set in SMI_EN, that's QEMU's way to tell us that SMI
> > + // support is not available. (For example due to KVM lacking it.)
> Otherwise,
> > + // this bit is clear after each reset.
> > + //
> > + SmiEnableVal = IoRead32 (mSmiEnable);
> > + if ((SmiEnableVal & ICH10_SMI_EN_APMC_EN) != 0) {
> > + DEBUG ((EFI_D_ERROR, "%a: this X58 implementation lacks SMI\n",
> > + __FUNCTION__));
> > + }
> > +
> > + //
> > + // Otherwise, configure the board to inject an SMI when ICH10_APM_CNT
> is
> > + // written to. (See the Trigger() method above.)
> > + //
> > + SmiEnableVal |= ICH10_SMI_EN_APMC_EN |
> ICH10_SMI_EN_GBL_SMI_EN;
> > + IoWrite32 (mSmiEnable, SmiEnableVal);
> > +
> > + //
> > + // Prevent software from undoing the above (until platform reset).
> > + //
> > + PciOr16 (POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
> > + ICH10_GEN_PMCON_1_SMI_LOCK);
> > +
> > + //
> > + // If we can clear GBL_SMI_EN now, that means QEMU's SMI support is
> not
> > + // appropriate.
> > + //
> > + IoWrite32 (mSmiEnable, SmiEnableVal &
> > ~(UINT32)ICH10_SMI_EN_GBL_SMI_EN);
> > + if (IoRead32 (mSmiEnable) != SmiEnableVal) {
> > + DEBUG ((EFI_D_ERROR, "%a: failed to lock down GBL_SMI_EN\n",
> > + __FUNCTION__));
> > + goto FatalError;
> > + }
> > +
> > + VOID *Registration;
> > +
> > + //
> > + // On S3 resume the above register settings have to be repeated. Register
> a
> > + // protocol notify callback that, when boot script saving becomes
> > + // available, saves operations equivalent to the above to the boot script.
> > + //
> > + Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK,
> > + OnS3SaveStateInstalled, NULL /* Context */,
> > + &mS3SaveStateInstalled);
> > + if (EFI_ERROR (Status)) {
> > + DEBUG ((EFI_D_ERROR, "%a: CreateEvent: %r\n", __FUNCTION__,
> Status));
> > + goto FatalError;
> > + }
> > +
> > + Status = gBS->RegisterProtocolNotify (&gEfiS3SaveStateProtocolGuid,
> > + mS3SaveStateInstalled, &Registration);
> > + if (EFI_ERROR (Status)) {
> > + DEBUG ((EFI_D_ERROR, "%a: RegisterProtocolNotify: %r\n",
> > __FUNCTION__,
> > + Status));
> > + goto ReleaseEvent;
> > + }
> > +
> > + //
> > + // Kick the event right now -- maybe the boot script is already saveable.
> > + //
> > + Status = gBS->SignalEvent (mS3SaveStateInstalled);
> > + if (EFI_ERROR (Status)) {
> > + DEBUG ((EFI_D_ERROR, "%a: SignalEvent: %r\n", __FUNCTION__,
> Status));
> > + goto ReleaseEvent;
> > + }
> > +
> > + //
> > + // We have no pointers to convert to virtual addresses. The handle itself
> > + // doesn't matter, as protocol services are not accessible at runtime.
> > + //
> > + Status = gBS->InstallMultipleProtocolInterfaces (&ImageHandle,
> > + &gEfiSmmControl2ProtocolGuid, &mControl2,
> > + NULL);
> > + if (EFI_ERROR (Status)) {
> > + DEBUG ((EFI_D_ERROR, "%a: InstallMultipleProtocolInterfaces: %r\n",
> > + __FUNCTION__, Status));
> > + goto ReleaseEvent;
> > + }
> > +
> > + return EFI_SUCCESS;
> > +
> > +ReleaseEvent:
> > + if (mS3SaveStateInstalled != NULL) {
> > + gBS->CloseEvent (mS3SaveStateInstalled);
> > + }
> > +
> > +FatalError:
> > + //
> > + // We really don't want to continue in this case.
> > + //
> > + ASSERT (FALSE);
> > + CpuDeadLoop ();
> > + return EFI_UNSUPPORTED;
> > +}
> > +
> > +/**
> > + Notification callback for S3SaveState installation.
> > +
> > + @param[in] Event Event whose notification function is being invoked.
> > +
> > + @param[in] Context The pointer to the notification function's context,
> which
> > + is implementation-dependent.
> > +**/
> > +STATIC
> > +VOID
> > +EFIAPI
> > +OnS3SaveStateInstalled (
> > + IN EFI_EVENT Event,
> > + IN VOID *Context
> > + )
> > +{
> > + EFI_STATUS Status;
> > + EFI_S3_SAVE_STATE_PROTOCOL *S3SaveState;
> > + UINT32 SmiEnOrMask, SmiEnAndMask;
> > + UINT16 GenPmCon1OrMask, GenPmCon1AndMask;
> > +
> > + ASSERT (Event == mS3SaveStateInstalled);
> > +
> > + Status = gBS->LocateProtocol (&gEfiS3SaveStateProtocolGuid,
> > + NULL /* Registration */, (VOID **)&S3SaveState);
> > + if (EFI_ERROR (Status)) {
> > + return;
> > + }
> > +
> > + //
> > + // These operations were originally done, verified and explained in the
> entry
> > + // point function of the driver.
> > + //
> > + SmiEnOrMask = ICH10_SMI_EN_APMC_EN |
> ICH10_SMI_EN_GBL_SMI_EN;
> > + SmiEnAndMask = MAX_UINT32;
> > + Status = S3SaveState->Write (
> > + S3SaveState,
> > + EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE,
> > + EfiBootScriptWidthUint32,
> > + (UINT64)mSmiEnable,
> > + &SmiEnOrMask,
> > + &SmiEnAndMask
> > + );
> > + if (EFI_ERROR (Status)) {
> > + DEBUG ((EFI_D_ERROR, "%a:
> > EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE: %r\n",
> > + __FUNCTION__, Status));
> > + ASSERT (FALSE);
> > + CpuDeadLoop ();
> > + }
> > +
> > + GenPmCon1OrMask = ICH10_GEN_PMCON_1_SMI_LOCK;
> > + GenPmCon1AndMask = MAX_UINT16;
> > + Status = S3SaveState->Write (
> > + S3SaveState,
> > + EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE,
> > + EfiBootScriptWidthUint16,
> > + (UINT64)POWER_MGMT_REGISTER_ICH10
> > (ICH10_GEN_PMCON_1),
> > + &GenPmCon1OrMask,
> > + &GenPmCon1AndMask
> > + );
> > + if (EFI_ERROR (Status)) {
> > + DEBUG ((EFI_D_ERROR,
> > + "%a: EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE: %r\n",
> > __FUNCTION__,
> > + Status));
> > + ASSERT (FALSE);
> > + CpuDeadLoop ();
> > + }
> > +
> > + DEBUG ((EFI_D_VERBOSE, "%a: boot script fragment saved\n",
> > __FUNCTION__));
> > + gBS->CloseEvent (Event);
> > + mS3SaveStateInstalled = NULL;
> > +}
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> > b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> > new file mode 100644
> > index 0000000000..19eb469657
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
> > @@ -0,0 +1,175 @@
> > +/** @file
> > + PCH SPI SMM Driver implements the SPI Host Controller Compatibility
> > Interface.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#include "PchSpi.h"
> > +
> > +//
> > +// Global variables
> > +//
> > +GLOBAL_REMOVE_IF_UNREFERENCED SPI_INSTANCE *mSpiInstance;
> > +//
> > +// mPchSpiResvMmioAddr keeps the reserved MMIO range assiged to SPI.
> > +// In SMM it always set back the reserved MMIO address to SPI BAR0 to
> ensure
> > the MMIO range
> > +// won't overlap with SMRAM range, and trusted.
> > +//
> > +GLOBAL_REMOVE_IF_UNREFERENCED UINT32
> mSpiResvMmioAddr;
> > +
> > +/**
> > + <b>SPI Runtime SMM Module Entry Point</b>\n
> > + - <b>Introduction</b>\n
> > + The SPI SMM module provide a standard way for other modules to use
> the
> > PCH SPI Interface in SMM.
> > +
> > + - @pre
> > + - EFI_SMM_BASE2_PROTOCOL
> > + - Documented in System Management Mode Core Interface
> Specification .
> > +
> > + - @result
> > + The SPI SMM driver produces @link _PCH_SPI_PROTOCOL
> > PCH_SPI_PROTOCOL @endlink with GUID
> > + gPchSmmSpiProtocolGuid which is different from SPI RUNTIME driver.
> > +
> > + - <b>Integration Check List</b>\n
> > + - This driver supports Descriptor Mode only.
> > + - This driver supports Hardware Sequence only.
> > + - When using SMM SPI Protocol to perform flash access in an SMI
> handler,
> > + and the SMI occurrence is asynchronous to normal mode code
> execution,
> > + proper synchronization mechanism must be applied, e.g. disable SMI
> before
> > + the normal mode SendSpiCmd() starts and re-enable SMI after
> > + the normal mode SendSpiCmd() completes.
> > + @note The implementation of SendSpiCmd() uses GBL_SMI_EN in
> > + SMI_EN register (ABase + 30h) to disable and enable SMIs. But this may
> > + not be effective as platform may well set the SMI_LOCK bit (i.e., PMC
> PCI
> > Offset A0h [4]).
> > + So the synchronization at caller level is likely needed.
> > +
> > + @param[in] ImageHandle Image handle of this driver.
> > + @param[in] SystemTable Global system service table.
> > +
> > + @retval EFI_SUCCESS Initialization complete.
> > + @exception EFI_UNSUPPORTED The chipset is unsupported by this
> driver.
> > + @retval EFI_OUT_OF_RESOURCES Do not have enough resources to
> > initialize the driver.
> > + @retval EFI_DEVICE_ERROR Device error, driver exits abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +InstallPchSpi (
> > + IN EFI_HANDLE ImageHandle,
> > + IN EFI_SYSTEM_TABLE *SystemTable
> > + )
> > +{
> > + EFI_STATUS Status;
> > +
> > + //
> > + // Init PCH spi reserved MMIO address.
> > + //
> > + mSpiResvMmioAddr = PCH_SPI_BASE_ADDRESS;
> > +
> > + ///
> > + /// Allocate pool for SPI protocol instance
> > + ///
> > + Status = gSmst->SmmAllocatePool (
> > + EfiRuntimeServicesData, /// MemoryType don't care
> > + sizeof (SPI_INSTANCE),
> > + (VOID **) &mSpiInstance
> > + );
> > + if (EFI_ERROR (Status)) {
> > + return Status;
> > + }
> > +
> > + if (mSpiInstance == NULL) {
> > + return EFI_OUT_OF_RESOURCES;
> > + }
> > +
> > + ZeroMem ((VOID *) mSpiInstance, sizeof (SPI_INSTANCE));
> > + ///
> > + /// Initialize the SPI protocol instance
> > + ///
> > + Status = SpiProtocolConstructor (mSpiInstance);
> > + if (EFI_ERROR (Status)) {
> > + return Status;
> > + }
> > + //
> > + // Install the SMM EFI_SPI_PROTOCOL interface
> > + //
> > + Status = gSmst->SmmInstallProtocolInterface (
> > + &(mSpiInstance->Handle),
> > + &gEfiSmmSpiProtocolGuid,
> > + EFI_NATIVE_INTERFACE,
> > + &(mSpiInstance->SpiProtocol)
> > + );
> > + if (EFI_ERROR (Status)) {
> > + gSmst->SmmFreePool (mSpiInstance);
> > + return EFI_DEVICE_ERROR;
> > + }
> > +
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + Acquire PCH spi mmio address.
> > + It is not expected for this BAR0 to change because the SPI device is hidden
> > + from the OS for SKL PCH LP/H B stepping and above (refer to section
> 3.5.1),
> > + but if it is ever different from the preallocated address, reassign it back.
> > + In SMM, it always override the BAR0 and returns the reserved MMIO
> range
> > for SPI.
> > +
> > + @param[in] SpiInstance Pointer to SpiInstance to initialize
> > +
> > + @retval PchSpiBar0 return SPI MMIO address
> > +**/
> > +UINTN
> > +AcquireSpiBar0 (
> > + IN SPI_INSTANCE *SpiInstance
> > + )
> > +{
> > + //
> > + // SPIBAR0 will be different before and after PCI enum so need to get it
> from
> > SPI BAR0 reg.
> > + //
> > + return mSpiResvMmioAddr;
> > +}
> > +
> > +/**
> > + Release pch spi mmio address. Do nothing.
> > +
> > + @param[in] SpiInstance Pointer to SpiInstance to initialize
> > +
> > + @retval None
> > +**/
> > +VOID
> > +ReleaseSpiBar0 (
> > + IN SPI_INSTANCE *SpiInstance
> > + )
> > +{
> > +}
> > +
> > +/**
> > + This function is a hook for Spi to disable BIOS Write Protect
> > +
> > + @retval EFI_SUCCESS The protocol instance was properly
> initialized
> > + @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in
> > SMM phase
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +DisableBiosWriteProtect (
> > + VOID
> > + )
> > +{
> > +
> > + return EFI_SUCCESS;
> > +}
> > +
> > +/**
> > + This function is a hook for Spi to enable BIOS Write Protect
> > +
> > +
> > +**/
> > +VOID
> > +EFIAPI
> > +EnableBiosWriteProtect (
> > + VOID
> > + )
> > +{
> > +}
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> > b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> > new file mode 100644
> > index 0000000000..f9d340d6df
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
> > @@ -0,0 +1,22 @@
> > +## @file
> > +# Copyright (c) 2014 - 2016 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[Defines]
> > + DEC_SPECIFICATION = 0x00010005
> > + PACKAGE_NAME = ICH10Pkg
> > + PACKAGE_GUID = 4E97AC4B-F64C-4008-BBDE-01CC3B0BAA6B
> > + PACKAGE_VERSION = 0.91
> > +
> > +[Includes]
> > + Include
> > +
> > +[Ppis]
> > +
> > +[Guids]
> > + gEfiPchTokenSpaceGuid = { 0x89a1b278, 0xa1a1, 0x4df7, { 0xb1, 0x37,
> 0xde,
> > 0x5a, 0xd7, 0xc4, 0x79, 0x13 } }
> > +[Protocols]
> > + gEfiSmmSpiProtocolGuid = {0xbd75fe35, 0xfdce, 0x49d7, {0xa9, 0xdd,
> 0xb2,
> > 0x6f, 0x1f, 0xc6, 0xb4, 0x37}}
> > diff --git
> a/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> > new file mode 100644
> > index 0000000000..c36360bcb0
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
> > @@ -0,0 +1,98 @@
> > +/** @file
> > + The header file includes the common header files, defines
> > + internal structure and functions used by SpiFlashCommonLib.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef __SPI_FLASH_COMMON_LIB_H__
> > +#define __SPI_FLASH_COMMON_LIB_H__
> > +
> > +#include <Uefi.h>
> > +#include <Library/BaseLib.h>
> > +#include <Library/PcdLib.h>
> > +#include <Library/DebugLib.h>
> > +#include <Library/BaseMemoryLib.h>
> > +#include <Library/MemoryAllocationLib.h>
> > +#include <Library/UefiDriverEntryPoint.h>
> > +#include <Library/UefiBootServicesTableLib.h>
> > +
> > +#define SECTOR_SIZE_4KB 0x1000 // Common 4kBytes sector size
> > +/**
> > + Enable block protection on the Serial Flash device.
> > +
> > + @retval EFI_SUCCESS Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashLock (
> > + VOID
> > + );
> > +
> > +/**
> > + Read NumBytes bytes of data from the address specified by
> > + PAddress into Buffer.
> > +
> > + @param[in] Address The starting physical address of the read.
> > + @param[in,out] NumBytes On input, the number of bytes to read. On
> > output, the number
> > + of bytes actually read.
> > + @param[out] Buffer The destination data buffer for the read.
> > +
> > + @retval EFI_SUCCESS Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashRead (
> > + IN UINTN Address,
> > + IN OUT UINT32 *NumBytes,
> > + OUT UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Write NumBytes bytes of data from Buffer to the address specified by
> > + PAddresss.
> > +
> > + @param[in] Address The starting physical address of the write.
> > + @param[in,out] NumBytes On input, the number of bytes to write.
> On
> > output,
> > + the actual number of bytes written.
> > + @param[in] Buffer The source data buffer for the write.
> > +
> > + @retval EFI_SUCCESS Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashWrite (
> > + IN UINTN Address,
> > + IN OUT UINT32 *NumBytes,
> > + IN UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Erase the block starting at Address.
> > +
> > + @param[in] Address The starting physical address of the block to be
> > erased.
> > + This library assume that caller garantee that the PAddress
> > + is at the starting address of this block.
> > + @param[in] NumBytes On input, the number of bytes of the logical
> block
> > to be erased.
> > + On output, the actual number of bytes erased.
> > +
> > + @retval EFI_SUCCESS. Opertion is successful.
> > + @retval EFI_DEVICE_ERROR If there is any device errors.
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiFlashBlockErase (
> > + IN UINTN Address,
> > + IN UINTN *NumBytes
> > + );
> > +
> > +#endif
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> > new file mode 100644
> > index 0000000000..552ce28d8c
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
> > @@ -0,0 +1,43 @@
> > +/** @file
> > + Macros that simplify accessing PCH devices's PCI registers.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_ACCESS_H_
> > +#define _PCH_ACCESS_H_
> > +
> > +#include "PchReservedResources.h"
> > +
> > +#ifndef STALL_ONE_MICRO_SECOND
> > +#define STALL_ONE_MICRO_SECOND 1
> > +#endif
> > +#ifndef STALL_ONE_SECOND
> > +#define STALL_ONE_SECOND 1000000
> > +#endif
> > +
> > +
> > +///
> > +/// The default PCH PCI bus number
> > +///
> > +#define DEFAULT_PCI_BUS_NUMBER_PCH 0
> > +
> > +//
> > +// Default Vendor ID and Subsystem ID
> > +//
> > +#define V_PCH_INTEL_VENDOR_ID 0x8086 ///< Default Intel PCH
> Vendor
> > ID
> > +#define V_PCH_DEFAULT_SID 0x7270 ///< Default Intel PCH
> Subsystem
> > ID
> > +#define V_PCH_DEFAULT_SVID_SID (V_INTEL_VENDOR_ID +
> > (V_PCH_DEFAULT_SID << 16)) ///< Default INTEL PCH Vendor ID and
> > Subsystem ID
> > +
> > +//
> > +// Include device register definitions
> > +//
> > +
> > +#include "Register/PchRegsPmc.h"
> > +
> > +#include "Register/PchRegsSpi.h"
> > +
> > +#endif
> > +
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> > new file mode 100644
> > index 0000000000..d503d130c8
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
> > @@ -0,0 +1,94 @@
> > +/** @file
> > + Build time limits of PCH resources.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_LIMITS_H_
> > +#define _PCH_LIMITS_H_
> > +
> > +//
> > +// PCIe limits
> > +//
> > +#define PCH_MAX_PCIE_ROOT_PORTS
> > PCH_H_PCIE_MAX_ROOT_PORTS
> > +#define PCH_H_PCIE_MAX_ROOT_PORTS 20
> > +#define PCH_LP_PCIE_MAX_ROOT_PORTS 12
> > +
> > +#define PCH_MAX_PCIE_CONTROLLERS
> > PCH_H_PCIE_MAX_CONTROLLERS
> > +#define PCH_PCIE_CONTROLLER_PORTS 4
> > +#define PCH_H_PCIE_MAX_CONTROLLERS
> > (PCH_H_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
> > +#define PCH_LP_PCIE_MAX_CONTROLLERS
> > (PCH_LP_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
> > +
> > +//
> > +// PCIe clocks limits
> > +//
> > +#define PCH_LP_PCIE_MAX_CLK_REQ 6
> > +#define PCH_H_PCIE_MAX_CLK_REQ 16
> > +
> > +//
> > +// RST PCIe Storage Cycle Router limits
> > +//
> > +#define PCH_MAX_RST_PCIE_STORAGE_CR 3
> > +
> > +//
> > +// SATA limits
> > +//
> > +#define PCH_MAX_SATA_PORTS PCH_H_AHCI_MAX_PORTS
> > +#define PCH_H_AHCI_MAX_PORTS 8 ///< Max number of sata
> > ports in SKL PCH H
> > +#define PCH_LP_AHCI_MAX_PORTS 3 ///< Max number of sata
> > ports in SKL PCH LP
> > +#define PCH_SATA_MAX_DEVICES_PER_PORT 1 ///< Max support
> > device numner per port, Port Multiplier is not support.
> > +
> > +//
> > +// USB limits
> > +//
> > +#define PCH_MAX_USB2_PORTS
> PCH_H_XHCI_MAX_USB2_PORTS
> > +
> > +#define PCH_H_XHCI_MAX_USB2_PHYSICAL_PORTS 14 ///< Max
> Physical
> > Connector XHCI, not counting virtual ports like USB-R.
> > +#define PCH_LP_XHCI_MAX_USB2_PHYSICAL_PORTS 10 ///< Max
> Physical
> > Connector XHCI, not counting virtual ports like USB-R.
> > +
> > +#define PCH_H_XHCI_MAX_USB2_PORTS 16 ///< 14 High Speed
> lanes
> > + Including two ports reserved for USBr
> > +#define PCH_LP_XHCI_MAX_USB2_PORTS 12 ///< 10 High Speed
> lanes
> > + Including two ports reserved for USBr
> > +
> > +#define PCH_MAX_USB3_PORTS
> PCH_H_XHCI_MAX_USB3_PORTS
> > +
> > +#define PCH_H_XHCI_MAX_USB3_PORTS 10 ///< 10 Super Speed
> > lanes
> > +#define PCH_LP_XHCI_MAX_USB3_PORTS 6 ///< 6 Super Speed
> lanes
> > +
> > +#define PCH_XHCI_MAX_SSIC_PORT_COUNT 2 ///< 2 SSIC ports in
> SKL
> > PCH-LP and SKL PCH-H
> > +
> > +//
> > +// SerialIo limits
> > +//
> > +#define PCH_SERIALIO_MAX_CONTROLLERS 11 ///< Number of
> SerialIo
> > controllers, this includes I2C, SPI and UART
> > +#define PCH_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of
> SerialIo
> > I2C controllers
> > +#define PCH_LP_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of
> > SerialIo I2C controllers for PCH-LP
> > +#define PCH_H_SERIALIO_MAX_I2C_CONTROLLERS 4 ///< Number of
> > SerialIo I2C controllers for PCH-H
> > +#define PCH_SERIALIO_MAX_SPI_CONTROLLERS 2 ///< Number of
> SerialIo
> > SPI controllers
> > +#define PCH_SERIALIO_MAX_UART_CONTROLLERS 3 ///< Number of
> > SerialIo UART controllers
> > +
> > +//
> > +// ISH limits
> > +//
> > +#define PCH_ISH_MAX_GP_PINS 8
> > +#define PCH_ISH_MAX_UART_CONTROLLERS 2
> > +#define PCH_ISH_MAX_I2C_CONTROLLERS 3
> > +#define PCH_ISH_MAX_SPI_CONTROLLERS 1
> > +
> > +//
> > +// SCS limits
> > +//
> > +#define PCH_SCS_MAX_CONTROLLERS 3 ///< Number of Storage
> and
> > Communication Subsystem controllers, this includes eMMC, SDIO, SDCARD
> > +
> > +//
> > +// Flash Protection Range Register
> > +//
> > +#define PCH_FLASH_PROTECTED_RANGES 5
> > +
> > +//
> > +// Number of eSPI slaves
> > +//
> > +#define PCH_ESPI_MAX_SLAVE_ID 2
> > +#endif // _PCH_LIMITS_H_
> > +
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> > new file mode 100644
> > index 0000000000..00139fc230
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
> > @@ -0,0 +1,60 @@
> > +/** @file
> > + PCH preserved MMIO resource definitions.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_PRESERVED_RESOURCES_H_
> > +#define _PCH_PRESERVED_RESOURCES_H_
> > +
> > +/**
> > + PCH preserved MMIO range, 24 MB, from 0xFD000000 to 0xFE7FFFFF
> > +
> > + Detailed recommended static allocation
> > + +-------------------------------------------------------------------------+
> > + | Size | Start | End | Usage |
> > + | 16 MB | 0xFD000000 | 0xFDFFFFFF | SBREG |
> > + | 64 KB | 0xFE000000 | 0xFE00FFFF | PMC MBAR |
> > + | 4 KB | 0xFE010000 | 0xFE010FFF | SPI BAR0 |
> > + | 88 KB | 0xFE020000 | 0xFE035FFF | SerialIo BAR in ACPI mode |
> > + | 24 KB | 0xFE036000 | 0xFE03BFFF | Unused |
> > + | 4 KB | 0xFE03C000 | 0xFE03CFFF | Thermal Device in ACPI mode
> |
> > + | 524 KB | 0xFE03D000 | 0xFE0BFFFF | Unused |
> > + | 256 KB | 0xFE0C0000 | 0xFE0FFFFF | TraceHub FW BAR |
> > + | 1 MB | 0xFE100000 | 0xFE1FFFFF | TraceHub MTB BAR |
> > + | 2 MB | 0xFE200000 | 0xFE3FFFFF | TraceHub SW BAR |
> > + | 64 KB | 0xFE400000 | 0xFE40FFFF | CIO2 MMIO BAR in ACPI mode
> |
> > + | 2 MB - 64KB | 0xFE410000 | 0xFE5FFFFF | Unused |
> > + | 2 MB | 0xFE600000 | 0xFE7FFFFF | Temp address |
> > + +-------------------------------------------------------------------------+
> > +**/
> > +#define PCH_PRESERVED_BASE_ADDRESS 0xFD000000 ///< Pch
> > preserved MMIO base address
> > +#define PCH_PRESERVED_MMIO_SIZE 0x01800000 ///< 24MB
> > +#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO
> > base address
> > +#define PCH_PCR_MMIO_SIZE 0x01000000 ///< 16MB
> > +#define PCH_PWRM_BASE_ADDRESS 0xFE000000 ///< PMC MBAR
> > MMIO base address
> > +#define PCH_PWRM_MMIO_SIZE 0x00010000 ///< 64KB
> > +#define PCH_SPI_BASE_ADDRESS 0xFED1C000 + 0x3800 ///< SPI
> > MBAR MMIO base address
> > +#define PCH_SPI_MMIO_SIZE 0x00001000 ///< 4KB
> > +#define PCH_SERIAL_IO_BASE_ADDRESS 0xFE020000 ///< SerialIo
> MMIO
> > base address
> > +#define PCH_SERIAL_IO_MMIO_SIZE 0x00016000 ///< 88KB
> > +#define PCH_THERMAL_BASE_ADDRESS 0xFE03C000 ///< Thermal
> > Device in ACPI mode
> > +#define PCH_THERMAL_MMIO_SIZE 0x00001000 ///< 4KB
> > +#define PCH_TRACE_HUB_FW_BASE_ADDRESS 0xFE0C0000 ///<
> TraceHub
> > FW MMIO base address
> > +#define PCH_TRACE_HUB_FW_MMIO_SIZE 0x00040000 ///< 256KB
> > +#define PCH_TRACE_HUB_MTB_BASE_ADDRESS 0xFE100000 ///<
> > TraceHub MTB MMIO base address
> > +#define PCH_TRACE_HUB_MTB_MMIO_SIZE 0x00100000 ///< 1MB
> > +#define PCH_TRACE_HUB_SW_BASE_ADDRESS 0xFE200000 ///<
> TraceHub
> > SW MMIO base address
> > +#define PCH_TRACE_HUB_SW_MMIO_SIZE 0x00200000 ///< 2MB
> > +#define PCH_CIO2_BASE_ADDRESS 0xFE400000 ///< CIO2 MMIO
> BAR
> > in ACPI mode
> > +#define PCH_CIO2_MMIO_SIZE 0x00010000 ///< 64KB
> > +#define PCH_TEMP_BASE_ADDRESS 0xFE600000 ///< preserved
> temp
> > address for misc usage
> > +#define PCH_TEMP_MMIO_SIZE 0x00200000 ///< 2MB
> > +
> > +#define RCRB 0xFED1C000
> > +#define SPIBAR 0x3800
> > +
> > +#endif // _PCH_PRESERVED_RESOURCES_H_
> > +
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> > new file mode 100644
> > index 0000000000..cb5f26c47b
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
> > @@ -0,0 +1,295 @@
> > +/** @file
> > + This file defines the PCH SPI Protocol which implements the
> > + Intel(R) PCH SPI Host Controller Compatibility Interface.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_SPI_PROTOCOL_H_
> > +#define _PCH_SPI_PROTOCOL_H_
> > +
> > +//
> > +// Extern the GUID for protocol users.
> > +//
> > +extern EFI_GUID gEfiSpiProtocolGuid;
> > +extern EFI_GUID gEfiSmmSpiProtocolGuid;
> > +
> > +//
> > +// Forward reference for ANSI C compatibility
> > +//
> > +typedef struct _PCH_SPI_PROTOCOL EFI_SPI_PROTOCOL;
> > +
> > +//
> > +// SPI protocol data structures and definitions
> > +//
> > +
> > +/**
> > + Flash Region Type
> > +**/
> > +typedef enum {
> > + FlashRegionDescriptor,
> > + FlashRegionBios,
> > + FlashRegionMe,
> > + FlashRegionGbE,
> > + FlashRegionPlatformData,
> > + FlashRegionDer,
> > + FlashRegionAll,
> > + FlashRegionMax
> > +} FLASH_REGION_TYPE;
> > +
> > +
> > +//
> > +// Protocol member functions
> > +//
> > +
> > +/**
> > + Read data from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[out] Buffer The Pointer to caller-allocated buffer
> containing
> > the dada received.
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_READ) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Write data to the flash part. Remark: Erase may be needed before write to
> the
> > flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[in] Buffer Pointer to caller-allocated buffer containing
> the
> > data sent during the SPI cycle.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_WRITE) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + IN UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Erase some area on the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_ERASE) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount
> > + );
> > +
> > +/**
> > + Read SFDP data from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ComponentNumber The Componen Number for chip
> select
> > + @param[in] Address The starting byte address for SFDP data read.
> > + @param[in] ByteCount Number of bytes in SFDP data portion of
> the SPI
> > cycle
> > + @param[out] SfdpData The Pointer to caller-allocated buffer
> containing
> > the SFDP data received
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_READ_SFDP) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT8 ComponentNumber,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *SfdpData
> > + );
> > +
> > +/**
> > + Read Jedec Id from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ComponentNumber The Componen Number for chip
> select
> > + @param[in] ByteCount Number of bytes in JedecId data portion of
> the
> > SPI cycle, the data size is 3 typically
> > + @param[out] JedecId The Pointer to caller-allocated buffer
> containing
> > JEDEC ID received
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_READ_JEDEC_ID) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT8 ComponentNumber,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *JedecId
> > + );
> > +
> > +/**
> > + Write the status register in the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ByteCount Number of bytes in Status data portion of
> the
> > SPI cycle, the data size is 1 typically
> > + @param[in] StatusValue The Pointer to caller-allocated buffer
> containing
> > the value of Status register writing
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_WRITE_STATUS) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 ByteCount,
> > + IN UINT8 *StatusValue
> > + );
> > +
> > +/**
> > + Read status register in the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ByteCount Number of bytes in Status data portion of
> the
> > SPI cycle, the data size is 1 typically
> > + @param[out] StatusValue The Pointer to caller-allocated buffer
> > containing the value of Status register received.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_FLASH_READ_STATUS) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *StatusValue
> > + );
> > +
> > +/**
> > + Get the SPI region base and size, based on the enum type
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for for the base
> > address which is listed in the Descriptor.
> > + @param[out] BaseAddress The Flash Linear Address for the Region
> 'n'
> > Base
> > + @param[out] RegionSize The size for the Region 'n'
> > +
> > + @retval EFI_SUCCESS Read success
> > + @retval EFI_INVALID_PARAMETER Invalid region type given
> > + @retval EFI_DEVICE_ERROR The region is not used
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_GET_REGION_ADDRESS) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + OUT UINT32 *BaseAddress,
> > + OUT UINT32 *RegionSize
> > + );
> > +
> > +/**
> > + Read PCH Soft Strap Values
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> > + @param[in] ByteCount Number of bytes in SoftStrap data portion
> of
> > the SPI cycle
> > + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> > containing PCH Soft Strap Value.
> > + If the value of ByteCount is 0, the data type of
> > SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> > Length
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_READ_PCH_SOFTSTRAP) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 SoftStrapAddr,
> > + IN UINT32 ByteCount,
> > + OUT VOID *SoftStrapValue
> > + );
> > +
> > +/**
> > + Read CPU Soft Strap Values
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SoftStrapAddr CPU Soft Strap address offset from
> FCPUSBA.
> > + @param[in] ByteCount Number of bytes in SoftStrap data portion
> of
> > the SPI cycle.
> > + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> > containing CPU Soft Strap Value.
> > + If the value of ByteCount is 0, the data type of
> > SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> > Length
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +typedef
> > +EFI_STATUS
> > +(EFIAPI *PCH_SPI_READ_CPU_SOFTSTRAP) (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 SoftStrapAddr,
> > + IN UINT32 ByteCount,
> > + OUT VOID *SoftStrapValue
> > + );
> > +
> > +/**
> > + These protocols/PPI allows a platform module to perform SPI operations
> > through the
> > + Intel PCH SPI Host Controller Interface.
> > +**/
> > +struct _PCH_SPI_PROTOCOL {
> > + /**
> > + This member specifies the revision of this structure. This field is used to
> > + indicate backwards compatible changes to the protocol.
> > + **/
> > + UINT8 Revision;
> > + PCH_SPI_FLASH_READ FlashRead; ///< Read data from the
> flash
> > part.
> > + PCH_SPI_FLASH_WRITE FlashWrite; ///< Write data to the
> flash
> > part. Remark: Erase may be needed before write to the flash part.
> > + PCH_SPI_FLASH_ERASE FlashErase; ///< Erase some area on
> the
> > flash part.
> > + PCH_SPI_FLASH_READ_SFDP FlashReadSfdp; ///< Read SFDP
> data
> > from the flash part.
> > + PCH_SPI_FLASH_READ_JEDEC_ID FlashReadJedecId; ///< Read Jedec
> Id
> > from the flash part.
> > + PCH_SPI_FLASH_WRITE_STATUS FlashWriteStatus; ///< Write the
> status
> > register in the flash part.
> > + PCH_SPI_FLASH_READ_STATUS FlashReadStatus; ///< Read status
> > register in the flash part.
> > + PCH_SPI_GET_REGION_ADDRESS GetRegionAddress; ///< Get the
> SPI
> > region base and size
> > + PCH_SPI_READ_PCH_SOFTSTRAP ReadPchSoftStrap; ///< Read PCH
> Soft
> > Strap Values
> > + PCH_SPI_READ_CPU_SOFTSTRAP ReadCpuSoftStrap; ///< Read CPU
> Soft
> > Strap Values
> > +};
> > +
> > +/**
> > + PCH SPI PPI/PROTOCOL revision number
> > +
> > + Revision 1: Initial version
> > +**/
> > +#define PCH_SPI_SERVICES_REVISION 1
> > +
> > +#endif
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> > new file mode 100644
> > index 0000000000..e08721f405
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
> > @@ -0,0 +1,647 @@
> > +/** @file
> > + Register names for PCH PMC device
> > +
> > + Conventions:
> > +
> > + - Prefixes:
> > + Definitions beginning with "R_" are registers
> > + Definitions beginning with "B_" are bits within registers
> > + Definitions beginning with "V_" are meaningful values within the bits
> > + Definitions beginning with "S_" are register sizes
> > + Definitions beginning with "N_" are the bit position
> > + - In general, PCH registers are denoted by "_PCH_" in register names
> > + - Registers / bits that are different between PCH generations are denoted
> by
> > + "_PCH_[generation_name]_" in register/bit names.
> > + - Registers / bits that are specific to PCH-H denoted by "_H_" in
> register/bit
> > names.
> > + Registers / bits that are specific to PCH-LP denoted by "_LP_" in
> register/bit
> > names.
> > + e.g., "_PCH_H_", "_PCH_LP_"
> > + Registers / bits names without _H_ or _LP_ apply for both H and LP.
> > + - Registers / bits that are different between SKUs are denoted by
> > "_[SKU_name]"
> > + at the end of the register/bit names
> > + - Registers / bits of new devices introduced in a PCH generation will be
> just
> > named
> > + as "_PCH_" without [generation_name] inserted.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_REGS_PMC_H_
> > +#define _PCH_REGS_PMC_H_
> > +
> > +//
> > +// PMC Registers (D31:F2)
> > +//
> > +#define PCI_DEVICE_NUMBER_PCH_PMC 31
> > +#define PCI_FUNCTION_NUMBER_PCH_PMC 2
> > +
> > +#define R_PCH_PMC_PM_DATA_BAR 0x10
> > +#define B_PCH_PMC_PM_DATA_BAR 0xFFFFC000
> > +#define R_PCH_PMC_ACPI_BASE 0x40
> > +#define B_PCH_PMC_ACPI_BASE_BAR 0xFFFC
> > +#define R_PCH_PMC_ACPI_CNT 0x44
> > +#define B_PCH_PMC_ACPI_CNT_PWRM_EN BIT8
> > ///< PWRM enable
> > +#define B_PCH_PMC_ACPI_CNT_ACPI_EN BIT7
> ///<
> > ACPI eanble
> > +#define B_PCH_PMC_ACPI_CNT_SCIS (BIT2 | BIT1 | BIT0)
> > ///< SCI IRQ select
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ9 0
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ10 1
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ11 2
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ20 4
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ21 5
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ22 6
> > +#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ23 7
> > +#define R_PCH_PMC_PWRM_BASE 0x48
> > +#define B_PCH_PMC_PWRM_BASE_BAR 0xFFFF0000
> > ///< PWRM must be 64KB alignment to align the source decode.
> > +#define R_PCH_PMC_GEN_PMCON_A 0xA0
> > +#define B_PCH_PMC_GEN_PMCON_A_DC_PP_DIS BIT30
> > +#define B_PCH_PMC_GEN_PMCON_A_DSX_PP_DIS BIT29
> > +#define B_PCH_PMC_GEN_PMCON_A_AG3_PP_EN BIT28
> > +#define B_PCH_PMC_GEN_PMCON_A_SX_PP_EN BIT27
> > +#define B_PCH_PMC_GEN_PMCON_A_DISB BIT23
> > +#define B_PCH_PMC_GEN_PMCON_A_MEM_SR BIT21
> > +#define B_PCH_PMC_GEN_PMCON_A_MS4V BIT18
> > +#define B_PCH_PMC_GEN_PMCON_A_GBL_RST_STS BIT16
> > +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_OPI_PLL_SD_INC0
> BIT13
> > +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_SPXB_CG_INC0 BIT12
> > +#define B_PCH_PMC_GEN_PMCON_A_BIOS_PCI_EXP_EN BIT10
> > +#define B_PCH_PMC_GEN_PMCON_A_PWRBTN_LVL BIT9
> > +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_C0 BIT7
> > +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_OPI_ON BIT6
> > +#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_BCLKREQ_ON
> > BIT5
> > +#define B_PCH_PMC_GEN_PMCON_A_SMI_LOCK BIT4
> > +#define B_PCH_PMC_GEN_PMCON_A_ESPI_SMI_LOCK BIT3
> > ///< ESPI SMI lock
> > +#define B_PCH_PMC_GEN_PMCON_A_PER_SMI_SEL 0x0003
> > +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_64S 0x0000
> > +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_32S 0x0001
> > +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_16S 0x0002
> > +#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_8S 0x0003
> > +#define R_PCH_PMC_GEN_PMCON_B 0xA4
> > +#define B_PCH_PMC_GEN_PMCON_B_SLPSX_STR_POL_LOCK BIT18
> > ///< Lock down SLP_S3/SLP_S4 Minimum Assertion width
> > +#define B_PCH_PMC_GEN_PMCON_B_ACPI_BASE_LOCK BIT17
> > ///< Lock ACPI BASE at 0x40, only cleared by reset when set
> > +#define B_PCH_PMC_GEN_PMCON_B_PM_DATA_BAR_DIS BIT16
> > +#define B_PCH_PMC_GEN_PMCON_B_PME_B0_S5_DIS BIT15
> > +#define B_PCH_PMC_GEN_PMCON_B_SUS_PWR_FLR BIT14
> > +#define B_PCH_PMC_GEN_PMCON_B_WOL_EN_OVRD BIT13
> > +#define B_PCH_PMC_GEN_PMCON_B_DISABLE_SX_STRETCH BIT12
> > +#define B_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW 0xC00
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_60US 0x000
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_1MS 0x400
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_50MS 0x800
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_2S 0xC00
> > +#define B_PCH_PMC_GEN_PMCON_B_HOST_RST_STS BIT9
> > +#define B_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL 0xC0
> > +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_64MS 0xC0
> > +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_32MS 0x80
> > +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_16MS 0x40
> > +#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_1_5MS 0x00
> > +#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW 0x30
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_1S 0x30
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_2S 0x20
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_3S 0x10
> > +#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_4S 0x00
> > +#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_ASE BIT3
> > +#define B_PCH_PMC_GEN_PMCON_B_RTC_PWR_STS BIT2
> > +#define B_PCH_PMC_GEN_PMCON_B_PWR_FLR BIT1
> > +#define B_PCH_PMC_GEN_PMCON_B_AFTERG3_EN BIT0
> > +#define R_PCH_PMC_BM_CX_CNF 0xA8
> > +#define B_PCH_PMC_BM_CX_CNF_STORAGE_BREAK_EN BIT31
> > +#define B_PCH_PMC_BM_CX_CNF_PCIE_BREAK_EN BIT30
> > +#define B_PCH_PMC_BM_CX_CNF_AZ_BREAK_EN BIT24
> > +#define B_PCH_PMC_BM_CX_CNF_DPSN_BREAK_EN BIT19
> > +#define B_PCH_PMC_BM_CX_CNF_XHCI_BREAK_EN BIT17
> > +#define B_PCH_PMC_BM_CX_CNF_SATA3_BREAK_EN BIT16
> > +#define B_PCH_PMC_BM_CX_CNF_SCRATCHPAD BIT15
> > +#define B_PCH_PMC_BM_CX_CNF_PHOLD_BM_STS_BLOCK BIT14
> > +#define B_PCH_PMC_BM_CX_CNF_MASK_CF BIT11
> > +#define B_PCH_PMC_BM_CX_CNF_BM_STS_ZERO_EN BIT10
> > +#define B_PCH_PMC_BM_CX_CNF_PM_SYNC_MSG_MODE BIT9
> > +#define R_PCH_PMC_ETR3 0xAC
> > +#define B_PCH_PMC_ETR3_CF9LOCK BIT31 ///<
> CF9h
> > Lockdown
> > +#define B_PCH_PMC_ETR3_USB_CACHE_DIS BIT21
> > +#define B_PCH_PMC_ETR3_CF9GR BIT20 ///< CF9h
> > Global Reset
> > +#define B_PCH_PMC_ETR3_SKIP_HOST_RST_HS BIT19
> > +#define B_PCH_PMC_ETR3_CWORWRE BIT18
> > +
> > +//
> > +// ACPI and legacy I/O register offsets from ACPIBASE
> > +//
> > +#define R_PCH_ACPI_PM1_STS 0x00
> > +#define S_PCH_ACPI_PM1_STS 2
> > +#define B_PCH_ACPI_PM1_STS_WAK BIT15
> > +#define B_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS BIT14
> > +#define B_PCH_ACPI_PM1_STS_PRBTNOR BIT11
> > +#define B_PCH_ACPI_PM1_STS_RTC BIT10
> > +#define B_PCH_ACPI_PM1_STS_PWRBTN BIT8
> > +#define B_PCH_ACPI_PM1_STS_GBL BIT5
> > +#define B_PCH_ACPI_PM1_STS_BM BIT4
> > +#define B_PCH_ACPI_PM1_STS_TMROF BIT0
> > +#define N_PCH_ACPI_PM1_STS_WAK 15
> > +#define N_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS 14
> > +#define N_PCH_ACPI_PM1_STS_PRBTNOR 11
> > +#define N_PCH_ACPI_PM1_STS_RTC 10
> > +#define N_PCH_ACPI_PM1_STS_PWRBTN 8
> > +#define N_PCH_ACPI_PM1_STS_GBL 5
> > +#define N_PCH_ACPI_PM1_STS_BM 4
> > +#define N_PCH_ACPI_PM1_STS_TMROF 0
> > +
> > +#define R_PCH_ACPI_PM1_EN 0x02
> > +#define S_PCH_ACPI_PM1_EN 2
> > +#define B_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS BIT14
> > +#define B_PCH_ACPI_PM1_EN_RTC BIT10
> > +#define B_PCH_ACPI_PM1_EN_PWRBTN BIT8
> > +#define B_PCH_ACPI_PM1_EN_GBL BIT5
> > +#define B_PCH_ACPI_PM1_EN_TMROF BIT0
> > +#define N_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS 14
> > +#define N_PCH_ACPI_PM1_EN_RTC 10
> > +#define N_PCH_ACPI_PM1_EN_PWRBTN 8
> > +#define N_PCH_ACPI_PM1_EN_GBL 5
> > +#define N_PCH_ACPI_PM1_EN_TMROF 0
> > +
> > +#define R_PCH_ACPI_PM1_CNT 0x04
> > +#define S_PCH_ACPI_PM1_CNT 4
> > +#define B_PCH_ACPI_PM1_CNT_SLP_EN BIT13
> > +#define B_PCH_ACPI_PM1_CNT_SLP_TYP (BIT12 | BIT11 | BIT10)
> > +#define V_PCH_ACPI_PM1_CNT_S0 0
> > +#define V_PCH_ACPI_PM1_CNT_S1 BIT10
> > +#define V_PCH_ACPI_PM1_CNT_S3 (BIT12 | BIT10)
> > +#define V_PCH_ACPI_PM1_CNT_S4 (BIT12 | BIT11)
> > +#define V_PCH_ACPI_PM1_CNT_S5 (BIT12 | BIT11 | BIT10)
> > +#define B_PCH_ACPI_PM1_CNT_GBL_RLS BIT2
> > +#define B_PCH_ACPI_PM1_CNT_BM_RLD BIT1
> > +#define B_PCH_ACPI_PM1_CNT_SCI_EN BIT0
> > +
> > +#define R_PCH_ACPI_PM1_TMR 0x08
> > +#define V_PCH_ACPI_TMR_FREQUENCY 3579545
> > +#define B_PCH_ACPI_PM1_TMR_VAL 0xFFFFFF
> > +#define V_PCH_ACPI_PM1_TMR_MAX_VAL 0x1000000 ///<
> The
> > timer is 24 bit overflow
> > +
> > +#define R_PCH_SMI_EN 0x30
> > +#define S_PCH_SMI_EN 4
> > +#define B_PCH_SMI_EN_LEGACY_USB3 BIT31
> > +#define B_PCH_SMI_EN_GPIO_UNLOCK_SMI BIT27
> > +#define B_PCH_SMI_EN_LEGACY_USB2 BIT17
> > +#define B_PCH_SMI_EN_PERIODIC BIT14
> > +#define B_PCH_SMI_EN_TCO BIT13
> > +#define B_PCH_SMI_EN_MCSMI BIT11
> > +#define B_PCH_SMI_EN_BIOS_RLS BIT7
> > +#define B_PCH_SMI_EN_SWSMI_TMR BIT6
> > +#define B_PCH_SMI_EN_APMC BIT5
> > +#define B_PCH_SMI_EN_ON_SLP_EN BIT4
> > +#define B_PCH_SMI_EN_LEGACY_USB BIT3
> > +#define B_PCH_SMI_EN_BIOS BIT2
> > +#define B_PCH_SMI_EN_EOS BIT1
> > +#define B_PCH_SMI_EN_GBL_SMI BIT0
> > +#define N_PCH_SMI_EN_LEGACY_USB3 31
> > +#define N_PCH_SMI_EN_ESPI 28
> > +#define N_PCH_SMI_EN_GPIO_UNLOCK 27
> > +#define N_PCH_SMI_EN_INTEL_USB2 18
> > +#define N_PCH_SMI_EN_LEGACY_USB2 17
> > +#define N_PCH_SMI_EN_PERIODIC 14
> > +#define N_PCH_SMI_EN_TCO 13
> > +#define N_PCH_SMI_EN_MCSMI 11
> > +#define N_PCH_SMI_EN_BIOS_RLS 7
> > +#define N_PCH_SMI_EN_SWSMI_TMR 6
> > +#define N_PCH_SMI_EN_APMC 5
> > +#define N_PCH_SMI_EN_ON_SLP_EN 4
> > +#define N_PCH_SMI_EN_LEGACY_USB 3
> > +#define N_PCH_SMI_EN_BIOS 2
> > +#define N_PCH_SMI_EN_EOS 1
> > +#define N_PCH_SMI_EN_GBL_SMI 0
> > +
> > +#define R_PCH_SMI_STS 0x34
> > +#define S_PCH_SMI_STS 4
> > +#define B_PCH_SMI_STS_LEGACY_USB3 BIT31
> > +#define B_PCH_SMI_STS_GPIO_UNLOCK BIT27
> > +#define B_PCH_SMI_STS_SPI BIT26
> > +#define B_PCH_SMI_STS_MONITOR BIT21
> > +#define B_PCH_SMI_STS_PCI_EXP BIT20
> > +#define B_PCH_SMI_STS_PATCH BIT19
> > +#define B_PCH_SMI_STS_INTEL_USB2 BIT18
> > +#define B_PCH_SMI_STS_LEGACY_USB2 BIT17
> > +#define B_PCH_SMI_STS_SMBUS BIT16
> > +#define B_PCH_SMI_STS_SERIRQ BIT15
> > +#define B_PCH_SMI_STS_PERIODIC BIT14
> > +#define B_PCH_SMI_STS_TCO BIT13
> > +#define B_PCH_SMI_STS_DEVMON BIT12
> > +#define B_PCH_SMI_STS_MCSMI BIT11
> > +#define B_PCH_SMI_STS_GPIO_SMI BIT10
> > +#define B_PCH_SMI_STS_GPE0 BIT9
> > +#define B_PCH_SMI_STS_PM1_STS_REG BIT8
> > +#define B_PCH_SMI_STS_SWSMI_TMR BIT6
> > +#define B_PCH_SMI_STS_APM BIT5
> > +#define B_PCH_SMI_STS_ON_SLP_EN BIT4
> > +#define B_PCH_SMI_STS_LEGACY_USB BIT3
> > +#define B_PCH_SMI_STS_BIOS BIT2
> > +#define N_PCH_SMI_STS_LEGACY_USB3 31
> > +#define N_PCH_SMI_STS_ESPI 28
> > +#define N_PCH_SMI_STS_GPIO_UNLOCK 27
> > +#define N_PCH_SMI_STS_SPI 26
> > +#define N_PCH_SMI_STS_MONITOR 21
> > +#define N_PCH_SMI_STS_PCI_EXP 20
> > +#define N_PCH_SMI_STS_PATCH 19
> > +#define N_PCH_SMI_STS_INTEL_USB2 18
> > +#define N_PCH_SMI_STS_LEGACY_USB2 17
> > +#define N_PCH_SMI_STS_SMBUS 16
> > +#define N_PCH_SMI_STS_SERIRQ 15
> > +#define N_PCH_SMI_STS_PERIODIC 14
> > +#define N_PCH_SMI_STS_TCO 13
> > +#define N_PCH_SMI_STS_DEVMON 12
> > +#define N_PCH_SMI_STS_MCSMI 11
> > +#define N_PCH_SMI_STS_GPIO_SMI 10
> > +#define N_PCH_SMI_STS_GPE0 9
> > +#define N_PCH_SMI_STS_PM1_STS_REG 8
> > +#define N_PCH_SMI_STS_SWSMI_TMR 6
> > +#define N_PCH_SMI_STS_APM 5
> > +#define N_PCH_SMI_STS_ON_SLP_EN 4
> > +#define N_PCH_SMI_STS_LEGACY_USB 3
> > +#define N_PCH_SMI_STS_BIOS 2
> > +
> > +#define R_PCH_ACPI_GPE_CNTL 0x40
> > +#define B_PCH_ACPI_GPE_CNTL_SWGPE_CTRL BIT17
> > +
> > +#define R_PCH_DEVACT_STS 0x44
> > +#define S_PCH_DEVACT_STS 2
> > +#define B_PCH_DEVACT_STS_MASK 0x13E1
> > +#define B_PCH_DEVACT_STS_KBC BIT12
> > +#define B_PCH_DEVACT_STS_PIRQDH BIT9
> > +#define B_PCH_DEVACT_STS_PIRQCG BIT8
> > +#define B_PCH_DEVACT_STS_PIRQBF BIT7
> > +#define B_PCH_DEVACT_STS_PIRQAE BIT6
> > +#define B_PCH_DEVACT_STS_D0_TRP BIT0
> > +#define N_PCH_DEVACT_STS_KBC 12
> > +#define N_PCH_DEVACT_STS_PIRQDH 9
> > +#define N_PCH_DEVACT_STS_PIRQCG 8
> > +#define N_PCH_DEVACT_STS_PIRQBF 7
> > +#define N_PCH_DEVACT_STS_PIRQAE 6
> > +
> > +#define R_PCH_ACPI_PM2_CNT 0x50
> > +#define B_PCH_ACPI_PM2_CNT_ARB_DIS BIT0
> > +
> > +#define R_PCH_OC_WDT_CTL 0x54
> > +#define B_PCH_OC_WDT_CTL_RLD BIT31
> > +#define B_PCH_OC_WDT_CTL_ICCSURV_STS BIT25
> > +#define B_PCH_OC_WDT_CTL_NO_ICCSURV_STS BIT24
> > +#define B_PCH_OC_WDT_CTL_FORCE_ALL BIT15
> > +#define B_PCH_OC_WDT_CTL_EN BIT14
> > +#define B_PCH_OC_WDT_CTL_ICCSURV BIT13
> > +#define B_PCH_OC_WDT_CTL_LCK BIT12
> > +#define B_PCH_OC_WDT_CTL_TOV_MASK 0x3FF
> > +#define B_PCH_OC_WDT_CTL_FAILURE_STS BIT23
> > +#define B_PCH_OC_WDT_CTL_UNXP_RESET_STS BIT22
> > +#define B_PCH_OC_WDT_CTL_AFTER_POST 0x3F0000
> > +#define V_PCH_OC_WDT_CTL_STATUS_FAILURE 1
> > +#define V_PCH_OC_WDT_CTL_STATUS_OK 0
> > +
> > +#define R_PCH_ACPI_GPE0_STS_31_0 0x80
> > +#define R_PCH_ACPI_GPE0_STS_63_32 0x84
> > +#define R_PCH_ACPI_GPE0_STS_95_64 0x88
> > +#define R_PCH_ACPI_GPE0_STS_127_96 0x8C
> > +#define S_PCH_ACPI_GPE0_STS_127_96 4
> > +#define B_PCH_ACPI_GPE0_STS_127_96_WADT BIT18
> > +#define B_PCH_ACPI_GPE0_STS_127_96_LAN_WAKE BIT16
> > +#define B_PCH_ACPI_GPE0_STS_127_96_PME_B0 BIT13
> > +#define B_PCH_ACPI_GPE0_STS_127_96_ME_SCI BIT12
> > +#define B_PCH_ACPI_GPE0_STS_127_96_PME BIT11
> > +#define B_PCH_ACPI_GPE0_STS_127_96_BATLOW BIT10
> > +#define B_PCH_ACPI_GPE0_STS_127_96_PCI_EXP BIT9
> > +#define B_PCH_ACPI_GPE0_STS_127_96_RI BIT8
> > +#define B_PCH_ACPI_GPE0_STS_127_96_SMB_WAK BIT7
> > +#define B_PCH_ACPI_GPE0_STS_127_96_TC0SCI BIT6
> > +#define B_PCH_ACPI_GPE0_STS_127_96_SWGPE BIT2
> > +#define B_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG BIT1
> > +#define N_PCH_ACPI_GPE0_STS_127_96_PME_B0 13
> > +#define N_PCH_ACPI_GPE0_STS_127_96_PME 11
> > +#define N_PCH_ACPI_GPE0_STS_127_96_BATLOW 10
> > +#define N_PCH_ACPI_GPE0_STS_127_96_PCI_EXP 9
> > +#define N_PCH_ACPI_GPE0_STS_127_96_RI 8
> > +#define N_PCH_ACPI_GPE0_STS_127_96_SMB_WAK 7
> > +#define N_PCH_ACPI_GPE0_STS_127_96_TC0SCI 6
> > +#define N_PCH_ACPI_GPE0_STS_127_96_SWGPE 2
> > +#define N_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG 1
> > +
> > +#define R_PCH_ACPI_GPE0_EN_31_0 0x90
> > +#define R_PCH_ACPI_GPE0_EN_63_32 0x94
> > +#define R_PCH_ACPI_GPE0_EN_95_64 0x98
> > +#define R_PCH_ACPI_GPE0_EN_127_96 0x9C
> > +#define S_PCH_ACPI_GPE0_EN_127_96 4
> > +#define B_PCH_ACPI_GPE0_EN_127_96_WADT BIT18
> > +#define B_PCH_ACPI_GPE0_EN_127_96_LAN_WAKE BIT16
> > +#define B_PCH_ACPI_GPE0_EN_127_96_PME_B0 BIT13
> > +#define B_PCH_ACPI_GPE0_EN_127_96_ME_SCI BIT12
> > +#define B_PCH_ACPI_GPE0_EN_127_96_PME BIT11
> > +#define B_PCH_ACPI_GPE0_EN_127_96_BATLOW BIT10
> > +#define B_PCH_ACPI_GPE0_EN_127_96_PCI_EXP BIT9
> > +#define B_PCH_ACPI_GPE0_EN_127_96_RI BIT8
> > +#define B_PCH_ACPI_GPE0_EN_127_96_TC0SCI BIT6
> > +#define B_PCH_ACPI_GPE0_EN_127_96_SWGPE BIT2
> > +#define B_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG BIT1
> > +#define N_PCH_ACPI_GPE0_EN_127_96_PME_B0 13
> > +#define N_PCH_ACPI_GPE0_EN_127_96_USB3 12
> > +#define N_PCH_ACPI_GPE0_EN_127_96_PME 11
> > +#define N_PCH_ACPI_GPE0_EN_127_96_BATLOW 10
> > +#define N_PCH_ACPI_GPE0_EN_127_96_PCI_EXP 9
> > +#define N_PCH_ACPI_GPE0_EN_127_96_RI 8
> > +#define N_PCH_ACPI_GPE0_EN_127_96_TC0SCI 6
> > +#define N_PCH_ACPI_GPE0_EN_127_96_SWGPE 2
> > +#define N_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG 1
> > +
> > +
> > +//
> > +// TCO register I/O map
> > +//
> > +#define R_PCH_TCO_RLD 0x0
> > +#define R_PCH_TCO_DAT_IN 0x2
> > +#define R_PCH_TCO_DAT_OUT 0x3
> > +#define R_PCH_TCO1_STS 0x04
> > +#define S_PCH_TCO1_STS 2
> > +#define B_PCH_TCO1_STS_DMISERR BIT12
> > +#define B_PCH_TCO1_STS_DMISMI BIT10
> > +#define B_PCH_TCO1_STS_DMISCI BIT9
> > +#define B_PCH_TCO1_STS_BIOSWR BIT8
> > +#define B_PCH_TCO1_STS_NEWCENTURY BIT7
> > +#define B_PCH_TCO1_STS_TIMEOUT BIT3
> > +#define B_PCH_TCO1_STS_TCO_INT BIT2
> > +#define B_PCH_TCO1_STS_SW_TCO_SMI BIT1
> > +#define B_PCH_TCO1_STS_NMI2SMI BIT0
> > +#define N_PCH_TCO1_STS_DMISMI 10
> > +#define N_PCH_TCO1_STS_BIOSWR 8
> > +#define N_PCH_TCO1_STS_NEWCENTURY 7
> > +#define N_PCH_TCO1_STS_TIMEOUT 3
> > +#define N_PCH_TCO1_STS_SW_TCO_SMI 1
> > +#define N_PCH_TCO1_STS_NMI2SMI 0
> > +
> > +#define R_PCH_TCO2_STS 0x06
> > +#define S_PCH_TCO2_STS 2
> > +#define B_PCH_TCO2_STS_SMLINK_SLV_SMI BIT4
> > +#define B_PCH_TCO2_STS_BAD_BIOS BIT3
> > +#define B_PCH_TCO2_STS_BOOT BIT2
> > +#define B_PCH_TCO2_STS_SECOND_TO BIT1
> > +#define B_PCH_TCO2_STS_INTRD_DET BIT0
> > +#define N_PCH_TCO2_STS_INTRD_DET 0
> > +
> > +#define R_PCH_TCO1_CNT 0x08
> > +#define S_PCH_TCO1_CNT 2
> > +#define B_PCH_TCO_CNT_LOCK BIT12
> > +#define B_PCH_TCO_CNT_TMR_HLT BIT11
> > +#define B_PCH_TCO_CNT_NMI2SMI_EN BIT9
> > +#define B_PCH_TCO_CNT_NMI_NOW BIT8
> > +#define N_PCH_TCO_CNT_NMI2SMI_EN 9
> > +
> > +#define R_PCH_TCO2_CNT 0x0A
> > +#define S_PCH_TCO2_CNT 2
> > +#define B_PCH_TCO2_CNT_OS_POLICY 0x0030
> > +#define B_PCH_TCO2_CNT_GPI11_ALERT_DISABLE 0x0008
> > +#define B_PCH_TCO2_CNT_INTRD_SEL 0x0006
> > +#define N_PCH_TCO2_CNT_INTRD_SEL 2
> > +
> > +#define R_PCH_TCO_MESSAGE1 0x0C
> > +#define R_PCH_TCO_MESSAGE2 0x0D
> > +#define R_PCH_TCO_WDCNT 0x0E
> > +#define R_PCH_TCO_SW_IRQ_GEN 0x10
> > +#define B_PCH_TCO_IRQ12_CAUSE BIT1
> > +#define B_PCH_TCO_IRQ1_CAUSE BIT0
> > +#define R_PCH_TCO_TMR 0x12
> > +
> > +//
> > +// PWRM Registers
> > +//
> > +#define R_PCH_WADT_AC 0x0 ///<
> Wake
> > Alarm Device Timer: AC
> > +#define R_PCH_WADT_DC 0x4 ///<
> Wake
> > Alarm Device Timer: DC
> > +#define R_PCH_WADT_EXP_AC 0x8 ///<
> Wake
> > Alarm Device Expired Timer: AC
> > +#define R_PCH_WADT_EXP_DC 0xC ///<
> Wake
> > Alarm Device Expired Timer: DC
> > +#define R_PCH_PWRM_PRSTS 0x10 ///<
> Power
> > and Reset Status
> > +#define B_PCH_PWRM_PRSTS_VE_WD_TMR_STS BIT7
> > ///< VE Watchdog Timer Status
> > +#define B_PCH_PWRM_PRSTS_WOL_OVR_WK_STS BIT5
> > +#define B_PCH_PWRM_PRSTS_FIELD_1 BIT4
> > +#define B_PCH_PWRM_PRSTS_ME_WAKE_STS BIT0
> > +#define R_PCH_PWRM_14 0x14
> > +#define R_PCH_PWRM_CFG 0x18 ///<
> Power
> > Management Configuration
> > +#define B_PCH_PWRM_CFG_ALLOW_24_OSC_SD BIT29
> > ///< Allow 24MHz Crystal Oscillator Shutdown
> > +#define B_PCH_PWRM_CFG_ALLOW_USB2_CORE_PG BIT25
> > ///< Allow USB2 Core Power Gating
> > +#define B_PCH_PWRM_CFG_RTC_DS_WAKE_DIS BIT21
> > ///< RTC Wake from Deep S4/S5 Disable
> > +#define B_PCH_PWRM_CFG_SSMAW_MASK (BIT19 |
> BIT18)
> > ///< SLP_SUS# Min Assertion Width
> > +#define V_PCH_PWRM_CFG_SSMAW_4S (BIT19 | BIT18)
> > ///< 4 seconds
> > +#define V_PCH_PWRM_CFG_SSMAW_1S BIT19
> > ///< 1 second
> > +#define V_PCH_PWRM_CFG_SSMAW_0_5S BIT18
> > ///< 0.5 second (500ms)
> > +#define V_PCH_PWRM_CFG_SSMAW_0S 0
> ///< 0
> > second
> > +#define B_PCH_PWRM_CFG_SAMAW_MASK (BIT17 |
> BIT16)
> > ///< SLP_A# Min Assertion Width
> > +#define V_PCH_PWRM_CFG_SAMAW_2S (BIT17 | BIT16)
> > ///< 2 seconds
> > +#define V_PCH_PWRM_CFG_SAMAW_98ms BIT17
> > ///< 98ms
> > +#define V_PCH_PWRM_CFG_SAMAW_4S BIT16
> > ///< 4 seconds
> > +#define V_PCH_PWRM_CFG_SAMAW_0S 0
> ///< 0
> > second
> > +#define B_PCH_PWRM_CFG_RPCD_MASK (BIT9 | BIT8)
> > ///< Reset Power Cycle Duration
> > +#define V_PCH_PWRM_CFG_RPCD_1S (BIT9 | BIT8)
> > ///< 1-2 seconds
> > +#define V_PCH_PWRM_CFG_RPCD_2S BIT9
> ///< 2-
> > 3 seconds
> > +#define V_PCH_PWRM_CFG_RPCD_3S BIT8
> ///< 3-
> > 4 seconds
> > +#define V_PCH_PWRM_CFG_RPCD_4S 0
> ///< 4-5
> > seconds (Default)
> > +#define R_PCH_PWRM_PCH_PM_STS 0x1C
> ///<
> > Contains misc. fields used to record PCH power management events
> > +#define B_PCH_PWRM_PCH_PM_STS_PMC_MSG_FULL_STS BIT24
> > ///< MTPMC transport mechanism full indication
> > +#define R_PCH_PWRM_MTPMC 0x20
> ///<
> > Message to PMC
> > +#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_0_15 0xE
> > ///< Command to override lanes 0-15 power gating
> > +#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_16_31 0xF
> > ///< Command to override lanes 16-31 power gating
> > +#define B_PCH_PWRM_MTPMC_PG_CMD_DATA 0xFFFF0000
> > ///< Data part of PowerGate Message to PMC
> > +#define N_PCH_PWRM_MTPMC_PG_CMD_DATA 16
> > +#define R_PCH_PWRM_PCH_PM_STS2 0x24
> ///<
> > PCH Power Management Status
> > +#define R_PCH_PWRM_S3_PWRGATE_POL 0x28
> > ///< S3 Power Gating Policies
> > +#define B_PCH_PWRM_S3DC_GATE_SUS BIT1
> ///<
> > Deep S3 Enable in DC Mode
> > +#define B_PCH_PWRM_S3AC_GATE_SUS BIT0
> ///<
> > Deep S3 Enable in AC Mode
> > +#define R_PCH_PWRM_S4_PWRGATE_POL 0x2C
> > ///< Deep S4 Power Policies
> > +#define B_PCH_PWRM_S4DC_GATE_SUS BIT1
> ///<
> > Deep S4 Enable in DC Mode
> > +#define B_PCH_PWRM_S4AC_GATE_SUS BIT0
> ///<
> > Deep S4 Enable in AC Mode
> > +#define R_PCH_PWRM_S5_PWRGATE_POL 0x30
> > ///< Deep S5 Power Policies
> > +#define B_PCH_PWRM_S5DC_GATE_SUS BIT15
> ///<
> > Deep S5 Enable in DC Mode
> > +#define B_PCH_PWRM_S5AC_GATE_SUS BIT14
> ///<
> > Deep S5 Enable in AC Mode
> > +#define R_PCH_PWRM_DSX_CFG 0x34
> ///<
> > Deep SX Configuration
> > +#define B_PCH_PWRM_DSX_CFG_WAKE_PIN_DSX_EN BIT2
> > ///< WAKE# Pin DeepSx Enable
> > +#define B_PCH_PWRM_DSX_CFG_ACPRES_PD_DSX_DIS BIT1
> > ///< AC_PRESENT pin pulldown in DeepSx disable
> > +#define B_PCH_PWRM_DSX_CFG_LAN_WAKE_EN BIT0
> > ///< LAN_WAKE Pin DeepSx Enable
> > +#define R_PCH_PWRM_CFG2 0x3C ///<
> Power
> > Management Configuration Reg 2
> > +#define B_PCH_PWRM_CFG2_PBOP (BIT31 | BIT30 |
> BIT29)
> > ///< Power Button Override Period (PBOP)
> > +#define N_PCH_PWRM_CFG2_PBOP 29
> ///<
> > Power Button Override Period (PBOP)
> > +#define B_PCH_PWRM_CFG2_PB_DIS BIT28
> ///<
> > Power Button Native Mode Disable (PB_DIS)
> > +#define B_PCH_PWRM_CFG2_DRAM_RESET_CTL BIT26
> > ///< DRAM RESET# control
> > +#define R_PCH_PWRM_EN_SN_SLOW_RING 0x48
> > ///< Enable Snoop Request to SLOW_RING
> > +#define R_PCH_PWRM_EN_SN_SLOW_RING2 0x4C
> > ///< Enable Snoop Request to SLOW_RING 2nd Reg
> > +#define R_PCH_PWRM_EN_SN_SA 0x50
> ///<
> > Enable Snoop Request to SA
> > +#define R_PCH_PWRM_EN_SN_SA2 0x54
> ///<
> > Enable Snoop Request to SA 2nd Reg
> > +#define R_PCH_PWRM_EN_SN_SLOW_RING_CF 0x58
> > ///< Enable Snoop Request to SLOW_RING_CF
> > +#define R_PCH_PWRM_EN_NS_SA 0x68
> ///<
> > Enable Non-Snoop Request to SA
> > +#define R_PCH_PWRM_EN_CW_SLOW_RING 0x80
> > ///< Enable Clock Wake to SLOW_RING
> > +#define R_PCH_PWRM_EN_CW_SLOW_RING2 0x84
> > ///< Enable Clock Wake to SLOW_RING 2nd Reg
> > +#define R_PCH_PWRM_EN_CW_SA 0x88
> ///<
> > Enable Clock Wake to SA
> > +#define R_PCH_PWRM_EN_CW_SA2 0x8C
> ///<
> > Enable Clock Wake to SA 2nd Reg
> > +#define R_PCH_PWRM_EN_CW_SLOW_RING_CF 0x98
> > ///< Enable Clock Wake to SLOW_RING_CF
> > +#define R_PCH_PWRM_EN_PA_SLOW_RING 0xA8
> > ///< Enable Pegged Active to SLOW_RING
> > +#define R_PCH_PWRM_EN_PA_SLOW_RING2 0xAC
> > ///< Enable Pegged Active to SLOW_RING 2nd Reg
> > +#define R_PCH_PWRM_EN_PA_SA 0xB0
> ///<
> > Enable Pegged Active to SA
> > +#define R_PCH_PWRM_EN_PA_SA2 0xB4
> ///<
> > Enable Pegged Active to SA 2nd Reg
> > +#define R_PCH_PWRM_EN_MISC_EVENT 0xC0
> ///<
> > Enable Misc PM_SYNC Events
> > +#define R_PCH_PWRM_PMSYNC_TPR_CONFIG 0xC4
> > +#define B_PCH_PWRM_PMSYNC_TPR_CONFIG_LOCK BIT31
> > +#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_EN BIT26
> > +#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE (BIT25 |
> > BIT24)
> > +#define N_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE 24
> > +#define V_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE_1 1
> > +#define R_PCH_PWRM_PMSYNC_MISC_CFG 0xC8
> > +#define B_PCH_PWRM_PMSYNC_PM_SYNC_LOCK BIT15
> > ///< PM_SYNC Configuration Lock
> > +#define B_PCH_PWRM_PMSYNC_GPIO_D_SEL BIT11
> > +#define B_PCH_PWRM_PMSYNC_GPIO_C_SEL BIT10
> > +#define R_PCH_PWRM_PM_SYNC_STATE_HYS 0xD0
> > ///< PM_SYNC State Hysteresis
> > +#define R_PCH_PWRM_PM_SYNC_MODE 0xD4
> > ///< PM_SYNC Pin Mode
> > +#define R_PCH_PWRM_CFG3 0xE0 ///<
> Power
> > Management Configuration Reg 3
> > +#define B_PCH_PWRM_CFG3_DSX_WLAN_PP_EN BIT16
> > ///< Deep-Sx WLAN Phy Power Enable
> > +#define B_PCH_PWRM_CFG3_HOST_WLAN_PP_EN BIT17
> > ///< Host Wireless LAN Phy Power Enable
> > +#define B_PCH_PWRM_CFG3_PWRG_LOCK BIT2
> > ///< Lock power gating override messages
> > +#define R_PCH_PWRM_PM_DOWN_PPB_CFG 0xE4
> > ///< PM_DOWN PCH_POWER_BUDGET CONFIGURATION
> > +#define R_PCH_PWRM_CFG4 0xE8 ///<
> Power
> > Management Configuration Reg 4
> > +#define B_PCH_PWRM_CFG4_U2_PHY_PG_EN BIT30
> > ///< USB2 PHY SUS Well Power Gating Enable
> > +#define B_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR
> > (0x000001FF) ///< CPU I/O VR Ramp Duration, [8:0]
> > +#define N_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR 0
> > +#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_70US 0x007
> > +#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_240US 0x018
> > +#define R_PCH_PWRM_CPU_EPOC 0xEC
> > +#define R_PCH_PWRM_VR_MISC_CTL 0x100
> > +#define B_PCH_PWRM_VR_MISC_CTL_VIDSOVEN BIT3
> > +#define R_PCH_PWRM_GPIO_CFG 0x120
> > +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW2 (BIT11 |
> BIT10 |
> > BIT9 | BIT8)
> > +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW2 8
> > +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW1 (BIT7 | BIT6 |
> > BIT5 | BIT4)
> > +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW1 4
> > +#define B_PCH_PWRM_GPIO_CFG_GPE0_DW0 (BIT3 | BIT2 |
> > BIT1 | BIT0)
> > +#define N_PCH_PWRM_GPIO_CFG_GPE0_DW0 0
> > +#define R_PCH_PWRM_PM_SYNC_MODE_C0 0xF4
> > ///< PM_SYNC Pin Mode in C0
> > +#define R_PCH_PWRM_ACPI_TMR_CTL 0xFC
> > +#define B_PCH_PWRM_ACPI_TMR_DIS BIT1
> > +#define R_PCH_PWRM_124 0x124
> > +#define R_PCH_PWRM_SLP_S0_RESIDENCY_COUNTER 0x13C
> > +#define R_PCH_PWRM_MODPHY_PM_CFG1 0x200
> > +#define R_PCH_PWRM_MODPHY_PM_CFG1_MLSXSWPGP
> 0xFFFF
> > +#define R_PCH_PWRM_MODPHY_PM_CFG2 0x204 ///<
> > ModPHY Power Management Configuration Reg 2
> > +#define B_PCH_PWRM_MODPHY_PM_CFG2_MLSPDDGE BIT30
> > ///< ModPHY Lane SUS Power Domain Dynamic Gating Enable
> > +#define B_PCH_PWRM_MODPHY_PM_CFG2_EMFC BIT29
> ///<
> > Enable ModPHY FET Control
> > +#define B_PCH_PWRM_MODPHY_PM_CFG2_EFRT (BIT28 |
> BIT27
> > | BIT26 | BIT25 | BIT24) ///< External FET Ramp Time
> > +#define N_PCH_PWRM_MODPHY_PM_CFG2_EFRT 24
> > +#define V_PCH_PWRM_MODPHY_PM_CFG2_EFRT_200US 0x0A
> > +#define B_PCH_PWRM_MODPHY_PM_CFG2_ASLOR_UFS BIT16
> > ///< UFS ModPHY SPD SPD Override
> > +#define R_PCH_PWRM_MODPHY_PM_CFG3 0x208 ///<
> > ModPHY Power Management Configuration Reg 3
> > +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_UFS
> BIT16
> > ///< UFS ModPHY SPD RT Request
> > +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XDCI
> BIT15
> > ///< xDCI ModPHY SPD RT Request
> > +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XHCI
> BIT14
> > ///< xHCI ModPHY SPD RT Request
> > +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_GBE
> BIT13
> > ///< GbE ModPHY SPD RT Request
> > +#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_SATA
> BIT12
> > ///< SATA ModPHY SPD RT Request
> > +#define R_PCH_PWRM_30C 0x30C
> > +#define R_PCH_PWRM_OBFF_CFG 0x314 ///<
> OBFF
> > Configuration
> > +#define R_PCH_PWRM_31C 0x31C
> > +#define R_PCH_PWRM_CPPM_MISC_CFG 0x320
> ///<
> > CPPM Miscellaneous Configuration
> > +#define R_PCH_PWRM_CPPM_CG_POL1A 0x324
> ///<
> > CPPM Clock Gating Policy Reg 1
> > +#define R_PCH_PWRM_CPPM_CG_POL2A 0x340
> ///<
> > CPPM Clock Gating Policy Reg 3
> > +#define R_PCH_PWRM_34C 0x34C
> > +#define R_PCH_PWRM_CPPM_CG_POL3A 0x3A8
> ///<
> > CPPM Clock Gating Policy Reg 5
> > +#define B_PCH_PWRM_CPPM_CG_POLXA_CPPM_GX_QUAL BIT30
> > ///< CPPM Shutdown Qualifier Enable for Clock Source Group X
> > +#define B_PCH_PWRM_CPPM_CG_POLXA_LTR_GX_THRESH
> > (0x000001FF) ///< LTR Threshold for Clock Source Group X, [8:0]
> > +#define R_PCH_PWRM_3D0 0x3D0
> > +#define R_PCH_PWRM_CPPM_MPG_POL1A 0x3E0
> ///<
> > CPPM ModPHY Gating Policy Reg 1A
> > +#define B_PCH_PWRM_CPPM_MPG_POL1A_CPPM_MODPHY_QUAL
> > BIT30 ///< CPPM Shutdown Qualifier Enable for ModPHY
> > +#define B_PCH_PWRM_CPPM_MPG_POL1A_LT_MODPHY_SEL
> BIT29
> > ///< ASLT/PLT Selection for ModPHY
> > +#define B_PCH_PWRM_CPPM_MPG_POL1A_LTR_MODPHY_THRESH
> > (0x000001FF) ///< LTR Threshold for ModPHY, [8:0]
> > +#define R_PCH_PWRM_CS_SD_CTL1 0x3E8 ///<
> Clock
> > Source Shutdown Control Reg 1
> > +#define B_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG (BIT22 |
> BIT21 |
> > BIT20) ///< Clock Source 5 Control Configuration
> > +#define N_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG 20
> > +#define B_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG (BIT2 | BIT1
> |
> > BIT0) ///< Clock Source 1 Control Configuration
> > +#define N_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG 0
> > +#define R_PCH_PWRM_CS_SD_CTL2 0x3EC ///<
> Clock
> > Source Shutdown Control Reg 2
> > +#define R_PCH_PWRM_HSWPGCR1 0x5D0
> > +#define B_PCH_PWRM_SW_PG_CTRL_LOCK BIT31
> > +#define B_PCH_PWRM_DFX_SW_PG_CTRL BIT0
> > +#define R_PCH_PWRM_600 0x600
> > +#define R_PCH_PWRM_604 0x604
> > +#define R_PCH_PWRM_ST_PG_FDIS_PMC_1 0x620 ///<
> Static
> > PG Related Function Disable Register 1
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ST_FDIS_LK BIT31
> ///<
> > Static Function Disable Lock (ST_FDIS_LK)
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_CAM_FDIS_PMC BIT6
> > ///< Camera Function Disable (PMC Version) (CAM_FDIS_PMC)
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ISH_FDIS_PMC BIT5
> ///<
> > SH Function Disable (PMC Version) (ISH_FDIS_PMC)
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_GBE_FDIS_PMC BIT0
> ///<
> > GBE Function Disable (PMC Version) (GBE_FDIS_PMC)
> > +#define R_PCH_PWRM_ST_PG_FDIS_PMC_2 0x624 ///<
> Static
> > Function Disable Control Register 2
> > +#define V_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_FDIS_PMC
> 0x7FF
> > ///< Static Function Disable Control Register 2
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI1_FDIS_PMC
> > BIT10 ///< SerialIo Controller GSPI Device 1 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI0_FDIS_PMC
> > BIT9 ///< SerialIo Controller GSPI Device 0 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART2_FDIS_PMC
> > BIT8 ///< SerialIo Controller UART Device 2 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART1_FDIS_PMC
> > BIT7 ///< SerialIo Controller UART Device 1 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART0_FDIS_PMC
> > BIT6 ///< SerialIo Controller UART Device 0 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C5_FDIS_PMC
> > BIT5 ///< SerialIo Controller I2C Device 5 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C4_FDIS_PMC
> > BIT4 ///< SerialIo Controller I2C Device 4 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C3_FDIS_PMC
> > BIT3 ///< SerialIo Controller I2C Device 3 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C2_FDIS_PMC
> > BIT2 ///< SerialIo Controller I2C Device 2 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C1_FDIS_PMC
> > BIT1 ///< SerialIo Controller I2C Device 1 Function Disable
> > +#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C0_FDIS_PMC
> > BIT0 ///< SerialIo Controller I2C Device 0 Function Disable
> > +#define R_PCH_PWRM_NST_PG_FDIS_1 0x628
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_SCC_FDIS_PMC BIT25
> ///<
> > SCC Function Disable. This is only avaiable in B0 onward.
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_XDCI_FDIS_PMC BIT24
> ///<
> > XDCI Function Disable. This is only avaiable in B0 onward.
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_ADSP_FDIS_PMC BIT23
> ///<
> > ADSP Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_SATA_FDIS_PMC BIT22
> ///<
> > SATA Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C3_FDIS_PMC BIT13
> ///<
> > PCIe Controller C Port 3 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C2_FDIS_PMC BIT12
> ///<
> > PCIe Controller C Port 2 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C1_FDIS_PMC BIT11
> ///<
> > PCIe Controller C Port 1 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C0_FDIS_PMC BIT10
> ///<
> > PCIe Controller C Port 0 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B3_FDIS_PMC BIT9
> ///<
> > PCIe Controller B Port 3 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B2_FDIS_PMC BIT8
> ///<
> > PCIe Controller B Port 2 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B1_FDIS_PMC BIT7
> ///<
> > PCIe Controller B Port 1 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B0_FDIS_PMC BIT6
> ///<
> > PCIe Controller B Port 0 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A3_FDIS_PMC BIT5
> ///<
> > PCIe Controller A Port 3 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A2_FDIS_PMC BIT4
> ///<
> > PCIe Controller A Port 2 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A1_FDIS_PMC BIT3
> ///<
> > PCIe Controller A Port 1 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A0_FDIS_PMC BIT2
> ///<
> > PCIe Controller A Port 0 Function Disable
> > +#define B_PCH_PWRM_NST_PG_FDIS_1_XHCI_FDIS_PMC BIT0 ///<
> > XHCI Function Disable
> > +#define R_PCH_PWRM_FUSE_DIS_RD_1 0x640 ///< Fuse
> > Disable Read 1 Register
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E3_FUSE_DIS BIT21
> ///<
> > PCIe Controller E Port 3 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E2_FUSE_DIS BIT20
> ///<
> > PCIe Controller E Port 2 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E1_FUSE_DIS BIT19
> ///<
> > PCIe Controller E Port 1 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E0_FUSE_DIS BIT18
> ///<
> > PCIe Controller E Port 0 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D3_FUSE_DIS BIT17
> ///<
> > PCIe Controller D Port 3 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D2_FUSE_DIS BIT16
> ///<
> > PCIe Controller D Port 2 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D1_FUSE_DIS BIT15
> ///<
> > PCIe Controller D Port 1 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D0_FUSE_DIS BIT14
> ///<
> > PCIe Controller D Port 0 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C3_FUSE_DIS BIT13
> ///<
> > PCIe Controller C Port 3 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C2_FUSE_DIS BIT12
> ///<
> > PCIe Controller C Port 2 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C1_FUSE_DIS BIT11
> ///<
> > PCIe Controller C Port 1 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C0_FUSE_DIS BIT10
> ///<
> > PCIe Controller C Port 0 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B3_FUSE_DIS BIT9
> ///<
> > PCIe Controller B Port 3 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B2_FUSE_DIS BIT8
> ///<
> > PCIe Controller B Port 2 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B1_FUSE_DIS BIT7
> ///<
> > PCIe Controller B Port 1 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B0_FUSE_DIS BIT6
> ///<
> > PCIe Controller B Port 0 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A3_FUSE_DIS BIT5
> ///<
> > PCIe Controller A Port 3 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A2_FUSE_DIS BIT4
> ///<
> > PCIe Controller A Port 2 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A1_FUSE_DIS BIT3
> ///<
> > PCIe Controller A Port 1 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A0_FUSE_DIS BIT2
> ///<
> > PCIe Controller A Port 0 Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_1_XHCI_FUSE_DIS BIT0 ///<
> > XHCI Fuse Disable
> > +#define R_PCH_PWRM_FUSE_DIS_RD_2 0x644 ///< Fuse
> > Disable Read 2 Register
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPC_SS_DIS BIT25 ///<
> SPC
> > Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPB_SS_DIS BIT24 ///<
> SPB
> > Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SPA_SS_DIS BIT23 ///<
> SPA
> > Fuse Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_PSTH_FUSE_SS_DIS BIT21
> ///<
> > PSTH Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_DMI_FUSE_SS_DIS BIT20
> ///<
> > DMI Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_OTG_FUSE_SS_DIS BIT19
> ///<
> > OTG Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_XHCI_SS_DIS BIT18 ///<
> > XHCI Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_FIA_FUSE_SS_DIS BIT17
> ///<
> > FIA Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_DSP_FUSE_SS_DIS BIT16
> ///<
> > DSP Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SATA_FUSE_SS_DIS BIT15
> ///<
> > SATA Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_ICC_FUSE_SS_DIS BIT14
> ///<
> > ICC Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_LPC_FUSE_SS_DIS BIT13
> ///<
> > LPC Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_RTC_FUSE_SS_DIS BIT12
> ///<
> > RTC Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_P2S_FUSE_SS_DIS BIT11
> ///<
> > P2S Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_TRSB_FUSE_SS_DIS BIT10
> ///<
> > TRSB Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SMB_FUSE_SS_DIS BIT9
> ///<
> > SMB Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_ITSS_FUSE_SS_DIS BIT8
> ///<
> > ITSS Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SERIALIO_FUSE_SS_DIS BIT6
> > ///< SerialIo Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_SCC_FUSE_SS_DIS BIT4
> ///<
> > SCC Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_P2D_FUSE_SS_DIS BIT3
> ///<
> > P2D Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_CAM_FUSE_SS_DIS BIT2
> ///<
> > Camera Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_ISH_FUSE_SS_DIS BIT1
> ///<
> > ISH Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_2_GBE_FUSE_SS_DIS BIT0
> ///<
> > GBE Fuse or Soft Strap Disable
> > +#define R_PCH_PWRM_FUSE_DIS_RD_3 0x648 ///< Static
> PG
> > Fuse and Soft Strap Disable Read Register 3
> > +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA3_FUSE_SS_DIS BIT3
> > ///< PNCRA3 Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA2_FUSE_SS_DIS BIT2
> > ///< PNCRA2 Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA1_FUSE_SS_DIS BIT1
> > ///< PNCRA1 Fuse or Soft Strap Disable
> > +#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA_FUSE_SS_DIS BIT0
> > ///< PNCRA Fuse or Soft Strap Disable
> > +
> > +
> > +#endif
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> > b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> > new file mode 100644
> > index 0000000000..a727aae927
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
> > @@ -0,0 +1,304 @@
> > +/** @file
> > + Register names for PCH SPI device.
> > +
> > + Conventions:
> > +
> > + - Prefixes:
> > + Definitions beginning with "R_" are registers
> > + Definitions beginning with "B_" are bits within registers
> > + Definitions beginning with "V_" are meaningful values within the bits
> > + Definitions beginning with "S_" are register sizes
> > + Definitions beginning with "N_" are the bit position
> > + - In general, PCH registers are denoted by "_PCH_" in register names
> > + - Registers / bits that are different between PCH generations are denoted
> by
> > + "_PCH_[generation_name]_" in register/bit names.
> > + - Registers / bits that are specific to PCH-H denoted by "_H_" in
> register/bit
> > names.
> > + Registers / bits that are specific to PCH-LP denoted by "_LP_" in
> register/bit
> > names.
> > + e.g., "_PCH_H_", "_PCH_LP_"
> > + Registers / bits names without _H_ or _LP_ apply for both H and LP.
> > + - Registers / bits that are different between SKUs are denoted by
> > "_[SKU_name]"
> > + at the end of the register/bit names
> > + - Registers / bits of new devices introduced in a PCH generation will be
> just
> > named
> > + as "_PCH_" without [generation_name] inserted.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_REGS_SPI_H_
> > +#define _PCH_REGS_SPI_H_
> > +
> > +//
> > +// SPI Registers (D31:F5)
> > +//
> > +
> > +#define PCI_DEVICE_NUMBER_PCH_SPI 31
> > +#define PCI_FUNCTION_NUMBER_PCH_SPI 5
> > +
> > +#define R_PCH_SPI_BAR0 0x10
> > +#define B_PCH_SPI_BAR0_MASK 0x0FFF
> > +
> > +#define R_PCH_SPI_BDE 0xD8
> > +#define B_PCH_SPI_BDE_F8 0x8000
> > +#define B_PCH_SPI_BDE_F0 0x4000
> > +#define B_PCH_SPI_BDE_E8 0x2000
> > +#define B_PCH_SPI_BDE_E0 0x1000
> > +#define B_PCH_SPI_BDE_D8 0x0800
> > +#define B_PCH_SPI_BDE_D0 0x0400
> > +#define B_PCH_SPI_BDE_C8 0x0200
> > +#define B_PCH_SPI_BDE_C0 0x0100
> > +#define B_PCH_SPI_BDE_LEG_F 0x0080
> > +#define B_PCH_SPI_BDE_LEG_E 0x0040
> > +#define B_PCH_SPI_BDE_70 0x0008
> > +#define B_PCH_SPI_BDE_60 0x0004
> > +#define B_PCH_SPI_BDE_50 0x0002
> > +#define B_PCH_SPI_BDE_40 0x0001
> > +
> > +#define R_PCH_SPI_BC 0xDC
> > +#define S_PCH_SPI_BC 4
> > +#define N_PCH_SPI_BC_ASE_BWP 11
> > +#define B_PCH_SPI_BC_ASE_BWP BIT11
> > +#define N_PCH_SPI_BC_ASYNC_SS 10
> > +#define B_PCH_SPI_BC_ASYNC_SS BIT10
> > +#define B_PCH_SPI_BC_OSFH BIT9 ///< OS Function Hide
> > +#define N_PCH_SPI_BC_SYNC_SS 8
> > +#define B_PCH_SPI_BC_SYNC_SS BIT8
> > +#define B_PCH_SPI_BC_BILD BIT7
> > +#define B_PCH_SPI_BC_BBS BIT6 ///< Boot BIOS strap
> > +#define N_PCH_SPI_BC_BBS 6
> > +#define V_PCH_SPI_BC_BBS_SPI 0 ///< Boot BIOS
> strapped to
> > SPI
> > +#define V_PCH_SPI_BC_BBS_LPC 1 ///< Boot BIOS
> strapped to
> > LPC
> > +#define B_PCH_SPI_BC_EISS BIT5 ///< Enable InSMM.STS
> > +#define B_PCH_SPI_BC_TSS BIT4
> > +#define B_PCH_SPI_BC_SRC (BIT3 | BIT2)
> > +#define N_PCH_SPI_BC_SRC 2
> > +#define V_PCH_SPI_BC_SRC_PREF_EN_CACHE_EN 0x02 ///<
> > Prefetching and Caching enabled
> > +#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_DIS 0x01 ///< No
> > prefetching and no caching
> > +#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_EN 0x00 ///< No
> > prefetching, but caching enabled
> > +#define B_PCH_SPI_BC_LE BIT1 ///< Lock Enable
> > +#define N_PCH_SPI_BC_BLE 1
> > +#define B_PCH_SPI_BC_WPD BIT0 ///< Write Protect
> Disable
> > +
> > +//
> > +// BIOS Flash Program Registers (based on SPI_BAR0)
> > +//
> > +#define R_PCH_SPI_BFPR 0x00 ///< BIOS Flash
> > Primary Region Register(32bits), which is RO and contains the same value
> from
> > FREG1
> > +#define B_PCH_SPI_BFPR_PRL 0x7FFF0000 ///< BIOS
> Flash
> > Primary Region Limit mask
> > +#define N_PCH_SPI_BFPR_PRL 16 ///< BIOS Flash
> > Primary Region Limit bit position
> > +#define B_PCH_SPI_BFPR_PRB 0x00007FFF ///< BIOS
> Flash
> > Primary Region Base mask
> > +#define N_PCH_SPI_BFPR_PRB 0 ///< BIOS Flash
> > Primary Region Base bit position
> > +#define R_PCH_SPI_HSFSC 0x04 ///< Hardware
> > Sequencing Flash Status and Control Register(32bits)
> > +#define B_PCH_SPI_HSFSC_FSMIE BIT31 ///< Flash
> SPI
> > SMI# Enable
> > +#define B_PCH_SPI_HSFSC_FDBC_MASK 0x3F000000 ///<
> > Flash Data Byte Count ( <= 64), Count = (Value in this field) + 1.
> > +#define N_PCH_SPI_HSFSC_FDBC 24
> > +#define B_PCH_SPI_HSFSC_CYCLE_MASK 0x001E0000 ///<
> > Flash Cycle.
> > +#define N_PCH_SPI_HSFSC_CYCLE 17
> > +#define V_PCH_SPI_HSFSC_CYCLE_READ 0 ///< Flash
> Cycle
> > Read
> > +#define V_PCH_SPI_HSFSC_CYCLE_WRITE 2 ///< Flash
> > Cycle Write
> > +#define V_PCH_SPI_HSFSC_CYCLE_4K_ERASE 3 ///<
> Flash
> > Cycle 4K Block Erase
> > +#define V_PCH_SPI_HSFSC_CYCLE_64K_ERASE 4 ///<
> Flash
> > Cycle 64K Sector Erase
> > +#define V_PCH_SPI_HSFSC_CYCLE_READ_SFDP 5 ///<
> Flash
> > Cycle Read SFDP
> > +#define V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID 6 ///<
> > Flash Cycle Read JEDEC ID
> > +#define V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS 7 ///<
> Flash
> > Cycle Write Status
> > +#define V_PCH_SPI_HSFSC_CYCLE_READ_STATUS 8 ///<
> Flash
> > Cycle Read Status
> > +#define B_PCH_SPI_HSFSC_CYCLE_FGO BIT16 ///<
> Flash
> > Cycle Go.
> > +#define B_PCH_SPI_HSFSC_FLOCKDN BIT15 ///< Flash
> > Configuration Lock-Down
> > +#define B_PCH_SPI_HSFSC_FDV BIT14 ///< Flash
> > Descriptor Valid, once valid software can use hareware sequencing regs
> > +#define B_PCH_SPI_HSFSC_FDOPSS BIT13 ///< Flash
> > Descriptor Override Pin-Strap Status
> > +#define B_PCH_SPI_HSFSC_PRR34_LOCKDN BIT12 ///<
> PRR3
> > PRR4 Lock-Down
> > +#define B_PCH_SPI_HSFSC_SAF_CE BIT8 ///< SAF
> ctype
> > error
> > +#define B_PCH_SPI_HSFSC_SAF_MODE_ACTIVE BIT7 ///<
> > Indicates flash is attached either directly to the PCH via the SPI bus or
> EC/BMC
> > +#define B_PCH_SPI_HSFSC_SAF_LE BIT6 ///< SAF
> link
> > error
> > +#define B_PCH_SPI_HSFSC_SCIP BIT5 ///< SPI cycle
> in
> > progress
> > +#define B_PCH_SPI_HSFSC_SAF_DLE BIT4 ///< SAF
> Data
> > length error
> > +#define B_PCH_SPI_HSFSC_SAF_ERROR BIT3 ///< SAF
> Error
> > +#define B_PCH_SPI_HSFSC_AEL BIT2 ///< Access
> Error
> > Log
> > +#define B_PCH_SPI_HSFSC_FCERR BIT1 ///< Flash
> Cycle
> > Error
> > +#define B_PCH_SPI_HSFSC_FDONE BIT0 ///< Flash
> Cycle
> > Done
> > +#define R_PCH_SPI_FADDR 0x08 ///< SPI Flash
> > Address
> > +#define B_PCH_SPI_FADDR_MASK 0x01FFFFFF ///< SPI
> > Flash Address Mask (0~24bit)
> > +#define R_PCH_SPI_DLOCK 0x0C ///< Discrete
> Lock
> > Bits
> > +#define B_PCH_SPI_DLOCK_PR0LOCKDN BIT8 ///<
> > PR0LOCKDN
> > +#define R_PCH_SPI_FDATA00 0x10 ///< SPI Data
> 00 (32
> > bits)
> > +#define R_PCH_SPI_FDATA01 0x14 ///< SPI Data
> 01
> > +#define R_PCH_SPI_FDATA02 0x18 ///< SPI Data
> 02
> > +#define R_PCH_SPI_FDATA03 0x1C ///< SPI Data
> 03
> > +#define R_PCH_SPI_FDATA04 0x20 ///< SPI Data
> 04
> > +#define R_PCH_SPI_FDATA05 0x24 ///< SPI Data
> 05
> > +#define R_PCH_SPI_FDATA06 0x28 ///< SPI Data
> 06
> > +#define R_PCH_SPI_FDATA07 0x2C ///< SPI Data
> 07
> > +#define R_PCH_SPI_FDATA08 0x30 ///< SPI Data
> 08
> > +#define R_PCH_SPI_FDATA09 0x34 ///< SPI Data
> 09
> > +#define R_PCH_SPI_FDATA10 0x38 ///< SPI Data
> 10
> > +#define R_PCH_SPI_FDATA11 0x3C ///< SPI Data
> 11
> > +#define R_PCH_SPI_FDATA12 0x40 ///< SPI Data
> 12
> > +#define R_PCH_SPI_FDATA13 0x44 ///< SPI Data
> 13
> > +#define R_PCH_SPI_FDATA14 0x48 ///< SPI Data
> 14
> > +#define R_PCH_SPI_FDATA15 0x4C ///< SPI Data
> 15
> > +#define R_PCH_SPI_FRAP 0x50 ///< Flash
> Region
> > Access Permisions Register
> > +#define B_PCH_SPI_FRAP_BRWA_MASK 0x0000FF00
> ///<
> > BIOS Region Write Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS;
> 2:
> > ME; 3: GbE; 4: PlatformData
> > +#define N_PCH_SPI_FRAP_BRWA 8 ///< BIOS
> Region
> > Write Access bit position
> > +#define B_PCH_SPI_FRAP_BRRA_MASK 0x000000FF ///<
> BIOS
> > Region Read Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME;
> 3:
> > GbE; 4: PlatformData
> > +#define B_PCH_SPI_FRAP_BMRAG_MASK 0x00FF0000
> ///<
> > BIOS Master Read Access Grant
> > +#define B_PCH_SPI_FRAP_BMWAG_MASK 0xFF000000
> ///<
> > BIOS Master Write Access Grant
> > +#define R_PCH_SPI_FREG0_FLASHD 0x54 ///< Flash
> > Region 0(Flash Descriptor)(32bits)
> > +#define R_PCH_SPI_FREG1_BIOS 0x58 ///< Flash
> Region
> > 1(BIOS)(32bits)
> > +#define R_PCH_SPI_FREG2_ME 0x5C ///< Flash
> Region
> > 2(ME)(32bits)
> > +#define R_PCH_SPI_FREG3_GBE 0x60 ///< Flash
> Region
> > 3(GbE)(32bits)
> > +#define R_PCH_SPI_FREG4_PLATFORM_DATA 0x64 ///<
> Flash
> > Region 4(Platform Data)(32bits)
> > +#define R_PCH_SPI_FREG5_DER 0x68 ///< Flash
> Region
> > 5(Device Expansion Region)(32bits)
> > +#define S_PCH_SPI_FREGX 4 ///< Size of Flash
> Region
> > register
> > +#define B_PCH_SPI_FREGX_LIMIT_MASK 0x7FFF0000 ///<
> > Flash Region Limit [30:16] represents [26:12], [11:0] are assumed to be
> FFFh
> > +#define N_PCH_SPI_FREGX_LIMIT 16 ///< Region
> limit
> > bit position
> > +#define N_PCH_SPI_FREGX_LIMIT_REPR 12 ///<
> Region
> > limit bit represents position
> > +#define B_PCH_SPI_FREGX_BASE_MASK 0x00007FFF ///<
> > Flash Region Base, [14:0] represents [26:12]
> > +#define N_PCH_SPI_FREGX_BASE 0 ///< Region
> base bit
> > position
> > +#define N_PCH_SPI_FREGX_BASE_REPR 12 ///<
> Region
> > base bit represents position
> > +#define R_PCH_SPI_PR0 0x84 ///< Protected
> Region 0
> > Register
> > +#define R_PCH_SPI_PR1 0x88 ///< Protected
> Region 1
> > Register
> > +#define R_PCH_SPI_PR2 0x8C ///< Protected
> Region 2
> > Register
> > +#define R_PCH_SPI_PR3 0x90 ///< Protected
> Region 3
> > Register
> > +#define R_PCH_SPI_PR4 0x94 ///< Protected
> Region 4
> > Register
> > +#define S_PCH_SPI_PRX 4 ///< Protected
> Region X
> > Register size
> > +#define B_PCH_SPI_PRX_WPE BIT31 ///< Write
> > Protection Enable
> > +#define B_PCH_SPI_PRX_PRL_MASK 0x7FFF0000 ///<
> > Protected Range Limit Mask, [30:16] here represents upper limit of address
> > [26:12]
> > +#define N_PCH_SPI_PRX_PRL 16 ///< Protected
> Range
> > Limit bit position
> > +#define B_PCH_SPI_PRX_RPE BIT15 ///< Read
> > Protection Enable
> > +#define B_PCH_SPI_PRX_PRB_MASK 0x00007FFF ///<
> > Protected Range Base Mask, [14:0] here represents base limit of address
> [26:12]
> > +#define N_PCH_SPI_PRX_PRB 0 ///< Protected
> Range
> > Base bit position
> > +#define R_PCH_SPI_SFRAP 0xB0 ///< Secondary
> Flash
> > Regions Access Permisions Register
> > +#define R_PCH_SPI_FDOC 0xB4 ///< Flash
> Descriptor
> > Observability Control Register(32 bits)
> > +#define B_PCH_SPI_FDOC_FDSS_MASK (BIT14 | BIT13 | BIT12)
> ///<
> > Flash Descritor Section Select
> > +#define V_PCH_SPI_FDOC_FDSS_FSDM 0x0000 ///<
> Flash
> > Signature and Descriptor Map
> > +#define V_PCH_SPI_FDOC_FDSS_COMP 0x1000 ///<
> > Component
> > +#define V_PCH_SPI_FDOC_FDSS_REGN 0x2000 ///<
> Region
> > +#define V_PCH_SPI_FDOC_FDSS_MSTR 0x3000 ///<
> Master
> > +#define V_PCH_SPI_FDOC_FDSS_PCHS 0x4000 ///<
> PCH
> > soft straps
> > +#define V_PCH_SPI_FDOC_FDSS_SFDP 0x5000 ///<
> SFDP
> > Parameter Table
> > +#define B_PCH_SPI_FDOC_FDSI_MASK 0x0FFC ///<
> Flash
> > Descriptor Section Index
> > +#define R_PCH_SPI_FDOD 0xB8 ///< Flash
> Descriptor
> > Observability Data Register(32 bits)
> > +#define R_PCH_SPI_SFDP0_VSCC0 0xC4 ///< Vendor
> > Specific Component Capabilities Register(32 bits)
> > +#define B_PCH_SPI_SFDPX_VSCCX_CPPTV BIT31 ///<
> > Component Property Parameter Table Valid
> > +#define B_PCH_SPI_SFDP0_VSCC0_VCL BIT30 ///<
> Vendor
> > Component Lock
> > +#define B_PCH_SPI_SFDPX_VSCCX_EO_64K BIT29 ///<
> 64k
> > Erase valid (EO_64k_valid)
> > +#define B_PCH_SPI_SFDPX_VSCCX_EO_4K BIT28 ///< 4k
> > Erase valid (EO_4k_valid)
> > +#define B_PCH_SPI_SFDPX_VSCCX_RPMC BIT27 ///<
> RPMC
> > Supported
> > +#define B_PCH_SPI_SFDPX_VSCCX_DPD BIT26 ///<
> Deep
> > Powerdown Supported
> > +#define B_PCH_SPI_SFDPX_VSCCX_SUSRES BIT25 ///<
> > Suspend/Resume Supported
> > +#define B_PCH_SPI_SFDPX_VSCCX_SOFTRES BIT24 ///<
> Soft
> > Reset Supported
> > +#define B_PCH_SPI_SFDPX_VSCCX_64k_EO_MASK 0x00FF0000
> > ///< 64k Erase Opcode (EO_64k)
> > +#define B_PCH_SPI_SFDPX_VSCCX_4k_EO_MASK 0x0000FF00
> > ///< 4k Erase Opcode (EO_4k)
> > +#define B_PCH_SPI_SFDPX_VSCCX_QER (BIT7 | BIT6 | BIT5)
> ///<
> > Quad Enable Requirements
> > +#define B_PCH_SPI_SFDPX_VSCCX_WEWS BIT4 ///<
> Write
> > Enable on Write Status
> > +#define B_PCH_SPI_SFDPX_VSCCX_WSR BIT3 ///<
> Write
> > Status Required
> > +#define B_PCH_SPI_SFDPX_VSCCX_WG_64B BIT2 ///<
> Write
> > Granularity, 0: 1 Byte; 1: 64 Bytes
> > +#define R_PCH_SPI_SFDP1_VSCC1 0xC8 ///< Vendor
> > Specific Component Capabilities Register(32 bits)
> > +#define R_PCH_SPI_PINTX 0xCC ///< Parameter
> Table
> > Index
> > +#define N_PCH_SPI_PINTX_SPT 14
> > +#define V_PCH_SPI_PINTX_SPT_CPT0 0x0 ///<
> Component
> > 0 Property Parameter Table
> > +#define V_PCH_SPI_PINTX_SPT_CPT1 0x1 ///<
> Component
> > 1 Property Parameter Table
> > +#define N_PCH_SPI_PINTX_HORD 12
> > +#define V_PCH_SPI_PINTX_HORD_SFDP 0x0 ///< SFDP
> > Header
> > +#define V_PCH_SPI_PINTX_HORD_PT 0x1 ///<
> Parameter
> > Table Header
> > +#define V_PCH_SPI_PINTX_HORD_DATA 0x2 ///< Data
> > +#define R_PCH_SPI_PTDATA 0xD0 ///<
> Parameter
> > Table Data
> > +#define R_PCH_SPI_SBRS 0xD4 ///< SPI Bus
> Requester
> > Status
> > +#define R_PCH_SPI_SSML 0xF0 ///< Set Strap
> Msg
> > Lock
> > +#define B_PCH_SPI_SSML_SSL BIT0 ///< Set_Strap
> Lock
> > +#define R_PCH_SPI_SSMC 0xF4 ///< Set Strap
> Msg
> > Control
> > +#define B_PCH_SPI_SSMC_SSMS BIT0 ///<
> Set_Strap
> > Mux Select
> > +#define R_PCH_SPI_SSMD 0xF8 ///< Set Strap
> Msg
> > Data
> > +//
> > +// @todo Follow up with EDS owner if it should be 3FFF or FFFF.
> > +//
> > +#define B_PCH_SPI_SRD_SSD 0x0000FFFF ///<
> Set_Strap
> > Data
> > +//
> > +// Flash Descriptor Base Address Region (FDBAR) from Flash Region 0
> > +//
> > +#define R_PCH_SPI_FDBAR_FLVALSIG 0x00 ///< Flash
> Valid
> > Signature
> > +#define V_PCH_SPI_FDBAR_FLVALSIG 0x0FF0A55A
> > +#define R_PCH_SPI_FDBAR_FLASH_MAP0 0x04
> > +#define B_PCH_SPI_FDBAR_FCBA 0x000000FF ///<
> Flash
> > Component Base Address
> > +#define B_PCH_SPI_FDBAR_NC 0x00000300 ///<
> Number
> > Of Components
> > +#define N_PCH_SPI_FDBAR_NC 8 ///< Number
> Of
> > Components
> > +#define V_PCH_SPI_FDBAR_NC_1 0x00000000
> > +#define V_PCH_SPI_FDBAR_NC_2 0x00000100
> > +#define B_PCH_SPI_FDBAR_FRBA 0x00FF0000 ///<
> Flash
> > Region Base Address
> > +#define B_PCH_SPI_FDBAR_NR 0x07000000 ///<
> Number
> > Of Regions
> > +#define R_PCH_SPI_FDBAR_FLASH_MAP1 0x08
> > +#define B_PCH_SPI_FDBAR_FMBA 0x000000FF ///<
> Flash
> > Master Base Address
> > +#define B_PCH_SPI_FDBAR_NM 0x00000700 ///<
> Number
> > Of Masters
> > +#define B_PCH_SPI_FDBAR_FPSBA 0x00FF0000 ///<
> PCH
> > Strap Base Address, [23:16] represents [11:4]
> > +#define N_PCH_SPI_FDBAR_FPSBA 16 ///< PCH
> Strap
> > base Address bit position
> > +#define N_PCH_SPI_FDBAR_FPSBA_REPR 4 ///< PCH
> Strap
> > base Address bit represents position
> > +#define B_PCH_SPI_FDBAR_PCHSL 0xFF000000 ///<
> PCH
> > Strap Length, [31:24] represents number of Dwords
> > +#define N_PCH_SPI_FDBAR_PCHSL 24 ///< PCH
> Strap
> > Length bit position
> > +#define R_PCH_SPI_FDBAR_FLASH_MAP2 0x0C
> > +#define B_PCH_SPI_FDBAR_FCPUSBA 0x000000FF ///<
> CPU
> > Strap Base Address, [7:0] represents [11:4]
> > +#define N_PCH_SPI_FDBAR_FCPUSBA 0 ///< CPU
> Strap
> > Base Address bit position
> > +#define N_PCH_SPI_FDBAR_FCPUSBA_REPR 4 ///<
> CPU
> > Strap Base Address bit represents position
> > +#define B_PCH_SPI_FDBAR_CPUSL 0x0000FF00 ///<
> CPU
> > Strap Length, [15:8] represents number of Dwords
> > +#define N_PCH_SPI_FDBAR_CPUSL 8 ///< CPU
> Strap
> > Length bit position
> > +//
> > +// Flash Component Base Address (FCBA) from Flash Region 0
> > +//
> > +#define R_PCH_SPI_FCBA_FLCOMP 0x00 ///< Flash
> > Components Register
> > +#define B_PCH_SPI_FLCOMP_RIDS_FREQ (BIT29 | BIT28 | BIT27)
> ///<
> > Read ID and Read Status Clock Frequency
> > +#define B_PCH_SPI_FLCOMP_WE_FREQ (BIT26 | BIT25 | BIT24)
> ///<
> > Write and Erase Clock Frequency
> > +#define B_PCH_SPI_FLCOMP_FRCF_FREQ (BIT23 | BIT22 | BIT21)
> ///<
> > Fast Read Clock Frequency
> > +#define B_PCH_SPI_FLCOMP_FR_SUP BIT20 ///< Fast
> Read
> > Support.
> > +#define B_PCH_SPI_FLCOMP_RC_FREQ (BIT19 | BIT18 | BIT17)
> ///<
> > Read Clock Frequency.
> > +#define V_PCH_SPI_FLCOMP_FREQ_48MHZ 0x02
> > +#define V_PCH_SPI_FLCOMP_FREQ_30MHZ 0x04
> > +#define V_PCH_SPI_FLCOMP_FREQ_17MHZ 0x06
> > +#define B_PCH_SPI_FLCOMP_COMP1_MASK 0xF0 ///<
> Flash
> > Component 1 Size MASK
> > +#define N_PCH_SPI_FLCOMP_COMP1 4 ///< Flash
> > Component 1 Size bit position
> > +#define B_PCH_SPI_FLCOMP_COMP0_MASK 0x0F ///<
> Flash
> > Component 0 Size MASK
> > +#define V_PCH_SPI_FLCOMP_COMP_512KB 0x80000
> > +//
> > +// Descriptor Upper Map Section from Flash Region 0
> > +//
> > +#define R_PCH_SPI_FLASH_UMAP1 0xEFC ///< Flash
> > Upper Map 1
> > +#define B_PCH_SPI_FLASH_UMAP1_VTBA 0x000000FF
> ///<
> > VSCC Table Base Address
> > +#define B_PCH_SPI_FLASH_UMAP1_VTL 0x0000FF00 ///<
> > VSCC Table Length
> > +
> > +#define R_PCH_SPI_VTBA_JID0 0x00 ///< JEDEC-ID
> 0
> > Register
> > +#define S_PCH_SPI_VTBA_JID0 0x04
> > +#define B_PCH_SPI_VTBA_JID0_VID 0x000000FF
> > +#define B_PCH_SPI_VTBA_JID0_DID0 0x0000FF00
> > +#define B_PCH_SPI_VTBA_JID0_DID1 0x00FF0000
> > +#define N_PCH_SPI_VTBA_JID0_DID0 0x08
> > +#define N_PCH_SPI_VTBA_JID0_DID1 0x10
> > +#define R_PCH_SPI_VTBA_VSCC0 0x04
> > +#define S_PCH_SPI_VTBA_VSCC0 0x04
> > +
> > +
> > +//
> > +// SPI Private Configuration Space Registers
> > +//
> > +#define R_PCH_PCR_SPI_CLK_CTL 0xC004
> > +#define R_PCH_PCR_SPI_PWR_CTL 0xC008
> > +#define R_PCH_PCR_SPI_ESPI_SOFTSTRAPS 0xC210
> > +#define B_PCH_PCR_SPI_ESPI_SOFTSTRAPS_SLAVE BIT12
> > +
> > +//
> > +// MMP0
> > +//
> > +#define R_PCH_SPI_STRP_MMP0 0xC4 ///< MMP0 Soft strap
> offset
> > +#define B_PCH_SPI_STRP_MMP0 0x10 ///< MMP0 Soft strap bit
> > +
> > +
> > +#define R_PCH_SPI_STRP_SFDP 0xF0 ///< PCH Soft Strap SFDP
> > +#define B_PCH_SPI_STRP_SFDP_QIORE BIT3 ///< Quad IO Read
> Enable
> > +#define B_PCH_SPI_STRP_SFDP_QORE BIT2 ///< Quad Output
> Read
> > Enable
> > +#define B_PCH_SPI_STRP_SFDP_DIORE BIT1 ///< Dual IO Read
> Enable
> > +#define B_PCH_SPI_STRP_SFDP_DORE BIT0 ///< Dual Output Read
> > Enable
> > +
> > +//
> > +// Descriptor Record 0
> > +//
> > +#define R_PCH_SPI_STRP_DSCR_0 0x00 ///< PCH Soft Strap 0
> > +#define B_PCH_SPI_STRP_DSCR_0_PTT_SUPP BIT22 ///< PTT
> Supported
> > +
> > +#endif
> > diff --git
> > a/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> > b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> > new file mode 100644
> > index 0000000000..5bdec96197
> > --- /dev/null
> > +++
> > b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
> > @@ -0,0 +1,396 @@
> > +/** @file
> > + Header file for the PCH SPI Common Driver.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_SPI_COMMON_LIB_H_
> > +#define _PCH_SPI_COMMON_LIB_H_
> > +
> > +//
> > +// Maximum time allowed while waiting the SPI cycle to complete
> > +// Wait Time = 6 seconds = 6000000 microseconds
> > +// Wait Period = 10 microseconds
> > +//
> > +#define SPI_WAIT_TIME 6000000 ///< Wait Time = 6 seconds =
> 6000000
> > microseconds
> > +#define SPI_WAIT_PERIOD 10 ///< Wait Period = 10 microseconds
> > +
> > +///
> > +/// Flash cycle Type
> > +///
> > +typedef enum {
> > + FlashCycleRead,
> > + FlashCycleWrite,
> > + FlashCycleErase,
> > + FlashCycleReadSfdp,
> > + FlashCycleReadJedecId,
> > + FlashCycleWriteStatus,
> > + FlashCycleReadStatus,
> > + FlashCycleMax
> > +} FLASH_CYCLE_TYPE;
> > +
> > +///
> > +/// Flash Component Number
> > +///
> > +typedef enum {
> > + FlashComponent0,
> > + FlashComponent1,
> > + FlashComponentMax
> > +} FLASH_COMPONENT_NUM;
> > +
> > +///
> > +/// Private data structure definitions for the driver
> > +///
> > +#define PCH_SPI_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('P', 'S', 'P',
> 'I')
> > +
> > +typedef struct {
> > + UINT32 Signature;
> > + EFI_HANDLE Handle;
> > + EFI_SPI_PROTOCOL SpiProtocol;
> > + UINT16 PchAcpiBase;
> > + UINTN PchSpiBase;
> > + UINT16 ReadPermission;
> > + UINT16 WritePermission;
> > + UINT32 SfdpVscc0Value;
> > + UINT32 SfdpVscc1Value;
> > + UINT16 PchStrapBaseAddr;
> > + UINT16 PchStrapSize;
> > + UINT16 CpuStrapBaseAddr;
> > + UINT16 CpuStrapSize;
> > + UINT8 NumberOfComponents;
> > + UINT32 Component1StartAddr;
> > + UINT32 TotalFlashSize;
> > +} SPI_INSTANCE;
> > +
> > +#define SPI_INSTANCE_FROM_SPIPROTOCOL(a) CR (a, SPI_INSTANCE,
> > SpiProtocol, PCH_SPI_PRIVATE_DATA_SIGNATURE)
> > +
> > +//
> > +// Function prototypes used by the SPI protocol.
> > +//
> > +
> > +/**
> > + Initialize an SPI protocol instance.
> > +
> > + @param[in] SpiInstance Pointer to SpiInstance to initialize
> > +
> > + @retval EFI_SUCCESS The protocol instance was properly
> initialized
> > + @exception EFI_UNSUPPORTED The PCH is not supported by this
> module
> > +**/
> > +EFI_STATUS
> > +SpiProtocolConstructor (
> > + IN SPI_INSTANCE *SpiInstance
> > + );
> > +
> > +/**
> > + This function is a hook for Spi to disable BIOS Write Protect
> > +
> > + @retval EFI_SUCCESS The protocol instance was properly
> initialized
> > + @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in
> > SMM phase
> > +
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +DisableBiosWriteProtect (
> > + VOID
> > + );
> > +
> > +/**
> > + This function is a hook for Spi to enable BIOS Write Protect
> > +
> > +
> > +**/
> > +VOID
> > +EFIAPI
> > +EnableBiosWriteProtect (
> > + VOID
> > + );
> > +
> > +/**
> > + Acquire pch spi mmio address.
> > +
> > + @param[in] SpiInstance Pointer to SpiInstance to initialize
> > +
> > + @retval PchSpiBar0 return SPI MMIO address
> > +**/
> > +UINTN
> > +AcquireSpiBar0 (
> > + IN SPI_INSTANCE *SpiInstance
> > + );
> > +
> > +/**
> > + Release pch spi mmio address.
> > +
> > + @param[in] SpiInstance Pointer to SpiInstance to initialize
> > +
> > + @retval None
> > +**/
> > +VOID
> > +ReleaseSpiBar0 (
> > + IN SPI_INSTANCE *SpiInstance
> > + );
> > +
> > +/**
> > + Read data from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[out] Buffer The Pointer to caller-allocated buffer
> containing
> > the dada received.
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashRead (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Write data to the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[in] Buffer Pointer to caller-allocated buffer containing
> the
> > data sent during the SPI cycle.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashWrite (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + IN UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Erase some area on the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for flash cycle
> which is
> > listed in the Descriptor.
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashErase (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount
> > + );
> > +
> > +/**
> > + Read SFDP data from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ComponentNumber The Componen Number for chip
> select
> > + @param[in] Address The starting byte address for SFDP data read.
> > + @param[in] ByteCount Number of bytes in SFDP data portion of
> the SPI
> > cycle
> > + @param[out] SfdpData The Pointer to caller-allocated buffer
> containing
> > the SFDP data received
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashReadSfdp (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT8 ComponentNumber,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *SfdpData
> > + );
> > +
> > +/**
> > + Read Jedec Id from the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ComponentNumber The Componen Number for chip
> select
> > + @param[in] ByteCount Number of bytes in JedecId data portion of
> the
> > SPI cycle, the data size is 3 typically
> > + @param[out] JedecId The Pointer to caller-allocated buffer
> containing
> > JEDEC ID received
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashReadJedecId (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT8 ComponentNumber,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *JedecId
> > + );
> > +
> > +/**
> > + Write the status register in the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ByteCount Number of bytes in Status data portion of
> the
> > SPI cycle, the data size is 1 typically
> > + @param[in] StatusValue The Pointer to caller-allocated buffer
> containing
> > the value of Status register writing
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashWriteStatus (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 ByteCount,
> > + IN UINT8 *StatusValue
> > + );
> > +
> > +/**
> > + Read status register in the flash part.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] ByteCount Number of bytes in Status data portion of
> the
> > SPI cycle, the data size is 1 typically
> > + @param[out] StatusValue The Pointer to caller-allocated buffer
> > containing the value of Status register received.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolFlashReadStatus (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 ByteCount,
> > + OUT UINT8 *StatusValue
> > + );
> > +
> > +/**
> > + Get the SPI region base and size, based on the enum type
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] FlashRegionType The Flash Region type for for the base
> > address which is listed in the Descriptor.
> > + @param[out] BaseAddress The Flash Linear Address for the Region
> 'n'
> > Base
> > + @param[out] RegionSize The size for the Region 'n'
> > +
> > + @retval EFI_SUCCESS Read success
> > + @retval EFI_INVALID_PARAMETER Invalid region type given
> > + @retval EFI_DEVICE_ERROR The region is not used
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolGetRegionAddress (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + OUT UINT32 *BaseAddress,
> > + OUT UINT32 *RegionSize
> > + );
> > +
> > +/**
> > + Read PCH Soft Strap Values
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
> > + @param[in] ByteCount Number of bytes in SoftStrap data portion
> of
> > the SPI cycle
> > + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> > containing PCH Soft Strap Value.
> > + If the value of ByteCount is 0, the data type of
> > SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> > Length
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolReadPchSoftStrap (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 SoftStrapAddr,
> > + IN UINT32 ByteCount,
> > + OUT VOID *SoftStrapValue
> > + );
> > +
> > +/**
> > + Read CPU Soft Strap Values
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SoftStrapAddr CPU Soft Strap address offset from
> FCPUSBA.
> > + @param[in] ByteCount Number of bytes in SoftStrap data portion
> of
> > the SPI cycle.
> > + @param[out] SoftStrapValue The Pointer to caller-allocated buffer
> > containing CPU Soft Strap Value.
> > + If the value of ByteCount is 0, the data type of
> > SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap
> > Length
> > + It is the caller's responsibility to make sure Buffer is
> large
> > enough for the total number of bytes read.
> > +
> > + @retval EFI_SUCCESS Command succeed.
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > + @retval EFI_DEVICE_ERROR Device error, command aborts
> abnormally.
> > +**/
> > +EFI_STATUS
> > +EFIAPI
> > +SpiProtocolReadCpuSoftStrap (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINT32 SoftStrapAddr,
> > + IN UINT32 ByteCount,
> > + OUT VOID *SoftStrapValue
> > + );
> > +
> > +/**
> > + This function sends the programmed SPI command to the slave device.
> > +
> > + @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
> > + @param[in] SpiRegionType The SPI Region type for flash cycle which
> is
> > listed in the Descriptor
> > + @param[in] FlashCycleType The Flash SPI cycle type list in HSFC
> (Hardware
> > Sequencing Flash Control Register) register
> > + @param[in] Address The Flash Linear Address must fall within a
> region
> > for which BIOS has access permissions.
> > + @param[in] ByteCount Number of bytes in the data portion of the
> SPI
> > cycle.
> > + @param[in,out] Buffer Pointer to caller-allocated buffer containing
> the
> > dada received or sent during the SPI cycle.
> > +
> > + @retval EFI_SUCCESS SPI command completes successfully.
> > + @retval EFI_DEVICE_ERROR Device error, the command aborts
> > abnormally.
> > + @retval EFI_ACCESS_DENIED Some unrecognized command
> encountered
> > in hardware sequencing mode
> > + @retval EFI_INVALID_PARAMETER The parameters specified are not
> valid.
> > +**/
> > +EFI_STATUS
> > +SendSpiCmd (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN FLASH_REGION_TYPE FlashRegionType,
> > + IN FLASH_CYCLE_TYPE FlashCycleType,
> > + IN UINT32 Address,
> > + IN UINT32 ByteCount,
> > + IN OUT UINT8 *Buffer
> > + );
> > +
> > +/**
> > + Wait execution cycle to complete on the SPI interface.
> > +
> > + @param[in] This The SPI protocol instance
> > + @param[in] PchSpiBar0 Spi MMIO base address
> > + @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error
> check
> > +
> > + @retval TRUE SPI cycle completed on the interface.
> > + @retval FALSE Time out while waiting the SPI cycle to
> complete.
> > + It's not safe to program the next command on the SPI
> > interface.
> > +**/
> > +BOOLEAN
> > +WaitForSpiCycleComplete (
> > + IN EFI_SPI_PROTOCOL *This,
> > + IN UINTN PchSpiBar0,
> > + IN BOOLEAN ErrorCheck
> > + );
> > +
> > +#endif
> > diff --git
> > a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> > b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> > new file mode 100644
> > index 0000000000..4af462da47
> > --- /dev/null
> > +++
> b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
> > @@ -0,0 +1,34 @@
> > +## @file
> > +# Library instance for ResetSystem library class for OVMF
> > +#
> > +# Copyright (c) 2006 - 2018 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[Defines]
> > + INF_VERSION = 0x00010005
> > + BASE_NAME = ResetSystemLib
> > + FILE_GUID = 66564872-21d4-4d2a-a68b-1e844f980820
> > + MODULE_TYPE = BASE
> > + VERSION_STRING = 1.0
> > + LIBRARY_CLASS = ResetSystemLib
> > +
> > +#
> > +# The following information is for reference only and not required by the
> build
> > tools.
> > +#
> > +# VALID_ARCHITECTURES = IA32 X64
> > +#
> > +
> > +[Sources]
> > + ResetSystemLib.c
> > +
> > +[Packages]
> > + MdePkg/MdePkg.dec
> > + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> > +
> > +[LibraryClasses]
> > + DebugLib
> > + IoLib
> > + TimerLib
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlas
> h
> > CommonLib.inf
> >
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFla
> sh
> > CommonLib.inf
> > new file mode 100644
> > index 0000000000..b5c97f1930
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFla
> sh
> > CommonLib.inf
> > @@ -0,0 +1,52 @@
> > +## @file
> > +# SMM Library instance of Spi Flash Common Library Class
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[Defines]
> > + INF_VERSION = 0x00010017
> > + BASE_NAME = SmmSpiFlashCommonLib
> > + FILE_GUID = 9632D96E-E849-4217-9217-DC500B8AAE47
> > + VERSION_STRING = 1.0
> > + MODULE_TYPE = DXE_SMM_DRIVER
> > + LIBRARY_CLASS = SpiFlashCommonLib|DXE_SMM_DRIVER
> > + CONSTRUCTOR = SmmSpiFlashCommonLibConstructor
> > +#
> > +# The following information is for reference only and not required by the
> build
> > tools.
> > +#
> > +# VALID_ARCHITECTURES = IA32 X64
> > +#
> > +
> > +[LibraryClasses]
> > + PciLib
> > + IoLib
> > + MemoryAllocationLib
> > + BaseLib
> > + UefiLib
> > + SmmServicesTableLib
> > + BaseMemoryLib
> > + DebugLib
> > +
> > +[Packages]
> > + MdePkg/MdePkg.dec
> > + SimicsICH10Pkg/ICH10Pkg.dec
> > + MinPlatformPkg/MinPlatformPkg.dec
> > +
> > +
> > +[Pcd]
> > + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ##
> CONSUMES
> > + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
> > +
> > +[Sources]
> > + SpiFlashCommonSmmLib.c
> > + SpiFlashCommon.c
> > +
> > +[Protocols]
> > + gEfiSmmSpiProtocolGuid ## CONSUMES
> > +
> > +[Depex.X64.DXE_SMM_DRIVER]
> > + gEfiSmmSpiProtocolGuid
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePc
> h
> > SpiCommonLib.inf
> >
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BaseP
> ch
> > SpiCommonLib.inf
> > new file mode 100644
> > index 0000000000..11c832e487
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BaseP
> ch
> > SpiCommonLib.inf
> > @@ -0,0 +1,33 @@
> > +## @file
> > +# Component description file for the PchSpiCommonLib
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[Defines]
> > + INF_VERSION = 0x00010005
> > + BASE_NAME = BasePchSpiCommonLib
> > + FILE_GUID = A37CB67E-7D85-45B3-B07E-BF65BDB603E8
> > + MODULE_TYPE = BASE
> > + VERSION_STRING = 1.0
> > + LIBRARY_CLASS = PchSpiCommonLib
> > +
> > +[Sources]
> > + SpiCommon.c
> > +
> > +[Packages]
> > + MdePkg/MdePkg.dec
> > + SimicsICH10Pkg/ICH10Pkg.dec
> > + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> > + MinPlatformPkg/MinPlatformPkg.dec
> > +
> > +[LibraryClasses]
> > + IoLib
> > + DebugLib
> > +
> > +[Pcd]
> > + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ##
> CONSUMES
> > + gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> > b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> > new file mode 100644
> > index 0000000000..a2d006ee35
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
> > @@ -0,0 +1,12 @@
> > +## @file
> > +# Component description file for the SkyLake SiPkg DXE libraries.
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[LibraryClasses.common]
> > + ResetSystemLib|$(PCH_PKG)/Library/ResetSystemLib/ResetSystemLib.inf
> > +
> >
> PchSpiCommonLib|$(PCH_PKG)/LibraryPrivate/BasePchSpiCommonLib/BaseP
> c
> > hSpiCommonLib.inf
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> > b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> > new file mode 100644
> > index 0000000000..78eca21a43
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
> > @@ -0,0 +1,9 @@
> > +## @file
> > +# Component description file for the SkyLake SiPkg DXE drivers.
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> > b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> > new file mode 100644
> > index 0000000000..2d3a127c20
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
> > @@ -0,0 +1,9 @@
> > +## @file
> > +# Component description file for the SkyLake SiPkg PEI drivers.
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> > b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> > new file mode 100644
> > index 0000000000..d079c593d9
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
> > @@ -0,0 +1,13 @@
> > +## @file
> > +# Component description file for the SkyLake SiPkg DXE drivers.
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +!if gMinPlatformPkgTokenSpaceGuid.PcdBootToShellOnly == FALSE
> > + INF $(PCH_PKG)/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
> > + INF $(PCH_PKG)/Spi/Smm/PchSpiSmm.inf
> > +!endif
> > diff --git
> >
> a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.i
> nf
> >
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.i
> nf
> > new file mode 100644
> > index 0000000000..e23dd9f2fe
> > --- /dev/null
> > +++
> >
> b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.i
> nf
> > @@ -0,0 +1,59 @@
> > +## @file
> > +# A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
> > +# EFI_SMM_CONTROL2_PROTOCOL.
> > +#
> > +# We expect the PEI phase to have covered the following:
> > +# - ensure that the underlying QEMU machine type be X58
> > +# (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
> > +# - ensure that the ACPI PM IO space be configured
> > +# (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
> > +#
> > +# Our own entry point is responsible for confirming the SMI feature and for
> > +# configuring it.
> > +#
> > +# Copyright (C) 2013, 2015, Red Hat, Inc.
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[Defines]
> > + INF_VERSION = 0x00010005
> > + BASE_NAME = SmmControl2Dxe
> > + FILE_GUID = 1206F7CA-A475-4624-A83E-E6FC9BB38E49
> > + MODULE_TYPE = DXE_RUNTIME_DRIVER
> > + VERSION_STRING = 1.0
> > + PI_SPECIFICATION_VERSION = 0x00010400
> > + ENTRY_POINT = SmmControl2DxeEntryPoint
> > +
> > +#
> > +# The following information is for reference only and not required by the
> build
> > tools.
> > +#
> > +# VALID_ARCHITECTURES = IA32 X64
> > +#
> > +
> > +[Sources]
> > + SmmControl2Dxe.c
> > +
> > +[Packages]
> > + MdePkg/MdePkg.dec
> > + SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
> > +
> > +[LibraryClasses]
> > + BaseLib
> > + DebugLib
> > + IoLib
> > + PcdLib
> > + PciLib
> > + UefiBootServicesTableLib
> > + UefiDriverEntryPoint
> > +
> > +[Protocols]
> > + gEfiS3SaveStateProtocolGuid ## SOMETIMES_CONSUMES
> > + gEfiSmmControl2ProtocolGuid ## PRODUCES
> > +
> > +[FeaturePcd]
> > + gSimicsX58PkgTokenSpaceGuid.PcdSmmSmramRequire
> > +
> > +[Depex]
> > + TRUE
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> > b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> > new file mode 100644
> > index 0000000000..f7fdd3abbe
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
> > @@ -0,0 +1,23 @@
> > +/** @file
> > + Header file for the PCH SPI SMM Driver.
> > +
> > + Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +
> > + SPDX-License-Identifier: BSD-2-Clause-Patent
> > +**/
> > +
> > +#ifndef _PCH_SPI_H_
> > +#define _PCH_SPI_H_
> > +
> > +#include <Library/IoLib.h>
> > +#include <Library/DebugLib.h>
> > +#include <Library/UefiDriverEntryPoint.h>
> > +#include <Library/UefiBootServicesTableLib.h>
> > +#include <Library/BaseLib.h>
> > +#include <Library/BaseMemoryLib.h>
> > +#include <Library/SmmServicesTableLib.h>
> > +#include <PchAccess.h>
> > +#include <Protocol/Spi.h>
> > +#include <IncludePrivate/Library/PchSpiCommonLib.h>
> > +
> > +#endif
> > diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> > b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> > new file mode 100644
> > index 0000000000..265af00ac0
> > --- /dev/null
> > +++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
> > @@ -0,0 +1,44 @@
> > +## @file
> > +# Component description file for the SPI SMM driver.
> > +#
> > +# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
> > +#
> > +# SPDX-License-Identifier: BSD-2-Clause-Patent
> > +#
> > +##
> > +
> > +[Defines]
> > + INF_VERSION = 0x00010017
> > + BASE_NAME = PchSpiSmm
> > + FILE_GUID = 27F4917B-A707-4aad-9676-26DF168CBF0D
> > + VERSION_STRING = 1.0
> > + MODULE_TYPE = DXE_SMM_DRIVER
> > + PI_SPECIFICATION_VERSION = 1.10
> > + ENTRY_POINT = InstallPchSpi
> > +
> > +
> > + [LibraryClasses]
> > + DebugLib
> > + IoLib
> > + UefiDriverEntryPoint
> > + UefiBootServicesTableLib
> > + BaseLib
> > + SmmServicesTableLib
> > + PchSpiCommonLib
> > +
> > +[Packages]
> > + MdePkg/MdePkg.dec
> > + SimicsICH10Pkg/ICH10Pkg.dec
> > +
> > +[Sources]
> > + PchSpi.h
> > + PchSpi.c
> > +
> > +
> > +[Protocols]
> > + gEfiSmmSpiProtocolGuid # PRODUCES #SERVER_BIOS
> > +
> > +
> > +[Depex]
> > + gEfiSmmBase2ProtocolGuid #This is for SmmServicesTableLib
> > + AND gEfiSmmCpuProtocolGuid # This is for
> > CpuSmmDisableBiosWriteProtect()
> > --
> > 2.16.2.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#46380): https://edk2.groups.io/g/devel/message/46380
Mute This Topic: https://groups.io/mt/32816096/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
Hi David,
Here are my comments:
1. All of the copyright years need to be updated to 2019.
2. Please remove " Contributed-under: TianoCore Contribution Agreement 1.0" from your commit message as it is no longer needed.
3. Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c - I am surprised to see the DisableBiosWriteProtect() and EnableBiosWriteProtect() functions empty. Does Simics not emulate the EISS and BC registers?
4. Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf - line 43 - Remove trailing whitespace
Other than that, looks good! Please send an updated patch.
Thanks,
Nate
-----Original Message-----
From: Wei, David Y
Sent: Friday, August 9, 2019 3:47 PM
To: devel@edk2.groups.io
Cc: Wu, Hao A <hao.a.wu@intel.com>; Gao, Liming <liming.gao@intel.com>; Sinha, Ankit <ankit.sinha@intel.com>; Agyeman, Prince <prince.agyeman@intel.com>; Kubacki, Michael A <michael.a.kubacki@intel.com>; Desimone, Nathaniel L <nathaniel.l.desimone@intel.com>; Kinney, Michael D <michael.d.kinney@intel.com>
Subject: [edk2-platform patch 2/7] SimicsICH10Pkg: Add PCH Pkg for SimicsICH10
Add PCH Pkg for SimicsICH10. It is added for simics QSP project support
Cc: Hao Wu <hao.a.wu@intel.com>
Cc: Liming Gao <liming.gao@intel.com>
Cc: Ankit Sinha <ankit.sinha@intel.com>
Cc: Agyeman Prince <prince.agyeman@intel.com>
Cc: Kubacki Michael A <michael.a.kubacki@intel.com>
Cc: Nate DeSimone <nathaniel.l.desimone@intel.com>
Cc: Michael D Kinney <michael.d.kinney@intel.com>
Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: David Wei <david.y.wei@intel.com>
---
.../Library/ResetSystemLib/ResetSystemLib.c | 137 +++
.../Library/SmmSpiFlashCommonLib/SpiFlashCommon.c | 194 +++++
.../SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c | 54 ++
.../LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c | 935 +++++++++++++++++++++
.../SmmControl/RuntimeDxe/SmmControl2Dxe.c | 410 +++++++++
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c | 175 ++++
Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec | 22 +
.../Include/Library/SpiFlashCommonLib.h | 98 +++
Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h | 43 +
Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h | 94 +++
.../SimicsICH10Pkg/Include/PchReservedResources.h | 60 ++
.../Intel/SimicsICH10Pkg/Include/Protocol/Spi.h | 295 +++++++
.../SimicsICH10Pkg/Include/Register/PchRegsPmc.h | 647 ++++++++++++++
.../SimicsICH10Pkg/Include/Register/PchRegsSpi.h | 304 +++++++
.../IncludePrivate/Library/PchSpiCommonLib.h | 396 +++++++++
.../Library/ResetSystemLib/ResetSystemLib.inf | 34 +
.../SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf | 52 ++
.../BasePchSpiCommonLib/BasePchSpiCommonLib.inf | 33 +
Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc | 12 +
.../Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf | 9 +
.../Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf | 9 +
.../Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf | 13 +
.../SmmControl/RuntimeDxe/SmmControl2Dxe.inf | 59 ++
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h | 23 +
Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf | 44 +
25 files changed, 4152 insertions(+)
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
create mode 100644 Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
create mode 100644 Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
new file mode 100644
index 0000000000..46355e191c
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.c
@@ -0,0 +1,137 @@
+/** @file
+ Reset System Library functions for OVMF
+
+ Copyright (c) 2006 - 2016 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Base.h>
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/TimerLib.h>
+#include <IndustryStandard/X58Ich10.h>
+
+
+VOID
+AcpiPmControl (
+ UINTN SuspendType
+ )
+{
+ ASSERT (SuspendType < 6);
+ DEBUG((EFI_D_ERROR, "SuspendType = 0x%x\n", SuspendType));
+
+ IoBitFieldWrite16 (ICH10_PMBASE_IO + 4, 10, 13, (UINT16) SuspendType);
+ IoOr16 (ICH10_PMBASE_IO + 0x04, BIT13);
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes a system-wide reset. This sets
+ all circuitry within the system to its initial state. This type of reset
+ is asynchronous to system operation and operates without regard to
+ cycle boundaries.
+
+ System reset should not return, if it returns, it means the system does
+ not support cold reset.
+**/
+VOID
+EFIAPI
+ResetCold (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetCold_CF9\n"));
+ IoWrite8 (0xCF9, BIT3 | BIT2 | BIT1); // 1st choice: PIIX3 RCR, RCPU|SRST
+ MicroSecondDelay (50);
+
+ DEBUG((EFI_D_ERROR, "ResetCold_Port64\n"));
+ IoWrite8 (0x64, 0xfe); // 2nd choice: keyboard controller
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes a system-wide initialization. The processors
+ are set to their initial state, and pending cycles are not corrupted.
+
+ System reset should not return, if it returns, it means the system does
+ not support warm reset.
+**/
+VOID
+EFIAPI
+ResetWarm (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetWarm\n"));
+ //
+ //BUGBUG workaround for warm reset
+ //
+ IoWrite8(0xCF9, BIT2 | BIT1);
+ MicroSecondDelay(50);
+
+ IoWrite8 (0x64, 0xfe);
+ CpuDeadLoop ();
+}
+
+/**
+ Calling this function causes the system to enter a power state equivalent
+ to the ACPI G2/S5 or G3 states.
+
+ System shutdown should not return, if it returns, it means the system does
+ not support shut down reset.
+**/
+VOID
+EFIAPI
+ResetShutdown (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetShutdown\n"));
+ AcpiPmControl (0);
+ ASSERT (FALSE);
+}
+
+
+/**
+ Calling this function causes the system to enter a power state for capsule
+ update.
+
+ Reset update should not return, if it returns, it means the system does
+ not support capsule update.
+
+**/
+VOID
+EFIAPI
+EnterS3WithImmediateWake (
+ VOID
+ )
+{
+ DEBUG((EFI_D_ERROR, "EnterS3WithImmediateWake\n"));
+ AcpiPmControl (1);
+ ASSERT (FALSE);
+}
+
+/**
+ This function causes a systemwide reset. The exact type of the reset is
+ defined by the EFI_GUID that follows the Null-terminated Unicode string passed
+ into ResetData. If the platform does not recognize the EFI_GUID in ResetData
+ the platform must pick a supported reset type to perform.The platform may
+ optionally log the parameters from any non-normal reset that occurs.
+
+ @param[in] DataSize The size, in bytes, of ResetData.
+ @param[in] ResetData The data buffer starts with a Null-terminated string,
+ followed by the EFI_GUID.
+**/
+VOID
+EFIAPI
+ResetPlatformSpecific (
+ IN UINTN DataSize,
+ IN VOID *ResetData
+ )
+{
+ DEBUG((EFI_D_ERROR, "ResetPlatformSpecific\n"));
+ ResetCold ();
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
new file mode 100644
index 0000000000..3d4e24eac6
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommon.c
@@ -0,0 +1,194 @@
+/** @file
+ Wrap EFI_SPI_PROTOCOL to provide some library level interfaces
+ for module use.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/SpiFlashCommonLib.h>
+#include <Library/IoLib.h>
+#include <Library/PciLib.h>
+#include <Protocol/Spi.h>
+
+
+EFI_SPI_PROTOCOL *mSpiProtocol;
+
+//
+// FlashAreaBaseAddress and Size for boottime and runtime usage.
+//
+UINTN mFlashAreaBaseAddress = 0;
+UINTN mFlashAreaSize = 0;
+
+/**
+ Enable block protection on the Serial Flash device.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashLock (
+ VOID
+ )
+{
+ return EFI_SUCCESS;
+}
+
+/**
+ Read NumBytes bytes of data from the address specified by
+ PAddress into Buffer.
+
+ @param[in] Address The starting physical address of the read.
+ @param[in,out] NumBytes On input, the number of bytes to read. On output, the number
+ of bytes actually read.
+ @param[out] Buffer The destination data buffer for the read.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashRead (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ OUT UINT8 *Buffer
+ )
+{
+ ASSERT ((NumBytes != NULL) && (Buffer != NULL));
+ if ((NumBytes == NULL) || (Buffer == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // This function is implemented specifically for those platforms
+ // at which the SPI device is memory mapped for read. So this
+ // function just do a memory copy for Spi Flash Read.
+ //
+ CopyMem (Buffer, (VOID *) Address, *NumBytes);
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Write NumBytes bytes of data from Buffer to the address specified by
+ PAddresss.
+
+ @param[in] Address The starting physical address of the write.
+ @param[in,out] NumBytes On input, the number of bytes to write. On output,
+ the actual number of bytes written.
+ @param[in] Buffer The source data buffer for the write.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashWrite (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ IN UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINTN Offset;
+ UINT32 Length;
+ UINT32 RemainingBytes;
+
+ ASSERT ((NumBytes != NULL) && (Buffer != NULL));
+ if ((NumBytes == NULL) || (Buffer == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ ASSERT (Address >= mFlashAreaBaseAddress);
+
+ Offset = Address - mFlashAreaBaseAddress;
+
+ ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
+
+ Status = EFI_SUCCESS;
+ RemainingBytes = *NumBytes;
+
+
+ while (RemainingBytes > 0) {
+ if (RemainingBytes > SECTOR_SIZE_4KB) {
+ Length = SECTOR_SIZE_4KB;
+ } else {
+ Length = RemainingBytes;
+ }
+ Status = mSpiProtocol->FlashWrite (
+ mSpiProtocol,
+ FlashRegionBios,
+ (UINT32) Offset,
+ Length,
+ Buffer
+ );
+ if (EFI_ERROR (Status)) {
+ break;
+ }
+ RemainingBytes -= Length;
+ Offset += Length;
+ Buffer += Length;
+ }
+
+ //
+ // Actual number of bytes written
+ //
+ *NumBytes -= RemainingBytes;
+
+ return Status;
+}
+
+/**
+ Erase the block starting at Address.
+
+ @param[in] Address The starting physical address of the block to be erased.
+ This library assume that caller garantee that the PAddress
+ is at the starting address of this block.
+ @param[in] NumBytes On input, the number of bytes of the logical block to be erased.
+ On output, the actual number of bytes erased.
+
+ @retval EFI_SUCCESS. Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashBlockErase (
+ IN UINTN Address,
+ IN UINTN *NumBytes
+ )
+{
+ EFI_STATUS Status;
+ UINTN Offset;
+ UINTN RemainingBytes;
+
+ ASSERT (NumBytes != NULL);
+ if (NumBytes == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ ASSERT (Address >= mFlashAreaBaseAddress);
+
+ Offset = Address - mFlashAreaBaseAddress;
+
+ ASSERT ((*NumBytes % SECTOR_SIZE_4KB) == 0);
+ ASSERT ((*NumBytes + Offset) <= mFlashAreaSize);
+
+ Status = EFI_SUCCESS;
+ RemainingBytes = *NumBytes;
+
+
+ Status = mSpiProtocol->FlashErase (
+ mSpiProtocol,
+ FlashRegionBios,
+ (UINT32) Offset,
+ (UINT32) RemainingBytes
+ );
+ return Status;
+}
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
new file mode 100644
index 0000000000..1e5cd0d744
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SpiFlashCommonSmmLib.c
@@ -0,0 +1,54 @@
+/** @file
+ SMM Library instance of SPI Flash Common Library Class
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/SpiFlashCommonLib.h>
+#include <Library/SmmServicesTableLib.h>
+#include <Protocol/Spi.h>
+
+extern EFI_SPI_PROTOCOL *mSpiProtocol;
+
+extern UINTN mFlashAreaBaseAddress;
+extern UINTN mFlashAreaSize;
+
+/**
+ The library constructuor.
+
+ The function does the necessary initialization work for this library
+ instance.
+
+ @param[in] ImageHandle The firmware allocated handle for the UEFI image.
+ @param[in] SystemTable A pointer to the EFI system table.
+
+ @retval EFI_SUCCESS The function always return EFI_SUCCESS for now.
+ It will ASSERT on error for debug version.
+ @retval EFI_ERROR Please reference LocateProtocol for error code details.
+**/
+EFI_STATUS
+EFIAPI
+SmmSpiFlashCommonLibConstructor (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ mFlashAreaBaseAddress = (UINTN)PcdGet32 (PcdFlashAreaBaseAddress);
+ mFlashAreaSize = (UINTN)PcdGet32 (PcdFlashAreaSize);
+
+ //
+ // Locate the SMM SPI protocol.
+ //
+ Status = gSmst->SmmLocateProtocol (
+ &gEfiSmmSpiProtocolGuid,
+ NULL,
+ (VOID **) &mSpiProtocol
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ return Status;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
new file mode 100644
index 0000000000..77fb76d7cd
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/SpiCommon.c
@@ -0,0 +1,935 @@
+/** @file
+ PCH SPI Common Driver implements the SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Uefi/UefiBaseType.h>
+#include <Library/IoLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <IndustryStandard/Pci30.h>
+#include <PchAccess.h>
+#include <Protocol/Spi.h>
+#include <IncludePrivate/Library/PchSpiCommonLib.h>
+#include <IndustryStandard/X58Ich10.h>
+
+/**
+ Initialize an SPI protocol instance.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @exception EFI_UNSUPPORTED The PCH is not supported by this module
+**/
+EFI_STATUS
+SpiProtocolConstructor (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+ UINTN PchSpiBar0;
+
+ //
+ // Initialize the SPI protocol instance
+ //
+ SpiInstance->Signature = PCH_SPI_PRIVATE_DATA_SIGNATURE;
+ SpiInstance->Handle = NULL;
+ SpiInstance->SpiProtocol.Revision = PCH_SPI_SERVICES_REVISION;
+ SpiInstance->SpiProtocol.FlashRead = SpiProtocolFlashRead;
+ SpiInstance->SpiProtocol.FlashWrite = SpiProtocolFlashWrite;
+ SpiInstance->SpiProtocol.FlashErase = SpiProtocolFlashErase;
+ SpiInstance->SpiProtocol.FlashReadSfdp = SpiProtocolFlashReadSfdp;
+ SpiInstance->SpiProtocol.FlashReadJedecId = SpiProtocolFlashReadJedecId;
+ SpiInstance->SpiProtocol.FlashWriteStatus = SpiProtocolFlashWriteStatus;
+ SpiInstance->SpiProtocol.FlashReadStatus = SpiProtocolFlashReadStatus;
+ SpiInstance->SpiProtocol.GetRegionAddress = SpiProtocolGetRegionAddress;
+ SpiInstance->SpiProtocol.ReadPchSoftStrap = SpiProtocolReadPchSoftStrap;
+ SpiInstance->SpiProtocol.ReadCpuSoftStrap = SpiProtocolReadCpuSoftStrap;
+
+ SpiInstance->PchAcpiBase = ICH10_PMBASE_IO;
+ ASSERT (SpiInstance->PchAcpiBase != 0);
+
+ PchSpiBar0 = RCRB + SPIBAR;
+
+ if (PchSpiBar0 == 0) {
+ DEBUG ((DEBUG_ERROR, "ERROR : PchSpiBar0 is invalid!\n"));
+ ASSERT (FALSE);
+ }
+
+ if ((MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC) & B_PCH_SPI_HSFSC_FDV) == 0) {
+ DEBUG ((DEBUG_ERROR, "ERROR : SPI Flash Signature invalid, cannot use the Hardware Sequencing registers!\n"));
+ ASSERT (FALSE);
+ }
+ SpiInstance->ReadPermission = 0xffff;
+ SpiInstance->WritePermission = 0xffff;
+ DEBUG ((DEBUG_INFO, "Flash Region Permission: Read- 0x%04x; Write= 0x%04x\n",
+ SpiInstance->ReadPermission,
+ SpiInstance->WritePermission));
+
+ //
+ SpiInstance->TotalFlashSize = PcdGet32(PcdFlashAreaSize);
+ DEBUG ((DEBUG_INFO, "Total Flash Size : %0x\n", SpiInstance->TotalFlashSize));
+ return EFI_SUCCESS;
+}
+
+/**
+ Delay for at least the request number of microseconds for Runtime usage.
+
+ @param[in] ABase Acpi base address
+ @param[in] Microseconds Number of microseconds to delay.
+
+**/
+VOID
+EFIAPI
+PchPmTimerStallRuntimeSafe (
+ IN UINT16 ABase,
+ IN UINTN Microseconds
+ )
+{
+ UINTN Ticks;
+ UINTN Counts;
+ UINTN CurrentTick;
+ UINTN OriginalTick;
+ UINTN RemainingTick;
+
+ if (Microseconds == 0) {
+ return;
+ }
+
+ OriginalTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) & B_PCH_ACPI_PM1_TMR_VAL;
+ 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 / V_PCH_ACPI_PM1_TMR_MAX_VAL;
+
+ //
+ // Remaining clocks within one loop
+ //
+ RemainingTick = Ticks % V_PCH_ACPI_PM1_TMR_MAX_VAL;
+
+ //
+ // 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) || (RemainingTick > CurrentTick)) {
+ CurrentTick = IoRead32 ((UINTN) (ABase + R_PCH_ACPI_PM1_TMR)) & B_PCH_ACPI_PM1_TMR_VAL;
+ //
+ // Check if timer overflow
+ //
+ if ((CurrentTick < OriginalTick)) {
+ if (Counts != 0) {
+ Counts--;
+ } else {
+ //
+ // If timer overflow and Counts equ to 0, that means we already stalled more than
+ // RemainingTick, break the loop here
+ //
+ break;
+ }
+ }
+
+ OriginalTick = CurrentTick;
+ }
+}
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashRead (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleRead,
+ Address,
+ ByteCount,
+ Buffer
+ );
+ return Status;
+}
+
+/**
+ Write data to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWrite (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleWrite,
+ Address,
+ ByteCount,
+ Buffer
+ );
+ return Status;
+}
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashErase (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionType,
+ FlashCycleErase,
+ Address,
+ ByteCount,
+ NULL
+ );
+ return Status;
+}
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadSfdp (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ EFI_STATUS Status;
+ UINT32 FlashAddress;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ Status = EFI_SUCCESS;
+
+ if (ComponentNumber > SpiInstance->NumberOfComponents) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ FlashAddress = 0;
+ if (ComponentNumber == FlashComponent1) {
+ FlashAddress = SpiInstance->Component1StartAddr;
+ }
+ FlashAddress += Address;
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadSfdp,
+ FlashAddress,
+ ByteCount,
+ SfdpData
+ );
+ return Status;
+}
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadJedecId (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ EFI_STATUS Status;
+ UINT32 Address;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ Status = EFI_SUCCESS;
+
+ if (ComponentNumber > SpiInstance->NumberOfComponents) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Address = 0;
+ if (ComponentNumber == FlashComponent1) {
+ Address = SpiInstance->Component1StartAddr;
+ }
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadJedecId,
+ Address,
+ ByteCount,
+ JedecId
+ );
+ return Status;
+}
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWriteStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleWriteStatus,
+ 0,
+ ByteCount,
+ StatusValue
+ );
+ return Status;
+}
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Sends the command to the SPI interface to execute.
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionAll,
+ FlashCycleReadStatus,
+ 0,
+ ByteCount,
+ StatusValue
+ );
+ return Status;
+}
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolGetRegionAddress (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINTN PchSpiBar0;
+ UINT32 ReadValue;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (FlashRegionType >= FlashRegionMax) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ if (FlashRegionType == FlashRegionAll) {
+ *BaseAddress = 0;
+ *RegionSize = SpiInstance->TotalFlashSize;
+ return EFI_SUCCESS;
+ }
+
+ PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
+ ReadValue = MmioRead32 (PchSpiBar0 + (R_PCH_SPI_FREG0_FLASHD + (S_PCH_SPI_FREGX * ((UINT32) FlashRegionType))));
+ ReleaseSpiBar0 (SpiInstance);
+
+ //
+ // If the region is not used, the Region Base is 7FFFh and Region Limit is 0000h
+ //
+ if (ReadValue == B_PCH_SPI_FREGX_BASE_MASK) {
+ return EFI_DEVICE_ERROR;
+ }
+ *BaseAddress = ((ReadValue & B_PCH_SPI_FREGX_BASE_MASK) >> N_PCH_SPI_FREGX_BASE) <<
+ N_PCH_SPI_FREGX_BASE_REPR;
+ //
+ // Region limit address Bits[11:0] are assumed to be FFFh
+ //
+ *RegionSize = ((((ReadValue & B_PCH_SPI_FREGX_LIMIT_MASK) >> N_PCH_SPI_FREGX_LIMIT) + 1) <<
+ N_PCH_SPI_FREGX_LIMIT_REPR) - *BaseAddress;
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadPchSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINT32 StrapFlashAddr;
+ EFI_STATUS Status;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (ByteCount == 0) {
+ *(UINT16 *) SoftStrapValue = SpiInstance->PchStrapSize;
+ return EFI_SUCCESS;
+ }
+
+ if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->PchStrapSize) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // PCH Strap Flash Address = FPSBA + RamAddr
+ //
+ StrapFlashAddr = SpiInstance->PchStrapBaseAddr + SoftStrapAddr;
+
+ //
+ // Read PCH Soft straps from using execute command
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionDescriptor,
+ FlashCycleRead,
+ StrapFlashAddr,
+ ByteCount,
+ SoftStrapValue
+ );
+ return Status;
+}
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadCpuSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ )
+{
+ SPI_INSTANCE *SpiInstance;
+ UINT32 StrapFlashAddr;
+ EFI_STATUS Status;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ if (ByteCount == 0) {
+ *(UINT16 *) SoftStrapValue = SpiInstance->CpuStrapSize;
+ return EFI_SUCCESS;
+ }
+
+ if ((SoftStrapAddr + ByteCount) > (UINT32) SpiInstance->CpuStrapSize) {
+ ASSERT (FALSE);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // CPU Strap Flash Address = FCPUSBA + RamAddr
+ //
+ StrapFlashAddr = SpiInstance->CpuStrapBaseAddr + SoftStrapAddr;
+
+ //
+ // Read Cpu Soft straps from using execute command
+ //
+ Status = SendSpiCmd (
+ This,
+ FlashRegionDescriptor,
+ FlashCycleRead,
+ StrapFlashAddr,
+ ByteCount,
+ SoftStrapValue
+ );
+ return Status;
+}
+
+/**
+ This function sends the programmed SPI command to the slave device.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SpiRegionType The SPI Region type for flash cycle which is listed in the Descriptor
+ @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware Sequencing Flash Control Register) register
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in,out] Buffer Pointer to caller-allocated buffer containing the dada received or sent during the SPI cycle.
+
+ @retval EFI_SUCCESS SPI command completes successfully.
+ @retval EFI_DEVICE_ERROR Device error, the command aborts abnormally.
+ @retval EFI_ACCESS_DENIED Some unrecognized command encountered in hardware sequencing mode
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+**/
+EFI_STATUS
+SendSpiCmd (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN FLASH_CYCLE_TYPE FlashCycleType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN OUT UINT8 *Buffer
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Index;
+ SPI_INSTANCE *SpiInstance;
+ UINTN SpiBaseAddress;
+ UINTN PchSpiBar0;
+ UINT32 HardwareSpiAddr;
+ UINT32 FlashRegionSize;
+ UINT32 SpiDataCount;
+ UINT32 FlashCycle;
+ UINT32 SmiEnSave;
+ UINT16 ABase;
+
+ Status = EFI_SUCCESS;
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+ SpiBaseAddress = SpiInstance->PchSpiBase;
+ PchSpiBar0 = AcquireSpiBar0 (SpiInstance);
+ SpiBaseAddress = SpiInstance->PchSpiBase;
+ ABase = SpiInstance->PchAcpiBase;
+
+ //
+ // Disable SMIs to make sure normal mode flash access is not interrupted by an SMI
+ // whose SMI handler accesses flash (e.g. for error logging)
+ //
+ // *** NOTE: if the SMI_LOCK bit is set (i.e., PMC PCI Offset A0h [4]='1'),
+ // clearing B_GBL_SMI_EN will not have effect. In this situation, some other
+ // synchronization methods must be applied here or in the consumer of the
+ // SendSpiCmd. An example method is disabling the specific SMI sources
+ // whose SMI handlers access flash before flash cycle and re-enabling the SMI
+ // sources after the flash cycle .
+ //
+ SmiEnSave = IoRead32 ((UINTN) (ABase + R_PCH_SMI_EN));
+ IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave & (UINT32) (~B_PCH_SMI_EN_GBL_SMI));
+
+ //
+ // If it's write cycle, disable Prefetching, Caching and disable BIOS Write Protect
+ //
+ if ((FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleErase)) {
+ Status = DisableBiosWriteProtect ();
+ if (EFI_ERROR (Status)) {
+ goto SendSpiCmdEnd;
+ }
+ }
+ //
+ // Make sure it's safe to program the command.
+ //
+ if (!WaitForSpiCycleComplete (This, PchSpiBar0, FALSE)) {
+ Status = EFI_DEVICE_ERROR;
+ goto SendSpiCmdEnd;
+ }
+
+ Status = SpiProtocolGetRegionAddress (This, FlashRegionType, &HardwareSpiAddr, &FlashRegionSize);
+ if (EFI_ERROR (Status)) {
+ goto SendSpiCmdEnd;
+ }
+ HardwareSpiAddr += Address;
+ if ((Address + ByteCount) > FlashRegionSize) {
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ }
+
+ //
+ // Check for PCH SPI hardware sequencing required commands
+ //
+ FlashCycle = 0;
+ switch (FlashCycleType) {
+ case FlashCycleRead:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleWrite:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleErase:
+ if (((ByteCount % SIZE_4KB) != 0) ||
+ ((HardwareSpiAddr % SIZE_4KB) != 0)) {
+ ASSERT (FALSE);
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ }
+ break;
+ case FlashCycleReadSfdp:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_SFDP << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleReadJedecId:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleWriteStatus:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ case FlashCycleReadStatus:
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_READ_STATUS << N_PCH_SPI_HSFSC_CYCLE);
+ break;
+ default:
+ //
+ // Unrecognized Operation
+ //
+ ASSERT (FALSE);
+ Status = EFI_INVALID_PARAMETER;
+ goto SendSpiCmdEnd;
+ break;
+ }
+
+ do {
+ SpiDataCount = ByteCount;
+ if ((FlashCycleType == FlashCycleRead) ||
+ (FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleReadSfdp)) {
+ //
+ // Trim at 256 byte boundary per operation,
+ // - PCH SPI controller requires trimming at 4KB boundary
+ // - Some SPI chips require trimming at 256 byte boundary for write operation
+ // - Trimming has limited performance impact as we can read / write atmost 64 byte
+ // per operation
+ //
+ if (HardwareSpiAddr + ByteCount > ((HardwareSpiAddr + BIT8) &~(BIT8 - 1))) {
+ SpiDataCount = (((UINT32) (HardwareSpiAddr) + BIT8) &~(BIT8 - 1)) - (UINT32) (HardwareSpiAddr);
+ }
+ //
+ // Calculate the number of bytes to shift in/out during the SPI data cycle.
+ // Valid settings for the number of bytes duing each data portion of the
+ // PCH SPI cycles are: 0, 1, 2, 3, 4, 5, 6, 7, 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ if (SpiDataCount >= 64) {
+ SpiDataCount = 64;
+ } else if ((SpiDataCount &~0x07) != 0) {
+ SpiDataCount = SpiDataCount &~0x07;
+ }
+ }
+ if (FlashCycleType == FlashCycleErase) {
+ if (((ByteCount / SIZE_64KB) != 0) &&
+ ((ByteCount % SIZE_64KB) == 0) &&
+ ((HardwareSpiAddr % SIZE_64KB) == 0)) {
+ if (HardwareSpiAddr < SpiInstance->Component1StartAddr) {
+ //
+ // Check whether Component0 support 64k Erase
+ //
+ if ((SpiInstance->SfdpVscc0Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K) != 0) {
+ SpiDataCount = SIZE_64KB;
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ } else {
+ //
+ // Check whether Component1 support 64k Erase
+ //
+ if ((SpiInstance->SfdpVscc1Value & B_PCH_SPI_SFDPX_VSCCX_EO_64K) != 0) {
+ SpiDataCount = SIZE_64KB;
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ }
+ } else {
+ SpiDataCount = SIZE_4KB;
+ }
+ if (SpiDataCount == SIZE_4KB) {
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_4K_ERASE << N_PCH_SPI_HSFSC_CYCLE);
+ } else {
+ FlashCycle = (UINT32) (V_PCH_SPI_HSFSC_CYCLE_64K_ERASE << N_PCH_SPI_HSFSC_CYCLE);
+ }
+ }
+ //
+ // If it's write cycle, load data into the SPI data buffer.
+ //
+ if ((FlashCycleType == FlashCycleWrite) || (FlashCycleType == FlashCycleWriteStatus)) {
+ if ((SpiDataCount & 0x07) != 0) {
+ //
+ // Use Byte write if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
+ //
+ for (Index = 0; Index < SpiDataCount; Index++) {
+ MmioWrite8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, Buffer[Index]);
+ }
+ } else {
+ //
+ // Use Dword write if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
+ MmioWrite32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index, *(UINT32 *) (Buffer + Index));
+ }
+ }
+ }
+
+ //
+ // Set the Flash Address
+ //
+ MmioWrite32 (
+ (PchSpiBar0 + R_PCH_SPI_FADDR),
+ (UINT32) (HardwareSpiAddr & B_PCH_SPI_FADDR_MASK)
+ );
+
+ //
+ // Set Data count, Flash cycle, and Set Go bit to start a cycle
+ //
+ MmioAndThenOr32 (
+ PchSpiBar0 + R_PCH_SPI_HSFSC,
+ (UINT32) (~(B_PCH_SPI_HSFSC_FDBC_MASK | B_PCH_SPI_HSFSC_CYCLE_MASK)),
+ (UINT32) ((((SpiDataCount - 1) << N_PCH_SPI_HSFSC_FDBC) & B_PCH_SPI_HSFSC_FDBC_MASK) | FlashCycle | B_PCH_SPI_HSFSC_CYCLE_FGO)
+ );
+ //
+ // end of command execution
+ //
+ // Wait the SPI cycle to complete.
+ //
+ if (!WaitForSpiCycleComplete (This, PchSpiBar0, TRUE)) {
+ ASSERT (FALSE);
+ Status = EFI_DEVICE_ERROR;
+ goto SendSpiCmdEnd;
+ }
+ //
+ // If it's read cycle, load data into the call's buffer.
+ //
+ if ((FlashCycleType == FlashCycleRead) ||
+ (FlashCycleType == FlashCycleReadSfdp) ||
+ (FlashCycleType == FlashCycleReadJedecId) ||
+ (FlashCycleType == FlashCycleReadStatus)) {
+ if ((SpiDataCount & 0x07) != 0) {
+ //
+ // Use Byte read if Data Count is 0, 1, 2, 3, 4, 5, 6, 7
+ //
+ for (Index = 0; Index < SpiDataCount; Index++) {
+ Buffer[Index] = MmioRead8 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index);
+ }
+ } else {
+ //
+ // Use Dword read if Data Count is 8, 16, 24, 32, 40, 48, 56, 64
+ //
+ for (Index = 0; Index < SpiDataCount; Index += sizeof (UINT32)) {
+ *(UINT32 *) (Buffer + Index) = MmioRead32 (PchSpiBar0 + R_PCH_SPI_FDATA00 + Index);
+ }
+ }
+ }
+
+ HardwareSpiAddr += SpiDataCount;
+ Buffer += SpiDataCount;
+ ByteCount -= SpiDataCount;
+ } while (ByteCount > 0);
+
+SendSpiCmdEnd:
+ //
+ // Restore the settings for SPI Prefetching and Caching and enable BIOS Write Protect
+ //
+ if ((FlashCycleType == FlashCycleWrite) ||
+ (FlashCycleType == FlashCycleErase)) {
+ EnableBiosWriteProtect ();
+ }
+ //
+ // Restore SMIs.
+ //
+ IoWrite32 ((UINTN) (ABase + R_PCH_SMI_EN), SmiEnSave);
+
+ ReleaseSpiBar0 (SpiInstance);
+ return Status;
+}
+
+/**
+ Wait execution cycle to complete on the SPI interface.
+
+ @param[in] This The SPI protocol instance
+ @param[in] PchSpiBar0 Spi MMIO base address
+ @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
+
+ @retval TRUE SPI cycle completed on the interface.
+ @retval FALSE Time out while waiting the SPI cycle to complete.
+ It's not safe to program the next command on the SPI interface.
+**/
+BOOLEAN
+WaitForSpiCycleComplete (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINTN PchSpiBar0,
+ IN BOOLEAN ErrorCheck
+ )
+{
+ UINT64 WaitTicks;
+ UINT64 WaitCount;
+ UINT32 Data32;
+ SPI_INSTANCE *SpiInstance;
+
+ SpiInstance = SPI_INSTANCE_FROM_SPIPROTOCOL (This);
+
+ //
+ // Convert the wait period allowed into to tick count
+ //
+ WaitCount = SPI_WAIT_TIME / SPI_WAIT_PERIOD;
+ //
+ // Wait for the SPI cycle to complete.
+ //
+ for (WaitTicks = 0; WaitTicks < WaitCount; WaitTicks++) {
+ Data32 = MmioRead32 (PchSpiBar0 + R_PCH_SPI_HSFSC);
+ if ((Data32 & B_PCH_SPI_HSFSC_SCIP) == 0) {
+ MmioWrite32 (PchSpiBar0 + R_PCH_SPI_HSFSC, B_PCH_SPI_HSFSC_FCERR | B_PCH_SPI_HSFSC_FDONE);
+ if (((Data32 & B_PCH_SPI_HSFSC_FCERR) != 0) && (ErrorCheck == TRUE)) {
+ return FALSE;
+ } else {
+ return TRUE;
+ }
+ }
+ PchPmTimerStallRuntimeSafe (SpiInstance->PchAcpiBase, SPI_WAIT_PERIOD);
+ }
+ return FALSE;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
new file mode 100644
index 0000000000..8fb4947b1a
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.c
@@ -0,0 +1,410 @@
+/** @file
+ A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
+ EFI_SMM_CONTROL2_PROTOCOL.
+
+ We expect the PEI phase to have covered the following:
+ - ensure that the underlying QEMU machine type be X58
+ (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
+ - ensure that the ACPI PM IO space be configured
+ (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
+
+ Our own entry point is responsible for confirming the SMI feature and for
+ configuring it.
+
+ Copyright (C) 2013, 2015, Red Hat, Inc.<BR>
+ Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <IndustryStandard/X58Ich10.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/PcdLib.h>
+#include <Library/PciLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Protocol/S3SaveState.h>
+#include <Protocol/SmmControl2.h>
+
+//
+// Forward declaration.
+//
+STATIC
+VOID
+EFIAPI
+OnS3SaveStateInstalled (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ );
+
+//
+// The absolute IO port address of the SMI Control and Enable Register. It is
+// only used to carry information from the entry point function to the
+// S3SaveState protocol installation callback, strictly before the runtime
+// phase.
+//
+STATIC UINTN mSmiEnable;
+
+//
+// Event signaled when an S3SaveState protocol interface is installed.
+//
+STATIC EFI_EVENT mS3SaveStateInstalled;
+
+/**
+ Clear the SMI status
+
+ @retval EFI_SUCCESS The function completes successfully
+ @retval EFI_DEVICE_ERROR Something error occurred
+
+**/
+EFI_STATUS
+EFIAPI
+SmmClear(
+ VOID
+)
+{
+ EFI_STATUS Status;
+ UINT32 OutputData;
+ UINT32 OutputPort;
+ UINT32 PmBase;
+
+ Status = EFI_SUCCESS;
+ PmBase = ICH10_PMBASE_IO;
+
+ OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_STS;
+ OutputData = ICH10_SMI_STS_APM;
+ IoWrite32(
+ (UINTN)OutputPort,
+ (UINT32)(OutputData)
+ );
+
+ ///
+ /// Set the EOS Bit
+ ///
+ OutputPort = PmBase + ICH10_PMBASE_OFS_SMI_EN;
+ OutputData = IoRead32((UINTN)OutputPort);
+ OutputData |= ICH10_SMI_EN_EOS;
+ IoWrite32(
+ (UINTN)OutputPort,
+ (UINT32)(OutputData)
+ );
+
+ ///
+ /// There is no need to read EOS back and check if it is set.
+ /// This can lead to a reading of zero if an SMI occurs right after the SMI_EN port read
+ /// but before the data is returned to the CPU.
+ /// SMM Dispatcher should make sure that EOS is set after all SMI sources are processed.
+ ///
+ return Status;
+}
+
+/**
+ Invokes SMI activation from either the preboot or runtime environment.
+
+ This function generates an SMI.
+
+ @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
+ @param[in,out] CommandPort The value written to the command port.
+ @param[in,out] DataPort The value written to the data port.
+ @param[in] Periodic Optional mechanism to engender a periodic
+ stream.
+ @param[in] ActivationInterval Optional parameter to repeat at this
+ period one time or, if the Periodic
+ Boolean is set, periodically.
+
+ @retval EFI_SUCCESS The SMI/PMI has been engendered.
+ @retval EFI_DEVICE_ERROR The timing is unsupported.
+ @retval EFI_INVALID_PARAMETER The activation period is unsupported.
+ @retval EFI_INVALID_PARAMETER The last periodic activation has not been
+ cleared.
+ @retval EFI_NOT_STARTED The SMM base service has not been initialized.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+SmmControl2DxeTrigger (
+ IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
+ IN OUT UINT8 *CommandPort OPTIONAL,
+ IN OUT UINT8 *DataPort OPTIONAL,
+ IN BOOLEAN Periodic OPTIONAL,
+ IN UINTN ActivationInterval OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ //
+ // No support for queued or periodic activation.
+ //
+ if (Periodic || ActivationInterval > 0) {
+ return EFI_DEVICE_ERROR;
+ }
+ ///
+ /// Clear any pending the APM SMI
+ ///
+ Status = SmmClear();
+ //
+ // The so-called "Advanced Power Management Status Port Register" is in fact
+ // a generic data passing register, between the caller and the SMI
+ // dispatcher. The ICH9 spec calls it "scratchpad register" -- calling it
+ // "status" elsewhere seems quite the misnomer. Status registers usually
+ // report about hardware status, while this register is fully governed by
+ // software.
+ //
+ // Write to the status register first, as this won't trigger the SMI just
+ // yet. Then write to the control register.
+ //
+ IoWrite8 (ICH10_APM_STS, DataPort == NULL ? 0 : *DataPort);
+ IoWrite8 (ICH10_APM_CNT, CommandPort == NULL ? 0 : *CommandPort);
+ return EFI_SUCCESS;
+}
+
+/**
+ Clears any system state that was created in response to the Trigger() call.
+
+ This function acknowledges and causes the deassertion of the SMI activation
+ source.
+
+ @param[in] This The EFI_SMM_CONTROL2_PROTOCOL instance.
+ @param[in] Periodic Optional parameter to repeat at this period
+ one time
+
+ @retval EFI_SUCCESS The SMI/PMI has been engendered.
+ @retval EFI_DEVICE_ERROR The source could not be cleared.
+ @retval EFI_INVALID_PARAMETER The service did not support the Periodic input
+ argument.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+SmmControl2DxeClear (
+ IN CONST EFI_SMM_CONTROL2_PROTOCOL *This,
+ IN BOOLEAN Periodic OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+
+ if (Periodic) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // The PI spec v1.4 explains that Clear() is only supposed to clear software
+ // status; it is not in fact responsible for deasserting the SMI. It gives
+ // two reasons for this: (a) many boards clear the SMI automatically when
+ // entering SMM, (b) if Clear() actually deasserted the SMI, then it could
+ // incorrectly suppress an SMI that was asynchronously asserted between the
+ // last return of the SMI handler and the call made to Clear().
+ //
+ // In fact QEMU automatically deasserts CPU_INTERRUPT_SMI in:
+ // - x86_cpu_exec_interrupt() [target-i386/seg_helper.c], and
+ // - kvm_arch_pre_run() [target-i386/kvm.c].
+ //
+ // So, nothing to do here.
+ //
+ Status = SmmClear();
+
+ return EFI_SUCCESS;
+}
+
+STATIC EFI_SMM_CONTROL2_PROTOCOL mControl2 = {
+ &SmmControl2DxeTrigger,
+ &SmmControl2DxeClear,
+ MAX_UINTN // MinimumTriggerPeriod -- we don't support periodic SMIs
+};
+
+//
+// Entry point of this driver.
+//
+EFI_STATUS
+EFIAPI
+SmmControl2DxeEntryPoint (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ UINT32 PmBase;
+ UINT32 SmiEnableVal;
+ EFI_STATUS Status;
+
+ //
+ // This module should only be included if SMRAM support is required.
+ //
+ ASSERT (FeaturePcdGet (PcdSmmSmramRequire));
+
+ //
+ // Calculate the absolute IO port address of the SMI Control and Enable
+ // Register. (As noted at the top, the PEI phase has left us with a working
+ // ACPI PM IO space.)
+ //
+ PmBase = PciRead32 (POWER_MGMT_REGISTER_ICH10 (ICH10_PMBASE)) &
+ ICH10_PMBASE_MASK;
+ mSmiEnable = PmBase + ICH10_PMBASE_OFS_SMI_EN;
+
+ //
+ // If APMC_EN is pre-set in SMI_EN, that's QEMU's way to tell us that SMI
+ // support is not available. (For example due to KVM lacking it.) Otherwise,
+ // this bit is clear after each reset.
+ //
+ SmiEnableVal = IoRead32 (mSmiEnable);
+ if ((SmiEnableVal & ICH10_SMI_EN_APMC_EN) != 0) {
+ DEBUG ((EFI_D_ERROR, "%a: this X58 implementation lacks SMI\n",
+ __FUNCTION__));
+ }
+
+ //
+ // Otherwise, configure the board to inject an SMI when ICH10_APM_CNT is
+ // written to. (See the Trigger() method above.)
+ //
+ SmiEnableVal |= ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
+ IoWrite32 (mSmiEnable, SmiEnableVal);
+
+ //
+ // Prevent software from undoing the above (until platform reset).
+ //
+ PciOr16 (POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
+ ICH10_GEN_PMCON_1_SMI_LOCK);
+
+ //
+ // If we can clear GBL_SMI_EN now, that means QEMU's SMI support is not
+ // appropriate.
+ //
+ IoWrite32 (mSmiEnable, SmiEnableVal & ~(UINT32)ICH10_SMI_EN_GBL_SMI_EN);
+ if (IoRead32 (mSmiEnable) != SmiEnableVal) {
+ DEBUG ((EFI_D_ERROR, "%a: failed to lock down GBL_SMI_EN\n",
+ __FUNCTION__));
+ goto FatalError;
+ }
+
+ VOID *Registration;
+
+ //
+ // On S3 resume the above register settings have to be repeated. Register a
+ // protocol notify callback that, when boot script saving becomes
+ // available, saves operations equivalent to the above to the boot script.
+ //
+ Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK,
+ OnS3SaveStateInstalled, NULL /* Context */,
+ &mS3SaveStateInstalled);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: CreateEvent: %r\n", __FUNCTION__, Status));
+ goto FatalError;
+ }
+
+ Status = gBS->RegisterProtocolNotify (&gEfiS3SaveStateProtocolGuid,
+ mS3SaveStateInstalled, &Registration);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: RegisterProtocolNotify: %r\n", __FUNCTION__,
+ Status));
+ goto ReleaseEvent;
+ }
+
+ //
+ // Kick the event right now -- maybe the boot script is already saveable.
+ //
+ Status = gBS->SignalEvent (mS3SaveStateInstalled);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: SignalEvent: %r\n", __FUNCTION__, Status));
+ goto ReleaseEvent;
+ }
+
+ //
+ // We have no pointers to convert to virtual addresses. The handle itself
+ // doesn't matter, as protocol services are not accessible at runtime.
+ //
+ Status = gBS->InstallMultipleProtocolInterfaces (&ImageHandle,
+ &gEfiSmmControl2ProtocolGuid, &mControl2,
+ NULL);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: InstallMultipleProtocolInterfaces: %r\n",
+ __FUNCTION__, Status));
+ goto ReleaseEvent;
+ }
+
+ return EFI_SUCCESS;
+
+ReleaseEvent:
+ if (mS3SaveStateInstalled != NULL) {
+ gBS->CloseEvent (mS3SaveStateInstalled);
+ }
+
+FatalError:
+ //
+ // We really don't want to continue in this case.
+ //
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ return EFI_UNSUPPORTED;
+}
+
+/**
+ Notification callback for S3SaveState installation.
+
+ @param[in] Event Event whose notification function is being invoked.
+
+ @param[in] Context The pointer to the notification function's context, which
+ is implementation-dependent.
+**/
+STATIC
+VOID
+EFIAPI
+OnS3SaveStateInstalled (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+{
+ EFI_STATUS Status;
+ EFI_S3_SAVE_STATE_PROTOCOL *S3SaveState;
+ UINT32 SmiEnOrMask, SmiEnAndMask;
+ UINT16 GenPmCon1OrMask, GenPmCon1AndMask;
+
+ ASSERT (Event == mS3SaveStateInstalled);
+
+ Status = gBS->LocateProtocol (&gEfiS3SaveStateProtocolGuid,
+ NULL /* Registration */, (VOID **)&S3SaveState);
+ if (EFI_ERROR (Status)) {
+ return;
+ }
+
+ //
+ // These operations were originally done, verified and explained in the entry
+ // point function of the driver.
+ //
+ SmiEnOrMask = ICH10_SMI_EN_APMC_EN | ICH10_SMI_EN_GBL_SMI_EN;
+ SmiEnAndMask = MAX_UINT32;
+ Status = S3SaveState->Write (
+ S3SaveState,
+ EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE,
+ EfiBootScriptWidthUint32,
+ (UINT64)mSmiEnable,
+ &SmiEnOrMask,
+ &SmiEnAndMask
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "%a: EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE: %r\n",
+ __FUNCTION__, Status));
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ }
+
+ GenPmCon1OrMask = ICH10_GEN_PMCON_1_SMI_LOCK;
+ GenPmCon1AndMask = MAX_UINT16;
+ Status = S3SaveState->Write (
+ S3SaveState,
+ EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE,
+ EfiBootScriptWidthUint16,
+ (UINT64)POWER_MGMT_REGISTER_ICH10 (ICH10_GEN_PMCON_1),
+ &GenPmCon1OrMask,
+ &GenPmCon1AndMask
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR,
+ "%a: EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE: %r\n", __FUNCTION__,
+ Status));
+ ASSERT (FALSE);
+ CpuDeadLoop ();
+ }
+
+ DEBUG ((EFI_D_VERBOSE, "%a: boot script fragment saved\n", __FUNCTION__));
+ gBS->CloseEvent (Event);
+ mS3SaveStateInstalled = NULL;
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
new file mode 100644
index 0000000000..19eb469657
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.c
@@ -0,0 +1,175 @@
+/** @file
+ PCH SPI SMM Driver implements the SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include "PchSpi.h"
+
+//
+// Global variables
+//
+GLOBAL_REMOVE_IF_UNREFERENCED SPI_INSTANCE *mSpiInstance;
+//
+// mPchSpiResvMmioAddr keeps the reserved MMIO range assiged to SPI.
+// In SMM it always set back the reserved MMIO address to SPI BAR0 to ensure the MMIO range
+// won't overlap with SMRAM range, and trusted.
+//
+GLOBAL_REMOVE_IF_UNREFERENCED UINT32 mSpiResvMmioAddr;
+
+/**
+ <b>SPI Runtime SMM Module Entry Point</b>\n
+ - <b>Introduction</b>\n
+ The SPI SMM module provide a standard way for other modules to use the PCH SPI Interface in SMM.
+
+ - @pre
+ - EFI_SMM_BASE2_PROTOCOL
+ - Documented in System Management Mode Core Interface Specification .
+
+ - @result
+ The SPI SMM driver produces @link _PCH_SPI_PROTOCOL PCH_SPI_PROTOCOL @endlink with GUID
+ gPchSmmSpiProtocolGuid which is different from SPI RUNTIME driver.
+
+ - <b>Integration Check List</b>\n
+ - This driver supports Descriptor Mode only.
+ - This driver supports Hardware Sequence only.
+ - When using SMM SPI Protocol to perform flash access in an SMI handler,
+ and the SMI occurrence is asynchronous to normal mode code execution,
+ proper synchronization mechanism must be applied, e.g. disable SMI before
+ the normal mode SendSpiCmd() starts and re-enable SMI after
+ the normal mode SendSpiCmd() completes.
+ @note The implementation of SendSpiCmd() uses GBL_SMI_EN in
+ SMI_EN register (ABase + 30h) to disable and enable SMIs. But this may
+ not be effective as platform may well set the SMI_LOCK bit (i.e., PMC PCI Offset A0h [4]).
+ So the synchronization at caller level is likely needed.
+
+ @param[in] ImageHandle Image handle of this driver.
+ @param[in] SystemTable Global system service table.
+
+ @retval EFI_SUCCESS Initialization complete.
+ @exception EFI_UNSUPPORTED The chipset is unsupported by this driver.
+ @retval EFI_OUT_OF_RESOURCES Do not have enough resources to initialize the driver.
+ @retval EFI_DEVICE_ERROR Device error, driver exits abnormally.
+**/
+EFI_STATUS
+EFIAPI
+InstallPchSpi (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Init PCH spi reserved MMIO address.
+ //
+ mSpiResvMmioAddr = PCH_SPI_BASE_ADDRESS;
+
+ ///
+ /// Allocate pool for SPI protocol instance
+ ///
+ Status = gSmst->SmmAllocatePool (
+ EfiRuntimeServicesData, /// MemoryType don't care
+ sizeof (SPI_INSTANCE),
+ (VOID **) &mSpiInstance
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (mSpiInstance == NULL) {
+ return EFI_OUT_OF_RESOURCES;
+ }
+
+ ZeroMem ((VOID *) mSpiInstance, sizeof (SPI_INSTANCE));
+ ///
+ /// Initialize the SPI protocol instance
+ ///
+ Status = SpiProtocolConstructor (mSpiInstance);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+ //
+ // Install the SMM EFI_SPI_PROTOCOL interface
+ //
+ Status = gSmst->SmmInstallProtocolInterface (
+ &(mSpiInstance->Handle),
+ &gEfiSmmSpiProtocolGuid,
+ EFI_NATIVE_INTERFACE,
+ &(mSpiInstance->SpiProtocol)
+ );
+ if (EFI_ERROR (Status)) {
+ gSmst->SmmFreePool (mSpiInstance);
+ return EFI_DEVICE_ERROR;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Acquire PCH spi mmio address.
+ It is not expected for this BAR0 to change because the SPI device is hidden
+ from the OS for SKL PCH LP/H B stepping and above (refer to section 3.5.1),
+ but if it is ever different from the preallocated address, reassign it back.
+ In SMM, it always override the BAR0 and returns the reserved MMIO range for SPI.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval PchSpiBar0 return SPI MMIO address
+**/
+UINTN
+AcquireSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+ //
+ // SPIBAR0 will be different before and after PCI enum so need to get it from SPI BAR0 reg.
+ //
+ return mSpiResvMmioAddr;
+}
+
+/**
+ Release pch spi mmio address. Do nothing.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval None
+**/
+VOID
+ReleaseSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ )
+{
+}
+
+/**
+ This function is a hook for Spi to disable BIOS Write Protect
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in SMM phase
+
+**/
+EFI_STATUS
+EFIAPI
+DisableBiosWriteProtect (
+ VOID
+ )
+{
+
+ return EFI_SUCCESS;
+}
+
+/**
+ This function is a hook for Spi to enable BIOS Write Protect
+
+
+**/
+VOID
+EFIAPI
+EnableBiosWriteProtect (
+ VOID
+ )
+{
+}
diff --git a/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
new file mode 100644
index 0000000000..f9d340d6df
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/ICH10Pkg.dec
@@ -0,0 +1,22 @@
+## @file
+# Copyright (c) 2014 - 2016 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ DEC_SPECIFICATION = 0x00010005
+ PACKAGE_NAME = ICH10Pkg
+ PACKAGE_GUID = 4E97AC4B-F64C-4008-BBDE-01CC3B0BAA6B
+ PACKAGE_VERSION = 0.91
+
+[Includes]
+ Include
+
+[Ppis]
+
+[Guids]
+ gEfiPchTokenSpaceGuid = { 0x89a1b278, 0xa1a1, 0x4df7, { 0xb1, 0x37, 0xde, 0x5a, 0xd7, 0xc4, 0x79, 0x13 } }
+[Protocols]
+ gEfiSmmSpiProtocolGuid = {0xbd75fe35, 0xfdce, 0x49d7, {0xa9, 0xdd, 0xb2, 0x6f, 0x1f, 0xc6, 0xb4, 0x37}}
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
new file mode 100644
index 0000000000..c36360bcb0
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Library/SpiFlashCommonLib.h
@@ -0,0 +1,98 @@
+/** @file
+ The header file includes the common header files, defines
+ internal structure and functions used by SpiFlashCommonLib.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef __SPI_FLASH_COMMON_LIB_H__
+#define __SPI_FLASH_COMMON_LIB_H__
+
+#include <Uefi.h>
+#include <Library/BaseLib.h>
+#include <Library/PcdLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+
+#define SECTOR_SIZE_4KB 0x1000 // Common 4kBytes sector size
+/**
+ Enable block protection on the Serial Flash device.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashLock (
+ VOID
+ );
+
+/**
+ Read NumBytes bytes of data from the address specified by
+ PAddress into Buffer.
+
+ @param[in] Address The starting physical address of the read.
+ @param[in,out] NumBytes On input, the number of bytes to read. On output, the number
+ of bytes actually read.
+ @param[out] Buffer The destination data buffer for the read.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashRead (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write NumBytes bytes of data from Buffer to the address specified by
+ PAddresss.
+
+ @param[in] Address The starting physical address of the write.
+ @param[in,out] NumBytes On input, the number of bytes to write. On output,
+ the actual number of bytes written.
+ @param[in] Buffer The source data buffer for the write.
+
+ @retval EFI_SUCCESS Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashWrite (
+ IN UINTN Address,
+ IN OUT UINT32 *NumBytes,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase the block starting at Address.
+
+ @param[in] Address The starting physical address of the block to be erased.
+ This library assume that caller garantee that the PAddress
+ is at the starting address of this block.
+ @param[in] NumBytes On input, the number of bytes of the logical block to be erased.
+ On output, the actual number of bytes erased.
+
+ @retval EFI_SUCCESS. Opertion is successful.
+ @retval EFI_DEVICE_ERROR If there is any device errors.
+
+**/
+EFI_STATUS
+EFIAPI
+SpiFlashBlockErase (
+ IN UINTN Address,
+ IN UINTN *NumBytes
+ );
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
new file mode 100644
index 0000000000..552ce28d8c
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchAccess.h
@@ -0,0 +1,43 @@
+/** @file
+ Macros that simplify accessing PCH devices's PCI registers.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_ACCESS_H_
+#define _PCH_ACCESS_H_
+
+#include "PchReservedResources.h"
+
+#ifndef STALL_ONE_MICRO_SECOND
+#define STALL_ONE_MICRO_SECOND 1
+#endif
+#ifndef STALL_ONE_SECOND
+#define STALL_ONE_SECOND 1000000
+#endif
+
+
+///
+/// The default PCH PCI bus number
+///
+#define DEFAULT_PCI_BUS_NUMBER_PCH 0
+
+//
+// Default Vendor ID and Subsystem ID
+//
+#define V_PCH_INTEL_VENDOR_ID 0x8086 ///< Default Intel PCH Vendor ID
+#define V_PCH_DEFAULT_SID 0x7270 ///< Default Intel PCH Subsystem ID
+#define V_PCH_DEFAULT_SVID_SID (V_INTEL_VENDOR_ID + (V_PCH_DEFAULT_SID << 16)) ///< Default INTEL PCH Vendor ID and Subsystem ID
+
+//
+// Include device register definitions
+//
+
+#include "Register/PchRegsPmc.h"
+
+#include "Register/PchRegsSpi.h"
+
+#endif
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
new file mode 100644
index 0000000000..d503d130c8
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchLimits.h
@@ -0,0 +1,94 @@
+/** @file
+ Build time limits of PCH resources.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_LIMITS_H_
+#define _PCH_LIMITS_H_
+
+//
+// PCIe limits
+//
+#define PCH_MAX_PCIE_ROOT_PORTS PCH_H_PCIE_MAX_ROOT_PORTS
+#define PCH_H_PCIE_MAX_ROOT_PORTS 20
+#define PCH_LP_PCIE_MAX_ROOT_PORTS 12
+
+#define PCH_MAX_PCIE_CONTROLLERS PCH_H_PCIE_MAX_CONTROLLERS
+#define PCH_PCIE_CONTROLLER_PORTS 4
+#define PCH_H_PCIE_MAX_CONTROLLERS (PCH_H_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
+#define PCH_LP_PCIE_MAX_CONTROLLERS (PCH_LP_PCIE_MAX_ROOT_PORTS / PCH_PCIE_CONTROLLER_PORTS)
+
+//
+// PCIe clocks limits
+//
+#define PCH_LP_PCIE_MAX_CLK_REQ 6
+#define PCH_H_PCIE_MAX_CLK_REQ 16
+
+//
+// RST PCIe Storage Cycle Router limits
+//
+#define PCH_MAX_RST_PCIE_STORAGE_CR 3
+
+//
+// SATA limits
+//
+#define PCH_MAX_SATA_PORTS PCH_H_AHCI_MAX_PORTS
+#define PCH_H_AHCI_MAX_PORTS 8 ///< Max number of sata ports in SKL PCH H
+#define PCH_LP_AHCI_MAX_PORTS 3 ///< Max number of sata ports in SKL PCH LP
+#define PCH_SATA_MAX_DEVICES_PER_PORT 1 ///< Max support device numner per port, Port Multiplier is not support.
+
+//
+// USB limits
+//
+#define PCH_MAX_USB2_PORTS PCH_H_XHCI_MAX_USB2_PORTS
+
+#define PCH_H_XHCI_MAX_USB2_PHYSICAL_PORTS 14 ///< Max Physical Connector XHCI, not counting virtual ports like USB-R.
+#define PCH_LP_XHCI_MAX_USB2_PHYSICAL_PORTS 10 ///< Max Physical Connector XHCI, not counting virtual ports like USB-R.
+
+#define PCH_H_XHCI_MAX_USB2_PORTS 16 ///< 14 High Speed lanes + Including two ports reserved for USBr
+#define PCH_LP_XHCI_MAX_USB2_PORTS 12 ///< 10 High Speed lanes + Including two ports reserved for USBr
+
+#define PCH_MAX_USB3_PORTS PCH_H_XHCI_MAX_USB3_PORTS
+
+#define PCH_H_XHCI_MAX_USB3_PORTS 10 ///< 10 Super Speed lanes
+#define PCH_LP_XHCI_MAX_USB3_PORTS 6 ///< 6 Super Speed lanes
+
+#define PCH_XHCI_MAX_SSIC_PORT_COUNT 2 ///< 2 SSIC ports in SKL PCH-LP and SKL PCH-H
+
+//
+// SerialIo limits
+//
+#define PCH_SERIALIO_MAX_CONTROLLERS 11 ///< Number of SerialIo controllers, this includes I2C, SPI and UART
+#define PCH_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo I2C controllers
+#define PCH_LP_SERIALIO_MAX_I2C_CONTROLLERS 6 ///< Number of SerialIo I2C controllers for PCH-LP
+#define PCH_H_SERIALIO_MAX_I2C_CONTROLLERS 4 ///< Number of SerialIo I2C controllers for PCH-H
+#define PCH_SERIALIO_MAX_SPI_CONTROLLERS 2 ///< Number of SerialIo SPI controllers
+#define PCH_SERIALIO_MAX_UART_CONTROLLERS 3 ///< Number of SerialIo UART controllers
+
+//
+// ISH limits
+//
+#define PCH_ISH_MAX_GP_PINS 8
+#define PCH_ISH_MAX_UART_CONTROLLERS 2
+#define PCH_ISH_MAX_I2C_CONTROLLERS 3
+#define PCH_ISH_MAX_SPI_CONTROLLERS 1
+
+//
+// SCS limits
+//
+#define PCH_SCS_MAX_CONTROLLERS 3 ///< Number of Storage and Communication Subsystem controllers, this includes eMMC, SDIO, SDCARD
+
+//
+// Flash Protection Range Register
+//
+#define PCH_FLASH_PROTECTED_RANGES 5
+
+//
+// Number of eSPI slaves
+//
+#define PCH_ESPI_MAX_SLAVE_ID 2
+#endif // _PCH_LIMITS_H_
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
new file mode 100644
index 0000000000..00139fc230
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/PchReservedResources.h
@@ -0,0 +1,60 @@
+/** @file
+ PCH preserved MMIO resource definitions.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_PRESERVED_RESOURCES_H_
+#define _PCH_PRESERVED_RESOURCES_H_
+
+/**
+ PCH preserved MMIO range, 24 MB, from 0xFD000000 to 0xFE7FFFFF
+
+ Detailed recommended static allocation
+ +-------------------------------------------------------------------------+
+ | Size | Start | End | Usage |
+ | 16 MB | 0xFD000000 | 0xFDFFFFFF | SBREG |
+ | 64 KB | 0xFE000000 | 0xFE00FFFF | PMC MBAR |
+ | 4 KB | 0xFE010000 | 0xFE010FFF | SPI BAR0 |
+ | 88 KB | 0xFE020000 | 0xFE035FFF | SerialIo BAR in ACPI mode |
+ | 24 KB | 0xFE036000 | 0xFE03BFFF | Unused |
+ | 4 KB | 0xFE03C000 | 0xFE03CFFF | Thermal Device in ACPI mode |
+ | 524 KB | 0xFE03D000 | 0xFE0BFFFF | Unused |
+ | 256 KB | 0xFE0C0000 | 0xFE0FFFFF | TraceHub FW BAR |
+ | 1 MB | 0xFE100000 | 0xFE1FFFFF | TraceHub MTB BAR |
+ | 2 MB | 0xFE200000 | 0xFE3FFFFF | TraceHub SW BAR |
+ | 64 KB | 0xFE400000 | 0xFE40FFFF | CIO2 MMIO BAR in ACPI mode |
+ | 2 MB - 64KB | 0xFE410000 | 0xFE5FFFFF | Unused |
+ | 2 MB | 0xFE600000 | 0xFE7FFFFF | Temp address |
+ +-------------------------------------------------------------------------+
+**/
+#define PCH_PRESERVED_BASE_ADDRESS 0xFD000000 ///< Pch preserved MMIO base address
+#define PCH_PRESERVED_MMIO_SIZE 0x01800000 ///< 24MB
+#define PCH_PCR_BASE_ADDRESS 0xFD000000 ///< SBREG MMIO base address
+#define PCH_PCR_MMIO_SIZE 0x01000000 ///< 16MB
+#define PCH_PWRM_BASE_ADDRESS 0xFE000000 ///< PMC MBAR MMIO base address
+#define PCH_PWRM_MMIO_SIZE 0x00010000 ///< 64KB
+#define PCH_SPI_BASE_ADDRESS 0xFED1C000 + 0x3800 ///< SPI MBAR MMIO base address
+#define PCH_SPI_MMIO_SIZE 0x00001000 ///< 4KB
+#define PCH_SERIAL_IO_BASE_ADDRESS 0xFE020000 ///< SerialIo MMIO base address
+#define PCH_SERIAL_IO_MMIO_SIZE 0x00016000 ///< 88KB
+#define PCH_THERMAL_BASE_ADDRESS 0xFE03C000 ///< Thermal Device in ACPI mode
+#define PCH_THERMAL_MMIO_SIZE 0x00001000 ///< 4KB
+#define PCH_TRACE_HUB_FW_BASE_ADDRESS 0xFE0C0000 ///< TraceHub FW MMIO base address
+#define PCH_TRACE_HUB_FW_MMIO_SIZE 0x00040000 ///< 256KB
+#define PCH_TRACE_HUB_MTB_BASE_ADDRESS 0xFE100000 ///< TraceHub MTB MMIO base address
+#define PCH_TRACE_HUB_MTB_MMIO_SIZE 0x00100000 ///< 1MB
+#define PCH_TRACE_HUB_SW_BASE_ADDRESS 0xFE200000 ///< TraceHub SW MMIO base address
+#define PCH_TRACE_HUB_SW_MMIO_SIZE 0x00200000 ///< 2MB
+#define PCH_CIO2_BASE_ADDRESS 0xFE400000 ///< CIO2 MMIO BAR in ACPI mode
+#define PCH_CIO2_MMIO_SIZE 0x00010000 ///< 64KB
+#define PCH_TEMP_BASE_ADDRESS 0xFE600000 ///< preserved temp address for misc usage
+#define PCH_TEMP_MMIO_SIZE 0x00200000 ///< 2MB
+
+#define RCRB 0xFED1C000
+#define SPIBAR 0x3800
+
+#endif // _PCH_PRESERVED_RESOURCES_H_
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
new file mode 100644
index 0000000000..cb5f26c47b
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Protocol/Spi.h
@@ -0,0 +1,295 @@
+/** @file
+ This file defines the PCH SPI Protocol which implements the
+ Intel(R) PCH SPI Host Controller Compatibility Interface.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_PROTOCOL_H_
+#define _PCH_SPI_PROTOCOL_H_
+
+//
+// Extern the GUID for protocol users.
+//
+extern EFI_GUID gEfiSpiProtocolGuid;
+extern EFI_GUID gEfiSmmSpiProtocolGuid;
+
+//
+// Forward reference for ANSI C compatibility
+//
+typedef struct _PCH_SPI_PROTOCOL EFI_SPI_PROTOCOL;
+
+//
+// SPI protocol data structures and definitions
+//
+
+/**
+ Flash Region Type
+**/
+typedef enum {
+ FlashRegionDescriptor,
+ FlashRegionBios,
+ FlashRegionMe,
+ FlashRegionGbE,
+ FlashRegionPlatformData,
+ FlashRegionDer,
+ FlashRegionAll,
+ FlashRegionMax
+} FLASH_REGION_TYPE;
+
+
+//
+// Protocol member functions
+//
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write data to the flash part. Remark: Erase may be needed before write to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_WRITE) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_ERASE) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ );
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_SFDP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ );
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_JEDEC_ID) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ );
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_WRITE_STATUS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ );
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_FLASH_READ_STATUS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ );
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_GET_REGION_ADDRESS) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ );
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_READ_PCH_SOFTSTRAP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+typedef
+EFI_STATUS
+(EFIAPI *PCH_SPI_READ_CPU_SOFTSTRAP) (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ These protocols/PPI allows a platform module to perform SPI operations through the
+ Intel PCH SPI Host Controller Interface.
+**/
+struct _PCH_SPI_PROTOCOL {
+ /**
+ This member specifies the revision of this structure. This field is used to
+ indicate backwards compatible changes to the protocol.
+ **/
+ UINT8 Revision;
+ PCH_SPI_FLASH_READ FlashRead; ///< Read data from the flash part.
+ PCH_SPI_FLASH_WRITE FlashWrite; ///< Write data to the flash part. Remark: Erase may be needed before write to the flash part.
+ PCH_SPI_FLASH_ERASE FlashErase; ///< Erase some area on the flash part.
+ PCH_SPI_FLASH_READ_SFDP FlashReadSfdp; ///< Read SFDP data from the flash part.
+ PCH_SPI_FLASH_READ_JEDEC_ID FlashReadJedecId; ///< Read Jedec Id from the flash part.
+ PCH_SPI_FLASH_WRITE_STATUS FlashWriteStatus; ///< Write the status register in the flash part.
+ PCH_SPI_FLASH_READ_STATUS FlashReadStatus; ///< Read status register in the flash part.
+ PCH_SPI_GET_REGION_ADDRESS GetRegionAddress; ///< Get the SPI region base and size
+ PCH_SPI_READ_PCH_SOFTSTRAP ReadPchSoftStrap; ///< Read PCH Soft Strap Values
+ PCH_SPI_READ_CPU_SOFTSTRAP ReadCpuSoftStrap; ///< Read CPU Soft Strap Values
+};
+
+/**
+ PCH SPI PPI/PROTOCOL revision number
+
+ Revision 1: Initial version
+**/
+#define PCH_SPI_SERVICES_REVISION 1
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
new file mode 100644
index 0000000000..e08721f405
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsPmc.h
@@ -0,0 +1,647 @@
+/** @file
+ Register names for PCH PMC device
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values within the bits
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, PCH registers are denoted by "_PCH_" in register names
+ - Registers / bits that are different between PCH generations are denoted by
+ "_PCH_[generation_name]_" in register/bit names.
+ - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit names.
+ Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit names.
+ e.g., "_PCH_H_", "_PCH_LP_"
+ Registers / bits names without _H_ or _LP_ apply for both H and LP.
+ - Registers / bits that are different between SKUs are denoted by "_[SKU_name]"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a PCH generation will be just named
+ as "_PCH_" without [generation_name] inserted.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_REGS_PMC_H_
+#define _PCH_REGS_PMC_H_
+
+//
+// PMC Registers (D31:F2)
+//
+#define PCI_DEVICE_NUMBER_PCH_PMC 31
+#define PCI_FUNCTION_NUMBER_PCH_PMC 2
+
+#define R_PCH_PMC_PM_DATA_BAR 0x10
+#define B_PCH_PMC_PM_DATA_BAR 0xFFFFC000
+#define R_PCH_PMC_ACPI_BASE 0x40
+#define B_PCH_PMC_ACPI_BASE_BAR 0xFFFC
+#define R_PCH_PMC_ACPI_CNT 0x44
+#define B_PCH_PMC_ACPI_CNT_PWRM_EN BIT8 ///< PWRM enable
+#define B_PCH_PMC_ACPI_CNT_ACPI_EN BIT7 ///< ACPI eanble
+#define B_PCH_PMC_ACPI_CNT_SCIS (BIT2 | BIT1 | BIT0) ///< SCI IRQ select
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ9 0
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ10 1
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ11 2
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ20 4
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ21 5
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ22 6
+#define V_PCH_PMC_ACPI_CNT_SCIS_IRQ23 7
+#define R_PCH_PMC_PWRM_BASE 0x48
+#define B_PCH_PMC_PWRM_BASE_BAR 0xFFFF0000 ///< PWRM must be 64KB alignment to align the source decode.
+#define R_PCH_PMC_GEN_PMCON_A 0xA0
+#define B_PCH_PMC_GEN_PMCON_A_DC_PP_DIS BIT30
+#define B_PCH_PMC_GEN_PMCON_A_DSX_PP_DIS BIT29
+#define B_PCH_PMC_GEN_PMCON_A_AG3_PP_EN BIT28
+#define B_PCH_PMC_GEN_PMCON_A_SX_PP_EN BIT27
+#define B_PCH_PMC_GEN_PMCON_A_DISB BIT23
+#define B_PCH_PMC_GEN_PMCON_A_MEM_SR BIT21
+#define B_PCH_PMC_GEN_PMCON_A_MS4V BIT18
+#define B_PCH_PMC_GEN_PMCON_A_GBL_RST_STS BIT16
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_OPI_PLL_SD_INC0 BIT13
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_SPXB_CG_INC0 BIT12
+#define B_PCH_PMC_GEN_PMCON_A_BIOS_PCI_EXP_EN BIT10
+#define B_PCH_PMC_GEN_PMCON_A_PWRBTN_LVL BIT9
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_C0 BIT7
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_OPI_ON BIT6
+#define B_PCH_PMC_GEN_PMCON_A_ALLOW_L1LOW_BCLKREQ_ON BIT5
+#define B_PCH_PMC_GEN_PMCON_A_SMI_LOCK BIT4
+#define B_PCH_PMC_GEN_PMCON_A_ESPI_SMI_LOCK BIT3 ///< ESPI SMI lock
+#define B_PCH_PMC_GEN_PMCON_A_PER_SMI_SEL 0x0003
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_64S 0x0000
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_32S 0x0001
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_16S 0x0002
+#define V_PCH_PMC_GEN_PMCON_A_PER_SMI_8S 0x0003
+#define R_PCH_PMC_GEN_PMCON_B 0xA4
+#define B_PCH_PMC_GEN_PMCON_B_SLPSX_STR_POL_LOCK BIT18 ///< Lock down SLP_S3/SLP_S4 Minimum Assertion width
+#define B_PCH_PMC_GEN_PMCON_B_ACPI_BASE_LOCK BIT17 ///< Lock ACPI BASE at 0x40, only cleared by reset when set
+#define B_PCH_PMC_GEN_PMCON_B_PM_DATA_BAR_DIS BIT16
+#define B_PCH_PMC_GEN_PMCON_B_PME_B0_S5_DIS BIT15
+#define B_PCH_PMC_GEN_PMCON_B_SUS_PWR_FLR BIT14
+#define B_PCH_PMC_GEN_PMCON_B_WOL_EN_OVRD BIT13
+#define B_PCH_PMC_GEN_PMCON_B_DISABLE_SX_STRETCH BIT12
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW 0xC00
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_60US 0x000
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_1MS 0x400
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_50MS 0x800
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S3_MAW_2S 0xC00
+#define B_PCH_PMC_GEN_PMCON_B_HOST_RST_STS BIT9
+#define B_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL 0xC0
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_64MS 0xC0
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_32MS 0x80
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_16MS 0x40
+#define V_PCH_PMC_GEN_PMCON_B_SWSMI_RTSL_1_5MS 0x00
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW 0x30
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_1S 0x30
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_2S 0x20
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_3S 0x10
+#define V_PCH_PMC_GEN_PMCON_B_SLP_S4_MAW_4S 0x00
+#define B_PCH_PMC_GEN_PMCON_B_SLP_S4_ASE BIT3
+#define B_PCH_PMC_GEN_PMCON_B_RTC_PWR_STS BIT2
+#define B_PCH_PMC_GEN_PMCON_B_PWR_FLR BIT1
+#define B_PCH_PMC_GEN_PMCON_B_AFTERG3_EN BIT0
+#define R_PCH_PMC_BM_CX_CNF 0xA8
+#define B_PCH_PMC_BM_CX_CNF_STORAGE_BREAK_EN BIT31
+#define B_PCH_PMC_BM_CX_CNF_PCIE_BREAK_EN BIT30
+#define B_PCH_PMC_BM_CX_CNF_AZ_BREAK_EN BIT24
+#define B_PCH_PMC_BM_CX_CNF_DPSN_BREAK_EN BIT19
+#define B_PCH_PMC_BM_CX_CNF_XHCI_BREAK_EN BIT17
+#define B_PCH_PMC_BM_CX_CNF_SATA3_BREAK_EN BIT16
+#define B_PCH_PMC_BM_CX_CNF_SCRATCHPAD BIT15
+#define B_PCH_PMC_BM_CX_CNF_PHOLD_BM_STS_BLOCK BIT14
+#define B_PCH_PMC_BM_CX_CNF_MASK_CF BIT11
+#define B_PCH_PMC_BM_CX_CNF_BM_STS_ZERO_EN BIT10
+#define B_PCH_PMC_BM_CX_CNF_PM_SYNC_MSG_MODE BIT9
+#define R_PCH_PMC_ETR3 0xAC
+#define B_PCH_PMC_ETR3_CF9LOCK BIT31 ///< CF9h Lockdown
+#define B_PCH_PMC_ETR3_USB_CACHE_DIS BIT21
+#define B_PCH_PMC_ETR3_CF9GR BIT20 ///< CF9h Global Reset
+#define B_PCH_PMC_ETR3_SKIP_HOST_RST_HS BIT19
+#define B_PCH_PMC_ETR3_CWORWRE BIT18
+
+//
+// ACPI and legacy I/O register offsets from ACPIBASE
+//
+#define R_PCH_ACPI_PM1_STS 0x00
+#define S_PCH_ACPI_PM1_STS 2
+#define B_PCH_ACPI_PM1_STS_WAK BIT15
+#define B_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS BIT14
+#define B_PCH_ACPI_PM1_STS_PRBTNOR BIT11
+#define B_PCH_ACPI_PM1_STS_RTC BIT10
+#define B_PCH_ACPI_PM1_STS_PWRBTN BIT8
+#define B_PCH_ACPI_PM1_STS_GBL BIT5
+#define B_PCH_ACPI_PM1_STS_BM BIT4
+#define B_PCH_ACPI_PM1_STS_TMROF BIT0
+#define N_PCH_ACPI_PM1_STS_WAK 15
+#define N_PCH_ACPI_PM1_STS_PCIEXP_WAKE_STS 14
+#define N_PCH_ACPI_PM1_STS_PRBTNOR 11
+#define N_PCH_ACPI_PM1_STS_RTC 10
+#define N_PCH_ACPI_PM1_STS_PWRBTN 8
+#define N_PCH_ACPI_PM1_STS_GBL 5
+#define N_PCH_ACPI_PM1_STS_BM 4
+#define N_PCH_ACPI_PM1_STS_TMROF 0
+
+#define R_PCH_ACPI_PM1_EN 0x02
+#define S_PCH_ACPI_PM1_EN 2
+#define B_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS BIT14
+#define B_PCH_ACPI_PM1_EN_RTC BIT10
+#define B_PCH_ACPI_PM1_EN_PWRBTN BIT8
+#define B_PCH_ACPI_PM1_EN_GBL BIT5
+#define B_PCH_ACPI_PM1_EN_TMROF BIT0
+#define N_PCH_ACPI_PM1_EN_PCIEXP_WAKE_DIS 14
+#define N_PCH_ACPI_PM1_EN_RTC 10
+#define N_PCH_ACPI_PM1_EN_PWRBTN 8
+#define N_PCH_ACPI_PM1_EN_GBL 5
+#define N_PCH_ACPI_PM1_EN_TMROF 0
+
+#define R_PCH_ACPI_PM1_CNT 0x04
+#define S_PCH_ACPI_PM1_CNT 4
+#define B_PCH_ACPI_PM1_CNT_SLP_EN BIT13
+#define B_PCH_ACPI_PM1_CNT_SLP_TYP (BIT12 | BIT11 | BIT10)
+#define V_PCH_ACPI_PM1_CNT_S0 0
+#define V_PCH_ACPI_PM1_CNT_S1 BIT10
+#define V_PCH_ACPI_PM1_CNT_S3 (BIT12 | BIT10)
+#define V_PCH_ACPI_PM1_CNT_S4 (BIT12 | BIT11)
+#define V_PCH_ACPI_PM1_CNT_S5 (BIT12 | BIT11 | BIT10)
+#define B_PCH_ACPI_PM1_CNT_GBL_RLS BIT2
+#define B_PCH_ACPI_PM1_CNT_BM_RLD BIT1
+#define B_PCH_ACPI_PM1_CNT_SCI_EN BIT0
+
+#define R_PCH_ACPI_PM1_TMR 0x08
+#define V_PCH_ACPI_TMR_FREQUENCY 3579545
+#define B_PCH_ACPI_PM1_TMR_VAL 0xFFFFFF
+#define V_PCH_ACPI_PM1_TMR_MAX_VAL 0x1000000 ///< The timer is 24 bit overflow
+
+#define R_PCH_SMI_EN 0x30
+#define S_PCH_SMI_EN 4
+#define B_PCH_SMI_EN_LEGACY_USB3 BIT31
+#define B_PCH_SMI_EN_GPIO_UNLOCK_SMI BIT27
+#define B_PCH_SMI_EN_LEGACY_USB2 BIT17
+#define B_PCH_SMI_EN_PERIODIC BIT14
+#define B_PCH_SMI_EN_TCO BIT13
+#define B_PCH_SMI_EN_MCSMI BIT11
+#define B_PCH_SMI_EN_BIOS_RLS BIT7
+#define B_PCH_SMI_EN_SWSMI_TMR BIT6
+#define B_PCH_SMI_EN_APMC BIT5
+#define B_PCH_SMI_EN_ON_SLP_EN BIT4
+#define B_PCH_SMI_EN_LEGACY_USB BIT3
+#define B_PCH_SMI_EN_BIOS BIT2
+#define B_PCH_SMI_EN_EOS BIT1
+#define B_PCH_SMI_EN_GBL_SMI BIT0
+#define N_PCH_SMI_EN_LEGACY_USB3 31
+#define N_PCH_SMI_EN_ESPI 28
+#define N_PCH_SMI_EN_GPIO_UNLOCK 27
+#define N_PCH_SMI_EN_INTEL_USB2 18
+#define N_PCH_SMI_EN_LEGACY_USB2 17
+#define N_PCH_SMI_EN_PERIODIC 14
+#define N_PCH_SMI_EN_TCO 13
+#define N_PCH_SMI_EN_MCSMI 11
+#define N_PCH_SMI_EN_BIOS_RLS 7
+#define N_PCH_SMI_EN_SWSMI_TMR 6
+#define N_PCH_SMI_EN_APMC 5
+#define N_PCH_SMI_EN_ON_SLP_EN 4
+#define N_PCH_SMI_EN_LEGACY_USB 3
+#define N_PCH_SMI_EN_BIOS 2
+#define N_PCH_SMI_EN_EOS 1
+#define N_PCH_SMI_EN_GBL_SMI 0
+
+#define R_PCH_SMI_STS 0x34
+#define S_PCH_SMI_STS 4
+#define B_PCH_SMI_STS_LEGACY_USB3 BIT31
+#define B_PCH_SMI_STS_GPIO_UNLOCK BIT27
+#define B_PCH_SMI_STS_SPI BIT26
+#define B_PCH_SMI_STS_MONITOR BIT21
+#define B_PCH_SMI_STS_PCI_EXP BIT20
+#define B_PCH_SMI_STS_PATCH BIT19
+#define B_PCH_SMI_STS_INTEL_USB2 BIT18
+#define B_PCH_SMI_STS_LEGACY_USB2 BIT17
+#define B_PCH_SMI_STS_SMBUS BIT16
+#define B_PCH_SMI_STS_SERIRQ BIT15
+#define B_PCH_SMI_STS_PERIODIC BIT14
+#define B_PCH_SMI_STS_TCO BIT13
+#define B_PCH_SMI_STS_DEVMON BIT12
+#define B_PCH_SMI_STS_MCSMI BIT11
+#define B_PCH_SMI_STS_GPIO_SMI BIT10
+#define B_PCH_SMI_STS_GPE0 BIT9
+#define B_PCH_SMI_STS_PM1_STS_REG BIT8
+#define B_PCH_SMI_STS_SWSMI_TMR BIT6
+#define B_PCH_SMI_STS_APM BIT5
+#define B_PCH_SMI_STS_ON_SLP_EN BIT4
+#define B_PCH_SMI_STS_LEGACY_USB BIT3
+#define B_PCH_SMI_STS_BIOS BIT2
+#define N_PCH_SMI_STS_LEGACY_USB3 31
+#define N_PCH_SMI_STS_ESPI 28
+#define N_PCH_SMI_STS_GPIO_UNLOCK 27
+#define N_PCH_SMI_STS_SPI 26
+#define N_PCH_SMI_STS_MONITOR 21
+#define N_PCH_SMI_STS_PCI_EXP 20
+#define N_PCH_SMI_STS_PATCH 19
+#define N_PCH_SMI_STS_INTEL_USB2 18
+#define N_PCH_SMI_STS_LEGACY_USB2 17
+#define N_PCH_SMI_STS_SMBUS 16
+#define N_PCH_SMI_STS_SERIRQ 15
+#define N_PCH_SMI_STS_PERIODIC 14
+#define N_PCH_SMI_STS_TCO 13
+#define N_PCH_SMI_STS_DEVMON 12
+#define N_PCH_SMI_STS_MCSMI 11
+#define N_PCH_SMI_STS_GPIO_SMI 10
+#define N_PCH_SMI_STS_GPE0 9
+#define N_PCH_SMI_STS_PM1_STS_REG 8
+#define N_PCH_SMI_STS_SWSMI_TMR 6
+#define N_PCH_SMI_STS_APM 5
+#define N_PCH_SMI_STS_ON_SLP_EN 4
+#define N_PCH_SMI_STS_LEGACY_USB 3
+#define N_PCH_SMI_STS_BIOS 2
+
+#define R_PCH_ACPI_GPE_CNTL 0x40
+#define B_PCH_ACPI_GPE_CNTL_SWGPE_CTRL BIT17
+
+#define R_PCH_DEVACT_STS 0x44
+#define S_PCH_DEVACT_STS 2
+#define B_PCH_DEVACT_STS_MASK 0x13E1
+#define B_PCH_DEVACT_STS_KBC BIT12
+#define B_PCH_DEVACT_STS_PIRQDH BIT9
+#define B_PCH_DEVACT_STS_PIRQCG BIT8
+#define B_PCH_DEVACT_STS_PIRQBF BIT7
+#define B_PCH_DEVACT_STS_PIRQAE BIT6
+#define B_PCH_DEVACT_STS_D0_TRP BIT0
+#define N_PCH_DEVACT_STS_KBC 12
+#define N_PCH_DEVACT_STS_PIRQDH 9
+#define N_PCH_DEVACT_STS_PIRQCG 8
+#define N_PCH_DEVACT_STS_PIRQBF 7
+#define N_PCH_DEVACT_STS_PIRQAE 6
+
+#define R_PCH_ACPI_PM2_CNT 0x50
+#define B_PCH_ACPI_PM2_CNT_ARB_DIS BIT0
+
+#define R_PCH_OC_WDT_CTL 0x54
+#define B_PCH_OC_WDT_CTL_RLD BIT31
+#define B_PCH_OC_WDT_CTL_ICCSURV_STS BIT25
+#define B_PCH_OC_WDT_CTL_NO_ICCSURV_STS BIT24
+#define B_PCH_OC_WDT_CTL_FORCE_ALL BIT15
+#define B_PCH_OC_WDT_CTL_EN BIT14
+#define B_PCH_OC_WDT_CTL_ICCSURV BIT13
+#define B_PCH_OC_WDT_CTL_LCK BIT12
+#define B_PCH_OC_WDT_CTL_TOV_MASK 0x3FF
+#define B_PCH_OC_WDT_CTL_FAILURE_STS BIT23
+#define B_PCH_OC_WDT_CTL_UNXP_RESET_STS BIT22
+#define B_PCH_OC_WDT_CTL_AFTER_POST 0x3F0000
+#define V_PCH_OC_WDT_CTL_STATUS_FAILURE 1
+#define V_PCH_OC_WDT_CTL_STATUS_OK 0
+
+#define R_PCH_ACPI_GPE0_STS_31_0 0x80
+#define R_PCH_ACPI_GPE0_STS_63_32 0x84
+#define R_PCH_ACPI_GPE0_STS_95_64 0x88
+#define R_PCH_ACPI_GPE0_STS_127_96 0x8C
+#define S_PCH_ACPI_GPE0_STS_127_96 4
+#define B_PCH_ACPI_GPE0_STS_127_96_WADT BIT18
+#define B_PCH_ACPI_GPE0_STS_127_96_LAN_WAKE BIT16
+#define B_PCH_ACPI_GPE0_STS_127_96_PME_B0 BIT13
+#define B_PCH_ACPI_GPE0_STS_127_96_ME_SCI BIT12
+#define B_PCH_ACPI_GPE0_STS_127_96_PME BIT11
+#define B_PCH_ACPI_GPE0_STS_127_96_BATLOW BIT10
+#define B_PCH_ACPI_GPE0_STS_127_96_PCI_EXP BIT9
+#define B_PCH_ACPI_GPE0_STS_127_96_RI BIT8
+#define B_PCH_ACPI_GPE0_STS_127_96_SMB_WAK BIT7
+#define B_PCH_ACPI_GPE0_STS_127_96_TC0SCI BIT6
+#define B_PCH_ACPI_GPE0_STS_127_96_SWGPE BIT2
+#define B_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG BIT1
+#define N_PCH_ACPI_GPE0_STS_127_96_PME_B0 13
+#define N_PCH_ACPI_GPE0_STS_127_96_PME 11
+#define N_PCH_ACPI_GPE0_STS_127_96_BATLOW 10
+#define N_PCH_ACPI_GPE0_STS_127_96_PCI_EXP 9
+#define N_PCH_ACPI_GPE0_STS_127_96_RI 8
+#define N_PCH_ACPI_GPE0_STS_127_96_SMB_WAK 7
+#define N_PCH_ACPI_GPE0_STS_127_96_TC0SCI 6
+#define N_PCH_ACPI_GPE0_STS_127_96_SWGPE 2
+#define N_PCH_ACPI_GPE0_STS_127_96_HOT_PLUG 1
+
+#define R_PCH_ACPI_GPE0_EN_31_0 0x90
+#define R_PCH_ACPI_GPE0_EN_63_32 0x94
+#define R_PCH_ACPI_GPE0_EN_95_64 0x98
+#define R_PCH_ACPI_GPE0_EN_127_96 0x9C
+#define S_PCH_ACPI_GPE0_EN_127_96 4
+#define B_PCH_ACPI_GPE0_EN_127_96_WADT BIT18
+#define B_PCH_ACPI_GPE0_EN_127_96_LAN_WAKE BIT16
+#define B_PCH_ACPI_GPE0_EN_127_96_PME_B0 BIT13
+#define B_PCH_ACPI_GPE0_EN_127_96_ME_SCI BIT12
+#define B_PCH_ACPI_GPE0_EN_127_96_PME BIT11
+#define B_PCH_ACPI_GPE0_EN_127_96_BATLOW BIT10
+#define B_PCH_ACPI_GPE0_EN_127_96_PCI_EXP BIT9
+#define B_PCH_ACPI_GPE0_EN_127_96_RI BIT8
+#define B_PCH_ACPI_GPE0_EN_127_96_TC0SCI BIT6
+#define B_PCH_ACPI_GPE0_EN_127_96_SWGPE BIT2
+#define B_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG BIT1
+#define N_PCH_ACPI_GPE0_EN_127_96_PME_B0 13
+#define N_PCH_ACPI_GPE0_EN_127_96_USB3 12
+#define N_PCH_ACPI_GPE0_EN_127_96_PME 11
+#define N_PCH_ACPI_GPE0_EN_127_96_BATLOW 10
+#define N_PCH_ACPI_GPE0_EN_127_96_PCI_EXP 9
+#define N_PCH_ACPI_GPE0_EN_127_96_RI 8
+#define N_PCH_ACPI_GPE0_EN_127_96_TC0SCI 6
+#define N_PCH_ACPI_GPE0_EN_127_96_SWGPE 2
+#define N_PCH_ACPI_GPE0_EN_127_96_HOT_PLUG 1
+
+
+//
+// TCO register I/O map
+//
+#define R_PCH_TCO_RLD 0x0
+#define R_PCH_TCO_DAT_IN 0x2
+#define R_PCH_TCO_DAT_OUT 0x3
+#define R_PCH_TCO1_STS 0x04
+#define S_PCH_TCO1_STS 2
+#define B_PCH_TCO1_STS_DMISERR BIT12
+#define B_PCH_TCO1_STS_DMISMI BIT10
+#define B_PCH_TCO1_STS_DMISCI BIT9
+#define B_PCH_TCO1_STS_BIOSWR BIT8
+#define B_PCH_TCO1_STS_NEWCENTURY BIT7
+#define B_PCH_TCO1_STS_TIMEOUT BIT3
+#define B_PCH_TCO1_STS_TCO_INT BIT2
+#define B_PCH_TCO1_STS_SW_TCO_SMI BIT1
+#define B_PCH_TCO1_STS_NMI2SMI BIT0
+#define N_PCH_TCO1_STS_DMISMI 10
+#define N_PCH_TCO1_STS_BIOSWR 8
+#define N_PCH_TCO1_STS_NEWCENTURY 7
+#define N_PCH_TCO1_STS_TIMEOUT 3
+#define N_PCH_TCO1_STS_SW_TCO_SMI 1
+#define N_PCH_TCO1_STS_NMI2SMI 0
+
+#define R_PCH_TCO2_STS 0x06
+#define S_PCH_TCO2_STS 2
+#define B_PCH_TCO2_STS_SMLINK_SLV_SMI BIT4
+#define B_PCH_TCO2_STS_BAD_BIOS BIT3
+#define B_PCH_TCO2_STS_BOOT BIT2
+#define B_PCH_TCO2_STS_SECOND_TO BIT1
+#define B_PCH_TCO2_STS_INTRD_DET BIT0
+#define N_PCH_TCO2_STS_INTRD_DET 0
+
+#define R_PCH_TCO1_CNT 0x08
+#define S_PCH_TCO1_CNT 2
+#define B_PCH_TCO_CNT_LOCK BIT12
+#define B_PCH_TCO_CNT_TMR_HLT BIT11
+#define B_PCH_TCO_CNT_NMI2SMI_EN BIT9
+#define B_PCH_TCO_CNT_NMI_NOW BIT8
+#define N_PCH_TCO_CNT_NMI2SMI_EN 9
+
+#define R_PCH_TCO2_CNT 0x0A
+#define S_PCH_TCO2_CNT 2
+#define B_PCH_TCO2_CNT_OS_POLICY 0x0030
+#define B_PCH_TCO2_CNT_GPI11_ALERT_DISABLE 0x0008
+#define B_PCH_TCO2_CNT_INTRD_SEL 0x0006
+#define N_PCH_TCO2_CNT_INTRD_SEL 2
+
+#define R_PCH_TCO_MESSAGE1 0x0C
+#define R_PCH_TCO_MESSAGE2 0x0D
+#define R_PCH_TCO_WDCNT 0x0E
+#define R_PCH_TCO_SW_IRQ_GEN 0x10
+#define B_PCH_TCO_IRQ12_CAUSE BIT1
+#define B_PCH_TCO_IRQ1_CAUSE BIT0
+#define R_PCH_TCO_TMR 0x12
+
+//
+// PWRM Registers
+//
+#define R_PCH_WADT_AC 0x0 ///< Wake Alarm Device Timer: AC
+#define R_PCH_WADT_DC 0x4 ///< Wake Alarm Device Timer: DC
+#define R_PCH_WADT_EXP_AC 0x8 ///< Wake Alarm Device Expired Timer: AC
+#define R_PCH_WADT_EXP_DC 0xC ///< Wake Alarm Device Expired Timer: DC
+#define R_PCH_PWRM_PRSTS 0x10 ///< Power and Reset Status
+#define B_PCH_PWRM_PRSTS_VE_WD_TMR_STS BIT7 ///< VE Watchdog Timer Status
+#define B_PCH_PWRM_PRSTS_WOL_OVR_WK_STS BIT5
+#define B_PCH_PWRM_PRSTS_FIELD_1 BIT4
+#define B_PCH_PWRM_PRSTS_ME_WAKE_STS BIT0
+#define R_PCH_PWRM_14 0x14
+#define R_PCH_PWRM_CFG 0x18 ///< Power Management Configuration
+#define B_PCH_PWRM_CFG_ALLOW_24_OSC_SD BIT29 ///< Allow 24MHz Crystal Oscillator Shutdown
+#define B_PCH_PWRM_CFG_ALLOW_USB2_CORE_PG BIT25 ///< Allow USB2 Core Power Gating
+#define B_PCH_PWRM_CFG_RTC_DS_WAKE_DIS BIT21 ///< RTC Wake from Deep S4/S5 Disable
+#define B_PCH_PWRM_CFG_SSMAW_MASK (BIT19 | BIT18) ///< SLP_SUS# Min Assertion Width
+#define V_PCH_PWRM_CFG_SSMAW_4S (BIT19 | BIT18) ///< 4 seconds
+#define V_PCH_PWRM_CFG_SSMAW_1S BIT19 ///< 1 second
+#define V_PCH_PWRM_CFG_SSMAW_0_5S BIT18 ///< 0.5 second (500ms)
+#define V_PCH_PWRM_CFG_SSMAW_0S 0 ///< 0 second
+#define B_PCH_PWRM_CFG_SAMAW_MASK (BIT17 | BIT16) ///< SLP_A# Min Assertion Width
+#define V_PCH_PWRM_CFG_SAMAW_2S (BIT17 | BIT16) ///< 2 seconds
+#define V_PCH_PWRM_CFG_SAMAW_98ms BIT17 ///< 98ms
+#define V_PCH_PWRM_CFG_SAMAW_4S BIT16 ///< 4 seconds
+#define V_PCH_PWRM_CFG_SAMAW_0S 0 ///< 0 second
+#define B_PCH_PWRM_CFG_RPCD_MASK (BIT9 | BIT8) ///< Reset Power Cycle Duration
+#define V_PCH_PWRM_CFG_RPCD_1S (BIT9 | BIT8) ///< 1-2 seconds
+#define V_PCH_PWRM_CFG_RPCD_2S BIT9 ///< 2-3 seconds
+#define V_PCH_PWRM_CFG_RPCD_3S BIT8 ///< 3-4 seconds
+#define V_PCH_PWRM_CFG_RPCD_4S 0 ///< 4-5 seconds (Default)
+#define R_PCH_PWRM_PCH_PM_STS 0x1C ///< Contains misc. fields used to record PCH power management events
+#define B_PCH_PWRM_PCH_PM_STS_PMC_MSG_FULL_STS BIT24 ///< MTPMC transport mechanism full indication
+#define R_PCH_PWRM_MTPMC 0x20 ///< Message to PMC
+#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_0_15 0xE ///< Command to override lanes 0-15 power gating
+#define V_PCH_PWRM_MTPMC_COMMAND_PG_LANE_16_31 0xF ///< Command to override lanes 16-31 power gating
+#define B_PCH_PWRM_MTPMC_PG_CMD_DATA 0xFFFF0000 ///< Data part of PowerGate Message to PMC
+#define N_PCH_PWRM_MTPMC_PG_CMD_DATA 16
+#define R_PCH_PWRM_PCH_PM_STS2 0x24 ///< PCH Power Management Status
+#define R_PCH_PWRM_S3_PWRGATE_POL 0x28 ///< S3 Power Gating Policies
+#define B_PCH_PWRM_S3DC_GATE_SUS BIT1 ///< Deep S3 Enable in DC Mode
+#define B_PCH_PWRM_S3AC_GATE_SUS BIT0 ///< Deep S3 Enable in AC Mode
+#define R_PCH_PWRM_S4_PWRGATE_POL 0x2C ///< Deep S4 Power Policies
+#define B_PCH_PWRM_S4DC_GATE_SUS BIT1 ///< Deep S4 Enable in DC Mode
+#define B_PCH_PWRM_S4AC_GATE_SUS BIT0 ///< Deep S4 Enable in AC Mode
+#define R_PCH_PWRM_S5_PWRGATE_POL 0x30 ///< Deep S5 Power Policies
+#define B_PCH_PWRM_S5DC_GATE_SUS BIT15 ///< Deep S5 Enable in DC Mode
+#define B_PCH_PWRM_S5AC_GATE_SUS BIT14 ///< Deep S5 Enable in AC Mode
+#define R_PCH_PWRM_DSX_CFG 0x34 ///< Deep SX Configuration
+#define B_PCH_PWRM_DSX_CFG_WAKE_PIN_DSX_EN BIT2 ///< WAKE# Pin DeepSx Enable
+#define B_PCH_PWRM_DSX_CFG_ACPRES_PD_DSX_DIS BIT1 ///< AC_PRESENT pin pulldown in DeepSx disable
+#define B_PCH_PWRM_DSX_CFG_LAN_WAKE_EN BIT0 ///< LAN_WAKE Pin DeepSx Enable
+#define R_PCH_PWRM_CFG2 0x3C ///< Power Management Configuration Reg 2
+#define B_PCH_PWRM_CFG2_PBOP (BIT31 | BIT30 | BIT29) ///< Power Button Override Period (PBOP)
+#define N_PCH_PWRM_CFG2_PBOP 29 ///< Power Button Override Period (PBOP)
+#define B_PCH_PWRM_CFG2_PB_DIS BIT28 ///< Power Button Native Mode Disable (PB_DIS)
+#define B_PCH_PWRM_CFG2_DRAM_RESET_CTL BIT26 ///< DRAM RESET# control
+#define R_PCH_PWRM_EN_SN_SLOW_RING 0x48 ///< Enable Snoop Request to SLOW_RING
+#define R_PCH_PWRM_EN_SN_SLOW_RING2 0x4C ///< Enable Snoop Request to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_SN_SA 0x50 ///< Enable Snoop Request to SA
+#define R_PCH_PWRM_EN_SN_SA2 0x54 ///< Enable Snoop Request to SA 2nd Reg
+#define R_PCH_PWRM_EN_SN_SLOW_RING_CF 0x58 ///< Enable Snoop Request to SLOW_RING_CF
+#define R_PCH_PWRM_EN_NS_SA 0x68 ///< Enable Non-Snoop Request to SA
+#define R_PCH_PWRM_EN_CW_SLOW_RING 0x80 ///< Enable Clock Wake to SLOW_RING
+#define R_PCH_PWRM_EN_CW_SLOW_RING2 0x84 ///< Enable Clock Wake to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_CW_SA 0x88 ///< Enable Clock Wake to SA
+#define R_PCH_PWRM_EN_CW_SA2 0x8C ///< Enable Clock Wake to SA 2nd Reg
+#define R_PCH_PWRM_EN_CW_SLOW_RING_CF 0x98 ///< Enable Clock Wake to SLOW_RING_CF
+#define R_PCH_PWRM_EN_PA_SLOW_RING 0xA8 ///< Enable Pegged Active to SLOW_RING
+#define R_PCH_PWRM_EN_PA_SLOW_RING2 0xAC ///< Enable Pegged Active to SLOW_RING 2nd Reg
+#define R_PCH_PWRM_EN_PA_SA 0xB0 ///< Enable Pegged Active to SA
+#define R_PCH_PWRM_EN_PA_SA2 0xB4 ///< Enable Pegged Active to SA 2nd Reg
+#define R_PCH_PWRM_EN_MISC_EVENT 0xC0 ///< Enable Misc PM_SYNC Events
+#define R_PCH_PWRM_PMSYNC_TPR_CONFIG 0xC4
+#define B_PCH_PWRM_PMSYNC_TPR_CONFIG_LOCK BIT31
+#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_EN BIT26
+#define B_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE (BIT25 | BIT24)
+#define N_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE 24
+#define V_PCH_PWRM_PMSYNC_PCH2CPU_TT_STATE_1 1
+#define R_PCH_PWRM_PMSYNC_MISC_CFG 0xC8
+#define B_PCH_PWRM_PMSYNC_PM_SYNC_LOCK BIT15 ///< PM_SYNC Configuration Lock
+#define B_PCH_PWRM_PMSYNC_GPIO_D_SEL BIT11
+#define B_PCH_PWRM_PMSYNC_GPIO_C_SEL BIT10
+#define R_PCH_PWRM_PM_SYNC_STATE_HYS 0xD0 ///< PM_SYNC State Hysteresis
+#define R_PCH_PWRM_PM_SYNC_MODE 0xD4 ///< PM_SYNC Pin Mode
+#define R_PCH_PWRM_CFG3 0xE0 ///< Power Management Configuration Reg 3
+#define B_PCH_PWRM_CFG3_DSX_WLAN_PP_EN BIT16 ///< Deep-Sx WLAN Phy Power Enable
+#define B_PCH_PWRM_CFG3_HOST_WLAN_PP_EN BIT17 ///< Host Wireless LAN Phy Power Enable
+#define B_PCH_PWRM_CFG3_PWRG_LOCK BIT2 ///< Lock power gating override messages
+#define R_PCH_PWRM_PM_DOWN_PPB_CFG 0xE4 ///< PM_DOWN PCH_POWER_BUDGET CONFIGURATION
+#define R_PCH_PWRM_CFG4 0xE8 ///< Power Management Configuration Reg 4
+#define B_PCH_PWRM_CFG4_U2_PHY_PG_EN BIT30 ///< USB2 PHY SUS Well Power Gating Enable
+#define B_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR (0x000001FF) ///< CPU I/O VR Ramp Duration, [8:0]
+#define N_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR 0
+#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_70US 0x007
+#define V_PCH_PWRM_CFG4_CPU_IOVR_RAMP_DUR_240US 0x018
+#define R_PCH_PWRM_CPU_EPOC 0xEC
+#define R_PCH_PWRM_VR_MISC_CTL 0x100
+#define B_PCH_PWRM_VR_MISC_CTL_VIDSOVEN BIT3
+#define R_PCH_PWRM_GPIO_CFG 0x120
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW2 (BIT11 | BIT10 | BIT9 | BIT8)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW2 8
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW1 (BIT7 | BIT6 | BIT5 | BIT4)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW1 4
+#define B_PCH_PWRM_GPIO_CFG_GPE0_DW0 (BIT3 | BIT2 | BIT1 | BIT0)
+#define N_PCH_PWRM_GPIO_CFG_GPE0_DW0 0
+#define R_PCH_PWRM_PM_SYNC_MODE_C0 0xF4 ///< PM_SYNC Pin Mode in C0
+#define R_PCH_PWRM_ACPI_TMR_CTL 0xFC
+#define B_PCH_PWRM_ACPI_TMR_DIS BIT1
+#define R_PCH_PWRM_124 0x124
+#define R_PCH_PWRM_SLP_S0_RESIDENCY_COUNTER 0x13C
+#define R_PCH_PWRM_MODPHY_PM_CFG1 0x200
+#define R_PCH_PWRM_MODPHY_PM_CFG1_MLSXSWPGP 0xFFFF
+#define R_PCH_PWRM_MODPHY_PM_CFG2 0x204 ///< ModPHY Power Management Configuration Reg 2
+#define B_PCH_PWRM_MODPHY_PM_CFG2_MLSPDDGE BIT30 ///< ModPHY Lane SUS Power Domain Dynamic Gating Enable
+#define B_PCH_PWRM_MODPHY_PM_CFG2_EMFC BIT29 ///< Enable ModPHY FET Control
+#define B_PCH_PWRM_MODPHY_PM_CFG2_EFRT (BIT28 | BIT27 | BIT26 | BIT25 | BIT24) ///< External FET Ramp Time
+#define N_PCH_PWRM_MODPHY_PM_CFG2_EFRT 24
+#define V_PCH_PWRM_MODPHY_PM_CFG2_EFRT_200US 0x0A
+#define B_PCH_PWRM_MODPHY_PM_CFG2_ASLOR_UFS BIT16 ///< UFS ModPHY SPD SPD Override
+#define R_PCH_PWRM_MODPHY_PM_CFG3 0x208 ///< ModPHY Power Management Configuration Reg 3
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_UFS BIT16 ///< UFS ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XDCI BIT15 ///< xDCI ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_XHCI BIT14 ///< xHCI ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_GBE BIT13 ///< GbE ModPHY SPD RT Request
+#define B_PCH_PWRM_MODPHY_PM_CFG3_MSPDRTREQ_SATA BIT12 ///< SATA ModPHY SPD RT Request
+#define R_PCH_PWRM_30C 0x30C
+#define R_PCH_PWRM_OBFF_CFG 0x314 ///< OBFF Configuration
+#define R_PCH_PWRM_31C 0x31C
+#define R_PCH_PWRM_CPPM_MISC_CFG 0x320 ///< CPPM Miscellaneous Configuration
+#define R_PCH_PWRM_CPPM_CG_POL1A 0x324 ///< CPPM Clock Gating Policy Reg 1
+#define R_PCH_PWRM_CPPM_CG_POL2A 0x340 ///< CPPM Clock Gating Policy Reg 3
+#define R_PCH_PWRM_34C 0x34C
+#define R_PCH_PWRM_CPPM_CG_POL3A 0x3A8 ///< CPPM Clock Gating Policy Reg 5
+#define B_PCH_PWRM_CPPM_CG_POLXA_CPPM_GX_QUAL BIT30 ///< CPPM Shutdown Qualifier Enable for Clock Source Group X
+#define B_PCH_PWRM_CPPM_CG_POLXA_LTR_GX_THRESH (0x000001FF) ///< LTR Threshold for Clock Source Group X, [8:0]
+#define R_PCH_PWRM_3D0 0x3D0
+#define R_PCH_PWRM_CPPM_MPG_POL1A 0x3E0 ///< CPPM ModPHY Gating Policy Reg 1A
+#define B_PCH_PWRM_CPPM_MPG_POL1A_CPPM_MODPHY_QUAL BIT30 ///< CPPM Shutdown Qualifier Enable for ModPHY
+#define B_PCH_PWRM_CPPM_MPG_POL1A_LT_MODPHY_SEL BIT29 ///< ASLT/PLT Selection for ModPHY
+#define B_PCH_PWRM_CPPM_MPG_POL1A_LTR_MODPHY_THRESH (0x000001FF) ///< LTR Threshold for ModPHY, [8:0]
+#define R_PCH_PWRM_CS_SD_CTL1 0x3E8 ///< Clock Source Shutdown Control Reg 1
+#define B_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG (BIT22 | BIT21 | BIT20) ///< Clock Source 5 Control Configuration
+#define N_PCH_PWRM_CS_SD_CTL1_CS5_CTL_CFG 20
+#define B_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG (BIT2 | BIT1 | BIT0) ///< Clock Source 1 Control Configuration
+#define N_PCH_PWRM_CS_SD_CTL1_CS1_CTL_CFG 0
+#define R_PCH_PWRM_CS_SD_CTL2 0x3EC ///< Clock Source Shutdown Control Reg 2
+#define R_PCH_PWRM_HSWPGCR1 0x5D0
+#define B_PCH_PWRM_SW_PG_CTRL_LOCK BIT31
+#define B_PCH_PWRM_DFX_SW_PG_CTRL BIT0
+#define R_PCH_PWRM_600 0x600
+#define R_PCH_PWRM_604 0x604
+#define R_PCH_PWRM_ST_PG_FDIS_PMC_1 0x620 ///< Static PG Related Function Disable Register 1
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ST_FDIS_LK BIT31 ///< Static Function Disable Lock (ST_FDIS_LK)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_CAM_FDIS_PMC BIT6 ///< Camera Function Disable (PMC Version) (CAM_FDIS_PMC)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_ISH_FDIS_PMC BIT5 ///< SH Function Disable (PMC Version) (ISH_FDIS_PMC)
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_1_GBE_FDIS_PMC BIT0 ///< GBE Function Disable (PMC Version) (GBE_FDIS_PMC)
+#define R_PCH_PWRM_ST_PG_FDIS_PMC_2 0x624 ///< Static Function Disable Control Register 2
+#define V_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_FDIS_PMC 0x7FF ///< Static Function Disable Control Register 2
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI1_FDIS_PMC BIT10 ///< SerialIo Controller GSPI Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_GSPI0_FDIS_PMC BIT9 ///< SerialIo Controller GSPI Device 0 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART2_FDIS_PMC BIT8 ///< SerialIo Controller UART Device 2 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART1_FDIS_PMC BIT7 ///< SerialIo Controller UART Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_UART0_FDIS_PMC BIT6 ///< SerialIo Controller UART Device 0 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C5_FDIS_PMC BIT5 ///< SerialIo Controller I2C Device 5 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C4_FDIS_PMC BIT4 ///< SerialIo Controller I2C Device 4 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C3_FDIS_PMC BIT3 ///< SerialIo Controller I2C Device 3 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C2_FDIS_PMC BIT2 ///< SerialIo Controller I2C Device 2 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C1_FDIS_PMC BIT1 ///< SerialIo Controller I2C Device 1 Function Disable
+#define B_PCH_PWRM_ST_PG_FDIS_PMC_2_SERIALIO_I2C0_FDIS_PMC BIT0 ///< SerialIo Controller I2C Device 0 Function Disable
+#define R_PCH_PWRM_NST_PG_FDIS_1 0x628
+#define B_PCH_PWRM_NST_PG_FDIS_1_SCC_FDIS_PMC BIT25 ///< SCC Function Disable. This is only avaiable in B0 onward.
+#define B_PCH_PWRM_NST_PG_FDIS_1_XDCI_FDIS_PMC BIT24 ///< XDCI Function Disable. This is only avaiable in B0 onward.
+#define B_PCH_PWRM_NST_PG_FDIS_1_ADSP_FDIS_PMC BIT23 ///< ADSP Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_SATA_FDIS_PMC BIT22 ///< SATA Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C3_FDIS_PMC BIT13 ///< PCIe Controller C Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C2_FDIS_PMC BIT12 ///< PCIe Controller C Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C1_FDIS_PMC BIT11 ///< PCIe Controller C Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_C0_FDIS_PMC BIT10 ///< PCIe Controller C Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B3_FDIS_PMC BIT9 ///< PCIe Controller B Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B2_FDIS_PMC BIT8 ///< PCIe Controller B Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B1_FDIS_PMC BIT7 ///< PCIe Controller B Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_B0_FDIS_PMC BIT6 ///< PCIe Controller B Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A3_FDIS_PMC BIT5 ///< PCIe Controller A Port 3 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A2_FDIS_PMC BIT4 ///< PCIe Controller A Port 2 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A1_FDIS_PMC BIT3 ///< PCIe Controller A Port 1 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_PCIE_A0_FDIS_PMC BIT2 ///< PCIe Controller A Port 0 Function Disable
+#define B_PCH_PWRM_NST_PG_FDIS_1_XHCI_FDIS_PMC BIT0 ///< XHCI Function Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_1 0x640 ///< Fuse Disable Read 1 Register
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E3_FUSE_DIS BIT21 ///< PCIe Controller E Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E2_FUSE_DIS BIT20 ///< PCIe Controller E Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E1_FUSE_DIS BIT19 ///< PCIe Controller E Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_E0_FUSE_DIS BIT18 ///< PCIe Controller E Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D3_FUSE_DIS BIT17 ///< PCIe Controller D Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D2_FUSE_DIS BIT16 ///< PCIe Controller D Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D1_FUSE_DIS BIT15 ///< PCIe Controller D Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_D0_FUSE_DIS BIT14 ///< PCIe Controller D Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C3_FUSE_DIS BIT13 ///< PCIe Controller C Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C2_FUSE_DIS BIT12 ///< PCIe Controller C Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C1_FUSE_DIS BIT11 ///< PCIe Controller C Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_C0_FUSE_DIS BIT10 ///< PCIe Controller C Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B3_FUSE_DIS BIT9 ///< PCIe Controller B Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B2_FUSE_DIS BIT8 ///< PCIe Controller B Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B1_FUSE_DIS BIT7 ///< PCIe Controller B Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_B0_FUSE_DIS BIT6 ///< PCIe Controller B Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A3_FUSE_DIS BIT5 ///< PCIe Controller A Port 3 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A2_FUSE_DIS BIT4 ///< PCIe Controller A Port 2 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A1_FUSE_DIS BIT3 ///< PCIe Controller A Port 1 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_PCIE_A0_FUSE_DIS BIT2 ///< PCIe Controller A Port 0 Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_1_XHCI_FUSE_DIS BIT0 ///< XHCI Fuse Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_2 0x644 ///< Fuse Disable Read 2 Register
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPC_SS_DIS BIT25 ///< SPC Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPB_SS_DIS BIT24 ///< SPB Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SPA_SS_DIS BIT23 ///< SPA Fuse Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_PSTH_FUSE_SS_DIS BIT21 ///< PSTH Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_DMI_FUSE_SS_DIS BIT20 ///< DMI Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_OTG_FUSE_SS_DIS BIT19 ///< OTG Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_XHCI_SS_DIS BIT18 ///< XHCI Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_FIA_FUSE_SS_DIS BIT17 ///< FIA Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_DSP_FUSE_SS_DIS BIT16 ///< DSP Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SATA_FUSE_SS_DIS BIT15 ///< SATA Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ICC_FUSE_SS_DIS BIT14 ///< ICC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_LPC_FUSE_SS_DIS BIT13 ///< LPC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_RTC_FUSE_SS_DIS BIT12 ///< RTC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_P2S_FUSE_SS_DIS BIT11 ///< P2S Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_TRSB_FUSE_SS_DIS BIT10 ///< TRSB Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SMB_FUSE_SS_DIS BIT9 ///< SMB Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ITSS_FUSE_SS_DIS BIT8 ///< ITSS Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SERIALIO_FUSE_SS_DIS BIT6 ///< SerialIo Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_SCC_FUSE_SS_DIS BIT4 ///< SCC Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_P2D_FUSE_SS_DIS BIT3 ///< P2D Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_CAM_FUSE_SS_DIS BIT2 ///< Camera Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_ISH_FUSE_SS_DIS BIT1 ///< ISH Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_2_GBE_FUSE_SS_DIS BIT0 ///< GBE Fuse or Soft Strap Disable
+#define R_PCH_PWRM_FUSE_DIS_RD_3 0x648 ///< Static PG Fuse and Soft Strap Disable Read Register 3
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA3_FUSE_SS_DIS BIT3 ///< PNCRA3 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA2_FUSE_SS_DIS BIT2 ///< PNCRA2 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA1_FUSE_SS_DIS BIT1 ///< PNCRA1 Fuse or Soft Strap Disable
+#define B_PCH_PWRM_FUSE_DIS_RD_3_PNCRA_FUSE_SS_DIS BIT0 ///< PNCRA Fuse or Soft Strap Disable
+
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
new file mode 100644
index 0000000000..a727aae927
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Include/Register/PchRegsSpi.h
@@ -0,0 +1,304 @@
+/** @file
+ Register names for PCH SPI device.
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values within the bits
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, PCH registers are denoted by "_PCH_" in register names
+ - Registers / bits that are different between PCH generations are denoted by
+ "_PCH_[generation_name]_" in register/bit names.
+ - Registers / bits that are specific to PCH-H denoted by "_H_" in register/bit names.
+ Registers / bits that are specific to PCH-LP denoted by "_LP_" in register/bit names.
+ e.g., "_PCH_H_", "_PCH_LP_"
+ Registers / bits names without _H_ or _LP_ apply for both H and LP.
+ - Registers / bits that are different between SKUs are denoted by "_[SKU_name]"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a PCH generation will be just named
+ as "_PCH_" without [generation_name] inserted.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_REGS_SPI_H_
+#define _PCH_REGS_SPI_H_
+
+//
+// SPI Registers (D31:F5)
+//
+
+#define PCI_DEVICE_NUMBER_PCH_SPI 31
+#define PCI_FUNCTION_NUMBER_PCH_SPI 5
+
+#define R_PCH_SPI_BAR0 0x10
+#define B_PCH_SPI_BAR0_MASK 0x0FFF
+
+#define R_PCH_SPI_BDE 0xD8
+#define B_PCH_SPI_BDE_F8 0x8000
+#define B_PCH_SPI_BDE_F0 0x4000
+#define B_PCH_SPI_BDE_E8 0x2000
+#define B_PCH_SPI_BDE_E0 0x1000
+#define B_PCH_SPI_BDE_D8 0x0800
+#define B_PCH_SPI_BDE_D0 0x0400
+#define B_PCH_SPI_BDE_C8 0x0200
+#define B_PCH_SPI_BDE_C0 0x0100
+#define B_PCH_SPI_BDE_LEG_F 0x0080
+#define B_PCH_SPI_BDE_LEG_E 0x0040
+#define B_PCH_SPI_BDE_70 0x0008
+#define B_PCH_SPI_BDE_60 0x0004
+#define B_PCH_SPI_BDE_50 0x0002
+#define B_PCH_SPI_BDE_40 0x0001
+
+#define R_PCH_SPI_BC 0xDC
+#define S_PCH_SPI_BC 4
+#define N_PCH_SPI_BC_ASE_BWP 11
+#define B_PCH_SPI_BC_ASE_BWP BIT11
+#define N_PCH_SPI_BC_ASYNC_SS 10
+#define B_PCH_SPI_BC_ASYNC_SS BIT10
+#define B_PCH_SPI_BC_OSFH BIT9 ///< OS Function Hide
+#define N_PCH_SPI_BC_SYNC_SS 8
+#define B_PCH_SPI_BC_SYNC_SS BIT8
+#define B_PCH_SPI_BC_BILD BIT7
+#define B_PCH_SPI_BC_BBS BIT6 ///< Boot BIOS strap
+#define N_PCH_SPI_BC_BBS 6
+#define V_PCH_SPI_BC_BBS_SPI 0 ///< Boot BIOS strapped to SPI
+#define V_PCH_SPI_BC_BBS_LPC 1 ///< Boot BIOS strapped to LPC
+#define B_PCH_SPI_BC_EISS BIT5 ///< Enable InSMM.STS
+#define B_PCH_SPI_BC_TSS BIT4
+#define B_PCH_SPI_BC_SRC (BIT3 | BIT2)
+#define N_PCH_SPI_BC_SRC 2
+#define V_PCH_SPI_BC_SRC_PREF_EN_CACHE_EN 0x02 ///< Prefetching and Caching enabled
+#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_DIS 0x01 ///< No prefetching and no caching
+#define V_PCH_SPI_BC_SRC_PREF_DIS_CACHE_EN 0x00 ///< No prefetching, but caching enabled
+#define B_PCH_SPI_BC_LE BIT1 ///< Lock Enable
+#define N_PCH_SPI_BC_BLE 1
+#define B_PCH_SPI_BC_WPD BIT0 ///< Write Protect Disable
+
+//
+// BIOS Flash Program Registers (based on SPI_BAR0)
+//
+#define R_PCH_SPI_BFPR 0x00 ///< BIOS Flash Primary Region Register(32bits), which is RO and contains the same value from FREG1
+#define B_PCH_SPI_BFPR_PRL 0x7FFF0000 ///< BIOS Flash Primary Region Limit mask
+#define N_PCH_SPI_BFPR_PRL 16 ///< BIOS Flash Primary Region Limit bit position
+#define B_PCH_SPI_BFPR_PRB 0x00007FFF ///< BIOS Flash Primary Region Base mask
+#define N_PCH_SPI_BFPR_PRB 0 ///< BIOS Flash Primary Region Base bit position
+#define R_PCH_SPI_HSFSC 0x04 ///< Hardware Sequencing Flash Status and Control Register(32bits)
+#define B_PCH_SPI_HSFSC_FSMIE BIT31 ///< Flash SPI SMI# Enable
+#define B_PCH_SPI_HSFSC_FDBC_MASK 0x3F000000 ///< Flash Data Byte Count ( <= 64), Count = (Value in this field) + 1.
+#define N_PCH_SPI_HSFSC_FDBC 24
+#define B_PCH_SPI_HSFSC_CYCLE_MASK 0x001E0000 ///< Flash Cycle.
+#define N_PCH_SPI_HSFSC_CYCLE 17
+#define V_PCH_SPI_HSFSC_CYCLE_READ 0 ///< Flash Cycle Read
+#define V_PCH_SPI_HSFSC_CYCLE_WRITE 2 ///< Flash Cycle Write
+#define V_PCH_SPI_HSFSC_CYCLE_4K_ERASE 3 ///< Flash Cycle 4K Block Erase
+#define V_PCH_SPI_HSFSC_CYCLE_64K_ERASE 4 ///< Flash Cycle 64K Sector Erase
+#define V_PCH_SPI_HSFSC_CYCLE_READ_SFDP 5 ///< Flash Cycle Read SFDP
+#define V_PCH_SPI_HSFSC_CYCLE_READ_JEDEC_ID 6 ///< Flash Cycle Read JEDEC ID
+#define V_PCH_SPI_HSFSC_CYCLE_WRITE_STATUS 7 ///< Flash Cycle Write Status
+#define V_PCH_SPI_HSFSC_CYCLE_READ_STATUS 8 ///< Flash Cycle Read Status
+#define B_PCH_SPI_HSFSC_CYCLE_FGO BIT16 ///< Flash Cycle Go.
+#define B_PCH_SPI_HSFSC_FLOCKDN BIT15 ///< Flash Configuration Lock-Down
+#define B_PCH_SPI_HSFSC_FDV BIT14 ///< Flash Descriptor Valid, once valid software can use hareware sequencing regs
+#define B_PCH_SPI_HSFSC_FDOPSS BIT13 ///< Flash Descriptor Override Pin-Strap Status
+#define B_PCH_SPI_HSFSC_PRR34_LOCKDN BIT12 ///< PRR3 PRR4 Lock-Down
+#define B_PCH_SPI_HSFSC_SAF_CE BIT8 ///< SAF ctype error
+#define B_PCH_SPI_HSFSC_SAF_MODE_ACTIVE BIT7 ///< Indicates flash is attached either directly to the PCH via the SPI bus or EC/BMC
+#define B_PCH_SPI_HSFSC_SAF_LE BIT6 ///< SAF link error
+#define B_PCH_SPI_HSFSC_SCIP BIT5 ///< SPI cycle in progress
+#define B_PCH_SPI_HSFSC_SAF_DLE BIT4 ///< SAF Data length error
+#define B_PCH_SPI_HSFSC_SAF_ERROR BIT3 ///< SAF Error
+#define B_PCH_SPI_HSFSC_AEL BIT2 ///< Access Error Log
+#define B_PCH_SPI_HSFSC_FCERR BIT1 ///< Flash Cycle Error
+#define B_PCH_SPI_HSFSC_FDONE BIT0 ///< Flash Cycle Done
+#define R_PCH_SPI_FADDR 0x08 ///< SPI Flash Address
+#define B_PCH_SPI_FADDR_MASK 0x01FFFFFF ///< SPI Flash Address Mask (0~24bit)
+#define R_PCH_SPI_DLOCK 0x0C ///< Discrete Lock Bits
+#define B_PCH_SPI_DLOCK_PR0LOCKDN BIT8 ///< PR0LOCKDN
+#define R_PCH_SPI_FDATA00 0x10 ///< SPI Data 00 (32 bits)
+#define R_PCH_SPI_FDATA01 0x14 ///< SPI Data 01
+#define R_PCH_SPI_FDATA02 0x18 ///< SPI Data 02
+#define R_PCH_SPI_FDATA03 0x1C ///< SPI Data 03
+#define R_PCH_SPI_FDATA04 0x20 ///< SPI Data 04
+#define R_PCH_SPI_FDATA05 0x24 ///< SPI Data 05
+#define R_PCH_SPI_FDATA06 0x28 ///< SPI Data 06
+#define R_PCH_SPI_FDATA07 0x2C ///< SPI Data 07
+#define R_PCH_SPI_FDATA08 0x30 ///< SPI Data 08
+#define R_PCH_SPI_FDATA09 0x34 ///< SPI Data 09
+#define R_PCH_SPI_FDATA10 0x38 ///< SPI Data 10
+#define R_PCH_SPI_FDATA11 0x3C ///< SPI Data 11
+#define R_PCH_SPI_FDATA12 0x40 ///< SPI Data 12
+#define R_PCH_SPI_FDATA13 0x44 ///< SPI Data 13
+#define R_PCH_SPI_FDATA14 0x48 ///< SPI Data 14
+#define R_PCH_SPI_FDATA15 0x4C ///< SPI Data 15
+#define R_PCH_SPI_FRAP 0x50 ///< Flash Region Access Permisions Register
+#define B_PCH_SPI_FRAP_BRWA_MASK 0x0000FF00 ///< BIOS Region Write Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3: GbE; 4: PlatformData
+#define N_PCH_SPI_FRAP_BRWA 8 ///< BIOS Region Write Access bit position
+#define B_PCH_SPI_FRAP_BRRA_MASK 0x000000FF ///< BIOS Region Read Access MASK, Region0~7 - 0: Flash Descriptor; 1: BIOS; 2: ME; 3: GbE; 4: PlatformData
+#define B_PCH_SPI_FRAP_BMRAG_MASK 0x00FF0000 ///< BIOS Master Read Access Grant
+#define B_PCH_SPI_FRAP_BMWAG_MASK 0xFF000000 ///< BIOS Master Write Access Grant
+#define R_PCH_SPI_FREG0_FLASHD 0x54 ///< Flash Region 0(Flash Descriptor)(32bits)
+#define R_PCH_SPI_FREG1_BIOS 0x58 ///< Flash Region 1(BIOS)(32bits)
+#define R_PCH_SPI_FREG2_ME 0x5C ///< Flash Region 2(ME)(32bits)
+#define R_PCH_SPI_FREG3_GBE 0x60 ///< Flash Region 3(GbE)(32bits)
+#define R_PCH_SPI_FREG4_PLATFORM_DATA 0x64 ///< Flash Region 4(Platform Data)(32bits)
+#define R_PCH_SPI_FREG5_DER 0x68 ///< Flash Region 5(Device Expansion Region)(32bits)
+#define S_PCH_SPI_FREGX 4 ///< Size of Flash Region register
+#define B_PCH_SPI_FREGX_LIMIT_MASK 0x7FFF0000 ///< Flash Region Limit [30:16] represents [26:12], [11:0] are assumed to be FFFh
+#define N_PCH_SPI_FREGX_LIMIT 16 ///< Region limit bit position
+#define N_PCH_SPI_FREGX_LIMIT_REPR 12 ///< Region limit bit represents position
+#define B_PCH_SPI_FREGX_BASE_MASK 0x00007FFF ///< Flash Region Base, [14:0] represents [26:12]
+#define N_PCH_SPI_FREGX_BASE 0 ///< Region base bit position
+#define N_PCH_SPI_FREGX_BASE_REPR 12 ///< Region base bit represents position
+#define R_PCH_SPI_PR0 0x84 ///< Protected Region 0 Register
+#define R_PCH_SPI_PR1 0x88 ///< Protected Region 1 Register
+#define R_PCH_SPI_PR2 0x8C ///< Protected Region 2 Register
+#define R_PCH_SPI_PR3 0x90 ///< Protected Region 3 Register
+#define R_PCH_SPI_PR4 0x94 ///< Protected Region 4 Register
+#define S_PCH_SPI_PRX 4 ///< Protected Region X Register size
+#define B_PCH_SPI_PRX_WPE BIT31 ///< Write Protection Enable
+#define B_PCH_SPI_PRX_PRL_MASK 0x7FFF0000 ///< Protected Range Limit Mask, [30:16] here represents upper limit of address [26:12]
+#define N_PCH_SPI_PRX_PRL 16 ///< Protected Range Limit bit position
+#define B_PCH_SPI_PRX_RPE BIT15 ///< Read Protection Enable
+#define B_PCH_SPI_PRX_PRB_MASK 0x00007FFF ///< Protected Range Base Mask, [14:0] here represents base limit of address [26:12]
+#define N_PCH_SPI_PRX_PRB 0 ///< Protected Range Base bit position
+#define R_PCH_SPI_SFRAP 0xB0 ///< Secondary Flash Regions Access Permisions Register
+#define R_PCH_SPI_FDOC 0xB4 ///< Flash Descriptor Observability Control Register(32 bits)
+#define B_PCH_SPI_FDOC_FDSS_MASK (BIT14 | BIT13 | BIT12) ///< Flash Descritor Section Select
+#define V_PCH_SPI_FDOC_FDSS_FSDM 0x0000 ///< Flash Signature and Descriptor Map
+#define V_PCH_SPI_FDOC_FDSS_COMP 0x1000 ///< Component
+#define V_PCH_SPI_FDOC_FDSS_REGN 0x2000 ///< Region
+#define V_PCH_SPI_FDOC_FDSS_MSTR 0x3000 ///< Master
+#define V_PCH_SPI_FDOC_FDSS_PCHS 0x4000 ///< PCH soft straps
+#define V_PCH_SPI_FDOC_FDSS_SFDP 0x5000 ///< SFDP Parameter Table
+#define B_PCH_SPI_FDOC_FDSI_MASK 0x0FFC ///< Flash Descriptor Section Index
+#define R_PCH_SPI_FDOD 0xB8 ///< Flash Descriptor Observability Data Register(32 bits)
+#define R_PCH_SPI_SFDP0_VSCC0 0xC4 ///< Vendor Specific Component Capabilities Register(32 bits)
+#define B_PCH_SPI_SFDPX_VSCCX_CPPTV BIT31 ///< Component Property Parameter Table Valid
+#define B_PCH_SPI_SFDP0_VSCC0_VCL BIT30 ///< Vendor Component Lock
+#define B_PCH_SPI_SFDPX_VSCCX_EO_64K BIT29 ///< 64k Erase valid (EO_64k_valid)
+#define B_PCH_SPI_SFDPX_VSCCX_EO_4K BIT28 ///< 4k Erase valid (EO_4k_valid)
+#define B_PCH_SPI_SFDPX_VSCCX_RPMC BIT27 ///< RPMC Supported
+#define B_PCH_SPI_SFDPX_VSCCX_DPD BIT26 ///< Deep Powerdown Supported
+#define B_PCH_SPI_SFDPX_VSCCX_SUSRES BIT25 ///< Suspend/Resume Supported
+#define B_PCH_SPI_SFDPX_VSCCX_SOFTRES BIT24 ///< Soft Reset Supported
+#define B_PCH_SPI_SFDPX_VSCCX_64k_EO_MASK 0x00FF0000 ///< 64k Erase Opcode (EO_64k)
+#define B_PCH_SPI_SFDPX_VSCCX_4k_EO_MASK 0x0000FF00 ///< 4k Erase Opcode (EO_4k)
+#define B_PCH_SPI_SFDPX_VSCCX_QER (BIT7 | BIT6 | BIT5) ///< Quad Enable Requirements
+#define B_PCH_SPI_SFDPX_VSCCX_WEWS BIT4 ///< Write Enable on Write Status
+#define B_PCH_SPI_SFDPX_VSCCX_WSR BIT3 ///< Write Status Required
+#define B_PCH_SPI_SFDPX_VSCCX_WG_64B BIT2 ///< Write Granularity, 0: 1 Byte; 1: 64 Bytes
+#define R_PCH_SPI_SFDP1_VSCC1 0xC8 ///< Vendor Specific Component Capabilities Register(32 bits)
+#define R_PCH_SPI_PINTX 0xCC ///< Parameter Table Index
+#define N_PCH_SPI_PINTX_SPT 14
+#define V_PCH_SPI_PINTX_SPT_CPT0 0x0 ///< Component 0 Property Parameter Table
+#define V_PCH_SPI_PINTX_SPT_CPT1 0x1 ///< Component 1 Property Parameter Table
+#define N_PCH_SPI_PINTX_HORD 12
+#define V_PCH_SPI_PINTX_HORD_SFDP 0x0 ///< SFDP Header
+#define V_PCH_SPI_PINTX_HORD_PT 0x1 ///< Parameter Table Header
+#define V_PCH_SPI_PINTX_HORD_DATA 0x2 ///< Data
+#define R_PCH_SPI_PTDATA 0xD0 ///< Parameter Table Data
+#define R_PCH_SPI_SBRS 0xD4 ///< SPI Bus Requester Status
+#define R_PCH_SPI_SSML 0xF0 ///< Set Strap Msg Lock
+#define B_PCH_SPI_SSML_SSL BIT0 ///< Set_Strap Lock
+#define R_PCH_SPI_SSMC 0xF4 ///< Set Strap Msg Control
+#define B_PCH_SPI_SSMC_SSMS BIT0 ///< Set_Strap Mux Select
+#define R_PCH_SPI_SSMD 0xF8 ///< Set Strap Msg Data
+//
+// @todo Follow up with EDS owner if it should be 3FFF or FFFF.
+//
+#define B_PCH_SPI_SRD_SSD 0x0000FFFF ///< Set_Strap Data
+//
+// Flash Descriptor Base Address Region (FDBAR) from Flash Region 0
+//
+#define R_PCH_SPI_FDBAR_FLVALSIG 0x00 ///< Flash Valid Signature
+#define V_PCH_SPI_FDBAR_FLVALSIG 0x0FF0A55A
+#define R_PCH_SPI_FDBAR_FLASH_MAP0 0x04
+#define B_PCH_SPI_FDBAR_FCBA 0x000000FF ///< Flash Component Base Address
+#define B_PCH_SPI_FDBAR_NC 0x00000300 ///< Number Of Components
+#define N_PCH_SPI_FDBAR_NC 8 ///< Number Of Components
+#define V_PCH_SPI_FDBAR_NC_1 0x00000000
+#define V_PCH_SPI_FDBAR_NC_2 0x00000100
+#define B_PCH_SPI_FDBAR_FRBA 0x00FF0000 ///< Flash Region Base Address
+#define B_PCH_SPI_FDBAR_NR 0x07000000 ///< Number Of Regions
+#define R_PCH_SPI_FDBAR_FLASH_MAP1 0x08
+#define B_PCH_SPI_FDBAR_FMBA 0x000000FF ///< Flash Master Base Address
+#define B_PCH_SPI_FDBAR_NM 0x00000700 ///< Number Of Masters
+#define B_PCH_SPI_FDBAR_FPSBA 0x00FF0000 ///< PCH Strap Base Address, [23:16] represents [11:4]
+#define N_PCH_SPI_FDBAR_FPSBA 16 ///< PCH Strap base Address bit position
+#define N_PCH_SPI_FDBAR_FPSBA_REPR 4 ///< PCH Strap base Address bit represents position
+#define B_PCH_SPI_FDBAR_PCHSL 0xFF000000 ///< PCH Strap Length, [31:24] represents number of Dwords
+#define N_PCH_SPI_FDBAR_PCHSL 24 ///< PCH Strap Length bit position
+#define R_PCH_SPI_FDBAR_FLASH_MAP2 0x0C
+#define B_PCH_SPI_FDBAR_FCPUSBA 0x000000FF ///< CPU Strap Base Address, [7:0] represents [11:4]
+#define N_PCH_SPI_FDBAR_FCPUSBA 0 ///< CPU Strap Base Address bit position
+#define N_PCH_SPI_FDBAR_FCPUSBA_REPR 4 ///< CPU Strap Base Address bit represents position
+#define B_PCH_SPI_FDBAR_CPUSL 0x0000FF00 ///< CPU Strap Length, [15:8] represents number of Dwords
+#define N_PCH_SPI_FDBAR_CPUSL 8 ///< CPU Strap Length bit position
+//
+// Flash Component Base Address (FCBA) from Flash Region 0
+//
+#define R_PCH_SPI_FCBA_FLCOMP 0x00 ///< Flash Components Register
+#define B_PCH_SPI_FLCOMP_RIDS_FREQ (BIT29 | BIT28 | BIT27) ///< Read ID and Read Status Clock Frequency
+#define B_PCH_SPI_FLCOMP_WE_FREQ (BIT26 | BIT25 | BIT24) ///< Write and Erase Clock Frequency
+#define B_PCH_SPI_FLCOMP_FRCF_FREQ (BIT23 | BIT22 | BIT21) ///< Fast Read Clock Frequency
+#define B_PCH_SPI_FLCOMP_FR_SUP BIT20 ///< Fast Read Support.
+#define B_PCH_SPI_FLCOMP_RC_FREQ (BIT19 | BIT18 | BIT17) ///< Read Clock Frequency.
+#define V_PCH_SPI_FLCOMP_FREQ_48MHZ 0x02
+#define V_PCH_SPI_FLCOMP_FREQ_30MHZ 0x04
+#define V_PCH_SPI_FLCOMP_FREQ_17MHZ 0x06
+#define B_PCH_SPI_FLCOMP_COMP1_MASK 0xF0 ///< Flash Component 1 Size MASK
+#define N_PCH_SPI_FLCOMP_COMP1 4 ///< Flash Component 1 Size bit position
+#define B_PCH_SPI_FLCOMP_COMP0_MASK 0x0F ///< Flash Component 0 Size MASK
+#define V_PCH_SPI_FLCOMP_COMP_512KB 0x80000
+//
+// Descriptor Upper Map Section from Flash Region 0
+//
+#define R_PCH_SPI_FLASH_UMAP1 0xEFC ///< Flash Upper Map 1
+#define B_PCH_SPI_FLASH_UMAP1_VTBA 0x000000FF ///< VSCC Table Base Address
+#define B_PCH_SPI_FLASH_UMAP1_VTL 0x0000FF00 ///< VSCC Table Length
+
+#define R_PCH_SPI_VTBA_JID0 0x00 ///< JEDEC-ID 0 Register
+#define S_PCH_SPI_VTBA_JID0 0x04
+#define B_PCH_SPI_VTBA_JID0_VID 0x000000FF
+#define B_PCH_SPI_VTBA_JID0_DID0 0x0000FF00
+#define B_PCH_SPI_VTBA_JID0_DID1 0x00FF0000
+#define N_PCH_SPI_VTBA_JID0_DID0 0x08
+#define N_PCH_SPI_VTBA_JID0_DID1 0x10
+#define R_PCH_SPI_VTBA_VSCC0 0x04
+#define S_PCH_SPI_VTBA_VSCC0 0x04
+
+
+//
+// SPI Private Configuration Space Registers
+//
+#define R_PCH_PCR_SPI_CLK_CTL 0xC004
+#define R_PCH_PCR_SPI_PWR_CTL 0xC008
+#define R_PCH_PCR_SPI_ESPI_SOFTSTRAPS 0xC210
+#define B_PCH_PCR_SPI_ESPI_SOFTSTRAPS_SLAVE BIT12
+
+//
+// MMP0
+//
+#define R_PCH_SPI_STRP_MMP0 0xC4 ///< MMP0 Soft strap offset
+#define B_PCH_SPI_STRP_MMP0 0x10 ///< MMP0 Soft strap bit
+
+
+#define R_PCH_SPI_STRP_SFDP 0xF0 ///< PCH Soft Strap SFDP
+#define B_PCH_SPI_STRP_SFDP_QIORE BIT3 ///< Quad IO Read Enable
+#define B_PCH_SPI_STRP_SFDP_QORE BIT2 ///< Quad Output Read Enable
+#define B_PCH_SPI_STRP_SFDP_DIORE BIT1 ///< Dual IO Read Enable
+#define B_PCH_SPI_STRP_SFDP_DORE BIT0 ///< Dual Output Read Enable
+
+//
+// Descriptor Record 0
+//
+#define R_PCH_SPI_STRP_DSCR_0 0x00 ///< PCH Soft Strap 0
+#define B_PCH_SPI_STRP_DSCR_0_PTT_SUPP BIT22 ///< PTT Supported
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
new file mode 100644
index 0000000000..5bdec96197
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/IncludePrivate/Library/PchSpiCommonLib.h
@@ -0,0 +1,396 @@
+/** @file
+ Header file for the PCH SPI Common Driver.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_COMMON_LIB_H_
+#define _PCH_SPI_COMMON_LIB_H_
+
+//
+// Maximum time allowed while waiting the SPI cycle to complete
+// Wait Time = 6 seconds = 6000000 microseconds
+// Wait Period = 10 microseconds
+//
+#define SPI_WAIT_TIME 6000000 ///< Wait Time = 6 seconds = 6000000 microseconds
+#define SPI_WAIT_PERIOD 10 ///< Wait Period = 10 microseconds
+
+///
+/// Flash cycle Type
+///
+typedef enum {
+ FlashCycleRead,
+ FlashCycleWrite,
+ FlashCycleErase,
+ FlashCycleReadSfdp,
+ FlashCycleReadJedecId,
+ FlashCycleWriteStatus,
+ FlashCycleReadStatus,
+ FlashCycleMax
+} FLASH_CYCLE_TYPE;
+
+///
+/// Flash Component Number
+///
+typedef enum {
+ FlashComponent0,
+ FlashComponent1,
+ FlashComponentMax
+} FLASH_COMPONENT_NUM;
+
+///
+/// Private data structure definitions for the driver
+///
+#define PCH_SPI_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('P', 'S', 'P', 'I')
+
+typedef struct {
+ UINT32 Signature;
+ EFI_HANDLE Handle;
+ EFI_SPI_PROTOCOL SpiProtocol;
+ UINT16 PchAcpiBase;
+ UINTN PchSpiBase;
+ UINT16 ReadPermission;
+ UINT16 WritePermission;
+ UINT32 SfdpVscc0Value;
+ UINT32 SfdpVscc1Value;
+ UINT16 PchStrapBaseAddr;
+ UINT16 PchStrapSize;
+ UINT16 CpuStrapBaseAddr;
+ UINT16 CpuStrapSize;
+ UINT8 NumberOfComponents;
+ UINT32 Component1StartAddr;
+ UINT32 TotalFlashSize;
+} SPI_INSTANCE;
+
+#define SPI_INSTANCE_FROM_SPIPROTOCOL(a) CR (a, SPI_INSTANCE, SpiProtocol, PCH_SPI_PRIVATE_DATA_SIGNATURE)
+
+//
+// Function prototypes used by the SPI protocol.
+//
+
+/**
+ Initialize an SPI protocol instance.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @exception EFI_UNSUPPORTED The PCH is not supported by this module
+**/
+EFI_STATUS
+SpiProtocolConstructor (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ This function is a hook for Spi to disable BIOS Write Protect
+
+ @retval EFI_SUCCESS The protocol instance was properly initialized
+ @retval EFI_ACCESS_DENIED The BIOS Region can only be updated in SMM phase
+
+**/
+EFI_STATUS
+EFIAPI
+DisableBiosWriteProtect (
+ VOID
+ );
+
+/**
+ This function is a hook for Spi to enable BIOS Write Protect
+
+
+**/
+VOID
+EFIAPI
+EnableBiosWriteProtect (
+ VOID
+ );
+
+/**
+ Acquire pch spi mmio address.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval PchSpiBar0 return SPI MMIO address
+**/
+UINTN
+AcquireSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ Release pch spi mmio address.
+
+ @param[in] SpiInstance Pointer to SpiInstance to initialize
+
+ @retval None
+**/
+VOID
+ReleaseSpiBar0 (
+ IN SPI_INSTANCE *SpiInstance
+ );
+
+/**
+ Read data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[out] Buffer The Pointer to caller-allocated buffer containing the dada received.
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashRead (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *Buffer
+ );
+
+/**
+ Write data to the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in] Buffer Pointer to caller-allocated buffer containing the data sent during the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWrite (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN UINT8 *Buffer
+ );
+
+/**
+ Erase some area on the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for flash cycle which is listed in the Descriptor.
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashErase (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount
+ );
+
+/**
+ Read SFDP data from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] Address The starting byte address for SFDP data read.
+ @param[in] ByteCount Number of bytes in SFDP data portion of the SPI cycle
+ @param[out] SfdpData The Pointer to caller-allocated buffer containing the SFDP data received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadSfdp (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ OUT UINT8 *SfdpData
+ );
+
+/**
+ Read Jedec Id from the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ComponentNumber The Componen Number for chip select
+ @param[in] ByteCount Number of bytes in JedecId data portion of the SPI cycle, the data size is 3 typically
+ @param[out] JedecId The Pointer to caller-allocated buffer containing JEDEC ID received
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadJedecId (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT8 ComponentNumber,
+ IN UINT32 ByteCount,
+ OUT UINT8 *JedecId
+ );
+
+/**
+ Write the status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[in] StatusValue The Pointer to caller-allocated buffer containing the value of Status register writing
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashWriteStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ IN UINT8 *StatusValue
+ );
+
+/**
+ Read status register in the flash part.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] ByteCount Number of bytes in Status data portion of the SPI cycle, the data size is 1 typically
+ @param[out] StatusValue The Pointer to caller-allocated buffer containing the value of Status register received.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolFlashReadStatus (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 ByteCount,
+ OUT UINT8 *StatusValue
+ );
+
+/**
+ Get the SPI region base and size, based on the enum type
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] FlashRegionType The Flash Region type for for the base address which is listed in the Descriptor.
+ @param[out] BaseAddress The Flash Linear Address for the Region 'n' Base
+ @param[out] RegionSize The size for the Region 'n'
+
+ @retval EFI_SUCCESS Read success
+ @retval EFI_INVALID_PARAMETER Invalid region type given
+ @retval EFI_DEVICE_ERROR The region is not used
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolGetRegionAddress (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ OUT UINT32 *BaseAddress,
+ OUT UINT32 *RegionSize
+ );
+
+/**
+ Read PCH Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr PCH Soft Strap address offset from FPSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing PCH Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadPchSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ Read CPU Soft Strap Values
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SoftStrapAddr CPU Soft Strap address offset from FCPUSBA.
+ @param[in] ByteCount Number of bytes in SoftStrap data portion of the SPI cycle.
+ @param[out] SoftStrapValue The Pointer to caller-allocated buffer containing CPU Soft Strap Value.
+ If the value of ByteCount is 0, the data type of SoftStrapValue should be UINT16 and SoftStrapValue will be PCH Soft Strap Length
+ It is the caller's responsibility to make sure Buffer is large enough for the total number of bytes read.
+
+ @retval EFI_SUCCESS Command succeed.
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+ @retval EFI_DEVICE_ERROR Device error, command aborts abnormally.
+**/
+EFI_STATUS
+EFIAPI
+SpiProtocolReadCpuSoftStrap (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINT32 SoftStrapAddr,
+ IN UINT32 ByteCount,
+ OUT VOID *SoftStrapValue
+ );
+
+/**
+ This function sends the programmed SPI command to the slave device.
+
+ @param[in] This Pointer to the PCH_SPI_PROTOCOL instance.
+ @param[in] SpiRegionType The SPI Region type for flash cycle which is listed in the Descriptor
+ @param[in] FlashCycleType The Flash SPI cycle type list in HSFC (Hardware Sequencing Flash Control Register) register
+ @param[in] Address The Flash Linear Address must fall within a region for which BIOS has access permissions.
+ @param[in] ByteCount Number of bytes in the data portion of the SPI cycle.
+ @param[in,out] Buffer Pointer to caller-allocated buffer containing the dada received or sent during the SPI cycle.
+
+ @retval EFI_SUCCESS SPI command completes successfully.
+ @retval EFI_DEVICE_ERROR Device error, the command aborts abnormally.
+ @retval EFI_ACCESS_DENIED Some unrecognized command encountered in hardware sequencing mode
+ @retval EFI_INVALID_PARAMETER The parameters specified are not valid.
+**/
+EFI_STATUS
+SendSpiCmd (
+ IN EFI_SPI_PROTOCOL *This,
+ IN FLASH_REGION_TYPE FlashRegionType,
+ IN FLASH_CYCLE_TYPE FlashCycleType,
+ IN UINT32 Address,
+ IN UINT32 ByteCount,
+ IN OUT UINT8 *Buffer
+ );
+
+/**
+ Wait execution cycle to complete on the SPI interface.
+
+ @param[in] This The SPI protocol instance
+ @param[in] PchSpiBar0 Spi MMIO base address
+ @param[in] ErrorCheck TRUE if the SpiCycle needs to do the error check
+
+ @retval TRUE SPI cycle completed on the interface.
+ @retval FALSE Time out while waiting the SPI cycle to complete.
+ It's not safe to program the next command on the SPI interface.
+**/
+BOOLEAN
+WaitForSpiCycleComplete (
+ IN EFI_SPI_PROTOCOL *This,
+ IN UINTN PchSpiBar0,
+ IN BOOLEAN ErrorCheck
+ );
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
new file mode 100644
index 0000000000..4af462da47
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/ResetSystemLib/ResetSystemLib.inf
@@ -0,0 +1,34 @@
+## @file
+# Library instance for ResetSystem library class for OVMF
+#
+# Copyright (c) 2006 - 2018 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = ResetSystemLib
+ FILE_GUID = 66564872-21d4-4d2a-a68b-1e844f980820
+ MODULE_TYPE = BASE
+ VERSION_STRING = 1.0
+ LIBRARY_CLASS = ResetSystemLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[Sources]
+ ResetSystemLib.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+
+[LibraryClasses]
+ DebugLib
+ IoLib
+ TimerLib
diff --git a/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
new file mode 100644
index 0000000000..b5c97f1930
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Library/SmmSpiFlashCommonLib/SmmSpiFlashCommonLib.inf
@@ -0,0 +1,52 @@
+## @file
+# SMM Library instance of Spi Flash Common Library Class
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010017
+ BASE_NAME = SmmSpiFlashCommonLib
+ FILE_GUID = 9632D96E-E849-4217-9217-DC500B8AAE47
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_SMM_DRIVER
+ LIBRARY_CLASS = SpiFlashCommonLib|DXE_SMM_DRIVER
+ CONSTRUCTOR = SmmSpiFlashCommonLibConstructor
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[LibraryClasses]
+ PciLib
+ IoLib
+ MemoryAllocationLib
+ BaseLib
+ UefiLib
+ SmmServicesTableLib
+ BaseMemoryLib
+ DebugLib
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+ MinPlatformPkg/MinPlatformPkg.dec
+
+
+[Pcd]
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
+
+[Sources]
+ SpiFlashCommonSmmLib.c
+ SpiFlashCommon.c
+
+[Protocols]
+ gEfiSmmSpiProtocolGuid ## CONSUMES
+
+[Depex.X64.DXE_SMM_DRIVER]
+ gEfiSmmSpiProtocolGuid
diff --git a/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
new file mode 100644
index 0000000000..11c832e487
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
@@ -0,0 +1,33 @@
+## @file
+# Component description file for the PchSpiCommonLib
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = BasePchSpiCommonLib
+ FILE_GUID = A37CB67E-7D85-45B3-B07E-BF65BDB603E8
+ MODULE_TYPE = BASE
+ VERSION_STRING = 1.0
+ LIBRARY_CLASS = PchSpiCommonLib
+
+[Sources]
+ SpiCommon.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+ MinPlatformPkg/MinPlatformPkg.dec
+
+[LibraryClasses]
+ IoLib
+ DebugLib
+
+[Pcd]
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaBaseAddress ## CONSUMES
+ gMinPlatformPkgTokenSpaceGuid.PcdFlashAreaSize ## CONSUMES
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
new file mode 100644
index 0000000000..a2d006ee35
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchCommonLib.dsc
@@ -0,0 +1,12 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE libraries.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[LibraryClasses.common]
+ ResetSystemLib|$(PCH_PKG)/Library/ResetSystemLib/ResetSystemLib.inf
+ PchSpiCommonLib|$(PCH_PKG)/LibraryPrivate/BasePchSpiCommonLib/BasePchSpiCommonLib.inf
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
new file mode 100644
index 0000000000..78eca21a43
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchPostMemoryInclude.fdf
@@ -0,0 +1,9 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
new file mode 100644
index 0000000000..2d3a127c20
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchPreMemoryInclude.fdf
@@ -0,0 +1,9 @@
+## @file
+# Component description file for the SkyLake SiPkg PEI drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
diff --git a/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
new file mode 100644
index 0000000000..d079c593d9
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/PchUefiBootInclude.fdf
@@ -0,0 +1,13 @@
+## @file
+# Component description file for the SkyLake SiPkg DXE drivers.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+!if gMinPlatformPkgTokenSpaceGuid.PcdBootToShellOnly == FALSE
+ INF $(PCH_PKG)/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
+ INF $(PCH_PKG)/Spi/Smm/PchSpiSmm.inf
+!endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
new file mode 100644
index 0000000000..e23dd9f2fe
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/SmmControl/RuntimeDxe/SmmControl2Dxe.inf
@@ -0,0 +1,59 @@
+## @file
+# A DXE_RUNTIME_DRIVER providing synchronous SMI activations via the
+# EFI_SMM_CONTROL2_PROTOCOL.
+#
+# We expect the PEI phase to have covered the following:
+# - ensure that the underlying QEMU machine type be X58
+# (responsible: OvmfPkg/SmmAccess/SmmAccessPei.inf)
+# - ensure that the ACPI PM IO space be configured
+# (responsible: OvmfPkg/PlatformPei/PlatformPei.inf)
+#
+# Our own entry point is responsible for confirming the SMI feature and for
+# configuring it.
+#
+# Copyright (C) 2013, 2015, Red Hat, Inc.
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = SmmControl2Dxe
+ FILE_GUID = 1206F7CA-A475-4624-A83E-E6FC9BB38E49
+ MODULE_TYPE = DXE_RUNTIME_DRIVER
+ VERSION_STRING = 1.0
+ PI_SPECIFICATION_VERSION = 0x00010400
+ ENTRY_POINT = SmmControl2DxeEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64
+#
+
+[Sources]
+ SmmControl2Dxe.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsOpenBoardPkg/SimicsOpenBoardPkg.dec
+
+[LibraryClasses]
+ BaseLib
+ DebugLib
+ IoLib
+ PcdLib
+ PciLib
+ UefiBootServicesTableLib
+ UefiDriverEntryPoint
+
+[Protocols]
+ gEfiS3SaveStateProtocolGuid ## SOMETIMES_CONSUMES
+ gEfiSmmControl2ProtocolGuid ## PRODUCES
+
+[FeaturePcd]
+ gSimicsX58PkgTokenSpaceGuid.PcdSmmSmramRequire
+
+[Depex]
+ TRUE
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
new file mode 100644
index 0000000000..f7fdd3abbe
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpi.h
@@ -0,0 +1,23 @@
+/** @file
+ Header file for the PCH SPI SMM Driver.
+
+ Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PCH_SPI_H_
+#define _PCH_SPI_H_
+
+#include <Library/IoLib.h>
+#include <Library/DebugLib.h>
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/SmmServicesTableLib.h>
+#include <PchAccess.h>
+#include <Protocol/Spi.h>
+#include <IncludePrivate/Library/PchSpiCommonLib.h>
+
+#endif
diff --git a/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
new file mode 100644
index 0000000000..265af00ac0
--- /dev/null
+++ b/Silicon/Intel/SimicsICH10Pkg/Spi/Smm/PchSpiSmm.inf
@@ -0,0 +1,44 @@
+## @file
+# Component description file for the SPI SMM driver.
+#
+# Copyright (c) 2017 Intel Corporation. All rights reserved. <BR>
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+ INF_VERSION = 0x00010017
+ BASE_NAME = PchSpiSmm
+ FILE_GUID = 27F4917B-A707-4aad-9676-26DF168CBF0D
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_SMM_DRIVER
+ PI_SPECIFICATION_VERSION = 1.10
+ ENTRY_POINT = InstallPchSpi
+
+
+ [LibraryClasses]
+ DebugLib
+ IoLib
+ UefiDriverEntryPoint
+ UefiBootServicesTableLib
+ BaseLib
+ SmmServicesTableLib
+ PchSpiCommonLib
+
+[Packages]
+ MdePkg/MdePkg.dec
+ SimicsICH10Pkg/ICH10Pkg.dec
+
+[Sources]
+ PchSpi.h
+ PchSpi.c
+
+
+[Protocols]
+ gEfiSmmSpiProtocolGuid # PRODUCES #SERVER_BIOS
+
+
+[Depex]
+ gEfiSmmBase2ProtocolGuid #This is for SmmServicesTableLib
+ AND gEfiSmmCpuProtocolGuid # This is for CpuSmmDisableBiosWriteProtect()
--
2.16.2.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#45698): https://edk2.groups.io/g/devel/message/45698
Mute This Topic: https://groups.io/mt/32816096/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
© 2016 - 2025 Red Hat, Inc.