diff options
Diffstat (limited to 'Chipset/NB/SystemAgentWrap/UpdateMemoryRecord')
6 files changed, 2020 insertions, 0 deletions
diff --git a/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.c b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.c new file mode 100644 index 0000000..cd4a8f6 --- /dev/null +++ b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.c @@ -0,0 +1,1701 @@ +//************************************************************************* +//************************************************************************* +//** ** +//** (C)Copyright 1985-2011, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//************************************************************************* +//************************************************************************* + +//************************************************************************* +// $Header: /Alaska/Projects/Intel/Haswell/LynxPoint_SharkBay-DT_Crb_1AQQW/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.c 1 4/19/16 7:41a Chienhsieh $ +// +// $Revision: 1 $ +// +// $Date: 4/19/16 7:41a $ +//************************************************************************* +// Revision History +// ---------------- +// $Log: /Alaska/Projects/Intel/Haswell/LynxPoint_SharkBay-DT_Crb_1AQQW/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.c $ +// +// 1 4/19/16 7:41a Chienhsieh +// Update rev10. +// +// 10 12/21/15 5:58a Chienhsieh +// [TAG] EIP249553 +// [Category] Improvement +// [Description] SMBIOS Type17 memory speed report issue with Hawell +// (Sharkbay) platform +// [Files] UpdateMemoryRecord.c +// +// 9 8/23/13 2:59a Ireneyang +// [TAG] EIP126356 +// [Category] Improvement +// [Description] Change calucating method for Dimm Frequency. +// [Files] UpdateMemoryRecord.c; +// +// 8 7/31/13 3:38a Ireneyang +// [TAG] None +// [Category] Improvement +// [Description] Change token name REFERENCE_DDR_IO_BUS to DCLK_FREQUENCY. +// When it's 0, it would show DDR Frequency in SMBIOS +// (DCLK Frequency). +// When it's 1, it would show DDR IO Bus Clock in SMBIOS +// (QCLK Frequency). +// [Files] SystemAgentWrap.sdl; UpdateMemoryRecord.c; +// +// 7 6/26/13 10:00a Ireneyang +// [TAG] None +// [Category] Improvement +// [Description] According to SMBIOS spec, Set REFERENCE_DDR_IO_BUS token +// for choosing how to show DDR speed. +// [Files] SystemAgentWrap.sdl; UpdateMemoryRecord.c; +// +// 5 6/26/13 4:27a Ireneyang +// [TAG] None +// [Category] Improvement +// [Description] Rename NbSmbiosType17Voltage() to +// NbSmbiosType17VoltageAndSpeed(). +// [Files] UpdateMemoryRecord.c; +// +// 4 6/13/13 7:14a Ireneyang +// [TAG] EIP125449 +// [Category] Improvement +// [Description] Update XmpId for SMBIOS Spec 2.8.0. +// +// 3 6/07/13 8:13a Ireneyang +// [TAG] EIP125449 +// [Category] Improvement +// [Description] Update SMBIOS Spec 2.8.0. +// +// 2 1/28/13 2:58a Jeffch +// [TAG] None +// [Category] Improvement +// [Description] Update SMBIOS Spec 2.7.1. +// +// +// 1 2/08/12 4:37a Yurenlai +// Intel Haswell/NB eChipset initially releases. +// +//************************************************************************* +//<AMI_FHDR_START> +// +// Name: UpdateMemoryRecord.c +// +// Description: This file for update SMBIOS Type 16 ~19. +// +//<AMI_FHDR_END> +//********************************************************************** + +#include "UpdateMemoryRecord.h" + +#include <MemInfo\MemInfo.h> +#define __EFI__H__ +#ifndef GUID_VARIABLE_DEFINITION +#define GUID_VARIABLE_DECLARATION(Variable, Guid) extern EFI_GUID Variable +#else +#define GUID_VARIABLE_DECLARATION(Variable, Guid) GLOBAL_REMOVE_IF_UNREFERENCED EFI_GUID Variable=Guid +#endif +#include <Protocol\SmBus.h> + +#include <Protocol\SaPlatformPolicy\SaPlatformPolicy.h> + + +#define EFI_SMBIOS_BOARD_PROTOCOL_GUID \ + {0x903dd14, 0x2ca0, 0x458a, 0xb5, 0xeb, 0xc, 0xc, 0xa3, 0xd, 0x78, 0x5c} + +#define EFI_MEMORY_SUBCLASS_DRIVER_GUID \ + { 0x1767CEED, 0xDB82, 0x47cd, 0xBF, 0x2B, 0x68, 0x45, 0x8A, 0x8C, 0xCF, 0xFF } + + +EFI_GUID gEfiMemorySubClassDriverGuid = EFI_MEMORY_SUBCLASS_DRIVER_GUID; +EFI_GUID gEfiSmbiosBoardProtocolGuid = EFI_SMBIOS_BOARD_PROTOCOL_GUID; +EFI_GUID gEfiSmbiosUpdateDataProtocolGuid = EFI_SMBIOS_UPDATE_DATA_PROTOCOL_GUID; +EFI_GUID gDxePlatformSaPolicyGuid = DXE_PLATFORM_SA_POLICY_GUID; +EFI_GUID gMemInfoHobProtocolGuid = MEM_INFO_PROTOCOL_GUID; +EFI_GUID gEfiSmbusProtocolGuid = EFI_SMBUS_HC_PROTOCOL_GUID; + + +EFI_SMBIOS_UPDATE_DATA_PROTOCOL *gSBUpdate; +EFI_SMBIOS_PROTOCOL *gSmbiosProtocol; +MEM_INFO_PROTOCOL *gMemInfoHobProtocol = NULL; +EFI_SMBUS_HC_PROTOCOL *gSmbusProtocol = NULL; +DXE_PLATFORM_SA_POLICY_PROTOCOL *gDxePlatformSaPolicy = NULL; +static UINT8 DimmNumber = 0; +static UINT8 DimmSlot[4] = { DIMM1_SMBUS_ADDRESS, + DIMM2_SMBUS_ADDRESS, + DIMM3_SMBUS_ADDRESS, + DIMM4_SMBUS_ADDRESS + }; + +#define MRC_REF_CLOCK_133 (0) +#define MRC_REF_CLOCK_100 (1) +#define fNoInit (0) +#define f800 (800) +#define f1000 (1000) +#define f1067 (1067) +#define f1200 (1200) +#define f1333 (1333) +#define f1400 (1400) +#define f1600 (1600) +#define f1800 (1800) +#define f1867 (1867) +#define f2000 (2000) +#define f2133 (2133) +#define f2200 (2200) +#define f2400 (2400) +#define f2600 (2600) +#define f2667 (2667) +#define fUnSupport (0x7FFFFFFF) + +#define MRC_FREQUENCY_MTB_OFFSET 1000000 +#define MRC_FREQUENCY_FTB_OFFSET 1000 +#define MRC_DDR3_800_TCK_MIN 2500000 /// 1/(800/2) femtoseconds +#define MRC_DDR3_1000_TCK_MIN 2000000 /// 1/(1000/2) femtoseconds +#define MRC_DDR3_1067_TCK_MIN 1875000 /// 1/(1067/2) femtoseconds +#define MRC_DDR3_1200_TCK_MIN 1666666 /// 1/(1200/2) femtoseconds +#define MRC_DDR3_1333_TCK_MIN 1500000 /// 1/(1333/2) femtoseconds +#define MRC_DDR3_1400_TCK_MIN 1428571 /// 1/(1400/2) femtoseconds +#define MRC_DDR3_1600_TCK_MIN 1250000 /// 1/(1600/2) femtoseconds +#define MRC_DDR3_1800_TCK_MIN 1111111 /// 1/(1800/2) femtoseconds +#define MRC_DDR3_1867_TCK_MIN 1071428 /// 1/(1867/2) femtoseconds +#define MRC_DDR3_2000_TCK_MIN 1000000 /// 1/(2000/2) femtoseconds +#define MRC_DDR3_2133_TCK_MIN 937500 /// 1/(2133/2) femtoseconds +#define MRC_DDR3_2200_TCK_MIN 909090 /// 1/(2200/2) femtoseconds +#define MRC_DDR3_2400_TCK_MIN 833333 /// 1/(2400/2) femtoseconds +#define MRC_DDR3_2600_TCK_MIN 769230 /// 1/(2600/2) femtoseconds +#define MRC_DDR3_2667_TCK_MIN 750000 /// 1/(2667/2) femtoseconds +#define MRC_DDR3_2800_TCK_MIN 714285 /// 1/(2800/2) femtoseconds +#define TREFIMULTIPLIER 1000 /// tREFI value defined in XMP 1.3 spec is actually in thousands of MTB units. +#define MAX(a,b) (((a) > (b)) ? (a) : (b)) +#define MIN(a,b) (((a) < (b)) ? (a) : (b)) + +typedef struct { + UINT32 tCK; + UINT32 DDRFreq; + UINT8 RefClkFlag; // 0 = invalid freq. 1 = valid only at 133 RefClk, 2 = valid only at 100 RefClk, 3 = valid at both. +} NbTRangeTable; + +// Timing Range table +const NbTRangeTable NbRange[] = { + { 0xFFFFFFFF, fUnSupport, (0 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_800_TCK_MIN, f800, (1 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1000_TCK_MIN, f1000, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1067_TCK_MIN, f1067, (1 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1200_TCK_MIN, f1200, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1333_TCK_MIN, f1333, (1 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1400_TCK_MIN, f1400, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1600_TCK_MIN, f1600, (1 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1800_TCK_MIN, f1800, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_1867_TCK_MIN, f1867, (1 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_2000_TCK_MIN, f2000, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_2133_TCK_MIN, f2133, (1 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_2200_TCK_MIN, f2200, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_2400_TCK_MIN, f2400, (1 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_2600_TCK_MIN, f2600, (0 << MRC_REF_CLOCK_133) | (1 << MRC_REF_CLOCK_100) }, + { MRC_DDR3_2667_TCK_MIN, f2667, (1 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) }, + { 0, fNoInit, (0 << MRC_REF_CLOCK_133) | (0 << MRC_REF_CLOCK_100) } +}; + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: ReadSpdData +// +// Description: Returns the length of the Dimm Spd +// +// Input: UINT8 SpdSalveAddr, +// UINT8 Offset, +// UINTN Count, +// Output: UINT8 *Buffer +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +EFI_STATUS ReadSpdData ( + IN UINT8 SpdSalveAddr, + IN UINT8 Offset, + IN UINTN Count, + OUT UINT8 *Buffer + ) +{ + EFI_STATUS Status; + UINTN Index; + UINTN Length; + EFI_SMBUS_OPERATION Operation; + EFI_SMBUS_DEVICE_COMMAND Command; + EFI_SMBUS_DEVICE_ADDRESS SlaveAddress; + + if(gSmbusProtocol == NULL) return EFI_UNSUPPORTED; + + SlaveAddress.SmbusDeviceAddress = SpdSalveAddr >> 1; + + for (Index = 0; Index < Count; Index++) + { + Command = Offset + Index; + + Length = 1; + Operation = EfiSmbusReadByte; + Status = gSmbusProtocol->Execute (gSmbusProtocol, + SlaveAddress, + Command, + Operation, + FALSE, + &Length, + &Buffer[Index] ); + if (EFI_ERROR(Status)) return Status; + } + + return EFI_SUCCESS; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: NbGetDimmTCK +// +// Description: Returns the Dimm tCK Timing +// +// +// Input: UINT32 tCK +// +// Output: TRUE - Have tCK Timing +// FALSE - Not have tCK Timing +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> + +static BOOLEAN +NbGetDimmTCK ( + UINT8 SpdFtbDividend, + UINT8 SpdFtbDivisor, + UINT8 SpdMtbDividend, + UINT8 SpdMtbDivisor, + UINT8 tCKminMtb, +// UINT8 tCKminFine, // EIP249553 + INT8 tCKminFine, + OUT UINT32 *tCK + ) +{ + INT32 MediumTimebase = 0; + INT32 FineTimebase = 0; + + FineTimebase = (SpdFtbDivisor == 0) ? 0 : (SpdFtbDividend * MRC_FREQUENCY_FTB_OFFSET) / SpdFtbDivisor; + MediumTimebase = (SpdMtbDivisor == 0) ? 0 : (SpdMtbDividend * MRC_FREQUENCY_MTB_OFFSET) / SpdMtbDivisor; + *tCK = (MediumTimebase * tCKminMtb) + (FineTimebase * tCKminFine); + + return (MediumTimebase == 0) ? FALSE : TRUE; +} +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: NbGetDimmFrequency +// +// Description: Returns Dimm Frequency +// +// +// Input: UINT32 tCK +// +// Output: UINT32 XmpFrequency +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> + +static +UINT32 +NbGetDimmFrequency ( + IN UINT32 tCK + ) +{ + UINT32 Index; + UINT32 XmpFrequency = fNoInit; + UINT32 NbRangeSize = (sizeof (NbRange) / sizeof (NbTRangeTable)) - 1; + + if(tCK == 0 || tCK == 0xffffffff) return fNoInit; + + for (Index = 0; Index < NbRangeSize; Index++) { + if ((tCK <= NbRange[Index].tCK) && (tCK > NbRange[Index + 1].tCK)) { + XmpFrequency = NbRange[Index].DDRFreq; + break; + } + } + + while (Index) { + if ((NbRange[Index].RefClkFlag & (1 << gMemInfoHobProtocol->MemInfoData.RefClk)) == MRC_REF_CLOCK_133) { + XmpFrequency = NbRange[--Index].DDRFreq; + } else break; + } + + return XmpFrequency; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: NbSmbiosType17Voltage +// +// Description: To update MinimumVoltage, MaximumVoltage, ConfiguredVoltage +// and Dimm Frequency +// +// +// Input: SMBIOS_MEMORY_DEVICE_INFO *TypeBuffer +// +// Output: SMBIOS_MEMORY_DEVICE_INFO *TypeBuffer +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +EFI_STATUS NbSmbiosType17VoltageAndSpeed ( + IN OUT SMBIOS_MEMORY_DEVICE_INFO *TypeBuffer + ) +{ + UINT8 VoltageCap = 0; + UINT16 XmpId = 0; + UINT8 XmpProfileCap = 0; + UINT8 SpdFtbDividend = 0; + UINT8 SpdFtbDivisor = 0; + UINT8 SpdMtbDividend = 0; + UINT8 SpdMtbDivisor = 0; + UINT8 tCKminMtb = 0; +// UINT8 tCKminFine = 0; // EIP249553 + INT8 tCKminFine; + UINT32 tCK = 0; + UINT32 XmpProfile1Speed = 0; + UINT32 XmpProfile2Speed = 0; + UINT8 SpdData[18] = {6, 9, 10, 11, 12, 34, 176, 177, 178, 180, 181, 182, 183, 184, 186, 211, 221, 246}; + EFI_STATUS Status; + UINT8 i; + + // find DimmNumber + for ( ; DimmNumber < 4; DimmNumber++) { + if (DimmSlot[DimmNumber] != 0) break; + } + + if(gMemInfoHobProtocol != NULL) { + if (gMemInfoHobProtocol->MemInfoData.DimmExist[DimmNumber]) { // DIMM_PRESENT + for (i = 0; i < sizeof(SpdData) ; i++) { + // Get Spd data + Status = ReadSpdData(DimmSlot[DimmNumber], SpdData[i], 1, &SpdData[i]); + if (EFI_ERROR (Status)) { + // if memory down mode, use MemInfoHob + SpdData[i] = *(UINT8 *)(gMemInfoHobProtocol->MemInfoData.DimmsSpdData[DimmNumber] + SpdData[i]); + } + } + + XmpId = *(UINT16 *)&SpdData[6]; + + VoltageCap = SpdData[0]; + XmpProfileCap = SpdData[8]; + +#if defined AMI_SMBIOS_MODULE_VERSION && AMI_SMBIOS_MODULE_VERSION >= 105 + if (VoltageCap & 0x04) { // 1.25 v + TypeBuffer->MinimumVoltage = 1250; + } else if (VoltageCap & 0x02) { // 1.35 v + TypeBuffer->MinimumVoltage = 1350; + } else if (!(VoltageCap & 0x01)) { // 1.5 v bit0 = 0 + TypeBuffer->MinimumVoltage = 1500; + } + + if (!(VoltageCap & 0x01)) { // 1.5 v bit0 = 0 + TypeBuffer->MaximumVoltage = 1500; + } else if (VoltageCap & 0x02) { // 1.35 v + TypeBuffer->MaximumVoltage = 1350; + } else if (VoltageCap & 0x04) { // 1.25 v + TypeBuffer->MaximumVoltage = 1250; + } + + TypeBuffer->ConfiguredVoltage = gMemInfoHobProtocol->MemInfoData.VddVoltage[0]; +#endif + // Calculate Dimm STD Profile + SpdFtbDivisor = SpdData[1]; + SpdFtbDividend = (UINT8)(SpdFtbDivisor >> 4); + SpdFtbDivisor &= 0x0f; + SpdMtbDividend = SpdData[2]; + SpdMtbDivisor = SpdData[3]; + tCKminMtb = SpdData[4]; + tCKminFine = SpdData[5]; + // Get tCK Timing + if(NbGetDimmTCK(SpdFtbDividend, SpdFtbDivisor, SpdMtbDividend, SpdMtbDivisor, tCKminMtb, tCKminFine, &tCK)){ + // Get Dimm Frequency + TypeBuffer->Speed = NbGetDimmFrequency(tCK); + +#if defined DCLK_FREQUENCY && DCLK_FREQUENCY == 1 + // Get Dimm Frequency + if((NbGetDimmFrequency(tCK)%5) == 3) { + TypeBuffer->Speed = (NbGetDimmFrequency(tCK)/2)+1; + } else { + TypeBuffer->Speed = (NbGetDimmFrequency(tCK)/2); + } +#endif + } + + if(XmpId == 0x4A0C) { // is XMP + + // Calculate Dimm XMP Profile 1 + if (XmpProfileCap & 0x01) { + SpdFtbDivisor = SpdData[13]; + SpdFtbDividend = (UINT8)(SpdFtbDivisor >> 4); + SpdFtbDivisor &= 0x0f; + SpdMtbDividend = SpdData[9]; + SpdMtbDivisor = SpdData[10]; + tCKminMtb = SpdData[14]; + tCKminFine = SpdData[15]; + // Get tCK Timing + if(NbGetDimmTCK(SpdFtbDividend, SpdFtbDivisor, SpdMtbDividend, SpdMtbDivisor, tCKminMtb, tCKminFine, &tCK)){ + // Get Dimm Frequency + XmpProfile1Speed = NbGetDimmFrequency(tCK); + // Speed must MAX Speed. + TypeBuffer->Speed = MAX(TypeBuffer->Speed, XmpProfile1Speed); + +#if defined DCLK_FREQUENCY && DCLK_FREQUENCY == 1 + // Speed must MAX Speed. + TypeBuffer->Speed = MAX(TypeBuffer->Speed, ((XmpProfile1Speed/2)+1)); +#endif + } + } + + // Calculate Dimm XMP Profile 2 + if (XmpProfileCap & 0x02) { + SpdFtbDivisor = SpdData[13]; + SpdFtbDividend = (UINT8)(SpdFtbDivisor >> 4); + SpdFtbDivisor &= 0x0f; + SpdMtbDividend = SpdData[11]; + SpdMtbDivisor = SpdData[12]; + tCKminMtb = SpdData[16]; + tCKminFine = SpdData[17]; + // Get tCK Timing + if(NbGetDimmTCK(SpdFtbDividend, SpdFtbDivisor, SpdMtbDividend, SpdMtbDivisor, tCKminMtb, tCKminFine, &tCK)){ + // Get Dimm Frequency + XmpProfile2Speed = NbGetDimmFrequency(tCK); + // Speed must MAX Speed. + TypeBuffer->Speed = MAX(TypeBuffer->Speed, XmpProfile2Speed); + +#if defined DCLK_FREQUENCY && DCLK_FREQUENCY == 1 + // Speed must MAX Speed. + TypeBuffer->Speed = MAX(TypeBuffer->Speed, ((XmpProfile2Speed/2)+1)); +#endif + } + } + + } // if(XmpId == 0x4A0C) + } // if (gMemInfoHobProtocol.MemInfoData.DimmExist != DIMM_PRESENT) + } // if(gMemInfoHobProtocol != NULL) + + return EFI_SUCCESS; +}; + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: GetStructureLength +// +// Description: Returns the length of the structure pointed by BufferStart +// in bytes +// +// Input: UINT8 *BufferStart +// +// Output: Structure Size +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT16 +GetStructureLength( + IN UINT8 *BufferStart +) +{ + UINT8 *BufferEnd = BufferStart; + + BufferEnd += ((SMBIOS_STRUCTURE_HEADER*)BufferStart)->Length; + while (*(UINT16*)BufferEnd != 0) + { + BufferEnd++; + } + + return (UINT16)(BufferEnd + 2 - BufferStart); // +2 for double zero terminator +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: FindStructureType +// +// Description: Find structure type starting from memory location pointed by +// Buffer +// +// Input: UINT8 **Buffer +// UINT8 **StructureFoundPtr +// UINT8 SearchType +// UINT8 Instance +// +// Output: If SearchType is found: +// UINT8 **Buffer - Points to the next structure +// UINT8 **StructureFoundPtr - Points to the structure +// that was found +// If SearchType is not found: +// UINT8 **Buffer - No change +// UINT8 **StructureFoundPtr = NULL +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +BOOLEAN +FindStructureType( + IN OUT UINT8 **Buffer, + IN OUT UINT8 **StructureFoundPtr, + IN UINT8 SearchType, + IN UINT8 Instance // 1-based +) +{ + UINT8 *BufferPtr = *Buffer; + BOOLEAN FindStatus = FALSE; + + *StructureFoundPtr = NULL; + while (((SMBIOS_STRUCTURE_HEADER*)BufferPtr)->Type != 127) + { + if (((SMBIOS_STRUCTURE_HEADER*)BufferPtr)->Type == SearchType) + { + // If this instance, set the find status flag and update the Buffer pointer + if (--Instance == 0) + { + FindStatus = TRUE; + *StructureFoundPtr = BufferPtr; + *Buffer = BufferPtr + GetStructureLength(BufferPtr); + break; + } + } + BufferPtr += GetStructureLength(BufferPtr); + } + + if ((FindStatus == FALSE) & (SearchType == 127)) + { + FindStatus = TRUE; + *StructureFoundPtr = BufferPtr; + *Buffer = BufferPtr + GetStructureLength(BufferPtr); + } + + return FindStatus; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: BuildType16 +// +// Description: Build SMBIOS Type 16 +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, +// EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +// +// Output: +// None +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +BuildType16( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + IN EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +) +{ + SMBIOS_PHYSICAL_MEM_ARRAY_INFO *TypeBuffer; + UINT16 bsize; + + // Allocate temporary buffer + TypeBuffer = EfiLibAllocateZeroPool(sizeof(SMBIOS_PHYSICAL_MEM_ARRAY_INFO)+0x100); + + // Build header of structure + TypeBuffer->StructureType.Type = 16; // Type 16 + TypeBuffer->StructureType.Length = sizeof(SMBIOS_PHYSICAL_MEM_ARRAY_INFO); + TypeBuffer->StructureType.Handle = gSBUpdate->SMBIOS_GetFreeHandle(SmbiosBuffer); + + // Build Content of structure + TypeBuffer->Location = MemorySubClassData->ArrayLocationData.MemoryArrayLocation; + TypeBuffer->Use = MemorySubClassData->ArrayLocationData.MemoryArrayUse; + TypeBuffer->MemErrorCorrection = MemorySubClassData->ArrayLocationData.MemoryErrorCorrection; + TypeBuffer->MaxCapacity = MemorySubClassData->ArrayLocationData.MaximumMemoryCapacity; + if (TypeBuffer->MaxCapacity >= 0x80000000) + { + TypeBuffer->ExtMaxCapacity = TypeBuffer->MaxCapacity; + TypeBuffer->MaxCapacity = 0x80000000; + } + else + { + TypeBuffer->ExtMaxCapacity = 0; + } + + // + // Maximum memory supported by the memory controller + // 2 GB in terms of KB + // +#if MEMORY_ERROR_INFO + TypeBuffer->MemErrInfoHandle = SMBIOS_UNKNOW; +#else + TypeBuffer->MemErrInfoHandle = SMBIOS_NOT_PROVIDE; +#endif + TypeBuffer->NumberOfMemDev = MemorySubClassData->ArrayLocationData.NumberMemoryDevices; + + // Write structure To SMBIOS Buffer + bsize = SMBIOS_GetStructureTotalSize((UINT8 *)TypeBuffer); + gSBUpdate->SMBIOS_InsertStructure(SmbiosBuffer, (UINT8 *)TypeBuffer, bsize); + + // Fix handle link + SMBIOS_FixHandleLink(SmbiosBuffer); + + // Free temporary buffer + gBS->FreePool(TypeBuffer); +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: BuildType17 +// +// Description: Build SMBIOS Type 17 +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, +// EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +// +// Output: None +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +BuildType17( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + IN EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +) +{ + SMBIOS_MEMORY_DEVICE_INFO *TypeBuffer; + UINT16 bsize; + + // Allocate temporary buffer + TypeBuffer = EfiLibAllocateZeroPool(sizeof(SMBIOS_MEMORY_DEVICE_INFO)+0x100); + + // Build header of structure + TypeBuffer->StructureType.Type = 17; // Type 17 + TypeBuffer->StructureType.Length = sizeof(SMBIOS_MEMORY_DEVICE_INFO); + TypeBuffer->StructureType.Handle = gSBUpdate->SMBIOS_GetFreeHandle(SmbiosBuffer); + + // Build Content of structure + TypeBuffer->PhysicalMemArrayHandle = (UINT16)gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 16, 1); +#if MEMORY_ERROR_INFO + TypeBuffer->MemErrorInfoHandle = SMBIOS_UNKNOW; +#else + TypeBuffer->MemErrorInfoHandle = SMBIOS_NOT_PROVIDE; +#endif + TypeBuffer->TotalWidth = MemorySubClassData->ArrayLink.MemoryTotalWidth; + TypeBuffer->DataWidth = MemorySubClassData->ArrayLink.MemoryDataWidth; + TypeBuffer->Size = (UINT16) (RShiftU64 (MemorySubClassData->ArrayLink.MemoryDeviceSize, 20)); + TypeBuffer->FormFactor = MemorySubClassData->ArrayLink.MemoryFormFactor; + TypeBuffer->DeviceSet = MemorySubClassData->ArrayLink.MemoryDeviceSet; + TypeBuffer->DeviceLocator = TransferHiiStringToSmbios((UINT8 *)TypeBuffer, MemorySubClassData->ArrayLink.MemoryDeviceLocator); + TypeBuffer->BankLocator = TransferHiiStringToSmbios((UINT8 *)TypeBuffer, MemorySubClassData->ArrayLink.MemoryBankLocator); + TypeBuffer->MemoryType = MemorySubClassData->ArrayLink.MemoryType; + TypeBuffer->TypeDetail = *((UINT16*)(&(MemorySubClassData->ArrayLink.MemoryTypeDetail))); + TypeBuffer->Speed = 0; + TypeBuffer->Manufacturer = TransferHiiStringToSmbios((UINT8 *)TypeBuffer, MemorySubClassData->ArrayLink.MemoryManufacturer); + TypeBuffer->SerialNumber = TransferHiiStringToSmbios((UINT8 *)TypeBuffer, MemorySubClassData->ArrayLink.MemorySerialNumber); + TypeBuffer->AssetTag = TransferHiiStringToSmbios((UINT8 *)TypeBuffer, MemorySubClassData->ArrayLink.MemoryAssetTag); + TypeBuffer->PartNumber = TransferHiiStringToSmbios((UINT8 *)TypeBuffer, MemorySubClassData->ArrayLink.MemoryPartNumber); + TypeBuffer->Attributes = MemorySubClassData->ArrayLink.MemoryAttributes; + TypeBuffer->ConfMemClkSpeed = MemorySubClassData->ArrayLink.MemorySpeed; +#if defined DCLK_FREQUENCY && DCLK_FREQUENCY == 1 + TypeBuffer->ConfMemClkSpeed = ((MemorySubClassData->ArrayLink.MemorySpeed)/2)+1; +#endif + TypeBuffer->ExtendedSize = 0; +#if defined AMI_SMBIOS_MODULE_VERSION && AMI_SMBIOS_MODULE_VERSION >= 105 + TypeBuffer->MinimumVoltage = 0; // unknown SmBios 2.8.0+ + TypeBuffer->MaximumVoltage = 0; // unknown SmBios 2.8.0+ + TypeBuffer->ConfiguredVoltage = 0; // unknown SmBios 2.8.0+ +#endif + + if (TypeBuffer->Size >= 0x8000 ) // 32G + { + TypeBuffer->ExtendedSize = TypeBuffer->Size; + + // ExtendedSize Bit 31 is reserved for future use and must be set to 0. + if (TypeBuffer->ExtendedSize >= BIT31) { + TypeBuffer->ExtendedSize = BIT31 - 1; + } + TypeBuffer->Size = 0x7FFF; + } + + // SmBios 2.8.0+ + // To update MinimumVoltage, MaximumVoltage, ConfiguredVoltage and Dimm Frequency + NbSmbiosType17VoltageAndSpeed (TypeBuffer); + + // Write structure To SMBIOS Buffer + bsize = SMBIOS_GetStructureTotalSize((UINT8 *)TypeBuffer); + gSBUpdate->SMBIOS_InsertStructure(SmbiosBuffer, (UINT8 *)TypeBuffer, bsize); + + // Fix handle link + SMBIOS_FixHandleLink(SmbiosBuffer); + + // Free temporary buffer + gBS->FreePool(TypeBuffer); +} + +#if MEMORY_ERROR_INFO +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: BuildType18 +// +// Description: Build SMBIOS Type 18 +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, +// EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +// +// Output: None +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +BuildType18( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + IN EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +) +{ + SMBIOS_MEMORY_ERROR_INFO *TypeBuffer; + UINT16 bsize; + + // Allocate temporary buffer + TypeBuffer = EfiLibAllocateZeroPool(sizeof(SMBIOS_MEMORY_ERROR_INFO)+0x100); + + // Build header of structure + TypeBuffer->StructureType.Type = 18; // Type 18 + TypeBuffer->StructureType.Length = sizeof(SMBIOS_MEMORY_ERROR_INFO); + TypeBuffer->StructureType.Handle = gSBUpdate->SMBIOS_GetFreeHandle(SmbiosBuffer); + + //Memory.PhysicalMemArray[PMAIdx].ArrayMemoryError.ErrorType = 3; + TypeBuffer->ErrorType = 3; + //Memory.PhysicalMemArray[PMAIdx].ArrayMemoryError.ErrorGranularity = 2; + TypeBuffer->ErrorGranularity = 2; + //Memory.PhysicalMemArray[PMAIdx].ArrayMemoryError.ErrorOperation = 2; + TypeBuffer->ErrorOperation = 2; + //Memory.PhysicalMemArray[PMAIdx].ArrayMemoryError.MemArrayErrorAddress = 0x80000000; + TypeBuffer->MemArrayErrorAddress = 0x80000000; + //Memory.PhysicalMemArray[PMAIdx].ArrayMemoryError.DeviceErrorAddress = 0x80000000; + TypeBuffer->DeviceErrorAddress = 0x80000000; + //Memory.PhysicalMemArray[PMAIdx].ArrayMemoryError.ErrorResolution = 0x80000000; + TypeBuffer->ErrorResolution = 0x80000000; + + // Write structure To SMBIOS Buffer + bsize = SMBIOS_GetStructureTotalSize((UINT8 *)TypeBuffer); + gSBUpdate->SMBIOS_InsertStructure(SmbiosBuffer, (UINT8 *)TypeBuffer, bsize); + + // Fix handle link + SMBIOS_FixHandleLink(SmbiosBuffer); + + // Free temporary buffer + gBS->FreePool(TypeBuffer); + +} +#endif + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: BuildType19 +// +// Description: Build SMBIOS Type 19 +// +// +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, +// EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +// +// Output: None +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +BuildType19( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + IN EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +) +{ + SMBIOS_MEM_ARRAY_MAP_ADDR_INFO *TypeBuffer; + UINT16 bsize; + + // Allocate temporary buffer + TypeBuffer = EfiLibAllocateZeroPool(sizeof(SMBIOS_MEM_ARRAY_MAP_ADDR_INFO)+0x100); + + // Build header of structure + TypeBuffer->StructureType.Type = 19; // Type 19 + TypeBuffer->StructureType.Length = sizeof(SMBIOS_MEM_ARRAY_MAP_ADDR_INFO); + TypeBuffer->StructureType.Handle = gSBUpdate->SMBIOS_GetFreeHandle(SmbiosBuffer); + + // Build Content of structure + TypeBuffer->StartingAddress = (UINT32)(MemorySubClassData->ArrayStartAddress.MemoryArrayStartAddress / 1024); + TypeBuffer->EndingAddress = (UINT32)(MemorySubClassData->ArrayStartAddress.MemoryArrayEndAddress / 1024); + TypeBuffer->MemoryArrayHandle = (UINT16)gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 16, 0); + TypeBuffer->PartitionWidth = (UINT8) MemorySubClassData->ArrayStartAddress.MemoryArrayPartitionWidth; + TypeBuffer->ExtendedStartAddr = (MemorySubClassData->ArrayStartAddress.MemoryArrayStartAddress / 1024); + if ((MemorySubClassData->ArrayStartAddress.MemoryArrayEndAddress / 1024) >= 0xFFFFFFFF) + { + TypeBuffer->ExtendedEndAddr = (MemorySubClassData->ArrayStartAddress.MemoryArrayEndAddress / 1024); + TypeBuffer->EndingAddress = 0xFFFFFFFF; + } + else + { + TypeBuffer->ExtendedEndAddr = 0; + } + + // Write structure To SMBIOS Buffer + bsize = SMBIOS_GetStructureTotalSize((UINT8 *)TypeBuffer); + gSBUpdate->SMBIOS_InsertStructure(SmbiosBuffer, (UINT8 *)TypeBuffer, bsize); + + // Fix handle link + SMBIOS_FixHandleLink(SmbiosBuffer); + + // Free temporary buffer + gBS->FreePool(TypeBuffer); + +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: BuildType20 +// +// Description: Build SMBIOS Type 20 +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, +// EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +// +// Output: None +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +BuildType20( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + IN EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData +) +{ + SMBIOS_MEM_DEV_MAP_ADDR_INFO *TypeBuffer; + UINT16 bsize; + + // Allocate temporary buffer + TypeBuffer = EfiLibAllocateZeroPool(sizeof(SMBIOS_MEM_DEV_MAP_ADDR_INFO)+0x100); + + // Build header of structure + TypeBuffer->StructureType.Type = 20; // Type 20 + TypeBuffer->StructureType.Length = sizeof(SMBIOS_MEM_DEV_MAP_ADDR_INFO); + TypeBuffer->StructureType.Handle = gSBUpdate->SMBIOS_GetFreeHandle(SmbiosBuffer); + + // Build Content of structure + TypeBuffer->StartingAddress = (UINT32)(MemorySubClassData->DeviceStartAddress.MemoryDeviceStartAddress / 1024); + TypeBuffer->EndingAddress = (UINT32)(MemorySubClassData->DeviceStartAddress.MemoryDeviceEndAddress / 1024); + + TypeBuffer->MemoryDeviceHandle = SMBIOS_UNKNOW; + TypeBuffer->MemoryArrayMapAddrHandle = (UINT16)gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 19, 1); + + TypeBuffer->PartitionRowPosition = 0xFF;// unknow type. + //MemorySubClassData->DeviceStartAddress.MemoryDevicePartitionRowPosition; + TypeBuffer->InterleavePosition = 0xFF;// unknow type. + //MemorySubClassData->DeviceStartAddress.MemoryDeviceInterleavePosition; + TypeBuffer->InterleaveDataDepth = 0xFF;// unknow type. + //MemorySubClassData->DeviceStartAddress.MemoryDeviceInterleaveDataDepth; + if ((MemorySubClassData->DeviceStartAddress.MemoryDeviceEndAddress / 1024) >= 0xFFFFFFFF) + { + TypeBuffer->ExtendedEndAddr = (MemorySubClassData->DeviceStartAddress.MemoryDeviceEndAddress / 1024); + TypeBuffer->EndingAddress = 0xFFFFFFFF; + } + else + { + TypeBuffer->ExtendedEndAddr = 0; + } + + // Write structure To SMBIOS Buffer + bsize = SMBIOS_GetStructureTotalSize((UINT8 *)TypeBuffer); + gSBUpdate->SMBIOS_InsertStructure(SmbiosBuffer, (UINT8 *)TypeBuffer, bsize); + + // Fix handle link + SMBIOS_FixHandleLink(SmbiosBuffer); + + // Free temporary buffer + gBS->FreePool(TypeBuffer); +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SmbiosProcessMemoryDataRecord +// +// Description: +// This function parses the data record and stores it into the Smbios format +// +// Input: EFI_DATA_RECORD_HEADER *Record, +// SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer +// +// Output: None +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +SmbiosProcessMemoryDataRecord( + IN EFI_DATA_RECORD_HEADER *Record, + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer +) +{ + UINT8 *SrcData; + EFI_SUBCLASS_TYPE1_HEADER *DataHeader; + EFI_MEMORY_SUBCLASS_RECORDS *MemorySubClassData; + + if (EfiCompareGuid (&Record->DataRecordGuid, &gEfiMemorySubClassGuid)) + { + DEBUG((EFI_D_ERROR, "SMBIOS Memory Record Address:0x%X\n", Record)); + + DataHeader = (EFI_SUBCLASS_TYPE1_HEADER *) (Record + 1); + SrcData = (UINT8 *) (DataHeader + 1); + MemorySubClassData = (EFI_MEMORY_SUBCLASS_RECORDS *) SrcData; + + switch (DataHeader->RecordType) + { + case EFI_MEMORY_ARRAY_LOCATION_RECORD_NUMBER: // 16 + BuildType16(SmbiosBuffer, MemorySubClassData); + break; + case EFI_MEMORY_ARRAY_LINK_RECORD_NUMBER: // 17 + BuildType17(SmbiosBuffer, MemorySubClassData); +#if MEMORY_ERROR_INFO + BuildType18(SmbiosBuffer, MemorySubClassData); // 18 +#endif + // next dimm + DimmNumber ++; + break; + case EFI_MEMORY_ARRAY_START_ADDRESS_RECORD_NUMBER: // 19 + BuildType19(SmbiosBuffer, MemorySubClassData); + break; + case EFI_MEMORY_DEVICE_START_ADDRESS_RECORD_NUMBER: // 20 + BuildType20(SmbiosBuffer, MemorySubClassData); + break; + } + } + + return; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: DynamicUpdateMemoryRecord +// +// Description: Updates Memory related structures (Type 16-20) in +// input Buffer with dynamically detected Record for Intel Tiano +// SmBiosMemory Driver. +// +// Input: UINT8 *Buffer +// +// Output: EFI_STATUS - EFI_SUCCESS +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +EFI_STATUS DynamicUpdateMemoryRecord( + IN SMBIOS_TABLE_ENTRY_POINT *Buffer +) +{ + EFI_STATUS Status; + EFI_HANDLE DataHubHandle; + UINTN HandleSize; + UINT64 MonotonicCount; + EFI_DATA_HUB_PROTOCOL *DataHub; + EFI_DATA_RECORD_HEADER *Record; + EFI_GUID gEfiDataHubProtocolGuid = EFI_DATA_HUB_PROTOCOL_GUID; + UINT8 BitIndex; + + Status = EFI_SUCCESS; + DataHub = NULL; + + // + // Get the SmbusProtocol. + // + Status = gBS->LocateProtocol( &gEfiSmbusProtocolGuid, \ + NULL, \ + &gSmbusProtocol ); + // + // Get the MemInfoHobProtocol. + // + Status = gBS->LocateProtocol (&gMemInfoHobProtocolGuid, \ + NULL, \ + &gMemInfoHobProtocol); + + // + // Get the DxePlatformSaPolicyProtocol. + // + Status = gBS->LocateProtocol (&gDxePlatformSaPolicyGuid, \ + NULL, \ + &gDxePlatformSaPolicy); + if (EFI_ERROR (Status)) return Status; + + // Check User Dimm Map + for (BitIndex = 0; BitIndex < 2; BitIndex++) { + if (!((gDxePlatformSaPolicy->MemoryConfig->ChannelASlotMap >> BitIndex) & BIT0)) { + DimmSlot[BitIndex] = 0; //if not, Clear Spd sddress; + } + if (!((gDxePlatformSaPolicy->MemoryConfig->ChannelBSlotMap >> BitIndex) & BIT0)) { + DimmSlot[BitIndex + 2] = 0; //if not, Clear Spd sddress; + } + } + + // + // Get the Data Hub Protocol. Assume only one instance + // of Data Hub Protocol is availabe in the system. + // + HandleSize = sizeof (EFI_HANDLE); + + Status = gBS->LocateHandle ( + ByProtocol, + &gEfiDataHubProtocolGuid, + NULL, + &HandleSize, + &DataHubHandle + ); + + if (EFI_ERROR (Status)) + { + return EFI_SUCCESS; + } + Status = gBS->HandleProtocol ( + DataHubHandle, + &gEfiDataHubProtocolGuid, + &DataHub + ); + + if (EFI_ERROR (Status)) + { + return EFI_SUCCESS; + } +#if defined (MEMORY_DEVICE_INFO) && MEMORY_DEVICE_INFO == 1 + // Clean strcutures which need rebuild + SMBIOS_DeleteStructureByType(Buffer, 16, SMBIOS_FOR_ALL); + SMBIOS_DeleteStructureByType(Buffer, 17, SMBIOS_FOR_ALL); +#if defined (MEMORY_ERROR_INFO) && MEMORY_ERROR_INFO == 1 + SMBIOS_DeleteStructureByType(Buffer, 18, SMBIOS_FOR_ALL); +#endif + SMBIOS_DeleteStructureByType(Buffer, 19, SMBIOS_FOR_ALL); + SMBIOS_DeleteStructureByType(Buffer, 20, SMBIOS_FOR_ALL); +#endif + // + // Get all available data records from data hub + // + MonotonicCount = 0; + Record = NULL; + + do { + Status = DataHub->GetNextRecord ( + DataHub, + &MonotonicCount, + NULL, + &Record + ); + + if (!EFI_ERROR (Status)) + { + if (Record->DataRecordClass == EFI_DATA_RECORD_CLASS_DATA) + { + SmbiosProcessMemoryDataRecord (Record, Buffer); + } + } + } while (!EFI_ERROR (Status) && (MonotonicCount != 0)); + + return EFI_SUCCESS; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMIBiosUpdateMemoryRecordDriverEntryPoint +// +// Description: Update memory record DXE driver for Intel Tiano SmBiosMemory Driver. +// +// Input: ImageHandle - Image handle. +// SystemTable - Pointer to the system table. +// +// Output: EFI_STATUS - EFI_SUCCESS. +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +EFI_STATUS SMIBiosUpdateMemoryRecordDriverEntryPoint( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable +) +{ + EFI_STATUS Status; + EFI_GUID gEfiSmbiosProtocolGuid = EFI_SMBIOS_PROTOCOL_GUID; + SMBIOS_TABLE_ENTRY_POINT *SmbiosTableEntryPoint; + + DxeInitializeDriverLib (ImageHandle, SystemTable); + Status = gBS->LocateProtocol(&gEfiSmbiosUpdateDataProtocolGuid, NULL, &gSBUpdate); + ASSERT_EFI_ERROR(Status); + + Status = gBS->LocateProtocol(&gEfiSmbiosProtocolGuid, NULL, &gSmbiosProtocol); + ASSERT_EFI_ERROR(Status); + SmbiosTableEntryPoint = gSmbiosProtocol->SmbiosGetTableEntryPoint(); + + Status = DynamicUpdateMemoryRecord(SmbiosTableEntryPoint); + ASSERT_EFI_ERROR(Status); + + return EFI_SUCCESS; +} + +//----------------------------------------------------------------------------- +// SMBIOS Dynamic Maintain Functions +//----------------------------------------------------------------------------- + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_DeleteStructureByType +// +// Description: SMBIOS Delete Structure Type +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, +// UINT8 Type, +// UINT8 Index +// +// Output: UINTN count +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINTN +SMBIOS_DeleteStructureByType( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + IN UINT8 Type, + IN UINT8 Index +) +{ + UINT8 i; + UINT16 handle; + UINTN count; + + count = 0; + if (Index != SMBIOS_FOR_ALL) + { // for Single + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, Type, Index); + if (handle != SMBIOS_NOT_FOUND) + { + gSBUpdate->SMBIOS_DeleteStructure(SmbiosBuffer, handle); + } + } else { // -1 for ALL + for(i = 0; i < MAX_HANDLES; i++) + { + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, Type, 1); + if (handle != SMBIOS_NOT_FOUND) + { + gSBUpdate->SMBIOS_DeleteStructure(SmbiosBuffer, handle); + count++; + } + } + } + + return count; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_GetStructureTotalSize +// +// Description: SMBIOS get structure total size +// +// Input: UINT8 *BufferStart +// +// Output: UINT16 Total Size. +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT16 +SMBIOS_GetStructureTotalSize( + IN UINT8 *BufferStart +) +{ + UINT8 *BufferEnd; + + BufferEnd = BufferStart; + BufferEnd += ((SMBIOS_STRUCTURE_HEADER*)BufferStart)->Length; + while (*(UINT16*)BufferEnd != 0) + { + BufferEnd++; + } + + return (UINT16)(BufferEnd + 2 - BufferStart); // +2 for double zero terminator +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_GetStringBase +// +// Description: SMBIOS get String Base +// +// Input: UINT8 *Buffer +// +// Output: UINT8 Buffer +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT8* SMBIOS_GetStringBase( + IN UINT8 *Buffer +) +{ + SMBIOS_STRUCTURE_HEADER *p; + + p = (SMBIOS_STRUCTURE_HEADER *)Buffer; + Buffer += p->Length; + + return Buffer; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_NextString +// +// Description: SMBIOS next String +// +// Input: UINT8 *String +// +// Output: String point. +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT8* SMBIOS_NextString( + IN UINT8 *String +) +{ + return String+(EfiAsciiStrLen(String)+1); +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_FindString +// +// Description: SMBIOS find String +// +// Input: CHAR8 *Buffer +// CHAR8 *String +// +// Output: String point. +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT8 +SMBIOS_FindString( + IN CHAR8 *Buffer, + IN CHAR8 *String +) +{ + CHAR8 *sp; + UINT8 i; + UINTN quit; + UINTN l; + + quit = 0; + i = 1; + sp = SMBIOS_GetStringBase(Buffer); + while (quit == 0) + { + l = EfiAsciiStrLen(sp); + if (l == 0) + { + i = 0xFF; + quit = 1; + } else if (EfiAsciiStrCmp(String, sp) == 0) + { + quit = 1; + } else { + sp = SMBIOS_NextString(sp); + i++; + } + } + + return i; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_AddString +// +// Description: SMBIOS add String +// +// Input: CHAR8 *Buffer +// CHAR8 *String +// +// Output: UINT8 +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT8 +SMBIOS_AddString( + IN CHAR8 *Buffer, + IN CHAR8 *String +) +{ + CHAR8 *sp; + UINT8 i; + UINTN l; + + if (EfiAsciiStrLen(String) == 0) + { + EfiAsciiStrCpy(String, "[Empty]"); + } + + i = 1; + sp = SMBIOS_GetStringBase(Buffer); + while ((l = EfiAsciiStrLen(sp)) != 0) + { + sp = sp + (l+1); + i++; + } + + EfiAsciiStrCpy(sp, String); + sp = SMBIOS_NextString(sp); + *sp = 0; + + return i; + +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: SMBIOS_FixHandleLink +// +// Description: SMBIOS fix handle link +// +// Input: SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer +// +// +// Output: VOID +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +SMBIOS_FixHandleLink( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer +) +{ + UINT16 handle; + SMBIOS_PHYSICAL_MEM_ARRAY_INFO *T16_p; + SMBIOS_MEMORY_DEVICE_INFO *T17_p; + SMBIOS_MEM_ARRAY_MAP_ADDR_INFO *T19_p; + SMBIOS_MEM_DEV_MAP_ADDR_INFO *T20_p; + UINT16 T19_Handle; + UINT16 T17_Size_KB; + UINT16 T20_Size_KB; + UINTN Q_flag; + UINT8 i, j; +#if MEMORY_ERROR_INFO + SMBIOS_MEMORY_ERROR_INFO *T18_p = NULL; +#endif + + T16_p = NULL; + T17_p = NULL; + T19_p = NULL; + T20_p = NULL; + T19_Handle = SMBIOS_UNKNOW; + Q_flag = 0; + T17_Size_KB = 0; + + // Looking for Type 19 to set MemoryArrayHandle + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 19, 1); + if (handle != SMBIOS_NOT_FOUND) + { + T19_p = (SMBIOS_MEM_ARRAY_MAP_ADDR_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + T19_Handle = T19_p->StructureType.Handle; + if (T19_p->MemoryArrayHandle == SMBIOS_UNKNOW) + { + // Looking for Type 16 + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 16, 1); + if (handle != SMBIOS_NOT_FOUND) + { + T16_p = (SMBIOS_PHYSICAL_MEM_ARRAY_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + T19_p->MemoryArrayHandle = T16_p->StructureType.Handle; + } + } + } + +#if MEMORY_ERROR_INFO + // Looking for Type 16 + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 16, 1); + if (handle != SMBIOS_NOT_FOUND) + { + T16_p = (SMBIOS_PHYSICAL_MEM_ARRAY_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + if (T16_p->MemErrInfoHandle == SMBIOS_UNKNOW) + { + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 18, 1); + if (handle != SMBIOS_NOT_FOUND) + { + T18_p = (SMBIOS_MEMORY_ERROR_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + T16_p->MemErrInfoHandle = T18_p->StructureType.Handle; + } + } + } + + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 17, 1); + if (handle != SMBIOS_NOT_FOUND) + { + T17_p = (SMBIOS_MEMORY_DEVICE_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + if (T17_p->MemErrorInfoHandle == SMBIOS_UNKNOW) + { + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 18, 2); + if (handle != SMBIOS_NOT_FOUND) + { + T18_p = (SMBIOS_MEMORY_ERROR_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + T17_p->MemErrorInfoHandle = T18_p->StructureType.Handle; + } + } + } + + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 17, 3); + if (handle != SMBIOS_NOT_FOUND) + { + T17_p = (SMBIOS_MEMORY_DEVICE_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + if (T17_p->MemErrorInfoHandle == SMBIOS_UNKNOW) + { + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 18, 3); + if (handle != SMBIOS_NOT_FOUND) + { + T18_p = (SMBIOS_MEMORY_ERROR_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + T17_p->MemErrorInfoHandle = T18_p->StructureType.Handle; + } + } + } +#endif + + Q_flag = 0; + // Looking for Type 20 to set MemoryArrayMapAddrHandle and MemoryDeviceHandle + for(i = 1; i < MAX_HANDLES; i++) + { + T20_Size_KB = 0; + + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 20, i); + if (handle != SMBIOS_NOT_FOUND) + { + T20_p = (SMBIOS_MEM_DEV_MAP_ADDR_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + T20_p->MemoryArrayMapAddrHandle = T19_Handle; + if (T20_p->MemoryDeviceHandle == SMBIOS_UNKNOW) + { + T20_Size_KB =(UINT16) T20_p->EndingAddress + 1; + + // Looking for Type 17 + for(j = i; j < MAX_HANDLES; j++) + { + handle = gSBUpdate->SMBIOS_FindStructure(SmbiosBuffer, 17, j); + if (handle != SMBIOS_NOT_FOUND) + { + T17_p = (SMBIOS_MEMORY_DEVICE_INFO *)gSBUpdate->SMBIOS_GetStructureBase(SmbiosBuffer, handle); + + T17_Size_KB = (T17_p->Size & 0x7FFF) * ((T17_p->Size & 0x8000) ? 1 : 1024); + if (T17_Size_KB == T20_Size_KB) + { + T20_p->MemoryDeviceHandle = T17_p->StructureType.Handle; + } + } + } + } + Q_flag++; + } + + if (Q_flag == 0) + break; + } +} + +#if (EFI_SPECIFICATION_VERSION < 0x0002000A) +//----------------------------------------------------------------------------- +// HII Functions +//----------------------------------------------------------------------------- +EFI_HII_HANDLE HiiHandle; +EFI_HII_PROTOCOL *Hii = NULL; + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: InitHiiString +// +// Description: Init Hii string +// +// Input: VOID +// +// +// Output: VOID +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +InitHiiString(VOID) +{ + EFI_STATUS Status; + UINT16 HandleBufferLength; + EFI_HII_HANDLE *HiiHandleBuffer; + UINTN NumberOfHiiHandles; + UINTN Index; + UINT16 Length; + EFI_GUID HiiGuid; + + if (Hii == NULL) + { + HandleBufferLength = 0x1000; + HiiHandleBuffer = NULL; + HiiHandle = 0; + + // + // Locate HII protocol + // + Status = gBS->LocateProtocol (&gEfiHiiProtocolGuid, NULL, &Hii); + ASSERT_EFI_ERROR (Status); + + HiiHandleBuffer = EfiLibAllocateZeroPool (HandleBufferLength); + + Status = Hii->FindHandles (Hii, &HandleBufferLength, HiiHandleBuffer); + ASSERT_EFI_ERROR (Status); + + // + // Get the Hii Handle that matches the StructureNode->ProducerName + // + NumberOfHiiHandles = HandleBufferLength / sizeof (EFI_HII_HANDLE); + for (Index = 0; Index < NumberOfHiiHandles; Index++) + { + Length = 0; + Status = ExtractDataFromHiiHandle ( + HiiHandleBuffer[Index], + &Length, + NULL, + &HiiGuid + ); + if (EfiCompareGuid (&gEfiMemorySubClassDriverGuid, &HiiGuid)) + { + HiiHandle = HiiHandleBuffer[Index]; + break; + } + } + gBS->FreePool (HiiHandleBuffer); + } +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: HiiGetString +// +// Description: Init get string +// +// Input: STRING_REF Token +// +// +// Output: VOID +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +CHAR16 * +HiiGetString( + IN STRING_REF Token +) +{ + UINTN StringBufferLength; + CHAR16 *StringBuffer; + EFI_STATUS Status; + + InitHiiString(); + + Status = EFI_SUCCESS; + StringBufferLength = 0x100; + StringBuffer = EfiLibAllocateZeroPool(StringBufferLength); + ASSERT(StringBuffer); + + // + // Find the string based on the current language + // + Status = Hii->GetString ( + Hii, + HiiHandle, + Token, + FALSE, + NULL, + &StringBufferLength, + StringBuffer + ); + + if (EFI_ERROR (Status)) + { + gBS->FreePool(StringBuffer); + StringBuffer = NULL; + } + + return StringBuffer; +} +#endif //EFI_SPECIFICATION_VERSION < 0x0002000A + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: ConvertChar16ToChar8 +// +// Description: Convert char 16 to char 8 +// +// Input: CHAR8 *Dest +// CHAR16 *Src +// +// Output: VOID +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +VOID +ConvertChar16ToChar8 ( + IN CHAR8 *Dest, + IN CHAR16 *Src +) +{ + while (*Src) + { + *Dest++ = (UINT8) (*Src++); + } + + *Dest = 0; +} + +//<AMI_PHDR_START> +//---------------------------------------------------------------------------- +// Procedure: TransferHiiStringToSmbios +// +// Description: Transfer Hii string to Smbios +// +// Input: CHAR8 *Structure +// STRING_REF Token +// +// Output: VOID +// +//---------------------------------------------------------------------------- +//<AMI_PHDR_END> +UINT8 +TransferHiiStringToSmbios ( + IN UINT8 *Structure, + IN STRING_REF Token +) +{ + CHAR8 *Buffer; + UINTN BufferSize; + UINT8 i; + CHAR16 *String; + +#if (EFI_SPECIFICATION_VERSION >= 0x0002000A) + EFI_STATUS Status; +#endif + + BufferSize = 0x100; + Buffer = EfiLibAllocateZeroPool(BufferSize); + ASSERT(Buffer); + i = (UINT8) -1; + +#if (EFI_SPECIFICATION_VERSION < 0x0002000A) + String = HiiGetString(Token); +#else + + Status = GetStringFromToken (&gEfiMemorySubClassDriverGuid, Token, (EFI_STRING *)&String); + ASSERT_EFI_ERROR(Status); + +#endif + + ConvertChar16ToChar8(Buffer, String); + + i = SMBIOS_AddString(Structure, Buffer); + gBS->FreePool(String); + gBS->FreePool(Buffer); + return i; +} + +//************************************************************************* +//************************************************************************* +//** ** +//** (C)Copyright 1985-2011, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//************************************************************************* +//************************************************************************* diff --git a/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.cif b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.cif new file mode 100644 index 0000000..e0e556e --- /dev/null +++ b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.cif @@ -0,0 +1,12 @@ +<component> + name = "UpdateMemoryRecord" + category = ModulePart + LocalRoot = "Chipset\NB\SystemAgentWrap\UpdateMemoryRecord" + RefName = "UpdateMemoryRecord" +[files] +"UpdateMemoryRecord.sdl" +"UpdateMemoryRecord.mak" +"UpdateMemoryRecord.dxs" +"UpdateMemoryRecord.c" +"UpdateMemoryRecord.h" +<endComponent> diff --git a/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.dxs b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.dxs new file mode 100644 index 0000000..fe4a9cb --- /dev/null +++ b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.dxs @@ -0,0 +1,86 @@ +//************************************************************************* +//************************************************************************* +//** ** +//** (C)Copyright 1985-2011, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//************************************************************************* +//************************************************************************* + +//************************************************************************* +// $Header: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.dxs 2 8/31/12 2:38a Yurenlai $ +// +// $Revision: 2 $ +// +// $Date: 8/31/12 2:38a $ +//************************************************************************* +// Revision History +// ---------------- +// $Log: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.dxs $ +// +// 2 8/31/12 2:38a Yurenlai +// [TAG] EIP99526 +// [Category] Improvement +// [Severity] Important +// [Description] Fixed system hang at CKP 0x6A if +// PI_SPECIFICATION_VERSION = 0x10000. +// [Files] UpdateMemoryRecord.dxs +// +// 1 2/08/12 4:37a Yurenlai +// Intel Haswell/NB eChipset initially releases. +// +//************************************************************************* + +#if (PI_SPECIFICATION_VERSION < 0x10014) +#include <Token.h> +#include <protocol\SmbiosGetFlashDataProtocol.h> +#define __AMIHOBS_H__ +#include <protocol\SmbiosDynamicData.h> +#include <Protocol\Datahub.h> +#if (EFI_SPECIFICATION_VERSION >= 0x0002000A) +#include <Protocol/HiiDatabase.h> +#else +#include <Protocol/HII.h> +#endif +#define __EFI__H__ +#include <Protocol\Smbus.h> +#include <SmbiosUpdateDataProtocol.h> +#include <SaInfo\SaInfo.h> + +DEPENDENCY_START + EFI_SMBIOS_BOARD_PROTOCOL_GUID AND + EFI_DATA_HUB_PROTOCOL_GUID AND +#if (EFI_SPECIFICATION_VERSION >= 0x0002000A) + EFI_HII_DATABASE_PROTOCOL_GUID AND +#else + EFI_HII_PROTOCOL_GUID AND +#endif + EFI_SA_INFO_PROTOCOL_GUID AND + EFI_SMBUS_HC_PROTOCOL_GUID AND + EFI_SMBIOS_PROTOCOL_GUID AND + EFI_SMBIOS_UPDATE_DATA_PROTOCOL_GUID +DEPENDENCY_END +#else +DEPENDENCY_START + AFTER {0xEDA39402, 0xF375, 0x4496, 0x92, 0xD3, 0x83, 0xB4, 0x3C, 0xB8, 0xA7, 0x6A} +DEPENDENCY_END +#endif + +//************************************************************************* +//************************************************************************* +//** ** +//** (C)Copyright 1985-2011, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//************************************************************************* +//*************************************************************************
\ No newline at end of file diff --git a/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.h b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.h new file mode 100644 index 0000000..254f132 --- /dev/null +++ b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.h @@ -0,0 +1,108 @@ +//************************************************************************* +//************************************************************************* +//** ** +//** (C)Copyright 1985-2011, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//************************************************************************* +//************************************************************************* + +//************************************************************************* +// $Header: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.h 1 2/08/12 4:37a Yurenlai $ +// +// $Revision: 1 $ +// +// $Date: 2/08/12 4:37a $ +//************************************************************************* +// Revision History +// ---------------- +// $Log: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.h $ +// +// 1 2/08/12 4:37a Yurenlai +// Intel Haswell/NB eChipset initially releases. +// +//************************************************************************* +//<AMI_FHDR_START> +// +// Name: UpdateMemoryRecord.h +// +// Description: +// +//<AMI_FHDR_END> +//********************************************************************** +#ifndef __UPDATE_MEMORY_RECORD_H__ +#define __UPDATE_MEMORY_RECORD_H__ + +#include <Tiano.h> +#include <Protocol\SMBios.h> +#include <Protocol\SmbiosGetFlashDataProtocol.h> +#include "EfiDriverLib.h" +#include "Guid\DataHubRecords\DataHubSubClassMemory.h" +#include "SmbiosUpdateDataProtocol.h" + +#if (EFI_SPECIFICATION_VERSION >= 0x0002000A) +#include "UefiIfrLibrary.h" +#include EFI_PROTOCOL_DEPENDENCY (HiiDatabase) +#include EFI_PROTOCOL_DEPENDENCY (HiiString) +#else +#include "Library\Dxe\EfiIfrSupportLib\IfrLibrary.h" +#include EFI_PROTOCOL_DEPENDENCY (Hii) +#endif + +#define SMBIOS_NOT_FOUND 0xFFFF +#define SMBIOS_UNKNOW 0xFFFF +#define SMBIOS_NOT_PROVIDE 0xFFFE +#define MAX_HANDLES 0x10 +#define SMBIOS_FOR_ALL 0xFF + +VOID +SMBIOS_FixHandleLink( + IN SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer +); + +EFI_STATUS +ExtractDataFromHiiHandle ( + IN EFI_HII_HANDLE HiiHandle, + IN OUT UINT16 *ImageLength, + OUT UINT8 *DefaultImage, + OUT EFI_GUID *Guid +); + + +UINT8 +TransferHiiStringToSmbios ( + IN UINT8 *Structure, + IN STRING_REF Token +); + +UINT16 +SMBIOS_GetStructureTotalSize( + IN UINT8 *BufferStart +); + +UINTN +SMBIOS_DeleteStructureByType ( + SMBIOS_TABLE_ENTRY_POINT *SmbiosBuffer, + UINT8 Type, + UINT8 Index +); + +#endif +//************************************************************************* +//************************************************************************* +//** ** +//** (C)Copyright 1985-2011, American Megatrends, Inc. ** +//** ** +//** All Rights Reserved. ** +//** ** +//** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +//** ** +//** Phone: (770)-246-8600 ** +//** ** +//************************************************************************* +//*************************************************************************
\ No newline at end of file diff --git a/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.mak b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.mak new file mode 100644 index 0000000..df6ad4a --- /dev/null +++ b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.mak @@ -0,0 +1,44 @@ +# /*++ +# Copyright (c) 2011 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. +# --*/ +all : UpdateMemoryRecord + +UpdateMemoryRecord : $(BUILD_DIR)\UpdateMemoryRecord.mak UpdateMemoryRecordBin + +$(BUILD_DIR)\UpdateMemoryRecord.mak : $(UpdateMemroyRecord_DIR)\UpdateMemoryRecord.CIF $(UpdateMemroyRecord_DIR)\$(@B).mak $(BUILD_RULES) + $(CIF2MAK) $(UpdateMemroyRecord_DIR)\UpdateMemoryRecord.CIF $(CIF2MAK_DEFAULTS) + +MemoryRecord_INCLUDES = \ + $(EDK_INCLUDES)\ + $(INTEL_MCH_INCLUDES) \ + /I$(SMBIOSUpdateData_DIR)\ + /I$(UefiEfiIfrSupportLib_DIR)\ + /I$(PROJECT_DIR)\ + /IInclude\ + +MemoryRecord_LIB_LINKS =\ + $(EFIDRIVERLIB)\ +!IF $(EFI_SPECIFICATION_VERSION) >= 0x2000A + $(UEFIEFIIFRSUPPORTLIB) +!ELSE + $(EFIIFRSUPPORTLIB)\ +!ENDIF + +UpdateMemoryRecordBin : $(MemoryRecord_LIB_LINKS) + $(MAKE) /$(MAKEFLAGS) $(EDK_DEFAULTS)\ + /f $(BUILD_DIR)\UpdateMemoryRecord.mak all\ + NAME=UpdateMemoryRecord\ + "MY_INCLUDES=$(MemoryRecord_INCLUDES)"\ + GUID=24CCD374-3DF6-4181-86F6-E3C66920A145\ + ENTRY_POINT=SMIBiosUpdateMemoryRecordDriverEntryPoint\ + DEPEX1=$(UpdateMemroyRecord_DIR)\UpdateMemoryRecord.dxs \ + DEPEX1_TYPE=EFI_SECTION_DXE_DEPEX \ + TYPE=BS_DRIVER\ + COMPRESS=1\ diff --git a/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.sdl b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.sdl new file mode 100644 index 0000000..8accc20 --- /dev/null +++ b/Chipset/NB/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.sdl @@ -0,0 +1,69 @@ +#************************************************************************* +#************************************************************************* +#** ** +#** (C)Copyright 1985-2011, American Megatrends, Inc. ** +#** ** +#** All Rights Reserved. ** +#** ** +#** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +#** ** +#** Phone: (770)-246-8600 ** +#** ** +#************************************************************************* +#************************************************************************* + +#************************************************************************* +# $Header: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.sdl 1 2/08/12 4:37a Yurenlai $ +# +# $Revision: 1 $ +# +# $Date: 2/08/12 4:37a $ +#************************************************************************* +# Revision History +# ---------------- +# $Log: /Alaska/BIN/Chipset/Intel/NorthBridge/Haswell/Intel SystemAgent NB Chipset/SystemAgentWrap/UpdateMemoryRecord/UpdateMemoryRecord.sdl $ +# +# 1 2/08/12 4:37a Yurenlai +# Intel Haswell/NB eChipset initially releases. +# +#************************************************************************* +TOKEN + Name = "UpdateMemoryRecord_SUPPORT" + Value = "1" + Help = "Main switch to enable UpdateMemoryRecord support in Project" + TokenType = Boolean + TargetEQU = Yes + TargetMAK = Yes + Master = Yes + Token = "SMBIOS_MEMORY_SUPPORT" "=" "1" + Token = "SMBIOS_SUPPORT" "=" "1" +End + +PATH + Name = "UpdateMemroyRecord_DIR" +End + +MODULE + Help = "Includes UpdateMemoryRecord.mak to Project" + File = "UpdateMemoryRecord.mak" +End + +ELINK + Name = "$(BUILD_DIR)\UpdateMemoryRecord.ffs" + Parent = "FV_MAIN" + InvokeOrder = AfterParent +End + +#************************************************************************* +#************************************************************************* +#** ** +#** (C)Copyright 1985-2011, American Megatrends, Inc. ** +#** ** +#** All Rights Reserved. ** +#** ** +#** 5555 Oakbrook Parkway, Suite 200, Norcross, GA 30093 ** +#** ** +#** Phone: (770)-246-8600 ** +#** ** +#************************************************************************* +#*************************************************************************
\ No newline at end of file |