mirror of
https://https.git.savannah.gnu.org/git/bash.git
synced 2026-07-01 01:20:00 +02:00
make completion of nofork comsubs a little better; fix leaks on signals for non-incremental searches; fix leaks in readstr interface
This commit is contained in:
@@ -8371,3 +8371,68 @@ subst.c
|
||||
- function_substitute: unwind-protect current_builtin and this_shell_builtin
|
||||
like we do this_shell_function
|
||||
From a fuzzing report by Nathan Mills <the.true.nathan.mills@gmail.com>
|
||||
|
||||
1/24
|
||||
----
|
||||
braces.c
|
||||
- brace_gobbler: handle nofork command substitutions; skip over any
|
||||
enclosed command and any braces it contains
|
||||
|
||||
bashline.c
|
||||
- check_redir: return 0 if we're in a nofork comsub, so we will attempt
|
||||
command word completion if appropriate
|
||||
|
||||
1/26
|
||||
----
|
||||
lib/readline/readline.h
|
||||
- RL_STATE_READSTR: new state flag saying we are reading an arbitrary
|
||||
string from the keyboard using rl_readstr
|
||||
|
||||
lib/readline/rlprivate.h
|
||||
- READSTR_FREEPMT: new context state flag for rl_readstr; indicates
|
||||
that we have allocated a new prompt with _rl_make_prompt_for_search
|
||||
and we should free it with rl_restore_prompt because rl_clear_message
|
||||
will not do it
|
||||
|
||||
lib/readline/text.c
|
||||
- _rl_readstr_init,_rl_readstr_cleanup: set and unset RL_STATE_READSTR
|
||||
- _rl_unsave_saved_readstr_line: free any rl_undo_list, which we may
|
||||
have accumulated while reading the string, before restoring the line
|
||||
Fixes leaks reported by sparrowhawk996@gmail.com.
|
||||
- _rl_readstr_init: set the READSTR_FREEPMT context flag after we
|
||||
call _rl_make_prompt_for_search, which calls rl_save_prompt
|
||||
- _rl_readstr_sigcleanup: new function to call from signal cleanup;
|
||||
restores prompt and calls _rl_readstr_cleanup to free the readstr
|
||||
context
|
||||
- _rl_readstr_restore: if the RL_READSTR_FREEPMT flag is set in the
|
||||
context, call rl_restore_prompt to deallocate the prompt we created
|
||||
|
||||
lib/readline/callback.c
|
||||
- rl_callback_sigcleanup: call _rl_readstr_sigcleanup to deallocate
|
||||
readstr state on a signal
|
||||
|
||||
lib/readline/text.c
|
||||
- rl_execute_named_command: free COMMAND before returning
|
||||
|
||||
1/27
|
||||
----
|
||||
lib/readline/rlprivate.h
|
||||
- SF_FREEPMT: new flag for non-incremental search contexts: means we
|
||||
saved the prompt data with _rl_make_prompt_for_search and need to
|
||||
restore it with rl_restore_prompt, since rl_clear_message will not
|
||||
|
||||
lib/readline/search.c
|
||||
- _rl_nsearch_sigcleanup: new function that if calls rl_restore_prompt
|
||||
to clean up the saved prompt data if necessary before calling the
|
||||
context cleanup function, avoids memory leak
|
||||
- _rl_nsearch_init: set the SF_FREEPMPT flag after calling
|
||||
_rl_make_prompt_from_search so we can clean it up properly on errors
|
||||
- _rl_nsearch_abort,_rl_nsearch_dosearch: call rl_restore_prompt only
|
||||
if cxt->sflags includes SF_FREEPMT, manage SF_FREEPMT state
|
||||
|
||||
lib/readline/signals.c
|
||||
- _rl_state_sigcleanup: call _rl_nsearch_sigcleanup
|
||||
|
||||
lib/readline/callback.c
|
||||
- _rl_callback_sigcleanup: call _rl_nsearch_sigcleanup
|
||||
|
||||
|
||||
+7
-2
@@ -1385,17 +1385,18 @@ bash_spell_correct_shellword (int count, int key)
|
||||
static inline int
|
||||
check_redir (int ti)
|
||||
{
|
||||
register int this_char, prev_char;
|
||||
int this_char, prev_char, next_char;
|
||||
|
||||
/* Handle the two character tokens `>&', `<&', and `>|'.
|
||||
We are not in a command position after one of these. */
|
||||
this_char = rl_line_buffer[ti];
|
||||
prev_char = (ti > 0) ? rl_line_buffer[ti - 1] : 0;
|
||||
next_char = (ti < rl_end) ? rl_line_buffer[ti + 1] : 0;
|
||||
|
||||
if ((this_char == '&' && (prev_char == '<' || prev_char == '>')) ||
|
||||
(this_char == '|' && prev_char == '>'))
|
||||
return (1);
|
||||
else if (this_char == '{' && prev_char == '$') /*}*/
|
||||
else if (this_char == '{' && prev_char == '$' && FUNSUB_CHAR (next_char) == 0) /*}*/
|
||||
return (1);
|
||||
#if 0 /* Not yet */
|
||||
else if (this_char == '(' && prev_char == '$') /*)*/
|
||||
@@ -1789,6 +1790,8 @@ bash_default_completion (const char *text, int start, int end, int qc, int compf
|
||||
{
|
||||
if (qc != '\'' && text[1] == '(') /* ) */
|
||||
matches = rl_completion_matches (text, command_subst_completion_function);
|
||||
else if (qc != '\'' && text[1] == '{' && FUNSUB_CHAR (text[2])) /* } */
|
||||
matches = rl_completion_matches (text, command_subst_completion_function);
|
||||
else
|
||||
{
|
||||
matches = rl_completion_matches (text, variable_completion_function);
|
||||
@@ -2401,6 +2404,8 @@ command_subst_completion_function (const char *text, int state)
|
||||
text++;
|
||||
else if (*text == '$' && text[1] == '(') /* ) */
|
||||
text += 2;
|
||||
else if (*text == '$' && text[1] == '{' && FUNSUB_CHAR (text[2])) /*}*/
|
||||
text += 3; /* nofork command substitution */
|
||||
/* If the text was quoted, suppress any quote character that the
|
||||
readline completion code would insert. */
|
||||
rl_completion_suppress_quote = 1;
|
||||
|
||||
@@ -38,6 +38,7 @@
|
||||
|
||||
#if defined (SHELL)
|
||||
# include "shell.h"
|
||||
# include "parser.h" /* FUNSUB_CHAR */
|
||||
#else
|
||||
# if defined (TEST)
|
||||
typedef char *WORD_DESC;
|
||||
@@ -619,33 +620,34 @@ brace_gobbler (char *text, size_t tlen, int *indx, int satisfy)
|
||||
|
||||
#if defined (SHELL)
|
||||
/* If compiling for the shell, treat ${...} like \{...} */
|
||||
if (c == '$' && text[i+1] == '{' && quoted != '\'') /* } */
|
||||
if (c == '$' && i < tlen && text[i+1] == '{' && quoted != '\'') /* } */
|
||||
{
|
||||
#if 0
|
||||
/* If we want to inhibit brace expansion during parameter expansions,
|
||||
we need to skip over parameter expansions here. This is easier
|
||||
than teaching brace expansion about the idiosyncracies of shell
|
||||
word expansion. */
|
||||
int o, f;
|
||||
o = no_longjmp_on_fatal_error;
|
||||
no_longjmp_on_fatal_error = 1;
|
||||
f = (quoted == '"') ? Q_DOUBLE_QUOTES : 0;
|
||||
si = i + 2;
|
||||
t = extract_dollar_brace_string (text, &si, f, SX_NOALLOC|SX_NOLONGJMP|SX_COMPLETE|SX_NOERROR);
|
||||
i = si + 1;
|
||||
no_longjmp_on_fatal_error = o;
|
||||
if (i > tlen)
|
||||
#if 1
|
||||
/* nofork command substitution */
|
||||
if (i < tlen - 1 && FUNSUB_CHAR (text[i+2]))
|
||||
{
|
||||
i = tlen;
|
||||
c = 0;
|
||||
break;
|
||||
int o, f;
|
||||
funsub:
|
||||
o = no_longjmp_on_fatal_error;
|
||||
no_longjmp_on_fatal_error = 1;
|
||||
f = (quoted == '"') ? Q_DOUBLE_QUOTES : 0;
|
||||
si = i + 2;
|
||||
t = extract_function_subst (text, &si, f, SX_NOALLOC|SX_NOLONGJMP|SX_NOERROR);
|
||||
i = si + 1;
|
||||
no_longjmp_on_fatal_error = o;
|
||||
if (i > tlen)
|
||||
{
|
||||
i = tlen;
|
||||
c = 0;
|
||||
break;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
#else
|
||||
#endif
|
||||
pass_next = 1;
|
||||
i++;
|
||||
if (quoted == 0)
|
||||
level++;
|
||||
#endif
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
@@ -656,7 +658,7 @@ brace_gobbler (char *text, size_t tlen, int *indx, int satisfy)
|
||||
quoted = 0;
|
||||
#if defined (SHELL)
|
||||
/* The shell allows quoted command substitutions */
|
||||
if (quoted == '"' && c == '$' && text[i+1] == '(') /*)*/
|
||||
if (quoted == '"' && c == '$' && i < tlen && text[i+1] == '(') /*)*/
|
||||
goto comsub;
|
||||
#endif
|
||||
#if defined (SHELL)
|
||||
@@ -676,7 +678,7 @@ brace_gobbler (char *text, size_t tlen, int *indx, int satisfy)
|
||||
|
||||
#if defined (SHELL)
|
||||
/* Pass new-style command and process substitutions through unchanged. */
|
||||
if ((c == '$' || c == '<' || c == '>') && text[i+1] == '(') /* ) */
|
||||
if ((c == '$' || c == '<' || c == '>') && i < tlen && text[i+1] == '(') /* ) */
|
||||
{
|
||||
int o;
|
||||
|
||||
@@ -684,11 +686,7 @@ comsub:
|
||||
o = no_longjmp_on_fatal_error;
|
||||
no_longjmp_on_fatal_error = 1;
|
||||
si = i + 2;
|
||||
#if 0
|
||||
t = extract_command_subst (text, &si, SX_NOALLOC|SX_NOLONGJMP|SX_NOERROR|SX_COMPLETE);
|
||||
#else
|
||||
t = extract_command_subst (text, &si, SX_NOALLOC|SX_NOLONGJMP|SX_NOERROR);
|
||||
#endif
|
||||
i = si + 1;
|
||||
no_longjmp_on_fatal_error = o;
|
||||
if (i > tlen)
|
||||
|
||||
@@ -363,7 +363,7 @@ rl_callback_sigcleanup (void)
|
||||
if (RL_ISSTATE (RL_STATE_ISEARCH))
|
||||
_rl_isearch_cleanup (_rl_iscxt, 0);
|
||||
else if (RL_ISSTATE (RL_STATE_NSEARCH))
|
||||
_rl_nsearch_cleanup (_rl_nscxt, 0);
|
||||
_rl_nsearch_sigcleanup (_rl_nscxt, 0);
|
||||
else if (RL_ISSTATE (RL_STATE_VIMOTION))
|
||||
RL_UNSETSTATE (RL_STATE_VIMOTION);
|
||||
else if (RL_ISSTATE (RL_STATE_NUMERICARG))
|
||||
@@ -373,6 +373,9 @@ rl_callback_sigcleanup (void)
|
||||
}
|
||||
else if (RL_ISSTATE (RL_STATE_MULTIKEY))
|
||||
RL_UNSETSTATE (RL_STATE_MULTIKEY);
|
||||
else if (RL_ISSTATE (RL_STATE_READSTR))
|
||||
_rl_readstr_sigcleanup (_rl_rscxt, 0);
|
||||
|
||||
if (RL_ISSTATE (RL_STATE_CHARSEARCH))
|
||||
RL_UNSETSTATE (RL_STATE_CHARSEARCH);
|
||||
|
||||
|
||||
+32
-29
@@ -914,37 +914,40 @@ extern int rl_persistent_signal_handlers;
|
||||
#define MULT_MATCH 2
|
||||
|
||||
/* Possible state values for rl_readline_state */
|
||||
#define RL_STATE_NONE 0x000000 /* no state; before first call */
|
||||
#define RL_STATE_NONE 0x0000000 /* no state; before first call */
|
||||
|
||||
#define RL_STATE_INITIALIZING 0x0000001 /* initializing */
|
||||
#define RL_STATE_INITIALIZED 0x0000002 /* initialization done */
|
||||
#define RL_STATE_TERMPREPPED 0x0000004 /* terminal is prepped */
|
||||
#define RL_STATE_READCMD 0x0000008 /* reading a command key */
|
||||
#define RL_STATE_METANEXT 0x0000010 /* reading input after ESC */
|
||||
#define RL_STATE_DISPATCHING 0x0000020 /* dispatching to a command */
|
||||
#define RL_STATE_MOREINPUT 0x0000040 /* reading more input in a command function */
|
||||
#define RL_STATE_ISEARCH 0x0000080 /* doing incremental search */
|
||||
#define RL_STATE_NSEARCH 0x0000100 /* doing non-inc search */
|
||||
#define RL_STATE_SEARCH 0x0000200 /* doing a history search */
|
||||
#define RL_STATE_NUMERICARG 0x0000400 /* reading numeric argument */
|
||||
#define RL_STATE_MACROINPUT 0x0000800 /* getting input from a macro */
|
||||
#define RL_STATE_MACRODEF 0x0001000 /* defining keyboard macro */
|
||||
#define RL_STATE_OVERWRITE 0x0002000 /* overwrite mode */
|
||||
#define RL_STATE_COMPLETING 0x0004000 /* doing completion */
|
||||
#define RL_STATE_SIGHANDLER 0x0008000 /* in readline sighandler */
|
||||
#define RL_STATE_UNDOING 0x0010000 /* doing an undo */
|
||||
#define RL_STATE_INPUTPENDING 0x0020000 /* rl_execute_next called */
|
||||
#define RL_STATE_TTYCSAVED 0x0040000 /* tty special chars saved */
|
||||
#define RL_STATE_CALLBACK 0x0080000 /* using the callback interface */
|
||||
#define RL_STATE_VIMOTION 0x0100000 /* reading vi motion arg */
|
||||
#define RL_STATE_MULTIKEY 0x0200000 /* reading multiple-key command */
|
||||
#define RL_STATE_VICMDONCE 0x0400000 /* entered vi command mode at least once */
|
||||
#define RL_STATE_CHARSEARCH 0x0800000 /* vi mode char search */
|
||||
#define RL_STATE_REDISPLAYING 0x1000000 /* updating terminal display */
|
||||
#define RL_STATE_INITIALIZING 0x00000001 /* initializing */
|
||||
#define RL_STATE_INITIALIZED 0x00000002 /* initialization done */
|
||||
#define RL_STATE_TERMPREPPED 0x00000004 /* terminal is prepped */
|
||||
#define RL_STATE_READCMD 0x00000008 /* reading a command key */
|
||||
#define RL_STATE_METANEXT 0x00000010 /* reading input after ESC */
|
||||
#define RL_STATE_DISPATCHING 0x00000020 /* dispatching to a command */
|
||||
#define RL_STATE_MOREINPUT 0x00000040 /* reading more input in a command function */
|
||||
#define RL_STATE_ISEARCH 0x00000080 /* doing incremental search */
|
||||
#define RL_STATE_NSEARCH 0x00000100 /* doing non-inc search */
|
||||
#define RL_STATE_SEARCH 0x00000200 /* doing a history search */
|
||||
#define RL_STATE_NUMERICARG 0x00000400 /* reading numeric argument */
|
||||
#define RL_STATE_MACROINPUT 0x00000800 /* getting input from a macro */
|
||||
#define RL_STATE_MACRODEF 0x00001000 /* defining keyboard macro */
|
||||
#define RL_STATE_OVERWRITE 0x00002000 /* overwrite mode */
|
||||
#define RL_STATE_COMPLETING 0x00004000 /* doing completion */
|
||||
#define RL_STATE_SIGHANDLER 0x00008000 /* in readline sighandler */
|
||||
#define RL_STATE_UNDOING 0x00010000 /* doing an undo */
|
||||
#define RL_STATE_INPUTPENDING 0x00020000 /* rl_execute_next called */
|
||||
#define RL_STATE_TTYCSAVED 0x00040000 /* tty special chars saved */
|
||||
#define RL_STATE_CALLBACK 0x00080000 /* using the callback interface */
|
||||
#define RL_STATE_VIMOTION 0x00100000 /* reading vi motion arg */
|
||||
#define RL_STATE_MULTIKEY 0x00200000 /* reading multiple-key command */
|
||||
#define RL_STATE_VICMDONCE 0x00400000 /* entered vi command mode at least once */
|
||||
#define RL_STATE_CHARSEARCH 0x00800000 /* vi mode char search */
|
||||
#define RL_STATE_REDISPLAYING 0x01000000 /* updating terminal display */
|
||||
|
||||
#define RL_STATE_DONE 0x2000000 /* done; accepted line */
|
||||
#define RL_STATE_TIMEOUT 0x4000000 /* done; timed out */
|
||||
#define RL_STATE_EOF 0x8000000 /* done; got eof on read */
|
||||
#define RL_STATE_DONE 0x02000000 /* done; accepted line */
|
||||
#define RL_STATE_TIMEOUT 0x04000000 /* done; timed out */
|
||||
#define RL_STATE_EOF 0x08000000 /* done; got eof on read */
|
||||
|
||||
/* Rearrange these for next major version */
|
||||
#define RL_STATE_READSTR 0x10000000 /* reading a string for M-x */
|
||||
|
||||
#define RL_SETSTATE(x) (rl_readline_state |= (x))
|
||||
#define RL_UNSETSTATE(x) (rl_readline_state &= ~(x))
|
||||
|
||||
@@ -67,6 +67,7 @@
|
||||
#define SF_CHGKMAP 0x08
|
||||
#define SF_PATTERN 0x10
|
||||
#define SF_NOCASE 0x20 /* unused so far */
|
||||
#define SF_FREEPMT 0x40 /* saved prompt separately, need to free it */
|
||||
|
||||
typedef struct __rl_search_context
|
||||
{
|
||||
@@ -111,7 +112,8 @@ typedef struct __rl_search_context
|
||||
} _rl_search_cxt;
|
||||
|
||||
/* readstr flags */
|
||||
#define RL_READSTR_NOSPACE 0x01 /* don't insert space, use for completion */
|
||||
#define READSTR_NOSPACE 0x01 /* don't insert space, use for completion */
|
||||
#define READSTR_FREEPMT 0x02 /* called rl_save_prompt, need to free it ourselves */
|
||||
|
||||
typedef struct __rl_readstr_context
|
||||
{
|
||||
@@ -432,6 +434,7 @@ extern int _rl_restore_tty_signals (void);
|
||||
/* search.c */
|
||||
extern int _rl_nsearch_callback (_rl_search_cxt *);
|
||||
extern int _rl_nsearch_cleanup (_rl_search_cxt *, int);
|
||||
extern int _rl_nsearch_sigcleanup (_rl_search_cxt *, int);
|
||||
|
||||
extern void _rl_free_saved_search_line (void);
|
||||
|
||||
@@ -443,6 +446,8 @@ extern void _rl_release_sigint (void);
|
||||
extern void _rl_block_sigwinch (void);
|
||||
extern void _rl_release_sigwinch (void);
|
||||
|
||||
extern void _rl_state_sigcleanup (void);
|
||||
|
||||
/* terminal.c */
|
||||
extern void _rl_get_screen_size (int, int);
|
||||
extern void _rl_sigwinch_resize_terminal (void);
|
||||
@@ -488,6 +493,7 @@ extern void _rl_free_saved_readstr_line (void);
|
||||
extern void _rl_unsave_saved_readstr_line (void);
|
||||
extern _rl_readstr_cxt *_rl_readstr_init (int, int);
|
||||
extern int _rl_readstr_cleanup (_rl_readstr_cxt *, int);
|
||||
extern int _rl_readstr_sigcleanup (_rl_readstr_cxt *, int);
|
||||
extern void _rl_readstr_restore (_rl_readstr_cxt *);
|
||||
extern int _rl_readstr_getchar (_rl_readstr_cxt *);
|
||||
extern int _rl_readstr_dispatch (_rl_readstr_cxt *, int);
|
||||
|
||||
+19
-3
@@ -286,6 +286,7 @@ _rl_nsearch_init (int dir, int pchar)
|
||||
rl_end = rl_point = 0;
|
||||
|
||||
p = _rl_make_prompt_for_search (pchar ? pchar : ':');
|
||||
cxt->sflags |= SF_FREEPMT;
|
||||
rl_message ("%s", p);
|
||||
xfree (p);
|
||||
|
||||
@@ -313,13 +314,24 @@ _rl_nsearch_abort (_rl_search_cxt *cxt)
|
||||
_rl_unsave_saved_search_line ();
|
||||
rl_point = cxt->save_point;
|
||||
rl_mark = cxt->save_mark;
|
||||
rl_restore_prompt ();
|
||||
if (cxt->sflags & SF_FREEPMT)
|
||||
rl_restore_prompt (); /* _rl_make_prompt_for_search saved it */
|
||||
cxt->sflags &= ~SF_FREEPMT;
|
||||
rl_clear_message ();
|
||||
_rl_fix_point (1);
|
||||
|
||||
RL_UNSETSTATE (RL_STATE_NSEARCH);
|
||||
}
|
||||
|
||||
int
|
||||
_rl_nsearch_sigcleanup (_rl_search_cxt *cxt, int r)
|
||||
{
|
||||
if (cxt->sflags & SF_FREEPMT)
|
||||
rl_restore_prompt (); /* _rl_make_prompt_for_search saved it */
|
||||
cxt->sflags &= ~SF_FREEPMT;
|
||||
return (_rl_nsearch_cleanup (cxt, r));
|
||||
}
|
||||
|
||||
/* Process just-read character C according to search context CXT. Return -1
|
||||
if the caller should abort the search, 0 if we should break out of the
|
||||
loop, and 1 if we should continue to read characters. */
|
||||
@@ -427,7 +439,9 @@ _rl_nsearch_dosearch (_rl_search_cxt *cxt)
|
||||
{
|
||||
_rl_free_saved_search_line ();
|
||||
rl_ding ();
|
||||
rl_restore_prompt ();
|
||||
if (cxt->sflags & SF_FREEPMT)
|
||||
rl_restore_prompt ();
|
||||
cxt->sflags &= ~SF_FREEPMT;
|
||||
RL_UNSETSTATE (RL_STATE_NSEARCH);
|
||||
return -1;
|
||||
}
|
||||
@@ -452,7 +466,9 @@ _rl_nsearch_dosearch (_rl_search_cxt *cxt)
|
||||
#endif
|
||||
}
|
||||
|
||||
rl_restore_prompt ();
|
||||
if (cxt->sflags & SF_FREEPMT)
|
||||
rl_restore_prompt ();
|
||||
cxt->sflags &= ~SF_FREEPMT;
|
||||
return (noninc_dosearch (noninc_search_string, cxt->direction, cxt->sflags&SF_PATTERN));
|
||||
}
|
||||
|
||||
|
||||
@@ -585,6 +585,19 @@ rl_reset_after_signal (void)
|
||||
rl_set_signals ();
|
||||
}
|
||||
|
||||
/* Similar to rl_callback_sigcleanup, but cleans up operations that allocate
|
||||
state even when not in callback mode. */
|
||||
void
|
||||
_rl_state_sigcleanup (void)
|
||||
{
|
||||
if (RL_ISSTATE (RL_STATE_ISEARCH)) /* incremental search */
|
||||
_rl_isearch_cleanup (_rl_iscxt, 0);
|
||||
else if (RL_ISSTATE (RL_STATE_NSEARCH)) /* non-incremental search */
|
||||
_rl_nsearch_sigcleanup (_rl_nscxt, 0);
|
||||
else if (RL_ISSTATE (RL_STATE_READSTR)) /* reading a string */
|
||||
_rl_readstr_sigcleanup (_rl_rscxt, 0);
|
||||
}
|
||||
|
||||
/* Free up the readline variable line state for the current line (undo list,
|
||||
any partial history entry, any keyboard macros in progress, and any
|
||||
numeric arguments in process) after catching a signal, before calling
|
||||
@@ -594,6 +607,9 @@ rl_free_line_state (void)
|
||||
{
|
||||
register HIST_ENTRY *entry;
|
||||
|
||||
if (RL_ISSTATE (RL_STATE_CALLBACK) == 0)
|
||||
_rl_state_sigcleanup ();
|
||||
|
||||
rl_free_undo_list ();
|
||||
|
||||
entry = current_history ();
|
||||
|
||||
+27
-4
@@ -1971,10 +1971,13 @@ _rl_rscxt_dispose (_rl_readstr_cxt *cxt, int flags)
|
||||
xfree (cxt);
|
||||
}
|
||||
|
||||
/* This isn't used yet */
|
||||
void
|
||||
_rl_free_saved_readstr_line ()
|
||||
{
|
||||
if (_rl_saved_line_for_readstr)
|
||||
/* This doesn't free any saved undo list, if it needs to,
|
||||
rl_clear_history shows how to do it. */
|
||||
_rl_free_saved_line (_rl_saved_line_for_readstr);
|
||||
_rl_saved_line_for_readstr = (HIST_ENTRY *)NULL;
|
||||
}
|
||||
@@ -1983,7 +1986,10 @@ void
|
||||
_rl_unsave_saved_readstr_line ()
|
||||
{
|
||||
if (_rl_saved_line_for_readstr)
|
||||
_rl_unsave_line (_rl_saved_line_for_readstr);
|
||||
{
|
||||
_rl_free_undo_list (rl_undo_list);
|
||||
_rl_unsave_line (_rl_saved_line_for_readstr); /* restores rl_undo_list */
|
||||
}
|
||||
_rl_saved_line_for_readstr = (HIST_ENTRY *)NULL;
|
||||
}
|
||||
|
||||
@@ -2004,9 +2010,12 @@ _rl_readstr_init (int pchar, int flags)
|
||||
rl_end = rl_point = 0;
|
||||
|
||||
p = _rl_make_prompt_for_search (pchar ? pchar : '@');
|
||||
cxt->flags |= READSTR_FREEPMT;
|
||||
rl_message ("%s", p);
|
||||
xfree (p);
|
||||
|
||||
RL_SETSTATE (RL_STATE_READSTR);
|
||||
|
||||
_rl_rscxt = cxt;
|
||||
|
||||
return cxt;
|
||||
@@ -2018,6 +2027,8 @@ _rl_readstr_cleanup (_rl_readstr_cxt *cxt, int r)
|
||||
_rl_rscxt_dispose (cxt, 0);
|
||||
_rl_rscxt = 0;
|
||||
|
||||
RL_UNSETSTATE (RL_STATE_READSTR);
|
||||
|
||||
return (r != 1);
|
||||
}
|
||||
|
||||
@@ -2027,11 +2038,22 @@ _rl_readstr_restore (_rl_readstr_cxt *cxt)
|
||||
_rl_unsave_saved_readstr_line (); /* restores rl_undo_list */
|
||||
rl_point = cxt->save_point;
|
||||
rl_mark = cxt->save_mark;
|
||||
rl_restore_prompt (); /* _rl_make_prompt_for_search saved it */
|
||||
if (cxt->flags & READSTR_FREEPMT)
|
||||
rl_restore_prompt (); /* _rl_make_prompt_for_search saved it */
|
||||
cxt->flags &= ~READSTR_FREEPMT;
|
||||
rl_clear_message ();
|
||||
_rl_fix_point (1);
|
||||
}
|
||||
|
||||
int
|
||||
_rl_readstr_sigcleanup (_rl_readstr_cxt *cxt, int r)
|
||||
{
|
||||
if (cxt->flags & READSTR_FREEPMT)
|
||||
rl_restore_prompt (); /* _rl_make_prompt_for_search saved it */
|
||||
cxt->flags &= ~READSTR_FREEPMT;
|
||||
return (_rl_readstr_cleanup (cxt, r));
|
||||
}
|
||||
|
||||
int
|
||||
_rl_readstr_getchar (_rl_readstr_cxt *cxt)
|
||||
{
|
||||
@@ -2130,7 +2152,7 @@ _rl_readstr_dispatch (_rl_readstr_cxt *cxt, int c)
|
||||
break;
|
||||
|
||||
case ' ':
|
||||
if ((cxt->flags & RL_READSTR_NOSPACE) == 0)
|
||||
if ((cxt->flags & READSTR_NOSPACE) == 0)
|
||||
{
|
||||
_rl_insert_char (1, c);
|
||||
break;
|
||||
@@ -2273,7 +2295,7 @@ _rl_read_command_name ()
|
||||
char *ret;
|
||||
int c, r;
|
||||
|
||||
cxt = _rl_readstr_init ('!', RL_READSTR_NOSPACE);
|
||||
cxt = _rl_readstr_init ('!', READSTR_NOSPACE);
|
||||
cxt->compfunc = _rl_readcmd_complete;
|
||||
|
||||
/* skip callback stuff for now */
|
||||
@@ -2344,5 +2366,6 @@ rl_execute_named_command (int count, int key)
|
||||
r = 1;
|
||||
}
|
||||
|
||||
free (command);
|
||||
return r;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user