aboutsummaryrefslogtreecommitdiffstats
path: root/src/afs-discover.c
diff options
context:
space:
mode:
authorJosé Bollo <jose.bollo@iot.bzh>2018-02-14 15:12:30 +0100
committerJosé Bollo <jose.bollo@iot.bzh>2018-02-14 15:12:30 +0100
commitabbb4599f0b921c6f434b6bd02bcfb277eecf745 (patch)
treefd8a7449742fbb4c445286529349ab12cca9540a /src/afs-discover.c
parent4788fcd7becaef5a665dea0f9c0345401c80f757 (diff)
afs-supervisor: Add discovery mechanic
Change-Id: Icfcdcc16d0433454c9bb0785d0690f7f173980ae Signed-off-by: José Bollo <jose.bollo@iot.bzh>
Diffstat (limited to 'src/afs-discover.c')
-rw-r--r--src/afs-discover.c66
1 files changed, 66 insertions, 0 deletions
diff --git a/src/afs-discover.c b/src/afs-discover.c
new file mode 100644
index 00000000..cad95574
--- /dev/null
+++ b/src/afs-discover.c
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2016, 2017 "IoT.bzh"
+ * Author José Bollo <jose.bollo@iot.bzh>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#define _GNU_SOURCE
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <stdint.h>
+#include <string.h>
+#include <ctype.h>
+#include <dirent.h>
+#include <unistd.h>
+#include <sys/types.h>
+
+void afs_discover(const char *pattern, void (*callback)(void *closure, pid_t pid), void *closure)
+{
+ intmax_t n;
+ DIR *dir;
+ struct dirent *ent;
+ char *name;
+ char exe[PATH_MAX], lnk[PATH_MAX];
+
+ dir = opendir("/proc");
+ while ((ent = readdir(dir))) {
+ name = ent->d_name;
+ while (isdigit(*name))
+ name++;
+ if (*name)
+ continue;
+ n = snprintf(exe, sizeof exe, "/proc/%s/exe", ent->d_name);
+ if (n < 0 || (size_t)n >= sizeof exe)
+ continue;
+ n = readlink(exe, lnk, sizeof lnk);
+ if (n < 0 || (size_t)n >= sizeof lnk)
+ continue;
+ lnk[n] = 0;
+ name = lnk;
+ while(*name) {
+ while(*name == '/')
+ name++;
+ if (*name) {
+ if (!strcmp(name, pattern)) {
+ callback(closure, (pid_t)atoi(ent->d_name));
+ break;
+ }
+ while(*++name && *name != '/');
+ }
+ }
+ }
+ closedir(dir);
+}
+