Last year, I worked on a vulnerability in Zimbra
(CVE-2022-41352 - my
AttackerKB analysis for Rapid7)
that turned out to be a new(-ish) exploit path for a really old bug in cpio
-
CVE-2015-1194. But that was patched in 2019, so what happened?
(I posted this as a tweet-thread awhile back, but I decided to flesh it out and make it into a full blog post!)
cpio
is an archive tool commonly used for system-level stuff (firmware images
and such). It can also extract other format, like .tar
, which we’ll use since
it’s more familiar.
cpio
has a flag (--no-absolute-filenames
), off by default,
that purports to prevent writing files outside of the target directory. That’s
handy when, for example, extracting untrusted files with Amavis
(like Zimbra does).
The problem is, symbolic links can point to absolute paths, and therefore, even
with --no-absolute-filenames
, there was no safe way to extract an untrusted
archive (outside of using a chroot
environment or something similar, which
they really ought to do).
Much later, in 2019, the cpio
team released cpio
version 2.13, which
includes a patch for
CVE-2015-1194,
with unit tests and everything.
Some (not all) modern OSes include the patched version of cpio, which should be the end of the story, but it’s not!
I’m currently writing this on Fedora 35, so let’s try exploiting it. We can
confirm that the version of cpio
installed with the OS is, indeed, the fixed
version:
[email protected] ~ $ cpio --version
cpio (GNU cpio) 2.13
Copyright (C) 2017 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Written by Phil Nelson, David MacKenzie, John Oleynick,
and Sergey Poznyakoff.
That means that we shouldn’t be able to use symlinks to write outside of the
target directory, so let’s create a .tar
file that includes a symlink and a
file written through that symlink (this is largely copied from
this mailing list post:
So now we have a .tar
with a symlink that goes outside the directory:
[email protected] ~/cpiotest $ tar -tvf ./demo.tar
lrwxrwxrwx ron/ron 0 2023-01-13 15:03 demo -> /tmp/
-rw-r--r-- ron/ron 6 2023-01-13 15:03 demo/imafile
In theory, we shouldn’t be able to extract that. Certainly, we can’t with the
standard tar
executable:
[email protected] ~/cpiotest $ tar -xvf ./demo.tar
demo
demo/imafile
tar: demo/imafile: Cannot open: Not a directory
tar: Exiting with failure status due to previous errors
And we shouldn’t be able to with cpio
, since it’s patched…. right?
Wait, what’s happening? This messed me up for awhile! By all accounts, the
current version of cpio
on a nearly-current version of Fedora shouldn’t be
vulnerable, but it is!
I did some spelunking into the source RPMs and DEBs, and found that both Red Hat and Debian (and all derived OSes) specifically remove the patch, citing this forum post where somebody ran into a bug with initrd!
The mailing list post, from 2019, says they’ll look into how to fix this, but as
far as I can tell, nobody ever did. I imagine that removing
--no-absolute-filenames
would fix it, but I don’t think anybody actually
looked into this.
Years later, we come to find out that Zimbra uses Amavis, which uses cpio
by
default (if pax isn’t installed). We found it out because somebody got
exploited, and was kind enough to
post details about the compromise.
Since I had seen and written about
a very similar vulnerability recently, I recognized what was going on in the
forum post. The biggest hurdle was the confusion about why modern systems are
impacted!
Zimbra did roll out a fix eventually - specifically, Zimbra now requires the
pax
executable, which is not vulnerable. We
wrote a blog about this back in October when it was new.
One more fun fact.. Ubuntu 18.04 (and as far as I can tell, ONLY Ubuntu 18.04)
backported the patch to cpio 2.12, which really confused my research! I just
happened to be testing Zimbra on Ubuntu 18.04, which includes cpio
version
2.12, which should be vulnerable, but it wasn’t!
It took me awhile to unravel all the weirdness, and I’m happy to report that it’s all sorted out now.