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