1 /******************************************************************************
2 *
3 * Nagios check_disk plugin
4 *
5 * License: GPL
6 * Copyright (c) 1999-2006 nagios-plugins team
7 *
8 * Last Modified: $Date$
9 *
10 * Description:
11 *
12 * This file contains the check_disk plugin
13 *
14 * License Information:
15 *
16 * This program is free software; you can redistribute it and/or modify
17 * it under the terms of the GNU General Public License as published by
18 * the Free Software Foundation; either version 2 of the License, or
19 * (at your option) any later version.
20 *
21 * This program is distributed in the hope that it will be useful,
22 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 * GNU General Public License for more details.
25 *
26 * You should have received a copy of the GNU General Public License
27 * along with this program; if not, write to the Free Software
28 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29 *
30 * $Id$
31 *
32 *****************************************************************************/
34 const char *progname = "check_disk";
35 const char *program_name = "check_disk"; /* Required for coreutils libs */
36 const char *revision = "$Revision$";
37 const char *copyright = "1999-2006";
38 const char *email = "nagiosplug-devel@lists.sourceforge.net";
41 #include "common.h"
42 #if HAVE_INTTYPES_H
43 # include <inttypes.h>
44 #endif
45 #include <assert.h>
46 #include "popen.h"
47 #include "utils.h"
48 #include "utils_disk.h"
49 #include <stdarg.h>
50 #include "fsusage.h"
51 #include "mountlist.h"
52 #include "intprops.h" /* necessary for TYPE_MAXIMUM */
53 #if HAVE_LIMITS_H
54 # include <limits.h>
55 #endif
58 /* If nonzero, show inode information. */
59 static int inode_format = 1;
61 /* If nonzero, show even filesystems with zero size or
62 uninteresting types. */
63 static int show_all_fs = 1;
65 /* If nonzero, show only local filesystems. */
66 static int show_local_fs = 0;
68 /* If positive, the units to use when printing sizes;
69 if negative, the human-readable base. */
70 /* static int output_block_size; */
72 /* If nonzero, invoke the `sync' system call before getting any usage data.
73 Using this option can make df very slow, especially with many or very
74 busy disks. Note that this may make a difference on some systems --
75 SunOs4.1.3, for one. It is *not* necessary on Linux. */
76 /* static int require_sync = 0; */
78 /* Linked list of filesystem types to display.
79 If `fs_select_list' is NULL, list all types.
80 This table is generated dynamically from command-line options,
81 rather than hardcoding into the program what it thinks are the
82 valid filesystem types; let the user specify any filesystem type
83 they want to, and if there are any filesystems of that type, they
84 will be shown.
86 Some filesystem types:
87 4.2 4.3 ufs nfs swap ignore io vm efs dbg */
89 /* static struct parameter_list *fs_select_list; */
91 /* Linked list of filesystem types to omit.
92 If the list is empty, don't exclude any types. */
94 static struct name_list *fs_exclude_list;
96 static struct name_list *dp_exclude_list;
98 static struct parameter_list *path_select_list = NULL;
100 /* Linked list of mounted filesystems. */
101 static struct mount_entry *mount_list;
103 /* For long options that have no equivalent short option, use a
104 non-character as a pseudo short option, starting with CHAR_MAX + 1. */
105 enum
106 {
107 SYNC_OPTION = CHAR_MAX + 1,
108 NO_SYNC_OPTION,
109 BLOCK_SIZE_OPTION
110 };
112 #ifdef _AIX
113 #pragma alloca
114 #endif
116 /* Linked list of mounted filesystems. */
117 static struct mount_entry *mount_list;
119 int process_arguments (int, char **);
120 void print_path (const char *mypath);
121 int validate_arguments (uintmax_t, uintmax_t, double, double, double, double, char *);
122 void print_help (void);
123 void print_usage (void);
124 double calculate_percent(uintmax_t, uintmax_t);
126 double w_dfp = -1.0;
127 double c_dfp = -1.0;
128 char *path;
129 char *exclude_device;
130 char *units;
131 uintmax_t mult = 1024 * 1024;
132 int verbose = 0;
133 int erronly = FALSE;
134 int display_mntp = FALSE;
135 int exact_match = FALSE;
136 char *warn_freespace_units = NULL;
137 char *crit_freespace_units = NULL;
138 char *warn_freespace_percent = NULL;
139 char *crit_freespace_percent = NULL;
140 char *warn_usedspace_units = NULL;
141 char *crit_usedspace_units = NULL;
142 char *warn_usedspace_percent = NULL;
143 char *crit_usedspace_percent = NULL;
144 char *warn_usedinodes_percent = NULL;
145 char *crit_usedinodes_percent = NULL;
148 int
149 main (int argc, char **argv)
150 {
151 int result = STATE_UNKNOWN;
152 int disk_result = STATE_UNKNOWN;
153 char *output;
154 char *details;
155 char *perf;
156 char *preamble;
157 double inode_space_pct;
158 uintmax_t total, available, available_to_root, used;
159 double dfree_pct = -1, dused_pct = -1;
160 double dused_units, dfree_units, dtotal_units;
161 double dused_inodes_percent, dfree_inodes_percent;
162 double warning_high_tide = UINT_MAX;
163 double critical_high_tide = UINT_MAX;
164 int temp_result;
166 struct mount_entry *me;
167 struct fs_usage fsp;
168 struct parameter_list *temp_list, *path;
169 struct name_list *seen = NULL;
171 preamble = strdup (" - free space:");
172 output = strdup ("");
173 details = strdup ("");
174 perf = strdup ("");
176 setlocale (LC_ALL, "");
177 bindtextdomain (PACKAGE, LOCALEDIR);
178 textdomain (PACKAGE);
180 mount_list = read_file_system_list (0);
182 if (process_arguments (argc, argv) == ERROR)
183 usage4 (_("Could not parse arguments"));
185 /* If a list of paths has not been selected, find entire
186 mount list and create list of paths
187 */
188 if (! path_select_list) {
189 for (me = mount_list; me; me = me->me_next) {
190 path = np_add_parameter(&path_select_list, me->me_mountdir);
191 path->best_match = me;
192 set_thresholds(&path->freespace_units, warn_freespace_units, crit_freespace_units);
193 set_thresholds(&path->freespace_percent, warn_freespace_percent, crit_freespace_percent);
194 set_thresholds(&path->usedspace_units, warn_usedspace_units, crit_usedspace_units);
195 set_thresholds(&path->usedspace_percent, warn_usedspace_percent, crit_usedspace_percent);
196 set_thresholds(&path->usedinodes_percent, warn_usedinodes_percent, crit_usedinodes_percent);
197 }
198 } else {
199 np_set_best_match(path_select_list, mount_list, exact_match);
201 /* Error if no match found for specified paths */
202 temp_list = path_select_list;
203 while (temp_list) {
204 if (! temp_list->best_match) {
205 die (STATE_CRITICAL, _("DISK %s: %s not found\n"), _("CRITICAL"), temp_list->name);
206 }
207 temp_list = temp_list->name_next;
208 }
209 }
211 /* Process for every path in list */
212 for (path = path_select_list; path; path=path->name_next) {
214 /* reset disk result */
215 disk_result = STATE_UNKNOWN;
217 me = path->best_match;
219 /* Filters */
221 /* Remove filesystems already seen */
222 if (np_seen_name(seen, me->me_mountdir)) {
223 continue;
224 } else {
225 np_add_name(&seen, me->me_mountdir);
226 }
227 /* Skip remote filesystems if we're not interested in them */
228 if (me->me_remote && show_local_fs) {
229 continue;
230 /* Skip pseudo fs's if we haven't asked for all fs's */
231 } else if (me->me_dummy && !show_all_fs) {
232 continue;
233 /* Skip excluded fstypes */
234 } else if (fs_exclude_list && np_find_name (fs_exclude_list, me->me_type)) {
235 continue;
236 /* Skip excluded fs's */
237 } else if (dp_exclude_list &&
238 (np_find_name (dp_exclude_list, me->me_devname) ||
239 np_find_name (dp_exclude_list, me->me_mountdir))) {
240 continue;
241 }
243 get_fs_usage (me->me_mountdir, me->me_devname, &fsp);
245 if (fsp.fsu_blocks && strcmp ("none", me->me_mountdir)) {
246 total = fsp.fsu_blocks;
247 available = fsp.fsu_bavail;
248 available_to_root = fsp.fsu_bfree;
249 used = total - available_to_root;
251 dused_pct = calculate_percent( used, used + available ); /* used + available can never be > uintmax */
253 dfree_pct = 100 - dused_pct;
254 dused_units = used*fsp.fsu_blocksize/mult;
255 dfree_units = available*fsp.fsu_blocksize/mult;
256 dtotal_units = total*fsp.fsu_blocksize/mult;
257 dused_inodes_percent = calculate_percent(fsp.fsu_files - fsp.fsu_ffree, fsp.fsu_files);
258 dfree_inodes_percent = 100 - dused_inodes_percent;
260 if (verbose >= 3) {
261 printf ("For %s, used_pct=%g free_pct=%g used_units=%g free_units=%g total_units=%g used_inodes_pct=%g\n",
262 me->me_mountdir, dused_pct, dfree_pct, dused_units, dfree_units, dtotal_units, dused_inodes_percent);
263 }
265 /* Threshold comparisons */
267 temp_result = get_status(dfree_units, path->freespace_units);
268 if (verbose >=3) printf("Freespace_units result=%d\n", temp_result);
269 disk_result = max_state( disk_result, temp_result );
271 temp_result = get_status(dfree_pct, path->freespace_percent);
272 if (verbose >=3) printf("Freespace%% result=%d\n", temp_result);
273 disk_result = max_state( disk_result, temp_result );
275 temp_result = get_status(dused_units, path->usedspace_units);
276 if (verbose >=3) printf("Usedspace_units result=%d\n", temp_result);
277 disk_result = max_state( disk_result, temp_result );
279 temp_result = get_status(dused_pct, path->usedspace_percent);
280 if (verbose >=3) printf("Usedspace_percent result=%d\n", temp_result);
281 disk_result = max_state( disk_result, temp_result );
283 temp_result = get_status(dused_inodes_percent, path->usedinodes_percent);
284 if (verbose >=3) printf("Usedinodes_percent result=%d\n", temp_result);
285 disk_result = max_state( disk_result, temp_result );
287 result = max_state(result, disk_result);
289 /* What a mess of units. The output shows free space, the perf data shows used space. Yikes!
290 Hack here. Trying to get warn/crit levels from freespace_(units|percent) for perf
291 data. Assumption that start=0. Roll on new syntax...
292 */
293 if (path->freespace_units->warning != NULL) {
294 warning_high_tide = dtotal_units - path->freespace_units->warning->end;
295 }
296 if (path->freespace_percent->warning != NULL) {
297 warning_high_tide = abs( min( (double) warning_high_tide, (double) (1.0 - path->freespace_percent->warning->end/100)*dtotal_units ));
298 }
299 if (path->freespace_units->critical != NULL) {
300 critical_high_tide = dtotal_units - path->freespace_units->critical->end;
301 }
302 if (path->freespace_percent->critical != NULL) {
303 critical_high_tide = abs( min( (double) critical_high_tide, (double) (1.0 - path->freespace_percent->critical->end/100)*dtotal_units ));
304 }
306 asprintf (&perf, "%s %s", perf,
307 perfdata ((!strcmp(me->me_mountdir, "none") || display_mntp) ? me->me_devname : me->me_mountdir,
308 dused_units, units,
309 TRUE, warning_high_tide,
310 TRUE, critical_high_tide,
311 TRUE, 0,
312 TRUE, dtotal_units));
314 if (disk_result==STATE_OK && erronly && !verbose)
315 continue;
317 if (disk_result!=STATE_OK || verbose>=0) {
318 asprintf (&output, "%s %s %.0f %s (%.0f%%",
319 output,
320 (!strcmp(me->me_mountdir, "none") || display_mntp) ? me->me_devname : me->me_mountdir,
321 dfree_units,
322 units,
323 dfree_pct);
324 if (dused_inodes_percent < 0) {
325 asprintf(&output, "%s inode=-);", output);
326 } else {
327 asprintf(&output, "%s inode=%.0f%%);", output, dfree_inodes_percent );
328 }
329 }
331 /* TODO: Need to do a similar debug line
332 asprintf (&details, _("%s\n\
333 %.0f of %.0f %s (%.0f%% inode=%.0f%%) free on %s (type %s mounted on %s) warn:%lu crit:%lu warn%%:%.0f%% crit%%:%.0f%%"),
334 details, dfree_units, dtotal_units, units, dfree_pct, inode_space_pct,
335 me->me_devname, me->me_type, me->me_mountdir,
336 (unsigned long)w_df, (unsigned long)c_df, w_dfp, c_dfp);
337 */
339 }
341 }
343 if (verbose > 2)
344 asprintf (&output, "%s%s", output, details);
347 printf ("DISK %s%s%s|%s\n", state_text (result), (erronly && result==STATE_OK) ? "" : preamble, output, perf);
348 return result;
349 }
352 double calculate_percent(uintmax_t value, uintmax_t total) {
353 double pct = -1;
354 /* I don't understand the below, but it is taken from coreutils' df */
355 /* Seems to be calculating pct, in the best possible way */
356 if (value <= TYPE_MAXIMUM(uintmax_t) / 100
357 && total != 0) {
358 uintmax_t u100 = value * 100;
359 pct = u100 / total + (u100 % total != 0);
360 } else {
361 /* Possible rounding errors - see coreutils' df for more explanation */
362 double u = value;
363 double t = total;
364 if (t) {
365 long int lipct = pct = u * 100 / t;
366 double ipct = lipct;
368 /* Like 'pct = ceil (dpct);', but without ceil - from coreutils again */
369 if (ipct - 1 < pct && pct <= ipct + 1)
370 pct = ipct + (ipct < pct);
371 }
372 }
373 return pct;
374 }
376 /* process command-line arguments */
377 int
378 process_arguments (int argc, char **argv)
379 {
380 int c;
381 struct parameter_list *se;
382 struct parameter_list *temp_list;
383 int result = OK;
384 struct stat *stat_buf;
386 int option = 0;
387 static struct option longopts[] = {
388 {"timeout", required_argument, 0, 't'},
389 {"warning", required_argument, 0, 'w'},
390 {"critical", required_argument, 0, 'c'},
391 {"iwarning", required_argument, 0, 'W'},
392 /* Dang, -C is taken. We might want to reshuffle this. */
393 {"icritical", required_argument, 0, 'K'},
394 {"local", required_argument, 0, 'l'},
395 {"kilobytes", required_argument, 0, 'k'},
396 {"megabytes", required_argument, 0, 'm'},
397 {"units", required_argument, 0, 'u'},
398 {"path", required_argument, 0, 'p'},
399 {"partition", required_argument, 0, 'p'},
400 {"exclude_device", required_argument, 0, 'x'},
401 {"exclude-type", required_argument, 0, 'X'},
402 {"mountpoint", no_argument, 0, 'M'},
403 {"errors-only", no_argument, 0, 'e'},
404 {"exact-match", no_argument, 0, 'E'},
405 {"verbose", no_argument, 0, 'v'},
406 {"quiet", no_argument, 0, 'q'},
407 {"clear", no_argument, 0, 'C'},
408 {"version", no_argument, 0, 'V'},
409 {"help", no_argument, 0, 'h'},
410 {0, 0, 0, 0}
411 };
413 if (argc < 2)
414 return ERROR;
416 np_add_name(&fs_exclude_list, "iso9660");
418 for (c = 1; c < argc; c++)
419 if (strcmp ("-to", argv[c]) == 0)
420 strcpy (argv[c], "-t");
422 while (1) {
423 c = getopt_long (argc, argv, "+?VqhveCt:c:w:K:W:u:p:x:X:mklME", longopts, &option);
425 if (c == -1 || c == EOF)
426 break;
428 switch (c) {
429 case 't': /* timeout period */
430 if (is_integer (optarg)) {
431 timeout_interval = atoi (optarg);
432 break;
433 }
434 else {
435 usage2 (_("Timeout interval must be a positive integer"), optarg);
436 }
438 /* See comments for 'c' */
439 case 'w': /* warning threshold */
440 if (strstr(optarg, "%")) {
441 if (*optarg == '@') {
442 warn_freespace_percent = optarg;
443 } else {
444 asprintf(&warn_freespace_percent, "@%s", optarg);
445 }
446 } else {
447 if (*optarg == '@') {
448 warn_freespace_units = optarg;
449 } else {
450 asprintf(&warn_freespace_units, "@%s", optarg);
451 }
452 }
453 break;
455 /* Awful mistake where the range values do not make sense. Normally,
456 you alert if the value is within the range, but since we are using
457 freespace, we have to alert if outside the range. Thus we artifically
458 force @ at the beginning of the range, so that it is backwards compatible
459 */
460 case 'c': /* critical threshold */
461 if (strstr(optarg, "%")) {
462 if (*optarg == '@') {
463 crit_freespace_percent = optarg;
464 } else {
465 asprintf(&crit_freespace_percent, "@%s", optarg);
466 }
467 } else {
468 if (*optarg == '@') {
469 crit_freespace_units = optarg;
470 } else {
471 asprintf(&crit_freespace_units, "@%s", optarg);
472 }
473 }
474 break;
476 case 'W': /* warning inode threshold */
477 warn_usedinodes_percent = optarg;
478 break;
479 case 'K': /* critical inode threshold */
480 crit_usedinodes_percent = optarg;
481 break;
482 case 'u':
483 if (units)
484 free(units);
485 if (! strcmp (optarg, "bytes")) {
486 mult = (uintmax_t)1;
487 units = strdup ("B");
488 } else if (! strcmp (optarg, "kB")) {
489 mult = (uintmax_t)1024;
490 units = strdup ("kB");
491 } else if (! strcmp (optarg, "MB")) {
492 mult = (uintmax_t)1024 * 1024;
493 units = strdup ("MB");
494 } else if (! strcmp (optarg, "GB")) {
495 mult = (uintmax_t)1024 * 1024 * 1024;
496 units = strdup ("GB");
497 } else if (! strcmp (optarg, "TB")) {
498 mult = (uintmax_t)1024 * 1024 * 1024 * 1024;
499 units = strdup ("TB");
500 } else {
501 die (STATE_UNKNOWN, _("unit type %s not known\n"), optarg);
502 }
503 if (units == NULL)
504 die (STATE_UNKNOWN, _("failed allocating storage for '%s'\n"), "units");
505 break;
506 case 'k': /* display mountpoint */
507 mult = 1024;
508 if (units)
509 free(units);
510 units = strdup ("kB");
511 break;
512 case 'm': /* display mountpoint */
513 mult = 1024 * 1024;
514 if (units)
515 free(units);
516 units = strdup ("MB");
517 break;
518 case 'l':
519 show_local_fs = 1;
520 break;
521 case 'p': /* select path */
522 if (! (warn_freespace_units || crit_freespace_units || warn_freespace_percent ||
523 crit_freespace_percent || warn_usedspace_units || crit_usedspace_units ||
524 warn_usedspace_percent || crit_usedspace_percent || warn_usedinodes_percent ||
525 crit_usedinodes_percent)) {
526 die (STATE_UNKNOWN, "DISK %s: %s", _("UNKNOWN"), _("Must set a threshold value before using -p\n"));
527 }
528 se = np_add_parameter(&path_select_list, optarg);
529 set_thresholds(&se->freespace_units, warn_freespace_units, crit_freespace_units);
530 set_thresholds(&se->freespace_percent, warn_freespace_percent, crit_freespace_percent);
531 set_thresholds(&se->usedspace_units, warn_usedspace_units, crit_usedspace_units);
532 set_thresholds(&se->usedspace_percent, warn_usedspace_percent, crit_usedspace_percent);
533 set_thresholds(&se->usedinodes_percent, warn_usedinodes_percent, crit_usedinodes_percent);
534 break;
535 case 'x': /* exclude path or partition */
536 np_add_name(&dp_exclude_list, optarg);
537 break;
538 case 'X': /* exclude file system type */
539 np_add_name(&fs_exclude_list, optarg);
540 break;
541 case 'v': /* verbose */
542 verbose++;
543 break;
544 case 'q': /* verbose */
545 verbose--;
546 break;
547 case 'e':
548 erronly = TRUE;
549 break;
550 case 'E':
551 exact_match = TRUE;
552 break;
553 case 'M': /* display mountpoint */
554 display_mntp = TRUE;
555 break;
556 case 'C':
557 warn_freespace_units = NULL;
558 crit_freespace_units = NULL;
559 warn_usedspace_units = NULL;
560 crit_usedspace_units = NULL;
561 warn_freespace_percent = NULL;
562 crit_freespace_percent = NULL;
563 warn_usedspace_percent = NULL;
564 crit_usedspace_percent = NULL;
565 warn_usedinodes_percent = NULL;
566 crit_usedinodes_percent = NULL;
567 break;
568 case 'V': /* version */
569 print_revision (progname, revision);
570 exit (STATE_OK);
571 case 'h': /* help */
572 print_help ();
573 exit (STATE_OK);
574 case '?': /* help */
575 usage (_("Unknown argument"));
576 }
577 }
579 /* Support for "check_disk warn crit [fs]" with thresholds at used% level */
580 c = optind;
581 if (warn_usedspace_percent == NULL && argc > c && is_intnonneg (argv[c]))
582 warn_usedspace_percent = argv[c++];
584 if (crit_usedspace_percent == NULL && argc > c && is_intnonneg (argv[c]))
585 crit_usedspace_percent = argv[c++];
587 if (argc > c && path == NULL) {
588 se = np_add_parameter(&path_select_list, strdup(argv[c++]));
589 set_thresholds(&se->freespace_units, warn_freespace_units, crit_freespace_units);
590 set_thresholds(&se->freespace_percent, warn_freespace_percent, crit_freespace_percent);
591 set_thresholds(&se->usedspace_units, warn_usedspace_units, crit_usedspace_units);
592 set_thresholds(&se->usedspace_percent, warn_usedspace_percent, crit_usedspace_percent);
593 set_thresholds(&se->usedinodes_percent, warn_usedinodes_percent, crit_usedinodes_percent);
594 }
596 if (units == NULL) {
597 units = strdup ("MB");
598 mult = (uintmax_t)1024 * 1024;
599 }
601 if (path_select_list) {
602 temp_list = path_select_list;
603 stat_buf = malloc(sizeof *stat_buf);
604 while (temp_list) {
605 /* Stat each entry to check that dir exists */
606 if (stat (temp_list->name, &stat_buf[0])) {
607 printf("DISK %s - ", _("CRITICAL"));
608 die (STATE_CRITICAL, _("%s does not exist\n"), temp_list->name);
609 }
610 /* if (validate_arguments (temp_list->w_df,
611 temp_list->c_df,
612 temp_list->w_dfp,
613 temp_list->c_dfp,
614 temp_list->w_idfp,
615 temp_list->c_idfp,
616 temp_list->name) == ERROR)
617 result = ERROR;
618 */
619 temp_list = temp_list->name_next;
620 }
621 free(stat_buf);
622 return result;
623 } else {
624 return TRUE;
625 /* return validate_arguments (w_df, c_df, w_dfp, c_dfp, w_idfp, c_idfp, NULL); */
626 }
627 }
631 void
632 print_path (const char *mypath)
633 {
634 if (mypath == NULL)
635 printf ("\n");
636 else
637 printf (_(" for %s\n"), mypath);
639 //return;
640 }
644 /* TODO: Remove?
646 int
647 validate_arguments (uintmax_t w, uintmax_t c, double wp, double cp, double iwp, double icp, char *mypath)
648 {
649 if (w < 0 && c < 0 && wp < 0.0 && cp < 0.0) {
650 printf (_("INPUT ERROR: No thresholds specified"));
651 print_path (mypath);
652 return ERROR;
653 }
654 else if ((wp >= 0.0 || cp >= 0.0) &&
655 (wp < 0.0 || cp < 0.0 || wp > 100.0 || cp > 100.0 || cp > wp)) {
656 printf (_("\
657 INPUT ERROR: C_DFP (%f) should be less than W_DFP (%.1f) and both should be between zero and 100 percent, inclusive"),
658 cp, wp);
659 print_path (mypath);
660 return ERROR;
661 }
662 else if ((iwp >= 0.0 || icp >= 0.0) &&
663 (iwp < 0.0 || icp < 0.0 || iwp > 100.0 || icp > 100.0 || icp > iwp)) {
664 printf (_("\
665 INPUT ERROR: C_IDFP (%f) should be less than W_IDFP (%.1f) and both should be between zero and 100 percent, inclusive"),
666 icp, iwp);
667 print_path (mypath);
668 return ERROR;
669 }
670 else if ((w > 0 || c > 0) && (w == 0 || c == 0 || c > w)) {
671 printf (_("\
672 INPUT ERROR: C_DF (%lu) should be less than W_DF (%lu) and both should be greater than zero"),
673 (unsigned long)c, (unsigned long)w);
674 print_path (mypath);
675 return ERROR;
676 }
678 return OK;
679 }
681 */
689 void
690 print_help (void)
691 {
692 print_revision (progname, revision);
694 printf ("Copyright (c) 1999 Ethan Galstad <nagios@nagios.org>\n");
695 printf (COPYRIGHT, copyright, email);
697 printf ("%s\n", _("This plugin checks the amount of used disk space on a mounted file system"));
698 printf ("%s\n", _("and generates an alert if free space is less than one of the threshold values"));
700 printf ("\n\n");
702 print_usage ();
704 printf (_(UT_HELP_VRSN));
706 printf (" %s\n", "-w, --warning=INTEGER");
707 printf (" %s\n", _("Exit with WARNING status if less than INTEGER units of disk are free"));
708 printf (" %s\n", "-w, --warning=PERCENT%");
709 printf (" %s\n", _("Exit with WARNING status if less than PERCENT of disk space is free"));
710 printf (" %s\n", "-W, --iwarning=PERCENT%");
711 printf (" %s\n", _("Exit with WARNING status if less than PERCENT of inode space is free"));
712 printf (" %s\n", "-K, --icritical=PERCENT%");
713 printf (" %s\n", _("Exit with CRITICAL status if less than PERCENT of inode space is free"));
714 printf (" %s\n", "-c, --critical=INTEGER");
715 printf (" %s\n", _("Exit with CRITICAL status if less than INTEGER units of disk are free"));
716 printf (" %s\n", "-c, --critical=PERCENT%");
717 printf (" %s\n", _("Exit with CRITCAL status if less than PERCENT of disk space is free"));
718 printf (" %s\n", "-C, --clear");
719 printf (" %s\n", _("Clear thresholds"));
720 printf (" %s\n", "-u, --units=STRING");
721 printf (" %s\n", _("Choose bytes, kB, MB, GB, TB (default: MB)"));
722 printf (" %s\n", "-k, --kilobytes");
723 printf (" %s\n", _("Same as '--units kB'"));
724 printf (" %s\n", "-m, --megabytes");
725 printf (" %s\n", _("Same as '--units MB'"));
726 printf (" %s\n", "-l, --local");
727 printf (" %s\n", _("Only check local filesystems"));
728 printf (" %s\n", "-p, --path=PATH, --partition=PARTITION");
729 printf (" %s\n", _("Path or partition (may be repeated)"));
730 printf (" %s\n", "-x, --exclude_device=PATH <STRING>");
731 printf (" %s\n", _("Ignore device (only works if -p unspecified)"));
732 printf (" %s\n", _("-X, --exclude-type=TYPE <STRING>"));
733 printf (" %s\n", _("Ignore all filesystems of indicated type (may be repeated)"));
734 printf (" %s\n", "-m, --mountpoint");
735 printf (" %s\n", _("Display the mountpoint instead of the partition"));
736 printf (" %s\n", "-E, --exact-match");
737 printf (" %s\n", _("For paths or partitions specified with -p, only check for exact paths"));
738 printf (" %s\n", "-e, --errors-only");
739 printf (" %s\n", _("Display only devices/mountpoints with errors"));
740 printf (_(UT_TIMEOUT), DEFAULT_SOCKET_TIMEOUT);
741 printf (_(UT_VERBOSE));
742 printf ("\n");
743 printf ("%s\n", _("Examples:"));
744 printf (" %s\n", "check_disk -w 10% -c 5% -p /tmp -p /var -C -w 100000 -c 50000 -p /");
745 printf (" %s\n", _("Checks /tmp and /var at 10% and 5%, and / at 100MB and 50MB"));
746 printf (_(UT_SUPPORT));
747 }
751 void
752 print_usage (void)
753 {
754 printf (_("Usage:"));
755 printf (" %s -w limit -c limit [-p path | -x device] [-t timeout]", progname);
756 printf ("[-m] [-e] [-W limit] [-K limit] [-v] [-q] [-E]\n");
757 }