/** @file This driver parses the mSmbiosMiscDataTable structure and reports any generated data using SMBIOS protocol. Based on files under Nt32Pkg/MiscSubClassPlatformDxe/ Copyright (c) 2021, NUVIA Inc. All rights reserved.
Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.
Copyright (c) 2015, Hisilicon Limited. All rights reserved.
Copyright (c) 2015, Linaro Limited. All rights reserved.
SPDX-License-Identifier: BSD-2-Clause-Patent **/ #include #include #include #include #include #include #include "SmbiosMisc.h" STATIC EFI_HANDLE mSmbiosMiscImageHandle; STATIC EFI_SMBIOS_PROTOCOL *mSmbiosMiscSmbios = NULL; EFI_HII_HANDLE mSmbiosMiscHiiHandle; /** Standard EFI driver point. This driver parses the mSmbiosMiscDataTable structure and reports any generated data using SMBIOS protocol. @param ImageHandle Handle for the image of this driver @param SystemTable Pointer to the EFI System Table @retval EFI_SUCCESS The data was successfully stored. **/ EFI_STATUS EFIAPI SmbiosMiscEntryPoint( IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable ) { UINTN Index; EFI_STATUS EfiStatus; mSmbiosMiscImageHandle = ImageHandle; EfiStatus = gBS->LocateProtocol (&gEfiSmbiosProtocolGuid, NULL, (VOID**)&mSmbiosMiscSmbios); if (EFI_ERROR (EfiStatus)) { DEBUG ((DEBUG_ERROR, "Could not locate SMBIOS protocol. %r\n", EfiStatus)); return EfiStatus; } mSmbiosMiscHiiHandle = HiiAddPackages (&gEfiCallerIdGuid, mSmbiosMiscImageHandle, SmbiosMiscDxeStrings, NULL ); if (mSmbiosMiscHiiHandle == NULL) { return EFI_OUT_OF_RESOURCES; } for (Index = 0; Index < mSmbiosMiscDataTableEntries; ++Index) { // // If the entry have a function pointer, just log the data. // if (mSmbiosMiscDataTable[Index].Function != NULL) { EfiStatus = (*mSmbiosMiscDataTable[Index].Function)(mSmbiosMiscDataTable[Index].RecordData, mSmbiosMiscSmbios ); if (EFI_ERROR(EfiStatus)) { DEBUG ((DEBUG_ERROR, "Misc smbios store error. Index=%d," "ReturnStatus=%r\n", Index, EfiStatus)); return EfiStatus; } } } return EfiStatus; } /** Adds an SMBIOS record. @param Buffer The data for the SMBIOS record. The format of the record is determined by EFI_SMBIOS_TABLE_HEADER.Type. The size of the formatted area is defined by EFI_SMBIOS_TABLE_HEADER.Length and either followed by a double-null (0x0000) or a set of null terminated strings and a null. @param SmbiosHandle A unique handle will be assigned to the SMBIOS record if not NULL. @retval EFI_SUCCESS Record was added. @retval EFI_OUT_OF_RESOURCES Record was not added due to lack of system resources. @retval EFI_ALREADY_STARTED The SmbiosHandle passed in was already in use. **/ EFI_STATUS SmbiosMiscAddRecord ( IN UINT8 *Buffer, IN OUT EFI_SMBIOS_HANDLE *SmbiosHandle OPTIONAL ) { EFI_STATUS Status; EFI_SMBIOS_HANDLE Handle; Handle = SMBIOS_HANDLE_PI_RESERVED; if (SmbiosHandle != NULL) { Handle = *SmbiosHandle; } Status = mSmbiosMiscSmbios->Add ( mSmbiosMiscSmbios, NULL, &Handle, (EFI_SMBIOS_TABLE_HEADER *)Buffer ); if (SmbiosHandle != NULL) { *SmbiosHandle = Handle; } return Status; } /** Fetches the number of handles of the specified SMBIOS type. * * @param SmbiosType The type of SMBIOS record to look for. * * @return The number of handles * **/ STATIC UINTN GetHandleCount ( IN UINT8 SmbiosType ) { UINTN HandleCount; EFI_STATUS Status; EFI_SMBIOS_HANDLE SmbiosHandle; EFI_SMBIOS_TABLE_HEADER *Record; HandleCount = 0; // Iterate through entries to get the number do { Status = mSmbiosMiscSmbios->GetNext (mSmbiosMiscSmbios, &SmbiosHandle, &SmbiosType, &Record, NULL ); if (Status == EFI_SUCCESS) { HandleCount++; } } while (!EFI_ERROR (Status)); return HandleCount; } /** Fetches a list of the specified SMBIOS table types. @param[in] SmbiosType The type of table to fetch @param[out] **HandleArray The array of handles @param[out] *HandleCount Number of handles in the array **/ VOID SmbiosMiscGetLinkTypeHandle( IN UINT8 SmbiosType, OUT SMBIOS_HANDLE **HandleArray, OUT UINTN *HandleCount ) { UINTN Index; EFI_STATUS Status; EFI_SMBIOS_HANDLE SmbiosHandle; EFI_SMBIOS_TABLE_HEADER *Record; if (mSmbiosMiscSmbios == NULL) { return; } SmbiosHandle = SMBIOS_HANDLE_PI_RESERVED; *HandleCount = GetHandleCount (SmbiosType); *HandleArray = AllocateZeroPool (sizeof (SMBIOS_HANDLE) * (*HandleCount)); if (*HandleArray == NULL) { DEBUG ((DEBUG_ERROR, "HandleArray allocate memory resource failed.\n")); *HandleCount = 0; return; } SmbiosHandle = SMBIOS_HANDLE_PI_RESERVED; for (Index = 0; Index < (*HandleCount); Index++) { Status = mSmbiosMiscSmbios->GetNext (mSmbiosMiscSmbios, &SmbiosHandle, &SmbiosType, &Record, NULL ); if (!EFI_ERROR (Status)) { (*HandleArray)[Index] = Record->Handle; } else { break; } } }