/* source: xio-readline.c */
/* Copyright Gerhard Rieger and contributors (see file CHANGES) */
/* Published under the GNU General Public License V.2, see file COPYING */

/* this file contains the source for opening the readline address */

#include "xiosysincludes.h"
#include "xioopen.h"

#include "xio-termios.h"
#include "xio-readline.h"


#if WITH_READLINE

/*
options: history file
	prompt
	mode=vi?
	inputrc=?

uses stdin!!
*/

/* length of buffer for dynamic prompt */
#define READLINE_MAXPROMPT 512

static int xioopen_readline(int argc, const char *argv[], struct opt *opts, int rw, xiofile_t *xfd, const struct addrdesc *addrdesc);


const struct addrdesc xioaddr_readline = { "READLINE", 3, xioopen_readline, GROUP_FD|GROUP_TERMIOS|GROUP_READLINE, 0, 0, 0 HELP(NULL) };

const struct optdesc opt_history_file = { "history-file", "history", OPT_HISTORY_FILE, GROUP_READLINE, PH_LATE, TYPE_STRING, OFUNC_OFFSET, XIO_OFFSETOF(para.readline.history_file) };
const struct optdesc opt_prompt       = { "prompt",       NULL,      OPT_PROMPT,       GROUP_READLINE, PH_LATE, TYPE_STRING, OFUNC_OFFSET, XIO_OFFSETOF(para.readline.prompt) };
const struct optdesc opt_noprompt     = { "noprompt",     NULL,      OPT_NOPROMPT,     GROUP_READLINE, PH_LATE, TYPE_BOOL,   OFUNC_SPEC,   0 };
const struct optdesc opt_noecho       = { "noecho",       NULL,      OPT_NOECHO,       GROUP_READLINE, PH_LATE, TYPE_STRING, OFUNC_SPEC,   0 };

static int xioopen_readline(
	int argc,
	const char *argv[],
	struct opt *opts,
	int xioflags,
	xiofile_t *xfd,
	const struct addrdesc *addrdesc)
{
   struct single *sfd = &xfd->stream;
   int rw = (xioflags & XIO_ACCMODE);
   char msgbuf[256], *cp = msgbuf;
   bool noprompt = false;
   char *noecho = NULL;

   if (argc != 1) {
      xio_syntax(argv[0], 0, argc-1, addrdesc->syntax);
      return STAT_NORETRY;
   }

   if (!(xioflags & XIO_MAYCONVERT)) {
      Error("address with data processing not allowed here");
      return STAT_NORETRY;
   }
   xfd->common.flags |= XIO_DOESCONVERT;

   strcpy(cp, "using "); cp = strchr(cp, '\0');
   if ((rw+1)&1) {
      strcpy(cp, "readline on stdin for reading"); cp = strchr(cp, '\0');

      if ((rw+1)&2) {
	 strcpy(cp, " and ");
	 cp = strchr(cp, '\0');
      }
   }
   if ((rw+1)&2) {
      strcpy(cp, "stdio for writing"); cp = strchr(cp, '\0');
   }
   Notice(msgbuf);

   xfd->stream.fd = 0;	/* stdin */
   xfd->stream.howtoend = END_NONE;
   xfd->stream.dtype    = XIODATA_READLINE;

#if WITH_TERMIOS
   if (Isatty(xfd->stream.fd)) {
      if (Tcgetattr(xfd->stream.fd, &xfd->stream.savetty) < 0) {
	 Warn2("cannot query current terminal settings on fd %d. %s",
	       xfd->stream.fd, strerror(errno));
      } else {
	 xfd->stream.ttyvalid = true;
      }
   }
#endif /* WITH_TERMIOS */

   if (applyopts_single(sfd, opts, PH_INIT) < 0)  return -1;
   applyopts(sfd, -1, opts, PH_INIT);

   applyopts2(sfd, -1, opts, PH_INIT, PH_FD);

   Using_history();
   applyopts_offset(&xfd->stream, opts);
   retropt_bool(opts, OPT_NOPROMPT, &noprompt);
   if (!noprompt && !xfd->stream.para.readline.prompt) {
      xfd->stream.para.readline.dynbytes = READLINE_MAXPROMPT;
      xfd->stream.para.readline.dynprompt =
	 Malloc(xfd->stream.para.readline.dynbytes+1);
      xfd->stream.para.readline.dynend =
	 xfd->stream.para.readline.dynprompt;
   }

#if HAVE_REGEX_H
   retropt_string(opts, OPT_NOECHO, &noecho);
   if (noecho) {
      int errcode;
      char errbuf[128];
      if ((errcode = regcomp(&xfd->stream.para.readline.noecho, noecho,
			     REG_EXTENDED|REG_NOSUB))
	  != 0) {
	 regerror(errcode, &xfd->stream.para.readline.noecho,
		  errbuf, sizeof(errbuf));
	 Error3("regcomp(%p, \"%s\", REG_EXTENDED|REG_NOSUB): %s",
		&xfd->stream.para.readline.noecho, noecho, errbuf);
	 return -1;
      }
      xfd->stream.para.readline.hasnoecho = true;
   }
#endif /* HAVE_REGEX_H */
   if (xfd->stream.para.readline.history_file) {
      Read_history(xfd->stream.para.readline.history_file);
   }
#if _WITH_TERMIOS
   xiotermios_clrflag(xfd->stream.fd, 3, ICANON|ECHO);
   xiotermios_flush(xfd->stream.fd);
#endif /* _WITH_TERMIOS */
   return _xio_openlate(&xfd->stream, opts);
}


ssize_t xioread_readline(struct single *pipe, void *buff, size_t bufsiz) {
   /*! indent */
   ssize_t bytes;
   char *line;
   int _errno;

#if HAVE_REGEX_H
      if (pipe->para.readline.dynprompt &&
	  pipe->para.readline.hasnoecho &&
	  !regexec(&pipe->para.readline.noecho,
		   pipe->para.readline.dynprompt, 0, NULL, 0)) {
#if _WITH_TERMIOS
      /* under these conditions, we do not echo input, thus we circumvent
	 readline */
	 struct termios saveterm, setterm;
	 *pipe->para.readline.dynend = '\0';
	 Tcgetattr(pipe->fd, &saveterm);	/*! error */
	 setterm = saveterm;
	 setterm.c_lflag |= ICANON;
	 Tcsetattr(pipe->fd, TCSANOW, &setterm);	/*!*/
#endif /* _WITH_TERMIOS */
	 do {
	    bytes = Read(pipe->fd, buff, bufsiz);
	 } while (bytes < 0 && errno == EINTR);
	 if (bytes < 0) {
	    _errno = errno;
	    Error4("read(%d, %p, "F_Zu"): %s",
		   pipe->fd, buff, bufsiz, strerror(_errno));
	    errno = _errno;
	    return -1;
	 }
#if _WITH_TERMIOS
	 setterm.c_lflag &= ~ICANON;
	 Tcgetattr(pipe->fd, &setterm);	/*! error */
	 Tcsetattr(pipe->fd, TCSANOW, &saveterm);	/*!*/
#endif /* _WITH_TERMIOS */
	 pipe->para.readline.dynend = pipe->para.readline.dynprompt;
	 /*Write(pipe->fd, "\n", 1);*/	/*!*/
	 return bytes;
      }
#endif /* HAVE_REGEX_H */

#if _WITH_TERMIOS
      xiotermios_setflag(pipe->fd, 3, ECHO);
      xiotermios_flush(pipe->fd);
#endif /* _WITH_TERMIOS */
      if (pipe->para.readline.prompt || pipe->para.readline.dynprompt) {
	 /* we must carriage return, because readline will first print the
	    prompt */
	 ssize_t writt;
	 writt = writefull(pipe->fd, "\r", 1);
	 if (writt < 0) {
	    Warn2("write(%d, \"\\r\", 1): %s",
		   pipe->fd, strerror(errno));
	 } else if (writt < 1) {
	    Warn1("write() only wrote "F_Zu" of 1 byte", writt);
	 }
      }

      if (pipe->para.readline.dynprompt) {
	 *pipe->para.readline.dynend = '\0';
	 line = Readline(pipe->para.readline.dynprompt);
	 pipe->para.readline.dynend = pipe->para.readline.dynprompt;
      } else {
	 line = Readline(pipe->para.readline.prompt);
      }
      /* GNU readline defines no error return */
      if (line == NULL) {
	 return 0;	/* EOF */
      }
#if _WITH_TERMIOS
      xiotermios_clrflag(pipe->fd, 3, ECHO);
      xiotermios_flush(pipe->fd);
#endif /* _WITH_TERMIOS */
      Add_history(line);
      bytes = strlen(line);
      ((char *)buff)[0] = '\0'; strncat(buff, line, bufsiz-1);
      free(line);
      if ((size_t)bytes < bufsiz) {
	 strcat(buff, "\n");  ++bytes;
      }
      return bytes;
}

void xioscan_readline(struct single *pipe, const void *buff, size_t bytes) {
   if (pipe->dtype == XIODATA_READLINE && pipe->para.readline.dynprompt) {
      /* we save the last part of the output as possible prompt */
      const void *ptr = buff;
      const void *pcr;
      const void *plf;
      size_t len;

      if (bytes > pipe->para.readline.dynbytes) {
	 ptr = (const char *)buff + bytes - pipe->para.readline.dynbytes;
	 len = pipe->para.readline.dynbytes;
      } else {
	 len = bytes;
      }
      pcr = memrchr(ptr, '\r', len);
      plf = memrchr(ptr, '\n', len);
      if (pcr != NULL || plf != NULL) {
	 const void *peol = Max(pcr, plf);
	 /* forget old prompt */
	 pipe->para.readline.dynend = pipe->para.readline.dynprompt;
	 len -= (peol+1 - ptr);
	 /* new prompt starts here */
	 ptr = (const char *)peol+1;
      }
      if (pipe->para.readline.dynend - pipe->para.readline.dynprompt + len >
	  pipe->para.readline.dynbytes) {
	 memmove(pipe->para.readline.dynprompt,
		 pipe->para.readline.dynend -
		    (pipe->para.readline.dynbytes - len),
		 pipe->para.readline.dynbytes - len);
	 pipe->para.readline.dynend =
	    pipe->para.readline.dynprompt + pipe->para.readline.dynbytes - len;
      }
      memcpy(pipe->para.readline.dynend, ptr, len);
      pipe->para.readline.dynend = pipe->para.readline.dynend + len;
   }
   return;
}

#endif /* WITH_READLINE */
