[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: bug with edit-and-execute-command and multiline commands
From: |
Chet Ramey |
Subject: |
Re: bug with edit-and-execute-command and multiline commands |
Date: |
Sat, 7 Aug 2021 13:56:20 -0400 |
User-agent: |
Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:78.0) Gecko/20100101 Thunderbird/78.10.0 |
On 8/6/21 9:49 PM, Emanuele Torre wrote:
Bash Version: 5.1
Patch Level: 8
Release Status: release
Description:
rwp suggested me to re report this bug via bashbug instead of using
savannah since it is the preferred method.
Here is the original savannah support report:
https://savannah.gnu.org/support/?110523
edit-and-execute-command seems to have odd and unintened behaviour
when used while bash is reading multiline commands that are
inconsistent between bash versions and patch levels.
Here are the main ones I noticed in bash 5.1-8.
If I type-in a multiline command in an interactive bash shell and
then use edit-and-execute-command, that command will get executed,
but bash will continue reading for the multiline command.
I think there's a basic misunderstanding of how edit-and-execute-command
works.
It's a bindable readline command. That means that not only does it not
interrupt or otherwise alter the command currently being parsed, it doesn't
cause the current call to readline() to return. It's a bindable command
like any other, executed in the context of a single call to readline().
From the shell's perspective, it's still reading and parsing the same
(multiline) command it was when it called readline().
The command essentially does the following: save the parsing state, save
the editing state, save the current command to a file, call the editor to
edit that file, then execute the result (the latter two steps are actually
accomplished by the `fc' builtin). Then it restores everything. The parser
is back to where it was: reading lines for a multiline command.
Example: if I type-in "if true" newline "then echo hi" newline "else
echo hello" newline "fi", and then I press \C-x\C-e (to trigger
edit-and-execute-command) and exit the editor, "hi" will be printed;
then, if I enter "echo hey" newline "echo good morning" and again
\C-x\C-e and close the editor, "hi", "hey", and "good morning" get
printed.
Because you're still parsing the original command. Nothing new gets saved
to the history list until readline() returns.
The behaviour is a bit different (but still probably not intended)
if the first line is "\" and the second line is a simple commands.
Example: "\" newline "ls /" \C-x\C-e, when I exit the editor the
command is executed; then:
You're still parsing the original command. edit-and-execute-command is
careful to save and restore the parsing state. That original command has
not been terminated; the shell is still at $PS2 waiting for the command
to be completed with a newline.
* if I type-in "echo hi" and then press enter, "hi" is printed and
I get back to the regular bash prompt.
The newline terminates the command.
* if I type-in "echo hi" and then use \C-x\C-e, the editor opens
with "ls / echo hi" and if I close it, "ls / echo hi" is run, and
then it keeps reading lines for the command;
This is how adding entries to the history works by default, since bash
tries hard to save commands to the history as a single entry, inserting
command terminators like `;' where necessary. There are no command
terminators here -- you're just parsing a simple command -- so it appends
the `echo hi' to the history entry with no intervening separators.
Bash leaves the partial command that `fc' operated on in the history; that
was covered in
https://lists.gnu.org/archive/html/bug-bash/2016-06/msg00063.html
and is responsible for the `additive' behavior you're seeing.
if I use \C-x\C-e,
it keeps adding the line as arguments of the command, otherwise,
if I press return, it executes the last line as a standalone
command and then it stops reading the multiline command and goes
back to the regular prompt.
The newline terminates the simple command.
NB: The second part of the second example only occurs the simple
command is an external command: "\" newline "echo hi" \C-x\C-e
"echo hello" \C-x\C-e opens the editor with "echo hi; echo hello",
not "echo hi echo hello"
I can't reproduce this behavior.
rwp told me that he experienced different (but still weird)
behaviours on older bash versions.
The save and restore of the parsing state has improved between bash
versions; I assume that's what is preventing the syntax error Bob saw in
bash-4.4.
--
``The lyf so short, the craft so long to lerne.'' - Chaucer
``Ars longa, vita brevis'' - Hippocrates
Chet Ramey, UTech, CWRU chet@case.edu http://tiswww.cwru.edu/~chet/