From 0b6423f9c99d9edf8c96fefd0f6c453859395aa1 Mon Sep 17 00:00:00 2001 From: Holger Weiss Date: Mon, 30 Sep 2013 00:03:24 +0200 Subject: Import Nagios Plugins site Import the Nagios Plugins web site, Cronjobs, infrastructure scripts, and configuration files. --- web/attachments/104059-check_smtp.c.patch | 491 ++++++++++++++++++++++++++++++ 1 file changed, 491 insertions(+) create mode 100644 web/attachments/104059-check_smtp.c.patch (limited to 'web/attachments/104059-check_smtp.c.patch') diff --git a/web/attachments/104059-check_smtp.c.patch b/web/attachments/104059-check_smtp.c.patch new file mode 100644 index 0000000..4977bcc --- /dev/null +++ b/web/attachments/104059-check_smtp.c.patch @@ -0,0 +1,491 @@ +*** check_smtp.c Fri Mar 7 02:15:40 2003 +--- /usr/local/projects/nagios-plugins-1.3.1/plugins//check_smtp.c Wed Sep 29 15:14:33 2004 +*************** +*** 37,46 **** +--- 37,64 ---- + #include "config.h" + #include "common.h" + #include "netutils.h" + #include "utils.h" + ++ #ifdef HAVE_SSL ++ #include ++ #include ++ #include ++ #include ++ #endif ++ ++ #ifdef HAVE_SSL ++ int check_cert = FALSE; ++ int days_till_exp; ++ SSL_CTX *ctx; ++ SSL *ssl; ++ X509 *server_cert; ++ int connect_SSL (void); ++ int check_certificate (X509 **); ++ #endif ++ ++ + const char *progname = "check_smtp"; + + #define SMTP_PORT 25 + #define SMTP_EXPECT "220" + #define SMTP_HELO "HELO " +*************** +*** 57,66 **** +--- 75,85 ---- + */ + + #define SMTP_DUMMYCMD "MAIL " + #define SMTP_USE_DUMMYCMD 1 + #define SMTP_QUIT "QUIT\r\n" ++ #define SMTP_STARTTLS "STARTTLS\r\n" + + int process_arguments (int, char **); + int validate_arguments (void); + void print_help (void); + void print_usage (void); +*************** +*** 72,88 **** + int warning_time = 0; + int check_warning_time = FALSE; + int critical_time = 0; + int check_critical_time = FALSE; + int verbose = FALSE; + + int + main (int argc, char **argv) + { +! int sd; + int result = STATE_UNKNOWN; +- char buffer[MAX_INPUT_BUFFER] = ""; + char *from_str = NULL; + char *helocmd = NULL; + + if (process_arguments (argc, argv) != OK) + usage ("Invalid command arguments supplied\n"); +--- 91,116 ---- + int warning_time = 0; + int check_warning_time = FALSE; + int critical_time = 0; + int check_critical_time = FALSE; + int verbose = FALSE; ++ int use_ssl = FALSE; ++ int sd; ++ char timestamp[17] = ""; ++ //char *buffer = ""; ++ char buffer[MAX_INPUT_BUFFER] = ""; ++ enum { ++ TCP_PROTOCOL = 1, ++ UDP_PROTOCOL = 2, ++ MAXBUF = 1024 ++ }; + + int + main (int argc, char **argv) + { +! + int result = STATE_UNKNOWN; + char *from_str = NULL; + char *helocmd = NULL; + + if (process_arguments (argc, argv) != OK) + usage ("Invalid command arguments supplied\n"); +*************** +*** 114,130 **** + /* we connected, so close connection before exiting */ + if (result == STATE_OK) { + + /* watch for the SMTP connection string and */ + /* return a WARNING status if we couldn't read any data */ +! if (recv (sd, buffer, MAX_INPUT_BUFFER - 1, 0) == -1) { +! printf ("recv() failed\n"); + result = STATE_WARNING; + } + else { + /* strip the buffer of carriage returns */ +! strip (buffer); + /* make sure we find the response we are looking for */ + if (!strstr (buffer, server_expect)) { + if (server_port == SMTP_PORT) + printf ("Invalid SMTP response received from host\n"); + else +--- 142,158 ---- + /* we connected, so close connection before exiting */ + if (result == STATE_OK) { + + /* watch for the SMTP connection string and */ + /* return a WARNING status if we couldn't read any data */ +! if (recv(sd, buffer, MAX_INPUT_BUFFER-1, 0) == -1) { +! printf ("my_recv() failed\n"); + result = STATE_WARNING; + } + else { + /* strip the buffer of carriage returns */ +! strip (buffer); + /* make sure we find the response we are looking for */ + if (!strstr (buffer, server_expect)) { + if (server_port == SMTP_PORT) + printf ("Invalid SMTP response received from host\n"); + else +*************** +*** 132,162 **** + server_port); + result = STATE_WARNING; + } + } + + /* send the HELO command */ + send(sd, helocmd, strlen(helocmd), 0); + + /* allow for response to helo command to reach us */ +! recv(sd, buffer, MAX_INPUT_BUFFER-1, 0); +! + #ifdef SMTP_USE_DUMMYCMD + send(sd, from_str, strlen(from_str), 0); + + /* allow for response to DUMMYCMD to reach us */ +! recv(sd, buffer, MAX_INPUT_BUFFER-1, 0); + + if (verbose == TRUE) + printf("DUMMYCMD: %s\n%s\n",from_str,buffer); + #endif /* SMTP_USE_DUMMYCMD */ +! + /* tell the server we're done */ + send (sd, SMTP_QUIT, strlen (SMTP_QUIT), 0); + + /* finally close the connection */ +! close (sd); + } + + /* reset the alarm */ + alarm (0); + +--- 160,228 ---- + server_port); + result = STATE_WARNING; + } + } + ++ #ifdef HAVE_SSL ++ if(use_ssl) { ++ /* send the STARTTLS command */ ++ send(sd, SMTP_STARTTLS, strlen(SMTP_STARTTLS), 0); ++ ++ recv(sd, buffer, MAX_INPUT_BUFFER-1, 0); // wait for it ++ if(connect_STARTTLS() != OK) { ++ printf ("ERROR: Cannot create SSL context.\n"); ++ return STATE_CRITICAL; ++ } ++ if ( check_cert ) { ++ if ((server_cert = SSL_get_peer_certificate (ssl)) != NULL) { ++ result = check_certificate (&server_cert); ++ X509_free(server_cert); ++ } ++ else { ++ printf("ERROR: Cannot retrieve server certificate.\n"); ++ result = STATE_CRITICAL; ++ } ++ my_close (); ++ return result; ++ } ++ } ++ #endif ++ + /* send the HELO command */ ++ #ifdef HAVE_SSL ++ if (use_ssl) ++ SSL_write(ssl, helocmd, strlen (helocmd)); ++ else ++ #endif + send(sd, helocmd, strlen(helocmd), 0); + + /* allow for response to helo command to reach us */ +! my_recv(); +! #if defined(SMTP_USE_DUMMYCMD) && defined(HAVE_SSL) +! if (use_ssl) +! SSL_write(ssl,from_str, strlen(from_str)); +! else +! #endif + #ifdef SMTP_USE_DUMMYCMD + send(sd, from_str, strlen(from_str), 0); + + /* allow for response to DUMMYCMD to reach us */ +! my_recv(); + + if (verbose == TRUE) + printf("DUMMYCMD: %s\n%s\n",from_str,buffer); + #endif /* SMTP_USE_DUMMYCMD */ +! #ifdef HAVE_SSL +! if (use_ssl) +! SSL_write(ssl,SMTP_QUIT,strlen (SMTP_QUIT)); +! else +! #endif + /* tell the server we're done */ + send (sd, SMTP_QUIT, strlen (SMTP_QUIT), 0); + + /* finally close the connection */ +! my_close (); + } + + /* reset the alarm */ + alarm (0); + +*************** +*** 197,206 **** +--- 263,274 ---- + {"port", required_argument, 0, 'p'}, + {"from", required_argument, 0, 'f'}, + {"verbose", no_argument, 0, 'v'}, + {"version", no_argument, 0, 'V'}, + {"help", no_argument, 0, 'h'}, ++ {"starttls",no_argument,0,'S'}, ++ {"certificate",required_argument,0,'C'}, + {0, 0, 0, 0} + }; + #endif + + if (argc < 2) +*************** +*** 216,229 **** + } + + while (1) { + #ifdef HAVE_GETOPT_H + c = +! getopt_long (argc, argv, "+hVvt:p:f:e:c:w:H:", long_options, + &option_index); + #else +! c = getopt (argc, argv, "+?hVvt:p:f:e:c:w:H:"); + #endif + if (c == -1 || c == EOF) + break; + + switch (c) { +--- 284,297 ---- + } + + while (1) { + #ifdef HAVE_GETOPT_H + c = +! getopt_long (argc, argv, "+hVvt:p:f:e:c:w:H:SC:", long_options, + &option_index); + #else +! c = getopt (argc, argv, "+?hVvt:p:f:e:c:w:H:SC:"); + #endif + if (c == -1 || c == EOF) + break; + + switch (c) { +*************** +*** 276,285 **** +--- 344,369 ---- + } + else { + usage ("Time interval must be a nonnegative integer\n"); + } + break; ++ case 'S': ++ /* starttls */ ++ use_ssl = TRUE; ++ break; ++ case 'C': /* Check SSL cert validity */ ++ #ifdef HAVE_SSL ++ if (!is_intnonneg (optarg)) ++ usage2 ("invalid certificate expiration period", optarg); ++ days_till_exp = atoi (optarg); ++ check_cert = TRUE; ++ use_ssl = TRUE; ++ #else ++ terminate (STATE_UNKNOWN, ++ "SSL support not available. Install OpenSSL and recompile."); ++ #endif ++ break; + case 'V': /* version */ + print_revision (progname, "$Revision: 1.9.2.2 $"); + exit (STATE_OK); + case 'h': /* help */ + print_help (); +*************** +*** 344,353 **** +--- 428,443 ---- + " Seconds necessary to result in a warning status\n" + " -c, --critical=INTEGER\n" + " Seconds necessary to result in a critical status\n" + " -t, --timeout=INTEGER\n" + " Seconds before connection attempt times out (default: %d)\n" ++ #ifdef HAVE_SSL ++ " -S, --starttls\n" ++ " Use starttls for connection\n" ++ " -C, --certificate\n" ++ " Check certificate\n" ++ #endif + " -v, --verbose\n" + " Print extra information (command-line use only)\n" + " -h, --help\n" + " Print detailed help screen\n" + " -V, --version\n" +*************** +*** 365,370 **** +--- 455,615 ---- + { + printf + ("Usage: %s -H host [-e expect] [-p port] [-f from addr] [-w warn] [-c crit] [-t timeout] [-v]\n" + " %s --help\n" + " %s --version\n", progname, progname, progname); ++ } ++ ++ #ifdef HAVE_SSL ++ int ++ connect_STARTTLS (void) ++ { ++ SSL_METHOD *meth; ++ ++ /* Initialize SSL context */ ++ SSLeay_add_ssl_algorithms (); ++ meth = SSLv2_client_method (); ++ SSL_load_error_strings (); ++ if ((ctx = SSL_CTX_new (meth)) == NULL) ++ { ++ printf ("ERROR: Cannot create SSL context.\n"); ++ return STATE_CRITICAL; ++ } ++ /* Do the SSL handshake */ ++ if ((ssl = SSL_new (ctx)) != NULL) ++ { ++ SSL_set_fd (ssl, sd); ++ /* original version checked for -1 ++ I look for success instead (1) */ ++ if (SSL_connect (ssl) == 1) ++ return OK; ++ ERR_print_errors_fp (stderr); ++ } ++ else ++ { ++ printf ("ERROR: Cannot initiate SSL handshake.\n"); ++ } ++ /* this causes a seg fault ++ not sure why, being sloppy ++ and commenting it out */ ++ // SSL_free (ssl); ++ ++ ++ SSL_CTX_free (ctx); ++ my_close (); ++ ++ return STATE_CRITICAL; ++ } ++ #endif ++ ++ #ifdef HAVE_SSL ++ int ++ check_certificate (X509 ** certificate) ++ { ++ ASN1_STRING *tm; ++ int offset; ++ struct tm stamp; ++ int days_left; ++ ++ ++ /* Retrieve timestamp of certificate */ ++ tm = X509_get_notAfter (*certificate); ++ ++ /* Generate tm structure to process timestamp */ ++ if (tm->type == V_ASN1_UTCTIME) { ++ if (tm->length < 10) { ++ printf ("ERROR: Wrong time format in certificate.\n"); ++ return STATE_CRITICAL; ++ } ++ else { ++ stamp.tm_year = (tm->data[0] - '0') * 10 + (tm->data[1] - '0'); ++ if (stamp.tm_year < 50) ++ stamp.tm_year += 100; ++ offset = 0; ++ } ++ } ++ else { ++ if (tm->length < 12) { ++ printf ("ERROR: Wrong time format in certificate.\n"); ++ return STATE_CRITICAL; ++ } ++ else { ++ stamp.tm_year = ++ (tm->data[0] - '0') * 1000 + (tm->data[1] - '0') * 100 + ++ (tm->data[2] - '0') * 10 + (tm->data[3] - '0'); ++ stamp.tm_year -= 1900; ++ offset = 2; ++ } ++ } ++ stamp.tm_mon = ++ (tm->data[2 + offset] - '0') * 10 + (tm->data[3 + offset] - '0') - 1; ++ stamp.tm_mday = ++ (tm->data[4 + offset] - '0') * 10 + (tm->data[5 + offset] - '0'); ++ stamp.tm_hour = ++ (tm->data[6 + offset] - '0') * 10 + (tm->data[7 + offset] - '0'); ++ stamp.tm_min = ++ (tm->data[8 + offset] - '0') * 10 + (tm->data[9 + offset] - '0'); ++ stamp.tm_sec = 0; ++ stamp.tm_isdst = -1; ++ ++ days_left = (mktime (&stamp) - time (NULL)) / 86400; ++ snprintf ++ (timestamp, 16, "%02d/%02d/%04d %02d:%02d", ++ stamp.tm_mon + 1, ++ stamp.tm_mday, stamp.tm_year + 1900, stamp.tm_hour, stamp.tm_min); ++ ++ if (days_left > 0 && days_left <= days_till_exp) { ++ printf ("Certificate expires in %d day(s) (%s).\n", days_left, timestamp); ++ return STATE_WARNING; ++ } ++ if (days_left < 0) { ++ printf ("Certificate expired on %s.\n", timestamp); ++ return STATE_CRITICAL; ++ } ++ ++ if (days_left == 0) { ++ printf ("Certificate expires today (%s).\n", timestamp); ++ return STATE_WARNING; ++ } ++ ++ printf ("Certificate will expire on %s.\n", timestamp); ++ ++ return STATE_OK; ++ } ++ #endif ++ ++ int ++ my_recv (void) ++ { ++ int i; ++ ++ #ifdef HAVE_SSL ++ if (use_ssl) { ++ i = SSL_read (ssl, buffer, MAXBUF - 1); ++ } ++ else { ++ #endif ++ i = read (sd, buffer, MAXBUF - 1); ++ #ifdef HAVE_SSL ++ } ++ #endif ++ ++ return i; ++ } ++ ++ int ++ my_close (void) ++ { ++ #ifdef HAVE_SSL ++ if (use_ssl == TRUE) { ++ SSL_shutdown (ssl); ++ SSL_free (ssl); ++ SSL_CTX_free (ctx); ++ return 0; ++ } ++ else { ++ #endif ++ return close (sd); ++ #ifdef HAVE_SSL ++ } ++ #endif + } -- cgit v1.2.3-74-g34f1