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

Re: Bug in Functions/Misc/regexp-replace



2021-04-29 19:53:52 -0400, Jacob Menke:
[...]
> regexp-replace str 'a' 'z' && echo $str
> 
> Actual Output:
> (eval):1: bzd not found
> 
> Expected:
> x :=bzd
[...]

One might argue there's a problem with the (q) parameter
expansion flag, it escapes leading =s but not the =s that follow
: even though they're special there in assignments.

$ echo a=x:=y
a=x:=y
$ a=x:=y
zsh: y not found

BTW, zsh is the only shell where ~ is expanded in:

$ zsh -c 'a=a\:~; echo $a'
a:/home/chazelas

[...]
> One way to fix:
> 41: eval ${1}=${(qqq)5}

The safest quoting operator is the (qq) one. I wouldn't use any
other for things to be reinput to the shell.

See
https://unix.stackexchange.com/questions/379181/escape-a-variable-for-use-as-content-of-another-script/600214#600214
for details on that.

In particular qqq uses double quotes inside which \ and ` are
still special and those characters also appear in the encoding
of some other characters in some locales.

But here, the best thing to do is to not expose the parser to
the contents of $5 by doing:

eval "$1=\$5"

(which tells the shell to evaluate varname=$5)

You need to expand $1 here which contains the variable name.

Note that as already noted at
https://www.zsh.org/mla/workers/2019/msg01113.html
whether you use that or

: ${(P)1::="$5"}

You'll still have a command injection vulnerability if $1 is not
guaranteed to be a variable name.

-- 
Stephane




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