diff options
| author | Ludovic Courtès <ludo@gnu.org> | 2025-02-11 17:42:37 +0100 |
|---|---|---|
| committer | Ludovic Courtès <ludo@gnu.org> | 2025-03-26 17:57:42 +0100 |
| commit | f03e6eff2f491fbf1a38b36d46c0fe2fdd3e6886 (patch) | |
| tree | 91c7edbe4864fe80d17d7754d7e833dfafb75ef3 | |
| parent | 92205bab4dcf25a9c4dbe08daf0e53c6e608ca3e (diff) | |
daemon: Use ‘close_range’ where available.
* nix/libutil/util.cc (closeMostFDs) [HAVE_CLOSE_RANGE]: Use
‘close_range’ when ‘exceptions’ is empty.
* config-daemon.ac: Check for <linux/close_range.h> and the
‘close_range’ symbol.
Change-Id: I12fa3bde58b003fcce5ea5a1fee1dcf9a92c0359
| -rw-r--r-- | config-daemon.ac | 5 | ||||
| -rw-r--r-- | nix/libutil/util.cc | 23 |
2 files changed, 20 insertions, 8 deletions
diff --git a/config-daemon.ac b/config-daemon.ac index 6731c68bc39..4e949bc88a3 100644 --- a/config-daemon.ac +++ b/config-daemon.ac | |||
| @@ -78,7 +78,8 @@ if test "x$guix_build_daemon" = "xyes"; then | |||
| 78 | 78 | ||
| 79 | dnl Chroot support. | 79 | dnl Chroot support. |
| 80 | AC_CHECK_FUNCS([chroot unshare]) | 80 | AC_CHECK_FUNCS([chroot unshare]) |
| 81 | AC_CHECK_HEADERS([sched.h sys/param.h sys/mount.h sys/syscall.h]) | 81 | AC_CHECK_HEADERS([sched.h sys/param.h sys/mount.h sys/syscall.h \ |
| 82 | linux/close_range.h]) | ||
| 82 | 83 | ||
| 83 | if test "x$ac_cv_func_chroot" != "xyes"; then | 84 | if test "x$ac_cv_func_chroot" != "xyes"; then |
| 84 | AC_MSG_ERROR(['chroot' function missing, bailing out]) | 85 | AC_MSG_ERROR(['chroot' function missing, bailing out]) |
| @@ -95,7 +96,7 @@ if test "x$guix_build_daemon" = "xyes"; then | |||
| 95 | dnl strsignal: for error reporting. | 96 | dnl strsignal: for error reporting. |
| 96 | dnl statx: fine-grain 'stat' call, new in glibc 2.28. | 97 | dnl statx: fine-grain 'stat' call, new in glibc 2.28. |
| 97 | AC_CHECK_FUNCS([lutimes lchown posix_fallocate sched_setaffinity \ | 98 | AC_CHECK_FUNCS([lutimes lchown posix_fallocate sched_setaffinity \ |
| 98 | statvfs nanosleep strsignal statx]) | 99 | statvfs nanosleep strsignal statx close_range]) |
| 99 | 100 | ||
| 100 | dnl Check for <locale>. | 101 | dnl Check for <locale>. |
| 101 | AC_LANG_PUSH(C++) | 102 | AC_LANG_PUSH(C++) |
diff --git a/nix/libutil/util.cc b/nix/libutil/util.cc index 3206dea11b1..eb2d16e1cc3 100644 --- a/nix/libutil/util.cc +++ b/nix/libutil/util.cc | |||
| @@ -23,6 +23,10 @@ | |||
| 23 | #include <sys/prctl.h> | 23 | #include <sys/prctl.h> |
| 24 | #endif | 24 | #endif |
| 25 | 25 | ||
| 26 | #ifdef HAVE_LINUX_CLOSE_RANGE_H | ||
| 27 | # include <linux/close_range.h> | ||
| 28 | #endif | ||
| 29 | |||
| 26 | 30 | ||
| 27 | extern char * * environ; | 31 | extern char * * environ; |
| 28 | 32 | ||
| @@ -1087,12 +1091,19 @@ string runProgram(Path program, bool searchPath, const Strings & args) | |||
| 1087 | 1091 | ||
| 1088 | void closeMostFDs(const set<int> & exceptions) | 1092 | void closeMostFDs(const set<int> & exceptions) |
| 1089 | { | 1093 | { |
| 1090 | int maxFD = 0; | 1094 | #ifdef HAVE_CLOSE_RANGE |
| 1091 | maxFD = sysconf(_SC_OPEN_MAX); | 1095 | if (exceptions.empty()) |
| 1092 | for (int fd = 0; fd < maxFD; ++fd) | 1096 | close_range(3, ~0U, 0); |
| 1093 | if (fd != STDIN_FILENO && fd != STDOUT_FILENO && fd != STDERR_FILENO | 1097 | else |
| 1094 | && exceptions.find(fd) == exceptions.end()) | 1098 | #endif |
| 1095 | close(fd); /* ignore result */ | 1099 | { |
| 1100 | int maxFD = 0; | ||
| 1101 | maxFD = sysconf(_SC_OPEN_MAX); | ||
| 1102 | for (int fd = 0; fd < maxFD; ++fd) | ||
| 1103 | if (fd != STDIN_FILENO && fd != STDOUT_FILENO && fd != STDERR_FILENO | ||
| 1104 | && exceptions.find(fd) == exceptions.end()) | ||
| 1105 | close(fd); /* ignore result */ | ||
| 1106 | } | ||
| 1096 | } | 1107 | } |
| 1097 | 1108 | ||
| 1098 | 1109 | ||
