]>
Commit | Line | Data |
---|---|---|
53e1b683 | 1 | /* SPDX-License-Identifier: LGPL-2.1+ */ |
449ddb2d | 2 | |
449ddb2d | 3 | #include <errno.h> |
cf0fbc49 | 4 | #include <mntent.h> |
449ddb2d | 5 | #include <string.h> |
b16fee15 | 6 | #include <sys/prctl.h> |
449ddb2d LP |
7 | #include <sys/stat.h> |
8 | #include <sys/wait.h> | |
cf0fbc49 | 9 | #include <unistd.h> |
449ddb2d | 10 | |
4349cd7c | 11 | #include "exit-status.h" |
449ddb2d | 12 | #include "log.h" |
5e332028 | 13 | #include "main-func.h" |
4349cd7c LP |
14 | #include "mount-setup.h" |
15 | #include "mount-util.h" | |
9eb977db | 16 | #include "path-util.h" |
b16fee15 | 17 | #include "process-util.h" |
24882e06 | 18 | #include "signal-util.h" |
b16fee15 | 19 | #include "strv.h" |
4349cd7c | 20 | #include "util.h" |
449ddb2d LP |
21 | |
22 | /* Goes through /etc/fstab and remounts all API file systems, applying | |
23 | * options that are in /etc/fstab that systemd might not have | |
24 | * respected */ | |
25 | ||
6e61c701 | 26 | static int run(int argc, char *argv[]) { |
b16fee15 | 27 | _cleanup_hashmap_free_free_ Hashmap *pids = NULL; |
5862d652 | 28 | _cleanup_endmntent_ FILE *f = NULL; |
449ddb2d | 29 | struct mntent* me; |
b16fee15 | 30 | int r; |
449ddb2d | 31 | |
6bf3c61c | 32 | log_setup_service(); |
449ddb2d | 33 | |
baaa35ad ZJS |
34 | if (argc > 1) |
35 | return log_error_errno(SYNTHETIC_ERRNO(EINVAL), | |
36 | "This program takes no arguments."); | |
6e61c701 | 37 | |
4c12626c LP |
38 | umask(0022); |
39 | ||
9ffcff0e | 40 | f = setmntent("/etc/fstab", "re"); |
adb2ce5f | 41 | if (!f) { |
6e61c701 ZJS |
42 | if (errno == ENOENT) |
43 | return 0; | |
e0295d26 | 44 | |
6e61c701 | 45 | return log_error_errno(errno, "Failed to open /etc/fstab: %m"); |
449ddb2d LP |
46 | } |
47 | ||
d5099efc | 48 | pids = hashmap_new(NULL); |
6e61c701 ZJS |
49 | if (!pids) |
50 | return log_oom(); | |
449ddb2d | 51 | |
449ddb2d | 52 | while ((me = getmntent(f))) { |
6e61c701 | 53 | _cleanup_free_ char *s = NULL; |
449ddb2d LP |
54 | pid_t pid; |
55 | int k; | |
449ddb2d | 56 | |
b4efdf97 | 57 | /* Remount the root fs, /usr and all API VFS */ |
2b93b027 | 58 | if (!mount_point_is_api(me->mnt_dir) && |
b4efdf97 LP |
59 | !path_equal(me->mnt_dir, "/") && |
60 | !path_equal(me->mnt_dir, "/usr")) | |
449ddb2d LP |
61 | continue; |
62 | ||
63 | log_debug("Remounting %s", me->mnt_dir); | |
64 | ||
0672e2c6 | 65 | r = safe_fork("(remount)", FORK_RESET_SIGNALS|FORK_DEATHSIG|FORK_RLIMIT_NOFILE_SAFE|FORK_LOG, &pid); |
b6e1fff1 | 66 | if (r < 0) |
6e61c701 | 67 | return r; |
4c253ed1 | 68 | if (r == 0) { |
449ddb2d LP |
69 | /* Child */ |
70 | ||
b16fee15 | 71 | execv(MOUNT_PATH, STRV_MAKE(MOUNT_PATH, me->mnt_dir, "-o", "remount")); |
449ddb2d | 72 | |
f00929ad | 73 | log_error_errno(errno, "Failed to execute " MOUNT_PATH ": %m"); |
22f4096c | 74 | _exit(EXIT_FAILURE); |
449ddb2d LP |
75 | } |
76 | ||
77 | /* Parent */ | |
78 | ||
79 | s = strdup(me->mnt_dir); | |
6e61c701 ZJS |
80 | if (!s) |
81 | return log_oom(); | |
adb2ce5f | 82 | |
4a0b58c4 | 83 | k = hashmap_put(pids, PID_TO_PTR(pid), s); |
6e61c701 ZJS |
84 | if (k < 0) |
85 | return log_oom(); | |
86 | TAKE_PTR(s); | |
449ddb2d LP |
87 | } |
88 | ||
b16fee15 | 89 | r = 0; |
449ddb2d | 90 | while (!hashmap_isempty(pids)) { |
b92bea5d | 91 | siginfo_t si = {}; |
6e61c701 | 92 | _cleanup_free_ char *s = NULL; |
449ddb2d | 93 | |
449ddb2d | 94 | if (waitid(P_ALL, 0, &si, WEXITED) < 0) { |
449ddb2d LP |
95 | if (errno == EINTR) |
96 | continue; | |
97 | ||
6e61c701 | 98 | return log_error_errno(errno, "waitid() failed: %m"); |
449ddb2d LP |
99 | } |
100 | ||
4a0b58c4 | 101 | s = hashmap_remove(pids, PID_TO_PTR(si.si_pid)); |
6e61c701 ZJS |
102 | if (s && |
103 | !is_clean_exit(si.si_code, si.si_status, EXIT_CLEAN_COMMAND, NULL)) { | |
104 | if (si.si_code == CLD_EXITED) | |
105 | log_error(MOUNT_PATH " for %s exited with exit status %i.", s, si.si_status); | |
106 | else | |
107 | log_error(MOUNT_PATH " for %s terminated by signal %s.", s, signal_to_string(si.si_status)); | |
108 | ||
109 | r = -ENOEXEC; | |
449ddb2d LP |
110 | } |
111 | } | |
112 | ||
6e61c701 | 113 | return r; |
449ddb2d | 114 | } |
6e61c701 ZJS |
115 | |
116 | DEFINE_MAIN_FUNCTION(run); |