#!/usr/bin/perl -w ############################## check_snmp_env ################# # Version : 1.3 # Date : May 24 2007 # Author : Patrick Proy ( patrick at proy.org) # Help : http://www.manubulon.com/nagios/ # License : GPL - http://www.fsf.org/licenses/gpl.txt # Changelog : # Contributors : Fredrik Vocks ################################################################# # # Help : ./check_snmp_env.pl -h # use strict; use Net::SNMP; use Getopt::Long; # Icinga specific my $TIMEOUT = 15; my %ERRORS = ('OK' => 0, 'WARNING' => 1, 'CRITICAL' => 2, 'UNKNOWN' => 3, 'DEPENDENT' => 4); my @Nagios_state = ("UNKNOWN", "OK", "WARNING", "CRITICAL"); # Nagios states coding # SNMP Datas # CISCO-ENVMON-MIB my $ciscoEnvMonMIB = "1.3.6.1.4.1.9.9.13"; # Cisco env base table my %CiscoEnvMonState = (1, "normal", 2, "warning", 3, "critical", 4, "shutdown", 5, "notPresent", 6, "notFunctioning"); # Cisco states my %CiscoEnvMonNagios = (1, 1, 2, 2, 3, 3, 4, 3, 5, 0, 6, 3); # Nagios states returned for CIsco states (coded see @Nagios_state). my $ciscoVoltageTable = $ciscoEnvMonMIB . ".1.2.1"; # Cisco voltage table my $ciscoVoltageTableIndex = $ciscoVoltageTable . ".1"; #Index table my $ciscoVoltageTableDesc = $ciscoVoltageTable . ".2"; #Description my $ciscoVoltageTableValue = $ciscoVoltageTable . ".3"; #Value my $ciscoVoltageTableState = $ciscoVoltageTable . ".7"; #Status # CiscoEnvMonVoltageStatusEntry ::= # 1 ciscoEnvMonVoltageStatusIndex Integer32 (0..2147483647), # 2 ciscoEnvMonVoltageStatusDescr DisplayString, # 3 ciscoEnvMonVoltageStatusValue CiscoSignedGauge, # 4 ciscoEnvMonVoltageThresholdLow Integer32, # 5 ciscoEnvMonVoltageThresholdHigh Integer32, # 6 ciscoEnvMonVoltageLastShutdown Integer32, # 7 ciscoEnvMonVoltageState CiscoEnvMonState my $ciscoTempTable = $ciscoEnvMonMIB . ".1.3.1"; # Cisco temprature table my $ciscoTempTableIndex = $ciscoTempTable . ".1"; #Index table my $ciscoTempTableDesc = $ciscoTempTable . ".2"; #Description my $ciscoTempTableValue = $ciscoTempTable . ".3"; #Value my $ciscoTempTableState = $ciscoTempTable . ".6"; #Status # CiscoEnvMonTemperatureStatusEntry ::= # ciscoEnvMonTemperatureStatusIndex Integer32 (0..2147483647), # ciscoEnvMonTemperatureStatusDescr DisplayString, # ciscoEnvMonTemperatureStatusValue Gauge32, # ciscoEnvMonTemperatureThreshold Integer32, # ciscoEnvMonTemperatureLastShutdown Integer32, # ciscoEnvMonTemperatureState CiscoEnvMonState my $ciscoFanTable = $ciscoEnvMonMIB . ".1.4.1"; # Cisco fan table my $ciscoFanTableIndex = $ciscoFanTable . ".1"; #Index table my $ciscoFanTableDesc = $ciscoFanTable . ".2"; #Description my $ciscoFanTableState = $ciscoFanTable . ".3"; #Status # CiscoEnvMonFanStatusEntry ::= # ciscoEnvMonFanStatusIndex Integer32 (0..2147483647), # ciscoEnvMonFanStatusDescr DisplayString, # ciscoEnvMonFanState CiscoEnvMonState my $ciscoPSTable = $ciscoEnvMonMIB . ".1.5.1"; # Cisco power supply table my $ciscoPSTableIndex = $ciscoPSTable . ".1"; #Index table my $ciscoPSTableDesc = $ciscoPSTable . ".2"; #Description my $ciscoPSTableState = $ciscoPSTable . ".3"; #Status # CiscoEnvMonSupplyStatusEntry ::= # ciscoEnvMonSupplyStatusIndex Integer32 (0..2147483647), # ciscoEnvMonSupplyStatusDescr DisplayString, # ciscoEnvMonSupplyState CiscoEnvMonState, # ciscoEnvMonSupplySource INTEGER # Nokia env mib my $nokia_temp_tbl = "1.3.6.1.4.1.94.1.21.1.1.5"; my $nokia_temp = "1.3.6.1.4.1.94.1.21.1.1.5.0"; my $nokia_fan_table = "1.3.6.1.4.1.94.1.21.1.2"; my $nokia_fan_status = "1.3.6.1.4.1.94.1.21.1.2.1.1.2"; my $nokia_ps_table = "1.3.6.1.4.1.94.1.21.1.3"; my $nokia_ps_temp = "1.3.6.1.4.1.94.1.21.1.3.1.1.2"; my $nokia_ps_status = "1.3.6.1.4.1.94.1.21.1.3.1.1.3"; # Bluecoat env mib my @bc_SensorCode = ( "", "ok", "unknown", "not-installed", "voltage-low-warning", "voltage-low-critical", "no-power", "voltage-high-warning", "voltage-high-critical", "voltage-high-severe", "temperature-high-warning", "temperature-high-critical", "temperature-high-severe", "fan-slow-warning", "fan-slow-critical", "fan-stopped" ); # BC element status returned by MIB my @bc_status_nagios = (3, 0, 3, 3, 1, 2, 2, 1, 2, 2, 1, 2, 2, 1, 2, 2); # nagios status equivallent to BC status my @bc_SensorStatus = ("", "ok", "unavailable", "nonoperational"); # ok(1),unavailable(2),nonoperational(3) my @bc_mesure = ("", "", "", "Enum", "volts", "celsius", "rpm"); my @bc_DiskStatus = ("", "present", "initializing", "inserted", "offline", "removed", "not-present", "empty", "bad", "unknown"); my @bc_dsk_status_nagios = (3, 0, 0, 1, 1, 1, 2, 2, 2, 3); my $bc_sensor_table = "1.3.6.1.4.1.3417.2.1.1.1.1.1"; # sensor table my $bc_sensor_units = "1.3.6.1.4.1.3417.2.1.1.1.1.1.3"; # cf bc_mesure my $bc_sensor_Scale = "1.3.6.1.4.1.3417.2.1.1.1.1.1.4"; # * 10^value my $bc_sensor_Value = "1.3.6.1.4.1.3417.2.1.1.1.1.1.5"; # value my $bc_sensor_Code = "1.3.6.1.4.1.3417.2.1.1.1.1.1.6"; # bc_SensorCode my $bc_sensor_Status = "1.3.6.1.4.1.3417.2.1.1.1.1.1.7"; # bc_SensorStatus my $bc_sensor_Name = "1.3.6.1.4.1.3417.2.1.1.1.1.1.9"; # name my $bc_dsk_table = "1.3.6.1.4.1.3417.2.2.1.1.1.1"; #disk table my $bc_dsk_status = "1.3.6.1.4.1.3417.2.2.1.1.1.1.3"; # cf bc_DiskStatus my $bc_dsk_vendor = "1.3.6.1.4.1.3417.2.2.1.1.1.1.5"; # cf bc_DiskStatus my $bc_dsk_serial = "1.3.6.1.4.1.3417.2.2.1.1.1.1.8"; # cf bc_DiskStatus # Ironport env mib my $iron_ps_table = "1.3.6.1.4.1.15497.1.1.1.8"; # ps table my $iron_ps_status = "1.3.6.1.4.1.15497.1.1.1.8.1.2"; # ps status #powerSupplyNotInstalled(1), powerSupplyHealthy(2), powerSupplyNoAC(3), powerSupplyFaulty(4) my @iron_ps_status_name = ("", "powerSupplyNotInstalled", "powerSupplyHealthy", "powerSupplyNoAC", "powerSupplyFaulty"); my @iron_ps_status_nagios = (3, 3, 0, 2, 2); my $iron_ps_ha = "1.3.6.1.4.1.15497.1.1.1.8.1.3"; # ps redundancy status #powerSupplyRedundancyOK(1), powerSupplyRedundancyLost(2) my @iron_ps_ha_name = ("", "powerSupplyRedundancyOK", "powerSupplyRedundancyLost"); my @iron_ps_ha_nagios = (3, 0, 1); my $iron_ps_name = "1.3.6.1.4.1.15497.1.1.1.8.1.4"; # ps name my $iron_tmp_table = "1.3.6.1.4.1.15497.1.1.1.9"; # temp table my $iron_tmp_celcius = "1.3.6.1.4.1.15497.1.1.1.9.1.2"; # temp in celcius my $iron_tmp_name = "1.3.6.1.4.1.15497.1.1.1.9.1.3"; # name my $iron_fan_table = "1.3.6.1.4.1.15497.1.1.1.10"; # fan table my $iron_fan_rpm = "1.3.6.1.4.1.15497.1.1.1.10.1.2"; # fan speed in RPM my $iron_fan_name = "1.3.6.1.4.1.15497.1.1.1.10.1.3"; # fan name # Foundry BigIron Router Switch (FOUNDRY-SN-AGENT-MIB) my $foundry_temp = "1.3.6.1.4.1.1991.1.1.1.1.18.0"; # Chassis temperature in Deg C *2 my $foundry_temp_warn = "1.3.6.1.4.1.1991.1.1.1.1.19.0"; # Chassis warn temperature in Deg C *2 my $foundry_temp_crit = "1.3.6.1.4.1.1991.1.1.1.1.20.0"; # Chassis warn temperature in Deg C *2 my $foundry_ps_table = "1.3.6.1.4.1.1991.1.1.1.2.1"; # PS table my $foundry_ps_desc = "1.3.6.1.4.1.1991.1.1.1.2.1.1.2"; # PS desc my $foundry_ps_status = "1.3.6.1.4.1.1991.1.1.1.2.1.1.3"; # PS status my $foundry_fan_table = "1.3.6.1.4.1.1991.1.1.1.3.1"; # FAN table my $foundry_fan_desc = "1.3.6.1.4.1.1991.1.1.1.3.1.1.2"; # FAN desc my $foundry_fan_status = "1.3.6.1.4.1.1991.1.1.1.3.1.1.3"; # FAN status my @foundry_status = (3, 0, 2); # oper status : 1:other, 2: Normal, 3: Failure # Linux Net-SNMP with LM-SENSORS my $linux_temp = "1.3.6.1.4.1.2021.13.16.2.1"; # temperature table my $linux_temp_descr = "1.3.6.1.4.1.2021.13.16.2.1.2"; # temperature entry description my $linux_temp_value = "1.3.6.1.4.1.2021.13.16.2.1.3"; # temperature entry value (mC) my $linux_fan = "1.3.6.1.4.1.2021.13.16.3.1"; # fan table my $linux_fan_descr = "1.3.6.1.4.1.2021.13.16.3.1.2"; # fan entry description my $linux_fan_value = "1.3.6.1.4.1.2021.13.16.3.1.3"; # fan entry value (RPM) my $linux_volt = "1.3.6.1.4.1.2021.13.16.4.1"; # voltage table my $linux_volt_descr = "1.3.6.1.4.1.2021.13.16.4.1.2"; # voltage entry description my $linux_volt_value = "1.3.6.1.4.1.2021.13.16.4.1.3"; # voltage entry value (mV) my $linux_misc = "1.3.6.1.4.1.2021.13.16.4.1"; # misc table my $linux_misc_descr = "1.3.6.1.4.1.2021.13.16.4.1.2"; # misc entry description my $linux_misc_value = "1.3.6.1.4.1.2021.13.16.4.1.3"; # misc entry value # Globals my $VERSION = "2.0.0"; my $o_host = undef; # hostname my $o_community = undef; # community my $o_port = 161; # port my $o_help = undef; # wan't some help ? my $o_verb = undef; # verbose mode my $o_version = undef; # print version my $o_timeout = undef; # Timeout (Default 5) my $o_perf = undef; # Output performance data my $o_version2 = undef; # use snmp v2c # check type my $o_check_type = "cisco"; # default Cisco my @valid_types = ("cisco", "nokia", "bc", "iron", "foundry", "linux"); my $o_temp = undef; # max temp my $o_fan = undef; # min fan speed # SNMPv3 specific my $o_login = undef; # Login for snmpv3 my $o_passwd = undef; # Pass for snmpv3 my $v3protocols = undef; # V3 protocol list. my $o_authproto = 'md5'; # Auth protocol my $o_privproto = 'des'; # Priv protocol my $o_privpass = undef; # priv password # functions sub p_version { print "check_snmp_env version : $VERSION\n"; } sub print_usage { print "Usage: $0 [-v] -H -C [-2] | (-l login -x passwd [-X pass -L ,]) [-p ] -T (cisco|nokia|bc|iron|foundry|linux) [-F ] [-c ] [-f] [-t ] [-V]\n"; } sub isnnum { # Return true if arg is not a number my $num = shift; if ($num =~ /^(\d+\.?\d*)|(^\.\d+)$/) { return 0; } return 1; } sub set_status { # return worst status with this order : OK, unknwonw, warning, critical my $new_status = shift; my $cur_status = shift; if (($cur_status == 0) || ($new_status == $cur_status)) { return $new_status; } if ($new_status == 3) { return $cur_status; } if ($new_status > $cur_status) { return $new_status; } return $cur_status; } sub help { print "\nSNMP environmental Monitor for Icinga/Nagios/Naemon/Shinken, Version ", $VERSION, "\n"; print "GPL License, (c)2006-2007 Patrick Proy\n\n"; print_usage(); print <, : Authentication protocol (md5|sha : default md5) : Priv protocole (des|aes : default des) -P, --port=PORT SNMP port (Default 161) -T, --type=cisco|nokia|bc|iron|foundry Environemental check : cisco : All Cisco equipements : voltage,temp,fan,power supply (will try to check everything in the env mib) nokia : Nokia IP platforms : fan and power supply bc : BlueCoat platforms : fans, power supply, voltage, disks iron : IronPort platforms : fans, power supply, temp foundry : Foundry Network platforms : power supply, temp linux : Net-SNMP with LM-SENSORS : temp, fan, volt, misc -F, --fan= Minimum fan rpm value (only needed for 'iron' & 'linux') -c, --celcius= Maximum temp in degree celcius (only needed for 'iron' & 'linux') -f, --perfparse Perfparse compatible output -t, --timeout=INTEGER timeout for SNMP in seconds (Default: 5) -V, --version prints version number EOT } # For verbose output sub verb { my $t = shift; print $t, "\n" if defined($o_verb); } sub check_options { Getopt::Long::Configure("bundling"); GetOptions( 'v' => \$o_verb, 'verbose' => \$o_verb, 'h' => \$o_help, 'help' => \$o_help, 'H:s' => \$o_host, 'hostname:s' => \$o_host, 'p:i' => \$o_port, 'port:i' => \$o_port, 'C:s' => \$o_community, 'community:s' => \$o_community, 'l:s' => \$o_login, 'login:s' => \$o_login, 'x:s' => \$o_passwd, 'passwd:s' => \$o_passwd, 'X:s' => \$o_privpass, 'privpass:s' => \$o_privpass, 'L:s' => \$v3protocols, 'protocols:s' => \$v3protocols, 't:i' => \$o_timeout, 'timeout:i' => \$o_timeout, 'V' => \$o_version, 'version' => \$o_version, '2' => \$o_version2, 'v2c' => \$o_version2, 'f' => \$o_perf, 'perfparse' => \$o_perf, 'T:s' => \$o_check_type, 'type:s' => \$o_check_type, 'F:i' => \$o_fan, 'fan:i' => \$o_fan, 'c:i' => \$o_temp, 'celcius:i' => \$o_temp ); # check the -T option my $T_option_valid = 0; foreach (@valid_types) { if ($_ eq $o_check_type) { $T_option_valid = 1 } } if ($T_option_valid == 0) { print "Invalid check type (-T)!\n"; print_usage(); exit $ERRORS{"UNKNOWN"} } # Basic checks if (defined($o_timeout) && (isnnum($o_timeout) || ($o_timeout < 2) || ($o_timeout > 60))) { print "Timeout must be >1 and <60 !\n"; print_usage(); exit $ERRORS{"UNKNOWN"}; } if (!defined($o_timeout)) { $o_timeout = 5; } if (defined($o_help)) { help(); exit $ERRORS{"UNKNOWN"} } if (defined($o_version)) { p_version(); exit $ERRORS{"UNKNOWN"} } if (!defined($o_host)) # check host and filter { print_usage(); exit $ERRORS{"UNKNOWN"}; } # check snmp information if (!defined($o_community) && (!defined($o_login) || !defined($o_passwd))) { print "Put snmp login info!\n"; print_usage(); exit $ERRORS{"UNKNOWN"}; } if ((defined($o_login) || defined($o_passwd)) && (defined($o_community) || defined($o_version2))) { print "Can't mix snmp v1,2c,3 protocols!\n"; print_usage(); exit $ERRORS{"UNKNOWN"}; } if (defined($v3protocols)) { if (!defined($o_login)) { print "Put snmp V3 login info with protocols!\n"; print_usage(); exit $ERRORS{"UNKNOWN"}; } my @v3proto = split(/,/, $v3protocols); if ((defined($v3proto[0])) && ($v3proto[0] ne "")) { $o_authproto = $v3proto[0]; } # Auth protocol if (defined($v3proto[1])) { $o_privproto = $v3proto[1]; } # Priv protocol if ((defined($v3proto[1])) && (!defined($o_privpass))) { print "Put snmp V3 priv login info with priv protocols!\n"; print_usage(); exit $ERRORS{"UNKNOWN"}; } } } ########## MAIN ####### check_options(); # Check gobal timeout if snmp screws up if (defined($TIMEOUT)) { verb("Alarm at $TIMEOUT + 5"); alarm($TIMEOUT + 5); } else { verb("no global timeout defined : $o_timeout + 10"); alarm($o_timeout + 10); } $SIG{'ALRM'} = sub { print "No answer from host\n"; exit $ERRORS{"UNKNOWN"}; }; # Connect to host my ($session, $error); if (defined($o_login) && defined($o_passwd)) { # SNMPv3 login verb("SNMPv3 login"); if (!defined($o_privpass)) { verb("SNMPv3 AuthNoPriv login : $o_login, $o_authproto"); ($session, $error) = Net::SNMP->session( -hostname => $o_host, -version => '3', -username => $o_login, -authpassword => $o_passwd, -authprotocol => $o_authproto, -timeout => $o_timeout ); } else { verb("SNMPv3 AuthPriv login : $o_login, $o_authproto, $o_privproto"); ($session, $error) = Net::SNMP->session( -hostname => $o_host, -version => '3', -username => $o_login, -authpassword => $o_passwd, -authprotocol => $o_authproto, -privpassword => $o_privpass, -privprotocol => $o_privproto, -timeout => $o_timeout ); } } else { if (defined($o_version2)) { # SNMPv2 Login verb("SNMP v2c login"); ($session, $error) = Net::SNMP->session( -hostname => $o_host, -version => 2, -community => $o_community, -port => $o_port, -timeout => $o_timeout ); } else { # SNMPV1 login verb("SNMP v1 login"); ($session, $error) = Net::SNMP->session( -hostname => $o_host, -community => $o_community, -port => $o_port, -timeout => $o_timeout ); } } if (!defined($session)) { printf("ERROR opening session: %s.\n", $error); exit $ERRORS{"UNKNOWN"}; } my $exit_val = undef; ########### Cisco env checks ############## if ($o_check_type eq "cisco") { verb("Checking cisco env"); # Get load table my $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($ciscoEnvMonMIB) : $session->get_table(Baseoid => $ciscoEnvMonMIB); if (!defined($resultat)) { printf("ERROR: Description table : %s.\n", $session->error); $session->close; exit $ERRORS{"UNKNOWN"}; } $session->close; # Get env data index my (@voltindex, @tempindex, @fanindex, @psindex) = (undef, undef, undef, undef); my ($voltexist, $tempexist, $fanexist, $psexist) = (0, 0, 0, 0); my @oid = undef; foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); if ($key =~ /$ciscoVoltageTableDesc/) { @oid = split(/\./, $key); $voltindex[$voltexist++] = pop(@oid); } if ($key =~ /$ciscoTempTableDesc/) { @oid = split(/\./, $key); $tempindex[$tempexist++] = pop(@oid); } if ($key =~ /$ciscoFanTableDesc/) { @oid = split(/\./, $key); $fanindex[$fanexist++] = pop(@oid); } if ($key =~ /$ciscoPSTableDesc/) { @oid = split(/\./, $key); $psindex[$psexist++] = pop(@oid); } } if (($voltexist == 0) && ($tempexist == 0) && ($fanexist == 0) && ($psexist == 0)) { print "No Environemental data found : UNKNOWN"; exit $ERRORS{"UNKNOWN"}; } my $perf_output = ""; # Get the data my ($i, $cur_status) = (undef, undef); my $volt_global = 0; my %volt_status; if ($fanexist != 0) { for ($i = 0; $i < $voltexist; $i++) { $cur_status = $$resultat{ $ciscoVoltageTableState . "." . $voltindex[$i] }; verb($$resultat{ $ciscoVoltageTableDesc . "." . $voltindex[$i] }); verb($cur_status); if (!defined($cur_status)) { ### Error TODO $volt_global = 1; } if (defined($$resultat{ $ciscoVoltageTableValue . "." . $voltindex[$i] })) { $perf_output .= " '" . $$resultat{ $ciscoVoltageTableDesc . "." . $voltindex[$i] } . "'="; $perf_output .= $$resultat{ $ciscoVoltageTableValue . "." . $voltindex[$i] }; } if ($Nagios_state[$CiscoEnvMonNagios{$cur_status}] ne "OK") { $volt_global = 1; $volt_status{ $$resultat{ $ciscoVoltageTableDesc . "." . $voltindex[$i] } } = $cur_status; } } } my $temp_global = 0; my %temp_status; if ($tempexist != 0) { for ($i = 0; $i < $tempexist; $i++) { $cur_status = $$resultat{ $ciscoTempTableState . "." . $tempindex[$i] }; verb($$resultat{ $ciscoTempTableDesc . "." . $tempindex[$i] }); verb($cur_status); if (!defined($cur_status)) { ### Error TODO $temp_global = 1; } if (defined($$resultat{ $ciscoTempTableValue . "." . $tempindex[$i] })) { $perf_output .= " '" . $$resultat{ $ciscoTempTableDesc . "." . $tempindex[$i] } . "'="; $perf_output .= $$resultat{ $ciscoTempTableValue . "." . $tempindex[$i] }; } if ($Nagios_state[$CiscoEnvMonNagios{$cur_status}] ne "OK") { $temp_global = 1; $temp_status{ $$resultat{ $ciscoTempTableDesc . "." . $tempindex[$i] } } = $cur_status; } } } my $fan_global = 0; my %fan_status; if ($fanexist != 0) { for ($i = 0; $i < $fanexist; $i++) { $cur_status = $$resultat{ $ciscoFanTableState . "." . $fanindex[$i] }; verb($$resultat{ $ciscoFanTableDesc . "." . $fanindex[$i] }); verb($cur_status); if (!defined($cur_status)) { ### Error TODO $fan_global = 1; } if ($Nagios_state[$CiscoEnvMonNagios{$cur_status}] ne "OK") { $fan_global = 1; $fan_status{ $$resultat{ $ciscoFanTableDesc . "." . $fanindex[$i] } } = $cur_status; } } } my $ps_global = 0; my %ps_status; if ($psexist != 0) { for ($i = 0; $i < $psexist; $i++) { $cur_status = $$resultat{ $ciscoPSTableState . "." . $psindex[$i] }; if (!defined($cur_status)) { ### Error TODO $fan_global = 1; } if ($Nagios_state[$CiscoEnvMonNagios{$cur_status}] ne "OK") { $ps_global = 1; $ps_status{ $$resultat{ $ciscoPSTableDesc . "." . $psindex[$i] } } = $cur_status; } } } my $global_state = 0; my $output = ""; if ($fanexist != 0) { if ($fan_global == 0) { $output .= $fanexist . " Fan OK"; $global_state = 1 if ($global_state == 0); } else { foreach (keys %fan_status) { $output .= "Fan " . $_ . ":" . $CiscoEnvMonState{ $fan_status{$_} } . " "; if ($global_state < $CiscoEnvMonNagios{ $fan_status{$_} }) { $global_state = $CiscoEnvMonNagios{ $fan_status{$_} }; } } } } if ($psexist != 0) { $output .= ", " if ($output ne ""); if ($ps_global == 0) { $output .= $psexist . " ps OK"; $global_state = 1 if ($global_state == 0); } else { foreach (keys %ps_status) { $output .= "ps " . $_ . ":" . $CiscoEnvMonState{ $ps_status{$_} } . " "; if ($global_state < $CiscoEnvMonNagios{ $ps_status{$_} }) { $global_state = $CiscoEnvMonNagios{ $ps_status{$_} }; } } } } if ($voltexist != 0) { $output .= ", " if ($output ne ""); if ($volt_global == 0) { $output .= $voltexist . " volt OK"; $global_state = 1 if ($global_state == 0); } else { foreach (keys %volt_status) { $output .= "volt " . $_ . ":" . $CiscoEnvMonState{ $volt_status{$_} } . " "; if ($global_state < $CiscoEnvMonNagios{ $volt_status{$_} }) { $global_state = $CiscoEnvMonNagios{ $volt_status{$_} }; } } } } if ($tempexist != 0) { $output .= ", " if ($output ne ""); if ($temp_global == 0) { $output .= $tempexist . " temp OK"; $global_state = 1 if ($global_state == 0); } else { foreach (keys %temp_status) { $output .= "temp " . $_ . ":" . $CiscoEnvMonState{ $temp_status{$_} } . " "; if ($global_state < $CiscoEnvMonNagios{ $temp_status{$_} }) { $global_state = $CiscoEnvMonNagios{ $temp_status{$_} }; } } } } #print $output," : ",$Nagios_state[$global_state]," | ",$perf_output,"\n"; print $output, " : ", $Nagios_state[$global_state], "\n"; $exit_val = $ERRORS{ $Nagios_state[$global_state] }; exit $exit_val; } ############# Nokia checks if ($o_check_type eq "nokia") { verb("Checking nokia env"); my $resultat; # status : 0=ok, 1=nok, 2=temp prb my ($fan_status, $ps_status, $temp_status) = (0, 0, 0); my ($fan_exist, $ps_exist, $temp_exist) = (0, 0, 0); my ($num_fan, $num_ps) = (0, 0); my ($num_fan_nok, $num_ps_nok) = (0, 0); my $global_status = 0; my $output = ""; # get temp $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($nokia_temp_tbl) : $session->get_table(Baseoid => $nokia_temp_tbl); if (defined($resultat)) { verb("temp found"); $temp_exist = 1; if ($$resultat{$nokia_temp} != 1) { $temp_status = 2; $global_status = 1; $output = "Temp CRITICAL "; } else { $output = "Temp OK "; } } # Get fan table $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($nokia_fan_table) : $session->get_table(Baseoid => $nokia_fan_table); if (defined($resultat)) { $fan_exist = 1; foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); if ($key =~ /$nokia_fan_status/) { if ($$resultat{$key} != 1) { $fan_status = 1; $num_fan_nok++ } $num_fan++; } } if ($fan_status == 0) { $output .= ", " . $num_fan . " fan OK"; } else { $output .= ", " . $num_fan_nok . "/" . $num_fan . " fan CRITICAL"; $global_status = 2; } } # Get ps table $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($nokia_ps_table) : $session->get_table(Baseoid => $nokia_ps_table); if (defined($resultat)) { $ps_exist = 1; foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); if ($key =~ /$nokia_ps_status/) { if ($$resultat{$key} != 1) { $ps_status = 1; $num_ps_nok++; } $num_ps++; } if ($key =~ /$nokia_ps_temp/) { if ($$resultat{$key} != 1) { if ($ps_status == 0) { $ps_status = 2; $num_ps_nok++; } } } } if ($ps_status == 0) { $output .= ", " . $num_ps . " ps OK"; } elsif ($ps_status == 2) { $output .= ", " . $num_ps_nok . "/" . $num_ps . " ps WARNING (temp)"; if ($global_status != 2) { $global_status = 1; } } else { $output .= ", " . $num_ps_nok . "/" . $num_ps . " ps CRITICAL"; $global_status = 2; } } $session->close; verb("status : $global_status"); if (($fan_exist + $ps_exist + $temp_exist) == 0) { print "No environemental informations found : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"}; } if ($global_status == 0) { print $output. " : all OK\n"; exit $ERRORS{"OK"}; } if ($global_status == 1) { print $output. " : WARNING\n"; exit $ERRORS{"WARNING"}; } if ($global_status == 2) { print $output. " : CRITICAL\n"; exit $ERRORS{"CRITICAL"}; } } ############# Bluecoat checks if ($o_check_type eq "bc") { verb("Checking bluecoat env"); my $resultat; my $global_status = 0; my ($num_fan, $num_other, $num_volt, $num_temp, $num_disk) = (0, 0, 0, 0, 0); my ($num_fan_ok, $num_other_ok, $num_volt_ok, $num_temp_ok, $num_disk_ok) = (0, 0, 0, 0, 0); my $output = ""; my $output_perf = ""; # get sensor table $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($bc_sensor_table) : $session->get_table(Baseoid => $bc_sensor_table); if (defined($resultat)) { verb("sensor table found"); my ($sens_name, $sens_status, $sens_value, $sens_unit) = (undef, undef, undef, undef); foreach my $key (keys %$resultat) { if ($key =~ /$bc_sensor_Name/) { $sens_name = $$resultat{$key}; $key =~ s/$bc_sensor_Name//; $sens_unit = $$resultat{ $bc_sensor_units . $key }; if ($$resultat{ $bc_sensor_Status . $key } != 1) { # sensor not operating : output and status unknown if ($output ne "") { $output .= ", "; } $output .= $sens_name . " sensor " . $bc_SensorStatus[$$resultat{ $bc_sensor_Status . $key }]; if ($global_status == 0) { $global_status = 3; } } else { # Get status $sens_status = $bc_status_nagios[$$resultat{ $bc_sensor_Code . $key }]; if ($sens_status != 0) { # warn/critical/unknown : output if ($output ne "") { $output .= ", "; } $output .= $sens_name . ":" . $bc_SensorCode[$sens_status]; set_status($sens_status, $global_status); } } if (defined($o_perf)) { if ($output_perf ne "") { $output_perf .= " "; } $output_perf .= "'" . $sens_name . "'="; my $perf_value = $$resultat{ $bc_sensor_Value . $key } * 10**$$resultat{ $bc_sensor_Scale . $key }; $output_perf .= $perf_value; } ### FAN if ($bc_mesure[$sens_unit] eq "rpm") { $num_fan++; if ($sens_status == 0) { $num_fan_ok++; } } elsif ($bc_mesure[$sens_unit] eq "celsius") { $num_fan++; if ($sens_status == 0) { $num_temp_ok++; } } elsif ($bc_mesure[$sens_unit] eq "volts") { $num_volt++; if ($sens_status == 0) { $num_volt_ok++; } } else { $num_other++; if ($sens_status == 0) { $num_other_ok++; } } } } } # Get disk table $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($bc_dsk_table) : $session->get_table(Baseoid => $bc_dsk_table); if (defined($resultat)) { foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); my ($dsk_name, $dsk_status) = (undef, undef, undef); if ($key =~ /$bc_dsk_status/) { $num_disk++; $dsk_status = $bc_dsk_status_nagios[$$resultat{$key}]; if ($dsk_status != 0) { $key =~ s/$bc_dsk_status//; $dsk_name = $$resultat{ $bc_dsk_vendor . $key } . "(" . $$resultat{ $bc_dsk_serial . $key } . ")"; if ($output ne "") { $output .= ", "; } $output .= $dsk_name . ":" . $bc_DiskStatus[$$resultat{ $bc_dsk_status . $key }]; set_status($dsk_status, $global_status); } else { $num_disk_ok++; } } } } if ($num_fan + $num_other + $num_volt + $num_temp + $num_disk == 0) { print "No information found : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"}; } if ($output ne "") { $output .= ", "; } if ($num_fan_ok != 0) { $output .= $num_fan_ok . " fan OK "; } if ($num_other_ok != 0) { $output .= $num_other_ok . " other OK "; } if ($num_volt_ok != 0) { $output .= $num_volt_ok . " voltage OK "; } if ($num_temp_ok != 0) { $output .= $num_temp_ok . " temp OK "; } if ($num_disk_ok != 0) { $output .= $num_disk_ok . " disk OK "; } if (defined($o_perf)) { $output_perf = " | " . $output_perf; } if ($global_status == 3) { print $output, " : UNKNOWN", $output_perf, "\n"; exit $ERRORS{"UNKNOWN"}; } if ($global_status == 2) { print $output, " : CRITICAL", $output_perf, "\n"; exit $ERRORS{"CRITICAL"}; } if ($global_status == 1) { print $output, " : WARNING", $output_perf, "\n"; exit $ERRORS{"WARNING"}; } print $output, " : OK", $output_perf, "\n"; exit $ERRORS{"OK"}; } ############# Ironport checks if ($o_check_type eq "iron") { verb("Checking Ironport env"); my $resultat; # status : 0=ok, 1=warn, 2=crit my ($fan_status, $ps_status, $temp_status) = (0, 0, 0); my ($fan_exist, $ps_exist, $temp_exist) = (0, 0, 0); my ($num_fan, $num_ps, $num_temp) = (0, 0, 0); my ($num_fan_nok, $num_ps_nok, $num_temp_nok) = (0, 0, 0); my $global_status = 0; my $output = ""; # get temp if $o_temp is defined if (defined($o_temp)) { verb("Checking temp < $o_temp"); $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($iron_tmp_table) : $session->get_table(Baseoid => $iron_tmp_table); if (defined($resultat)) { verb("temp found"); $temp_exist = 1; foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); if ($key =~ /$iron_tmp_celcius/) { verb("Status : $$resultat{$key}"); if ($$resultat{$key} > $o_temp) { my @index_oid = split(/\./, $key); my $index_oid_key = pop(@index_oid); $output .= ",Temp : " . $$resultat{ $iron_tmp_name . "." . $index_oid_key } . " : " . $$resultat{$key} . " C"; $temp_status = 2; $num_temp_nok++; } $num_temp++; } } if ($temp_status == 0) { $output .= ", " . $num_temp . " temp < " . $o_temp . " OK"; } else { $output .= ", " . $num_temp_nok . "/" . $num_temp . " temp probes CRITICAL"; $global_status = 2; } } } # Get fan status if $o_fan is defined if (defined($o_fan)) { verb("Checking fan > $o_fan"); $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($iron_fan_table) : $session->get_table(Baseoid => $iron_fan_table); if (defined($resultat)) { verb("fan found"); $fan_exist = 1; foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); if ($key =~ /$iron_fan_rpm/) { verb("Status : $$resultat{$key}"); if ($$resultat{$key} < $o_fan) { my @index_oid = split(/\./, $key); my $index_oid_key = pop(@index_oid); $output .= ",Fan " . $$resultat{ $iron_fan_name . "." . $index_oid_key } . " : " . $$resultat{$key} . " RPM"; $fan_status = 2; $num_fan_nok++; } $num_fan++; } } if ($fan_status == 0) { $output .= ", " . $num_fan . " fan > " . $o_fan . " OK"; } else { $output .= ", " . $num_fan_nok . "/" . $num_fan . " fans CRITICAL"; $global_status = 2; } } } # Get power supply status verb("Checking PS"); $resultat = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($iron_ps_table) : $session->get_table(Baseoid => $iron_ps_table); if (defined($resultat)) { verb("ps found"); $ps_exist = 1; foreach my $key (keys %$resultat) { verb("OID : $key, Desc : $$resultat{$key}"); if ($key =~ /$iron_ps_status/) { verb("Status : $iron_ps_status_name[$$resultat{$key}]"); if ($iron_ps_status_nagios[$$resultat{$key}] != 0) { my @index_oid = split(/\./, $key); my $index_oid_key = pop(@index_oid); $output .= ",PS " . $$resultat{ $iron_ps_name . "." . $index_oid_key } . " : " . $iron_ps_status_name[$$resultat{$key}]; $ps_status = 2; $num_ps_nok++; } $num_ps++; } } if ($ps_status == 0) { $output .= ", " . $num_ps . " ps OK"; } else { $output .= ", " . $num_ps_nok . "/" . $num_ps . " ps CRITICAL"; $global_status = 2; } } $session->close; verb("status : $global_status"); if (($fan_exist + $ps_exist + $temp_exist) == 0) { print "No environemental informations found : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"}; } $output =~ s/^,//; if ($global_status == 0) { print $output. " : all OK\n"; exit $ERRORS{"OK"}; } if ($global_status == 1) { print $output. " : WARNING\n"; exit $ERRORS{"WARNING"}; } if ($global_status == 2) { print $output. " : CRITICAL\n"; exit $ERRORS{"CRITICAL"}; } } ########### Foundry env checks ############## if ($o_check_type eq "foundry") { verb("Checking foundry env"); my $global_status = 0; # status to UNKNOWN my $output = ""; # Get temperature my @foundry_temp_oid = ($foundry_temp, $foundry_temp_warn, $foundry_temp_crit); my $result_temp = $session->get_request(Varbindlist => \@foundry_temp_oid); my $temp_found = 0; if (defined($result_temp)) { $temp_found = 1; #Temp found $output = "Temp : " . $$result_temp{$foundry_temp} / 2; if ($$result_temp{$foundry_temp} > $$result_temp{$foundry_temp_crit}) { # Temp above critical $output .= " > " . $$result_temp{$foundry_temp_crit} / 2 . " : CRITICAL"; $global_status = 3; } elsif ($$result_temp{$foundry_temp} > $$result_temp{$foundry_temp_warn}) { # Temp above warning $output .= " > " . $$result_temp{$foundry_temp_warn} / 2 . " : WARNING"; $global_status = 2; } else { $output .= " < " . $$result_temp{$foundry_temp_warn} / 2 . " : OK"; $global_status = 1; } } # Get PS table (TODO : Bug in FAN table, see with Foundry). my $result_ps = (version->parse(Net::SNMP->VERSION) < 4) ? $session->get_table($foundry_ps_table) : $session->get_table(Baseoid => $foundry_ps_table); my $ps_num = 0; if (defined($result_ps)) { $output .= ", " if defined($output); foreach my $key (keys %$result_ps) { verb("OID : $key, Desc : $$result_ps{$key}"); if ($$result_ps{$key} =~ /$foundry_ps_desc/) { $ps_num++; my @oid_list = split(/\./, $key); my $index_ps = pop(@oid_list); $index_ps = $foundry_ps_status . "." . $index_ps; if (defined($$result_ps{$index_ps})) { if ($$result_ps{$index_ps} == 3) { $output .= "PS " . $$result_ps{$key} . " : FAILURE"; $global_status = 3; } elsif ($$result_ps{$index_ps} == 2) { $global_status = 1 if ($global_status == 0); } else { $output .= "ps " . $$result_ps{$key} . " : OTHER"; } } else { $output .= "ps " . $$result_ps{$key} . " : UNDEFINED STATUS"; } } } } $session->close; if (($ps_num + $temp_found) == 0) { print "No data found : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"}; } if ($global_status == 1) { print $output. " : all OK\n"; exit $ERRORS{"OK"}; } if ($global_status == 2) { print $output. " : WARNING\n"; exit $ERRORS{"WARNING"}; } if ($global_status == 3) { print $output. " : CRITICAL\n"; exit $ERRORS{"CRITICAL"}; } print $output. " : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"}; } ########### Cisco env checks ############## if ($o_check_type eq "linux") { verb("Checking linux env"); print "Not implemented yet : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"}; } print "Unknown check type : UNKNOWN\n"; exit $ERRORS{"UNKNOWN"};