repart: Allow overriding fstype per partition designator
authorDaan De Meyer <daan.j.demeyer@gmail.com>
Tue, 2 Jul 2024 16:34:39 +0000 (18:34 +0200)
committerDaan De Meyer <daan.j.demeyer@gmail.com>
Tue, 16 Jul 2024 13:35:36 +0000 (15:35 +0200)
$SYSTEMD_REPART_OVERRIDE_FSTYPE is too invasive. Often you want to
override the fstype only for a specific designator, so let's support
that as well.

(cherry picked from commit 90a255779d1f8e6697e08e91918df88bb52274ad)

docs/ENVIRONMENT.md
src/partition/repart.c
src/shared/gpt.c
src/shared/gpt.h

index b661f18fc01a696ea93286c4fa26098e35aca515..c8b75ac2655f40d7ec50213b507330362f900f3c 100644 (file)
@@ -634,6 +634,10 @@ SYSTEMD_HOME_DEBUG_SUFFIX=foo \
 
 * `$SYSTEMD_REPART_OVERRIDE_FSTYPE` – if set the value will override the file
   system type specified in Format= lines in partition definition files.
+  Additionally, the filesystem for all partitions with a specific designator can
+  be overridden via a correspondingly named environment variable. For example,
+  to override the filesystem type for all partitions with `Type=root`, you can
+  set `SYSTEMD_REPART_OVERRIDE_FSTYPE_ROOT=ext4`.
 
 `systemd-nspawn`, `systemd-networkd`:
 
index f87a87e26fa34e84217a057ebc8e328a774de0d8..8a5ce7e9455a578c72a220360f584ccbe0ee3ce4 100644 (file)
@@ -1895,6 +1895,34 @@ static int config_parse_encrypted_volume(
 static DEFINE_CONFIG_PARSE_ENUM_WITH_DEFAULT(config_parse_verity, verity_mode, VerityMode, VERITY_OFF, "Invalid verity mode");
 static DEFINE_CONFIG_PARSE_ENUM_WITH_DEFAULT(config_parse_minimize, minimize_mode, MinimizeMode, MINIMIZE_OFF, "Invalid minimize mode");
 
+static int partition_finalize_fstype(Partition *p, const char *path) {
+        _cleanup_free_ char *e = NULL, *upper = NULL;
+
+        assert(p);
+        assert(path);
+
+        if (!gpt_partition_type_has_filesystem(p->type))
+                return 0;
+
+        upper = strdup(partition_designator_to_string(p->type.designator));
+        if (!upper)
+                return log_oom();
+
+        e = strjoin("SYSTEMD_REPART_OVERRIDE_FSTYPE_", string_replace_char(ascii_strupper(upper), '-', '_'));
+        if (!e)
+                return log_oom();
+
+        const char *v = secure_getenv(e);
+        if (!v || streq(p->format, v))
+                return 0;
+
+        log_syntax(NULL, LOG_NOTICE, path, 1, 0,
+                   "Overriding defined file system type '%s' for '%s' partition with '%s'.",
+                   p->format, partition_designator_to_string(p->type.designator), v);
+
+        return free_and_strdup_warn(&p->format, v);
+}
+
 static int partition_read_definition(Partition *p, const char *path, const char *const *conf_file_dirs) {
 
         ConfigTableItem table[] = {
@@ -2084,6 +2112,10 @@ static int partition_read_definition(Partition *p, const char *path, const char
         } else if (streq(p->split_name_format, "-"))
                 p->split_name_format = mfree(p->split_name_format);
 
+        r = partition_finalize_fstype(p, path);
+        if (r < 0)
+                return r;
+
         return 1;
 }
 
index d639463c24f542e74963ff7afe318881b937b33a..7d40c4ab5e83ea75197ee80a397da0aada26f8f5 100644 (file)
@@ -339,6 +339,18 @@ bool gpt_partition_type_knows_no_auto(GptPartitionType type) {
                       PARTITION_SWAP);
 }
 
+bool gpt_partition_type_has_filesystem(GptPartitionType type) {
+        return IN_SET(type.designator,
+                      PARTITION_ROOT,
+                      PARTITION_USR,
+                      PARTITION_HOME,
+                      PARTITION_SRV,
+                      PARTITION_ESP,
+                      PARTITION_XBOOTLDR,
+                      PARTITION_TMP,
+                      PARTITION_VAR);
+}
+
 bool gpt_header_has_signature(const GptHeader *p) {
         assert(p);
 
index 21976e5311f95d9e3bbabf1c36afc86c6c800f79..3d04c19cc578a4681962e2f675a39a3f0b00681a 100644 (file)
@@ -72,6 +72,7 @@ const char *gpt_partition_type_mountpoint_nulstr(GptPartitionType type);
 bool gpt_partition_type_knows_read_only(GptPartitionType type);
 bool gpt_partition_type_knows_growfs(GptPartitionType type);
 bool gpt_partition_type_knows_no_auto(GptPartitionType type);
+bool gpt_partition_type_has_filesystem(GptPartitionType type);
 
 typedef struct {
         uint8_t partition_type_guid[16];