Fitting Snake Into A QR Code

QR codes are usually associated with ASCII text like URLs or serial numbers, but did you know you can also encode binary data into them? To demonstrate this concept, [MattKC] embarked on a journey to create a QR code that holds an executable version of Snake. Video after the break.

As you might expect, the version 40 QR code he ended up using is much larger than the ones you normally see. Consisting of a 171 by 171 grid, it’s the largest version that can still be read by most software. This gave [MattKC] a whopping 2,953 bytes to work with. Not a lot of space, but still bigger than some classic video games of the past.

To start, he first wrote Snake to run in a web browser using HTML, CSS, and JavaScript, which was able to fit in the available space. Modern browsers do a lot of the lifting with built-in features, and [MattKC] wanted more of a challenge, so he decided to instead create a Windows executable file. His first attempts with compiled C code were too large, which led down the rabbit trail of x86 Assembly. Here he found that his knowledge of Assembly was too limited to create a small enough program without investing months into the project. He went back to C and managed to compress his executable using Crinkler, a compressing linker commonly used in the demoscene. This shrunk the file down to 1,478 bytes.

Zbar, a command-line barcode reader for Windows was used to test the final Snake QR code. [MattKC] discovered a bug in Zbarcam that prevented it from reading binary data via a webcam input, so through the power of open source, he submitted a bug fix which is now integrated into the official release.

All the files are available for anyone to play with on [MattKC]’s website. The video below goes into a lot of detail on the entire journey. Since this project proves software can be embedded in QR codes, it means that malware could also be hidden in a QR code, if there is an exploitable bug somewhere in a smartphone QR reader app.

QR codes are an interesting tool with a variety of uses. Take a deep dive into how they work, generate a 3D printable version, or build a QR jukebox, if you want to learn more.

18 thoughts on “Fitting Snake Into A QR Code

    1. it would be impossible to fit doom as even the largest size is 2953 bytes while the steam release of doom is 30,347,264 bytes. even DOOM.WAD wouldn’t fit as it is 12,408,292 bytes.

  1. Sure you can hide malware in binary form in a QR code, but you have to manually extract and run the file. If you find a buffer overflow in a protocol handler for VCards or similar in your QR Reader App, that would be exploitable and a serious issue.

    1. I was about to say the same thing. I remember reading about the e-Reader from a pamphlet or promotional book or something, and then sitting down with a friend and trying to calculate out the maximum bits per card. At the time it didn’t even occur to me that they might do some kind of compression.

      This makes me want to go back and learn more about the compression and implementation process.

  2. The PICO-8 console/game engine stores its games in a file they call a “cartridge”. That file can either be the raw binary .p8 file, or as a steganographically-encoded image file! You download a .p8.png file, and it will open up in an image viewer and appear as a screenshot of the game – but if you load it in to the P8 console, it runs the game itself!

    Here’s an example – this image file *IS* the game code: https://blog.lmorchard.com/uploads/2016/poke-the-mongo/poke-the-mongo.p8.png

Leave a Reply

Please be kind and respectful to help make the comments section excellent. (Comment Policy)

This site uses Akismet to reduce spam. Learn how your comment data is processed.