[pacman-dev] [PATCH v3] makepkg: do not eval dlcmd
Dave Reisner
d at falconindy.com
Wed Jan 7 04:39:56 UTC 2015
On Wed, Jan 07, 2015 at 02:24:19PM +1000, Allan McRae wrote:
> On 08/09/14 02:57, lolilolicon wrote:
> > This eval enables the following in a PKGBUILD to "just work":
> >
> > source=('$pkgname-$pkgver.tar.gz'::'https://host/$pkgver.tar.gz')
> >
> > This has at least two problems:
> >
> > - It violated the principle of least surprise.
> > - It could be a security issue since URLs are arbitrary input.
> >
> > Instead, expand the dlagent command line into an array, replace the %o,
> > %u place holders, and run the resultant command line as is.
> >
> > Embedded spaces in the DLAGENTS entry can be escaped with a backslash.
> >
> > Fixes FS#41682
> > ---
>
> This is broken with bash<4.3. There are extra quotes everywhere in the
> command.
>
> bash-4.2
> + /usr/bin/curl -fLC - --retry 3 --retry-delay 3 -o '"64.tar.xz.part"'
> '"http://allanmcrae.com/tmp/64.tar.xz"'
>
> bash-4.3
> + /usr/bin/curl -fLC - --retry 3 --retry-delay 3 -o 64.tar.xz.part
> http://allanmcrae.com/tmp/64.tar.xz
>
> @Dave: any suggestions on how to fix.
>
>
I'm not clear on what the problematic quoting actually fixes. If it
actually has a purpose, I'm fairly confident that we can just neglect
the esoteric edge case it covers, and leave behind a TODO that we should
re-fix it once we're comfortable with bash 4.3 being the required
minimum.
> > scripts/makepkg.sh.in | 21 ++++++++++-----------
> > 1 file changed, 10 insertions(+), 11 deletions(-)
> >
> > diff --git a/scripts/makepkg.sh.in b/scripts/makepkg.sh.in
> > index 8e8a64c..446e9b0 100644
> > --- a/scripts/makepkg.sh.in
> > +++ b/scripts/makepkg.sh.in
> > @@ -342,8 +342,9 @@ download_file() {
> > local proto=$(get_protocol "$netfile")
> >
> > # find the client we should use for this URL
> > - local dlcmd
> > - dlcmd=$(get_downloadclient "$proto") || exit $?
> > + local -a cmdline
> > + IFS=' ' read -a cmdline < <(get_downloadclient "$proto")
> > + (( ${#cmdline[@]} )) || exit
> >
> > local filename=$(get_filename "$netfile")
> > local url=$(get_url "$netfile")
> > @@ -359,20 +360,18 @@ download_file() {
> > local dlfile="${url##*/}"
> >
> > # replace %o by the temporary dlfile if it exists
> > - if [[ $dlcmd = *%o* ]]; then
> > - dlcmd=${dlcmd//\%o/\"$filename.part\"}
> > - dlfile="$filename.part"
> > + if [[ ${cmdline[*]} = *%o* ]]; then
> > + dlfile=$filename.part
> > + cmdline=("${cmdline[@]//%o/"$dlfile"}")
> > fi
> > # add the URL, either in place of %u or at the end
> > - if [[ $dlcmd = *%u* ]]; then
> > - dlcmd=${dlcmd//\%u/\"$url\"}
> > + if [[ ${cmdline[*]} = *%u* ]]; then
> > + cmdline=("${cmdline[@]//%u/"$url"}")
> > else
> > - dlcmd="$dlcmd \"$url\""
> > + cmdline+=("$url")
> > fi
> >
> > - local ret=0
> > - eval "$dlcmd >&2 || ret=\$?"
> > - if (( ret )); then
> > + if ! command -- "${cmdline[@]}" >&2; then
> > [[ ! -s $dlfile ]] && rm -f -- "$dlfile"
> > error "$(gettext "Failure while downloading %s")" "$filename"
> > plain "$(gettext "Aborting...")"
> >
More information about the pacman-dev
mailing list