backport FP_* fixes and revert FPCLASSIFY fix since there the FP_* values are defines.
[rrdtool.git] / src / rrd_daemon.c
index 2480958..4c3d7ed 100644 (file)
@@ -73,6 +73,7 @@
 
 #include "rrd.h"
 #include "rrd_client.h"
+#include "unused.h"
 
 #include <stdlib.h>
 
     syslog ((severity), __VA_ARGS__); \
   } while (0)
 
-#ifndef __GNUC__
-# define __attribute__(x) /**/
-#endif
-
 /*
  * Types
  */
@@ -155,12 +152,12 @@ typedef struct listen_socket_s listen_socket_t;
 struct command_s;
 typedef struct command_s command_t;
 /* note: guard against "unused" warnings in the handlers */
-#define DISPATCH_PROTO listen_socket_t *sock   __attribute__((unused)),\
-                       time_t now              __attribute__((unused)),\
-                       char  *buffer           __attribute__((unused)),\
-                       size_t buffer_size      __attribute__((unused))
+#define DISPATCH_PROTO listen_socket_t UNUSED(*sock),\
+                       time_t UNUSED(now),\
+                       char  UNUSED(*buffer),\
+                       size_t UNUSED(buffer_size)
 
-#define HANDLER_PROTO  command_t *cmd          __attribute__((unused)),\
+#define HANDLER_PROTO  command_t UNUSED(*cmd),\
                        DISPATCH_PROTO
 
 struct command_s {
@@ -303,23 +300,23 @@ static void sig_common (const char *sig) /* {{{ */
   pthread_cond_broadcast(&queue_cond);
 } /* }}} void sig_common */
 
-static void sig_int_handler (int s __attribute__((unused))) /* {{{ */
+static void sig_int_handler (int UNUSED(s)) /* {{{ */
 {
   sig_common("INT");
 } /* }}} void sig_int_handler */
 
-static void sig_term_handler (int s __attribute__((unused))) /* {{{ */
+static void sig_term_handler (int UNUSED(s)) /* {{{ */
 {
   sig_common("TERM");
 } /* }}} void sig_term_handler */
 
-static void sig_usr1_handler (int s __attribute__((unused))) /* {{{ */
+static void sig_usr1_handler (int UNUSED(s)) /* {{{ */
 {
   config_flush_at_shutdown = 1;
   sig_common("USR1");
 } /* }}} void sig_usr1_handler */
 
-static void sig_usr2_handler (int s __attribute__((unused))) /* {{{ */
+static void sig_usr2_handler (int UNUSED(s)) /* {{{ */
 {
   config_flush_at_shutdown = 0;
   sig_common("USR2");
@@ -844,7 +841,7 @@ static int flush_old_values (int max_age)
   return (0);
 } /* int flush_old_values */
 
-static void *flush_thread_main (void *args __attribute__((unused))) /* {{{ */
+static void *flush_thread_main (void UNUSED(*args)) /* {{{ */
 {
   struct timeval now;
   struct timespec next_flush;
@@ -897,7 +894,7 @@ static void *flush_thread_main (void *args __attribute__((unused))) /* {{{ */
   return NULL;
 } /* void *flush_thread_main */
 
-static void *queue_thread_main (void *args __attribute__((unused))) /* {{{ */
+static void *queue_thread_main (void UNUSED(*args)) /* {{{ */
 {
   pthread_mutex_lock (&cache_lock);
 
@@ -1479,13 +1476,11 @@ static int handle_request_update (HANDLER_PROTO) /* {{{ */
 
 static int handle_request_fetch (HANDLER_PROTO) /* {{{ */
 {
-  char *file;
+  char *file, file_tmp[PATH_MAX];
   char *cf;
 
   char *start_str;
   char *end_str;
-  rrd_time_value_t start_tv;
-  rrd_time_value_t end_tv;
   time_t start_tm;
   time_t end_tm;
 
@@ -1535,43 +1530,63 @@ static int handle_request_fetch (HANDLER_PROTO) /* {{{ */
   if (status != 0)
     return (syntax_error(sock,cmd));
 
+  get_abs_path(&file, file_tmp);
+  if (!check_file_access(file, sock)) return 0;
+
   status = flush_file (file);
   if ((status != 0) && (status != ENOENT))
     return (send_response (sock, RESP_ERR,
           "flush_file (%s) failed with status %i.\n", file, status));
 
+  t = time (NULL); /* "now" */
+
   /* Parse start time */
   if (start_str != NULL)
   {
-    const char *errmsg;
+    char *endptr;
+    long value;
 
-    errmsg = rrd_parsetime (start_str, &start_tv);
-    if (errmsg != NULL)
+    endptr = NULL;
+    errno = 0;
+    value = strtol (start_str, &endptr, /* base = */ 0);
+    if ((endptr == start_str) || (errno != 0))
       return (send_response(sock, RESP_ERR,
-            "Cannot parse start time `%s': %s\n", start_str, errmsg));
+            "Cannot parse start time `%s': Only simple integers are allowed.\n",
+            start_str));
+
+    if (value > 0)
+      start_tm = (time_t) value;
+    else
+      start_tm = (time_t) (t + value);
   }
   else
-    rrd_parsetime ("-86400", &start_tv);
+  {
+    start_tm = t - 86400;
+  }
 
   /* Parse end time */
   if (end_str != NULL)
   {
-    const char *errmsg;
+    char *endptr;
+    long value;
 
-    errmsg = rrd_parsetime (end_str, &end_tv);
-    if (errmsg != NULL)
+    endptr = NULL;
+    errno = 0;
+    value = strtol (end_str, &endptr, /* base = */ 0);
+    if ((endptr == end_str) || (errno != 0))
       return (send_response(sock, RESP_ERR,
-            "Cannot parse end time `%s': %s\n", end_str, errmsg));
+            "Cannot parse end time `%s': Only simple integers are allowed.\n",
+            end_str));
+
+    if (value > 0)
+      end_tm = (time_t) value;
+    else
+      end_tm = (time_t) (t + value);
   }
   else
-    rrd_parsetime ("now", &end_tv);
-
-  start_tm = 0;
-  end_tm = 0;
-  status = rrd_proc_start_end (&start_tv, &end_tv, &start_tm, &end_tm);
-  if (status != 0)
-    return (send_response(sock, RESP_ERR,
-          "rrd_proc_start_end failed: %s\n", rrd_get_error ()));
+  {
+    end_tm = t;
+  }
 
   step = -1;
   ds_cnt = 0;
@@ -1616,7 +1631,9 @@ static int handle_request_fetch (HANDLER_PROTO) /* {{{ */
       if (i > 0)
         SSTRCAT (linebuf, " ", linebuf_fill);
       SSTRCAT (linebuf, ds_namv[i], linebuf_fill);
+      rrd_freemem(ds_namv[i]);
     }
+    rrd_freemem(ds_namv);
     add_response_info (sock, "DSName: %s\n", linebuf);
   }
 
@@ -1642,6 +1659,7 @@ static int handle_request_fetch (HANDLER_PROTO) /* {{{ */
 
     add_response_info (sock, "%10lu:%s\n", (unsigned long) t, linebuf);
   } /* for (t) */
+  rrd_freemem(data);
 
   return (send_response (sock, RESP_OK, "Success\n"));
 #undef SSTRCAT
@@ -2296,6 +2314,10 @@ static void journal_init(void) /* {{{ */
   }
 
   dir = opendir(journal_dir);
+  if (!dir) {
+    RRDD_LOG(LOG_CRIT, "journal_init: opendir(%s) failed\n", journal_dir);
+    return;
+  }
   while ((dent = readdir(dir)) != NULL)
   {
     /* looks like a journal file? */
@@ -2707,7 +2729,7 @@ static int close_listen_sockets (void) /* {{{ */
   return (0);
 } /* }}} int close_listen_sockets */
 
-static void *listen_thread_main (void *args __attribute__((unused))) /* {{{ */
+static void *listen_thread_main (void UNUSED(*args)) /* {{{ */
 {
   struct pollfd *pollfds;
   int pollfds_num;
@@ -3247,7 +3269,9 @@ static int read_options (int argc, char **argv) /* {{{ */
 
       case 'j':
       {
-        const char *dir = journal_dir = strdup(optarg);
+        char journal_dir_actual[PATH_MAX];
+        const char *dir;
+        dir = journal_dir = strdup(realpath((const char *)optarg, journal_dir_actual));
 
         status = rrd_mkdir_p(dir, 0777);
         if (status != 0)