2 This PEIM will parse coreboot table in memory and report resource information into pei core.
3 This file contains the main entrypoint of the PEIM.
5 Copyright (c) 2014 - 2015, Intel Corporation. All rights reserved.<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
15 #include "CbSupportPei.h"
17 #define LEGACY_8259_MASK_REGISTER_MASTER 0x21
18 #define LEGACY_8259_MASK_REGISTER_SLAVE 0xA1
20 EFI_MEMORY_TYPE_INFORMATION mDefaultMemoryTypeInformation
[] = {
21 { EfiACPIReclaimMemory
, 0x008 },
22 { EfiACPIMemoryNVS
, 0x004 },
23 { EfiReservedMemoryType
, 0x004 },
24 { EfiRuntimeServicesData
, 0x080 },
25 { EfiRuntimeServicesCode
, 0x080 },
26 { EfiMaxMemoryType
, 0 }
29 EFI_PEI_PPI_DESCRIPTOR mPpiBootMode
[] = {
31 EFI_PEI_PPI_DESCRIPTOR_PPI
| EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST
,
32 &gEfiPeiMasterBootModePpiGuid
,
38 Create memory mapped io resource hob.
40 @param MmioBase Base address of the memory mapped io range
41 @param MmioSize Length of the memory mapped io range
45 BuildMemoryMappedIoRangeHob (
46 EFI_PHYSICAL_ADDRESS MmioBase
,
50 BuildResourceDescriptorHob (
51 EFI_RESOURCE_MEMORY_MAPPED_IO
,
52 (EFI_RESOURCE_ATTRIBUTE_PRESENT
|
53 EFI_RESOURCE_ATTRIBUTE_INITIALIZED
|
54 EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE
|
55 EFI_RESOURCE_ATTRIBUTE_TESTED
),
60 BuildMemoryAllocationHob (
68 Check the integrity of firmware volume header
70 @param[in] FwVolHeader A pointer to a firmware volume header
72 @retval TRUE The firmware volume is consistent
73 @retval FALSE The firmware volume has corrupted.
79 IN EFI_FIRMWARE_VOLUME_HEADER
*FwVolHeader
85 if (CompareMem (&FwVolHeader
->FileSystemGuid
, &gEfiFirmwareFileSystem2Guid
, sizeof(EFI_GUID
)) != 0 ) {
89 if ( (FwVolHeader
->Revision
!= EFI_FVH_REVISION
) ||
90 (FwVolHeader
->Signature
!= EFI_FVH_SIGNATURE
) ||
91 (FwVolHeader
->FvLength
== ((UINTN
) -1)) ||
92 ((FwVolHeader
->HeaderLength
& 0x01 ) !=0) ) {
96 Checksum
= CalculateCheckSum16 ((UINT16
*) FwVolHeader
, FwVolHeader
->HeaderLength
);
99 "ERROR - Invalid Firmware Volume Header Checksum, change 0x%04x to 0x%04x\r\n",
100 FwVolHeader
->Checksum
,
101 (UINT16
)( Checksum
+ FwVolHeader
->Checksum
)));
109 Install FvInfo PPI and create fv hobs for remained fvs
113 CbPeiReportRemainedFvs (
120 TempPtr
= (UINT8
* )(UINTN
) PcdGet32 (PcdPayloadFdMemBase
);
121 EndPtr
= (UINT8
* )(UINTN
) (PcdGet32 (PcdPayloadFdMemBase
) + PcdGet32 (PcdPayloadFdMemSize
));
123 for (;TempPtr
< EndPtr
;) {
124 if (IsFvHeaderValid ((EFI_FIRMWARE_VOLUME_HEADER
* )TempPtr
)) {
125 if (TempPtr
!= (UINT8
* )(UINTN
) PcdGet32 (PcdPayloadFdMemBase
)) {
127 DEBUG((EFI_D_ERROR
, "Found one valid fv : 0x%lx.\n", TempPtr
, ((EFI_FIRMWARE_VOLUME_HEADER
* )TempPtr
)->FvLength
));
129 PeiServicesInstallFvInfoPpi (
131 (VOID
*) (UINTN
) TempPtr
,
132 (UINT32
) (UINTN
) ((EFI_FIRMWARE_VOLUME_HEADER
* )TempPtr
)->FvLength
,
136 BuildFvHob ((EFI_PHYSICAL_ADDRESS
)(UINTN
) TempPtr
, ((EFI_FIRMWARE_VOLUME_HEADER
* )TempPtr
)->FvLength
);
139 TempPtr
+= ((EFI_FIRMWARE_VOLUME_HEADER
* )TempPtr
)->FvLength
;
144 This is the entrypoint of PEIM
146 @param FileHandle Handle of the file being invoked.
147 @param PeiServices Describes the list of possible PEI Services.
149 @retval EFI_SUCCESS if it completed successfully.
154 IN EFI_PEI_FILE_HANDLE FileHandle
,
155 IN CONST EFI_PEI_SERVICES
**PeiServices
159 UINT64 LowMemorySize
, HighMemorySize
;
160 UINT64 PeiMemSize
= SIZE_64MB
; // 64 MB
161 EFI_PHYSICAL_ADDRESS PeiMemBase
= 0;
163 UINT8 PhysicalAddressBits
;
166 UINT32 AcpiTableSize
;
168 UINT32 SmbiosTableSize
;
169 SYSTEM_TABLE_INFO
* pSystemTableInfo
;
170 FRAME_BUFFER_INFO FbInfo
;
171 FRAME_BUFFER_INFO
* pFbInfo
;
172 ACPI_BOARD_INFO
* pAcpiBoardInfo
;
173 UINTN PmCtrlRegBase
, PmTimerRegBase
, ResetRegAddress
, ResetValue
;
180 Status
= CbParseMemoryInfo (&LowMemorySize
, &HighMemorySize
);
181 if (EFI_ERROR(Status
))
184 DEBUG((EFI_D_ERROR
, "LowMemorySize: 0x%lx.\n", LowMemorySize
));
185 DEBUG((EFI_D_ERROR
, "HighMemorySize: 0x%lx.\n", HighMemorySize
));
187 ASSERT (LowMemorySize
> 0);
190 // Report lower 640KB of RAM. Attribute EFI_RESOURCE_ATTRIBUTE_TESTED
191 // is intentionally omitted to prevent erasing of the coreboot header
192 // record before it is processed by CbParseMemoryInfo.
194 BuildResourceDescriptorHob (
195 EFI_RESOURCE_SYSTEM_MEMORY
,
197 EFI_RESOURCE_ATTRIBUTE_PRESENT
|
198 EFI_RESOURCE_ATTRIBUTE_INITIALIZED
|
199 EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE
|
200 EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE
|
201 EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE
|
202 EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
204 (EFI_PHYSICAL_ADDRESS
)(0),
209 BuildResourceDescriptorHob (
210 EFI_RESOURCE_MEMORY_RESERVED
,
212 EFI_RESOURCE_ATTRIBUTE_PRESENT
|
213 EFI_RESOURCE_ATTRIBUTE_INITIALIZED
|
214 EFI_RESOURCE_ATTRIBUTE_TESTED
|
215 EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE
|
216 EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE
|
217 EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE
|
218 EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
220 (EFI_PHYSICAL_ADDRESS
)(0xA0000),
224 BuildResourceDescriptorHob (
225 EFI_RESOURCE_SYSTEM_MEMORY
,
227 EFI_RESOURCE_ATTRIBUTE_PRESENT
|
228 EFI_RESOURCE_ATTRIBUTE_INITIALIZED
|
229 EFI_RESOURCE_ATTRIBUTE_TESTED
|
230 EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE
|
231 EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE
|
232 EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE
|
233 EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
235 (EFI_PHYSICAL_ADDRESS
)(0x100000),
236 (UINT64
) (LowMemorySize
- 0x100000)
239 if (HighMemorySize
> 0) {
240 BuildResourceDescriptorHob (
241 EFI_RESOURCE_SYSTEM_MEMORY
,
243 EFI_RESOURCE_ATTRIBUTE_PRESENT
|
244 EFI_RESOURCE_ATTRIBUTE_INITIALIZED
|
245 EFI_RESOURCE_ATTRIBUTE_UNCACHEABLE
|
246 EFI_RESOURCE_ATTRIBUTE_WRITE_COMBINEABLE
|
247 EFI_RESOURCE_ATTRIBUTE_WRITE_THROUGH_CACHEABLE
|
248 EFI_RESOURCE_ATTRIBUTE_WRITE_BACK_CACHEABLE
250 (EFI_PHYSICAL_ADDRESS
)(0x100000000ULL
),
256 // Should be 64k aligned
258 PeiMemBase
= (LowMemorySize
- PeiMemSize
) & (~(BASE_64KB
- 1));
260 DEBUG((EFI_D_ERROR
, "PeiMemBase: 0x%lx.\n", PeiMemBase
));
261 DEBUG((EFI_D_ERROR
, "PeiMemSize: 0x%lx.\n", PeiMemSize
));
263 Status
= PeiServicesInstallPeiMemory (
267 ASSERT_EFI_ERROR (Status
);
270 // Set cache on the physical memory
272 MtrrSetMemoryAttribute (BASE_1MB
, LowMemorySize
- BASE_1MB
, CacheWriteBack
);
273 MtrrSetMemoryAttribute (0, 0xA0000, CacheWriteBack
);
276 // Create Memory Type Information HOB
279 &gEfiMemoryTypeInformationGuid
,
280 mDefaultMemoryTypeInformation
,
281 sizeof(mDefaultMemoryTypeInformation
)
287 CbPeiReportRemainedFvs ();
289 BuildMemoryAllocationHob (
290 PcdGet32 (PcdPayloadFdMemBase
),
291 PcdGet32 (PcdPayloadFdMemSize
),
296 // Build CPU memory space and IO space hob
298 AsmCpuid (0x80000000, &RegEax
, NULL
, NULL
, NULL
);
299 if (RegEax
>= 0x80000008) {
300 AsmCpuid (0x80000008, &RegEax
, NULL
, NULL
, NULL
);
301 PhysicalAddressBits
= (UINT8
) RegEax
;
303 PhysicalAddressBits
= 36;
306 // Create a CPU hand-off information
308 BuildCpuHob (PhysicalAddressBits
, 16);
311 // Report Local APIC range
313 BuildMemoryMappedIoRangeHob (0xFEC80000, SIZE_512KB
);
318 Status
= PeiServicesSetBootMode (BOOT_WITH_FULL_CONFIGURATION
);
319 ASSERT_EFI_ERROR (Status
);
321 Status
= PeiServicesInstallPpi (mPpiBootMode
);
322 ASSERT_EFI_ERROR (Status
);
325 // Set pcd to save the upper coreboot header in case the dxecore will
329 if ((CbParseGetCbHeader (1, &pCbHeader
) == RETURN_SUCCESS
)
330 && ((UINTN
)pCbHeader
> BASE_4KB
)) {
331 DEBUG((EFI_D_ERROR
, "Actual Coreboot header: %p.\n", pCbHeader
));
332 PcdSet32 (PcdCbHeaderPointer
, (UINT32
)(UINTN
)pCbHeader
);
336 // Create guid hob for system tables like acpi table and smbios table
342 Status
= CbParseAcpiTable (&pAcpiTable
, &AcpiTableSize
);
343 if (EFI_ERROR (Status
)) {
344 // ACPI table is oblidgible
345 DEBUG ((EFI_D_ERROR
, "Failed to find the required acpi table\n"));
348 CbParseSmbiosTable (&pSmbiosTable
, &SmbiosTableSize
);
350 pSystemTableInfo
= NULL
;
351 pSystemTableInfo
= BuildGuidHob (&gUefiSystemTableInfoGuid
, sizeof (SYSTEM_TABLE_INFO
));
352 ASSERT (pSystemTableInfo
!= NULL
);
353 pSystemTableInfo
->AcpiTableBase
= (UINT64
) (UINTN
)pAcpiTable
;
354 pSystemTableInfo
->AcpiTableSize
= AcpiTableSize
;
355 pSystemTableInfo
->SmbiosTableBase
= (UINT64
) (UINTN
)pSmbiosTable
;
356 pSystemTableInfo
->SmbiosTableSize
= SmbiosTableSize
;
357 DEBUG ((EFI_D_ERROR
, "Detected Acpi Table at 0x%lx, length 0x%x\n", pSystemTableInfo
->AcpiTableBase
, pSystemTableInfo
->AcpiTableSize
));
358 DEBUG ((EFI_D_ERROR
, "Detected Smbios Table at 0x%lx, length 0x%x\n", pSystemTableInfo
->SmbiosTableBase
, pSystemTableInfo
->SmbiosTableSize
));
359 DEBUG ((EFI_D_ERROR
, "Create system table info guid hob\n"));
362 // Create guid hob for acpi board information
364 Status
= CbParseFadtInfo (&PmCtrlRegBase
, &PmTimerRegBase
, &ResetRegAddress
, &ResetValue
, &PmEvtBase
, &PmGpeEnBase
);
365 ASSERT_EFI_ERROR (Status
);
366 pAcpiBoardInfo
= NULL
;
367 pAcpiBoardInfo
= BuildGuidHob (&gUefiAcpiBoardInfoGuid
, sizeof (ACPI_BOARD_INFO
));
368 ASSERT (pAcpiBoardInfo
!= NULL
);
369 pAcpiBoardInfo
->PmCtrlRegBase
= (UINT64
)PmCtrlRegBase
;
370 pAcpiBoardInfo
->PmTimerRegBase
= (UINT64
)PmTimerRegBase
;
371 pAcpiBoardInfo
->ResetRegAddress
= (UINT64
)ResetRegAddress
;
372 pAcpiBoardInfo
->ResetValue
= (UINT8
)ResetValue
;
373 pAcpiBoardInfo
->PmEvtBase
= (UINT64
)PmEvtBase
;
374 pAcpiBoardInfo
->PmGpeEnBase
= (UINT64
)PmGpeEnBase
;
375 DEBUG ((EFI_D_ERROR
, "Create acpi board info guid hob\n"));
378 // Create guid hob for frame buffer information
380 ZeroMem (&FbInfo
, sizeof (FRAME_BUFFER_INFO
));
381 Status
= CbParseFbInfo (&FbInfo
);
382 if (!EFI_ERROR (Status
)) {
383 pFbInfo
= BuildGuidHob (&gUefiFrameBufferInfoGuid
, sizeof (FRAME_BUFFER_INFO
));
384 ASSERT (pSystemTableInfo
!= NULL
);
385 CopyMem (pFbInfo
, &FbInfo
, sizeof (FRAME_BUFFER_INFO
));
386 DEBUG ((EFI_D_ERROR
, "Create frame buffer info guid hob\n"));
390 // Mask off all legacy 8259 interrupt sources
392 IoWrite8 (LEGACY_8259_MASK_REGISTER_MASTER
, 0xFF);
393 IoWrite8 (LEGACY_8259_MASK_REGISTER_SLAVE
, 0xFF);