snmpit_apc.pm 2.77 KB
Newer Older
1
#!/usr/bin/perl -w
Leigh B. Stoller's avatar
Leigh B. Stoller committed
2 3 4

#
# EMULAB-COPYRIGHT
5
# Copyright (c) 2000-2003 University of Utah and the Flux Group.
Leigh B. Stoller's avatar
Leigh B. Stoller committed
6 7 8
# All rights reserved.
#

9 10 11 12 13 14 15 16 17 18 19
#
# snmpit module for APC MasterSwitch power controllers
#
# supports new(ip), power(on|off|cyc[le],port)
#

package snmpit_apc;

$| = 1; # Turn off line buffering on output

use SNMP;
20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37
use strict;

sub new($$;$) {

    # The next two lines are some voodoo taken from perltoot(1)
    my $proto = shift;
    my $class = ref($proto) || $proto;

    my $devicename = shift;
    my $debug = shift;

    if (!defined($debug)) {
	$debug = 0;
    }

    if ($debug) {
	print "snmpit_apm module initializing... debug level $debug\n";
    }
38

39
    $SNMP::debugging = ($debug - 5) if $debug > 5;
40 41 42 43 44
    my $mibpath = "/usr/local/share/snmp/mibs";
    &SNMP::addMibDirs($mibpath);
    &SNMP::addMibFiles("$mibpath/RFC1155-SMI.txt",
	"$mibpath/PowerNet-MIB.txt");

45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62
    $SNMP::save_descriptions = 1; # must be set prior to mib initialization
    SNMP::initMib();              # parses default list of Mib modules
    $SNMP::use_enums = 1;         #use enum values instead of only ints
    print "Opening SNMP session to $devicename..." if $debug;
    my $sess =new SNMP::Session(DestHost => $devicename, Community => 'private');
    if (!defined($sess)) {
	warn("ERROR: Unable to connect to $devicename via SNMP\n");
	return undef;
    }

    my $self = {};

    $self->{SESS} = $sess;
    $self->{DEBUG} = $debug;
    $self->{DEVICENAME} = $devicename;

    bless($self,$class);
    return $self;
63 64 65
}

sub power {
66 67
    my $self = shift;
    my $op = shift;
68 69
    my @ports = @_;

70 71 72 73
    my $CtlOID = ".1.3.6.1.4.1.318.1.1.4.4.2.1.3";
    if    ($op eq "on")  { $op = "outletOn";    }
    elsif ($op eq "off") { $op = "outletOff";   }
    elsif ($op =~ /cyc/) { $op = "outletReboot";}
74 75 76 77 78 79 80 81 82

    my $errors = 0;

    foreach my $port (@ports) {
	print STDERR "**** Controlling port $port\n" if ($self->{DEBUG} > 1);
	if ($self->UpdateField($CtlOID,$port,$op)) {
	    print STDERR "Outlet #$port control failed.\n";
	    $errors++;
	}
83
    }
84 85

    return $errors;
86 87 88
}

sub UpdateField {
89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109
    my ($self,$OID,$port,$val) = @_;

    print "sess=$self->{SESS} $OID $port $val\n" if $self->{DEBUG} > 1;

    my $Status = 0;
    my $retval;

    print "Checking port $port of $self->{DEVICENAME} for $val..." if $self->{DEBUG};
    $Status = $self->{SESS}->get([[$OID,$port]]);
    if (!defined $Status) {
	print STDERR "Port $port, change to $val: No answer from device\n";
	return 1;
    } else {
	print "Okay.\nPort $port was $Status\n" if $self->{DEBUG};
	if ($Status ne $val) {
	    print "Setting $port to $val..." if $self->{DEBUG};
	    $retval = $self->{SESS}->set([[$OID,$port,$val,"INTEGER"]]);
	    print "Set returned '$retval'" if $self->{DEBUG};
	    if ($retval) { return 0; } else { return 1; }
	}
	return 0;
110 111 112 113 114
    }
}

# End with true
1;