-/*++ @file
- A simple FV stack so the SEC can extract the SEC Core from an
- FV.
-
-Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>
-This program and the accompanying materials
-are licensed and made available under the terms and conditions of the BSD License
-which accompanies this distribution. The full text of the license may be found at
-http://opensource.org/licenses/bsd-license.php
-
-THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
-WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
-
-**/
-
-#include <PiPei.h>
-
-
-#define GET_OCCUPIED_SIZE(ActualSize, Alignment) \
- (ActualSize) + (((Alignment) - ((ActualSize) & ((Alignment) - 1))) & ((Alignment) - 1))
-
-EFI_FFS_FILE_STATE
-GetFileState (
- IN UINT8 ErasePolarity,
- IN EFI_FFS_FILE_HEADER *FfsHeader
- )
-/*++
-
-Routine Description:
- Returns the highest bit set of the State field
-
-Arguments:
- ErasePolarity - Erase Polarity as defined by EFI_FVB2_ERASE_POLARITY
- in the Attributes field.
- FfsHeader - Pointer to FFS File Header.
-
-Returns:
- Returns the highest bit in the State field
-
-**/
-{
- EFI_FFS_FILE_STATE FileState;
- EFI_FFS_FILE_STATE HighestBit;
-
- FileState = FfsHeader->State;
-
- if (ErasePolarity != 0) {
- FileState = (EFI_FFS_FILE_STATE)~FileState;
- }
-
- HighestBit = 0x80;
- while (HighestBit != 0 && (HighestBit & FileState) == 0) {
- HighestBit >>= 1;
- }
-
- return HighestBit;
-}
-
-UINT8
-CalculateHeaderChecksum (
- IN EFI_FFS_FILE_HEADER *FileHeader
- )
-/*++
-
-Routine Description:
- Calculates the checksum of the header of a file.
-
-Arguments:
- FileHeader - Pointer to FFS File Header.
-
-Returns:
- Checksum of the header.
-
-**/
-{
- UINT8 *ptr;
- UINTN Index;
- UINT8 Sum;
-
- Sum = 0;
- ptr = (UINT8 *) FileHeader;
-
- for (Index = 0; Index < sizeof (EFI_FFS_FILE_HEADER) - 3; Index += 4) {
- Sum = (UINT8) (Sum + ptr[Index]);
- Sum = (UINT8) (Sum + ptr[Index + 1]);
- Sum = (UINT8) (Sum + ptr[Index + 2]);
- Sum = (UINT8) (Sum + ptr[Index + 3]);
- }
-
- for (; Index < sizeof (EFI_FFS_FILE_HEADER); Index++) {
- Sum = (UINT8) (Sum + ptr[Index]);
- }
- //
- // State field (since this indicates the different state of file).
- //
- Sum = (UINT8) (Sum - FileHeader->State);
- //
- // Checksum field of the file is not part of the header checksum.
- //
- Sum = (UINT8) (Sum - FileHeader->IntegrityCheck.Checksum.File);
-
- return Sum;
-}
-
-EFI_STATUS
-SecFfsFindNextFile (
- IN EFI_FV_FILETYPE SearchType,
- IN EFI_PEI_FV_HANDLE FvHandle,
- IN OUT EFI_PEI_FILE_HANDLE *FileHandle
- )
-/*++
-
-Routine Description:
- Given the input file pointer, search for the next matching file in the
- FFS volume as defined by SearchType. The search starts from FileHeader inside
- the Firmware Volume defined by FwVolHeader.
-
-Arguments:
- SearchType - Filter to find only files of this type.
- Type EFI_FV_FILETYPE_ALL causes no filtering to be done.
- FwVolHeader - Pointer to the FV header of the volume to search.
- This parameter must point to a valid FFS volume.
- FileHeader - Pointer to the current file from which to begin searching.
- This pointer will be updated upon return to reflect the file
- found.
-
-Returns:
- EFI_NOT_FOUND - No files matching the search criteria were found
- EFI_SUCCESS
-
-**/
-{
- EFI_FFS_FILE_HEADER *FfsFileHeader;
- UINT32 FileLength;
- UINT32 FileOccupiedSize;
- UINT32 FileOffset;
- UINT64 FvLength;
- UINT8 ErasePolarity;
- UINT8 FileState;
- EFI_FIRMWARE_VOLUME_HEADER *FwVolHeader;
- EFI_FFS_FILE_HEADER **FileHeader;
-
- //
- // Convert the handle of FV to FV header for memory-mapped firmware volume
- //
- FwVolHeader = (EFI_FIRMWARE_VOLUME_HEADER *) FvHandle;
- FileHeader = (EFI_FFS_FILE_HEADER **)FileHandle;
-
- FvLength = FwVolHeader->FvLength;
- if (FwVolHeader->Attributes & EFI_FVB2_ERASE_POLARITY) {
- ErasePolarity = 1;
- } else {
- ErasePolarity = 0;
- }
- //
- // If FileHeader is not specified (NULL) start with the first file in the
- // firmware volume. Otherwise, start from the FileHeader.
- //
- if (*FileHeader == NULL) {
- FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FwVolHeader + FwVolHeader->HeaderLength);
- } else {
- //
- // Length is 24 bits wide so mask upper 8 bits
- // FileLength is adjusted to FileOccupiedSize as it is 8 byte aligned.
- //
- FileLength = *(UINT32 *) (*FileHeader)->Size & 0x00FFFFFF;
- FileOccupiedSize = GET_OCCUPIED_SIZE (FileLength, 8);
- FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) *FileHeader + FileOccupiedSize);
- }
-
- FileOffset = (UINT32) ((UINT8 *) FfsFileHeader - (UINT8 *) FwVolHeader);
-
- while (FileOffset < (FvLength - sizeof (EFI_FFS_FILE_HEADER))) {
- //
- // Get FileState which is the highest bit of the State
- //
- FileState = GetFileState (ErasePolarity, FfsFileHeader);
-
- switch (FileState) {
-
- case EFI_FILE_HEADER_INVALID:
- FileOffset += sizeof (EFI_FFS_FILE_HEADER);
- FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FfsFileHeader + sizeof (EFI_FFS_FILE_HEADER));
- break;
-
- case EFI_FILE_DATA_VALID:
- case EFI_FILE_MARKED_FOR_UPDATE:
- if (CalculateHeaderChecksum (FfsFileHeader) == 0) {
- FileLength = *(UINT32 *) (FfsFileHeader->Size) & 0x00FFFFFF;
- FileOccupiedSize = GET_OCCUPIED_SIZE (FileLength, 8);
-
- if ((SearchType == FfsFileHeader->Type) || (SearchType == EFI_FV_FILETYPE_ALL)) {
-
- *FileHeader = FfsFileHeader;
-
- return EFI_SUCCESS;
- }
-
- FileOffset += FileOccupiedSize;
- FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FfsFileHeader + FileOccupiedSize);
- } else {
- return EFI_NOT_FOUND;
- }
- break;
-
- case EFI_FILE_DELETED:
- FileLength = *(UINT32 *) (FfsFileHeader->Size) & 0x00FFFFFF;
- FileOccupiedSize = GET_OCCUPIED_SIZE (FileLength, 8);
- FileOffset += FileOccupiedSize;
- FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FfsFileHeader + FileOccupiedSize);
- break;
-
- default:
- return EFI_NOT_FOUND;
-
- }
- }
-
- return EFI_NOT_FOUND;
-}
-
-EFI_STATUS
-SecFfsFindSectionData (
- IN EFI_SECTION_TYPE SectionType,
- IN EFI_FFS_FILE_HEADER *FfsFileHeader,
- IN OUT VOID **SectionData
- )
-/*++
-
-Routine Description:
- Given the input file pointer, search for the next matching section in the
- FFS volume.
-
-Arguments:
- SearchType - Filter to find only sections of this type.
- FfsFileHeader - Pointer to the current file to search.
- SectionData - Pointer to the Section matching SectionType in FfsFileHeader.
- NULL if section not found
-
-Returns:
- EFI_NOT_FOUND - No files matching the search criteria were found
- EFI_SUCCESS
-
-**/
-{
- UINT32 FileSize;
- EFI_COMMON_SECTION_HEADER *Section;
- UINT32 SectionLength;
- UINT32 ParsedLength;
-
- //
- // Size is 24 bits wide so mask upper 8 bits.
- // Does not include FfsFileHeader header size
- // FileSize is adjusted to FileOccupiedSize as it is 8 byte aligned.
- //
- Section = (EFI_COMMON_SECTION_HEADER *) (FfsFileHeader + 1);
- FileSize = *(UINT32 *) (FfsFileHeader->Size) & 0x00FFFFFF;
- FileSize -= sizeof (EFI_FFS_FILE_HEADER);
-
- *SectionData = NULL;
- ParsedLength = 0;
- while (ParsedLength < FileSize) {
- if (Section->Type == SectionType) {
- *SectionData = (VOID *) (Section + 1);
- return EFI_SUCCESS;
- }
- //
- // Size is 24 bits wide so mask upper 8 bits.
- // SectionLength is adjusted it is 4 byte aligned.
- // Go to the next section
- //
- SectionLength = *(UINT32 *) Section->Size & 0x00FFFFFF;
- SectionLength = GET_OCCUPIED_SIZE (SectionLength, 4);
-
- ParsedLength += SectionLength;
- Section = (EFI_COMMON_SECTION_HEADER *) ((UINT8 *) Section + SectionLength);
- }
-
- return EFI_NOT_FOUND;
-}
-
+/*++ @file\r
+ A simple FV stack so the SEC can extract the SEC Core from an\r
+ FV.\r
+\r
+Copyright (c) 2006, Intel Corporation. All rights reserved.<BR>\r
+This program and the accompanying materials\r
+are licensed and made available under the terms and conditions of the BSD License\r
+which accompanies this distribution. The full text of the license may be found at\r
+http://opensource.org/licenses/bsd-license.php\r
+\r
+THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
+WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+\r
+**/\r
+\r
+#include <PiPei.h>\r
+\r
+\r
+#define GET_OCCUPIED_SIZE(ActualSize, Alignment) \\r
+ (ActualSize) + (((Alignment) - ((ActualSize) & ((Alignment) - 1))) & ((Alignment) - 1))\r
+\r
+EFI_FFS_FILE_STATE\r
+GetFileState (\r
+ IN UINT8 ErasePolarity,\r
+ IN EFI_FFS_FILE_HEADER *FfsHeader\r
+ )\r
+/*++\r
+\r
+Routine Description:\r
+ Returns the highest bit set of the State field\r
+\r
+Arguments:\r
+ ErasePolarity - Erase Polarity as defined by EFI_FVB2_ERASE_POLARITY\r
+ in the Attributes field.\r
+ FfsHeader - Pointer to FFS File Header.\r
+\r
+Returns:\r
+ Returns the highest bit in the State field\r
+\r
+**/\r
+{\r
+ EFI_FFS_FILE_STATE FileState;\r
+ EFI_FFS_FILE_STATE HighestBit;\r
+\r
+ FileState = FfsHeader->State;\r
+\r
+ if (ErasePolarity != 0) {\r
+ FileState = (EFI_FFS_FILE_STATE)~FileState;\r
+ }\r
+\r
+ HighestBit = 0x80;\r
+ while (HighestBit != 0 && (HighestBit & FileState) == 0) {\r
+ HighestBit >>= 1;\r
+ }\r
+\r
+ return HighestBit;\r
+}\r
+\r
+UINT8\r
+CalculateHeaderChecksum (\r
+ IN EFI_FFS_FILE_HEADER *FileHeader\r
+ )\r
+/*++\r
+\r
+Routine Description:\r
+ Calculates the checksum of the header of a file.\r
+\r
+Arguments:\r
+ FileHeader - Pointer to FFS File Header.\r
+\r
+Returns:\r
+ Checksum of the header.\r
+\r
+**/\r
+{\r
+ UINT8 *ptr;\r
+ UINTN Index;\r
+ UINT8 Sum;\r
+\r
+ Sum = 0;\r
+ ptr = (UINT8 *) FileHeader;\r
+\r
+ for (Index = 0; Index < sizeof (EFI_FFS_FILE_HEADER) - 3; Index += 4) {\r
+ Sum = (UINT8) (Sum + ptr[Index]);\r
+ Sum = (UINT8) (Sum + ptr[Index + 1]);\r
+ Sum = (UINT8) (Sum + ptr[Index + 2]);\r
+ Sum = (UINT8) (Sum + ptr[Index + 3]);\r
+ }\r
+\r
+ for (; Index < sizeof (EFI_FFS_FILE_HEADER); Index++) {\r
+ Sum = (UINT8) (Sum + ptr[Index]);\r
+ }\r
+ //\r
+ // State field (since this indicates the different state of file).\r
+ //\r
+ Sum = (UINT8) (Sum - FileHeader->State);\r
+ //\r
+ // Checksum field of the file is not part of the header checksum.\r
+ //\r
+ Sum = (UINT8) (Sum - FileHeader->IntegrityCheck.Checksum.File);\r
+\r
+ return Sum;\r
+}\r
+\r
+EFI_STATUS\r
+SecFfsFindNextFile (\r
+ IN EFI_FV_FILETYPE SearchType,\r
+ IN EFI_PEI_FV_HANDLE FvHandle,\r
+ IN OUT EFI_PEI_FILE_HANDLE *FileHandle\r
+ )\r
+/*++\r
+\r
+Routine Description:\r
+ Given the input file pointer, search for the next matching file in the\r
+ FFS volume as defined by SearchType. The search starts from FileHeader inside\r
+ the Firmware Volume defined by FwVolHeader.\r
+\r
+Arguments:\r
+ SearchType - Filter to find only files of this type.\r
+ Type EFI_FV_FILETYPE_ALL causes no filtering to be done.\r
+ FwVolHeader - Pointer to the FV header of the volume to search.\r
+ This parameter must point to a valid FFS volume.\r
+ FileHeader - Pointer to the current file from which to begin searching.\r
+ This pointer will be updated upon return to reflect the file\r
+ found.\r
+\r
+Returns:\r
+ EFI_NOT_FOUND - No files matching the search criteria were found\r
+ EFI_SUCCESS\r
+\r
+**/\r
+{\r
+ EFI_FFS_FILE_HEADER *FfsFileHeader;\r
+ UINT32 FileLength;\r
+ UINT32 FileOccupiedSize;\r
+ UINT32 FileOffset;\r
+ UINT64 FvLength;\r
+ UINT8 ErasePolarity;\r
+ UINT8 FileState;\r
+ EFI_FIRMWARE_VOLUME_HEADER *FwVolHeader;\r
+ EFI_FFS_FILE_HEADER **FileHeader;\r
+\r
+ //\r
+ // Convert the handle of FV to FV header for memory-mapped firmware volume\r
+ //\r
+ FwVolHeader = (EFI_FIRMWARE_VOLUME_HEADER *) FvHandle;\r
+ FileHeader = (EFI_FFS_FILE_HEADER **)FileHandle;\r
+\r
+ FvLength = FwVolHeader->FvLength;\r
+ if (FwVolHeader->Attributes & EFI_FVB2_ERASE_POLARITY) {\r
+ ErasePolarity = 1;\r
+ } else {\r
+ ErasePolarity = 0;\r
+ }\r
+ //\r
+ // If FileHeader is not specified (NULL) start with the first file in the\r
+ // firmware volume. Otherwise, start from the FileHeader.\r
+ //\r
+ if (*FileHeader == NULL) {\r
+ FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FwVolHeader + FwVolHeader->HeaderLength);\r
+ } else {\r
+ //\r
+ // Length is 24 bits wide so mask upper 8 bits\r
+ // FileLength is adjusted to FileOccupiedSize as it is 8 byte aligned.\r
+ //\r
+ FileLength = *(UINT32 *) (*FileHeader)->Size & 0x00FFFFFF;\r
+ FileOccupiedSize = GET_OCCUPIED_SIZE (FileLength, 8);\r
+ FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) *FileHeader + FileOccupiedSize);\r
+ }\r
+\r
+ FileOffset = (UINT32) ((UINT8 *) FfsFileHeader - (UINT8 *) FwVolHeader);\r
+\r
+ while (FileOffset < (FvLength - sizeof (EFI_FFS_FILE_HEADER))) {\r
+ //\r
+ // Get FileState which is the highest bit of the State\r
+ //\r
+ FileState = GetFileState (ErasePolarity, FfsFileHeader);\r
+\r
+ switch (FileState) {\r
+\r
+ case EFI_FILE_HEADER_INVALID:\r
+ FileOffset += sizeof (EFI_FFS_FILE_HEADER);\r
+ FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FfsFileHeader + sizeof (EFI_FFS_FILE_HEADER));\r
+ break;\r
+\r
+ case EFI_FILE_DATA_VALID:\r
+ case EFI_FILE_MARKED_FOR_UPDATE:\r
+ if (CalculateHeaderChecksum (FfsFileHeader) == 0) {\r
+ FileLength = *(UINT32 *) (FfsFileHeader->Size) & 0x00FFFFFF;\r
+ FileOccupiedSize = GET_OCCUPIED_SIZE (FileLength, 8);\r
+\r
+ if ((SearchType == FfsFileHeader->Type) || (SearchType == EFI_FV_FILETYPE_ALL)) {\r
+\r
+ *FileHeader = FfsFileHeader;\r
+\r
+ return EFI_SUCCESS;\r
+ }\r
+\r
+ FileOffset += FileOccupiedSize;\r
+ FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FfsFileHeader + FileOccupiedSize);\r
+ } else {\r
+ return EFI_NOT_FOUND;\r
+ }\r
+ break;\r
+\r
+ case EFI_FILE_DELETED:\r
+ FileLength = *(UINT32 *) (FfsFileHeader->Size) & 0x00FFFFFF;\r
+ FileOccupiedSize = GET_OCCUPIED_SIZE (FileLength, 8);\r
+ FileOffset += FileOccupiedSize;\r
+ FfsFileHeader = (EFI_FFS_FILE_HEADER *) ((UINT8 *) FfsFileHeader + FileOccupiedSize);\r
+ break;\r
+\r
+ default:\r
+ return EFI_NOT_FOUND;\r
+\r
+ }\r
+ }\r
+\r
+ return EFI_NOT_FOUND;\r
+}\r
+\r
+EFI_STATUS\r
+SecFfsFindSectionData (\r
+ IN EFI_SECTION_TYPE SectionType,\r
+ IN EFI_FFS_FILE_HEADER *FfsFileHeader,\r
+ IN OUT VOID **SectionData\r
+ )\r
+/*++\r
+\r
+Routine Description:\r
+ Given the input file pointer, search for the next matching section in the\r
+ FFS volume.\r
+\r
+Arguments:\r
+ SearchType - Filter to find only sections of this type.\r
+ FfsFileHeader - Pointer to the current file to search.\r
+ SectionData - Pointer to the Section matching SectionType in FfsFileHeader.\r
+ NULL if section not found\r
+\r
+Returns:\r
+ EFI_NOT_FOUND - No files matching the search criteria were found\r
+ EFI_SUCCESS\r
+\r
+**/\r
+{\r
+ UINT32 FileSize;\r
+ EFI_COMMON_SECTION_HEADER *Section;\r
+ UINT32 SectionLength;\r
+ UINT32 ParsedLength;\r
+\r
+ //\r
+ // Size is 24 bits wide so mask upper 8 bits.\r
+ // Does not include FfsFileHeader header size\r
+ // FileSize is adjusted to FileOccupiedSize as it is 8 byte aligned.\r
+ //\r
+ Section = (EFI_COMMON_SECTION_HEADER *) (FfsFileHeader + 1);\r
+ FileSize = *(UINT32 *) (FfsFileHeader->Size) & 0x00FFFFFF;\r
+ FileSize -= sizeof (EFI_FFS_FILE_HEADER);\r
+\r
+ *SectionData = NULL;\r
+ ParsedLength = 0;\r
+ while (ParsedLength < FileSize) {\r
+ if (Section->Type == SectionType) {\r
+ *SectionData = (VOID *) (Section + 1);\r
+ return EFI_SUCCESS;\r
+ }\r
+ //\r
+ // Size is 24 bits wide so mask upper 8 bits.\r
+ // SectionLength is adjusted it is 4 byte aligned.\r
+ // Go to the next section\r
+ //\r
+ SectionLength = *(UINT32 *) Section->Size & 0x00FFFFFF;\r
+ SectionLength = GET_OCCUPIED_SIZE (SectionLength, 4);\r
+\r
+ ParsedLength += SectionLength;\r
+ Section = (EFI_COMMON_SECTION_HEADER *) ((UINT8 *) Section + SectionLength);\r
+ }\r
+\r
+ return EFI_NOT_FOUND;\r
+}\r
+\r