Commit 31c149ce 31c149ce587fd7ee7d7af90bc25bc143cc720741 by Sergey Poznyakoff

readline-related functions.

1 parent 293e836d
/* GNU mailutils - a suite of utilities for electronic mail
Copyright (C) 1999, 2000, 2001 Free Software Foundation, Inc.
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, 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. */
#include "mail.h"
static char **ml_command_completion __P((char *cmd, int start, int end));
static char *ml_command_generator __P((char *text, int state));
static int _interrupt;
static RETSIGTYPE
sig_int(int signo)
{
if (util_find_env("quit")->set)
exit (0);
_interrupt++;
signal (signo, sig_int);
}
void
ml_clear_interrupt()
{
_interrupt = 0;
}
int
ml_got_interrupt()
{
int rc = _interrupt;
_interrupt = 0;
return rc;
}
#ifdef WITH_READLINE
int
ml_getc (FILE *stream)
{
unsigned char c;
if (read (fileno (stream), &c, 1) == 1)
return c;
return EOF;
}
#endif
void
ml_readline_init ()
{
if (!interactive)
return;
#ifdef WITH_READLINE
rl_readline_name = "mail";
rl_attempted_completion_function = (CPPFunction*)ml_command_completion;
rl_getc_function = ml_getc;
#endif
signal(SIGINT, sig_int);
}
#ifdef WITH_READLINE
static char *insert_text;
static int
ml_insert_hook()
{
if (insert_text)
rl_insert_text(insert_text);
return 0;
}
int
ml_reread(char *prompt, char **text)
{
char *s;
insert_text = *text;
rl_startup_hook = ml_insert_hook;
s = readline(prompt);
if (*text)
free(*text);
*text = s;
rl_startup_hook = NULL;
return 0;
}
/*
* readline tab completion
*/
char **
ml_command_completion (char *cmd, int start, int end)
{
if (start == 0)
return completion_matches (cmd, ml_command_generator);
return NULL;
}
/*
* more readline
*/
char *
ml_command_generator (char *text, int state)
{
static int i, len;
char *name;
if (!state)
{
i = 0;
len = strlen (text);
}
while ((name = mail_command_table[i].longname))
{
if (strlen (mail_command_table[i].shortname) > strlen(name))
name = mail_command_table[i].shortname;
i++;
if (strncmp (name, text, len) == 0)
return (strdup(name));
}
return NULL;
}
#else
int
ml_reread(char *prompt, char **text)
{
char *s;
/*FIXME*/
s = readline(prompt);
if (*text)
free(*text);
*text = s;
return 0;
}
char *
readline (const char *prompt)
{
char *line;
char *p;
size_t alloclen, linelen;
if (prompt)
{
fprintf (ofile, "%s", prompt);
fflush (ofile);
}
p = line = calloc (1, 255);
alloclen = 255;
linelen = 0;
for (;;)
{
size_t n;
p = fgets (p, alloclen - linelen, stdin);
if (p)
n = strlen(p);
else if (_interrupt)
{
free (line);
return NULL;
}
else
n = 0;
linelen += n;
/* Error. */
if (linelen == 0)
{
free (line);
return NULL;
}
/* Ok. */
if (line[linelen - 1] == '\n')
{
line[linelen - 1] = '\0';
return line;
}
else
{
char *tmp;
alloclen *= 2;
tmp = realloc (line, alloclen);
if (tmp == NULL)
{
free (line);
return NULL;
}
line = tmp;
p = line + linelen;
}
}
}
#endif