2
2
libparted - a library for manipulating disk partitions
3
Copyright (C) 1999-2001, 2004-2005, 2007-2010 Free Software
3
Copyright (C) 1999-2001, 2004-2005, 2007-2012 Free Software Foundation,
6
6
This program is free software; you can redistribute it and/or modify
7
7
it under the terms of the GNU General Public License as published by
165
165
static PedDiskType msdos_disk_type;
168
From http://www.win.tue.nl/~aeb/linux/fs/fat/fat-1.html
170
The 2-byte numbers are stored little endian (low order byte first).
172
Here the FAT12 version, that is also the common part of the FAT12, FAT16 and FAT32 boot sectors. See further below.
175
0-2 Jump to bootstrap (E.g. eb 3c 90; on i86: JMP 003E NOP.
176
One finds either eb xx 90, or e9 xx xx.
177
The position of the bootstrap varies.)
178
3-10 OEM name/version (E.g. "IBM 3.3", "IBM 20.0", "MSDOS5.0", "MSWIN4.0".
179
Various format utilities leave their own name, like "CH-FOR18".
180
Sometimes just garbage. Microsoft recommends "MSWIN4.1".)
181
/* BIOS Parameter Block starts here */
182
11-12 Number of bytes per sector (512)
183
Must be one of 512, 1024, 2048, 4096.
184
13 Number of sectors per cluster (1)
185
Must be one of 1, 2, 4, 8, 16, 32, 64, 128.
186
A cluster should have at most 32768 bytes. In rare cases 65536 is OK.
187
14-15 Number of reserved sectors (1)
188
FAT12 and FAT16 use 1. FAT32 uses 32.
189
16 Number of FAT copies (2)
190
17-18 Number of root directory entries (224)
191
0 for FAT32. 512 is recommended for FAT16.
192
19-20 Total number of sectors in the filesystem (2880)
193
(in case the partition is not FAT32 and smaller than 32 MB)
194
21 Media descriptor type (f0: 1.4 MB floppy, f8: hard disk; see below)
195
22-23 Number of sectors per FAT (9)
197
24-25 Number of sectors per track (12)
198
26-27 Number of heads (2, for a double-sided diskette)
199
28-29 Number of hidden sectors (0)
200
Hidden sectors are sectors preceding the partition.
201
/* BIOS Parameter Block ends here */
203
510-511 Signature 55 aa
206
/* There is a significant risk of misclassifying (as msdos)
207
a disk that is composed solely of a single FAT partition.
208
Return false if sector S could not be a valid FAT boot sector.
209
Otherwise, return true. */
211
maybe_FAT (unsigned char const *s)
213
if (! (s[0] == 0xeb || s[0] == 0xe9))
216
unsigned int sector_size = PED_LE16_TO_CPU (*(uint16_t *) (s + 11));
228
if (! (s[21] == 0xf0 || s[21] == 0xf8))
168
235
msdos_probe (const PedDevice *dev)
191
258
* and ensure that each partition has a boot indicator that is
192
259
* either 0 or 0x80.
261
unsigned int n_active = 0;
194
262
for (i = 0; i < DOS_N_PRI_PARTITIONS; i++) {
263
if (part_table->partitions[i].boot_ind == 0x80)
195
265
if (part_table->partitions[i].boot_ind != 0
196
266
&& part_table->partitions[i].boot_ind != 0x80)
270
/* If there are no active partitions and this is probably
271
a FAT file system, do not classify it as msdos. */
272
if (n_active == 0 && maybe_FAT (label))
200
275
/* If this is a GPT disk, fail here */
201
276
for (i = 0; i < DOS_N_PRI_PARTITIONS; i++) {
202
277
if (part_table->partitions[i].type == PARTITION_GPT)
377
452
chs->sector = real_s + 1 + (real_c >> 8 << 6);
455
static PedSector _GL_ATTRIBUTE_PURE
381
456
legacy_start (const PedDisk* disk, const PedCHSGeometry* bios_geom,
382
457
const DosRawPartition* raw_part)
384
PED_ASSERT (disk != NULL, return 0);
385
PED_ASSERT (raw_part != NULL, return 0);
459
PED_ASSERT (disk != NULL);
460
PED_ASSERT (raw_part != NULL);
387
462
return chs_to_sector (disk->dev, bios_geom, &raw_part->chs_start);
465
static PedSector _GL_ATTRIBUTE_PURE
391
466
legacy_end (const PedDisk* disk, const PedCHSGeometry* bios_geom,
392
467
const DosRawPartition* raw_part)
394
PED_ASSERT (disk != NULL, return 0);
395
PED_ASSERT (raw_part != NULL, return 0);
469
PED_ASSERT (disk != NULL);
470
PED_ASSERT (raw_part != NULL);
397
472
return chs_to_sector (disk->dev, bios_geom, &raw_part->chs_end);
475
static PedSector _GL_ATTRIBUTE_PURE
401
476
linear_start (const PedDisk* disk, const DosRawPartition* raw_part,
402
477
PedSector offset)
404
PED_ASSERT (disk != NULL, return 0);
405
PED_ASSERT (raw_part != NULL, return 0);
479
PED_ASSERT (disk != NULL);
480
PED_ASSERT (raw_part != NULL);
407
482
return offset + PED_LE32_TO_CPU (raw_part->start);
485
static PedSector _GL_ATTRIBUTE_PURE
411
486
linear_end (const PedDisk* disk, const DosRawPartition* raw_part,
412
487
PedSector offset)
414
PED_ASSERT (disk != NULL, return 0);
415
PED_ASSERT (raw_part != NULL, return 0);
489
PED_ASSERT (disk != NULL);
490
PED_ASSERT (raw_part != NULL);
417
492
return (linear_start (disk, raw_part, offset)
418
493
+ (PED_LE32_TO_CPU (raw_part->length) - 1));
421
496
#ifndef DISCOVER_ONLY
497
static int _GL_ATTRIBUTE_PURE
423
498
partition_check_bios_geometry (PedPartition* part, PedCHSGeometry* bios_geom)
425
500
PedSector leg_start, leg_end;
426
501
DosPartitionData* dos_data;
429
PED_ASSERT (part != NULL, return 0);
430
PED_ASSERT (part->disk != NULL, return 0);
431
PED_ASSERT (part->disk_specific != NULL, return 0);
504
PED_ASSERT (part != NULL);
505
PED_ASSERT (part->disk != NULL);
506
PED_ASSERT (part->disk_specific != NULL);
432
507
dos_data = part->disk_specific;
434
509
if (!dos_data->orig)
523
static int _GL_ATTRIBUTE_PURE
449
524
disk_check_bios_geometry (const PedDisk* disk, PedCHSGeometry* bios_geom)
451
526
PedPartition* part = NULL;
453
PED_ASSERT (disk != NULL, return 0);
528
PED_ASSERT (disk != NULL);
455
530
while ((part = ped_disk_next_partition (disk, part))) {
456
531
if (ped_partition_is_active (part)) {
476
PED_ASSERT (bios_geom != NULL, return 0);
477
PED_ASSERT (part != NULL, return 0);
478
PED_ASSERT (part->disk != NULL, return 0);
479
PED_ASSERT (part->disk->dev != NULL, return 0);
480
PED_ASSERT (part->disk->dev->sector_size % PED_SECTOR_SIZE_DEFAULT == 0,
551
PED_ASSERT (bios_geom != NULL);
552
PED_ASSERT (part != NULL);
553
PED_ASSERT (part->disk != NULL);
554
PED_ASSERT (part->disk->dev != NULL);
555
PED_ASSERT (part->disk->dev->sector_size % PED_SECTOR_SIZE_DEFAULT == 0);
483
557
buf = ped_malloc (part->disk->dev->sector_size);
564
638
PedSector cyl_size, head_size;
565
639
PedSector cylinders, heads, sectors;
567
PED_ASSERT (part != NULL, return 0);
568
PED_ASSERT (part->disk_specific != NULL, return 0);
569
PED_ASSERT (bios_geom != NULL, return 0);
641
PED_ASSERT (part != NULL);
642
PED_ASSERT (part->disk_specific != NULL);
643
PED_ASSERT (bios_geom != NULL);
571
645
dos_data = part->disk_specific;
654
730
head_size = ( A_ - C * cyl_size ) / H;
656
732
/* should not happen because denum != 0 */
657
PED_ASSERT (0, return 0);
660
PED_ASSERT (head_size > 0, return 0);
661
PED_ASSERT (head_size <= 63, return 0);
736
if (!(head_size > 0))
738
if (!(head_size <= 63))
663
741
cylinders = part->disk->dev->length / cyl_size;
664
742
heads = cyl_size / head_size;
665
743
sectors = head_size;
667
PED_ASSERT (heads > 0, return 0);
668
PED_ASSERT (heads < 256, return 0);
670
PED_ASSERT (sectors > 0, return 0);
671
PED_ASSERT (sectors <= 63, return 0);
752
if (!(sectors <= 63))
673
755
/* Some broken OEM partitioning program(s) seem to have an out-by-one
674
756
* error on the end of partitions. We should offer to fix the
677
759
if (((C + 1) * heads + H) * sectors + S == A)
680
PED_ASSERT ((c * heads + h) * sectors + s == a, return 0);
681
PED_ASSERT ((C * heads + H) * sectors + S == A, return 0);
762
if (!((c * heads + h) * sectors + s == a))
764
if (!((C * heads + H) * sectors + S == A))
683
767
bios_geom->cylinders = cylinders;
684
768
bios_geom->heads = heads;
691
775
partition_probe_bios_geometry (const PedPartition* part,
692
776
PedCHSGeometry* bios_geom)
694
PED_ASSERT (part != NULL, return);
695
PED_ASSERT (part->disk != NULL, return);
696
PED_ASSERT (bios_geom != NULL, return);
778
PED_ASSERT (part != NULL);
779
PED_ASSERT (part->disk != NULL);
780
PED_ASSERT (bios_geom != NULL);
698
782
if (ped_partition_is_active (part)) {
699
783
if (probe_partition_for_geom (part, bios_geom))
981
1065
msdos_read (PedDisk* disk)
983
PED_ASSERT (disk != NULL, return 0);
984
PED_ASSERT (disk->dev != NULL, return 0);
1067
PED_ASSERT (disk != NULL);
1068
PED_ASSERT (disk->dev != NULL);
986
1070
ped_disk_delete_all (disk);
987
1071
if (!read_table (disk, 0, 0))
1016
1100
DosPartitionData* dos_data;
1017
1101
PedCHSGeometry bios_geom;
1019
PED_ASSERT (raw_part != NULL, return 0);
1020
PED_ASSERT (part != NULL, return 0);
1103
PED_ASSERT (raw_part != NULL);
1104
PED_ASSERT (part != NULL);
1022
1106
partition_probe_bios_geometry (part, &bios_geom);
1049
1133
const PedCHSGeometry* bios_geom,
1050
1134
const PedGeometry* geom, PedSector offset)
1052
PED_ASSERT (raw_part != NULL, return 0);
1053
PED_ASSERT (geom != NULL, return 0);
1054
PED_ASSERT (geom->dev != NULL, return 0);
1136
PED_ASSERT (raw_part != NULL);
1137
PED_ASSERT (geom != NULL);
1138
PED_ASSERT (geom->dev != NULL);
1056
1140
raw_part->boot_ind = 0;
1057
1141
raw_part->type = PARTITION_DOS_EXT;
1072
1156
PedPartition* part;
1073
1157
PedSector lba_offset;
1075
PED_ASSERT (disk != NULL, return 0);
1076
PED_ASSERT (ped_disk_extended_partition (disk) != NULL, return 0);
1077
PED_ASSERT (logical != NULL, return 0);
1159
PED_ASSERT (disk != NULL);
1160
PED_ASSERT (ped_disk_extended_partition (disk) != NULL);
1161
PED_ASSERT (logical != NULL);
1079
1163
lba_offset = ped_disk_extended_partition (disk)->geom.start;
1404
1488
PedPartition* walk;
1405
1489
DosPartitionData* dos_data;
1407
PED_ASSERT (part != NULL, return 0);
1408
PED_ASSERT (part->disk_specific != NULL, return 0);
1409
PED_ASSERT (part->disk != NULL, return 0);
1491
PED_ASSERT (part != NULL);
1492
PED_ASSERT (part->disk_specific != NULL);
1493
PED_ASSERT (part->disk != NULL);
1411
1495
dos_data = part->disk_specific;
1412
1496
disk = part->disk;
1563
static int _GL_ATTRIBUTE_PURE
1480
1564
msdos_partition_get_flag (const PedPartition* part, PedPartitionFlag flag)
1482
1566
DosPartitionData* dos_data;
1484
PED_ASSERT (part != NULL, return 0);
1485
PED_ASSERT (part->disk_specific != NULL, return 0);
1568
PED_ASSERT (part != NULL);
1569
PED_ASSERT (part->disk_specific != NULL);
1487
1571
dos_data = part->disk_specific;
1488
1572
switch (flag) {
1638
1722
dev->length - min_geom->end))
1641
/* Do not assume that length is larger than 1 cylinder's
1642
worth of sectors. This is useful when testing with
1643
a memory-mapped "disk" (a la scsi_debug) that is say,
1644
2048 sectors long. */
1645
if (cylinder_size < dev->length
1646
&& !ped_geometry_init (&start_geom, dev, cylinder_size,
1647
dev->length - cylinder_size))
1725
/* Use cylinder_size as the starting sector number
1726
when the device is large enough to accommodate that.
1727
Otherwise, use sector 1. */
1728
PedSector start = (cylinder_size < dev->length
1729
? cylinder_size : 1);
1730
if (!ped_geometry_init (&start_geom, dev, start,
1731
dev->length - start))
1649
1733
if (!ped_geometry_init (&end_geom, dev, 0, dev->length))
1916
2000
PedGeometry* solution = NULL;
1917
2001
PedConstraint *intersect, *log_meta_overlap;
1919
PED_ASSERT (ext_part != NULL, return 0);
2003
PED_ASSERT (ext_part != NULL);
1921
2005
log_meta_overlap = _log_meta_overlap_constraint(part, &part->geom);
1922
2006
intersect = ped_constraint_intersect (constraint, log_meta_overlap);
2054
2138
PedCHSGeometry bios_geom;
2055
2139
DosPartitionData* dos_data;
2057
PED_ASSERT (part != NULL, return 0);
2058
PED_ASSERT (part->disk_specific != NULL, return 0);
2141
PED_ASSERT (part != NULL);
2142
PED_ASSERT (part->disk_specific != NULL);
2060
2144
dos_data = part->disk_specific;
2314
2398
if (!ped_disk_get_partition (disk, i))
2404
static int _GL_ATTRIBUTE_PURE
2321
2405
next_logical (const PedDisk* disk)
2408
for (i=5; i<=MAX_TOTAL_PART; i++) {
2325
2409
if (!ped_disk_get_partition (disk, i))
2412
ped_exception_throw (
2413
PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL,
2414
_("cannot create any more partitions"),
2331
2420
msdos_partition_enumerate (PedPartition* part)
2333
PED_ASSERT (part != NULL, return 0);
2334
PED_ASSERT (part->disk != NULL, return 0);
2422
PED_ASSERT (part != NULL);
2423
PED_ASSERT (part->disk != NULL);
2336
2425
/* don't re-number a primary partition */
2337
2426
if (part->num != -1 && part->num <= DOS_N_PRI_PARTITIONS)