0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048
0049
0050
0051
0052
0053
0054
0055
0056
0057
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068
0069
0070
0071
0072
0073
0074
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084
0085 #include <linux/kernel.h>
0086 #include <linux/crc32.h>
0087 #include <linux/ctype.h>
0088 #include <linux/math64.h>
0089 #include <linux/slab.h>
0090 #include "check.h"
0091 #include "efi.h"
0092
0093
0094
0095
0096
0097 static int force_gpt;
0098 static int __init
0099 force_gpt_fn(char *str)
0100 {
0101 force_gpt = 1;
0102 return 1;
0103 }
0104 __setup("gpt", force_gpt_fn);
0105
0106
0107
0108
0109
0110
0111
0112
0113
0114
0115
0116
0117
0118
0119 static inline u32
0120 efi_crc32(const void *buf, unsigned long len)
0121 {
0122 return (crc32(~0L, buf, len) ^ ~0L);
0123 }
0124
0125
0126
0127
0128
0129
0130
0131
0132
0133
0134 static u64 last_lba(struct gendisk *disk)
0135 {
0136 return div_u64(bdev_nr_bytes(disk->part0),
0137 queue_logical_block_size(disk->queue)) - 1ULL;
0138 }
0139
0140 static inline int pmbr_part_valid(gpt_mbr_record *part)
0141 {
0142 if (part->os_type != EFI_PMBR_OSTYPE_EFI_GPT)
0143 goto invalid;
0144
0145
0146 if (le32_to_cpu(part->starting_lba) != GPT_PRIMARY_PARTITION_TABLE_LBA)
0147 goto invalid;
0148
0149 return GPT_MBR_PROTECTIVE;
0150 invalid:
0151 return 0;
0152 }
0153
0154
0155
0156
0157
0158
0159
0160
0161
0162
0163
0164
0165
0166
0167
0168
0169
0170
0171
0172 static int is_pmbr_valid(legacy_mbr *mbr, sector_t total_sectors)
0173 {
0174 uint32_t sz = 0;
0175 int i, part = 0, ret = 0;
0176
0177 if (!mbr || le16_to_cpu(mbr->signature) != MSDOS_MBR_SIGNATURE)
0178 goto done;
0179
0180 for (i = 0; i < 4; i++) {
0181 ret = pmbr_part_valid(&mbr->partition_record[i]);
0182 if (ret == GPT_MBR_PROTECTIVE) {
0183 part = i;
0184
0185
0186
0187
0188
0189 goto check_hybrid;
0190 }
0191 }
0192
0193 if (ret != GPT_MBR_PROTECTIVE)
0194 goto done;
0195 check_hybrid:
0196 for (i = 0; i < 4; i++)
0197 if ((mbr->partition_record[i].os_type !=
0198 EFI_PMBR_OSTYPE_EFI_GPT) &&
0199 (mbr->partition_record[i].os_type != 0x00))
0200 ret = GPT_MBR_HYBRID;
0201
0202
0203
0204
0205
0206
0207
0208
0209
0210
0211
0212
0213
0214 if (ret == GPT_MBR_PROTECTIVE) {
0215 sz = le32_to_cpu(mbr->partition_record[part].size_in_lba);
0216 if (sz != (uint32_t) total_sectors - 1 && sz != 0xFFFFFFFF)
0217 pr_debug("GPT: mbr size in lba (%u) different than whole disk (%u).\n",
0218 sz, min_t(uint32_t,
0219 total_sectors - 1, 0xFFFFFFFF));
0220 }
0221 done:
0222 return ret;
0223 }
0224
0225
0226
0227
0228
0229
0230
0231
0232
0233
0234
0235 static size_t read_lba(struct parsed_partitions *state,
0236 u64 lba, u8 *buffer, size_t count)
0237 {
0238 size_t totalreadcount = 0;
0239 sector_t n = lba *
0240 (queue_logical_block_size(state->disk->queue) / 512);
0241
0242 if (!buffer || lba > last_lba(state->disk))
0243 return 0;
0244
0245 while (count) {
0246 int copied = 512;
0247 Sector sect;
0248 unsigned char *data = read_part_sector(state, n++, §);
0249 if (!data)
0250 break;
0251 if (copied > count)
0252 copied = count;
0253 memcpy(buffer, data, copied);
0254 put_dev_sector(sect);
0255 buffer += copied;
0256 totalreadcount +=copied;
0257 count -= copied;
0258 }
0259 return totalreadcount;
0260 }
0261
0262
0263
0264
0265
0266
0267
0268
0269
0270
0271 static gpt_entry *alloc_read_gpt_entries(struct parsed_partitions *state,
0272 gpt_header *gpt)
0273 {
0274 size_t count;
0275 gpt_entry *pte;
0276
0277 if (!gpt)
0278 return NULL;
0279
0280 count = (size_t)le32_to_cpu(gpt->num_partition_entries) *
0281 le32_to_cpu(gpt->sizeof_partition_entry);
0282 if (!count)
0283 return NULL;
0284 pte = kmalloc(count, GFP_KERNEL);
0285 if (!pte)
0286 return NULL;
0287
0288 if (read_lba(state, le64_to_cpu(gpt->partition_entry_lba),
0289 (u8 *) pte, count) < count) {
0290 kfree(pte);
0291 pte=NULL;
0292 return NULL;
0293 }
0294 return pte;
0295 }
0296
0297
0298
0299
0300
0301
0302
0303
0304
0305
0306 static gpt_header *alloc_read_gpt_header(struct parsed_partitions *state,
0307 u64 lba)
0308 {
0309 gpt_header *gpt;
0310 unsigned ssz = queue_logical_block_size(state->disk->queue);
0311
0312 gpt = kmalloc(ssz, GFP_KERNEL);
0313 if (!gpt)
0314 return NULL;
0315
0316 if (read_lba(state, lba, (u8 *) gpt, ssz) < ssz) {
0317 kfree(gpt);
0318 gpt=NULL;
0319 return NULL;
0320 }
0321
0322 return gpt;
0323 }
0324
0325
0326
0327
0328
0329
0330
0331
0332
0333
0334
0335 static int is_gpt_valid(struct parsed_partitions *state, u64 lba,
0336 gpt_header **gpt, gpt_entry **ptes)
0337 {
0338 u32 crc, origcrc;
0339 u64 lastlba, pt_size;
0340
0341 if (!ptes)
0342 return 0;
0343 if (!(*gpt = alloc_read_gpt_header(state, lba)))
0344 return 0;
0345
0346
0347 if (le64_to_cpu((*gpt)->signature) != GPT_HEADER_SIGNATURE) {
0348 pr_debug("GUID Partition Table Header signature is wrong:"
0349 "%lld != %lld\n",
0350 (unsigned long long)le64_to_cpu((*gpt)->signature),
0351 (unsigned long long)GPT_HEADER_SIGNATURE);
0352 goto fail;
0353 }
0354
0355
0356 if (le32_to_cpu((*gpt)->header_size) >
0357 queue_logical_block_size(state->disk->queue)) {
0358 pr_debug("GUID Partition Table Header size is too large: %u > %u\n",
0359 le32_to_cpu((*gpt)->header_size),
0360 queue_logical_block_size(state->disk->queue));
0361 goto fail;
0362 }
0363
0364
0365 if (le32_to_cpu((*gpt)->header_size) < sizeof(gpt_header)) {
0366 pr_debug("GUID Partition Table Header size is too small: %u < %zu\n",
0367 le32_to_cpu((*gpt)->header_size),
0368 sizeof(gpt_header));
0369 goto fail;
0370 }
0371
0372
0373 origcrc = le32_to_cpu((*gpt)->header_crc32);
0374 (*gpt)->header_crc32 = 0;
0375 crc = efi_crc32((const unsigned char *) (*gpt), le32_to_cpu((*gpt)->header_size));
0376
0377 if (crc != origcrc) {
0378 pr_debug("GUID Partition Table Header CRC is wrong: %x != %x\n",
0379 crc, origcrc);
0380 goto fail;
0381 }
0382 (*gpt)->header_crc32 = cpu_to_le32(origcrc);
0383
0384
0385
0386 if (le64_to_cpu((*gpt)->my_lba) != lba) {
0387 pr_debug("GPT my_lba incorrect: %lld != %lld\n",
0388 (unsigned long long)le64_to_cpu((*gpt)->my_lba),
0389 (unsigned long long)lba);
0390 goto fail;
0391 }
0392
0393
0394
0395
0396 lastlba = last_lba(state->disk);
0397 if (le64_to_cpu((*gpt)->first_usable_lba) > lastlba) {
0398 pr_debug("GPT: first_usable_lba incorrect: %lld > %lld\n",
0399 (unsigned long long)le64_to_cpu((*gpt)->first_usable_lba),
0400 (unsigned long long)lastlba);
0401 goto fail;
0402 }
0403 if (le64_to_cpu((*gpt)->last_usable_lba) > lastlba) {
0404 pr_debug("GPT: last_usable_lba incorrect: %lld > %lld\n",
0405 (unsigned long long)le64_to_cpu((*gpt)->last_usable_lba),
0406 (unsigned long long)lastlba);
0407 goto fail;
0408 }
0409 if (le64_to_cpu((*gpt)->last_usable_lba) < le64_to_cpu((*gpt)->first_usable_lba)) {
0410 pr_debug("GPT: last_usable_lba incorrect: %lld > %lld\n",
0411 (unsigned long long)le64_to_cpu((*gpt)->last_usable_lba),
0412 (unsigned long long)le64_to_cpu((*gpt)->first_usable_lba));
0413 goto fail;
0414 }
0415
0416 if (le32_to_cpu((*gpt)->sizeof_partition_entry) != sizeof(gpt_entry)) {
0417 pr_debug("GUID Partition Entry Size check failed.\n");
0418 goto fail;
0419 }
0420
0421
0422 pt_size = (u64)le32_to_cpu((*gpt)->num_partition_entries) *
0423 le32_to_cpu((*gpt)->sizeof_partition_entry);
0424 if (pt_size > KMALLOC_MAX_SIZE) {
0425 pr_debug("GUID Partition Table is too large: %llu > %lu bytes\n",
0426 (unsigned long long)pt_size, KMALLOC_MAX_SIZE);
0427 goto fail;
0428 }
0429
0430 if (!(*ptes = alloc_read_gpt_entries(state, *gpt)))
0431 goto fail;
0432
0433
0434 crc = efi_crc32((const unsigned char *) (*ptes), pt_size);
0435
0436 if (crc != le32_to_cpu((*gpt)->partition_entry_array_crc32)) {
0437 pr_debug("GUID Partition Entry Array CRC check failed.\n");
0438 goto fail_ptes;
0439 }
0440
0441
0442 return 1;
0443
0444 fail_ptes:
0445 kfree(*ptes);
0446 *ptes = NULL;
0447 fail:
0448 kfree(*gpt);
0449 *gpt = NULL;
0450 return 0;
0451 }
0452
0453
0454
0455
0456
0457
0458
0459
0460 static inline int
0461 is_pte_valid(const gpt_entry *pte, const u64 lastlba)
0462 {
0463 if ((!efi_guidcmp(pte->partition_type_guid, NULL_GUID)) ||
0464 le64_to_cpu(pte->starting_lba) > lastlba ||
0465 le64_to_cpu(pte->ending_lba) > lastlba)
0466 return 0;
0467 return 1;
0468 }
0469
0470
0471
0472
0473
0474
0475
0476
0477
0478
0479
0480 static void
0481 compare_gpts(gpt_header *pgpt, gpt_header *agpt, u64 lastlba)
0482 {
0483 int error_found = 0;
0484 if (!pgpt || !agpt)
0485 return;
0486 if (le64_to_cpu(pgpt->my_lba) != le64_to_cpu(agpt->alternate_lba)) {
0487 pr_warn("GPT:Primary header LBA != Alt. header alternate_lba\n");
0488 pr_warn("GPT:%lld != %lld\n",
0489 (unsigned long long)le64_to_cpu(pgpt->my_lba),
0490 (unsigned long long)le64_to_cpu(agpt->alternate_lba));
0491 error_found++;
0492 }
0493 if (le64_to_cpu(pgpt->alternate_lba) != le64_to_cpu(agpt->my_lba)) {
0494 pr_warn("GPT:Primary header alternate_lba != Alt. header my_lba\n");
0495 pr_warn("GPT:%lld != %lld\n",
0496 (unsigned long long)le64_to_cpu(pgpt->alternate_lba),
0497 (unsigned long long)le64_to_cpu(agpt->my_lba));
0498 error_found++;
0499 }
0500 if (le64_to_cpu(pgpt->first_usable_lba) !=
0501 le64_to_cpu(agpt->first_usable_lba)) {
0502 pr_warn("GPT:first_usable_lbas don't match.\n");
0503 pr_warn("GPT:%lld != %lld\n",
0504 (unsigned long long)le64_to_cpu(pgpt->first_usable_lba),
0505 (unsigned long long)le64_to_cpu(agpt->first_usable_lba));
0506 error_found++;
0507 }
0508 if (le64_to_cpu(pgpt->last_usable_lba) !=
0509 le64_to_cpu(agpt->last_usable_lba)) {
0510 pr_warn("GPT:last_usable_lbas don't match.\n");
0511 pr_warn("GPT:%lld != %lld\n",
0512 (unsigned long long)le64_to_cpu(pgpt->last_usable_lba),
0513 (unsigned long long)le64_to_cpu(agpt->last_usable_lba));
0514 error_found++;
0515 }
0516 if (efi_guidcmp(pgpt->disk_guid, agpt->disk_guid)) {
0517 pr_warn("GPT:disk_guids don't match.\n");
0518 error_found++;
0519 }
0520 if (le32_to_cpu(pgpt->num_partition_entries) !=
0521 le32_to_cpu(agpt->num_partition_entries)) {
0522 pr_warn("GPT:num_partition_entries don't match: "
0523 "0x%x != 0x%x\n",
0524 le32_to_cpu(pgpt->num_partition_entries),
0525 le32_to_cpu(agpt->num_partition_entries));
0526 error_found++;
0527 }
0528 if (le32_to_cpu(pgpt->sizeof_partition_entry) !=
0529 le32_to_cpu(agpt->sizeof_partition_entry)) {
0530 pr_warn("GPT:sizeof_partition_entry values don't match: "
0531 "0x%x != 0x%x\n",
0532 le32_to_cpu(pgpt->sizeof_partition_entry),
0533 le32_to_cpu(agpt->sizeof_partition_entry));
0534 error_found++;
0535 }
0536 if (le32_to_cpu(pgpt->partition_entry_array_crc32) !=
0537 le32_to_cpu(agpt->partition_entry_array_crc32)) {
0538 pr_warn("GPT:partition_entry_array_crc32 values don't match: "
0539 "0x%x != 0x%x\n",
0540 le32_to_cpu(pgpt->partition_entry_array_crc32),
0541 le32_to_cpu(agpt->partition_entry_array_crc32));
0542 error_found++;
0543 }
0544 if (le64_to_cpu(pgpt->alternate_lba) != lastlba) {
0545 pr_warn("GPT:Primary header thinks Alt. header is not at the end of the disk.\n");
0546 pr_warn("GPT:%lld != %lld\n",
0547 (unsigned long long)le64_to_cpu(pgpt->alternate_lba),
0548 (unsigned long long)lastlba);
0549 error_found++;
0550 }
0551
0552 if (le64_to_cpu(agpt->my_lba) != lastlba) {
0553 pr_warn("GPT:Alternate GPT header not at the end of the disk.\n");
0554 pr_warn("GPT:%lld != %lld\n",
0555 (unsigned long long)le64_to_cpu(agpt->my_lba),
0556 (unsigned long long)lastlba);
0557 error_found++;
0558 }
0559
0560 if (error_found)
0561 pr_warn("GPT: Use GNU Parted to correct GPT errors.\n");
0562 return;
0563 }
0564
0565
0566
0567
0568
0569
0570
0571
0572
0573
0574
0575
0576
0577
0578
0579
0580
0581 static int find_valid_gpt(struct parsed_partitions *state, gpt_header **gpt,
0582 gpt_entry **ptes)
0583 {
0584 int good_pgpt = 0, good_agpt = 0, good_pmbr = 0;
0585 gpt_header *pgpt = NULL, *agpt = NULL;
0586 gpt_entry *pptes = NULL, *aptes = NULL;
0587 legacy_mbr *legacymbr;
0588 struct gendisk *disk = state->disk;
0589 const struct block_device_operations *fops = disk->fops;
0590 sector_t total_sectors = get_capacity(state->disk);
0591 u64 lastlba;
0592
0593 if (!ptes)
0594 return 0;
0595
0596 lastlba = last_lba(state->disk);
0597 if (!force_gpt) {
0598
0599 legacymbr = kzalloc(sizeof(*legacymbr), GFP_KERNEL);
0600 if (!legacymbr)
0601 goto fail;
0602
0603 read_lba(state, 0, (u8 *)legacymbr, sizeof(*legacymbr));
0604 good_pmbr = is_pmbr_valid(legacymbr, total_sectors);
0605 kfree(legacymbr);
0606
0607 if (!good_pmbr)
0608 goto fail;
0609
0610 pr_debug("Device has a %s MBR\n",
0611 good_pmbr == GPT_MBR_PROTECTIVE ?
0612 "protective" : "hybrid");
0613 }
0614
0615 good_pgpt = is_gpt_valid(state, GPT_PRIMARY_PARTITION_TABLE_LBA,
0616 &pgpt, &pptes);
0617 if (good_pgpt)
0618 good_agpt = is_gpt_valid(state,
0619 le64_to_cpu(pgpt->alternate_lba),
0620 &agpt, &aptes);
0621 if (!good_agpt && force_gpt)
0622 good_agpt = is_gpt_valid(state, lastlba, &agpt, &aptes);
0623
0624 if (!good_agpt && force_gpt && fops->alternative_gpt_sector) {
0625 sector_t agpt_sector;
0626 int err;
0627
0628 err = fops->alternative_gpt_sector(disk, &agpt_sector);
0629 if (!err)
0630 good_agpt = is_gpt_valid(state, agpt_sector,
0631 &agpt, &aptes);
0632 }
0633
0634
0635 if (!good_pgpt && !good_agpt)
0636 goto fail;
0637
0638 compare_gpts(pgpt, agpt, lastlba);
0639
0640
0641 if (good_pgpt) {
0642 *gpt = pgpt;
0643 *ptes = pptes;
0644 kfree(agpt);
0645 kfree(aptes);
0646 if (!good_agpt)
0647 pr_warn("Alternate GPT is invalid, using primary GPT.\n");
0648 return 1;
0649 }
0650 else if (good_agpt) {
0651 *gpt = agpt;
0652 *ptes = aptes;
0653 kfree(pgpt);
0654 kfree(pptes);
0655 pr_warn("Primary GPT is invalid, using alternate GPT.\n");
0656 return 1;
0657 }
0658
0659 fail:
0660 kfree(pgpt);
0661 kfree(agpt);
0662 kfree(pptes);
0663 kfree(aptes);
0664 *gpt = NULL;
0665 *ptes = NULL;
0666 return 0;
0667 }
0668
0669
0670
0671
0672
0673
0674
0675
0676
0677
0678 static void utf16_le_to_7bit(const __le16 *in, unsigned int size, u8 *out)
0679 {
0680 unsigned int i = 0;
0681
0682 out[size] = 0;
0683
0684 while (i < size) {
0685 u8 c = le16_to_cpu(in[i]) & 0xff;
0686
0687 if (c && !isprint(c))
0688 c = '!';
0689 out[i] = c;
0690 i++;
0691 }
0692 }
0693
0694
0695
0696
0697
0698
0699
0700
0701
0702
0703
0704
0705
0706
0707
0708
0709
0710
0711
0712
0713 int efi_partition(struct parsed_partitions *state)
0714 {
0715 gpt_header *gpt = NULL;
0716 gpt_entry *ptes = NULL;
0717 u32 i;
0718 unsigned ssz = queue_logical_block_size(state->disk->queue) / 512;
0719
0720 if (!find_valid_gpt(state, &gpt, &ptes) || !gpt || !ptes) {
0721 kfree(gpt);
0722 kfree(ptes);
0723 return 0;
0724 }
0725
0726 pr_debug("GUID Partition Table is valid! Yea!\n");
0727
0728 for (i = 0; i < le32_to_cpu(gpt->num_partition_entries) && i < state->limit-1; i++) {
0729 struct partition_meta_info *info;
0730 unsigned label_max;
0731 u64 start = le64_to_cpu(ptes[i].starting_lba);
0732 u64 size = le64_to_cpu(ptes[i].ending_lba) -
0733 le64_to_cpu(ptes[i].starting_lba) + 1ULL;
0734
0735 if (!is_pte_valid(&ptes[i], last_lba(state->disk)))
0736 continue;
0737
0738 put_partition(state, i+1, start * ssz, size * ssz);
0739
0740
0741 if (!efi_guidcmp(ptes[i].partition_type_guid, PARTITION_LINUX_RAID_GUID))
0742 state->parts[i + 1].flags = ADDPART_FLAG_RAID;
0743
0744 info = &state->parts[i + 1].info;
0745 efi_guid_to_str(&ptes[i].unique_partition_guid, info->uuid);
0746
0747
0748 label_max = min(ARRAY_SIZE(info->volname) - 1,
0749 ARRAY_SIZE(ptes[i].partition_name));
0750 utf16_le_to_7bit(ptes[i].partition_name, label_max, info->volname);
0751 state->parts[i + 1].has_info = true;
0752 }
0753 kfree(ptes);
0754 kfree(gpt);
0755 strlcat(state->pp_buf, "\n", PAGE_SIZE);
0756 return 1;
0757 }