after they return by adding an unwind-protect function
uw_restore_verbose()
Report and patch from Grisha Levit <grishalevit@gmail.com>
+
+ 5/18
+ ----
+doc/bash.1,doc/bashref.texi
+ - note that PS0 and PS4 are not fed to readline, so they shouldn't
+ contain the \[ and \] prompt escapes
+
+parse.y
+ - decode_prompt_string: if we're decoding a prompt string (is_prompt == 1),
+ ignore \[ and \] unless the prompt is PS1 or PS2.
+ Report from Egmont Koblinger <egmont@gmail.com>
+
+ 5/19
+ ----
+lib/readline/display.c
+ - rl_redisplay: when deciding whether or not to reprint the prompt from
+ column 0 because the cursor is before the last invisible character,
+ use local_prompt_len to compute index into the buffer in a multibyte
+ locale, since _rl_last_c_pos is a screen position. This still doesn't
+ fix the eventual redisplay breakage if readline starts with the
+ cursor somewhere other than column 0
+ Fixes issue reported by Lennart Ackermans <lennart@ackermans.ch>
+
+ 5/20
+ ----
+builtins/getopt.c
+examples/loadables/seq.c
+lib/sh/mbschr.c,lib/sh/utf8.c
+pathexp.c
+examples/loadables/seq.c
+ - fixes for `const' and gcc 15
+ Report and patch from Grisha Levit <grishalevit@gmail.com>
+
+ 5/21
+ ----
+subst.c
+ - string_list_dollar_atstar: fix memory leak by calling dispose_words(l2)
+ after the call to word_list_split(l2)
+ Report from Grisha Levit <grishalevit@gmail.com>
+
+ 5/22
+ ----
+lib/readline/display.c
+ - _rl_redisplay_after_sigwinch: call _rl_reset_prompt every time, so
+ the local_prompt_invis_chars array gets updated along with the
+ local_prompt_newlines array
+ Report and fix from Félix Bouynot <felix.bouynot@setenforce.one>
+
+ 5/25
+ ----
+builtins/mapfile.def
+ - mapfile: the callback can leave the variable in an inconsistent
+ state, or even unset it, so we use bind_array_variable to look it
+ up again every time through the loop
+ Report and patch from Philippe Grégoire <git@pgregoire.xyz>
/* getopt.c - getopt for Bash. Used by the getopt builtin. */
-/* Copyright (C) 1993-2009,2022 Free Software Foundation, Inc.
+/* Copyright (C) 1993-2009,2022,2026 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
int
sh_getopt (int argc, char *const *argv, const char *optstring)
{
- char c, *temp;
+ char c;
+ const char *temp;
sh_optarg = 0;
line_length = 0;
unbuffered_read = 0;
- /* The following check should be done before reading any lines. Doing it
- here allows us to call bind_array_element instead of bind_array_variable
- and skip the variable lookup on every call. */
+ /* The following check should be done before reading any lines. */
entry = builtin_find_indexed_array (array_name, flags & MAPF_CLEARARRAY);
if (entry == 0)
return EXECUTION_FAILURE;
run_callback (callback, array_index, line);
}
- /* XXX - bad things can happen if the callback modifies ENTRY, e.g.,
- unsetting it or changing it to a non-indexed-array type. */
+ /* Bad things can happen if the callback modifies ENTRY, e.g.,
+ unsetting it or changing it to a non-indexed-array type, so we
+ look it up again every time we need to assign something */
+ entry = bind_array_variable (array_name, array_index, line, 0);
+ if (entry == 0 || ASSIGN_DISALLOWED (entry, 0))
+ return EXECUTION_FAILURE;
+
bind_array_element (entry, array_index, line, 0);
/* Have we exceeded # of lines to store? */
.\" Case Western Reserve University
.\" chet.ramey@case.edu
.\"
-.\" Last Change: Wed May 6 16:08:33 EDT 2026
+.\" Last Change: Mon May 18 11:35:35 EDT 2026
.\"
.\" For bash_builtins, strip all but "SHELL BUILTIN COMMANDS" section
.\" For rbash, strip all but "RESTRICTED SHELL" section
.ds zX \" empty
.if \n(zZ=1 .ig zZ
.if \n(zY=1 .ig zY
-.TH BASH 1 "2026 May 6" "GNU Bash 5.3"
+.TH BASH 1 "2026 May 18" "GNU Bash 5.3"
.\"
.ie \n(.g \{\
.ds ' \(aq
.B bash
prints a message to standard error indicating failure,
does not perform the substitution,
-and does not execute the command associated with the expansion.
+and does not
+continue to execute the command in which the error occurs.
.SS Process Substitution
\fIProcess substitution\fP allows a process's input or output to be
referred to using a filename.
\fB<(\fP\fIlist\^\fP\fB)\fP
or
\fB>(\fP\fIlist\^\fP\fB)\fP.
-The process \fIlist\fP is run asynchronously, and its input or output
+The process \fIlist\fP,
+as long as it is not a null command without redirections,
+is run asynchronously, and its input or output
appears as a filename.
This filename is
passed as an argument to the current command as the result of the
.B \e[
Begin a sequence of non-printing characters, which could be used to
embed a terminal control sequence into the prompt.
+This escape is only useful when the prompt will be supplied to
+\fBreadline\fP, so it shouldn't be used in \fBPS0\fP or \fBPS4\fP.
.TP
.B \e]
-End a sequence of non-printing characters.
+End a sequence of non-printing characters begun with
+.BR \e[ .
.PD
.RE
.PP
If the expression is invalid, Bash prints a message indicating
failure to the standard error,
does not perform the substitution,
-and does not execute the command associated with the expansion.
+and does not
+continue to execute the command in which the error occurs.
@node Process Substitution
@subsection Process Substitution
>(@var{list})
@end example
@noindent
-The process @var{list} is run asynchronously, and its input or output
+The process @var{list},
+as long as it is not a null command without redirections,
+is run asynchronously, and its input or output
appears as a filename.
This filename is
passed as an argument to the current command as the result of the
Begin a sequence of non-printing characters.
This could be used to
embed a terminal control sequence into the prompt.
+This escape is only useful when the prompt will be supplied to
+Readline, so it shouldn't be used in @env{PS0} or @env{PS4}.
+
@item \]
-End a sequence of non-printing characters.
+End a sequence of non-printing characters begun with @samp{\[}
@end table
The command number and the history number are usually different:
Copyright (C) 1988-2026 Free Software Foundation, Inc.
@end ignore
-@set LASTCHANGE Wed May 6 16:08:14 EDT 2026
+@set LASTCHANGE Mon May 18 11:35:01 EDT 2026
@set EDITION 5.3
@set VERSION 5.3
-@set UPDATED 6 May 2026
+@set UPDATED 18 May 2026
@set UPDATED-MONTH May 2026
"processes to successive elements of ARRAY, beginning at 0. The",
"strings cut assigns to ARRAY are identical to the strings it would",
"write to the standard output if -a were not supplied.",
+ "",
+ "-s stops printing of lines not containing delimiters. -n is ignored.",
(char *)NULL
};
/* seq - print sequence of numbers to standard output.
- Copyright (C) 2018-2022 Free Software Foundation, Inc.
+ Copyright (C) 2018-2026 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
getprec (const char *numbuf)
{
int p;
- char *dp;
+ const char *dp;
if (dp = strchr (numbuf, decimal_point))
dp++; /* skip over decimal point */
/* display.c -- readline redisplay facility. */
-/* Copyright (C) 1987-2025 Free Software Foundation, Inc.
+/* Copyright (C) 1987-2026 Free Software Foundation, Inc.
This file is part of the GNU Readline Library (Readline), a library
for reading lines of text with interactive input and history editing.
the characters from the current cursor position. But we
only need to reprint it if the cursor is before the last
invisible character in the prompt string. */
- /* XXX - why not use local_prompt_len? */
nleft = prompt_visible_length + wrap_offset;
if (cursor_linenum == prompt_last_screen_line)
{
on the current screen line begins in the buffer. It is a
buffer position, an index into curline
(local_prompt + pmt_offset) */
- cursor_bufpos = pmt_offset;
- if (mb_cur_max == 1 || rl_byte_oriented)
- cursor_bufpos += _rl_last_c_pos;
- else
- cursor_bufpos += _rl_last_c_pos + curline_invchars;
+ cursor_bufpos = pmt_offset + local_prompt_len;
if (local_prompt && local_prompt_invis_chars[cursor_linenum] &&
_rl_last_c_pos > 0 &&
else
rl_crlf ();
- if (_rl_screenwidth < prompt_visible_length)
- _rl_reset_prompt (); /* update local_prompt_newlines array */
+ /* Let expand_prompt() update local_prompt_newlines and local_prompt_invis_chars
+ arrays */
+ _rl_reset_prompt ();
/* Redraw only the last line of a multi-line prompt. */
t = strrchr (rl_display_prompt, '\n');
/* mbschr.c - strchr(3) that handles multibyte characters. */
-/* Copyright (C) 2002 Free Software Foundation, Inc.
+/* Copyright (C) 2002-2026 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
}
else
#endif
- return (strchr (s, c));
+ return ((char *)strchr (s, c));
}
/* utf8.c - UTF-8 character handling functions */
-/* Copyright (C) 2018, 2022 Free Software Foundation, Inc.
+/* Copyright (C) 2018, 2022, 2026 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
char *
utf8_mbschr (const char *s, int c)
{
- return strchr (s, c); /* for now */
+ return (char *)strchr (s, c); /* for now */
}
int
#if defined (READLINE)
case '[':
case ']':
- if (no_line_editing)
+ if (no_line_editing || (is_prompt && decoding_prompt != ps1_prompt && decoding_prompt != ps2_prompt))
{
string++;
break;
/* pathexp.c -- The shell interface to the globbing library. */
-/* Copyright (C) 1995-2024 Free Software Foundation, Inc.
+/* Copyright (C) 1995-2024,2026 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
glob_name_is_acceptable (const char *name)
{
struct ign *p;
- char *n;
+ const char *n;
int flags;
/* . and .. are never matched. We extend this to the terminal component of a
don't want here. */
l = word_list_split (l2); /* pre-split, preserving empty arguments */
+ dispose_words (l2);
+
/* We want to turn words that are QUOTED_NULL with W_HASQUOTEDNULL set in
the word flags back into "" but leave every other $'\177' alone. */
for (l2 = l; l2; l2 = l2->next)
free (sep);
#endif
- dispose_words (l2);
dispose_words (l);
return ret;
*valp = temp ? savestring (temp) : temp;
}
}
+#if 0 /* TAG:bash-5.4 2026/05/11 YourLi@outlook.com */
+ /* For ksh93 compatibility, ${!ref} where ref is a non-special, nameref
+ variable, should expand to the value of ref, without resolving any
+ nameref chain. Previous versions treated an array variable without a
+ subscript the same as ref[0] (next clause). */
+ else if (shell_compatibility_level > 53 &&
+ want_indir && value && vtype == VT_VARIABLE &&
+ SPECIAL_VAR (varname, 1) == 0 &&
+ (v = find_variable_noref (varname + 1)) &&
+ nameref_p (v))
+ {
+ /* This is for compatibility with ksh93. */
+ vtype = VT_VARIABLE;
+ *varp = v;
+ *valp = savestring (value);
+ }
+#endif
else if ((v = find_variable (vname)) && (invisible_p (v) == 0) && (assoc_p (v) || array_p (v)))
{
vtype = VT_ARRAYMEMBER;