]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
repart: Discard from/to first/last usable lba
authorSjoerd Simons <sjoerd@collabora.com>
Thu, 23 Feb 2023 09:00:16 +0000 (10:00 +0100)
committerLennart Poettering <lennart@poettering.net>
Thu, 13 Apr 2023 09:12:52 +0000 (11:12 +0200)
Repart considers the start and end of the usable space to the first multiple
of grainsz (at least 4096 bytes). However the first usable LBA of a GPT
partition is at sector 34 (512 bytes sectors) which is not a multiple of 4096.
The backup GPT label at the end also takes up 33 sectors, meaning the last
usable LBA is at 34 sectors from the end, unlikely to be a 4096 multiple as
well.

This meant that the very first and last sectors were never discarded. However
more problematically if an existing partition started before the first
usable grainsz multiple its start didn't get taken into account as a valid
starting point and got its data discarded.

Signed-off-by: Sjoerd Simons <sjoerd@collabora.com>
src/partition/repart.c

index 23ad58f4439ead5c626a0a8be1b53af8bfbb6a07..0da07ee12293b9af7e7e34e64039591e6b0bffce 100644 (file)
@@ -3036,7 +3036,11 @@ static int context_discard_gap_after(Context *context, Partition *p) {
         if (p)
                 gap = p->offset + p->new_size;
         else
-                gap = context->start;
+                /* The context start gets rounded up to grain_size, however
+                 * existing partitions may be before that so ensure the gap
+                 * starts at the first actually usable lba
+                 */
+                gap = fdisk_get_first_lba(context->fdisk_context) * context->sector_size;
 
         LIST_FOREACH(partitions, q, context->partitions) {
                 if (q->dropped)
@@ -3053,7 +3057,7 @@ static int context_discard_gap_after(Context *context, Partition *p) {
         }
 
         if (next == UINT64_MAX) {
-                next = context->end;
+                next = (fdisk_get_last_lba(context->fdisk_context) + 1) * context->sector_size;
                 if (gap > next)
                         return log_error_errno(SYNTHETIC_ERRNO(EIO), "Partition end beyond disk end.");
         }