Smuggling files under Google's nose
This tale takes place at my office, where we use Google Mail/Chat for our internal communication needs. I'm pretty sure any dev in our situation has encountered that dreaded notice:
when trying to transfer some zip archives containing executables. Or more exactly, once the recipient tries to download it. Very annoying, and a challenge for stubborn nerds.
First blood: nested zips §
With my neighbouring colleague, we decided not to give up and use our clunky company NextCloud or return to USB drive throwing monke when we want to transfer files.
First joke try accompanied by a surely Google isn't that stupid
spoken aloud: file
extension swapping (e.g. .zip
-> .png
). Didn't work, almost
reassuringly.
The following fumbling around gave us a temporary solution: putting a zip within an encrypted zip (or was it the opposite?). You may understandably wonder why you'd need two zips: simple, zip encryption only applies to file contents, not metadata. Which means that Big Groogle can still see the stored file names and send your attachments to the iso-cubes based on that.
It did work, from memory, but was really too confusing and laborious, so it only survived as interesting trivia; which was broken by Google at some point any way.
Second skirmish: file signature doctoring §
After a few months, we decided to find a final solution to the problem. First, you must know
your enemy, which meant reading The Rules. A cursory Google (heh) search gave us the
following for Gmail and Gchat: basically,
multimedia/documents formats and archives containing those are allowed; explicitly banned are password-protected archives with archived content
. Damn.
From our failure with the extension swapping scheme, we inferred that Googleware must be
detecting zips using libmagic
to ascertain file
types. So we simply picked a format with a simple file signature to replace zip's leading PK
with: since the allowed BMP uses BM
, BMP it was. This is how gmail_zip.py
was born (in pure Python stdlib for our dear Windows lusers).
Final setback and victory §
A few days ago (actually the first time since then that we needed to use our masterpiece), it
stopped working. Why I couldn't say. Maybe Google strengthened their blocker to use whole file
content inspection, something like binwalk
? In the end, we decided
to reach for the big guns and simply encode length + data in image pixels. It's not like Google is
going to block our PNGs because they look like crappy modern art, right? This time, no Python, all
the Windows devs have Git Bash installed anyway so (mostly) POSIX sh and ImageMagick should do the
trick. img_store
brings us a well-deserved victory that we'll savour for as long as Google lets us.
PS: if someone knows a way to speed up POSIX dd ibs=1 count=###
without
having to write manual chunking (to replace head -c
), I'm all ears. Especially since
POSIX-2024 finally got us the all-important iflag=fullblock
.