repart: don't crash when looping over dropped partitions
Properly skip over dropped partitions and make sure they don't affect the final graphical output (for example by leaving empty "spaces" where their definition file name would otherwise be). Resolves: #30742
This commit is contained in:
committed by
Yu Watanabe
parent
0417d1d0e8
commit
f569dc6af2
+24
-13
@@ -2908,12 +2908,13 @@ static int context_dump_partitions(Context *context) {
|
||||
return table_print_with_pager(t, arg_json_format_flags, arg_pager_flags, arg_legend);
|
||||
}
|
||||
|
||||
static void context_bar_char_process_partition(
|
||||
static int context_bar_char_process_partition(
|
||||
Context *context,
|
||||
Partition *bar[],
|
||||
size_t n,
|
||||
Partition *p,
|
||||
size_t *ret_start) {
|
||||
size_t **start_array,
|
||||
size_t *n_start_array) {
|
||||
|
||||
uint64_t from, to, total;
|
||||
size_t x, y;
|
||||
@@ -2922,9 +2923,11 @@ static void context_bar_char_process_partition(
|
||||
assert(bar);
|
||||
assert(n > 0);
|
||||
assert(p);
|
||||
assert(start_array);
|
||||
assert(n_start_array);
|
||||
|
||||
if (p->dropped)
|
||||
return;
|
||||
return 0;
|
||||
|
||||
assert(p->offset != UINT64_MAX);
|
||||
assert(p->new_size != UINT64_MAX);
|
||||
@@ -2947,7 +2950,10 @@ static void context_bar_char_process_partition(
|
||||
for (size_t i = x; i < y; i++)
|
||||
bar[i] = p;
|
||||
|
||||
*ret_start = x;
|
||||
if (!GREEDY_REALLOC_APPEND(*start_array, *n_start_array, &x, 1))
|
||||
return log_oom();
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int partition_hint(const Partition *p, const char *node, char **ret) {
|
||||
@@ -2991,9 +2997,11 @@ done:
|
||||
static int context_dump_partition_bar(Context *context) {
|
||||
_cleanup_free_ Partition **bar = NULL;
|
||||
_cleanup_free_ size_t *start_array = NULL;
|
||||
size_t n_start_array = 0;
|
||||
Partition *last = NULL;
|
||||
bool z = false;
|
||||
size_t c, j = 0;
|
||||
int r;
|
||||
|
||||
assert_se((c = columns()) >= 2);
|
||||
c -= 2; /* We do not use the leftmost and rightmost character cell */
|
||||
@@ -3002,12 +3010,11 @@ static int context_dump_partition_bar(Context *context) {
|
||||
if (!bar)
|
||||
return log_oom();
|
||||
|
||||
start_array = new(size_t, context->n_partitions);
|
||||
if (!start_array)
|
||||
return log_oom();
|
||||
|
||||
LIST_FOREACH(partitions, p, context->partitions)
|
||||
context_bar_char_process_partition(context, bar, c, p, start_array + j++);
|
||||
LIST_FOREACH(partitions, p, context->partitions) {
|
||||
r = context_bar_char_process_partition(context, bar, c, p, &start_array, &n_start_array);
|
||||
if (r < 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
putc(' ', stdout);
|
||||
|
||||
@@ -3029,7 +3036,7 @@ static int context_dump_partition_bar(Context *context) {
|
||||
fputs(ansi_normal(), stdout);
|
||||
putc('\n', stdout);
|
||||
|
||||
for (size_t i = 0; i < context->n_partitions; i++) {
|
||||
for (size_t i = 0; i < n_start_array; i++) {
|
||||
_cleanup_free_ char **line = NULL;
|
||||
|
||||
line = new0(char*, c);
|
||||
@@ -3039,9 +3046,13 @@ static int context_dump_partition_bar(Context *context) {
|
||||
j = 0;
|
||||
LIST_FOREACH(partitions, p, context->partitions) {
|
||||
_cleanup_free_ char *d = NULL;
|
||||
|
||||
if (p->dropped)
|
||||
continue;
|
||||
|
||||
j++;
|
||||
|
||||
if (i < context->n_partitions - j) {
|
||||
if (i < n_start_array - j) {
|
||||
|
||||
if (line[start_array[j-1]]) {
|
||||
const char *e;
|
||||
@@ -3061,7 +3072,7 @@ static int context_dump_partition_bar(Context *context) {
|
||||
return log_oom();
|
||||
}
|
||||
|
||||
} else if (i == context->n_partitions - j) {
|
||||
} else if (i == n_start_array - j) {
|
||||
_cleanup_free_ char *hint = NULL;
|
||||
|
||||
(void) partition_hint(p, context->node, &hint);
|
||||
|
||||
@@ -1264,6 +1264,29 @@ EOF
|
||||
assert_in "${loop}p3 : start= *${start}, size= *${size}, type=0FC63DAF-8483-4772-8E79-3D69D8477DE4, uuid=DB081670-07AE-48CA-9F5E-813D5E40B976, name=\"linux-generic-2\"" "$output"
|
||||
}
|
||||
|
||||
testcase_dropped_partitions() {
|
||||
local workdir image defs
|
||||
|
||||
workdir="$(mktemp --directory "/tmp/test-repart.dropped-partitions.XXXXXXXXXX")"
|
||||
# shellcheck disable=SC2064
|
||||
trap "rm -rf '${workdir:?}'" RETURN
|
||||
|
||||
image="$workdir/image.img"
|
||||
truncate -s 32M "$image"
|
||||
|
||||
defs="$workdir/defs"
|
||||
mkdir "$defs"
|
||||
echo -ne "[Partition]\nType=root\n" >"$defs/10-part1.conf"
|
||||
echo -ne "[Partition]\nType=root\nSizeMinBytes=1T\nPriority=1\n" >"$defs/11-dropped-first.conf"
|
||||
echo -ne "[Partition]\nType=root\n" >"$defs/12-part2.conf"
|
||||
echo -ne "[Partition]\nType=root\nSizeMinBytes=1T\nPriority=2\n" >"$defs/13-dropped-second.conf"
|
||||
|
||||
systemd-repart --empty=allow --pretty=yes --dry-run=no --definitions="$defs" "$image"
|
||||
|
||||
sfdisk -q -l "$image"
|
||||
[[ "$(sfdisk -q -l "$image" | grep -c "$image")" -eq 2 ]]
|
||||
}
|
||||
|
||||
OFFLINE="yes"
|
||||
run_testcases
|
||||
|
||||
|
||||
Reference in New Issue
Block a user