]> git.proxmox.com Git - mirror_edk2.git/blame - UefiPayloadPkg/PayloadLoaderPeim/PayloadLoaderPeim.c
RedfishPkg: Fix various typos
[mirror_edk2.git] / UefiPayloadPkg / PayloadLoaderPeim / PayloadLoaderPeim.c
CommitLineData
fe471d4a
RN
1/** @file\r
2 ELF Load Image Support\r
3\r
4Copyright (c) 2021, Intel Corporation. All rights reserved.<BR>\r
5SPDX-License-Identifier: BSD-2-Clause-Patent\r
6\r
7**/\r
8\r
9#include <PiPei.h>\r
10#include <UniversalPayload/UniversalPayload.h>\r
11#include <UniversalPayload/ExtraData.h>\r
12\r
13#include <Ppi/LoadFile.h>\r
14\r
15#include <Library/DebugLib.h>\r
16#include <Library/HobLib.h>\r
17#include <Library/PeiServicesLib.h>\r
18#include <Library/MemoryAllocationLib.h>\r
19#include <Library/BaseMemoryLib.h>\r
20\r
21#include "ElfLib.h"\r
22\r
23/**\r
24 The wrapper function of PeiLoadImageLoadImage().\r
25\r
26 @param This - Pointer to EFI_PEI_LOAD_FILE_PPI.\r
27 @param FileHandle - Pointer to the FFS file header of the image.\r
28 @param ImageAddressArg - Pointer to PE/TE image.\r
29 @param ImageSizeArg - Size of PE/TE image.\r
30 @param EntryPoint - Pointer to entry point of specified image file for output.\r
31 @param AuthenticationState - Pointer to attestation authentication state of image.\r
32\r
33 @return Status of PeiLoadImageLoadImage().\r
34\r
35**/\r
36EFI_STATUS\r
37EFIAPI\r
38PeiLoadFileLoadPayload (\r
39 IN CONST EFI_PEI_LOAD_FILE_PPI *This,\r
40 IN EFI_PEI_FILE_HANDLE FileHandle,\r
41 OUT EFI_PHYSICAL_ADDRESS *ImageAddressArg, OPTIONAL\r
42 OUT UINT64 *ImageSizeArg, OPTIONAL\r
43 OUT EFI_PHYSICAL_ADDRESS *EntryPoint,\r
44 OUT UINT32 *AuthenticationState\r
45 )\r
46{\r
47 EFI_STATUS Status;\r
48 VOID *Elf;\r
49 UNIVERSAL_PAYLOAD_EXTRA_DATA *ExtraData;\r
50 ELF_IMAGE_CONTEXT Context;\r
51 UNIVERSAL_PAYLOAD_INFO_HEADER *PldInfo;\r
52 UINT32 Index;\r
53 UINT16 ExtraDataIndex;\r
54 CHAR8 *SectionName;\r
55 UINTN Offset;\r
56 UINTN Size;\r
57 UINT32 ExtraDataCount;\r
58 UINTN Instance;\r
9bf4aee7 59 UINTN Length;\r
fe471d4a
RN
60\r
61 //\r
62 // ELF is added to file as RAW section for EDKII bootloader.\r
63 // But RAW section might be added by build tool before the ELF RAW section when alignment is specified for ELF RAW section.\r
64 // Below loop skips the RAW section that doesn't contain valid ELF image.\r
65 //\r
66 Instance = 0;\r
67 do {\r
68 Status = PeiServicesFfsFindSectionData3 (EFI_SECTION_RAW, Instance++, FileHandle, &Elf, AuthenticationState);\r
69 if (EFI_ERROR (Status)) {\r
70 return Status;\r
71 }\r
72\r
73 ZeroMem (&Context, sizeof (Context));\r
74 Status = ParseElfImage (Elf, &Context);\r
75 } while (EFI_ERROR (Status));\r
76\r
77 DEBUG ((\r
78 DEBUG_INFO, "Payload File Size: 0x%08X, Mem Size: 0x%08x, Reload: %d\n",\r
79 Context.FileSize, Context.ImageSize, Context.ReloadRequired\r
80 ));\r
81\r
82 //\r
83 // Get UNIVERSAL_PAYLOAD_INFO_HEADER and number of additional PLD sections.\r
84 //\r
85 PldInfo = NULL;\r
86 ExtraDataCount = 0;\r
87 for (Index = 0; Index < Context.ShNum; Index++) {\r
88 Status = GetElfSectionName (&Context, Index, &SectionName);\r
89 if (EFI_ERROR(Status)) {\r
90 continue;\r
91 }\r
92 DEBUG ((DEBUG_INFO, "Payload Section[%d]: %a\n", Index, SectionName));\r
93 if (AsciiStrCmp(SectionName, UNIVERSAL_PAYLOAD_INFO_SEC_NAME) == 0) {\r
94 Status = GetElfSectionPos (&Context, Index, &Offset, &Size);\r
95 if (!EFI_ERROR(Status)) {\r
96 PldInfo = (UNIVERSAL_PAYLOAD_INFO_HEADER *)(Context.FileBase + Offset);\r
97 }\r
98 } else if (AsciiStrnCmp(SectionName, UNIVERSAL_PAYLOAD_EXTRA_SEC_NAME_PREFIX, UNIVERSAL_PAYLOAD_EXTRA_SEC_NAME_PREFIX_LENGTH) == 0) {\r
99 Status = GetElfSectionPos (&Context, Index, &Offset, &Size);\r
100 if (!EFI_ERROR (Status)) {\r
101 ExtraDataCount++;\r
102 }\r
103 }\r
104 }\r
105\r
106 //\r
107 // Report the additional PLD sections through HOB.\r
108 //\r
9bf4aee7 109 Length = sizeof (UNIVERSAL_PAYLOAD_EXTRA_DATA) + ExtraDataCount * sizeof (UNIVERSAL_PAYLOAD_EXTRA_DATA_ENTRY);\r
fe471d4a
RN
110 ExtraData = BuildGuidHob (\r
111 &gUniversalPayloadExtraDataGuid,\r
9bf4aee7 112 Length\r
fe471d4a
RN
113 );\r
114 ExtraData->Count = ExtraDataCount;\r
9bf4aee7
TD
115 ExtraData->Header.Revision = UNIVERSAL_PAYLOAD_EXTRA_DATA_REVISION;\r
116 ExtraData->Header.Length = (UINT16) Length;\r
fe471d4a
RN
117 if (ExtraDataCount != 0) {\r
118 for (ExtraDataIndex = 0, Index = 0; Index < Context.ShNum; Index++) {\r
119 Status = GetElfSectionName (&Context, Index, &SectionName);\r
120 if (EFI_ERROR(Status)) {\r
121 continue;\r
122 }\r
123 if (AsciiStrnCmp(SectionName, UNIVERSAL_PAYLOAD_EXTRA_SEC_NAME_PREFIX, UNIVERSAL_PAYLOAD_EXTRA_SEC_NAME_PREFIX_LENGTH) == 0) {\r
124 Status = GetElfSectionPos (&Context, Index, &Offset, &Size);\r
125 if (!EFI_ERROR (Status)) {\r
126 ASSERT (ExtraDataIndex < ExtraDataCount);\r
127 AsciiStrCpyS (\r
128 ExtraData->Entry[ExtraDataIndex].Identifier,\r
129 sizeof(ExtraData->Entry[ExtraDataIndex].Identifier),\r
130 SectionName + UNIVERSAL_PAYLOAD_EXTRA_SEC_NAME_PREFIX_LENGTH\r
131 );\r
132 ExtraData->Entry[ExtraDataIndex].Base = (UINTN)(Context.FileBase + Offset);\r
133 ExtraData->Entry[ExtraDataIndex].Size = Size;\r
134 ExtraDataIndex++;\r
135 }\r
136 }\r
137 }\r
138 }\r
139\r
140 if (Context.ReloadRequired || Context.PreferredImageAddress != Context.FileBase) {\r
141 Context.ImageAddress = AllocatePages (EFI_SIZE_TO_PAGES (Context.ImageSize));\r
142 } else {\r
143 Context.ImageAddress = Context.FileBase;\r
144 }\r
145\r
146 //\r
147 // Load ELF into the required base\r
148 //\r
149 Status = LoadElfImage (&Context);\r
150 if (!EFI_ERROR(Status)) {\r
151 *ImageAddressArg = (UINTN) Context.ImageAddress;\r
152 *EntryPoint = Context.EntryPoint;\r
153 *ImageSizeArg = Context.ImageSize;\r
154 }\r
155 return Status;\r
156}\r
157\r
158\r
159EFI_PEI_LOAD_FILE_PPI mPeiLoadFilePpi = {\r
160 PeiLoadFileLoadPayload\r
161};\r
162\r
163\r
164EFI_PEI_PPI_DESCRIPTOR gPpiLoadFilePpiList = {\r
165 (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),\r
166 &gEfiPeiLoadFilePpiGuid,\r
167 &mPeiLoadFilePpi\r
168};\r
169/**\r
170\r
171 Install Pei Load File PPI.\r
172\r
173 @param FileHandle Handle of the file being invoked.\r
174 @param PeiServices Describes the list of possible PEI Services.\r
175\r
176 @retval EFI_SUCESS The entry point executes successfully.\r
177 @retval Others Some error occurs during the execution of this function.\r
178\r
179**/\r
180EFI_STATUS\r
181EFIAPI\r
182InitializePayloadLoaderPeim (\r
183 IN EFI_PEI_FILE_HANDLE FileHandle,\r
184 IN CONST EFI_PEI_SERVICES **PeiServices\r
185 )\r
186{\r
187 EFI_STATUS Status;\r
188 Status = PeiServicesInstallPpi (&gPpiLoadFilePpiList);\r
189\r
190 return Status;\r
191}\r