Diff for /libaitcli/src/aitcli.c between versions 1.8.2.4 and 1.19.4.1

version 1.8.2.4, 2013/10/08 09:30:55 version 1.19.4.1, 2024/03/19 10:11:13
Line 12  terms: Line 12  terms:
 All of the documentation and software included in the ELWIX and AITNET  All of the documentation and software included in the ELWIX and AITNET
 Releases is copyrighted by ELWIX - Sofia/Bulgaria <info@elwix.org>  Releases is copyrighted by ELWIX - Sofia/Bulgaria <info@elwix.org>
   
Copyright 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013Copyright 2004 - 2022
         by Michael Pounov <misho@elwix.org>.  All rights reserved.          by Michael Pounov <misho@elwix.org>.  All rights reserved.
   
 Redistribution and use in source and binary forms, with or without  Redistribution and use in source and binary forms, with or without
Line 87  static inline void Line 87  static inline void
 clrscrEOL(linebuffer_t * __restrict buf)  clrscrEOL(linebuffer_t * __restrict buf)
 {  {
         register int i;          register int i;
           int ign __attribute__((unused));
   
         if (buf && buf->line_prompt) {          if (buf && buf->line_prompt) {
                write(buf->line_out, K_CR, 1);                ign = write(buf->line_out, K_CR, 1);
   
                 for (i = 0; i < buf->line_len; i++)                  for (i = 0; i < buf->line_len; i++)
                        write(buf->line_out, K_SPACE, 1);                        ign = write(buf->line_out, K_SPACE, 1);
         }          }
 }  }
   
 static inline void  static inline void
 printfEOL(linebuffer_t * __restrict buf, int len, int prompt)  printfEOL(linebuffer_t * __restrict buf, int len, int prompt)
 {  {
           int ign __attribute__((unused));
   
         if (buf) {          if (buf) {
                 if (prompt && buf->line_prompt) {                  if (prompt && buf->line_prompt) {
                        write(buf->line_out, K_CR, 1);                        ign = write(buf->line_out, K_CR, 1);
                        write(buf->line_out, buf->line_prompt, buf->line_bol);                        ign = write(buf->line_out, buf->line_prompt, buf->line_bol);
                 }                  }
   
                write(buf->line_out, buf->line_buf, len == -1 ?                 ign = write(buf->line_out, buf->line_buf, len == -1 ? 
                                buf->line_eol - buf->line_bol: len);                                buf->line_eol - buf->line_bol : len);
         }          }
 }  }
   
 static inline void  static inline void
 printfCR(linebuffer_t * __restrict buf, int prompt)  printfCR(linebuffer_t * __restrict buf, int prompt)
 {  {
           int ign __attribute__((unused));
   
         if (buf && prompt && buf->line_prompt) {          if (buf && prompt && buf->line_prompt) {
                write(buf->line_out, K_CR, 1);                ign = write(buf->line_out, K_CR, 1);
                write(buf->line_out, buf->line_prompt, buf->line_bol);                ign = write(buf->line_out, buf->line_prompt, buf->line_bol);
         }          }
 }  }
   
 static inline void  static inline void
 printfNL(linebuffer_t * __restrict buf, int prompt)  printfNL(linebuffer_t * __restrict buf, int prompt)
 {  {
           int ign __attribute__((unused));
   
         if (buf) {          if (buf) {
                write(buf->line_out, K_ENTER, 1);                ign = write(buf->line_out, K_ENTER, 1);
   
                 if (prompt)                  if (prompt)
                         if (prompt && buf->line_prompt)                          if (prompt && buf->line_prompt)
                                write(buf->line_out, buf->line_prompt, buf->line_bol);                                ign = write(buf->line_out, buf->line_prompt, buf->line_bol);
         }          }
 }  }
   
Line 138  bufCHAR(int idx, void * __restrict cli_buffer) Line 145  bufCHAR(int idx, void * __restrict cli_buffer)
 {  {
         linebuffer_t *buf = cli_buffer;          linebuffer_t *buf = cli_buffer;
         int pos;          int pos;
           int ign __attribute__((unused));
   
         if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)          if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)
                 return RETCODE_ERR;                  return RETCODE_ERR;
Line 154  bufCHAR(int idx, void * __restrict cli_buffer) Line 162  bufCHAR(int idx, void * __restrict cli_buffer)
         memcpy(buf->line_buf + pos, buf->line_keys[idx].key_ch, buf->line_keys[idx].key_len);          memcpy(buf->line_buf + pos, buf->line_keys[idx].key_ch, buf->line_keys[idx].key_len);
         buf->line_buf[buf->line_len - 1] = 0;          buf->line_buf[buf->line_len - 1] = 0;
   
        write(buf->line_out, buf->line_keys[idx].key_ch, buf->line_keys[idx].key_len);        if (buf->line_prompt)
                 ign = write(buf->line_out, buf->line_keys[idx].key_ch, buf->line_keys[idx].key_len);
   
         if (buf->line_mode == LINEMODE_INS) {          if (buf->line_mode == LINEMODE_INS) {
                write(buf->line_out, (const u_char*) buf->line_buf + pos + buf->line_keys[idx].key_len,                 ign = write(buf->line_out, (const u_char*) buf->line_buf + pos + buf->line_keys[idx].key_len, 
                                 buf->line_len - buf->line_eol);                                  buf->line_len - buf->line_eol);
                 printfEOL(buf, -1, 1);                  printfEOL(buf, -1, 1);
         }          }
Line 403  bufComp(int idx, void * __restrict cli_buffer) Line 412  bufComp(int idx, void * __restrict cli_buffer)
         register int i, j;          register int i, j;
         struct tagCommand *cmd, *c;          struct tagCommand *cmd, *c;
         int pos, ret = RETCODE_OK;          int pos, ret = RETCODE_OK;
           int ign __attribute__((unused));
   
         if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)          if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)
                 return RETCODE_ERR;                  return RETCODE_ERR;
Line 426  bufComp(int idx, void * __restrict cli_buffer) Line 436  bufComp(int idx, void * __restrict cli_buffer)
   
                 if (i) {                  if (i) {
                         SLIST_FOREACH(cmd, &buf->line_cmds, cmd_next) {                          SLIST_FOREACH(cmd, &buf->line_cmds, cmd_next) {
                                if (cmd->cmd_level == buf->line_level &&                                 if (cmd->cmd_level & (1 << buf->line_level) && 
                                                 !strncmp(cmd->cmd_name, items[0],                                                   !strncmp(cmd->cmd_name, items[0], 
                                                         strlen(items[0]))) {                                                          strlen(items[0]))) {
                                         if (strncmp(cmd->cmd_name, CLI_CMD_SEP,                                           if (strncmp(cmd->cmd_name, CLI_CMD_SEP, 
Line 452  bufComp(int idx, void * __restrict cli_buffer) Line 462  bufComp(int idx, void * __restrict cli_buffer)
         } else {          } else {
                 /* we on 0 position of prompt, show commands for this level */                  /* we on 0 position of prompt, show commands for this level */
                 SLIST_FOREACH(cmd, &buf->line_cmds, cmd_next) {                  SLIST_FOREACH(cmd, &buf->line_cmds, cmd_next) {
                        if (cmd->cmd_level == buf->line_level)                        if (cmd->cmd_level & (1 << buf->line_level))
                                 if (strncmp(cmd->cmd_name, CLI_CMD_SEP, strlen(CLI_CMD_SEP))) {                                  if (strncmp(cmd->cmd_name, CLI_CMD_SEP, strlen(CLI_CMD_SEP))) {
                                         j++;                                          j++;
                                         c = cmd;                                          c = cmd;
Line 465  bufComp(int idx, void * __restrict cli_buffer) Line 475  bufComp(int idx, void * __restrict cli_buffer)
         /* completion show actions ... */          /* completion show actions ... */
         if (j > 1 && c) {          if (j > 1 && c) {
                 printfNL(buf, 0);                  printfNL(buf, 0);
                write(buf->line_out, szLine, strlen(szLine));                ign = write(buf->line_out, szLine, strlen(szLine));
                 printfNL(buf, 1);                  printfNL(buf, 1);
                 printfEOL(buf, buf->line_len - 1, 1);                  printfEOL(buf, buf->line_len - 1, 1);
                 printfEOL(buf, -1, 1);                  printfEOL(buf, -1, 1);
Line 499  bufHelp(int idx, void * __restrict cli_buffer) Line 509  bufHelp(int idx, void * __restrict cli_buffer)
         if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)          if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)
                 return RETCODE_ERR;                  return RETCODE_ERR;
   
        cli_Cmd_Help(buf, -1, NULL);        cli_Cmd_Help(buf, buf->line_level, NULL);
   
         printfEOL(buf, buf->line_len - 1, 1);          printfEOL(buf, buf->line_len - 1, 1);
         printfEOL(buf, -1, 1);          printfEOL(buf, -1, 1);
         return RETCODE_OK;          return RETCODE_OK;
 }  }
   
   static int
   bufEndNode(int idx, void * __restrict cli_buffer)
   {
           linebuffer_t *buf = cli_buffer;
   
           if (!cli_buffer || idx < 0 || idx > MAX_BINDKEY)
                   return RETCODE_ERR;
   
           if (buf->line_level > 0) {
                   printfNL(cli_buffer, 0);
                   buf->line_level--;
                   cli_Printf(buf, "Enter to config level %d\n", buf->line_level);
           }
   
           return bufCLR(idx, cli_buffer);
   }
   
   
 /*  /*
  * cli_Printf() - Send message to CLI session   * cli_Printf() - Send message to CLI session
  *   *
Line 586  cli_BindKey(bindkey_t * __restrict key, linebuffer_t * Line 613  cli_BindKey(bindkey_t * __restrict key, linebuffer_t *
  *   *
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
  * @csCmd = Command name   * @csCmd = Command name
 * @cliLevel = Level in CLI, -1 unprivi(view from all), 0 main config, 1 sub config ... * @cliLevel = Level in CLI, -1 view from all levels, 0 hidden, >0 mask levels
  * @funcCmd = Callback function when user call command   * @funcCmd = Callback function when user call command
  * @csInfo = Inline information for command   * @csInfo = Inline information for command
  * @csHelp = Help line when call help   * @csHelp = Help line when call help
Line 627  cli_addCommand(linebuffer_t * __restrict cli_buffer, c Line 654  cli_addCommand(linebuffer_t * __restrict cli_buffer, c
  *   *
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
  * @csCmd = Command name   * @csCmd = Command name
 * @cliLevel = Level in CLI, -1 unprivi(view from all), 0 main config, 1 sub config ... * @cliLevel = Level in CLI, -1 view from all levels, 0 hidden, >0 mask levels
  * return: RETCODE_ERR error, RETCODE_OK ok   * return: RETCODE_ERR error, RETCODE_OK ok
 */  */
 int  int
Line 657  cli_delCommand(linebuffer_t * __restrict cli_buffer, c Line 684  cli_delCommand(linebuffer_t * __restrict cli_buffer, c
  *   *
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
  * @csCmd = Command name   * @csCmd = Command name
 * @cliLevel = Level in CLI, -1 unprivi(view from all), 0 main config, 1 sub config ... * @cliLevel = Level in CLI, -1 view from all levels, 0 hidden, >0 mask levels
  * @funcCmd = Callback function when user call command   * @funcCmd = Callback function when user call command
  * @csInfo = Inline information for command   * @csInfo = Inline information for command
  * @csHelp = Help line when call help   * @csHelp = Help line when call help
Line 676  cli_updCommand(linebuffer_t * __restrict cli_buffer, c Line 703  cli_updCommand(linebuffer_t * __restrict cli_buffer, c
                 return RETCODE_ERR;                  return RETCODE_ERR;
         }          }
   
        SLIST_FOREACH(cmd, &cli_buffer->line_cmds, cmd_next)         SLIST_FOREACH(cmd, &cli_buffer->line_cmds, cmd_next)
                if (cmd->cmd_level == cliLevel && !strcmp(cmd->cmd_name, csCmd)) {                if ((!cmd->cmd_level || cmd->cmd_level == cliLevel) && 
                        ret = 1;                                !strcmp(cmd->cmd_name, csCmd)) {
                        if (!cmd->cmd_level)
                                 cmd->cmd_level = cliLevel;
                         if (funcCmd)                          if (funcCmd)
                                 cmd->cmd_func = funcCmd;                                  cmd->cmd_func = funcCmd;
                         if (csInfo)                          if (csInfo)
Line 959  cliInit(int fin, int fout, const char *prompt) Line 987  cliInit(int fin, int fout, const char *prompt)
         linebuffer_t *cli_buffer;          linebuffer_t *cli_buffer;
         bindkey_t *keys;          bindkey_t *keys;
         register int i;          register int i;
           char szPrompt[STRSIZ + 16] = {[0 ... STRSIZ + 15] = 0};
   
         /* init buffer */          /* init buffer */
         cli_buffer = e_malloc(sizeof(linebuffer_t));          cli_buffer = e_malloc(sizeof(linebuffer_t));
Line 975  cliInit(int fin, int fout, const char *prompt) Line 1004  cliInit(int fin, int fout, const char *prompt)
                 SLIST_INIT(&cli_buffer->line_cmds);                  SLIST_INIT(&cli_buffer->line_cmds);
   
                 if (prompt) {                  if (prompt) {
                        cli_buffer->line_prompt = e_strdup(prompt);                        strlcpy(cli_buffer->line_porigin, prompt, sizeof cli_buffer->line_porigin);
                         snprintf(szPrompt, sizeof szPrompt, "%s{%d}> ", cli_buffer->line_porigin, cli_buffer->line_level);
                         cli_buffer->line_prompt = e_strdup(szPrompt);
                         if (!cli_buffer->line_prompt) {                          if (!cli_buffer->line_prompt) {
                                 LOGERR;                                  LOGERR;
                                 e_free(cli_buffer);                                  e_free(cli_buffer);
Line 1009  cliInit(int fin, int fout, const char *prompt) Line 1040  cliInit(int fin, int fout, const char *prompt)
                 memset(keys, 0, sizeof(bindkey_t) * (MAX_BINDKEY + 1));                  memset(keys, 0, sizeof(bindkey_t) * (MAX_BINDKEY + 1));
   
         /* add helper functions */          /* add helper functions */
        cli_addCommand(cli_buffer, "exit", 0, cli_Cmd_Exit, "exit <cr>", "Exit from console");        cli_addCommand(cli_buffer, "exit", 1, cli_Cmd_Exit, "exit <cr>", "Exit from console");
        cli_addCommand(cli_buffer, "help", 0, cli_Cmd_Help, "help [command] <cr>", "Help screen");        cli_addCommand(cli_buffer, "help", -1, cli_Cmd_Help, "help [command] <cr>", "Help screen");
        cli_addCommand(cli_buffer, "-------", 0, NULL, "-------------------------", NULL);        cli_addCommand(cli_buffer, "-------", -1, NULL, "-------------------------", NULL);
         cli_addCommand(cli_buffer, "where", -1, cli_Cmd_WhereAmI, "where <cr>", 
                         "Query current level of console");
         cli_addCommand(cli_buffer, "top", -1, cli_Cmd_Top, "top <cr>", "Top level of console");
         cli_addCommand(cli_buffer, "end", -1, cli_Cmd_End, "end <cr>", "End level of console");
         cli_addCommand(cli_buffer, "config", -1, cli_Cmd_Config, "config <cr>", 
                         "Config next level of console");
         cli_addCommand(cli_buffer, "-------", -1, NULL, "-------------------------", NULL);
   
         /* fill key bindings */          /* fill key bindings */
         /* ascii chars & ctrl+chars */          /* ascii chars & ctrl+chars */
Line 1025  cliInit(int fin, int fout, const char *prompt) Line 1063  cliInit(int fin, int fout, const char *prompt)
                         keys[i].key_func = bufEOL;                          keys[i].key_func = bufEOL;
                 if (cli_buffer->line_prompt && (i == *K_CTRL_H || i == *K_BACKSPACE))                  if (cli_buffer->line_prompt && (i == *K_CTRL_H || i == *K_BACKSPACE))
                         keys[i].key_func = bufBS;                          keys[i].key_func = bufBS;
                if (cli_buffer->line_prompt && i == *K_CTRL_C)                if (i == *K_CTRL_C)
                         keys[i].key_func = bufCLR;                          keys[i].key_func = bufCLR;
                 if (cli_buffer->line_prompt && i == *K_CTRL_A)                  if (cli_buffer->line_prompt && i == *K_CTRL_A)
                         keys[i].key_func = bufBEGIN;                          keys[i].key_func = bufBEGIN;
Line 1033  cliInit(int fin, int fout, const char *prompt) Line 1071  cliInit(int fin, int fout, const char *prompt)
                         keys[i].key_func = bufEND;                          keys[i].key_func = bufEND;
                 if (cli_buffer->line_prompt && i == *K_TAB)                  if (cli_buffer->line_prompt && i == *K_TAB)
                         keys[i].key_func = bufComp;                          keys[i].key_func = bufComp;
                   if (i == *K_CTRL_Z)
                           keys[i].key_func = bufEndNode;
                 if (i >= *K_SPACE && i < *K_BACKSPACE)                  if (i >= *K_SPACE && i < *K_BACKSPACE)
                         keys[i].key_func = bufCHAR;                          keys[i].key_func = bufCHAR;
                 if (i > *K_BACKSPACE && i < 0xff)                  if (i > *K_BACKSPACE && i < 0xff)
Line 1215  cliInit(int fin, int fout, const char *prompt) Line 1255  cliInit(int fin, int fout, const char *prompt)
 }  }
   
 /*  /*
 * cliInitLine() - Init CLI input line terminal * cliSetLine() - Set CLI input line terminal
  *   *
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
 * return: none * @old = Old terminal settings
  * return: -1 error or 0 ok
 */  */
 int  int
cliInitLine(linebuffer_t * __restrict cli_buffer)cliSetLine(linebuffer_t * __restrict cli_buffer, struct termios * __restrict old)
 {  {
         struct termios t;          struct termios t;
   
         memset(&t, 0, sizeof t);          memset(&t, 0, sizeof t);
         tcgetattr(cli_buffer->line_in, &t);          tcgetattr(cli_buffer->line_in, &t);
           if (old)
                   memcpy(old, &t, sizeof(struct termios));
         t.c_lflag &= ~(ICANON | ISIG | IEXTEN | ECHO |           t.c_lflag &= ~(ICANON | ISIG | IEXTEN | ECHO | 
                         ECHOCTL | ECHOE | ECHOK | ECHOKE | ECHONL | ECHOPRT);                          ECHOCTL | ECHOE | ECHOK | ECHOKE | ECHONL | ECHOPRT);
         t.c_iflag |= IGNBRK;          t.c_iflag |= IGNBRK;
Line 1236  cliInitLine(linebuffer_t * __restrict cli_buffer) Line 1279  cliInitLine(linebuffer_t * __restrict cli_buffer)
 }  }
   
 /*  /*
    * cliResetLine() - Reset CLI input line terminal
    *
    * @cli_buffer = CLI buffer
    * @old = Original terminal settings
    * return: -1 error or 0 ok
   */
   int
   cliResetLine(linebuffer_t * __restrict cli_buffer, struct termios * __restrict orig)
   {
           return tcsetattr(cli_buffer->line_in, TCSANOW, orig);
   }
   
   /*
  * cliReadLine() - Read line from opened CLI session   * cliReadLine() - Read line from opened CLI session
  *   *
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
    * @timeout = Session timeout (-1 infinit)
  * return: NULL if error or !=NULL readed line, must be e_free after use!   * return: NULL if error or !=NULL readed line, must be e_free after use!
 */  */
 char *  char *
cliReadLine(linebuffer_t * __restrict cli_buffer)cliReadLine(linebuffer_t * __restrict cli_buffer, int timeout)
 {  {
        int code, readLen;        int code, readLen, ret;
         register int i;          register int i;
         struct pollfd fds;          struct pollfd fds;
         char buf[BUFSIZ], *str = NULL;          char buf[BUFSIZ], *str = NULL;
Line 1252  cliReadLine(linebuffer_t * __restrict cli_buffer) Line 1309  cliReadLine(linebuffer_t * __restrict cli_buffer)
         if (!cli_buffer) {          if (!cli_buffer) {
                 cli_SetErr(EINVAL, "Invalid input parameters ...");                  cli_SetErr(EINVAL, "Invalid input parameters ...");
                 return NULL;                  return NULL;
        }        } else if (timeout > 0)
                 timeout *= 1000;        /* convert from sec to ms */
   
         memset(&fds, 0, sizeof fds);          memset(&fds, 0, sizeof fds);
         fds.fd = cli_buffer->line_in;          fds.fd = cli_buffer->line_in;
Line 1260  cliReadLine(linebuffer_t * __restrict cli_buffer) Line 1318  cliReadLine(linebuffer_t * __restrict cli_buffer)
   
         printfCR(cli_buffer, 1);          printfCR(cli_buffer, 1);
         while (42) {          while (42) {
                if (poll(&fds, 1, -1) < 1) {                if ((ret = poll(&fds, 1, timeout)) < 1) {
                        LOGERR;                        if (!ret) {
                                 cli_buffer->line_kill = 1;
                                 if (str) {
                                         e_free(str);
                                         str = NULL;
                                 }
                         } else
                                 LOGERR;
                         return str;                          return str;
                 }                  }
   
                 memset(buf, 0, sizeof buf);                  memset(buf, 0, sizeof buf);
                 readLen = read(cli_buffer->line_in, buf, BUFSIZ);                  readLen = read(cli_buffer->line_in, buf, BUFSIZ);
                if (readLen == -1) {                if (readLen < 1) {
                        LOGERR;                        if (readLen)
                        return str;                                LOGERR;
                         return NULL;
                 }                  }
                 if (!readLen) {  
                         if (cli_buffer->line_buf)  
                                 str = e_strdup(cli_buffer->line_buf);  
                         else  
                                 cli_SetErr(EPIPE, "Unknown state ...");  
                         return str;  
                 }  
   
 recheck:  recheck:
                 for (code = RETCODE_OK, i = MAX_BINDKEY - 1; i > -1; i--)                  for (code = RETCODE_OK, i = MAX_BINDKEY - 1; i > -1; i--)
Line 1316  recheck: Line 1375  recheck:
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
  * @csHistFile = History file name   * @csHistFile = History file name
  * @sock = client socket   * @sock = client socket
    * @timeout = Session timeout (-1 infinit)
  * return: RETCODE_ERR error, RETCODE_OK ok   * return: RETCODE_ERR error, RETCODE_OK ok
 */  */
 int  int
cliNetLoop(linebuffer_t * __restrict cli_buffer, const char *csHistFile, int sock)cliNetLoop(linebuffer_t * __restrict cli_buffer, const char *csHistFile, 
                 int sock, int timeout)
 {  {
         u_char buf[BUFSIZ];          u_char buf[BUFSIZ];
        int pid, stat, pty, r, s, alen, flg, attrlen = 0, ret = 0;        int pid, stat, pty, s, alen, flg, attrlen = 0, ret = 0;
         fd_set fds;          fd_set fds;
         struct timeval tv = { DEFAULT_SOCK_TIMEOUT, 0 };          struct timeval tv = { DEFAULT_SOCK_TIMEOUT, 0 };
         struct telnetAttrs *a, Attr[10];          struct telnetAttrs *a, Attr[10];
Line 1338  cliNetLoop(linebuffer_t * __restrict cli_buffer, const Line 1399  cliNetLoop(linebuffer_t * __restrict cli_buffer, const
                         } else                          } else
                                 close(sock);                                  close(sock);
   
                        ret = cliLoop(cli_buffer, csHistFile) < 0 ? 1 : 0;                        ret = cliLoop(cli_buffer, csHistFile, timeout) < 0 ? 1 : 0;
                         cliEnd(cli_buffer);                          cliEnd(cli_buffer);
   
                         _exit(ret);                          _exit(ret);
Line 1367  cliNetLoop(linebuffer_t * __restrict cli_buffer, const Line 1428  cliNetLoop(linebuffer_t * __restrict cli_buffer, const
                                         break;                                          break;
                                 }                                  }
   
                                 r = FD_ISSET(sock, &fds) ? sock : pty;  
                                 s = FD_ISSET(sock, &fds) ? pty : sock;                                  s = FD_ISSET(sock, &fds) ? pty : sock;
   
                                 if (FD_ISSET(sock, &fds)) {                                  if (FD_ISSET(sock, &fds)) {
Line 1407  cliNetLoop(linebuffer_t * __restrict cli_buffer, const Line 1467  cliNetLoop(linebuffer_t * __restrict cli_buffer, const
   
                                 if (FD_ISSET(pty, &fds)) {                                  if (FD_ISSET(pty, &fds)) {
                                         memset(buf, 0, BUFSIZ);                                          memset(buf, 0, BUFSIZ);
                                        if ((ret = read(pty, buf, BUFSIZ)) == -1) {                                        if ((ret = read(pty, buf, BUFSIZ)) < 1) {
                                                LOGERR;                                                if (ret)
                                                         LOGERR;
                                                 break;                                                  break;
                                         }                                          }
   
Line 1427  cliNetLoop(linebuffer_t * __restrict cli_buffer, const Line 1488  cliNetLoop(linebuffer_t * __restrict cli_buffer, const
 }  }
   
 /*  /*
 * cliLoop() - CLI main loop * cliRun() - CLI run command line
  *   *
  * @cli_buffer = CLI buffer   * @cli_buffer = CLI buffer
 * @csHistFile = History file name * @psInput = Input command line
  * @prompt = Display prompt after command
  * return: RETCODE_ERR error, RETCODE_OK ok   * return: RETCODE_ERR error, RETCODE_OK ok
 */  */
 int  int
cliLoop(linebuffer_t * __restrict cli_buffer, const char *csHistFile)cliRun(linebuffer_t * __restrict cli_buffer, char *psInput, int prompt)
 {  {
         char *line, *s, *t, **app, *items[MAX_PROMPT_ITEMS];          char *line, *s, *t, **app, *items[MAX_PROMPT_ITEMS];
         register int i;  
         int ret = RETCODE_OK;          int ret = RETCODE_OK;
         struct tagCommand *cmd;          struct tagCommand *cmd;
   
           if (!psInput)
                   return RETCODE_ERR;
           else
                   line = psInput;
   
           // clear whitespaces
           for (s = line; isspace((int) *s); s++);
           if (*s) {
                   for (t = s + strlen(s) - 1; t > s && isspace((int) *t); t--);
                   *++t = 0;
           }
   
           if (*s) {
                   memset(items, 0, sizeof(char*) * MAX_PROMPT_ITEMS);
                   for (app = items; app < items + MAX_PROMPT_ITEMS - 1 && 
                                   (*app = strsep(&s, " \t")); *app ? app++ : app);
   
                   // exec_cmd ...
                   SLIST_FOREACH(cmd, &cli_buffer->line_cmds, cmd_next) {
                           if (!(cmd->cmd_level & (1 << cli_buffer->line_level)))
                                   continue;
                           if (*items[0] && !strncmp(cmd->cmd_name, items[0], strlen(items[0])))
                                   break;
                   }
   
                   if (!cmd) {
                           cli_Printf(cli_buffer, "%sCommand '%s' not found!\n", 
                                           cli_buffer->line_prompt ? "\n" : "", items[0]);
                           ret = RETCODE_ERR;
                   } else
                           if (cmd->cmd_func) {
                                   if (prompt && cli_buffer->line_prompt)
                                           cli_Printf(cli_buffer, "\n");
                                   ret = cmd->cmd_func(cli_buffer, 
                                                   cli_buffer->line_level, items);
                           } else if (prompt) {
                                   clrscrEOL(cli_buffer);
                                   printfCR(cli_buffer, 1);
                           }
           }
   
           return ret;
   }
   
   /*
    * cliLoop() - CLI main loop
    *
    * @cli_buffer = CLI buffer
    * @csHistFile = History file name
    * @timeout = Session timeout (-1 infinit)
    * return: RETCODE_ERR error, RETCODE_OK ok
   */
   int
   cliLoop(linebuffer_t * __restrict cli_buffer, const char *csHistFile, int timeout)
   {
           char *line;
           int ret = RETCODE_OK;
           struct termios t;
   
         /* --- main body of CLI --- */          /* --- main body of CLI --- */
        cliInitLine(cli_buffer);        cliSetLine(cli_buffer, &t);
   
         if (cli_loadHistory(cli_buffer, csHistFile) == RETCODE_ERR)          if (cli_loadHistory(cli_buffer, csHistFile) == RETCODE_ERR)
                 return RETCODE_ERR;                  return RETCODE_ERR;
   
         do {          do {
                line = cliReadLine(cli_buffer);                line = cliReadLine(cli_buffer, timeout);
                 if (!line) {                  if (!line) {
                         printfNL(cli_buffer, 0);                          printfNL(cli_buffer, 0);
                         break;                          break;
                 } else                  } else
                         cli_addHistory(cli_buffer, NULL);                          cli_addHistory(cli_buffer, NULL);
                 // clear whitespaces  
                 for (s = line; isspace((int) *s); s++);  
                 if (*s) {  
                         for (t = s + strlen(s) - 1; t > s && isspace((int) *t); t--);  
                         *++t = 0;  
                 }  
   
                if (*s) {                ret = cliRun(cli_buffer, line, 42);
                        memset(items, 0, sizeof(char*) * MAX_PROMPT_ITEMS); 
                        for (app = items; app < items + MAX_PROMPT_ITEMS - 1 &&  
                                        (*app = strsep(&s, " \t")); *app ? app++ : app); 
   
                         // exec_cmd ...  
                         i = 0;  
                         SLIST_FOREACH(cmd, &cli_buffer->line_cmds, cmd_next) {  
                                 if (*items[0] && !strncmp(cmd->cmd_name, items[0], strlen(items[0])))  
                                         break;  
                                 else  
                                         i++;  
                         }  
   
                         if (!cmd) {  
                                 cli_Printf(cli_buffer, "\nCommand '%s' not found!\n", items[0]);  
                                 ret = -1;  
                         } else  
                                 if (cmd->cmd_func) {  
                                         cli_Printf(cli_buffer, "\n");  
                                         ret = cmd->cmd_func(cli_buffer,   
                                                         cli_buffer->line_level, items);  
                                 } else {  
                                         clrscrEOL(cli_buffer);  
                                         printfCR(cli_buffer, 1);  
                                 }  
                 }  
   
                 cli_freeLine(cli_buffer);                  cli_freeLine(cli_buffer);
                 cli_resetHistory(cli_buffer);                  cli_resetHistory(cli_buffer);
                 e_free(line);                  e_free(line);
        } while (ret < 1);        } while (!cli_buffer->line_kill);
   
         cli_saveHistory(cli_buffer, csHistFile, HISTORY_LINES);          cli_saveHistory(cli_buffer, csHistFile, HISTORY_LINES);
   
           /* --- restore tty --- */
           cliResetLine(cli_buffer, &t);
   
         return ret;          return ret;
 }  }

Removed from v.1.8.2.4  
changed lines
  Added in v.1.19.4.1


FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>