]> git.itanic.dy.fi Git - rrdd/commitdiff
onewire_parser: Add support for reading data from file system
authorTimo Kokkonen <timo.t.kokkonen@iki.fi>
Sun, 24 Jul 2016 12:42:16 +0000 (15:42 +0300)
committerTimo Kokkonen <timo.t.kokkonen@iki.fi>
Sun, 24 Jul 2016 13:02:04 +0000 (16:02 +0300)
Reading data from file system might be preferrable for example when
older ownet client code is in use and that is causing memory leaks.

In principle the logic is all the same regardless which method is
used, only the read method is different.

Signed-off-by: Timo Kokkonen <timo.t.kokkonen@iki.fi>
onewire_parser.c

index 96bd5b2b0cfb8a873991f310f8ab6571683d2f55..f07f7d9d45e095943d2a65f39dce6da87ce62ec6 100644 (file)
@@ -1,5 +1,9 @@
 #include <stdio.h>
 #include <ownetapi.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <unistd.h>
 
 #include "parser.h"
 #include "debug.h"
@@ -73,30 +77,80 @@ static int make_uncached(char *path, size_t len)
        return 0;
 }
 
+static int owfs_read(const char *mount_point, const char *path, char **res)
+{
+       char result[64];
+       char file[2048];
+       int fd, ret;
+
+       snprintf(file, sizeof(file), "%s/%s", mount_point, path);
+
+       fd = open(file, O_RDONLY | O_CLOEXEC);
+       if (fd < 0) {
+               pr_err("Failed to open file %s: %m\n", file);
+               return -1;
+       }
+
+       ret = read(fd, result, sizeof(result));
+       if (ret < 0) {
+               pr_err("Failed to read from file %s: %m\n", file);
+               goto out_close;
+       }
+
+       *res = strndup(result, sizeof(result));
+
+out_close:
+       close(fd);
+
+       return ret;
+}
+
+static int is_mount_point(const char *str)
+{
+       /*
+        * Filesystem paths begin with a slash, everything else must
+        * be a network addresses
+        */
+       if (str[0] == '/')
+               return 1;
+
+       return 0;
+}
+
 static int onewire_parser(char *rrd_data, const char **parser_data)
 {
        OWNET_HANDLE h;
-       const char *server_addr;
+       const char *server_addr, *mount_point;
        char buf[24], *tmp;
        int i = 1, ret;
        int max_str = RRD_DATA_MAX_LEN;
+       int is_mountpoint = is_mount_point(parser_data[0]);
 
        if (!parser_data) {
                pr_err("No parser data available\n");
                return -1;
        }
 
-       server_addr = parser_data[0];
+       if (is_mountpoint) {
+               mount_point = parser_data[0];
 
-       if (!server_addr) {
-               pr_err("Server address not specified\n");
-               return -1;
-       }
+               if (!mount_point) {
+                       pr_err("Server address not specified\n");
+                       return -1;
+               }
+       } else {
+               server_addr = parser_data[0];
 
-       h = OWNET_init(server_addr);
-       if (h < 0) {
-               pr_err("Failed to connect to server %s\n", server_addr);
-               return -1;
+               if (!server_addr) {
+                       pr_err("Server address not specified\n");
+                       return -1;
+               }
+
+               h = OWNET_init(server_addr);
+               if (h < 0) {
+                       pr_err("Failed to connect to server %s\n", server_addr);
+                       return -1;
+               }
        }
 
        while (parser_data[i]) {
@@ -121,7 +175,11 @@ undefined:
 
                        pr_info("Reading data for entry %s with offset of %.2f\n",
                                ow_path, offset);
-                       ret = OWNET_read(h, ow_path, &tmp);
+
+                       if (is_mountpoint)
+                               ret = owfs_read(mount_point, ow_path, &tmp);
+                       else
+                               ret = OWNET_read(h, ow_path, &tmp);
 
                        /* Skip leading white space */
                        tmp2 = tmp;
@@ -180,7 +238,9 @@ next:
        }
        rrd_data = 0;
 
-       OWNET_finish();
+       if (!is_mountpoint)
+               OWNET_finish();
+
        return 0;
 }