Code

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