]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
fsck: look for fsck binary not just in /sbin
authorFlorian Klink <flokli@flokli.de>
Thu, 13 Apr 2023 20:54:54 +0000 (22:54 +0200)
committerLuca Boccassi <luca.boccassi@gmail.com>
Sat, 15 Apr 2023 09:29:50 +0000 (10:29 +0100)
This removes remaining hardcoded occurences of `/sbin/fsck`, and instead
uses `find_executable` to find `fsck`.

We also use `fsck_exists_for_fstype` to check for the `fsck.*`
executable, which also checks in `$PATH`, so it's fair to assume fsck
itself is also available.

man/systemd-fsck@.service.xml
src/fsck/fsck.c
src/home/homework-luks.c
src/shared/dissect-image.c

index e928aebdb335c4e0d73ddbaedd3476c2807bba9e..403286829e1e7ec4efd7769c70df54d8c28308af 100644 (file)
     <para><filename>systemd-fsck</filename> does not know any details
     about specific filesystems, and simply executes file system
     checkers specific to each filesystem type
-    (<filename>/sbin/fsck.<replaceable>type</replaceable></filename>). These checkers will decide if
+    (<filename>fsck.<replaceable>type</replaceable></filename>). These checkers will decide if
     the filesystem should actually be checked based on the time since
     last check, number of mounts, unclean unmount, etc.</para>
 
     <para><filename>systemd-fsck-root.service</filename> and <filename>systemd-fsck-usr.service</filename>
-    will activate <filename>reboot.target</filename> if <filename>/sbin/fsck</filename> returns the "System
-    should reboot" condition, or <filename>emergency.target</filename> if <filename>/sbin/fsck</filename>
+    will activate <filename>reboot.target</filename> if <filename>fsck</filename> returns the "System
+    should reboot" condition, or <filename>emergency.target</filename> if <filename>fsck</filename>
     returns the "Filesystem errors left uncorrected" condition.</para>
 
     <para><filename>systemd-fsck@.service</filename> will fail if
-    <filename>/sbin/fsck</filename> returns with either "System should reboot"
+    <filename>fsck</filename> returns with either "System should reboot"
     or "Filesystem errors left uncorrected" conditions. For filesystems
     listed in <filename>/etc/fstab</filename> without <literal>nofail</literal>
     or <literal>noauto</literal> options, <literal>local-fs.target</literal>
index cfdc6b24bf908aa8198e7acc06a2499f26a41056..4d29babbd332ebb826e1ed8195b711b2cdc6baa4 100644 (file)
@@ -345,6 +345,7 @@ static int run(int argc, char *argv[]) {
         if (r == 0) {
                 char dash_c[STRLEN("-C") + DECIMAL_STR_MAX(int) + 1];
                 int progress_socket = -1;
+                _cleanup_free_ char *fsck_path = NULL;
                 const char *cmdline[9];
                 int i = 0;
 
@@ -365,7 +366,13 @@ static int run(int argc, char *argv[]) {
                 } else
                         dash_c[0] = 0;
 
-                cmdline[i++] = "/sbin/fsck";
+                r = find_executable("fsck", &fsck_path);
+                if (r < 0) {
+                        log_error_errno(r, "Cannot find fsck binary: %m");
+                        _exit(FSCK_OPERATIONAL_ERROR);
+                }
+
+                cmdline[i++] = fsck_path;
                 cmdline[i++] =  arg_repair;
                 cmdline[i++] = "-T";
 
index ac3d2b417c631080a029dfd6d5268a955d77be55..dda63d8fc052a1bddc22b7f9b7b85073080b1fc9 100644 (file)
@@ -215,6 +215,7 @@ static int block_get_size_by_path(const char *path, uint64_t *ret) {
 static int run_fsck(const char *node, const char *fstype) {
         int r, exit_status;
         pid_t fsck_pid;
+        _cleanup_free_ char *fsck_path = NULL;
 
         assert(node);
         assert(fstype);
@@ -227,6 +228,14 @@ static int run_fsck(const char *node, const char *fstype) {
                 return 0;
         }
 
+        r = find_executable("fsck", &fsck_path);
+        /* We proceed anyway if we can't determine whether the fsck
+         * binary for some specific fstype exists,
+         * but the lack of the main fsck binary should be considered
+         * an error. */
+        if (r < 0)
+                return log_error_errno(r, "Cannot find fsck binary: %m");
+
         r = safe_fork("(fsck)",
                       FORK_RESET_SIGNALS|FORK_RLIMIT_NOFILE_SAFE|FORK_DEATHSIG|FORK_LOG|FORK_STDOUT_TO_STDERR|FORK_CLOSE_ALL_FDS,
                       &fsck_pid);
@@ -234,7 +243,7 @@ static int run_fsck(const char *node, const char *fstype) {
                 return r;
         if (r == 0) {
                 /* Child */
-                execl("/sbin/fsck", "/sbin/fsck", "-aTl", node, NULL);
+                execl(fsck_path, fsck_path, "-aTl", node, NULL);
                 log_open();
                 log_error_errno(errno, "Failed to execute fsck: %m");
                 _exit(FSCK_OPERATIONAL_ERROR);
index 46c42cfc953bc554648d56001d505115f7f93c0d..b7c049e4c3a01bb072e058800b2c501d53d06cd8 100644 (file)
@@ -1693,6 +1693,7 @@ static int is_loop_device(const char *path) {
 static int run_fsck(int node_fd, const char *fstype) {
         int r, exit_status;
         pid_t pid;
+        _cleanup_free_ char *fsck_path = NULL;
 
         assert(node_fd >= 0);
         assert(fstype);
@@ -1707,6 +1708,14 @@ static int run_fsck(int node_fd, const char *fstype) {
                 return 0;
         }
 
+        r = find_executable("fsck", &fsck_path);
+        /* We proceed anyway if we can't determine whether the fsck
+         * binary for some specific fstype exists,
+         * but the lack of the main fsck binary should be considered
+         * an error. */
+        if (r < 0)
+                return log_error_errno(r, "Cannot find fsck binary: %m");
+
         r = safe_fork_full(
                         "(fsck)",
                         NULL,
@@ -1717,7 +1726,7 @@ static int run_fsck(int node_fd, const char *fstype) {
                 return log_debug_errno(r, "Failed to fork off fsck: %m");
         if (r == 0) {
                 /* Child */
-                execl("/sbin/fsck", "/sbin/fsck", "-aT", FORMAT_PROC_FD_PATH(node_fd), NULL);
+                execl(fsck_path, fsck_path, "-aT", FORMAT_PROC_FD_PATH(node_fd), NULL);
                 log_open();
                 log_debug_errno(errno, "Failed to execl() fsck: %m");
                 _exit(FSCK_OPERATIONAL_ERROR);
@@ -1725,7 +1734,7 @@ static int run_fsck(int node_fd, const char *fstype) {
 
         exit_status = wait_for_terminate_and_check("fsck", pid, 0);
         if (exit_status < 0)
-                return log_debug_errno(exit_status, "Failed to fork off /sbin/fsck: %m");
+                return log_debug_errno(exit_status, "Failed to fork off %s: %m", fsck_path);
 
         if ((exit_status & ~FSCK_ERROR_CORRECTED) != FSCK_SUCCESS) {
                 log_debug("fsck failed with exit status %i.", exit_status);