Christian Weisgerber:
> * archivers/unzip (zipgrep) -- AFFECTED
> archive member names are extracted with unzip -Z1, which renders
> \n as ^J. However, the result is processed by shell command
> substitution, so it undergoes field splitting and pathname
> expansion. If a file with an exploitable name is present in the
> current working directory, a archive member with a shell wildcard
> in its name may inadvertently feed it to sed. Yes, it's convoluted.
> The xzgrep fix can be applied.
Patch below.
The zipgrep script is not robust and will fail (harmlessly) with
adversarial filenames.
The patch addresses this case:
$ touch 'a
> b'
$ touch 'a*'
$ zip x.zip a*
adding: a^Jb (stored 0%)
adding: a* (stored 0%)
$ zipgrep.old foo x.zip
caution: filename not matched: a^Jb
sed: 1: "s|^|a
b:|": unescaped newline inside substitute pattern
$ zipgrep foo x.zip
caution: filename not matched: a^Jb
OK?
Index: Makefile
===================================================================
RCS file: /cvs/ports/archivers/unzip/Makefile,v
retrieving revision 1.67
diff -u -p -r1.67 Makefile
--- Makefile 11 Mar 2022 18:16:25 -0000 1.67
+++ Makefile 13 Apr 2022 21:53:40 -0000
@@ -5,7 +5,7 @@ COMMENT = extract, list & test files in
VERSION = 6.0
DISTNAME = unzip${VERSION:S/.//}
PKGNAME = unzip-${VERSION}
-REVISION = 14
+REVISION = 15
CATEGORIES = archivers
MASTER_SITES = ${MASTER_SITE_SOURCEFORGE:=infozip/} \
ftp://ftp.info-zip.org/pub/infozip/src/
Index: patches/patch-unix_zipgrep
===================================================================
RCS file: patches/patch-unix_zipgrep
diff -N patches/patch-unix_zipgrep
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ patches/patch-unix_zipgrep 13 Apr 2022 21:53:40 -0000
@@ -0,0 +1,18 @@
+Index: unix/zipgrep
+
+CVE-2022-1271
+Prevent arbitrary-file-write vulnerability if an archive member
+name contains shell wild cards that expand to an existing pathname
+with an exploit pattern.
+
+--- unix/zipgrep.orig
++++ unix/zipgrep
+@@ -70,7 +70,7 @@ for i in `unzip -Z1 "$zipfile" ${1+"$@"} | sed -e 's/\
+ # Escape (or re-escape) shell-special characters in the archive
+ # member name, "i".
+ i=` echo "$i" | \
+- sed -e 's/\\\\/\\\\\\\\/g' -e 's/|/\\\|/g' -e 's/&/\\\&/g' `
++ sed -e 's/\\\\/\\\\\\\\/g' -e 's/|/\\\|/g' -e 's/&/\\\&/g' -e
'$!s/$/\\\\/' `
+
+ # Globally, send fd 4 to stdout. In the pipeline, send normal
+ # stdout to fd 4, and send grep status to fd 3. Collect fd 3
--
Christian "naddy" Weisgerber [email protected]