Merged `branches/log-mode' to `trunk'
authorocto <octo>
Fri, 14 Apr 2006 10:53:44 +0000 (10:53 +0000)
committerocto <octo>
Fri, 14 Apr 2006 10:53:44 +0000 (10:53 +0000)
1  2 
AUTHORS
src/collectd.c
src/collectd.conf.pod
src/collectd.h
src/collectd.pod
src/common.c
src/common.h
src/configfile.c
src/network.c
src/plugin.c

diff --cc AUTHORS
Simple merge
diff --cc src/collectd.c
Simple merge
Simple merge
diff --cc src/collectd.h
  #define MODE_SERVER 0x01
  #define MODE_CLIENT 0x02
  #define MODE_LOCAL  0x04
+ #define MODE_LOG    0x08
  
 +#ifndef COLLECTD_STEP
 +#  define COLLECTD_STEP "10"
 +#endif
 +
 +#ifndef COLLECTD_HEARTBEAT
 +#  define COLLECTD_HEARTBEAT "25"
 +#endif
 +
 +#ifndef COLLECTD_ROWS
 +#  define COLLECTD_ROWS "1200"
 +#endif
 +
 +#ifndef COLLECTD_XFF
 +#  define COLLECTD_XFF 0.1
 +#endif
 +
  extern time_t curtime;
  
  #ifdef HAVE_LIBRRD
Simple merge
diff --cc src/common.c
  #include "common.h"
  #include "utils_debug.h"
  
 +#ifdef HAVE_MATH_H
 +#  include <math.h>
 +#endif
 +
+ extern int operating_mode;
  #ifdef HAVE_LIBKSTAT
  extern kstat_ctl_t *kc;
  #endif
@@@ -210,31 -204,7 +233,30 @@@ int escape_slashes (char *buf, int buf_
        return (0);
  }
  
- #ifdef HAVE_LIBRRD
- int check_create_dir (const char *file_orig)
 +int timeval_sub_timespec (struct timeval *tv0, struct timeval *tv1, struct timespec *ret)
 +{
 +      if ((tv0 == NULL) || (tv1 == NULL) || (ret == NULL))
 +              return (-2);
 +
 +      if ((tv0->tv_sec < tv1->tv_sec)
 +                      || ((tv0->tv_sec == tv1->tv_sec) && (tv0->tv_usec < tv1->tv_usec)))
 +              return (-1);
 +
 +      ret->tv_sec  = tv0->tv_sec - tv1->tv_sec;
 +      ret->tv_nsec = 1000 * ((long) (tv0->tv_usec - tv1->tv_usec));
 +
 +      if (ret->tv_nsec < 0)
 +      {
 +              assert (ret->tv_sec > 0);
 +
 +              ret->tv_nsec += 1000000000;
 +              ret->tv_sec  -= 1;
 +      }
 +
 +      return (0);
 +}
 +
+ static int check_create_dir (const char *file_orig)
  {
        struct stat statbuf;
  
        return (0);
  }
  
- int rrd_create_file (char *filename, char **ds_def, int ds_num)
 +/* * * * *
 + * Magic *
 + * * * * */
 +int rra_get (char ***ret)
 +{
 +      static char **rra_def = NULL;
 +      static int rra_num = 0;
 +
 +      int rra_max = rra_timespans_num * rra_types_num;
 +
 +      int step;
 +      int rows;
 +      int span;
 +
 +      int cdp_num;
 +      int cdp_len;
 +      int i, j;
 +
 +      char buffer[64];
 +
 +      if ((rra_num != 0) && (rra_def != NULL))
 +      {
 +              *ret = rra_def;
 +              return (rra_num);
 +      }
 +
 +      if ((rra_def = (char **) malloc ((rra_max + 1) * sizeof (char *))) == NULL)
 +              return (-1);
 +      memset (rra_def, '\0', (rra_max + 1) * sizeof (char *));
 +
 +      step = atoi (COLLECTD_STEP);
 +      rows = atoi (COLLECTD_ROWS);
 +
 +      if ((step <= 0) || (rows <= 0))
 +      {
 +              *ret = NULL;
 +              return (-1);
 +      }
 +
 +      cdp_len = 0;
 +      for (i = 0; i < rra_timespans_num; i++)
 +      {
 +              span = rra_timespans[i];
 +
 +              if ((span / step) < rows)
 +                      continue;
 +
 +              if (cdp_len == 0)
 +                      cdp_len = 1;
 +              else
 +                      cdp_len = (int) floor (((double) span) / ((double) (rows * step)));
 +
 +              cdp_num = (int) ceil (((double) span) / ((double) (cdp_len * step)));
 +
 +              for (j = 0; j < rra_types_num; j++)
 +              {
 +                      if (rra_num >= rra_max)
 +                              break;
 +
 +                      if (snprintf (buffer, sizeof(buffer), "RRA:%s:%3.1f:%u:%u",
 +                                              rra_types[j], COLLECTD_XFF,
 +                                              cdp_len, cdp_num) >= sizeof (buffer))
 +                      {
 +                              syslog (LOG_ERR, "rra_get: Buffer would have been truncated.");
 +                              continue;
 +                      }
 +
 +                      rra_def[rra_num++] = sstrdup (buffer);
 +              }
 +      }
 +
 +#if COLLECT_DEBUG
 +      DBG ("rra_num = %i", rra_num);
 +      for (i = 0; i < rra_num; i++)
 +              DBG ("  %s", rra_def[i]);
 +#endif
 +
 +      *ret = rra_def;
 +      return (rra_num);
 +}
 +
+ static int log_create_file (char *filename, char **ds_def, int ds_num)
+ {
+       FILE *log;
+       int i;
+       log = fopen (filename, "w");
+       if (log == NULL)
+       {
+               syslog (LOG_WARNING, "Failed to create %s: %s", filename,
+                               strerror(errno));
+               return (-1);
+       }
+       fprintf (log, "epoch");
+       for (i = 0; i < ds_num; i++)
+       {
+               char *name;
+               char *tmp;
+               name = strchr (ds_def[i], ':');
+               if (name == NULL)
+               {
+                       syslog (LOG_WARNING, "Invalid DS definition '%s' for %s",
+                                       ds_def[i], filename);
+                       fclose(log);
+                       remove(filename);
+                       return (-1);
+               }
+               name += 1;
+               tmp = strchr (name, ':');
+               if (tmp == NULL)
+               {
+                       syslog (LOG_WARNING, "Invalid DS definition '%s' for %s",
+                                       ds_def[i], filename);
+                       fclose(log);
+                       remove(filename);
+                       return (-1);
+               }
+               /* The `%.*s' is needed because there is no null-byte behind
+                * the name. */
+               fprintf(log, ",%.*s", (tmp - name), name);
+       }
+       fprintf(log, "\n");
+       fclose(log);
+       return 0;
+ }
+ static int log_update_file (char *host, char *file, char *values,
+               char **ds_def, int ds_num)
+ {
+       char *tmp;
+       FILE *fp;
+       struct stat statbuf;
+       char full_file[1024];
+       /* Cook the values a bit: Substitute colons with commas */
+       strsubstitute (values, ':', ',');
+       /* host == NULL => local mode */
+       if (host != NULL)
+       {
+               if (snprintf (full_file, 1024, "%s/%s", host, file) >= 1024)
+                       return (-1);
+       }
+       else
+       {
+               if (snprintf (full_file, 1024, "%s", file) >= 1024)
+                       return (-1);
+       }
+       strncpy (full_file, file, 1024);
+       tmp = full_file + strlen (full_file) - 4;
+       assert (tmp > 0);
+       /* Change the filename for logfiles. */
+       if (strncmp (tmp, ".rrd", 4) == 0)
+       {
+               time_t now;
+               struct tm *tm;
+               /* TODO: Find a way to minimize the calls to `localtime', since
+                * they are pretty expensive.. */
+               now = time (NULL);
+               tm = localtime (&now);
+               strftime (tmp, 1024 - (tmp - full_file), "-%Y-%m-%d", tm);
+               /* `localtime(3)' returns a pointer to static data,
+                * therefore the pointer may not be free'd. */
+       }
+       else
+               DBG ("The filename ends with `%s' which is unexpected.", tmp);
+       if (stat (full_file, &statbuf) == -1)
+       {
+               if (errno == ENOENT)
+               {
+                       if (log_create_file (full_file, ds_def, ds_num))
+                               return (-1);
+               }
+               else
+               {
+                       syslog (LOG_ERR, "stat %s: %s", full_file, strerror (errno));
+                       return (-1);
+               }
+       }
+       else if (!S_ISREG (statbuf.st_mode))
+       {
+               syslog (LOG_ERR, "stat %s: Not a regular file!", full_file);
+               return (-1);
+       }
+       fp = fopen (full_file, "a");
+       if (fp == NULL)
+       {
+               syslog (LOG_WARNING, "Failed to append to %s: %s", full_file,
+                               strerror(errno));
+               return (-1);
+       }
+       fprintf(fp, "%s\n", values);
+       fclose(fp);
+       return (0);
+ } /* int log_update_file */
+ #if HAVE_LIBRRD
+ static int rrd_create_file (char *filename, char **ds_def, int ds_num)
  {
        char **argv;
        int argc;
diff --cc src/common.h
@@@ -103,11 -103,8 +103,11 @@@ int strjoin (char *dst, size_t dst_len
   */
  int escape_slashes (char *buf, int buf_len);
  
- int rrd_update_file (char *host, char *file, char *values, char **ds_def,
-               int ds_num);
 +/* FIXME: `timeval_sub_timespec' needs a description */
 +int timeval_sub_timespec (struct timeval *tv0, struct timeval *tv1, struct timespec *ret);
 +
+ int rrd_update_file (char *host, char *file, char *values,
+               char **ds_def, int ds_num);
  
  #ifdef HAVE_LIBKSTAT
  int get_kstat (kstat_t **ksp_ptr, char *module, int instance, char *name);
Simple merge
diff --cc src/network.c
Simple merge
diff --cc src/plugin.c
Simple merge