X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=src%2Fcollectd-nagios.c;h=b190d6ee7a7f118bdcebea121856339ebc7542ca;hb=79f6d0d0005c09481208f9c99328a3754db2aaf7;hp=1d989cbd747ac9de096777d81c02760972c18db1;hpb=d324b71f4a80712261490d2c98bcca22a147c6c8;p=collectd.git diff --git a/src/collectd-nagios.c b/src/collectd-nagios.c index 1d989cbd..b190d6ee 100644 --- a/src/collectd-nagios.c +++ b/src/collectd-nagios.c @@ -1,6 +1,6 @@ /** * collectd-nagios - src/collectd-nagios.c - * Copyright (C) 2008 Florian octo Forster + * Copyright (C) 2008-2010 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 @@ -19,37 +19,14 @@ * Florian octo Forster **/ -/* Set to C99 and POSIX code */ -#ifndef _ISOC99_SOURCE -# define _ISOC99_SOURCE -#endif -#ifndef _POSIX_SOURCE -# define _POSIX_SOURCE -#endif -#ifndef _POSIX_C_SOURCE -# define _POSIX_C_SOURCE 200112L -#endif -#ifndef _REENTRANT -# define _REENTRANT -#endif - -/* Disable non-standard extensions */ -#ifdef _BSD_SOURCE -# undef _BSD_SOURCE -#endif -#ifdef _SVID_SOURCE -# undef _SVID_SOURCE -#endif -#ifdef _GNU_SOURCE -# undef _GNU_SOURCE +#if HAVE_CONFIG_H +# include "config.h" #endif #if !defined(__GNUC__) || !__GNUC__ # define __attribute__(x) /**/ #endif -#include "config.h" - #include #include #include @@ -119,6 +96,7 @@ static char *hostname_g = NULL; static range_t range_critical_g; static range_t range_warning_g; static int consolitation_g = CON_NONE; +static _Bool nan_is_error_g = 0; static char **match_ds_g = NULL; static int match_ds_num_g = 0; @@ -165,7 +143,7 @@ static int filter_ds (size_t *values_num, return (RET_UNKNOWN); } - for (i = 0; i < match_ds_num_g; i++) + for (i = 0; i < (size_t) match_ds_num_g; i++) { size_t j; @@ -273,10 +251,11 @@ static void usage (const char *name) " -d Select the DS to examine. May be repeated to examine multiple\n" " DSes. By default all DSes are used.\n" " -g Method to use to consolidate several DSes.\n" - " Valid arguments are `none', `average' and `sum'\n" + " See below for a list of valid arguments.\n" " -H Hostname to query the values for.\n" " -c Critical range\n" " -w Warning range\n" + " -m Treat \"Not a Number\" (NaN) as critical (default: warning)\n" "\n" "Consolidation functions:\n" " none: Apply the warning- and critical-ranges to each data-source\n" @@ -284,6 +263,8 @@ static void usage (const char *name) " average: Calculate the average of all matching DSes and apply the\n" " warning- and critical-ranges to the calculated average.\n" " sum: Apply the ranges to the sum of all DSes.\n" + " percentage: Apply the ranges to the ratio (in percent) of the first value\n" + " and the sum of all values." "\n", name); exit (1); } /* void usage */ @@ -296,12 +277,17 @@ static int do_check_con_none (size_t values_num, int num_okay = 0; const char *status_str = "UNKNOWN"; int status_code = RET_UNKNOWN; - int i; + size_t i; for (i = 0; i < values_num; i++) { if (isnan (values[i])) - num_warning++; + { + if (nan_is_error_g) + num_critical++; + else + num_warning++; + } else if (match_range (&range_critical_g, values[i]) != 0) num_critical++; else if (match_range (&range_warning_g, values[i]) != 0) @@ -337,7 +323,7 @@ static int do_check_con_none (size_t values_num, { printf (" |"); for (i = 0; i < values_num; i++) - printf (" %s=%g;;;;", values_names[i], values[i]); + printf (" %s=%f;;;;", values_names[i], values[i]); } printf ("\n"); @@ -347,7 +333,7 @@ static int do_check_con_none (size_t values_num, static int do_check_con_average (size_t values_num, double *values, char **values_names) { - int i; + size_t i; double total; int total_num; double average; @@ -358,11 +344,18 @@ static int do_check_con_average (size_t values_num, total_num = 0; for (i = 0; i < values_num; i++) { - if (!isnan (values[i])) + if (isnan (values[i])) { - total += values[i]; - total_num++; + if (!nan_is_error_g) + continue; + + printf ("CRITICAL: Data source \"%s\" is NaN\n", + values_names[i]); + return (RET_CRITICAL); } + + total += values[i]; + total_num++; } if (total_num == 0) @@ -391,7 +384,7 @@ static int do_check_con_average (size_t values_num, printf ("%s: %g average |", status_str, average); for (i = 0; i < values_num; i++) - printf (" %s=%g;;;;", values_names[i], values[i]); + printf (" %s=%f;;;;", values_names[i], values[i]); printf ("\n"); return (status_code); @@ -400,7 +393,7 @@ static int do_check_con_average (size_t values_num, static int do_check_con_sum (size_t values_num, double *values, char **values_names) { - int i; + size_t i; double total; int total_num; const char *status_str = "UNKNOWN"; @@ -410,11 +403,18 @@ static int do_check_con_sum (size_t values_num, total_num = 0; for (i = 0; i < values_num; i++) { - if (!isnan (values[i])) + if (isnan (values[i])) { - total += values[i]; - total_num++; + if (!nan_is_error_g) + continue; + + printf ("CRITICAL: Data source \"%s\" is NaN\n", + values_names[i]); + return (RET_CRITICAL); } + + total += values[i]; + total_num++; } if (total_num == 0) @@ -441,43 +441,71 @@ static int do_check_con_sum (size_t values_num, printf ("%s: %g sum |", status_str, total); for (i = 0; i < values_num; i++) - printf (" %s=%g;;;;", values_names[i], values[i]); + printf (" %s=%f;;;;", values_names[i], values[i]); printf ("\n"); return (status_code); } /* int do_check_con_sum */ -static int do_check_con_percentage (int values_num, double *values, char **values_names) +static int do_check_con_percentage (size_t values_num, + double *values, char **values_names) { - int i; + size_t i; + double sum = 0.0; double percentage; - if (values_num != 2) - return (RET_WARNING); - if (isnan (values[0]) || isnan (values[1])) - return (RET_WARNING); - if ((values[0] + values[1]) == 0) - return (RET_WARNING); + const char *status_str = "UNKNOWN"; + int status_code = RET_UNKNOWN; - percentage = 100 * values[1] / ( values[0] + values[1] ); + if ((values_num < 1) || (isnan (values[0]))) + { + printf ("WARNING: The first value is not defined\n"); + return (RET_WARNING); + } - printf ("%lf percentage |", percentage); for (i = 0; i < values_num; i++) - printf (" %s=%lf;;;;", values_names[i], values[i]); + { + if (isnan (values[i])) + { + if (!nan_is_error_g) + continue; + + printf ("CRITICAL: Data source \"%s\" is NaN\n", + values_names[i]); + return (RET_CRITICAL); + } + + sum += values[i]; + } + + if (sum == 0.0) + { + printf ("WARNING: Values sum up to zero\n"); + return (RET_WARNING); + } + + percentage = 100.0 * values[0] / sum; if (match_range (&range_critical_g, percentage) != 0) { - printf ("CRITICAL: percentage = %lf\n", percentage); - return (RET_CRITICAL); + status_str = "CRITICAL"; + status_code = RET_CRITICAL; } else if (match_range (&range_warning_g, percentage) != 0) { - printf ("WARNING: percentage = %lf\n", percentage); - return (RET_WARNING); - } + status_str = "WARNING"; + status_code = RET_WARNING; + } + else + { + status_str = "OKAY"; + status_code = RET_OKAY; + } - printf ("OKAY: percentage = %lf\n", percentage); - return (RET_OKAY); + printf ("%s: %lf percent |", status_str, percentage); + for (i = 0; i < values_num; i++) + printf (" %s=%lf;;;;", values_names[i], values[i]); + return (status_code); } /* int do_check_con_percentage */ static int do_check (void) @@ -567,7 +595,7 @@ int main (int argc, char **argv) { int c; - c = getopt (argc, argv, "w:c:s:n:H:g:d:h"); + c = getopt (argc, argv, "w:c:s:n:H:g:d:hm"); if (c < 0) break; @@ -598,7 +626,11 @@ int main (int argc, char **argv) else if (strcasecmp (optarg, "percentage") == 0) consolitation_g = CON_PERCENTAGE; else + { + fprintf (stderr, "Unknown consolidation function `%s'.\n", + optarg); usage (argv[0]); + } break; case 'd': { @@ -623,6 +655,9 @@ int main (int argc, char **argv) match_ds_num_g++; break; } + case 'm': + nan_is_error_g = 1; + break; default: usage (argv[0]); } /* switch (c) */ @@ -630,7 +665,10 @@ int main (int argc, char **argv) if ((socket_file_g == NULL) || (value_string_g == NULL) || (hostname_g == NULL)) + { + fprintf (stderr, "Missing required arguments.\n"); usage (argv[0]); + } return (do_check ()); } /* int main */