summaryrefslogtreecommitdiff
path: root/EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c
diff options
context:
space:
mode:
authorlgao4 <lgao4@6f19259b-4bc3-4df7-8a09-765794883524>2010-11-26 01:54:49 +0000
committerlgao4 <lgao4@6f19259b-4bc3-4df7-8a09-765794883524>2010-11-26 01:54:49 +0000
commit3e99020dbf0a159e34b84e7ae9125f2e368d5390 (patch)
tree0eb6339318f7bf7da1b679b8009cf267b2234566 /EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c
parent68bb5ce77e51cf35791e46f2202e36da97e5e6be (diff)
downloadedk2-platforms-3e99020dbf0a159e34b84e7ae9125f2e368d5390.tar.xz
Sync all bug fixes between EDK1.04 and EDK1.06 into EdkCompatibilityPkg.
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@11094 6f19259b-4bc3-4df7-8a09-765794883524
Diffstat (limited to 'EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c')
-rw-r--r--EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c740
1 files changed, 740 insertions, 0 deletions
diff --git a/EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c b/EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c
new file mode 100644
index 0000000000..c1a4c3358c
--- /dev/null
+++ b/EdkCompatibilityPkg/Sample/Tools/Source/UefiHiiPack/HiiPack.c
@@ -0,0 +1,740 @@
+/*++
+
+Copyright (c) 2008 - 2010, Intel Corporation. All rights reserved.<BR>
+This program and the accompanying materials
+are licensed and made available under the terms and conditions of the BSD License
+which accompanies this distribution. The full text of the license may be found at
+http://opensource.org/licenses/bsd-license.php
+
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+Module Name:
+
+ HiiPack.c
+
+Abstract:
+
+ Process HII package files to generate HII package list binary file or PE/COFF
+ resource script file (i.e. .rc file).
+
+--*/
+
+#include <stdio.h>
+#include <string.h>
+
+#include "Tiano.h"
+#include "EfiHii.h"
+
+#include "EfiUtilityMsgs.h"
+#include "ParseInf.h"
+
+#define UTILITY_VERSION "v1.0"
+#define UTILITY_NAME "HiiPack"
+#define MAX_PATH 260
+
+//
+// Define HII resource section type and name
+//
+#define HII_RESOURCE_TYPE "HII"
+#define HII_RESOURCE_NAME 1
+
+//
+// We'll store lists of file names from the command line in
+// a linked list of these
+//
+typedef struct _FILE_NAME_LIST {
+ struct _FILE_NAME_LIST *Next;
+ UINT8 FileName[MAX_PATH];
+ UINT32 PackageType;
+ UINT32 Length;
+ UINT8 *Data;
+} FILE_NAME_LIST;
+
+//
+// Create some defines for the different operation modes supported by this utility
+//
+#define MODE_CREATE_HII_RESOURCE_FILE 0x0001
+#define MODE_CREATE_HII_PACKAGE_LIST 0x0002
+
+//
+// Here's all our globals.
+//
+static struct {
+ FILE_NAME_LIST *PackageFile; // all include paths to search
+ FILE_NAME_LIST *LastPackageFile;
+ UINT8 PackageListFileName[MAX_PATH]; // Output package list file name
+ UINT8 ResourceFileName[MAX_PATH]; // Output HII resource file name
+ EFI_GUID Guid; // Guid specified on command line
+ BOOLEAN GuidSpecified;
+ BOOLEAN Verbose;
+ UINT32 Mode; // Mode this utility is operating in
+} mGlobals;
+
+static
+void
+Usage (
+ VOID
+ );
+
+static
+STATUS
+ProcessArgs (
+ int Argc,
+ char *Argv[]
+ );
+
+static
+void
+FreeGlobals (
+ VOID
+ );
+
+static
+void
+DumpRawBytes (
+ FILE *OutFptr,
+ UINT8 *Buffer,
+ int Count,
+ int Indent
+ );
+
+static
+STATUS
+CreateResourceScript (
+ char *OutputFileName,
+ EFI_GUID *PackageListGuid,
+ FILE_NAME_LIST *PackageFiles
+ );
+
+static
+STATUS
+CreatePackageList (
+ char *OutputFileName,
+ EFI_GUID *PackageListGuid,
+ FILE_NAME_LIST *PackageFiles
+ );
+
+int
+main (
+ int Argc,
+ char *Argv[]
+ )
+/*++
+
+Routine Description:
+
+ Call the routine to parse the command-line options, then process the file.
+
+Arguments:
+
+ Standard C main() argc and argv.
+
+Returns:
+
+ 0 if successful
+ nonzero otherwise
+
+--*/
+{
+ STATUS Status;
+
+ //
+ // Set the utility name for error reporting purposes
+ //
+ SetUtilityName (UTILITY_NAME);
+
+ //
+ // Process the command-line arguments
+ //
+ Status = ProcessArgs (Argc, Argv);
+ if (Status != STATUS_SUCCESS) {
+ return Status;
+ }
+
+ //
+ // Switch based on args
+ //
+ if (mGlobals.Mode & MODE_CREATE_HII_RESOURCE_FILE) {
+ CreateResourceScript (mGlobals.ResourceFileName, &mGlobals.Guid, mGlobals.PackageFile);
+ }
+
+ if (mGlobals.Mode & MODE_CREATE_HII_PACKAGE_LIST) {
+ CreatePackageList (mGlobals.PackageListFileName, &mGlobals.Guid, mGlobals.PackageFile);
+ }
+
+ FreeGlobals ();
+
+ return GetUtilityStatus ();
+}
+
+/******************************************************************************/
+static const char *gRcFileHeader[] = {
+ "//",
+ "// DO NOT EDIT -- auto-generated file",
+ "//",
+ "// This file is generated by the hiipack utility",
+ "//",
+ NULL
+};
+
+static
+STATUS
+CreateResourceScript (
+ char *OutputFileName,
+ EFI_GUID *PackageListGuid,
+ FILE_NAME_LIST *PackageFiles
+ )
+/*++
+
+Routine Description:
+
+ Given a linked list of HII package files, walk the list to
+ process them and create a single HII resource script file.
+
+Arguments:
+
+ OutputFileName - name of output HII resource script file to create
+ PackageListGuid - the specified package list GUID
+ PackageFiles - linked list of HII package files to process
+
+Returns:
+
+ STATUS_SUCCESS - if successful
+ STATUS_ERROR - otherwise
+
+--*/
+{
+ STATUS Status;
+ UINT8 *PackageList;
+ UINT8 *Buffer;
+ UINT32 PackageListLen;
+ FILE *OutFptr;
+ UINTN Index;
+ FILE_NAME_LIST *Package;
+
+ //
+ // If no input HII pack files, then why are we here? Should have been caught when
+ // args were processed though.
+ //
+ if (PackageFiles == NULL) {
+ Error (NULL, 0, 0, "no input package file(s) specified", NULL);
+ return STATUS_ERROR;
+ }
+
+ OutFptr = NULL;
+ Status = STATUS_ERROR;
+
+ //
+ // Open the output file for writing
+ //
+ if ((OutFptr = fopen (OutputFileName, "w")) == NULL) {
+ Error (NULL, 0, 0, OutputFileName, "failed to open output file for writing");
+ goto Done;
+ }
+
+ //
+ // Write file header
+ //
+ for (Index = 0; gRcFileHeader[Index] != NULL; Index++) {
+ fprintf (OutFptr, "%s\n", gRcFileHeader[Index]);
+ }
+
+ //
+ // Write nameID and typeID
+ //
+ fprintf (OutFptr, "\n");
+ fprintf (OutFptr, "%d %s\n", HII_RESOURCE_NAME, HII_RESOURCE_TYPE);
+ fprintf (OutFptr, "{\n");
+
+ //
+ // Prepare package list
+ //
+ PackageListLen = sizeof (EFI_HII_PACKAGE_LIST_HEADER);
+ Package = PackageFiles;
+ while (Package != NULL) {
+ PackageListLen += Package->Length;
+ Package = Package->Next;
+ }
+ //
+ // Inlucde the length of EFI_HII_PACKAGE_END
+ //
+ PackageListLen += sizeof (EFI_HII_PACKAGE_HEADER);
+
+ Buffer = (UINT8 *) malloc (PackageListLen);
+ if (Buffer == NULL) {
+ Error (NULL, 0, 0, "memory allocation failure", NULL);
+ goto Done;
+ }
+ PackageList = Buffer;
+
+ memcpy (Buffer, PackageListGuid, sizeof (EFI_GUID));
+ Buffer += sizeof (EFI_GUID);
+ memcpy (Buffer, &PackageListLen, sizeof (UINT32));
+ Buffer += sizeof (UINT32);
+
+ Package = PackageFiles;
+ while (Package != NULL) {
+ memcpy (Buffer, Package->Data, Package->Length);
+ Buffer += Package->Length;
+ Package = Package->Next;
+ }
+ //
+ // Append EFI_HII_PACKAGE_END
+ //
+ ((EFI_HII_PACKAGE_HEADER *) Buffer)->Type = EFI_HII_PACKAGE_END;
+ ((EFI_HII_PACKAGE_HEADER *) Buffer)->Length = sizeof (EFI_HII_PACKAGE_HEADER);
+
+ //
+ // Dump package list
+ //
+ DumpRawBytes (OutFptr, PackageList, PackageListLen, 2);
+
+ //
+ // Write file tail
+ //
+ fprintf (OutFptr, "}\n");
+
+ Status = STATUS_SUCCESS;
+
+Done:
+ if (OutFptr != NULL) {
+ fclose (OutFptr);
+ }
+
+ return Status;
+}
+
+static
+STATUS
+CreatePackageList (
+ char *OutputFileName,
+ EFI_GUID *PackageListGuid,
+ FILE_NAME_LIST *PackageFiles
+ )
+/*++
+
+Routine Description:
+
+ Given a linked list of HII package files, walk the list to
+ process them and create a binary HII package list file.
+
+Arguments:
+
+ OutputFileName - name of output HII package list file to create
+ PackageListGuid - the specified package list GUID
+ PackageFiles - linked list of HII package files to process
+
+Returns:
+
+ STATUS_SUCCESS - if successful
+ STATUS_ERROR - otherwise
+
+--*/
+{
+ FILE *OutFptr;
+ UINT32 PackageListLen;
+ FILE_NAME_LIST *Package;
+
+ if (OutputFileName == NULL || PackageListGuid == NULL || PackageFiles == NULL) {
+ return STATUS_ERROR;
+ }
+
+ //
+ // Open the output file for writing
+ //
+ if ((OutFptr = fopen (OutputFileName, "wb")) == NULL) {
+ Error (NULL, 0, 0, OutputFileName, "failed to open output file for writing");
+ goto Done;
+ }
+
+ //
+ // Write package list header
+ //
+ PackageListLen = sizeof (EFI_HII_PACKAGE_LIST_HEADER);
+ Package = PackageFiles;
+ while (Package != NULL) {
+ PackageListLen += Package->Length;
+ Package = Package->Next;
+ }
+ fwrite (PackageListGuid, sizeof (UINT8), sizeof (EFI_GUID), OutFptr);
+ fwrite (&PackageListLen, sizeof (UINT8), sizeof (UINT32), OutFptr);
+
+ //
+ // Write packages
+ //
+ Package = PackageFiles;
+ while (Package != NULL) {
+ fwrite (Package->Data, sizeof (UINT8), Package->Length, OutFptr);
+ Package = Package->Next;
+ }
+
+Done:
+ if (OutFptr != NULL) {
+ fclose (OutFptr);
+ }
+
+ return STATUS_SUCCESS;
+}
+
+static
+void
+FreeGlobals (
+ VOID
+ )
+/*++
+
+Routine Description:
+
+ Free up an memory we allocated so we can exit cleanly
+
+Arguments:
+
+Returns: NA
+
+--*/
+{
+ FILE_NAME_LIST *Next;
+
+ //
+ // Free up input package file names
+ //
+ while (mGlobals.PackageFile != NULL) {
+ Next = mGlobals.PackageFile->Next;
+ if (mGlobals.PackageFile->Data != NULL) {
+ free (mGlobals.PackageFile->Data);
+ }
+ free (mGlobals.PackageFile);
+ mGlobals.PackageFile = Next;
+ }
+}
+
+static
+void
+DumpRawBytes (
+ FILE *OutFptr,
+ UINT8 *Buffer,
+ int Count,
+ int Indent
+ )
+/*++
+
+Routine Description:
+
+ Dump buffer data into output file.
+
+Arguments:
+
+ OutFptr - FILE pointer to output file.
+ Buffer - the buffer to dump
+ Count - number of bytes to dump
+ Indent - indent at each line start
+
+Returns:
+
+ Nothing.
+
+--*/
+{
+ int Counter;
+ int Count2;
+ UINT16 *Ptr16;
+
+ Ptr16 = (UINT16 *) Buffer;
+ Count2 = Count - (Count & 0x1);
+
+ for (Counter = 0; Counter < Count2; Counter += 2) {
+ if ((Counter & 0xF) == 0) {
+ if (Counter == 0) {
+ fprintf (OutFptr, "%*c", Indent, ' ');
+ } else {
+ fprintf (OutFptr, "\n%*c", Indent, ' ');
+ }
+ }
+
+ fprintf (OutFptr, "0x%04X, ", (unsigned int) *Ptr16);
+ Ptr16++;
+ }
+
+ //
+ // Handle the last byte
+ //
+ if ((Count & 0x1) != 0) {
+ if ((Counter & 0xF) == 0) {
+ if (Counter == 0) {
+ fprintf (OutFptr, "%*c", Indent, ' ');
+ } else {
+ fprintf (OutFptr, "\n%*c", Indent, ' ');
+ }
+ }
+
+ fprintf (OutFptr, "0x%04X, ", (unsigned int) (*Ptr16 & 0xff));
+ }
+
+ fprintf (OutFptr, "\n");
+}
+
+static
+STATUS
+LoadPackage (
+ FILE_NAME_LIST *NameList
+ )
+/*++
+
+Routine Description:
+
+ Process the command line arguments
+
+Arguments:
+
+ NameList - the FILE_NAME_LIST linked list node
+
+Returns:
+
+ STATUS_SUCCESS - if successful
+ STATUS_ERROR - otherwise
+
+--*/
+{
+ STATUS Status;
+ FILE *InFptr;
+ UINT32 BufferSize;
+ UINT8 *Buffer;
+ EFI_HII_PACKAGE_HEADER *PackageHeader;
+ EFI_IFR_FORM_SET *FormSet;
+
+ Status = STATUS_SUCCESS;
+ if (NameList == NULL) {
+ return STATUS_ERROR;
+ }
+
+ //
+ // Try to open the package file
+ //
+ if ((InFptr = fopen (NameList->FileName, "rb")) == NULL) {
+ Error (NULL, 0, 0, NameList->FileName, "failed to open input file for read");
+ return STATUS_ERROR;
+ }
+
+ //
+ // Get the file size, then allocate a buffer and read in the file contents.
+ //
+ fseek (InFptr, 0, SEEK_END);
+ BufferSize = (UINT32) ftell (InFptr);
+ fseek (InFptr, 0, SEEK_SET);
+ Buffer = (UINT8 *) malloc (BufferSize);
+ if (Buffer == NULL) {
+ Error (NULL, 0, 0, "memory allocation failure", NULL);
+ goto Done;
+ }
+
+ if (fread (Buffer, sizeof (UINT8), BufferSize, InFptr) != BufferSize) {
+ Error (NULL, 0, 0, NameList->FileName, "error reading file contents");
+ Status = STATUS_ERROR;
+ goto Done;
+ }
+
+ NameList->Length = BufferSize;
+ NameList->Data = Buffer;
+
+ PackageHeader = (EFI_HII_PACKAGE_HEADER *) Buffer;
+ NameList->PackageType = PackageHeader->Type;
+
+ if (!mGlobals.GuidSpecified && NameList->PackageType == EFI_HII_PACKAGE_FORMS) {
+ FormSet = (EFI_IFR_FORM_SET *) (Buffer + sizeof (EFI_HII_PACKAGE_HEADER));
+ memcpy (&mGlobals.Guid, &FormSet->Guid, sizeof (EFI_GUID));
+ mGlobals.GuidSpecified = TRUE;
+ }
+
+Done:
+ fclose (InFptr);
+
+ return Status;
+}
+
+
+static
+STATUS
+ProcessArgs (
+ int Argc,
+ char *Argv[]
+ )
+/*++
+
+Routine Description:
+
+ Process the command line arguments
+
+Arguments:
+
+ As per standard C main()
+
+Returns:
+
+ STATUS_SUCCESS - if successful
+ STATUS_ERROR - otherwise
+
+--*/
+{
+ FILE_NAME_LIST *NewList;
+ STATUS Status;
+
+ Status = STATUS_SUCCESS;
+ memset ((void *) &mGlobals, 0, sizeof (mGlobals));
+
+ //
+ // Skip program name
+ //
+ Argc--;
+ Argv++;
+
+ if (Argc == 0) {
+ Usage ();
+ return STATUS_ERROR;
+ }
+
+ if (_stricmp (Argv[0], "-h") == 0 || _stricmp (Argv[0], "-?") == 0) {
+ Usage ();
+ return STATUS_ERROR;
+ }
+
+ //
+ // Process until no more args.
+ //
+ while (Argc > 0) {
+ if (_stricmp (Argv[0], "-rc") == 0) {
+ Argc--;
+ Argv++;
+
+ if (Argc == 0) {
+ Error (UTILITY_NAME, 0, 0, "mising HII resource file name", NULL);
+ Status = STATUS_ERROR;
+ goto Done;
+ }
+
+ strcpy (mGlobals.ResourceFileName, Argv[0]);
+ mGlobals.Mode |= MODE_CREATE_HII_RESOURCE_FILE;
+
+ } else if (_stricmp (Argv[0], "-hii") == 0) {
+ Argc--;
+ Argv++;
+
+ if (Argc == 0) {
+ Error (UTILITY_NAME, 0, 0, "mising HII package list file name", NULL);
+ Status = STATUS_ERROR;
+ goto Done;
+ }
+
+ strcpy (mGlobals.PackageListFileName, Argv[0]);
+ mGlobals.Mode |= MODE_CREATE_HII_PACKAGE_LIST;
+
+ } else if (_stricmp (Argv[0], "-g") == 0) {
+ Argc--;
+ Argv++;
+
+ if (Argc == 0) {
+ Error (UTILITY_NAME, 0, 0, "mising package list GUID", NULL);
+ Status = STATUS_ERROR;
+ goto Done;
+ }
+
+ Status = StringToGuid (Argv[0], &mGlobals.Guid);
+ if (Status != STATUS_SUCCESS) {
+ goto Done;
+ }
+ mGlobals.GuidSpecified = TRUE;
+
+ } else {
+ //
+ // This is a package file
+ //
+ NewList = malloc (sizeof (FILE_NAME_LIST));
+ if (NewList == NULL) {
+ Error (UTILITY_NAME, 0, 0, "memory allocation failure", NULL);
+ Status = STATUS_ERROR;
+ goto Done;
+ }
+
+ memset (NewList, 0, sizeof (FILE_NAME_LIST));
+ strcpy (NewList->FileName, Argv[0]);
+
+ if (mGlobals.PackageFile == NULL) {
+ mGlobals.PackageFile = NewList;
+ } else {
+ mGlobals.LastPackageFile->Next = NewList;
+ }
+ mGlobals.LastPackageFile = NewList;
+
+ Status = LoadPackage (NewList);
+ if (Status != STATUS_SUCCESS) {
+ goto Done;
+ }
+ }
+
+ Argc--;
+ Argv++;
+ }
+
+ if (!mGlobals.GuidSpecified) {
+ Error (UTILITY_NAME, 0, 0, "please specify HII pakcage list GUID", NULL);
+ Status = STATUS_ERROR;
+ }
+
+Done:
+ if (Status != STATUS_SUCCESS) {
+ FreeGlobals ();
+ }
+
+ return Status;
+}
+
+static
+void
+Usage (
+ VOID
+ )
+/*++
+
+Routine Description:
+
+ Print usage information for this utility.
+
+Arguments:
+
+ None.
+
+Returns:
+
+ Nothing.
+
+--*/
+{
+ int i;
+ const char *Str[] = {
+ UTILITY_NAME" "UTILITY_VERSION" - UEFI HII Package List Utility",
+ " Copyright (C), 2008 Intel Corporation",
+
+#if ( defined(UTILITY_BUILD) && defined(UTILITY_VENDOR) )
+ " Built from "UTILITY_BUILD", project of "UTILITY_VENDOR,
+#endif
+ "",
+ "Usage:",
+ " "UTILITY_NAME" [OPTION] PACKAGE [PACKAGE [...]]",
+ "Description:",
+ " Merge HII package files into a single HII Package List.",
+ "Options:",
+ " -rc FileName write output to PE/COFF Resource Script file",
+ " -hii FileName write output to binary Package List file",
+ " -g GUID use GUID for the HII Package List Guid",
+ "",
+ "PACKAGE is the raw binary HII package file generated by StrGather or",
+ "VfrCompiler which named as *.hpk. For example, merge a Form package and",
+ "a String package into one HII package list:",
+ " \""UTILITY_NAME" -rc Sample.rc -hii Sample.hii \\",
+ " -g 12345678-1234-1234-1234-123456789abc Vfr.hpk Strings.hpk\"",
+ NULL
+ };
+ for (i = 0; Str[i] != NULL; i++) {
+ fprintf (stdout, "%s\n", Str[i]);
+ }
+}