src/rrd_lastupdate.c: Implement the `--daemon' option for `rrdtool lastupdate'.
authorFlorian Forster <octo@leeloo.home.verplant.org>
Sun, 13 Jul 2008 14:08:21 +0000 (16:08 +0200)
committerFlorian Forster <octo@leeloo.home.verplant.org>
Sun, 13 Jul 2008 14:08:21 +0000 (16:08 +0200)
The new library function `rrd_lastupdate' takes the usual (argc, argv)
arguments. The `rrd_lastupdate_r' function has been changed to receive
a file name directly instead of using only argv[1].

src/librrd.sym
src/rrd.h
src/rrd_lastupdate.c
src/rrd_tool.c

index db276dd..47cc2b8 100644 (file)
@@ -25,6 +25,7 @@ rrd_init
 rrd_last
 rrd_last_r
 rrd_lastupdate
 rrd_last
 rrd_last_r
 rrd_lastupdate
+rrd_lastupdate_r
 rrd_lock
 rrd_new_context
 rrd_open
 rrd_lock
 rrd_new_context
 rrd_open
index b29d19d..f621e35 100644 (file)
--- a/src/rrd.h
+++ b/src/rrd.h
@@ -171,13 +171,7 @@ extern    "C" {
     time_t    rrd_last(
     int,
     char **);
     time_t    rrd_last(
     int,
     char **);
-    int       rrd_lastupdate(
-    int argc,
-    char **argv,
-    time_t *last_update,
-    unsigned long *ds_cnt,
-    char ***ds_namv,
-    char ***last_ds);
+    int rrd_lastupdate(int argc, char **argv);
     time_t    rrd_first(
     int,
     char **);
     time_t    rrd_first(
     int,
     char **);
@@ -229,8 +223,12 @@ extern    "C" {
     int       rrd_dump_r(
     const char *filename,
     char *outname);
     int       rrd_dump_r(
     const char *filename,
     char *outname);
-    time_t    rrd_last_r(
-    const char *filename);
+    time_t    rrd_last_r (const char *filename);
+    int rrd_lastupdate_r (const char *filename,
+            time_t *ret_last_update,
+            unsigned long *ret_ds_count,
+            char ***ret_ds_names,
+            char ***ret_last_ds);
     time_t    rrd_first_r(
     const char *filename,
     int rraindex);
     time_t    rrd_first_r(
     const char *filename,
     int rraindex);
index 06f0341..3ca78e1 100644 (file)
 /*****************************************************************************
  * RRDtool 1.3.0  Copyright by Tobi Oetiker, 1997-2008
 /*****************************************************************************
  * RRDtool 1.3.0  Copyright by Tobi Oetiker, 1997-2008
+ *                Copyright by Florian Forster, 2008
  *****************************************************************************
  * rrd_lastupdate  Get the last datum entered for each DS
  *****************************************************************************/
 
 #include "rrd_tool.h"
 #include "rrd_rpncalc.h"
  *****************************************************************************
  * rrd_lastupdate  Get the last datum entered for each DS
  *****************************************************************************/
 
 #include "rrd_tool.h"
 #include "rrd_rpncalc.h"
+#include "rrd_client.h"
 #include <stdarg.h>
 
 #include <stdarg.h>
 
-int rrd_lastupdate(
-    int argc,
-    char **argv,
-    time_t *last_update,
-    unsigned long *ds_cnt,
-    char ***ds_namv,
-    char ***last_ds)
+int rrd_lastupdate (int argc, char **argv)
+{
+    time_t    last_update;
+    char    **ds_names;
+    char    **last_ds;
+    unsigned long ds_count, i;
+    int status;
+
+    char *opt_daemon = NULL;
+
+    optind = 0;
+    opterr = 0;         /* initialize getopt */
+
+    while (42) {
+        int       opt;
+        int       option_index = 0;
+        static struct option long_options[] = {
+            {"daemon", required_argument, 0, 'd'},
+            {0, 0, 0, 0}
+        };
+
+        opt = getopt_long (argc, argv, "d:", long_options, &option_index);
+
+        if (opt == EOF)
+            break;
+
+        switch (opt) {
+        case 'd':
+            if (opt_daemon != NULL)
+                    free (opt_daemon);
+            opt_daemon = strdup (optarg);
+            if (opt_daemon == NULL)
+            {
+                rrd_set_error ("strdup failed.");
+                return (-1);
+            }
+            break;
+
+        default:
+            rrd_set_error ("Usage: rrdtool %s [--daemon <addr>] <file>",
+                    argv[0]);
+            return (-1);
+            break;
+        }
+    }                   /* while (42) */
+
+    if ((argc - optind) != 1) {
+        rrd_set_error ("Usage: rrdtool %s [--daemon <addr>] <file>",
+                argv[0]);
+        return (-1);
+    }
+
+    if (opt_daemon == NULL)
+    {
+        char *temp;
+
+        temp = getenv (ENV_RRDCACHED_ADDRESS);
+        if (temp != NULL)
+        {
+            opt_daemon = strdup (temp);
+            if (opt_daemon == NULL)
+            {
+                rrd_set_error("strdup failed.");
+                return (-1);
+            }
+        }
+    }
+
+    if (opt_daemon != NULL)
+    {
+        status = rrdc_connect (opt_daemon);
+        if (status != 0)
+        {
+            rrd_set_error ("rrdc_connect failed with status %i.", status);
+            return (-1);
+        }
+
+        status = rrdc_flush (argv[optind]);
+        if (status != 0)
+        {
+            rrd_set_error ("rrdc_flush (%s) failed with status %i.",
+                    argv[optind], status);
+            return (-1);
+        }
+
+        rrdc_disconnect ();
+    } /* if (opt_daemon) */
+
+    status = rrd_lastupdate_r (argv[optind],
+            &last_update, &ds_count, &ds_names, &last_ds);
+    if (status != 0)
+        return (status);
+
+    for (i = 0; i < ds_count; i++)
+        printf(" %s", ds_names[i]);
+    printf ("\n\n");
+
+    printf ("%10lu:", last_update);
+    for (i = 0; i < ds_count; i++) {
+        printf(" %s", last_ds[i]);
+        free(last_ds[i]);
+        free(ds_names[i]);
+    }
+    printf("\n");
+
+    free(last_ds);
+    free(ds_names);
+
+    return (0);
+} /* int rrd_lastupdate */
+
+int rrd_lastupdate_r(const char *filename,
+        time_t *ret_last_update,
+        unsigned long *ret_ds_count,
+        char ***ret_ds_names,
+        char ***ret_last_ds)
 {
     unsigned long i = 0;
 {
     unsigned long i = 0;
-    char     *filename;
     rrd_t     rrd;
     rrd_file_t *rrd_file;
 
     rrd_t     rrd;
     rrd_file_t *rrd_file;
 
-    if (argc < 2) {
-        rrd_set_error("please specify an rrd");
-        goto err_out;
+    rrd_file = rrd_open(filename, &rrd, RRD_READONLY);
+    if (rrd_file == NULL) {
+        rrd_free(&rrd);
+        return (-1);
     }
     }
-    filename = argv[1];
 
 
-    rrd_file = rrd_open(filename, &rrd, RRD_READONLY);
-    if (rrd_file == NULL)
-        goto err_free;
-
-    *last_update = rrd.live_head->last_up;
-    *ds_cnt = rrd.stat_head->ds_cnt;
-    if (((*ds_namv) =
-         (char **) malloc(rrd.stat_head->ds_cnt * sizeof(char *))) == NULL) {
-        rrd_set_error("malloc fetch ds_namv array");
-        goto err_close;
+    *ret_last_update = rrd.live_head->last_up;
+    *ret_ds_count = rrd.stat_head->ds_cnt;
+    *ret_ds_names = (char **) malloc (rrd.stat_head->ds_cnt * sizeof(char *));
+    if (*ret_ds_names == NULL) {
+        rrd_set_error ("malloc fetch ret_ds_names array");
+        rrd_close (rrd_file);
+        rrd_free (&rrd);
+        return (-1);
     }
     }
+    memset (*ret_ds_names, 0, rrd.stat_head->ds_cnt * sizeof(char *));
 
 
-    if (((*last_ds) =
-         (char **) malloc(rrd.stat_head->ds_cnt * sizeof(char *))) == NULL) {
-        rrd_set_error("malloc fetch last_ds array");
-        goto err_free_ds_namv;
+    *ret_last_ds = (char **) malloc (rrd.stat_head->ds_cnt * sizeof(char *));
+    if (*ret_last_ds == NULL) {
+        rrd_set_error ("malloc fetch ret_last_ds array");
+        free (*ret_ds_names);
+        *ret_ds_names = NULL;
+        rrd_close (rrd_file);
+        rrd_free (&rrd);
+        return (-1);
     }
     }
+    memset (*ret_last_ds, 0, rrd.stat_head->ds_cnt * sizeof(char *));
 
     for (i = 0; i < rrd.stat_head->ds_cnt; i++) {
 
     for (i = 0; i < rrd.stat_head->ds_cnt; i++) {
-        (*ds_namv)[i] = sprintf_alloc("%s", rrd.ds_def[i].ds_nam);
-        (*last_ds)[i] = sprintf_alloc("%s", rrd.pdp_prep[i].last_ds);
+        (*ret_ds_names)[i] = sprintf_alloc("%s", rrd.ds_def[i].ds_nam);
+        (*ret_last_ds)[i] = sprintf_alloc("%s", rrd.pdp_prep[i].last_ds);
+
+        if (((*ret_ds_names)[i] == NULL) || ((*ret_last_ds)[i] == NULL))
+            break;
+    }
+
+    /* Check if all names and values could be copied and free everything if
+     * not. */
+    if (i < rrd.stat_head->ds_cnt) {
+        rrd_set_error ("sprintf_alloc failed");
+        for (i = 0; i < rrd.stat_head->ds_cnt; i++) {
+            if ((*ret_ds_names)[i] != NULL)
+            {
+                free ((*ret_ds_names)[i]);
+                (*ret_ds_names)[i] = NULL;
+            }
+            if ((*ret_last_ds)[i] != NULL)
+            {
+                free ((*ret_last_ds)[i]);
+                (*ret_last_ds)[i] = NULL;
+            }
+        }
+        free (*ret_ds_names);
+        *ret_ds_names = NULL;
+        free (*ret_last_ds);
+        *ret_last_ds = NULL;
+        rrd_close (rrd_file);
+        rrd_free (&rrd);
+        return (-1);
     }
 
     rrd_free(&rrd);
     rrd_close(rrd_file);
     return (0);
     }
 
     rrd_free(&rrd);
     rrd_close(rrd_file);
     return (0);
-
-  err_free_ds_namv:
-    free(*ds_namv);
-  err_close:
-    rrd_close(rrd_file);
-  err_free:
-    rrd_free(&rrd);
-  err_out:
-    return (-1);
-}
+} /* int rrd_lastupdate_r */
index 42ebfd1..983cfb6 100644 (file)
@@ -648,26 +648,7 @@ int HandleInputLine(
     else if (strcmp("last", argv[1]) == 0)
         printf("%ld\n", rrd_last(argc - 1, &argv[1]));
     else if (strcmp("lastupdate", argv[1]) == 0) {
     else if (strcmp("last", argv[1]) == 0)
         printf("%ld\n", rrd_last(argc - 1, &argv[1]));
     else if (strcmp("lastupdate", argv[1]) == 0) {
-        time_t    last_update;
-        char    **ds_namv;
-        char    **last_ds;
-        unsigned long ds_cnt, i;
-
-        if (rrd_lastupdate(argc - 1, &argv[1], &last_update,
-                           &ds_cnt, &ds_namv, &last_ds) == 0) {
-            for (i = 0; i < ds_cnt; i++)
-                printf(" %s", ds_namv[i]);
-            printf("\n\n");
-            printf("%10lu:", last_update);
-            for (i = 0; i < ds_cnt; i++) {
-                printf(" %s", last_ds[i]);
-                free(last_ds[i]);
-                free(ds_namv[i]);
-            }
-            printf("\n");
-            free(last_ds);
-            free(ds_namv);
-        }
+        rrd_lastupdate(argc - 1, &argv[1]);
     } else if (strcmp("first", argv[1]) == 0)
         printf("%ld\n", rrd_first(argc - 1, &argv[1]));
     else if (strcmp("update", argv[1]) == 0)
     } else if (strcmp("first", argv[1]) == 0)
         printf("%ld\n", rrd_first(argc - 1, &argv[1]));
     else if (strcmp("update", argv[1]) == 0)