Silicon/Intel/Tools/FitGen/FitGen.c | 1186 ++++++++++++++++----------- Silicon/Intel/Tools/FitGen/FitGen.h | 7 +- 2 files changed, 722 insertions(+), 471 deletions(-)
REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4155
With new implementation, FITGEN will populate info needed
for the PROT assisted BootGuard solution and TXT on servers
using FIT 4 Entry. FitGen based on the CPU FMS FITGEN will
decide to call one of the two Type 2 FIT entry.
Signed-off-by: Rahul R Kumar <rahul.r.kumar@intel.com>
---
Silicon/Intel/Tools/FitGen/FitGen.c | 1186 ++++++++++++++++-----------
Silicon/Intel/Tools/FitGen/FitGen.h | 7 +-
2 files changed, 722 insertions(+), 471 deletions(-)
diff --git a/Silicon/Intel/Tools/FitGen/FitGen.c b/Silicon/Intel/Tools/FitGen/FitGen.c
index 87123f9922..4ba07945a6 100644
--- a/Silicon/Intel/Tools/FitGen/FitGen.c
+++ b/Silicon/Intel/Tools/FitGen/FitGen.c
@@ -44,11 +44,18 @@ typedef struct {
#define BIOS_MODULE_ALIGNMENT 0x3F // 64 bytes for AnC
#define MICROCODE_ALIGNMENT 0x7FF
+#define MICROCODE_EXTERNAL_HEADER_SIZE 0x30
+
#define ACM_PKCS_1_5_RSA_SIGNATURE_SHA256_SIZE 256
#define ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE 384
-#define ACM_HEADER_VERSION_3 (3 << 16)
-#define ACM_HEADER_VERSION_0 (0)
+#define ACM_XMSS_PUBLIC_KEY_SIZE 64
+#define ACM_XMSS_SIGNATURE_SIZE 2692
+
+#define ACM_HEADER_VERSION_5 0x50004
+#define ACM_HEADER_VERSION_4 (4 << 16)
+#define ACM_HEADER_VERSION_3 (3 << 16)
+#define ACM_HEADER_VERSION_0 (0)
#define ACM_MODULE_TYPE_CHIPSET_ACM 2
#define ACM_MODULE_SUBTYPE_CAPABLE_OF_EXECUTE_AT_RESET 0x1
#define ACM_MODULE_SUBTYPE_ANC_MODULE 0x2
@@ -56,6 +63,37 @@ typedef struct {
#define ACM_MODULE_FLAG_DEBUG_SIGN 0x8000
#define NIBBLES_TO_BYTE(A, B) (UINT8)(((A & (0x0F)) << 4) | (B & 0x0F))
+//
+//Flash Map 0 Register (Flash Descriptor Records)
+//
+typedef struct {
+ UINT32 Fcba : 8; //Bits[7:0]: Flash Component Base Address
+ UINT32 Nc : 2; //Bits[9:8]: Number of Components
+ UINT32 Rsvd0: 1; //Bit10: Reserved
+ UINT32 Rsvd1: 1; //Bit11: Reserved
+ UINT32 Rsvd2: 1; //Bit12: Reserved
+ UINT32 Rsvd3: 3; //Bits[15:13]: Reserved
+ UINT32 Frba : 8; //Bits[23:16]: Flash Region Base Address
+ UINT32 Rsvd4: 3; //Bits[26:24]: Reserved
+ UINT32 Rsvd5: 5; //Bits[31:27]: Reserved
+} FLASH_MAP_0_REGISTER;
+
+//
+//Flash Region 1 (BIOS) Register (Flash Descriptor Records)
+//
+typedef struct {
+ UINT32 RegionBase : 15; //Bits[14:0]: Region base
+ UINT32 Rsvd : 1; //Bit15: Reserved
+ UINT32 RegionLimit: 15; //Bits[30:16]: Region limit
+ UINT32 Rsvd1 : 1; //Bit31: Reserved
+} FLASH_REGION_1_BIOS_REGISTER;
+
+#define FLASH_VALID_SIGNATURE 0x0FF0A55A //Flash Valid Signature (Flash Descriptor Records)
+#define FLVALSIG_BASE_OFFSET 0x10 //Flash Valid Signature Base Offset
+#define FLMAP0_BASE_OFFSET 0x14 //Flash Map 0 Register Base Offset
+
+#define ACMFV_GUID \
+ { 0x8a4b197f, 0x1113, 0x43d0, { 0xa2, 0x3f, 0x26, 0xf3, 0x69, 0xb2, 0xb8, 0x41 }}
typedef struct {
UINT16 ModuleType;
@@ -98,6 +136,8 @@ typedef struct {
#define CHIPSET_ACM_TYPE_BIOS 0
#define CHIPSET_ACM_TYPE_SINIT 1
+#define DEFAULT_ACM_EXTENDED_MASK 0x00FFFFFF
+
typedef struct {
UINT32 Guid0;
UINT32 Guid1;
@@ -238,6 +278,7 @@ typedef struct {
#define FIT_TABLE_TYPE_MICROCODE 1
#define FIT_TABLE_TYPE_STARTUP_ACM 2
#define FIT_TABLE_TYPE_DIAGNST_ACM 3
+#define FIT_TABLE_TYPE_PROT_BOOT_POLICY 4
#define FIT_TABLE_TYPE_BIOS_MODULE 7
#define FIT_TABLE_TYPE_TPM_POLICY 8
#define FIT_TABLE_TYPE_BIOS_POLICY 9
@@ -252,7 +293,6 @@ typedef struct {
#define FIT_TABLE_TYPE_VAB_BOOT_IMAGE_MANIFEST 27
#define FIT_TABLE_TYPE_VAB_BOOT_KEY_MANIFEST 28
-
//
// With OptionalModule Address isn't known until free space has been
// identified and the optional module has been copied into the FLASH
@@ -284,9 +324,10 @@ typedef struct {
UINT32 GlobalVersion;
UINT32 FitHeaderVersion;
FIT_TABLE_CONTEXT_ENTRY StartupAcm[MAX_STARTUP_ACM_ENTRY];
- UINT32 StartupAcmVersion[MAX_STARTUP_ACM_ENTRY];
+ UINT32 StartupAcmFvSize;
FIT_TABLE_CONTEXT_ENTRY DiagnstAcm;
UINT32 DiagnstAcmVersion;
+ FIT_TABLE_CONTEXT_ENTRY ProtBootPolicy;
FIT_TABLE_CONTEXT_ENTRY BiosModule[MAX_BIOS_MODULE_ENTRY];
UINT32 BiosModuleVersion;
FIT_TABLE_CONTEXT_ENTRY Microcode[MAX_MICROCODE_ENTRY];
@@ -305,25 +346,87 @@ xtoi (
char *str
);
-VOID
-PrintUtilityInfo (
- VOID
- )
-/*++
+/**
+ Pass in supported CPU extended family/extended model/type
+ /family/model without stepping or CPU FMS >> 4.
+
+ @param FitEntry Pointer to Fit Entry table.
+ @param AcmFamilyModel Acm Family Model stepping.
+ @param AcmMask ACM mask.
+
+ @return STATUS_SUCCESS The file found and data read.
+**/
+STATUS
+SetFirmwareInterfaceTableEntryAcmFms(
+ FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry,
+ UINT32 AcmFamilyModel,
+ UINT32 AcmMask
+)
+{
+ if (FitEntry == NULL) {
+ return STATUS_ERROR;
+ }
+
+ FitEntry->Checksum = (UINT8)(((AcmFamilyModel & 0x000F0000) >> 16) | (((AcmMask & 0x000F0000) >> 16) << 4));
+ FitEntry->Rsvd = (UINT8)((AcmMask & 0x0000FF00) >> 8);
+ FitEntry->Size[2] = (UINT8)(AcmMask & 0x000000FF);
+ FitEntry->Size[1] = (UINT8)((AcmFamilyModel & 0x0000FF00) >> 8);
+ FitEntry->Size[0] = (UINT8)(AcmFamilyModel & 0x000000FF);
+ return STATUS_SUCCESS;
+}
+
+/**
+ Set the FIT Entry Size.
+
+ @param FitEntry Pointer to Fit Entry table.
+ @param SizeEntry Size of FIT entry.
-Routine Description:
+ @return STATUS_SUCCESS The file found and data read.
+**/
+STATUS
+SetFirmwareInterfaceTableEntrySize (
+ FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry,
+ UINT32 SizeEntry
+)
+{
+ if (FitEntry == NULL) {
+ return STATUS_ERROR;
+ }
+ FitEntry->Size[2] = (UINT8)((SizeEntry & 0x00FF0000) >> 16);
+ FitEntry->Size[1] = (UINT8)((SizeEntry & 0x0000FF00) >> 8);
+ FitEntry->Size[0] = (UINT8)(SizeEntry & 0x000000FF);
+ return STATUS_SUCCESS;
+}
- Displays the standard utility information to STDOUT
+/**
+ Get the FIT Entry Size.
-Arguments:
+ @param FitEntry Pointer to Fit Entry table.
- None
+ @return FitEntry pointer
+**/
+UINT32
+GetFirmwareInterfaceTableEntrySize (
+ FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry
+)
+{
+ if (FitEntry == NULL) {
+ return 0;
+ }
+ return (((UINT32)FitEntry->Size[2] << 16) | ((UINT32)FitEntry->Size[1] << 8) | (UINT32)FitEntry->Size[0]);
+}
-Returns:
+/**
+ Displays the FIT utility info
- None
+ @param None
---*/
+ @return None
+**/
+VOID
+PrintUtilityInfo (
+ VOID
+ )
{
printf (
"%s - Tiano IA32/X64 FIT table generation Utility for FIT spec revision %i.%i."" Version %i.%i\n\n",
@@ -335,25 +438,17 @@ Returns:
);
}
+/**
+ Displays the utility usage syntax to STDOUT.
+
+ @param None
+
+ @return None
+**/
VOID
PrintUsage (
VOID
)
-/*++
-
-Routine Description:
-
- Displays the utility usage syntax to STDOUT
-
-Arguments:
-
- None
-
-Returns:
-
- None
-
---*/
{
printf ("Usage (generate): %s [-D] InputFvRecoveryFile OutputFvRecoveryFile\n"
"\t[-V <FitEntryDefaultVersion>]\n"
@@ -371,6 +466,7 @@ Returns:
"\t[-M <MicrocodeAddress MicrocodeSize>] [-M ...]|[-U <MicrocodeFv MicrocodeBase>|<MicrocodeRegionOffset MicrocodeRegionSize>|<MicrocodeGuid>] [-V <MicrocodeVersion>]\n"
"\t[-O RecordType <RecordDataAddress RecordDataSize>|<RESERVE RecordDataSize>|<RecordDataGuid>|<RecordBinFile>|<CseRecordSubType RecordBinFile> [-V <RecordVersion>]] [-O ... [-V ...]]\n"
"\t[-P RecordType <IndexPort DataPort Width Bit Index> [-V <RecordVersion>]] [-P ... [-V ...]]\n"
+ "\t[-BP <BootPolicySize>[-V <BootPolicyVersion>]\n"
"\t[-T <FixedFitLocation>]\n"
, UTILITY_NAME);
printf (" Where:\n");
@@ -407,12 +503,14 @@ Returns:
printf ("\tRecordDataGuid - FIT entry record data GUID.\n");
printf ("\tRecordBinFile - FIT entry record data binary file.\n");
printf ("\tCseRecordSubType - FIT entry record subtype. Use to further distinguish CSE entries (see FIT spec revision 1.2 chapter 4.12).\n");
+ printf ("\tBootPolicySize - FIT entry size for type 04 boot policy.\n");
printf ("\tFitEntryDefaultVersion - The default version for all FIT table entries. 0x%04x is used if this is not specified.\n", DEFAULT_FIT_ENTRY_VERSION);
printf ("\tFitHeaderVersion - The version for FIT header. (Override default version)\n");
printf ("\tStartupAcmVersion - The version for StartupAcm. (Override default version)\n");
printf ("\tBiosModuleVersion - The version for BiosModule. (Override default version)\n");
printf ("\tMicrocodeVersion - The version for Microcode. (Override default version)\n");
printf ("\tRecordVersion - The version for Record. (Override default version)\n");
+ printf ("\tBootPolicyVersion - The version for BootPolicy. (Override default version)\n");
printf ("\tIndexPort - The Index Port Number.\n");
printf ("\tDataPort - The Data Port Number.\n");
printf ("\tWidth - The Width of the port.\n");
@@ -427,11 +525,20 @@ Returns:
printf ("\tSTATUS_SUCCESS=%d, STATUS_WARNING=%d, STATUS_ERROR=%d\n", STATUS_SUCCESS, STATUS_WARNING, STATUS_ERROR);
}
+/**
+ Set Value of memory.
+
+ @param Buffer The pointer where we need to set the memory.
+ @param Length Size of memory to be set.
+ @param Value Value of memory to be set.
+
+ @return Buffer The pointer address.
+**/
VOID *
SetMem (
- OUT VOID *Buffer,
- IN UINTN Length,
- IN UINT8 Value
+ OUT VOID *Buffer,
+ IN UINTN Length,
+ IN UINT8 Value
)
{
//
@@ -448,6 +555,14 @@ SetMem (
return Buffer;
}
+/**
+ check the input Path.
+
+ @param String Passed input path.
+
+ @return TRUE If the input path is correct.
+ @return FLASE if the input path is not correct.
+**/
BOOLEAN
CheckPath (
IN CHAR8 * String
@@ -476,28 +591,20 @@ CheckPath (
return TRUE;
}
+/**
+ Get fixed FIT location from argument.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings.
+
+ @return FitLocation The FIT location specified by Argument.
+ @return 0 Argument parse fail.
+**/
UINT32
GetFixedFitLocation (
IN INTN argc,
IN CHAR8 **argv
)
-/*++
-
-Routine Description:
-
- Get fixed FIT location from argument
-
-Arguments:
-
- argc - Number of command line parameters.
- argv - Array of pointers to parameter strings.
-
-Returns:
-
- FitLocation - The FIT location specified by Argument
- 0 - Argument parse fail
-
-*/
{
UINT32 FitLocation;
INTN Index;
@@ -516,6 +623,18 @@ Returns:
return FitLocation;
}
+/**
+ Read input file.
+
+ @param FileName The input file name.
+ @param FileData The input file data, the memory is aligned.
+ @param FileSize The input file size.
+ @param FileBufferRaw The memory to hold input file data. The caller must free the memory.
+
+ @return STATUS_SUCCESS The file found and data read.
+ @return STATUS_ERROR The file data is not read.
+ @return STATUS_WARNING The file is not found.
+**/
STATUS
ReadInputFile (
IN CHAR8 *FileName,
@@ -523,26 +642,6 @@ ReadInputFile (
OUT UINT32 *FileSize,
OUT UINT8 **FileBufferRaw OPTIONAL
)
-/*++
-
-Routine Description:
-
- Read input file
-
-Arguments:
-
- FileName - The input file name
- FileData - The input file data, the memory is aligned.
- FileSize - The input file size
- FileBufferRaw - The memory to hold input file data. The caller must free the memory.
-
-Returns:
-
- STATUS_SUCCESS - The file found and data read
- STATUS_ERROR - The file data is not read
- STATUS_WARNING - The file is not found
-
---*/
{
FILE *FpIn;
UINT32 TempResult;
@@ -612,24 +711,20 @@ Returns:
return STATUS_SUCCESS;
}
+/**
+ Find next FvHeader in the FileBuffer.
+
+ @param FileBuffer The start FileBuffer which needs to be searched.
+ @param FileLength The whole File Length.
+
+ @return FvHeader The FvHeader is found successfully.
+ @return NULL The FvHeader is not found.
+**/
UINT8 *
FindNextFvHeader (
IN UINT8 *FileBuffer,
IN UINTN FileLength
)
-/*++
-
- Routine Description:
- Find next FvHeader in the FileBuffer
-
- Parameters:
- FileBuffer - The start FileBuffer which needs to be searched
- FileLength - The whole File Length.
- Return:
- FvHeader - The FvHeader is found successfully.
- NULL - The FvHeader is not found.
-
---*/
{
UINT8 *FileHeader;
EFI_FIRMWARE_VOLUME_HEADER *FvHeader;
@@ -679,6 +774,17 @@ FindNextFvHeader (
return NULL;
}
+/**
+ Find File with GUID in an FV.
+
+ @param FvBuffer FV binary buffer.
+ @param FvSize FV size.
+ @param Guid File GUID value to be searched.
+ @param FileSize Guid File size.
+
+ @return FileLocation Guid File location.
+ @return NULL Guid File is not found.
+**/
UINT8 *
FindFileFromFvByGuid (
IN UINT8 *FvBuffer,
@@ -686,25 +792,6 @@ FindFileFromFvByGuid (
IN EFI_GUID *Guid,
OUT UINT32 *FileSize
)
-/*++
-
-Routine Description:
-
- Find File with GUID in an FV
-
-Arguments:
-
- FvBuffer - FV binary buffer
- FvSize - FV size
- Guid - File GUID value to be searched
- FileSize - Guid File size
-
-Returns:
-
- FileLocation - Guid File location.
- NULL - Guid File is not found.
-
---*/
{
EFI_FIRMWARE_VOLUME_HEADER *FvHeader;
EFI_FFS_FILE_HEADER *FileHeader;
@@ -783,28 +870,20 @@ Returns:
return NULL;
}
+/**
+ Check whether a string is a GUID.
+
+ @param StringData The String.
+ @param Guid Guid to hold the value
+
+ @return TRUE StringData is a GUID, and Guid field is filled.
+ @return FALSE StringData is not a GUID.
+**/
BOOLEAN
IsGuidData (
IN CHAR8 *StringData,
OUT EFI_GUID *Guid
)
-/*++
-
-Routine Description:
-
- Check whether a string is a GUID
-
-Arguments:
-
- StringData - the String
- Guid - Guid to hold the value
-
-Returns:
-
- TRUE - StringData is a GUID, and Guid field is filled.
- FALSE - StringData is not a GUID
-
---*/
{
if (strlen (StringData) != strlen ("00000000-0000-0000-0000-000000000000")) {
return FALSE;
@@ -821,6 +900,17 @@ Returns:
return TRUE;
}
+/**
+ Get FIT entry number and fill global FIT table context, from argument.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings.
+ @param FdBuffer FD binary buffer.
+ @param FdSize FD size.
+
+ @return FitEntryNumber The FIT entry number.
+ @return 0 Argument parse fail.
+**/
VOID
CheckOverlap (
IN UINT32 Address,
@@ -875,6 +965,17 @@ CheckOverlap (
}
}
+/**
+ Get FIT entry number and fill global FIT table context, from argument.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings.
+ @param FdBuffer FD binary buffer.
+ @param FdSize FD size.
+
+ @return FitEntryNumber The FIT entry number.
+ @return 0 Argument parse fail.
+**/
UINT8 *
GetMicrocodeBufferFromFv (
EFI_FIRMWARE_VOLUME_HEADER *FvHeader
@@ -906,6 +1007,17 @@ GetMicrocodeBufferFromFv (
return MicrocodeBuffer;
}
+/**
+ Get FIT entry number and fill global FIT table context, from argument.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings.
+ @param FdBuffer FD binary buffer.
+ @param FdSize FD size.
+
+ @return FitEntryNumber The FIT entry number.
+ @return 0 Argument parse fail.
+**/
UINT32
GetFitEntryNumber (
IN INTN argc,
@@ -913,25 +1025,6 @@ GetFitEntryNumber (
IN UINT8 *FdBuffer,
IN UINT32 FdSize
)
-/*++
-
-Routine Description:
-
- Get FIT entry number and fill global FIT table context, from argument
-
-Arguments:
-
- argc - Number of command line parameters.
- argv - Array of pointers to parameter strings.
- FdBuffer - FD binary buffer
- FdSize - FD size
-
-Returns:
-
- FitEntryNumber - The FIT entry number
- 0 - Argument parse fail
-
-*/
{
EFI_GUID Guid;
EFI_GUID MicrocodeFfsGuid;
@@ -1188,7 +1281,7 @@ Returns:
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Type = FIT_TABLE_TYPE_STARTUP_ACM;
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Address = (UINT32)BiosInfoStruct[BiosInfoIndex].Address;
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Size = (UINT32)BiosInfoStruct[BiosInfoIndex].Size;
- gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = BiosInfoStruct[BiosInfoIndex].Version;
+ gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = BiosInfoStruct[BiosInfoIndex].Version;
gFitTableContext.StartupAcmNumber ++;
gFitTableContext.FitEntryNumber ++;
break;
@@ -1203,6 +1296,13 @@ Returns:
gFitTableContext.DiagnstAcmVersion = DEFAULT_FIT_ENTRY_VERSION;
gFitTableContext.FitEntryNumber ++;
break;
+ case FIT_TABLE_TYPE_PROT_BOOT_POLICY:
+ gFitTableContext.ProtBootPolicy.Type = FIT_TABLE_TYPE_PROT_BOOT_POLICY;
+ gFitTableContext.ProtBootPolicy.Address = (UINT32)BiosInfoStruct[BiosInfoIndex].Address;
+ gFitTableContext.ProtBootPolicy.Size = (UINT32)BiosInfoStruct[BiosInfoIndex].Size;
+ gFitTableContext.ProtBootPolicy.Version = DEFAULT_FIT_ENTRY_VERSION;
+ gFitTableContext.FitEntryNumber ++;
+ break;
case FIT_TABLE_TYPE_BIOS_MODULE:
if ((BiosInfoStruct[BiosInfoIndex].Attributes & BIOS_INFO_STRUCT_ATTRIBUTE_BIOS_POST_IBB) != 0) {
continue;
@@ -1402,7 +1502,8 @@ Returns:
// not found
return 0;
}
- FileBuffer = (UINT8 *)MEMORY_TO_FLASH (FileBuffer, FdBuffer, FdSize);
+ gFitTableContext.StartupAcmFvSize = FdSize;
+ FileBuffer = (UINT8 *)MEMORY_TO_FLASH(FileBuffer, FdBuffer, FdSize);
Index += 2;
} else {
if (Index + 2 >= argc) {
@@ -1431,7 +1532,7 @@ Returns:
//
// Bypass
//
- gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = gFitTableContext.GlobalVersion;
+ gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = gFitTableContext.GlobalVersion;
} else {
if (Index + 2 >= argc) {
//
@@ -1443,7 +1544,7 @@ Returns:
//
// With the -I parameter should assign the type 2 entry version as 0x200 format
//
- gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = STARTUP_ACM_FIT_ENTRY_200_VERSION;
+ gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = STARTUP_ACM_FIT_ENTRY_200_VERSION;
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMS = (UINT32)xtoi (argv[Index + 1]);
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMSMask = (UINT32)xtoi (argv[Index + 2]);
@@ -1464,7 +1565,8 @@ Returns:
//
// Get offset from parameter
//
- gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = xtoi (argv[Index + 1]);
+ gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = gFitTableContext.GlobalVersion;
+ gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = xtoi (argv[Index + 1]);
Index += 2;
}
@@ -1942,7 +2044,7 @@ Returns:
//
// Get offset from parameter
//
- gFitTableContext.PortModule[gFitTableContext.PortModuleNumber].Version = xtoi (argv[Index + 1]);
+ gFitTableContext.PortModule[gFitTableContext.PortModuleNumber].Version = xtoi(argv[Index + 1]);
Index += 2;
}
@@ -1950,6 +2052,69 @@ Returns:
gFitTableContext.FitEntryNumber++;
}
+ //
+ // 6th, try FIT boot policy data
+ //
+ if ((Index < argc) &&
+ ((strcmp(argv[Index], "-BP") == 0) ||
+ (strcmp(argv[Index], "-bp") == 0))) {
+
+ if (Index + 1 >= argc) {
+ Error(NULL, 0, 0, "-BP: Invalid Parameters.", NULL);
+ FitEntryNumber = 0;
+ }
+
+ gFitTableContext.StartupAcmFvSize = GetFvAcmSizeFromFd(FdBuffer, FdSize);
+ if (gFitTableContext.StartupAcmFvSize == 0) {
+ Error(NULL, 0, 0, "FV_ACM not found in Fd file!", NULL);
+ }
+
+ //
+ // FIT type 04 record shares FV allocated space with FV_ACM.
+ //
+ FileSize = xtoi(argv[Index + 1]);
+
+ if (gFitTableContext.StartupAcm[0].Size + FileSize > gFitTableContext.StartupAcmFvSize) {
+ Error(NULL, 0, 0, "Error: not enough FV_ACM room for FIT type 04 record!", NULL);
+ FitEntryNumber = 0;
+ }
+
+ FileBuffer = malloc(FileSize);
+ if (FileBuffer == NULL) {
+ Error(NULL, 0, 0, "No sufficient memory to allocate!", NULL);
+ FitEntryNumber = 0;
+ }
+
+ SetMem(FileBuffer, FileSize, 0xFF);
+
+ gFitTableContext.ProtBootPolicy.Type = FIT_TABLE_TYPE_PROT_BOOT_POLICY;
+ gFitTableContext.ProtBootPolicy.Address = gFitTableContext.StartupAcm[0].Address + gFitTableContext.StartupAcm[0].Size;
+ gFitTableContext.ProtBootPolicy.Size = FileSize;
+ gFitTableContext.ProtBootPolicy.Version = 0;
+
+ Index += 2;
+
+ //
+ // 6.1 PROT Module version
+ //
+ if ((Index + 1 >= argc) ||
+ ((strcmp (argv[Index], "-V") != 0) &&
+ (strcmp (argv[Index], "-v") != 0)) ) {
+ //
+ // Bypass
+ //
+ gFitTableContext.ProtBootPolicy.Version = gFitTableContext.GlobalVersion;
+ } else {
+ //
+ // Get offset from parameter
+ //
+ gFitTableContext.ProtBootPolicy.Version = xtoi(argv[Index + 1]);
+ Index += 2;
+ }
+
+ gFitTableContext.FitEntryNumber++;
+ }
+
//
// Final: Check StartupAcm in BiosModule.
//
@@ -1974,31 +2139,23 @@ Returns:
return FitEntryNumber;
}
+/**
+ No enough space - it might happen that it is occupied by AP wake vector.
+ Last chance - skip this and search again.
+
+ @param FvBuffer FvRecovery binary buffer.
+ @param Address Address to be searched from.
+ @param Size Size need to be filled.
+
+ @return FitTableOffset The FIT table offset.
+ @return NULL No enough space for FIT table.
+**/
VOID *
FindSpaceSkipApVector (
IN UINT8 *FvBuffer,
IN UINT8 *Address,
IN UINTN Size
)
-/*++
-
-Routine Description:
-
- No enough space - it might happen that it is occupied by AP wake vector.
- Last chance - skip this and search again.
-
-Arguments:
-
- FvBuffer - FvRecovery binary buffer
- Address - Address to be searched from
- Size - Size need to be filled
-
-Returns:
-
- FitTableOffset - The FIT table offset
- NULL - No enough space for FIT table
-
-*/
{
UINT8 *ApVector;
UINT8 *NewAddress;
@@ -2018,6 +2175,17 @@ Returns:
return NewAddress;
}
+/**
+ Get free space for FIT table from FvRecovery.
+
+ @param FvBuffer FvRecovery binary buffer.
+ @param FvSize FvRecovery size.
+ @param FitTableSize The FIT table size.
+ @param FixedFitLocation Fixed FIT location provided by argument.
+
+ @return FitTableOffset The offset of FIT table in FvRecovery file.
+ @return NULL Free space not found.
+**/
VOID *
GetFreeSpaceForFit (
IN UINT8 *FvBuffer,
@@ -2025,25 +2193,6 @@ GetFreeSpaceForFit (
IN UINT32 FitTableSize,
IN UINT32 FixedFitLocation
)
-/*++
-
-Routine Description:
-
- Get free space for FIT table from FvRecovery
-
-Arguments:
-
- FvBuffer - FvRecovery binary buffer
- FvSize - FvRecovery size
- FitTableSize - The FIT table size
- FixedFitLocation - Fixed FIT location provided by argument
-
-Returns:
-
- FitTableOffset - The offset of FIT table in FvRecovery file
- NULL - Free space not found
-
---*/
{
UINT8 *FitTableOffset;
INTN Index;
@@ -2167,7 +2316,7 @@ Returns:
(gFitTableContext.OptionalModule[Index].Type == FIT_TABLE_TYPE_VAB_PROVISION_TABLE) ||
(gFitTableContext.OptionalModule[Index].Type == FIT_TABLE_TYPE_VAB_BOOT_IMAGE_MANIFEST) ||
(gFitTableContext.OptionalModule[Index].Type == FIT_TABLE_TYPE_VAB_BOOT_KEY_MANIFEST)) {
- // Let it 64 byte align
+ // Let it 64 byte align
AlignedSize += BIOS_MODULE_ALIGNMENT;
AlignedSize &= ~BIOS_MODULE_ALIGNMENT;
}
@@ -2228,25 +2377,17 @@ Returns:
return FitTableOffset;
}
+/**
+ Output FIT table information.
+
+ @param None
+
+ @return None
+**/
VOID
PrintFitData (
VOID
)
-/*++
-
-Routine Description:
-
- Output FIT table information
-
-Arguments:
-
- None
-
-Returns:
-
- None
-
---*/
{
UINT32 Index;
@@ -2257,11 +2398,15 @@ Returns:
printf ("Total FIT Entry number: 0x%x\n", gFitTableContext.FitEntryNumber);
printf ("FitHeader version: 0x%04x\n", gFitTableContext.FitHeaderVersion);
for (Index = 0; Index < gFitTableContext.StartupAcmNumber; Index++) {
- printf ("StartupAcm[%d] - (0x%08x, 0x%08x, 0x%04x)\n", Index, gFitTableContext.StartupAcm[Index].Address, gFitTableContext.StartupAcm[Index].Size, gFitTableContext.StartupAcmVersion[Index]);
+ printf("StartupAcm[%d] - (0x%08x, 0x%08x, 0x%04x)\n", Index, gFitTableContext.StartupAcm[Index].Address, gFitTableContext.StartupAcm[Index].Size, gFitTableContext.StartupAcm[Index].Version);
}
if (gFitTableContext.DiagnstAcm.Address != 0) {
printf ("DiagnosticAcm - (0x%08x, 0x%08x, 0x%04x)\n", gFitTableContext.DiagnstAcm.Address, gFitTableContext.DiagnstAcm.Size, gFitTableContext.DiagnstAcmVersion);
}
+
+ if (gFitTableContext.ProtBootPolicy.Address != 0) {
+ printf ("ProtBootPolicy - (0x%08x, 0x%08x, 0x%04x)\n", gFitTableContext.ProtBootPolicy.Address, gFitTableContext.ProtBootPolicy.Size, gFitTableContext.ProtBootPolicy.Version);
+ }
for (Index = 0; Index < gFitTableContext.BiosModuleNumber; Index++) {
printf ("BiosModule[%d] - (0x%08x, 0x%08x, 0x%04x)\n", Index, gFitTableContext.BiosModule[Index].Address, gFitTableContext.BiosModule[Index].Size, gFitTableContext.BiosModuleVersion);
}
@@ -2304,8 +2449,7 @@ CHAR8 *mFitTypeStr[] = {
"MICROCODE ",
"STARTUP_ACM",
"DIAGNST_ACM",
- " ",
- " ",
+ "BOOT_POLICY",
" ",
" ",
"BIOS_MODULE",
@@ -2320,27 +2464,19 @@ CHAR8 *mFitTypeStr[] = {
"CSE_SECUREB"
};
+/**
+ Convert FitEntry type to a string.
+
+ @param FitEntry Fit entry
+
+ @return String
+**/
CHAR8 mFitSignature[] = "'_FIT_ ' ";
CHAR8 mFitSignatureInHeader[] = "' ' ";
CHAR8 *
FitTypeToStr (
IN FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry
)
-/*++
-
-Routine Description:
-
- Convert FitEntry type to a string
-
-Arguments:
-
- FitEntry - Fit entry
-
-Returns:
-
- String
-
---*/
{
if (FitEntry->Type == FIT_TABLE_TYPE_HEADER) {
CopyMem (&mFitSignatureInHeader[1], &FitEntry->Address, sizeof(FitEntry->Address));
@@ -2361,27 +2497,19 @@ Returns:
}
}
+/**
+ Print Fit table in flash image.
+
+ @param FvBuffer FvRecovery binary buffer.
+ @param FvSize FvRecovery size.
+
+ @return None
+**/
VOID
PrintFitTable (
IN UINT8 *FvBuffer,
IN UINT32 FvSize
)
-/*++
-
-Routine Description:
-
- Print Fit table in flash image
-
-Arguments:
-
- FvBuffer - FvRecovery binary buffer
- FvSize - FvRecovery size
-
-Returns:
-
- None
-
---*/
{
FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry;
UINT32 EntryNum;
@@ -2460,11 +2588,12 @@ Returns:
}
/**
-
This function dump raw data.
- @param Data raw data
- @param Size raw data size
+ @param Data Raw data.
+ @param Size Raw data size.
+
+ @return none
**/
VOID
@@ -2480,12 +2609,12 @@ DumpData (
}
/**
-
This function dump raw data with colume format.
- @param Data raw data
- @param Size raw data size
+ @param Data Raw data
+ @param Size Raw data size
+ @return none
**/
VOID
DumpHex (
@@ -2532,25 +2661,17 @@ CHAR8 *mCapabilityStr[] = {
"STM support ",
};
+/**
+ DumpAcm information
+
+ @param Acm - ACM buffer
+
+ @retval None
+**/
VOID
DumpAcm (
IN ACM_FORMAT *Acm
)
-/*++
-
-Routine Description:
-
- DumpAcm information
-
-Arguments:
-
- Acm - ACM buffer
-
-Returns:
-
- None
-
---*/
{
CHIPSET_ACM_INFORMATION_TABLE *ChipsetAcmInformationTable;
CHIPSET_ID_LIST *ChipsetIdList;
@@ -2600,23 +2721,21 @@ Returns:
printf (" RSAPubKey - \n");
DumpHex (Buffer, Acm->KeySize * 4);
printf ("\n");
- Buffer += Acm->KeySize * 4;
- //
- // To simplify the tool and making it independent of ACM header change,
- // the rest of ACM parsing will be skipped starting ACM_HEADER_VERSION4
- //
- if((Acm->HeaderVersion != ACM_HEADER_VERSION_3) && (Acm->HeaderVersion != ACM_HEADER_VERSION_0)){
- printf (
- "*****************************************************************************\n\n"
- );
- return;
- }
+ Buffer += Acm->KeySize * 4; //add public key size (taken from header variable * 4) to buffer.
+
+ //add signature size to pointer.
if (Acm->HeaderVersion == ACM_HEADER_VERSION_3) {
printf (" RSASig - \n");
DumpHex (Buffer, ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE); // PKCS #1.5 RSA Signature
printf ("\n");
Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE;
- } else {
+ }
+ else if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) {
+ Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE;
+ Buffer += ACM_XMSS_PUBLIC_KEY_SIZE;
+ Buffer += ACM_XMSS_SIGNATURE_SIZE;
+ }
+ else {
printf (" RSAPubExp - %08x\n", *(UINT32 *)Buffer);
Buffer += 4;
@@ -2627,6 +2746,10 @@ Returns:
}
Buffer += Acm->ScratchSize * 4;
+ if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) {
+ Buffer += 60; //add reserved bytes.
+ }
+
if ((Acm->ModuleSubType & ACM_MODULE_SUBTYPE_ANC_MODULE) == 0) {
ChipsetAcmInformationTable = (CHIPSET_ACM_INFORMATION_TABLE *)Buffer;
printf ("Chipset ACM info:\n");
@@ -2697,28 +2820,77 @@ End:
);
}
-BOOLEAN
-CheckAcm (
- IN ACM_FORMAT *Acm,
- IN UINTN AcmMaxSize
- )
-/*++
+/**
+ Get ACM FMS information.
+
+ @param Acm ACM buffer.
+ @param AcmFms Get ACM FMS.
+ @param AcmMask Get ACM Mask.
+
+ @retval NULL
+**/
+VOID
+GetAcmFms(
+ IN ACM_FORMAT *Acm,
+ OUT UINT32 *AcmFms,
+ OUT UINT32 *AcmMask
+)
+{
+ UINT32 FmsOffset = 0;
+ UINT32 TmpFms = 0;
+ UINT32 TmpMask = 0;
+ UINT32 Index = 0;
+ PROCESSOR_ID_LIST *ProcessorIdList = NULL;
+
+ if ((Acm == NULL) || (AcmFms == NULL) || (AcmMask == NULL))
+ return;
+
+ *AcmFms = 0;
+ *AcmMask = 0;
+
+ switch (Acm->HeaderVersion) {
+ case ACM_HEADER_VERSION_3:
+ FmsOffset = *(UINT32*)((UINT8*)Acm + 0x6E8); //AcmInfoTable at 0x6C0, +0x28 for ProcessorIdList
+ break;
+ case ACM_HEADER_VERSION_4:
+ case ACM_HEADER_VERSION_5:
+ FmsOffset = *(UINT32*)((UINT8*)Acm + 0x1CA8); //AcmInfoTable at 0x1C80, +0x28 for ProcessorIdList
+ break;
+ default:
+ return;
+ }
-Routine Description:
+ ProcessorIdList = (PROCESSOR_ID_LIST *)((UINT8*)Acm + FmsOffset);
- Check Acm information
+ if (ProcessorIdList->Count > 0) {
+ TmpFms = ProcessorIdList->ProcessorID[0].FMS;
+ *AcmFms = TmpFms;
+ *AcmMask = DEFAULT_ACM_EXTENDED_MASK;
+ }
-Arguments:
+ for (Index = 1; Index < ProcessorIdList->Count; Index++) {
+ TmpMask = (TmpFms ^ ProcessorIdList->ProcessorID[Index].FMS);
+ TmpFms &= ProcessorIdList->ProcessorID[Index].FMS;
+ }
- Acm - ACM buffer
- AcmMaxSize - ACM max size
+ *AcmMask = ~TmpMask;
+ return;
+}
-Returns:
+/**
+ Check Acm information.
- TRUE - ACM is valid
- FALSE - ACM is invalid
+ @param Acm ACM buffer.
+ @param AcmMaxSize ACM max size.
---*/
+ @retval TRUE ACM is valid.
+ @retval FALSE ACM is invalid.
+**/
+BOOLEAN
+CheckAcm (
+ IN ACM_FORMAT *Acm,
+ IN UINTN AcmMaxSize
+ )
{
CHIPSET_ACM_INFORMATION_TABLE *ChipsetAcmInformationTable;
CHIPSET_ID_LIST *ChipsetIdList;
@@ -2734,24 +2906,27 @@ Returns:
return FALSE;
}
- //
- // To simplify the tool and making it independent of ACM header change,
- // the following check will be skipped starting ACM_HEADER_VERSION3
- //
- if((Acm->HeaderVersion != ACM_HEADER_VERSION_3) && (Acm->HeaderVersion != ACM_HEADER_VERSION_0)){
- printf ("ACM header Version 4 or higher, bypassing other checks!\n");
- return TRUE;
- }
+ //move buffer pointer to address past generic ACM header (post scratchsize)
Buffer = (UINT8 *)(Acm + 1);
Buffer += Acm->KeySize * 4;
if (Acm->HeaderVersion == ACM_HEADER_VERSION_3) {
Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE;
- } else {
+ }
+ else if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) {
+ Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE;
+ Buffer += ACM_XMSS_PUBLIC_KEY_SIZE;
+ Buffer += ACM_XMSS_SIGNATURE_SIZE;
+ }
+ else {
Buffer += 4;
Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA256_SIZE;
}
Buffer += Acm->ScratchSize * 4;
+ if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) {
+ Buffer += 60; //add reserved bytes.
+ }
+
if ((Acm->ModuleSubType & ACM_MODULE_SUBTYPE_ANC_MODULE) == 0) {
ChipsetAcmInformationTable = (CHIPSET_ACM_INFORMATION_TABLE *)Buffer;
if ((UINTN)ChipsetAcmInformationTable >= (UINTN)Acm + AcmMaxSize) {
@@ -2814,29 +2989,21 @@ End:
return TRUE;
}
+/**
+ Fill the FIT table information to FvRecovery.
+
+ @param FvBuffer FvRecovery binary buffer.
+ @param FvSize FvRecovery size.
+ @param FitTableOffset The offset of FIT table in FvRecovery file.
+
+ @retval None
+**/
VOID
FillFitTable (
IN UINT8 *FvBuffer,
IN UINT32 FvSize,
IN UINT8 *FitTableOffset
)
-/*++
-
-Routine Description:
-
- Fill the FIT table information to FvRecovery
-
-Arguments:
-
- FvBuffer - FvRecovery binary buffer
- FvSize - FvRecovery size
- FitTableOffset - The offset of FIT table in FvRecovery file
-
-Returns:
-
- None
-
---*/
{
FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry;
UINT32 FitIndex;
@@ -2899,15 +3066,18 @@ Returns:
// 4. StartupAcm
//
for (Index = 0; Index < gFitTableContext.StartupAcmNumber; Index++) {
- if (gFitTableContext.StartupAcmVersion[Index] == STARTUP_ACM_FIT_ENTRY_200_VERSION) {
+ if (gFitTableContext.StartupAcm[Index].Version == STARTUP_ACM_FIT_ENTRY_200_VERSION) {
+ printf("ACM version 0x200\n");
FMS.Uint32 = gFitTableContext.StartupAcm[Index].FMS;
FMSMask.Uint32 = gFitTableContext.StartupAcm[Index].FMSMask;
+ printf("ACM FMS:%08x\n", FMS.Uint32);
+ printf("ACM FMSMask:%08x\n", FMSMask.Uint32);
FitEntry[FitIndex].Address = gFitTableContext.StartupAcm[Index].Address;
FitEntry[FitIndex].Size[0] = NIBBLES_TO_BYTE (FMS.Bits.Family, FMS.Bits.Model);
FitEntry[FitIndex].Size[1] = NIBBLES_TO_BYTE (FMS.Bits.ExtendedModel, FMS.Bits.Type);
FitEntry[FitIndex].Size[2] = NIBBLES_TO_BYTE (FMSMask.Bits.Family, FMSMask.Bits.Model);
FitEntry[FitIndex].Rsvd = NIBBLES_TO_BYTE (FMSMask.Bits.ExtendedModel, FMSMask.Bits.Type);
- FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcmVersion[Index];
+ FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcm[Index].Version;
FitEntry[FitIndex].Type = FIT_TABLE_TYPE_STARTUP_ACM;
FitEntry[FitIndex].C_V = 0;
FitEntry[FitIndex].Checksum = NIBBLES_TO_BYTE (FMSMask.Bits.ExtendedFamily, FMS.Bits.ExtendedFamily);
@@ -2918,7 +3088,7 @@ Returns:
FitEntry[FitIndex].Size[1] = (UINT8)(FitEntrySizeValue >> 8);
FitEntry[FitIndex].Size[2] = (UINT8)(FitEntrySizeValue >> 16);
FitEntry[FitIndex].Rsvd = 0;
- FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcmVersion[Index];
+ FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcm[Index].Version;
FitEntry[FitIndex].Type = FIT_TABLE_TYPE_STARTUP_ACM;
FitEntry[FitIndex].C_V = 0;
FitEntry[FitIndex].Checksum = 0;
@@ -2943,7 +3113,23 @@ Returns:
FitIndex++;
}
//
- // 5. BiosModule
+ // 5. (4) Bootable BootPolicy Data
+ //
+ if (gFitTableContext.ProtBootPolicy.Address != 0) {
+ FitEntry[FitIndex].Address = gFitTableContext.ProtBootPolicy.Address;
+ FitEntry[FitIndex].Size[0] = (UINT8) (gFitTableContext.ProtBootPolicy.Size);
+ FitEntry[FitIndex].Size[1] = (UINT8) (gFitTableContext.ProtBootPolicy.Size >> 8);
+ FitEntry[FitIndex].Size[2] = (UINT8) (gFitTableContext.ProtBootPolicy.Size >> 16);
+ FitEntry[FitIndex].Rsvd = 0;
+ FitEntry[FitIndex].Version = (UINT16)gFitTableContext.ProtBootPolicy.Version;
+ FitEntry[FitIndex].Type = FIT_TABLE_TYPE_PROT_BOOT_POLICY;
+ FitEntry[FitIndex].C_V = 0;
+ FitEntry[FitIndex].Checksum = 0;
+ FitIndex++;
+ }
+
+ //
+ // 6. BiosModule
//
//
// BiosModule segments order needs to be put from low address to high for Btg requirement
@@ -2974,7 +3160,7 @@ Returns:
}
//
- // 6. Optional module
+ // 7. Optional module
//
for (Index = 0; Index < gFitTableContext.OptionalModuleNumber; Index++) {
FitEntrySizeValue = gFitTableContext.OptionalModule[Index].Size;
@@ -2993,7 +3179,7 @@ Returns:
}
//
- // 7. Port module
+ // 8. Port module
//
for (Index = 0; Index < gFitTableContext.PortModuleNumber; Index++) {
FitEntrySizeValue = 0;
@@ -3029,27 +3215,19 @@ Returns:
FitEntry[0].Checksum = Checksum;
}
+/**
+ Clear the FIT table information to Fvrecovery.
+
+ @param FvBuffer - Fvrecovery binary buffer.
+ @param FvSize - Fvrecovery size.
+
+ @retval None
+**/
VOID
ClearFitTable (
IN UINT8 *FvBuffer,
IN UINT32 FvSize
)
-/*++
-
-Routine Description:
-
- Clear the FIT table information to Fvrecovery
-
-Arguments:
-
- FvBuffer - Fvrecovery binary buffer
- FvSize - Fvrecovery size
-
-Returns:
-
- None
-
---*/
{
FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry;
UINT32 EntryNum;
@@ -3097,30 +3275,22 @@ Returns:
}
}
+/**
+ Read input file.
+
+ @param FileName The input file name.
+ @param FileData The input file data.
+ @paramFileSize The input file size.
+
+ @retval STATUS_SUCCESS Write file data successfully.
+ @retval STATUS_ERROR The file data is not written.
+**/
STATUS
WriteOutputFile (
IN CHAR8 *FileName,
IN UINT8 *FileData,
IN UINT32 FileSize
)
-/*++
-
-Routine Description:
-
- Read input file
-
-Arguments:
-
- FileName - The input file name
- FileData - The input file data
- FileSize - The input file size
-
-Returns:
-
- STATUS_SUCCESS - Write file data successfully
- STATUS_ERROR - The file data is not written
-
---*/
{
FILE *FpOut;
@@ -3157,28 +3327,78 @@ Returns:
return STATUS_SUCCESS;
}
+
UINT32
-GetFvRecoveryInfoFromFd (
+GetFvAcmSizeFromFd(
IN UINT8 *FdBuffer,
- IN UINT32 FdFileSize,
- OUT UINT8 **FvRecovery
- )
-/*++
+ IN UINT32 FdFileSize
+)
+/**
+ Get FV_ACM Size information from Fd file.
-Routine Description:
+ @param FdBuffer Fd file buffer.
+ @param FdFileSize Fd file size.
- Get FvRecovery information from Fd file.
+ @retval FvACM size
+
+**/
+{
+ UINT8 *FileBuffer = NULL;
+ UINT32 FvAcmSize = 0;
+ EFI_GUID ACMGuid = ACMFV_GUID;
+ UINT32 FvLength;
+ UINT32 FileLength;
+
+ //*FvRecovery = NULL;
+ FileBuffer = FindNextFvHeader(FdBuffer, FdFileSize);
+ if (FileBuffer == NULL) {
+ return 0;
+ }
-Arguments:
+ while ((UINTN)FileBuffer < (UINTN)FdBuffer + FdFileSize) {
+ FvLength = (UINT32)((EFI_FIRMWARE_VOLUME_HEADER *)FileBuffer)->FvLength;
- FdBuffer - Fd file buffer.
- FdFileSize - Fd file size.
- FvRecovery - FvRecovery pointer in Fd file buffer
+ if (FindFileFromFvByGuid(FileBuffer, FvLength, &ACMGuid, &FileLength) != NULL) {
+ //
+ // Found the ACM
+ //
+ FvAcmSize = FvLength;
+ }
-Returns:
- FvRecovery file size
+ //
+ // Next fv
+ //
+ FileBuffer = (UINT8 *)FileBuffer + FvLength;
+ if ((UINTN)FileBuffer >= (UINTN)FdBuffer + FdFileSize) {
+ break;
+ }
+ FileBuffer = FindNextFvHeader(FileBuffer, (UINTN)FdBuffer + FdFileSize - (UINTN)FileBuffer);
+ if (FileBuffer == NULL) {
+ break;
+ }
---*/
+ }
+
+ return FvAcmSize;
+}
+
+/**
+
+ Get FvRecovery information from Fd file.
+
+ @param FdBuffer Fd file buffer.
+ @param FdFileSize Fd file size.
+ @param FvRecovery FvRecovery pointer in Fd file buffer
+
+ @retval FvRecovery file size
+
+**/
+UINT32
+GetFvRecoveryInfoFromFd (
+ IN UINT8 *FdBuffer,
+ IN UINT32 FdFileSize,
+ OUT UINT8 **FvRecovery
+ )
{
UINT8 *FileBuffer = NULL;
UINT32 FvRecoveryFileSize =0;
@@ -3223,16 +3443,7 @@ Returns:
return FvRecoveryFileSize;
}
-void
-GetFMSFromFitEntry (
- IN FIRMWARE_INTERFACE_TABLE_ENTRY FitEntry,
- IN OUT PROCESSOR_ID *FMS,
- IN OUT PROCESSOR_ID *FMSMask
- )
-/*++
-
-Routine Description:
-
+/**
Get FMS information from FIT Entry.
Note: Since FIT entry not record all the processor ID information.
@@ -3260,17 +3471,18 @@ Routine Description:
| | Family | Model | ExtModel | Type | Family | Model | |
+----------+-----------------------+-----------------------+-----------------------+-----------------------+
+ @param FitEntry FIT entry information.
+ @param FMS Processor ID information.
+ @param FMSMask Processor ID mask information.
-Arguments:
-
- FitEntry - FIT entry information.
- FMS - Processor ID information.
- FMSMask - Processor ID mask information.
-
-Returns:
- None
-
---*/
+ @retval None
+**/
+void
+GetFMSFromFitEntry (
+ IN FIRMWARE_INTERFACE_TABLE_ENTRY FitEntry,
+ IN OUT PROCESSOR_ID *FMS,
+ IN OUT PROCESSOR_ID *FMSMask
+ )
{
FMS->Bits.Family = (FitEntry.Size[0] & 0xF0) >> 4;
@@ -3286,27 +3498,19 @@ Returns:
FMSMask->Bits.ExtendedFamily = (FitEntry.Checksum & 0xF0) >> 4;
}
+/**
+ Get the FIT table information from Fvrecovery.
+
+ @param FvBuffer Fvrecovery binary buffer.
+ @param FvSize Fvrecovery size.
+
+ @retval 0 - Fit Table not found
+**/
UINT32
GetFitEntryInfo (
IN UINT8 *FvBuffer,
IN UINT32 FvSize
)
-/*++
-
-Routine Description:
-
- Get the FIT table information from Fvrecovery
-
-Arguments:
-
- FvBuffer - Fvrecovery binary buffer
- FvSize - Fvrecovery size
-
-Returns:
-
- 0 - Fit Table not found
-
---*/
{
FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry;
UINT32 FitEntrySizeValue;
@@ -3360,14 +3564,20 @@ Returns:
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Address = (UINT32)FitEntry[FitIndex].Address;
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Size = FitEntrySizeValue;
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Type = FitEntry[FitIndex].Type;
- gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = FitEntry[FitIndex].Version;
- if (gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] == STARTUP_ACM_FIT_ENTRY_200_VERSION) {
+ gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = FitEntry[FitIndex].Version;
+
+ if (gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version == STARTUP_ACM_FIT_ENTRY_200_VERSION) {
GetFMSFromFitEntry (FitEntry[FitIndex], &FMS, &FMSMask);
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMS = FMS.Uint32;
gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMSMask = FMSMask.Uint32;
}
gFitTableContext.StartupAcmNumber++;
break;
+ case FIT_TABLE_TYPE_PROT_BOOT_POLICY:
+ gFitTableContext.ProtBootPolicy.Address = (UINT32)FitEntry[FitIndex].Address;
+ gFitTableContext.ProtBootPolicy.Version = FitEntry[FitIndex].Version;
+ gFitTableContext.ProtBootPolicy.Size = GetFirmwareInterfaceTableEntrySize (&FitEntry[FitIndex]);
+ break;
case FIT_TABLE_TYPE_BIOS_MODULE:
gFitTableContext.BiosModule[gFitTableContext.BiosModuleNumber].Address = (UINT32)FitEntry[FitIndex].Address;
gFitTableContext.BiosModule[gFitTableContext.BiosModuleNumber].Size = FitEntrySizeValue * 16;
@@ -3398,27 +3608,20 @@ Returns:
return gFitTableContext.FitEntryNumber;
}
+/**
+ Main function for FitGen.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings.
+
+ @retval STATUS_SUCCESS Utility exits successfully.
+ @retval STATUS_ERROR Some error occurred during execution.
+**/
STATUS
FitGen (
IN INTN argc,
IN CHAR8 **argv
)
-/*++
-
-Routine Description:
-
- Main function for FitGen.
-
-Arguments:
-
- argc - Number of command line parameters.
- argv - Array of pointers to parameter strings.
-
-Returns:
- STATUS_SUCCESS - Utility exits successfully.
- STATUS_ERROR - Some error occurred during execution.
-
---*/
{
UINT32 FvRecoveryFileSize;
UINT8 *FileBuffer;
@@ -3433,7 +3636,7 @@ Returns:
UINT32 FdFileSize;
UINT8 *AcmBuffer;
- INTN Index;
+ INTN Index = 0;
UINT32 FixedFitLocation;
FileBufferRaw = NULL;
@@ -3514,6 +3717,7 @@ Returns:
FitTableOffset = GetFreeSpaceForFit (FileBuffer, FvRecoveryFileSize, FitTableSize, FixedFitLocation);
if (FitTableOffset == NULL) {
+ printf ("Error - FitTableOffset is NULL\n");
return STATUS_ERROR;
}
@@ -3526,7 +3730,10 @@ Returns:
// Get ACM buffer
//
for (Index = 0; Index < (INTN)gFitTableContext.StartupAcmNumber; Index ++) {
+ printf("ACM address:%08x\n", gFitTableContext.StartupAcm[Index].Address);
+ printf("ACM size:%08x\n", gFitTableContext.StartupAcm[Index].Size);
if (gFitTableContext.StartupAcm[Index].Address != 0) {
+ printf("get AcmBuffer\n");
AcmBuffer = FLASH_TO_MEMORY(gFitTableContext.StartupAcm[Index].Address, FdFileBuffer, FdFileSize);
if ((AcmBuffer < FdFileBuffer) || (AcmBuffer + gFitTableContext.StartupAcm[Index].Size > FdFileBuffer + FdFileSize)) {
printf ("ACM out of range - can not validate it\n");
@@ -3534,11 +3741,20 @@ Returns:
}
if (AcmBuffer != NULL) {
- if (CheckAcm ((ACM_FORMAT *)AcmBuffer, gFitTableContext.StartupAcm[Index].Size)) {
- DumpAcm ((ACM_FORMAT *)AcmBuffer);
- } else {
- Status = STATUS_ERROR;
- goto exitFunc;
+ if (CheckAcm((ACM_FORMAT *)AcmBuffer, gFitTableContext.StartupAcm[Index].Size)) {
+ DumpAcm((ACM_FORMAT *)AcmBuffer);
+
+ if (gFitTableContext.StartupAcm[Index].Version >= 0x200) {
+ GetAcmFms((ACM_FORMAT *)AcmBuffer, &gFitTableContext.StartupAcm[Index].FMS, &gFitTableContext.StartupAcm[Index].FMSMask);
+ printf("ACM FMS:%08x\n", gFitTableContext.StartupAcm[Index].FMS);
+ printf("ACM FMS Mask:%08x\n", gFitTableContext.StartupAcm[Index].FMSMask);
+ }
+ }
+ else {
+ if (Index == 0) {
+ Status = STATUS_ERROR;
+ goto exitFunc;
+ }
}
}
}
@@ -3592,32 +3808,31 @@ exitFunc:
return Status;
}
+/**
+ View function for FitGen.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings
+
+ @retval STATUS_SUCCESS Utility exits successfully.
+ @retval STATUS_ERROR Some error occurred during execution.
+**/
STATUS
FitView (
IN INTN argc,
IN CHAR8 **argv
)
-/*++
-
-Routine Description:
-
- View function for FitGen.
-
-Arguments:
-
- argc - Number of command line parameters.
- argv - Array of pointers to parameter strings.
-
-Returns:
- STATUS_SUCCESS - Utility exits successfully.
- STATUS_ERROR - Some error occurred during execution.
-
---*/
{
- UINT32 FvRecoveryFileSize;
- UINT8 *FileBuffer;
- UINT8 *FileBufferRaw = NULL;
- STATUS Status;
+ UINT32 FvRecoveryFileSize;
+ UINT8 *FileBuffer;
+ UINT8 *FileBufferRaw = NULL;
+ STATUS Status;
+ FILE *FpIn;
+ UINT32 FlashValidSig = 0;
+ UINT32 Frba;
+ UINT32 BiosRegionBaseOffset;
+ FLASH_MAP_0_REGISTER FlashMap0;
+ FLASH_REGION_1_BIOS_REGISTER FlashRegion1;
//
// Step 1: Read input file
@@ -3642,13 +3857,57 @@ Returns:
gFitTableContext.FitTablePointerOffset = xtoi (argv[3 + 1]);
} else {
Error (NULL, 0, 0, "FIT offset not specified!", NULL);
+ Status = STATUS_ERROR;
goto exitFunc;
}
} else {
Error (NULL, 0, 0, "Invalid view option: ", "%s", argv[3]);
+ Status = STATUS_ERROR;
goto exitFunc;
}
+ //
+ //Check the File Path
+ //
+ if (!CheckPath (argv[2])) {
+ Error (NULL, 0, 0, "File path is invalid!", NULL);
+ Status = STATUS_ERROR;
+ goto exitFunc;
+ }
+ //
+ // Open the Input file
+ //
+ if ((FpIn = fopen (argv[2], "rb")) == NULL) {
+ Error (NULL, 0, 0, "Unable open the file!", NULL);
+ Status = STATUS_WARNING;
+ goto exitFunc;
+ }
+ //
+ //Seek and read the Flash Valid Signature;
+ //
+ fseek (FpIn, FLVALSIG_BASE_OFFSET, SEEK_SET);
+ fread (&FlashValidSig, 4, 1, FpIn);
+ if (FlashValidSig == FLASH_VALID_SIGNATURE) {
+ //
+ //Seek and read the Flash Map 0 Register;
+ //
+ fseek (FpIn, FLMAP0_BASE_OFFSET, SEEK_SET);
+ fread (&FlashMap0, 4, 1, FpIn);
+ Frba = FlashMap0.Frba << 4 & 0xFF0; //FRBA identifies address bits [11:4] for the region portion of the flashdescriptor, bits [26:12] and bits [3:0] are 0
+ //
+ //Seek and read the Flash Region 1 (BIOS) Register;
+ //
+ BiosRegionBaseOffset = Frba + 0x4;
+ fseek (FpIn, BiosRegionBaseOffset, SEEK_SET);
+ fread (&FlashRegion1, 4, 1, FpIn);
+ FileBuffer = (UINT8 *)(FileBuffer + (FlashRegion1.RegionBase << 12)); // RegionBase specifies address bits [26:12] for the Region Base.
+ FvRecoveryFileSize = ((FlashRegion1.RegionLimit << 12 | 0xFFF) + 1) - (FlashRegion1.RegionBase << 12); //RegionLimit specifies bits [26:12] of the ending address for this region, bits [11:0] are assumed to be FFFh.
+ }
+ //
+ // Close the Input file
+ //
+ fclose (FpIn);
+
//
// For debug
//
@@ -3661,27 +3920,20 @@ exitFunc:
return Status;
}
+/**
+ Main function.
+
+ @param argc Number of command line parameters.
+ @param argv Array of pointers to parameter strings
+
+ @retval STATUS_SUCCESS Utility exits successfully.
+ @retval STATUS_ERROR Some error occurred during execution.
+**/
int
main (
int argc,
char **argv
)
-/*++
-
-Routine Description:
-
- Main function.
-
-Arguments:
-
- argc - Number of command line parameters.
- argv - Array of pointers to parameter strings.
-
-Returns:
- STATUS_SUCCESS - Utility exits successfully.
- STATUS_ERROR - Some error occurred during execution.
-
---*/
{
SetUtilityName (UTILITY_NAME);
@@ -3703,24 +3955,18 @@ Returns:
return STATUS_ERROR;
}
}
+/**
+ Convert hex string to uint
+
+ @param str The string
+ @retval Integer value
+
+**/
unsigned int
xtoi (
char *str
)
-/*++
-
-Routine Description:
-
- Convert hex string to uint
-
-Arguments:
-
- str - The string
-
-Returns:
-
---*/
{
unsigned int u;
char c;
diff --git a/Silicon/Intel/Tools/FitGen/FitGen.h b/Silicon/Intel/Tools/FitGen/FitGen.h
index 511ab652ab..2d24ecb584 100644
--- a/Silicon/Intel/Tools/FitGen/FitGen.h
+++ b/Silicon/Intel/Tools/FitGen/FitGen.h
@@ -36,7 +36,6 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#define FIT_SPEC_VERSION_MAJOR 1
#define FIT_SPEC_VERSION_MINOR 4
-
//
// The minimum number of arguments accepted from the command line.
//
@@ -50,4 +49,10 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#define ROUNDUP(Size, Alignment) (((Size) + (Alignment) - 1) / (Alignment) * (Alignment))
+UINT32
+GetFvAcmSizeFromFd(
+IN UINT8 *FdBuffer,
+IN UINT32 FdFileSize
+);
+
#endif
--
2.30.1.windows.1
-=-=-=-=-=-=-=-=-=-=-=-
Groups.io Links: You receive all messages sent to this group.
View/Reply Online (#96430): https://edk2.groups.io/g/devel/message/96430
Mute This Topic: https://groups.io/mt/95067601/1787277
Group Owner: devel+owner@edk2.groups.io
Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org]
-=-=-=-=-=-=-=-=-=-=-=-
Reviewed-by: Bob Feng <bob.c.feng@intel.com> -----Original Message----- From: Kumar, Rahul R <rahul.r.kumar@intel.com> Sent: Wednesday, November 16, 2022 9:58 AM To: devel@edk2.groups.io; Feng, Bob C <bob.c.feng@intel.com>; Gao, Liming <gaoliming@byosoft.com.cn>; Chen, Christine <yuwei.chen@intel.com>; Oram, Isaac W <isaac.w.oram@intel.com>; Chaganty, Rangasai V <rangasai.v.chaganty@intel.com>; West, Catharine <catharine.west@intel.com> Cc: Kumar, Rahul R <rahul.r.kumar@intel.com> Subject: [PATCH] Silicon/Intel/FitGen:FitGen Supporting MultiFIT 2 rc REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4155 With new implementation, FITGEN will populate info needed for the PROT assisted BootGuard solution and TXT on servers using FIT 4 Entry. FitGen based on the CPU FMS FITGEN will decide to call one of the two Type 2 FIT entry. Signed-off-by: Rahul R Kumar <rahul.r.kumar@intel.com> --- Silicon/Intel/Tools/FitGen/FitGen.c | 1186 ++++++++++++++++----------- Silicon/Intel/Tools/FitGen/FitGen.h | 7 +- 2 files changed, 722 insertions(+), 471 deletions(-) diff --git a/Silicon/Intel/Tools/FitGen/FitGen.c b/Silicon/Intel/Tools/FitGen/FitGen.c index 87123f9922..4ba07945a6 100644 --- a/Silicon/Intel/Tools/FitGen/FitGen.c +++ b/Silicon/Intel/Tools/FitGen/FitGen.c @@ -44,11 +44,18 @@ typedef struct { #define BIOS_MODULE_ALIGNMENT 0x3F // 64 bytes for AnC #define MICROCODE_ALIGNMENT 0x7FF +#define MICROCODE_EXTERNAL_HEADER_SIZE 0x30 + #define ACM_PKCS_1_5_RSA_SIGNATURE_SHA256_SIZE 256 #define ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE 384 -#define ACM_HEADER_VERSION_3 (3 << 16) -#define ACM_HEADER_VERSION_0 (0) +#define ACM_XMSS_PUBLIC_KEY_SIZE 64 +#define ACM_XMSS_SIGNATURE_SIZE 2692 + +#define ACM_HEADER_VERSION_5 0x50004 +#define ACM_HEADER_VERSION_4 (4 << 16) +#define ACM_HEADER_VERSION_3 (3 << 16) +#define ACM_HEADER_VERSION_0 (0) #define ACM_MODULE_TYPE_CHIPSET_ACM 2 #define ACM_MODULE_SUBTYPE_CAPABLE_OF_EXECUTE_AT_RESET 0x1 #define ACM_MODULE_SUBTYPE_ANC_MODULE 0x2 @@ -56,6 +63,37 @@ typedef struct { #define ACM_MODULE_FLAG_DEBUG_SIGN 0x8000 #define NIBBLES_TO_BYTE(A, B) (UINT8)(((A & (0x0F)) << 4) | (B & 0x0F)) +// +//Flash Map 0 Register (Flash Descriptor Records) +// +typedef struct { + UINT32 Fcba : 8; //Bits[7:0]: Flash Component Base Address + UINT32 Nc : 2; //Bits[9:8]: Number of Components + UINT32 Rsvd0: 1; //Bit10: Reserved + UINT32 Rsvd1: 1; //Bit11: Reserved + UINT32 Rsvd2: 1; //Bit12: Reserved + UINT32 Rsvd3: 3; //Bits[15:13]: Reserved + UINT32 Frba : 8; //Bits[23:16]: Flash Region Base Address + UINT32 Rsvd4: 3; //Bits[26:24]: Reserved + UINT32 Rsvd5: 5; //Bits[31:27]: Reserved +} FLASH_MAP_0_REGISTER; + +// +//Flash Region 1 (BIOS) Register (Flash Descriptor Records) +// +typedef struct { + UINT32 RegionBase : 15; //Bits[14:0]: Region base + UINT32 Rsvd : 1; //Bit15: Reserved + UINT32 RegionLimit: 15; //Bits[30:16]: Region limit + UINT32 Rsvd1 : 1; //Bit31: Reserved +} FLASH_REGION_1_BIOS_REGISTER; + +#define FLASH_VALID_SIGNATURE 0x0FF0A55A //Flash Valid Signature (Flash Descriptor Records) +#define FLVALSIG_BASE_OFFSET 0x10 //Flash Valid Signature Base Offset +#define FLMAP0_BASE_OFFSET 0x14 //Flash Map 0 Register Base Offset + +#define ACMFV_GUID \ + { 0x8a4b197f, 0x1113, 0x43d0, { 0xa2, 0x3f, 0x26, 0xf3, 0x69, 0xb2, 0xb8, 0x41 }} typedef struct { UINT16 ModuleType; @@ -98,6 +136,8 @@ typedef struct { #define CHIPSET_ACM_TYPE_BIOS 0 #define CHIPSET_ACM_TYPE_SINIT 1 +#define DEFAULT_ACM_EXTENDED_MASK 0x00FFFFFF + typedef struct { UINT32 Guid0; UINT32 Guid1; @@ -238,6 +278,7 @@ typedef struct { #define FIT_TABLE_TYPE_MICROCODE 1 #define FIT_TABLE_TYPE_STARTUP_ACM 2 #define FIT_TABLE_TYPE_DIAGNST_ACM 3 +#define FIT_TABLE_TYPE_PROT_BOOT_POLICY 4 #define FIT_TABLE_TYPE_BIOS_MODULE 7 #define FIT_TABLE_TYPE_TPM_POLICY 8 #define FIT_TABLE_TYPE_BIOS_POLICY 9 @@ -252,7 +293,6 @@ typedef struct { #define FIT_TABLE_TYPE_VAB_BOOT_IMAGE_MANIFEST 27 #define FIT_TABLE_TYPE_VAB_BOOT_KEY_MANIFEST 28 - // // With OptionalModule Address isn't known until free space has been // identified and the optional module has been copied into the FLASH @@ -284,9 +324,10 @@ typedef struct { UINT32 GlobalVersion; UINT32 FitHeaderVersion; FIT_TABLE_CONTEXT_ENTRY StartupAcm[MAX_STARTUP_ACM_ENTRY]; - UINT32 StartupAcmVersion[MAX_STARTUP_ACM_ENTRY]; + UINT32 StartupAcmFvSize; FIT_TABLE_CONTEXT_ENTRY DiagnstAcm; UINT32 DiagnstAcmVersion; + FIT_TABLE_CONTEXT_ENTRY ProtBootPolicy; FIT_TABLE_CONTEXT_ENTRY BiosModule[MAX_BIOS_MODULE_ENTRY]; UINT32 BiosModuleVersion; FIT_TABLE_CONTEXT_ENTRY Microcode[MAX_MICROCODE_ENTRY]; @@ -305,25 +346,87 @@ xtoi ( char *str ); -VOID -PrintUtilityInfo ( - VOID - ) -/*++ +/** + Pass in supported CPU extended family/extended model/type + /family/model without stepping or CPU FMS >> 4. + + @param FitEntry Pointer to Fit Entry table. + @param AcmFamilyModel Acm Family Model stepping. + @param AcmMask ACM mask. + + @return STATUS_SUCCESS The file found and data read. +**/ +STATUS +SetFirmwareInterfaceTableEntryAcmFms( + FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry, + UINT32 AcmFamilyModel, + UINT32 AcmMask +) +{ + if (FitEntry == NULL) { + return STATUS_ERROR; + } + + FitEntry->Checksum = (UINT8)(((AcmFamilyModel & 0x000F0000) >> 16) | (((AcmMask & 0x000F0000) >> 16) << 4)); + FitEntry->Rsvd = (UINT8)((AcmMask & 0x0000FF00) >> 8); + FitEntry->Size[2] = (UINT8)(AcmMask & 0x000000FF); + FitEntry->Size[1] = (UINT8)((AcmFamilyModel & 0x0000FF00) >> 8); + FitEntry->Size[0] = (UINT8)(AcmFamilyModel & 0x000000FF); + return STATUS_SUCCESS; +} + +/** + Set the FIT Entry Size. + + @param FitEntry Pointer to Fit Entry table. + @param SizeEntry Size of FIT entry. -Routine Description: + @return STATUS_SUCCESS The file found and data read. +**/ +STATUS +SetFirmwareInterfaceTableEntrySize ( + FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry, + UINT32 SizeEntry +) +{ + if (FitEntry == NULL) { + return STATUS_ERROR; + } + FitEntry->Size[2] = (UINT8)((SizeEntry & 0x00FF0000) >> 16); + FitEntry->Size[1] = (UINT8)((SizeEntry & 0x0000FF00) >> 8); + FitEntry->Size[0] = (UINT8)(SizeEntry & 0x000000FF); + return STATUS_SUCCESS; +} - Displays the standard utility information to STDOUT +/** + Get the FIT Entry Size. -Arguments: + @param FitEntry Pointer to Fit Entry table. - None + @return FitEntry pointer +**/ +UINT32 +GetFirmwareInterfaceTableEntrySize ( + FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry +) +{ + if (FitEntry == NULL) { + return 0; + } + return (((UINT32)FitEntry->Size[2] << 16) | ((UINT32)FitEntry->Size[1] << 8) | (UINT32)FitEntry->Size[0]); +} -Returns: +/** + Displays the FIT utility info - None + @param None ---*/ + @return None +**/ +VOID +PrintUtilityInfo ( + VOID + ) { printf ( "%s - Tiano IA32/X64 FIT table generation Utility for FIT spec revision %i.%i."" Version %i.%i\n\n", @@ -335,25 +438,17 @@ Returns: ); } +/** + Displays the utility usage syntax to STDOUT. + + @param None + + @return None +**/ VOID PrintUsage ( VOID ) -/*++ - -Routine Description: - - Displays the utility usage syntax to STDOUT - -Arguments: - - None - -Returns: - - None - ---*/ { printf ("Usage (generate): %s [-D] InputFvRecoveryFile OutputFvRecoveryFile\n" "\t[-V <FitEntryDefaultVersion>]\n" @@ -371,6 +466,7 @@ Returns: "\t[-M <MicrocodeAddress MicrocodeSize>] [-M ...]|[-U <MicrocodeFv MicrocodeBase>|<MicrocodeRegionOffset MicrocodeRegionSize>|<MicrocodeGuid>] [-V <MicrocodeVersion>]\n" "\t[-O RecordType <RecordDataAddress RecordDataSize>|<RESERVE RecordDataSize>|<RecordDataGuid>|<RecordBinFile>|<CseRecordSubType RecordBinFile> [-V <RecordVersion>]] [-O ... [-V ...]]\n" "\t[-P RecordType <IndexPort DataPort Width Bit Index> [-V <RecordVersion>]] [-P ... [-V ...]]\n" + "\t[-BP <BootPolicySize>[-V <BootPolicyVersion>]\n" "\t[-T <FixedFitLocation>]\n" , UTILITY_NAME); printf (" Where:\n"); @@ -407,12 +503,14 @@ Returns: printf ("\tRecordDataGuid - FIT entry record data GUID.\n"); printf ("\tRecordBinFile - FIT entry record data binary file.\n"); printf ("\tCseRecordSubType - FIT entry record subtype. Use to further distinguish CSE entries (see FIT spec revision 1.2 chapter 4.12).\n"); + printf ("\tBootPolicySize - FIT entry size for type 04 boot policy.\n"); printf ("\tFitEntryDefaultVersion - The default version for all FIT table entries. 0x%04x is used if this is not specified.\n", DEFAULT_FIT_ENTRY_VERSION); printf ("\tFitHeaderVersion - The version for FIT header. (Override default version)\n"); printf ("\tStartupAcmVersion - The version for StartupAcm. (Override default version)\n"); printf ("\tBiosModuleVersion - The version for BiosModule. (Override default version)\n"); printf ("\tMicrocodeVersion - The version for Microcode. (Override default version)\n"); printf ("\tRecordVersion - The version for Record. (Override default version)\n"); + printf ("\tBootPolicyVersion - The version for BootPolicy. (Override default version)\n"); printf ("\tIndexPort - The Index Port Number.\n"); printf ("\tDataPort - The Data Port Number.\n"); printf ("\tWidth - The Width of the port.\n"); @@ -427,11 +525,20 @@ Returns: printf ("\tSTATUS_SUCCESS=%d, STATUS_WARNING=%d, STATUS_ERROR=%d\n", STATUS_SUCCESS, STATUS_WARNING, STATUS_ERROR); } +/** + Set Value of memory. + + @param Buffer The pointer where we need to set the memory. + @param Length Size of memory to be set. + @param Value Value of memory to be set. + + @return Buffer The pointer address. +**/ VOID * SetMem ( - OUT VOID *Buffer, - IN UINTN Length, - IN UINT8 Value + OUT VOID *Buffer, + IN UINTN Length, + IN UINT8 Value ) { // @@ -448,6 +555,14 @@ SetMem ( return Buffer; } +/** + check the input Path. + + @param String Passed input path. + + @return TRUE If the input path is correct. + @return FLASE if the input path is not correct. +**/ BOOLEAN CheckPath ( IN CHAR8 * String @@ -476,28 +591,20 @@ CheckPath ( return TRUE; } +/** + Get fixed FIT location from argument. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings. + + @return FitLocation The FIT location specified by Argument. + @return 0 Argument parse fail. +**/ UINT32 GetFixedFitLocation ( IN INTN argc, IN CHAR8 **argv ) -/*++ - -Routine Description: - - Get fixed FIT location from argument - -Arguments: - - argc - Number of command line parameters. - argv - Array of pointers to parameter strings. - -Returns: - - FitLocation - The FIT location specified by Argument - 0 - Argument parse fail - -*/ { UINT32 FitLocation; INTN Index; @@ -516,6 +623,18 @@ Returns: return FitLocation; } +/** + Read input file. + + @param FileName The input file name. + @param FileData The input file data, the memory is aligned. + @param FileSize The input file size. + @param FileBufferRaw The memory to hold input file data. The caller must free the memory. + + @return STATUS_SUCCESS The file found and data read. + @return STATUS_ERROR The file data is not read. + @return STATUS_WARNING The file is not found. +**/ STATUS ReadInputFile ( IN CHAR8 *FileName, @@ -523,26 +642,6 @@ ReadInputFile ( OUT UINT32 *FileSize, OUT UINT8 **FileBufferRaw OPTIONAL ) -/*++ - -Routine Description: - - Read input file - -Arguments: - - FileName - The input file name - FileData - The input file data, the memory is aligned. - FileSize - The input file size - FileBufferRaw - The memory to hold input file data. The caller must free the memory. - -Returns: - - STATUS_SUCCESS - The file found and data read - STATUS_ERROR - The file data is not read - STATUS_WARNING - The file is not found - ---*/ { FILE *FpIn; UINT32 TempResult; @@ -612,24 +711,20 @@ Returns: return STATUS_SUCCESS; } +/** + Find next FvHeader in the FileBuffer. + + @param FileBuffer The start FileBuffer which needs to be searched. + @param FileLength The whole File Length. + + @return FvHeader The FvHeader is found successfully. + @return NULL The FvHeader is not found. +**/ UINT8 * FindNextFvHeader ( IN UINT8 *FileBuffer, IN UINTN FileLength ) -/*++ - - Routine Description: - Find next FvHeader in the FileBuffer - - Parameters: - FileBuffer - The start FileBuffer which needs to be searched - FileLength - The whole File Length. - Return: - FvHeader - The FvHeader is found successfully. - NULL - The FvHeader is not found. - ---*/ { UINT8 *FileHeader; EFI_FIRMWARE_VOLUME_HEADER *FvHeader; @@ -679,6 +774,17 @@ FindNextFvHeader ( return NULL; } +/** + Find File with GUID in an FV. + + @param FvBuffer FV binary buffer. + @param FvSize FV size. + @param Guid File GUID value to be searched. + @param FileSize Guid File size. + + @return FileLocation Guid File location. + @return NULL Guid File is not found. +**/ UINT8 * FindFileFromFvByGuid ( IN UINT8 *FvBuffer, @@ -686,25 +792,6 @@ FindFileFromFvByGuid ( IN EFI_GUID *Guid, OUT UINT32 *FileSize ) -/*++ - -Routine Description: - - Find File with GUID in an FV - -Arguments: - - FvBuffer - FV binary buffer - FvSize - FV size - Guid - File GUID value to be searched - FileSize - Guid File size - -Returns: - - FileLocation - Guid File location. - NULL - Guid File is not found. - ---*/ { EFI_FIRMWARE_VOLUME_HEADER *FvHeader; EFI_FFS_FILE_HEADER *FileHeader; @@ -783,28 +870,20 @@ Returns: return NULL; } +/** + Check whether a string is a GUID. + + @param StringData The String. + @param Guid Guid to hold the value + + @return TRUE StringData is a GUID, and Guid field is filled. + @return FALSE StringData is not a GUID. +**/ BOOLEAN IsGuidData ( IN CHAR8 *StringData, OUT EFI_GUID *Guid ) -/*++ - -Routine Description: - - Check whether a string is a GUID - -Arguments: - - StringData - the String - Guid - Guid to hold the value - -Returns: - - TRUE - StringData is a GUID, and Guid field is filled. - FALSE - StringData is not a GUID - ---*/ { if (strlen (StringData) != strlen ("00000000-0000-0000-0000-000000000000")) { return FALSE; @@ -821,6 +900,17 @@ Returns: return TRUE; } +/** + Get FIT entry number and fill global FIT table context, from argument. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings. + @param FdBuffer FD binary buffer. + @param FdSize FD size. + + @return FitEntryNumber The FIT entry number. + @return 0 Argument parse fail. +**/ VOID CheckOverlap ( IN UINT32 Address, @@ -875,6 +965,17 @@ CheckOverlap ( } } +/** + Get FIT entry number and fill global FIT table context, from argument. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings. + @param FdBuffer FD binary buffer. + @param FdSize FD size. + + @return FitEntryNumber The FIT entry number. + @return 0 Argument parse fail. +**/ UINT8 * GetMicrocodeBufferFromFv ( EFI_FIRMWARE_VOLUME_HEADER *FvHeader @@ -906,6 +1007,17 @@ GetMicrocodeBufferFromFv ( return MicrocodeBuffer; } +/** + Get FIT entry number and fill global FIT table context, from argument. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings. + @param FdBuffer FD binary buffer. + @param FdSize FD size. + + @return FitEntryNumber The FIT entry number. + @return 0 Argument parse fail. +**/ UINT32 GetFitEntryNumber ( IN INTN argc, @@ -913,25 +1025,6 @@ GetFitEntryNumber ( IN UINT8 *FdBuffer, IN UINT32 FdSize ) -/*++ - -Routine Description: - - Get FIT entry number and fill global FIT table context, from argument - -Arguments: - - argc - Number of command line parameters. - argv - Array of pointers to parameter strings. - FdBuffer - FD binary buffer - FdSize - FD size - -Returns: - - FitEntryNumber - The FIT entry number - 0 - Argument parse fail - -*/ { EFI_GUID Guid; EFI_GUID MicrocodeFfsGuid; @@ -1188,7 +1281,7 @@ Returns: gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Type = FIT_TABLE_TYPE_STARTUP_ACM; gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Address = (UINT32)BiosInfoStruct[BiosInfoIndex].Address; gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Size = (UINT32)BiosInfoStruct[BiosInfoIndex].Size; - gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = BiosInfoStruct[BiosInfoIndex].Version; + gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = BiosInfoStruct[BiosInfoIndex].Version; gFitTableContext.StartupAcmNumber ++; gFitTableContext.FitEntryNumber ++; break; @@ -1203,6 +1296,13 @@ Returns: gFitTableContext.DiagnstAcmVersion = DEFAULT_FIT_ENTRY_VERSION; gFitTableContext.FitEntryNumber ++; break; + case FIT_TABLE_TYPE_PROT_BOOT_POLICY: + gFitTableContext.ProtBootPolicy.Type = FIT_TABLE_TYPE_PROT_BOOT_POLICY; + gFitTableContext.ProtBootPolicy.Address = (UINT32)BiosInfoStruct[BiosInfoIndex].Address; + gFitTableContext.ProtBootPolicy.Size = (UINT32)BiosInfoStruct[BiosInfoIndex].Size; + gFitTableContext.ProtBootPolicy.Version = DEFAULT_FIT_ENTRY_VERSION; + gFitTableContext.FitEntryNumber ++; + break; case FIT_TABLE_TYPE_BIOS_MODULE: if ((BiosInfoStruct[BiosInfoIndex].Attributes & BIOS_INFO_STRUCT_ATTRIBUTE_BIOS_POST_IBB) != 0) { continue; @@ -1402,7 +1502,8 @@ Returns: // not found return 0; } - FileBuffer = (UINT8 *)MEMORY_TO_FLASH (FileBuffer, FdBuffer, FdSize); + gFitTableContext.StartupAcmFvSize = FdSize; + FileBuffer = (UINT8 *)MEMORY_TO_FLASH(FileBuffer, FdBuffer, FdSize); Index += 2; } else { if (Index + 2 >= argc) { @@ -1431,7 +1532,7 @@ Returns: // // Bypass // - gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = gFitTableContext.GlobalVersion; + gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = gFitTableContext.GlobalVersion; } else { if (Index + 2 >= argc) { // @@ -1443,7 +1544,7 @@ Returns: // // With the -I parameter should assign the type 2 entry version as 0x200 format // - gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = STARTUP_ACM_FIT_ENTRY_200_VERSION; + gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = STARTUP_ACM_FIT_ENTRY_200_VERSION; gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMS = (UINT32)xtoi (argv[Index + 1]); gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMSMask = (UINT32)xtoi (argv[Index + 2]); @@ -1464,7 +1565,8 @@ Returns: // // Get offset from parameter // - gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = xtoi (argv[Index + 1]); + gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = gFitTableContext.GlobalVersion; + gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = xtoi (argv[Index + 1]); Index += 2; } @@ -1942,7 +2044,7 @@ Returns: // // Get offset from parameter // - gFitTableContext.PortModule[gFitTableContext.PortModuleNumber].Version = xtoi (argv[Index + 1]); + gFitTableContext.PortModule[gFitTableContext.PortModuleNumber].Version = xtoi(argv[Index + 1]); Index += 2; } @@ -1950,6 +2052,69 @@ Returns: gFitTableContext.FitEntryNumber++; } + // + // 6th, try FIT boot policy data + // + if ((Index < argc) && + ((strcmp(argv[Index], "-BP") == 0) || + (strcmp(argv[Index], "-bp") == 0))) { + + if (Index + 1 >= argc) { + Error(NULL, 0, 0, "-BP: Invalid Parameters.", NULL); + FitEntryNumber = 0; + } + + gFitTableContext.StartupAcmFvSize = GetFvAcmSizeFromFd(FdBuffer, FdSize); + if (gFitTableContext.StartupAcmFvSize == 0) { + Error(NULL, 0, 0, "FV_ACM not found in Fd file!", NULL); + } + + // + // FIT type 04 record shares FV allocated space with FV_ACM. + // + FileSize = xtoi(argv[Index + 1]); + + if (gFitTableContext.StartupAcm[0].Size + FileSize > gFitTableContext.StartupAcmFvSize) { + Error(NULL, 0, 0, "Error: not enough FV_ACM room for FIT type 04 record!", NULL); + FitEntryNumber = 0; + } + + FileBuffer = malloc(FileSize); + if (FileBuffer == NULL) { + Error(NULL, 0, 0, "No sufficient memory to allocate!", NULL); + FitEntryNumber = 0; + } + + SetMem(FileBuffer, FileSize, 0xFF); + + gFitTableContext.ProtBootPolicy.Type = FIT_TABLE_TYPE_PROT_BOOT_POLICY; + gFitTableContext.ProtBootPolicy.Address = gFitTableContext.StartupAcm[0].Address + gFitTableContext.StartupAcm[0].Size; + gFitTableContext.ProtBootPolicy.Size = FileSize; + gFitTableContext.ProtBootPolicy.Version = 0; + + Index += 2; + + // + // 6.1 PROT Module version + // + if ((Index + 1 >= argc) || + ((strcmp (argv[Index], "-V") != 0) && + (strcmp (argv[Index], "-v") != 0)) ) { + // + // Bypass + // + gFitTableContext.ProtBootPolicy.Version = gFitTableContext.GlobalVersion; + } else { + // + // Get offset from parameter + // + gFitTableContext.ProtBootPolicy.Version = xtoi(argv[Index + 1]); + Index += 2; + } + + gFitTableContext.FitEntryNumber++; + } + // // Final: Check StartupAcm in BiosModule. // @@ -1974,31 +2139,23 @@ Returns: return FitEntryNumber; } +/** + No enough space - it might happen that it is occupied by AP wake vector. + Last chance - skip this and search again. + + @param FvBuffer FvRecovery binary buffer. + @param Address Address to be searched from. + @param Size Size need to be filled. + + @return FitTableOffset The FIT table offset. + @return NULL No enough space for FIT table. +**/ VOID * FindSpaceSkipApVector ( IN UINT8 *FvBuffer, IN UINT8 *Address, IN UINTN Size ) -/*++ - -Routine Description: - - No enough space - it might happen that it is occupied by AP wake vector. - Last chance - skip this and search again. - -Arguments: - - FvBuffer - FvRecovery binary buffer - Address - Address to be searched from - Size - Size need to be filled - -Returns: - - FitTableOffset - The FIT table offset - NULL - No enough space for FIT table - -*/ { UINT8 *ApVector; UINT8 *NewAddress; @@ -2018,6 +2175,17 @@ Returns: return NewAddress; } +/** + Get free space for FIT table from FvRecovery. + + @param FvBuffer FvRecovery binary buffer. + @param FvSize FvRecovery size. + @param FitTableSize The FIT table size. + @param FixedFitLocation Fixed FIT location provided by argument. + + @return FitTableOffset The offset of FIT table in FvRecovery file. + @return NULL Free space not found. +**/ VOID * GetFreeSpaceForFit ( IN UINT8 *FvBuffer, @@ -2025,25 +2193,6 @@ GetFreeSpaceForFit ( IN UINT32 FitTableSize, IN UINT32 FixedFitLocation ) -/*++ - -Routine Description: - - Get free space for FIT table from FvRecovery - -Arguments: - - FvBuffer - FvRecovery binary buffer - FvSize - FvRecovery size - FitTableSize - The FIT table size - FixedFitLocation - Fixed FIT location provided by argument - -Returns: - - FitTableOffset - The offset of FIT table in FvRecovery file - NULL - Free space not found - ---*/ { UINT8 *FitTableOffset; INTN Index; @@ -2167,7 +2316,7 @@ Returns: (gFitTableContext.OptionalModule[Index].Type == FIT_TABLE_TYPE_VAB_PROVISION_TABLE) || (gFitTableContext.OptionalModule[Index].Type == FIT_TABLE_TYPE_VAB_BOOT_IMAGE_MANIFEST) || (gFitTableContext.OptionalModule[Index].Type == FIT_TABLE_TYPE_VAB_BOOT_KEY_MANIFEST)) { - // Let it 64 byte align + // Let it 64 byte align AlignedSize += BIOS_MODULE_ALIGNMENT; AlignedSize &= ~BIOS_MODULE_ALIGNMENT; } @@ -2228,25 +2377,17 @@ Returns: return FitTableOffset; } +/** + Output FIT table information. + + @param None + + @return None +**/ VOID PrintFitData ( VOID ) -/*++ - -Routine Description: - - Output FIT table information - -Arguments: - - None - -Returns: - - None - ---*/ { UINT32 Index; @@ -2257,11 +2398,15 @@ Returns: printf ("Total FIT Entry number: 0x%x\n", gFitTableContext.FitEntryNumber); printf ("FitHeader version: 0x%04x\n", gFitTableContext.FitHeaderVersion); for (Index = 0; Index < gFitTableContext.StartupAcmNumber; Index++) { - printf ("StartupAcm[%d] - (0x%08x, 0x%08x, 0x%04x)\n", Index, gFitTableContext.StartupAcm[Index].Address, gFitTableContext.StartupAcm[Index].Size, gFitTableContext.StartupAcmVersion[Index]); + printf("StartupAcm[%d] - (0x%08x, 0x%08x, 0x%04x)\n", Index, gFitTableContext.StartupAcm[Index].Address, gFitTableContext.StartupAcm[Index].Size, gFitTableContext.StartupAcm[Index].Version); } if (gFitTableContext.DiagnstAcm.Address != 0) { printf ("DiagnosticAcm - (0x%08x, 0x%08x, 0x%04x)\n", gFitTableContext.DiagnstAcm.Address, gFitTableContext.DiagnstAcm.Size, gFitTableContext.DiagnstAcmVersion); } + + if (gFitTableContext.ProtBootPolicy.Address != 0) { + printf ("ProtBootPolicy - (0x%08x, 0x%08x, 0x%04x)\n", gFitTableContext.ProtBootPolicy.Address, gFitTableContext.ProtBootPolicy.Size, gFitTableContext.ProtBootPolicy.Version); + } for (Index = 0; Index < gFitTableContext.BiosModuleNumber; Index++) { printf ("BiosModule[%d] - (0x%08x, 0x%08x, 0x%04x)\n", Index, gFitTableContext.BiosModule[Index].Address, gFitTableContext.BiosModule[Index].Size, gFitTableContext.BiosModuleVersion); } @@ -2304,8 +2449,7 @@ CHAR8 *mFitTypeStr[] = { "MICROCODE ", "STARTUP_ACM", "DIAGNST_ACM", - " ", - " ", + "BOOT_POLICY", " ", " ", "BIOS_MODULE", @@ -2320,27 +2464,19 @@ CHAR8 *mFitTypeStr[] = { "CSE_SECUREB" }; +/** + Convert FitEntry type to a string. + + @param FitEntry Fit entry + + @return String +**/ CHAR8 mFitSignature[] = "'_FIT_ ' "; CHAR8 mFitSignatureInHeader[] = "' ' "; CHAR8 * FitTypeToStr ( IN FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry ) -/*++ - -Routine Description: - - Convert FitEntry type to a string - -Arguments: - - FitEntry - Fit entry - -Returns: - - String - ---*/ { if (FitEntry->Type == FIT_TABLE_TYPE_HEADER) { CopyMem (&mFitSignatureInHeader[1], &FitEntry->Address, sizeof(FitEntry->Address)); @@ -2361,27 +2497,19 @@ Returns: } } +/** + Print Fit table in flash image. + + @param FvBuffer FvRecovery binary buffer. + @param FvSize FvRecovery size. + + @return None +**/ VOID PrintFitTable ( IN UINT8 *FvBuffer, IN UINT32 FvSize ) -/*++ - -Routine Description: - - Print Fit table in flash image - -Arguments: - - FvBuffer - FvRecovery binary buffer - FvSize - FvRecovery size - -Returns: - - None - ---*/ { FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry; UINT32 EntryNum; @@ -2460,11 +2588,12 @@ Returns: } /** - This function dump raw data. - @param Data raw data - @param Size raw data size + @param Data Raw data. + @param Size Raw data size. + + @return none **/ VOID @@ -2480,12 +2609,12 @@ DumpData ( } /** - This function dump raw data with colume format. - @param Data raw data - @param Size raw data size + @param Data Raw data + @param Size Raw data size + @return none **/ VOID DumpHex ( @@ -2532,25 +2661,17 @@ CHAR8 *mCapabilityStr[] = { "STM support ", }; +/** + DumpAcm information + + @param Acm - ACM buffer + + @retval None +**/ VOID DumpAcm ( IN ACM_FORMAT *Acm ) -/*++ - -Routine Description: - - DumpAcm information - -Arguments: - - Acm - ACM buffer - -Returns: - - None - ---*/ { CHIPSET_ACM_INFORMATION_TABLE *ChipsetAcmInformationTable; CHIPSET_ID_LIST *ChipsetIdList; @@ -2600,23 +2721,21 @@ Returns: printf (" RSAPubKey - \n"); DumpHex (Buffer, Acm->KeySize * 4); printf ("\n"); - Buffer += Acm->KeySize * 4; - // - // To simplify the tool and making it independent of ACM header change, - // the rest of ACM parsing will be skipped starting ACM_HEADER_VERSION4 - // - if((Acm->HeaderVersion != ACM_HEADER_VERSION_3) && (Acm->HeaderVersion != ACM_HEADER_VERSION_0)){ - printf ( - "*****************************************************************************\n\n" - ); - return; - } + Buffer += Acm->KeySize * 4; //add public key size (taken from header variable * 4) to buffer. + + //add signature size to pointer. if (Acm->HeaderVersion == ACM_HEADER_VERSION_3) { printf (" RSASig - \n"); DumpHex (Buffer, ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE); // PKCS #1.5 RSA Signature printf ("\n"); Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE; - } else { + } + else if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) { + Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE; + Buffer += ACM_XMSS_PUBLIC_KEY_SIZE; + Buffer += ACM_XMSS_SIGNATURE_SIZE; + } + else { printf (" RSAPubExp - %08x\n", *(UINT32 *)Buffer); Buffer += 4; @@ -2627,6 +2746,10 @@ Returns: } Buffer += Acm->ScratchSize * 4; + if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) { + Buffer += 60; //add reserved bytes. + } + if ((Acm->ModuleSubType & ACM_MODULE_SUBTYPE_ANC_MODULE) == 0) { ChipsetAcmInformationTable = (CHIPSET_ACM_INFORMATION_TABLE *)Buffer; printf ("Chipset ACM info:\n"); @@ -2697,28 +2820,77 @@ End: ); } -BOOLEAN -CheckAcm ( - IN ACM_FORMAT *Acm, - IN UINTN AcmMaxSize - ) -/*++ +/** + Get ACM FMS information. + + @param Acm ACM buffer. + @param AcmFms Get ACM FMS. + @param AcmMask Get ACM Mask. + + @retval NULL +**/ +VOID +GetAcmFms( + IN ACM_FORMAT *Acm, + OUT UINT32 *AcmFms, + OUT UINT32 *AcmMask +) +{ + UINT32 FmsOffset = 0; + UINT32 TmpFms = 0; + UINT32 TmpMask = 0; + UINT32 Index = 0; + PROCESSOR_ID_LIST *ProcessorIdList = NULL; + + if ((Acm == NULL) || (AcmFms == NULL) || (AcmMask == NULL)) + return; + + *AcmFms = 0; + *AcmMask = 0; + + switch (Acm->HeaderVersion) { + case ACM_HEADER_VERSION_3: + FmsOffset = *(UINT32*)((UINT8*)Acm + 0x6E8); //AcmInfoTable at 0x6C0, +0x28 for ProcessorIdList + break; + case ACM_HEADER_VERSION_4: + case ACM_HEADER_VERSION_5: + FmsOffset = *(UINT32*)((UINT8*)Acm + 0x1CA8); //AcmInfoTable at 0x1C80, +0x28 for ProcessorIdList + break; + default: + return; + } -Routine Description: + ProcessorIdList = (PROCESSOR_ID_LIST *)((UINT8*)Acm + FmsOffset); - Check Acm information + if (ProcessorIdList->Count > 0) { + TmpFms = ProcessorIdList->ProcessorID[0].FMS; + *AcmFms = TmpFms; + *AcmMask = DEFAULT_ACM_EXTENDED_MASK; + } -Arguments: + for (Index = 1; Index < ProcessorIdList->Count; Index++) { + TmpMask = (TmpFms ^ ProcessorIdList->ProcessorID[Index].FMS); + TmpFms &= ProcessorIdList->ProcessorID[Index].FMS; + } - Acm - ACM buffer - AcmMaxSize - ACM max size + *AcmMask = ~TmpMask; + return; +} -Returns: +/** + Check Acm information. - TRUE - ACM is valid - FALSE - ACM is invalid + @param Acm ACM buffer. + @param AcmMaxSize ACM max size. ---*/ + @retval TRUE ACM is valid. + @retval FALSE ACM is invalid. +**/ +BOOLEAN +CheckAcm ( + IN ACM_FORMAT *Acm, + IN UINTN AcmMaxSize + ) { CHIPSET_ACM_INFORMATION_TABLE *ChipsetAcmInformationTable; CHIPSET_ID_LIST *ChipsetIdList; @@ -2734,24 +2906,27 @@ Returns: return FALSE; } - // - // To simplify the tool and making it independent of ACM header change, - // the following check will be skipped starting ACM_HEADER_VERSION3 - // - if((Acm->HeaderVersion != ACM_HEADER_VERSION_3) && (Acm->HeaderVersion != ACM_HEADER_VERSION_0)){ - printf ("ACM header Version 4 or higher, bypassing other checks!\n"); - return TRUE; - } + //move buffer pointer to address past generic ACM header (post scratchsize) Buffer = (UINT8 *)(Acm + 1); Buffer += Acm->KeySize * 4; if (Acm->HeaderVersion == ACM_HEADER_VERSION_3) { Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE; - } else { + } + else if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) { + Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA384_SIZE; + Buffer += ACM_XMSS_PUBLIC_KEY_SIZE; + Buffer += ACM_XMSS_SIGNATURE_SIZE; + } + else { Buffer += 4; Buffer += ACM_PKCS_1_5_RSA_SIGNATURE_SHA256_SIZE; } Buffer += Acm->ScratchSize * 4; + if ((Acm->HeaderVersion == ACM_HEADER_VERSION_4) || (Acm->HeaderVersion == ACM_HEADER_VERSION_5)) { + Buffer += 60; //add reserved bytes. + } + if ((Acm->ModuleSubType & ACM_MODULE_SUBTYPE_ANC_MODULE) == 0) { ChipsetAcmInformationTable = (CHIPSET_ACM_INFORMATION_TABLE *)Buffer; if ((UINTN)ChipsetAcmInformationTable >= (UINTN)Acm + AcmMaxSize) { @@ -2814,29 +2989,21 @@ End: return TRUE; } +/** + Fill the FIT table information to FvRecovery. + + @param FvBuffer FvRecovery binary buffer. + @param FvSize FvRecovery size. + @param FitTableOffset The offset of FIT table in FvRecovery file. + + @retval None +**/ VOID FillFitTable ( IN UINT8 *FvBuffer, IN UINT32 FvSize, IN UINT8 *FitTableOffset ) -/*++ - -Routine Description: - - Fill the FIT table information to FvRecovery - -Arguments: - - FvBuffer - FvRecovery binary buffer - FvSize - FvRecovery size - FitTableOffset - The offset of FIT table in FvRecovery file - -Returns: - - None - ---*/ { FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry; UINT32 FitIndex; @@ -2899,15 +3066,18 @@ Returns: // 4. StartupAcm // for (Index = 0; Index < gFitTableContext.StartupAcmNumber; Index++) { - if (gFitTableContext.StartupAcmVersion[Index] == STARTUP_ACM_FIT_ENTRY_200_VERSION) { + if (gFitTableContext.StartupAcm[Index].Version == STARTUP_ACM_FIT_ENTRY_200_VERSION) { + printf("ACM version 0x200\n"); FMS.Uint32 = gFitTableContext.StartupAcm[Index].FMS; FMSMask.Uint32 = gFitTableContext.StartupAcm[Index].FMSMask; + printf("ACM FMS:%08x\n", FMS.Uint32); + printf("ACM FMSMask:%08x\n", FMSMask.Uint32); FitEntry[FitIndex].Address = gFitTableContext.StartupAcm[Index].Address; FitEntry[FitIndex].Size[0] = NIBBLES_TO_BYTE (FMS.Bits.Family, FMS.Bits.Model); FitEntry[FitIndex].Size[1] = NIBBLES_TO_BYTE (FMS.Bits.ExtendedModel, FMS.Bits.Type); FitEntry[FitIndex].Size[2] = NIBBLES_TO_BYTE (FMSMask.Bits.Family, FMSMask.Bits.Model); FitEntry[FitIndex].Rsvd = NIBBLES_TO_BYTE (FMSMask.Bits.ExtendedModel, FMSMask.Bits.Type); - FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcmVersion[Index]; + FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcm[Index].Version; FitEntry[FitIndex].Type = FIT_TABLE_TYPE_STARTUP_ACM; FitEntry[FitIndex].C_V = 0; FitEntry[FitIndex].Checksum = NIBBLES_TO_BYTE (FMSMask.Bits.ExtendedFamily, FMS.Bits.ExtendedFamily); @@ -2918,7 +3088,7 @@ Returns: FitEntry[FitIndex].Size[1] = (UINT8)(FitEntrySizeValue >> 8); FitEntry[FitIndex].Size[2] = (UINT8)(FitEntrySizeValue >> 16); FitEntry[FitIndex].Rsvd = 0; - FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcmVersion[Index]; + FitEntry[FitIndex].Version = (UINT16)gFitTableContext.StartupAcm[Index].Version; FitEntry[FitIndex].Type = FIT_TABLE_TYPE_STARTUP_ACM; FitEntry[FitIndex].C_V = 0; FitEntry[FitIndex].Checksum = 0; @@ -2943,7 +3113,23 @@ Returns: FitIndex++; } // - // 5. BiosModule + // 5. (4) Bootable BootPolicy Data + // + if (gFitTableContext.ProtBootPolicy.Address != 0) { + FitEntry[FitIndex].Address = gFitTableContext.ProtBootPolicy.Address; + FitEntry[FitIndex].Size[0] = (UINT8) (gFitTableContext.ProtBootPolicy.Size); + FitEntry[FitIndex].Size[1] = (UINT8) (gFitTableContext.ProtBootPolicy.Size >> 8); + FitEntry[FitIndex].Size[2] = (UINT8) (gFitTableContext.ProtBootPolicy.Size >> 16); + FitEntry[FitIndex].Rsvd = 0; + FitEntry[FitIndex].Version = (UINT16)gFitTableContext.ProtBootPolicy.Version; + FitEntry[FitIndex].Type = FIT_TABLE_TYPE_PROT_BOOT_POLICY; + FitEntry[FitIndex].C_V = 0; + FitEntry[FitIndex].Checksum = 0; + FitIndex++; + } + + // + // 6. BiosModule // // // BiosModule segments order needs to be put from low address to high for Btg requirement @@ -2974,7 +3160,7 @@ Returns: } // - // 6. Optional module + // 7. Optional module // for (Index = 0; Index < gFitTableContext.OptionalModuleNumber; Index++) { FitEntrySizeValue = gFitTableContext.OptionalModule[Index].Size; @@ -2993,7 +3179,7 @@ Returns: } // - // 7. Port module + // 8. Port module // for (Index = 0; Index < gFitTableContext.PortModuleNumber; Index++) { FitEntrySizeValue = 0; @@ -3029,27 +3215,19 @@ Returns: FitEntry[0].Checksum = Checksum; } +/** + Clear the FIT table information to Fvrecovery. + + @param FvBuffer - Fvrecovery binary buffer. + @param FvSize - Fvrecovery size. + + @retval None +**/ VOID ClearFitTable ( IN UINT8 *FvBuffer, IN UINT32 FvSize ) -/*++ - -Routine Description: - - Clear the FIT table information to Fvrecovery - -Arguments: - - FvBuffer - Fvrecovery binary buffer - FvSize - Fvrecovery size - -Returns: - - None - ---*/ { FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry; UINT32 EntryNum; @@ -3097,30 +3275,22 @@ Returns: } } +/** + Read input file. + + @param FileName The input file name. + @param FileData The input file data. + @paramFileSize The input file size. + + @retval STATUS_SUCCESS Write file data successfully. + @retval STATUS_ERROR The file data is not written. +**/ STATUS WriteOutputFile ( IN CHAR8 *FileName, IN UINT8 *FileData, IN UINT32 FileSize ) -/*++ - -Routine Description: - - Read input file - -Arguments: - - FileName - The input file name - FileData - The input file data - FileSize - The input file size - -Returns: - - STATUS_SUCCESS - Write file data successfully - STATUS_ERROR - The file data is not written - ---*/ { FILE *FpOut; @@ -3157,28 +3327,78 @@ Returns: return STATUS_SUCCESS; } + UINT32 -GetFvRecoveryInfoFromFd ( +GetFvAcmSizeFromFd( IN UINT8 *FdBuffer, - IN UINT32 FdFileSize, - OUT UINT8 **FvRecovery - ) -/*++ + IN UINT32 FdFileSize +) +/** + Get FV_ACM Size information from Fd file. -Routine Description: + @param FdBuffer Fd file buffer. + @param FdFileSize Fd file size. - Get FvRecovery information from Fd file. + @retval FvACM size + +**/ +{ + UINT8 *FileBuffer = NULL; + UINT32 FvAcmSize = 0; + EFI_GUID ACMGuid = ACMFV_GUID; + UINT32 FvLength; + UINT32 FileLength; + + //*FvRecovery = NULL; + FileBuffer = FindNextFvHeader(FdBuffer, FdFileSize); + if (FileBuffer == NULL) { + return 0; + } -Arguments: + while ((UINTN)FileBuffer < (UINTN)FdBuffer + FdFileSize) { + FvLength = (UINT32)((EFI_FIRMWARE_VOLUME_HEADER *)FileBuffer)->FvLength; - FdBuffer - Fd file buffer. - FdFileSize - Fd file size. - FvRecovery - FvRecovery pointer in Fd file buffer + if (FindFileFromFvByGuid(FileBuffer, FvLength, &ACMGuid, &FileLength) != NULL) { + // + // Found the ACM + // + FvAcmSize = FvLength; + } -Returns: - FvRecovery file size + // + // Next fv + // + FileBuffer = (UINT8 *)FileBuffer + FvLength; + if ((UINTN)FileBuffer >= (UINTN)FdBuffer + FdFileSize) { + break; + } + FileBuffer = FindNextFvHeader(FileBuffer, (UINTN)FdBuffer + FdFileSize - (UINTN)FileBuffer); + if (FileBuffer == NULL) { + break; + } ---*/ + } + + return FvAcmSize; +} + +/** + + Get FvRecovery information from Fd file. + + @param FdBuffer Fd file buffer. + @param FdFileSize Fd file size. + @param FvRecovery FvRecovery pointer in Fd file buffer + + @retval FvRecovery file size + +**/ +UINT32 +GetFvRecoveryInfoFromFd ( + IN UINT8 *FdBuffer, + IN UINT32 FdFileSize, + OUT UINT8 **FvRecovery + ) { UINT8 *FileBuffer = NULL; UINT32 FvRecoveryFileSize =0; @@ -3223,16 +3443,7 @@ Returns: return FvRecoveryFileSize; } -void -GetFMSFromFitEntry ( - IN FIRMWARE_INTERFACE_TABLE_ENTRY FitEntry, - IN OUT PROCESSOR_ID *FMS, - IN OUT PROCESSOR_ID *FMSMask - ) -/*++ - -Routine Description: - +/** Get FMS information from FIT Entry. Note: Since FIT entry not record all the processor ID information. @@ -3260,17 +3471,18 @@ Routine Description: | | Family | Model | ExtModel | Type | Family | Model | | +----------+-----------------------+-----------------------+-----------------------+-----------------------+ + @param FitEntry FIT entry information. + @param FMS Processor ID information. + @param FMSMask Processor ID mask information. -Arguments: - - FitEntry - FIT entry information. - FMS - Processor ID information. - FMSMask - Processor ID mask information. - -Returns: - None - ---*/ + @retval None +**/ +void +GetFMSFromFitEntry ( + IN FIRMWARE_INTERFACE_TABLE_ENTRY FitEntry, + IN OUT PROCESSOR_ID *FMS, + IN OUT PROCESSOR_ID *FMSMask + ) { FMS->Bits.Family = (FitEntry.Size[0] & 0xF0) >> 4; @@ -3286,27 +3498,19 @@ Returns: FMSMask->Bits.ExtendedFamily = (FitEntry.Checksum & 0xF0) >> 4; } +/** + Get the FIT table information from Fvrecovery. + + @param FvBuffer Fvrecovery binary buffer. + @param FvSize Fvrecovery size. + + @retval 0 - Fit Table not found +**/ UINT32 GetFitEntryInfo ( IN UINT8 *FvBuffer, IN UINT32 FvSize ) -/*++ - -Routine Description: - - Get the FIT table information from Fvrecovery - -Arguments: - - FvBuffer - Fvrecovery binary buffer - FvSize - Fvrecovery size - -Returns: - - 0 - Fit Table not found - ---*/ { FIRMWARE_INTERFACE_TABLE_ENTRY *FitEntry; UINT32 FitEntrySizeValue; @@ -3360,14 +3564,20 @@ Returns: gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Address = (UINT32)FitEntry[FitIndex].Address; gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Size = FitEntrySizeValue; gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Type = FitEntry[FitIndex].Type; - gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] = FitEntry[FitIndex].Version; - if (gFitTableContext.StartupAcmVersion[gFitTableContext.StartupAcmNumber] == STARTUP_ACM_FIT_ENTRY_200_VERSION) { + gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version = FitEntry[FitIndex].Version; + + if (gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].Version == STARTUP_ACM_FIT_ENTRY_200_VERSION) { GetFMSFromFitEntry (FitEntry[FitIndex], &FMS, &FMSMask); gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMS = FMS.Uint32; gFitTableContext.StartupAcm[gFitTableContext.StartupAcmNumber].FMSMask = FMSMask.Uint32; } gFitTableContext.StartupAcmNumber++; break; + case FIT_TABLE_TYPE_PROT_BOOT_POLICY: + gFitTableContext.ProtBootPolicy.Address = (UINT32)FitEntry[FitIndex].Address; + gFitTableContext.ProtBootPolicy.Version = FitEntry[FitIndex].Version; + gFitTableContext.ProtBootPolicy.Size = GetFirmwareInterfaceTableEntrySize (&FitEntry[FitIndex]); + break; case FIT_TABLE_TYPE_BIOS_MODULE: gFitTableContext.BiosModule[gFitTableContext.BiosModuleNumber].Address = (UINT32)FitEntry[FitIndex].Address; gFitTableContext.BiosModule[gFitTableContext.BiosModuleNumber].Size = FitEntrySizeValue * 16; @@ -3398,27 +3608,20 @@ Returns: return gFitTableContext.FitEntryNumber; } +/** + Main function for FitGen. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings. + + @retval STATUS_SUCCESS Utility exits successfully. + @retval STATUS_ERROR Some error occurred during execution. +**/ STATUS FitGen ( IN INTN argc, IN CHAR8 **argv ) -/*++ - -Routine Description: - - Main function for FitGen. - -Arguments: - - argc - Number of command line parameters. - argv - Array of pointers to parameter strings. - -Returns: - STATUS_SUCCESS - Utility exits successfully. - STATUS_ERROR - Some error occurred during execution. - ---*/ { UINT32 FvRecoveryFileSize; UINT8 *FileBuffer; @@ -3433,7 +3636,7 @@ Returns: UINT32 FdFileSize; UINT8 *AcmBuffer; - INTN Index; + INTN Index = 0; UINT32 FixedFitLocation; FileBufferRaw = NULL; @@ -3514,6 +3717,7 @@ Returns: FitTableOffset = GetFreeSpaceForFit (FileBuffer, FvRecoveryFileSize, FitTableSize, FixedFitLocation); if (FitTableOffset == NULL) { + printf ("Error - FitTableOffset is NULL\n"); return STATUS_ERROR; } @@ -3526,7 +3730,10 @@ Returns: // Get ACM buffer // for (Index = 0; Index < (INTN)gFitTableContext.StartupAcmNumber; Index ++) { + printf("ACM address:%08x\n", gFitTableContext.StartupAcm[Index].Address); + printf("ACM size:%08x\n", gFitTableContext.StartupAcm[Index].Size); if (gFitTableContext.StartupAcm[Index].Address != 0) { + printf("get AcmBuffer\n"); AcmBuffer = FLASH_TO_MEMORY(gFitTableContext.StartupAcm[Index].Address, FdFileBuffer, FdFileSize); if ((AcmBuffer < FdFileBuffer) || (AcmBuffer + gFitTableContext.StartupAcm[Index].Size > FdFileBuffer + FdFileSize)) { printf ("ACM out of range - can not validate it\n"); @@ -3534,11 +3741,20 @@ Returns: } if (AcmBuffer != NULL) { - if (CheckAcm ((ACM_FORMAT *)AcmBuffer, gFitTableContext.StartupAcm[Index].Size)) { - DumpAcm ((ACM_FORMAT *)AcmBuffer); - } else { - Status = STATUS_ERROR; - goto exitFunc; + if (CheckAcm((ACM_FORMAT *)AcmBuffer, gFitTableContext.StartupAcm[Index].Size)) { + DumpAcm((ACM_FORMAT *)AcmBuffer); + + if (gFitTableContext.StartupAcm[Index].Version >= 0x200) { + GetAcmFms((ACM_FORMAT *)AcmBuffer, &gFitTableContext.StartupAcm[Index].FMS, &gFitTableContext.StartupAcm[Index].FMSMask); + printf("ACM FMS:%08x\n", gFitTableContext.StartupAcm[Index].FMS); + printf("ACM FMS Mask:%08x\n", gFitTableContext.StartupAcm[Index].FMSMask); + } + } + else { + if (Index == 0) { + Status = STATUS_ERROR; + goto exitFunc; + } } } } @@ -3592,32 +3808,31 @@ exitFunc: return Status; } +/** + View function for FitGen. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings + + @retval STATUS_SUCCESS Utility exits successfully. + @retval STATUS_ERROR Some error occurred during execution. +**/ STATUS FitView ( IN INTN argc, IN CHAR8 **argv ) -/*++ - -Routine Description: - - View function for FitGen. - -Arguments: - - argc - Number of command line parameters. - argv - Array of pointers to parameter strings. - -Returns: - STATUS_SUCCESS - Utility exits successfully. - STATUS_ERROR - Some error occurred during execution. - ---*/ { - UINT32 FvRecoveryFileSize; - UINT8 *FileBuffer; - UINT8 *FileBufferRaw = NULL; - STATUS Status; + UINT32 FvRecoveryFileSize; + UINT8 *FileBuffer; + UINT8 *FileBufferRaw = NULL; + STATUS Status; + FILE *FpIn; + UINT32 FlashValidSig = 0; + UINT32 Frba; + UINT32 BiosRegionBaseOffset; + FLASH_MAP_0_REGISTER FlashMap0; + FLASH_REGION_1_BIOS_REGISTER FlashRegion1; // // Step 1: Read input file @@ -3642,13 +3857,57 @@ Returns: gFitTableContext.FitTablePointerOffset = xtoi (argv[3 + 1]); } else { Error (NULL, 0, 0, "FIT offset not specified!", NULL); + Status = STATUS_ERROR; goto exitFunc; } } else { Error (NULL, 0, 0, "Invalid view option: ", "%s", argv[3]); + Status = STATUS_ERROR; goto exitFunc; } + // + //Check the File Path + // + if (!CheckPath (argv[2])) { + Error (NULL, 0, 0, "File path is invalid!", NULL); + Status = STATUS_ERROR; + goto exitFunc; + } + // + // Open the Input file + // + if ((FpIn = fopen (argv[2], "rb")) == NULL) { + Error (NULL, 0, 0, "Unable open the file!", NULL); + Status = STATUS_WARNING; + goto exitFunc; + } + // + //Seek and read the Flash Valid Signature; + // + fseek (FpIn, FLVALSIG_BASE_OFFSET, SEEK_SET); + fread (&FlashValidSig, 4, 1, FpIn); + if (FlashValidSig == FLASH_VALID_SIGNATURE) { + // + //Seek and read the Flash Map 0 Register; + // + fseek (FpIn, FLMAP0_BASE_OFFSET, SEEK_SET); + fread (&FlashMap0, 4, 1, FpIn); + Frba = FlashMap0.Frba << 4 & 0xFF0; //FRBA identifies address bits [11:4] for the region portion of the flashdescriptor, bits [26:12] and bits [3:0] are 0 + // + //Seek and read the Flash Region 1 (BIOS) Register; + // + BiosRegionBaseOffset = Frba + 0x4; + fseek (FpIn, BiosRegionBaseOffset, SEEK_SET); + fread (&FlashRegion1, 4, 1, FpIn); + FileBuffer = (UINT8 *)(FileBuffer + (FlashRegion1.RegionBase << 12)); // RegionBase specifies address bits [26:12] for the Region Base. + FvRecoveryFileSize = ((FlashRegion1.RegionLimit << 12 | 0xFFF) + 1) - (FlashRegion1.RegionBase << 12); //RegionLimit specifies bits [26:12] of the ending address for this region, bits [11:0] are assumed to be FFFh. + } + // + // Close the Input file + // + fclose (FpIn); + // // For debug // @@ -3661,27 +3920,20 @@ exitFunc: return Status; } +/** + Main function. + + @param argc Number of command line parameters. + @param argv Array of pointers to parameter strings + + @retval STATUS_SUCCESS Utility exits successfully. + @retval STATUS_ERROR Some error occurred during execution. +**/ int main ( int argc, char **argv ) -/*++ - -Routine Description: - - Main function. - -Arguments: - - argc - Number of command line parameters. - argv - Array of pointers to parameter strings. - -Returns: - STATUS_SUCCESS - Utility exits successfully. - STATUS_ERROR - Some error occurred during execution. - ---*/ { SetUtilityName (UTILITY_NAME); @@ -3703,24 +3955,18 @@ Returns: return STATUS_ERROR; } } +/** + Convert hex string to uint + + @param str The string + @retval Integer value + +**/ unsigned int xtoi ( char *str ) -/*++ - -Routine Description: - - Convert hex string to uint - -Arguments: - - str - The string - -Returns: - ---*/ { unsigned int u; char c; diff --git a/Silicon/Intel/Tools/FitGen/FitGen.h b/Silicon/Intel/Tools/FitGen/FitGen.h index 511ab652ab..2d24ecb584 100644 --- a/Silicon/Intel/Tools/FitGen/FitGen.h +++ b/Silicon/Intel/Tools/FitGen/FitGen.h @@ -36,7 +36,6 @@ SPDX-License-Identifier: BSD-2-Clause-Patent #define FIT_SPEC_VERSION_MAJOR 1 #define FIT_SPEC_VERSION_MINOR 4 - // // The minimum number of arguments accepted from the command line. // @@ -50,4 +49,10 @@ SPDX-License-Identifier: BSD-2-Clause-Patent #define ROUNDUP(Size, Alignment) (((Size) + (Alignment) - 1) / (Alignment) * (Alignment)) +UINT32 +GetFvAcmSizeFromFd( +IN UINT8 *FdBuffer, +IN UINT32 FdFileSize +); + #endif -- 2.30.1.windows.1 -=-=-=-=-=-=-=-=-=-=-=- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#96525): https://edk2.groups.io/g/devel/message/96525 Mute This Topic: https://groups.io/mt/95067601/1787277 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [importer@patchew.org] -=-=-=-=-=-=-=-=-=-=-=-
© 2016 - 2024 Red Hat, Inc.