Home | History | Annotate | Download | only in Fv2OnFvThunk
      1 /** @file
      2 Module produce FV2 on top of FV.
      3 
      4 UEFI PI specification supersedes Inte's Framework Specification.
      5 EFI_FIRMWARE_VOLUME_PROTOCOL defined in Intel Framework Pkg is replaced by
      6 EFI_FIRMWARE_VOLUME2_PROTOCOL in MdePkg.
      7 This module produces FV2 on top of FV. This module is used on platform when both of
      8 these two conditions are true:
      9 1) Framework module producing FV is present
     10 2) And the rest of modules on the platform consume FV2
     11 
     12 Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
     13 This program and the accompanying materials
     14 are licensed and made available under the terms and conditions of the BSD License
     15 which accompanies this distribution.  The full text of the license may be found at
     16 http://opensource.org/licenses/bsd-license.php
     17 
     18 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
     19 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
     20 Module Name:
     21 
     22 **/
     23 
     24 #include <PiDxe.h>
     25 #include <Protocol/FirmwareVolume2.h>
     26 #include <Protocol/FirmwareVolume.h>
     27 #include <Library/BaseLib.h>
     28 #include <Library/DebugLib.h>
     29 #include <Library/UefiBootServicesTableLib.h>
     30 #include <Library/UefiDriverEntryPoint.h>
     31 #include <Library/UefiLib.h>
     32 #include <Library/MemoryAllocationLib.h>
     33 
     34 /**
     35 
     36   Because of constraints imposed by the underlying firmware
     37   storage, an instance of the Firmware Volume Protocol may not
     38   be to able to support all possible variations of this
     39   architecture. These constraints and the current state of the
     40   firmware volume are exposed to the caller using the
     41   GetVolumeAttributes() function. GetVolumeAttributes() is
     42   callable only from TPL_NOTIFY and below. Behavior of
     43   GetVolumeAttributes() at any EFI_TPL above TPL_NOTIFY is
     44   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI
     45   2.0 specification.
     46 
     47   @param  This    Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
     48                   instance.
     49 
     50   @param  FvAttributes  Pointer to an EFI_FV_ATTRIBUTES in which
     51                         the attributes and current settings are
     52                         returned.
     53 
     54 
     55   @retval EFI_SUCCESS   The firmware volume attributes were
     56                         returned.
     57 
     58 **/
     59 EFI_STATUS
     60 EFIAPI
     61 Fv2GetVolumeAttributes (
     62   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
     63   OUT       EFI_FV_ATTRIBUTES             *FvAttributes
     64   );
     65 
     66 
     67 /**
     68   The SetVolumeAttributes() function is used to set configurable
     69   firmware volume attributes. Only EFI_FV_READ_STATUS,
     70   EFI_FV_WRITE_STATUS, and EFI_FV_LOCK_STATUS may be modified, and
     71    then only in accordance with the declared capabilities. All
     72   other bits of FvAttributes are ignored on input. On successful
     73   return, all bits of *FvAttributes are valid and it contains the
     74   completed EFI_FV_ATTRIBUTES for the volume. To modify an
     75   attribute, the corresponding status bit in the EFI_FV_ATTRIBUTES
     76   is set to the desired value on input. The EFI_FV_LOCK_STATUS bit
     77   does not affect the ability to read or write the firmware
     78   volume. Rather, once the EFI_FV_LOCK_STATUS bit is set, it
     79   prevents further modification to all the attribute bits.
     80   SetVolumeAttributes() is callable only from TPL_NOTIFY and
     81   below. Behavior of SetVolumeAttributes() at any EFI_TPL above
     82   TPL_NOTIFY is undefined. Type EFI_TPL is defined in
     83   RaiseTPL() in the UEFI 2.0 specification.
     84 
     85 
     86   @param  This  Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
     87                 instance.
     88 
     89   @param  FvAttributes  On input, FvAttributes is a pointer to
     90                         an EFI_FV_ATTRIBUTES containing the
     91                         desired firmware volume settings. On
     92                         successful return, it contains the new
     93                         settings of the firmware volume. On
     94                         unsuccessful return, FvAttributes is not
     95                         modified and the firmware volume
     96                         settings are not changed.
     97 
     98   @retval EFI_SUCCESS   The requested firmware volume attributes
     99                         were set and the resulting
    100                         EFI_FV_ATTRIBUTES is returned in
    101                         FvAttributes.
    102 
    103   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_READ_STATUS
    104                                 is set to 1 on input, but the
    105                                 device does not support enabling
    106                                 reads
    107                                 (FvAttributes:EFI_FV_READ_ENABLE
    108                                 is clear on return from
    109                                 GetVolumeAttributes()). Actual
    110                                 volume attributes are unchanged.
    111 
    112   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_READ_STATUS
    113                                 is cleared to 0 on input, but
    114                                 the device does not support
    115                                 disabling reads
    116                                 (FvAttributes:EFI_FV_READ_DISABL
    117                                 is clear on return from
    118                                 GetVolumeAttributes()). Actual
    119                                 volume attributes are unchanged.
    120 
    121   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_WRITE_STATUS
    122                                 is set to 1 on input, but the
    123                                 device does not support enabling
    124                                 writes
    125                                 (FvAttributes:EFI_FV_WRITE_ENABL
    126                                 is clear on return from
    127                                 GetVolumeAttributes()). Actual
    128                                 volume attributes are unchanged.
    129 
    130   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_WRITE_STATUS
    131                                 is cleared to 0 on input, but
    132                                 the device does not support
    133                                 disabling writes
    134                                 (FvAttributes:EFI_FV_WRITE_DISAB
    135                                 is clear on return from
    136                                 GetVolumeAttributes()). Actual
    137                                 volume attributes are unchanged.
    138 
    139   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_LOCK_STATUS
    140                                 is set on input, but the device
    141                                 does not support locking
    142                                 (FvAttributes:EFI_FV_LOCK_CAP is
    143                                 clear on return from
    144                                 GetVolumeAttributes()). Actual
    145                                 volume attributes are unchanged.
    146 
    147   @retval EFI_ACCESS_DENIED     Device is locked and does not
    148                                 allow attribute modification
    149                                 (FvAttributes:EFI_FV_LOCK_STATUS
    150                                 is set on return from
    151                                 GetVolumeAttributes()). Actual
    152                                 volume attributes are unchanged.
    153 
    154 **/
    155 EFI_STATUS
    156 EFIAPI
    157 Fv2SetVolumeAttributes (
    158   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    159   IN OUT    EFI_FV_ATTRIBUTES             *FvAttributes
    160   );
    161 
    162 
    163 /**
    164   ReadFile() is used to retrieve any file from a firmware volume
    165   during the DXE phase. The actual binary encoding of the file in
    166   the firmware volume media may be in any arbitrary format as long
    167   as it does the following: It is accessed using the Firmware
    168   Volume Protocol. The image that is returned follows the image
    169   format defined in Code Definitions: PI Firmware File Format.
    170   If the input value of Buffer==NULL, it indicates the caller is
    171   requesting only that the type, attributes, and size of the
    172   file be returned and that there is no output buffer. In this
    173   case, the following occurs:
    174   - BufferSize is returned with the size that is required to
    175     successfully complete the read.
    176   - The output parameters FoundType and *FileAttributes are
    177   returned with valid values.
    178   - The returned value of *AuthenticationStatus is undefined.
    179 
    180   If the input value of Buffer!=NULL, the output buffer is
    181   specified by a double indirection of the Buffer parameter. The
    182   input value of *Buffer is used to determine if the output
    183   buffer is caller allocated or is dynamically allocated by
    184   ReadFile(). If the input value of *Buffer!=NULL, it indicates
    185   the output buffer is caller allocated. In this case, the input
    186    value of *BufferSize indicates the size of the
    187   caller-allocated output buffer. If the output buffer is not
    188   large enough to contain the entire requested output, it is
    189   filled up to the point that the output buffer is exhausted and
    190   EFI_WARN_BUFFER_TOO_SMALL is returned, and then BufferSize is
    191    returned with the size required to successfully complete the
    192   read. All other output parameters are returned with valid
    193   values. If the input value of *Buffer==NULL, it indicates the
    194   output buffer is to be allocated by ReadFile(). In this case,
    195   ReadFile() will allocate an appropriately sized buffer from
    196   boot services pool memory, which will be returned in Buffer.
    197   The size of the new buffer is returned in BufferSize and all
    198   other output parameters are returned with valid values.
    199   ReadFile() is callable only from TPL_NOTIFY and below.
    200   Behavior of ReadFile() at any EFI_TPL above TPL_NOTIFY is
    201   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI
    202   2.0 specification.
    203 
    204   @param  This  Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
    205                 instance.
    206 
    207   @param  NameGuid  Pointer to an EFI_GUID, which is the file
    208                     name. All firmware file names are EFI_GUIDs.
    209                     A single firmware volume must not have two
    210                     valid files with the same file name
    211                     EFI_GUID.
    212 
    213   @param  Buffer  Pointer to a pointer to a buffer in which the
    214                   file contents are returned, not including the
    215                   file header.
    216   @param  BufferSize  Pointer to a caller-allocated UINTN. It
    217                       indicates the size of the memory
    218                       represented by Buffer.
    219 
    220   @param  FoundType   Pointer to a caller-allocated
    221                       EFI_FV_FILETYPE.
    222 
    223   @param  FileAttributes  Pointer to a  caller-allocated
    224                           EFI_FV_FILE_ATTRIBUTES.
    225 
    226   @param  AuthenticationStatus  Pointer to a caller-allocated
    227                                 UINT32 in which the
    228                                 authentication status is
    229                                 returned.
    230 
    231   @retval EFI_SUCCESS   The call completed successfully.
    232 
    233   @retval EFI_WARN_BUFFER_TOO_SMALL   The buffer is too small to
    234                                       contain the requested
    235                                       output. The buffer is
    236                                       filled and the output is
    237                                       truncated.
    238 
    239   @retval EFI_OUT_OF_RESOURCES  An allocation failure occurred.
    240 
    241   @retval EFI_NOT_FOUND   Name was not found in the firmware
    242                           volume.
    243 
    244   @retval EFI_DEVICE_ERROR  A hardware error occurred when
    245                             attempting to access the firmware
    246                             volume.
    247 
    248   @retval EFI_ACCESS_DENIED The firmware volume is configured to
    249                             isallow reads.
    250 
    251 **/
    252 EFI_STATUS
    253 EFIAPI
    254 Fv2ReadFile (
    255   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    256   IN CONST  EFI_GUID                      *NameGuid,
    257   IN OUT    VOID                          **Buffer,
    258   IN OUT    UINTN                         *BufferSize,
    259   OUT       EFI_FV_FILETYPE               *FoundType,
    260   OUT       EFI_FV_FILE_ATTRIBUTES        *FileAttributes,
    261   OUT       UINT32                        *AuthenticationStatus
    262   );
    263 
    264 /**
    265   ReadSection() is used to retrieve a specific section from a file
    266   within a firmware volume. The section returned is determined
    267   using a depth-first, left-to-right search algorithm through all
    268   sections found in the specified file. The output buffer is
    269   specified by a double indirection of the Buffer parameter.
    270   The input value of Buffer is used to determine
    271   if the output buffer is caller allocated or is
    272   dynamically allocated by ReadSection(). If the input value of
    273   Buffer!=NULL, it indicates that the output buffer is caller
    274   allocated. In this case, the input value of *BufferSize
    275   indicates the size of the caller-allocated output buffer. If
    276   the output buffer is not large enough to contain the entire
    277   requested output, it is filled up to the point that the output
    278   buffer is exhausted and EFI_WARN_BUFFER_TOO_SMALL is returned,
    279   and then BufferSize is returned with the size that is required
    280   to successfully complete the read. All other
    281   output parameters are returned with valid values. If the input
    282   value of *Buffer==NULL, it indicates the output buffer is to
    283   be allocated by ReadSection(). In this case, ReadSection()
    284   will allocate an appropriately sized buffer from boot services
    285   pool memory, which will be returned in *Buffer. The size of
    286   the new buffer is returned in *BufferSize and all other output
    287   parameters are returned with valid values. ReadSection() is
    288   callable only from TPL_NOTIFY and below. Behavior of
    289   ReadSection() at any EFI_TPL above TPL_NOTIFY is
    290   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI
    291   2.0 specification.
    292 
    293 
    294   @param This   Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
    295                 instance.
    296 
    297   @param NameGuid   Pointer to an EFI_GUID, which indicates the
    298                     file name from which the requested section
    299                     will be read.
    300 
    301   @param SectionType  Indicates the section type to return.
    302                       SectionType in conjunction with
    303                       SectionInstance indicates which section to
    304                       return.
    305 
    306   @param SectionInstance  Indicates which instance of sections
    307                           with a type of SectionType to return.
    308                           SectionType in conjunction with
    309                           SectionInstance indicates which
    310                           section to return. SectionInstance is
    311                           zero based.
    312 
    313   @param Buffer   Pointer to a pointer to a buffer in which the
    314                   section contents are returned, not including
    315                   the section header.
    316 
    317   @param BufferSize   Pointer to a caller-allocated UINTN. It
    318                       indicates the size of the memory
    319                       represented by Buffer.
    320 
    321   @param AuthenticationStatus Pointer to a caller-allocated
    322                               UINT32 in which the authentication
    323                               status is returned.
    324 
    325 
    326   @retval EFI_SUCCESS   The call completed successfully.
    327 
    328   @retval EFI_WARN_BUFFER_TOO_SMALL   The caller-allocated
    329                                       buffer is too small to
    330                                       contain the requested
    331                                       output. The buffer is
    332                                       filled and the output is
    333                                       truncated.
    334 
    335   @retval EFI_OUT_OF_RESOURCES  An allocation failure occurred.
    336 
    337   @retval EFI_NOT_FOUND   The requested file was not found in
    338                           the firmware volume. EFI_NOT_FOUND The
    339                           requested section was not found in the
    340                           specified file.
    341 
    342   @retval EFI_DEVICE_ERROR  A hardware error occurred when
    343                             attempting to access the firmware
    344                             volume.
    345 
    346   @retval EFI_ACCESS_DENIED The firmware volume is configured to
    347                             disallow reads. EFI_PROTOCOL_ERROR
    348                             The requested section was not found,
    349                             but the file could not be fully
    350                             parsed because a required
    351                             GUIDED_SECTION_EXTRACTION_PROTOCOL
    352                             was not found. It is possible the
    353                             requested section exists within the
    354                             file and could be successfully
    355                             extracted once the required
    356                             GUIDED_SECTION_EXTRACTION_PROTOCOL
    357                             is published.
    358 
    359 **/
    360 EFI_STATUS
    361 EFIAPI
    362 Fv2ReadSection (
    363   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    364   IN CONST  EFI_GUID                      *NameGuid,
    365   IN        EFI_SECTION_TYPE              SectionType,
    366   IN        UINTN                         SectionInstance,
    367   IN OUT    VOID                          **Buffer,
    368   IN OUT    UINTN                         *BufferSize,
    369   OUT       UINT32                        *AuthenticationStatus
    370   );
    371 
    372 /**
    373   WriteFile() is used to write one or more files to a firmware
    374   volume. Each file to be written is described by an
    375   EFI_FV_WRITE_FILE_DATA structure. The caller must ensure that
    376   any required alignment for all files listed in the FileData
    377   array is compatible with the firmware volume. Firmware volume
    378   capabilities can be determined using the GetVolumeAttributes()
    379   call. Similarly, if the WritePolicy is set to
    380   EFI_FV_RELIABLE_WRITE, the caller must check the firmware volume
    381   capabilities to ensure EFI_FV_RELIABLE_WRITE is supported by the
    382   firmware volume. EFI_FV_UNRELIABLE_WRITE must always be
    383   supported. Writing a file with a size of zero
    384   (FileData[n].BufferSize == 0) deletes the file from the firmware
    385   volume if it exists. Deleting a file must be done one at a time.
    386   Deleting a file as part of a multiple file write is not allowed.
    387   Platform Initialization Specification VOLUME 3 Shared
    388   Architectural Elements 84 August 21, 2006 Version 1.0
    389   WriteFile() is callable only from TPL_NOTIFY and below.
    390   Behavior of WriteFile() at any EFI_TPL above TPL_NOTIFY is
    391   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI 2.0
    392   specification.
    393 
    394   @param This           Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL instance.
    395 
    396   @param NumberOfFiles  Indicates the number of elements in the
    397                         array pointed to by FileData.
    398 
    399   @param WritePolicy  Indicates the level of reliability for the
    400                       write in the event of a power failure or
    401                       other system failure during the write
    402                       operation.
    403 
    404   @param FileData   Pointer to an array of
    405                     EFI_FV_WRITE_FILE_DATA. Each element of
    406                     FileData[] represents a file to be written.
    407 
    408 
    409   @retval EFI_SUCCESS The write completed successfully.
    410 
    411   @retval EFI_OUT_OF_RESOURCES  The firmware volume does not
    412                                 have enough free space to
    413                                 storefile(s).
    414 
    415   @retval EFI_DEVICE_ERROR  A hardware error occurred when
    416                             attempting to access the firmware volume.
    417 
    418   @retval EFI_WRITE_PROTECTED   The firmware volume is
    419                                 configured to disallow writes.
    420 
    421   @retval EFI_NOT_FOUND   A delete was requested, but the
    422                           requested file was not found in the
    423                           firmware volume.
    424 
    425   @retval EFI_INVALID_PARAMETER   A delete was requested with a
    426                                   multiple file write.
    427 
    428   @retval EFI_INVALID_PARAMETER   An unsupported WritePolicy was
    429                                   requested.
    430 
    431   @retval EFI_INVALID_PARAMETER   An unknown file type was
    432                                   specified.
    433 
    434   @retval EFI_INVALID_PARAMETER   A file system specific error
    435                                   has occurred.
    436 
    437 **/
    438 EFI_STATUS
    439 EFIAPI
    440 Fv2WriteFile (
    441   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    442   IN        UINT32                        NumberOfFiles,
    443   IN        EFI_FV_WRITE_POLICY           WritePolicy,
    444   IN        EFI_FV_WRITE_FILE_DATA        *FileData
    445   );
    446 
    447 /**
    448   GetNextFile() is the interface that is used to search a firmware
    449   volume for a particular file. It is called successively until
    450   the desired file is located or the function returns
    451    EFI_NOT_FOUND. To filter uninteresting files from the output,
    452   the type of file to search for may be specified in FileType. For
    453   example, if *FileType is EFI_FV_FILETYPE_DRIVER, only files of
    454   this type will be returned in the output. If *FileType is
    455   EFI_FV_FILETYPE_ALL, no filtering of file types is done. The Key
    456   parameter is used to indicate a starting point of the search. If
    457   the buffer *Key is completely initialized to zero, the search
    458   re-initialized and starts at the beginning. Subsequent calls to
    459   GetNextFile() must maintain the value of *Key returned by the
    460   immediately previous call. The actual contents of *Key are
    461   implementation specific and no semantic content is implied.
    462   GetNextFile() is callable only from TPL_NOTIFY and below.
    463   Behavior of GetNextFile() at any EFI_TPL above TPL_NOTIFY is
    464   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI 2.0
    465   specification. Status Codes Returned
    466 
    467 
    468   @param This Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
    469               instance.
    470 
    471   @param Key  Pointer to a caller-allocated buffer
    472               that contains implementation-specific data that is
    473               used to track where to begin the search for the
    474               next file. The size of the buffer must be at least
    475               This->KeySize bytes long. To re-initialize the
    476               search and begin from the beginning of the
    477               firmware volume, the entire buffer must be cleared
    478               to zero. Other than clearing the buffer to
    479               initiate a new search, the caller must not modify
    480               the data in the buffer between calls to
    481               GetNextFile().
    482 
    483   @param FileType   Pointer to a caller-allocated
    484                     EFI_FV_FILETYPE. The GetNextFile() API can
    485                     filter its search for files based on the
    486                     value of the FileType input. A *FileType
    487                     input of EFI_FV_FILETYPE_ALL causes
    488                     GetNextFile() to search for files of all
    489                     types. If a file is found, the file's type
    490                     is returned in FileType. *FileType is not
    491                     modified if no file is found.
    492 
    493   @param NameGuid   Pointer to a caller-allocated EFI_GUID. If a
    494                     matching file is found, the file's name is
    495                     returned in NameGuid. If no matching file is
    496                     found, *NameGuid is not modified.
    497 
    498   @param Attributes Pointer to a caller-allocated
    499                     EFI_FV_FILE_ATTRIBUTES. If a matching file
    500                     is found, the file's attributes are returned
    501                     in Attributes. If no matching file is found,
    502                     Attributes is not modified. Type
    503                     EFI_FV_FILE_ATTRIBUTES is defined in
    504                     ReadFile().
    505 
    506   @param Size   Pointer to a caller-allocated UINTN. If a
    507                 matching file is found, the file's size is
    508                 returned in *Size. If no matching file is found,
    509                 Size is not modified.
    510 
    511   @retval EFI_SUCCESS The output parameters are filled with data
    512                       obtained from the first matching file that
    513                       was found.
    514 
    515   @retval FI_NOT_FOUND  No files of type FileType were found.
    516 
    517 
    518   @retval EFI_DEVICE_ERROR  A hardware error occurred when
    519                             attempting to access the firmware
    520                             volume.
    521 
    522   @retval EFI_ACCESS_DENIED The firmware volume is configured to
    523                             disallow reads.
    524 
    525 
    526 **/
    527 EFI_STATUS
    528 EFIAPI
    529 Fv2GetNextFile (
    530   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    531   IN OUT    VOID                          *Key,
    532   IN OUT    EFI_FV_FILETYPE               *FileType,
    533   OUT       EFI_GUID                      *NameGuid,
    534   OUT       EFI_FV_FILE_ATTRIBUTES        *Attributes,
    535   OUT       UINTN                         *Size
    536   );
    537 
    538 /**
    539   The GetInfo() function returns information of type
    540   InformationType for the requested firmware volume. If the volume
    541   does not support the requested information type, then
    542   EFI_UNSUPPORTED is returned. If the buffer is not large enough
    543   to hold the requested structure, EFI_BUFFER_TOO_SMALL is
    544   returned and the BufferSize is set to the size of buffer that is
    545   required to make the request. The information types defined by
    546   this specification are required information types that all file
    547   systems must support.
    548 
    549   @param This A pointer to the EFI_FIRMWARE_VOLUME2_PROTOCOL
    550               instance that is the file handle the requested
    551               information is for.
    552 
    553   @param InformationType  The type identifier for the
    554                           information being requested.
    555 
    556   @param BufferSize   On input, the size of Buffer. On output,
    557                       the amount of data returned in Buffer. In
    558                       both cases, the size is measured in bytes.
    559 
    560   @param Buffer   A pointer to the data buffer to return. The
    561                   buffer's type is indicated by InformationType.
    562 
    563 
    564   @retval EFI_SUCCESS   The information was retrieved.
    565 
    566   @retval EFI_UNSUPPORTED   The InformationType is not known.
    567 
    568   @retval EFI_NO_MEDIA  The device has no medium.
    569 
    570   @retval EFI_DEVICE_ERROR  The device reported an error.
    571 
    572   @retval EFI_VOLUME_CORRUPTED  The file system structures are
    573                                 corrupted.
    574 
    575   @retval EFI_BUFFER_TOO_SMALL  The BufferSize is too small to
    576                                 read the current directory
    577                                 entry. BufferSize has been
    578                                 updated with the size needed to
    579                                 complete the request.
    580 
    581 
    582 **/
    583 EFI_STATUS
    584 EFIAPI
    585 Fv2GetInfo (
    586   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    587   IN CONST  EFI_GUID                      *InformationType,
    588   IN OUT    UINTN                         *BufferSize,
    589   OUT       VOID                          *Buffer
    590   );
    591 
    592 /**
    593 
    594   The SetInfo() function sets information of type InformationType
    595   on the requested firmware volume.
    596 
    597 
    598   @param This   A pointer to the EFI_FIRMWARE_VOLUME2_PROTOCOL
    599                 instance that is the file handle the information
    600                 is for.
    601 
    602   @param InformationType  The type identifier for the
    603                           information being set.
    604 
    605   @param BufferSize   The size, in bytes, of Buffer.
    606 
    607   @param Buffer A pointer to the data buffer to write. The
    608                 buffer's type is indicated by InformationType.
    609 
    610   @retval EFI_SUCCESS The information was set.
    611 
    612   @retval EFI_UNSUPPORTED The InformationType is not known.
    613 
    614   @retval EFI_NO_MEDIA  The device has no medium.
    615 
    616   @retval EFI_DEVICE_ERROR  The device reported an error.
    617 
    618   @retval EFI_VOLUME_CORRUPTED  The file system structures are
    619                                 corrupted.
    620 
    621 
    622   @retval EFI_WRITE_PROTECTED The media is read only.
    623 
    624   @retval EFI_VOLUME_FULL   The volume is full.
    625 
    626   @retval EFI_BAD_BUFFER_SIZE BufferSize is smaller than the
    627                               size of the type indicated by
    628                               InformationType.
    629 
    630 **/
    631 EFI_STATUS
    632 EFIAPI
    633 Fv2SetInfo (
    634   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    635   IN CONST  EFI_GUID                      *InformationType,
    636   IN        UINTN                         BufferSize,
    637   IN CONST  VOID                          *Buffer
    638   );
    639 
    640 //
    641 //
    642 //
    643 #define FIRMWARE_VOLUME2_PRIVATE_DATA_SIGNATURE  SIGNATURE_32 ('f', 'v', '2', 't')
    644 
    645 typedef struct {
    646   UINTN                          Signature;
    647   EFI_FIRMWARE_VOLUME2_PROTOCOL  FirmwareVolume2;
    648   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
    649 } FIRMWARE_VOLUME2_PRIVATE_DATA;
    650 
    651 #define FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS(a) CR (a, FIRMWARE_VOLUME2_PRIVATE_DATA, FirmwareVolume2, FIRMWARE_VOLUME2_PRIVATE_DATA_SIGNATURE)
    652 
    653 //
    654 // Firmware Volume Protocol template
    655 //
    656 EFI_EVENT  mFv2Registration;
    657 
    658 FIRMWARE_VOLUME2_PRIVATE_DATA gFirmwareVolume2PrivateDataTemplate = {
    659   FIRMWARE_VOLUME2_PRIVATE_DATA_SIGNATURE,
    660   {
    661     Fv2GetVolumeAttributes,
    662     Fv2SetVolumeAttributes,
    663     Fv2ReadFile,
    664     Fv2ReadSection,
    665     Fv2WriteFile,
    666     Fv2GetNextFile,
    667     0,
    668     NULL,
    669     Fv2GetInfo,
    670     Fv2SetInfo
    671   },
    672   NULL
    673 };
    674 
    675 //
    676 // Module globals
    677 //
    678 /**
    679   This notification function is invoked when an instance of the
    680   EFI_FIRMWARE_VOLUME_PROTOCOL is produced. It installs another instance of the
    681   EFI_FIRMWARE_VOLUME2_PROTOCOL on the same handle.
    682 
    683   @param  Event                 The event that occured
    684   @param  Context               Context of event. Not used in this nofication function.
    685 
    686 **/
    687 VOID
    688 EFIAPI
    689 Fv2NotificationEvent (
    690   IN  EFI_EVENT       Event,
    691   IN  VOID            *Context
    692   )
    693 {
    694   EFI_STATUS                     Status;
    695   UINTN                          BufferSize;
    696   EFI_HANDLE                     Handle;
    697   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
    698   EFI_FIRMWARE_VOLUME2_PROTOCOL  *FirmwareVolume2;
    699 
    700   while (TRUE) {
    701     BufferSize = sizeof (Handle);
    702     Status = gBS->LocateHandle (
    703                     ByRegisterNotify,
    704                     &gEfiFirmwareVolumeProtocolGuid,
    705                     mFv2Registration,
    706                     &BufferSize,
    707                     &Handle
    708                     );
    709     if (EFI_ERROR (Status)) {
    710       //
    711       // Exit Path of While Loop....
    712       //
    713       break;
    714     }
    715 
    716     //
    717     // Skip this handle if the Firmware Volume Protocol is already installed
    718     //
    719     Status = gBS->HandleProtocol (
    720                     Handle,
    721                     &gEfiFirmwareVolume2ProtocolGuid,
    722                     (VOID **)&FirmwareVolume2
    723                     );
    724     if (!EFI_ERROR (Status)) {
    725       continue;
    726     }
    727 
    728     //
    729     // Allocate private data structure
    730     //
    731     Private = AllocateCopyPool (sizeof (FIRMWARE_VOLUME2_PRIVATE_DATA), &gFirmwareVolume2PrivateDataTemplate);
    732     if (Private == NULL) {
    733       continue;
    734     }
    735 
    736     //
    737     // Retrieve the Firmware Volume2 Protocol
    738     //
    739     Status = gBS->HandleProtocol (
    740                     Handle,
    741                     &gEfiFirmwareVolumeProtocolGuid,
    742                     (VOID **)&Private->FirmwareVolume
    743                     );
    744     ASSERT_EFI_ERROR (Status);
    745 
    746     //
    747     // Fill in rest of private data structure
    748     //
    749     Private->FirmwareVolume2.KeySize      = Private->FirmwareVolume->KeySize;
    750     Private->FirmwareVolume2.ParentHandle = Private->FirmwareVolume->ParentHandle;
    751 
    752     //
    753     // Install Firmware Volume Protocol onto same handle
    754     //
    755     Status = gBS->InstallMultipleProtocolInterfaces (
    756                     &Handle,
    757                     &gEfiFirmwareVolume2ProtocolGuid,
    758                     &Private->FirmwareVolume2,
    759                     NULL
    760                     );
    761     ASSERT_EFI_ERROR (Status);
    762   }
    763 }
    764 
    765 
    766 /**
    767   The user Entry Point for DXE driver. The user code starts with this function
    768   as the real entry point for the image goes into a library that calls this
    769   function.
    770 
    771   @param[in] ImageHandle    The firmware allocated handle for the EFI image.
    772   @param[in] SystemTable    A pointer to the EFI System Table.
    773 
    774   @retval EFI_SUCCESS       The entry point is executed successfully.
    775   @retval other             Some error occurs when executing this entry point.
    776 
    777 **/
    778 EFI_STATUS
    779 EFIAPI
    780 InitializeFirmwareVolume (
    781   IN EFI_HANDLE        ImageHandle,
    782   IN EFI_SYSTEM_TABLE  *SystemTable
    783   )
    784 {
    785   EfiCreateProtocolNotifyEvent (
    786     &gEfiFirmwareVolumeProtocolGuid,
    787     TPL_CALLBACK,
    788     Fv2NotificationEvent,
    789     NULL,
    790     &mFv2Registration
    791     );
    792   return EFI_SUCCESS;
    793 }
    794 
    795 /**
    796   Convert FV attributes defined in Framework Specification
    797   to FV attributes defined in PI specification.
    798 
    799   @param FvAttributes          The FV attributes defined in Framework Specification.
    800 
    801   @retval                      The FV attributes defined in PI Specification.
    802 **/
    803 EFI_FV_ATTRIBUTES
    804 FvAttributesToFv2Attributes (
    805   EFI_FV_ATTRIBUTES FvAttributes
    806   )
    807 {
    808   INTN                           Alignment;
    809 
    810   Alignment = LowBitSet64 (RShiftU64 (FvAttributes, 16) & 0xffff);
    811   if (Alignment != -1) {
    812     Alignment = Alignment << 16;
    813   } else {
    814     Alignment = 0;
    815   }
    816   FvAttributes = (FvAttributes & 0x1ff) | Alignment;
    817 
    818   return FvAttributes;
    819 }
    820 
    821 /**
    822 
    823   Because of constraints imposed by the underlying firmware
    824   storage, an instance of the Firmware Volume Protocol may not
    825   be to able to support all possible variations of this
    826   architecture. These constraints and the current state of the
    827   firmware volume are exposed to the caller using the
    828   GetVolumeAttributes() function. GetVolumeAttributes() is
    829   callable only from TPL_NOTIFY and below. Behavior of
    830   GetVolumeAttributes() at any EFI_TPL above TPL_NOTIFY is
    831   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI
    832   2.0 specification.
    833 
    834   @param  This    Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
    835                   instance.
    836 
    837   @param  FvAttributes  Pointer to an EFI_FV_ATTRIBUTES in which
    838                         the attributes and current settings are
    839                         returned.
    840 
    841 
    842   @retval EFI_SUCCESS   The firmware volume attributes were
    843                         returned.
    844 
    845 **/
    846 EFI_STATUS
    847 EFIAPI
    848 Fv2GetVolumeAttributes (
    849   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    850   OUT       EFI_FV_ATTRIBUTES             *FvAttributes
    851   )
    852 {
    853   EFI_STATUS                     Status;
    854   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
    855   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
    856 
    857   Private = FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS (This);
    858   FirmwareVolume = Private->FirmwareVolume;
    859   Status = FirmwareVolume->GetVolumeAttributes (
    860                              FirmwareVolume,
    861                              (FRAMEWORK_EFI_FV_ATTRIBUTES *)FvAttributes
    862                              );
    863   if (!EFI_ERROR (Status)) {
    864     *FvAttributes = FvAttributesToFv2Attributes (*FvAttributes);
    865   }
    866   return Status;
    867 }
    868 
    869 /**
    870   The SetVolumeAttributes() function is used to set configurable
    871   firmware volume attributes. Only EFI_FV_READ_STATUS,
    872   EFI_FV_WRITE_STATUS, and EFI_FV_LOCK_STATUS may be modified, and
    873    then only in accordance with the declared capabilities. All
    874   other bits of FvAttributes are ignored on input. On successful
    875   return, all bits of *FvAttributes are valid and it contains the
    876   completed EFI_FV_ATTRIBUTES for the volume. To modify an
    877   attribute, the corresponding status bit in the EFI_FV_ATTRIBUTES
    878   is set to the desired value on input. The EFI_FV_LOCK_STATUS bit
    879   does not affect the ability to read or write the firmware
    880   volume. Rather, once the EFI_FV_LOCK_STATUS bit is set, it
    881   prevents further modification to all the attribute bits.
    882   SetVolumeAttributes() is callable only from TPL_NOTIFY and
    883   below. Behavior of SetVolumeAttributes() at any EFI_TPL above
    884   TPL_NOTIFY is undefined. Type EFI_TPL is defined in
    885   RaiseTPL() in the UEFI 2.0 specification.
    886 
    887 
    888   @param  This  Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
    889                 instance.
    890 
    891   @param  FvAttributes  On input, FvAttributes is a pointer to
    892                         an EFI_FV_ATTRIBUTES containing the
    893                         desired firmware volume settings. On
    894                         successful return, it contains the new
    895                         settings of the firmware volume. On
    896                         unsuccessful return, FvAttributes is not
    897                         modified and the firmware volume
    898                         settings are not changed.
    899 
    900   @retval EFI_SUCCESS   The requested firmware volume attributes
    901                         were set and the resulting
    902                         EFI_FV_ATTRIBUTES is returned in
    903                         FvAttributes.
    904 
    905   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_READ_STATUS
    906                                 is set to 1 on input, but the
    907                                 device does not support enabling
    908                                 reads
    909                                 (FvAttributes:EFI_FV_READ_ENABLE
    910                                 is clear on return from
    911                                 GetVolumeAttributes()). Actual
    912                                 volume attributes are unchanged.
    913 
    914   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_READ_STATUS
    915                                 is cleared to 0 on input, but
    916                                 the device does not support
    917                                 disabling reads
    918                                 (FvAttributes:EFI_FV_READ_DISABL
    919                                 is clear on return from
    920                                 GetVolumeAttributes()). Actual
    921                                 volume attributes are unchanged.
    922 
    923   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_WRITE_STATUS
    924                                 is set to 1 on input, but the
    925                                 device does not support enabling
    926                                 writes
    927                                 (FvAttributes:EFI_FV_WRITE_ENABL
    928                                 is clear on return from
    929                                 GetVolumeAttributes()). Actual
    930                                 volume attributes are unchanged.
    931 
    932   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_WRITE_STATUS
    933                                 is cleared to 0 on input, but
    934                                 the device does not support
    935                                 disabling writes
    936                                 (FvAttributes:EFI_FV_WRITE_DISAB
    937                                 is clear on return from
    938                                 GetVolumeAttributes()). Actual
    939                                 volume attributes are unchanged.
    940 
    941   @retval EFI_INVALID_PARAMETER FvAttributes:EFI_FV_LOCK_STATUS
    942                                 is set on input, but the device
    943                                 does not support locking
    944                                 (FvAttributes:EFI_FV_LOCK_CAP is
    945                                 clear on return from
    946                                 GetVolumeAttributes()). Actual
    947                                 volume attributes are unchanged.
    948 
    949   @retval EFI_ACCESS_DENIED     Device is locked and does not
    950                                 allow attribute modification
    951                                 (FvAttributes:EFI_FV_LOCK_STATUS
    952                                 is set on return from
    953                                 GetVolumeAttributes()). Actual
    954                                 volume attributes are unchanged.
    955 
    956 **/
    957 EFI_STATUS
    958 EFIAPI
    959 Fv2SetVolumeAttributes (
    960   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
    961   IN OUT    EFI_FV_ATTRIBUTES             *FvAttributes
    962   )
    963 {
    964   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
    965   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
    966   FRAMEWORK_EFI_FV_ATTRIBUTES    FrameworkFvAttributes;
    967   EFI_STATUS                     Status;
    968   UINTN                          Shift;
    969 
    970   if ((*FvAttributes & (EFI_FV2_READ_LOCK_STATUS | EFI_FV2_WRITE_LOCK_STATUS)) != 0) {
    971     //
    972     // Framework FV protocol does not support EFI_FV2_READ_LOCK_* | EFI_FV2_WRITE_LOCK_*
    973     //
    974     return EFI_INVALID_PARAMETER;
    975   }
    976 
    977   *FvAttributes = *FvAttributes & (EFI_FV2_READ_STATUS | EFI_FV2_WRITE_STATUS | EFI_FV2_LOCK_STATUS);
    978 
    979   Private = FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS (This);
    980   FirmwareVolume = Private->FirmwareVolume;
    981 
    982   FrameworkFvAttributes = (*FvAttributes & 0x1ff);
    983   Shift = (UINTN) RShiftU64(*FvAttributes & EFI_FV2_ALIGNMENT, 16);
    984   FrameworkFvAttributes = FrameworkFvAttributes | LShiftU64 (EFI_FV_ALIGNMENT_2, Shift);
    985 
    986   Status =  FirmwareVolume->SetVolumeAttributes (
    987                            FirmwareVolume,
    988                            &FrameworkFvAttributes
    989                            );
    990 
    991   if (!EFI_ERROR (Status)) {
    992     *FvAttributes = FvAttributesToFv2Attributes (FrameworkFvAttributes);
    993   }
    994 
    995   return Status;
    996 }
    997 
    998 /**
    999   ReadFile() is used to retrieve any file from a firmware volume
   1000   during the DXE phase. The actual binary encoding of the file in
   1001   the firmware volume media may be in any arbitrary format as long
   1002   as it does the following: It is accessed using the Firmware
   1003   Volume Protocol. The image that is returned follows the image
   1004   format defined in Code Definitions: PI Firmware File Format.
   1005   If the input value of Buffer==NULL, it indicates the caller is
   1006   requesting only that the type, attributes, and size of the
   1007   file be returned and that there is no output buffer. In this
   1008   case, the following occurs:
   1009   - BufferSize is returned with the size that is required to
   1010     successfully complete the read.
   1011   - The output parameters FoundType and *FileAttributes are
   1012   returned with valid values.
   1013   - The returned value of *AuthenticationStatus is undefined.
   1014 
   1015   If the input value of Buffer!=NULL, the output buffer is
   1016   specified by a double indirection of the Buffer parameter. The
   1017   input value of *Buffer is used to determine if the output
   1018   buffer is caller allocated or is dynamically allocated by
   1019   ReadFile(). If the input value of *Buffer!=NULL, it indicates
   1020   the output buffer is caller allocated. In this case, the input
   1021    value of *BufferSize indicates the size of the
   1022   caller-allocated output buffer. If the output buffer is not
   1023   large enough to contain the entire requested output, it is
   1024   filled up to the point that the output buffer is exhausted and
   1025   EFI_WARN_BUFFER_TOO_SMALL is returned, and then BufferSize is
   1026    returned with the size required to successfully complete the
   1027   read. All other output parameters are returned with valid
   1028   values. If the input value of *Buffer==NULL, it indicates the
   1029   output buffer is to be allocated by ReadFile(). In this case,
   1030   ReadFile() will allocate an appropriately sized buffer from
   1031   boot services pool memory, which will be returned in Buffer.
   1032   The size of the new buffer is returned in BufferSize and all
   1033   other output parameters are returned with valid values.
   1034   ReadFile() is callable only from TPL_NOTIFY and below.
   1035   Behavior of ReadFile() at any EFI_TPL above TPL_NOTIFY is
   1036   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI
   1037   2.0 specification.
   1038 
   1039   @param  This  Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
   1040                 instance.
   1041 
   1042   @param  NameGuid  Pointer to an EFI_GUID, which is the file
   1043                     name. All firmware file names are EFI_GUIDs.
   1044                     A single firmware volume must not have two
   1045                     valid files with the same file name
   1046                     EFI_GUID.
   1047 
   1048   @param  Buffer  Pointer to a pointer to a buffer in which the
   1049                   file contents are returned, not including the
   1050                   file header.
   1051   @param  BufferSize  Pointer to a caller-allocated UINTN. It
   1052                       indicates the size of the memory
   1053                       represented by Buffer.
   1054 
   1055   @param  FoundType   Pointer to a caller-allocated
   1056                       EFI_FV_FILETYPE.
   1057 
   1058   @param  FileAttributes  Pointer to a  caller-allocated
   1059                           EFI_FV_FILE_ATTRIBUTES.
   1060 
   1061   @param  AuthenticationStatus  Pointer to a caller-allocated
   1062                                 UINT32 in which the
   1063                                 authentication status is
   1064                                 returned.
   1065 
   1066   @retval EFI_SUCCESS   The call completed successfully.
   1067 
   1068   @retval EFI_WARN_BUFFER_TOO_SMALL   The buffer is too small to
   1069                                       contain the requested
   1070                                       output. The buffer is
   1071                                       filled and the output is
   1072                                       truncated.
   1073 
   1074   @retval EFI_OUT_OF_RESOURCES  An allocation failure occurred.
   1075 
   1076   @retval EFI_NOT_FOUND   Name was not found in the firmware
   1077                           volume.
   1078 
   1079   @retval EFI_DEVICE_ERROR  A hardware error occurred when
   1080                             attempting to access the firmware
   1081                             volume.
   1082 
   1083   @retval EFI_ACCESS_DENIED The firmware volume is configured to
   1084                             isallow reads.
   1085 
   1086 **/
   1087 EFI_STATUS
   1088 EFIAPI
   1089 Fv2ReadFile (
   1090   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
   1091   IN CONST  EFI_GUID                      *NameGuid,
   1092   IN OUT    VOID                          **Buffer,
   1093   IN OUT    UINTN                         *BufferSize,
   1094   OUT       EFI_FV_FILETYPE               *FoundType,
   1095   OUT       EFI_FV_FILE_ATTRIBUTES        *FileAttributes,
   1096   OUT       UINT32                        *AuthenticationStatus
   1097   )
   1098 {
   1099   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
   1100   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
   1101 
   1102   Private = FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS (This);
   1103   FirmwareVolume = Private->FirmwareVolume;
   1104 
   1105   return FirmwareVolume->ReadFile (
   1106                            FirmwareVolume,
   1107                            (EFI_GUID *)NameGuid,
   1108                            Buffer,
   1109                            BufferSize,
   1110                            FoundType,
   1111                            FileAttributes,
   1112                            AuthenticationStatus
   1113                            );
   1114 }
   1115 
   1116 /**
   1117   ReadSection() is used to retrieve a specific section from a file
   1118   within a firmware volume. The section returned is determined
   1119   using a depth-first, left-to-right search algorithm through all
   1120   sections found in the specified file.The output buffer is specified
   1121   by a double indirection of the Buffer parameter. The input value of Buffer
   1122   is used to determine if the output buffer is caller allocated or is
   1123   dynamically allocated by ReadSection(). If the input value of
   1124   Buffer!=NULL, it indicates that the output buffer is caller
   1125   allocated. In this case, the input value of *BufferSize
   1126   indicates the size of the caller-allocated output buffer. If
   1127   the output buffer is not large enough to contain the entire
   1128   requested output, it is filled up to the point that the output
   1129   buffer is exhausted and EFI_WARN_BUFFER_TOO_SMALL is returned,
   1130   and then BufferSize is returned with the size that is required
   1131   to successfully complete the read. All other
   1132   output parameters are returned with valid values. If the input
   1133   value of *Buffer==NULL, it indicates the output buffer is to
   1134   be allocated by ReadSection(). In this case, ReadSection()
   1135   will allocate an appropriately sized buffer from boot services
   1136   pool memory, which will be returned in *Buffer. The size of
   1137   the new buffer is returned in *BufferSize and all other output
   1138   parameters are returned with valid values. ReadSection() is
   1139   callable only from TPL_NOTIFY and below. Behavior of
   1140   ReadSection() at any EFI_TPL above TPL_NOTIFY is
   1141   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI
   1142   2.0 specification.
   1143 
   1144 
   1145   @param This   Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
   1146                 instance.
   1147 
   1148   @param NameGuid   Pointer to an EFI_GUID, which indicates the
   1149                     file name from which the requested section
   1150                     will be read.
   1151 
   1152   @param SectionType  Indicates the section type to return.
   1153                       SectionType in conjunction with
   1154                       SectionInstance indicates which section to
   1155                       return.
   1156 
   1157   @param SectionInstance  Indicates which instance of sections
   1158                           with a type of SectionType to return.
   1159                           SectionType in conjunction with
   1160                           SectionInstance indicates which
   1161                           section to return. SectionInstance is
   1162                           zero based.
   1163 
   1164   @param Buffer   Pointer to a pointer to a buffer in which the
   1165                   section contents are returned, not including
   1166                   the section header.
   1167 
   1168   @param BufferSize   Pointer to a caller-allocated UINTN. It
   1169                       indicates the size of the memory
   1170                       represented by Buffer.
   1171 
   1172   @param AuthenticationStatus Pointer to a caller-allocated
   1173                               UINT32 in which the authentication
   1174                               status is returned.
   1175 
   1176 
   1177   @retval EFI_SUCCESS   The call completed successfully.
   1178 
   1179   @retval EFI_WARN_BUFFER_TOO_SMALL   The caller-allocated
   1180                                       buffer is too small to
   1181                                       contain the requested
   1182                                       output. The buffer is
   1183                                       filled and the output is
   1184                                       truncated.
   1185 
   1186   @retval EFI_OUT_OF_RESOURCES  An allocation failure occurred.
   1187 
   1188   @retval EFI_NOT_FOUND   The requested file was not found in
   1189                           the firmware volume. EFI_NOT_FOUND The
   1190                           requested section was not found in the
   1191                           specified file.
   1192 
   1193   @retval EFI_DEVICE_ERROR  A hardware error occurred when
   1194                             attempting to access the firmware
   1195                             volume.
   1196 
   1197   @retval EFI_ACCESS_DENIED The firmware volume is configured to
   1198                             disallow reads. EFI_PROTOCOL_ERROR
   1199                             The requested section was not found,
   1200                             but the file could not be fully
   1201                             parsed because a required
   1202                             GUIDED_SECTION_EXTRACTION_PROTOCOL
   1203                             was not found. It is possible the
   1204                             requested section exists within the
   1205                             file and could be successfully
   1206                             extracted once the required
   1207                             GUIDED_SECTION_EXTRACTION_PROTOCOL
   1208                             is published.
   1209 
   1210 **/
   1211 EFI_STATUS
   1212 EFIAPI
   1213 Fv2ReadSection (
   1214   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
   1215   IN CONST  EFI_GUID                      *NameGuid,
   1216   IN        EFI_SECTION_TYPE              SectionType,
   1217   IN        UINTN                         SectionInstance,
   1218   IN OUT    VOID                          **Buffer,
   1219   IN OUT    UINTN                         *BufferSize,
   1220   OUT       UINT32                        *AuthenticationStatus
   1221   )
   1222 {
   1223   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
   1224   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
   1225 
   1226   Private = FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS (This);
   1227   FirmwareVolume = Private->FirmwareVolume;
   1228 
   1229   return FirmwareVolume->ReadSection (
   1230                            FirmwareVolume,
   1231                            (EFI_GUID *)NameGuid,
   1232                            SectionType,
   1233                            SectionInstance,
   1234                            Buffer,
   1235                            BufferSize,
   1236                            AuthenticationStatus
   1237                            );
   1238 }
   1239 
   1240 /**
   1241   WriteFile() is used to write one or more files to a firmware
   1242   volume. Each file to be written is described by an
   1243   EFI_FV_WRITE_FILE_DATA structure. The caller must ensure that
   1244   any required alignment for all files listed in the FileData
   1245   array is compatible with the firmware volume. Firmware volume
   1246   capabilities can be determined using the GetVolumeAttributes()
   1247   call. Similarly, if the WritePolicy is set to
   1248   EFI_FV_RELIABLE_WRITE, the caller must check the firmware volume
   1249   capabilities to ensure EFI_FV_RELIABLE_WRITE is supported by the
   1250   firmware volume. EFI_FV_UNRELIABLE_WRITE must always be
   1251   supported. Writing a file with a size of zero
   1252   (FileData[n].BufferSize == 0) deletes the file from the firmware
   1253   volume if it exists. Deleting a file must be done one at a time.
   1254   Deleting a file as part of a multiple file write is not allowed.
   1255   Platform Initialization Specification VOLUME 3 Shared
   1256   Architectural Elements 84 August 21, 2006 Version 1.0
   1257   WriteFile() is callable only from TPL_NOTIFY and below.
   1258   Behavior of WriteFile() at any EFI_TPL above TPL_NOTIFY is
   1259   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI 2.0
   1260   specification.
   1261 
   1262   @param This           Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL instance.
   1263 
   1264   @param NumberOfFiles  Indicates the number of
   1265                         elements in the array pointed to by FileData.
   1266 
   1267 
   1268   @param WritePolicy  Indicates the level of reliability for the
   1269                       write in the event of a power failure or
   1270                       other system failure during the write
   1271                       operation.
   1272 
   1273   @param FileData   Pointer to an array of
   1274                     EFI_FV_WRITE_FILE_DATA. Each element of
   1275                     FileData[] represents a file to be written.
   1276 
   1277 
   1278   @retval EFI_SUCCESS The write completed successfully.
   1279 
   1280   @retval EFI_OUT_OF_RESOURCES  The firmware volume does not
   1281                                 have enough free space to
   1282                                 storefile(s).
   1283 
   1284   @retval EFI_DEVICE_ERROR  A hardware error occurred when
   1285                             attempting to access the firmware volume.
   1286 
   1287   @retval EFI_WRITE_PROTECTED   The firmware volume is
   1288                                 configured to disallow writes.
   1289 
   1290   @retval EFI_NOT_FOUND   A delete was requested, but the
   1291                           requested file was not found in the
   1292                           firmware volume.
   1293 
   1294   @retval EFI_INVALID_PARAMETER   A delete was requested with a
   1295                                   multiple file write.
   1296 
   1297   @retval EFI_INVALID_PARAMETER   An unsupported WritePolicy was
   1298                                   requested.
   1299 
   1300   @retval EFI_INVALID_PARAMETER   An unknown file type was
   1301                                   specified.
   1302 
   1303   @retval EFI_INVALID_PARAMETER   A file system specific error
   1304                                   has occurred.
   1305 
   1306 **/
   1307 EFI_STATUS
   1308 EFIAPI
   1309 Fv2WriteFile (
   1310   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
   1311   IN        UINT32                        NumberOfFiles,
   1312   IN        EFI_FV_WRITE_POLICY           WritePolicy,
   1313   IN        EFI_FV_WRITE_FILE_DATA        *FileData
   1314   )
   1315 {
   1316   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
   1317   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
   1318 
   1319   Private = FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS (This);
   1320   FirmwareVolume = Private->FirmwareVolume;
   1321 
   1322   return FirmwareVolume->WriteFile (
   1323                            FirmwareVolume,
   1324                            NumberOfFiles,
   1325                            WritePolicy,
   1326                            (FRAMEWORK_EFI_FV_WRITE_FILE_DATA *)FileData
   1327                            );
   1328 }
   1329 
   1330 /**
   1331   GetNextFile() is the interface that is used to search a firmware
   1332   volume for a particular file. It is called successively until
   1333   the desired file is located or the function returns
   1334    EFI_NOT_FOUND. To filter uninteresting files from the output,
   1335   the type of file to search for may be specified in FileType. For
   1336   example, if *FileType is EFI_FV_FILETYPE_DRIVER, only files of
   1337   this type will be returned in the output. If *FileType is
   1338   EFI_FV_FILETYPE_ALL, no filtering of file types is done. The Key
   1339   parameter is used to indicate a starting point of the search. If
   1340   the buffer *Key is completely initialized to zero, the search
   1341   re-initialized and starts at the beginning. Subsequent calls to
   1342   GetNextFile() must maintain the value of *Key returned by the
   1343   immediately previous call. The actual contents of *Key are
   1344   implementation specific and no semantic content is implied.
   1345   GetNextFile() is callable only from TPL_NOTIFY and below.
   1346   Behavior of GetNextFile() at any EFI_TPL above TPL_NOTIFY is
   1347   undefined. Type EFI_TPL is defined in RaiseTPL() in the UEFI 2.0
   1348   specification. Status Codes Returned
   1349 
   1350 
   1351   @param This Indicates the EFI_FIRMWARE_VOLUME2_PROTOCOL
   1352               instance.
   1353 
   1354   @param Key  Pointer to a caller-allocated buffer
   1355               that contains implementation-specific data that is
   1356               used to track where to begin the search for the
   1357               next file. The size of the buffer must be at least
   1358               This->KeySize bytes long. To re-initialize the
   1359               search and begin from the beginning of the
   1360               firmware volume, the entire buffer must be cleared
   1361               to zero. Other than clearing the buffer to
   1362               initiate a new search, the caller must not modify
   1363               the data in the buffer between calls to
   1364               GetNextFile().
   1365 
   1366   @param FileType   Pointer to a caller-allocated
   1367                     EFI_FV_FILETYPE. The GetNextFile() API can
   1368                     filter its search for files based on the
   1369                     value of the FileType input. A *FileType
   1370                     input of EFI_FV_FILETYPE_ALL causes
   1371                     GetNextFile() to search for files of all
   1372                     types. If a file is found, the file's type
   1373                     is returned in FileType. *FileType is not
   1374                     modified if no file is found.
   1375 
   1376   @param NameGuid   Pointer to a caller-allocated EFI_GUID. If a
   1377                     matching file is found, the file's name is
   1378                     returned in NameGuid. If no matching file is
   1379                     found, *NameGuid is not modified.
   1380 
   1381   @param Attributes Pointer to a caller-allocated
   1382                     EFI_FV_FILE_ATTRIBUTES. If a matching file
   1383                     is found, the file's attributes are returned
   1384                     in Attributes. If no matching file is found,
   1385                     Attributes is not modified. Type
   1386                     EFI_FV_FILE_ATTRIBUTES is defined in
   1387                     ReadFile().
   1388 
   1389   @param Size   Pointer to a caller-allocated UINTN. If a
   1390                 matching file is found, the file's size is
   1391                 returned in *Size. If no matching file is found,
   1392                 Size is not modified.
   1393 
   1394   @retval EFI_SUCCESS The output parameters are filled with data
   1395                       obtained from the first matching file that
   1396                       was found.
   1397 
   1398   @retval FI_NOT_FOUND  No files of type FileType were found.
   1399 
   1400 
   1401   @retval EFI_DEVICE_ERROR  A hardware error occurred when
   1402                             attempting to access the firmware
   1403                             volume.
   1404 
   1405   @retval EFI_ACCESS_DENIED The firmware volume is configured to
   1406                             disallow reads.
   1407 
   1408 
   1409 **/
   1410 EFI_STATUS
   1411 EFIAPI
   1412 Fv2GetNextFile (
   1413   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
   1414   IN OUT    VOID                          *Key,
   1415   IN OUT    EFI_FV_FILETYPE               *FileType,
   1416   OUT       EFI_GUID                      *NameGuid,
   1417   OUT       EFI_FV_FILE_ATTRIBUTES        *Attributes,
   1418   OUT       UINTN                         *Size
   1419   )
   1420 {
   1421   FIRMWARE_VOLUME2_PRIVATE_DATA  *Private;
   1422   EFI_FIRMWARE_VOLUME_PROTOCOL   *FirmwareVolume;
   1423 
   1424   Private = FIRMWARE_VOLUME2_PRIVATE_DATA_FROM_THIS (This);
   1425   FirmwareVolume = Private->FirmwareVolume;
   1426 
   1427   return FirmwareVolume->GetNextFile (
   1428                            FirmwareVolume,
   1429                            Key,
   1430                            FileType,
   1431                            NameGuid,
   1432                            Attributes,
   1433                            Size
   1434                            );
   1435 }
   1436 
   1437 /**
   1438   The GetInfo() function returns information of type
   1439   InformationType for the requested firmware volume. If the volume
   1440   does not support the requested information type, then
   1441   EFI_UNSUPPORTED is returned. If the buffer is not large enough
   1442   to hold the requested structure, EFI_BUFFER_TOO_SMALL is
   1443   returned and the BufferSize is set to the size of buffer that is
   1444   required to make the request. The information types defined by
   1445   this specification are required information types that all file
   1446   systems must support.
   1447 
   1448   @param This A pointer to the EFI_FIRMWARE_VOLUME2_PROTOCOL
   1449               instance that is the file handle the requested
   1450               information is for.
   1451 
   1452   @param InformationType  The type identifier for the
   1453                           information being requested.
   1454 
   1455   @param BufferSize   On input, the size of Buffer. On output,
   1456                       the amount of data returned in Buffer. In
   1457                       both cases, the size is measured in bytes.
   1458 
   1459   @param Buffer   A pointer to the data buffer to return. The
   1460                   buffer's type is indicated by InformationType.
   1461 
   1462 
   1463   @retval EFI_SUCCESS   The information was retrieved.
   1464 
   1465   @retval EFI_UNSUPPORTED   The InformationType is not known.
   1466 
   1467   @retval EFI_NO_MEDIA  The device has no medium.
   1468 
   1469   @retval EFI_DEVICE_ERROR  The device reported an error.
   1470 
   1471   @retval EFI_VOLUME_CORRUPTED  The file system structures are
   1472                                 corrupted.
   1473 
   1474   @retval EFI_BUFFER_TOO_SMALL  The BufferSize is too small to
   1475                                 read the current directory
   1476                                 entry. BufferSize has been
   1477                                 updated with the size needed to
   1478                                 complete the request.
   1479 
   1480 
   1481 **/
   1482 EFI_STATUS
   1483 EFIAPI
   1484 Fv2GetInfo (
   1485   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
   1486   IN CONST  EFI_GUID                      *InformationType,
   1487   IN OUT    UINTN                         *BufferSize,
   1488   OUT       VOID                          *Buffer
   1489   )
   1490 {
   1491   return EFI_UNSUPPORTED;
   1492 }
   1493 
   1494 /**
   1495 
   1496   The SetInfo() function sets information of type InformationType
   1497   on the requested firmware volume.
   1498 
   1499 
   1500   @param This   A pointer to the EFI_FIRMWARE_VOLUME2_PROTOCOL
   1501                 instance that is the file handle the information
   1502                 is for.
   1503 
   1504   @param InformationType  The type identifier for the
   1505                           information being set.
   1506 
   1507   @param BufferSize   The size, in bytes, of Buffer.
   1508 
   1509   @param Buffer A pointer to the data buffer to write. The
   1510                 buffer's type is indicated by InformationType.
   1511 
   1512   @retval EFI_SUCCESS The information was set.
   1513 
   1514   @retval EFI_UNSUPPORTED The InformationType is not known.
   1515 
   1516   @retval EFI_NO_MEDIA  The device has no medium.
   1517 
   1518   @retval EFI_DEVICE_ERROR  The device reported an error.
   1519 
   1520   @retval EFI_VOLUME_CORRUPTED  The file system structures are
   1521                                 corrupted.
   1522 
   1523 
   1524   @retval EFI_WRITE_PROTECTED The media is read only.
   1525 
   1526   @retval EFI_VOLUME_FULL   The volume is full.
   1527 
   1528   @retval EFI_BAD_BUFFER_SIZE BufferSize is smaller than the
   1529                               size of the type indicated by
   1530                               InformationType.
   1531 
   1532 **/
   1533 EFI_STATUS
   1534 EFIAPI
   1535 Fv2SetInfo (
   1536   IN CONST  EFI_FIRMWARE_VOLUME2_PROTOCOL *This,
   1537   IN CONST  EFI_GUID                      *InformationType,
   1538   IN        UINTN                         BufferSize,
   1539   IN CONST  VOID                          *Buffer
   1540   )
   1541 {
   1542   return EFI_UNSUPPORTED;
   1543 }
   1544