diff --git a/src/fstab-generator/fstab-generator.c b/src/fstab-generator/fstab-generator.c index 7e84be499d7..17791b965f1 100644 --- a/src/fstab-generator/fstab-generator.c +++ b/src/fstab-generator/fstab-generator.c @@ -420,14 +420,19 @@ static int write_mounts_for( return 0; } -static int write_extra_dependencies(FILE *f, const char *where, const char *opts) { +static bool has_pre_dependencies(const char *opts) { + return fstab_test_option( + opts, + "x-systemd.after\0" + "x-systemd.requires\0" + "x-systemd.wants\0" + "x-systemd.requires-mounts-for\0" + "x-systemd.wants-mounts-for\0"); +} + +static int write_pre_dependencies(FILE *f, const char *where, const char *opts) { int r; - assert(f); - - if (isempty(opts)) - return 0; - r = write_after(f, where, opts); if (r < 0) return r; @@ -440,10 +445,6 @@ static int write_extra_dependencies(FILE *f, const char *where, const char *opts if (r < 0) return r; - r = write_before(f, where, opts); - if (r < 0) - return r; - r = write_mounts_for(f, where, opts, "x-systemd.requires-mounts-for\0", "RequiresMountsFor"); if (r < 0) @@ -457,6 +458,52 @@ static int write_extra_dependencies(FILE *f, const char *where, const char *opts return 0; } +static int write_extra_dependencies( + const char *source, const char *dest, FILE *f, const char *where, const char *opts) { + int r; + + assert(f); + + if (isempty(opts)) + return 0; + + r = write_before(f, where, opts); + if (r < 0) + return r; + + r = has_pre_dependencies(opts); + if (r <= 0) + return r; + + _cleanup_free_ char *pre_name = NULL; + _cleanup_fclose_ FILE *pre_f = NULL; + + r = unit_name_from_path_instance("fs-pre", where, ".target", &pre_name); + if (r < 0) + return log_error_errno(r, "Failed to generate unit name: %m"); + + fprintf(f, + "Requires=%s\n" + "After=%s\n", + pre_name, + pre_name); + + r = generator_open_unit_file(dest, source, pre_name, &pre_f); + if (r < 0) + return r; + + fprintf(pre_f, + "[Unit]\n" + "Documentation=man:fstab(5) man:systemd-fstab-generator(8)\n" + "SourcePath=%s\n", + source); + r = write_pre_dependencies(pre_f, where, opts); + if (r < 0) + return log_error_errno(r, "Failed to write pre dependencies: %m"); + + return 0; +} + static int mandatory_mount_drop_unapplicable_options( MountPointFlags *flags, const char *where, @@ -588,7 +635,7 @@ static int add_mount( f); } - r = write_extra_dependencies(f, where, opts); + r = write_extra_dependencies(source, dest, f, where, opts); if (r < 0) return r; diff --git a/src/shared/generator.c b/src/shared/generator.c index f2997c1b167..5db048f4daf 100644 --- a/src/shared/generator.c +++ b/src/shared/generator.c @@ -326,7 +326,7 @@ int generator_write_fsck_deps( return log_error_errno(errno, "Failed to create symlink %s: %m", lnk); } else { - _cleanup_free_ char *_fsck = NULL; + _cleanup_free_ char *_fsck = NULL, *fs_pre_unit = NULL; const char *fsck, *dep; if (in_initrd() && path_equal(where, "/sysroot")) { @@ -363,6 +363,23 @@ int generator_write_fsck_deps( "%1$s=%2$s\n" "After=%2$s\n", dep, fsck); + + r = unit_name_from_path_instance("fs-pre", where, ".target", &fs_pre_unit); + if (r < 0) + return r; + + r = write_drop_in_format( + dir, + fsck, + 50, + "fs-pre", + "# Automatically generated by %s\n" + "[Unit]\n" + "After=%s", + program_invocation_short_name, + fs_pre_unit); + if (r < 0) + return r; } return 0; @@ -597,7 +614,8 @@ int generator_hook_up_mkfs( const char *where, const char *type) { - _cleanup_free_ char *node = NULL, *unit = NULL, *escaped = NULL, *where_unit = NULL; + _cleanup_free_ char *node = NULL, *unit = NULL, *escaped = NULL, *where_unit = NULL, + *fs_pre_unit = NULL; _cleanup_fclose_ FILE *f = NULL; const char *fsck_unit; int r; @@ -642,6 +660,10 @@ int generator_hook_up_mkfs( return log_error_errno(r, "Failed to make unit name from path \"%s\": %m", where); + r = unit_name_from_path_instance("fs-pre", where, ".target", &fs_pre_unit); + if (r < 0) + return log_error_errno(r, "Failed to make unit name from path \"%s\": %m", where); + r = generator_open_unit_file(dir, /* source = */ NULL, unit, &f); if (r < 0) return r; @@ -654,6 +676,7 @@ int generator_hook_up_mkfs( "DefaultDependencies=no\n" "BindsTo=%%i.device\n" "After=%%i.device\n" + "After=%s\n" /* fsck might or might not be used, so let's be safe and order * ourselves before both systemd-fsck@.service and the mount unit. */ "Before=%s %s\n" @@ -665,6 +688,7 @@ int generator_hook_up_mkfs( "RemainAfterExit=yes\n" "ExecStart="SYSTEMD_MAKEFS_PATH " %s %s\n" "TimeoutSec=infinity\n", + fs_pre_unit, fsck_unit, where_unit, type,