/* * openupsd.h -- global stuff * Copyright (C) 2002-2003 Fred Barnes * * 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. */ #ifndef __OPENUPSD_H #define __OPENUPSD_H /*{{{ generic stuff*/ #if defined(HAVE_SYSLOG_H) && defined(HAVE_SYSLOG) #define SUPPORT_SYSLOG 1 #else #undef SUPPORT_SYSLOG #endif #ifndef EXIT_SUCCESS #define EXIT_SUCCESS 0 #endif #ifndef EXIT_FAILURE #define EXIT_FAILURE 1 #endif /*}}}*/ /*{{{ UPS state stuff (specifically for watching for power-issues)*/ #define UPSD_BAT_WEAK 0x01 #define UPSD_BAT_WEAK_MASK UPSD_BAT_WEAK #define UPSD_BAT_DISCHARGE 0x02 #define UPSD_BAT_DISCHARGE_MASK UPSD_BAT_DISCHARGE #define UPSD_OUT_INVERTER 0x01 #define UPSD_OUT_INVERTER_MASK UPSD_OUT_INVERTER #define UPSD_ST_OVERHEAT 0x01 #define UPSD_ST_ONBATTERY 0x02 #define UPSD_ST_OUTPUTBAD 0x04 #define UPSD_ST_OVERLOAD 0x08 #define UPSD_ST_BYPASSBAD 0x10 #define UPSD_ST_OUTPUTOFF 0x20 #define UPSD_ST_CHARGERBAD 0x40 #define UPSD_ST_UPSOFF 0x80 #define UPSD_ST_FANFAIL 0x100 #define UPSD_ST_FUSEBREAK 0x200 #define UPSD_ST_FAULT 0x400 #define UPSD_ST_AWAITPOWER 0x800 #define UPSD_ST_BUZZERON 0x1000 /* field constants, used to access particular members of this structure (in a round-about way) */ #define UPSD_DS_MODEL 0 /* model name */ #define UPSD_DS_BAT_COND 1 /* battery condition (UPSD_BAT_WEAK) */ #define UPSD_DS_BAT_IS 2 /* battery charge/discharge (UPSD_BAD_DISCHARGE) */ #define UPSD_DS_BAT_VOLTS 3 /* battery volts */ #define UPSD_DS_BAT_TEMP 4 /* battery temperature */ #define UPSD_DS_BAT_CHARGE 5 /* battery charge */ #define UPSD_DS_IN_FREQ 6 /* input frequency */ #define UPSD_DS_IN_VOLTS 7 /* input voltage */ #define UPSD_DS_OUT_FROM 8 /* output from (UPSD_OUT_INVERTER) */ #define UPSD_DS_OUT_FREQ 9 /* output frequency */ #define UPSD_DS_OUT_VOLTS 10 /* output voltage */ #define UPSD_DS_OUT_LOAD 11 /* output load */ #define UPSD_DS_STATUS 12 /* status field (UPSD_ST_...) */ #define UPSD_DS_NUMFIELDS 13 /* number of fields */ #define UPSD_DS_STRINGS {"model","battery-condition","battery-is","battery-voltage","battery-temperature",\ "battery-charge","input-frequency","input-voltage","output-from","output-frequency",\ "output-voltage","output-load","status-field",NULL} typedef struct TAG_openupsd_ds_t { char model_name[32]; /* NULL terminated model name */ unsigned int bat_flags; /* UPSD_BAT_.. battery status */ int x_bvolts; /* battery volts * 10 */ int btemp, bcharge; /* battery temperature (deg C) and charge (percent) */ int x_ifreq, x_ivolts; /* input frequency * 10 and voltage * 10 */ int x_ofreq, x_ovolts; /* output frequency * 10 and voltage * 10 */ unsigned int out_flags; /* UPSD_OUT_.. output status (only one thing atm) */ int out_load; /* output load (percent) */ unsigned int st_flags; /* UPSD_ST_.. status flags */ char *devname; /* pointer to the device name (inside an openupsd_sdev_t or openupsd_netcli_t) */ } openupsd_ds_t; #define UPSD_ALARM_POLL 1 /* poll the device */ #define UPSD_ALARM_RECONNECT 2 /* attempt (outgoing) client reconnection */ #define UPSD_ALARM_MAXINT 3 /* for deciding whether internal/external alarm */ #define UPSD_ACTION_EXEC 1 /* execute something */ #define UPSD_ACTION_LOG 2 /* log something */ #define UPSD_CMP_EQ 1 #define UPSD_CMP_NE 2 #define UPSD_CMP_LT 3 #define UPSD_CMP_LE 4 #define UPSD_CMP_GT 5 #define UPSD_CMP_GE 6 struct TAG_openupsd_trigger_t; /* forward */ struct TAG_openupsd_alarm_t; /* forward */ typedef struct TAG_openupsd_inv_t { struct TAG_openupsd_inv_t *next, *prev; /* prev/next in the invalidators list */ struct TAG_openupsd_trigger_t *when; /* when this one occurs */ struct TAG_openupsd_trigger_t *trash; /* which one to trash */ } openupsd_inv_t; typedef struct TAG_openupsd_trigger_t { struct TAG_openupsd_trigger_t *next, *prev; /* prev/next in the triggers list */ char *name; /* smalloc()d (user) name of trigger */ int trig; /* UPSD_DS_.. field involved */ int comp; /* UPSD_CMP_.. comparison involved */ void *rhs; /* what's being compared -- this will either be an (int) or a smalloc()d (char *), depending on the field */ DYNARRAY(openupsd_inv_t *,inv); /* invalidators for this alarm */ } openupsd_trigger_t; typedef struct { int pid; /* PID of process */ int out_fd; /* output file-descriptor */ char outbuf[256]; /* output buffer (to collect lines in) */ int bytesout; /* number of bytes in buffer */ } openupsd_eenv_t; typedef struct TAG_openupsd_exec_t { struct TAG_openupsd_exec_t *next, *prev; /* prev/next when on the "running" list */ char *path_to_run; /* path to executable */ DYNARRAY(char*, args); /* arguments (including path first) */ struct TAG_openupsd_alarm_t *alarm; /* alarm with which this is associated */ openupsd_eenv_t *env; /* environment (fds, etc.) associated with running process */ } openupsd_exec_t; typedef struct TAG_openupsd_alarm_t { struct TAG_openupsd_alarm_t *next, *prev; /* prev/next in the (time-sorted) queue */ time_t time; /* time this goes off at */ openupsd_trigger_t *alarm; /* trigger that sets this off */ int action; /* UPSD_ACTION_.. indicator */ void *xdata; /* links to serial device for internal POLL alarm, to netcli device for internal RECONNECT alarm, or to openupsd_exec_t for ACTION_EXEC */ char *devname; /* for the action-queue only -- the device that generated this */ int initial; /* whether this alarm should be generated initially (only meaningful for static alarms) */ } openupsd_alarm_t; /*}}}*/ /*{{{ text-output file info*/ typedef struct TAG_openupsd_ofile_t { struct TAG_openupsd_ofile_t *next, *prev; /* prev/next in the output file list */ char *fname; /* smalloc()'d output file name */ } openupsd_ofile_t; /*}}}*/ /*{{{ networking support structs.*/ typedef struct { unsigned long allow_net, allow_mask; /* network byte-order network and netmask */ } openupsd_netnet_t; typedef struct { struct sockaddr_in sin; /* the remote address */ int fd; /* file-descriptor of remote client */ char *outbuf; /* output buffer */ int bufsize; /* buffer size (needed by srealloc) */ int left; /* amount still to send */ int gone; /* amount already gone */ } openupsd_rclient_t; typedef struct TAG_openupsd_netsvr_t { struct TAG_openupsd_netsvr_t *next, *prev; /* prev/next in the net-server list */ struct sockaddr_in listen_host; /* listen for connections on this address/port */ int fd; /* server socket */ DYNARRAY(openupsd_netnet_t*, allow); /* array of networks/netmasks to explicitly allow connections from */ DYNARRAY(openupsd_netnet_t*, disallow); /* array of networks/netmasks to explicitly deny connections from */ DYNARRAY(openupsd_rclient_t*, clients); /* array of remotely connected clients */ } openupsd_netsvr_t; #define UPSD_NETCLI_INACTIVE 0 #define UPSD_NETCLI_CONNECTING 1 #define UPSD_NETCLI_CONNECTED 2 typedef struct TAG_openupsd_netcli_t { struct TAG_openupsd_netcli_t *next, *prev; /* prev/next in the net-client list */ char *name; /* name associated with this */ int fd; /* client socket */ int state; /* client state */ time_t retry; /* seconds between retries (defaults to 60) */ struct sockaddr_in ups_host; /* host/port the client connects to (TCP) */ char *inbuf; /* input buffer */ int bufsize; /* input buffer size */ int inbytes; /* number of bytes in buffer */ DYNARRAY(openupsd_ofile_t*, outfiles); /* array of output files for this remote device */ DYNARRAY(openupsd_netsvr_t*, outtcpsvrs); /* array of output servers for re-notify */ DYNARRAY(openupsd_alarm_t*, alarms); /* array of alarms for this */ DYNARRAY(int, triggered); /* array that follows "alarms" indicating which ones are currently active */ } openupsd_netcli_t; /*}}}*/ /*{{{ serial device info*/ typedef struct TAG_openupsd_sdev_t { struct TAG_openupsd_sdev_t *next, *prev; /* prev/next in the device list */ char *name; /* smalloc()'d user-specified name for the device */ char *device; /* smalloc()'d "/dev/tty.." */ int fd; /* descriptor */ int inter_poll_sec; /* seconds between polls for data */ int s_baud; /* baud rate */ int s_data, s_stop; /* data and stop bit counts */ char s_parity; /* parity 'N', 'E', 'O', 'M' or 'S' (none, even, odd, mark, space) */ struct termios saved_state; /* saved state of the serial device */ DYNARRAY(openupsd_ofile_t*, outfiles); /* array of output files for this device */ DYNARRAY(openupsd_netsvr_t*, outtcpsvrs); /* array of output servers for re-notify */ DYNARRAY(openupsd_alarm_t*, alarms); /* array of alarms for this */ DYNARRAY(int, triggered); /* array that follows "alarms" indicating which ones are currently active */ } openupsd_sdev_t; /*}}}*/ /*{{{ openupsd_t struct*/ typedef struct { openupsd_sdev_t *sdev; /* serial devices */ openupsd_netcli_t *netcli; /* network client list */ openupsd_netsvr_t *netsvr; /* network server list (for listening for connections) */ openupsd_ofile_t *outfiles; /* list of all output files */ char *conffile; /* config file (might be NULL) */ int verbose; /* be verbose ? */ int daemonise; /* become a daemon ? */ #ifdef SUPPORT_SYSLOG int use_syslog; /* use syslog for messages ? */ #endif char *logfilename; /* smalloc()'d name of a logfile, if one was specified */ FILE *logfile; /* otherwise we might have been told to use some log file somewhere else (NULL if syslog/none)*/ char *pidfilename; /* smalloc()'d name of a pidfile, if one was specified */ openupsd_alarm_t *salarms; /* "static" alarms (user config) */ openupsd_alarm_t *aalarms; /* "active" alarms (things that will happen soon) */ openupsd_trigger_t *trigs; /* list of all triggers */ openupsd_inv_t *invds; /* list of all invalidators */ openupsd_exec_t *proclist; /* list of currently running programs (waiting for termination) */ } openupsd_t; /*}}}*/ /*{{{ external decls*/ extern char *progname; /* program name minus leading path (points in argv) */ /* note: use LOG_{INFO,DEBUG,...} for `urgency' below */ extern int parse_config (openupsd_t *upsinfo, FILE *errstream); /* cfg.c */ extern void openupsd_log (openupsd_t *upsinfo, int urgency, const char *fmt, ...); /* openupsd.c */ /*}}}*/ #endif /* !__OPENUPSD_H */