src/liboconfig/parser.h
src/liboconfig/scanner.c
+# protobuf stuff:
+src/*.pb-c.[ch]
+
# make dist stuff:
/collectd-*.tar.gz
/collectd-*.tar.bz2
+2013-04-09, Version 5.3.0
+ * collectd: The "Include" statements can now be limited to include
+ only matching files in a directory. Thanks to Sebastian Harl for his
+ patch.
+ * collectd: Dispatches / writes are now handled by a thread pool. This
+ improves reliability and throughput for instances configured to act
+ as a "server". Thanks to Sebastian Harl and Dan Fandrich for
+ reviewing this change and fixing bugs.
+ * aggregation plugin: Selection of value lists is now possible using
+ regular expressions. Parts of the identifier of the resulting metric
+ can now be set via the configuration file.
+ * apcups plugin: The "ReportSeconds" option has been implemented.
+ * curl* plugins: Support for POST requests and custom request headers
+ has been added. Thanks to Dan Fandrich for his patch.
+ * curl_xml plugin: Support for XML namespaces has been added. Thanks
+ to Dan Fandrich for his patch.
+ * dbi plugin: Support for numeric options has been added. The
+ "Host" option has been added. Thanks to Daniel Hilst for his patch.
+ * disk plugin: Support for systems with >256 has been fixed. Thanks to
+ Greg Mason for his patch.
+ * libvirt plugin: Support for memory allocation has been added. Thanks
+ to Johan Wirén for his patch.
+ * netapp plugin: Support for "SnapVault", "VFiler" and deduplication /
+ compression and quota metrics. Thanks to Sebastian Harl for his
+ patches and teamix GmbH for sponsoring this work.
+ * postgresql plugin: The reconnection logic has been improved. Thanks
+ to Sebastian Harl for his patches.
+ * rrdtool, rrdcached plugins: The "CreateFilesAsync" option has been
+ implemented. When enabled, new RRD files will be created
+ asynchronously, which improved throughput of "server" instances.
+ Many thanks to Yves Mettier for all his input and code.
+ * tail_csv plugin: This new plugins allows to read metrics from CSV
+ files, such as Snort's statistics file. Thanks to Kris Nielander for
+ his patch.
+ * write_mongodb plugin: Authentication options have been added.
+ * write_riemann plugin: This new plugin allows sending metrics to
+ Riemann, a stream processing and alerting tool. Big thanks to
+ Pierre-Yves Ritschard for his work.
+
+2013-04-08, Version 5.2.2
+ * Build system: A bad interaction between the Java detection code and
+ libltdl has been fixed. Thanks to Dave Cottlehuber for his patch.
+ Installation of the Perl bindings has been improved / fixed. Thanks
+ to Sebastian Harl for his patch.
+ * collectd: Fixed read callback scheduling at startup.
+ * apache, ascent, bind, curl, curl_json, curl_xml, nginx and
+ write_http plugins: Portability fixes, protection from infinite
+ redirect loops, improved error handling and incorrect dereferences
+ have been fixed. Most of these are related to the cURL library.
+ Thanks to Dan Fandrich for his patches.
+ * logfile plugin: Flush the output file handle. This works around
+ caching when logging to STDOUT and redirecting into a file. Thanks
+ to Nathan Huff for the patch.
+ * mysql plugin: Fix a memory leak in the error handling. Thanks to
+ Tomas Doran for his patch.
+ * netapp plugin: Fix the interval with which values are dispatched.
+ * network plugin: Build issues under FreeBSD and initialization have
+ been fixed. Thanks to Ed Schouten for his patch.
+ * nfs plugin: A compilation problem has been fixed.
+ * notify_email plugin: Add a character set to the mail header. Thanks
+ to Manuel Cissé for his patch.
+ * pf plugin: Build issues have been fixed.
+ * postgresql plugin: Build issues have been fixed.
+ * rrdcached plugin: Connect to the daemon from the read callback.
+ * snmp plugin: Matching of SNMP subtrees has been improved. Thanks to
+ "jkrabbe" for the patch.
+ * thermal plugin: The initialization of dispatched value lists has
+ been fixed. Thanks to Markus Knetschke for his patch.
+ * unixsock plugin: Parsing of options with an underscore, e.g.
+ "plugin_instance" has been fixed. Thanks to Tommie Gannert for his
+ patch.
+
2013-01-27, Version 5.2.1
* Build system: "make distcheck" has been fixed. Build fixes Solaris
and systems without gcrypt. Thanks to Yves Mettier for his patches.
* tcpconns plugin: Use a netlink socket rather than reading from /proc
for improved performance. Thanks to Michael Stapelberg for the patch.
+2013-04-08, Version 5.1.3
+ * Build system: A bad interaction between the Java detection code and
+ libltdl has been fixed. Thanks to Dave Cottlehuber for his patch.
+ * collectd: Fixed read callback scheduling at startup.
+ * apache, ascent, bind, curl, curl_json, curl_xml, nginx and
+ write_http plugins: Portability fixes, protection from infinite
+ redirect loops, improved error handling and incorrect dereferences
+ have been fixed. Most of these are related to the cURL library.
+ Thanks to Dan Fandrich for his patches.
+ * logfile plugin: Flush the output file handle. This works around
+ caching when logging to STDOUT and redirecting into a file. Thanks
+ to Nathan Huff for the patch.
+ * mysql plugin: Fix a memory leak in the error handling. Thanks to
+ Tomas Doran for his patch.
+ * netapp plugin: Fix the interval with which values are dispatched.
+ * network plugin: Build issues under FreeBSD and initialization have
+ been fixed. Thanks to Ed Schouten for his patch.
+ * nfs plugin: A compilation problem has been fixed.
+ * notify_email plugin: Add a character set to the mail header. Thanks
+ to Manuel Cissé for his patch.
+ * rrdcached plugin: Connect to the daemon from the read callback.
+ * snmp plugin: Matching of SNMP subtrees has been improved. Thanks to
+ "jkrabbe" for the patch.
+ * thermal plugin: The initialization of dispatched value lists has
+ been fixed. Thanks to Markus Knetschke for his patch.
+ * unixsock plugin: Parsing of options with an underscore, e.g.
+ "plugin_instance" has been fixed. Thanks to Tommie Gannert for his
+ patch.
+
2013-01-25, Version 5.1.2
* Build system: "make distcheck" has been fixed. Thanks to Yves
Mettier for his patches.
* v5upgrade target: Target for converting v4 data sets to the v5
schema.
+2013-04-07, Version 4.10.9
+ * Build system: A bad interaction between the Java detection code and
+ libltdl has been fixed. Thanks to Dave Cottlehuber for his patch.
+ * apache, ascent, bind, curl, curl_json, curl_xml, nginx and
+ write_http plugins: Portability fixes, protection from infinite
+ redirect loops, improved error handling and incorrect dereferences
+ have been fixed. Most of these are related to the cURL library.
+ Thanks to Dan Fandrich for his patches.
+ * logfile plugin: Flush the output file handle. This works around
+ caching when logging to STDOUT and redirecting into a file. Thanks
+ to Nathan Huff for the patch.
+ * network plugin: Build issues under FreeBSD and initialization have
+ been fixed. Thanks to Ed Schouten for his patch.
+ * mysql plugin: Fix a memory leak in the error handling. Thanks to
+ Tomas Doran for his patch.
+ * thermal plugin: The initialization of dispatched value lists has
+ been fixed. Thanks to Markus Knetschke for his patch.
+ * unixsock plugin: Parsing of options with an underscore, e.g.
+ "plugin_instance" has been fixed. Thanks to Tommie Gannert for his
+ patch.
+
2012-11-11, Version 4.10.8
* collectd: Create new directories with mode 0777 and let umask remove
unwanted permission bits.
buildperl/Makefile: .perl-directory-stamp buildperl/Makefile.PL \
$(top_builddir)/config.status
- cd buildperl && @PERL@ Makefile.PL INSTALL_BASE=$(DESTDIR)$(prefix) @PERL_BINDINGS_OPTIONS@
+ @# beautify the output a bit
+ @echo 'cd buildperl && @PERL@ Makefile.PL @PERL_BINDINGS_OPTIONS@'
+ @cd buildperl && ( if ! @PERL@ Makefile.PL @PERL_BINDINGS_OPTIONS@; then \
+ echo ""; \
+ echo 'Check whether you have set $$PERL_MM_OPT in your environment and try using ./configure --with-perl-bindings=""'; \
+ echo ""; \
+ fi )
buildperl/Makefile.PL: .perl-directory-stamp $(top_builddir)/config.status
PKG_PROG_PKG_CONFIG
AC_CHECK_PROG([have_protoc_c], [protoc-c], [yes], [no])
-if test "x$have_protoc_c" = "xyes"
-then
- AC_CHECK_HEADERS([google/protobuf-c/protobuf-c.h],
- [have_protobuf_c_h="yes"],
- [have_protobuf_c_h="no"])
-fi
+AC_CHECK_HEADERS([google/protobuf-c/protobuf-c.h],
+ [have_protobuf_c_h="yes"],
+ [have_protobuf_c_h="no"])
if test "x$have_protoc_c" = "xyes" && test "x$have_protobuf_c_h" != "xyes"
then
- have_protoc_c="no (unable to find protobuf-c.h)"
+ have_protoc_c="no (unable to find <google/protobuf-c/protobuf-c.h>)"
fi
AM_CONDITIONAL(HAVE_PROTOC_C, test "x$have_protoc_c" = "xyes")
[c_cv_have_strtok_r_default],
AC_LINK_IFELSE(
[AC_LANG_PROGRAM(
- [[[
+[[[
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
- ]]],
- [[[
+]]],
+[[[
char buffer[] = "foo,bar,baz";
char *token;
char *dummy;
dummy = NULL;
printf ("token = %s;\n", token);
}
- ]]])],
+]]]
+ )],
[c_cv_have_strtok_r_default="yes"],
[c_cv_have_strtok_r_default="no"]
)
[c_cv_have_strtok_r_reentrant],
AC_LINK_IFELSE(
[AC_LANG_PROGRAM(
- [[[
+[[[
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
- ]]],
- [[[
+]]],
+[[[
char buffer[] = "foo,bar,baz";
char *token;
char *dummy;
dummy = NULL;
printf ("token = %s;\n", token);
}
- ]]])],
+]]]
+ )],
[c_cv_have_strtok_r_reentrant="yes"],
[AC_MSG_FAILURE([strtok_r isn't available. Please file a bugreport!])]
)
then
AC_CACHE_CHECK([whether strptime is exported by default],
[c_cv_have_strptime_default],
- AC_COMPILE_IFELSE(
-[AC_LANG_PROGRAM(
+ AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
[[[
#include <time.h>
]]],
[[[
struct tm stm;
(void) strptime ("2010-12-30%13:42:42", "%Y-%m-%dT%T", &stm);
-]]])],
+]]]
+ )],
[c_cv_have_strptime_default="yes"],
[c_cv_have_strptime_default="no"]))
fi
then
AC_CACHE_CHECK([whether strptime needs standards mode],
[c_cv_have_strptime_standards],
- AC_COMPILE_IFELSE(
-[AC_LANG_PROGRAM(
+ AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
[[[
#ifndef _ISOC99_SOURCE
# define _ISOC99_SOURCE 1
#ifndef _XOPEN_SOURCE
# define _XOPEN_SOURCE 500
#endif
-
#include <time.h>
]]],
[[[
struct tm stm;
(void) strptime ("2010-12-30%13:42:42", "%Y-%m-%dT%T", &stm);
-]]])],
+]]]
+ )],
[c_cv_have_strptime_standards="yes"],
[c_cv_have_strptime_standards="no"]))
then
CFLAGS="$SAVE_CFLAGS"
fi
-
# }}} Check for strptime
AC_CHECK_FUNCS(swapctl, [have_swapctl="yes"], [have_swapctl="no"])
AC_CACHE_CHECK([whether swapctl takes two arguments],
[c_cv_have_swapctl_two_args],
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
-[[
+[[[
#if HAVE_SYS_SWAP_H && !defined(_LP64) && _FILE_OFFSET_BITS == 64
# undef _FILE_OFFSET_BITS
# undef _LARGEFILE64_SOURCE
#endif
#include <sys/stat.h>
#include <sys/swap.h>
-]],
-[[
+]]],
+[[[
int num = swapctl(0, NULL);
-]]
+]]]
)],
[c_cv_have_swapctl_two_args="yes"],
[c_cv_have_swapctl_two_args="no"]
[c_cv_have_swapctl_three_args],
AC_COMPILE_IFELSE(
[AC_LANG_PROGRAM(
-[[
+[[[
#if HAVE_SYS_SWAP_H && !defined(_LP64) && _FILE_OFFSET_BITS == 64
# undef _FILE_OFFSET_BITS
# undef _LARGEFILE64_SOURCE
#endif
#include <sys/stat.h>
#include <sys/swap.h>
-]],
-[[
+]]],
+[[[
int num = swapctl(0, NULL, 0);
-]]
+]]]
)],
[c_cv_have_swapctl_three_args="yes"],
[c_cv_have_swapctl_three_args="no"]
if test "x$nan_type" = "xnone"; then
AC_CACHE_CHECK([whether NAN is defined by default],
[c_cv_have_nan_default],
- AC_COMPILE_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <stdlib.h>
#include <math.h>
static double foo = NAN;
- ]]],
- [[[
+]]],
+[[[
if (isnan (foo))
return 0;
else
return 1;
- ]]])],
+]]]
+ )],
[c_cv_have_nan_default="yes"],
[c_cv_have_nan_default="no"]
)
if test "x$nan_type" = "xnone"; then
AC_CACHE_CHECK([whether NAN is defined by __USE_ISOC99],
[c_cv_have_nan_isoc],
- AC_COMPILE_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <stdlib.h>
#define __USE_ISOC99 1
#include <math.h>
static double foo = NAN;
- ]]],
- [[[
+]]],
+[[[
if (isnan (foo))
return 0;
else
return 1;
- ]]])],
+]]]
+ )],
[c_cv_have_nan_isoc="yes"],
[c_cv_have_nan_isoc="no"]
)
LDFLAGS="$LDFLAGS -lm"
AC_CACHE_CHECK([whether NAN can be defined by 0/0],
[c_cv_have_nan_zero],
- AC_RUN_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_RUN_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <stdlib.h>
#include <math.h>
#ifdef NAN
# define isnan(f) ((f) != (f))
#endif
static double foo = NAN;
- ]]],
- [[[
+]]],
+[[[
if (isnan (foo))
return 0;
else
return 1;
- ]]])],
+]]]
+ )],
[c_cv_have_nan_zero="yes"],
[c_cv_have_nan_zero="no"]
)
if test "x$fp_layout_type" = "xunknown"; then
AC_CACHE_CHECK([if doubles are stored in x86 representation],
[c_cv_fp_layout_need_nothing],
- AC_RUN_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_RUN_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#if HAVE_STDBOOL_H
# include <stdbool.h>
#endif
- ]]],
- [[[
+]]],
+[[[
uint64_t i0;
uint64_t i1;
uint8_t c[8];
return (0);
else
return (1);
- ]]])],
+]]]
+ )],
[c_cv_fp_layout_need_nothing="yes"],
[c_cv_fp_layout_need_nothing="no"]
)
if test "x$fp_layout_type" = "xunknown"; then
AC_CACHE_CHECK([if endianflip converts to x86 representation],
[c_cv_fp_layout_need_endianflip],
- AC_RUN_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_RUN_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
(((uint64_t)(A) & 0x0000000000ff0000LL) << 24) | \
(((uint64_t)(A) & 0x000000000000ff00LL) << 40) | \
(((uint64_t)(A) & 0x00000000000000ffLL) << 56))
- ]]],
- [[[
+]]],
+[[[
uint64_t i0;
uint64_t i1;
uint8_t c[8];
return (0);
else
return (1);
- ]]])],
+]]]
+ )],
[c_cv_fp_layout_need_endianflip="yes"],
[c_cv_fp_layout_need_endianflip="no"]
)
if test "x$fp_layout_type" = "xunknown"; then
AC_CACHE_CHECK([if intswap converts to x86 representation],
[c_cv_fp_layout_need_intswap],
- AC_RUN_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_RUN_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#endif
#define intswap(A) ((((uint64_t)(A) & 0xffffffff00000000LL) >> 32) | \
(((uint64_t)(A) & 0x00000000ffffffffLL) << 32))
- ]]],
- [[[
+]]],
+[[[
uint64_t i0;
uint64_t i1;
uint8_t c[8];
return (0);
else
return (1);
- ]]])],
+]]]
+ )],
[c_cv_fp_layout_need_intswap="yes"],
[c_cv_fp_layout_need_intswap="no"]
)
[c_cv_have_one_getmntent],
AC_COMPILE_IFELSE(
[AC_LANG_PROGRAM(
-[[
+[[[
#include "$srcdir/src/utils_mount.h"
-]],
-[[
+]]],
+[[[
FILE *fh;
struct mntent *me;
fh = setmntent ("/etc/mtab", "r");
me = getmntent (fh);
-]]
+]]]
)],
[c_cv_have_one_getmntent="yes"],
[c_cv_have_one_getmntent="no"]
[c_cv_have_two_getmntent],
AC_COMPILE_IFELSE(
[AC_LANG_PROGRAM(
-[[
+[[[
#include "$srcdir/src/utils_mount.h"
-]],
-[[
+]]],
+[[[
FILE *fh;
struct mnttab mt;
int status;
fh = fopen ("/etc/mnttab", "r");
status = getmntent (fh, &mt);
-]]
+]]]
)],
[c_cv_have_two_getmntent="yes"],
[c_cv_have_two_getmntent="no"]
AC_MSG_CHECKING([if have htonll defined])
have_htonll="no"
- AC_LINK_IFELSE([
- AC_LANG_PROGRAM([[[
+ AC_LINK_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <sys/types.h>
#include <netinet/in.h>
#if HAVE_INTTYPES_H
# include <inttypes.h>
#endif
- ]]], [[[
+]]],
+[[[
return htonll(0);
- ]]])
- ], [
+]]]
+ )],
+ [
have_htonll="yes"
AC_DEFINE(HAVE_HTONLL, 1, [Define if the function htonll exists.])
])
if test "$with_libgcrypt" != "no"; then
AM_PATH_LIBGCRYPT(1:1.2.0,,with_libgcrypt="no (version 1.2.0+ required)")
- GCRYPT_CPPFLAGS="$LIBGCRYPT_CPPFLAGS"
+ GCRYPT_CPPFLAGS="$LIBGCRYPT_CPPFLAGS $LIBGCRYPT_CFLAGS"
GCRYPT_LIBS="$LIBGCRYPT_LIBS"
fi
fi
if test -d "$with_java_home"
then
AC_MSG_CHECKING([for jni.h])
- TMPDIR=`find "$with_java_home" -name jni.h -type f -exec 'dirname' '{}' ';' 2>/dev/null | head -n 1`
- if test "x$TMPDIR" != "x"
+ TMPVAR=`find "$with_java_home" -name jni.h -type f -exec 'dirname' '{}' ';' 2>/dev/null | head -n 1`
+ if test "x$TMPVAR" != "x"
then
- AC_MSG_RESULT([found in $TMPDIR])
- JAVA_CPPFLAGS="$JAVA_CPPFLAGS -I$TMPDIR"
+ AC_MSG_RESULT([found in $TMPVAR])
+ JAVA_CPPFLAGS="$JAVA_CPPFLAGS -I$TMPVAR"
else
AC_MSG_RESULT([not found])
fi
AC_MSG_CHECKING([for jni_md.h])
- TMPDIR=`find "$with_java_home" -name jni_md.h -type f -exec 'dirname' '{}' ';' 2>/dev/null | head -n 1`
- if test "x$TMPDIR" != "x"
+ TMPVAR=`find "$with_java_home" -name jni_md.h -type f -exec 'dirname' '{}' ';' 2>/dev/null | head -n 1`
+ if test "x$TMPVAR" != "x"
then
- AC_MSG_RESULT([found in $TMPDIR])
- JAVA_CPPFLAGS="$JAVA_CPPFLAGS -I$TMPDIR"
+ AC_MSG_RESULT([found in $TMPVAR])
+ JAVA_CPPFLAGS="$JAVA_CPPFLAGS -I$TMPVAR"
else
AC_MSG_RESULT([not found])
fi
AC_MSG_CHECKING([for libjvm.so])
- TMPDIR=`find "$with_java_home" -name libjvm.so -type f -exec 'dirname' '{}' ';' 2>/dev/null | head -n 1`
- if test "x$TMPDIR" != "x"
+ TMPVAR=`find "$with_java_home" -name libjvm.so -type f -exec 'dirname' '{}' ';' 2>/dev/null | head -n 1`
+ if test "x$TMPVAR" != "x"
then
- AC_MSG_RESULT([found in $TMPDIR])
- JAVA_LDFLAGS="$JAVA_LDFLAGS -L$TMPDIR -Wl,-rpath -Wl,$TMPDIR"
+ AC_MSG_RESULT([found in $TMPVAR])
+ JAVA_LDFLAGS="$JAVA_LDFLAGS -L$TMPVAR -Wl,-rpath -Wl,$TMPVAR"
else
AC_MSG_RESULT([not found])
fi
if test "x$JAVAC" = "x"
then
AC_MSG_CHECKING([for javac])
- TMPDIR=`find "$with_java_home" -name javac -type f 2>/dev/null | head -n 1`
- if test "x$TMPDIR" != "x"
+ TMPVAR=`find "$with_java_home" -name javac -type f 2>/dev/null | head -n 1`
+ if test "x$TMPVAR" != "x"
then
- JAVAC="$TMPDIR"
+ JAVAC="$TMPVAR"
AC_MSG_RESULT([$JAVAC])
else
AC_MSG_RESULT([not found])
if test "x$JAR" = "x"
then
AC_MSG_CHECKING([for jar])
- TMPDIR=`find "$with_java_home" -name jar -type f 2>/dev/null | head -n 1`
- if test "x$TMPDIR" != "x"
+ TMPVAR=`find "$with_java_home" -name jar -type f 2>/dev/null | head -n 1`
+ if test "x$TMPVAR" != "x"
then
- JAR="$TMPDIR"
+ JAR="$TMPVAR"
AC_MSG_RESULT([$JAR])
else
AC_MSG_RESULT([not found])
#include <sys/socket.h>])
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
-[[
+[[[
#include <stdio.h>
#include <sys/types.h>
#include <asm/types.h>
#include <sys/socket.h>
#include <linux/netlink.h>
#include <linux/rtnetlink.h>
-]],
-[[
+]]],
+[[[
int retval = TCA_STATS2;
return (retval);
-]]
+]]]
)],
[AC_DEFINE([HAVE_TCA_STATS2], [1], [True if the enum-member TCA_STATS2 exists])])
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
-[[
+[[[
#include <stdio.h>
#include <sys/types.h>
#include <asm/types.h>
#include <sys/socket.h>
#include <linux/netlink.h>
#include <linux/rtnetlink.h>
-]],
-[[
+]]],
+[[[
int retval = TCA_STATS;
return (retval);
-]]
+]]]
)],
[AC_DEFINE([HAVE_TCA_STATS], 1, [True if the enum-member TCA_STATS exists])])
[if function 'rtnl_dump_filter' expects five arguments],
[c_cv_rtnl_dump_filter_five_args],
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
-[[
+[[[
#include <stdio.h>
#include <sys/types.h>
#include <asm/types.h>
#elif HAVE_LINUX_LIBNETLINK_H
# include <linux/libnetlink.h>
#endif
-]],
-[[
+]]],
+[[[
if (rtnl_dump_filter(NULL, NULL, NULL, NULL, NULL))
return 1;
return 0;
-]]
+]]]
)],
[c_cv_rtnl_dump_filter_five_args="yes"],
[c_cv_rtnl_dump_filter_five_args="no"]
[if function 'rtnl_dump_filter' expects three arguments],
[c_cv_rtnl_dump_filter_three_args],
AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
-[[
+[[[
#include <stdio.h>
#include <sys/types.h>
#include <asm/types.h>
#elif HAVE_LINUX_LIBNETLINK_H
# include <linux/libnetlink.h>
#endif
-]],
-[[
+]]],
+[[[
if (rtnl_dump_filter(NULL, NULL, NULL))
return 1;
return 0;
-]]
+]]]
)],
[c_cv_rtnl_dump_filter_three_args="yes"],
[c_cv_rtnl_dump_filter_three_args="no"]
AC_CACHE_CHECK([for libperl],
[c_cv_have_libperl],
- AC_LINK_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_LINK_IFELSE([AC_LANG_PROGRAM(
+[[[
#define PERL_NO_GET_CONTEXT
#include <EXTERN.h>
#include <perl.h>
#include <XSUB.h>
- ]]],
- [[[
+]]],
+[[[
dTHX;
load_module (PERL_LOADMOD_NOIMPORT,
newSVpv ("Collectd::Plugin::FooBar", 24),
Nullsv);
- ]]])],
+]]]
+ )],
[c_cv_have_libperl="yes"],
[c_cv_have_libperl="no"]
)
AC_CACHE_CHECK([if perl supports ithreads],
[c_cv_have_perl_ithreads],
- AC_LINK_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_LINK_IFELSE([AC_LANG_PROGRAM(
+[[[
#include <EXTERN.h>
#include <perl.h>
#include <XSUB.h>
#if !defined(USE_ITHREADS)
# error "Perl does not support ithreads!"
#endif /* !defined(USE_ITHREADS) */
- ]]],
- [[[ ]]])],
+]]],
+[[[ ]]]
+ )],
[c_cv_have_perl_ithreads="yes"],
[c_cv_have_perl_ithreads="no"]
)
AC_CACHE_CHECK([for broken Perl_load_module()],
[c_cv_have_broken_perl_load_module],
- AC_LINK_IFELSE(
- [AC_LANG_PROGRAM(
- [[[
+ AC_LINK_IFELSE([AC_LANG_PROGRAM(
+[[[
#define PERL_NO_GET_CONTEXT
#include <EXTERN.h>
#include <perl.h>
#include <XSUB.h>
- ]]],
- [[[
+]]],
+[[[
dTHX;
load_module (PERL_LOADMOD_NOIMPORT,
newSVpv ("Collectd::Plugin::FooBar", 24),
Nullsv);
- ]]])],
+]]]
+ )],
[c_cv_have_broken_perl_load_module="no"],
[c_cv_have_broken_perl_load_module="yes"]
)
fi
dnl Perl bindings
+PERL_BINDINGS_OPTIONS="PREFIX=${prefix}"
AC_ARG_WITH(perl-bindings, [AS_HELP_STRING([--with-perl-bindings@<:@=OPTIONS@:>@], [Options passed to "perl Makefile.PL".])],
[
if test "x$withval" != "xno" && test "x$withval" != "xyes"
PERL_BINDINGS_OPTIONS="$withval"
with_perl_bindings="yes"
else
- PERL_BINDINGS_OPTIONS=""
with_perl_bindings="$withval"
fi
],
[
- PERL_BINDINGS_OPTIONS=""
if test -n "$perl_interpreter"
then
with_perl_bindings="yes"
%define with_syslog 0%{!?_without_syslog:1}
%define with_table 0%{!?_without_table:1}
%define with_tail 0%{!?_without_tail:1}
+%define with_tail_csv 0%{!?_without_tail_csv:1}
%define with_tcpconns 0%{!?_without_tcpconns:1}
%define with_teamspeak2 0%{!?_without_teamspeak2:1}
%define with_ted 0%{!?_without_ted:1}
%define with_wireless 0%{!?_without_wireless:1}
%define with_write_graphite 0%{!?_without_write_graphite:1}
%define with_write_http 0%{!?_without_write_http:1}
+%define with_write_riemann 0%{!?_without_write_riemann:1}
# disabled plugins
%define with_apple_sensors 0%{!?_without_apple_sensors:0}
Summary: Statistics collection daemon for filling RRD files
Name: collectd
-Version: 5.2.0
-Release: 3%{?dist}
+Version: 5.3.0
+Release: 1%{?dist}
URL: http://collectd.org
-Source: http://collectd.org/files/%{name}-%{version}.tar.gz
+Source: http://collectd.org/files/%{name}-%{version}.tar.bz2
License: GPLv2
Group: System Environment/Daemons
BuildRoot: %{_tmppath}/%{name}-%{version}-root
The Write Redis plugin stores values in Redis, a “data structures server”.
%endif
+%if %{with_write_riemann}
+%package write_riemann
+Summary: riemann plugin for collectd
+Group: System Environment/Daemons
+Requires: %{name}%{?_isa} = %{version}-%{release}
+BuildRequires: protobuf-c-devel
+%description write_riemann
+The riemann plugin submits values to Riemann, an event stream processor.
+%endif
+
%package collection3
Summary: Web-based viewer for collectd
Group: System Environment/Daemons
%prep
%setup -q
-
%build
%if %{with_aggregation}
%define _with_aggregation --enable-aggregation
%define _with_tail --disable-tail
%endif
+%if %{with_tail_csv}
+%define _with_tail_csv --enable-tail_csv
+%else
+%define _with_tail_csv --disable-tail_csv
+%endif
+
%if %{with_tape}
%define _with_tape --enable-tape
%else
%define _with_write_redis --disable-write_redis --without-libcredis
%endif
+%if %{with_write_riemann}
+%define _with_write_riemann --enable-write_riemann
+%else
+%define _with_write_riemann --disable-write_riemann
+%endif
+
%if %{with_xmms}
%define _with_xmms --enable-xmms
%else
%{?_with_syslog} \
%{?_with_table} \
%{?_with_tail} \
+ %{?_with_tail_csv} \
%{?_with_tcpconns} \
%{?_with_teamspeak2} \
%{?_with_ted} \
%{?_with_vserver} \
%{?_with_wireless}\
%{?_with_write_graphite} \
- %{?_with_write_http}
+ %{?_with_write_http} \
+ %{?_with_write_riemann}
%{__make} %{?_smp_mflags}
%{_mandir}/man1/collectd.1*
%{_mandir}/man1/collectdctl.1*
%{_mandir}/man1/collectdmon.1*
+%{_mandir}/man1/collectd-tg.1*
%{_mandir}/man5/collectd-email.5*
%{_mandir}/man5/collectd-exec.5*
%{_mandir}/man5/collectd-threshold.5*
%if %{with_tail}
%{_libdir}/%{name}/tail.so
%endif
+%if %{with_tail_csv}
+%{_libdir}/%{name}/tail_csv.so
+%endif
%if %{with_tcpconns}
%{_libdir}/%{name}/tcpconns.so
%endif
%{_libdir}/%{name}/write_redis.so
%endif
+%if %{with_write_riemann}
+%files write_riemann
+%{_libdir}/%{name}/write_riemann.so
+%endif
+
%files collection3
%{_localstatedir}/www/collection3
%{_sysconfdir}/httpd/conf.d/collection3.conf
%doc contrib/
%changelog
+* Wed Apr 10 2013 Marc Fournier <marc.fournier@camptocamp.com> 5.3.0-1
+- New upstream version
+- Enabled write_riemann plugin
+- Enabled tail_csv plugin
+- Installed collectd-tc manpage
+
* Thu Jan 11 2013 Marc Fournier <marc.fournier@camptocamp.com> 5.2.0-3
- remove dependency on libstatgrab, which isn't required on linux
pkglib_LTLIBRARIES =
BUILT_SOURCES =
-CLEANFILES =
+CLEANFILES =
if BUILD_PLUGIN_AGGREGATION
pkglib_LTLIBRARIES += aggregation.la
endif
if BUILD_PLUGIN_PINBA
-BUILT_SOURCES += pinba.pb-c.c pinba.pb-c.h
-CLEANFILES += pinba.pb-c.c pinba.pb-c.h
pkglib_LTLIBRARIES += pinba.la
pinba_la_SOURCES = pinba.c
+nodist_pinba_la_SOURCES = pinba.pb-c.c pinba.pb-c.h
pinba_la_LDFLAGS = -module -avoid-version
pinba_la_LIBADD = -lprotobuf-c
collectd_LDADD += "-dlopen" pinba.la
endif
if BUILD_PLUGIN_WRITE_RIEMANN
-BUILT_SOURCES += riemann.pb-c.c riemann.pb-c.h
-CLEANFILES += riemann.pb-c.c riemann.pb-c.h
pkglib_LTLIBRARIES += write_riemann.la
-write_riemann_la_SOURCES = write_riemann.c riemann.pb-c.c
+write_riemann_la_SOURCES = write_riemann.c
+nodist_write_riemann_la_SOURCES = riemann.pb-c.c riemann.pb-c.h
write_riemann_la_LDFLAGS = -module -avoid-version
write_riemann_la_LIBADD = -lprotobuf-c
collectd_LDADD += "-dlopen" write_riemann.la
#collectd_1_SOURCES = collectd.pod
-EXTRA_DIST = types.db pinba.proto riemann.proto
+EXTRA_DIST = types.db
EXTRA_DIST += collectd.conf.pod \
collectd-email.pod \
echo "$@ has some POD errors!"; false; \
fi
+# Protocol buffer for the "pinba" plugin.
+EXTRA_DIST += pinba.proto
+if HAVE_PROTOC_C
+CLEANFILES += pinba.pb-c.c pinba.pb-c.h
+BUILT_SOURCES += pinba.pb-c.c pinba.pb-c.h
+
pinba.pb-c.c pinba.pb-c.h: pinba.proto
protoc-c -I$(srcdir) --c_out . $(srcdir)/pinba.proto
+endif
+
+# Protocol buffer for the "write_riemann" plugin.
+EXTRA_DIST += riemann.proto
+if HAVE_PROTOC_C
+CLEANFILES += riemann.pb-c.c riemann.pb-c.h
+
+BUILT_SOURCES += riemann.pb-c.c riemann.pb-c.h
riemann.pb-c.c riemann.pb-c.h: riemann.proto
protoc-c -I$(srcdir) --c_out . $(srcdir)/riemann.proto
+endif
install-exec-hook:
$(mkinstalldirs) $(DESTDIR)$(sysconfdir)
/* publish only */
conf->delivery_mode = CAMQP_DM_VOLATILE;
conf->store_rates = 0;
+ conf->graphite_flags = 0;
/* publish & graphite only */
conf->prefix = NULL;
conf->postfix = NULL;
}
else if ((strcasecmp ("Format", child->key) == 0) && publish)
status = camqp_config_set_format (child, conf);
+ else if ((strcasecmp ("GraphiteSeparateInstances", child->key) == 0) && publish)
+ status = cf_util_get_flag (child, &conf->graphite_flags,
+ GRAPHITE_SEPARATE_INSTANCES);
+ else if ((strcasecmp ("GraphiteAlwaysAppendDS", child->key) == 0) && publish)
+ status = cf_util_get_flag (child, &conf->graphite_flags,
+ GRAPHITE_ALWAYS_APPEND_DS);
else if ((strcasecmp ("GraphitePrefix", child->key) == 0) && publish)
status = cf_util_get_string (child, &conf->prefix);
else if ((strcasecmp ("GraphitePostfix", child->key) == 0) && publish)
(*m->proc.destroy) (&m->user_data);
else if (m->user_data != NULL)
{
- ERROR ("Filter sybsystem: fc_free_matches: There is user data, but no "
+ ERROR ("Filter subsystem: fc_free_matches: There is user data, but no "
"destroy functions has been specified. "
"Memory will probably be lost!");
}
(*t->proc.destroy) (&t->user_data);
else if (t->user_data != NULL)
{
- ERROR ("Filter sybsystem: fc_free_targets: There is user data, but no "
+ ERROR ("Filter subsystem: fc_free_targets: There is user data, but no "
"destroy functions has been specified. "
"Memory will probably be lost!");
}
#endif
} /* }}} _Bool have_gcrypt */
+#ifndef HAVE_HTONLL
static uint64_t htonll (uint64_t val) /* {{{ */
{
static int config = 0;
return ((((uint64_t) lo) << 32) | ((uint64_t) hi));
} /* }}} uint64_t htonll */
+#endif
static double htond (double val) /* {{{ */
{
_Bool slave_sql_running;
MYSQL *con;
- int state;
+ _Bool is_connected;
};
typedef struct mysql_database_s mysql_database_t; /* }}} */
static MYSQL *getconnection (mysql_database_t *db)
{
- if (db->state != 0)
+ if (db->is_connected)
{
- int err;
- if ((err = mysql_ping (db->con)) != 0)
- {
- /* Assured by "mysql_config_database" */
- assert (db->instance != NULL);
- WARNING ("mysql_ping failed for instance \"%s\": %s",
- db->instance,
- mysql_error (db->con));
- db->state = 0;
- }
- else
- {
- db->state = 1;
+ int status;
+
+ status = mysql_ping (db->con);
+ if (status == 0)
return (db->con);
- }
+
+ WARNING ("mysql plugin: Lost connection to instance \"%s\": %s",
+ db->instance, mysql_error (db->con));
}
+ db->is_connected = 0;
- if ((db->con = mysql_init (db->con)) == NULL)
+ if (db->con == NULL)
{
- ERROR ("mysql_init failed: %s", mysql_error (db->con));
- db->state = 0;
- return (NULL);
+ db->con = mysql_init (NULL);
+ if (db->con == NULL)
+ {
+ ERROR ("mysql plugin: mysql_init failed: %s",
+ mysql_error (db->con));
+ return (NULL);
+ }
}
if (mysql_real_connect (db->con, db->host, db->user, db->pass,
(db->database != NULL) ? db->database : "<none>",
(db->host != NULL) ? db->host : "localhost",
mysql_error (db->con));
- db->state = 0;
return (NULL);
}
- else
- {
- INFO ("mysql plugin: Successfully connected to database %s "
- "at server %s (server version: %s, protocol version: %d)",
- (db->database != NULL) ? db->database : "<none>",
- mysql_get_host_info (db->con),
- mysql_get_server_info (db->con),
- mysql_get_proto_info (db->con));
- db->state = 1;
- return (db->con);
- }
+
+ INFO ("mysql plugin: Successfully connected to database %s "
+ "at server %s (server version: %s, protocol version: %d)",
+ (db->database != NULL) ? db->database : "<none>",
+ mysql_get_host_info (db->con),
+ mysql_get_server_info (db->con),
+ mysql_get_proto_info (db->con));
+
+ db->is_connected = 1;
+ return (db->con);
} /* static MYSQL *getconnection (mysql_database_t *db) */
static void set_host (mysql_database_t *db, char *buf, size_t buflen)
/* Submits all the caches used by WAFL. Uses "submit_cache_ratio". */
static int submit_wafl_data (const char *hostname, const char *instance, /* {{{ */
- cfg_wafl_t *old_data, const cfg_wafl_t *new_data, int interval)
+ cfg_wafl_t *old_data, const cfg_wafl_t *new_data, cdtime_t interval)
{
/* Submit requested counters */
if (HAS_ALL_FLAGS (old_data->flags, CFG_WAFL_NAME_CACHE | HAVE_WAFL_NAME_CACHE)
*/
/* Data corresponding to <WAFL /> */
static int cna_handle_wafl_data (const char *hostname, cfg_wafl_t *cfg_wafl, /* {{{ */
- na_elem_t *data, int interval)
+ na_elem_t *data, cdtime_t interval)
{
cfg_wafl_t perf_data;
const char *plugin_inst;
return (-1);
}
- status = cna_handle_wafl_data (host->name, host->cfg_wafl, data, host->interval);
+ status = cna_handle_wafl_data (host->name, host->cfg_wafl, data,
+ host->cfg_wafl->interval.interval);
if (status == 0)
host->cfg_wafl->interval.last_read = now;
return (-1);
}
- status = cna_handle_disk_data (host->name, host->cfg_disk, data, host->interval);
+ status = cna_handle_disk_data (host->name, host->cfg_disk, data,
+ host->cfg_disk->interval.interval);
if (status == 0)
host->cfg_disk->interval.last_read = now;
return (-1);
}
- status = cna_handle_volume_perf_data (host->name, host->cfg_volume_perf, data, host->interval);
+ status = cna_handle_volume_perf_data (host->name, host->cfg_volume_perf, data,
+ host->cfg_volume_perf->interval.interval);
if (status == 0)
host->cfg_volume_perf->interval.last_read = now;
}
} /* for (elem_volume) */
- return (cna_submit_volume_usage_data (host->name, cfg_volume, host->interval));
+ return (cna_submit_volume_usage_data (host->name, cfg_volume,
+ host->cfg_volume_usage->interval.interval));
} /* }}} int cna_handle_volume_usage_data */
static int cna_setup_volume_usage (cfg_volume_usage_t *cvu) /* {{{ */
value *= 1024; /* disk-used reports kilobytes */
submit_double (host->name, plugin_instance,
/* type = */ "df_complex", /* type instance = */ NULL,
- (double)value, /* timestamp = */ 0, host->interval);
+ (double)value, /* timestamp = */ 0,
+ host->cfg_quota->interval.interval);
}
value = na_child_get_uint64 (elem_quota, "files-used", UINT64_MAX);
if (value != UINT64_MAX) {
submit_double (host->name, plugin_instance,
/* type = */ "files", /* type instance = */ NULL,
- (double)value, /* timestamp = */ 0, host->interval);
+ (double)value, /* timestamp = */ 0,
+ host->cfg_quota->interval.interval);
}
} /* for (elem_quota) */
return (-1);
}
- cna_handle_snapvault_data (host->name, host->cfg_snapvault, elem, host->interval);
+ cna_handle_snapvault_data (host->name, host->cfg_snapvault, elem,
+ host->cfg_snapvault->interval.interval);
na_elem_free (elem);
}
return (-1);
}
- status = cna_handle_system_data (host->name, host->cfg_system, data, host->interval);
+ status = cna_handle_system_data (host->name, host->cfg_system, data,
+ host->cfg_system->interval.interval);
if (status == 0)
host->cfg_system->interval.last_read = now;
/**
* collectd - src/network.c
- * Copyright (C) 2005-2010 Florian octo Forster
+ * Copyright (C) 2005-2013 Florian octo Forster
* Copyright (C) 2009 Aman Gupta
*
* This program is free software; you can redistribute it and/or modify it
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*
* Authors:
- * Florian octo Forster <octo at verplant.org>
+ * Florian octo Forster <octo at collectd.org>
* Aman Gupta <aman at tmm1.net>
**/
} /* }}} int network_dispatch_notification */
#if HAVE_LIBGCRYPT
+static void network_init_gcrypt (void) /* {{{ */
+{
+ /* http://lists.gnupg.org/pipermail/gcrypt-devel/2003-August/000458.html
+ * Because you can't know in a library whether another library has
+ * already initialized the library */
+ if (gcry_control (GCRYCTL_ANY_INITIALIZATION_P))
+ return;
+
+ gcry_check_version (NULL); /* before calling any other functions */
+ gcry_control (GCRYCTL_SET_THREAD_CBS, &gcry_threads_pthread);
+ gcry_control (GCRYCTL_INIT_SECMEM, 32768);
+ gcry_control (GCRYCTL_INITIALIZATION_FINISHED);
+} /* }}} void network_init_gcrypt */
+
static gcry_cipher_hd_t network_get_aes256_cypher (sockent_t *se, /* {{{ */
const void *iv, size_t iv_size, const char *username)
{
{
if (se->data.client.security_level > SECURITY_LEVEL_NONE)
{
+ network_init_gcrypt ();
+
if ((se->data.client.username == NULL)
|| (se->data.client.password == NULL))
{
{
if (se->data.server.security_level > SECURITY_LEVEL_NONE)
{
+ network_init_gcrypt ();
+
if (se->data.server.auth_file == NULL)
{
ERROR ("network plugin: Server socket with "
have_init = 1;
#if HAVE_LIBGCRYPT
- /* http://lists.gnupg.org/pipermail/gcrypt-devel/2003-August/000458.html
- * Because you can't know in a library whether another library has
- * already initialized the library
- */
- if (!gcry_control (GCRYCTL_ANY_INITIALIZATION_P))
- {
- gcry_check_version(NULL); /* before calling any other functions */
- gcry_control (GCRYCTL_SET_THREAD_CBS, &gcry_threads_pthread);
- gcry_control (GCRYCTL_INIT_SECMEM, 32768, 0);
- gcry_control (GCRYCTL_INITIALIZATION_FINISHED, 0);
- }
+ network_init_gcrypt ();
#endif
if (network_config_stats != 0)
/**
* collectd - src/nfs.c
* Copyright (C) 2005,2006 Jason Pepas
+ * Copyright (C) 2012,2013 Florian Forster
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
*
* Authors:
* Jason Pepas <cell at ices.utexas.edu>
- * Florian octo Forster <octo at verplant.org>
+ * Florian octo Forster <octo at collectd.org>
* Cosmin Ioiart <cioiart at gmail.com>
**/
#if HAVE_LIBKSTAT
static int nfs_read_kstat (kstat_t *ksp, int nfs_version, char *inst,
- const char **proc_names, size_t proc_names_num)
+ char const **proc_names, size_t proc_names_num)
{
char plugin_instance[DATA_MAX_NAME_LEN];
value_t values[proc_names_num];
kstat_read(kc, ksp, NULL);
for (i = 0; i < proc_names_num; i++)
- values[i].counter = (derive_t) get_kstat_value (ksp,
- (char *)proc_names[i]);
+ {
+ /* The name passed to kstat_data_lookup() doesn't have the
+ * "const" modifier, so we need to copy the name here. */
+ char name[32];
+ sstrncpy (name, proc_names[i], sizeof (name));
+
+ values[i].counter = (derive_t) get_kstat_value (ksp, name);
+ }
nfs_procedures_submit (plugin_instance, proc_names, values,
proc_names_num);
/* Let's make RFC822 message text with \r\n EOLs */
ssnprintf (buf, buf_len,
"MIME-Version: 1.0\r\n"
- "Content-Type: text/plain;\r\n"
+ "Content-Type: text/plain; charset=\"US-ASCII\"\r\n"
"Content-Transfer-Encoding: 8bit\r\n"
"Subject: %s\r\n"
"\r\n"
optional string description = 5;
repeated string tags = 7;
optional float ttl = 8;
+ repeated Attribute attributes = 9;
optional sint64 metric_sint64 = 13;
optional double metric_d = 14;
repeated State states = 4;
optional Query query = 5;
repeated Event events = 6;
-}
\ No newline at end of file
+}
+
+message Attribute {
+ required string key = 1;
+ optional string value = 2;
+}
/**
* collectd - src/rrdcached.c
- * Copyright (C) 2008-2012 Florian octo Forster
+ * Copyright (C) 2008-2013 Florian octo Forster
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
sstrncpy (vl.host, daemon_address, sizeof (vl.host));
sstrncpy (vl.plugin, "rrdcached", sizeof (vl.plugin));
+ status = rrdc_connect (daemon_address);
+ if (status != 0)
+ {
+ ERROR ("rrdcached plugin: rrdc_connect (%s) failed with status %i.",
+ daemon_address, status);
+ return (-1);
+ }
+
head = NULL;
status = rrdc_stats_get (&head);
if (status != 0)
return (ret);
} /* value_t csnmp_value_list_to_value */
-/* Returns true if all OIDs have left their subtree */
-static int csnmp_check_res_left_subtree (const host_definition_t *host,
- const data_definition_t *data,
- struct snmp_pdu *res)
-{
- struct variable_list *vb;
- int num_checked;
- int num_left_subtree;
- int i;
-
- vb = res->variables;
- if (vb == NULL)
- return (-1);
-
- num_checked = 0;
- num_left_subtree = 0;
-
- /* check all the variables and count how many have left their subtree */
- for (vb = res->variables, i = 0;
- (vb != NULL) && (i < data->values_len);
- vb = vb->next_variable, i++)
- {
- num_checked++;
-
- if ((vb->type == SNMP_ENDOFMIBVIEW)
- || (snmp_oid_ncompare (data->values[i].oid,
- data->values[i].oid_len,
- vb->name, vb->name_length,
- data->values[i].oid_len) != 0))
- num_left_subtree++;
- }
-
- /* check if enough variables have been returned */
- if (i < data->values_len)
- {
- ERROR ("snmp plugin: host %s: Expected %i variables, but got only %i",
- host->name, data->values_len, i);
- return (-1);
- }
-
- if (data->instance.oid.oid_len > 0)
- {
- if (vb == NULL)
- {
- ERROR ("snmp plugin: host %s: Expected one more variable for "
- "the instance..", host->name);
- return (-1);
- }
-
- num_checked++;
- if (snmp_oid_ncompare (data->instance.oid.oid,
- data->instance.oid.oid_len,
- vb->name, vb->name_length,
- data->instance.oid.oid_len) != 0)
- num_left_subtree++;
- }
-
- DEBUG ("snmp plugin: csnmp_check_res_left_subtree: %i of %i variables have "
- "left their subtree",
- num_left_subtree, num_checked);
- if (num_left_subtree >= num_checked)
- return (1);
- return (0);
-} /* int csnmp_check_res_left_subtree */
-
static int csnmp_strvbcopy_hexstring (char *dst, /* {{{ */
const struct variable_list *vb, size_t dst_size)
{
struct variable_list *vb;
const data_set_t *ds;
- oid_t *oid_list;
- uint32_t oid_list_len;
+
+ uint32_t oid_list_len = (uint32_t) (data->values_len + 1);
+ /* Holds the last OID returned by the device. We use this in the GETNEXT
+ * request to proceed. */
+ oid_t oid_list[oid_list_len];
+ /* Set to false when an OID has left its subtree so we don't re-request it
+ * again. */
+ _Bool oid_list_todo[oid_list_len];
int status;
int i;
+ uint32_t j;
/* `value_list_head' and `value_list_tail' implement a linked list for each
* value. `instance_list_head' and `instance_list_tail' implement a linked list of
}
/* We need a copy of all the OIDs, because GETNEXT will destroy them. */
- oid_list_len = data->values_len + 1;
- oid_list = (oid_t *) malloc (sizeof (oid_t) * (oid_list_len));
- if (oid_list == NULL)
- {
- ERROR ("snmp plugin: csnmp_read_table: malloc failed.");
- return (-1);
- }
memcpy (oid_list, data->values, data->values_len * sizeof (oid_t));
if (data->instance.oid.oid_len > 0)
memcpy (oid_list + data->values_len, &data->instance.oid, sizeof (oid_t));
- else
+ else /* no InstanceFrom option specified. */
oid_list_len--;
+ for (j = 0; j < oid_list_len; j++)
+ oid_list_todo[j] = 1;
+
/* We're going to construct n linked lists, one for each "value".
* value_list_head will contain pointers to the heads of these linked lists,
* value_list_tail will contain pointers to the tail of the lists. */
if ((value_list_head == NULL) || (value_list_tail == NULL))
{
ERROR ("snmp plugin: csnmp_read_table: calloc failed.");
- sfree (oid_list);
sfree (value_list_head);
sfree (value_list_tail);
return (-1);
status = 0;
while (status == 0)
{
+ int oid_list_todo_num;
+
req = snmp_pdu_create (SNMP_MSG_GETNEXT);
if (req == NULL)
{
break;
}
- for (i = 0; (uint32_t) i < oid_list_len; i++)
- snmp_add_null_var (req, oid_list[i].oid, oid_list[i].oid_len);
+ oid_list_todo_num = 0;
+ for (j = 0; j < oid_list_len; j++)
+ {
+ /* Do not rerequest already finished OIDs */
+ if (!oid_list_todo[j])
+ continue;
+ oid_list_todo_num++;
+ snmp_add_null_var (req, oid_list[j].oid, oid_list[j].oid_len);
+ }
+
+ if (oid_list_todo_num == 0)
+ {
+ /* The request is still empty - so we are finished */
+ DEBUG ("snmp plugin: all variables have left their subtree");
+ status = 0;
+ break;
+ }
res = NULL;
status = snmp_sess_synch_response (host->sess_handle, req, &res);
-
if ((status != STAT_SUCCESS) || (res == NULL))
{
char *errstr = NULL;
status = -1;
break;
}
+
status = 0;
assert (res != NULL);
c_release (LOG_INFO, &host->complaint,
break;
}
- /* Check if all values (and possibly the instance) have left their
- * subtree */
- if (csnmp_check_res_left_subtree (host, data, res) != 0)
+ for (vb = res->variables, i = 0; (vb != NULL); vb = vb->next_variable, i++)
{
- status = 0;
- break;
- }
+ /* Calculate value index from todo list */
+ while (!oid_list_todo[i] && (i < oid_list_len))
+ i++;
- /* Copy the OID of the value used as instance to oid_list, if an instance
- * is configured. */
- if (data->instance.oid.oid_len > 0)
- {
- /* Allocate a new `csnmp_list_instances_t', insert the instance name and
- * add it to the list */
- if (csnmp_instance_list_add (&instance_list_head, &instance_list_tail,
- res, host, data) != 0)
+ /* An instance is configured and the res variable we process is the
+ * instance value (last index) */
+ if ((data->instance.oid.oid_len > 0) && (i == data->values_len))
{
- ERROR ("snmp plugin: csnmp_instance_list_add failed.");
- status = -1;
- break;
- }
-
- /* The instance OID is added to the list of OIDs to GET from the
- * snmp agent last, so set vb on the last variable returned and copy
- * that OID. */
- for (vb = res->variables;
- (vb != NULL) && (vb->next_variable != NULL);
- vb = vb->next_variable)
- /* do nothing */;
- assert (vb != NULL);
-
- /* Copy the OID of the instance value to oid_list[data->values_len].
- * "oid_list" is used for the next GETNEXT request. */
- memcpy (oid_list[data->values_len].oid, vb->name,
- sizeof (oid) * vb->name_length);
- oid_list[data->values_len].oid_len = vb->name_length;
- }
-
- /* Iterate over all the (non-instance) values returned by the agent. The
- * (i < value_len) check will make sure we're not handling the instance OID
- * twice. */
- for (vb = res->variables, i = 0;
- (vb != NULL) && (i < data->values_len);
- vb = vb->next_variable, i++)
- {
- csnmp_table_values_t *vt;
- oid_t vb_name;
- oid_t suffix;
-
- csnmp_oid_init (&vb_name, vb->name, vb->name_length);
-
- /* Calculate the current suffix. This is later used to check that the
- * suffix is increasing. This also checks if we left the subtree */
- status = csnmp_oid_suffix (&suffix, &vb_name, data->values + i);
- if (status != 0)
- {
- DEBUG ("snmp plugin: host = %s; data = %s; Value %i failed. "
- "It probably left its subtree.",
- host->name, data->name, i);
- continue;
+ if ((vb->type == SNMP_ENDOFMIBVIEW)
+ || (snmp_oid_ncompare (data->instance.oid.oid,
+ data->instance.oid.oid_len,
+ vb->name, vb->name_length,
+ data->instance.oid.oid_len) != 0))
+ {
+ DEBUG ("snmp plugin: host = %s; data = %s; Instance left its subtree.",
+ host->name, data->name);
+ oid_list_todo[i] = 0;
+ continue;
+ }
+
+ /* Allocate a new `csnmp_list_instances_t', insert the instance name and
+ * add it to the list */
+ if (csnmp_instance_list_add (&instance_list_head, &instance_list_tail,
+ res, host, data) != 0)
+ {
+ ERROR ("snmp plugin: csnmp_instance_list_add failed.");
+ status = -1;
+ break;
+ }
}
-
- /* Make sure the OIDs returned by the agent are increasing. Otherwise our
- * table matching algorithm will get confused. */
- if ((value_list_tail[i] != NULL)
- && (csnmp_oid_compare (&suffix, &value_list_tail[i]->suffix) <= 0))
+ else /* The variable we are processing is a normal value */
{
- DEBUG ("snmp plugin: host = %s; data = %s; i = %i; "
- "Suffix is not increasing.",
- host->name, data->name, i);
- continue;
- }
+ csnmp_table_values_t *vt;
+ oid_t vb_name;
+ oid_t suffix;
+
+ csnmp_oid_init (&vb_name, vb->name, vb->name_length);
+
+ /* Calculate the current suffix. This is later used to check that the
+ * suffix is increasing. This also checks if we left the subtree */
+ status = csnmp_oid_suffix (&suffix, &vb_name, data->values + i);
+ if (status != 0)
+ {
+ DEBUG ("snmp plugin: host = %s; data = %s; i = %i; "
+ "Value probably left its subtree.",
+ host->name, data->name, i);
+ oid_list_todo[i] = 0;
+ continue;
+ }
+
+ /* Make sure the OIDs returned by the agent are increasing. Otherwise our
+ * table matching algorithm will get confused. */
+ if ((value_list_tail[i] != NULL)
+ && (csnmp_oid_compare (&suffix, &value_list_tail[i]->suffix) <= 0))
+ {
+ DEBUG ("snmp plugin: host = %s; data = %s; i = %i; "
+ "Suffix is not increasing.",
+ host->name, data->name, i);
+ oid_list_todo[i] = 0;
+ continue;
+ }
+
+ vt = malloc (sizeof (*vt));
+ if (vt == NULL)
+ {
+ ERROR ("snmp plugin: malloc failed.");
+ status = -1;
+ break;
+ }
+ memset (vt, 0, sizeof (*vt));
- vt = malloc (sizeof (*vt));
- if (vt == NULL)
- {
- ERROR ("snmp plugin: malloc failed.");
- status = -1;
- break;
+ vt->value = csnmp_value_list_to_value (vb, ds->ds[i].type,
+ data->scale, data->shift, host->name, data->name);
+ memcpy (&vt->suffix, &suffix, sizeof (vt->suffix));
+ vt->next = NULL;
+
+ if (value_list_tail[i] == NULL)
+ value_list_head[i] = vt;
+ else
+ value_list_tail[i]->next = vt;
+ value_list_tail[i] = vt;
}
- memset (vt, 0, sizeof (*vt));
- vt->value = csnmp_value_list_to_value (vb, ds->ds[i].type,
- data->scale, data->shift, host->name, data->name);
- memcpy (&vt->suffix, &suffix, sizeof (vt->suffix));
- vt->next = NULL;
-
- if (value_list_tail[i] == NULL)
- value_list_head[i] = vt;
- else
- value_list_tail[i]->next = vt;
- value_list_tail[i] = vt;
-
- /* Copy OID to oid_list[i + 1] */
+ /* Copy OID to oid_list[i] */
memcpy (oid_list[i].oid, vb->name, sizeof (oid) * vb->name_length);
oid_list[i].oid_len = vb->name_length;
- } /* for (i = data->values_len) */
+
+ } /* for (vb = res->variables ...) */
if (res != NULL)
snmp_free_pdu (res);
sfree (value_list_head);
sfree (value_list_tail);
- sfree (oid_list);
return (0);
} /* int csnmp_read_table */
if ((time_end - time_start) > host->interval)
{
WARNING ("snmp plugin: Host `%s' should be queried every %.3f "
- "seconds, but reading all values takes %.3f seconds.",
- host->name,
- CDTIME_T_TO_DOUBLE (host->interval),
- CDTIME_T_TO_DOUBLE (time_end - time_start));
+ "seconds, but reading all values takes %.3f seconds.",
+ host->name,
+ CDTIME_T_TO_DOUBLE (host->interval),
+ CDTIME_T_TO_DOUBLE (time_end - time_start));
}
if (success == 0)
v.gauge = value;
vl.values = &v;
+ vl.values_len = 1;
+
+ sstrncpy (vl.host, hostname_g, sizeof (vl.host));
sstrncpy (vl.plugin, "thermal", sizeof(vl.plugin));
if (plugin_instance != NULL)
sstrncpy (vl.plugin_instance, plugin_instance,
/* Look for the equal sign */
buffer = key;
- while (isalnum ((int) *buffer))
+ while (isalnum ((int) *buffer) || *buffer == '_')
buffer++;
if ((*buffer != '=') || (buffer == key))
return (1);
static char **riemann_tags;
static size_t riemann_tags_num;
-static int riemann_send(struct riemann_host *, Msg const *);
-static int riemann_notification(const notification_t *, user_data_t *);
-static int riemann_write(const data_set_t *, const value_list_t *, user_data_t *);
-static int riemann_connect(struct riemann_host *);
-static int riemann_disconnect (struct riemann_host *host);
-static void riemann_free(void *);
-static int riemann_config_node(oconfig_item_t *);
-static int riemann_config(oconfig_item_t *);
-void module_register(void);
-
static void riemann_event_protobuf_free (Event *event) /* {{{ */
{
if (event == NULL)
sfree (msg);
} /* }}} void riemann_msg_protobuf_free */
+/* host->lock must be held when calling this function. */
+static int
+riemann_connect(struct riemann_host *host)
+{
+ int e;
+ struct addrinfo *ai, *res, hints;
+ char const *node;
+ char const *service;
+
+ if (host->flags & F_CONNECT)
+ return 0;
+
+ memset(&hints, 0, sizeof(hints));
+ memset(&service, 0, sizeof(service));
+ hints.ai_family = AF_UNSPEC;
+ hints.ai_socktype = host->use_tcp ? SOCK_STREAM : SOCK_DGRAM;
+#ifdef AI_ADDRCONFIG
+ hints.ai_flags |= AI_ADDRCONFIG;
+#endif
+
+ node = (host->node != NULL) ? host->node : RIEMANN_HOST;
+ service = (host->service != NULL) ? host->service : RIEMANN_PORT;
+
+ if ((e = getaddrinfo(node, service, &hints, &res)) != 0) {
+ ERROR ("write_riemann plugin: Unable to resolve host \"%s\": %s",
+ node, gai_strerror(e));
+ return -1;
+ }
+
+ host->s = -1;
+ for (ai = res; ai != NULL; ai = ai->ai_next) {
+ if ((host->s = socket(ai->ai_family,
+ ai->ai_socktype,
+ ai->ai_protocol)) == -1) {
+ continue;
+ }
+
+ if (connect(host->s, ai->ai_addr, ai->ai_addrlen) != 0) {
+ close(host->s);
+ host->s = -1;
+ continue;
+ }
+
+ host->flags |= F_CONNECT;
+ DEBUG("write_riemann plugin: got a succesful connection for: %s:%s",
+ node, service);
+ break;
+ }
+
+ freeaddrinfo(res);
+
+ if (host->s < 0) {
+ WARNING("write_riemann plugin: Unable to connect to Riemann at %s:%s",
+ node, service);
+ return -1;
+ }
+ return 0;
+}
+
+/* host->lock must be held when calling this function. */
+static int
+riemann_disconnect (struct riemann_host *host)
+{
+ if ((host->flags & F_CONNECT) == 0)
+ return (0);
+
+ close (host->s);
+ host->s = -1;
+ host->flags &= ~F_CONNECT;
+
+ return (0);
+}
+
static int
riemann_send(struct riemann_host *host, Msg const *msg)
{
return 0;
}
-static int riemann_event_add_tag (Event *event, /* {{{ */
- char const *format, ...)
+static int riemann_event_add_tag (Event *event, char const *tag) /* {{{ */
{
- va_list ap;
- char buffer[1024];
- size_t ret;
-
- va_start (ap, format);
- ret = vsnprintf (buffer, sizeof (buffer), format, ap);
- if (ret >= sizeof (buffer))
- ret = sizeof (buffer) - 1;
- buffer[ret] = 0;
- va_end (ap);
-
- return (strarray_add (&event->tags, &event->n_tags, buffer));
+ return (strarray_add (&event->tags, &event->n_tags, tag));
} /* }}} int riemann_event_add_tag */
+static int riemann_event_add_attribute (Event *event, /* {{{ */
+ char const *key, char const *value)
+{
+ Attribute **new_attributes;
+ Attribute *a;
+
+ new_attributes = realloc (event->attributes,
+ sizeof (*event->attributes) * (event->n_attributes + 1));
+ if (new_attributes == NULL)
+ {
+ ERROR ("write_riemann plugin: realloc failed.");
+ return (ENOMEM);
+ }
+ event->attributes = new_attributes;
+
+ a = malloc (sizeof (*a));
+ if (a == NULL)
+ {
+ ERROR ("write_riemann plugin: malloc failed.");
+ return (ENOMEM);
+ }
+ attribute__init (a);
+
+ a->key = strdup (key);
+ if (value != NULL)
+ a->value = strdup (value);
+
+ event->attributes[event->n_attributes] = a;
+ event->n_attributes++;
+
+ return (0);
+} /* }}} int riemann_event_add_attribute */
+
static Msg *riemann_notification_to_protobuf (struct riemann_host *host, /* {{{ */
notification_t const *n)
{
event->state = strdup (severity);
riemann_event_add_tag (event, "notification");
+ if (n->host[0] != 0)
+ riemann_event_add_attribute (event, "host", n->host);
if (n->plugin[0] != 0)
- riemann_event_add_tag (event, "plugin:%s", n->plugin);
+ riemann_event_add_attribute (event, "plugin", n->plugin);
if (n->plugin_instance[0] != 0)
- riemann_event_add_tag (event, "plugin_instance:%s",
+ riemann_event_add_attribute (event, "plugin_instance",
n->plugin_instance);
if (n->type[0] != 0)
- riemann_event_add_tag (event, "type:%s", n->type);
+ riemann_event_add_attribute (event, "type", n->type);
if (n->type_instance[0] != 0)
- riemann_event_add_tag (event, "type_instance:%s",
+ riemann_event_add_attribute (event, "type_instance",
n->type_instance);
for (i = 0; i < riemann_tags_num; i++)
- riemann_event_add_tag (event, "%s", riemann_tags[i]);
+ riemann_event_add_tag (event, riemann_tags[i]);
format_name (service_buffer, sizeof (service_buffer),
/* host = */ "", n->plugin, n->plugin_instance,
event->ttl = CDTIME_T_TO_TIME_T (2 * vl->interval);
event->has_ttl = 1;
- riemann_event_add_tag (event, "plugin:%s", vl->plugin);
+ riemann_event_add_attribute (event, "plugin", vl->plugin);
if (vl->plugin_instance[0] != 0)
- riemann_event_add_tag (event, "plugin_instance:%s",
+ riemann_event_add_attribute (event, "plugin_instance",
vl->plugin_instance);
- riemann_event_add_tag (event, "type:%s", vl->type);
+ riemann_event_add_attribute (event, "type", vl->type);
if (vl->type_instance[0] != 0)
- riemann_event_add_tag (event, "type_instance:%s",
+ riemann_event_add_attribute (event, "type_instance",
vl->type_instance);
if ((ds->ds[index].type != DS_TYPE_GAUGE) && (rates != NULL))
{
- riemann_event_add_tag (event, "ds_type:%s:rate",
+ char ds_type[DATA_MAX_NAME_LEN];
+
+ ssnprintf (ds_type, sizeof (ds_type), "%s:rate",
DS_TYPE_TO_STRING(ds->ds[index].type));
+ riemann_event_add_attribute (event, "ds_type", ds_type);
}
else
{
- riemann_event_add_tag (event, "ds_type:%s",
+ riemann_event_add_attribute (event, "ds_type",
DS_TYPE_TO_STRING(ds->ds[index].type));
}
- riemann_event_add_tag (event, "ds_name:%s", ds->ds[index].name);
- riemann_event_add_tag (event, "ds_index:%zu", index);
+ riemann_event_add_attribute (event, "ds_name", ds->ds[index].name);
+ {
+ char ds_index[DATA_MAX_NAME_LEN];
+
+ ssnprintf (ds_index, sizeof (ds_index), "%zu", index);
+ riemann_event_add_attribute (event, "ds_index", ds_index);
+ }
for (i = 0; i < riemann_tags_num; i++)
- riemann_event_add_tag (event, "%s", riemann_tags[i]);
+ riemann_event_add_tag (event, riemann_tags[i]);
if (ds->ds[index].type == DS_TYPE_GAUGE)
{
return status;
}
-/* host->lock must be held when calling this function. */
-static int
-riemann_connect(struct riemann_host *host)
-{
- int e;
- struct addrinfo *ai, *res, hints;
- char const *node;
- char const *service;
-
- if (host->flags & F_CONNECT)
- return 0;
-
- memset(&hints, 0, sizeof(hints));
- memset(&service, 0, sizeof(service));
- hints.ai_family = AF_UNSPEC;
- hints.ai_socktype = host->use_tcp ? SOCK_STREAM : SOCK_DGRAM;
-#ifdef AI_ADDRCONFIG
- hints.ai_flags |= AI_ADDRCONFIG;
-#endif
-
- node = (host->node != NULL) ? host->node : RIEMANN_HOST;
- service = (host->service != NULL) ? host->service : RIEMANN_PORT;
-
- if ((e = getaddrinfo(node, service, &hints, &res)) != 0) {
- ERROR ("write_riemann plugin: Unable to resolve host \"%s\": %s",
- node, gai_strerror(e));
- return -1;
- }
-
- host->s = -1;
- for (ai = res; ai != NULL; ai = ai->ai_next) {
- if ((host->s = socket(ai->ai_family,
- ai->ai_socktype,
- ai->ai_protocol)) == -1) {
- continue;
- }
-
- if (connect(host->s, ai->ai_addr, ai->ai_addrlen) != 0) {
- close(host->s);
- host->s = -1;
- continue;
- }
-
- host->flags |= F_CONNECT;
- DEBUG("write_riemann plugin: got a succesful connection for: %s:%s",
- node, service);
- break;
- }
-
- freeaddrinfo(res);
-
- if (host->s < 0) {
- WARNING("write_riemann plugin: Unable to connect to Riemann at %s:%s",
- node, service);
- return -1;
- }
- return 0;
-}
-
-/* host->lock must be held when calling this function. */
-static int
-riemann_disconnect (struct riemann_host *host)
-{
- if ((host->flags & F_CONNECT) == 0)
- return (0);
-
- close (host->s);
- host->s = -1;
- host->flags &= ~F_CONNECT;
-
- return (0);
-}
-
static void
riemann_free(void *p)
{
#!/usr/bin/env bash
-DEFAULT_VERSION="5.2.1.git"
+DEFAULT_VERSION="5.3.0.git"
VERSION="`git describe 2> /dev/null | sed -e 's/^collectd-//'`"