]> git.proxmox.com Git - mirror_edk2.git/blame - UefiCpuPkg/Library/MpInitLib/PeiMpLib.c
UefiCpuPkg/MpInitLib: Register one End of PEI callback function
[mirror_edk2.git] / UefiCpuPkg / Library / MpInitLib / PeiMpLib.c
CommitLineData
3e8ad6bd
JF
1/** @file\r
2 MP initialize support functions for PEI phase.\r
3\r
4 Copyright (c) 2016, Intel Corporation. All rights reserved.<BR>\r
5 This program and the accompanying materials\r
6 are licensed and made available under the terms and conditions of the BSD License\r
7 which accompanies this distribution. The full text of the license may be found at\r
8 http://opensource.org/licenses/bsd-license.php\r
9\r
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
12\r
13**/\r
14\r
15#include "MpLib.h"\r
6dc05093
JF
16#include <Ppi/EndOfPeiPhase.h>\r
17#include <Library/PeiServicesLib.h>\r
18\r
19//\r
20// Global PEI notify function descriptor on EndofPei event\r
21//\r
22GLOBAL_REMOVE_IF_UNREFERENCED EFI_PEI_NOTIFY_DESCRIPTOR mMpInitLibNotifyList = {\r
23 (EFI_PEI_PPI_DESCRIPTOR_NOTIFY_CALLBACK | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),\r
24 &gEfiEndOfPeiSignalPpiGuid,\r
25 CpuMpEndOfPeiCallback\r
26};\r
3e8ad6bd 27\r
93ca4c0f
JF
28/**\r
29 Get pointer to CPU MP Data structure.\r
30\r
31 @return The pointer to CPU MP Data structure.\r
32**/\r
33CPU_MP_DATA *\r
34GetCpuMpData (\r
35 VOID\r
36 )\r
37{\r
38 CPU_MP_DATA *CpuMpData;\r
39\r
40 CpuMpData = GetCpuMpDataFromGuidedHob ();\r
41 ASSERT (CpuMpData != NULL);\r
42 return CpuMpData;\r
43}\r
44\r
45/**\r
46 Save the pointer to CPU MP Data structure.\r
47\r
48 @param[in] CpuMpData The pointer to CPU MP Data structure will be saved.\r
49**/\r
50VOID\r
51SaveCpuMpData (\r
52 IN CPU_MP_DATA *CpuMpData\r
53 )\r
54{\r
55 UINT64 Data64;\r
56 //\r
57 // Build location of CPU MP DATA buffer in HOB\r
58 //\r
59 Data64 = (UINT64) (UINTN) CpuMpData;\r
60 BuildGuidDataHob (\r
61 &mCpuInitMpLibHobGuid,\r
62 (VOID *) &Data64,\r
63 sizeof (UINT64)\r
64 );\r
65}\r
66\r
67\r
6dc05093
JF
68/**\r
69/**\r
70 Notify function on End Of PEI PPI.\r
71\r
72 On S3 boot, this function will restore wakeup buffer data.\r
73 On normal boot, this function will flag wakeup buffer to be un-used type.\r
74\r
75 @param[in] PeiServices The pointer to the PEI Services Table.\r
76 @param[in] NotifyDescriptor Address of the notification descriptor data structure.\r
77 @param[in] Ppi Address of the PPI that was installed.\r
78\r
79 @retval EFI_SUCCESS When everything is OK.\r
80**/\r
81EFI_STATUS\r
82EFIAPI\r
83CpuMpEndOfPeiCallback (\r
84 IN EFI_PEI_SERVICES **PeiServices,\r
85 IN EFI_PEI_NOTIFY_DESCRIPTOR *NotifyDescriptor,\r
86 IN VOID *Ppi\r
87 )\r
88{\r
89\r
90 DEBUG ((DEBUG_INFO, "PeiMpInitLib: CpuMpEndOfPeiCallback () invoked\n"));\r
91\r
92 return EFI_SUCCESS;\r
93}\r
93ca4c0f
JF
94/**\r
95 Initialize global data for MP support.\r
96\r
97 @param[in] CpuMpData The pointer to CPU MP Data structure.\r
98**/\r
99VOID\r
100InitMpGlobalData (\r
101 IN CPU_MP_DATA *CpuMpData\r
102 )\r
103{\r
6dc05093 104 EFI_STATUS Status;\r
93ca4c0f
JF
105\r
106 SaveCpuMpData (CpuMpData);\r
6dc05093
JF
107 //\r
108 // Register an event for EndOfPei\r
109 //\r
110 Status = PeiServicesNotifyPpi (&mMpInitLibNotifyList);\r
111 ASSERT_EFI_ERROR (Status);\r
93ca4c0f
JF
112}\r
113\r
3e8ad6bd
JF
114/**\r
115 This service executes a caller provided function on all enabled APs.\r
116\r
117 @param[in] Procedure A pointer to the function to be run on\r
118 enabled APs of the system. See type\r
119 EFI_AP_PROCEDURE.\r
120 @param[in] SingleThread If TRUE, then all the enabled APs execute\r
121 the function specified by Procedure one by\r
122 one, in ascending order of processor handle\r
123 number. If FALSE, then all the enabled APs\r
124 execute the function specified by Procedure\r
125 simultaneously.\r
126 @param[in] WaitEvent The event created by the caller with CreateEvent()\r
127 service. If it is NULL, then execute in\r
128 blocking mode. BSP waits until all APs finish\r
129 or TimeoutInMicroSeconds expires. If it's\r
130 not NULL, then execute in non-blocking mode.\r
131 BSP requests the function specified by\r
132 Procedure to be started on all the enabled\r
133 APs, and go on executing immediately. If\r
134 all return from Procedure, or TimeoutInMicroSeconds\r
135 expires, this event is signaled. The BSP\r
136 can use the CheckEvent() or WaitForEvent()\r
137 services to check the state of event. Type\r
138 EFI_EVENT is defined in CreateEvent() in\r
139 the Unified Extensible Firmware Interface\r
140 Specification.\r
141 @param[in] TimeoutInMicrosecsond Indicates the time limit in microseconds for\r
142 APs to return from Procedure, either for\r
143 blocking or non-blocking mode. Zero means\r
144 infinity. If the timeout expires before\r
145 all APs return from Procedure, then Procedure\r
146 on the failed APs is terminated. All enabled\r
147 APs are available for next function assigned\r
148 by MpInitLibStartupAllAPs() or\r
149 MPInitLibStartupThisAP().\r
150 If the timeout expires in blocking mode,\r
151 BSP returns EFI_TIMEOUT. If the timeout\r
152 expires in non-blocking mode, WaitEvent\r
153 is signaled with SignalEvent().\r
154 @param[in] ProcedureArgument The parameter passed into Procedure for\r
155 all APs.\r
156 @param[out] FailedCpuList If NULL, this parameter is ignored. Otherwise,\r
157 if all APs finish successfully, then its\r
158 content is set to NULL. If not all APs\r
159 finish before timeout expires, then its\r
160 content is set to address of the buffer\r
161 holding handle numbers of the failed APs.\r
162 The buffer is allocated by MP Initialization\r
163 library, and it's the caller's responsibility to\r
164 free the buffer with FreePool() service.\r
165 In blocking mode, it is ready for consumption\r
166 when the call returns. In non-blocking mode,\r
167 it is ready when WaitEvent is signaled. The\r
168 list of failed CPU is terminated by\r
169 END_OF_CPU_LIST.\r
170\r
171 @retval EFI_SUCCESS In blocking mode, all APs have finished before\r
172 the timeout expired.\r
173 @retval EFI_SUCCESS In non-blocking mode, function has been dispatched\r
174 to all enabled APs.\r
175 @retval EFI_UNSUPPORTED A non-blocking mode request was made after the\r
176 UEFI event EFI_EVENT_GROUP_READY_TO_BOOT was\r
177 signaled.\r
178 @retval EFI_UNSUPPORTED WaitEvent is not NULL if non-blocking mode is not\r
179 supported.\r
180 @retval EFI_DEVICE_ERROR Caller processor is AP.\r
181 @retval EFI_NOT_STARTED No enabled APs exist in the system.\r
182 @retval EFI_NOT_READY Any enabled APs are busy.\r
183 @retval EFI_NOT_READY MP Initialize Library is not initialized.\r
184 @retval EFI_TIMEOUT In blocking mode, the timeout expired before\r
185 all enabled APs have finished.\r
186 @retval EFI_INVALID_PARAMETER Procedure is NULL.\r
187\r
188**/\r
189EFI_STATUS\r
190EFIAPI\r
191MpInitLibStartupAllAPs (\r
192 IN EFI_AP_PROCEDURE Procedure,\r
193 IN BOOLEAN SingleThread,\r
194 IN EFI_EVENT WaitEvent OPTIONAL,\r
195 IN UINTN TimeoutInMicroseconds,\r
196 IN VOID *ProcedureArgument OPTIONAL,\r
197 OUT UINTN **FailedCpuList OPTIONAL\r
198 )\r
199{\r
200 return EFI_UNSUPPORTED;\r
201}\r
202\r
203/**\r
204 This service lets the caller get one enabled AP to execute a caller-provided\r
205 function.\r
206\r
207 @param[in] Procedure A pointer to the function to be run on the\r
208 designated AP of the system. See type\r
209 EFI_AP_PROCEDURE.\r
210 @param[in] ProcessorNumber The handle number of the AP. The range is\r
211 from 0 to the total number of logical\r
212 processors minus 1. The total number of\r
213 logical processors can be retrieved by\r
214 MpInitLibGetNumberOfProcessors().\r
215 @param[in] WaitEvent The event created by the caller with CreateEvent()\r
216 service. If it is NULL, then execute in\r
217 blocking mode. BSP waits until this AP finish\r
218 or TimeoutInMicroSeconds expires. If it's\r
219 not NULL, then execute in non-blocking mode.\r
220 BSP requests the function specified by\r
221 Procedure to be started on this AP,\r
222 and go on executing immediately. If this AP\r
223 return from Procedure or TimeoutInMicroSeconds\r
224 expires, this event is signaled. The BSP\r
225 can use the CheckEvent() or WaitForEvent()\r
226 services to check the state of event. Type\r
227 EFI_EVENT is defined in CreateEvent() in\r
228 the Unified Extensible Firmware Interface\r
229 Specification.\r
230 @param[in] TimeoutInMicrosecsond Indicates the time limit in microseconds for\r
231 this AP to finish this Procedure, either for\r
232 blocking or non-blocking mode. Zero means\r
233 infinity. If the timeout expires before\r
234 this AP returns from Procedure, then Procedure\r
235 on the AP is terminated. The\r
236 AP is available for next function assigned\r
237 by MpInitLibStartupAllAPs() or\r
238 MpInitLibStartupThisAP().\r
239 If the timeout expires in blocking mode,\r
240 BSP returns EFI_TIMEOUT. If the timeout\r
241 expires in non-blocking mode, WaitEvent\r
242 is signaled with SignalEvent().\r
243 @param[in] ProcedureArgument The parameter passed into Procedure on the\r
244 specified AP.\r
245 @param[out] Finished If NULL, this parameter is ignored. In\r
246 blocking mode, this parameter is ignored.\r
247 In non-blocking mode, if AP returns from\r
248 Procedure before the timeout expires, its\r
249 content is set to TRUE. Otherwise, the\r
250 value is set to FALSE. The caller can\r
251 determine if the AP returned from Procedure\r
252 by evaluating this value.\r
253\r
254 @retval EFI_SUCCESS In blocking mode, specified AP finished before\r
255 the timeout expires.\r
256 @retval EFI_SUCCESS In non-blocking mode, the function has been\r
257 dispatched to specified AP.\r
258 @retval EFI_UNSUPPORTED A non-blocking mode request was made after the\r
259 UEFI event EFI_EVENT_GROUP_READY_TO_BOOT was\r
260 signaled.\r
261 @retval EFI_UNSUPPORTED WaitEvent is not NULL if non-blocking mode is not\r
262 supported.\r
263 @retval EFI_DEVICE_ERROR The calling processor is an AP.\r
264 @retval EFI_TIMEOUT In blocking mode, the timeout expired before\r
265 the specified AP has finished.\r
266 @retval EFI_NOT_READY The specified AP is busy.\r
267 @retval EFI_NOT_READY MP Initialize Library is not initialized.\r
268 @retval EFI_NOT_FOUND The processor with the handle specified by\r
269 ProcessorNumber does not exist.\r
270 @retval EFI_INVALID_PARAMETER ProcessorNumber specifies the BSP or disabled AP.\r
271 @retval EFI_INVALID_PARAMETER Procedure is NULL.\r
272\r
273**/\r
274EFI_STATUS\r
275EFIAPI\r
276MpInitLibStartupThisAP (\r
277 IN EFI_AP_PROCEDURE Procedure,\r
278 IN UINTN ProcessorNumber,\r
279 IN EFI_EVENT WaitEvent OPTIONAL,\r
280 IN UINTN TimeoutInMicroseconds,\r
281 IN VOID *ProcedureArgument OPTIONAL,\r
282 OUT BOOLEAN *Finished OPTIONAL\r
283 )\r
284{\r
285 return EFI_UNSUPPORTED;\r
286}\r
287\r
288/**\r
289 This service switches the requested AP to be the BSP from that point onward.\r
290 This service changes the BSP for all purposes. This call can only be performed\r
291 by the current BSP.\r
292\r
293 @param[in] ProcessorNumber The handle number of AP that is to become the new\r
294 BSP. The range is from 0 to the total number of\r
295 logical processors minus 1. The total number of\r
296 logical processors can be retrieved by\r
297 MpInitLibGetNumberOfProcessors().\r
298 @param[in] EnableOldBSP If TRUE, then the old BSP will be listed as an\r
299 enabled AP. Otherwise, it will be disabled.\r
300\r
301 @retval EFI_SUCCESS BSP successfully switched.\r
302 @retval EFI_UNSUPPORTED Switching the BSP cannot be completed prior to\r
303 this service returning.\r
304 @retval EFI_UNSUPPORTED Switching the BSP is not supported.\r
305 @retval EFI_DEVICE_ERROR The calling processor is an AP.\r
306 @retval EFI_NOT_FOUND The processor with the handle specified by\r
307 ProcessorNumber does not exist.\r
308 @retval EFI_INVALID_PARAMETER ProcessorNumber specifies the current BSP or\r
309 a disabled AP.\r
310 @retval EFI_NOT_READY The specified AP is busy.\r
311 @retval EFI_NOT_READY MP Initialize Library is not initialized.\r
312\r
313**/\r
314EFI_STATUS\r
315EFIAPI\r
316MpInitLibSwitchBSP (\r
317 IN UINTN ProcessorNumber,\r
318 IN BOOLEAN EnableOldBSP\r
319 )\r
320{\r
321 return EFI_UNSUPPORTED;\r
322}\r
323\r
324/**\r
325 This service lets the caller enable or disable an AP from this point onward.\r
326 This service may only be called from the BSP.\r
327\r
328 @param[in] ProcessorNumber The handle number of AP.\r
329 The range is from 0 to the total number of\r
330 logical processors minus 1. The total number of\r
331 logical processors can be retrieved by\r
332 MpInitLibGetNumberOfProcessors().\r
333 @param[in] EnableAP Specifies the new state for the processor for\r
334 enabled, FALSE for disabled.\r
335 @param[in] HealthFlag If not NULL, a pointer to a value that specifies\r
336 the new health status of the AP. This flag\r
337 corresponds to StatusFlag defined in\r
338 EFI_MP_SERVICES_PROTOCOL.GetProcessorInfo(). Only\r
339 the PROCESSOR_HEALTH_STATUS_BIT is used. All other\r
340 bits are ignored. If it is NULL, this parameter\r
341 is ignored.\r
342\r
343 @retval EFI_SUCCESS The specified AP was enabled or disabled successfully.\r
344 @retval EFI_UNSUPPORTED Enabling or disabling an AP cannot be completed\r
345 prior to this service returning.\r
346 @retval EFI_UNSUPPORTED Enabling or disabling an AP is not supported.\r
347 @retval EFI_DEVICE_ERROR The calling processor is an AP.\r
348 @retval EFI_NOT_FOUND Processor with the handle specified by ProcessorNumber\r
349 does not exist.\r
350 @retval EFI_INVALID_PARAMETER ProcessorNumber specifies the BSP.\r
351 @retval EFI_NOT_READY MP Initialize Library is not initialized.\r
352\r
353**/\r
354EFI_STATUS\r
355EFIAPI\r
356MpInitLibEnableDisableAP (\r
357 IN UINTN ProcessorNumber,\r
358 IN BOOLEAN EnableAP,\r
359 IN UINT32 *HealthFlag OPTIONAL\r
360 )\r
361{\r
362 return EFI_UNSUPPORTED;\r
363}\r
364\r
365\r