2 Decode a hard disk partitioned with the GPT scheme in the UEFI 2.0
5 Caution: This file requires additional review when modified.
6 This driver will have external input - disk partition.
7 This external input must be validated carefully to avoid security issue like
8 buffer overflow, integer overflow.
10 PartitionInstallGptChildHandles() routine will read disk partition content and
11 do basic validation before PartitionInstallChildHandle().
13 PartitionValidGptTable(), PartitionCheckGptEntry() routine will accept disk
14 partition content and validate the GPT table and GPT entry.
16 Copyright (c) 2006 - 2013, Intel Corporation. All rights reserved.<BR>
17 This program and the accompanying materials
18 are licensed and made available under the terms and conditions of the BSD License
19 which accompanies this distribution. The full text of the license may be found at
20 http://opensource.org/licenses/bsd-license.php
22 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
23 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
28 #include "Partition.h"
31 Install child handles if the Handle supports GPT partition structure.
33 Caution: This function may receive untrusted input.
34 The GPT partition table header is external input, so this routine
35 will do basic validation for GPT partition table header before return.
37 @param[in] BlockIo Parent BlockIo interface.
38 @param[in] DiskIo Disk Io protocol.
39 @param[in] Lba The starting Lba of the Partition Table
40 @param[out] PartHeader Stores the partition table that is read
42 @retval TRUE The partition table is valid
43 @retval FALSE The partition table is not valid
47 PartitionValidGptTable (
48 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
49 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
51 OUT EFI_PARTITION_TABLE_HEADER
*PartHeader
55 Check if the CRC field in the Partition table header is valid
56 for Partition entry array.
58 @param[in] BlockIo Parent BlockIo interface
59 @param[in] DiskIo Disk Io Protocol.
60 @param[in] PartHeader Partition table header structure
62 @retval TRUE the CRC is valid
63 @retval FALSE the CRC is invalid
67 PartitionCheckGptEntryArrayCRC (
68 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
69 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
70 IN EFI_PARTITION_TABLE_HEADER
*PartHeader
75 Restore Partition Table to its alternate place
76 (Primary -> Backup or Backup -> Primary).
78 @param[in] BlockIo Parent BlockIo interface.
79 @param[in] DiskIo Disk Io Protocol.
80 @param[in] PartHeader Partition table header structure.
82 @retval TRUE Restoring succeeds
83 @retval FALSE Restoring failed
87 PartitionRestoreGptTable (
88 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
89 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
90 IN EFI_PARTITION_TABLE_HEADER
*PartHeader
95 This routine will check GPT partition entry and return entry status.
97 Caution: This function may receive untrusted input.
98 The GPT partition entry is external input, so this routine
99 will do basic validation for GPT partition entry and report status.
101 @param[in] PartHeader Partition table header structure
102 @param[in] PartEntry The partition entry array
103 @param[out] PEntryStatus the partition entry status array
104 recording the status of each partition
108 PartitionCheckGptEntry (
109 IN EFI_PARTITION_TABLE_HEADER
*PartHeader
,
110 IN EFI_PARTITION_ENTRY
*PartEntry
,
111 OUT EFI_PARTITION_ENTRY_STATUS
*PEntryStatus
116 Checks the CRC32 value in the table header.
118 @param MaxSize Max Size limit
119 @param Size The size of the table
120 @param Hdr Table to check
122 @return TRUE CRC Valid
123 @return FALSE CRC Invalid
127 PartitionCheckCrcAltSize (
130 IN OUT EFI_TABLE_HEADER
*Hdr
135 Checks the CRC32 value in the table header.
137 @param MaxSize Max Size limit
138 @param Hdr Table to check
140 @return TRUE CRC Valid
141 @return FALSE CRC Invalid
147 IN OUT EFI_TABLE_HEADER
*Hdr
152 Updates the CRC32 value in the table header.
154 @param Size The size of the table
155 @param Hdr Table to update
159 PartitionSetCrcAltSize (
161 IN OUT EFI_TABLE_HEADER
*Hdr
166 Updates the CRC32 value in the table header.
168 @param Hdr Table to update
173 IN OUT EFI_TABLE_HEADER
*Hdr
177 Install child handles if the Handle supports GPT partition structure.
179 Caution: This function may receive untrusted input.
180 The GPT partition table is external input, so this routine
181 will do basic validation for GPT partition table before install
182 child handle for each GPT partition.
184 @param[in] This Calling context.
185 @param[in] Handle Parent Handle.
186 @param[in] DiskIo Parent DiskIo interface.
187 @param[in] BlockIo Parent BlockIo interface.
188 @param[in] BlockIo2 Parent BlockIo2 interface.
189 @param[in] DevicePath Parent Device Path.
191 @retval EFI_SUCCESS Valid GPT disk.
192 @retval EFI_MEDIA_CHANGED Media changed Detected.
193 @retval other Not a valid GPT disk.
197 PartitionInstallGptChildHandles (
198 IN EFI_DRIVER_BINDING_PROTOCOL
*This
,
199 IN EFI_HANDLE Handle
,
200 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
201 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
202 IN EFI_BLOCK_IO2_PROTOCOL
*BlockIo2
,
203 IN EFI_DEVICE_PATH_PROTOCOL
*DevicePath
209 MASTER_BOOT_RECORD
*ProtectiveMbr
;
210 EFI_PARTITION_TABLE_HEADER
*PrimaryHeader
;
211 EFI_PARTITION_TABLE_HEADER
*BackupHeader
;
212 EFI_PARTITION_ENTRY
*PartEntry
;
213 EFI_PARTITION_ENTRY
*Entry
;
214 EFI_PARTITION_ENTRY_STATUS
*PEntryStatus
;
216 EFI_STATUS GptValidStatus
;
217 HARDDRIVE_DEVICE_PATH HdDev
;
220 ProtectiveMbr
= NULL
;
221 PrimaryHeader
= NULL
;
226 BlockSize
= BlockIo
->Media
->BlockSize
;
227 LastBlock
= BlockIo
->Media
->LastBlock
;
228 MediaId
= BlockIo
->Media
->MediaId
;
230 DEBUG ((EFI_D_INFO
, " BlockSize : %d \n", BlockSize
));
231 DEBUG ((EFI_D_INFO
, " LastBlock : %lx \n", LastBlock
));
233 GptValidStatus
= EFI_NOT_FOUND
;
236 // Allocate a buffer for the Protective MBR
238 ProtectiveMbr
= AllocatePool (BlockSize
);
239 if (ProtectiveMbr
== NULL
) {
240 return EFI_NOT_FOUND
;
244 // Read the Protective MBR from LBA #0
246 Status
= DiskIo
->ReadDisk (
253 if (EFI_ERROR (Status
)) {
254 GptValidStatus
= Status
;
259 // Verify that the Protective MBR is valid
261 for (Index
= 0; Index
< MAX_MBR_PARTITIONS
; Index
++) {
262 if (ProtectiveMbr
->Partition
[Index
].BootIndicator
== 0x00 &&
263 ProtectiveMbr
->Partition
[Index
].OSIndicator
== PMBR_GPT_PARTITION
&&
264 UNPACK_UINT32 (ProtectiveMbr
->Partition
[Index
].StartingLBA
) == 1
269 if (Index
== MAX_MBR_PARTITIONS
) {
274 // Allocate the GPT structures
276 PrimaryHeader
= AllocateZeroPool (sizeof (EFI_PARTITION_TABLE_HEADER
));
277 if (PrimaryHeader
== NULL
) {
281 BackupHeader
= AllocateZeroPool (sizeof (EFI_PARTITION_TABLE_HEADER
));
282 if (BackupHeader
== NULL
) {
287 // Check primary and backup partition tables
289 if (!PartitionValidGptTable (BlockIo
, DiskIo
, PRIMARY_PART_HEADER_LBA
, PrimaryHeader
)) {
290 DEBUG ((EFI_D_INFO
, " Not Valid primary partition table\n"));
292 if (!PartitionValidGptTable (BlockIo
, DiskIo
, LastBlock
, BackupHeader
)) {
293 DEBUG ((EFI_D_INFO
, " Not Valid backup partition table\n"));
296 DEBUG ((EFI_D_INFO
, " Valid backup partition table\n"));
297 DEBUG ((EFI_D_INFO
, " Restore primary partition table by the backup\n"));
298 if (!PartitionRestoreGptTable (BlockIo
, DiskIo
, BackupHeader
)) {
299 DEBUG ((EFI_D_INFO
, " Restore primary partition table error\n"));
302 if (PartitionValidGptTable (BlockIo
, DiskIo
, BackupHeader
->AlternateLBA
, PrimaryHeader
)) {
303 DEBUG ((EFI_D_INFO
, " Restore backup partition table success\n"));
306 } else if (!PartitionValidGptTable (BlockIo
, DiskIo
, PrimaryHeader
->AlternateLBA
, BackupHeader
)) {
307 DEBUG ((EFI_D_INFO
, " Valid primary and !Valid backup partition table\n"));
308 DEBUG ((EFI_D_INFO
, " Restore backup partition table by the primary\n"));
309 if (!PartitionRestoreGptTable (BlockIo
, DiskIo
, PrimaryHeader
)) {
310 DEBUG ((EFI_D_INFO
, " Restore backup partition table error\n"));
313 if (PartitionValidGptTable (BlockIo
, DiskIo
, PrimaryHeader
->AlternateLBA
, BackupHeader
)) {
314 DEBUG ((EFI_D_INFO
, " Restore backup partition table success\n"));
319 DEBUG ((EFI_D_INFO
, " Valid primary and Valid backup partition table\n"));
322 // Read the EFI Partition Entries
324 PartEntry
= AllocatePool (PrimaryHeader
->NumberOfPartitionEntries
* PrimaryHeader
->SizeOfPartitionEntry
);
325 if (PartEntry
== NULL
) {
326 DEBUG ((EFI_D_ERROR
, "Allocate pool error\n"));
330 Status
= DiskIo
->ReadDisk (
333 MultU64x32(PrimaryHeader
->PartitionEntryLBA
, BlockSize
),
334 PrimaryHeader
->NumberOfPartitionEntries
* (PrimaryHeader
->SizeOfPartitionEntry
),
337 if (EFI_ERROR (Status
)) {
338 GptValidStatus
= Status
;
339 DEBUG ((EFI_D_ERROR
, " Partition Entry ReadDisk error\n"));
343 DEBUG ((EFI_D_INFO
, " Partition entries read block success\n"));
345 DEBUG ((EFI_D_INFO
, " Number of partition entries: %d\n", PrimaryHeader
->NumberOfPartitionEntries
));
347 PEntryStatus
= AllocateZeroPool (PrimaryHeader
->NumberOfPartitionEntries
* sizeof (EFI_PARTITION_ENTRY_STATUS
));
348 if (PEntryStatus
== NULL
) {
349 DEBUG ((EFI_D_ERROR
, "Allocate pool error\n"));
354 // Check the integrity of partition entries
356 PartitionCheckGptEntry (PrimaryHeader
, PartEntry
, PEntryStatus
);
359 // If we got this far the GPT layout of the disk is valid and we should return true
361 GptValidStatus
= EFI_SUCCESS
;
364 // Create child device handles
366 for (Index
= 0; Index
< PrimaryHeader
->NumberOfPartitionEntries
; Index
++) {
367 Entry
= (EFI_PARTITION_ENTRY
*) ((UINT8
*) PartEntry
+ Index
* PrimaryHeader
->SizeOfPartitionEntry
);
368 if (CompareGuid (&Entry
->PartitionTypeGUID
, &gEfiPartTypeUnusedGuid
) ||
369 PEntryStatus
[Index
].OutOfRange
||
370 PEntryStatus
[Index
].Overlap
||
371 PEntryStatus
[Index
].OsSpecific
374 // Don't use null EFI Partition Entries, Invalid Partition Entries or OS specific
380 ZeroMem (&HdDev
, sizeof (HdDev
));
381 HdDev
.Header
.Type
= MEDIA_DEVICE_PATH
;
382 HdDev
.Header
.SubType
= MEDIA_HARDDRIVE_DP
;
383 SetDevicePathNodeLength (&HdDev
.Header
, sizeof (HdDev
));
385 HdDev
.PartitionNumber
= (UINT32
) Index
+ 1;
386 HdDev
.MBRType
= MBR_TYPE_EFI_PARTITION_TABLE_HEADER
;
387 HdDev
.SignatureType
= SIGNATURE_TYPE_GUID
;
388 HdDev
.PartitionStart
= Entry
->StartingLBA
;
389 HdDev
.PartitionSize
= Entry
->EndingLBA
- Entry
->StartingLBA
+ 1;
390 CopyMem (HdDev
.Signature
, &Entry
->UniquePartitionGUID
, sizeof (EFI_GUID
));
392 DEBUG ((EFI_D_INFO
, " Index : %d\n", (UINT32
) Index
));
393 DEBUG ((EFI_D_INFO
, " Start LBA : %lx\n", (UINT64
) HdDev
.PartitionStart
));
394 DEBUG ((EFI_D_INFO
, " End LBA : %lx\n", (UINT64
) Entry
->EndingLBA
));
395 DEBUG ((EFI_D_INFO
, " Partition size: %lx\n", (UINT64
) HdDev
.PartitionSize
));
396 DEBUG ((EFI_D_INFO
, " Start : %lx", MultU64x32 (Entry
->StartingLBA
, BlockSize
)));
397 DEBUG ((EFI_D_INFO
, " End : %lx\n", MultU64x32 (Entry
->EndingLBA
, BlockSize
)));
399 Status
= PartitionInstallChildHandle (
406 (EFI_DEVICE_PATH_PROTOCOL
*) &HdDev
,
410 CompareGuid(&Entry
->PartitionTypeGUID
, &gEfiPartTypeSystemPartGuid
)
414 DEBUG ((EFI_D_INFO
, "Prepare to Free Pool\n"));
417 if (ProtectiveMbr
!= NULL
) {
418 FreePool (ProtectiveMbr
);
420 if (PrimaryHeader
!= NULL
) {
421 FreePool (PrimaryHeader
);
423 if (BackupHeader
!= NULL
) {
424 FreePool (BackupHeader
);
426 if (PartEntry
!= NULL
) {
427 FreePool (PartEntry
);
429 if (PEntryStatus
!= NULL
) {
430 FreePool (PEntryStatus
);
433 return GptValidStatus
;
437 This routine will read GPT partition table header and return it.
439 Caution: This function may receive untrusted input.
440 The GPT partition table header is external input, so this routine
441 will do basic validation for GPT partition table header before return.
443 @param[in] BlockIo Parent BlockIo interface.
444 @param[in] DiskIo Disk Io protocol.
445 @param[in] Lba The starting Lba of the Partition Table
446 @param[out] PartHeader Stores the partition table that is read
448 @retval TRUE The partition table is valid
449 @retval FALSE The partition table is not valid
453 PartitionValidGptTable (
454 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
455 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
457 OUT EFI_PARTITION_TABLE_HEADER
*PartHeader
462 EFI_PARTITION_TABLE_HEADER
*PartHdr
;
465 BlockSize
= BlockIo
->Media
->BlockSize
;
466 MediaId
= BlockIo
->Media
->MediaId
;
467 PartHdr
= AllocateZeroPool (BlockSize
);
469 if (PartHdr
== NULL
) {
470 DEBUG ((EFI_D_ERROR
, "Allocate pool error\n"));
474 // Read the EFI Partition Table Header
476 Status
= DiskIo
->ReadDisk (
479 MultU64x32 (Lba
, BlockSize
),
483 if (EFI_ERROR (Status
)) {
488 if ((PartHdr
->Header
.Signature
!= EFI_PTAB_HEADER_ID
) ||
489 !PartitionCheckCrc (BlockSize
, &PartHdr
->Header
) ||
490 PartHdr
->MyLBA
!= Lba
||
491 (PartHdr
->SizeOfPartitionEntry
< sizeof (EFI_PARTITION_ENTRY
))
493 DEBUG ((EFI_D_INFO
, "Invalid efi partition table header\n"));
499 // Ensure the NumberOfPartitionEntries * SizeOfPartitionEntry doesn't overflow.
501 if (PartHdr
->NumberOfPartitionEntries
> DivU64x32 (MAX_UINTN
, PartHdr
->SizeOfPartitionEntry
)) {
506 CopyMem (PartHeader
, PartHdr
, sizeof (EFI_PARTITION_TABLE_HEADER
));
507 if (!PartitionCheckGptEntryArrayCRC (BlockIo
, DiskIo
, PartHeader
)) {
512 DEBUG ((EFI_D_INFO
, " Valid efi partition table header\n"));
518 Check if the CRC field in the Partition table header is valid
519 for Partition entry array.
521 @param[in] BlockIo Parent BlockIo interface
522 @param[in] DiskIo Disk Io Protocol.
523 @param[in] PartHeader Partition table header structure
525 @retval TRUE the CRC is valid
526 @retval FALSE the CRC is invalid
530 PartitionCheckGptEntryArrayCRC (
531 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
532 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
533 IN EFI_PARTITION_TABLE_HEADER
*PartHeader
542 // Read the EFI Partition Entries
544 Ptr
= AllocatePool (PartHeader
->NumberOfPartitionEntries
* PartHeader
->SizeOfPartitionEntry
);
546 DEBUG ((EFI_D_ERROR
, " Allocate pool error\n"));
550 Status
= DiskIo
->ReadDisk (
552 BlockIo
->Media
->MediaId
,
553 MultU64x32(PartHeader
->PartitionEntryLBA
, BlockIo
->Media
->BlockSize
),
554 PartHeader
->NumberOfPartitionEntries
* PartHeader
->SizeOfPartitionEntry
,
557 if (EFI_ERROR (Status
)) {
562 Size
= PartHeader
->NumberOfPartitionEntries
* PartHeader
->SizeOfPartitionEntry
;
564 Status
= gBS
->CalculateCrc32 (Ptr
, Size
, &Crc
);
565 if (EFI_ERROR (Status
)) {
566 DEBUG ((EFI_D_ERROR
, "CheckPEntryArrayCRC: Crc calculation failed\n"));
573 return (BOOLEAN
) (PartHeader
->PartitionEntryArrayCRC32
== Crc
);
578 Restore Partition Table to its alternate place
579 (Primary -> Backup or Backup -> Primary).
581 @param[in] BlockIo Parent BlockIo interface.
582 @param[in] DiskIo Disk Io Protocol.
583 @param[in] PartHeader Partition table header structure.
585 @retval TRUE Restoring succeeds
586 @retval FALSE Restoring failed
590 PartitionRestoreGptTable (
591 IN EFI_BLOCK_IO_PROTOCOL
*BlockIo
,
592 IN EFI_DISK_IO_PROTOCOL
*DiskIo
,
593 IN EFI_PARTITION_TABLE_HEADER
*PartHeader
598 EFI_PARTITION_TABLE_HEADER
*PartHdr
;
606 BlockSize
= BlockIo
->Media
->BlockSize
;
607 MediaId
= BlockIo
->Media
->MediaId
;
609 PartHdr
= AllocateZeroPool (BlockSize
);
611 if (PartHdr
== NULL
) {
612 DEBUG ((EFI_D_ERROR
, "Allocate pool error\n"));
616 PEntryLBA
= (PartHeader
->MyLBA
== PRIMARY_PART_HEADER_LBA
) ? \
617 (PartHeader
->LastUsableLBA
+ 1) : \
618 (PRIMARY_PART_HEADER_LBA
+ 1);
620 CopyMem (PartHdr
, PartHeader
, sizeof (EFI_PARTITION_TABLE_HEADER
));
622 PartHdr
->MyLBA
= PartHeader
->AlternateLBA
;
623 PartHdr
->AlternateLBA
= PartHeader
->MyLBA
;
624 PartHdr
->PartitionEntryLBA
= PEntryLBA
;
625 PartitionSetCrc ((EFI_TABLE_HEADER
*) PartHdr
);
627 Status
= DiskIo
->WriteDisk (
630 MultU64x32 (PartHdr
->MyLBA
, (UINT32
) BlockSize
),
634 if (EFI_ERROR (Status
)) {
638 Ptr
= AllocatePool (PartHeader
->NumberOfPartitionEntries
* PartHeader
->SizeOfPartitionEntry
);
640 DEBUG ((EFI_D_ERROR
, " Allocate pool error\n"));
641 Status
= EFI_OUT_OF_RESOURCES
;
645 Status
= DiskIo
->ReadDisk (
648 MultU64x32(PartHeader
->PartitionEntryLBA
, (UINT32
) BlockSize
),
649 PartHeader
->NumberOfPartitionEntries
* PartHeader
->SizeOfPartitionEntry
,
652 if (EFI_ERROR (Status
)) {
656 Status
= DiskIo
->WriteDisk (
659 MultU64x32(PEntryLBA
, (UINT32
) BlockSize
),
660 PartHeader
->NumberOfPartitionEntries
* PartHeader
->SizeOfPartitionEntry
,
671 if (EFI_ERROR (Status
)) {
679 This routine will check GPT partition entry and return entry status.
681 Caution: This function may receive untrusted input.
682 The GPT partition entry is external input, so this routine
683 will do basic validation for GPT partition entry and report status.
685 @param[in] PartHeader Partition table header structure
686 @param[in] PartEntry The partition entry array
687 @param[out] PEntryStatus the partition entry status array
688 recording the status of each partition
692 PartitionCheckGptEntry (
693 IN EFI_PARTITION_TABLE_HEADER
*PartHeader
,
694 IN EFI_PARTITION_ENTRY
*PartEntry
,
695 OUT EFI_PARTITION_ENTRY_STATUS
*PEntryStatus
700 EFI_PARTITION_ENTRY
*Entry
;
704 DEBUG ((EFI_D_INFO
, " start check partition entries\n"));
705 for (Index1
= 0; Index1
< PartHeader
->NumberOfPartitionEntries
; Index1
++) {
706 Entry
= (EFI_PARTITION_ENTRY
*) ((UINT8
*) PartEntry
+ Index1
* PartHeader
->SizeOfPartitionEntry
);
707 if (CompareGuid (&Entry
->PartitionTypeGUID
, &gEfiPartTypeUnusedGuid
)) {
711 StartingLBA
= Entry
->StartingLBA
;
712 EndingLBA
= Entry
->EndingLBA
;
713 if (StartingLBA
> EndingLBA
||
714 StartingLBA
< PartHeader
->FirstUsableLBA
||
715 StartingLBA
> PartHeader
->LastUsableLBA
||
716 EndingLBA
< PartHeader
->FirstUsableLBA
||
717 EndingLBA
> PartHeader
->LastUsableLBA
719 PEntryStatus
[Index1
].OutOfRange
= TRUE
;
723 if ((Entry
->Attributes
& BIT1
) != 0) {
725 // If Bit 1 is set, this indicate that this is an OS specific GUID partition.
727 PEntryStatus
[Index1
].OsSpecific
= TRUE
;
730 for (Index2
= Index1
+ 1; Index2
< PartHeader
->NumberOfPartitionEntries
; Index2
++) {
731 Entry
= (EFI_PARTITION_ENTRY
*) ((UINT8
*) PartEntry
+ Index2
* PartHeader
->SizeOfPartitionEntry
);
732 if (CompareGuid (&Entry
->PartitionTypeGUID
, &gEfiPartTypeUnusedGuid
)) {
736 if (Entry
->EndingLBA
>= StartingLBA
&& Entry
->StartingLBA
<= EndingLBA
) {
738 // This region overlaps with the Index1'th region
740 PEntryStatus
[Index1
].Overlap
= TRUE
;
741 PEntryStatus
[Index2
].Overlap
= TRUE
;
747 DEBUG ((EFI_D_INFO
, " End check partition entries\n"));
752 Updates the CRC32 value in the table header.
754 @param Hdr Table to update
759 IN OUT EFI_TABLE_HEADER
*Hdr
762 PartitionSetCrcAltSize (Hdr
->HeaderSize
, Hdr
);
767 Updates the CRC32 value in the table header.
769 @param Size The size of the table
770 @param Hdr Table to update
774 PartitionSetCrcAltSize (
776 IN OUT EFI_TABLE_HEADER
*Hdr
782 gBS
->CalculateCrc32 ((UINT8
*) Hdr
, Size
, &Crc
);
788 Checks the CRC32 value in the table header.
790 @param MaxSize Max Size limit
791 @param Hdr Table to check
793 @return TRUE CRC Valid
794 @return FALSE CRC Invalid
800 IN OUT EFI_TABLE_HEADER
*Hdr
803 return PartitionCheckCrcAltSize (MaxSize
, Hdr
->HeaderSize
, Hdr
);
808 Checks the CRC32 value in the table header.
810 @param MaxSize Max Size limit
811 @param Size The size of the table
812 @param Hdr Table to check
814 @return TRUE CRC Valid
815 @return FALSE CRC Invalid
819 PartitionCheckCrcAltSize (
822 IN OUT EFI_TABLE_HEADER
*Hdr
833 // If header size is 0 CRC will pass so return FALSE here
838 if ((MaxSize
!= 0) && (Size
> MaxSize
)) {
839 DEBUG ((EFI_D_ERROR
, "CheckCrc32: Size > MaxSize\n"));
843 // clear old crc from header
848 Status
= gBS
->CalculateCrc32 ((UINT8
*) Hdr
, Size
, &Crc
);
849 if (EFI_ERROR (Status
)) {
850 DEBUG ((EFI_D_ERROR
, "CheckCrc32: Crc calculation failed\n"));
863 DEBUG ((EFI_D_ERROR
, "CheckCrc32: Crc check failed\n"));
867 return (BOOLEAN
) (OrgCrc
== Crc
);