1 /*****************************************************************************
3 * Monitoring check_procs plugin
6 * Copyright (c) 2000-2024 Monitoring Plugins Development Team
10 * This file contains the check_procs plugin
12 * Checks all processes and generates WARNING or CRITICAL states if the
13 * specified metric is outside the required threshold ranges. The metric
14 * defaults to number of processes. Search filters can be applied to limit
15 * the processes to check.
17 * The parent process, check_procs itself and any child process of
18 * check_procs (ps) are excluded from any checks to prevent false positives.
21 * This program is free software: you can redistribute it and/or modify
22 * it under the terms of the GNU General Public License as published by
23 * the Free Software Foundation, either version 3 of the License, or
24 * (at your option) any later version.
26 * This program is distributed in the hope that it will be useful,
27 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
29 * GNU General Public License for more details.
31 * You should have received a copy of the GNU General Public License
32 * along with this program. If not, see <http://www.gnu.org/licenses/>.
35 *****************************************************************************/
37 const char *progname
= "check_procs";
38 const char *program_name
= "check_procs"; /* Required for coreutils libs */
39 const char *copyright
= "2000-2024";
40 const char *email
= "devel@monitoring-plugins.org";
44 #include "utils_cmd.h"
50 #ifdef HAVE_SYS_STAT_H
54 static int process_arguments (int /*argc*/, char ** /*argv*/);
55 static int validate_arguments (void);
56 static int convert_to_seconds (char * /*etime*/);
57 static void print_help (void);
58 void print_usage (void);
60 static char *warning_range
= NULL
;
61 static char *critical_range
= NULL
;
62 static thresholds
*procs_thresholds
= NULL
;
64 static int options
= 0; /* bitmask of filter criteria to test against */
75 #define EREG_ARGS 1024
76 #define EXCLUDE_PROGS 2048
78 #define KTHREAD_PARENT "kthreadd" /* the parent process of kernel threads:
79 ppid of procs are compared to pid of this proc*/
81 /* Different metrics */
90 enum metric metric
= METRIC_PROCS
;
92 static int verbose
= 0;
98 static char *statopts
;
100 static char *exclude_progs
;
101 static char **exclude_progs_arr
= NULL
;
102 static char exclude_progs_counter
= 0;
104 static char *input_filename
= NULL
;
105 static regex_t re_args
;
108 static char tmp
[MAX_INPUT_BUFFER
];
109 static int kthread_filter
= 0;
110 static int usepid
= 0; /* whether to test for pid or /proc/pid/exe */
113 stat_exe (const pid_t pid
, struct stat
*buf
) {
116 xasprintf(&path
, "/proc/%d/exe", pid
);
117 ret
= stat(path
, buf
);
124 main (int argc
, char **argv
)
138 pid_t kthread_ppid
= 0;
144 char procetime
[MAX_INPUT_BUFFER
] = { '\0' };
147 const char *zombie
= "Z";
149 int resultsum
= 0; /* bitmask of the filter criteria met by a process */
150 int found
= 0; /* counter for number of lines returned in `ps` output */
151 int procs
= 0; /* counter for number of processes meeting filter criteria */
152 int pos
; /* number of spaces before 'args' in `ps` output */
153 int cols
; /* number of columns in ps output */
154 int expected_cols
= PS_COLS
- 1;
155 int warn
= 0; /* number of processes in warn state */
156 int crit
= 0; /* number of processes in crit state */
158 int result
= STATE_UNKNOWN
;
160 output chld_out
, chld_err
;
162 setlocale (LC_ALL
, "");
163 bindtextdomain (PACKAGE
, LOCALEDIR
);
164 textdomain (PACKAGE
);
165 setlocale(LC_NUMERIC
, "POSIX");
167 input_buffer
= malloc (MAX_INPUT_BUFFER
);
168 procprog
= malloc (MAX_INPUT_BUFFER
);
170 xasprintf (&metric_name
, "PROCS");
171 metric
= METRIC_PROCS
;
173 /* Parse extra opts if any */
174 argv
=np_extra_opts (&argc
, argv
, progname
);
176 if (process_arguments (argc
, argv
) == ERROR
)
177 usage4 (_("Could not parse arguments"));
182 if (usepid
|| stat_exe(mypid
, &statbuf
) == -1) {
183 /* usepid might have been set by -T */
187 mydev
= statbuf
.st_dev
;
188 myino
= statbuf
.st_ino
;
191 /* Set signal handling and alarm timeout */
192 if (signal (SIGALRM
, timeout_alarm_handler
) == SIG_ERR
) {
193 die (STATE_UNKNOWN
, _("Cannot catch SIGALRM"));
195 (void) alarm ((unsigned) timeout_interval
);
198 printf (_("CMD: %s\n"), PS_COMMAND
);
200 if (input_filename
== NULL
) {
201 result
= cmd_run( PS_COMMAND
, &chld_out
, &chld_err
, 0);
202 if (chld_err
.lines
> 0) {
203 printf ("%s: %s", _("System call sent warnings to stderr"), chld_err
.line
[0]);
207 result
= cmd_file_read( input_filename
, &chld_out
, 0);
210 /* flush first line: j starts at 1 */
211 for (size_t j
= 1; j
< chld_out
.lines
; j
++) {
212 input_line
= chld_out
.line
[j
];
215 printf ("%s", input_line
);
217 strcpy (procprog
, "");
218 xasprintf (&procargs
, "%s", "");
220 cols
= sscanf (input_line
, PS_FORMAT
, PS_VARLIST
);
222 /* Zombie processes do not give a procprog command */
223 if ( cols
< expected_cols
&& strstr(procstat
, zombie
) ) {
224 cols
= expected_cols
;
226 if ( cols
>= expected_cols
) {
228 xasprintf (&procargs
, "%s", input_line
+ pos
);
231 /* Some ps return full pathname for command. This removes path */
232 strcpy(procprog
, base_name(procprog
));
234 /* we need to convert the elapsed time to seconds */
235 procseconds
= convert_to_seconds(procetime
);
238 printf ("proc#=%d uid=%d vsz=%d rss=%d pid=%d ppid=%d pcpu=%.2f stat=%s etime=%s prog=%s args=%s\n",
239 procs
, procuid
, procvsz
, procrss
,
240 procpid
, procppid
, procpcpu
, procstat
,
241 procetime
, procprog
, procargs
);
244 if ((usepid
&& mypid
== procpid
) ||
245 ( ((!usepid
) && ((ret
= stat_exe(procpid
, &statbuf
) != -1) && statbuf
.st_dev
== mydev
&& statbuf
.st_ino
== myino
)) ||
246 (ret
== -1 && errno
== ENOENT
))
249 printf("not considering - is myself or gone\n");
253 else if (myppid
== procpid
) {
255 printf("not considering - is parent\n");
259 /* Ignore our own children */
260 if (procppid
== mypid
) {
262 printf("not considering - is our child\n");
266 /* Ignore excluded processes by name */
267 if(options
& EXCLUDE_PROGS
) {
271 for(i
=0; i
< (exclude_progs_counter
); i
++) {
272 if(!strcmp(procprog
, exclude_progs_arr
[i
])) {
277 resultsum
|= EXCLUDE_PROGS
;
281 printf("excluding - by ignorelist\n");
285 /* filter kernel threads (children of KTHREAD_PARENT)*/
286 /* TODO adapt for other OSes than GNU/Linux
287 sorry for not doing that, but I've no other OSes to test :-( */
288 if (kthread_filter
== 1) {
289 /* get pid KTHREAD_PARENT */
290 if (kthread_ppid
== 0 && !strcmp(procprog
, KTHREAD_PARENT
) )
291 kthread_ppid
= procpid
;
293 if (kthread_ppid
== procppid
) {
295 printf ("Ignore kernel thread: pid=%d ppid=%d prog=%s args=%s\n", procpid
, procppid
, procprog
, procargs
);
300 if ((options
& STAT
) && (strstr (procstat
, statopts
)))
302 if ((options
& ARGS
) && procargs
&& (strstr (procargs
, args
) != NULL
))
304 if ((options
& EREG_ARGS
) && procargs
&& (regexec(&re_args
, procargs
, (size_t) 0, NULL
, 0) == 0))
305 resultsum
|= EREG_ARGS
;
306 if ((options
& PROG
) && procprog
&& (strcmp (prog
, procprog
) == 0))
308 if ((options
& PPID
) && (procppid
== ppid
))
310 if ((options
& USER
) && (procuid
== uid
))
312 if ((options
& VSZ
) && (procvsz
>= vsz
))
314 if ((options
& RSS
) && (procrss
>= rss
))
316 if ((options
& PCPU
) && (procpcpu
>= pcpu
))
321 /* Next line if filters not matched */
322 if (!(options
== resultsum
|| options
== ALL
))
327 printf ("Matched: uid=%d vsz=%d rss=%d pid=%d ppid=%d pcpu=%.2f stat=%s etime=%s prog=%s args=%s\n",
328 procuid
, procvsz
, procrss
,
329 procpid
, procppid
, procpcpu
, procstat
,
330 procetime
, procprog
, procargs
);
333 if (metric
== METRIC_VSZ
)
334 i
= get_status ((double)procvsz
, procs_thresholds
);
335 else if (metric
== METRIC_RSS
)
336 i
= get_status ((double)procrss
, procs_thresholds
);
337 /* TODO? float thresholds for --metric=CPU */
338 else if (metric
== METRIC_CPU
)
339 i
= get_status (procpcpu
, procs_thresholds
);
340 else if (metric
== METRIC_ELAPSED
)
341 i
= get_status ((double)procseconds
, procs_thresholds
);
343 if (metric
!= METRIC_PROCS
) {
344 if (i
== STATE_WARNING
) {
346 xasprintf (&fails
, "%s%s%s", fails
, (strcmp(fails
,"") ? ", " : ""), procprog
);
347 result
= max_state (result
, i
);
349 if (i
== STATE_CRITICAL
) {
351 xasprintf (&fails
, "%s%s%s", fails
, (strcmp(fails
,"") ? ", " : ""), procprog
);
352 result
= max_state (result
, i
);
356 /* This should not happen */
358 printf(_("Not parseable: %s"), input_buffer
);
362 if (found
== 0) { /* no process lines parsed so return STATE_UNKNOWN */
363 printf (_("Unable to read output\n"));
364 return STATE_UNKNOWN
;
367 if ( result
== STATE_UNKNOWN
)
370 /* Needed if procs found, but none match filter */
371 if ( metric
== METRIC_PROCS
) {
372 result
= max_state (result
, get_status ((double)procs
, procs_thresholds
) );
375 if ( result
== STATE_OK
) {
376 printf ("%s %s: ", metric_name
, _("OK"));
377 } else if (result
== STATE_WARNING
) {
378 printf ("%s %s: ", metric_name
, _("WARNING"));
379 if ( metric
!= METRIC_PROCS
) {
380 printf (_("%d warn out of "), warn
);
382 } else if (result
== STATE_CRITICAL
) {
383 printf ("%s %s: ", metric_name
, _("CRITICAL"));
384 if (metric
!= METRIC_PROCS
) {
385 printf (_("%d crit, %d warn out of "), crit
, warn
);
388 printf (ngettext ("%d process", "%d processes", (unsigned long) procs
), procs
);
390 if (strcmp(fmt
,"") != 0) {
391 printf (_(" with %s"), fmt
);
394 if ( verbose
>= 1 && strcmp(fails
,"") )
395 printf (" [%s]", fails
);
397 if (metric
== METRIC_PROCS
)
398 printf (" | procs=%d;%s;%s;0;", procs
,
399 warning_range
? warning_range
: "",
400 critical_range
? critical_range
: "");
402 printf (" | procs=%d;;;0; procs_warn=%d;;;0; procs_crit=%d;;;0;", procs
, warn
, crit
);
410 /* process command-line arguments */
412 process_arguments (int argc
, char **argv
)
419 int cflags
= REG_NOSUB
| REG_EXTENDED
;
420 char errbuf
[MAX_INPUT_BUFFER
];
423 static struct option longopts
[] = {
424 {"warning", required_argument
, 0, 'w'},
425 {"critical", required_argument
, 0, 'c'},
426 {"metric", required_argument
, 0, 'm'},
427 {"timeout", required_argument
, 0, 't'},
428 {"status", required_argument
, 0, 's'},
429 {"ppid", required_argument
, 0, 'p'},
430 {"user", required_argument
, 0, 'u'},
431 {"command", required_argument
, 0, 'C'},
432 {"vsz", required_argument
, 0, 'z'},
433 {"rss", required_argument
, 0, 'r'},
434 {"pcpu", required_argument
, 0, 'P'},
435 {"elapsed", required_argument
, 0, 'e'},
436 {"argument-array", required_argument
, 0, 'a'},
437 {"help", no_argument
, 0, 'h'},
438 {"version", no_argument
, 0, 'V'},
439 {"verbose", no_argument
, 0, 'v'},
440 {"ereg-argument-array", required_argument
, 0, CHAR_MAX
+1},
441 {"input-file", required_argument
, 0, CHAR_MAX
+2},
442 {"no-kthreads", required_argument
, 0, 'k'},
443 {"traditional-filter", no_argument
, 0, 'T'},
444 {"exclude-process", required_argument
, 0, 'X'},
448 for (c
= 1; c
< argc
; c
++)
449 if (strcmp ("-to", argv
[c
]) == 0)
450 strcpy (argv
[c
], "-t");
453 c
= getopt_long (argc
, argv
, "Vvhkt:c:w:p:s:u:C:a:z:r:m:P:T:X:",
456 if (c
== -1 || c
== EOF
)
464 exit (STATE_UNKNOWN
);
465 case 'V': /* version */
466 print_revision (progname
, NP_VERSION
);
467 exit (STATE_UNKNOWN
);
468 case 't': /* timeout period */
469 if (!is_integer (optarg
))
470 usage2 (_("Timeout interval must be a positive integer"), optarg
);
472 timeout_interval
= atoi (optarg
);
474 case 'c': /* critical threshold */
475 critical_range
= optarg
;
477 case 'w': /* warning threshold */
478 warning_range
= optarg
;
480 case 'p': /* process id */
481 if (sscanf (optarg
, "%d%[^0-9]", &ppid
, tmp
) == 1) {
482 xasprintf (&fmt
, "%s%sPPID = %d", (fmt
? fmt
: "") , (options
? ", " : ""), ppid
);
486 usage4 (_("Parent Process ID must be an integer!"));
487 case 's': /* status */
492 xasprintf (&fmt
, _("%s%sSTATE = %s"), (fmt
? fmt
: ""), (options
? ", " : ""), statopts
);
495 case 'u': /* user or user id */
496 if (is_integer (optarg
)) {
498 pw
= getpwuid ((uid_t
) uid
);
499 /* check to be sure user exists */
501 usage2 (_("UID was not found"), optarg
);
504 pw
= getpwnam (optarg
);
505 /* check to be sure user exists */
507 usage2 (_("User name was not found"), optarg
);
512 xasprintf (&fmt
, "%s%sUID = %d (%s)", (fmt
? fmt
: ""), (options
? ", " : ""),
516 case 'C': /* command */
517 /* TODO: allow this to be passed in with --metric */
522 xasprintf (&fmt
, _("%s%scommand name '%s'"), (fmt
? fmt
: ""), (options
? ", " : ""),
530 exclude_progs
= optarg
;
531 xasprintf (&fmt
, _("%s%sexclude progs '%s'"), (fmt
? fmt
: ""), (options
? ", " : ""),
533 char *p
= strtok(exclude_progs
, ",");
536 exclude_progs_arr
= realloc(exclude_progs_arr
, sizeof(char*) * ++exclude_progs_counter
);
537 exclude_progs_arr
[exclude_progs_counter
-1] = p
;
538 p
= strtok(NULL
, ",");
541 options
|= EXCLUDE_PROGS
;
543 case 'a': /* args (full path name with args) */
544 /* TODO: allow this to be passed in with --metric */
549 xasprintf (&fmt
, "%s%sargs '%s'", (fmt
? fmt
: ""), (options
? ", " : ""), args
);
553 err
= regcomp(&re_args
, optarg
, cflags
);
555 regerror (err
, &re_args
, errbuf
, MAX_INPUT_BUFFER
);
556 die (STATE_UNKNOWN
, "PROCS %s: %s - %s\n", _("UNKNOWN"), _("Could not compile regular expression"), errbuf
);
558 /* Strip off any | within the regex optarg */
559 temp_string
= strdup(optarg
);
560 while(temp_string
[i
]!='\0'){
561 if(temp_string
[i
]=='|')
565 xasprintf (&fmt
, "%s%sregex args '%s'", (fmt
? fmt
: ""), (options
? ", " : ""), temp_string
);
566 options
|= EREG_ARGS
;
569 if (sscanf (optarg
, "%d%[^0-9]", &rss
, tmp
) == 1) {
570 xasprintf (&fmt
, "%s%sRSS >= %d", (fmt
? fmt
: ""), (options
? ", " : ""), rss
);
574 usage4 (_("RSS must be an integer!"));
576 if (sscanf (optarg
, "%d%[^0-9]", &vsz
, tmp
) == 1) {
577 xasprintf (&fmt
, "%s%sVSZ >= %d", (fmt
? fmt
: ""), (options
? ", " : ""), vsz
);
581 usage4 (_("VSZ must be an integer!"));
583 /* TODO: -P 1.5.5 is accepted */
584 if (sscanf (optarg
, "%f%[^0-9.]", &pcpu
, tmp
) == 1) {
585 xasprintf (&fmt
, "%s%sPCPU >= %.2f", (fmt
? fmt
: ""), (options
? ", " : ""), pcpu
);
589 usage4 (_("PCPU must be a float!"));
591 xasprintf (&metric_name
, "%s", optarg
);
592 if ( strcmp(optarg
, "PROCS") == 0) {
593 metric
= METRIC_PROCS
;
596 else if ( strcmp(optarg
, "VSZ") == 0) {
600 else if ( strcmp(optarg
, "RSS") == 0 ) {
604 else if ( strcmp(optarg
, "CPU") == 0 ) {
608 else if ( strcmp(optarg
, "ELAPSED") == 0) {
609 metric
= METRIC_ELAPSED
;
613 usage4 (_("Metric must be one of PROCS, VSZ, RSS, CPU, ELAPSED!"));
614 case 'k': /* linux kernel thread filter */
617 case 'v': /* command */
624 input_filename
= optarg
;
630 if ((! warning_range
) && argv
[c
])
631 warning_range
= argv
[c
++];
632 if ((! critical_range
) && argv
[c
])
633 critical_range
= argv
[c
++];
634 if (statopts
== NULL
&& argv
[c
]) {
635 xasprintf (&statopts
, "%s", argv
[c
++]);
636 xasprintf (&fmt
, _("%s%sSTATE = %s"), (fmt
? fmt
: ""), (options
? ", " : ""), statopts
);
640 /* this will abort in case of invalid ranges */
641 set_thresholds (&procs_thresholds
, warning_range
, critical_range
);
643 return validate_arguments ();
649 validate_arguments ()
655 statopts
= strdup("");
673 /* convert the elapsed time to seconds */
675 convert_to_seconds(char *etime
) {
694 for (ptr
= etime
; *ptr
!= '\0'; ptr
++) {
707 sscanf(etime
, "%d-%d:%d:%d",
708 &days
, &hours
, &minutes
, &seconds
);
709 /* linux 2.6.5/2.6.6 reporting some processes with infinite
710 * elapsed times for some reason */
716 sscanf(etime
, "%d:%d:%d",
717 &hours
, &minutes
, &seconds
);
718 } else if (coloncnt
== 1) {
719 sscanf(etime
, "%d:%d",
724 total
= (days
* 86400) +
729 if (verbose
>= 3 && metric
== METRIC_ELAPSED
) {
730 printf("seconds: %d\n", total
);
739 print_revision (progname
, NP_VERSION
);
741 printf ("Copyright (c) 1999 Ethan Galstad <nagios@nagios.org>\n");
742 printf (COPYRIGHT
, copyright
, email
);
744 printf ("%s\n", _("Checks all processes and generates WARNING or CRITICAL states if the specified"));
745 printf ("%s\n", _("metric is outside the required threshold ranges. The metric defaults to number"));
746 printf ("%s\n", _("of processes. Search filters can be applied to limit the processes to check."));
750 printf ("%s\n", _("The parent process, check_procs itself and any child process of check_procs (ps)"));
751 printf ("%s\n", _("are excluded from any checks to prevent false positives."));
757 printf (UT_HELP_VRSN
);
758 printf (UT_EXTRA_OPTS
);
759 printf (" %s\n", "-w, --warning=RANGE");
760 printf (" %s\n", _("Generate warning state if metric is outside this range"));
761 printf (" %s\n", "-c, --critical=RANGE");
762 printf (" %s\n", _("Generate critical state if metric is outside this range"));
763 printf (" %s\n", "-m, --metric=TYPE");
764 printf (" %s\n", _("Check thresholds against metric. Valid types:"));
765 printf (" %s\n", _("PROCS - number of processes (default)"));
766 printf (" %s\n", _("VSZ - virtual memory size"));
767 printf (" %s\n", _("RSS - resident set memory size"));
768 printf (" %s\n", _("CPU - percentage CPU"));
769 /* only linux etime is support currently */
770 #if defined( __linux__ )
771 printf (" %s\n", _("ELAPSED - time elapsed in seconds"));
772 #endif /* defined(__linux__) */
773 printf (UT_PLUG_TIMEOUT
, DEFAULT_SOCKET_TIMEOUT
);
775 printf (" %s\n", "-v, --verbose");
776 printf (" %s\n", _("Extra information. Up to 3 verbosity levels"));
778 printf (" %s\n", "-T, --traditional");
779 printf (" %s\n", _("Filter own process the traditional way by PID instead of /proc/pid/exe"));
782 printf ("%s\n", "Filters:");
783 printf (" %s\n", "-s, --state=STATUSFLAGS");
784 printf (" %s\n", _("Only scan for processes that have, in the output of `ps`, one or"));
785 printf (" %s\n", _("more of the status flags you specify (for example R, Z, S, RS,"));
786 printf (" %s\n", _("RSZDT, plus others based on the output of your 'ps' command)."));
787 printf (" %s\n", "-p, --ppid=PPID");
788 printf (" %s\n", _("Only scan for children of the parent process ID indicated."));
789 printf (" %s\n", "-z, --vsz=VSZ");
790 printf (" %s\n", _("Only scan for processes with VSZ higher than indicated."));
791 printf (" %s\n", "-r, --rss=RSS");
792 printf (" %s\n", _("Only scan for processes with RSS higher than indicated."));
793 printf (" %s\n", "-P, --pcpu=PCPU");
794 printf (" %s\n", _("Only scan for processes with PCPU higher than indicated."));
795 printf (" %s\n", "-u, --user=USER");
796 printf (" %s\n", _("Only scan for processes with user name or ID indicated."));
797 printf (" %s\n", "-a, --argument-array=STRING");
798 printf (" %s\n", _("Only scan for processes with args that contain STRING."));
799 printf (" %s\n", "--ereg-argument-array=STRING");
800 printf (" %s\n", _("Only scan for processes with args that contain the regex STRING."));
801 printf (" %s\n", "-C, --command=COMMAND");
802 printf (" %s\n", _("Only scan for exact matches of COMMAND (without path)."));
803 printf (" %s\n", "-X, --exclude-process");
804 printf (" %s\n", _("Exclude processes which match this comma separated list"));
805 printf (" %s\n", "-k, --no-kthreads");
806 printf (" %s\n", _("Only scan for non kernel threads (works on Linux only)."));
809 RANGEs are specified 'min:max' or 'min:' or ':max' (or 'max'). If\n\
810 specified 'max:min', a warning status will be generated if the\n\
811 count is inside the specified range\n\n"));
814 This plugin checks the number of currently running processes and\n\
815 generates WARNING or CRITICAL states if the process count is outside\n\
816 the specified threshold ranges. The process count can be filtered by\n\
817 process owner, parent process PID, current state (e.g., 'Z'), or may\n\
818 be the total number of running processes\n\n"));
820 printf ("%s\n", _("Examples:"));
821 printf (" %s\n", "check_procs -w 2:2 -c 2:1024 -C portsentry");
822 printf (" %s\n", _("Warning if not two processes with command name portsentry."));
823 printf (" %s\n\n", _("Critical if < 2 or > 1024 processes"));
824 printf (" %s\n", "check_procs -c 1: -C sshd");
825 printf (" %s\n", _("Critical if not at least 1 process with command sshd"));
826 printf (" %s\n", "check_procs -w 1024 -c 1: -C sshd");
827 printf (" %s\n", _("Warning if > 1024 processes with command name sshd."));
828 printf (" %s\n\n", _("Critical if < 1 processes with command name sshd."));
829 printf (" %s\n", "check_procs -w 10 -a '/usr/local/bin/perl' -u root");
830 printf (" %s\n", _("Warning alert if > 10 processes with command arguments containing"));
831 printf (" %s\n\n", _("'/usr/local/bin/perl' and owned by root"));
832 printf (" %s\n", "check_procs -w 50000 -c 100000 --metric=VSZ");
833 printf (" %s\n\n", _("Alert if VSZ of any processes over 50K or 100K"));
834 printf (" %s\n", "check_procs -w 10 -c 20 --metric=CPU");
835 printf (" %s\n", _("Alert if CPU of any processes over 10%% or 20%%"));
843 printf ("%s\n", _("Usage:"));
844 printf ("%s -w <range> -c <range> [-m metric] [-s state] [-p ppid]\n", progname
);
845 printf (" [-u user] [-r rss] [-z vsz] [-P %%cpu] [-a argument-array]\n");
846 printf (" [-C command] [-X process_to_exclude] [-k] [-t timeout] [-v]\n");