/** @file ;****************************************************************************** ;* Copyright (c) 2014 - 2021, Insyde Software Corporation. All Rights Reserved. ;* ;* You may not reproduce, distribute, publish, display, perform, modify, adapt, ;* transmit, broadcast, present, recite, release, license or otherwise exploit ;* any part of this publication in any form, by any means, without the prior ;* written permission of Insyde Software Corporation. ;* ;****************************************************************************** */ #include PLATFORM_INFO_DISPLAY_TABLE mDisplayPlatformInfoFunction[] = { PLATFORM_INFO_DISPLAY_OPTION_TABLE_LIST }; EFI_HII_STRING_PROTOCOL *mIfrLibHiiString; STATIC CHAR16 *mMemFormFactorStr[] = {L"Other", L"Unknown", L"SIMM", L"SIP", L"Chip", L"DIP", L"ZIP", L"Proprietary Card", L"DIMM", L"TSOP", L"Row of chips", L"RIMM", L"SODIMM", L"SRIMM", L"FB-DIMM" }; /** Create Ramslot information. And save string tokens into destination Hii handle. @param[in] SourceHiiHandle Input source Hii handle. @param[in] DestinationHiiHandle Input destination Hii handle. @retval EFI_SUCCESS If the create Ramslot and save string tokens could be successfully. @retval Others Failed to update Form. **/ STATIC EFI_STATUS CreateRamSlotInfo ( IN EFI_HII_HANDLE SourceHiiHandle, IN EFI_HII_HANDLE DestinationHiiHandle ) { VOID *StartOpCodeHandle; VOID *EndOpCodeHandle; EFI_IFR_GUID_LABEL *StartLabel; EFI_IFR_GUID_LABEL *EndLabel; EFI_STATUS Status; EFI_STRING_ID StrToken1; EFI_STRING_ID StrToken2; EFI_SMBIOS_TABLE_HEADER *Record; EFI_SMBIOS_HANDLE SmbiosHandle; EFI_SMBIOS_PROTOCOL *Smbios; MEM_INFO_PROTOCOL *MemInfoProtocol; SMBIOS_TABLE_TYPE17 *Type17Record; CHAR16 StrBuffer[120]; CHAR16 StrType[40]; UINTN Node; UINTN Channel; UINTN Dimm; UINTN Index; //[-start-210322-IB18770020-add]# MEMORY_INFO_DATA *MemInfoData; UINT8 MemoryType; EFI_STRING_ID StrToken[DIMM_NUM * 2]; UINTN DimmNum[DIMM_NUM]; //[-end-210322-IB18770020-add]# StartOpCodeHandle = HiiAllocateOpCodeHandle (); ASSERT (StartOpCodeHandle != NULL); EndOpCodeHandle = HiiAllocateOpCodeHandle (); ASSERT (EndOpCodeHandle != NULL); StartLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (StartOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL)); StartLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL; StartLabel->Number = UPDATE_INFO_RAM_SLOT_LABEL; EndLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (EndOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL)); EndLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL; EndLabel->Number = MAIN_PAGE_PLATFORM_INFO_LABEL; Status = gBS->LocateProtocol ( &gEfiSmbiosProtocolGuid, NULL, (VOID **) &Smbios ); ASSERT_EFI_ERROR (Status); if (EFI_ERROR (Status)) { return Status; } ZeroMem (StrType, sizeof (StrType)); SmbiosHandle = SMBIOS_HANDLE_PI_RESERVED; do { Status = Smbios->GetNext (Smbios, &SmbiosHandle, NULL, &Record, NULL); if (EFI_ERROR(Status)) { break; } if (Record->Type == EFI_SMBIOS_TYPE_MEMORY_DEVICE) { Type17Record = (SMBIOS_TABLE_TYPE17 *) Record; // // Get slot index and update all memory device slot string at first time. // if (Type17Record->FormFactor >= MemoryFormFactorOther && Type17Record->FormFactor <= MemoryFormFactorFbDimm) { if (Type17Record->Size != 0 && Type17Record->Size != 0xFFFF) { UnicodeSPrint (StrType, sizeof (StrType), L"%s", mMemFormFactorStr[Type17Record->FormFactor - 1]); break; } } } } while(Status == EFI_SUCCESS); Status = gBS->LocateProtocol (&gMemInfoProtocolGuid, NULL, (VOID **) &MemInfoProtocol); ASSERT_EFI_ERROR (Status); if (EFI_ERROR (Status)) { return EFI_NOT_FOUND; } //[-start-210322-IB18770020-modify]# // DDR5 has two independent channel per DIMM, therefore, remove the display of Channel in Memory info. Only displays Controller and string in MemFormFactorStr MemInfoData = &MemInfoProtocol->MemInfoData; MemoryType = MemInfoData->DdrType; Index = 0; for (Dimm = 0; Dimm < DIMM_NUM; Dimm++){ DimmNum[Dimm] = 0; } switch(MemoryType) { case MRC_DDR_TYPE_LPDDR5: case MRC_DDR_TYPE_DDR5: for (Node = 0; Node < NODE_NUM; Node++){ for (Channel = 0; Channel < CH_NUM; Channel++){ for (Dimm = 0; Dimm < DIMM_NUM; Dimm++){ if (MemInfoProtocol->MemInfoData.dimmSize[Index] > 0) { DimmNum[Dimm] += (UINTN) MemInfoProtocol->MemInfoData.dimmSize[Index]; UnicodeSPrint (StrBuffer, sizeof (StrBuffer), L"Controller%d %s%d", Node, StrType, Dimm); StrToken[Dimm * 2] = HiiSetString (DestinationHiiHandle, 0, StrBuffer, NULL); UnicodeSPrint (StrBuffer, sizeof (StrBuffer), L"%d MB", DimmNum[Dimm]); StrToken[(Dimm * 2) + 1] = HiiSetString (DestinationHiiHandle, 0, StrBuffer, NULL); } Index++; } } for (Dimm = 0; Dimm < DIMM_NUM; Dimm++){ if (DimmNum[Dimm]) { HiiCreateTextOpCode ( StartOpCodeHandle, StrToken[Dimm * 2], 0, StrToken[(Dimm * 2) + 1] ); } DimmNum[Dimm] = 0; } } break; case MRC_DDR_TYPE_DDR4: case MRC_DDR_TYPE_LPDDR4: for (Node = 0; Node < NODE_NUM; Node++){ for (Channel = 0; Channel < CH_NUM; Channel++){ for (Dimm = 0; Dimm < DIMM_NUM; Dimm++){ if (MemInfoProtocol->MemInfoData.dimmSize[Index] > 0) { UnicodeSPrint (StrBuffer, sizeof (StrBuffer), L"Controller%d Channel%d %s%d", Node, Channel, StrType, Dimm); StrToken1 = HiiSetString (DestinationHiiHandle, 0, StrBuffer, NULL); UnicodeSPrint (StrBuffer, sizeof (StrBuffer), L"%d MB", MemInfoProtocol->MemInfoData.dimmSize[Index]); StrToken2 = HiiSetString (DestinationHiiHandle, 0, StrBuffer, NULL); HiiCreateTextOpCode ( StartOpCodeHandle, StrToken1, 0, StrToken2 ); } Index++; } } } break; } //[-end-210322-IB18770020-modify]# // // Add Text op-code // Status = HiiUpdateForm ( DestinationHiiHandle, NULL, ROOT_FORM_ID, StartOpCodeHandle, EndOpCodeHandle ); HiiFreeOpCodeHandle (StartOpCodeHandle); HiiFreeOpCodeHandle (EndOpCodeHandle); return Status; } /** Update new string to Hii Handle. @param [in] SrcHiiHandle New Hii Handle. @param [in] SrcStringId New String Token. @param [in] DstHiiHandle Hii Handle of the package to be updated. @param [out] DstStringId String Token to be updated. @retval EFI_SUCCESS String update successfully. **/ EFI_STATUS NewStringToHandle ( IN EFI_HII_HANDLE SrcHiiHandle, IN EFI_STRING_ID SrcStringId, IN EFI_HII_HANDLE DstHiiHandle, OUT EFI_STRING_ID *DstStringId ) { EFI_STATUS Status; CHAR16 *String; UINTN Size; UINTN StringSize; CHAR8 *Languages; CHAR8 *LangStrings; CHAR8 Lang[RFC_3066_ENTRY_SIZE]; StringSize = 0x200; String = AllocateZeroPool (StringSize); if (String == NULL) { return EFI_OUT_OF_RESOURCES; } // // Use english string as the default string. // Size = StringSize; Status = mIfrLibHiiString->GetString ( mIfrLibHiiString, "en-US", SrcHiiHandle, SrcStringId, String, &Size, NULL ); if (Status == EFI_BUFFER_TOO_SMALL) { gBS->FreePool (String); StringSize = Size; String = AllocateZeroPool (StringSize); Status = mIfrLibHiiString->GetString ( mIfrLibHiiString, "eng", SrcHiiHandle, SrcStringId, String, &Size, NULL ); if (EFI_ERROR (Status)) { gBS->FreePool (String); return Status; } } else if (EFI_ERROR (Status)) { return Status; } *DstStringId = HiiSetString (DstHiiHandle, 0, String, NULL); // // Update string by each language. // Languages = HiiGetSupportedLanguages (DstHiiHandle); if (Languages == NULL) { gBS->FreePool (String); return EFI_NOT_FOUND; } LangStrings = Languages; while (*LangStrings != 0) { SetupUtilityLibGetNextLanguage (&LangStrings, Lang); Size = StringSize; Status = mIfrLibHiiString->GetString ( mIfrLibHiiString, Lang, SrcHiiHandle, SrcStringId, String, &Size, NULL ); if (!EFI_ERROR (Status)) { mIfrLibHiiString->SetString ( mIfrLibHiiString, DstHiiHandle, *DstStringId, Lang, String, NULL ); } } gBS->FreePool (String); gBS->FreePool (Languages); return EFI_SUCCESS; } /** Acquire the string associated with the Index from smbios structure and return it. The caller is responsible for free the string buffer. @param OptionalStrStart The start position to search the string @param Index The index of the string to extract @param String The string that is extracted @retval EFI_SUCCESS Get index string successfully. @retval EFI_INVALID_PARAMETER Index is zero. It is invalid value. @retval EFI_ABORTED Get missing string fail . @retval EFI_OUT_OF_RESOURCES Allocate memory fail. @retval Other Get setup browser data fail. **/ EFI_STATUS GetStringByIndex ( IN CHAR8 *OptionalStrStart, IN UINT8 Index, OUT CHAR16 **String ) { UINTN StrSize; CHAR16 *StringBuffer; if (Index == 0) { return EFI_INVALID_PARAMETER; } StrSize = 0; do { Index--; OptionalStrStart += StrSize; StrSize = AsciiStrSize (OptionalStrStart); } while (OptionalStrStart[StrSize] != 0 && Index != 0); if ((Index != 0) || (StrSize == 1)) { // // Meet the end of strings set but Index is non-zero // return EFI_ABORTED; } StringBuffer = AllocatePool (StrSize * sizeof (CHAR16)); if (StringBuffer == NULL) { return EFI_OUT_OF_RESOURCES; } AsciiStrToUnicodeStrS (OptionalStrStart, StringBuffer, StrSize); *String = StringBuffer; return EFI_SUCCESS; } /** Update Memory Infomation. @param SUBrowser Setup utility bowser data point @retval EFI_SUCCESS If the Memory Infomation could be successfully updated. @retval Other Failed to update Memory Infomation. **/ EFI_STATUS UpdateMemoryInfo ( IN SETUP_UTILITY_BROWSER_DATA *SUBrowser ) { EFI_HII_HANDLE LocalMainHiiHandle; EFI_HII_HANDLE LocalAdvanceHiiHandle; EFI_STATUS Status; Status = gBS->LocateProtocol (&gEfiHiiStringProtocolGuid, NULL, (VOID **)&mIfrLibHiiString); ASSERT_EFI_ERROR (Status); if (EFI_ERROR (Status)) { return Status; } LocalMainHiiHandle = SUBrowser->SUCInfo->MapTable[MainHiiHandle].HiiHandle; LocalAdvanceHiiHandle = SUBrowser->SUCInfo->MapTable[AdvanceHiiHandle].HiiHandle; Status = CreateRamSlotInfo (LocalAdvanceHiiHandle, LocalMainHiiHandle); return EFI_SUCCESS; } EFI_STATUS DisplayPlatformInfo ( IN SETUP_UTILITY_BROWSER_DATA *SUBrowser ) { EFI_STATUS Status; CHAR16 *StringBuffer; EFI_HII_HANDLE LocalMainHiiHandle; EFI_HII_HANDLE LocalAdvanceHiiHandle; EFI_STRING_ID PlatformInfoTitleString; EFI_STRING_ID PlatformInfoHelp; EFI_STRING_ID BlankString; VOID *StartOpCodeHandle; EFI_IFR_GUID_LABEL *StartLabel; Status = EFI_SUCCESS; StringBuffer = NULL; PlatformInfoHelp = 0; PlatformInfoTitleString = 0; LocalMainHiiHandle = SUBrowser->SUCInfo->MapTable[MainHiiHandle].HiiHandle; LocalAdvanceHiiHandle = SUBrowser->SUCInfo->MapTable[AdvanceHiiHandle].HiiHandle; Status = gBS->LocateProtocol (&gEfiHiiStringProtocolGuid, NULL, (VOID **)&mIfrLibHiiString); ASSERT_EFI_ERROR (Status); // // Allocate space for creation of Buffer // StartOpCodeHandle = HiiAllocateOpCodeHandle (); ASSERT (StartOpCodeHandle != NULL); StartLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (StartOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL)); StartLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL; StartLabel->Number = MAIN_PAGE_PLATFORM_INFO_LABEL; // // In order to prevent to grayout the label MAIN_PAGE_PLATFORM_INFO_LABEL, // the below precedure // NewStringToHandle ( LocalAdvanceHiiHandle, STRING_TOKEN (STR_PLATFORM_CONFIG_FORM_TITLE), LocalMainHiiHandle, &PlatformInfoTitleString ); NewStringToHandle ( LocalAdvanceHiiHandle, STRING_TOKEN (STR_PLATFORM_CONFIG_FORM_HELP), LocalMainHiiHandle, &PlatformInfoHelp ); NewStringToHandle ( LocalAdvanceHiiHandle, STRING_TOKEN (STR_BLANK_STRING), LocalMainHiiHandle, &BlankString ); HiiCreateTextOpCode (StartOpCodeHandle,PlatformInfoTitleString, PlatformInfoHelp, BlankString ); PlatformInfoInit (StartOpCodeHandle, LocalMainHiiHandle, LocalAdvanceHiiHandle); HiiUpdateForm ( LocalMainHiiHandle, NULL, ROOT_FORM_ID, StartOpCodeHandle, NULL ); gBS->FreePool (StringBuffer); HiiFreeOpCodeHandle (StartOpCodeHandle); return Status; } /** Init Platform Infomation Setup Form To display the following Data of platform infomation: 1. CPUID 2. Number of Core 3. Number of Thread per core 4. Microcode Version 5. TXT 6. VT-d 7. VT-x 8. PCH Reversion 9. SA Reversion 10.VBIOS Version 11.EC Version @param [in] OpCodeHandle @param [in] MainHiiHandle @param [in] AdvanceHiiHandle @retval EFI_SUCCESS **/ EFI_STATUS PlatformInfoInit ( IN VOID *OpCodeHandle, IN EFI_HII_HANDLE MainHiiHandle, IN EFI_HII_HANDLE AdvanceHiiHandle ) { EFI_STATUS Status; UINTN Index; CHAR16 *StringDataBuffer; Status = EFI_SUCCESS; StringDataBuffer = NULL; StringDataBuffer = AllocateZeroPool (0x100); if (StringDataBuffer == NULL) { return EFI_OUT_OF_RESOURCES; } for (Index = 0; mDisplayPlatformInfoFunction[Index].DisplayPlatformInfoFunction != NULL; Index++) { if (mDisplayPlatformInfoFunction[Index].Option == DISPLAY_ENABLE) { ZeroMem(StringDataBuffer, 0x100); mDisplayPlatformInfoFunction[Index].DisplayPlatformInfoFunction (OpCodeHandle, MainHiiHandle, AdvanceHiiHandle, StringDataBuffer); } } gBS->FreePool (StringDataBuffer); return Status; }