Zsh Mailing List Archive
Messages sorted by: Reverse Date, Date, Thread, Author

Re: Bug in completion with curly braces?



Felipe Contreras wrote on Fri, 20 Nov 2020 01:50 +00:00:
>   compadd -Q -- 'stash@{0}' 'stash@{1}'
> 
> The first completion correctly generates "stash@{", but the second one
> generates curly braces, the third one does the same, and so on ad
> infinitum.
> 

I can reproduce this in «zsh -f» zsh-5.8-259-g00d20ed.  I don't get a segfault.

> I didn't specify file (-f) or any special completion, so why would zle
> attempt curly brace expansion, especially if the words contain curly
> braces, and the current character is a curly brace?

Inserting the braces into the command line unescaped is correct since -Q
was passed to compadd.  (Note that when -Q is not provided, the braces
_are_ inserted escaped.)

Treating them as starting a brace expansion is also correct, because -Q
doesn't disable that part of the grammar.  -Q only means that when a
candidate completion is inserted into the command line, the inserted
word doesn't get escaped (e.g., compare «compadd 'foo$bar'» to «compadd
-Q 'foo$bar'»).  If that word contains metacharacters (e.g., «compadd -Q
'|| /bin/echo hello world'»), then -Q makes it the caller's
responsibility to escape them as needed.

Consequently, brace expansion is presumably attempted for the same
reason it s attempted when the words don't contain braces.  E.g., after
«compadd -Q bar baz» followed by «foo ba{<TAB>», it offers «r» and «z»
as completions, which let you build up «{bar,baz}» and «{baz,bar}»
respectively.  Similarly, given «stash@{<TAB>», it presumably takes the
brace for the start of a brace expansion, and the analogous construct
which that behaviour lets you build up is «stash@{\{0\},\{1\}}» or
«stash@{\{1\},\{0\}}» — except that when you press <TAB> a second time,
the newly-inserted brace is once again inserted unescaped, which
presumably gets handled as the start of a nested brace expansion.

As to -f, curly brace expansion is perfectly valid for arguments that
aren't filenames, such as «compadd -Q stash@\{{0,1}\}».  (Brace
expansion is several layers removed from filenameness checks, which is
why stuff like «ls {-{l,d},/bin}» works.)

You can probably just remove the -Q.

Daniel




Messages sorted by: Reverse Date, Date, Thread, Author