As we want the user to be able do issue all shutdown methods manually,
adjust sdcmd_*() to use STAT_INSTCMD_{HANDLED,FAILED}, so they can
be used directly.

Also minor text corrections, and APC specific command renames.

Signed-off-by: Michal Soltys <[email protected]>
---
 drivers/apcsmart.c |   75 ++++++++++++++++++++++++++++++++++------------------
 drivers/apcsmart.h |    5 +++-
 2 files changed, 53 insertions(+), 27 deletions(-)

diff --git a/drivers/apcsmart.c b/drivers/apcsmart.c
index 70aebfc..7f3c575 100644
--- a/drivers/apcsmart.c
+++ b/drivers/apcsmart.c
@@ -835,11 +835,11 @@ static int sdok(void)
 
        if (!strcmp(temp, "*") || !strcmp(temp, "OK")) {
                upsdebugx(4, "Last issued shutdown command succeeded");
-               return 1;
+               return STAT_INSTCMD_HANDLED;
        }
 
        upsdebugx(1, "Last issued shutdown command failed");
-       return 0;
+       return STAT_INSTCMD_FAILED;
 }
 
 /* soft hibernate: S - working only when OB, otherwise ignored */
@@ -864,7 +864,7 @@ static int sdcmd_CS(int status)
                ser_send_char(upsfd, 'U');
                ser_get_line(upsfd, temp, sizeof(temp), ENDCHAR, IGNCHARS, 
SER_WAIT_SEC, SER_WAIT_USEC);
        }
-       return sdcmd_S(tval);
+       return sdcmd_S(0);
 }
 
 /*
@@ -897,7 +897,7 @@ static int sdcmd_ATn(int cnt)
        ser_send_pace(upsfd, UPSDELAY, temp);
 
        ret = sdok();
-       if (ret || cnt == 3)
+       if (ret == STAT_INSTCMD_HANDLED || cnt == 3)
                return ret;
 
        /*
@@ -998,7 +998,7 @@ static void upsdrv_shutdown_simple(int status)
                        (status & APC_STAT_OL) ? "on-line" : "on battery");
 
                /* S works only when OB */
-               if ((status & APC_STAT_OB) && sdcmd_S(0))
+               if ((status & APC_STAT_OB) && sdcmd_S(0) == 
STAT_INSTCMD_HANDLED)
                        break;
                sdcmd_ATn(3);
                break;
@@ -1051,7 +1051,7 @@ static void upsdrv_shutdown_advanced(int status)
                } else if (strval[i] - 48 == SDIDX_AT2N) {
                        n = 2;
                }
-               if (sdlist[strval[i] - 48](n))
+               if (sdlist[strval[i] - 48](n) == STAT_INSTCMD_HANDLED)
                        break;  /* finish if command succeeded */
        }
 }
@@ -1343,7 +1343,7 @@ static int do_cmd(apc_cmdtab_t *ct)
 
        if (ret != 1) {
                upslog_with_errno(LOG_ERR, "do_cmd: ser_send_char failed");
-               return STAT_INSTCMD_HANDLED;            /* FUTURE: failed */
+               return STAT_INSTCMD_FAILED;
        }
 
        /* some commands have to be sent twice with a 1.5s gap */
@@ -1354,24 +1354,24 @@ static int do_cmd(apc_cmdtab_t *ct)
 
                if (ret != 1) {
                        upslog_with_errno(LOG_ERR, "do_cmd: ser_send_char 
failed");
-                       return STAT_INSTCMD_HANDLED;    /* FUTURE: failed */
+                       return STAT_INSTCMD_FAILED;
                }
        }
 
        ret = read_buf(buf, sizeof(buf));
 
        if (ret < 1)
-               return STAT_INSTCMD_HANDLED;            /* FUTURE: failed */
+               return STAT_INSTCMD_FAILED;
 
-       if (strcmp(buf, "OK") != 0) {
+       if (strcmp(buf, "OK") != 0 && strcmp(buf, "*") != 0) {
                upslogx(LOG_WARNING, "Got [%s] after command [%s]",
                        buf, ct->name);
 
-               return STAT_INSTCMD_HANDLED;            /* FUTURE: failed */
+               return STAT_INSTCMD_FAILED;
        }
 
        upslogx(LOG_INFO, "Command: %s", ct->name);
-       return STAT_INSTCMD_HANDLED;                    /* FUTURE: success */
+       return STAT_INSTCMD_HANDLED;
 }
 
 /* some commands must be repeated in a window to execute */
@@ -1390,10 +1390,10 @@ static int instcmd_chktime(apc_cmdtab_t *ct)
        if ((elapsed < MINCMDTIME) || (elapsed > MAXCMDTIME)) {
                upsdebugx(1, "instcmd_chktime: outside window for %s (%2.0f)",
                                ct->name, elapsed);
-               return STAT_INSTCMD_HANDLED;            /* FUTURE: again */
+               return 0;
        }
 
-       return do_cmd(ct);
+       return 1;
 }
 
 static int instcmd(const char *cmdname, const char *extra)
@@ -1424,10 +1424,33 @@ static int instcmd(const char *cmdname, const char 
*extra)
        if (!strcasecmp(cmdname, "calibrate.stop"))
                return do_cal(0);
 
-       if (ct->flags & APC_NASTY)
-               return instcmd_chktime(ct);
+       /* standard non-APC_NASTY command */
+       if (!(ct->flags & APC_NASTY))
+               return do_cmd(ct);
+
+       /* APC_NASTY barrier */
+       if (!instcmd_chktime(ct))
+               return STAT_INSTCMD_FAILED;             /* FUTURE: again */
+
+       if (!strcasecmp(cmdname, "load.off"))
+               return sdcmd_Z(0);
+
+       if (!strcasecmp(cmdname, "shutdown.stayoff"))
+               return sdcmd_K(0);
+
+       if (!strcasecmp(cmdname, "shutdown.return"))
+               return sdcmd_S(0);
+
+       if (!strcasecmp(cmdname, "shutdown.return.cs"))
+               return sdcmd_CS(ups_status);
+
+       if (!strcasecmp(cmdname, "shutdown.return.awd"))
+               return sdcmd_ATn(3);
+
+       if (!strcasecmp(cmdname, "shutdown.return.awd.h"))
+               return sdcmd_ATn(2);
 
-       /* nothing special here */
+       /* standard APC_NASTY command */
        return do_cmd(ct);
 }      
 
@@ -1443,7 +1466,7 @@ static void setuphandlers(void)
 void upsdrv_makevartable(void)
 {
        addvar(VAR_VALUE, "cable", "Specify alternate cable (940-0095B)");
-       addvar(VAR_VALUE, "wugrace", "Hard hibernate's wakeup grace");
+       addvar(VAR_VALUE, "awd", "Additional wakeup delay for hard hibernate 
command");
        addvar(VAR_VALUE, "sdtype", "Specify simple shutdown method (0-6)");
        addvar(VAR_VALUE, "advorder", "Enable advanced shutdown control");
 }
@@ -1475,8 +1498,8 @@ void upsdrv_help(void)
        "  advorder:\n"
        "    see \"Advanced shutdown control\" below for details\n\n"
 
-       "  wugrace:\n"
-       "    Additional grace period used with 'hard hibernate' shutdown 
command.\n"
+       "  awd:\n"
+       "    Additional wakeup delay used with \"hard hibernate\" shutdown 
command.\n"
        "    The value is in 6 minute units and its acceptable range is 0 - 
999.\n"
        "    If the value is invalid or out of range, it's assumed to be 0.\n"
        "    \"nn hack\" version of the command expects 0 - 99 range.\n\n"
@@ -1492,7 +1515,7 @@ void upsdrv_help(void)
 
        "    On older models (usually w/o programmable eeprom), the ups will 
power up\n"
        "    immediately after the power returns. On such models, it's safer to 
use\n"
-       "    'hard hibernate'. YMMV, depending on the ups model and firmware\n"
+       "    \"hard hibernate\". YMMV, depending on the ups model and 
firmware\n"
        "    revision.\n\n"
 
        "  hard hibernate:\n"
@@ -1500,8 +1523,8 @@ void upsdrv_help(void)
        "    after the eeprom defined grace period. The ups will wake up when 
the\n"
        "    power returns, after the eeprom defined delay + 6*n AND if the 
eeprom\n"
        "    defined min. battery charge level is met. The delay is counted 
from the\n"
-       "    power's return. Value 'n' is in 6 minute units, and can be 
provided by\n"
-       "    the user.\n\n"
+       "    power's return. Value \"n\" is in 6 minute units, and can be 
provided by\n"
+       "    the user (see \"awd\" option).\n\n"
 
        "    On older models (usually w/o programmable eeprom), the ups will 
power up\n"
        "    after 6*n minutes, often regardless it the power returned on not. 
YMMV,\n"
@@ -1516,7 +1539,7 @@ void upsdrv_help(void)
        "    user's intervention.\n\n"
 
        "  CS 350 hack:\n"
-       "    The same as 'soft hibernate', but first the ups is forced to go 
into OB\n"
+       "    The same as \"soft hibernate\", but first the ups is forced to go 
into OB\n"
        "    state.\n\n"
 
        "Simple shutdown method:\n\n"
@@ -1529,7 +1552,7 @@ void upsdrv_help(void)
        "    5: \"hack nn\" hard hibernate only\n"
        "    6: hard hibernate only\n\n"
 
-       "  User should provide requested method in 'sdtype'. The default is 
0.\n\n"
+       "  User should provide requested method in \"sdtype\". The default is 
0.\n\n"
 
        "Advanced shutdown control:\n\n"
 
@@ -1540,7 +1563,7 @@ void upsdrv_help(void)
        "    4: \"force OB\" hack method for CS 350\n"
        "    5: \"nn hack\" hard hibernate\n\n"
 
-       "  User should set the 'advorder' option and provide the list of the 
methods.\n"
+       "  User should set the \"advorder\" option and provide the list of the 
methods.\n"
        "  The methods are tried in order, until one of them succeedes.\n"
        "  If the list is too long or contains invalid characters, it will 
fallback to\n"
        "  the default - 0123. You can also use \"no\" to explicitly ignore it 
and use\n"
diff --git a/drivers/apcsmart.h b/drivers/apcsmart.h
index 9862326..6c4df52 100644
--- a/drivers/apcsmart.h
+++ b/drivers/apcsmart.h
@@ -235,9 +235,12 @@ apc_cmdtab_t       apc_cmdtab[] =
        { "test.battery.start", 0,                      APC_CMD_BTESTTOGGLE },
        { "test.battery.stop",  0,                      APC_CMD_BTESTTOGGLE },
 
-       { "shutdown.return.grace",
+       { "shutdown.return.awd",APC_NASTY,              APC_CMD_GRACEDOWN  },
+       { "shutdown.return.awd.h",
                                APC_NASTY,              APC_CMD_GRACEDOWN  },
        { "shutdown.return",    APC_NASTY,              APC_CMD_SOFTDOWN  },
+       { "shutdown.return.cs",
+                               APC_NASTY,              APC_CMD_SOFTDOWN  },
        { "shutdown.stayoff",   APC_NASTY|APC_REPEAT,   APC_CMD_SHUTDOWN  },
 
        { "calibrate.start",    0,                      APC_CMD_CALTOGGLE },
-- 
1.7.2.1


_______________________________________________
Nut-upsdev mailing list
[email protected]
http://lists.alioth.debian.org/mailman/listinfo/nut-upsdev

Reply via email to