]> git.proxmox.com Git - mirror_edk2.git/blame - IntelFsp2WrapperPkg/FspsWrapperPeim/FspsWrapperPeim.c
IntelFsp2WrapperPkg: Add error handling for possible NULL ptr dereference
[mirror_edk2.git] / IntelFsp2WrapperPkg / FspsWrapperPeim / FspsWrapperPeim.c
CommitLineData
cf1d4549
JY
1/** @file\r
2 This will be invoked only once. It will call FspMemoryInit API,\r
3 register TemporaryRamDonePpi to call TempRamExit API, and register MemoryDiscoveredPpi\r
4 notify to call FspSiliconInit API.\r
5\r
6 Copyright (c) 2014 - 2016, Intel Corporation. All rights reserved.<BR>\r
7 This program and the accompanying materials\r
8 are licensed and made available under the terms and conditions of the BSD License\r
9 which accompanies this distribution. The full text of the license may be found at\r
10 http://opensource.org/licenses/bsd-license.php.\r
11\r
12 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
13 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
14\r
15**/\r
16\r
17#include <PiPei.h>\r
18\r
19#include <Library/PeimEntryPoint.h>\r
20#include <Library/PeiServicesLib.h>\r
21#include <Library/PeiServicesTablePointerLib.h>\r
22#include <Library/BaseLib.h>\r
23#include <Library/DebugLib.h>\r
24#include <Library/BaseMemoryLib.h>\r
25#include <Library/HobLib.h>\r
26#include <Library/PcdLib.h>\r
27#include <Library/MemoryAllocationLib.h>\r
28#include <Library/FspWrapperPlatformLib.h>\r
29#include <Library/FspWrapperHobProcessLib.h>\r
30#include <Library/TimerLib.h>\r
31#include <Library/PerformanceLib.h>\r
32#include <Library/FspWrapperApiLib.h>\r
33\r
34#include <Ppi/FspSiliconInitDone.h>\r
35#include <Ppi/EndOfPeiPhase.h>\r
36#include <Ppi/MemoryDiscovered.h>\r
37#include <Ppi/TemporaryRamDone.h>\r
38#include <Ppi/SecPlatformInformation.h>\r
39#include <Library/PlatformSecLib.h>\r
40#include <Library/FspWrapperApiTestLib.h>\r
41#include <FspEas.h>\r
42\r
43extern EFI_PEI_NOTIFY_DESCRIPTOR mS3EndOfPeiNotifyDesc;\r
44extern EFI_GUID gFspHobGuid;\r
45\r
46/**\r
47This function handles S3 resume task at the end of PEI\r
48\r
49@param[in] PeiServices Pointer to PEI Services Table.\r
50@param[in] NotifyDesc Pointer to the descriptor for the Notification event that\r
51caused this function to execute.\r
52@param[in] Ppi Pointer to the PPI data associated with this function.\r
53\r
54@retval EFI_STATUS Always return EFI_SUCCESS\r
55**/\r
56EFI_STATUS\r
57EFIAPI\r
58S3EndOfPeiNotify(\r
59 IN EFI_PEI_SERVICES **PeiServices,\r
60 IN EFI_PEI_NOTIFY_DESCRIPTOR *NotifyDesc,\r
61 IN VOID *Ppi\r
62 );\r
63\r
64EFI_PEI_NOTIFY_DESCRIPTOR mS3EndOfPeiNotifyDesc = {\r
65 (EFI_PEI_PPI_DESCRIPTOR_NOTIFY_CALLBACK | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),\r
66 &gEfiEndOfPeiSignalPpiGuid,\r
67 S3EndOfPeiNotify\r
68};\r
69\r
70/**\r
71This function handles S3 resume task at the end of PEI\r
72\r
73@param[in] PeiServices Pointer to PEI Services Table.\r
74@param[in] NotifyDesc Pointer to the descriptor for the Notification event that\r
75caused this function to execute.\r
76@param[in] Ppi Pointer to the PPI data associated with this function.\r
77\r
78@retval EFI_STATUS Always return EFI_SUCCESS\r
79**/\r
80EFI_STATUS\r
81EFIAPI\r
82S3EndOfPeiNotify(\r
83 IN EFI_PEI_SERVICES **PeiServices,\r
84 IN EFI_PEI_NOTIFY_DESCRIPTOR *NotifyDesc,\r
85 IN VOID *Ppi\r
86 )\r
87{\r
88 NOTIFY_PHASE_PARAMS NotifyPhaseParams;\r
89 EFI_STATUS Status;\r
90\r
91 DEBUG((DEBUG_INFO, "S3EndOfPeiNotify enter\n"));\r
92\r
93 NotifyPhaseParams.Phase = EnumInitPhaseAfterPciEnumeration;\r
94 Status = CallFspNotifyPhase (&NotifyPhaseParams);\r
95 DEBUG((DEBUG_INFO, "FSP S3NotifyPhase AfterPciEnumeration status: 0x%x\n", Status));\r
96\r
f862a3b6
JY
97 //\r
98 // Reset the system if FSP API returned FSP_STATUS_RESET_REQUIRED status\r
99 //\r
100 if ((Status >= FSP_STATUS_RESET_REQUIRED_COLD) && (Status <= FSP_STATUS_RESET_REQUIRED_8)) {\r
101 DEBUG((DEBUG_INFO, "FSP S3NotifyPhase AfterPciEnumeration requested reset 0x%x\n", Status));\r
102 CallFspWrapperResetSystem ((UINT32)Status);\r
103 }\r
104\r
cf1d4549
JY
105 NotifyPhaseParams.Phase = EnumInitPhaseReadyToBoot;\r
106 Status = CallFspNotifyPhase (&NotifyPhaseParams);\r
107 DEBUG((DEBUG_INFO, "FSP S3NotifyPhase ReadyToBoot status: 0x%x\n", Status));\r
108\r
f862a3b6
JY
109 //\r
110 // Reset the system if FSP API returned FSP_STATUS_RESET_REQUIRED status\r
111 //\r
112 if ((Status >= FSP_STATUS_RESET_REQUIRED_COLD) && (Status <= FSP_STATUS_RESET_REQUIRED_8)) {\r
113 DEBUG((DEBUG_INFO, "FSP S3NotifyPhase ReadyToBoot requested reset 0x%x\n", Status));\r
114 CallFspWrapperResetSystem ((UINT32)Status);\r
115 }\r
116\r
cf1d4549
JY
117 NotifyPhaseParams.Phase = EnumInitPhaseEndOfFirmware;\r
118 Status = CallFspNotifyPhase (&NotifyPhaseParams);\r
119 DEBUG((DEBUG_INFO, "FSP S3NotifyPhase EndOfFirmware status: 0x%x\n", Status));\r
120\r
f862a3b6
JY
121 //\r
122 // Reset the system if FSP API returned FSP_STATUS_RESET_REQUIRED status\r
123 //\r
124 if ((Status >= FSP_STATUS_RESET_REQUIRED_COLD) && (Status <= FSP_STATUS_RESET_REQUIRED_8)) {\r
125 DEBUG((DEBUG_INFO, "FSP S3NotifyPhase EndOfFirmware requested reset 0x%x\n", Status));\r
126 CallFspWrapperResetSystem ((UINT32)Status);\r
127 }\r
128\r
cf1d4549
JY
129 return EFI_SUCCESS;\r
130}\r
131\r
132/**\r
133Return Hob list produced by FSP.\r
134\r
135@param[in] PeiServices The pointer to the PEI Services Table.\r
136@param[in] This The pointer to this instance of this PPI.\r
137@param[out] FspHobList The pointer to Hob list produced by FSP.\r
138\r
139@return EFI_SUCCESS FReturn Hob list produced by FSP successfully.\r
140**/\r
141EFI_STATUS\r
142EFIAPI\r
143FspSiliconInitDoneGetFspHobList (\r
144 IN CONST EFI_PEI_SERVICES **PeiServices,\r
145 IN FSP_SILICON_INIT_DONE_PPI *This,\r
146 OUT VOID **FspHobList\r
147 );\r
148\r
149FSP_SILICON_INIT_DONE_PPI mFspSiliconInitDonePpi = {\r
150 FspSiliconInitDoneGetFspHobList\r
151};\r
152\r
153EFI_PEI_PPI_DESCRIPTOR mPeiFspSiliconInitDonePpi = {\r
154 EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST,\r
155 &gFspSiliconInitDonePpiGuid,\r
156 &mFspSiliconInitDonePpi\r
157};\r
158\r
159/**\r
160Return Hob list produced by FSP.\r
161\r
162@param[in] PeiServices The pointer to the PEI Services Table.\r
163@param[in] This The pointer to this instance of this PPI.\r
164@param[out] FspHobList The pointer to Hob list produced by FSP.\r
165\r
166@return EFI_SUCCESS FReturn Hob list produced by FSP successfully.\r
167**/\r
168EFI_STATUS\r
169EFIAPI\r
170FspSiliconInitDoneGetFspHobList (\r
171 IN CONST EFI_PEI_SERVICES **PeiServices,\r
172 IN FSP_SILICON_INIT_DONE_PPI *This,\r
173 OUT VOID **FspHobList\r
174 )\r
175{\r
176 EFI_HOB_GUID_TYPE *GuidHob;\r
177\r
178 GuidHob = GetFirstGuidHob (&gFspHobGuid);\r
179 if (GuidHob != NULL) {\r
180 *FspHobList = *(VOID **)GET_GUID_HOB_DATA(GuidHob);\r
181 return EFI_SUCCESS;\r
182 } else {\r
183 return EFI_NOT_FOUND;\r
184 }\r
185}\r
186\r
187/**\r
188 This function is called after PEI core discover memory and finish migration.\r
189\r
190 @param[in] PeiServices Pointer to PEI Services Table.\r
191 @param[in] NotifyDesc Pointer to the descriptor for the Notification event that\r
192 caused this function to execute.\r
193 @param[in] Ppi Pointer to the PPI data associated with this function.\r
194\r
195 @retval EFI_STATUS Always return EFI_SUCCESS\r
196**/\r
197EFI_STATUS\r
198EFIAPI\r
199PeiMemoryDiscoveredNotify (\r
200 IN EFI_PEI_SERVICES **PeiServices,\r
201 IN EFI_PEI_NOTIFY_DESCRIPTOR *NotifyDesc,\r
202 IN VOID *Ppi\r
203 );\r
204\r
205EFI_PEI_NOTIFY_DESCRIPTOR mPeiMemoryDiscoveredNotifyDesc = {\r
206 (EFI_PEI_PPI_DESCRIPTOR_NOTIFY_CALLBACK | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),\r
207 &gEfiPeiMemoryDiscoveredPpiGuid,\r
208 PeiMemoryDiscoveredNotify\r
209};\r
210\r
211/**\r
212This function is called after PEI core discover memory and finish migration.\r
213\r
214@param[in] PeiServices Pointer to PEI Services Table.\r
215@param[in] NotifyDesc Pointer to the descriptor for the Notification event that\r
216caused this function to execute.\r
217@param[in] Ppi Pointer to the PPI data associated with this function.\r
218\r
219@retval EFI_STATUS Always return EFI_SUCCESS\r
220**/\r
221EFI_STATUS\r
222EFIAPI\r
223PeiMemoryDiscoveredNotify (\r
224 IN EFI_PEI_SERVICES **PeiServices,\r
225 IN EFI_PEI_NOTIFY_DESCRIPTOR *NotifyDesc,\r
226 IN VOID *Ppi\r
227 )\r
228{\r
229 FSP_INFO_HEADER *FspsHeaderPtr;\r
230 UINT64 TimeStampCounterStart;\r
231 EFI_STATUS Status;\r
232 VOID *FspHobListPtr;\r
233 EFI_HOB_GUID_TYPE *GuidHob;\r
234 FSPS_UPD_COMMON *FspsUpdDataPtr;\r
235 UINTN *SourceData;\r
236\r
237 \r
238 DEBUG ((DEBUG_INFO, "PeiMemoryDiscoveredNotify enter\n"));\r
239 \r
240 //\r
241 // Copy default FSP-S UPD data from Flash\r
242 //\r
243 FspsHeaderPtr = (FSP_INFO_HEADER *)FspFindFspHeader (PcdGet32 (PcdFspsBaseAddress));\r
599c45ff
HW
244 DEBUG ((DEBUG_INFO, "FspsHeaderPtr - 0x%x\n", FspsHeaderPtr));\r
245 if (FspsHeaderPtr == NULL) {\r
246 return EFI_DEVICE_ERROR;\r
247 }\r
248\r
cf1d4549
JY
249 FspsUpdDataPtr = (FSPS_UPD_COMMON *)AllocateZeroPool ((UINTN)FspsHeaderPtr->CfgRegionSize);\r
250 ASSERT (FspsUpdDataPtr != NULL);\r
251 SourceData = (UINTN *)((UINTN)FspsHeaderPtr->ImageBase + (UINTN)FspsHeaderPtr->CfgRegionOffset);\r
252 CopyMem (FspsUpdDataPtr, SourceData, (UINTN)FspsHeaderPtr->CfgRegionSize);\r
253\r
254 UpdateFspsUpdData ((VOID *)FspsUpdDataPtr);\r
255\r
256 TimeStampCounterStart = AsmReadTsc ();\r
257 PERF_START_EX(&gFspApiPerformanceGuid, "EventRec", NULL, 0, 0x9000);\r
258 Status = CallFspSiliconInit ((VOID *)FspsUpdDataPtr);\r
259 PERF_END_EX(&gFspApiPerformanceGuid, "EventRec", NULL, 0, 0x907F);\r
260 DEBUG ((DEBUG_INFO, "Total time spent executing FspSiliconInitApi: %d millisecond\n", DivU64x32 (GetTimeInNanoSecond (AsmReadTsc () - TimeStampCounterStart), 1000000)));\r
f862a3b6
JY
261\r
262 //\r
263 // Reset the system if FSP API returned FSP_STATUS_RESET_REQUIRED status\r
264 //\r
265 if ((Status >= FSP_STATUS_RESET_REQUIRED_COLD) && (Status <= FSP_STATUS_RESET_REQUIRED_8)) {\r
266 DEBUG((DEBUG_INFO, "FspSiliconInitApi requested reset 0x%x\n", Status));\r
267 CallFspWrapperResetSystem ((UINT32)Status);\r
268 }\r
269\r
cf1d4549
JY
270 if (EFI_ERROR(Status)) {\r
271 DEBUG ((DEBUG_ERROR, "ERROR - Failed to execute FspSiliconInitApi(), Status = %r\n", Status));\r
272 }\r
273 DEBUG((DEBUG_INFO, "FspSiliconInit status: 0x%x\n", Status));\r
274 ASSERT_EFI_ERROR (Status);\r
275\r
276 Status = TestFspSiliconInitApiOutput ((VOID *)NULL);\r
277 if (RETURN_ERROR (Status)) {\r
278 DEBUG ((DEBUG_ERROR, "ERROR - TestFspSiliconInitApiOutput () fail, Status = %r\n", Status));\r
279 }\r
280\r
281 //\r
282 // Now FspHobList complete, process it\r
283 //\r
284 GuidHob = GetFirstGuidHob (&gFspHobGuid);\r
285 ASSERT (GuidHob != NULL);\r
286 FspHobListPtr = *(VOID **)GET_GUID_HOB_DATA (GuidHob);\r
287 DEBUG ((DEBUG_INFO, "FspHobListPtr - 0x%x\n", FspHobListPtr));\r
288 PostFspsHobProcess (FspHobListPtr);\r
289\r
290 //\r
291 // Install FspSiliconInitDonePpi so that any other driver can consume this info.\r
292 //\r
293 Status = PeiServicesInstallPpi (&mPeiFspSiliconInitDonePpi);\r
294 ASSERT_EFI_ERROR(Status);\r
295\r
296 return Status;\r
297}\r
298\r
299/**\r
300 Do FSP initialization.\r
301\r
302 @return FSP initialization status.\r
303**/\r
304EFI_STATUS\r
305FspsWrapperInit (\r
306 VOID\r
307 )\r
308{\r
309 EFI_STATUS Status;\r
310 EFI_BOOT_MODE BootMode;\r
311\r
312 //\r
313 // Register MemoryDiscovered Nofity to run FspSiliconInit\r
314 //\r
315 Status = PeiServicesNotifyPpi (&mPeiMemoryDiscoveredNotifyDesc);\r
316 ASSERT_EFI_ERROR (Status);\r
317 \r
318 //\r
319 // Register EndOfPei Notify for S3 to run FSP NotifyPhase\r
320 //\r
321 PeiServicesGetBootMode (&BootMode);\r
322 if (BootMode == BOOT_ON_S3_RESUME) {\r
323 Status = PeiServicesNotifyPpi (&mS3EndOfPeiNotifyDesc);\r
324 ASSERT_EFI_ERROR (Status);\r
325 }\r
326\r
327 return EFI_SUCCESS;\r
328}\r
329\r
330/**\r
331 This is the entrypoint of PEIM\r
332\r
333 @param[in] FileHandle Handle of the file being invoked.\r
334 @param[in] PeiServices Describes the list of possible PEI Services.\r
335\r
336 @retval EFI_SUCCESS if it completed successfully.\r
337**/\r
338EFI_STATUS\r
339EFIAPI\r
340FspsWrapperPeimEntryPoint (\r
341 IN EFI_PEI_FILE_HANDLE FileHandle,\r
342 IN CONST EFI_PEI_SERVICES **PeiServices\r
343 )\r
344{\r
345\r
346 DEBUG ((DEBUG_INFO, "FspsWrapperPeimEntryPoint\n"));\r
347\r
348 FspsWrapperInit ();\r
349\r
350 return EFI_SUCCESS;\r
351}\r