summaryrefslogtreecommitdiff
path: root/ReferenceCode/ME/Library
diff options
context:
space:
mode:
authorraywu <raywu0301@gmail.com>2018-06-15 00:00:50 +0800
committerraywu <raywu0301@gmail.com>2018-06-15 00:00:50 +0800
commitb7c51c9cf4864df6aabb99a1ae843becd577237c (patch)
treeeebe9b0d0ca03062955223097e57da84dd618b9a /ReferenceCode/ME/Library
downloadzprj-b7c51c9cf4864df6aabb99a1ae843becd577237c.tar.xz
init. 1AQQW051HEADmaster
Diffstat (limited to 'ReferenceCode/ME/Library')
-rw-r--r--ReferenceCode/ME/Library/AMT/AmtLibrary.cif11
-rw-r--r--ReferenceCode/ME/Library/AMT/AmtLibrary.sdl20
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtLib.c526
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtLib.h257
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtLib.inf75
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.cif16
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.mak54
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.sdl36
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyDebugDumpDxe.c115
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.c547
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.h298
-rw-r--r--ReferenceCode/ME/Library/AMT/Dxe/MebxSetupDebugDumpDxe.c75
-rw-r--r--ReferenceCode/ME/Library/AMT/Include/Amt.h59
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.cif13
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.h26
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.inf51
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.mak50
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.sdl36
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.c241
-rw-r--r--ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.h126
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/AtLibrary.cif10
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/AtLibrary.sdl20
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.c630
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.h119
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.cif14
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.inf69
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.mak54
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.sdl36
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyDebugDumpDxe.c51
-rw-r--r--ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyLib.h39
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.c112
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.cif11
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.inf61
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.mak53
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.sdl70
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.c2702
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.h782
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MbpDebugDumpDxe.c150
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.c712
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.h203
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.inf68
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.cif18
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.mak60
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.sdl36
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyDebugDumpDxe.c72
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.c182
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.h95
-rw-r--r--ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.cif12
-rw-r--r--ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.sdl20
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.c185
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.h86
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.cif15
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.h27
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.inf56
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.mak53
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.sdl36
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.c59
-rw-r--r--ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.h42
-rw-r--r--ReferenceCode/ME/Library/MeKernel/include/CoreBiosMsg.h625
-rw-r--r--ReferenceCode/ME/Library/MeKernel/include/MeAccess.h338
-rw-r--r--ReferenceCode/ME/Library/MeKernel/include/MeChipset.h196
-rw-r--r--ReferenceCode/ME/Library/MeKernel/include/MeChipsetLib.h54
-rw-r--r--ReferenceCode/ME/Library/MeKernel/include/MeState.h67
-rw-r--r--ReferenceCode/ME/Library/MeKernel/include/MkhiMsgs.h533
-rw-r--r--ReferenceCode/ME/Library/MeLibrary.cif22
-rw-r--r--ReferenceCode/ME/Library/MeLibrary.sdl32
-rw-r--r--ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.c606
-rw-r--r--ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.cif8
-rw-r--r--ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.cif9
-rw-r--r--ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.h37
-rw-r--r--ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.inf73
-rw-r--r--ReferenceCode/ME/Library/Ptt/Include/PttHciDeviceLib.h175
-rw-r--r--ReferenceCode/ME/Library/Ptt/Include/PttHciRegs.h100
-rw-r--r--ReferenceCode/ME/Library/Ptt/Include/PttLibInc.cif9
-rw-r--r--ReferenceCode/ME/Library/Ptt/Pei/PttHciDeviceLib.c590
-rw-r--r--ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.cif12
-rw-r--r--ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.h37
-rw-r--r--ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.inf71
-rw-r--r--ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.mak80
-rw-r--r--ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.sdl36
-rw-r--r--ReferenceCode/ME/Library/Ptt/PttLibrary.cif14
-rw-r--r--ReferenceCode/ME/Library/Ptt/PttLibrary.mak101
-rw-r--r--ReferenceCode/ME/Library/Ptt/PttLibrary.sdl59
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.c145
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.cif12
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.h37
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.inf68
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.mak40
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.sdl36
-rw-r--r--ReferenceCode/ME/Library/PttHeci/Include/PttHeciLib.h73
90 files changed, 13947 insertions, 0 deletions
diff --git a/ReferenceCode/ME/Library/AMT/AmtLibrary.cif b/ReferenceCode/ME/Library/AMT/AmtLibrary.cif
new file mode 100644
index 0000000..c5be1a2
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/AmtLibrary.cif
@@ -0,0 +1,11 @@
+<component>
+ name = "AmtLibrary"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\AMT\"
+ RefName = "AmtLibrary"
+[files]
+"AmtLibrary.sdl"
+[parts]
+"AmtLibDxe"
+"AmtLibPei"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/AMT/AmtLibrary.sdl b/ReferenceCode/ME/Library/AMT/AmtLibrary.sdl
new file mode 100644
index 0000000..0e43375
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/AmtLibrary.sdl
@@ -0,0 +1,20 @@
+TOKEN
+ Name = "AmtLibrary_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable AmtLibDxe support in Project"
+End
+
+PATH
+ Name = "AmtLibrary_DIR"
+ Help = "iAMT Library file source directory"
+End
+
+ELINK
+ Name = "/I$(AmtLibrary_DIR)\Include"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.c b/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.c
new file mode 100644
index 0000000..6b69b16
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.c
@@ -0,0 +1,526 @@
+/** @file
+ Implementation file for AMT functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+
+#include "EdkIIGlueDxe.h"
+#include "AmtLib.h"
+#include "MeLib.h"
+
+#include EFI_PROTOCOL_CONSUMER (Heci)
+#include EFI_PROTOCOL_CONSUMER (ActiveManagement)
+#include EFI_PROTOCOL_CONSUMER (AmtPlatformPolicy)
+#include EFI_GUID_DEFINITION (MeBiosExtensionSetup)
+#endif
+
+EFI_ACTIVE_MANAGEMENT_PROTOCOL *mActiveManagement = NULL;
+//
+// AMT GUID and Variable Name
+//
+EFI_GUID mEfiMeBiosExtensionSetupGuid = EFI_ME_BIOS_EXTENSION_SETUP_GUID;
+CHAR16 mEfiMeBiosExtensionSetupName[] = EFI_ME_BIOS_EXTENSION_SETUP_VARIABLE_NAME;
+
+/**
+ Check if Asf is enabled in setup options.
+
+ @param[in] None.
+ @retval EFI_SUCCESS mActiveManagement is not NULL
+ @retval Error Status code returned by
+ LocateProtocol.
+**/
+EFI_STATUS
+AmtLibInit (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mActiveManagement == NULL) {
+ Status = gBS->LocateProtocol (
+ &gEfiActiveManagementProtocolGuid,
+ NULL,
+ (VOID **) &mActiveManagement
+ );
+ } else {
+ Status = EFI_SUCCESS;
+ }
+
+ return Status;
+}
+
+/**
+ This will return IDE Redirection Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True IDE-R is enabled.
+ @retval False IDE-R is disabled.
+**/
+BOOLEAN
+ActiveManagementEnableIdeR (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+ UINTN VariableSize;
+ EFI_STATUS Status;
+ ME_BIOS_EXTENSION_SETUP MeBiosExtensionSetupData;
+
+ CurrentState = FALSE;
+ VariableSize = 0;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetIderState (mActiveManagement, &CurrentState);
+ }
+
+ VariableSize = sizeof (MeBiosExtensionSetupData);
+ Status = gRT->GetVariable (
+ mEfiMeBiosExtensionSetupName,
+ &mEfiMeBiosExtensionSetupGuid,
+ NULL,
+ &VariableSize,
+ &MeBiosExtensionSetupData
+ );
+ if (!EFI_ERROR (Status)) {
+ if ((MeBiosExtensionSetupData.AmtSolIder & IDER_ENABLE) == 0) {
+ CurrentState = FALSE;
+ }
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return Enforce Secure Boot over IDER Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True Enforce Secure Boot is enabled.
+ @retval False Enforce Secure Boot is disabled.
+**/
+BOOLEAN
+ActiveManagementEnforceSecureBoot (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+
+ CurrentState = FALSE;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetEnforceSecureBootState (mActiveManagement, &CurrentState);
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return BIOS Pause Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True BIOS Pause is enabled.
+ @retval False BIOS Pause is disabled.
+**/
+BOOLEAN
+ActiveManagementPauseBoot (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+
+ CurrentState = FALSE;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetBiosPauseState (mActiveManagement, &CurrentState);
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return BIOS Setup Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True BIOS Setup is enabled.
+ @retval False BIOS Setup is disabled.
+**/
+BOOLEAN
+ActiveManagementEnterSetup (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+
+ CurrentState = FALSE;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetBiosSetupState (mActiveManagement, &CurrentState);
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return Serial-over-Lan Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True Console Lock is enabled.
+ @retval False Console Lock is disabled.
+**/
+BOOLEAN
+ActiveManagementConsoleLocked (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+
+ CurrentState = FALSE;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetConsoleLockState (mActiveManagement, &CurrentState);
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return KVM Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True KVM is enabled.
+ @retval False KVM is disabled.
+**/
+BOOLEAN
+ActiveManagementEnableKvm (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+
+ CurrentState = FALSE;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetKvmState (mActiveManagement, &CurrentState);
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return Serial-over-Lan Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True Serial-over-Lan is enabled.
+ @retval False Serial-over-Lan is disabled.
+**/
+BOOLEAN
+ActiveManagementEnableSol (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+ UINTN VariableSize;
+ EFI_STATUS Status;
+ ME_BIOS_EXTENSION_SETUP MeBiosExtensionSetupData;
+
+ CurrentState = FALSE;
+ VariableSize = 0;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetSolState (mActiveManagement, &CurrentState);
+ }
+
+ VariableSize = sizeof (MeBiosExtensionSetupData);
+ Status = gRT->GetVariable (
+ mEfiMeBiosExtensionSetupName,
+ &mEfiMeBiosExtensionSetupGuid,
+ NULL,
+ &VariableSize,
+ &MeBiosExtensionSetupData
+ );
+ if (!EFI_ERROR (Status)) {
+ if ((MeBiosExtensionSetupData.AmtSolIder & SOL_ENABLE) == 0) {
+ CurrentState = FALSE;
+ }
+ }
+
+ return CurrentState;
+}
+
+/**
+ This will return IDE Redirection boot device index to boot
+
+ @param[in] None.
+
+ @retval IdeBootDevice Return the boot device number to boot
+ Bits 0-1: If IDER boot is selected in Perimeter 1 then Bits 1,2 define the drive on the IDER controller to be used as the boot driver.
+ Bit 1 Bit0
+ 0 0 Primary Master Drive
+ 0 1 Primary Slave Drive
+ 1 0 Secondary Master Drive
+ 1 1 Secondary Slave Drive
+ Bits 2-7: Reserved set to 0
+**/
+UINT8
+ActiveManagementIderBootDeviceGet (
+ VOID
+ )
+{
+ UINT8 IderBootDevice;
+ IderBootDevice = 0;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetIderBootDeviceSelectd (mActiveManagement, &IderBootDevice);
+ }
+
+ return IderBootDevice;
+}
+
+/**
+ Stop ASF Watch Dog Timer
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+AsfStopWatchDog (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ UINT32 HeciLength;
+ ASF_STOP_WDT AsfStopWdt;
+ UINT32 MeStatus;
+ UINT32 MeMode;
+ EFI_HECI_PROTOCOL *Heci;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+
+ if (!EFI_ERROR (Status)) {
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ DEBUG ((EFI_D_ERROR, "MeMode is %x, Unable to Stop ME BIOS Watch Dog Timer", MeMode));
+
+ return ;
+ }
+ ///
+ /// Check ME Status
+ ///
+ Status = Heci->GetMeStatus (&MeStatus);
+ ASSERT_EFI_ERROR (Status);
+ ///
+ /// Send EOP/WDT message when ME is ready. Do not care about if ME FW INIT is completed.
+ ///
+ if (ME_STATUS_ME_STATE_ONLY (MeStatus) == ME_READY) {
+ ///
+ /// Check if watch dog is enabled in BIOS Setup
+ ///
+ if (AmtWatchDog ()) {
+ ZeroMem ((VOID *) &AsfStopWdt, sizeof (ASF_STOP_WDT));
+ AsfStopWdt.Command = EFI_ASF_MESSAGE_COMMAND_MANAGEMENT_CONTROL;
+ AsfStopWdt.ByteCount = EFI_ASF_STOP_WDT_BYTE_COUNT;
+ AsfStopWdt.SubCommand = ASF_SUB_COMMAND_STOP_WDT;
+ AsfStopWdt.VersionNumber = EFI_ASF_STOP_WDT_VERSION;
+
+ HeciLength = ASF_STOP_WDT_LENGTH;
+ Status = Heci->SendMsg (
+ (UINT32 *) &AsfStopWdt,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ASF_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Stop ME BIOS Watch Dog Timer"));
+ }
+ }
+ }
+ }
+
+ return ;
+}
+
+/**
+ Start ASF Watch Dog Timer
+
+ @param[in] WatchDogType Which kind of WatchDog, ASF OS WatchDog Timer setting or ASF BIOS WatchDog Timer setting
+
+ @retval None
+**/
+VOID
+AsfStartWatchDog (
+ IN UINT8 WatchDogType
+ )
+{
+ EFI_STATUS Status;
+ UINT32 HeciLength;
+ ASF_START_WDT AsfStartWdt;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeStatus;
+ UINT32 MeMode;
+ UINT16 WaitTimer;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+
+ if (!EFI_ERROR (Status)) {
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ DEBUG ((EFI_D_ERROR, "MeMode is %x, Unable to Start ME Watch Dog Timer", MeMode));
+
+ return ;
+ }
+ ///
+ /// Check ME Status
+ ///
+ Status = Heci->GetMeStatus (&MeStatus);
+ ASSERT_EFI_ERROR (Status);
+ ///
+ /// Send EOP/WDT message when ME is ready. Do not care about if ME FW INIT is completed.
+ ///
+ if (ME_STATUS_ME_STATE_ONLY (MeStatus) == ME_READY) {
+ ///
+ /// Check if watch dog is enabled in BIOS Setup
+ ///
+ if (AmtWatchDog ()) {
+ ZeroMem ((VOID *) &AsfStartWdt, sizeof (ASF_START_WDT));
+ AsfStartWdt.Command = EFI_ASF_MESSAGE_COMMAND_MANAGEMENT_CONTROL;
+ AsfStartWdt.ByteCount = EFI_ASF_START_WDT_BYTE_COUNT;
+ AsfStartWdt.SubCommand = ASF_SUB_COMMAND_START_WDT;
+ AsfStartWdt.VersionNumber = EFI_ASF_START_WDT_VERSION_NUMBER;
+ AsfStartWdt.EventSensorType = EFI_ASF_START_WDT_EVENT_SENSOR_TYPE;
+ AsfStartWdt.EventType = EFI_ASF_START_WDT_EVENT_TYPE;
+ AsfStartWdt.EventOffset = EFI_ASF_START_WDT_EVENT_OFFSET;
+ AsfStartWdt.EventSeverity = EFI_ASF_START_WDT_EVENT_SEVERITY;
+ AsfStartWdt.SensorDevice = EFI_ASF_START_WDT_SENSOR_DEVICE;
+ AsfStartWdt.SensorNumber = EFI_ASF_START_WDT_SENSOR_NUMBER;
+ AsfStartWdt.Entity = EFI_ASF_START_WDT_ENTITY;
+ AsfStartWdt.EntityInstance = EFI_ASF_START_WDT_ENTITY_INSTANCE;
+ AsfStartWdt.EventData[0] = EFI_ASF_START_WDT_EVENT_DATA_BYTE_0;
+ if (WatchDogType == ASF_START_BIOS_WDT) {
+ AsfStartWdt.EventSourceType = EFI_ASF_START_WDT_EVENT_SOURCE_TYPE_BIOS;
+ AsfStartWdt.EventData[1] = EFI_ASF_START_WDT_EVENT_DATA_BYTE_1_BIOS_TIMEOUT;
+ WaitTimer = AmtWatchDogTimerBiosGet ();
+ } else {
+ AsfStartWdt.EventSourceType = EFI_ASF_START_WDT_EVENT_SOURCE_TYPE_OS;
+ AsfStartWdt.EventData[1] = EFI_ASF_START_WDT_EVENT_DATA_BYTE_1_OS_TIMEOUT;
+ WaitTimer = AmtWatchDogTimerOsGet ();
+ }
+
+ AsfStartWdt.TimeoutLow = (UINT8) WaitTimer;
+ AsfStartWdt.TimeoutHigh = (UINT8) (WaitTimer >> 8);
+
+ HeciLength = ASF_START_WDT_LENGTH;
+
+ Status = Heci->SendMsg (
+ (UINT32 *) &AsfStartWdt,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ASF_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Start ME Watch Dog Timer"));
+ }
+ }
+ }
+ }
+
+ return ;
+}
+
+/**
+ This will return progress event Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True progress event is enabled.
+ @retval False progress event is disabled.
+**/
+BOOLEAN
+ActiveManagementFwProgress (
+ VOID
+ )
+{
+ BOOLEAN CurrentState;
+
+ CurrentState = FALSE;
+
+ if (mActiveManagement != NULL) {
+ mActiveManagement->GetProgressMsgRequest (mActiveManagement, &CurrentState);
+ }
+
+ return CurrentState;
+}
+
+/**
+ Sent initialize KVM message
+
+ @param[in] None.
+
+ @retval True KVM Initialization is successful
+ @retval False KVM is not enabled
+**/
+BOOLEAN
+BdsKvmInitialization (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ UINT32 ResponseCode;
+
+ MeReportError (MSG_KVM_WAIT);
+ Status = HeciQueryKvmRequest (QUERY_REQUEST, &ResponseCode);
+ if (EFI_ERROR (Status)) {
+ MeReportError (MSG_KVM_TIMES_UP);
+ Status = HeciQueryKvmRequest (CANCEL_REQUEST, &ResponseCode);
+ } else if (ResponseCode == KVM_SESSION_CANCELLED) {
+ MeReportError (MSG_KVM_REJECTED);
+ } else {
+ return TRUE;
+ }
+
+ return FALSE;
+}
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.h b/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.h
new file mode 100644
index 0000000..b89ae0a
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.h
@@ -0,0 +1,257 @@
+/** @file
+ Header file for AMT functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _AMT_LIB_H_
+#define _AMT_LIB_H_
+
+#include "AmtPolicyLib.h"
+
+//
+// ASF Message
+//
+#define EFI_ASF_START_WDT_VERSION 0x10
+#define EFI_ASF_STOP_WDT_VERSION 0x10
+
+#define EFI_ASF_MESSAGE_COMMAND_SENSE_DEVICE_SYSTEM_STATE 0x01
+#define EFI_ASF_MESSAGE_COMMAND_MANAGEMENT_CONTROL 0x02
+#define EFI_ASF_MESSAGE_COMMAND_ASF_CONFIGURATION 0x03
+#define EFI_ASF_MESSAGE_COMMAND_MESSAGE 0x04
+#define EFI_ASF_MESSAGE_COMMAND_GETUUID 0xC7
+
+//
+// HECI ASF Command
+//
+#define EFI_ASF_START_WDT_BYTE_COUNT 0x0F
+#define EFI_ASF_START_WDT_VERSION_NUMBER 0x10
+#define EFI_ASF_START_WDT_EVENT_SENSOR_TYPE 0x23
+#define EFI_ASF_START_WDT_EVENT_TYPE 0x6F
+#define EFI_ASF_START_WDT_EVENT_OFFSET 0x00
+#define EFI_ASF_START_WDT_EVENT_SOURCE_TYPE_OS 0x48
+#define EFI_ASF_START_WDT_EVENT_SOURCE_TYPE_BIOS 0x00
+#define EFI_ASF_START_WDT_EVENT_SOURCE_TYPE 0x00 ///< 0x00 - BIOs, 0x48 - OS
+#define EFI_ASF_START_WDT_EVENT_SEVERITY 0x10 ///< critical
+#define EFI_ASF_START_WDT_SENSOR_DEVICE 0xFF ///< unspecified
+#define EFI_ASF_START_WDT_SENSOR_NUMBER 0xFF ///< unspecified
+#define EFI_ASF_START_WDT_ENTITY 0x00 ///< unspecified
+#define EFI_ASF_START_WDT_ENTITY_INSTANCE 0x00 ///< unspecified
+#define EFI_ASF_START_WDT_EVENT_DATA_BYTE_0 0x40
+#define EFI_ASF_START_WDT_EVENT_DATA_BYTE_1 0x02 ///< 0x02 BIOS POST WDT Timeout, 0x04 OS WDT timeout
+#define EFI_ASF_START_WDT_EVENT_DATA_BYTE_1_BIOS_TIMEOUT 0x02
+#define EFI_ASF_START_WDT_EVENT_DATA_BYTE_1_OS_TIMEOUT 0x04
+
+#define EFI_ASF_STOP_WDT_BYTE_COUNT 0x02
+
+#define ASF_START_BIOS_WDT 0
+#define ASF_START_OS_WDT 1
+
+/**
+ Check if Asf is enabled in setup options.
+
+ @param[in] None.
+ @retval EFI_SUCCESS mActiveManagement is not NULL
+ @retval Error Status code returned by
+ LocateProtocol.
+**/
+EFI_STATUS
+AmtLibInit (
+ VOID
+ )
+;
+
+/**
+ This will return IDE Redirection Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True IDE-R is enabled.
+ @retval False IDE-R is disabled.
+**/
+BOOLEAN
+ActiveManagementEnableIdeR (
+ VOID
+ )
+;
+
+/**
+ This will return Enforce Secure Boot over IDER Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True Enforce Secure Boot is enabled.
+ @retval False Enforce Secure Boot is disabled.
+**/
+BOOLEAN
+ActiveManagementEnforceSecureBoot (
+ VOID
+ )
+;
+
+/**
+ This will return BIOS Pause Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True BIOS Pause is enabled.
+ @retval False BIOS Pause is disabled.
+**/
+BOOLEAN
+ActiveManagementPauseBoot (
+ VOID
+ )
+;
+
+/**
+ This will return BIOS Setup Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True BIOS Setup is enabled.
+ @retval False BIOS Setup is disabled.
+**/
+BOOLEAN
+ActiveManagementEnterSetup (
+ VOID
+ )
+;
+
+/**
+ This will return Serial-over-Lan Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True Console Lock is enabled.
+ @retval False Console Lock is disabled.
+**/
+BOOLEAN
+ActiveManagementConsoleLocked (
+ VOID
+ )
+;
+
+/**
+ This will return KVM Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True KVM is enabled.
+ @retval False KVM is disabled.
+**/
+BOOLEAN
+ActiveManagementEnableKvm (
+ VOID
+ )
+;
+
+/**
+ This will return Serial-over-Lan Boot Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True Serial-over-Lan is enabled.
+ @retval False Serial-over-Lan is disabled.
+**/
+BOOLEAN
+ActiveManagementEnableSol (
+ VOID
+ )
+;
+
+/**
+ This will return IDE Redirection boot device index to boot
+
+ @param[in] None.
+
+ @retval IdeBootDevice Return the boot device number to boot
+ Bits 0-1: If IDER boot is selected in Perimeter 1 then Bits 1,2 define the drive on the IDER controller to be used as the boot driver.
+ Bit 1 Bit0
+ 0 0 Primary Master Drive
+ 0 1 Primary Slave Drive
+ 1 0 Secondary Master Drive
+ 1 1 Secondary Slave Drive
+ Bits 2-7: Reserved set to 0
+**/
+UINT8
+ActiveManagementIderBootDeviceGet (
+ VOID
+ )
+;
+
+/**
+ Stop ASF Watch Dog Timer
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+AsfStopWatchDog (
+ VOID
+ )
+;
+
+/**
+ Start ASF Watch Dog Timer
+
+ @param[in] WatchDogType Which kind of WatchDog, ASF OS WatchDog Timer setting or ASF BIOS WatchDog Timer setting
+
+ @retval None
+**/
+VOID
+AsfStartWatchDog (
+ IN UINT8 WatchDogType
+ )
+;
+
+/**
+ This will return progress event Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True progress event is enabled.
+ @retval False progress event is disabled.
+**/
+BOOLEAN
+ActiveManagementFwProgress (
+ VOID
+ )
+;
+
+/**
+ Sent initialize KVM message
+
+ @param[in] None.
+
+ @retval True KVM Initialization is successful
+ @retval False KVM is not enabled
+**/
+BOOLEAN
+BdsKvmInitialization (
+ VOID
+ )
+;
+#endif
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.inf b/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.inf
new file mode 100644
index 0000000..4089248
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtLib.inf
@@ -0,0 +1,75 @@
+## @file
+# Component description file for AMT functionality
+#
+#@copyright
+# Copyright (c) 2010 - 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = AmtLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ AmtLib.c
+ AmtLib.h
+ AmtPolicyLib.c
+ AmtPolicyLib.h
+ AmtPolicyDebugDumpDxe.c
+ MebxSetupDebugDumpDxe.c
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Include
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Dxe
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Heci/Include
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include
+
+#
+# Typically the sample code referenced will be available in the code base already
+# So keep this include at the end to defer to the source base definition
+# and only use the sample code definition if source base does not include these files.
+#
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ MeLib
+ MeProtocolLib
+ EdkIIGlueBaseMemoryLib
+ EdkIIGlueUefiRuntimeServicesTableLib
+ EdkIIGlueUefiBootServicesTableLib
+ EdkIIGlueBasePciLibPciExpress
+ EdkIIGlueDxeDebugLibReportStatusCode
+ EdkIIGlueDxeReportStatusCodeLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_DXE_REPORT_STATUS_CODE_LIB__ \
+ -D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__ \
+ -D __EDKII_GLUE_UEFI_RUNTIME_SERVICES_TABLE_LIB__
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.cif b/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.cif
new file mode 100644
index 0000000..9aae0a8
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.cif
@@ -0,0 +1,16 @@
+<component>
+ name = "AmtLibDxe"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\AMT\Dxe\"
+ RefName = "AmtLibDxe"
+[files]
+"AmtLib.c"
+"AmtLib.h"
+"AmtLib.inf"
+"AmtLibDxe.mak"
+"AmtLibDxe.sdl"
+"AmtPolicyLib.c"
+"AmtPolicyLib.h"
+"AmtPolicyDebugDumpDxe.c"
+"MebxSetupDebugDumpDxe.c"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.mak b/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.mak
new file mode 100644
index 0000000..1d0a64b
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.mak
@@ -0,0 +1,54 @@
+# /*++
+# Copyright (c) 2009 Intel Corporation. All rights reserved.
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+# --*/
+# MAK file for the ModulePart:AmtLibDxe
+all : AmtLibDxe
+
+$(BUILD_DIR)\AmtLibDxe.lib : AmtLibDxe
+
+AmtLibDxe : $(BUILD_DIR)\AmtLibDxe.mak AmtLibDxeBin
+
+$(BUILD_DIR)\AmtLibDxe.mak : $(AmtLibDxe_DIR)\$(@B).cif $(AmtLibDxe_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(AmtLibDxe_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+AmtLibDxe_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES) \
+ $(ME_INCLUDES)\
+ $(INTEL_PCH_INCLUDES)\
+
+AmtLibDxe_DEFINES=\
+ $(MY_DEFINES)/D __EDKII_GLUE_BASE_MEMORY_LIB__\
+ /D __EDKII_GLUE_EDK_DXE_RUNTIME_DRIVER_LIB__\
+ /D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__\
+
+AmtLibDxe_LIBS=\
+ $(MeProtocolLib_LIB)\
+ $(MeLibDxe_LIB)
+
+AmtLibDxeBin : $(AmtLibDxe_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ /f $(BUILD_DIR)\AmtLibDxe.mak all \
+ "MY_INCLUDES=$(AmtLibDxe_INCLUDES)" \
+ "MY_DEFINES=$(AmtLibDxe_DEFINES)"\
+ TYPE=LIBRARY \
+#**********************************************************************
+#**********************************************************************
+#** **
+#** (C)Copyright 1985-2006, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 6145-F Northbelt Pkwy, Norcross, GA 30071 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#**********************************************************************
+#**********************************************************************
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.sdl b/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.sdl
new file mode 100644
index 0000000..054446f
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtLibDxe.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "AmtLibDxe_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable AmtLibDxe support in Project"
+End
+
+MODULE
+ Help = "Includes AmtLibDxe.mak to Project"
+ File = "AmtLibDxe.mak"
+End
+
+PATH
+ Name = "AmtLibDxe_DIR"
+ Help = "iAMT Library file source directory"
+End
+
+ELINK
+ Name = "AmtLibDxe_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\AmtLibDxe.lib"
+ Parent = "AmtLibDxe_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(AmtLibDxe_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyDebugDumpDxe.c b/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyDebugDumpDxe.c
new file mode 100644
index 0000000..608f886
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyDebugDumpDxe.c
@@ -0,0 +1,115 @@
+/** @file
+ Dump whole DXE_AMT_POLICY_PROTOCOL and serial out.
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "AmtPolicyLib.h"
+#endif
+
+extern DXE_AMT_POLICY_PROTOCOL *mDxePlatformAmtPolicy;
+
+/**
+ Dump DXE Amt Platform Policy
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+DxeAmtPolicyDebugDump (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ Status = AmtPolicyLibInit ();
+ if (EFI_ERROR(Status)) {
+ return;
+ }
+
+ DEBUG ((EFI_D_INFO, "\n------------------------ AmtPlatformPolicy Dump Begin -----------------\n"));
+ DEBUG ((EFI_D_INFO, " Revision : 0x%x\n", mDxePlatformAmtPolicy->Revision));
+ DEBUG ((EFI_D_INFO, "AmtConfig ---\n"));
+ //
+ // Byte 0, bit definition for functionality enable/disable
+ //
+ DEBUG ((EFI_D_INFO, " AsfEnabled : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.AsfEnabled));
+ DEBUG ((EFI_D_INFO, " iAmtEnabled : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.iAmtEnabled));
+ DEBUG ((EFI_D_INFO, " iAmtbxPasswordWrite : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.iAmtbxPasswordWrite));
+ DEBUG ((EFI_D_INFO, " WatchDog : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.WatchDog));
+ DEBUG ((EFI_D_INFO, " CiraRequest : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.CiraRequest));
+ DEBUG ((EFI_D_INFO, " ManageabilityMode : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.ManageabilityMode));
+ DEBUG ((EFI_D_INFO, " UnConfigureMe : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.UnConfigureMe));
+ DEBUG ((EFI_D_INFO, " MebxDebugMsg : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.MebxDebugMsg));
+
+ //
+ // Byte 1, bit definition for functionality enable/disable
+ //
+ DEBUG ((EFI_D_INFO, " ForcMebxSyncUp : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.ForcMebxSyncUp));
+ DEBUG ((EFI_D_INFO, " UsbrEnabled : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.UsbrEnabled));
+ DEBUG ((EFI_D_INFO, " UsbLockingEnabled : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.UsbLockingEnabled));
+ DEBUG ((EFI_D_INFO, " HideUnConfigureMeConfirm : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.HideUnConfigureMeConfirm));
+ DEBUG ((EFI_D_INFO, " USBProvision : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.USBProvision));
+ DEBUG ((EFI_D_INFO, " FWProgress : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.FWProgress));
+ DEBUG ((EFI_D_INFO, " iAmtbxHotKeyPressed : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.iAmtbxHotkeyPressed));
+ DEBUG ((EFI_D_INFO, " iAmtbxSelectionScreen : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.iAmtbxSelectionScreen));
+
+ //
+ // Byte 2, bit definition for functionality enable/disable
+ //
+ DEBUG ((EFI_D_INFO, " AtEnabled : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.AtEnabled));
+
+ //
+ // Byte 3-4 OS WatchDog Timer
+ //
+ DEBUG ((EFI_D_INFO, " WatchDogTimerOs : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.WatchDogTimerOs));
+
+ //
+ // Byte 5-6 BIOS WatchDog Timer
+ //
+ DEBUG ((EFI_D_INFO, " WatchDogTimerBios : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.WatchDogTimerBios));
+
+ //
+ // Byte 7 CIRA Timeout, Client Initiated Remote Access Timeout
+ // OEM defined timeout for MPS connection to be established.
+ //
+ DEBUG ((EFI_D_INFO, " CiraTimeout : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.CiraTimeout));
+
+ //
+ // Byte 8 CPU Replacement Timeout
+ //
+ DEBUG ((EFI_D_INFO, " CPU Replacement Timeout : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.CpuReplacementTimeout));
+
+ //
+ // Byte 9-10 OemResolutionSettings
+ //
+ DEBUG ((EFI_D_INFO, " MebxNonUiTextMode : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.MebxNonUiTextMode));
+ DEBUG ((EFI_D_INFO, " MebxUiTextMode : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.MebxUiTextMode));
+ DEBUG ((EFI_D_INFO, " MebxGraphicsMode : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.MebxGraphicsMode));
+
+ //
+ // Byte 11-14 Pointer to a list which contain on-board devices bus/device/fun number
+ //
+ DEBUG ((EFI_D_INFO, " PciDeviceFilterOutTable Pointer : 0x%x\n", mDxePlatformAmtPolicy->AmtConfig.PciDeviceFilterOutTable));
+
+ DEBUG ((EFI_D_INFO, "\n------------------------ AmtPlatformPolicy Dump End -------------------\n"));
+}
+
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.c b/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.c
new file mode 100644
index 0000000..4448504
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.c
@@ -0,0 +1,547 @@
+/** @file
+ Implementation file for AMT Policy functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+
+#include "EdkIIGlueDxe.h"
+#include "AmtPolicyLib.h"
+#include "MeLib.h"
+
+#include EFI_PROTOCOL_CONSUMER (ActiveManagement)
+#include EFI_PROTOCOL_CONSUMER (AmtPlatformPolicy)
+#endif
+//
+// Global variables
+//
+DXE_AMT_POLICY_PROTOCOL *mDxePlatformAmtPolicy = NULL;
+
+/**
+ Check if AMT is enabled in setup options.
+
+ @param[in] None.
+
+ @retval EFI_SUCCESS AMT platform policy pointer is initialized.
+ @retval All other error conditions encountered when no AMT platform policy available.
+**/
+EFI_STATUS
+AmtPolicyLibInit (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy != NULL) {
+ return EFI_SUCCESS;
+ }
+ //
+ // Get the desired platform setup policy.
+ //
+ Status = gBS->LocateProtocol (&gDxePlatformAmtPolicyGuid, NULL, (VOID **) &mDxePlatformAmtPolicy);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "No AMT Platform Policy Protocol available"));
+ ASSERT_EFI_ERROR(Status);
+ } else if (mDxePlatformAmtPolicy == NULL) {
+ DEBUG ((EFI_D_ERROR, "No AMT Platform Policy Protocol available"));
+ Status = EFI_UNSUPPORTED;
+ }
+
+ return Status;
+}
+
+/**
+ Check if Asf is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE Asf is disabled.
+ @retval TRUE Asf is enabled.
+**/
+BOOLEAN
+AsfSupported (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ //
+ // First check if ASF support is enabled in Setup.
+ //
+ if (mDxePlatformAmtPolicy->AmtConfig.AsfEnabled != 1) {
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+/**
+ Check if Amt is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE Amt is disabled.
+ @retval TRUE Amt is enabled.
+**/
+BOOLEAN
+AmtSupported (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ //
+ // First check if AMT support is enabled in Setup.
+ //
+ if (mDxePlatformAmtPolicy->AmtConfig.iAmtEnabled != 1) {
+ return FALSE;
+ }
+
+ return TRUE;
+}
+
+/**
+ Check if AMT BIOS Extension hotkey was pressed during BIOS boot.
+
+ @param[in] None.
+
+ @retval FALSE MEBx hotkey was not pressed.
+ @retval TRUE MEBx hotkey was pressed.
+**/
+BOOLEAN
+AmtHotkeyPressed (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ //
+ // First check if AMT Setup Prompt is enabled in Setup.
+ //
+ if (mDxePlatformAmtPolicy->AmtConfig.iAmtbxHotkeyPressed == 1) {
+ Supported = TRUE;
+ } else {
+ Supported = FALSE;
+ }
+
+ return Supported;
+}
+
+/**
+ Check if AMT BIOS Extension Selection Screen is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE AMT Selection Screen is disabled.
+ @retval TRUE AMT Selection Screen is enabled.
+**/
+BOOLEAN
+AmtSelectionScreen (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ //
+ // First check if AMT Selection Screen is enabled in Setup.
+ //
+ if (mDxePlatformAmtPolicy->AmtConfig.iAmtbxSelectionScreen == 1) {
+ Supported = TRUE;
+ } else {
+ Supported = FALSE;
+ }
+
+ return Supported;
+}
+
+/**
+ Check if AMT WatchDog is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE AMT WatchDog is disabled.
+ @retval TRUE AMT WatchDog is enabled.
+**/
+BOOLEAN
+AmtWatchDog (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ Supported = FALSE;
+ if (ManageabilityModeSetting () != 0) {
+ //
+ // First check if AMT WatchDog is enabled in Setup.
+ //
+ if (AsfSupported ()) {
+ if (mDxePlatformAmtPolicy->AmtConfig.WatchDog == 1) {
+ Supported = TRUE;
+ }
+ }
+ }
+
+ return Supported;
+}
+
+/**
+ Return BIOS watchdog timer
+
+ @param[in] None.
+
+ @retval UINT16 BIOS ASF Watchdog Timer
+**/
+UINT16
+AmtWatchDogTimerBiosGet (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return 0;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.WatchDogTimerBios;
+}
+
+/**
+ Return OS watchdog timer
+
+ @param[in] None.
+
+ @retval UINT16 OS ASF Watchdog Timer
+**/
+UINT16
+AmtWatchDogTimerOsGet (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return 0;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.WatchDogTimerOs;
+}
+
+/**
+ Provide CIRA request information from OEM code.
+
+ @param[in] None.
+
+ @retval Check if any CIRA requirement during POST
+**/
+BOOLEAN
+AmtCiraRequestTrigger (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.CiraRequest == 1;
+}
+
+/**
+ Provide CIRA request Timeout from OEM code.
+
+ @param[in] None.
+
+ @retval CIRA require Timeout for MPS connection to be estabilished
+**/
+UINT8
+AmtCiraRequestTimeout (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.CiraTimeout;
+}
+
+/**
+ Provide Manageability Mode setting from MEBx BIOS Sync Data
+
+ @param[in] None
+
+ @retval UINT8 Manageability Mode = MNT_AMT or MNT_ASF
+**/
+UINT8
+ManageabilityModeSetting (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return 0;
+ }
+ }
+ return (UINT8) (mDxePlatformAmtPolicy->AmtConfig.ManageabilityMode);
+}
+
+/**
+ Provide UnConfigure ME without password request from OEM code.
+
+ @param[in] None.
+
+ @retval Check if unConfigure ME without password request
+**/
+BOOLEAN
+AmtUnConfigureMe (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.UnConfigureMe == 1;
+}
+
+/**
+ Provide 'Hiding the Unconfigure ME without password confirmation prompt' request from OEM code.
+
+ @param[in] None.
+
+ @retval Check if 'Hide unConfigure ME without password Confirmation prompt' request
+**/
+BOOLEAN
+AmtHideUnConfigureMeConfPrompt (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.HideUnConfigureMeConfirm == 1;
+}
+
+/**
+ Provide show MEBx debug message request from OEM code.
+
+ @param[in] None.
+
+ @retval Check show MEBx debug message request
+ **/
+BOOLEAN
+AmtMebxDebugMsg (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.MebxDebugMsg == 1;
+}
+
+/**
+ Provide on-board device list table and do not need to report them to AMT. AMT only need to know removable PCI device
+ information.
+
+ @param[in] None.
+
+ @retval on-board device list table pointer other than system device.
+**/
+UINT32
+AmtPciDeviceFilterOutTable (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return 0;
+ }
+ }
+ return mDxePlatformAmtPolicy->AmtConfig.PciDeviceFilterOutTable;
+}
+
+/**
+ Check if USB provisioning enabled/disabled in platform policy.
+
+ @param[in] None.
+
+ @retval FALSE USB provisioning is disabled.
+ @retval TRUE USB provisioning is enabled.
+**/
+BOOLEAN
+USBProvisionSupport (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ Supported = FALSE;
+
+ //
+ // First check if USB Provision is enabled in Setup.
+ //
+ if (mDxePlatformAmtPolicy->AmtConfig.USBProvision == 1) {
+ Supported = TRUE;
+ }
+
+ return Supported;
+}
+
+/**
+ This will return progress event Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True progress event is enabled.
+ @retval False progress event is disabled.
+**/
+BOOLEAN
+FwProgressSupport (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ Supported = FALSE;
+
+ //
+ // First check if FW Progress is enabled in Setup.
+ //
+ if (mDxePlatformAmtPolicy->AmtConfig.FWProgress == 1) {
+ Supported = TRUE;
+ }
+
+ return Supported;
+}
+
+/**
+ Check if ForcMebxSyncUp is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE ForcMebxSyncUp is disabled.
+ @retval TRUE ForcMebxSyncUp is enabled.
+**/
+BOOLEAN
+AmtForcMebxSyncUp (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformAmtPolicy == NULL) {
+ Status = AmtPolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ if (mDxePlatformAmtPolicy->AmtConfig.ForcMebxSyncUp == 1) {
+ Supported = TRUE;
+ } else {
+ Supported = FALSE;
+ }
+
+ return Supported;
+}
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.h b/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.h
new file mode 100644
index 0000000..866c5c0
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/AmtPolicyLib.h
@@ -0,0 +1,298 @@
+/** @file
+ Header file for AMT Policy functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _AMT_POLICY_LIB_H_
+#define _AMT_POLICY_LIB_H_
+
+#include EFI_PROTOCOL_DEFINITION (AmtPlatformPolicy)
+#include EFI_GUID_DEFINITION (MeBiosExtensionSetup)
+
+/**
+ Check if AMT is enabled in setup options.
+
+ @param[in] None.
+
+ @retval EFI_SUCCESS AMT platform policy is initialized.
+ @retval All other error conditions encountered when no AMT platform policy available.
+**/
+EFI_STATUS
+AmtPolicyLibInit (
+ VOID
+ )
+;
+
+/**
+ Check if Asf is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE Asf is disabled.
+ @retval TRUE Asf is enabled.
+**/
+BOOLEAN
+AsfSupported (
+ VOID
+ )
+;
+
+/**
+ Check if Amt is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE Amt is disabled.
+ @retval TRUE Amt is enabled.
+**/
+BOOLEAN
+AmtSupported (
+ VOID
+ )
+;
+
+/**
+ Check if AMT BIOS Extension hotkey was pressed during BIOS boot.
+
+ @param[in] None.
+
+ @retval FALSE MEBx hotkey was not pressed.
+ @retval TRUE MEBx hotkey was pressed.
+**/
+BOOLEAN
+AmtHotkeyPressed (
+ VOID
+ )
+;
+
+/**
+ Check if AMT BIOS Extension Selection Screen is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE AMT Selection Screen is disabled.
+ @retval TRUE AMT Selection Screen is enabled.
+**/
+BOOLEAN
+AmtSelectionScreen (
+ VOID
+ )
+;
+
+/**
+ Check if AMT WatchDog is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE AMT WatchDog is disabled.
+ @retval TRUE AMT WatchDog is enabled.
+**/
+BOOLEAN
+AmtWatchDog (
+ VOID
+ )
+;
+
+/**
+ Return BIOS watchdog timer
+
+ @param[in] None.
+
+ @retval UINT16 BIOS ASF Watchdog Timer
+**/
+UINT16
+AmtWatchDogTimerBiosGet (
+ VOID
+ )
+;
+
+/**
+ Return OS watchdog timer
+
+ @param[in] None.
+
+ @retval UINT16 OS ASF Watchdog Timer
+**/
+UINT16
+AmtWatchDogTimerOsGet (
+ VOID
+ )
+;
+
+/**
+ Provide CIRA request information from OEM code.
+
+ @param[in] None.
+
+ @retval Check if any CIRA requirement during POST
+**/
+BOOLEAN
+AmtCiraRequestTrigger (
+ VOID
+ )
+;
+
+/**
+ Provide CIRA request Timeout from OEM code.
+
+ @param[in] None.
+
+ @retval CIRA require Timeout for MPS connection to be estabilished
+**/
+UINT8
+AmtCiraRequestTimeout (
+ VOID
+ )
+
+;
+
+/**
+ Provide Manageability Mode setting from MEBx BIOS Sync Data
+
+ @param[in] None
+
+ @retval UINT8 Manageability Mode = MNT_AMT or MNT_ASF
+**/
+UINT8
+ManageabilityModeSetting (
+ VOID
+ )
+;
+
+/**
+ Provide UnConfigure ME without password request from OEM code.
+
+ @param[in] None.
+
+ @retval Check if unConfigure ME without password request
+**/
+BOOLEAN
+AmtUnConfigureMe (
+ VOID
+ )
+;
+
+/**
+ Provide 'Hiding the Unconfigure ME without password confirmation prompt' request from OEM code.
+
+ @param[in] None.
+
+ @retval Check if 'Hide unConfigure ME without password Confirmation prompt' request
+**/
+BOOLEAN
+AmtHideUnConfigureMeConfPrompt (
+ VOID
+ )
+;
+
+/**
+ Provide show MEBx debug message request from OEM code.
+
+ @param[in] None.
+
+ @retval Check show MEBx debug message request
+ **/
+BOOLEAN
+AmtMebxDebugMsg (
+ VOID
+ )
+;
+
+/**
+ Provide on-board device list table and do not need to report them to AMT. AMT only need to know removable PCI device
+ information.
+
+ @param[in] None.
+
+ @retval on-board device list table pointer other than system device.
+**/
+UINT32
+AmtPciDeviceFilterOutTable (
+ VOID
+ )
+;
+
+/**
+ Check if USB provisioning enabled/disabled in platform policy.
+
+ @param[in] None.
+
+ @retval FALSE USB provisioning is disabled.
+ @retval TRUE USB provisioning is enabled.
+**/
+BOOLEAN
+USBProvisionSupport (
+ VOID
+ )
+;
+
+/**
+ This will return progress event Option.
+ True if the option is enabled.
+
+ @param[in] None.
+
+ @retval True progress event is enabled.
+ @retval False progress event is disabled.
+**/
+BOOLEAN
+FwProgressSupport (
+ VOID
+ )
+;
+
+/**
+ Check if ForcMebxSyncUp is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE ForcMebxSyncUp is disabled.
+ @retval TRUE ForcMebxSyncUp is enabled.
+**/
+BOOLEAN
+AmtForcMebxSyncUp (
+ VOID
+ )
+;
+
+/**
+ Dump DXE Amt Platform Policy
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+DxeAmtPolicyDebugDump (
+ VOID
+ )
+;
+
+/**
+ Dump ME_BIOS_EXTENSION_SETUP variable
+
+ @param[in] MeBiosExtensionSetup Pointer to ME_BIOS_EXTENSION_SETUP variable
+
+ @retval None
+**/
+VOID
+DxeMebxSetupVariableDebugDump (
+ IN ME_BIOS_EXTENSION_SETUP *MeBiosExtensionSetup OPTIONAL
+ )
+;
+#endif
diff --git a/ReferenceCode/ME/Library/AMT/Dxe/MebxSetupDebugDumpDxe.c b/ReferenceCode/ME/Library/AMT/Dxe/MebxSetupDebugDumpDxe.c
new file mode 100644
index 0000000..7fd5048
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Dxe/MebxSetupDebugDumpDxe.c
@@ -0,0 +1,75 @@
+/** @file
+ Dump whole ME_BIOS_EXTENSION_SETUP and serial out.
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "AmtPolicyLib.h"
+#endif
+
+/**
+ Dump ME_BIOS_EXTENSION_SETUP variable
+
+ @param[in] MeBiosExtensionSetup Pointer to ME_BIOS_EXTENSION_SETUP variable
+
+ @retval None
+**/
+VOID
+DxeMebxSetupVariableDebugDump (
+ IN ME_BIOS_EXTENSION_SETUP *MeBiosExtensionSetup OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ UINTN VariableSize;
+ ME_BIOS_EXTENSION_SETUP MeBxSetup;
+ ME_BIOS_EXTENSION_SETUP *MeBxSetupPtr;
+
+ if (MeBiosExtensionSetup == NULL) {
+ Status = gRT->GetVariable (
+ gEfiMeBiosExtensionSetupName,
+ &gEfiMeBiosExtensionSetupGuid,
+ NULL,
+ &VariableSize,
+ &MeBxSetup
+ );
+ if (EFI_ERROR(Status)) {
+ return;
+ }
+ MeBxSetupPtr = &MeBxSetup;
+ } else {
+ MeBxSetupPtr = MeBiosExtensionSetup;
+ }
+
+ DEBUG ((EFI_D_INFO, "\n------------------------ MeBiosExtensionSetup Dump Begin -----------------\n"));
+ DEBUG ((EFI_D_INFO, " InterfaceVersion : 0x%x\n", MeBxSetupPtr->InterfaceVersion));
+ DEBUG ((EFI_D_INFO, " Flags : 0x%x\n", MeBxSetupPtr->Flags));
+ DEBUG ((EFI_D_INFO, " PlatformMngSel : 0x%x\n", MeBxSetupPtr->PlatformMngSel));
+ DEBUG ((EFI_D_INFO, " AmtSolIder : 0x%x\n", MeBxSetupPtr->AmtSolIder));
+ DEBUG (
+ (EFI_D_INFO,
+ " RemoteAssistanceTriggerAvailablilty : 0x%x\n",
+ MeBxSetupPtr->RemoteAssistanceTriggerAvailablilty)
+ );
+ DEBUG ((EFI_D_INFO, " KvmEnable : 0x%x\n", MeBxSetupPtr->KvmEnable));
+ DEBUG ((EFI_D_INFO, " MebxDefaultSolIder : 0x%x\n", MeBxSetupPtr->MebxDefaultSolIder));
+
+ DEBUG ((EFI_D_INFO, "\n------------------------ MeBiosExtensionSetup Dump End -------------------\n"));
+
+}
diff --git a/ReferenceCode/ME/Library/AMT/Include/Amt.h b/ReferenceCode/ME/Library/AMT/Include/Amt.h
new file mode 100644
index 0000000..9698218
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Include/Amt.h
@@ -0,0 +1,59 @@
+/** @file
+ Header file for common Active Management Technology defines.
+
+@copyright
+ Copyright (c) 2010 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _AMT_H_
+#define _AMT_H_
+
+///
+/// Intel Internet Assigned Numbers Authority Manufacturer ID
+/// (The firmware sends 0x57010000 for decimal value 343)
+///
+#define INTEL_IANA_SWAP32(x) ((((x) & 0xff) << 24) | (((x) & 0xff00) << 8) | \
+ (((x) & 0xff0000) >> 8) | (((x) & 0xff000000) >> 24))
+#define ASF_INTEL_IANA 0x00000157
+#define ASF_INTEL_CONVERTED_IANA INTEL_IANA_SWAP32 (ASF_INTEL_IANA) ///< 0X57010000, received from ME
+///
+/// Intel OEM Special Command
+///
+#define ASF_INTEL_OEM_CMD 0xC1
+
+///
+/// Intel OEM Parameters 16 bit OEM Parameter values
+///
+#define USE_SOL 0x0001 ///< 0000 0000 0000 0001 - bit 0, use SOL on the next boot
+//
+// Intel OEM Command 16 bit special command parameter values
+//
+#define USE_IDER 0x0001 ///< 0000 0000 0000 0001 - bit 0 Paramater 2 will be used to indicate the channel
+#define ENFORCE_SECURE_BOOT 0x0002 ///< 0000 0000 0000 0010 - bit 1 Enforce secure boot over IDER
+#define REFLASH_BIOS 0x0004 ///< 0000 0000 0000 0100 - bit 2
+#define BIOS_SETUP 0x0008 ///< 0000 0000 0000 1000 - bit 3
+#define BIOS_PAUSE 0x0010 ///< 0000 0000 0001 0000 - bit 4
+#define USE_KVM 0x0020 ///< 0000 0000 0010 0000 - bit 5
+#define IDER_CD 0x0100 ///< 0000 0001 0000 0000 - bit 8 Primary Slave Drive
+#define IDER_PRIMARY_MASTER 0x0000
+#define IDER_PRIMARY_SLAVE 0x0100
+#define IDER_SECONDARY_MASTER 0x0200
+#define IDER_SECONDARY_SLAVE 0x0300
+
+#define IDER_BOOT_DEVICE_MASK 0x0300
+#define IDER_BOOT_DEVICE_SHIFT 8
+
+#endif
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.cif b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.cif
new file mode 100644
index 0000000..1c34f45
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.cif
@@ -0,0 +1,13 @@
+<component>
+ name = "AmtLibPei"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\AMT\Pei\"
+ RefName = "AmtLibPei"
+[files]
+"AmtLibPei.sdl"
+"AmtLibPei.mak"
+"AmtPolicyLibPei.c"
+"AmtPolicyLibPei.h"
+"AmtLibPei.h"
+"AmtLibPei.inf"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.h b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.h
new file mode 100644
index 0000000..4b29fc9
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.h
@@ -0,0 +1,26 @@
+/** @file
+ Header file for PEI AMT functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PEI_AMT_LIB_H_
+#define _PEI_AMT_LIB_H_
+
+#include "AmtPolicyLibPei.h"
+
+#endif
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.inf b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.inf
new file mode 100644
index 0000000..44d88ad
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.inf
@@ -0,0 +1,51 @@
+## @file
+# Component description file for AMT Library functions for PEIMs
+#
+#@copyright
+# Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = AmtLibPei
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ AmtPolicyLibPei.c
+ AmtPolicyLibPei.h
+ AmtLibPei.h
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Include/Pei
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ EdkIIGluePeiServicesLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_PEI_SERVICES_LIB__
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.mak b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.mak
new file mode 100644
index 0000000..e31ecc5
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.mak
@@ -0,0 +1,50 @@
+# /*++
+# Copyright (c) 2009 Intel Corporation. All rights reserved.
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+# --*/
+# MAK file for the ModulePart:AmtLibPei
+all : AmtLibPei
+
+$(BUILD_DIR)\AmtLibPei.lib : AmtLibPei
+
+AmtLibPei : $(BUILD_DIR)\AmtLibPei.mak AmtLibPeiBin
+
+$(BUILD_DIR)\AmtLibPei.mak : $(AmtLibPei_DIR)\$(@B).cif $(AmtLibPei_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(AmtLibPei_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+AmtLibPei_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES)\
+ $(ME_INCLUDES) \
+
+AmtLibPei_DEFINES=\
+ /D __EDKII_GLUE_PEI_SERVICES_LIB__
+
+AmtLibPei_LIBS=\
+ $(EdkIIGluePeiServicesLib_LIB)\
+
+AmtLibPeiBin : $(AmtLibPei_LIBS) $(MeLibPei_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ /f $(BUILD_DIR)\AmtLibPei.mak all \
+ "MY_INCLUDES=$(AmtLibPei_INCLUDES)" \
+ "CFLAGS=$(CFLAGS) $(AmtLibPei_DEFINES)"\
+ TYPE=PEI_LIBRARY \
+#**********************************************************************
+#**********************************************************************
+#** **
+#** (C)Copyright 1985-2006, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 6145-F Northbelt Pkwy, Norcross, GA 30071 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#**********************************************************************
+#**********************************************************************
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.sdl b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.sdl
new file mode 100644
index 0000000..b3a63bd
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtLibPei.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "AmtLibPei_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable AmtLibPei support in Project"
+End
+
+MODULE
+ Help = "Includes AmtLibPei.mak to Project"
+ File = "AmtLibPei.mak"
+End
+
+PATH
+ Name = "AmtLibPei_DIR"
+ Help = "iAMT Library file source directory"
+End
+
+ELINK
+ Name = "AmtLibPei_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\AmtLibPei.lib"
+ Parent = "AmtLibPei_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(AmtLibPei_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.c b/ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.c
new file mode 100644
index 0000000..472ebbc
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.c
@@ -0,0 +1,241 @@
+/** @file
+ Implementation file for AMT Policy functionality for PEIM
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGluePeim.h"
+#include "AmtPolicyLibPei.h"
+#endif
+
+EFI_GUID mPeiAmtStatusCodePpiGuid = PEI_AMT_STATUS_CODE_PPI_GUID;
+
+/**
+ Check if Amt is enabled in setup options.
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] PeiAmtPlatformPolicy The AMT Platform Policy protocol instance
+
+ @retval EFI_SUCCESS AMT platform policy Ppi located
+ @retval All other error conditions encountered result in an ASSERT.
+**/
+EFI_STATUS
+PeiAmtPolicyLibInit (
+ EFI_PEI_SERVICES **PeiServices,
+ PEI_AMT_PLATFORM_POLICY_PPI **PeiAmtPlatformPolicy
+ )
+{
+ EFI_STATUS Status;
+
+ ///
+ /// Locate system configuration variable
+ ///
+ Status = PeiServicesLocatePpi (
+ &gPeiAmtPlatformPolicyPpiGuid, // GUID
+ 0, // INSTANCE
+ NULL, // EFI_PEI_PPI_DESCRIPTOR
+ (VOID **) PeiAmtPlatformPolicy // PPI
+ );
+ ASSERT_EFI_ERROR (Status);
+ return Status;
+}
+
+/**
+ Check if AMT WatchDog is enabled in setup options.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval FALSE AMT WatchDog is disabled.
+ @retval TRUE AMT WatchDog is enabled.
+**/
+BOOLEAN
+PeiAmtWatchDog (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+{
+ EFI_STATUS Status;
+ BOOLEAN Supported;
+ PEI_AMT_PLATFORM_POLICY_PPI *PeiAmtPlatformPolicy;
+
+ Supported = FALSE;
+ if (ManageabilityModeSetting (PeiServices) != 0) {
+ Status = PeiAmtPolicyLibInit (PeiServices, &PeiAmtPlatformPolicy);
+ ASSERT_EFI_ERROR (Status);
+ //
+ // First check if AMT WatchDog is enabled in Setup.
+ //
+ if (PeiAmtPlatformPolicy->WatchDog == 1) {
+ Supported = TRUE;
+ }
+ }
+
+ return Supported;
+}
+
+/**
+ Get WatchDog BIOS Timmer.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval UINT16 WatchDog BIOS Timer
+**/
+UINT16
+PeiAmtWatchTimerBiosGet (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+{
+ EFI_STATUS Status;
+ PEI_AMT_PLATFORM_POLICY_PPI *PeiAmtPlatformPolicy;
+
+ Status = PeiAmtPolicyLibInit (PeiServices, &PeiAmtPlatformPolicy);
+ ASSERT_EFI_ERROR (Status);
+
+ return PeiAmtPlatformPolicy->WatchDogTimerBios;
+}
+
+/**
+ Check if AMT is enabled in setup options.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval FALSE ActiveManagement is disabled.
+ @retval TRUE ActiveManagement is enabled.
+**/
+BOOLEAN
+PeiAmtSupported (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+{
+ EFI_STATUS Status;
+ BOOLEAN Supported;
+ PEI_AMT_PLATFORM_POLICY_PPI *PeiAmtPlatformPolicy;
+
+ Status = PeiAmtPolicyLibInit (PeiServices, &PeiAmtPlatformPolicy);
+ ASSERT_EFI_ERROR (Status);
+
+ //
+ // First check if AMT support is enabled in Setup.
+ //
+ if (PeiAmtPlatformPolicy->iAmtEnabled == 1) {
+ Supported = TRUE;
+ } else {
+ Supported = FALSE;
+ }
+
+ return Supported;
+}
+
+/**
+ Check if ASF is enabled in setup options.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval FALSE ASF is disabled.
+ @retval TRUE ASF is enabled.
+**/
+BOOLEAN
+PeiAsfSupported (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+{
+ EFI_STATUS Status;
+ BOOLEAN Supported;
+ PEI_AMT_PLATFORM_POLICY_PPI *PeiAmtPlatformPolicy;
+
+ Status = PeiAmtPolicyLibInit (PeiServices, &PeiAmtPlatformPolicy);
+ ASSERT_EFI_ERROR (Status);
+
+ if (PeiAmtPlatformPolicy->Revision < PEI_AMT_PLATFORM_POLICY_PPI_REVISION_2) {
+ return FALSE;
+ }
+ //
+ // First check if ASF support is enabled in Setup.
+ //
+ if (PeiAmtPlatformPolicy->AsfEnabled == 1) {
+ Supported = TRUE;
+ } else {
+ Supported = FALSE;
+ }
+
+ return Supported;
+}
+
+/**
+ Provide Manageability Mode setting from MEBx BIOS Sync Data
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval UINT8 Manageability Mode = MNT_AMT or MNT_ASF
+**/
+UINT8
+ManageabilityModeSetting (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+{
+ EFI_STATUS Status;
+ PEI_AMT_PLATFORM_POLICY_PPI *PeiAmtPlatformPolicy;
+
+ Status = PeiAmtPolicyLibInit (PeiServices, &PeiAmtPlatformPolicy);
+ ASSERT_EFI_ERROR (Status);
+
+ if (PeiAmtPlatformPolicy->Revision < PEI_AMT_PLATFORM_POLICY_PPI_REVISION_2) {
+ return 0;
+ }
+
+ return (UINT8) (PeiAmtPlatformPolicy->ManageabilityMode);
+}
+
+/**
+ This will return progress event Option.
+ True if the option is enabled.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval True progress event is enabled.
+ @retval False progress event is disabled.
+**/
+BOOLEAN
+PeiFwProgressSupport (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+{
+ EFI_STATUS Status;
+ BOOLEAN Supported;
+ PEI_AMT_PLATFORM_POLICY_PPI *PeiAmtPlatformPolicy;
+
+ Status = PeiAmtPolicyLibInit (PeiServices, &PeiAmtPlatformPolicy);
+ ASSERT_EFI_ERROR (Status);
+
+ Supported = FALSE;
+
+ if (PeiAmtPlatformPolicy->Revision >= PEI_AMT_PLATFORM_POLICY_PPI_REVISION_3) {
+ //
+ // Check if progress event is enabled in Setup.
+ //
+ if (PeiAmtPlatformPolicy->FWProgress == 1) {
+ Supported = TRUE;
+ }
+ }
+
+ return Supported;
+}
diff --git a/ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.h b/ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.h
new file mode 100644
index 0000000..b7361f4
--- /dev/null
+++ b/ReferenceCode/ME/Library/AMT/Pei/AmtPolicyLibPei.h
@@ -0,0 +1,126 @@
+/** @file
+ Header file for PEI AMT Policy functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PEI_AMT_POLICY_LIB_H_
+#define _PEI_AMT_POLICY_LIB_H_
+
+#include EFI_PPI_DEFINITION (AmtPlatformPolicyPei)
+#include EFI_PPI_DEFINITION (AmtStatusCode)
+
+/**
+ Check if Amt is enabled in setup options.
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] PeiAmtPlatformPolicy The AMT Platform Policy protocol instance
+
+ @retval EFI_SUCCESS AMT platform policy Ppi located
+ @retval All other error conditions encountered result in an ASSERT.
+**/
+EFI_STATUS
+PeiAmtPolicyLibInit (
+ EFI_PEI_SERVICES **PeiServices,
+ PEI_AMT_PLATFORM_POLICY_PPI **PeiAmtPlatformPolicy
+ )
+;
+
+/**
+ Check if AMT WatchDog is enabled in setup options.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval FALSE AMT WatchDog is disabled.
+ @retval TRUE AMT WatchDog is enabled.
+**/
+BOOLEAN
+PeiAmtWatchDog (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+;
+
+/**
+ Get WatchDog BIOS Timmer.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval UINT16 WatchDog BIOS Timer
+**/
+UINT16
+PeiAmtWatchTimerBiosGet (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+;
+
+/**
+ Check if AMT is enabled in setup options.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval FALSE ActiveManagement is disabled.
+ @retval TRUE ActiveManagement is enabled.
+**/
+BOOLEAN
+PeiAmtSupported (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+;
+
+/**
+ Check if ASF is enabled in setup options.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval FALSE ASF is disabled.
+ @retval TRUE ASF is enabled.
+**/
+BOOLEAN
+PeiAsfSupported (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+;
+
+/**
+ Provide Manageability Mode setting from MEBx BIOS Sync Data
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval UINT8 Manageability Mode = MNT_AMT or MNT_ASF
+**/
+UINT8
+ManageabilityModeSetting (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+;
+
+/**
+ This will return progress event Option.
+ True if the option is enabled.
+
+ @param[in] PeiServices Point to Pei Services structure
+
+ @retval True progress event is enabled.
+ @retval False progress event is disabled.
+**/
+BOOLEAN
+PeiFwProgressSupport (
+ IN EFI_PEI_SERVICES **PeiServices
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/AtLibrary/AtLibrary.cif b/ReferenceCode/ME/Library/AtLibrary/AtLibrary.cif
new file mode 100644
index 0000000..1584c4d
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/AtLibrary.cif
@@ -0,0 +1,10 @@
+<component>
+ name = "AtLibrary"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\AtLibrary\"
+ RefName = "AtLibrary"
+[files]
+"AtLibrary.sdl"
+[parts]
+"AtDxeLib"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/AtLibrary/AtLibrary.sdl b/ReferenceCode/ME/Library/AtLibrary/AtLibrary.sdl
new file mode 100644
index 0000000..c712a95
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/AtLibrary.sdl
@@ -0,0 +1,20 @@
+TOKEN
+ Name = "AtLibrary_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable AmtLibDxe support in Project"
+End
+
+PATH
+ Name = "AtLibrary_DIR"
+ Help = "iAMT Library file source directory"
+End
+
+ELINK
+ Name = "/I$(AtLibrary_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.c b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.c
new file mode 100644
index 0000000..54b5959
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.c
@@ -0,0 +1,630 @@
+/** @file
+ AT authetication module for using AT DXE driver.
+ This driver uses the AT protocol, HECI Protocol and AT Platform Policy to implement Theft Deterrence Technology AM module.
+
+@copyright
+ Copyright (c) 2004 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+
+#include "AtAmHelper.h"
+
+const CHAR8 *PEMCodes = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-!=";
+const CHAR8 *LineBreak = " \n\t";
+
+/**
+ Convert Hex values into Base32 values
+
+ @param[in] encodedStr Array of encoded BASE values.
+ @param[in] encodedLen Length of encoded values.
+ @param[out] rawData Array of Hex strings that needs to be encoded into BASE32.
+ @param[out] rawDataLen Length of Hex values.
+
+ @retval EFI_BUFFER_TOO_SMALL Buffer to store encoded string too small.
+ @retval EFI_SUCCESS Initialization complete.
+**/
+EFI_STATUS
+Base32Encode (
+ IN UINT8 *encodedStr,
+ IN UINTN *encodedLen,
+ OUT UINT8 *rawData,
+ OUT UINTN rawDataLen
+ )
+{
+ UINTN i;
+ UINTN j;
+ UINT8 value;
+ INTN shift;
+ INTN shifttable[] = { 3, -2, 1, -4, -1, 2, -3, 0 };
+
+ if (encodedLen && *encodedLen < (rawDataLen * 8) / 5) {
+ DEBUG ((EFI_D_ERROR, "ATAm::Base32Encode: Buffer to store encoded string too small"));
+ return EFI_BUFFER_TOO_SMALL;
+ }
+
+ for (i = 0, j = 0; i < rawDataLen; j++) {
+ shift = shifttable[j % 8];
+ if (shift > 0) {
+ value = (UINT8) (rawData[i] >> shift);
+ } else {
+ value = (UINT8) (rawData[i] << (-shift));
+ if (i++ < rawDataLen - 1) {
+ value |= (rawData[i] >> (8 + shift));
+ }
+ }
+
+ value &= 0x1f;
+ if (25 >= value) {
+ value += 'A';
+ } else {
+ value += '2' - 26;
+ }
+
+ if (encodedStr && encodedLen) {
+ encodedStr[j] = value;
+ }
+ }
+
+ if (encodedStr && encodedLen) {
+ *encodedLen = j;
+ encodedStr[j] = L'\0';
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Convert Base32 values into Hex values.
+
+ @param[in] encodedStr Array of Decimal numbers.
+ @param[out] decodedData Converted Hex values.
+
+ @retval Length of the Hex Strings that expected.
+**/
+INTN
+Base32Decode (
+ IN UINT8 *encodedStr,
+ IN UINT8 *decodedData
+ )
+{
+ UINTN i;
+ UINTN j;
+ INTN retVal;
+ UINT8 value;
+ UINTN decodedLen;
+ INTN shifttable[] = { 3, -2, 1, -4, -1, 2, -3, 0 };
+ INTN shift;
+ UINTN encodedLen;
+
+ retVal = 1;
+ encodedLen = AsciiStrLen ((char *) encodedStr);
+
+ decodedLen = (encodedLen * 5) / 8;
+
+ decodedData[0] = 0;
+ for (i = 0, j = 0; i < encodedLen; i++) {
+ if ('A' <= encodedStr[i] && 'Z' >= encodedStr[i]) {
+ value = encodedStr[i] - 'A';
+ } else if ('a' <= encodedStr[i] && 'z' >= encodedStr[i]) {
+ value = encodedStr[i] - 'a';
+ } else if ('2' <= encodedStr[i] && '7' >= encodedStr[i]) {
+ value = encodedStr[i] - '2' + 26;
+ } else {
+ retVal = 0;
+ break;
+ }
+
+ shift = shifttable[i % 8];
+ if (shift > 0) {
+ decodedData[j] |= (value << shift);
+ } else {
+ decodedData[j] |= (value >> (-shift));
+ ///
+ /// Pack the bits that are going to fall off due to right shift in next byte
+ /// (left justfied) unless decoding the last character. In case of last
+ /// character, the extra bits are just padding to make the length of input
+ /// bits a multiple of 5 while encoding - so ignore them
+ ///
+ if (i != encodedLen - 1) {
+ decodedData[++j] = (UINT8) (value << (8 + shift));
+ }
+ }
+ }
+
+ return retVal;
+}
+
+/**
+ Decimal large (BASE10) into hex value.
+
+ @param[in][out] decStr Array of Decimal numbers.
+ @param[out] u8Hex Converted Hex values.
+ @param[in] hexIndex Length of the Hex Strings that expected
+
+ @retval None
+**/
+VOID
+DecimalToHexString (
+ IN OUT CHAR8 *decStr,
+ OUT UINT8 *u8Hex,
+ IN UINTN hexIndex
+ )
+{
+
+ UINTN i;
+ UINTN j;
+ UINTN Remainder;
+ CHAR8 Quotient;
+ UINTN num;
+ UINTN len;
+ UINTN leadingZero;
+
+ leadingZero = 1;
+
+ len = AsciiStrLen ((CHAR8 *) decStr);
+ Remainder = decStr[0] - '0';
+
+ if (len > 1) {
+ Remainder = Remainder * 10 + decStr[1] - '0';
+ }
+
+ if (len < 3) {
+ u8Hex[hexIndex] = (UINT8) Remainder;
+ return;
+ }
+
+ i = 2;
+ j = 0;
+ while (i < len) {
+ num = Remainder * 10 + decStr[i] - '0';
+ Quotient = (CHAR8) (num / 256);
+ if (!leadingZero || Quotient) {
+ decStr[j++] = '0' + Quotient;
+ leadingZero = 0;
+ }
+
+ Remainder = num % 256;
+ i++;
+
+ }
+
+ decStr[j] = L'\0';
+ u8Hex[hexIndex--] = (UINT8) Remainder;
+
+ if (decStr[0] != L'\0') {
+ DecimalToHexString (decStr, u8Hex, hexIndex);
+ }
+
+ return;
+}
+
+/**
+ Convert the CHAR8 ASCII into CHAR16 Unicode strings.
+
+ @param[in] AsciiString Ascii String.
+ @param[out] UnicodeString Buffer for converted Unicode string.
+
+ @retval None
+**/
+VOID
+Uint8ToUnicode (
+ IN CHAR8 *AsciiString,
+ OUT CHAR16 *UnicodeString
+ )
+{
+ UINT8 Index;
+
+ Index = 0;
+
+ while (AsciiString[Index] != 0) {
+ UnicodeString[Index] = (CHAR16) AsciiString[Index];
+ Index++;
+ }
+}
+
+/**
+ Decode a PEM-encoded character.
+
+ @param[in] pemChar PEM-encoded character.
+
+ @retval Value orresponding to the character, or PEM_INVALID_CHARACTER if the input character could not be decoded.
+**/
+UINT8
+DecodePEMChar (
+ IN UINT8 pemChar
+ )
+{
+ if ((pemChar >= 'A') && (pemChar <= 'Z')) {
+ return pemChar - 'A';
+ }
+
+ if ((pemChar >= 'a') && (pemChar <= 'z')) {
+ return (pemChar - 'a') + 26;
+ }
+
+ if ((pemChar >= '0') && (pemChar <= '9')) {
+ return (pemChar - '0') + 52;
+ }
+
+ if (pemChar == '-') {
+ return 62;
+ }
+
+ if (pemChar == '!') {
+ return 63;
+ }
+
+ if (pemChar == '=') {
+ return PEM_PAD_CHAR;
+
+ }
+
+ DEBUG ((EFI_D_ERROR, "DecodePEMChar: Invalid character %d\n", pemChar));
+ return PEM_INVALID_CHAR;
+}
+
+/**
+ Decode character in ASCII to hexadecimal
+
+ @param[in] base16char Character in ASCII
+
+ @retval Value in hexadecimal.
+**/
+UINT8
+DecodeBase16Char (
+ IN UINT8 base16char
+ )
+{
+ if (base16char >= '0' && base16char <= '9') {
+ return base16char - '0';
+ } else if (base16char >= 'A' && base16char <= 'F') {
+ return base16char - 'A' + 0xA;
+ } else if (base16char >= 'a' && base16char <= 'f') {
+ return base16char - 'a' + 0xA;
+ }
+
+ return 0;
+}
+
+/**
+ Decode ASCII string to hexadecimal string
+
+ @param[in] pString Pointer of ASCII string
+ @param[in] stringLen Size of the ASCII string
+ @param[out] pDecodedData Pointer of hexadecimal string
+ @param[out] pBufLength Pointer to buffer length returned
+
+ @retval FALSE Failed to decode the string by invalid length or buffer size
+ @retval TRUE The hexadecimal string returned
+**/
+BOOLEAN
+Base16Decode (
+ IN UINT8 *pString,
+ IN UINT32 stringLen,
+ OUT UINT8 *pDecodedData,
+ OUT UINT32 *pBufLength
+ )
+{
+ UINT32 i;
+ if (stringLen % 2 != 0) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode hexadecimal string -- invalid length\n"));
+ } else if (*pBufLength < stringLen / 2) {
+ DEBUG ((EFI_D_ERROR, "Base16 decode - output buffer too small\n"));
+ } else {
+ for (i = 0; i < (UINT32) stringLen / 2; i++) {
+ pDecodedData[i] = DecodeBase16Char (pString[2 * i]) << 4;
+ pDecodedData[i] |= DecodeBase16Char (pString[2 * i + 1]);
+ }
+
+ *pBufLength = i;
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+ Encode string to ASCII code
+
+ @param[in] pData Pointer of string to be encoded
+ @param[in] dataLength Size of the string to be
+ @param[out] pEncodedData Pointer of encoded string
+ @param[out] pBufLength Pointer to buffer length returned
+
+ @retval FALSE Failed to encode the string by invalid length or buffer size
+ @retval TRUE The encoded string returned
+**/
+BOOLEAN
+Base16Encode (
+ IN UINT8 *pData,
+ IN UINT32 dataLength,
+ OUT UINT8 *pEncodedData,
+ OUT UINT32 *pBufLength
+ )
+{
+ UINT32 i;
+ if (*pBufLength < 2 * dataLength) {
+ DEBUG ((EFI_D_ERROR, "Cannot encode data -- output buffer too small\n"));
+ return FALSE;
+ }
+
+ DEBUG ((EFI_D_ERROR, "Base16Encode dataLength : %d\n", dataLength));
+
+ for (i = 0; i < dataLength; i++) {
+ AsciiSPrint ((CHAR8 *) &pEncodedData[2 * i], 3 * sizeof (UINT8), "%02x", pData[i] & 0xFF);
+ }
+
+ DEBUG ((EFI_D_ERROR, "Base16Encode AsciiSPrint : %s\n", (char *) pEncodedData));
+ DEBUG ((EFI_D_ERROR, "Base16Encode Sprint : %s\n", (char *) pEncodedData));
+
+ *pBufLength = 2 * dataLength;
+
+ return TRUE;
+}
+
+/**
+ Decode PEM-Encoded data
+
+ @param[in] pPEMString Pointer to PEM-Encoded buffer
+ @param[in] lineLength Length in bytes
+ @param[in] pDecodedData Pointer to buffer to receive decoded bytes
+ @param[in] pBufLength Pointer to the size of the output buffer. Upon return this will
+ contain the length of the decoded data
+
+ @retval Returns status code indicating outcome of operation
+**/
+BOOLEAN
+PEMSMSDecode (
+ IN UINT8 *pPEMString,
+ IN UINT32 lineLength,
+ OUT UINT8 *pDecodedData,
+ OUT UINT32 *pBufLength
+ )
+{
+ UINT8 *pStr;
+ UINT32 curOutLen;
+ UINT8 *pOut;
+ UINT32 i;
+ UINT32 padBytes;
+ UINT8 val1;
+ UINT8 val2;
+ UINT8 decodedValue[4];
+ UINT32 ii;
+ UINT32 unitCount;
+ UINT32 decodedBytes;
+
+ pStr = pPEMString;
+ curOutLen = *pBufLength;
+ pOut = pDecodedData;
+ padBytes = 0;
+
+ if (pStr != NULL) {
+ if ((lineLength % 4) != 0) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode PEM string -- invalid length -1\n"));
+ return FALSE;
+ }
+
+ unitCount = lineLength / 4;
+
+ for (i = 0; (i < unitCount) && (padBytes == 0); i++) {
+ val1 = DecodePEMChar (*pStr++);
+ val2 = DecodePEMChar (*pStr++);
+
+ if ((val1 == PEM_INVALID_CHAR) || (val2 == PEM_INVALID_CHAR)) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode PEM string -- invalid character -2\n"));
+ return FALSE;
+ }
+
+ decodedValue[0] = ((val1 << 2) | (val2 >> 4));
+ val1 = DecodePEMChar (*pStr++);
+ if (val1 == PEM_INVALID_CHAR) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode PEM string -- invalid character -3\n"));
+ return FALSE;
+ }
+
+ if (val1 != PEM_PAD_CHAR) {
+ decodedValue[1] = ((val2 << 4) | (val1 >> 2));
+ val2 = DecodePEMChar (*pStr++);
+ if (val2 == PEM_INVALID_CHAR) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode PEM string -- invalid character -4\n"));
+ return FALSE;
+ }
+
+ if (val2 == PEM_PAD_CHAR) {
+ padBytes = 1;
+ } else {
+ decodedValue[2] = ((val1 << 6) | val2);
+ }
+ } else {
+ val2 = DecodePEMChar (*pStr++);
+ if (val2 != PEM_PAD_CHAR) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode PEM string -- invalid encoding -4\n"));
+ return FALSE;
+ }
+
+ padBytes = 2;
+ }
+
+ decodedBytes = (3 - padBytes);
+ if (curOutLen < decodedBytes) {
+ DEBUG ((EFI_D_ERROR, "Cannot decode PEM string -- out buffer too small-5\n"));
+ return FALSE;
+ }
+
+ for (ii = 0; ii < decodedBytes; ii++) {
+ pOut[ii] = decodedValue[ii];
+
+ }
+
+ curOutLen -= decodedBytes;
+ pOut += decodedBytes;
+ }
+ }
+
+ *pBufLength = *pBufLength - curOutLen;
+ return TRUE;
+}
+
+/**
+ Encoded data
+
+ @param[in] pData Pointer to buffer
+ @param[in] dataLength Length in bytes
+ @param[out] pPEMString Pointer to buffer to receive encoded bytes
+ @param[out] pBufLength Pointer to the size of the output buffer. Upon return this will
+ contain the length of the encoded data
+
+ @retval Returns status code indicating outcome of operation
+**/
+BOOLEAN
+PEMSMSEncode (
+ IN UINT8 *pData,
+ IN UINT32 dataLength,
+ OUT UINT8 *pPEMString,
+ OUT UINT32 *pBufLength
+ )
+{
+ UINT32 encodeUnits;
+ UINT32 paddedInputLength;
+ UINT32 padBytes;
+ UINT32 outLength;
+ UINT8 encodeBuf[3];
+ UINT32 i;
+ UINT8 *pOctet;
+ UINT32 ipos;
+ UINT32 opos;
+ UINT32 index;
+
+ encodeUnits = (dataLength + 2) / 3;
+ paddedInputLength = encodeUnits * 3;
+ padBytes = paddedInputLength - dataLength;
+ outLength = encodeUnits * 4;
+ pOctet = pData;
+ ipos = 0;
+ opos = 0;
+
+ outLength = encodeUnits * 4;
+ if (outLength % 64) {
+ outLength += ((outLength / 64) + 1);
+ } else {
+ outLength += (outLength / 64);
+
+ }
+
+ outLength++;
+ DEBUG ((EFI_D_ERROR, "ATAM: Pbuflength: %d OutLength: %d \n", *pBufLength, outLength));
+ if (*pBufLength < outLength) {
+ DEBUG ((EFI_D_ERROR, "ATAM: Failed \n"));
+ return FALSE;
+ }
+
+ for (i = 0; i < encodeUnits; i++) {
+ if ((i == encodeUnits - 1) && (padBytes > 0)) {
+ //
+ // Encode last piece, with padding
+ //
+ encodeBuf[0] = *pOctet++;
+ encodeBuf[1] = (padBytes == 1) ? encodeBuf[1] = *pOctet++ : 0;
+ encodeBuf[2] = 0;
+ ipos += (3 - padBytes);
+
+ index = encodeBuf[0] >> 2;
+ pPEMString[opos++] = PEMCodes[index];
+ index = ((encodeBuf[0] & 0x03) << 4) | (encodeBuf[1] >> 4);
+ pPEMString[opos++] = PEMCodes[index];
+
+ if (padBytes == 1) {
+ index = ((encodeBuf[1] & 0x0f) << 2) | (encodeBuf[2] >> 6);
+ pPEMString[opos++] = PEMCodes[index];
+ pPEMString[opos++] = '=';
+ } else {
+ pPEMString[opos++] = '=';
+ pPEMString[opos++] = '=';
+ }
+ } else {
+ //
+ // Encode next 3 bytes
+ //
+ encodeBuf[0] = *pOctet++;
+ encodeBuf[1] = *pOctet++;
+ encodeBuf[2] = *pOctet++;
+ ipos += 3;
+ index = encodeBuf[0] >> 2;
+ pPEMString[opos++] = PEMCodes[index];
+ index = ((encodeBuf[0] & 0x03) << 4) | (encodeBuf[1] >> 4);
+ pPEMString[opos++] = PEMCodes[index];
+ index = ((encodeBuf[1] & 0x0f) << 2) | (encodeBuf[2] >> 6);
+ pPEMString[opos++] = PEMCodes[index];
+ index = encodeBuf[2] & 0x3f;
+ pPEMString[opos++] = PEMCodes[index];
+ }
+ }
+
+ pPEMString[opos] = 0;
+ *pBufLength = opos;
+
+ return TRUE;
+}
+
+#ifdef EFI_DEBUG
+
+/**
+ This routine displays the debug message in ASCII
+
+ @param[in] Message Message to be displayed
+ @param[in] Length Length of the message
+
+ @retval None
+**/
+VOID
+ShowBuffer (
+ IN UINT8 *Message,
+ IN UINT32 Length
+ )
+{
+ UINT32 LineBreak;
+ UINT32 Index;
+ LineBreak = 0;
+ Index = 0;
+
+ while (Length-- > 0) {
+ if (LineBreak == 0) {
+ DEBUG ((EFI_D_ERROR, "%02x: ", (Index & 0xF0)));
+ }
+
+ DEBUG ((EFI_D_ERROR, "%02x ", Message[Index++]));
+ LineBreak++;
+ if (LineBreak == 16) {
+ DEBUG ((EFI_D_ERROR, "\n"));
+ LineBreak = 0;
+ }
+
+ if (LineBreak == 8) {
+ DEBUG ((EFI_D_ERROR, "- "));
+ }
+ }
+
+ DEBUG ((EFI_D_ERROR, "\n"));
+ return ;
+}
+
+#endif // End Of EFI_DEBUG
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.h b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.h
new file mode 100644
index 0000000..43f2ffe
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtAmHelper.h
@@ -0,0 +1,119 @@
+/** @file
+ AT authetication module for using AT DXE driver.
+ This library is utilized by the AT and related drivers to implement Theft Deterrence Technology AM module.
+
+@copyright
+ Copyright (c) 2004-2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+#ifndef _ATAM_HELPER_H_
+#define _ATAM_HELPER_H_
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#endif
+#include "Tiano.h"
+
+#define PEM_LINE_SIZE 64
+#define PEM_INPUT_LINE_SIZE 48
+#define PEM_UNITS_PER_LINE (PEM_INPUT_LINE_SIZE / 3)
+#define PEM_DECODED_LINE_SIZE 48
+#define PEM_INVALID_CHAR 255
+#define PEM_PAD_CHAR 64
+
+/**
+ Convert Hex values into Base32 values
+
+ @param[in] encodedStr Array of encoded BASE values.
+ @param[in] encodedLen Length of encoded values.
+ @param[out] rawData Array of Hex strings that needs to be encoded into BASE32.
+ @param[out] rawDataLen Length of Hex values.
+
+ @retval EFI_BUFFER_TOO_SMALL Buffer to store encoded string too small.
+ @retval EFI_SUCCESS Initialization complete.
+**/
+EFI_STATUS
+Base32Encode (
+ IN UINT8 *encodedStr,
+ IN UINTN *encodedLen,
+ OUT UINT8 *rawData,
+ OUT UINTN rawDataLen
+ )
+;
+
+/**
+ Convert Base32 values into Hex values.
+
+ @param[in] encodedStr Array of Decimal numbers.
+ @param[out] decodedData Converted Hex values.
+
+ @retval Length of the Hex Strings that expected.
+**/
+INTN
+Base32Decode (
+ IN UINT8 *encodedStr,
+ IN UINT8 *decodedData
+ )
+;
+
+/**
+ Decimal large (BASE10) into hex value.
+
+ @param[in][out] decStr Array of Decimal numbers.
+ @param[out] u8Hex Converted Hex values.
+ @param[in] hexIndex Length of the Hex Strings that expected
+
+ @retval None
+**/
+VOID
+DecimalToHexString (
+ IN OUT CHAR8 *decStr,
+ OUT UINT8 *u8Hex,
+ IN UINTN hexIndex
+ )
+;
+
+/**
+ Convert the CHAR8 ASCII into CHAR16 Unicode strings.
+
+ @param[in] AsciiString Ascii String.
+ @param[out] UnicodeString Buffer for converted Unicode string.
+
+ @retval None
+**/
+VOID
+Uint8ToUnicode (
+ IN CHAR8 *AsciiString,
+ OUT CHAR16 *UnicodeString
+)
+;
+
+/**
+ This routine displays the debug message in ASCII
+
+ @param[in] Message Message to be displayed
+ @param[in] Length Length of the message
+
+ @retval None
+**/
+VOID
+ShowBuffer (
+ IN UINT8 *Message,
+ IN UINT32 Length
+ )
+;
+
+#endif // _ATAM_HELPER_H_
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.cif b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.cif
new file mode 100644
index 0000000..f7268fd
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.cif
@@ -0,0 +1,14 @@
+<component>
+ name = "AtDxeLib"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\AtLibrary\Dxe\"
+ RefName = "AtDxeLib"
+[files]
+"AtDxeLib.mak"
+"AtDxeLib.sdl"
+"AtAmHelper.c"
+"AtDxeLib.inf"
+"AtPolicyDebugDumpDxe.c"
+"AtAmHelper.h"
+"AtPolicyLib.h"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.inf b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.inf
new file mode 100644
index 0000000..e99a072
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.inf
@@ -0,0 +1,69 @@
+## @file
+# Component description file for AT functionality
+#
+#@copyright
+# Copyright (c) 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = AtDxeLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ AtAmHelper.c
+ AtAmHelper.h
+ AtPolicyLib.h
+ AtPolicyDebugDumpDxe.c
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+
+#
+# Typically the sample code referenced will be available in the code base already
+# So keep this include at the end to defer to the source base definition
+# and only use the sample code definition if source base does not include these files.
+#
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ MeLib
+ MeProtocolLib
+ EdkIIGlueBaseMemoryLib
+ EdkIIGlueUefiRuntimeServicesTableLib
+ EdkIIGlueUefiBootServicesTableLib
+ EdkIIGlueBasePciLibPciExpress
+ EdkIIGlueDxeDebugLibReportStatusCode
+ EdkIIGlueDxeReportStatusCodeLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_DXE_REPORT_STATUS_CODE_LIB__ \
+ -D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__ \
+ -D __EDKII_GLUE_UEFI_RUNTIME_SERVICES_TABLE_LIB__
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.mak b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.mak
new file mode 100644
index 0000000..67282e9
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.mak
@@ -0,0 +1,54 @@
+# /*++
+# Copyright (c) 2009 Intel Corporation. All rights reserved.
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+# --*/
+# MAK file for the ModulePart:AtDxeLib
+all : AtDxeLib
+
+$(BUILD_DIR)\AtDxeLib.lib : AtDxeLib
+
+AtDxeLib : $(BUILD_DIR)\AtDxeLib.mak AtDxeLibBin
+
+$(BUILD_DIR)\AtDxeLib.mak : $(AtDxeLib_DIR)\$(@B).cif $(AtDxeLib_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(AtDxeLib_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+AtDxeLib_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES) \
+ $(ME_INCLUDES)\
+
+AtDxeLib_DEFINES=\
+ $(MY_DEFINES)\
+ /D __EDKII_GLUE_BASE_MEMORY_LIB__\
+ /D __EDKII_GLUE_EDK_DXE_RUNTIME_DRIVER_LIB__\
+ /D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__\
+
+AtDxeLib_LIBS=\
+ $(MeProtocolLib_LIB)\
+ $(MeLibDxe_LIB)
+
+AtDxeLibBin : $(AtDxeLib_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ /f $(BUILD_DIR)\AtDxeLib.mak all \
+ "MY_INCLUDES=$(AtDxeLib_INCLUDES)" \
+ "MY_DEFINES=$(AtDxeLib_DEFINES)"\
+ TYPE=LIBRARY \
+#**********************************************************************
+#**********************************************************************
+#** **
+#** (C)Copyright 1985-2006, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 6145-F Northbelt Pkwy, Norcross, GA 30071 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#**********************************************************************
+#**********************************************************************
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.sdl b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.sdl
new file mode 100644
index 0000000..746b618
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtDxeLib.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "AtDxeLib_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable AtDxeLib support in Project"
+End
+
+MODULE
+ Help = "Includes AtDxeLib.mak to Project"
+ File = "AtDxeLib.mak"
+End
+
+PATH
+ Name = "AtDxeLib_DIR"
+ Help = "iAMT Library file source directory"
+End
+
+ELINK
+ Name = "AtDxeLib_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\AtDxeLib.lib"
+ Parent = "AtDxeLib_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(AtDxeLib_DIR)"
+ Parent = "AT_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyDebugDumpDxe.c b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyDebugDumpDxe.c
new file mode 100644
index 0000000..699ed1b
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyDebugDumpDxe.c
@@ -0,0 +1,51 @@
+/** @file
+ Dump whole DXE_AT_POLICY_PROTOCOL and serial out.
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "AtPolicyLib.h"
+#endif
+
+extern DXE_AT_POLICY_PROTOCOL *mDxePlatformAtPolicy;
+
+/**
+ Dump DXE AT Platform Policy
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+DxeAtPolicyDebugDump (
+ VOID
+ )
+{
+ if (mDxePlatformAtPolicy == NULL) {
+ return;
+ }
+ DEBUG ((EFI_D_INFO, "\n------------------------ AtPlatformPolicy Dump Begin ------------------\n"));
+ DEBUG ((EFI_D_INFO, " Revision : 0x%x\n", mDxePlatformAtPolicy->Revision));
+ DEBUG ((EFI_D_INFO, "At ---\n"));
+ DEBUG ((EFI_D_INFO, " AtConfig : 0x%x\n", mDxePlatformAtPolicy->At.AtAmBypass));
+ DEBUG ((EFI_D_INFO, " AtEnterSuspendState : 0x%x\n", mDxePlatformAtPolicy->At.AtEnterSuspendState));
+ DEBUG ((EFI_D_INFO, "\n------------------------ AtPlatformPolicy Dump End --------------------\n"));
+}
+
diff --git a/ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyLib.h b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyLib.h
new file mode 100644
index 0000000..edde46a
--- /dev/null
+++ b/ReferenceCode/ME/Library/AtLibrary/Dxe/AtPolicyLib.h
@@ -0,0 +1,39 @@
+/** @file
+ Header file for AT Policy functionality
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _AT_POLICY_LIB_H_
+#define _AT_POLICY_LIB_H_
+
+#include EFI_PROTOCOL_DEFINITION (AtPlatformPolicy)
+
+/**
+ Dump DXE AT Platform Policy
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+DxeAtPolicyDebugDump (
+ VOID
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.c b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.c
new file mode 100644
index 0000000..aac3afb
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.c
@@ -0,0 +1,112 @@
+/** @file
+ Me Chipset Lib implementation.
+
+@copyright
+ Copyright (c) 2004 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#include "MeAccess.h"
+#include "PchPlatformLib.h"
+#endif
+
+/**
+ Enable/Disable Me devices
+
+ @param[in] WhichDevice Select of Me device
+ @param[in] DeviceFuncCtrl Function control
+
+ @retval None
+**/
+VOID
+MeDeviceControl (
+ IN ME_DEVICE WhichDevice,
+ IN ME_DEVICE_FUNC_CTRL DeviceFuncCtrl
+ )
+{
+ switch (WhichDevice) {
+ case HECI1:
+ case HECI2:
+ case IDER:
+ case SOL:
+ if (DeviceFuncCtrl) {
+ Mmio16And (PCH_RCRB_BASE, R_PCH_RCRB_FD2, ~(BIT0 << WhichDevice));
+ } else {
+ Mmio16Or (PCH_RCRB_BASE, R_PCH_RCRB_FD2, BIT0 << WhichDevice);
+ }
+ Mmio16 (PCH_RCRB_BASE, R_PCH_RCRB_FD2);
+ break;
+
+ case USBR1:
+ if (DeviceFuncCtrl) {
+ MmioOr16 (
+ MmPciAddress (0,
+ DEFAULT_PCI_BUS_NUMBER_PCH,
+ PCI_DEVICE_NUMBER_PCH_USB,
+ PCI_FUNCTION_NUMBER_PCH_EHCI,
+ 0x7A),
+ (UINT16) (0x100)
+ );
+ } else {
+ MmioAnd16 (
+ MmPciAddress (0,
+ DEFAULT_PCI_BUS_NUMBER_PCH,
+ PCI_DEVICE_NUMBER_PCH_USB,
+ PCI_FUNCTION_NUMBER_PCH_EHCI,
+ 0x7A),
+ (UINT16) (~0x100)
+ );
+ }
+ break;
+
+ case USBR2:
+ if (GetPchSeries() == PchH) {
+ if (DeviceFuncCtrl) {
+ MmioOr16 (
+ MmPciAddress (0,
+ DEFAULT_PCI_BUS_NUMBER_PCH,
+ PCI_DEVICE_NUMBER_PCH_USB_EXT,
+ PCI_FUNCTION_NUMBER_PCH_EHCI2,
+ 0x7A),
+ (UINT16) (0x100)
+ );
+ } else {
+ MmioAnd16 (
+ MmPciAddress (0,
+ DEFAULT_PCI_BUS_NUMBER_PCH,
+ PCI_DEVICE_NUMBER_PCH_USB_EXT,
+ PCI_FUNCTION_NUMBER_PCH_EHCI2,
+ 0x7A),
+ (UINT16) (~0x100)
+ );
+ }
+ }
+ break;
+
+ ///
+ /// Function Disable SUS well lockdown
+ ///
+ case FDSWL:
+ if (DeviceFuncCtrl) {
+ Mmio16Or (PCH_RCRB_BASE, R_PCH_RCRB_FDSW, (UINT16) B_PCH_RCRB_FDSW_FDSWL);
+ } else {
+ Mmio16And (PCH_RCRB_BASE, R_PCH_RCRB_FDSW, (UINT16)~(B_PCH_RCRB_FDSW_FDSWL));
+ }
+ Mmio16 (PCH_RCRB_BASE, R_PCH_RCRB_FDSW);
+ break;
+ }
+} \ No newline at end of file
diff --git a/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.cif b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.cif
new file mode 100644
index 0000000..d4962a1
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.cif
@@ -0,0 +1,11 @@
+<component>
+ name = "MeChipsetLib"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\MeKernel\Common\MeChipsetLib\"
+ RefName = "MeChipsetLib"
+[files]
+"MeChipsetLib.mak"
+"MeChipsetLib.sdl"
+"MeChipsetLib.c"
+"MeChipsetLib.inf"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.inf b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.inf
new file mode 100644
index 0000000..aa44c98
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.inf
@@ -0,0 +1,61 @@
+## @file
+# Component description file for PEI/DXE ME Chipset Lib
+#
+#@copyright
+# Copyright (c) 1999 - 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = MeChipsetLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ MeChipsetLib.c
+
+[sources.ia32]
+
+[sources.x64]
+
+[sources.ipf]
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Include
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include/Library
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ MeProtocolLib
+ PchPlatformLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__ \
+ -D __EDKII_GLUE_UEFI_RUNTIME_SERVICES_TABLE_LIB__
diff --git a/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.mak b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.mak
new file mode 100644
index 0000000..91ac39a
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.mak
@@ -0,0 +1,53 @@
+# MAK file for the ModulePart:MeChipsetLib
+EDK : MeChipsetLib
+
+MeChipsetLib : MeChipsetSmmLib MeChipsetDxeLib MeChipsetPeiLib
+
+$(MeChipsetSmmLib_LIB) : MeChipsetSmmLib
+$(MeChipsetDxeLib_LIB) : MeChipsetDxeLib
+$(MeChipsetPeiLib_LIB) : MeChipsetPeiLib
+
+MeChipsetSmmLib : $(BUILD_DIR)\MeChipsetLib.mak MeChipsetLibSmmBin
+
+MeChipsetDxeLib : $(BUILD_DIR)\MeChipsetLib.mak MeChipsetLibDxeBin
+
+MeChipsetPeiLib : $(BUILD_DIR)\MeChipsetLib.mak MeChipsetLibPeiBin
+
+$(BUILD_DIR)\MeChipsetLib.mak : $(MeChipsetLib_DIR)\$(@B).cif $(MeChipsetLib_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(MeChipsetLib_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+MeChipsetLib_INCLUDES =\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES) \
+ $(ME_INCLUDES) \
+ $(INTEL_PCH_INCLUDES)
+
+MeChipsetLibSmmBin :
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS)\
+ /f $(BUILD_DIR)\MeChipsetLib.mak all\
+ "MY_INCLUDES=$(MeChipsetLib_INCLUDES)" \
+ TYPE=LIBRARY \
+ LIBRARIES=\
+ LIBRARY_NAME=$(MeChipsetSmmLib_LIB)
+
+MeChipsetLibDxeBin :
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS)\
+ /f $(BUILD_DIR)\MeChipsetLib.mak all\
+ "MY_INCLUDES=$(MeChipsetLib_INCLUDES)" \
+ "CFLAGS=$(CFLAGS) $(MeChipsetLib_DEFINES)"\
+ TYPE=LIBRARY \
+ LIBRARIES=\
+ LIBRARY_NAME=$(MeChipsetDxeLib_LIB)
+
+MeChipsetLibPeiBin :
+!IF "$(x64_BUILD)"=="1"
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) BUILD_DIR=$(BUILD_DIR)\IA32\
+!ELSE
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS)\
+!ENDIF
+ /f $(BUILD_DIR)\MeChipsetLib.mak all\
+ "MY_INCLUDES=$(MeChipsetLib_INCLUDES)"\
+ "CFLAGS=$(CFLAGS) $(MeChipsetLib_DEFINES)"\
+ TYPE=PEI_LIBRARY \
+ LIBRARIES=\
+ LIBRARY_NAME=$(MeChipsetPeiLib_LIB)
diff --git a/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.sdl b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.sdl
new file mode 100644
index 0000000..a668016
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Common/MeChipsetLib/MeChipsetLib.sdl
@@ -0,0 +1,70 @@
+TOKEN
+ Name = "MeChipsetLib_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable MeChipsetLib support in Project"
+End
+
+MODULE
+ Help = "Includes MeChipsetLib.mak to Project"
+ File = "MeChipsetLib.mak"
+End
+
+PATH
+ Name = "MeChipsetLib_DIR"
+ Help = "Me Chipset Library file source directory"
+End
+
+ELINK
+ Name = "MeChipsetPeiLib_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\MeChipsetPeiLib.lib"
+ Parent = "MeChipsetPeiLib_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MeChipsetLib_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "MeChipsetDxeLib_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\MeChipsetDxeLib.lib"
+ Parent = "MeChipsetDxeLib_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MeChipsetLib_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "MeChipsetSmmLib_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\MeChipsetSmmLib.lib"
+ Parent = "MeChipsetSmmLib_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MeChipsetLib_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.c b/ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.c
new file mode 100644
index 0000000..fd83e9b
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.c
@@ -0,0 +1,2702 @@
+/** @file
+ Implementation file for Heci Message functionality
+
+@copyright
+ Copyright (c) 2006 - 2013 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "HeciMsgLib.h"
+#include "MeAccess.h"
+#include "HeciRegs.h"
+#include "CoreBiosMsg.h"
+#include EFI_PROTOCOL_CONSUMER (Wdt)
+#include EFI_PROTOCOL_CONSUMER (PchReset)
+#endif
+
+BOOLEAN
+IsAfterEndOfPost (
+ VOID
+ );
+
+//
+// Internal function for HeciMsgLib used only
+//
+
+/**
+ Convert EFI Status Code severity to Mdes severity.
+
+ @param[in] statusToConv EFI Status Code severity.
+
+ @retval UINT16 Mdes severity.
+**/
+STATIC
+UINT16
+BiosToMdesSeverity (
+ IN EFI_STATUS statusToConv
+ )
+{
+ UINT16 MdesSev;
+
+ MdesSev = SEV_NO_ERROR;
+ switch (statusToConv & EFI_STATUS_CODE_SEVERITY_MASK) {
+ case (EFI_ERROR_MINOR):
+ MdesSev = SEV_LOW_ERROR;
+ break;
+
+ case (EFI_ERROR_MAJOR):
+ MdesSev = SEV_HIGH_ERROR;
+ break;
+
+ case (EFI_ERROR_UNRECOVERED):
+ MdesSev = SEV_CRITICAL_ERROR;
+ break;
+
+ case (EFI_ERROR_UNCONTAINED):
+ MdesSev = SEV_CRITICAL_ERROR;
+ break;
+ }
+
+ return MdesSev;
+}
+
+//
+// Interface functions of HeciMsgLib
+//
+
+/**
+ Send the required system ChipsetInit Table to ME FW.
+
+ @param[in] ChipsetInitTable The required system ChipsetInit Table.
+ @param[in] ChipsetInitTableLen Length of the table in bytes
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciChipsetInitSyncMsg (
+ IN UINT8 *ChipsetInitTable,
+ IN UINT32 ChipsetInitTableLen
+ )
+{
+ EFI_HECI_PROTOCOL *Heci;
+ EFI_STATUS Status;
+ UINT32 ReqSize;
+ PCH_RESET_PROTOCOL *PchResetProtocol;
+ EFI_GUID PchResetProtocolGuid = PCH_RESET_PROTOCOL_GUID;
+ MPHY_WRITE_SETTINGS_REQ *MPhyWriteSettingsReqPtr;
+
+ DEBUG ((EFI_D_ERROR, "HeciChipsetInitSyncMsg(0x%08X, %d): Start\n", ChipsetInitTable, ChipsetInitTableLen));
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8130);
+ ASSERT(ChipsetInitTableLen <= 1024); // ChipsetInit table should not get too large
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "EfiHeciProtocol not found.\n"));
+ return Status;
+ }
+
+ Status = gBS->LocateProtocol (
+ &PchResetProtocolGuid,
+ NULL,
+ (VOID **) &PchResetProtocol);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "PchResetProtocol not found.\n"));
+ return Status;
+ }
+
+ //
+ // Allocate a buffer for the Request Structure and the ChipsetInit Table
+ //
+ ReqSize = sizeof (MPHY_WRITE_SETTINGS_REQ) + ChipsetInitTableLen;
+ MPhyWriteSettingsReqPtr = AllocateZeroPool (ReqSize);
+ if (MPhyWriteSettingsReqPtr == NULL) {
+ DEBUG ((EFI_D_ERROR, "(MPHY) HeciChipsetInitSyncMsg: Could not allocate Memory\n"));
+ return EFI_ABORTED;
+ }
+
+ //
+ // Setup the HECI message for a MPHY Write
+ //
+ MPhyWriteSettingsReqPtr->Header.ApiVersion = LYNX_POINT_PLATFORM;
+ MPhyWriteSettingsReqPtr->Header.IccCommand = WRITE_MPHY_SETTINGS;
+ MPhyWriteSettingsReqPtr->Header.BufferLength = ReqSize - sizeof (ICC_HEADER);
+ MPhyWriteSettingsReqPtr->PostedWrite = FALSE;
+ CopyMem (MPhyWriteSettingsReqPtr+1, ChipsetInitTable, ChipsetInitTableLen);
+
+ DEBUG ((EFI_D_ERROR, "(MPHY) mPhyChipsetInitTable[] = \n"));
+ DEBUG ((EFI_D_ERROR, " Ver=%d CRC=0x%04X NumEntries=%d\n",
+ *((UINT16*)&ChipsetInitTable[2]), *((UINT16*)&ChipsetInitTable[0]), ChipsetInitTable[4]));
+ #ifdef EFI_DEBUG
+ {
+ int ii;
+ UINT8* entry_ptr = &ChipsetInitTable[5];
+ for (ii = 0; ii < ChipsetInitTable[4]; ii++) {
+ DEBUG ((EFI_D_ERROR, " %d: EP=0x%02X OFFSET=0x%04X VALUE=0x%08X\n",
+ ii, entry_ptr[6],*((UINT16*)&entry_ptr[0]),*((UINT32*)&entry_ptr[2])));
+ entry_ptr += 7;
+ }
+ }
+ #endif
+
+ //
+ // Send ChipsetInit Table to ME
+ //
+ Status = Heci->SendwACK (
+ (UINT32 *)MPhyWriteSettingsReqPtr,
+ ReqSize,
+ &ReqSize,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ICC_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_INFO, "(MPHY) Write MPHY Settings Message failed! EFI_STATUS = %r\n", Status));
+ }
+ else if (MPhyWriteSettingsReqPtr->Header.IccResponse != ICC_STATUS_SUCCESS) {
+ DEBUG ((EFI_D_ERROR,"(MPHY) Write MPHY Settings failed!: FW Response=0x%x\n",MPhyWriteSettingsReqPtr->Header.IccResponse));
+ Status = EFI_DEVICE_ERROR;
+ }
+
+ FreePool (MPhyWriteSettingsReqPtr);
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8140);
+ return Status;
+ }
+
+ if (PchResetProtocol != NULL) {
+ DEBUG ((EFI_D_ERROR, "HeciChipsetInitSyncMsg(): Reset required for ChipsetInit Settings synch\n"));
+ PchResetProtocol->Reset (PchResetProtocol, ColdReset);
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8140);
+ DEBUG ((EFI_D_ERROR, "HeciChipsetInitSyncMsg(): End\n"));
+ return Status;
+}
+
+//
+// Interface functions of HeciMsgLib
+//
+
+/**
+ Send Core BIOS Reset Request Message through HECI to reset the system.
+
+ @param[in] ResetOrigin Reset source
+ @param[in] ResetType Global or Host reset
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciSendCbmResetRequest (
+ IN UINT8 ResetOrigin,
+ IN UINT8 ResetType
+ )
+{
+ EFI_HECI_PROTOCOL *Heci;
+ EFI_STATUS Status;
+ UINT32 HeciLength;
+ CBM_RESET_REQ CbmResetRequest;
+ PLATFORM_ME_HOOK_PROTOCOL *PlatformMeHook;
+ EFI_GUID WdtProtocolGuid = WDT_PROTOCOL_GUID;
+ WDT_PROTOCOL *WdtProtocol;
+ UINT32 MeMode;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gPlatformMeHookProtocolGuid,
+ NULL,
+ (VOID **) &PlatformMeHook
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Locate PlatformMeHook Protocol for Global Reset Hook, so skip instead.- %r\n", Status));
+ } else {
+ PlatformMeHook->PreGlobalReset ();
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ CbmResetRequest.MKHIHeader.Data = 0;
+ CbmResetRequest.MKHIHeader.Fields.Command = CBM_RESET_REQ_CMD;
+ CbmResetRequest.MKHIHeader.Fields.IsResponse = 0;
+ CbmResetRequest.MKHIHeader.Fields.GroupId = MKHI_CBM_GROUP_ID;
+ CbmResetRequest.MKHIHeader.Fields.Reserved = 0;
+ CbmResetRequest.MKHIHeader.Fields.Result = 0;
+ CbmResetRequest.Data.RequestOrigin = ResetOrigin;
+ CbmResetRequest.Data.ResetType = ResetType;
+
+ HeciLength = sizeof (CBM_RESET_REQ);
+
+ Status = gBS->LocateProtocol (&WdtProtocolGuid, NULL, (VOID **) &WdtProtocol);
+ ASSERT_EFI_ERROR (Status);
+ WdtProtocol->AllowKnownReset ();
+
+ Status = Heci->SendMsg (
+ (UINT32 *) &CbmResetRequest,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Send Reset Request - %r\n", Status));
+ }
+
+ return Status;
+}
+
+/**
+ Send Hardware Asset Tables to Firmware
+
+ @param[in] Handle A handle for this module
+ @param[in] AssetTableData Hardware Asset Table Data
+ @param[in] TableDataSize Size of Asset table
+
+ @retval EFI_SUCCESS Table sent
+ @retval EFI_ABORTED Could not allocate Memory
+**/
+EFI_STATUS
+HeciAssetUpdateFwMsg (
+ IN EFI_HANDLE Handle,
+ IN TABLE_PUSH_DATA *AssetTableData,
+ IN UINT16 TableDataSize
+ )
+{
+ AU_TABLE_PUSH_MSG *SendAssetTableDataMsg;
+ EFI_STATUS Status;
+ EFI_HECI_PROTOCOL *Heci;
+
+ Status = EFI_SUCCESS;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+ ///
+ /// Subtract off single byte from TABLE_PUSH_DATA.TableData[1]
+ ///
+ SendAssetTableDataMsg = AllocateZeroPool (sizeof (AU_TABLE_PUSH_MSG) + MAX_ASSET_TABLE_ALLOCATED_SIZE - 1);
+ if (SendAssetTableDataMsg == NULL) {
+ DEBUG ((EFI_D_ERROR, "AssetUpdateFwMsg Error: Could not allocate Memory\n"));
+ return EFI_ABORTED;
+ }
+
+ if (TableDataSize > MAX_ASSET_TABLE_ALLOCATED_SIZE) {
+ TableDataSize = MAX_ASSET_TABLE_ALLOCATED_SIZE;
+ }
+
+ SendAssetTableDataMsg->Header.Data = 0;
+ ///
+ /// Subtract off single byte from TABLE_PUSH_DATA.TableData[1]
+ ///
+ SendAssetTableDataMsg->Header.Fields.MessageLength = TableDataSize + sizeof (TABLE_PUSH_DATA) - 1;
+ SendAssetTableDataMsg->Header.Fields.Command = HWA_TABLE_PUSH_CMD;
+ SendAssetTableDataMsg->Header.Fields.FRUTablePresent = 1;
+ SendAssetTableDataMsg->Header.Fields.SMBIOSTablePresent = 1;
+ SendAssetTableDataMsg->Header.Fields.ASFTablePresent = 1;
+ if (AssetTableData->Tables[HWAI_TABLE_TYPE_INDEX_MEDIA_DEVICE].Length == 0) {
+ SendAssetTableDataMsg->Header.Fields.MediaTablePresent = 0;
+ } else {
+ SendAssetTableDataMsg->Header.Fields.MediaTablePresent = 1;
+ }
+
+ CopyMem (&SendAssetTableDataMsg->Data, AssetTableData, SendAssetTableDataMsg->Header.Fields.MessageLength);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8020);
+ Status = Heci->SendMsg (
+ (UINT32 *) SendAssetTableDataMsg,
+ SendAssetTableDataMsg->Header.Fields.MessageLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_HWA_CLIENT_ID
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "AssetUpdateFwMsg: Failed to Send SendAssetTableDataMsg\n"));
+
+ }
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8021);
+
+ FreePool (SendAssetTableDataMsg);
+
+ return Status;
+
+}
+
+/**
+ Send End of Post Request Message through HECI.
+
+ @param[in] Handle A handle for this module
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciSendEndOfPostMessage (
+ IN EFI_HANDLE Handle
+ )
+{
+ EFI_STATUS Status;
+ UINT32 HeciSendLength;
+ UINT32 HeciRecvLength;
+ GEN_END_OF_POST_ACK CbmEndOfPost;
+ UINT32 MeMode;
+ EFI_HECI_PROTOCOL *Heci;
+ PCH_RESET_PROTOCOL *PchResetProtocol;
+ EFI_GUID PchResetProtocolGuid = PCH_RESET_PROTOCOL_GUID;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = gBS->LocateProtocol (&PchResetProtocolGuid, NULL, (VOID **) &PchResetProtocol);
+
+ if (EFI_ERROR (Status)) {
+ PchResetProtocol = NULL;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ CbmEndOfPost.Header.Data = 0;
+ CbmEndOfPost.Header.Fields.Command = CBM_END_OF_POST_CMD;
+ CbmEndOfPost.Header.Fields.IsResponse = 0;
+ CbmEndOfPost.Header.Fields.GroupId = MKHI_GEN_GROUP_ID;
+ CbmEndOfPost.Data.RequestedActions = 0;
+
+ HeciSendLength = sizeof (MKHI_MESSAGE_HEADER);
+ HeciRecvLength = sizeof (GEN_END_OF_POST_ACK);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8030);
+ Status = Heci->SendMsg (
+ (UINT32 *) &CbmEndOfPost,
+ HeciSendLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+
+ if (EFI_ERROR(Status)) {
+ return Status;
+ }
+
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &CbmEndOfPost,
+ &HeciRecvLength
+ );
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8031);
+
+ if (CbmEndOfPost.Data.RequestedActions == HECI_EOP_PERFORM_GLOBAL_RESET) {
+ if (PchResetProtocol != NULL) {
+ DEBUG ((EFI_D_ERROR, "HeciSendEndOfPostMessage(): Reset requested by FW EOP ACK %r\n"));
+ PchResetProtocol->Reset (PchResetProtocol, GlobalReset);
+ }
+ }
+
+ return Status;
+}
+
+/**
+ Send Get Firmware SKU Request to ME
+
+ @param[in] MsgGenGetFwCapsSku Return message for Get Firmware Capability SKU
+ @param[in] MsgGenGetFwCapsSkuAck Return message for Get Firmware Capability SKU ACK
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetFwCapsSkuMsg (
+ IN OUT GEN_GET_FW_CAPSKU *MsgGenGetFwCapsSku,
+ IN OUT GEN_GET_FW_CAPS_SKU_ACK *MsgGenGetFwCapsSkuAck
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenGetFwCapsSku->MKHIHeader.Data = 0;
+ MsgGenGetFwCapsSku->MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenGetFwCapsSku->MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ MsgGenGetFwCapsSku->MKHIHeader.Fields.IsResponse = 0;
+ MsgGenGetFwCapsSku->Data.RuleId = 0;
+ Length = sizeof (GEN_GET_FW_CAPSKU);
+
+ ///
+ /// Send Get FW SKU Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8040);
+ Status = Heci->SendMsg (
+ (UINT32 *) MsgGenGetFwCapsSku,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_FW_CAPS_SKU_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) MsgGenGetFwCapsSkuAck,
+ &Length
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8042);
+ return Status;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8041);
+ return Status;
+}
+
+/**
+ Send Get Firmware Version Request to ME
+
+ @param[in][out] MsgGenGetFwVersionAck Return themessage of FW version
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetFwVersionMsg (
+ IN OUT GEN_GET_FW_VER_ACK *MsgGenGetFwVersionAck
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ GEN_GET_FW_VER *MsgGenGetFwVersion;
+ GEN_GET_FW_VER GenGetFwVersion;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+ ///
+ /// Allocate MsgGenGetFwVersion data structure
+ ///
+ MsgGenGetFwVersion = &GenGetFwVersion;
+ MsgGenGetFwVersion->MKHIHeader.Data = 0;
+ MsgGenGetFwVersion->MKHIHeader.Fields.GroupId = MKHI_GEN_GROUP_ID;
+ MsgGenGetFwVersion->MKHIHeader.Fields.Command = GEN_GET_FW_VERSION_CMD;
+ MsgGenGetFwVersion->MKHIHeader.Fields.IsResponse = 0;
+ Length = sizeof (GEN_GET_FW_VER);
+ ///
+ /// Send Get Firmware Version Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8050);
+ Status = Heci->SendMsg (
+ (UINT32 *) MsgGenGetFwVersion,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_FW_VER_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) MsgGenGetFwVersionAck,
+ &Length
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8052);
+ return Status;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8051);
+ return Status;
+}
+
+/**
+ Sends a message to ME to unlock a specified SPI Flash region for writing and receiving a response message.
+ It is recommended that HMRFPO_ENABLE MEI message needs to be sent after all OROMs finish their initialization.
+
+ @param[in] Nonce Nonce received in previous HMRFPO_ENABLE Response Message
+ @param[in] Result HMRFPO_ENABLE response
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciHmrfpoEnable (
+ IN UINT64 Nonce,
+ OUT UINT8 *Result
+ )
+{
+ EFI_STATUS Status;
+ EFI_HECI_PROTOCOL *Heci;
+ MKHI_HMRFPO_ENABLE HmrfpoEnableRequest;
+ MKHI_HMRFPO_ENABLE_RESPONSE HmrfpoEnableResponse;
+ UINT32 HeciLength;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ HmrfpoEnableRequest.MkhiHeader.Data = 0;
+ HmrfpoEnableRequest.MkhiHeader.Fields.GroupId = MKHI_SPI_GROUP_ID;
+ HmrfpoEnableRequest.MkhiHeader.Fields.Command = HMRFPO_ENABLE_CMD_ID;
+ HmrfpoEnableRequest.MkhiHeader.Fields.IsResponse = 0;
+ HmrfpoEnableRequest.Nonce = Nonce;
+
+ HeciLength = sizeof (MKHI_HMRFPO_ENABLE);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8070);
+ Status = Heci->SendMsg (
+ (UINT32 *) &HmrfpoEnableRequest,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Send HMRFPO_ENABLE_CMD_ID Request - %r\n", Status));
+ return Status;
+ }
+
+ HeciLength = sizeof (MKHI_HMRFPO_ENABLE_RESPONSE);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &HmrfpoEnableResponse,
+ &HeciLength
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Read HMRFPO_ENABLE_CMD_ID Result - %r\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8072);
+ return Status;
+ }
+
+ *Result = HmrfpoEnableResponse.Status;
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8071);
+
+ return Status;
+}
+
+/**
+ Sends a message to ME to lock a specified SPI Flash region for writing and receiving a response message.
+
+ @param[out] Nonce Random number generated by Ignition ME FW. When BIOS
+ want to unlock region it should use this value
+ in HMRFPO_ENABLE Request Message
+ @param[out] FactoryDefaultBase The base of the factory default calculated from the start of the ME region.
+ BIOS sets a Protected Range (PR) register "Protected Range Base" field with this value
+ + the base address of the region.
+ @param[out] FactoryDefaultLimit The length of the factory image.
+ BIOS sets a Protected Range (PR) register "Protected Range Limit" field with this value
+ @param[out] Result Status report
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciHmrfpoLock (
+ OUT UINT64 *Nonce,
+ OUT UINT32 *FactoryDefaultBase,
+ OUT UINT32 *FactoryDefaultLimit,
+ OUT UINT8 *Result
+ )
+{
+ EFI_STATUS Status;
+ EFI_HECI_PROTOCOL *Heci;
+ MKHI_HMRFPO_LOCK HmrfpoLockRequest;
+ MKHI_HMRFPO_LOCK_RESPONSE HmrfpoLockResponse;
+ UINT32 HeciLength;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ HmrfpoLockRequest.MkhiHeader.Data = 0;
+ HmrfpoLockRequest.MkhiHeader.Fields.GroupId = MKHI_SPI_GROUP_ID;
+ HmrfpoLockRequest.MkhiHeader.Fields.Command = HMRFPO_LOCK_CMD_ID;
+ HmrfpoLockRequest.MkhiHeader.Fields.IsResponse = 0;
+
+ HeciLength = sizeof (MKHI_HMRFPO_LOCK);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8080);
+ Status = Heci->SendMsg (
+ (UINT32 *) &HmrfpoLockRequest,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Send HMRFPO_LOCK_CMD_ID Request - %r\n", Status));
+ return Status;
+ }
+
+ HeciLength = sizeof (MKHI_HMRFPO_LOCK_RESPONSE);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &HmrfpoLockResponse,
+ &HeciLength
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to read HMRFPO_LOCK_CMD_ID response - %r.\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8082);
+ return Status;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8081);
+
+ *Nonce = HmrfpoLockResponse.Nonce;
+ *FactoryDefaultBase = HmrfpoLockResponse.FactoryDefaultBase;
+ *FactoryDefaultLimit = HmrfpoLockResponse.FactoryDefaultLimit;
+ *Result = HmrfpoLockResponse.Status;
+
+ return Status;
+}
+
+/**
+ System BIOS sends this message to get status for HMRFPO_LOCK message.
+
+ @param[out] Result HMRFPO_GET_STATUS response
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciHmrfpoGetStatus (
+ OUT UINT8 *Result
+ )
+{
+ EFI_STATUS Status;
+ EFI_HECI_PROTOCOL *Heci;
+ MKHI_HMRFPO_GET_STATUS HmrfpoGetStatusRequest;
+ MKHI_HMRFPO_GET_STATUS_RESPONSE HmrfpoGetStatusResponse;
+ UINT32 HeciLength;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ HmrfpoGetStatusRequest.MkhiHeader.Data = 0;
+ HmrfpoGetStatusRequest.MkhiHeader.Fields.GroupId = MKHI_SPI_GROUP_ID;
+ HmrfpoGetStatusRequest.MkhiHeader.Fields.Command = HMRFPO_GET_STATUS_CMD_ID;
+ HmrfpoGetStatusRequest.MkhiHeader.Fields.IsResponse = 0;
+
+ HeciLength = sizeof (MKHI_HMRFPO_GET_STATUS);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8090);
+ Status = Heci->SendMsg (
+ (UINT32 *) &HmrfpoGetStatusRequest,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Send HMRFPO_GET_STATUS_CMD_ID - %r\n", Status));
+ return Status;
+ }
+
+ HeciLength = sizeof (MKHI_HMRFPO_GET_STATUS_RESPONSE);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &HmrfpoGetStatusResponse,
+ &HeciLength
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Read HMRFPO_GET_STATUS_CMD_ID Result - %r\n", Status));
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8091);
+ *Result = HmrfpoGetStatusResponse.Status;
+
+ return Status;
+}
+
+/**
+ This is used to send KVM request message to Intel ME. When
+ Bootoptions indicate that a KVM session is requested then BIOS
+ will send this message before any graphical display output to
+ ensure that FW is ready for KVM session.
+
+ @param[in] QueryType 0 - Query Request
+ 1 - Cancel Request
+ @param[out] ResponseCode 1h - Continue, KVM session established.
+ 2h - Continue, KVM session cancelled.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciQueryKvmRequest (
+ IN UINT32 QueryType,
+ OUT UINT32 *ResponseCode
+ )
+{
+ EFI_STATUS Status;
+ EFI_HECI_PROTOCOL *Heci;
+ AMT_QUERY_KVM_REQUEST QueryKvmRequest;
+ AMT_QUERY_KVM_RESPONSE QueryKvmResponse;
+ UINT32 HeciLength;
+ UINT16 TimeOut;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ QueryKvmRequest.Command = EFI_KVM_MESSAGE_COMMAND;
+ QueryKvmRequest.ByteCount = EFI_KVM_BYTE_COUNT;
+ QueryKvmRequest.SubCommand = EFI_KVM_QUERY_REQUES;
+ QueryKvmRequest.VersionNumber = EFI_KVM_VERSION;
+ QueryKvmRequest.QueryType = QueryType;
+
+ HeciLength = sizeof (AMT_QUERY_KVM_REQUEST);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8060);
+ Status = Heci->SendMsg (
+ (UINT32 *) &QueryKvmRequest,
+ HeciLength,
+ BIOS_ASF_HOST_ADDR,
+ HECI_ASF_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Query KVM failed %r\n", Status));
+ }
+
+ TimeOut = 0;
+ HeciLength = sizeof (AMT_QUERY_KVM_RESPONSE);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &QueryKvmResponse,
+ &HeciLength
+ );
+
+ if (QueryType == QUERY_REQUEST) {
+ while (EFI_ERROR (Status)) {
+ gBS->Stall (EFI_KVM_STALL_1_SECOND);
+ TimeOut++;
+
+ if (TimeOut > EFI_KVM_MAX_WAIT_TIME) {
+ break;
+ }
+
+ HeciLength = sizeof (AMT_QUERY_KVM_RESPONSE);
+ Status = Heci->ReadMsg (
+ NON_BLOCKING,
+ (UINT32 *) &QueryKvmResponse,
+ &HeciLength
+ );
+ }
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8061);
+ *ResponseCode = QueryKvmResponse.ResponseCode;
+
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP) on the boot
+ where host wants to query the local firmware update interface status.
+
+ @param[out] RuleData 1 - local firmware update interface enable
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetLocalFwUpdate (
+ OUT UINT8 *RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_GET_LOCAL_FW_UPDATE MsgGenGetLocalFwUpdate;
+ GEN_GET_LOCAL_FW_UPDATE_ACK MsgGenGetLocalFwUpdatekuAck;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenGetLocalFwUpdate.MKHIHeader.Data = 0;
+ MsgGenGetLocalFwUpdate.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenGetLocalFwUpdate.MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ MsgGenGetLocalFwUpdate.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenGetLocalFwUpdate.Data.RuleId = 7;
+ Length = sizeof (GEN_GET_LOCAL_FW_UPDATE);
+
+ ///
+ /// Send Get Local FW update Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80A0);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenGetLocalFwUpdate,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_LOCAL_FW_UPDATE_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenGetLocalFwUpdatekuAck,
+ &Length
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80A2);
+ return Status;
+ }
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80A1);
+ *RuleData = MsgGenGetLocalFwUpdatekuAck.Data.RuleData;
+
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP) on the boot
+ where host wants to enable or disable the local firmware update interface.
+ The firmware allows a single update once it receives the enable command
+
+ @param[in] RuleData 1 - local firmware update interface enable
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciSetLocalFwUpdate (
+ IN UINT8 RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_SET_LOCAL_FW_UPDATE MsgGenSetLocalFwUpdate;
+ GEN_SET_LOCAL_FW_UPDATE_ACK MsgGenSetLocalFwUpdateAck;
+ UINT32 MeMode;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenSetLocalFwUpdate.MKHIHeader.Data = 0;
+ MsgGenSetLocalFwUpdate.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenSetLocalFwUpdate.MKHIHeader.Fields.Command = FWCAPS_SET_RULE_CMD;
+ MsgGenSetLocalFwUpdate.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenSetLocalFwUpdate.Data.RuleId = 7;
+ MsgGenSetLocalFwUpdate.Data.RuleDataLen = 1;
+ MsgGenSetLocalFwUpdate.Data.RuleData = RuleData;
+ Length = sizeof (GEN_SET_LOCAL_FW_UPDATE);
+
+ ///
+ /// Send Get Local FW update Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80B0);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenSetLocalFwUpdate,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80B2);
+ return Status;
+ }
+
+ Length = sizeof (GEN_SET_LOCAL_FW_UPDATE_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenSetLocalFwUpdateAck,
+ &Length
+ );
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80B1);
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to enable the ME State. The firmware allows a single
+ update once it receives the enable command. Once firmware receives this message,
+ the firmware will be in normal mode after a global reset.
+
+ @param[in] None
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS ME enabled message sent
+**/
+EFI_STATUS
+HeciSetMeEnableMsg (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_SET_FW_CAPSKU_ACK MsgMeStateControlAck;
+ HECI_FWS_REGISTER MeFirmwareStatus;
+ UINTN HeciPciAddressBase;
+ UINT16 TimeOut;
+ UINT32 MeMode;
+
+ TimeOut = 0;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (MeMode == ME_MODE_NORMAL) {
+ return EFI_SUCCESS;
+ }
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_TEMP_DISABLED)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ HeciPciAddressBase = PCI_LIB_ADDRESS (
+ ME_BUS,
+ ME_DEVICE_NUMBER,
+ HECI_FUNCTION_NUMBER,
+ 0
+ );
+ PciWrite8 (HeciPciAddressBase + R_GEN_STS + 3, 0x20);
+ do {
+ MeFirmwareStatus.ul = PciRead32 (HeciPciAddressBase + R_FWSTATE);
+ gBS->Stall (EFI_ME_STATE_STALL_1_SECOND);
+ TimeOut++;
+ } while ((MeFirmwareStatus.r.FwInitComplete != ME_FIRMWARE_COMPLETED) && (TimeOut < EFI_ME_STATE_MAX_TIMEOUT));
+
+ Length = sizeof (GEN_SET_FW_CAPSKU_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgMeStateControlAck,
+ &Length
+ );
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to disable the ME State. The firmware allows a single
+ update once it receives the disable command Once firmware receives this message,
+ the firmware will work in "Soft Temporary Disable" mode (HFS[19:16] = 3) after a
+ global reset. Note, this message is not allowed when AT firmware is enrolled/configured.
+
+ @param[in] None
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS ME is disabled
+**/
+EFI_STATUS
+HeciSetMeDisableMsg (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_SET_FW_CAPSKU MsgMeStateControl;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (MeMode == ME_MODE_TEMP_DISABLED) {
+ return EFI_SUCCESS;
+ }
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgMeStateControl.MKHIHeader.Data = 0;
+ MsgMeStateControl.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgMeStateControl.MKHIHeader.Fields.Command = FWCAPS_SET_RULE_CMD;
+ MsgMeStateControl.MKHIHeader.Fields.IsResponse = 0;
+ MsgMeStateControl.Data.RuleId.Data = 6;
+ MsgMeStateControl.Data.RuleDataLen = 1;
+ MsgMeStateControl.Data.RuleData = 0;
+
+ Length = sizeof (GEN_SET_FW_CAPSKU);
+
+ Status = Heci->SendwACK (
+ (UINT32 *) &MsgMeStateControl,
+ Length,
+ &Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to get Ibex Peak platform type.
+ One of usages is to utilize this command to determine if the platform runs in
+ 1.5M or 5M size firmware.
+
+ @param[in] RuleData PlatformBrand,
+ IntelMeFwImageType,
+ SuperSku,
+ PlatformTargetMarketType,
+ PlatformTargetUsageType
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetPlatformTypeMsg (
+ OUT PLATFORM_TYPE_RULE_DATA *RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_GET_PLATFORM_TYPE MsgGenGetPlatformType;
+ GEN_GET_PLATFORM_TYPE_ACK MsgGenGetPlatformTypeAck;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenGetPlatformType.MKHIHeader.Data = 0;
+ MsgGenGetPlatformType.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenGetPlatformType.MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ MsgGenGetPlatformType.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenGetPlatformType.Data.RuleId = 0x1D;
+ Length = sizeof (GEN_GET_PLATFORM_TYPE);
+
+ ///
+ /// Send Get Platform Type Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80C0);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenGetPlatformType,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80C2);
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_PLATFORM_TYPE_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenGetPlatformTypeAck,
+ &Length
+ );
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80C1);
+ *RuleData = MsgGenGetPlatformTypeAck.Data.RuleData;
+
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS on the boot where the host wants to get the firmware provisioning state.
+ The firmware will respond to AMT BIOS SYNCH INFO message even after the End of Post.
+
+ @param[out] RuleData Bit [2:0] Reserved
+ Bit [4:3] Provisioning State
+ 00 - Pre -provisioning
+ 01 - In -provisioning
+ 02 - Post !Vprovisioning
+ Bit [31:5] Reserved
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Firmware provisioning state returned
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciAmtBiosSynchInfo (
+ OUT UINT32 *RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_AMT_BIOS_SYNCH_INFO MsgGenAmtBiosSynchInfo;
+ GEN_AMT_BIOS_SYNCH_INFO_ACK MsgGenAmtBiosSynchInfoAck;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenAmtBiosSynchInfo.MKHIHeader.Data = 0;
+ MsgGenAmtBiosSynchInfo.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenAmtBiosSynchInfo.MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ MsgGenAmtBiosSynchInfo.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenAmtBiosSynchInfo.Data.RuleId = 0x30005;
+ Length = sizeof (GEN_AMT_BIOS_SYNCH_INFO);
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8130);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenAmtBiosSynchInfo,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8132);
+ return Status;
+ }
+
+ Length = sizeof (GEN_AMT_BIOS_SYNCH_INFO_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenAmtBiosSynchInfoAck,
+ &Length
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8133);
+ return Status;
+ }
+
+ *RuleData = MsgGenAmtBiosSynchInfoAck.RuleData;
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8131);
+ return Status;
+}
+
+/**
+ The firmware will respond to GET OEM TAG message even after the End of Post (EOP).
+
+ @param[in] RuleData Default is zero. Tool can create the OEM specific OEM TAG data.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetOemTagMsg (
+ OUT UINT32 *RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_GET_OEM_TAG_MSG MsgGenGetOemTagMsg;
+ GEN_GET_OEM_TAG_MSG_ACK MsgGenGetOemTagMsgAck;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenGetOemTagMsg.MKHIHeader.Data = 0;
+ MsgGenGetOemTagMsg.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenGetOemTagMsg.MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ MsgGenGetOemTagMsg.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenGetOemTagMsg.Data.RuleId = 0x2B;
+ Length = sizeof (GEN_GET_OEM_TAG_MSG);
+
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenGetOemTagMsg,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_OEM_TAG_MSG_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenGetOemTagMsgAck,
+ &Length
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ *RuleData = MsgGenGetOemTagMsgAck.RuleData;
+
+ return Status;
+}
+
+/**
+ Enables/disables clocks. Used to turn off clocks in unused pci/pcie slots.
+ BIOS use this command when it enumerates PCI slots. When PCI slot is found unpopulated, the
+ BIOS can disable its clock through this MEI message. It is the BIOS requirement to know which
+ slot is controlled by which control bit.
+
+ @param[in] Enables each bit means corresponding clock should be turned on (1) or off (0)
+ @param[in] EnablesMask each bit means corresponding enable bit is valid (1) or should be ignored (0)
+ @param[in] ResponseMode 0 wait for response, 1 - skip
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY ME is not ready
+ @retval EFI_INVALID_PARAMETER ResponseMode is invalid value
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+EFIAPI
+HeciSetIccClockEnables (
+ IN UINT32 Enables,
+ IN UINT32 EnablesMask,
+ IN UINT8 ResponseMode
+ )
+{
+ EFI_STATUS Status;
+ ICC_SET_CLK_ENABLES_BUFFER Buffer;
+ UINT32 CommandSize;
+ UINT32 ResponseSize;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+ UINT32 MeStatus;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ if ((ResponseMode != ICC_RESPONSE_MODE_SKIP) && (ResponseMode != ICC_RESPONSE_MODE_WAIT)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = Heci->GetMeStatus (&MeStatus);
+ if (EFI_ERROR (Status) || ((MeStatus & 0xF) != ME_READY)) {
+ return EFI_NOT_READY;
+ }
+
+ CommandSize = sizeof (ICC_SET_CLK_ENABLES_MESSAGE);
+ ResponseSize = sizeof (ICC_SET_CLK_ENABLES_RESPONSE);
+
+ Buffer.message.Header.ApiVersion = LYNX_POINT_PLATFORM;
+ Buffer.message.Header.IccCommand = SET_CLOCK_ENABLES;
+ Buffer.message.Header.IccResponse = 0;
+ Buffer.message.Header.BufferLength = CommandSize - sizeof (ICC_HEADER);
+ Buffer.message.Header.Reserved = 0;
+ Buffer.message.ClockEnables = Enables;
+ Buffer.message.ClockEnablesMask = EnablesMask;
+ Buffer.message.Params = ResponseMode;
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D0);
+ Status = Heci->SendMsg (
+ (UINT32 *) &Buffer,
+ CommandSize,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ICC_MESSAGE_ADDR
+ );
+
+ if (ResponseMode == ICC_RESPONSE_MODE_WAIT) {
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &Buffer,
+ &ResponseSize
+ );
+ }
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "(ICC) IccSetClockEnables: Message failed! EFI_STATUS = %r\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D2);
+ return Status;
+ }
+
+ if (ResponseMode == ICC_RESPONSE_MODE_SKIP) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D3);
+ return EFI_SUCCESS;
+ }
+
+ if (Buffer.response.Header.IccResponse != ICC_STATUS_SUCCESS) {
+ DEBUG (
+ (EFI_D_ERROR,
+ "(ICC) IccSetClockEnables: Wrong response! IccHeader.Response = 0x%x\n",
+ Buffer.response.Header.IccResponse)
+ );
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D4);
+ return EFI_DEVICE_ERROR;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D1);
+ return Status;
+}
+
+/**
+ Sets or reads Lock mask on ICC registers.
+ @param[in] AccessMode 0 - set, 1 - get
+ @param[in] ResponseMode 0 - firmware will answer, 1 - firmware will not answer
+ @param[in][out] LockRegInfo bundle count info and mask of registers to become (for 'set' mode) or are
+ (for 'get' mode) locked. Each bit represents a register. 0=lock, 1=don't lock
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_INVALID_PARAMETER ResponseMode or pointer of Mask is invalid value
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY Heci device hasn't ready yet
+**/
+EFI_STATUS
+HeciLockIccRegisters (
+ IN UINT8 AccessMode,
+ IN UINT8 ResponseMode,
+ IN OUT ICC_LOCK_REGS_INFO *LockRegInfo
+ )
+{
+ EFI_STATUS Status;
+ ICC_LOCK_REGISTERS_BUFFER Buffer;
+ UINT32 CommandSize;
+ UINT32 ResponseSize;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+ UINT32 MeStatus;
+ UINT32 i;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ if ((ResponseMode != ICC_RESPONSE_MODE_SKIP) && (ResponseMode != ICC_RESPONSE_MODE_WAIT)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = Heci->GetMeStatus (&MeStatus);
+ if (EFI_ERROR (Status) || ((MeStatus & 0xF) != ME_READY)) {
+ return EFI_NOT_READY;
+ }
+
+ DEBUG ((EFI_D_INFO, "(ICC) LockIccRegisters\n"));
+ if (LockRegInfo == NULL) {
+ return EFI_INVALID_PARAMETER;
+
+ }
+
+ CommandSize = sizeof (ICC_LOCK_REGISTERS_MESSAGE) -
+ sizeof(UINT32) * ICC_LOCK_MASK_COUNT +
+ sizeof(UINT32) * LockRegInfo->RegBundles.BundlesCnt;
+ ResponseSize = sizeof (ICC_LOCK_REGISTERS_RESPONSE);
+
+ Buffer.message.Header.ApiVersion = LYNX_POINT_PLATFORM;
+ Buffer.message.Header.IccCommand = LOCK_ICC_REGISTERS;
+ Buffer.message.Header.IccResponse = 0;
+ Buffer.message.Header.BufferLength = CommandSize - sizeof (ICC_HEADER);
+ Buffer.message.Header.Reserved = 0;
+ Buffer.message.AccessMode = AccessMode;
+ Buffer.message.Parameters = ResponseMode;
+ Buffer.message.Reserved[0] = 0;
+ Buffer.message.Reserved[1] = 0;
+ Buffer.message.LockRegInfo.RegBundles = LockRegInfo->RegBundles;
+ for (i = 0; i < LockRegInfo->RegBundles.BundlesCnt; i++) {
+ Buffer.message.LockRegInfo.RegMask[i] = LockRegInfo->RegMask[i];
+ }
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80E0);
+ Status = Heci->SendMsg (
+ (UINT32 *) &Buffer,
+ CommandSize,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ICC_MESSAGE_ADDR
+ );
+
+ if (ResponseMode == ICC_RESPONSE_MODE_WAIT) {
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &Buffer,
+ &ResponseSize
+ );
+ }
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "(ICC) LockIccRegisters: Message failed! EFI_STATUS = %r\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80E2);
+ return Status;
+ }
+
+ if (ResponseMode == ICC_RESPONSE_MODE_SKIP) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80E3);
+ return EFI_SUCCESS;
+ }
+
+ if (Buffer.response.Header.IccResponse != ICC_STATUS_SUCCESS) {
+ DEBUG (
+ (EFI_D_ERROR,
+ "(ICC) LockIccRegisters: Wrong response! IccHeader.Response = 0x%x\n",
+ Buffer.response.Header.IccResponse)
+ );
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80E4);
+ return EFI_DEVICE_ERROR;
+ }
+
+ if (AccessMode == ICC_LOCK_ACCESS_MODE_GET) {
+ LockRegInfo->RegBundles = Buffer.response.LockRegInfo.RegBundles;
+ LockRegInfo->RegMask[0] = Buffer.response.LockRegInfo.RegMask[0];
+ LockRegInfo->RegMask[1] = Buffer.response.LockRegInfo.RegMask[1];
+ LockRegInfo->RegMask[2] = Buffer.response.LockRegInfo.RegMask[2];
+ }
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80E1);
+
+ return Status;
+}
+
+/**
+ retrieves the number of currently used ICC clock profile
+
+ @param[out] Profile number of current ICC clock profile
+
+ @exception EFI_UNSUPPORTED ICC clock profile doesn't support
+ @retval EFI_NOT_READY Heci device hasn't ready yet
+**/
+EFI_STATUS
+HeciGetIccProfile (
+ OUT UINT8 *Profile
+ )
+{
+ EFI_STATUS Status;
+ ICC_GET_PROFILE_BUFFER Buffer;
+ UINT32 CommandSize;
+ UINT32 ResponseSize;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+ UINT32 MeStatus;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = Heci->GetMeStatus (&MeStatus);
+ if (EFI_ERROR (Status) || ((MeStatus & 0xF) != ME_READY)) {
+ return EFI_NOT_READY;
+ }
+
+ DEBUG ((EFI_D_INFO, "(ICC) GetIccProfile\n"));
+ CommandSize = sizeof (ICC_GET_PROFILE_MESSAGE);
+ ResponseSize = sizeof (ICC_GET_PROFILE_RESPONSE);
+
+ Buffer.message.Header.ApiVersion = LYNX_POINT_PLATFORM;
+ Buffer.message.Header.IccCommand = GET_ICC_PROFILE;
+ Buffer.message.Header.IccResponse = 0;
+ Buffer.message.Header.BufferLength = CommandSize - sizeof (ICC_HEADER);
+ Buffer.message.Header.Reserved = 0;
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80F0);
+ Status = Heci->SendwACK (
+ (UINT32 *) &Buffer,
+ CommandSize,
+ &ResponseSize,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ICC_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_INFO, "(ICC) GetIccProfile: Message failed! EFI_STATUS = %r\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80F2);
+ return Status;
+ }
+
+ if (Buffer.response.Header.IccResponse != ICC_STATUS_SUCCESS) {
+ DEBUG (
+ (EFI_D_ERROR,
+ "(ICC) GetIccProfile: Wrong response! IccHeader.Response = 0x%x\n",
+ Buffer.response.Header.IccResponse)
+ );
+ Status = EFI_DEVICE_ERROR;
+ } else {
+ DEBUG ((EFI_D_INFO, "(ICC) GetIccProfile: Current profile = 0x%x\n", Buffer.response.IccProfileIndex));
+ }
+
+ if (Profile != NULL) {
+ *Profile = Buffer.response.IccProfileIndex;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80F1);
+
+ return Status;
+}
+
+/**
+ Sets ICC clock profile to be used on next and following boots
+
+ @param[in] Profile number of profile to be used
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY Heci device hasn't ready yet
+**/
+EFI_STATUS
+HeciSetIccProfile (
+ IN UINT8 Profile
+ )
+{
+ EFI_STATUS Status;
+ ICC_SET_PROFILE_BUFFER Buffer;
+ UINT32 CommandSize;
+ UINT32 ResponseSize;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+ UINT32 MeStatus;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = Heci->GetMeStatus (&MeStatus);
+ if (EFI_ERROR (Status) || ((MeStatus & 0xF) != ME_READY)) {
+ return EFI_NOT_READY;
+ }
+
+ DEBUG ((EFI_D_INFO, "(ICC) SetIccProfile\n"));
+
+ CommandSize = sizeof (ICC_SET_PROFILE_MESSAGE);
+ ResponseSize = sizeof (ICC_SET_PROFILE_RESPONSE);
+
+ Buffer.message.Header.ApiVersion = LYNX_POINT_PLATFORM;
+ Buffer.message.Header.IccCommand = SET_ICC_PROFILE;
+ Buffer.message.Header.IccResponse = 0;
+ Buffer.message.Header.BufferLength = CommandSize - sizeof (ICC_HEADER);
+ Buffer.message.Header.Reserved = 0;
+ Buffer.message.ProfileBIOS = Profile;
+ Buffer.message.PaddingA = 0;
+ Buffer.message.PaddingB = 0;
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8100);
+ Status = Heci->SendwACK (
+ (UINT32 *) &Buffer,
+ CommandSize,
+ &ResponseSize,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ICC_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "(ICC) SetIccProfile: Message failed! EFI_STATUS = %r\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8102);
+ return Status;
+ }
+
+ if (Buffer.response.Header.IccResponse != ICC_STATUS_SUCCESS) {
+ DEBUG (
+ (EFI_D_ERROR,
+ "(ICC) SetIccProfile: Wrong response! IccHeader.Response = 0x%x\n",
+ Buffer.response.Header.IccResponse)
+ );
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8103);
+ return EFI_DEVICE_ERROR;
+ }
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8101);
+
+ return Status;
+}
+
+/**
+ Writes 1 dword of data to the icc register offset specified by RegOffset in the ICC Aux space
+ @param[in] RegOffset Register Offset in ICC Aux Space to write
+ @param[in] RegData Dword ICC register data to write
+ @param[in] ResponseMode 0 Wait for response, 1 - skip
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY ME is not ready
+ @retval EFI_INVALID_PARAMETER ResponseMode is invalid value
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+EFIAPI
+HeciWriteIccRegDword (
+ IN UINT16 RegOffset,
+ IN UINT32 RegData,
+ IN UINT8 ResponseMode
+ )
+{
+ EFI_STATUS Status;
+ ICC_WRITE_ICC_REG_BUFFER Buffer;
+ UINT32 CommandSize;
+ UINT32 ResponseSize;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+ UINT32 MeStatus;
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ if ((ResponseMode != ICC_RESPONSE_MODE_SKIP) && (ResponseMode != ICC_RESPONSE_MODE_WAIT)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = Heci->GetMeStatus (&MeStatus);
+ if (EFI_ERROR (Status) || ((MeStatus & 0xF) != ME_READY)) {
+ return EFI_NOT_READY;
+ }
+
+ CommandSize = sizeof (ICC_WRITE_ICC_REG_DWORD_MESSAGE);
+ ResponseSize = sizeof (ICC_WRITE_ICC_REG_DWORD_RESPONSE);
+
+ Buffer.message.Header.ApiVersion = LYNX_POINT_PLATFORM;
+ Buffer.message.Header.IccCommand = WRITE_ICC_REGISTER;
+ Buffer.message.Header.IccResponse = 0;
+ Buffer.message.Header.BufferLength = CommandSize - sizeof (ICC_HEADER);
+ Buffer.message.Header.Reserved = 0;
+ Buffer.message.Reserved = 0;
+ Buffer.message.Reserved1 = 0;
+ Buffer.message.Params = ResponseMode;
+ Buffer.message.RecordDword.RecordFlags = WRITE_ICC_RECORD_FLAGS;
+ Buffer.message.RecordDword.BundleCount.BundlesCnt = WRITE_ICC_REG_BUNDLE_COUNT;
+ Buffer.message.RecordDword.BundleCount.AU = 0;
+ Buffer.message.RecordDword.BundleCount.Reserved = 0;
+ Buffer.message.RecordDword.AddressMask.AddressMaskData = RegOffset | ADDRESS_MASK_FIXED_DATA;
+ Buffer.message.RecordDword.RegValue = RegData;
+
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D0);
+ Status = Heci->SendMsg (
+ (UINT32 *) &Buffer,
+ CommandSize,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ICC_MESSAGE_ADDR
+ );
+
+ if (ResponseMode == ICC_RESPONSE_MODE_WAIT) {
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &Buffer,
+ &ResponseSize
+ );
+
+ }
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "(ICC) HeciWriteIccRegDword: Message failed! EFI_STATUS = %r\n", Status));
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D2);
+ return Status;
+ }
+
+ if (ResponseMode == ICC_RESPONSE_MODE_SKIP) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D3);
+ return EFI_SUCCESS;
+ }
+
+ if (Buffer.response.Header.IccResponse != ICC_STATUS_SUCCESS) {
+ DEBUG (
+ (EFI_D_ERROR,
+ "(ICC) HeciWriteIccRegDword: Wrong response! IccHeader.Response = 0x%x\n",
+ Buffer.response.Header.IccResponse)
+ );
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D4);
+ return EFI_DEVICE_ERROR;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x80D1);
+ return Status;
+}
+
+/**
+ This message is used to turn on the Intel ME firmware MDES
+ capability, Intel SVT for PCH capability or both when the
+ system is in a post-manufactured state. Once firmware receives
+ this message, the firmware will enable selected platform debug
+ capabilities . The firmware will automatically disable all
+ platform debug capabilities if this message is not received
+ before receiving End Of Post.
+
+ @param[in] Data capabilities to be enabled
+ @param[out] Result 0x00 : Enable Success
+ Others : Enable Failure
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciPlatformDebugCapabilityMsg (
+ IN PLATFORM_DEBUG_CAP Data,
+ OUT UINT8 *Result
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_PLATFORM_DEBUG_CAP_MKHI_CMD_MSG PlatformDebug;
+ UINT32 MeMode;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ PlatformDebug.MKHIHeader.Data = 0;
+ PlatformDebug.MKHIHeader.Fields.GroupId = MKHI_MDES_GROUP_ID;
+ PlatformDebug.MKHIHeader.Fields.Command = MDES_ENABLE_MKHI_CMD;
+ PlatformDebug.MKHIHeader.Fields.IsResponse = 0;
+ PlatformDebug.Capability = Data;
+ Length = sizeof (GEN_PLATFORM_DEBUG_CAP_MKHI_CMD_MSG);
+
+ Status = Heci->SendwACK (
+ (UINT32 *) &PlatformDebug,
+ Length,
+ &Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+
+ if (Status == EFI_SUCCESS) {
+ *Result = (UINT8) PlatformDebug.MKHIHeader.Fields.Result;
+ }
+
+ return Status;
+}
+
+/**
+ It creates and sends Heci messages.
+
+ Remark:
+ Functionality is available only in release mode.
+ Using MDES in debug mode causes recursive calling of this function
+ because debug messages are sending from Heci->SendMsg function.
+
+ @param[in] CodeType Indicates the type of status code being reported.
+ @param[in] Value Describes the current status of a hardware or software entity.
+ This included information about the class and subclass that is
+ used to classify the entity as well as an operation.
+ @param[in] Instance The enumeration of a hardware or software entity within
+ the system. Valid instance numbers start with 1.
+ @param[in] CallerId This optional parameter may be used to identify the caller.
+ This parameter allows the status code driver to apply different
+ rules to different callers.
+ @param[in] Data This optional parameter may be used to pass additional data.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Opcode evaluation success.
+ @retval Other Opcode evaluation failed.
+**/
+EFI_STATUS
+HeciSendMdesStatusCode (
+ IN EFI_STATUS_CODE_TYPE CodeType,
+ IN EFI_STATUS_CODE_VALUE Value,
+ IN UINT32 Instance,
+ IN EFI_GUID * CallerId OPTIONAL,
+ IN EFI_STATUS_CODE_DATA * Data OPTIONAL
+ )
+{
+ CBM_BIOS_MDES_MSG_REQ MsgData;
+ EFI_STATUS Status;
+ UINT32 HeciLength;
+ UINT32 MeMode;
+ EFI_HECI_PROTOCOL *Heci;
+ static UINT32 sNr = 0;
+ UINT32 ExtendedDataSize;
+ UINT32 StringCnt;
+
+ ExtendedDataSize = 0;
+ StringCnt = 0;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgData.MKHIHeader.Fields.GroupId = MKHI_MDES_GROUP_ID;
+ MsgData.MKHIHeader.Fields.Command = MDES_BIOS_MSG_LOG_REQ_CMD;
+ MsgData.MKHIHeader.Fields.IsResponse = 0;
+ MsgData.MKHIHeader.Fields.Result = 0;
+
+ MsgData.Data.MdesAttr.Severity = BiosToMdesSeverity (CodeType);
+ MsgData.Data.MdesAttr.PayLoadType = EFI_STATUS_CODE;
+ MsgData.Data.BiosAttr.CallerIdData = (CallerId == 0) ? 0 : 1;
+ MsgData.Data.BiosAttr.ExtendedDataHeader = (Data == 0) ? 0 : 1;
+ MsgData.Data.Serial = sNr++;
+ MsgData.Data.StatusType = CodeType;
+ MsgData.Data.StatusCode = Value;
+ MsgData.Data.Instance = Instance;
+
+ if (CallerId != 0) {
+ CopyMem (&MsgData.Data.CallerId, CallerId, sizeof(EFI_GUID));
+ }
+
+ if (Data != 0) {
+ ExtendedDataSize = Data->Size;
+ if (ExtendedDataSize > SIZE_OF_MDES_EXTENDED_DATA) {
+ ASSERT (FALSE);
+ //
+ // extended data too long
+ //
+ ExtendedDataSize = SIZE_OF_MDES_EXTENDED_DATA;
+ }
+
+ if (CompareGuid (&gEfiStatusCodeDataTypeStringGuid, &Data->Type)) {
+
+ EFI_STATUS_CODE_STRING_DATA *str_data;
+
+ str_data = (EFI_STATUS_CODE_STRING_DATA *) Data;
+ MsgData.Data.ExtendedData[0] = (UINT8) (str_data->StringType);
+ MsgData.Data.ExtendedData[1] = 0;
+ MsgData.Data.ExtendedData[2] = 0;
+ MsgData.Data.ExtendedData[3] = 0;
+
+ if (str_data->StringType == EfiStringAscii) {
+ AsciiStrnCpy ((CHAR8 *) &MsgData.Data.ExtendedData[4], str_data->String.Ascii, SIZE_OF_MDES_EXTENDED_DATA);
+ StringCnt = (UINT32) AsciiStrLen ((CHAR8 *) &MsgData.Data.ExtendedData[4]);
+ ExtendedDataSize = 4 + StringCnt;
+ if (ExtendedDataSize > SIZE_OF_MDES_EXTENDED_DATA) {
+ ExtendedDataSize = SIZE_OF_MDES_EXTENDED_DATA;
+ }
+
+ } else if (str_data->StringType == EfiStringUnicode) {
+ StrnCpy ((CHAR16 *) &MsgData.Data.ExtendedData[4], str_data->String.Unicode, SIZE_OF_MDES_EXTENDED_DATA);
+ StringCnt = (UINT32) StrLen ((CHAR16 *) &MsgData.Data.ExtendedData[4]);
+ ExtendedDataSize = 4 + StringCnt;
+ if (ExtendedDataSize > SIZE_OF_MDES_EXTENDED_DATA) {
+ ExtendedDataSize = SIZE_OF_MDES_EXTENDED_DATA;
+ }
+
+ } else if (str_data->StringType == EfiStringToken) {
+ CopyMem (MsgData.Data.ExtendedData, Data + Data->HeaderSize, ExtendedDataSize);
+ }
+ } else {
+ CopyMem (MsgData.Data.ExtendedData, Data + Data->HeaderSize, ExtendedDataSize);
+ }
+
+ MsgData.Data.ExtendedDataHeader.Size = (UINT16) ExtendedDataSize;
+ MsgData.Data.ExtendedDataHeader.HeaderSize = sizeof (MDES_EXTENDED_DATA_HEADER);
+ CopyMem (&MsgData.Data.ExtendedDataHeader.Type, &Data->Type, sizeof(EFI_GUID));
+ }
+
+ if (CallerId != 0) {
+ HeciLength = sizeof (CBM_BIOS_MDES_MSG_REQ) - SIZE_OF_MDES_EXTENDED_DATA - sizeof (MDES_EXTENDED_DATA_HEADER);
+ } else {
+ HeciLength = sizeof (CBM_BIOS_MDES_MSG_REQ) -
+ SIZE_OF_MDES_EXTENDED_DATA -
+ sizeof (MDES_EXTENDED_DATA_HEADER) -
+ sizeof (EFI_GUID);
+ }
+
+ if (Data != 0) {
+ HeciLength = sizeof (CBM_BIOS_MDES_MSG_REQ) - SIZE_OF_MDES_EXTENDED_DATA + ExtendedDataSize;
+ }
+
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgData,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+
+ return Status;
+}
+
+/**
+ Provides an interface to call function to send HECI message.
+
+ @param[in] Flags Indicates the status of the BIOS MDES.
+ @param[in] BiosEventFilters Indicates the status of the BIOS event filter group.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS HECI sent with success.
+**/
+EFI_STATUS
+HeciGetMdesConfig (
+ OUT MDES_BIOS_FLAGS *Flags,
+ OUT UINT32 *BiosEventFilters
+ )
+{
+ EFI_STATUS Status;
+ EFI_HECI_PROTOCOL *Heci;
+ UINT32 MeMode;
+ UINT32 Length;
+ MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_ACK MsgMdesAvailabilityAck;
+ MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_REQ MsgMdesAvailabilityReq;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgMdesAvailabilityReq.MKHIHeader.Fields.GroupId = MKHI_MDES_GROUP_ID;
+ MsgMdesAvailabilityReq.MKHIHeader.Fields.Command = MDES_BIOS_MSG_GET_CONFIG_CMD;
+ MsgMdesAvailabilityReq.MKHIHeader.Fields.IsResponse = 0;
+ MsgMdesAvailabilityReq.MKHIHeader.Fields.Result = 0;
+
+ Length = sizeof (MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_REQ);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgMdesAvailabilityReq,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Length = sizeof (MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgMdesAvailabilityAck,
+ &Length
+ );
+
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ *Flags = MsgMdesAvailabilityAck.Data.Flags;
+ *BiosEventFilters = MsgMdesAvailabilityAck.Data.BiosEventFilters;
+
+ return Status;
+}
+
+
+/**
+ Sends the MKHI Enable/Disable manageability message.
+ The message will only work if bit 2 in the bitmasks is toggled.
+ To enable manageability:
+ EnableState = 0x00000004, and
+ DisableState = 0x00000000.
+ To disable manageability:
+ EnableState = 0x00000000, and
+ DisableState = 0x00000004
+
+ @param[in] EnableState Enable Bit Mask
+ @param[in] DisableState Disable Bit Mask
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciFwFeatureStateOverride (
+ IN UINT32 EnableState,
+ IN UINT32 DisableState
+ )
+{
+ EFI_STATUS Status;
+ UINT32 HeciLength;
+ UINT32 MeMode;
+ FIRMWARE_CAPABILITY_OVERRIDE MngStateCmd;
+ FIRMWARE_CAPABILITY_OVERRIDE_ACK MngStateAck;
+ EFI_HECI_PROTOCOL *Heci;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MngStateCmd.MKHIHeader.Data = 0;
+ MngStateCmd.MKHIHeader.Fields.Command = FIRMWARE_CAPABILITY_OVERRIDE_CMD;
+ MngStateCmd.MKHIHeader.Fields.IsResponse = 0;
+ MngStateCmd.MKHIHeader.Fields.GroupId = MKHI_GEN_GROUP_ID;
+ MngStateCmd.MKHIHeader.Fields.Reserved = 0;
+ MngStateCmd.MKHIHeader.Fields.Result = 0;
+ MngStateCmd.FeatureState.EnableFeature = EnableState;
+ MngStateCmd.FeatureState.DisableFeature = DisableState;
+ HeciLength = sizeof (FIRMWARE_CAPABILITY_OVERRIDE);
+
+ Status = Heci->SendMsg (
+ (UINT32 *) &MngStateCmd,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ HeciLength = sizeof (FIRMWARE_CAPABILITY_OVERRIDE_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MngStateAck,
+ &HeciLength
+ );
+
+ return Status;
+}
+
+/**
+ The Get FW Feature Status message is based on MKHI interface.
+ This command is used by BIOS/IntelR MEBX to get firmware runtime status.
+ The GET FW RUNTIME STATUS message doesn't need to check the HFS.
+ FWInitComplete value before sending the command.
+ It means this message can be sent regardless of HFS.FWInitComplete.
+
+ @param[out] RuleData MEFWCAPS_SKU message
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+**/
+EFI_STATUS
+HeciGetFwFeatureStateMsg (
+ OUT MEFWCAPS_SKU *RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ GEN_GET_FW_FEATURE_STATUS GetFwFeatureStatus;
+ GEN_GET_FW_FEATURE_STATUS_ACK GetFwFeatureStatusAck;
+ UINT32 MeMode;
+ EFI_HECI_PROTOCOL *Heci;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ GetFwFeatureStatus.MKHIHeader.Data = 0;
+ GetFwFeatureStatus.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ GetFwFeatureStatus.MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ GetFwFeatureStatus.MKHIHeader.Fields.IsResponse = 0;
+ GetFwFeatureStatus.Data.RuleId = 0x20;
+
+ Length = sizeof (GEN_GET_FW_FEATURE_STATUS);
+ Status = Heci->SendMsg (
+ (UINT32 *) &GetFwFeatureStatus,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_FW_FEATURE_STATUS_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &GetFwFeatureStatusAck,
+ &Length
+ );
+
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ RuleData->Data = GetFwFeatureStatusAck.RuleData.Data;
+
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS when it wants to query
+ the independent firmware recovery (IFR).
+
+ @param[in] RuleData 1 - local firmware update interface enable
+
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetIfrUpdate (
+ OUT UINT8 *RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_GET_LOCAL_FW_UPDATE MsgGenGetLocalFwUpdate;
+ GEN_GET_LOCAL_FW_UPDATE_ACK MsgGenGetLocalFwUpdatekuAck;
+ UINT32 MeMode;
+
+ Status = EFI_SUCCESS;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenGetLocalFwUpdate.MKHIHeader.Data = 0;
+ MsgGenGetLocalFwUpdate.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenGetLocalFwUpdate.MKHIHeader.Fields.Command = FWCAPS_GET_RULE_CMD;
+ MsgGenGetLocalFwUpdate.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenGetLocalFwUpdate.Data.RuleId = MEFWCAPS_ME_FWU_IFR_RULE;
+ Length = sizeof (GEN_GET_LOCAL_FW_UPDATE);
+
+ ///
+ /// Send Get Local FW update Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8110);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenGetLocalFwUpdate,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8112);
+ return Status;
+ }
+
+ Length = sizeof (GEN_GET_LOCAL_FW_UPDATE_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenGetLocalFwUpdatekuAck,
+ &Length
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8113);
+ return Status;
+ }
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8111);
+ *RuleData = MsgGenGetLocalFwUpdatekuAck.Data.RuleData;
+
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS when it wants to set
+ the independent firmware recovery (IFR) state.
+
+ @param[in] RuleData 1 - local firmware update interface enable
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciSetIfrUpdate (
+ IN UINT8 RuleData
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ GEN_SET_LOCAL_FW_UPDATE MsgGenSetLocalFwUpdate;
+ GEN_SET_LOCAL_FW_UPDATE_ACK MsgGenSetLocalFwUpdateAck;
+ UINT32 MeMode;
+
+ Status = EFI_SUCCESS;
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ Status = Heci->GetMeMode (&MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgGenSetLocalFwUpdate.MKHIHeader.Data = 0;
+ MsgGenSetLocalFwUpdate.MKHIHeader.Fields.GroupId = MKHI_FWCAPS_GROUP_ID;
+ MsgGenSetLocalFwUpdate.MKHIHeader.Fields.Command = FWCAPS_SET_RULE_CMD;
+ MsgGenSetLocalFwUpdate.MKHIHeader.Fields.IsResponse = 0;
+ MsgGenSetLocalFwUpdate.Data.RuleId = MEFWCAPS_ME_FWU_IFR_RULE;
+ MsgGenSetLocalFwUpdate.Data.RuleDataLen = 1;
+ MsgGenSetLocalFwUpdate.Data.RuleData = RuleData;
+ Length = sizeof (GEN_SET_LOCAL_FW_UPDATE);
+
+ ///
+ /// Send Set Local FW update Request to ME
+ ///
+ PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8120);
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgGenSetLocalFwUpdate,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR (Status)) {
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8122);
+ return Status;
+ }
+
+ Length = sizeof (GEN_SET_LOCAL_FW_UPDATE_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgGenSetLocalFwUpdateAck,
+ &Length
+ );
+
+ PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8121);
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS if EOP-ACK not received to force ME to disable
+ HECI interfaces.
+
+ @param[in] None
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS HECI interfaces disabled by ME
+**/
+EFI_STATUS
+HeciDisableHeciBusMsg (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ UINT32 Length;
+ EFI_HECI_PROTOCOL *Heci;
+ HECI_BUS_DISABLE_CMD_ACK MsgHeciBusDisable;
+
+ ZeroMem(&MsgHeciBusDisable, sizeof(HECI_BUS_DISABLE_CMD_ACK));
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ MsgHeciBusDisable.Command.Data = HECI_BUS_DISABLE_OPCODE;
+ Length = sizeof (HECI_BUS_DISABLE_CMD_ACK);
+
+ Status = Heci->SendMsg (
+ (UINT32 *) &MsgHeciBusDisable,
+ Length,
+ BIOS_FIXED_HOST_ADDR,
+ ME_HECI_FIXED_ADDRESS
+ );
+ if (EFI_ERROR(Status)) {
+ return Status;
+ }
+
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &MsgHeciBusDisable,
+ &Length
+ );
+ if ((MsgHeciBusDisable.Command.Data != HECI_BUS_DISABLE_ACK_OPCODE)
+ || (MsgHeciBusDisable.Status != 0)) {
+ Status = EFI_ABORTED;
+ }
+
+ return Status;
+}
+
+/**
+ This message is sent by the BIOS to inform ME FW whether or not to take the
+ TPM 1.2 Deactivate flow
+
+ @param[in] UINT8 TpmDeactivate 0 - ME FW should not take the
+ deactivate flow.
+ 1 - ME FW should take the deactivate
+ flow.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS HECI interfaces disabled by ME
+**/
+EFI_STATUS
+HeciSendTpmData (
+ IN UINT8 TpmDeactivate
+ )
+{
+ EFI_STATUS Status;
+ UINT32 HeciSendLength;
+ UINT32 HeciRecvLength;
+ EFI_HECI_PROTOCOL *Heci;
+ BIOSNV_SET_ACM_TPM SetAcmTpmMsg;
+ BIOSNV_SET_ACM_TPM_ACK SetAcmTpmMsgAck;
+
+ DEBUG ((EFI_D_ERROR, "HeciSendTpmData Message. TpmDeactivate Setup Data = %d\n", TpmDeactivate));
+
+ ZeroMem(&SetAcmTpmMsg, sizeof(BIOSNV_SET_ACM_TPM));
+ ZeroMem(&SetAcmTpmMsgAck, sizeof(BIOSNV_SET_ACM_TPM_ACK));
+
+ Status = gBS->LocateProtocol (
+ &gEfiHeciProtocolGuid,
+ NULL,
+ (VOID **) &Heci
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (IsAfterEndOfPost ()) {
+ return EFI_UNSUPPORTED;
+ }
+
+ SetAcmTpmMsg.MKHIHeader.Data = ACM_TPM_DATA_MKHI_DATA;
+ SetAcmTpmMsg.AcmTpmData.RuleId.Fields.RuleTypeId = ACM_TPM_DATA_RULE_TYPE_ID;
+ SetAcmTpmMsg.AcmTpmData.RuleDataLen = ACM_TPM_DATA_RULE_DATA_LENGTH;
+ SetAcmTpmMsg.AcmTpmData.TpmState.Fields.TpmDeactivate = FALSE;
+
+ if (TpmDeactivate == 1) {
+ SetAcmTpmMsg.AcmTpmData.TpmState.Fields.TpmDeactivate = TRUE;
+ }
+
+ //
+ // Send Set ACM TPM Data MKHI message
+ //
+ HeciSendLength = sizeof (BIOSNV_SET_ACM_TPM);
+ Status = Heci->SendMsg (
+ (UINT32 *) &SetAcmTpmMsg,
+ HeciSendLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+ if (EFI_ERROR(Status)) {
+ return Status;
+ }
+
+ //
+ // Get Set ACM TPM Data MKHI ACK message
+ //
+ HeciRecvLength = sizeof (BIOSNV_SET_ACM_TPM_ACK);
+ Status = Heci->ReadMsg (
+ BLOCKING,
+ (UINT32 *) &SetAcmTpmMsgAck,
+ &HeciRecvLength
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ return Status;
+}
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.h b/ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.h
new file mode 100644
index 0000000..4622608
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/HeciMsgLib.h
@@ -0,0 +1,782 @@
+/** @file
+ Header file for Heci Message functionality
+
+@copyright
+ Copyright (c) 2006 - 2013 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+--*/
+#ifndef _HECI_MESSAGE_LIB_H_
+#define _HECI_MESSAGE_LIB_H_
+
+#include "CoreBiosMsg.h"
+
+#include EFI_PROTOCOL_DEFINITION (HECI)
+#include EFI_PROTOCOL_DEFINITION (PlatformMeHook)
+#include EFI_PROTOCOL_DEFINITION (MePlatformPolicy)
+
+//
+// Reset Request Origin Codes.
+//
+#define PEI_HECI_REQ_ORIGIN_BIOS_MEMORY_INIT 0x01
+#define PEI_HECI_REQ_ORIGIN_BIOS_POST 0x02
+#define PEI_HECI_REQ_ORIGIN_AMTBX_LAN_DISABLE 0x03
+
+//
+// End of Post Codes
+//
+#define HECI_EOP_STATUS_SUCCESS 0x0
+#define HECI_EOP_PERFORM_GLOBAL_RESET 0x1
+#define MAX_EOP_SEND_RETRIES 0x2
+
+//
+// IFR Update states
+//
+#define IFR_UPDATE_ENABLE 1
+#define IFR_UPDATE_DISABLE 0
+
+#define EFI_ME_FW_SKU_VARIABLE_GUID \
+ { \
+ 0xe1a21d94, 0x4a20, 0x4e0e, 0xae, 0x9, 0xa9, 0xa2, 0x1f, 0x24, 0xbb, 0x9e \
+ }
+
+//
+// Heci Bus Disable defines
+//
+#define HECI_BUS_DISABLE_OPCODE 0x0C
+#define HECI_BUS_DISABLE_ACK_OPCODE 0x8C
+#define ME_HECI_FIXED_ADDRESS 0x0
+
+//
+// Defines the HECI request buffer format for the ICC_MPHY_WRITE_SETTINGS_CMD.
+//
+typedef struct _ICC_MPHY_WRITE_SETTINGS_REQ
+{
+ ICC_HEADER Header; // Standard ICC HECI Header
+ UINT32 Reserved : 4; // Reserved for future use
+ UINT32 PostedWrite : 1; // 0-Response returned, 1-No Response returned
+ UINT32 Reserved2 : 23; // Reserved for future use
+}MPHY_WRITE_SETTINGS_REQ;
+
+typedef union _HBM_COMMAND {
+ UINT8 Data;
+ struct {
+ UINT8 Command : 7;
+ UINT8 IsResponse : 1;
+ } Fields;
+} HBM_COMMAND;
+
+typedef struct _HECI_BUS_DISABLE_CMD {
+ HBM_COMMAND Command;
+ UINT8 Reserved[3];
+} HECI_BUS_DISABLE_CMD;
+
+typedef struct _HECI_BUS_DISABLE_CMD_ACK {
+ HBM_COMMAND Command;
+ UINT8 Status;
+ UINT8 Reserved[2];
+} HECI_BUS_DISABLE_CMD_ACK;
+
+typedef struct {
+ UINT32 MeEnabled : 1; ///< [0] ME enabled/Disabled
+ UINT32 Reserved : 2; ///< [2:1] Reserved, must set to 0
+ UINT32 IntelAmtFw : 1; ///< [3] Intel AMT FW support
+ UINT32 IntelAmtFwStandard : 1; ///< [4] Intel AMT Standard FW support
+ UINT32 IntelSmallBusiness : 1; ///< [5] Intel Small Business Technology support
+ UINT32 Reserved1 : 7; ///< [12:6] Reserved
+ UINT32 AtSupported : 1; ///< [13] AT Support
+ UINT32 IntelKVM : 1; ///< [14] Intel KVM supported
+ UINT32 LocalWakeupTimer : 1; ///< [15] Local Wakeup Timer support
+ UINT32 Reserved2 : 16; ///< [31:16] Reserved, must set to 0
+ UINT32 MeMinorVer : 16; ///< [47:32] ME FW Minor Version.
+ UINT32 MeMajorVer : 16; ///< [63:48] ME FW Major Version.
+ UINT32 MeBuildNo : 16; ///< [79:64] ME FW Build Number.
+ UINT32 MeHotFixNo : 16; ///< [95:80] ME FW Hotfix Number
+} ME_CAP;
+
+#define MAX_ASSET_TABLE_ALLOCATED_SIZE 0x3000
+#define HECI_HWA_CLIENT_ID 11
+#define HWA_TABLE_PUSH_CMD 0
+
+#pragma pack(1)
+
+typedef enum _HWAI_TABLE_TYPE_INDEX
+{
+ HWAI_TABLE_TYPE_INDEX_FRU_DEVICE = 0,
+ HWAI_TABLE_TYPE_INDEX_MEDIA_DEVICE,
+ HWAI_TABLE_TYPE_INDEX_SMBIOS,
+ HWAI_TABLE_TYPE_INDEX_ASF,
+ HWAI_TABLE_TYPE_INDEX_MAX = 4,
+} HWAI_TABLE_TYPE_INDEX;
+
+typedef struct _SINGLE_TABLE_POSITION {
+ UINT16 Offset;
+ UINT16 Length;
+} SINGLE_TABLE_POSITION;
+
+typedef struct _TABLE_PUSH_DATA {
+ SINGLE_TABLE_POSITION Tables[HWAI_TABLE_TYPE_INDEX_MAX];
+ UINT8 TableData[1];
+} TABLE_PUSH_DATA;
+
+typedef union {
+ UINT32 Data;
+ struct {
+ UINT32 MessageLength : 16;
+ UINT32 Command : 4; ///< only supported command would be HWA_TABLE_PUSH=0;
+ UINT32 FRUTablePresent : 1;
+ UINT32 MediaTablePresent : 1;
+ UINT32 SMBIOSTablePresent : 1;
+ UINT32 ASFTablePresent : 1;
+ UINT32 Reserved : 8;
+ } Fields;
+} AU_MESSAGE_HEADER;
+
+typedef struct _AU_TABLE_PUSH_MSG {
+ AU_MESSAGE_HEADER Header;
+ TABLE_PUSH_DATA Data;
+} AU_TABLE_PUSH_MSG;
+
+typedef enum {
+ SEV_NO_ERROR = 0,
+ SEV_LOW_ERROR,
+ SEV_HIGH_ERROR,
+ SEV_CRITICAL_ERROR
+} MDES_SEVERITY_LEVEL;
+
+typedef enum {
+ EFI_STATUS_CODE = 1,
+ RAW_BUFFER,
+ ASCII_DATA,
+} MDES_BIOS_PAYLOAD_TYPE;
+
+#pragma pack()
+
+/**
+ Send the required system ChipsetInit Table to ME FW.
+
+ @param[in] ChipsetInitTable The required system ChipsetInit Table.
+ @param[in] ChipsetInitTableLen Length of the table in bytes
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciChipsetInitSyncMsg (
+ IN UINT8 *ChipsetInitTable,
+ IN UINT32 ChipsetInitTableLen
+ )
+;
+
+/**
+ Send Core BIOS Reset Request Message through HECI to reset the system.
+
+ @param[in] ResetOrigin Reset source
+ @param[in] ResetType Global or Host reset
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciSendCbmResetRequest (
+ IN UINT8 ResetOrigin,
+ IN UINT8 ResetType
+ )
+;
+
+/**
+ Send Hardware Asset Tables to Firmware
+
+ @param[in] Handle A handle for this module
+ @param[in] AssetTableData Hardware Asset Table Data
+ @param[in] TableDataSize Size of Asset table
+
+ @retval EFI_SUCCESS Table sent
+ @retval EFI_ABORTED Could not allocate Memory
+**/
+EFI_STATUS
+HeciAssetUpdateFwMsg (
+ IN EFI_HANDLE Handle,
+ IN TABLE_PUSH_DATA *AssetTableData,
+ IN UINT16 TableDataSize
+ )
+;
+
+/**
+ Send End of Post Request Message through HECI.
+
+ @param[in] Handle A handle for this module
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciSendEndOfPostMessage (
+ IN EFI_HANDLE Handle
+ )
+;
+
+/**
+ Send Get Firmware SKU Request to ME
+
+ @param[in] MsgGenGetFwCapsSku Return message for Get Firmware Capability SKU
+ @param[in] MsgGenGetFwCapsSkuAck Return message for Get Firmware Capability SKU ACK
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetFwCapsSkuMsg (
+ IN OUT GEN_GET_FW_CAPSKU *MsgGenGetFwCapsSku,
+ IN OUT GEN_GET_FW_CAPS_SKU_ACK *MsgGenGetFwCapsSkuAck
+ )
+;
+
+/**
+ Send Get Firmware Version Request to ME
+
+ @param[in][out] MsgGenGetFwVersionAck Return themessage of FW version
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetFwVersionMsg (
+ IN OUT GEN_GET_FW_VER_ACK *MsgGenGetFwVersionAck
+ )
+;
+
+/**
+ Sends a message to ME to unlock a specified SPI Flash region for writing and receiving a response message.
+ It is recommended that HMRFPO_ENABLE MEI message needs to be sent after all OROMs finish their initialization.
+
+ @param[in] Nonce Nonce received in previous HMRFPO_ENABLE Response Message
+ @param[in] Result HMRFPO_ENABLE response
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciHmrfpoEnable (
+ IN UINT64 Nonce,
+ OUT UINT8 *Result
+ )
+;
+
+/**
+ Sends a message to ME to lock a specified SPI Flash region for writing and receiving a response message.
+
+ @param[out] Nonce Random number generated by Ignition ME FW. When BIOS
+ want to unlock region it should use this value
+ in HMRFPO_ENABLE Request Message
+ @param[out] FactoryDefaultBase The base of the factory default calculated from the start of the ME region.
+ BIOS sets a Protected Range (PR) register "Protected Range Base" field with this value
+ + the base address of the region.
+ @param[out] FactoryDefaultLimit The length of the factory image.
+ BIOS sets a Protected Range (PR) register "Protected Range Limit" field with this value
+ @param[out] Result Status report
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciHmrfpoLock (
+ OUT UINT64 *Nonce,
+ OUT UINT32 *FactoryDefaultBase,
+ OUT UINT32 *FactoryDefaultLimit,
+ OUT UINT8 *Result
+ )
+;
+
+/**
+ System BIOS sends this message to get status for HMRFPO_LOCK message.
+
+ @param[out] Result HMRFPO_GET_STATUS response
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+HeciHmrfpoGetStatus (
+ OUT UINT8 *Result
+ )
+;
+
+/**
+ This is used to send KVM request message to Intel ME. When
+ Bootoptions indicate that a KVM session is requested then BIOS
+ will send this message before any graphical display output to
+ ensure that FW is ready for KVM session.
+
+ @param[in] QueryType 0 - Query Request
+ 1 - Cancel Request
+ @param[out] ResponseCode 1h - Continue, KVM session established.
+ 2h - Continue, KVM session cancelled.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciQueryKvmRequest (
+ IN UINT32 QueryType,
+ OUT UINT32 *ResponseCode
+ )
+;
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP) on the boot
+ where host wants to query the local firmware update interface status.
+
+ @param[out] RuleData 1 - local firmware update interface enable
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetLocalFwUpdate (
+ OUT UINT8 *RuleData
+ )
+;
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP) on the boot
+ where host wants to enable or disable the local firmware update interface.
+ The firmware allows a single update once it receives the enable command
+
+ @param[in] RuleData 1 - local firmware update interface enable
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciSetLocalFwUpdate (
+ IN UINT8 RuleData
+ )
+;
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to enable the ME State. The firmware allows a single
+ update once it receives the enable command. Once firmware receives this message,
+ the firmware will be in normal mode after a global reset.
+
+ @param[in] None
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS ME enabled message sent
+**/
+EFI_STATUS
+HeciSetMeEnableMsg (
+ VOID
+ )
+;
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to disable the ME State. The firmware allows a single
+ update once it receives the disable command Once firmware receives this message,
+ the firmware will work in "Soft Temporary Disable" mode (HFS[19:16] = 3) after a
+ global reset. Note, this message is not allowed when AT firmware is enrolled/configured.
+
+ @param[in] None
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS ME is disabled
+**/
+EFI_STATUS
+HeciSetMeDisableMsg (
+ VOID
+ )
+;
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to get Ibex Peak platform type.
+ One of usages is to utilize this command to determine if the platform runs in
+ 1.5M or 5M size firmware.
+
+ @param[in] RuleData PlatformBrand,
+ IntelMeFwImageType,
+ SuperSku,
+ PlatformTargetMarketType,
+ PlatformTargetUsageType
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetPlatformTypeMsg (
+ OUT PLATFORM_TYPE_RULE_DATA *RuleData
+ )
+;
+
+/**
+ This message is sent by the BIOS on the boot where the host wants to get the firmware provisioning state.
+ The firmware will respond to AMT BIOS SYNCH INFO message even after the End of Post.
+
+ @param[out] RuleData Bit [2:0] Reserved
+ Bit [4:3] Provisioning State
+ 00 - Pre -provisioning
+ 01 - In -provisioning
+ 02 - Post !Vprovisioning
+ Bit [31:5] Reserved
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Firmware provisioning state returned
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciAmtBiosSynchInfo (
+ OUT UINT32 *RuleData
+ )
+;
+
+/**
+ The firmware will respond to GET OEM TAG message even after the End of Post (EOP).
+
+ @param[in] RuleData Default is zero. Tool can create the OEM specific OEM TAG data.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetOemTagMsg (
+ OUT UINT32 *RuleData
+ )
+;
+
+/**
+ Enables/disables clocks. Used to turn off clocks in unused pci/pcie slots.
+ BIOS use this command when it enumerates PCI slots. When PCI slot is found unpopulated, the
+ BIOS can disable its clock through this MEI message. It is the BIOS requirement to know which
+ slot is controlled by which control bit.
+
+ @param[in] Enables each bit means corresponding clock should be turned on (1) or off (0)
+ @param[in] EnablesMask each bit means corresponding enable bit is valid (1) or should be ignored (0)
+ @param[in] ResponseMode 0 wait for response, 1 - skip
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY ME is not ready
+ @retval EFI_INVALID_PARAMETER ResponseMode is invalid value
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+EFIAPI
+HeciSetIccClockEnables (
+ IN UINT32 Enables,
+ IN UINT32 EnablesMask,
+ IN UINT8 ResponseMode
+ )
+;
+
+/**
+ Sets or reads Lock mask on ICC registers.
+ @param[in] AccessMode 0 - set, 1 - get
+ @param[in] ResponseMode 0 - firmware will answer, 1 - firmware will not answer
+ @param[in][out] LockRegInfo bundle count info and mask of registers to become (for 'set' mode) or are
+ (for 'get' mode) locked. Each bit represents a register. 0=lock, 1=don't lock
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_INVALID_PARAMETER ResponseMode or pointer of Mask is invalid value
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY Heci device hasn't ready yet
+**/
+EFI_STATUS
+HeciLockIccRegisters (
+ IN UINT8 AccessMode,
+ IN UINT8 ResponseMode,
+ IN OUT ICC_LOCK_REGS_INFO *LockRegInfo
+ )
+;
+
+/**
+ retrieves the number of currently used ICC clock profile
+
+ @param[out] Profile number of current ICC clock profile
+
+ @exception EFI_UNSUPPORTED ICC clock profile doesn't support
+ @retval EFI_NOT_READY Heci device hasn't ready yet
+**/
+EFI_STATUS
+HeciGetIccProfile (
+ OUT UINT8 *Profile
+ )
+;
+
+/**
+ Sets ICC clock profile to be used on next and following boots
+
+ @param[in] Profile number of profile to be used
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY Heci device hasn't ready yet
+**/
+EFI_STATUS
+HeciSetIccProfile (
+ IN UINT8 Profile
+ )
+;
+
+/**
+ Writes 1 dword of data to the icc register offset specified by RegOffset in the ICC Aux space
+ @param[in] RegOffset Register Offset in ICC Aux Space to write
+ @param[in] RegData Dword ICC register data to write
+ @param[in] ResponseMode 0 Wait for response, 1 - skip
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_DEVICE_ERROR Wrong response
+ @retval EFI_NOT_READY ME is not ready
+ @retval EFI_INVALID_PARAMETER ResponseMode is invalid value
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+EFIAPI
+HeciWriteIccRegDword (
+ IN UINT16 RegOffset,
+ IN UINT32 RegData,
+ IN UINT8 ResponseMode
+ )
+;
+/**
+ This message is used to turn on the Intel ME firmware MDES
+ capability, Intel SVT for PCH capability or both when the
+ system is in a post-manufactured state. Once firmware receives
+ this message, the firmware will enable selected platform debug
+ capabilities . The firmware will automatically disable all
+ platform debug capabilities if this message is not received
+ before receiving End Of Post.
+
+ @param[in] Data capabilities to be enabled
+ @param[out] Result 0x00 : Enable Success
+ Others : Enable Failure
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciPlatformDebugCapabilityMsg (
+ IN PLATFORM_DEBUG_CAP Data,
+ OUT UINT8 *Result
+ )
+;
+
+/**
+ It creates and sends Heci messages.
+
+ Remark:
+ Functionality is available only in release mode.
+ Using MDES in debug mode causes recursive calling of this function
+ because debug messages are sending from Heci->SendMsg function.
+
+ @param[in] CodeType Indicates the type of status code being reported.
+ @param[in] Value Describes the current status of a hardware or software entity.
+ This included information about the class and subclass that is
+ used to classify the entity as well as an operation.
+ @param[in] Instance The enumeration of a hardware or software entity within
+ the system. Valid instance numbers start with 1.
+ @param[in] CallerId This optional parameter may be used to identify the caller.
+ This parameter allows the status code driver to apply different
+ rules to different callers.
+ @param[in] Data This optional parameter may be used to pass additional data.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Opcode evaluation success.
+ @retval Other Opcode evaluation failed.
+**/
+EFI_STATUS
+HeciSendMdesStatusCode (
+ IN EFI_STATUS_CODE_TYPE CodeType,
+ IN EFI_STATUS_CODE_VALUE Value,
+ IN UINT32 Instance,
+ IN EFI_GUID * CallerId OPTIONAL,
+ IN EFI_STATUS_CODE_DATA * Data OPTIONAL
+ )
+;
+
+/**
+ Provides an interface to call function to send HECI message.
+
+ @param[in] Flags Indicates the status of the BIOS MDES.
+ @param[in] BiosEventFilters Indicates the status of the BIOS event filter group.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS HECI sent with success.
+**/
+EFI_STATUS
+HeciGetMdesConfig (
+ OUT MDES_BIOS_FLAGS *Flags,
+ OUT UINT32 *BiosEventFilters
+ )
+;
+
+
+/**
+ Sends the MKHI Enable/Disable manageability message.
+ The message will only work if bit 2 in the bitmasks is toggled.
+ To enable manageability:
+ EnableState = 0x00000004, and
+ DisableState = 0x00000000.
+ To disable manageability:
+ EnableState = 0x00000000, and
+ DisableState = 0x00000004
+
+ @param[in] EnableState Enable Bit Mask
+ @param[in] DisableState Disable Bit Mask
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciFwFeatureStateOverride (
+ IN UINT32 EnableState,
+ IN UINT32 DisableState
+ )
+;
+
+/**
+ The Get FW Feature Status message is based on MKHI interface.
+ This command is used by BIOS/IntelR MEBX to get firmware runtime status.
+ The GET FW RUNTIME STATUS message doesn't need to check the HFS.
+ FWInitComplete value before sending the command.
+ It means this message can be sent regardless of HFS.FWInitComplete.
+
+ @param[out] RuleData MEFWCAPS_SKU message
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+**/
+EFI_STATUS
+HeciGetFwFeatureStateMsg (
+ OUT MEFWCAPS_SKU *RuleData
+ )
+;
+
+/**
+ This message is sent by the BIOS when it wants to query
+ the independent firmware recovery (IFR).
+
+ @param[in] RuleData 1 - local firmware update interface enable
+
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciGetIfrUpdate (
+ OUT UINT8 *RuleData
+ )
+;
+
+/**
+ This message is sent by the BIOS when it wants to set
+ the independent firmware recovery (IFR) state.
+
+ @param[in] RuleData 1 - local firmware update interface enable
+ 0 - local firmware update interface disable
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+ @retval EFI_BUFFER_TOO_SMALL Message Buffer is too smallfor the Acknowledge
+**/
+EFI_STATUS
+HeciSetIfrUpdate (
+ IN UINT8 RuleData
+ )
+;
+
+/**
+ This message is sent by the BIOS if EOP-ACK not received to force ME to disable
+ HECI interfaces.
+
+ @param[in] None
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS HECI interfaces disabled by ME
+**/
+EFI_STATUS
+HeciDisableHeciBusMsg (
+ VOID
+ )
+;
+
+/**
+ This message is sent by the BIOS to inform ME FW whether or not to take the
+ TPM 1.2 Deactivate flow
+
+ @param[in] UINT8 TpmDeactivate 0 - ME FW should not take the
+ deactivate flow.
+ 1 - ME FW should take the deactivate
+ flow.
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS HECI interfaces disabled by ME
+**/
+EFI_STATUS
+HeciSendTpmData (
+ IN UINT8 TpmDeactivate
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MbpDebugDumpDxe.c b/ReferenceCode/ME/Library/MeKernel/Dxe/MbpDebugDumpDxe.c
new file mode 100644
index 0000000..b7cc842
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MbpDebugDumpDxe.c
@@ -0,0 +1,150 @@
+/** @file
+ Dump whole DXE_MBP_DATA_PROTOCOL and serial out.
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include EFI_PROTOCOL_CONSUMER (MeBiosPayloadData)
+#endif
+
+/**
+ Dump DXE_MBP_DATA_PROTOCOL
+
+ @param[in] MbpData Pointer to DXE_MBP_DATA_PROTOCOL
+
+ @retval None
+**/
+VOID
+DxeMbpDebugDump (
+ IN DXE_MBP_DATA_PROTOCOL *MbpPtr
+ )
+{
+ UINTN i;
+
+ if (MbpPtr == NULL) {
+ return;
+ }
+ DEBUG ((EFI_D_INFO, "\n------------------------ MeBiosPayload Data Protocol Dump Begin -----------------\n"));
+ DEBUG ((EFI_D_INFO, " Revision : 0x%x\n", MbpPtr->Revision));
+ DEBUG ((EFI_D_INFO, "MeBiosPayload FwVersionName ---\n"));
+ DEBUG ((EFI_D_INFO, " ME FW MajorVersion : 0x%x\n", MbpPtr->MeBiosPayload.FwVersionName.MajorVersion));
+ DEBUG ((EFI_D_INFO, " ME FW MinorVersion : 0x%x\n", MbpPtr->MeBiosPayload.FwVersionName.MinorVersion));
+ DEBUG ((EFI_D_INFO, " ME FW HotfixVersion : 0x%x\n", MbpPtr->MeBiosPayload.FwVersionName.HotfixVersion));
+ DEBUG ((EFI_D_INFO, " ME FW BuildVersion : 0x%x\n", MbpPtr->MeBiosPayload.FwVersionName.BuildVersion));
+
+ if (MbpPtr->MeBiosPayload.FwCapsSku.Available == TRUE) {
+ DEBUG ((EFI_D_INFO, "MeBiosPayload FwCapabilities ---\n"));
+ DEBUG ((EFI_D_INFO, " FullNet : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.FullNet));
+ DEBUG ((EFI_D_INFO, " StdNet : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.StdNet));
+ DEBUG ((EFI_D_INFO, " Manageability : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.Manageability));
+ DEBUG ((EFI_D_INFO, " SmallBusiness : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.SmallBusiness));
+ DEBUG ((EFI_D_INFO, " IntelAT : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.IntelAT));
+ DEBUG ((EFI_D_INFO, " IntelCLS : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.IntelCLS));
+ DEBUG ((EFI_D_INFO, " IntelMPC : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.IntelMPC));
+ DEBUG ((EFI_D_INFO, " IccOverClocking : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.IccOverClocking));
+ DEBUG ((EFI_D_INFO, " PAVP : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.PAVP));
+ DEBUG ((EFI_D_INFO, " IPV6 : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.IPV6));
+ DEBUG ((EFI_D_INFO, " KVM : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.KVM));
+ DEBUG ((EFI_D_INFO, " OCH : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.OCH));
+ DEBUG ((EFI_D_INFO, " VLAN : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.VLAN));
+ DEBUG ((EFI_D_INFO, " TLS : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.TLS));
+ DEBUG ((EFI_D_INFO, " WLAN : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.WLAN));
+ DEBUG ((EFI_D_INFO, " NFC : 0x%x\n", MbpPtr->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.NFC));
+ }
+
+ if (MbpPtr->MeBiosPayload.FwFeaturesState.Available == TRUE) {
+ DEBUG ((EFI_D_INFO, "MeBiosPayload FwFeaturesState ---\n"));
+ DEBUG ((EFI_D_INFO, " FullNet : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.FullNet));
+ DEBUG ((EFI_D_INFO, " StdNet : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.StdNet));
+ DEBUG ((EFI_D_INFO, " Manageability : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.Manageability));
+ DEBUG ((EFI_D_INFO, " SmallBusiness : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.SmallBusiness));
+ DEBUG ((EFI_D_INFO, " IntelAT : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.IntelAT));
+ DEBUG ((EFI_D_INFO, " IntelCLS : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.IntelCLS));
+ DEBUG ((EFI_D_INFO, " IntelMPC : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.IntelMPC));
+ DEBUG ((EFI_D_INFO, " IccOverClocking : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.IccOverClocking));
+ DEBUG ((EFI_D_INFO, " PAVP : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.PAVP));
+ DEBUG ((EFI_D_INFO, " IPV6 : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.IPV6));
+ DEBUG ((EFI_D_INFO, " KVM : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.KVM));
+ DEBUG ((EFI_D_INFO, " OCH : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.OCH));
+ DEBUG ((EFI_D_INFO, " VLAN : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.VLAN));
+ DEBUG ((EFI_D_INFO, " TLS : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.TLS));
+ DEBUG ((EFI_D_INFO, " WLAN : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.WLAN));
+ DEBUG ((EFI_D_INFO, " NFC : 0x%x\n", MbpPtr->MeBiosPayload.FwFeaturesState.FwFeatures.Fields.NFC));
+ }
+
+ DEBUG ((EFI_D_INFO, "MeBiosPayload RomBistData ---\n"));
+ DEBUG ((EFI_D_INFO, " DeviceId : 0x%x\n", MbpPtr->MeBiosPayload.RomBistData.DeviceId));
+ DEBUG ((EFI_D_INFO, " FuseTestFlags : 0x%x\n", MbpPtr->MeBiosPayload.RomBistData.FuseTestFlags));
+ for (i = 0; i < 4; i++) {
+ DEBUG ((EFI_D_INFO, " UMCHID[0x%x] : 0x%x \n", i, MbpPtr->MeBiosPayload.RomBistData.UMCHID[i]));
+ }
+
+ DEBUG ((EFI_D_INFO, "MeBiosPayload Platform Key ---\n"));
+ for (i = 0; i < 8; i++) {
+ DEBUG ((EFI_D_INFO, " Key[0x%x] : 0x%x \n", i, MbpPtr->MeBiosPayload.PlatformKey.Key[i]));
+ }
+
+ if (MbpPtr->MeBiosPayload.FwPlatType.Available == TRUE) {
+ DEBUG ((EFI_D_INFO, "MeBiosPayload ME Platform TYpe ---\n"));
+ DEBUG ((EFI_D_INFO, " PlatformTargetUsageType : 0x%x\n", MbpPtr->MeBiosPayload.FwPlatType.RuleData.Fields.PlatformTargetUsageType));
+ DEBUG ((EFI_D_INFO, " PlatformTargetMarketType : 0x%x\n", MbpPtr->MeBiosPayload.FwPlatType.RuleData.Fields.PlatformTargetMarketType));
+ DEBUG ((EFI_D_INFO, " SuperSku : 0x%x\n", MbpPtr->MeBiosPayload.FwPlatType.RuleData.Fields.SuperSku));
+ DEBUG ((EFI_D_INFO, " IntelMeFwImageType : 0x%x\n", MbpPtr->MeBiosPayload.FwPlatType.RuleData.Fields.IntelMeFwImageType));
+ DEBUG ((EFI_D_INFO, " PlatformBrand : 0x%x\n", MbpPtr->MeBiosPayload.FwPlatType.RuleData.Fields.PlatformBrand));
+ }
+
+ DEBUG ((EFI_D_INFO, "MeBiosPayload IccProfile ---\n"));
+ DEBUG ((EFI_D_INFO, " NumIccProfiles : 0x%x\n", MbpPtr->MeBiosPayload.IccProfile.NumIccProfiles));
+ DEBUG ((EFI_D_INFO, " IccProfileSoftStrap : 0x%x\n", MbpPtr->MeBiosPayload.IccProfile.IccProfileSoftStrap));
+ DEBUG ((EFI_D_INFO, " IccProfileIndex : 0x%x\n", MbpPtr->MeBiosPayload.IccProfile.IccProfileIndex));
+ DEBUG ((EFI_D_INFO, " RegBundles : 0x%x\n", MbpPtr->MeBiosPayload.IccProfile.IccLockRegInfo.RegBundles));
+ for (i = 0; i < MbpPtr->MeBiosPayload.IccProfile.IccLockRegInfo.RegBundles.BundlesCnt; i++) {
+ DEBUG ((EFI_D_INFO, " RegMask[0x%x] : 0x%x\n", i, MbpPtr->MeBiosPayload.IccProfile.IccLockRegInfo.RegMask[i]));
+ }
+
+ DEBUG ((EFI_D_INFO, "MeBiosPayload AtState ---\n"));
+ DEBUG ((EFI_D_INFO, " State : 0x%x\n", MbpPtr->MeBiosPayload.AtState.State));
+ DEBUG ((EFI_D_INFO, " LastTheftTrigger : 0x%x\n", MbpPtr->MeBiosPayload.AtState.LastTheftTrigger));
+ DEBUG ((EFI_D_INFO, " LockState : 0x%x\n", MbpPtr->MeBiosPayload.AtState.flags.LockState));
+ DEBUG ((EFI_D_INFO, " AuthenticateModule : 0x%x\n", MbpPtr->MeBiosPayload.AtState.flags.AuthenticateModule));
+ DEBUG ((EFI_D_INFO, " S3Authentication : 0x%x\n", MbpPtr->MeBiosPayload.AtState.flags.S3Authentication));
+ DEBUG ((EFI_D_INFO, " FlashWearOut : 0x%x\n", MbpPtr->MeBiosPayload.AtState.flags.FlashWearOut));
+ DEBUG ((EFI_D_INFO, " FlashVariableSecurity : 0x%x\n", MbpPtr->MeBiosPayload.AtState.flags.FlashVariableSecurity));
+
+ DEBUG ((EFI_D_INFO, "MeBiosPayload MFSIntegrity: 0x%x\n", MbpPtr->MeBiosPayload.MFSIntegrity));
+
+ if (MbpPtr->MeBiosPayload.HwaRequest.Available == TRUE) {
+ DEBUG ((EFI_D_INFO, "MeBiosPayload HwaRequest ---\n"));
+ DEBUG ((EFI_D_INFO, " MediaTablePush : 0x%x\n", MbpPtr->MeBiosPayload.HwaRequest.Data.Fields.MediaTablePush));
+ }
+
+ if (MbpPtr->MeBiosPayload.NfcSupport.Available == TRUE) {
+ DEBUG ((EFI_D_INFO, "MeBiosPayload NFC ---\n"));
+ DEBUG ((EFI_D_INFO, " DeviceType : 0x%x\n", MbpPtr->MeBiosPayload.NfcSupport.NfcData.DeviceType));
+ DEBUG ((EFI_D_INFO, " Hide : 0x%x\n", MbpPtr->MeBiosPayload.NfcSupport.NfcData.Hide));
+ }
+
+ DEBUG ((EFI_D_INFO, "\n------------------------ MeBiosPayload Data Protocol Dump End -------------------\n"));
+}
+
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.c b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.c
new file mode 100644
index 0000000..b0df6c6
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.c
@@ -0,0 +1,712 @@
+/** @file
+ This is a library to get Intel ME information
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "MeLib.h"
+#include "MeAccess.h"
+#endif
+
+/**
+ Check if Me is enabled
+
+ @param[in] None.
+
+ @retval None
+**/
+EFI_STATUS
+MeLibInit (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ Status = EFI_SUCCESS;
+
+ return Status;
+}
+
+/**
+ Send Get Firmware SKU Request to ME
+
+ @param[in] FwCapsSku Return Data from Get Firmware Capabilities MKHI Request
+
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+HeciGetFwCapsSku (
+ MEFWCAPS_SKU *FwCapsSku
+ )
+{
+ EFI_STATUS Status;
+ GEN_GET_FW_CAPSKU MsgGenGetFwCapsSku;
+ GEN_GET_FW_CAPS_SKU_ACK MsgGenGetFwCapsSkuAck;
+
+ Status = HeciGetFwCapsSkuMsg (&MsgGenGetFwCapsSku, &MsgGenGetFwCapsSkuAck);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (((MsgGenGetFwCapsSkuAck.MKHIHeader.Fields.Command) == FWCAPS_GET_RULE_CMD) &&
+ ((MsgGenGetFwCapsSkuAck.MKHIHeader.Fields.IsResponse) == 1) &&
+ (MsgGenGetFwCapsSkuAck.MKHIHeader.Fields.Result == 0)
+ ) {
+ *FwCapsSku = MsgGenGetFwCapsSkuAck.Data.FWCapSku;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ This message is sent by the BIOS or IntelR MEBX prior to the End of Post (EOP)
+ on the boot where host wants to get Ibex Peak platform type.
+ One of usages is to utilize this command to determine if the platform runs in
+ 4M or 8M size firmware.
+
+ @param[in] RuleData PlatformBrand,
+ IntelMeFwImageType,
+ SuperSku,
+ PlatformTargetMarketType,
+ PlatformTargetUsageType
+
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+HeciGetPlatformType (
+ OUT PLATFORM_TYPE_RULE_DATA *RuleData
+ )
+{
+ EFI_STATUS Status;
+
+ Status = HeciGetPlatformTypeMsg (RuleData);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ return EFI_SUCCESS;
+}
+
+VOID
+MbpGiveUp (
+ IN VOID
+ )
+{
+ UINT32 HECI_BASE_ADDRESS;
+ HECI_HOST_CONTROL_REGISTER HeciRegHCsr;
+ VOLATILE HECI_HOST_CONTROL_REGISTER *HeciRegHCsrPtr;
+
+ HECI_BASE_ADDRESS = PciRead32 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI_FUNCTION_NUMBER, R_HECIMBAR)) & 0xFFFFFFF0;
+ HeciRegHCsrPtr = (VOID *) (UINTN) (HECI_BASE_ADDRESS + H_CSR);
+
+ //
+ // Set MBP_GIVE_UP bit
+ //
+ HeciPciOr32(R_ME_H_GS2, B_ME_MBP_GIVE_UP);
+
+ //
+ // Set H_RST and H_IG bits to reset HECI
+ //
+ HeciRegHCsr.ul = HeciRegHCsrPtr->ul;
+ HeciRegHCsr.r.H_RST = 1;
+ HeciRegHCsr.r.H_IG = 1;
+ HeciRegHCsrPtr->ul = HeciRegHCsr.ul;
+}
+
+/**
+ Routine checks whether MBP buffer has been cleared form HECI buffer or not.
+ BIOS must check this before executing any 3rd paty code or Oprom
+
+ @param[in] Event The event that triggered this notification function
+ @param[in] Context Pointer to the notification functions context
+**/
+VOID
+EFIAPI
+MbpCleared (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+{
+ EFI_STATUS Status;
+ HECI_GS_SHDW_REGISTER MeFwsts2;
+ DXE_MBP_DATA_PROTOCOL *MbpData;
+ HECI_FWS_REGISTER MeFirmwareStatus;
+ UINT32 Timeout;
+
+ gBS->CloseEvent (Event);
+
+ Status = gBS->LocateProtocol (&gMeBiosPayloadDataProtocolGuid, NULL, (VOID **) &MbpData);
+ if (!EFI_ERROR (Status)) {
+ //
+ // UnInstall the MBP protocol
+ //
+ Status = gBS->UninstallMultipleProtocolInterfaces (
+ MbpData->Handle,
+ &gMeBiosPayloadDataProtocolGuid,
+ MbpData,
+ NULL
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Uninstall Mbp protocol and Status is %r\n", Status));
+ }
+ }
+
+ //
+ // Check for MEI1 PCI device availability
+ //
+ if (HeciPciRead32 (R_VENDORID) == 0xFFFFFFFF) {
+ DEBUG ((EFI_D_ERROR, "MEI1 PCI device does not exist\n"));
+ return;
+ }
+
+ //
+ // BIOS polls on FWSTS.MbpCleared until it is set or 1s timeout reached
+ //
+ Timeout = 0;
+
+ do {
+ MeFwsts2.ul = HeciPciRead32 (R_ME_GS_SHDW);
+
+ if (MeFwsts2.r.MbpCleared) {
+ break;
+ }
+
+ gBS->Stall (FIVE_MS_TIMEOUT);
+ Timeout += FIVE_MS_TIMEOUT;
+ } while (Timeout <= HECI_MBP_CLR_TIMEOUT);
+
+ DEBUG ((EFI_D_ERROR, "MbpCleared = %x\n", MeFwsts2.r.MbpCleared));
+
+ if (!MeFwsts2.r.MbpCleared) {
+ MbpGiveUp();
+ }
+
+ MeFirmwareStatus.ul = HeciPciRead32 (R_FWSTATE);
+ if (MeFirmwareStatus.r.ErrorCode == ME_ERROR_CODE_UNKNOWN || MeFirmwareStatus.r.ErrorCode == ME_ERROR_CODE_IMAGE_FAILURE) {
+ DisableAllMEDevices ();
+ }
+
+ return;
+}
+
+/**
+ Calculate if the circular buffer has overflowed.
+ Corresponds to HECI HPS (part of) section 4.2.1
+
+ @param[in] ReadPointer Location of the read pointer.
+ @param[in] WritePointer Location of the write pointer.
+
+ @retval UINT8 Number of filled slots.
+**/
+UINT8
+FilledSlots2 (
+ IN UINT32 ReadPointer,
+ IN UINT32 WritePointer
+ )
+{
+ UINT8 FilledSlots;
+
+ ///
+ /// Calculation documented in HECI HPS 0.68 section 4.2.1
+ ///
+ FilledSlots = (((INT8) WritePointer) - ((INT8) ReadPointer));
+
+ return FilledSlots;
+}
+
+/**
+ This routine returns ME-BIOS Payload information.
+
+ @param[out] MbpPtr ME-BIOS Payload information.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_DEVICE_ERROR Failed to consume MBP
+**/
+EFI_STATUS
+PrepareMeBiosPayload (
+ OUT ME_BIOS_PAYLOAD *MbpPtr
+ )
+{
+ EFI_STATUS Status;
+ UINT32 *Ptr;
+ UINT32 MbpItemId;
+ UINT32 MbpItemSize;
+ UINT32 i;
+ UINT32 Index;
+ UINT32 Timeout;
+ UINT8 MbpReadAttempts;
+ MBP_HEADER MbpHeader;
+ MBP_ITEM_HEADER MbpItemHeader;
+ VOID *Registration;
+ EFI_EVENT Event;
+
+ HECI_GS_SHDW_REGISTER MeFwsts2;
+ UINT32 HECI_BASE_ADDRESS;
+ HECI_ME_CONTROL_REGISTER HeciRegMeCsrHa;
+ HECI_HOST_CONTROL_REGISTER HeciRegHCsr;
+ VOLATILE HECI_HOST_CONTROL_REGISTER *HeciRegHCsrPtr;
+ VOLATILE HECI_ME_CONTROL_REGISTER *HeciRegMeCsrHaPtr;
+ VOLATILE UINT32 *HeciRegMeCbrwPtr;
+ VOID *DestPtr;
+ UINTN DestSize;
+ BOOLEAN MbpReadError;
+
+ Ptr = NULL;
+ Status = EFI_SUCCESS;
+
+ //
+ // Initialize memory mapped register pointers
+ //
+ HECI_BASE_ADDRESS = PciRead32 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI_FUNCTION_NUMBER, R_HECIMBAR)) & 0xFFFFFFF0;
+ HeciRegHCsrPtr = (VOID *) (UINTN) (HECI_BASE_ADDRESS + H_CSR);
+ HeciRegMeCsrHaPtr = (VOID *) (UINTN) (HECI_BASE_ADDRESS + ME_CSR_HA);
+ HeciRegMeCbrwPtr = (VOID *) (UINTN) (HECI_BASE_ADDRESS + ME_CB_RW);
+
+ MeFwsts2.ul = HeciPciRead32 (R_ME_GS_SHDW);
+
+ for (MbpReadAttempts = 0; MbpReadAttempts <= HECI_MBP_READ_MAX_RETRIES; MbpReadAttempts++) {
+
+ DEBUG ((EFI_D_INFO, "MbpPresent = %x\n", MeFwsts2.r.MbpRdy));
+
+ if (MeFwsts2.r.MbpRdy) {
+
+ MbpReadError = FALSE;
+ HeciRegMeCsrHa.ul = HeciRegMeCsrHaPtr->ul;
+
+ if (FilledSlots2 (HeciRegMeCsrHa.r.ME_CBRP_HRA, HeciRegMeCsrHa.r.ME_CBWP_HRA) == 0) {
+ //
+ // Exit if the circular buffer is empty
+ //
+ DEBUG ((EFI_D_ERROR, "MBP is present but circular buffer is empty, exit.\n"));
+ MbpReadError = TRUE;
+ } else {
+
+ MbpHeader.Data = *HeciRegMeCbrwPtr;
+
+ DEBUG ((EFI_D_INFO, "MBP header: %x\n", MbpHeader.Data));
+ DEBUG ((EFI_D_INFO, "MbpSize: %x\n", MbpHeader.Fields.MbpSize));
+ DEBUG ((EFI_D_INFO, "No. of Mbp Entries: %x\n", MbpHeader.Fields.NumEntries));
+
+ MbpPtr->FwCapsSku.Available = FALSE;
+ MbpPtr->FwPlatType.Available = FALSE;
+ MbpPtr->HwaRequest.Available = FALSE;
+ MbpPtr->PlatBootPerfData.Available = FALSE;
+ MbpPtr->HwaRequest.Data.Fields.MediaTablePush = FALSE;
+ MbpPtr->NfcSupport.Available = FALSE;
+
+ for (i = 0; i < MbpHeader.Fields.NumEntries; i++) {
+ //
+ // If MBP Data Item is available but, RD and WR pointer are same, it indicates an error
+ // ME FW indication of number of MBP entries and size are wrong
+ //
+ HeciRegMeCsrHa.ul = HeciRegMeCsrHaPtr->ul;
+ if (FilledSlots2 (HeciRegMeCsrHa.r.ME_CBRP_HRA, HeciRegMeCsrHa.r.ME_CBWP_HRA) == 0) {
+ //
+ // Exit if the circular buffer is empty
+ //
+ DEBUG ((EFI_D_ERROR, "MBP Item is present but circular buffer is empty, exit.\n"));
+ MbpReadError = TRUE;
+ break;
+ }
+ //
+ // Consume MBP Item Header
+ //
+ MbpItemHeader.Data = *HeciRegMeCbrwPtr;
+ DEBUG ((EFI_D_INFO, "MBP Item %x header: %x\n", i + 1, MbpItemHeader.Data));
+
+ MbpItemId = (MbpItemHeader.Fields.AppId << 4) | MbpItemHeader.Fields.ItemId;
+ //
+ // Copy data from HECI buffer per size of each MBP item
+ //
+ MbpItemSize = MbpItemHeader.Fields.Length - 1;
+ Ptr = AllocateZeroPool ((MbpItemSize) * 4);
+ ASSERT (Ptr);
+ if (Ptr == NULL) {
+ goto MbpGiveup;
+ }
+
+ for (Index = 0; Index < MbpItemSize; Index++) {
+ Ptr[Index] = *HeciRegMeCbrwPtr;
+ DEBUG ((EFI_D_INFO, "MBP Item Data: %x\n", Ptr[Index]));
+ }
+
+ switch (MbpItemId) {
+ case 0x11:
+ //
+ // FW Version Name
+ //
+ DestSize = sizeof (MbpPtr->FwVersionName);
+ DestPtr = &MbpPtr->FwVersionName;
+ break;
+
+ case 0x12:
+ //
+ // FW Capabilities
+ //
+ DestSize = sizeof (MbpPtr->FwCapsSku.FwCapabilities);
+ DestPtr = &MbpPtr->FwCapsSku.FwCapabilities;
+ MbpPtr->FwCapsSku.Available = TRUE;
+ break;
+
+ case 0x13:
+ //
+ // ROM BIST Data
+ //
+ DestSize = sizeof (MbpPtr->RomBistData);
+ DestPtr = &MbpPtr->RomBistData;
+ break;
+
+ case 0x14:
+ //
+ // Platform Key
+ //
+ DestSize = sizeof (MbpPtr->PlatformKey);
+ DestPtr = &MbpPtr->PlatformKey;
+ break;
+
+ case 0x15:
+ //
+ // ME Platform TYpe
+ //
+ DestSize = sizeof (MbpPtr->FwPlatType.RuleData);
+ DestPtr = &MbpPtr->FwPlatType.RuleData;
+ MbpPtr->FwPlatType.Available = TRUE;
+ break;
+
+ case 0x16:
+ //
+ // ME MFS status
+ //
+ DestSize = sizeof (MbpPtr->MFSIntegrity);
+ DestPtr = &MbpPtr->MFSIntegrity;
+ break;
+
+ case 0x17:
+ ///
+ /// Platform timing information
+ ///
+ DestSize = sizeof (MbpPtr->PlatBootPerfData.MbpPerfData);
+ DestPtr = &MbpPtr->PlatBootPerfData.MbpPerfData;
+ MbpPtr->PlatBootPerfData.Available = TRUE;
+ break;
+
+ case 0x19:
+ //
+ // FW Features State
+ //
+ DestSize = sizeof (MbpPtr->FwFeaturesState.FwFeatures);
+ DestPtr = &MbpPtr->FwFeaturesState.FwFeatures;
+ MbpPtr->FwFeaturesState.Available = TRUE;
+ break;
+
+ case 0x31:
+ //
+ // AT State
+ //
+ DestSize = sizeof (MbpPtr->AtState);
+ DestPtr = &MbpPtr->AtState;
+ break;
+
+ case 0x41:
+ //
+ // HWA Request
+ //
+ DestSize = sizeof (MbpPtr->HwaRequest.Data);
+ DestPtr = &MbpPtr->HwaRequest.Data;
+ MbpPtr->HwaRequest.Available = TRUE;
+ break;
+
+ case 0x51:
+ //
+ // ICC Profile
+ //
+ DestSize = sizeof (MbpPtr->IccProfile);
+ DestPtr = &MbpPtr->IccProfile;
+ break;
+
+ case 0x61:
+ //
+ // NFC Data
+ //
+ DestSize = sizeof (MbpPtr->NfcSupport.NfcData);
+ DestPtr = &MbpPtr->NfcSupport.NfcData;
+ MbpPtr->NfcSupport.Available = TRUE;
+ break;
+
+ default:
+ //
+ // default case
+ //
+ DestSize = 0;
+ DestPtr = NULL;
+ break;
+ }
+ if (DestPtr != NULL) {
+ if ((MbpItemSize * 4) <= DestSize) {
+ CopyMem (DestPtr, Ptr, (MbpItemSize * 4));
+ } else {
+ DEBUG ((EFI_D_INFO, "Data size is larger than destination buffer. This item is not copied.\n"));
+ }
+ //
+ // Clear buffer
+ //
+ ZeroMem (Ptr, MbpItemSize * 4);
+ FreePool (Ptr);
+ }
+ }
+
+ //
+ // Check if after consuming MBP R/W counters are ok:
+ // ME_CBRP_HRA == ME_CBWP_HRA != 0
+ //
+ HeciRegMeCsrHa.ul = HeciRegMeCsrHaPtr->ul;
+
+ if (FilledSlots2 (HeciRegMeCsrHa.r.ME_CBRP_HRA, HeciRegMeCsrHa.r.ME_CBWP_HRA) != 0
+ || HeciRegMeCsrHa.r.ME_CBWP_HRA == 0) {
+ DEBUG ((EFI_D_INFO, "R/W pointers mismatch after MBP consume: ME_CBRP_HRA = %x, ME_CBWP_HRA = %x\n",
+ HeciRegMeCsrHa.r.ME_CBRP_HRA, HeciRegMeCsrHa.r.ME_CBWP_HRA));
+ MbpReadError = TRUE;
+ }
+
+ if (!MbpReadError) {
+ //
+ // Interrupt ME FW so FW can clear HECI buffer after MBP is consumed
+ //
+ HeciRegHCsr.ul = HeciRegHCsrPtr->ul;
+ HeciRegHCsr.r.H_IG = 1;
+ HeciRegHCsrPtr->ul = HeciRegHCsr.ul;
+
+ //
+ // Create a callback event to check MBP FWSTS bit
+ //
+ Status = gBS->CreateEvent (
+ EFI_EVENT_NOTIFY_SIGNAL,
+ EFI_TPL_CALLBACK,
+ MbpCleared,
+ NULL,
+ &Event
+ );
+ ASSERT_EFI_ERROR (Status);
+ //
+ // Register EXIT_PM_AUTH_PROTOCOL notify function
+ //
+ Status = gBS->RegisterProtocolNotify (
+ &gExitPmAuthProtocolGuid,
+ Event,
+ &Registration
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ goto Done;
+ }
+ }
+ } else {
+ //
+ // If MBP_RDY not set, give up reading MBP and continue
+ //
+ goto MbpGiveup;
+ }
+
+ //
+ // If MAX_RETRIES exceeded, give up
+ //
+ if (MbpReadError && MbpReadAttempts == HECI_MBP_READ_MAX_RETRIES) {
+ goto MbpGiveup;
+ }
+
+ //
+ // Interrupt ME FW so FW knows we're done with this MBP read attempt
+ //
+ HeciRegHCsr.ul = HeciRegHCsrPtr->ul;
+ HeciRegHCsr.r.H_IG = 1;
+ HeciRegHCsrPtr->ul = HeciRegHCsr.ul;
+
+ //
+ // Wait for MBP_RDY after failed read attempt
+ //
+ Timeout = 0;
+
+ do {
+ MeFwsts2.ul = HeciPciRead32 (R_ME_GS_SHDW);
+
+ if (MeFwsts2.r.MbpRdy) {
+ break;
+ }
+
+ gBS->Stall (FIVE_MS_TIMEOUT);
+ Timeout += FIVE_MS_TIMEOUT;
+ } while (Timeout <= HECI_MBP_RDY_TIMEOUT);
+ }
+
+MbpGiveup:
+ MbpGiveUp();
+ Status = EFI_DEVICE_ERROR;
+
+Done:
+ return Status;
+}
+
+/**
+ Send Get Firmware Version Request to ME
+
+ @param[in] MsgGenGetFwVersionAckData Return themessage of FW version
+
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+HeciGetFwVersion (
+ IN OUT GEN_GET_FW_VER_ACK_DATA *MsgGenGetFwVersionAckData
+ )
+{
+ EFI_STATUS Status;
+ GEN_GET_FW_VER_ACK MsgGenGetFwVersionAck;
+
+ Status = HeciGetFwVersionMsg (&MsgGenGetFwVersionAck);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if ((MsgGenGetFwVersionAck.MKHIHeader.Fields.Command == GEN_GET_FW_VERSION_CMD) &&
+ (MsgGenGetFwVersionAck.MKHIHeader.Fields.IsResponse == 1) &&
+ (MsgGenGetFwVersionAck.MKHIHeader.Fields.Result == 0)
+ ) {
+ *MsgGenGetFwVersionAckData = MsgGenGetFwVersionAck.Data;
+ }
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Host client gets Firmware update info from ME client
+
+ @param[in] MECapability Structure of FirmwareUpdateInfo
+
+ @exception EFI_UNSUPPORTED No MBP Data Protocol available
+**/
+EFI_STATUS
+HeciGetMeFwInfo (
+ IN OUT ME_CAP *MECapability
+ )
+{
+ EFI_STATUS Status;
+ DXE_MBP_DATA_PROTOCOL *MbpData;
+ MEFWCAPS_SKU FwCapsSku;
+
+ //
+ // Get the MBP Data.
+ //
+ Status = gBS->LocateProtocol (&gMeBiosPayloadDataProtocolGuid, NULL, (VOID **) &MbpData);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "HeciGetMeFwInfo: No MBP Data Protocol available\n"));
+ return EFI_UNSUPPORTED;
+ }
+
+ MECapability->MeEnabled = 1;
+
+ FwCapsSku.Data = MbpData->MeBiosPayload.FwCapsSku.FwCapabilities.Data;
+ if (FwCapsSku.Fields.IntelAT) {
+ MECapability->AtSupported = 1;
+ }
+
+ if (FwCapsSku.Fields.KVM) {
+ MECapability->IntelKVM = 1;
+ }
+
+ switch (MbpData->MeBiosPayload.FwPlatType.RuleData.Fields.PlatformBrand) {
+ case INTEL_AMT_BRAND:
+ MECapability->IntelAmtFw = 1;
+ MECapability->LocalWakeupTimer = 1;
+ break;
+
+ case INTEL_STAND_MANAGEABILITY_BRAND:
+ MECapability->IntelAmtFwStandard = 1;
+ break;
+
+ case INTEL_SMALL_BUSINESS_TECHNOLOGY_BRAND:
+ MECapability->IntelSmallBusiness = 1;
+ break;
+ }
+
+ MECapability->MeMajorVer = MbpData->MeBiosPayload.FwVersionName.MajorVersion;
+ MECapability->MeMinorVer = MbpData->MeBiosPayload.FwVersionName.MinorVersion;
+ MECapability->MeBuildNo = MbpData->MeBiosPayload.FwVersionName.BuildVersion;
+ MECapability->MeHotFixNo = MbpData->MeBiosPayload.FwVersionName.HotfixVersion;
+
+ return Status;
+}
+
+/**
+ Dummy return for Me signal event use
+
+ @param[in] Event The event that triggered this notification function
+ @param[in] Context Pointer to the notification functions context
+**/
+VOID
+EFIAPI
+MeEmptyEvent (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+{
+ return;
+}
+
+/**
+ Get AT State Information From Stored ME platform policy
+
+ @param[in] AtState Pointer to AT State Information
+ @param[in] AtLastTheftTrigger Pointer to Variable holding the cause of last AT Stolen Stae
+ @param[in] AtLockState Pointer to variable indicating whether AT is locked or not
+ @param[in] AtAmPref Pointer to variable indicating whether ATAM or PBA should be used
+
+ @retval EFI_SUCCESS The function completed successfully
+ @exception EFI_UNSUPPORTED No MBP Data Protocol available
+**/
+EFI_STATUS
+GetAtStateInfo (
+ IN AT_STATE_INFO *AtStateInfo
+ )
+{
+ EFI_STATUS Status;
+ DXE_MBP_DATA_PROTOCOL *MbpData;
+
+ //
+ // Get the ME platform policy.
+ //
+ Status = gBS->LocateProtocol (&gMeBiosPayloadDataProtocolGuid, NULL, (VOID **) &MbpData);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "GetAtStateInfo: No MBP Data Protocol available\n"));
+ return EFI_UNSUPPORTED;
+ }
+ AtStateInfo->State = MbpData->MeBiosPayload.AtState.State;
+ AtStateInfo->LastTheftTrigger = MbpData->MeBiosPayload.AtState.LastTheftTrigger;
+ AtStateInfo->flags.LockState = MbpData->MeBiosPayload.AtState.flags.LockState;
+ AtStateInfo->flags.AuthenticateModule = MbpData->MeBiosPayload.AtState.flags.AuthenticateModule;
+ AtStateInfo->flags.S3Authentication = MbpData->MeBiosPayload.AtState.flags.S3Authentication;
+ AtStateInfo->flags.FlashVariableSecurity = MbpData->MeBiosPayload.AtState.flags.FlashVariableSecurity;
+ AtStateInfo->flags.FlashWearOut = MbpData->MeBiosPayload.AtState.flags.FlashWearOut;
+
+ return EFI_SUCCESS;
+}
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.h b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.h
new file mode 100644
index 0000000..00ceec0
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.h
@@ -0,0 +1,203 @@
+/** @file
+ Header file for functions to get Intel ME information
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _ME_LIB_H_
+#define _ME_LIB_H_
+
+#include "MePolicyLib.h"
+#include "HeciMsgLib.h"
+#include "MeChipset.h"
+#include "HeciRegs.h"
+#include EFI_PROTOCOL_CONSUMER (MeBiosPayloadData)
+
+#define MBP_PRESENT_MASK 0x00000020
+#define FIVE_MS_TIMEOUT 5000
+
+extern EFI_GUID gExitPmAuthProtocolGuid;
+
+#pragma pack(push, 1)
+
+typedef union _MBP_HEADER {
+ UINT32 Data;
+ struct {
+ UINT32 MbpSize : 8; ///< Byte 0 - MBP Size in DW including Header
+ UINT32 NumEntries : 8; ///< Byte 1 - Number of Entries (Data Items) in MBP
+ UINT32 Rsvd : 16; ///< Byte 3:2 - Reserved
+ } Fields;
+} MBP_HEADER;
+
+typedef union _MBP_ITEM_HEADER {
+ UINT32 Data;
+ struct {
+ UINT32 AppId : 8; ///< Byte 0 - Application ID
+ UINT32 ItemId : 8; ///< Byte 1 - Item ID
+ UINT32 Length : 8; ///< Byte 2 - Length in DW
+ UINT32 Rsvd : 8; ///< Byte 3 - Reserved
+ } Fields;
+} MBP_ITEM_HEADER;
+
+#pragma pack(pop)
+
+/**
+ Check if Me is enabled
+
+ @param[in] None.
+
+ @retval None
+**/
+EFI_STATUS
+MeLibInit (
+ VOID
+ )
+;
+
+/**
+ Send Get Firmware SKU Request to ME
+
+ @param[in] FwCapsSku Return Data from Get Firmware Capabilities MKHI Request
+
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+HeciGetFwCapsSku (
+ MEFWCAPS_SKU *FwCapsSku
+ )
+;
+
+/**
+ This message is sent by the BIOS or Intel(R) MEBX prior to the End of Post (EOP) on the boot
+ where host wants to get Lynx Point platform type. One of usages is to utilize this command to
+ determine if the platform runs in 1.5M or 5M size firmware.
+
+ @param[out] RuleData PlatformBrand,
+ IntelMeFwImageType,
+ SuperSku,
+ PlatformTargetMarketType,
+ PlatformTargetUsageType
+
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+HeciGetPlatformType (
+ OUT PLATFORM_TYPE_RULE_DATA *RuleData
+ )
+;
+
+/**
+ Routine checks whether MBP buffer has been cleared form HECI buffer or not.
+ BIOS must check this before executing any 3rd paty code or Oprom
+
+ @param[in] Event The event that triggered this notification function
+ @param[in] Context Pointer to the notification functions context
+**/
+VOID
+EFIAPI
+MbpCleared (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+;
+
+/**
+ This routine returns ME-BIOS Payload information from HECI buffer
+
+ @param[out] MbpPtr ME-BIOS Payload information.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_DEVICE_ERROR Failed to consume MBP
+**/
+EFI_STATUS
+PrepareMeBiosPayload (
+ OUT ME_BIOS_PAYLOAD *MbpPtr
+ )
+;
+
+/**
+ Send Get Firmware Version Request to ME
+
+ @param[in] MsgGenGetFwVersionAckData Return themessage of FW version
+
+ @retval EFI_SUCCESS The function completed successfully.
+**/
+EFI_STATUS
+HeciGetFwVersion (
+ IN OUT GEN_GET_FW_VER_ACK_DATA *MsgGenGetFwVersionAckData
+ )
+;
+
+/**
+ Host client gets Firmware update info from ME client for SMBIOS Table 131
+
+ @param[in][out] MECapability Structure of FirmwareUpdateInfo
+
+ @exception EFI_UNSUPPORTED No MBP Data Protocol available
+**/
+EFI_STATUS
+HeciGetMeFwInfo (
+ IN OUT ME_CAP *MECapability
+ )
+;
+
+/**
+ This is a dummy event to be hooked to provide ME or Platform
+ code before EOP Heci message is sent
+
+ @param[in] Event The event that triggered this notification function
+ @param[in] Context Pointer to the notification functions context
+**/
+VOID
+EFIAPI
+MeEmptyEvent (
+ IN EFI_EVENT Event,
+ IN VOID *Context
+ )
+;
+
+/**
+ Get AT State Information From ME FW
+
+ @param[in] AtState Pointer to AT State Information
+ @param[in] AtLastTheftTrigger Pointer to Variable holding the cause of last AT Stolen Stae
+ @param[in] AtLockState Pointer to variable indicating whether AT is locked or not
+ @param[in] AtAmPref Pointer to variable indicating whether ATAM or PBA should be used
+
+ @retval EFI_SUCCESS The function completed successfully
+ @exception EFI_UNSUPPORTED No MBP Data Protocol available
+**/
+EFI_STATUS
+GetAtStateInfo (
+ IN AT_STATE_INFO *AtStateInfo
+ )
+;
+
+/**
+ Dump DXE_MBP_DATA_PROTOCOL
+
+ @param[in] MbpData Pointer to DXE_MBP_DATA_PROTOCOL
+
+ @retval None
+**/
+VOID
+DxeMbpDebugDump (
+ IN DXE_MBP_DATA_PROTOCOL *MbpPtr
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.inf b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.inf
new file mode 100644
index 0000000..5e340e4
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLib.inf
@@ -0,0 +1,68 @@
+## @file
+# Component description file for Me functionality
+#
+#@copyright
+# Copyright (c) 2010 - 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = MeLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ MeLib.c
+ MeLib.h
+ MePolicyLib.c
+ MePolicyLib.h
+ HeciMsgLib.c
+ HeciMsgLib.h
+ MePolicyDebugDumpDxe.c
+ MbpDebugDumpDxe.c
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Include
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Heci/Include
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ MeProtocolLib
+ MeChipsetLib
+ EdkIIGlueBasePciLibPciExpress
+ EdkIIGlueDxeMemoryAllocationLib
+ EdkFrameworkProtocolLib
+ PrintLib
+ EfiCommonLib
+ EdkIIGlueDxeFirmwarePerformanceLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__ \
+ -D __EDKII_GLUE_UEFI_RUNTIME_SERVICES_TABLE_LIB__
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.cif b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.cif
new file mode 100644
index 0000000..3fc38ab
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.cif
@@ -0,0 +1,18 @@
+<component>
+ name = "MeLibDxe"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\MeKernel\Dxe\"
+ RefName = "MeLibDxe"
+[files]
+"MeLib.c"
+"MeLib.h"
+"MeLibDxe.mak"
+"MeLibDxe.sdl"
+"MePolicyLib.c"
+"MePolicyLib.h"
+"MeLib.inf"
+"HeciMsgLib.c"
+"HeciMsgLib.h"
+"MbpDebugDumpDxe.c"
+"MePolicyDebugDumpDxe.c"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.mak b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.mak
new file mode 100644
index 0000000..367e4c0
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.mak
@@ -0,0 +1,60 @@
+# /*++
+# Copyright (c) 2009 Intel Corporation. All rights reserved.
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+# --*/
+# MAK file for the ModulePart:MeLibDxe
+all : MeLibDxe
+
+$(BUILD_DIR)\MeLibDxe.lib : MeLibDxe
+
+MeLibDxe : $(BUILD_DIR)\MeLibDxe.mak MeLibDxeBin
+
+$(BUILD_DIR)\MeLibDxe.mak : $(MeLibDxe_DIR)\$(@B).cif $(MeLibDxe_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(MeLibDxe_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+MeLibDxe_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES) \
+ $(ME_INCLUDES) \
+ -I$(INTEL_COUGAR_POINT_DIR)\
+ $(INTEL_PCH_INCLUDES)
+
+MeLibDxe_DEFINES=\
+ $(MY_DEFINES)/D __EDKII_GLUE_BASE_MEMORY_LIB__\
+ /D __EDKII_GLUE_EDK_DXE_RUNTIME_DRIVER_LIB__\
+ /D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__\
+ /D __EDKII_GLUE_BASE_PCI_LIB_PCI_EXPRESS__
+
+MeLibDxe_LIBS=\
+ $(MeProtocolLib_LIB)\
+ $(EdkIIGlueBasePciLibPciExpress_LIB)\
+ $(COMPILERSTUB)\
+ $(EdkIIGlueSmmFirmwarePerformanceLib_LIB)\
+ $(EDKFRAMEWORKGUIDLIB)\
+
+
+MeLibDxeBin : $(MeLibDxe_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ /f $(BUILD_DIR)\MeLibDxe.mak all \
+ "MY_INCLUDES=$(MeLibDxe_INCLUDES)" \
+ "MY_DEFINES=$(MeLibDxe_DEFINES)"\
+ TYPE=LIBRARY \
+#**********************************************************************
+#**********************************************************************
+#** **
+#** (C)Copyright 1985-2006, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 6145-F Northbelt Pkwy, Norcross, GA 30071 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#**********************************************************************
+#**********************************************************************
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.sdl b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.sdl
new file mode 100644
index 0000000..f69bf74
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MeLibDxe.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "MeLibDxe_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable MeLibDxe support in Project"
+End
+
+MODULE
+ Help = "Includes MeLibDxe.mak to Project"
+ File = "MeLibDxe.mak"
+End
+
+PATH
+ Name = "MeLibDxe_DIR"
+ Help = "Me Library file source directory"
+End
+
+ELINK
+ Name = "MeLibDxe_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\MeLibDxe.lib"
+ Parent = "MeLibDxe_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MeLibDxe_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyDebugDumpDxe.c b/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyDebugDumpDxe.c
new file mode 100644
index 0000000..bdfe7e5
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyDebugDumpDxe.c
@@ -0,0 +1,72 @@
+/** @file
+ Dump whole DXE_ME_POLICY_PROTOCOL and serial out.
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "MePolicyLib.h"
+#endif
+
+extern DXE_ME_POLICY_PROTOCOL *mDxePlatformMePolicy;
+
+/**
+ Dump DXE ME Platform Policy
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+DxeMePolicyDebugDump (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ Status = MePolicyLibInit ();
+ if (EFI_ERROR (Status)) {
+ return;
+ }
+
+#ifdef EFI_DEBUG
+ DEBUG ((EFI_D_INFO, "\n------------------------ MePlatformPolicy Dump Begin -----------------\n"));
+ DEBUG ((EFI_D_INFO, " Revision : 0x%x\n", mDxePlatformMePolicy->Revision));
+ DEBUG ((EFI_D_INFO, "MeConfig ---\n"));
+ //
+ // Byte 0, bit definition for functionality enable/disable
+ //
+ DEBUG ((EFI_D_INFO, " MeFwDownGrade : 0x%x\n", mDxePlatformMePolicy->MeConfig.MeFwDownGrade));
+ DEBUG ((EFI_D_INFO, " MeLocalFwUpdEnabled : 0x%x\n", mDxePlatformMePolicy->MeConfig.MeLocalFwUpdEnabled));
+ DEBUG ((EFI_D_INFO, " EndOfPostEnabled : 0x%x\n", mDxePlatformMePolicy->MeConfig.EndOfPostEnabled));
+ DEBUG ((EFI_D_INFO, " EndOfPostDone : 0x%x\n", mDxePlatformMePolicy->MeConfig.EndOfPostDone));
+ DEBUG ((EFI_D_INFO, " MdesCapability : 0x%x\n", mDxePlatformMePolicy->MeConfig.MdesCapability));
+ DEBUG ((EFI_D_INFO, " SvtForPchCap : 0x%x\n", mDxePlatformMePolicy->MeConfig.SvtForPchCap));
+ DEBUG ((EFI_D_INFO, " MdesForBiosState : 0x%x\n", mDxePlatformMePolicy->MeConfig.MdesForBiosState));
+
+ DEBUG ((EFI_D_INFO, "MeMiscConfig ---\n"));
+ DEBUG ((EFI_D_INFO, " FviSmbiosType : 0x%x\n", mDxePlatformMePolicy->MeMiscConfig.FviSmbiosType));
+ DEBUG ((EFI_D_INFO, "\n------------------------ MePlatformPolicy Dump End -------------------\n"));
+#endif
+}
+
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.c b/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.c
new file mode 100644
index 0000000..5f69857
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.c
@@ -0,0 +1,182 @@
+/** @file
+ Implementation file for Me Policy functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#include "MePolicyLib.h"
+#include "MeAccess.h"
+#include EFI_PROTOCOL_DEFINITION (HECI)
+#endif
+
+//
+// Global variables
+//
+DXE_ME_POLICY_PROTOCOL *mDxePlatformMePolicy = NULL;
+
+/**
+ Check if Me is enabled.
+
+ @param[in] None.
+
+ @retval EFI_SUCCESS ME platform policy pointer is initialized.
+ @retval All other error conditions encountered when no ME platform policy available.
+**/
+EFI_STATUS
+MePolicyLibInit (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformMePolicy != NULL) {
+ return EFI_SUCCESS;
+ }
+ //
+ // Get the desired platform setup policy.
+ //
+ Status = gBS->LocateProtocol (&gDxePlatformMePolicyGuid, NULL, (VOID **) &mDxePlatformMePolicy);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "No ME Platform Policy Protocol available"));
+ ASSERT_EFI_ERROR (Status);
+ } else if (mDxePlatformMePolicy == NULL) {
+ DEBUG ((EFI_D_ERROR, "No ME Platform Policy Protocol available"));
+ Status = EFI_UNSUPPORTED;
+ }
+ return Status;
+}
+
+/**
+ Check if End of Post Message is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE EndOfPost is disabled.
+ @retval TRUE EndOfPost is enabled.
+**/
+BOOLEAN
+MeEndOfPostEnabled (
+ VOID
+ )
+{
+ BOOLEAN Supported;
+ EFI_STATUS Status;
+
+ if (mDxePlatformMePolicy == NULL) {
+ Status = MePolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ if (mDxePlatformMePolicy->MeConfig.EndOfPostEnabled != 1) {
+ Supported = FALSE;
+ } else {
+ Supported = TRUE;
+ }
+
+ return Supported;
+}
+
+/**
+ Checks if EndOfPost event already happened
+
+ @param[in] None
+
+ @retval TRUE if end of post happened
+ @retval FALSE if not yet
+**/
+BOOLEAN
+IsAfterEndOfPost (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformMePolicy == NULL) {
+ Status = MePolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+
+ if (mDxePlatformMePolicy->MeConfig.EndOfPostDone == TRUE) {
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+ Show Me Error message. This is used to support display error message on the screen for localization
+ description
+
+ @param[in] MsgId Me error message ID for displaying on screen message
+
+ @retval None
+**/
+VOID
+MeReportError (
+ IN ME_ERROR_MSG_ID MsgId
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformMePolicy == NULL) {
+ Status = MePolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return;
+ }
+ }
+ mDxePlatformMePolicy->MeReportError (MsgId);
+
+ return ;
+}
+
+/**
+ Check if MeFwDowngrade is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE MeFwDowngrade is disabled.
+ @retval TRUE MeFwDowngrade is enabled.
+**/
+BOOLEAN
+MeFwDowngradeSupported (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ if (mDxePlatformMePolicy == NULL) {
+ Status = MePolicyLibInit();
+ if (EFI_ERROR(Status)) {
+ return FALSE;
+ }
+ }
+ if (mDxePlatformMePolicy->MeConfig.MeFwDownGrade == 1) {
+ return TRUE;
+ }
+
+ return FALSE;
+}
diff --git a/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.h b/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.h
new file mode 100644
index 0000000..1d315b5
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Dxe/MePolicyLib.h
@@ -0,0 +1,95 @@
+/** @file
+ Header file for Me Policy functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _ME_POLICY_LIB_H_
+#define _ME_POLICY_LIB_H_
+
+#include EFI_PROTOCOL_DEFINITION (MePlatformPolicy)
+
+/**
+ Check if Me is enabled.
+
+ @param[in] None.
+
+ @retval EFI_SUCCESS ME platform policy pointer is initialized.
+ @retval All other error conditions encountered when no ME platform policy available.
+**/
+EFI_STATUS
+MePolicyLibInit (
+ VOID
+ )
+;
+
+/**
+ Check if End of Post Message is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE EndOfPost is disabled.
+ @retval TRUE EndOfPost is enabled.
+**/
+BOOLEAN
+MeEndOfPostEnabled (
+ VOID
+ )
+;
+
+
+/**
+ Show Me Error message. This is used to support display error message on the screen for localization
+ description
+
+ @param[in] MsgId Me error message ID for displaying on screen message
+
+ @retval None
+**/
+VOID
+MeReportError (
+ IN ME_ERROR_MSG_ID MsgId
+ )
+;
+
+/**
+ Check if MeFwDowngrade is enabled in setup options.
+
+ @param[in] None.
+
+ @retval FALSE MeFwDowngrade is disabled.
+ @retval TRUE MeFwDowngrade is enabled.
+**/
+BOOLEAN
+MeFwDowngradeSupported (
+ VOID
+ )
+;
+
+/**
+ Dump DXE ME Platform Policy
+
+ @param[in] None.
+
+ @retval None
+**/
+VOID
+DxeMePolicyDebugDump (
+ VOID
+ )
+;
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.cif b/ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.cif
new file mode 100644
index 0000000..eaef885
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.cif
@@ -0,0 +1,12 @@
+<component>
+ name = "MeKernelLibrary"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\Me\Library\MeKernel\"
+ RefName = "MeKernelLibrary"
+[files]
+"MeKernelLibrary.sdl"
+[parts]
+"MeChipsetLib"
+"MeLibDxe"
+"MeLibPei"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.sdl b/ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.sdl
new file mode 100644
index 0000000..6055d0a
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/MeKernelLibrary.sdl
@@ -0,0 +1,20 @@
+TOKEN
+ Name = "MeKernelLibrary_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable Me Kernel Library support in Project"
+End
+
+PATH
+ Name = "MeKernelLibrary_DIR"
+ Help = "Me Library file source directory"
+End
+
+ELINK
+ Name = "/I$(MeKernelLibrary_DIR)\Include"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.c b/ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.c
new file mode 100644
index 0000000..905020b
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.c
@@ -0,0 +1,185 @@
+/** @file
+ Implementation file for Heci Message functionality
+
+@copyright
+ Copyright (c) 2010 - 2012 Intel Corporation. All rights
+ reserved This software and associated documentation (if any)
+ is furnished under a license and may only be used or copied in
+ accordance with the terms of the license. Except as permitted
+ by such license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGluePeim.h"
+#include "CoreBiosMsg.h"
+#include "HeciMsgLibPei.h"
+#include EFI_PPI_CONSUMER (Wdt)
+
+#endif
+
+/**
+ Start Watch Dog Timer HECI message
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] HeciPpi The pointer to HECI PPI
+ @param[in] HeciMemBar HECI Memory BAR
+ @param[in] WaitTimerBios The value of waiting limit
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+PeiHeciAsfStartWatchDog (
+ IN EFI_PEI_SERVICES **PeiServices,
+ IN PEI_HECI_PPI *HeciPpi,
+ IN UINT32 HeciMemBar,
+ IN UINT16 WaitTimerBios
+ )
+{
+ EFI_STATUS Status;
+ ASF_START_WDT AsfStartWdt;
+ UINT32 HeciLength;
+ UINT32 MeMode;
+
+ Status = HeciPpi->GetMeMode (PeiServices, &MeMode);
+ if (EFI_ERROR (Status) || (MeMode != ME_MODE_NORMAL)) {
+ return EFI_UNSUPPORTED;
+ }
+ ///
+ /// Clear Start Watch Dog Timer HECI message
+ ///
+ ZeroMem ((VOID *) &AsfStartWdt, sizeof (ASF_START_WDT));
+
+ AsfStartWdt.Command = ASF_MANAGEMENT_CONTROL;
+ AsfStartWdt.ByteCount = START_WDT_BYTE_COUNT;
+ AsfStartWdt.SubCommand = ASF_SUB_COMMAND_START_WDT;
+ AsfStartWdt.VersionNumber = START_WDT_VERSION_NUMBER;
+ AsfStartWdt.TimeoutLow = (UINT8) WaitTimerBios;
+ AsfStartWdt.TimeoutHigh = (UINT8) (WaitTimerBios >> 8);
+ AsfStartWdt.EventSensorType = START_WDT_EVENT_SENSOR_TYPE;
+ AsfStartWdt.EventType = START_WDT_EVENT_TYPE;
+ AsfStartWdt.EventOffset = START_WDT_EVENT_OFFSET;
+ AsfStartWdt.EventSourceType = START_WDT_EVENT_SOURCE_TYPE_BIOS;
+ AsfStartWdt.EventSeverity = START_WDT_EVENT_SEVERITY;
+ AsfStartWdt.SensorDevice = START_WDT_SENSOR_DEVICE;
+ AsfStartWdt.SensorNumber = START_WDT_SENSOR_NUMBER;
+ AsfStartWdt.Entity = START_WDT_ENTITY;
+ AsfStartWdt.EntityInstance = START_WDT_ENTITY_INSTANCE;
+ AsfStartWdt.EventData[0] = START_WDT_EVENT_DATA_BYTE_0;
+ AsfStartWdt.EventData[1] = START_WDT_EVENT_DATA_BYTE_1_BIOS_TIMEOUT;
+
+ HeciLength = ASF_START_WDT_LENGTH;
+
+ Status = HeciPpi->SendMsg (
+ PeiServices,
+ HeciPpi,
+ (UINT32 *) &AsfStartWdt,
+ HeciMemBar,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_ASF_MESSAGE_ADDR
+ );
+
+ return Status;
+}
+
+/**
+ Send Core BIOS Reset Request Message through HECI to reset the system.
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] ResetOrigin Reset source
+ @param[in] ResetType Global or Host reset
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+PeiHeciSendCbmResetRequest (
+ IN EFI_PEI_SERVICES **PeiServices,
+ IN UINT8 ResetOrigin,
+ IN UINT8 ResetType
+ )
+{
+ EFI_STATUS Status;
+ PEI_HECI_PPI *HeciPpi;
+ CBM_RESET_REQ CbmResetRequest;
+ UINT32 HeciLength;
+ UINT32 HeciMemBar;
+ PLATFORM_ME_HOOK_PPI *PlatformMeHookPpi;
+ EFI_GUID WdtPpiGuid = WDT_PPI_GUID;
+ WDT_PPI *WdtPpi;
+
+ Status = PeiServicesLocatePpi (
+ &gPlatformMeHookPpiGuid, // GUID
+ 0, // INSTANCE
+ NULL, // EFI_PEI_PPI_DESCRIPTOR
+ (VOID **) &PlatformMeHookPpi // PPI
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "Unable to Locate PlatformMeHook Protocol for Global Reset Hook, so skip instead.", Status));
+ } else {
+ PlatformMeHookPpi->PreGlobalReset (PeiServices, PlatformMeHookPpi);
+ }
+
+ Status = PeiServicesLocatePpi (
+ &gPeiHeciPpiGuid, // GUID
+ 0, // INSTANCE
+ NULL, // EFI_PEI_PPI_DESCRIPTOR
+ (VOID **) &HeciPpi // PPI
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ Status = HeciPpi->InitializeHeci (PeiServices, HeciPpi, &HeciMemBar);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ CbmResetRequest.MKHIHeader.Data = 0;
+ CbmResetRequest.MKHIHeader.Fields.Command = CBM_RESET_REQ_CMD;
+ CbmResetRequest.MKHIHeader.Fields.IsResponse = 0;
+ CbmResetRequest.MKHIHeader.Fields.GroupId = MKHI_CBM_GROUP_ID;
+ CbmResetRequest.MKHIHeader.Fields.Reserved = 0;
+ CbmResetRequest.MKHIHeader.Fields.Result = 0;
+ CbmResetRequest.Data.RequestOrigin = CBM_RR_REQ_ORIGIN_BIOS_MEMORY_INIT;
+ CbmResetRequest.Data.ResetType = CBM_HRR_GLOBAL_RESET;
+
+ HeciLength = sizeof (CBM_RESET_REQ);
+
+ Status = PeiServicesLocatePpi (
+ &WdtPpiGuid, // GUID
+ 0, // INSTANCE
+ NULL, // EFI_PEI_PPI_DESCRIPTOR
+ (VOID **) &WdtPpi // PPI
+ );
+ ASSERT_EFI_ERROR (Status);
+ WdtPpi->AllowKnownReset ();
+
+ Status = HeciPpi->SendMsg (
+ PeiServices,
+ HeciPpi,
+ (UINT32 *) &CbmResetRequest,
+ HeciMemBar,
+ HeciLength,
+ BIOS_FIXED_HOST_ADDR,
+ HECI_CORE_MESSAGE_ADDR
+ );
+
+ return Status;
+}
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.h b/ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.h
new file mode 100644
index 0000000..7d5c7ce
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/HeciMsgLibPei.h
@@ -0,0 +1,86 @@
+/** @file
+ Header file for Heci Message functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PEI_HECI_MESSAGE_LIB_H_
+#define _PEI_HECI_MESSAGE_LIB_H_
+
+#include EFI_PPI_DEFINITION (Heci)
+#include EFI_PPI_DEFINITION (PlatformMeHook)
+
+#define START_WDT_BYTE_COUNT 0x0F
+#define START_WDT_VERSION_NUMBER 0x10
+#define START_WDT_EVENT_SENSOR_TYPE 0x23
+#define START_WDT_EVENT_TYPE 0x6F
+#define START_WDT_EVENT_OFFSET 0x00
+#define START_WDT_EVENT_SOURCE_TYPE_OS 0x48
+#define START_WDT_EVENT_SOURCE_TYPE_BIOS 0x00
+#define START_WDT_EVENT_SOURCE_TYPE 0x00 ///< 0x00 - BIOs, 0x48 - OS
+#define START_WDT_EVENT_SEVERITY 0x10 ///< critical
+#define START_WDT_SENSOR_DEVICE 0xFF ///< unspecified
+#define START_WDT_SENSOR_NUMBER 0xFF ///< unspecified
+#define START_WDT_ENTITY 0x00 ///< unspecified
+#define START_WDT_ENTITY_INSTANCE 0x00 ///< unspecified
+#define START_WDT_EVENT_DATA_BYTE_0 0x40
+#define START_WDT_EVENT_DATA_BYTE_1 0x02 ///< 0x02 BIOS POST WDT Timeout, 0x04 OS WDT timeout
+#define START_WDT_EVENT_DATA_BYTE_1_BIOS_TIMEOUT 0x02
+#define START_WDT_EVENT_DATA_BYTE_1_OS_TIMEOUT 0x04
+
+/**
+ Start Watch Dog Timer HECI message
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] HeciPpi The pointer to HECI PPI
+ @param[in] HeciMemBar HECI Memory BAR
+ @param[in] WaitTimerBios The value of waiting limit
+
+ @exception EFI_UNSUPPORTED Current ME mode doesn't support this function
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+PeiHeciAsfStartWatchDog (
+ IN EFI_PEI_SERVICES **PeiServices,
+ IN PEI_HECI_PPI *HeciPpi,
+ IN UINT32 HeciMemBar,
+ IN UINT16 WaitTimerBios
+ )
+;
+
+/**
+ Send Core BIOS Reset Request Message through HECI to reset the system.
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] ResetOrigin Reset source
+ @param[in] ResetType Global or Host reset
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+ @retval EFI_TIMEOUT HECI does not return the buffer before timeout
+**/
+EFI_STATUS
+PeiHeciSendCbmResetRequest (
+ IN EFI_PEI_SERVICES **PeiServices,
+ IN UINT8 ResetOrigin,
+ IN UINT8 ResetType
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.cif b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.cif
new file mode 100644
index 0000000..195b908
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.cif
@@ -0,0 +1,15 @@
+<component>
+ name = "MeLibPei"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\MeKernel\Pei\"
+ RefName = "MeLibPei"
+[files]
+"MeLibPei.sdl"
+"MeLibPei.mak"
+"MePolicyLibPei.c"
+"MePolicyLibPei.h"
+"HeciMsgLibPei.c"
+"HeciMsgLibPei.h"
+"MeLibPei.h"
+"MeLibPei.inf"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.h b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.h
new file mode 100644
index 0000000..af3ad62
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.h
@@ -0,0 +1,27 @@
+/** @file
+ Header file for PEI Me functionality
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PEI_ME_LIB_H_
+#define _PEI_ME_LIB_H_
+
+#include "MePolicyLibPei.h"
+#include "HeciMsgLibPei.h"
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.inf b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.inf
new file mode 100644
index 0000000..78478c4
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.inf
@@ -0,0 +1,56 @@
+## @file
+# Component description file for Me Library functions for PEIMs
+#
+#@copyright
+# Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = MeLibPei
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ MePolicyLibPei.c
+ MePolicyLibPei.h
+ HeciMsgLibPei.c
+ HEciMsgLibPei.h
+ MeLibPei.h
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Include
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Include/Pei
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ MeLibPpi
+ EdkIIGluePeiServicesLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_PEI_SERVICES_LIB__
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.mak b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.mak
new file mode 100644
index 0000000..b9abbdf
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.mak
@@ -0,0 +1,53 @@
+# /*++
+# Copyright (c) 2009 Intel Corporation. All rights reserved.
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+# --*/
+# MAK file for the ModulePart:MeLibPei
+all : MeLibPei
+
+$(BUILD_DIR)\MeLibPei.lib : MeLibPei
+
+MeLibPei : $(BUILD_DIR)\MeLibPei.mak MeLibPeiBin
+
+$(BUILD_DIR)\MeLibPei.mak : $(MeLibPei_DIR)\$(@B).cif $(MeLibPei_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(MeLibPei_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+MeLibPei_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES)\
+ $(ME_INCLUDES) \
+ /I$(NB_BOARD_DIR)\
+ -I$(INTEL_COUGAR_POINT_DIR)\
+
+MeLibPei_DEFINES=\
+ /D __EDKII_GLUE_PEI_SERVICES_LIB__
+
+MeLibPei_LIBS=\
+ $(EdkIIGluePeiServicesLib_LIB)\
+ $(MeLibPpi_LIB)
+
+MeLibPeiBin : $(MeLibPei_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ /f $(BUILD_DIR)\MeLibPei.mak all \
+ "MY_INCLUDES=$(MeLibPei_INCLUDES)" \
+ "CFLAGS=$(CFLAGS) $(MeLibPei_DEFINES)"\
+ TYPE=PEI_LIBRARY \
+#**********************************************************************
+#**********************************************************************
+#** **
+#** (C)Copyright 1985-2006, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 6145-F Northbelt Pkwy, Norcross, GA 30071 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#**********************************************************************
+#**********************************************************************
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.sdl b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.sdl
new file mode 100644
index 0000000..9dfe312
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MeLibPei.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "MeLibPei_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable MeLibPei support in Project"
+End
+
+MODULE
+ Help = "Includes MeLibPei.mak to Project"
+ File = "MeLibPei.mak"
+End
+
+PATH
+ Name = "MeLibPei_DIR"
+ Help = "Me Library file source directory"
+End
+
+ELINK
+ Name = "MeLibPei_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\MeLibPei.lib"
+ Parent = "MeLibPei_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MeLibPei_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.c b/ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.c
new file mode 100644
index 0000000..733d6e3
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.c
@@ -0,0 +1,59 @@
+/** @file
+ Implementation file for Me Policy functionality for PEIM
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+
+//
+// External include files do NOT need to be explicitly specified in real EDKII
+// environment
+//
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGluePeim.h"
+#include "MePolicyLibPei.h"
+#endif
+
+/**
+ Check if Me is enabled.
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] PeiMePlatformPolicy The Me Platform Policy protocol instance
+
+ @retval EFI_SUCCESS ME platform policy Ppi loacted
+ @retval All other error conditions encountered when no ME platform policy Ppi
+**/
+EFI_STATUS
+PeiMePolicyLibInit (
+ IN EFI_PEI_SERVICES **PeiServices,
+ IN PEI_ME_PLATFORM_POLICY_PPI **PeiMePlatformPolicy
+ )
+{
+ EFI_STATUS Status;
+
+ //
+ // Locate system configuration variable
+ //
+ Status = PeiServicesLocatePpi (
+ &gPeiMePlatformPolicyPpiGuid, // GUID
+ 0, // INSTANCE
+ NULL, // EFI_PEI_PPI_DESCRIPTOR
+ (VOID **) PeiMePlatformPolicy // PPI
+ );
+ ASSERT_EFI_ERROR (Status);
+ return Status;
+}
diff --git a/ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.h b/ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.h
new file mode 100644
index 0000000..7de458b
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/Pei/MePolicyLibPei.h
@@ -0,0 +1,42 @@
+/** @file
+ Header file to define some function for getting the Intel ME policy PEI phase.
+
+@copyright
+ Copyright (c) 2006 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PEI_ME_POLICY_LIB_H_
+#define _PEI_ME_POLICY_LIB_H_
+
+#include EFI_PPI_DEFINITION (MePlatformPolicyPei)
+
+/**
+ Check if Me is enabled.
+
+ @param[in] PeiServices General purpose services available to every PEIM.
+ @param[in] PeiMePlatformPolicy The Me Platform Policy protocol instance
+
+ @retval EFI_SUCCESS ME platform policy Ppi loacted
+ @retval All other error conditions encountered when no ME platform policy Ppi
+**/
+EFI_STATUS
+PeiMePolicyLibInit (
+ IN EFI_PEI_SERVICES **PeiServices,
+ IN PEI_ME_PLATFORM_POLICY_PPI **PeiMePlatformPolicy
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/include/CoreBiosMsg.h b/ReferenceCode/ME/Library/MeKernel/include/CoreBiosMsg.h
new file mode 100644
index 0000000..bda1bc4
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/include/CoreBiosMsg.h
@@ -0,0 +1,625 @@
+/** @file
+ Core BIOS Messages
+
+@copyright
+ Copyright (c) 2008 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef CORE_BIOS_MSG_H
+#define CORE_BIOS_MSG_H
+
+#include "MkhiMsgs.h"
+
+#pragma pack(1)
+
+#define CBM_RESET_REQ_CMD 0x0B
+#define CBM_RESET_REQ_CMD_ACK 0x8B
+#define CBM_END_OF_POST_CMD 0x0C
+#define CBM_END_OF_POST_CMD_ACK 0x8C
+#define GEN_SET_DEBUG_MEMORY_CMD 0x11
+
+//
+// HECI Client Address - Core Messages
+// Core messages to coordinate memory initialization and UMA allocation with ME
+// as well as to inform ME of the end of POST event
+//
+#define HECI_CLIENT_CORE_MSG_DISPATCHER 0x07
+#define HOST_FIXED_ADDRESS 0x00
+
+typedef union _HECI_MESSAGE_HEADER {
+ UINT32 Data;
+ struct {
+ UINT32 MeAddress : 8;
+ UINT32 HostAddress : 8;
+ UINT32 Length : 9;
+ UINT32 Reserved : 6;
+ UINT32 MessageComplete : 1;
+ } Fields;
+} HECI_MESSAGE_HEADER;
+
+///
+/// Reset request message
+///
+typedef struct _CBM_RESET_REQ_DATA {
+ UINT8 RequestOrigin;
+ UINT8 ResetType;
+} CBM_RESET_REQ_DATA;
+
+typedef struct _CBM_RESET_REQ {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ CBM_RESET_REQ_DATA Data;
+} CBM_RESET_REQ;
+
+typedef struct _MKHI_CBM_RESET_REQ {
+ HECI_MESSAGE_HEADER Header;
+ CBM_RESET_REQ Msg;
+} MKHI_CBM_RESET_REQ;
+
+///
+/// Reset request ack message
+///
+typedef struct _CBM_RESET_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+} CBM_RESET_ACK;
+
+typedef struct _MKHI_CBM_RESET_ACK {
+ HECI_MESSAGE_HEADER Header;
+ CBM_RESET_ACK Msg;
+} MKHI_CBM_RESET_ACK;
+
+//
+// ASF Watch Dog Timer
+//
+#define ASF_MANAGEMENT_CONTROL 0x02
+#define ASF_SUB_COMMAND_START_WDT 0x13
+#define ASF_SUB_COMMAND_STOP_WDT 0x14
+
+///
+/// ASF Start Watch Dog
+///
+typedef struct _ASF_START_WDT {
+ UINT8 Command;
+ UINT8 ByteCount;
+ UINT8 SubCommand;
+ UINT8 VersionNumber;
+ UINT8 TimeoutLow;
+ UINT8 TimeoutHigh;
+ UINT8 EventSensorType;
+ UINT8 EventType;
+ UINT8 EventOffset;
+ UINT8 EventSourceType;
+ UINT8 EventSeverity;
+ UINT8 SensorDevice;
+ UINT8 SensorNumber;
+ UINT8 Entity;
+ UINT8 EntityInstance;
+ UINT8 EventData[5];
+} ASF_START_WDT;
+
+#define ASF_START_WDT_LENGTH 0x14
+
+///
+/// ASF Stop Watch Dog
+///
+typedef struct _ASF_STOP_WDT {
+ UINT8 Command;
+ UINT8 ByteCount;
+ UINT8 SubCommand;
+ UINT8 VersionNumber;
+} ASF_STOP_WDT;
+
+#define ASF_STOP_WDT_LENGTH 0x04
+
+//
+// HECI Header Definitions for Core BIOS Messages
+//
+#define CBM_END_OF_POST_HECI_HDR 0x80080001
+#define CBM_END_OF_POST_RESPONSE_HECI_HDR 0x80010001
+#define CBM_RESET_REQUEST_HECI_HDR 0x80030001
+#define CBM_RESET_RESPONSE_HECI_HDR 0x80020001
+
+//
+// Enumerations used in Core BIOS Messages
+//
+// End Of Post Codes.
+//
+#define CBM_EOP_EXITING_G3 0x01
+#define CBM_EOP_RESERVED 0x02
+#define CBM_EOP_EXITING_S3 0x03
+#define CBM_EOP_EXITING_S4 0x04
+#define CBM_EOP_EXITING_S5 0x05
+
+//
+// Reset Request Origin Codes.
+//
+#define CBM_RR_REQ_ORIGIN_BIOS_MEMORY_INIT 0x01
+#define CBM_RR_REQ_ORIGIN_BIOS_POST 0x02
+#define CBM_RR_REQ_ORIGIN_MEBX 0x03
+
+//
+// Reset Type Codes.
+//
+#define CBM_HRR_GLOBAL_RESET 0x01
+
+//
+// Reset Response Codes.
+//
+#define CBM_HRR_RES_REQ_NOT_ACCEPTED 0x01
+
+//
+// definitions for ICC MEI Messages
+//
+#define IBEX_PEAK_PLATFORM 0x00010000
+#define COUGAR_POINT_PLATFORM 0x00020000
+#define LYNX_POINT_PLATFORM 0x00030000
+
+typedef enum {
+ ICC_STATUS_SUCCESS = 0,
+ ICC_STATUS_SUCCESS_WAITING_FOR_RESET,
+ ICC_STATUS_INCORRECT_API_VERSION,
+ ICC_STATUS_INVALID_FUNCTION,
+ ICC_STATUS_INVALID_BUFFER_LENGTH,
+ ICC_STATUS_INVALID_PARAMETERS,
+ ICC_STATUS_FLASH_WEAR_OUT_VIOLATION,
+ ICC_STATUS_CLOCK_REQ_ENTRY_VIOLATION,
+ ICC_STATUS_STATIC_REGISTER_MASK_VIOLATION,
+ ICC_STATUS_DYNAMIC_REGISTER_MASK_VIOLATION,
+ ICC_STATUS_IMMEDIATE_REQUIRES_POWER_CYCLE,
+ ICC_STATUS_ILLEGAL_RECORD_ID,
+ ICC_STATUS_ENABLED_CLOCK_MASK_VIOLATION,
+ ICC_STATUS_INVALID = 0xFFFFFFFF
+} ICC_MEI_CMD_STATUS;
+
+typedef union _ICC_CLOCK_ENABLES_CONTROL_MASK {
+ UINT32 Dword;
+ struct {
+ UINT32 Flex0 : 1;
+ UINT32 Flex1 : 1;
+ UINT32 Flex2 : 1;
+ UINT32 Flex3 : 1;
+ UINT32 Reserved1 : 3;
+ UINT32 PCI_Clock0 : 1;
+ UINT32 PCI_Clock1 : 1;
+ UINT32 PCI_Clock2 : 1;
+ UINT32 PCI_Clock3 : 1;
+ UINT32 PCI_Clock4 : 1;
+ UINT32 Reserved2 : 4;
+ UINT32 SRC0 : 1;
+ UINT32 SRC1 : 1;
+ UINT32 SRC2 : 1;
+ UINT32 SRC3 : 1;
+ UINT32 SRC4 : 1;
+ UINT32 SRC5 : 1;
+ UINT32 SRC6 : 1;
+ UINT32 SRC7 : 1;
+ UINT32 CSI_SRC8 : 1;
+ UINT32 CSI_DP : 1;
+ UINT32 PEG_A : 1;
+ UINT32 PEG_B : 1;
+ UINT32 DMI : 1;
+ UINT32 Reserved3 : 3;
+ } Fields;
+} ICC_CLOCK_ENABLES_CONTROL_MASK;
+
+typedef enum {
+ LOCK_ICC_REGISTERS = 0x2,
+ SET_CLOCK_ENABLES = 0x3,
+ GET_ICC_PROFILE = 0x4,
+ SET_ICC_PROFILE = 0x5,
+ GET_ICC_CLOCKS_CAPABILITIES = 0x6,
+ GET_OEM_CLOCK_RANGE_DEFINITION_RECORD = 0x7,
+ GET_ICC_RECORD = 0x8,
+ READ_ICC_REGISTER = 0x9,
+ WRITE_ICC_REGISTER = 0xa,
+ WRITE_UOB_RECORD = 0xb,
+ READ_MPHY_SETTINGS = 0xe,
+ WRITE_MPHY_SETTINGS = 0xf
+} ICC_MEI_COMMAND_ID;
+
+typedef struct {
+ UINT32 ApiVersion;
+ ICC_MEI_COMMAND_ID IccCommand;
+ ICC_MEI_CMD_STATUS IccResponse;
+ UINT32 BufferLength;
+ UINT32 Reserved;
+} ICC_HEADER;
+
+typedef struct {
+ ICC_HEADER Header;
+} ICC_GET_PROFILE_MESSAGE;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT8 SupportedProfilesNumber;
+ UINT8 IccProfileSoftStrap;
+ UINT8 IccProfileIndex;
+ UINT8 Padding;
+} ICC_GET_PROFILE_RESPONSE;
+
+typedef union {
+ ICC_GET_PROFILE_MESSAGE message;
+ ICC_GET_PROFILE_RESPONSE response;
+} ICC_GET_PROFILE_BUFFER;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT8 ProfileBIOS;
+ UINT8 PaddingA;
+ UINT16 PaddingB;
+} ICC_SET_PROFILE_MESSAGE;
+
+typedef struct {
+ ICC_HEADER Header;
+} ICC_SET_PROFILE_RESPONSE;
+
+typedef union {
+ ICC_SET_PROFILE_MESSAGE message;
+ ICC_SET_PROFILE_RESPONSE response;
+} ICC_SET_PROFILE_BUFFER;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT32 ClockEnables;
+ UINT32 ClockEnablesMask;
+ UINT32 Params;
+} ICC_SET_CLK_ENABLES_MESSAGE;
+
+typedef struct {
+ ICC_HEADER Header;
+} ICC_SET_CLK_ENABLES_RESPONSE;
+
+typedef union {
+ ICC_SET_CLK_ENABLES_MESSAGE message;
+ ICC_SET_CLK_ENABLES_RESPONSE response;
+} ICC_SET_CLK_ENABLES_BUFFER;
+
+typedef struct {
+ ICC_HEADER Header;
+} ICC_GET_CLK_CAPABILITIES_MESSAGE;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT32 VersionNumber;
+ UINT8 IccHwSku;
+ UINT8 Reserved;
+ UINT16 MaxSusramRecordSize;
+ UINT64 IccSkuEnforcementTable;
+ UINT32 IccBootStatusReport;
+} ICC_GET_CLK_CAPABILITIES_RESPONSE;
+
+typedef union {
+ ICC_GET_CLK_CAPABILITIES_MESSAGE message;
+ ICC_GET_CLK_CAPABILITIES_RESPONSE response;
+} ICC_GET_CLK_CAPABILITIES_BUFFER;
+
+#define ICC_RESPONSE_MODE_WAIT 0
+#define ICC_RESPONSE_MODE_SKIP 1
+#define ICC_LOCK_ACCESS_MODE_SET 0
+#define ICC_LOCK_ACCESS_MODE_GET 1
+#define ICC_LOCK_MASK_COUNT 255
+#define WRITE_ICC_REG_BUNDLE_COUNT 1 ///< 1 bundle for 1 DWORD register write
+#define ADDRESS_MASK_FIXED_DATA 0x00017F01 ///< Target ID = 7F (Aux), MWM = 1(16 bits)
+#define WRITE_ICC_RECORD_FLAGS 0x00012010 ///< 16 byte record length, No param section, valid bit
+
+typedef struct _ICC_REG_BUNDLES
+{
+ UINT32 BundlesCnt :16; ///< Bundles Count - number of Address Mask entries
+ UINT32 AU :1; ///< AU=1 -> All regisaters are Unlocked
+ UINT32 Reserved :15;
+} ICC_REG_BUNDLES;
+
+typedef struct {
+ ICC_REG_BUNDLES RegBundles;
+ UINT32 RegMask[ICC_LOCK_MASK_COUNT];
+} ICC_LOCK_REGS_INFO;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT8 AccessMode;
+ UINT8 Parameters;
+ UINT8 Reserved[2];
+ ICC_LOCK_REGS_INFO LockRegInfo;
+} ICC_LOCK_REGISTERS_MESSAGE;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT32 Reserved;
+ ICC_LOCK_REGS_INFO LockRegInfo;
+} ICC_LOCK_REGISTERS_RESPONSE;
+
+typedef union {
+ ICC_LOCK_REGISTERS_MESSAGE message;
+ ICC_LOCK_REGISTERS_RESPONSE response;
+} ICC_LOCK_REGISTERS_BUFFER;
+
+typedef union _ICC_ADDRESS_MASK
+{
+ UINT32 AddressMaskData;
+ struct
+ {
+ UINT32 MaskWidthModifier :2;
+ UINT32 Offset :6;
+ UINT32 TargetId :7;
+ UINT32 Reserved :1;
+ }Fields;
+} ICC_ADDRESS_MASK;
+
+typedef struct _ICC_DWORD_RECORD
+{
+ UINT32 RecordFlags;
+ ICC_REG_BUNDLES BundleCount;
+ ICC_ADDRESS_MASK AddressMask;
+ UINT32 RegValue;
+} ICC_RECORD_DWORD;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT16 Reserved;
+ UINT8 Params;
+ UINT8 Reserved1;
+ ICC_RECORD_DWORD RecordDword;
+} ICC_WRITE_ICC_REG_DWORD_MESSAGE;
+
+typedef struct {
+ ICC_HEADER Header;
+ UINT16 BytesProcessed;
+ UINT16 Reserved;
+} ICC_WRITE_ICC_REG_DWORD_RESPONSE;
+
+typedef union {
+ ICC_WRITE_ICC_REG_DWORD_MESSAGE message;
+ ICC_WRITE_ICC_REG_DWORD_RESPONSE response;
+} ICC_WRITE_ICC_REG_BUFFER;
+
+//
+// SPI MEI Messages
+//
+#define HMRFPO_ENABLE_CMD_ID 0x01
+#define HMRFPO_LOCK_CMD_ID 0x02
+#define HMRFPO_GET_STATUS_CMD_ID 0x03
+
+typedef enum {
+ HMRFPO_ENABLE_SUCCESS = 0,
+ HMRFPO_ENABLE_LOCKED,
+ HMRFPO_NVAR_FAILURE,
+ HMRFOP_ATP_POLICY,
+ HMRFPO_ENABLE_UNKNOWN_FAILURE
+} HMRFPO_ENABLE_STATUS;
+
+typedef struct _MKHI_HMRFPO_ENABLE {
+ MKHI_MESSAGE_HEADER MkhiHeader;
+ UINT64 Nonce;
+} MKHI_HMRFPO_ENABLE;
+
+typedef struct _HMRFPO_ENABLE {
+ HECI_MESSAGE_HEADER Header;
+ MKHI_HMRFPO_ENABLE Msg;
+} HMRFPO_ENABLE;
+
+typedef struct _MKHI_HMRFPO_ENABLE_RESPONSE {
+ MKHI_MESSAGE_HEADER MkhiHeader;
+ UINT32 FactoryDefaultBase;
+ UINT32 FactoryDefaultLimit;
+ UINT8 Status;
+ UINT8 Rsvd[3];
+} MKHI_HMRFPO_ENABLE_RESPONSE;
+
+typedef struct _HMRFPO_ENABLE_RESPONSE {
+ HECI_MESSAGE_HEADER Header;
+ MKHI_HMRFPO_ENABLE_RESPONSE Msg;
+} HMRFPO_ENABLE_RESPONSE;
+
+typedef enum {
+ HMRFPO_LOCK_SUCCESS = 0,
+ HMRFPO_LOCK_FAILURE
+} HMRFPO_LOCK_STATUS;
+
+typedef struct _MKHI_HMRFPO_LOCK {
+ MKHI_MESSAGE_HEADER MkhiHeader;
+} MKHI_HMRFPO_LOCK;
+
+typedef struct _HMRFPO_LOCK {
+ HECI_MESSAGE_HEADER Header;
+ MKHI_HMRFPO_LOCK Msg;
+} HMRFPO_LOCK;
+
+typedef struct _MKHI_HMRFPO_LOCK_RESPONSE {
+ MKHI_MESSAGE_HEADER MkhiHeader;
+ UINT64 Nonce;
+ UINT32 FactoryDefaultBase;
+ UINT32 FactoryDefaultLimit;
+ UINT8 Status;
+ UINT8 Reserved[3];
+} MKHI_HMRFPO_LOCK_RESPONSE;
+
+typedef struct _HMRFPO_LOCK_RESPONSE {
+ HECI_MESSAGE_HEADER Header;
+ MKHI_HMRFPO_LOCK_RESPONSE Data;
+} HMRFPO_LOCK_RESPONSE;
+
+typedef struct _MKHI_HMRFPO_GET_STATUS {
+ MKHI_MESSAGE_HEADER MkhiHeader;
+} MKHI_HMRFPO_GET_STATUS;
+
+typedef struct _HMRFPO_GET_STATUS {
+ HECI_MESSAGE_HEADER Header;
+ MKHI_HMRFPO_GET_STATUS Msg;
+} HMRFPO_GET_STATUS;
+
+typedef struct _MKHI_HMRFPO_GET_STATUS_RESPONSE {
+ MKHI_MESSAGE_HEADER MkhiHeader;
+ UINT8 Status;
+ UINT8 Reserved[3];
+} MKHI_HMRFPO_GET_STATUS_RESPONSE;
+
+typedef struct _HMRFPO_GET_STATUS_RESPONSE {
+ HECI_MESSAGE_HEADER Header;
+ MKHI_HMRFPO_GET_STATUS_RESPONSE Data;
+} HMRFPO_GET_STATUS_RESPONSE;
+
+#define HMRFPO_LOCKED 1
+#define HMRFPO_ENABLED 2
+
+//
+// ME State Control
+//
+#define EFI_ME_STATE_STALL_1_SECOND 1000000
+#define EFI_ME_STATE_MAX_TIMEOUT 20
+//
+// KVM support
+//
+#define EFI_KVM_MESSAGE_COMMAND 0x08
+#define EFI_KVM_BYTE_COUNT 0x06
+#define EFI_KVM_QUERY_REQUES 0x01
+#define EFI_KVM_QUERY_RESPONSE 0x02
+#define EFI_KVM_VERSION 0x10
+
+#define EFI_KVM_STALL_1_SECOND 1000000 ///< Stall 1 second
+#define EFI_KVM_MAX_WAIT_TIME (60 * 8) ///< 8 Mins
+typedef enum {
+ QUERY_REQUEST = 0,
+ CANCEL_REQUEST
+} QUERY_TYPE;
+
+typedef struct _AMT_QUERY_KVM_REQUEST {
+ UINT8 Command;
+ UINT8 ByteCount;
+ UINT8 SubCommand;
+ UINT8 VersionNumber;
+ UINT32 QueryType;
+} AMT_QUERY_KVM_REQUEST;
+
+typedef enum {
+ KVM_SESSION_ESTABLISHED = 1,
+ KVM_SESSION_CANCELLED
+} RESPONSE_CODE;
+
+typedef struct _AMT_QUERY_KVM_RESPONSE {
+ UINT8 Command;
+ UINT8 ByteCount;
+ UINT8 SubCommand;
+ UINT8 VersionNumber;
+ UINT32 ResponseCode;
+} AMT_QUERY_KVM_RESPONSE;
+
+///
+/// ME Memory Debug support
+///
+typedef struct _SET_DEBUG_MEMORY_DATA {
+ UINT32 BiosDebugMemoryAddress;
+ UINT32 BiosDebugMemorySize;
+ UINT32 MeVeDebugMemoryAddress;
+ UINT32 MeVeDebugMemorySize;
+} SET_DEBUG_MEMORY_DATA;
+
+typedef struct _GEN_SET_DEBUG_MEMORY {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ SET_DEBUG_MEMORY_DATA Data;
+} GEN_SET_DEBUG_MEMORY;
+
+typedef struct _GEN_SET_DEBUG_MEMORY_ACK {
+ MKHI_MESSAGE_HEADER Header;
+} GEN_SET_DEBUG_MEMORY_ACK;
+
+//
+// BIOS MDES messaging
+//
+#define MDES_BIOS_MSG_LOG_REQ_CMD 0x0B
+#define MDES_BIOS_MSG_GET_CONFIG_CMD 0x0C
+
+typedef struct _MDES_ATTR {
+ UINT16 Severity : 2;
+ UINT16 PayLoadType : 6;
+ UINT16 Reserved : 8;
+} MDES_ATTR;
+
+typedef struct _BIOS_ATTR {
+ UINT16 CallerIdData : 1;
+ UINT16 ExtendedDataHeader : 1;
+ UINT16 Reserved : 14;
+} BIOS_ATTR;
+
+typedef struct {
+ UINT16 HeaderSize;
+ UINT16 Size;
+ EFI_GUID Type;
+} MDES_EXTENDED_DATA_HEADER;
+
+#define SIZE_OF_MDES_EXTENDED_DATA (2048 - \
+ ( \
+ 16 + sizeof (MDES_ATTR) + sizeof (BIOS_ATTR) + sizeof (EFI_GUID) + sizeof (MDES_EXTENDED_DATA_HEADER) + \
+ sizeof (MKHI_MESSAGE_HEADER) \
+ ) \
+ )
+
+typedef struct _CBM_BIOS_MDES_MSG_DATA {
+ MDES_ATTR MdesAttr;
+ BIOS_ATTR BiosAttr;
+ UINT32 Serial;
+ UINT32 StatusType;
+ UINT32 StatusCode;
+ UINT32 Instance;
+ EFI_GUID CallerId;
+ MDES_EXTENDED_DATA_HEADER ExtendedDataHeader;
+ UINT8 ExtendedData[SIZE_OF_MDES_EXTENDED_DATA];
+} CBM_BIOS_MDES_MSG_DATA;
+
+typedef struct _CBM_BIOS_MDES_MSG_REQ {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ CBM_BIOS_MDES_MSG_DATA Data;
+} CBM_BIOS_MDES_MSG_REQ;
+
+typedef struct _MKHI_CBM_BIOS_MDES_MSG_REQ {
+ HECI_MESSAGE_HEADER Header;
+ CBM_BIOS_MDES_MSG_REQ Msg;
+} MKHI_CBM_BIOS_MDES_MSG_REQ;
+
+typedef struct _MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_REQ {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+} MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_REQ;
+
+typedef union _MDES_BIOS_FLAGS {
+ volatile UINT32 ul;
+ struct {
+ UINT32 MdesEnabled : 1; ///< High level indication if MDES is enabled
+ UINT32 MdesLogPaused : 1; ///< A caller paused MDES logging as part of the log retrieval process
+ UINT32 LanInterfaceEnabled : 1; ///< The user configuration has enabled the LAN debug interface
+ UINT32 SmbusInterfaceEnabled : 1; ///< The user configuration has enabled the SMBus debug interface
+ UINT32 PramLogEnabled : 1; ///< The user configuration has enabled the PRAM debug log
+ UINT32 FlashLogEnabled : 1; ///< The user configuration has enabled the flash error log
+ UINT32 MdesBlockingModeEn : 1; ///< Set to 0 when operating in buffered mode, set to 1 when MDES blocks the caller until the event is dispatched.
+ UINT32 Reserved7 : 2;
+ UINT32 SensitiveMsgEnabled : 1; ///< Set to 1 to indicate Sensitive messages are enabled
+ UINT32 DescriptorUnlocked : 1; ///< Set when FW reads all regions are unlocked. Enables 'none' sensitivity messages.
+ UINT32 MdesPolicyEnabled : 1; ///< Set to 1 to indicate MDES is enabled due to BIOS sending the enable message (on current or previous boot)
+ UINT32 MdesEnableRcvdFromBios : 1; ///< BIOS has sent the MDES policy to 'enabled' via a MKHI message on this current boot
+ UINT32 Reserved13 : 19;
+ } fl;
+} MDES_BIOS_FLAGS;
+
+typedef struct _CBM_BIOS_MDES_MSG_GET_CONFIG_DATA {
+ MDES_BIOS_FLAGS Flags;
+ UINT32 BiosEventFilters;
+} CBM_BIOS_MDES_MSG_GET_CONFIG_DATA;
+
+typedef struct _MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_ACK {
+ MKHI_MESSAGE_HEADER Header;
+ CBM_BIOS_MDES_MSG_GET_CONFIG_DATA Data;
+} MKHI_CBM_BIOS_MDES_MSG_GET_CONFIG_ACK;
+
+#pragma pack()
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/include/MeAccess.h b/ReferenceCode/ME/Library/MeKernel/include/MeAccess.h
new file mode 100644
index 0000000..6a7c16d
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/include/MeAccess.h
@@ -0,0 +1,338 @@
+/** @file
+ Macros to simplify and abstract the interface to PCI configuration.
+
+@copyright
+ Copyright (c) 2010 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _ME_ACCESS_H_
+#define _ME_ACCESS_H_
+
+#include "MeChipset.h"
+#include "PchAccess.h"
+
+///
+/// HECI PCI Access Macro
+///
+#define HeciPciRead32(Register) PciRead32 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI_FUNCTION_NUMBER, Register))
+
+#define HeciPciWrite32(Register, Data) \
+ PciWrite32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) Data \
+ )
+
+#define HeciPciOr32(Register, Data) \
+ PciOr32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) Data \
+ )
+
+#define HeciPciAnd32(Register, Data) \
+ PciAnd32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) Data \
+ )
+
+#define HeciPciAndThenOr32(Register, AndData, OrData) \
+ PciAndThenOr32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) AndData, \
+ (UINT32) OrData \
+ )
+
+#define HeciPciRead16(Register) PciRead16 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI_FUNCTION_NUMBER, Register))
+
+#define HeciPciWrite16(Register, Data) \
+ PciWrite16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) Data \
+ )
+
+#define HeciPciOr16(Register, Data) \
+ PciOr16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) Data \
+ )
+
+#define HeciPciAnd16(Register, Data) \
+ PciAnd16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) Data \
+ )
+
+#define HeciPciAndThenOr16(Register, AndData, OrData) \
+ PciAndThenOr16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) AndData, \
+ (UINT16) OrData \
+ )
+
+#define HeciPciRead8(Register) PciRead8 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI_FUNCTION_NUMBER, Register))
+
+#define HeciPciWrite8(Register, Data) \
+ PciWrite8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) Data \
+ )
+
+#define HeciPciOr8(Register, Data) \
+ PciOr8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) Data \
+ )
+
+#define HeciPciAnd8(Register, Data) \
+ PciAnd8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) Data \
+ )
+
+#define HeciPciAndThenOr8(Register, AndData, OrData) \
+ PciAndThenOr8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) AndData, \
+ (UINT8) OrData \
+ )
+
+///
+/// HECI2 PCI Access Macro
+///
+#define Heci2PciRead32(Register) PciRead32 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI2_FUNCTION_NUMBER, Register))
+
+#define Heci2PciWrite32(Register, Data) \
+ PciWrite32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) Data \
+ )
+
+#define Heci2PciOr32(Register, Data) \
+ PciOr32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) Data \
+ )
+
+#define Heci2PciAnd32(Register, Data) \
+ PciAnd32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) Data \
+ )
+
+#define Heci2PciAndThenOr32(Register, AndData, OrData) \
+ PciAndThenOr32 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT32) AndData, \
+ (UINT32) OrData \
+ )
+
+#define Heci2PciRead16(Register) PciRead16 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI2_FUNCTION_NUMBER, Register))
+
+#define Heci2PciWrite16(Register, Data) \
+ PciWrite16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) Data \
+ )
+
+#define Heci2PciOr16(Register, Data) \
+ PciOr16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) Data \
+ )
+
+#define Heci2PciAnd16(Register, Data) \
+ PciAnd16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) Data \
+ )
+
+#define Heci2PciAndThenOr16(Register, AndData, OrData) \
+ PciAndThenOr16 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT16) AndData, \
+ (UINT16) OrData \
+ )
+
+#define Heci2PciRead8(Register) PciRead8 (PCI_LIB_ADDRESS (ME_BUS, ME_DEVICE_NUMBER, HECI2_FUNCTION_NUMBER, Register))
+
+#define Heci2PciWrite8(Register, Data) \
+ PciWrite8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) Data \
+ )
+
+#define Heci2PciOr8(Register, Data) \
+ PciOr8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) Data \
+ )
+
+#define Heci2PciAnd8(Register, Data) \
+ PciAnd8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) Data \
+ )
+
+#define Heci2PciAndThenOr8(Register, AndData, OrData) \
+ PciAndThenOr8 ( \
+ PCI_LIB_ADDRESS (ME_BUS, \
+ ME_DEVICE_NUMBER, \
+ HECI2_FUNCTION_NUMBER, \
+ Register), \
+ (UINT8) AndData, \
+ (UINT8) OrData \
+ )
+
+#ifndef MmPciAddress
+#define MmPciAddress(Segment, Bus, Device, Function, Register) \
+ ( \
+ (UINTN) (PciRead32 (PCI_LIB_ADDRESS (0,0,0,0x60)) & 0xFC000000) + \
+ (UINTN) (Bus << 20) + (UINTN) (Device << 15) + (UINTN) \
+ (Function << 12) + (UINTN) (Register) \
+ )
+#endif
+///
+/// ME Macro Setting
+///
+#define McD0PciCfg64(Register) MmPci64 (0, SA_MC_BUS, 0, 0, Register)
+#define McD0PciCfg32And(Register, AndData) PciAnd32 (PCI_LIB_ADDRESS (SA_MC_BUS, 0, 0, Register), (UINT32) AndData)
+#define McD0PciCfg16And(Register, AndData) PciAnd16 (PCI_LIB_ADDRESS (SA_MC_BUS, 0, 0, Register), (UINT16) AndData)
+
+///
+/// MMIO access macros
+///
+#define MmioAddress(BaseAddr, Register) ((UINTN) BaseAddr + (UINTN) (Register))
+
+///
+/// 16 bit MMIO access
+///
+#define Mmio16Ptr(BaseAddr, Register) ((volatile UINT16 *) MmioAddress (BaseAddr, Register))
+
+#define Mmio16(BaseAddr, Register) *Mmio16Ptr (BaseAddr, Register)
+
+#define Mmio16Or(BaseAddr, Register, OrData) \
+ Mmio16 (BaseAddr, Register) = (UINT16) \
+ (Mmio16 (BaseAddr, Register) | (UINT16) (OrData))
+
+#define Mmio16And(BaseAddr, Register, AndData) \
+ Mmio16 (BaseAddr, Register) = (UINT16) \
+ (Mmio16 (BaseAddr, Register) & (UINT16) (AndData))
+
+#define Mmio16AndThenOr(BaseAddr, Register, AndData, OrData) \
+ Mmio16 (BaseAddr, Register) = (UINT16) \
+ ((Mmio16 (BaseAddr, Register) & (UINT16) (AndData)) | (UINT16) (OrData))
+
+///
+/// 32 bit MMIO access
+///
+#define Mmio32Ptr(BaseAddr, Register) ((volatile UINT32 *) MmioAddress (BaseAddr, Register))
+
+#define Mmio32(BaseAddr, Register) *Mmio32Ptr (BaseAddr, Register)
+
+#define Mmio32Or(BaseAddr, Register, OrData) \
+ Mmio32 (BaseAddr, Register) = (UINT32) \
+ (Mmio32 (BaseAddr, Register) | (UINT32) (OrData))
+
+#define Mmio32And(BaseAddr, Register, AndData) \
+ Mmio32 (BaseAddr, Register) = (UINT32) \
+ (Mmio32 (BaseAddr, Register) & (UINT32) (AndData))
+
+#define Mmio32AndThenOr(BaseAddr, Register, AndData, OrData) \
+ Mmio32 (BaseAddr, Register) = (UINT32) \
+ ((Mmio32 (BaseAddr, Register) & (UINT32) (AndData)) | (UINT32) (OrData))
+
+///
+/// Memory Controller PCI access macros
+///
+#define MCH_REGION_BASE (McD0PciCfg64 (MC_MCHBAR_OFFSET) &~BIT0)
+#define McMmioAddress(Register) ((UINTN) MCH_REGION_BASE + (UINTN) (Register))
+
+#define McMmio8Ptr(Register) ((volatile UINT8 *) McMmioAddress (Register))
+#define McMmio8(Register) *McMmio8Ptr (Register)
+#define McMmio8Or(Register, OrData) (McMmio8 (Register) |= (UINT8) (OrData))
+#define McMmio8And(Register, AndData) (McMmio8 (Register) &= (UINT8) (AndData))
+#define McMmio8AndThenOr(Register, AndData, OrData) \
+ (McMmio8 (Register) = (McMmio8 (Register) & (UINT8) (AndData)) | (UINT8) (OrData))
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/include/MeChipset.h b/ReferenceCode/ME/Library/MeKernel/include/MeChipset.h
new file mode 100644
index 0000000..f18ac61
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/include/MeChipset.h
@@ -0,0 +1,196 @@
+/** @file
+ Chipset definition for ME Devices.
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values of bits within the registers
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+ - In general, ME registers are denoted by "_ME_" in register names
+ - Registers / bits that are different between ME generations are denoted by
+ "_ME_<generation_name>_" in register/bit names. e.g., "_ME_CPT_"
+ - Registers / bits that are different between SKUs are denoted by "_<SKU_name>"
+ at the end of the register/bit names
+ - Registers / bits of new devices introduced in a ME generation will be just named
+ as "_ME_" without <generation_name> inserted.
+
+@copyright
+ Copyright (c) 2011 - 2013 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _ME_CHIPSET_H_
+#define _ME_CHIPSET_H_
+
+#include "MeChipsetLib.h"
+
+#define ME_BUS 0
+#define ME_DEVICE_NUMBER 22
+
+#define HECI_FUNCTION_NUMBER 0x00
+#define HECI2_FUNCTION_NUMBER 0x01
+#define IDER_FUNCTION_NUMBER 0x02
+#define SOL_FUNCTION_NUMBER 0x03
+
+#define IDER_BUS_NUMBER ME_BUS
+#define IDER_DEVICE_NUMBER ME_DEVICE_NUMBER
+#define SOL_BUS_NUMBER ME_BUS
+#define SOL_DEVICE_NUMBER ME_DEVICE_NUMBER
+#define HECI_DEV_FCN ((ME_DEVICE_NUMBER) << 3 | (HECI_FUNCTION_NUMBER))
+#define HECI2_DEV_FCN ((ME_DEVICE_NUMBER) << 3 | (HECI2_FUNCTION_NUMBER))
+
+///
+/// Default Vendor ID and Device ID
+///
+#define V_INTEL_VENDOR_ID 0x8086
+
+#define V_ME_HECI_VENDOR_ID V_INTEL_VENDOR_ID
+#define V_ME_IDER_VENDOR_ID V_INTEL_VENDOR_ID
+#define V_ME_SOL_VENDOR_ID V_INTEL_VENDOR_ID
+
+#define V_ME_HECI_DEVICE_ID 0x8C3A
+#define V_ME_HECI2_DEVICE_ID 0x8C3B
+#define V_ME_IDER_DEVICE_ID 0x8C3C
+#define V_ME_SOL_DEVICE_ID 0x8C3D
+
+#define V_ME_LPTLP_HECI_DEVICE_ID 0x9C3A
+#define V_ME_LPTLP_HECI2_DEVICE_ID 0x9C3B
+#define V_ME_LPTLP_IDER_DEVICE_ID 0x9C3C
+#define V_ME_LPTLP_SOL_DEVICE_ID 0x9C3D
+
+#define R_ME_HFS 0x40
+#define R_ME_MISC_SHDW 0x44
+#define R_ME_GS_SHDW 0x48
+#define R_ME_HFS_4 0x64
+#define R_ME_HFS_5 0x68
+#define R_ME_HFS_6 0x6C
+#define B_BOOT_GUARD_ENF_MASK 0x0200
+#define B_TPM_DISCONNECT 0x1000
+#define B_TPM1_2_DEACTIVATED 0x0100
+
+#define R_ME_H_GS 0x4C
+#define B_ME_DID_RAPID_START_BIT BIT23
+#define B_ME_DID_TYPE_MASK BIT28
+#define R_ME_H_GS2 0x70
+#define B_ME_MBP_GIVE_UP BIT0
+#define R_ME_HERS 0xBC
+#define B_ME_EXTEND_REG_VALID BIT31
+#define B_ME_EXTEND_REG_ALGORITHM (BIT0 | BIT1 | BIT2 | BIT3)
+#define V_ME_SHA_1 0x00
+#define V_ME_SHA_256 0x02
+#define R_ME_HER1 0xC0
+#define R_ME_HER2 0xC4
+#define R_ME_HER3 0xC8
+#define R_ME_HER4 0xCC
+#define R_ME_HER5 0xD0
+#define R_ME_HER6 0xD4
+#define R_ME_HER7 0xD8
+#define R_ME_HER8 0xDC
+
+///
+/// ME-related Chipset Definition
+///
+#define HeciEnable() MeDeviceControl (HECI1, Enabled);
+#define Heci2Enable() MeDeviceControl (HECI2, Enabled);
+#define IderEnable() MeDeviceControl (IDER, Enabled);
+#define SolEnable() MeDeviceControl (SOL, Enabled);
+#define Usbr1Enable() MeDeviceControl (USBR1, Enabled);
+#define Usbr2Enable() MeDeviceControl (USBR2, Enabled);
+
+#define HeciDisable() MeDeviceControl (HECI1, Disabled);
+#define Heci2Disable() MeDeviceControl (HECI2, Disabled);
+#define IderDisable() MeDeviceControl (IDER, Disabled);
+#define SolDisable() MeDeviceControl (SOL, Disabled);
+#define Usbr1Disable() MeDeviceControl (USBR1, Disabled);
+#define Usbr2Disable() MeDeviceControl (USBR2, Disabled);
+#define DisableAllMEDevices() \
+ HeciDisable (); \
+ Heci2Disable (); \
+ IderDisable (); \
+ SolDisable ();
+
+#define IS_PCH_LPTH_HECI_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_HECI_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPTLP_HECI_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_LPTLP_HECI_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPT_HECI_DEVICE_ID(DeviceId) \
+ ( \
+ IS_PCH_LPTH_HECI_DEVICE_ID(DeviceId) || \
+ IS_PCH_LPTLP_HECI_DEVICE_ID(DeviceId) \
+ )
+
+#define IS_PCH_LPTH_HECI2_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_HECI2_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPTLP_HECI2_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_LPTLP_HECI2_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPT_HECI2_DEVICE_ID(DeviceId) \
+ ( \
+ IS_PCH_LPTH_HECI2_DEVICE_ID(DeviceId) || \
+ IS_PCH_LPTLP_HECI2_DEVICE_ID(DeviceId) \
+ )
+
+#define IS_PCH_LPTH_IDER_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_IDER_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPTLP_IDER_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_LPTLP_IDER_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPT_IDER_DEVICE_ID(DeviceId) \
+ ( \
+ IS_PCH_LPTH_IDER_DEVICE_ID(DeviceId) || \
+ IS_PCH_LPTLP_IDER_DEVICE_ID(DeviceId) \
+ )
+
+#define IS_PCH_LPTH_SOL_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_SOL_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPTLP_SOL_DEVICE_ID(DeviceId) \
+ ( \
+ (DeviceId == V_ME_LPTLP_SOL_DEVICE_ID) \
+ )
+
+#define IS_PCH_LPT_SOL_DEVICE_ID(DeviceId) \
+ ( \
+ IS_PCH_LPTH_SOL_DEVICE_ID(DeviceId) || \
+ IS_PCH_LPTLP_SOL_DEVICE_ID(DeviceId) \
+ )
+
+///
+/// Function Disable SUS well lockdown
+///
+#define FunctionDisableWellLockdown() MeDeviceControl (FDSWL, Enabled);
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/include/MeChipsetLib.h b/ReferenceCode/ME/Library/MeKernel/include/MeChipsetLib.h
new file mode 100644
index 0000000..dfa9417
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/include/MeChipsetLib.h
@@ -0,0 +1,54 @@
+/** @file
+ Header file for Me Chipset Lib
+
+@copyright
+ Copyright (c) 2010 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _ME_CHIPSET_LIB_H_
+#define _ME_CHIPSET_LIB_H_
+
+typedef enum {
+ HECI1 = 1,
+ HECI2,
+ IDER,
+ SOL,
+ USBR1,
+ USBR2,
+ FDSWL,
+} ME_DEVICE;
+
+typedef enum {
+ Disabled= 0,
+ Enabled,
+} ME_DEVICE_FUNC_CTRL;
+
+/**
+ Enable/Disable Me devices
+
+ @param[in] WhichDevice Select of Me device
+ @param[in] DeviceFuncCtrl Function control
+
+ @retval None
+**/
+VOID
+MeDeviceControl (
+ IN ME_DEVICE WhichDevice,
+ IN ME_DEVICE_FUNC_CTRL DeviceFuncCtrl
+ )
+;
+
+#endif
diff --git a/ReferenceCode/ME/Library/MeKernel/include/MeState.h b/ReferenceCode/ME/Library/MeKernel/include/MeState.h
new file mode 100644
index 0000000..55bb7bd
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/include/MeState.h
@@ -0,0 +1,67 @@
+/** @file
+ Register Definitions for Me States
+
+@copyright
+ Copyright (c) 2009 - 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _ME_STATE_H
+#define _ME_STATE_H
+///
+/// Ignore ME_FW_INIT_COMPLETE status Macro
+///
+#define ME_STATUS_ME_STATE_ONLY(a) ((a) & (~(ME_FW_INIT_COMPLETE | ME_FW_BOOT_OPTIONS_PRESENT)))
+
+///
+/// Macro to check if ME FW INIT is completed
+///
+#define ME_STATUS_IS_ME_FW_INIT_COMPLETE(a) (((a) & ME_FW_INIT_COMPLETE) == ME_FW_INIT_COMPLETE)
+
+///
+/// Marco to combind the complete bit to status
+///
+#define ME_STATUS_WITH_ME_INIT_COMPLETE(a) ((a) | ME_FW_INIT_COMPLETE)
+
+///
+/// Macro to check ME Boot Option Present
+///
+#define ME_STATUS_IS_ME_FW_BOOT_OPTIONS_PRESENT(a) (((a) & ME_FW_BOOT_OPTIONS_PRESENT) == ME_FW_BOOT_OPTIONS_PRESENT)
+
+//
+// Abstract ME Mode Definitions
+//
+#define ME_MODE_NORMAL 0x00
+#define ME_MODE_DEBUG 0x02
+#define ME_MODE_TEMP_DISABLED 0x03
+#define ME_MODE_SECOVER 0x04
+#define ME_MODE_FAILED 0x06
+
+//
+// Abstract ME Status definitions
+//
+#define ME_READY 0x00
+#define ME_INITIALIZING 0x01
+#define ME_IN_RECOVERY_MODE 0x02
+#define ME_DISABLE_WAIT 0x06
+#define ME_TRANSITION 0x07
+#define ME_NOT_READY 0x0F
+#define ME_FW_INIT_COMPLETE 0x80
+#define ME_FW_BOOT_OPTIONS_PRESENT 0x100
+#define ME_FW_UPDATES_IN_PROGRESS 0x200
+
+#pragma pack()
+
+#endif // ME_STATE_H
diff --git a/ReferenceCode/ME/Library/MeKernel/include/MkhiMsgs.h b/ReferenceCode/ME/Library/MeKernel/include/MkhiMsgs.h
new file mode 100644
index 0000000..9005d62
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeKernel/include/MkhiMsgs.h
@@ -0,0 +1,533 @@
+/** @file
+ MKHI Messages
+
+@copyright
+ Copyright (c) 2010 - 2013 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _MKHI_MSGS_H
+#define _MKHI_MSGS_H
+
+#pragma pack(1)
+
+#define BIOS_FIXED_HOST_ADDR 0
+#define PREBOOT_FIXED_ME_ADDR 7
+#define BIOS_ASF_HOST_ADDR 1
+
+#define HECI_CORE_MESSAGE_ADDR 0x07
+#define HECI_ASF_MESSAGE_ADDR 0x02
+#define HECI_FSC_MESSAGE_ADDR 0x03
+#define HECI_POLICY_MANAGER_ADDR 0x05
+#define HECI_AT_MESSAGE_ADDR 0x05 ///< Added to support AT
+#define HECI_ME_PASSWORD_SERVICE_ADDR 0x06
+#define HECI_ICC_MESSAGE_ADDR 0x08
+#define HECI_TR_MESSAGE_ADDR 0x09
+#define HECI_SPI_MESSAGE_ADDR 0x0A
+
+#define NON_BLOCKING 0
+#define BLOCKING 1
+
+//
+// command handle by HCI
+//
+#define GEN_GET_MKHI_VERSION_CMD 0x01
+#define GEN_GET_MKHI_VERSION_CMD_ACK 0x81
+#define GEN_GET_FW_VERSION_CMD 0x02
+#define GEN_GET_FW_VERSION_CMD_ACK 0x82
+#define GEN_UNCFG_WO_PWD_CMD 0x0D
+#define GEN_UNCFG_WO_PWD_CMD_ACK 0x8D
+
+#define FWCAPS_GET_RULE_CMD 0x02
+#define FWCAPS_SET_RULE_CMD 0x03
+
+#define AT_ME_RULE_ID 0xd0000
+
+//
+// Enums for Result field of MHKI Header
+//
+#define ME_SUCCESS 0x00
+#define ME_ERROR_ALIAS_CHECK_FAILED 0x01
+#define ME_INVALID_MESSAGE 0x02
+#define ME_M1_DATA_OLDER_VER 0x03
+#define ME_M1_DATA_INVALID_VER 0x04
+#define ME_INVALID_M1_DATA 0x05
+
+//
+// MDES
+//
+#define MDES_ENABLE_MKHI_CMD 0x09
+#define MDES_ENABLE_MKHI_CMD_ACK 0x89
+
+///
+/// IFR Update
+///
+#define MEFWCAPS_ME_FWU_IFR_RULE 0x2E
+
+//
+// Manageability State Control
+//
+#define FIRMWARE_CAPABILITY_OVERRIDE_CMD 0x14
+#define FIRMWARE_CAPABILITY_OVERRIDE_CMD_ACK 0x94
+
+///
+/// Typedef for GroupID
+///
+typedef enum {
+ MKHI_CBM_GROUP_ID = 0,
+ MKHI_PM_GROUP_ID,
+ MKHI_PWD_GROUP_ID,
+ MKHI_FWCAPS_GROUP_ID,
+ MKHI_APP_GROUP_ID,
+ MKHI_SPI_GROUP_ID,
+ MKHI_MDES_GROUP_ID = 8,
+ MKHI_MAX_GROUP_ID,
+ MKHI_GEN_GROUP_ID = 0xFF
+} MKHI_GROUP_ID;
+
+///
+/// Typedef for AT State
+///
+typedef enum _AT_STATE
+{
+ AT_STATE_INACTIVE = 0,
+ AT_STATE_ACTIVE,
+ AT_STATE_STOLEN,
+ AT_STATE_SUSPEND,
+ AT_STATE_MAX
+} AT_STATE;
+
+///
+/// MKHI host message header. This header is part of HECI message sent from MEBx via
+/// Host Configuration Interface (HCI). ME Configuration Manager or Power Configuration
+/// Manager also include this header with appropriate fields set as part of the
+/// response message to the HCI.
+///
+typedef union _MKHI_MESSAGE_HEADER {
+ UINT32 Data;
+ struct {
+ UINT32 GroupId : 8;
+ UINT32 Command : 7;
+ UINT32 IsResponse : 1;
+ UINT32 Reserved : 8;
+ UINT32 Result : 8;
+ } Fields;
+} MKHI_MESSAGE_HEADER;
+
+///
+/// End of Post ACK message
+///
+typedef struct _CBM_EOP_ACK_DATA {
+ UINT32 RequestedActions;
+} CBM_EOP_ACK_DATA;
+
+typedef struct _GEN_END_OF_POST_ACK {
+ MKHI_MESSAGE_HEADER Header;
+ CBM_EOP_ACK_DATA Data;
+} GEN_END_OF_POST_ACK;
+
+typedef union _MKHI_VERSION {
+ UINT32 Data;
+ struct {
+ UINT32 Minor : 16;
+ UINT32 Major : 16;
+ } Fields;
+} MKHI_VERSION;
+
+///
+/// MKHI version messages
+///
+typedef struct _GEN_GET_MKHI_VERSION {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+} GEN_GET_MKHI_VERSION;
+
+typedef struct _GET_MKHI_VERSION_ACK_DATA {
+ MKHI_VERSION MKHIVersion;
+} GET_MKHI_VERSION_ACK_DATA;
+
+typedef struct _GEN_GET_MKHI_VERSION_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_MKHI_VERSION_ACK_DATA Data;
+} GEN_GET_MKHI_VERSION_ACK;
+
+///
+/// FW version messages
+///
+typedef struct _GEN_GET_FW_VER {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+} GEN_GET_FW_VER;
+
+typedef struct _GEN_GET_FW_VER_ACK_DATA {
+ UINT32 CodeMinor : 16;
+ UINT32 CodeMajor : 16;
+ UINT32 CodeBuildNo : 16;
+ UINT32 CodeHotFix : 16;
+ UINT32 RcvyMinor : 16;
+ UINT32 RcvyMajor : 16;
+ UINT32 RcvyBuildNo : 16;
+ UINT32 RcvyHotFix : 16;
+ UINT32 FitcMinor : 16;
+ UINT32 FitcMajor : 16;
+ UINT32 FitcBuildNo : 16;
+ UINT32 FitcHotFix : 16;
+} GEN_GET_FW_VER_ACK_DATA;
+
+typedef struct _GEN_GET_FW_VER_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GEN_GET_FW_VER_ACK_DATA Data;
+} GEN_GET_FW_VER_ACK;
+
+///
+/// Unconfig without password messages
+///
+typedef struct _GEN_UNCFG_WO_PWD {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+} GEN_UNCFG_WO_PWD;
+
+typedef struct _GEN_UNCFG_WO_PWD_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+} GEN_UNCFG_WO_PWD_ACK;
+
+///
+/// Get Firmware Capability MKHI
+///
+typedef struct _GET_RULE_DATA {
+ UINT32 RuleId;
+} GET_RULE_DATA;
+
+typedef struct _GEN_GET_FW_CAPSKU {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_GET_FW_CAPSKU;
+
+typedef union _RULE_ID {
+ UINT32 Data;
+ struct {
+ UINT32 RuleTypeId : 16;
+ UINT32 FeatureId : 8;
+ UINT32 Reserved : 8;
+ } Fields;
+} RULE_ID;
+
+typedef struct _SET_RULE_DATA {
+ RULE_ID RuleId;
+ UINT8 RuleDataLen;
+ UINT8 RuleData;
+} SET_RULE_DATA;
+
+typedef struct _SET_RULE_ACK_DATA {
+ UINT32 RuleId;
+} SET_RULE_ACK_DATA;
+
+typedef struct _GEN_SET_FW_CAPSKU {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ SET_RULE_DATA Data;
+} GEN_SET_FW_CAPSKU;
+
+typedef struct _GEN_SET_FW_CAPSKU_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ SET_RULE_ACK_DATA Data;
+} GEN_SET_FW_CAPSKU_ACK;
+typedef union _MEFWCAPS_SKU {
+ UINT32 Data;
+ struct {
+ UINT32 FullNet : 1; ///< [0] Full network manageability
+ UINT32 StdNet : 1; ///< [1] Standard network manageability
+ UINT32 Manageability : 1; ///< [2] Manageability
+ UINT32 SmallBusiness : 1; ///< [3] Small business technology
+ UINT32 Reserved2 : 1; ///< [4] Reserved
+ UINT32 IntelAT : 1; ///< [5] IntelR Anti-Theft (AT)
+ UINT32 IntelCLS : 1; ///< [6] IntelR Capability Licensing Service (CLS)
+ UINT32 Reserved : 3; ///< [9:7] Reserved
+ UINT32 IntelMPC : 1; ///< [10] IntelR Power Sharing Technology (MPC)
+ UINT32 IccOverClocking : 1; ///< [11] ICC Over Clocking
+ UINT32 PAVP : 1; ///< [12] Protected Audio Video Path (PAVP)
+ UINT32 Reserved1 : 4; ///< [16:13] Reserved
+ UINT32 IPV6 : 1; ///< [17] IPV6
+ UINT32 KVM : 1; ///< [18] KVM Remote Control (KVM)
+ UINT32 OCH : 1; ///< [19] Outbreak Containment Heuristic (OCH)
+ UINT32 VLAN : 1; ///< [20] Virtual LAN (VLAN)
+ UINT32 TLS : 1; ///< [21] TLS
+ UINT32 Reserved4 : 1; ///< [22] Reserved
+ UINT32 WLAN : 1; ///< [23] Wireless LAN (WLAN)
+ UINT32 Reserved5 : 5; ///< [28:24] Reserved
+ UINT32 PTT : 1; ///< [29] Platform Trust Technoogy (PTT)
+ UINT32 Reserved6 : 1; ///< [30] Reserved
+ UINT32 NFC : 1; ///< [31] NFC
+ } Fields;
+} MEFWCAPS_SKU;
+
+typedef struct _AT_STATE_FLAG {
+ UINT16 LockState : 1; ///< Indicate whether the platform is locked */
+ UINT16 AuthenticateModule : 1; ///< Preferred Authentication Module */
+ UINT16 S3Authentication : 1; ///< indicates whether S3 authentication is enabled */
+ UINT16 FlashWearOut : 1; ///< indicates whether the AT flash partition is currently in violation of flash wear out rules */
+ UINT16 FlashVariableSecurity : 1; ///< indicates whether the AT flash variables have been tampered with */
+ UINT16 Reserved : 11;
+} AT_STATE_FLAG;
+
+typedef struct _AT_STATE_INFO {
+ UINT8 State;
+ UINT8 LastTheftTrigger;
+ AT_STATE_FLAG flags;
+} AT_STATE_INFO;
+
+typedef struct {
+ UINT8 AtState; ///< State of AT
+ UINT8 AtLastTheftTrigger; ///< Reason for the last trigger
+ AT_STATE_FLAG AtStateFlags; ///< State of AT Fw
+} AT_STATE_STRUCT;
+
+typedef struct _GEN_GET_FW_CAPS_SKU_ACK_DATA {
+ UINT32 RuleID;
+ UINT8 RuleDataLen;
+ MEFWCAPS_SKU FWCapSku;
+} GEN_GET_FW_CAPS_SKU_ACK_DATA;
+
+typedef struct _GEN_GET_FW_CAPSKU_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GEN_GET_FW_CAPS_SKU_ACK_DATA Data;
+} GEN_GET_FW_CAPS_SKU_ACK;
+
+typedef union _GEN_GET_FW_CAPS_SKU_BUFFER {
+ GEN_GET_FW_CAPSKU Request;
+ GEN_GET_FW_CAPS_SKU_ACK Response;
+} GEN_GET_FW_CAPS_SKU_BUFFER;
+
+typedef enum {
+ UPDATE_DISABLED = 0,
+ UPDATE_ENABLED
+} LOCAL_FW_UPDATE;
+
+typedef enum {
+ LOCAL_FW_ALWAYS = 0,
+ LOCAL_FW_NEVER,
+ LOCAL_FW_RESTRICTED,
+} LOCAL_FW_QUALIFIER;
+
+typedef struct _GEN_LOCAL_FW_UPDATE_DATA {
+ UINT32 RuleId;
+ UINT8 RuleDataLen;
+ UINT8 RuleData;
+ UINT8 Reserved[30];
+} GEN_LOCAL_FW_UPDATE_DATA;
+
+typedef struct _GEN_GET_LOCAL_FW_UPDATE {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_GET_LOCAL_FW_UPDATE;
+
+typedef struct _GEN_GET_LOCAL_FW_UPDATE_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GEN_LOCAL_FW_UPDATE_DATA Data;
+} GEN_GET_LOCAL_FW_UPDATE_ACK;
+
+typedef struct _GEN_SET_LOCAL_FW_UPDATE {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GEN_LOCAL_FW_UPDATE_DATA Data;
+} GEN_SET_LOCAL_FW_UPDATE;
+
+typedef struct _GEN_SET_LOCAL_FW_UPDATE_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_SET_LOCAL_FW_UPDATE_ACK;
+
+typedef enum {
+ NO_BRAND = 0,
+ INTEL_AMT_BRAND,
+ INTEL_STAND_MANAGEABILITY_BRAND,
+ INTEL_LEVEL_III_MANAGEABILITY_UPGRADE_BRAND,
+ INTEL_RESERVED_BRAND,
+ INTEL_SMALL_BUSINESS_TECHNOLOGY_BRAND,
+} PLATFORM_BRAND;
+
+typedef enum {
+ INTEL_ME_1_5MB_FW = 3,
+ INTEL_ME_5MB_FW,
+} ME_IMAGE_TYPE;
+
+#define REGULAR_SKU 0
+#define SUPER_SKU 1
+
+#define PLATFORM_MARKET_CORPORATE 1
+#define PLATFORM_MARKET_CONSUMER 2
+
+#define PLATFORM_MOBILE 1
+#define PLATFORM_DESKTOP 2
+#define PLATFORM_SERVER 4
+#define PLATFORM_WORKSTATION 8
+
+typedef union _PLATFORM_TYPE_RULE_DATA {
+ UINT32 Data;
+ struct {
+ UINT32 PlatformTargetUsageType : 4;
+ UINT32 PlatformTargetMarketType : 2;
+ UINT32 SuperSku : 1;
+ UINT32 Reserved : 1;
+ UINT32 IntelMeFwImageType : 4;
+ UINT32 PlatformBrand : 4;
+ UINT32 Reserved1 : 16;
+ } Fields;
+} PLATFORM_TYPE_RULE_DATA;
+
+typedef struct _GEN_PLATFORM_TYPE_DATA {
+ UINT32 RuleId;
+ UINT8 RuleDataLen;
+ PLATFORM_TYPE_RULE_DATA RuleData;
+ UINT8 Reserved[27];
+} GEN_PLATFORM_TYPE_DATA;
+
+typedef struct _GEN_GET_PLATFORM_TYPE {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_GET_PLATFORM_TYPE;
+
+typedef struct _GEN_GET_PLATFORM_TYPE_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GEN_PLATFORM_TYPE_DATA Data;
+} GEN_GET_PLATFORM_TYPE_ACK;
+
+typedef union _GEN_GET_PLATFORM_TYPE_BUFFER {
+ GEN_GET_PLATFORM_TYPE Request;
+ GEN_GET_PLATFORM_TYPE_ACK Response;
+} GEN_GET_PLATFORM_TYPE_BUFFER;
+
+typedef struct _GET_AT_ME_RULE_CMD {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ UINT32 RuleId;
+
+} GET_AT_ME_RULE_CMD;
+
+typedef struct _GET_AT_ME_RULE_RSP {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ UINT32 RuleId;
+ UINT8 RuleDataLength;
+ AT_STATE_INFO AtRuleData;
+
+} GET_AT_ME_RULE_RSP;
+
+typedef struct _GET_FW_FEATURE_STATUS {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_GET_FW_FEATURE_STATUS;
+
+typedef struct _GET_FW_FEATURE_STATUS_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ UINT32 RuleId;
+ UINT8 RuleDataLength;
+ MEFWCAPS_SKU RuleData;
+} GEN_GET_FW_FEATURE_STATUS_ACK;
+
+typedef struct _GEN_AMT_BIOS_SYNCH_INFO {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_AMT_BIOS_SYNCH_INFO;
+
+typedef struct _GEN_AMT_BIOS_SYNCH_INFO_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ UINT32 RuleId;
+ UINT8 RuleDataLength;
+ UINT32 RuleData;
+} GEN_AMT_BIOS_SYNCH_INFO_ACK;
+
+typedef struct _GEN_GET_OEM_TAG_MSG {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ GET_RULE_DATA Data;
+} GEN_GET_OEM_TAG_MSG;
+
+typedef struct _GEN_GET_OEM_TAG_MSG_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ UINT32 RuleId;
+ UINT8 RuleDataLength;
+ UINT32 RuleData;
+} GEN_GET_OEM_TAG_MSG_ACK;
+
+typedef union _PLATFORM_DEBUG_CAP {
+ UINT8 Data;
+ struct {
+ UINT8 Mdes : 1;
+ UINT8 SvtForPch : 1;
+ UINT8 Reserved : 6;
+ } Fields;
+} PLATFORM_DEBUG_CAP;
+
+typedef struct _GEN_PLATFORM_DEBUG_CAP_MKHI_CMD_MSG {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ PLATFORM_DEBUG_CAP Capability;
+} GEN_PLATFORM_DEBUG_CAP_MKHI_CMD_MSG;
+
+///
+/// Manageability State Control MKHI definitions
+///
+typedef struct _FIRMWARE_CAPABILITY_OVERRIDE_DATA {
+ UINT32 EnableFeature;
+ UINT32 DisableFeature;
+} FIRMWARE_CAPABILITY_OVERRIDE_DATA;
+
+typedef struct _FIRMWARE_CAPABILITY_OVERRIDE {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ FIRMWARE_CAPABILITY_OVERRIDE_DATA FeatureState;
+} FIRMWARE_CAPABILITY_OVERRIDE;
+
+typedef enum _FIRMWARE_CAPABILITY_RESPONSE
+{
+ SET_FEATURE_STATE_ACCEPTED = 0,
+ SET_FEATURE_STATE_REJECTED
+} FIRMWARE_CAPABILITY_RESPONSE;
+
+typedef struct _FIRMWARE_CAPABILITY_OVERRIDE_ACK_DATA {
+ FIRMWARE_CAPABILITY_RESPONSE Response;
+} FIRMWARE_CAPABILITY_OVERRIDE_ACK_DATA;
+
+typedef struct _FIRMWARE_CAPABILITY_OVERRIDE_ACK {
+ MKHI_MESSAGE_HEADER Header;
+ FIRMWARE_CAPABILITY_OVERRIDE_ACK_DATA Data;
+} FIRMWARE_CAPABILITY_OVERRIDE_ACK;
+
+///
+/// Set ACM TPM Data MKHI
+///
+#define ACM_TPM_DATA_MKHI_DATA 0x00000303
+#define ACM_TPM_DATA_RULE_TYPE_ID 0x2F
+#define ACM_TPM_DATA_RULE_DATA_LENGTH 0x04
+
+typedef union _TPM_STATE {
+ UINT16 Data;
+ struct {
+ UINT16 Reserved_0: 8;
+ UINT16 TpmDeactivate: 1;
+ UINT16 Reserved_1: 7;
+ } Fields;
+} TPM_STATE;
+
+typedef struct _ACM_TPM_DATA {
+ RULE_ID RuleId;
+ UINT8 RuleDataLen;
+ TPM_STATE TpmState;
+ UINT8 Reserved[2];
+} ACM_TPM_DATA;
+
+typedef struct _BIOSNV_SET_ACM_TPM_DATA {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ ACM_TPM_DATA AcmTpmData;
+} BIOSNV_SET_ACM_TPM;
+
+typedef struct _BIOSNV_SET_ACM_TPM_DATA_ACK {
+ MKHI_MESSAGE_HEADER MKHIHeader;
+ RULE_ID RuleId;
+} BIOSNV_SET_ACM_TPM_ACK;
+
+#pragma pack()
+
+#endif // _MKHI_MSGS_H
diff --git a/ReferenceCode/ME/Library/MeLibrary.cif b/ReferenceCode/ME/Library/MeLibrary.cif
new file mode 100644
index 0000000..76bce81
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeLibrary.cif
@@ -0,0 +1,22 @@
+<component>
+ name = "MeLibrary"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\"
+ RefName = "MeLibrary"
+[files]
+"MeLibrary.sdl"
+"MeKernel\include\CoreBiosMsg.h"
+"MeKernel\include\MkhiMsgs.h"
+"MeKernel\include\MeAccess.h"
+"MeKernel\include\MeChipset.h"
+"MeKernel\include\MeChipsetLib.h"
+"MeKernel\include\MeState.h"
+"AMT\Include\Amt.h"
+"PttHeci\Include\PttHeciLib.h"
+[parts]
+"MeKernelLibrary"
+"AmtLibrary"
+"AtLibrary"
+"PttLibrary"
+"PttHeciDxeLib"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/MeLibrary.sdl b/ReferenceCode/ME/Library/MeLibrary.sdl
new file mode 100644
index 0000000..6617dce
--- /dev/null
+++ b/ReferenceCode/ME/Library/MeLibrary.sdl
@@ -0,0 +1,32 @@
+TOKEN
+ Name = "MeLibrary_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable MeLibrary support in Project"
+End
+
+PATH
+ Name = "MeLibrary_DIR"
+ Help = "Me Library file source directory"
+End
+
+ELINK
+ Name = "/I$(MeLibrary_DIR)\Include"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MeLibrary_DIR)\PttHeci\Include"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(INTEL_PCH_INCLUDES)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.c b/ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.c
new file mode 100644
index 0000000..38b33b5
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.c
@@ -0,0 +1,606 @@
+/** @file
+ Implements Platform Trust Technology (FTPM) HCI Device Library.
+
+@copyright
+ Copyright (c) 2012 - 2013 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+
+**/
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#endif
+
+#ifdef PTT_FLAG
+#include "PttHciRegs.h"
+#include "PttHciDeviceLib.h"
+#include <IndustryStandard/Tpm20.h>
+
+
+#ifdef EFI_DEBUG
+/**
+ Prints command or response buffer for debugging purposes.
+
+ @param[in] Buffer Buffer to print.
+ @param[in] BufferSize Buffer data length.
+**/
+VOID
+EFIAPI
+PttHciPrintBuffer(IN UINT8 *Buffer, IN UINT32 BufferSize)
+{
+ UINT32 Index;
+
+ DEBUG ((EFI_D_INFO, "Buffer Address: 0x%08x, Size: 0x%08x, Value:\n", Buffer, BufferSize));
+ for(Index = 0; Index < BufferSize; Index++){
+ DEBUG ((EFI_D_INFO, "%02x ", *(Buffer + Index)));
+ if((Index+1) % 16 == 0) DEBUG ((EFI_D_INFO, "\n"));
+ }
+ DEBUG ((EFI_D_INFO, "\n"));
+}
+#endif // EFI_DEBUG
+
+
+VOID MicroSecDelay (
+ UINTN Delay
+)
+{
+ UINTN Counter, i;
+ UINT32 Data32, PrevData;
+ UINT32 Remainder;
+
+ Counter = (UINTN)DivU64x32Remainder ((UINT64)(Delay * 10), 3, &Remainder);
+ if (Remainder != 0) {
+ Counter++;
+ }
+ //
+ // Call WaitForTick for Counter + 1 ticks to try to guarantee Counter tick
+ // periods, thus attempting to ensure Microseconds of stall time.
+ //
+ if (Counter != 0) {
+
+ PrevData = IoRead32(PM_BASE_ADDRESS + 8);
+ for (i = 0; i < Counter; ) {
+ Data32 = IoRead32(PM_BASE_ADDRESS + 8);
+ if (Data32 < PrevData) { // Reset if there is a overlap
+ PrevData=Data32;
+ continue;
+ }
+ i += (Data32 - PrevData);
+ PrevData = Data32;
+ }
+ }
+ return;
+}
+
+
+/**
+ Copy data from the MMIO region to system memory by using 32-bit access.
+
+ Copy data from the MMIO region specified by starting address StartAddress
+ to system memory specified by Buffer by using 32-bit access. The total
+ number of byte to be copied is specified by Length. Buffer is returned.
+
+ If StartAddress is not aligned on a 32-bit boundary, then ASSERT().
+
+ If Length is greater than (MAX_ADDRESS - StartAddress + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+
+ @param StartAddress The starting address for the MMIO region to be copied from.
+ @param Length The size, in bytes, of Buffer.
+ @param Buffer The pointer to a system memory buffer receiving the data read.
+
+ @return Buffer
+**/
+UINT32 *
+EFIAPI
+MmioReadBuffer32 (
+ IN UINTN StartAddress,
+ IN UINTN Length,
+ OUT UINT32 *Buffer
+ )
+{
+ UINT32 *ReturnBuffer;
+
+ ASSERT ((StartAddress & (sizeof (UINT32) - 1)) == 0);
+
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - StartAddress));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN) Buffer));
+
+ ASSERT ((Length & (sizeof (UINT32) - 1)) == 0);
+ ASSERT (((UINTN) Buffer & (sizeof (UINT32) - 1)) == 0);
+
+ ReturnBuffer = Buffer;
+
+ while (Length != 0) {
+ *(Buffer++) = MmioRead32 (StartAddress);
+ StartAddress += sizeof (UINT32);
+ Length -= sizeof (UINT32);
+ }
+
+ return ReturnBuffer;
+}
+
+/**
+ Copy data from system memory to the MMIO region by using 32-bit access.
+
+ Copy data from system memory specified by Buffer to the MMIO region specified
+ by starting address StartAddress by using 32-bit access. The total number
+ of byte to be copied is specified by Length. Buffer is returned.
+
+ If StartAddress is not aligned on a 32-bit boundary, then ASSERT().
+
+ If Length is greater than (MAX_ADDRESS - StartAddress + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS -Buffer + 1), then ASSERT().
+
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+
+ @param StartAddress The starting address for the MMIO region to be copied to.
+ @param Length The size, in bytes, of Buffer.
+ @param Buffer The pointer to a system memory buffer containing the data to write.
+
+ @return Buffer
+**/
+UINT32 *
+EFIAPI
+MmioWriteBuffer32 (
+ IN UINTN StartAddress,
+ IN UINTN Length,
+ IN CONST UINT32 *Buffer
+ )
+{
+ UINT32 *ReturnBuffer;
+
+ ASSERT ((StartAddress & (sizeof (UINT32) - 1)) == 0);
+
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - StartAddress));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN) Buffer));
+
+ ASSERT ((Length & (sizeof (UINT32) - 1)) == 0);
+ ASSERT (((UINTN) Buffer & (sizeof (UINT32) - 1)) == 0);
+
+ ReturnBuffer = (UINT32 *) Buffer;
+
+ while (Length != 0) {
+ MmioWrite32 (StartAddress, *(Buffer++));
+
+ StartAddress += sizeof (UINT32);
+ Length -= sizeof (UINT32);
+ }
+
+ return ReturnBuffer;
+}
+
+/**
+ Checks whether FTPM is enabled (FTPM_STS::FTPM_EN).
+
+ @retval TRUE FTPM is enabled.
+ @retval FALSE FTPM is disabled. All LT writes will be dropped.
+ All LT reads will be returned with read data value of all 0's.
+ The bit can only be written once per ME power cycle.
+
+**/
+BOOLEAN
+EFIAPI
+PttHciPresenceCheck (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+ DEBUG ((EFI_D_INFO, "PTT: PttHciPresenceCheck start\n"));
+
+ DEBUG ((EFI_D_INFO, "Check FTPM_STS - ENABLED bit (@ 0x%08x)\n", (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS)));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS),
+ B_PTT_HCI_STS_ENABLED,
+ V_PTT_HCI_IGNORE_BITS,
+ PTT_HCI_TIMEOUT_A
+ );
+ if(Status == EFI_SUCCESS){
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+ Checks whether PTT is Ready
+
+ @retval TRUE PTT is ready.
+ @retval FALSE PTT is not ready
+
+**/
+BOOLEAN
+EFIAPI
+PttHciReadyCheck (
+ VOID
+ )
+{
+ UINT32 RegRead;
+
+ RegRead = MmioRead32 ((UINTN) ( R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS ));
+ DEBUG ((EFI_D_INFO, "Check PTT_STS - READY bit (@ 0x%08x)\n", RegRead));
+
+ if(( B_PTT_HCI_STS_READY & RegRead) != 0){
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+ Checks whether TPM2_Startup command has been executed (FTPM_STS::STARTUP_EXEC).
+ If command was executed, it should not be redundantly issued again.
+
+ @retval TRUE Startup command executed already.
+ @retval FALSE Startup command not executed yet.
+
+**/
+BOOLEAN
+EFIAPI
+PttHciStartupExecuted (
+ VOID
+ )
+{
+ EFI_STATUS Status;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciStartupExecuted start\n"));
+ DEBUG ((EFI_D_INFO, "Check FTPM_STS - STARTUP_EXECECUTED bit (@ 0x%08x)\n", (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS)));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS),
+ B_PTT_HCI_STS_STARTUP_EXEC,
+ V_PTT_HCI_IGNORE_BITS,
+ PTT_HCI_TIMEOUT_A
+ );
+ if(Status == EFI_SUCCESS){
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+ Sets FTPM_CMD and CA_START register to a defined value to indicate that a command is
+ available for processing.
+ Any host write to this register shall result in an interrupt to the ME firmware.
+
+ @retval EFI_SUCCESS Register successfully written.
+ @retval TBD
+
+**/
+EFI_STATUS
+EFIAPI
+PttHciRequestCommandExec (
+ VOID
+ )
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciRequestCommandExec start\n"));
+
+ DEBUG ((EFI_D_INFO, "Command ready for processing - write 0x%08x to FTPM_CA_START register (@ 0x%08x)\n",
+ V_PTT_HCI_COMMAND_AVAILABLE_START,
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START)));
+ MmioWrite32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START, V_PTT_HCI_COMMAND_AVAILABLE_START);
+
+ ///
+ /// Write 0x1 to HCI CMD register to indicate that a command is available for processing
+ ///
+ DEBUG ((EFI_D_INFO, "Command ready for processing - write 0x%08x to FTPM_CMD register (@ 0x%08x)\n",
+ V_PTT_HCI_COMMAND_AVAILABLE_CMD,
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CMD)));
+ MmioWrite32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CMD, V_PTT_HCI_COMMAND_AVAILABLE_CMD);
+
+ return Status;
+}
+
+/**
+ Checks whether the value of a FTPM register satisfies the input BIT setting.
+
+ @param[in] Register Address port of register to be checked.
+ @param[in] BitSet Check these data bits are set.
+ @param[in] BitClear Check these data bits are clear.
+ @param[in] TimeOut The max wait time (unit MicroSecond) when checking register.
+
+ @retval EFI_SUCCESS The register satisfies the check bit.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+**/
+EFI_STATUS
+EFIAPI
+PttHciWaitRegisterBits(
+ IN EFI_PHYSICAL_ADDRESS RegAddress,
+ IN UINT32 BitSet,
+ IN UINT32 BitClear,
+ IN UINT32 TimeOut
+ )
+{
+ UINT32 RegRead;
+ UINT32 WaitTime;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciWaitRegisterBits start\n"));
+
+ for (WaitTime = 0; WaitTime < TimeOut; WaitTime += PTT_HCI_POLLING_PERIOD){
+ RegRead = MmioRead32 ((UINTN)RegAddress);
+ DEBUG ((EFI_D_INFO, "RegRead: 0x%08x, BitSetMask: 0x%08x, BitClearMask: 0x%08x, WaitTime: %d (microsec)\n", RegRead, BitSet, BitClear, WaitTime));
+
+ if (RegRead == 0xFFFFFFFF)
+ continue;
+
+ if ((RegRead & BitSet) == BitSet && (RegRead & BitClear) == 0) {
+ return EFI_SUCCESS;
+ }
+// MicroSecondDelay (PTT_HCI_POLLING_PERIOD); Override
+ MicroSecDelay(PTT_HCI_POLLING_PERIOD);
+ }
+ return EFI_TIMEOUT;
+}
+
+/**
+ Sends command to FTPM for execution.
+
+ @param[in] FtpmBuffer Buffer for TPM command data.
+ @param[in] DataLength TPM command data length.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+**/
+EFI_STATUS
+EFIAPI
+PttHciSend(
+ IN UINT8 *FtpmBuffer,
+ IN UINT32 DataLength
+ )
+{
+ EFI_STATUS Status;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciSend start\n"));
+
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START),
+ V_PTT_HCI_IGNORE_BITS,
+ V_PTT_HCI_START_CLEAR,
+ PTT_HCI_TIMEOUT_A
+ );
+
+ if(EFI_ERROR (Status)){
+ DEBUG ((EFI_D_ERROR, "FTPM_CA_START register not clear - TPM2 command cannot be sent! EFI_ERROR = %r\n", Status));
+ return EFI_NOT_READY;
+ }
+ ///
+ /// Align command size to dword before writing to FTPM_CRB
+ ///
+ if(DataLength % 4 != 0){
+ DEBUG ((EFI_D_INFO, "Alignment: DataLength change from %d ", DataLength));
+ DataLength += (4 - (DataLength % 4));
+ DEBUG ((EFI_D_INFO, "to %d\n", DataLength));
+ }
+
+ MmioWriteBuffer32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB), (UINTN)DataLength, (UINT32*)FtpmBuffer);
+
+ ///
+ /// FTPM_CA_CMD - the physical address to which the TPM 2.0 driver will write the command to execute
+ ///
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD), R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB);
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD_SZ), S_PTT_HCI_CRB_LENGTH);
+
+ DEBUG ((EFI_D_INFO, "FTPM_CA_CMD (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD),
+ R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB));
+ DEBUG ((EFI_D_INFO, "FTPM_CA_CMD_SZ (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD_SZ), DataLength));
+
+ ///
+ /// Set FTPM_CMD and FTPM_CA_START registers to indicate TPM command ready for execution
+ ///
+ Status = PttHciRequestCommandExec();
+#ifdef EFI_DEBUG
+ if(Status == EFI_SUCCESS){
+ DEBUG ((EFI_D_INFO, "FTPM_CMD register written - TPM2 command available for processing\n"));
+ }
+#endif
+
+ return Status;
+}
+
+/**
+ Receives response data of last command from FTPM.
+
+ @param[out] FtpmBuffer Buffer for response data.
+ @param[out] RespSize Response data length.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+ @retval EFI_DEVICE_ERROR Unexpected device status.
+ @retval EFI_BUFFER_TOO_SMALL Response data is too long.
+**/
+EFI_STATUS
+EFIAPI
+PttHciReceive(
+ OUT UINT8 *FtpmBuffer,
+ OUT UINT32 *RespSize
+ )
+{
+ EFI_STATUS Status;
+ UINT16 Data16;
+ UINT32 Data32;
+ DEBUG ((EFI_D_INFO, "PTT: PttHciReceive start\n"));
+
+ ///
+ /// Wait for the command completion - poll FTPM_CA_START clear
+ ///
+ DEBUG ((EFI_D_INFO, "PTT: Check Start status (FTPM_CA_START)\n"));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START),
+ V_PTT_HCI_IGNORE_BITS,
+ V_PTT_HCI_START_CLEAR,
+ PTT_HCI_TIMEOUT_D
+ );
+ if(EFI_ERROR (Status)){
+ DEBUG ((EFI_D_ERROR, "FTPM_CA_START register not clear - TPM2 response cannot be read! EFI_ERROR = %r\n", Status));
+ goto Exit;
+ }
+
+ ///
+ /// Check for error condition - FTPM_CA_ERROR
+ ///
+ DEBUG ((EFI_D_INFO, "PTT: Check Error status (FTPM_CA_ERROR)\n"));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_ERROR),
+ V_PTT_HCI_IGNORE_BITS,
+ V_PTT_HCI_ALL_BITS_CLEAR,
+ PTT_HCI_TIMEOUT_A
+ );
+ if(EFI_ERROR (Status)){
+ DEBUG ((EFI_D_ERROR, "FTPM_CA_ERROR register set - TPM2 response cannot be provided! EFI_ERROR = %r\n", Status));
+ Status = EFI_DEVICE_ERROR;
+ goto Exit;
+ }
+
+ DEBUG ((EFI_D_INFO, "FTPM_CA_START register clear - TPM2 command processing completed - ready to read\n"));
+
+ ///
+ /// Read the response data header
+ ///
+ MmioReadBuffer32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB, PTT_HCI_RESPONSE_HEADER_SIZE, (UINT32*)FtpmBuffer);
+
+ ///
+ /// Check the reponse data header (tag, parasize and returncode)
+ ///
+ CopyMem (&Data16, FtpmBuffer, sizeof (UINT16));
+ DEBUG ((EFI_D_INFO, "TPM2_RESPONSE_HEADER.tag = 0x%04x\n", SwapBytes16(Data16)));
+
+ ///
+ /// TPM Rev 2.0 Part 2 - 6.9 TPM_ST (Structure Tags)
+ /// TPM_ST_RSP_COMMAND - Used in a response that has an error in the tag.
+ ///
+ if (SwapBytes16(Data16) == TPM_ST_RSP_COMMAND) {
+ DEBUG ((EFI_D_ERROR, "TPM2_RESPONSE_HEADER.tag = TPM_ST_RSP_COMMAND - Error in response!\n"));
+ Status = EFI_DEVICE_ERROR;
+ goto Exit;
+ }
+
+ CopyMem(&Data32, (FtpmBuffer + 2), sizeof(UINT32));
+ DEBUG ((EFI_D_INFO, "TPM2_RESPONSE_HEADER.paramSize = 0x%08x\n", SwapBytes32(Data32)));
+
+ *RespSize = SwapBytes32(Data32);
+
+ if(*RespSize == sizeof(TPM2_RESPONSE_HEADER)) {
+ Status = EFI_SUCCESS;
+ goto Exit;
+ }
+ if(*RespSize < sizeof(TPM2_RESPONSE_HEADER)) {
+ Status = EFI_DEVICE_ERROR;
+ goto Exit;
+ }
+ if(*RespSize > S_PTT_HCI_CRB_LENGTH) {
+ Status = EFI_BUFFER_TOO_SMALL;
+ goto Exit;
+ }
+
+ ///
+ /// Align command size to dword before writing to FTPM_CRB
+ ///
+ if(*RespSize % 4 != 0){
+ DEBUG ((EFI_D_INFO, "Alignment: RespSize change from %d ", *RespSize));
+ *RespSize += (4 - (*RespSize % 4));
+ DEBUG ((EFI_D_INFO, "to %d\n", *RespSize));
+ }
+
+ ///
+ /// Reading the entire response data
+ ///
+ MmioReadBuffer32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB, *RespSize, (UINT32*)FtpmBuffer);
+
+ Exit:
+ if(!EFI_ERROR(Status)){
+ ///
+ /// FTPM_CA_CMD - the physical address from which the TPM 2.0 driver will read command responses
+ ///
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP), R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB);
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP_SZ),S_PTT_HCI_CRB_LENGTH);
+ DEBUG ((EFI_D_INFO, "FTPM_CA_RSP (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP),
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB)));
+ DEBUG ((EFI_D_INFO, "FTPM_CA_RSP_SZ (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP_SZ), *RespSize));
+ }
+
+ return Status;
+}
+
+/**
+ Sends formatted command to FTPM for execution and returns formatted response data.
+
+ @param[in] InputBuffer Buffer for the input data.
+ @param[in] InputBufferSize Size of the input buffer.
+ @param[out] ReturnBuffer Buffer for the output data.
+ @param[out] ReturnBufferSize Size of the output buffer.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+**/
+EFI_STATUS
+EFIAPI
+PttHciSubmitCommand(
+ IN UINT8 *InputBuffer,
+ IN UINT32 InputBufferSize,
+ OUT UINT8 *ReturnBuffer,
+ OUT UINT32 *ReturnBufferSize
+ )
+{
+ EFI_STATUS Status;
+ DEBUG ((EFI_D_INFO, "PTT: PttHciSubmitCommand start\n"));
+
+ if(!PttHciReadyCheck()){
+ DEBUG ((EFI_D_ERROR, "PTT device not ready. \n"));
+ return EFI_NOT_READY;
+ }
+
+ if(InputBuffer == NULL || ReturnBuffer == NULL || InputBufferSize == 0){
+ DEBUG ((EFI_D_ERROR, "Buffer == NULL or InputBufferSize == 0\n"));
+ return EFI_INVALID_PARAMETER;
+ }
+
+ DEBUG ((EFI_D_INFO, "PTT: Command Buffer dump\n"));
+
+ ///
+ /// Send the command to TPM
+ ///
+ Status = PttHciSend(InputBuffer, InputBufferSize);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "FTpmHciSend EFI_ERROR = %r\n", Status));
+ return Status;
+ }
+
+ ///
+ /// Receive the response data from TPM
+ ///
+ Status = PttHciReceive(ReturnBuffer, ReturnBufferSize);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "FTpmHciReceive EFI_ERROR = %r\n", Status));
+ return Status;
+ }
+
+ DEBUG ((EFI_D_INFO, "PTT: Response Buffer dump\n"));
+
+ return Status;
+}
+
+#endif // PTT_FLAG
diff --git a/ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.cif b/ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.cif
new file mode 100644
index 0000000..56a7865
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Common/PttHciDeviceLib.cif
@@ -0,0 +1,8 @@
+<component>
+ name = "PTT Common Library"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\ME\Library\Ptt\Common\"
+ RefName = "PttHciDeviceLib"
+[files]
+"PttHciDeviceLib.c"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.cif b/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.cif
new file mode 100644
index 0000000..341920f
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.cif
@@ -0,0 +1,9 @@
+<component>
+ name = "PTT Dxe Library"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\Me\Library\Ptt\Dxe\"
+ RefName = "PttHciDeviceDxeLib"
+[files]
+"PttHciDeviceDxeLib.inf"
+"PttHciDeviceDxeLib.h"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.h b/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.h
new file mode 100644
index 0000000..c8a042f
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.h
@@ -0,0 +1,37 @@
+/** @file
+ Platform Trust Technology (FTPM) HCI Device Dxe Library
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PTT_HCI_DEVICE_DXE_LIB_H_
+#define _PTT_HCI_DEVICE_DXE_LIB_H_
+
+#ifdef PTT_FLAG
+///
+/// External include files do NOT need to be explicitly specified in real EDKII
+/// environment
+///
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#endif
+///
+/// Common header for HCI Library
+///
+#include "PttHciDeviceLib.h"
+#endif // PTT_FLAG
+#endif
diff --git a/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.inf b/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.inf
new file mode 100644
index 0000000..7bc28ad
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Dxe/PttHciDeviceDxeLib.inf
@@ -0,0 +1,73 @@
+## @file
+# Component description file for PttHciDevice DXE Library.
+#
+#@copyright
+# Copyright (c) 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = PttHciDeviceDxeLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ PttHciDeviceDxeLib.h
+ ../Common/PttHciDeviceLib.c
+ ../Include/PttHciRegs.h
+ ../Include/PttHciDeviceLib.h
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/Ptt/Include
+#
+# Path to Tpm20.h should be updated when available in the code tree (core)
+# $(EFI_SOURCE)/SecurityPkg/Include/IndustryStandard
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+#
+# Typically the sample code referenced will be available in the code base already
+# So keep this include at the end to defer to the source base definition
+# and only use the sample code definition if source base does not include these files.
+#
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode/Include
+
+[libraries.common]
+ EdkIIGlueBaseLib
+ EdkIIGlueUefiLib
+ EdkIIGlueBaseMemoryLib
+ EdkIIGlueBaseIoLibIntrinsic
+ EdkIIGlueBaseTimerLibLocalApic
+ EdkIIGlueDxeDebugLibReportStatusCode
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_LIB__ \
+ -D __EDKII_GLUE_UEFI_LIB__ \
+ -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_BASE_IO_LIB_INTRINSIC__ \
+ -D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D PTT_FLAG
diff --git a/ReferenceCode/ME/Library/Ptt/Include/PttHciDeviceLib.h b/ReferenceCode/ME/Library/Ptt/Include/PttHciDeviceLib.h
new file mode 100644
index 0000000..e6e92de
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Include/PttHciDeviceLib.h
@@ -0,0 +1,175 @@
+/** @file
+ Platform Trust Technology (FTPM) HCI Device Library
+
+@copyright
+ Copyright (c) 2012 -2013 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PTT_HCI_DEVICE_LIB_H_
+#define _PTT_HCI_DEVICE_LIB_H_
+
+#ifdef PTT_FLAG
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#endif
+
+///
+/// Default Timeout values
+/// @todo these values should be adjusted on actual silicon after power-on
+///
+#define PTT_HCI_TIMEOUT_A 500 ///< 500 microseconds
+// AMI-Core Override for PTT +
+//#define PTT_HCI_TIMEOUT_B 10 * 1000 ///< 10ms (max command processing time in PK-TPM ca. 3ms)
+#define PTT_HCI_TIMEOUT_B 500 * 1000 ///< 10ms (max command processing time in PK-TPM ca. 3ms)
+// AMI-Core Override for PTT -
+#define PTT_HCI_TIMEOUT_C 1000 * 1000 ///< 1s
+#define PTT_HCI_TIMEOUT_D 500 * 1000 ///< 500 ms
+#define PTT_HCI_POLLING_PERIOD 140 ///< Poll register every 140 microsecondss
+
+/// TPM2_RESPONSE_HEADER size (10B) aligned to dword
+#define PTT_HCI_RESPONSE_HEADER_SIZE 12 ///< 12B
+
+/**
+ Checks whether FTPM is enabled (FTPM_STS::FTPM_EN).
+
+ @retval TRUE FTPM is enabled.
+ @retval FALSE FTPM is disabled. All LT writes will be dropped.
+ All LT reads will be returned with read data value of all 0's.
+ The bit can only be written once per ME power cycle.
+**/
+BOOLEAN
+EFIAPI
+PttHciPresenceCheck (
+ VOID
+ );
+
+/**
+ Checks whether TPM2_Startup command has been executed (FTPM_STS::STARTUP_EXEC).
+ If command was executed, it should not be redundantly issued again.
+
+ @retval TRUE Startup command executed already.
+ @retval FALSE Startup command not executed yet.
+**/
+BOOLEAN
+EFIAPI
+PttHciStartupExecuted (
+ VOID
+ );
+
+/**
+ Sets FTPM_CMD and CA_START register to a defined value to indicate that a command is
+ available for processing.
+ Any host write to this register shall result in an interrupt to the ME firmware.
+
+ @retval EFI_SUCCESS Register successfully written.
+ @retval TBD
+**/
+EFI_STATUS
+EFIAPI
+PttHciRequestCommandExec (
+ VOID
+ );
+
+/**
+ Checks whether the value of a FTPM register satisfies the input BIT setting.
+
+ @param[in] Register Address port of register to be checked.
+ @param[in] BitSet Check these data bits are set.
+ @param[in] BitClear Check these data bits are clear.
+ @param[in] TimeOut The max wait time (unit MicroSecond) when checking register.
+
+ @retval EFI_SUCCESS The register satisfies the check bit.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+**/
+EFI_STATUS
+EFIAPI
+PttHciWaitRegisterBits(
+ IN EFI_PHYSICAL_ADDRESS RegAddress,
+ IN UINT32 BitSet,
+ IN UINT32 BitClear,
+ IN UINT32 TimeOut
+ );
+
+/**
+ Sends command to FTPM for execution.
+
+ @param[in] FtpmBuffer Buffer for TPM command data.
+ @param[in] DataLength TPM command data length.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+**/
+EFI_STATUS
+EFIAPI
+PttHciSend(
+ IN UINT8 *FtpmBuffer,
+ IN UINT32 DataLength
+ );
+
+/**
+ Receives response data of last command from FTPM.
+
+ @param[out] FtpmBuffer Buffer for response data.
+ @param[out] RespSize Response data length.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+ @retval EFI_DEVICE_ERROR Unexpected device status.
+ @retval EFI_BUFFER_TOO_SMALL Response data is too long.
+**/
+EFI_STATUS
+EFIAPI
+PttHciReceive(
+ OUT UINT8 *FtpmBuffer,
+ OUT UINT32 *RespSize
+ );
+
+/**
+ Sends formatted command to FTPM for execution and returns formatted response data.
+
+ @param[in] InputBuffer Buffer for the input data.
+ @param[in] InputBufferSize Size of the input buffer.
+ @param[out] ReturnBuffer Buffer for the output data.
+ @param[out] ReturnBufferSize Size of the output buffer.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+**/
+EFI_STATUS
+EFIAPI
+PttHciSubmitCommand(
+ IN UINT8 *InputBuffer,
+ IN UINT32 InputBufferSize,
+ OUT UINT8 *ReturnBuffer,
+ OUT UINT32 *ReturnBufferSize
+ );
+
+/**
+ Checks whether PTT is Ready
+
+ @retval TRUE PTT is ready.
+ @retval FALSE PTT is not ready
+
+**/
+BOOLEAN
+EFIAPI
+PttHciReadyCheck (
+ VOID
+ );
+
+#endif // PTT_FLAG
+#endif
diff --git a/ReferenceCode/ME/Library/Ptt/Include/PttHciRegs.h b/ReferenceCode/ME/Library/Ptt/Include/PttHciRegs.h
new file mode 100644
index 0000000..cba0c8a
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Include/PttHciRegs.h
@@ -0,0 +1,100 @@
+/** @file
+ Register definitions for PTT HCI (Platform Trust Technology - Host Controller Interface).
+
+ Conventions:
+
+ - Prefixes:
+ Definitions beginning with "R_" are registers
+ Definitions beginning with "B_" are bits within registers
+ Definitions beginning with "V_" are meaningful values of bits within the registers
+ Definitions beginning with "S_" are register sizes
+ Definitions beginning with "N_" are the bit position
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PTT_HCI_REGS_H_
+#define _PTT_HCI_REGS_H_
+
+#ifdef PTT_FLAG
+
+///
+/// FTPM HCI register base address
+///
+#define R_PTT_HCI_BASE_ADDRESS 0xFED70000
+
+//
+// FTPM HCI Control Area
+//
+#define R_PTT_HCI_CA_RSVD 0x00
+#define R_PTT_HCI_CA_ERROR 0x04
+#define R_PTT_HCI_CA_CANCEL 0x08
+#define R_PTT_HCI_CA_START 0x0C
+#define R_PTT_HCI_CA_INT_RSVD 0x10
+#define R_PTT_HCI_CA_CMD_SZ 0x18
+#define R_PTT_HCI_CA_CMD 0x1C
+#define R_PTT_HCI_CA_RSP_SZ 0x24
+#define R_PTT_HCI_CA_RSP 0x28
+
+//
+// FTPM HCI Private Area
+//
+#define R_PTT_HCI_CMD 0x40
+#define R_PTT_HCI_STS 0x44
+
+///
+/// FTPM HCI Command and Response Buffer
+///
+#define R_PTT_HCI_CRB 0x80
+
+//
+// R_PTT_HCI_STS Flags
+//
+#define B_PTT_HCI_STS_ENABLED 0x00000001 ///< BIT0
+#define B_PTT_HCI_STS_READY 0x00000002 ///< BIT1
+#define B_PTT_HCI_STS_ACM_AS_CRTM 0x00000004 ///< BIT2
+#define B_PTT_HCI_STS_STARTUP_EXEC 0x00000008 ///< BIT3
+
+//
+// Value written to R_PTT_HCI_CMD and CA_START
+// to indicate that a command is available for processing
+//
+#define V_PTT_HCI_COMMAND_AVAILABLE_START 0x00000001
+#define V_PTT_HCI_COMMAND_AVAILABLE_CMD 0x00000000
+#define V_PTT_HCI_BUFFER_ADDRESS_RDY 0x00000003
+
+///
+/// Ignore bit setting mask for WaitRegisterBits
+///
+#define V_PTT_HCI_IGNORE_BITS 0x00000000
+
+///
+/// All bits clear mask for WaitRegisterBits
+///
+#define V_PTT_HCI_ALL_BITS_CLEAR 0xFFFFFFFF
+#define V_PTT_HCI_START_CLEAR 0x00000001
+
+///
+/// Max FTPM command/reponse buffer length
+///
+#define S_PTT_HCI_CRB_LENGTH 3968 ///< 0xFED70080:0xFED70FFF = 3968 Bytes
+// AMI-Core Override for PTT +
+#define PM_BASE_ADDRESS 0x1800
+// AMI-Core Override for PTT -
+
+#endif // PTT_FLAG
+#endif
diff --git a/ReferenceCode/ME/Library/Ptt/Include/PttLibInc.cif b/ReferenceCode/ME/Library/Ptt/Include/PttLibInc.cif
new file mode 100644
index 0000000..a444f07
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Include/PttLibInc.cif
@@ -0,0 +1,9 @@
+<component>
+ name = "PttLibrary Include"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\Me\Library\Ptt\Include"
+ RefName = "PttLibInc"
+[files]
+"PttHciDeviceLib.h"
+"PttHciRegs.h"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/Ptt/Pei/PttHciDeviceLib.c b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDeviceLib.c
new file mode 100644
index 0000000..107a3ca
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDeviceLib.c
@@ -0,0 +1,590 @@
+/**
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+/**
+
+Copyright (c) 2012 Intel Corporation. All rights reserved
+This software and associated documentation (if any) is furnished
+under a license and may only be used or copied in accordance
+with the terms of the license. Except as permitted by such
+license, no part of this software or documentation 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.
+
+ @file
+ PttHciDeviceLib.c
+
+ @brief
+ Implements Platform Trust Technology (FTPM) HCI Device Library.
+
+**/
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#endif
+
+#ifdef PTT_FLAG
+#include "PttHciRegs.h"
+#include "PttHciDeviceLib.h"
+#include <IndustryStandard/Tpm20.h>
+
+#ifdef EFI_DEBUG
+/**
+
+ Prints command or response buffer for debugging purposes.
+
+ @param[in] Buffer Buffer to print.
+ @param[in] BufferSize Buffer data length.
+
+**/
+VOID
+EFIAPI
+PttHciPrintBuffer(IN UINT8 *Buffer, IN UINT32 BufferSize)
+{
+ UINT32 Index;
+
+ DEBUG ((EFI_D_INFO, "Buffer Address: 0x%08x, Size: 0x%08x, Value:\n", Buffer, BufferSize));
+ for(Index = 0; Index < BufferSize; Index++){
+ DEBUG ((EFI_D_INFO, "%02x ", *(Buffer + Index)));
+ if((Index+1) % 16 == 0) DEBUG ((EFI_D_INFO, "\n"));
+ }
+ DEBUG ((EFI_D_INFO, "\n"));
+}
+#endif // EFI_DEBUG
+
+
+
+VOID MicroSecDelay (
+ UINTN Delay
+)
+{
+ UINTN Counter, i;
+ UINT32 Data32, PrevData;
+ UINT32 Remainder;
+
+ Counter = (UINTN)DivU64x32Remainder ((UINT64)(Delay * 10), 3, &Remainder);
+ if (Remainder != 0) {
+ Counter++;
+ }
+ //
+ // Call WaitForTick for Counter + 1 ticks to try to guarantee Counter tick
+ // periods, thus attempting to ensure Microseconds of stall time.
+ //
+ if (Counter != 0) {
+
+ PrevData = IoRead32(PM_BASE_ADDRESS + 8);
+ for (i = 0; i < Counter; ) {
+ Data32 = IoRead32(PM_BASE_ADDRESS + 8);
+ if (Data32 < PrevData) { // Reset if there is a overlap
+ PrevData=Data32;
+ continue;
+ }
+ i += (Data32 - PrevData);
+ PrevData = Data32;
+ }
+ }
+ return;
+}
+
+/**
+ Copy data from the MMIO region to system memory by using 32-bit access.
+
+ Copy data from the MMIO region specified by starting address StartAddress
+ to system memory specified by Buffer by using 32-bit access. The total
+ number of byte to be copied is specified by Length. Buffer is returned.
+
+ If StartAddress is not aligned on a 32-bit boundary, then ASSERT().
+
+ If Length is greater than (MAX_ADDRESS - StartAddress + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS - Buffer + 1), then ASSERT().
+
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+
+ @param StartAddress The starting address for the MMIO region to be copied from.
+ @param Length The size, in bytes, of Buffer.
+ @param Buffer The pointer to a system memory buffer receiving the data read.
+
+ @return Buffer
+
+**/
+UINT32 *
+EFIAPI
+MmioReadBuffer32 (
+ IN UINTN StartAddress,
+ IN UINTN Length,
+ OUT UINT32 *Buffer
+ )
+{
+ UINT32 *ReturnBuffer;
+
+ ASSERT ((StartAddress & (sizeof (UINT32) - 1)) == 0);
+
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - StartAddress));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN) Buffer));
+
+ ASSERT ((Length & (sizeof (UINT32) - 1)) == 0);
+ ASSERT (((UINTN) Buffer & (sizeof (UINT32) - 1)) == 0);
+
+ ReturnBuffer = Buffer;
+
+ while (Length != 0) {
+ *(Buffer++) = MmioRead32 (StartAddress);
+ StartAddress += sizeof (UINT32);
+ Length -= sizeof (UINT32);
+ }
+
+ return ReturnBuffer;
+}
+
+/**
+ Copy data from system memory to the MMIO region by using 32-bit access.
+
+ Copy data from system memory specified by Buffer to the MMIO region specified
+ by starting address StartAddress by using 32-bit access. The total number
+ of byte to be copied is specified by Length. Buffer is returned.
+
+ If StartAddress is not aligned on a 32-bit boundary, then ASSERT().
+
+ If Length is greater than (MAX_ADDRESS - StartAddress + 1), then ASSERT().
+ If Length is greater than (MAX_ADDRESS -Buffer + 1), then ASSERT().
+
+ If Length is not aligned on a 32-bit boundary, then ASSERT().
+
+ If Buffer is not aligned on a 32-bit boundary, then ASSERT().
+
+ @param StartAddress The starting address for the MMIO region to be copied to.
+ @param Length The size, in bytes, of Buffer.
+ @param Buffer The pointer to a system memory buffer containing the data to write.
+
+ @return Buffer
+
+**/
+UINT32 *
+EFIAPI
+MmioWriteBuffer32 (
+ IN UINTN StartAddress,
+ IN UINTN Length,
+ IN CONST UINT32 *Buffer
+ )
+{
+ UINT32 *ReturnBuffer;
+
+ ASSERT ((StartAddress & (sizeof (UINT32) - 1)) == 0);
+
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - StartAddress));
+ ASSERT ((Length - 1) <= (MAX_ADDRESS - (UINTN) Buffer));
+
+ ASSERT ((Length & (sizeof (UINT32) - 1)) == 0);
+ ASSERT (((UINTN) Buffer & (sizeof (UINT32) - 1)) == 0);
+
+ ReturnBuffer = (UINT32 *) Buffer;
+
+ while (Length != 0) {
+ MmioWrite32 (StartAddress, *(Buffer++));
+
+ StartAddress += sizeof (UINT32);
+ Length -= sizeof (UINT32);
+ }
+
+ return ReturnBuffer;
+}
+
+/**
+
+ Checks whether FTPM is enabled (FTPM_STS::FTPM_EN).
+
+ @retval TRUE FTPM is enabled.
+ @retval FALSE FTPM is disabled. All LT writes will be dropped.
+ All LT reads will be returned with read data value of all 0’s.
+ The bit can only be written once per ME power cycle.
+
+**/
+BOOLEAN
+EFIAPI
+PttHciPresenceCheck()
+{
+ EFI_STATUS Status;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciPresenceCheck start\n"));
+ DEBUG ((EFI_D_INFO, "Check FTPM_STS - ENABLED bit (@ 0x%08x)\n", (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS)));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS),
+ B_PTT_HCI_STS_ENABLED,
+ V_PTT_HCI_IGNORE_BITS,
+ PTT_HCI_TIMEOUT_A
+ );
+ if(Status == EFI_SUCCESS){
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+
+ Checks whether TPM2_Startup command has been executed (FTPM_STS::STARTUP_EXEC).
+ If command was executed, it should not be redundantly issued again.
+
+ @retval TRUE Startup command executed already.
+ @retval FALSE Startup command not executed yet.
+
+**/
+BOOLEAN
+EFIAPI
+PttHciStartupExecuted()
+{
+ EFI_STATUS Status;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciStartupExecuted start\n"));
+ DEBUG ((EFI_D_INFO, "Check FTPM_STS - STARTUP_EXECECUTED bit (@ 0x%08x)\n", (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS)));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_STS),
+ B_PTT_HCI_STS_STARTUP_EXEC,
+ V_PTT_HCI_IGNORE_BITS,
+ PTT_HCI_TIMEOUT_A
+ );
+ if(Status == EFI_SUCCESS){
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
+/**
+
+ Sets FTPM_CMD and CA_START register to a defined value to indicate that a command is
+ available for processing.
+ Any host write to this register shall result in an interrupt to the ME firmware.
+
+ @retval EFI_SUCCESS Register successfully written.
+ @retval TBD
+
+**/
+EFI_STATUS
+EFIAPI
+PttHciRequestCommandExec()
+{
+ EFI_STATUS Status = EFI_SUCCESS;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciRequestCommandExec start\n"));
+
+ DEBUG ((EFI_D_INFO, "Command ready for processing - write 0x%08x to FTPM_CA_START register (@ 0x%08x)\n",
+ V_PTT_HCI_COMMAND_AVAILABLE_START,
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START)));
+ MmioWrite32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START, V_PTT_HCI_COMMAND_AVAILABLE_START);
+
+ ///
+ /// Write 0x1 to HCI CMD register to indicate that a command is available for processing
+ ///
+ DEBUG ((EFI_D_INFO, "Command ready for processing - write 0x%08x to FTPM_CMD register (@ 0x%08x)\n",
+ V_PTT_HCI_COMMAND_AVAILABLE_CMD,
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CMD)));
+ MmioWrite32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CMD, V_PTT_HCI_COMMAND_AVAILABLE_CMD);
+
+ return Status;
+}
+
+/**
+
+ Checks whether the value of a FTPM register satisfies the input BIT setting.
+
+ @param[in] Register Address port of register to be checked.
+ @param[in] BitSet Check these data bits are set.
+ @param[in] BitClear Check these data bits are clear.
+ @param[in] TimeOut The max wait time (unit MicroSecond) when checking register.
+
+ @retval EFI_SUCCESS The register satisfies the check bit.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+
+**/
+EFI_STATUS
+EFIAPI
+PttHciWaitRegisterBits(
+ IN EFI_PHYSICAL_ADDRESS RegAddress,
+ IN UINT32 BitSet,
+ IN UINT32 BitClear,
+ IN UINT32 TimeOut
+ )
+{
+ UINT32 RegRead;
+ UINT32 WaitTime;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciWaitRegisterBits start\n"));
+
+ for (WaitTime = 0; WaitTime < TimeOut; WaitTime += PTT_HCI_POLLING_PERIOD){
+ RegRead = MmioRead32 ((UINTN)RegAddress);
+ DEBUG ((EFI_D_INFO, "RegRead: 0x%08x, BitSetMask: 0x%08x, BitClearMask: 0x%08x, WaitTime: %d (microsec)\n", RegRead, BitSet, BitClear, WaitTime));
+
+ if (RegRead == 0xFFFFFFFF)
+ continue;
+
+ if ((RegRead & BitSet) == BitSet && (RegRead & BitClear) == 0) {
+ return EFI_SUCCESS;
+ }
+
+// MicroSecondDelay (PTT_HCI_POLLING_PERIOD);
+ MicroSecDelay(PTT_HCI_POLLING_PERIOD);
+ }
+ return EFI_TIMEOUT;
+}
+
+/**
+
+ Sends command to FTPM for execution.
+
+ @param[in] FtpmBuffer Buffer for TPM command data.
+ @param[in] DataLength TPM command data length.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+
+**/
+EFI_STATUS
+EFIAPI
+PttHciSend(
+ IN UINT8 *FtpmBuffer,
+ IN UINT32 DataLength
+ )
+{
+ EFI_STATUS Status;
+
+ DEBUG ((EFI_D_INFO, "PTT: PttHciSend start\n"));
+
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START),
+ V_PTT_HCI_IGNORE_BITS,
+ V_PTT_HCI_START_CLEAR,
+ PTT_HCI_TIMEOUT_A
+ );
+
+ if(EFI_ERROR (Status)){
+ DEBUG ((EFI_D_ERROR, "FTPM_CA_START register not clear - TPM2 command cannot be sent! EFI_ERROR = %r\n", Status));
+ return EFI_NOT_READY;
+ }
+ ///
+ /// Align command size to dword before writing to FTPM_CRB
+ ///
+ if(DataLength % 4 != 0){
+ DEBUG ((EFI_D_INFO, "Alignment: DataLength change from %d ", DataLength));
+ DataLength += (4 - (DataLength % 4));
+ DEBUG ((EFI_D_INFO, "to %d\n", DataLength));
+ }
+
+ MmioWriteBuffer32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB), (UINTN)DataLength, (UINT32*)FtpmBuffer);
+
+ ///
+ /// FTPM_CA_CMD - the physical address to which the TPM 2.0 driver will write the command to execute
+ ///
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD), R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB);
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD_SZ), S_PTT_HCI_CRB_LENGTH);
+
+ DEBUG ((EFI_D_INFO, "FTPM_CA_CMD (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD),
+ R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB));
+ DEBUG ((EFI_D_INFO, "FTPM_CA_CMD_SZ (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_CMD_SZ), DataLength));
+
+ ///
+ /// Set FTPM_CMD and FTPM_CA_START registers to indicate TPM command ready for execution
+ ///
+ Status = PttHciRequestCommandExec();
+#ifdef EFI_DEBUG
+ if(Status == EFI_SUCCESS){
+ DEBUG ((EFI_D_INFO, "FTPM_CMD register written - TPM2 command available for processing\n"));
+ }
+#endif
+
+ return Status;
+}
+
+/**
+
+ Receives response data of last command from FTPM.
+
+ @param[out] FtpmBuffer Buffer for response data.
+ @param[out] RespSize Response data length.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+ @retval EFI_DEVICE_ERROR Unexpected device status.
+ @retval EFI_BUFFER_TOO_SMALL Response data is too long.
+
+**/
+EFI_STATUS
+EFIAPI
+PttHciReceive(
+ OUT UINT8 *FtpmBuffer,
+ OUT UINT32 *RespSize
+ )
+{
+ EFI_STATUS Status;
+ UINT16 Data16;
+ UINT32 Data32;
+ DEBUG ((EFI_D_INFO, "PTT: PttHciReceive start\n"));
+
+ ///
+ /// Wait for the command completion - poll FTPM_CA_START clear
+ ///
+ DEBUG ((EFI_D_INFO, "PTT: Check Start status (FTPM_CA_START)\n"));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_START),
+ V_PTT_HCI_IGNORE_BITS,
+ V_PTT_HCI_START_CLEAR,
+ PTT_HCI_TIMEOUT_B
+ );
+ if(EFI_ERROR (Status)){
+ DEBUG ((EFI_D_ERROR, "FTPM_CA_START register not clear - TPM2 response cannot be read! EFI_ERROR = %r\n", Status));
+ goto Exit;
+ }
+
+ ///
+ /// Check for error condition - FTPM_CA_ERROR
+ ///
+ DEBUG ((EFI_D_INFO, "PTT: Check Error status (FTPM_CA_ERROR)\n"));
+ Status = PttHciWaitRegisterBits(
+ (EFI_PHYSICAL_ADDRESS)(UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_ERROR),
+ V_PTT_HCI_IGNORE_BITS,
+ V_PTT_HCI_ALL_BITS_CLEAR,
+ PTT_HCI_TIMEOUT_A
+ );
+ if(EFI_ERROR (Status)){
+ DEBUG ((EFI_D_ERROR, "FTPM_CA_ERROR register set - TPM2 response cannot be provided! EFI_ERROR = %r\n", Status));
+ Status = EFI_DEVICE_ERROR;
+ goto Exit;
+ }
+
+ DEBUG ((EFI_D_INFO, "FTPM_CA_START register clear - TPM2 command processing completed - ready to read\n"));
+
+ ///
+ /// Read the response data header
+ ///
+ MmioReadBuffer32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB, PTT_HCI_RESPONSE_HEADER_SIZE, (UINT32*)FtpmBuffer);
+
+ ///
+ /// Check the reponse data header (tag, parasize and returncode)
+ ///
+ CopyMem (&Data16, FtpmBuffer, sizeof (UINT16));
+ DEBUG ((EFI_D_INFO, "TPM2_RESPONSE_HEADER.tag = 0x%04x\n", SwapBytes16(Data16)));
+
+ ///
+ /// TPM Rev 2.0 Part 2 - 6.9 TPM_ST (Structure Tags)
+ /// TPM_ST_RSP_COMMAND - Used in a response that has an error in the tag.
+ ///
+ if (SwapBytes16(Data16) == TPM_ST_RSP_COMMAND) {
+ DEBUG ((EFI_D_ERROR, "TPM2_RESPONSE_HEADER.tag = TPM_ST_RSP_COMMAND - Error in response!\n"));
+ Status = EFI_DEVICE_ERROR;
+ goto Exit;
+ }
+
+ CopyMem(&Data32, (FtpmBuffer + 2), sizeof(UINT32));
+ DEBUG ((EFI_D_INFO, "TPM2_RESPONSE_HEADER.paramSize = 0x%08x\n", SwapBytes32(Data32)));
+
+ *RespSize = SwapBytes32(Data32);
+
+ if(*RespSize == sizeof(TPM2_RESPONSE_HEADER)) {
+ Status = EFI_SUCCESS;
+ goto Exit;
+ }
+ if(*RespSize < sizeof(TPM2_RESPONSE_HEADER)) {
+ Status = EFI_DEVICE_ERROR;
+ goto Exit;
+ }
+ if(*RespSize > S_PTT_HCI_CRB_LENGTH) {
+ Status = EFI_BUFFER_TOO_SMALL;
+ goto Exit;
+ }
+
+ ///
+ /// Align command size to dword before writing to FTPM_CRB
+ ///
+ if(*RespSize % 4 != 0){
+ DEBUG ((EFI_D_INFO, "Alignment: RespSize change from %d ", *RespSize));
+ *RespSize += (4 - (*RespSize % 4));
+ DEBUG ((EFI_D_INFO, "to %d\n", *RespSize));
+ }
+
+ ///
+ /// Reading the entire response data
+ ///
+ MmioReadBuffer32((UINTN)R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB, *RespSize, (UINT32*)FtpmBuffer);
+
+ Exit:
+ if(!EFI_ERROR(Status)){
+ ///
+ /// FTPM_CA_CMD - the physical address from which the TPM 2.0 driver will read command responses
+ ///
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP), R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB);
+ MmioWrite32((UINTN)(R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP_SZ),S_PTT_HCI_CRB_LENGTH);
+ DEBUG ((EFI_D_INFO, "FTPM_CA_RSP (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP),
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CRB)));
+ DEBUG ((EFI_D_INFO, "FTPM_CA_RSP_SZ (@ 0x%08x) written, value = 0x%08x\n",
+ (R_PTT_HCI_BASE_ADDRESS + R_PTT_HCI_CA_RSP_SZ), *RespSize));
+ }
+
+ return Status;
+}
+
+/**
+
+ Sends formatted command to FTPM for execution and returns formatted response data.
+
+ @param[in] InputBuffer Buffer for the input data.
+ @param[in] InputBufferSize Size of the input buffer.
+ @param[out] ReturnBuffer Buffer for the output data.
+ @param[out] ReturnBufferSize Size of the output buffer.
+
+ @retval EFI_SUCCESS Operation completed successfully.
+ @retval EFI_TIMEOUT The register can't run into the expected status in time.
+
+**/
+EFI_STATUS
+EFIAPI
+PttHciSubmitCommand(
+ IN UINT8 *InputBuffer,
+ IN UINT32 InputBufferSize,
+ OUT UINT8 *ReturnBuffer,
+ OUT UINT32 *ReturnBufferSize
+ )
+{
+ EFI_STATUS Status;
+ DEBUG ((EFI_D_INFO, "PTT: PttHciSubmitCommand start\n"));
+
+ if(InputBuffer == NULL || ReturnBuffer == NULL || InputBufferSize == 0){
+ DEBUG ((EFI_D_ERROR, "Buffer == NULL or InputBufferSize == 0\n"));
+ return EFI_INVALID_PARAMETER;
+ }
+
+ DEBUG ((EFI_D_INFO, "PTT: Command Buffer dump\n"));
+
+ ///
+ /// Send the command to TPM
+ ///
+ Status = PttHciSend(InputBuffer, InputBufferSize);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "FTpmHciSend EFI_ERROR = %r\n", Status));
+ return Status;
+ }
+
+ ///
+ /// Receive the response data from TPM
+ ///
+ Status = PttHciReceive(ReturnBuffer, ReturnBufferSize);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "FTpmHciReceive EFI_ERROR = %r\n", Status));
+ return Status;
+ }
+
+ DEBUG ((EFI_D_INFO, "PTT: Response Buffer dump\n"));
+
+ return Status;
+}
+
+#endif // PTT_FLAG \ No newline at end of file
diff --git a/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.cif b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.cif
new file mode 100644
index 0000000..c0c66b4
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.cif
@@ -0,0 +1,12 @@
+<component>
+ name = "PTT Pei Library"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\Me\Library\Ptt\Pei\"
+ RefName = "PttHciDevicePeiLib"
+[files]
+"PttHciDevicePeiLib.inf"
+"PttHciDeviceLib.c"
+"PttHciDevicePeiLib.h"
+"PttHciDevicePeiLib.sdl"
+"PttHciDevicePeiLib.mak"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.h b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.h
new file mode 100644
index 0000000..2decd76
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.h
@@ -0,0 +1,37 @@
+/** @file
+ Platform Trust Technology (FTPM) HCI Device Pei Library
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PTT_HCI_DEVICE_PEI_LIB_H_
+#define _PTT_HCI_DEVICE_PEI_LIB_H_
+
+#ifdef PTT_FLAG
+///
+/// External include files do NOT need to be explicitly specified in real EDKII
+/// environment
+///
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGluePeim.h"
+#endif
+///
+/// Common header for HCI Library
+///
+#include "PttHciDeviceLib.h"
+#endif // PTT_FLAG
+#endif
diff --git a/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.inf b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.inf
new file mode 100644
index 0000000..faac249
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.inf
@@ -0,0 +1,71 @@
+## @file
+# Component description file for PttHciDevice PEI Library.
+#
+#@copyright
+# Copyright (c) 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = PttHciDevicePeiLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ PttHciDevicePeiLib.h
+ ../Common/PttHciDeviceLib.c
+ ../Include/PttHciRegs.h
+ ../Include/PttHciDeviceLib.h
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/Ptt/Include
+# Path to Tpm20.h should be updated when available in the code tree (core)
+# $(EFI_SOURCE)/SecurityPkg/Include/IndustryStandard
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+#
+# Typically the sample code referenced will be available in the code base already
+# So keep this include at the end to defer to the source base definition
+# and only use the sample code definition if source base does not include these files.
+#
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode/Include
+
+[libraries.common]
+ EdkIIGlueBaseLib
+ EdkIIGlueBaseMemoryLib
+ EdkIIGlueBaseIoLibIntrinsic
+ EdkIIGlueBaseTimerLibLocalApic
+ EdkIIGluePeiDebugLibReportStatusCode
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_LIB__ \
+ -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_BASE_IO_LIB_INTRINSIC__ \
+ -D __EDKII_GLUE_PEI_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D PTT_FLAG
+
diff --git a/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.mak b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.mak
new file mode 100644
index 0000000..d791a33
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.mak
@@ -0,0 +1,80 @@
+#*************************************************************************
+#*************************************************************************
+#** **
+#** (C)Copyright 1985-2010, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#*************************************************************************
+#*************************************************************************
+#**********************************************************************
+#
+# $Header: /Alaska/SOURCE/Modules/SharkBayRefCodes/ME/MeLibrary/PTT/PTT Pei Library/PttHciDevicePeiLib.mak 1 12/18/12 5:48a Klzhan $
+#
+# $Revision: 1 $
+#
+# $Date: 12/18/12 5:48a $
+#
+#**********************************************************************
+# Revision History
+# ----------------
+# $Log: /Alaska/SOURCE/Modules/SharkBayRefCodes/ME/MeLibrary/PTT/PTT Pei Library/PttHciDevicePeiLib.mak $
+#
+# 1 12/18/12 5:48a Klzhan
+# [TAG] EIPNone
+# [Category] Improvement
+# [Description] AMI modify for TPM2.0
+#
+#**********************************************************************
+#
+#<AMI_FHDR_START>
+#----------------------------------------------------------------------------
+#
+# Name:
+#
+# Description:
+#
+#----------------------------------------------------------------------------
+#<AMI_FHDR_END>
+all : PttHciDevicePeiLib
+
+PttHciDevicePeiLib : $(BUILD_DIR)\PttHciDevicePeiLib.mak PttHciDevicePeiLibBin
+
+$(BUILD_DIR)\PttHciDevicePeiLib.mak : $(PttHciDevicePeiLib_DIR)\PttHciDevicePeiLib.cif $(PttHciDevicePeiLib_DIR)\PttHciDevicePeiLib.mak $(BUILD_RULES)
+ $(CIF2MAK) $(PttHciDevicePeiLib_DIR)\PttHciDevicePeiLib.cif $(CIF2MAK_DEFAULTS)
+
+PttHciDevicePeiLib_INCLUDES= \
+ $(ME_INCLUDES)\
+ $(EdkIIGlueLib_INCLUDES)\
+ $(EdkIIGlueInclude)\
+ $(IndustryStandard_INCLUDES)\
+ /IReferenceCode\ME\SampleCode\
+ $(INTEL_PCH_INCLUDES)\
+
+
+PttHciDevicePeiLib_DEFINES = $(MY_DEFINES)\
+ /D __EDKII_GLUE_PEI_SERVICES_LIB__ \
+!IF "$(IntelPTT_SUPPORT)"=="1"
+ /D PTT_FLAG
+!ENDIF
+
+
+PttHciDevicePeiLib_LIB_LINKS =\
+ $(EdkIIGlueBaseLib_LIB)\
+ $(EdkIIGlueBaseMemoryLib_LIB)\
+ $(EdkIIGlueBaseIoLibIntrinsic_LIB)\
+ $(EdkIIGluePeiDebugLibReportStatusCode_LIB)\
+ $(EdkIIGlueBaseTimerLibLocalApic_LIB)
+
+
+PttHciDevicePeiLibBin: $(PttHciDevicePeiLib_LIB_LINKS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS)\
+ /f $(BUILD_DIR)\PttHciDevicePeiLib.mak all\
+ "MY_INCLUDES=$(PttHciDevicePeiLib_INCLUDES)"\
+ "MY_DEFINES=$(PttHciDevicePeiLib_DEFINES)"\
+ GUID=D58E4250-FDFF-4f6c-B972-9FCA453B3397\
+ TYPE=PEI_LIBRARY
diff --git a/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.sdl b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.sdl
new file mode 100644
index 0000000..fc3f8cf
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/Pei/PttHciDevicePeiLib.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "PttHciDevicePeiLib_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable PttHciDevicePeiLib support in Project"
+End
+
+MODULE
+ Help = "Includes PttHciDevicePeiLib.mak to Project"
+ File = "PttHciDevicePeiLib.mak"
+End
+
+PATH
+ Name = "PttHciDevicePeiLib_DIR"
+ Help = ""
+End
+
+ELINK
+ Name = "PttHciDevicePeiLib_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\PttHciDevicePeiLib.lib"
+ Parent = "PttHciDevicePeiLib_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(PttHciDevicePeiLib_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/Ptt/PttLibrary.cif b/ReferenceCode/ME/Library/Ptt/PttLibrary.cif
new file mode 100644
index 0000000..f768f03
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/PttLibrary.cif
@@ -0,0 +1,14 @@
+<component>
+ name = "PttLibrary"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\Me\Library\Ptt\"
+ RefName = "PttLibrary"
+[files]
+"PttLibrary.sdl"
+"PttLibrary.mak"
+[parts]
+"PttHciDeviceLib"
+"PttHciDeviceDxeLib"
+"PttHciDevicePeiLib"
+"PttLibInc"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/Ptt/PttLibrary.mak b/ReferenceCode/ME/Library/Ptt/PttLibrary.mak
new file mode 100644
index 0000000..0f65d78
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/PttLibrary.mak
@@ -0,0 +1,101 @@
+# /*++
+# Copyright (c) 2009 Intel Corporation. All rights reserved.
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+# --*/
+# MAK file for the ModulePart:AtDxeLib
+all : PttDxeLib PttPeiLib
+
+
+$(BUILD_DIR)\PttDxeLibrary.lib : PttDxeLib
+
+PttDxeLib : $(BUILD_DIR)\PttLibrary.mak PttDxeLibBin
+
+PttDxeLib_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES) \
+ $(ME_INCLUDES) \
+ -IReferenceCode\ME\SampleCode\Include\IndustryStandard\
+
+PttDxeLib_DEFINES=\
+ -D __EDKII_GLUE_BASE_LIB__ \
+ -D __EDKII_GLUE_UEFI_LIB__ \
+ -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_BASE_IO_LIB_INTRINSIC__ \
+ -D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D TIANO_RELEASE_VERSION=0x00080006\
+ -D PTT_FLAG
+
+$(BUILD_DIR)\PttLibrary.mak : $(MePttLibrary_DIR)\Common\PttHciDeviceLib.cif $(MePttLibrary_DIR)\PttLibrary.mak $(BUILD_RULES)
+ $(CIF2MAK) $(MePttLibrary_DIR)\Common\PttHciDeviceLib.cif $(CIF2MAK_DEFAULTS)
+
+PttDxeLib_LIBS=\
+ $(EdkIIGlueBaseLib_LIB)\
+ $(EdkIIGlueUefiLib_LIB)\
+ $(EdkIIGlueBaseMemoryLib_LIB)\
+ $(EdkIIGlueBaseIoLibIntrinsic_LIB)\
+ $(EdkIIGlueBaseTimerLibLocalApic_LIB)\
+ $(EdkIIGlueDxeDebugLibReportStatusCode_LIB)\
+
+PttDxeLibBin : $(PttDxeLib_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ MAKEFILE=$(BUILD_DIR)\PttLibrary.mak \
+ /f $(BUILD_DIR)\PttLibrary.mak all \
+ "MY_INCLUDES=$(PttDxeLib_INCLUDES)" \
+ "MY_DEFINES=$(PttDxeLib_DEFINES)"\
+ LIBRARY_NAME=$(BUILD_DIR)\PttDxeLibrary.lib\
+ TYPE=LIBRARY \
+
+$(BUILD_DIR)\PttPeiLibrary.lib : PttPeiLib
+
+PttPeiLib : $(BUILD_DIR)\PttLibrary.mak PttPeiLibBin
+
+PttPeiLib_DEFINES=\
+ -D __EDKII_GLUE_BASE_LIB__ \
+ -D __EDKII_GLUE_UEFI_LIB__ \
+ -D __EDKII_GLUE_BASE_MEMORY_LIB__ \
+ -D __EDKII_GLUE_BASE_IO_LIB_INTRINSIC__ \
+ -D __EDKII_GLUE_PEI_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D TIANO_RELEASE_VERSION=0x00080006\
+ -D PTT_FLAG
+
+PttPeiLib_LIBS=\
+ $(EdkIIGlueBaseLib_LIB)\
+ $(EdkIIGlueUefiLib_LIB)\
+ $(EdkIIGlueBaseMemoryLib_LIB)\
+ $(EdkIIGlueBaseIoLibIntrinsic_LIB)\
+ $(EdkIIGlueBaseTimerLibLocalApic_LIB)\
+ $(EdkIIGluePeiDebugLibReportStatusCode_LIB)\
+
+PttPeiLibBin : $(PttPeiLib_LIBS)
+!IF "$(x64_BUILD)"=="1"
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) BUILD_DIR=$(BUILD_DIR)\IA32\
+!ELSE
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS)\
+!ENDIF
+ MAKEFILE=$(BUILD_DIR)\PttLibrary.mak \
+ /f $(BUILD_DIR)\PttLibrary.mak all \
+ "MY_INCLUDES=$(PttDxeLib_INCLUDES)" \
+ "MY_DEFINES=$(PttPeiLib_DEFINES)"\
+ LIBRARY_NAME=$(BUILD_DIR)\PttPeiLibrary.lib\
+ TYPE=PEI_LIBRARY \
+
+
+#**********************************************************************
+#**********************************************************************
+#** **
+#** (C)Copyright 1985-2006, American Megatrends, Inc. **
+#** **
+#** All Rights Reserved. **
+#** **
+#** 6145-F Northbelt Pkwy, Norcross, GA 30071 **
+#** **
+#** Phone: (770)-246-8600 **
+#** **
+#**********************************************************************
+#**********************************************************************
diff --git a/ReferenceCode/ME/Library/Ptt/PttLibrary.sdl b/ReferenceCode/ME/Library/Ptt/PttLibrary.sdl
new file mode 100644
index 0000000..3dd234e
--- /dev/null
+++ b/ReferenceCode/ME/Library/Ptt/PttLibrary.sdl
@@ -0,0 +1,59 @@
+TOKEN
+ Name = "MePttLibrary_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable Me Kernel Library support in Project"
+End
+
+PATH
+ Name = "MePttLibrary_DIR"
+ Help = "Me Library file source directory"
+End
+
+ELINK
+ Name = "/I$(MePttLibrary_DIR)\Include"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MePttLibrary_DIR)\Pei"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(MePttLibrary_DIR)\Dxe"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
+
+MODULE
+ Help = "Includes PttLibrary.mak to Project"
+ File = "PttLibrary.mak"
+End
+
+ELINK
+ Name = "PttPei_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "PttDxe_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\PttPeiLibrary.lib"
+ Parent = "PttPei_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\PttDxeLibrary.lib"
+ Parent = "PttDxe_LIB"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.c b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.c
new file mode 100644
index 0000000..2e87dd6
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.c
@@ -0,0 +1,145 @@
+/** @file
+ Implements Platform Trust Technology (FTPM) HECI SkuMgr Interface Library.
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+
+**/
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#endif
+
+#ifdef PTT_FLAG
+#include "PttHeciLib.h"
+#include "HeciMsgLib.h"
+
+#define PTT_BITMASK 0x20000000 //BIT29
+
+#define CLEAR_PTT_BIT 0x00000000
+
+/**
+ Checks whether ME FW has the Platform Trust Technology capability.
+
+ @param[out] PttCapability TRUE if PTT is supported, FALSE othewrwise.
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+**/
+EFI_STATUS
+EFIAPI
+PttHeciGetCapability(
+ OUT BOOLEAN *PttCapability
+ )
+{
+ EFI_STATUS Status;
+ GEN_GET_FW_CAPSKU MsgGenGetFwCapsSku;
+ GEN_GET_FW_CAPS_SKU_ACK MsgGenGetFwCapsSkuAck;
+
+ *PttCapability = FALSE;
+
+ Status = HeciGetFwCapsSkuMsg (&MsgGenGetFwCapsSku, &MsgGenGetFwCapsSkuAck);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (((MsgGenGetFwCapsSkuAck.MKHIHeader.Fields.Command) == FWCAPS_GET_RULE_CMD) &&
+ ((MsgGenGetFwCapsSkuAck.MKHIHeader.Fields.IsResponse) == 1) &&
+ (MsgGenGetFwCapsSkuAck.MKHIHeader.Fields.Result == 0)
+ ) {
+
+ if (MsgGenGetFwCapsSkuAck.Data.FWCapSku.Fields.PTT) {
+ *PttCapability = TRUE;
+ }
+ }
+ DEBUG ((EFI_D_INFO, "PTT SkuMgr: PttCapability = %d\n", *PttCapability));
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Checks Platform Trust Technology enablement state.
+
+ @param[out] IsPttEnabledState TRUE if PTT is enabled, FALSE othewrwise.
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+**/
+EFI_STATUS
+EFIAPI
+PttHeciGetState(
+ OUT BOOLEAN *IsPttEnabledState
+ )
+{
+ EFI_STATUS Status;
+ MEFWCAPS_SKU CurrentFeatures;
+
+ *IsPttEnabledState = FALSE;
+
+ Status = HeciGetFwFeatureStateMsg (&CurrentFeatures);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ if (CurrentFeatures.Fields.PTT) {
+ *IsPttEnabledState = TRUE;
+ }
+
+ DEBUG ((EFI_D_INFO, "PTT SkuMgr: PttState = %d\n", *IsPttEnabledState));
+
+ return EFI_SUCCESS;
+}
+
+/**
+ Changes current Platform Trust Technology state.
+
+ @param[in] PttEnabledState TRUE to enable, FALSE to disable.
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+**/
+EFI_STATUS
+EFIAPI
+PttHeciSetState(
+ IN BOOLEAN PttEnabledState
+ )
+{
+ EFI_STATUS Status;
+ UINT32 EnableBitmap;
+ UINT32 DisableBitmap;
+
+ if (PttEnabledState) {
+ //
+ // Enable PTT
+ //
+ DEBUG ((EFI_D_INFO, "PTT SkuMgr: Enable PTT\n"));
+ EnableBitmap = PTT_BITMASK;
+ DisableBitmap = CLEAR_PTT_BIT;
+ } else {
+ //
+ // Disable PTT
+ //
+ DEBUG ((EFI_D_INFO, "PTT SkuMgr: Disable PTT\n"));
+ EnableBitmap = CLEAR_PTT_BIT;
+ DisableBitmap = PTT_BITMASK;
+ }
+ Status = HeciFwFeatureStateOverride (EnableBitmap, DisableBitmap);
+
+ return Status;
+}
+
+#endif // PTT_FLAG
diff --git a/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.cif b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.cif
new file mode 100644
index 0000000..60dd251
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.cif
@@ -0,0 +1,12 @@
+<component>
+ name = "PttHeciDxeLib"
+ category = ModulePart
+ LocalRoot = "ReferenceCode\Me\Library\PttHeci\Dxe\"
+ RefName = "PttHeciDxeLib"
+[files]
+"PttHeciDxeLib.sdl"
+"PttHeciDxeLib.mak"
+"PttHeciDxeLib.c"
+"PttHeciDxeLib.h"
+"PttHeciDxeLib.inf"
+<endComponent>
diff --git a/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.h b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.h
new file mode 100644
index 0000000..6b370f4
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.h
@@ -0,0 +1,37 @@
+/** @file
+ Platform Trust Technology (FTPM) HECI SkuMgr Dxe Library
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PTT_HECI_DXE_LIB_H_
+#define _PTT_HECI_DXE_LIB_H_
+
+#ifdef PTT_FLAG
+///
+/// External include files do NOT need to be explicitly specified in real EDKII
+/// environment
+///
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueDxe.h"
+#endif
+///
+/// Common header for HECI Library
+///
+#include "PttHeciLib.h"
+#endif // PTT_FLAG
+#endif
diff --git a/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.inf b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.inf
new file mode 100644
index 0000000..da2f485
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.inf
@@ -0,0 +1,68 @@
+## @file
+# Component description file for PTT Heci DXE Library.
+#
+#@copyright
+# Copyright (c) 2012 Intel Corporation. All rights reserved
+# This software and associated documentation (if any) is furnished
+# under a license and may only be used or copied in accordance
+# with the terms of the license. Except as permitted by such
+# license, no part of this software or documentation 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.
+#
+# This file contains a 'Sample Driver' and is licensed as such
+# under the terms of your license agreement with Intel or your
+# vendor. This file may be modified by the user, subject to
+# the additional terms of the license agreement
+#
+
+[defines]
+BASE_NAME = PttHeciDxeLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ PttHeciDxeLib.h
+ PttHeciDxeLib.c
+ ../Include/PttHeciLib.h
+
+[includes.common]
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/PttHeci/Include
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/include
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Dxe
+
+#
+# EDK II Glue Library utilizes some standard headers from EDK
+#
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+#
+# Typically the sample code referenced will be available in the code base already
+# So keep this include at the end to defer to the source base definition
+# and only use the sample code definition if source base does not include these files.
+#
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode
+ $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/SampleCode/Include
+
+[libraries.common]
+ EdkIIGlueBaseLib
+ EdkIIGlueUefiLib
+ EdkIIGlueDxeDebugLibReportStatusCode
+ MeLib
+
+[nmake.common]
+ C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_BASE_LIB__ \
+ -D __EDKII_GLUE_UEFI_LIB__ \
+ -D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ -D PTT_FLAG \ No newline at end of file
diff --git a/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.mak b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.mak
new file mode 100644
index 0000000..ed8afdd
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.mak
@@ -0,0 +1,40 @@
+all : PttHeciDxeLib
+
+$(BUILD_DIR)\PttHeciDxeLib.lib : PttHeciDxeLib
+
+PttHeciDxeLib : $(BUILD_DIR)\PttHeciDxeLib.mak PttHeciDxeLibBin
+
+$(BUILD_DIR)\PttHeciDxeLib.mak : $(PttHeciDxeLib_DIR)\$(@B).cif $(PttHeciDxeLib_DIR)\$(@B).mak $(BUILD_RULES)
+ $(CIF2MAK) $(PttHeciDxeLib_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS)
+
+PttHeciDxeLib_INCLUDES=\
+ $(EDK_INCLUDES) \
+ $(EdkIIGlueLib_INCLUDES) \
+ $(ME_INCLUDES) \
+ -I$(INTEL_COUGAR_POINT_DIR)\
+ $(INTEL_PCH_INCLUDES)
+
+PttHeciDxeLib_DEFINES=$(MY_DEFINES)\
+ /D __EDKII_GLUE_BASE_LIB__ \
+ /D __EDKII_GLUE_UEFI_LIB__ \
+ /D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \
+ /D PTT_FLAG
+
+PttHeciDxeLib_LIBS=\
+ $(EdkIIGlueBaseLib_LIB)\
+!IF "$(x64_BUILD)"=="1"
+ $(EdkIIGlueBaseLibX64_LIB)\
+!ELSE
+ $(EdkIIGlueBaseLibIA32_LIB)\
+!ENDIF
+ $(EdkIIGlueUefiLib_LIB)\
+ $(EdkIIGlueDxeDebugLibReportStatusCode_LIB)\
+ $(MeProtocolLib_LIB)\
+
+
+PttHeciDxeLibBin : $(PttHeciDxeLib_LIBS)
+ $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS) \
+ /f $(BUILD_DIR)\PttHeciDxeLib.mak all \
+ "MY_INCLUDES=$(PttHeciDxeLib_INCLUDES)" \
+ "MY_DEFINES=$(PttHeciDxeLib_DEFINES)"\
+ TYPE=LIBRARY \
diff --git a/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.sdl b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.sdl
new file mode 100644
index 0000000..8d6ba28
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Dxe/PttHeciDxeLib.sdl
@@ -0,0 +1,36 @@
+TOKEN
+ Name = "PttHeciDxeLib_SUPPORT"
+ Value = "1"
+ TokenType = Boolean
+ TargetEQU = Yes
+ TargetMAK = Yes
+ Master = Yes
+ Help = "Main switch to enable PttHeciDxeLib support in Project"
+End
+
+MODULE
+ Help = "Includes PttHeciDxeLib.mak to Project"
+ File = "PttHeciDxeLib.mak"
+End
+
+PATH
+ Name = "PttHeciDxeLib_DIR"
+ Help = "Me Library file source directory"
+End
+
+ELINK
+ Name = "PttHeciDxeLib_LIB"
+ InvokeOrder = ReplaceParent
+End
+
+ELINK
+ Name = "$(BUILD_DIR)\PttHeciDxeLib.lib"
+ Parent = "PttHeciDxeLib_LIB"
+ InvokeOrder = AfterParent
+End
+
+ELINK
+ Name = "/I$(PttHeciDxeLib_DIR)"
+ Parent = "ME_INCLUDES"
+ InvokeOrder = AfterParent
+End
diff --git a/ReferenceCode/ME/Library/PttHeci/Include/PttHeciLib.h b/ReferenceCode/ME/Library/PttHeci/Include/PttHeciLib.h
new file mode 100644
index 0000000..4b74795
--- /dev/null
+++ b/ReferenceCode/ME/Library/PttHeci/Include/PttHeciLib.h
@@ -0,0 +1,73 @@
+/** @file
+ Platform Trust Technology (FTPM) HECI SkuMgr Library
+
+@copyright
+ Copyright (c) 2012 Intel Corporation. All rights reserved
+ This software and associated documentation (if any) is furnished
+ under a license and may only be used or copied in accordance
+ with the terms of the license. Except as permitted by such
+ license, no part of this software or documentation 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.
+
+ This file contains an 'Intel Peripheral Driver' and uniquely
+ identified as "Intel Reference Module" and is
+ licensed for Intel CPUs and chipsets under the terms of your
+ license agreement with Intel or your vendor. This file may
+ be modified by the user, subject to additional terms of the
+ license agreement
+**/
+#ifndef _PTT_HECI_LIB_H_
+#define _PTT_HECI_LIB_H_
+
+#ifdef PTT_FLAG
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#endif
+
+/**
+ Checks whether ME FW has the Platform Trust Technology capability.
+
+ @param[out] PttCapability TRUE if PTT is supported, FALSE othewrwise.
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+**/
+EFI_STATUS
+EFIAPI
+PttHeciGetCapability(
+ OUT BOOLEAN *PttCapability
+ );
+
+/**
+ Checks Platform Trust Technology enablement state.
+
+ @param[out] IsPttEnabledState TRUE if PTT is enabled, FALSE othewrwise.
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+**/
+EFI_STATUS
+EFIAPI
+PttHeciGetState(
+ OUT BOOLEAN *IsPttEnabledState
+ );
+
+/**
+ Changes current Platform Trust Technology state.
+
+ @param[in] PttEnabledState TRUE to enable, FALSE to disable.
+
+ @retval EFI_SUCCESS Command succeeded
+ @retval EFI_DEVICE_ERROR HECI Device error, command aborts abnormally
+**/
+EFI_STATUS
+EFIAPI
+PttHeciSetState(
+ IN BOOLEAN PttEnabledState
+ );
+
+#endif // PTT_FLAG
+#endif