2 Pei Core Firmware File System service routines.
4 Copyright (c) 2006 - 2007, Intel Corporation
5 All rights reserved. This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
17 STATIC EFI_PEI_NOTIFY_DESCRIPTOR mNotifyOnFvInfoList
= {
18 (EFI_PEI_PPI_DESCRIPTOR_NOTIFY_CALLBACK
| EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST
),
19 &gEfiPeiFirmwareVolumeInfoPpiGuid
,
20 FirmwareVolmeInfoPpiNotifyCallback
24 #define GET_OCCUPIED_SIZE(ActualSize, Alignment) \
25 (ActualSize) + (((Alignment) - ((ActualSize) & ((Alignment) - 1))) & ((Alignment) - 1))
28 Returns the highest bit set of the State field
30 @param ErasePolarity Erase Polarity as defined by EFI_FVB2_ERASE_POLARITY
31 in the Attributes field.
32 @param FfsHeader Pointer to FFS File Header.
34 @return Returns the highest bit in the State field
39 IN UINT8 ErasePolarity
,
40 IN EFI_FFS_FILE_HEADER
*FfsHeader
43 EFI_FFS_FILE_STATE FileState
;
44 EFI_FFS_FILE_STATE HighestBit
;
46 FileState
= FfsHeader
->State
;
48 if (ErasePolarity
!= 0) {
49 FileState
= (EFI_FFS_FILE_STATE
)~FileState
;
53 while (HighestBit
!= 0 && (HighestBit
& FileState
) == 0) {
61 Calculates the checksum of the header of a file.
63 @param FileHeader Pointer to FFS File Header.
65 @return Checksum of the header.
66 The header is zero byte checksum.
67 Zero means the header is good.
68 Non-zero means the header is bad.
71 CalculateHeaderChecksum (
72 IN EFI_FFS_FILE_HEADER
*FileHeader
80 Ptr
= (UINT8
*)FileHeader
;
82 for (Index
= 0; Index
< sizeof(EFI_FFS_FILE_HEADER
) - 3; Index
+= 4) {
83 Sum
= (UINT8
)(Sum
+ Ptr
[Index
]);
84 Sum
= (UINT8
)(Sum
+ Ptr
[Index
+1]);
85 Sum
= (UINT8
)(Sum
+ Ptr
[Index
+2]);
86 Sum
= (UINT8
)(Sum
+ Ptr
[Index
+3]);
89 for (; Index
< sizeof(EFI_FFS_FILE_HEADER
); Index
++) {
90 Sum
= (UINT8
)(Sum
+ Ptr
[Index
]);
94 // State field (since this indicates the different state of file).
96 Sum
= (UINT8
)(Sum
- FileHeader
->State
);
98 // Checksum field of the file is not part of the header checksum.
100 Sum
= (UINT8
)(Sum
- FileHeader
->IntegrityCheck
.Checksum
.File
);
106 Find FV handler according some FileHandle in that FV.
108 @param FileHandle Handle of file image
109 @param VolumeHandle Handle of FV
111 @return EDES_TODO: Add description for return value
116 PeiFileHandleToVolume (
117 IN EFI_PEI_FILE_HANDLE FileHandle
,
118 OUT EFI_PEI_FV_HANDLE
*VolumeHandle
122 PEI_CORE_INSTANCE
*PrivateData
;
123 EFI_FIRMWARE_VOLUME_HEADER
*FwVolHeader
;
125 PrivateData
= PEI_CORE_INSTANCE_FROM_PS_THIS (GetPeiServicesTablePointer ());
126 for (Index
= 0; Index
< PrivateData
->FvCount
; Index
++) {
127 FwVolHeader
= PrivateData
->Fv
[Index
].FvHeader
;
128 if (((UINT64
) (UINTN
) FileHandle
> (UINT64
) (UINTN
) FwVolHeader
) && \
129 ((UINT64
) (UINTN
) FileHandle
<= ((UINT64
) (UINTN
) FwVolHeader
+ FwVolHeader
->FvLength
- 1))) {
130 *VolumeHandle
= (EFI_PEI_FV_HANDLE
)FwVolHeader
;
138 Given the input file pointer, search for the next matching file in the
139 FFS volume as defined by SearchType. The search starts from FileHeader inside
140 the Firmware Volume defined by FwVolHeader.
143 @param FvHandle Pointer to the FV header of the volume to search
144 @param FileName File name
145 @param SearchType Filter to find only files of this type.
146 Type EFI_FV_FILETYPE_ALL causes no filtering to be done.
147 @param FileHandle This parameter must point to a valid FFS volume.
148 @param AprioriFile Pointer to AprioriFile image in this FV if has
150 @return EFI_NOT_FOUND No files matching the search criteria were found
151 @retval EFI_SUCCESS Success to search given file
156 IN CONST EFI_PEI_FV_HANDLE FvHandle
,
157 IN CONST EFI_GUID
*FileName
, OPTIONAL
158 IN EFI_FV_FILETYPE SearchType
,
159 IN OUT EFI_PEI_FILE_HANDLE
*FileHandle
,
160 IN OUT EFI_PEI_FV_HANDLE
*AprioriFile OPTIONAL
163 EFI_FIRMWARE_VOLUME_HEADER
*FwVolHeader
;
164 EFI_FFS_FILE_HEADER
**FileHeader
;
165 EFI_FFS_FILE_HEADER
*FfsFileHeader
;
166 EFI_FIRMWARE_VOLUME_EXT_HEADER
*FwVolExHeaderInfo
;
168 UINT32 FileOccupiedSize
;
174 FwVolHeader
= (EFI_FIRMWARE_VOLUME_HEADER
*)FvHandle
;
175 FileHeader
= (EFI_FFS_FILE_HEADER
**)FileHandle
;
177 FvLength
= FwVolHeader
->FvLength
;
178 if (FwVolHeader
->Attributes
& EFI_FVB2_ERASE_POLARITY
) {
185 // If FileHeader is not specified (NULL) or FileName is not NULL,
186 // start with the first file in the firmware volume. Otherwise,
187 // start from the FileHeader.
189 if ((*FileHeader
== NULL
) || (FileName
!= NULL
)) {
190 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)((UINT8
*)FwVolHeader
+ FwVolHeader
->HeaderLength
);
191 if (FwVolHeader
->ExtHeaderOffset
!= 0) {
192 FwVolExHeaderInfo
= (EFI_FIRMWARE_VOLUME_EXT_HEADER
*)(((UINT8
*)FwVolHeader
) + FwVolHeader
->ExtHeaderOffset
);
193 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)(((UINT8
*)FwVolExHeaderInfo
) + FwVolExHeaderInfo
->ExtHeaderSize
);
197 // Length is 24 bits wide so mask upper 8 bits
198 // FileLength is adjusted to FileOccupiedSize as it is 8 byte aligned.
200 FileLength
= *(UINT32
*)(*FileHeader
)->Size
& 0x00FFFFFF;
201 FileOccupiedSize
= GET_OCCUPIED_SIZE (FileLength
, 8);
202 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)((UINT8
*)*FileHeader
+ FileOccupiedSize
);
205 FileOffset
= (UINT32
) ((UINT8
*)FfsFileHeader
- (UINT8
*)FwVolHeader
);
206 ASSERT (FileOffset
<= 0xFFFFFFFF);
208 while (FileOffset
< (FvLength
- sizeof (EFI_FFS_FILE_HEADER
))) {
210 // Get FileState which is the highest bit of the State
212 FileState
= GetFileState (ErasePolarity
, FfsFileHeader
);
215 case EFI_FILE_HEADER_INVALID
:
216 FileOffset
+= sizeof(EFI_FFS_FILE_HEADER
);
217 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)((UINT8
*)FfsFileHeader
+ sizeof(EFI_FFS_FILE_HEADER
));
220 case EFI_FILE_DATA_VALID
:
221 case EFI_FILE_MARKED_FOR_UPDATE
:
222 if (CalculateHeaderChecksum (FfsFileHeader
) != 0) {
225 return EFI_NOT_FOUND
;
228 FileLength
= *(UINT32
*)(FfsFileHeader
->Size
) & 0x00FFFFFF;
229 FileOccupiedSize
= GET_OCCUPIED_SIZE(FileLength
, 8);
231 if (FileName
!= NULL
) {
232 if (CompareGuid (&FfsFileHeader
->Name
, (EFI_GUID
*)FileName
)) {
233 *FileHeader
= FfsFileHeader
;
236 } else if (SearchType
== PEI_CORE_INTERNAL_FFS_FILE_DISPATCH_TYPE
) {
237 if ((FfsFileHeader
->Type
== EFI_FV_FILETYPE_PEIM
) ||
238 (FfsFileHeader
->Type
== EFI_FV_FILETYPE_COMBINED_PEIM_DRIVER
) ||
239 (FfsFileHeader
->Type
== EFI_FV_FILETYPE_FIRMWARE_VOLUME_IMAGE
)) {
241 *FileHeader
= FfsFileHeader
;
243 } else if (AprioriFile
!= NULL
) {
244 if (FfsFileHeader
->Type
== EFI_FV_FILETYPE_FREEFORM
) {
245 if (CompareGuid (&FfsFileHeader
->Name
, &gPeiAprioriFileNameGuid
)) {
246 *AprioriFile
= FfsFileHeader
;
250 } else if (((SearchType
== FfsFileHeader
->Type
) || (SearchType
== EFI_FV_FILETYPE_ALL
)) &&
251 (FfsFileHeader
->Type
!= EFI_FV_FILETYPE_FFS_PAD
)) {
252 *FileHeader
= FfsFileHeader
;
256 FileOffset
+= FileOccupiedSize
;
257 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)((UINT8
*)FfsFileHeader
+ FileOccupiedSize
);
260 case EFI_FILE_DELETED
:
261 FileLength
= *(UINT32
*)(FfsFileHeader
->Size
) & 0x00FFFFFF;
262 FileOccupiedSize
= GET_OCCUPIED_SIZE(FileLength
, 8);
263 FileOffset
+= FileOccupiedSize
;
264 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)((UINT8
*)FfsFileHeader
+ FileOccupiedSize
);
269 return EFI_NOT_FOUND
;
274 return EFI_NOT_FOUND
;
278 Initialize PeiCore Fv List.
280 @param PrivateData - Pointer to PEI_CORE_INSTANCE.
281 @param SecCoreData - Pointer to EFI_SEC_PEI_HAND_OFF.
285 IN PEI_CORE_INSTANCE
*PrivateData
,
286 IN CONST EFI_SEC_PEI_HAND_OFF
*SecCoreData
291 // The BFV must be the first entry. The Core FV support is stateless
292 // The AllFV list has a single entry per FV in PEI.
293 // The Fv list only includes FV that PEIMs will be dispatched from and
294 // its File System Format is PI 1.0 definition.
296 PrivateData
->FvCount
= 1;
297 PrivateData
->Fv
[0].FvHeader
= (EFI_FIRMWARE_VOLUME_HEADER
*)SecCoreData
->BootFirmwareVolumeBase
;
299 PrivateData
->AllFvCount
= 1;
300 PrivateData
->AllFv
[0] = (EFI_PEI_FV_HANDLE
)PrivateData
->Fv
[0].FvHeader
;
304 // Post a call-back for the FvInfoPPI services to expose
305 // additional Fvs to PeiCore.
307 Status
= PeiServicesNotifyPpi (&mNotifyOnFvInfoList
);
308 ASSERT_EFI_ERROR (Status
);
313 Process Firmware Volum Information once FvInfoPPI install.
316 @param PeiServices - General purpose services available to every PEIM.
317 @param NotifyDescriptor EDES_TODO: Add parameter description
318 @param Ppi EDES_TODO: Add parameter description
320 @retval EFI_SUCCESS if the interface could be successfully installed
325 FirmwareVolmeInfoPpiNotifyCallback (
326 IN EFI_PEI_SERVICES
**PeiServices
,
327 IN EFI_PEI_NOTIFY_DESCRIPTOR
*NotifyDescriptor
,
332 EFI_PEI_FIRMWARE_VOLUME_INFO_PPI
*Fv
;
333 PEI_CORE_INSTANCE
*PrivateData
;
334 EFI_PEI_FILE_HANDLE FileHandle
;
336 UINT32 AuthenticationStatus
;
341 Status
= EFI_SUCCESS
;
342 PrivateData
= PEI_CORE_INSTANCE_FROM_PS_THIS (PeiServices
);
344 if (PrivateData
->FvCount
>= FixedPcdGet32 (PcdPeiCoreMaxFvSupported
)) {
348 Fv
= (EFI_PEI_FIRMWARE_VOLUME_INFO_PPI
*)Ppi
;
350 if (CompareGuid (&Fv
->FvFormat
, &gEfiFirmwareFileSystem2Guid
)) {
351 for (FvCount
= 0; FvCount
< PrivateData
->FvCount
; FvCount
++) {
352 if ((UINTN
)PrivateData
->Fv
[FvCount
].FvHeader
== (UINTN
)Fv
->FvInfo
) {
356 PrivateData
->Fv
[PrivateData
->FvCount
++].FvHeader
= (EFI_FIRMWARE_VOLUME_HEADER
*)Fv
->FvInfo
;
359 // Only add FileSystem2 Fv to the All list
361 PrivateData
->AllFv
[PrivateData
->AllFvCount
++] = (EFI_PEI_FV_HANDLE
)Fv
->FvInfo
;
363 DEBUG ((EFI_D_INFO
, "The %dth FvImage start address is 0x%11p and size is 0x%08x\n", PrivateData
->AllFvCount
, (VOID
*) Fv
->FvInfo
, Fv
->FvInfoSize
));
365 // Preprocess all FV type files in this new FileSystem2 Fv image
368 Status
= PeiFindFileEx (
369 (EFI_PEI_FV_HANDLE
)Fv
->FvInfo
,
371 EFI_FV_FILETYPE_FIRMWARE_VOLUME_IMAGE
,
375 if (!EFI_ERROR (Status
)) {
376 Status
= PeiFfsFindSectionData (
377 (CONST EFI_PEI_SERVICES
**) PeiServices
,
378 EFI_SECTION_PEI_DEPEX
,
382 if (!EFI_ERROR (Status
)) {
383 if (!PeimDispatchReadiness (PeiServices
, DepexData
)) {
385 // Dependency is not satisfied.
391 // Process FvFile to install FvInfo ppi and build FvHob
393 ProcessFvFile (PeiServices
, FileHandle
, &AuthenticationStatus
);
395 } while (FileHandle
!= NULL
);
403 Go through the file to search SectionType section,
404 when meeting an encapsuled section.
407 @param PeiServices - General purpose services available to every PEIM.
408 SearchType - Filter to find only section of this type.
409 @param SectionType EDES_TODO: Add parameter description
410 @param Section - From where to search.
411 @param SectionSize - The file size to search.
412 @param OutputBuffer - Pointer to the section to search.
418 PeiFfsProcessSection (
419 IN CONST EFI_PEI_SERVICES
**PeiServices
,
420 IN EFI_SECTION_TYPE SectionType
,
421 IN EFI_COMMON_SECTION_HEADER
*Section
,
422 IN UINTN SectionSize
,
423 OUT VOID
**OutputBuffer
427 UINT32 SectionLength
;
429 EFI_PEI_GUIDED_SECTION_EXTRACTION_PPI
*GuidSectionPpi
;
430 EFI_PEI_DECOMPRESS_PPI
*DecompressPpi
;
434 UINT32 Authentication
;
435 PEI_CORE_INSTANCE
*PrivateData
;
437 PrivateData
= PEI_CORE_INSTANCE_FROM_PS_THIS (PeiServices
);
438 *OutputBuffer
= NULL
;
441 Status
= EFI_NOT_FOUND
;
444 while (ParsedLength
< SectionSize
) {
445 if (Section
->Type
== SectionType
) {
446 *OutputBuffer
= (VOID
*)(Section
+ 1);
448 } else if ((Section
->Type
== EFI_SECTION_GUID_DEFINED
) || (Section
->Type
== EFI_SECTION_COMPRESSION
)) {
450 // Check the encapsulated section is extracted into the cache data.
452 for (Index
= 0; Index
< PrivateData
->CacheSection
.AllSectionCount
; Index
++) {
453 if (Section
== PrivateData
->CacheSection
.Section
[Index
]) {
454 PpiOutput
= PrivateData
->CacheSection
.SectionData
[Index
];
455 PpiOutputSize
= PrivateData
->CacheSection
.SectionSize
[Index
];
457 // Search section directly from the cache data.
459 return PeiFfsProcessSection (
469 Status
= EFI_NOT_FOUND
;
470 if (Section
->Type
== EFI_SECTION_GUID_DEFINED
) {
471 Status
= PeiServicesLocatePpi (
472 &((EFI_GUID_DEFINED_SECTION
*)Section
)->SectionDefinitionGuid
,
475 (VOID
**) &GuidSectionPpi
477 if (!EFI_ERROR (Status
)) {
478 Status
= GuidSectionPpi
->ExtractSection (
486 } else if (Section
->Type
== EFI_SECTION_COMPRESSION
) {
487 Status
= PeiServicesLocatePpi (&gEfiPeiDecompressPpiGuid
, 0, NULL
, (VOID
**) &DecompressPpi
);
488 if (!EFI_ERROR (Status
)) {
489 Status
= DecompressPpi
->Decompress (
491 (CONST EFI_COMPRESSION_SECTION
*) Section
,
498 if (!EFI_ERROR (Status
)) {
500 // Update cache section data.
502 if (PrivateData
->CacheSection
.AllSectionCount
< CACHE_SETION_MAX_NUMBER
) {
503 PrivateData
->CacheSection
.AllSectionCount
++;
505 PrivateData
->CacheSection
.Section
[PrivateData
->CacheSection
.SectionIndex
] = Section
;
506 PrivateData
->CacheSection
.SectionData
[PrivateData
->CacheSection
.SectionIndex
] = PpiOutput
;
507 PrivateData
->CacheSection
.SectionSize
[PrivateData
->CacheSection
.SectionIndex
] = PpiOutputSize
;
508 PrivateData
->CacheSection
.SectionIndex
= (PrivateData
->CacheSection
.SectionIndex
+ 1)%CACHE_SETION_MAX_NUMBER
;
510 return PeiFfsProcessSection (
521 // Size is 24 bits wide so mask upper 8 bits.
522 // SectionLength is adjusted it is 4 byte aligned.
523 // Go to the next section
525 SectionLength
= *(UINT32
*)Section
->Size
& 0x00FFFFFF;
526 SectionLength
= GET_OCCUPIED_SIZE (SectionLength
, 4);
527 ASSERT (SectionLength
!= 0);
528 ParsedLength
+= SectionLength
;
529 Section
= (EFI_COMMON_SECTION_HEADER
*)((UINT8
*)Section
+ SectionLength
);
532 return EFI_NOT_FOUND
;
537 Given the input file pointer, search for the next matching section in the
541 @param PeiServices Pointer to the PEI Core Services Table.
542 @param SectionType Filter to find only sections of this type.
543 @param FileHandle Pointer to the current file to search.
544 @param SectionData Pointer to the Section matching SectionType in FfsFileHeader.
545 NULL if section not found
547 @retval EFI_NOT_FOUND No files matching the search criteria were found
548 @retval EFI_SUCCESS Success to find section data in given file
553 PeiFfsFindSectionData (
554 IN CONST EFI_PEI_SERVICES
**PeiServices
,
555 IN EFI_SECTION_TYPE SectionType
,
556 IN EFI_PEI_FILE_HANDLE FileHandle
,
557 IN OUT VOID
**SectionData
560 EFI_FFS_FILE_HEADER
*FfsFileHeader
;
562 EFI_COMMON_SECTION_HEADER
*Section
;
564 FfsFileHeader
= (EFI_FFS_FILE_HEADER
*)(FileHandle
);
567 // Size is 24 bits wide so mask upper 8 bits.
568 // Does not include FfsFileHeader header size
569 // FileSize is adjusted to FileOccupiedSize as it is 8 byte aligned.
571 Section
= (EFI_COMMON_SECTION_HEADER
*)(FfsFileHeader
+ 1);
572 FileSize
= *(UINT32
*)(FfsFileHeader
->Size
) & 0x00FFFFFF;
573 FileSize
-= sizeof (EFI_FFS_FILE_HEADER
);
575 return PeiFfsProcessSection (
585 Given the input file pointer, search for the next matching file in the
586 FFS volume as defined by SearchType. The search starts from FileHeader inside
587 the Firmware Volume defined by FwVolHeader.
590 @param PeiServices Pointer to the PEI Core Services Table.
591 @param SearchType Filter to find only files of this type.
592 Type EFI_FV_FILETYPE_ALL causes no filtering to be done.
593 @param VolumeHandle Pointer to the FV header of the volume to search.
594 @param FileHandle Pointer to the current file from which to begin searching.
595 This pointer will be updated upon return to reflect the file found.
596 @retval EFI_NOT_FOUND No files matching the search criteria were found
597 @retval EFI_SUCCESS Success to find next file in given volume
603 IN CONST EFI_PEI_SERVICES
**PeiServices
,
605 IN EFI_PEI_FV_HANDLE VolumeHandle
,
606 IN OUT EFI_PEI_FILE_HANDLE
*FileHandle
609 return PeiFindFileEx (VolumeHandle
, NULL
, SearchType
, FileHandle
, NULL
);
614 search the firmware volumes by index
616 @param PeiServices The PEI core services table.
617 @param Instance Instance of FV to find
618 @param VolumeHandle Pointer to found Volume.
620 @retval EFI_INVALID_PARAMETER FwVolHeader is NULL
621 @retval EFI_SUCCESS Firmware volume instance successfully found.
626 PeiFvFindNextVolume (
627 IN CONST EFI_PEI_SERVICES
**PeiServices
,
629 IN OUT EFI_PEI_FV_HANDLE
*VolumeHandle
632 PEI_CORE_INSTANCE
*Private
;
634 Private
= PEI_CORE_INSTANCE_FROM_PS_THIS (PeiServices
);
635 if (VolumeHandle
== NULL
) {
636 return EFI_INVALID_PARAMETER
;
639 if (Instance
>= Private
->AllFvCount
) {
641 return EFI_NOT_FOUND
;
644 *VolumeHandle
= Private
->AllFv
[Instance
];
651 Given the input VolumeHandle, search for the next matching name file.
654 @param FileName - File name to search.
655 @param VolumeHandle - The current FV to search.
656 @param FileHandle - Pointer to the file matching name in VolumeHandle.
657 - NULL if file not found
664 PeiFfsFindFileByName (
665 IN CONST EFI_GUID
*FileName
,
666 IN EFI_PEI_FV_HANDLE VolumeHandle
,
667 OUT EFI_PEI_FILE_HANDLE
*FileHandle
671 if ((VolumeHandle
== NULL
) || (FileName
== NULL
) || (FileHandle
== NULL
)) {
672 return EFI_INVALID_PARAMETER
;
674 Status
= PeiFindFileEx (VolumeHandle
, FileName
, 0, FileHandle
, NULL
);
675 if (Status
== EFI_NOT_FOUND
) {
683 Returns information about a specific file.
686 @param FileHandle - The handle to file.
687 @param FileInfo - Pointer to the file information.
689 @retval EFI_INVALID_PARAMETER Invalid FileHandle or FileInfo.
690 @retval EFI_SUCCESS Success to collect file info.
696 IN EFI_PEI_FILE_HANDLE FileHandle
,
697 OUT EFI_FV_FILE_INFO
*FileInfo
702 EFI_FFS_FILE_HEADER
*FileHeader
;
703 EFI_PEI_FV_HANDLE VolumeHandle
;
705 if ((FileHandle
== NULL
) || (FileInfo
== NULL
)) {
706 return EFI_INVALID_PARAMETER
;
711 // Retrieve the FirmwareVolume which the file resides in.
713 if (!PeiFileHandleToVolume(FileHandle
, &VolumeHandle
)) {
714 return EFI_INVALID_PARAMETER
;
717 if (((EFI_FIRMWARE_VOLUME_HEADER
*)VolumeHandle
)->Attributes
& EFI_FVB2_ERASE_POLARITY
) {
724 // Get FileState which is the highest bit of the State
726 FileState
= GetFileState (ErasePolarity
, (EFI_FFS_FILE_HEADER
*)FileHandle
);
729 case EFI_FILE_DATA_VALID
:
730 case EFI_FILE_MARKED_FOR_UPDATE
:
733 return EFI_INVALID_PARAMETER
;
736 FileHeader
= (EFI_FFS_FILE_HEADER
*)FileHandle
;
737 CopyMem (&FileInfo
->FileName
, &FileHeader
->Name
, sizeof(EFI_GUID
));
738 FileInfo
->FileType
= FileHeader
->Type
;
739 FileInfo
->FileAttributes
= FileHeader
->Attributes
;
740 FileInfo
->BufferSize
= ((*(UINT32
*)FileHeader
->Size
) & 0x00FFFFFF) - sizeof (EFI_FFS_FILE_HEADER
);
741 FileInfo
->Buffer
= (FileHeader
+ 1);
748 Collect information of given Fv Volume.
750 @param VolumeHandle - The handle to Fv Volume.
751 @param VolumeInfo - The pointer to volume information.
753 @retval EFI_INVALID_PARAMETER VolumeInfo is NULL
754 @retval EFI_SUCCESS Success to collect fv info.
758 PeiFfsGetVolumeInfo (
759 IN EFI_PEI_FV_HANDLE VolumeHandle
,
760 OUT EFI_FV_INFO
*VolumeInfo
763 EFI_FIRMWARE_VOLUME_HEADER FwVolHeader
;
764 EFI_FIRMWARE_VOLUME_EXT_HEADER
*FwVolExHeaderInfo
;
766 if (VolumeInfo
== NULL
) {
767 return EFI_INVALID_PARAMETER
;
771 // VolumeHandle may not align at 8 byte,
772 // but FvLength is UINT64 type, which requires FvHeader align at least 8 byte.
773 // So, Copy FvHeader into the local FvHeader structure.
775 CopyMem (&FwVolHeader
, VolumeHandle
, sizeof (EFI_FIRMWARE_VOLUME_HEADER
));
777 // Check Fv Image Signature
779 if (FwVolHeader
.Signature
!= EFI_FVH_SIGNATURE
) {
780 return EFI_INVALID_PARAMETER
;
782 VolumeInfo
->FvAttributes
= FwVolHeader
.Attributes
;
783 VolumeInfo
->FvStart
= (VOID
*) VolumeHandle
;
784 VolumeInfo
->FvSize
= FwVolHeader
.FvLength
;
785 CopyMem (&VolumeInfo
->FvFormat
, &FwVolHeader
.FileSystemGuid
, sizeof(EFI_GUID
));
787 if (FwVolHeader
.ExtHeaderOffset
!= 0) {
788 FwVolExHeaderInfo
= (EFI_FIRMWARE_VOLUME_EXT_HEADER
*)(((UINT8
*)VolumeHandle
) + FwVolHeader
.ExtHeaderOffset
);
789 CopyMem (&VolumeInfo
->FvName
, &FwVolExHeaderInfo
->FvName
, sizeof(EFI_GUID
));