From 32d637298717446a4edd3c8fbe637462fab4c000 Mon Sep 17 00:00:00 2001 From: Phillip Susi Date: Sat, 26 Apr 2014 18:25:38 -0400 Subject: [PATCH 108/131] libparted: fix loop labels to not vanish The loop label type was using the existence of a partition as a proxy for a filesystem being detected, and loop_write() would try to write a loop signature if there was no filesystem, and erase it if there was. Because of this, creating a partition without writing a filesystem to it caused loop_write to erase the loop label. There seems to be no reason to bother erasing the loop label if it is still present along with a filesystem signature, so don't bother with this, and actually check to see if a filesystem is detected in the partition rather than using the existence of a partition to decide if writing the loop signature is needed. Finally, since there is no way to preserve the existence of a partition with no filesystem in it, have loop_read() always create a partition, even if no filesystem is detected. --- NEWS | 6 ++++++ libparted/labels/loop.c | 53 ++++++++++++++++++++++--------------------------- 2 files changed, 30 insertions(+), 29 deletions(-) diff --git a/NEWS b/NEWS index 3dc39fd..8ec11ab 100644 --- a/NEWS +++ b/NEWS @@ -29,6 +29,9 @@ GNU parted NEWS -*- outline -*- ** Bug Fixes + libparted: fix loop labels to not vanish if you don't create + a filesystem, and to not return an error syncing when you do. + libparted: remove all old partitions, even if new label does not allow as many. @@ -116,6 +119,9 @@ GNU parted NEWS -*- outline -*- ** Changes in behavior + When creating a loop label, it automatically comes with a partition + using the whole disk. + parted -l no longer lists device-mapper devices other than dmraid whole disks. diff --git a/libparted/labels/loop.c b/libparted/labels/loop.c index ea8f007..8ebb1f4 100644 --- a/libparted/labels/loop.c +++ b/libparted/labels/loop.c @@ -80,7 +80,23 @@ loop_alloc (const PedDevice* dev) if (dev->length < 256) return NULL; - return _ped_disk_alloc ((PedDevice*)dev, &loop_disk_type); + PedDisk *disk = _ped_disk_alloc ((PedDevice*)dev, &loop_disk_type); + PED_ASSERT (disk != NULL); + PedGeometry *geom = ped_geometry_new (dev, 0, dev->length); + PED_ASSERT (geom != NULL); + PedPartition *part = ped_partition_new (disk, PED_PARTITION_NORMAL, + NULL, geom->start, geom->end); + PED_ASSERT (part != NULL); + ped_geometry_destroy (geom); + PedConstraint *constraint_any = ped_constraint_any (dev); + if (!ped_disk_add_partition (disk, part, constraint_any)) + goto error; + ped_constraint_destroy (constraint_any); + return disk; + error: + ped_constraint_destroy (constraint_any); + ped_disk_destroy (disk); + return NULL; } static PedDisk* @@ -118,18 +134,12 @@ loop_read (PedDisk* disk) int found_sig = !strncmp (buf, LOOP_SIGNATURE, strlen (LOOP_SIGNATURE)); free (buf); - - if (found_sig) { - ped_constraint_destroy (constraint_any); - return 1; - } - geom = ped_geometry_new (dev, 0, dev->length); if (!geom) goto error; fs_type = ped_file_system_probe (geom); - if (!fs_type) + if (!fs_type && !found_sig) goto error_free_geom; part = ped_partition_new (disk, PED_PARTITION_NORMAL, @@ -137,7 +147,6 @@ loop_read (PedDisk* disk) ped_geometry_destroy (geom); if (!part) goto error; - part->fs_type = fs_type; if (!ped_disk_add_partition (disk, part, constraint_any)) goto error; @@ -156,29 +165,15 @@ static int loop_write (const PedDisk* disk) { size_t buflen = disk->dev->sector_size; - char *buf = ped_malloc (buflen); - if (buf == NULL) - return 0; - - if (ped_disk_get_partition (disk, 1)) { - if (!ped_device_read (disk->dev, buf, 0, 1)) { - free (buf); - return 0; - } - if (strncmp (buf, LOOP_SIGNATURE, strlen (LOOP_SIGNATURE)) != 0) { - free (buf); - return 1; - } - memset (buf, 0, strlen (LOOP_SIGNATURE)); - return ped_device_write (disk->dev, buf, 0, 1); - } - + char *buf = alloca (buflen); + PedPartition *part = ped_disk_get_partition (disk, 1); + /* if there is already a filesystem on the disk, we don't need to write the signature */ + if (part && part->fs_type) + return 1; memset (buf, 0, buflen); strcpy (buf, LOOP_SIGNATURE); - int write_ok = ped_device_write (disk->dev, buf, 0, 1); - free (buf); - return write_ok; + return ped_device_write (disk->dev, buf, 0, 1); } #endif /* !DISCOVER_ONLY */ -- 1.9.3