Code

Merge pull request #1220 from rubenk/set-package-bugreport-and-homepage
authorRuben Kerkhof <ruben@tilaa.nl>
Sat, 28 Nov 2015 12:15:44 +0000 (13:15 +0100)
committerRuben Kerkhof <ruben@tilaa.nl>
Sat, 28 Nov 2015 12:15:44 +0000 (13:15 +0100)
Set bugreport url and homepage url

58 files changed:
.travis.yml
Makefile.am
bindings/perl/lib/Collectd/Unixsock.pm
configure.ac
contrib/systemd.collectd.service
src/Makefile.am
src/apache.c
src/apcups.c
src/ascent.c
src/bind.c
src/collectd-exec.pod
src/collectd-tg.c
src/collectd.conf.in
src/collectd.conf.pod
src/curl.c
src/curl_json.c
src/curl_xml.c
src/daemon/Makefile.am
src/daemon/collectd.c
src/daemon/common.c
src/daemon/common_test.c
src/daemon/meta_data.c
src/daemon/meta_data_test.c
src/daemon/plugin.c
src/daemon/utils_avltree.c
src/daemon/utils_avltree_test.c
src/daemon/utils_ignorelist.c [new file with mode: 0644]
src/daemon/utils_ignorelist.h [new file with mode: 0644]
src/daemon/utils_subst_test.c
src/daemon/utils_time.h
src/daemon/utils_time_test.c [new file with mode: 0644]
src/dbi.c
src/dns.c
src/exec.c [changed mode: 0644->0755]
src/libcollectdclient/Makefile.am
src/liboconfig/scanner.l
src/log_logstash.c
src/memory.c
src/mqtt.c
src/nginx.c
src/pf.c
src/processes.c
src/python.c
src/snmp.c
src/statsd.c
src/table.c
src/testing.h
src/types.db
src/utils_ignorelist.c [deleted file]
src/utils_ignorelist.h [deleted file]
src/utils_latency_test.c
src/utils_mount.c
src/utils_mount_test.c
src/utils_vl_lookup.c
src/virt.c
src/write_http.c
src/write_redis.c
src/zfs_arc.c

index 09adb4d9a5e79b8c404365f9c0dc045c001e5c73..435669bcb691775ff350f09d43cd747c073165c2 100644 (file)
@@ -1,25 +1,55 @@
-sudo: false
+sudo: required
+dist: trusty
 compiler:
   - gcc
   - clang
-addons:
-  apt:
-    packages:
-      - iptables-dev
-      - libcap-dev
-      - libdbi-dev
-      - libhiredis-dev
-      - libnfnetlink-dev
-      - libnotify-dev
-      - libpcap-dev
-      - libperl-dev
-      - libprotobuf-c0-dev
-      - librrd-dev
-      - libsnmp-dev
-      - libudev-dev
-      - libvarnishapi-dev
-      - libyajl-dev
-      - linux-libc-dev
-      - protobuf-c-compiler
 language: c
+before_install:
+  - sudo apt-get update -qq
+  - sudo apt-get install -qq --no-install-recommends
+      libatasmart-dev
+      libcap-dev
+      libcurl4-gnutls-dev
+      libdbi0-dev
+      libesmtp-dev
+      libganglia1-dev
+      libgcrypt11-dev
+      libglib2.0-dev
+      libhiredis-dev
+      libi2c-dev
+      libldap2-dev
+      libltdl-dev
+      liblvm2-dev
+      libmemcached-dev
+      libmnl-dev
+      libmodbus-dev
+      libmosquitto0-dev
+      libmysqlclient-dev
+      libnotify-dev
+      libopenipmi-dev
+      liboping-dev
+      libow-dev
+      libpcap-dev
+      libperl-dev
+      libpq-dev
+      libprotobuf-c0-dev
+      librabbitmq-dev
+      librdkafka-dev
+      librrd-dev
+      libsensors4-dev
+      libsigrok-dev
+      libsnmp-dev
+      libstatgrab-dev
+      libtokyocabinet-dev
+      libtokyotyrant-dev
+      libudev-dev
+      libupsclient-dev
+      libvarnish-dev
+      libvirt-dev
+      libxml2-dev
+      libyajl-dev
+      linux-libc-dev
+      perl
+      protobuf-c-compiler
+      python-dev
 script: sh build.sh && ./configure && make distcheck
index 35f24cb1a8b5258e1f7d926bf25d0643cf5ba56a..b79ea1cabfbdc562cfcd46983771b1351d6a5d23 100644 (file)
@@ -1,6 +1,12 @@
 ACLOCAL_AMFLAGS = -I libltdl/m4
 
-SUBDIRS = libltdl src bindings .
+SUBDIRS =
+
+if BUILD_INCLUDED_LTDL
+SUBDIRS += libltdl
+endif
+
+SUBDIRS += src bindings .
 
 AM_CPPFLAGS = $(LTDLINCL)
 
index 69c755b6a92996cd192b9845ea87c866dd51b741..d927d13e4bc486b48110c5d786ad537d763f8de8 100644 (file)
@@ -262,10 +262,11 @@ sub getthreshold # {{{
     $self->_socket_chat($msg, sub {
             local $_ = shift;
             my $ret = shift;
-                   /^\s*([^:]+):\s*(.*)/ and do {
-                           $1 =~ s/\s*$//;
-                           $ret->{$1} = $2;
-                   };
+            my ( $key, $val );
+            ( $key, $val ) = /^\s*([^:]+):\s*(.*)/ and do {
+                  $key =~ s/\s*$//;
+                  $ret->{$key} = $val;
+            };
         }, $ret
     );
        return $ret;
index 70c29b27a51f9bc3bbf6aa4551e09242c731674c..bb400dea9c50cb735118c4a8df1f676a8c467773 100644 (file)
@@ -8,6 +8,11 @@ AC_CONFIG_SRCDIR(src/)
 AC_CONFIG_HEADERS(src/config.h)
 AC_CONFIG_AUX_DIR([libltdl/config])
 
+dnl older automake's default of ARFLAGS=cru is noisy on newer binutils;
+dnl we don't really need the 'u' even in older toolchains.  Then there is
+dnl older libtool, which spelled it AR_FLAGS
+m4_divert_text([DEFAULTS], [: "${ARFLAGS=cr} ${AR_FLAGS=cr}"])
+
 m4_ifdef([LT_PACKAGE_VERSION],
        # libtool >= 2.2
        [
@@ -28,6 +33,8 @@ m4_ifdef([LT_PACKAGE_VERSION],
        ]
 )
 
+AM_CONDITIONAL([BUILD_INCLUDED_LTDL], [test "x$LTDLDEPS" != "x"])
+
 AM_INIT_AUTOMAKE([tar-pax dist-bzip2 foreign])
 m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES([yes])])
 AC_LANG(C)
@@ -636,6 +643,9 @@ AC_CHECK_HEADERS(net/pfvar.h,
 #if HAVE_NET_IF_H
 # include <net/if.h>
 #endif
+#if HAVE_NETINET_IN_H
+# include <netinet/in.h>
+#endif
 ])
 
 # For the multimeter plugin
@@ -1248,6 +1258,8 @@ have_getvfsstat="no"
 AC_CHECK_FUNCS(getvfsstat, [have_getvfsstat="yes"])
 have_listmntent="no"
 AC_CHECK_FUNCS(listmntent, [have_listmntent="yes"])
+have_getmntent_r="no"
+AC_CHECK_FUNCS(getmntent_r, [have_getmntent_r="yes"])
 
 have_getmntent="no"
 AC_CHECK_FUNCS(getmntent, [have_getmntent="c"])
@@ -1919,30 +1931,33 @@ AC_ARG_WITH(libganglia, [AS_HELP_STRING([--with-libganglia@<:@=PREFIX@:>@], [Pat
         GANGLIA_LDFLAGS="-L$withval/lib"
         with_libganglia="yes"
  else
-        with_libganglia_config="ganglia-config"
         with_libganglia="$withval"
  fi; fi; fi
 ],
 [
- with_libganglia_config="ganglia-config"
  with_libganglia="yes"
 ])
 
-if test "x$with_libganglia" = "xyes" && test "x$with_libganglia_config" != "x"
+if test "x$with_libganglia" = "xyes"
 then
-       if test "x$GANGLIA_CPPFLAGS" = "x"
+       if test "x$with_libganglia_config" != "x"
        then
-               GANGLIA_CPPFLAGS=`"$with_libganglia_config" --cflags 2>/dev/null`
-       fi
+               if test "x$GANGLIA_CPPFLAGS" = "x"
+               then
+                       GANGLIA_CPPFLAGS=`"$with_libganglia_config" --cflags 2>/dev/null`
+               fi
 
-       if test "x$GANGLIA_LDFLAGS" = "x"
-       then
-               GANGLIA_LDFLAGS=`"$with_libganglia_config" --ldflags 2>/dev/null`
-       fi
+               if test "x$GANGLIA_LDFLAGS" = "x"
+               then
+                       GANGLIA_LDFLAGS=`"$with_libganglia_config" --ldflags 2>/dev/null`
+               fi
 
-       if test "x$GANGLIA_LIBS" = "x"
-       then
-               GANGLIA_LIBS=`"$with_libganglia_config" --libs 2>/dev/null`
+               if test "x$GANGLIA_LIBS" = "x"
+               then
+                       GANGLIA_LIBS=`"$with_libganglia_config" --libs 2>/dev/null`
+               fi
+       else
+               GANGLIA_LIBS="-lganglia"
        fi
 fi
 
@@ -2732,7 +2747,7 @@ AC_ARG_WITH(libmysql, [AS_HELP_STRING([--with-libmysql@<:@=PREFIX@:>@], [Path to
 ])
 if test "x$with_libmysql" = "xyes"
 then
-       with_mysql_cflags=`$with_mysql_config --cflags 2>/dev/null`
+       with_mysql_cflags=`$with_mysql_config --include 2>/dev/null`
        mysql_config_status=$?
 
        if test $mysql_config_status -ne 0
@@ -2768,15 +2783,17 @@ then
        then
                with_libmysql="no ($with_mysql_config failed)"
        else
-               AC_CHECK_LIB(mysqlclient, mysql_init,
-                [with_libmysql="yes"],
-                [with_libmysql="no (symbol 'mysql_init' not found)"],
-                [$with_mysql_libs])
-
-               AC_CHECK_LIB(mysqlclient, mysql_get_server_version,
+               SAVE_CPPFLAGS="$CPPFLAGS"
+               CPPFLAGS="$CPPFLAGS $with_mysql_cflags"
+               SAVE_LIBS="$LIBS"
+               LIBS="$with_mysql_libs"
+               AC_SEARCH_LIBS([mysql_get_server_version],
+                [],
                 [with_libmysql="yes"],
                 [with_libmysql="no (symbol 'mysql_get_server_version' not found)"],
-                [$with_mysql_libs])
+                [])
+               CPPFLAGS="$SAVE_CPPFLAGS"
+               LIBS="$SAVE_LIBS"
        fi
 fi
 if test "x$with_libmysql" = "xyes"
@@ -3295,11 +3312,6 @@ then
                         [with_libpcap="no (pcap.h not found)"])
 fi
 if test "x$with_libpcap" = "xyes"
-then
-       AC_CHECK_HEADERS(pcap-bpf.h,,
-                        [with_libpcap="no (pcap-bpf.h not found)"])
-fi
-if test "x$with_libpcap" = "xyes"
 then
        AC_CACHE_CHECK([whether libpcap has PCAP_ERROR_IFACE_NOT_UP],
                       [c_cv_libpcap_have_pcap_error_iface_not_up],
@@ -5245,6 +5257,7 @@ collectd features:])
 AC_COLLECTD([debug],     [enable],  [feature], [debugging])
 AC_COLLECTD([daemon],    [disable], [feature], [daemon mode])
 AC_COLLECTD([getifaddrs],[enable],  [feature], [getifaddrs under Linux])
+AC_COLLECTD([werror],    [disable], [feature], [building with -Werror])
 
 dependency_warning="no"
 dependency_error="no"
@@ -5508,6 +5521,11 @@ then
        plugin_df="yes"
 fi
 
+if test "x$c_cv_have_getmntent_r" = "xyes"
+then
+       plugin_df="yes"
+fi
+
 # Df plugin: Check if we have either `statfs' or `statvfs' second.
 if test "x$plugin_df" = "xyes"
 then
@@ -5914,6 +5932,13 @@ AC_SUBST(LCC_VERSION_STRING)
 
 AC_CONFIG_FILES(src/libcollectdclient/collectd/lcc_features.h)
 
+AM_CFLAGS="-Wall"
+if test "x$enable_werror" != "xno"
+then
+        AM_CFLAGS="$AM_CFLAGS -Werror"
+fi
+AC_SUBST([AM_CFLAGS])
+
 AC_CONFIG_FILES([Makefile src/Makefile src/daemon/Makefile src/collectd.conf src/libcollectdclient/Makefile src/libcollectdclient/libcollectdclient.pc src/liboconfig/Makefile bindings/Makefile bindings/java/Makefile])
 AC_OUTPUT
 
@@ -5944,6 +5969,17 @@ fi
 cat <<EOF;
 
 Configuration:
+  Build:
+    Platform  . . . . . . $ac_system
+    CC  . . . . . . . . . $CC
+    CFLAGS  . . . . . . . $AM_CFLAGS $CFLAGS
+    CPP . . . . . . . . . $CPP
+    CPPFLAGS  . . . . . . $CPPFLAGS
+    LD  . . . . . . . . . $LD
+    LDFLAGS . . . . . . . $LDFLAGS
+    YACC  . . . . . . . . $YACC
+    YFLAGS  . . . . . . . $YFLAGS
+
   Libraries:
     intel mic . . . . . . $with_mic
     libaquaero5 . . . . . $with_libaquaero5
index 96df8a576a694670f1af076e344b0be7f1c45767..0e758e40ef85a9fb6aba1c921da5a0f27c89a41d 100644 (file)
@@ -7,19 +7,24 @@ Requires=local-fs.target network.target
 ExecStart=/usr/sbin/collectd
 EnvironmentFile=-/etc/sysconfig/collectd
 EnvironmentFile=-/etc/default/collectd
+ProtectSystem=full
+ProtectHome=true
+
+# drop all capabilities:
+CapabilityBoundingSet=
+# use this instead if you use the dns or ping plugin
+#CapabilityBoundingSet=CAP_NET_RAW
+# turn this on if you use the iptables next to the dns or ping plugin
+#CapabilityBoundingSet=CAP_NET_RAW CAP_NET_ADMIN
+
+NoNewPrivileges=true
 
 # Tell systemd it will receive a notification from collectd over it's control
 # socket once the daemon is ready. See systemd.service(5) for more details.
 Type=notify
-NotifyAccess=main
 
 # Restart the collectd daemon after a 10 seconds delay, in case it crashes.
-Restart=always
-RestartSec=10
-
-# Send all console messages to syslog.
-StandardOutput=syslog
-StandardError=syslog
+Restart=on-failure
 
 [Install]
 WantedBy=multi-user.target
index 9493c246239e01aff76354e2bd9e5ffb8039452d..199adcfcafee10a08c8389689eadb7f92395934f 100644 (file)
@@ -6,10 +6,6 @@ SUBDIRS += daemon
 
 PLUGIN_LDFLAGS = -module -avoid-version -export-symbols-regex '\<module_register\>'
 
-if COMPILER_IS_GCC
-AM_CFLAGS = -Wall -Werror
-endif
-
 AM_CPPFLAGS = -I$(srcdir)/daemon
 AM_CPPFLAGS += -DPREFIX='"${prefix}"'
 AM_CPPFLAGS += -DCONFIGFILE='"${sysconfdir}/${PACKAGE_NAME}.conf"'
@@ -41,6 +37,9 @@ check_PROGRAMS += test_utils_vl_lookup
 TESTS += test_utils_vl_lookup
 test_utils_vl_lookup_SOURCES = utils_vl_lookup_test.c testing.h
 test_utils_vl_lookup_LDADD = liblookup.la daemon/libcommon.la daemon/libplugin_mock.la
+if BUILD_WITH_LIBKSTAT
+test_utils_vl_lookup_LDADD += -lkstat
+endif
 
 noinst_LTLIBRARIES += libmount.la
 libmount_la_SOURCES = utils_mount.c utils_mount.h
@@ -48,7 +47,9 @@ check_PROGRAMS += test_utils_mount
 TESTS += test_utils_mount
 test_utils_mount_SOURCES = utils_mount_test.c testing.h
 test_utils_mount_LDADD = libmount.la daemon/libcommon.la daemon/libplugin_mock.la
-
+if BUILD_WITH_LIBKSTAT
+test_utils_mount_LDADD += -lkstat
+endif
 
 sbin_PROGRAMS = collectdmon
 bin_PROGRAMS = collectd-nagios collectdctl collectd-tg
@@ -210,8 +211,7 @@ endif
 
 if BUILD_PLUGIN_CGROUPS
 pkglib_LTLIBRARIES += cgroups.la
-cgroups_la_SOURCES = cgroups.c \
-                    utils_ignorelist.c utils_ignorelist.h
+cgroups_la_SOURCES = cgroups.c
 cgroups_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 cgroups_la_LIBADD = libmount.la
 endif
@@ -310,16 +310,14 @@ endif
 
 if BUILD_PLUGIN_DF
 pkglib_LTLIBRARIES += df.la
-df_la_SOURCES = df.c \
-               utils_ignorelist.c utils_ignorelist.h
+df_la_SOURCES = df.c
 df_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 df_la_LIBADD = libmount.la
 endif
 
 if BUILD_PLUGIN_DISK
 pkglib_LTLIBRARIES += disk.la
-disk_la_SOURCES = disk.c \
-                 utils_ignorelist.c utils_ignorelist.h
+disk_la_SOURCES = disk.c
 disk_la_CFLAGS = $(AM_CFLAGS)
 disk_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 disk_la_LIBADD =
@@ -422,8 +420,7 @@ endif
 
 if BUILD_PLUGIN_INTERFACE
 pkglib_LTLIBRARIES += interface.la
-interface_la_SOURCES = interface.c \
-                      utils_ignorelist.c utils_ignorelist.h
+interface_la_SOURCES = interface.c
 interface_la_CFLAGS = $(AM_CFLAGS)
 interface_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 interface_la_LIBADD =
@@ -460,8 +457,7 @@ endif
 
 if BUILD_PLUGIN_IPMI
 pkglib_LTLIBRARIES += ipmi.la
-ipmi_la_SOURCES = ipmi.c \
-                 utils_ignorelist.c utils_ignorelist.h
+ipmi_la_SOURCES = ipmi.c
 ipmi_la_CFLAGS = $(AM_CFLAGS) $(BUILD_WITH_OPENIPMI_CFLAGS)
 ipmi_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 ipmi_la_LIBADD = $(BUILD_WITH_OPENIPMI_LIBS)
@@ -480,8 +476,7 @@ endif
 
 if BUILD_PLUGIN_IRQ
 pkglib_LTLIBRARIES += irq.la
-irq_la_SOURCES = irq.c \
-                utils_ignorelist.c utils_ignorelist.h
+irq_la_SOURCES = irq.c
 irq_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 endif
 
@@ -540,8 +535,7 @@ endif
 
 if BUILD_PLUGIN_MADWIFI
 pkglib_LTLIBRARIES += madwifi.la
-madwifi_la_SOURCES = madwifi.c madwifi.h \
-                    utils_ignorelist.c utils_ignorelist.h
+madwifi_la_SOURCES = madwifi.c madwifi.h
 madwifi_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 endif
 
@@ -587,8 +581,7 @@ endif
 
 if BUILD_PLUGIN_MD
 pkglib_LTLIBRARIES += md.la
-md_la_SOURCES = md.c \
-               utils_ignorelist.c utils_ignorelist.h
+md_la_SOURCES = md.c
 md_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 endif
 
@@ -633,8 +626,7 @@ endif
 
 if BUILD_PLUGIN_MIC
 pkglib_LTLIBRARIES += mic.la
-mic_la_SOURCES = mic.c \
-                utils_ignorelist.c utils_ignorelist.h
+mic_la_SOURCES = mic.c
 mic_la_LDFLAGS = $(PLUGIN_LDFLAGS) $(BUILD_WITH_MIC_LIBPATH)
 mic_la_CFLAGS = $(AM_CFLAGS) $(BUILD_WITH_MIC_CPPFLAGS)
 mic_la_LIBADD = $(BUILD_WITH_MIC_LDADD)
@@ -676,8 +668,7 @@ endif
 
 if BUILD_PLUGIN_NETAPP
 pkglib_LTLIBRARIES += netapp.la
-netapp_la_SOURCES = netapp.c \
-                   utils_ignorelist.c utils_ignorelist.h
+netapp_la_SOURCES = netapp.c
 netapp_la_CPPFLAGS = $(AM_CPPFLAGS) $(LIBNETAPP_CPPFLAGS)
 netapp_la_LDFLAGS = $(PLUGIN_LDFLAGS) $(LIBNETAPP_LDFLAGS)
 netapp_la_LIBADD = $(LIBNETAPP_LIBS)
@@ -783,8 +774,7 @@ endif
 
 if BUILD_PLUGIN_ONEWIRE
 pkglib_LTLIBRARIES += onewire.la
-onewire_la_SOURCES = onewire.c \
-                    utils_ignorelist.c utils_ignorelist.h
+onewire_la_SOURCES = onewire.c
 onewire_la_CFLAGS = $(AM_CFLAGS)
 onewire_la_CPPFLAGS = $(AM_CPPFLAGS) $(BUILD_WITH_LIBOWCAPI_CPPFLAGS)
 onewire_la_LIBADD = $(BUILD_WITH_LIBOWCAPI_LIBS)
@@ -897,8 +887,7 @@ endif
 
 if BUILD_PLUGIN_PROTOCOLS
 pkglib_LTLIBRARIES += protocols.la
-protocols_la_SOURCES = protocols.c \
-                      utils_ignorelist.c utils_ignorelist.h
+protocols_la_SOURCES = protocols.c
 protocols_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 endif
 
@@ -936,8 +925,7 @@ endif
 
 if BUILD_PLUGIN_SENSORS
 pkglib_LTLIBRARIES += sensors.la
-sensors_la_SOURCES = sensors.c \
-                    utils_ignorelist.c utils_ignorelist.h
+sensors_la_SOURCES = sensors.c
 sensors_la_CFLAGS = $(AM_CFLAGS) $(BUILD_WITH_LIBSENSORS_CFLAGS)
 sensors_la_LDFLAGS = $(PLUGIN_LDFLAGS) $(BUILD_WITH_LIBSENSORS_LDFLAGS)
 sensors_la_LIBADD = -lsensors
@@ -960,8 +948,7 @@ endif
 if BUILD_PLUGIN_SMART
 if BUILD_WITH_LIBUDEV
 pkglib_LTLIBRARIES += smart.la
-smart_la_SOURCES = smart.c \
-                  utils_ignorelist.c utils_ignorelist.h
+smart_la_SOURCES = smart.c
 smart_la_CFLAGS = $(AM_CFLAGS) $(BUILD_WITH_LIBATASMART_CPPFLAGS)
 smart_la_LDFLAGS = $(PLUGIN_LDFLAGS) $(BUILD_WITH_LIBATASMART_LDFLAGS)
 smart_la_LIBADD = $(BUILD_WITH_LIBATASMART_LIBS) -ludev
@@ -1100,8 +1087,7 @@ endif
 
 if BUILD_PLUGIN_THERMAL
 pkglib_LTLIBRARIES += thermal.la
-thermal_la_SOURCES = thermal.c \
-                    utils_ignorelist.c utils_ignorelist.h
+thermal_la_SOURCES = thermal.c
 thermal_la_LDFLAGS = $(PLUGIN_LDFLAGS)
 endif
 
@@ -1186,8 +1172,7 @@ endif
 
 if BUILD_PLUGIN_VIRT
 pkglib_LTLIBRARIES += virt.la
-virt_la_SOURCES = virt.c \
-                 utils_ignorelist.c utils_ignorelist.h
+virt_la_SOURCES = virt.c
 virt_la_CFLAGS = $(AM_CFLAGS) \
                $(BUILD_WITH_LIBVIRT_CFLAGS) $(BUILD_WITH_LIBXML2_CFLAGS)
 virt_la_LIBADD = $(BUILD_WITH_LIBVIRT_LIBS) $(BUILD_WITH_LIBXML2_LIBS)
index e384d800acdf0758579015c5643d7d50c0920e7a..b306032b6c55fddb512b17c0fb24aa252271dbf2 100644 (file)
@@ -383,8 +383,7 @@ static int init_host (apache_t *st) /* {{{ */
        if (st->timeout >= 0)
                curl_easy_setopt (st->curl, CURLOPT_TIMEOUT_MS, (long) st->timeout);
        else
-               curl_easy_setopt (st->curl, CURLOPT_TIMEOUT_MS,
-                               CDTIME_T_TO_MS(plugin_get_interval()));
+               curl_easy_setopt (st->curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(plugin_get_interval()));
 #endif
 
        return (0);
@@ -520,12 +519,9 @@ static void submit_scoreboard (char *buf, apache_t *st)
 
 static int apache_read_host (user_data_t *user_data) /* {{{ */
 {
-       int i;
-
        char *ptr;
        char *saveptr;
-       char *lines[16];
-       int   lines_num = 0;
+       char *line;
 
        char *fields[4];
        int   fields_num;
@@ -565,29 +561,17 @@ static int apache_read_host (user_data_t *user_data) /* {{{ */
 
        ptr = st->apache_buffer;
        saveptr = NULL;
-       while ((lines[lines_num] = strtok_r (ptr, "\n\r", &saveptr)) != NULL)
+       while ((line = strtok_r (ptr, "\n\r", &saveptr)) != NULL)
        {
                ptr = NULL;
-               lines_num++;
-
-               if (lines_num >= 16)
-                       break;
-       }
-
-       for (i = 0; i < lines_num; i++)
-       {
-               fields_num = strsplit (lines[i], fields, 4);
+               fields_num = strsplit (line, fields, STATIC_ARRAY_SIZE (fields));
 
                if (fields_num == 3)
                {
-                       if ((strcmp (fields[0], "Total") == 0)
-                                       && (strcmp (fields[1], "Accesses:") == 0))
-                               submit_derive ("apache_requests", "",
-                                               atoll (fields[2]), st);
-                       else if ((strcmp (fields[0], "Total") == 0)
-                                       && (strcmp (fields[1], "kBytes:") == 0))
-                               submit_derive ("apache_bytes", "",
-                                               1024LL * atoll (fields[2]), st);
+                       if ((strcmp (fields[0], "Total") == 0) && (strcmp (fields[1], "Accesses:") == 0))
+                               submit_derive ("apache_requests", "", atoll (fields[2]), st);
+                       else if ((strcmp (fields[0], "Total") == 0) && (strcmp (fields[1], "kBytes:") == 0))
+                               submit_derive ("apache_bytes", "", 1024LL * atoll (fields[2]), st);
                }
                else if (fields_num == 2)
                {
index 718061ae36e693a9125325f3403da98f25be2316..29d58c3ad6e0a2d1b2038bf6433d078113fe0497 100644 (file)
@@ -125,7 +125,7 @@ static int net_open (char const *node, char const *service)
        if (status != 0)
        {
                char errbuf[1024];
-               INFO ("getaddrinfo failed: %s",
+               INFO ("apcups plugin: getaddrinfo failed: %s",
                                (status == EAI_SYSTEM)
                                ? sstrerror (errno, errbuf, sizeof (errbuf))
                                : gai_strerror (status));
@@ -144,7 +144,7 @@ static int net_open (char const *node, char const *service)
 
        if (sd < 0)
        {
-               DEBUG ("Unable to open a socket");
+               DEBUG ("apcups plugin: Unable to open a socket");
                freeaddrinfo (ai_return);
                return (-1);
        }
@@ -156,13 +156,13 @@ static int net_open (char const *node, char const *service)
        if (status != 0) /* `connect(2)' failed */
        {
                char errbuf[1024];
-               INFO ("connect failed: %s",
+               INFO ("apcups plugin: connect failed: %s",
                                sstrerror (errno, errbuf, sizeof (errbuf)));
                close (sd);
                return (-1);
        }
 
-       DEBUG ("Done opening a socket %i", sd);
+       DEBUG ("apcups plugin: Done opening a socket %i", sd);
 
        return (sd);
 } /* int net_open */
@@ -455,7 +455,7 @@ static int apcups_read (void)
         */
        if (status != 0)
        {
-               DEBUG ("apc_query_server (%s, %s) = %i",
+               DEBUG ("apcups plugin: apc_query_server (%s, %s) = %i",
                                (conf_node == NULL) ? APCUPS_DEFAULT_NODE : conf_node,
                                (conf_service == NULL) ? APCUPS_DEFAULT_SERVICE : conf_service,
                                status);
index 11175af5e6104afa7b39291fd77fd45441a0cb64..2ba3c772d5f9f8116f4100b6f3484756cfbb8ef7 100644 (file)
@@ -594,8 +594,7 @@ static int ascent_init (void) /* {{{ */
   if (timeout != NULL)
     curl_easy_setopt (curl, CURLOPT_TIMEOUT_MS, atol(timeout));
   else
-    curl_easy_setopt (curl, CURLOPT_TIMEOUT_MS,
-       CDTIME_T_TO_MS(plugin_get_interval()));
+    curl_easy_setopt (curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(plugin_get_interval()));
 #endif
 
   return (0);
index 32b0f16e21f50311d530f934f72964076dfee0ee..06b4ace00393e2321fc7bef9762f4b320c582aa5 100644 (file)
@@ -1759,7 +1759,7 @@ static int bind_init (void) /* {{{ */
   curl_easy_setopt (curl, CURLOPT_MAXREDIRS, 50L);
 #ifdef HAVE_CURLOPT_TIMEOUT_MS
   curl_easy_setopt (curl, CURLOPT_TIMEOUT_MS, (timeout >= 0) ?
-      (long) timeout : CDTIME_T_TO_MS(plugin_get_interval()));
+      (long) timeout : (long) CDTIME_T_TO_MS(plugin_get_interval()));
 #endif
 
 
index 10f9f618a2ef976f07222cf69e8edfc8d55727a6..0e4cd53af6d7dfeb9997b8971eb576b65b3f83d8 100644 (file)
@@ -17,7 +17,7 @@ collectd-exec - Documentation of collectd's C<exec plugin>
 
 =head1 DESCRIPTION
 
-The C<exec plugin> forks of an executable either to receive values or to
+The C<exec plugin> forks off an executable either to receive values or to
 dispatch notifications to the outside world. The syntax of the configuration is
 explained in L<collectd.conf(5)> but summarized in the above synopsis.
 
@@ -42,7 +42,7 @@ time and continuously write values to C<STDOUT>.
 See L<EXEC DATA FORMAT> below for a description of the output format expected
 from these programs.
 
-B<Warning:> If the executable only writes one value and then exits I will be
+B<Warning:> If the executable only writes one value and then exits it will be
 executed every I<Interval> seconds. If I<Interval> is short (the default is 10
 seconds) this may result in serious system load.
 
index 80473e0ef79816fe53becb2ab41f4f86c5c86715..9bd65bca8936c7175b7981dd0d2d8f72b008208b 100644 (file)
@@ -40,6 +40,7 @@
 #include <signal.h>
 #include <errno.h>
 #include <math.h>
+#include <sys/time.h>
 
 #include "utils_heap.h"
 
@@ -100,6 +101,7 @@ static void signal_handler (int signal) /* {{{ */
   loop = 0;
 } /* }}} void signal_handler */
 
+#if HAVE_CLOCK_GETTIME
 static double dtime (void) /* {{{ */
 {
   struct timespec ts = { 0 };
@@ -109,6 +111,18 @@ static double dtime (void) /* {{{ */
 
   return ((double) ts.tv_sec) + (((double) ts.tv_nsec) / 1e9);
 } /* }}} double dtime */
+#else
+/* Work around for Mac OS X which doesn't have clock_gettime(2). *sigh* */
+static double dtime (void) /* {{{ */
+{
+  struct timeval tv = { 0 };
+
+  if (gettimeofday (&tv, /* timezone = */ NULL) != 0)
+    perror ("gettimeofday");
+
+  return ((double) tv.tv_sec) + (((double) tv.tv_usec) / 1e6);
+} /* }}} double dtime */
+#endif
 
 static int compare_time (const void *v0, const void *v1) /* {{{ */
 {
index 1f4ccf8175a99d44cecfa325429ddb586631e0dc..30d536a1ef9f9f534caad11b474c797e79d5c6d6 100644 (file)
 
 #<Plugin "battery">
 #  ValuesPercentage false
-#  ReportDegraded
+#  ReportDegraded false
 #</Plugin>
 
 #<Plugin "bind">
 #              Prefix "collectd"
 #              StoreRates true
 #              Retain false
+#              CACert "/etc/ssl/ca.crt"
+#              CertificateFile "/etc/ssl/client.crt"
+#              CertificateKeyFile "/etc/ssl/client.pem"
+#              TLSProtocol "tlsv1.2"
+#              CipherSuite "ciphers"
 #      </Publish>
 #      <Subscribe "name">
 #              Host "localhost"
index aaeeaf419b703913392ef5e78448ffa76fc451dc..78a130cf1e1c5a5daff3de2ac537f42730bdc8ae 100644 (file)
@@ -1827,6 +1827,7 @@ than those of other plugins. It usually looks something like this:
     </Query>
     <Database "product_information">
       Driver "mysql"
+      Interval 120
       DriverOption "host" "localhost"
       DriverOption "username" "collectd"
       DriverOption "password" "aZo6daiw"
@@ -2006,6 +2007,11 @@ the daemon. Other than that, that name is not used.
 
 =over 4
 
+=item B<Interval> I<Interval>
+
+Sets the interval (in seconds) in which the values will be collected from this
+database. By default the global B<Interval> setting will be used.
+
 =item B<Driver> I<Driver>
 
 Specifies the driver to use to connect to the database. In many cases those
@@ -3341,6 +3347,38 @@ Configures the topic(s) to subscribe to. You can use the single level C<+> and
 multi level C<#> wildcards. Defaults to B<collectd/#>, i.e. all topics beneath
 the B<collectd> branch.
 
+=item B<CACert> I<file>
+
+Path to the PEM-encoded CA certificate file. Setting this option enables TLS
+communication with the MQTT broker, and as such, B<Port> should be the TLS-enabled
+port of the MQTT broker.
+A valid TLS configuration requires B<CACert>, B<CertificateFile> and B<CertificateKeyFile>.
+
+=item B<CertificateFile> I<file>
+
+Path to the PEM-encoded certificate file to use as client certificate when
+connecting to the MQTT broker.
+A valid TLS configuration requires B<CACert>, B<CertificateFile> and B<CertificateKeyFile>.
+
+=item B<CertificateKeyFile> I<file>
+
+Path to the unencrypted PEM-encoded key file corresponding to B<CertificateFile>.
+A valid TLS configuration requires B<CACert>, B<CertificateFile> and B<CertificateKeyFile>.
+
+=item B<TLSProtocol> I<protocol>
+
+If configured, this specifies the string protocol version (e.g. C<tlsv1>,
+C<tlsv1.2>) to use for the TLS connection to the broker. If not set a default
+version is used which depends on the version of OpenSSL the Mosquitto library
+was linked against.
+
+=item B<CipherSuite> I<ciphersuite>
+
+A string describing the ciphers available for use. See L<ciphers(1)> and the
+C<openssl ciphers> utility for more information. If unset, the default ciphers
+will be used.
+
+
 =back
 
 =head2 Plugin C<mysql>
@@ -7133,14 +7171,18 @@ setting B<name>.
 B<address> means use the interface's mac address. This is useful since the
 interface path might change between reboots of a guest or across migrations.
 
-=item B<PluginInstanceFormat> B<name|uuid>
+=item B<PluginInstanceFormat> B<name|uuid|none>
 
 When the virt plugin logs data, it sets the plugin_instance of the collected
-data according to this setting. The default is to use the guest name as provided
-by the hypervisor, which is equal to setting B<name>.
+data according to this setting. The default is to not set the plugin_instance.
 
+B<name> means use the guest's name as provided by the hypervisor.
 B<uuid> means use the guest's UUID.
 
+You can also specify combinations of the B<name> and B<uuid> fields.
+For example B<name uuid> means to concatenate the guest name and UUID
+(with a literal colon character between, thus I<"foo:1234-1234-1234-1234">).
+
 =back
 
 =head2 Plugin C<vmem>
@@ -7482,6 +7524,10 @@ complete. When this limit is reached, the POST operation will be aborted, and
 all the data in the current send buffer will probably be lost. Defaults to 0,
 which means the connection never times out.
 
+=item B<LogHttpError> B<false>|B<true>
+
+Enables printing of HTTP error code to log. Turned off by default.
+
 The C<write_http> plugin regularly submits the collected values to the HTTP
 server. How frequently this happens depends on how much data you are collecting
 and the size of B<BufferSize>. The optimal value to set B<Timeout> to is
@@ -7610,6 +7656,8 @@ Synopsis:
         Timeout 1000
         Prefix "collectd/"
         Database 1
+        MaxSetSize -1
+        StoreRates true
     </Node>
   </Plugin>
 
@@ -7618,7 +7666,7 @@ the timestamp as the score. Retrieving a date range can then be done using the
 C<ZRANGEBYSCORE> I<Redis> command. Additionally, all the identifiers of these
 I<Sorted Sets> are kept in a I<Set> called C<collectd/values> (or
 C<${prefix}/values> if the B<Prefix> option was specified) and can be retrieved
-using the C<SMEMBERS> I<Redis> command. You can specify the database to use 
+using the C<SMEMBERS> I<Redis> command. You can specify the database to use
 with the B<Database> parameter (default is C<0>). See
 L<http://redis.io/commands#sorted_set> and L<http://redis.io/commands#set> for
 details.
@@ -7663,7 +7711,18 @@ is recommended but not required to include a trailing slash in I<Prefix>.
 
 =item B<Database> I<Index>
 
-This index selects the redis database to use for writing operations. Defaults to C<0>.
+This index selects the redis database to use for writing operations. Defaults
+to C<0>.
+
+=item B<MaxSetSize> I<Items>
+
+The B<MaxSetSize> option limits the number of items that the I<Sorted Sets> can
+hold. Negative values for I<Items> sets no limit, which is the default behavior.
+
+=item B<StoreRates> B<true>|B<false>
+
+If set to B<true> (the default), convert counter values to rates. If set to
+B<false> counter values are stored as is, i.e. as an increasing integer number.
 
 =back
 
@@ -7744,7 +7803,7 @@ C<ds_type:derive:rate>.
 
 =item B<AlwaysAppendDS> B<false>|B<true>
 
-If set the B<true>, append the name of the I<Data Source> (DS) to the
+If set to B<true>, append the name of the I<Data Source> (DS) to the
 "service", i.e. the field that, together with the "host" field, uniquely
 identifies a metric in I<Riemann>. If set to B<false> (the default), this is
 only done when there is more than one DS.
index ac4cc512c63fd51dcdd9190814aca5e0eaf1cc7d..16ae3ababc1d48c421c85c814b2eb0499edd699e 100644 (file)
@@ -418,8 +418,7 @@ static int cc_page_init_curl (web_page_t *wp) /* {{{ */
   if (wp->timeout >= 0)
     curl_easy_setopt (wp->curl, CURLOPT_TIMEOUT_MS, (long) wp->timeout);
   else
-    curl_easy_setopt (wp->curl, CURLOPT_TIMEOUT_MS,
-       CDTIME_T_TO_MS(plugin_get_interval()));
+    curl_easy_setopt (wp->curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(plugin_get_interval()));
 #endif
 
   return (0);
index 80632424785ae697b8a809588cac5f1b2e61ba15..510d9b621d0b9a32b235337856f455c82eef2b3e 100644 (file)
@@ -654,11 +654,9 @@ static int cj_init_curl (cj_t *db) /* {{{ */
   if (db->timeout >= 0)
     curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS, (long) db->timeout);
   else if (db->interval > 0)
-    curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS,
-        CDTIME_T_TO_MS(db->timeout));
+    curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(db->timeout));
   else
-    curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS,
-        CDTIME_T_TO_MS(plugin_get_interval()));
+    curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(plugin_get_interval()));
 #endif
 
   return (0);
index 8a466bae6f98ff383979e60a2c586ae8e274e6cd..5a1f2baba232e7c56d5ed2ade5b8912e0f13ddd9 100644 (file)
@@ -897,8 +897,7 @@ static int cx_init_curl (cx_t *db) /* {{{ */
   if (db->timeout >= 0)
     curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS, (long) db->timeout);
   else
-    curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS,
-       CDTIME_T_TO_MS(plugin_get_interval()));
+    curl_easy_setopt (db->curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(plugin_get_interval()));
 #endif
 
   return (0);
index 1634713b97393a8ecd97d0d31b0f87494aafcb38..3d50029bac73d6ea41a9124c9063e70cfca9f29d 100644 (file)
@@ -1,7 +1,3 @@
-if COMPILER_IS_GCC
-AM_CFLAGS = -Wall -Werror
-endif
-
 AM_CPPFLAGS = -I$(top_srcdir)/src
 AM_CPPFLAGS += -DPREFIX='"${prefix}"'
 AM_CPPFLAGS += -DCONFIGFILE='"${sysconfdir}/${PACKAGE_NAME}.conf"'
@@ -62,6 +58,7 @@ collectd_SOURCES = collectd.c collectd.h \
                   plugin.c plugin.h \
                   utils_cache.c utils_cache.h \
                   utils_complain.c utils_complain.h \
+                  utils_ignorelist.c utils_ignorelist.h \
                   utils_llist.c utils_llist.h \
                   utils_random.c utils_random.h \
                   utils_tail_match.c utils_tail_match.h \
@@ -93,8 +90,8 @@ else
 collectd_LDADD += -loconfig
 endif
 
-check_PROGRAMS = test_common test_meta_data test_utils_avltree test_utils_heap test_utils_subst
-TESTS          = test_common test_meta_data test_utils_avltree test_utils_heap test_utils_subst
+check_PROGRAMS = test_common test_meta_data test_utils_avltree test_utils_heap test_utils_time test_utils_subst
+TESTS          = test_common test_meta_data test_utils_avltree test_utils_heap test_utils_time test_utils_subst
 
 test_common_SOURCES = common_test.c ../testing.h
 test_common_LDADD = libcommon.la libplugin_mock.la
@@ -108,6 +105,8 @@ test_utils_avltree_LDADD = libavltree.la $(COMMON_LIBS)
 test_utils_heap_SOURCES = utils_heap_test.c ../testing.h
 test_utils_heap_LDADD = libheap.la $(COMMON_LIBS)
 
+test_utils_time_SOURCES = utils_time_test.c ../testing.h
+
 test_utils_subst_SOURCES = utils_subst_test.c ../testing.h \
                           utils_subst.c utils_subst.h
 test_utils_subst_LDADD = libcommon.la libplugin_mock.la
index 58325b95be73973b5cd5c596466255d3a325f6a5..fc52933111e79fec0c291d115618d4b57f6032e5 100644 (file)
@@ -459,7 +459,11 @@ int notify_systemd (void)
 
     unsetenv ("NOTIFY_SOCKET");
 
+#if defined(SOCK_CLOEXEC)
+    fd = socket (AF_UNIX, SOCK_DGRAM|SOCK_CLOEXEC, /* protocol = */ 0);
+#else
     fd = socket (AF_UNIX, SOCK_DGRAM, /* protocol = */ 0);
+#endif
     if (fd < 0) {
         char errbuf[1024];
         ERROR ("creating UNIX socket failed: %s",
@@ -477,7 +481,6 @@ int notify_systemd (void)
     }
     else
     {
-#if KERNEL_LINUX
         /* Linux abstract namespace socket: specify address as "\0foo", i.e.
          * start with a null byte. Since null bytes have no special meaning in
          * that case, we have to set su_size correctly to cover only the bytes
@@ -487,11 +490,6 @@ int notify_systemd (void)
         su_size = sizeof (sa_family_t) + strlen (notifysocket);
         if (su_size > sizeof (su))
             su_size = sizeof (su);
-#else
-       ERROR ("Systemd socket uses Linux abstract namespace notation (\"%s\"), "
-                       "but I don't appear to be running on Linux.", notifysocket);
-       return 0;
-#endif
     }
 
     if (sendto (fd, buffer, strlen (buffer), MSG_NOSIGNAL, (void *) &su, (socklen_t) su_size) < 0)
@@ -503,6 +501,7 @@ int notify_systemd (void)
         return 0;
     }
 
+    unsetenv ("NOTIFY_SOCKET");
     close(fd);
     return 1;
 }
index 8f22011ed57c46c94244f8273461fce3fa7af155..dfaa61aa24fc4e49c6617497981b7f108819ef49 100644 (file)
@@ -48,6 +48,8 @@
 #include <sys/types.h>
 #include <netdb.h>
 
+#include <poll.h>
+
 #if HAVE_NETINET_IN_H
 # include <netinet/in.h>
 #endif
@@ -269,9 +271,23 @@ ssize_t swrite (int fd, const void *buf, size_t count)
        const char *ptr;
        size_t      nleft;
        ssize_t     status;
+       struct      pollfd pfd;
 
        ptr   = (const char *) buf;
        nleft = count;
+       
+       /* checking for closed peer connection */
+       pfd.fd = fd;
+       pfd.events = POLLIN | POLLHUP;
+       pfd.revents = 0;
+       if (poll(&pfd, 1, 0) > 0) {
+               char buffer[32];
+               if (recv(fd, buffer, sizeof(buffer), MSG_PEEK | MSG_DONTWAIT) == 0) {
+                       // if recv returns zero (even though poll() said there is data to be read),
+                       // that means the connection has been closed
+                       return -1;
+               }
+       }
 
        while (nleft > 0)
        {
index 0ee4e7e0eb2c6823e81f32063ceff48eaca8c127..399f8b533b2bcfdce28afa6b9c3a9f7573a89a75 100644 (file)
 #include "testing.h"
 #include "common.h"
 
+#if HAVE_LIBKSTAT
+kstat_ctl_t *kc;
+#endif /* HAVE_LIBKSTAT */
+
 DEF_TEST(sstrncpy)
 {
   char buffer[16] = "";
@@ -38,18 +42,18 @@ DEF_TEST(sstrncpy)
 
   ret = sstrncpy (ptr, "foobar", 8);
   OK(ret == ptr);
-  STREQ ("foobar", ptr);
+  EXPECT_EQ_STR ("foobar", ptr);
   OK(buffer[3] == buffer[12]);
 
   ret = sstrncpy (ptr, "abc", 8);
   OK(ret == ptr);
-  STREQ ("abc", ptr);
+  EXPECT_EQ_STR ("abc", ptr);
   OK(buffer[3] == buffer[12]);
 
   ret = sstrncpy (ptr, "collectd", 8);
   OK(ret == ptr);
   OK(ptr[7] == 0);
-  STREQ ("collect", ptr);
+  EXPECT_EQ_STR ("collect", ptr);
   OK(buffer[3] == buffer[12]);
 
   return (0);
@@ -66,12 +70,12 @@ DEF_TEST(ssnprintf)
 
   status = ssnprintf (ptr, 8, "%i", 1337);
   OK(status == 4);
-  STREQ ("1337", ptr);
+  EXPECT_EQ_STR ("1337", ptr);
 
   status = ssnprintf (ptr, 8, "%s", "collectd");
   OK(status == 8);
   OK(ptr[7] == 0);
-  STREQ ("collect", ptr);
+  EXPECT_EQ_STR ("collect", ptr);
   OK(buffer[3] == buffer[12]);
 
   return (0);
@@ -83,7 +87,7 @@ DEF_TEST(sstrdup)
 
   ptr = sstrdup ("collectd");
   OK(ptr != NULL);
-  STREQ ("collectd", ptr);
+  EXPECT_EQ_STR ("collectd", ptr);
 
   sfree(ptr);
   OK(ptr == NULL);
@@ -103,40 +107,40 @@ DEF_TEST(strsplit)
   strncpy (buffer, "foo bar", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
   OK(status == 2);
-  STREQ ("foo", fields[0]);
-  STREQ ("bar", fields[1]);
+  EXPECT_EQ_STR ("foo", fields[0]);
+  EXPECT_EQ_STR ("bar", fields[1]);
 
   strncpy (buffer, "foo \t bar", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
   OK(status == 2);
-  STREQ ("foo", fields[0]);
-  STREQ ("bar", fields[1]);
+  EXPECT_EQ_STR ("foo", fields[0]);
+  EXPECT_EQ_STR ("bar", fields[1]);
 
   strncpy (buffer, "one two\tthree\rfour\nfive", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
   OK(status == 5);
-  STREQ ("one", fields[0]);
-  STREQ ("two", fields[1]);
-  STREQ ("three", fields[2]);
-  STREQ ("four", fields[3]);
-  STREQ ("five", fields[4]);
+  EXPECT_EQ_STR ("one", fields[0]);
+  EXPECT_EQ_STR ("two", fields[1]);
+  EXPECT_EQ_STR ("three", fields[2]);
+  EXPECT_EQ_STR ("four", fields[3]);
+  EXPECT_EQ_STR ("five", fields[4]);
 
   strncpy (buffer, "\twith trailing\n", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
   OK(status == 2);
-  STREQ ("with", fields[0]);
-  STREQ ("trailing", fields[1]);
+  EXPECT_EQ_STR ("with", fields[0]);
+  EXPECT_EQ_STR ("trailing", fields[1]);
 
   strncpy (buffer, "1 2 3 4 5 6 7 8 9 10 11 12 13", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
   OK(status == 8);
-  STREQ ("7", fields[6]);
-  STREQ ("8", fields[7]);
+  EXPECT_EQ_STR ("7", fields[6]);
+  EXPECT_EQ_STR ("8", fields[7]);
 
   strncpy (buffer, "single", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
   OK(status == 1);
-  STREQ ("single", fields[0]);
+  EXPECT_EQ_STR ("single", fields[0]);
 
   strncpy (buffer, "", sizeof (buffer));
   status = strsplit (buffer, fields, 8);
@@ -158,26 +162,26 @@ DEF_TEST(strjoin)
 
   status = strjoin (buffer, sizeof (buffer), fields, 2, "!");
   OK(status == 7);
-  STREQ ("foo!bar", buffer);
+  EXPECT_EQ_STR ("foo!bar", buffer);
 
   status = strjoin (buffer, sizeof (buffer), fields, 1, "!");
   OK(status == 3);
-  STREQ ("foo", buffer);
+  EXPECT_EQ_STR ("foo", buffer);
 
   status = strjoin (buffer, sizeof (buffer), fields, 0, "!");
   OK(status < 0);
 
   status = strjoin (buffer, sizeof (buffer), fields, 2, "rcht");
   OK(status == 10);
-  STREQ ("foorchtbar", buffer);
+  EXPECT_EQ_STR ("foorchtbar", buffer);
 
   status = strjoin (buffer, sizeof (buffer), fields, 4, "");
   OK(status == 12);
-  STREQ ("foobarbazqux", buffer);
+  EXPECT_EQ_STR ("foobarbazqux", buffer);
 
   status = strjoin (buffer, sizeof (buffer), fields, 4, "!");
   OK(status == 15);
-  STREQ ("foo!bar!baz!qux", buffer);
+  EXPECT_EQ_STR ("foo!bar!baz!qux", buffer);
 
   fields[0] = "0123";
   fields[1] = "4567";
@@ -207,7 +211,7 @@ DEF_TEST(escape_slashes)
 
     strncpy (buffer, cases[i].str, sizeof (buffer));
     OK(escape_slashes (buffer, sizeof (buffer)) == 0);
-    STREQ(cases[i].want, buffer);
+    EXPECT_EQ_STR(cases[i].want, buffer);
   }
 
   return 0;
@@ -234,7 +238,7 @@ DEF_TEST(escape_string)
 
     strncpy (buffer, cases[i].str, sizeof (buffer));
     OK(escape_string (buffer, sizeof (buffer)) == 0);
-    STREQ(cases[i].want, buffer);
+    EXPECT_EQ_STR(cases[i].want, buffer);
   }
 
   return 0;
@@ -248,23 +252,23 @@ DEF_TEST(strunescape)
   strncpy (buffer, "foo\\tbar", sizeof (buffer));
   status = strunescape (buffer, sizeof (buffer));
   OK(status == 0);
-  STREQ ("foo\tbar", buffer);
+  EXPECT_EQ_STR ("foo\tbar", buffer);
 
   strncpy (buffer, "\\tfoo\\r\\n", sizeof (buffer));
   status = strunescape (buffer, sizeof (buffer));
   OK(status == 0);
-  STREQ ("\tfoo\r\n", buffer);
+  EXPECT_EQ_STR ("\tfoo\r\n", buffer);
 
   strncpy (buffer, "With \\\"quotes\\\"", sizeof (buffer));
   status = strunescape (buffer, sizeof (buffer));
   OK(status == 0);
-  STREQ ("With \"quotes\"", buffer);
+  EXPECT_EQ_STR ("With \"quotes\"", buffer);
 
   /* Backslash before null byte */
   strncpy (buffer, "\\tbackslash end\\", sizeof (buffer));
   status = strunescape (buffer, sizeof (buffer));
   OK(status != 0);
-  STREQ ("\tbackslash end", buffer);
+  EXPECT_EQ_STR ("\tbackslash end", buffer);
   return (0);
 
   /* Backslash at buffer end */
@@ -328,11 +332,11 @@ DEF_TEST(parse_values)
     };
 
     int status = parse_values (cases[i].buffer, &vl, &ds);
-    EXPECT_INTEQ (cases[i].status, status);
+    EXPECT_EQ_INT (cases[i].status, status);
     if (status != 0)
       continue;
 
-    DBLEQ (cases[i].value, vl.values[0].gauge);
+    EXPECT_EQ_DOUBLE (cases[i].value, vl.values[0].gauge);
   }
 
   return (0);
@@ -370,7 +374,7 @@ DEF_TEST(value_to_rate)
     }
 
     OK(value_to_rate (&got, cases[i].v1, cases[i].ds_type, TIME_T_TO_CDTIME_T(cases[i].t1), &state) == 0);
-    DBLEQ(cases[i].want, got);
+    EXPECT_EQ_DOUBLE(cases[i].want, got);
   }
 
   return 0;
index 6ee8446b37639dc38e479db4f6dcd48807cde725..4e46ed53355ff30346a239d3d8bcb3d3c5511e34 100644 (file)
@@ -255,7 +255,6 @@ void meta_data_destroy (meta_data_t *md) /* {{{ */
   if (md == NULL)
     return;
 
-  pthread_mutex_destroy(&md->lock);
   md_entry_free (md->head);
   pthread_mutex_destroy (&md->lock);
   free (md);
index 6d61107d50a6bf97b285739b735edf1c2730eec5..b4c0e27690ebb09b4edbf66e60a58d830661aa6b 100644 (file)
@@ -71,27 +71,27 @@ DEF_TEST(base)
 
   /* retrieve and check all values */
   CHECK_ZERO (meta_data_get_string (m, "string", &s));
-  STREQ ("foobar", s);
+  EXPECT_EQ_STR ("foobar", s);
   sfree (s);
 
   CHECK_ZERO (meta_data_get_signed_int (m, "signed_int", &si));
-  EXPECT_INTEQ (-1, (int) si);
+  EXPECT_EQ_INT (-1, (int) si);
 
   CHECK_ZERO (meta_data_get_unsigned_int (m, "unsigned_int", &ui));
-  EXPECT_INTEQ (1, (int) ui);
+  EXPECT_EQ_INT (1, (int) ui);
 
   CHECK_ZERO (meta_data_get_double (m, "double", &d));
-  DBLEQ (47.11, d);
+  EXPECT_EQ_DOUBLE (47.11, d);
 
   CHECK_ZERO (meta_data_get_boolean (m, "boolean", &b));
   OK1 (b, "b evaluates to true");
 
   /* retrieving the wrong type always fails */
-  EXPECT_INTEQ (-2, meta_data_get_boolean (m, "string", &b));
-  EXPECT_INTEQ (-2, meta_data_get_string (m, "signed_int", &s));
-  EXPECT_INTEQ (-2, meta_data_get_string (m, "unsigned_int", &s));
-  EXPECT_INTEQ (-2, meta_data_get_string (m, "double", &s));
-  EXPECT_INTEQ (-2, meta_data_get_string (m, "boolean", &s));
+  EXPECT_EQ_INT (-2, meta_data_get_boolean (m, "string", &b));
+  EXPECT_EQ_INT (-2, meta_data_get_string (m, "signed_int", &s));
+  EXPECT_EQ_INT (-2, meta_data_get_string (m, "unsigned_int", &s));
+  EXPECT_EQ_INT (-2, meta_data_get_string (m, "double", &s));
+  EXPECT_EQ_INT (-2, meta_data_get_string (m, "boolean", &s));
 
   /* replace existing keys */
   CHECK_ZERO (meta_data_add_signed_int (m, "string", 666));
@@ -99,11 +99,11 @@ DEF_TEST(base)
 
   CHECK_ZERO (meta_data_add_signed_int (m, "signed_int", 666));
   CHECK_ZERO (meta_data_get_signed_int (m, "signed_int", &si));
-  EXPECT_INTEQ (666, (int) si);
+  EXPECT_EQ_INT (666, (int) si);
 
   /* deleting keys */
   CHECK_ZERO (meta_data_delete (m, "signed_int"));
-  EXPECT_INTEQ (-2, meta_data_delete (m, "doesnt exist"));
+  EXPECT_EQ_INT (-2, meta_data_delete (m, "doesnt exist"));
 
   meta_data_destroy (m);
   return 0;
index be3f03fc57d5a7d1a68a4fd0b831543f44b6f03f..831e3fb0311398c5c1b75cddc67b5e5d4b2b8c0e 100644 (file)
@@ -1089,6 +1089,7 @@ int plugin_load (char const *plugin_name, uint32_t flags)
                        /* success */
                        plugin_mark_loaded (plugin_name);
                        ret = 0;
+                       INFO ("plugin_load: plugin \"%s\" successfully loaded.", plugin_name);
                        break;
                }
                else
@@ -1724,8 +1725,6 @@ void plugin_init_all (void)
                write_threads_num = 5;
        }
 
-       start_write_threads ((size_t) write_threads_num);
-
        if ((list_init == NULL) && (read_heap == NULL))
                return;
 
@@ -1761,6 +1760,8 @@ void plugin_init_all (void)
                le = le->next;
        }
 
+       start_write_threads ((size_t) write_threads_num);
+
        max_read_interval = global_option_get_time ("MaxReadInterval",
                        DEFAULT_MAX_READ_INTERVAL);
 
index e251975bac6479e8410d64aa9e16b898e38a8839..58b8b8479128b6a9b25377412e1e9e608070826a 100644 (file)
@@ -652,6 +652,7 @@ int c_avl_pick (c_avl_tree_t *t, void **key, void **value)
        *value = n->value;
 
        free_node (n);
+       --t->size;
        rebalance (t, p);
 
        return (0);
index 2a8244c9f3e6cd1008649091de98b595ebf386f6..6dbafe18a4bcfd3712af89bb3812ab3fc7e833bb 100644 (file)
@@ -27,6 +27,7 @@
 #include "testing.h"
 #include "collectd.h"
 #include "utils_avltree.h"
+#include "common.h" /* STATIC_ARRAY_SIZE */
 
 static int compare_total_count = 0;
 #define RESET_COUNTS() do { compare_total_count = 0; } while (0)
@@ -42,30 +43,99 @@ static int compare_callback (void const *v0, void const *v1)
 
 DEF_TEST(success)
 {
+  struct {
+    char *key;
+    char *value;
+  } cases[] = {
+    {"Eeph7chu", "vai1reiV"},
+    {"igh3Paiz", "teegh1Ee"},
+    {"caip6Uu8", "ooteQu8n"},
+    {"Aech6vah", "AijeeT0l"},
+    {"Xah0et2L", "gah8Taep"},
+    {"BocaeB8n", "oGaig8io"},
+    {"thai8AhM", "ohjeFo3f"},
+    {"ohth6ieC", "hoo8ieWo"},
+    {"aej7Woow", "phahuC2s"},
+    {"Hai8ier2", "Yie6eimi"},
+    {"phuXi3Li", "JaiF7ieb"},
+    {"Shaig5ef", "aihi5Zai"},
+    {"voh6Aith", "Oozaeto0"},
+    {"zaiP5kie", "seep5veM"},
+    {"pae7ba7D", "chie8Ojo"},
+    {"Gou2ril3", "ouVoo0ha"},
+    {"lo3Thee3", "ahDu4Zuj"},
+    {"Rah8kohv", "ieShoc7E"},
+    {"ieN5engi", "Aevou1ah"},
+    {"ooTe4OhP", "aingai5Y"},
+  };
+
   c_avl_tree_t *t;
-  char key_orig[] = "foo";
-  char value_orig[] = "bar";
-  char *key_ret = NULL;
-  char *value_ret = NULL;
+  size_t i;
 
   RESET_COUNTS ();
-  t = c_avl_create (compare_callback);
-  OK (t != NULL);
+  CHECK_NOT_NULL (t = c_avl_create (compare_callback));
+
+  /* insert */
+  for (i = 0; i < STATIC_ARRAY_SIZE (cases); i++)
+  {
+    char *key;
+    char *value;
 
-  OK (c_avl_insert (t, key_orig, value_orig) == 0);
-  OK (c_avl_size (t) == 1);
+    CHECK_NOT_NULL (key = strdup (cases[i].key));
+    CHECK_NOT_NULL (value = strdup (cases[i].value));
+
+    CHECK_ZERO (c_avl_insert (t, key, value));
+    EXPECT_EQ_INT ((int) (i + 1), c_avl_size (t));
+  }
 
   /* Key already exists. */
-  OK (c_avl_insert (t, "foo", "qux") > 0);
+  for (i = 0; i < STATIC_ARRAY_SIZE (cases); i++)
+    EXPECT_EQ_INT (1, c_avl_insert (t, cases[i].key, cases[i].value));
+
+  /* get */
+  for (i = 0; i < STATIC_ARRAY_SIZE (cases); i++)
+  {
+    char *value_ret = NULL;
+
+    CHECK_ZERO (c_avl_get (t, cases[i].key, (void *) &value_ret));
+    EXPECT_EQ_STR (cases[i].value, value_ret);
+  }
+
+  /* remove half */
+  for (i = 0; i < STATIC_ARRAY_SIZE (cases) / 2; i++)
+  {
+    char *key = NULL;
+    char *value = NULL;
+
+    int expected_size = (int) (STATIC_ARRAY_SIZE (cases) - (i + 1));
+
+    CHECK_ZERO (c_avl_remove (t, cases[i].key, (void *) &key, (void *) &value));
+
+    EXPECT_EQ_STR (cases[i].key, key);
+    EXPECT_EQ_STR (cases[i].value, value);
+
+    free (key);
+    free (value);
+
+    EXPECT_EQ_INT (expected_size, c_avl_size (t));
+  }
+
+  /* pick the other half */
+  for (i = STATIC_ARRAY_SIZE (cases) / 2; i < STATIC_ARRAY_SIZE (cases); i++)
+  {
+    char *key = NULL;
+    char *value = NULL;
+
+    int expected_size = (int) (STATIC_ARRAY_SIZE (cases) - (i + 1));
+
+    EXPECT_EQ_INT (expected_size + 1, c_avl_size (t));
+    EXPECT_EQ_INT (0, c_avl_pick (t, (void *) &key, (void *) &value));
 
-  OK (c_avl_get (t, "foo", (void *) &value_ret) == 0);
-  OK (value_ret == &value_orig[0]);
+    free (key);
+    free (value);
 
-  key_ret = value_ret = NULL;
-  OK (c_avl_remove (t, "foo", (void *) &key_ret, (void *) &value_ret) == 0);
-  OK (key_ret == &key_orig[0]);
-  OK (value_ret == &value_orig[0]);
-  OK (c_avl_size (t) == 0);
+    EXPECT_EQ_INT (expected_size, c_avl_size (t));
+  }
 
   c_avl_destroy (t);
 
diff --git a/src/daemon/utils_ignorelist.c b/src/daemon/utils_ignorelist.c
new file mode 100644 (file)
index 0000000..a8ca7db
--- /dev/null
@@ -0,0 +1,338 @@
+/**
+ * collectd - src/utils_ignorelist.c
+ * Copyright (C) 2006 Lubos Stanek <lubek at users.sourceforge.net>
+ * Copyright (C) 2008 Florian Forster <octo at collectd.org>
+ *
+ * This program is free software; you can redistribute it and/
+ * or modify it under the terms of the GNU General Public Li-
+ * cence as published by the Free Software Foundation; either
+ * version 2 of the Licence, or any later version.
+ *
+ * This program is distributed in the hope that it will be use-
+ * ful, but WITHOUT ANY WARRANTY; without even the implied war-
+ * ranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ * See the GNU General Public Licence for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * Licence along with this program; if not, write to the Free
+ * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139,
+ * USA.
+ *
+ * Authors:
+ *   Lubos Stanek <lubek at users.sourceforge.net>
+ *   Florian Forster <octo at collectd.org>
+ **/
+/**
+ * ignorelist handles plugin's list of configured collectable
+ * entries with global ignore action
+ **/
+/**
+ * Usage:
+ * 
+ * Define plugin's global pointer variable of type ignorelist_t:
+ *   ignorelist_t *myconfig_ignore;
+ * If you know the state of the global ignore (IgnoreSelected),
+ * allocate the variable with:
+ *   myconfig_ignore = ignorelist_create (YourKnownIgnore);
+ * If you do not know the state of the global ignore,
+ * initialize the global variable and set the ignore flag later:
+ *   myconfig_ignore = ignorelist_init ();
+ * Append single entries in your cf_register'ed callback function:
+ *   ignorelist_add (myconfig_ignore, newentry);
+ * When you hit the IgnoreSelected config option,
+ * offer it to the list:
+ *   ignorelist_ignore (myconfig_ignore, instantly_got_value_of_ignore);
+ * That is all for the ignorelist initialization.
+ * Later during read and write (plugin's registered functions) get
+ * the information whether this entry would be collected or not:
+ *   if (ignorelist_match (myconfig_ignore, thisentry))
+ *     return;
+ **/
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include "common.h"
+#include "plugin.h"
+#include "utils_ignorelist.h"
+
+/*
+ * private prototypes
+ */
+struct ignorelist_item_s
+{
+#if HAVE_REGEX_H
+       regex_t *rmatch;        /* regular expression entry identification */
+#endif
+       char *smatch;           /* string entry identification */
+       struct ignorelist_item_s *next;
+};
+typedef struct ignorelist_item_s ignorelist_item_t;
+
+struct ignorelist_s
+{
+       int ignore;             /* ignore entries */
+       ignorelist_item_t *head;        /* pointer to the first entry */
+};
+
+/* *** *** *** ********************************************* *** *** *** */
+/* *** *** *** *** *** ***   private functions   *** *** *** *** *** *** */
+/* *** *** *** ********************************************* *** *** *** */
+
+static inline void ignorelist_append (ignorelist_t *il, ignorelist_item_t *item)
+{
+       assert ((il != NULL) && (item != NULL));
+
+       item->next = il->head;
+       il->head = item;
+}
+
+#if HAVE_REGEX_H
+static int ignorelist_append_regex(ignorelist_t *il, const char *re_str)
+{
+       regex_t *re;
+       ignorelist_item_t *entry;
+       int status;
+
+       re = malloc (sizeof (*re));
+       if (re == NULL)
+       {
+               ERROR ("utils_ignorelist: malloc failed");
+               return (ENOMEM);
+       }
+       memset (re, 0, sizeof (*re));
+
+       status = regcomp (re, re_str, REG_EXTENDED);
+       if (status != 0)
+       {
+               char errbuf[1024] = "";
+               regerror (status, re, errbuf, sizeof (errbuf));
+               ERROR ("utils_ignorelist: regcomp failed: %s", errbuf);
+               regfree (re);
+               sfree (re);
+               return (status);
+       }
+
+       entry = malloc (sizeof (*entry));
+       if (entry == NULL)
+       {
+               ERROR ("utils_ignorelist: malloc failed");
+               regfree (re);
+               sfree (re);
+               return (ENOMEM);
+       }
+       memset (entry, 0, sizeof (*entry));
+       entry->rmatch = re;
+
+       ignorelist_append (il, entry);
+       return (0);
+} /* int ignorelist_append_regex */
+#endif
+
+static int ignorelist_append_string(ignorelist_t *il, const char *entry)
+{
+       ignorelist_item_t *new;
+
+       /* create new entry */
+       if ((new = malloc(sizeof(ignorelist_item_t))) == NULL )
+       {
+               ERROR ("cannot allocate new entry");
+               return (1);
+       }
+       memset (new, '\0', sizeof(ignorelist_item_t));
+       new->smatch = sstrdup(entry);
+
+       /* append new entry */
+       ignorelist_append (il, new);
+
+       return (0);
+} /* int ignorelist_append_string(ignorelist_t *il, const char *entry) */
+
+#if HAVE_REGEX_H
+/*
+ * check list for entry regex match
+ * return 1 if found
+ */
+static int ignorelist_match_regex (ignorelist_item_t *item, const char *entry)
+{
+       assert ((item != NULL) && (item->rmatch != NULL)
+                       && (entry != NULL) && (strlen (entry) > 0));
+
+       /* match regex */
+       if (regexec (item->rmatch, entry, 0, NULL, 0) == 0)
+               return (1);
+
+       return (0);
+} /* int ignorelist_match_regex (ignorelist_item_t *item, const char *entry) */
+#endif
+
+/*
+ * check list for entry string match
+ * return 1 if found
+ */
+static int ignorelist_match_string (ignorelist_item_t *item, const char *entry)
+{
+       assert ((item != NULL) && (item->smatch != NULL)
+                       && (entry != NULL) && (strlen (entry) > 0));
+
+       if (strcmp (entry, item->smatch) == 0)
+               return (1);
+
+       return (0);
+} /* int ignorelist_match_string (ignorelist_item_t *item, const char *entry) */
+
+
+/* *** *** *** ******************************************** *** *** *** */
+/* *** *** *** *** *** ***   public functions   *** *** *** *** *** *** */
+/* *** *** *** ******************************************** *** *** *** */
+
+/*
+ * create the ignorelist_t with known ignore state
+ * return pointer to ignorelist_t
+ */
+ignorelist_t *ignorelist_create (int invert)
+{
+       ignorelist_t *il;
+
+       /* smalloc exits if it failes */
+       il = (ignorelist_t *) smalloc (sizeof (ignorelist_t));
+       memset (il, '\0', sizeof (ignorelist_t));
+
+       /*
+        * ->ignore == 0  =>  collect
+        * ->ignore == 1  =>  ignore
+        */
+       il->ignore = invert ? 0 : 1;
+
+       return (il);
+} /* ignorelist_t *ignorelist_create (int ignore) */
+
+/*
+ * free memory used by ignorelist_t
+ */
+void ignorelist_free (ignorelist_t *il)
+{
+       ignorelist_item_t *this;
+       ignorelist_item_t *next;
+
+       if (il == NULL)
+               return;
+
+       for (this = il->head; this != NULL; this = next)
+       {
+               next = this->next;
+#if HAVE_REGEX_H
+               if (this->rmatch != NULL)
+               {
+                       regfree (this->rmatch);
+                       sfree (this->rmatch);
+                       this->rmatch = NULL;
+               }
+#endif
+               if (this->smatch != NULL)
+               {
+                       sfree (this->smatch);
+                       this->smatch = NULL;
+               }
+               sfree (this);
+       }
+
+       sfree (il);
+       il = NULL;
+} /* void ignorelist_destroy (ignorelist_t *il) */
+
+/*
+ * set ignore state of the ignorelist_t
+ */
+void ignorelist_set_invert (ignorelist_t *il, int invert)
+{
+       if (il == NULL)
+       {
+               DEBUG("ignore call with ignorelist_t == NULL");
+               return;
+       }
+
+       il->ignore = invert ? 0 : 1;
+} /* void ignorelist_set_invert (ignorelist_t *il, int ignore) */
+
+/*
+ * append entry into ignorelist_t
+ * return 0 for success
+ */
+int ignorelist_add (ignorelist_t *il, const char *entry)
+{
+       size_t entry_len;
+
+       if (il == NULL)
+       {
+               DEBUG ("add called with ignorelist_t == NULL");
+               return (1);
+       }
+
+       entry_len = strlen (entry);
+
+       /* append nothing */
+       if (entry_len == 0)
+       {
+               DEBUG("not appending: empty entry");
+               return (1);
+       }
+
+#if HAVE_REGEX_H
+       /* regex string is enclosed in "/.../" */
+       if ((entry_len > 2) && (entry[0] == '/') && entry[entry_len - 1] == '/')
+       {
+               char *entry_copy;
+               size_t entry_copy_size;
+               int status;
+
+               /* We need to copy `entry' since it's const */
+               entry_copy_size = entry_len - 1;
+               entry_copy = smalloc (entry_copy_size);
+               sstrncpy (entry_copy, entry + 1, entry_copy_size);
+
+               status = ignorelist_append_regex(il, entry_copy);
+               sfree (entry_copy);
+               return status;
+       }
+#endif
+
+       return ignorelist_append_string(il, entry);
+} /* int ignorelist_add (ignorelist_t *il, const char *entry) */
+
+/*
+ * check list for entry
+ * return 1 for ignored entry
+ */
+int ignorelist_match (ignorelist_t *il, const char *entry)
+{
+       ignorelist_item_t *traverse;
+
+       /* if no entries, collect all */
+       if ((il == NULL) || (il->head == NULL))
+               return (0);
+
+       if ((entry == NULL) || (strlen (entry) == 0))
+               return (0);
+
+       /* traverse list and check entries */
+       for (traverse = il->head; traverse != NULL; traverse = traverse->next)
+       {
+#if HAVE_REGEX_H
+               if (traverse->rmatch != NULL)
+               {
+                       if (ignorelist_match_regex (traverse, entry))
+                               return (il->ignore);
+               }
+               else
+#endif
+               {
+                       if (ignorelist_match_string (traverse, entry))
+                               return (il->ignore);
+               }
+       } /* for traverse */
+
+       return (1 - il->ignore);
+} /* int ignorelist_match (ignorelist_t *il, const char *entry) */
+
diff --git a/src/daemon/utils_ignorelist.h b/src/daemon/utils_ignorelist.h
new file mode 100644 (file)
index 0000000..b47b55a
--- /dev/null
@@ -0,0 +1,70 @@
+/**
+ * collectd - src/utils_ignorelist.h
+ * Copyright (C) 2006 Lubos Stanek <lubek at users.sourceforge.net>
+ *
+ * This program is free software; you can redistribute it and/
+ * or modify it under the terms of the GNU General Public Li-
+ * cence as published by the Free Software Foundation; either
+ * version 2 of the Licence, or any later version.
+ *
+ * This program is distributed in the hope that it will be use-
+ * ful, but WITHOUT ANY WARRANTY; without even the implied war-
+ * ranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ * See the GNU General Public Licence for more details.
+ *
+ * You should have received a copy of the GNU General Public
+ * Licence along with this program; if not, write to the Free
+ * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139,
+ * USA.
+ *
+ * Authors:
+ *   Lubos Stanek <lubek at users.sourceforge.net>
+ **/
+/**
+ * ignorelist handles plugin's list of configured collectable
+ * entries with global ignore action
+ **/
+
+#ifndef UTILS_IGNORELIST_H
+#define UTILS_IGNORELIST_H 1
+
+#include "collectd.h"
+
+#if HAVE_REGEX_H
+# include <regex.h>
+#endif
+
+/* public prototypes */
+
+struct ignorelist_s;
+typedef struct ignorelist_s ignorelist_t;
+
+/*
+ * create the ignorelist_t with known ignore state
+ * return pointer to ignorelist_t
+ */
+ignorelist_t *ignorelist_create (int invert);
+
+/*
+ * free memory used by ignorelist_t
+ */
+void ignorelist_free (ignorelist_t *il);
+
+/*
+ * set ignore state of the ignorelist_t
+ */
+void ignorelist_set_invert (ignorelist_t *il, int invert);
+
+/*
+ * append entry to ignorelist_t
+ * returns zero on success, non-zero upon failure.
+ */
+int ignorelist_add (ignorelist_t *il, const char *entry);
+
+/*
+ * check list for entry
+ * return 1 for ignored entry
+ */
+int ignorelist_match (ignorelist_t *il, const char *entry);
+
+#endif /* UTILS_IGNORELIST_H */
index 751976630fb87e0819053bf123b728f71e6aca29..c12aa1057fe3d91022c67983d6a4e338c3b7f6ea 100644 (file)
 #include "common.h" /* for STATIC_ARRAY_SIZE */
 #include "utils_subst.h"
 
+#if HAVE_LIBKSTAT
+kstat_ctl_t *kc;
+#endif /* HAVE_LIBKSTAT */
+
 DEF_TEST(subst)
 {
   struct {
@@ -82,7 +86,7 @@ DEF_TEST(subst)
     }
 
     OK(subst (buffer, sizeof (buffer), cases[i].str, cases[i].off1, cases[i].off2, cases[i].rplmt) == &buffer[0]);
-    STREQ(cases[i].want, buffer);
+    EXPECT_EQ_STR(cases[i].want, buffer);
   }
 
   return 0;
@@ -112,7 +116,7 @@ DEF_TEST(subst_string)
     }
 
     OK(subst_string (buffer, sizeof (buffer), cases[i].str, cases[i].srch, cases[i].rplmt) == buffer);
-    STREQ(cases[i].want, buffer);
+    EXPECT_EQ_STR(cases[i].want, buffer);
   }
 
   return 0;
index 9b08e8e4de68f011d24b4dc947c9d23922506544..6566a739bdf8be34b695a3d715dd90b7644e2f23 100644 (file)
@@ -1,6 +1,6 @@
 /**
- * collectd - src/utils_time.h
- * Copyright (C) 2010       Florian octo Forster
+ * collectd - src/daemon/utils_time.h
+ * Copyright (C) 2010-2015  Florian octo Forster
  *
  * Permission is hereby granted, free of charge, to any person obtaining a
  * copy of this software and associated documentation files (the "Software"),
@@ -21,7 +21,7 @@
  * DEALINGS IN THE SOFTWARE.
  *
  * Authors:
- *   Florian octo Forster <ff at octo.it>
+ *   Florian octo Forster <octo at collectd.org>
  **/
 
 #ifndef UTILS_TIME_H
 /* typedef uint64_t cdtime_t; */
 
 /* 2^30 = 1073741824 */
-#define TIME_T_TO_CDTIME_T(t) (((cdtime_t) (t)) * 1073741824)
-#define CDTIME_T_TO_TIME_T(t) ((time_t) ((t) / 1073741824))
+#define TIME_T_TO_CDTIME_T(t) (((cdtime_t) (t)) << 30)
+
+#define MS_TO_CDTIME_T(ms) (((((cdtime_t) (ms)) / 1000) << 30) | \
+    ((((((cdtime_t) (ms)) % 1000) << 30) + 500) / 1000))
+#define US_TO_CDTIME_T(us) (((((cdtime_t) (us)) / 1000000) << 30) | \
+    ((((((cdtime_t) (us)) % 1000000) << 30) + 500000) / 1000000))
+#define NS_TO_CDTIME_T(ns) (((((cdtime_t) (ns)) / 1000000000) << 30) | \
+    ((((((cdtime_t) (ns)) % 1000000000) << 30) + 500000000) / 1000000000))
+
+#define CDTIME_T_TO_TIME_T(t) ((time_t) (((t) + (1 << 29)) >> 30))
+#define CDTIME_T_TO_MS(t)  ((uint64_t) ((((t) >> 30) * 1000) + \
+  ((((t) & 0x3fffffff) * 1000 + (1 << 29)) >> 30)))
+#define CDTIME_T_TO_US(t)  ((uint64_t) ((((t) >> 30) * 1000000) + \
+  ((((t) & 0x3fffffff) * 1000000 + (1 << 29)) >> 30)))
+#define CDTIME_T_TO_NS(t)  ((uint64_t) ((((t) >> 30) * 1000000000) + \
+  ((((t) & 0x3fffffff) * 1000000000 + (1 << 29)) >> 30)))
 
 #define CDTIME_T_TO_DOUBLE(t) (((double) (t)) / 1073741824.0)
 #define DOUBLE_TO_CDTIME_T(d) ((cdtime_t) ((d) * 1073741824.0))
 
-#define MS_TO_CDTIME_T(ms) ((cdtime_t)    (((double) (ms)) * 1073741.824))
-#define CDTIME_T_TO_MS(t)  ((long)        (((double) (t))  / 1073741.824))
-#define US_TO_CDTIME_T(us) ((cdtime_t)    (((double) (us)) * 1073.741824))
-#define CDTIME_T_TO_US(t)  ((suseconds_t) (((double) (t))  / 1073.741824))
-#define NS_TO_CDTIME_T(ns) ((cdtime_t)    (((double) (ns)) * 1.073741824))
-#define CDTIME_T_TO_NS(t)  ((long)        (((double) (t))  / 1.073741824))
-
 #define CDTIME_T_TO_TIMEVAL(cdt,tvp) do {                                    \
         (tvp)->tv_sec = CDTIME_T_TO_TIME_T (cdt);                            \
-        (tvp)->tv_usec = CDTIME_T_TO_US ((cdt) % 1073741824);                \
+        (tvp)->tv_usec = (suseconds_t) CDTIME_T_TO_US ((cdt) & 0x3fffffff);  \
 } while (0)
-#define TIMEVAL_TO_CDTIME_T(tv) (TIME_T_TO_CDTIME_T ((tv)->tv_sec)           \
-    + US_TO_CDTIME_T ((tv)->tv_usec))
+#define TIMEVAL_TO_CDTIME_T(tv) US_TO_CDTIME_T(1000000 * (tv)->tv_sec + (tv)->tv_usec)
 
 #define CDTIME_T_TO_TIMESPEC(cdt,tsp) do {                                   \
   (tsp)->tv_sec = CDTIME_T_TO_TIME_T (cdt);                                  \
-  (tsp)->tv_nsec = CDTIME_T_TO_NS ((cdt) % 1073741824);                      \
+  (tsp)->tv_nsec = (long) CDTIME_T_TO_NS ((cdt) & 0x3fffffff);               \
 } while (0)
-#define TIMESPEC_TO_CDTIME_T(ts) (TIME_T_TO_CDTIME_T ((ts)->tv_sec)           \
-    + NS_TO_CDTIME_T ((ts)->tv_nsec))
+#define TIMESPEC_TO_CDTIME_T(ts) NS_TO_CDTIME_T(1000000000ULL * (ts)->tv_sec + (ts)->tv_nsec)
 
 cdtime_t cdtime (void);
 
diff --git a/src/daemon/utils_time_test.c b/src/daemon/utils_time_test.c
new file mode 100644 (file)
index 0000000..8eac0b6
--- /dev/null
@@ -0,0 +1,125 @@
+/**
+ * collectd - src/daemon/utils_time_test.c
+ * Copyright (C) 2015       Florian octo Forster
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ *
+ * Authors:
+ *   Florian octo Forster <octo at collectd.org>
+ */
+
+#define DBL_PRECISION 1e-3
+
+#include "testing.h"
+#include "collectd.h"
+#include "utils_time.h"
+
+DEF_TEST(conversion)
+{
+  struct {
+    cdtime_t t;
+    double d;
+    time_t tt;
+    uint64_t ms;
+    struct timeval tv;
+    struct timespec ts;
+  } cases[] = {
+  /*              cdtime          double      time_t   milliseconds               timeval                 timespec */
+    {                     0,          0.0  ,          0,                0, {         0,      0}, {         0,         0}},
+    {        10737418240ULL,         10.0  ,         10,            10000, {        10,      0}, {        10,         0}},
+    {1542908534771941376ULL, 1436945549.0  , 1436945549, 1436945549000ULL, {1436945549,      0}, {1436945549,         0}},
+    {1542908535540740522ULL, 1436945549.716, 1436945550, 1436945549716ULL, {1436945549, 716000}, {1436945549, 716000000}},
+    // 1426076671.123 * 2^30 = 1531238166015458148.352
+    {1531238166015458148ULL, 1426076671.123, 1426076671, 1426076671123ULL, {1426076671, 123000}, {1426076671, 123000000}},
+    // 1426076681.234 * 2^30 = 1531238176872061730.816
+    {1531238176872061731ULL, 1426076681.234, 1426076681, 1426076681234ULL, {1426076681, 234000}, {1426076681, 234000000}},
+    // 1426083986.314 * 2^30 = 1531246020641985396.736
+    {1531246020641985397ULL, 1426083986.314, 1426083986, 1426083986314ULL, {1426083986, 314000}, {1426083986, 314000000}},
+    // 1426083986.494142531 * 2^30 = 1531246020835411966.5
+    {1531246020835411967ULL, 1426083986.494, 1426083986, 1426083986494ULL, {1426083986, 494143}, {1426083986, 494142531}},
+    // 1426083986.987410814 * 2^30 = 1531246021365054752.4
+    {1531246021365054752ULL, 1426083986.987, 1426083987, 1426083986987ULL, {1426083986, 987411}, {1426083986, 987410814}},
+
+    /* These cases test the cdtime_t -> ns conversion rounds correctly. */
+    // 1546167635576736987 / 2^30 = 1439980823.1524536265...
+    {1546167635576736987ULL, 1439980823.152, 1439980823, 1439980823152ULL, {1439980823, 152454}, {1439980823, 152453627}},
+    // 1546167831554815222 / 2^30 = 1439981005.6712620165...
+    {1546167831554815222ULL, 1439981005.671, 1439981006, 1439981005671ULL, {1439981005, 671262}, {1439981005, 671262017}},
+    // 1546167986577716567 / 2^30 = 1439981150.0475896215...
+    {1546167986577716567ULL, 1439981150.048, 1439981150, 1439981150048ULL, {1439981150,  47590}, {1439981005,  47589622}},
+  };
+  size_t i;
+
+  for (i = 0; i < (sizeof (cases) / sizeof (cases[0])); i++) {
+    struct timeval tv;
+    struct timespec ts;
+
+    // cdtime -> s
+    EXPECT_EQ_UINT64 (cases[i].tt, CDTIME_T_TO_TIME_T (cases[i].t));
+
+    // cdtime -> ms
+    EXPECT_EQ_UINT64(cases[i].ms, CDTIME_T_TO_MS (cases[i].t));
+
+    // cdtime -> us
+    CDTIME_T_TO_TIMEVAL (cases[i].t, &tv);
+    EXPECT_EQ_UINT64 (cases[i].tv.tv_usec, tv.tv_usec);
+
+    // cdtime -> ns
+    CDTIME_T_TO_TIMESPEC (cases[i].t, &ts);
+    EXPECT_EQ_UINT64 (cases[i].ts.tv_nsec, ts.tv_nsec);
+
+    // cdtime -> double
+    EXPECT_EQ_DOUBLE (cases[i].d, CDTIME_T_TO_DOUBLE (cases[i].t));
+  }
+
+  return 0;
+}
+
+/* These cases test the ns -> cdtime_t conversion rounds correctly. */
+DEF_TEST(ns_to_cdtime)
+{
+  struct {
+    uint64_t ns;
+    cdtime_t want;
+  } cases[] = {
+    // 1439981652801860766 * 2^30 / 10^9 = 1546168526406004689.4
+    {1439981652801860766ULL, 1546168526406004689ULL},
+    // 1439981836985281914 * 2^30 / 10^9 = 1546168724171447263.4
+    {1439981836985281914ULL, 1546168724171447263ULL},
+    // 1439981880053705608 * 2^30 / 10^9 = 1546168770415815077.4
+    {1439981880053705608ULL, 1546168770415815077ULL},
+  };
+  size_t i;
+
+  for (i = 0; i < (sizeof (cases) / sizeof (cases[0])); i++) {
+    EXPECT_EQ_UINT64 (cases[i].want, NS_TO_CDTIME_T (cases[i].ns));
+  }
+
+  return 0;
+}
+
+int main (void)
+{
+  RUN_TEST(conversion);
+  RUN_TEST(ns_to_cdtime);
+
+  END_TEST;
+}
+
+/* vim: set sw=2 sts=2 et : */
index c851ba2b121dc272874e513a18eb26ea888178e7..94d0762d261fada2a4ebda04278f43947dc0b006 100644 (file)
--- a/src/dbi.c
+++ b/src/dbi.c
@@ -64,6 +64,8 @@ struct cdbi_database_s /* {{{ */
   char *name;
   char *select_db;
 
+  cdtime_t interval;
+
   char *driver;
   char *host;
   cdbi_driver_option_t *driver_options;
@@ -215,6 +217,7 @@ static void cdbi_database_free (cdbi_database_t *db) /* {{{ */
  *     
  *   <Database "plugin_instance1">
  *     Driver "mysql"
+ *     Interval 120
  *     DriverOption "hostname" "localhost"
  *     ...
  *     Query "plugin_instance0"
@@ -322,6 +325,8 @@ static int cdbi_config_add_database (oconfig_item_t *ci) /* {{{ */
           &db->queries, &db->queries_num);
     else if (strcasecmp ("Host", child->key) == 0)
       status = cf_util_get_string (child, &db->host);
+    else if (strcasecmp ("Interval", child->key) == 0)
+      status = cf_util_get_cdtime(child, &db->interval);
     else
     {
       WARNING ("dbi plugin: Option `%s' not allowed here.", child->key);
@@ -407,7 +412,7 @@ static int cdbi_config_add_database (oconfig_item_t *ci) /* {{{ */
       plugin_register_complex_read (/* group = */ NULL,
           /* name = */ name ? name : db->name,
           /* callback = */ cdbi_read_database,
-          /* interval = */ 0,
+          /* interval = */ (db->interval > 0) ? db->interval : 0,
           /* user_data = */ &ud);
       free (name);
     }
@@ -597,7 +602,7 @@ static int cdbi_read_database_query (cdbi_database_t *db, /* {{{ */
 
   udb_query_prepare_result (q, prep_area, (db->host ? db->host : hostname_g),
       /* plugin = */ "dbi", db->name,
-      column_names, column_num, /* interval = */ 0);
+      column_names, column_num, /* interval = */ (db->interval > 0) ? db->interval : 0);
 
   /* 0 = error; 1 = success; */
   status = dbi_result_first_row (res); /* {{{ */
index fd75dc93a9437fb9bd0d7a580c1937e26f19b859..3421c475d7e6fc49c2419332dbcd8e5d3dd09f06 100644 (file)
--- a/src/dns.c
+++ b/src/dns.c
@@ -34,7 +34,6 @@
 #include <poll.h>
 
 #include <pcap.h>
-#include <pcap-bpf.h>
 
 /*
  * Private data types
old mode 100644 (file)
new mode 100755 (executable)
index 8d737ce..f080ad6
@@ -355,6 +355,31 @@ static void reset_signal_mask (void) /* {{{ */
   sigprocmask (SIG_SETMASK, &ss, /* old mask = */ NULL);
 } /* }}} void reset_signal_mask */
 
+static int create_pipe (int fd_pipe[2]) /* {{{ */
+{
+  char errbuf[1024];
+  int status;
+
+  status = pipe (fd_pipe);
+  if (status != 0)
+  {
+    ERROR ("exec plugin: pipe failed: %s",
+        sstrerror (errno, errbuf, sizeof (errbuf)));
+    return (-1);
+  }
+
+  return 0;
+} /* }}} int create_pipe */
+
+static void close_pipe (int fd_pipe[2]) /* {{{ */
+{
+  if (fd_pipe[0] != -1)
+    close (fd_pipe[0]);
+
+  if (fd_pipe[1] != -1)
+    close (fd_pipe[1]);
+} /* }}} void close_pipe */
+
 /*
  * Creates three pipes (one for reading, one for writing and one for errors),
  * forks a child, sets up the pipes so that fd_in is connected to STDIN of
@@ -363,9 +388,9 @@ static void reset_signal_mask (void) /* {{{ */
  */
 static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err) /* {{{ */
 {
-  int fd_pipe_in[2];
-  int fd_pipe_out[2];
-  int fd_pipe_err[2];
+  int fd_pipe_in[2] = {-1, -1};
+  int fd_pipe_out[2] = {-1, -1};
+  int fd_pipe_err[2] = {-1, -1};
   char errbuf[1024];
   int status;
   int pid;
@@ -381,29 +406,10 @@ static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err)
   if (pl->pid != 0)
     return (-1);
 
-  status = pipe (fd_pipe_in);
-  if (status != 0)
-  {
-    ERROR ("exec plugin: pipe failed: %s",
-        sstrerror (errno, errbuf, sizeof (errbuf)));
-    return (-1);
-  }
-
-  status = pipe (fd_pipe_out);
-  if (status != 0)
-  {
-    ERROR ("exec plugin: pipe failed: %s",
-        sstrerror (errno, errbuf, sizeof (errbuf)));
-    return (-1);
-  }
-
-  status = pipe (fd_pipe_err);
-  if (status != 0)
-  {
-    ERROR ("exec plugin: pipe failed: %s",
-        sstrerror (errno, errbuf, sizeof (errbuf)));
-    return (-1);
-  }
+  if ((create_pipe(fd_pipe_in) == -1)
+      || (create_pipe(fd_pipe_out) == -1)
+      || (create_pipe(fd_pipe_err) == -1))
+    goto failed;
 
   sp_ptr = NULL;
   status = getpwnam_r (pl->user, &sp, nambuf, sizeof (nambuf), &sp_ptr);
@@ -411,12 +417,13 @@ static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err)
   {
     ERROR ("exec plugin: Failed to get user information for user ``%s'': %s",
         pl->user, sstrerror (errno, errbuf, sizeof (errbuf)));
-    return (-1);
+    goto failed;
   }
+
   if (sp_ptr == NULL)
   {
     ERROR ("exec plugin: No such user: `%s'", pl->user);
-    return (-1);
+    goto failed;
   }
 
   uid = sp.pw_uid;
@@ -424,7 +431,7 @@ static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err)
   if (uid == 0)
   {
     ERROR ("exec plugin: Cowardly refusing to exec program as root.");
-    return (-1);
+    goto failed;
   }
 
   /* The group configured in the configfile is set as effective group, because
@@ -442,12 +449,12 @@ static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err)
         ERROR ("exec plugin: Failed to get group information "
             "for group ``%s'': %s", pl->group,
             sstrerror (errno, errbuf, sizeof (errbuf)));
-        return (-1);
+        goto failed;
       }
       if (NULL == gr_ptr)
       {
         ERROR ("exec plugin: No such group: `%s'", pl->group);
-        return (-1);
+        goto failed;
       }
 
       egid = gr.gr_gid;
@@ -463,7 +470,7 @@ static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err)
   {
     ERROR ("exec plugin: fork failed: %s",
         sstrerror (errno, errbuf, sizeof (errbuf)));
-    return (-1);
+    goto failed;
   }
   else if (pid == 0)
   {
@@ -531,6 +538,13 @@ static int fork_child (program_list_t *pl, int *fd_in, int *fd_out, int *fd_err)
     close (fd_pipe_err[0]);
 
   return (pid);
+
+failed:
+  close_pipe(fd_pipe_in);
+  close_pipe(fd_pipe_out);
+  close_pipe(fd_pipe_err);
+
+  return (-1);
 } /* int fork_child }}} */
 
 static int parse_line (char *buffer) /* {{{ */
index 5abee2f1a44f1fd0abdce185c1cb390ffd00aeab..e81a59438394960ab8cb6b4b0c0e40a30ca6befa 100644 (file)
@@ -1,9 +1,5 @@
 AUTOMAKE_OPTIONS = foreign no-dependencies
 
-if COMPILER_IS_GCC
-AM_CFLAGS = -Wall -Werror
-endif
-
 pkginclude_HEADERS = collectd/client.h collectd/network.h collectd/network_buffer.h collectd/lcc_features.h
 lib_LTLIBRARIES = libcollectdclient.la
 nodist_pkgconfig_DATA = libcollectdclient.pc
index 638e3a232b3c688970194231b938c911a58b4186..41d66438dd86e1176621034734d4666a29e0d773 100644 (file)
@@ -28,6 +28,7 @@
 
 %{
 #include <stdlib.h>
+#include <string.h>
 #include "oconfig.h"
 #include "aux_types.h"
 #include "parser.h"
index 2883e6c97d2872ac8e4e396cdedbe849e4effce5..2d5f6203802852b0bf7174eaf0ab8c22bdf237a9 100644 (file)
@@ -147,7 +147,7 @@ static void log_logstash_print (yajl_gen g, int severity,
         * format time as a UTC ISO 8601 compliant string
         */
        strftime (timestamp_str, sizeof (timestamp_str),
-                 "%Y-%m-%d %H:%M:%SZ", &timestamp_tm);
+                 "%Y-%m-%dT%H:%M:%SZ", &timestamp_tm);
        timestamp_str[sizeof (timestamp_str) - 1] = '\0';
 
        if (yajl_gen_string(g, (u_char *)timestamp_str,
index fb2f3d38a4045fd8790160a1155ed04cda33ab23..ea16ce315f102126d7ca0f497ea8d153fb6c2339 100644 (file)
@@ -76,6 +76,7 @@ static vm_size_t pagesize;
 #elif HAVE_LIBKSTAT
 static int pagesize;
 static kstat_t *ksp;
+static kstat_t *ksz;
 /* #endif HAVE_LIBKSTAT */
 
 #elif HAVE_SYSCTL
@@ -137,6 +138,12 @@ static int memory_init (void)
                ksp = NULL;
                return (-1);
        }
+       if (get_kstat (&ksz, "zfs", 0, "arcstats") != 0)
+       {
+               ksz = NULL;
+               return (-1);
+       }
+
 /* #endif HAVE_LIBKSTAT */
 
 #elif HAVE_SYSCTL
@@ -371,6 +378,8 @@ static int memory_read_internal (value_list_t *vl)
        long long mem_lock;
        long long mem_kern;
        long long mem_unus;
+       long long arcsize;
+
 
        long long pp_kernel;
        long long physmem;
@@ -378,17 +387,20 @@ static int memory_read_internal (value_list_t *vl)
 
        if (ksp == NULL)
                return (-1);
+       if (ksz == NULL)
+               return (-1);
 
        mem_used = get_kstat_value (ksp, "pagestotal");
        mem_free = get_kstat_value (ksp, "pagesfree");
        mem_lock = get_kstat_value (ksp, "pageslocked");
-       mem_kern = 0;
-       mem_unus = 0;
-
+       arcsize = get_kstat_value (ksz, "size");
        pp_kernel = get_kstat_value (ksp, "pp_kernel");
        physmem = get_kstat_value (ksp, "physmem");
        availrmem = get_kstat_value (ksp, "availrmem");
 
+       mem_kern = 0;
+       mem_unus = 0;
+
        if ((mem_used < 0LL) || (mem_free < 0LL) || (mem_lock < 0LL))
        {
                WARNING ("memory plugin: one of used, free or locked is negative.");
@@ -431,11 +443,14 @@ static int memory_read_internal (value_list_t *vl)
        mem_lock *= pagesize; /* some? ;) */
        mem_kern *= pagesize; /* it's 2011 RAM is cheap */
        mem_unus *= pagesize;
+       mem_kern -= arcsize;
+
 
        MEMORY_SUBMIT ("used",     (gauge_t) mem_used,
                       "free",     (gauge_t) mem_free,
                       "locked",   (gauge_t) mem_lock,
                       "kernel",   (gauge_t) mem_kern,
+                      "arc",      (gauge_t) arcsize,
                       "unusable", (gauge_t) mem_unus);
 /* #endif HAVE_LIBKSTAT */
 
index 210d38cbef7d9b0fd89e2863eee88042bc3ebd2a..7003fcc63e19b08d775d1c258e058383c3061389 100644 (file)
@@ -24,6 +24,7 @@
  * Authors:
  *   Marc Falzon <marc at baha dot mu>
  *   Florian octo Forster <octo at collectd.org>
+ *   Jan-Piet Mens <jpmens at gmail.com>
  **/
 
 // Reference: http://mosquitto.org/api/files/mosquitto-h.html
@@ -48,6 +49,9 @@
 #ifndef MQTT_KEEPALIVE
 # define MQTT_KEEPALIVE 60
 #endif
+#ifndef SSL_VERIFY_PEER
+# define SSL_VERIFY_PEER  1
+#endif
 
 
 /*
@@ -67,6 +71,11 @@ struct mqtt_client_conf
     char               *username;
     char               *password;
     int                 qos;
+    char                *cacertificatefile;
+    char                *certificatefile;
+    char                *certificatekeyfile;
+    char                *tlsprotocol;
+    char                *ciphersuite;
 
     /* For publishing */
     char               *topic_prefix;
@@ -176,9 +185,10 @@ static void on_message (
     char *payload;
     int status;
 
-    if ((msg->payloadlen <= 0)
-            || (((uint8_t *) msg->payload)[msg->payloadlen - 1] != 0))
+    if (msg->payloadlen <= 0) {
+        DEBUG ("mqtt plugin: message has empty payload");
         return;
+    }
 
     topic = strdup (msg->topic);
     name = strip_prefix (topic);
@@ -207,7 +217,15 @@ static void on_message (
     }
     vl.values_len = ds->ds_num;
 
-    payload = strdup ((void *) msg->payload);
+    payload = malloc (msg->payloadlen+1);
+    if (payload == NULL)
+    {
+        ERROR ("mqtt plugin: malloc for payload buffer failed.");
+        return;
+    }
+    memmove (payload, msg->payload, msg->payloadlen);
+    payload[msg->payloadlen] = 0;
+
     DEBUG ("mqtt plugin: payload = \"%s\"", payload);
     status = parse_values (payload, &vl, ds);
     if (status != 0)
@@ -277,6 +295,35 @@ static int mqtt_connect (mqtt_client_conf_t *conf)
         return (-1);
     }
 
+#if LIBMOSQUITTO_MAJOR != 0
+    if (conf->cacertificatefile) {
+        status = mosquitto_tls_set(conf->mosq, conf->cacertificatefile, NULL,
+                                  conf->certificatefile, conf->certificatekeyfile, /* pw_callback */NULL);
+        if (status != MOSQ_ERR_SUCCESS) {
+            ERROR ("mqtt plugin: cannot mosquitto_tls_set: %s", mosquitto_strerror(status));
+            mosquitto_destroy (conf->mosq);
+            conf->mosq = NULL;
+            return (-1);
+        }
+
+        status = mosquitto_tls_opts_set(conf->mosq, SSL_VERIFY_PEER, conf->tlsprotocol, conf->ciphersuite);
+        if (status != MOSQ_ERR_SUCCESS) {
+            ERROR ("mqtt plugin: cannot mosquitto_tls_opts_set: %s", mosquitto_strerror(status));
+            mosquitto_destroy (conf->mosq);
+            conf->mosq = NULL;
+            return (-1);
+        }
+
+        status = mosquitto_tls_insecure_set(conf->mosq, false);
+        if (status != MOSQ_ERR_SUCCESS) {
+            ERROR ("mqtt plugin: cannot mosquitto_tls_insecure_set: %s", mosquitto_strerror(status));
+            mosquitto_destroy (conf->mosq);
+            conf->mosq = NULL;
+            return (-1);
+        }
+    }
+#endif
+
     if (conf->username && conf->password)
     {
         status = mosquitto_username_pw_set (conf->mosq, conf->username, conf->password);
@@ -407,11 +454,11 @@ static int publish (mqtt_client_conf_t *conf, char const *topic,
     {
         char errbuf[1024];
         c_complain (LOG_ERR,
-                &conf->complaint_cantpublish,
-                "plugin mqtt: mosquitto_publish failed: %s",
-                status == MOSQ_ERR_ERRNO ?
-                sstrerror(errno, errbuf, sizeof (errbuf)) :
-                mosquitto_strerror(status));
+            &conf->complaint_cantpublish,
+            "mqtt plugin: mosquitto_publish failed: %s",
+            (status == MOSQ_ERR_ERRNO)
+            ? sstrerror(errno, errbuf, sizeof (errbuf))
+            : mosquitto_strerror(status));
         /* Mark our connection "down" regardless of the error as a safety
          * measure; we will try to reconnect the next time we have to publish a
          * message */
@@ -494,6 +541,10 @@ static int mqtt_write (const data_set_t *ds, const value_list_t *vl,
  *   StoreRates true
  *   Retain false
  *   QoS 0
+ *   CACert "ca.pem"                   Enables TLS if set
+ *   CertificateFile "client-cert.pem"         optional
+ *   CertificateKeyFile "client-key.pem"               optional
+ *   TLSProtocol "tlsv1.2"             optional
  * </Publish>
  */
 static int mqtt_config_publisher (oconfig_item_t *ci)
@@ -527,6 +578,13 @@ static int mqtt_config_publisher (oconfig_item_t *ci)
     conf->topic_prefix = strdup (MQTT_DEFAULT_TOPIC_PREFIX);
     conf->store_rates = 1;
 
+    status = pthread_mutex_init (&conf->lock, NULL);
+    if (status != 0)
+    {
+      mqtt_free (conf);
+      return (status);
+    }
+
     C_COMPLAIN_INIT (&conf->complaint_cantpublish);
 
     for (i = 0; i < ci->children_num; i++)
@@ -563,6 +621,16 @@ static int mqtt_config_publisher (oconfig_item_t *ci)
             cf_util_get_boolean (child, &conf->store_rates);
         else if (strcasecmp ("Retain", child->key) == 0)
             cf_util_get_boolean (child, &conf->retain);
+        else if (strcasecmp ("CACert", child->key) == 0)
+            cf_util_get_string (child, &conf->cacertificatefile);
+        else if (strcasecmp ("CertificateFile", child->key) == 0)
+            cf_util_get_string (child, &conf->certificatefile);
+        else if (strcasecmp ("CertificateKeyFile", child->key) == 0)
+            cf_util_get_string (child, &conf->certificatekeyfile);
+        else if (strcasecmp ("TLSProtocol", child->key) == 0)
+            cf_util_get_string (child, &conf->tlsprotocol);
+        else if (strcasecmp ("CipherSuite", child->key) == 0)
+            cf_util_get_string (child, &conf->ciphersuite);
         else
             ERROR ("mqtt plugin: Unknown config option: %s", child->key);
     }
@@ -583,7 +651,7 @@ static int mqtt_config_publisher (oconfig_item_t *ci)
  *   User "guest"
  *   Password "secret"
  *   Topic "collectd/#"
- * </Publish>
+ * </Subscribe>
  */
 static int mqtt_config_subscriber (oconfig_item_t *ci)
 {
@@ -615,6 +683,13 @@ static int mqtt_config_subscriber (oconfig_item_t *ci)
     conf->topic = strdup (MQTT_DEFAULT_TOPIC);
     conf->clean_session = 1;
 
+    status = pthread_mutex_init (&conf->lock, NULL);
+    if (status != 0)
+    {
+      mqtt_free (conf);
+      return (status);
+    }
+
     C_COMPLAIN_INIT (&conf->complaint_cantpublish);
 
     for (i = 0; i < ci->children_num; i++)
index 4e4ce3bbc6115572873668a76507f80ccd82b316..69ec06dc996edc9452ea565776c9d9d70c241e68 100644 (file)
@@ -188,8 +188,7 @@ static int init (void)
   }
   else
   {
-    curl_easy_setopt (curl, CURLOPT_TIMEOUT_MS,
-       CDTIME_T_TO_MS(plugin_get_interval()));
+    curl_easy_setopt (curl, CURLOPT_TIMEOUT_MS, (long) CDTIME_T_TO_MS(plugin_get_interval()));
   }
 #endif
 
index d11bd8aaedabb6c2b5232009671007218156a0a3..a2bd5499916d735a3ec8143e93c8d79caa3485cf 100644 (file)
--- a/src/pf.c
+++ b/src/pf.c
@@ -29,6 +29,9 @@
 #if HAVE_NET_IF_H
 # include <net/if.h>
 #endif
+#if HAVE_NETINET_IN_H
+# include <netinet/in.h>
+#endif
 
 #include <net/pfvar.h>
 
index 24dbf49299edfcaa964ce54fd8a5cf6ce7d695fd..d094e73ec005830f6937a6b94eb4d65ce81c7c38 100644 (file)
@@ -2027,18 +2027,18 @@ static int ps_read (void)
                        pse.io_syscw = -1;
 
                        ps_list_add (procs[i].ki_comm, have_cmdline ? cmdline : NULL, &pse);
-               } /* if ((proc_ptr == NULL) || (proc_ptr->ki_pid != procs[i].ki_pid)) */
 
-               switch (procs[i].ki_stat)
-               {
-                       case SSTOP:     stopped++;      break;
-                       case SSLEEP:    sleeping++;     break;
-                       case SRUN:      running++;      break;
-                       case SIDL:      idle++;         break;
-                       case SWAIT:     wait++;         break;
-                       case SLOCK:     blocked++;      break;
-                       case SZOMB:     zombies++;      break;
-               }
+                       switch (procs[i].ki_stat)
+                       {
+                               case SSTOP:     stopped++;      break;
+                               case SSLEEP:    sleeping++;     break;
+                               case SRUN:      running++;      break;
+                               case SIDL:      idle++;         break;
+                               case SWAIT:     wait++;         break;
+                               case SLOCK:     blocked++;      break;
+                               case SZOMB:     zombies++;      break;
+                       }
+               } /* if ((proc_ptr == NULL) || (proc_ptr->ki_pid != procs[i].ki_pid)) */
        }
 
        kvm_close(kd);
@@ -2163,18 +2163,18 @@ static int ps_read (void)
                        pse.cswitch_invol = -1;
 
                        ps_list_add (procs[i].p_comm, have_cmdline ? cmdline : NULL, &pse);
-               } /* if ((proc_ptr == NULL) || (proc_ptr->p_pid != procs[i].p_pid)) */
 
-               switch (procs[i].p_stat)
-               {
-                       case SSTOP:     stopped++;      break;
-                       case SSLEEP:    sleeping++;     break;
-                       case SRUN:      running++;      break;
-                       case SIDL:      idle++;         break;
-                       case SONPROC:   onproc++;       break;
-                       case SDEAD:     dead++;         break;
-                       case SZOMB:     zombies++;      break;
-               }
+                       switch (procs[i].p_stat)
+                       {
+                               case SSTOP:     stopped++;      break;
+                               case SSLEEP:    sleeping++;     break;
+                               case SRUN:      running++;      break;
+                               case SIDL:      idle++;         break;
+                               case SONPROC:   onproc++;       break;
+                               case SDEAD:     dead++;         break;
+                               case SZOMB:     zombies++;      break;
+                       }
+               } /* if ((proc_ptr == NULL) || (proc_ptr->p_pid != procs[i].p_pid)) */
        }
 
        kvm_close(kd);
index b7cc5b9150e4b10eef61e251218258124da95c2b..210d785c847d9d5b6e5577efdca0001163ffd9c7 100644 (file)
@@ -302,7 +302,7 @@ void cpy_log_exception(const char *context) {
                Py_XDECREF(traceback);
                return;
        }
-       list = PyObject_CallFunction(cpy_format_exception, "NNN", type, value, traceback); /* New reference. */
+       list = PyObject_CallFunction(cpy_format_exception, "NNN", type, value, traceback); /* New reference. Steals references from "type", "value" and "traceback". */
        if (list)
                l = PyObject_Length(list);
        for (i = 0; i < l; ++i) {
@@ -322,9 +322,6 @@ void cpy_log_exception(const char *context) {
        }
        Py_XDECREF(list);
        PyErr_Clear();
-       Py_DECREF(type);
-       Py_XDECREF(value);
-       Py_XDECREF(traceback);
 }
 
 static int cpy_read_callback(user_data_t *data) {
index d9a932a393ba65e33be5c3970046326d5df6c0e8..6a03a19dd8603adfca9b16001b7296ce1352d352 100644 (file)
@@ -924,8 +924,7 @@ static value_t csnmp_value_list_to_value (struct variable_list *vl, int type,
     tmp_unsigned = (uint32_t) *vl->val.integer;
     tmp_signed = (int32_t) *vl->val.integer;
 
-    if ((vl->type == ASN_INTEGER)
-        || (vl->type == ASN_GAUGE))
+    if (vl->type == ASN_INTEGER)
       prefer_signed = 1;
 
     DEBUG ("snmp plugin: Parsed int32 value is %"PRIu64".", tmp_unsigned);
@@ -1681,7 +1680,7 @@ static int csnmp_read_value (host_definition_t *host, data_definition_t *data)
 
   if (host->sess_handle == NULL)
   {
-    DEBUG ("snmp plugin: csnmp_read_table: host->sess_handle == NULL");
+    DEBUG ("snmp plugin: csnmp_read_value: host->sess_handle == NULL");
     return (-1);
   }
 
index 9a6da1d34fafafa49f2681149e5d7161176a613e..8047b1a68911e69fda55b0073a90102d997c195e 100644 (file)
@@ -850,8 +850,19 @@ static int statsd_metric_submit_unsafe (char const *name, /* {{{ */
     else
       values[0].gauge = (gauge_t) c_avl_size (metric->set);
   }
-  else
-    values[0].derive = (derive_t) metric->value;
+  else { /* STATSD_COUNTER */
+      /*
+       * Expand a single value to two metrics:
+       *
+       * - The absolute counter, as a gauge
+       * - A derived rate for this counter
+       */
+      values[0].derive = (derive_t) metric->value;
+      plugin_dispatch_values(&vl);
+
+      sstrncpy(vl.type, "gauge", sizeof (vl.type));
+      values[0].gauge = (gauge_t) metric->value;
+  }
 
   return (plugin_dispatch_values (&vl));
 } /* }}} int statsd_metric_submit_unsafe */
@@ -941,7 +952,7 @@ static int statsd_shutdown (void) /* {{{ */
   while (c_avl_pick (metrics_tree, &key, &value) == 0)
   {
     sfree (key);
-    sfree (value);
+    statsd_metric_free (value);
   }
   c_avl_destroy (metrics_tree);
   metrics_tree = NULL;
index b0bc95f80bb90c5f999c525d17aa9d94bbc1d8b7..4e34a9ec718ed9e90683981c93eb8a5bbc2c1588 100644 (file)
@@ -458,7 +458,7 @@ static int tbl_parse_line (tbl_t *tbl, char *line, size_t len)
        }
 
        if (i <= tbl->max_colnum) {
-               log_err ("Not enough columns in line "
+               log_warn ("Not enough columns in line "
                                "(expected at least %zu, got %zu).",
                                tbl->max_colnum + 1, i);
                return -1;
@@ -490,11 +490,11 @@ static int tbl_read_table (tbl_t *tbl)
        while (NULL != fgets (buf, sizeof (buf), fh)) {
                if ('\0' != buf[sizeof (buf) - 1]) {
                        buf[sizeof (buf) - 1] = '\0';
-                       log_err ("Table %s: Truncated line: %s", tbl->file, buf);
+                       log_warn ("Table %s: Truncated line: %s", tbl->file, buf);
                }
 
                if (0 != tbl_parse_line (tbl, buf, sizeof (buf))) {
-                       log_err ("Table %s: Failed to parse line: %s", tbl->file, buf);
+                       log_warn ("Table %s: Failed to parse line: %s", tbl->file, buf);
                        continue;
                }
        }
index 84a1242953284309fe015df0ee6c43d95e6ba434..0c415e48909f96db0d8844e3f422cdd7325d86a1 100644 (file)
@@ -24,6 +24,8 @@
  *   Florian octo Forster <octo at collectd.org>
  */
 
+#include <inttypes.h>
+
 static int fail_count__ = 0;
 static int check_count__ = 0;
 
@@ -50,36 +52,50 @@ static int check_count__ = 0;
 } while (0)
 #define OK(cond) OK1(cond, #cond)
 
-#define STREQ(expect, actual) do { \
+#define EXPECT_EQ_STR(expect, actual) do { \
   if (strcmp (expect, actual) != 0) { \
-    printf ("not ok %i - %s incorrect: expected \"%s\", got \"%s\"\n", \
-        ++check_count__, #actual, expect, actual); \
+    printf ("not ok %i - %s = \"%s\", want \"%s\"\n", \
+        ++check_count__, #actual, actual, expect); \
+    return (-1); \
+  } \
+  printf ("ok %i - %s = \"%s\"\n", ++check_count__, #actual, actual); \
+} while (0)
+
+#define EXPECT_EQ_INT(expect, actual) do { \
+  int want__ = (int) expect; \
+  int got__  = (int) actual; \
+  if (got__ != want__) { \
+    printf ("not ok %i - %s = %d, want %d\n", \
+        ++check_count__, #actual, got__, want__); \
     return (-1); \
   } \
-  printf ("ok %i - %s evaluates to \"%s\"\n", ++check_count__, #actual, expect); \
+  printf ("ok %i - %s = %d\n", ++check_count__, #actual, got__); \
 } while (0)
 
-#define EXPECT_INTEQ(expect, actual) do { \
-  if ((expect) != (actual)) {\
-    printf ("not ok %i - %s incorrect: expected %d, got %d\n", \
-        ++check_count__, #actual, expect, actual); \
+#define EXPECT_EQ_UINT64(expect, actual) do { \
+  uint64_t want__ = (uint64_t) expect; \
+  uint64_t got__  = (uint64_t) actual; \
+  if (got__ != want__) { \
+    printf ("not ok %i - %s = %"PRIu64", want %"PRIu64"\n", \
+        ++check_count__, #actual, got__, want__); \
     return (-1); \
   } \
-  printf ("ok %i - %s evaluates to %d\n", ++check_count__, #actual, expect); \
+  printf ("ok %i - %s = %"PRIu64"\n", ++check_count__, #actual, got__); \
 } while (0)
 
-#define DBLEQ(expect, actual) do { \
-  double e = (expect); double a = (actual); \
-  if (isnan (e) && !isnan (a)) { \
-    printf ("not ok %i - %s incorrect: expected %.15g, got %.15g\n", \
-        ++check_count__, #actual, e, a); \
+#define EXPECT_EQ_DOUBLE(expect, actual) do { \
+  double want__ = (double) expect; \
+  double got__  = (double) actual; \
+  if (isnan (want__) && !isnan (got__)) { \
+    printf ("not ok %i - %s = %.15g, want %.15g\n", \
+        ++check_count__, #actual, got__, want__); \
     return (-1); \
-  } else if (!isnan (e) && (((e-a) < -DBL_PRECISION) || ((e-a) > DBL_PRECISION))) { \
-    printf ("not ok %i - %s incorrect: expected %.15g, got %.15g\n", \
-        ++check_count__, #actual, e, a); \
+  } else if (!isnan (want__) && (((want__-got__) < -DBL_PRECISION) || ((want__-got__) > DBL_PRECISION))) { \
+    printf ("not ok %i - %s = %.15g, want %.15g\n", \
+        ++check_count__, #actual, got__, want__); \
     return (-1); \
   } \
-  printf ("ok %i - %s evaluates to %.15g\n", ++check_count__, #actual, e); \
+  printf ("ok %i - %s = %.15g\n", ++check_count__, #actual, got__); \
 } while (0)
 
 #define CHECK_NOT_NULL(expr) do { \
index 38fb546c867170f43eada049718786e46e6a1060..5847218aa0fe1cb17a057e98bd596849cc7af4ce 100644 (file)
@@ -14,7 +14,8 @@ cache_eviction                value:DERIVE:0:U
 cache_operation                value:DERIVE:0:U
 cache_ratio            value:GAUGE:0:100
 cache_result           value:DERIVE:0:U
-cache_size             value:GAUGE:0:U
+cache_size             value:GAUGE:0:1125899906842623
+capacity       value:GAUGE:0:U
 ceph_bytes             value:GAUGE:U:U
 ceph_latency   value:GAUGE:U:U
 ceph_rate                      value:DERIVE:0:U
diff --git a/src/utils_ignorelist.c b/src/utils_ignorelist.c
deleted file mode 100644 (file)
index a8ca7db..0000000
+++ /dev/null
@@ -1,338 +0,0 @@
-/**
- * collectd - src/utils_ignorelist.c
- * Copyright (C) 2006 Lubos Stanek <lubek at users.sourceforge.net>
- * Copyright (C) 2008 Florian Forster <octo at collectd.org>
- *
- * This program is free software; you can redistribute it and/
- * or modify it under the terms of the GNU General Public Li-
- * cence as published by the Free Software Foundation; either
- * version 2 of the Licence, or any later version.
- *
- * This program is distributed in the hope that it will be use-
- * ful, but WITHOUT ANY WARRANTY; without even the implied war-
- * ranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public Licence for more details.
- *
- * You should have received a copy of the GNU General Public
- * Licence along with this program; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139,
- * USA.
- *
- * Authors:
- *   Lubos Stanek <lubek at users.sourceforge.net>
- *   Florian Forster <octo at collectd.org>
- **/
-/**
- * ignorelist handles plugin's list of configured collectable
- * entries with global ignore action
- **/
-/**
- * Usage:
- * 
- * Define plugin's global pointer variable of type ignorelist_t:
- *   ignorelist_t *myconfig_ignore;
- * If you know the state of the global ignore (IgnoreSelected),
- * allocate the variable with:
- *   myconfig_ignore = ignorelist_create (YourKnownIgnore);
- * If you do not know the state of the global ignore,
- * initialize the global variable and set the ignore flag later:
- *   myconfig_ignore = ignorelist_init ();
- * Append single entries in your cf_register'ed callback function:
- *   ignorelist_add (myconfig_ignore, newentry);
- * When you hit the IgnoreSelected config option,
- * offer it to the list:
- *   ignorelist_ignore (myconfig_ignore, instantly_got_value_of_ignore);
- * That is all for the ignorelist initialization.
- * Later during read and write (plugin's registered functions) get
- * the information whether this entry would be collected or not:
- *   if (ignorelist_match (myconfig_ignore, thisentry))
- *     return;
- **/
-
-#if HAVE_CONFIG_H
-# include "config.h"
-#endif
-
-#include "common.h"
-#include "plugin.h"
-#include "utils_ignorelist.h"
-
-/*
- * private prototypes
- */
-struct ignorelist_item_s
-{
-#if HAVE_REGEX_H
-       regex_t *rmatch;        /* regular expression entry identification */
-#endif
-       char *smatch;           /* string entry identification */
-       struct ignorelist_item_s *next;
-};
-typedef struct ignorelist_item_s ignorelist_item_t;
-
-struct ignorelist_s
-{
-       int ignore;             /* ignore entries */
-       ignorelist_item_t *head;        /* pointer to the first entry */
-};
-
-/* *** *** *** ********************************************* *** *** *** */
-/* *** *** *** *** *** ***   private functions   *** *** *** *** *** *** */
-/* *** *** *** ********************************************* *** *** *** */
-
-static inline void ignorelist_append (ignorelist_t *il, ignorelist_item_t *item)
-{
-       assert ((il != NULL) && (item != NULL));
-
-       item->next = il->head;
-       il->head = item;
-}
-
-#if HAVE_REGEX_H
-static int ignorelist_append_regex(ignorelist_t *il, const char *re_str)
-{
-       regex_t *re;
-       ignorelist_item_t *entry;
-       int status;
-
-       re = malloc (sizeof (*re));
-       if (re == NULL)
-       {
-               ERROR ("utils_ignorelist: malloc failed");
-               return (ENOMEM);
-       }
-       memset (re, 0, sizeof (*re));
-
-       status = regcomp (re, re_str, REG_EXTENDED);
-       if (status != 0)
-       {
-               char errbuf[1024] = "";
-               regerror (status, re, errbuf, sizeof (errbuf));
-               ERROR ("utils_ignorelist: regcomp failed: %s", errbuf);
-               regfree (re);
-               sfree (re);
-               return (status);
-       }
-
-       entry = malloc (sizeof (*entry));
-       if (entry == NULL)
-       {
-               ERROR ("utils_ignorelist: malloc failed");
-               regfree (re);
-               sfree (re);
-               return (ENOMEM);
-       }
-       memset (entry, 0, sizeof (*entry));
-       entry->rmatch = re;
-
-       ignorelist_append (il, entry);
-       return (0);
-} /* int ignorelist_append_regex */
-#endif
-
-static int ignorelist_append_string(ignorelist_t *il, const char *entry)
-{
-       ignorelist_item_t *new;
-
-       /* create new entry */
-       if ((new = malloc(sizeof(ignorelist_item_t))) == NULL )
-       {
-               ERROR ("cannot allocate new entry");
-               return (1);
-       }
-       memset (new, '\0', sizeof(ignorelist_item_t));
-       new->smatch = sstrdup(entry);
-
-       /* append new entry */
-       ignorelist_append (il, new);
-
-       return (0);
-} /* int ignorelist_append_string(ignorelist_t *il, const char *entry) */
-
-#if HAVE_REGEX_H
-/*
- * check list for entry regex match
- * return 1 if found
- */
-static int ignorelist_match_regex (ignorelist_item_t *item, const char *entry)
-{
-       assert ((item != NULL) && (item->rmatch != NULL)
-                       && (entry != NULL) && (strlen (entry) > 0));
-
-       /* match regex */
-       if (regexec (item->rmatch, entry, 0, NULL, 0) == 0)
-               return (1);
-
-       return (0);
-} /* int ignorelist_match_regex (ignorelist_item_t *item, const char *entry) */
-#endif
-
-/*
- * check list for entry string match
- * return 1 if found
- */
-static int ignorelist_match_string (ignorelist_item_t *item, const char *entry)
-{
-       assert ((item != NULL) && (item->smatch != NULL)
-                       && (entry != NULL) && (strlen (entry) > 0));
-
-       if (strcmp (entry, item->smatch) == 0)
-               return (1);
-
-       return (0);
-} /* int ignorelist_match_string (ignorelist_item_t *item, const char *entry) */
-
-
-/* *** *** *** ******************************************** *** *** *** */
-/* *** *** *** *** *** ***   public functions   *** *** *** *** *** *** */
-/* *** *** *** ******************************************** *** *** *** */
-
-/*
- * create the ignorelist_t with known ignore state
- * return pointer to ignorelist_t
- */
-ignorelist_t *ignorelist_create (int invert)
-{
-       ignorelist_t *il;
-
-       /* smalloc exits if it failes */
-       il = (ignorelist_t *) smalloc (sizeof (ignorelist_t));
-       memset (il, '\0', sizeof (ignorelist_t));
-
-       /*
-        * ->ignore == 0  =>  collect
-        * ->ignore == 1  =>  ignore
-        */
-       il->ignore = invert ? 0 : 1;
-
-       return (il);
-} /* ignorelist_t *ignorelist_create (int ignore) */
-
-/*
- * free memory used by ignorelist_t
- */
-void ignorelist_free (ignorelist_t *il)
-{
-       ignorelist_item_t *this;
-       ignorelist_item_t *next;
-
-       if (il == NULL)
-               return;
-
-       for (this = il->head; this != NULL; this = next)
-       {
-               next = this->next;
-#if HAVE_REGEX_H
-               if (this->rmatch != NULL)
-               {
-                       regfree (this->rmatch);
-                       sfree (this->rmatch);
-                       this->rmatch = NULL;
-               }
-#endif
-               if (this->smatch != NULL)
-               {
-                       sfree (this->smatch);
-                       this->smatch = NULL;
-               }
-               sfree (this);
-       }
-
-       sfree (il);
-       il = NULL;
-} /* void ignorelist_destroy (ignorelist_t *il) */
-
-/*
- * set ignore state of the ignorelist_t
- */
-void ignorelist_set_invert (ignorelist_t *il, int invert)
-{
-       if (il == NULL)
-       {
-               DEBUG("ignore call with ignorelist_t == NULL");
-               return;
-       }
-
-       il->ignore = invert ? 0 : 1;
-} /* void ignorelist_set_invert (ignorelist_t *il, int ignore) */
-
-/*
- * append entry into ignorelist_t
- * return 0 for success
- */
-int ignorelist_add (ignorelist_t *il, const char *entry)
-{
-       size_t entry_len;
-
-       if (il == NULL)
-       {
-               DEBUG ("add called with ignorelist_t == NULL");
-               return (1);
-       }
-
-       entry_len = strlen (entry);
-
-       /* append nothing */
-       if (entry_len == 0)
-       {
-               DEBUG("not appending: empty entry");
-               return (1);
-       }
-
-#if HAVE_REGEX_H
-       /* regex string is enclosed in "/.../" */
-       if ((entry_len > 2) && (entry[0] == '/') && entry[entry_len - 1] == '/')
-       {
-               char *entry_copy;
-               size_t entry_copy_size;
-               int status;
-
-               /* We need to copy `entry' since it's const */
-               entry_copy_size = entry_len - 1;
-               entry_copy = smalloc (entry_copy_size);
-               sstrncpy (entry_copy, entry + 1, entry_copy_size);
-
-               status = ignorelist_append_regex(il, entry_copy);
-               sfree (entry_copy);
-               return status;
-       }
-#endif
-
-       return ignorelist_append_string(il, entry);
-} /* int ignorelist_add (ignorelist_t *il, const char *entry) */
-
-/*
- * check list for entry
- * return 1 for ignored entry
- */
-int ignorelist_match (ignorelist_t *il, const char *entry)
-{
-       ignorelist_item_t *traverse;
-
-       /* if no entries, collect all */
-       if ((il == NULL) || (il->head == NULL))
-               return (0);
-
-       if ((entry == NULL) || (strlen (entry) == 0))
-               return (0);
-
-       /* traverse list and check entries */
-       for (traverse = il->head; traverse != NULL; traverse = traverse->next)
-       {
-#if HAVE_REGEX_H
-               if (traverse->rmatch != NULL)
-               {
-                       if (ignorelist_match_regex (traverse, entry))
-                               return (il->ignore);
-               }
-               else
-#endif
-               {
-                       if (ignorelist_match_string (traverse, entry))
-                               return (il->ignore);
-               }
-       } /* for traverse */
-
-       return (1 - il->ignore);
-} /* int ignorelist_match (ignorelist_t *il, const char *entry) */
-
diff --git a/src/utils_ignorelist.h b/src/utils_ignorelist.h
deleted file mode 100644 (file)
index b47b55a..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/**
- * collectd - src/utils_ignorelist.h
- * Copyright (C) 2006 Lubos Stanek <lubek at users.sourceforge.net>
- *
- * This program is free software; you can redistribute it and/
- * or modify it under the terms of the GNU General Public Li-
- * cence as published by the Free Software Foundation; either
- * version 2 of the Licence, or any later version.
- *
- * This program is distributed in the hope that it will be use-
- * ful, but WITHOUT ANY WARRANTY; without even the implied war-
- * ranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- * See the GNU General Public Licence for more details.
- *
- * You should have received a copy of the GNU General Public
- * Licence along with this program; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139,
- * USA.
- *
- * Authors:
- *   Lubos Stanek <lubek at users.sourceforge.net>
- **/
-/**
- * ignorelist handles plugin's list of configured collectable
- * entries with global ignore action
- **/
-
-#ifndef UTILS_IGNORELIST_H
-#define UTILS_IGNORELIST_H 1
-
-#include "collectd.h"
-
-#if HAVE_REGEX_H
-# include <regex.h>
-#endif
-
-/* public prototypes */
-
-struct ignorelist_s;
-typedef struct ignorelist_s ignorelist_t;
-
-/*
- * create the ignorelist_t with known ignore state
- * return pointer to ignorelist_t
- */
-ignorelist_t *ignorelist_create (int invert);
-
-/*
- * free memory used by ignorelist_t
- */
-void ignorelist_free (ignorelist_t *il);
-
-/*
- * set ignore state of the ignorelist_t
- */
-void ignorelist_set_invert (ignorelist_t *il, int invert);
-
-/*
- * append entry to ignorelist_t
- * returns zero on success, non-zero upon failure.
- */
-int ignorelist_add (ignorelist_t *il, const char *entry);
-
-/*
- * check list for entry
- * return 1 for ignored entry
- */
-int ignorelist_match (ignorelist_t *il, const char *entry);
-
-#endif /* UTILS_IGNORELIST_H */
index b039c54619cdd4caff78a53d041f7e5260a4d044..5769ec9546ed0a85af234d3bf739471955380d57 100644 (file)
@@ -59,10 +59,10 @@ DEF_TEST(simple)
         i, cases[i].val, DOUBLE_TO_CDTIME_T (cases[i].val));
     latency_counter_add (l, DOUBLE_TO_CDTIME_T (cases[i].val));
 
-    DBLEQ (cases[i].min, CDTIME_T_TO_DOUBLE (latency_counter_get_min (l)));
-    DBLEQ (cases[i].max, CDTIME_T_TO_DOUBLE (latency_counter_get_max (l)));
-    DBLEQ (cases[i].sum, CDTIME_T_TO_DOUBLE (latency_counter_get_sum (l)));
-    DBLEQ (cases[i].avg, CDTIME_T_TO_DOUBLE (latency_counter_get_average (l)));
+    EXPECT_EQ_DOUBLE (cases[i].min, CDTIME_T_TO_DOUBLE (latency_counter_get_min (l)));
+    EXPECT_EQ_DOUBLE (cases[i].max, CDTIME_T_TO_DOUBLE (latency_counter_get_max (l)));
+    EXPECT_EQ_DOUBLE (cases[i].sum, CDTIME_T_TO_DOUBLE (latency_counter_get_sum (l)));
+    EXPECT_EQ_DOUBLE (cases[i].avg, CDTIME_T_TO_DOUBLE (latency_counter_get_average (l)));
   }
 
   latency_counter_destroy (l);
@@ -80,15 +80,15 @@ DEF_TEST(percentile)
     latency_counter_add (l, TIME_T_TO_CDTIME_T (((time_t) i) + 1));
   }
 
-  DBLEQ (  1.0, CDTIME_T_TO_DOUBLE (latency_counter_get_min (l)));
-  DBLEQ (100.0, CDTIME_T_TO_DOUBLE (latency_counter_get_max (l)));
-  DBLEQ (100.0 * 101.0 / 2.0, CDTIME_T_TO_DOUBLE (latency_counter_get_sum (l)));
-  DBLEQ ( 50.5, CDTIME_T_TO_DOUBLE (latency_counter_get_average (l)));
+  EXPECT_EQ_DOUBLE (  1.0, CDTIME_T_TO_DOUBLE (latency_counter_get_min (l)));
+  EXPECT_EQ_DOUBLE (100.0, CDTIME_T_TO_DOUBLE (latency_counter_get_max (l)));
+  EXPECT_EQ_DOUBLE (100.0 * 101.0 / 2.0, CDTIME_T_TO_DOUBLE (latency_counter_get_sum (l)));
+  EXPECT_EQ_DOUBLE ( 50.5, CDTIME_T_TO_DOUBLE (latency_counter_get_average (l)));
 
-  DBLEQ (50.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 50.0)));
-  DBLEQ (80.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 80.0)));
-  DBLEQ (95.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 95.0)));
-  DBLEQ (99.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 99.0)));
+  EXPECT_EQ_DOUBLE (50.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 50.0)));
+  EXPECT_EQ_DOUBLE (80.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 80.0)));
+  EXPECT_EQ_DOUBLE (95.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 95.0)));
+  EXPECT_EQ_DOUBLE (99.0, CDTIME_T_TO_DOUBLE (latency_counter_get_percentile (l, 99.0)));
 
   CHECK_ZERO (latency_counter_get_percentile (l, -1.0));
   CHECK_ZERO (latency_counter_get_percentile (l, 101.0));
index b63a81ad29b44fe13c113ca8843a7abb701bcfbf..afeb39e1162af515ddac44dfda578b3a76c2cdb4 100644 (file)
@@ -571,6 +571,64 @@ static cu_mount_t *cu_mount_gen_getmntent (void)
 #warn "This version of `getmntent' hat not yet been implemented!"
 /* #endif HAVE_SEQ_GETMNTENT */
 
+#elif HAVE_GETMNTENT_R
+static cu_mount_t *cu_mount_getmntent (void)
+{
+       FILE *fp;
+       struct mntent me;
+       char mntbuf[1024];
+
+       cu_mount_t *first = NULL;
+       cu_mount_t *last  = NULL;
+       cu_mount_t *new   = NULL;
+
+       DEBUG ("utils_mount: (void); COLLECTD_MNTTAB = %s", COLLECTD_MNTTAB);
+
+       if ((fp = setmntent (COLLECTD_MNTTAB, "r")) == NULL)
+       {
+               char errbuf[1024];
+               ERROR ("setmntent (%s): %s", COLLECTD_MNTTAB,
+                               sstrerror (errno, errbuf, sizeof (errbuf)));
+               return (NULL);
+       }
+
+       while (getmntent_r (fp, &me, mntbuf, sizeof (mntbuf) ))
+       {
+               if ((new = malloc (sizeof (cu_mount_t))) == NULL)
+                       break;
+               memset (new, '\0', sizeof (cu_mount_t));
+
+               /* Copy values from `struct mntent *' */
+               new->dir         = sstrdup (me.mnt_dir);
+               new->spec_device = sstrdup (me.mnt_fsname);
+               new->type        = sstrdup (me.mnt_type);
+               new->options     = sstrdup (me.mnt_opts);
+               new->device      = get_device_name (new->options);
+               new->next        = NULL;
+
+               DEBUG ("utils_mount: new = {dir = %s, spec_device = %s, type = %s, options = %s, device = %s}",
+                               new->dir, new->spec_device, new->type, new->options, new->device);
+
+               /* Append to list */
+               if (first == NULL)
+               {
+                       first = new;
+                       last  = new;
+               }
+               else
+               {
+                       last->next = new;
+                       last       = new;
+               }
+       }
+
+       endmntent (fp);
+
+       DEBUG ("utils_mount: return (0x%p)", (void *) first);
+
+       return (first);
+} /* HAVE_GETMNTENT_R */
+
 #elif HAVE_ONE_GETMNTENT
 static cu_mount_t *cu_mount_getmntent (void)
 {
index c5ffbfbcf9fb9d701db96f02aafa1cc9873b4790..b4cb43219a0e63b1ff8200ee79c3e2953704ca9c 100644 (file)
 #include "collectd.h"
 #include "utils_mount.h"
 
+#if HAVE_LIBKSTAT
+kstat_ctl_t *kc;
+#endif /* HAVE_LIBKSTAT */
+
 DEF_TEST(cu_mount_checkoption)
 {
   char line_opts[] = "foo=one,bar=two,qux=three";
@@ -77,14 +81,14 @@ DEF_TEST(cu_mount_getoptionvalue)
   char line_opts[] = "foo=one,bar=two,qux=three";
   char line_bool[] = "one,two,three";
 
-  STREQ ("one", cu_mount_getoptionvalue (line_opts, "foo="));
-  STREQ ("two", cu_mount_getoptionvalue (line_opts, "bar="));
-  STREQ ("three", cu_mount_getoptionvalue (line_opts, "qux="));
+  EXPECT_EQ_STR ("one", cu_mount_getoptionvalue (line_opts, "foo="));
+  EXPECT_EQ_STR ("two", cu_mount_getoptionvalue (line_opts, "bar="));
+  EXPECT_EQ_STR ("three", cu_mount_getoptionvalue (line_opts, "qux="));
   OK (NULL == cu_mount_getoptionvalue (line_opts, "unknown="));
 
-  STREQ ("", cu_mount_getoptionvalue (line_bool, "one"));
-  STREQ ("", cu_mount_getoptionvalue (line_bool, "two"));
-  STREQ ("", cu_mount_getoptionvalue (line_bool, "three"));
+  EXPECT_EQ_STR ("", cu_mount_getoptionvalue (line_bool, "one"));
+  EXPECT_EQ_STR ("", cu_mount_getoptionvalue (line_bool, "two"));
+  EXPECT_EQ_STR ("", cu_mount_getoptionvalue (line_bool, "three"));
   OK (NULL == cu_mount_getoptionvalue (line_bool, "four"));
 
   return (0);
index 75c0206169666da7b693f59880a5603c52ff5a03..f85910e1737e7b5d1c328a6e9e15896be2d60d99 100644 (file)
 #include "utils_vl_lookup.h"
 #include "utils_avltree.h"
 
+#if HAVE_LIBKSTAT
+kstat_ctl_t *kc;
+#endif /* HAVE_LIBKSTAT */
+
 #if BUILD_TEST
 # define sstrncpy strncpy
 # define plugin_log(s, ...) do { \
@@ -304,9 +308,10 @@ static int lu_handle_user_class (lookup_t *obj, /* {{{ */
   {
     /* call lookup_class_callback_t() and insert into the list of user objects. */
     user_obj = lu_create_user_obj (obj, ds, vl, user_class);
-    pthread_mutex_unlock (&user_class->lock);
-    if (user_obj == NULL)
+    if (user_obj == NULL) {
+      pthread_mutex_unlock (&user_class->lock);
       return (-1);
+    }
   }
   pthread_mutex_unlock (&user_class->lock);
 
index dff8f71dcb9119c812ad9645f72ea2d5f010b824..6824b134aeed727de314b5006fee3f14477ae6f5 100644 (file)
@@ -128,7 +128,7 @@ enum plginst_field {
 };
 
 static enum plginst_field plugin_instance_format[PLGINST_MAX_FIELDS] =
-    { plginst_name };
+    { plginst_none };
 
 /* InterfaceFormat. */
 enum if_field {
@@ -417,8 +417,8 @@ lv_config (const char *key, const char *value)
             else if (strcasecmp (fields[i], "uuid") == 0)
                 hostname_format[i] = hf_uuid;
             else {
-                sfree (value_copy);
                 ERROR (PLUGIN_NAME " plugin: unknown HostnameFormat field: %s", fields[i]);
+                sfree (value_copy);
                 return -1;
             }
         }
@@ -449,13 +449,16 @@ lv_config (const char *key, const char *value)
         }
 
         for (i = 0; i < n; ++i) {
-            if (strcasecmp (fields[i], "name") == 0)
+            if (strcasecmp (fields[i], "none") == 0) {
+                plugin_instance_format[i] = plginst_none;
+                break;
+            } else if (strcasecmp (fields[i], "name") == 0)
                 plugin_instance_format[i] = plginst_name;
             else if (strcasecmp (fields[i], "uuid") == 0)
                 plugin_instance_format[i] = plginst_uuid;
             else {
+                ERROR (PLUGIN_NAME " plugin: unknown PluginInstanceFormat field: %s", fields[i]);
                 sfree (value_copy);
-                ERROR (PLUGIN_NAME " plugin: unknown HostnameFormat field: %s", fields[i]);
                 return -1;
             }
         }
index ed596bbf56b9e9ee88becd425126951a4591fb91..868bca84395ac23fe0e672b179f882ec3f488c53 100644 (file)
@@ -59,6 +59,7 @@ struct wh_callback_s
         char *clientkeypass;
         long sslversion;
         _Bool store_rates;
+        _Bool log_http_error;
         int   low_speed_limit;
         time_t low_speed_time;
         int timeout;
@@ -80,6 +81,19 @@ struct wh_callback_s
 };
 typedef struct wh_callback_s wh_callback_t;
 
+static void wh_log_http_error (wh_callback_t *cb)
+{
+        if (!cb->log_http_error)
+                return;
+
+        long http_code = 0;
+
+        curl_easy_getinfo (cb->curl, CURLINFO_RESPONSE_CODE, &http_code);
+
+        if (http_code != 200)
+                INFO ("write_http plugin: HTTP Error code: %lu", http_code);
+}
+
 static void wh_reset_buffer (wh_callback_t *cb)  /* {{{ */
 {
         memset (cb->send_buffer, 0, cb->send_buffer_size);
@@ -101,6 +115,9 @@ static int wh_send_buffer (wh_callback_t *cb) /* {{{ */
 
         curl_easy_setopt (cb->curl, CURLOPT_POSTFIELDS, cb->send_buffer);
         status = curl_easy_perform (cb->curl);
+
+        wh_log_http_error (cb);
+
         if (status != CURLE_OK)
         {
                 ERROR ("write_http plugin: curl_easy_perform failed with "
@@ -538,6 +555,7 @@ static int wh_config_node (oconfig_item_t *ci) /* {{{ */
         cb->sslversion = CURL_SSLVERSION_DEFAULT;
         cb->low_speed_limit = 0;
         cb->timeout = 0;
+        cb->log_http_error = 0;
 
         pthread_mutex_init (&cb->send_lock, /* attr = */ NULL);
 
@@ -609,6 +627,8 @@ static int wh_config_node (oconfig_item_t *ci) /* {{{ */
                         cf_util_get_int (child, &cb->low_speed_limit);
                 else if (strcasecmp ("Timeout", child->key) == 0)
                         cf_util_get_int (child, &cb->timeout);
+                else if (strcasecmp ("LogHttpError", child->key) == 0)
+                        cf_util_get_boolean (child, &cb->log_http_error);
                 else
                 {
                         ERROR ("write_http plugin: Invalid configuration "
index 7ba476c92fa2164322c4d3ad5ba73b64ea67e322..1eb082fb331cfcb9496658c8e98ef4fb8e5297b4 100644 (file)
@@ -46,6 +46,8 @@ struct wr_node_s
   struct timeval timeout;
   char *prefix;
   int database;
+  int max_set_size;
+  _Bool store_rates;
 
   redisContext *conn;
   pthread_mutex_t lock;
@@ -68,7 +70,6 @@ static int wr_write (const data_set_t *ds, /* {{{ */
   char *value_ptr;
   int status;
   redisReply   *rr;
-  int i;
 
   status = FORMAT_VL (ident, sizeof (ident), vl);
   if (status != 0)
@@ -81,40 +82,7 @@ static int wr_write (const data_set_t *ds, /* {{{ */
   memset (value, 0, sizeof (value));
   value_size = sizeof (value);
   value_ptr = &value[0];
-
-#define APPEND(...) do {                                             \
-  status = snprintf (value_ptr, value_size, __VA_ARGS__);            \
-  if (((size_t) status) > value_size)                                \
-  {                                                                  \
-    value_ptr += value_size;                                         \
-    value_size = 0;                                                  \
-  }                                                                  \
-  else                                                               \
-  {                                                                  \
-    value_ptr += status;                                             \
-    value_size -= status;                                            \
-  }                                                                  \
-} while (0)
-
-  APPEND ("%s:", time);
-
-  for (i = 0; i < ds->ds_num; i++)
-  {
-    if (ds->ds[i].type == DS_TYPE_COUNTER)
-      APPEND ("%llu", vl->values[i].counter);
-    else if (ds->ds[i].type == DS_TYPE_GAUGE)
-      APPEND (GAUGE_FORMAT, vl->values[i].gauge);
-    else if (ds->ds[i].type == DS_TYPE_DERIVE)
-      APPEND ("%"PRIi64, vl->values[i].derive);
-    else if (ds->ds[i].type == DS_TYPE_ABSOLUTE)
-      APPEND ("%"PRIu64, vl->values[i].absolute);
-    else
-      assert (23 == 42);
-  }
-
-#undef APPEND
-
-  status = format_values (value_ptr, value_size, ds, vl, /* store rates = */ 0);
+  status = format_values (value_ptr, value_size, ds, vl, node->store_rates);
   pthread_mutex_lock (&node->lock);
   if (status != 0)
     return (status);
@@ -139,7 +107,7 @@ static int wr_write (const data_set_t *ds, /* {{{ */
       pthread_mutex_unlock (&node->lock);
       return (-1);
     }
-   
+
     rr = redisCommand(node->conn, "SELECT %d", node->database);
     if (rr == NULL)
       WARNING("SELECT command error. database:%d message:%s", node->database, node->conn->errstr);
@@ -153,6 +121,15 @@ static int wr_write (const data_set_t *ds, /* {{{ */
   else
     freeReplyObject (rr);
 
+  if (node->max_set_size >= 0)
+  {
+    rr = redisCommand (node->conn, "ZREMRANGEBYRANK %s %d %d", key, 0, (-1 * node->max_set_size) - 1);
+    if (rr == NULL)
+      WARNING("ZREMRANGEBYRANK command error. key:%s message:%s", key, node->conn->errstr);
+    else
+      freeReplyObject (rr);
+  }
+
   /* TODO(octo): This is more overhead than necessary. Use the cache and
    * metadata to determine if it is a new metric and call SADD only once for
    * each metric. */
@@ -204,6 +181,8 @@ static int wr_config_node (oconfig_item_t *ci) /* {{{ */
   node->conn = NULL;
   node->prefix = NULL;
   node->database = 0;
+  node->max_set_size = -1;
+  node->store_rates = 1;
   pthread_mutex_init (&node->lock, /* attr = */ NULL);
 
   status = cf_util_get_string_buffer (ci, node->name, sizeof (node->name));
@@ -238,6 +217,12 @@ static int wr_config_node (oconfig_item_t *ci) /* {{{ */
     else if (strcasecmp ("Database", child->key) == 0) {
       status = cf_util_get_int (child, &node->database);
     }
+    else if (strcasecmp ("MaxSetSize", child->key) == 0) {
+      status = cf_util_get_int (child, &node->max_set_size);
+    }
+    else if (strcasecmp ("StoreRates", child->key) == 0) {
+      status = cf_util_get_boolean (child, &node->store_rates);
+    }
     else
       WARNING ("write_redis plugin: Ignoring unknown config option \"%s\".",
           child->key);
index f0d23239a82ab158c03c669f9a96cf2fc7f8dd24..dd633d5f2287352969f1619f553c105eccd7eade 100644 (file)
@@ -251,6 +251,9 @@ static int za_read (void)
 
        /* Sizes */
        za_read_gauge (ksp, "size",    "cache_size", "arc");
+       za_read_gauge (ksp, "c",    "cache_size", "c");
+       za_read_gauge (ksp, "c_min",    "cache_size", "c_min");
+       za_read_gauge (ksp, "c_max",    "cache_size", "c_max");
 
        /* The "l2_size" value has disappeared from Solaris some time in
         * early 2013, and has only reappeared recently in Solaris 11.2.