1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
4 This file is part of systemd.
6 Copyright 2010 Lennart Poettering
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
31 #include <sys/resource.h>
32 #include <linux/sched.h>
33 #include <sys/types.h>
37 #include <sys/ioctl.h>
39 #include <linux/tiocl.h>
42 #include <sys/inotify.h>
46 #include <sys/prctl.h>
47 #include <sys/utsname.h>
49 #include <netinet/ip.h>
58 #include <linux/magic.h>
70 #include "path-util.h"
71 #include "exit-status.h"
75 char **saved_argv = NULL;
77 static volatile unsigned cached_columns = 0;
78 static volatile unsigned cached_lines = 0;
80 bool is_efiboot(void) {
81 return access("/sys/firmware/efi", F_OK) >= 0;
84 size_t page_size(void) {
85 static __thread size_t pgsz = 0;
88 if (_likely_(pgsz > 0))
91 r = sysconf(_SC_PAGESIZE);
98 bool streq_ptr(const char *a, const char *b) {
100 /* Like streq(), but tries to make sense of NULL pointers */
111 char* endswith(const char *s, const char *postfix) {
118 pl = strlen(postfix);
121 return (char*) s + sl;
126 if (memcmp(s + sl - pl, postfix, pl) != 0)
129 return (char*) s + sl - pl;
132 char* startswith(const char *s, const char *prefix) {
149 char* startswith_no_case(const char *s, const char *prefix) {
159 if (tolower(*a) != tolower(*b))
166 bool first_word(const char *s, const char *word) {
181 if (memcmp(s, word, wl) != 0)
185 strchr(WHITESPACE, s[wl]);
188 int close_nointr(int fd) {
203 void close_nointr_nofail(int fd) {
204 int saved_errno = errno;
206 /* like close_nointr() but cannot fail, and guarantees errno
209 assert_se(close_nointr(fd) == 0);
214 void close_many(const int fds[], unsigned n_fd) {
217 for (i = 0; i < n_fd; i++)
218 close_nointr_nofail(fds[i]);
221 int parse_boolean(const char *v) {
224 if (streq(v, "1") || v[0] == 'y' || v[0] == 'Y' || v[0] == 't' || v[0] == 'T' || !strcasecmp(v, "on"))
226 else if (streq(v, "0") || v[0] == 'n' || v[0] == 'N' || v[0] == 'f' || v[0] == 'F' || !strcasecmp(v, "off"))
232 int parse_pid(const char *s, pid_t* ret_pid) {
233 unsigned long ul = 0;
240 r = safe_atolu(s, &ul);
246 if ((unsigned long) pid != ul)
256 int parse_uid(const char *s, uid_t* ret_uid) {
257 unsigned long ul = 0;
264 r = safe_atolu(s, &ul);
270 if ((unsigned long) uid != ul)
277 int safe_atou(const char *s, unsigned *ret_u) {
285 l = strtoul(s, &x, 0);
287 if (!x || x == s || *x || errno)
288 return errno ? -errno : -EINVAL;
290 if ((unsigned long) (unsigned) l != l)
293 *ret_u = (unsigned) l;
297 int safe_atoi(const char *s, int *ret_i) {
305 l = strtol(s, &x, 0);
307 if (!x || x == s || *x || errno)
308 return errno ? -errno : -EINVAL;
310 if ((long) (int) l != l)
317 int safe_atollu(const char *s, long long unsigned *ret_llu) {
319 unsigned long long l;
325 l = strtoull(s, &x, 0);
327 if (!x || x == s || *x || errno)
328 return errno ? -errno : -EINVAL;
334 int safe_atolli(const char *s, long long int *ret_lli) {
342 l = strtoll(s, &x, 0);
344 if (!x || x == s || *x || errno)
345 return errno ? -errno : -EINVAL;
351 /* Split a string into words. */
352 char *split(const char *c, size_t *l, const char *separator, char **state) {
355 current = *state ? *state : (char*) c;
357 if (!*current || *c == 0)
360 current += strspn(current, separator);
361 *l = strcspn(current, separator);
364 return (char*) current;
367 /* Split a string into words, but consider strings enclosed in '' and
368 * "" as words even if they include spaces. */
369 char *split_quoted(const char *c, size_t *l, char **state) {
371 bool escaped = false;
373 current = *state ? *state : (char*) c;
375 if (!*current || *c == 0)
378 current += strspn(current, WHITESPACE);
380 if (*current == '\'') {
383 for (e = current; *e; e++) {
393 *state = *e == 0 ? e : e+1;
394 } else if (*current == '\"') {
397 for (e = current; *e; e++) {
407 *state = *e == 0 ? e : e+1;
409 for (e = current; *e; e++) {
414 else if (strchr(WHITESPACE, *e))
421 return (char*) current;
424 int get_parent_of_pid(pid_t pid, pid_t *_ppid) {
426 _cleanup_fclose_ FILE *f = NULL;
427 char fn[PATH_MAX], line[LINE_MAX], *p;
433 assert_se(snprintf(fn, sizeof(fn)-1, "/proc/%lu/stat", (unsigned long) pid) < (int) (sizeof(fn)-1));
440 if (!fgets(line, sizeof(line), f)) {
441 r = feof(f) ? -EIO : -errno;
445 /* Let's skip the pid and comm fields. The latter is enclosed
446 * in () but does not escape any () in its value, so let's
447 * skip over it manually */
449 p = strrchr(line, ')');
461 if ((long unsigned) (pid_t) ppid != ppid)
464 *_ppid = (pid_t) ppid;
469 int get_starttime_of_pid(pid_t pid, unsigned long long *st) {
470 _cleanup_fclose_ FILE *f = NULL;
471 char fn[PATH_MAX], line[LINE_MAX], *p;
476 assert_se(snprintf(fn, sizeof(fn)-1, "/proc/%lu/stat", (unsigned long) pid) < (int) (sizeof(fn)-1));
483 if (!fgets(line, sizeof(line), f)) {
490 /* Let's skip the pid and comm fields. The latter is enclosed
491 * in () but does not escape any () in its value, so let's
492 * skip over it manually */
494 p = strrchr(line, ')');
516 "%*d " /* priority */
518 "%*d " /* num_threads */
519 "%*d " /* itrealvalue */
520 "%llu " /* starttime */,
527 int write_one_line_file(const char *fn, const char *line) {
528 _cleanup_fclose_ FILE *f = NULL;
538 if (fputs(line, f) < 0)
539 return errno ? -errno : -EIO;
541 if (!endswith(line, "\n"))
547 return errno ? -errno : -EIO;
552 int fchmod_umask(int fd, mode_t m) {
557 r = fchmod(fd, m & (~u)) < 0 ? -errno : 0;
563 int write_one_line_file_atomic(const char *fn, const char *line) {
571 r = fopen_temporary(fn, &f, &p);
575 fchmod_umask(fileno(f), 0644);
578 if (fputs(line, f) < 0) {
583 if (!endswith(line, "\n"))
594 if (rename(p, fn) < 0)
610 int read_one_line_file(const char *fn, char **line) {
611 _cleanup_fclose_ FILE *f = NULL;
612 char t[LINE_MAX], *c;
621 if (!fgets(t, sizeof(t), f)) {
624 return errno ? -errno : -EIO;
638 int read_full_file(const char *fn, char **contents, size_t *size) {
639 _cleanup_fclose_ FILE *f = NULL;
641 _cleanup_free_ char *buf = NULL;
651 if (fstat(fileno(f), &st) < 0)
655 if (st.st_size > 4*1024*1024)
658 n = st.st_size > 0 ? st.st_size : LINE_MAX;
665 t = realloc(buf, n+1);
670 k = fread(buf + l, 1, n - l, f);
699 const char *separator, ...) {
702 char *contents = NULL, *p;
707 if ((r = read_full_file(fname, &contents, NULL)) < 0)
712 const char *key = NULL;
714 p += strspn(p, separator);
715 p += strspn(p, WHITESPACE);
720 if (!strchr(COMMENTS, *p)) {
724 va_start(ap, separator);
725 while ((key = va_arg(ap, char *))) {
729 value = va_arg(ap, char **);
732 if (strncmp(p, key, n) != 0 ||
737 n = strcspn(p, separator);
740 strchr(QUOTES, p[0]) &&
742 v = strndup(p+1, n-2);
753 /* return empty value strings as NULL */
770 p += strcspn(p, separator);
791 if (!(f = fopen(fname, "re")))
795 char l[LINE_MAX], *p, *u, *cs;
798 if (!fgets(l, sizeof(l), f)) {
808 cs = endswith(l, "\\\n");
833 p = strstrip(c ? c : l);
838 if (strchr(COMMENTS, *p))
841 if (!(u = normalize_env_assignment(p))) {
848 t = strv_append(m, u);
876 int write_env_file(const char *fname, char **l) {
881 r = fopen_temporary(fname, &f, &p);
885 fchmod_umask(fileno(f), 0644);
901 if (rename(p, fname) < 0)
916 char *truncate_nl(char *s) {
919 s[strcspn(s, NEWLINE)] = 0;
923 int get_process_comm(pid_t pid, char **name) {
929 r = read_one_line_file("/proc/self/comm", name);
932 if (asprintf(&p, "/proc/%lu/comm", (unsigned long) pid) < 0)
935 r = read_one_line_file(p, name);
942 int get_process_cmdline(pid_t pid, size_t max_length, bool comm_fallback, char **line) {
950 f = fopen("/proc/self/cmdline", "re");
953 if (asprintf(&p, "/proc/%lu/cmdline", (unsigned long) pid) < 0)
962 if (max_length == 0) {
964 while ((c = getc(f)) != EOF) {
965 k = realloc(r, len+1);
972 r[len-1] = isprint(c) ? c : ' ';
979 r = new(char, max_length);
987 while ((c = getc(f)) != EOF) {
1009 size_t n = MIN(left-1, 3U);
1010 memcpy(k, "...", n);
1018 /* Kernel threads have no argv[] */
1019 if (r == NULL || r[0] == 0) {
1028 h = get_process_comm(pid, &t);
1032 r = strjoin("[", t, "]", NULL);
1043 int is_kernel_thread(pid_t pid) {
1053 if (asprintf(&p, "/proc/%lu/cmdline", (unsigned long) pid) < 0)
1062 count = fread(&c, 1, 1, f);
1066 /* Kernel threads have an empty cmdline */
1069 return eof ? 1 : -errno;
1074 int get_process_exe(pid_t pid, char **name) {
1080 r = readlink_malloc("/proc/self/exe", name);
1083 if (asprintf(&p, "/proc/%lu/exe", (unsigned long) pid) < 0)
1086 r = readlink_malloc(p, name);
1093 static int get_process_id(pid_t pid, const char *field, uid_t *uid) {
1103 if (asprintf(&p, "/proc/%lu/status", (unsigned long) pid) < 0)
1113 char line[LINE_MAX], *l;
1115 if (!fgets(line, sizeof(line), f)) {
1125 if (startswith(l, field)) {
1127 l += strspn(l, WHITESPACE);
1129 l[strcspn(l, WHITESPACE)] = 0;
1131 r = parse_uid(l, uid);
1144 int get_process_uid(pid_t pid, uid_t *uid) {
1145 return get_process_id(pid, "Uid:", uid);
1148 int get_process_gid(pid_t pid, gid_t *gid) {
1149 return get_process_id(pid, "Gid:", gid);
1152 char *strnappend(const char *s, const char *suffix, size_t b) {
1160 return strndup(suffix, b);
1169 if (b > ((size_t) -1) - a)
1172 r = new(char, a+b+1);
1177 memcpy(r+a, suffix, b);
1183 char *strappend(const char *s, const char *suffix) {
1184 return strnappend(s, suffix, suffix ? strlen(suffix) : 0);
1187 int readlink_malloc(const char *p, char **r) {
1197 if (!(c = new(char, l)))
1200 if ((n = readlink(p, c, l-1)) < 0) {
1206 if ((size_t) n < l-1) {
1217 int readlink_and_make_absolute(const char *p, char **r) {
1224 if ((j = readlink_malloc(p, &target)) < 0)
1227 k = file_in_same_dir(p, target);
1237 int readlink_and_canonicalize(const char *p, char **r) {
1244 j = readlink_and_make_absolute(p, &t);
1248 s = canonicalize_file_name(t);
1255 path_kill_slashes(*r);
1260 int reset_all_signal_handlers(void) {
1263 for (sig = 1; sig < _NSIG; sig++) {
1264 struct sigaction sa;
1266 if (sig == SIGKILL || sig == SIGSTOP)
1270 sa.sa_handler = SIG_DFL;
1271 sa.sa_flags = SA_RESTART;
1273 /* On Linux the first two RT signals are reserved by
1274 * glibc, and sigaction() will return EINVAL for them. */
1275 if ((sigaction(sig, &sa, NULL) < 0))
1276 if (errno != EINVAL)
1283 char *strstrip(char *s) {
1286 /* Drops trailing whitespace. Modifies the string in
1287 * place. Returns pointer to first non-space character */
1289 s += strspn(s, WHITESPACE);
1291 for (e = strchr(s, 0); e > s; e --)
1292 if (!strchr(WHITESPACE, e[-1]))
1300 char *delete_chars(char *s, const char *bad) {
1303 /* Drops all whitespace, regardless where in the string */
1305 for (f = s, t = s; *f; f++) {
1306 if (strchr(bad, *f))
1317 bool in_charset(const char *s, const char* charset) {
1323 for (i = s; *i; i++)
1324 if (!strchr(charset, *i))
1330 char *file_in_same_dir(const char *path, const char *filename) {
1337 /* This removes the last component of path and appends
1338 * filename, unless the latter is absolute anyway or the
1341 if (path_is_absolute(filename))
1342 return strdup(filename);
1344 if (!(e = strrchr(path, '/')))
1345 return strdup(filename);
1347 k = strlen(filename);
1348 if (!(r = new(char, e-path+1+k+1)))
1351 memcpy(r, path, e-path+1);
1352 memcpy(r+(e-path)+1, filename, k+1);
1357 int rmdir_parents(const char *path, const char *stop) {
1366 /* Skip trailing slashes */
1367 while (l > 0 && path[l-1] == '/')
1373 /* Skip last component */
1374 while (l > 0 && path[l-1] != '/')
1377 /* Skip trailing slashes */
1378 while (l > 0 && path[l-1] == '/')
1384 if (!(t = strndup(path, l)))
1387 if (path_startswith(stop, t)) {
1396 if (errno != ENOENT)
1404 char hexchar(int x) {
1405 static const char table[16] = "0123456789abcdef";
1407 return table[x & 15];
1410 int unhexchar(char c) {
1412 if (c >= '0' && c <= '9')
1415 if (c >= 'a' && c <= 'f')
1416 return c - 'a' + 10;
1418 if (c >= 'A' && c <= 'F')
1419 return c - 'A' + 10;
1424 char octchar(int x) {
1425 return '0' + (x & 7);
1428 int unoctchar(char c) {
1430 if (c >= '0' && c <= '7')
1436 char decchar(int x) {
1437 return '0' + (x % 10);
1440 int undecchar(char c) {
1442 if (c >= '0' && c <= '9')
1448 char *cescape(const char *s) {
1454 /* Does C style string escaping. */
1456 r = new(char, strlen(s)*4 + 1);
1460 for (f = s, t = r; *f; f++)
1506 /* For special chars we prefer octal over
1507 * hexadecimal encoding, simply because glib's
1508 * g_strescape() does the same */
1509 if ((*f < ' ') || (*f >= 127)) {
1511 *(t++) = octchar((unsigned char) *f >> 6);
1512 *(t++) = octchar((unsigned char) *f >> 3);
1513 *(t++) = octchar((unsigned char) *f);
1524 char *cunescape_length_with_prefix(const char *s, size_t length, const char *prefix) {
1531 /* Undoes C style string escaping, and optionally prefixes it. */
1533 pl = prefix ? strlen(prefix) : 0;
1535 r = new(char, pl+length+1);
1540 memcpy(r, prefix, pl);
1542 for (f = s, t = r + pl; f < s + length; f++) {
1585 /* This is an extension of the XDG syntax files */
1590 /* hexadecimal encoding */
1593 a = unhexchar(f[1]);
1594 b = unhexchar(f[2]);
1596 if (a < 0 || b < 0) {
1597 /* Invalid escape code, let's take it literal then */
1601 *(t++) = (char) ((a << 4) | b);
1616 /* octal encoding */
1619 a = unoctchar(f[0]);
1620 b = unoctchar(f[1]);
1621 c = unoctchar(f[2]);
1623 if (a < 0 || b < 0 || c < 0) {
1624 /* Invalid escape code, let's take it literal then */
1628 *(t++) = (char) ((a << 6) | (b << 3) | c);
1636 /* premature end of string.*/
1641 /* Invalid escape code, let's take it literal then */
1653 char *cunescape_length(const char *s, size_t length) {
1654 return cunescape_length_with_prefix(s, length, NULL);
1657 char *cunescape(const char *s) {
1660 return cunescape_length(s, strlen(s));
1663 char *xescape(const char *s, const char *bad) {
1667 /* Escapes all chars in bad, in addition to \ and all special
1668 * chars, in \xFF style escaping. May be reversed with
1671 r = new(char, strlen(s) * 4 + 1);
1675 for (f = s, t = r; *f; f++) {
1677 if ((*f < ' ') || (*f >= 127) ||
1678 (*f == '\\') || strchr(bad, *f)) {
1681 *(t++) = hexchar(*f >> 4);
1682 *(t++) = hexchar(*f);
1692 char *bus_path_escape(const char *s) {
1698 /* Escapes all chars that D-Bus' object path cannot deal
1699 * with. Can be reverse with bus_path_unescape() */
1701 if (!(r = new(char, strlen(s)*3+1)))
1704 for (f = s, t = r; *f; f++) {
1706 if (!(*f >= 'A' && *f <= 'Z') &&
1707 !(*f >= 'a' && *f <= 'z') &&
1708 !(*f >= '0' && *f <= '9')) {
1710 *(t++) = hexchar(*f >> 4);
1711 *(t++) = hexchar(*f);
1721 char *bus_path_unescape(const char *f) {
1726 if (!(r = strdup(f)))
1729 for (t = r; *f; f++) {
1734 if ((a = unhexchar(f[1])) < 0 ||
1735 (b = unhexchar(f[2])) < 0) {
1736 /* Invalid escape code, let's take it literal then */
1739 *(t++) = (char) ((a << 4) | b);
1751 char *ascii_strlower(char *t) {
1756 for (p = t; *p; p++)
1757 if (*p >= 'A' && *p <= 'Z')
1758 *p = *p - 'A' + 'a';
1763 static bool ignore_file_allow_backup(const char *filename) {
1767 filename[0] == '.' ||
1768 streq(filename, "lost+found") ||
1769 streq(filename, "aquota.user") ||
1770 streq(filename, "aquota.group") ||
1771 endswith(filename, ".rpmnew") ||
1772 endswith(filename, ".rpmsave") ||
1773 endswith(filename, ".rpmorig") ||
1774 endswith(filename, ".dpkg-old") ||
1775 endswith(filename, ".dpkg-new") ||
1776 endswith(filename, ".swp");
1779 bool ignore_file(const char *filename) {
1782 if (endswith(filename, "~"))
1785 return ignore_file_allow_backup(filename);
1788 int fd_nonblock(int fd, bool nonblock) {
1793 if ((flags = fcntl(fd, F_GETFL, 0)) < 0)
1797 flags |= O_NONBLOCK;
1799 flags &= ~O_NONBLOCK;
1801 if (fcntl(fd, F_SETFL, flags) < 0)
1807 int fd_cloexec(int fd, bool cloexec) {
1812 if ((flags = fcntl(fd, F_GETFD, 0)) < 0)
1816 flags |= FD_CLOEXEC;
1818 flags &= ~FD_CLOEXEC;
1820 if (fcntl(fd, F_SETFD, flags) < 0)
1826 static bool fd_in_set(int fd, const int fdset[], unsigned n_fdset) {
1829 assert(n_fdset == 0 || fdset);
1831 for (i = 0; i < n_fdset; i++)
1838 int close_all_fds(const int except[], unsigned n_except) {
1843 assert(n_except == 0 || except);
1845 d = opendir("/proc/self/fd");
1850 /* When /proc isn't available (for example in chroots)
1851 * the fallback is brute forcing through the fd
1854 assert_se(getrlimit(RLIMIT_NOFILE, &rl) >= 0);
1855 for (fd = 3; fd < (int) rl.rlim_max; fd ++) {
1857 if (fd_in_set(fd, except, n_except))
1860 if (close_nointr(fd) < 0)
1861 if (errno != EBADF && r == 0)
1868 while ((de = readdir(d))) {
1871 if (ignore_file(de->d_name))
1874 if (safe_atoi(de->d_name, &fd) < 0)
1875 /* Let's better ignore this, just in case */
1884 if (fd_in_set(fd, except, n_except))
1887 if (close_nointr(fd) < 0) {
1888 /* Valgrind has its own FD and doesn't want to have it closed */
1889 if (errno != EBADF && r == 0)
1898 bool chars_intersect(const char *a, const char *b) {
1901 /* Returns true if any of the chars in a are in b. */
1902 for (p = a; *p; p++)
1909 bool fstype_is_network(const char *fstype) {
1910 static const char table[] =
1919 return nulstr_contains(table, fstype);
1923 _cleanup_close_ int fd;
1925 fd = open_terminal("/dev/tty0", O_RDWR|O_NOCTTY|O_CLOEXEC);
1931 TIOCL_GETKMSGREDIRECT,
1935 if (ioctl(fd, TIOCLINUX, tiocl) < 0)
1938 vt = tiocl[0] <= 0 ? 1 : tiocl[0];
1941 if (ioctl(fd, VT_ACTIVATE, vt) < 0)
1947 int read_one_char(FILE *f, char *ret, usec_t t, bool *need_nl) {
1948 struct termios old_termios, new_termios;
1950 char line[LINE_MAX];
1955 if (tcgetattr(fileno(f), &old_termios) >= 0) {
1956 new_termios = old_termios;
1958 new_termios.c_lflag &= ~ICANON;
1959 new_termios.c_cc[VMIN] = 1;
1960 new_termios.c_cc[VTIME] = 0;
1962 if (tcsetattr(fileno(f), TCSADRAIN, &new_termios) >= 0) {
1965 if (t != (usec_t) -1) {
1966 if (fd_wait_for_event(fileno(f), POLLIN, t) <= 0) {
1967 tcsetattr(fileno(f), TCSADRAIN, &old_termios);
1972 k = fread(&c, 1, 1, f);
1974 tcsetattr(fileno(f), TCSADRAIN, &old_termios);
1980 *need_nl = c != '\n';
1987 if (t != (usec_t) -1)
1988 if (fd_wait_for_event(fileno(f), POLLIN, t) <= 0)
1991 if (!fgets(line, sizeof(line), f))
1996 if (strlen(line) != 1)
2006 int ask(char *ret, const char *replies, const char *text, ...) {
2016 bool need_nl = true;
2019 fputs(ANSI_HIGHLIGHT_ON, stdout);
2026 fputs(ANSI_HIGHLIGHT_OFF, stdout);
2030 r = read_one_char(stdin, &c, (usec_t) -1, &need_nl);
2033 if (r == -EBADMSG) {
2034 puts("Bad input, please try again.");
2045 if (strchr(replies, c)) {
2050 puts("Read unexpected character, please try again.");
2054 int reset_terminal_fd(int fd, bool switch_to_text) {
2055 struct termios termios;
2058 /* Set terminal to some sane defaults */
2062 /* We leave locked terminal attributes untouched, so that
2063 * Plymouth may set whatever it wants to set, and we don't
2064 * interfere with that. */
2066 /* Disable exclusive mode, just in case */
2067 ioctl(fd, TIOCNXCL);
2069 /* Switch to text mode */
2071 ioctl(fd, KDSETMODE, KD_TEXT);
2073 /* Enable console unicode mode */
2074 ioctl(fd, KDSKBMODE, K_UNICODE);
2076 if (tcgetattr(fd, &termios) < 0) {
2081 /* We only reset the stuff that matters to the software. How
2082 * hardware is set up we don't touch assuming that somebody
2083 * else will do that for us */
2085 termios.c_iflag &= ~(IGNBRK | BRKINT | ISTRIP | INLCR | IGNCR | IUCLC);
2086 termios.c_iflag |= ICRNL | IMAXBEL | IUTF8;
2087 termios.c_oflag |= ONLCR;
2088 termios.c_cflag |= CREAD;
2089 termios.c_lflag = ISIG | ICANON | IEXTEN | ECHO | ECHOE | ECHOK | ECHOCTL | ECHOPRT | ECHOKE;
2091 termios.c_cc[VINTR] = 03; /* ^C */
2092 termios.c_cc[VQUIT] = 034; /* ^\ */
2093 termios.c_cc[VERASE] = 0177;
2094 termios.c_cc[VKILL] = 025; /* ^X */
2095 termios.c_cc[VEOF] = 04; /* ^D */
2096 termios.c_cc[VSTART] = 021; /* ^Q */
2097 termios.c_cc[VSTOP] = 023; /* ^S */
2098 termios.c_cc[VSUSP] = 032; /* ^Z */
2099 termios.c_cc[VLNEXT] = 026; /* ^V */
2100 termios.c_cc[VWERASE] = 027; /* ^W */
2101 termios.c_cc[VREPRINT] = 022; /* ^R */
2102 termios.c_cc[VEOL] = 0;
2103 termios.c_cc[VEOL2] = 0;
2105 termios.c_cc[VTIME] = 0;
2106 termios.c_cc[VMIN] = 1;
2108 if (tcsetattr(fd, TCSANOW, &termios) < 0)
2112 /* Just in case, flush all crap out */
2113 tcflush(fd, TCIOFLUSH);
2118 int reset_terminal(const char *name) {
2121 fd = open_terminal(name, O_RDWR|O_NOCTTY|O_CLOEXEC);
2125 r = reset_terminal_fd(fd, true);
2126 close_nointr_nofail(fd);
2131 int open_terminal(const char *name, int mode) {
2136 * If a TTY is in the process of being closed opening it might
2137 * cause EIO. This is horribly awful, but unlikely to be
2138 * changed in the kernel. Hence we work around this problem by
2139 * retrying a couple of times.
2141 * https://bugs.launchpad.net/ubuntu/+source/linux/+bug/554172/comments/245
2145 fd = open(name, mode);
2152 /* Max 1s in total */
2156 usleep(50 * USEC_PER_MSEC);
2165 close_nointr_nofail(fd);
2170 close_nointr_nofail(fd);
2177 int flush_fd(int fd) {
2178 struct pollfd pollfd;
2182 pollfd.events = POLLIN;
2189 if ((r = poll(&pollfd, 1, 0)) < 0) {
2200 if ((l = read(fd, buf, sizeof(buf))) < 0) {
2205 if (errno == EAGAIN)
2216 int acquire_terminal(
2220 bool ignore_tiocstty_eperm,
2223 int fd = -1, notify = -1, r = 0, wd = -1;
2225 struct sigaction sa_old, sa_new;
2229 /* We use inotify to be notified when the tty is closed. We
2230 * create the watch before checking if we can actually acquire
2231 * it, so that we don't lose any event.
2233 * Note: strictly speaking this actually watches for the
2234 * device being closed, it does *not* really watch whether a
2235 * tty loses its controlling process. However, unless some
2236 * rogue process uses TIOCNOTTY on /dev/tty *after* closing
2237 * its tty otherwise this will not become a problem. As long
2238 * as the administrator makes sure not configure any service
2239 * on the same tty as an untrusted user this should not be a
2240 * problem. (Which he probably should not do anyway.) */
2242 if (timeout != (usec_t) -1)
2243 ts = now(CLOCK_MONOTONIC);
2245 if (!fail && !force) {
2246 notify = inotify_init1(IN_CLOEXEC | (timeout != (usec_t) -1 ? IN_NONBLOCK : 0));
2252 wd = inotify_add_watch(notify, name, IN_CLOSE);
2261 r = flush_fd(notify);
2266 /* We pass here O_NOCTTY only so that we can check the return
2267 * value TIOCSCTTY and have a reliable way to figure out if we
2268 * successfully became the controlling process of the tty */
2269 fd = open_terminal(name, O_RDWR|O_NOCTTY|O_CLOEXEC);
2273 /* Temporarily ignore SIGHUP, so that we don't get SIGHUP'ed
2274 * if we already own the tty. */
2276 sa_new.sa_handler = SIG_IGN;
2277 sa_new.sa_flags = SA_RESTART;
2278 assert_se(sigaction(SIGHUP, &sa_new, &sa_old) == 0);
2280 /* First, try to get the tty */
2281 if (ioctl(fd, TIOCSCTTY, force) < 0)
2284 assert_se(sigaction(SIGHUP, &sa_old, NULL) == 0);
2286 /* Sometimes it makes sense to ignore TIOCSCTTY
2287 * returning EPERM, i.e. when very likely we already
2288 * are have this controlling terminal. */
2289 if (r < 0 && r == -EPERM && ignore_tiocstty_eperm)
2292 if (r < 0 && (force || fail || r != -EPERM)) {
2301 assert(notify >= 0);
2304 uint8_t inotify_buffer[sizeof(struct inotify_event) + FILENAME_MAX];
2306 struct inotify_event *e;
2308 if (timeout != (usec_t) -1) {
2311 n = now(CLOCK_MONOTONIC);
2312 if (ts + timeout < n) {
2317 r = fd_wait_for_event(fd, POLLIN, ts + timeout - n);
2327 l = read(notify, inotify_buffer, sizeof(inotify_buffer));
2330 if (errno == EINTR || errno == EAGAIN)
2337 e = (struct inotify_event*) inotify_buffer;
2342 if (e->wd != wd || !(e->mask & IN_CLOSE)) {
2347 step = sizeof(struct inotify_event) + e->len;
2348 assert(step <= (size_t) l);
2350 e = (struct inotify_event*) ((uint8_t*) e + step);
2357 /* We close the tty fd here since if the old session
2358 * ended our handle will be dead. It's important that
2359 * we do this after sleeping, so that we don't enter
2360 * an endless loop. */
2361 close_nointr_nofail(fd);
2365 close_nointr_nofail(notify);
2367 r = reset_terminal_fd(fd, true);
2369 log_warning("Failed to reset terminal: %s", strerror(-r));
2375 close_nointr_nofail(fd);
2378 close_nointr_nofail(notify);
2383 int release_terminal(void) {
2385 struct sigaction sa_old, sa_new;
2387 if ((fd = open("/dev/tty", O_RDWR|O_NOCTTY|O_NDELAY|O_CLOEXEC)) < 0)
2390 /* Temporarily ignore SIGHUP, so that we don't get SIGHUP'ed
2391 * by our own TIOCNOTTY */
2394 sa_new.sa_handler = SIG_IGN;
2395 sa_new.sa_flags = SA_RESTART;
2396 assert_se(sigaction(SIGHUP, &sa_new, &sa_old) == 0);
2398 if (ioctl(fd, TIOCNOTTY) < 0)
2401 assert_se(sigaction(SIGHUP, &sa_old, NULL) == 0);
2403 close_nointr_nofail(fd);
2407 int sigaction_many(const struct sigaction *sa, ...) {
2412 while ((sig = va_arg(ap, int)) > 0)
2413 if (sigaction(sig, sa, NULL) < 0)
2420 int ignore_signals(int sig, ...) {
2421 struct sigaction sa;
2426 sa.sa_handler = SIG_IGN;
2427 sa.sa_flags = SA_RESTART;
2429 if (sigaction(sig, &sa, NULL) < 0)
2433 while ((sig = va_arg(ap, int)) > 0)
2434 if (sigaction(sig, &sa, NULL) < 0)
2441 int default_signals(int sig, ...) {
2442 struct sigaction sa;
2447 sa.sa_handler = SIG_DFL;
2448 sa.sa_flags = SA_RESTART;
2450 if (sigaction(sig, &sa, NULL) < 0)
2454 while ((sig = va_arg(ap, int)) > 0)
2455 if (sigaction(sig, &sa, NULL) < 0)
2462 int close_pipe(int p[]) {
2468 a = close_nointr(p[0]);
2473 b = close_nointr(p[1]);
2477 return a < 0 ? a : b;
2480 ssize_t loop_read(int fd, void *buf, size_t nbytes, bool do_poll) {
2489 while (nbytes > 0) {
2492 if ((k = read(fd, p, nbytes)) <= 0) {
2494 if (k < 0 && errno == EINTR)
2497 if (k < 0 && errno == EAGAIN && do_poll) {
2498 struct pollfd pollfd;
2502 pollfd.events = POLLIN;
2504 if (poll(&pollfd, 1, -1) < 0) {
2508 return n > 0 ? n : -errno;
2511 if (pollfd.revents != POLLIN)
2512 return n > 0 ? n : -EIO;
2517 return n > 0 ? n : (k < 0 ? -errno : 0);
2528 ssize_t loop_write(int fd, const void *buf, size_t nbytes, bool do_poll) {
2537 while (nbytes > 0) {
2540 k = write(fd, p, nbytes);
2543 if (k < 0 && errno == EINTR)
2546 if (k < 0 && errno == EAGAIN && do_poll) {
2547 struct pollfd pollfd;
2551 pollfd.events = POLLOUT;
2553 if (poll(&pollfd, 1, -1) < 0) {
2557 return n > 0 ? n : -errno;
2560 if (pollfd.revents != POLLOUT)
2561 return n > 0 ? n : -EIO;
2566 return n > 0 ? n : (k < 0 ? -errno : 0);
2577 int parse_bytes(const char *t, off_t *bytes) {
2578 static const struct {
2584 { "M", 1024ULL*1024ULL },
2585 { "G", 1024ULL*1024ULL*1024ULL },
2586 { "T", 1024ULL*1024ULL*1024ULL*1024ULL },
2587 { "P", 1024ULL*1024ULL*1024ULL*1024ULL*1024ULL },
2588 { "E", 1024ULL*1024ULL*1024ULL*1024ULL*1024ULL*1024ULL },
2605 l = strtoll(p, &e, 10);
2616 e += strspn(e, WHITESPACE);
2618 for (i = 0; i < ELEMENTSOF(table); i++)
2619 if (startswith(e, table[i].suffix)) {
2620 r += (off_t) l * table[i].factor;
2621 p = e + strlen(table[i].suffix);
2625 if (i >= ELEMENTSOF(table))
2635 int make_stdio(int fd) {
2640 r = dup3(fd, STDIN_FILENO, 0);
2641 s = dup3(fd, STDOUT_FILENO, 0);
2642 t = dup3(fd, STDERR_FILENO, 0);
2645 close_nointr_nofail(fd);
2647 if (r < 0 || s < 0 || t < 0)
2650 /* We rely here that the new fd has O_CLOEXEC not set */
2655 int make_null_stdio(void) {
2658 null_fd = open("/dev/null", O_RDWR|O_NOCTTY);
2662 return make_stdio(null_fd);
2665 bool is_device_path(const char *path) {
2667 /* Returns true on paths that refer to a device, either in
2668 * sysfs or in /dev */
2671 path_startswith(path, "/dev/") ||
2672 path_startswith(path, "/sys/");
2675 int dir_is_empty(const char *path) {
2676 _cleanup_closedir_ DIR *d;
2685 union dirent_storage buf;
2687 r = readdir_r(d, &buf.de, &de);
2694 if (!ignore_file(de->d_name))
2699 unsigned long long random_ull(void) {
2700 _cleanup_close_ int fd;
2704 fd = open("/dev/urandom", O_RDONLY|O_CLOEXEC|O_NOCTTY);
2708 r = loop_read(fd, &ull, sizeof(ull), true);
2709 if (r != sizeof(ull))
2715 return random() * RAND_MAX + random();
2718 void rename_process(const char name[8]) {
2721 /* This is a like a poor man's setproctitle(). It changes the
2722 * comm field, argv[0], and also the glibc's internally used
2723 * name of the process. For the first one a limit of 16 chars
2724 * applies, to the second one usually one of 10 (i.e. length
2725 * of "/sbin/init"), to the third one one of 7 (i.e. length of
2726 * "systemd"). If you pass a longer string it will be
2729 prctl(PR_SET_NAME, name);
2731 if (program_invocation_name)
2732 strncpy(program_invocation_name, name, strlen(program_invocation_name));
2734 if (saved_argc > 0) {
2738 strncpy(saved_argv[0], name, strlen(saved_argv[0]));
2740 for (i = 1; i < saved_argc; i++) {
2744 memset(saved_argv[i], 0, strlen(saved_argv[i]));
2749 void sigset_add_many(sigset_t *ss, ...) {
2756 while ((sig = va_arg(ap, int)) > 0)
2757 assert_se(sigaddset(ss, sig) == 0);
2761 char* gethostname_malloc(void) {
2764 assert_se(uname(&u) >= 0);
2766 if (!isempty(u.nodename) && !streq(u.nodename, "(none)"))
2767 return strdup(u.nodename);
2769 return strdup(u.sysname);
2772 bool hostname_is_set(void) {
2775 assert_se(uname(&u) >= 0);
2777 return !isempty(u.nodename) && !streq(u.nodename, "(none)");
2780 static char *lookup_uid(uid_t uid) {
2783 _cleanup_free_ char *buf = NULL;
2784 struct passwd pwbuf, *pw = NULL;
2786 /* Shortcut things to avoid NSS lookups */
2788 return strdup("root");
2790 bufsize = sysconf(_SC_GETPW_R_SIZE_MAX);
2794 buf = malloc(bufsize);
2798 if (getpwuid_r(uid, &pwbuf, buf, bufsize, &pw) == 0 && pw)
2799 return strdup(pw->pw_name);
2801 if (asprintf(&name, "%lu", (unsigned long) uid) < 0)
2807 char* getlogname_malloc(void) {
2811 if (isatty(STDIN_FILENO) && fstat(STDIN_FILENO, &st) >= 0)
2816 return lookup_uid(uid);
2819 char *getusername_malloc(void) {
2826 return lookup_uid(getuid());
2829 int getttyname_malloc(int fd, char **r) {
2830 char path[PATH_MAX], *c;
2835 k = ttyname_r(fd, path, sizeof(path));
2841 c = strdup(startswith(path, "/dev/") ? path + 5 : path);
2849 int getttyname_harder(int fd, char **r) {
2853 k = getttyname_malloc(fd, &s);
2857 if (streq(s, "tty")) {
2859 return get_ctty(0, NULL, r);
2866 int get_ctty_devnr(pid_t pid, dev_t *d) {
2868 char line[LINE_MAX], *p, *fn;
2869 unsigned long ttynr;
2872 if (asprintf(&fn, "/proc/%lu/stat", (unsigned long) (pid <= 0 ? getpid() : pid)) < 0)
2875 f = fopen(fn, "re");
2880 if (!fgets(line, sizeof(line), f)) {
2881 k = feof(f) ? -EIO : -errno;
2888 p = strrchr(line, ')');
2898 "%*d " /* session */
2903 if (major(ttynr) == 0 && minor(ttynr) == 0)
2910 int get_ctty(pid_t pid, dev_t *_devnr, char **r) {
2912 char fn[PATH_MAX], *s, *b, *p;
2917 k = get_ctty_devnr(pid, &devnr);
2921 snprintf(fn, sizeof(fn), "/dev/char/%u:%u", major(devnr), minor(devnr));
2924 k = readlink_malloc(fn, &s);
2930 /* This is an ugly hack */
2931 if (major(devnr) == 136) {
2932 if (asprintf(&b, "pts/%lu", (unsigned long) minor(devnr)) < 0)
2942 /* Probably something like the ptys which have no
2943 * symlink in /dev/char. Let's return something
2944 * vaguely useful. */
2957 if (startswith(s, "/dev/"))
2959 else if (startswith(s, "../"))
2977 int rm_rf_children_dangerous(int fd, bool only_dirs, bool honour_sticky, struct stat *root_dev) {
2983 /* This returns the first error we run into, but nevertheless
2984 * tries to go on. This closes the passed fd. */
2988 close_nointr_nofail(fd);
2990 return errno == ENOENT ? 0 : -errno;
2995 union dirent_storage buf;
2996 bool is_dir, keep_around;
3000 r = readdir_r(d, &buf.de, &de);
3001 if (r != 0 && ret == 0) {
3009 if (streq(de->d_name, ".") || streq(de->d_name, ".."))
3012 if (de->d_type == DT_UNKNOWN ||
3014 (de->d_type == DT_DIR && root_dev)) {
3015 if (fstatat(fd, de->d_name, &st, AT_SYMLINK_NOFOLLOW) < 0) {
3016 if (ret == 0 && errno != ENOENT)
3021 is_dir = S_ISDIR(st.st_mode);
3024 (st.st_uid == 0 || st.st_uid == getuid()) &&
3025 (st.st_mode & S_ISVTX);
3027 is_dir = de->d_type == DT_DIR;
3028 keep_around = false;
3034 /* if root_dev is set, remove subdirectories only, if device is same as dir */
3035 if (root_dev && st.st_dev != root_dev->st_dev)
3038 subdir_fd = openat(fd, de->d_name,
3039 O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC|O_NOFOLLOW|O_NOATIME);
3040 if (subdir_fd < 0) {
3041 if (ret == 0 && errno != ENOENT)
3046 r = rm_rf_children_dangerous(subdir_fd, only_dirs, honour_sticky, root_dev);
3047 if (r < 0 && ret == 0)
3051 if (unlinkat(fd, de->d_name, AT_REMOVEDIR) < 0) {
3052 if (ret == 0 && errno != ENOENT)
3056 } else if (!only_dirs && !keep_around) {
3058 if (unlinkat(fd, de->d_name, 0) < 0) {
3059 if (ret == 0 && errno != ENOENT)
3070 static int is_temporary_fs(struct statfs *s) {
3072 return s->f_type == TMPFS_MAGIC ||
3073 (long)s->f_type == (long)RAMFS_MAGIC;
3076 int rm_rf_children(int fd, bool only_dirs, bool honour_sticky, struct stat *root_dev) {
3081 if (fstatfs(fd, &s) < 0) {
3082 close_nointr_nofail(fd);
3086 /* We refuse to clean disk file systems with this call. This
3087 * is extra paranoia just to be sure we never ever remove
3089 if (!is_temporary_fs(&s)) {
3090 log_error("Attempted to remove disk file system, and we can't allow that.");
3091 close_nointr_nofail(fd);
3095 return rm_rf_children_dangerous(fd, only_dirs, honour_sticky, root_dev);
3098 static int rm_rf_internal(const char *path, bool only_dirs, bool delete_root, bool honour_sticky, bool dangerous) {
3104 /* We refuse to clean the root file system with this
3105 * call. This is extra paranoia to never cause a really
3106 * seriously broken system. */
3107 if (path_equal(path, "/")) {
3108 log_error("Attempted to remove entire root file system, and we can't allow that.");
3112 fd = open(path, O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC|O_NOFOLLOW|O_NOATIME);
3115 if (errno != ENOTDIR)
3119 if (statfs(path, &s) < 0)
3122 if (!is_temporary_fs(&s)) {
3123 log_error("Attempted to remove disk file system, and we can't allow that.");
3128 if (delete_root && !only_dirs)
3129 if (unlink(path) < 0 && errno != ENOENT)
3136 if (fstatfs(fd, &s) < 0) {
3137 close_nointr_nofail(fd);
3141 if (!is_temporary_fs(&s)) {
3142 log_error("Attempted to remove disk file system, and we can't allow that.");
3143 close_nointr_nofail(fd);
3148 r = rm_rf_children_dangerous(fd, only_dirs, honour_sticky, NULL);
3151 if (honour_sticky && file_is_priv_sticky(path) > 0)
3154 if (rmdir(path) < 0 && errno != ENOENT) {
3163 int rm_rf(const char *path, bool only_dirs, bool delete_root, bool honour_sticky) {
3164 return rm_rf_internal(path, only_dirs, delete_root, honour_sticky, false);
3167 int rm_rf_dangerous(const char *path, bool only_dirs, bool delete_root, bool honour_sticky) {
3168 return rm_rf_internal(path, only_dirs, delete_root, honour_sticky, true);
3171 int chmod_and_chown(const char *path, mode_t mode, uid_t uid, gid_t gid) {
3174 /* Under the assumption that we are running privileged we
3175 * first change the access mode and only then hand out
3176 * ownership to avoid a window where access is too open. */
3178 if (mode != (mode_t) -1)
3179 if (chmod(path, mode) < 0)
3182 if (uid != (uid_t) -1 || gid != (gid_t) -1)
3183 if (chown(path, uid, gid) < 0)
3189 int fchmod_and_fchown(int fd, mode_t mode, uid_t uid, gid_t gid) {
3192 /* Under the assumption that we are running privileged we
3193 * first change the access mode and only then hand out
3194 * ownership to avoid a window where access is too open. */
3196 if (fchmod(fd, mode) < 0)
3199 if (fchown(fd, uid, gid) < 0)
3205 cpu_set_t* cpu_set_malloc(unsigned *ncpus) {
3209 /* Allocates the cpuset in the right size */
3212 if (!(r = CPU_ALLOC(n)))
3215 if (sched_getaffinity(0, CPU_ALLOC_SIZE(n), r) >= 0) {
3216 CPU_ZERO_S(CPU_ALLOC_SIZE(n), r);
3226 if (errno != EINVAL)
3233 int status_vprintf(const char *status, bool ellipse, const char *format, va_list ap) {
3234 static const char status_indent[] = " "; /* "[" STATUS "] " */
3235 _cleanup_free_ char *s = NULL;
3236 _cleanup_close_ int fd = -1;
3237 struct iovec iovec[5];
3242 /* This is independent of logging, as status messages are
3243 * optional and go exclusively to the console. */
3245 if (vasprintf(&s, format, ap) < 0)
3248 fd = open_terminal("/dev/console", O_WRONLY|O_NOCTTY|O_CLOEXEC);
3261 sl = status ? sizeof(status_indent)-1 : 0;
3267 e = ellipsize(s, emax, 75);
3277 if (!isempty(status)) {
3278 IOVEC_SET_STRING(iovec[n++], "[");
3279 IOVEC_SET_STRING(iovec[n++], status);
3280 IOVEC_SET_STRING(iovec[n++], "] ");
3282 IOVEC_SET_STRING(iovec[n++], status_indent);
3285 IOVEC_SET_STRING(iovec[n++], s);
3286 IOVEC_SET_STRING(iovec[n++], "\n");
3288 if (writev(fd, iovec, n) < 0)
3294 int status_printf(const char *status, bool ellipse, const char *format, ...) {
3300 va_start(ap, format);
3301 r = status_vprintf(status, ellipse, format, ap);
3307 int status_welcome(void) {
3309 _cleanup_free_ char *pretty_name = NULL, *ansi_color = NULL;
3311 r = parse_env_file("/etc/os-release", NEWLINE,
3312 "PRETTY_NAME", &pretty_name,
3313 "ANSI_COLOR", &ansi_color,
3315 if (r < 0 && r != -ENOENT)
3316 log_warning("Failed to read /etc/os-release: %s", strerror(-r));
3318 return status_printf(NULL, false,
3319 "\nWelcome to \x1B[%sm%s\x1B[0m!\n",
3320 isempty(ansi_color) ? "1" : ansi_color,
3321 isempty(pretty_name) ? "Linux" : pretty_name);
3324 char *replace_env(const char *format, char **env) {
3331 const char *e, *word = format;
3336 for (e = format; *e; e ++) {
3347 if (!(k = strnappend(r, word, e-word-1)))
3356 } else if (*e == '$') {
3357 if (!(k = strnappend(r, word, e-word)))
3373 if (!(t = strv_env_get_with_length(env, word+2, e-word-2)))
3376 if (!(k = strappend(r, t)))
3389 if (!(k = strnappend(r, word, e-word)))
3400 char **replace_env_argv(char **argv, char **env) {
3402 unsigned k = 0, l = 0;
3404 l = strv_length(argv);
3406 if (!(r = new(char*, l+1)))
3409 STRV_FOREACH(i, argv) {
3411 /* If $FOO appears as single word, replace it by the split up variable */
3412 if ((*i)[0] == '$' && (*i)[1] != '{') {
3417 if ((e = strv_env_get(env, *i+1))) {
3419 if (!(m = strv_split_quoted(e))) {
3430 if (!(w = realloc(r, sizeof(char*) * (l+1)))) {
3439 memcpy(r + k, m, q * sizeof(char*));
3447 /* If ${FOO} appears as part of a word, replace it by the variable as-is */
3448 if (!(r[k++] = replace_env(*i, env))) {
3458 int fd_columns(int fd) {
3462 if (ioctl(fd, TIOCGWINSZ, &ws) < 0)
3471 unsigned columns(void) {
3475 if (_likely_(cached_columns > 0))
3476 return cached_columns;
3479 e = getenv("COLUMNS");
3484 c = fd_columns(STDOUT_FILENO);
3493 int fd_lines(int fd) {
3497 if (ioctl(fd, TIOCGWINSZ, &ws) < 0)
3506 unsigned lines(void) {
3510 if (_likely_(cached_lines > 0))
3511 return cached_lines;
3514 e = getenv("LINES");
3519 l = fd_lines(STDOUT_FILENO);
3525 return cached_lines;
3528 /* intended to be used as a SIGWINCH sighandler */
3529 void columns_lines_cache_reset(int signum) {
3535 static int cached_on_tty = -1;
3537 if (_unlikely_(cached_on_tty < 0))
3538 cached_on_tty = isatty(STDOUT_FILENO) > 0;
3540 return cached_on_tty;
3543 int running_in_chroot(void) {
3549 /* Only works as root */
3551 if (stat("/proc/1/root", &a) < 0)
3554 if (stat("/", &b) < 0)
3558 a.st_dev != b.st_dev ||
3559 a.st_ino != b.st_ino;
3562 char *ellipsize_mem(const char *s, size_t old_length, size_t new_length, unsigned percent) {
3567 assert(percent <= 100);
3568 assert(new_length >= 3);
3570 if (old_length <= 3 || old_length <= new_length)
3571 return strndup(s, old_length);
3573 r = new0(char, new_length+1);
3577 x = (new_length * percent) / 100;
3579 if (x > new_length - 3)
3587 s + old_length - (new_length - x - 3),
3588 new_length - x - 3);
3593 char *ellipsize(const char *s, size_t length, unsigned percent) {
3594 return ellipsize_mem(s, strlen(s), length, percent);
3597 int touch(const char *path) {
3602 /* This just opens the file for writing, ensuring it
3603 * exists. It doesn't call utimensat() the way /usr/bin/touch
3606 fd = open(path, O_WRONLY|O_CREAT|O_CLOEXEC|O_NOCTTY, 0644);
3610 close_nointr_nofail(fd);
3614 char *unquote(const char *s, const char* quotes) {
3618 /* This is rather stupid, simply removes the heading and
3619 * trailing quotes if there is one. Doesn't care about
3620 * escaping or anything. We should make this smarter one
3627 if (strchr(quotes, s[0]) && s[l-1] == s[0])
3628 return strndup(s+1, l-2);
3633 char *normalize_env_assignment(const char *s) {
3634 _cleanup_free_ char *name = NULL, *value = NULL, *p = NULL;
3637 eq = strchr(s, '=');
3649 memmove(r, t, strlen(t) + 1);
3653 name = strndup(s, eq - s);
3661 value = unquote(strstrip(p), QUOTES);
3665 if (asprintf(&r, "%s=%s", strstrip(name), value) < 0)
3671 int wait_for_terminate(pid_t pid, siginfo_t *status) {
3682 if (waitid(P_PID, pid, status, WEXITED) < 0) {
3694 int wait_for_terminate_and_warn(const char *name, pid_t pid) {
3701 r = wait_for_terminate(pid, &status);
3703 log_warning("Failed to wait for %s: %s", name, strerror(-r));
3707 if (status.si_code == CLD_EXITED) {
3708 if (status.si_status != 0) {
3709 log_warning("%s failed with error code %i.", name, status.si_status);
3710 return status.si_status;
3713 log_debug("%s succeeded.", name);
3716 } else if (status.si_code == CLD_KILLED ||
3717 status.si_code == CLD_DUMPED) {
3719 log_warning("%s terminated by signal %s.", name, signal_to_string(status.si_status));
3723 log_warning("%s failed due to unknown reason.", name);
3727 _noreturn_ void freeze(void) {
3729 /* Make sure nobody waits for us on a socket anymore */
3730 close_all_fds(NULL, 0);
3738 bool null_or_empty(struct stat *st) {
3741 if (S_ISREG(st->st_mode) && st->st_size <= 0)
3744 if (S_ISCHR(st->st_mode) || S_ISBLK(st->st_mode))
3750 int null_or_empty_path(const char *fn) {
3755 if (stat(fn, &st) < 0)
3758 return null_or_empty(&st);
3761 DIR *xopendirat(int fd, const char *name, int flags) {
3765 nfd = openat(fd, name, O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC|flags);
3771 close_nointr_nofail(nfd);
3778 int signal_from_string_try_harder(const char *s) {
3782 signo = signal_from_string(s);
3784 if (startswith(s, "SIG"))
3785 return signal_from_string(s+3);
3790 static char *tag_to_udev_node(const char *tagvalue, const char *by) {
3794 /* FIXME: to follow udev's logic 100% we need to leave valid
3795 * UTF8 chars unescaped */
3797 u = unquote(tagvalue, "\"\'");
3801 t = xescape(u, "/ ");
3807 r = asprintf(&dn, "/dev/disk/by-%s/%s", by, t);
3816 char *fstab_node_to_udev_node(const char *p) {
3819 if (startswith(p, "LABEL="))
3820 return tag_to_udev_node(p+6, "label");
3822 if (startswith(p, "UUID="))
3823 return tag_to_udev_node(p+5, "uuid");
3825 if (startswith(p, "PARTUUID="))
3826 return tag_to_udev_node(p+9, "partuuid");
3828 if (startswith(p, "PARTLABEL="))
3829 return tag_to_udev_node(p+10, "partlabel");
3834 bool tty_is_vc(const char *tty) {
3837 if (startswith(tty, "/dev/"))
3840 return vtnr_from_tty(tty) >= 0;
3843 bool tty_is_console(const char *tty) {
3846 if (startswith(tty, "/dev/"))
3849 return streq(tty, "console");
3852 int vtnr_from_tty(const char *tty) {
3857 if (startswith(tty, "/dev/"))
3860 if (!startswith(tty, "tty") )
3863 if (tty[3] < '0' || tty[3] > '9')
3866 r = safe_atoi(tty+3, &i);
3870 if (i < 0 || i > 63)
3876 bool tty_is_vc_resolve(const char *tty) {
3877 char *active = NULL;
3882 if (startswith(tty, "/dev/"))
3885 /* Resolve where /dev/console is pointing to, if /sys is
3886 * actually ours (i.e. not read-only-mounted which is a sign
3887 * for container setups) */
3888 if (streq(tty, "console") && path_is_read_only_fs("/sys") <= 0)
3889 if (read_one_line_file("/sys/class/tty/console/active", &active) >= 0) {
3890 /* If multiple log outputs are configured the
3891 * last one is what /dev/console points to */
3892 tty = strrchr(active, ' ');
3905 const char *default_term_for_tty(const char *tty) {
3908 return tty_is_vc_resolve(tty) ? "TERM=linux" : "TERM=vt102";
3911 bool dirent_is_file(const struct dirent *de) {
3914 if (ignore_file(de->d_name))
3917 if (de->d_type != DT_REG &&
3918 de->d_type != DT_LNK &&
3919 de->d_type != DT_UNKNOWN)
3925 bool dirent_is_file_with_suffix(const struct dirent *de, const char *suffix) {
3928 if (de->d_type != DT_REG &&
3929 de->d_type != DT_LNK &&
3930 de->d_type != DT_UNKNOWN)
3933 if (ignore_file_allow_backup(de->d_name))
3936 return endswith(de->d_name, suffix);
3939 void execute_directory(const char *directory, DIR *d, char *argv[]) {
3942 Hashmap *pids = NULL;
3946 /* Executes all binaries in a directory in parallel and waits
3947 * until all they all finished. */
3950 if (!(_d = opendir(directory))) {
3952 if (errno == ENOENT)
3955 log_error("Failed to enumerate directory %s: %m", directory);
3962 if (!(pids = hashmap_new(trivial_hash_func, trivial_compare_func))) {
3963 log_error("Failed to allocate set.");
3967 while ((de = readdir(d))) {
3972 if (!dirent_is_file(de))
3975 if (asprintf(&path, "%s/%s", directory, de->d_name) < 0) {
3980 if ((pid = fork()) < 0) {
3981 log_error("Failed to fork: %m");
3999 log_error("Failed to execute %s: %m", path);
4000 _exit(EXIT_FAILURE);
4003 log_debug("Spawned %s as %lu", path, (unsigned long) pid);
4005 if ((k = hashmap_put(pids, UINT_TO_PTR(pid), path)) < 0) {
4006 log_error("Failed to add PID to set: %s", strerror(-k));
4011 while (!hashmap_isempty(pids)) {
4012 pid_t pid = PTR_TO_UINT(hashmap_first_key(pids));
4017 if (waitid(P_PID, pid, &si, WEXITED) < 0) {
4022 log_error("waitid() failed: %m");
4026 if ((path = hashmap_remove(pids, UINT_TO_PTR(si.si_pid)))) {
4027 if (!is_clean_exit(si.si_code, si.si_status, NULL)) {
4028 if (si.si_code == CLD_EXITED)
4029 log_error("%s exited with exit status %i.", path, si.si_status);
4031 log_error("%s terminated by signal %s.", path, signal_to_string(si.si_status));
4033 log_debug("%s exited successfully.", path);
4044 hashmap_free_free(pids);
4047 int kill_and_sigcont(pid_t pid, int sig) {
4050 r = kill(pid, sig) < 0 ? -errno : 0;
4058 bool nulstr_contains(const char*nulstr, const char *needle) {
4064 NULSTR_FOREACH(i, nulstr)
4065 if (streq(i, needle))
4071 bool plymouth_running(void) {
4072 return access("/run/plymouth/pid", F_OK) >= 0;
4075 char* strshorten(char *s, size_t l) {
4084 static bool hostname_valid_char(char c) {
4086 (c >= 'a' && c <= 'z') ||
4087 (c >= 'A' && c <= 'Z') ||
4088 (c >= '0' && c <= '9') ||
4094 bool hostname_is_valid(const char *s) {
4100 for (p = s; *p; p++)
4101 if (!hostname_valid_char(*p))
4104 if (p-s > HOST_NAME_MAX)
4110 char* hostname_cleanup(char *s) {
4113 for (p = s, d = s; *p; p++)
4114 if ((*p >= 'a' && *p <= 'z') ||
4115 (*p >= 'A' && *p <= 'Z') ||
4116 (*p >= '0' && *p <= '9') ||
4124 strshorten(s, HOST_NAME_MAX);
4128 int pipe_eof(int fd) {
4129 struct pollfd pollfd;
4134 pollfd.events = POLLIN|POLLHUP;
4136 r = poll(&pollfd, 1, 0);
4143 return pollfd.revents & POLLHUP;
4146 int fd_wait_for_event(int fd, int event, usec_t t) {
4147 struct pollfd pollfd;
4152 pollfd.events = event;
4154 r = poll(&pollfd, 1, t == (usec_t) -1 ? -1 : (int) (t / USEC_PER_MSEC));
4161 return pollfd.revents;
4164 int fopen_temporary(const char *path, FILE **_f, char **_temp_path) {
4175 t = new(char, strlen(path) + 1 + 6 + 1);
4179 fn = path_get_file_name(path);
4183 stpcpy(stpcpy(t+k+1, fn), "XXXXXX");
4185 fd = mkostemp(t, O_WRONLY|O_CLOEXEC);
4191 f = fdopen(fd, "we");
4204 int terminal_vhangup_fd(int fd) {
4207 if (ioctl(fd, TIOCVHANGUP) < 0)
4213 int terminal_vhangup(const char *name) {
4216 fd = open_terminal(name, O_RDWR|O_NOCTTY|O_CLOEXEC);
4220 r = terminal_vhangup_fd(fd);
4221 close_nointr_nofail(fd);
4226 int vt_disallocate(const char *name) {
4230 /* Deallocate the VT if possible. If not possible
4231 * (i.e. because it is the active one), at least clear it
4232 * entirely (including the scrollback buffer) */
4234 if (!startswith(name, "/dev/"))
4237 if (!tty_is_vc(name)) {
4238 /* So this is not a VT. I guess we cannot deallocate
4239 * it then. But let's at least clear the screen */
4241 fd = open_terminal(name, O_RDWR|O_NOCTTY|O_CLOEXEC);
4246 "\033[r" /* clear scrolling region */
4247 "\033[H" /* move home */
4248 "\033[2J", /* clear screen */
4250 close_nointr_nofail(fd);
4255 if (!startswith(name, "/dev/tty"))
4258 r = safe_atou(name+8, &u);
4265 /* Try to deallocate */
4266 fd = open_terminal("/dev/tty0", O_RDWR|O_NOCTTY|O_CLOEXEC);
4270 r = ioctl(fd, VT_DISALLOCATE, u);
4271 close_nointr_nofail(fd);
4279 /* Couldn't deallocate, so let's clear it fully with
4281 fd = open_terminal(name, O_RDWR|O_NOCTTY|O_CLOEXEC);
4286 "\033[r" /* clear scrolling region */
4287 "\033[H" /* move home */
4288 "\033[3J", /* clear screen including scrollback, requires Linux 2.6.40 */
4290 close_nointr_nofail(fd);
4295 int copy_file(const char *from, const char *to) {
4301 fdf = open(from, O_RDONLY|O_CLOEXEC|O_NOCTTY);
4305 fdt = open(to, O_WRONLY|O_CREAT|O_EXCL|O_CLOEXEC|O_NOCTTY, 0644);
4307 close_nointr_nofail(fdf);
4315 n = read(fdf, buf, sizeof(buf));
4319 close_nointr_nofail(fdf);
4330 k = loop_write(fdt, buf, n, false);
4332 r = k < 0 ? k : (errno ? -errno : -EIO);
4334 close_nointr_nofail(fdf);
4342 close_nointr_nofail(fdf);
4343 r = close_nointr(fdt);
4353 int symlink_atomic(const char *from, const char *to) {
4355 _cleanup_free_ char *t;
4358 unsigned long long ull;
4365 t = new(char, strlen(to) + 1 + 16 + 1);
4369 fn = path_get_file_name(to);
4373 x = stpcpy(t+k+1, fn);
4376 for (i = 0; i < 16; i++) {
4377 *(x++) = hexchar(ull & 0xF);
4383 if (symlink(from, t) < 0)
4386 if (rename(t, to) < 0) {
4395 bool display_is_local(const char *display) {
4399 display[0] == ':' &&
4400 display[1] >= '0' &&
4404 int socket_from_display(const char *display, char **path) {
4411 if (!display_is_local(display))
4414 k = strspn(display+1, "0123456789");
4416 f = new(char, sizeof("/tmp/.X11-unix/X") + k);
4420 c = stpcpy(f, "/tmp/.X11-unix/X");
4421 memcpy(c, display+1, k);
4430 const char **username,
4431 uid_t *uid, gid_t *gid,
4433 const char **shell) {
4441 /* We enforce some special rules for uid=0: in order to avoid
4442 * NSS lookups for root we hardcode its data. */
4444 if (streq(*username, "root") || streq(*username, "0")) {
4462 if (parse_uid(*username, &u) >= 0) {
4466 /* If there are multiple users with the same id, make
4467 * sure to leave $USER to the configured value instead
4468 * of the first occurrence in the database. However if
4469 * the uid was configured by a numeric uid, then let's
4470 * pick the real username from /etc/passwd. */
4472 *username = p->pw_name;
4475 p = getpwnam(*username);
4479 return errno != 0 ? -errno : -ESRCH;
4491 *shell = p->pw_shell;
4496 char* uid_to_name(uid_t uid) {
4501 return strdup("root");
4505 return strdup(p->pw_name);
4507 if (asprintf(&r, "%lu", (unsigned long) uid) < 0)
4513 int get_group_creds(const char **groupname, gid_t *gid) {
4519 /* We enforce some special rules for gid=0: in order to avoid
4520 * NSS lookups for root we hardcode its data. */
4522 if (streq(*groupname, "root") || streq(*groupname, "0")) {
4523 *groupname = "root";
4531 if (parse_gid(*groupname, &id) >= 0) {
4536 *groupname = g->gr_name;
4539 g = getgrnam(*groupname);
4543 return errno != 0 ? -errno : -ESRCH;
4551 int in_group(const char *name) {
4553 int ngroups_max, r, i;
4555 r = get_group_creds(&name, &gid);
4559 if (getgid() == gid)
4562 if (getegid() == gid)
4565 ngroups_max = sysconf(_SC_NGROUPS_MAX);
4566 assert(ngroups_max > 0);
4568 gids = alloca(sizeof(gid_t) * ngroups_max);
4570 r = getgroups(ngroups_max, gids);
4574 for (i = 0; i < r; i++)
4581 int glob_exists(const char *path) {
4589 k = glob(path, GLOB_NOSORT|GLOB_BRACE, NULL, &g);
4591 if (k == GLOB_NOMATCH)
4593 else if (k == GLOB_NOSPACE)
4596 r = !strv_isempty(g.gl_pathv);
4598 r = errno ? -errno : -EIO;
4605 int dirent_ensure_type(DIR *d, struct dirent *de) {
4611 if (de->d_type != DT_UNKNOWN)
4614 if (fstatat(dirfd(d), de->d_name, &st, AT_SYMLINK_NOFOLLOW) < 0)
4618 S_ISREG(st.st_mode) ? DT_REG :
4619 S_ISDIR(st.st_mode) ? DT_DIR :
4620 S_ISLNK(st.st_mode) ? DT_LNK :
4621 S_ISFIFO(st.st_mode) ? DT_FIFO :
4622 S_ISSOCK(st.st_mode) ? DT_SOCK :
4623 S_ISCHR(st.st_mode) ? DT_CHR :
4624 S_ISBLK(st.st_mode) ? DT_BLK :
4630 int in_search_path(const char *path, char **search) {
4634 r = path_get_parent(path, &parent);
4640 STRV_FOREACH(i, search) {
4641 if (path_equal(parent, *i)) {
4652 int get_files_in_directory(const char *path, char ***list) {
4660 /* Returns all files in a directory in *list, and the number
4661 * of files as return value. If list is NULL returns only the
4670 union dirent_storage buf;
4673 k = readdir_r(d, &buf.de, &de);
4682 dirent_ensure_type(d, de);
4684 if (!dirent_is_file(de))
4688 if ((unsigned) r >= n) {
4692 t = realloc(l, sizeof(char*) * n);
4701 assert((unsigned) r < n);
4703 l[r] = strdup(de->d_name);
4727 char *strjoin(const char *x, ...) {
4741 t = va_arg(ap, const char *);
4746 if (n > ((size_t) -1) - l) {
4770 t = va_arg(ap, const char *);
4784 bool is_main_thread(void) {
4785 static __thread int cached = 0;
4787 if (_unlikely_(cached == 0))
4788 cached = getpid() == gettid() ? 1 : -1;
4793 int block_get_whole_disk(dev_t d, dev_t *ret) {
4800 /* If it has a queue this is good enough for us */
4801 if (asprintf(&p, "/sys/dev/block/%u:%u/queue", major(d), minor(d)) < 0)
4804 r = access(p, F_OK);
4812 /* If it is a partition find the originating device */
4813 if (asprintf(&p, "/sys/dev/block/%u:%u/partition", major(d), minor(d)) < 0)
4816 r = access(p, F_OK);
4822 /* Get parent dev_t */
4823 if (asprintf(&p, "/sys/dev/block/%u:%u/../dev", major(d), minor(d)) < 0)
4826 r = read_one_line_file(p, &s);
4832 r = sscanf(s, "%u:%u", &m, &n);
4838 /* Only return this if it is really good enough for us. */
4839 if (asprintf(&p, "/sys/dev/block/%u:%u/queue", m, n) < 0)
4842 r = access(p, F_OK);
4846 *ret = makedev(m, n);
4853 int file_is_priv_sticky(const char *p) {
4858 if (lstat(p, &st) < 0)
4862 (st.st_uid == 0 || st.st_uid == getuid()) &&
4863 (st.st_mode & S_ISVTX);
4866 static const char *const ioprio_class_table[] = {
4867 [IOPRIO_CLASS_NONE] = "none",
4868 [IOPRIO_CLASS_RT] = "realtime",
4869 [IOPRIO_CLASS_BE] = "best-effort",
4870 [IOPRIO_CLASS_IDLE] = "idle"
4873 DEFINE_STRING_TABLE_LOOKUP_WITH_FALLBACK(ioprio_class, int, INT_MAX);
4875 static const char *const sigchld_code_table[] = {
4876 [CLD_EXITED] = "exited",
4877 [CLD_KILLED] = "killed",
4878 [CLD_DUMPED] = "dumped",
4879 [CLD_TRAPPED] = "trapped",
4880 [CLD_STOPPED] = "stopped",
4881 [CLD_CONTINUED] = "continued",
4884 DEFINE_STRING_TABLE_LOOKUP(sigchld_code, int);
4886 static const char *const log_facility_unshifted_table[LOG_NFACILITIES] = {
4887 [LOG_FAC(LOG_KERN)] = "kern",
4888 [LOG_FAC(LOG_USER)] = "user",
4889 [LOG_FAC(LOG_MAIL)] = "mail",
4890 [LOG_FAC(LOG_DAEMON)] = "daemon",
4891 [LOG_FAC(LOG_AUTH)] = "auth",
4892 [LOG_FAC(LOG_SYSLOG)] = "syslog",
4893 [LOG_FAC(LOG_LPR)] = "lpr",
4894 [LOG_FAC(LOG_NEWS)] = "news",
4895 [LOG_FAC(LOG_UUCP)] = "uucp",
4896 [LOG_FAC(LOG_CRON)] = "cron",
4897 [LOG_FAC(LOG_AUTHPRIV)] = "authpriv",
4898 [LOG_FAC(LOG_FTP)] = "ftp",
4899 [LOG_FAC(LOG_LOCAL0)] = "local0",
4900 [LOG_FAC(LOG_LOCAL1)] = "local1",
4901 [LOG_FAC(LOG_LOCAL2)] = "local2",
4902 [LOG_FAC(LOG_LOCAL3)] = "local3",
4903 [LOG_FAC(LOG_LOCAL4)] = "local4",
4904 [LOG_FAC(LOG_LOCAL5)] = "local5",
4905 [LOG_FAC(LOG_LOCAL6)] = "local6",
4906 [LOG_FAC(LOG_LOCAL7)] = "local7"
4909 DEFINE_STRING_TABLE_LOOKUP_WITH_FALLBACK(log_facility_unshifted, int, LOG_FAC(~0));
4911 static const char *const log_level_table[] = {
4912 [LOG_EMERG] = "emerg",
4913 [LOG_ALERT] = "alert",
4914 [LOG_CRIT] = "crit",
4916 [LOG_WARNING] = "warning",
4917 [LOG_NOTICE] = "notice",
4918 [LOG_INFO] = "info",
4919 [LOG_DEBUG] = "debug"
4922 DEFINE_STRING_TABLE_LOOKUP_WITH_FALLBACK(log_level, int, LOG_DEBUG);
4924 static const char* const sched_policy_table[] = {
4925 [SCHED_OTHER] = "other",
4926 [SCHED_BATCH] = "batch",
4927 [SCHED_IDLE] = "idle",
4928 [SCHED_FIFO] = "fifo",
4932 DEFINE_STRING_TABLE_LOOKUP_WITH_FALLBACK(sched_policy, int, INT_MAX);
4934 static const char* const rlimit_table[] = {
4935 [RLIMIT_CPU] = "LimitCPU",
4936 [RLIMIT_FSIZE] = "LimitFSIZE",
4937 [RLIMIT_DATA] = "LimitDATA",
4938 [RLIMIT_STACK] = "LimitSTACK",
4939 [RLIMIT_CORE] = "LimitCORE",
4940 [RLIMIT_RSS] = "LimitRSS",
4941 [RLIMIT_NOFILE] = "LimitNOFILE",
4942 [RLIMIT_AS] = "LimitAS",
4943 [RLIMIT_NPROC] = "LimitNPROC",
4944 [RLIMIT_MEMLOCK] = "LimitMEMLOCK",
4945 [RLIMIT_LOCKS] = "LimitLOCKS",
4946 [RLIMIT_SIGPENDING] = "LimitSIGPENDING",
4947 [RLIMIT_MSGQUEUE] = "LimitMSGQUEUE",
4948 [RLIMIT_NICE] = "LimitNICE",
4949 [RLIMIT_RTPRIO] = "LimitRTPRIO",
4950 [RLIMIT_RTTIME] = "LimitRTTIME"
4953 DEFINE_STRING_TABLE_LOOKUP(rlimit, int);
4955 static const char* const ip_tos_table[] = {
4956 [IPTOS_LOWDELAY] = "low-delay",
4957 [IPTOS_THROUGHPUT] = "throughput",
4958 [IPTOS_RELIABILITY] = "reliability",
4959 [IPTOS_LOWCOST] = "low-cost",
4962 DEFINE_STRING_TABLE_LOOKUP_WITH_FALLBACK(ip_tos, int, 0xff);
4964 static const char *const __signal_table[] = {
4981 [SIGSTKFLT] = "STKFLT", /* Linux on SPARC doesn't know SIGSTKFLT */
4992 [SIGVTALRM] = "VTALRM",
4994 [SIGWINCH] = "WINCH",
5000 DEFINE_PRIVATE_STRING_TABLE_LOOKUP(__signal, int);
5002 const char *signal_to_string(int signo) {
5003 static __thread char buf[12];
5006 name = __signal_to_string(signo);
5010 if (signo >= SIGRTMIN && signo <= SIGRTMAX)
5011 snprintf(buf, sizeof(buf) - 1, "RTMIN+%d", signo - SIGRTMIN);
5013 snprintf(buf, sizeof(buf) - 1, "%d", signo);
5018 int signal_from_string(const char *s) {
5023 signo = __signal_from_string(s);
5027 if (startswith(s, "RTMIN+")) {
5031 if (safe_atou(s, &u) >= 0) {
5032 signo = (int) u + offset;
5033 if (signo > 0 && signo < _NSIG)
5039 bool kexec_loaded(void) {
5040 bool loaded = false;
5043 if (read_one_line_file("/sys/kernel/kexec_loaded", &s) >= 0) {
5051 int strdup_or_null(const char *a, char **b) {
5069 int prot_from_flags(int flags) {
5071 switch (flags & O_ACCMODE) {
5080 return PROT_READ|PROT_WRITE;
5087 char *format_bytes(char *buf, size_t l, off_t t) {
5090 static const struct {
5094 { "E", 1024ULL*1024ULL*1024ULL*1024ULL*1024ULL*1024ULL },
5095 { "P", 1024ULL*1024ULL*1024ULL*1024ULL*1024ULL },
5096 { "T", 1024ULL*1024ULL*1024ULL*1024ULL },
5097 { "G", 1024ULL*1024ULL*1024ULL },
5098 { "M", 1024ULL*1024ULL },
5102 for (i = 0; i < ELEMENTSOF(table); i++) {
5104 if (t >= table[i].factor) {
5107 (unsigned long long) (t / table[i].factor),
5108 (unsigned long long) (((t*10ULL) / table[i].factor) % 10ULL),
5115 snprintf(buf, l, "%lluB", (unsigned long long) t);
5123 void* memdup(const void *p, size_t l) {
5136 int fd_inc_sndbuf(int fd, size_t n) {
5138 socklen_t l = sizeof(value);
5140 r = getsockopt(fd, SOL_SOCKET, SO_SNDBUF, &value, &l);
5142 l == sizeof(value) &&
5143 (size_t) value >= n*2)
5147 r = setsockopt(fd, SOL_SOCKET, SO_SNDBUF, &value, sizeof(value));
5154 int fd_inc_rcvbuf(int fd, size_t n) {
5156 socklen_t l = sizeof(value);
5158 r = getsockopt(fd, SOL_SOCKET, SO_RCVBUF, &value, &l);
5160 l == sizeof(value) &&
5161 (size_t) value >= n*2)
5165 r = setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &value, sizeof(value));
5172 int fork_agent(pid_t *pid, const int except[], unsigned n_except, const char *path, ...) {
5173 pid_t parent_pid, agent_pid;
5175 bool stdout_is_tty, stderr_is_tty;
5183 parent_pid = getpid();
5185 /* Spawns a temporary TTY agent, making sure it goes away when
5192 if (agent_pid != 0) {
5199 * Make sure the agent goes away when the parent dies */
5200 if (prctl(PR_SET_PDEATHSIG, SIGTERM) < 0)
5201 _exit(EXIT_FAILURE);
5203 /* Check whether our parent died before we were able
5204 * to set the death signal */
5205 if (getppid() != parent_pid)
5206 _exit(EXIT_SUCCESS);
5208 /* Don't leak fds to the agent */
5209 close_all_fds(except, n_except);
5211 stdout_is_tty = isatty(STDOUT_FILENO);
5212 stderr_is_tty = isatty(STDERR_FILENO);
5214 if (!stdout_is_tty || !stderr_is_tty) {
5215 /* Detach from stdout/stderr. and reopen
5216 * /dev/tty for them. This is important to
5217 * ensure that when systemctl is started via
5218 * popen() or a similar call that expects to
5219 * read EOF we actually do generate EOF and
5220 * not delay this indefinitely by because we
5221 * keep an unused copy of stdin around. */
5222 fd = open("/dev/tty", O_WRONLY);
5224 log_error("Failed to open /dev/tty: %m");
5225 _exit(EXIT_FAILURE);
5229 dup2(fd, STDOUT_FILENO);
5232 dup2(fd, STDERR_FILENO);
5238 /* Count arguments */
5240 for (n = 0; va_arg(ap, char*); n++)
5245 l = alloca(sizeof(char *) * (n + 1));
5247 /* Fill in arguments */
5249 for (i = 0; i <= n; i++)
5250 l[i] = va_arg(ap, char*);
5254 _exit(EXIT_FAILURE);
5257 int setrlimit_closest(int resource, const struct rlimit *rlim) {
5258 struct rlimit highest, fixed;
5262 if (setrlimit(resource, rlim) >= 0)
5268 /* So we failed to set the desired setrlimit, then let's try
5269 * to get as close as we can */
5270 assert_se(getrlimit(resource, &highest) == 0);
5272 fixed.rlim_cur = MIN(rlim->rlim_cur, highest.rlim_max);
5273 fixed.rlim_max = MIN(rlim->rlim_max, highest.rlim_max);
5275 if (setrlimit(resource, &fixed) < 0)
5281 int getenv_for_pid(pid_t pid, const char *field, char **_value) {
5282 char path[sizeof("/proc/")-1+10+sizeof("/environ")], *value = NULL;
5294 snprintf(path, sizeof(path), "/proc/%lu/environ", (unsigned long) pid);
5297 f = fopen(path, "re");
5305 char line[LINE_MAX];
5308 for (i = 0; i < sizeof(line)-1; i++) {
5312 if (_unlikely_(c == EOF)) {
5322 if (memcmp(line, field, l) == 0 && line[l] == '=') {
5323 value = strdup(line + l + 1);
5343 int can_sleep(const char *type) {
5347 _cleanup_free_ char *p = NULL;
5351 /* If /sys is read-only we cannot sleep */
5352 if (access("/sys/power/state", W_OK) < 0)
5355 r = read_one_line_file("/sys/power/state", &p);
5360 FOREACH_WORD_SEPARATOR(w, l, p, WHITESPACE, state)
5361 if (l == k && memcmp(w, type, l) == 0)
5367 int can_sleep_disk(const char *type) {
5371 _cleanup_free_ char *p = NULL;
5375 /* If /sys is read-only we cannot sleep */
5376 if (access("/sys/power/state", W_OK) < 0 ||
5377 access("/sys/power/disk", W_OK) < 0)
5380 r = read_one_line_file("/sys/power/disk", &p);
5385 FOREACH_WORD_SEPARATOR(w, l, p, WHITESPACE, state) {
5386 if (l == k && memcmp(w, type, l) == 0)
5389 if (l == k + 2 && w[0] == '[' && memcmp(w + 1, type, l - 2) == 0 && w[l-1] == ']')
5396 bool is_valid_documentation_url(const char *url) {
5399 if (startswith(url, "http://") && url[7])
5402 if (startswith(url, "https://") && url[8])
5405 if (startswith(url, "file:") && url[5])
5408 if (startswith(url, "info:") && url[5])
5411 if (startswith(url, "man:") && url[4])
5417 bool in_initrd(void) {
5418 static __thread int saved = -1;
5424 /* We make two checks here:
5426 * 1. the flag file /etc/initrd-release must exist
5427 * 2. the root file system must be a memory file system
5429 * The second check is extra paranoia, since misdetecting an
5430 * initrd can have bad bad consequences due the initrd
5431 * emptying when transititioning to the main systemd.
5434 saved = access("/etc/initrd-release", F_OK) >= 0 &&
5435 statfs("/", &s) >= 0 &&
5436 is_temporary_fs(&s);
5441 void warn_melody(void) {
5442 _cleanup_close_ int fd = -1;
5444 fd = open("/dev/console", O_WRONLY|O_CLOEXEC|O_NOCTTY);
5448 /* Yeah, this is synchronous. Kinda sucks. But well... */
5450 ioctl(fd, KIOCSOUND, (int)(1193180/440));
5451 usleep(125*USEC_PER_MSEC);
5453 ioctl(fd, KIOCSOUND, (int)(1193180/220));
5454 usleep(125*USEC_PER_MSEC);
5456 ioctl(fd, KIOCSOUND, (int)(1193180/220));
5457 usleep(125*USEC_PER_MSEC);
5459 ioctl(fd, KIOCSOUND, 0);
5462 int make_console_stdio(void) {
5465 /* Make /dev/console the controlling terminal and stdin/stdout/stderr */
5467 fd = acquire_terminal("/dev/console", false, true, true, (usec_t) -1);
5469 log_error("Failed to acquire terminal: %s", strerror(-fd));
5475 log_error("Failed to duplicate terminal fd: %s", strerror(-r));
5482 int get_home_dir(char **_h) {
5490 /* Take the user specified one */
5501 /* Hardcode home directory for root to avoid NSS */
5504 h = strdup("/root");
5512 /* Check the database... */
5516 return errno ? -errno : -ESRCH;
5518 if (!path_is_absolute(p->pw_dir))
5521 h = strdup(p->pw_dir);
5529 int get_shell(char **_sh) {
5537 /* Take the user specified one */
5538 e = getenv("SHELL");
5548 /* Hardcode home directory for root to avoid NSS */
5551 sh = strdup("/bin/sh");
5559 /* Check the database... */
5563 return errno ? -errno : -ESRCH;
5565 if (!path_is_absolute(p->pw_shell))
5568 sh = strdup(p->pw_shell);
5576 void freep(void *p) {
5580 void fclosep(FILE **f) {
5585 void closep(int *fd) {
5587 close_nointr_nofail(*fd);
5590 void closedirp(DIR **d) {
5595 void umaskp(mode_t *u) {
5599 bool filename_is_safe(const char *p) {
5613 if (strlen(p) > FILENAME_MAX)
5619 bool string_is_safe(const char *p) {
5624 for (t = p; *t; t++) {
5625 if (*t > 0 && *t < ' ')
5628 if (strchr("\\\"\'", *t))
5635 /* hey glibc, APIs with callbacks without a user pointer are so useless */
5636 void *xbsearch_r(const void *key, const void *base, size_t nmemb, size_t size,
5637 int (*compar) (const void *, const void *, void *), void *arg) {
5646 p = (void *)(((const char *) base) + (idx * size));
5647 comparison = compar(key, p, arg);
5650 else if (comparison > 0)
5658 bool is_locale_utf8(void) {
5660 static int cached_answer = -1;
5662 if (cached_answer >= 0)
5665 if (!setlocale(LC_ALL, "")) {
5666 cached_answer = true;
5670 set = nl_langinfo(CODESET);
5672 cached_answer = true;
5676 cached_answer = streq(set, "UTF-8");
5678 return (bool)cached_answer;
5681 const char *draw_special_char(DrawSpecialChar ch) {
5682 static const char *draw_table[2][_DRAW_SPECIAL_CHAR_MAX] = {
5684 [DRAW_TREE_VERT] = "\342\224\202 ", /* │ */
5685 [DRAW_TREE_BRANCH] = "\342\224\234\342\224\200", /* ├─ */
5686 [DRAW_TREE_RIGHT] = "\342\224\224\342\224\200", /* └─ */
5687 [DRAW_TREE_SPACE] = " ", /* */
5688 [DRAW_TRIANGULAR_BULLET] = "\342\200\243 ", /* ‣ */
5690 /* ASCII fallback */ {
5691 [DRAW_TREE_VERT] = "| ",
5692 [DRAW_TREE_BRANCH] = "|-",
5693 [DRAW_TREE_RIGHT] = "`-",
5694 [DRAW_TREE_SPACE] = " ",
5695 [DRAW_TRIANGULAR_BULLET] = "> ",
5699 return draw_table[!is_locale_utf8()][ch];
5702 char *strreplace(const char *text, const char *old_string, const char *new_string) {
5705 size_t l, old_len, new_len;
5711 old_len = strlen(old_string);
5712 new_len = strlen(new_string);
5725 if (!startswith(f, old_string)) {
5731 nl = l - old_len + new_len;
5732 a = realloc(r, nl + 1);
5740 t = stpcpy(t, new_string);
5752 char *strip_tab_ansi(char **ibuf, size_t *_isz) {
5753 const char *i, *begin = NULL;
5758 } state = STATE_OTHER;
5760 size_t osz = 0, isz;
5766 /* Strips ANSI color and replaces TABs by 8 spaces */
5768 isz = _isz ? *_isz : strlen(*ibuf);
5770 f = open_memstream(&obuf, &osz);
5774 for (i = *ibuf; i < *ibuf + isz + 1; i++) {
5779 if (i >= *ibuf + isz) /* EOT */
5781 else if (*i == '\x1B')
5782 state = STATE_ESCAPE;
5783 else if (*i == '\t')
5790 if (i >= *ibuf + isz) { /* EOT */
5793 } else if (*i == '[') {
5794 state = STATE_BRACKET;
5799 state = STATE_OTHER;
5806 if (i >= *ibuf + isz || /* EOT */
5807 (!(*i >= '0' && *i <= '9') && *i != ';' && *i != 'm')) {
5810 state = STATE_OTHER;
5812 } else if (*i == 'm')
5813 state = STATE_OTHER;
5835 int on_ac_power(void) {
5836 bool found_offline = false, found_online = false;
5837 _cleanup_closedir_ DIR *d = NULL;
5839 d = opendir("/sys/class/power_supply");
5845 union dirent_storage buf;
5846 _cleanup_free_ char *p = NULL;
5847 _cleanup_close_ int fd = -1, device = -1;
5852 k = readdir_r(d, &buf.de, &de);
5859 if (ignore_file(de->d_name))
5862 device = openat(dirfd(d), de->d_name, O_DIRECTORY|O_RDONLY|O_CLOEXEC|O_NOCTTY);
5864 if (errno == ENOENT || errno == ENOTDIR)
5870 fd = openat(device, "type", O_RDONLY|O_CLOEXEC|O_NOCTTY);
5872 if (errno == ENOENT)
5878 n = read(fd, contents, sizeof(contents));
5882 if (n != 6 || memcmp(contents, "Mains\n", 6))
5885 close_nointr_nofail(fd);
5886 fd = openat(device, "online", O_RDONLY|O_CLOEXEC|O_NOCTTY);
5888 if (errno == ENOENT)
5894 n = read(fd, contents, sizeof(contents));
5898 if (n != 2 || contents[1] != '\n')
5901 if (contents[0] == '1') {
5902 found_online = true;
5904 } else if (contents[0] == '0')
5905 found_offline = true;
5910 return found_online || !found_offline;