check_imap.c 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340
  1. /******************************************************************************
  2. *
  3. * CHECK_IMAP.C
  4. *
  5. * Program: IMAP4 plugin for Nagios
  6. * License: GPL
  7. * Copyright (c) 1999 Tom Shields (tom.shields@basswood.com)
  8. *
  9. * $Id$
  10. *
  11. * Description:
  12. *
  13. * This plugin will attempt to open an IMAP connection with the host.
  14. * Successul connects return STATE_OK, refusals and timeouts return
  15. * STATE_CRITICAL, other errors return STATE_UNKNOWN. Successful
  16. * connects, but incorrect reponse messages from the host result in
  17. * STATE_WARNING return values.
  18. *
  19. * Modifications:
  20. * 04-13-1999 Tom Shields
  21. * Initial code
  22. * 08-18-1999 Ethan Galstad <nagios@nagios.org>
  23. * Modified code to work with common plugin functions, added socket
  24. * timeout, string * length checking
  25. * 09-19-1999 Ethan Galstad <nagios@nagios.org>
  26. * Changed expect string from "+OK" to "* OK" and default port to 143
  27. *****************************************************************************/
  28. #include "config.h"
  29. #include "common.h"
  30. #include "netutils.h"
  31. #include "utils.h"
  32. #define PROGNAME "check_imap"
  33. #define PORT 143
  34. #define EXPECT "* OK"
  35. #define QUIT "a1 LOGOUT\n"
  36. int process_arguments (int, char **);
  37. int call_getopt (int, char **);
  38. int validate_arguments (void);
  39. int check_disk (int usp, int free_disk);
  40. void print_help (void);
  41. void print_usage (void);
  42. int server_port = PORT;
  43. char *server_address = NULL;
  44. char *server_expect = NULL;
  45. int warning_time = 0;
  46. int check_warning_time = FALSE;
  47. int critical_time = 0;
  48. int check_critical_time = FALSE;
  49. int verbose = FALSE;
  50. int
  51. main (int argc, char **argv)
  52. {
  53. int sd;
  54. int result;
  55. char buffer[MAX_INPUT_BUFFER];
  56. if (process_arguments (argc, argv) != OK)
  57. usage ("Invalid command arguments supplied\n");
  58. /* initialize alarm signal handling */
  59. signal (SIGALRM, socket_timeout_alarm_handler);
  60. /* set socket timeout */
  61. alarm (socket_timeout);
  62. /* try to connect to the host at the given port number */
  63. time (&start_time);
  64. result = my_tcp_connect (server_address, server_port, &sd);
  65. /* we connected, so close connection before exiting */
  66. if (result == STATE_OK) {
  67. /* watch for the IMAP connection string */
  68. result = recv (sd, buffer, MAX_INPUT_BUFFER - 1, 0);
  69. /* strip carriange returns */
  70. strip (buffer);
  71. /* return a WARNING status if we couldn't read any data */
  72. if (result == -1) {
  73. printf ("recv() failed\n");
  74. result = STATE_WARNING;
  75. }
  76. else {
  77. /* make sure we find the response we are looking for */
  78. if (!strstr (buffer, server_expect)) {
  79. if (server_port == server_port)
  80. printf ("Invalid IMAP response received from host\n");
  81. else
  82. printf ("Invalid IMAP response received from host on port %d\n",
  83. server_port);
  84. result = STATE_WARNING;
  85. }
  86. else {
  87. time (&end_time);
  88. printf ("IMAP ok - %d second response time\n",
  89. (int) (end_time - start_time));
  90. result = STATE_OK;
  91. }
  92. }
  93. /* close the connection */
  94. send (sd, QUIT, strlen (QUIT), 0);
  95. close (sd);
  96. }
  97. /* reset the alarm handler */
  98. alarm (0);
  99. return result;
  100. }
  101. /* process command-line arguments */
  102. int
  103. process_arguments (int argc, char **argv)
  104. {
  105. int c;
  106. if (argc < 2)
  107. return ERROR;
  108. for (c = 1; c < argc; c++) {
  109. if (strcmp ("-to", argv[c]) == 0)
  110. strcpy (argv[c], "-t");
  111. else if (strcmp ("-wt", argv[c]) == 0)
  112. strcpy (argv[c], "-w");
  113. else if (strcmp ("-ct", argv[c]) == 0)
  114. strcpy (argv[c], "-c");
  115. }
  116. c = 0;
  117. while ((c += (call_getopt (argc - c, &argv[c]))) < argc) {
  118. if (is_option (argv[c]))
  119. continue;
  120. if (server_address == NULL) {
  121. if (is_host (argv[c])) {
  122. server_address = argv[c];
  123. }
  124. else {
  125. usage ("Invalid host name");
  126. }
  127. }
  128. }
  129. if (server_address == NULL)
  130. server_address = strscpy (NULL, "127.0.0.1");
  131. if (server_expect == NULL)
  132. server_expect = strscpy (NULL, EXPECT);
  133. return validate_arguments ();
  134. }
  135. int
  136. call_getopt (int argc, char **argv)
  137. {
  138. int c, i = 0;
  139. #ifdef HAVE_GETOPT_H
  140. int option_index = 0;
  141. static struct option long_options[] = {
  142. {"hostname", required_argument, 0, 'H'},
  143. {"expect", required_argument, 0, 'e'},
  144. {"critical", required_argument, 0, 'c'},
  145. {"warning", required_argument, 0, 'w'},
  146. {"port", required_argument, 0, 'P'},
  147. {"verbose", no_argument, 0, 'v'},
  148. {"version", no_argument, 0, 'V'},
  149. {"help", no_argument, 0, 'h'},
  150. {0, 0, 0, 0}
  151. };
  152. #endif
  153. while (1) {
  154. #ifdef HAVE_GETOPT_H
  155. c =
  156. getopt_long (argc, argv, "+hVvt:p:e:c:w:H:", long_options,
  157. &option_index);
  158. #else
  159. c = getopt (argc, argv, "+?hVvt:p:e:c:w:H:");
  160. #endif
  161. i++;
  162. if (c == -1 || c == EOF || c == 1)
  163. break;
  164. switch (c) {
  165. case 't':
  166. case 'p':
  167. case 'e':
  168. case 'c':
  169. case 'w':
  170. case 'H':
  171. i++;
  172. }
  173. switch (c) {
  174. case 'H': /* hostname */
  175. if (is_host (optarg)) {
  176. server_address = optarg;
  177. }
  178. else {
  179. usage ("Invalid host name\n");
  180. }
  181. break;
  182. case 'p': /* port */
  183. if (is_intpos (optarg)) {
  184. server_port = atoi (optarg);
  185. }
  186. else {
  187. usage ("Server port must be a positive integer\n");
  188. }
  189. break;
  190. case 'e': /* username */
  191. server_expect = optarg;
  192. break;
  193. case 'c': /* critical time threshold */
  194. if (is_intnonneg (optarg)) {
  195. critical_time = atoi (optarg);
  196. check_critical_time = TRUE;
  197. }
  198. else {
  199. usage ("Critical time must be a nonnegative integer\n");
  200. }
  201. break;
  202. case 'w': /* warning time threshold */
  203. if (is_intnonneg (optarg)) {
  204. warning_time = atoi (optarg);
  205. check_warning_time = TRUE;
  206. }
  207. else {
  208. usage ("Warning time must be a nonnegative integer\n");
  209. }
  210. break;
  211. case 'v': /* verbose */
  212. verbose = TRUE;
  213. break;
  214. case 't': /* timeout */
  215. if (is_intnonneg (optarg)) {
  216. socket_timeout = atoi (optarg);
  217. }
  218. else {
  219. usage ("Time interval must be a nonnegative integer\n");
  220. }
  221. break;
  222. case 'V': /* version */
  223. print_revision (PROGNAME, "$Revision$");
  224. exit (STATE_OK);
  225. case 'h': /* help */
  226. print_help ();
  227. exit (STATE_OK);
  228. case '?': /* help */
  229. usage ("Invalid argument\n");
  230. }
  231. }
  232. return i;
  233. }
  234. int
  235. validate_arguments (void)
  236. {
  237. return OK;
  238. }
  239. void
  240. print_help (void)
  241. {
  242. print_revision (PROGNAME, "$Revision$");
  243. printf
  244. ("Copyright (c) 2000 Tom Shields/Karl DeBisschop\n\n"
  245. "This plugin tests the IMAP4 service on the specified host.\n\n");
  246. print_usage ();
  247. printf
  248. ("\nOptions:\n"
  249. " -H, --hostname=STRING or IPADDRESS\n"
  250. " Check server on the indicated host\n"
  251. " -p, --port=INTEGER\n"
  252. " Make connection on the indicated port (default: %d)\n"
  253. " -e, --expect=STRING\n"
  254. " String to expect in first line of server response (default: %s)\n"
  255. " -w, --warning=INTEGER\n"
  256. " Seconds necessary to result in a warning status\n"
  257. " -c, --critical=INTEGER\n"
  258. " Seconds necessary to result in a critical status\n"
  259. " -t, --timeout=INTEGER\n"
  260. " Seconds before connection attempt times out (default: %d)\n"
  261. " -v, --verbose\n"
  262. " Print extra information (command-line use only)\n"
  263. " -h, --help\n"
  264. " Print detailed help screen\n"
  265. " -V, --version\n"
  266. " Print version information\n\n",
  267. PORT, EXPECT, DEFAULT_SOCKET_TIMEOUT);
  268. support ();
  269. }
  270. void
  271. print_usage (void)
  272. {
  273. printf
  274. ("Usage: %s -H host [-e expect] [-p port] [-w warn] [-c crit]\n"
  275. " [-t timeout] [-v]\n"
  276. " %s --help\n"
  277. " %s --version\n", PROGNAME, PROGNAME, PROGNAME);
  278. }