# -*-perl-*- # Cricket: a configuration, polling and data display wrapper for RRD files # # Copyright (C) 1998 Jeff R. Allen and WebTV Networks, Inc. # # 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; either version 2 of the License, or # (at your option) any later version. # # 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., 675 Mass Ave, Cambridge, MA 02139, USA. # This lets people replace our choice of snmp libraries by simply # replacing snmpUtils.pm (Ed, this means you! ) use snmpUtils; use Common::Log; use strict; # This tells the collector that we are open for business and # happy to handle snmp:// datasources. $main::gDSFetch{'snmp'} = \&snmpFetch; sub snmpFetch { # This procedure is passed a REFERENCE to an array of SNMP datasources. # # Each element consists of a string like: # index://community@host:port/oid # community and port are optional. If they are left out, they # will default to public and 161, respectively. # # VERY IMPORTANT: The index MUST be returned with the corresponding value, # otherwise it'll get put back into the wrong spot in the RRD. my($dsList, $name, $target) = @_; my(%oidsPerSnmp) = (); my($dsspec); my($oidMap) = $main::gCT->configHash($name, 'oid'); foreach $dsspec (@{ $dsList }) { my($index); ($index, $dsspec) = split(/:/, $dsspec, 2); $dsspec =~ s#^//##; # This little hack is for people who like to use slashes in their # community strings. my($comm, $cinfo) = split(/@/, $dsspec, 2); my($snmp, $oid) = split(/\//, $cinfo, 2); $snmp = $comm . "@" . $snmp; $oid = mapOid($oidMap, $oid); if (! defined $oid) { Warn("Could not find an OID in $dsspec"); return (); } # Debug("SNMP parser: snmp://$snmp/$oid"); # we only try to process them if we didn't find a problem # above (hence the check for undef) push(@{ $oidsPerSnmp{$snmp} }, "$index:$oid") if (defined $oid); } my(@results) = (); while (my($snmp, $snmpDSRef) = each %oidsPerSnmp) { my(@oidsToQuery) = (); if ($#{ $snmpDSRef } >= 0) { my(@oidsToQuery) = my(@indices) = (); my($line); while ($line = shift @{ $snmpDSRef }) { my($index, $oid) = split(/:/, $line); push(@indices, $index); push(@oidsToQuery, $oid); } Debug("Getting from $snmp ", join(" ", @oidsToQuery)); my(@hostResults) = snmpUtils::get($snmp, @oidsToQuery); Debug("Got: ", join(" ", @hostResults)); # it tells us everything went to hell by returning # scalar -1. Unfortunately, we interpret that as the first # result. So, make it undef so that we fix it later. # hopefully, we don't need to fetch a -1 all the time... if (defined($hostResults[0]) && $hostResults[0] == -1) { $hostResults[0] = undef; } # turn undefs into "U"'s to make RRD happy my($ctr); for $ctr ( 0..$#indices ) { my($res) = $hostResults[$ctr]; $res = "U" if (! defined($res)); push(@results, "$indices[$ctr]:" . Common::Util::fixNum($res)); } } } return @results; } 1; # Local Variables: # mode: perl # indent-tabs-mode: nil # tab-width: 4 # perl-indent-level: 4 # End: