Lines 25-34
Link Here
|
25 |
#include "main.h" |
25 |
#include "main.h" |
26 |
#include "serial.h" |
26 |
#include "serial.h" |
27 |
#include "megatec.h" |
27 |
#include "megatec.h" |
|
|
28 |
#include "timehead.h" |
28 |
|
29 |
|
29 |
#include <stdio.h> |
30 |
#include <stdio.h> |
30 |
#include <limits.h> |
31 |
#include <limits.h> |
31 |
#include <string.h> |
32 |
#include <string.h> |
|
|
33 |
#include <ctype.h> |
32 |
|
34 |
|
33 |
|
35 |
|
34 |
#define ENDCHAR '\r' |
36 |
#define ENDCHAR '\r' |
Lines 49-58
Link Here
|
49 |
|
51 |
|
50 |
#define MAX_START_DELAY 9999 |
52 |
#define MAX_START_DELAY 9999 |
51 |
#define MAX_SHUTDOWN_DELAY 99 |
53 |
#define MAX_SHUTDOWN_DELAY 99 |
|
|
54 |
#define MAX_REPEAT_DELAY 15000 |
52 |
|
55 |
|
53 |
/* Maximum length of a string representing these values */ |
56 |
/* Maximum length of a string representing these values */ |
54 |
#define MAX_START_DELAY_LEN 4 |
57 |
#define MAX_START_DELAY_LEN 4 |
55 |
#define MAX_SHUTDOWN_DELAY_LEN 2 |
58 |
#define MAX_SHUTDOWN_DELAY_LEN 2 |
|
|
59 |
#define MAX_REPEAT_DELAY_LEN 5 |
56 |
|
60 |
|
57 |
#define N_FLAGS 8 |
61 |
#define N_FLAGS 8 |
58 |
|
62 |
|
Lines 130-136
Link Here
|
130 |
|
134 |
|
131 |
/* In minutes: */ |
135 |
/* In minutes: */ |
132 |
static short start_delay = 2; /* wait this amount of time to come back online */ |
136 |
static short start_delay = 2; /* wait this amount of time to come back online */ |
133 |
static short shutdown_delay = 0; /* wait until going offline */ |
137 |
static unsigned char shutdown_delay[3] = ".2"; /* wait until going offline */ |
|
|
138 |
|
139 |
/* In milliseconds: */ |
140 |
static short off_cmd_repeat = 0; /* wait this amount of time to repeat off/shutdown command */ |
134 |
|
141 |
|
135 |
/* In percentage: */ |
142 |
/* In percentage: */ |
136 |
static float lowbatt = -1; /* disabled */ |
143 |
static float lowbatt = -1; /* disabled */ |
Lines 412-418
Link Here
|
412 |
} |
419 |
} |
413 |
|
420 |
|
414 |
if (getval("offdelay")) { |
421 |
if (getval("offdelay")) { |
415 |
shutdown_delay = CLAMP(atoi(getval("offdelay")), 0, MAX_SHUTDOWN_DELAY); |
422 |
shutdown_delay[2] = '\0'; |
|
|
423 |
strncpy(shutdown_delay, getval("offdelay"), 2); |
424 |
if (shutdown_delay[0] == '\0') { |
425 |
shutdown_delay[0] = '.'; |
426 |
shutdown_delay[1] = '2'; |
427 |
} else if (shutdown_delay[0] != '.') { |
428 |
i = CLAMP(atoi(shutdown_delay), 0, MAX_SHUTDOWN_DELAY); |
429 |
snprintf(shutdown_delay, 2, "%02d", i); |
430 |
} else if (shutdown_delay[1] == '\0') { |
431 |
shutdown_delay[1] = '2'; |
432 |
} |
433 |
} |
434 |
|
435 |
if (getval("cmdrepeat")) { |
436 |
off_cmd_repeat = CLAMP(atoi(getval("cmdrepeat")), 0, MAX_REPEAT_DELAY); |
416 |
} |
437 |
} |
417 |
|
438 |
|
418 |
/* |
439 |
/* |
Lines 422-431
Link Here
|
422 |
dstate_setflags("ups.delay.start", ST_FLAG_RW | ST_FLAG_STRING); |
443 |
dstate_setflags("ups.delay.start", ST_FLAG_RW | ST_FLAG_STRING); |
423 |
dstate_setaux("ups.delay.start", MAX_START_DELAY_LEN); |
444 |
dstate_setaux("ups.delay.start", MAX_START_DELAY_LEN); |
424 |
|
445 |
|
425 |
dstate_setinfo("ups.delay.shutdown", "%d", shutdown_delay); |
446 |
dstate_setinfo("ups.delay.shutdown", "%s", shutdown_delay); |
426 |
dstate_setflags("ups.delay.shutdown", ST_FLAG_RW | ST_FLAG_STRING); |
447 |
dstate_setflags("ups.delay.shutdown", ST_FLAG_RW | ST_FLAG_STRING); |
427 |
dstate_setaux("ups.delay.shutdown", MAX_SHUTDOWN_DELAY_LEN); |
448 |
dstate_setaux("ups.delay.shutdown", MAX_SHUTDOWN_DELAY_LEN); |
428 |
|
449 |
|
|
|
450 |
dstate_setinfo("ups.delay.cmdrepeat", "%d", off_cmd_repeat); |
451 |
dstate_setflags("ups.delay.cmdrepeat", ST_FLAG_RW | ST_FLAG_STRING); |
452 |
dstate_setaux("ups.delay.cmdrepeat", MAX_REPEAT_DELAY_LEN); |
453 |
|
429 |
/* |
454 |
/* |
430 |
* Register the available instant commands. |
455 |
* Register the available instant commands. |
431 |
*/ |
456 |
*/ |
Lines 543-549
Link Here
|
543 |
upslogx(LOG_INFO, "Shutting down UPS immediately."); |
568 |
upslogx(LOG_INFO, "Shutting down UPS immediately."); |
544 |
|
569 |
|
545 |
ser_send_pace(upsfd, SEND_PACE, "C%c", ENDCHAR); |
570 |
ser_send_pace(upsfd, SEND_PACE, "C%c", ENDCHAR); |
546 |
ser_send_pace(upsfd, SEND_PACE, "S%02dR%04d%c", shutdown_delay, start_delay, ENDCHAR); |
571 |
ser_send_pace(upsfd, SEND_PACE, "S%.2sR%04d%c", shutdown_delay, start_delay, ENDCHAR); |
|
|
572 |
if (off_cmd_repeat > 0) { |
573 |
usleep(off_cmd_repeat * 1000); |
574 |
ser_send_pace(upsfd, SEND_PACE, "S%.2sR%04d%c", shutdown_delay, start_delay, ENDCHAR); |
575 |
} |
547 |
} |
576 |
} |
548 |
|
577 |
|
549 |
|
578 |
|
Lines 598-604
Link Here
|
598 |
ser_send_pace(upsfd, SEND_PACE, "C%c", ENDCHAR); |
627 |
ser_send_pace(upsfd, SEND_PACE, "C%c", ENDCHAR); |
599 |
watchdog_enabled = 0; |
628 |
watchdog_enabled = 0; |
600 |
|
629 |
|
601 |
ser_send_pace(upsfd, SEND_PACE, "S%02dR%04d%c", shutdown_delay, start_delay, ENDCHAR); |
630 |
ser_send_pace(upsfd, SEND_PACE, "S%.2sR%04d%c", shutdown_delay, start_delay, ENDCHAR); |
|
|
631 |
if (off_cmd_repeat > 0) { |
632 |
usleep(off_cmd_repeat * 1000); |
633 |
ser_send_pace(upsfd, SEND_PACE, "S%.2sR%04d%c", shutdown_delay, start_delay, ENDCHAR); |
634 |
} |
602 |
|
635 |
|
603 |
upslogx(LOG_INFO, "Shutdown (return) initiated."); |
636 |
upslogx(LOG_INFO, "Shutdown (return) initiated."); |
604 |
|
637 |
|
Lines 609-615
Link Here
|
609 |
ser_send_pace(upsfd, SEND_PACE, "C%c", ENDCHAR); |
642 |
ser_send_pace(upsfd, SEND_PACE, "C%c", ENDCHAR); |
610 |
watchdog_enabled = 0; |
643 |
watchdog_enabled = 0; |
611 |
|
644 |
|
612 |
ser_send_pace(upsfd, SEND_PACE, "S%02dR0000%c", shutdown_delay, ENDCHAR); |
645 |
ser_send_pace(upsfd, SEND_PACE, "S%.2sR0000%c", shutdown_delay, ENDCHAR); |
|
|
646 |
if (off_cmd_repeat > 0) { |
647 |
usleep(off_cmd_repeat * 1000); |
648 |
ser_send_pace(upsfd, SEND_PACE, "S%.2sR0000%c", shutdown_delay, ENDCHAR); |
649 |
} |
613 |
|
650 |
|
614 |
upslogx(LOG_INFO, "Shutdown (stayoff) initiated."); |
651 |
upslogx(LOG_INFO, "Shutdown (stayoff) initiated."); |
615 |
|
652 |
|
Lines 639-644
Link Here
|
639 |
watchdog_enabled = 0; |
676 |
watchdog_enabled = 0; |
640 |
|
677 |
|
641 |
ser_send_pace(upsfd, SEND_PACE, "S00R0000%c", ENDCHAR); |
678 |
ser_send_pace(upsfd, SEND_PACE, "S00R0000%c", ENDCHAR); |
|
|
679 |
if (off_cmd_repeat > 0) { |
680 |
usleep(off_cmd_repeat * 1000); |
681 |
ser_send_pace(upsfd, SEND_PACE, "S00R0000%c", ENDCHAR); |
682 |
} |
642 |
|
683 |
|
643 |
upslogx(LOG_INFO, "Turning load off."); |
684 |
upslogx(LOG_INFO, "Turning load off."); |
644 |
|
685 |
|
Lines 688-699
Link Here
|
688 |
int setvar(const char *varname, const char *val) |
729 |
int setvar(const char *varname, const char *val) |
689 |
{ |
730 |
{ |
690 |
int delay; |
731 |
int delay; |
|
|
732 |
int i; |
691 |
|
733 |
|
692 |
if (sscanf(val, "%d", &delay) != 1) { |
734 |
i = sscanf(val, "%d", &delay); |
693 |
return STAT_SET_UNKNOWN; |
|
|
694 |
} |
695 |
|
735 |
|
696 |
if (strcasecmp(varname, "ups.delay.start") == 0) { |
736 |
if (strcasecmp(varname, "ups.delay.start") == 0) { |
|
|
737 |
if (i != 1) { |
738 |
return STAT_SET_UNKNOWN; |
739 |
} |
697 |
delay = CLAMP(delay, 0, MAX_START_DELAY); |
740 |
delay = CLAMP(delay, 0, MAX_START_DELAY); |
698 |
start_delay = delay; |
741 |
start_delay = delay; |
699 |
dstate_setinfo("ups.delay.start", "%d", delay); |
742 |
dstate_setinfo("ups.delay.start", "%d", delay); |
Lines 704-712
Link Here
|
704 |
} |
747 |
} |
705 |
|
748 |
|
706 |
if (strcasecmp(varname, "ups.delay.shutdown") == 0) { |
749 |
if (strcasecmp(varname, "ups.delay.shutdown") == 0) { |
707 |
delay = CLAMP(delay, 0, MAX_SHUTDOWN_DELAY); |
750 |
if (!val || !val[0]) { |
708 |
shutdown_delay = delay; |
751 |
return STAT_SET_UNKNOWN; |
709 |
dstate_setinfo("ups.delay.shutdown", "%d", delay); |
752 |
} |
|
|
753 |
if (val[0] != '.' ) { |
754 |
if (i != 1) { |
755 |
return STAT_SET_UNKNOWN; |
756 |
} |
757 |
delay = CLAMP(delay, 0, MAX_SHUTDOWN_DELAY); |
758 |
snprintf(shutdown_delay, 2, "%02d", delay); |
759 |
} else { |
760 |
i = val[1]; |
761 |
if (!isdigit(i)) { |
762 |
return STAT_SET_UNKNOWN; |
763 |
} |
764 |
strncpy(shutdown_delay, val, 2); |
765 |
} |
766 |
shutdown_delay[2] = '\0'; |
767 |
dstate_setinfo("ups.delay.shutdown", "%s", shutdown_delay); |
768 |
|
769 |
dstate_dataok(); |
770 |
|
771 |
return STAT_SET_HANDLED; |
772 |
} |
773 |
|
774 |
if (strcasecmp(varname, "ups.delay.cmdrepeat") == 0) { |
775 |
if (i != 1) { |
776 |
return STAT_SET_UNKNOWN; |
777 |
} |
778 |
delay = CLAMP(delay, 0, MAX_REPEAT_DELAY); |
779 |
off_cmd_repeat = delay; |
780 |
dstate_setinfo("ups.delay.cmdrepeat", "%d", delay); |
710 |
|
781 |
|
711 |
dstate_dataok(); |
782 |
dstate_dataok(); |
712 |
|
783 |
|
Lines 730-735
Link Here
|
730 |
addvar(VAR_VALUE, "lowbatt", "Low battery level (%)"); |
801 |
addvar(VAR_VALUE, "lowbatt", "Low battery level (%)"); |
731 |
addvar(VAR_VALUE, "ondelay", "Delay before UPS startup (minutes)"); |
802 |
addvar(VAR_VALUE, "ondelay", "Delay before UPS startup (minutes)"); |
732 |
addvar(VAR_VALUE, "offdelay", "Delay before UPS shutdown (minutes)"); |
803 |
addvar(VAR_VALUE, "offdelay", "Delay before UPS shutdown (minutes)"); |
|
|
804 |
addvar(VAR_VALUE, "cmdrepeat", "Delay (msec) to repeat shutdown cmd"); |
733 |
} |
805 |
} |
734 |
|
806 |
|
735 |
|
807 |
|