]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
process-util: add simple wrapper around PR_SET_CHILD_SUBREAPER
authorLennart Poettering <lennart@poettering.net>
Thu, 22 Jun 2023 20:24:04 +0000 (22:24 +0200)
committerLennart Poettering <lennart@poettering.net>
Fri, 23 Jun 2023 08:05:16 +0000 (10:05 +0200)
Let's a simple helper that knows how to deal with PID == 1.

src/basic/process-util.c
src/basic/process-util.h
src/core/main.c
src/nspawn/nspawn.c
src/test/test-async.c
src/test/test-process-util.c

index 437e83bc6d7f2d3f07eca2eee568db454e9345e0..001002a55e9f8466feabbacc366685080191acaf 100644 (file)
@@ -1705,6 +1705,24 @@ int is_reaper_process(void) {
         return b != 0;
 }
 
+int make_reaper_process(bool b) {
+
+        if (getpid_cached() == 1) {
+
+                if (!b)
+                        return -EINVAL;
+
+                return 0;
+        }
+
+        /* Some prctl()s insist that all 5 arguments are specified, others do not. Let's always specify all,
+         * to avoid any ambiguities */
+        if (prctl(PR_SET_CHILD_SUBREAPER, (unsigned long) b, 0UL, 0UL, 0UL) < 0)
+                return -errno;
+
+        return 0;
+}
+
 static const char *const sigchld_code_table[] = {
         [CLD_EXITED] = "exited",
         [CLD_KILLED] = "killed",
index 1b77478cf5b24bf0aefd216de64d5fcb09a8cbf1..8f87fdc2ae74f578fe129046668d7a0e8f925f77 100644 (file)
@@ -209,3 +209,4 @@ _noreturn_ void freeze(void);
 int get_process_threads(pid_t pid);
 
 int is_reaper_process(void);
+int make_reaper_process(bool b);
index f067b13fff876057b5e70cbf1da39a5973d1390a..208d22f4f329848b7d4825d322eaf953512ed5a2 100644 (file)
@@ -2294,10 +2294,9 @@ static int initialize_runtime(
                 }
         }
 
-        if (arg_runtime_scope == RUNTIME_SCOPE_USER)
-                /* Become reaper of our children */
-                if (prctl(PR_SET_CHILD_SUBREAPER, 1) < 0)
-                        log_warning_errno(errno, "Failed to make us a subreaper, ignoring: %m");
+        r = make_reaper_process(true);
+        if (r < 0)
+                log_warning_errno(r, "Failed to make us a subreaper, ignoring: %m");
 
         /* Bump up RLIMIT_NOFILE for systemd itself */
         (void) bump_rlimit_nofile(saved_rlimit_nofile);
index 97a2c386e6bc82e27a835aa0f14bb903191930d7..4fdb5e9fd78a5172ef8bb2fbc8705e750ca15c66 100644 (file)
@@ -5826,8 +5826,9 @@ static int run(int argc, char *argv[]) {
 
         assert_se(sigprocmask_many(SIG_BLOCK, NULL, SIGCHLD, SIGWINCH, SIGTERM, SIGINT, SIGRTMIN+18, -1) >= 0);
 
-        if (prctl(PR_SET_CHILD_SUBREAPER, 1, 0, 0, 0) < 0) {
-                r = log_error_errno(errno, "Failed to become subreaper: %m");
+        r = make_reaper_process(true);
+        if (r < 0) {
+                log_error_errno(r, "Failed to become subreaper: %m");
                 goto finish;
         }
 
index 64b94886ff332d5d1bc85aa1d3cd4bb5aa07f901..dc0e34b48f7cbb3903935f7432c0c03f30c2545d 100644 (file)
@@ -36,7 +36,7 @@ TEST(asynchronous_close) {
         if (r == 0) {
                 /* child */
 
-                assert(prctl(PR_SET_CHILD_SUBREAPER, 1, 0, 0, 0) >= 0);
+                assert(make_reaper_process(true) >= 0);
 
                 fd = open("/dev/null", O_RDONLY|O_CLOEXEC);
                 assert_se(fd >= 0);
@@ -72,7 +72,7 @@ TEST(asynchronous_rm_rf) {
                 /* child */
 
                 assert_se(sigprocmask_many(SIG_BLOCK, NULL, SIGCHLD, -1) >= 0);
-                assert_se(prctl(PR_SET_CHILD_SUBREAPER, 1, 0, 0, 0) >= 0);
+                assert_se(make_reaper_process(true) >= 0);
 
                 assert_se(mkdtemp_malloc(NULL, &tt) >= 0);
                 assert_se(kk = path_join(tt, "somefile"));
index 6de09c3c11f8a5d5fa6fd0375a34cf43ecd0a386..ebf73c54ec6dcc50fb819fc86d81b16ad1becee0 100644 (file)
@@ -931,7 +931,7 @@ TEST(is_reaper_process) {
         assert_se(r >= 0);
         if (r == 0) {
                 /* child */
-                assert_se(prctl(PR_SET_CHILD_SUBREAPER, 1, 0, 0, 0) >= 0);
+                assert_se(make_reaper_process(true) >= 0);
 
                 assert_se(is_reaper_process() > 0);
                 _exit(EXIT_SUCCESS);