]> git.proxmox.com Git - mirror_edk2.git/blobdiff - MdeModulePkg/Core/DxeIplPeim/DxeLoad.c
Enable PeiCore to dispatch the encapsulated fv images with depex expression. This...
[mirror_edk2.git] / MdeModulePkg / Core / DxeIplPeim / DxeLoad.c
index b7cadedd89c9f479adcc3095c3409d795c747e02..65d0e86d75402a09acc2295533614b92762d8984 100644 (file)
@@ -135,11 +135,11 @@ PeimInitializeDxeIpl (
   }\r
   \r
   //\r
-  // Install FvFileLoader and DxeIpl PPIs.\r
+  // Install DxeIpl and Decompress PPIs.\r
   //\r
   Status = PeiServicesInstallPpi (mPpiList);\r
-  ASSERT_EFI_ERROR(Status);  \r
-       \r
+  ASSERT_EFI_ERROR(Status);\r
+\r
   return Status;\r
 }\r
 \r
@@ -167,9 +167,7 @@ DxeLoadCore (
   UINT64                                    DxeCoreSize;\r
   EFI_PHYSICAL_ADDRESS                      DxeCoreEntryPoint;\r
   EFI_BOOT_MODE                             BootMode;\r
-  EFI_PEI_FV_HANDLE                         VolumeHandle;\r
   EFI_PEI_FILE_HANDLE                       FileHandle;\r
-  UINTN                                     Instance;\r
   EFI_PEI_READ_ONLY_VARIABLE2_PPI           *Variable;\r
   UINTN                                     DataSize;\r
   EFI_MEMORY_TYPE_INFORMATION               MemoryData [EfiMaxMemoryType + 1];\r
@@ -194,7 +192,7 @@ DxeLoadCore (
     // Now should have a HOB with the DXE core w/ the old HOB destroyed\r
     //\r
   }\r
-  \r
+\r
   Status = PeiServicesLocatePpi (\r
              &gEfiPeiReadOnlyVariable2PpiGuid,\r
              0,\r
@@ -223,16 +221,12 @@ DxeLoadCore (
       DataSize\r
       );\r
   }\r
-  //\r
-  // If any FV contains an encapsulated FV extract that FV\r
-  //\r
-  DxeIplAddEncapsulatedFirmwareVolumes ();\r
-  \r
+\r
   //\r
   // Look in all the FVs present in PEI and find the DXE Core\r
   //\r
-  Instance = 0;\r
-  Status = DxeIplFindFirmwareVolumeInstance (&Instance, EFI_FV_FILETYPE_DXE_CORE, &VolumeHandle, &FileHandle);\r
+  FileHandle = NULL;\r
+  Status = DxeIplFindDxeCore (&FileHandle);\r
   ASSERT_EFI_ERROR (Status);\r
 \r
   CopyMem(&DxeCoreFileName, &(((EFI_FFS_FILE_HEADER*)FileHandle)->Name), sizeof (EFI_GUID));\r
@@ -297,171 +291,38 @@ DxeLoadCore (
   return EFI_OUT_OF_RESOURCES;\r
 }\r
 \r
-\r
-STATIC\r
-EFI_STATUS\r
-GetFvAlignment (\r
-  IN    EFI_FIRMWARE_VOLUME_HEADER   *FvHeader,\r
-  OUT   UINT32                      *FvAlignment\r
-  )\r
-{\r
-  //\r
-  // Because FvLength in FvHeader is UINT64 type, \r
-  // so FvHeader must meed at least 8 bytes alignment.\r
-  // Get the appropriate alignment requirement.\r
-  // \r
-  if ((FvHeader->Attributes & EFI_FVB2_ALIGNMENT) < EFI_FVB2_ALIGNMENT_8) {\r
-    return EFI_UNSUPPORTED;\r
-  }\r
-  \r
-   *FvAlignment = 1 << ((FvHeader->Attributes & EFI_FVB2_ALIGNMENT) >> 16);\r
-   return EFI_SUCCESS;\r
-}\r
-\r
-/**\r
-   Search EFI_FV_FILETYPE_FIRMWARE_VOLUME_IMAGE image and expand \r
-   as memory FV \r
-    \r
-   @return EFI_OUT_OF_RESOURCES There are no memory space to exstract FV\r
-   @return EFI_SUCESS           Sucess to find the FV \r
-**/\r
-EFI_STATUS\r
-DxeIplAddEncapsulatedFirmwareVolumes (\r
-  VOID\r
-  )\r
-{\r
-  EFI_STATUS                  Status;\r
-  EFI_STATUS                  VolumeStatus;\r
-  UINTN                       Index;\r
-  EFI_FV_INFO                 VolumeInfo; \r
-  EFI_PEI_FV_HANDLE           VolumeHandle;\r
-  EFI_PEI_FILE_HANDLE         FileHandle;\r
-  UINT32                      SectionLength;\r
-  EFI_FIRMWARE_VOLUME_HEADER  *FvHeader;\r
-  EFI_FIRMWARE_VOLUME_IMAGE_SECTION *SectionHeader;\r
-  VOID                        *DstBuffer;\r
-  UINT32                       FvAlignment;\r
-\r
-  Status = EFI_NOT_FOUND;\r
-  Index  = 0;\r
-\r
-  do {\r
-    VolumeStatus = DxeIplFindFirmwareVolumeInstance (\r
-                    &Index, \r
-                    EFI_FV_FILETYPE_FIRMWARE_VOLUME_IMAGE, \r
-                    &VolumeHandle, \r
-                    &FileHandle\r
-                    );\r
-                    \r
-    if (!EFI_ERROR (VolumeStatus)) {\r
-         Status = PeiServicesFfsFindSectionData (\r
-                    EFI_SECTION_FIRMWARE_VOLUME_IMAGE, \r
-                    (EFI_FFS_FILE_HEADER *)FileHandle, \r
-                    (VOID **)&FvHeader\r
-                    );\r
-                    \r
-      if (!EFI_ERROR (Status)) {\r
-        if (FvHeader->Signature == EFI_FVH_SIGNATURE) {\r
-          //\r
-          // Because FvLength in FvHeader is UINT64 type, \r
-          // so FvHeader must meed at least 8 bytes alignment.\r
-          // If current FvImage base address doesn't meet its alignment,\r
-          // we need to reload this FvImage to another correct memory address.\r
-          //\r
-          Status = GetFvAlignment(FvHeader, &FvAlignment); \r
-          if (EFI_ERROR(Status)) {\r
-            return Status;\r
-          }\r
-          if (((UINTN) FvHeader % FvAlignment) != 0) {\r
-            SectionHeader = (EFI_FIRMWARE_VOLUME_IMAGE_SECTION*)((UINTN)FvHeader - sizeof(EFI_FIRMWARE_VOLUME_IMAGE_SECTION));\r
-            SectionLength =  *(UINT32 *)SectionHeader->Size & 0x00FFFFFF;\r
-            \r
-            DstBuffer = AllocateAlignedPages (EFI_SIZE_TO_PAGES ((UINTN) SectionLength - sizeof (EFI_COMMON_SECTION_HEADER)), FvAlignment);\r
-            if (DstBuffer == NULL) {\r
-              return EFI_OUT_OF_RESOURCES;\r
-            }\r
-            CopyMem (DstBuffer, FvHeader, (UINTN) SectionLength - sizeof (EFI_COMMON_SECTION_HEADER));\r
-            FvHeader = (EFI_FIRMWARE_VOLUME_HEADER *) DstBuffer;  \r
-          }\r
-\r
-          //\r
-          // This new Firmware Volume comes from a firmware file within a firmware volume.\r
-          // Record the original Firmware Volume Name.\r
-          //\r
-          PeiServicesFfsGetVolumeInfo (&VolumeHandle, &VolumeInfo);\r
-\r
-          PiLibInstallFvInfoPpi (\r
-            NULL,\r
-            FvHeader,\r
-            (UINT32) FvHeader->FvLength,\r
-            &(VolumeInfo.FvName),\r
-            &(((EFI_FFS_FILE_HEADER*)FileHandle)->Name)\r
-            );\r
-\r
-          //\r
-          // Inform HOB consumer phase, i.e. DXE core, the existance of this FV\r
-          //\r
-          BuildFvHob (\r
-            (EFI_PHYSICAL_ADDRESS) (UINTN) FvHeader,\r
-            FvHeader->FvLength\r
-          );\r
-            \r
-          ASSERT_EFI_ERROR (Status);\r
-\r
-          //\r
-          // Makes the encapsulated volume show up in DXE phase to skip processing of\r
-          // encapsulated file again.\r
-          //\r
-          BuildFv2Hob (\r
-            (EFI_PHYSICAL_ADDRESS)(UINTN)FvHeader,\r
-            FvHeader->FvLength, \r
-            &VolumeInfo.FvName,\r
-            &(((EFI_FFS_FILE_HEADER *)FileHandle)->Name)\r
-            );\r
-          return Status;\r
-        }\r
-      }\r
-    }\r
-  } while (!EFI_ERROR (VolumeStatus));\r
-  \r
-  return Status;\r
-}\r
-\r
 /**\r
-   Find the First Volume that contains the first FileType.\r
+   Find DxeCore driver from all First Volumes.\r
 \r
-   @param Instance      The Fv instance.\r
-   @param SeachType     The type of file to search.\r
-   @param VolumeHandle  Pointer to Fv which contains the file to search. \r
    @param FileHandle    Pointer to FFS file to search.\r
    \r
    @return EFI_SUCESS   Success to find the FFS in specificed FV\r
    @return others       Fail to find the FFS in specificed FV\r
  */\r
 EFI_STATUS\r
-DxeIplFindFirmwareVolumeInstance (\r
-  IN OUT UINTN              *Instance,\r
-  IN  EFI_FV_FILETYPE       SeachType,\r
-  OUT EFI_PEI_FV_HANDLE     *VolumeHandle,\r
+DxeIplFindDxeCore (\r
   OUT EFI_PEI_FILE_HANDLE   *FileHandle\r
   )\r
 {\r
-  EFI_STATUS  Status;\r
-  EFI_STATUS  VolumeStatus;\r
+  EFI_STATUS        Status;\r
+  EFI_STATUS        FileStatus;\r
+  UINTN             Instance;\r
+  EFI_PEI_FV_HANDLE VolumeHandle;\r
+  \r
+  Instance    = 0;\r
+  *FileHandle = NULL;\r
 \r
   do {\r
-    VolumeStatus = PeiServicesFfsFindNextVolume (*Instance, VolumeHandle);\r
-    if (!EFI_ERROR (VolumeStatus)) {\r
-      *FileHandle = NULL;\r
-      Status = PeiServicesFfsFindNextFile (SeachType, *VolumeHandle, FileHandle);\r
-      if (!EFI_ERROR (Status)) {\r
-        return Status;\r
+    Status = PeiServicesFfsFindNextVolume (Instance++, &VolumeHandle);\r
+    if (!EFI_ERROR (Status)) {\r
+      FileStatus = PeiServicesFfsFindNextFile (EFI_FV_FILETYPE_DXE_CORE, VolumeHandle, FileHandle);\r
+      if (!EFI_ERROR (FileStatus)) {\r
+        return FileStatus;\r
       }\r
     }\r
-    *Instance += 1;\r
-  } while (!EFI_ERROR (VolumeStatus));\r
+  } while (!EFI_ERROR (Status));\r
 \r
-  return VolumeStatus;\r
+  return EFI_NOT_FOUND;\r
 }\r
 \r
 /**\r
@@ -646,10 +507,16 @@ CustomGuidedSectionExtract (
     //\r
     // Allocate output buffer\r
     //\r
-    *OutputBuffer = AllocatePages (EFI_SIZE_TO_PAGES (OutputBufferSize));\r
+    *OutputBuffer = AllocatePages (EFI_SIZE_TO_PAGES (OutputBufferSize) + 1);\r
     if (*OutputBuffer == NULL) {\r
       return EFI_OUT_OF_RESOURCES;\r
     }\r
+    DEBUG ((EFI_D_INFO, "Customed Guided section Memory Size required is 0x%x and address is 0x%p\n", OutputBufferSize, *OutputBuffer));\r
+    //\r
+    // *OutputBuffer still is one section. Adjust *OutputBuffer offset, \r
+    // skip EFI section header to make section data at page alignment.\r
+    //\r
+    *OutputBuffer = (VOID *)((UINT8 *) *OutputBuffer + EFI_PAGE_SIZE - sizeof (EFI_COMMON_SECTION_HEADER));\r
   }\r
   \r
   Status = ExtractGuidedSectionDecode (\r
@@ -728,13 +595,18 @@ Decompress (
       return EFI_OUT_OF_RESOURCES;\r
     }\r
     //\r
-    // Allocate destination buffer\r
+    // Allocate destination buffer, extra one page for adjustment \r
     //\r
-    DstBuffer = AllocatePages (EFI_SIZE_TO_PAGES (DstBufferSize));\r
+    DstBuffer = AllocatePages (EFI_SIZE_TO_PAGES (DstBufferSize) + 1);\r
     if (DstBuffer == NULL) {\r
       return EFI_OUT_OF_RESOURCES;\r
     }\r
     //\r
+    // DstBuffer still is one section. Adjust DstBuffer offset, skip EFI section header\r
+    // to make section data at page alignment.\r
+    //\r
+    DstBuffer = DstBuffer + EFI_PAGE_SIZE - sizeof (EFI_COMMON_SECTION_HEADER);\r
+    //\r
     // Call decompress function\r
     //\r
     Status = UefiDecompress (\r
@@ -751,18 +623,21 @@ Decompress (
     }\r
     break;\r
 \r
-  // porting note the original branch for customized compress is removed, it should be change to use GUID compress\r
-\r
   case EFI_NOT_COMPRESSED:\r
     //\r
     // Allocate destination buffer\r
     //\r
     DstBufferSize = CompressionSection->UncompressedLength;\r
-    DstBuffer     = AllocatePages (EFI_SIZE_TO_PAGES (DstBufferSize));\r
+    DstBuffer     = AllocatePages (EFI_SIZE_TO_PAGES (DstBufferSize) + 1);\r
     if (DstBuffer == NULL) {\r
       return EFI_OUT_OF_RESOURCES;\r
     }\r
     //\r
+    // Adjust DstBuffer offset, skip EFI section header\r
+    // to make section data at page alignment.\r
+    //\r
+    DstBuffer = DstBuffer + EFI_PAGE_SIZE - sizeof (EFI_COMMON_SECTION_HEADER);\r
+    //\r
     // stream is not actually compressed, just encapsulated.  So just copy it.\r
     //\r
     CopyMem (DstBuffer, CompressionSection + 1, DstBufferSize);\r