3 Copyright (c) 2014 - 2015, 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.
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.
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>
26 #include <Protocol/PciEnumerationComplete.h>
28 EFI_PEI_PPI_DESCRIPTOR mPeiPostPciEnumerationPpi
= {
29 (EFI_PEI_PPI_DESCRIPTOR_PPI
| EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST
),
30 &gEfiPciEnumerationCompleteProtocolGuid
,
34 EFI_PEI_PPI_DESCRIPTOR mPeiReadyToBootPpi
= {
35 (EFI_PEI_PPI_DESCRIPTOR_PPI
| EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST
),
36 &gEfiEventReadyToBootGuid
,
41 UINT32 mFspNotifySequence
[] = {
42 EnumInitPhaseAfterPciEnumeration
,
43 EnumInitPhaseReadyToBoot
47 Install FSP notification.
49 @param[in] NotificationCode FSP notification code
51 @retval EFI_SUCCESS Notify FSP successfully
52 @retval EFI_INVALID_PARAMETER NotificationCode is invalid
57 FspNotificationHandler (
58 IN UINT32 NotificationCode
65 switch (NotificationCode
) {
66 case EnumInitPhaseAfterPciEnumeration
:
68 // Do POST PCI initialization if needed
70 DEBUG ((DEBUG_INFO
| DEBUG_INIT
, "FSP Post PCI Enumeration ...\n"));
71 PeiServicesInstallPpi (&mPeiPostPciEnumerationPpi
);
74 case EnumInitPhaseReadyToBoot
:
78 DEBUG ((DEBUG_INFO
| DEBUG_INIT
, "FSP Ready To Boot ...\n"));
79 PeiServicesInstallPpi (&mPeiReadyToBootPpi
);
83 Status
= EFI_INVALID_PARAMETER
;
91 This function transfer control to the ContinuationFunc passed in by the
101 FSP_INIT_PARAMS
*FspInitParams
;
103 if (GetFspApiCallingMode() == 0) {
105 // FspInit API is used, so jump into the ContinuationFunc
107 FspInitParams
= (FSP_INIT_PARAMS
*)GetFspApiParameter ();
110 // Modify the parameters for ContinuationFunc
112 SetFspContinuationFuncParameter(EFI_SUCCESS
, 0);
113 SetFspContinuationFuncParameter((UINT32
)GetHobList(), 1);
116 // Modify the return address to ContinuationFunc
118 SetFspApiReturnAddress((UINT32
)FspInitParams
->ContinuationFunc
);
121 // Give control back to the boot loader framework caller after FspInit is done
122 // It is done throught the continuation function
124 SetFspMeasurePoint (FSP_PERF_ID_API_FSPINIT_EXIT
);
127 // FspMemoryInit API is used, so return directly
131 // This is the end of the FspSiliconInit API
132 // Give control back to the boot loader
134 DEBUG ((DEBUG_INFO
| DEBUG_INIT
, "FspSiliconInitApi() - End\n"));
135 SetFspApiReturnStatus (EFI_SUCCESS
);
138 Pei2LoaderSwitchStack();
142 This function handle NotifyPhase API call from the BootLoader.
143 It gives control back to the BootLoader after it is handled. If the
144 Notification code is a ReadyToBoot event, this function will return
145 and FSP continues the remaining execution until it reaches the DxeIpl.
154 UINT32 NotificationValue
;
155 UINT32 NotificationCount
;
158 NotificationCount
= 0;
159 while (NotificationCount
< sizeof(mFspNotifySequence
) / sizeof(UINT32
)) {
161 Count
= (UINT8
)((NotificationCount
<< 1) & 0x07);
162 SetFspMeasurePoint (FSP_PERF_ID_API_NOTIFY_POSTPCI_ENTRY
+ Count
);
164 NotificationValue
= ((NOTIFY_PHASE_PARAMS
*)(UINTN
)GetFspApiParameter ())->Phase
;
165 DEBUG ((DEBUG_INFO
, "FSP Got Notification. Notification Value : 0x%08X\n", NotificationValue
));
167 if (mFspNotifySequence
[NotificationCount
] != NotificationValue
) {
169 // Notify code does not follow the predefined order
171 DEBUG ((DEBUG_INFO
, "Unsupported FSP Notification Value\n"));
172 SetFspApiReturnStatus(EFI_UNSUPPORTED
);
175 // Process Notification and Give control back to the boot loader framework caller
177 Status
= FspNotificationHandler (NotificationValue
);
178 DEBUG ((DEBUG_INFO
, "FSP Notification Handler Returns : 0x%08X\n", Status
));
179 SetFspApiReturnStatus(Status
);
180 if (!EFI_ERROR(Status
)) {
182 SetFspApiReturnStatus(EFI_SUCCESS
);
183 if (NotificationValue
== EnumInitPhaseReadyToBoot
) {
188 SetFspMeasurePoint (FSP_PERF_ID_API_NOTIFY_POSTPCI_EXIT
+ Count
);
189 Pei2LoaderSwitchStack();
193 // Control goes back to the PEI Core and it dispatches further PEIMs.
194 // DXEIPL is the final one to transfer control back to the boot loader.