From 9b722622ae0f2f54bce6a6ea660cf5db1afa53c5 Mon Sep 17 00:00:00 2001 From: Rien Broekstra Date: Wed, 5 Aug 2009 10:43:46 +0200 Subject: [PATCH] Initial version --- plugins/other/snmp__ipoman_ | 445 ++++++++++++++++++++++++++++++++++++ 1 file changed, 445 insertions(+) create mode 100755 plugins/other/snmp__ipoman_ diff --git a/plugins/other/snmp__ipoman_ b/plugins/other/snmp__ipoman_ new file mode 100755 index 00000000..322909d0 --- /dev/null +++ b/plugins/other/snmp__ipoman_ @@ -0,0 +1,445 @@ +#!/usr/bin/perl -w +# +# What is snmp__ipoman_ +# ---------------------- +# snmp__ipoman is a munin plugin written for the Ingrasys IpomanII 1202 +# Power Distribution Unit. It should work on any PDU conforming to +# the IPOMANII-MIB. +# +# How do I use it +# --------------- +# You can use this plugin on a system with a working munin-node. Here's +# how: +# +# 1. Copy snmp__ipoman_ to the directory where all your munin plugins +# reside, for example /usr/share/munin/plugins. +# +# 2. Make the following symlinks to snmp__ipoman_ in that same directory +# +# snmp__ipoman_inletcurrent_ +# snmp__ipoman_inletpower_ +# snmp__ipoman_inletvoltage_ +# snmp__ipoman_outletpower_ +# snmp__ipoman_outletcurrent_ +# +# (If you wonder why. I did not manage to make a plugin which has both +# the 'snmpconf' and the 'suggest' capabilities. So either I had to make +# separate plugins for all graph types, or I would have to make +# assumptions on the number of ports and the address of the ipoman in +# the script.) +# +# 3. Change to the directory where the links to munin plugins reside +# that are to be run by munin-node, for example /etc/munin/plugins/ +# +# 4. Run munin-node-configure-snmp: +# +# $ munin-node-configure-snmp --snmpversion=1 | sh -x +# +# where is the hostname or ip address of your ipoman. This +# will create and print a bunch of symlinks to snmp__ipoman_ which will +# output current and power usage for all available outlets of the +# ipoman, and current, power usage and voltage/frequency on all inlets +# of the ipoman. +# +# 5. Restart munin-node +# +# 6. Make an entry in your munin server's munin.conf: +# +# [] +# address
+# use_node_name no +# +# 7. Done. +# +# Copyright (C) 2009 Rien Broekstra +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; version 2 dated June, +# 1991. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# Munin plugin to monitor power consumption and current of the sockets of an +# Ingrasys IpomanII 1202 Power Distribution Unit, or any power distribution +# unit that conforms to IPOMANII-MIB via SNMP. +# +# Parameters: +# +# config +# snmpconf +# +# Relevant OID's under .iso.org.dod.internet.private.enterprises.ingrasys.product.pduAgent.iPoManII +# .ipmObjects.ipmDevice.ipmDeviceOutlet.ipmDeviceOutletNumber.0 +# .ipmObjects.ipmDevice.ipmDeviceOutlet.ipmDeviceOutletStatusTable.ipmDeviceOutletStatusEntry.outletStatusIndex.1 +# .ipmObjects.ipmDevice.ipmDeviceOutlet.ipmDeviceOutletStatusTable.ipmDeviceOutletStatusEntry.outletStatusCurrent.1 +# .ipmObjects.ipmDevice.ipmDeviceOutlet.ipmDeviceOutletStatusTable.ipmDeviceOutletStatusEntry.outletStatusKwatt.1 +# .ipmObjects.ipmDevice.ipmDeviceOutlet.ipmDeviceOutletStatusTable.ipmDeviceOutletStatusEntry.outletStatusWH.1 +# +# Version 0.1, Aug 4, 2009 +# +# +# +# +# +# +# +# +# +# +# MAGIC MARKERS: +# +#%# family=snmpauto +#%# capabilities=snmpconf + +use strict; +use Net::SNMP; + +my $DEBUG = 0; + +my $host = $ENV{host} || undef; +my $port = $ENV{port} || 161; +my $community = $ENV{community} || "public"; +my $iface = $ENV{interface} || undef; + +my $socketnumber; +my $response; +my $graphtype; + +# +# Infer host, inlet/socketnumber and graphtype from the symlink name to this plugin. +# +if ($0 =~ /^(?:|.*\/)snmp_([^_]*)_ipoman_([^_]*)_(.*)$/) +{ + $host = $1; + $graphtype = $2; + $socketnumber = $3; + if ($host =~ /^([^:]+):(\d+)$/) { + $host = $1; + $port = $2; + } +} + +if (!defined($graphtype)) { + die "# Error: couldn't understand what quantity I'm supposed to monitor."; +} + +# +# The relevant OID's on the IPOMAN +# +my $oid_inletnumber = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.1.0"; +my $oid_inletindextable = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.2.1.1."; +my $oid_inletvoltage = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.3.1.2."; +my $oid_inletcurrent = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.3.1.3."; +my $oid_inletfrequency = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.3.1.4."; +my $oid_inletenergy = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.3.1.5."; + +my $oid_outletnumber = ".1.3.6.1.4.1.2468.1.4.2.1.3.2.1.0"; +my $oid_outletindextable = ".1.3.6.1.4.1.2468.1.4.2.1.3.2.3.1.1."; +my $oid_outletdescription = ".1.3.6.1.4.1.2468.1.4.2.1.3.2.2.1.2."; +my $oid_outletcurrent = ".1.3.6.1.4.1.2468.1.4.2.1.3.2.3.1.3."; +my $oid_outletenergy = ".1.3.6.1.4.1.2468.1.4.2.1.3.2.3.1.4."; +# FIXME: The voltage is not defined per outlet. For now we just assume that all sockets have the voltage on inlet 1. +my $oid_outletvoltage = ".1.3.6.1.4.1.2468.1.4.2.1.3.1.3.1.2.1"; + +# +# The snmpconf section prints out what oid's we need for the quantity we want to monitor, and where we find out how many ports the device has. +# +if (defined $ARGV[0] and $ARGV[0] eq "snmpconf") { + if ($graphtype eq "inletvoltage") { + print "number $oid_inletnumber\n"; + print "index $oid_inletindextable\n"; + print "require $oid_inletvoltage [0-9]+\n"; + print "require $oid_inletfrequency [0-9]+\n"; + } + elsif ($graphtype eq "inletcurrent") { + print "number $oid_inletnumber\n"; + print "index $oid_inletindextable\n"; + print "require $oid_inletcurrent [0-9]+\n"; + } + elsif ($graphtype eq "inletpower") { + print "number $oid_inletnumber\n"; + print "index $oid_inletindextable\n"; + print "require $oid_inletvoltage [0-9]+\n"; + print "require $oid_inletcurrent [0-9]+\n"; + } + elsif ($graphtype eq "outletcurrent") { + print "number $oid_outletnumber\n"; + print "index $oid_outletindextable\n"; + print "require $oid_outletcurrent [0-9]+\n"; + } + elsif ($graphtype eq "outletpower") { + print "number $oid_outletnumber\n"; + print "index $oid_outletindextable\n"; + print "require $oid_outletvoltage [0-9]+\n"; + print "require $oid_outletcurrent [0-9]+\n"; + } + else { + print "require dont.graph.anything [0-9]+\n" + } + exit 0; +} + +# +# For all other options we need to connect to the host in our $0. if we cannot, bail out. +# +if (!defined($host)) +{ + print "# Debug: $0 -- $1 -- $2\n" if $DEBUG; + die "# Error: couldn't understand what I'm supposed to monitor."; +} + +my ($session, $error) = Net::SNMP->session( + -hostname => $host, + -community => $community, + -port => $port + ); + +if (!defined ($session)) +{ + die "Croaking: $error"; +} + +# +# Output graph configuration depending on what quantity we want to plot +# +if (defined $ARGV[0] and $ARGV[0] eq "config") { + print "host_name $host\n"; + if ($graphtype eq "inletvoltage") { + + print "graph_title Inlet $socketnumber voltage/frequency\n"; + + print "graph_args --base 1000 -l 0\n"; + print "graph_category system\n"; + print "graph_info This graph shows the tension and frequency to inlet $socketnumber on the Power Distribution Unit\n"; + + print "voltage.label Tension (V)\n"; + print "voltage.draw LINE2\n"; + print "voltage.type GAUGE\n"; + + print "frequency.label Frequency (Hz)\n"; + print "frequency.draw LINE2\n"; + print "frequency.type GAUGE\n"; + + } + elsif ($graphtype eq "inletcurrent") { + print "graph_title Inlet $socketnumber current\n"; + + print "graph_args --base 1000 -l 0\n"; + print "graph_category system\n"; + print "graph_info This graph shows the delivered current to inlet $socketnumber on the Power Distribution Unit\n"; + + print "current.label Current (A)\n"; + print "current.draw AREA\n"; + print "current.type GAUGE\n"; + + } + elsif ($graphtype eq "inletpower") { + print "graph_title Inlet $socketnumber power\n"; + + print "graph_args --base 1000 -l 0\n"; + print "graph_category system\n"; + print "graph_info This graph shows the delivered apparent and real power to inlet $socketnumber of the Power Distribution Unit\n"; + + print "apparentpower.label Apparent power (kVA)\n"; + print "apparentpower.draw LINE3\n"; + print "apparentpower.type GAUGE\n"; + + print "realpower.label Real power (kW)\n"; + print "realpower.draw AREA\n"; + print "realpower.type COUNTER\n"; + + exit 0; + } + elsif ($graphtype eq "outletcurrent") { + print "graph_title Outlet $socketnumber current\n"; + + print "graph_args --base 1000 -l 0\n"; + print "graph_category system\n"; + print "graph_info This graph shows the delivered current to outlet $socketnumber of the Power Distribution Unit\n"; + + print "current.label Delivered current (A)\n"; + print "current.draw AREA\n"; + print "current.type GAUGE\n"; + } + elsif ($graphtype eq "outletpower") { + print "graph_title Outlet $socketnumber power\n"; + + print "graph_args --base 1000 -l 0\n"; + print "graph_category system\n"; + print "graph_info This graph shows the delivered apparent and real power to outlet $socketnumber of the Power Distribution Unit\n"; + + print "apparentpower.label Apparent power (kVA)\n"; + print "apparentpower.draw LINE3\n"; + print "apparentpower.type GAUGE\n"; + + print "realpower.label Real power (kW)\n"; + print "realpower.draw AREA\n"; + print "realpower.type COUNTER\n"; + + exit 0; + } + exit 0; +} + +if ($graphtype eq "inletvoltage") { + my ($voltage, $frequency); + + if (defined ($response = $session->get_request($oid_inletvoltage.$socketnumber))) { + $voltage = $response->{$oid_inletvoltage.$socketnumber}; + } + else { + $voltage = 'U'; + } + + if (defined ($response = $session->get_request($oid_inletfrequency.$socketnumber))) { + $frequency = $response->{$oid_inletfrequency.$socketnumber}; + } + else { + $frequency = 'U'; + } + + # The IPOMAN returns tension in 0.1V units. + # Convert to V + if ($voltage ne 'U') { + $voltage = $voltage/10; + } + + # The IPOMAN returns frequency in 0.1Hz units. + # Convert to Hz + if ($frequency ne 'U') { + $frequency = $frequency/10; + } + + print "voltage.value ", $voltage, "\n"; + print "frequency.value ", $frequency, "\n"; +} +elsif ($graphtype eq "inletcurrent") { + my $current; + + if (defined ($response = $session->get_request($oid_inletcurrent.$socketnumber))) { + $current = $response->{$oid_inletcurrent.$socketnumber}; + } + else { + $current = 'U'; + } + + # The IPOMAN returns power in mA. + # Convert to A: + # + if ($current ne 'U') { + $current = $current/1000; + } + + print "current.value ", $current, "\n"; +} +elsif ($graphtype eq "inletpower") { + my ($current, $energy, $voltage, $apparentpower); + + if (defined ($response = $session->get_request($oid_inletcurrent.$socketnumber))) { + $current = $response->{$oid_inletcurrent.$socketnumber}; + } + else { + $current = 'U'; + } + + if (defined ($response = $session->get_request($oid_inletenergy.$socketnumber))) { + $energy = $response->{$oid_inletenergy.$socketnumber}; + } + else { + $energy = 'U'; + } + + if (defined ($response = $session->get_request($oid_inletvoltage.$socketnumber))) { + $voltage = $response->{$oid_inletvoltage.$socketnumber}; + } + else { + $voltage = 'U'; + } + + # Calculate results + # Apparent power (VA)= Voltage (V)* Current(A). + # IPOMAN delivers voltage in units of 0.1V. and current in units of mA: + if ($current ne 'U' && $voltage ne 'U') { + $apparentpower = ($current/1000)*($voltage/10); + } + + # + # The IPOMAN returns consumed energy in Wh. We want it in J (= Ws), in order for munin to graph in W. + # + if ($energy ne 'U') { + $energy = $energy*3600; + } + + print "realpower.value ", $energy, "\n"; + print "apparentpower.value ", $apparentpower, "\n"; +} +elsif ($graphtype eq "outletcurrent") { + my $current; + + if (defined ($response = $session->get_request($oid_outletcurrent.$socketnumber))) { + $current = $response->{$oid_outletcurrent.$socketnumber}; + } + else { + $current = 'U'; + } + + # The IPOMAN returns power in mA. + # Convert to A: + # + if ($current ne 'U') { + $current = $current/1000; + } + + print "current.value ", $current, "\n"; +} +elsif ($graphtype eq "outletpower") { + my ($current, $energy, $voltage, $apparentpower); + + if (defined ($response = $session->get_request($oid_outletcurrent.$socketnumber))) { + $current = $response->{$oid_outletcurrent.$socketnumber}; + } + else { + $current = 'U'; + } + + if (defined ($response = $session->get_request($oid_outletenergy.$socketnumber))) { + $energy = $response->{$oid_outletenergy.$socketnumber}; + } + else { + $energy = 'U'; + } + + if (defined ($response = $session->get_request($oid_outletvoltage))) { + $voltage = $response->{$oid_outletvoltage}; + } + else { + $voltage = 'U'; + } + + # + # Calculate results + # Apparent power (VA)= Voltage (V)* Current(A). + # IPOMAN delivers voltage in units of 0.1V. and current in units of mA: + if ($current ne 'U' && $voltage ne 'U') { + $apparentpower = ($current/1000)*($voltage/10); + } + + # + # The IPOMAN returns consumed energy in Wh. We want it in J (= Ws), in order for munin to graph in W. + # + if ($energy ne 'U') { + $energy = $energy*3600; + } + + print "realpower.value ", $energy, "\n"; + print "apparentpower.value ", $apparentpower, "\n"; +} +exit 0;