]> git.proxmox.com Git - mirror_edk2.git/blob - MdePkg/Library/PeiHobLib/HobLib.c
Update HobLib and PeCoffLib according to MDE Lib Spec 0.61c
[mirror_edk2.git] / MdePkg / Library / PeiHobLib / HobLib.c
1 /** @file
2 Provide Hob Library functions for Pei phase.
3
4 Copyright (c) 2007 - 2008, Intel Corporation<BR>
5 All rights reserved. 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
16 #include <PiPei.h>
17
18 #include <Guid/MemoryAllocationHob.h>
19
20 #include <Library/HobLib.h>
21 #include <Library/DebugLib.h>
22 #include <Library/PeiServicesLib.h>
23 #include <Library/BaseMemoryLib.h>
24
25 /**
26 Returns the pointer to the HOB list.
27 ASSERT() if the HOB list returned by GetHobList() is NULL.
28
29 This function returns the pointer to first HOB in the list.
30
31 @return The pointer to the HOB list.
32
33 **/
34 VOID *
35 EFIAPI
36 GetHobList (
37 VOID
38 )
39 {
40 EFI_STATUS Status;
41 VOID *HobList;
42
43 Status = PeiServicesGetHobList (&HobList);
44 ASSERT_EFI_ERROR (Status);
45 ASSERT (HobList != NULL);
46
47 return HobList;
48 }
49
50 /**
51 Returns the next instance of a HOB type from the starting HOB.
52
53 This function searches the first instance of a HOB type from the starting HOB pointer.
54 If there does not exist such HOB type from the starting HOB pointer, it will return NULL.
55 In contrast with macro GET_NEXT_HOB(), this function does not skip the starting HOB pointer
56 unconditionally: it returns HobStart back if HobStart itself meets the requirement;
57 caller is required to use GET_NEXT_HOB() if it wishes to skip current HobStart.
58 If HobStart is NULL, then ASSERT().
59
60 @param Type The HOB type to return.
61 @param HobStart The starting HOB pointer to search from.
62
63 @return The next instance of a HOB type from the starting HOB.
64
65 **/
66 VOID *
67 EFIAPI
68 GetNextHob (
69 IN UINT16 Type,
70 IN CONST VOID *HobStart
71 )
72 {
73 EFI_PEI_HOB_POINTERS Hob;
74
75 ASSERT (HobStart != NULL);
76
77 Hob.Raw = (UINT8 *) HobStart;
78 //
79 // Parse the HOB list until end of list or matching type is found.
80 //
81 while (!END_OF_HOB_LIST (Hob)) {
82 if (Hob.Header->HobType == Type) {
83 return Hob.Raw;
84 }
85 Hob.Raw = GET_NEXT_HOB (Hob);
86 }
87 return NULL;
88 }
89
90 /**
91 Returns the first instance of a HOB type among the whole HOB list.
92
93 This function searches the first instance of a HOB type among the whole HOB list.
94 If there does not exist such HOB type in the HOB list, it will return NULL.
95
96 @param Type The HOB type to return.
97
98 @return The next instance of a HOB type from the starting HOB.
99
100 **/
101 VOID *
102 EFIAPI
103 GetFirstHob (
104 IN UINT16 Type
105 )
106 {
107 VOID *HobList;
108
109 HobList = GetHobList ();
110 return GetNextHob (Type, HobList);
111 }
112
113 /**
114 This function searches the first instance of a HOB from the starting HOB pointer.
115 Such HOB should satisfy two conditions:
116 its HOB type is EFI_HOB_TYPE_GUID_EXTENSION and its GUID Name equals to the input Guid.
117 If there does not exist such HOB from the starting HOB pointer, it will return NULL.
118 Caller is required to apply GET_GUID_HOB_DATA () and GET_GUID_HOB_DATA_SIZE ()
119 to extract the data section and its size info respectively.
120 In contrast with macro GET_NEXT_HOB(), this function does not skip the starting HOB pointer
121 unconditionally: it returns HobStart back if HobStart itself meets the requirement;
122 caller is required to use GET_NEXT_HOB() if it wishes to skip current HobStart.
123 If Guid is NULL, then ASSERT().
124 If HobStart is NULL, then ASSERT().
125
126 @param Guid The GUID to match with in the HOB list.
127 @param HobStart A pointer to a Guid.
128
129 @return The next instance of the matched GUID HOB from the starting HOB.
130
131 **/
132 VOID *
133 EFIAPI
134 GetNextGuidHob (
135 IN CONST EFI_GUID *Guid,
136 IN CONST VOID *HobStart
137 )
138 {
139 EFI_PEI_HOB_POINTERS GuidHob;
140
141 GuidHob.Raw = (UINT8 *) HobStart;
142 while ((GuidHob.Raw = GetNextHob (EFI_HOB_TYPE_GUID_EXTENSION, GuidHob.Raw)) != NULL) {
143 if (CompareGuid (Guid, &GuidHob.Guid->Name)) {
144 break;
145 }
146 GuidHob.Raw = GET_NEXT_HOB (GuidHob);
147 }
148 return GuidHob.Raw;
149 }
150
151 /**
152 This function searches the first instance of a HOB among the whole HOB list.
153 Such HOB should satisfy two conditions:
154 its HOB type is EFI_HOB_TYPE_GUID_EXTENSION and its GUID Name equals to the input Guid.
155 If there does not exist such HOB from the starting HOB pointer, it will return NULL.
156 Caller is required to apply GET_GUID_HOB_DATA () and GET_GUID_HOB_DATA_SIZE ()
157 to extract the data section and its size info respectively.
158 If Guid is NULL, then ASSERT().
159
160 @param Guid The GUID to match with in the HOB list.
161
162 @return The first instance of the matched GUID HOB among the whole HOB list.
163
164 **/
165 VOID *
166 EFIAPI
167 GetFirstGuidHob (
168 IN CONST EFI_GUID *Guid
169 )
170 {
171 VOID *HobList;
172
173 HobList = GetHobList ();
174 return GetNextGuidHob (Guid, HobList);
175 }
176
177 /**
178 Get the Boot Mode from the HOB list.
179
180 This function returns the system boot mode information
181 by PeiCore GetBootMode Service.
182
183 @param VOID
184
185 @return The Boot Mode.
186
187 **/
188 EFI_BOOT_MODE
189 EFIAPI
190 GetBootModeHob (
191 VOID
192 )
193 {
194 EFI_STATUS Status;
195 EFI_BOOT_MODE BootMode;
196
197 Status = PeiServicesGetBootMode (&BootMode);
198 ASSERT_EFI_ERROR (Status);
199
200 return BootMode;
201 }
202
203 /**
204 Adds a new HOB to the HOB List.
205
206 This internal function enables PEIMs to create various types of HOBs.
207
208 @param Type Type of the new HOB.
209 @param Length Length of the new HOB to allocate.
210
211 @return The address of new HOB.
212
213 **/
214 VOID *
215 EFIAPI
216 InternalPeiCreateHob (
217 IN UINT16 Type,
218 IN UINT16 Length
219 )
220 {
221 EFI_STATUS Status;
222 VOID *Hob;
223
224 Status = PeiServicesCreateHob (Type, Length, &Hob);
225 //
226 // Assume the process of HOB building is always successful.
227 //
228 ASSERT_EFI_ERROR (Status);
229 return Hob;
230 }
231
232 /**
233 Builds a HOB for a loaded PE32 module.
234
235 This function builds a HOB for a loaded PE32 module.
236 It can only be invoked during PEI phase;
237 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
238 If ModuleName is NULL, then ASSERT().
239 If there is no additional space for HOB creation, then ASSERT().
240
241 @param ModuleName The GUID File Name of the module.
242 @param MemoryAllocationModule The 64 bit physical address of the module.
243 @param ModuleLength The length of the module in bytes.
244 @param EntryPoint The 64 bit physical address of the module's entry point.
245
246 **/
247 VOID
248 EFIAPI
249 BuildModuleHob (
250 IN CONST EFI_GUID *ModuleName,
251 IN EFI_PHYSICAL_ADDRESS MemoryAllocationModule,
252 IN UINT64 ModuleLength,
253 IN EFI_PHYSICAL_ADDRESS EntryPoint
254 )
255 {
256 EFI_HOB_MEMORY_ALLOCATION_MODULE *Hob;
257
258 ASSERT (((MemoryAllocationModule & (EFI_PAGE_SIZE - 1)) == 0) &&
259 ((ModuleLength & (EFI_PAGE_SIZE - 1)) == 0));
260
261 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_MEMORY_ALLOCATION, sizeof (EFI_HOB_MEMORY_ALLOCATION_MODULE));
262
263 CopyGuid (&(Hob->MemoryAllocationHeader.Name), &gEfiHobMemoryAllocModuleGuid);
264 Hob->MemoryAllocationHeader.MemoryBaseAddress = MemoryAllocationModule;
265 Hob->MemoryAllocationHeader.MemoryLength = ModuleLength;
266 Hob->MemoryAllocationHeader.MemoryType = EfiBootServicesCode;
267
268 //
269 // Zero the reserved space to match HOB spec
270 //
271 ZeroMem (Hob->MemoryAllocationHeader.Reserved, sizeof (Hob->MemoryAllocationHeader.Reserved));
272
273 CopyGuid (&Hob->ModuleName, ModuleName);
274 Hob->EntryPoint = EntryPoint;
275 }
276
277 /**
278 Builds a HOB that describes a chunk of system memory.
279
280 This function builds a HOB that describes a chunk of system memory.
281 It can only be invoked during PEI phase;
282 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
283 If there is no additional space for HOB creation, then ASSERT().
284
285 @param ResourceType The type of resource described by this HOB.
286 @param ResourceAttribute The resource attributes of the memory described by this HOB.
287 @param PhysicalStart The 64 bit physical address of memory described by this HOB.
288 @param NumberOfBytes The length of the memory described by this HOB in bytes.
289
290 **/
291 VOID
292 EFIAPI
293 BuildResourceDescriptorHob (
294 IN EFI_RESOURCE_TYPE ResourceType,
295 IN EFI_RESOURCE_ATTRIBUTE_TYPE ResourceAttribute,
296 IN EFI_PHYSICAL_ADDRESS PhysicalStart,
297 IN UINT64 NumberOfBytes
298 )
299 {
300 EFI_HOB_RESOURCE_DESCRIPTOR *Hob;
301
302 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_RESOURCE_DESCRIPTOR, sizeof (EFI_HOB_RESOURCE_DESCRIPTOR));
303
304 Hob->ResourceType = ResourceType;
305 Hob->ResourceAttribute = ResourceAttribute;
306 Hob->PhysicalStart = PhysicalStart;
307 Hob->ResourceLength = NumberOfBytes;
308 }
309
310 /**
311 Builds a GUID HOB with a certain data length.
312
313 This function builds a customized HOB tagged with a GUID for identification
314 and returns the start address of GUID HOB data so that caller can fill the customized data.
315 The HOB Header and Name field is already stripped.
316 It can only be invoked during PEI phase;
317 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
318 If Guid is NULL, then ASSERT().
319 If there is no additional space for HOB creation, then ASSERT().
320 If DataLength >= (0x10000 - sizeof (EFI_HOB_GUID_TYPE)), then ASSERT().
321
322 @param Guid The GUID to tag the customized HOB.
323 @param DataLength The size of the data payload for the GUID HOB.
324
325 @return The start address of GUID HOB data.
326
327 **/
328 VOID *
329 EFIAPI
330 BuildGuidHob (
331 IN CONST EFI_GUID *Guid,
332 IN UINTN DataLength
333 )
334 {
335 EFI_HOB_GUID_TYPE *Hob;
336
337 //
338 // Make sure that data length is not too long.
339 //
340 ASSERT (DataLength <= (0xffff - sizeof (EFI_HOB_GUID_TYPE)));
341
342 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_GUID_EXTENSION, (UINT16) (sizeof (EFI_HOB_GUID_TYPE) + DataLength));
343 CopyGuid (&Hob->Name, Guid);
344 return Hob + 1;
345 }
346
347 /**
348 Copies a data buffer to a newly-built HOB.
349
350 This function builds a customized HOB tagged with a GUID for identification,
351 copies the input data to the HOB data field and returns the start address of the GUID HOB data.
352 The HOB Header and Name field is already stripped.
353 It can only be invoked during PEI phase;
354 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
355 If Guid is NULL, then ASSERT().
356 If Data is NULL and DataLength > 0, then ASSERT().
357 If there is no additional space for HOB creation, then ASSERT().
358 If DataLength >= (0x10000 - sizeof (EFI_HOB_GUID_TYPE)), then ASSERT().
359
360 @param Guid The GUID to tag the customized HOB.
361 @param Data The data to be copied into the data field of the GUID HOB.
362 @param DataLength The size of the data payload for the GUID HOB.
363
364 @return The start address of GUID HOB data.
365
366 **/
367 VOID *
368 EFIAPI
369 BuildGuidDataHob (
370 IN CONST EFI_GUID *Guid,
371 IN VOID *Data,
372 IN UINTN DataLength
373 )
374 {
375 VOID *HobData;
376
377 ASSERT (Data != NULL || DataLength == 0);
378
379 HobData = BuildGuidHob (Guid, DataLength);
380
381 return CopyMem (HobData, Data, DataLength);
382 }
383
384 /**
385 Builds a Firmware Volume HOB.
386
387 This function builds a Firmware Volume HOB.
388 It can only be invoked during PEI phase;
389 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
390 If there is no additional space for HOB creation, then ASSERT().
391
392 @param BaseAddress The base address of the Firmware Volume.
393 @param Length The size of the Firmware Volume in bytes.
394
395 **/
396 VOID
397 EFIAPI
398 BuildFvHob (
399 IN EFI_PHYSICAL_ADDRESS BaseAddress,
400 IN UINT64 Length
401 )
402 {
403 EFI_HOB_FIRMWARE_VOLUME *Hob;
404
405 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_FV, sizeof (EFI_HOB_FIRMWARE_VOLUME));
406
407 Hob->BaseAddress = BaseAddress;
408 Hob->Length = Length;
409 }
410
411 /**
412 Builds a EFI_HOB_TYPE_FV2 HOB.
413
414 This function builds a EFI_HOB_TYPE_FV2 HOB.
415 It can only be invoked during PEI phase;
416 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
417 If there is no additional space for HOB creation, then ASSERT().
418
419 @param BaseAddress The base address of the Firmware Volume.
420 @param Length The size of the Firmware Volume in bytes.
421 @param FvName The name of the Firmware Volume.
422 @param FileName The name of the file.
423
424 **/
425 VOID
426 EFIAPI
427 BuildFv2Hob (
428 IN EFI_PHYSICAL_ADDRESS BaseAddress,
429 IN UINT64 Length,
430 IN CONST EFI_GUID *FvName,
431 IN CONST EFI_GUID *FileName
432 )
433 {
434 EFI_HOB_FIRMWARE_VOLUME2 *Hob;
435
436 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_FV2, sizeof (EFI_HOB_FIRMWARE_VOLUME2));
437
438 Hob->BaseAddress = BaseAddress;
439 Hob->Length = Length;
440 CopyGuid (&Hob->FvName, FvName);
441 CopyGuid (&Hob->FileName, FileName);
442 }
443
444 /**
445 Builds a Capsule Volume HOB.
446
447 This function is not supported, because Capsule Volume Hob is the platform
448 specific. It is not the common defintion in PI and UEFI spec.
449
450 **/
451 VOID
452 EFIAPI
453 BuildCvHob (
454 IN EFI_PHYSICAL_ADDRESS BaseAddress,
455 IN UINT64 Length
456 )
457 {
458 ASSERT (FALSE);
459 }
460
461 /**
462 Builds a HOB for the CPU.
463
464 This function builds a HOB for the CPU.
465 It can only be invoked during PEI phase;
466 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
467 If there is no additional space for HOB creation, then ASSERT().
468
469 @param SizeOfMemorySpace The maximum physical memory addressability of the processor.
470 @param SizeOfIoSpace The maximum physical I/O addressability of the processor.
471
472 **/
473 VOID
474 EFIAPI
475 BuildCpuHob (
476 IN UINT8 SizeOfMemorySpace,
477 IN UINT8 SizeOfIoSpace
478 )
479 {
480 EFI_HOB_CPU *Hob;
481
482 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_CPU, sizeof (EFI_HOB_CPU));
483
484 Hob->SizeOfMemorySpace = SizeOfMemorySpace;
485 Hob->SizeOfIoSpace = SizeOfIoSpace;
486
487 //
488 // Zero the reserved space to match HOB spec
489 //
490 ZeroMem (Hob->Reserved, sizeof (Hob->Reserved));
491 }
492
493 /**
494 Builds a HOB for the Stack.
495
496 This function builds a HOB for the stack.
497 It can only be invoked during PEI phase;
498 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
499 If there is no additional space for HOB creation, then ASSERT().
500
501 @param BaseAddress The 64 bit physical address of the Stack.
502 @param Length The length of the stack in bytes.
503
504 **/
505 VOID
506 EFIAPI
507 BuildStackHob (
508 IN EFI_PHYSICAL_ADDRESS BaseAddress,
509 IN UINT64 Length
510 )
511 {
512 EFI_HOB_MEMORY_ALLOCATION_STACK *Hob;
513
514 ASSERT (((BaseAddress & (EFI_PAGE_SIZE - 1)) == 0) &&
515 ((Length & (EFI_PAGE_SIZE - 1)) == 0));
516
517 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_MEMORY_ALLOCATION, sizeof (EFI_HOB_MEMORY_ALLOCATION_STACK));
518
519 CopyGuid (&(Hob->AllocDescriptor.Name), &gEfiHobMemoryAllocStackGuid);
520 Hob->AllocDescriptor.MemoryBaseAddress = BaseAddress;
521 Hob->AllocDescriptor.MemoryLength = Length;
522 Hob->AllocDescriptor.MemoryType = EfiBootServicesData;
523
524 //
525 // Zero the reserved space to match HOB spec
526 //
527 ZeroMem (Hob->AllocDescriptor.Reserved, sizeof (Hob->AllocDescriptor.Reserved));
528 }
529
530 /**
531 Builds a HOB for the BSP store.
532
533 This function builds a HOB for BSP store.
534 It can only be invoked during PEI phase;
535 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
536 If there is no additional space for HOB creation, then ASSERT().
537
538 @param BaseAddress The 64 bit physical address of the BSP.
539 @param Length The length of the BSP store in bytes.
540 @param MemoryType Type of memory allocated by this HOB.
541
542 **/
543 VOID
544 EFIAPI
545 BuildBspStoreHob (
546 IN EFI_PHYSICAL_ADDRESS BaseAddress,
547 IN UINT64 Length,
548 IN EFI_MEMORY_TYPE MemoryType
549 )
550 {
551 EFI_HOB_MEMORY_ALLOCATION_BSP_STORE *Hob;
552
553 ASSERT (((BaseAddress & (EFI_PAGE_SIZE - 1)) == 0) &&
554 ((Length & (EFI_PAGE_SIZE - 1)) == 0));
555
556 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_MEMORY_ALLOCATION, sizeof (EFI_HOB_MEMORY_ALLOCATION_BSP_STORE));
557
558 CopyGuid (&(Hob->AllocDescriptor.Name), &gEfiHobMemoryAllocBspStoreGuid);
559 Hob->AllocDescriptor.MemoryBaseAddress = BaseAddress;
560 Hob->AllocDescriptor.MemoryLength = Length;
561 Hob->AllocDescriptor.MemoryType = MemoryType;
562
563 //
564 // Zero the reserved space to match HOB spec
565 //
566 ZeroMem (Hob->AllocDescriptor.Reserved, sizeof (Hob->AllocDescriptor.Reserved));
567 }
568
569 /**
570 Builds a HOB for the memory allocation.
571
572 This function builds a HOB for the memory allocation.
573 It can only be invoked during PEI phase;
574 for DXE phase, it will ASSERT() since PEI HOB is read-only for DXE phase.
575 If there is no additional space for HOB creation, then ASSERT().
576
577 @param BaseAddress The 64 bit physical address of the memory.
578 @param Length The length of the memory allocation in bytes.
579 @param MemoryType Type of memory allocated by this HOB.
580
581 **/
582 VOID
583 EFIAPI
584 BuildMemoryAllocationHob (
585 IN EFI_PHYSICAL_ADDRESS BaseAddress,
586 IN UINT64 Length,
587 IN EFI_MEMORY_TYPE MemoryType
588 )
589 {
590 EFI_HOB_MEMORY_ALLOCATION *Hob;
591
592 ASSERT (((BaseAddress & (EFI_PAGE_SIZE - 1)) == 0) &&
593 ((Length & (EFI_PAGE_SIZE - 1)) == 0));
594
595 Hob = InternalPeiCreateHob (EFI_HOB_TYPE_MEMORY_ALLOCATION, sizeof (EFI_HOB_MEMORY_ALLOCATION));
596
597 ZeroMem (&(Hob->AllocDescriptor.Name), sizeof (EFI_GUID));
598 Hob->AllocDescriptor.MemoryBaseAddress = BaseAddress;
599 Hob->AllocDescriptor.MemoryLength = Length;
600 Hob->AllocDescriptor.MemoryType = MemoryType;
601 //
602 // Zero the reserved space to match HOB spec
603 //
604 ZeroMem (Hob->AllocDescriptor.Reserved, sizeof (Hob->AllocDescriptor.Reserved));
605 }