minor readline fixes for isearch, insert-char,quoted-insert, and do-lowercase-version; fix buffer overflow with printf %b; work around issues with isblank in UTF-8 locales on macOS; fixes for the enable builtin

This commit is contained in:
Chet Ramey
2023-05-31 10:40:39 -04:00
parent e252024788
commit 353e3749e9
12 changed files with 123 additions and 18 deletions
+52
View File
@@ -6442,3 +6442,55 @@ eval.c
back to 0 if we should not exit. This can occur when EOF delimits
a simple command (simple_command_terminator)
From a report by Grisha Levit <grishalevit@gmail.com>
5/27
----
lib/readline/mbutil.c
- _rl_get_char_len: if SRC is "", make sure to return 0
lib/readline/isearch.c
- _rl_isearch_callback: if _rl_search_getchar returns EOF, return 1
to abort search; if it returns with RL_STATE_ISEARCH unset, return
1 (handling a signal can turn it off via _rl_isearch_cleanup)
5/29
----
lib/readline/text.c
- _rl_insert_char, rl_quoted_insert: minor fixes from Grisha Levit
builtins/printf.def
- bexpand: use the same calculation for the size of the return buffer
as ansicstr().
From a report by Grisha Levit <grishalevit@gmail.com>
locale.c
- locale_setblanks: work around problem with macOS where isblank(x)
incorrectly returns true for characters 0x80-0xff in a UTF-8 locale
From a report by Grisha Levit <grishalevit@gmail.com>
- set_default_locale_vars,set_locale_vars,reset_locale_vars: make sure
we call locale_setblanks after setting/resetting locale_utf8locale,
since we use that in locale_setblanks
lib/sh/smatch.c
- charseqcmp,is_cclass,FOLD: make sure we don't treat chars >= 0x80
as valid in a UTF-8 locale, since they are multibyte characters.
From a report by Grisha Levit <grishalevit@gmail.com> with a full
explanation in http://www.openradar.me/FB9973780
5/30
----
builtins/enable.def
- enable_builtin: don't call dlopen with a null pathname, it will
succeed. Report from Wiley Young <wyeth2485@gmail.com>
lib/readline/readline.c
- _rl_dispatch_subseq: if a user binds do-lowercase-version to something
that isn't an uppercase character, flag an error rather than recurse.
From a report by Grisha Levit <grishalevit@gmail.com>
5/31
----
builtins/enable.def
- enable_builtin: don't try to load a builtin that's not found if
the -n flag is supplied.
From a report from Emanuele Torre <torreemanuele6@gmail.com>
+7 -4
View File
@@ -215,20 +215,23 @@ enable_builtin (WORD_LIST *list)
{
while (list)
{
opt = enable_shell_command (list->word->word, flags & NFLAG);
char *command;
command = list->word->word;
opt = enable_shell_command (command, flags & NFLAG);
next = list->next;
#if defined (HAVE_DLOPEN) && defined (HAVE_DLSYM)
/* If we try to enable a non-existent builtin, and we have dynamic
loading, try the equivalent of `enable -f name name'. */
if (opt == EX_NOTFOUND)
if (*command && (flags & NFLAG) == 0 && opt == EX_NOTFOUND)
{
int dflags, r;
dflags = ENABLED|SILENT|((flags & SFLAG) ? SPECIAL : 0);
list->next = 0;
r = dyn_load_builtin (list, dflags, list->word->word);
r = dyn_load_builtin (list, dflags, command);
list->next = next;
if (r == EXECUTION_SUCCESS)
opt = r;
@@ -240,7 +243,7 @@ enable_builtin (WORD_LIST *list)
if (opt == EX_NOTFOUND)
{
sh_notbuiltin (list->word->word);
sh_notbuiltin (command);
result = EXECUTION_FAILURE;
}
else if (opt != EXECUTION_SUCCESS)
+9
View File
@@ -1152,7 +1152,16 @@ bexpand (char *string, int len, int *sawc, int *lenp)
return (ret);
}
#if defined (HANDLE_MULTIBYTE)
/* same logic as lib/sh/strtrans.c:ansicstr() */
temp = 4*len + 4;
if (temp < 12)
temp = 12; /* ensure enough for eventual u32cesc */
ret = (char *)xmalloc (temp);
#else
ret = (char *)xmalloc (len + 1);
#endif
temp = 0;
for (r = ret, s = string; s && *s; )
{
c = *s++;
+5
View File
@@ -55,6 +55,9 @@ extern int locale_utf8locale; /* XXX */
#define UTF8_MBFIRSTCHAR(c) (((c) & 0xc0) == 0xc0)
#define UTF8_MBCHAR(c) (((c) & 0xc0) == 0x80)
/* Is an eight-bit quantity a valid character in the current locale? */
#define VALID_SINGLEBYTE_CHAR(c) (locale_utf8locale == 0 || ((c) & 0x80) == 0)
#else /* !HANDLE_MULTIBYTE */
#undef MB_LEN_MAX
@@ -83,6 +86,8 @@ extern int locale_utf8locale; /* XXX */
#define UTF8_SINGLEBYTE(c) (1)
#define UTF8_MBFIRSTCHAR(c) (0)
#defined VALID_SINGLEBYTE_CHAR(c) (1)
#endif /* !HANDLE_MULTIBYTE */
/* Declare and initialize a multibyte state. Call must be terminated
+11 -3
View File
@@ -141,6 +141,10 @@ rangecmp (int c1, int c2, int forcecoll)
static int
collseqcmp (int c, int equiv)
{
/* Make sure characters >= 0x80 are compared as bytes in a UTF-8 locale. */
if (locale_utf8locale && (UTF8_SINGLEBYTE (c) == 0 || UTF8_SINGLEBYTE (equiv) == 0))
return (c == equiv);
if (charcmp (c, equiv, 1) == 0)
return 1;
@@ -281,6 +285,9 @@ is_cclass (int c, const char *name)
enum char_class char_class;
int result;
if (locale_utf8locale && UTF8_SINGLEBYTE (c) == 0)
return -1;
char_class = is_valid_cclass (name);
if (char_class == CC_NO_CLASS)
return -1;
@@ -291,9 +298,10 @@ is_cclass (int c, const char *name)
/* Now include `sm_loop.c' for single-byte characters. */
/* The result of FOLD is an `unsigned char' */
# define FOLD(c) ((flags & FNM_CASEFOLD) \
? TOLOWER ((unsigned char)c) \
: ((unsigned char)c))
# define FOLD(c) \
(((flags & FNM_CASEFOLD) && (locale_utf8locale == 0 || UTF8_SINGLEBYTE (c))) \
? TOLOWER ((unsigned char)c) \
: ((unsigned char)c))
#if !defined (__CYGWIN__)
# define ISDIRSEP(c) ((c) == '/')
+7
View File
@@ -919,6 +919,13 @@ _rl_isearch_callback (_rl_search_cxt *cxt)
int c, r;
c = _rl_search_getchar (cxt);
if (c < 0) /* EOF */
return 1;
if (RL_ISSTATE (RL_STATE_ISEARCH) == 0) /* signal could turn it off */
return 1;
/* We might want to handle EOF here */
r = _rl_isearch_dispatch (cxt, cxt->lastc);
+2 -2
View File
@@ -361,8 +361,8 @@ _rl_get_char_len (const char *src, mbstate_t *ps)
int mb_cur_max;
/* Look at no more than MB_CUR_MAX characters */
l = (size_t)strlen (src);
if (_rl_utf8locale && l > 0 && UTF8_SINGLEBYTE(*src))
l = strlen (src);
if (_rl_utf8locale && l >= 0 && UTF8_SINGLEBYTE(*src))
tmp = (*src != 0) ? 1 : 0;
else
{
+11 -2
View File
@@ -905,8 +905,17 @@ _rl_dispatch_subseq (register int key, Keymap map, int got_subseq)
{
/* Special case rl_do_lowercase_version (). */
if (func == rl_do_lowercase_version)
/* Should we do anything special if key == ANYOTHERKEY? */
return (_rl_dispatch (_rl_to_lower ((unsigned char)key), map));
{
/* Should we do anything special if key == ANYOTHERKEY? */
newkey = _rl_to_lower ((unsigned char)key);
if (newkey != key)
return (_rl_dispatch (newkey, map));
else
{
rl_ding (); /* gentle failure */
return 0;
}
}
rl_executing_keymap = map;
rl_executing_key = key;
+6
View File
@@ -853,7 +853,11 @@ _rl_insert_char (int count, int c)
rl_insert_text (string);
xfree (string);
#if defined (HANDLE_MULTIBYTE)
return (pending_bytes_length != 0);
#else
return 0;
#endif
}
if (count > TEXT_COUNT_MAX)
@@ -1112,6 +1116,8 @@ rl_quoted_insert (int count, int key)
r = _rl_insert_next (1);
while (r == 0 && ++count < 0);
}
else
r = _rl_insert_next (count);
if (r == 1)
_rl_insert_char (0, 0); /* insert partial multibyte character */
+11 -5
View File
@@ -112,9 +112,9 @@ set_default_locale_vars (void)
if (val == 0 && lc_all && *lc_all)
{
setlocale (LC_CTYPE, lc_all);
locale_setblanks ();
locale_mb_cur_max = MB_CUR_MAX;
locale_utf8locale = locale_isutf8 (lc_all);
locale_setblanks ();
# if defined (HANDLE_MULTIBYTE)
locale_shiftstates = mblen ((char *)NULL, 0);
@@ -219,11 +219,11 @@ set_locale_var (const char *var, const char *value)
else
internal_warning(_("setlocale: LC_ALL: cannot change locale (%s): %s"), lc_all, strerror (errno));
}
locale_setblanks ();
locale_mb_cur_max = MB_CUR_MAX;
/* if LC_ALL == "", reset_locale_vars has already called this */
if (*lc_all && x)
locale_utf8locale = locale_isutf8 (lc_all);
locale_setblanks ();
# if defined (HANDLE_MULTIBYTE)
locale_shiftstates = mblen ((char *)NULL, 0);
# else
@@ -243,11 +243,11 @@ set_locale_var (const char *var, const char *value)
if (lc_all == 0 || *lc_all == '\0')
{
x = setlocale (LC_CTYPE, get_locale_var ("LC_CTYPE"));
locale_setblanks ();
locale_mb_cur_max = MB_CUR_MAX;
/* if setlocale() returns NULL, the locale is not changed */
if (x)
locale_utf8locale = locale_isutf8 (x);
locale_setblanks ();
#if defined (HANDLE_MULTIBYTE)
locale_shiftstates = mblen ((char *)NULL, 0);
#else
@@ -396,10 +396,10 @@ reset_locale_vars (void)
retval = 0;
# endif
locale_setblanks ();
locale_mb_cur_max = MB_CUR_MAX;
if (x)
locale_utf8locale = locale_isutf8 (x);
locale_setblanks ();
# if defined (HANDLE_MULTIBYTE)
locale_shiftstates = mblen ((char *)NULL, 0);
# else
@@ -575,6 +575,12 @@ locale_expand (const char *string, int start, int end, int lineno, size_t *lenp)
}
#endif
/* Is character C in the [:blank:] class in the current locale? Work around
systems like macOS that treat some characters 0x80-0xff as blanks even in
a UTF-8 locale where they are multibyte characters. */
#define locale_isblank(c) \
((locale_utf8locale == 0 || ((c) & 0x80) == 0) && isblank ((unsigned char)(c)))
/* Set every character in the <blank> character class to be a shell break
character for the lexical analyzer when the locale changes. */
static void
@@ -584,7 +590,7 @@ locale_setblanks (void)
for (x = 0; x < sh_syntabsiz; x++)
{
if (isblank ((unsigned char)x))
if (locale_isblank (x))
sh_syntaxtab[x] |= CSHBRK|CBLANK;
else if (member (x, shell_break_chars))
{
BIN
View File
Binary file not shown.
+2 -2
View File
@@ -9,7 +9,7 @@ msgstr ""
"Project-Id-Version: bash-5.2-rc1\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2022-01-11 14:50-0500\n"
"PO-Revision-Date: 2023-05-01 16:11-0700\n"
"PO-Revision-Date: 2023-05-23 19:54-0700\n"
"Last-Translator: Božidar Putanec <bozidarp@yahoo.com>\n"
"Language-Team: Croatian <lokalizacija@linux.hr>\n"
"Language: hr\n"
@@ -4064,7 +4064,7 @@ msgstr ""
"\n"
" Opcije:\n"
" -f navedena IMENA se odnose samo na funkcije\n"
" -n ukloni izvezeni atribut iz svakog IMENA \n"
" -n ukloni izvezeni atribut iz svakog IMENA\n"
" -p izlista popis svih izvezenih varijabli i funkcija\n"
"\n"
" Argument „--“ spriječi daljnje procesiranje opcija.\n"