IntelFsp2Pkg BaseFspPlatformLib: Remove Boot Loader tempram Migration
[mirror_edk2.git] / IntelFsp2Pkg / Library / BaseFspPlatformLib / FspPlatformNotify.c
1 /** @file
2
3 Copyright (c) 2014 - 2016, Intel Corporation. All rights reserved.<BR>
4 This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php.
8
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
11
12 **/
13
14 #include <PiPei.h>
15 #include <Library/PeiServicesLib.h>
16 #include <Library/PeiServicesTablePointerLib.h>
17 #include <Library/BaseLib.h>
18 #include <Library/BaseMemoryLib.h>
19 #include <Library/PcdLib.h>
20 #include <Library/DebugLib.h>
21 #include <Library/HobLib.h>
22 #include <Library/FspSwitchStackLib.h>
23 #include <Library/FspCommonLib.h>
24 #include <Guid/EventGroup.h>
25 #include <FspEas.h>
26 #include <FspStatusCode.h>
27 #include <Protocol/PciEnumerationComplete.h>
28 #include <Library/ReportStatusCodeLib.h>
29 #include <Library/PerformanceLib.h>
30 extern EFI_GUID gFspPerformanceDataGuid;
31
32 EFI_PEI_PPI_DESCRIPTOR mPeiPostPciEnumerationPpi = {
33 (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
34 &gEfiPciEnumerationCompleteProtocolGuid,
35 NULL
36 };
37
38 EFI_PEI_PPI_DESCRIPTOR mPeiReadyToBootPpi = {
39 (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
40 &gEfiEventReadyToBootGuid,
41 NULL
42 };
43
44 EFI_PEI_PPI_DESCRIPTOR mPeiEndOfFirmwarePpi = {
45 (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
46 &gFspEventEndOfFirmwareGuid,
47 NULL
48 };
49
50 UINT32 mFspNotifySequence[] = {
51 EnumInitPhaseAfterPciEnumeration,
52 EnumInitPhaseReadyToBoot,
53 EnumInitPhaseEndOfFirmware
54 };
55
56 /**
57 Install FSP notification.
58
59 @param[in] NotificationCode FSP notification code
60
61 @retval EFI_SUCCESS Notify FSP successfully
62 @retval EFI_INVALID_PARAMETER NotificationCode is invalid
63
64 **/
65 EFI_STATUS
66 EFIAPI
67 FspNotificationHandler (
68 IN UINT32 NotificationCode
69 )
70 {
71 EFI_STATUS Status;
72
73 Status = EFI_SUCCESS;
74
75 switch (NotificationCode) {
76 case EnumInitPhaseAfterPciEnumeration:
77 //
78 // Do POST PCI initialization if needed
79 //
80 DEBUG ((DEBUG_INFO | DEBUG_INIT, "FSP Post PCI Enumeration ...\n"));
81 PeiServicesInstallPpi (&mPeiPostPciEnumerationPpi);
82 break;
83
84 case EnumInitPhaseReadyToBoot:
85 //
86 // Ready To Boot
87 //
88 DEBUG ((DEBUG_INFO| DEBUG_INIT, "FSP Ready To Boot ...\n"));
89 PeiServicesInstallPpi (&mPeiReadyToBootPpi);
90 break;
91
92 case EnumInitPhaseEndOfFirmware:
93 //
94 // End of Firmware
95 //
96 DEBUG ((DEBUG_INFO| DEBUG_INIT, "FSP End of Firmware ...\n"));
97 PeiServicesInstallPpi (&mPeiEndOfFirmwarePpi);
98 break;
99
100 default:
101 Status = EFI_INVALID_PARAMETER;
102 break;
103 }
104
105 return Status;
106 }
107
108 /**
109 This function transfer control back to BootLoader after FspSiliconInit.
110
111 **/
112 VOID
113 EFIAPI
114 FspSiliconInitDone (
115 VOID
116 )
117 {
118 //
119 // This is the end of the FspSiliconInit API
120 // Give control back to the boot loader
121 //
122 SetFspMeasurePoint (FSP_PERF_ID_API_FSP_SILICON_INIT_EXIT);
123 DEBUG ((DEBUG_INFO | DEBUG_INIT, "FspSiliconInitApi() - End\n"));
124
125 PERF_END_EX (&gFspPerformanceDataGuid, "EventRec", NULL, 0, 0x907F);
126
127 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_EXIT);
128 SetFspApiReturnStatus (EFI_SUCCESS);
129
130 Pei2LoaderSwitchStack();
131
132 PERF_START_EX (&gFspPerformanceDataGuid, "EventRec", NULL, 0, 0x6000);
133 }
134
135 /**
136 This function returns control to BootLoader after MemoryInitApi.
137
138 @param[in,out] HobListPtr The address of HobList pointer.
139 **/
140 VOID
141 EFIAPI
142 FspMemoryInitDone (
143 IN OUT VOID **HobListPtr
144 )
145 {
146 //
147 // Calling use FspMemoryInit API
148 // Update HOB and return the control directly
149 //
150 if (HobListPtr != NULL) {
151 *HobListPtr = (VOID *) GetHobList ();
152 }
153
154 //
155 // This is the end of the FspMemoryInit API
156 // Give control back to the boot loader
157 //
158 SetFspMeasurePoint (FSP_PERF_ID_API_FSP_MEMORY_INIT_EXIT);
159 DEBUG ((DEBUG_INFO | DEBUG_INIT, "FspMemoryInitApi() - End\n"));
160 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_MEMORY_INIT | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_EXIT);
161 SetFspApiReturnStatus (EFI_SUCCESS);
162 Pei2LoaderSwitchStack ();
163
164 //
165 // The TempRamExitApi is called
166 //
167 if (GetFspApiCallingIndex () == TempRamExitApiIndex) {
168 SetPhaseStatusCode (FSP_STATUS_CODE_TEMP_RAM_EXIT);
169 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_TEMP_RAM_EXIT | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_ENTRY);
170 SetFspMeasurePoint (FSP_PERF_ID_API_TEMP_RAM_EXIT_ENTRY);
171 DEBUG ((DEBUG_INFO | DEBUG_INIT, "TempRamExitApi() - Begin\n"));
172 } else {
173 SetFspMeasurePoint (FSP_PERF_ID_API_FSP_SILICON_INIT_ENTRY);
174 DEBUG ((DEBUG_INFO | DEBUG_INIT, "FspSiliconInitApi() - Begin\n"));
175 SetPhaseStatusCode (FSP_STATUS_CODE_SILICON_INIT);
176 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_SILICON_INIT | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_ENTRY);
177 }
178 }
179
180 /**
181 This function returns control to BootLoader after TempRamExitApi.
182
183 **/
184 VOID
185 EFIAPI
186 FspTempRamExitDone (
187 VOID
188 )
189 {
190
191 //
192 // This is the end of the TempRamExit API
193 // Give control back to the boot loader
194 //
195 SetFspMeasurePoint (FSP_PERF_ID_API_TEMP_RAM_EXIT_EXIT);
196 DEBUG ((DEBUG_INFO | DEBUG_INIT, "TempRamExitApi() - End\n"));
197 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_TEMP_RAM_EXIT | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_EXIT);
198 SetFspApiReturnStatus (EFI_SUCCESS);
199 Pei2LoaderSwitchStack ();
200
201 SetPhaseStatusCode (FSP_STATUS_CODE_SILICON_INIT);
202 SetFspMeasurePoint (FSP_PERF_ID_API_FSP_SILICON_INIT_ENTRY);
203 DEBUG ((DEBUG_INFO | DEBUG_INIT, "SiliconInitApi() - Begin\n"));
204 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_SILICON_INIT | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_ENTRY);
205 }
206
207 /**
208 This function handle NotifyPhase API call from the BootLoader.
209 It gives control back to the BootLoader after it is handled. If the
210 Notification code is a ReadyToBoot event, this function will return
211 and FSP continues the remaining execution until it reaches the DxeIpl.
212
213 **/
214 VOID
215 FspWaitForNotify (
216 VOID
217 )
218 {
219 EFI_STATUS Status;
220 UINT32 NotificationValue;
221 UINT32 NotificationCount;
222 UINT8 Count;
223
224 NotificationCount = 0;
225 while (NotificationCount < sizeof(mFspNotifySequence) / sizeof(UINT32)) {
226
227 Count = (UINT8)((NotificationCount << 1) & 0x07);
228 SetFspMeasurePoint (FSP_PERF_ID_API_NOTIFY_POST_PCI_ENTRY + Count);
229
230 if (NotificationCount == 0) {
231 SetPhaseStatusCode (FSP_STATUS_CODE_POST_PCIE_ENUM_NOTIFICATION);
232 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_POST_PCIE_ENUM_NOTIFICATION | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_ENTRY);
233 } else if (NotificationCount == 1) {
234 SetPhaseStatusCode (FSP_STATUS_CODE_READY_TO_BOOT_NOTIFICATION);
235 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_READY_TO_BOOT_NOTIFICATION | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_ENTRY);
236 } else if (NotificationCount == 2) {
237 SetPhaseStatusCode (FSP_STATUS_CODE_END_OF_FIRMWARE_NOTIFICATION);
238 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_END_OF_FIRMWARE_NOTIFICATION | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_ENTRY);
239 }
240
241 NotificationValue = ((NOTIFY_PHASE_PARAMS *)(UINTN)GetFspApiParameter ())->Phase;
242 DEBUG ((DEBUG_INFO | DEBUG_INIT, "NotifyPhaseApi() - Begin [Phase: %08X]\n", NotificationValue));
243 if (mFspNotifySequence[NotificationCount] != NotificationValue) {
244 //
245 // Notify code does not follow the predefined order
246 //
247 DEBUG ((DEBUG_INFO, "Unsupported FSP Notification Value\n"));
248 Status = EFI_UNSUPPORTED;
249 } else {
250 //
251 // Process Notification and Give control back to the boot loader framework caller
252 //
253 Status = FspNotificationHandler (NotificationValue);
254 if (!EFI_ERROR(Status)) {
255 NotificationCount++;
256 }
257 }
258
259 SetFspApiReturnStatus(Status);
260 DEBUG ((DEBUG_INFO | DEBUG_INIT, "NotifyPhaseApi() - End [Status: 0x%08X]\n", Status));
261
262 SetFspMeasurePoint (FSP_PERF_ID_API_NOTIFY_POST_PCI_EXIT + Count);
263
264 if ((NotificationCount - 1) == 0) {
265 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_POST_PCIE_ENUM_NOTIFICATION | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_EXIT);
266 } else if ((NotificationCount - 1) == 1) {
267 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_READY_TO_BOOT_NOTIFICATION | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_EXIT);
268 } else if ((NotificationCount - 1) == 2) {
269 REPORT_STATUS_CODE (EFI_PROGRESS_CODE, FSP_STATUS_CODE_END_OF_FIRMWARE_NOTIFICATION | FSP_STATUS_CODE_COMMON_CODE | FSP_STATUS_CODE_API_EXIT);
270 }
271 Pei2LoaderSwitchStack();
272 }
273
274 //
275 // Control goes back to the PEI Core and it dispatches further PEIMs.
276 // DXEIPL is the final one to transfer control back to the boot loader.
277 //
278 }
279