about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--Makefile1
-rw-r--r--main.c1
-rw-r--r--netif.c63
3 files changed, 65 insertions, 0 deletions
diff --git a/Makefile b/Makefile
index 91d7f13..ff78405 100644
--- a/Makefile
+++ b/Makefile
@@ -24,6 +24,7 @@ COLLECTORS += hwmon
 COLLECTORS += mdstat
 COLLECTORS += meminfo
 COLLECTORS += netdev
+COLLECTORS += netif
 COLLECTORS += loadavg
 COLLECTORS += pressure
 COLLECTORS += rapl
diff --git a/main.c b/main.c
index fbd610a..2cec7ec 100644
--- a/main.c
+++ b/main.c
@@ -40,6 +40,7 @@
   X(mdstat) \
   X(meminfo) \
   X(netdev) \
+  X(netif) \
   X(pressure) \
   X(rapl) \
   X(schedstat) \
diff --git a/netif.c b/netif.c
new file mode 100644
index 0000000..1fe20b5
--- /dev/null
+++ b/netif.c
@@ -0,0 +1,63 @@
+#define _GNU_SOURCE
+#include <fcntl.h>
+#include <glob.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "scrape.h"
+#include "util.h"
+
+// size of input buffer for paths and lines
+#define BUF_SIZE 256
+
+static void netif_collect(scrape_req *req, void *ctx);
+
+const struct collector netif_collector = {
+  .name = "netif",
+  .collect = netif_collect,
+};
+
+static void netif_collect_dir(scrape_req *req, char *dir) {
+  char buf[BUF_SIZE];
+  char dev[32] = { 0 };
+  strcpy(dev, dir + 15 /* "/sys/class/net" */);
+
+  int dirfd = open(dir, O_PATH);
+  if (dirfd < 0)
+    return;
+
+  struct label dev_label[] = {
+    { .key = "device", .value = dev },
+    LABEL_END,
+  };
+
+  if (read_file_at(dirfd, "carrier", buf, sizeof buf) > 0)
+    scrape_write(req, "node_network_carrier", dev_label, atof(buf));
+
+  if (read_file_at(dirfd, "carrier_changes", buf, sizeof buf) > 0)
+    scrape_write(req, "node_network_carrier_changes_total", dev_label, atof(buf));
+
+  if (read_file_at(dirfd, "speed", buf, sizeof buf) > 0)
+    if (atof(buf) > 0)
+      scrape_write(req, "node_network_speed_bytes", dev_label,
+          atof(buf) * 125000.0); /* Mbit -> bytes */
+
+  close(dirfd);
+}
+
+static void netif_collect(scrape_req *req, void *ctx) {
+  (void) ctx;
+
+  // scan /sys/class/net for metrics
+
+  glob_t globbuf = { 0 };
+  if (glob("/sys/class/net/*", GLOB_NOSORT | GLOB_ONLYDIR, 0, &globbuf) != 0)
+    return;
+
+  for (size_t i = 0; i < globbuf.gl_pathc; i++)
+    netif_collect_dir(req, globbuf.gl_pathv[i]);
+
+  globfree(&globbuf);
+}