From: Mike Yuan Date: Wed, 20 Nov 2024 14:17:30 +0000 (+0100) Subject: process-util: port pidref_get_uid() and pidref_is_my_child() to pidfd helpers X-Git-Tag: v258-rc1~1704^2~3 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=47f64104d195a06aa89cf63f98e8287126e07903;p=thirdparty%2Fsystemd.git process-util: port pidref_get_uid() and pidref_is_my_child() to pidfd helpers --- diff --git a/src/basic/namespace-util.c b/src/basic/namespace-util.c index 74876100697..9293999a019 100644 --- a/src/basic/namespace-util.c +++ b/src/basic/namespace-util.c @@ -349,7 +349,7 @@ int namespace_get_leader(pid_t pid, NamespaceType type, pid_t *ret) { for (;;) { pid_t ppid; - r = get_process_ppid(pid, &ppid); + r = pid_get_ppid(pid, &ppid); if (r < 0) return r; diff --git a/src/basic/pidfd-util.c b/src/basic/pidfd-util.c index b2a2188e4ba..204439e4447 100644 --- a/src/basic/pidfd-util.c +++ b/src/basic/pidfd-util.c @@ -188,7 +188,7 @@ int pidfd_get_ppid(int fd, pid_t *ret) { assert(FLAGS_SET(info.mask, PIDFD_INFO_PID)); - if (info.ppid == 0) + if (info.ppid == 0) /* See comments in pid_get_ppid() */ return -EADDRNOTAVAIL; if (ret) diff --git a/src/basic/process-util.c b/src/basic/process-util.c index e0ba9126339..f412d202eb8 100644 --- a/src/basic/process-util.c +++ b/src/basic/process-util.c @@ -48,6 +48,7 @@ #include "nulstr-util.h" #include "parse-util.h" #include "path-util.h" +#include "pidfd-util.h" #include "process-util.h" #include "raw-clone.h" #include "rlimit-util.h" @@ -557,7 +558,6 @@ int pid_get_uid(pid_t pid, uid_t *ret) { } int pidref_get_uid(const PidRef *pid, uid_t *ret) { - uid_t uid; int r; if (!pidref_is_set(pid)) @@ -566,6 +566,13 @@ int pidref_get_uid(const PidRef *pid, uid_t *ret) { if (pidref_is_remote(pid)) return -EREMOTE; + if (pid->fd >= 0) { + r = pidfd_get_uid(pid->fd, ret); + if (!ERRNO_IS_NEG_NOT_SUPPORTED(r)) + return r; + } + + uid_t uid; r = pid_get_uid(pid->pid, &uid); if (r < 0) return r; @@ -651,7 +658,7 @@ int get_process_environ(pid_t pid, char **ret) { return 0; } -int get_process_ppid(pid_t pid, pid_t *ret) { +int pid_get_ppid(pid_t pid, pid_t *ret) { _cleanup_free_ char *line = NULL; unsigned long ppid; const char *p; @@ -706,6 +713,35 @@ int get_process_ppid(pid_t pid, pid_t *ret) { return 0; } +int pidref_get_ppid(const PidRef *pidref, pid_t *ret) { + int r; + + if (!pidref_is_set(pidref)) + return -ESRCH; + + if (pidref_is_remote(pidref)) + return -EREMOTE; + + if (pidref->fd >= 0) { + r = pidfd_get_ppid(pidref->fd, ret); + if (!ERRNO_IS_NEG_NOT_SUPPORTED(r)) + return r; + } + + pid_t ppid; + r = pid_get_ppid(pidref->pid, ret ? &ppid : NULL); + if (r < 0) + return r; + + r = pidref_verify(pidref); + if (r < 0) + return r; + + if (ret) + *ret = ppid; + return 0; +} + int pid_get_start_time(pid_t pid, usec_t *ret) { _cleanup_free_ char *line = NULL; const char *p; @@ -1046,41 +1082,32 @@ int getenv_for_pid(pid_t pid, const char *field, char **ret) { return 0; } -int pid_is_my_child(pid_t pid) { - pid_t ppid; +int pidref_is_my_child(const PidRef *pid) { int r; - if (pid < 0) + if (!pidref_is_set(pid)) return -ESRCH; - if (pid <= 1) + if (pidref_is_remote(pid)) + return -EREMOTE; + + if (pid->pid == 1 || pidref_is_self(pid)) return false; - r = get_process_ppid(pid, &ppid); + pid_t ppid; + r = pidref_get_ppid(pid, &ppid); if (r < 0) return r; return ppid == getpid_cached(); } -int pidref_is_my_child(const PidRef *pid) { - int r, result; - - if (!pidref_is_set(pid)) - return -ESRCH; - - if (pidref_is_remote(pid)) - return -EREMOTE; - - result = pid_is_my_child(pid->pid); - if (result < 0) - return result; +int pid_is_my_child(pid_t pid) { - r = pidref_verify(pid); - if (r < 0) - return r; + if (pid == 0) + return false; - return result; + return pidref_is_my_child(&PIDREF_MAKE_FROM_PID(pid)); } int pid_is_unwaited(pid_t pid) { diff --git a/src/basic/process-util.h b/src/basic/process-util.h index 78cf90d3706..b436a7b1b31 100644 --- a/src/basic/process-util.h +++ b/src/basic/process-util.h @@ -52,9 +52,10 @@ int get_process_gid(pid_t pid, gid_t *ret); int get_process_cwd(pid_t pid, char **ret); int get_process_root(pid_t pid, char **ret); int get_process_environ(pid_t pid, char **ret); -int get_process_ppid(pid_t pid, pid_t *ret); +int pid_get_ppid(pid_t pid, pid_t *ret); +int pidref_get_ppid(const PidRef *pidref, pid_t *ret); int pid_get_start_time(pid_t pid, usec_t *ret); -int pidref_get_start_time(const PidRef* pid, usec_t *ret); +int pidref_get_start_time(const PidRef *pid, usec_t *ret); int get_process_umask(pid_t pid, mode_t *ret); int container_get_leader(const char *machine, pid_t *pid); diff --git a/src/test/test-process-util.c b/src/test/test-process-util.c index e6ba6fea707..5a6bcdffcc0 100644 --- a/src/test/test-process-util.c +++ b/src/test/test-process-util.c @@ -69,7 +69,7 @@ static void test_pid_get_comm_one(pid_t pid) { ASSERT_OK(pid_get_cmdline(pid, 1, 0, &d)); log_info("PID"PID_FMT" cmdline truncated to 1: '%s'", pid, d); - r = get_process_ppid(pid, &e); + r = pid_get_ppid(pid, &e); if (pid == 1) ASSERT_ERROR(r, EADDRNOTAVAIL); else @@ -813,18 +813,18 @@ TEST(setpriority_closest) { } } -TEST(get_process_ppid) { +TEST(pid_get_ppid) { uint64_t limit; int r; - ASSERT_ERROR(get_process_ppid(1, NULL), EADDRNOTAVAIL); + ASSERT_ERROR(pid_get_ppid(1, NULL), EADDRNOTAVAIL); /* the process with the PID above the global limit definitely doesn't exist. Verify that */ ASSERT_OK(procfs_get_pid_max(&limit)); log_debug("kernel.pid_max = %"PRIu64, limit); if (limit < INT_MAX) { - r = get_process_ppid(limit + 1, NULL); + r = pid_get_ppid(limit + 1, NULL); log_debug_errno(r, "get_process_limit(%"PRIu64") → %d/%m", limit + 1, r); assert(r == -ESRCH); } @@ -833,7 +833,7 @@ TEST(get_process_ppid) { _cleanup_free_ char *c1 = NULL, *c2 = NULL; pid_t ppid; - r = get_process_ppid(pid, &ppid); + r = pid_get_ppid(pid, &ppid); if (r == -EADDRNOTAVAIL) { log_info("No further parent PID"); break;