SC3026: [!0] causes history expansion in interactive zsh

maxnikulin
2023-04-18 18:32:39 +07:00
parent 9dfd253471
commit affd2f4213

@@ -18,6 +18,8 @@ echo foo-[!0]*.jpg
However, strictly speaking, the only range complement syntax guaranteed to be supported across shells is `[!c]`. POSIX explicitly states that behavior of `[^c]` is unspecified. Dash used to support `[^c]` when compiled with `fnmatch` and `glob` from glibc, but it was considered as a [bug](https://lore.kernel.org/dash/09fd70edcf08c75b4f9f2e158e3e6c0832d35d90.camel@scientia.org/t/#u) and fixed in version 0.5.12. Busybox has a similar [bug 14516](https://bugs.busybox.net/show_bug.cgi?id=14516). However, strictly speaking, the only range complement syntax guaranteed to be supported across shells is `[!c]`. POSIX explicitly states that behavior of `[^c]` is unspecified. Dash used to support `[^c]` when compiled with `fnmatch` and `glob` from glibc, but it was considered as a [bug](https://lore.kernel.org/dash/09fd70edcf08c75b4f9f2e158e3e6c0832d35d90.camel@scientia.org/t/#u) and fixed in version 0.5.12. Busybox has a similar [bug 14516](https://bugs.busybox.net/show_bug.cgi?id=14516).
In zsh interactive sessions `echo foo-[!0]*.jpg` may cause `zsh: event not found: 0` error due to attempt of history expansion. BASH however suppresses history expansion when `!` is first character in square brackets.
Discrepancy of negation syntax in regular expressions and shell pattern matching appeared in early UNIX versions. Pipeline syntax in shells had not settled yet, some terminals had no `|` key, so `^` was used there. That is why in some shells exclamation mark `!` was chosen instead of circumflex (caret) `^` symbol for negation in globs. For more details related to shell history see ["The `^` `=` `|` ?" thread](https://inbox.vuxu.org/tuhs/20030126014003.GA3818@sydney.worldwide.lemis.com/T/#u) in the Unix Heritage Society mailing list or [Sven Mascheck. The Traditional Bourne Shell Family. History and Development](https://www.in-ulm.de/~mascheck/bourne/) page. Discrepancy of negation syntax in regular expressions and shell pattern matching appeared in early UNIX versions. Pipeline syntax in shells had not settled yet, some terminals had no `|` key, so `^` was used there. That is why in some shells exclamation mark `!` was chosen instead of circumflex (caret) `^` symbol for negation in globs. For more details related to shell history see ["The `^` `=` `|` ?" thread](https://inbox.vuxu.org/tuhs/20030126014003.GA3818@sydney.worldwide.lemis.com/T/#u) in the Unix Heritage Society mailing list or [Sven Mascheck. The Traditional Bourne Shell Family. History and Development](https://www.in-ulm.de/~mascheck/bourne/) page.
### Exceptions: ### Exceptions: