diff --git a/plugins/check_snmp.c b/plugins/check_snmp.c
index bb3d295e0f31fe0a14b822a7ccfeaf5f72648d1e..2bc6024f42bab4ca06475ab69473f3d1fc64e729 100644 (file)
--- a/plugins/check_snmp.c
+++ b/plugins/check_snmp.c
#define MAX_OIDS 8
+/* Gobble to string - stop incrementing c when c[0] match one of the
+ * characters in s */
+#define GOBBLE_TOS(c, s) while(c[0]!='\0' && strchr(s, c[0])==NULL) { c++; }
+/* Given c, keep track of backslashes (bk) and double-quotes (dq)
+ * from c[0] */
+#define COUNT_SEQ(c, bk, dq) switch(c[0]) {\
+ case '\\': \
+ if (bk) bk--; \
+ else bk++; \
+ break; \
+ case '"': \
+ if (!dq) { dq++; } \
+ else if(!bk) { dq--; } \
+ else { bk--; } \
+ break; \
+ }
+
+
+
int process_arguments (int, char **);
int validate_arguments (void);
char *thisarg (char *str);
int
main (int argc, char **argv)
{
- int i;
+ int i, len, line;
+ unsigned int bk_count = 0, dq_count = 0;
int iresult = STATE_UNKNOWN;
int result = STATE_UNKNOWN;
int return_code = 0;
char *cl_hidden_auth = NULL;
char *oidname = NULL;
char *response = NULL;
+ char *mult_resp = NULL;
char *outbuff;
char *ptr = NULL;
char *show = NULL;
}else{
snmpcmd = strdup (PATH_TO_SNMPGET);
}
-
+
/* 9 arguments to pass before authpriv options + 1 for host and numoids. Add one for terminating NULL */
command_line = calloc (9 + numauthpriv + 1 + numoids + 1, sizeof (char *));
command_line[0] = snmpcmd;
}
}
- for (i = 0; i < chld_out.lines; i++) {
+ for (line=0, i=0; line < chld_out.lines; line++, i++) {
const char *conv = "%.0f";
- ptr = chld_out.line[i];
+ ptr = chld_out.line[line];
oidname = strpcpy (oidname, ptr, delimiter);
response = strstr (ptr, delimiter);
+ if (response == NULL)
+ break;
+
if (verbose > 2) {
- printf("Processing line %i\n oidname: %s\n response: %s\n", i+1, oidname, response);
+ printf("Processing oid %i (line %i)\n oidname: %s\n response: %s\n", i+1, line+1, oidname, response);
}
- /* We strip out the datatype indicator for PHBs */
-
/* Clean up type array - Sol10 does not necessarily zero it out */
bzero(type, sizeof(type));
+ /* We strip out the datatype indicator for PHBs */
if (strstr (response, "Gauge: "))
show = strstr (response, "Gauge: ") + 7;
else if (strstr (response, "Gauge32: "))
else if (strstr (response, "STRING: ")) {
show = strstr (response, "STRING: ") + 8;
conv = "%.10g";
+
+ /* Get the rest of the string on multi-line strings */
+ ptr = show;
+ COUNT_SEQ(ptr, bk_count, dq_count)
+ while (dq_count && ptr[0] != '\n' && ptr[0] != '\0') {
+ ptr++;
+ GOBBLE_TOS(ptr, "\n\"\\")
+ COUNT_SEQ(ptr, bk_count, dq_count)
+ }
+
+ if (dq_count) { /* unfinished line */
+ /* copy show verbatim first */
+ if (!mult_resp) mult_resp = strdup("");
+ asprintf (&mult_resp, "%s%s:\n%s\n", mult_resp, oids[i], show);
+ /* then strip out unmatched double-quote from single-line output */
+ if (show[0] == '"') show++;
+
+ /* Keep reading until we match end of double-quoted string */
+ for (line++; line < chld_out.lines; line++) {
+ ptr = chld_out.line[line];
+ asprintf (&mult_resp, "%s%s\n", mult_resp, ptr);
+
+ COUNT_SEQ(ptr, bk_count, dq_count)
+ while (dq_count && ptr[0] != '\n' && ptr[0] != '\0') {
+ ptr++;
+ GOBBLE_TOS(ptr, "\n\"\\")
+ COUNT_SEQ(ptr, bk_count, dq_count)
+ }
+ /* Break for loop before next line increment when done */
+ if (!dq_count) break;
+ }
+ }
+
}
else if (strstr (response, "Timeticks: "))
show = strstr (response, "Timeticks: ");
if (nunits > (size_t)0 && (size_t)i < nunits && unitv[i] != NULL)
asprintf (&outbuff, "%s %s", outbuff, unitv[i]);
- if (is_numeric(show)) {
+ /* Write perfdata with whatever can be parsed by strtod, if possible */
+ ptr = NULL;
+ strtod(show, &ptr);
+ if (ptr > show) {
strncat(perfstr, oidname, sizeof(perfstr)-strlen(perfstr)-1);
strncat(perfstr, "=", sizeof(perfstr)-strlen(perfstr)-1);
- strncat(perfstr, show, sizeof(perfstr)-strlen(perfstr)-1);
+ len = sizeof(perfstr)-strlen(perfstr)-1;
+ strncat(perfstr, show, len>ptr-show ? ptr-show : len);
if (type)
strncat(perfstr, type, sizeof(perfstr)-strlen(perfstr)-1);
}
}
- printf ("%s %s -%s %s \n", label, state_text (result), outbuff, perfstr);
+ printf ("%s %s -%s %s\n", label, state_text (result), outbuff, perfstr);
+ if (mult_resp) printf ("%s", mult_resp);
return result;
}
*/
needmibs = TRUE;
}
- oids = calloc(MAX_OIDS, sizeof (char *));
+ if (!oids) oids = calloc(MAX_OIDS, sizeof (char *));
for (ptr = strtok(optarg, ", "); ptr != NULL && j < MAX_OIDS; ptr = strtok(NULL, ", "), j++) {
oids[j] = strdup(ptr);
}
print_usage ();
- printf (_(UT_HELP_VRSN));
- printf (_(UT_EXTRA_OPTS));
+ printf (UT_HELP_VRSN);
+ printf (UT_EXTRA_OPTS);
- printf (_(UT_HOST_PORT), 'p', DEFAULT_PORT);
+ printf (UT_HOST_PORT, 'p', DEFAULT_PORT);
/* SNMP and Authentication Protocol */
printf (" %s\n", "-n, --next");
printf (" %s\n", "-D, --output-delimiter=STRING");
printf (" %s\n", _("Separates output on multiple OID requests"));
- printf (_(UT_TIMEOUT), DEFAULT_SOCKET_TIMEOUT);
+ printf (UT_TIMEOUT, DEFAULT_SOCKET_TIMEOUT);
printf (" %s\n", "-e, --retries=INTEGER");
printf (" %s\n", _("Number of retries to be used in the requests"));
- printf (_(UT_VERBOSE));
+ printf (UT_VERBOSE);
printf ("\n");
printf ("%s\n", _("This plugin uses the 'snmpget' command included with the NET-SNMP package."));
printf (" %s\n", _("- Multiple OIDs may be indicated by a comma- or space-delimited list (lists with"));
printf (" %s\n", _("internal spaces must be quoted) [max 8 OIDs]"));
- printf(" -%s", _(UT_THRESHOLDS_NOTES));
+ printf(" -%s", UT_THRESHOLDS_NOTES);
printf (" %s\n", _("- When checking multiple OIDs, separate ranges by commas like '-w 1:10,1:,:20'"));
printf (" %s\n", _("- Note that only one string and one regex may be checked at present"));
printf (" %s\n", _("- All evaluation methods other than PR, STR, and SUBSTR expect that the value"));
printf (" %s\n", _("returned from the SNMP query is an unsigned integer."));
-#ifdef NP_EXTRA_OPTS
- printf (" -%s", _(UT_EXTRA_OPTS_NOTES));
-#endif
- printf (_(UT_SUPPORT));
+ printf (UT_SUPPORT);
}
void
print_usage (void)
{
- printf (_("Usage:"));
+ printf ("%s\n", _("Usage:"));
printf ("%s -H <ip_address> -o <OID> [-w warn_range] [-c crit_range]\n",progname);
printf ("[-C community] [-s string] [-r regex] [-R regexi] [-t timeout] [-e retries]\n");
printf ("[-l label] [-u units] [-p port-number] [-d delimiter] [-D output-delimiter]\n");