summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2023-10-17 13:41:08 +0200
committerLennart Poettering <lennart@poettering.net>2023-10-18 14:49:40 +0200
commiteefb7d22ceb0f6c2dcbba1b0648d2aea3be0ed0d (patch)
treead237fbab5af972757c32c440daef8b943e3cf56
parentprocess-util: add pidref_is_unwaited() and make pid_is_unwaited() return errors (diff)
downloadsystemd-eefb7d22ceb0f6c2dcbba1b0648d2aea3be0ed0d.tar.xz
systemd-eefb7d22ceb0f6c2dcbba1b0648d2aea3be0ed0d.zip
process-util: add API for enumerating processes in /proc/ and pinning them via PidRef
-rw-r--r--src/basic/process-util.c69
-rw-r--r--src/basic/process-util.h4
2 files changed, 73 insertions, 0 deletions
diff --git a/src/basic/process-util.c b/src/basic/process-util.c
index 75bbebd60f..c5883b05d1 100644
--- a/src/basic/process-util.c
+++ b/src/basic/process-util.c
@@ -25,6 +25,7 @@
#include "alloc-util.h"
#include "architecture.h"
#include "argv-util.h"
+#include "dirent-util.h"
#include "env-file.h"
#include "env-util.h"
#include "errno-util.h"
@@ -1963,6 +1964,74 @@ fail:
return -r;
}
+int proc_dir_open(DIR **ret) {
+ DIR *d;
+
+ assert(ret);
+
+ d = opendir("/proc");
+ if (!d)
+ return -errno;
+
+ *ret = d;
+ return 0;
+}
+
+int proc_dir_read(DIR *d, pid_t *ret) {
+ assert(d);
+
+ for (;;) {
+ struct dirent *de;
+
+ errno = 0;
+ de = readdir_no_dot(d);
+ if (!de) {
+ if (errno != 0)
+ return -errno;
+
+ break;
+ }
+
+ if (!IN_SET(de->d_type, DT_DIR, DT_UNKNOWN))
+ continue;
+
+ if (parse_pid(de->d_name, ret) >= 0)
+ return 1;
+ }
+
+ if (ret)
+ *ret = 0;
+ return 0;
+}
+
+int proc_dir_read_pidref(DIR *d, PidRef *ret) {
+ int r;
+
+ assert(d);
+
+ for (;;) {
+ pid_t pid;
+
+ r = proc_dir_read(d, &pid);
+ if (r < 0)
+ return r;
+ if (r == 0)
+ break;
+
+ r = pidref_set_pid(ret, pid);
+ if (r == -ESRCH) /* gone by now? skip it */
+ continue;
+ if (r < 0)
+ return r;
+
+ return 1;
+ }
+
+ if (ret)
+ *ret = PIDREF_NULL;
+ return 0;
+}
+
static const char *const sigchld_code_table[] = {
[CLD_EXITED] = "exited",
[CLD_KILLED] = "killed",
diff --git a/src/basic/process-util.h b/src/basic/process-util.h
index 7c05a69ca0..a18a730936 100644
--- a/src/basic/process-util.h
+++ b/src/basic/process-util.h
@@ -223,3 +223,7 @@ int is_reaper_process(void);
int make_reaper_process(bool b);
int posix_spawn_wrapper(const char *path, char *const *argv, char *const *envp, pid_t *ret_pid);
+
+int proc_dir_open(DIR **ret);
+int proc_dir_read(DIR *d, pid_t *ret);
+int proc_dir_read_pidref(DIR *d, PidRef *ret);