Handling power status using snmptrapd

Home | Myself | Resume | Articles | Tutorials

If you are new to this topic

Refer the following if you are new to SNMP

Net-snmp

Various tools relating to the Simple Network Management Protocol including:

See NET-SNMP site

snmptrapd

Snmptrapd is an SNMP application that receives and logs snmp trap messages sent to the SNMP-TRAP port (162) on the local machine. It can be configured to run a specific program on receiving a snmp trap.

snmptrapd.conf

snmptrapd.conf is the configuration file(s) which define how the ucd-snmp SNMP trap receiving demon operates when it receives a trap.

ups-MIB

RFC1628 document defines the managed objects for Uninterruptible Power Supplies which are to be manageable via the Simple Network Management Protocol (SNMP)

How to use snmptrapd with powerd

Please Note: I renamed 'powerd' as 'powerh' as here it is not a daemon but only a trap handling routine

We had the powerd to handle the Power Status of the system. powerd communicates with the UPS through the serial port. However, in a networked system where a number of machines are using the same UPS it is not possible for each system to directly communicate with the UPS. Most modern high capacity UPS support the SNMP Protocol either directly or through a proxy. To handle various power status follow these steps

1. To your snmptrapd.conf add the following lines

traphandle 33.2.3 powerh b
traphandle 33.2.4 powerh p

2. Compile the following c code by entering cc powerh.c -o powerhand copy powerh to a directory in path like /usr/local/sbin/






#include <string.h>
#include <unistd.h>
#include <stdio.h>
#include <fcntl.h>
#include <signal.h>


#define PWRSTAT "/etc/powerstatus"

void powerfail(int);

main(int argc, char* argv[]) {
    char s[1000];
    int i=0;
    while(i<7) {
        scanf("%s",s);
        i++;
    }
    scanf("%s",s);
    if (!strcmp("b",argv[1]))
        if ((!strcmp(s,"33.1.6.3.3"))||(!strcmp(s,"upsMIB.upsObjects.upsAlarm.upsWellKnownAlarms.upsAlarmLowBattery")))
            powerfail(1);
    if (!strcmp("p",argv[1]))
        if ((!strcmp(s,"33.1.6.3.3"))||(!strcmp(s,"upsMIB.upsObjects.upsAlarm.upsWellKnownAlarms.upsAlarmLowBattery")))
            powerfail(0);
}
/* As the program may be activated in the event of other alarms as well, the inner 'if' are necessary */
void powerfail(int event) {
    int fd;
    unlink(PWRSTAT);
    if ((fd = open(PWRSTAT, O_CREAT|O_WRONLY, 0644)) >= 0) {
          switch (event)
           {
           case 0:
                  write(fd, "OKWAIT\n", 7);
                   break;

             case 1:
                    write(fd, "FAIL\n", 5);
                     break;
             }
          close(fd);
       }
       kill(1, SIGPWR);
}



3. Run snmptrapd on your system (you can configure it in the init scripts)

The system will shutdown 2 minutes after receiving a 'battery low alarm' from the UPS and if power is OK before the shutdown it will cancel shutdown or as configured in the powerfail and powerokwait lines in /etc/inittabCode Explanation

When received a trap 33.2.3 (upsMIB.upsTraps.upsTrapAlarmEntryAdded) the program is executed with a 'b' option. Program checks for the 'upsAlarmId' send by the trap and if it is 33.1.6.3.3 (upsMIB.upsObjects.upsAlarm.upsWellKnownAlarms.upsAlarmLowBattery) it notfies init that a power failure occurred. This alarm is added to the alarm table by the ups agent if the remaining battery run-time is less than or equal to upsConfigLowBattTime. It is removed when the power is back and is acknowledged by trap 33.2.4. The program then sends init a powerokwait message.

Drawbacks

TODO

I would like to see this few lines of code grow into a complete general purpose UPS managing software capable of

All Suggestions, Criticisms,Contibutions(code and idea only - no cash please ;) ) etc. are welcome. You can contact me at [email protected].


This site is under construction. Last updated on 29th March 2004
Hosted by www.Geocities.ws

1