public inbox for devel@edk2.groups.io
 help / color / mirror / Atom feed
* [PATCH] UefiPayloadPkg: Enhance UEFI payload for coreboot and Slim Bootloader
@ 2019-04-11 15:03 Guo Dong
  0 siblings, 0 replies; 9+ messages in thread
From: Guo Dong @ 2019-04-11 15:03 UTC (permalink / raw)
  To: devel; +Cc: maurice.ma, prince.agyeman, benjamin.you, guo.dong

CorebootModulePkg and CorebootPayloadPkg originally supports coreboot only.
In order to support other bootloaders, such as Slim Bootloader, they need
be updated to be more generic.
UEFI Payload (UefiPayloadPkg) a converged package from CorebootModulePkg
and CorebootPayloadPkg with following updates:
a. Support both coreboot and Slim Bootloader
b. Removed SataControllerDxe and BaseSerialPortLib16550 to use EDK2 modules
c. Support passing bootloader parameter to UEFI payload, e.g. coreboot
   table from coreboot or HOB list from Slim Bootloader
d. Using GraphicsOutputDxe from EDK2 with minor change instead of FbGop
e. Remove the dependency to IntelFrameworkPkg and IntelFrameworkModulePkg
   and QuarkSocPkg
f. Use BaseDebugLibSerialPort library as DebugLib
g. Use HPET timer, drop legacy 8254 timer support
h. Use BaseXApicX2ApicLib instead of BaseXApicLib
i. Remove HOB gUefiFrameBufferInfoGuid to use EDK2 graphics HOBs.
j. Other clean ups

On how UefiPayloadPkg could work with coreboot/Slim Bootloader, please
refer UefiPayloadPkg/BuildAndIntegrationInstructions.txt

Once UefiPayloadPkg is checked-in, CorebootModulePkg and CorebootPayloadPkg
could be retired.

Signed-off-by: Guo Dong <guo.dong@intel.com>
Reviewed-by: Maurice Ma <maurice.ma@intel.com>
---
 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c         | 158 +++++
 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h         |  30 +
 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf       |  58 ++
 UefiPayloadPkg/BlSupportPei/BlSupportPei.c         | 566 ++++++++++++++++
 UefiPayloadPkg/BlSupportPei/BlSupportPei.h         |  39 ++
 UefiPayloadPkg/BlSupportPei/BlSupportPei.inf       |  73 ++
 UefiPayloadPkg/BuildAndIntegrationInstructions.txt |  82 +++
 UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c   | 184 +++++
 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c  | 739 +++++++++++++++++++++
 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h  |  53 ++
 .../GraphicsOutputDxe/GraphicsOutputDxe.inf        |  53 ++
 UefiPayloadPkg/Include/Coreboot.h                  | 249 +++++++
 UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h    |  29 +
 UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h    |  36 +
 UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h   |  31 +
 UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h  |  26 +
 UefiPayloadPkg/Include/Library/BlParseLib.h        | 120 ++++
 .../Include/Library/PlatformSupportLib.h           |  28 +
 UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c | 270 ++++++++
 .../Library/AcpiTimerLib/AcpiTimerLib.inf          |  40 ++
 UefiPayloadPkg/Library/CbParseLib/CbParseLib.c     | 560 ++++++++++++++++
 UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf   |  39 ++
 .../Library/PciHostBridgeLib/PciHostBridge.h       |  80 +++
 .../Library/PciHostBridgeLib/PciHostBridgeLib.c    | 222 +++++++
 .../Library/PciHostBridgeLib/PciHostBridgeLib.inf  |  41 ++
 .../PciHostBridgeLib/PciHostBridgeSupport.c        | 584 ++++++++++++++++
 .../PlatformBootManagerLib/PlatformBootManager.c   | 265 ++++++++
 .../PlatformBootManagerLib/PlatformBootManager.h   | 132 ++++
 .../PlatformBootManagerLib.inf                     |  71 ++
 .../PlatformBootManagerLib/PlatformConsole.c       | 599 +++++++++++++++++
 .../PlatformBootManagerLib/PlatformConsole.h       |  70 ++
 .../Library/PlatformBootManagerLib/PlatformData.c  |  39 ++
 .../Library/PlatformHookLib/PlatformHookLib.c      |  98 +++
 .../Library/PlatformHookLib/PlatformHookLib.inf    |  39 ++
 .../PlatformSupportLibNull.c                       |  29 +
 .../PlatformSupportLibNull.inf                     |  28 +
 .../Library/ResetSystemLib/ResetSystemLib.c        | 171 +++++
 .../Library/ResetSystemLib/ResetSystemLib.inf      |  40 ++
 UefiPayloadPkg/Library/SblParseLib/SblParseLib.c   | 223 +++++++
 UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf |  46 ++
 UefiPayloadPkg/SecCore/FindPeiCore.c               | 193 ++++++
 UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm          |  78 +++
 UefiPayloadPkg/SecCore/Ia32/Stack.nasm             |  72 ++
 UefiPayloadPkg/SecCore/SecCore.inf                 |  58 ++
 UefiPayloadPkg/SecCore/SecMain.c                   | 288 ++++++++
 UefiPayloadPkg/SecCore/SecMain.h                   | 131 ++++
 UefiPayloadPkg/UefiPayloadPkg.dec                  |  71 ++
 UefiPayloadPkg/UefiPayloadPkg.fdf                  | 288 ++++++++
 UefiPayloadPkg/UefiPayloadPkgIa32.dsc              | 573 ++++++++++++++++
 UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc           | 574 ++++++++++++++++
 50 files changed, 8566 insertions(+)
 create mode 100644 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c
 create mode 100644 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h
 create mode 100644 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
 create mode 100644 UefiPayloadPkg/BlSupportPei/BlSupportPei.c
 create mode 100644 UefiPayloadPkg/BlSupportPei/BlSupportPei.h
 create mode 100644 UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
 create mode 100644 UefiPayloadPkg/BuildAndIntegrationInstructions.txt
 create mode 100644 UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c
 create mode 100644 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c
 create mode 100644 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h
 create mode 100644 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
 create mode 100644 UefiPayloadPkg/Include/Coreboot.h
 create mode 100644 UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h
 create mode 100644 UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h
 create mode 100644 UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h
 create mode 100644 UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h
 create mode 100644 UefiPayloadPkg/Include/Library/BlParseLib.h
 create mode 100644 UefiPayloadPkg/Include/Library/PlatformSupportLib.h
 create mode 100644 UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c
 create mode 100644 UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
 create mode 100644 UefiPayloadPkg/Library/CbParseLib/CbParseLib.c
 create mode 100644 UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
 create mode 100644 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h
 create mode 100644 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c
 create mode 100644 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
 create mode 100644 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c
 create mode 100644 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c
 create mode 100644 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h
 create mode 100644 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
 create mode 100644 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c
 create mode 100644 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h
 create mode 100644 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c
 create mode 100644 UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c
 create mode 100644 UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
 create mode 100644 UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c
 create mode 100644 UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
 create mode 100644 UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c
 create mode 100644 UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
 create mode 100644 UefiPayloadPkg/Library/SblParseLib/SblParseLib.c
 create mode 100644 UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
 create mode 100644 UefiPayloadPkg/SecCore/FindPeiCore.c
 create mode 100644 UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm
 create mode 100644 UefiPayloadPkg/SecCore/Ia32/Stack.nasm
 create mode 100644 UefiPayloadPkg/SecCore/SecCore.inf
 create mode 100644 UefiPayloadPkg/SecCore/SecMain.c
 create mode 100644 UefiPayloadPkg/SecCore/SecMain.h
 create mode 100644 UefiPayloadPkg/UefiPayloadPkg.dec
 create mode 100644 UefiPayloadPkg/UefiPayloadPkg.fdf
 create mode 100644 UefiPayloadPkg/UefiPayloadPkgIa32.dsc
 create mode 100644 UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc

diff --git a/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c
new file mode 100644
index 0000000000..bcee4cd9bc
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c
@@ -0,0 +1,158 @@
+/** @file
+  This driver will report some MMIO/IO resources to dxe core, extract smbios and acpi
+  tables from bootloader.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#include "BlSupportDxe.h"
+
+/**
+  Reserve MMIO/IO resource in GCD
+
+  @param  IsMMIO        Flag of whether it is mmio resource or io resource.
+  @param  GcdType       Type of the space.
+  @param  BaseAddress   Base address of the space.
+  @param  Length        Length of the space.
+  @param  Alignment     Align with 2^Alignment
+  @param  ImageHandle   Handle for the image of this driver.
+
+  @retval EFI_SUCCESS   Reserve successful
+**/
+EFI_STATUS
+ReserveResourceInGcd (
+  IN BOOLEAN               IsMMIO,
+  IN UINTN                 GcdType,
+  IN EFI_PHYSICAL_ADDRESS  BaseAddress,
+  IN UINT64                Length,
+  IN UINTN                 Alignment,
+  IN EFI_HANDLE            ImageHandle
+  )
+{
+  EFI_STATUS               Status;
+
+  if (IsMMIO) {
+    Status = gDS->AddMemorySpace (
+                    GcdType,
+                    BaseAddress,
+                    Length,
+                    EFI_MEMORY_UC
+                    );
+    if (EFI_ERROR (Status)) {
+      DEBUG ((
+        DEBUG_ERROR,
+        "Failed to add memory space :0x%lx 0x%lx\n",
+        BaseAddress,
+        Length
+        ));
+    }
+    ASSERT_EFI_ERROR (Status);
+    Status = gDS->AllocateMemorySpace (
+                    EfiGcdAllocateAddress,
+                    GcdType,
+                    Alignment,
+                    Length,
+                    &BaseAddress,
+                    ImageHandle,
+                    NULL
+                    );
+    ASSERT_EFI_ERROR (Status);
+  } else {
+    Status = gDS->AddIoSpace (
+                    GcdType,
+                    BaseAddress,
+                    Length
+                    );
+    ASSERT_EFI_ERROR (Status);
+    Status = gDS->AllocateIoSpace (
+                    EfiGcdAllocateAddress,
+                    GcdType,
+                    Alignment,
+                    Length,
+                    &BaseAddress,
+                    ImageHandle,
+                    NULL
+                    );
+    ASSERT_EFI_ERROR (Status);
+  }
+  return Status;
+}
+
+
+/**
+  Main entry for the bootloader support DXE module.
+
+  @param[in] ImageHandle    The firmware allocated handle for the EFI image.
+  @param[in] SystemTable    A pointer to the EFI System Table.
+
+  @retval EFI_SUCCESS       The entry point is executed successfully.
+  @retval other             Some error occurs when executing this entry point.
+
+**/
+EFI_STATUS
+EFIAPI
+BlDxeEntryPoint (
+  IN EFI_HANDLE              ImageHandle,
+  IN EFI_SYSTEM_TABLE        *SystemTable
+  )
+{
+  EFI_STATUS Status;
+  EFI_HOB_GUID_TYPE          *GuidHob;
+  SYSTEM_TABLE_INFO          *SystemTableInfo;
+  EFI_PEI_GRAPHICS_INFO_HOB  *GfxInfo;
+
+  Status = EFI_SUCCESS;
+  //
+  // Report MMIO/IO Resources
+  //
+  Status = ReserveResourceInGcd (TRUE, EfiGcdMemoryTypeMemoryMappedIo, 0xFEC00000, SIZE_4KB, 0, SystemTable); // IOAPIC
+  ASSERT_EFI_ERROR (Status);
+
+  Status = ReserveResourceInGcd (TRUE, EfiGcdMemoryTypeMemoryMappedIo, 0xFED00000, SIZE_1KB, 0, SystemTable); // HPET
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Find the system table information guid hob
+  //
+  GuidHob = GetFirstGuidHob (&gUefiSystemTableInfoGuid);
+  ASSERT (GuidHob != NULL);
+  SystemTableInfo = (SYSTEM_TABLE_INFO *)GET_GUID_HOB_DATA (GuidHob);
+
+  //
+  // Install Acpi Table
+  //
+  if (SystemTableInfo->AcpiTableBase != 0 && SystemTableInfo->AcpiTableSize != 0) {
+    DEBUG ((DEBUG_ERROR, "Install Acpi Table at 0x%lx, length 0x%x\n", SystemTableInfo->AcpiTableBase, SystemTableInfo->AcpiTableSize));
+    Status = gBS->InstallConfigurationTable (&gEfiAcpiTableGuid, (VOID *)(UINTN)SystemTableInfo->AcpiTableBase);
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  //
+  // Install Smbios Table
+  //
+  if (SystemTableInfo->SmbiosTableBase != 0 && SystemTableInfo->SmbiosTableSize != 0) {
+    DEBUG ((DEBUG_ERROR, "Install Smbios Table at 0x%lx, length 0x%x\n", SystemTableInfo->SmbiosTableBase, SystemTableInfo->SmbiosTableSize));
+    Status = gBS->InstallConfigurationTable (&gEfiSmbiosTableGuid, (VOID *)(UINTN)SystemTableInfo->SmbiosTableBase);
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  //
+  // Find the frame buffer information and update PCDs
+  //
+  GuidHob = GetFirstGuidHob (&gEfiGraphicsInfoHobGuid);
+  if (GuidHob != NULL) {
+    GfxInfo = (EFI_PEI_GRAPHICS_INFO_HOB *)GET_GUID_HOB_DATA (GuidHob);
+    Status = PcdSet32S (PcdVideoHorizontalResolution, GfxInfo->GraphicsMode.HorizontalResolution);
+    ASSERT_EFI_ERROR (Status);
+    Status = PcdSet32S (PcdVideoVerticalResolution, GfxInfo->GraphicsMode.VerticalResolution);
+    ASSERT_EFI_ERROR (Status);
+    Status = PcdSet32S (PcdSetupVideoHorizontalResolution, GfxInfo->GraphicsMode.HorizontalResolution);
+    ASSERT_EFI_ERROR (Status);
+    Status = PcdSet32S (PcdSetupVideoVerticalResolution, GfxInfo->GraphicsMode.VerticalResolution);
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h
new file mode 100644
index 0000000000..512105fafd
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h
@@ -0,0 +1,30 @@
+/** @file
+  The header file of bootloader support DXE.
+
+Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#ifndef __DXE_BOOTLOADER_SUPPORT_H__
+#define __DXE_BOOTLOADER_SUPPORT_H__
+
+#include <PiDxe.h>
+
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/DxeServicesTableLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+
+#include <Guid/Acpi.h>
+#include <Guid/SmBios.h>
+#include <Guid/SystemTableInfoGuid.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+#include <Guid/GraphicsInfoHob.h>
+
+#include <IndustryStandard/Acpi.h>
+
+#endif
diff --git a/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
new file mode 100644
index 0000000000..4c2b4670af
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
@@ -0,0 +1,58 @@
+## @file
+# Bootloader Support DXE Module
+#
+# Report some MMIO/IO resources to dxe core, extract smbios and acpi tables
+#
+#  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+#
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = BlSupportDxe
+  FILE_GUID                      = C68DAA4E-7AB5-41e8-A91D-5954421053F3
+  MODULE_TYPE                    = DXE_DRIVER
+  VERSION_STRING                 = 1.0
+  ENTRY_POINT                    = BlDxeEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  BlSupportDxe.c
+  BlSupportDxe.h
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  UefiDriverEntryPoint
+  UefiBootServicesTableLib
+  DxeServicesTableLib
+  DebugLib
+  BaseMemoryLib
+  UefiLib
+  HobLib
+
+[Guids]
+  gEfiAcpiTableGuid
+  gEfiSmbiosTableGuid
+  gUefiSystemTableInfoGuid
+  gUefiAcpiBoardInfoGuid
+  gEfiGraphicsInfoHobGuid
+
+[Pcd]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution
+
+[Depex]
+  TRUE
diff --git a/UefiPayloadPkg/BlSupportPei/BlSupportPei.c b/UefiPayloadPkg/BlSupportPei/BlSupportPei.c
new file mode 100644
index 0000000000..90433b609f
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportPei/BlSupportPei.c
@@ -0,0 +1,566 @@
+/** @file
+  This PEIM will parse bootloader information and report resource information into pei core.
+  This file contains the main entrypoint of the PEIM.
+
+Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#include "BlSupportPei.h"
+
+#define LEGACY_8259_MASK_REGISTER_MASTER  0x21
+#define LEGACY_8259_MASK_REGISTER_SLAVE   0xA1
+
+EFI_MEMORY_TYPE_INFORMATION mDefaultMemoryTypeInformation[] = {
+  { EfiACPIReclaimMemory,   FixedPcdGet32 (PcdMemoryTypeEfiACPIReclaimMemory) },
+  { EfiACPIMemoryNVS,       FixedPcdGet32 (PcdMemoryTypeEfiACPIMemoryNVS) },
+  { EfiReservedMemoryType,  FixedPcdGet32 (PcdMemoryTypeEfiReservedMemoryType) },
+  { EfiRuntimeServicesData, FixedPcdGet32 (PcdMemoryTypeEfiRuntimeServicesData) },
+  { EfiRuntimeServicesCode, FixedPcdGet32 (PcdMemoryTypeEfiRuntimeServicesCode) },
+  { EfiMaxMemoryType,       0     }
+};
+
+EFI_PEI_PPI_DESCRIPTOR   mPpiBootMode[] = {
+  {
+    EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST,
+    &gEfiPeiMasterBootModePpiGuid,
+    NULL
+  }
+};
+
+EFI_PEI_GRAPHICS_DEVICE_INFO_HOB mDefaultGraphicsDeviceInfo = {
+  MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT8,  MAX_UINT8
+};
+
+/**
+  Create memory mapped io resource hob.
+
+  @param  MmioBase    Base address of the memory mapped io range
+  @param  MmioSize    Length of the memory mapped io range
+
+**/
+VOID
+BuildMemoryMappedIoRangeHob (
+  EFI_PHYSICAL_ADDRESS        MmioBase,
+  UINT64                      MmioSize
+  )
+{
+  BuildResourceDescriptorHob (
+    EFI_RESOURCE_MEMORY_MAPPED_IO,
+    (EFI_RESOURCE_ATTRIBUTE_PRESENT    |
+    EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+    EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_TESTED),
+    MmioBase,
+    MmioSize
+    );
+
+  BuildMemoryAllocationHob (
+    MmioBase,
+    MmioSize,
+    EfiMemoryMappedIO
+    );
+}
+
+/**
+  Check the integrity of firmware volume header
+
+  @param[in]  FwVolHeader   A pointer to a firmware volume header
+
+  @retval     TRUE          The firmware volume is consistent
+  @retval     FALSE         The firmware volume has corrupted.
+
+**/
+STATIC
+BOOLEAN
+IsFvHeaderValid (
+  IN EFI_FIRMWARE_VOLUME_HEADER    *FwVolHeader
+  )
+{
+  UINT16 Checksum;
+
+  // Skip nv storage fv
+  if (CompareMem (&FwVolHeader->FileSystemGuid, &gEfiFirmwareFileSystem2Guid, sizeof(EFI_GUID)) != 0 ) {
+    return FALSE;
+  }
+
+  if ( (FwVolHeader->Revision != EFI_FVH_REVISION)   ||
+     (FwVolHeader->Signature != EFI_FVH_SIGNATURE) ||
+     (FwVolHeader->FvLength == ((UINTN) -1))       ||
+     ((FwVolHeader->HeaderLength & 0x01 ) !=0) )  {
+    return FALSE;
+  }
+
+  Checksum = CalculateCheckSum16 ((UINT16 *) FwVolHeader, FwVolHeader->HeaderLength);
+  if (Checksum != 0) {
+    DEBUG (( DEBUG_ERROR,
+              "ERROR - Invalid Firmware Volume Header Checksum, change 0x%04x to 0x%04x\r\n",
+              FwVolHeader->Checksum,
+              (UINT16)( Checksum + FwVolHeader->Checksum )));
+    return TRUE; //FALSE; Need update UEFI build tool when patching entrypoin @start of fd.
+  }
+
+  return TRUE;
+}
+
+/**
+  Install FvInfo PPI and create fv hobs for remained fvs
+
+**/
+VOID
+PeiReportRemainedFvs (
+  VOID
+  )
+{
+  UINT8*  TempPtr;
+  UINT8*  EndPtr;
+
+  TempPtr = (UINT8* )(UINTN) PcdGet32 (PcdPayloadFdMemBase);
+  EndPtr = (UINT8* )(UINTN) (PcdGet32 (PcdPayloadFdMemBase) + PcdGet32 (PcdPayloadFdMemSize));
+
+  for (;TempPtr < EndPtr;) {
+    if (IsFvHeaderValid ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)) {
+      if (TempPtr != (UINT8* )(UINTN) PcdGet32 (PcdPayloadFdMemBase))  {
+        // Skip the PEI FV
+        DEBUG((DEBUG_INFO, "Found one valid fv : 0x%lx.\n", TempPtr, ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength));
+
+        PeiServicesInstallFvInfoPpi (
+          NULL,
+          (VOID *) (UINTN) TempPtr,
+          (UINT32) (UINTN) ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength,
+          NULL,
+          NULL
+          );
+        BuildFvHob ((EFI_PHYSICAL_ADDRESS)(UINTN) TempPtr, ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength);
+      }
+    }
+    TempPtr += ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength;
+  }
+}
+
+
+/**
+  Find the board related info from ACPI table
+
+  @param  AcpiTableBase          ACPI table start address in memory
+  @param  AcpiBoardInfo          Pointer to the acpi board info strucutre
+
+  @retval RETURN_SUCCESS     Successfully find out all the required information.
+  @retval RETURN_NOT_FOUND   Failed to find the required info.
+
+**/
+RETURN_STATUS
+ParseAcpiInfo (
+  IN   UINT64                                   AcpiTableBase,
+  OUT  ACPI_BOARD_INFO                          *AcpiBoardInfo
+  )
+{
+  EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER  *Rsdp;
+  EFI_ACPI_DESCRIPTION_HEADER                   *Rsdt;
+  UINT32                                        *Entry32;
+  UINTN                                         Entry32Num;
+  EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE     *Fadt;
+  EFI_ACPI_DESCRIPTION_HEADER                   *Xsdt;
+  UINT64                                        *Entry64;
+  UINTN                                         Entry64Num;
+  UINTN                                         Idx;
+  EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_BASE_ADDRESS_TABLE_HEADER *MmCfgHdr;
+  EFI_ACPI_MEMORY_MAPPED_ENHANCED_CONFIGURATION_SPACE_BASE_ADDRESS_ALLOCATION_STRUCTURE *MmCfgBase;
+
+  Rsdp = (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER *)(UINTN)AcpiTableBase;
+  DEBUG ((DEBUG_INFO, "Rsdp at 0x%p\n", Rsdp));
+  DEBUG ((DEBUG_INFO, "Rsdt at 0x%x, Xsdt at 0x%lx\n", Rsdp->RsdtAddress, Rsdp->XsdtAddress));
+
+  //
+  // Search Rsdt First
+  //
+  Fadt     = NULL;
+  MmCfgHdr = NULL;
+  Rsdt     = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN)(Rsdp->RsdtAddress);
+  if (Rsdt != NULL) {
+    Entry32  = (UINT32 *)(Rsdt + 1);
+    Entry32Num = (Rsdt->Length - sizeof(EFI_ACPI_DESCRIPTION_HEADER)) >> 2;
+    for (Idx = 0; Idx < Entry32Num; Idx++) {
+      if (*(UINT32 *)(UINTN)(Entry32[Idx]) == EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE) {
+        Fadt = (EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE *)(UINTN)(Entry32[Idx]);
+        DEBUG ((DEBUG_INFO, "Found Fadt in Rsdt\n"));
+      }
+
+      if (*(UINT32 *)(UINTN)(Entry32[Idx]) == EFI_ACPI_5_0_PCI_EXPRESS_MEMORY_MAPPED_CONFIGURATION_SPACE_BASE_ADDRESS_DESCRIPTION_TABLE_SIGNATURE) {
+        MmCfgHdr = (EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_BASE_ADDRESS_TABLE_HEADER *)(UINTN)(Entry32[Idx]);
+        DEBUG ((DEBUG_INFO, "Found MM config address in Rsdt\n"));
+      }
+
+      if ((Fadt != NULL) && (MmCfgHdr != NULL)) {
+        goto Done;
+      }
+    }
+  }
+
+  //
+  // Search Xsdt Second
+  //
+  Xsdt     = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN)(Rsdp->XsdtAddress);
+  if (Xsdt != NULL) {
+    Entry64  = (UINT64 *)(Xsdt + 1);
+    Entry64Num = (Xsdt->Length - sizeof(EFI_ACPI_DESCRIPTION_HEADER)) >> 3;
+    for (Idx = 0; Idx < Entry64Num; Idx++) {
+      if (*(UINT32 *)(UINTN)(Entry64[Idx]) == EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE) {
+        Fadt = (EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE *)(UINTN)(Entry64[Idx]);
+        DEBUG ((DEBUG_INFO, "Found Fadt in Xsdt\n"));
+      }
+
+      if (*(UINT32 *)(UINTN)(Entry64[Idx]) == EFI_ACPI_5_0_PCI_EXPRESS_MEMORY_MAPPED_CONFIGURATION_SPACE_BASE_ADDRESS_DESCRIPTION_TABLE_SIGNATURE) {
+        MmCfgHdr = (EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_BASE_ADDRESS_TABLE_HEADER *)(UINTN)(Entry32[Idx]);
+        DEBUG ((DEBUG_INFO, "Found MM config address in Xsdt\n"));
+      }
+
+      if ((Fadt != NULL) && (MmCfgHdr != NULL)) {
+        goto Done;
+      }
+    }
+  }
+
+  if (Fadt == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+Done:
+
+  AcpiBoardInfo->PmCtrlRegBase   = Fadt->Pm1aCntBlk;
+  AcpiBoardInfo->PmTimerRegBase  = Fadt->PmTmrBlk;
+  AcpiBoardInfo->ResetRegAddress = Fadt->ResetReg.Address;
+  AcpiBoardInfo->ResetValue      = Fadt->ResetValue;
+  AcpiBoardInfo->PmEvtBase       = Fadt->Pm1aEvtBlk;
+  AcpiBoardInfo->PmGpeEnBase     = Fadt->Gpe0Blk + Fadt->Gpe0BlkLen / 2;
+
+  if (MmCfgHdr != NULL) {
+    MmCfgBase = (EFI_ACPI_MEMORY_MAPPED_ENHANCED_CONFIGURATION_SPACE_BASE_ADDRESS_ALLOCATION_STRUCTURE *)((UINT8*) MmCfgHdr + sizeof (*MmCfgHdr));
+    AcpiBoardInfo->PcieBaseAddress = MmCfgBase->BaseAddress;
+  } else {
+    AcpiBoardInfo->PcieBaseAddress = 0;
+  }
+  DEBUG ((DEBUG_INFO, "PmCtrl  Reg 0x%lx\n",  AcpiBoardInfo->PmCtrlRegBase));
+  DEBUG ((DEBUG_INFO, "PmTimer Reg 0x%lx\n",  AcpiBoardInfo->PmTimerRegBase));
+  DEBUG ((DEBUG_INFO, "Reset   Reg 0x%lx\n",  AcpiBoardInfo->ResetRegAddress));
+  DEBUG ((DEBUG_INFO, "Reset   Value 0x%x\n", AcpiBoardInfo->ResetValue));
+  DEBUG ((DEBUG_INFO, "PmEvt   Reg 0x%lx\n",  AcpiBoardInfo->PmEvtBase));
+  DEBUG ((DEBUG_INFO, "PmGpeEn Reg 0x%lx\n",  AcpiBoardInfo->PmGpeEnBase));
+  DEBUG ((DEBUG_INFO, "PcieBaseAddr 0x%lx\n", AcpiBoardInfo->PcieBaseAddress));
+
+  //
+  // Verify values for proper operation
+  //
+  ASSERT(Fadt->Pm1aCntBlk != 0);
+  ASSERT(Fadt->PmTmrBlk != 0);
+  ASSERT(Fadt->ResetReg.Address != 0);
+  ASSERT(Fadt->Pm1aEvtBlk != 0);
+  ASSERT(Fadt->Gpe0Blk != 0);
+
+  DEBUG_CODE_BEGIN ();
+    BOOLEAN    SciEnabled;
+
+    //
+    // Check the consistency of SCI enabling
+    //
+
+    //
+    // Get SCI_EN value
+    //
+   if (Fadt->Pm1CntLen == 4) {
+      SciEnabled = (IoRead32 (Fadt->Pm1aCntBlk) & BIT0)? TRUE : FALSE;
+    } else {
+      //
+      // if (Pm1CntLen == 2), use 16 bit IO read;
+      // if (Pm1CntLen != 2 && Pm1CntLen != 4), use 16 bit IO read as a fallback
+      //
+      SciEnabled = (IoRead16 (Fadt->Pm1aCntBlk) & BIT0)? TRUE : FALSE;
+    }
+
+    if (!(Fadt->Flags & EFI_ACPI_5_0_HW_REDUCED_ACPI) &&
+        (Fadt->SmiCmd == 0) &&
+       !SciEnabled) {
+      //
+      // The ACPI enabling status is inconsistent: SCI is not enabled but ACPI
+      // table does not provide a means to enable it through FADT->SmiCmd
+      //
+      DEBUG ((DEBUG_ERROR, "ERROR: The ACPI enabling status is inconsistent: SCI is not"
+        " enabled but the ACPI table does not provide a means to enable it through FADT->SmiCmd."
+        " This may cause issues in OS.\n"));
+    }
+  DEBUG_CODE_END ();
+
+  return RETURN_SUCCESS;
+}
+
+EFI_STATUS
+MemInfoCallback (
+  IN MEMROY_MAP_ENTRY             *MemoryMapEntry,
+  IN VOID                         *Params
+  )
+{
+  PAYLOAD_MEM_INFO        *MemInfo;
+  UINTN                   Attribue;
+  EFI_PHYSICAL_ADDRESS    Base;
+  EFI_RESOURCE_TYPE       Type;
+  UINT64                  Size;
+  UINT32                  SystemLowMemTop;
+
+  Attribue = EFI_RESOURCE_ATTRIBUTE_PRESENT |
+             EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+             EFI_RESOURCE_ATTRIBUTE_TESTED |
+             EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+             EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE |
+             EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE |
+             EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE;
+
+  MemInfo = (PAYLOAD_MEM_INFO *)Params;
+  Type    = (MemoryMapEntry->Type == 1) ? EFI_RESOURCE_SYSTEM_MEMORY : EFI_RESOURCE_MEMORY_RESERVED;
+  Base    = MemoryMapEntry->Base;
+  Size    = MemoryMapEntry->Size;
+
+  if ((Base  < 0x100000) && ((Base + Size) > 0x100000)) {
+    Size -= (0x100000 - Base);
+    Base  = 0x100000;
+  }
+
+  if (Base >= 0x100000) {
+    if (Type == EFI_RESOURCE_SYSTEM_MEMORY) {
+      if (Base < 0x100000000ULL) {
+        MemInfo->UsableLowMemTop = (UINT32)(Base + Size);
+      } else {
+        Attribue &= ~EFI_RESOURCE_ATTRIBUTE_TESTED;
+      }
+      BuildResourceDescriptorHob (
+        EFI_RESOURCE_SYSTEM_MEMORY,
+        Attribue,
+        (EFI_PHYSICAL_ADDRESS)Base,
+        Size
+        );
+    } else if (Type == EFI_RESOURCE_MEMORY_RESERVED) {
+      BuildResourceDescriptorHob (
+        EFI_RESOURCE_MEMORY_RESERVED,
+        Attribue,
+        (EFI_PHYSICAL_ADDRESS)Base,
+        Size
+        );
+      if (Base < 0x100000000ULL) {
+        SystemLowMemTop = ((UINT32)(Base + Size) + 0x0FFFFFFF) & 0xF0000000;
+        if (SystemLowMemTop > MemInfo->SystemLowMemTop) {
+          MemInfo->SystemLowMemTop = SystemLowMemTop;
+        }
+      }
+    }
+  }
+
+  return EFI_SUCCESS;
+}
+
+/**
+  This is the entrypoint of PEIM
+
+  @param  FileHandle  Handle of the file being invoked.
+  @param  PeiServices Describes the list of possible PEI Services.
+
+  @retval EFI_SUCCESS if it completed successfully.
+**/
+EFI_STATUS
+EFIAPI
+BlPeiEntryPoint (
+  IN       EFI_PEI_FILE_HANDLE     FileHandle,
+  IN CONST EFI_PEI_SERVICES        **PeiServices
+  )
+{
+  EFI_STATUS                       Status;
+  UINT64                           LowMemorySize;
+  UINT64                           PeiMemSize = SIZE_64MB;
+  EFI_PHYSICAL_ADDRESS             PeiMemBase = 0;
+  UINT32                           RegEax;
+  UINT8                            PhysicalAddressBits;
+  PAYLOAD_MEM_INFO                 PldMemInfo;
+  SYSTEM_TABLE_INFO                SysTableInfo;
+  SYSTEM_TABLE_INFO                *NewSysTableInfo;
+  ACPI_BOARD_INFO                  AcpiBoardInfo;
+  ACPI_BOARD_INFO                  *NewAcpiBoardInfo;
+  EFI_PEI_GRAPHICS_INFO_HOB        GfxInfo;
+  EFI_PEI_GRAPHICS_INFO_HOB        *NewGfxInfo;
+  EFI_PEI_GRAPHICS_DEVICE_INFO_HOB GfxDeviceInfo;
+  EFI_PEI_GRAPHICS_DEVICE_INFO_HOB *NewGfxDeviceInfo;
+
+
+  //
+  // Report lower 640KB of RAM. Attribute EFI_RESOURCE_ATTRIBUTE_TESTED
+  // is intentionally omitted to prevent erasing of the coreboot header
+  // record before it is processed by ParseMemoryInfo.
+  //
+  BuildResourceDescriptorHob (
+    EFI_RESOURCE_SYSTEM_MEMORY,
+    (
+    EFI_RESOURCE_ATTRIBUTE_PRESENT |
+    EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+    EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
+    ),
+    (EFI_PHYSICAL_ADDRESS)(0),
+    (UINT64)(0xA0000)
+    );
+
+  BuildResourceDescriptorHob (
+    EFI_RESOURCE_MEMORY_RESERVED,
+    (
+    EFI_RESOURCE_ATTRIBUTE_PRESENT |
+    EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+    EFI_RESOURCE_ATTRIBUTE_TESTED |
+    EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
+    ),
+    (EFI_PHYSICAL_ADDRESS)(0xA0000),
+    (UINT64)(0x60000)
+    );
+
+
+  //
+  // Parse memory info
+  //
+  ZeroMem (&PldMemInfo, sizeof(PldMemInfo));
+  Status = ParseMemoryInfo (MemInfoCallback, &PldMemInfo);
+  if (EFI_ERROR(Status)) {
+    return Status;
+  }
+
+  //
+  // Install memory
+  //
+  LowMemorySize = PldMemInfo.UsableLowMemTop;
+  PeiMemBase = (LowMemorySize - PeiMemSize) & (~(BASE_64KB - 1));
+  DEBUG ((DEBUG_INFO, "Low memory 0x%lx\n", LowMemorySize));
+  DEBUG ((DEBUG_INFO, "SystemLowMemTop 0x%x\n", PldMemInfo.SystemLowMemTop));
+  DEBUG ((DEBUG_INFO, "PeiMemBase: 0x%lx.\n", PeiMemBase));
+  DEBUG ((DEBUG_INFO, "PeiMemSize: 0x%lx.\n", PeiMemSize));
+  Status = PeiServicesInstallPeiMemory (PeiMemBase, PeiMemSize);
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Set cache on the physical memory
+  //
+  MtrrSetMemoryAttribute (BASE_1MB, LowMemorySize - BASE_1MB, CacheWriteBack);
+  MtrrSetMemoryAttribute (0, 0xA0000, CacheWriteBack);
+
+  //
+  // Create Memory Type Information HOB
+  //
+  BuildGuidDataHob (
+    &gEfiMemoryTypeInformationGuid,
+    mDefaultMemoryTypeInformation,
+    sizeof(mDefaultMemoryTypeInformation)
+    );
+
+  //
+  // Create Fv hob
+  //
+  PeiReportRemainedFvs ();
+
+  BuildMemoryAllocationHob (
+    PcdGet32 (PcdPayloadFdMemBase),
+    PcdGet32 (PcdPayloadFdMemSize),
+    EfiBootServicesData
+    );
+
+  //
+  // Build CPU memory space and IO space hob
+  //
+  AsmCpuid (0x80000000, &RegEax, NULL, NULL, NULL);
+  if (RegEax >= 0x80000008) {
+    AsmCpuid (0x80000008, &RegEax, NULL, NULL, NULL);
+    PhysicalAddressBits = (UINT8) RegEax;
+  } else {
+    PhysicalAddressBits  = 36;
+  }
+
+  //
+  // Create a CPU hand-off information
+  //
+  BuildCpuHob (PhysicalAddressBits, 16);
+
+  //
+  // Report Local APIC range
+  //
+  BuildMemoryMappedIoRangeHob (0xFEC80000, SIZE_512KB);
+
+  //
+  // Boot mode
+  //
+  Status = PeiServicesSetBootMode (BOOT_WITH_FULL_CONFIGURATION);
+  ASSERT_EFI_ERROR (Status);
+
+  Status = PeiServicesInstallPpi (mPpiBootMode);
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Create guid hob for frame buffer information
+  //
+  Status = ParseGfxInfo (&GfxInfo);
+  if (!EFI_ERROR (Status)) {
+    NewGfxInfo = BuildGuidHob (&gEfiGraphicsInfoHobGuid, sizeof (GfxInfo));
+    ASSERT (NewGfxInfo != NULL);
+    CopyMem (NewGfxInfo, &GfxInfo, sizeof (GfxInfo));
+    DEBUG ((DEBUG_INFO, "Created graphics info hob\n"));
+  }
+
+
+  Status = ParseGfxDeviceInfo (&GfxDeviceInfo);
+  if (!EFI_ERROR (Status)) {
+    NewGfxDeviceInfo = BuildGuidHob (&gEfiGraphicsDeviceInfoHobGuid, sizeof (GfxDeviceInfo));
+    ASSERT (NewGfxDeviceInfo != NULL);
+    CopyMem (NewGfxDeviceInfo, &GfxDeviceInfo, sizeof (GfxDeviceInfo));
+    DEBUG ((DEBUG_INFO, "Created graphics device info hob\n"));
+  }
+
+
+  //
+  // Create guid hob for system tables like acpi table and smbios table
+  //
+  Status = ParseSystemTable(&SysTableInfo);
+  ASSERT_EFI_ERROR (Status);
+  if (!EFI_ERROR (Status)) {
+    NewSysTableInfo = BuildGuidHob (&gUefiSystemTableInfoGuid, sizeof (SYSTEM_TABLE_INFO));
+    ASSERT (NewSysTableInfo != NULL);
+    CopyMem (NewSysTableInfo, &SysTableInfo, sizeof (SYSTEM_TABLE_INFO));
+    DEBUG ((DEBUG_INFO, "Detected Acpi Table at 0x%lx, length 0x%x\n", SysTableInfo.AcpiTableBase, SysTableInfo.AcpiTableSize));
+    DEBUG ((DEBUG_INFO, "Detected Smbios Table at 0x%lx, length 0x%x\n", SysTableInfo.SmbiosTableBase, SysTableInfo.SmbiosTableSize));
+  }
+
+  //
+  // Create guid hob for acpi board information
+  //
+  Status = ParseAcpiInfo (SysTableInfo.AcpiTableBase, &AcpiBoardInfo);
+  ASSERT_EFI_ERROR (Status);
+  if (!EFI_ERROR (Status)) {
+    NewAcpiBoardInfo = BuildGuidHob (&gUefiAcpiBoardInfoGuid, sizeof (ACPI_BOARD_INFO));
+    ASSERT (NewAcpiBoardInfo != NULL);
+    CopyMem (NewAcpiBoardInfo, &AcpiBoardInfo, sizeof (ACPI_BOARD_INFO));
+    DEBUG ((DEBUG_INFO, "Create acpi board info guid hob\n"));
+  }
+
+  //
+  // Parse platform specific information.
+  //
+  Status = ParsePlatformInfo ();
+  if (EFI_ERROR (Status)) {
+    DEBUG ((DEBUG_ERROR, "Error when parsing platform info, Status = %r\n", Status));
+    return Status;
+  }
+
+  //
+  // Mask off all legacy 8259 interrupt sources
+  //
+  IoWrite8 (LEGACY_8259_MASK_REGISTER_MASTER, 0xFF);
+  IoWrite8 (LEGACY_8259_MASK_REGISTER_SLAVE,  0xFF);
+
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/BlSupportPei/BlSupportPei.h b/UefiPayloadPkg/BlSupportPei/BlSupportPei.h
new file mode 100644
index 0000000000..d11a3570a1
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportPei/BlSupportPei.h
@@ -0,0 +1,39 @@
+/** @file
+  The header file of bootloader support PEIM.
+
+Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#ifndef __PEI_BOOTLOADER_SUPPORT_H__
+#define __PEI_BOOTLOADER_SUPPORT_H__
+
+#include <PiPei.h>
+#include <Library/PeimEntryPoint.h>
+#include <Library/PeiServicesLib.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/HobLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BlParseLib.h>
+#include <Library/MtrrLib.h>
+#include <Library/IoLib.h>
+#include <Library/PlatformSupportLib.h>
+#include <IndustryStandard/Acpi.h>
+#include <Guid/MemoryTypeInformation.h>
+#include <Guid/FirmwareFileSystem2.h>
+#include <Guid/SystemTableInfoGuid.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+#include <Guid/GraphicsInfoHob.h>
+#include <Ppi/MasterBootMode.h>
+#include <IndustryStandard/MemoryMappedConfigurationSpaceAccessTable.h>
+
+typedef struct {
+  UINT32  UsableLowMemTop;
+  UINT32  SystemLowMemTop;
+} PAYLOAD_MEM_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/BlSupportPei/BlSupportPei.inf b/UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
new file mode 100644
index 0000000000..711fe63fe6
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
@@ -0,0 +1,73 @@
+## @file
+# Bootloader Support PEI Module
+#
+# Parses bootloader information and report resource information into pei core. It will install
+# the memory as required.
+#
+#  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+#
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = BlSupportPeim
+  FILE_GUID                      = 352C6AF8-315B-4bd6-B04F-31D4ED1EBE57
+  MODULE_TYPE                    = PEIM
+  VERSION_STRING                 = 1.0
+  ENTRY_POINT                    = BlPeiEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources]
+  BlSupportPei.c
+  BlSupportPei.h
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  IntelFsp2Pkg/IntelFsp2Pkg.dec
+  IntelFsp2WrapperPkg/IntelFsp2WrapperPkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+  UefiCpuPkg/UefiCpuPkg.dec
+
+[LibraryClasses]
+  PeimEntryPoint
+  PeiServicesLib
+  BaseLib
+  BaseMemoryLib
+  DebugLib
+  HobLib
+  PcdLib
+  BlParseLib
+  MtrrLib
+  IoLib
+  PlatformSupportLib
+
+[Guids]
+  gEfiMemoryTypeInformationGuid
+  gEfiFirmwareFileSystem2Guid
+  gUefiSystemTableInfoGuid
+  gEfiGraphicsInfoHobGuid
+  gEfiGraphicsDeviceInfoHobGuid
+  gUefiAcpiBoardInfoGuid
+
+[Ppis]
+  gEfiPeiMasterBootModePpiGuid
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIReclaimMemory
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIMemoryNVS
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiReservedMemoryType
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesData
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesCode
+
+[Depex]
+  TRUE
diff --git a/UefiPayloadPkg/BuildAndIntegrationInstructions.txt b/UefiPayloadPkg/BuildAndIntegrationInstructions.txt
new file mode 100644
index 0000000000..2cacd48904
--- /dev/null
+++ b/UefiPayloadPkg/BuildAndIntegrationInstructions.txt
@@ -0,0 +1,82 @@
+================================================================================
+Build And Integration Instructions
+2019 March 27th
+================================================================================
+
+================================================================================
+DISCLAIMER
+================================================================================
+This release note as well as the software described in it is furnished under license
+and may only be used or copied in accordance with the terms of the license. The
+information in this manual is furnished for informational use only, is subject to
+change without notice, and should not be construed as a commitment by Intel Corporation.
+Intel Corporation assumes no responsibility or liability for any errors or inaccuracies
+that may appear in this document or any software that may be provided in association
+with this document.
+Except as permitted by such license, no part of this document may be reproduced,
+stored in a retrieval system, or transmitted in any form or by any means without
+the express written consent of Intel Corporation.
+
+================================================================================
+                                     INDEX
+================================================================================
+A. INTRODUCTION
+B. HOW TO BUILD
+C. HOW TO INTEGRATE INTO COREBOOT
+D. HOW TO INTEGRATE INTO SLIM BOOTLOADER
+
+================================================================================
+A. INTRODUCTION
+================================================================================
+This document provides instructions on how to build UEFI Payload and how to
+integrate it into coreboot or Slim Bootloader firmware.
+
+================================================================================
+B. HOW TO BUILD
+================================================================================
+1. Run the below two commands in windows command prompt window:
+   edksetup.bat
+
+   For debug ia32 build:
+   build -a IA32 -p UefiPayloadPkg\UefiPayloadPkgIa32.dsc -b DEBUG -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   For release ia32 build:
+   build -a IA32 -p UefiPayloadPkg\UefiPayloadPkgIa32.dsc -b RELEASE -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   For debug X64 build:
+   build -a IA32 -a X64 -p UefiPayloadPkg\UefiPayloadPkgIa32X64.dsc -b DEBUG -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   For release X64 build:
+   build -a IA32 -a X64 -p UefiPayloadPkg\UefiPayloadPkgIa32X64.dsc -b RELEASE -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   <ToolChain> is the EDK II build environment on your host. Currently it was tested
+   with VS2015x86 toolchain.
+   <Bootloader> could be "SBL" for Slim Bootloader and "COREBOOT" for coreboot.
+
+   Refer to https://github.com/tianocore/tianocore.github.io/wiki/UDK2018-How-to-Build for
+   details about EDK II build steps.
+
+2. If build is successfully, the payload image (UEFIPAYLOAD.fd) will be generated inside the
+   folder of Build\UefiPayloadPkg.
+
+================================================================================
+C. HOW TO INTEGRATE INTO COREBOOT
+================================================================================
+1. Copy the payload image (UEFIPAYLOAD.fd) into the top-level directory of Coreboot source tree.
+2. Run "make menuconfig" in linux console to start Coreboot configuration surface.
+3. In the Payload section,
+   1) Choose "An ELF executable payload" for the option of "Add a payload".
+   2) Type the path of payload image for the option of "Payload path and filename".
+   3) Select the option of "Use LZMA compression for payloads".
+4. If the graphics console is required in UEFI payload, enable framebuffer initialization in coreboot.
+   This could be done by enabling native graphics or using VGA BIOS option rom.
+5. Build the coreboot firmware image.
+
+================================================================================
+D. HOW TO INTEGRATE INTO SLIM BOOTLOADER
+================================================================================
+Please refer https://slimbootloader.github.io/how-tos/integrate-multiple-payloads.html for below steps.
+1. Copy the payload image (UEFIPAYLOAD.fd) into Slim Bootloader source at PayloadPkg\PayloadBins\UefiPld.fd
+2. Update config data to make UEFI payload as default payload if required.
+3. Build Slim Bootloader with UEFI payload:
+   BuildLoader.py build <Platform> -p "OsLoader.efi:LLDR:Lz4;UefiPld.fd:UEFI:Lzma"
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c b/UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c
new file mode 100644
index 0000000000..7b7f5683a5
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c
@@ -0,0 +1,184 @@
+/** @file
+  UEFI Component Name(2) protocol implementation for the generic GOP driver.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+
+**/
+
+#include <PiDxe.h>
+#include <Library/UefiLib.h>
+
+extern EFI_COMPONENT_NAME_PROTOCOL  mGraphicsOutputComponentName;
+extern EFI_COMPONENT_NAME2_PROTOCOL mGraphicsOutputComponentName2;
+
+//
+// Driver name table for GraphicsOutput module.
+// It is shared by the implementation of ComponentName & ComponentName2 Protocol.
+//
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE mGraphicsOutputDriverNameTable[] = {
+  {
+    "eng;en",
+    L"Generic Graphics Output Driver"
+  },
+  {
+    NULL,
+    NULL
+  }
+};
+
+/**
+  Retrieves a Unicode string that is the user readable name of the driver.
+
+  This function retrieves the user readable name of a driver in the form of a
+  Unicode string. If the driver specified by This has a user readable name in
+  the language specified by Language, then a pointer to the driver name is
+  returned in DriverName, and EFI_SUCCESS is returned. If the driver specified
+  by This does not support the language specified by Language,
+  then EFI_UNSUPPORTED is returned.
+
+  @param  This[in]              A pointer to the EFI_COMPONENT_NAME2_PROTOCOL or
+                                EFI_COMPONENT_NAME_PROTOCOL instance.
+
+  @param  Language[in]          A pointer to a Null-terminated ASCII string
+                                array indicating the language. This is the
+                                language of the driver name that the caller is
+                                requesting, and it must match one of the
+                                languages specified in SupportedLanguages. The
+                                number of languages supported by a driver is up
+                                to the driver writer. Language is specified
+                                in RFC 4646 or ISO 639-2 language code format.
+
+  @param  DriverName[out]       A pointer to the Unicode string to return.
+                                This Unicode string is the name of the
+                                driver specified by This in the language
+                                specified by Language.
+
+  @retval EFI_SUCCESS           The Unicode string for the Driver specified by
+                                This and the language specified by Language was
+                                returned in DriverName.
+
+  @retval EFI_INVALID_PARAMETER Language is NULL.
+
+  @retval EFI_INVALID_PARAMETER DriverName is NULL.
+
+  @retval EFI_UNSUPPORTED       The driver specified by This does not support
+                                the language specified by Language.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputComponentNameGetDriverName (
+  IN  EFI_COMPONENT_NAME_PROTOCOL  *This,
+  IN  CHAR8                        *Language,
+  OUT CHAR16                       **DriverName
+  )
+{
+  return LookupUnicodeString2 (
+           Language,
+           This->SupportedLanguages,
+           mGraphicsOutputDriverNameTable,
+           DriverName,
+           (BOOLEAN) (This == &mGraphicsOutputComponentName)
+           );
+}
+
+/**
+  Retrieves a Unicode string that is the user readable name of the controller
+  that is being managed by a driver.
+
+  This function retrieves the user readable name of the controller specified by
+  ControllerHandle and ChildHandle in the form of a Unicode string. If the
+  driver specified by This has a user readable name in the language specified by
+  Language, then a pointer to the controller name is returned in ControllerName,
+  and EFI_SUCCESS is returned.  If the driver specified by This is not currently
+  managing the controller specified by ControllerHandle and ChildHandle,
+  then EFI_UNSUPPORTED is returned.  If the driver specified by This does not
+  support the language specified by Language, then EFI_UNSUPPORTED is returned.
+
+  @param  This[in]              A pointer to the EFI_COMPONENT_NAME2_PROTOCOL or
+                                EFI_COMPONENT_NAME_PROTOCOL instance.
+
+  @param  ControllerHandle[in]  The handle of a controller that the driver
+                                specified by This is managing.  This handle
+                                specifies the controller whose name is to be
+                                returned.
+
+  @param  ChildHandle[in]       The handle of the child controller to retrieve
+                                the name of.  This is an optional parameter that
+                                may be NULL.  It will be NULL for device
+                                drivers.  It will also be NULL for a bus drivers
+                                that wish to retrieve the name of the bus
+                                controller.  It will not be NULL for a bus
+                                driver that wishes to retrieve the name of a
+                                child controller.
+
+  @param  Language[in]          A pointer to a Null-terminated ASCII string
+                                array indicating the language.  This is the
+                                language of the driver name that the caller is
+                                requesting, and it must match one of the
+                                languages specified in SupportedLanguages. The
+                                number of languages supported by a driver is up
+                                to the driver writer. Language is specified in
+                                RFC 4646 or ISO 639-2 language code format.
+
+  @param  ControllerName[out]   A pointer to the Unicode string to return.
+                                This Unicode string is the name of the
+                                controller specified by ControllerHandle and
+                                ChildHandle in the language specified by
+                                Language from the point of view of the driver
+                                specified by This.
+
+  @retval EFI_SUCCESS           The Unicode string for the user readable name in
+                                the language specified by Language for the
+                                driver specified by This was returned in
+                                DriverName.
+
+  @retval EFI_INVALID_PARAMETER ControllerHandle is NULL.
+
+  @retval EFI_INVALID_PARAMETER ChildHandle is not NULL and it is not a valid
+                                EFI_HANDLE.
+
+  @retval EFI_INVALID_PARAMETER Language is NULL.
+
+  @retval EFI_INVALID_PARAMETER ControllerName is NULL.
+
+  @retval EFI_UNSUPPORTED       The driver specified by This is not currently
+                                managing the controller specified by
+                                ControllerHandle and ChildHandle.
+
+  @retval EFI_UNSUPPORTED       The driver specified by This does not support
+                                the language specified by Language.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputComponentNameGetControllerName (
+  IN  EFI_COMPONENT_NAME_PROTOCOL                     *This,
+  IN  EFI_HANDLE                                      ControllerHandle,
+  IN  EFI_HANDLE                                      ChildHandle        OPTIONAL,
+  IN  CHAR8                                           *Language,
+  OUT CHAR16                                          **ControllerName
+  )
+{
+  return EFI_UNSUPPORTED;
+}
+
+//
+// EFI Component Name Protocol
+//
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME_PROTOCOL  mGraphicsOutputComponentName = {
+  GraphicsOutputComponentNameGetDriverName,
+  GraphicsOutputComponentNameGetControllerName,
+  "eng"
+};
+
+//
+// EFI Component Name 2 Protocol
+//
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME2_PROTOCOL mGraphicsOutputComponentName2 = {
+  (EFI_COMPONENT_NAME2_GET_DRIVER_NAME) GraphicsOutputComponentNameGetDriverName,
+  (EFI_COMPONENT_NAME2_GET_CONTROLLER_NAME) GraphicsOutputComponentNameGetControllerName,
+  "en"
+};
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c
new file mode 100644
index 0000000000..43787d279a
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c
@@ -0,0 +1,739 @@
+/** @file
+  Implementation for a generic GOP driver.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+
+**/
+
+#include "GraphicsOutput.h"
+CONST ACPI_ADR_DEVICE_PATH mGraphicsOutputAdrNode = {
+  {
+    ACPI_DEVICE_PATH,
+    ACPI_ADR_DP,
+    { sizeof (ACPI_ADR_DEVICE_PATH), 0 },
+  },
+  ACPI_DISPLAY_ADR (1, 0, 0, 1, 0, ACPI_ADR_DISPLAY_TYPE_VGA, 0, 0)
+};
+
+EFI_PEI_GRAPHICS_DEVICE_INFO_HOB mDefaultGraphicsDeviceInfo = {
+  MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT8, MAX_UINT8
+};
+
+//
+// The driver should only start on one graphics controller.
+// So a global flag is used to remember that the driver is already started.
+//
+BOOLEAN mDriverStarted = FALSE;
+
+/**
+  Returns information for an available graphics mode that the graphics device
+  and the set of active video output devices supports.
+
+  @param  This                  The EFI_GRAPHICS_OUTPUT_PROTOCOL instance.
+  @param  ModeNumber            The mode number to return information on.
+  @param  SizeOfInfo            A pointer to the size, in bytes, of the Info buffer.
+  @param  Info                  A pointer to callee allocated buffer that returns information about ModeNumber.
+
+  @retval EFI_SUCCESS           Valid mode information was returned.
+  @retval EFI_DEVICE_ERROR      A hardware error occurred trying to retrieve the video mode.
+  @retval EFI_INVALID_PARAMETER ModeNumber is not valid.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputQueryMode (
+  IN  EFI_GRAPHICS_OUTPUT_PROTOCOL          *This,
+  IN  UINT32                                ModeNumber,
+  OUT UINTN                                 *SizeOfInfo,
+  OUT EFI_GRAPHICS_OUTPUT_MODE_INFORMATION  **Info
+  )
+{
+  if (This == NULL || Info == NULL || SizeOfInfo == NULL || ModeNumber >= This->Mode->MaxMode) {
+    return EFI_INVALID_PARAMETER;
+  }
+
+  *SizeOfInfo = This->Mode->SizeOfInfo;
+  *Info       = AllocateCopyPool (*SizeOfInfo, This->Mode->Info);
+  return EFI_SUCCESS;
+}
+
+/**
+  Set the video device into the specified mode and clears the visible portions of
+  the output display to black.
+
+  @param  This              The EFI_GRAPHICS_OUTPUT_PROTOCOL instance.
+  @param  ModeNumber        Abstraction that defines the current video mode.
+
+  @retval EFI_SUCCESS       The graphics mode specified by ModeNumber was selected.
+  @retval EFI_DEVICE_ERROR  The device had an error and could not complete the request.
+  @retval EFI_UNSUPPORTED   ModeNumber is not supported by this device.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputSetMode (
+  IN  EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
+  IN  UINT32                       ModeNumber
+)
+{
+  RETURN_STATUS                    Status;
+  EFI_GRAPHICS_OUTPUT_BLT_PIXEL    Black;
+  GRAPHICS_OUTPUT_PRIVATE_DATA     *Private;
+
+  if (ModeNumber >= This->Mode->MaxMode) {
+    return EFI_UNSUPPORTED;
+  }
+
+  Private = GRAPHICS_OUTPUT_PRIVATE_FROM_THIS (This);
+
+  Black.Blue = 0;
+  Black.Green = 0;
+  Black.Red = 0;
+  Black.Reserved = 0;
+
+  Status = FrameBufferBlt (
+             Private->FrameBufferBltLibConfigure,
+             &Black,
+             EfiBltVideoFill,
+             0, 0,
+             0, 0,
+             This->Mode->Info->HorizontalResolution,
+             This->Mode->Info->VerticalResolution,
+             0
+             );
+  return RETURN_ERROR (Status) ? EFI_DEVICE_ERROR : EFI_SUCCESS;
+}
+
+/**
+  Blt a rectangle of pixels on the graphics screen. Blt stands for BLock Transfer.
+
+  @param  This         Protocol instance pointer.
+  @param  BltBuffer    The data to transfer to the graphics screen.
+                       Size is at least Width*Height*sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL).
+  @param  BltOperation The operation to perform when copying BltBuffer on to the graphics screen.
+  @param  SourceX      The X coordinate of source for the BltOperation.
+  @param  SourceY      The Y coordinate of source for the BltOperation.
+  @param  DestinationX The X coordinate of destination for the BltOperation.
+  @param  DestinationY The Y coordinate of destination for the BltOperation.
+  @param  Width        The width of a rectangle in the blt rectangle in pixels.
+  @param  Height       The height of a rectangle in the blt rectangle in pixels.
+  @param  Delta        Not used for EfiBltVideoFill or the EfiBltVideoToVideo operation.
+                       If a Delta of zero is used, the entire BltBuffer is being operated on.
+                       If a subrectangle of the BltBuffer is being used then Delta
+                       represents the number of bytes in a row of the BltBuffer.
+
+  @retval EFI_SUCCESS           BltBuffer was drawn to the graphics screen.
+  @retval EFI_INVALID_PARAMETER BltOperation is not valid.
+  @retval EFI_DEVICE_ERROR      The device had an error and could not complete the request.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputBlt (
+  IN  EFI_GRAPHICS_OUTPUT_PROTOCOL      *This,
+  IN  EFI_GRAPHICS_OUTPUT_BLT_PIXEL     *BltBuffer, OPTIONAL
+  IN  EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
+  IN  UINTN                             SourceX,
+  IN  UINTN                             SourceY,
+  IN  UINTN                             DestinationX,
+  IN  UINTN                             DestinationY,
+  IN  UINTN                             Width,
+  IN  UINTN                             Height,
+  IN  UINTN                             Delta         OPTIONAL
+  )
+{
+  RETURN_STATUS                         Status;
+  EFI_TPL                               Tpl;
+  GRAPHICS_OUTPUT_PRIVATE_DATA          *Private;
+
+  Private = GRAPHICS_OUTPUT_PRIVATE_FROM_THIS (This);
+  //
+  // We have to raise to TPL_NOTIFY, so we make an atomic write to the frame buffer.
+  // We would not want a timer based event (Cursor, ...) to come in while we are
+  // doing this operation.
+  //
+  Tpl = gBS->RaiseTPL (TPL_NOTIFY);
+  Status = FrameBufferBlt (
+             Private->FrameBufferBltLibConfigure,
+             BltBuffer,
+             BltOperation,
+             SourceX, SourceY,
+             DestinationX, DestinationY, Width, Height,
+             Delta
+             );
+  gBS->RestoreTPL (Tpl);
+
+  return RETURN_ERROR (Status) ? EFI_INVALID_PARAMETER : EFI_SUCCESS;
+}
+
+CONST GRAPHICS_OUTPUT_PRIVATE_DATA mGraphicsOutputInstanceTemplate = {
+  GRAPHICS_OUTPUT_PRIVATE_DATA_SIGNATURE,          // Signature
+  NULL,                                            // GraphicsOutputHandle
+  {
+    GraphicsOutputQueryMode,
+    GraphicsOutputSetMode,
+    GraphicsOutputBlt,
+    NULL                                           // Mode
+  },
+  {
+    1,                                             // MaxMode
+    0,                                             // Mode
+    NULL,                                          // Info
+    sizeof (EFI_GRAPHICS_OUTPUT_MODE_INFORMATION), // SizeOfInfo
+    0,                                             // FrameBufferBase
+    0                                              // FrameBufferSize
+  },
+  NULL,                                            // DevicePath
+  NULL,                                            // PciIo
+  0,                                               // PciAttributes
+  NULL,                                            // FrameBufferBltLibConfigure
+  0                                                // FrameBufferBltLibConfigureSize
+};
+
+/**
+  Test whether the Controller can be managed by the driver.
+
+  @param  This                 Driver Binding protocol instance pointer.
+  @param  Controller           The PCI controller.
+  @param  RemainingDevicePath  Optional parameter use to pick a specific child
+                               device to start.
+
+  @retval EFI_SUCCESS          The driver can manage the video device.
+  @retval other                The driver cannot manage the video device.
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputDriverBindingSupported (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN EFI_DEVICE_PATH_PROTOCOL       *RemainingDevicePath
+  )
+{
+  EFI_STATUS                        Status;
+  EFI_PCI_IO_PROTOCOL               *PciIo;
+  EFI_DEVICE_PATH_PROTOCOL          *DevicePath;
+
+  //
+  // Since there is only one GraphicsInfo HOB, the driver only manages one video device.
+  //
+  if (mDriverStarted) {
+    return EFI_ALREADY_STARTED;
+  }
+
+  //
+  // Test the PCI I/O Protocol
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIo,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+  gBS->CloseProtocol (
+         Controller,
+         &gEfiPciIoProtocolGuid,
+         This->DriverBindingHandle,
+         Controller
+         );
+
+  //
+  // Test the DevicePath protocol
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiDevicePathProtocolGuid,
+                  (VOID **) &DevicePath,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+  gBS->CloseProtocol (
+         Controller,
+         &gEfiDevicePathProtocolGuid,
+         This->DriverBindingHandle,
+         Controller
+         );
+
+  if ((RemainingDevicePath == NULL) ||
+      IsDevicePathEnd (RemainingDevicePath) ||
+      CompareMem (RemainingDevicePath, &mGraphicsOutputAdrNode, sizeof (mGraphicsOutputAdrNode)) == 0) {
+    return EFI_SUCCESS;
+  } else {
+    return EFI_INVALID_PARAMETER;
+  }
+}
+
+/**
+  Start the video controller.
+
+  @param  This                 Driver Binding protocol instance pointer.
+  @param  ControllerHandle     The PCI controller.
+  @param  RemainingDevicePath  Optional parameter use to pick a specific child
+                               device to start.
+
+  @retval EFI_SUCCESS          The driver starts to manage the video device.
+  @retval other                The driver cannot manage the video device.
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputDriverBindingStart (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN EFI_DEVICE_PATH_PROTOCOL       *RemainingDevicePath
+  )
+{
+  EFI_STATUS                        Status;
+  RETURN_STATUS                     ReturnStatus;
+  GRAPHICS_OUTPUT_PRIVATE_DATA      *Private;
+  EFI_PCI_IO_PROTOCOL               *PciIo;
+  EFI_DEVICE_PATH                   *PciDevicePath;
+  PCI_TYPE00                        Pci;
+  UINT8                             Index;
+  EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR *Resources;
+  VOID                              *HobStart;
+  EFI_PEI_GRAPHICS_INFO_HOB         *GraphicsInfo;
+  EFI_PEI_GRAPHICS_DEVICE_INFO_HOB  *DeviceInfo;
+  EFI_PHYSICAL_ADDRESS              FrameBufferBase;
+
+  FrameBufferBase = 0;
+
+  HobStart = GetFirstGuidHob (&gEfiGraphicsInfoHobGuid);
+  ASSERT ((HobStart != NULL) && (GET_GUID_HOB_DATA_SIZE (HobStart) == sizeof (EFI_PEI_GRAPHICS_INFO_HOB)));
+  GraphicsInfo = (EFI_PEI_GRAPHICS_INFO_HOB *) (GET_GUID_HOB_DATA (HobStart));
+
+  HobStart = GetFirstGuidHob (&gEfiGraphicsDeviceInfoHobGuid);
+  if ((HobStart == NULL) || (GET_GUID_HOB_DATA_SIZE (HobStart) < sizeof (*DeviceInfo))) {
+    //
+    // Use default device infomation when the device info HOB doesn't exist
+    //
+    DeviceInfo = &mDefaultGraphicsDeviceInfo;
+    DEBUG ((DEBUG_INFO, "[%a]: GraphicsDeviceInfo HOB doesn't exist!\n", gEfiCallerBaseName));
+  } else {
+    DeviceInfo = (EFI_PEI_GRAPHICS_DEVICE_INFO_HOB *) (GET_GUID_HOB_DATA (HobStart));
+    DEBUG ((DEBUG_INFO, "[%a]: GraphicsDeviceInfo HOB:\n"
+            "  VendorId = %04x, DeviceId = %04x,\n"
+            "  RevisionId = %02x, BarIndex = %x,\n"
+            "  SubsystemVendorId = %04x, SubsystemId = %04x\n",
+            gEfiCallerBaseName,
+            DeviceInfo->VendorId, DeviceInfo->DeviceId,
+            DeviceInfo->RevisionId, DeviceInfo->BarIndex,
+            DeviceInfo->SubsystemVendorId, DeviceInfo->SubsystemId));
+  }
+
+  //
+  // Open the PCI I/O Protocol
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIo,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  ASSERT_EFI_ERROR (Status);
+
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiDevicePathProtocolGuid,
+                  (VOID **) &PciDevicePath,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Read the PCI Class Code from the PCI Device
+  //
+  Status = PciIo->Pci.Read (PciIo, EfiPciIoWidthUint8, 0, sizeof (Pci), &Pci);
+  if (!EFI_ERROR (Status)) {
+    if (!IS_PCI_DISPLAY (&Pci) || (
+        ((DeviceInfo->VendorId != MAX_UINT16) && (DeviceInfo->VendorId != Pci.Hdr.VendorId)) ||
+        ((DeviceInfo->DeviceId != MAX_UINT16) && (DeviceInfo->DeviceId != Pci.Hdr.DeviceId)) ||
+        ((DeviceInfo->RevisionId != MAX_UINT8) && (DeviceInfo->RevisionId != Pci.Hdr.RevisionID)) ||
+        ((DeviceInfo->SubsystemVendorId != MAX_UINT16) && (DeviceInfo->SubsystemVendorId != Pci.Device.SubsystemVendorID)) ||
+        ((DeviceInfo->SubsystemId != MAX_UINT16) && (DeviceInfo->SubsystemId != Pci.Device.SubsystemID))
+        )
+        ) {
+      //
+      // It's not a video device, or device infomation doesn't match.
+      //
+      Status = EFI_UNSUPPORTED;
+    } else {
+      //
+      // If it's a video device and device information matches, use the BarIndex
+      // from device information, or any BAR if BarIndex is not specified
+      // whose size >= the frame buffer size from GraphicsInfo HOB.
+      // Store the new frame buffer base.
+      //
+      for (Index = 0; Index < MAX_PCI_BAR; Index++) {
+        if ((DeviceInfo->BarIndex != MAX_UINT8) && (DeviceInfo->BarIndex != Index)) {
+          continue;
+        }
+        Status = PciIo->GetBarAttributes (PciIo, Index, NULL, (VOID**) &Resources);
+        if (!EFI_ERROR (Status)) {
+          DEBUG ((DEBUG_INFO, "[%a]: BAR[%d]: Base = %lx, Length = %lx\n",
+                  gEfiCallerBaseName, Index, Resources->AddrRangeMin, Resources->AddrLen));
+          if ((Resources->Desc == ACPI_ADDRESS_SPACE_DESCRIPTOR) &&
+            (Resources->Len == (UINT16) (sizeof (EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR) - 3)) &&
+              (Resources->ResType == ACPI_ADDRESS_SPACE_TYPE_MEM) &&
+              (Resources->AddrLen >= GraphicsInfo->FrameBufferSize)
+              ) {
+            if (FrameBufferBase == 0) {
+              FrameBufferBase = Resources->AddrRangeMin;
+            }
+            if (DeviceInfo->BarIndex == MAX_UINT8) {
+              if (Resources->AddrRangeMin == GraphicsInfo->FrameBufferBase) {
+                FrameBufferBase = Resources->AddrRangeMin;
+                break;
+              }
+            } else {
+              break;
+            }
+          }
+        }
+      }
+      if (Index == MAX_PCI_BAR) {
+        Status = EFI_UNSUPPORTED;
+      } else {
+        DEBUG ((DEBUG_INFO, "[%a]: ... matched!\n", gEfiCallerBaseName));
+      }
+    }
+  }
+
+  if (EFI_ERROR (Status)) {
+    goto CloseProtocols;
+  }
+
+  if ((RemainingDevicePath != NULL) && IsDevicePathEnd (RemainingDevicePath)) {
+    return EFI_SUCCESS;
+  }
+
+  Private = AllocateCopyPool (sizeof (mGraphicsOutputInstanceTemplate), &mGraphicsOutputInstanceTemplate);
+  if (Private == NULL) {
+    Status = EFI_OUT_OF_RESOURCES;
+    goto CloseProtocols;
+  }
+
+  Private->GraphicsOutputMode.FrameBufferBase = FrameBufferBase;
+  Private->GraphicsOutputMode.FrameBufferSize = GraphicsInfo->FrameBufferSize;
+  Private->GraphicsOutputMode.Info = &GraphicsInfo->GraphicsMode;
+
+  //
+  // Fix up Mode pointer in GraphicsOutput
+  //
+  Private->GraphicsOutput.Mode = &Private->GraphicsOutputMode;
+
+  //
+  // Set attributes
+  //
+  Status = PciIo->Attributes (
+                    PciIo,
+                    EfiPciIoAttributeOperationGet,
+                    0,
+                    &Private->PciAttributes
+                    );
+  if (!EFI_ERROR (Status)) {
+    Status = PciIo->Attributes (
+                      PciIo,
+                      EfiPciIoAttributeOperationEnable,
+                      EFI_PCI_DEVICE_ENABLE,
+                      NULL
+                      );
+  }
+
+  if (EFI_ERROR (Status)) {
+    goto FreeMemory;
+  }
+
+  //
+  // Create the FrameBufferBltLib configuration.
+  //
+  ReturnStatus = FrameBufferBltConfigure (
+                   (VOID *) (UINTN) Private->GraphicsOutput.Mode->FrameBufferBase,
+                   Private->GraphicsOutput.Mode->Info,
+                   Private->FrameBufferBltLibConfigure,
+                   &Private->FrameBufferBltLibConfigureSize
+                   );
+  if (ReturnStatus == RETURN_BUFFER_TOO_SMALL) {
+    Private->FrameBufferBltLibConfigure = AllocatePool (Private->FrameBufferBltLibConfigureSize);
+    if (Private->FrameBufferBltLibConfigure != NULL) {
+      ReturnStatus = FrameBufferBltConfigure (
+                       (VOID *) (UINTN) Private->GraphicsOutput.Mode->FrameBufferBase,
+                       Private->GraphicsOutput.Mode->Info,
+                       Private->FrameBufferBltLibConfigure,
+                       &Private->FrameBufferBltLibConfigureSize
+                       );
+    }
+  }
+  if (RETURN_ERROR (ReturnStatus)) {
+    Status = EFI_OUT_OF_RESOURCES;
+    goto RestorePciAttributes;
+  }
+
+  Private->DevicePath = AppendDevicePathNode (PciDevicePath, (EFI_DEVICE_PATH_PROTOCOL *) &mGraphicsOutputAdrNode);
+  if (Private->DevicePath == NULL) {
+    Status = EFI_OUT_OF_RESOURCES;
+    goto RestorePciAttributes;
+  }
+
+  Status = gBS->InstallMultipleProtocolInterfaces (
+                  &Private->GraphicsOutputHandle,
+                  &gEfiGraphicsOutputProtocolGuid, &Private->GraphicsOutput,
+                  &gEfiDevicePathProtocolGuid, Private->DevicePath,
+                  NULL
+                  );
+
+  if (!EFI_ERROR (Status)) {
+    Status = gBS->OpenProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    (VOID **) &Private->PciIo,
+                    This->DriverBindingHandle,
+                    Private->GraphicsOutputHandle,
+                    EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER
+                    );
+    if (!EFI_ERROR (Status)) {
+      mDriverStarted = TRUE;
+    } else {
+      gBS->UninstallMultipleProtocolInterfaces (
+             Private->GraphicsOutputHandle,
+             &gEfiGraphicsOutputProtocolGuid, &Private->GraphicsOutput,
+             &gEfiDevicePathProtocolGuid, Private->DevicePath,
+             NULL
+             );
+    }
+  }
+
+RestorePciAttributes:
+  if (EFI_ERROR (Status)) {
+    //
+    // Restore original PCI attributes
+    //
+    PciIo->Attributes (
+             PciIo,
+             EfiPciIoAttributeOperationSet,
+             Private->PciAttributes,
+             NULL
+             );
+  }
+
+FreeMemory:
+  if (EFI_ERROR (Status)) {
+    if (Private != NULL) {
+      if (Private->DevicePath != NULL) {
+        FreePool (Private->DevicePath);
+      }
+      if (Private->FrameBufferBltLibConfigure != NULL) {
+        FreePool (Private->FrameBufferBltLibConfigure);
+      }
+      FreePool (Private);
+    }
+  }
+
+CloseProtocols:
+  if (EFI_ERROR (Status)) {
+    //
+    // Close the PCI I/O Protocol
+    //
+    gBS->CloseProtocol (
+           Controller,
+           &gEfiDevicePathProtocolGuid,
+           This->DriverBindingHandle,
+           Controller
+           );
+
+    //
+    // Close the PCI I/O Protocol
+    //
+    gBS->CloseProtocol (
+           Controller,
+           &gEfiPciIoProtocolGuid,
+           This->DriverBindingHandle,
+           Controller
+           );
+  }
+  return Status;
+}
+
+/**
+  Stop the video controller.
+
+  @param  This                 Driver Binding protocol instance pointer.
+  @param  Controller           The PCI controller.
+  @param  NumberOfChildren     The number of child device handles in ChildHandleBuffer.
+  @param  ChildHandleBuffer    An array of child handles to be freed. May be NULL
+                               if NumberOfChildren is 0.
+
+  @retval EFI_SUCCESS          The device was stopped.
+  @retval EFI_DEVICE_ERROR     The device could not be stopped due to a device error.
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputDriverBindingStop (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN UINTN                          NumberOfChildren,
+  IN EFI_HANDLE                     *ChildHandleBuffer
+  )
+{
+  EFI_STATUS                        Status;
+  EFI_GRAPHICS_OUTPUT_PROTOCOL      *Gop;
+  GRAPHICS_OUTPUT_PRIVATE_DATA      *Private;
+
+  if (NumberOfChildren == 0) {
+
+    //
+    // Close the PCI I/O Protocol
+    //
+    Status = gBS->CloseProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    This->DriverBindingHandle,
+                    Controller
+                    );
+    ASSERT_EFI_ERROR (Status);
+
+    Status = gBS->CloseProtocol (
+                    Controller,
+                    &gEfiDevicePathProtocolGuid,
+                    This->DriverBindingHandle,
+                    Controller
+                    );
+    ASSERT_EFI_ERROR (Status);
+    return EFI_SUCCESS;
+  }
+
+  ASSERT (NumberOfChildren == 1);
+  Status = gBS->OpenProtocol (
+                  ChildHandleBuffer[0],
+                  &gEfiGraphicsOutputProtocolGuid,
+                  (VOID **) &Gop,
+                  This->DriverBindingHandle,
+                  ChildHandleBuffer[0],
+                  EFI_OPEN_PROTOCOL_GET_PROTOCOL
+                  );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Private = GRAPHICS_OUTPUT_PRIVATE_FROM_THIS (Gop);
+
+  Status = gBS->CloseProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  This->DriverBindingHandle,
+                  Private->GraphicsOutputHandle
+                  );
+  ASSERT_EFI_ERROR (Status);
+  //
+  // Remove the GOP protocol interface from the system
+  //
+  Status = gBS->UninstallMultipleProtocolInterfaces (
+                  Private->GraphicsOutputHandle,
+                  &gEfiGraphicsOutputProtocolGuid, &Private->GraphicsOutput,
+                  &gEfiDevicePathProtocolGuid, Private->DevicePath,
+                  NULL
+                  );
+  if (!EFI_ERROR (Status)) {
+    //
+    // Restore original PCI attributes
+    //
+    Status = Private->PciIo->Attributes (
+                               Private->PciIo,
+                               EfiPciIoAttributeOperationSet,
+                               Private->PciAttributes,
+                               NULL
+                               );
+    ASSERT_EFI_ERROR (Status);
+
+    FreePool (Private->DevicePath);
+    FreePool (Private->FrameBufferBltLibConfigure);
+    mDriverStarted = FALSE;
+  } else {
+    Status = gBS->OpenProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    (VOID **) &Private->PciIo,
+                    This->DriverBindingHandle,
+                    Private->GraphicsOutputHandle,
+                    EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER
+                    );
+    ASSERT_EFI_ERROR (Status);
+  }
+  return Status;
+}
+
+EFI_DRIVER_BINDING_PROTOCOL mGraphicsOutputDriverBinding = {
+  GraphicsOutputDriverBindingSupported,
+  GraphicsOutputDriverBindingStart,
+  GraphicsOutputDriverBindingStop,
+  0x10,
+  NULL,
+  NULL
+};
+
+/**
+  The Entry Point for GraphicsOutput driver.
+
+  It installs DriverBinding, ComponentName and ComponentName2 protocol if there is
+  GraphicsInfo HOB passed from Graphics PEIM.
+
+  @param[in] ImageHandle    The firmware allocated handle for the EFI image.
+  @param[in] SystemTable    A pointer to the EFI System Table.
+
+  @retval EFI_SUCCESS       The entry point is executed successfully.
+  @retval other             Some error occurs when executing this entry point.
+
+**/
+EFI_STATUS
+EFIAPI
+InitializeGraphicsOutput (
+  IN EFI_HANDLE                        ImageHandle,
+  IN EFI_SYSTEM_TABLE                  *SystemTable
+  )
+{
+  EFI_STATUS                           Status;
+  VOID                                 *HobStart;
+
+  HobStart = GetFirstGuidHob (&gEfiGraphicsInfoHobGuid);
+
+  if ((HobStart == NULL) || (GET_GUID_HOB_DATA_SIZE (HobStart) < sizeof (EFI_PEI_GRAPHICS_INFO_HOB))) {
+    return EFI_NOT_FOUND;
+  }
+
+  Status = EfiLibInstallDriverBindingComponentName2 (
+             ImageHandle,
+             SystemTable,
+             &mGraphicsOutputDriverBinding,
+             ImageHandle,
+             &mGraphicsOutputComponentName,
+             &mGraphicsOutputComponentName2
+             );
+  ASSERT_EFI_ERROR (Status);
+
+  return Status;
+}
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h
new file mode 100644
index 0000000000..a40768b1ee
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h
@@ -0,0 +1,53 @@
+/** @file
+  Header file for a generic GOP driver.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+
+**/
+#ifndef _GRAPHICS_OUTPUT_DXE_H_
+#define _GRAPHICS_OUTPUT_DXE_H_
+#include <PiDxe.h>
+
+#include <IndustryStandard/Pci.h>
+#include <IndustryStandard/Acpi.h>
+#include <Guid/GraphicsInfoHob.h>
+#include <Protocol/DriverBinding.h>
+#include <Protocol/PciIo.h>
+#include <Protocol/DevicePath.h>
+#include <Protocol/GraphicsOutput.h>
+#include <Protocol/ComponentName.h>
+#include <Protocol/ComponentName2.h>
+
+#include <Library/BaseLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/HobLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/FrameBufferBltLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiLib.h>
+
+#define MAX_PCI_BAR  6
+
+typedef struct {
+  UINT32                            Signature;
+  EFI_HANDLE                        GraphicsOutputHandle;
+  EFI_GRAPHICS_OUTPUT_PROTOCOL      GraphicsOutput;
+  EFI_GRAPHICS_OUTPUT_PROTOCOL_MODE GraphicsOutputMode;
+  EFI_DEVICE_PATH_PROTOCOL          *DevicePath;
+  EFI_PCI_IO_PROTOCOL               *PciIo;
+  UINT64                            PciAttributes;
+  FRAME_BUFFER_CONFIGURE            *FrameBufferBltLibConfigure;
+  UINTN                             FrameBufferBltLibConfigureSize;
+} GRAPHICS_OUTPUT_PRIVATE_DATA;
+
+#define GRAPHICS_OUTPUT_PRIVATE_DATA_SIGNATURE  SIGNATURE_32 ('g', 'g', 'o', 'p')
+#define GRAPHICS_OUTPUT_PRIVATE_FROM_THIS(a) \
+  CR(a, GRAPHICS_OUTPUT_PRIVATE_DATA, GraphicsOutput, GRAPHICS_OUTPUT_PRIVATE_DATA_SIGNATURE)
+
+extern EFI_COMPONENT_NAME_PROTOCOL  mGraphicsOutputComponentName;
+extern EFI_COMPONENT_NAME2_PROTOCOL mGraphicsOutputComponentName2;
+#endif
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
new file mode 100644
index 0000000000..af21095a66
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
@@ -0,0 +1,53 @@
+## @file
+# This driver produces GraphicsOutput protocol based on the GraphicsInfo HOB information.
+#
+# Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+#
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = GraphicsOutputDxe
+  FILE_GUID                      = 0B04B2ED-861C-42cd-A22F-C3AAFACCB896
+  MODULE_TYPE                    = UEFI_DRIVER
+  VERSION_STRING                 = 1.0
+  ENTRY_POINT                    = InitializeGraphicsOutput
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources.common]
+  GraphicsOutput.h
+  GraphicsOutput.c
+  ComponentName.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+
+[LibraryClasses]
+  UefiDriverEntryPoint
+  UefiBootServicesTableLib
+  DxeServicesTableLib
+  DebugLib
+  MemoryAllocationLib
+  BaseMemoryLib
+  DevicePathLib
+  FrameBufferBltLib
+  UefiLib
+  HobLib
+
+[Guids]
+  gEfiGraphicsInfoHobGuid                       ## CONSUMES ## HOB
+  gEfiGraphicsDeviceInfoHobGuid                 ## CONSUMES ## HOB
+
+[Protocols]
+  gEfiGraphicsOutputProtocolGuid                ## BY_START
+  gEfiDevicePathProtocolGuid                    ## BY_START
+  gEfiPciIoProtocolGuid                         ## TO_START
diff --git a/UefiPayloadPkg/Include/Coreboot.h b/UefiPayloadPkg/Include/Coreboot.h
new file mode 100644
index 0000000000..8a6c300cde
--- /dev/null
+++ b/UefiPayloadPkg/Include/Coreboot.h
@@ -0,0 +1,249 @@
+/** @file
+  Coreboot PEI module include file.
+
+  Copyright (c) 2014 - 2015, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+/*
+ * This file is part of the libpayload project.
+ *
+ * Copyright (C) 2008 Advanced Micro Devices, Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. The name of the author may not be used to endorse or promote products
+ *    derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+
+#ifndef _COREBOOT_PEI_H_INCLUDED_
+#define _COREBOOT_PEI_H_INCLUDED_
+
+#if defined(_MSC_VER)
+#pragma warning( disable : 4200 )
+#endif
+
+#define DYN_CBMEM_ALIGN_SIZE (4096)
+
+#define IMD_ENTRY_MAGIC      (~0xC0389481)
+#define CBMEM_ENTRY_MAGIC    (~0xC0389479)
+
+struct cbmem_entry {
+  UINT32 magic;
+  UINT32 start;
+  UINT32 size;
+  UINT32 id;
+};
+
+struct cbmem_root {
+  UINT32 max_entries;
+  UINT32 num_entries;
+  UINT32 locked;
+  UINT32 size;
+  struct cbmem_entry entries[0];
+};
+
+struct imd_entry {
+  UINT32 magic;
+  UINT32 start_offset;
+  UINT32 size;
+  UINT32 id;
+};
+
+struct imd_root {
+  UINT32 max_entries;
+  UINT32 num_entries;
+  UINT32 flags;
+  UINT32 entry_align;
+  UINT32 max_offset;
+  struct imd_entry entries[0];
+};
+
+struct cbuint64 {
+  UINT32 lo;
+  UINT32 hi;
+};
+
+#define CB_HEADER_SIGNATURE 0x4F49424C
+
+struct cb_header {
+  UINT32 signature;
+  UINT32 header_bytes;
+  UINT32 header_checksum;
+  UINT32 table_bytes;
+  UINT32 table_checksum;
+  UINT32 table_entries;
+};
+
+struct cb_record {
+  UINT32 tag;
+  UINT32 size;
+};
+
+#define CB_TAG_UNUSED     0x0000
+#define CB_TAG_MEMORY     0x0001
+
+struct cb_memory_range {
+  struct cbuint64 start;
+  struct cbuint64 size;
+  UINT32 type;
+};
+
+#define CB_MEM_RAM    1
+#define CB_MEM_RESERVED     2
+#define CB_MEM_ACPI   3
+#define CB_MEM_NVS    4
+#define CB_MEM_UNUSABLE     5
+#define CB_MEM_VENDOR_RSVD  6
+#define CB_MEM_TABLE       16
+
+struct cb_memory {
+  UINT32 tag;
+  UINT32 size;
+  struct cb_memory_range map[0];
+};
+
+#define CB_TAG_MAINBOARD  0x0003
+
+struct cb_mainboard {
+  UINT32 tag;
+  UINT32 size;
+  UINT8 vendor_idx;
+  UINT8 part_number_idx;
+  UINT8 strings[0];
+};
+#define CB_TAG_VERSION  0x0004
+#define CB_TAG_EXTRA_VERSION  0x0005
+#define CB_TAG_BUILD    0x0006
+#define CB_TAG_COMPILE_TIME   0x0007
+#define CB_TAG_COMPILE_BY     0x0008
+#define CB_TAG_COMPILE_HOST   0x0009
+#define CB_TAG_COMPILE_DOMAIN 0x000a
+#define CB_TAG_COMPILER       0x000b
+#define CB_TAG_LINKER   0x000c
+#define CB_TAG_ASSEMBLER      0x000d
+
+struct cb_string {
+  UINT32 tag;
+  UINT32 size;
+  UINT8 string[0];
+};
+
+#define CB_TAG_SERIAL   0x000f
+
+struct cb_serial {
+  UINT32 tag;
+  UINT32 size;
+#define CB_SERIAL_TYPE_IO_MAPPED     1
+#define CB_SERIAL_TYPE_MEMORY_MAPPED 2
+  UINT32 type;
+  UINT32 baseaddr;
+  UINT32 baud;
+  UINT32 regwidth;
+
+  // Crystal or input frequency to the chip containing the UART.
+  // Provide the board specific details to allow the payload to
+  // initialize the chip containing the UART and make independent
+  // decisions as to which dividers to select and their values
+  // to eventually arrive at the desired console baud-rate.
+  UINT32 input_hertz;
+
+  // UART PCI address: bus, device, function
+  // 1 << 31 - Valid bit, PCI UART in use
+  // Bus << 20
+  // Device << 15
+  // Function << 12
+  UINT32 uart_pci_addr;
+};
+
+#define CB_TAG_CONSOLE       0x00010
+
+struct cb_console {
+  UINT32 tag;
+  UINT32 size;
+  UINT16 type;
+};
+
+#define CB_TAG_CONSOLE_SERIAL8250 0
+#define CB_TAG_CONSOLE_VGA  1 // OBSOLETE
+#define CB_TAG_CONSOLE_BTEXT      2 // OBSOLETE
+#define CB_TAG_CONSOLE_LOGBUF     3
+#define CB_TAG_CONSOLE_SROM       4 // OBSOLETE
+#define CB_TAG_CONSOLE_EHCI       5
+
+#define CB_TAG_FORWARD       0x00011
+
+struct cb_forward {
+  UINT32 tag;
+  UINT32 size;
+  UINT64 forward;
+};
+
+#define CB_TAG_FRAMEBUFFER      0x0012
+struct cb_framebuffer {
+  UINT32 tag;
+  UINT32 size;
+
+  UINT64 physical_address;
+  UINT32 x_resolution;
+  UINT32 y_resolution;
+  UINT32 bytes_per_line;
+  UINT8 bits_per_pixel;
+  UINT8 red_mask_pos;
+  UINT8 red_mask_size;
+  UINT8 green_mask_pos;
+  UINT8 green_mask_size;
+  UINT8 blue_mask_pos;
+  UINT8 blue_mask_size;
+  UINT8 reserved_mask_pos;
+  UINT8 reserved_mask_size;
+};
+
+#define CB_TAG_VDAT     0x0015
+struct cb_vdat {
+  UINT32 tag;
+  UINT32 size;  /* size of the entire entry */
+  UINT64 vdat_addr;
+  UINT32 vdat_size;
+};
+
+#define CB_TAG_TIMESTAMPS       0x0016
+#define CB_TAG_CBMEM_CONSOLE    0x0017
+#define CB_TAG_MRC_CACHE  0x0018
+struct cb_cbmem_tab {
+  UINT32 tag;
+  UINT32 size;
+  UINT64 cbmem_tab;
+};
+
+/* Helpful macros */
+
+#define MEM_RANGE_COUNT(_rec) \
+  (((_rec)->size - sizeof(*(_rec))) / sizeof((_rec)->map[0]))
+
+#define MEM_RANGE_PTR(_rec, _idx) \
+  (void *)(((UINT8 *) (_rec)) + sizeof(*(_rec)) \
+    + (sizeof((_rec)->map[0]) * (_idx)))
+
+
+#endif // _COREBOOT_PEI_H_INCLUDED_
diff --git a/UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h b/UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h
new file mode 100644
index 0000000000..fe783fe5e1
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h
@@ -0,0 +1,29 @@
+/** @file
+  This file defines the hob structure for board related information from acpi table
+
+  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __ACPI_BOARD_INFO_GUID_H__
+#define __ACPI_BOARD_INFO_GUID_H__
+
+///
+/// Board information GUID
+///
+extern EFI_GUID gUefiAcpiBoardInfoGuid;
+
+typedef struct {
+  UINT8              Revision;
+  UINT8              Reserved0[2];
+  UINT8              ResetValue;
+  UINT64             PmEvtBase;
+  UINT64             PmGpeEnBase;
+  UINT64             PmCtrlRegBase;
+  UINT64             PmTimerRegBase;
+  UINT64             ResetRegAddress;
+  UINT64             PcieBaseAddress;
+} ACPI_BOARD_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h b/UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h
new file mode 100644
index 0000000000..99187e8037
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h
@@ -0,0 +1,36 @@
+/** @file
+  This file defines the hob structure for memory map information.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __MEMORY_MAP_INFO_GUID_H__
+#define __MEMORY_MAP_INFO_GUID_H__
+
+#include <Library/PcdLib.h>
+
+///
+/// Memory Map Information GUID
+///
+extern EFI_GUID gLoaderMemoryMapInfoGuid;
+
+#pragma pack(1)
+typedef struct {
+  UINT64 Base;
+  UINT64 Size;
+  UINT8  Type;
+  UINT8  Flag;
+  UINT8  Reserved[6];
+} MEMROY_MAP_ENTRY;
+
+typedef struct {
+  UINT8  Revision;
+  UINT8  Reserved0[3];
+  UINT32 Count;
+  MEMROY_MAP_ENTRY  Entry[0];
+} MEMROY_MAP_INFO;
+#pragma pack()
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h b/UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h
new file mode 100644
index 0000000000..a15d5b8671
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h
@@ -0,0 +1,31 @@
+/** @file
+  This file defines the hob structure for serial port.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __SERIAL_PORT_INFO_GUID_H__
+#define __SERIAL_PORT_INFO_GUID_H__
+
+///
+/// Serial Port Information GUID
+///
+extern EFI_GUID gUefiSerialPortInfoGuid;
+
+#define PLD_SERIAL_TYPE_IO_MAPPED     1
+#define PLD_SERIAL_TYPE_MEMORY_MAPPED 2
+
+typedef struct {
+  UINT8  Revision;
+  UINT8  Reserved0[3];
+  UINT32 Type;
+  UINT32 BaseAddr;
+  UINT32 Baud;
+  UINT32 RegWidth;
+  UINT32 InputHertz;
+  UINT32 UartPciAddr;
+} SERIAL_PORT_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h b/UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h
new file mode 100644
index 0000000000..2446820285
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h
@@ -0,0 +1,26 @@
+/** @file
+  This file defines the hob structure for system tables like ACPI, SMBIOS tables.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __SYSTEM_TABLE_INFO_GUID_H__
+#define __SYSTEM_TABLE_INFO_GUID_H__
+
+///
+/// System Table Information GUID
+///
+extern EFI_GUID gUefiSystemTableInfoGuid;
+
+typedef struct {
+  UINT8     Revision;
+  UINT8     Reserved0[3];
+  UINT64    AcpiTableBase;
+  UINT32    AcpiTableSize;
+  UINT64    SmbiosTableBase;
+  UINT32    SmbiosTableSize;
+} SYSTEM_TABLE_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Library/BlParseLib.h b/UefiPayloadPkg/Include/Library/BlParseLib.h
new file mode 100644
index 0000000000..3f9e591ede
--- /dev/null
+++ b/UefiPayloadPkg/Include/Library/BlParseLib.h
@@ -0,0 +1,120 @@
+/** @file
+  This library will parse the coreboot table in memory and extract those required
+  information.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#include <PiPei.h>
+#include <Guid/GraphicsInfoHob.h>
+#include <Guid/MemoryMapInfoGuid.h>
+#include <Guid/SerialPortInfoGuid.h>
+#include <Guid/SystemTableInfoGuid.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+
+#ifndef __BOOTLOADER_PARSE_LIB__
+#define __BOOTLOADER_PARSE_LIB__
+
+#define GET_BOOTLOADER_PARAMETER()      (*(UINT32 *)(UINTN)(PcdGet32(PcdPayloadStackTop) - sizeof(UINT32)))
+#define SET_BOOTLOADER_PARAMETER(Value) GET_BOOTLOADER_PARAMETER()=Value
+
+typedef RETURN_STATUS \
+        (*BL_MEM_INFO_CALLBACK) (MEMROY_MAP_ENTRY *MemoryMapEntry, VOID *Param);
+
+/**
+  This function retrieves the parameter base address from boot loader.
+
+  This function will get bootloader specific parameter address for UEFI payload.
+  e.g. HobList pointer for Slim Bootloader, and coreboot table header for Coreboot.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+EFIAPI
+GetParameterBase (
+  VOID
+  );
+
+/**
+  Acquire the memory map information.
+
+  @param  MemInfoCallback     The callback routine
+  @param  Params              Pointer to the callback routine parameter
+
+  @retval RETURN_SUCCESS     Successfully find out the memory information.
+  @retval RETURN_NOT_FOUND   Failed to find the memory information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseMemoryInfo (
+  IN  BL_MEM_INFO_CALLBACK       MemInfoCallback,
+  IN  VOID                       *Params
+  );
+
+/**
+  Acquire acpi table and smbios table from slim bootloader
+
+  @param  SystemTableInfo           Pointer to the system table info
+
+  @retval RETURN_SUCCESS            Successfully find out the tables.
+  @retval RETURN_NOT_FOUND          Failed to find the tables.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSystemTable (
+  OUT SYSTEM_TABLE_INFO     *SystemTableInfo
+  );
+
+
+/**
+  Find the serial port information
+
+  @param  SERIAL_PORT_INFO   Pointer to serial port info structure
+
+  @retval RETURN_SUCCESS     Successfully find the serial port information.
+  @retval RETURN_NOT_FOUND   Failed to find the serial port information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSerialInfo (
+  OUT SERIAL_PORT_INFO     *SerialPortInfo
+  );
+
+
+/**
+  Find the video frame buffer information
+
+  @param  GfxInfo             Pointer to the EFI_PEI_GRAPHICS_INFO_HOB structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseGfxInfo (
+  OUT EFI_PEI_GRAPHICS_INFO_HOB       *GfxInfo
+  );
+
+/**
+  Find the video frame buffer device information
+
+  @param  GfxDeviceInfo      Pointer to the EFI_PEI_GRAPHICS_DEVICE_INFO_HOB structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseGfxDeviceInfo (
+  OUT EFI_PEI_GRAPHICS_DEVICE_INFO_HOB       *GfxDeviceInfo
+  );
+
+#endif
diff --git a/UefiPayloadPkg/Include/Library/PlatformSupportLib.h b/UefiPayloadPkg/Include/Library/PlatformSupportLib.h
new file mode 100644
index 0000000000..d9f0b83075
--- /dev/null
+++ b/UefiPayloadPkg/Include/Library/PlatformSupportLib.h
@@ -0,0 +1,28 @@
+/** @file
+  Bootloader Platform Support library. Platform can provide an implementation of this
+  library class to provide hooks that may be required for some type of
+  platform features.
+
+Copyright (c) 2016 - 2019, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef __BOOTLOADER_PLATFORM_SUPPORT_LIB__
+#define __BOOTLOADER_PLATFORM_SUPPORT_LIB__
+
+/**
+  Parse platform specific information from bootloader
+
+  @retval RETURN_SUCCESS       The platform specific coreboot support succeeded.
+  @retval RETURN_DEVICE_ERROR  The platform specific coreboot support could not be completed.
+
+**/
+EFI_STATUS
+EFIAPI
+ParsePlatformInfo (
+  VOID
+  );
+
+#endif // __BOOTLOADER_PLATFORM_SUPPORT_LIB__
+
diff --git a/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c
new file mode 100644
index 0000000000..b86382d709
--- /dev/null
+++ b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c
@@ -0,0 +1,270 @@
+/** @file
+  ACPI Timer implements one instance of Timer Library.
+
+  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <PiPei.h>
+#include <Library/TimerLib.h>
+#include <Library/BaseLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+#include <Library/DebugLib.h>
+
+#include <Guid/AcpiBoardInfoGuid.h>
+#include <IndustryStandard/Acpi.h>
+
+#define ACPI_TIMER_COUNT_SIZE  BIT24
+
+UINTN mPmTimerReg = 0;
+
+/**
+  The constructor function enables ACPI IO space.
+
+  If ACPI I/O space not enabled, this function will enable it.
+  It will always return RETURN_SUCCESS.
+
+  @retval EFI_SUCCESS   The constructor always returns RETURN_SUCCESS.
+
+**/
+RETURN_STATUS
+EFIAPI
+AcpiTimerLibConstructor (
+  VOID
+  )
+{
+  EFI_HOB_GUID_TYPE  *GuidHob;
+  ACPI_BOARD_INFO    *pAcpiBoardInfo;
+
+  //
+  // Find the acpi board information guid hob
+  //
+  GuidHob = GetFirstGuidHob (&gUefiAcpiBoardInfoGuid);
+  ASSERT (GuidHob != NULL);
+
+  pAcpiBoardInfo = (ACPI_BOARD_INFO *)GET_GUID_HOB_DATA (GuidHob);
+
+  mPmTimerReg = (UINTN)pAcpiBoardInfo->PmTimerRegBase;
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Internal function to read the current tick counter of ACPI.
+
+  Internal function to read the current tick counter of ACPI.
+
+  @return The tick counter read.
+
+**/
+UINT32
+InternalAcpiGetTimerTick (
+  VOID
+  )
+{
+  if (mPmTimerReg == 0) {
+    AcpiTimerLibConstructor ();
+  }
+  return IoRead32 (mPmTimerReg);
+}
+
+/**
+  Stalls the CPU for at least the given number of ticks.
+
+  Stalls the CPU for at least the given number of ticks. It's invoked by
+  MicroSecondDelay() and NanoSecondDelay().
+
+  @param  Delay     A period of time to delay in ticks.
+
+**/
+VOID
+InternalAcpiDelay (
+  IN      UINT32                    Delay
+  )
+{
+  UINT32                            Ticks;
+  UINT32                            Times;
+
+  Times    = Delay >> 22;
+  Delay   &= BIT22 - 1;
+  do {
+    //
+    // The target timer count is calculated here
+    //
+    Ticks    = InternalAcpiGetTimerTick () + Delay;
+    Delay    = BIT22;
+    //
+    // Wait until time out
+    // Delay >= 2^23 could not be handled by this function
+    // Timer wrap-arounds are handled correctly by this function
+    //
+    while (((Ticks - InternalAcpiGetTimerTick ()) & BIT23) == 0) {
+      CpuPause ();
+    }
+  } while (Times-- > 0);
+}
+
+/**
+  Stalls the CPU for at least the given number of microseconds.
+
+  Stalls the CPU for the number of microseconds specified by MicroSeconds.
+
+  @param  MicroSeconds  The minimum number of microseconds to delay.
+
+  @return MicroSeconds
+
+**/
+UINTN
+EFIAPI
+MicroSecondDelay (
+  IN UINTN                          MicroSeconds
+  )
+{
+  InternalAcpiDelay (
+    (UINT32)DivU64x32 (
+              MultU64x32 (
+                MicroSeconds,
+                ACPI_TIMER_FREQUENCY
+                ),
+              1000000u
+              )
+    );
+  return MicroSeconds;
+}
+
+/**
+  Stalls the CPU for at least the given number of nanoseconds.
+
+  Stalls the CPU for the number of nanoseconds specified by NanoSeconds.
+
+  @param  NanoSeconds The minimum number of nanoseconds to delay.
+
+  @return NanoSeconds
+
+**/
+UINTN
+EFIAPI
+NanoSecondDelay (
+  IN      UINTN                     NanoSeconds
+  )
+{
+  InternalAcpiDelay (
+    (UINT32)DivU64x32 (
+              MultU64x32 (
+                NanoSeconds,
+                ACPI_TIMER_FREQUENCY
+                ),
+              1000000000u
+              )
+    );
+  return NanoSeconds;
+}
+
+/**
+  Retrieves the current value of a 64-bit free running performance counter.
+
+  Retrieves the current value of a 64-bit free running performance counter. The
+  counter can either count up by 1 or count down by 1. If the physical
+  performance counter counts by a larger increment, then the counter values
+  must be translated. The properties of the counter can be retrieved from
+  GetPerformanceCounterProperties().
+
+  @return The current value of the free running performance counter.
+
+**/
+UINT64
+EFIAPI
+GetPerformanceCounter (
+  VOID
+  )
+{
+  return (UINT64)InternalAcpiGetTimerTick ();
+}
+
+/**
+  Retrieves the 64-bit frequency in Hz and the range of performance counter
+  values.
+
+  If StartValue is not NULL, then the value that the performance counter starts
+  with immediately after is it rolls over is returned in StartValue. If
+  EndValue is not NULL, then the value that the performance counter end with
+  immediately before it rolls over is returned in EndValue. The 64-bit
+  frequency of the performance counter in Hz is always returned. If StartValue
+  is less than EndValue, then the performance counter counts up. If StartValue
+  is greater than EndValue, then the performance counter counts down. For
+  example, a 64-bit free running counter that counts up would have a StartValue
+  of 0 and an EndValue of 0xFFFFFFFFFFFFFFFF. A 24-bit free running counter
+  that counts down would have a StartValue of 0xFFFFFF and an EndValue of 0.
+
+  @param  StartValue  The value the performance counter starts with when it
+                      rolls over.
+  @param  EndValue    The value that the performance counter ends with before
+                      it rolls over.
+
+  @return The frequency in Hz.
+
+**/
+UINT64
+EFIAPI
+GetPerformanceCounterProperties (
+  OUT      UINT64                    *StartValue,  OPTIONAL
+  OUT      UINT64                    *EndValue     OPTIONAL
+  )
+{
+  if (StartValue != NULL) {
+    *StartValue = 0;
+  }
+
+  if (EndValue != NULL) {
+    *EndValue = ACPI_TIMER_COUNT_SIZE - 1;
+  }
+
+  return ACPI_TIMER_FREQUENCY;
+}
+
+/**
+  Converts elapsed ticks of performance counter to time in nanoseconds.
+
+  This function converts the elapsed ticks of running performance counter to
+  time value in unit of nanoseconds.
+
+  @param  Ticks     The number of elapsed ticks of running performance counter.
+
+  @return The elapsed time in nanoseconds.
+
+**/
+UINT64
+EFIAPI
+GetTimeInNanoSecond (
+  IN      UINT64                     Ticks
+  )
+{
+  UINT64  Frequency;
+  UINT64  NanoSeconds;
+  UINT64  Remainder;
+  INTN    Shift;
+
+  Frequency = GetPerformanceCounterProperties (NULL, NULL);
+
+  //
+  //          Ticks
+  // Time = --------- x 1,000,000,000
+  //        Frequency
+  //
+  NanoSeconds = MultU64x32 (DivU64x64Remainder (Ticks, Frequency, &Remainder), 1000000000u);
+
+  //
+  // Ensure (Remainder * 1,000,000,000) will not overflow 64-bit.
+  // Since 2^29 < 1,000,000,000 = 0x3B9ACA00 < 2^30, Remainder should < 2^(64-30) = 2^34,
+  // i.e. highest bit set in Remainder should <= 33.
+  //
+  Shift = MAX (0, HighBitSet64 (Remainder) - 33);
+  Remainder = RShiftU64 (Remainder, (UINTN) Shift);
+  Frequency = RShiftU64 (Frequency, (UINTN) Shift);
+  NanoSeconds += DivU64x64Remainder (MultU64x32 (Remainder, 1000000000u), Frequency, NULL);
+
+  return NanoSeconds;
+}
+
diff --git a/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
new file mode 100644
index 0000000000..3e177cadc0
--- /dev/null
+++ b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
@@ -0,0 +1,40 @@
+## @file
+#  ACPI Timer Library Instance.
+#
+#  Copyright (c) 2014 - 2018, Intel Corporation. All rights reserved.<BR>
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = AcpiTimerLib
+  FILE_GUID                      = A41BF616-EF77-4658-9992-D813071C34CF
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = TimerLib
+
+  CONSTRUCTOR                    = AcpiTimerLibConstructor
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  AcpiTimerLib.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  IoLib
+  HobLib
+  DebugLib
+
+[Guids]
+  gUefiAcpiBoardInfoGuid
diff --git a/UefiPayloadPkg/Library/CbParseLib/CbParseLib.c b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.c
new file mode 100644
index 0000000000..4e23cff50e
--- /dev/null
+++ b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.c
@@ -0,0 +1,560 @@
+/** @file
+  This library will parse the coreboot table in memory and extract those required
+  information.
+
+  Copyright (c) 2014 - 2016, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Uefi/UefiBaseType.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/IoLib.h>
+#include <Library/BlParseLib.h>
+#include <IndustryStandard/Acpi.h>
+#include <Coreboot.h>
+
+
+/**
+  Convert a packed value from cbuint64 to a UINT64 value.
+
+  @param  val      The pointer to packed data.
+
+  @return          the UNIT64 value after conversion.
+
+**/
+UINT64
+cb_unpack64 (
+  IN struct cbuint64 val
+  )
+{
+  return LShiftU64 (val.hi, 32) | val.lo;
+}
+
+
+/**
+  Returns the sum of all elements in a buffer of 16-bit values.  During
+  calculation, the carry bits are also been added.
+
+  @param  Buffer      The pointer to the buffer to carry out the sum operation.
+  @param  Length      The size, in bytes, of Buffer.
+
+  @return Sum         The sum of Buffer with carry bits included during additions.
+
+**/
+UINT16
+CbCheckSum16 (
+  IN UINT16   *Buffer,
+  IN UINTN    Length
+  )
+{
+  UINT32      Sum;
+  UINT32      TmpValue;
+  UINTN       Idx;
+  UINT8       *TmpPtr;
+
+  Sum = 0;
+  TmpPtr = (UINT8 *)Buffer;
+  for(Idx = 0; Idx < Length; Idx++) {
+    TmpValue  = TmpPtr[Idx];
+    if (Idx % 2 == 1) {
+      TmpValue <<= 8;
+    }
+
+    Sum += TmpValue;
+
+    // Wrap
+    if (Sum >= 0x10000) {
+      Sum = (Sum + (Sum >> 16)) & 0xFFFF;
+    }
+  }
+
+  return (UINT16)((~Sum) & 0xFFFF);
+}
+
+
+/**
+  Check the coreboot table if it is valid.
+
+  @param  Header            Pointer to coreboot table
+
+  @retval TRUE              The coreboot table is valid.
+  @retval Others            The coreboot table is not valid.
+
+**/
+BOOLEAN
+IsValidCbTable (
+  IN struct cb_header   *Header
+  )
+{
+  UINT16                 CheckSum;
+
+  if ((Header == NULL) || (Header->table_bytes == 0)) {
+    return FALSE;
+  }
+
+  if (Header->signature != CB_HEADER_SIGNATURE) {
+    return FALSE;
+  }
+
+  //
+  // Check the checksum of the coreboot table header
+  //
+  CheckSum = CbCheckSum16 ((UINT16 *)Header, sizeof (*Header));
+  if (CheckSum != 0) {
+    DEBUG ((DEBUG_ERROR, "Invalid coreboot table header checksum\n"));
+    return FALSE;
+  }
+
+  CheckSum = CbCheckSum16 ((UINT16 *)((UINT8 *)Header + sizeof (*Header)), Header->table_bytes);
+  if (CheckSum != Header->table_checksum) {
+    DEBUG ((DEBUG_ERROR, "Incorrect checksum of all the coreboot table entries\n"));
+    return FALSE;
+  }
+
+  return TRUE;
+}
+
+
+/**
+  This function retrieves the parameter base address from boot loader.
+
+  This function will get bootloader specific parameter address for UEFI payload.
+  e.g. HobList pointer for Slim Bootloader, and coreboot table header for Coreboot.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+EFIAPI
+GetParameterBase (
+  VOID
+  )
+{
+  struct cb_header   *Header;
+  struct cb_record   *Record;
+  UINT8              *TmpPtr;
+  UINT8              *CbTablePtr;
+  UINTN              Idx;
+
+  //
+  // coreboot could pass coreboot table to UEFI payload
+  //
+  Header = (struct cb_header *)(UINTN)GET_BOOTLOADER_PARAMETER ();
+  if (IsValidCbTable (Header)) {
+    return Header;
+  }
+
+  //
+  // Find simplified coreboot table in memory range 0 ~ 4KB.
+  // Some GCC version does not allow directly access to NULL pointer,
+  // so start the search from 0x10 instead.
+  //
+  for (Idx = 16; Idx < 4096; Idx += 16) {
+    Header = (struct cb_header *)Idx;
+    if (Header->signature == CB_HEADER_SIGNATURE) {
+      break;
+    }
+  }
+
+  if (Idx >= 4096) {
+    return NULL;
+  }
+
+  //
+  // Check the coreboot header
+  //
+  if (!IsValidCbTable (Header)) {
+    return NULL;
+  }
+
+  //
+  // Find full coreboot table in high memory
+  //
+  CbTablePtr = NULL;
+  TmpPtr = (UINT8 *)Header + Header->header_bytes;
+  for (Idx = 0; Idx < Header->table_entries; Idx++) {
+    Record = (struct cb_record *)TmpPtr;
+    if (Record->tag == CB_TAG_FORWARD) {
+      CbTablePtr = (VOID *)(UINTN)((struct cb_forward *)(UINTN)Record)->forward;
+      break;
+    }
+    TmpPtr += Record->size;
+  }
+
+  //
+  // Check the coreboot header in high memory
+  //
+  if (!IsValidCbTable ((struct cb_header *)CbTablePtr)) {
+    return NULL;
+  }
+
+  SET_BOOTLOADER_PARAMETER ((UINT32)(UINTN)CbTablePtr);
+
+  return CbTablePtr;
+}
+
+
+/**
+  Find coreboot record with given Tag.
+
+  @param  Tag                The tag id to be found
+
+  @retval NULL              The Tag is not found.
+  @retval Others            The pointer to the record found.
+
+**/
+VOID *
+FindCbTag (
+  IN  UINT32         Tag
+  )
+{
+  struct cb_header   *Header;
+  struct cb_record   *Record;
+  UINT8              *TmpPtr;
+  UINT8              *TagPtr;
+  UINTN              Idx;
+
+  Header = (struct cb_header *) GetParameterBase ();
+
+  TagPtr = NULL;
+  TmpPtr = (UINT8 *)Header + Header->header_bytes;
+  for (Idx = 0; Idx < Header->table_entries; Idx++) {
+    Record = (struct cb_record *)TmpPtr;
+    if (Record->tag == Tag) {
+      TagPtr = TmpPtr;
+      break;
+    }
+    TmpPtr += Record->size;
+  }
+
+  return TagPtr;
+}
+
+
+/**
+  Find the given table with TableId from the given coreboot memory Root.
+
+  @param  Root               The coreboot memory table to be searched in
+  @param  TableId            Table id to be found
+  @param  MemTable           To save the base address of the memory table found
+  @param  MemTableSize       To save the size of memory table found
+
+  @retval RETURN_SUCCESS            Successfully find out the memory table.
+  @retval RETURN_INVALID_PARAMETER  Invalid input parameters.
+  @retval RETURN_NOT_FOUND          Failed to find the memory table.
+
+**/
+RETURN_STATUS
+FindCbMemTable (
+  IN  struct cbmem_root  *Root,
+  IN  UINT32             TableId,
+  OUT VOID               **MemTable,
+  OUT UINT32             *MemTableSize
+  )
+{
+  UINTN                  Idx;
+  BOOLEAN                IsImdEntry;
+  struct cbmem_entry     *Entries;
+
+  if ((Root == NULL) || (MemTable == NULL)) {
+    return RETURN_INVALID_PARAMETER;
+  }
+  //
+  // Check if the entry is CBMEM or IMD
+  // and handle them separately
+  //
+  Entries = Root->entries;
+  if (Entries[0].magic == CBMEM_ENTRY_MAGIC) {
+    IsImdEntry = FALSE;
+  } else {
+    Entries = (struct cbmem_entry *)((struct imd_root *)Root)->entries;
+    if (Entries[0].magic == IMD_ENTRY_MAGIC) {
+      IsImdEntry = TRUE;
+    } else {
+      return RETURN_NOT_FOUND;
+    }
+  }
+
+  for (Idx = 0; Idx < Root->num_entries; Idx++) {
+    if (Entries[Idx].id == TableId) {
+      if (IsImdEntry) {
+        *MemTable = (VOID *) ((UINTN)Entries[Idx].start + (UINTN)Root);
+      } else {
+        *MemTable = (VOID *) (UINTN)Entries[Idx].start;
+      }
+      if (MemTableSize != NULL) {
+        *MemTableSize = Entries[Idx].size;
+      }
+
+      DEBUG ((DEBUG_INFO, "Find CbMemTable Id 0x%x, base %p, size 0x%x\n",
+        TableId, *MemTable, Entries[Idx].size));
+      return RETURN_SUCCESS;
+    }
+  }
+
+  return RETURN_NOT_FOUND;
+}
+
+/**
+  Acquire the coreboot memory table with the given table id
+
+  @param  TableId            Table id to be searched
+  @param  MemTable           Pointer to the base address of the memory table
+  @param  MemTableSize       Pointer to the size of the memory table
+
+  @retval RETURN_SUCCESS     Successfully find out the memory table.
+  @retval RETURN_INVALID_PARAMETER  Invalid input parameters.
+  @retval RETURN_NOT_FOUND   Failed to find the memory table.
+
+**/
+RETURN_STATUS
+ParseCbMemTable (
+  IN  UINT32               TableId,
+  OUT VOID                 **MemTable,
+  OUT UINT32               *MemTableSize
+  )
+{
+  EFI_STATUS               Status;
+  struct cb_memory         *rec;
+  struct cb_memory_range   *Range;
+  UINT64                   Start;
+  UINT64                   Size;
+  UINTN                    Index;
+  struct cbmem_root        *CbMemRoot;
+
+  if (MemTable == NULL) {
+    return RETURN_INVALID_PARAMETER;
+  }
+
+  *MemTable = NULL;
+  Status    = RETURN_NOT_FOUND;
+
+  //
+  // Get the coreboot memory table
+  //
+  rec = (struct cb_memory *)FindCbTag (CB_TAG_MEMORY);
+  if (rec == NULL) {
+    return Status;
+  }
+
+  for (Index = 0; Index < MEM_RANGE_COUNT(rec); Index++) {
+    Range = MEM_RANGE_PTR(rec, Index);
+    Start = cb_unpack64(Range->start);
+    Size = cb_unpack64(Range->size);
+
+    if ((Range->type == CB_MEM_TABLE) && (Start > 0x1000)) {
+      CbMemRoot = (struct  cbmem_root *)(UINTN)(Start + Size - DYN_CBMEM_ALIGN_SIZE);
+      Status = FindCbMemTable (CbMemRoot, TableId, MemTable, MemTableSize);
+      if (!EFI_ERROR (Status)) {
+        break;
+      }
+    }
+  }
+
+  return Status;
+}
+
+
+
+/**
+  Acquire the memory information from the coreboot table in memory.
+
+  @param  MemInfoCallback     The callback routine
+  @param  Params              Pointer to the callback routine parameter
+
+  @retval RETURN_SUCCESS     Successfully find out the memory information.
+  @retval RETURN_NOT_FOUND   Failed to find the memory information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseMemoryInfo (
+  IN  BL_MEM_INFO_CALLBACK  MemInfoCallback,
+  IN  VOID                  *Params
+  )
+{
+  struct cb_memory         *rec;
+  struct cb_memory_range   *Range;
+  UINTN                    Index;
+  MEMROY_MAP_ENTRY         MemoryMap;
+
+  //
+  // Get the coreboot memory table
+  //
+  rec = (struct cb_memory *)FindCbTag (CB_TAG_MEMORY);
+  if (rec == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  for (Index = 0; Index < MEM_RANGE_COUNT(rec); Index++) {
+    Range = MEM_RANGE_PTR(rec, Index);
+    MemoryMap.Base = cb_unpack64(Range->start);
+    MemoryMap.Size = cb_unpack64(Range->size);
+    MemoryMap.Type = (UINT8)Range->type;
+    MemoryMap.Flag = 0;
+    DEBUG ((DEBUG_INFO, "%d. %016lx - %016lx [%02x]\n",
+            Index, MemoryMap.Base, MemoryMap.Base + MemoryMap.Size - 1, MemoryMap.Type));
+
+    MemInfoCallback (&MemoryMap, Params);
+  }
+
+  return RETURN_SUCCESS;
+}
+
+
+/**
+  Acquire acpi table and smbios table from coreboot
+
+  @param  SystemTableInfo          Pointer to the system table info
+
+  @retval RETURN_SUCCESS            Successfully find out the tables.
+  @retval RETURN_NOT_FOUND          Failed to find the tables.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSystemTable (
+  OUT SYSTEM_TABLE_INFO     *SystemTableInfo
+  )
+{
+  EFI_STATUS       Status;
+  VOID             *MemTable;
+  UINT32           MemTableSize;
+
+  Status = ParseCbMemTable (SIGNATURE_32 ('T', 'B', 'M', 'S'), &MemTable, &MemTableSize);
+  if (EFI_ERROR (Status)) {
+    return EFI_NOT_FOUND;
+  }
+  SystemTableInfo->SmbiosTableBase = (UINT64) (UINTN)MemTable;
+  SystemTableInfo->SmbiosTableSize = MemTableSize;
+
+  Status = ParseCbMemTable (SIGNATURE_32 ('I', 'P', 'C', 'A'), &MemTable, &MemTableSize);
+  if (EFI_ERROR (Status)) {
+    return EFI_NOT_FOUND;
+  }
+  SystemTableInfo->AcpiTableBase = (UINT64) (UINTN)MemTable;
+  SystemTableInfo->AcpiTableSize = MemTableSize;
+
+  return Status;
+}
+
+
+/**
+  Find the serial port information
+
+  @param  SERIAL_PORT_INFO   Pointer to serial port info structure
+
+  @retval RETURN_SUCCESS     Successfully find the serial port information.
+  @retval RETURN_NOT_FOUND   Failed to find the serial port information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSerialInfo (
+  OUT SERIAL_PORT_INFO     *SerialPortInfo
+  )
+{
+  struct cb_serial          *CbSerial;
+
+  CbSerial = FindCbTag (CB_TAG_SERIAL);
+  if (CbSerial == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  SerialPortInfo->BaseAddr    = CbSerial->baseaddr;
+  SerialPortInfo->RegWidth    = CbSerial->regwidth;
+  SerialPortInfo->Type        = CbSerial->type;
+  SerialPortInfo->Baud        = CbSerial->baud;
+  SerialPortInfo->InputHertz  = CbSerial->input_hertz;
+  SerialPortInfo->UartPciAddr = CbSerial->uart_pci_addr;
+
+  return RETURN_SUCCESS;
+}
+
+/**
+  Find the video frame buffer information
+
+  @param  GfxInfo             Pointer to the EFI_PEI_GRAPHICS_INFO_HOB structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseGfxInfo (
+  OUT EFI_PEI_GRAPHICS_INFO_HOB         *GfxInfo
+  )
+{
+  struct cb_framebuffer                 *CbFbRec;
+  EFI_GRAPHICS_OUTPUT_MODE_INFORMATION  *GfxMode;
+
+  if (GfxInfo == NULL) {
+    return RETURN_INVALID_PARAMETER;
+  }
+
+  CbFbRec = FindCbTag (CB_TAG_FRAMEBUFFER);
+  if (CbFbRec == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  DEBUG ((DEBUG_INFO, "Found coreboot video frame buffer information\n"));
+  DEBUG ((DEBUG_INFO, "physical_address: 0x%lx\n", CbFbRec->physical_address));
+  DEBUG ((DEBUG_INFO, "x_resolution: 0x%x\n", CbFbRec->x_resolution));
+  DEBUG ((DEBUG_INFO, "y_resolution: 0x%x\n", CbFbRec->y_resolution));
+  DEBUG ((DEBUG_INFO, "bits_per_pixel: 0x%x\n", CbFbRec->bits_per_pixel));
+  DEBUG ((DEBUG_INFO, "bytes_per_line: 0x%x\n", CbFbRec->bytes_per_line));
+
+  DEBUG ((DEBUG_INFO, "red_mask_size: 0x%x\n", CbFbRec->red_mask_size));
+  DEBUG ((DEBUG_INFO, "red_mask_pos: 0x%x\n", CbFbRec->red_mask_pos));
+  DEBUG ((DEBUG_INFO, "green_mask_size: 0x%x\n", CbFbRec->green_mask_size));
+  DEBUG ((DEBUG_INFO, "green_mask_pos: 0x%x\n", CbFbRec->green_mask_pos));
+  DEBUG ((DEBUG_INFO, "blue_mask_size: 0x%x\n", CbFbRec->blue_mask_size));
+  DEBUG ((DEBUG_INFO, "blue_mask_pos: 0x%x\n", CbFbRec->blue_mask_pos));
+  DEBUG ((DEBUG_INFO, "reserved_mask_size: 0x%x\n", CbFbRec->reserved_mask_size));
+  DEBUG ((DEBUG_INFO, "reserved_mask_pos: 0x%x\n", CbFbRec->reserved_mask_pos));
+
+  GfxMode = &GfxInfo->GraphicsMode;
+  GfxMode->Version              = 0;
+  GfxMode->HorizontalResolution = CbFbRec->x_resolution;
+  GfxMode->VerticalResolution   = CbFbRec->y_resolution;
+  GfxMode->PixelsPerScanLine    = (CbFbRec->bytes_per_line << 3) / CbFbRec->bits_per_pixel;
+  if ((CbFbRec->red_mask_pos == 0) && (CbFbRec->green_mask_pos == 8) && (CbFbRec->blue_mask_pos == 16)) {
+    GfxMode->PixelFormat = PixelRedGreenBlueReserved8BitPerColor;
+  } else if ((CbFbRec->blue_mask_pos == 0) && (CbFbRec->green_mask_pos == 8) && (CbFbRec->red_mask_pos == 16)) {
+     GfxMode->PixelFormat = PixelBlueGreenRedReserved8BitPerColor;
+  }
+  GfxMode->PixelInformation.RedMask      = ((1 << CbFbRec->red_mask_size)      - 1) << CbFbRec->red_mask_pos;
+  GfxMode->PixelInformation.GreenMask    = ((1 << CbFbRec->green_mask_size)    - 1) << CbFbRec->green_mask_pos;
+  GfxMode->PixelInformation.BlueMask     = ((1 << CbFbRec->blue_mask_size)     - 1) << CbFbRec->blue_mask_pos;
+  GfxMode->PixelInformation.ReservedMask = ((1 << CbFbRec->reserved_mask_size) - 1) << CbFbRec->reserved_mask_pos;
+
+  GfxInfo->FrameBufferBase = CbFbRec->physical_address;
+  GfxInfo->FrameBufferSize = CbFbRec->bytes_per_line *  CbFbRec->y_resolution;
+
+  return RETURN_SUCCESS;
+}
+
+/**
+  Find the video frame buffer device information
+
+  @param  GfxDeviceInfo      Pointer to the EFI_PEI_GRAPHICS_DEVICE_INFO_HOB structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseGfxDeviceInfo (
+  OUT EFI_PEI_GRAPHICS_DEVICE_INFO_HOB       *GfxDeviceInfo
+  )
+{
+  return RETURN_NOT_FOUND;
+}
+
diff --git a/UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
new file mode 100644
index 0000000000..52e3ad2054
--- /dev/null
+++ b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
@@ -0,0 +1,39 @@
+## @file
+#  Coreboot Table Parse Library.
+#
+#  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = CbParseLib
+  FILE_GUID                      = 49EDFC9E-5945-4386-9C0B-C9B60CD45BB1
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = BlParseLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources]
+  CbParseLib.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  BaseMemoryLib
+  IoLib
+  DebugLib
+  PcdLib
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h
new file mode 100644
index 0000000000..c2961b3bee
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h
@@ -0,0 +1,80 @@
+/** @file
+  Header file of PciHostBridgeLib.
+
+  Copyright (C) 2016, Red Hat, Inc.
+  Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef _PCI_HOST_BRIDGE_H
+#define _PCI_HOST_BRIDGE_H
+
+typedef struct {
+  ACPI_HID_DEVICE_PATH     AcpiDevicePath;
+  EFI_DEVICE_PATH_PROTOCOL EndDevicePath;
+} CB_PCI_ROOT_BRIDGE_DEVICE_PATH;
+
+PCI_ROOT_BRIDGE *
+ScanForRootBridges (
+  UINTN      *NumberOfRootBridges
+);
+
+/**
+  Initialize a PCI_ROOT_BRIDGE structure.
+
+  @param[in]  Supports         Supported attributes.
+
+  @param[in]  Attributes       Initial attributes.
+
+  @param[in]  AllocAttributes  Allocation attributes.
+
+  @param[in]  RootBusNumber    The bus number to store in RootBus.
+
+  @param[in]  MaxSubBusNumber  The inclusive maximum bus number that can be
+                               assigned to any subordinate bus found behind any
+                               PCI bridge hanging off this root bus.
+
+                               The caller is responsible for ensuring that
+                               RootBusNumber <= MaxSubBusNumber. If
+                               RootBusNumber equals MaxSubBusNumber, then the
+                               root bus has no room for subordinate buses.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+
+  @param[out] RootBus          The PCI_ROOT_BRIDGE structure (allocated by the
+                               caller) that should be filled in by this
+                               function.
+
+  @retval EFI_SUCCESS           Initialization successful. A device path
+                                consisting of an ACPI device path node, with
+                                UID = RootBusNumber, has been allocated and
+                                linked into RootBus.
+
+  @retval EFI_OUT_OF_RESOURCES  Memory allocation failed.
+**/
+EFI_STATUS
+InitRootBridge (
+  IN  UINT64                   Supports,
+  IN  UINT64                   Attributes,
+  IN  UINT64                   AllocAttributes,
+  IN  UINT8                    RootBusNumber,
+  IN  UINT8                    MaxSubBusNumber,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Io,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Mem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *MemAbove4G,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMemAbove4G,
+  OUT PCI_ROOT_BRIDGE          *RootBus
+);
+
+#endif
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c
new file mode 100644
index 0000000000..512c3127cc
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c
@@ -0,0 +1,222 @@
+/** @file
+  Library instance of PciHostBridgeLib library class for coreboot.
+
+  Copyright (C) 2016, Red Hat, Inc.
+  Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+#include <PiDxe.h>
+
+#include <IndustryStandard/Pci.h>
+#include <Protocol/PciHostBridgeResourceAllocation.h>
+#include <Protocol/PciRootBridgeIo.h>
+
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/PciHostBridgeLib.h>
+#include <Library/PciLib.h>
+
+#include "PciHostBridge.h"
+
+STATIC
+CONST
+CB_PCI_ROOT_BRIDGE_DEVICE_PATH mRootBridgeDevicePathTemplate = {
+  {
+    {
+      ACPI_DEVICE_PATH,
+      ACPI_DP,
+      {
+        (UINT8) (sizeof(ACPI_HID_DEVICE_PATH)),
+        (UINT8) ((sizeof(ACPI_HID_DEVICE_PATH)) >> 8)
+      }
+    },
+    EISA_PNP_ID(0x0A03), // HID
+    0                    // UID
+  },
+
+  {
+    END_DEVICE_PATH_TYPE,
+    END_ENTIRE_DEVICE_PATH_SUBTYPE,
+    {
+      END_DEVICE_PATH_LENGTH,
+      0
+    }
+  }
+};
+
+
+/**
+  Initialize a PCI_ROOT_BRIDGE structure.
+
+  @param[in]  Supports         Supported attributes.
+
+  @param[in]  Attributes       Initial attributes.
+
+  @param[in]  AllocAttributes  Allocation attributes.
+
+  @param[in]  RootBusNumber    The bus number to store in RootBus.
+
+  @param[in]  MaxSubBusNumber  The inclusive maximum bus number that can be
+                               assigned to any subordinate bus found behind any
+                               PCI bridge hanging off this root bus.
+
+                               The caller is responsible for ensuring that
+                               RootBusNumber <= MaxSubBusNumber. If
+                               RootBusNumber equals MaxSubBusNumber, then the
+                               root bus has no room for subordinate buses.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+
+  @param[out] RootBus          The PCI_ROOT_BRIDGE structure (allocated by the
+                               caller) that should be filled in by this
+                               function.
+
+  @retval EFI_SUCCESS           Initialization successful. A device path
+                                consisting of an ACPI device path node, with
+                                UID = RootBusNumber, has been allocated and
+                                linked into RootBus.
+
+  @retval EFI_OUT_OF_RESOURCES  Memory allocation failed.
+**/
+EFI_STATUS
+InitRootBridge (
+  IN  UINT64                   Supports,
+  IN  UINT64                   Attributes,
+  IN  UINT64                   AllocAttributes,
+  IN  UINT8                    RootBusNumber,
+  IN  UINT8                    MaxSubBusNumber,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Io,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Mem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *MemAbove4G,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMemAbove4G,
+  OUT PCI_ROOT_BRIDGE          *RootBus
+)
+{
+  CB_PCI_ROOT_BRIDGE_DEVICE_PATH *DevicePath;
+
+  //
+  // Be safe if other fields are added to PCI_ROOT_BRIDGE later.
+  //
+  ZeroMem (RootBus, sizeof *RootBus);
+
+  RootBus->Segment = 0;
+
+  RootBus->Supports   = Supports;
+  RootBus->Attributes = Attributes;
+
+  RootBus->DmaAbove4G = FALSE;
+
+  RootBus->AllocationAttributes = AllocAttributes;
+  RootBus->Bus.Base  = RootBusNumber;
+  RootBus->Bus.Limit = MaxSubBusNumber;
+  CopyMem (&RootBus->Io, Io, sizeof (*Io));
+  CopyMem (&RootBus->Mem, Mem, sizeof (*Mem));
+  CopyMem (&RootBus->MemAbove4G, MemAbove4G, sizeof (*MemAbove4G));
+  CopyMem (&RootBus->PMem, PMem, sizeof (*PMem));
+  CopyMem (&RootBus->PMemAbove4G, PMemAbove4G, sizeof (*PMemAbove4G));
+
+  RootBus->NoExtendedConfigSpace = FALSE;
+
+  DevicePath = AllocateCopyPool (sizeof (mRootBridgeDevicePathTemplate),
+                                 &mRootBridgeDevicePathTemplate);
+  if (DevicePath == NULL) {
+    DEBUG ((DEBUG_ERROR, "%a: %r\n", __FUNCTION__, EFI_OUT_OF_RESOURCES));
+    return EFI_OUT_OF_RESOURCES;
+  }
+  DevicePath->AcpiDevicePath.UID = RootBusNumber;
+  RootBus->DevicePath = (EFI_DEVICE_PATH_PROTOCOL *)DevicePath;
+
+  DEBUG ((DEBUG_INFO,
+          "%a: populated root bus %d, with room for %d subordinate bus(es)\n",
+          __FUNCTION__, RootBusNumber, MaxSubBusNumber - RootBusNumber));
+  return EFI_SUCCESS;
+}
+
+
+/**
+  Return all the root bridge instances in an array.
+
+  @param Count  Return the count of root bridge instances.
+
+  @return All the root bridge instances in an array.
+          The array should be passed into PciHostBridgeFreeRootBridges()
+          when it's not used.
+**/
+PCI_ROOT_BRIDGE *
+EFIAPI
+PciHostBridgeGetRootBridges (
+  UINTN *Count
+)
+{
+  return ScanForRootBridges (Count);
+}
+
+
+/**
+  Free the root bridge instances array returned from
+  PciHostBridgeGetRootBridges().
+
+  @param  The root bridge instances array.
+  @param  The count of the array.
+**/
+VOID
+EFIAPI
+PciHostBridgeFreeRootBridges (
+  PCI_ROOT_BRIDGE *Bridges,
+  UINTN           Count
+)
+{
+  if (Bridges == NULL && Count == 0) {
+    return;
+  }
+  ASSERT (Bridges != NULL && Count > 0);
+
+  do {
+    --Count;
+    FreePool (Bridges[Count].DevicePath);
+  } while (Count > 0);
+
+  FreePool (Bridges);
+}
+
+
+/**
+  Inform the platform that the resource conflict happens.
+
+  @param HostBridgeHandle Handle of the Host Bridge.
+  @param Configuration    Pointer to PCI I/O and PCI memory resource
+                          descriptors. The Configuration contains the resources
+                          for all the root bridges. The resource for each root
+                          bridge is terminated with END descriptor and an
+                          additional END is appended indicating the end of the
+                          entire resources. The resource descriptor field
+                          values follow the description in
+                          EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL
+                          .SubmitResources().
+**/
+VOID
+EFIAPI
+PciHostBridgeResourceConflict (
+  EFI_HANDLE                        HostBridgeHandle,
+  VOID                              *Configuration
+)
+{
+  //
+  // coreboot UEFI Payload does not do PCI enumeration and should not call this
+  // library interface.
+  //
+  ASSERT (FALSE);
+}
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
new file mode 100644
index 0000000000..7896df2416
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
@@ -0,0 +1,41 @@
+## @file
+#  Library instance of PciHostBridgeLib library class for coreboot.
+#
+#  Copyright (C) 2016, Red Hat, Inc.
+#  Copyright (c) 2016 - 2018, Intel Corporation. All rights reserved.<BR>
+#
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PciHostBridgeLib
+  FILE_GUID                      = 62EE5269-CFFD-43a3-BE3F-622FC79F467E
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PciHostBridgeLib
+
+#
+# The following information is for reference only and not required by the build
+# tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  PciHostBridge.h
+  PciHostBridgeLib.c
+  PciHostBridgeSupport.c
+
+[Packages]
+  MdeModulePkg/MdeModulePkg.dec
+  MdePkg/MdePkg.dec
+
+[LibraryClasses]
+  BaseMemoryLib
+  DebugLib
+  DevicePathLib
+  MemoryAllocationLib
+  PciLib
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c
new file mode 100644
index 0000000000..fffbf04cad
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c
@@ -0,0 +1,584 @@
+/** @file
+  Scan the entire PCI bus for root bridges to support coreboot UEFI payload.
+
+  Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <PiDxe.h>
+#include <IndustryStandard/Pci.h>
+#include <Protocol/PciHostBridgeResourceAllocation.h>
+#include <Protocol/PciRootBridgeIo.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/PciHostBridgeLib.h>
+#include <Library/PciLib.h>
+#include "PciHostBridge.h"
+
+/**
+  Adjust the collected PCI resource.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+**/
+VOID
+AdjustRootBridgeResource (
+  IN  PCI_ROOT_BRIDGE_APERTURE *Io,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Mem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *MemAbove4G,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMemAbove4G
+)
+{
+  UINT64  Mask;
+
+  //
+  // For now try to downgrade everything into MEM32 since
+  // - coreboot does not assign resource above 4GB
+  // - coreboot might allocate interleaved MEM32 and PMEM32 resource
+  //   in some cases
+  //
+  if (PMem->Base < Mem->Base) {
+    Mem->Base = PMem->Base;
+  }
+
+  if (PMem->Limit > Mem->Limit) {
+    Mem->Limit = PMem->Limit;
+  }
+
+  PMem->Base  = MAX_UINT64;
+  PMem->Limit = 0;
+
+  if (MemAbove4G->Base < 0x100000000ULL) {
+    if (MemAbove4G->Base < Mem->Base) {
+      Mem->Base  = MemAbove4G->Base;
+    }
+    if (MemAbove4G->Limit > Mem->Limit) {
+      Mem->Limit = MemAbove4G->Limit;
+    }
+    MemAbove4G->Base  = MAX_UINT64;
+    MemAbove4G->Limit = 0;
+  }
+
+  if (PMemAbove4G->Base < 0x100000000ULL) {
+    if (PMemAbove4G->Base < Mem->Base) {
+      Mem->Base  = PMemAbove4G->Base;
+    }
+    if (PMemAbove4G->Limit > Mem->Limit) {
+      Mem->Limit = PMemAbove4G->Limit;
+    }
+    PMemAbove4G->Base  = MAX_UINT64;
+    PMemAbove4G->Limit = 0;
+  }
+
+  //
+  // Align IO  resource at 4K  boundary
+  //
+  Mask        = 0xFFFULL;
+  Io->Limit   = ((Io->Limit + Mask) & ~Mask) - 1;
+  if (Io->Base != MAX_UINT64) {
+    Io->Base &= ~Mask;
+  }
+
+  //
+  // Align MEM resource at 1MB boundary
+  //
+  Mask        = 0xFFFFFULL;
+  Mem->Limit  = ((Mem->Limit + Mask) & ~Mask) - 1;
+  if (Mem->Base != MAX_UINT64) {
+    Mem->Base &= ~Mask;
+  }
+}
+
+/**
+  Probe a bar is existed or not.
+
+  @param[in]    Address           PCI address for the BAR.
+  @param[out]   OriginalValue     The original bar value returned.
+  @param[out]   Value             The probed bar value returned.
+**/
+STATIC
+VOID
+PcatPciRootBridgeBarExisted (
+  IN  UINT64                         Address,
+  OUT UINT32                         *OriginalValue,
+  OUT UINT32                         *Value
+)
+{
+  UINTN   PciAddress;
+
+  PciAddress = (UINTN)Address;
+
+  //
+  // Preserve the original value
+  //
+  *OriginalValue = PciRead32 (PciAddress);
+
+  //
+  // Disable timer interrupt while the BAR is probed
+  //
+  DisableInterrupts ();
+
+  PciWrite32 (PciAddress, 0xFFFFFFFF);
+  *Value = PciRead32 (PciAddress);
+  PciWrite32 (PciAddress, *OriginalValue);
+
+  //
+  // Enable interrupt
+  //
+  EnableInterrupts ();
+}
+
+/**
+  Parse PCI bar and collect the assigned PCI resource information.
+
+  @param[in]  Command          Supported attributes.
+
+  @param[in]  Bus              PCI bus number.
+
+  @param[in]  Device           PCI device number.
+
+  @param[in]  Function         PCI function number.
+
+  @param[in]  BarOffsetBase    PCI bar start offset.
+
+  @param[in]  BarOffsetEnd     PCI bar end offset.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+**/
+STATIC
+VOID
+PcatPciRootBridgeParseBars (
+  IN UINT16                         Command,
+  IN UINTN                          Bus,
+  IN UINTN                          Device,
+  IN UINTN                          Function,
+  IN UINTN                          BarOffsetBase,
+  IN UINTN                          BarOffsetEnd,
+  IN PCI_ROOT_BRIDGE_APERTURE       *Io,
+  IN PCI_ROOT_BRIDGE_APERTURE       *Mem,
+  IN PCI_ROOT_BRIDGE_APERTURE       *MemAbove4G,
+  IN PCI_ROOT_BRIDGE_APERTURE       *PMem,
+  IN PCI_ROOT_BRIDGE_APERTURE       *PMemAbove4G
+
+)
+{
+  UINT32                            OriginalValue;
+  UINT32                            Value;
+  UINT32                            OriginalUpperValue;
+  UINT32                            UpperValue;
+  UINT64                            Mask;
+  UINTN                             Offset;
+  UINTN                             LowBit;
+  UINT64                            Base;
+  UINT64                            Length;
+  UINT64                            Limit;
+  PCI_ROOT_BRIDGE_APERTURE          *MemAperture;
+
+  for (Offset = BarOffsetBase; Offset < BarOffsetEnd; Offset += sizeof (UINT32)) {
+    PcatPciRootBridgeBarExisted (
+      PCI_LIB_ADDRESS (Bus, Device, Function, Offset),
+      &OriginalValue, &Value
+    );
+    if (Value == 0) {
+      continue;
+    }
+    if ((Value & BIT0) == BIT0) {
+      //
+      // IO Bar
+      //
+      if (Command & EFI_PCI_COMMAND_IO_SPACE) {
+        Mask = 0xfffffffc;
+        Base = OriginalValue & Mask;
+        Length = ((~(Value & Mask)) & Mask) + 0x04;
+        if (!(Value & 0xFFFF0000)) {
+          Length &= 0x0000FFFF;
+        }
+        Limit = Base + Length - 1;
+
+        if ((Base > 0) && (Base < Limit)) {
+          if (Io->Base > Base) {
+            Io->Base = Base;
+          }
+          if (Io->Limit < Limit) {
+            Io->Limit = Limit;
+          }
+        }
+      }
+    } else {
+      //
+      // Mem Bar
+      //
+      if (Command & EFI_PCI_COMMAND_MEMORY_SPACE) {
+
+        Mask = 0xfffffff0;
+        Base = OriginalValue & Mask;
+        Length = Value & Mask;
+
+        if ((Value & (BIT1 | BIT2)) == 0) {
+          //
+          // 32bit
+          //
+          Length = ((~Length) + 1) & 0xffffffff;
+
+          if ((Value & BIT3) == BIT3) {
+            MemAperture = PMem;
+          } else {
+            MemAperture = Mem;
+          }
+        } else {
+          //
+          // 64bit
+          //
+          Offset += 4;
+          PcatPciRootBridgeBarExisted (
+            PCI_LIB_ADDRESS (Bus, Device, Function, Offset),
+            &OriginalUpperValue,
+            &UpperValue
+          );
+
+          Base = Base | LShiftU64 ((UINT64) OriginalUpperValue, 32);
+          Length = Length | LShiftU64 ((UINT64) UpperValue, 32);
+          if (Length != 0) {
+            LowBit = LowBitSet64 (Length);
+            Length = LShiftU64 (1ULL, LowBit);
+          }
+
+          if ((Value & BIT3) == BIT3) {
+            MemAperture = PMemAbove4G;
+          } else {
+            MemAperture = MemAbove4G;
+          }
+        }
+
+        Limit = Base + Length - 1;
+        if ((Base > 0) && (Base < Limit)) {
+          if (MemAperture->Base > Base) {
+            MemAperture->Base = Base;
+          }
+          if (MemAperture->Limit < Limit) {
+            MemAperture->Limit = Limit;
+          }
+        }
+      }
+    }
+  }
+}
+
+/**
+  Scan for all root bridges in platform.
+
+  @param[out] NumberOfRootBridges  Number of root bridges detected
+
+  @retval     Pointer to the allocated PCI_ROOT_BRIDGE structure array.
+**/
+PCI_ROOT_BRIDGE *
+ScanForRootBridges (
+  OUT UINTN      *NumberOfRootBridges
+)
+{
+  UINTN      PrimaryBus;
+  UINTN      SubBus;
+  UINT8      Device;
+  UINT8      Function;
+  UINTN      NumberOfDevices;
+  UINTN      Address;
+  PCI_TYPE01 Pci;
+  UINT64     Attributes;
+  UINT64     Base;
+  UINT64     Limit;
+  UINT64     Value;
+  PCI_ROOT_BRIDGE_APERTURE Io, Mem, MemAbove4G, PMem, PMemAbove4G, *MemAperture;
+  PCI_ROOT_BRIDGE *RootBridges;
+  UINTN      BarOffsetEnd;
+
+
+  *NumberOfRootBridges = 0;
+  RootBridges = NULL;
+
+  //
+  // After scanning all the PCI devices on the PCI root bridge's primary bus,
+  // update the Primary Bus Number for the next PCI root bridge to be this PCI
+  // root bridge's subordinate bus number + 1.
+  //
+  for (PrimaryBus = 0; PrimaryBus <= PCI_MAX_BUS; PrimaryBus = SubBus + 1) {
+    SubBus = PrimaryBus;
+    Attributes = 0;
+
+    ZeroMem (&Io, sizeof (Io));
+    ZeroMem (&Mem, sizeof (Mem));
+    ZeroMem (&MemAbove4G, sizeof (MemAbove4G));
+    ZeroMem (&PMem, sizeof (PMem));
+    ZeroMem (&PMemAbove4G, sizeof (PMemAbove4G));
+    Io.Base = Mem.Base = MemAbove4G.Base = PMem.Base = PMemAbove4G.Base = MAX_UINT64;
+    //
+    // Scan all the PCI devices on the primary bus of the PCI root bridge
+    //
+    for (Device = 0, NumberOfDevices = 0; Device <= PCI_MAX_DEVICE; Device++) {
+
+      for (Function = 0; Function <= PCI_MAX_FUNC; Function++) {
+
+        //
+        // Compute the PCI configuration address of the PCI device to probe
+        //
+        Address = PCI_LIB_ADDRESS (PrimaryBus, Device, Function, 0);
+
+        //
+        // Read the Vendor ID from the PCI Configuration Header
+        //
+        if (PciRead16 (Address) == MAX_UINT16) {
+          if (Function == 0) {
+            //
+            // If the PCI Configuration Read fails, or a PCI device does not
+            // exist, then skip this entire PCI device
+            //
+            break;
+          } else {
+            //
+            // If PCI function != 0, VendorId == 0xFFFF, we continue to search
+            // PCI function.
+            //
+            continue;
+          }
+        }
+
+        //
+        // Read the entire PCI Configuration Header
+        //
+        PciReadBuffer (Address, sizeof (Pci), &Pci);
+
+        //
+        // Increment the number of PCI device found on the primary bus of the
+        // PCI root bridge
+        //
+        NumberOfDevices++;
+
+        //
+        // Look for devices with the VGA Palette Snoop enabled in the COMMAND
+        // register of the PCI Config Header
+        //
+        if ((Pci.Hdr.Command & EFI_PCI_COMMAND_VGA_PALETTE_SNOOP) != 0) {
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO_16;
+        }
+
+        BarOffsetEnd = 0;
+
+        //
+        // PCI-PCI Bridge
+        //
+        if (IS_PCI_BRIDGE (&Pci)) {
+          //
+          // Get the Bus range that the PPB is decoding
+          //
+          if (Pci.Bridge.SubordinateBus > SubBus) {
+            //
+            // If the subordinate bus number of the PCI-PCI bridge is greater
+            // than the PCI root bridge's current subordinate bus number,
+            // then update the PCI root bridge's subordinate bus number
+            //
+            SubBus = Pci.Bridge.SubordinateBus;
+          }
+
+          //
+          // Get the I/O range that the PPB is decoding
+          //
+          Value = Pci.Bridge.IoBase & 0x0f;
+          Base = ((UINT32) Pci.Bridge.IoBase & 0xf0) << 8;
+          Limit = (((UINT32) Pci.Bridge.IoLimit & 0xf0) << 8) | 0x0fff;
+          if (Value == BIT0) {
+            Base |= ((UINT32) Pci.Bridge.IoBaseUpper16 << 16);
+            Limit |= ((UINT32) Pci.Bridge.IoLimitUpper16 << 16);
+          }
+          if ((Base > 0) && (Base < Limit)) {
+            if (Io.Base > Base) {
+              Io.Base = Base;
+            }
+            if (Io.Limit < Limit) {
+              Io.Limit = Limit;
+            }
+          }
+
+          //
+          // Get the Memory range that the PPB is decoding
+          //
+          Base = ((UINT32) Pci.Bridge.MemoryBase & 0xfff0) << 16;
+          Limit = (((UINT32) Pci.Bridge.MemoryLimit & 0xfff0) << 16) | 0xfffff;
+          if ((Base > 0) && (Base < Limit)) {
+            if (Mem.Base > Base) {
+              Mem.Base = Base;
+            }
+            if (Mem.Limit < Limit) {
+              Mem.Limit = Limit;
+            }
+          }
+
+          //
+          // Get the Prefetchable Memory range that the PPB is decoding
+          //
+          Value = Pci.Bridge.PrefetchableMemoryBase & 0x0f;
+          Base = ((UINT32) Pci.Bridge.PrefetchableMemoryBase & 0xfff0) << 16;
+          Limit = (((UINT32) Pci.Bridge.PrefetchableMemoryLimit & 0xfff0)
+                   << 16) | 0xfffff;
+          MemAperture = &PMem;
+          if (Value == BIT0) {
+            Base |= LShiftU64 (Pci.Bridge.PrefetchableBaseUpper32, 32);
+            Limit |= LShiftU64 (Pci.Bridge.PrefetchableLimitUpper32, 32);
+            MemAperture = &PMemAbove4G;
+          }
+          if ((Base > 0) && (Base < Limit)) {
+            if (MemAperture->Base > Base) {
+              MemAperture->Base = Base;
+            }
+            if (MemAperture->Limit < Limit) {
+              MemAperture->Limit = Limit;
+            }
+          }
+
+          //
+          // Look at the PPB Configuration for legacy decoding attributes
+          //
+          if ((Pci.Bridge.BridgeControl & EFI_PCI_BRIDGE_CONTROL_ISA)
+              == EFI_PCI_BRIDGE_CONTROL_ISA) {
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO_16;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_MOTHERBOARD_IO;
+          }
+          if ((Pci.Bridge.BridgeControl & EFI_PCI_BRIDGE_CONTROL_VGA)
+              == EFI_PCI_BRIDGE_CONTROL_VGA) {
+            Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_VGA_MEMORY;
+            Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO;
+            if ((Pci.Bridge.BridgeControl & EFI_PCI_BRIDGE_CONTROL_VGA_16)
+                != 0) {
+              Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO_16;
+              Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO_16;
+            }
+          }
+
+          BarOffsetEnd = OFFSET_OF (PCI_TYPE01, Bridge.Bar[2]);
+        } else {
+          //
+          // Parse the BARs of the PCI device to get what I/O Ranges, Memory
+          // Ranges, and Prefetchable Memory Ranges the device is decoding
+          //
+          if ((Pci.Hdr.HeaderType & HEADER_LAYOUT_CODE) == HEADER_TYPE_DEVICE) {
+            BarOffsetEnd = OFFSET_OF (PCI_TYPE00, Device.Bar[6]);
+          }
+        }
+
+        PcatPciRootBridgeParseBars (
+          Pci.Hdr.Command,
+          PrimaryBus,
+          Device,
+          Function,
+          OFFSET_OF (PCI_TYPE00, Device.Bar),
+          BarOffsetEnd,
+          &Io,
+          &Mem, &MemAbove4G,
+          &PMem, &PMemAbove4G
+        );
+
+        //
+        // See if the PCI device is an IDE controller
+        //
+        if (IS_CLASS2 (&Pci, PCI_CLASS_MASS_STORAGE,
+                       PCI_CLASS_MASS_STORAGE_IDE)) {
+          if (Pci.Hdr.ClassCode[0] & 0x80) {
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_PRIMARY_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_SECONDARY_IO;
+          }
+          if (Pci.Hdr.ClassCode[0] & 0x01) {
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_PRIMARY_IO;
+          }
+          if (Pci.Hdr.ClassCode[0] & 0x04) {
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_SECONDARY_IO;
+          }
+        }
+
+        //
+        // See if the PCI device is a legacy VGA controller or
+        // a standard VGA controller
+        //
+        if (IS_CLASS2 (&Pci, PCI_CLASS_OLD, PCI_CLASS_OLD_VGA) ||
+            IS_CLASS2 (&Pci, PCI_CLASS_DISPLAY, PCI_CLASS_DISPLAY_VGA)
+           ) {
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO_16;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_MEMORY;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO_16;
+        }
+
+        //
+        // See if the PCI Device is a PCI - ISA or PCI - EISA
+        // or ISA_POSITIVE_DECODE Bridge device
+        //
+        if (Pci.Hdr.ClassCode[2] == PCI_CLASS_BRIDGE) {
+          if (Pci.Hdr.ClassCode[1] == PCI_CLASS_BRIDGE_ISA ||
+              Pci.Hdr.ClassCode[1] == PCI_CLASS_BRIDGE_EISA ||
+              Pci.Hdr.ClassCode[1] == PCI_CLASS_BRIDGE_ISA_PDECODE) {
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO_16;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_MOTHERBOARD_IO;
+          }
+        }
+
+        //
+        // If this device is not a multi function device, then skip the rest
+        // of this PCI device
+        //
+        if (Function == 0 && !IS_PCI_MULTI_FUNC (&Pci)) {
+          break;
+        }
+      }
+    }
+
+    //
+    // If at least one PCI device was found on the primary bus of this PCI
+    // root bridge, then the PCI root bridge exists.
+    //
+    if (NumberOfDevices > 0) {
+      RootBridges = ReallocatePool (
+                      (*NumberOfRootBridges) * sizeof (PCI_ROOT_BRIDGE),
+                      (*NumberOfRootBridges + 1) * sizeof (PCI_ROOT_BRIDGE),
+                      RootBridges
+                    );
+      ASSERT (RootBridges != NULL);
+
+      AdjustRootBridgeResource (&Io, &Mem, &MemAbove4G, &PMem, &PMemAbove4G);
+
+      InitRootBridge (
+        Attributes, Attributes, 0,
+        (UINT8) PrimaryBus, (UINT8) SubBus,
+        &Io, &Mem, &MemAbove4G, &PMem, &PMemAbove4G,
+        &RootBridges[*NumberOfRootBridges]
+      );
+      RootBridges[*NumberOfRootBridges].ResourceAssigned = TRUE;
+      //
+      // Increment the index for the next PCI Root Bridge
+      //
+      (*NumberOfRootBridges)++;
+    }
+  }
+
+  return RootBridges;
+}
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c
new file mode 100644
index 0000000000..c5c6af0abc
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c
@@ -0,0 +1,265 @@
+/** @file
+  This file include all platform action which can be customized
+  by IBV/OEM.
+
+Copyright (c) 2015 - 2018, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "PlatformBootManager.h"
+#include "PlatformConsole.h"
+
+VOID
+InstallReadyToLock (
+  VOID
+  )
+{
+  EFI_STATUS                            Status;
+  EFI_HANDLE                            Handle;
+  EFI_SMM_ACCESS2_PROTOCOL              *SmmAccess;
+
+  DEBUG((DEBUG_INFO,"InstallReadyToLock  entering......\n"));
+  //
+  // Inform the SMM infrastructure that we're entering BDS and may run 3rd party code hereafter
+  // Since PI1.2.1, we need signal EndOfDxe as ExitPmAuth
+  //
+  EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid);
+  DEBUG((DEBUG_INFO,"All EndOfDxe callbacks have returned successfully\n"));
+
+  //
+  // Install DxeSmmReadyToLock protocol in order to lock SMM
+  //
+  Status = gBS->LocateProtocol (&gEfiSmmAccess2ProtocolGuid, NULL, (VOID **) &SmmAccess);
+  if (!EFI_ERROR (Status)) {
+    Handle = NULL;
+    Status = gBS->InstallProtocolInterface (
+                    &Handle,
+                    &gEfiDxeSmmReadyToLockProtocolGuid,
+                    EFI_NATIVE_INTERFACE,
+                    NULL
+                    );
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  DEBUG((DEBUG_INFO,"InstallReadyToLock  end\n"));
+  return;
+}
+
+/**
+  Return the index of the load option in the load option array.
+
+  The function consider two load options are equal when the
+  OptionType, Attributes, Description, FilePath and OptionalData are equal.
+
+  @param Key    Pointer to the load option to be found.
+  @param Array  Pointer to the array of load options to be found.
+  @param Count  Number of entries in the Array.
+
+  @retval -1          Key wasn't found in the Array.
+  @retval 0 ~ Count-1 The index of the Key in the Array.
+**/
+INTN
+PlatformFindLoadOption (
+  IN CONST EFI_BOOT_MANAGER_LOAD_OPTION *Key,
+  IN CONST EFI_BOOT_MANAGER_LOAD_OPTION *Array,
+  IN UINTN                              Count
+)
+{
+  UINTN                             Index;
+
+  for (Index = 0; Index < Count; Index++) {
+    if ((Key->OptionType == Array[Index].OptionType) &&
+        (Key->Attributes == Array[Index].Attributes) &&
+        (StrCmp (Key->Description, Array[Index].Description) == 0) &&
+        (CompareMem (Key->FilePath, Array[Index].FilePath, GetDevicePathSize (Key->FilePath)) == 0) &&
+        (Key->OptionalDataSize == Array[Index].OptionalDataSize) &&
+        (CompareMem (Key->OptionalData, Array[Index].OptionalData, Key->OptionalDataSize) == 0)) {
+      return (INTN) Index;
+    }
+  }
+
+  return -1;
+}
+
+/**
+  Register a boot option using a file GUID in the FV.
+
+  @param FileGuid     The file GUID name in FV.
+  @param Description  The boot option description.
+  @param Attributes   The attributes used for the boot option loading.
+**/
+VOID
+PlatformRegisterFvBootOption (
+  EFI_GUID                         *FileGuid,
+  CHAR16                           *Description,
+  UINT32                           Attributes
+)
+{
+  EFI_STATUS                        Status;
+  UINTN                             OptionIndex;
+  EFI_BOOT_MANAGER_LOAD_OPTION      NewOption;
+  EFI_BOOT_MANAGER_LOAD_OPTION      *BootOptions;
+  UINTN                             BootOptionCount;
+  MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileNode;
+  EFI_LOADED_IMAGE_PROTOCOL         *LoadedImage;
+  EFI_DEVICE_PATH_PROTOCOL          *DevicePath;
+
+  Status = gBS->HandleProtocol (gImageHandle, &gEfiLoadedImageProtocolGuid, (VOID **) &LoadedImage);
+  ASSERT_EFI_ERROR (Status);
+
+  EfiInitializeFwVolDevicepathNode (&FileNode, FileGuid);
+  DevicePath = AppendDevicePathNode (
+                 DevicePathFromHandle (LoadedImage->DeviceHandle),
+                 (EFI_DEVICE_PATH_PROTOCOL *) &FileNode
+               );
+
+  Status = EfiBootManagerInitializeLoadOption (
+             &NewOption,
+             LoadOptionNumberUnassigned,
+             LoadOptionTypeBoot,
+             Attributes,
+             Description,
+             DevicePath,
+             NULL,
+             0
+           );
+  if (!EFI_ERROR (Status)) {
+    BootOptions = EfiBootManagerGetLoadOptions (&BootOptionCount, LoadOptionTypeBoot);
+
+    OptionIndex = PlatformFindLoadOption (&NewOption, BootOptions, BootOptionCount);
+
+    if (OptionIndex == -1) {
+      Status = EfiBootManagerAddLoadOptionVariable (&NewOption, (UINTN) -1);
+      ASSERT_EFI_ERROR (Status);
+    }
+    EfiBootManagerFreeLoadOption (&NewOption);
+    EfiBootManagerFreeLoadOptions (BootOptions, BootOptionCount);
+  }
+}
+
+/**
+  Do the platform specific action before the console is connected.
+
+  Such as:
+    Update console variable;
+    Register new Driver#### or Boot####;
+    Signal ReadyToLock event.
+**/
+VOID
+EFIAPI
+PlatformBootManagerBeforeConsole (
+  VOID
+)
+{
+  EFI_INPUT_KEY                Enter;
+  EFI_INPUT_KEY                F2;
+  EFI_INPUT_KEY                Down;
+  EFI_BOOT_MANAGER_LOAD_OPTION BootOption;
+
+  PlatformConsoleInit ();
+
+  //
+  // Register ENTER as CONTINUE key
+  //
+  Enter.ScanCode    = SCAN_NULL;
+  Enter.UnicodeChar = CHAR_CARRIAGE_RETURN;
+  EfiBootManagerRegisterContinueKeyOption (0, &Enter, NULL);
+
+  //
+  // Map F2 to Boot Manager Menu
+  //
+  F2.ScanCode    = SCAN_F2;
+  F2.UnicodeChar = CHAR_NULL;
+  EfiBootManagerGetBootManagerMenu (&BootOption);
+  EfiBootManagerAddKeyOptionVariable (NULL, (UINT16) BootOption.OptionNumber, 0, &F2, NULL);
+
+  //
+  // Also add Down key to Boot Manager Menu since some serial terminals don't support F2 key.
+  //
+  Down.ScanCode    = SCAN_DOWN;
+  Down.UnicodeChar = CHAR_NULL;
+  EfiBootManagerGetBootManagerMenu (&BootOption);
+  EfiBootManagerAddKeyOptionVariable (NULL, (UINT16) BootOption.OptionNumber, 0, &Down, NULL);
+
+  //
+  // Install ready to lock.
+  // This needs to be done before option rom dispatched.
+  //
+  InstallReadyToLock ();
+
+  //
+  // Dispatch deferred images after EndOfDxe event and ReadyToLock installation.
+  //
+  EfiBootManagerDispatchDeferredImages ();
+}
+
+/**
+  Do the platform specific action after the console is connected.
+
+  Such as:
+    Dynamically switch output mode;
+    Signal console ready platform customized event;
+    Run diagnostics like memory testing;
+    Connect certain devices;
+    Dispatch additional option roms.
+**/
+VOID
+EFIAPI
+PlatformBootManagerAfterConsole (
+  VOID
+)
+{
+  EFI_GRAPHICS_OUTPUT_BLT_PIXEL  Black;
+  EFI_GRAPHICS_OUTPUT_BLT_PIXEL  White;
+
+  Black.Blue = Black.Green = Black.Red = Black.Reserved = 0;
+  White.Blue = White.Green = White.Red = White.Reserved = 0xFF;
+
+  EfiBootManagerConnectAll ();
+  EfiBootManagerRefreshAllBootOption ();
+
+  //
+  // Register UEFI Shell
+  //
+  PlatformRegisterFvBootOption (PcdGetPtr (PcdShellFile), L"UEFI Shell", LOAD_OPTION_ACTIVE);
+
+  Print (
+    L"\n"
+    L"F2 or Down      to enter Boot Manager Menu.\n"
+    L"ENTER           to boot directly.\n"
+    L"\n"
+  );
+
+}
+
+/**
+  This function is called each second during the boot manager waits the timeout.
+
+  @param TimeoutRemain  The remaining timeout.
+**/
+VOID
+EFIAPI
+PlatformBootManagerWaitCallback (
+  UINT16          TimeoutRemain
+)
+{
+  return;
+}
+
+/**
+  The function is called when no boot option could be launched,
+  including platform recovery options and options pointing to applications
+  built into firmware volumes.
+
+  If this function returns, BDS attempts to enter an infinite loop.
+**/
+VOID
+EFIAPI
+PlatformBootManagerUnableToBoot (
+  VOID
+  )
+{
+  return;
+}
+
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h
new file mode 100644
index 0000000000..2f600c796f
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h
@@ -0,0 +1,132 @@
+/**@file
+   Head file for BDS Platform specific code
+
+Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PLATFORM_BOOT_MANAGER_H
+#define _PLATFORM_BOOT_MANAGER_H
+
+#include <PiDxe.h>
+#include <Protocol/LoadedImage.h>
+
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/UefiRuntimeServicesTableLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/BaseLib.h>
+#include <Library/UefiRuntimeServicesTableLib.h>
+#include <Library/UefiLib.h>
+#include <Library/UefiBootManagerLib.h>
+#include <Library/PcdLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/HiiLib.h>
+#include <Library/PrintLib.h>
+#include <Library/DxeServicesLib.h>
+#include <Library/BootLogoLib.h>
+#include <Protocol/SmmAccess2.h>
+
+typedef struct {
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+  UINTN                     ConnectType;
+} PLATFORM_CONSOLE_CONNECT_ENTRY;
+
+extern PLATFORM_CONSOLE_CONNECT_ENTRY  gPlatformConsole[];
+
+#define gEndEntire \
+  { \
+    END_DEVICE_PATH_TYPE,\
+    END_ENTIRE_DEVICE_PATH_SUBTYPE,\
+    { END_DEVICE_PATH_LENGTH, 0 },\
+  }
+
+#define CONSOLE_OUT BIT0
+#define CONSOLE_IN  BIT1
+#define STD_ERROR   BIT2
+
+#define CLASS_HID           3
+#define SUBCLASS_BOOT       1
+#define PROTOCOL_KEYBOARD   1
+
+typedef struct {
+  USB_CLASS_DEVICE_PATH           UsbClass;
+  EFI_DEVICE_PATH_PROTOCOL        End;
+} USB_CLASS_FORMAT_DEVICE_PATH;
+
+typedef struct {
+  VENDOR_DEVICE_PATH  VendorDevicePath;
+  UINT32              Instance;
+} WIN_NT_VENDOR_DEVICE_PATH_NODE;
+
+//
+// Below is the platform console device path
+//
+typedef struct {
+  VENDOR_DEVICE_PATH              NtBus;
+  WIN_NT_VENDOR_DEVICE_PATH_NODE  SerialDevice;
+  UART_DEVICE_PATH                Uart;
+  VENDOR_DEVICE_PATH              TerminalType;
+  EFI_DEVICE_PATH_PROTOCOL        End;
+} NT_ISA_SERIAL_DEVICE_PATH;
+
+typedef struct {
+  VENDOR_DEVICE_PATH              NtBus;
+  WIN_NT_VENDOR_DEVICE_PATH_NODE  NtGopDevice;
+  EFI_DEVICE_PATH_PROTOCOL        End;
+} NT_PLATFORM_GOP_DEVICE_PATH;
+
+extern USB_CLASS_FORMAT_DEVICE_PATH              gUsbClassKeyboardDevicePath;
+
+/**
+  Use SystemTable Conout to stop video based Simple Text Out consoles from going
+  to the video device. Put up LogoFile on every video device that is a console.
+
+  @param[in]  LogoFile   File name of logo to display on the center of the screen.
+
+  @retval EFI_SUCCESS     ConsoleControl has been flipped to graphics and logo displayed.
+  @retval EFI_UNSUPPORTED Logo not found
+
+**/
+EFI_STATUS
+PlatformBootManagerEnableQuietBoot (
+  IN  EFI_GUID  *LogoFile
+);
+
+/**
+  Use SystemTable Conout to turn on video based Simple Text Out consoles. The
+  Simple Text Out screens will now be synced up with all non video output devices
+
+  @retval EFI_SUCCESS     UGA devices are back in text mode and synced up.
+
+**/
+EFI_STATUS
+PlatformBootManagerDisableQuietBoot (
+  VOID
+);
+
+/**
+  Show progress bar with title above it. It only works in Graphics mode.
+
+  @param TitleForeground Foreground color for Title.
+  @param TitleBackground Background color for Title.
+  @param Title           Title above progress bar.
+  @param ProgressColor   Progress bar color.
+  @param Progress        Progress (0-100)
+  @param PreviousValue   The previous value of the progress.
+
+  @retval  EFI_STATUS       Success update the progress bar
+
+**/
+EFI_STATUS
+PlatformBootManagerShowProgress (
+  IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL TitleForeground,
+  IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL TitleBackground,
+  IN CHAR16                        *Title,
+  IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL ProgressColor,
+  IN UINTN                         Progress,
+  IN UINTN                         PreviousValue
+);
+
+#endif // _PLATFORM_BOOT_MANAGER_H
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
new file mode 100644
index 0000000000..1f5a0bcad0
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
@@ -0,0 +1,71 @@
+## @file
+#  Include all platform action which can be customized by IBV/OEM.
+#
+#  Copyright (c) 2012 - 2016, Intel Corporation. All rights reserved.<BR>
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PlatformBootManagerLib
+  FILE_GUID                      = F0D9063A-DADB-4185-85E2-D7ACDA93F7A6
+  MODULE_TYPE                    = DXE_DRIVER
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PlatformBootManagerLib|DXE_DRIVER
+
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  PlatformData.c
+  PlatformConsole.c
+  PlatformConsole.h
+  PlatformBootManager.c
+  PlatformBootManager.h
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  UefiBootServicesTableLib
+  UefiRuntimeServicesTableLib
+  UefiLib
+  UefiBootManagerLib
+  PcdLib
+  DxeServicesLib
+  MemoryAllocationLib
+  DevicePathLib
+  HiiLib
+  PrintLib
+  PlatformHookLib
+
+[Guids]
+  gEfiEndOfDxeEventGroupGuid
+
+[Protocols]
+  gEfiGenericMemTestProtocolGuid  ## CONSUMES
+  gEfiGraphicsOutputProtocolGuid  ## CONSUMES
+  gEfiUgaDrawProtocolGuid         ## CONSUMES
+  gEfiBootLogoProtocolGuid        ## CONSUMES
+  gEfiDxeSmmReadyToLockProtocolGuid
+  gEfiSmmAccess2ProtocolGuid
+
+[Pcd]
+  gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut
+  gEfiMdePkgTokenSpaceGuid.PcdUgaConsumeSupport
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConInConnectOnDemand
+  gUefiPayloadPkgTokenSpaceGuid.PcdShellFile
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultDataBits
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultParity
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultStopBits
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c
new file mode 100644
index 0000000000..80a11d7451
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c
@@ -0,0 +1,599 @@
+/** @file
+This file include all platform action which can be customized by IBV/OEM.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include "PlatformBootManager.h"
+#include "PlatformConsole.h"
+
+#define PCI_DEVICE_PATH_NODE(Func, Dev) \
+  { \
+    { \
+      HARDWARE_DEVICE_PATH, \
+      HW_PCI_DP, \
+      { \
+        (UINT8) (sizeof (PCI_DEVICE_PATH)), \
+        (UINT8) ((sizeof (PCI_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    (Func), \
+    (Dev) \
+  }
+
+#define PNPID_DEVICE_PATH_NODE(PnpId) \
+  { \
+    { \
+      ACPI_DEVICE_PATH, \
+      ACPI_DP, \
+      { \
+        (UINT8) (sizeof (ACPI_HID_DEVICE_PATH)), \
+        (UINT8) ((sizeof (ACPI_HID_DEVICE_PATH)) >> 8) \
+      }, \
+    }, \
+    EISA_PNP_ID((PnpId)), \
+    0 \
+  }
+
+#define gPciRootBridge \
+  PNPID_DEVICE_PATH_NODE(0x0A03)
+
+#define gPnp16550ComPort \
+  PNPID_DEVICE_PATH_NODE(0x0501)
+
+#define gUartVendor \
+  { \
+    { \
+      HARDWARE_DEVICE_PATH, \
+      HW_VENDOR_DP, \
+      { \
+        (UINT8) (sizeof (VENDOR_DEVICE_PATH)), \
+        (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    {0xD3987D4B, 0x971A, 0x435F, {0x8C, 0xAF, 0x49, 0x67, 0xEB, 0x62, 0x72, 0x41}} \
+  }
+
+#define gUart \
+  { \
+    { \
+      MESSAGING_DEVICE_PATH, \
+      MSG_UART_DP, \
+      { \
+        (UINT8) (sizeof (UART_DEVICE_PATH)), \
+        (UINT8) ((sizeof (UART_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    0, \
+    115200, \
+    8, \
+    1, \
+    1 \
+  }
+
+#define gPcAnsiTerminal \
+  { \
+    { \
+      MESSAGING_DEVICE_PATH, \
+      MSG_VENDOR_DP, \
+      { \
+        (UINT8) (sizeof (VENDOR_DEVICE_PATH)), \
+        (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    DEVICE_PATH_MESSAGING_PC_ANSI \
+  }
+
+
+ACPI_HID_DEVICE_PATH       gPnp16550ComPortDeviceNode = gPnp16550ComPort;
+UART_DEVICE_PATH           gUartDeviceNode            = gUart;
+VENDOR_DEVICE_PATH         gTerminalTypeDeviceNode    = gPcAnsiTerminal;
+VENDOR_DEVICE_PATH         gUartDeviceVendorNode      = gUartVendor;
+
+//
+// Predefined platform root bridge
+//
+PLATFORM_ROOT_BRIDGE_DEVICE_PATH  gPlatformRootBridge0 = {
+  gPciRootBridge,
+  gEndEntire
+};
+
+EFI_DEVICE_PATH_PROTOCOL          *gPlatformRootBridges[] = {
+  (EFI_DEVICE_PATH_PROTOCOL *) &gPlatformRootBridge0,
+  NULL
+};
+
+BOOLEAN       mDetectVgaOnly;
+
+/**
+  Add UART to ConOut, ConIn, ErrOut.
+
+  @param[in]   DeviceHandle - LPC device path.
+
+  @retval EFI_SUCCESS  - Serial console is added to ConOut, ConIn, and ErrOut.
+  @retval EFI_STATUS   - No serial console is added.
+**/
+EFI_STATUS
+PrepareLpcBridgeDevicePath (
+  IN EFI_HANDLE                DeviceHandle
+)
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+
+  DevicePath = NULL;
+  Status = gBS->HandleProtocol (
+             DeviceHandle,
+             &gEfiDevicePathProtocolGuid,
+             (VOID*)&DevicePath
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  //
+  // Register COM1
+  //
+  DevicePath = AppendDevicePathNode ((EFI_DEVICE_PATH_PROTOCOL *)NULL, (EFI_DEVICE_PATH_PROTOCOL *)&gUartDeviceVendorNode);
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gUartDeviceNode);
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gTerminalTypeDeviceNode);
+
+  EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ConIn, DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ErrOut, DevicePath, NULL);
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Return the GOP device path in the platform.
+
+  @param[in]   PciDevicePath - Device path for the PCI graphics device.
+  @param[out]  GopDevicePath - Return the device path with GOP installed.
+
+  @retval EFI_SUCCESS  - PCI VGA is added to ConOut.
+  @retval EFI_INVALID_PARAMETER   - The device path parameter is invalid.
+  @retval EFI_STATUS   - No GOP device found.
+**/
+EFI_STATUS
+GetGopDevicePath (
+  IN  EFI_DEVICE_PATH_PROTOCOL *PciDevicePath,
+  OUT EFI_DEVICE_PATH_PROTOCOL **GopDevicePath
+)
+{
+  UINTN                           Index;
+  EFI_STATUS                      Status;
+  EFI_HANDLE                      PciDeviceHandle;
+  EFI_DEVICE_PATH_PROTOCOL        *TempDevicePath;
+  EFI_DEVICE_PATH_PROTOCOL        *TempPciDevicePath;
+  UINTN                           GopHandleCount;
+  EFI_HANDLE                      *GopHandleBuffer;
+
+  if (PciDevicePath == NULL || GopDevicePath == NULL) {
+    return EFI_INVALID_PARAMETER;
+  }
+
+  //
+  // Initialize the GopDevicePath to be PciDevicePath
+  //
+  *GopDevicePath    = PciDevicePath;
+  TempPciDevicePath = PciDevicePath;
+
+  Status = gBS->LocateDevicePath (
+             &gEfiDevicePathProtocolGuid,
+             &TempPciDevicePath,
+             &PciDeviceHandle
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  gBS->ConnectController (PciDeviceHandle, NULL, NULL, FALSE);
+
+  Status = gBS->LocateHandleBuffer (
+             ByProtocol,
+             &gEfiGraphicsOutputProtocolGuid,
+             NULL,
+             &GopHandleCount,
+             &GopHandleBuffer
+           );
+  if (!EFI_ERROR (Status)) {
+    //
+    // Add all the child handles as possible Console Device
+    //
+    for (Index = 0; Index < GopHandleCount; Index++) {
+      Status = gBS->HandleProtocol (GopHandleBuffer[Index], &gEfiDevicePathProtocolGuid, (VOID*)&TempDevicePath);
+      if (EFI_ERROR (Status)) {
+        continue;
+      }
+      if (CompareMem (
+            PciDevicePath,
+            TempDevicePath,
+            GetDevicePathSize (PciDevicePath) - END_DEVICE_PATH_LENGTH
+          ) == 0) {
+        //
+        // In current implementation, we only enable one of the child handles
+        // as console device, i.e. sotre one of the child handle's device
+        // path to variable "ConOut"
+        // In future, we could select all child handles to be console device
+        //
+        *GopDevicePath = TempDevicePath;
+
+        //
+        // Delete the PCI device's path that added by GetPlugInPciVgaDevicePath()
+        // Add the integrity GOP device path.
+        //
+        EfiBootManagerUpdateConsoleVariable (ConOut, NULL, PciDevicePath);
+        EfiBootManagerUpdateConsoleVariable (ConOut, TempDevicePath, NULL);
+      }
+    }
+    gBS->FreePool (GopHandleBuffer);
+  }
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Add PCI VGA to ConOut, ConIn, ErrOut.
+
+  @param[in]  DeviceHandle - Handle of PciIo protocol.
+
+  @retval EFI_SUCCESS  - PCI VGA is added to ConOut.
+  @retval EFI_STATUS   - No PCI VGA device is added.
+
+**/
+EFI_STATUS
+PreparePciVgaDevicePath (
+  IN EFI_HANDLE                DeviceHandle
+)
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+  EFI_DEVICE_PATH_PROTOCOL  *GopDevicePath;
+
+  DevicePath = NULL;
+  Status = gBS->HandleProtocol (
+             DeviceHandle,
+             &gEfiDevicePathProtocolGuid,
+             (VOID*)&DevicePath
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  GetGopDevicePath (DevicePath, &GopDevicePath);
+  DevicePath = GopDevicePath;
+
+  EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Add PCI Serial to ConOut, ConIn, ErrOut.
+
+  @param[in]  DeviceHandle - Handle of PciIo protocol.
+
+  @retval EFI_SUCCESS  - PCI Serial is added to ConOut, ConIn, and ErrOut.
+  @retval EFI_STATUS   - No PCI Serial device is added.
+
+**/
+EFI_STATUS
+PreparePciSerialDevicePath (
+  IN EFI_HANDLE                DeviceHandle
+)
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+
+  DevicePath = NULL;
+  Status = gBS->HandleProtocol (
+             DeviceHandle,
+             &gEfiDevicePathProtocolGuid,
+             (VOID*)&DevicePath
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gUartDeviceNode);
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gTerminalTypeDeviceNode);
+
+  EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ConIn,  DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ErrOut, DevicePath, NULL);
+
+  return EFI_SUCCESS;
+}
+
+
+/**
+  For every PCI instance execute a callback function.
+
+  @param[in]  Id                 - The protocol GUID for callback
+  @param[in]  CallBackFunction   - The callback function
+  @param[in]  Context    - The context of the callback
+
+  @retval EFI_STATUS - Callback function failed.
+
+**/
+EFI_STATUS
+EFIAPI
+VisitAllInstancesOfProtocol (
+  IN EFI_GUID                    *Id,
+  IN PROTOCOL_INSTANCE_CALLBACK  CallBackFunction,
+  IN VOID                        *Context
+)
+{
+  EFI_STATUS                Status;
+  UINTN                     HandleCount;
+  EFI_HANDLE                *HandleBuffer;
+  UINTN                     Index;
+  VOID                      *Instance;
+
+  //
+  // Start to check all the PciIo to find all possible device
+  //
+  HandleCount = 0;
+  HandleBuffer = NULL;
+  Status = gBS->LocateHandleBuffer (
+             ByProtocol,
+             Id,
+             NULL,
+             &HandleCount,
+             &HandleBuffer
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  for (Index = 0; Index < HandleCount; Index++) {
+    Status = gBS->HandleProtocol (HandleBuffer[Index], Id, &Instance);
+    if (EFI_ERROR (Status)) {
+      continue;
+    }
+
+    Status = (*CallBackFunction) (
+               HandleBuffer[Index],
+               Instance,
+               Context
+             );
+  }
+
+  gBS->FreePool (HandleBuffer);
+
+  return EFI_SUCCESS;
+}
+
+
+/**
+  For every PCI instance execute a callback function.
+
+  @param[in]  Handle     - The PCI device handle
+  @param[in]  Instance   - The instance of the PciIo protocol
+  @param[in]  Context    - The context of the callback
+
+  @retval EFI_STATUS - Callback function failed.
+
+**/
+EFI_STATUS
+EFIAPI
+VisitingAPciInstance (
+  IN EFI_HANDLE  Handle,
+  IN VOID        *Instance,
+  IN VOID        *Context
+)
+{
+  EFI_STATUS                Status;
+  EFI_PCI_IO_PROTOCOL       *PciIo;
+  PCI_TYPE00                Pci;
+
+  PciIo = (EFI_PCI_IO_PROTOCOL*) Instance;
+
+  //
+  // Check for all PCI device
+  //
+  Status = PciIo->Pci.Read (
+             PciIo,
+             EfiPciIoWidthUint32,
+             0,
+             sizeof (Pci) / sizeof (UINT32),
+             &Pci
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  return (*(VISIT_PCI_INSTANCE_CALLBACK)(UINTN) Context) (
+           Handle,
+           PciIo,
+           &Pci
+         );
+
+}
+
+
+/**
+  For every PCI instance execute a callback function.
+
+  @param[in]  CallBackFunction - Callback function pointer
+
+  @retval EFI_STATUS - Callback function failed.
+
+**/
+EFI_STATUS
+EFIAPI
+VisitAllPciInstances (
+  IN VISIT_PCI_INSTANCE_CALLBACK CallBackFunction
+)
+{
+  return VisitAllInstancesOfProtocol (
+           &gEfiPciIoProtocolGuid,
+           VisitingAPciInstance,
+           (VOID*)(UINTN) CallBackFunction
+         );
+}
+
+
+/**
+  Do platform specific PCI Device check and add them to
+  ConOut, ConIn, ErrOut.
+
+  @param[in]  Handle - Handle of PCI device instance
+  @param[in]  PciIo - PCI IO protocol instance
+  @param[in]  Pci - PCI Header register block
+
+  @retval EFI_SUCCESS - PCI Device check and Console variable update successfully.
+  @retval EFI_STATUS - PCI Device check or Console variable update fail.
+
+**/
+EFI_STATUS
+EFIAPI
+DetectAndPreparePlatformPciDevicePath (
+  IN EFI_HANDLE           Handle,
+  IN EFI_PCI_IO_PROTOCOL  *PciIo,
+  IN PCI_TYPE00           *Pci
+)
+{
+  EFI_STATUS                Status;
+
+  Status = PciIo->Attributes (
+             PciIo,
+             EfiPciIoAttributeOperationEnable,
+             EFI_PCI_DEVICE_ENABLE,
+             NULL
+           );
+  ASSERT_EFI_ERROR (Status);
+
+  if (!mDetectVgaOnly) {
+    //
+    // Here we decide whether it is LPC Bridge
+    //
+    if ((IS_PCI_LPC (Pci)) ||
+        ((IS_PCI_ISA_PDECODE (Pci)) &&
+         (Pci->Hdr.VendorId == 0x8086)
+        )
+       ) {
+      //
+      // Add IsaKeyboard to ConIn,
+      // add IsaSerial to ConOut, ConIn, ErrOut
+      //
+      DEBUG ((DEBUG_INFO, "Found LPC Bridge device\n"));
+      PrepareLpcBridgeDevicePath (Handle);
+      return EFI_SUCCESS;
+    }
+    //
+    // Here we decide which Serial device to enable in PCI bus
+    //
+    if (IS_PCI_16550SERIAL (Pci)) {
+      //
+      // Add them to ConOut, ConIn, ErrOut.
+      //
+      DEBUG ((DEBUG_INFO, "Found PCI 16550 SERIAL device\n"));
+      PreparePciSerialDevicePath (Handle);
+      return EFI_SUCCESS;
+    }
+  }
+
+  //
+  // Here we decide which VGA device to enable in PCI bus
+  //
+  if (IS_PCI_VGA (Pci)) {
+    //
+    // Add them to ConOut.
+    //
+    DEBUG ((DEBUG_INFO, "Found PCI VGA device\n"));
+    PreparePciVgaDevicePath (Handle);
+    return EFI_SUCCESS;
+  }
+
+  return Status;
+}
+
+
+/**
+  Do platform specific PCI Device check and add them to ConOut, ConIn, ErrOut
+
+  @param[in]  DetectVgaOnly - Only detect VGA device if it's TRUE.
+
+  @retval EFI_SUCCESS - PCI Device check and Console variable update successfully.
+  @retval EFI_STATUS - PCI Device check or Console variable update fail.
+
+**/
+EFI_STATUS
+DetectAndPreparePlatformPciDevicePaths (
+  BOOLEAN DetectVgaOnly
+)
+{
+  mDetectVgaOnly = DetectVgaOnly;
+
+  EfiBootManagerUpdateConsoleVariable (
+    ConIn,
+    (EFI_DEVICE_PATH_PROTOCOL *) &gUsbClassKeyboardDevicePath,
+    NULL
+    );
+
+  return VisitAllPciInstances (DetectAndPreparePlatformPciDevicePath);
+}
+
+
+/**
+  The function will connect root bridge
+
+   @return EFI_SUCCESS      Connect RootBridge successfully.
+
+**/
+EFI_STATUS
+ConnectRootBridge (
+  VOID
+)
+{
+  EFI_STATUS                Status;
+  EFI_HANDLE                RootHandle;
+
+  //
+  // Make all the PCI_IO protocols on PCI Seg 0 show up
+  //
+  Status = gBS->LocateDevicePath (
+             &gEfiDevicePathProtocolGuid,
+             &gPlatformRootBridges[0],
+             &RootHandle
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = gBS->ConnectController (RootHandle, NULL, NULL, FALSE);
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Platform console init. Include the platform firmware vendor, revision
+  and so crc check.
+
+**/
+VOID
+EFIAPI
+PlatformConsoleInit (
+  VOID
+)
+{
+  gUartDeviceNode.BaudRate = PcdGet64 (PcdUartDefaultBaudRate);
+  gUartDeviceNode.DataBits = PcdGet8 (PcdUartDefaultDataBits);
+  gUartDeviceNode.Parity   = PcdGet8 (PcdUartDefaultParity);
+  gUartDeviceNode.StopBits = PcdGet8 (PcdUartDefaultStopBits);
+
+  ConnectRootBridge ();
+
+  //
+  // Do platform specific PCI Device check and add them to ConOut, ConIn, ErrOut
+  //
+  DetectAndPreparePlatformPciDevicePaths (FALSE);
+
+}
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h
new file mode 100644
index 0000000000..68bdf5e555
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h
@@ -0,0 +1,70 @@
+/** @file
+Head file for BDS Platform specific code
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef _PLATFORM_CONSOLE_H
+#define _PLATFORM_CONSOLE_H
+
+#include <PiDxe.h>
+#include <IndustryStandard/Pci.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/BaseLib.h>
+#include <Library/PcdLib.h>
+#include <Library/UefiLib.h>
+#include <Library/DevicePathLib.h>
+#include <Protocol/PciIo.h>
+
+#define IS_PCI_ISA_PDECODE(_p)        IS_CLASS3 (_p, PCI_CLASS_BRIDGE, PCI_CLASS_BRIDGE_ISA_PDECODE, 0)
+#define IS_PCI_16550SERIAL(_p)        IS_CLASS3 (_p, PCI_CLASS_SCC, PCI_SUBCLASS_SERIAL, PCI_IF_16550)
+
+//
+// Type definitions
+//
+
+//
+// Platform Root Bridge
+//
+typedef struct {
+  ACPI_HID_DEVICE_PATH      PciRootBridge;
+  EFI_DEVICE_PATH_PROTOCOL  End;
+} PLATFORM_ROOT_BRIDGE_DEVICE_PATH;
+
+typedef
+EFI_STATUS
+(EFIAPI *PROTOCOL_INSTANCE_CALLBACK)(
+  IN EFI_HANDLE            Handle,
+  IN VOID                 *Instance,
+  IN VOID                 *Context
+);
+
+/**
+  @param[in]  Handle - Handle of PCI device instance
+  @param[in]  PciIo - PCI IO protocol instance
+  @param[in]  Pci - PCI Header register block
+**/
+typedef
+EFI_STATUS
+(EFIAPI *VISIT_PCI_INSTANCE_CALLBACK)(
+  IN EFI_HANDLE           Handle,
+  IN EFI_PCI_IO_PROTOCOL  *PciIo,
+  IN PCI_TYPE00           *Pci
+);
+
+/**
+  Platform console init. Include the platform firmware vendor, revision
+  and so crc check.
+
+**/
+VOID
+EFIAPI
+PlatformConsoleInit (
+  VOID
+);
+
+#endif
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c
new file mode 100644
index 0000000000..d17e660e0f
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c
@@ -0,0 +1,39 @@
+/**@file
+  Defined the platform specific device path which will be filled to
+  ConIn/ConOut variables.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include "PlatformBootManager.h"
+
+///
+/// Predefined platform default console device path
+///
+GLOBAL_REMOVE_IF_UNREFERENCED PLATFORM_CONSOLE_CONNECT_ENTRY   gPlatformConsole[] = {
+  {
+    NULL,
+    0
+  }
+};
+
+
+GLOBAL_REMOVE_IF_UNREFERENCED USB_CLASS_FORMAT_DEVICE_PATH gUsbClassKeyboardDevicePath = {
+  {
+    {
+      MESSAGING_DEVICE_PATH,
+      MSG_USB_CLASS_DP,
+      {
+        (UINT8) (sizeof (USB_CLASS_DEVICE_PATH)),
+        (UINT8) ((sizeof (USB_CLASS_DEVICE_PATH)) >> 8)
+      }
+    },
+    0xffff,           // VendorId
+    0xffff,           // ProductId
+    CLASS_HID,        // DeviceClass
+    SUBCLASS_BOOT,    // DeviceSubClass
+    PROTOCOL_KEYBOARD // DeviceProtocol
+  },
+  gEndEntire
+};
diff --git a/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c
new file mode 100644
index 0000000000..72a17dc8a7
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c
@@ -0,0 +1,98 @@
+/** @file
+  Platform Hook Library instance for UART device.
+
+  Copyright (c) 2015, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Base.h>
+#include <Uefi/UefiBaseType.h>
+#include <Library/PciLib.h>
+#include <Library/PlatformHookLib.h>
+#include <Library/BlParseLib.h>
+#include <Library/PcdLib.h>
+
+typedef struct {
+  UINT16  VendorId;          ///< Vendor ID to match the PCI device.  The value 0xFFFF terminates the list of entries.
+  UINT16  DeviceId;          ///< Device ID to match the PCI device
+  UINT32  ClockRate;         ///< UART clock rate.  Set to 0 for default clock rate of 1843200 Hz
+  UINT64  Offset;            ///< The byte offset into to the BAR
+  UINT8   BarIndex;          ///< Which BAR to get the UART base address
+  UINT8   RegisterStride;    ///< UART register stride in bytes.  Set to 0 for default register stride of 1 byte.
+  UINT16  ReceiveFifoDepth;  ///< UART receive FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  UINT16  TransmitFifoDepth; ///< UART transmit FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  UINT8   Reserved[2];
+} PCI_SERIAL_PARAMETER;
+
+/**
+  Performs platform specific initialization required for the CPU to access
+  the hardware associated with a SerialPortLib instance.  This function does
+  not initialize the serial port hardware itself.  Instead, it initializes
+  hardware devices that are required for the CPU to access the serial port
+  hardware.  This function may be called more than once.
+
+  @retval RETURN_SUCCESS       The platform specific initialization succeeded.
+  @retval RETURN_DEVICE_ERROR  The platform specific initialization could not be completed.
+
+**/
+RETURN_STATUS
+EFIAPI
+PlatformHookSerialPortInitialize (
+  VOID
+  )
+{
+  RETURN_STATUS         Status;
+  UINT32                DeviceVendor;
+  PCI_SERIAL_PARAMETER  *SerialParam;
+  SERIAL_PORT_INFO      SerialPortInfo;
+
+  Status = ParseSerialInfo (&SerialPortInfo);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  if (SerialPortInfo.Type == PLD_SERIAL_TYPE_MEMORY_MAPPED) {
+    Status = PcdSetBoolS (PcdSerialUseMmio, TRUE);
+  } else { //IO
+    Status = PcdSetBoolS (PcdSerialUseMmio, FALSE);
+  }
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+  Status = PcdSet64S (PcdSerialRegisterBase, SerialPortInfo.BaseAddr);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet32S (PcdSerialRegisterStride, SerialPortInfo.RegWidth);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet32S (PcdSerialBaudRate, SerialPortInfo.Baud);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet64S (PcdUartDefaultBaudRate, SerialPortInfo.Baud);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet32S (PcdSerialClockRate, SerialPortInfo.InputHertz);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  if (SerialPortInfo.UartPciAddr >= 0x80000000) {
+    DeviceVendor = PciRead32 (SerialPortInfo.UartPciAddr & 0x0ffff000);
+    SerialParam  = PcdGetPtr(PcdPciSerialParameters);
+    SerialParam->VendorId  = (UINT16)DeviceVendor;
+    SerialParam->DeviceId  = DeviceVendor >> 16;
+    SerialParam->ClockRate = SerialPortInfo.InputHertz;
+    SerialParam->RegisterStride = (UINT8)SerialPortInfo.RegWidth;
+  }
+
+  return RETURN_SUCCESS;
+}
diff --git a/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
new file mode 100644
index 0000000000..2415d99c64
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
@@ -0,0 +1,39 @@
+## @file
+#  Platform Hook Library instance for UART device.
+#
+#  Copyright (c) 2015, Intel Corporation. All rights reserved.<BR>
+#
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PlatformHookLib
+  FILE_GUID                      = 40A2CBC6-CFB8-447b-A90E-198E88FD345E
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PlatformHookLib
+  CONSTRUCTOR                    = PlatformHookSerialPortInitialize
+
+[Sources]
+  PlatformHookLib.c
+
+[LibraryClasses]
+  BlParseLib
+  PcdLib
+  PciLib
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[Pcd]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio         ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase    ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate        ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride  ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate       ## PRODUCES
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate         ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciSerialParameters   ## PRODUCES
diff --git a/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c
new file mode 100644
index 0000000000..a1b129814e
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c
@@ -0,0 +1,29 @@
+/** @file
+  Include all platform specific features which can be customized by IBV/OEM.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Uefi.h>
+#include <Library/BaseLib.h>
+#include <Library/UefiLib.h>
+#include <Library/PlatformSupportLib.h>
+
+/**
+  Parse platform specific information from coreboot.
+
+  @retval RETURN_SUCCESS       The platform specific coreboot support succeeded.
+  @retval RETURN_DEVICE_ERROR  The platform specific coreboot support could not be completed.
+
+**/
+EFI_STATUS
+EFIAPI
+ParsePlatformInfo (
+  VOID
+  )
+{
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
new file mode 100644
index 0000000000..1f4a5a35f4
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
@@ -0,0 +1,28 @@
+## @file
+#  Include all platform specific features which can be customized by IBV/OEM.
+#
+#  Copyright (c) 2016 - 2019, Intel Corporation. All rights reserved.<BR>
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PlatformSupportLib
+  FILE_GUID                      = B42AA265-00CA-4d4b-AC14-DBD5268E1BC7
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PlatformSupportLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  PlatformSupportLibNull.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
diff --git a/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c
new file mode 100644
index 0000000000..3fe3c805af
--- /dev/null
+++ b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c
@@ -0,0 +1,171 @@
+/** @file
+  Reset System Library functions for bootloader
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <PiDxe.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+
+ACPI_BOARD_INFO    mAcpiBoardInfo;
+
+/**
+  The constructor function to initialize mAcpiBoardInfo.
+
+  @retval EFI_SUCCESS   The constructor always returns RETURN_SUCCESS.
+
+**/
+RETURN_STATUS
+EFIAPI
+ResetSystemLibConstructor (
+  VOID
+  )
+{
+  EFI_HOB_GUID_TYPE  *GuidHob;
+  ACPI_BOARD_INFO    *AcpiBoardInfoPtr;
+
+  //
+  // Find the acpi board information guid hob
+  //
+  GuidHob = GetFirstGuidHob (&gUefiAcpiBoardInfoGuid);
+  ASSERT (GuidHob != NULL);
+
+  AcpiBoardInfoPtr = (ACPI_BOARD_INFO *)GET_GUID_HOB_DATA (GuidHob);
+  CopyMem (&mAcpiBoardInfo, AcpiBoardInfoPtr, sizeof (ACPI_BOARD_INFO));
+
+  return EFI_SUCCESS;
+}
+
+
+VOID
+AcpiPmControl (
+  UINTN   SuspendType
+  )
+{
+  UINTN              PmCtrlReg;
+
+  ASSERT (SuspendType <= 7);
+
+  PmCtrlReg = (UINTN)mAcpiBoardInfo.PmCtrlRegBase;
+  IoAndThenOr16 (PmCtrlReg, (UINT16) ~0x3c00, (UINT16) (SuspendType << 10));
+  IoOr16 (PmCtrlReg, 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
+  )
+{
+  IoWrite8 ((UINTN)mAcpiBoardInfo.ResetRegAddress, mAcpiBoardInfo.ResetValue);
+  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
+  )
+{
+  IoWrite8 ((UINTN)mAcpiBoardInfo.ResetRegAddress, mAcpiBoardInfo.ResetValue);
+  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
+  )
+{
+  UINTN              PmCtrlReg;
+
+  //
+  // GPE0_EN should be disabled to avoid any GPI waking up the system from S5
+  //
+  IoWrite16 ((UINTN)mAcpiBoardInfo.PmGpeEnBase,  0);
+
+  //
+  // Clear Power Button Status
+  //
+  IoWrite16((UINTN) mAcpiBoardInfo.PmEvtBase, BIT8);
+
+  //
+  // Transform system into S5 sleep state
+  //
+  PmCtrlReg = (UINTN)mAcpiBoardInfo.PmCtrlRegBase;
+  IoAndThenOr16 (PmCtrlReg, (UINT16) ~0x3c00, (UINT16) (7 << 10));
+  IoOr16 (PmCtrlReg, BIT13);
+  CpuDeadLoop ();
+
+  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
+  )
+{
+  AcpiPmControl (5);
+  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
+  )
+{
+  ResetCold ();
+}
diff --git a/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
new file mode 100644
index 0000000000..e7341c341a
--- /dev/null
+++ b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
@@ -0,0 +1,40 @@
+## @file
+#  Library instance for ResetSystem library class for bootloader
+#
+#  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = ResetSystemLib
+  FILE_GUID                      = C5CD4EEE-527F-47df-9C92-B41414AF7479
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = ResetSystemLib
+
+  CONSTRUCTOR                    = ResetSystemLibConstructor
+#
+# 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
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  DebugLib
+  IoLib
+  HobLib
+  BaseMemoryLib
+
+[Guids]
+  gUefiAcpiBoardInfoGuid
+
diff --git a/UefiPayloadPkg/Library/SblParseLib/SblParseLib.c b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.c
new file mode 100644
index 0000000000..7214fd87d2
--- /dev/null
+++ b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.c
@@ -0,0 +1,223 @@
+/** @file
+  This library will parse the Slim Bootloader to get required information.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <PiDxe.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+#include <Library/BlParseLib.h>
+#include <IndustryStandard/Acpi.h>
+
+
+/**
+  This function retrieves the parameter base address from boot loader.
+
+  This function will get bootloader specific parameter address for UEFI payload.
+  e.g. HobList pointer for Slim Bootloader, and coreboot table header for Coreboot.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+EFIAPI
+GetParameterBase (
+  VOID
+  )
+{
+  EFI_HOB_HANDOFF_INFO_TABLE          *HandoffTable;
+
+  HandoffTable = (EFI_HOB_HANDOFF_INFO_TABLE *)(UINTN) GET_BOOTLOADER_PARAMETER ();
+  if ((HandoffTable->Header.HobType == EFI_HOB_TYPE_HANDOFF) &&
+    (HandoffTable->Header.HobLength == sizeof (EFI_HOB_HANDOFF_INFO_TABLE)) &&
+    (HandoffTable->Header.Reserved == 0)) {
+    return (VOID *)HandoffTable;
+  }
+
+  return NULL;
+}
+
+
+/**
+  This function retrieves a GUIDed HOB data from Slim Bootloader.
+
+  This function will search SBL HOB list to find the first GUIDed HOB that
+  its GUID matches Guid.
+
+  @param[in]  Guid        A pointer to HOB GUID to search.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+GetGuidHobDataFromSbl (
+  IN       EFI_GUID      *Guid
+  )
+{
+  UINT8                  *GuidHob;
+  CONST VOID             *HobList;
+
+  HobList = GetParameterBase ();
+  ASSERT (HobList != NULL);
+  GuidHob = GetNextGuidHob (Guid, HobList);
+  if (GuidHob != NULL) {
+    return GET_GUID_HOB_DATA (GuidHob);
+  }
+
+  return NULL;
+}
+
+/**
+  Acquire the memory map information.
+
+  @param  MemInfoCallback     The callback routine
+  @param  Params              Pointer to the callback routine parameter
+
+  @retval RETURN_SUCCESS     Successfully find out the memory information.
+  @retval RETURN_NOT_FOUND   Failed to find the memory information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseMemoryInfo (
+  IN  BL_MEM_INFO_CALLBACK       MemInfoCallback,
+  IN  VOID                       *Params
+  )
+{
+  MEMROY_MAP_INFO               *MemoryMapInfo;
+  UINTN                          Idx;
+
+  MemoryMapInfo = (MEMROY_MAP_INFO *) GetGuidHobDataFromSbl (&gLoaderMemoryMapInfoGuid);
+  if (MemoryMapInfo == NULL) {
+    ASSERT (FALSE);
+    return RETURN_NOT_FOUND;
+  }
+
+  for (Idx = 0; Idx < MemoryMapInfo->Count; Idx++) {
+    MemInfoCallback (&MemoryMapInfo->Entry[Idx], Params);
+  }
+
+  return RETURN_SUCCESS;
+}
+
+/**
+  Acquire acpi table and smbios table from slim bootloader
+
+  @param  SystemTableInfo           Pointer to the system table info
+
+  @retval RETURN_SUCCESS            Successfully find out the tables.
+  @retval RETURN_NOT_FOUND          Failed to find the tables.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSystemTable (
+  OUT SYSTEM_TABLE_INFO     *SystemTableInfo
+  )
+{
+  SYSTEM_TABLE_INFO         *TableInfo;
+
+  TableInfo = (SYSTEM_TABLE_INFO *)GetGuidHobDataFromSbl (&gUefiSystemTableInfoGuid);
+  if (TableInfo == NULL) {
+    ASSERT (FALSE);
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (SystemTableInfo, TableInfo, sizeof (SYSTEM_TABLE_INFO));
+
+  return RETURN_SUCCESS;
+}
+
+
+/**
+  Find the serial port information
+
+  @param  SERIAL_PORT_INFO   Pointer to serial port info structure
+
+  @retval RETURN_SUCCESS     Successfully find the serial port information.
+  @retval RETURN_NOT_FOUND   Failed to find the serial port information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSerialInfo (
+  OUT SERIAL_PORT_INFO     *SerialPortInfo
+  )
+{
+  SERIAL_PORT_INFO              *BlSerialInfo;
+
+  BlSerialInfo = (SERIAL_PORT_INFO *) GetGuidHobDataFromSbl (&gUefiSerialPortInfoGuid);
+  if (BlSerialInfo == NULL) {
+    ASSERT (FALSE);
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (SerialPortInfo, BlSerialInfo, sizeof (SERIAL_PORT_INFO));
+
+  return RETURN_SUCCESS;
+}
+
+
+/**
+  Find the video frame buffer information
+
+  @param  GfxInfo             Pointer to the EFI_PEI_GRAPHICS_INFO_HOB structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseGfxInfo (
+  OUT EFI_PEI_GRAPHICS_INFO_HOB       *GfxInfo
+  )
+{
+  EFI_PEI_GRAPHICS_INFO_HOB           *BlGfxInfo;
+
+  BlGfxInfo = (EFI_PEI_GRAPHICS_INFO_HOB *) GetGuidHobDataFromSbl (&gEfiGraphicsInfoHobGuid);
+  if (BlGfxInfo == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (GfxInfo, BlGfxInfo, sizeof (EFI_PEI_GRAPHICS_INFO_HOB));
+
+  return RETURN_SUCCESS;
+}
+
+/**
+  Find the video frame buffer device information
+
+  @param  GfxDeviceInfo      Pointer to the EFI_PEI_GRAPHICS_DEVICE_INFO_HOB structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseGfxDeviceInfo (
+  OUT EFI_PEI_GRAPHICS_DEVICE_INFO_HOB       *GfxDeviceInfo
+  )
+{
+  EFI_PEI_GRAPHICS_DEVICE_INFO_HOB           *BlGfxDeviceInfo;
+
+  BlGfxDeviceInfo = (EFI_PEI_GRAPHICS_DEVICE_INFO_HOB *) GetGuidHobDataFromSbl (&gEfiGraphicsDeviceInfoHobGuid);
+  if (BlGfxDeviceInfo == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (GfxDeviceInfo, BlGfxDeviceInfo, sizeof (EFI_PEI_GRAPHICS_DEVICE_INFO_HOB));
+
+  return RETURN_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
new file mode 100644
index 0000000000..9ce2864f9f
--- /dev/null
+++ b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
@@ -0,0 +1,46 @@
+## @file
+#  Slim Bootloader parse library.
+#
+#  Copyright (c) 2019, Intel Corporation. All rights reserved.<BR>
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = SblParseLib
+  FILE_GUID                      = DE6FB32C-52CF-4A17-A84C-B323653CB5E0
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = BlParseLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources]
+  SblParseLib.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  BaseMemoryLib
+  DebugLib
+  PcdLib
+  HobLib
+
+[Guids]
+  gUefiSystemTableInfoGuid
+  gUefiSerialPortInfoGuid
+  gLoaderMemoryMapInfoGuid
+  gEfiGraphicsInfoHobGuid
+  gEfiGraphicsDeviceInfoHobGuid
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop
diff --git a/UefiPayloadPkg/SecCore/FindPeiCore.c b/UefiPayloadPkg/SecCore/FindPeiCore.c
new file mode 100644
index 0000000000..f67d1afb96
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/FindPeiCore.c
@@ -0,0 +1,193 @@
+/** @file
+  Locate the entry point for the PEI Core
+
+Copyright (c) 2013, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <PiPei.h>
+#include <Library/BaseLib.h>
+#include <Library/PeCoffGetEntryPointLib.h>
+
+#include "SecMain.h"
+
+/**
+  Find core image base.
+
+  @param   BootFirmwareVolumePtr    Point to the boot firmware volume.
+  @param   SecCoreImageBase         The base address of the SEC core image.
+  @param   PeiCoreImageBase         The base address of the PEI core image.
+
+**/
+EFI_STATUS
+EFIAPI
+FindImageBase (
+  IN  EFI_FIRMWARE_VOLUME_HEADER       *BootFirmwareVolumePtr,
+  OUT EFI_PHYSICAL_ADDRESS             *SecCoreImageBase,
+  OUT EFI_PHYSICAL_ADDRESS             *PeiCoreImageBase
+  )
+{
+  EFI_PHYSICAL_ADDRESS        CurrentAddress;
+  EFI_PHYSICAL_ADDRESS        EndOfFirmwareVolume;
+  EFI_FFS_FILE_HEADER         *File;
+  UINT32                      Size;
+  EFI_PHYSICAL_ADDRESS        EndOfFile;
+  EFI_COMMON_SECTION_HEADER   *Section;
+  EFI_PHYSICAL_ADDRESS        EndOfSection;
+
+  *SecCoreImageBase = 0;
+  *PeiCoreImageBase = 0;
+
+  CurrentAddress = (EFI_PHYSICAL_ADDRESS)(UINTN) BootFirmwareVolumePtr;
+  EndOfFirmwareVolume = CurrentAddress + BootFirmwareVolumePtr->FvLength;
+
+  //
+  // Loop through the FFS files in the Boot Firmware Volume
+  //
+  for (EndOfFile = CurrentAddress + BootFirmwareVolumePtr->HeaderLength; ; ) {
+
+    CurrentAddress = (EndOfFile + 7) & 0xfffffffffffffff8ULL;
+    if (CurrentAddress > EndOfFirmwareVolume) {
+      return EFI_NOT_FOUND;
+    }
+
+    File = (EFI_FFS_FILE_HEADER*)(UINTN) CurrentAddress;
+    if (IS_FFS_FILE2 (File)) {
+      Size = FFS_FILE2_SIZE (File);
+      if (Size <= 0x00FFFFFF) {
+        return EFI_NOT_FOUND;
+      }
+    } else {
+      Size = FFS_FILE_SIZE (File);
+      if (Size < sizeof (EFI_FFS_FILE_HEADER)) {
+        return EFI_NOT_FOUND;
+      }
+    }
+
+    EndOfFile = CurrentAddress + Size;
+    if (EndOfFile > EndOfFirmwareVolume) {
+      return EFI_NOT_FOUND;
+    }
+
+    //
+    // Look for SEC Core / PEI Core files
+    //
+    if (File->Type != EFI_FV_FILETYPE_SECURITY_CORE &&
+        File->Type != EFI_FV_FILETYPE_PEI_CORE) {
+      continue;
+    }
+
+    //
+    // Loop through the FFS file sections within the FFS file
+    //
+    if (IS_FFS_FILE2 (File)) {
+      EndOfSection = (EFI_PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) File + sizeof (EFI_FFS_FILE_HEADER2));
+    } else {
+      EndOfSection = (EFI_PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) File + sizeof (EFI_FFS_FILE_HEADER));
+    }
+    for (;;) {
+      CurrentAddress = (EndOfSection + 3) & 0xfffffffffffffffcULL;
+      Section = (EFI_COMMON_SECTION_HEADER*)(UINTN) CurrentAddress;
+
+      if (IS_SECTION2 (Section)) {
+        Size = SECTION2_SIZE (Section);
+        if (Size <= 0x00FFFFFF) {
+          return EFI_NOT_FOUND;
+        }
+      } else {
+        Size = SECTION_SIZE (Section);
+        if (Size < sizeof (EFI_COMMON_SECTION_HEADER)) {
+          return EFI_NOT_FOUND;
+        }
+      }
+
+      EndOfSection = CurrentAddress + Size;
+      if (EndOfSection > EndOfFile) {
+        return EFI_NOT_FOUND;
+      }
+
+      //
+      // Look for executable sections
+      //
+      if (Section->Type == EFI_SECTION_PE32 || Section->Type == EFI_SECTION_TE) {
+        if (File->Type == EFI_FV_FILETYPE_SECURITY_CORE) {
+          if (IS_SECTION2 (Section)) {
+            *SecCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER2));
+          } else {
+            *SecCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER));
+          }
+        } else {
+          if (IS_SECTION2 (Section)) {
+            *PeiCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER2));
+          } else {
+            *PeiCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER));
+          }
+        }
+        break;
+      }
+    }
+
+    //
+    // Both SEC Core and PEI Core images found
+    //
+    if (*SecCoreImageBase != 0 && *PeiCoreImageBase != 0) {
+      return EFI_SUCCESS;
+    }
+  }
+}
+
+/**
+  Find and return Pei Core entry point.
+
+  It also find SEC and PEI Core file debug information. It will report them if
+  remote debug is enabled.
+
+  @param   BootFirmwareVolumePtr    Point to the boot firmware volume.
+  @param   PeiCoreEntryPoint        The entry point of the PEI core.
+
+**/
+VOID
+EFIAPI
+FindAndReportEntryPoints (
+  IN  EFI_FIRMWARE_VOLUME_HEADER       *BootFirmwareVolumePtr,
+  OUT EFI_PEI_CORE_ENTRY_POINT         *PeiCoreEntryPoint
+  )
+{
+  EFI_STATUS                       Status;
+  EFI_PHYSICAL_ADDRESS             SecCoreImageBase;
+  EFI_PHYSICAL_ADDRESS             PeiCoreImageBase;
+  PE_COFF_LOADER_IMAGE_CONTEXT     ImageContext;
+
+  //
+  // Find SEC Core and PEI Core image base
+  //
+  Status = FindImageBase (BootFirmwareVolumePtr, &SecCoreImageBase, &PeiCoreImageBase);
+  ASSERT_EFI_ERROR (Status);
+
+  ZeroMem ((VOID *) &ImageContext, sizeof (PE_COFF_LOADER_IMAGE_CONTEXT));
+  //
+  // Report SEC Core debug information when remote debug is enabled
+  //
+  ImageContext.ImageAddress = SecCoreImageBase;
+  ImageContext.PdbPointer = PeCoffLoaderGetPdbPointer ((VOID*) (UINTN) ImageContext.ImageAddress);
+  PeCoffLoaderRelocateImageExtraAction (&ImageContext);
+
+  //
+  // Report PEI Core debug information when remote debug is enabled
+  //
+  ImageContext.ImageAddress = PeiCoreImageBase;
+  ImageContext.PdbPointer = PeCoffLoaderGetPdbPointer ((VOID*) (UINTN) ImageContext.ImageAddress);
+  PeCoffLoaderRelocateImageExtraAction (&ImageContext);
+
+  //
+  // Find PEI Core entry point
+  //
+  Status = PeCoffLoaderGetEntryPoint ((VOID *) (UINTN) PeiCoreImageBase, (VOID**) PeiCoreEntryPoint);
+  if (EFI_ERROR (Status)) {
+    *PeiCoreEntryPoint = 0;
+  }
+
+  return;
+}
+
diff --git a/UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm b/UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm
new file mode 100644
index 0000000000..877fc61ef0
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm
@@ -0,0 +1,78 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Abstract:
+;
+;   Entry point for the coreboot UEFI payload.
+;
+;------------------------------------------------------------------------------
+
+SECTION .text
+
+; C Functions
+extern  ASM_PFX(SecStartup)
+
+; Pcds
+extern  ASM_PFX(PcdGet32 (PcdPayloadFdMemBase))
+extern  ASM_PFX(PcdGet32 (PcdPayloadStackTop))
+
+;
+; SecCore Entry Point
+;
+; Processor is in flat protected mode
+;
+; @param[in]  EAX   Initial value of the EAX register (BIST: Built-in Self Test)
+; @param[in]  DI    'BP': boot-strap processor, or 'AP': application processor
+; @param[in]  EBP   Pointer to the start of the Boot Firmware Volume
+;
+; @return     None  This routine does not return
+;
+global ASM_PFX(_ModuleEntryPoint)
+ASM_PFX(_ModuleEntryPoint):
+  ;
+  ; Disable all the interrupts
+  ;
+  cli
+
+  ;
+  ; Save the Payload HOB base address before switching the stack
+  ;
+  mov     eax, [esp + 4]
+
+  ;
+  ; Construct the temporary memory at 0x80000, length 0x10000
+  ;
+  mov     esp, DWORD [ASM_PFX(PcdGet32 (PcdPayloadStackTop))]
+
+  ;
+  ; Push the Payload HOB base address onto new stack
+  ;
+  push    eax
+
+  ;
+  ; Pass BFV into the PEI Core
+  ;
+  push    DWORD [ASM_PFX(PcdGet32 (PcdPayloadFdMemBase))]
+
+  ;
+  ; Pass stack base into the PEI Core
+  ;
+  push    BASE_512KB
+
+  ;
+  ; Pass stack size into the PEI Core
+  ;
+  push    SIZE_64KB
+
+  ;
+  ; Pass Control into the PEI Core
+  ;
+  call    ASM_PFX(SecStartup)
+
+  ;
+  ; Should never return
+  ;
+  jmp     $
+
diff --git a/UefiPayloadPkg/SecCore/Ia32/Stack.nasm b/UefiPayloadPkg/SecCore/Ia32/Stack.nasm
new file mode 100644
index 0000000000..55fd2243c8
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/Ia32/Stack.nasm
@@ -0,0 +1,72 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+; SPDX-License-Identifier: BSD-2-Clause-Patent
+;
+; Abstract:
+;
+;   Switch the stack from temporary memory to permanent memory.
+;
+;------------------------------------------------------------------------------
+
+SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; SecSwitchStack (
+;   UINT32   TemporaryMemoryBase,
+;   UINT32   PermenentMemoryBase
+;   );
+;------------------------------------------------------------------------------
+global ASM_PFX(SecSwitchStack)
+ASM_PFX(SecSwitchStack):
+    ;
+    ; Save three register: eax, ebx, ecx
+    ;
+    push  eax
+    push  ebx
+    push  ecx
+    push  edx
+
+    ;
+    ; !!CAUTION!! this function address's is pushed into stack after
+    ; migration of whole temporary memory, so need save it to permanent
+    ; memory at first!
+    ;
+
+    mov   ebx,  [esp + 20]          ; Save the first parameter
+    mov   ecx,  [esp + 24]          ; Save the second parameter
+
+    ;
+    ; Save this function's return address into permanent memory at first.
+    ; Then, Fixup the esp point to permanent memory
+    ;
+    mov   eax,  esp
+    sub   eax,  ebx
+    add   eax,  ecx
+    mov   edx,  [esp]               ; copy pushed register's value to permanent memory
+    mov   [eax], edx
+    mov   edx,  [esp + 4]
+    mov   [eax + 4], edx
+    mov   edx,  [esp + 8]
+    mov   [eax + 8], edx
+    mov   edx,  [esp + 12]
+    mov   [eax + 12], edx
+    mov   edx,  [esp + 16]          ; Update return address into permanent memory
+    mov   [eax + 16], edx
+    mov   esp,  eax                 ; From now, esp is pointed to permanent memory
+
+    ;
+    ; Fixup the ebp point to permanent memory
+    ;
+    mov   eax,  ebp
+    sub   eax,  ebx
+    add   eax,  ecx
+    mov   ebp,  eax                 ; From now, ebp is pointed to permanent memory
+
+    pop   edx
+    pop   ecx
+    pop   ebx
+    pop   eax
+    ret
diff --git a/UefiPayloadPkg/SecCore/SecCore.inf b/UefiPayloadPkg/SecCore/SecCore.inf
new file mode 100644
index 0000000000..82ca7f567f
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/SecCore.inf
@@ -0,0 +1,58 @@
+## @file
+# This is the first module taking control from the coreboot.
+#
+#  Copyright (c) 2013 - 2019, Intel Corporation. All rights reserved.<BR>
+#
+#  SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = SecCore
+  FILE_GUID                      = BA7BE337-6CFB-4dbb-B26C-21EC2FC16073
+  MODULE_TYPE                    = SEC
+  VERSION_STRING                 = 1.0
+
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  SecMain.c
+  SecMain.h
+  FindPeiCore.c
+
+[Sources.IA32]
+  Ia32/Stack.nasm
+  Ia32/SecEntry.nasm
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiCpuPkg/UefiCpuPkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseMemoryLib
+  DebugLib
+  BaseLib
+  PcdLib
+  DebugAgentLib
+  UefiCpuLib
+  PeCoffGetEntryPointLib
+  PeCoffExtraActionLib
+
+[Ppis]
+  gEfiSecPlatformInformationPpiGuid             # PPI ALWAYS_PRODUCED
+  gEfiTemporaryRamSupportPpiGuid                # PPI ALWAYS_PRODUCED
+  gEfiPayLoadHobBasePpiGuid                     # PPI ALWAYS_PRODUCED
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop
diff --git a/UefiPayloadPkg/SecCore/SecMain.c b/UefiPayloadPkg/SecCore/SecMain.c
new file mode 100644
index 0000000000..c0ca0e7d40
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/SecMain.c
@@ -0,0 +1,288 @@
+/** @file
+  C functions in SEC
+
+Copyright (c) 2013, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+
+#include "SecMain.h"
+
+EFI_PEI_TEMPORARY_RAM_SUPPORT_PPI gSecTemporaryRamSupportPpi = {
+  SecTemporaryRamSupport
+};
+
+EFI_PEI_PPI_DESCRIPTOR            mPeiSecPlatformInformationPpi[] = {
+  {
+    (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
+    &gEfiTemporaryRamSupportPpiGuid,
+    &gSecTemporaryRamSupportPpi
+  }
+};
+
+//
+// These are IDT entries pointing to 10:FFFFFFE4h.
+//
+UINT64  mIdtEntryTemplate = 0xffff8e000010ffe4ULL;
+
+/**
+  Caller provided function to be invoked at the end of InitializeDebugAgent().
+
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+  @param[in] Context    The first input parameter of InitializeDebugAgent().
+
+**/
+VOID
+EFIAPI
+SecStartupPhase2(
+  IN VOID                     *Context
+  );
+
+
+/**
+
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+
+  @param SizeOfRam           Size of the temporary memory available for use.
+  @param TempRamBase         Base address of temporary ram
+  @param BootFirmwareVolume  Base address of the Boot Firmware Volume.
+  @param BootloaderParameter A parameter from bootloader, e.g. HobList from SlimBootloader
+
+**/
+VOID
+EFIAPI
+SecStartup (
+  IN UINT32                   SizeOfRam,
+  IN UINT32                   TempRamBase,
+  IN VOID                     *BootFirmwareVolume,
+  IN UINT32                   BootloaderParameter
+  )
+{
+  EFI_SEC_PEI_HAND_OFF        SecCoreData;
+  IA32_DESCRIPTOR             IdtDescriptor;
+  SEC_IDT_TABLE               IdtTableInStack;
+  UINT32                      Index;
+  UINT32                      PeiStackSize;
+
+  PeiStackSize = (SizeOfRam >> 1);
+
+  ASSERT (PeiStackSize < SizeOfRam);
+
+  //
+  // Process all libraries constructor function linked to SecCore.
+  //
+  ProcessLibraryConstructorList ();
+
+  //
+  // Initialize floating point operating environment
+  // to be compliant with UEFI spec.
+  //
+  InitializeFloatingPointUnits ();
+
+
+  // |-------------------|---->
+  // |Idt Table          |
+  // |-------------------|
+  // |PeiService Pointer |    PeiStackSize
+  // |-------------------|
+  // |                   |
+  // |      Stack        |
+  // |-------------------|---->
+  // |                   |
+  // |                   |
+  // |      Heap         |    PeiTemporaryRamSize
+  // |                   |
+  // |                   |
+  // |-------------------|---->  TempRamBase
+
+  IdtTableInStack.PeiService = 0;
+  for (Index = 0; Index < SEC_IDT_ENTRY_COUNT; Index ++) {
+    CopyMem ((VOID*)&IdtTableInStack.IdtTable[Index], (VOID*)&mIdtEntryTemplate, sizeof (UINT64));
+  }
+
+  IdtDescriptor.Base  = (UINTN) &IdtTableInStack.IdtTable;
+  IdtDescriptor.Limit = (UINT16)(sizeof (IdtTableInStack.IdtTable) - 1);
+
+  AsmWriteIdtr (&IdtDescriptor);
+
+  //
+  // Update the base address and length of Pei temporary memory
+  //
+  SecCoreData.DataSize               = (UINT16) sizeof (EFI_SEC_PEI_HAND_OFF);
+  SecCoreData.BootFirmwareVolumeBase = BootFirmwareVolume;
+  SecCoreData.BootFirmwareVolumeSize = (UINTN)(0x100000000ULL - (UINTN) BootFirmwareVolume);
+  SecCoreData.TemporaryRamBase       = (VOID*)(UINTN) TempRamBase;
+  SecCoreData.TemporaryRamSize       = SizeOfRam;
+  SecCoreData.PeiTemporaryRamBase    = SecCoreData.TemporaryRamBase;
+  SecCoreData.PeiTemporaryRamSize    = SizeOfRam - PeiStackSize;
+  SecCoreData.StackBase              = (VOID*)(UINTN)(TempRamBase + SecCoreData.PeiTemporaryRamSize);
+  SecCoreData.StackSize              = PeiStackSize;
+
+  //
+  // Initialize Debug Agent to support source level debug in SEC/PEI phases before memory ready.
+  //
+  InitializeDebugAgent (DEBUG_AGENT_INIT_PREMEM_SEC, &SecCoreData, SecStartupPhase2);
+
+}
+
+/**
+  Caller provided function to be invoked at the end of InitializeDebugAgent().
+
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+  @param[in] Context    The first input parameter of InitializeDebugAgent().
+
+**/
+VOID
+EFIAPI
+SecStartupPhase2(
+  IN VOID                     *Context
+  )
+{
+  EFI_SEC_PEI_HAND_OFF        *SecCoreData;
+  EFI_PEI_CORE_ENTRY_POINT    PeiCoreEntryPoint;
+
+  SecCoreData = (EFI_SEC_PEI_HAND_OFF *) Context;
+  //
+  // Find Pei Core entry point. It will report SEC and Pei Core debug information if remote debug
+  // is enabled.
+  //
+  FindAndReportEntryPoints ((EFI_FIRMWARE_VOLUME_HEADER *) SecCoreData->BootFirmwareVolumeBase, &PeiCoreEntryPoint);
+  if (PeiCoreEntryPoint == NULL)
+  {
+    CpuDeadLoop ();
+  }
+
+  //
+  // Transfer the control to the PEI core
+  //
+  ASSERT (PeiCoreEntryPoint != NULL);
+  (*PeiCoreEntryPoint) (SecCoreData, (EFI_PEI_PPI_DESCRIPTOR *)&mPeiSecPlatformInformationPpi);
+
+  //
+  // Should not come here.
+  //
+  return ;
+}
+
+/**
+  This service of the TEMPORARY_RAM_SUPPORT_PPI that migrates temporary RAM into
+  permanent memory.
+
+  @param PeiServices            Pointer to the PEI Services Table.
+  @param TemporaryMemoryBase    Source Address in temporary memory from which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param PermanentMemoryBase    Destination Address in permanent memory into which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param CopySize               Amount of memory to migrate from temporary to permanent memory.
+
+  @retval EFI_SUCCESS           The data was successfully returned.
+  @retval EFI_INVALID_PARAMETER PermanentMemoryBase + CopySize > TemporaryMemoryBase when
+                                TemporaryMemoryBase > PermanentMemoryBase.
+
+**/
+EFI_STATUS
+EFIAPI
+SecTemporaryRamSupport (
+  IN CONST EFI_PEI_SERVICES   **PeiServices,
+  IN EFI_PHYSICAL_ADDRESS     TemporaryMemoryBase,
+  IN EFI_PHYSICAL_ADDRESS     PermanentMemoryBase,
+  IN UINTN                    CopySize
+  )
+{
+  IA32_DESCRIPTOR   IdtDescriptor;
+  VOID*             OldHeap;
+  VOID*             NewHeap;
+  VOID*             OldStack;
+  VOID*             NewStack;
+  DEBUG_AGENT_CONTEXT_POSTMEM_SEC  DebugAgentContext;
+  BOOLEAN           OldStatus;
+  UINTN             PeiStackSize;
+
+  PeiStackSize = (CopySize >> 1);
+
+  ASSERT (PeiStackSize < CopySize);
+
+  //
+  // |-------------------|---->
+  // |      Stack        |    PeiStackSize
+  // |-------------------|---->
+  // |      Heap         |    PeiTemporaryRamSize
+  // |-------------------|---->  TempRamBase
+  //
+  // |-------------------|---->
+  // |      Heap         |    PeiTemporaryRamSize
+  // |-------------------|---->
+  // |      Stack        |    PeiStackSize
+  // |-------------------|---->  PermanentMemoryBase
+  //
+
+  OldHeap = (VOID*)(UINTN)TemporaryMemoryBase;
+  NewHeap = (VOID*)((UINTN)PermanentMemoryBase + PeiStackSize);
+
+  OldStack = (VOID*)((UINTN)TemporaryMemoryBase + CopySize - PeiStackSize);
+  NewStack = (VOID*)(UINTN)PermanentMemoryBase;
+
+  DebugAgentContext.HeapMigrateOffset = (UINTN)NewHeap - (UINTN)OldHeap;
+  DebugAgentContext.StackMigrateOffset = (UINTN)NewStack - (UINTN)OldStack;
+
+  OldStatus = SaveAndSetDebugTimerInterrupt (FALSE);
+  //
+  // Initialize Debug Agent to support source level debug in PEI phase after memory ready.
+  // It will build HOB and fix up the pointer in IDT table.
+  //
+  InitializeDebugAgent (DEBUG_AGENT_INIT_POSTMEM_SEC, (VOID *) &DebugAgentContext, NULL);
+
+  //
+  // Migrate Heap
+  //
+  CopyMem (NewHeap, OldHeap, CopySize - PeiStackSize);
+
+  //
+  // Migrate Stack
+  //
+  CopyMem (NewStack, OldStack, PeiStackSize);
+
+
+  //
+  // We need *not* fix the return address because currently,
+  // The PeiCore is executed in flash.
+  //
+
+  //
+  // Rebase IDT table in permanent memory
+  //
+  AsmReadIdtr (&IdtDescriptor);
+  IdtDescriptor.Base = IdtDescriptor.Base - (UINTN)OldStack + (UINTN)NewStack;
+
+  AsmWriteIdtr (&IdtDescriptor);
+
+
+  //
+  // Program MTRR
+  //
+
+  //
+  // SecSwitchStack function must be invoked after the memory migration
+  // immediately, also we need fixup the stack change caused by new call into
+  // permanent memory.
+  //
+  SecSwitchStack (
+    (UINT32) (UINTN) OldStack,
+    (UINT32) (UINTN) NewStack
+    );
+
+  SaveAndSetDebugTimerInterrupt (OldStatus);
+
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/SecCore/SecMain.h b/UefiPayloadPkg/SecCore/SecMain.h
new file mode 100644
index 0000000000..ca0a95d03e
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/SecMain.h
@@ -0,0 +1,131 @@
+/** @file
+  Master header file for SecCore.
+
+Copyright (c) 2013, Intel Corporation. All rights reserved.<BR>
+SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef _SEC_CORE_H_
+#define _SEC_CORE_H_
+
+
+#include <PiPei.h>
+
+#include <Ppi/SecPlatformInformation.h>
+#include <Ppi/TemporaryRamSupport.h>
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiCpuLib.h>
+#include <Library/PeCoffGetEntryPointLib.h>
+#include <Library/PeCoffExtraActionLib.h>
+#include <Library/DebugAgentLib.h>
+
+
+#define SEC_IDT_ENTRY_COUNT  34
+
+typedef struct _SEC_IDT_TABLE {
+  //
+  // Reserved 8 bytes preceding IDT to store EFI_PEI_SERVICES**, since IDT base
+  // address should be 8-byte alignment.
+  // Note: For IA32, only the 4 bytes immediately preceding IDT is used to store
+  // EFI_PEI_SERVICES**
+  //
+  UINT64            PeiService;
+  UINT64            IdtTable[SEC_IDT_ENTRY_COUNT];
+} SEC_IDT_TABLE;
+
+/**
+  Switch the stack in the temporary memory to the one in the permanent memory.
+
+  This function must be invoked after the memory migration immediately. The relative
+  position of the stack in the temporary and permanent memory is same.
+
+  @param TemporaryMemoryBase  Base address of the temporary memory.
+  @param PermenentMemoryBase  Base address of the permanent memory.
+**/
+VOID
+EFIAPI
+SecSwitchStack (
+  UINT32   TemporaryMemoryBase,
+  UINT32   PermenentMemoryBase
+  );
+
+/**
+  This service of the TEMPORARY_RAM_SUPPORT_PPI that migrates temporary RAM into
+  permanent memory.
+
+  @param PeiServices            Pointer to the PEI Services Table.
+  @param TemporaryMemoryBase    Source Address in temporary memory from which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param PermanentMemoryBase    Destination Address in permanent memory into which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param CopySize               Amount of memory to migrate from temporary to permanent memory.
+
+  @retval EFI_SUCCESS           The data was successfully returned.
+  @retval EFI_INVALID_PARAMETER PermanentMemoryBase + CopySize > TemporaryMemoryBase when
+                                TemporaryMemoryBase > PermanentMemoryBase.
+
+**/
+EFI_STATUS
+EFIAPI
+SecTemporaryRamSupport (
+  IN CONST EFI_PEI_SERVICES   **PeiServices,
+  IN EFI_PHYSICAL_ADDRESS     TemporaryMemoryBase,
+  IN EFI_PHYSICAL_ADDRESS     PermanentMemoryBase,
+  IN UINTN                    CopySize
+  );
+
+/**
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+  @param SizeOfRam           Size of the temporary memory available for use.
+  @param TempRamBase         Base address of temporary ram
+  @param BootFirmwareVolume  Base address of the Boot Firmware Volume.
+  @param BootloaderParameter A parameter from bootloader, e.g. HobList from SlimBootloader
+
+**/
+VOID
+EFIAPI
+SecStartup (
+  IN UINT32                   SizeOfRam,
+  IN UINT32                   TempRamBase,
+  IN VOID                     *BootFirmwareVolume,
+  IN UINT32                   BootloaderParameter
+  );
+
+/**
+  Find and return Pei Core entry point.
+
+  It also find SEC and PEI Core file debug information. It will report them if
+  remote debug is enabled.
+
+  @param  BootFirmwareVolumePtr  Point to the boot firmware volume.
+  @param  PeiCoreEntryPoint      Point to the PEI core entry point.
+
+**/
+VOID
+EFIAPI
+FindAndReportEntryPoints (
+  IN  EFI_FIRMWARE_VOLUME_HEADER       *BootFirmwareVolumePtr,
+  OUT EFI_PEI_CORE_ENTRY_POINT         *PeiCoreEntryPoint
+  );
+
+/**
+  Autogenerated function that calls the library constructors for all of the module's
+  dependent libraries.  This function must be called by the SEC Core once a stack has
+  been established.
+
+**/
+VOID
+EFIAPI
+ProcessLibraryConstructorList (
+  VOID
+  );
+
+#endif
diff --git a/UefiPayloadPkg/UefiPayloadPkg.dec b/UefiPayloadPkg/UefiPayloadPkg.dec
new file mode 100644
index 0000000000..1559735db2
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkg.dec
@@ -0,0 +1,71 @@
+## @file
+# UEFI Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+[Defines]
+  DEC_SPECIFICATION              = 0x00010005
+  PACKAGE_NAME                   = UefiPayloadPkg
+  PACKAGE_GUID                   = E0FC9D50-415E-4946-B686-9A130D5859E7
+  PACKAGE_VERSION                = 0.1
+
+[Includes]
+  Include
+
+
+[Guids]
+  #
+  ## Defines the token space for the UEFI Payload Package PCDs.
+  #
+  gUefiPayloadPkgTokenSpaceGuid  = {0x1d127ea, 0xf6f1, 0x4ef6, {0x94, 0x15, 0x8a, 0x0, 0x0, 0x93, 0xf8, 0x9d}}
+
+  #
+  # Gop Temp
+  #
+  gBmpImageGuid                           = { 0x878AC2CC, 0x5343, 0x46F2, { 0xB5, 0x63, 0x51, 0xF8, 0x9D, 0xAF, 0x56, 0xBA } }
+
+  gUefiSystemTableInfoGuid = {0x16c8a6d0, 0xfe8a, 0x4082, {0xa2, 0x8, 0xcf, 0x89, 0xc4, 0x29, 0x4, 0x33}}
+  gUefiAcpiBoardInfoGuid   = {0xad3d31b, 0xb3d8, 0x4506, {0xae, 0x71, 0x2e, 0xf1, 0x10, 0x6, 0xd9, 0xf}}
+  gUefiSerialPortInfoGuid  = { 0x6c6872fe, 0x56a9, 0x4403, { 0xbb, 0x98, 0x95, 0x8d, 0x62, 0xde, 0x87, 0xf1 } }
+  gLoaderMemoryMapInfoGuid = { 0xa1ff7424, 0x7a1a, 0x478e, { 0xa9, 0xe4, 0x92, 0xf3, 0x57, 0xd1, 0x28, 0x32 } }
+
+[Ppis]
+  gEfiPayLoadHobBasePpiGuid = { 0xdbe23aa1, 0xa342, 0x4b97, {0x85, 0xb6, 0xb2, 0x26, 0xf1, 0x61, 0x73, 0x89} }
+
+[Protocols]
+  #
+  # Gop Temp
+  #
+  gPlatformGOPPolicyGuid                  = { 0xec2e931b, 0x3281, 0x48a5, { 0x81, 0x07, 0xdf, 0x8a, 0x8b, 0xed, 0x3c, 0x5d } }
+
+################################################################################
+#
+# PCD Declarations section - list of all PCDs Declared by this Package
+#                            Only this package should be providing the
+#                            declaration, other packages should not.
+#
+################################################################################
+[PcdsFixedAtBuild, PcdsPatchableInModule]
+## Indicates the base address of the payload binary in memory
+gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase|0|UINT32|0x10000001
+## Provides the size of the payload binary in memory
+gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize|0|UINT32|0x10000002
+## Payload stack top
+gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop|0x90000|UINT32|0x10000004
+
+## FFS filename to find the shell application.
+gUefiPayloadPkgTokenSpaceGuid.PcdShellFile|{ 0x83, 0xA5, 0x04, 0x7C, 0x3E, 0x9E, 0x1c, 0x4f, 0xAD, 0x65, 0xE0, 0x52, 0x68, 0xD0, 0xB4, 0xD1 }|VOID*|0x10000005
+
+## Used to help reduce fragmentation in the EFI memory map
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIReclaimMemory|0x08|UINT32|0x10000012
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIMemoryNVS|0x04|UINT32|0x10000013
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiReservedMemoryType|0x04|UINT32|0x00000014
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesData|0xC0|UINT32|0x00000015
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesCode|0x80|UINT32|0x00000016
+
+
diff --git a/UefiPayloadPkg/UefiPayloadPkg.fdf b/UefiPayloadPkg/UefiPayloadPkg.fdf
new file mode 100644
index 0000000000..ce3b34999b
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkg.fdf
@@ -0,0 +1,288 @@
+## @file
+# Bootloader Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+################################################################################
+[FD.UefiPayload]
+BaseAddress   = 0x800000|gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase
+Size          = 0x410000|gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize
+ErasePolarity = 1
+BlockSize     = 0x1000
+NumBlocks     = 0x410
+
+0x00000000|0x030000
+FV = PEIFV
+
+0x00030000|0x3E0000
+FV = DXEFV
+
+################################################################################
+[FV.PEIFV]
+BlockSize          = 0x1000
+FvAlignment        = 16
+ERASE_POLARITY     = 1
+MEMORY_MAPPED      = TRUE
+STICKY_WRITE       = TRUE
+LOCK_CAP           = TRUE
+LOCK_STATUS        = TRUE
+WRITE_DISABLED_CAP = TRUE
+WRITE_ENABLED_CAP  = TRUE
+WRITE_STATUS       = TRUE
+WRITE_LOCK_CAP     = TRUE
+WRITE_LOCK_STATUS  = TRUE
+READ_DISABLED_CAP  = TRUE
+READ_ENABLED_CAP   = TRUE
+READ_STATUS        = TRUE
+READ_LOCK_CAP      = TRUE
+READ_LOCK_STATUS   = TRUE
+
+INF UefiPayloadPkg/SecCore/SecCore.inf
+
+INF MdeModulePkg/Core/Pei/PeiMain.inf
+INF MdeModulePkg/Universal/PCD/Pei/Pcd.inf
+INF MdeModulePkg/Universal/ReportStatusCodeRouter/Pei/ReportStatusCodeRouterPei.inf
+INF MdeModulePkg/Universal/StatusCodeHandler/Pei/StatusCodeHandlerPei.inf
+INF UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
+INF MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf
+
+################################################################################
+
+[FV.DXEFV]
+BlockSize          = 0x1000
+FvForceRebase      = FALSE
+FvAlignment        = 16
+ERASE_POLARITY     = 1
+MEMORY_MAPPED      = TRUE
+STICKY_WRITE       = TRUE
+LOCK_CAP           = TRUE
+LOCK_STATUS        = TRUE
+WRITE_DISABLED_CAP = TRUE
+WRITE_ENABLED_CAP  = TRUE
+WRITE_STATUS       = TRUE
+WRITE_LOCK_CAP     = TRUE
+WRITE_LOCK_STATUS  = TRUE
+READ_DISABLED_CAP  = TRUE
+READ_ENABLED_CAP   = TRUE
+READ_STATUS        = TRUE
+READ_LOCK_CAP      = TRUE
+READ_LOCK_STATUS   = TRUE
+
+APRIORI DXE {
+  INF  MdeModulePkg/Universal/PCD/Dxe/Pcd.inf
+  INF  MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+  INF  MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+}
+
+#
+# DXE Phase modules
+#
+INF MdeModulePkg/Core/Dxe/DxeMain.inf
+INF MdeModulePkg/Universal/PCD/Dxe/Pcd.inf
+INF MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+INF MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+
+INF MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf
+INF UefiCpuPkg/CpuDxe/CpuDxe.inf
+INF MdeModulePkg/Universal/BdsDxe/BdsDxe.inf
+INF MdeModulePkg/Application/UiApp/UiApp.inf
+INF PcAtChipsetPkg/HpetTimerDxe/HpetTimerDxe.inf
+INF MdeModulePkg/Universal/Metronome/Metronome.inf
+INF MdeModulePkg/Universal/WatchdogTimerDxe/WatchdogTimer.inf
+INF MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf
+INF MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
+INF MdeModulePkg/Universal/MonotonicCounterRuntimeDxe/MonotonicCounterRuntimeDxe.inf
+INF MdeModulePkg/Universal/ResetSystemRuntimeDxe/ResetSystemRuntimeDxe.inf
+INF PcAtChipsetPkg/PcatRealTimeClockRuntimeDxe/PcatRealTimeClockRuntimeDxe.inf
+INF MdeModulePkg/Universal/Variable/RuntimeDxe/VariableRuntimeDxe.inf
+
+INF UefiCpuPkg/CpuIo2Dxe/CpuIo2Dxe.inf
+INF MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf
+INF MdeModulePkg/Universal/MemoryTest/NullMemoryTestDxe/NullMemoryTestDxe.inf
+INF PcAtChipsetPkg/8259InterruptControllerDxe/8259.inf
+INF MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf
+INF MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf
+INF MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf
+INF UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
+
+INF MdeModulePkg/Universal/SmbiosDxe/SmbiosDxe.inf
+#
+# PCI Support
+#
+INF MdeModulePkg/Bus/Pci/PciBusDxe/PciBusDxe.inf
+INF MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf
+
+#
+# ISA Support
+#
+INF MdeModulePkg/Universal/SerialDxe/SerialDxe.inf
+
+#
+# Console Support
+#
+INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
+INF MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf
+INF MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf
+INF MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf
+INF UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
+
+#
+# SCSI/ATA/IDE/DISK Support
+#
+INF MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf
+INF MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf
+INF MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf
+INF MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf
+INF MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf
+INF MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf
+INF MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf
+INF MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf
+
+INF FatPkg/EnhancedFatDxe/Fat.inf
+
+#
+# SD/eMMC Support
+#
+INF MdeModulePkg/Bus/Pci/SdMmcPciHcDxe/SdMmcPciHcDxe.inf
+INF MdeModulePkg/Bus/Sd/EmmcDxe/EmmcDxe.inf
+INF MdeModulePkg/Bus/Sd/SdDxe/SdDxe.inf
+
+#
+# Usb Support
+#
+INF MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf
+INF MdeModulePkg/Bus/Pci/EhciDxe/EhciDxe.inf
+INF MdeModulePkg/Bus/Pci/XhciDxe/XhciDxe.inf
+INF MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBusDxe.inf
+INF MdeModulePkg/Bus/Usb/UsbKbDxe/UsbKbDxe.inf
+INF MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassStorageDxe.inf
+
+
+#
+# Shell
+#
+!if $(SHELL_TYPE) == BUILD_SHELL
+INF ShellPkg/DynamicCommand/TftpDynamicCommand/TftpDynamicCommand.inf
+INF ShellPkg/DynamicCommand/DpDynamicCommand/DpDynamicCommand.inf
+INF ShellPkg/Application/Shell/Shell.inf
+!endif
+
+!if $(SHELL_TYPE) == MIN_BIN
+!if $(ARCH) == IA32
+INF  RuleOverride = BINARY USE = IA32 ShellBinPkg/MinUefiShell/MinUefiShell.inf
+!else
+INF  RuleOverride = BINARY USE = X64 ShellBinPkg/MinUefiShell/MinUefiShell.inf
+!endif
+!endif
+
+!if $(SHELL_TYPE) == UEFI_BIN
+!if $(ARCH) == IA32
+INF  RuleOverride = BINARY USE = IA32 ShellBinPkg/UefiShell/UefiShell.inf
+!else
+INF  RuleOverride = BINARY USE = X64 ShellBinPkg/UefiShell/UefiShell.inf
+!endif
+!endif
+
+
+################################################################################
+#
+# Rules are use with the [FV] section's module INF type to define
+# how an FFS file is created for a given INF file. The following Rule are the default
+# rules for the different module type. User can add the customized rules to define the
+# content of the FFS file.
+#
+################################################################################
+
+[Rule.Common.SEC]
+  FILE SEC = $(NAMED_GUID) {
+    PE32     PE32   Align=32    $(INF_OUTPUT)/$(MODULE_NAME).efi
+  }
+
+[Rule.Common.PEI_CORE]
+  FILE PEI_CORE = $(NAMED_GUID) {
+    PE32     PE32   Align=Auto    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING ="$(MODULE_NAME)" Optional
+    VERSION  STRING ="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.PEIM]
+  FILE PEIM = $(NAMED_GUID) {
+     PEI_DEPEX PEI_DEPEX Optional        $(INF_OUTPUT)/$(MODULE_NAME).depex
+     PE32      PE32   Align=Auto           $(INF_OUTPUT)/$(MODULE_NAME).efi
+     UI       STRING="$(MODULE_NAME)" Optional
+     VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.DXE_CORE]
+  FILE DXE_CORE = $(NAMED_GUID) {
+    PE32     PE32           $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.DXE_DRIVER]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX    DXE_DEPEX Optional      $(INF_OUTPUT)/$(MODULE_NAME).depex
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.DXE_RUNTIME_DRIVER]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX    DXE_DEPEX Optional      $(INF_OUTPUT)/$(MODULE_NAME).depex
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_DRIVER]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX    DXE_DEPEX Optional      $(INF_OUTPUT)/$(MODULE_NAME).depex
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_DRIVER.BINARY]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX DXE_DEPEX Optional      |.depex
+    PE32      PE32                    |.efi
+    UI        STRING="$(MODULE_NAME)" Optional
+    VERSION   STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_APPLICATION]
+  FILE APPLICATION = $(NAMED_GUID) {
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_APPLICATION.BINARY]
+  FILE APPLICATION = $(NAMED_GUID) {
+    PE32      PE32                    |.efi
+    UI        STRING="$(MODULE_NAME)" Optional
+    VERSION   STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.USER_DEFINED.ACPITABLE]
+  FILE FREEFORM = $(NAMED_GUID) {
+    RAW ACPI               |.acpi
+    RAW ASL                |.aml
+  }
+
+[Rule.Common.USER_DEFINED.CSM]
+  FILE FREEFORM = $(NAMED_GUID) {
+    RAW BIN                |.bin
+  }
+
+[Rule.Common.SEC.RESET_VECTOR]
+  FILE RAW = $(NAMED_GUID) {
+    RAW RAW                |.raw
+  }
diff --git a/UefiPayloadPkg/UefiPayloadPkgIa32.dsc b/UefiPayloadPkg/UefiPayloadPkgIa32.dsc
new file mode 100644
index 0000000000..13983d0895
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkgIa32.dsc
@@ -0,0 +1,573 @@
+## @file
+# Bootloader Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+################################################################################
+#
+# Defines Section - statements that will be processed to create a Makefile.
+#
+################################################################################
+[Defines]
+  PLATFORM_NAME                       = UefiPayloadPkg
+  PLATFORM_GUID                       = F71608AB-D63D-4491-B744-A99998C8CD96
+  PLATFORM_VERSION                    = 0.1
+  DSC_SPECIFICATION                   = 0x00010005
+  SUPPORTED_ARCHITECTURES             = IA32
+  BUILD_TARGETS                       = DEBUG|RELEASE|NOOPT
+  SKUID_IDENTIFIER                    = DEFAULT
+  OUTPUT_DIRECTORY                    = Build/UefiPayloadPkgIA32
+  FLASH_DEFINITION                    = UefiPayloadPkg/UefiPayloadPkg.fdf
+
+  DEFINE SOURCE_DEBUG_ENABLE          = FALSE
+
+  #
+  # SBL:      UEFI payload for Slim Bootloader
+  # COREBOOT: UEFI payload for coreboot
+  #
+  DEFINE   BOOTLOADER = SBL
+
+  #
+  # CPU options
+  #
+  DEFINE MAX_LOGICAL_PROCESSORS       = 64
+
+  #
+  # PCI options
+  #
+  DEFINE PCIE_BASE                    = 0xE0000000
+
+  #
+  # Serial port set up
+  #
+  DEFINE BAUD_RATE                    = 115200
+  DEFINE SERIAL_CLOCK_RATE            = 1843200
+  DEFINE SERIAL_LINE_CONTROL          = 3 # 8-bits, no parity
+  DEFINE SERIAL_HARDWARE_FLOW_CONTROL = FALSE
+  DEFINE SERIAL_DETECT_CABLE          = FALSE
+  DEFINE SERIAL_FIFO_CONTROL          = 7 # Enable FIFO
+  DEFINE SERIAL_EXTENDED_TX_FIFO_SIZE = 16
+  DEFINE UART_DEFAULT_BAUD_RATE       = $(BAUD_RATE)
+  DEFINE UART_DEFAULT_DATA_BITS       = 8
+  DEFINE UART_DEFAULT_PARITY          = 1
+  DEFINE UART_DEFAULT_STOP_BITS       = 1
+  DEFINE DEFAULT_TERMINAL_TYPE        = 0
+
+  #
+  #  typedef struct {
+  #    UINT16  VendorId;          ///< Vendor ID to match the PCI device.  The value 0xFFFF terminates the list of entries.
+  #    UINT16  DeviceId;          ///< Device ID to match the PCI device
+  #    UINT32  ClockRate;         ///< UART clock rate.  Set to 0 for default clock rate of 1843200 Hz
+  #    UINT64  Offset;            ///< The byte offset into to the BAR
+  #    UINT8   BarIndex;          ///< Which BAR to get the UART base address
+  #    UINT8   RegisterStride;    ///< UART register stride in bytes.  Set to 0 for default register stride of 1 byte.
+  #    UINT16  ReceiveFifoDepth;  ///< UART receive FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT16  TransmitFifoDepth; ///< UART transmit FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT8   Reserved[2];
+  #  } PCI_SERIAL_PARAMETER;
+  #
+  # Vendor FFFF Device 0000 Prog Interface 1, BAR #0, Offset 0, Stride = 1, Clock 1843200 (0x1c2000)
+  #
+  #                                       [Vendor]   [Device]  [----ClockRate---]  [------------Offset-----------] [Bar] [Stride] [RxFifo] [TxFifo]   [Rsvd]   [Vendor]
+  DEFINE PCI_SERIAL_PARAMETERS        = {0xff,0xff, 0x00,0x00, 0x0,0x20,0x1c,0x00, 0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0, 0x00,    0x01, 0x0,0x0, 0x0,0x0, 0x0,0x0, 0xff,0xff}
+
+  #
+  # Shell options: [BUILD_SHELL, MIN_BIN, NONE, UEFI_BIN]
+  #
+  DEFINE SHELL_TYPE                   = BUILD_SHELL
+
+[BuildOptions]
+  *_*_*_CC_FLAGS                 = -D DISABLE_NEW_DEPRECATED_INTERFACES
+  GCC:*_UNIXGCC_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  GCC:RELEASE_*_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  INTEL:RELEASE_*_*_CC_FLAGS     = /D MDEPKG_NDEBUG
+  MSFT:RELEASE_*_*_CC_FLAGS      = /D MDEPKG_NDEBUG
+
+
+################################################################################
+#
+# SKU Identification section - list of all SKU IDs supported by this Platform.
+#
+################################################################################
+[SkuIds]
+  0|DEFAULT
+
+################################################################################
+#
+# Library Class section - list of all Library Classes needed by this Platform.
+#
+################################################################################
+[LibraryClasses]
+  #
+  # Entry point
+  #
+  PeiCoreEntryPoint|MdePkg/Library/PeiCoreEntryPoint/PeiCoreEntryPoint.inf
+  PeimEntryPoint|MdePkg/Library/PeimEntryPoint/PeimEntryPoint.inf
+  DxeCoreEntryPoint|MdePkg/Library/DxeCoreEntryPoint/DxeCoreEntryPoint.inf
+  UefiDriverEntryPoint|MdePkg/Library/UefiDriverEntryPoint/UefiDriverEntryPoint.inf
+  UefiApplicationEntryPoint|MdePkg/Library/UefiApplicationEntryPoint/UefiApplicationEntryPoint.inf
+
+  #
+  # Basic
+  #
+  BaseLib|MdePkg/Library/BaseLib/BaseLib.inf
+  BaseMemoryLib|MdePkg/Library/BaseMemoryLibRepStr/BaseMemoryLibRepStr.inf
+  SynchronizationLib|MdePkg/Library/BaseSynchronizationLib/BaseSynchronizationLib.inf
+  PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf
+  CpuLib|MdePkg/Library/BaseCpuLib/BaseCpuLib.inf
+  IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf
+!if $(PCIE_BASE) == 0
+  PciLib|MdePkg/Library/BasePciLibCf8/BasePciLibCf8.inf
+  PciCf8Lib|MdePkg/Library/BasePciCf8Lib/BasePciCf8Lib.inf
+!else
+  PciLib|MdePkg/Library/BasePciLibPciExpress/BasePciLibPciExpress.inf
+  PciExpressLib|MdePkg/Library/BasePciExpressLib/BasePciExpressLib.inf
+!endif
+  PciSegmentLib|MdePkg/Library/BasePciSegmentLibPci/BasePciSegmentLibPci.inf
+  PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf
+  PeCoffGetEntryPointLib|MdePkg/Library/BasePeCoffGetEntryPointLib/BasePeCoffGetEntryPointLib.inf
+  CacheMaintenanceLib|MdePkg/Library/BaseCacheMaintenanceLib/BaseCacheMaintenanceLib.inf
+
+  #
+  # UEFI & PI
+  #
+  UefiBootServicesTableLib|MdePkg/Library/UefiBootServicesTableLib/UefiBootServicesTableLib.inf
+  UefiRuntimeServicesTableLib|MdePkg/Library/UefiRuntimeServicesTableLib/UefiRuntimeServicesTableLib.inf
+  UefiRuntimeLib|MdePkg/Library/UefiRuntimeLib/UefiRuntimeLib.inf
+  UefiLib|MdePkg/Library/UefiLib/UefiLib.inf
+  UefiHiiServicesLib|MdeModulePkg/Library/UefiHiiServicesLib/UefiHiiServicesLib.inf
+  HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  UefiDecompressLib|MdePkg/Library/BaseUefiDecompressLib/BaseUefiDecompressLib.inf
+  PeiServicesTablePointerLib|MdePkg/Library/PeiServicesTablePointerLibIdt/PeiServicesTablePointerLibIdt.inf
+  PeiServicesLib|MdePkg/Library/PeiServicesLib/PeiServicesLib.inf
+  DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf
+  DxeServicesTableLib|MdePkg/Library/DxeServicesTableLib/DxeServicesTableLib.inf
+  UefiCpuLib|UefiCpuPkg/Library/BaseUefiCpuLib/BaseUefiCpuLib.inf
+  SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+
+  #
+  # Generic Modules
+  #
+  UefiUsbLib|MdePkg/Library/UefiUsbLib/UefiUsbLib.inf
+  UefiScsiLib|MdePkg/Library/UefiScsiLib/UefiScsiLib.inf
+  OemHookStatusCodeLib|MdeModulePkg/Library/OemHookStatusCodeLibNull/OemHookStatusCodeLibNull.inf
+  CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf
+  SecurityManagementLib|MdeModulePkg/Library/DxeSecurityManagementLib/DxeSecurityManagementLib.inf
+  UefiBootManagerLib|MdeModulePkg/Library/UefiBootManagerLib/UefiBootManagerLib.inf
+  CustomizedDisplayLib|MdeModulePkg/Library/CustomizedDisplayLib/CustomizedDisplayLib.inf
+  FrameBufferBltLib|MdeModulePkg/Library/FrameBufferBltLib/FrameBufferBltLib.inf
+
+  #
+  # CPU
+  #
+  MtrrLib|UefiCpuPkg/Library/MtrrLib/MtrrLib.inf
+  LocalApicLib|UefiCpuPkg/Library/BaseXApicX2ApicLib/BaseXApicX2ApicLib.inf
+
+  #
+  # Platform
+  #
+  TimerLib|UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
+  ResetSystemLib|UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
+  SerialPortLib|MdeModulePkg/Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf
+  PlatformHookLib|UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
+  PlatformBootManagerLib|UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
+  IoApicLib|PcAtChipsetPkg/Library/BaseIoApicLib/BaseIoApicLib.inf
+
+  #
+  # Misc
+  #
+  DebugPrintErrorLevelLib|MdePkg/Library/BaseDebugPrintErrorLevelLib/BaseDebugPrintErrorLevelLib.inf
+  PerformanceLib|MdePkg/Library/BasePerformanceLibNull/BasePerformanceLibNull.inf
+!if $(SOURCE_DEBUG_ENABLE) == TRUE
+  PeCoffExtraActionLib|SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLibDebug.inf
+  DebugCommunicationLib|SourceLevelDebugPkg/Library/DebugCommunicationLibSerialPort/DebugCommunicationLibSerialPort.inf
+!else
+  PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+!endif
+  PlatformSupportLib|UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
+!if $(BOOTLOADER) == "COREBOOT"
+  BlParseLib|UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
+!else
+  BlParseLib|UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
+!endif
+
+  DebugLib|MdePkg/Library/BaseDebugLibSerialPort/BaseDebugLibSerialPort.inf
+  LockBoxLib|MdeModulePkg/Library/LockBoxNullLib/LockBoxNullLib.inf
+  FileExplorerLib|MdeModulePkg/Library/FileExplorerLib/FileExplorerLib.inf
+  AuthVariableLib|MdeModulePkg/Library/AuthVariableLibNull/AuthVariableLibNull.inf
+  TpmMeasurementLib|MdeModulePkg/Library/TpmMeasurementLibNull/TpmMeasurementLibNull.inf
+  VarCheckLib|MdeModulePkg/Library/VarCheckLib/VarCheckLib.inf
+
+[LibraryClasses.IA32.SEC]
+  DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+  ReportStatusCodeLib|MdePkg/Library/BaseReportStatusCodeLibNull/BaseReportStatusCodeLibNull.inf
+
+[LibraryClasses.IA32.PEI_CORE, LibraryClasses.IA32.PEIM]
+  PcdLib|MdePkg/Library/PeiPcdLib/PeiPcdLib.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/PeiReportStatusCodeLib/PeiReportStatusCodeLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/PeiExtractGuidedSectionLib/PeiExtractGuidedSectionLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf
+!endif
+
+[LibraryClasses.common.DXE_CORE]
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/DxeCoreHobLib/DxeCoreHobLib.inf
+  MemoryAllocationLib|MdeModulePkg/Library/DxeCoreMemoryAllocationLib/DxeCoreMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+
+[LibraryClasses.common.DXE_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+  MpInitLib|UefiCpuPkg/Library/MpInitLib/DxeMpInitLib.inf
+
+[LibraryClasses.common.DXE_RUNTIME_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/RuntimeDxeReportStatusCodeLib/RuntimeDxeReportStatusCodeLib.inf
+
+[LibraryClasses.common.UEFI_DRIVER,LibraryClasses.common.UEFI_APPLICATION]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+
+################################################################################
+#
+# Pcd Section - list of all EDK II PCD Entries defined by this Platform.
+#
+################################################################################
+[PcdsFeatureFlag]
+!if $(TARGET) == DEBUG
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|TRUE
+!else
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|FALSE
+!endif
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseMemory|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdDxeIplSwitchToLongMode|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutGopSupport|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutUgaSupport|FALSE
+
+[PcdsFixedAtBuild]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize|0x10000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize|0x8000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVariableStoreSize|0x10000
+  #
+  # Make VariableRuntimeDxe work at emulated non-volatile variable mode.
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvModeEnable|TRUE
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVpdBaseAddress|0x0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdBootManagerMenuFile|{ 0x21, 0xaa, 0x2c, 0x46, 0x14, 0x76, 0x03, 0x45, 0x83, 0x6e, 0x8a, 0xb6, 0xf4, 0x66, 0x23, 0x31 }
+
+  gEfiMdePkgTokenSpaceGuid.PcdPciExpressBaseAddress|$(PCIE_BASE)
+
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiSourceLevelDebugPkgTokenSpaceGuid.PcdDebugLoadImageMethod|0x2
+!endif
+
+[PcdsPatchableInModule.common]
+  gEfiMdePkgTokenSpaceGuid.PcdReportStatusCodePropertyMask|0x7
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPrintErrorLevel|0x8000004F
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x17
+!else
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x2F
+!endif
+
+  #
+  # The following parameters are set by Library/PlatformHookLib
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase|0x3f8
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate|$(BAUD_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride|1
+
+  #
+  # Enable these parameters to be set on the command line
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate|$(SERIAL_CLOCK_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialLineControl|$(SERIAL_LINE_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseHardwareFlowControl|$(SERIAL_HARDWARE_FLOW_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialDetectCable|$(SERIAL_DETECT_CABLE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialFifoControl|$(SERIAL_FIFO_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialExtendedTxFifoSize|$(SERIAL_EXTENDED_TX_FIFO_SIZE)
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciDisableBusEnumeration|TRUE
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate|$(UART_DEFAULT_BAUD_RATE)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultDataBits|$(UART_DEFAULT_DATA_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultParity|$(UART_DEFAULT_PARITY)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultStopBits|$(UART_DEFAULT_STOP_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdDefaultTerminalType|$(DEFAULT_TERMINAL_TYPE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciSerialParameters|$(PCI_SERIAL_PARAMETERS)
+
+  gUefiCpuPkgTokenSpaceGuid.PcdCpuMaxLogicalProcessorNumber|$(MAX_LOGICAL_PROCESSORS)
+
+
+################################################################################
+#
+# Pcd Dynamic Section - list of all EDK II PCD Entries defined by this Platform
+#
+################################################################################
+
+[PcdsDynamicDefault]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvStoreReserved|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase|0
+  gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut|3
+
+  ## This PCD defines the video horizontal resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution|0
+  ## This PCD defines the video vertical resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution|0
+
+  ## The PCD is used to specify the video horizontal resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution|0
+  ## The PCD is used to specify the video vertical resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution|0
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow|31
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn|100
+
+################################################################################
+#
+# Components Section - list of all EDK II Modules needed by this Platform.
+#
+################################################################################
+[Components.IA32]
+  #
+  # SEC Core
+  #
+  UefiPayloadPkg/SecCore/SecCore.inf
+
+  #
+  # PEI Core
+  #
+  MdeModulePkg/Core/Pei/PeiMain.inf
+
+  #
+  # PEIM
+  #
+  MdeModulePkg/Universal/PCD/Pei/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+  MdeModulePkg/Universal/ReportStatusCodeRouter/Pei/ReportStatusCodeRouterPei.inf
+  MdeModulePkg/Universal/StatusCodeHandler/Pei/StatusCodeHandlerPei.inf
+
+  UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
+  MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf
+
+[Components.IA32]
+  #
+  # DXE Core
+  #
+  MdeModulePkg/Core/Dxe/DxeMain.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf
+  }
+
+  #
+  # Components that produce the architectural protocols
+  #
+  MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf
+  UefiCpuPkg/CpuDxe/CpuDxe.inf
+  MdeModulePkg/Universal/BdsDxe/BdsDxe.inf
+  MdeModulePkg/Application/UiApp/UiApp.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/DeviceManagerUiLib/DeviceManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootManagerUiLib/BootManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootMaintenanceManagerUiLib/BootMaintenanceManagerUiLib.inf
+  }
+
+  PcAtChipsetPkg/HpetTimerDxe/HpetTimerDxe.inf
+  MdeModulePkg/Universal/Metronome/Metronome.inf
+  MdeModulePkg/Universal/WatchdogTimerDxe/WatchdogTimer.inf
+  MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf
+  MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
+  MdeModulePkg/Universal/MonotonicCounterRuntimeDxe/MonotonicCounterRuntimeDxe.inf
+  MdeModulePkg/Universal/ResetSystemRuntimeDxe/ResetSystemRuntimeDxe.inf
+  PcAtChipsetPkg/PcatRealTimeClockRuntimeDxe/PcatRealTimeClockRuntimeDxe.inf
+  MdeModulePkg/Universal/Variable/RuntimeDxe/VariableRuntimeDxe.inf
+
+  #
+  # Following are the DXE drivers
+  #
+  MdeModulePkg/Universal/PCD/Dxe/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+
+  MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+  MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+  UefiCpuPkg/CpuIo2Dxe/CpuIo2Dxe.inf
+  MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf
+  MdeModulePkg/Universal/MemoryTest/NullMemoryTestDxe/NullMemoryTestDxe.inf
+  PcAtChipsetPkg/8259InterruptControllerDxe/8259.inf
+  MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf
+  MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf
+  MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf
+
+  UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
+
+  #
+  # SMBIOS Support
+  #
+  MdeModulePkg/Universal/SmbiosDxe/SmbiosDxe.inf
+
+  #
+  # ACPI Support
+  #
+  MdeModulePkg/Universal/Acpi/AcpiTableDxe/AcpiTableDxe.inf
+
+  #
+  # PCI Support
+  #
+  MdeModulePkg/Bus/Pci/PciBusDxe/PciBusDxe.inf
+  MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf {
+    <LibraryClasses>
+      PciHostBridgeLib|UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
+  }
+
+  #
+  # SCSI/ATA/IDE/DISK Support
+  #
+  MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf
+  MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf
+  MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf
+  FatPkg/EnhancedFatDxe/Fat.inf
+  MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf
+  MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf
+  MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf
+  MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf
+  MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf
+
+  #
+  # SD/eMMC Support
+  #
+  MdeModulePkg/Bus/Pci/SdMmcPciHcDxe/SdMmcPciHcDxe.inf
+  MdeModulePkg/Bus/Sd/EmmcDxe/EmmcDxe.inf
+  MdeModulePkg/Bus/Sd/SdDxe/SdDxe.inf
+
+  #
+  # Usb Support
+  #
+  MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf
+  MdeModulePkg/Bus/Pci/EhciDxe/EhciDxe.inf
+  MdeModulePkg/Bus/Pci/XhciDxe/XhciDxe.inf
+  MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBusDxe.inf
+  MdeModulePkg/Bus/Usb/UsbKbDxe/UsbKbDxe.inf
+  MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassStorageDxe.inf
+
+  #
+  # ISA Support
+  #
+  MdeModulePkg/Universal/SerialDxe/SerialDxe.inf
+
+  #
+  # Console Support
+  #
+  MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
+  MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf
+  MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf
+  MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf
+  UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
+
+  #------------------------------
+  #  Build the shell
+  #------------------------------
+
+!if $(SHELL_TYPE) == BUILD_SHELL
+
+  #
+  # Shell Lib
+  #
+[LibraryClasses]
+  BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  FileHandleLib|MdePkg/Library/UefiFileHandleLib/UefiFileHandleLib.inf
+  ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf
+  NetLib|MdeModulePkg/Library/DxeNetLib/DxeNetLib.inf
+
+[Components.IA32]
+  ShellPkg/DynamicCommand/TftpDynamicCommand/TftpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/DynamicCommand/DpDynamicCommand/DpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/Application/Shell/Shell.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the shell application itself only.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+
+    #------------------------------
+    #  Basic commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
+
+    #------------------------------
+    #  Networking commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
+
+    #------------------------------
+    #  Support libraries
+    #------------------------------
+
+    <LibraryClasses>
+      DebugLib|MdePkg/Library/UefiDebugLibConOut/UefiDebugLibConOut.inf
+      DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+      HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf
+      PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+      ShellCEntryLib|ShellPkg/Library/UefiShellCEntryLib/UefiShellCEntryLib.inf
+      ShellCommandLib|ShellPkg/Library/UefiShellCommandLib/UefiShellCommandLib.inf
+      SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+  }
+
+!endif
diff --git a/UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc b/UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc
new file mode 100644
index 0000000000..dc38d6528e
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc
@@ -0,0 +1,574 @@
+## @file
+# Bootloader Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+#
+##
+
+################################################################################
+#
+# Defines Section - statements that will be processed to create a Makefile.
+#
+################################################################################
+[Defines]
+  PLATFORM_NAME                       = UefiPayloadPkg
+  PLATFORM_GUID                       = F71608AB-D63D-4491-B744-A99998C8CD96
+  PLATFORM_VERSION                    = 0.1
+  DSC_SPECIFICATION                   = 0x00010005
+  SUPPORTED_ARCHITECTURES             = IA32|X64
+  BUILD_TARGETS                       = DEBUG|RELEASE|NOOPT
+  SKUID_IDENTIFIER                    = DEFAULT
+  OUTPUT_DIRECTORY                    = Build/UefiPayloadPkgX64
+  FLASH_DEFINITION                    = UefiPayloadPkg/UefiPayloadPkg.fdf
+
+  DEFINE SOURCE_DEBUG_ENABLE          = FALSE
+
+  #
+  # SBL:      UEFI payload for Slim Bootloader
+  # COREBOOT: UEFI payload for coreboot
+  #
+  DEFINE   BOOTLOADER = SBL
+
+  #
+  # CPU options
+  #
+  DEFINE MAX_LOGICAL_PROCESSORS       = 64
+
+  #
+  # PCI options
+  #
+  DEFINE PCIE_BASE                    = 0xE0000000
+
+  #
+  # Serial port set up
+  #
+  DEFINE BAUD_RATE                    = 115200
+  DEFINE SERIAL_CLOCK_RATE            = 1843200
+  DEFINE SERIAL_LINE_CONTROL          = 3 # 8-bits, no parity
+  DEFINE SERIAL_HARDWARE_FLOW_CONTROL = FALSE
+  DEFINE SERIAL_DETECT_CABLE          = FALSE
+  DEFINE SERIAL_FIFO_CONTROL          = 7 # Enable FIFO
+  DEFINE SERIAL_EXTENDED_TX_FIFO_SIZE = 16
+  DEFINE UART_DEFAULT_BAUD_RATE       = $(BAUD_RATE)
+  DEFINE UART_DEFAULT_DATA_BITS       = 8
+  DEFINE UART_DEFAULT_PARITY          = 1
+  DEFINE UART_DEFAULT_STOP_BITS       = 1
+  DEFINE DEFAULT_TERMINAL_TYPE        = 0
+
+  #
+  #  typedef struct {
+  #    UINT16  VendorId;          ///< Vendor ID to match the PCI device.  The value 0xFFFF terminates the list of entries.
+  #    UINT16  DeviceId;          ///< Device ID to match the PCI device
+  #    UINT32  ClockRate;         ///< UART clock rate.  Set to 0 for default clock rate of 1843200 Hz
+  #    UINT64  Offset;            ///< The byte offset into to the BAR
+  #    UINT8   BarIndex;          ///< Which BAR to get the UART base address
+  #    UINT8   RegisterStride;    ///< UART register stride in bytes.  Set to 0 for default register stride of 1 byte.
+  #    UINT16  ReceiveFifoDepth;  ///< UART receive FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT16  TransmitFifoDepth; ///< UART transmit FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT8   Reserved[2];
+  #  } PCI_SERIAL_PARAMETER;
+  #
+  # Vendor FFFF Device 0000 Prog Interface 1, BAR #0, Offset 0, Stride = 1, Clock 1843200 (0x1c2000)
+  #
+  #                                       [Vendor]   [Device]  [----ClockRate---]  [------------Offset-----------] [Bar] [Stride] [RxFifo] [TxFifo]   [Rsvd]   [Vendor]
+  DEFINE PCI_SERIAL_PARAMETERS        = {0xff,0xff, 0x00,0x00, 0x0,0x20,0x1c,0x00, 0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0, 0x00,    0x01, 0x0,0x0, 0x0,0x0, 0x0,0x0, 0xff,0xff}
+
+  #
+  # Shell options: [BUILD_SHELL, MIN_BIN, NONE, UEFI_BIN]
+  #
+  DEFINE SHELL_TYPE                   = BUILD_SHELL
+
+[BuildOptions]
+  *_*_*_CC_FLAGS                 = -D DISABLE_NEW_DEPRECATED_INTERFACES
+  GCC:*_UNIXGCC_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  GCC:RELEASE_*_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  INTEL:RELEASE_*_*_CC_FLAGS     = /D MDEPKG_NDEBUG
+  MSFT:RELEASE_*_*_CC_FLAGS      = /D MDEPKG_NDEBUG
+
+
+################################################################################
+#
+# SKU Identification section - list of all SKU IDs supported by this Platform.
+#
+################################################################################
+[SkuIds]
+  0|DEFAULT
+
+################################################################################
+#
+# Library Class section - list of all Library Classes needed by this Platform.
+#
+################################################################################
+[LibraryClasses]
+  #
+  # Entry point
+  #
+  PeiCoreEntryPoint|MdePkg/Library/PeiCoreEntryPoint/PeiCoreEntryPoint.inf
+  PeimEntryPoint|MdePkg/Library/PeimEntryPoint/PeimEntryPoint.inf
+  DxeCoreEntryPoint|MdePkg/Library/DxeCoreEntryPoint/DxeCoreEntryPoint.inf
+  UefiDriverEntryPoint|MdePkg/Library/UefiDriverEntryPoint/UefiDriverEntryPoint.inf
+  UefiApplicationEntryPoint|MdePkg/Library/UefiApplicationEntryPoint/UefiApplicationEntryPoint.inf
+
+  #
+  # Basic
+  #
+  BaseLib|MdePkg/Library/BaseLib/BaseLib.inf
+  BaseMemoryLib|MdePkg/Library/BaseMemoryLibRepStr/BaseMemoryLibRepStr.inf
+  SynchronizationLib|MdePkg/Library/BaseSynchronizationLib/BaseSynchronizationLib.inf
+  PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf
+  CpuLib|MdePkg/Library/BaseCpuLib/BaseCpuLib.inf
+  IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf
+!if $(PCIE_BASE) == 0
+  PciLib|MdePkg/Library/BasePciLibCf8/BasePciLibCf8.inf
+  PciCf8Lib|MdePkg/Library/BasePciCf8Lib/BasePciCf8Lib.inf
+!else
+  PciLib|MdePkg/Library/BasePciLibPciExpress/BasePciLibPciExpress.inf
+  PciExpressLib|MdePkg/Library/BasePciExpressLib/BasePciExpressLib.inf
+!endif
+  PciSegmentLib|MdePkg/Library/BasePciSegmentLibPci/BasePciSegmentLibPci.inf
+  PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf
+  PeCoffGetEntryPointLib|MdePkg/Library/BasePeCoffGetEntryPointLib/BasePeCoffGetEntryPointLib.inf
+  CacheMaintenanceLib|MdePkg/Library/BaseCacheMaintenanceLib/BaseCacheMaintenanceLib.inf
+
+  #
+  # UEFI & PI
+  #
+  UefiBootServicesTableLib|MdePkg/Library/UefiBootServicesTableLib/UefiBootServicesTableLib.inf
+  UefiRuntimeServicesTableLib|MdePkg/Library/UefiRuntimeServicesTableLib/UefiRuntimeServicesTableLib.inf
+  UefiRuntimeLib|MdePkg/Library/UefiRuntimeLib/UefiRuntimeLib.inf
+  UefiLib|MdePkg/Library/UefiLib/UefiLib.inf
+  UefiHiiServicesLib|MdeModulePkg/Library/UefiHiiServicesLib/UefiHiiServicesLib.inf
+  HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  UefiDecompressLib|MdePkg/Library/BaseUefiDecompressLib/BaseUefiDecompressLib.inf
+  PeiServicesTablePointerLib|MdePkg/Library/PeiServicesTablePointerLibIdt/PeiServicesTablePointerLibIdt.inf
+  PeiServicesLib|MdePkg/Library/PeiServicesLib/PeiServicesLib.inf
+  DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf
+  DxeServicesTableLib|MdePkg/Library/DxeServicesTableLib/DxeServicesTableLib.inf
+  UefiCpuLib|UefiCpuPkg/Library/BaseUefiCpuLib/BaseUefiCpuLib.inf
+  SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+
+  #
+  # Generic Modules
+  #
+  UefiUsbLib|MdePkg/Library/UefiUsbLib/UefiUsbLib.inf
+  UefiScsiLib|MdePkg/Library/UefiScsiLib/UefiScsiLib.inf
+  OemHookStatusCodeLib|MdeModulePkg/Library/OemHookStatusCodeLibNull/OemHookStatusCodeLibNull.inf
+  CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf
+  SecurityManagementLib|MdeModulePkg/Library/DxeSecurityManagementLib/DxeSecurityManagementLib.inf
+  UefiBootManagerLib|MdeModulePkg/Library/UefiBootManagerLib/UefiBootManagerLib.inf
+  CustomizedDisplayLib|MdeModulePkg/Library/CustomizedDisplayLib/CustomizedDisplayLib.inf
+  FrameBufferBltLib|MdeModulePkg/Library/FrameBufferBltLib/FrameBufferBltLib.inf
+
+  #
+  # CPU
+  #
+  MtrrLib|UefiCpuPkg/Library/MtrrLib/MtrrLib.inf
+  LocalApicLib|UefiCpuPkg/Library/BaseXApicX2ApicLib/BaseXApicX2ApicLib.inf
+
+  #
+  # Platform
+  #
+  TimerLib|UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
+  ResetSystemLib|UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
+  SerialPortLib|MdeModulePkg/Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf
+  PlatformHookLib|UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
+  PlatformBootManagerLib|UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
+  IoApicLib|PcAtChipsetPkg/Library/BaseIoApicLib/BaseIoApicLib.inf
+
+  #
+  # Misc
+  #
+  DebugPrintErrorLevelLib|MdePkg/Library/BaseDebugPrintErrorLevelLib/BaseDebugPrintErrorLevelLib.inf
+  PerformanceLib|MdePkg/Library/BasePerformanceLibNull/BasePerformanceLibNull.inf
+!if $(SOURCE_DEBUG_ENABLE) == TRUE
+  PeCoffExtraActionLib|SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLibDebug.inf
+  DebugCommunicationLib|SourceLevelDebugPkg/Library/DebugCommunicationLibSerialPort/DebugCommunicationLibSerialPort.inf
+!else
+  PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+!endif
+  PlatformSupportLib|UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
+!if $(BOOTLOADER) == "COREBOOT"
+  BlParseLib|UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
+!else
+  BlParseLib|UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
+!endif
+
+  DebugLib|MdePkg/Library/BaseDebugLibSerialPort/BaseDebugLibSerialPort.inf
+  LockBoxLib|MdeModulePkg/Library/LockBoxNullLib/LockBoxNullLib.inf
+  FileExplorerLib|MdeModulePkg/Library/FileExplorerLib/FileExplorerLib.inf
+  AuthVariableLib|MdeModulePkg/Library/AuthVariableLibNull/AuthVariableLibNull.inf
+  TpmMeasurementLib|MdeModulePkg/Library/TpmMeasurementLibNull/TpmMeasurementLibNull.inf
+  VarCheckLib|MdeModulePkg/Library/VarCheckLib/VarCheckLib.inf
+
+[LibraryClasses.IA32.SEC]
+  DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+  ReportStatusCodeLib|MdePkg/Library/BaseReportStatusCodeLibNull/BaseReportStatusCodeLibNull.inf
+
+[LibraryClasses.IA32.PEI_CORE, LibraryClasses.IA32.PEIM]
+  PcdLib|MdePkg/Library/PeiPcdLib/PeiPcdLib.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/PeiReportStatusCodeLib/PeiReportStatusCodeLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/PeiExtractGuidedSectionLib/PeiExtractGuidedSectionLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf
+!endif
+
+[LibraryClasses.common.DXE_CORE]
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/DxeCoreHobLib/DxeCoreHobLib.inf
+  MemoryAllocationLib|MdeModulePkg/Library/DxeCoreMemoryAllocationLib/DxeCoreMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+
+[LibraryClasses.common.DXE_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+  MpInitLib|UefiCpuPkg/Library/MpInitLib/DxeMpInitLib.inf
+
+[LibraryClasses.common.DXE_RUNTIME_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/RuntimeDxeReportStatusCodeLib/RuntimeDxeReportStatusCodeLib.inf
+
+[LibraryClasses.common.UEFI_DRIVER,LibraryClasses.common.UEFI_APPLICATION]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+
+################################################################################
+#
+# Pcd Section - list of all EDK II PCD Entries defined by this Platform.
+#
+################################################################################
+[PcdsFeatureFlag]
+!if $(TARGET) == DEBUG
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|TRUE
+!else
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|FALSE
+!endif
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseMemory|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdDxeIplSwitchToLongMode|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutGopSupport|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutUgaSupport|FALSE
+
+[PcdsFixedAtBuild]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize|0x10000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize|0x8000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVariableStoreSize|0x10000
+  #
+  # Make VariableRuntimeDxe work at emulated non-volatile variable mode.
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvModeEnable|TRUE
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVpdBaseAddress|0x0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdUse1GPageTable|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdBootManagerMenuFile|{ 0x21, 0xaa, 0x2c, 0x46, 0x14, 0x76, 0x03, 0x45, 0x83, 0x6e, 0x8a, 0xb6, 0xf4, 0x66, 0x23, 0x31 }
+
+  gEfiMdePkgTokenSpaceGuid.PcdPciExpressBaseAddress|$(PCIE_BASE)
+
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiSourceLevelDebugPkgTokenSpaceGuid.PcdDebugLoadImageMethod|0x2
+!endif
+
+[PcdsPatchableInModule.common]
+  gEfiMdePkgTokenSpaceGuid.PcdReportStatusCodePropertyMask|0x7
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPrintErrorLevel|0x8000004F
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x17
+!else
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x2F
+!endif
+
+  #
+  # The following parameters are set by Library/PlatformHookLib
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase|0x3f8
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate|$(BAUD_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride|1
+
+  #
+  # Enable these parameters to be set on the command line
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate|$(SERIAL_CLOCK_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialLineControl|$(SERIAL_LINE_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseHardwareFlowControl|$(SERIAL_HARDWARE_FLOW_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialDetectCable|$(SERIAL_DETECT_CABLE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialFifoControl|$(SERIAL_FIFO_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialExtendedTxFifoSize|$(SERIAL_EXTENDED_TX_FIFO_SIZE)
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciDisableBusEnumeration|TRUE
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate|$(UART_DEFAULT_BAUD_RATE)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultDataBits|$(UART_DEFAULT_DATA_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultParity|$(UART_DEFAULT_PARITY)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultStopBits|$(UART_DEFAULT_STOP_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdDefaultTerminalType|$(DEFAULT_TERMINAL_TYPE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciSerialParameters|$(PCI_SERIAL_PARAMETERS)
+
+  gUefiCpuPkgTokenSpaceGuid.PcdCpuMaxLogicalProcessorNumber|$(MAX_LOGICAL_PROCESSORS)
+
+
+################################################################################
+#
+# Pcd Dynamic Section - list of all EDK II PCD Entries defined by this Platform
+#
+################################################################################
+
+[PcdsDynamicDefault]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvStoreReserved|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase|0
+  gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut|3
+
+  ## This PCD defines the video horizontal resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution|0
+  ## This PCD defines the video vertical resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution|0
+
+  ## The PCD is used to specify the video horizontal resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution|0
+  ## The PCD is used to specify the video vertical resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution|0
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow|31
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn|100
+
+################################################################################
+#
+# Components Section - list of all EDK II Modules needed by this Platform.
+#
+################################################################################
+[Components.IA32]
+  #
+  # SEC Core
+  #
+  UefiPayloadPkg/SecCore/SecCore.inf
+
+  #
+  # PEI Core
+  #
+  MdeModulePkg/Core/Pei/PeiMain.inf
+
+  #
+  # PEIM
+  #
+  MdeModulePkg/Universal/PCD/Pei/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+  MdeModulePkg/Universal/ReportStatusCodeRouter/Pei/ReportStatusCodeRouterPei.inf
+  MdeModulePkg/Universal/StatusCodeHandler/Pei/StatusCodeHandlerPei.inf
+
+  UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
+  MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf
+
+[Components.X64]
+  #
+  # DXE Core
+  #
+  MdeModulePkg/Core/Dxe/DxeMain.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf
+  }
+
+  #
+  # Components that produce the architectural protocols
+  #
+  MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf
+  UefiCpuPkg/CpuDxe/CpuDxe.inf
+  MdeModulePkg/Universal/BdsDxe/BdsDxe.inf
+  MdeModulePkg/Application/UiApp/UiApp.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/DeviceManagerUiLib/DeviceManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootManagerUiLib/BootManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootMaintenanceManagerUiLib/BootMaintenanceManagerUiLib.inf
+  }
+
+  PcAtChipsetPkg/HpetTimerDxe/HpetTimerDxe.inf
+  MdeModulePkg/Universal/Metronome/Metronome.inf
+  MdeModulePkg/Universal/WatchdogTimerDxe/WatchdogTimer.inf
+  MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf
+  MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
+  MdeModulePkg/Universal/MonotonicCounterRuntimeDxe/MonotonicCounterRuntimeDxe.inf
+  MdeModulePkg/Universal/ResetSystemRuntimeDxe/ResetSystemRuntimeDxe.inf
+  PcAtChipsetPkg/PcatRealTimeClockRuntimeDxe/PcatRealTimeClockRuntimeDxe.inf
+  MdeModulePkg/Universal/Variable/RuntimeDxe/VariableRuntimeDxe.inf
+
+  #
+  # Following are the DXE drivers
+  #
+  MdeModulePkg/Universal/PCD/Dxe/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+
+  MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+  MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+  UefiCpuPkg/CpuIo2Dxe/CpuIo2Dxe.inf
+  MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf
+  MdeModulePkg/Universal/MemoryTest/NullMemoryTestDxe/NullMemoryTestDxe.inf
+  PcAtChipsetPkg/8259InterruptControllerDxe/8259.inf
+  MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf
+  MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf
+  MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf
+
+  UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
+
+  #
+  # SMBIOS Support
+  #
+  MdeModulePkg/Universal/SmbiosDxe/SmbiosDxe.inf
+
+  #
+  # ACPI Support
+  #
+  MdeModulePkg/Universal/Acpi/AcpiTableDxe/AcpiTableDxe.inf
+
+  #
+  # PCI Support
+  #
+  MdeModulePkg/Bus/Pci/PciBusDxe/PciBusDxe.inf
+  MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf {
+    <LibraryClasses>
+      PciHostBridgeLib|UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
+  }
+
+  #
+  # SCSI/ATA/IDE/DISK Support
+  #
+  MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf
+  MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf
+  MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf
+  FatPkg/EnhancedFatDxe/Fat.inf
+  MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf
+  MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf
+  MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf
+  MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf
+  MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf
+
+  #
+  # SD/eMMC Support
+  #
+  MdeModulePkg/Bus/Pci/SdMmcPciHcDxe/SdMmcPciHcDxe.inf
+  MdeModulePkg/Bus/Sd/EmmcDxe/EmmcDxe.inf
+  MdeModulePkg/Bus/Sd/SdDxe/SdDxe.inf
+
+  #
+  # Usb Support
+  #
+  MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf
+  MdeModulePkg/Bus/Pci/EhciDxe/EhciDxe.inf
+  MdeModulePkg/Bus/Pci/XhciDxe/XhciDxe.inf
+  MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBusDxe.inf
+  MdeModulePkg/Bus/Usb/UsbKbDxe/UsbKbDxe.inf
+  MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassStorageDxe.inf
+
+  #
+  # ISA Support
+  #
+  MdeModulePkg/Universal/SerialDxe/SerialDxe.inf
+
+  #
+  # Console Support
+  #
+  MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
+  MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf
+  MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf
+  MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf
+  UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
+
+  #------------------------------
+  #  Build the shell
+  #------------------------------
+
+!if $(SHELL_TYPE) == BUILD_SHELL
+
+  #
+  # Shell Lib
+  #
+[LibraryClasses]
+  BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  FileHandleLib|MdePkg/Library/UefiFileHandleLib/UefiFileHandleLib.inf
+  ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf
+  NetLib|MdeModulePkg/Library/DxeNetLib/DxeNetLib.inf
+
+[Components.X64]
+  ShellPkg/DynamicCommand/TftpDynamicCommand/TftpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/DynamicCommand/DpDynamicCommand/DpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/Application/Shell/Shell.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the shell application itself only.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+
+    #------------------------------
+    #  Basic commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
+
+    #------------------------------
+    #  Networking commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
+
+    #------------------------------
+    #  Support libraries
+    #------------------------------
+
+    <LibraryClasses>
+      DebugLib|MdePkg/Library/UefiDebugLibConOut/UefiDebugLibConOut.inf
+      DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+      HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf
+      PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+      ShellCEntryLib|ShellPkg/Library/UefiShellCEntryLib/UefiShellCEntryLib.inf
+      ShellCommandLib|ShellPkg/Library/UefiShellCommandLib/UefiShellCommandLib.inf
+      SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+  }
+
+!endif
-- 
2.16.2.windows.1


^ permalink raw reply related	[flat|nested] 9+ messages in thread
* [PATCH] UefiPayloadPkg: Enhance UEFI payload for coreboot and Slim Bootloader
@ 2019-03-29  0:33 Guo Dong
  2019-03-29  5:15 ` Ni, Ray
  2019-04-03 14:13 ` Ma, Maurice
  0 siblings, 2 replies; 9+ messages in thread
From: Guo Dong @ 2019-03-29  0:33 UTC (permalink / raw)
  To: edk2-devel

CorebootModulePkg and CorebootPayloadPkg originally supports coreboot only.
In order to support other bootloaders, such as Slim Bootloader, they need
be updated to be more generic.
UEFI Payload (UefiPayloadPkg) a converged package from CorebootModulePkg
and CorebootPayloadPkg with following updates:
a. Support both coreboot and Slim Bootloader
b. Removed SataControllerDxe and BaseSerialPortLib16550 to use EDK2 modules
c. Support passing bootloader parameter to UEFI payload, e.g. coreboot
   table from coreboot or HOB list from Slim Bootloader
d. Using GraphicsOutputDxe from EDK2 with minor change instead of FbGop
e. Remove the dependency to IntelFrameworkPkg and IntelFrameworkModulePkg
   and QuarkSocPkg
f. Use BaseDebugLibSerialPort library as DebugLib
g. Use HPET timer, drop legacy 8254 timer support
h. Use BaseXApicX2ApicLib instead of BaseXApicLib
i. Other clean ups

On how UefiPayloadPkg could work with coreboot/Slim Bootloader, please
refer UefiPayloadPkg/BuildAndIntegrationInstructions.txt

Once UefiPayloadPkg is checked-in, CorebootModulePkg and CorebootPayloadPkg
could be retired.

Contributed-under: TianoCore Contribution Agreement 1.1
Signed-off-by: Guo Dong <guo.dong@intel.com>
---
 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c                               | 164 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h                               |  36 ++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf                             |  63 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/BlSupportPei/BlSupportPei.c                               | 592 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/BlSupportPei/BlSupportPei.h                               |  46 ++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/BlSupportPei/BlSupportPei.inf                             |  79 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/BuildAndIntegrationInstructions.txt                       |  82 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c                         | 190 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c                        | 745 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h                        |  59 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf                   |  58 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Coreboot.h                                        | 255 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h                          |  35 +++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Guid/FrameBufferInfoGuid.h                        |  42 ++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h                          |  42 ++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h                         |  37 +++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h                        |  32 ++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Library/BlParseLib.h                              | 111 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Include/Library/PlatformSupportLib.h                      |  34 ++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c                       | 276 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf                     |  46 ++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/CbParseLib/CbParseLib.c                           | 543 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf                         |  45 +++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h                  |  86 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c               | 228 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf             |  47 +++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c           | 590 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c      | 271 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h      | 138 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf |  77 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c          | 605 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h          |  76 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c             |  45 +++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c                 | 104 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf               |  44 ++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c   |  35 +++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf |  34 ++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c                   | 177 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf                 |  46 ++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/SblParseLib/SblParseLib.c                         | 202 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf                       |  51 +++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/SecCore/FindPeiCore.c                                     | 199 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm                                |  84 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/SecCore/Ia32/Stack.nasm                                   |  78 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/SecCore/SecCore.inf                                       |  63 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/SecCore/SecMain.c                                         | 294 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/SecCore/SecMain.h                                         | 137 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/UefiPayloadPkg.dec                                        |  78 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/UefiPayloadPkg.fdf                                        | 297 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/UefiPayloadPkgIa32.dsc                                    | 579 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc                                 | 580 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 51 files changed, 8857 insertions(+)

diff --git a/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c
new file mode 100644
index 0000000000..6b733c66b4
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.c
@@ -0,0 +1,164 @@
+/** @file
+  This driver will report some MMIO/IO resources to dxe core, extract smbios and acpi
+  tables from bootloader.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+#include "BlSupportDxe.h"
+
+/**
+  Reserve MMIO/IO resource in GCD
+
+  @param  IsMMIO        Flag of whether it is mmio resource or io resource.
+  @param  GcdType       Type of the space.
+  @param  BaseAddress   Base address of the space.
+  @param  Length        Length of the space.
+  @param  Alignment     Align with 2^Alignment
+  @param  ImageHandle   Handle for the image of this driver.
+
+  @retval EFI_SUCCESS   Reserve successful
+**/
+EFI_STATUS
+ReserveResourceInGcd (
+  IN BOOLEAN               IsMMIO,
+  IN UINTN                 GcdType,
+  IN EFI_PHYSICAL_ADDRESS  BaseAddress,
+  IN UINT64                Length,
+  IN UINTN                 Alignment,
+  IN EFI_HANDLE            ImageHandle
+  )
+{
+  EFI_STATUS               Status;
+
+  if (IsMMIO) {
+    Status = gDS->AddMemorySpace (
+                    GcdType,
+                    BaseAddress,
+                    Length,
+                    EFI_MEMORY_UC
+                    );
+    if (EFI_ERROR (Status)) {
+      DEBUG ((
+        DEBUG_ERROR,
+        "Failed to add memory space :0x%lx 0x%lx\n",
+        BaseAddress,
+        Length
+        ));
+    }
+    ASSERT_EFI_ERROR (Status);
+    Status = gDS->AllocateMemorySpace (
+                    EfiGcdAllocateAddress,
+                    GcdType,
+                    Alignment,
+                    Length,
+                    &BaseAddress,
+                    ImageHandle,
+                    NULL
+                    );
+    ASSERT_EFI_ERROR (Status);
+  } else {
+    Status = gDS->AddIoSpace (
+                    GcdType,
+                    BaseAddress,
+                    Length
+                    );
+    ASSERT_EFI_ERROR (Status);
+    Status = gDS->AllocateIoSpace (
+                    EfiGcdAllocateAddress,
+                    GcdType,
+                    Alignment,
+                    Length,
+                    &BaseAddress,
+                    ImageHandle,
+                    NULL
+                    );
+    ASSERT_EFI_ERROR (Status);
+  }
+  return Status;
+}
+
+
+/**
+  Main entry for the bootloader support DXE module.
+
+  @param[in] ImageHandle    The firmware allocated handle for the EFI image.
+  @param[in] SystemTable    A pointer to the EFI System Table.
+
+  @retval EFI_SUCCESS       The entry point is executed successfully.
+  @retval other             Some error occurs when executing this entry point.
+
+**/
+EFI_STATUS
+EFIAPI
+BlDxeEntryPoint (
+  IN EFI_HANDLE         ImageHandle,
+  IN EFI_SYSTEM_TABLE   *SystemTable
+  )
+{
+  EFI_STATUS Status;
+  EFI_HOB_GUID_TYPE  *GuidHob;
+  SYSTEM_TABLE_INFO  *pSystemTableInfo;
+  FRAME_BUFFER_INFO  *FbInfo;
+
+  Status = EFI_SUCCESS;
+  //
+  // Report MMIO/IO Resources
+  //
+  Status = ReserveResourceInGcd (TRUE, EfiGcdMemoryTypeMemoryMappedIo, 0xFEC00000, SIZE_4KB, 0, SystemTable); // IOAPIC
+  ASSERT_EFI_ERROR (Status);
+
+  Status = ReserveResourceInGcd (TRUE, EfiGcdMemoryTypeMemoryMappedIo, 0xFED00000, SIZE_1KB, 0, SystemTable); // HPET
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Find the system table information guid hob
+  //
+  GuidHob = GetFirstGuidHob (&gUefiSystemTableInfoGuid);
+  ASSERT (GuidHob != NULL);
+  pSystemTableInfo = (SYSTEM_TABLE_INFO *)GET_GUID_HOB_DATA (GuidHob);
+
+  //
+  // Install Acpi Table
+  //
+  if (pSystemTableInfo->AcpiTableBase != 0 && pSystemTableInfo->AcpiTableSize != 0) {
+    DEBUG ((DEBUG_ERROR, "Install Acpi Table at 0x%lx, length 0x%x\n", pSystemTableInfo->AcpiTableBase, pSystemTableInfo->AcpiTableSize));
+    Status = gBS->InstallConfigurationTable (&gEfiAcpiTableGuid, (VOID *)(UINTN)pSystemTableInfo->AcpiTableBase);
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  //
+  // Install Smbios Table
+  //
+  if (pSystemTableInfo->SmbiosTableBase != 0 && pSystemTableInfo->SmbiosTableSize != 0) {
+    DEBUG ((DEBUG_ERROR, "Install Smbios Table at 0x%lx, length 0x%x\n", pSystemTableInfo->SmbiosTableBase, pSystemTableInfo->SmbiosTableSize));
+    Status = gBS->InstallConfigurationTable (&gEfiSmbiosTableGuid, (VOID *)(UINTN)pSystemTableInfo->SmbiosTableBase);
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  //
+  // Find the frame buffer information and update PCDs
+  //
+  GuidHob = GetFirstGuidHob (&gUefiFrameBufferInfoGuid);
+  if (GuidHob != NULL) {
+    FbInfo  = (FRAME_BUFFER_INFO *)GET_GUID_HOB_DATA (GuidHob);
+    Status = PcdSet32S (PcdVideoHorizontalResolution, FbInfo->HorizontalResolution);
+    ASSERT_EFI_ERROR (Status);
+    Status = PcdSet32S (PcdVideoVerticalResolution, FbInfo->VerticalResolution);
+    ASSERT_EFI_ERROR (Status);
+    Status = PcdSet32S (PcdSetupVideoHorizontalResolution, FbInfo->HorizontalResolution);
+    ASSERT_EFI_ERROR (Status);
+    Status = PcdSet32S (PcdSetupVideoVerticalResolution, FbInfo->VerticalResolution);
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h
new file mode 100644
index 0000000000..55e1eb7759
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.h
@@ -0,0 +1,36 @@
+/** @file
+  The header file of bootloader support DXE.
+
+Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+#ifndef __DXE_BOOTLOADER_SUPPORT_H__
+#define __DXE_BOOTLOADER_SUPPORT_H__
+
+#include <PiDxe.h>
+
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/DxeServicesTableLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+
+#include <Guid/Acpi.h>
+#include <Guid/SmBios.h>
+#include <Guid/SystemTableInfoGuid.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+#include <Guid/FrameBufferInfoGuid.h>
+
+#include <IndustryStandard/Acpi.h>
+
+#endif
diff --git a/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
new file mode 100644
index 0000000000..b0be831432
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
@@ -0,0 +1,63 @@
+## @file
+# Bootloader Support DXE Module
+#
+# Report some MMIO/IO resources to dxe core, extract smbios and acpi tables
+#
+#  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+#
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution. The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php.
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = BlSupportDxe
+  FILE_GUID                      = C68DAA4E-7AB5-41e8-A91D-5954421053F3
+  MODULE_TYPE                    = DXE_DRIVER
+  VERSION_STRING                 = 1.0
+  ENTRY_POINT                    = BlDxeEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  BlSupportDxe.c
+  BlSupportDxe.h
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  UefiDriverEntryPoint
+  UefiBootServicesTableLib
+  DxeServicesTableLib
+  DebugLib
+  BaseMemoryLib
+  UefiLib
+  HobLib
+
+[Guids]
+  gEfiAcpiTableGuid
+  gEfiSmbiosTableGuid
+  gUefiSystemTableInfoGuid
+  gUefiAcpiBoardInfoGuid
+  gUefiFrameBufferInfoGuid
+
+[Pcd]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution
+
+[Depex]
+  TRUE
diff --git a/UefiPayloadPkg/BlSupportPei/BlSupportPei.c b/UefiPayloadPkg/BlSupportPei/BlSupportPei.c
new file mode 100644
index 0000000000..9045175aec
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportPei/BlSupportPei.c
@@ -0,0 +1,592 @@
+/** @file
+  This PEIM will parse bootloader information and report resource information into pei core.
+  This file contains the main entrypoint of the PEIM.
+
+Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+#include "BlSupportPei.h"
+
+#define LEGACY_8259_MASK_REGISTER_MASTER  0x21
+#define LEGACY_8259_MASK_REGISTER_SLAVE   0xA1
+
+EFI_MEMORY_TYPE_INFORMATION mDefaultMemoryTypeInformation[] = {
+  { EfiACPIReclaimMemory,   FixedPcdGet32 (PcdMemoryTypeEfiACPIReclaimMemory) },
+  { EfiACPIMemoryNVS,       FixedPcdGet32 (PcdMemoryTypeEfiACPIMemoryNVS) },
+  { EfiReservedMemoryType,  FixedPcdGet32 (PcdMemoryTypeEfiReservedMemoryType) },
+  { EfiRuntimeServicesData, FixedPcdGet32 (PcdMemoryTypeEfiRuntimeServicesData) },
+  { EfiRuntimeServicesCode, FixedPcdGet32 (PcdMemoryTypeEfiRuntimeServicesCode) },
+  { EfiMaxMemoryType,       0     }
+};
+
+EFI_PEI_PPI_DESCRIPTOR   mPpiBootMode[] = {
+  {
+    EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST,
+    &gEfiPeiMasterBootModePpiGuid,
+    NULL
+  }
+};
+
+EFI_PEI_GRAPHICS_DEVICE_INFO_HOB mDefaultGraphicsDeviceInfo = {
+  MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT8,  MAX_UINT8
+};
+
+/**
+  Create memory mapped io resource hob.
+
+  @param  MmioBase    Base address of the memory mapped io range
+  @param  MmioSize    Length of the memory mapped io range
+
+**/
+VOID
+BuildMemoryMappedIoRangeHob (
+  EFI_PHYSICAL_ADDRESS        MmioBase,
+  UINT64                      MmioSize
+  )
+{
+  BuildResourceDescriptorHob (
+    EFI_RESOURCE_MEMORY_MAPPED_IO,
+    (EFI_RESOURCE_ATTRIBUTE_PRESENT    |
+    EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+    EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_TESTED),
+    MmioBase,
+    MmioSize
+    );
+
+  BuildMemoryAllocationHob (
+    MmioBase,
+    MmioSize,
+    EfiMemoryMappedIO
+    );
+}
+
+/**
+  Check the integrity of firmware volume header
+
+  @param[in]  FwVolHeader   A pointer to a firmware volume header
+
+  @retval     TRUE          The firmware volume is consistent
+  @retval     FALSE         The firmware volume has corrupted.
+
+**/
+STATIC
+BOOLEAN
+IsFvHeaderValid (
+  IN EFI_FIRMWARE_VOLUME_HEADER    *FwVolHeader
+  )
+{
+  UINT16 Checksum;
+
+  // Skip nv storage fv
+  if (CompareMem (&FwVolHeader->FileSystemGuid, &gEfiFirmwareFileSystem2Guid, sizeof(EFI_GUID)) != 0 ) {
+    return FALSE;
+  }
+
+  if ( (FwVolHeader->Revision != EFI_FVH_REVISION)   ||
+     (FwVolHeader->Signature != EFI_FVH_SIGNATURE) ||
+     (FwVolHeader->FvLength == ((UINTN) -1))       ||
+     ((FwVolHeader->HeaderLength & 0x01 ) !=0) )  {
+    return FALSE;
+  }
+
+  Checksum = CalculateCheckSum16 ((UINT16 *) FwVolHeader, FwVolHeader->HeaderLength);
+  if (Checksum != 0) {
+    DEBUG (( DEBUG_ERROR,
+              "ERROR - Invalid Firmware Volume Header Checksum, change 0x%04x to 0x%04x\r\n",
+              FwVolHeader->Checksum,
+              (UINT16)( Checksum + FwVolHeader->Checksum )));
+    return TRUE; //FALSE; Need update UEFI build tool when patching entrypoin @start of fd.
+  }
+
+  return TRUE;
+}
+
+/**
+  Install FvInfo PPI and create fv hobs for remained fvs
+
+**/
+VOID
+PeiReportRemainedFvs (
+  VOID
+  )
+{
+  UINT8*  TempPtr;
+  UINT8*  EndPtr;
+
+  TempPtr = (UINT8* )(UINTN) PcdGet32 (PcdPayloadFdMemBase);
+  EndPtr = (UINT8* )(UINTN) (PcdGet32 (PcdPayloadFdMemBase) + PcdGet32 (PcdPayloadFdMemSize));
+
+  for (;TempPtr < EndPtr;) {
+    if (IsFvHeaderValid ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)) {
+      if (TempPtr != (UINT8* )(UINTN) PcdGet32 (PcdPayloadFdMemBase))  {
+        // Skip the PEI FV
+        DEBUG((DEBUG_INFO, "Found one valid fv : 0x%lx.\n", TempPtr, ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength));
+
+        PeiServicesInstallFvInfoPpi (
+          NULL,
+          (VOID *) (UINTN) TempPtr,
+          (UINT32) (UINTN) ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength,
+          NULL,
+          NULL
+          );
+        BuildFvHob ((EFI_PHYSICAL_ADDRESS)(UINTN) TempPtr, ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength);
+      }
+    }
+    TempPtr += ((EFI_FIRMWARE_VOLUME_HEADER* )TempPtr)->FvLength;
+  }
+}
+
+
+/**
+  Find the board related info from ACPI table
+
+  @param  AcpiTableBase          ACPI table start address in memory
+  @param  AcpiBoardInfo          Pointer to the acpi board info strucutre
+
+  @retval RETURN_SUCCESS     Successfully find out all the required information.
+  @retval RETURN_NOT_FOUND   Failed to find the required info.
+
+**/
+RETURN_STATUS
+ParseAcpiInfo (
+  IN   UINT64                                   AcpiTableBase,
+  OUT  ACPI_BOARD_INFO                          *AcpiBoardInfo
+  )
+{
+  EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER  *Rsdp;
+  EFI_ACPI_DESCRIPTION_HEADER                   *Rsdt;
+  UINT32                                        *Entry32;
+  UINTN                                         Entry32Num;
+  EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE     *Fadt;
+  EFI_ACPI_DESCRIPTION_HEADER                   *Xsdt;
+  UINT64                                        *Entry64;
+  UINTN                                         Entry64Num;
+  UINTN                                         Idx;
+  EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_BASE_ADDRESS_TABLE_HEADER *MmCfgHdr;
+  EFI_ACPI_MEMORY_MAPPED_ENHANCED_CONFIGURATION_SPACE_BASE_ADDRESS_ALLOCATION_STRUCTURE *MmCfgBase;
+
+  Rsdp = (EFI_ACPI_3_0_ROOT_SYSTEM_DESCRIPTION_POINTER *)(UINTN)AcpiTableBase;
+  DEBUG ((DEBUG_INFO, "Rsdp at 0x%p\n", Rsdp));
+  DEBUG ((DEBUG_INFO, "Rsdt at 0x%x, Xsdt at 0x%lx\n", Rsdp->RsdtAddress, Rsdp->XsdtAddress));
+
+  //
+  // Search Rsdt First
+  //
+  Fadt     = NULL;
+  MmCfgHdr = NULL;
+  Rsdt     = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN)(Rsdp->RsdtAddress);
+  if (Rsdt != NULL) {
+    Entry32  = (UINT32 *)(Rsdt + 1);
+    Entry32Num = (Rsdt->Length - sizeof(EFI_ACPI_DESCRIPTION_HEADER)) >> 2;
+    for (Idx = 0; Idx < Entry32Num; Idx++) {
+      if (*(UINT32 *)(UINTN)(Entry32[Idx]) == EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE) {
+        Fadt = (EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE *)(UINTN)(Entry32[Idx]);
+        DEBUG ((DEBUG_INFO, "Found Fadt in Rsdt\n"));
+      }
+
+      if (*(UINT32 *)(UINTN)(Entry32[Idx]) == EFI_ACPI_5_0_PCI_EXPRESS_MEMORY_MAPPED_CONFIGURATION_SPACE_BASE_ADDRESS_DESCRIPTION_TABLE_SIGNATURE) {
+        MmCfgHdr = (EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_BASE_ADDRESS_TABLE_HEADER *)(UINTN)(Entry32[Idx]);
+        DEBUG ((DEBUG_INFO, "Found MM config address in Rsdt\n"));
+      }
+
+      if ((Fadt != NULL) && (MmCfgHdr != NULL)) {
+        goto Done;
+      }
+    }
+  }
+
+  //
+  // Search Xsdt Second
+  //
+  Xsdt     = (EFI_ACPI_DESCRIPTION_HEADER *)(UINTN)(Rsdp->XsdtAddress);
+  if (Xsdt != NULL) {
+    Entry64  = (UINT64 *)(Xsdt + 1);
+    Entry64Num = (Xsdt->Length - sizeof(EFI_ACPI_DESCRIPTION_HEADER)) >> 3;
+    for (Idx = 0; Idx < Entry64Num; Idx++) {
+      if (*(UINT32 *)(UINTN)(Entry64[Idx]) == EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE_SIGNATURE) {
+        Fadt = (EFI_ACPI_3_0_FIXED_ACPI_DESCRIPTION_TABLE *)(UINTN)(Entry64[Idx]);
+        DEBUG ((DEBUG_INFO, "Found Fadt in Xsdt\n"));
+      }
+
+      if (*(UINT32 *)(UINTN)(Entry64[Idx]) == EFI_ACPI_5_0_PCI_EXPRESS_MEMORY_MAPPED_CONFIGURATION_SPACE_BASE_ADDRESS_DESCRIPTION_TABLE_SIGNATURE) {
+        MmCfgHdr = (EFI_ACPI_MEMORY_MAPPED_CONFIGURATION_BASE_ADDRESS_TABLE_HEADER *)(UINTN)(Entry32[Idx]);
+        DEBUG ((DEBUG_INFO, "Found MM config address in Xsdt\n"));
+      }
+
+      if ((Fadt != NULL) && (MmCfgHdr != NULL)) {
+        goto Done;
+      }
+    }
+  }
+
+  if (Fadt == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+Done:
+
+  AcpiBoardInfo->PmCtrlRegBase   = Fadt->Pm1aCntBlk;
+  AcpiBoardInfo->PmTimerRegBase  = Fadt->PmTmrBlk;
+  AcpiBoardInfo->ResetRegAddress = Fadt->ResetReg.Address;
+  AcpiBoardInfo->ResetValue      = Fadt->ResetValue;
+  AcpiBoardInfo->PmEvtBase       = Fadt->Pm1aEvtBlk;
+  AcpiBoardInfo->PmGpeEnBase     = Fadt->Gpe0Blk + Fadt->Gpe0BlkLen / 2;
+
+  if (MmCfgHdr != NULL) {
+    MmCfgBase = (EFI_ACPI_MEMORY_MAPPED_ENHANCED_CONFIGURATION_SPACE_BASE_ADDRESS_ALLOCATION_STRUCTURE *)((UINT8*) MmCfgHdr + sizeof (*MmCfgHdr));
+    AcpiBoardInfo->PcieBaseAddress = MmCfgBase->BaseAddress;
+  } else {
+    AcpiBoardInfo->PcieBaseAddress = 0;
+  }
+  DEBUG ((DEBUG_INFO, "PmCtrl  Reg 0x%lx\n",  AcpiBoardInfo->PmCtrlRegBase));
+  DEBUG ((DEBUG_INFO, "PmTimer Reg 0x%lx\n",  AcpiBoardInfo->PmTimerRegBase));
+  DEBUG ((DEBUG_INFO, "Reset   Reg 0x%lx\n",  AcpiBoardInfo->ResetRegAddress));
+  DEBUG ((DEBUG_INFO, "Reset   Value 0x%x\n", AcpiBoardInfo->ResetValue));
+  DEBUG ((DEBUG_INFO, "PmEvt   Reg 0x%lx\n",  AcpiBoardInfo->PmEvtBase));
+  DEBUG ((DEBUG_INFO, "PmGpeEn Reg 0x%lx\n",  AcpiBoardInfo->PmGpeEnBase));
+  DEBUG ((DEBUG_INFO, "PcieBaseAddr 0x%lx\n", AcpiBoardInfo->PcieBaseAddress));
+
+  //
+  // Verify values for proper operation
+  //
+  ASSERT(Fadt->Pm1aCntBlk != 0);
+  ASSERT(Fadt->PmTmrBlk != 0);
+  ASSERT(Fadt->ResetReg.Address != 0);
+  ASSERT(Fadt->Pm1aEvtBlk != 0);
+  ASSERT(Fadt->Gpe0Blk != 0);
+
+  DEBUG_CODE_BEGIN ();
+    BOOLEAN    SciEnabled;
+
+    //
+    // Check the consistency of SCI enabling
+    //
+
+    //
+    // Get SCI_EN value
+    //
+   if (Fadt->Pm1CntLen == 4) {
+      SciEnabled = (IoRead32 (Fadt->Pm1aCntBlk) & BIT0)? TRUE : FALSE;
+    } else {
+      //
+      // if (Pm1CntLen == 2), use 16 bit IO read;
+      // if (Pm1CntLen != 2 && Pm1CntLen != 4), use 16 bit IO read as a fallback
+      //
+      SciEnabled = (IoRead16 (Fadt->Pm1aCntBlk) & BIT0)? TRUE : FALSE;
+    }
+
+    if (!(Fadt->Flags & EFI_ACPI_5_0_HW_REDUCED_ACPI) &&
+        (Fadt->SmiCmd == 0) &&
+       !SciEnabled) {
+      //
+      // The ACPI enabling status is inconsistent: SCI is not enabled but ACPI
+      // table does not provide a means to enable it through FADT->SmiCmd
+      //
+      DEBUG ((DEBUG_ERROR, "ERROR: The ACPI enabling status is inconsistent: SCI is not"
+        " enabled but the ACPI table does not provide a means to enable it through FADT->SmiCmd."
+        " This may cause issues in OS.\n"));
+    }
+  DEBUG_CODE_END ();
+
+  return RETURN_SUCCESS;
+}
+
+EFI_STATUS
+MemInfoCallback (
+  IN MEMROY_MAP_ENTRY             *MemoryMapEntry,
+  IN VOID                         *Params
+  )
+{
+  PAYLOAD_MEM_INFO        *MemInfo;
+  UINTN                   Attribue;
+  EFI_PHYSICAL_ADDRESS    Base;
+  EFI_RESOURCE_TYPE       Type;
+  UINT64                  Size;
+  UINT32                  SystemLowMemTop;
+
+  Attribue = EFI_RESOURCE_ATTRIBUTE_PRESENT |
+             EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+             EFI_RESOURCE_ATTRIBUTE_TESTED |
+             EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+             EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE |
+             EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE |
+             EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE;
+
+  MemInfo = (PAYLOAD_MEM_INFO *)Params;
+  Type    = (MemoryMapEntry->Type == 1) ? EFI_RESOURCE_SYSTEM_MEMORY : EFI_RESOURCE_MEMORY_RESERVED;
+  Base    = MemoryMapEntry->Base;
+  Size    = MemoryMapEntry->Size;
+
+  if ((Base  < 0x100000) && ((Base + Size) > 0x100000)) {
+    Size -= (0x100000 - Base);
+    Base  = 0x100000;
+  }
+
+  if (Base >= 0x100000) {
+    if (Type == EFI_RESOURCE_SYSTEM_MEMORY) {
+      if (Base < 0x100000000ULL) {
+        MemInfo->UsableLowMemTop = (UINT32)(Base + Size);
+      } else {
+        Attribue &= ~EFI_RESOURCE_ATTRIBUTE_TESTED;
+      }
+      BuildResourceDescriptorHob (
+        EFI_RESOURCE_SYSTEM_MEMORY,
+        Attribue,
+        (EFI_PHYSICAL_ADDRESS)Base,
+        Size
+        );
+    } else if (Type == EFI_RESOURCE_MEMORY_RESERVED) {
+      BuildResourceDescriptorHob (
+        EFI_RESOURCE_MEMORY_RESERVED,
+        Attribue,
+        (EFI_PHYSICAL_ADDRESS)Base,
+        Size
+        );
+      if (Base < 0x100000000ULL) {
+        SystemLowMemTop = ((UINT32)(Base + Size) + 0x0FFFFFFF) & 0xF0000000;
+        if (SystemLowMemTop > MemInfo->SystemLowMemTop) {
+          MemInfo->SystemLowMemTop = SystemLowMemTop;
+        }
+      }
+    }
+  }
+
+  return EFI_SUCCESS;
+}
+
+/**
+  This is the entrypoint of PEIM
+
+  @param  FileHandle  Handle of the file being invoked.
+  @param  PeiServices Describes the list of possible PEI Services.
+
+  @retval EFI_SUCCESS if it completed successfully.
+**/
+EFI_STATUS
+EFIAPI
+BlPeiEntryPoint (
+  IN       EFI_PEI_FILE_HANDLE  FileHandle,
+  IN CONST EFI_PEI_SERVICES     **PeiServices
+  )
+{
+  EFI_STATUS           Status;
+  UINT64               LowMemorySize;
+  UINT64               PeiMemSize = SIZE_64MB;   // 64 MB
+  EFI_PHYSICAL_ADDRESS PeiMemBase = 0;
+  UINT32               RegEax;
+  UINT8                PhysicalAddressBits;
+  PAYLOAD_MEM_INFO     PldMemInfo;
+  SYSTEM_TABLE_INFO    SysTableInfo;
+  SYSTEM_TABLE_INFO    *NewSysTableInfo;
+  ACPI_BOARD_INFO      AcpiBoardInfo;
+  ACPI_BOARD_INFO      *NewAcpiBoardInfo;
+  FRAME_BUFFER_INFO    FbInfo;
+  FRAME_BUFFER_INFO    *NewFbInfo;
+  EFI_GRAPHICS_OUTPUT_MODE_INFORMATION  *GfxMode;
+  EFI_PEI_GRAPHICS_INFO_HOB             *EfiGfxInfo;
+
+  //
+  // Report lower 640KB of RAM. Attribute EFI_RESOURCE_ATTRIBUTE_TESTED
+  // is intentionally omitted to prevent erasing of the coreboot header
+  // record before it is processed by ParseMemoryInfo.
+  //
+  BuildResourceDescriptorHob (
+    EFI_RESOURCE_SYSTEM_MEMORY,
+    (
+    EFI_RESOURCE_ATTRIBUTE_PRESENT |
+    EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+    EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
+    ),
+    (EFI_PHYSICAL_ADDRESS)(0),
+    (UINT64)(0xA0000)
+    );
+
+  BuildResourceDescriptorHob (
+    EFI_RESOURCE_MEMORY_RESERVED,
+    (
+    EFI_RESOURCE_ATTRIBUTE_PRESENT |
+    EFI_RESOURCE_ATTRIBUTE_INITIALIZED |
+    EFI_RESOURCE_ATTRIBUTE_TESTED |
+    EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE |
+    EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
+    ),
+    (EFI_PHYSICAL_ADDRESS)(0xA0000),
+    (UINT64)(0x60000)
+    );
+
+
+  //
+  // Parse memory info
+  //
+  ZeroMem (&PldMemInfo, sizeof(PldMemInfo));
+  Status = ParseMemoryInfo (MemInfoCallback, &PldMemInfo);
+  if (EFI_ERROR(Status)) {
+    return Status;
+  }
+
+  //
+  // Install memory
+  //
+  LowMemorySize = PldMemInfo.UsableLowMemTop;
+  PeiMemBase = (LowMemorySize - PeiMemSize) & (~(BASE_64KB - 1));
+  DEBUG ((DEBUG_INFO, "Low memory 0x%lx\n", LowMemorySize));
+  DEBUG ((DEBUG_INFO, "SystemLowMemTop 0x%x\n", PldMemInfo.SystemLowMemTop));
+  DEBUG ((DEBUG_INFO, "PeiMemBase: 0x%lx.\n", PeiMemBase));
+  DEBUG ((DEBUG_INFO, "PeiMemSize: 0x%lx.\n", PeiMemSize));
+  Status = PeiServicesInstallPeiMemory (PeiMemBase, PeiMemSize);
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Set cache on the physical memory
+  //
+  MtrrSetMemoryAttribute (BASE_1MB, LowMemorySize - BASE_1MB, CacheWriteBack);
+  MtrrSetMemoryAttribute (0, 0xA0000, CacheWriteBack);
+
+  //
+  // Create Memory Type Information HOB
+  //
+  BuildGuidDataHob (
+    &gEfiMemoryTypeInformationGuid,
+    mDefaultMemoryTypeInformation,
+    sizeof(mDefaultMemoryTypeInformation)
+    );
+
+  //
+  // Create Fv hob
+  //
+  PeiReportRemainedFvs ();
+
+  BuildMemoryAllocationHob (
+    PcdGet32 (PcdPayloadFdMemBase),
+    PcdGet32 (PcdPayloadFdMemSize),
+    EfiBootServicesData
+    );
+
+  //
+  // Build CPU memory space and IO space hob
+  //
+  AsmCpuid (0x80000000, &RegEax, NULL, NULL, NULL);
+  if (RegEax >= 0x80000008) {
+    AsmCpuid (0x80000008, &RegEax, NULL, NULL, NULL);
+    PhysicalAddressBits = (UINT8) RegEax;
+  } else {
+    PhysicalAddressBits  = 36;
+  }
+
+  //
+  // Create a CPU hand-off information
+  //
+  BuildCpuHob (PhysicalAddressBits, 16);
+
+  //
+  // Report Local APIC range
+  //
+  BuildMemoryMappedIoRangeHob (0xFEC80000, SIZE_512KB);
+
+  //
+  // Boot mode
+  //
+  Status = PeiServicesSetBootMode (BOOT_WITH_FULL_CONFIGURATION);
+  ASSERT_EFI_ERROR (Status);
+
+  Status = PeiServicesInstallPpi (mPpiBootMode);
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Create guid hob for frame buffer information
+  //
+  Status = ParseFbInfo (&FbInfo);
+  if (!EFI_ERROR (Status)) {
+    if (!((FbInfo.LinearFrameBuffer == 0)  || (FbInfo.HorizontalResolution == 0) || \
+          (FbInfo.VerticalResolution == 0) || (FbInfo.BitsPerPixel == 0) || \
+          (FbInfo.BytesPerScanLine == 0))) {
+      NewFbInfo = BuildGuidHob (&gUefiFrameBufferInfoGuid, sizeof (FRAME_BUFFER_INFO));
+      ASSERT (NewFbInfo != NULL);
+
+      CopyMem (NewFbInfo, &FbInfo, sizeof (FRAME_BUFFER_INFO));
+
+      EfiGfxInfo = BuildGuidHob (&gEfiGraphicsInfoHobGuid, sizeof (EFI_PEI_GRAPHICS_INFO_HOB));
+      ASSERT (NewFbInfo != NULL);
+      if (EfiGfxInfo != NULL) {
+        EfiGfxInfo->FrameBufferBase = FbInfo.LinearFrameBuffer;
+        EfiGfxInfo->FrameBufferSize = FbInfo.BytesPerScanLine * FbInfo.VerticalResolution;
+
+        GfxMode = &EfiGfxInfo->GraphicsMode;
+        GfxMode->Version = 0;
+        GfxMode->HorizontalResolution = FbInfo.HorizontalResolution;
+        GfxMode->VerticalResolution   = FbInfo.VerticalResolution;
+        GfxMode->PixelsPerScanLine    = (FbInfo.BytesPerScanLine << 3) / FbInfo.BitsPerPixel;
+
+        if ((FbInfo.Red.Position == 0) && (FbInfo.Green.Position == 8) && (FbInfo.Blue.Position == 16)) {
+          GfxMode->PixelFormat = PixelRedGreenBlueReserved8BitPerColor;
+        } else if ((FbInfo.Blue.Position == 0) && (FbInfo.Green.Position == 8) && (FbInfo.Red.Position == 16)) {
+          GfxMode->PixelFormat = PixelBlueGreenRedReserved8BitPerColor;
+        }
+        GfxMode->PixelInformation.RedMask      = FbInfo.Red.Mask << FbInfo.Red.Position;
+        GfxMode->PixelInformation.GreenMask    = FbInfo.Green.Mask << FbInfo.Green.Position;
+        GfxMode->PixelInformation.BlueMask     = FbInfo.Blue.Mask << FbInfo.Blue.Position;
+        GfxMode->PixelInformation.ReservedMask = FbInfo.Reserved.Mask << FbInfo.Reserved.Position;
+
+        DEBUG ((DEBUG_INFO, "Create frame buffer info guid hob\n"));
+      }
+    } else {
+      DEBUG ((DEBUG_ERROR, "Invalid Framebuffer info\n"));
+    }
+  }
+
+  //
+  // Create guid hob for system tables like acpi table and smbios table
+  //
+  Status = ParseSystemTable(&SysTableInfo);
+  ASSERT_EFI_ERROR (Status);
+  if (!EFI_ERROR (Status)) {
+    NewSysTableInfo = BuildGuidHob (&gUefiSystemTableInfoGuid, sizeof (SYSTEM_TABLE_INFO));
+    ASSERT (NewSysTableInfo != NULL);
+    CopyMem (NewSysTableInfo, &SysTableInfo, sizeof (SYSTEM_TABLE_INFO));
+    DEBUG ((DEBUG_INFO, "Detected Acpi Table at 0x%lx, length 0x%x\n", SysTableInfo.AcpiTableBase, SysTableInfo.AcpiTableSize));
+    DEBUG ((DEBUG_INFO, "Detected Smbios Table at 0x%lx, length 0x%x\n", SysTableInfo.SmbiosTableBase, SysTableInfo.SmbiosTableSize));
+  }
+
+  //
+  // Create guid hob for acpi board information
+  //
+  Status = ParseAcpiInfo (SysTableInfo.AcpiTableBase, &AcpiBoardInfo);
+  ASSERT_EFI_ERROR (Status);
+  if (!EFI_ERROR (Status)) {
+    NewAcpiBoardInfo = BuildGuidHob (&gUefiAcpiBoardInfoGuid, sizeof (ACPI_BOARD_INFO));
+    ASSERT (NewAcpiBoardInfo != NULL);
+    CopyMem (NewAcpiBoardInfo, &AcpiBoardInfo, sizeof (ACPI_BOARD_INFO));
+    DEBUG ((DEBUG_INFO, "Create acpi board info guid hob\n"));
+  }
+
+  //
+  // Parse platform specific information.
+  //
+  Status = ParsePlatformInfo ();
+  if (EFI_ERROR (Status)) {
+    DEBUG ((DEBUG_ERROR, "Error when parsing platform info, Status = %r\n", Status));
+    return Status;
+  }
+
+  //
+  // Mask off all legacy 8259 interrupt sources
+  //
+  IoWrite8 (LEGACY_8259_MASK_REGISTER_MASTER, 0xFF);
+  IoWrite8 (LEGACY_8259_MASK_REGISTER_SLAVE,  0xFF);
+
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/BlSupportPei/BlSupportPei.h b/UefiPayloadPkg/BlSupportPei/BlSupportPei.h
new file mode 100644
index 0000000000..bf5d92d1ae
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportPei/BlSupportPei.h
@@ -0,0 +1,46 @@
+/** @file
+  The header file of bootloader support PEIM.
+
+Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+
+#ifndef __PEI_BOOTLOADER_SUPPORT_H__
+#define __PEI_BOOTLOADER_SUPPORT_H__
+
+#include <PiPei.h>
+#include <Library/PeimEntryPoint.h>
+#include <Library/PeiServicesLib.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/HobLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BlParseLib.h>
+#include <Library/MtrrLib.h>
+#include <Library/IoLib.h>
+#include <Library/PlatformSupportLib.h>
+#include <IndustryStandard/Acpi.h>
+#include <Guid/MemoryTypeInformation.h>
+#include <Guid/FirmwareFileSystem2.h>
+#include <Guid/FrameBufferInfoGuid.h>
+#include <Guid/SystemTableInfoGuid.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+#include <Guid/GraphicsInfoHob.h>
+#include <Ppi/MasterBootMode.h>
+#include <IndustryStandard/MemoryMappedConfigurationSpaceAccessTable.h>
+
+typedef struct {
+  UINT32  UsableLowMemTop;
+  UINT32  SystemLowMemTop;
+} PAYLOAD_MEM_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/BlSupportPei/BlSupportPei.inf b/UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
new file mode 100644
index 0000000000..525470b619
--- /dev/null
+++ b/UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
@@ -0,0 +1,79 @@
+## @file
+# Bootloader Support PEI Module
+#
+# Parses bootloader information and report resource information into pei core. It will install
+# the memory as required.
+#
+#  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+#
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution. The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php.
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = BlSupportPeim
+  FILE_GUID                      = 352C6AF8-315B-4bd6-B04F-31D4ED1EBE57
+  MODULE_TYPE                    = PEIM
+  VERSION_STRING                 = 1.0
+  ENTRY_POINT                    = BlPeiEntryPoint
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources]
+  BlSupportPei.c
+  BlSupportPei.h
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  IntelFsp2Pkg/IntelFsp2Pkg.dec
+  IntelFsp2WrapperPkg/IntelFsp2WrapperPkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+  UefiCpuPkg/UefiCpuPkg.dec
+
+[LibraryClasses]
+  PeimEntryPoint
+  PeiServicesLib
+  BaseLib
+  BaseMemoryLib
+  DebugLib
+  HobLib
+  PcdLib
+  BlParseLib
+  MtrrLib
+  IoLib
+  PlatformSupportLib
+
+[Guids]
+  gEfiMemoryTypeInformationGuid
+  gEfiFirmwareFileSystem2Guid
+  gUefiSystemTableInfoGuid
+  gUefiFrameBufferInfoGuid
+  gEfiGraphicsInfoHobGuid
+  gEfiGraphicsDeviceInfoHobGuid
+  gUefiAcpiBoardInfoGuid
+
+[Ppis]
+  gEfiPeiMasterBootModePpiGuid
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIReclaimMemory
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIMemoryNVS
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiReservedMemoryType
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesData
+  gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesCode
+
+[Depex]
+  TRUE
diff --git a/UefiPayloadPkg/BuildAndIntegrationInstructions.txt b/UefiPayloadPkg/BuildAndIntegrationInstructions.txt
new file mode 100644
index 0000000000..2cacd48904
--- /dev/null
+++ b/UefiPayloadPkg/BuildAndIntegrationInstructions.txt
@@ -0,0 +1,82 @@
+================================================================================
+Build And Integration Instructions
+2019 March 27th
+================================================================================
+
+================================================================================
+DISCLAIMER
+================================================================================
+This release note as well as the software described in it is furnished under license
+and may only be used or copied in accordance with the terms of the license. The
+information in this manual is furnished for informational use only, is subject to
+change without notice, and should not be construed as a commitment by Intel Corporation.
+Intel Corporation assumes no responsibility or liability for any errors or inaccuracies
+that may appear in this document or any software that may be provided in association
+with this document.
+Except as permitted by such license, no part of this document may be reproduced,
+stored in a retrieval system, or transmitted in any form or by any means without
+the express written consent of Intel Corporation.
+
+================================================================================
+                                     INDEX
+================================================================================
+A. INTRODUCTION
+B. HOW TO BUILD
+C. HOW TO INTEGRATE INTO COREBOOT
+D. HOW TO INTEGRATE INTO SLIM BOOTLOADER
+
+================================================================================
+A. INTRODUCTION
+================================================================================
+This document provides instructions on how to build UEFI Payload and how to
+integrate it into coreboot or Slim Bootloader firmware.
+
+================================================================================
+B. HOW TO BUILD
+================================================================================
+1. Run the below two commands in windows command prompt window:
+   edksetup.bat
+
+   For debug ia32 build:
+   build -a IA32 -p UefiPayloadPkg\UefiPayloadPkgIa32.dsc -b DEBUG -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   For release ia32 build:
+   build -a IA32 -p UefiPayloadPkg\UefiPayloadPkgIa32.dsc -b RELEASE -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   For debug X64 build:
+   build -a IA32 -a X64 -p UefiPayloadPkg\UefiPayloadPkgIa32X64.dsc -b DEBUG -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   For release X64 build:
+   build -a IA32 -a X64 -p UefiPayloadPkg\UefiPayloadPkgIa32X64.dsc -b RELEASE -t <ToolChain> -D BOOTLOADER=<Bootloader>
+
+   <ToolChain> is the EDK II build environment on your host. Currently it was tested
+   with VS2015x86 toolchain.
+   <Bootloader> could be "SBL" for Slim Bootloader and "COREBOOT" for coreboot.
+
+   Refer to https://github.com/tianocore/tianocore.github.io/wiki/UDK2018-How-to-Build for
+   details about EDK II build steps.
+
+2. If build is successfully, the payload image (UEFIPAYLOAD.fd) will be generated inside the
+   folder of Build\UefiPayloadPkg.
+
+================================================================================
+C. HOW TO INTEGRATE INTO COREBOOT
+================================================================================
+1. Copy the payload image (UEFIPAYLOAD.fd) into the top-level directory of Coreboot source tree.
+2. Run "make menuconfig" in linux console to start Coreboot configuration surface.
+3. In the Payload section,
+   1) Choose "An ELF executable payload" for the option of "Add a payload".
+   2) Type the path of payload image for the option of "Payload path and filename".
+   3) Select the option of "Use LZMA compression for payloads".
+4. If the graphics console is required in UEFI payload, enable framebuffer initialization in coreboot.
+   This could be done by enabling native graphics or using VGA BIOS option rom.
+5. Build the coreboot firmware image.
+
+================================================================================
+D. HOW TO INTEGRATE INTO SLIM BOOTLOADER
+================================================================================
+Please refer https://slimbootloader.github.io/how-tos/integrate-multiple-payloads.html for below steps.
+1. Copy the payload image (UEFIPAYLOAD.fd) into Slim Bootloader source at PayloadPkg\PayloadBins\UefiPld.fd
+2. Update config data to make UEFI payload as default payload if required.
+3. Build Slim Bootloader with UEFI payload:
+   BuildLoader.py build <Platform> -p "OsLoader.efi:LLDR:Lz4;UefiPld.fd:UEFI:Lzma"
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c b/UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c
new file mode 100644
index 0000000000..aa19263154
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/ComponentName.c
@@ -0,0 +1,190 @@
+/** @file
+  UEFI Component Name(2) protocol implementation for the generic GOP driver.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+
+**/
+
+#include <PiDxe.h>
+#include <Library/UefiLib.h>
+
+extern EFI_COMPONENT_NAME_PROTOCOL  mGraphicsOutputComponentName;
+extern EFI_COMPONENT_NAME2_PROTOCOL mGraphicsOutputComponentName2;
+
+//
+// Driver name table for GraphicsOutput module.
+// It is shared by the implementation of ComponentName & ComponentName2 Protocol.
+//
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_UNICODE_STRING_TABLE mGraphicsOutputDriverNameTable[] = {
+  {
+    "eng;en",
+    L"Generic Graphics Output Driver"
+  },
+  {
+    NULL,
+    NULL
+  }
+};
+
+/**
+  Retrieves a Unicode string that is the user readable name of the driver.
+
+  This function retrieves the user readable name of a driver in the form of a
+  Unicode string. If the driver specified by This has a user readable name in
+  the language specified by Language, then a pointer to the driver name is
+  returned in DriverName, and EFI_SUCCESS is returned. If the driver specified
+  by This does not support the language specified by Language,
+  then EFI_UNSUPPORTED is returned.
+
+  @param  This[in]              A pointer to the EFI_COMPONENT_NAME2_PROTOCOL or
+                                EFI_COMPONENT_NAME_PROTOCOL instance.
+
+  @param  Language[in]          A pointer to a Null-terminated ASCII string
+                                array indicating the language. This is the
+                                language of the driver name that the caller is
+                                requesting, and it must match one of the
+                                languages specified in SupportedLanguages. The
+                                number of languages supported by a driver is up
+                                to the driver writer. Language is specified
+                                in RFC 4646 or ISO 639-2 language code format.
+
+  @param  DriverName[out]       A pointer to the Unicode string to return.
+                                This Unicode string is the name of the
+                                driver specified by This in the language
+                                specified by Language.
+
+  @retval EFI_SUCCESS           The Unicode string for the Driver specified by
+                                This and the language specified by Language was
+                                returned in DriverName.
+
+  @retval EFI_INVALID_PARAMETER Language is NULL.
+
+  @retval EFI_INVALID_PARAMETER DriverName is NULL.
+
+  @retval EFI_UNSUPPORTED       The driver specified by This does not support
+                                the language specified by Language.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputComponentNameGetDriverName (
+  IN  EFI_COMPONENT_NAME_PROTOCOL  *This,
+  IN  CHAR8                        *Language,
+  OUT CHAR16                       **DriverName
+  )
+{
+  return LookupUnicodeString2 (
+           Language,
+           This->SupportedLanguages,
+           mGraphicsOutputDriverNameTable,
+           DriverName,
+           (BOOLEAN) (This == &mGraphicsOutputComponentName)
+           );
+}
+
+/**
+  Retrieves a Unicode string that is the user readable name of the controller
+  that is being managed by a driver.
+
+  This function retrieves the user readable name of the controller specified by
+  ControllerHandle and ChildHandle in the form of a Unicode string. If the
+  driver specified by This has a user readable name in the language specified by
+  Language, then a pointer to the controller name is returned in ControllerName,
+  and EFI_SUCCESS is returned.  If the driver specified by This is not currently
+  managing the controller specified by ControllerHandle and ChildHandle,
+  then EFI_UNSUPPORTED is returned.  If the driver specified by This does not
+  support the language specified by Language, then EFI_UNSUPPORTED is returned.
+
+  @param  This[in]              A pointer to the EFI_COMPONENT_NAME2_PROTOCOL or
+                                EFI_COMPONENT_NAME_PROTOCOL instance.
+
+  @param  ControllerHandle[in]  The handle of a controller that the driver
+                                specified by This is managing.  This handle
+                                specifies the controller whose name is to be
+                                returned.
+
+  @param  ChildHandle[in]       The handle of the child controller to retrieve
+                                the name of.  This is an optional parameter that
+                                may be NULL.  It will be NULL for device
+                                drivers.  It will also be NULL for a bus drivers
+                                that wish to retrieve the name of the bus
+                                controller.  It will not be NULL for a bus
+                                driver that wishes to retrieve the name of a
+                                child controller.
+
+  @param  Language[in]          A pointer to a Null-terminated ASCII string
+                                array indicating the language.  This is the
+                                language of the driver name that the caller is
+                                requesting, and it must match one of the
+                                languages specified in SupportedLanguages. The
+                                number of languages supported by a driver is up
+                                to the driver writer. Language is specified in
+                                RFC 4646 or ISO 639-2 language code format.
+
+  @param  ControllerName[out]   A pointer to the Unicode string to return.
+                                This Unicode string is the name of the
+                                controller specified by ControllerHandle and
+                                ChildHandle in the language specified by
+                                Language from the point of view of the driver
+                                specified by This.
+
+  @retval EFI_SUCCESS           The Unicode string for the user readable name in
+                                the language specified by Language for the
+                                driver specified by This was returned in
+                                DriverName.
+
+  @retval EFI_INVALID_PARAMETER ControllerHandle is NULL.
+
+  @retval EFI_INVALID_PARAMETER ChildHandle is not NULL and it is not a valid
+                                EFI_HANDLE.
+
+  @retval EFI_INVALID_PARAMETER Language is NULL.
+
+  @retval EFI_INVALID_PARAMETER ControllerName is NULL.
+
+  @retval EFI_UNSUPPORTED       The driver specified by This is not currently
+                                managing the controller specified by
+                                ControllerHandle and ChildHandle.
+
+  @retval EFI_UNSUPPORTED       The driver specified by This does not support
+                                the language specified by Language.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputComponentNameGetControllerName (
+  IN  EFI_COMPONENT_NAME_PROTOCOL                     *This,
+  IN  EFI_HANDLE                                      ControllerHandle,
+  IN  EFI_HANDLE                                      ChildHandle        OPTIONAL,
+  IN  CHAR8                                           *Language,
+  OUT CHAR16                                          **ControllerName
+  )
+{
+  return EFI_UNSUPPORTED;
+}
+
+//
+// EFI Component Name Protocol
+//
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME_PROTOCOL  mGraphicsOutputComponentName = {
+  GraphicsOutputComponentNameGetDriverName,
+  GraphicsOutputComponentNameGetControllerName,
+  "eng"
+};
+
+//
+// EFI Component Name 2 Protocol
+//
+GLOBAL_REMOVE_IF_UNREFERENCED EFI_COMPONENT_NAME2_PROTOCOL mGraphicsOutputComponentName2 = {
+  (EFI_COMPONENT_NAME2_GET_DRIVER_NAME) GraphicsOutputComponentNameGetDriverName,
+  (EFI_COMPONENT_NAME2_GET_CONTROLLER_NAME) GraphicsOutputComponentNameGetControllerName,
+  "en"
+};
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c
new file mode 100644
index 0000000000..79da3c0171
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.c
@@ -0,0 +1,745 @@
+/** @file
+  Implementation for a generic GOP driver.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+
+**/
+
+#include "GraphicsOutput.h"
+CONST ACPI_ADR_DEVICE_PATH mGraphicsOutputAdrNode = {
+  {
+    ACPI_DEVICE_PATH,
+    ACPI_ADR_DP,
+    { sizeof (ACPI_ADR_DEVICE_PATH), 0 },
+  },
+  ACPI_DISPLAY_ADR (1, 0, 0, 1, 0, ACPI_ADR_DISPLAY_TYPE_VGA, 0, 0)
+};
+
+EFI_PEI_GRAPHICS_DEVICE_INFO_HOB mDefaultGraphicsDeviceInfo = {
+  MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT16, MAX_UINT8, MAX_UINT8
+};
+
+//
+// The driver should only start on one graphics controller.
+// So a global flag is used to remember that the driver is already started.
+//
+BOOLEAN mDriverStarted = FALSE;
+
+/**
+  Returns information for an available graphics mode that the graphics device
+  and the set of active video output devices supports.
+
+  @param  This                  The EFI_GRAPHICS_OUTPUT_PROTOCOL instance.
+  @param  ModeNumber            The mode number to return information on.
+  @param  SizeOfInfo            A pointer to the size, in bytes, of the Info buffer.
+  @param  Info                  A pointer to callee allocated buffer that returns information about ModeNumber.
+
+  @retval EFI_SUCCESS           Valid mode information was returned.
+  @retval EFI_DEVICE_ERROR      A hardware error occurred trying to retrieve the video mode.
+  @retval EFI_INVALID_PARAMETER ModeNumber is not valid.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputQueryMode (
+  IN  EFI_GRAPHICS_OUTPUT_PROTOCOL          *This,
+  IN  UINT32                                ModeNumber,
+  OUT UINTN                                 *SizeOfInfo,
+  OUT EFI_GRAPHICS_OUTPUT_MODE_INFORMATION  **Info
+  )
+{
+  if (This == NULL || Info == NULL || SizeOfInfo == NULL || ModeNumber >= This->Mode->MaxMode) {
+    return EFI_INVALID_PARAMETER;
+  }
+
+  *SizeOfInfo = This->Mode->SizeOfInfo;
+  *Info       = AllocateCopyPool (*SizeOfInfo, This->Mode->Info);
+  return EFI_SUCCESS;
+}
+
+/**
+  Set the video device into the specified mode and clears the visible portions of
+  the output display to black.
+
+  @param  This              The EFI_GRAPHICS_OUTPUT_PROTOCOL instance.
+  @param  ModeNumber        Abstraction that defines the current video mode.
+
+  @retval EFI_SUCCESS       The graphics mode specified by ModeNumber was selected.
+  @retval EFI_DEVICE_ERROR  The device had an error and could not complete the request.
+  @retval EFI_UNSUPPORTED   ModeNumber is not supported by this device.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputSetMode (
+  IN  EFI_GRAPHICS_OUTPUT_PROTOCOL *This,
+  IN  UINT32                       ModeNumber
+)
+{
+  RETURN_STATUS                    Status;
+  EFI_GRAPHICS_OUTPUT_BLT_PIXEL    Black;
+  GRAPHICS_OUTPUT_PRIVATE_DATA     *Private;
+
+  if (ModeNumber >= This->Mode->MaxMode) {
+    return EFI_UNSUPPORTED;
+  }
+
+  Private = GRAPHICS_OUTPUT_PRIVATE_FROM_THIS (This);
+
+  Black.Blue = 0;
+  Black.Green = 0;
+  Black.Red = 0;
+  Black.Reserved = 0;
+
+  Status = FrameBufferBlt (
+             Private->FrameBufferBltLibConfigure,
+             &Black,
+             EfiBltVideoFill,
+             0, 0,
+             0, 0,
+             This->Mode->Info->HorizontalResolution,
+             This->Mode->Info->VerticalResolution,
+             0
+             );
+  return RETURN_ERROR (Status) ? EFI_DEVICE_ERROR : EFI_SUCCESS;
+}
+
+/**
+  Blt a rectangle of pixels on the graphics screen. Blt stands for BLock Transfer.
+
+  @param  This         Protocol instance pointer.
+  @param  BltBuffer    The data to transfer to the graphics screen.
+                       Size is at least Width*Height*sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL).
+  @param  BltOperation The operation to perform when copying BltBuffer on to the graphics screen.
+  @param  SourceX      The X coordinate of source for the BltOperation.
+  @param  SourceY      The Y coordinate of source for the BltOperation.
+  @param  DestinationX The X coordinate of destination for the BltOperation.
+  @param  DestinationY The Y coordinate of destination for the BltOperation.
+  @param  Width        The width of a rectangle in the blt rectangle in pixels.
+  @param  Height       The height of a rectangle in the blt rectangle in pixels.
+  @param  Delta        Not used for EfiBltVideoFill or the EfiBltVideoToVideo operation.
+                       If a Delta of zero is used, the entire BltBuffer is being operated on.
+                       If a subrectangle of the BltBuffer is being used then Delta
+                       represents the number of bytes in a row of the BltBuffer.
+
+  @retval EFI_SUCCESS           BltBuffer was drawn to the graphics screen.
+  @retval EFI_INVALID_PARAMETER BltOperation is not valid.
+  @retval EFI_DEVICE_ERROR      The device had an error and could not complete the request.
+
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputBlt (
+  IN  EFI_GRAPHICS_OUTPUT_PROTOCOL      *This,
+  IN  EFI_GRAPHICS_OUTPUT_BLT_PIXEL     *BltBuffer, OPTIONAL
+  IN  EFI_GRAPHICS_OUTPUT_BLT_OPERATION BltOperation,
+  IN  UINTN                             SourceX,
+  IN  UINTN                             SourceY,
+  IN  UINTN                             DestinationX,
+  IN  UINTN                             DestinationY,
+  IN  UINTN                             Width,
+  IN  UINTN                             Height,
+  IN  UINTN                             Delta         OPTIONAL
+  )
+{
+  RETURN_STATUS                         Status;
+  EFI_TPL                               Tpl;
+  GRAPHICS_OUTPUT_PRIVATE_DATA          *Private;
+
+  Private = GRAPHICS_OUTPUT_PRIVATE_FROM_THIS (This);
+  //
+  // We have to raise to TPL_NOTIFY, so we make an atomic write to the frame buffer.
+  // We would not want a timer based event (Cursor, ...) to come in while we are
+  // doing this operation.
+  //
+  Tpl = gBS->RaiseTPL (TPL_NOTIFY);
+  Status = FrameBufferBlt (
+             Private->FrameBufferBltLibConfigure,
+             BltBuffer,
+             BltOperation,
+             SourceX, SourceY,
+             DestinationX, DestinationY, Width, Height,
+             Delta
+             );
+  gBS->RestoreTPL (Tpl);
+
+  return RETURN_ERROR (Status) ? EFI_INVALID_PARAMETER : EFI_SUCCESS;
+}
+
+CONST GRAPHICS_OUTPUT_PRIVATE_DATA mGraphicsOutputInstanceTemplate = {
+  GRAPHICS_OUTPUT_PRIVATE_DATA_SIGNATURE,          // Signature
+  NULL,                                            // GraphicsOutputHandle
+  {
+    GraphicsOutputQueryMode,
+    GraphicsOutputSetMode,
+    GraphicsOutputBlt,
+    NULL                                           // Mode
+  },
+  {
+    1,                                             // MaxMode
+    0,                                             // Mode
+    NULL,                                          // Info
+    sizeof (EFI_GRAPHICS_OUTPUT_MODE_INFORMATION), // SizeOfInfo
+    0,                                             // FrameBufferBase
+    0                                              // FrameBufferSize
+  },
+  NULL,                                            // DevicePath
+  NULL,                                            // PciIo
+  0,                                               // PciAttributes
+  NULL,                                            // FrameBufferBltLibConfigure
+  0                                                // FrameBufferBltLibConfigureSize
+};
+
+/**
+  Test whether the Controller can be managed by the driver.
+
+  @param  This                 Driver Binding protocol instance pointer.
+  @param  Controller           The PCI controller.
+  @param  RemainingDevicePath  Optional parameter use to pick a specific child
+                               device to start.
+
+  @retval EFI_SUCCESS          The driver can manage the video device.
+  @retval other                The driver cannot manage the video device.
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputDriverBindingSupported (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN EFI_DEVICE_PATH_PROTOCOL       *RemainingDevicePath
+  )
+{
+  EFI_STATUS                        Status;
+  EFI_PCI_IO_PROTOCOL               *PciIo;
+  EFI_DEVICE_PATH_PROTOCOL          *DevicePath;
+
+  //
+  // Since there is only one GraphicsInfo HOB, the driver only manages one video device.
+  //
+  if (mDriverStarted) {
+    return EFI_ALREADY_STARTED;
+  }
+
+  //
+  // Test the PCI I/O Protocol
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIo,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+  gBS->CloseProtocol (
+         Controller,
+         &gEfiPciIoProtocolGuid,
+         This->DriverBindingHandle,
+         Controller
+         );
+
+  //
+  // Test the DevicePath protocol
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiDevicePathProtocolGuid,
+                  (VOID **) &DevicePath,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+  gBS->CloseProtocol (
+         Controller,
+         &gEfiDevicePathProtocolGuid,
+         This->DriverBindingHandle,
+         Controller
+         );
+
+  if ((RemainingDevicePath == NULL) ||
+      IsDevicePathEnd (RemainingDevicePath) ||
+      CompareMem (RemainingDevicePath, &mGraphicsOutputAdrNode, sizeof (mGraphicsOutputAdrNode)) == 0) {
+    return EFI_SUCCESS;
+  } else {
+    return EFI_INVALID_PARAMETER;
+  }
+}
+
+/**
+  Start the video controller.
+
+  @param  This                 Driver Binding protocol instance pointer.
+  @param  ControllerHandle     The PCI controller.
+  @param  RemainingDevicePath  Optional parameter use to pick a specific child
+                               device to start.
+
+  @retval EFI_SUCCESS          The driver starts to manage the video device.
+  @retval other                The driver cannot manage the video device.
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputDriverBindingStart (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN EFI_DEVICE_PATH_PROTOCOL       *RemainingDevicePath
+  )
+{
+  EFI_STATUS                        Status;
+  RETURN_STATUS                     ReturnStatus;
+  GRAPHICS_OUTPUT_PRIVATE_DATA      *Private;
+  EFI_PCI_IO_PROTOCOL               *PciIo;
+  EFI_DEVICE_PATH                   *PciDevicePath;
+  PCI_TYPE00                        Pci;
+  UINT8                             Index;
+  EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR *Resources;
+  VOID                              *HobStart;
+  EFI_PEI_GRAPHICS_INFO_HOB         *GraphicsInfo;
+  EFI_PEI_GRAPHICS_DEVICE_INFO_HOB  *DeviceInfo;
+  EFI_PHYSICAL_ADDRESS              FrameBufferBase;
+
+  FrameBufferBase = 0;
+
+  HobStart = GetFirstGuidHob (&gEfiGraphicsInfoHobGuid);
+  ASSERT ((HobStart != NULL) && (GET_GUID_HOB_DATA_SIZE (HobStart) == sizeof (EFI_PEI_GRAPHICS_INFO_HOB)));
+  GraphicsInfo = (EFI_PEI_GRAPHICS_INFO_HOB *) (GET_GUID_HOB_DATA (HobStart));
+
+  HobStart = GetFirstGuidHob (&gEfiGraphicsDeviceInfoHobGuid);
+  if ((HobStart == NULL) || (GET_GUID_HOB_DATA_SIZE (HobStart) < sizeof (*DeviceInfo))) {
+    //
+    // Use default device infomation when the device info HOB doesn't exist
+    //
+    DeviceInfo = &mDefaultGraphicsDeviceInfo;
+    DEBUG ((DEBUG_INFO, "[%a]: GraphicsDeviceInfo HOB doesn't exist!\n", gEfiCallerBaseName));
+  } else {
+    DeviceInfo = (EFI_PEI_GRAPHICS_DEVICE_INFO_HOB *) (GET_GUID_HOB_DATA (HobStart));
+    DEBUG ((DEBUG_INFO, "[%a]: GraphicsDeviceInfo HOB:\n"
+            "  VendorId = %04x, DeviceId = %04x,\n"
+            "  RevisionId = %02x, BarIndex = %x,\n"
+            "  SubsystemVendorId = %04x, SubsystemId = %04x\n",
+            gEfiCallerBaseName,
+            DeviceInfo->VendorId, DeviceInfo->DeviceId,
+            DeviceInfo->RevisionId, DeviceInfo->BarIndex,
+            DeviceInfo->SubsystemVendorId, DeviceInfo->SubsystemId));
+  }
+
+  //
+  // Open the PCI I/O Protocol
+  //
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  (VOID **) &PciIo,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  ASSERT_EFI_ERROR (Status);
+
+  Status = gBS->OpenProtocol (
+                  Controller,
+                  &gEfiDevicePathProtocolGuid,
+                  (VOID **) &PciDevicePath,
+                  This->DriverBindingHandle,
+                  Controller,
+                  EFI_OPEN_PROTOCOL_BY_DRIVER
+                  );
+  if (Status == EFI_ALREADY_STARTED) {
+    Status = EFI_SUCCESS;
+  }
+  ASSERT_EFI_ERROR (Status);
+
+  //
+  // Read the PCI Class Code from the PCI Device
+  //
+  Status = PciIo->Pci.Read (PciIo, EfiPciIoWidthUint8, 0, sizeof (Pci), &Pci);
+  if (!EFI_ERROR (Status)) {
+    if (!IS_PCI_DISPLAY (&Pci) || (
+        ((DeviceInfo->VendorId != MAX_UINT16) && (DeviceInfo->VendorId != Pci.Hdr.VendorId)) ||
+        ((DeviceInfo->DeviceId != MAX_UINT16) && (DeviceInfo->DeviceId != Pci.Hdr.DeviceId)) ||
+        ((DeviceInfo->RevisionId != MAX_UINT8) && (DeviceInfo->RevisionId != Pci.Hdr.RevisionID)) ||
+        ((DeviceInfo->SubsystemVendorId != MAX_UINT16) && (DeviceInfo->SubsystemVendorId != Pci.Device.SubsystemVendorID)) ||
+        ((DeviceInfo->SubsystemId != MAX_UINT16) && (DeviceInfo->SubsystemId != Pci.Device.SubsystemID))
+        )
+        ) {
+      //
+      // It's not a video device, or device infomation doesn't match.
+      //
+      Status = EFI_UNSUPPORTED;
+    } else {
+      //
+      // If it's a video device and device information matches, use the BarIndex
+      // from device information, or any BAR if BarIndex is not specified
+      // whose size >= the frame buffer size from GraphicsInfo HOB.
+      // Store the new frame buffer base.
+      //
+      for (Index = 0; Index < MAX_PCI_BAR; Index++) {
+        if ((DeviceInfo->BarIndex != MAX_UINT8) && (DeviceInfo->BarIndex != Index)) {
+          continue;
+        }
+        Status = PciIo->GetBarAttributes (PciIo, Index, NULL, (VOID**) &Resources);
+        if (!EFI_ERROR (Status)) {
+          DEBUG ((DEBUG_INFO, "[%a]: BAR[%d]: Base = %lx, Length = %lx\n",
+                  gEfiCallerBaseName, Index, Resources->AddrRangeMin, Resources->AddrLen));
+          if ((Resources->Desc == ACPI_ADDRESS_SPACE_DESCRIPTOR) &&
+            (Resources->Len == (UINT16) (sizeof (EFI_ACPI_ADDRESS_SPACE_DESCRIPTOR) - 3)) &&
+              (Resources->ResType == ACPI_ADDRESS_SPACE_TYPE_MEM) &&
+              (Resources->AddrLen >= GraphicsInfo->FrameBufferSize)
+              ) {
+            if (FrameBufferBase == 0) {
+              FrameBufferBase = Resources->AddrRangeMin;
+            }
+            if (DeviceInfo->BarIndex == MAX_UINT8) {
+              if (Resources->AddrRangeMin == GraphicsInfo->FrameBufferBase) {
+                FrameBufferBase = Resources->AddrRangeMin;
+                break;
+              }
+            } else {
+              break;
+            }
+          }
+        }
+      }
+      if (Index == MAX_PCI_BAR) {
+        Status = EFI_UNSUPPORTED;
+      } else {
+        DEBUG ((DEBUG_INFO, "[%a]: ... matched!\n", gEfiCallerBaseName));
+      }
+    }
+  }
+
+  if (EFI_ERROR (Status)) {
+    goto CloseProtocols;
+  }
+
+  if ((RemainingDevicePath != NULL) && IsDevicePathEnd (RemainingDevicePath)) {
+    return EFI_SUCCESS;
+  }
+
+  Private = AllocateCopyPool (sizeof (mGraphicsOutputInstanceTemplate), &mGraphicsOutputInstanceTemplate);
+  if (Private == NULL) {
+    Status = EFI_OUT_OF_RESOURCES;
+    goto CloseProtocols;
+  }
+
+  Private->GraphicsOutputMode.FrameBufferBase = FrameBufferBase;
+  Private->GraphicsOutputMode.FrameBufferSize = GraphicsInfo->FrameBufferSize;
+  Private->GraphicsOutputMode.Info = &GraphicsInfo->GraphicsMode;
+
+  //
+  // Fix up Mode pointer in GraphicsOutput
+  //
+  Private->GraphicsOutput.Mode = &Private->GraphicsOutputMode;
+
+  //
+  // Set attributes
+  //
+  Status = PciIo->Attributes (
+                    PciIo,
+                    EfiPciIoAttributeOperationGet,
+                    0,
+                    &Private->PciAttributes
+                    );
+  if (!EFI_ERROR (Status)) {
+    Status = PciIo->Attributes (
+                      PciIo,
+                      EfiPciIoAttributeOperationEnable,
+                      EFI_PCI_DEVICE_ENABLE,
+                      NULL
+                      );
+  }
+
+  if (EFI_ERROR (Status)) {
+    goto FreeMemory;
+  }
+
+  //
+  // Create the FrameBufferBltLib configuration.
+  //
+  ReturnStatus = FrameBufferBltConfigure (
+                   (VOID *) (UINTN) Private->GraphicsOutput.Mode->FrameBufferBase,
+                   Private->GraphicsOutput.Mode->Info,
+                   Private->FrameBufferBltLibConfigure,
+                   &Private->FrameBufferBltLibConfigureSize
+                   );
+  if (ReturnStatus == RETURN_BUFFER_TOO_SMALL) {
+    Private->FrameBufferBltLibConfigure = AllocatePool (Private->FrameBufferBltLibConfigureSize);
+    if (Private->FrameBufferBltLibConfigure != NULL) {
+      ReturnStatus = FrameBufferBltConfigure (
+                       (VOID *) (UINTN) Private->GraphicsOutput.Mode->FrameBufferBase,
+                       Private->GraphicsOutput.Mode->Info,
+                       Private->FrameBufferBltLibConfigure,
+                       &Private->FrameBufferBltLibConfigureSize
+                       );
+    }
+  }
+  if (RETURN_ERROR (ReturnStatus)) {
+    Status = EFI_OUT_OF_RESOURCES;
+    goto RestorePciAttributes;
+  }
+
+  Private->DevicePath = AppendDevicePathNode (PciDevicePath, (EFI_DEVICE_PATH_PROTOCOL *) &mGraphicsOutputAdrNode);
+  if (Private->DevicePath == NULL) {
+    Status = EFI_OUT_OF_RESOURCES;
+    goto RestorePciAttributes;
+  }
+
+  Status = gBS->InstallMultipleProtocolInterfaces (
+                  &Private->GraphicsOutputHandle,
+                  &gEfiGraphicsOutputProtocolGuid, &Private->GraphicsOutput,
+                  &gEfiDevicePathProtocolGuid, Private->DevicePath,
+                  NULL
+                  );
+
+  if (!EFI_ERROR (Status)) {
+    Status = gBS->OpenProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    (VOID **) &Private->PciIo,
+                    This->DriverBindingHandle,
+                    Private->GraphicsOutputHandle,
+                    EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER
+                    );
+    if (!EFI_ERROR (Status)) {
+      mDriverStarted = TRUE;
+    } else {
+      gBS->UninstallMultipleProtocolInterfaces (
+             Private->GraphicsOutputHandle,
+             &gEfiGraphicsOutputProtocolGuid, &Private->GraphicsOutput,
+             &gEfiDevicePathProtocolGuid, Private->DevicePath,
+             NULL
+             );
+    }
+  }
+
+RestorePciAttributes:
+  if (EFI_ERROR (Status)) {
+    //
+    // Restore original PCI attributes
+    //
+    PciIo->Attributes (
+             PciIo,
+             EfiPciIoAttributeOperationSet,
+             Private->PciAttributes,
+             NULL
+             );
+  }
+
+FreeMemory:
+  if (EFI_ERROR (Status)) {
+    if (Private != NULL) {
+      if (Private->DevicePath != NULL) {
+        FreePool (Private->DevicePath);
+      }
+      if (Private->FrameBufferBltLibConfigure != NULL) {
+        FreePool (Private->FrameBufferBltLibConfigure);
+      }
+      FreePool (Private);
+    }
+  }
+
+CloseProtocols:
+  if (EFI_ERROR (Status)) {
+    //
+    // Close the PCI I/O Protocol
+    //
+    gBS->CloseProtocol (
+           Controller,
+           &gEfiDevicePathProtocolGuid,
+           This->DriverBindingHandle,
+           Controller
+           );
+
+    //
+    // Close the PCI I/O Protocol
+    //
+    gBS->CloseProtocol (
+           Controller,
+           &gEfiPciIoProtocolGuid,
+           This->DriverBindingHandle,
+           Controller
+           );
+  }
+  return Status;
+}
+
+/**
+  Stop the video controller.
+
+  @param  This                 Driver Binding protocol instance pointer.
+  @param  Controller           The PCI controller.
+  @param  NumberOfChildren     The number of child device handles in ChildHandleBuffer.
+  @param  ChildHandleBuffer    An array of child handles to be freed. May be NULL
+                               if NumberOfChildren is 0.
+
+  @retval EFI_SUCCESS          The device was stopped.
+  @retval EFI_DEVICE_ERROR     The device could not be stopped due to a device error.
+**/
+EFI_STATUS
+EFIAPI
+GraphicsOutputDriverBindingStop (
+  IN EFI_DRIVER_BINDING_PROTOCOL    *This,
+  IN EFI_HANDLE                     Controller,
+  IN UINTN                          NumberOfChildren,
+  IN EFI_HANDLE                     *ChildHandleBuffer
+  )
+{
+  EFI_STATUS                        Status;
+  EFI_GRAPHICS_OUTPUT_PROTOCOL      *Gop;
+  GRAPHICS_OUTPUT_PRIVATE_DATA      *Private;
+
+  if (NumberOfChildren == 0) {
+
+    //
+    // Close the PCI I/O Protocol
+    //
+    Status = gBS->CloseProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    This->DriverBindingHandle,
+                    Controller
+                    );
+    ASSERT_EFI_ERROR (Status);
+
+    Status = gBS->CloseProtocol (
+                    Controller,
+                    &gEfiDevicePathProtocolGuid,
+                    This->DriverBindingHandle,
+                    Controller
+                    );
+    ASSERT_EFI_ERROR (Status);
+    return EFI_SUCCESS;
+  }
+
+  ASSERT (NumberOfChildren == 1);
+  Status = gBS->OpenProtocol (
+                  ChildHandleBuffer[0],
+                  &gEfiGraphicsOutputProtocolGuid,
+                  (VOID **) &Gop,
+                  This->DriverBindingHandle,
+                  ChildHandleBuffer[0],
+                  EFI_OPEN_PROTOCOL_GET_PROTOCOL
+                  );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Private = GRAPHICS_OUTPUT_PRIVATE_FROM_THIS (Gop);
+
+  Status = gBS->CloseProtocol (
+                  Controller,
+                  &gEfiPciIoProtocolGuid,
+                  This->DriverBindingHandle,
+                  Private->GraphicsOutputHandle
+                  );
+  ASSERT_EFI_ERROR (Status);
+  //
+  // Remove the GOP protocol interface from the system
+  //
+  Status = gBS->UninstallMultipleProtocolInterfaces (
+                  Private->GraphicsOutputHandle,
+                  &gEfiGraphicsOutputProtocolGuid, &Private->GraphicsOutput,
+                  &gEfiDevicePathProtocolGuid, Private->DevicePath,
+                  NULL
+                  );
+  if (!EFI_ERROR (Status)) {
+    //
+    // Restore original PCI attributes
+    //
+    Status = Private->PciIo->Attributes (
+                               Private->PciIo,
+                               EfiPciIoAttributeOperationSet,
+                               Private->PciAttributes,
+                               NULL
+                               );
+    ASSERT_EFI_ERROR (Status);
+
+    FreePool (Private->DevicePath);
+    FreePool (Private->FrameBufferBltLibConfigure);
+    mDriverStarted = FALSE;
+  } else {
+    Status = gBS->OpenProtocol (
+                    Controller,
+                    &gEfiPciIoProtocolGuid,
+                    (VOID **) &Private->PciIo,
+                    This->DriverBindingHandle,
+                    Private->GraphicsOutputHandle,
+                    EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER
+                    );
+    ASSERT_EFI_ERROR (Status);
+  }
+  return Status;
+}
+
+EFI_DRIVER_BINDING_PROTOCOL mGraphicsOutputDriverBinding = {
+  GraphicsOutputDriverBindingSupported,
+  GraphicsOutputDriverBindingStart,
+  GraphicsOutputDriverBindingStop,
+  0x10,
+  NULL,
+  NULL
+};
+
+/**
+  The Entry Point for GraphicsOutput driver.
+
+  It installs DriverBinding, ComponentName and ComponentName2 protocol if there is
+  GraphicsInfo HOB passed from Graphics PEIM.
+
+  @param[in] ImageHandle    The firmware allocated handle for the EFI image.
+  @param[in] SystemTable    A pointer to the EFI System Table.
+
+  @retval EFI_SUCCESS       The entry point is executed successfully.
+  @retval other             Some error occurs when executing this entry point.
+
+**/
+EFI_STATUS
+EFIAPI
+InitializeGraphicsOutput (
+  IN EFI_HANDLE                        ImageHandle,
+  IN EFI_SYSTEM_TABLE                  *SystemTable
+  )
+{
+  EFI_STATUS                           Status;
+  VOID                                 *HobStart;
+
+  HobStart = GetFirstGuidHob (&gEfiGraphicsInfoHobGuid);
+
+  if ((HobStart == NULL) || (GET_GUID_HOB_DATA_SIZE (HobStart) < sizeof (EFI_PEI_GRAPHICS_INFO_HOB))) {
+    return EFI_NOT_FOUND;
+  }
+
+  Status = EfiLibInstallDriverBindingComponentName2 (
+             ImageHandle,
+             SystemTable,
+             &mGraphicsOutputDriverBinding,
+             ImageHandle,
+             &mGraphicsOutputComponentName,
+             &mGraphicsOutputComponentName2
+             );
+  ASSERT_EFI_ERROR (Status);
+
+  return Status;
+}
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h
new file mode 100644
index 0000000000..fb1ab7e356
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutput.h
@@ -0,0 +1,59 @@
+/** @file
+  Header file for a generic GOP driver.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+
+**/
+#ifndef _GRAPHICS_OUTPUT_DXE_H_
+#define _GRAPHICS_OUTPUT_DXE_H_
+#include <PiDxe.h>
+
+#include <IndustryStandard/Pci.h>
+#include <IndustryStandard/Acpi.h>
+#include <Guid/GraphicsInfoHob.h>
+#include <Protocol/DriverBinding.h>
+#include <Protocol/PciIo.h>
+#include <Protocol/DevicePath.h>
+#include <Protocol/GraphicsOutput.h>
+#include <Protocol/ComponentName.h>
+#include <Protocol/ComponentName2.h>
+
+#include <Library/BaseLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/HobLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/FrameBufferBltLib.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiLib.h>
+
+#define MAX_PCI_BAR  6
+
+typedef struct {
+  UINT32                            Signature;
+  EFI_HANDLE                        GraphicsOutputHandle;
+  EFI_GRAPHICS_OUTPUT_PROTOCOL      GraphicsOutput;
+  EFI_GRAPHICS_OUTPUT_PROTOCOL_MODE GraphicsOutputMode;
+  EFI_DEVICE_PATH_PROTOCOL          *DevicePath;
+  EFI_PCI_IO_PROTOCOL               *PciIo;
+  UINT64                            PciAttributes;
+  FRAME_BUFFER_CONFIGURE            *FrameBufferBltLibConfigure;
+  UINTN                             FrameBufferBltLibConfigureSize;
+} GRAPHICS_OUTPUT_PRIVATE_DATA;
+
+#define GRAPHICS_OUTPUT_PRIVATE_DATA_SIGNATURE  SIGNATURE_32 ('g', 'g', 'o', 'p')
+#define GRAPHICS_OUTPUT_PRIVATE_FROM_THIS(a) \
+  CR(a, GRAPHICS_OUTPUT_PRIVATE_DATA, GraphicsOutput, GRAPHICS_OUTPUT_PRIVATE_DATA_SIGNATURE)
+
+extern EFI_COMPONENT_NAME_PROTOCOL  mGraphicsOutputComponentName;
+extern EFI_COMPONENT_NAME2_PROTOCOL mGraphicsOutputComponentName2;
+#endif
diff --git a/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
new file mode 100644
index 0000000000..035245e9f1
--- /dev/null
+++ b/UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
@@ -0,0 +1,58 @@
+## @file
+# This driver produces GraphicsOutput protocol based on the GraphicsInfo HOB information.
+#
+# Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+#
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution. The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = GraphicsOutputDxe
+  FILE_GUID                      = 0B04B2ED-861C-42cd-A22F-C3AAFACCB896
+  MODULE_TYPE                    = UEFI_DRIVER
+  VERSION_STRING                 = 1.0
+  ENTRY_POINT                    = InitializeGraphicsOutput
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources.common]
+  GraphicsOutput.h
+  GraphicsOutput.c
+  ComponentName.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+
+[LibraryClasses]
+  UefiDriverEntryPoint
+  UefiBootServicesTableLib
+  DxeServicesTableLib
+  DebugLib
+  MemoryAllocationLib
+  BaseMemoryLib
+  DevicePathLib
+  FrameBufferBltLib
+  UefiLib
+  HobLib
+
+[Guids]
+  gEfiGraphicsInfoHobGuid                       ## CONSUMES ## HOB
+  gEfiGraphicsDeviceInfoHobGuid                 ## CONSUMES ## HOB
+
+[Protocols]
+  gEfiGraphicsOutputProtocolGuid                ## BY_START
+  gEfiDevicePathProtocolGuid                    ## BY_START
+  gEfiPciIoProtocolGuid                         ## TO_START
diff --git a/UefiPayloadPkg/Include/Coreboot.h b/UefiPayloadPkg/Include/Coreboot.h
new file mode 100644
index 0000000000..b622e6f17e
--- /dev/null
+++ b/UefiPayloadPkg/Include/Coreboot.h
@@ -0,0 +1,255 @@
+/** @file
+  Coreboot PEI module include file.
+
+  Copyright (c) 2014 - 2015, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+/*
+ * This file is part of the libpayload project.
+ *
+ * Copyright (C) 2008 Advanced Micro Devices, Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. The name of the author may not be used to endorse or promote products
+ *    derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+
+#ifndef _COREBOOT_PEI_H_INCLUDED_
+#define _COREBOOT_PEI_H_INCLUDED_
+
+#if defined(_MSC_VER)
+#pragma warning( disable : 4200 )
+#endif
+
+#define DYN_CBMEM_ALIGN_SIZE (4096)
+
+#define IMD_ENTRY_MAGIC      (~0xC0389481)
+#define CBMEM_ENTRY_MAGIC    (~0xC0389479)
+
+struct cbmem_entry {
+  UINT32 magic;
+  UINT32 start;
+  UINT32 size;
+  UINT32 id;
+};
+
+struct cbmem_root {
+  UINT32 max_entries;
+  UINT32 num_entries;
+  UINT32 locked;
+  UINT32 size;
+  struct cbmem_entry entries[0];
+};
+
+struct imd_entry {
+  UINT32 magic;
+  UINT32 start_offset;
+  UINT32 size;
+  UINT32 id;
+};
+
+struct imd_root {
+  UINT32 max_entries;
+  UINT32 num_entries;
+  UINT32 flags;
+  UINT32 entry_align;
+  UINT32 max_offset;
+  struct imd_entry entries[0];
+};
+
+struct cbuint64 {
+  UINT32 lo;
+  UINT32 hi;
+};
+
+#define CB_HEADER_SIGNATURE 0x4F49424C
+
+struct cb_header {
+  UINT32 signature;
+  UINT32 header_bytes;
+  UINT32 header_checksum;
+  UINT32 table_bytes;
+  UINT32 table_checksum;
+  UINT32 table_entries;
+};
+
+struct cb_record {
+  UINT32 tag;
+  UINT32 size;
+};
+
+#define CB_TAG_UNUSED     0x0000
+#define CB_TAG_MEMORY     0x0001
+
+struct cb_memory_range {
+  struct cbuint64 start;
+  struct cbuint64 size;
+  UINT32 type;
+};
+
+#define CB_MEM_RAM    1
+#define CB_MEM_RESERVED     2
+#define CB_MEM_ACPI   3
+#define CB_MEM_NVS    4
+#define CB_MEM_UNUSABLE     5
+#define CB_MEM_VENDOR_RSVD  6
+#define CB_MEM_TABLE       16
+
+struct cb_memory {
+  UINT32 tag;
+  UINT32 size;
+  struct cb_memory_range map[0];
+};
+
+#define CB_TAG_MAINBOARD  0x0003
+
+struct cb_mainboard {
+  UINT32 tag;
+  UINT32 size;
+  UINT8 vendor_idx;
+  UINT8 part_number_idx;
+  UINT8 strings[0];
+};
+#define CB_TAG_VERSION  0x0004
+#define CB_TAG_EXTRA_VERSION  0x0005
+#define CB_TAG_BUILD    0x0006
+#define CB_TAG_COMPILE_TIME   0x0007
+#define CB_TAG_COMPILE_BY     0x0008
+#define CB_TAG_COMPILE_HOST   0x0009
+#define CB_TAG_COMPILE_DOMAIN 0x000a
+#define CB_TAG_COMPILER       0x000b
+#define CB_TAG_LINKER   0x000c
+#define CB_TAG_ASSEMBLER      0x000d
+
+struct cb_string {
+  UINT32 tag;
+  UINT32 size;
+  UINT8 string[0];
+};
+
+#define CB_TAG_SERIAL   0x000f
+
+struct cb_serial {
+  UINT32 tag;
+  UINT32 size;
+#define CB_SERIAL_TYPE_IO_MAPPED     1
+#define CB_SERIAL_TYPE_MEMORY_MAPPED 2
+  UINT32 type;
+  UINT32 baseaddr;
+  UINT32 baud;
+  UINT32 regwidth;
+
+  // Crystal or input frequency to the chip containing the UART.
+  // Provide the board specific details to allow the payload to
+  // initialize the chip containing the UART and make independent
+  // decisions as to which dividers to select and their values
+  // to eventually arrive at the desired console baud-rate.
+  UINT32 input_hertz;
+
+  // UART PCI address: bus, device, function
+  // 1 << 31 - Valid bit, PCI UART in use
+  // Bus << 20
+  // Device << 15
+  // Function << 12
+  UINT32 uart_pci_addr;
+};
+
+#define CB_TAG_CONSOLE       0x00010
+
+struct cb_console {
+  UINT32 tag;
+  UINT32 size;
+  UINT16 type;
+};
+
+#define CB_TAG_CONSOLE_SERIAL8250 0
+#define CB_TAG_CONSOLE_VGA  1 // OBSOLETE
+#define CB_TAG_CONSOLE_BTEXT      2 // OBSOLETE
+#define CB_TAG_CONSOLE_LOGBUF     3
+#define CB_TAG_CONSOLE_SROM       4 // OBSOLETE
+#define CB_TAG_CONSOLE_EHCI       5
+
+#define CB_TAG_FORWARD       0x00011
+
+struct cb_forward {
+  UINT32 tag;
+  UINT32 size;
+  UINT64 forward;
+};
+
+#define CB_TAG_FRAMEBUFFER      0x0012
+struct cb_framebuffer {
+  UINT32 tag;
+  UINT32 size;
+
+  UINT64 physical_address;
+  UINT32 x_resolution;
+  UINT32 y_resolution;
+  UINT32 bytes_per_line;
+  UINT8 bits_per_pixel;
+  UINT8 red_mask_pos;
+  UINT8 red_mask_size;
+  UINT8 green_mask_pos;
+  UINT8 green_mask_size;
+  UINT8 blue_mask_pos;
+  UINT8 blue_mask_size;
+  UINT8 reserved_mask_pos;
+  UINT8 reserved_mask_size;
+};
+
+#define CB_TAG_VDAT     0x0015
+struct cb_vdat {
+  UINT32 tag;
+  UINT32 size;  /* size of the entire entry */
+  UINT64 vdat_addr;
+  UINT32 vdat_size;
+};
+
+#define CB_TAG_TIMESTAMPS       0x0016
+#define CB_TAG_CBMEM_CONSOLE    0x0017
+#define CB_TAG_MRC_CACHE  0x0018
+struct cb_cbmem_tab {
+  UINT32 tag;
+  UINT32 size;
+  UINT64 cbmem_tab;
+};
+
+/* Helpful macros */
+
+#define MEM_RANGE_COUNT(_rec) \
+  (((_rec)->size - sizeof(*(_rec))) / sizeof((_rec)->map[0]))
+
+#define MEM_RANGE_PTR(_rec, _idx) \
+  (void *)(((UINT8 *) (_rec)) + sizeof(*(_rec)) \
+    + (sizeof((_rec)->map[0]) * (_idx)))
+
+
+#endif // _COREBOOT_PEI_H_INCLUDED_
diff --git a/UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h b/UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h
new file mode 100644
index 0000000000..ff5b657fce
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/AcpiBoardInfoGuid.h
@@ -0,0 +1,35 @@
+/** @file
+  This file defines the hob structure for board related information from acpi table
+
+  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef __ACPI_BOARD_INFO_GUID_H__
+#define __ACPI_BOARD_INFO_GUID_H__
+
+///
+/// Board information GUID
+///
+extern EFI_GUID gUefiAcpiBoardInfoGuid;
+
+typedef struct {
+  UINT8              Revision;
+  UINT8              Reserved0[2];
+  UINT8              ResetValue;
+  UINT64             PmEvtBase;
+  UINT64             PmGpeEnBase;
+  UINT64             PmCtrlRegBase;
+  UINT64             PmTimerRegBase;
+  UINT64             ResetRegAddress;
+  UINT64             PcieBaseAddress;
+} ACPI_BOARD_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/FrameBufferInfoGuid.h b/UefiPayloadPkg/Include/Guid/FrameBufferInfoGuid.h
new file mode 100644
index 0000000000..4853b4a72c
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/FrameBufferInfoGuid.h
@@ -0,0 +1,42 @@
+/** @file
+  This file defines the hob structure for frame buffer device.
+
+  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef __FRAME_BUFFER_INFO_GUID_H__
+#define __FRAME_BUFFER_INFO_GUID_H__
+
+///
+/// Frame Buffer Information GUID
+///
+extern EFI_GUID gUefiFrameBufferInfoGuid;
+
+typedef struct {
+  UINT8 Position; // Position of the color
+  UINT8 Mask;     // The number of bits expressed as a mask
+} COLOR_PLACEMENT;
+
+typedef struct {
+  UINT8              Revision;
+  UINT8              Reserved0[3];
+  UINT64             LinearFrameBuffer;
+  UINT32             HorizontalResolution;
+  UINT32             VerticalResolution;
+  UINT32             BitsPerPixel;
+  UINT16             BytesPerScanLine;
+  COLOR_PLACEMENT    Red;
+  COLOR_PLACEMENT    Green;
+  COLOR_PLACEMENT    Blue;
+  COLOR_PLACEMENT    Reserved;
+} FRAME_BUFFER_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h b/UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h
new file mode 100644
index 0000000000..1ea4ad51ab
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/MemoryMapInfoGuid.h
@@ -0,0 +1,42 @@
+/** @file
+  This file defines the hob structure for memory map information.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef __MEMORY_MAP_INFO_GUID_H__
+#define __MEMORY_MAP_INFO_GUID_H__
+
+#include <Library/PcdLib.h>
+
+///
+/// Memory Map Information GUID
+///
+extern EFI_GUID gLoaderMemoryMapInfoGuid;
+
+#pragma pack(1)
+typedef struct {
+  UINT64 Base;
+  UINT64 Size;
+  UINT8  Type;
+  UINT8  Flag;
+  UINT8  Reserved[6];
+} MEMROY_MAP_ENTRY;
+
+typedef struct {
+  UINT8  Revision;
+  UINT8  Reserved0[3];
+  UINT32 Count;
+  MEMROY_MAP_ENTRY  Entry[0];
+} MEMROY_MAP_INFO;
+#pragma pack()
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h b/UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h
new file mode 100644
index 0000000000..8ae726169b
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/SerialPortInfoGuid.h
@@ -0,0 +1,37 @@
+/** @file
+  This file defines the hob structure for serial port.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef __SERIAL_PORT_INFO_GUID_H__
+#define __SERIAL_PORT_INFO_GUID_H__
+
+///
+/// Serial Port Information GUID
+///
+extern EFI_GUID gUefiSerialPortInfoGuid;
+
+#define PLD_SERIAL_TYPE_IO_MAPPED     1
+#define PLD_SERIAL_TYPE_MEMORY_MAPPED 2
+
+typedef struct {
+  UINT8  Revision;
+  UINT8  Reserved0[3];
+  UINT32 Type;
+  UINT32 BaseAddr;
+  UINT32 Baud;
+  UINT32 RegWidth;
+  UINT32 InputHertz;
+  UINT32 UartPciAddr;
+} SERIAL_PORT_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h b/UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h
new file mode 100644
index 0000000000..2bf6eed7bd
--- /dev/null
+++ b/UefiPayloadPkg/Include/Guid/SystemTableInfoGuid.h
@@ -0,0 +1,32 @@
+/** @file
+  This file defines the hob structure for system tables like ACPI, SMBIOS tables.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef __SYSTEM_TABLE_INFO_GUID_H__
+#define __SYSTEM_TABLE_INFO_GUID_H__
+
+///
+/// System Table Information GUID
+///
+extern EFI_GUID gUefiSystemTableInfoGuid;
+
+typedef struct {
+  UINT8     Revision;
+  UINT8     Reserved0[3];
+  UINT64    AcpiTableBase;
+  UINT32    AcpiTableSize;
+  UINT64    SmbiosTableBase;
+  UINT32    SmbiosTableSize;
+} SYSTEM_TABLE_INFO;
+
+#endif
diff --git a/UefiPayloadPkg/Include/Library/BlParseLib.h b/UefiPayloadPkg/Include/Library/BlParseLib.h
new file mode 100644
index 0000000000..53070e68c4
--- /dev/null
+++ b/UefiPayloadPkg/Include/Library/BlParseLib.h
@@ -0,0 +1,111 @@
+/** @file
+  This library will parse the coreboot table in memory and extract those required
+  information.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+#include <PiPei.h>
+#include <Guid/FrameBufferInfoGuid.h>
+#include <Guid/MemoryMapInfoGuid.h>
+#include <Guid/SerialPortInfoGuid.h>
+#include <Guid/SystemTableInfoGuid.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+
+#ifndef __BOOTLOADER_PARSE_LIB__
+#define __BOOTLOADER_PARSE_LIB__
+
+#define GET_BOOTLOADER_PARAMETER()      (*(UINT32 *)(UINTN)(PcdGet32(PcdPayloadStackTop) - sizeof(UINT32)))
+#define SET_BOOTLOADER_PARAMETER(Value) GET_BOOTLOADER_PARAMETER()=Value
+
+typedef RETURN_STATUS \
+        (*BL_MEM_INFO_CALLBACK) (MEMROY_MAP_ENTRY *MemoryMapEntry, VOID *Param);
+
+/**
+  This function retrieves the parameter base address from boot loader.
+
+  This function will get bootloader specific parameter address for UEFI payload.
+  e.g. HobList pointer for Slim Bootloader, and coreboot table header for Coreboot.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+EFIAPI
+GetParameterBase (
+  VOID
+  );
+
+/**
+  Acquire the memory map information.
+
+  @param  MemInfoCallback     The callback routine
+  @param  Params              Pointer to the callback routine parameter
+
+  @retval RETURN_SUCCESS     Successfully find out the memory information.
+  @retval RETURN_NOT_FOUND   Failed to find the memory information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseMemoryInfo (
+  IN  BL_MEM_INFO_CALLBACK       MemInfoCallback,
+  IN  VOID                       *Params
+  );
+
+/**
+  Acquire acpi table and smbios table from slim bootloader
+
+  @param  SystemTableInfo           Pointer to the system table info
+
+  @retval RETURN_SUCCESS            Successfully find out the tables.
+  @retval RETURN_NOT_FOUND          Failed to find the tables.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSystemTable (
+  OUT SYSTEM_TABLE_INFO     *SystemTableInfo
+  );
+
+
+/**
+  Find the serial port information
+
+  @param  SERIAL_PORT_INFO   Pointer to serial port info structure
+
+  @retval RETURN_SUCCESS     Successfully find the serial port information.
+  @retval RETURN_NOT_FOUND   Failed to find the serial port information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSerialInfo (
+  OUT SERIAL_PORT_INFO     *SerialPortInfo
+  );
+
+
+/**
+  Find the video frame buffer information
+
+  @param   FbInfo            Pointer to the FRAME_BUFFER_INFO structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseFbInfo (
+  OUT FRAME_BUFFER_INFO       *FbInfo
+  );
+
+#endif
diff --git a/UefiPayloadPkg/Include/Library/PlatformSupportLib.h b/UefiPayloadPkg/Include/Library/PlatformSupportLib.h
new file mode 100644
index 0000000000..b8136b6a0a
--- /dev/null
+++ b/UefiPayloadPkg/Include/Library/PlatformSupportLib.h
@@ -0,0 +1,34 @@
+/** @file
+  Bootloader Platform Support library. Platform can provide an implementation of this
+  library class to provide hooks that may be required for some type of
+  platform features.
+
+Copyright (c) 2016 - 2019, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials are licensed and made available under
+the terms and conditions of the BSD License that accompanies this distribution.
+The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php.
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef __BOOTLOADER_PLATFORM_SUPPORT_LIB__
+#define __BOOTLOADER_PLATFORM_SUPPORT_LIB__
+
+/**
+  Parse platform specific information from bootloader
+
+  @retval RETURN_SUCCESS       The platform specific coreboot support succeeded.
+  @retval RETURN_DEVICE_ERROR  The platform specific coreboot support could not be completed.
+
+**/
+EFI_STATUS
+EFIAPI
+ParsePlatformInfo (
+  VOID
+  );
+
+#endif // __BOOTLOADER_PLATFORM_SUPPORT_LIB__
+
diff --git a/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c
new file mode 100644
index 0000000000..a3af1fc292
--- /dev/null
+++ b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.c
@@ -0,0 +1,276 @@
+/** @file
+  ACPI Timer implements one instance of Timer Library.
+
+  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials are
+  licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <PiPei.h>
+#include <Library/TimerLib.h>
+#include <Library/BaseLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+#include <Library/DebugLib.h>
+
+#include <Guid/AcpiBoardInfoGuid.h>
+#include <IndustryStandard/Acpi.h>
+
+#define ACPI_TIMER_COUNT_SIZE  BIT24
+
+UINTN mPmTimerReg = 0;
+
+/**
+  The constructor function enables ACPI IO space.
+
+  If ACPI I/O space not enabled, this function will enable it.
+  It will always return RETURN_SUCCESS.
+
+  @retval EFI_SUCCESS   The constructor always returns RETURN_SUCCESS.
+
+**/
+RETURN_STATUS
+EFIAPI
+AcpiTimerLibConstructor (
+  VOID
+  )
+{
+  EFI_HOB_GUID_TYPE  *GuidHob;
+  ACPI_BOARD_INFO    *pAcpiBoardInfo;
+
+  //
+  // Find the acpi board information guid hob
+  //
+  GuidHob = GetFirstGuidHob (&gUefiAcpiBoardInfoGuid);
+  ASSERT (GuidHob != NULL);
+
+  pAcpiBoardInfo = (ACPI_BOARD_INFO *)GET_GUID_HOB_DATA (GuidHob);
+
+  mPmTimerReg = (UINTN)pAcpiBoardInfo->PmTimerRegBase;
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Internal function to read the current tick counter of ACPI.
+
+  Internal function to read the current tick counter of ACPI.
+
+  @return The tick counter read.
+
+**/
+UINT32
+InternalAcpiGetTimerTick (
+  VOID
+  )
+{
+  if (mPmTimerReg == 0) {
+    AcpiTimerLibConstructor ();
+  }
+  return IoRead32 (mPmTimerReg);
+}
+
+/**
+  Stalls the CPU for at least the given number of ticks.
+
+  Stalls the CPU for at least the given number of ticks. It's invoked by
+  MicroSecondDelay() and NanoSecondDelay().
+
+  @param  Delay     A period of time to delay in ticks.
+
+**/
+VOID
+InternalAcpiDelay (
+  IN      UINT32                    Delay
+  )
+{
+  UINT32                            Ticks;
+  UINT32                            Times;
+
+  Times    = Delay >> 22;
+  Delay   &= BIT22 - 1;
+  do {
+    //
+    // The target timer count is calculated here
+    //
+    Ticks    = InternalAcpiGetTimerTick () + Delay;
+    Delay    = BIT22;
+    //
+    // Wait until time out
+    // Delay >= 2^23 could not be handled by this function
+    // Timer wrap-arounds are handled correctly by this function
+    //
+    while (((Ticks - InternalAcpiGetTimerTick ()) & BIT23) == 0) {
+      CpuPause ();
+    }
+  } while (Times-- > 0);
+}
+
+/**
+  Stalls the CPU for at least the given number of microseconds.
+
+  Stalls the CPU for the number of microseconds specified by MicroSeconds.
+
+  @param  MicroSeconds  The minimum number of microseconds to delay.
+
+  @return MicroSeconds
+
+**/
+UINTN
+EFIAPI
+MicroSecondDelay (
+  IN UINTN                          MicroSeconds
+  )
+{
+  InternalAcpiDelay (
+    (UINT32)DivU64x32 (
+              MultU64x32 (
+                MicroSeconds,
+                ACPI_TIMER_FREQUENCY
+                ),
+              1000000u
+              )
+    );
+  return MicroSeconds;
+}
+
+/**
+  Stalls the CPU for at least the given number of nanoseconds.
+
+  Stalls the CPU for the number of nanoseconds specified by NanoSeconds.
+
+  @param  NanoSeconds The minimum number of nanoseconds to delay.
+
+  @return NanoSeconds
+
+**/
+UINTN
+EFIAPI
+NanoSecondDelay (
+  IN      UINTN                     NanoSeconds
+  )
+{
+  InternalAcpiDelay (
+    (UINT32)DivU64x32 (
+              MultU64x32 (
+                NanoSeconds,
+                ACPI_TIMER_FREQUENCY
+                ),
+              1000000000u
+              )
+    );
+  return NanoSeconds;
+}
+
+/**
+  Retrieves the current value of a 64-bit free running performance counter.
+
+  Retrieves the current value of a 64-bit free running performance counter. The
+  counter can either count up by 1 or count down by 1. If the physical
+  performance counter counts by a larger increment, then the counter values
+  must be translated. The properties of the counter can be retrieved from
+  GetPerformanceCounterProperties().
+
+  @return The current value of the free running performance counter.
+
+**/
+UINT64
+EFIAPI
+GetPerformanceCounter (
+  VOID
+  )
+{
+  return (UINT64)InternalAcpiGetTimerTick ();
+}
+
+/**
+  Retrieves the 64-bit frequency in Hz and the range of performance counter
+  values.
+
+  If StartValue is not NULL, then the value that the performance counter starts
+  with immediately after is it rolls over is returned in StartValue. If
+  EndValue is not NULL, then the value that the performance counter end with
+  immediately before it rolls over is returned in EndValue. The 64-bit
+  frequency of the performance counter in Hz is always returned. If StartValue
+  is less than EndValue, then the performance counter counts up. If StartValue
+  is greater than EndValue, then the performance counter counts down. For
+  example, a 64-bit free running counter that counts up would have a StartValue
+  of 0 and an EndValue of 0xFFFFFFFFFFFFFFFF. A 24-bit free running counter
+  that counts down would have a StartValue of 0xFFFFFF and an EndValue of 0.
+
+  @param  StartValue  The value the performance counter starts with when it
+                      rolls over.
+  @param  EndValue    The value that the performance counter ends with before
+                      it rolls over.
+
+  @return The frequency in Hz.
+
+**/
+UINT64
+EFIAPI
+GetPerformanceCounterProperties (
+  OUT      UINT64                    *StartValue,  OPTIONAL
+  OUT      UINT64                    *EndValue     OPTIONAL
+  )
+{
+  if (StartValue != NULL) {
+    *StartValue = 0;
+  }
+
+  if (EndValue != NULL) {
+    *EndValue = ACPI_TIMER_COUNT_SIZE - 1;
+  }
+
+  return ACPI_TIMER_FREQUENCY;
+}
+
+/**
+  Converts elapsed ticks of performance counter to time in nanoseconds.
+
+  This function converts the elapsed ticks of running performance counter to
+  time value in unit of nanoseconds.
+
+  @param  Ticks     The number of elapsed ticks of running performance counter.
+
+  @return The elapsed time in nanoseconds.
+
+**/
+UINT64
+EFIAPI
+GetTimeInNanoSecond (
+  IN      UINT64                     Ticks
+  )
+{
+  UINT64  Frequency;
+  UINT64  NanoSeconds;
+  UINT64  Remainder;
+  INTN    Shift;
+
+  Frequency = GetPerformanceCounterProperties (NULL, NULL);
+
+  //
+  //          Ticks
+  // Time = --------- x 1,000,000,000
+  //        Frequency
+  //
+  NanoSeconds = MultU64x32 (DivU64x64Remainder (Ticks, Frequency, &Remainder), 1000000000u);
+
+  //
+  // Ensure (Remainder * 1,000,000,000) will not overflow 64-bit.
+  // Since 2^29 < 1,000,000,000 = 0x3B9ACA00 < 2^30, Remainder should < 2^(64-30) = 2^34,
+  // i.e. highest bit set in Remainder should <= 33.
+  //
+  Shift = MAX (0, HighBitSet64 (Remainder) - 33);
+  Remainder = RShiftU64 (Remainder, (UINTN) Shift);
+  Frequency = RShiftU64 (Frequency, (UINTN) Shift);
+  NanoSeconds += DivU64x64Remainder (MultU64x32 (Remainder, 1000000000u), Frequency, NULL);
+
+  return NanoSeconds;
+}
+
diff --git a/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
new file mode 100644
index 0000000000..36d9afa47f
--- /dev/null
+++ b/UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
@@ -0,0 +1,46 @@
+## @file
+#  ACPI Timer Library Instance.
+#
+#  Copyright (c) 2014 - 2018, Intel Corporation. All rights reserved.<BR>
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution.  The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = AcpiTimerLib
+  FILE_GUID                      = A41BF616-EF77-4658-9992-D813071C34CF
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = TimerLib
+
+  CONSTRUCTOR                    = AcpiTimerLibConstructor
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  AcpiTimerLib.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  IoLib
+  HobLib
+  DebugLib
+
+[Guids]
+  gUefiAcpiBoardInfoGuid
diff --git a/UefiPayloadPkg/Library/CbParseLib/CbParseLib.c b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.c
new file mode 100644
index 0000000000..752834aecc
--- /dev/null
+++ b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.c
@@ -0,0 +1,543 @@
+/** @file
+  This library will parse the coreboot table in memory and extract those required
+  information.
+
+  Copyright (c) 2014 - 2016, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <Uefi/UefiBaseType.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/IoLib.h>
+#include <Library/BlParseLib.h>
+#include <IndustryStandard/Acpi.h>
+#include <Coreboot.h>
+
+
+/**
+  Convert a packed value from cbuint64 to a UINT64 value.
+
+  @param  val      The pointer to packed data.
+
+  @return          the UNIT64 value after conversion.
+
+**/
+UINT64
+cb_unpack64 (
+  IN struct cbuint64 val
+  )
+{
+  return LShiftU64 (val.hi, 32) | val.lo;
+}
+
+
+/**
+  Returns the sum of all elements in a buffer of 16-bit values.  During
+  calculation, the carry bits are also been added.
+
+  @param  Buffer      The pointer to the buffer to carry out the sum operation.
+  @param  Length      The size, in bytes, of Buffer.
+
+  @return Sum         The sum of Buffer with carry bits included during additions.
+
+**/
+UINT16
+CbCheckSum16 (
+  IN UINT16   *Buffer,
+  IN UINTN    Length
+  )
+{
+  UINT32      Sum;
+  UINT32      TmpValue;
+  UINTN       Idx;
+  UINT8       *TmpPtr;
+
+  Sum = 0;
+  TmpPtr = (UINT8 *)Buffer;
+  for(Idx = 0; Idx < Length; Idx++) {
+    TmpValue  = TmpPtr[Idx];
+    if (Idx % 2 == 1) {
+      TmpValue <<= 8;
+    }
+
+    Sum += TmpValue;
+
+    // Wrap
+    if (Sum >= 0x10000) {
+      Sum = (Sum + (Sum >> 16)) & 0xFFFF;
+    }
+  }
+
+  return (UINT16)((~Sum) & 0xFFFF);
+}
+
+
+/**
+  Check the coreboot table if it is valid.
+
+  @param  Header            Pointer to coreboot table
+
+  @retval TRUE              The coreboot table is valid.
+  @retval Others            The coreboot table is not valid.
+
+**/
+BOOLEAN
+IsValidCbTable (
+  IN struct cb_header   *Header
+  )
+{
+  UINT16                 CheckSum;
+
+  if ((Header == NULL) || (Header->table_bytes == 0)) {
+    return FALSE;
+  }
+
+  if (Header->signature != CB_HEADER_SIGNATURE) {
+    return FALSE;
+  }
+
+  //
+  // Check the checksum of the coreboot table header
+  //
+  CheckSum = CbCheckSum16 ((UINT16 *)Header, sizeof (*Header));
+  if (CheckSum != 0) {
+    DEBUG ((DEBUG_ERROR, "Invalid coreboot table header checksum\n"));
+    return FALSE;
+  }
+
+  CheckSum = CbCheckSum16 ((UINT16 *)((UINT8 *)Header + sizeof (*Header)), Header->table_bytes);
+  if (CheckSum != Header->table_checksum) {
+    DEBUG ((DEBUG_ERROR, "Incorrect checksum of all the coreboot table entries\n"));
+    return FALSE;
+  }
+
+  return TRUE;
+}
+
+
+/**
+  This function retrieves the parameter base address from boot loader.
+
+  This function will get bootloader specific parameter address for UEFI payload.
+  e.g. HobList pointer for Slim Bootloader, and coreboot table header for Coreboot.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+EFIAPI
+GetParameterBase (
+  VOID
+  )
+{
+  struct cb_header   *Header;
+  struct cb_record   *Record;
+  UINT8              *TmpPtr;
+  UINT8              *CbTablePtr;
+  UINTN              Idx;
+
+  //
+  // coreboot could pass coreboot table to UEFI payload
+  //
+  Header = (struct cb_header *)(UINTN)GET_BOOTLOADER_PARAMETER ();
+  if (IsValidCbTable (Header)) {
+    return Header;
+  }
+
+  //
+  // Find simplified coreboot table in memory range 0 ~ 4KB.
+  // Some GCC version does not allow directly access to NULL pointer,
+  // so start the search from 0x10 instead.
+  //
+  for (Idx = 16; Idx < 4096; Idx += 16) {
+    Header = (struct cb_header *)Idx;
+    if (Header->signature == CB_HEADER_SIGNATURE) {
+      break;
+    }
+  }
+
+  if (Idx >= 4096) {
+    return NULL;
+  }
+
+  //
+  // Check the coreboot header
+  //
+  if (!IsValidCbTable (Header)) {
+    return NULL;
+  }
+
+  //
+  // Find full coreboot table in high memory
+  //
+  CbTablePtr = NULL;
+  TmpPtr = (UINT8 *)Header + Header->header_bytes;
+  for (Idx = 0; Idx < Header->table_entries; Idx++) {
+    Record = (struct cb_record *)TmpPtr;
+    if (Record->tag == CB_TAG_FORWARD) {
+      CbTablePtr = (VOID *)(UINTN)((struct cb_forward *)(UINTN)Record)->forward;
+      break;
+    }
+    TmpPtr += Record->size;
+  }
+
+  //
+  // Check the coreboot header in high memory
+  //
+  if (!IsValidCbTable ((struct cb_header *)CbTablePtr)) {
+    return NULL;
+  }
+
+  SET_BOOTLOADER_PARAMETER ((UINT32)(UINTN)CbTablePtr);
+
+  return CbTablePtr;
+}
+
+
+/**
+  Find coreboot record with given Tag.
+
+  @param  Tag                The tag id to be found
+
+  @retval NULL              The Tag is not found.
+  @retval Others            The pointer to the record found.
+
+**/
+VOID *
+FindCbTag (
+  IN  UINT32         Tag
+  )
+{
+  struct cb_header   *Header;
+  struct cb_record   *Record;
+  UINT8              *TmpPtr;
+  UINT8              *TagPtr;
+  UINTN              Idx;
+
+  Header = (struct cb_header *) GetParameterBase ();
+
+  TagPtr = NULL;
+  TmpPtr = (UINT8 *)Header + Header->header_bytes;
+  for (Idx = 0; Idx < Header->table_entries; Idx++) {
+    Record = (struct cb_record *)TmpPtr;
+    if (Record->tag == Tag) {
+      TagPtr = TmpPtr;
+      break;
+    }
+    TmpPtr += Record->size;
+  }
+
+  return TagPtr;
+}
+
+
+/**
+  Find the given table with TableId from the given coreboot memory Root.
+
+  @param  Root               The coreboot memory table to be searched in
+  @param  TableId            Table id to be found
+  @param  MemTable           To save the base address of the memory table found
+  @param  MemTableSize       To save the size of memory table found
+
+  @retval RETURN_SUCCESS            Successfully find out the memory table.
+  @retval RETURN_INVALID_PARAMETER  Invalid input parameters.
+  @retval RETURN_NOT_FOUND          Failed to find the memory table.
+
+**/
+RETURN_STATUS
+FindCbMemTable (
+  IN  struct cbmem_root  *Root,
+  IN  UINT32             TableId,
+  OUT VOID               **MemTable,
+  OUT UINT32             *MemTableSize
+  )
+{
+  UINTN                  Idx;
+  BOOLEAN                IsImdEntry;
+  struct cbmem_entry     *Entries;
+
+  if ((Root == NULL) || (MemTable == NULL)) {
+    return RETURN_INVALID_PARAMETER;
+  }
+  //
+  // Check if the entry is CBMEM or IMD
+  // and handle them separately
+  //
+  Entries = Root->entries;
+  if (Entries[0].magic == CBMEM_ENTRY_MAGIC) {
+    IsImdEntry = FALSE;
+  } else {
+    Entries = (struct cbmem_entry *)((struct imd_root *)Root)->entries;
+    if (Entries[0].magic == IMD_ENTRY_MAGIC) {
+      IsImdEntry = TRUE;
+    } else {
+      return RETURN_NOT_FOUND;
+    }
+  }
+
+  for (Idx = 0; Idx < Root->num_entries; Idx++) {
+    if (Entries[Idx].id == TableId) {
+      if (IsImdEntry) {
+        *MemTable = (VOID *) ((UINTN)Entries[Idx].start + (UINTN)Root);
+      } else {
+        *MemTable = (VOID *) (UINTN)Entries[Idx].start;
+      }
+      if (MemTableSize != NULL) {
+        *MemTableSize = Entries[Idx].size;
+      }
+
+      DEBUG ((DEBUG_INFO, "Find CbMemTable Id 0x%x, base %p, size 0x%x\n",
+        TableId, *MemTable, Entries[Idx].size));
+      return RETURN_SUCCESS;
+    }
+  }
+
+  return RETURN_NOT_FOUND;
+}
+
+/**
+  Acquire the coreboot memory table with the given table id
+
+  @param  TableId            Table id to be searched
+  @param  MemTable           Pointer to the base address of the memory table
+  @param  MemTableSize       Pointer to the size of the memory table
+
+  @retval RETURN_SUCCESS     Successfully find out the memory table.
+  @retval RETURN_INVALID_PARAMETER  Invalid input parameters.
+  @retval RETURN_NOT_FOUND   Failed to find the memory table.
+
+**/
+RETURN_STATUS
+ParseCbMemTable (
+  IN  UINT32               TableId,
+  OUT VOID                 **MemTable,
+  OUT UINT32               *MemTableSize
+  )
+{
+  EFI_STATUS               Status;
+  struct cb_memory         *rec;
+  struct cb_memory_range   *Range;
+  UINT64                   Start;
+  UINT64                   Size;
+  UINTN                    Index;
+  struct cbmem_root        *CbMemRoot;
+
+  if (MemTable == NULL) {
+    return RETURN_INVALID_PARAMETER;
+  }
+
+  *MemTable = NULL;
+  Status    = RETURN_NOT_FOUND;
+
+  //
+  // Get the coreboot memory table
+  //
+  rec = (struct cb_memory *)FindCbTag (CB_TAG_MEMORY);
+  if (rec == NULL) {
+    return Status;
+  }
+
+  for (Index = 0; Index < MEM_RANGE_COUNT(rec); Index++) {
+    Range = MEM_RANGE_PTR(rec, Index);
+    Start = cb_unpack64(Range->start);
+    Size = cb_unpack64(Range->size);
+
+    if ((Range->type == CB_MEM_TABLE) && (Start > 0x1000)) {
+      CbMemRoot = (struct  cbmem_root *)(UINTN)(Start + Size - DYN_CBMEM_ALIGN_SIZE);
+      Status = FindCbMemTable (CbMemRoot, TableId, MemTable, MemTableSize);
+      if (!EFI_ERROR (Status)) {
+        break;
+      }
+    }
+  }
+
+  return Status;
+}
+
+
+
+/**
+  Acquire the memory information from the coreboot table in memory.
+
+  @param  MemInfoCallback     The callback routine
+  @param  Params              Pointer to the callback routine parameter
+
+  @retval RETURN_SUCCESS     Successfully find out the memory information.
+  @retval RETURN_NOT_FOUND   Failed to find the memory information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseMemoryInfo (
+  IN  BL_MEM_INFO_CALLBACK  MemInfoCallback,
+  IN  VOID                  *Params
+  )
+{
+  struct cb_memory         *rec;
+  struct cb_memory_range   *Range;
+  UINTN                    Index;
+  MEMROY_MAP_ENTRY         MemoryMap;
+
+  //
+  // Get the coreboot memory table
+  //
+  rec = (struct cb_memory *)FindCbTag (CB_TAG_MEMORY);
+  if (rec == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  for (Index = 0; Index < MEM_RANGE_COUNT(rec); Index++) {
+    Range = MEM_RANGE_PTR(rec, Index);
+    MemoryMap.Base = cb_unpack64(Range->start);
+    MemoryMap.Size = cb_unpack64(Range->size);
+    MemoryMap.Type = (UINT8)Range->type;
+    MemoryMap.Flag = 0;
+    DEBUG ((DEBUG_INFO, "%d. %016lx - %016lx [%02x]\n",
+            Index, MemoryMap.Base, MemoryMap.Base + MemoryMap.Size - 1, MemoryMap.Type));
+
+    MemInfoCallback (&MemoryMap, Params);
+  }
+
+  return RETURN_SUCCESS;
+}
+
+
+/**
+  Acquire acpi table and smbios table from coreboot
+
+  @param  SystemTableInfo          Pointer to the system table info
+
+  @retval RETURN_SUCCESS            Successfully find out the tables.
+  @retval RETURN_NOT_FOUND          Failed to find the tables.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSystemTable (
+  OUT SYSTEM_TABLE_INFO     *SystemTableInfo
+  )
+{
+  EFI_STATUS       Status;
+  VOID             *MemTable;
+  UINT32           MemTableSize;
+
+  Status = ParseCbMemTable (SIGNATURE_32 ('T', 'B', 'M', 'S'), &MemTable, &MemTableSize);
+  if (EFI_ERROR (Status)) {
+    return EFI_NOT_FOUND;
+  }
+  SystemTableInfo->SmbiosTableBase = (UINT64) (UINTN)MemTable;
+  SystemTableInfo->SmbiosTableSize = MemTableSize;
+
+  Status = ParseCbMemTable (SIGNATURE_32 ('I', 'P', 'C', 'A'), &MemTable, &MemTableSize);
+  if (EFI_ERROR (Status)) {
+    return EFI_NOT_FOUND;
+  }
+  SystemTableInfo->AcpiTableBase = (UINT64) (UINTN)MemTable;
+  SystemTableInfo->AcpiTableSize = MemTableSize;
+
+  return Status;
+}
+
+
+/**
+  Find the serial port information
+
+  @param  SERIAL_PORT_INFO   Pointer to serial port info structure
+
+  @retval RETURN_SUCCESS     Successfully find the serial port information.
+  @retval RETURN_NOT_FOUND   Failed to find the serial port information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSerialInfo (
+  OUT SERIAL_PORT_INFO     *SerialPortInfo
+  )
+{
+  struct cb_serial          *CbSerial;
+
+  CbSerial = FindCbTag (CB_TAG_SERIAL);
+  if (CbSerial == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  SerialPortInfo->BaseAddr    = CbSerial->baseaddr;
+  SerialPortInfo->RegWidth    = CbSerial->regwidth;
+  SerialPortInfo->Type        = CbSerial->type;
+  SerialPortInfo->Baud        = CbSerial->baud;
+  SerialPortInfo->InputHertz  = CbSerial->input_hertz;
+  SerialPortInfo->UartPciAddr = CbSerial->uart_pci_addr;
+
+  return RETURN_SUCCESS;
+}
+
+/**
+  Find the video frame buffer information
+
+  @param  FbInfo            Pointer to the FRAME_BUFFER_INFO structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseFbInfo (
+  OUT FRAME_BUFFER_INFO       *FbInfo
+  )
+{
+  struct cb_framebuffer       *CbFbRec;
+
+  if (FbInfo == NULL) {
+    return RETURN_INVALID_PARAMETER;
+  }
+
+  CbFbRec = FindCbTag (CB_TAG_FRAMEBUFFER);
+  if (CbFbRec == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  DEBUG ((DEBUG_INFO, "Found coreboot video frame buffer information\n"));
+  DEBUG ((DEBUG_INFO, "physical_address: 0x%lx\n", CbFbRec->physical_address));
+  DEBUG ((DEBUG_INFO, "x_resolution: 0x%x\n", CbFbRec->x_resolution));
+  DEBUG ((DEBUG_INFO, "y_resolution: 0x%x\n", CbFbRec->y_resolution));
+  DEBUG ((DEBUG_INFO, "bits_per_pixel: 0x%x\n", CbFbRec->bits_per_pixel));
+  DEBUG ((DEBUG_INFO, "bytes_per_line: 0x%x\n", CbFbRec->bytes_per_line));
+
+  DEBUG ((DEBUG_INFO, "red_mask_size: 0x%x\n", CbFbRec->red_mask_size));
+  DEBUG ((DEBUG_INFO, "red_mask_pos: 0x%x\n", CbFbRec->red_mask_pos));
+  DEBUG ((DEBUG_INFO, "green_mask_size: 0x%x\n", CbFbRec->green_mask_size));
+  DEBUG ((DEBUG_INFO, "green_mask_pos: 0x%x\n", CbFbRec->green_mask_pos));
+  DEBUG ((DEBUG_INFO, "blue_mask_size: 0x%x\n", CbFbRec->blue_mask_size));
+  DEBUG ((DEBUG_INFO, "blue_mask_pos: 0x%x\n", CbFbRec->blue_mask_pos));
+  DEBUG ((DEBUG_INFO, "reserved_mask_size: 0x%x\n", CbFbRec->reserved_mask_size));
+  DEBUG ((DEBUG_INFO, "reserved_mask_pos: 0x%x\n", CbFbRec->reserved_mask_pos));
+
+  FbInfo->LinearFrameBuffer    = CbFbRec->physical_address;
+  FbInfo->HorizontalResolution = CbFbRec->x_resolution;
+  FbInfo->VerticalResolution   = CbFbRec->y_resolution;
+  FbInfo->BitsPerPixel         = CbFbRec->bits_per_pixel;
+  FbInfo->BytesPerScanLine     = (UINT16)CbFbRec->bytes_per_line;
+  FbInfo->Red.Mask             = (1 << CbFbRec->red_mask_size) - 1;
+  FbInfo->Red.Position         = CbFbRec->red_mask_pos;
+  FbInfo->Green.Mask           = (1 << CbFbRec->green_mask_size) - 1;
+  FbInfo->Green.Position       = CbFbRec->green_mask_pos;
+  FbInfo->Blue.Mask            = (1 << CbFbRec->blue_mask_size) - 1;
+  FbInfo->Blue.Position        = CbFbRec->blue_mask_pos;
+  FbInfo->Reserved.Mask        = (1 << CbFbRec->reserved_mask_size) - 1;
+  FbInfo->Reserved.Position    = CbFbRec->reserved_mask_pos;
+
+  return RETURN_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
new file mode 100644
index 0000000000..822252c67e
--- /dev/null
+++ b/UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
@@ -0,0 +1,45 @@
+## @file
+#  Coreboot Table Parse Library.
+#
+#  Copyright (c) 2014, Intel Corporation. All rights reserved.<BR>
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution.  The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = CbParseLib
+  FILE_GUID                      = 49EDFC9E-5945-4386-9C0B-C9B60CD45BB1
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = BlParseLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources]
+  CbParseLib.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  BaseMemoryLib
+  IoLib
+  DebugLib
+  PcdLib
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h
new file mode 100644
index 0000000000..c777cdbac1
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridge.h
@@ -0,0 +1,86 @@
+/** @file
+  Header file of PciHostBridgeLib.
+
+  Copyright (C) 2016, Red Hat, Inc.
+  Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+
+  This program and the accompanying materials are licensed and made available
+  under the terms and conditions of the BSD License which accompanies this
+  distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, WITHOUT
+  WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef _PCI_HOST_BRIDGE_H
+#define _PCI_HOST_BRIDGE_H
+
+typedef struct {
+  ACPI_HID_DEVICE_PATH     AcpiDevicePath;
+  EFI_DEVICE_PATH_PROTOCOL EndDevicePath;
+} CB_PCI_ROOT_BRIDGE_DEVICE_PATH;
+
+PCI_ROOT_BRIDGE *
+ScanForRootBridges (
+  UINTN      *NumberOfRootBridges
+);
+
+/**
+  Initialize a PCI_ROOT_BRIDGE structure.
+
+  @param[in]  Supports         Supported attributes.
+
+  @param[in]  Attributes       Initial attributes.
+
+  @param[in]  AllocAttributes  Allocation attributes.
+
+  @param[in]  RootBusNumber    The bus number to store in RootBus.
+
+  @param[in]  MaxSubBusNumber  The inclusive maximum bus number that can be
+                               assigned to any subordinate bus found behind any
+                               PCI bridge hanging off this root bus.
+
+                               The caller is responsible for ensuring that
+                               RootBusNumber <= MaxSubBusNumber. If
+                               RootBusNumber equals MaxSubBusNumber, then the
+                               root bus has no room for subordinate buses.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+
+  @param[out] RootBus          The PCI_ROOT_BRIDGE structure (allocated by the
+                               caller) that should be filled in by this
+                               function.
+
+  @retval EFI_SUCCESS           Initialization successful. A device path
+                                consisting of an ACPI device path node, with
+                                UID = RootBusNumber, has been allocated and
+                                linked into RootBus.
+
+  @retval EFI_OUT_OF_RESOURCES  Memory allocation failed.
+**/
+EFI_STATUS
+InitRootBridge (
+  IN  UINT64                   Supports,
+  IN  UINT64                   Attributes,
+  IN  UINT64                   AllocAttributes,
+  IN  UINT8                    RootBusNumber,
+  IN  UINT8                    MaxSubBusNumber,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Io,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Mem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *MemAbove4G,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMemAbove4G,
+  OUT PCI_ROOT_BRIDGE          *RootBus
+);
+
+#endif
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c
new file mode 100644
index 0000000000..d41c357f0e
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.c
@@ -0,0 +1,228 @@
+/** @file
+  Library instance of PciHostBridgeLib library class for coreboot.
+
+  Copyright (C) 2016, Red Hat, Inc.
+  Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+
+  This program and the accompanying materials are licensed and made available
+  under the terms and conditions of the BSD License which accompanies this
+  distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, WITHOUT
+  WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+#include <PiDxe.h>
+
+#include <IndustryStandard/Pci.h>
+#include <Protocol/PciHostBridgeResourceAllocation.h>
+#include <Protocol/PciRootBridgeIo.h>
+
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/PciHostBridgeLib.h>
+#include <Library/PciLib.h>
+
+#include "PciHostBridge.h"
+
+STATIC
+CONST
+CB_PCI_ROOT_BRIDGE_DEVICE_PATH mRootBridgeDevicePathTemplate = {
+  {
+    {
+      ACPI_DEVICE_PATH,
+      ACPI_DP,
+      {
+        (UINT8) (sizeof(ACPI_HID_DEVICE_PATH)),
+        (UINT8) ((sizeof(ACPI_HID_DEVICE_PATH)) >> 8)
+      }
+    },
+    EISA_PNP_ID(0x0A03), // HID
+    0                    // UID
+  },
+
+  {
+    END_DEVICE_PATH_TYPE,
+    END_ENTIRE_DEVICE_PATH_SUBTYPE,
+    {
+      END_DEVICE_PATH_LENGTH,
+      0
+    }
+  }
+};
+
+
+/**
+  Initialize a PCI_ROOT_BRIDGE structure.
+
+  @param[in]  Supports         Supported attributes.
+
+  @param[in]  Attributes       Initial attributes.
+
+  @param[in]  AllocAttributes  Allocation attributes.
+
+  @param[in]  RootBusNumber    The bus number to store in RootBus.
+
+  @param[in]  MaxSubBusNumber  The inclusive maximum bus number that can be
+                               assigned to any subordinate bus found behind any
+                               PCI bridge hanging off this root bus.
+
+                               The caller is responsible for ensuring that
+                               RootBusNumber <= MaxSubBusNumber. If
+                               RootBusNumber equals MaxSubBusNumber, then the
+                               root bus has no room for subordinate buses.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+
+  @param[out] RootBus          The PCI_ROOT_BRIDGE structure (allocated by the
+                               caller) that should be filled in by this
+                               function.
+
+  @retval EFI_SUCCESS           Initialization successful. A device path
+                                consisting of an ACPI device path node, with
+                                UID = RootBusNumber, has been allocated and
+                                linked into RootBus.
+
+  @retval EFI_OUT_OF_RESOURCES  Memory allocation failed.
+**/
+EFI_STATUS
+InitRootBridge (
+  IN  UINT64                   Supports,
+  IN  UINT64                   Attributes,
+  IN  UINT64                   AllocAttributes,
+  IN  UINT8                    RootBusNumber,
+  IN  UINT8                    MaxSubBusNumber,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Io,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Mem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *MemAbove4G,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMemAbove4G,
+  OUT PCI_ROOT_BRIDGE          *RootBus
+)
+{
+  CB_PCI_ROOT_BRIDGE_DEVICE_PATH *DevicePath;
+
+  //
+  // Be safe if other fields are added to PCI_ROOT_BRIDGE later.
+  //
+  ZeroMem (RootBus, sizeof *RootBus);
+
+  RootBus->Segment = 0;
+
+  RootBus->Supports   = Supports;
+  RootBus->Attributes = Attributes;
+
+  RootBus->DmaAbove4G = FALSE;
+
+  RootBus->AllocationAttributes = AllocAttributes;
+  RootBus->Bus.Base  = RootBusNumber;
+  RootBus->Bus.Limit = MaxSubBusNumber;
+  CopyMem (&RootBus->Io, Io, sizeof (*Io));
+  CopyMem (&RootBus->Mem, Mem, sizeof (*Mem));
+  CopyMem (&RootBus->MemAbove4G, MemAbove4G, sizeof (*MemAbove4G));
+  CopyMem (&RootBus->PMem, PMem, sizeof (*PMem));
+  CopyMem (&RootBus->PMemAbove4G, PMemAbove4G, sizeof (*PMemAbove4G));
+
+  RootBus->NoExtendedConfigSpace = FALSE;
+
+  DevicePath = AllocateCopyPool (sizeof (mRootBridgeDevicePathTemplate),
+                                 &mRootBridgeDevicePathTemplate);
+  if (DevicePath == NULL) {
+    DEBUG ((DEBUG_ERROR, "%a: %r\n", __FUNCTION__, EFI_OUT_OF_RESOURCES));
+    return EFI_OUT_OF_RESOURCES;
+  }
+  DevicePath->AcpiDevicePath.UID = RootBusNumber;
+  RootBus->DevicePath = (EFI_DEVICE_PATH_PROTOCOL *)DevicePath;
+
+  DEBUG ((DEBUG_INFO,
+          "%a: populated root bus %d, with room for %d subordinate bus(es)\n",
+          __FUNCTION__, RootBusNumber, MaxSubBusNumber - RootBusNumber));
+  return EFI_SUCCESS;
+}
+
+
+/**
+  Return all the root bridge instances in an array.
+
+  @param Count  Return the count of root bridge instances.
+
+  @return All the root bridge instances in an array.
+          The array should be passed into PciHostBridgeFreeRootBridges()
+          when it's not used.
+**/
+PCI_ROOT_BRIDGE *
+EFIAPI
+PciHostBridgeGetRootBridges (
+  UINTN *Count
+)
+{
+  return ScanForRootBridges (Count);
+}
+
+
+/**
+  Free the root bridge instances array returned from
+  PciHostBridgeGetRootBridges().
+
+  @param  The root bridge instances array.
+  @param  The count of the array.
+**/
+VOID
+EFIAPI
+PciHostBridgeFreeRootBridges (
+  PCI_ROOT_BRIDGE *Bridges,
+  UINTN           Count
+)
+{
+  if (Bridges == NULL && Count == 0) {
+    return;
+  }
+  ASSERT (Bridges != NULL && Count > 0);
+
+  do {
+    --Count;
+    FreePool (Bridges[Count].DevicePath);
+  } while (Count > 0);
+
+  FreePool (Bridges);
+}
+
+
+/**
+  Inform the platform that the resource conflict happens.
+
+  @param HostBridgeHandle Handle of the Host Bridge.
+  @param Configuration    Pointer to PCI I/O and PCI memory resource
+                          descriptors. The Configuration contains the resources
+                          for all the root bridges. The resource for each root
+                          bridge is terminated with END descriptor and an
+                          additional END is appended indicating the end of the
+                          entire resources. The resource descriptor field
+                          values follow the description in
+                          EFI_PCI_HOST_BRIDGE_RESOURCE_ALLOCATION_PROTOCOL
+                          .SubmitResources().
+**/
+VOID
+EFIAPI
+PciHostBridgeResourceConflict (
+  EFI_HANDLE                        HostBridgeHandle,
+  VOID                              *Configuration
+)
+{
+  //
+  // coreboot UEFI Payload does not do PCI enumeration and should not call this
+  // library interface.
+  //
+  ASSERT (FALSE);
+}
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
new file mode 100644
index 0000000000..d8f974d209
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
@@ -0,0 +1,47 @@
+## @file
+#  Library instance of PciHostBridgeLib library class for coreboot.
+#
+#  Copyright (C) 2016, Red Hat, Inc.
+#  Copyright (c) 2016 - 2018, Intel Corporation. All rights reserved.<BR>
+#
+#  This program and the accompanying materials are licensed and made available
+#  under the terms and conditions of the BSD License which accompanies this
+#  distribution. The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR
+#  IMPLIED.
+#
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PciHostBridgeLib
+  FILE_GUID                      = 62EE5269-CFFD-43a3-BE3F-622FC79F467E
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PciHostBridgeLib
+
+#
+# The following information is for reference only and not required by the build
+# tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  PciHostBridge.h
+  PciHostBridgeLib.c
+  PciHostBridgeSupport.c
+
+[Packages]
+  MdeModulePkg/MdeModulePkg.dec
+  MdePkg/MdePkg.dec
+
+[LibraryClasses]
+  BaseMemoryLib
+  DebugLib
+  DevicePathLib
+  MemoryAllocationLib
+  PciLib
diff --git a/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c
new file mode 100644
index 0000000000..d06db1e12e
--- /dev/null
+++ b/UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeSupport.c
@@ -0,0 +1,590 @@
+/** @file
+  Scan the entire PCI bus for root bridges to support coreboot UEFI payload.
+
+  Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+
+  This program and the accompanying materials are licensed and made available
+  under the terms and conditions of the BSD License which accompanies this
+  distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php.
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, WITHOUT
+  WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <PiDxe.h>
+#include <IndustryStandard/Pci.h>
+#include <Protocol/PciHostBridgeResourceAllocation.h>
+#include <Protocol/PciRootBridgeIo.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/PciHostBridgeLib.h>
+#include <Library/PciLib.h>
+#include "PciHostBridge.h"
+
+/**
+  Adjust the collected PCI resource.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+**/
+VOID
+AdjustRootBridgeResource (
+  IN  PCI_ROOT_BRIDGE_APERTURE *Io,
+  IN  PCI_ROOT_BRIDGE_APERTURE *Mem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *MemAbove4G,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMem,
+  IN  PCI_ROOT_BRIDGE_APERTURE *PMemAbove4G
+)
+{
+  UINT64  Mask;
+
+  //
+  // For now try to downgrade everything into MEM32 since
+  // - coreboot does not assign resource above 4GB
+  // - coreboot might allocate interleaved MEM32 and PMEM32 resource
+  //   in some cases
+  //
+  if (PMem->Base < Mem->Base) {
+    Mem->Base = PMem->Base;
+  }
+
+  if (PMem->Limit > Mem->Limit) {
+    Mem->Limit = PMem->Limit;
+  }
+
+  PMem->Base  = MAX_UINT64;
+  PMem->Limit = 0;
+
+  if (MemAbove4G->Base < 0x100000000ULL) {
+    if (MemAbove4G->Base < Mem->Base) {
+      Mem->Base  = MemAbove4G->Base;
+    }
+    if (MemAbove4G->Limit > Mem->Limit) {
+      Mem->Limit = MemAbove4G->Limit;
+    }
+    MemAbove4G->Base  = MAX_UINT64;
+    MemAbove4G->Limit = 0;
+  }
+
+  if (PMemAbove4G->Base < 0x100000000ULL) {
+    if (PMemAbove4G->Base < Mem->Base) {
+      Mem->Base  = PMemAbove4G->Base;
+    }
+    if (PMemAbove4G->Limit > Mem->Limit) {
+      Mem->Limit = PMemAbove4G->Limit;
+    }
+    PMemAbove4G->Base  = MAX_UINT64;
+    PMemAbove4G->Limit = 0;
+  }
+
+  //
+  // Align IO  resource at 4K  boundary
+  //
+  Mask        = 0xFFFULL;
+  Io->Limit   = ((Io->Limit + Mask) & ~Mask) - 1;
+  if (Io->Base != MAX_UINT64) {
+    Io->Base &= ~Mask;
+  }
+
+  //
+  // Align MEM resource at 1MB boundary
+  //
+  Mask        = 0xFFFFFULL;
+  Mem->Limit  = ((Mem->Limit + Mask) & ~Mask) - 1;
+  if (Mem->Base != MAX_UINT64) {
+    Mem->Base &= ~Mask;
+  }
+}
+
+/**
+  Probe a bar is existed or not.
+
+  @param[in]    Address           PCI address for the BAR.
+  @param[out]   OriginalValue     The original bar value returned.
+  @param[out]   Value             The probed bar value returned.
+**/
+STATIC
+VOID
+PcatPciRootBridgeBarExisted (
+  IN  UINT64                         Address,
+  OUT UINT32                         *OriginalValue,
+  OUT UINT32                         *Value
+)
+{
+  UINTN   PciAddress;
+
+  PciAddress = (UINTN)Address;
+
+  //
+  // Preserve the original value
+  //
+  *OriginalValue = PciRead32 (PciAddress);
+
+  //
+  // Disable timer interrupt while the BAR is probed
+  //
+  DisableInterrupts ();
+
+  PciWrite32 (PciAddress, 0xFFFFFFFF);
+  *Value = PciRead32 (PciAddress);
+  PciWrite32 (PciAddress, *OriginalValue);
+
+  //
+  // Enable interrupt
+  //
+  EnableInterrupts ();
+}
+
+/**
+  Parse PCI bar and collect the assigned PCI resource information.
+
+  @param[in]  Command          Supported attributes.
+
+  @param[in]  Bus              PCI bus number.
+
+  @param[in]  Device           PCI device number.
+
+  @param[in]  Function         PCI function number.
+
+  @param[in]  BarOffsetBase    PCI bar start offset.
+
+  @param[in]  BarOffsetEnd     PCI bar end offset.
+
+  @param[in]  Io               IO aperture.
+
+  @param[in]  Mem              MMIO aperture.
+
+  @param[in]  MemAbove4G       MMIO aperture above 4G.
+
+  @param[in]  PMem             Prefetchable MMIO aperture.
+
+  @param[in]  PMemAbove4G      Prefetchable MMIO aperture above 4G.
+**/
+STATIC
+VOID
+PcatPciRootBridgeParseBars (
+  IN UINT16                         Command,
+  IN UINTN                          Bus,
+  IN UINTN                          Device,
+  IN UINTN                          Function,
+  IN UINTN                          BarOffsetBase,
+  IN UINTN                          BarOffsetEnd,
+  IN PCI_ROOT_BRIDGE_APERTURE       *Io,
+  IN PCI_ROOT_BRIDGE_APERTURE       *Mem,
+  IN PCI_ROOT_BRIDGE_APERTURE       *MemAbove4G,
+  IN PCI_ROOT_BRIDGE_APERTURE       *PMem,
+  IN PCI_ROOT_BRIDGE_APERTURE       *PMemAbove4G
+
+)
+{
+  UINT32                            OriginalValue;
+  UINT32                            Value;
+  UINT32                            OriginalUpperValue;
+  UINT32                            UpperValue;
+  UINT64                            Mask;
+  UINTN                             Offset;
+  UINTN                             LowBit;
+  UINT64                            Base;
+  UINT64                            Length;
+  UINT64                            Limit;
+  PCI_ROOT_BRIDGE_APERTURE          *MemAperture;
+
+  for (Offset = BarOffsetBase; Offset < BarOffsetEnd; Offset += sizeof (UINT32)) {
+    PcatPciRootBridgeBarExisted (
+      PCI_LIB_ADDRESS (Bus, Device, Function, Offset),
+      &OriginalValue, &Value
+    );
+    if (Value == 0) {
+      continue;
+    }
+    if ((Value & BIT0) == BIT0) {
+      //
+      // IO Bar
+      //
+      if (Command & EFI_PCI_COMMAND_IO_SPACE) {
+        Mask = 0xfffffffc;
+        Base = OriginalValue & Mask;
+        Length = ((~(Value & Mask)) & Mask) + 0x04;
+        if (!(Value & 0xFFFF0000)) {
+          Length &= 0x0000FFFF;
+        }
+        Limit = Base + Length - 1;
+
+        if ((Base > 0) && (Base < Limit)) {
+          if (Io->Base > Base) {
+            Io->Base = Base;
+          }
+          if (Io->Limit < Limit) {
+            Io->Limit = Limit;
+          }
+        }
+      }
+    } else {
+      //
+      // Mem Bar
+      //
+      if (Command & EFI_PCI_COMMAND_MEMORY_SPACE) {
+
+        Mask = 0xfffffff0;
+        Base = OriginalValue & Mask;
+        Length = Value & Mask;
+
+        if ((Value & (BIT1 | BIT2)) == 0) {
+          //
+          // 32bit
+          //
+          Length = ((~Length) + 1) & 0xffffffff;
+
+          if ((Value & BIT3) == BIT3) {
+            MemAperture = PMem;
+          } else {
+            MemAperture = Mem;
+          }
+        } else {
+          //
+          // 64bit
+          //
+          Offset += 4;
+          PcatPciRootBridgeBarExisted (
+            PCI_LIB_ADDRESS (Bus, Device, Function, Offset),
+            &OriginalUpperValue,
+            &UpperValue
+          );
+
+          Base = Base | LShiftU64 ((UINT64) OriginalUpperValue, 32);
+          Length = Length | LShiftU64 ((UINT64) UpperValue, 32);
+          if (Length != 0) {
+            LowBit = LowBitSet64 (Length);
+            Length = LShiftU64 (1ULL, LowBit);
+          }
+
+          if ((Value & BIT3) == BIT3) {
+            MemAperture = PMemAbove4G;
+          } else {
+            MemAperture = MemAbove4G;
+          }
+        }
+
+        Limit = Base + Length - 1;
+        if ((Base > 0) && (Base < Limit)) {
+          if (MemAperture->Base > Base) {
+            MemAperture->Base = Base;
+          }
+          if (MemAperture->Limit < Limit) {
+            MemAperture->Limit = Limit;
+          }
+        }
+      }
+    }
+  }
+}
+
+/**
+  Scan for all root bridges in platform.
+
+  @param[out] NumberOfRootBridges  Number of root bridges detected
+
+  @retval     Pointer to the allocated PCI_ROOT_BRIDGE structure array.
+**/
+PCI_ROOT_BRIDGE *
+ScanForRootBridges (
+  OUT UINTN      *NumberOfRootBridges
+)
+{
+  UINTN      PrimaryBus;
+  UINTN      SubBus;
+  UINT8      Device;
+  UINT8      Function;
+  UINTN      NumberOfDevices;
+  UINTN      Address;
+  PCI_TYPE01 Pci;
+  UINT64     Attributes;
+  UINT64     Base;
+  UINT64     Limit;
+  UINT64     Value;
+  PCI_ROOT_BRIDGE_APERTURE Io, Mem, MemAbove4G, PMem, PMemAbove4G, *MemAperture;
+  PCI_ROOT_BRIDGE *RootBridges;
+  UINTN      BarOffsetEnd;
+
+
+  *NumberOfRootBridges = 0;
+  RootBridges = NULL;
+
+  //
+  // After scanning all the PCI devices on the PCI root bridge's primary bus,
+  // update the Primary Bus Number for the next PCI root bridge to be this PCI
+  // root bridge's subordinate bus number + 1.
+  //
+  for (PrimaryBus = 0; PrimaryBus <= PCI_MAX_BUS; PrimaryBus = SubBus + 1) {
+    SubBus = PrimaryBus;
+    Attributes = 0;
+
+    ZeroMem (&Io, sizeof (Io));
+    ZeroMem (&Mem, sizeof (Mem));
+    ZeroMem (&MemAbove4G, sizeof (MemAbove4G));
+    ZeroMem (&PMem, sizeof (PMem));
+    ZeroMem (&PMemAbove4G, sizeof (PMemAbove4G));
+    Io.Base = Mem.Base = MemAbove4G.Base = PMem.Base = PMemAbove4G.Base = MAX_UINT64;
+    //
+    // Scan all the PCI devices on the primary bus of the PCI root bridge
+    //
+    for (Device = 0, NumberOfDevices = 0; Device <= PCI_MAX_DEVICE; Device++) {
+
+      for (Function = 0; Function <= PCI_MAX_FUNC; Function++) {
+
+        //
+        // Compute the PCI configuration address of the PCI device to probe
+        //
+        Address = PCI_LIB_ADDRESS (PrimaryBus, Device, Function, 0);
+
+        //
+        // Read the Vendor ID from the PCI Configuration Header
+        //
+        if (PciRead16 (Address) == MAX_UINT16) {
+          if (Function == 0) {
+            //
+            // If the PCI Configuration Read fails, or a PCI device does not
+            // exist, then skip this entire PCI device
+            //
+            break;
+          } else {
+            //
+            // If PCI function != 0, VendorId == 0xFFFF, we continue to search
+            // PCI function.
+            //
+            continue;
+          }
+        }
+
+        //
+        // Read the entire PCI Configuration Header
+        //
+        PciReadBuffer (Address, sizeof (Pci), &Pci);
+
+        //
+        // Increment the number of PCI device found on the primary bus of the
+        // PCI root bridge
+        //
+        NumberOfDevices++;
+
+        //
+        // Look for devices with the VGA Palette Snoop enabled in the COMMAND
+        // register of the PCI Config Header
+        //
+        if ((Pci.Hdr.Command & EFI_PCI_COMMAND_VGA_PALETTE_SNOOP) != 0) {
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO_16;
+        }
+
+        BarOffsetEnd = 0;
+
+        //
+        // PCI-PCI Bridge
+        //
+        if (IS_PCI_BRIDGE (&Pci)) {
+          //
+          // Get the Bus range that the PPB is decoding
+          //
+          if (Pci.Bridge.SubordinateBus > SubBus) {
+            //
+            // If the subordinate bus number of the PCI-PCI bridge is greater
+            // than the PCI root bridge's current subordinate bus number,
+            // then update the PCI root bridge's subordinate bus number
+            //
+            SubBus = Pci.Bridge.SubordinateBus;
+          }
+
+          //
+          // Get the I/O range that the PPB is decoding
+          //
+          Value = Pci.Bridge.IoBase & 0x0f;
+          Base = ((UINT32) Pci.Bridge.IoBase & 0xf0) << 8;
+          Limit = (((UINT32) Pci.Bridge.IoLimit & 0xf0) << 8) | 0x0fff;
+          if (Value == BIT0) {
+            Base |= ((UINT32) Pci.Bridge.IoBaseUpper16 << 16);
+            Limit |= ((UINT32) Pci.Bridge.IoLimitUpper16 << 16);
+          }
+          if ((Base > 0) && (Base < Limit)) {
+            if (Io.Base > Base) {
+              Io.Base = Base;
+            }
+            if (Io.Limit < Limit) {
+              Io.Limit = Limit;
+            }
+          }
+
+          //
+          // Get the Memory range that the PPB is decoding
+          //
+          Base = ((UINT32) Pci.Bridge.MemoryBase & 0xfff0) << 16;
+          Limit = (((UINT32) Pci.Bridge.MemoryLimit & 0xfff0) << 16) | 0xfffff;
+          if ((Base > 0) && (Base < Limit)) {
+            if (Mem.Base > Base) {
+              Mem.Base = Base;
+            }
+            if (Mem.Limit < Limit) {
+              Mem.Limit = Limit;
+            }
+          }
+
+          //
+          // Get the Prefetchable Memory range that the PPB is decoding
+          //
+          Value = Pci.Bridge.PrefetchableMemoryBase & 0x0f;
+          Base = ((UINT32) Pci.Bridge.PrefetchableMemoryBase & 0xfff0) << 16;
+          Limit = (((UINT32) Pci.Bridge.PrefetchableMemoryLimit & 0xfff0)
+                   << 16) | 0xfffff;
+          MemAperture = &PMem;
+          if (Value == BIT0) {
+            Base |= LShiftU64 (Pci.Bridge.PrefetchableBaseUpper32, 32);
+            Limit |= LShiftU64 (Pci.Bridge.PrefetchableLimitUpper32, 32);
+            MemAperture = &PMemAbove4G;
+          }
+          if ((Base > 0) && (Base < Limit)) {
+            if (MemAperture->Base > Base) {
+              MemAperture->Base = Base;
+            }
+            if (MemAperture->Limit < Limit) {
+              MemAperture->Limit = Limit;
+            }
+          }
+
+          //
+          // Look at the PPB Configuration for legacy decoding attributes
+          //
+          if ((Pci.Bridge.BridgeControl & EFI_PCI_BRIDGE_CONTROL_ISA)
+              == EFI_PCI_BRIDGE_CONTROL_ISA) {
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO_16;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_MOTHERBOARD_IO;
+          }
+          if ((Pci.Bridge.BridgeControl & EFI_PCI_BRIDGE_CONTROL_VGA)
+              == EFI_PCI_BRIDGE_CONTROL_VGA) {
+            Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_VGA_MEMORY;
+            Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO;
+            if ((Pci.Bridge.BridgeControl & EFI_PCI_BRIDGE_CONTROL_VGA_16)
+                != 0) {
+              Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO_16;
+              Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO_16;
+            }
+          }
+
+          BarOffsetEnd = OFFSET_OF (PCI_TYPE01, Bridge.Bar[2]);
+        } else {
+          //
+          // Parse the BARs of the PCI device to get what I/O Ranges, Memory
+          // Ranges, and Prefetchable Memory Ranges the device is decoding
+          //
+          if ((Pci.Hdr.HeaderType & HEADER_LAYOUT_CODE) == HEADER_TYPE_DEVICE) {
+            BarOffsetEnd = OFFSET_OF (PCI_TYPE00, Device.Bar[6]);
+          }
+        }
+
+        PcatPciRootBridgeParseBars (
+          Pci.Hdr.Command,
+          PrimaryBus,
+          Device,
+          Function,
+          OFFSET_OF (PCI_TYPE00, Device.Bar),
+          BarOffsetEnd,
+          &Io,
+          &Mem, &MemAbove4G,
+          &PMem, &PMemAbove4G
+        );
+
+        //
+        // See if the PCI device is an IDE controller
+        //
+        if (IS_CLASS2 (&Pci, PCI_CLASS_MASS_STORAGE,
+                       PCI_CLASS_MASS_STORAGE_IDE)) {
+          if (Pci.Hdr.ClassCode[0] & 0x80) {
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_PRIMARY_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_SECONDARY_IO;
+          }
+          if (Pci.Hdr.ClassCode[0] & 0x01) {
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_PRIMARY_IO;
+          }
+          if (Pci.Hdr.ClassCode[0] & 0x04) {
+            Attributes |= EFI_PCI_ATTRIBUTE_IDE_SECONDARY_IO;
+          }
+        }
+
+        //
+        // See if the PCI device is a legacy VGA controller or
+        // a standard VGA controller
+        //
+        if (IS_CLASS2 (&Pci, PCI_CLASS_OLD, PCI_CLASS_OLD_VGA) ||
+            IS_CLASS2 (&Pci, PCI_CLASS_DISPLAY, PCI_CLASS_DISPLAY_VGA)
+           ) {
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_PALETTE_IO_16;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_MEMORY;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO;
+          Attributes |= EFI_PCI_ATTRIBUTE_VGA_IO_16;
+        }
+
+        //
+        // See if the PCI Device is a PCI - ISA or PCI - EISA
+        // or ISA_POSITIVE_DECODE Bridge device
+        //
+        if (Pci.Hdr.ClassCode[2] == PCI_CLASS_BRIDGE) {
+          if (Pci.Hdr.ClassCode[1] == PCI_CLASS_BRIDGE_ISA ||
+              Pci.Hdr.ClassCode[1] == PCI_CLASS_BRIDGE_EISA ||
+              Pci.Hdr.ClassCode[1] == PCI_CLASS_BRIDGE_ISA_PDECODE) {
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_IO_16;
+            Attributes |= EFI_PCI_ATTRIBUTE_ISA_MOTHERBOARD_IO;
+          }
+        }
+
+        //
+        // If this device is not a multi function device, then skip the rest
+        // of this PCI device
+        //
+        if (Function == 0 && !IS_PCI_MULTI_FUNC (&Pci)) {
+          break;
+        }
+      }
+    }
+
+    //
+    // If at least one PCI device was found on the primary bus of this PCI
+    // root bridge, then the PCI root bridge exists.
+    //
+    if (NumberOfDevices > 0) {
+      RootBridges = ReallocatePool (
+                      (*NumberOfRootBridges) * sizeof (PCI_ROOT_BRIDGE),
+                      (*NumberOfRootBridges + 1) * sizeof (PCI_ROOT_BRIDGE),
+                      RootBridges
+                    );
+      ASSERT (RootBridges != NULL);
+
+      AdjustRootBridgeResource (&Io, &Mem, &MemAbove4G, &PMem, &PMemAbove4G);
+
+      InitRootBridge (
+        Attributes, Attributes, 0,
+        (UINT8) PrimaryBus, (UINT8) SubBus,
+        &Io, &Mem, &MemAbove4G, &PMem, &PMemAbove4G,
+        &RootBridges[*NumberOfRootBridges]
+      );
+      RootBridges[*NumberOfRootBridges].ResourceAssigned = TRUE;
+      //
+      // Increment the index for the next PCI Root Bridge
+      //
+      (*NumberOfRootBridges)++;
+    }
+  }
+
+  return RootBridges;
+}
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c
new file mode 100644
index 0000000000..b66684cdff
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.c
@@ -0,0 +1,271 @@
+/** @file
+  This file include all platform action which can be customized
+  by IBV/OEM.
+
+Copyright (c) 2015 - 2018, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include "PlatformBootManager.h"
+#include "PlatformConsole.h"
+
+VOID
+InstallReadyToLock (
+  VOID
+  )
+{
+  EFI_STATUS                            Status;
+  EFI_HANDLE                            Handle;
+  EFI_SMM_ACCESS2_PROTOCOL              *SmmAccess;
+
+  DEBUG((DEBUG_INFO,"InstallReadyToLock  entering......\n"));
+  //
+  // Inform the SMM infrastructure that we're entering BDS and may run 3rd party code hereafter
+  // Since PI1.2.1, we need signal EndOfDxe as ExitPmAuth
+  //
+  EfiEventGroupSignal (&gEfiEndOfDxeEventGroupGuid);
+  DEBUG((DEBUG_INFO,"All EndOfDxe callbacks have returned successfully\n"));
+
+  //
+  // Install DxeSmmReadyToLock protocol in order to lock SMM
+  //
+  Status = gBS->LocateProtocol (&gEfiSmmAccess2ProtocolGuid, NULL, (VOID **) &SmmAccess);
+  if (!EFI_ERROR (Status)) {
+    Handle = NULL;
+    Status = gBS->InstallProtocolInterface (
+                    &Handle,
+                    &gEfiDxeSmmReadyToLockProtocolGuid,
+                    EFI_NATIVE_INTERFACE,
+                    NULL
+                    );
+    ASSERT_EFI_ERROR (Status);
+  }
+
+  DEBUG((DEBUG_INFO,"InstallReadyToLock  end\n"));
+  return;
+}
+
+/**
+  Return the index of the load option in the load option array.
+
+  The function consider two load options are equal when the
+  OptionType, Attributes, Description, FilePath and OptionalData are equal.
+
+  @param Key    Pointer to the load option to be found.
+  @param Array  Pointer to the array of load options to be found.
+  @param Count  Number of entries in the Array.
+
+  @retval -1          Key wasn't found in the Array.
+  @retval 0 ~ Count-1 The index of the Key in the Array.
+**/
+INTN
+PlatformFindLoadOption (
+  IN CONST EFI_BOOT_MANAGER_LOAD_OPTION *Key,
+  IN CONST EFI_BOOT_MANAGER_LOAD_OPTION *Array,
+  IN UINTN                              Count
+)
+{
+  UINTN                             Index;
+
+  for (Index = 0; Index < Count; Index++) {
+    if ((Key->OptionType == Array[Index].OptionType) &&
+        (Key->Attributes == Array[Index].Attributes) &&
+        (StrCmp (Key->Description, Array[Index].Description) == 0) &&
+        (CompareMem (Key->FilePath, Array[Index].FilePath, GetDevicePathSize (Key->FilePath)) == 0) &&
+        (Key->OptionalDataSize == Array[Index].OptionalDataSize) &&
+        (CompareMem (Key->OptionalData, Array[Index].OptionalData, Key->OptionalDataSize) == 0)) {
+      return (INTN) Index;
+    }
+  }
+
+  return -1;
+}
+
+/**
+  Register a boot option using a file GUID in the FV.
+
+  @param FileGuid     The file GUID name in FV.
+  @param Description  The boot option description.
+  @param Attributes   The attributes used for the boot option loading.
+**/
+VOID
+PlatformRegisterFvBootOption (
+  EFI_GUID                         *FileGuid,
+  CHAR16                           *Description,
+  UINT32                           Attributes
+)
+{
+  EFI_STATUS                        Status;
+  UINTN                             OptionIndex;
+  EFI_BOOT_MANAGER_LOAD_OPTION      NewOption;
+  EFI_BOOT_MANAGER_LOAD_OPTION      *BootOptions;
+  UINTN                             BootOptionCount;
+  MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileNode;
+  EFI_LOADED_IMAGE_PROTOCOL         *LoadedImage;
+  EFI_DEVICE_PATH_PROTOCOL          *DevicePath;
+
+  Status = gBS->HandleProtocol (gImageHandle, &gEfiLoadedImageProtocolGuid, (VOID **) &LoadedImage);
+  ASSERT_EFI_ERROR (Status);
+
+  EfiInitializeFwVolDevicepathNode (&FileNode, FileGuid);
+  DevicePath = AppendDevicePathNode (
+                 DevicePathFromHandle (LoadedImage->DeviceHandle),
+                 (EFI_DEVICE_PATH_PROTOCOL *) &FileNode
+               );
+
+  Status = EfiBootManagerInitializeLoadOption (
+             &NewOption,
+             LoadOptionNumberUnassigned,
+             LoadOptionTypeBoot,
+             Attributes,
+             Description,
+             DevicePath,
+             NULL,
+             0
+           );
+  if (!EFI_ERROR (Status)) {
+    BootOptions = EfiBootManagerGetLoadOptions (&BootOptionCount, LoadOptionTypeBoot);
+
+    OptionIndex = PlatformFindLoadOption (&NewOption, BootOptions, BootOptionCount);
+
+    if (OptionIndex == -1) {
+      Status = EfiBootManagerAddLoadOptionVariable (&NewOption, (UINTN) -1);
+      ASSERT_EFI_ERROR (Status);
+    }
+    EfiBootManagerFreeLoadOption (&NewOption);
+    EfiBootManagerFreeLoadOptions (BootOptions, BootOptionCount);
+  }
+}
+
+/**
+  Do the platform specific action before the console is connected.
+
+  Such as:
+    Update console variable;
+    Register new Driver#### or Boot####;
+    Signal ReadyToLock event.
+**/
+VOID
+EFIAPI
+PlatformBootManagerBeforeConsole (
+  VOID
+)
+{
+  EFI_INPUT_KEY                Enter;
+  EFI_INPUT_KEY                F2;
+  EFI_INPUT_KEY                Down;
+  EFI_BOOT_MANAGER_LOAD_OPTION BootOption;
+
+  PlatformConsoleInit ();
+
+  //
+  // Register ENTER as CONTINUE key
+  //
+  Enter.ScanCode    = SCAN_NULL;
+  Enter.UnicodeChar = CHAR_CARRIAGE_RETURN;
+  EfiBootManagerRegisterContinueKeyOption (0, &Enter, NULL);
+
+  //
+  // Map F2 to Boot Manager Menu
+  //
+  F2.ScanCode    = SCAN_F2;
+  F2.UnicodeChar = CHAR_NULL;
+  EfiBootManagerGetBootManagerMenu (&BootOption);
+  EfiBootManagerAddKeyOptionVariable (NULL, (UINT16) BootOption.OptionNumber, 0, &F2, NULL);
+
+  //
+  // Also add Down key to Boot Manager Menu since some serial terminals don't support F2 key.
+  //
+  Down.ScanCode    = SCAN_DOWN;
+  Down.UnicodeChar = CHAR_NULL;
+  EfiBootManagerGetBootManagerMenu (&BootOption);
+  EfiBootManagerAddKeyOptionVariable (NULL, (UINT16) BootOption.OptionNumber, 0, &Down, NULL);
+
+  //
+  // Install ready to lock.
+  // This needs to be done before option rom dispatched.
+  //
+  InstallReadyToLock ();
+
+  //
+  // Dispatch deferred images after EndOfDxe event and ReadyToLock installation.
+  //
+  EfiBootManagerDispatchDeferredImages ();
+}
+
+/**
+  Do the platform specific action after the console is connected.
+
+  Such as:
+    Dynamically switch output mode;
+    Signal console ready platform customized event;
+    Run diagnostics like memory testing;
+    Connect certain devices;
+    Dispatch additional option roms.
+**/
+VOID
+EFIAPI
+PlatformBootManagerAfterConsole (
+  VOID
+)
+{
+  EFI_GRAPHICS_OUTPUT_BLT_PIXEL  Black;
+  EFI_GRAPHICS_OUTPUT_BLT_PIXEL  White;
+
+  Black.Blue = Black.Green = Black.Red = Black.Reserved = 0;
+  White.Blue = White.Green = White.Red = White.Reserved = 0xFF;
+
+  EfiBootManagerConnectAll ();
+  EfiBootManagerRefreshAllBootOption ();
+
+  //
+  // Register UEFI Shell
+  //
+  PlatformRegisterFvBootOption (PcdGetPtr (PcdShellFile), L"UEFI Shell", LOAD_OPTION_ACTIVE);
+
+  Print (
+    L"\n"
+    L"F2 or Down      to enter Boot Manager Menu.\n"
+    L"ENTER           to boot directly.\n"
+    L"\n"
+  );
+
+}
+
+/**
+  This function is called each second during the boot manager waits the timeout.
+
+  @param TimeoutRemain  The remaining timeout.
+**/
+VOID
+EFIAPI
+PlatformBootManagerWaitCallback (
+  UINT16          TimeoutRemain
+)
+{
+  return;
+}
+
+/**
+  The function is called when no boot option could be launched,
+  including platform recovery options and options pointing to applications
+  built into firmware volumes.
+
+  If this function returns, BDS attempts to enter an infinite loop.
+**/
+VOID
+EFIAPI
+PlatformBootManagerUnableToBoot (
+  VOID
+  )
+{
+  return;
+}
+
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h
new file mode 100644
index 0000000000..230f0b9e3a
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManager.h
@@ -0,0 +1,138 @@
+/**@file
+   Head file for BDS Platform specific code
+
+Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+**/
+
+#ifndef _PLATFORM_BOOT_MANAGER_H
+#define _PLATFORM_BOOT_MANAGER_H
+
+#include <PiDxe.h>
+#include <Protocol/LoadedImage.h>
+
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/UefiRuntimeServicesTableLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/BaseLib.h>
+#include <Library/UefiRuntimeServicesTableLib.h>
+#include <Library/UefiLib.h>
+#include <Library/UefiBootManagerLib.h>
+#include <Library/PcdLib.h>
+#include <Library/DevicePathLib.h>
+#include <Library/HiiLib.h>
+#include <Library/PrintLib.h>
+#include <Library/DxeServicesLib.h>
+#include <Library/BootLogoLib.h>
+#include <Protocol/SmmAccess2.h>
+
+typedef struct {
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+  UINTN                     ConnectType;
+} PLATFORM_CONSOLE_CONNECT_ENTRY;
+
+extern PLATFORM_CONSOLE_CONNECT_ENTRY  gPlatformConsole[];
+
+#define gEndEntire \
+  { \
+    END_DEVICE_PATH_TYPE,\
+    END_ENTIRE_DEVICE_PATH_SUBTYPE,\
+    { END_DEVICE_PATH_LENGTH, 0 },\
+  }
+
+#define CONSOLE_OUT BIT0
+#define CONSOLE_IN  BIT1
+#define STD_ERROR   BIT2
+
+#define CLASS_HID           3
+#define SUBCLASS_BOOT       1
+#define PROTOCOL_KEYBOARD   1
+
+typedef struct {
+  USB_CLASS_DEVICE_PATH           UsbClass;
+  EFI_DEVICE_PATH_PROTOCOL        End;
+} USB_CLASS_FORMAT_DEVICE_PATH;
+
+typedef struct {
+  VENDOR_DEVICE_PATH  VendorDevicePath;
+  UINT32              Instance;
+} WIN_NT_VENDOR_DEVICE_PATH_NODE;
+
+//
+// Below is the platform console device path
+//
+typedef struct {
+  VENDOR_DEVICE_PATH              NtBus;
+  WIN_NT_VENDOR_DEVICE_PATH_NODE  SerialDevice;
+  UART_DEVICE_PATH                Uart;
+  VENDOR_DEVICE_PATH              TerminalType;
+  EFI_DEVICE_PATH_PROTOCOL        End;
+} NT_ISA_SERIAL_DEVICE_PATH;
+
+typedef struct {
+  VENDOR_DEVICE_PATH              NtBus;
+  WIN_NT_VENDOR_DEVICE_PATH_NODE  NtGopDevice;
+  EFI_DEVICE_PATH_PROTOCOL        End;
+} NT_PLATFORM_GOP_DEVICE_PATH;
+
+extern USB_CLASS_FORMAT_DEVICE_PATH              gUsbClassKeyboardDevicePath;
+
+/**
+  Use SystemTable Conout to stop video based Simple Text Out consoles from going
+  to the video device. Put up LogoFile on every video device that is a console.
+
+  @param[in]  LogoFile   File name of logo to display on the center of the screen.
+
+  @retval EFI_SUCCESS     ConsoleControl has been flipped to graphics and logo displayed.
+  @retval EFI_UNSUPPORTED Logo not found
+
+**/
+EFI_STATUS
+PlatformBootManagerEnableQuietBoot (
+  IN  EFI_GUID  *LogoFile
+);
+
+/**
+  Use SystemTable Conout to turn on video based Simple Text Out consoles. The
+  Simple Text Out screens will now be synced up with all non video output devices
+
+  @retval EFI_SUCCESS     UGA devices are back in text mode and synced up.
+
+**/
+EFI_STATUS
+PlatformBootManagerDisableQuietBoot (
+  VOID
+);
+
+/**
+  Show progress bar with title above it. It only works in Graphics mode.
+
+  @param TitleForeground Foreground color for Title.
+  @param TitleBackground Background color for Title.
+  @param Title           Title above progress bar.
+  @param ProgressColor   Progress bar color.
+  @param Progress        Progress (0-100)
+  @param PreviousValue   The previous value of the progress.
+
+  @retval  EFI_STATUS       Success update the progress bar
+
+**/
+EFI_STATUS
+PlatformBootManagerShowProgress (
+  IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL TitleForeground,
+  IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL TitleBackground,
+  IN CHAR16                        *Title,
+  IN EFI_GRAPHICS_OUTPUT_BLT_PIXEL ProgressColor,
+  IN UINTN                         Progress,
+  IN UINTN                         PreviousValue
+);
+
+#endif // _PLATFORM_BOOT_MANAGER_H
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
new file mode 100644
index 0000000000..7010794fbe
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
@@ -0,0 +1,77 @@
+## @file
+#  Include all platform action which can be customized by IBV/OEM.
+#
+#  Copyright (c) 2012 - 2016, Intel Corporation. All rights reserved.<BR>
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution.  The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PlatformBootManagerLib
+  FILE_GUID                      = F0D9063A-DADB-4185-85E2-D7ACDA93F7A6
+  MODULE_TYPE                    = DXE_DRIVER
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PlatformBootManagerLib|DXE_DRIVER
+
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  PlatformData.c
+  PlatformConsole.c
+  PlatformConsole.h
+  PlatformBootManager.c
+  PlatformBootManager.h
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  UefiBootServicesTableLib
+  UefiRuntimeServicesTableLib
+  UefiLib
+  UefiBootManagerLib
+  PcdLib
+  DxeServicesLib
+  MemoryAllocationLib
+  DevicePathLib
+  HiiLib
+  PrintLib
+  PlatformHookLib
+
+[Guids]
+  gEfiEndOfDxeEventGroupGuid
+
+[Protocols]
+  gEfiGenericMemTestProtocolGuid  ## CONSUMES
+  gEfiGraphicsOutputProtocolGuid  ## CONSUMES
+  gEfiUgaDrawProtocolGuid         ## CONSUMES
+  gEfiBootLogoProtocolGuid        ## CONSUMES
+  gEfiDxeSmmReadyToLockProtocolGuid
+  gEfiSmmAccess2ProtocolGuid
+
+[Pcd]
+  gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut
+  gEfiMdePkgTokenSpaceGuid.PcdUgaConsumeSupport
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConInConnectOnDemand
+  gUefiPayloadPkgTokenSpaceGuid.PcdShellFile
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultDataBits
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultParity
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultStopBits
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c
new file mode 100644
index 0000000000..b8b2048baa
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.c
@@ -0,0 +1,605 @@
+/** @file
+This file include all platform action which can be customized by IBV/OEM.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include "PlatformBootManager.h"
+#include "PlatformConsole.h"
+
+#define PCI_DEVICE_PATH_NODE(Func, Dev) \
+  { \
+    { \
+      HARDWARE_DEVICE_PATH, \
+      HW_PCI_DP, \
+      { \
+        (UINT8) (sizeof (PCI_DEVICE_PATH)), \
+        (UINT8) ((sizeof (PCI_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    (Func), \
+    (Dev) \
+  }
+
+#define PNPID_DEVICE_PATH_NODE(PnpId) \
+  { \
+    { \
+      ACPI_DEVICE_PATH, \
+      ACPI_DP, \
+      { \
+        (UINT8) (sizeof (ACPI_HID_DEVICE_PATH)), \
+        (UINT8) ((sizeof (ACPI_HID_DEVICE_PATH)) >> 8) \
+      }, \
+    }, \
+    EISA_PNP_ID((PnpId)), \
+    0 \
+  }
+
+#define gPciRootBridge \
+  PNPID_DEVICE_PATH_NODE(0x0A03)
+
+#define gPnp16550ComPort \
+  PNPID_DEVICE_PATH_NODE(0x0501)
+
+#define gUartVendor \
+  { \
+    { \
+      HARDWARE_DEVICE_PATH, \
+      HW_VENDOR_DP, \
+      { \
+        (UINT8) (sizeof (VENDOR_DEVICE_PATH)), \
+        (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    {0xD3987D4B, 0x971A, 0x435F, {0x8C, 0xAF, 0x49, 0x67, 0xEB, 0x62, 0x72, 0x41}} \
+  }
+
+#define gUart \
+  { \
+    { \
+      MESSAGING_DEVICE_PATH, \
+      MSG_UART_DP, \
+      { \
+        (UINT8) (sizeof (UART_DEVICE_PATH)), \
+        (UINT8) ((sizeof (UART_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    0, \
+    115200, \
+    8, \
+    1, \
+    1 \
+  }
+
+#define gPcAnsiTerminal \
+  { \
+    { \
+      MESSAGING_DEVICE_PATH, \
+      MSG_VENDOR_DP, \
+      { \
+        (UINT8) (sizeof (VENDOR_DEVICE_PATH)), \
+        (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8) \
+      } \
+    }, \
+    DEVICE_PATH_MESSAGING_PC_ANSI \
+  }
+
+
+ACPI_HID_DEVICE_PATH       gPnp16550ComPortDeviceNode = gPnp16550ComPort;
+UART_DEVICE_PATH           gUartDeviceNode            = gUart;
+VENDOR_DEVICE_PATH         gTerminalTypeDeviceNode    = gPcAnsiTerminal;
+VENDOR_DEVICE_PATH         gUartDeviceVendorNode      = gUartVendor;
+
+//
+// Predefined platform root bridge
+//
+PLATFORM_ROOT_BRIDGE_DEVICE_PATH  gPlatformRootBridge0 = {
+  gPciRootBridge,
+  gEndEntire
+};
+
+EFI_DEVICE_PATH_PROTOCOL          *gPlatformRootBridges[] = {
+  (EFI_DEVICE_PATH_PROTOCOL *) &gPlatformRootBridge0,
+  NULL
+};
+
+BOOLEAN       mDetectVgaOnly;
+
+/**
+  Add UART to ConOut, ConIn, ErrOut.
+
+  @param[in]   DeviceHandle - LPC device path.
+
+  @retval EFI_SUCCESS  - Serial console is added to ConOut, ConIn, and ErrOut.
+  @retval EFI_STATUS   - No serial console is added.
+**/
+EFI_STATUS
+PrepareLpcBridgeDevicePath (
+  IN EFI_HANDLE                DeviceHandle
+)
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+
+  DevicePath = NULL;
+  Status = gBS->HandleProtocol (
+             DeviceHandle,
+             &gEfiDevicePathProtocolGuid,
+             (VOID*)&DevicePath
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  //
+  // Register COM1
+  //
+  DevicePath = AppendDevicePathNode ((EFI_DEVICE_PATH_PROTOCOL *)NULL, (EFI_DEVICE_PATH_PROTOCOL *)&gUartDeviceVendorNode);
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gUartDeviceNode);
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gTerminalTypeDeviceNode);
+
+  EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ConIn, DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ErrOut, DevicePath, NULL);
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Return the GOP device path in the platform.
+
+  @param[in]   PciDevicePath - Device path for the PCI graphics device.
+  @param[out]  GopDevicePath - Return the device path with GOP installed.
+
+  @retval EFI_SUCCESS  - PCI VGA is added to ConOut.
+  @retval EFI_INVALID_PARAMETER   - The device path parameter is invalid.
+  @retval EFI_STATUS   - No GOP device found.
+**/
+EFI_STATUS
+GetGopDevicePath (
+  IN  EFI_DEVICE_PATH_PROTOCOL *PciDevicePath,
+  OUT EFI_DEVICE_PATH_PROTOCOL **GopDevicePath
+)
+{
+  UINTN                           Index;
+  EFI_STATUS                      Status;
+  EFI_HANDLE                      PciDeviceHandle;
+  EFI_DEVICE_PATH_PROTOCOL        *TempDevicePath;
+  EFI_DEVICE_PATH_PROTOCOL        *TempPciDevicePath;
+  UINTN                           GopHandleCount;
+  EFI_HANDLE                      *GopHandleBuffer;
+
+  if (PciDevicePath == NULL || GopDevicePath == NULL) {
+    return EFI_INVALID_PARAMETER;
+  }
+
+  //
+  // Initialize the GopDevicePath to be PciDevicePath
+  //
+  *GopDevicePath    = PciDevicePath;
+  TempPciDevicePath = PciDevicePath;
+
+  Status = gBS->LocateDevicePath (
+             &gEfiDevicePathProtocolGuid,
+             &TempPciDevicePath,
+             &PciDeviceHandle
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  gBS->ConnectController (PciDeviceHandle, NULL, NULL, FALSE);
+
+  Status = gBS->LocateHandleBuffer (
+             ByProtocol,
+             &gEfiGraphicsOutputProtocolGuid,
+             NULL,
+             &GopHandleCount,
+             &GopHandleBuffer
+           );
+  if (!EFI_ERROR (Status)) {
+    //
+    // Add all the child handles as possible Console Device
+    //
+    for (Index = 0; Index < GopHandleCount; Index++) {
+      Status = gBS->HandleProtocol (GopHandleBuffer[Index], &gEfiDevicePathProtocolGuid, (VOID*)&TempDevicePath);
+      if (EFI_ERROR (Status)) {
+        continue;
+      }
+      if (CompareMem (
+            PciDevicePath,
+            TempDevicePath,
+            GetDevicePathSize (PciDevicePath) - END_DEVICE_PATH_LENGTH
+          ) == 0) {
+        //
+        // In current implementation, we only enable one of the child handles
+        // as console device, i.e. sotre one of the child handle's device
+        // path to variable "ConOut"
+        // In future, we could select all child handles to be console device
+        //
+        *GopDevicePath = TempDevicePath;
+
+        //
+        // Delete the PCI device's path that added by GetPlugInPciVgaDevicePath()
+        // Add the integrity GOP device path.
+        //
+        EfiBootManagerUpdateConsoleVariable (ConOut, NULL, PciDevicePath);
+        EfiBootManagerUpdateConsoleVariable (ConOut, TempDevicePath, NULL);
+      }
+    }
+    gBS->FreePool (GopHandleBuffer);
+  }
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Add PCI VGA to ConOut, ConIn, ErrOut.
+
+  @param[in]  DeviceHandle - Handle of PciIo protocol.
+
+  @retval EFI_SUCCESS  - PCI VGA is added to ConOut.
+  @retval EFI_STATUS   - No PCI VGA device is added.
+
+**/
+EFI_STATUS
+PreparePciVgaDevicePath (
+  IN EFI_HANDLE                DeviceHandle
+)
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+  EFI_DEVICE_PATH_PROTOCOL  *GopDevicePath;
+
+  DevicePath = NULL;
+  Status = gBS->HandleProtocol (
+             DeviceHandle,
+             &gEfiDevicePathProtocolGuid,
+             (VOID*)&DevicePath
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  GetGopDevicePath (DevicePath, &GopDevicePath);
+  DevicePath = GopDevicePath;
+
+  EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Add PCI Serial to ConOut, ConIn, ErrOut.
+
+  @param[in]  DeviceHandle - Handle of PciIo protocol.
+
+  @retval EFI_SUCCESS  - PCI Serial is added to ConOut, ConIn, and ErrOut.
+  @retval EFI_STATUS   - No PCI Serial device is added.
+
+**/
+EFI_STATUS
+PreparePciSerialDevicePath (
+  IN EFI_HANDLE                DeviceHandle
+)
+{
+  EFI_STATUS                Status;
+  EFI_DEVICE_PATH_PROTOCOL  *DevicePath;
+
+  DevicePath = NULL;
+  Status = gBS->HandleProtocol (
+             DeviceHandle,
+             &gEfiDevicePathProtocolGuid,
+             (VOID*)&DevicePath
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gUartDeviceNode);
+  DevicePath = AppendDevicePathNode (DevicePath, (EFI_DEVICE_PATH_PROTOCOL *)&gTerminalTypeDeviceNode);
+
+  EfiBootManagerUpdateConsoleVariable (ConOut, DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ConIn,  DevicePath, NULL);
+  EfiBootManagerUpdateConsoleVariable (ErrOut, DevicePath, NULL);
+
+  return EFI_SUCCESS;
+}
+
+
+/**
+  For every PCI instance execute a callback function.
+
+  @param[in]  Id                 - The protocol GUID for callback
+  @param[in]  CallBackFunction   - The callback function
+  @param[in]  Context    - The context of the callback
+
+  @retval EFI_STATUS - Callback function failed.
+
+**/
+EFI_STATUS
+EFIAPI
+VisitAllInstancesOfProtocol (
+  IN EFI_GUID                    *Id,
+  IN PROTOCOL_INSTANCE_CALLBACK  CallBackFunction,
+  IN VOID                        *Context
+)
+{
+  EFI_STATUS                Status;
+  UINTN                     HandleCount;
+  EFI_HANDLE                *HandleBuffer;
+  UINTN                     Index;
+  VOID                      *Instance;
+
+  //
+  // Start to check all the PciIo to find all possible device
+  //
+  HandleCount = 0;
+  HandleBuffer = NULL;
+  Status = gBS->LocateHandleBuffer (
+             ByProtocol,
+             Id,
+             NULL,
+             &HandleCount,
+             &HandleBuffer
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  for (Index = 0; Index < HandleCount; Index++) {
+    Status = gBS->HandleProtocol (HandleBuffer[Index], Id, &Instance);
+    if (EFI_ERROR (Status)) {
+      continue;
+    }
+
+    Status = (*CallBackFunction) (
+               HandleBuffer[Index],
+               Instance,
+               Context
+             );
+  }
+
+  gBS->FreePool (HandleBuffer);
+
+  return EFI_SUCCESS;
+}
+
+
+/**
+  For every PCI instance execute a callback function.
+
+  @param[in]  Handle     - The PCI device handle
+  @param[in]  Instance   - The instance of the PciIo protocol
+  @param[in]  Context    - The context of the callback
+
+  @retval EFI_STATUS - Callback function failed.
+
+**/
+EFI_STATUS
+EFIAPI
+VisitingAPciInstance (
+  IN EFI_HANDLE  Handle,
+  IN VOID        *Instance,
+  IN VOID        *Context
+)
+{
+  EFI_STATUS                Status;
+  EFI_PCI_IO_PROTOCOL       *PciIo;
+  PCI_TYPE00                Pci;
+
+  PciIo = (EFI_PCI_IO_PROTOCOL*) Instance;
+
+  //
+  // Check for all PCI device
+  //
+  Status = PciIo->Pci.Read (
+             PciIo,
+             EfiPciIoWidthUint32,
+             0,
+             sizeof (Pci) / sizeof (UINT32),
+             &Pci
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  return (*(VISIT_PCI_INSTANCE_CALLBACK)(UINTN) Context) (
+           Handle,
+           PciIo,
+           &Pci
+         );
+
+}
+
+
+/**
+  For every PCI instance execute a callback function.
+
+  @param[in]  CallBackFunction - Callback function pointer
+
+  @retval EFI_STATUS - Callback function failed.
+
+**/
+EFI_STATUS
+EFIAPI
+VisitAllPciInstances (
+  IN VISIT_PCI_INSTANCE_CALLBACK CallBackFunction
+)
+{
+  return VisitAllInstancesOfProtocol (
+           &gEfiPciIoProtocolGuid,
+           VisitingAPciInstance,
+           (VOID*)(UINTN) CallBackFunction
+         );
+}
+
+
+/**
+  Do platform specific PCI Device check and add them to
+  ConOut, ConIn, ErrOut.
+
+  @param[in]  Handle - Handle of PCI device instance
+  @param[in]  PciIo - PCI IO protocol instance
+  @param[in]  Pci - PCI Header register block
+
+  @retval EFI_SUCCESS - PCI Device check and Console variable update successfully.
+  @retval EFI_STATUS - PCI Device check or Console variable update fail.
+
+**/
+EFI_STATUS
+EFIAPI
+DetectAndPreparePlatformPciDevicePath (
+  IN EFI_HANDLE           Handle,
+  IN EFI_PCI_IO_PROTOCOL  *PciIo,
+  IN PCI_TYPE00           *Pci
+)
+{
+  EFI_STATUS                Status;
+
+  Status = PciIo->Attributes (
+             PciIo,
+             EfiPciIoAttributeOperationEnable,
+             EFI_PCI_DEVICE_ENABLE,
+             NULL
+           );
+  ASSERT_EFI_ERROR (Status);
+
+  if (!mDetectVgaOnly) {
+    //
+    // Here we decide whether it is LPC Bridge
+    //
+    if ((IS_PCI_LPC (Pci)) ||
+        ((IS_PCI_ISA_PDECODE (Pci)) &&
+         (Pci->Hdr.VendorId == 0x8086)
+        )
+       ) {
+      //
+      // Add IsaKeyboard to ConIn,
+      // add IsaSerial to ConOut, ConIn, ErrOut
+      //
+      DEBUG ((DEBUG_INFO, "Found LPC Bridge device\n"));
+      PrepareLpcBridgeDevicePath (Handle);
+      return EFI_SUCCESS;
+    }
+    //
+    // Here we decide which Serial device to enable in PCI bus
+    //
+    if (IS_PCI_16550SERIAL (Pci)) {
+      //
+      // Add them to ConOut, ConIn, ErrOut.
+      //
+      DEBUG ((DEBUG_INFO, "Found PCI 16550 SERIAL device\n"));
+      PreparePciSerialDevicePath (Handle);
+      return EFI_SUCCESS;
+    }
+  }
+
+  //
+  // Here we decide which VGA device to enable in PCI bus
+  //
+  if (IS_PCI_VGA (Pci)) {
+    //
+    // Add them to ConOut.
+    //
+    DEBUG ((DEBUG_INFO, "Found PCI VGA device\n"));
+    PreparePciVgaDevicePath (Handle);
+    return EFI_SUCCESS;
+  }
+
+  return Status;
+}
+
+
+/**
+  Do platform specific PCI Device check and add them to ConOut, ConIn, ErrOut
+
+  @param[in]  DetectVgaOnly - Only detect VGA device if it's TRUE.
+
+  @retval EFI_SUCCESS - PCI Device check and Console variable update successfully.
+  @retval EFI_STATUS - PCI Device check or Console variable update fail.
+
+**/
+EFI_STATUS
+DetectAndPreparePlatformPciDevicePaths (
+  BOOLEAN DetectVgaOnly
+)
+{
+  mDetectVgaOnly = DetectVgaOnly;
+
+  EfiBootManagerUpdateConsoleVariable (
+    ConIn,
+    (EFI_DEVICE_PATH_PROTOCOL *) &gUsbClassKeyboardDevicePath,
+    NULL
+    );
+
+  return VisitAllPciInstances (DetectAndPreparePlatformPciDevicePath);
+}
+
+
+/**
+  The function will connect root bridge
+
+   @return EFI_SUCCESS      Connect RootBridge successfully.
+
+**/
+EFI_STATUS
+ConnectRootBridge (
+  VOID
+)
+{
+  EFI_STATUS                Status;
+  EFI_HANDLE                RootHandle;
+
+  //
+  // Make all the PCI_IO protocols on PCI Seg 0 show up
+  //
+  Status = gBS->LocateDevicePath (
+             &gEfiDevicePathProtocolGuid,
+             &gPlatformRootBridges[0],
+             &RootHandle
+           );
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = gBS->ConnectController (RootHandle, NULL, NULL, FALSE);
+  if (EFI_ERROR (Status)) {
+    return Status;
+  }
+
+  return EFI_SUCCESS;
+}
+
+/**
+  Platform console init. Include the platform firmware vendor, revision
+  and so crc check.
+
+**/
+VOID
+EFIAPI
+PlatformConsoleInit (
+  VOID
+)
+{
+  gUartDeviceNode.BaudRate = PcdGet64 (PcdUartDefaultBaudRate);
+  gUartDeviceNode.DataBits = PcdGet8 (PcdUartDefaultDataBits);
+  gUartDeviceNode.Parity   = PcdGet8 (PcdUartDefaultParity);
+  gUartDeviceNode.StopBits = PcdGet8 (PcdUartDefaultStopBits);
+
+  ConnectRootBridge ();
+
+  //
+  // Do platform specific PCI Device check and add them to ConOut, ConIn, ErrOut
+  //
+  DetectAndPreparePlatformPciDevicePaths (FALSE);
+
+}
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h
new file mode 100644
index 0000000000..5e9fb92610
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformConsole.h
@@ -0,0 +1,76 @@
+/** @file
+Head file for BDS Platform specific code
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+**/
+
+#ifndef _PLATFORM_CONSOLE_H
+#define _PLATFORM_CONSOLE_H
+
+#include <PiDxe.h>
+#include <IndustryStandard/Pci.h>
+#include <Library/DebugLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/BaseLib.h>
+#include <Library/PcdLib.h>
+#include <Library/UefiLib.h>
+#include <Library/DevicePathLib.h>
+#include <Protocol/PciIo.h>
+
+#define IS_PCI_ISA_PDECODE(_p)        IS_CLASS3 (_p, PCI_CLASS_BRIDGE, PCI_CLASS_BRIDGE_ISA_PDECODE, 0)
+#define IS_PCI_16550SERIAL(_p)        IS_CLASS3 (_p, PCI_CLASS_SCC, PCI_SUBCLASS_SERIAL, PCI_IF_16550)
+
+//
+// Type definitions
+//
+
+//
+// Platform Root Bridge
+//
+typedef struct {
+  ACPI_HID_DEVICE_PATH      PciRootBridge;
+  EFI_DEVICE_PATH_PROTOCOL  End;
+} PLATFORM_ROOT_BRIDGE_DEVICE_PATH;
+
+typedef
+EFI_STATUS
+(EFIAPI *PROTOCOL_INSTANCE_CALLBACK)(
+  IN EFI_HANDLE            Handle,
+  IN VOID                 *Instance,
+  IN VOID                 *Context
+);
+
+/**
+  @param[in]  Handle - Handle of PCI device instance
+  @param[in]  PciIo - PCI IO protocol instance
+  @param[in]  Pci - PCI Header register block
+**/
+typedef
+EFI_STATUS
+(EFIAPI *VISIT_PCI_INSTANCE_CALLBACK)(
+  IN EFI_HANDLE           Handle,
+  IN EFI_PCI_IO_PROTOCOL  *PciIo,
+  IN PCI_TYPE00           *Pci
+);
+
+/**
+  Platform console init. Include the platform firmware vendor, revision
+  and so crc check.
+
+**/
+VOID
+EFIAPI
+PlatformConsoleInit (
+  VOID
+);
+
+#endif
diff --git a/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c
new file mode 100644
index 0000000000..50a595ed63
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformData.c
@@ -0,0 +1,45 @@
+/**@file
+  Defined the platform specific device path which will be filled to
+  ConIn/ConOut variables.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+**/
+
+#include "PlatformBootManager.h"
+
+///
+/// Predefined platform default console device path
+///
+GLOBAL_REMOVE_IF_UNREFERENCED PLATFORM_CONSOLE_CONNECT_ENTRY   gPlatformConsole[] = {
+  {
+    NULL,
+    0
+  }
+};
+
+
+GLOBAL_REMOVE_IF_UNREFERENCED USB_CLASS_FORMAT_DEVICE_PATH gUsbClassKeyboardDevicePath = {
+  {
+    {
+      MESSAGING_DEVICE_PATH,
+      MSG_USB_CLASS_DP,
+      {
+        (UINT8) (sizeof (USB_CLASS_DEVICE_PATH)),
+        (UINT8) ((sizeof (USB_CLASS_DEVICE_PATH)) >> 8)
+      }
+    },
+    0xffff,           // VendorId
+    0xffff,           // ProductId
+    CLASS_HID,        // DeviceClass
+    SUBCLASS_BOOT,    // DeviceSubClass
+    PROTOCOL_KEYBOARD // DeviceProtocol
+  },
+  gEndEntire
+};
diff --git a/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c
new file mode 100644
index 0000000000..a53582f181
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.c
@@ -0,0 +1,104 @@
+/** @file
+  Platform Hook Library instance for UART device.
+
+  Copyright (c) 2015, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <Base.h>
+#include <Uefi/UefiBaseType.h>
+#include <Library/PciLib.h>
+#include <Library/PlatformHookLib.h>
+#include <Library/BlParseLib.h>
+#include <Library/PcdLib.h>
+
+typedef struct {
+  UINT16  VendorId;          ///< Vendor ID to match the PCI device.  The value 0xFFFF terminates the list of entries.
+  UINT16  DeviceId;          ///< Device ID to match the PCI device
+  UINT32  ClockRate;         ///< UART clock rate.  Set to 0 for default clock rate of 1843200 Hz
+  UINT64  Offset;            ///< The byte offset into to the BAR
+  UINT8   BarIndex;          ///< Which BAR to get the UART base address
+  UINT8   RegisterStride;    ///< UART register stride in bytes.  Set to 0 for default register stride of 1 byte.
+  UINT16  ReceiveFifoDepth;  ///< UART receive FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  UINT16  TransmitFifoDepth; ///< UART transmit FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  UINT8   Reserved[2];
+} PCI_SERIAL_PARAMETER;
+
+/**
+  Performs platform specific initialization required for the CPU to access
+  the hardware associated with a SerialPortLib instance.  This function does
+  not initialize the serial port hardware itself.  Instead, it initializes
+  hardware devices that are required for the CPU to access the serial port
+  hardware.  This function may be called more than once.
+
+  @retval RETURN_SUCCESS       The platform specific initialization succeeded.
+  @retval RETURN_DEVICE_ERROR  The platform specific initialization could not be completed.
+
+**/
+RETURN_STATUS
+EFIAPI
+PlatformHookSerialPortInitialize (
+  VOID
+  )
+{
+  RETURN_STATUS         Status;
+  UINT32                DeviceVendor;
+  PCI_SERIAL_PARAMETER  *SerialParam;
+  SERIAL_PORT_INFO      SerialPortInfo;
+
+  Status = ParseSerialInfo (&SerialPortInfo);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  if (SerialPortInfo.Type == PLD_SERIAL_TYPE_MEMORY_MAPPED) {
+    Status = PcdSetBoolS (PcdSerialUseMmio, TRUE);
+  } else { //IO
+    Status = PcdSetBoolS (PcdSerialUseMmio, FALSE);
+  }
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+  Status = PcdSet64S (PcdSerialRegisterBase, SerialPortInfo.BaseAddr);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet32S (PcdSerialRegisterStride, SerialPortInfo.RegWidth);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet32S (PcdSerialBaudRate, SerialPortInfo.Baud);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet64S (PcdUartDefaultBaudRate, SerialPortInfo.Baud);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  Status = PcdSet32S (PcdSerialClockRate, SerialPortInfo.InputHertz);
+  if (RETURN_ERROR (Status)) {
+    return Status;
+  }
+
+  if (SerialPortInfo.UartPciAddr >= 0x80000000) {
+    DeviceVendor = PciRead32 (SerialPortInfo.UartPciAddr & 0x0ffff000);
+    SerialParam  = PcdGetPtr(PcdPciSerialParameters);
+    SerialParam->VendorId  = (UINT16)DeviceVendor;
+    SerialParam->DeviceId  = DeviceVendor >> 16;
+    SerialParam->ClockRate = SerialPortInfo.InputHertz;
+    SerialParam->RegisterStride = (UINT8)SerialPortInfo.RegWidth;
+  }
+
+  return RETURN_SUCCESS;
+}
diff --git a/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
new file mode 100644
index 0000000000..6f4a2e3b99
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
@@ -0,0 +1,44 @@
+## @file
+#  Platform Hook Library instance for UART device.
+#
+#  Copyright (c) 2015, Intel Corporation. All rights reserved.<BR>
+#
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution. The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PlatformHookLib
+  FILE_GUID                      = 40A2CBC6-CFB8-447b-A90E-198E88FD345E
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PlatformHookLib
+  CONSTRUCTOR                    = PlatformHookSerialPortInitialize
+
+[Sources]
+  PlatformHookLib.c
+
+[LibraryClasses]
+  BlParseLib
+  PcdLib
+  PciLib
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[Pcd]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio         ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase    ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate        ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride  ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate       ## PRODUCES
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate         ## PRODUCES
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciSerialParameters   ## PRODUCES
diff --git a/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c
new file mode 100644
index 0000000000..46cdd75eff
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.c
@@ -0,0 +1,35 @@
+/** @file
+  Include all platform specific features which can be customized by IBV/OEM.
+
+Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <Uefi.h>
+#include <Library/BaseLib.h>
+#include <Library/UefiLib.h>
+#include <Library/PlatformSupportLib.h>
+
+/**
+  Parse platform specific information from coreboot.
+
+  @retval RETURN_SUCCESS       The platform specific coreboot support succeeded.
+  @retval RETURN_DEVICE_ERROR  The platform specific coreboot support could not be completed.
+
+**/
+EFI_STATUS
+EFIAPI
+ParsePlatformInfo (
+  VOID
+  )
+{
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
new file mode 100644
index 0000000000..d0179c570e
--- /dev/null
+++ b/UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
@@ -0,0 +1,34 @@
+## @file
+#  Include all platform specific features which can be customized by IBV/OEM.
+#
+#  Copyright (c) 2016 - 2019, Intel Corporation. All rights reserved.<BR>
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution.  The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = PlatformSupportLib
+  FILE_GUID                      = B42AA265-00CA-4d4b-AC14-DBD5268E1BC7
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = PlatformSupportLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  PlatformSupportLibNull.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
diff --git a/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c
new file mode 100644
index 0000000000..da8815a887
--- /dev/null
+++ b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.c
@@ -0,0 +1,177 @@
+/** @file
+  Reset System Library functions for bootloader
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <PiDxe.h>
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Guid/AcpiBoardInfoGuid.h>
+
+ACPI_BOARD_INFO    mAcpiBoardInfo;
+
+/**
+  The constructor function to initialize mAcpiBoardInfo.
+
+  @retval EFI_SUCCESS   The constructor always returns RETURN_SUCCESS.
+
+**/
+RETURN_STATUS
+EFIAPI
+ResetSystemLibConstructor (
+  VOID
+  )
+{
+  EFI_HOB_GUID_TYPE  *GuidHob;
+  ACPI_BOARD_INFO    *AcpiBoardInfoPtr;
+
+  //
+  // Find the acpi board information guid hob
+  //
+  GuidHob = GetFirstGuidHob (&gUefiAcpiBoardInfoGuid);
+  ASSERT (GuidHob != NULL);
+
+  AcpiBoardInfoPtr = (ACPI_BOARD_INFO *)GET_GUID_HOB_DATA (GuidHob);
+  CopyMem (&mAcpiBoardInfo, AcpiBoardInfoPtr, sizeof (ACPI_BOARD_INFO));
+
+  return EFI_SUCCESS;
+}
+
+
+VOID
+AcpiPmControl (
+  UINTN   SuspendType
+  )
+{
+  UINTN              PmCtrlReg;
+
+  ASSERT (SuspendType <= 7);
+
+  PmCtrlReg = (UINTN)mAcpiBoardInfo.PmCtrlRegBase;
+  IoAndThenOr16 (PmCtrlReg, (UINT16) ~0x3c00, (UINT16) (SuspendType << 10));
+  IoOr16 (PmCtrlReg, 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
+  )
+{
+  IoWrite8 ((UINTN)mAcpiBoardInfo.ResetRegAddress, mAcpiBoardInfo.ResetValue);
+  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
+  )
+{
+  IoWrite8 ((UINTN)mAcpiBoardInfo.ResetRegAddress, mAcpiBoardInfo.ResetValue);
+  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
+  )
+{
+  UINTN              PmCtrlReg;
+
+  //
+  // GPE0_EN should be disabled to avoid any GPI waking up the system from S5
+  //
+  IoWrite16 ((UINTN)mAcpiBoardInfo.PmGpeEnBase,  0);
+
+  //
+  // Clear Power Button Status
+  //
+  IoWrite16((UINTN) mAcpiBoardInfo.PmEvtBase, BIT8);
+
+  //
+  // Transform system into S5 sleep state
+  //
+  PmCtrlReg = (UINTN)mAcpiBoardInfo.PmCtrlRegBase;
+  IoAndThenOr16 (PmCtrlReg, (UINT16) ~0x3c00, (UINT16) (7 << 10));
+  IoOr16 (PmCtrlReg, BIT13);
+  CpuDeadLoop ();
+
+  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
+  )
+{
+  AcpiPmControl (5);
+  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
+  )
+{
+  ResetCold ();
+}
diff --git a/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
new file mode 100644
index 0000000000..92c6d70eb9
--- /dev/null
+++ b/UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
@@ -0,0 +1,46 @@
+## @file
+#  Library instance for ResetSystem library class for bootloader
+#
+#  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution.  The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = ResetSystemLib
+  FILE_GUID                      = C5CD4EEE-527F-47df-9C92-B41414AF7479
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = ResetSystemLib
+
+  CONSTRUCTOR                    = ResetSystemLibConstructor
+#
+# 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
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  DebugLib
+  IoLib
+  HobLib
+  BaseMemoryLib
+
+[Guids]
+  gUefiAcpiBoardInfoGuid
+
diff --git a/UefiPayloadPkg/Library/SblParseLib/SblParseLib.c b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.c
new file mode 100644
index 0000000000..6a64d0ff05
--- /dev/null
+++ b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.c
@@ -0,0 +1,202 @@
+/** @file
+  This library will parse the Slim Bootloader to get required information.
+
+  Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+  This program and the accompanying materials
+  are licensed and made available under the terms and conditions of the BSD License
+  which accompanies this distribution.  The full text of the license may be found at
+  http://opensource.org/licenses/bsd-license.php
+
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <PiDxe.h>
+#include <Library/BaseLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/IoLib.h>
+#include <Library/HobLib.h>
+#include <Library/BlParseLib.h>
+#include <IndustryStandard/Acpi.h>
+
+
+/**
+  This function retrieves the parameter base address from boot loader.
+
+  This function will get bootloader specific parameter address for UEFI payload.
+  e.g. HobList pointer for Slim Bootloader, and coreboot table header for Coreboot.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+EFIAPI
+GetParameterBase (
+  VOID
+  )
+{
+  EFI_HOB_HANDOFF_INFO_TABLE          *HandoffTable;
+
+  HandoffTable = (EFI_HOB_HANDOFF_INFO_TABLE *)(UINTN) GET_BOOTLOADER_PARAMETER ();
+  if ((HandoffTable->Header.HobType == EFI_HOB_TYPE_HANDOFF) &&
+    (HandoffTable->Header.HobLength == sizeof (EFI_HOB_HANDOFF_INFO_TABLE)) &&
+    (HandoffTable->Header.Reserved == 0)) {
+    return (VOID *)HandoffTable;
+  }
+
+  return NULL;
+}
+
+
+/**
+  This function retrieves a GUIDed HOB data from Slim Bootloader.
+
+  This function will search SBL HOB list to find the first GUIDed HOB that
+  its GUID matches Guid.
+
+  @param[in]  Guid        A pointer to HOB GUID to search.
+
+  @retval NULL            Failed to find the GUID HOB.
+  @retval others          GUIDed HOB data pointer.
+
+**/
+VOID *
+GetGuidHobDataFromSbl (
+  IN       EFI_GUID      *Guid
+  )
+{
+  UINT8                  *GuidHob;
+  CONST VOID             *HobList;
+
+  HobList = GetParameterBase ();
+  ASSERT (HobList != NULL);
+  GuidHob = GetNextGuidHob (Guid, HobList);
+  if (GuidHob != NULL) {
+    return GET_GUID_HOB_DATA (GuidHob);
+  }
+
+  return NULL;
+}
+
+/**
+  Acquire the memory map information.
+
+  @param  MemInfoCallback     The callback routine
+  @param  Params              Pointer to the callback routine parameter
+
+  @retval RETURN_SUCCESS     Successfully find out the memory information.
+  @retval RETURN_NOT_FOUND   Failed to find the memory information.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseMemoryInfo (
+  IN  BL_MEM_INFO_CALLBACK       MemInfoCallback,
+  IN  VOID                       *Params
+  )
+{
+  MEMROY_MAP_INFO               *MemoryMapInfo;
+  UINTN                          Idx;
+
+  MemoryMapInfo = (MEMROY_MAP_INFO *) GetGuidHobDataFromSbl (&gLoaderMemoryMapInfoGuid);
+  if (MemoryMapInfo == NULL) {
+    ASSERT (FALSE);
+    return RETURN_NOT_FOUND;
+  }
+
+  for (Idx = 0; Idx < MemoryMapInfo->Count; Idx++) {
+    MemInfoCallback (&MemoryMapInfo->Entry[Idx], Params);
+  }
+
+  return RETURN_SUCCESS;
+}
+
+/**
+  Acquire acpi table and smbios table from slim bootloader
+
+  @param  SystemTableInfo           Pointer to the system table info
+
+  @retval RETURN_SUCCESS            Successfully find out the tables.
+  @retval RETURN_NOT_FOUND          Failed to find the tables.
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSystemTable (
+  OUT SYSTEM_TABLE_INFO     *SystemTableInfo
+  )
+{
+  SYSTEM_TABLE_INFO         *TableInfo;
+
+  TableInfo = (SYSTEM_TABLE_INFO *)GetGuidHobDataFromSbl (&gUefiSystemTableInfoGuid);
+  if (TableInfo == NULL) {
+    ASSERT (FALSE);
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (SystemTableInfo, TableInfo, sizeof (SYSTEM_TABLE_INFO));
+
+  return RETURN_SUCCESS;
+}
+
+
+/**
+  Find the serial port information
+
+  @param  SERIAL_PORT_INFO   Pointer to serial port info structure
+
+  @retval RETURN_SUCCESS     Successfully find the serial port information.
+  @retval RETURN_NOT_FOUND   Failed to find the serial port information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseSerialInfo (
+  OUT SERIAL_PORT_INFO     *SerialPortInfo
+  )
+{
+  SERIAL_PORT_INFO              *BlSerialInfo;
+
+  BlSerialInfo = (SERIAL_PORT_INFO *) GetGuidHobDataFromSbl (&gUefiSerialPortInfoGuid);
+  if (BlSerialInfo == NULL) {
+    ASSERT (FALSE);
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (SerialPortInfo, BlSerialInfo, sizeof (SERIAL_PORT_INFO));
+
+  return RETURN_SUCCESS;
+}
+
+
+/**
+  Find the video frame buffer information
+
+  @param  FbInfo             Pointer to the FRAME_BUFFER_INFO structure
+
+  @retval RETURN_SUCCESS     Successfully find the video frame buffer information.
+  @retval RETURN_NOT_FOUND   Failed to find the video frame buffer information .
+
+**/
+RETURN_STATUS
+EFIAPI
+ParseFbInfo (
+  OUT FRAME_BUFFER_INFO       *FbInfo
+  )
+{
+  FRAME_BUFFER_INFO           *BlFbInfo;
+
+  BlFbInfo = (FRAME_BUFFER_INFO *) GetGuidHobDataFromSbl (&gUefiFrameBufferInfoGuid);
+  if (BlFbInfo == NULL) {
+    return RETURN_NOT_FOUND;
+  }
+
+  CopyMem (FbInfo, BlFbInfo, sizeof (FRAME_BUFFER_INFO));
+
+  return RETURN_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
new file mode 100644
index 0000000000..61e203c113
--- /dev/null
+++ b/UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
@@ -0,0 +1,51 @@
+## @file
+#  Slim Bootloader parse library.
+#
+#  Copyright (c) 2019, Intel Corporation. All rights reserved.<BR>
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution.  The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php
+#
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = SblParseLib
+  FILE_GUID                      = DE6FB32C-52CF-4A17-A84C-B323653CB5E0
+  MODULE_TYPE                    = BASE
+  VERSION_STRING                 = 1.0
+  LIBRARY_CLASS                  = BlParseLib
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64
+#
+
+[Sources]
+  SblParseLib.c
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseLib
+  BaseMemoryLib
+  DebugLib
+  PcdLib
+  HobLib
+
+[Guids]
+  gUefiFrameBufferInfoGuid
+  gUefiSystemTableInfoGuid
+  gUefiSerialPortInfoGuid
+  gLoaderMemoryMapInfoGuid
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop
diff --git a/UefiPayloadPkg/SecCore/FindPeiCore.c b/UefiPayloadPkg/SecCore/FindPeiCore.c
new file mode 100644
index 0000000000..c7427ab9b7
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/FindPeiCore.c
@@ -0,0 +1,199 @@
+/** @file
+  Locate the entry point for the PEI Core
+
+Copyright (c) 2013, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include <PiPei.h>
+#include <Library/BaseLib.h>
+#include <Library/PeCoffGetEntryPointLib.h>
+
+#include "SecMain.h"
+
+/**
+  Find core image base.
+
+  @param   BootFirmwareVolumePtr    Point to the boot firmware volume.
+  @param   SecCoreImageBase         The base address of the SEC core image.
+  @param   PeiCoreImageBase         The base address of the PEI core image.
+
+**/
+EFI_STATUS
+EFIAPI
+FindImageBase (
+  IN  EFI_FIRMWARE_VOLUME_HEADER       *BootFirmwareVolumePtr,
+  OUT EFI_PHYSICAL_ADDRESS             *SecCoreImageBase,
+  OUT EFI_PHYSICAL_ADDRESS             *PeiCoreImageBase
+  )
+{
+  EFI_PHYSICAL_ADDRESS        CurrentAddress;
+  EFI_PHYSICAL_ADDRESS        EndOfFirmwareVolume;
+  EFI_FFS_FILE_HEADER         *File;
+  UINT32                      Size;
+  EFI_PHYSICAL_ADDRESS        EndOfFile;
+  EFI_COMMON_SECTION_HEADER   *Section;
+  EFI_PHYSICAL_ADDRESS        EndOfSection;
+
+  *SecCoreImageBase = 0;
+  *PeiCoreImageBase = 0;
+
+  CurrentAddress = (EFI_PHYSICAL_ADDRESS)(UINTN) BootFirmwareVolumePtr;
+  EndOfFirmwareVolume = CurrentAddress + BootFirmwareVolumePtr->FvLength;
+
+  //
+  // Loop through the FFS files in the Boot Firmware Volume
+  //
+  for (EndOfFile = CurrentAddress + BootFirmwareVolumePtr->HeaderLength; ; ) {
+
+    CurrentAddress = (EndOfFile + 7) & 0xfffffffffffffff8ULL;
+    if (CurrentAddress > EndOfFirmwareVolume) {
+      return EFI_NOT_FOUND;
+    }
+
+    File = (EFI_FFS_FILE_HEADER*)(UINTN) CurrentAddress;
+    if (IS_FFS_FILE2 (File)) {
+      Size = FFS_FILE2_SIZE (File);
+      if (Size <= 0x00FFFFFF) {
+        return EFI_NOT_FOUND;
+      }
+    } else {
+      Size = FFS_FILE_SIZE (File);
+      if (Size < sizeof (EFI_FFS_FILE_HEADER)) {
+        return EFI_NOT_FOUND;
+      }
+    }
+
+    EndOfFile = CurrentAddress + Size;
+    if (EndOfFile > EndOfFirmwareVolume) {
+      return EFI_NOT_FOUND;
+    }
+
+    //
+    // Look for SEC Core / PEI Core files
+    //
+    if (File->Type != EFI_FV_FILETYPE_SECURITY_CORE &&
+        File->Type != EFI_FV_FILETYPE_PEI_CORE) {
+      continue;
+    }
+
+    //
+    // Loop through the FFS file sections within the FFS file
+    //
+    if (IS_FFS_FILE2 (File)) {
+      EndOfSection = (EFI_PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) File + sizeof (EFI_FFS_FILE_HEADER2));
+    } else {
+      EndOfSection = (EFI_PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) File + sizeof (EFI_FFS_FILE_HEADER));
+    }
+    for (;;) {
+      CurrentAddress = (EndOfSection + 3) & 0xfffffffffffffffcULL;
+      Section = (EFI_COMMON_SECTION_HEADER*)(UINTN) CurrentAddress;
+
+      if (IS_SECTION2 (Section)) {
+        Size = SECTION2_SIZE (Section);
+        if (Size <= 0x00FFFFFF) {
+          return EFI_NOT_FOUND;
+        }
+      } else {
+        Size = SECTION_SIZE (Section);
+        if (Size < sizeof (EFI_COMMON_SECTION_HEADER)) {
+          return EFI_NOT_FOUND;
+        }
+      }
+
+      EndOfSection = CurrentAddress + Size;
+      if (EndOfSection > EndOfFile) {
+        return EFI_NOT_FOUND;
+      }
+
+      //
+      // Look for executable sections
+      //
+      if (Section->Type == EFI_SECTION_PE32 || Section->Type == EFI_SECTION_TE) {
+        if (File->Type == EFI_FV_FILETYPE_SECURITY_CORE) {
+          if (IS_SECTION2 (Section)) {
+            *SecCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER2));
+          } else {
+            *SecCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER));
+          }
+        } else {
+          if (IS_SECTION2 (Section)) {
+            *PeiCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER2));
+          } else {
+            *PeiCoreImageBase = (PHYSICAL_ADDRESS) (UINTN) ((UINT8 *) Section + sizeof (EFI_COMMON_SECTION_HEADER));
+          }
+        }
+        break;
+      }
+    }
+
+    //
+    // Both SEC Core and PEI Core images found
+    //
+    if (*SecCoreImageBase != 0 && *PeiCoreImageBase != 0) {
+      return EFI_SUCCESS;
+    }
+  }
+}
+
+/**
+  Find and return Pei Core entry point.
+
+  It also find SEC and PEI Core file debug information. It will report them if
+  remote debug is enabled.
+
+  @param   BootFirmwareVolumePtr    Point to the boot firmware volume.
+  @param   PeiCoreEntryPoint        The entry point of the PEI core.
+
+**/
+VOID
+EFIAPI
+FindAndReportEntryPoints (
+  IN  EFI_FIRMWARE_VOLUME_HEADER       *BootFirmwareVolumePtr,
+  OUT EFI_PEI_CORE_ENTRY_POINT         *PeiCoreEntryPoint
+  )
+{
+  EFI_STATUS                       Status;
+  EFI_PHYSICAL_ADDRESS             SecCoreImageBase;
+  EFI_PHYSICAL_ADDRESS             PeiCoreImageBase;
+  PE_COFF_LOADER_IMAGE_CONTEXT     ImageContext;
+
+  //
+  // Find SEC Core and PEI Core image base
+  //
+  Status = FindImageBase (BootFirmwareVolumePtr, &SecCoreImageBase, &PeiCoreImageBase);
+  ASSERT_EFI_ERROR (Status);
+
+  ZeroMem ((VOID *) &ImageContext, sizeof (PE_COFF_LOADER_IMAGE_CONTEXT));
+  //
+  // Report SEC Core debug information when remote debug is enabled
+  //
+  ImageContext.ImageAddress = SecCoreImageBase;
+  ImageContext.PdbPointer = PeCoffLoaderGetPdbPointer ((VOID*) (UINTN) ImageContext.ImageAddress);
+  PeCoffLoaderRelocateImageExtraAction (&ImageContext);
+
+  //
+  // Report PEI Core debug information when remote debug is enabled
+  //
+  ImageContext.ImageAddress = PeiCoreImageBase;
+  ImageContext.PdbPointer = PeCoffLoaderGetPdbPointer ((VOID*) (UINTN) ImageContext.ImageAddress);
+  PeCoffLoaderRelocateImageExtraAction (&ImageContext);
+
+  //
+  // Find PEI Core entry point
+  //
+  Status = PeCoffLoaderGetEntryPoint ((VOID *) (UINTN) PeiCoreImageBase, (VOID**) PeiCoreEntryPoint);
+  if (EFI_ERROR (Status)) {
+    *PeiCoreEntryPoint = 0;
+  }
+
+  return;
+}
+
diff --git a/UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm b/UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm
new file mode 100644
index 0000000000..ba507a103c
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/Ia32/SecEntry.nasm
@@ -0,0 +1,84 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+; This program and the accompanying materials
+; are licensed and made available under the terms and conditions of the BSD License
+; which accompanies this distribution.  The full text of the license may be found at
+; http://opensource.org/licenses/bsd-license.php.
+;
+; THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+; WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+;
+; Abstract:
+;
+;   Entry point for the coreboot UEFI payload.
+;
+;------------------------------------------------------------------------------
+
+SECTION .text
+
+; C Functions
+extern  ASM_PFX(SecStartup)
+
+; Pcds
+extern  ASM_PFX(PcdGet32 (PcdPayloadFdMemBase))
+extern  ASM_PFX(PcdGet32 (PcdPayloadStackTop))
+
+;
+; SecCore Entry Point
+;
+; Processor is in flat protected mode
+;
+; @param[in]  EAX   Initial value of the EAX register (BIST: Built-in Self Test)
+; @param[in]  DI    'BP': boot-strap processor, or 'AP': application processor
+; @param[in]  EBP   Pointer to the start of the Boot Firmware Volume
+;
+; @return     None  This routine does not return
+;
+global ASM_PFX(_ModuleEntryPoint)
+ASM_PFX(_ModuleEntryPoint):
+  ;
+  ; Disable all the interrupts
+  ;
+  cli
+
+  ;
+  ; Save the Payload HOB base address before switching the stack
+  ;
+  mov     eax, [esp + 4]
+
+  ;
+  ; Construct the temporary memory at 0x80000, length 0x10000
+  ;
+  mov     esp, DWORD [ASM_PFX(PcdGet32 (PcdPayloadStackTop))]
+
+  ;
+  ; Push the Payload HOB base address onto new stack
+  ;
+  push    eax
+
+  ;
+  ; Pass BFV into the PEI Core
+  ;
+  push    DWORD [ASM_PFX(PcdGet32 (PcdPayloadFdMemBase))]
+
+  ;
+  ; Pass stack base into the PEI Core
+  ;
+  push    BASE_512KB
+
+  ;
+  ; Pass stack size into the PEI Core
+  ;
+  push    SIZE_64KB
+
+  ;
+  ; Pass Control into the PEI Core
+  ;
+  call    ASM_PFX(SecStartup)
+
+  ;
+  ; Should never return
+  ;
+  jmp     $
+
diff --git a/UefiPayloadPkg/SecCore/Ia32/Stack.nasm b/UefiPayloadPkg/SecCore/Ia32/Stack.nasm
new file mode 100644
index 0000000000..d66150c236
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/Ia32/Stack.nasm
@@ -0,0 +1,78 @@
+;------------------------------------------------------------------------------
+;
+; Copyright (c) 2015 - 2016, Intel Corporation. All rights reserved.<BR>
+; This program and the accompanying materials
+; are licensed and made available under the terms and conditions of the BSD License
+; which accompanies this distribution.  The full text of the license may be found at
+; http://opensource.org/licenses/bsd-license.php.
+;
+; THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+; WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+;
+; Abstract:
+;
+;   Switch the stack from temporary memory to permanent memory.
+;
+;------------------------------------------------------------------------------
+
+SECTION .text
+
+;------------------------------------------------------------------------------
+; VOID
+; EFIAPI
+; SecSwitchStack (
+;   UINT32   TemporaryMemoryBase,
+;   UINT32   PermenentMemoryBase
+;   );
+;------------------------------------------------------------------------------
+global ASM_PFX(SecSwitchStack)
+ASM_PFX(SecSwitchStack):
+    ;
+    ; Save three register: eax, ebx, ecx
+    ;
+    push  eax
+    push  ebx
+    push  ecx
+    push  edx
+
+    ;
+    ; !!CAUTION!! this function address's is pushed into stack after
+    ; migration of whole temporary memory, so need save it to permanent
+    ; memory at first!
+    ;
+
+    mov   ebx,  [esp + 20]          ; Save the first parameter
+    mov   ecx,  [esp + 24]          ; Save the second parameter
+
+    ;
+    ; Save this function's return address into permanent memory at first.
+    ; Then, Fixup the esp point to permanent memory
+    ;
+    mov   eax,  esp
+    sub   eax,  ebx
+    add   eax,  ecx
+    mov   edx,  [esp]               ; copy pushed register's value to permanent memory
+    mov   [eax], edx
+    mov   edx,  [esp + 4]
+    mov   [eax + 4], edx
+    mov   edx,  [esp + 8]
+    mov   [eax + 8], edx
+    mov   edx,  [esp + 12]
+    mov   [eax + 12], edx
+    mov   edx,  [esp + 16]          ; Update return address into permanent memory
+    mov   [eax + 16], edx
+    mov   esp,  eax                 ; From now, esp is pointed to permanent memory
+
+    ;
+    ; Fixup the ebp point to permanent memory
+    ;
+    mov   eax,  ebp
+    sub   eax,  ebx
+    add   eax,  ecx
+    mov   ebp,  eax                 ; From now, ebp is pointed to permanent memory
+
+    pop   edx
+    pop   ecx
+    pop   ebx
+    pop   eax
+    ret
diff --git a/UefiPayloadPkg/SecCore/SecCore.inf b/UefiPayloadPkg/SecCore/SecCore.inf
new file mode 100644
index 0000000000..4c4070d0f5
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/SecCore.inf
@@ -0,0 +1,63 @@
+## @file
+# This is the first module taking control from the coreboot.
+#
+#  Copyright (c) 2013 - 2019, Intel Corporation. All rights reserved.<BR>
+#
+#  This program and the accompanying materials
+#  are licensed and made available under the terms and conditions of the BSD License
+#  which accompanies this distribution. The full text of the license may be found at
+#  http://opensource.org/licenses/bsd-license.php.
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+#
+##
+
+[Defines]
+  INF_VERSION                    = 0x00010005
+  BASE_NAME                      = SecCore
+  FILE_GUID                      = BA7BE337-6CFB-4dbb-B26C-21EC2FC16073
+  MODULE_TYPE                    = SEC
+  VERSION_STRING                 = 1.0
+
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+#  VALID_ARCHITECTURES           = IA32 X64 EBC
+#
+
+[Sources]
+  SecMain.c
+  SecMain.h
+  FindPeiCore.c
+
+[Sources.IA32]
+  Ia32/Stack.nasm
+  Ia32/SecEntry.nasm
+
+[Packages]
+  MdePkg/MdePkg.dec
+  MdeModulePkg/MdeModulePkg.dec
+  UefiCpuPkg/UefiCpuPkg.dec
+  UefiPayloadPkg/UefiPayloadPkg.dec
+
+[LibraryClasses]
+  BaseMemoryLib
+  DebugLib
+  BaseLib
+  PcdLib
+  DebugAgentLib
+  UefiCpuLib
+  PeCoffGetEntryPointLib
+  PeCoffExtraActionLib
+
+[Ppis]
+  gEfiSecPlatformInformationPpiGuid             # PPI ALWAYS_PRODUCED
+  gEfiTemporaryRamSupportPpiGuid                # PPI ALWAYS_PRODUCED
+  gEfiPayLoadHobBasePpiGuid                     # PPI ALWAYS_PRODUCED
+
+[Pcd]
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize
+  gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop
diff --git a/UefiPayloadPkg/SecCore/SecMain.c b/UefiPayloadPkg/SecCore/SecMain.c
new file mode 100644
index 0000000000..112a06caa7
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/SecMain.c
@@ -0,0 +1,294 @@
+/** @file
+  C functions in SEC
+
+Copyright (c) 2013, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+
+#include "SecMain.h"
+
+EFI_PEI_TEMPORARY_RAM_SUPPORT_PPI gSecTemporaryRamSupportPpi = {
+  SecTemporaryRamSupport
+};
+
+EFI_PEI_PPI_DESCRIPTOR            mPeiSecPlatformInformationPpi[] = {
+  {
+    (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
+    &gEfiTemporaryRamSupportPpiGuid,
+    &gSecTemporaryRamSupportPpi
+  }
+};
+
+//
+// These are IDT entries pointing to 10:FFFFFFE4h.
+//
+UINT64  mIdtEntryTemplate = 0xffff8e000010ffe4ULL;
+
+/**
+  Caller provided function to be invoked at the end of InitializeDebugAgent().
+
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+  @param[in] Context    The first input parameter of InitializeDebugAgent().
+
+**/
+VOID
+EFIAPI
+SecStartupPhase2(
+  IN VOID                     *Context
+  );
+
+
+/**
+
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+
+  @param SizeOfRam           Size of the temporary memory available for use.
+  @param TempRamBase         Base address of temporary ram
+  @param BootFirmwareVolume  Base address of the Boot Firmware Volume.
+  @param BootloaderParameter A parameter from bootloader, e.g. HobList from SlimBootloader
+
+**/
+VOID
+EFIAPI
+SecStartup (
+  IN UINT32                   SizeOfRam,
+  IN UINT32                   TempRamBase,
+  IN VOID                     *BootFirmwareVolume,
+  IN UINT32                   BootloaderParameter
+  )
+{
+  EFI_SEC_PEI_HAND_OFF        SecCoreData;
+  IA32_DESCRIPTOR             IdtDescriptor;
+  SEC_IDT_TABLE               IdtTableInStack;
+  UINT32                      Index;
+  UINT32                      PeiStackSize;
+
+  PeiStackSize = (SizeOfRam >> 1);
+
+  ASSERT (PeiStackSize < SizeOfRam);
+
+  //
+  // Process all libraries constructor function linked to SecCore.
+  //
+  ProcessLibraryConstructorList ();
+
+  //
+  // Initialize floating point operating environment
+  // to be compliant with UEFI spec.
+  //
+  InitializeFloatingPointUnits ();
+
+
+  // |-------------------|---->
+  // |Idt Table          |
+  // |-------------------|
+  // |PeiService Pointer |    PeiStackSize
+  // |-------------------|
+  // |                   |
+  // |      Stack        |
+  // |-------------------|---->
+  // |                   |
+  // |                   |
+  // |      Heap         |    PeiTemporaryRamSize
+  // |                   |
+  // |                   |
+  // |-------------------|---->  TempRamBase
+
+  IdtTableInStack.PeiService = 0;
+  for (Index = 0; Index < SEC_IDT_ENTRY_COUNT; Index ++) {
+    CopyMem ((VOID*)&IdtTableInStack.IdtTable[Index], (VOID*)&mIdtEntryTemplate, sizeof (UINT64));
+  }
+
+  IdtDescriptor.Base  = (UINTN) &IdtTableInStack.IdtTable;
+  IdtDescriptor.Limit = (UINT16)(sizeof (IdtTableInStack.IdtTable) - 1);
+
+  AsmWriteIdtr (&IdtDescriptor);
+
+  //
+  // Update the base address and length of Pei temporary memory
+  //
+  SecCoreData.DataSize               = (UINT16) sizeof (EFI_SEC_PEI_HAND_OFF);
+  SecCoreData.BootFirmwareVolumeBase = BootFirmwareVolume;
+  SecCoreData.BootFirmwareVolumeSize = (UINTN)(0x100000000ULL - (UINTN) BootFirmwareVolume);
+  SecCoreData.TemporaryRamBase       = (VOID*)(UINTN) TempRamBase;
+  SecCoreData.TemporaryRamSize       = SizeOfRam;
+  SecCoreData.PeiTemporaryRamBase    = SecCoreData.TemporaryRamBase;
+  SecCoreData.PeiTemporaryRamSize    = SizeOfRam - PeiStackSize;
+  SecCoreData.StackBase              = (VOID*)(UINTN)(TempRamBase + SecCoreData.PeiTemporaryRamSize);
+  SecCoreData.StackSize              = PeiStackSize;
+
+  //
+  // Initialize Debug Agent to support source level debug in SEC/PEI phases before memory ready.
+  //
+  InitializeDebugAgent (DEBUG_AGENT_INIT_PREMEM_SEC, &SecCoreData, SecStartupPhase2);
+
+}
+
+/**
+  Caller provided function to be invoked at the end of InitializeDebugAgent().
+
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+  @param[in] Context    The first input parameter of InitializeDebugAgent().
+
+**/
+VOID
+EFIAPI
+SecStartupPhase2(
+  IN VOID                     *Context
+  )
+{
+  EFI_SEC_PEI_HAND_OFF        *SecCoreData;
+  EFI_PEI_CORE_ENTRY_POINT    PeiCoreEntryPoint;
+
+  SecCoreData = (EFI_SEC_PEI_HAND_OFF *) Context;
+  //
+  // Find Pei Core entry point. It will report SEC and Pei Core debug information if remote debug
+  // is enabled.
+  //
+  FindAndReportEntryPoints ((EFI_FIRMWARE_VOLUME_HEADER *) SecCoreData->BootFirmwareVolumeBase, &PeiCoreEntryPoint);
+  if (PeiCoreEntryPoint == NULL)
+  {
+    CpuDeadLoop ();
+  }
+
+  //
+  // Transfer the control to the PEI core
+  //
+  ASSERT (PeiCoreEntryPoint != NULL);
+  (*PeiCoreEntryPoint) (SecCoreData, (EFI_PEI_PPI_DESCRIPTOR *)&mPeiSecPlatformInformationPpi);
+
+  //
+  // Should not come here.
+  //
+  return ;
+}
+
+/**
+  This service of the TEMPORARY_RAM_SUPPORT_PPI that migrates temporary RAM into
+  permanent memory.
+
+  @param PeiServices            Pointer to the PEI Services Table.
+  @param TemporaryMemoryBase    Source Address in temporary memory from which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param PermanentMemoryBase    Destination Address in permanent memory into which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param CopySize               Amount of memory to migrate from temporary to permanent memory.
+
+  @retval EFI_SUCCESS           The data was successfully returned.
+  @retval EFI_INVALID_PARAMETER PermanentMemoryBase + CopySize > TemporaryMemoryBase when
+                                TemporaryMemoryBase > PermanentMemoryBase.
+
+**/
+EFI_STATUS
+EFIAPI
+SecTemporaryRamSupport (
+  IN CONST EFI_PEI_SERVICES   **PeiServices,
+  IN EFI_PHYSICAL_ADDRESS     TemporaryMemoryBase,
+  IN EFI_PHYSICAL_ADDRESS     PermanentMemoryBase,
+  IN UINTN                    CopySize
+  )
+{
+  IA32_DESCRIPTOR   IdtDescriptor;
+  VOID*             OldHeap;
+  VOID*             NewHeap;
+  VOID*             OldStack;
+  VOID*             NewStack;
+  DEBUG_AGENT_CONTEXT_POSTMEM_SEC  DebugAgentContext;
+  BOOLEAN           OldStatus;
+  UINTN             PeiStackSize;
+
+  PeiStackSize = (CopySize >> 1);
+
+  ASSERT (PeiStackSize < CopySize);
+
+  //
+  // |-------------------|---->
+  // |      Stack        |    PeiStackSize
+  // |-------------------|---->
+  // |      Heap         |    PeiTemporaryRamSize
+  // |-------------------|---->  TempRamBase
+  //
+  // |-------------------|---->
+  // |      Heap         |    PeiTemporaryRamSize
+  // |-------------------|---->
+  // |      Stack        |    PeiStackSize
+  // |-------------------|---->  PermanentMemoryBase
+  //
+
+  OldHeap = (VOID*)(UINTN)TemporaryMemoryBase;
+  NewHeap = (VOID*)((UINTN)PermanentMemoryBase + PeiStackSize);
+
+  OldStack = (VOID*)((UINTN)TemporaryMemoryBase + CopySize - PeiStackSize);
+  NewStack = (VOID*)(UINTN)PermanentMemoryBase;
+
+  DebugAgentContext.HeapMigrateOffset = (UINTN)NewHeap - (UINTN)OldHeap;
+  DebugAgentContext.StackMigrateOffset = (UINTN)NewStack - (UINTN)OldStack;
+
+  OldStatus = SaveAndSetDebugTimerInterrupt (FALSE);
+  //
+  // Initialize Debug Agent to support source level debug in PEI phase after memory ready.
+  // It will build HOB and fix up the pointer in IDT table.
+  //
+  InitializeDebugAgent (DEBUG_AGENT_INIT_POSTMEM_SEC, (VOID *) &DebugAgentContext, NULL);
+
+  //
+  // Migrate Heap
+  //
+  CopyMem (NewHeap, OldHeap, CopySize - PeiStackSize);
+
+  //
+  // Migrate Stack
+  //
+  CopyMem (NewStack, OldStack, PeiStackSize);
+
+
+  //
+  // We need *not* fix the return address because currently,
+  // The PeiCore is executed in flash.
+  //
+
+  //
+  // Rebase IDT table in permanent memory
+  //
+  AsmReadIdtr (&IdtDescriptor);
+  IdtDescriptor.Base = IdtDescriptor.Base - (UINTN)OldStack + (UINTN)NewStack;
+
+  AsmWriteIdtr (&IdtDescriptor);
+
+
+  //
+  // Program MTRR
+  //
+
+  //
+  // SecSwitchStack function must be invoked after the memory migration
+  // immediately, also we need fixup the stack change caused by new call into
+  // permanent memory.
+  //
+  SecSwitchStack (
+    (UINT32) (UINTN) OldStack,
+    (UINT32) (UINTN) NewStack
+    );
+
+  SaveAndSetDebugTimerInterrupt (OldStatus);
+
+  return EFI_SUCCESS;
+}
+
diff --git a/UefiPayloadPkg/SecCore/SecMain.h b/UefiPayloadPkg/SecCore/SecMain.h
new file mode 100644
index 0000000000..605dc2415c
--- /dev/null
+++ b/UefiPayloadPkg/SecCore/SecMain.h
@@ -0,0 +1,137 @@
+/** @file
+  Master header file for SecCore.
+
+Copyright (c) 2013, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution.  The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#ifndef _SEC_CORE_H_
+#define _SEC_CORE_H_
+
+
+#include <PiPei.h>
+
+#include <Ppi/SecPlatformInformation.h>
+#include <Ppi/TemporaryRamSupport.h>
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/UefiCpuLib.h>
+#include <Library/PeCoffGetEntryPointLib.h>
+#include <Library/PeCoffExtraActionLib.h>
+#include <Library/DebugAgentLib.h>
+
+
+#define SEC_IDT_ENTRY_COUNT  34
+
+typedef struct _SEC_IDT_TABLE {
+  //
+  // Reserved 8 bytes preceding IDT to store EFI_PEI_SERVICES**, since IDT base
+  // address should be 8-byte alignment.
+  // Note: For IA32, only the 4 bytes immediately preceding IDT is used to store
+  // EFI_PEI_SERVICES**
+  //
+  UINT64            PeiService;
+  UINT64            IdtTable[SEC_IDT_ENTRY_COUNT];
+} SEC_IDT_TABLE;
+
+/**
+  Switch the stack in the temporary memory to the one in the permanent memory.
+
+  This function must be invoked after the memory migration immediately. The relative
+  position of the stack in the temporary and permanent memory is same.
+
+  @param TemporaryMemoryBase  Base address of the temporary memory.
+  @param PermenentMemoryBase  Base address of the permanent memory.
+**/
+VOID
+EFIAPI
+SecSwitchStack (
+  UINT32   TemporaryMemoryBase,
+  UINT32   PermenentMemoryBase
+  );
+
+/**
+  This service of the TEMPORARY_RAM_SUPPORT_PPI that migrates temporary RAM into
+  permanent memory.
+
+  @param PeiServices            Pointer to the PEI Services Table.
+  @param TemporaryMemoryBase    Source Address in temporary memory from which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param PermanentMemoryBase    Destination Address in permanent memory into which the SEC or PEIM will copy the
+                                Temporary RAM contents.
+  @param CopySize               Amount of memory to migrate from temporary to permanent memory.
+
+  @retval EFI_SUCCESS           The data was successfully returned.
+  @retval EFI_INVALID_PARAMETER PermanentMemoryBase + CopySize > TemporaryMemoryBase when
+                                TemporaryMemoryBase > PermanentMemoryBase.
+
+**/
+EFI_STATUS
+EFIAPI
+SecTemporaryRamSupport (
+  IN CONST EFI_PEI_SERVICES   **PeiServices,
+  IN EFI_PHYSICAL_ADDRESS     TemporaryMemoryBase,
+  IN EFI_PHYSICAL_ADDRESS     PermanentMemoryBase,
+  IN UINTN                    CopySize
+  );
+
+/**
+  Entry point to the C language phase of SEC. After the SEC assembly
+  code has initialized some temporary memory and set up the stack,
+  the control is transferred to this function.
+
+  @param SizeOfRam           Size of the temporary memory available for use.
+  @param TempRamBase         Base address of temporary ram
+  @param BootFirmwareVolume  Base address of the Boot Firmware Volume.
+  @param BootloaderParameter A parameter from bootloader, e.g. HobList from SlimBootloader
+
+**/
+VOID
+EFIAPI
+SecStartup (
+  IN UINT32                   SizeOfRam,
+  IN UINT32                   TempRamBase,
+  IN VOID                     *BootFirmwareVolume,
+  IN UINT32                   BootloaderParameter
+  );
+
+/**
+  Find and return Pei Core entry point.
+
+  It also find SEC and PEI Core file debug information. It will report them if
+  remote debug is enabled.
+
+  @param  BootFirmwareVolumePtr  Point to the boot firmware volume.
+  @param  PeiCoreEntryPoint      Point to the PEI core entry point.
+
+**/
+VOID
+EFIAPI
+FindAndReportEntryPoints (
+  IN  EFI_FIRMWARE_VOLUME_HEADER       *BootFirmwareVolumePtr,
+  OUT EFI_PEI_CORE_ENTRY_POINT         *PeiCoreEntryPoint
+  );
+
+/**
+  Autogenerated function that calls the library constructors for all of the module's
+  dependent libraries.  This function must be called by the SEC Core once a stack has
+  been established.
+
+**/
+VOID
+EFIAPI
+ProcessLibraryConstructorList (
+  VOID
+  );
+
+#endif
diff --git a/UefiPayloadPkg/UefiPayloadPkg.dec b/UefiPayloadPkg/UefiPayloadPkg.dec
new file mode 100644
index 0000000000..38f476bc3e
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkg.dec
@@ -0,0 +1,78 @@
+## @file
+# UEFI Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# This program and the accompanying materials are licensed and made available under
+# the terms and conditions of the BSD License that accompanies this distribution.
+# The full text of the license may be found at
+# http://opensource.org/licenses/bsd-license.php.
+#
+# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+[Defines]
+  DEC_SPECIFICATION              = 0x00010005
+  PACKAGE_NAME                   = UefiPayloadPkg
+  PACKAGE_GUID                   = E0FC9D50-415E-4946-B686-9A130D5859E7
+  PACKAGE_VERSION                = 0.1
+
+[Includes]
+  Include
+
+
+[Guids]
+  #
+  ## Defines the token space for the UEFI Payload Package PCDs.
+  #
+  gUefiPayloadPkgTokenSpaceGuid  = {0x1d127ea, 0xf6f1, 0x4ef6, {0x94, 0x15, 0x8a, 0x0, 0x0, 0x93, 0xf8, 0x9d}}
+
+  #
+  # Gop Temp
+  #
+  gBmpImageGuid                           = { 0x878AC2CC, 0x5343, 0x46F2, { 0xB5, 0x63, 0x51, 0xF8, 0x9D, 0xAF, 0x56, 0xBA } }
+
+  gUefiSystemTableInfoGuid = {0x16c8a6d0, 0xfe8a, 0x4082, {0xa2, 0x8, 0xcf, 0x89, 0xc4, 0x29, 0x4, 0x33}}
+  gUefiFrameBufferInfoGuid = {0xdc2cd8bd, 0x402c, 0x4dc4, {0x9b, 0xe0, 0xc, 0x43, 0x2b, 0x7, 0xfa, 0x34}}
+  gUefiAcpiBoardInfoGuid   = {0xad3d31b, 0xb3d8, 0x4506, {0xae, 0x71, 0x2e, 0xf1, 0x10, 0x6, 0xd9, 0xf}}
+  gUefiSerialPortInfoGuid  = { 0x6c6872fe, 0x56a9, 0x4403, { 0xbb, 0x98, 0x95, 0x8d, 0x62, 0xde, 0x87, 0xf1 } }
+  gLoaderMemoryMapInfoGuid = { 0xa1ff7424, 0x7a1a, 0x478e, { 0xa9, 0xe4, 0x92, 0xf3, 0x57, 0xd1, 0x28, 0x32 } }
+
+[Ppis]
+  gEfiPayLoadHobBasePpiGuid = { 0xdbe23aa1, 0xa342, 0x4b97, {0x85, 0xb6, 0xb2, 0x26, 0xf1, 0x61, 0x73, 0x89} }
+
+[Protocols]
+  #
+  # Gop Temp
+  #
+  gPlatformGOPPolicyGuid                  = { 0xec2e931b, 0x3281, 0x48a5, { 0x81, 0x07, 0xdf, 0x8a, 0x8b, 0xed, 0x3c, 0x5d } }
+
+################################################################################
+#
+# PCD Declarations section - list of all PCDs Declared by this Package
+#                            Only this package should be providing the
+#                            declaration, other packages should not.
+#
+################################################################################
+[PcdsFixedAtBuild, PcdsPatchableInModule]
+## Indicates the base address of the payload binary in memory
+gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase|0|UINT32|0x10000001
+## Provides the size of the payload binary in memory
+gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize|0|UINT32|0x10000002
+## Payload stack top
+gUefiPayloadPkgTokenSpaceGuid.PcdPayloadStackTop|0x90000|UINT32|0x10000004
+
+## FFS filename to find the shell application.
+gUefiPayloadPkgTokenSpaceGuid.PcdShellFile|{ 0x83, 0xA5, 0x04, 0x7C, 0x3E, 0x9E, 0x1c, 0x4f, 0xAD, 0x65, 0xE0, 0x52, 0x68, 0xD0, 0xB4, 0xD1 }|VOID*|0x10000005
+
+## Used to help reduce fragmentation in the EFI memory map
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIReclaimMemory|0x08|UINT32|0x10000012
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiACPIMemoryNVS|0x04|UINT32|0x10000013
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiReservedMemoryType|0x04|UINT32|0x00000014
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesData|0xC0|UINT32|0x00000015
+gUefiPayloadPkgTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesCode|0x80|UINT32|0x00000016
+
+
diff --git a/UefiPayloadPkg/UefiPayloadPkg.fdf b/UefiPayloadPkg/UefiPayloadPkg.fdf
new file mode 100644
index 0000000000..0cf2921398
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkg.fdf
@@ -0,0 +1,297 @@
+## @file
+# Bootloader Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# This program and the accompanying materials are licensed and made available under
+# the terms and conditions of the BSD License that accompanies this distribution.
+# The full text of the license may be found at
+# http://opensource.org/licenses/bsd-license.php.
+#
+# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+################################################################################
+[FD.UefiPayload]
+BaseAddress   = 0x800000|gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemBase
+Size          = 0x410000|gUefiPayloadPkgTokenSpaceGuid.PcdPayloadFdMemSize
+ErasePolarity = 1
+BlockSize     = 0x1000
+NumBlocks     = 0x410
+
+0x00000000|0x030000
+FV = PEIFV
+
+0x00030000|0x3E0000
+FV = DXEFV
+
+################################################################################
+[FV.PEIFV]
+BlockSize          = 0x1000
+FvAlignment        = 16
+ERASE_POLARITY     = 1
+MEMORY_MAPPED      = TRUE
+STICKY_WRITE       = TRUE
+LOCK_CAP           = TRUE
+LOCK_STATUS        = TRUE
+WRITE_DISABLED_CAP = TRUE
+WRITE_ENABLED_CAP  = TRUE
+WRITE_STATUS       = TRUE
+WRITE_LOCK_CAP     = TRUE
+WRITE_LOCK_STATUS  = TRUE
+READ_DISABLED_CAP  = TRUE
+READ_ENABLED_CAP   = TRUE
+READ_STATUS        = TRUE
+READ_LOCK_CAP      = TRUE
+READ_LOCK_STATUS   = TRUE
+
+INF UefiPayloadPkg/SecCore/SecCore.inf
+
+INF MdeModulePkg/Core/Pei/PeiMain.inf
+INF MdeModulePkg/Universal/PCD/Pei/Pcd.inf
+INF MdeModulePkg/Universal/ReportStatusCodeRouter/Pei/ReportStatusCodeRouterPei.inf
+INF MdeModulePkg/Universal/StatusCodeHandler/Pei/StatusCodeHandlerPei.inf
+INF UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
+INF MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf
+
+################################################################################
+
+[FV.DXEFV]
+BlockSize          = 0x1000
+FvForceRebase      = FALSE
+FvAlignment        = 16
+ERASE_POLARITY     = 1
+MEMORY_MAPPED      = TRUE
+STICKY_WRITE       = TRUE
+LOCK_CAP           = TRUE
+LOCK_STATUS        = TRUE
+WRITE_DISABLED_CAP = TRUE
+WRITE_ENABLED_CAP  = TRUE
+WRITE_STATUS       = TRUE
+WRITE_LOCK_CAP     = TRUE
+WRITE_LOCK_STATUS  = TRUE
+READ_DISABLED_CAP  = TRUE
+READ_ENABLED_CAP   = TRUE
+READ_STATUS        = TRUE
+READ_LOCK_CAP      = TRUE
+READ_LOCK_STATUS   = TRUE
+
+APRIORI DXE {
+  INF  MdeModulePkg/Universal/PCD/Dxe/Pcd.inf
+  INF  MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+  INF  MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+}
+
+#
+# DXE Phase modules
+#
+INF MdeModulePkg/Core/Dxe/DxeMain.inf
+INF MdeModulePkg/Universal/PCD/Dxe/Pcd.inf
+INF MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+INF MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+
+INF MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf
+INF UefiCpuPkg/CpuDxe/CpuDxe.inf
+INF MdeModulePkg/Universal/BdsDxe/BdsDxe.inf
+INF MdeModulePkg/Application/UiApp/UiApp.inf
+INF PcAtChipsetPkg/HpetTimerDxe/HpetTimerDxe.inf
+INF MdeModulePkg/Universal/Metronome/Metronome.inf
+INF MdeModulePkg/Universal/WatchdogTimerDxe/WatchdogTimer.inf
+INF MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf
+INF MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
+INF MdeModulePkg/Universal/MonotonicCounterRuntimeDxe/MonotonicCounterRuntimeDxe.inf
+INF MdeModulePkg/Universal/ResetSystemRuntimeDxe/ResetSystemRuntimeDxe.inf
+INF PcAtChipsetPkg/PcatRealTimeClockRuntimeDxe/PcatRealTimeClockRuntimeDxe.inf
+INF MdeModulePkg/Universal/Variable/RuntimeDxe/VariableRuntimeDxe.inf
+
+INF UefiCpuPkg/CpuIo2Dxe/CpuIo2Dxe.inf
+INF MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf
+INF MdeModulePkg/Universal/MemoryTest/NullMemoryTestDxe/NullMemoryTestDxe.inf
+INF PcAtChipsetPkg/8259InterruptControllerDxe/8259.inf
+INF MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf
+INF MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf
+INF MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf
+INF UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
+
+INF MdeModulePkg/Universal/SmbiosDxe/SmbiosDxe.inf
+#
+# PCI Support
+#
+INF MdeModulePkg/Bus/Pci/PciBusDxe/PciBusDxe.inf
+INF MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf
+
+#
+# ISA Support
+#
+INF MdeModulePkg/Universal/SerialDxe/SerialDxe.inf
+
+#
+# Console Support
+#
+INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
+INF MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf
+INF MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf
+INF MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf
+
+#
+# SCSI/ATA/IDE/DISK Support
+#
+INF MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf
+INF MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf
+INF MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf
+INF MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf
+INF MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf
+INF MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf
+INF MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf
+INF MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf
+
+INF FatPkg/EnhancedFatDxe/Fat.inf
+
+#
+# SD/eMMC Support
+#
+INF MdeModulePkg/Bus/Pci/SdMmcPciHcDxe/SdMmcPciHcDxe.inf
+INF MdeModulePkg/Bus/Sd/EmmcDxe/EmmcDxe.inf
+INF MdeModulePkg/Bus/Sd/SdDxe/SdDxe.inf
+
+#
+# Usb Support
+#
+INF MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf
+INF MdeModulePkg/Bus/Pci/EhciDxe/EhciDxe.inf
+INF MdeModulePkg/Bus/Pci/XhciDxe/XhciDxe.inf
+INF MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBusDxe.inf
+INF MdeModulePkg/Bus/Usb/UsbKbDxe/UsbKbDxe.inf
+INF MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassStorageDxe.inf
+
+
+#
+# Shell
+#
+!if $(SHELL_TYPE) == BUILD_SHELL
+INF ShellPkg/DynamicCommand/TftpDynamicCommand/TftpDynamicCommand.inf
+INF ShellPkg/DynamicCommand/DpDynamicCommand/DpDynamicCommand.inf
+INF ShellPkg/Application/Shell/Shell.inf
+!endif
+
+!if $(SHELL_TYPE) == MIN_BIN
+!if $(ARCH) == IA32
+INF  RuleOverride = BINARY USE = IA32 ShellBinPkg/MinUefiShell/MinUefiShell.inf
+!else
+INF  RuleOverride = BINARY USE = X64 ShellBinPkg/MinUefiShell/MinUefiShell.inf
+!endif
+!endif
+
+!if $(SHELL_TYPE) == UEFI_BIN
+!if $(ARCH) == IA32
+INF  RuleOverride = BINARY USE = IA32 ShellBinPkg/UefiShell/UefiShell.inf
+!else
+INF  RuleOverride = BINARY USE = X64 ShellBinPkg/UefiShell/UefiShell.inf
+!endif
+!endif
+
+#
+# Framebuffer Gop
+#
+INF UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
+
+################################################################################
+#
+# Rules are use with the [FV] section's module INF type to define
+# how an FFS file is created for a given INF file. The following Rule are the default
+# rules for the different module type. User can add the customized rules to define the
+# content of the FFS file.
+#
+################################################################################
+
+[Rule.Common.SEC]
+  FILE SEC = $(NAMED_GUID) {
+    PE32     PE32   Align=32    $(INF_OUTPUT)/$(MODULE_NAME).efi
+  }
+
+[Rule.Common.PEI_CORE]
+  FILE PEI_CORE = $(NAMED_GUID) {
+    PE32     PE32   Align=Auto    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING ="$(MODULE_NAME)" Optional
+    VERSION  STRING ="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.PEIM]
+  FILE PEIM = $(NAMED_GUID) {
+     PEI_DEPEX PEI_DEPEX Optional        $(INF_OUTPUT)/$(MODULE_NAME).depex
+     PE32      PE32   Align=Auto           $(INF_OUTPUT)/$(MODULE_NAME).efi
+     UI       STRING="$(MODULE_NAME)" Optional
+     VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.DXE_CORE]
+  FILE DXE_CORE = $(NAMED_GUID) {
+    PE32     PE32           $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.DXE_DRIVER]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX    DXE_DEPEX Optional      $(INF_OUTPUT)/$(MODULE_NAME).depex
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.DXE_RUNTIME_DRIVER]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX    DXE_DEPEX Optional      $(INF_OUTPUT)/$(MODULE_NAME).depex
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_DRIVER]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX    DXE_DEPEX Optional      $(INF_OUTPUT)/$(MODULE_NAME).depex
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_DRIVER.BINARY]
+  FILE DRIVER = $(NAMED_GUID) {
+    DXE_DEPEX DXE_DEPEX Optional      |.depex
+    PE32      PE32                    |.efi
+    UI        STRING="$(MODULE_NAME)" Optional
+    VERSION   STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_APPLICATION]
+  FILE APPLICATION = $(NAMED_GUID) {
+    PE32     PE32                    $(INF_OUTPUT)/$(MODULE_NAME).efi
+    UI       STRING="$(MODULE_NAME)" Optional
+    VERSION  STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.UEFI_APPLICATION.BINARY]
+  FILE APPLICATION = $(NAMED_GUID) {
+    PE32      PE32                    |.efi
+    UI        STRING="$(MODULE_NAME)" Optional
+    VERSION   STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER)
+  }
+
+[Rule.Common.USER_DEFINED.ACPITABLE]
+  FILE FREEFORM = $(NAMED_GUID) {
+    RAW ACPI               |.acpi
+    RAW ASL                |.aml
+  }
+
+[Rule.Common.USER_DEFINED.CSM]
+  FILE FREEFORM = $(NAMED_GUID) {
+    RAW BIN                |.bin
+  }
+
+[Rule.Common.SEC.RESET_VECTOR]
+  FILE RAW = $(NAMED_GUID) {
+    RAW RAW                |.raw
+  }
diff --git a/UefiPayloadPkg/UefiPayloadPkgIa32.dsc b/UefiPayloadPkg/UefiPayloadPkgIa32.dsc
new file mode 100644
index 0000000000..4fe7e0f552
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkgIa32.dsc
@@ -0,0 +1,579 @@
+## @file
+# Bootloader Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# This program and the accompanying materials are licensed and made available under
+# the terms and conditions of the BSD License that accompanies this distribution.
+# The full text of the license may be found at
+# http://opensource.org/licenses/bsd-license.php.
+#
+# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+################################################################################
+#
+# Defines Section - statements that will be processed to create a Makefile.
+#
+################################################################################
+[Defines]
+  PLATFORM_NAME                       = UefiPayloadPkg
+  PLATFORM_GUID                       = F71608AB-D63D-4491-B744-A99998C8CD96
+  PLATFORM_VERSION                    = 0.1
+  DSC_SPECIFICATION                   = 0x00010005
+  SUPPORTED_ARCHITECTURES             = IA32
+  BUILD_TARGETS                       = DEBUG|RELEASE|NOOPT
+  SKUID_IDENTIFIER                    = DEFAULT
+  OUTPUT_DIRECTORY                    = Build/UefiPayloadPkgIA32
+  FLASH_DEFINITION                    = UefiPayloadPkg/UefiPayloadPkg.fdf
+
+  DEFINE SOURCE_DEBUG_ENABLE          = FALSE
+
+  #
+  # SBL:      UEFI payload for Slim Bootloader
+  # COREBOOT: UEFI payload for coreboot
+  #
+  DEFINE   BOOTLOADER = SBL
+
+  #
+  # CPU options
+  #
+  DEFINE MAX_LOGICAL_PROCESSORS       = 64
+
+  #
+  # PCI options
+  #
+  DEFINE PCIE_BASE                    = 0xE0000000
+
+  #
+  # Serial port set up
+  #
+  DEFINE BAUD_RATE                    = 115200
+  DEFINE SERIAL_CLOCK_RATE            = 1843200
+  DEFINE SERIAL_LINE_CONTROL          = 3 # 8-bits, no parity
+  DEFINE SERIAL_HARDWARE_FLOW_CONTROL = FALSE
+  DEFINE SERIAL_DETECT_CABLE          = FALSE
+  DEFINE SERIAL_FIFO_CONTROL          = 7 # Enable FIFO
+  DEFINE SERIAL_EXTENDED_TX_FIFO_SIZE = 16
+  DEFINE UART_DEFAULT_BAUD_RATE       = $(BAUD_RATE)
+  DEFINE UART_DEFAULT_DATA_BITS       = 8
+  DEFINE UART_DEFAULT_PARITY          = 1
+  DEFINE UART_DEFAULT_STOP_BITS       = 1
+  DEFINE DEFAULT_TERMINAL_TYPE        = 0
+
+  #
+  #  typedef struct {
+  #    UINT16  VendorId;          ///< Vendor ID to match the PCI device.  The value 0xFFFF terminates the list of entries.
+  #    UINT16  DeviceId;          ///< Device ID to match the PCI device
+  #    UINT32  ClockRate;         ///< UART clock rate.  Set to 0 for default clock rate of 1843200 Hz
+  #    UINT64  Offset;            ///< The byte offset into to the BAR
+  #    UINT8   BarIndex;          ///< Which BAR to get the UART base address
+  #    UINT8   RegisterStride;    ///< UART register stride in bytes.  Set to 0 for default register stride of 1 byte.
+  #    UINT16  ReceiveFifoDepth;  ///< UART receive FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT16  TransmitFifoDepth; ///< UART transmit FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT8   Reserved[2];
+  #  } PCI_SERIAL_PARAMETER;
+  #
+  # Vendor FFFF Device 0000 Prog Interface 1, BAR #0, Offset 0, Stride = 1, Clock 1843200 (0x1c2000)
+  #
+  #                                       [Vendor]   [Device]  [----ClockRate---]  [------------Offset-----------] [Bar] [Stride] [RxFifo] [TxFifo]   [Rsvd]   [Vendor]
+  DEFINE PCI_SERIAL_PARAMETERS        = {0xff,0xff, 0x00,0x00, 0x0,0x20,0x1c,0x00, 0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0, 0x00,    0x01, 0x0,0x0, 0x0,0x0, 0x0,0x0, 0xff,0xff}
+
+  #
+  # Shell options: [BUILD_SHELL, MIN_BIN, NONE, UEFI_BIN]
+  #
+  DEFINE SHELL_TYPE                   = BUILD_SHELL
+
+[BuildOptions]
+  *_*_*_CC_FLAGS                 = -D DISABLE_NEW_DEPRECATED_INTERFACES
+  GCC:*_UNIXGCC_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  GCC:RELEASE_*_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  INTEL:RELEASE_*_*_CC_FLAGS     = /D MDEPKG_NDEBUG
+  MSFT:RELEASE_*_*_CC_FLAGS      = /D MDEPKG_NDEBUG
+
+
+################################################################################
+#
+# SKU Identification section - list of all SKU IDs supported by this Platform.
+#
+################################################################################
+[SkuIds]
+  0|DEFAULT
+
+################################################################################
+#
+# Library Class section - list of all Library Classes needed by this Platform.
+#
+################################################################################
+[LibraryClasses]
+  #
+  # Entry point
+  #
+  PeiCoreEntryPoint|MdePkg/Library/PeiCoreEntryPoint/PeiCoreEntryPoint.inf
+  PeimEntryPoint|MdePkg/Library/PeimEntryPoint/PeimEntryPoint.inf
+  DxeCoreEntryPoint|MdePkg/Library/DxeCoreEntryPoint/DxeCoreEntryPoint.inf
+  UefiDriverEntryPoint|MdePkg/Library/UefiDriverEntryPoint/UefiDriverEntryPoint.inf
+  UefiApplicationEntryPoint|MdePkg/Library/UefiApplicationEntryPoint/UefiApplicationEntryPoint.inf
+
+  #
+  # Basic
+  #
+  BaseLib|MdePkg/Library/BaseLib/BaseLib.inf
+  BaseMemoryLib|MdePkg/Library/BaseMemoryLibRepStr/BaseMemoryLibRepStr.inf
+  SynchronizationLib|MdePkg/Library/BaseSynchronizationLib/BaseSynchronizationLib.inf
+  PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf
+  CpuLib|MdePkg/Library/BaseCpuLib/BaseCpuLib.inf
+  IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf
+!if $(PCIE_BASE) == 0
+  PciLib|MdePkg/Library/BasePciLibCf8/BasePciLibCf8.inf
+  PciCf8Lib|MdePkg/Library/BasePciCf8Lib/BasePciCf8Lib.inf
+!else
+  PciLib|MdePkg/Library/BasePciLibPciExpress/BasePciLibPciExpress.inf
+  PciExpressLib|MdePkg/Library/BasePciExpressLib/BasePciExpressLib.inf
+!endif
+  PciSegmentLib|MdePkg/Library/BasePciSegmentLibPci/BasePciSegmentLibPci.inf
+  PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf
+  PeCoffGetEntryPointLib|MdePkg/Library/BasePeCoffGetEntryPointLib/BasePeCoffGetEntryPointLib.inf
+  CacheMaintenanceLib|MdePkg/Library/BaseCacheMaintenanceLib/BaseCacheMaintenanceLib.inf
+
+  #
+  # UEFI & PI
+  #
+  UefiBootServicesTableLib|MdePkg/Library/UefiBootServicesTableLib/UefiBootServicesTableLib.inf
+  UefiRuntimeServicesTableLib|MdePkg/Library/UefiRuntimeServicesTableLib/UefiRuntimeServicesTableLib.inf
+  UefiRuntimeLib|MdePkg/Library/UefiRuntimeLib/UefiRuntimeLib.inf
+  UefiLib|MdePkg/Library/UefiLib/UefiLib.inf
+  UefiHiiServicesLib|MdeModulePkg/Library/UefiHiiServicesLib/UefiHiiServicesLib.inf
+  HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  UefiDecompressLib|MdePkg/Library/BaseUefiDecompressLib/BaseUefiDecompressLib.inf
+  PeiServicesTablePointerLib|MdePkg/Library/PeiServicesTablePointerLibIdt/PeiServicesTablePointerLibIdt.inf
+  PeiServicesLib|MdePkg/Library/PeiServicesLib/PeiServicesLib.inf
+  DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf
+  DxeServicesTableLib|MdePkg/Library/DxeServicesTableLib/DxeServicesTableLib.inf
+  UefiCpuLib|UefiCpuPkg/Library/BaseUefiCpuLib/BaseUefiCpuLib.inf
+  SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+
+  #
+  # Generic Modules
+  #
+  UefiUsbLib|MdePkg/Library/UefiUsbLib/UefiUsbLib.inf
+  UefiScsiLib|MdePkg/Library/UefiScsiLib/UefiScsiLib.inf
+  OemHookStatusCodeLib|MdeModulePkg/Library/OemHookStatusCodeLibNull/OemHookStatusCodeLibNull.inf
+  CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf
+  SecurityManagementLib|MdeModulePkg/Library/DxeSecurityManagementLib/DxeSecurityManagementLib.inf
+  UefiBootManagerLib|MdeModulePkg/Library/UefiBootManagerLib/UefiBootManagerLib.inf
+  CustomizedDisplayLib|MdeModulePkg/Library/CustomizedDisplayLib/CustomizedDisplayLib.inf
+  FrameBufferBltLib|MdeModulePkg/Library/FrameBufferBltLib/FrameBufferBltLib.inf
+
+  #
+  # CPU
+  #
+  MtrrLib|UefiCpuPkg/Library/MtrrLib/MtrrLib.inf
+  LocalApicLib|UefiCpuPkg/Library/BaseXApicX2ApicLib/BaseXApicX2ApicLib.inf
+
+  #
+  # Platform
+  #
+  TimerLib|UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
+  ResetSystemLib|UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
+  SerialPortLib|MdeModulePkg/Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf
+  PlatformHookLib|UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
+  PlatformBootManagerLib|UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
+  IoApicLib|PcAtChipsetPkg/Library/BaseIoApicLib/BaseIoApicLib.inf
+
+  #
+  # Misc
+  #
+  DebugPrintErrorLevelLib|MdePkg/Library/BaseDebugPrintErrorLevelLib/BaseDebugPrintErrorLevelLib.inf
+  PerformanceLib|MdePkg/Library/BasePerformanceLibNull/BasePerformanceLibNull.inf
+!if $(SOURCE_DEBUG_ENABLE) == TRUE
+  PeCoffExtraActionLib|SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLibDebug.inf
+  DebugCommunicationLib|SourceLevelDebugPkg/Library/DebugCommunicationLibSerialPort/DebugCommunicationLibSerialPort.inf
+!else
+  PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+!endif
+  PlatformSupportLib|UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
+!if $(BOOTLOADER) == "COREBOOT"
+  BlParseLib|UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
+!else
+  BlParseLib|UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
+!endif
+
+  DebugLib|MdePkg/Library/BaseDebugLibSerialPort/BaseDebugLibSerialPort.inf
+  LockBoxLib|MdeModulePkg/Library/LockBoxNullLib/LockBoxNullLib.inf
+  FileExplorerLib|MdeModulePkg/Library/FileExplorerLib/FileExplorerLib.inf
+  AuthVariableLib|MdeModulePkg/Library/AuthVariableLibNull/AuthVariableLibNull.inf
+  TpmMeasurementLib|MdeModulePkg/Library/TpmMeasurementLibNull/TpmMeasurementLibNull.inf
+  VarCheckLib|MdeModulePkg/Library/VarCheckLib/VarCheckLib.inf
+
+[LibraryClasses.IA32.SEC]
+  DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+  ReportStatusCodeLib|MdePkg/Library/BaseReportStatusCodeLibNull/BaseReportStatusCodeLibNull.inf
+
+[LibraryClasses.IA32.PEI_CORE, LibraryClasses.IA32.PEIM]
+  PcdLib|MdePkg/Library/PeiPcdLib/PeiPcdLib.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/PeiReportStatusCodeLib/PeiReportStatusCodeLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/PeiExtractGuidedSectionLib/PeiExtractGuidedSectionLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf
+!endif
+
+[LibraryClasses.common.DXE_CORE]
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/DxeCoreHobLib/DxeCoreHobLib.inf
+  MemoryAllocationLib|MdeModulePkg/Library/DxeCoreMemoryAllocationLib/DxeCoreMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+
+[LibraryClasses.common.DXE_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+  MpInitLib|UefiCpuPkg/Library/MpInitLib/DxeMpInitLib.inf
+
+[LibraryClasses.common.DXE_RUNTIME_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/RuntimeDxeReportStatusCodeLib/RuntimeDxeReportStatusCodeLib.inf
+
+[LibraryClasses.common.UEFI_DRIVER,LibraryClasses.common.UEFI_APPLICATION]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+
+################################################################################
+#
+# Pcd Section - list of all EDK II PCD Entries defined by this Platform.
+#
+################################################################################
+[PcdsFeatureFlag]
+!if $(TARGET) == DEBUG
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|TRUE
+!else
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|FALSE
+!endif
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseMemory|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdDxeIplSwitchToLongMode|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutGopSupport|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutUgaSupport|FALSE
+
+[PcdsFixedAtBuild]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize|0x10000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize|0x8000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVariableStoreSize|0x10000
+  #
+  # Make VariableRuntimeDxe work at emulated non-volatile variable mode.
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvModeEnable|TRUE
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVpdBaseAddress|0x0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdBootManagerMenuFile|{ 0x21, 0xaa, 0x2c, 0x46, 0x14, 0x76, 0x03, 0x45, 0x83, 0x6e, 0x8a, 0xb6, 0xf4, 0x66, 0x23, 0x31 }
+
+  gEfiMdePkgTokenSpaceGuid.PcdPciExpressBaseAddress|$(PCIE_BASE)
+
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiSourceLevelDebugPkgTokenSpaceGuid.PcdDebugLoadImageMethod|0x2
+!endif
+
+[PcdsPatchableInModule.common]
+  gEfiMdePkgTokenSpaceGuid.PcdReportStatusCodePropertyMask|0x7
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPrintErrorLevel|0x8000004F
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x17
+!else
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x2F
+!endif
+
+  #
+  # The following parameters are set by Library/PlatformHookLib
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase|0x3f8
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate|$(BAUD_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride|1
+
+  #
+  # Enable these parameters to be set on the command line
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate|$(SERIAL_CLOCK_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialLineControl|$(SERIAL_LINE_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseHardwareFlowControl|$(SERIAL_HARDWARE_FLOW_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialDetectCable|$(SERIAL_DETECT_CABLE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialFifoControl|$(SERIAL_FIFO_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialExtendedTxFifoSize|$(SERIAL_EXTENDED_TX_FIFO_SIZE)
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciDisableBusEnumeration|TRUE
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate|$(UART_DEFAULT_BAUD_RATE)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultDataBits|$(UART_DEFAULT_DATA_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultParity|$(UART_DEFAULT_PARITY)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultStopBits|$(UART_DEFAULT_STOP_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdDefaultTerminalType|$(DEFAULT_TERMINAL_TYPE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciSerialParameters|$(PCI_SERIAL_PARAMETERS)
+
+  gUefiCpuPkgTokenSpaceGuid.PcdCpuMaxLogicalProcessorNumber|$(MAX_LOGICAL_PROCESSORS)
+
+
+################################################################################
+#
+# Pcd Dynamic Section - list of all EDK II PCD Entries defined by this Platform
+#
+################################################################################
+
+[PcdsDynamicDefault]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvStoreReserved|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase|0
+  gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut|3
+
+  ## This PCD defines the video horizontal resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution|0
+  ## This PCD defines the video vertical resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution|0
+
+  ## The PCD is used to specify the video horizontal resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution|0
+  ## The PCD is used to specify the video vertical resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution|0
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow|31
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn|100
+
+################################################################################
+#
+# Components Section - list of all EDK II Modules needed by this Platform.
+#
+################################################################################
+[Components.IA32]
+  #
+  # SEC Core
+  #
+  UefiPayloadPkg/SecCore/SecCore.inf
+
+  #
+  # PEI Core
+  #
+  MdeModulePkg/Core/Pei/PeiMain.inf
+
+  #
+  # PEIM
+  #
+  MdeModulePkg/Universal/PCD/Pei/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+  MdeModulePkg/Universal/ReportStatusCodeRouter/Pei/ReportStatusCodeRouterPei.inf
+  MdeModulePkg/Universal/StatusCodeHandler/Pei/StatusCodeHandlerPei.inf
+
+  UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
+  MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf
+
+[Components.IA32]
+  #
+  # DXE Core
+  #
+  MdeModulePkg/Core/Dxe/DxeMain.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf
+  }
+
+  #
+  # Components that produce the architectural protocols
+  #
+  MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf
+  UefiCpuPkg/CpuDxe/CpuDxe.inf
+  MdeModulePkg/Universal/BdsDxe/BdsDxe.inf
+  MdeModulePkg/Application/UiApp/UiApp.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/DeviceManagerUiLib/DeviceManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootManagerUiLib/BootManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootMaintenanceManagerUiLib/BootMaintenanceManagerUiLib.inf
+  }
+
+  PcAtChipsetPkg/HpetTimerDxe/HpetTimerDxe.inf
+  MdeModulePkg/Universal/Metronome/Metronome.inf
+  MdeModulePkg/Universal/WatchdogTimerDxe/WatchdogTimer.inf
+  MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf
+  MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
+  MdeModulePkg/Universal/MonotonicCounterRuntimeDxe/MonotonicCounterRuntimeDxe.inf
+  MdeModulePkg/Universal/ResetSystemRuntimeDxe/ResetSystemRuntimeDxe.inf
+  PcAtChipsetPkg/PcatRealTimeClockRuntimeDxe/PcatRealTimeClockRuntimeDxe.inf
+  MdeModulePkg/Universal/Variable/RuntimeDxe/VariableRuntimeDxe.inf
+
+  #
+  # Following are the DXE drivers
+  #
+  MdeModulePkg/Universal/PCD/Dxe/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+
+  MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+  MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+  UefiCpuPkg/CpuIo2Dxe/CpuIo2Dxe.inf
+  MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf
+  MdeModulePkg/Universal/MemoryTest/NullMemoryTestDxe/NullMemoryTestDxe.inf
+  PcAtChipsetPkg/8259InterruptControllerDxe/8259.inf
+  MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf
+  MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf
+  MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf
+
+  UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
+
+  #
+  # SMBIOS Support
+  #
+  MdeModulePkg/Universal/SmbiosDxe/SmbiosDxe.inf
+
+  #
+  # ACPI Support
+  #
+  MdeModulePkg/Universal/Acpi/AcpiTableDxe/AcpiTableDxe.inf
+
+  #
+  # PCI Support
+  #
+  MdeModulePkg/Bus/Pci/PciBusDxe/PciBusDxe.inf
+  MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf {
+    <LibraryClasses>
+      PciHostBridgeLib|UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
+  }
+
+  #
+  # SCSI/ATA/IDE/DISK Support
+  #
+  MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf
+  MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf
+  MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf
+  FatPkg/EnhancedFatDxe/Fat.inf
+  MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf
+  MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf
+  MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf
+  MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf
+  MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf
+
+  #
+  # SD/eMMC Support
+  #
+  MdeModulePkg/Bus/Pci/SdMmcPciHcDxe/SdMmcPciHcDxe.inf
+  MdeModulePkg/Bus/Sd/EmmcDxe/EmmcDxe.inf
+  MdeModulePkg/Bus/Sd/SdDxe/SdDxe.inf
+
+  #
+  # Usb Support
+  #
+  MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf
+  MdeModulePkg/Bus/Pci/EhciDxe/EhciDxe.inf
+  MdeModulePkg/Bus/Pci/XhciDxe/XhciDxe.inf
+  MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBusDxe.inf
+  MdeModulePkg/Bus/Usb/UsbKbDxe/UsbKbDxe.inf
+  MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassStorageDxe.inf
+
+  #
+  # ISA Support
+  #
+  MdeModulePkg/Universal/SerialDxe/SerialDxe.inf
+
+  #
+  # Console Support
+  #
+  MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
+  MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf
+  MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf
+  MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf
+  UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
+
+  #------------------------------
+  #  Build the shell
+  #------------------------------
+
+!if $(SHELL_TYPE) == BUILD_SHELL
+
+  #
+  # Shell Lib
+  #
+[LibraryClasses]
+  BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  FileHandleLib|MdePkg/Library/UefiFileHandleLib/UefiFileHandleLib.inf
+  ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf
+  NetLib|MdeModulePkg/Library/DxeNetLib/DxeNetLib.inf
+
+[Components.IA32]
+  ShellPkg/DynamicCommand/TftpDynamicCommand/TftpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/DynamicCommand/DpDynamicCommand/DpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/Application/Shell/Shell.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the shell application itself only.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+
+    #------------------------------
+    #  Basic commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
+
+    #------------------------------
+    #  Networking commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
+
+    #------------------------------
+    #  Support libraries
+    #------------------------------
+
+    <LibraryClasses>
+      DebugLib|MdePkg/Library/UefiDebugLibConOut/UefiDebugLibConOut.inf
+      DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+      HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf
+      PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+      ShellCEntryLib|ShellPkg/Library/UefiShellCEntryLib/UefiShellCEntryLib.inf
+      ShellCommandLib|ShellPkg/Library/UefiShellCommandLib/UefiShellCommandLib.inf
+      SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+  }
+
+!endif
diff --git a/UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc b/UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc
new file mode 100644
index 0000000000..007d66e362
--- /dev/null
+++ b/UefiPayloadPkg/UefiPayloadPkgIa32X64.dsc
@@ -0,0 +1,580 @@
+## @file
+# Bootloader Payload Package
+#
+# Provides drivers and definitions to create uefi payload for bootloaders.
+#
+# Copyright (c) 2014 - 2019, Intel Corporation. All rights reserved.<BR>
+# This program and the accompanying materials are licensed and made available under
+# the terms and conditions of the BSD License that accompanies this distribution.
+# The full text of the license may be found at
+# http://opensource.org/licenses/bsd-license.php.
+#
+# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+#
+##
+
+################################################################################
+#
+# Defines Section - statements that will be processed to create a Makefile.
+#
+################################################################################
+[Defines]
+  PLATFORM_NAME                       = UefiPayloadPkg
+  PLATFORM_GUID                       = F71608AB-D63D-4491-B744-A99998C8CD96
+  PLATFORM_VERSION                    = 0.1
+  DSC_SPECIFICATION                   = 0x00010005
+  SUPPORTED_ARCHITECTURES             = IA32|X64
+  BUILD_TARGETS                       = DEBUG|RELEASE|NOOPT
+  SKUID_IDENTIFIER                    = DEFAULT
+  OUTPUT_DIRECTORY                    = Build/UefiPayloadPkgX64
+  FLASH_DEFINITION                    = UefiPayloadPkg/UefiPayloadPkg.fdf
+
+  DEFINE SOURCE_DEBUG_ENABLE          = FALSE
+
+  #
+  # SBL:      UEFI payload for Slim Bootloader
+  # COREBOOT: UEFI payload for coreboot
+  #
+  DEFINE   BOOTLOADER = SBL
+
+  #
+  # CPU options
+  #
+  DEFINE MAX_LOGICAL_PROCESSORS       = 64
+
+  #
+  # PCI options
+  #
+  DEFINE PCIE_BASE                    = 0xE0000000
+
+  #
+  # Serial port set up
+  #
+  DEFINE BAUD_RATE                    = 115200
+  DEFINE SERIAL_CLOCK_RATE            = 1843200
+  DEFINE SERIAL_LINE_CONTROL          = 3 # 8-bits, no parity
+  DEFINE SERIAL_HARDWARE_FLOW_CONTROL = FALSE
+  DEFINE SERIAL_DETECT_CABLE          = FALSE
+  DEFINE SERIAL_FIFO_CONTROL          = 7 # Enable FIFO
+  DEFINE SERIAL_EXTENDED_TX_FIFO_SIZE = 16
+  DEFINE UART_DEFAULT_BAUD_RATE       = $(BAUD_RATE)
+  DEFINE UART_DEFAULT_DATA_BITS       = 8
+  DEFINE UART_DEFAULT_PARITY          = 1
+  DEFINE UART_DEFAULT_STOP_BITS       = 1
+  DEFINE DEFAULT_TERMINAL_TYPE        = 0
+
+  #
+  #  typedef struct {
+  #    UINT16  VendorId;          ///< Vendor ID to match the PCI device.  The value 0xFFFF terminates the list of entries.
+  #    UINT16  DeviceId;          ///< Device ID to match the PCI device
+  #    UINT32  ClockRate;         ///< UART clock rate.  Set to 0 for default clock rate of 1843200 Hz
+  #    UINT64  Offset;            ///< The byte offset into to the BAR
+  #    UINT8   BarIndex;          ///< Which BAR to get the UART base address
+  #    UINT8   RegisterStride;    ///< UART register stride in bytes.  Set to 0 for default register stride of 1 byte.
+  #    UINT16  ReceiveFifoDepth;  ///< UART receive FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT16  TransmitFifoDepth; ///< UART transmit FIFO depth in bytes. Set to 0 for a default FIFO depth of 16 bytes.
+  #    UINT8   Reserved[2];
+  #  } PCI_SERIAL_PARAMETER;
+  #
+  # Vendor FFFF Device 0000 Prog Interface 1, BAR #0, Offset 0, Stride = 1, Clock 1843200 (0x1c2000)
+  #
+  #                                       [Vendor]   [Device]  [----ClockRate---]  [------------Offset-----------] [Bar] [Stride] [RxFifo] [TxFifo]   [Rsvd]   [Vendor]
+  DEFINE PCI_SERIAL_PARAMETERS        = {0xff,0xff, 0x00,0x00, 0x0,0x20,0x1c,0x00, 0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0, 0x00,    0x01, 0x0,0x0, 0x0,0x0, 0x0,0x0, 0xff,0xff}
+
+  #
+  # Shell options: [BUILD_SHELL, MIN_BIN, NONE, UEFI_BIN]
+  #
+  DEFINE SHELL_TYPE                   = BUILD_SHELL
+
+[BuildOptions]
+  *_*_*_CC_FLAGS                 = -D DISABLE_NEW_DEPRECATED_INTERFACES
+  GCC:*_UNIXGCC_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  GCC:RELEASE_*_*_CC_FLAGS       = -DMDEPKG_NDEBUG
+  INTEL:RELEASE_*_*_CC_FLAGS     = /D MDEPKG_NDEBUG
+  MSFT:RELEASE_*_*_CC_FLAGS      = /D MDEPKG_NDEBUG
+
+
+################################################################################
+#
+# SKU Identification section - list of all SKU IDs supported by this Platform.
+#
+################################################################################
+[SkuIds]
+  0|DEFAULT
+
+################################################################################
+#
+# Library Class section - list of all Library Classes needed by this Platform.
+#
+################################################################################
+[LibraryClasses]
+  #
+  # Entry point
+  #
+  PeiCoreEntryPoint|MdePkg/Library/PeiCoreEntryPoint/PeiCoreEntryPoint.inf
+  PeimEntryPoint|MdePkg/Library/PeimEntryPoint/PeimEntryPoint.inf
+  DxeCoreEntryPoint|MdePkg/Library/DxeCoreEntryPoint/DxeCoreEntryPoint.inf
+  UefiDriverEntryPoint|MdePkg/Library/UefiDriverEntryPoint/UefiDriverEntryPoint.inf
+  UefiApplicationEntryPoint|MdePkg/Library/UefiApplicationEntryPoint/UefiApplicationEntryPoint.inf
+
+  #
+  # Basic
+  #
+  BaseLib|MdePkg/Library/BaseLib/BaseLib.inf
+  BaseMemoryLib|MdePkg/Library/BaseMemoryLibRepStr/BaseMemoryLibRepStr.inf
+  SynchronizationLib|MdePkg/Library/BaseSynchronizationLib/BaseSynchronizationLib.inf
+  PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf
+  CpuLib|MdePkg/Library/BaseCpuLib/BaseCpuLib.inf
+  IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf
+!if $(PCIE_BASE) == 0
+  PciLib|MdePkg/Library/BasePciLibCf8/BasePciLibCf8.inf
+  PciCf8Lib|MdePkg/Library/BasePciCf8Lib/BasePciCf8Lib.inf
+!else
+  PciLib|MdePkg/Library/BasePciLibPciExpress/BasePciLibPciExpress.inf
+  PciExpressLib|MdePkg/Library/BasePciExpressLib/BasePciExpressLib.inf
+!endif
+  PciSegmentLib|MdePkg/Library/BasePciSegmentLibPci/BasePciSegmentLibPci.inf
+  PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf
+  PeCoffGetEntryPointLib|MdePkg/Library/BasePeCoffGetEntryPointLib/BasePeCoffGetEntryPointLib.inf
+  CacheMaintenanceLib|MdePkg/Library/BaseCacheMaintenanceLib/BaseCacheMaintenanceLib.inf
+
+  #
+  # UEFI & PI
+  #
+  UefiBootServicesTableLib|MdePkg/Library/UefiBootServicesTableLib/UefiBootServicesTableLib.inf
+  UefiRuntimeServicesTableLib|MdePkg/Library/UefiRuntimeServicesTableLib/UefiRuntimeServicesTableLib.inf
+  UefiRuntimeLib|MdePkg/Library/UefiRuntimeLib/UefiRuntimeLib.inf
+  UefiLib|MdePkg/Library/UefiLib/UefiLib.inf
+  UefiHiiServicesLib|MdeModulePkg/Library/UefiHiiServicesLib/UefiHiiServicesLib.inf
+  HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  UefiDecompressLib|MdePkg/Library/BaseUefiDecompressLib/BaseUefiDecompressLib.inf
+  PeiServicesTablePointerLib|MdePkg/Library/PeiServicesTablePointerLibIdt/PeiServicesTablePointerLibIdt.inf
+  PeiServicesLib|MdePkg/Library/PeiServicesLib/PeiServicesLib.inf
+  DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf
+  DxeServicesTableLib|MdePkg/Library/DxeServicesTableLib/DxeServicesTableLib.inf
+  UefiCpuLib|UefiCpuPkg/Library/BaseUefiCpuLib/BaseUefiCpuLib.inf
+  SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+
+  #
+  # Generic Modules
+  #
+  UefiUsbLib|MdePkg/Library/UefiUsbLib/UefiUsbLib.inf
+  UefiScsiLib|MdePkg/Library/UefiScsiLib/UefiScsiLib.inf
+  OemHookStatusCodeLib|MdeModulePkg/Library/OemHookStatusCodeLibNull/OemHookStatusCodeLibNull.inf
+  CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf
+  SecurityManagementLib|MdeModulePkg/Library/DxeSecurityManagementLib/DxeSecurityManagementLib.inf
+  UefiBootManagerLib|MdeModulePkg/Library/UefiBootManagerLib/UefiBootManagerLib.inf
+  CustomizedDisplayLib|MdeModulePkg/Library/CustomizedDisplayLib/CustomizedDisplayLib.inf
+  FrameBufferBltLib|MdeModulePkg/Library/FrameBufferBltLib/FrameBufferBltLib.inf
+
+  #
+  # CPU
+  #
+  MtrrLib|UefiCpuPkg/Library/MtrrLib/MtrrLib.inf
+  LocalApicLib|UefiCpuPkg/Library/BaseXApicX2ApicLib/BaseXApicX2ApicLib.inf
+
+  #
+  # Platform
+  #
+  TimerLib|UefiPayloadPkg/Library/AcpiTimerLib/AcpiTimerLib.inf
+  ResetSystemLib|UefiPayloadPkg/Library/ResetSystemLib/ResetSystemLib.inf
+  SerialPortLib|MdeModulePkg/Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf
+  PlatformHookLib|UefiPayloadPkg/Library/PlatformHookLib/PlatformHookLib.inf
+  PlatformBootManagerLib|UefiPayloadPkg/Library/PlatformBootManagerLib/PlatformBootManagerLib.inf
+  IoApicLib|PcAtChipsetPkg/Library/BaseIoApicLib/BaseIoApicLib.inf
+
+  #
+  # Misc
+  #
+  DebugPrintErrorLevelLib|MdePkg/Library/BaseDebugPrintErrorLevelLib/BaseDebugPrintErrorLevelLib.inf
+  PerformanceLib|MdePkg/Library/BasePerformanceLibNull/BasePerformanceLibNull.inf
+!if $(SOURCE_DEBUG_ENABLE) == TRUE
+  PeCoffExtraActionLib|SourceLevelDebugPkg/Library/PeCoffExtraActionLibDebug/PeCoffExtraActionLibDebug.inf
+  DebugCommunicationLib|SourceLevelDebugPkg/Library/DebugCommunicationLibSerialPort/DebugCommunicationLibSerialPort.inf
+!else
+  PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+!endif
+  PlatformSupportLib|UefiPayloadPkg/Library/PlatformSupportLibNull/PlatformSupportLibNull.inf
+!if $(BOOTLOADER) == "COREBOOT"
+  BlParseLib|UefiPayloadPkg/Library/CbParseLib/CbParseLib.inf
+!else
+  BlParseLib|UefiPayloadPkg/Library/SblParseLib/SblParseLib.inf
+!endif
+
+  DebugLib|MdePkg/Library/BaseDebugLibSerialPort/BaseDebugLibSerialPort.inf
+  LockBoxLib|MdeModulePkg/Library/LockBoxNullLib/LockBoxNullLib.inf
+  FileExplorerLib|MdeModulePkg/Library/FileExplorerLib/FileExplorerLib.inf
+  AuthVariableLib|MdeModulePkg/Library/AuthVariableLibNull/AuthVariableLibNull.inf
+  TpmMeasurementLib|MdeModulePkg/Library/TpmMeasurementLibNull/TpmMeasurementLibNull.inf
+  VarCheckLib|MdeModulePkg/Library/VarCheckLib/VarCheckLib.inf
+
+[LibraryClasses.IA32.SEC]
+  DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf
+  ReportStatusCodeLib|MdePkg/Library/BaseReportStatusCodeLibNull/BaseReportStatusCodeLibNull.inf
+
+[LibraryClasses.IA32.PEI_CORE, LibraryClasses.IA32.PEIM]
+  PcdLib|MdePkg/Library/PeiPcdLib/PeiPcdLib.inf
+  HobLib|MdePkg/Library/PeiHobLib/PeiHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/PeiMemoryAllocationLib/PeiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/PeiReportStatusCodeLib/PeiReportStatusCodeLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/PeiExtractGuidedSectionLib/PeiExtractGuidedSectionLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/SecPeiDebugAgentLib.inf
+!endif
+
+[LibraryClasses.common.DXE_CORE]
+  PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  HobLib|MdePkg/Library/DxeCoreHobLib/DxeCoreHobLib.inf
+  MemoryAllocationLib|MdeModulePkg/Library/DxeCoreMemoryAllocationLib/DxeCoreMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+
+[LibraryClasses.common.DXE_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+!if $(SOURCE_DEBUG_ENABLE)
+  DebugAgentLib|SourceLevelDebugPkg/Library/DebugAgent/DxeDebugAgentLib.inf
+!endif
+  CpuExceptionHandlerLib|UefiCpuPkg/Library/CpuExceptionHandlerLib/DxeCpuExceptionHandlerLib.inf
+  MpInitLib|UefiCpuPkg/Library/MpInitLib/DxeMpInitLib.inf
+
+[LibraryClasses.common.DXE_RUNTIME_DRIVER]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/RuntimeDxeReportStatusCodeLib/RuntimeDxeReportStatusCodeLib.inf
+
+[LibraryClasses.common.UEFI_DRIVER,LibraryClasses.common.UEFI_APPLICATION]
+  PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+  MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
+  ReportStatusCodeLib|MdeModulePkg/Library/DxeReportStatusCodeLib/DxeReportStatusCodeLib.inf
+  HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf
+
+################################################################################
+#
+# Pcd Section - list of all EDK II PCD Entries defined by this Platform.
+#
+################################################################################
+[PcdsFeatureFlag]
+!if $(TARGET) == DEBUG
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|TRUE
+!else
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|FALSE
+!endif
+  gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseMemory|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdDxeIplSwitchToLongMode|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutGopSupport|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutUgaSupport|FALSE
+
+[PcdsFixedAtBuild]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxVariableSize|0x10000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdMaxHardwareErrorVariableSize|0x8000
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVariableStoreSize|0x10000
+  #
+  # Make VariableRuntimeDxe work at emulated non-volatile variable mode.
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvModeEnable|TRUE
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVpdBaseAddress|0x0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdUse1GPageTable|TRUE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdBootManagerMenuFile|{ 0x21, 0xaa, 0x2c, 0x46, 0x14, 0x76, 0x03, 0x45, 0x83, 0x6e, 0x8a, 0xb6, 0xf4, 0x66, 0x23, 0x31 }
+
+  gEfiMdePkgTokenSpaceGuid.PcdPciExpressBaseAddress|$(PCIE_BASE)
+
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiSourceLevelDebugPkgTokenSpaceGuid.PcdDebugLoadImageMethod|0x2
+!endif
+
+[PcdsPatchableInModule.common]
+  gEfiMdePkgTokenSpaceGuid.PcdReportStatusCodePropertyMask|0x7
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPrintErrorLevel|0x8000004F
+!if $(SOURCE_DEBUG_ENABLE)
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x17
+!else
+  gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x2F
+!endif
+
+  #
+  # The following parameters are set by Library/PlatformHookLib
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio|FALSE
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase|0x3f8
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate|$(BAUD_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride|1
+
+  #
+  # Enable these parameters to be set on the command line
+  #
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate|$(SERIAL_CLOCK_RATE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialLineControl|$(SERIAL_LINE_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseHardwareFlowControl|$(SERIAL_HARDWARE_FLOW_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialDetectCable|$(SERIAL_DETECT_CABLE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialFifoControl|$(SERIAL_FIFO_CONTROL)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSerialExtendedTxFifoSize|$(SERIAL_EXTENDED_TX_FIFO_SIZE)
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciDisableBusEnumeration|TRUE
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate|$(UART_DEFAULT_BAUD_RATE)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultDataBits|$(UART_DEFAULT_DATA_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultParity|$(UART_DEFAULT_PARITY)
+  gEfiMdePkgTokenSpaceGuid.PcdUartDefaultStopBits|$(UART_DEFAULT_STOP_BITS)
+  gEfiMdePkgTokenSpaceGuid.PcdDefaultTerminalType|$(DEFAULT_TERMINAL_TYPE)
+  gEfiMdeModulePkgTokenSpaceGuid.PcdPciSerialParameters|$(PCI_SERIAL_PARAMETERS)
+
+  gUefiCpuPkgTokenSpaceGuid.PcdCpuMaxLogicalProcessorNumber|$(MAX_LOGICAL_PROCESSORS)
+
+
+################################################################################
+#
+# Pcd Dynamic Section - list of all EDK II PCD Entries defined by this Platform
+#
+################################################################################
+
+[PcdsDynamicDefault]
+  gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvStoreReserved|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageVariableBase64|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwWorkingBase|0
+  gEfiMdeModulePkgTokenSpaceGuid.PcdFlashNvStorageFtwSpareBase|0
+  gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut|3
+
+  ## This PCD defines the video horizontal resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoHorizontalResolution|0
+  ## This PCD defines the video vertical resolution.
+  #  This PCD could be set to 0 then video resolution could be at highest resolution.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdVideoVerticalResolution|0
+
+  ## The PCD is used to specify the video horizontal resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoHorizontalResolution|0
+  ## The PCD is used to specify the video vertical resolution of text setup.
+  gEfiMdeModulePkgTokenSpaceGuid.PcdSetupVideoVerticalResolution|0
+
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow|31
+  gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn|100
+
+################################################################################
+#
+# Components Section - list of all EDK II Modules needed by this Platform.
+#
+################################################################################
+[Components.IA32]
+  #
+  # SEC Core
+  #
+  UefiPayloadPkg/SecCore/SecCore.inf
+
+  #
+  # PEI Core
+  #
+  MdeModulePkg/Core/Pei/PeiMain.inf
+
+  #
+  # PEIM
+  #
+  MdeModulePkg/Universal/PCD/Pei/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+  MdeModulePkg/Universal/ReportStatusCodeRouter/Pei/ReportStatusCodeRouterPei.inf
+  MdeModulePkg/Universal/StatusCodeHandler/Pei/StatusCodeHandlerPei.inf
+
+  UefiPayloadPkg/BlSupportPei/BlSupportPei.inf
+  MdeModulePkg/Core/DxeIplPeim/DxeIpl.inf
+
+[Components.X64]
+  #
+  # DXE Core
+  #
+  MdeModulePkg/Core/Dxe/DxeMain.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf
+  }
+
+  #
+  # Components that produce the architectural protocols
+  #
+  MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf
+  UefiCpuPkg/CpuDxe/CpuDxe.inf
+  MdeModulePkg/Universal/BdsDxe/BdsDxe.inf
+  MdeModulePkg/Application/UiApp/UiApp.inf {
+    <LibraryClasses>
+      NULL|MdeModulePkg/Library/DeviceManagerUiLib/DeviceManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootManagerUiLib/BootManagerUiLib.inf
+      NULL|MdeModulePkg/Library/BootMaintenanceManagerUiLib/BootMaintenanceManagerUiLib.inf
+  }
+
+  PcAtChipsetPkg/HpetTimerDxe/HpetTimerDxe.inf
+  MdeModulePkg/Universal/Metronome/Metronome.inf
+  MdeModulePkg/Universal/WatchdogTimerDxe/WatchdogTimer.inf
+  MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf
+  MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
+  MdeModulePkg/Universal/MonotonicCounterRuntimeDxe/MonotonicCounterRuntimeDxe.inf
+  MdeModulePkg/Universal/ResetSystemRuntimeDxe/ResetSystemRuntimeDxe.inf
+  PcAtChipsetPkg/PcatRealTimeClockRuntimeDxe/PcatRealTimeClockRuntimeDxe.inf
+  MdeModulePkg/Universal/Variable/RuntimeDxe/VariableRuntimeDxe.inf
+
+  #
+  # Following are the DXE drivers
+  #
+  MdeModulePkg/Universal/PCD/Dxe/Pcd.inf {
+    <LibraryClasses>
+      PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
+  }
+
+  MdeModulePkg/Universal/ReportStatusCodeRouter/RuntimeDxe/ReportStatusCodeRouterRuntimeDxe.inf
+  MdeModulePkg/Universal/StatusCodeHandler/RuntimeDxe/StatusCodeHandlerRuntimeDxe.inf
+  UefiCpuPkg/CpuIo2Dxe/CpuIo2Dxe.inf
+  MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf
+  MdeModulePkg/Universal/MemoryTest/NullMemoryTestDxe/NullMemoryTestDxe.inf
+  PcAtChipsetPkg/8259InterruptControllerDxe/8259.inf
+  MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf
+  MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf
+  MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf
+
+  UefiPayloadPkg/BlSupportDxe/BlSupportDxe.inf
+
+  #
+  # SMBIOS Support
+  #
+  MdeModulePkg/Universal/SmbiosDxe/SmbiosDxe.inf
+
+  #
+  # ACPI Support
+  #
+  MdeModulePkg/Universal/Acpi/AcpiTableDxe/AcpiTableDxe.inf
+
+  #
+  # PCI Support
+  #
+  MdeModulePkg/Bus/Pci/PciBusDxe/PciBusDxe.inf
+  MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf {
+    <LibraryClasses>
+      PciHostBridgeLib|UefiPayloadPkg/Library/PciHostBridgeLib/PciHostBridgeLib.inf
+  }
+
+  #
+  # SCSI/ATA/IDE/DISK Support
+  #
+  MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf
+  MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf
+  MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf
+  FatPkg/EnhancedFatDxe/Fat.inf
+  MdeModulePkg/Bus/Pci/SataControllerDxe/SataControllerDxe.inf
+  MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBusDxe.inf
+  MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.inf
+  MdeModulePkg/Bus/Scsi/ScsiBusDxe/ScsiBusDxe.inf
+  MdeModulePkg/Bus/Scsi/ScsiDiskDxe/ScsiDiskDxe.inf
+
+  #
+  # SD/eMMC Support
+  #
+  MdeModulePkg/Bus/Pci/SdMmcPciHcDxe/SdMmcPciHcDxe.inf
+  MdeModulePkg/Bus/Sd/EmmcDxe/EmmcDxe.inf
+  MdeModulePkg/Bus/Sd/SdDxe/SdDxe.inf
+
+  #
+  # Usb Support
+  #
+  MdeModulePkg/Bus/Pci/UhciDxe/UhciDxe.inf
+  MdeModulePkg/Bus/Pci/EhciDxe/EhciDxe.inf
+  MdeModulePkg/Bus/Pci/XhciDxe/XhciDxe.inf
+  MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBusDxe.inf
+  MdeModulePkg/Bus/Usb/UsbKbDxe/UsbKbDxe.inf
+  MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassStorageDxe.inf
+
+  #
+  # ISA Support
+  #
+  MdeModulePkg/Universal/SerialDxe/SerialDxe.inf
+
+  #
+  # Console Support
+  #
+  MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
+  MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf
+  MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf
+  MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf
+  UefiPayloadPkg/GraphicsOutputDxe/GraphicsOutputDxe.inf
+
+  #------------------------------
+  #  Build the shell
+  #------------------------------
+
+!if $(SHELL_TYPE) == BUILD_SHELL
+
+  #
+  # Shell Lib
+  #
+[LibraryClasses]
+  BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
+  DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+  FileHandleLib|MdePkg/Library/UefiFileHandleLib/UefiFileHandleLib.inf
+  ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf
+  NetLib|MdeModulePkg/Library/DxeNetLib/DxeNetLib.inf
+
+[Components.X64]
+  ShellPkg/DynamicCommand/TftpDynamicCommand/TftpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/DynamicCommand/DpDynamicCommand/DpDynamicCommand.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the dynamic command.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+  }
+  ShellPkg/Application/Shell/Shell.inf {
+    <PcdsFixedAtBuild>
+      ## This flag is used to control initialization of the shell library
+      #  This should be FALSE for compiling the shell application itself only.
+      gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE
+
+    #------------------------------
+    #  Basic commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf
+      NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf
+
+    #------------------------------
+    #  Networking commands
+    #------------------------------
+
+    <LibraryClasses>
+      NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf
+
+    #------------------------------
+    #  Support libraries
+    #------------------------------
+
+    <LibraryClasses>
+      DebugLib|MdePkg/Library/UefiDebugLibConOut/UefiDebugLibConOut.inf
+      DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf
+      HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf
+      PcdLib|MdePkg/Library/DxePcdLib/DxePcdLib.inf
+      ShellCEntryLib|ShellPkg/Library/UefiShellCEntryLib/UefiShellCEntryLib.inf
+      ShellCommandLib|ShellPkg/Library/UefiShellCommandLib/UefiShellCommandLib.inf
+      SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf
+  }
+
+!endif
-- 
2.16.2.windows.1



^ permalink raw reply related	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2019-04-11 15:59 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2019-04-11 15:03 [PATCH] UefiPayloadPkg: Enhance UEFI payload for coreboot and Slim Bootloader Guo Dong
  -- strict thread matches above, loose matches on Subject: below --
2019-03-29  0:33 Guo Dong
2019-03-29  5:15 ` Ni, Ray
2019-03-29 15:07   ` Dong, Guo
2019-04-01 14:05   ` Laszlo Ersek
2019-04-02  1:53     ` Wu, Hao A
2019-04-03 14:13 ` Ma, Maurice
     [not found]   ` <734D49CCEBEEF84792F5B80ED585239D5C0E0C06@SHSMSX104.ccr.corp.intel.com>
2019-04-11 15:38     ` Ma, Maurice
2019-04-11 15:58       ` Guo Dong

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox