wireless: fix use-after-free bug
[project/netifd.git] / utils.c
diff --git a/utils.c b/utils.c
index 986cee9..d202505 100644 (file)
--- a/utils.c
+++ b/utils.c
 #include <arpa/inet.h>
 #include <netinet/in.h>
 
+#ifdef __APPLE__
+#include <libproc.h>
+#endif
+
 void
 __vlist_simple_init(struct vlist_simple_tree *tree, int offset)
 {
@@ -129,3 +133,65 @@ parse_ip_and_netmask(int af, const char *str, void *addr, unsigned int *netmask)
 
        return inet_pton(af, astr, addr);
 }
+
+char *
+format_macaddr(uint8_t *mac)
+{
+       static char str[sizeof("ff:ff:ff:ff:ff:ff ")];
+
+       snprintf(str, sizeof(str), "%02x:%02x:%02x:%02x:%02x:%02x",
+                mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]);
+
+       return str;
+}
+
+uint32_t
+crc32_file(FILE *fp)
+{
+       static uint32_t *crcvals = NULL;
+       if (!crcvals) {
+               crcvals = malloc(sizeof(*crcvals) * 256);
+
+               for (size_t i = 0; i < 256; ++i) {
+                       uint32_t c = i;
+                       for (size_t j = 0; j < 8; ++j)
+                               c = (c & 1) ? (0xEDB88320 ^ (c >> 1)) : (c >> 1);
+                       crcvals[i] = c;
+               }
+       }
+
+       uint8_t buf[1024];
+       size_t len;
+       uint32_t c = 0xFFFFFFFF;
+
+       do {
+               len = fread(buf, 1, sizeof(buf), fp);
+               for (size_t i = 0; i < len; ++i)
+                       c = crcvals[(c ^ buf[i]) & 0xFF] ^ (c >> 8);
+       } while (len == sizeof(buf));
+
+       return c ^ 0xFFFFFFFF;
+}
+
+bool check_pid_path(int pid, const char *exe)
+{
+       int proc_exe_len;
+       int exe_len = strlen(exe);
+
+#ifdef __APPLE__
+       char proc_exe_buf[PROC_PIDPATHINFO_SIZE];
+
+       proc_exe_len = proc_pidpath(pid, proc_exe_buf, sizeof(proc_exe_buf));
+#else
+       char proc_exe[32];
+       char *proc_exe_buf = alloca(exe_len);
+
+       sprintf(proc_exe, "/proc/%d/exe", pid);
+       proc_exe_len = readlink(proc_exe, proc_exe_buf, exe_len);
+#endif
+
+       if (proc_exe_len != exe_len)
+               return false;
+
+       return !memcmp(exe, proc_exe_buf, exe_len);
+}