Since expanding a prompt string that contains a funsub will modify the value of $_, would it make sense to restore the value of $_ after the expansion is complete, as we do when executing PROMPT_COMMAND?
$ PS0='${ : X; }' bash --norc bash-5.3$ : A bash-5.3$ echo $_ X P.S. Technically, it was also possible to modify the value of $_ during prompt string expansion even before the addition of funsubs by doing a direct assignment to `_' in an arithmetic expansion, something like: PS1='${X[_=1]}$ ' but I hope that there is not a legitimate use case for preserving a $_ value so modified past the prompt string expansion phase, as this patch will also cause such an assignment to be reverted. --- parse.y | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/parse.y b/parse.y index e1e64f5c..57b13aa1 100644 --- a/parse.y +++ b/parse.y @@ -6126,7 +6126,7 @@ char * decode_prompt_string (char *string) { WORD_LIST *list; - char *result, *t, *orig_string; + char *result, *t, *orig_string, *last_lastarg; struct dstack save_dstack; int last_exit_value, last_comsub_pid, last_comsub_status; #if defined (PROMPT_STRING_DECODE) @@ -6535,10 +6535,15 @@ not_escape: last_exit_value = last_command_exit_value; last_comsub_pid = last_command_subst_pid; last_comsub_status = last_command_subst_status; + last_lastarg = get_string_value ("_"); + if (last_lastarg) + last_lastarg = savestring (last_lastarg); list = expand_prompt_string (result, Q_DOUBLE_QUOTES, 0); free (result); result = string_list (list); dispose_words (list); + bind_lastarg (last_lastarg); + FREE (last_lastarg); last_command_exit_value = last_exit_value; last_command_subst_pid = last_comsub_pid; last_command_subst_status = last_comsub_status; -- 2.43.0