summaryrefslogtreecommitdiff
path: root/ReferenceCode/Haswell/Library/OverclockingLib
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/Haswell/Library/OverclockingLib
downloadzprj-master.tar.xz
init. 1AQQW051HEADmaster
Diffstat (limited to 'ReferenceCode/Haswell/Library/OverclockingLib')
-rw-r--r--ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLib.inf69
-rw-r--r--ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.c621
-rw-r--r--ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.h352
3 files changed, 1042 insertions, 0 deletions
diff --git a/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLib.inf b/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLib.inf
new file mode 100644
index 0000000..8c286ef
--- /dev/null
+++ b/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLib.inf
@@ -0,0 +1,69 @@
+## @file
+# Component description file for CPU PPI library.
+#
+#@copyright
+# Copyright (c) 2005 - 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
+#
+
+[defines]
+BASE_NAME = OverclockingLib
+COMPONENT_TYPE = LIBRARY
+
+[sources.common]
+ OverclockingLibrary.c
+ OverclockingLibrary.h
+
+[includes.common]
+ $(EDK_SOURCE)/Foundation/Efi
+ $(EDK_SOURCE)/Foundation/Include
+ $(EDK_SOURCE)/Foundation/Efi/Include
+ $(EDK_SOURCE)/Foundation/Framework/Include
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Include/Pei
+ $(EDK_SOURCE)/Foundation/Library/Pei/Include
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EFI_SOURCE)/$(PROJECT_CPU_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_CPU_ROOT)/Include
+ $(EFI_SOURCE)/$(PROJECT_CPU_ROOT)/Include/Library
+ $(EFI_SOURCE)/$(PROJECT_CPU_ROOT)/Library
+ $(EFI_SOURCE)/$(PROJECT_CPU_ROOT)/Library/CpuPlatformLib
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include
+ $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include/Library
+
+#
+# Edk II Glue Library, some hearder are included by R9 header so have to include
+#
+ $(EFI_SOURCE)
+ $(EFI_SOURCE)/Framework
+ $(EDK_SOURCE)/Foundation
+ $(EDK_SOURCE)/Foundation/Framework
+ $(EDK_SOURCE)/Foundation/Include/IndustryStandard
+ $(EDK_SOURCE)/Foundation/Core/Dxe
+ $(EDK_SOURCE)/Foundation/Include/Pei
+ $(EDK_SOURCE)/Foundation/Library/Dxe/Include
+ $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include
+
+[libraries.common]
+ CpuPlatformLib
+
+[nmake.common]
+C_STD_INCLUDE=
+
+
diff --git a/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.c b/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.c
new file mode 100644
index 0000000..e4576fc
--- /dev/null
+++ b/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.c
@@ -0,0 +1,621 @@
+/** @file
+ CPU Platform Lib implementation.
+
+@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
+
+**/
+#include "OverclockingLibrary.h"
+#include "CpuPlatformLibrary.h"
+
+EFI_STATUS
+EFIAPI
+GetVoltageFrequencyItem (
+ OUT VOLTAGE_FREQUENCY_ITEM *VfSettings,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Gets the Voltage and Frequency information for a given CPU domain
+
+ @param[OUT] *VfSettings
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ UINT16 TempVoltageTarget;
+ INT16 TempVoltageOffset;
+ OC_MAILBOX_ITEM VfMsg;
+
+ Status = EFI_SUCCESS;
+
+ ZeroMem(&VfMsg,sizeof(VfMsg));
+ ///
+ /// Convert v/f command to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_GET_VOLTAGE_FREQUENCY;
+
+ ConvertToMailboxFormat((VOID *)VfSettings, &VfMsg, CommandId);
+
+ ///
+ /// Read From the OC Library
+ ///
+ Status = MailboxRead(MAILBOX_TYPE_OC, VfMsg.Interface.InterfaceData, &VfMsg.Data, LibStatus);
+
+ ///
+ /// Copy mailbox data to VfSettings
+ ///
+ if ( (Status == EFI_SUCCESS) && (*LibStatus == OC_LIB_COMPLETION_CODE_SUCCESS)) {
+ VfSettings->VfSettings.MaxOcRatio = (UINT8) (VfMsg.Data & MAX_RATIO_MASK);
+ VfSettings->VfSettings.VoltageTargetMode = (UINT8) ( (VfMsg.Data & VOLTAGE_MODE_MASK) >> VOLTAGE_MODE_OFFSET);
+
+ TempVoltageTarget = (UINT16) (VfMsg.Data & VOLTAGE_TARGET_MASK) >> VOLTAGE_TARGET_OFFSET;
+ ConvertVoltageTarget(TempVoltageTarget, &VfSettings->VfSettings.VoltageTarget, CONVERT_TO_BINARY_MILLIVOLT);
+
+ TempVoltageOffset = (INT16)((VfMsg.Data & VOLTAGE_OFFSET_MASK) >> VOLTAGE_OFFSET_OFFSET);
+ ConvertVoltageOffset(TempVoltageOffset, &VfSettings->VfSettings.VoltageOffset, CONVERT_TO_BINARY_MILLIVOLT);
+ }
+
+ return Status;
+}
+
+EFI_STATUS
+EFIAPI
+SetVoltageFrequencyItem (
+ IN VOLTAGE_FREQUENCY_ITEM VfSettings,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Sets the Voltage and Frequency information for a given CPU domain
+
+ @param[IN] *VfSettings
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ OC_MAILBOX_ITEM VfMsg;
+
+ Status = EFI_SUCCESS;
+
+ ///
+ /// Convert v/f Commands to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_SET_VOLTAGE_FREQUENCY;
+ ConvertToMailboxFormat((VOID *)&VfSettings, &VfMsg, CommandId);
+
+ ///
+ /// Write the v/f Settings to the OC Mailbox
+ ///
+ Status = MailboxWrite(MAILBOX_TYPE_OC, VfMsg.Interface.InterfaceData, VfMsg.Data, LibStatus);
+
+ return Status;
+}
+
+EFI_STATUS
+EFIAPI
+GetFivrConfig (
+ OUT GLOBAL_CONFIG_ITEM *FivrConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Get the global FIVR Configuration information
+
+ @param[OUT] *FivrConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ OC_MAILBOX_ITEM FivrMsg;
+
+ Status = EFI_SUCCESS;
+ ZeroMem(&FivrMsg, sizeof(FivrMsg));
+
+ ///
+ /// Convert FIVR message to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_GET_GLOBAL_CONFIG;
+ ConvertToMailboxFormat((VOID *)FivrConfig, &FivrMsg, CommandId);
+
+ ///
+ /// Read From the OC Library
+ ///
+ Status = MailboxRead(MAILBOX_TYPE_OC, FivrMsg.Interface.InterfaceData, &FivrMsg.Data, LibStatus);
+
+ ///
+ /// Copy mailbox data to FivrConfig
+ ///
+ if ( (Status == EFI_SUCCESS) && (*LibStatus == OC_LIB_COMPLETION_CODE_SUCCESS)) {
+ FivrConfig->DisableFivrFaults = FivrMsg.Data & FIVR_FAULTS_MASK;
+ FivrConfig->DisableFivrEfficiency = (FivrMsg.Data & FIVR_EFFICIENCY_MASK) >> FIVR_EFFICIENCY_OFFSET;
+ }
+
+ return Status;
+}
+
+EFI_STATUS
+EFIAPI
+SetFivrConfig (
+ IN GLOBAL_CONFIG_ITEM FivrConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Set the Global FIVR Configuration information
+
+ @param[IN] FivrConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ OC_MAILBOX_ITEM FivrMsg;
+
+ Status = EFI_SUCCESS;
+
+ ///
+ /// Convert FIVR Command to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_SET_GLOBAL_CONFIG;
+ ConvertToMailboxFormat((VOID *)&FivrConfig, &FivrMsg, CommandId);
+
+ ///
+ /// Write the FIVR Settings to the OC Mailbox
+ ///
+ Status = MailboxWrite(MAILBOX_TYPE_OC, FivrMsg.Interface.InterfaceData, FivrMsg.Data, LibStatus);
+
+ return Status;
+
+}
+
+EFI_STATUS
+EFIAPI
+GetSvidConfig (
+ OUT SVID_CONFIG_ITEM *SvidConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Get the SVID Configuration information
+
+ @param[OUT] *SvidConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ OC_MAILBOX_ITEM SvidMsg;
+
+ Status = EFI_SUCCESS;
+ ZeroMem(&SvidMsg, sizeof(SvidMsg));
+
+ ///
+ /// Convert SVID message to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_GET_SVID_CONFIG;
+ ConvertToMailboxFormat((VOID *)SvidConfig, &SvidMsg, CommandId);
+
+ ///
+ /// Read From the OC Library
+ ///
+ Status = MailboxRead(MAILBOX_TYPE_OC, SvidMsg.Interface.InterfaceData, &SvidMsg.Data, LibStatus);
+
+ ///
+ /// Copy mailbox data to SvidConfig
+ ///
+ if ( (Status == EFI_SUCCESS) && (*LibStatus == OC_LIB_COMPLETION_CODE_SUCCESS)) {
+ SvidConfig->VoltageTarget = (UINT16) SvidMsg.Data & SVID_VOLTAGE_MASK;
+ SvidConfig->SvidDisable = (UINT8) ((SvidMsg.Data & SVID_DISABLE_MASK) >> SVID_DISABLE_OFFSET);
+ }
+
+ return Status;
+}
+
+EFI_STATUS
+EFIAPI
+SetSvidConfig (
+ IN SVID_CONFIG_ITEM SvidConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Set the SVID Configuration information
+
+ @param[IN] SvidConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ OC_MAILBOX_ITEM SvidMsg;
+
+ Status = EFI_SUCCESS;
+
+ ///
+ /// Convert SVID Commands to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_SET_SVID_CONFIG;
+ ConvertToMailboxFormat((VOID *)&SvidConfig, &SvidMsg, CommandId);
+
+ ///
+ /// Write the Svid Settings to the OC Mailbox
+ ///
+ Status = MailboxWrite(MAILBOX_TYPE_OC, SvidMsg.Interface.InterfaceData, SvidMsg.Data, LibStatus);
+
+ return Status;
+}
+
+EFI_STATUS
+EFIAPI
+GetOcCapabilities (
+ OUT OC_CAPABILITIES_ITEM *OcCapabilities,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Get the overclocking capabilities for a given CPU Domain
+
+ @param[OUT] *OcCapabilities
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+{
+ EFI_STATUS Status;
+ UINT32 CommandId;
+ OC_MAILBOX_ITEM OcCapsMsg;
+
+ Status = EFI_SUCCESS;
+
+ ZeroMem(&OcCapsMsg,sizeof(OC_MAILBOX_ITEM));
+
+ ///
+ /// Convert OC capabilties message to Mailbox command format
+ ///
+ CommandId = OC_LIB_CMD_GET_OC_CAPABILITIES;
+ ConvertToMailboxFormat((VOID *)OcCapabilities, &OcCapsMsg, CommandId);
+
+ ///
+ /// Read From the OC Library
+ ///
+ Status = MailboxRead(MAILBOX_TYPE_OC, OcCapsMsg.Interface.InterfaceData, &OcCapsMsg.Data, LibStatus);
+
+ ///
+ /// Copy mailbox data to OC Capabilities structure
+ ///
+ if ( (Status == EFI_SUCCESS) && (*LibStatus == OC_LIB_COMPLETION_CODE_SUCCESS)) {
+ OcCapabilities->MaxOcRatioLimit =
+ (UINT8) OcCapsMsg.Data & OC_CAPS_MAX_RATIO_MASK;
+
+ OcCapabilities->RatioOcSupported =
+ (UINT8) ((OcCapsMsg.Data & OC_CAPS_RATIO_SUPPORT_MASK) >> OC_CAPS_RATIO_SUPPORT_OFFSET);
+
+ OcCapabilities->VoltageOverridesSupported =
+ (UINT8) ((OcCapsMsg.Data & OC_CAPS_OVERRIDE_SUPPORT_MASK) >> OC_CAPS_OVERRIDE_SUPPORT_OFFSET);
+
+ OcCapabilities->VoltageOffsetSupported =
+ (UINT8) ((OcCapsMsg.Data & OC_CAPS_OFFSET_SUPPORT_MASK) >> OC_CAPS_OFFSET_SUPPORT_OFFSET);
+ }
+
+ return Status;
+}
+
+VOID
+ConvertVoltageTarget (
+ IN UINT16 InputVoltageTarget,
+ OUT UINT16 *OutputVoltageTarget,
+ IN UINT8 ConversionType
+ )
+/**
+ Converts the input voltage target to the fixed point U12.2.10 Volt format or
+ the Binary millivolts representation based on the ConversionType
+
+@param[IN] InputVoltageTarget
+@param[OUT] *OutputVoltageTarget
+@param[IN] ConversionType - 0:fixed point, 1:Binary millivolts
+**/
+{
+UINT32 Remainder;
+ /// Fixed point representation:
+ ///
+ /// U12.2.10V format
+ /// | | | |
+ /// | | | v
+ /// | | v Exponent
+ /// | v Significand Size
+ /// v Size
+ /// Signed/Unsigned
+ ///
+ /// Float Value = Significand x (Base ^ Exponent)
+ /// (Base ^ Exponent) = 2 ^ 10 = 1024
+ ///
+ Remainder = 0;
+
+ if (InputVoltageTarget == 0) {
+ *OutputVoltageTarget = 0;
+ return;
+ }
+
+ if (ConversionType == CONVERT_TO_FIXED_POINT_VOLTS) {
+ ///
+ /// Input Voltage is in number of millivolts. Clip the input Voltage
+ /// to the max allowed by the fixed point format
+ ///
+ if (InputVoltageTarget > MAX_TARGET_MV)
+ InputVoltageTarget = MAX_TARGET_MV;
+
+ ///
+ /// InputTargetVoltage is the significand in mV. Need to convert to Volts
+ ///
+ *OutputVoltageTarget = (UINT16) DivU64x32Remainder (
+ (UINT64) (InputVoltageTarget * 1024), MILLIVOLTS_PER_VOLT,&Remainder);
+
+ if (Remainder >= 500) {
+ *OutputVoltageTarget += 1;
+ }
+ } else if (ConversionType == CONVERT_TO_BINARY_MILLIVOLT) {
+ ///
+ /// InputVoltage is specified in fixed point representation, need to
+ /// convert to millivolts
+ ///
+ *OutputVoltageTarget = (UINT16) DivU64x32Remainder (
+ (UINT64) (InputVoltageTarget * MILLIVOLTS_PER_VOLT), 1024,&Remainder);
+
+ if (Remainder >= 500) {
+ *OutputVoltageTarget += 1;
+ }
+ }
+
+ return;
+}
+
+VOID
+ConvertVoltageOffset (
+ IN INT16 InputVoltageOffset,
+ OUT INT16 *OutputVoltageOffset,
+ IN UINT8 ConversionType
+ )
+/**
+ Converts the input votlage Offset to the fixed point S11.0.10 Volt format or
+ to Binary illivolts representation based on the ConversionType.
+
+@param[IN] InputVoltageTarget
+@param[OUT] *OutputVoltageTarget
+@param[IN] ConversionType - 0:fixed point, 1:Signed Binary millivolts
+**/
+{
+ BOOLEAN NumIsNegative;
+ UINT32 Remainder;
+ /// Fixed point representation:
+ ///
+ /// S11.0.10V format
+ /// | | | |
+ /// | | | v
+ /// | | v Exponent
+ /// | v Significand Size
+ /// v Size
+ /// Signed/Unsigned
+ ///
+ /// Float Value = Significand x (Base ^ Exponent)
+ /// (Base ^ Exponent) = 2 ^ 10 = 1024
+ ///
+ *OutputVoltageOffset = 0;
+ NumIsNegative = FALSE;
+ Remainder = 0;
+
+ if (InputVoltageOffset == 0) {
+ *OutputVoltageOffset = 0;
+ return;
+ }
+
+ if (ConversionType == CONVERT_TO_FIXED_POINT_VOLTS) {
+ ///
+ /// Input Voltage is in INT16 representation. Check if numenr is negative
+ ///
+ if ( (InputVoltageOffset & INT16_SIGN_BIT_MASK) != 0) {
+ NumIsNegative = TRUE;
+ ///
+ /// Need to 2's complement adjust to make this number positive for
+ /// voltage calculation
+ ///
+ InputVoltageOffset = (~InputVoltageOffset+1) & (INT16_SIGN_BIT_MASK -1);
+ }
+
+ ///
+ /// Clip the input Voltage Offset to 500mv
+ ///
+ if (InputVoltageOffset > MAX_OFFSET_MV) {
+ InputVoltageOffset = MAX_OFFSET_MV;
+ }
+
+ ///
+ /// Convert to fixed point representation
+ ///
+ *OutputVoltageOffset = (UINT16) DivU64x32Remainder (
+ (UINT64) (InputVoltageOffset * 1024), MILLIVOLTS_PER_VOLT,&Remainder);
+
+ if (Remainder >= 500) {
+ *OutputVoltageOffset += 1;
+ }
+
+ if (NumIsNegative) {
+ /// 2's complement back to a negative number
+ *OutputVoltageOffset = ~(*OutputVoltageOffset) + 1;
+ }
+ } else if (ConversionType == CONVERT_TO_BINARY_MILLIVOLT) {
+ ///
+ /// Input Voltage is in fixed point representation. Check if number negative
+ ///
+ if ( (InputVoltageOffset & FIXED_POINT_SIGN_BIT_MASK)!= 0) {
+ NumIsNegative = TRUE;
+ ///
+ /// Need to 2's complement adjust to make this number positive for
+ /// voltage calculation
+ ///
+ InputVoltageOffset = (~InputVoltageOffset+1) & (FIXED_POINT_SIGN_BIT_MASK -1);
+ }
+
+ ///
+ /// Convert to INT16 representation in millivolts
+ ///
+ *OutputVoltageOffset = (UINT16) DivU64x32Remainder (
+ (UINT64) (InputVoltageOffset * MILLIVOLTS_PER_VOLT), 1024,&Remainder);
+
+ if (Remainder >= 500) {
+ *OutputVoltageOffset += 1;
+ }
+
+ if (NumIsNegative) {
+ /// 2's complement back to a negative number
+ *OutputVoltageOffset = ~(*OutputVoltageOffset) + 1;
+ }
+ }
+
+ return;
+}
+
+VOID
+ConvertToMailboxFormat (
+ IN VOID *InputData,
+ OUT OC_MAILBOX_ITEM *MailboxData,
+ IN UINT32 CommandId
+ )
+/**
+ Converts the input data to valid mailbox command format based on CommandID
+
+@param[IN] InputData
+@param[OUT] *MailboxData
+@param[IN] CommandId
+**/
+{
+ VOLTAGE_FREQUENCY_ITEM *VfItem;
+ SVID_CONFIG_ITEM *SvidItem;
+ OC_CAPABILITIES_ITEM *OcCapItem;
+ CORE_RATIO_LIMITS_ITEM *CoreRatioItem;
+ GLOBAL_CONFIG_ITEM *GlobalConfigItem;
+ VF_MAILBOX_COMMAND_DATA VfMailboxCommandData;
+ UINT16 TempVoltage;
+
+ ///
+ /// Initialize local varaibles and mailbox data
+ ///
+ ZeroMem ((UINT32 *)MailboxData, sizeof(OC_MAILBOX_ITEM));
+
+ ///
+ /// Then make a decision based on CommandId how to format
+ ///
+ switch (CommandId) {
+ case OC_LIB_CMD_GET_OC_CAPABILITIES:
+ OcCapItem = (OC_CAPABILITIES_ITEM *) InputData;
+ ///
+ /// OC Capabilities are returned on a per domain basis
+ ///
+ MailboxData->Data = 0;
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_GET_OC_CAPABILITIES;
+ MailboxData->Interface.Fields.Param1 = OcCapItem->DomainId;
+ break;
+
+ case OC_LIB_CMD_GET_PER_CORE_RATIO_LIMIT:
+ CoreRatioItem = (CORE_RATIO_LIMITS_ITEM *) InputData;
+ ///
+ /// Core Ratio Limits are only valid in the IA Core domain
+ ///
+ MailboxData->Data = 0;
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_GET_PER_CORE_RATIO_LIMIT;
+ MailboxData->Interface.Fields.Param1 = OC_LIB_DOMAIN_ID_IA_CORE;
+ MailboxData->Interface.Fields.Param2 = CoreRatioItem->Index;
+ break;
+
+ case OC_LIB_CMD_GET_VOLTAGE_FREQUENCY:
+ VfItem = (VOLTAGE_FREQUENCY_ITEM *) InputData;
+ ///
+ /// Voltage Frequency Settings are on a per domain basis
+ ///
+ MailboxData->Data = 0;
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_GET_VOLTAGE_FREQUENCY;
+ MailboxData->Interface.Fields.Param1 = VfItem->DomainId;
+ break;
+
+ case OC_LIB_CMD_SET_VOLTAGE_FREQUENCY:
+ VfItem = (VOLTAGE_FREQUENCY_ITEM *) InputData;
+ ///
+ /// Voltages are stored in a fixed point format
+ ///
+ VfMailboxCommandData.MaxOcRatio = VfItem->VfSettings.MaxOcRatio;
+
+ TempVoltage = 0;
+ ConvertVoltageTarget(VfItem->VfSettings.VoltageTarget, &TempVoltage, CONVERT_TO_FIXED_POINT_VOLTS);
+ VfMailboxCommandData.VoltageTargetU12 = TempVoltage;
+
+ VfMailboxCommandData.TargetMode = VfItem->VfSettings.VoltageTargetMode;
+
+ TempVoltage = 0;
+ ConvertVoltageOffset(VfItem->VfSettings.VoltageOffset, (INT16 *) &TempVoltage, CONVERT_TO_FIXED_POINT_VOLTS);
+ VfMailboxCommandData.VoltageOffsetS11 = TempVoltage;
+
+ CopyMem(&MailboxData->Data, &VfMailboxCommandData, sizeof(VfMailboxCommandData));
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_SET_VOLTAGE_FREQUENCY;
+ MailboxData->Interface.Fields.Param1 = VfItem->DomainId;
+ break;
+
+ case OC_LIB_CMD_GET_SVID_CONFIG:
+ MailboxData->Data = 0;
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_GET_SVID_CONFIG;
+ MailboxData->Interface.Fields.Param1 = 0;
+ break;
+
+ case OC_LIB_CMD_SET_SVID_CONFIG:
+ SvidItem = (SVID_CONFIG_ITEM *) InputData;
+ ConvertVoltageTarget(SvidItem->VoltageTarget, &TempVoltage, CONVERT_TO_FIXED_POINT_VOLTS);
+ MailboxData->Data = TempVoltage | (SvidItem->SvidDisable << SVID_DISABLE_OFFSET);
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_SET_SVID_CONFIG;
+ MailboxData->Interface.Fields.Param1 = 0;
+ break;
+
+ case OC_LIB_CMD_GET_GLOBAL_CONFIG:
+ MailboxData->Data = 0;
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_GET_GLOBAL_CONFIG;
+ MailboxData->Interface.Fields.Param1 = 0;
+ break;
+
+ case OC_LIB_CMD_SET_GLOBAL_CONFIG:
+ GlobalConfigItem = (GLOBAL_CONFIG_ITEM *) InputData;
+ MailboxData->Data =
+ (GlobalConfigItem->DisableFivrFaults & BIT0_MASK) |
+ ((GlobalConfigItem->DisableFivrEfficiency & BIT0_MASK) << FIVR_EFFICIENCY_OFFSET);
+ MailboxData->Interface.Fields.CommandCompletion = OC_LIB_CMD_SET_GLOBAL_CONFIG;
+ MailboxData->Interface.Fields.Param1 = 0;
+ break;
+
+ default:
+ DEBUG ((EFI_D_ERROR, "(OC MAILBOX) Unknown Command ID\n"));
+
+ break;
+
+ }
+
+}
+
diff --git a/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.h b/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.h
new file mode 100644
index 0000000..fd32d1f
--- /dev/null
+++ b/ReferenceCode/Haswell/Library/OverclockingLib/OverclockingLibrary.h
@@ -0,0 +1,352 @@
+/** @file
+ Header file for Cpu Platform Lib implementation.
+
+@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
+**/
+#ifndef _OVERCLOCKING_LIBRARY_H_
+#define _OVERCLOCKING_LIBRARY_H_
+
+#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000)
+#include "EdkIIGlueBase.h"
+#endif
+
+//
+// OC Mailbox MSR
+//
+#define MSR_OC_MAILBOX 0x00000150
+#define OC_LIB_WAIT_TIMEOUT 5000 ///< 5 milliseconds
+
+//
+// OC Mailbox commands
+//
+#define OC_LIB_CMD_GET_OC_CAPABILITIES 0x01
+#define OC_LIB_CMD_GET_PER_CORE_RATIO_LIMIT 0x02
+#define OC_LIB_CMD_GET_VOLTAGE_FREQUENCY 0x10
+#define OC_LIB_CMD_SET_VOLTAGE_FREQUENCY 0x11
+#define OC_LIB_CMD_GET_SVID_CONFIG 0x12
+#define OC_LIB_CMD_SET_SVID_CONFIG 0x13
+#define OC_LIB_CMD_GET_GLOBAL_CONFIG 0x14
+#define OC_LIB_CMD_SET_GLOBAL_CONFIG 0x15
+
+//
+// OC Mailbox completion codes
+//
+#define OC_LIB_COMPLETION_CODE_SUCCESS 0x00
+#define OC_LIB_COMPLETION_CODE_OC_LOCKED 0x01
+#define OC_LIB_COMPLETION_CODE_INVALID_DOMAIN 0x02
+#define OC_LIB_COMPLETION_CODE_MAX_RATIO_EXCEEDED 0x03
+#define OC_LIB_COMPLETION_CODE_MAX_VOLTAGE_EXCEEDED 0x04
+#define OC_LIB_COMPLETION_CODE_OC_NOT_SUPPORTED 0x05
+#define OC_LIB_COMPLETION_CODE_WRITE_FAILED 0x06
+#define OC_LIB_COMPLETION_CODE_READ_FAILED 0x07
+
+//
+// Domain ID definitions
+//
+#define OC_LIB_DOMAIN_ID_IA_CORE 0x00
+#define OC_LIB_DOMAIN_ID_GT 0x01
+#define OC_LIB_DOMAIN_ID_CLR 0x02
+#define OC_LIB_DOMAIN_ID_UNCORE 0x03
+#define OC_LIB_DOMAIN_ID_IOA 0x04
+#define OC_LIB_DOMAIN_ID_IOD 0x05
+
+//
+// Bit 10 is the S11.0.10V sign bit
+//
+#define FIXED_POINT_SIGN_BIT_MASK 0x0400
+#define INT16_SIGN_BIT_MASK 0x8000
+
+//
+// Voltage Conversion defines
+//
+#define MILLIVOLTS_PER_VOLT 1000
+#define MAX_TARGET_MV 4095
+#define MAX_OFFSET_MV 500
+
+#define CONVERT_TO_FIXED_POINT_VOLTS 0
+#define CONVERT_TO_BINARY_MILLIVOLT 1
+
+//
+// Masks and offsets
+//
+#define BIT0_MASK 0x1
+#define MAX_RATIO_MASK 0x000000FF
+#define VOLTAGE_TARGET_MASK 0x000FFF00
+#define VOLTAGE_TARGET_OFFSET 8
+#define VOLTAGE_MODE_MASK 0x00100000
+#define VOLTAGE_MODE_OFFSET 20
+#define VOLTAGE_OFFSET_MASK 0xFFE00000
+#define VOLTAGE_OFFSET_OFFSET 21
+
+#define SVID_DISABLE_MASK 0x80000000
+#define SVID_DISABLE_OFFSET 31
+#define SVID_VOLTAGE_MASK 0x00000FFF
+
+#define FIVR_FAULTS_MASK 0x00000001
+#define FIVR_EFFICIENCY_MASK 0x00000002
+#define FIVR_EFFICIENCY_OFFSET 1
+
+#define OC_CAPS_MAX_RATIO_MASK 0x000000FF
+#define OC_CAPS_RATIO_SUPPORT_MASK 0x00000100
+#define OC_CAPS_RATIO_SUPPORT_OFFSET 8
+#define OC_CAPS_OVERRIDE_SUPPORT_MASK 0x00000200
+#define OC_CAPS_OVERRIDE_SUPPORT_OFFSET 9
+#define OC_CAPS_OFFSET_SUPPORT_MASK 0x00000400
+#define OC_CAPS_OFFSET_SUPPORT_OFFSET 10
+
+//
+// Voltage offset definitions
+//
+#define OC_LIB_OFFSET_ADAPTIVE 0
+#define OC_LIB_OFFSET_OVERRIDE 1
+#define OC_LIB_VOLTAGE_DO_NOT_UPDATE 0xFFFF
+
+///
+/// OC Library structures
+///
+typedef struct {
+ UINT32 CommandData;
+ UINT8 CommandCompletion : 8;
+ UINT8 Param1 : 8;
+ UINT8 Param2 : 8;
+ UINT8 Reserved : 7;
+ UINT8 RunBusy : 1;
+} OC_LIBRARY_COMMAND;
+
+typedef union _OC_MAILBOX_COMMAND {
+ UINT32 InterfaceData;
+ struct {
+ UINT8 CommandCompletion : 8;
+ UINT8 Param1 : 8;
+ UINT8 Param2 : 8;
+ UINT8 Reserved : 7;
+ UINT8 RunBusy : 1;
+ } Fields;
+} OC_MAILBOX_COMMAND;
+
+typedef struct _OC_MAILBOX_ITEM {
+ UINT32 Data;
+ OC_MAILBOX_COMMAND Interface;
+} OC_MAILBOX_ITEM;
+
+typedef struct {
+ UINT8 MaxOcRatio;
+ UINT8 VoltageTargetMode;
+ UINT16 VoltageTarget;
+ INT16 VoltageOffset;
+} VOLTAGE_FREQUENCY_SETTINGS;
+
+typedef struct {
+ VOLTAGE_FREQUENCY_SETTINGS VfSettings;
+ UINT8 DomainId;
+} VOLTAGE_FREQUENCY_ITEM;
+
+typedef enum {
+ IaCore,
+ Gt,
+ Clr,
+ Uncore
+} CPU_DOMAIN_ID;
+
+typedef struct {
+ UINT16 VoltageTarget;
+ BOOLEAN SvidDisable;
+} SVID_CONFIG_ITEM;
+
+typedef struct {
+ UINT8 MaxOcRatioLimit;
+ BOOLEAN RatioOcSupported;
+ BOOLEAN VoltageOverridesSupported;
+ BOOLEAN VoltageOffsetSupported;
+ UINT8 DomainId;
+} OC_CAPABILITIES_ITEM;
+
+typedef struct {
+ UINT8 MaxOcRatioLimit1C;
+ UINT8 MaxOcRatioLimit2C;
+ UINT8 MaxOcRatioLimit3C;
+ UINT8 MaxOcRatioLimit4C;
+ UINT8 Index;
+} CORE_RATIO_LIMITS_ITEM;
+
+typedef struct {
+ UINT8 DisableFivrFaults;
+ UINT8 DisableFivrEfficiency;
+} GLOBAL_CONFIG_ITEM;
+
+typedef struct {
+ UINT32 MaxOcRatio : 8;
+ UINT32 VoltageTargetU12 : 12;
+ UINT32 TargetMode : 1;
+ UINT32 VoltageOffsetS11 : 11;
+} VF_MAILBOX_COMMAND_DATA;
+
+///
+/// OC Library Function Prototypes
+///
+EFI_STATUS
+EFIAPI GetVoltageFrequencyItem (
+ OUT VOLTAGE_FREQUENCY_ITEM *VfSettings,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Gets the Voltage and Frequency information for a given CPU domain
+
+ @param[OUT] *VfSettings
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+EFI_STATUS
+EFIAPI SetVoltageFrequencyItem (
+ IN VOLTAGE_FREQUENCY_ITEM VfSettings,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Sets the Voltage and Frequency information for a given CPU domain
+
+ @param[IN] *VfSettings
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+EFI_STATUS
+EFIAPI GetFivrConfig (
+ OUT GLOBAL_CONFIG_ITEM *FivrConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Get the global FIVR Configuration information
+
+ @param[OUT] *FivrConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+EFI_STATUS
+EFIAPI SetFivrConfig (
+ IN GLOBAL_CONFIG_ITEM FivrConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Set the Global FIVR Configuration information
+
+ @param[IN] FivrConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+EFI_STATUS
+EFIAPI GetSvidConfig (
+ OUT SVID_CONFIG_ITEM *SvidConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Get the SVID Configuration information
+
+ @param[OUT] *SvidConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+EFI_STATUS
+EFIAPI SetSvidConfig (
+ IN SVID_CONFIG_ITEM SvidConfig,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Set the SVID Configuration information
+
+ @param[IN] SvidConfig
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+EFI_STATUS
+EFIAPI GetOcCapabilities (
+ OUT OC_CAPABILITIES_ITEM *OcCapabilities,
+ OUT UINT32 *LibStatus
+ )
+/**
+ Get the overclocking capabilities for a given CPU Domain
+
+ @param[OUT] *OcCapabilities
+ @param[OUT] *LibStatus
+
+ @retval EFI_STATUS
+**/
+;
+
+VOID
+ConvertVoltageTarget (
+ IN UINT16 InputVoltageTarget,
+ OUT UINT16 *OutputVoltageTarget,
+ IN UINT8 ConversionType
+ )
+/**
+ Converts the input voltage target to the fixed point U12.2.10 Volt format or
+ the Binary millivolts representation based on the ConversionType
+
+@param[IN] InputVoltageTarget
+@param[OUT] *OutputVoltageTarget
+@param[IN] ConversionType - 0:fixed point, 1:Binary millivolts
+**/
+;
+
+VOID
+ConvertVoltageOffset (
+ IN INT16 InputVoltageOffset,
+ OUT INT16 *OutputVoltageOffset,
+ IN UINT8 ConversionType
+ )
+/**
+ Converts the input votlage Offset to the fixed point S11.0.10 Volt format or
+ to Binary illivolts representation based on the ConversionType.
+
+@param[IN] InputVoltageTarget
+@param[OUT] *OutputVoltageTarget
+@param[IN] ConversionType - 0:fixed point, 1:Signed Binary millivolts
+**/
+;
+
+VOID
+ConvertToMailboxFormat (
+ IN VOID *InputData,
+ OUT OC_MAILBOX_ITEM *MailboxData,
+ IN UINT32 CommandId
+ )
+/**
+ Converts the input data to valid mailbox command format based on CommandID
+
+@param[IN] InputData
+@param[OUT] *MailboxData
+@param[IN] CommandId
+**/
+;
+
+#endif