Warum erweitert der Shell-expand-line-Befehl von GNU Readline nur das erste Auftreten von Tilde (~)?


7

Gemäß dem Bash-Handbuch shell-expand-linesollte der Befehl GNU Readline die Befehlszeile erweitern, so wie es Bash normalerweise tun würde, einschließlich Alias- und Verlaufserweiterung.

Die aktuelle Einstellung kann angezeigt werden mit bind -P | grep shell-expand-line:

shell-expand-line can be found on "\e\C-e".

Mein Problem ist, dass ~im folgenden Beispiel nur die erste tilde ( ) erweitert wird:

~/foo/bar ~/foo/baz

Nach dem Drücken von "\ e \ Ce":

/Users/nlykkei/foo/bar ~/foo/baz

Warum?


Sieht für mich wie ein Käfer aus. Noch seltsamer ist, dass echo *nichts geändert wird, sondern echo $(echo *)die Liste der Dateinamen im aktuellen Verzeichnis erweitert wird.
Gilles 'SO - hör auf böse zu sein'

Antworten:


4

Wenn Sie sich den Quellcode ansehen , werden Sie sehen, shell-expand-linedass er eigentlich heißen sollte shell-expand-line-as-if-it-were-a-word:

>> bashline.c
static int
shell_expand_line (count, ignore)
     int count, ignore;
{
     ...
      w->word = savestring (rl_line_buffer);
      w->flags = rl_explicit_arg ? (W_NOPROCSUB|W_NOCOMSUB) : 0;
      expanded_string = expand_word (w, rl_explicit_arg ? Q_HERE_DOCUMENT : 0);
>>> subst.c
/* Expand WORD, performing word splitting on the result.  This does
   parameter expansion, command substitution, arithmetic expansion,
   word splitting, and quote removal. */

WORD_LIST *
expand_word (word, quoted)
     WORD_DESC *word;
     int quoted;

Beachten Sie, dass dieser Kommentar weder Dateinamen noch Tilde-Erweiterung enthält. Es ist also im Grunde ein Zufall, dass es sogar für die erste Tilde funktioniert (Tilde hat sowieso nur am Anfang eines Wortes eine Bedeutung). Dies führt aber auch zu Prozessersetzungen, die ebenfalls nicht erwähnt werden. Das schwere Heben ist in der expand_word_internalFunktion in der gleichen Datei.

Das rl_explicit_argim ersten Snippet bedeutet, dass, wenn Sie Esc-1 oder Alt-2 drücken, bevor die Tastenkombination gebunden ist shell-expand-line, keine Anführungszeichen entfernt und kein Prozess / Befehl ersetzt wird. Ziemlich intuitiv, nicht wahr?

Sie können versuchen, einen Fehlerbericht einzureichen, aber es gibt wahrscheinlich bereits Tausende ähnlicher Einschränkungen und Sonderfälle wie diesen in bash.


Vielen Dank, ich denke, die Manpage ist dann etwas irreführend, weil sie besagt, dass der Befehl Readline die Zeile erweitert, wie es Bash normalerweise tun würde, oder interpretieren Sie die Dokumentation auf hoher Ebene anders?
Shuzheng

Die Manpage lügt. Versuchen Sie zB. mit einer Linie wie (bar=*; echo $bar)oder einfach echo *.
Mosvy

mosvy - werden Sie so freundlich sein, einen Link zum Quellcode bereitzustellen? :-)
Shuzheng

Ist git.savannah.gnu.org/cgit das offizielle Repository für alle (Standard-) Linux-Programme?
Shuzheng

Nein, nur für einige Programme. Wenn Sie auf Debian / Ubuntu sind, können Sie die genaue Quelle der von Ihnen verwendeten Programme (einschließlich Distribution-Patches) von erhalten apt-get source pkg-name.
Mosvy
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.