From nobody Sat Feb 7 07:12:15 2026 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of groups.io designates 66.175.222.12 as permitted sender) client-ip=66.175.222.12; envelope-from=bounce+27952+43542+1787277+3901457@groups.io; helo=web01.groups.io; Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zoho.com: domain of groups.io designates 66.175.222.12 as permitted sender) smtp.mailfrom=bounce+27952+43542+1787277+3901457@groups.io; dmarc=fail(p=none dis=none) header.from=intel.com ARC-Seal: i=1; a=rsa-sha256; t=1562809506; cv=none; d=zoho.com; s=zohoarc; b=AuhKDFZYPB4TiW0XKhLxJSnD5NiiBoNT9iiUItoWYDj2E8g3SHG1wBOSSDYSwfGQ66bFnbDa9UcpVe3meWgFgRKIGeUE7iin4uZc7GDaMrtYKJSABmvr9D+LXoZbYBBKLLRd7ZmXyylThjhC9yqMwA9ncL72RwejkeZ2B8D5PCA= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com; s=zohoarc; t=1562809506; h=Cc:Date:From:In-Reply-To:List-Id:List-Unsubscribe:Message-ID:Reply-To:References:Sender:Subject:To:ARC-Authentication-Results; bh=5QLR1T7Upqarl95NrT3NBdiQrEJNH58lXHMfiQNMYVc=; b=KuEgiGjOmD3vR9+67ewQkDzP02bJ7Rq1DwDQ2ta9uqYDNE2oaKQK9AMbqhvOtYjXZIpmNTN7RlND597+h37fm6TfK3mwYVML6Z3xbonuCY7TxnkSk2ooRPdhySIMTY+HoDRzQXN4uT6+CwM82dyZ8a4TXIcGgLYH0ZN68W4STaI= ARC-Authentication-Results: i=1; mx.zoho.com; dkim=pass; spf=pass (zoho.com: domain of groups.io designates 66.175.222.12 as permitted sender) smtp.mailfrom=bounce+27952+43542+1787277+3901457@groups.io; dmarc=fail header.from= (p=none dis=none) header.from= Received: from web01.groups.io (web01.groups.io [66.175.222.12]) by mx.zohomail.com with SMTPS id 1562809505985635.046008672207; Wed, 10 Jul 2019 18:45:05 -0700 (PDT) Return-Path: X-Received: from mga17.intel.com (mga17.intel.com [192.55.52.151]) by groups.io with SMTP; Wed, 10 Jul 2019 18:45:04 -0700 X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False X-Received: from orsmga002.jf.intel.com ([10.7.209.21]) by fmsmga107.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 10 Jul 2019 18:45:02 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.63,476,1557212400"; d="scan'208";a="177020300" X-Received: from unknown (HELO lgao4-MOBL1.ccr.corp.intel.com) ([10.239.197.238]) by orsmga002.jf.intel.com with ESMTP; 10 Jul 2019 18:44:57 -0700 From: "Liming Gao" To: devel@edk2.groups.io Cc: Leif Lindholm , Feng Bob C Subject: [edk2-devel] [Patch 6/7] Revert "BaseTools/FCE: Add a tool FCE" Date: Thu, 11 Jul 2019 09:44:39 +0800 Message-Id: <20190711014440.19812-7-liming.gao@intel.com> In-Reply-To: <20190711014440.19812-1-liming.gao@intel.com> References: <20190711014440.19812-1-liming.gao@intel.com> Precedence: Bulk List-Unsubscribe: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,liming.gao@intel.com DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=groups.io; q=dns/txt; s=20140610; t=1562809505; bh=RQMDvvD+hB5k2UrryLTkkPFu14MjW0tfmqjew9tbyLM=; h=Cc:Date:From:Reply-To:Subject:To; b=bRuFyTU1zpdj+lYPkZ/v6sXWdqiIBI3xnzxJL/CM0vZwyJpOEg6M9SoIguo25fQeSUO 2zltiXhc6Zi7OUExjHbrWq/BqgpZH6esCi/DnmfOafW3QlqW810KYXf38Gj3OZFuVJZzp Hkgf8hJ6LPbcFRXSAQfTnysRpotBVcbLo80= X-ZohoMail-DKIM: pass (identity @groups.io) Content-Transfer-Encoding: quoted-printable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" This reverts commit 3c59d94637adbfdd497b5a2c16073c7dc62b669c. There are the concerns on code design and code quality, and request to rewrite FCE, BfmLib and FMMT for the review. Cc: Leif Lindholm Cc: Feng Bob C Signed-off-by: Liming Gao --- BaseTools/Source/C/FCE/BinaryCreate.c | 216 - BaseTools/Source/C/FCE/BinaryParse.c | 1326 ----- BaseTools/Source/C/FCE/Common.c | 2183 -------- BaseTools/Source/C/FCE/Expression.c | 2367 --------- BaseTools/Source/C/FCE/Fce.c | 6449 -------------------= ---- BaseTools/Source/C/FCE/IfrParse.c | 4836 ----------------- BaseTools/Source/C/FCE/MonotonicBasedVariable.c | 874 --- BaseTools/Source/C/FCE/TimeBasedVariable.c | 878 --- BaseTools/Source/C/FCE/Variable.c | 1091 ---- BaseTools/BinWrappers/PosixLike/FCE | 29 - BaseTools/Source/C/FCE/BinaryCreate.h | 157 - BaseTools/Source/C/FCE/BinaryParse.h | 187 - BaseTools/Source/C/FCE/Common.h | 999 ---- BaseTools/Source/C/FCE/Fce.h | 447 -- BaseTools/Source/C/FCE/GNUmakefile | 55 - BaseTools/Source/C/FCE/IfrParse.h | 789 --- BaseTools/Source/C/FCE/Makefile | 19 - BaseTools/Source/C/FCE/MonotonicBasedVariable.h | 162 - BaseTools/Source/C/FCE/TimeBasedVariable.h | 166 - BaseTools/Source/C/FCE/Variable.h | 154 - BaseTools/Source/C/FCE/VariableCommon.h | 55 - BaseTools/Source/C/GNUmakefile | 3 +- BaseTools/Source/C/Makefile | 3 +- 23 files changed, 2 insertions(+), 23443 deletions(-) delete mode 100644 BaseTools/Source/C/FCE/BinaryCreate.c delete mode 100644 BaseTools/Source/C/FCE/BinaryParse.c delete mode 100644 BaseTools/Source/C/FCE/Common.c delete mode 100644 BaseTools/Source/C/FCE/Expression.c delete mode 100644 BaseTools/Source/C/FCE/Fce.c delete mode 100644 BaseTools/Source/C/FCE/IfrParse.c delete mode 100644 BaseTools/Source/C/FCE/MonotonicBasedVariable.c delete mode 100644 BaseTools/Source/C/FCE/TimeBasedVariable.c delete mode 100644 BaseTools/Source/C/FCE/Variable.c delete mode 100755 BaseTools/BinWrappers/PosixLike/FCE delete mode 100644 BaseTools/Source/C/FCE/BinaryCreate.h delete mode 100644 BaseTools/Source/C/FCE/BinaryParse.h delete mode 100644 BaseTools/Source/C/FCE/Common.h delete mode 100644 BaseTools/Source/C/FCE/Fce.h delete mode 100644 BaseTools/Source/C/FCE/GNUmakefile delete mode 100644 BaseTools/Source/C/FCE/IfrParse.h delete mode 100644 BaseTools/Source/C/FCE/Makefile delete mode 100644 BaseTools/Source/C/FCE/MonotonicBasedVariable.h delete mode 100644 BaseTools/Source/C/FCE/TimeBasedVariable.h delete mode 100644 BaseTools/Source/C/FCE/Variable.h delete mode 100644 BaseTools/Source/C/FCE/VariableCommon.h diff --git a/BaseTools/Source/C/FCE/BinaryCreate.c b/BaseTools/Source/C/FCE= /BinaryCreate.c deleted file mode 100644 index 2f36bc2ef3..0000000000 --- a/BaseTools/Source/C/FCE/BinaryCreate.c +++ /dev/null @@ -1,216 +0,0 @@ -/** @file - - The API to create the binary. - - Copyright (c) 2011-2019, Intel Corporation. All rights reserved.
- SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#include "BinaryCreate.h" -#ifndef __GNUC__ -#define GENSEC_RAW "GenSec -s %s \"%s\" -o \"%s\" > NUL" -#else -#define GENSEC_RAW "GenSec -s %s \"%s\" -o \"%s\" > /dev/null" -#endif - -// -// The guid is to for FFS of BFV. -// -EFI_GUID gEfiFfsBfvForMultiPlatformGuid =3D EFI_FFS_BFV_FOR_MULTIPLATFORM_= GUID; -EFI_GUID gEfiFfsBfvForMultiPlatformGuid2 =3D EFI_FFS_BFV_FOR_MULTIPLATFORM= _GUID2; - -/** - Convert a GUID to a string. - - @param[in] Guid Pointer to GUID to print. - - @return The string after convert. -**/ -static -CHAR8 * -LibBfmGuidToStr ( - IN EFI_GUID *Guid -) -{ - CHAR8 * Buffer; - - Buffer =3D NULL; - - if (Guid =3D=3D NULL) { - return NULL; - } - - Buffer =3D (CHAR8 *) malloc (36 + 1); - - if (Buffer =3D=3D NULL) { - return NULL; - } - memset (Buffer, '\0', 36 + 1); - - sprintf ( - Buffer, - "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x", - Guid->Data1, - Guid->Data2, - Guid->Data3, - Guid->Data4[0], - Guid->Data4[1], - Guid->Data4[2], - Guid->Data4[3], - Guid->Data4[4], - Guid->Data4[5], - Guid->Data4[6], - Guid->Data4[7] - ); - - return Buffer; -} - -/** - Create the Ras section in FFS - - @param[in] InputFilePath .efi file, it's optional unless process PE/= TE section. - @param[in] OutputFilePath .te or .pe file - - @retval EFI_SUCCESS - -**/ -EFI_STATUS -CreateRawSection ( - IN CHAR8* InputFilePath, - IN CHAR8* OutputFilePath - ) -{ - INT32 ReturnValue; - CHAR8* SystemCommand; - - SystemCommand =3D NULL; - SystemCommand =3D malloc ( - strlen (GENSEC_RAW) + - strlen ("EFI_SECTION_RAW") + - strlen (InputFilePath) + - strlen (OutputFilePath) + - 1 - ); - if (NULL =3D=3D SystemCommand) { - return EFI_OUT_OF_RESOURCES; - } - sprintf ( - SystemCommand, - GENSEC_RAW, - "EFI_SECTION_RAW", - InputFilePath, - OutputFilePath - ); - ReturnValue =3D system (SystemCommand); - free(SystemCommand); - - if (ReturnValue !=3D 0) { - printf ("Error. Call GenSec failed.\n"); - return EFI_ABORTED; - } - return EFI_SUCCESS; -} - -/** - Create the Ras type of FFS - - @param[in] InputFilePath .efi file, it's optional unless process PE/= TE section. - @param[in] OutputFilePath .te or .pe file - - @retval EFI_SUCCESS - -**/ -EFI_STATUS -CreateRawFfs ( - IN CHAR8** InputFilePaths, - IN CHAR8* OutputFilePath, - IN BOOLEAN SizeOptimized - ) -{ - INT32 ReturnValue; - CHAR8* SystemCommandFormatString; - CHAR8* SystemCommand; - CHAR8* GuidStr; - CHAR8* FilePathFormatStr; - CHAR8* FilePathStr; - UINT32 Index; - UINT32 StrLen; - UINT32 Size; - - SystemCommand =3D NULL; - GuidStr =3D NULL; - FilePathStr =3D NULL; - StrLen =3D 0; - - FilePathFormatStr =3D " -i \""; - - for (Index =3D 0; InputFilePaths[Index] !=3D NULL; Index++) { - Size =3D strlen (FilePathFormatStr) + strlen (InputFilePaths[Index]) += 2; // 2 menas "" " - if (FilePathStr =3D=3D NULL) { - FilePathStr =3D malloc (Size); - if (NULL =3D=3D FilePathStr) { - return EFI_OUT_OF_RESOURCES; - } - } else { - FilePathStr =3D realloc (FilePathStr, StrLen + Size); - if (NULL =3D=3D FilePathStr) { - return EFI_OUT_OF_RESOURCES; - } - } - memset (FilePathStr + StrLen, ' ', Size); - memcpy (FilePathStr + StrLen, FilePathFormatStr, strlen(FilePathFormat= Str)); - memcpy(FilePathStr + StrLen + strlen(FilePathFormatStr), InputFilePath= s[Index], strlen(InputFilePaths[Index])); - StrLen +=3D Size; - *(FilePathStr + StrLen - 2) =3D '\"'; - } - if (FilePathStr =3D=3D NULL) { - return EFI_ABORTED; - } - *(FilePathStr + StrLen - 1)=3D '\0'; - - - if (SizeOptimized) { - GuidStr =3D LibBfmGuidToStr(&gEfiFfsBfvForMultiPlatformGuid2); - } else { - GuidStr =3D LibBfmGuidToStr(&gEfiFfsBfvForMultiPlatformGuid); - } - if (NULL =3D=3D GuidStr) { - free (FilePathStr); - return EFI_OUT_OF_RESOURCES; - } - SystemCommandFormatString =3D "GenFfs -t %s %s -g %s -o \"%s\""; - SystemCommand =3D malloc ( - strlen (SystemCommandFormatString) + - strlen ("EFI_FV_FILETYPE_FREEFORM") + - strlen (FilePathStr) + - strlen (GuidStr) + - strlen (OutputFilePath) + - 1 - ); - if (NULL =3D=3D SystemCommand) { - free (GuidStr); - free (FilePathStr); - return EFI_OUT_OF_RESOURCES; - } - sprintf ( - SystemCommand, - "GenFfs -t %s %s -g %s -o \"%s\"", - "EFI_FV_FILETYPE_FREEFORM",// -t - FilePathStr, // -i - GuidStr, // -g - OutputFilePath // -o - ); - ReturnValue =3D system (SystemCommand); - free(SystemCommand); - free (FilePathStr); - free (GuidStr); - - if (ReturnValue !=3D 0) { - printf ("Error. Call GenFfs failed.\n"); - return EFI_ABORTED; - } - return EFI_SUCCESS; -} - diff --git a/BaseTools/Source/C/FCE/BinaryParse.c b/BaseTools/Source/C/FCE/= BinaryParse.c deleted file mode 100644 index e9f8ee6826..0000000000 --- a/BaseTools/Source/C/FCE/BinaryParse.c +++ /dev/null @@ -1,1326 +0,0 @@ -/** @file - - The API to parse the binary. - - Copyright (c) 2011-2019, Intel Corporation. All rights reserved.
- SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#ifndef __GNUC__ -#include "windows.h" -#else -#include -#include -#include -#endif -#include "BinaryParse.h" -#include "BinaryCreate.h" -#include "VariableCommon.h" -#include "FirmwareVolumeBufferLib.h" - -extern G_EFI_FD_INFO gEfiFdInfo; -extern EFI_HANDLE mParsedGuidedSectionTools; -extern CHAR8 mInputFdName[MAX_FILENAME_LEN]; - -// -// The Guid to sign the position of Vfr and Uni array in FV -// -EFI_GUID gVfrArrayAttractGuid =3D EFI_VFR_ATTRACT= _GUID; -EFI_GUID gUniStrArrayAttractGuid =3D EFI_UNI_STR_ATT= RACT_GUID; -EFI_GUID gEfiSystemNvDataFvGuid =3D EFI_SYSTEM_NVDA= TA_FV_GUID; -EFI_GUID gEfiCrc32GuidedSectionExtractionProtocolGuid =3D EFI_CRC32_GUIDE= D_SECTION_EXTRACTION_PROTOCOL_GUID; - -/** - Converts a three byte length value into a UINT32. - - @param ThreeByteLength Pointer to the first of the 3 byte length. - - @retval Length Size of the section - -**/ -static -UINT32 -Get3ByteLength ( - IN UINT8 *ThreeByteLength - ) -{ - UINT32 Length; - - Length =3D 0; - - if (ThreeByteLength =3D=3D NULL) { - return 0; - } - - Length =3D *((UINT32 *) ThreeByteLength); - Length =3D Length & 0x00FFFFFF; - - return Length; -} - -/** - Generate the unique template filename. -**/ -CHAR8 * -GenTempFile ( - VOID - ) -{ - CHAR8 *TemString; - TemString =3D NULL; -#ifndef __GNUC__ - TemString =3D CloneString (tmpnam (NULL)); -#else - CHAR8 tmp[] =3D "/tmp/fileXXXXXX"; - UINTN Fdtmp; - Fdtmp =3D mkstemp(tmp); - TemString =3D CloneString(tmp); - close(Fdtmp); -#endif - return TemString; -} - -/** - Check whether exist the same Ifr FFS. If not existed, return TRUE. - - @param[in] FfsImage The pointer to the binary. - @param[in] FileSize The size of binary. - - @return The string after convert. -**/ -static -BOOLEAN -NotExistSameFfsIfr ( - IN VOID *FfsImage -) -{ - UINT32 Index; - - Index =3D 0; - - while (gEfiFdInfo.FfsArray[Index] !=3D NULL) { - if (memcmp (gEfiFdInfo.FfsArray[Index], FfsImage, sizeof (EFI_GUID)) = =3D=3D 0) { - return FALSE; - } - Index++; - } - return TRUE; -} - -/** - This function returns the next larger size that meets the alignment - requirement specified. - - @param ActualSize The size. - @param Alignment The desired alignment. - - @retval The Occupied length - -**/ -static -UINT32 -GetOccupiedSize ( - IN UINT32 ActualSize, - IN UINT32 Alignment - ) -{ - UINT32 OccupiedSize; - - OccupiedSize =3D ActualSize; - while ((OccupiedSize & (Alignment - 1)) !=3D 0) { - OccupiedSize++; - } - - return OccupiedSize; -} - - -/** - Parses FFS Sections, and remove the FFS headers. Tis function olny handl= e one efi in this FFS. - - @param SectionBuffer The section base address - @param BufferLength The length of FFS. - @param EfiBufferHeader The structure dual pointer to the efi informat= ions - - @retval EFI_SUCCESS The application exited normally. - @retval EFI_ABORTED An error occurred. - -**/ -EFI_STATUS -ParseSection ( - IN BOOLEAN IsFfsOrEfi, - IN OUT UINT8 *SectionBuffer, - IN UINT32 BufferLength, - IN OUT EFI_SECTION_STRUCT **EfiBufferHeader - ) -{ - UINT32 ParsedLength; - EFI_SECTION_TYPE Type; - UINT8 *Ptr; - UINT32 SectionLength; - UINT8 *CompressedBuffer; - UINT32 CompressedLength; - UINT8 *UncompressedBuffer; - UINT32 UncompressedLength; - UINT8 CompressionType; - DECOMPRESS_FUNCTION DecompressFunction; - GETINFO_FUNCTION GetInfoFunction; - UINT32 ScratchSize; - UINT8 *ScratchBuffer; - EFI_STATUS Status; - UINT32 DstSize; - CHAR8 *ExtractionTool; - CHAR8 *ToolInputFile; - CHAR8 *ToolOutputFile; - CHAR8 *SystemCommandFormatString; - CHAR8 *SystemCommand; - UINT8 *ToolOutputBuffer; - UINT32 ToolOutputLength; - BOOLEAN HasDepexSection; - - Ptr =3D NULL; - SectionLength =3D 0; - CompressedBuffer =3D NULL; - CompressedLength =3D 0; - UncompressedBuffer =3D NULL; - UncompressedLength =3D 0; - CompressionType =3D 0; - ScratchSize =3D 0; - ScratchBuffer =3D NULL; - Status =3D EFI_SUCCESS; - DstSize =3D 0; - ExtractionTool =3D NULL; - ToolInputFile =3D NULL; - ToolOutputFile =3D NULL; - SystemCommandFormatString =3D NULL; - SystemCommand =3D NULL; - - // - // Jump the FFS header - // - if (IsFfsOrEfi) { - SectionBuffer =3D SectionBuffer + sizeof (EFI_FFS_FILE_HEADER); - BufferLength =3D BufferLength - sizeof (EFI_FFS_FILE_HEADER); - } - ParsedLength =3D 0; - HasDepexSection =3D FALSE; - ExtractionTool =3D NULL; - ToolOutputLength =3D 0; - ToolOutputBuffer =3D NULL; - - (*EfiBufferHeader)->Length =3D BufferLength; - - while (ParsedLength < BufferLength) { - Ptr =3D SectionBuffer + ParsedLength; - - SectionLength =3D Get3ByteLength (((EFI_COMMON_SECTION_HEADER *) Ptr)-= >Size); - Type =3D ((EFI_COMMON_SECTION_HEADER *) Ptr)->Type; - - // - // This is sort of an odd check, but is necessary because FFS files are - // padded to a QWORD boundary, meaning there is potentially a whole se= ction - // header worth of 0xFF bytes. - // - if ((SectionLength =3D=3D 0xffffff) && (Type =3D=3D 0xff)) { - ParsedLength +=3D 4; - continue; - } - - switch (Type) { - - case EFI_SECTION_PE32: - case EFI_SECTION_TE: - // - //Got the correct address - // - (*EfiBufferHeader)->BufferBase =3D (UINTN)(Ptr + sizeof (EFI_COMMON_S= ECTION_HEADER)); - return EFI_SUCCESS; - - case EFI_SECTION_RAW: - case EFI_SECTION_PIC: - break; - - case EFI_SECTION_USER_INTERFACE: - HasDepexSection =3D FALSE; - break; - - case EFI_SECTION_FIRMWARE_VOLUME_IMAGE: - case EFI_SECTION_COMPATIBILITY16: - case EFI_SECTION_FREEFORM_SUBTYPE_GUID: - break; - - case EFI_SECTION_PEI_DEPEX: - case EFI_SECTION_DXE_DEPEX: - case EFI_SECTION_SMM_DEPEX: - HasDepexSection =3D TRUE; - break; - - case EFI_SECTION_VERSION: - break; - case EFI_SECTION_COMPRESSION: - UncompressedBuffer =3D NULL; - CompressedLength =3D SectionLength - sizeof (EFI_COMPRESSION_SECT= ION); - UncompressedLength =3D ((EFI_COMPRESSION_SECTION *) Ptr)->Uncompres= sedLength; - CompressionType =3D ((EFI_COMPRESSION_SECTION *) Ptr)->Compressi= onType; - - if (CompressionType =3D=3D EFI_NOT_COMPRESSED) { - if (CompressedLength !=3D UncompressedLength) { - Error ( - NULL, - 0, - 0, - "file is not compressed, but the compressed length does not ma= tch the uncompressed length", - NULL - ); - return EFI_ABORTED; - } - - UncompressedBuffer =3D Ptr + sizeof (EFI_COMPRESSION_SECTION); - } else if (CompressionType =3D=3D EFI_STANDARD_COMPRESSION) { - GetInfoFunction =3D EfiGetInfo; - DecompressFunction =3D EfiDecompress; - CompressedBuffer =3D Ptr + sizeof (EFI_COMPRESSION_SECTION); - - Status =3D GetInfoFunction ( - CompressedBuffer, - CompressedLength, - &DstSize, - &ScratchSize - ); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 0003, "error getting compression info from compr= ession section", NULL); - return EFI_ABORTED; - } - - if (DstSize !=3D UncompressedLength) { - Error (NULL, 0, 0003, "compression error in the compression sect= ion", NULL); - return EFI_ABORTED; - } - - ScratchBuffer =3D malloc (ScratchSize); - if (ScratchBuffer =3D=3D NULL) { - return EFI_ABORTED; - } - UncompressedBuffer =3D malloc (UncompressedLength); - if (UncompressedBuffer =3D=3D NULL) { - free (ScratchBuffer); - return EFI_ABORTED; - } - memset (UncompressedBuffer, 0, UncompressedLength); - - Status =3D DecompressFunction ( - CompressedBuffer, - CompressedLength, - UncompressedBuffer, - UncompressedLength, - ScratchBuffer, - ScratchSize - ); - free (ScratchBuffer); - if (Status !=3D EFI_SUCCESS) { - Error (NULL, 0, 0003, "decompress failed", NULL); - free (UncompressedBuffer); - return EFI_ABORTED; - } - } else { - Error (NULL, 0, 0003, "unrecognized compression type", "type 0x%X"= , CompressionType); - return EFI_ABORTED; - } - - Status =3D ParseSection (FALSE, UncompressedBuffer, UncompressedLeng= th, EfiBufferHeader); - if (Status !=3D EFI_SUCCESS) { - Error (NULL, 0, 0003, "failed to parse section", NULL); - free (UncompressedBuffer); - UncompressedBuffer =3D NULL; - } else { - return EFI_SUCCESS; - } - // - // Store the allocate memory address for UncompressedBuffer - // - if (UncompressedBuffer !=3D NULL) { - (*EfiBufferHeader)->UncompressedBuffer[(*EfiBufferHeader)->UnCompr= essIndex] =3D (UINTN) UncompressedBuffer; - (*EfiBufferHeader)->UnCompressIndex =3D (*EfiBufferHeader)->UnComp= ressIndex + 1; - } - break; - - case EFI_SECTION_GUID_DEFINED: - // - // Decompress failed, and then check for CRC32 sections which we can= handle internally if needed. - // Maybe this section is no-compressed. - // - if (!CompareGuid ( - &((EFI_GUID_DEFINED_SECTION *) Ptr)->SectionDefinitionGuid, - &gEfiCrc32GuidedSectionExtractionProtocolGuid - )) { - // - // CRC32 guided section - // - Status =3D ParseSection ( - FALSE, - SectionBuffer + ((EFI_GUID_DEFINED_SECTION *) Ptr)->Dat= aOffset, - BufferLength - ((EFI_GUID_DEFINED_SECTION *) Ptr)->Data= Offset, - EfiBufferHeader - ); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 0003, "parse of CRC32 GUIDED section failed", NU= LL); - return EFI_ABORTED; - } else { - return EFI_SUCCESS; - } - } else { - ExtractionTool =3D LookupGuidedSectionToolPath ( - mParsedGuidedSectionTools, - &((EFI_GUID_DEFINED_SECTION *) Ptr)->SectionDef= initionGuid - ); - - if (ExtractionTool !=3D NULL) { - ToolInputFile =3D GenTempFile (); - ToolOutputFile =3D GenTempFile (); - // - // Construction 'system' command string - // - SystemCommandFormatString =3D "%s -d -o \"%s\" \"%s\""; - SystemCommand =3D malloc ( - strlen (SystemCommandFormatString) \ - + strlen (ExtractionTool) \ - + strlen (ToolInputFile) \ - + strlen (ToolOutputFile) \ - + 1 - ); - if (SystemCommand =3D=3D NULL) { - free (ExtractionTool); - free (ToolInputFile); - free (ToolOutputFile); - return EFI_ABORTED; - } - sprintf ( - SystemCommand, - "%s -d -o \"%s\" \"%s\"", - ExtractionTool, - ToolOutputFile, - ToolInputFile - ); - free (ExtractionTool); - - Status =3D PutFileImage ( - ToolInputFile, - (CHAR8*) Ptr + ((EFI_GUID_DEFINED_SECTION *) Ptr)->Da= taOffset, - SectionLength - ((EFI_GUID_DEFINED_SECTION *) Ptr)->D= ataOffset - ); - - if (HasDepexSection) { - HasDepexSection =3D FALSE; - } - - system (SystemCommand); - remove (ToolInputFile); - free (ToolInputFile); - ToolInputFile =3D NULL; - free (SystemCommand); - SystemCommand =3D NULL; - - if (EFI_ERROR (Status)) { - Error ("FCE", 0, 0004, "unable to decoded GUIDED section", NUL= L); - free (ToolOutputFile); - return EFI_ABORTED; - } - - Status =3D GetFileImage ( - ToolOutputFile, - (CHAR8 **)&ToolOutputBuffer, - &ToolOutputLength - ); - remove (ToolOutputFile); - free (ToolOutputFile); - ToolOutputFile =3D NULL; - if (EFI_ERROR (Status)) { - return EFI_ABORTED; - } - } - Status =3D ParseSection ( - FALSE, - ToolOutputBuffer, - ToolOutputLength, - EfiBufferHeader - ); - if (EFI_ERROR (Status)) { - Error (NULL, 0, 0003, "parse of decoded GUIDED section failed", = NULL); - return EFI_ABORTED; - } - } - break; - - default: - ; - } - ParsedLength +=3D SectionLength; - // - // We make then next section begin on a 4-byte boundary - // - ParsedLength =3D GetOccupiedSize (ParsedLength, 4); - } - - return EFI_ABORTED; -} - -static -BOOLEAN -GetNextOffset ( - IN UINT8 *Data, - IN EFI_GUID *Guid, - IN UINTN Len, - IN OUT UINTN *Offset - ) -{ - UINTN NextOffset; - if (*Offset >=3D Len || Len - *Offset <=3D sizeof (EFI_GUID)) { - return FALSE; - } - - for (NextOffset =3D *Offset; NextOffset < Len - sizeof (EFI_GUID); NextO= ffset++) { - if (CompareGuid(Guid, (EFI_GUID*)(Data + NextOffset)) =3D=3D 0) { - *Offset =3D NextOffset + sizeof(EFI_GUID); - return TRUE; - } - } - return FALSE; -} - -/** - Get the address by Guid. - - Parse the FFS image, and find the GUID address.There may be some Guids m= atching the - searched Guid. - - @param Fv the Pointer to the image. - @param Guid The Guid need to find. - @param Offset The dual Pointer to the offset. - @param NumOfMatchGuid The number of matching Guid offset. - - @retval EFI_SUCCESS The Search was complete successfully - @return EFI_ABORTED An error occurred -**/ -EFI_STATUS -GetAddressByGuid ( - IN VOID *Fv, - IN EFI_GUID *Guid, - IN UINTN Len, - OUT UINTN **Offset, - OUT UINT8 *NumOfMatchGuid - ) -{ - VOID *LocalFv; - UINT8 Flag; - - EFI_RAW_SECTION* Section; - UINT8 *RawData; - VOID* SectionStart; - UINTN NextOffset; - UINTN Key; - UINTN TotalSectionsSize; - UINTN SecLen; - UINTN SecHdr; - EFI_STATUS Status; - - if( (Fv =3D=3D NULL) || (Fv =3D=3D NULL) || (Guid =3D=3D NULL) || Len = =3D=3D 0 ){ - return EFI_ABORTED; - } - - LocalFv =3D Fv; - Flag =3D 0; - Section =3D NULL; - Key =3D 0; - - if (NumOfMatchGuid !=3D NULL) { - *NumOfMatchGuid =3D 0; - } - - SectionStart =3D (VOID*)((UINTN)LocalFv + FvBufGetFfsHeaderSize(LocalFv)= ); - TotalSectionsSize =3D Len - FvBufGetFfsHeaderSize(LocalFv); - while (TRUE) { - Status =3D FvBufFindNextSection ( - SectionStart, - TotalSectionsSize, - &Key, - (VOID **)&Section - ); - if (Section =3D=3D NULL || EFI_ERROR (Status)) { - break; - } - - if (EFI_SECTION_RAW =3D=3D Section->Type) { - if ((*(UINT32 *)Section->Size & 0xffffff) =3D=3D 0xffffff) { - SecLen =3D ((EFI_RAW_SECTION2 *)Section)->ExtendedSize; - SecHdr =3D sizeof(EFI_RAW_SECTION2); - } else { - SecLen =3D *(UINT32 *)Section->Size & 0xffffff; - SecHdr =3D sizeof(EFI_RAW_SECTION); - } - if (SecLen <=3D SecHdr || SecLen - SecHdr < sizeof(EFI_GUID)) { - continue; - } - RawData =3D (UINT8 *)Section + SecHdr; - NextOffset =3D 0; - while (GetNextOffset(RawData, Guid, SecLen - SecHdr, &NextOffset)) { - Flag =3D 1; - if ((NumOfMatchGuid !=3D NULL) && (Offset !=3D NULL)) { - if (*NumOfMatchGuid =3D=3D 0) { - *Offset =3D malloc (sizeof (UINTN) * MAX_MATCH_GUID_NUM); - if (*Offset =3D=3D NULL) { - return EFI_ABORTED; - } - memset (*Offset, 0, sizeof (UINTN) * MAX_MATCH_GUID_NUM); - } - *(*Offset + *NumOfMatchGuid) =3D NextOffset + (RawData - (UINT8 = *)Fv); - (*NumOfMatchGuid)++; - } else { - return EFI_SUCCESS; - } - } - } - } - - if( Flag =3D=3D 0 ) { - return EFI_ABORTED; - } - return EFI_SUCCESS; -} - -/** - Search the VfrBin Base address. - - According the known GUID gVfrArrayAttractGuid to get the base address fr= om FFS. - - @param Fv the Pointer to the FFS - @param EfiAddr the Pointer to the EFI in FFS - @param Length the length of Fv - @param Offset the Pointer to the Addr (Offset) - @param NumOfMachingOffset the number of Addr (Offset) - - @retval EFI_SUCCESS Get the address successfully. -**/ -EFI_STATUS -SearchVfrBinInFFS ( - IN VOID *Fv, - IN VOID *EfiAddr, - IN UINTN Length, - OUT UINTN **Offset, - OUT UINT8 *NumOfMachingOffset - ) -{ - UINTN Index; - EFI_STATUS Status; - UINTN VirOffValue; - - Index =3D 0; - Status =3D EFI_SUCCESS; - VirOffValue =3D 0; - - if ((Fv =3D=3D NULL) || (Offset =3D=3D NULL)) { - return EFI_ABORTED; - } - Status =3D GetAddressByGuid ( - Fv, - &gVfrArrayAttractGuid, - Length, - Offset, - NumOfMachingOffset - ); - if (Status !=3D EFI_SUCCESS) { - return EFI_ABORTED; - } - - while (Index < *NumOfMachingOffset) { - // - // Got the virOffset after the GUID - // - VirOffValue =3D *(UINTN *)((UINTN)Fv + *(*Offset + Index)); - // - //Transfer the offset to the VA address. One modules may own more VfrB= in address. - // - *(*Offset + Index) =3D (UINTN) EfiAddr + VirOffValue; - Index++; - } - return EFI_SUCCESS; -} - -/** - Search the UniBin Base address. - - According the known GUID gUniStrArrayAttractGuid to get the base address= from FFS. - - @param Fv the Pointer to the FFS - @param EfiAddr the Pointer to the EFI in FFS - @param Length the length of Fv - @param Offset the Pointer to the Addr (Offset) - - @retval Base address Get the address successfully. -**/ -EFI_STATUS -SearchUniBinInFFS ( - IN VOID *Fv, - IN VOID *EfiAddr, - IN UINTN Length, - OUT UINTN **Offset - ) -{ - UINT8 NumOfMachingOffset; - EFI_STATUS Status; - UINTN VirOffValue; - - NumOfMachingOffset =3D 0; - Status =3D EFI_SUCCESS; - VirOffValue =3D 0; - - if ((Fv =3D=3D NULL) || (Offset =3D=3D NULL)) { - return EFI_ABORTED; - } - Status =3D GetAddressByGuid ( - Fv, - &gUniStrArrayAttractGuid, - Length, - Offset, - &NumOfMachingOffset - ); - if (Status !=3D EFI_SUCCESS) { - return EFI_ABORTED; - } - // - //Transfer the offset to the VA address. There is only one UniArray in o= ne modules. - // - if (NumOfMachingOffset =3D=3D 1) { - VirOffValue =3D *(UINTN *)((UINTN)Fv + **Offset); - **Offset =3D (UINTN) EfiAddr + VirOffValue; - } else { - printf ("Error. Find more than 1 UniBin in FFS.\n"); - return EFI_ABORTED; - } - - return EFI_SUCCESS; -} - -EFI_STATUS -SearchNvStoreDatabaseInFd( - IN VOID *Fv, - IN UINTN length - ) -{ - EFI_STATUS Status; - UINTN Offset; - PCD_NV_STORE_DEFAULT_BUFFER_HEADER *NvStoreHeader; - Status =3D EFI_SUCCESS; - Offset =3D 0; - if (Fv =3D=3D NULL) { - printf ("The FV is NULL."); - return EFI_ABORTED; - } - while (Offset < (length - sizeof(PCD_NV_STORE_DEFAULT_BUFFER_HEADER))){ - NvStoreHeader =3D (PCD_NV_STORE_DEFAULT_BUFFER_HEADER *)((UINT8*)Fv + = Offset); - if (NvStoreHeader->Signature =3D=3D PCD_NV_STORE_DEFAULT_BUFFER_SIGNAT= URE) { - gEfiFdInfo.ExistNvStoreDatabase =3D TRUE; - gEfiFdInfo.NvStoreDatabase =3D (UINT8 *) NvStoreHeader; - break; - } - Offset++; - } - if (Offset =3D=3D (length - sizeof(PCD_NV_STORE_DEFAULT_BUFFER_HEADER)) = || gEfiFdInfo.ExistNvStoreDatabase !=3D TRUE) { - //printf ("Not found the PcdNvStoreDefaultValueBuffer\n"); - return Status; - } - return Status; -} - -/** - Get the address by Guid. - - Parse the FD image, and find the GUID address.There may be some Guids ma= tching the - searched Guid. - - @param Fv the Pointer to the image. - @param Guid The Guid need to find. - @param Offset The dual Pointer to the offset. - @param NumOfMatchGuid The number of matching Guid offset. - - @retval EFI_SUCCESS The Search was complete successfully - @return EFI_ABORTED An error occurred -**/ -EFI_STATUS -GetVariableAddressByGuid ( - IN VOID *Fv, - IN EFI_GUID *Guid, - IN UINTN Len, - OUT UINTN **Offset, - OUT UINT8 *NumOfMatchGuid - ) -{ - UINTN NextOffset; - UINT8 Flag; - - if( (Fv =3D=3D NULL) || (Fv =3D=3D NULL) || (Guid =3D=3D NULL) ){ - return EFI_ABORTED; - } - - Flag =3D 0; - NextOffset =3D 0; - - if (NumOfMatchGuid !=3D NULL) { - *NumOfMatchGuid =3D 0; - } - while (GetNextOffset(Fv, Guid, Len, &NextOffset)) { - Flag =3D 1; - if (NumOfMatchGuid !=3D NULL && Offset !=3D NULL) { - if (*NumOfMatchGuid =3D=3D 0) { - *Offset =3D malloc (sizeof (UINTN) * MAX_MATCH_GUID_NUM); - if (*Offset =3D=3D NULL) { - return EFI_ABORTED; - } - memset (*Offset, 0, sizeof (UINTN) * MAX_MATCH_GUID_NUM); - } - *(*Offset + *NumOfMatchGuid) =3D NextOffset; - (*NumOfMatchGuid)++; - } else { - return EFI_SUCCESS; - } - } - - if( Flag =3D=3D 0 ) { - return EFI_ABORTED; - } - return EFI_SUCCESS; -} - -/** - Search the EFI Variable Base address. - - According the known GUID gEfiSystemNvDataFvGuid to get the base address = from FFS. - - @param Fv the Pointer to the FFS - @param Length the length of Fv - @param Offset the Pointer to the Addr (Offset) - @param NumOfMachingOffset the number of IFR array in one FFS - - @retval EFI_SUCCESS Get the address successfully. - @retval EFI_ABORTED An error occured. -**/ -EFI_STATUS -SearchEfiVarInFFS ( - IN VOID *Fv, - IN UINTN Length, - OUT UINTN **Offset, - OUT UINT8 *NumOfMachingOffset - ) -{ - EFI_STATUS Status; - UINT8 Index; - - Status =3D EFI_SUCCESS; - Index =3D 0; - - if ((Fv =3D=3D NULL) || (Offset =3D=3D NULL)) { - printf ("The FV or offset is NULL."); - return EFI_ABORTED; - } - Status =3D GetVariableAddressByGuid ( - Fv, - &gEfiSystemNvDataFvGuid, - Length, - Offset, - NumOfMachingOffset - ); - if (Status !=3D EFI_SUCCESS) { - return EFI_ABORTED; - } - // - //Transfer the offset to the VA address. - // - while (Index < *NumOfMachingOffset) { - *(*Offset + Index) =3D (UINTN) Fv + *(*Offset + Index); - Index++; - } - return EFI_SUCCESS; -} - -/** - Parse the Ffs header to get the size. - - @param InputFile The pointer to the input file - @param FvSize The pointer to the file size - - @return EFI_SUCCESS Get the file size successfully -**/ -EFI_STATUS -ReadFfsHeader ( - IN FILE *InputFile, - OUT UINT32 *FvSize - ) -{ - EFI_FFS_FILE_HEADER FfsHeader; - EFI_FV_FILETYPE Type; - - // - // Check input parameters - // - if ((InputFile =3D=3D NULL) || (FvSize =3D=3D NULL)) { - return EFI_ABORTED; - } - // - // Read the header - // - fread ( - &FfsHeader, - sizeof (EFI_FFS_FILE_HEADER), - 1, - InputFile - ); - Type =3D FfsHeader.Type; - - if (Type =3D=3D EFI_FV_FILETYPE_DRIVER) { - *FvSize =3D *(UINT32 *)FfsHeader.Size & 0xffffff; - } else if (Type =3D=3D EFI_FV_FILETYPE_APPLICATION) { - *FvSize =3D *(UINT32 *)FfsHeader.Size & 0xffffff; - } else if (Type =3D=3D EFI_FV_FILETYPE_FREEFORM) { - *FvSize =3D *(UINT32 *)FfsHeader.Size & 0xffffff; - } else { - return EFI_ABORTED; - } - return EFI_SUCCESS; -} - -/* - Read the length of the whole FD - - This function determines the size of the FV. - - @param InputFile The file that contains the FV image. - @param FvSize The size of the FV. - - @retval EFI_SUCCESS The application exited normally. - @retval EFI_ABORTED An error occurred. - -**/ -static -EFI_STATUS -ReadFdHeader ( - IN FILE *InputFile, - OUT UINT32 *FvSize - ) -{ - // - // Check input parameters - // - if ((InputFile =3D=3D NULL) || (FvSize =3D=3D NULL)) { - return EFI_ABORTED; - } - *FvSize =3D 0; - // - // Get the total size of FD file (Fixed the length) - // - fseek(InputFile,0,SEEK_END); - *FvSize =3D ftell(InputFile); - fseek(InputFile,0,SEEK_SET); - - if (*FvSize =3D=3D 0) { - return EFI_ABORTED; - } - return EFI_SUCCESS; -} - -/** - Read the file to memory. - - @param InputFile The file that contains the FV image. - @param Size The size of the file. - - @retval The pointer to the begining position of memory. -**/ -VOID * -ReadFileToMemory ( - IN CHAR8 *FileName, - OUT UINT32 *Size - ) -{ - FILE *InFile; - VOID *Address; - UINT32 BytesRead; - EFI_STATUS Status; - - InFile =3D NULL; - Address =3D NULL; - BytesRead =3D 0; - Status =3D EFI_SUCCESS; - - InFile =3D fopen (FileName,"rb"); - if (InFile =3D=3D NULL) { - return NULL; - } - // - // Determine the size of FV - // - Status =3D ReadFdHeader (InFile, Size); - if (Status !=3D EFI_SUCCESS) { - fclose (InFile); - return NULL; - } - // - // Allocate a buffer for the FV image - // - Address =3D malloc (*Size); - if (Address =3D=3D NULL) { - fclose (InFile); - return NULL; - } - memset (Address, 0, *Size); - // - // Seek to the start of the image, then read the entire FV to the buffer - // - fseek (InFile, 0, SEEK_SET); - BytesRead =3D fread (Address, 1, *Size, InFile); - fclose (InFile); - if ((UINTN) BytesRead !=3D *Size) { - free (Address); - return NULL; - } - return Address; -} - -/** - Search the EFI variables address in Fd. - - Open and read the *.fd to the memory, initialize the global structure. - Update the EFI variables addr and the begining position of memory. - - @retval EFI_SUCCESS Get the address successfully. -**/ -EFI_STATUS -GetEfiVariablesAddr ( - BOOLEAN UqiIsSet - ) -{ - VOID *FdImage; - UINT32 FdSize; - EFI_STATUS Status; - UINTN *EfiVarAddr; - UINT8 NumOfMachingVar; - UINT32 Index; - BOOLEAN GotFlag; - EFI_FIRMWARE_VOLUME_HEADER *Variable; - BOOLEAN AuthencitatedMonotonicOrNot; - BOOLEAN AuthencitatedBasedTimeOrNot; - BOOLEAN NormalOrNot; - - FdImage =3D NULL; - FdSize =3D 0; - Status =3D EFI_SUCCESS; - EfiVarAddr =3D NULL; - NumOfMachingVar =3D 0; - Index =3D 0; - GotFlag =3D TRUE; - Variable =3D NULL; - - FdImage =3D ReadFileToMemory (mInputFdName, &FdSize); - if (FdImage =3D=3D NULL) { - return EFI_ABORTED; - } - if (!UqiIsSet) { - Status =3D SearchNvStoreDatabaseInFd(FdImage, FdSize); - if (EFI_ERROR (Status)) { - return EFI_ABORTED; - } - } - Status =3D SearchEfiVarInFFS ( - FdImage, - FdSize, - &EfiVarAddr, - &NumOfMachingVar - ); - if (EFI_ERROR (Status)) { - return EFI_ABORTED; - } - // - // Check the signature "_FVH" - // - Index =3D 0; - GotFlag =3D FALSE; - - while (Index < NumOfMachingVar) { - Variable =3D (EFI_FIRMWARE_VOLUME_HEADER *)(*(EfiVarAddr + Index) - 0x= 20); - if (Variable->Signature =3D=3D 0x4856465F) { - AuthencitatedMonotonicOrNot =3D CheckMonotonicBasedVarStore ((UINT8= *)Variable + Variable->HeaderLength); - AuthencitatedBasedTimeOrNot =3D CheckTimeBasedVarStoreOrNot ((UINT8= *)Variable + Variable->HeaderLength); - NormalOrNot =3D CheckNormalVarStoreOrNot ((UINT8 *)= Variable + Variable->HeaderLength); - if (AuthencitatedMonotonicOrNot || AuthencitatedBasedTimeOrNot || No= rmalOrNot) { - GotFlag =3D TRUE; - gEfiFdInfo.EfiVariableAddr =3D (UINTN)Variable; - break; - } - } - Index++; - } - free (EfiVarAddr); - if (!GotFlag) { - return EFI_ABORTED; - } - gEfiFdInfo.Fd =3D FdImage; - gEfiFdInfo.FdSize =3D FdSize; - - return EFI_SUCCESS; -} - -/** - Pick up the FFS which includes IFR section. - - Parse all FFS extracted by BfmLib, and save all which includes IFR - Binary to gEfiFdInfo structure. - - @retval EFI_SUCCESS Get the address successfully. - @retval EFI_BUFFER_TOO_SMALL Memory can't be allocated. - @retval EFI_ABORTED Read FFS Failed. -**/ -EFI_STATUS -FindFileInFolder ( - IN CHAR8 *FolderName, - OUT BOOLEAN *ExistStorageInBfv, - OUT BOOLEAN *SizeOptimized -) -{ - CHAR8 *FileName; - CHAR8 *CurFolderName; - EFI_STATUS Status; - UINTN MaxFileNameLen; - UINTN Index; - CHAR8 FileNameArry[MAX_FILENAME_LEN]; - FILE *FfsFile; - UINTN FileSize; - VOID *FfsImage; - UINTN BytesRead; -#ifndef __GNUC__ - HANDLE FindHandle; - WIN32_FIND_DATA FindFileData; -#else - struct dirent *pDirent; - DIR *pDir; -#endif - - FileName =3D NULL; - CurFolderName =3D NULL; - Status =3D EFI_SUCCESS; - MaxFileNameLen =3D 0; - Index =3D 0; - FileSize =3D 0; - BytesRead =3D 0; - FfsImage =3D NULL; - FfsFile =3D NULL; - - MaxFileNameLen =3D strlen (FolderName) + MAX_FILENAME_LEN; - CurFolderName =3D (CHAR8 *)calloc( - strlen (FolderName) + strlen (OS_SEP_STR) + strlen ("= *.*")+ 1, - sizeof(CHAR8) - ); - if (CurFolderName =3D=3D NULL) { - return EFI_BUFFER_TOO_SMALL; - } - strcpy (CurFolderName, FolderName); - strcat (CurFolderName, OS_SEP_STR); - strcat (CurFolderName, "*.*"); - FileName =3D (CHAR8 *)calloc( - MaxFileNameLen, - sizeof(CHAR8) - ); - if (FileName =3D=3D NULL) { - free (CurFolderName); - return EFI_BUFFER_TOO_SMALL; - } - -#ifndef __GNUC__ - if((FindHandle =3D FindFirstFile(CurFolderName, &FindFileData)) !=3D INV= ALID_HANDLE_VALUE){ - do { - memset (FileName, 0, MaxFileNameLen); - if ((strcmp (FindFileData.cFileName, ".") =3D=3D 0) - || (strcmp (FindFileData.cFileName, "..") =3D=3D 0) - ) { - continue; - } - if (strlen(FolderName) + strlen ("\\") + strlen (FindFileData.cFileN= ame) > MAX_FILENAME_LEN - 1) { - Status =3D EFI_ABORTED; - goto Done; - } - snprintf (FileNameArry, MAX_FILENAME_LEN, "%s%c%s", FolderName, OS_S= EP, FindFileData.cFileName); - FfsFile =3D fopen (FileNameArry, "rb"); - if (FfsFile =3D=3D NULL) { - Status =3D EFI_ABORTED; - goto Done; - } - Status =3D ReadFfsHeader (FfsFile, (UINT32 *)&FileSize); - if (EFI_ERROR (Status)) { - fclose (FfsFile); - Status =3D EFI_SUCCESS; - continue; - } - // - // Allocate a buffer for the FFS file - // - FfsImage =3D malloc (FileSize); - if (FfsImage =3D=3D NULL) { - fclose (FfsFile); - Status =3D EFI_BUFFER_TOO_SMALL; - goto Done; - } - // - // Seek to the start of the image, then read the entire FV to the bu= ffer - // - fseek (FfsFile, 0, SEEK_SET); - BytesRead =3D fread (FfsImage, 1, FileSize, FfsFile); - fclose (FfsFile); - - if ((UINTN) BytesRead !=3D FileSize) { - free (FfsImage); - Status =3D EFI_ABORTED; - goto Done; - } - // - // Check whether exists the storage ffs in BFV for multi-platform mo= de - // - if (CompareGuid(&gEfiFfsBfvForMultiPlatformGuid,(EFI_GUID *) FfsImag= e) =3D=3D 0) { - *ExistStorageInBfv =3D TRUE; - *SizeOptimized =3D FALSE; - gEfiFdInfo.StorageFfsInBfv =3D FfsImage; - continue; - } - // - // Check whether exists the optimized storage ffs in BFV for multi-p= latform mode - // - if (CompareGuid(&gEfiFfsBfvForMultiPlatformGuid2,(EFI_GUID *) FfsIma= ge) =3D=3D 0) { - *ExistStorageInBfv =3D TRUE; - *SizeOptimized =3D TRUE; - gEfiFdInfo.StorageFfsInBfv =3D FfsImage; - continue; - } - // - // Check whether current FFS includes IFR - // - Status =3D GetAddressByGuid ( - FfsImage, - &gVfrArrayAttractGuid, - FileSize, - NULL, - NULL - ); - if (EFI_ERROR (Status)) { - free (FfsImage); - Status =3D EFI_SUCCESS; - } else { - // - // Check whether existed same IFR binary. If existed, not insert th= e new one. - // - if (NotExistSameFfsIfr (FfsImage)) { - gEfiFdInfo.FfsArray[Index] =3D FfsImage; - gEfiFdInfo.Length[Index++] =3D FileSize; - } - } - - } while (FindNextFile (FindHandle, &FindFileData)); - FindClose(FindHandle); - } else { - Status =3D EFI_ABORTED; - goto Done; - } - -Done: - free (CurFolderName); - free (FileName); - -#else - if((pDir =3D opendir(FolderName)) !=3D NULL){ - while ((pDirent =3D readdir(pDir)) !=3D NULL){ - memset (FileName, 0, MaxFileNameLen); - if ((strcmp (pDirent->d_name, ".") =3D=3D 0) - || (strcmp (pDirent->d_name, "..") =3D=3D 0) - ) { - continue; - } - sprintf (FileNameArry, "%s%c%s", FolderName, OS_SEP, pDirent->d_name= ); - FfsFile =3D fopen (FileNameArry, "rb"); - Status =3D ReadFfsHeader (FfsFile, (UINT32 *)&FileSize); - if (EFI_ERROR (Status)) { - fclose (FfsFile); - Status =3D EFI_SUCCESS; - continue; - } - // - // Allocate a buffer for the FFS file - // - FfsImage =3D malloc (FileSize); - if (FfsImage =3D=3D NULL) { - fclose (FfsFile); - Status =3D EFI_BUFFER_TOO_SMALL; - goto Done; - } - // - // Seek to the start of the image, then read the entire FV to the bu= ffer - // - fseek (FfsFile, 0, SEEK_SET); - BytesRead =3D fread (FfsImage, 1, FileSize, FfsFile); - fclose (FfsFile); - - if ((UINTN) BytesRead !=3D FileSize) { - free (FfsImage); - Status =3D EFI_ABORTED; - goto Done; - } - // - // Check whether exists the storage ffs in BFV for multi-platform mo= de - // - if (CompareGuid(&gEfiFfsBfvForMultiPlatformGuid,(EFI_GUID *) FfsImag= e) =3D=3D 0) { - *ExistStorageInBfv =3D TRUE; - *SizeOptimized =3D FALSE; - gEfiFdInfo.StorageFfsInBfv =3D FfsImage; - continue; - } - // - // Check whether exists the optimized storage ffs in BFV for multi-p= latform mode - // - if (CompareGuid(&gEfiFfsBfvForMultiPlatformGuid2,(EFI_GUID *) FfsIma= ge) =3D=3D 0) { - *ExistStorageInBfv =3D TRUE; - *SizeOptimized =3D TRUE; - gEfiFdInfo.StorageFfsInBfv =3D FfsImage; - continue; - } - // - // Check whether current FFS includes IFR - // - Status =3D GetAddressByGuid ( - FfsImage, - &gVfrArrayAttractGuid, - FileSize, - NULL, - NULL - ); - if (EFI_ERROR (Status)) { - free (FfsImage); - Status =3D EFI_SUCCESS; - } else { - // - // Check whether existed same IFR binary. If existed, not insert th= e new one. - // - if (NotExistSameFfsIfr (FfsImage)) { - gEfiFdInfo.FfsArray[Index] =3D FfsImage; - gEfiFdInfo.Length[Index++] =3D FileSize; - } - } - - } - closedir(pDir); - } else { - Status =3D EFI_ABORTED; - goto Done; - } - -Done: - free (CurFolderName); - free (FileName); -#endif - return Status; -} - diff --git a/BaseTools/Source/C/FCE/Common.c b/BaseTools/Source/C/FCE/Commo= n.c deleted file mode 100644 index 9b14a24a9b..0000000000 --- a/BaseTools/Source/C/FCE/Common.c +++ /dev/null @@ -1,2183 +0,0 @@ -/** @file - - Common library. - - Copyright (c) 2011-2019, Intel Corporation. All rights reserved.
- SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ -#include "Common.h" - -#define WARNING_STATUS_NUMBER 4 -#define ERROR_STATUS_NUMBER 24 - -CONST CHAR8 mHexStr[] =3D {'0','1','2','3','4','5','6','7','8','9','A','B'= ,'C','D','E','F'}; - -CONST CHAR8 *mStatusString[] =3D { - "Success", // RETURN_SUCCESS =3D 0 - "Warning Unknown Glyph", // RETURN_WARN_UNKNOWN_GLYPH =3D 1 - "Warning Delete Failure", // RETURN_WARN_DELETE_FAILURE =3D 2 - "Warning Write Failure", // RETURN_WARN_WRITE_FAILURE =3D 3 - "Warning Buffer Too Small", // RETURN_WARN_BUFFER_TOO_SMALL =3D 4 - "Load Error", // RETURN_LOAD_ERROR =3D 1 = | MAX_BIT - "Invalid Parameter", // RETURN_INVALID_PARAMETER =3D 2 = | MAX_BIT - "Unsupported", // RETURN_UNSUPPORTED =3D 3 = | MAX_BIT - "Bad Buffer Size", // RETURN_BAD_BUFFER_SIZE =3D 4 = | MAX_BIT - "Buffer Too Small", // RETURN_BUFFER_TOO_SMALL, =3D 5 = | MAX_BIT - "Not Ready", // RETURN_NOT_READY =3D 6 = | MAX_BIT - "Device Error", // RETURN_DEVICE_ERROR =3D 7 = | MAX_BIT - "Write Protected", // RETURN_WRITE_PROTECTED =3D 8 = | MAX_BIT - "Out of Resources", // RETURN_OUT_OF_RESOURCES =3D 9 = | MAX_BIT - "Volume Corrupt", // RETURN_VOLUME_CORRUPTED =3D 10= | MAX_BIT - "Volume Full", // RETURN_VOLUME_FULL =3D 11= | MAX_BIT - "No Media", // RETURN_NO_MEDIA =3D 12= | MAX_BIT - "Media changed", // RETURN_MEDIA_CHANGED =3D 13= | MAX_BIT - "Not Found", // RETURN_NOT_FOUND =3D 14= | MAX_BIT - "Access Denied", // RETURN_ACCESS_DENIED =3D 15= | MAX_BIT - "No Response", // RETURN_NO_RESPONSE =3D 16= | MAX_BIT - "No mapping", // RETURN_NO_MAPPING =3D 17= | MAX_BIT - "Time out", // RETURN_TIMEOUT =3D 18= | MAX_BIT - "Not started", // RETURN_NOT_STARTED =3D 19= | MAX_BIT - "Already started", // RETURN_ALREADY_STARTED =3D 20= | MAX_BIT - "Aborted", // RETURN_ABORTED =3D 21= | MAX_BIT - "ICMP Error", // RETURN_ICMP_ERROR =3D 22= | MAX_BIT - "TFTP Error", // RETURN_TFTP_ERROR =3D 23= | MAX_BIT - "Protocol Error" // RETURN_PROTOCOL_ERROR =3D 24= | MAX_BIT -}; - -/** - Copies one Null-terminated Unicode string to another Null-terminated Uni= code - string and returns the new Unicode string. - - This function copies the contents of the Unicode string Source to the Un= icode - string Destination, and returns Destination. If Source and Destination - overlap, then the results are undefined. - - If Destination is NULL, then return NULL. - If Destination is not aligned on a 16-bit boundary, then return NULL. - - @param Destination A pointer to a Null-terminated Unicode string. - @param Source A pointer to a Null-terminated Unicode string. - - @return Destination. - -**/ -CHAR16 * -StrCpy ( - OUT CHAR16 *Destination, - IN CONST CHAR16 *Source - ) -{ - CHAR16 *ReturnValue; - - ReturnValue =3D NULL; - - if ((Destination =3D=3D NULL) || ((UINTN) Destination % 2 !=3D 0)) { - return NULL; - } - - ReturnValue =3D Destination; - while (*Source !=3D 0) { - *(Destination++) =3D *(Source++); - } - *Destination =3D 0; - return ReturnValue; -} - -/** - Returns the length of a Null-terminated Unicode string. - - This function returns the number of Unicode characters in the Null-termi= nated - Unicode string specified by String. - - If String is NULL, then return 0. - - @param String A pointer to a Null-terminated Unicode string. - - @return The length of String. - -**/ -UINTN -FceStrLen ( - IN CONST CHAR16 *String - ) -{ - UINTN Length; - - if (String =3D=3D NULL) { - return 0; - } - for (Length =3D 0; *String !=3D L'\0'; String++, Length++) { - ; - } - return Length; -} - -/** - Returns the size of a Null-terminated Unicode string in bytes, including= the - Null terminator. - - This function returns the size, in bytes, of the Null-terminated Unicode= string - specified by String. - - If String is NULL, then ASSERT(). - If String is not aligned on a 16-bit boundary, then ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and String contains more t= han - PcdMaximumUnicodeStringLength Unicode characters, not including the - Null-terminator, then ASSERT(). - - @param String A pointer to a Null-terminated Unicode string. - - @return The size of String. - -**/ -UINTN -FceStrSize ( - IN CONST CHAR16 *String - ) -{ - return (FceStrLen (String) + 1) * sizeof (*String); -} - -/** - Compares two Null-terminated Unicode strings, and returns the difference - between the first mismatched Unicode characters. - - This function compares the Null-terminated Unicode string FirstString to= the - Null-terminated Unicode string SecondString. If FirstString is identical= to - SecondString, then 0 is returned. Otherwise, the value returned is the f= irst - mismatched Unicode character in SecondString subtracted from the first - mismatched Unicode character in FirstString. - - @param FirstString A pointer to a Null-terminated Unicode string. - @param SecondString A pointer to a Null-terminated Unicode string. - - @retval 0 FirstString is identical to SecondString. - @return others FirstString is not identical to SecondString. - -**/ -INTN -FceStrCmp ( - IN CONST CHAR16 *FirstString, - IN CONST CHAR16 *SecondString - ) -{ - while ((*FirstString !=3D L'\0') && (*FirstString =3D=3D *SecondString))= { - FirstString++; - SecondString++; - } - return *FirstString - *SecondString; -} - -/** - Concatenates one Null-terminated Unicode string to another Null-terminat= ed - Unicode string, and returns the concatenated Unicode string. - - This function concatenates two Null-terminated Unicode strings. The cont= ents - of Null-terminated Unicode string Source are concatenated to the end of - Null-terminated Unicode string Destination. The Null-terminated concaten= ated - Unicode String is returned. If Source and Destination overlap, then the - results are undefined. - - If Destination is NULL, then ASSERT(). - If Destination is not aligned on a 16-bit boundary, then ASSERT(). - If Source is NULL, then ASSERT(). - If Source is not aligned on a 16-bit boundary, then ASSERT(). - If Source and Destination overlap, then ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and Destination contains m= ore - than PcdMaximumUnicodeStringLength Unicode characters, not including the - Null-terminator, then ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and Source contains more t= han - PcdMaximumUnicodeStringLength Unicode characters, not including the - Null-terminator, then ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and concatenating Destinat= ion - and Source results in a Unicode string with more than - PcdMaximumUnicodeStringLength Unicode characters, not including the - Null-terminator, then ASSERT(). - - @param Destination A pointer to a Null-terminated Unicode string. - @param Source A pointer to a Null-terminated Unicode string. - - @return Destination. - -**/ -CHAR16 * -StrCat ( - IN OUT CHAR16 *Destination, - IN CONST CHAR16 *Source - ) -{ - StrCpy (Destination + FceStrLen (Destination), Source); - - // - // Size of the resulting string should never be zero. - // PcdMaximumUnicodeStringLength is tested inside FceStrLen(). - // - ASSERT (FceStrSize (Destination) !=3D 0); - return Destination; -} - -/** - Returns the first occurrence of a Null-terminated Unicode sub-string - in a Null-terminated Unicode string. - - This function scans the contents of the Null-terminated Unicode string - specified by String and returns the first occurrence of SearchString. - If SearchString is not found in String, then NULL is returned. If - the length of SearchString is zero, then String is - returned. - - If String is NULL, then ASSERT(). - If String is not aligned on a 16-bit boundary, then ASSERT(). - If SearchString is NULL, then ASSERT(). - If SearchString is not aligned on a 16-bit boundary, then ASSERT(). - - If PcdMaximumUnicodeStringLength is not zero, and SearchString - or String contains more than PcdMaximumUnicodeStringLength Unicode - characters, not including the Null-terminator, then ASSERT(). - - @param String A pointer to a Null-terminated Unicode string. - @param SearchString A pointer to a Null-terminated Unicode string to= search for. - - @retval NULL If the SearchString does not appear in String. - @return others If there is a match. - -**/ -CHAR16 * -StrStr ( - IN CONST CHAR16 *String, - IN CONST CHAR16 *SearchString - ) -{ - CONST CHAR16 *FirstMatch; - CONST CHAR16 *SearchStringTmp; - - // - // ASSERT both strings are less long than PcdMaximumUnicodeStringLength. - // Length tests are performed inside FceStrLen(). - // - ASSERT (FceStrSize (String) !=3D 0); - ASSERT (FceStrSize (SearchString) !=3D 0); - - if (*SearchString =3D=3D L'\0') { - return (CHAR16 *) String; - } - - while (*String !=3D L'\0') { - SearchStringTmp =3D SearchString; - FirstMatch =3D String; - - while ((*String =3D=3D *SearchStringTmp) - && (*String !=3D L'\0')) { - String++; - SearchStringTmp++; - } - - if (*SearchStringTmp =3D=3D L'\0') { - return (CHAR16 *) FirstMatch; - } - - if (*String =3D=3D L'\0') { - return NULL; - } - - String =3D FirstMatch + 1; - } - - return NULL; -} - -/** - Convert one Null-terminated ASCII string to a Null-terminated - Unicode string and returns the Unicode string. - - This function converts the contents of the ASCII string Source to the Un= icode - string Destination, and returns Destination. The function terminates the - Unicode string Destination by appending a Null-terminator character at t= he end. - The caller is responsible to make sure Destination points to a buffer wi= th size - equal or greater than ((AsciiStrLen (Source) + 1) * sizeof (CHAR16)) in = bytes. - - @param Source A pointer to a Null-terminated ASCII string. - @param Destination A pointer to a Null-terminated Unicode string. - - @return Destination. - @return NULL If Destination or Source is NULL, return NULL. - -**/ -CHAR16 * -AsciiStrToUnicodeStr ( - IN CONST CHAR8 *Source, - OUT CHAR16 *Destination - ) -{ - CHAR16 *ReturnValue; - - ReturnValue =3D NULL; - - if ((Destination =3D=3D NULL) || (Source =3D=3D NULL) || (strlen (Source= ) =3D=3D 0)) { - return NULL; - } - ReturnValue =3D Destination; - while (*Source !=3D '\0') { - *(Destination++) =3D (CHAR16) *(Source++); - } - // - // End the Destination with a NULL. - // - *Destination =3D '\0'; - - return ReturnValue; -} - -/** - Internal function that convert a number to a string in Buffer. - - Print worker function that converts a decimal or hexadecimal number to a= n ASCII string in Buffer. - - @param Buffer Location to place the ASCII string of Value. - @param Value The value to convert to a Decimal or Hexadecimal strin= g in Buffer. - @param Radix Radix of the value - - @return A pointer to the end of buffer filled with ASCII string. - -**/ -CHAR8 * -BasePrintLibValueToString ( - IN OUT CHAR8 *Buffer, - IN INT64 Value, - IN UINTN Radix - ) -{ - UINT32 Remainder; - - // - // Loop to convert one digit at a time in reverse order - // - *Buffer =3D 0; - do { - Value =3D (INT64)DivU64x32Remainder ((UINT64)Value, (UINT32)Radix, &Re= mainder); - *(++Buffer) =3D mHexStr[Remainder]; - } while (Value !=3D 0); - - // - // Return pointer of the end of filled buffer. - // - return Buffer; -} - -/** - Reads a 16-bit value from memory that may be unaligned. - - This function returns the 16-bit value pointed to by Buffer. The function - guarantees that the read operation does not produce an alignment fault. - - If the Buffer is NULL, then ASSERT(). - - @param Buffer A pointer to a 16-bit value that may be unaligned. - - @return The 16-bit value read from Buffer. - -**/ -UINT16 -FceReadUnaligned16 ( - IN CONST UINT16 *Buffer - ) -{ - ASSERT (Buffer !=3D NULL); - - return *Buffer; -} - -/** - Reads a 32-bit value from memory that may be unaligned. - - This function returns the 32-bit value pointed to by Buffer. The function - guarantees that the read operation does not produce an alignment fault. - - If the Buffer is NULL, then ASSERT(). - - @param Buffer A pointer to a 32-bit value that may be unaligned. - - @return The 32-bit value read from Buffer. - -**/ -UINT32 -ReadUnaligned32 ( - IN CONST UINT32 *Buffer - ) -{ - ASSERT (Buffer !=3D NULL); - - return *Buffer; -} - -/** - Internal function that places the character into the Buffer. - - Internal function that places ASCII or Unicode character into the Buffer. - - @param Buffer The buffer to place the Unicode or ASCII string. - @param EndBuffer The end of the input Buffer. No characters will be - placed after that. - @param Length The count of character to be placed into Buffer. - (Negative value indicates no buffer fill.) - @param Character The character to be placed into Buffer. - @param Increment The character increment in Buffer. - - @return Buffer. - -**/ -CHAR8 * -BasePrintLibFillBuffer ( - OUT CHAR8 *Buffer, - IN CHAR8 *EndBuffer, - IN INTN Length, - IN UINTN Character, - IN INTN Increment - ) -{ - INTN Index; - - for (Index =3D 0; Index < Length && Buffer < EndBuffer; Index++) { - *Buffer =3D (CHAR8) Character; - if (Increment !=3D 1) { - *(Buffer + 1) =3D (CHAR8)(Character >> 8); - } - Buffer +=3D Increment; - } - - return Buffer; -} - -/** - Worker function that produces a Null-terminated string in an output buff= er - based on a Null-terminated format string and a VA_LIST argument list. - - VSPrint function to process format and place the results in Buffer. Sinc= e a - VA_LIST is used this routine allows the nesting of Vararg routines. Thus - this is the main print working routine. - - If COUNT_ONLY_NO_PRINT is set in Flags, Buffer will not be modified at a= ll. - - @param[out] Buffer The character buffer to print the results of= the - parsing of Format into. - @param[in] BufferSize The maximum number of characters to put into - buffer. - @param[in] Flags Initial flags value. - Can only have FORMAT_UNICODE, OUTPUT_UNICODE, - and COUNT_ONLY_NO_PRINT set. - @param[in] Format A Null-terminated format string. - @param[in] VaListMarker VA_LIST style variable argument list consume= d by - processing Format. - @param[in] BaseListMarker BASE_LIST style variable argument list consu= med - by processing Format. - - @return The number of characters printed not including the Null-terminat= or. - If COUNT_ONLY_NO_PRINT was set returns the same, but without any - modification to Buffer. - -**/ -UINTN -BasePrintLibSPrintMarker ( - OUT CHAR8 *Buffer, - IN UINTN BufferSize, - IN UINTN Flags, - IN CONST CHAR8 *Format, - IN VA_LIST VaListMarker, OPTIONAL - IN BASE_LIST BaseListMarker OPTIONAL - ) -{ - CHAR8 *OriginalBuffer; - CHAR8 *EndBuffer; - CHAR8 ValueBuffer[MAXIMUM_VALUE_CHARACTERS]; - UINT32 BytesPerOutputCharacter; - UINTN BytesPerFormatCharacter; - UINTN FormatMask; - UINTN FormatCharacter; - UINTN Width; - UINTN Precision; - INT64 Value; - CONST CHAR8 *ArgumentString; - UINTN Character; - EFI_GUID *TmpGuid; - TIME *TmpTime; - UINTN Count; - UINTN ArgumentMask; - INTN BytesPerArgumentCharacter; - UINTN ArgumentCharacter; - BOOLEAN Done; - UINTN Index; - CHAR8 Prefix; - BOOLEAN ZeroPad; - BOOLEAN Comma; - UINTN Digits; - UINTN Radix; - RETURN_STATUS Status; - UINT32 GuidData1; - UINT16 GuidData2; - UINT16 GuidData3; - UINTN LengthToReturn; - - // - // If you change this code be sure to match the 2 versions of this funct= ion. - // Nearly identical logic is found in the BasePrintLib and - // DxePrintLibPrint2Protocol (both PrintLib instances). - // - - if ((Flags & COUNT_ONLY_NO_PRINT) !=3D 0) { - if (BufferSize =3D=3D 0) { - Buffer =3D NULL; - } - } else { - // - // We can run without a Buffer for counting only. - // - if (BufferSize =3D=3D 0) { - return 0; - } - ASSERT (Buffer !=3D NULL); - } - - if ((Flags & OUTPUT_UNICODE) !=3D 0) { - BytesPerOutputCharacter =3D 2; - } else { - BytesPerOutputCharacter =3D 1; - } - - LengthToReturn =3D 0; - - // - // Reserve space for the Null terminator. - // - BufferSize--; - OriginalBuffer =3D Buffer; - - // - // Set the tag for the end of the input Buffer. - // - EndBuffer =3D Buffer + BufferSize * BytesPerOutputCharacter; - - if ((Flags & FORMAT_UNICODE) !=3D 0) { - // - // Make sure format string cannot contain more than PcdMaximumUnicodeS= tringLength - // Unicode characters if PcdMaximumUnicodeStringLength is not zero. - // - ASSERT (FceStrSize ((CHAR16 *) Format) !=3D 0); - BytesPerFormatCharacter =3D 2; - FormatMask =3D 0xffff; - } else { - // - // Make sure format string cannot contain more than PcdMaximumAsciiStr= ingLength - // Ascii characters if PcdMaximumAsciiStringLength is not zero. - // - ASSERT (strlen (Format) + 1 !=3D 0); - BytesPerFormatCharacter =3D 1; - FormatMask =3D 0xff; - } - - // - // Get the first character from the format string - // - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & FormatMa= sk; - - // - // Loop until the end of the format string is reached or the output buff= er is full - // - while (FormatCharacter !=3D 0 && Buffer < EndBuffer) { - // - // Clear all the flag bits except those that may have been passed in - // - Flags &=3D (OUTPUT_UNICODE | FORMAT_UNICODE | COUNT_ONLY_NO_PRINT); - - // - // Set the default width to zero, and the default precision to 1 - // - Width =3D 0; - Precision =3D 1; - Prefix =3D 0; - Comma =3D FALSE; - ZeroPad =3D FALSE; - Count =3D 0; - Digits =3D 0; - - switch (FormatCharacter) { - case '%': - // - // Parse Flags and Width - // - for (Done =3D FALSE; !Done; ) { - Format +=3D BytesPerFormatCharacter; - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & Fo= rmatMask; - switch (FormatCharacter) { - case '.': - Flags |=3D PRECISION; - break; - case '-': - Flags |=3D LEFT_JUSTIFY; - break; - case '+': - Flags |=3D PREFIX_SIGN; - break; - case ' ': - Flags |=3D PREFIX_BLANK; - break; - case ',': - Flags |=3D COMMA_TYPE; - break; - case 'L': - case 'l': - Flags |=3D LONG_TYPE; - break; - case '*': - if ((Flags & PRECISION) =3D=3D 0) { - Flags |=3D PAD_TO_WIDTH; - if (BaseListMarker =3D=3D NULL) { - Width =3D VA_ARG (VaListMarker, UINTN); - } else { - Width =3D BASE_ARG (BaseListMarker, UINTN); - } - } else { - if (BaseListMarker =3D=3D NULL) { - Precision =3D VA_ARG (VaListMarker, UINTN); - } else { - Precision =3D BASE_ARG (BaseListMarker, UINTN); - } - } - break; - case '0': - if ((Flags & PRECISION) =3D=3D 0) { - Flags |=3D PREFIX_ZERO; - } - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - for (Count =3D 0; ((FormatCharacter >=3D '0') && (FormatCharact= er <=3D '9')); ){ - Count =3D (Count * 10) + FormatCharacter - '0'; - Format +=3D BytesPerFormatCharacter; - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) = & FormatMask; - } - Format -=3D BytesPerFormatCharacter; - if ((Flags & PRECISION) =3D=3D 0) { - Flags |=3D PAD_TO_WIDTH; - Width =3D Count; - } else { - Precision =3D Count; - } - break; - - case '\0': - // - // Make no output if Format string terminates unexpectedly when - // looking up for flag, width, precision and type. - // - Format -=3D BytesPerFormatCharacter; - Precision =3D 0; - // - // break skipped on purpose. - // - default: - Done =3D TRUE; - break; - } - } - - // - // Handle each argument type - // - switch (FormatCharacter) { - case 'p': - // - // Flag space, +, 0, L & l are invalid for type p. - // - Flags &=3D ~(PREFIX_BLANK | PREFIX_SIGN | PREFIX_ZERO | LONG_TYPE); - if (sizeof (VOID *) > 4) { - Flags |=3D LONG_TYPE; - } - case 'X': - Flags |=3D PREFIX_ZERO; - // - // break skipped on purpose - // - case 'x': - Flags |=3D RADIX_HEX; - // - // break skipped on purpose - // - case 'd': - if ((Flags & LONG_TYPE) =3D=3D 0) { - // - // 'd','x', and 'X' that are not preceded by 'l' or 'L' are assu= med to be type "int". - // This assumption is made so the format string definition is co= mpatible with the ANSI C - // Specification for formatted strings. It is recommended that = the Base Types be used - // everywhere, but in this one case, compliance with ANSI C is m= ore important, and - // provides an implementation that is compatible with that large= st possible set of CPU - // architectures. This is why the type "int" is used in this on= e case. - // - if (BaseListMarker =3D=3D NULL) { - Value =3D VA_ARG (VaListMarker, int); - } else { - Value =3D BASE_ARG (BaseListMarker, int); - } - } else { - if (BaseListMarker =3D=3D NULL) { - Value =3D VA_ARG (VaListMarker, INT64); - } else { - Value =3D BASE_ARG (BaseListMarker, INT64); - } - } - if ((Flags & PREFIX_BLANK) !=3D 0) { - Prefix =3D ' '; - } - if ((Flags & PREFIX_SIGN) !=3D 0) { - Prefix =3D '+'; - } - if ((Flags & COMMA_TYPE) !=3D 0) { - Comma =3D TRUE; - } - if ((Flags & RADIX_HEX) =3D=3D 0) { - Radix =3D 10; - if (Comma) { - Flags &=3D (~PREFIX_ZERO); - Precision =3D 1; - } - if (Value < 0) { - Flags |=3D PREFIX_SIGN; - Prefix =3D '-'; - Value =3D -Value; - } - } else { - Radix =3D 16; - Comma =3D FALSE; - if ((Flags & LONG_TYPE) =3D=3D 0 && Value < 0) { - // - // 'd','x', and 'X' that are not preceded by 'l' or 'L' are as= sumed to be type "int". - // This assumption is made so the format string definition is = compatible with the ANSI C - // Specification for formatted strings. It is recommended tha= t the Base Types be used - // everywhere, but in this one case, compliance with ANSI C is= more important, and - // provides an implementation that is compatible with that lar= gest possible set of CPU - // architectures. This is why the type "unsigned int" is used= in this one case. - // - Value =3D (unsigned int)Value; - } - } - // - // Convert Value to a reversed string - // - Count =3D BasePrintLibValueToString (ValueBuffer, Value, Radix) - = ValueBuffer; - if (Value =3D=3D 0 && Precision =3D=3D 0) { - Count =3D 0; - } - ArgumentString =3D (CHAR8 *)ValueBuffer + Count; - - Digits =3D Count % 3; - if (Digits !=3D 0) { - Digits =3D 3 - Digits; - } - if (Comma && Count !=3D 0) { - Count +=3D ((Count - 1) / 3); - } - if (Prefix !=3D 0) { - Count++; - Precision++; - } - Flags |=3D ARGUMENT_REVERSED; - ZeroPad =3D TRUE; - if ((Flags & PREFIX_ZERO) !=3D 0) { - if ((Flags & LEFT_JUSTIFY) =3D=3D 0) { - if ((Flags & PAD_TO_WIDTH) !=3D 0) { - if ((Flags & PRECISION) =3D=3D 0) { - Precision =3D Width; - } - } - } - } - break; - - case 's': - case 'S': - Flags |=3D ARGUMENT_UNICODE; - // - // break skipped on purpose - // - case 'a': - if (BaseListMarker =3D=3D NULL) { - ArgumentString =3D VA_ARG (VaListMarker, CHAR8 *); - } else { - ArgumentString =3D BASE_ARG (BaseListMarker, CHAR8 *); - } - if (ArgumentString =3D=3D NULL) { - Flags &=3D (~ARGUMENT_UNICODE); - ArgumentString =3D ""; - } - // - // Set the default precision for string to be zero if not specifie= d. - // - if ((Flags & PRECISION) =3D=3D 0) { - Precision =3D 0; - } - break; - - case 'c': - if (BaseListMarker =3D=3D NULL) { - Character =3D VA_ARG (VaListMarker, UINTN) & 0xffff; - } else { - Character =3D BASE_ARG (BaseListMarker, UINTN) & 0xffff; - } - ArgumentString =3D (CHAR8 *)&Character; - Flags |=3D ARGUMENT_UNICODE; - break; - - case 'g': - if (BaseListMarker =3D=3D NULL) { - TmpGuid =3D VA_ARG (VaListMarker, EFI_GUID *); - } else { - TmpGuid =3D BASE_ARG (BaseListMarker, EFI_GUID *); - } - if (TmpGuid =3D=3D NULL) { - ArgumentString =3D ""; - } else { - GuidData1 =3D ReadUnaligned32 (&(TmpGuid->Data1)); - GuidData2 =3D FceReadUnaligned16 (&(TmpGuid->Data2)); - GuidData3 =3D FceReadUnaligned16 (&(TmpGuid->Data3)); - BasePrintLibSPrint ( - ValueBuffer, - MAXIMUM_VALUE_CHARACTERS, - 0, - "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x", - GuidData1, - GuidData2, - GuidData3, - TmpGuid->Data4[0], - TmpGuid->Data4[1], - TmpGuid->Data4[2], - TmpGuid->Data4[3], - TmpGuid->Data4[4], - TmpGuid->Data4[5], - TmpGuid->Data4[6], - TmpGuid->Data4[7] - ); - ArgumentString =3D ValueBuffer; - } - break; - - case 't': - if (BaseListMarker =3D=3D NULL) { - TmpTime =3D VA_ARG (VaListMarker, TIME *); - } else { - TmpTime =3D BASE_ARG (BaseListMarker, TIME *); - } - if (TmpTime =3D=3D NULL) { - ArgumentString =3D ""; - } else { - BasePrintLibSPrint ( - ValueBuffer, - MAXIMUM_VALUE_CHARACTERS, - 0, - "%02d/%02d/%04d %02d:%02d", - TmpTime->Month, - TmpTime->Day, - TmpTime->Year, - TmpTime->Hour, - TmpTime->Minute - ); - ArgumentString =3D ValueBuffer; - } - break; - - case 'r': - if (BaseListMarker =3D=3D NULL) { - Status =3D VA_ARG (VaListMarker, RETURN_STATUS); - } else { - Status =3D BASE_ARG (BaseListMarker, RETURN_STATUS); - } - ArgumentString =3D ValueBuffer; - if (RETURN_ERROR (Status)) { - // - // Clear error bit - // - Index =3D Status & ~MAX_BIT; - if (Index > 0 && Index <=3D ERROR_STATUS_NUMBER) { - ArgumentString =3D mStatusString [Index + WARNING_STATUS_NUMBE= R]; - } - } else { - Index =3D Status; - if (Index <=3D WARNING_STATUS_NUMBER) { - ArgumentString =3D mStatusString [Index]; - } - } - if (ArgumentString =3D=3D ValueBuffer) { - BasePrintLibSPrint ((CHAR8 *) ValueBuffer, MAXIMUM_VALUE_CHARACT= ERS, 0, "%08X", Status); - } - break; - - case '\r': - Format +=3D BytesPerFormatCharacter; - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & Fo= rmatMask; - if (FormatCharacter =3D=3D '\n') { - // - // Translate '\r\n' to '\r\n' - // - ArgumentString =3D "\r\n"; - } else { - // - // Translate '\r' to '\r' - // - ArgumentString =3D "\r"; - Format -=3D BytesPerFormatCharacter; - } - break; - - case '\n': - // - // Translate '\n' to '\r\n' and '\n\r' to '\r\n' - // - ArgumentString =3D "\r\n"; - Format +=3D BytesPerFormatCharacter; - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & Fo= rmatMask; - if (FormatCharacter !=3D '\r') { - Format -=3D BytesPerFormatCharacter; - } - break; - - case '%': - default: - // - // if the type is '%' or unknown, then print it to the screen - // - ArgumentString =3D (CHAR8 *)&FormatCharacter; - Flags |=3D ARGUMENT_UNICODE; - break; - } - break; - - case '\r': - Format +=3D BytesPerFormatCharacter; - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & Form= atMask; - if (FormatCharacter =3D=3D '\n') { - // - // Translate '\r\n' to '\r\n' - // - ArgumentString =3D "\r\n"; - } else { - // - // Translate '\r' to '\r' - // - ArgumentString =3D "\r"; - Format -=3D BytesPerFormatCharacter; - } - break; - - case '\n': - // - // Translate '\n' to '\r\n' and '\n\r' to '\r\n' - // - ArgumentString =3D "\r\n"; - Format +=3D BytesPerFormatCharacter; - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & Form= atMask; - if (FormatCharacter !=3D '\r') { - Format -=3D BytesPerFormatCharacter; - } - break; - - default: - ArgumentString =3D (CHAR8 *)&FormatCharacter; - Flags |=3D ARGUMENT_UNICODE; - break; - } - - // - // Retrieve the ArgumentString attriubutes - // - if ((Flags & ARGUMENT_UNICODE) !=3D 0) { - ArgumentMask =3D 0xffff; - BytesPerArgumentCharacter =3D 2; - } else { - ArgumentMask =3D 0xff; - BytesPerArgumentCharacter =3D 1; - } - if ((Flags & ARGUMENT_REVERSED) !=3D 0) { - BytesPerArgumentCharacter =3D -BytesPerArgumentCharacter; - } else { - // - // Compute the number of characters in ArgumentString and store it i= n Count - // ArgumentString is either null-terminated, or it contains Precisio= n characters - // - for (Count =3D 0; Count < Precision || ((Flags & PRECISION) =3D=3D 0= ); Count++) { - ArgumentCharacter =3D ((ArgumentString[Count * BytesPerArgumentCha= racter] & 0xff) | ((ArgumentString[Count * BytesPerArgumentCharacter + 1]) = << 8)) & ArgumentMask; - if (ArgumentCharacter =3D=3D 0) { - break; - } - } - } - - if (Precision < Count) { - Precision =3D Count; - } - - // - // Pad before the string - // - if ((Flags & (PAD_TO_WIDTH | LEFT_JUSTIFY)) =3D=3D (PAD_TO_WIDTH)) { - LengthToReturn +=3D ((Width - Precision) * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, Width - Prec= ision, ' ', BytesPerOutputCharacter); - } - } - - if (ZeroPad) { - if (Prefix !=3D 0) { - LengthToReturn +=3D (1 * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, 1, Prefix,= BytesPerOutputCharacter); - } - } - LengthToReturn +=3D ((Precision - Count) * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, Precision - = Count, '0', BytesPerOutputCharacter); - } - } else { - LengthToReturn +=3D ((Precision - Count) * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, Precision - = Count, ' ', BytesPerOutputCharacter); - } - if (Prefix !=3D 0) { - LengthToReturn +=3D (1 * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, 1, Prefix,= BytesPerOutputCharacter); - } - } - } - - // - // Output the Prefix character if it is present - // - Index =3D 0; - if (Prefix !=3D 0) { - Index++; - } - - // - // Copy the string into the output buffer performing the required type= conversions - // - while (Index < Count) { - ArgumentCharacter =3D ((*ArgumentString & 0xff) | (*(ArgumentString = + 1) << 8)) & ArgumentMask; - - LengthToReturn +=3D (1 * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, 1, ArgumentC= haracter, BytesPerOutputCharacter); - } - ArgumentString +=3D BytesPerArgumentCharacter; - Index++; - if (Comma) { - Digits++; - if (Digits =3D=3D 3) { - Digits =3D 0; - Index++; - if (Index < Count) { - LengthToReturn +=3D (1 * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL= ) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, 1, ','= , BytesPerOutputCharacter); - } - } - } - } - } - - // - // Pad after the string - // - if ((Flags & (PAD_TO_WIDTH | LEFT_JUSTIFY)) =3D=3D (PAD_TO_WIDTH | LEF= T_JUSTIFY)) { - LengthToReturn +=3D ((Width - Precision) * BytesPerOutputCharacter); - if ((Flags & COUNT_ONLY_NO_PRINT) =3D=3D 0 && Buffer !=3D NULL) { - Buffer =3D BasePrintLibFillBuffer (Buffer, EndBuffer, Width - Prec= ision, ' ', BytesPerOutputCharacter); - } - } - - // - // Get the next character from the format string - // - Format +=3D BytesPerFormatCharacter; - - // - // Get the next character from the format string - // - FormatCharacter =3D ((*Format & 0xff) | (*(Format + 1) << 8)) & Format= Mask; - } - - if ((Flags & COUNT_ONLY_NO_PRINT) !=3D 0) { - return (LengthToReturn / BytesPerOutputCharacter); - } - - ASSERT (Buffer !=3D NULL); - // - // Null terminate the Unicode or ASCII string - // - BasePrintLibFillBuffer (Buffer, EndBuffer + BytesPerOutputCharacter, 1, = 0, BytesPerOutputCharacter); - // - // Make sure output buffer cannot contain more than PcdMaximumUnicodeStr= ingLength - // Unicode characters if PcdMaximumUnicodeStringLength is not zero. - // - ASSERT ((((Flags & OUTPUT_UNICODE) =3D=3D 0)) || (FceStrSize ((CHAR16 *)= OriginalBuffer) !=3D 0)); - // - // Make sure output buffer cannot contain more than PcdMaximumAsciiStrin= gLength - // ASCII characters if PcdMaximumAsciiStringLength is not zero. - // - ASSERT ((((Flags & OUTPUT_UNICODE) !=3D 0)) || ((strlen (OriginalBuffer)= + 1) !=3D 0)); - - return ((Buffer - OriginalBuffer) / BytesPerOutputCharacter); -} - -/** - Worker function that produces a Null-terminated string in an output buff= er - based on a Null-terminated format string and variable argument list. - - VSPrint function to process format and place the results in Buffer. Sinc= e a - VA_LIST is used this routine allows the nesting of Vararg routines. Thus - this is the main print working routine - - @param StartOfBuffer The character buffer to print the results of the p= arsing - of Format into. - @param BufferSize The maximum number of characters to put into buffe= r. - Zero means no limit. - @param Flags Initial flags value. - Can only have FORMAT_UNICODE and OUTPUT_UNICODE set - @param FormatString A Null-terminated format string. - @param ... The variable argument list. - - @return The number of characters printed. - -**/ -UINTN -BasePrintLibSPrint ( - OUT CHAR8 *StartOfBuffer, - IN UINTN BufferSize, - IN UINTN Flags, - IN CONST CHAR8 *FormatString, - ... - ) -{ - VA_LIST Marker; - - VA_START (Marker, FormatString); - return BasePrintLibSPrintMarker (StartOfBuffer, BufferSize, Flags, Forma= tString, Marker, NULL); -} - -/** - Produces a Null-terminated Unicode string in an output buffer based on - a Null-terminated Unicode format string and a VA_LIST argument list - - Produces a Null-terminated Unicode string in the output buffer specified= by StartOfBuffer - and BufferSize. - The Unicode string is produced by parsing the format string specified by= FormatString. - Arguments are pulled from the variable argument list specified by Marker= based on the - contents of the format string. - The number of Unicode characters in the produced output buffer is return= ed not including - the Null-terminator. - If BufferSize is 0 or 1, then no output buffer is produced and 0 is retu= rned. - - If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). - If BufferSize > 1 and StartOfBuffer is not aligned on a 16-bit boundary,= then ASSERT(). - If BufferSize > 1 and FormatString is NULL, then ASSERT(). - If BufferSize > 1 and FormatString is not aligned on a 16-bit boundary, = then ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and FormatString contains = more than - PcdMaximumUnicodeStringLength Unicode characters not including the Null-= terminator, then - ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and produced Null-terminat= ed Unicode string - contains more than PcdMaximumUnicodeStringLength Unicode characters not = including the - Null-terminator, then ASSERT(). - - @param StartOfBuffer A pointer to the output buffer for the produced = Null-terminated - Unicode string. - @param BufferSize The size, in bytes, of the output buffer specifi= ed by StartOfBuffer. - @param FormatString A Null-terminated Unicode format string. - @param Marker VA_LIST marker for the variable argument list. - - @return The number of Unicode characters in the produced output buffer n= ot including the - Null-terminator. - -**/ -UINTN -UnicodeVSPrint ( - OUT CHAR16 *StartOfBuffer, - IN UINTN BufferSize, - IN CONST CHAR16 *FormatString, - IN VA_LIST Marker - ) -{ - ASSERT_UNICODE_BUFFER (StartOfBuffer); - ASSERT_UNICODE_BUFFER (FormatString); - return BasePrintLibSPrintMarker ((CHAR8 *)StartOfBuffer, BufferSize >> 1= , FORMAT_UNICODE | OUTPUT_UNICODE, (CHAR8 *)FormatString, Marker, NULL); -} - -/** - Produces a Null-terminated Unicode string in an output buffer based on a= Null-terminated - Unicode format string and variable argument list. - - Produces a Null-terminated Unicode string in the output buffer specified= by StartOfBuffer - and BufferSize. - The Unicode string is produced by parsing the format string specified by= FormatString. - Arguments are pulled from the variable argument list based on the conten= ts of the format string. - The number of Unicode characters in the produced output buffer is return= ed not including - the Null-terminator. - If BufferSize is 0 or 1, then no output buffer is produced and 0 is retu= rned. - - If BufferSize > 1 and StartOfBuffer is NULL, then ASSERT(). - If BufferSize > 1 and StartOfBuffer is not aligned on a 16-bit boundary,= then ASSERT(). - If BufferSize > 1 and FormatString is NULL, then ASSERT(). - If BufferSize > 1 and FormatString is not aligned on a 16-bit boundary, = then ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and FormatString contains = more than - PcdMaximumUnicodeStringLength Unicode characters not including the Null-= terminator, then - ASSERT(). - If PcdMaximumUnicodeStringLength is not zero, and produced Null-terminat= ed Unicode string - contains more than PcdMaximumUnicodeStringLength Unicode characters not = including the - Null-terminator, then ASSERT(). - - @param StartOfBuffer A pointer to the output buffer for the produced = Null-terminated - Unicode string. - @param BufferSize The size, in bytes, of the output buffer specifi= ed by StartOfBuffer. - @param FormatString A Null-terminated Unicode format string. - @param ... Variable argument list whose contents are access= ed based on the - format string specified by FormatString. - - @return The number of Unicode characters in the produced output buffer n= ot including the - Null-terminator. - -**/ -UINTN -UnicodeSPrint ( - OUT CHAR16 *StartOfBuffer, - IN UINTN BufferSize, - IN CONST CHAR16 *FormatString, - ... - ) -{ - VA_LIST Marker; - - VA_START (Marker, FormatString); - return UnicodeVSPrint (StartOfBuffer, BufferSize, FormatString, Marker); -} - -/** - Convert a Null-terminated Unicode string to a Null-terminated - ASCII string and returns the ASCII string. - - This function converts the content of the Unicode string Source - to the ASCII string Destination by copying the lower 8 bits of - each Unicode character. It returns Destination. The function terminates - the ASCII string Destination by appending a Null-terminator character - at the end. The caller is responsible to make sure Destination points - to a buffer with size equal or greater than (FceStrLen (Source) + 1) in = bytes. - - If Destination is NULL, then ASSERT(). - If Source is NULL, then ASSERT(). - If Source is not aligned on a 16-bit boundary, then ASSERT(). - If Source and Destination overlap, then ASSERT(). - - If any Unicode characters in Source contain non-zero value in - the upper 8 bits, then ASSERT(). - - @param Source Pointer to a Null-terminated Unicode string. - @param Destination Pointer to a Null-terminated ASCII string. - - @reture Destination - -**/ -CHAR8 * -UnicodeStrToAsciiStr ( - IN CONST CHAR16 *Source, - OUT CHAR8 *Destination - ) -{ - CHAR8 *ReturnValue; - - ReturnValue =3D Destination; - assert (Destination !=3D NULL); - assert (Source !=3D NULL); - assert (((UINTN) Source & 0x01) =3D=3D 0); - - while (*Source !=3D L'\0') { - // - // If any Unicode characters in Source contain - // non-zero value in the upper 8 bits, then ASSERT(). - // - assert (*Source < 0x100); - *(ReturnValue++) =3D (CHAR8) *(Source++); - } - - *ReturnValue =3D '\0'; - - return Destination; -} - -/** - Allocate new memory and then copy the Unicode string Source to Destinati= on. - - @param Dest Location to copy string - @param Src String to copy - -**/ -VOID -NewStringCpy ( - IN OUT CHAR16 **Dest, - IN CHAR16 *Src - ) -{ - if (*Dest !=3D NULL) { - FreePool (*Dest); - } - *Dest =3D FceAllocateCopyPool (FceStrSize (Src), Src); - ASSERT (*Dest !=3D NULL); -} - -/** - Check if a Unicode character is a decimal character. - - This internal function checks if a Unicode character is a - decimal character. The valid decimal character is from - L'0' to L'9'. - - @param Char The character to check against. - - @retval TRUE If the Char is a decmial character. - @retval FALSE If the Char is not a decmial character. - -**/ -BOOLEAN -FceInternalIsDecimalDigitCharacter ( - IN CHAR16 Char - ) -{ - return (BOOLEAN) ((Char >=3D L'0') && (Char <=3D L'9')); -} - -/** - Convert a Unicode character to upper case only if - it maps to a valid small-case ASCII character. - - This internal function only deal with Unicode character - which maps to a valid small-case ASCII character, i.e. - L'a' to L'z'. For other Unicode character, the input character - is returned directly. - - @param Char The character to convert. - - @retval LowerCharacter If the Char is with range L'a' to L'z'. - @retval Unchanged Otherwise. - -**/ -CHAR16 -FceInternalCharToUpper ( - IN CHAR16 Char - ) -{ - if ((Char >=3D L'a') && (Char <=3D L'z')) { - return (CHAR16) (Char - (L'a' - L'A')); - } - - return Char; -} - -/** - Convert a Unicode character to numerical value. - - This internal function only deal with Unicode character - which maps to a valid hexadecimal ASII character, i.e. - L'0' to L'9', L'a' to L'f' or L'A' to L'F'. For other - Unicode character, the value returned does not make sense. - - @param Char The character to convert. - - @return The numerical value converted. - -**/ -UINTN -FceInternalHexCharToUintn ( - IN CHAR16 Char - ) -{ - if (FceInternalIsDecimalDigitCharacter (Char)) { - return Char - L'0'; - } - - return (UINTN) (10 + FceInternalCharToUpper (Char) - L'A'); -} - -/** - Check if a Unicode character is a hexadecimal character. - - This internal function checks if a Unicode character is a - decimal character. The valid hexadecimal character is - L'0' to L'9', L'a' to L'f', or L'A' to L'F'. - - - @param Char The character to check against. - - @retval TRUE If the Char is a hexadecmial character. - @retval FALSE If the Char is not a hexadecmial character. - -**/ -BOOLEAN -FceInternalIsHexaDecimalDigitCharacter ( - IN CHAR16 Char - ) -{ - - return (BOOLEAN) (FceInternalIsDecimalDigitCharacter (Char) || - ((Char >=3D L'A') && (Char <=3D L'F')) || - ((Char >=3D L'a') && (Char <=3D L'f'))); -} - - -/** - Convert a Null-terminated Unicode decimal string to a value of - type UINT64. - - This function returns a value of type UINT64 by interpreting the contents - of the Unicode string specified by String as a decimal number. The format - of the input Unicode string String is: - - [spaces] [decimal digits]. - - The valid decimal digit character is in the range [0-9]. The - function will ignore the pad space, which includes spaces or - tab characters, before [decimal digits]. The running zero in the - beginning of [decimal digits] will be ignored. Then, the function - stops at the first character that is a not a valid decimal character - or a Null-terminator, whichever one comes first. - - If String is NULL, then ASSERT(). - If String is not aligned in a 16-bit boundary, then ASSERT(). - If String has only pad spaces, then 0 is returned. - If String has no pad spaces or valid decimal digits, - then 0 is returned. - If the number represented by String overflows according - to the range defined by UINT64, then ASSERT(). - - If PcdMaximumUnicodeStringLength is not zero, and String contains - more than PcdMaximumUnicodeStringLength Unicode characters, not including - the Null-terminator, then ASSERT(). - - @param String A pointer to a Null-terminated Unicode string. - - @retval Value translated from String. - -**/ -UINT64 -FceStrDecimalToUint64 ( - IN CONST CHAR16 *String - ) -{ - UINT64 Result; - - // - // ASSERT String is less long than PcdMaximumUnicodeStringLength. - // Length tests are performed inside FceStrLen(). - // - ASSERT (FceStrSize (String) !=3D 0); - - // - // Ignore the pad spaces (space or tab) - // - while ((*String =3D=3D L' ') || (*String =3D=3D L'\t')) { - String++; - } - - // - // Ignore leading Zeros after the spaces - // - while (*String =3D=3D L'0') { - String++; - } - - Result =3D 0; - - while (FceInternalIsDecimalDigitCharacter (*String)) { - // - // If the number represented by String overflows according - // to the range defined by UINTN, then ASSERT(). - // - ASSERT (Result <=3D DivU64x32 (((UINT64) ~0) - (*String - L'0') , 10)); - - Result =3D MultU64x32 (Result, 10) + (*String - L'0'); - String++; - } - - return Result; -} - - -/** - Convert a Null-terminated Unicode hexadecimal string to a value of type = UINT64. - - This function returns a value of type UINT64 by interpreting the contents - of the Unicode string specified by String as a hexadecimal number. - The format of the input Unicode string String is - - [spaces][zeros][x][hexadecimal digits]. - - The valid hexadecimal digit character is in the range [0-9], [a-f] and [= A-F]. - The prefix "0x" is optional. Both "x" and "X" is allowed in "0x" prefix. - If "x" appears in the input string, it must be prefixed with at least on= e 0. - The function will ignore the pad space, which includes spaces or tab cha= racters, - before [zeros], [x] or [hexadecimal digit]. The running zero before [x] = or - [hexadecimal digit] will be ignored. Then, the decoding starts after [x]= or the - first valid hexadecimal digit. Then, the function stops at the first cha= racter that is - a not a valid hexadecimal character or NULL, whichever one comes first. - - If String is NULL, then ASSERT(). - If String is not aligned in a 16-bit boundary, then ASSERT(). - If String has only pad spaces, then zero is returned. - If String has no leading pad spaces, leading zeros or valid hexadecimal = digits, - then zero is returned. - If the number represented by String overflows according to the range def= ined by - UINT64, then ASSERT(). - - If PcdMaximumUnicodeStringLength is not zero, and String contains more t= han - PcdMaximumUnicodeStringLength Unicode characters, not including the Null= -terminator, - then ASSERT(). - - @param String A pointer to a Null-terminated Unicode string. - - @retval Value translated from String. - -**/ -UINT64 -FceStrHexToUint64 ( - IN CONST CHAR16 *String - ) -{ - UINT64 Result; - - // - // ASSERT String is less long than PcdMaximumUnicodeStringLength. - // Length tests are performed inside FceStrLen(). - // - ASSERT (FceStrSize (String) !=3D 0); - - // - // Ignore the pad spaces (space or tab) - // - while ((*String =3D=3D L' ') || (*String =3D=3D L'\t')) { - String++; - } - - // - // Ignore leading Zeros after the spaces - // - while (*String =3D=3D L'0') { - String++; - } - - if (FceInternalCharToUpper (*String) =3D=3D L'X') { - ASSERT (*(String - 1) =3D=3D L'0'); - if (*(String - 1) !=3D L'0') { - return 0; - } - // - // Skip the 'X' - // - String++; - } - - Result =3D 0; - - while (FceInternalIsHexaDecimalDigitCharacter (*String)) { - // - // If the Hex Number represented by String overflows according - // to the range defined by UINTN, then ASSERT(). - // - ASSERT (Result <=3D RShiftU64 (((UINT64) ~0) - FceInternalHexCharToUin= tn (*String) , 4)); - - Result =3D LShiftU64 (Result, 4); - Result =3D Result + FceInternalHexCharToUintn (*String); - String++; - } - - return Result; -} - - -CHAR16 -ToUpper ( - CHAR16 a - ) -{ - if (('a' <=3D a) && (a <=3D 'z')) { - return (CHAR16) (a - 0x20); - } else { - return a; - } -} - -CHAR16 -ToLower ( - CHAR16 a - ) -{ - if (('A' <=3D a) && (a <=3D 'Z')) { - return (CHAR16) (a + 0x20); - } else { - return a; - } -} - -/** - Performs a case-insensitive comparison between a Null-terminated - Unicode pattern string and a Null-terminated Unicode string. - - @param String - A pointer to a Null-terminated Unicode string. - @param Pattern - A pointer to a Null-terminated Unicode pattern string. - - - @retval TRUE - Pattern was found in String. - @retval FALSE - Pattern was not found in String. - -**/ -BOOLEAN -MetaiMatch ( - IN CHAR16 *String, - IN CHAR16 *Pattern - ) -{ - CHAR16 c; - CHAR16 p; - - assert (String !=3D NULL); - assert (Pattern !=3D NULL); - - for (;;) { - p =3D *Pattern; - Pattern +=3D 1; - - if (p =3D=3D 0) { - // - // End of pattern. If end of string, TRUE match - // - if (*String) { - return FALSE; - } else { - return TRUE; - } - - } else { - - c =3D *String; - if (ToUpper (c) !=3D ToUpper (p)) { - return FALSE; - } - - String +=3D 1; - - } - - } - -} -/** - Multiplies a 64-bit unsigned integer by a 32-bit unsigned integer and - generates a 64-bit unsigned result. - - This function multiplies the 64-bit unsigned value Multiplicand by the 3= 2-bit - unsigned value Multiplier and generates a 64-bit unsigned result. This 6= 4- - bit unsigned result is returned. - - @param Multiplicand A 64-bit unsigned value. - @param Multiplier A 32-bit unsigned value. - - @return Multiplicand * Multiplier. - -**/ -UINT64 -MultU64x32 ( - IN UINT64 Multiplicand, - IN UINT32 Multiplier - ) -{ - return Multiplicand * Multiplier; -} - -/** - Divides a 64-bit unsigned integer by a 32-bit unsigned integer and gener= ates - a 64-bit unsigned result. - - This function divides the 64-bit unsigned value Dividend by the 32-bit - unsigned value Divisor and generates a 64-bit unsigned quotient. This - function returns the 64-bit unsigned quotient. - - If Divisor is 0, then ASSERT(). - - @param Dividend A 64-bit unsigned value. - @param Divisor A 32-bit unsigned value. - - @return Dividend / Divisor - -**/ -UINT64 -DivU64x32 ( - IN UINT64 Dividend, - IN UINT32 Divisor - ) -{ - ASSERT (Divisor !=3D 0); - return Dividend / Divisor; -} - -/** - Shifts a 64-bit integer left between 0 and 63 bits. The low bits are fil= led - with zeros. The shifted value is returned. - - This function shifts the 64-bit value Operand to the left by Count bits.= The - low Count bits are set to zero. The shifted value is returned. - - If Count is greater than 63, then ASSERT(). - - @param Operand The 64-bit operand to shift left. - @param Count The number of bits to shift left. - - @return Operand << Count. - -**/ -UINT64 -LShiftU64 ( - IN UINT64 Operand, - IN UINTN Count - ) -{ - ASSERT (Count < 64); - return Operand << Count; -} - -/** - Shifts a 64-bit integer right between 0 and 63 bits. This high bits are - filled with zeros. The shifted value is returned. - - This function shifts the 64-bit value Operand to the right by Count bits= . The - high Count bits are set to zero. The shifted value is returned. - - If Count is greater than 63, then ASSERT(). - - @param Operand The 64-bit operand to shift right. - @param Count The number of bits to shift right. - - @return Operand >> Count. - -**/ -UINT64 -RShiftU64 ( - IN UINT64 Operand, - IN UINTN Count - ) - -{ - ASSERT (Count < 64); - return Operand >> Count; -} - - -/** - Divides a 64-bit unsigned integer by a 32-bit unsigned integer and gener= ates - a 64-bit unsigned result and an optional 32-bit unsigned remainder. - - This function divides the 64-bit unsigned value Dividend by the 32-bit - unsigned value Divisor and generates a 64-bit unsigned quotient. If Rema= inder - is not NULL, then the 32-bit unsigned remainder is returned in Remainder. - This function returns the 64-bit unsigned quotient. - - If Divisor is 0, then ASSERT(). - - @param Dividend A 64-bit unsigned value. - @param Divisor A 32-bit unsigned value. - @param Remainder A pointer to a 32-bit unsigned value. This parameter is - optional and may be NULL. - - @return Dividend / Divisor - -**/ -UINT64 -DivU64x32Remainder ( - IN UINT64 Dividend, - IN UINT32 Divisor, - OUT UINT32 *Remainder - ) -{ - ASSERT (Divisor !=3D 0); - - if (Remainder !=3D NULL) { - *Remainder =3D (UINT32)(Dividend % Divisor); - } - return Dividend / Divisor; -} - -/** - Copies a buffer to an allocated buffer. - - Allocates the number bytes specified by AllocationSize, copies allocatio= nSize bytes - from Buffer to the newly allocated buffer, and returns a pointer to the = allocated - buffer. If AllocationSize is 0, then a valid buffer of 0 size is return= ed. If there - is not enough memory remaining to satisfy the request, then NULL is retu= rned. - - If Buffer is NULL, then ASSERT(). - - @param AllocationSize The number of bytes to allocate and zero. - @param Buffer The buffer to copy to the allocated buffer. - - @return A pointer to the allocated buffer or NULL if allocation fails. - -**/ -VOID * -FceAllocateCopyPool ( - IN UINTN AllocationSize, - IN CONST VOID *Buffer - ) -{ - VOID *Memory; - - Memory =3D NULL; - - if ((Buffer =3D=3D NULL) || (AllocationSize =3D=3D 0)) { - return Memory; - } - - Memory =3D calloc (AllocationSize, sizeof (CHAR8)); - if (Memory !=3D NULL) { - Memory =3D memcpy (Memory, Buffer, AllocationSize); - } - return Memory; -} - -/** - Initializes the head node of a doubly-linked list, and returns the point= er to - the head node of the doubly-linked list. - - Initializes the forward and backward links of a new linked list. After - initializing a linked list with this function, the other linked list - functions may be used to add and remove nodes from the linked list. It i= s up - to the caller of this function to allocate the memory for ListHead. - - If ListHead is NULL, then ASSERT(). - - @param ListHead A pointer to the head node of a new doubly-linked list. - - @return ListHead - -**/ -LIST_ENTRY * -InitializeListHead ( - IN OUT LIST_ENTRY *ListHead - ) - -{ - assert (ListHead !=3D NULL); - - ListHead->ForwardLink =3D ListHead; - ListHead->BackLink =3D ListHead; - return ListHead; -} - -/** - Adds a node to the beginning of a doubly-linked list, and returns the po= inter - to the head node of the doubly-linked list. - - Adds the node Entry at the beginning of the doubly-linked list denoted by - ListHead, and returns ListHead. - - If ListHead is NULL, then ASSERT(). - If Entry is NULL, then ASSERT(). - If ListHead was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and prior to insertion the num= ber - of nodes in ListHead, including the ListHead node, is greater than or - equal to PcdMaximumLinkedListLength, then ASSERT(). - - @param ListHead A pointer to the head node of a doubly-linked list. - @param Entry A pointer to a node that is to be inserted at the begi= nning - of a doubly-linked list. - - @return ListHead - -**/ -LIST_ENTRY * -InsertHeadList ( - IN OUT LIST_ENTRY *ListHead, - IN OUT LIST_ENTRY *Entry - ) -{ - assert ((ListHead !=3D NULL) && (Entry !=3D NULL)); - - Entry->ForwardLink =3D ListHead->ForwardLink; - Entry->BackLink =3D ListHead; - Entry->ForwardLink->BackLink =3D Entry; - ListHead->ForwardLink =3D Entry; - return ListHead; -} - -/** - Adds a node to the end of a doubly-linked list, and returns the pointer = to - the head node of the doubly-linked list. - - Adds the node Entry to the end of the doubly-linked list denoted by List= Head, - and returns ListHead. - - If ListHead is NULL, then ASSERT(). - If Entry is NULL, then ASSERT(). - If ListHead was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and prior to insertion the num= ber - of nodes in ListHead, including the ListHead node, is greater than or - equal to PcdMaximumLinkedListLength, then ASSERT(). - - @param ListHead A pointer to the head node of a doubly-linked list. - @param Entry A pointer to a node that is to be added at the end of = the - doubly-linked list. - - @return ListHead - -**/ -LIST_ENTRY * -InsertTailList ( - IN OUT LIST_ENTRY *ListHead, - IN OUT LIST_ENTRY *Entry - ) -{ - assert ((ListHead !=3D NULL) && (Entry !=3D NULL)); - - Entry->ForwardLink =3D ListHead; - Entry->BackLink =3D ListHead->BackLink; - Entry->BackLink->ForwardLink =3D Entry; - ListHead->BackLink =3D Entry; - return ListHead; -} - -/** - Retrieves the first node of a doubly-linked list. - - Returns the first node of a doubly-linked list. List must have been - initialized with INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead(). - If List is empty, then List is returned. - - If List is NULL, then ASSERT(). - If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and the number of nodes - in List, including the List node, is greater than or equal to - PcdMaximumLinkedListLength, then ASSERT(). - - @param List A pointer to the head node of a doubly-linked list. - - @return The first node of a doubly-linked list. - @retval NULL The list is empty. - -**/ -LIST_ENTRY * -GetFirstNode ( - IN CONST LIST_ENTRY *List - ) -{ - assert (List !=3D NULL); - - return List->ForwardLink; -} - -/** - Retrieves the next node of a doubly-linked list. - - Returns the node of a doubly-linked list that follows Node. - List must have been initialized with INTIALIZE_LIST_HEAD_VARIABLE() - or InitializeListHead(). If List is empty, then List is returned. - - If List is NULL, then ASSERT(). - If Node is NULL, then ASSERT(). - If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and List contains more than - PcdMaximumLinkedListLenth nodes, then ASSERT(). - If PcdVerifyNodeInList is TRUE and Node is not a node in List, then ASSE= RT(). - - @param List A pointer to the head node of a doubly-linked list. - @param Node A pointer to a node in the doubly-linked list. - - @return A pointer to the next node if one exists. Otherwise List is retu= rned. - -**/ -LIST_ENTRY * -GetNextNode ( - IN CONST LIST_ENTRY *List, - IN CONST LIST_ENTRY *Node - ) -{ - assert ((List !=3D NULL) && (Node !=3D NULL)); - - return Node->ForwardLink; -} - -/** - Retrieves the previous node of a doubly-linked list. - - Returns the node of a doubly-linked list that precedes Node. - List must have been initialized with INTIALIZE_LIST_HEAD_VARIABLE() - or InitializeListHead(). If List is empty, then List is returned. - - If List is NULL, then ASSERT(). - If Node is NULL, then ASSERT(). - If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and List contains more than - PcdMaximumLinkedListLenth nodes, then ASSERT(). - If PcdVerifyNodeInList is TRUE and Node is not a node in List, then ASSE= RT(). - - @param List A pointer to the head node of a doubly-linked list. - @param Node A pointer to a node in the doubly-linked list. - - @return A pointer to the previous node if one exists. Otherwise List is = returned. - -**/ -LIST_ENTRY * -GetPreviousNode ( - IN CONST LIST_ENTRY *List, - IN CONST LIST_ENTRY *Node - ) -{ - assert ((List !=3D NULL) && (Node !=3D NULL)); - - return Node->BackLink; -} - -/** - Checks to see if a doubly-linked list is empty or not. - - Checks to see if the doubly-linked list is empty. If the linked list con= tains - zero nodes, this function returns TRUE. Otherwise, it returns FALSE. - - If ListHead is NULL, then ASSERT(). - If ListHead was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and the number of nodes - in List, including the List node, is greater than or equal to - PcdMaximumLinkedListLength, then ASSERT(). - - @param ListHead A pointer to the head node of a doubly-linked list. - - @retval TRUE The linked list is empty. - @retval FALSE The linked list is not empty. - -**/ -BOOLEAN -IsListEmpty ( - IN CONST LIST_ENTRY *ListHead - ) -{ - assert (ListHead !=3D NULL); - - return (BOOLEAN)(ListHead->ForwardLink =3D=3D ListHead); -} - -/** - Determines if a node in a doubly-linked list is the head node of a the s= ame - doubly-linked list. This function is typically used to terminate a loop= that - traverses all the nodes in a doubly-linked list starting with the head n= ode. - - Returns TRUE if Node is equal to List. Returns FALSE if Node is one of = the - nodes in the doubly-linked list specified by List. List must have been - initialized with INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead(). - - If List is NULL, then ASSERT(). - If Node is NULL, then ASSERT(). - If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or Initi= alizeListHead(), - then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and the number of nodes - in List, including the List node, is greater than or equal to - PcdMaximumLinkedListLength, then ASSERT(). - If PcdVerifyNodeInList is TRUE and Node is not a node in List and Node i= s not - equal to List, then ASSERT(). - - @param List A pointer to the head node of a doubly-linked list. - @param Node A pointer to a node in the doubly-linked list. - - @retval TRUE Node is the head of the doubly-linked list pointed by List. - @retval FALSE Node is not the head of the doubly-linked list pointed by = List. - -**/ -BOOLEAN -IsNull ( - IN CONST LIST_ENTRY *List, - IN CONST LIST_ENTRY *Node - ) -{ - assert ((List !=3D NULL) && (Node !=3D NULL)); - - return (BOOLEAN)(Node =3D=3D List); -} - -/** - Determines if a node the last node in a doubly-linked list. - - Returns TRUE if Node is the last node in the doubly-linked list specifie= d by - List. Otherwise, FALSE is returned. List must have been initialized with - INTIALIZE_LIST_HEAD_VARIABLE() or InitializeListHead(). - - If List is NULL, then ASSERT(). - If Node is NULL, then ASSERT(). - If List was not initialized with INTIALIZE_LIST_HEAD_VARIABLE() or - InitializeListHead(), then ASSERT(). - If PcdMaximumLinkedListLenth is not zero, and the number of nodes - in List, including the List node, is greater than or equal to - PcdMaximumLinkedListLength, then ASSERT(). - If PcdVerifyNodeInList is TRUE and Node is not a node in List, then ASSE= RT(). - - @param List A pointer to the head node of a doubly-linked list. - @param Node A pointer to a node in the doubly-linked list. - - @retval TRUE Node is the last node in the linked list. - @retval FALSE Node is not the last node in the linked list. - -**/ -BOOLEAN -IsNodeAtEnd ( - IN CONST LIST_ENTRY *List, - IN CONST LIST_ENTRY *Node - ) -{ - assert ((List !=3D NULL) && (Node !=3D NULL)); - - return (BOOLEAN)(!IsNull (List, Node) && (List->BackLink =3D=3D Node)); -} - -/** - Removes a node from a doubly-linked list, and returns the node that foll= ows - the removed node. - - Removes the node Entry from a doubly-linked list. It is up to the caller= of - this function to release the memory used by this node if that is require= d. On - exit, the node following Entry in the doubly-linked list is returned. If - Entry is the only node in the linked list, then the head node of the lin= ked - list is returned. - - If Entry is NULL, then ASSERT(). - If Entry is the head node of an empty list, then ASSERT(). - If PcdMaximumLinkedListLength is not zero, and the number of nodes in the - linked list containing Entry, including the Entry node, is greater than - or equal to PcdMaximumLinkedListLength, then ASSERT(). - - @param Entry A pointer to a node in a linked list. - - @return Entry. - -**/ -LIST_ENTRY * -RemoveEntryList ( - IN CONST LIST_ENTRY *Entry - ) -{ - assert (!IsListEmpty (Entry)); - - Entry->ForwardLink->BackLink =3D Entry->BackLink; - Entry->BackLink->ForwardLink =3D Entry->ForwardLink; - return Entry->ForwardLink; -} - diff --git a/BaseTools/Source/C/FCE/Expression.c b/BaseTools/Source/C/FCE/E= xpression.c deleted file mode 100644 index 34b310d97f..0000000000 --- a/BaseTools/Source/C/FCE/Expression.c +++ /dev/null @@ -1,2367 +0,0 @@ -/** @file - - Utility functions for expression evaluation. - - Copyright (c) 2011-2019, Intel Corporation. All rights reserved.
- SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#include "IfrParse.h" - -#define gEmptyString L"" -// -// Global stack used to evaluate boolean expresions -// -EFI_HII_VALUE *mOpCodeScopeStack =3D NULL; -EFI_HII_VALUE *mOpCodeScopeStackEnd =3D NULL; -EFI_HII_VALUE *mOpCodeScopeStackPointer =3D NULL; - -EFI_HII_VALUE *mExpressionEvaluationStack =3D NULL; -EFI_HII_VALUE *mExpressionEvaluationStackEnd =3D NULL; -EFI_HII_VALUE *mExpressionEvaluationStackPointer =3D NULL; -UINTN mExpressionEvaluationStackOffset =3D 0; - -EFI_HII_VALUE *mCurrentExpressionStack =3D NULL; -EFI_HII_VALUE *mCurrentExpressionEnd =3D NULL; -EFI_HII_VALUE *mCurrentExpressionPointer =3D NULL; - -EFI_HII_VALUE *mMapExpressionListStack =3D NULL; -EFI_HII_VALUE *mMapExpressionListEnd =3D NULL; -EFI_HII_VALUE *mMapExpressionListPointer =3D NULL; - -/** - Get Value for given Name from a NameValue Storage. - - @param Storage The NameValue Storage. - @param Name The Name. - @param Value The retured Value. - - @retval EFI_SUCCESS Value found for given Name. - @retval EFI_NOT_FOUND No such Name found in NameValue storage. - -**/ -EFI_STATUS -GetValueByName ( - IN FORMSET_STORAGE *Storage, - IN CHAR16 *Name, - IN OUT CHAR16 **Value - ) -{ - LIST_ENTRY *Link; - NAME_VALUE_NODE *Node; - - *Value =3D NULL; - - Link =3D GetFirstNode (&Storage->NameValueListHead); - while (!IsNull (&Storage->NameValueListHead, Link)) { - Node =3D NAME_VALUE_NODE_FROM_LINK (Link); - - if (FceStrCmp (Name, Node->Name) =3D=3D 0) { - NewStringCpy (Value, Node->EditValue); - return EFI_SUCCESS; - } - - Link =3D GetNextNode (&Storage->NameValueListHead, Link); - } - - return EFI_NOT_FOUND; -} - -/** - Grow size of the stack. - - This is an internal function. - - @param Stack On input: old stack; On output: new stack - @param StackPtr On input: old stack pointer; On output: n= ew stack - pointer - @param StackEnd On input: old stack end; On output: new s= tack end - - @retval EFI_SUCCESS Grow stack success. - @retval EFI_OUT_OF_RESOURCES No enough memory for stack space. - -**/ -EFI_STATUS -GrowStack ( - IN OUT EFI_HII_VALUE **Stack, - IN OUT EFI_HII_VALUE **StackPtr, - IN OUT EFI_HII_VALUE **StackEnd - ) -{ - UINTN Size; - EFI_HII_VALUE *NewStack; - - Size =3D EXPRESSION_STACK_SIZE_INCREMENT; - if (*StackPtr !=3D NULL) { - Size =3D Size + (*StackEnd - *Stack); - } - - NewStack =3D AllocatePool (Size * sizeof (EFI_HII_VALUE)); - if (NewStack =3D=3D NULL) { - return EFI_OUT_OF_RESOURCES; - } - - if (*StackPtr !=3D NULL) { - // - // Copy from Old Stack to the New Stack - // - CopyMem ( - NewStack, - *Stack, - (*StackEnd - *Stack) * sizeof (EFI_HII_VALUE) - ); - - // - // Free The Old Stack - // - FreePool (*Stack); - } - - // - // Make the Stack pointer point to the old data in the new stack - // - *StackPtr =3D NewStack + (*StackPtr - *Stack); - *Stack =3D NewStack; - *StackEnd =3D NewStack + Size; - - return EFI_SUCCESS; -} - - -/** - Push an element onto the Boolean Stack. - - @param Stack On input: old stack; On output: new stack - @param StackPtr On input: old stack pointer; On output: n= ew stack - pointer - @param StackEnd On input: old stack end; On output: new s= tack end - @param Data Data to push. - - @retval EFI_SUCCESS Push stack success. - -**/ -EFI_STATUS -PushStack ( - IN OUT EFI_HII_VALUE **Stack, - IN OUT EFI_HII_VALUE **StackPtr, - IN OUT EFI_HII_VALUE **StackEnd, - IN EFI_HII_VALUE *Data - ) -{ - EFI_STATUS Status; - - // - // Check for a stack overflow condition - // - if (*StackPtr >=3D *StackEnd) { - // - // Grow the stack - // - Status =3D GrowStack (Stack, StackPtr, StackEnd); - if (EFI_ERROR (Status)) { - return Status; - } - } - - // - // Push the item onto the stack - // - CopyMem (*StackPtr, Data, sizeof (EFI_HII_VALUE)); - *StackPtr =3D *StackPtr + 1; - - return EFI_SUCCESS; -} - - -/** - Pop an element from the stack. - - @param Stack On input: old stack - @param StackPtr On input: old stack pointer; On output: n= ew stack pointer - @param Data Data to pop. - - @retval EFI_SUCCESS The value was popped onto the stack. - @retval EFI_ACCESS_DENIED The pop operation underflowed the stack - -**/ -EFI_STATUS -PopStack ( - IN EFI_HII_VALUE *Stack, - IN OUT EFI_HII_VALUE **StackPtr, - OUT EFI_HII_VALUE *Data - ) -{ - // - // Check for a stack underflow condition - // - if (*StackPtr =3D=3D Stack) { - return EFI_ACCESS_DENIED; - } - - // - // Pop the item off the stack - // - *StackPtr =3D *StackPtr - 1; - CopyMem (Data, *StackPtr, sizeof (EFI_HII_VALUE)); - return EFI_SUCCESS; -} - - -/** - Reset stack pointer to begin of the stack. - -**/ -VOID -ResetCurrentExpressionStack ( - VOID - ) -{ - mCurrentExpressionPointer =3D mCurrentExpressionStack; -} - - -/** - Push current expression onto the Stack - - @param Pointer Pointer to current expression. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the stack. - -**/ -EFI_STATUS -PushCurrentExpression ( - IN VOID *Pointer - ) -{ - EFI_HII_VALUE Data; - - Data.Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - Data.Value.u64 =3D (UINT64) (UINTN) Pointer; - - return PushStack ( - &mCurrentExpressionStack, - &mCurrentExpressionPointer, - &mCurrentExpressionEnd, - &Data - ); -} - - -/** - Pop current expression from the Stack - - @param Pointer Pointer to current expression to be pop. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the stack. - -**/ -EFI_STATUS -PopCurrentExpression ( - OUT VOID **Pointer - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Data; - - Status =3D PopStack ( - mCurrentExpressionStack, - &mCurrentExpressionPointer, - &Data - ); - - *Pointer =3D (VOID *) (UINTN) Data.Value.u64; - - return Status; -} - -/** - Reset stack pointer to begin of the stack. - -**/ -VOID -ResetMapExpressionListStack ( - VOID - ) -{ - mMapExpressionListPointer =3D mMapExpressionListStack; -} - - -/** - Push the list of map expression onto the Stack - - @param Pointer Pointer to the list of map expression to = be pushed. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the stack. - -**/ -EFI_STATUS -PushMapExpressionList ( - IN VOID *Pointer - ) -{ - EFI_HII_VALUE Data; - - Data.Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - Data.Value.u64 =3D (UINT64) (UINTN) Pointer; - - return PushStack ( - &mMapExpressionListStack, - &mMapExpressionListPointer, - &mMapExpressionListEnd, - &Data - ); -} - - -/** - Pop the list of map expression from the Stack - - @param Pointer Pointer to the list of map expression to = be pop. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the stack. - -**/ -EFI_STATUS -PopMapExpressionList ( - OUT VOID **Pointer - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Data; - - Status =3D PopStack ( - mMapExpressionListStack, - &mMapExpressionListPointer, - &Data - ); - - *Pointer =3D (VOID *) (UINTN) Data.Value.u64; - - return Status; -} - -/** - Reset stack pointer to begin of the stack. - -**/ -VOID -ResetScopeStack ( - VOID - ) -{ - mOpCodeScopeStackPointer =3D mOpCodeScopeStack; -} - - -/** - Push an Operand onto the Stack - - @param Operand Operand to push. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the - stack. - -**/ -EFI_STATUS -PushScope ( - IN UINT8 Operand - ) -{ - EFI_HII_VALUE Data; - - Data.Type =3D EFI_IFR_TYPE_NUM_SIZE_8; - Data.Value.u8 =3D Operand; - - return PushStack ( - &mOpCodeScopeStack, - &mOpCodeScopeStackPointer, - &mOpCodeScopeStackEnd, - &Data - ); -} - - -/** - Pop an Operand from the Stack - - @param Operand Operand to pop. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the - stack. - -**/ -EFI_STATUS -PopScope ( - OUT UINT8 *Operand - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Data; - - Status =3D PopStack ( - mOpCodeScopeStack, - &mOpCodeScopeStackPointer, - &Data - ); - - *Operand =3D Data.Value.u8; - - return Status; -} - - -/** - Push an Expression value onto the Stack - - @param Value Expression value to push. - - @retval EFI_SUCCESS The value was pushed onto the stack. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the - stack. - -**/ -EFI_STATUS -PushExpression ( - IN EFI_HII_VALUE *Value - ) -{ - return PushStack ( - &mExpressionEvaluationStack, - &mExpressionEvaluationStackPointer, - &mExpressionEvaluationStackEnd, - Value - ); -} - - -/** - Pop an Expression value from the stack. - - @param Value Expression value to pop. - - @retval EFI_SUCCESS The value was popped onto the stack. - @retval EFI_ACCESS_DENIED The pop operation underflowed the stack - -**/ -EFI_STATUS -PopExpression ( - OUT EFI_HII_VALUE *Value - ) -{ - return PopStack ( - mExpressionEvaluationStack + mExpressionEvaluationStackOffset, - &mExpressionEvaluationStackPointer, - Value - ); -} - -/** - Get current stack offset from stack start. - - @return Stack offset to stack start. -**/ -UINTN -SaveExpressionEvaluationStackOffset ( - ) -{ - UINTN TempStackOffset; - TempStackOffset =3D mExpressionEvaluationStackOffset; - mExpressionEvaluationStackOffset =3D mExpressionEvaluationStackPointer -= mExpressionEvaluationStack; - return TempStackOffset; -} - -/** - Restore stack offset based on input stack offset - - @param StackOffset Offset to stack start. - -**/ -VOID -RestoreExpressionEvaluationStackOffset ( - UINTN StackOffset - ) -{ - mExpressionEvaluationStackOffset =3D StackOffset; -} - - -/** - Search a Question in Form scope using its QuestionId. - - @param Form The form which contains this Question. - @param QuestionId Id of this Question. - - @retval Pointer The Question. - @retval NULL Specified Question not found in the form. - -**/ -FORM_BROWSER_STATEMENT * -IdToQuestion2 ( - IN FORM_BROWSER_FORM *Form, - IN UINT16 QuestionId - ) -{ - LIST_ENTRY *Link; - FORM_BROWSER_STATEMENT *Question; - - if (QuestionId =3D=3D 0) { - // - // The value of zero is reserved - // - return NULL; - } - - Link =3D GetFirstNode (&Form->StatementListHead); - while (!IsNull (&Form->StatementListHead, Link)) { - Question =3D FORM_BROWSER_STATEMENT_FROM_LINK (Link); - - if (Question->QuestionId =3D=3D QuestionId) { - return Question; - } - - Link =3D GetNextNode (&Form->StatementListHead, Link); - } - - return NULL; -} - - -/** - Search a Question in Formset scope using its QuestionId. - - @param FormSet The formset which contains this form. - @param Form The form which contains this Question. - @param QuestionId Id of this Question. - - @retval Pointer The Question. - @retval NULL Specified Question not found in the form. - -**/ -FORM_BROWSER_STATEMENT * -IdToQuestion ( - IN FORM_BROWSER_FORMSET *FormSet, - IN FORM_BROWSER_FORM *Form, - IN UINT16 QuestionId - ) -{ - LIST_ENTRY *Link; - FORM_BROWSER_STATEMENT *Question; - - // - // Search in the form scope first - // - Question =3D IdToQuestion2 (Form, QuestionId); - if (Question !=3D NULL) { - return Question; - } - - // - // Search in the formset scope - // - Link =3D GetFirstNode (&FormSet->FormListHead); - while (!IsNull (&FormSet->FormListHead, Link)) { - Form =3D FORM_BROWSER_FORM_FROM_LINK (Link); - - Question =3D IdToQuestion2 (Form, QuestionId); - if (Question !=3D NULL) { - return Question; - } - - Link =3D GetNextNode (&FormSet->FormListHead, Link); - } - - return NULL; -} - - -/** - Get Expression given its RuleId. - - @param Form The form which contains this Expression. - @param RuleId Id of this Expression. - - @retval Pointer The Expression. - @retval NULL Specified Expression not found in the for= m. - -**/ -FORM_EXPRESSION * -RuleIdToExpression ( - IN FORM_BROWSER_FORM *Form, - IN UINT8 RuleId - ) -{ - LIST_ENTRY *Link; - FORM_EXPRESSION *Expression; - - Link =3D GetFirstNode (&Form->ExpressionListHead); - while (!IsNull (&Form->ExpressionListHead, Link)) { - Expression =3D FORM_EXPRESSION_FROM_LINK (Link); - - if ((Expression->Type =3D=3D EFI_HII_EXPRESSION_RULE) && (Expression->= RuleId =3D=3D RuleId)) { - return Expression; - } - - Link =3D GetNextNode (&Form->ExpressionListHead, Link); - } - - return NULL; -} - -/** - Convert the input Unicode character to upper. - - @param String Th Unicode character to be converted. - -**/ -VOID -IfrStrToUpper ( - IN CHAR16 *String - ) -{ - while (*String !=3D 0) { - if ((*String >=3D 'a') && (*String <=3D 'z')) { - *String =3D (UINT16) ((*String) & ((UINT16) ~0x20)); - } - String++; - } -} - -/** - Evaluate opcode EFI_IFR_TO_STRING. - - @param FormSet Formset which contains this opcode. - @param Format String format in EFI_IFR_TO_STRING. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrToString ( - IN FORM_BROWSER_FORMSET *FormSet, - IN UINT8 Format, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *PrintFormat; - CHAR16 Buffer[MAXIMUM_VALUE_CHARACTERS]; - UINTN BufferSize; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - - switch (Value.Type) { - case EFI_IFR_TYPE_NUM_SIZE_8: - case EFI_IFR_TYPE_NUM_SIZE_16: - case EFI_IFR_TYPE_NUM_SIZE_32: - case EFI_IFR_TYPE_NUM_SIZE_64: - BufferSize =3D MAXIMUM_VALUE_CHARACTERS * sizeof (CHAR16); - switch (Format) { - case EFI_IFR_STRING_UNSIGNED_DEC: - case EFI_IFR_STRING_SIGNED_DEC: - PrintFormat =3D L"%ld"; - break; - - case EFI_IFR_STRING_LOWERCASE_HEX: - PrintFormat =3D L"%lx"; - break; - - case EFI_IFR_STRING_UPPERCASE_HEX: - PrintFormat =3D L"%lX"; - break; - - default: - return EFI_UNSUPPORTED; - } - UnicodeSPrint (Buffer, BufferSize, PrintFormat, Value.Value.u64); - break; - - case EFI_IFR_TYPE_STRING: - CopyMem (Result, &Value, sizeof (EFI_HII_VALUE)); - return EFI_SUCCESS; - - case EFI_IFR_TYPE_BOOLEAN: - break; - - default: - return EFI_UNSUPPORTED; - } - - Result->Type =3D EFI_IFR_TYPE_STRING; - //Result->Value.string =3D NewString (String, FormSet->HiiHandle); - return EFI_SUCCESS; -} - -/** - Evaluate opcode EFI_IFR_TO_UINT. - - @param FormSet Formset which contains this opcode. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrToUint ( - IN FORM_BROWSER_FORMSET *FormSet, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String; - CHAR16 *StringPtr; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - - if (Value.Type >=3D EFI_IFR_TYPE_OTHER) { - return EFI_UNSUPPORTED; - } - - Status =3D EFI_SUCCESS; - if (Value.Type =3D=3D EFI_IFR_TYPE_STRING) { - String =3D GetToken (Value.Value.string, FormSet->UnicodeBinary); - if (String =3D=3D NULL) { - return EFI_NOT_FOUND; - } - - IfrStrToUpper (String); - StringPtr =3D StrStr (String, L"0X"); - if (StringPtr !=3D NULL) { - // - // Hex string - // - Result->Value.u64 =3D FceStrHexToUint64 (String); - } else { - // - // decimal string - // - Result->Value.u64 =3D FceStrDecimalToUint64 (String); - } - FreePool (String); - } else { - CopyMem (Result, &Value, sizeof (EFI_HII_VALUE)); - } - - Result->Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - return Status; -} - -/** - Evaluate opcode EFI_IFR_CATENATE. - - @param FormSet Formset which contains this opcode. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrCatenate ( - IN FORM_BROWSER_FORMSET *FormSet, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String[2]; - UINTN Index; - CHAR16 *StringPtr; - UINTN Size; - - // - // String[0] - The second string - // String[1] - The first string - // - String[0] =3D NULL; - String[1] =3D NULL; - StringPtr =3D NULL; - Status =3D EFI_SUCCESS; - - for (Index =3D 0; Index < 2; Index++) { - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - if (Value.Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - String[Index] =3D GetToken (Value.Value.string, FormSet->UnicodeBinary= ); - if (String[Index] =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - } - - Size =3D FceStrSize (String[0]); - StringPtr=3D AllocatePool (FceStrSize (String[1]) + Size); - ASSERT (StringPtr !=3D NULL); - StrCpy (StringPtr, String[1]); - StrCat (StringPtr, String[0]); - - Result->Type =3D EFI_IFR_TYPE_STRING; - //Result->Value.string =3D NewString (StringPtr, FormSet->HiiHandle); - -Done: - if (String[0] !=3D NULL) { - FreePool (String[0]); - } - if (String[1] !=3D NULL) { - FreePool (String[1]); - } - if (StringPtr !=3D NULL) { - FreePool (StringPtr); - } - - return Status; -} - -/** - Evaluate opcode EFI_IFR_MATCH. - - @param FormSet Formset which contains this opcode. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrMatch ( - IN FORM_BROWSER_FORMSET *FormSet, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String[2]; - UINTN Index; - - // - // String[0] - The string to search - // String[1] - pattern - // - String[0] =3D NULL; - String[1] =3D NULL; - Status =3D EFI_SUCCESS; - for (Index =3D 0; Index < 2; Index++) { - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - if (Value.Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - String[Index] =3D GetToken (Value.Value.string, FormSet->UnicodeBinary= ); - if (String [Index] =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - } - - Result->Type =3D EFI_IFR_TYPE_BOOLEAN; - Result->Value.b =3D MetaiMatch (String[0], String[1]); - -Done: - if (String[0] !=3D NULL) { - FreePool (String[0]); - } - if (String[1] !=3D NULL) { - FreePool (String[1]); - } - - return Status; -} - - -/** - Evaluate opcode EFI_IFR_FIND. - - @param FormSet Formset which contains this opcode. - @param Format Case sensitive or insensitive. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrFind ( - IN FORM_BROWSER_FORMSET *FormSet, - IN UINT8 Format, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String[2]; - UINTN Base; - CHAR16 *StringPtr; - UINTN Index; - - if (Format > EFI_IFR_FF_CASE_INSENSITIVE) { - return EFI_UNSUPPORTED; - } - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - if (Value.Type > EFI_IFR_TYPE_NUM_SIZE_64) { - return EFI_UNSUPPORTED; - } - Base =3D (UINTN) Value.Value.u64; - - // - // String[0] - sub-string - // String[1] - The string to search - // - String[0] =3D NULL; - String[1] =3D NULL; - for (Index =3D 0; Index < 2; Index++) { - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - if (Value.Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - String[Index] =3D GetToken (Value.Value.string, FormSet->UnicodeBinary= ); - if (String[Index] =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - if (Format =3D=3D EFI_IFR_FF_CASE_INSENSITIVE) { - // - // Case insensitive, convert both string to upper case - // - IfrStrToUpper (String[Index]); - } - } - - Result->Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - if (Base >=3D FceStrLen (String[1])) { - Result->Value.u64 =3D 0xFFFFFFFFFFFFFFFFULL; - } else { - StringPtr =3D StrStr (String[1] + Base, String[0]); - Result->Value.u64 =3D (StringPtr =3D=3D NULL) ? 0xFFFFFFFFFFFFFFFFULL = : (StringPtr - String[1]); - } - -Done: - if (String[0] !=3D NULL) { - FreePool (String[0]); - } - if (String[1] !=3D NULL) { - FreePool (String[1]); - } - - return Status; -} - - -/** - Evaluate opcode EFI_IFR_MID. - - @param FormSet Formset which contains this opcode. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrMid ( - IN FORM_BROWSER_FORMSET *FormSet, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String; - UINTN Base; - UINTN Length; - CHAR16 *SubString; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - if (Value.Type > EFI_IFR_TYPE_NUM_SIZE_64) { - return EFI_UNSUPPORTED; - } - Length =3D (UINTN) Value.Value.u64; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - if (Value.Type > EFI_IFR_TYPE_NUM_SIZE_64) { - return EFI_UNSUPPORTED; - } - Base =3D (UINTN) Value.Value.u64; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - if (Value.Type !=3D EFI_IFR_TYPE_STRING) { - return EFI_UNSUPPORTED; - } - String =3D GetToken (Value.Value.string, FormSet->UnicodeBinary); - if (String =3D=3D NULL) { - return EFI_NOT_FOUND; - } - - if ((Length =3D=3D 0) || (Base >=3D FceStrLen (String))) { - SubString =3D gEmptyString; - } else { - SubString =3D String + Base; - if ((Base + Length) < FceStrLen (String)) { - SubString[Length] =3D L'\0'; - } - } - - Result->Type =3D EFI_IFR_TYPE_STRING; - //Result->Value.string =3D NewString (SubString, FormSet->HiiHandle); - - FreePool (String); - - return Status; -} - -/** - Evaluate opcode EFI_IFR_TOKEN. - - @param FormSet Formset which contains this opcode. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrToken ( - IN FORM_BROWSER_FORMSET *FormSet, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String[2]; - UINTN Count; - CHAR16 *Delimiter; - CHAR16 *SubString; - CHAR16 *StringPtr; - UINTN Index; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - if (Value.Type > EFI_IFR_TYPE_NUM_SIZE_64) { - return EFI_UNSUPPORTED; - } - Count =3D (UINTN) Value.Value.u64; - - // - // String[0] - Delimiter - // String[1] - The string to search - // - String[0] =3D NULL; - String[1] =3D NULL; - for (Index =3D 0; Index < 2; Index++) { - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - if (Value.Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - String[Index] =3D GetToken (Value.Value.string, FormSet->UnicodeBinary= ); - if (String[Index] =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - } - - Delimiter =3D String[0]; - SubString =3D String[1]; - while (Count > 0) { - SubString =3D StrStr (SubString, Delimiter); - if (SubString !=3D NULL) { - // - // Skip over the delimiter - // - SubString =3D SubString + FceStrLen (Delimiter); - } else { - break; - } - Count--; - } - - if (SubString =3D=3D NULL) { - // - // nth delimited sub-string not found, push an empty string - // - SubString =3D gEmptyString; - } else { - // - // Put a NULL terminator for nth delimited sub-string - // - StringPtr =3D StrStr (SubString, Delimiter); - if (StringPtr !=3D NULL) { - *StringPtr =3D L'\0'; - } - } - - Result->Type =3D EFI_IFR_TYPE_STRING; - //Result->Value.string =3D NewString (SubString, FormSet->HiiHandle); - -Done: - if (String[0] !=3D NULL) { - FreePool (String[0]); - } - if (String[1] !=3D NULL) { - FreePool (String[1]); - } - - return Status; -} - - -/** - Evaluate opcode EFI_IFR_SPAN. - - @param FormSet Formset which contains this opcode. - @param Flags FIRST_MATCHING or FIRST_NON_MATCHING. - @param Result Evaluation result for this opcode. - - @retval EFI_SUCCESS Opcode evaluation success. - @retval Other Opcode evaluation failed. - -**/ -EFI_STATUS -IfrSpan ( - IN FORM_BROWSER_FORMSET *FormSet, - IN UINT8 Flags, - OUT EFI_HII_VALUE *Result - ) -{ - EFI_STATUS Status; - EFI_HII_VALUE Value; - CHAR16 *String[2]; - CHAR16 *Charset; - UINTN Base; - UINTN Index; - CHAR16 *StringPtr; - BOOLEAN Found; - - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - return Status; - } - if (Value.Type > EFI_IFR_TYPE_NUM_SIZE_64) { - return EFI_UNSUPPORTED; - } - Base =3D (UINTN) Value.Value.u64; - - // - // String[0] - Charset - // String[1] - The string to search - // - String[0] =3D NULL; - String[1] =3D NULL; - for (Index =3D 0; Index < 2; Index++) { - Status =3D PopExpression (&Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - if (Value.Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - String[Index] =3D GetToken (Value.Value.string, FormSet->UnicodeBinary= ); - if (String [Index] =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - } - - if (Base >=3D FceStrLen (String[1])) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - Found =3D FALSE; - StringPtr =3D String[1] + Base; - Charset =3D String[0]; - while (*StringPtr !=3D 0 && !Found) { - Index =3D 0; - while (Charset[Index] !=3D 0) { - if ((*StringPtr >=3D Charset[Index]) && (*StringPtr <=3D Charset[Ind= ex + 1])) { - if (Flags =3D=3D EFI_IFR_FLAGS_FIRST_MATCHING) { - Found =3D TRUE; - break; - } - } else { - if (Flags =3D=3D EFI_IFR_FLAGS_FIRST_NON_MATCHING) { - Found =3D TRUE; - break; - } - } - // - // Skip characters pair representing low-end of a range and high-end= of a range - // - Index +=3D 2; - } - - if (!Found) { - StringPtr++; - } - } - - Result->Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - Result->Value.u64 =3D StringPtr - String[1]; - -Done: - if (String[0] !=3D NULL) { - FreePool (String[0]); - } - if (String[1] !=3D NULL) { - FreePool (String[1]); - } - - return Status; -} - - -/** - Zero extend integer/boolean/date/time to UINT64 for comparing. - - @param Value HII Value to be converted. - -**/ -VOID -ExtendValueToU64 ( - IN EFI_HII_VALUE *Value - ) -{ - UINT64 Temp; - - Temp =3D 0; - switch (Value->Type) { - case EFI_IFR_TYPE_NUM_SIZE_8: - Temp =3D Value->Value.u8; - break; - - case EFI_IFR_TYPE_NUM_SIZE_16: - Temp =3D Value->Value.u16; - break; - - case EFI_IFR_TYPE_NUM_SIZE_32: - Temp =3D Value->Value.u32; - break; - - case EFI_IFR_TYPE_BOOLEAN: - Temp =3D Value->Value.b; - break; - - case EFI_IFR_TYPE_TIME: - Temp =3D Value->Value.u32 & 0xffffff; - break; - - case EFI_IFR_TYPE_DATE: - Temp =3D Value->Value.u32; - break; - - default: - return; - } - - Value->Value.u64 =3D Temp; -} - - -/** - Compare two Hii value. - - @param Value1 Expression value to compare on left-hand. - @param Value2 Expression value to compare on right-hand. - @param FormSet The pointer to the Formset. - - @retval EFI_INVALID_PARAMETER Could not perform compare on two values. - @retval 0 Two operators equal. - @return Positive value if Value1 is greater than Value2. - @retval Negative value if Value1 is less than Value2. - -**/ -INTN -CompareHiiValue ( - IN EFI_HII_VALUE *Value1, - IN EFI_HII_VALUE *Value2, - IN FORM_BROWSER_FORMSET *FormSet - ) -{ - INTN Result; - INT64 Temp64; - CHAR16 *Str1; - CHAR16 *Str2; - - if ((Value1->Type >=3D EFI_IFR_TYPE_OTHER) || (Value2->Type >=3D EFI_IFR= _TYPE_OTHER) ) { - return EFI_INVALID_PARAMETER; - } - - if ((Value1->Type =3D=3D EFI_IFR_TYPE_STRING) || (Value2->Type =3D=3D EF= I_IFR_TYPE_STRING) ) { - if (Value1->Type !=3D Value2->Type) { - // - // Both Operator should be type of String - // - return EFI_INVALID_PARAMETER; - } - - if ((Value1->Value.string =3D=3D 0) || (Value2->Value.string =3D=3D 0)= ) { - // - // StringId 0 is reserved - // - return EFI_INVALID_PARAMETER; - } - - if (Value1->Value.string =3D=3D Value2->Value.string) { - return 0; - } - - Str1 =3D GetToken (Value1->Value.string, FormSet->UnicodeBinary); - if (Str1 =3D=3D NULL) { - // - // String not found - // - return EFI_INVALID_PARAMETER; - } - - Str2 =3D GetToken (Value2->Value.string, FormSet->UnicodeBinary); - if (Str2 =3D=3D NULL) { - FreePool (Str1); - return EFI_INVALID_PARAMETER; - } - - Result =3D FceStrCmp (Str1, Str2); - - FreePool (Str1); - FreePool (Str2); - - return Result; - } - - // - // Take remain types(integer, boolean, date/time) as integer - // - Temp64 =3D (INT64) (Value1->Value.u64 - Value2->Value.u64); - if (Temp64 > 0) { - Result =3D 1; - } else if (Temp64 < 0) { - Result =3D -1; - } else { - Result =3D 0; - } - - return Result; -} - -/** - Tell whether this Operand is an constant Expression or not - - @param Operand Operand of an IFR OpCode. - - @retval TRUE This is an Expression OpCode. - @retval FALSE Not an Expression OpCode. - -**/ -BOOLEAN -IsConstantExpressionOpCode ( - IN UINT8 Operand - ) -{ - if ((Operand =3D=3D EFI_IFR_EQ_ID_VAL_OP) || - (Operand =3D=3D EFI_IFR_EQ_ID_ID_OP) || - (Operand =3D=3D EFI_IFR_EQ_ID_VAL_LIST_OP )|| - (Operand =3D=3D EFI_IFR_QUESTION_REF1_OP) || - (Operand =3D=3D EFI_IFR_QUESTION_REF2_OP) || - (Operand =3D=3D EFI_IFR_QUESTION_REF3_OP) || - (Operand =3D=3D EFI_IFR_THIS_OP ) || - (Operand =3D=3D EFI_IFR_SECURITY_OP) || - (Operand =3D=3D EFI_IFR_GET_OP) || - (Operand =3D=3D EFI_IFR_SET_OP) - ) { - return FALSE; - } else { - return TRUE; - } -} - -/** - Update the HiiValue of question from its variable. - - @param FormSet FormSet associated with this expression. - @param Question The pointer to the Question - - @return EFI_SUCCESS - @return EFI_NOT_FOUND -**/ -EFI_STATUS -UpdateHiiValue ( - IN FORM_BROWSER_FORMSET *FormSet, - IN FORM_BROWSER_STATEMENT *Question - ) -{ - EFI_STATUS Status; - FORMSET_STORAGE *VarList; - UINT8 *VarBuffer; - EFI_HII_VALUE *HiiValue; - - Status =3D EFI_SUCCESS; - HiiValue =3D &Question->HiiValue; - - Status =3D SearchVarStorage ( - Question, - NULL, - Question->VarStoreInfo.VarOffset, - FormSet->StorageListHead, - (CHAR8 **)&VarBuffer, - &VarList - ); - if (EFI_ERROR(Status)) { - return Status; - } - if (Question->QuestionReferToBitField) { - GetBitsQuestionValue (Question, VarBuffer, &HiiValue->Value.u32); - } else { - CopyMem (&HiiValue->Value.u64, VarBuffer, Question->StorageWidth); - } - return Status; -} -/** - Evaluate the result of a HII expression. - - If Expression is NULL, then ASSERT. - - @param FormSet FormSet associated with this expression. - @param Form Form associated with this expression. - @param Expression Expression to be evaluated. - @param ConstantExpression The pointer to the flag of constant expre= ssion. If constant, will return TRUE. - - @retval EFI_SUCCESS The expression evaluated successfuly - @retval EFI_NOT_FOUND The Question which referenced by a Questi= onId - could not be found. - @retval EFI_OUT_OF_RESOURCES There is not enough system memory to grow= the - stack. - @retval EFI_ACCESS_DENIED The pop operation underflowed the stack - @retval EFI_INVALID_PARAMETER Syntax error with the Expression - -**/ -EFI_STATUS -EvaluateExpression ( - IN FORM_BROWSER_FORMSET *FormSet, - IN FORM_BROWSER_FORM *Form, - IN OUT FORM_EXPRESSION *Expression, - IN OUT BOOLEAN *ConstantExpression - ) -{ - EFI_STATUS Status; - LIST_ENTRY *Link; - EXPRESSION_OPCODE *OpCode; - FORM_BROWSER_STATEMENT *Question; - FORM_BROWSER_STATEMENT *Question2; - UINT16 Index; - EFI_HII_VALUE Data1; - EFI_HII_VALUE Data2; - EFI_HII_VALUE Data3; - FORM_EXPRESSION *RuleExpression; - EFI_HII_VALUE *Value; - INTN Result; - CHAR16 *StrPtr; - UINT32 TempValue; - LIST_ENTRY *SubExpressionLink; - FORM_EXPRESSION *SubExpression; - UINTN StackOffset; - UINTN TempLength; - CHAR16 TempStr[5]; - UINT8 DigitUint8; - UINT8 *TempBuffer; - - // - // Save current stack offset. - // - StackOffset =3D SaveExpressionEvaluationStackOffset (); - - ASSERT (Expression !=3D NULL); - Expression->Result.Type =3D EFI_IFR_TYPE_OTHER; - - Link =3D GetFirstNode (&Expression->OpCodeListHead); - while (!IsNull (&Expression->OpCodeListHead, Link)) { - OpCode =3D EXPRESSION_OPCODE_FROM_LINK (Link); - - Link =3D GetNextNode (&Expression->OpCodeListHead, Link); - - ZeroMem (&Data1, sizeof (EFI_HII_VALUE)); - ZeroMem (&Data2, sizeof (EFI_HII_VALUE)); - ZeroMem (&Data3, sizeof (EFI_HII_VALUE)); - - Value =3D &Data3; - Value->Type =3D EFI_IFR_TYPE_BOOLEAN; - Status =3D EFI_SUCCESS; - - // - // Check whether it is a constant expression or not - // - if (*ConstantExpression) { - *ConstantExpression =3D IsConstantExpressionOpCode (OpCode->Operand); - } - - switch (OpCode->Operand) { - // - // Built-in functions - // - case EFI_IFR_EQ_ID_VAL_OP: - Question =3D IdToQuestion (FormSet, Form, OpCode->QuestionId); - if (Question =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - UpdateHiiValue (FormSet, Question); - Result =3D CompareHiiValue (&Question->HiiValue, &OpCode->Value, For= mSet); - if ((EFI_STATUS)Result =3D=3D EFI_INVALID_PARAMETER) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - Value->Value.b =3D (BOOLEAN) ((Result =3D=3D 0) ? TRUE : FALSE); - break; - - case EFI_IFR_EQ_ID_ID_OP: - Question =3D IdToQuestion (FormSet, Form, OpCode->QuestionId); - if (Question =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - Question2 =3D IdToQuestion (FormSet, Form, OpCode->QuestionId2); - if (Question2 =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - UpdateHiiValue (FormSet, Question); - UpdateHiiValue (FormSet, Question2); - Result =3D CompareHiiValue (&Question->HiiValue, &Question2->HiiValu= e, FormSet); - if ((EFI_STATUS)Result =3D=3D EFI_INVALID_PARAMETER) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - Value->Value.b =3D (BOOLEAN) ((Result =3D=3D 0) ? TRUE : FALSE); - break; - - case EFI_IFR_EQ_ID_VAL_LIST_OP: - - Question =3D IdToQuestion (FormSet, Form, OpCode->QuestionId); - if (Question =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - UpdateHiiValue (FormSet, Question); - Value->Value.b =3D FALSE; - for (Index =3D0; Index < OpCode->ListLength; Index++) { - if (Question->HiiValue.Value.u16 =3D=3D OpCode->ValueList[Index]) { - Value->Value.b =3D TRUE; - break; - } - } - break; - - case EFI_IFR_DUP_OP: - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - Status =3D PushExpression (Value); - break; - - case EFI_IFR_QUESTION_REF1_OP: - case EFI_IFR_THIS_OP: - Question =3D IdToQuestion (FormSet, Form, OpCode->QuestionId); - if (Question =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - UpdateHiiValue (FormSet, Question); - Value =3D &Question->HiiValue; - break; - - case EFI_IFR_SECURITY_OP: - // - // Do nothing, as no need for static scaning - // - break; - - case EFI_IFR_GET_OP: - // - // Get Value from VarStore buffer, EFI VarStore, Name/Value VarStore. - // - Value->Type =3D EFI_IFR_TYPE_UNDEFINED; - Value->Value.u8 =3D 0; - if (OpCode->VarStorage !=3D NULL) { - switch (OpCode->VarStorage->Type) { - case EFI_IFR_VARSTORE_OP: - // - // Get value from Buffer - // - Value->Type =3D OpCode->ValueType; - CopyMem (&Value->Value, OpCode->VarStorage->Buffer + OpCode->Var= StoreInfo.VarOffset, OpCode->ValueWidth); - break; - - case EFI_IFR_VARSTORE_EFI_OP: - // - // Get value from Buffer - // - if (OpCode->VarStorage->NewEfiVarstore) { - Value->Type =3D OpCode->ValueType; - CopyMem (&Value->Value, OpCode->VarStorage->Buffer + OpCode->V= arStoreInfo.VarOffset, OpCode->ValueWidth); - } else { - CopyMem (&Value->Value, OpCode->VarStorage->Buffer, OpCode->ValueW= idth); - } - - - break; - case EFI_HII_VARSTORE_NAME_VALUE: - if (OpCode->ValueType !=3D EFI_IFR_TYPE_STRING) { - // - // Get value from string except for STRING value. - // - Status =3D GetValueByName (OpCode->VarStorage, OpCode->ValueNa= me, &StrPtr); - if (!EFI_ERROR (Status)) { - ASSERT (StrPtr !=3D NULL); - TempLength =3D FceStrLen (StrPtr); - if (OpCode->ValueWidth >=3D ((TempLength + 1) / 2)) { - Value->Type =3D OpCode->ValueType; - TempBuffer =3D (UINT8 *) &Value->Value; - ZeroMem (TempStr, sizeof (TempStr)); - for (Index =3D 0; Index < TempLength; Index ++) { - TempStr[0] =3D StrPtr[TempLength - Index - 1]; - DigitUint8 =3D (UINT8) FceStrHexToUint64 (TempStr); - if ((Index & 1) =3D=3D 0) { - TempBuffer [Index/2] =3D DigitUint8; - } else { - TempBuffer [Index/2] =3D (UINT8) ((DigitUint8 << 4) + = TempBuffer [Index/2]); - } - } - } - free (StrPtr); - StrPtr =3D NULL; - } - } - break; - default: - // - // Not recognize storage. - // - Status =3D EFI_UNSUPPORTED; - goto Done; - } - } - - break; - - case EFI_IFR_QUESTION_REF3_OP: - if (OpCode->DevicePath =3D=3D 0) { - // - // EFI_IFR_QUESTION_REF3 - // Pop an expression from the expression stack - // - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // Validate the expression value - // - if ((Value->Type > EFI_IFR_TYPE_NUM_SIZE_64) || (Value->Value.u64 = > 0xffff)) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - Question =3D IdToQuestion (FormSet, Form, Value->Value.u16); - if (Question =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - // - // push the questions' value on to the expression stack - // - Value =3D &Question->HiiValue; - } else { - // - // BUGBUG: push 0 for EFI_IFR_QUESTION_REF3_2 and EFI_IFR_QUESTION= _REF3_3, - // since it is impractical to evaluate the value of a Question in = another - // Hii Package list. - // - ZeroMem (Value, sizeof (EFI_HII_VALUE)); - } - break; - - case EFI_IFR_RULE_REF_OP: - // - // Find expression for this rule - // - RuleExpression =3D RuleIdToExpression (Form, OpCode->RuleId); - if (RuleExpression =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - // - // Evaluate this rule expression - // - Status =3D EvaluateExpression (FormSet, Form, RuleExpression, Consta= ntExpression); - if (EFI_ERROR (Status)) { - goto Done; - } - - Value =3D &RuleExpression->Result; - break; - - case EFI_IFR_STRING_REF1_OP: - Value->Type =3D EFI_IFR_TYPE_STRING; - Value->Value.string =3D OpCode->Value.Value.string; - break; - - // - // Constant - // - case EFI_IFR_TRUE_OP: - case EFI_IFR_FALSE_OP: - case EFI_IFR_ONE_OP: - case EFI_IFR_ONES_OP: - case EFI_IFR_UINT8_OP: - case EFI_IFR_UINT16_OP: - case EFI_IFR_UINT32_OP: - case EFI_IFR_UINT64_OP: - case EFI_IFR_UNDEFINED_OP: - case EFI_IFR_VERSION_OP: - case EFI_IFR_ZERO_OP: - Value =3D &OpCode->Value; - break; - - // - // unary-op - // - case EFI_IFR_LENGTH_OP: - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Value->Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - StrPtr =3D GetToken (Value->Value.string, FormSet->UnicodeBinary); - if (StrPtr =3D=3D NULL) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - Value->Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - Value->Value.u64 =3D FceStrLen (StrPtr); - FreePool (StrPtr); - break; - - case EFI_IFR_NOT_OP: - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Value->Type !=3D EFI_IFR_TYPE_BOOLEAN) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - Value->Value.b =3D (BOOLEAN) (!Value->Value.b); - break; - - case EFI_IFR_QUESTION_REF2_OP: - // - // Pop an expression from the expression stack - // - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // Validate the expression value - // - if ((Value->Type > EFI_IFR_TYPE_NUM_SIZE_64) || (Value->Value.u64 > = 0xffff)) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - Question =3D IdToQuestion (FormSet, Form, Value->Value.u16); - if (Question =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - Value =3D &Question->HiiValue; - break; - - case EFI_IFR_STRING_REF2_OP: - // - // Pop an expression from the expression stack - // - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // Validate the expression value - // - if ((Value->Type > EFI_IFR_TYPE_NUM_SIZE_64) || (Value->Value.u64 > = 0xffff)) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - - Value->Type =3D EFI_IFR_TYPE_STRING; - StrPtr =3D GetToken (Value->Value.u16, FormSet->UnicodeBinary); - if (StrPtr =3D=3D NULL) { - // - // If String not exit, push an empty string - // - //Value->Value.string =3D NewString (gEmptyString, FormSet->HiiHan= dle); - } else { - Index =3D (UINT16) Value->Value.u64; - Value->Value.string =3D Index; - FreePool (StrPtr); - } - break; - - case EFI_IFR_TO_BOOLEAN_OP: - // - // Pop an expression from the expression stack - // - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // Convert an expression to a Boolean - // - if (Value->Type <=3D EFI_IFR_TYPE_DATE) { - // - // When converting from an unsigned integer, zero will be conver= ted to - // FALSE and any other value will be converted to TRUE. - // - Value->Value.b =3D (BOOLEAN) (Value->Value.u64 !=3D 0); - - Value->Type =3D EFI_IFR_TYPE_BOOLEAN; - } else if (Value->Type =3D=3D EFI_IFR_TYPE_STRING) { - // - // When converting from a string, if case-insensitive compare - // with "true" is True, then push True. If a case-insensitive co= mpare - // with "false" is True, then push False. Otherwise, push Undefi= ned. - // - StrPtr =3D GetToken (Value->Value.string, FormSet->UnicodeBinary= ); - if (StrPtr =3D=3D NULL) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - IfrStrToUpper (StrPtr); - if (FceStrCmp (StrPtr, L"TRUE") =3D=3D 0){ - Value->Value.b =3D TRUE; - } else if (FceStrCmp (StrPtr, L"FALSE") =3D=3D 0) { - Value->Value.b =3D FALSE; - } else { - Status =3D EFI_INVALID_PARAMETER; - FreePool (StrPtr); - goto Done; - } - FreePool (StrPtr); - Value->Type =3D EFI_IFR_TYPE_BOOLEAN; - } - break; - - case EFI_IFR_TO_STRING_OP: - //Status =3D IfrToString (FormSet, OpCode->Format, Value); - break; - - case EFI_IFR_TO_UINT_OP: - Status =3D IfrToUint (FormSet, Value); - break; - - case EFI_IFR_TO_LOWER_OP: - case EFI_IFR_TO_UPPER_OP: - - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - if (Value->Type !=3D EFI_IFR_TYPE_STRING) { - Status =3D EFI_UNSUPPORTED; - goto Done; - } - - StrPtr =3D GetToken (Value->Value.string, FormSet->UnicodeBinary); - if (StrPtr =3D=3D NULL) { - Status =3D EFI_NOT_FOUND; - goto Done; - } - // - // Do nothing here, as these two Opcode are to change or update the = String Package - // - FreePool (StrPtr); - break; - - case EFI_IFR_BITWISE_NOT_OP: - // - // Pop an expression from the expression stack - // - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Value->Type > EFI_IFR_TYPE_DATE) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - Value->Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - Value->Value.u64 =3D ~Value->Value.u64; - break; - - case EFI_IFR_SET_OP: - // - // Pop an expression from the expression stack - // - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - Data1.Type =3D EFI_IFR_TYPE_BOOLEAN; - Data1.Value.b =3D FALSE; - // - // Not support SetOpcode for static scaning - // - if (OpCode->VarStorage !=3D NULL) { - switch (OpCode->VarStorage->Type) { - - case EFI_IFR_VARSTORE_OP: - CopyMem (OpCode->VarStorage->Buffer + OpCode->VarStoreInfo.VarOff= set, &Value->Value, OpCode->ValueWidth); - Data1.Value.b =3D TRUE; - break; - case EFI_IFR_VARSTORE_EFI_OP: - if (OpCode->VarStorage->NewEfiVarstore) { - CopyMem (OpCode->VarStorage->Buffer + OpCode->VarStoreInfo.V= arOffset, &Value->Value, OpCode->ValueWidth); - Data1.Value.b =3D TRUE; - } else { - CopyMem (OpCode->VarStorage->Buffer, &Value->Value, OpCode->Valu= eWidth); - Data1.Value.b =3D TRUE; - } - break; - case EFI_HII_VARSTORE_NAME_VALUE: - - break; - break; - default: - // - // Not recognize storage. - // - Status =3D EFI_UNSUPPORTED; - goto Done; - break; - } - Value =3D &Data1; - } - break; - - // - // binary-op - // - case EFI_IFR_ADD_OP: - case EFI_IFR_SUBTRACT_OP: - case EFI_IFR_MULTIPLY_OP: - case EFI_IFR_DIVIDE_OP: - case EFI_IFR_MODULO_OP: - case EFI_IFR_BITWISE_AND_OP: - case EFI_IFR_BITWISE_OR_OP: - case EFI_IFR_SHIFT_LEFT_OP: - case EFI_IFR_SHIFT_RIGHT_OP: - // - // Pop an expression from the expression stack - // - Status =3D PopExpression (&Data2); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Data2.Type > EFI_IFR_TYPE_DATE) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - // - // Pop another expression from the expression stack - // - Status =3D PopExpression (&Data1); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Data1.Type > EFI_IFR_TYPE_DATE) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - Value->Type =3D EFI_IFR_TYPE_NUM_SIZE_64; - - switch (OpCode->Operand) { - case EFI_IFR_ADD_OP: - Value->Value.u64 =3D Data1.Value.u64 + Data2.Value.u64; - break; - - case EFI_IFR_SUBTRACT_OP: - Value->Value.u64 =3D Data1.Value.u64 - Data2.Value.u64; - break; - - case EFI_IFR_MULTIPLY_OP: - Value->Value.u64 =3D MultU64x32 (Data1.Value.u64, (UINT32) Data2= .Value.u64); - break; - - case EFI_IFR_DIVIDE_OP: - Value->Value.u64 =3D DivU64x32 (Data1.Value.u64, (UINT32) Data2.= Value.u64); - break; - - case EFI_IFR_MODULO_OP: - DivU64x32Remainder (Data1.Value.u64, (UINT32) Data2.Value.u64, = &TempValue); - Value->Value.u64 =3D TempValue; - break; - - case EFI_IFR_BITWISE_AND_OP: - Value->Value.u64 =3D Data1.Value.u64 & Data2.Value.u64; - break; - - case EFI_IFR_BITWISE_OR_OP: - Value->Value.u64 =3D Data1.Value.u64 | Data2.Value.u64; - break; - - case EFI_IFR_SHIFT_LEFT_OP: - Value->Value.u64 =3D LShiftU64 (Data1.Value.u64, (UINTN) Data2.V= alue.u64); - break; - - case EFI_IFR_SHIFT_RIGHT_OP: - Value->Value.u64 =3D RShiftU64 (Data1.Value.u64, (UINTN) Data2.V= alue.u64); - break; - - default: - break; - } - break; - - case EFI_IFR_AND_OP: - case EFI_IFR_OR_OP: - // - // Two Boolean operator - // - Status =3D PopExpression (&Data2); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Data2.Type !=3D EFI_IFR_TYPE_BOOLEAN) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - // - // Pop another expression from the expression stack - // - Status =3D PopExpression (&Data1); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Data1.Type !=3D EFI_IFR_TYPE_BOOLEAN) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - if (OpCode->Operand =3D=3D EFI_IFR_AND_OP) { - Value->Value.b =3D (BOOLEAN) (Data1.Value.b && Data2.Value.b); - } else { - Value->Value.b =3D (BOOLEAN) (Data1.Value.b || Data2.Value.b); - } - break; - - case EFI_IFR_EQUAL_OP: - case EFI_IFR_NOT_EQUAL_OP: - case EFI_IFR_GREATER_EQUAL_OP: - case EFI_IFR_GREATER_THAN_OP: - case EFI_IFR_LESS_EQUAL_OP: - case EFI_IFR_LESS_THAN_OP: - // - // Compare two integer, string, boolean or date/time - // - Status =3D PopExpression (&Data2); - if (EFI_ERROR (Status)) { - goto Done; - } - if ((Data2.Type > EFI_IFR_TYPE_BOOLEAN) && (Data2.Type !=3D EFI_IFR_= TYPE_STRING)) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - // - // Pop another expression from the expression stack - // - Status =3D PopExpression (&Data1); - if (EFI_ERROR (Status)) { - goto Done; - } - - Result =3D CompareHiiValue (&Data1, &Data2, FormSet); - if ((EFI_STATUS)Result =3D=3D EFI_INVALID_PARAMETER) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - switch (OpCode->Operand) { - case EFI_IFR_EQUAL_OP: - Value->Value.b =3D (BOOLEAN) ((Result =3D=3D 0) ? TRUE : FALSE); - break; - - case EFI_IFR_NOT_EQUAL_OP: - Value->Value.b =3D (BOOLEAN) ((Result !=3D 0) ? TRUE : FALSE); - break; - - case EFI_IFR_GREATER_EQUAL_OP: - Value->Value.b =3D (BOOLEAN) ((Result >=3D 0) ? TRUE : FALSE); - break; - - case EFI_IFR_GREATER_THAN_OP: - Value->Value.b =3D (BOOLEAN) ((Result > 0) ? TRUE : FALSE); - break; - - case EFI_IFR_LESS_EQUAL_OP: - Value->Value.b =3D (BOOLEAN) ((Result <=3D 0) ? TRUE : FALSE); - break; - - case EFI_IFR_LESS_THAN_OP: - Value->Value.b =3D (BOOLEAN) ((Result < 0) ? TRUE : FALSE); - break; - - default: - break; - } - break; - - case EFI_IFR_MATCH_OP: - Status =3D IfrMatch (FormSet, Value); - break; - - case EFI_IFR_CATENATE_OP: - Status =3D IfrCatenate (FormSet, Value); - break; - - // - // ternary-op - // - case EFI_IFR_CONDITIONAL_OP: - // - // Pop third expression from the expression stack - // - Status =3D PopExpression (&Data3); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // Pop second expression from the expression stack - // - Status =3D PopExpression (&Data2); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // Pop first expression from the expression stack - // - Status =3D PopExpression (&Data1); - if (EFI_ERROR (Status)) { - goto Done; - } - if (Data1.Type !=3D EFI_IFR_TYPE_BOOLEAN) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - - if (Data1.Value.b) { - Value =3D &Data3; - } else { - Value =3D &Data2; - } - break; - - case EFI_IFR_FIND_OP: - Status =3D IfrFind (FormSet, OpCode->Format, Value); - break; - - case EFI_IFR_MID_OP: - Status =3D IfrMid (FormSet, Value); - break; - - case EFI_IFR_TOKEN_OP: - Status =3D IfrToken (FormSet, Value); - break; - - case EFI_IFR_SPAN_OP: - Status =3D IfrSpan (FormSet, OpCode->Flags, Value); - break; - - case EFI_IFR_MAP_OP: - // - // Pop the check value - // - Status =3D PopExpression (&Data1); - if (EFI_ERROR (Status)) { - goto Done; - } - // - // Check MapExpression list is valid. - // - if (OpCode->MapExpressionList.ForwardLink =3D=3D NULL) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - // - // Go through map expression list. - // - SubExpressionLink =3D GetFirstNode(&OpCode->MapExpressionList); - while (!IsNull (&OpCode->MapExpressionList, SubExpressionLink)) { - SubExpression =3D FORM_EXPRESSION_FROM_LINK (SubExpressionLink); - // - // Evaluate the first expression in this pair. - // - Status =3D EvaluateExpression (FormSet, Form, SubExpression, Const= antExpression); - if (EFI_ERROR (Status)) { - goto Done; - } - // - // Compare the expression value with current value - // - if (CompareHiiValue (&Data1, &SubExpression->Result, FormSet) =3D= =3D 0) { - // - // Try get the map value. - // - SubExpressionLink =3D GetNextNode (&OpCode->MapExpressionList, S= ubExpressionLink); - if (IsNull (&OpCode->MapExpressionList, SubExpressionLink)) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - SubExpression =3D FORM_EXPRESSION_FROM_LINK (SubExpressionLink); - Status =3D EvaluateExpression (FormSet, Form, SubExpression, Con= stantExpression); - if (EFI_ERROR (Status)) { - goto Done; - } - Value =3D &SubExpression->Result; - break; - } - // - // Skip the second expression on this pair. - // - SubExpressionLink =3D GetNextNode (&OpCode->MapExpressionList, Sub= ExpressionLink); - if (IsNull (&OpCode->MapExpressionList, SubExpressionLink)) { - Status =3D EFI_INVALID_PARAMETER; - goto Done; - } - // - // Goto the first expression on next pair. - // - SubExpressionLink =3D GetNextNode (&OpCode->MapExpressionList, Sub= ExpressionLink); - } - - // - // No map value is found. - // - if (IsNull (&OpCode->MapExpressionList, SubExpressionLink)) { - Value->Type =3D EFI_IFR_TYPE_UNDEFINED; - Value->Value.u8 =3D 0; - } - break; - - default: - break; - } - if (EFI_ERROR (Status)) { - goto Done; - } - - Status =3D PushExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - } - - // - // Pop the final result from expression stack - // - Value =3D &Data1; - Status =3D PopExpression (Value); - if (EFI_ERROR (Status)) { - goto Done; - } - - // - // After evaluating an expression, there should be only one value left o= n the expression stack - // - if (PopExpression (Value) !=3D EFI_ACCESS_DENIED) { - Status =3D EFI_INVALID_PARAMETER; - } - -Done: - RestoreExpressionEvaluationStackOffset (StackOffset); - if (!EFI_ERROR (Status)) { - CopyMem (&Expression->Result, Value, sizeof (EFI_HII_VALUE)); - } - - return Status; -} diff --git a/BaseTools/Source/C/FCE/Fce.c b/BaseTools/Source/C/FCE/Fce.c deleted file mode 100644 index 1845c508b5..0000000000 --- a/BaseTools/Source/C/FCE/Fce.c +++ /dev/null @@ -1,6449 +0,0 @@ -/** @file - - FCE is a tool which enables developers to retrieve and change HII configu= ration ("Setup") - data in Firmware Device files (".fd" files). - - Copyright (c) 2011-2019, Intel Corporation. All rights reserved.
- SPDX-License-Identifier: BSD-2-Clause-Patent - -**/ - -#include "Fce.h" - -#ifndef __GNUC__ -#define COPY_STR "copy \"%s\" \"%s\" > NUL" -#define RMDIR_STR "rmdir /S /Q \"%s\" > NUL" -#define DEL_STR "del \"%s\" > NUL" -#else -#define COPY_STR "cp \"%s\" \"%s\" > /dev/null" -#define RMDIR_STR "rm -r \"%s\" > /dev/null" -#define DEL_STR "rm \"%s\" > /dev/null" -#endif - -// -// Utility global variables -// -OPERATION_TYPE Operations; - -CHAR8 mInputFdName[MAX_FILENAME_LEN]; -CHAR8 mOutputFdName[MAX_FILENAME_LEN]; -CHAR8 mOutTxtName[MAX_FILENAME_LEN]; -CHAR8 mSetupTxtName[MAX_FILENAME_LEN]; - -CHAR8* mUtilityFilename =3D NULL; -UINT32 mEfiVariableAddr =3D 0; - -UQI_PARAM_LIST *mUqiList =3D NULL; -UQI_PARAM_LIST *mLastUqiList =3D NULL; -LIST_ENTRY mVarListEntry; -LIST_ENTRY mBfvVarListEntry; -LIST_ENTRY mAllVarListEntry; -LIST_ENTRY mFormSetListEntry; - -// -// Store GUIDed Section guid->tool mapping -// -EFI_HANDLE mParsedGuidedSectionTools =3D NULL; - -CHAR8* mGuidToolDefinition =3D "GuidToolDefinitionConf.ini"; - -// -//gFfsArray is used to store all the FFS informations of Fd -// -G_EFI_FD_INFO gEfiFdInfo; -// -//mMultiPlatformParam is used to store the structures about multi-platform= support -// -MULTI_PLATFORM_PARAMETERS mMultiPlatformParam; - -UINT32 mFormSetOrderRead; -UINT32 mFormSetOrderParse; - -CHAR8 mFullGuidToolDefinitionDir[_MAX_PATH]; - -CHAR8 *mFvNameGuidString =3D NULL; - -/** - Check the revision of BfmLib. If not matched, return an error. - - @retval EFI_SUCCESS If revision matched, return EFI_SUCCESS. - @retval EFI_UNSUPPORTED Other cases. -**/ -static -EFI_STATUS -CheckBfmLibRevision ( - VOID - ) -{ - CHAR8 *SystemCommandFormatString; - CHAR8 *SystemCommand; - CHAR8 *TempSystemCommand; - CHAR8 *Revision; - FILE *FileHandle; - CHAR8 RevisionStr[_MAX_BUILD_VERSION]; - UINT32 Len; - - SystemCommandFormatString =3D NULL; - SystemCommand =3D NULL; - TempSystemCommand =3D NULL; - Revision =3D "Revision.txt"; - - memset (RevisionStr, 0, _MAX_BUILD_VERSION); - - // - // Construction 'system' command string - // - SystemCommandFormatString =3D "BfmLib -v > %s"; - SystemCommand =3D malloc ( - strlen (SystemCommandFormatString) + strlen (Revision)= + 1 - ); - if (SystemCommand =3D=3D NULL) { - return EFI_UNSUPPORTED; - } - sprintf ( - SystemCommand, - "BfmLib -v > %s", - Revision - ); - - if (mFullGuidToolDefinitionDir[0] !=3D 0) { - TempSystemCommand =3D SystemCommand; - SystemCommand =3D malloc ( - strlen (mFullGuidToolDefinitionDir) + strlen (OS_SEP_S= TR) + strlen (SystemCommandFormatString) + strlen (Revision) + 1 - ); - - if (SystemCommand =3D=3D NULL) { - free (TempSystemCommand); - return EFI_UNSUPPORTED; - } - strcpy (SystemCommand, mFullGuidToolDefinitionDir); - strcat (SystemCommand, OS_SEP_STR); - strcat (SystemCommand, TempSystemCommand); - free (TempSystemCommand); - } - - system (SystemCommand); - free (SystemCommand); - FileHandle =3D fopen (Revision, "r"); - if (FileHandle =3D=3D NULL) { - printf ("Error. Read the revision file of BfmLib failed.\n"); - return EFI_ABORTED; - } - fgets(RevisionStr, _MAX_BUILD_VERSION, FileHandle); - Len =3D strlen(RevisionStr); - if (RevisionStr[Len - 1] =3D=3D '\n') { - RevisionStr[Len - 1] =3D 0; - } - fclose (FileHandle); - remove (Revision); - - if (strlen (RevisionStr) > _MAX_BUILD_VERSION - 1) { - printf ("The revision string is too long"); - return EFI_UNSUPPORTED; - } - if (strcmp (RevisionStr, __BUILD_VERSION) =3D=3D 0) { - return EFI_SUCCESS; - } - return EFI_UNSUPPORTED; -} - -/** - Transfer the Ascii string to the Dec Number - - @param InStr The Ascii string. - - @retval DecNum Return the Dec number. -**/ -static -UINT64 -StrToDec ( - IN CHAR8 *InStr - ) -{ - UINT8 Index; - UINTN DecNum; - UINTN Temp; - - Index =3D 0; - DecNum =3D 0; - Temp =3D 0; - - if (InStr =3D=3D NULL) { - return (UINT64)-1; - } - while (Index < strlen (InStr)) { - - if ((*(InStr + Index) >=3D '0') && (*(InStr + Index) <=3D '9')) { - Temp =3D *(InStr + Index) - '0'; - } else if ((*(InStr + Index) >=3D 'a') && (*(InStr + Index) <=3D 'f'))= { - Temp =3D *(InStr + Index) - 'a' + 10; - } else if ((*(InStr + Index) >=3D 'A') && (*(InStr + Index) <=3D 'F'))= { - Temp =3D *(InStr + Index) - 'A' + 10; - } - DecNum =3D DecNum + Temp * (UINTN) pow (16, strlen (InStr) - Index - 1= ); - Index++; - } - return DecNum; -} -/** - Check whether there are some errors in uqi parameters of One_of - - @param Question The pointer to the question Node. - @param UqiValue The value of One_of. - - @retval TRUE If existed error, return TRUE; - @return FALSE Otherwise, return FALSE; -**/ -static -BOOLEAN -CheckOneOfParamError ( - IN CONST FORM_BROWSER_STATEMENT *Question, - IN UINT64 UqiValue - ) -{ - LIST_ENTRY *Link; - QUESTION_OPTION *Option; - UINT64 Value; - - Link =3D NULL; - Option =3D NULL; - Value =3D 0; - - Link =3D GetFirstNode (&Question->OptionListHead); - while (!IsNull (&Question->OptionListHead, Link)) { - Option =3D QUESTION_OPTION_FROM_LINK (Link); - Value =3D 0; - CopyMem (&Value, &Option->Value.Value.u64, Question->StorageWidth); - if (Value =3D=3D UqiValue) { - return FALSE; - } - Link =3D GetNextNode (&Question->OptionListHead, Link); - } - - return TRUE; -} - -/** - Check whether there are some errors in uqi parameters of Orderlist - - @param HiiObjList The pointer to the Hii Object Node. - @param UqiValue The pointer to the Uqi parameter. - - @retval TRUE If existed error, return TRUE; - @return FALSE Otherwise, return FALSE; -**/ -static -BOOLEAN -CheckOrderParamError ( - IN CONST FORM_BROWSER_STATEMENT *Question, - IN CHAR8 *UqiValue - ) -{ - UINT8 MaxNum; - MaxNum =3D UqiValue[0]; - - if (MaxNum !=3D (UINT8)(Question->MaxContainers)) { - return TRUE; - } - - return FALSE; -} - -/** - Writes a Unicode string - - @param Package A pointer to the Unicode string. - - @return NULL -**/ -static -VOID -WriteUnicodeStr ( - IN CHAR16 *pcString - ) -{ - UINTN Index; - - if (pcString =3D=3D NULL) { - return; - } - - for (Index =3D 0; pcString[Index] !=3D 0; Index++) { - printf("%c", pcString[Index] & 0x00FF); - } -} - -/** - Parse and set the quick configure information by the command line. - - Read the UQI Config information from command line directly, and then com= pare it with the value in VarList. - Update the Update flag in Varlist. - - @param CurUqiList The pointer to the current uqi - @param DefaultId The default Id. - @param PlatformId The platform Id. - @param CurQuestion The pointer to the matched question - - @retval EFI_SUCCESS It was complete successfully - @retval EFI_UNSUPPORTED Update a read-only value - @return EFI_ABORTED An error occurred -**/ -static -EFI_STATUS -SetUqiParametersWithQuestion ( - IN UQI_PARAM_LIST *CurUqiList, - IN UINT16 DefaultId, - IN UINT64 PlatformId, - IN FORM_BROWSER_STATEMENT *CurQuestion - ) -{ - FORMSET_STORAGE *VarList; - BOOLEAN IsFound; - UINT8 *ValueAddrOfVar; - UINT16 Index; - UINT64 QuestionValue; - UINT64 UqiValue; - EFI_STATUS Status; - CHAR8 *ErrorStr; - FORM_BROWSER_FORMSET *FormSet; - LIST_ENTRY *FormSetLink; - UINT64 CurValue; - - VarList =3D NULL; - Index =3D 0; - ValueAddrOfVar =3D NULL; - QuestionValue =3D 0; - UqiValue =3D 0; - ErrorStr =3D NULL; - Status =3D EFI_SUCCESS; - FormSet =3D NULL; - FormSetLink =3D NULL; - CurValue =3D 0; - - // - // Search the Variable List by VarStoreId and Offset - // - IsFound =3D FALSE; - FormSetLink =3D GetFirstNode (&mFormSetListEntry); - while (!IsNull (&mFormSetListEntry, FormSetLink)) { - FormSet =3D FORM_BROWSER_FORMSET_FROM_LINK (FormSetLink); - Status =3D SearchVarStorage ( - CurQuestion, - NULL, - CurQuestion->VarStoreInfo.VarOffset, - FormSet->StorageListHead, - (CHAR8 **) &ValueAddrOfVar, - &VarList - ); - - if (!EFI_ERROR (Status)) { - IsFound =3D TRUE; - break; - } - FormSetLink =3D GetNextNode (&mFormSetListEntry, FormSetLink); - } - - if (!IsFound) { - if (CurUqiList->Header.ScriptsLine =3D=3D 0) { - printf ("Error. The question in the command line doesn't store value= by EFI_VARSTORE_IFR or EFI_VARSTORE_IFR_EFI.\n"); - } else { - printf ("Error. The question in the line %d of script doesn't store = value by EFI_VARSTORE_IFR or EFI_VARSTORE_IFR_EFI.\n", CurUqiList->Header.S= criptsLine); - } - return EFI_ABORTED; - } - - // - // Check the length of variable value - // - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)&QuestionV= alue); - } else { - switch (CurQuestion->StorageWidth) { - - case sizeof (UINT8): - QuestionValue =3D *(UINT8 *)ValueAddrOfVar; - break; - - case sizeof (UINT16): - QuestionValue =3D *(UINT16 *)ValueAddrOfVar; - break; - - case sizeof (UINT32): - QuestionValue =3D *(UINT32 *)ValueAddrOfVar; - break; - - case sizeof (UINT64): - QuestionValue =3D *(UINT64 *)ValueAddrOfVar; - break; - - default: - // - // The storage width of ORDERED_LIST may not be any type above. - // - ; - break; - } - } - UqiValue =3D *(UINT64 *)CurUqiList->Header.Value; - CurUqiList->SameOrNot =3D TRUE; - - // - // Check and set the checkbox value - // - if (CurQuestion->Operand =3D=3D EFI_IFR_CHECKBOX_OP) { - if ((UqiValue !=3D 0) && (UqiValue !=3D 1)) { - CurUqiList->ErrorOrNot =3D TRUE; - CurUqiList->SameOrNot =3D FALSE; - CurUqiList->Error =3D malloc (ERROR_INFO_LENGTH * sizeof (CHAR8= )); - if (CurUqiList->Error =3D=3D NULL) { - printf ("Fail to allocate memory!\n"); - return EFI_ABORTED; - } - memset (CurUqiList->Error, 0, ERROR_INFO_LENGTH); - sprintf (CurUqiList->Error, "Error. The updated value of CHECKBOX 0x= %llx is invalid.\n", (unsigned long long) UqiValue); - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)CurUqi= List->Header.DiffValue); - } else { - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - } - } else { - if (QuestionValue !=3D UqiValue) { - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)CurU= qiList->Header.DiffValue); - SetBitsQuestionValue (CurQuestion, ValueAddrOfVar, *(UINT32*)Cur= UqiList->Header.Value); - } else { - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - memcpy ( - ValueAddrOfVar, - CurUqiList->Header.Value, - CurQuestion->StorageWidth - ); - } - CurUqiList->SameOrNot =3D FALSE; - } - } - } - if (CurQuestion->Operand =3D=3D EFI_IFR_STRING_OP) { - if ((FceStrLen((wchar_t *)CurUqiList->Header.Value) + 1) * 2 > CurQuest= ion->StorageWidth) { - CurUqiList->ErrorOrNot =3D TRUE; - CurUqiList->Error =3D malloc (ERROR_INFO_LENGTH * sizeof (CHAR8)); - if (CurUqiList->Error =3D=3D NULL) { - printf ("Fail to allocate memory!\n"); - return EFI_ABORTED; - } - memset (CurUqiList->Error, 0, ERROR_INFO_LENGTH); - sprintf (CurUqiList->Error, "Error. The updated value of STRING excee= d its Size.\n"); - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - } else { - if (memcmp((CHAR8 *)CurUqiList->Header.Value, ValueAddrOfVar, CurQues= tion->StorageWidth) !=3D 0) { - memcpy( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - memcpy( - ValueAddrOfVar, - CurUqiList->Header.Value, - CurQuestion->StorageWidth - ); - CurUqiList->SameOrNot =3D FALSE; - } - } - } - // - // Check and set the NUMERIC value - // - if (CurQuestion->Operand =3D=3D EFI_IFR_NUMERIC_OP) { - if ((UqiValue < CurQuestion->Minimum) || (UqiValue > CurQuestion->Maxi= mum)) { - CurUqiList->ErrorOrNot =3D TRUE; - CurUqiList->SameOrNot =3D FALSE; - CurUqiList->Error =3D malloc (ERROR_INFO_LENGTH * sizeof (CHAR8)); - if (CurUqiList->Error =3D=3D NULL) { - printf ("Fail to allocate memory!\n"); - return EFI_ABORTED; - } - memset (CurUqiList->Error, 0, ERROR_INFO_LENGTH); - sprintf (CurUqiList->Error, "Error. The updated value of NUMERIC 0x%= llx is invalid.\n", (unsigned long long) UqiValue); - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)CurUqi= List->Header.DiffValue); - } else { - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - } - } else { - if (QuestionValue !=3D UqiValue) { - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)CurU= qiList->Header.DiffValue); - SetBitsQuestionValue (CurQuestion, ValueAddrOfVar, *(UINT32*)Cur= UqiList->Header.Value); - } else { - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - memcpy ( - ValueAddrOfVar, - CurUqiList->Header.Value, - CurQuestion->StorageWidth - ); - } - CurUqiList->SameOrNot =3D FALSE; - } - } - } - // - // Check and set the ONE_OF value - // - if (CurQuestion->Operand =3D=3D EFI_IFR_ONE_OF_OP) { - if (CheckOneOfParamError (CurQuestion, UqiValue)) { - CurUqiList->ErrorOrNot =3D TRUE; - CurUqiList->SameOrNot =3D FALSE; - CurUqiList->Error =3D malloc (ERROR_INFO_LENGTH * sizeof (CHAR8)); - if (CurUqiList->Error =3D=3D NULL) { - printf ("Fail to allocate memory!\n"); - return EFI_ABORTED; - } - memset (CurUqiList->Error, 0, ERROR_INFO_LENGTH); - sprintf (CurUqiList->Error, "Error. The updated ONE_OF value 0x%llx = is invalid.\n", (unsigned long long) UqiValue); - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)CurUqi= List->Header.DiffValue); - } else { - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - } - } else { - if (QuestionValue !=3D UqiValue) { - if (CurQuestion->QuestionReferToBitField) { - GetBitsQuestionValue (CurQuestion, ValueAddrOfVar, (UINT32*)CurU= qiList->Header.DiffValue); - SetBitsQuestionValue (CurQuestion, ValueAddrOfVar, *(UINT32*)Cur= UqiList->Header.Value); - } else { - memcpy ( - CurUqiList->Header.DiffValue, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - memcpy ( - ValueAddrOfVar, - CurUqiList->Header.Value, - CurQuestion->StorageWidth - ); - } - CurUqiList->SameOrNot =3D FALSE; - } - } - } - // - // Check and set the ORDER_LIST value - // - if (CurQuestion->Operand =3D=3D EFI_IFR_ORDERED_LIST_OP) { - // - // Synchronize the MaxContainers value - // - *CurUqiList->Header.DiffValue =3D (UINT8)CurQuestion->MaxContainers; - - if (CheckOrderParamError (CurQuestion, (CHAR8 *)CurUqiList->Header.Val= ue)) { - - CurUqiList->ErrorOrNot =3D TRUE; - CurUqiList->SameOrNot =3D FALSE; - CurUqiList->Error =3D malloc (ERROR_INFO_LENGTH * sizeof (CHAR8)); - if (CurUqiList->Error =3D=3D NULL) { - printf ("Fail to allocate memory!\n"); - return EFI_ABORTED; - } - memset (CurUqiList->Error, 0, ERROR_INFO_LENGTH); - - ErrorStr =3D CurUqiList->Error; - sprintf (ErrorStr, "Error. The updated NORDERED_LIST value "); - ErrorStr =3D ErrorStr + strlen ("Error. The updated NORDERED_LIST va= lue "); - - for (Index =3D 0; Index < CurQuestion->StorageWidth; Index++) { - sprintf (ErrorStr, "%02x ", *(CurUqiList->Header.Value + Index + 1= )); - ErrorStr +=3D3; - } - sprintf (ErrorStr, "is invalid.\n"); - memcpy ( - CurUqiList->Header.DiffValue + 1, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - } else { - for (Index =3D 0; Index < CurQuestion->StorageWidth/CurQuestion->Max= Containers; Index++) { - CurValue =3D 0; - memcpy ( - &CurValue, - (ValueAddrOfVar + Index * CurQuestion->StorageWidth/CurQuestion-= >MaxContainers), - CurQuestion->StorageWidth/CurQuestion->MaxContainers - ); - if (CurValue !=3D *((UINT64 *)CurUqiList->Header.Value + Index + 1= )) { - CurUqiList->SameOrNot =3D FALSE; - break; - } - } - if (!CurUqiList->SameOrNot) { - memcpy ( - CurUqiList->Header.DiffValue + 1, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - for (Index =3D 0; Index < CurQuestion->MaxContainers; Index++) { - switch (CurQuestion->StorageWidth/CurQuestion->MaxContainers) { - - case sizeof (UINT8): - *((UINT8 *)ValueAddrOfVar + Index) =3D *(UINT8 *)((UINT64 *)Cu= rUqiList->Header.Value + 1 + Index); - break; - - case sizeof (UINT16): - *((UINT16 *)ValueAddrOfVar + Index) =3D *(UINT16 *)((UINT64 *)= CurUqiList->Header.Value + 1 + Index); - break; - - case sizeof (UINT32): - *((UINT32 *)ValueAddrOfVar + Index) =3D *(UINT32 *)((UINT64 *)= CurUqiList->Header.Value + 1 + Index); - break; - - case sizeof (UINT64): - *((UINT64 *)ValueAddrOfVar + Index) =3D *((UINT64 *)CurUqiList= ->Header.Value + 1 + Index); - break; - - default: - *((UINT8 *)ValueAddrOfVar + Index) =3D *(UINT8 *)((UINT64 *)Cu= rUqiList->Header.Value + 1 + Index); - break; - } - } - // - // Update the vaule of ORDERED_LIST according to its size - // - CurUqiList->Header.Value =3D (UINT8 *)((UINT64 *)CurUqiList->Heade= r.Value); - memcpy ( - CurUqiList->Header.Value + 1, - ValueAddrOfVar, - CurQuestion->StorageWidth - ); - } - } - } - - return EFI_SUCCESS; -} - -/** - Parse and set the quick configure information by the command line. - - Read the UQI Config information from command line directly, and then com= pare it with the value in VarList. - Update the Update flag in Varlist. - - @param UqiList The pointer to the uqi list - @param DefaultId The default Id. - @param PlatformId The platform Id. - - @retval EFI_SUCCESS It was complete successfully - @retval EFI_UNSUPPORTED Update a read-only value - @return EFI_ABORTED An error occurred -**/ -static -EFI_STATUS -SetUqiParameters ( - IN UQI_PARAM_LIST *UqiList, - IN UINT16 DefaultId, - IN UINT64 PlatformId - ) -{ - FORM_BROWSER_FORMSET *FormSet; - LIST_ENTRY *FormSetLink; - FORM_BROWSER_FORM *Form; - LIST_ENTRY *FormLink; - FORM_BROWSER_STATEMENT *Question; - LIST_ENTRY *QuestionLink; - LIST_ENTRY *FormSetEntryListHead; - UQI_PARAM_LIST *CurUqiList; - - FormSet =3D NULL; - FormSetLink =3D NULL; - Form =3D NULL; - FormLink =3D NULL; - Question =3D NULL; - QuestionLink =3D NULL; - FormSetEntryListHead =3D &mFormSetListEntry; - - FormSetLink =3D GetFirstNode (FormSetEntryListHead); - while (!IsNull (FormSetEntryListHead, FormSetLink)) { - FormSet =3D FORM_BROWSER_FORMSET_FROM_LINK (FormSetLink); - // - // Parse all forms in formset - // - FormLink =3D GetFirstNode (&FormSet->FormListHead); - - while (!IsNull (&FormSet->FormListHead, FormLink)) { - Form =3D FORM_BROWSER_FORM_FROM_LINK (FormLink); - // - // Parse five kinds of Questions in Form - // - QuestionLink =3D GetFirstNode (&Form->StatementListHead); - - while (!IsNull (&Form->StatementListHead, QuestionLink)) { - Question =3D FORM_BROWSER_STATEMENT_FROM_LINK (QuestionLink); - QuestionLink =3D GetNextNode (&Form->StatementListHead, QuestionLi= nk); - // - // Parse five kinds of Questions in Form - // - if ((Question->Operand =3D=3D EFI_IFR_ONE_OF_OP) - || (Question->Operand =3D=3D EFI_IFR_NUMERIC_OP) - || (Question->Operand =3D=3D EFI_IFR_CHECKBOX_OP) - || (Question->Operand =3D=3D EFI_IFR_ORDERED_LIST_OP) - || (Question->Operand =3D=3D EFI_IFR_STRING_OP) - ) { - if (mMultiPlatformParam.MultiPlatformOrNot) { - // - // Only compare the valid EFI_IFR_VARSTORE_EFI_OP in multi-pla= tform mode - // - if (Question->Type !=3D EFI_IFR_VARSTORE_EFI_OP) { - continue; - } - if ((Question->Type =3D=3D EFI_IFR_VARSTORE_EFI_OP) - && Question->NewEfiVarstore - && ((Question->Attributes & EFI_VARIABLE_NON_VOLATILE) =3D= =3D 0)) { - continue; - } - } - - CurUqiList =3D UqiList; - while (CurUqiList !=3D NULL) { - if ((PlatformId =3D=3D CurUqiList->Header.PlatformId[0]) - && (DefaultId =3D=3D CurUqiList->Header.DefaultId[0]) - && CompareUqiHeader (&(Question->Uqi), &(CurUqiList->Header)) - ) { - // - // Add further check to avoid a case that there are many opt= ions with a - // same UQI (en-Us), but always returns the first one. - // - if (!CurUqiList->ParseOrNot) { - CurUqiList->ParseOrNot =3D TRUE; - break; - } - } - CurUqiList =3D CurUqiList->Next; - } - if (CurUqiList !=3D NULL) { - SetUqiParametersWithQuestion (CurUqiList, DefaultId, PlatformI= d, Question); - } - } - } - FormLink =3D GetNextNode (&FormSet->FormListHead, FormLink); - } - FormSetLink =3D GetNextNode (FormSetEntryListHead, FormSetLink); - } - - return EFI_SUCCESS; -} - -/** - Set question value per UqiList. - - @param UqiList The pointer to the uqi list - @param DefaultId The default Id. - @param PlatformId The platform Id. -**/ -VOID -SetUqiParametersMultiMode ( - IN UQI_PARAM_LIST *UqiList, - IN UINT16 DefaultId, - IN UINT64 PlatformId - ) -{ - UQI_PARAM_LIST *CurUqiList; - - CurUqiList =3D UqiList; - while (CurUqiList !=3D NULL) { - if ((CurUqiList->ParseOrNot =3D=3D FALSE) - && (PlatformId =3D=3D CurUqiList->Header.PlatformId[0]) - && (DefaultId =3D=3D CurUqiList->Header.DefaultId[0]) - ) { - CurUqiList->ParseOrNot =3D TRUE; - if (CurUqiList->Header.Question !=3D NULL) { - SetUqiParametersWithQuestion (CurUqiList, DefaultId, PlatformId, C= urUqiList->Header.Question); - } - } - CurUqiList =3D CurUqiList->Next; - } -} - -/** - Find the matched question for each UQI string in UqiList - -**/ -EFI_STATUS -ScanUqiFullList ( - IN UQI_PARAM_LIST *UqiList - ) -{ - FORM_BROWSER_FORMSET *FormSet; - LIST_ENTRY *FormSetLink; - FORM_BROWSER_FORM *Form; - LIST_ENTRY *FormLink; - FORM_BROWSER_STATEMENT *Question; - LIST_ENTRY *QuestionLink; - LIST_ENTRY *FormSetEntryListHead; - UQI_PARAM_LIST *CurUqiList; - UINT64 PlatformId; - UINT16 DefaultId; - - if (UqiList =3D=3D NULL) { - return EFI_SUCCESS; - } - FormSet =3D NULL; - FormSetLink =3D NULL; - Form =3D NULL; - FormLink =3D NULL; - Question =3D NULL; - QuestionLink =3D NULL; - FormSetEntryListHead =3D &mFormSetListEntry; - - FormSetLink =3D FormSetEntryListHead->ForwardLink; - while (FormSetEntryListHead !=3D FormSetLink) { - FormSet =3D FORM_BROWSER_FORMSET_FROM_LINK (FormSetLink); - // - // Parse all forms in formset - // - FormLink =3D FormSet->FormListHead.ForwardLink; - - while (&FormSet->FormListHead !=3D FormLink) { - Form =3D FORM_BROWSER_FORM_FROM_LINK (FormLink); - // - // Parse five kinds of Questions in Form - // - QuestionLink =3D Form->StatementListHead.ForwardLink; - - while (&Form->StatementListHead !=3D QuestionLink) { - Question =3D FORM_BROWSER_STATEMENT_FROM_LINK (QuestionLink); - QuestionLink =3D QuestionLink->ForwardLink; - // - // Parse five kinds of Questions in Form - // - if ((Question->Operand =3D=3D EFI_IFR_ONE_OF_OP) - || (Question->Operand =3D=3D EFI_IFR_NUMERIC_OP) - || (Question->Operand =3D=3D EFI_IFR_CHECKBOX_OP) - || (Question->Operand =3D=3D EFI_IFR_ORDERED_LIST_OP) - || (Question->Operand =3D=3D EFI_IFR_STRING_OP) - ) { - // - // Only compare the valid EFI_IFR_VARSTORE_EFI_OP in multi-platf= orm mode - // - if (Question->Type !=3D EFI_IFR_VARSTORE_EFI_OP) { - continue; - } else if (Question->NewEfiVarstore - && ((Question->Attributes & EFI_VARIABLE_NON_VOLATILE) =3D=3D = 0)) { - continue; - } - - CurUqiList =3D UqiList; - PlatformId =3D 0xFFFFFFFF; - DefaultId =3D 0xFFFF; - while (CurUqiList !=3D NULL) { - if ((CurUqiList->Header.Question =3D=3D NULL) - && CompareUqiHeader (&(Question->Uqi), &(CurUqiList->Header)) - && ((PlatformId !=3D CurUqiList->Header.PlatformId[0]) || (D= efaultId !=3D CurUqiList->Header.DefaultId[0])) - ) { - CurUqiList->Header.Question =3D Question; - PlatformId =3D CurUqiList->Header.PlatformId[0]; - DefaultId =3D CurUqiList->Header.DefaultId[0]; - } - CurUqiList =3D CurUqiList->Next; - } - } - } - FormLink =3D FormLink->ForwardLink; - } - FormSetLink =3D FormSetLink->ForwardLink; - } - - return EFI_SUCCESS; -} - -/** - Create and insert the UQI Node to the UQI parameter list. - - @retval Node address If successed, return the node address. - @retval NULL An error occurred. - -**/ -static -UQI_PARAM_LIST * -CreateInsertUqiNode ( - ) -{ - UQI_PARAM_LIST *Node; - - Node =3D (UQI_PARAM_LIST *) malloc (sizeof (UQI_PARAM_LIST)); - if (Node =3D=3D NULL) { - return NULL; - } - memset (Node, 0, sizeof (UQI_PARAM_LIST)); - - if (mUqiList =3D=3D NULL) { - mUqiList =3D Node; - } else { - mLastUqiList->Next =3D Node; - } - - mLastUqiList =3D Node; - return Node; -} -/** - Parse the first part of QUI string - - @param **argv[] The dual array pointer to the paramet= ers. - @param Number The pointer to the number of the firs= t character of UQI. - @param Buffer The buffer to store the first part of= UQI. - - @retval EFI_SUCCESS Parse the QUI parameters successfully. - @retval EFI_INVALID_PARAMETER An error occurred. - -**/ -static -EFI_STATUS -ParseFirstpartOfUqi ( - IN CHAR8 **argv[], - OUT UINT32 *Number, - OUT UINT16 **Buffer - ) -{ - UINT32 Index; - - Index =3D 0; - - *Number =3D (UINT32)StrToDec ((*argv)[0]); - - if ((*Number <=3D 0) || (*Number > MAX_QUI_PARAM_LEN)) { - printf ("Error. Invalid UQI.\n"); - return EFI_INVALID_PARAMETER; - } - - *Buffer =3D malloc ((*Number + 1) * sizeof (CHAR16)); - assert (*Buffer !=3D NULL); - memset (*Buffer, 0, (*Number + 1) * sizeof (CHAR16)); - - for (Index =3D 0; Index < *Number; Index++) { - if (StrToDec ((*argv)[Index]) > 0xff) { - printf ("Error. Invalid UQI.\n"); - return EFI_INVALID_PARAMETER; - } - *(*Buffer + Index) =3D (UINT16)StrToDec ((*argv)[Index + 1]); - } - return EFI_SUCCESS; -} - -/** - Parse the QUI input parameters from the command line - - @param argc The pointer to the number of input pa= rameters. - @param **argv[] The dual array pointer to the paramet= ers. - - @retval EFI_SUCCESS Parse the QUI parameters successfully. - @retval EFI_INVALID_PARAMETER An error occurred. - -**/ -static -EFI_STATUS -ParseUqiParam ( - IN UINT32 *argc, - IN CHAR8 **argv[] - ) -{ - UINT32 Index; - UQI_PARAM_LIST *UqiNode; - EFI_STATUS Status; - - Index =3D 0; - UqiNode =3D NULL; - - if (*argc < 4) { - printf ("Error. The correct command is 'FCE updateq -i -o '.\n"); - return EFI_INVALID_PARAMETER; - } - - UqiNode =3D CreateInsertUqiNode (); - assert (UqiNode !=3D NULL); - - UqiNode->Header.DefaultId =3D (UINT16 *) calloc (1, sizeof (UINT16)); - UqiNode->Header.PlatformId =3D (UINT64 *) calloc (1, sizeof (UINT64)); - - Status =3D ParseFirstpartOfUqi (argv, &(UqiNode->Header.HexNum), &(UqiNo= de->Header.Data)); - if (EFI_ERROR (Status)) { - return Status; - } - *argc -=3D (UqiNode->Header.HexNum + 1); - *argv +=3D UqiNode->Header.HexNum + 1; - // - // Parse the TYPE and value - // - if (strcmp ("ONE_OF", (*argv)[0]) =3D=3D 0) { - UqiNode->Header.Type =3D ONE_OF; - } else if (strcmp ("NUMERIC", (*argv)[0]) =3D=3D 0) { - UqiNode->Header.Type =3D NUMERIC; - } else if (strcmp ("CHECKBOX", (*argv)[0]) =3D=3D 0) { - UqiNode->Header.Type =3D CHECKBOX; - } else if (strcmp ("STRING", (*argv)[0]) =3D=3D 0) { - UqiNode->Header.Type =3D STRING; - } else if (strcmp ("ORDERED_LIST", (*argv)[0]) =3D=3D 0) { - UqiNode->Header.Type =3D ORDERED_LIST; - } else { - printf ("Error. The correct command is 'FCE updateq -i -o '.\n"); - return EFI_INVALID_PARAMETER; - } - *argc -=3D 1; - *argv +=3D 1; - // - // Get the value according to the type of questions. - // - switch (UqiNode->Header.Type) { - - case ONE_OF: - case NUMERIC: - case CHECKBOX: - UqiNode->Header.Value =3D malloc (sizeof (UINT64)); - if (UqiNode->Header.Value =3D=3D NULL) { - printf ("Fali to allocate memory!\n"); - return EFI_OUT_OF_RESOURCES; - } - memset (UqiNode->Header.Value, 0, sizeof (UINT64)); - - UqiNode->Header.DiffValue =3D malloc (sizeof (UINT64)); - if (UqiNode->Header.DiffValue =3D=3D NULL) { - printf ("Fali to allocate memory!\n"); - return EFI_OUT_OF_RESOURCES; - } - memset ( - UqiNode->Header.DiffValue, - 0, - sizeof (UINT64) - ); - *(UINT64 *)(UqiNode->Header.Value) =3D (UINT64)StrToDec ((*argv)[0]); - break; - - case ORDERED_LIST: - UqiNode->Header.Value =3D malloc (((UINTN)StrToDec ((*argv)[0]) + 1= ) * sizeof (UINT64)); - if (UqiNode->Header.Value =3D=3D NULL) { - printf ("Fali to allocate memory!\n"); - return EFI_OUT_OF_RESOURCES; - } - memset ( - UqiNode->Header.Value, - 0, - (UINTN)StrToDec(((*argv)[0]) + 1) * sizeof (UINT64) - ); - - UqiNode->Header.DiffValue =3D malloc (((UINTN)StrToDec ((*argv)[0])= + 1) * sizeof (UINT64)); - if (UqiNode->Header.DiffValue =3D=3D NULL) { - printf ("Fali to allocate memory!\n"); - return EFI_OUT_OF_RESOURCES; - } - memset ( - UqiNode->Header.DiffValue, - 0, - (UINTN)(StrToDec ((*argv)[0]) + 1) * sizeof (UINT64) - ); - - *UqiNode->Header.Value =3D (UINT8)StrToDec ((*argv)[0]); - for (Index =3D 1; Index <=3D StrToDec ((*argv)[0]); Index++) { - *((UINT64 *)UqiNode->Header.Value + Index) =3D StrToDec ((*argv)[Ind= ex]); - } - *argc -=3D (UINTN)StrToDec ((*argv)[0]); - *argv +=3D (UINTN)StrToDec ((*argv)[0]); - break; - - default: - break; - } - - *argc -=3D 1; - *argv +=3D 1; - - if (*argc > 0) { - printf ("Error. The correct command is 'FCE updateq -i -o '.\n"); - return EFI_INVALID_PARAMETER; - } - return EFI_SUCCESS; -} -/** - Parse the input Fd file, and get the file name according to the FILETYPE. - - @param FdName The Name of Fd file - @param FILETYPE The type of Fd file - - @return EFI_SUCCESS Get the file name successfully - @return EFI_ABORTED An error occurred. -**/ -static -EFI_STATUS -ParseInFile ( - IN CHAR8 *FdName, - IN FILETYPE Type -) -{ - FILE *Fptr; - - Fptr =3D NULL; - - if ((Type =3D=3D INFD) && ((FdName =3D=3D NULL) || (Fptr =3D fopen (FdNa= me, "r")) =3D=3D NULL)) { - if (FdName !=3D NULL) { - printf ("Error: The file doesn't exist '%s'\n", FdName); - } - return EFI_ABORTED; - } - if ((Type =3D=3D OUTFD) && (FdName =3D=3D NULL) ) { - printf ("Error: The name is NULL.\n"); - return EFI_ABORTED; - } - if ((Type =3D=3D SETUPTXT) && (FdName =3D=3D NULL) ) { - printf ("Error: The