#!/usr/bin/perl # # Decide if a host is up by looking at the last ping result. # # This will run under the embedded perl interpreter, so the code needs to be squeaky clean. # # $Header: /opt/home/doke/work/nagios/RCS/check_host_via_ping_service,v 1.2 2008/04/23 21:54:22 doke Exp $ use strict; use warnings; no warnings 'redefine'; use Getopt::Long; use vars qw( $target_host $verbose $help $statusfile ); $statusfile = "/var/run/nagios/status.dat"; sub usage { my( $rc ) = @_; print "Usage: $0 [-vh] \n", exit $rc; } $verbose = 0; $help = 0; Getopt::Long::Configure ("bundling"); GetOptions( 'v+' => \$verbose, 'h' => \$help, ); &usage( 0 ) if ( $help ); $target_host = shift; &usage( 1 ) if ( ! defined $target_host ); exit check_ping_status(); ################### sub check_ping_status { my( $in_service, $host, $service, $current_state, $state_type ); if ( ! open( fH, $statusfile ) ) { print "can't open $statusfile: $!\n"; return -1; } while ( ) { chomp; if ( m/^service\s*{/ ) { # } make vi happy $in_service = 1; $host = undef; $service = undef; $current_state = -1; $state_type = 0; } elsif ( m/^\s*host_name=(.*)/ ) { $host = $1; } elsif ( m/^\s*service_description=(.*)/ ) { $service = $1; } elsif ( m/^\s*current_state=(\d+)/ ) { $current_state = $1; } elsif ( m/^\s*state_type=(\d+)/ ) { $state_type = $1; } # { make vi happy elsif ( m/^\s*}\s*$/ ) { $verbose && print "in_service $in_service, host $host, service $service, ", "current_state $current_state, state_type $state_type\n"; if ( $in_service && $host eq $target_host && $service eq 'ping' ) { close fH; if ( $state_type == 1 && $current_state != 0 ) { # state hard, so it's failed all retries # and current state is not ok print "DOWN -- last service ping failed hard\n"; return 2; } print "Up\n"; return 0; # ok } $host = undef; $service = undef; $in_service = 0; $current_state = -1; $state_type = 0; } } close fH; print "service '$target_host/ping' not found in status file\n"; return -1; # unknown }