Skip to content

read-only · compressed · deduplicating

Pack a whole tree into one file. Start from it fast.

stipplefs is a filesystem image format and FUSE mount for Linux. It packs a directory into a single compressed, deduplicated, checksummed file, then mounts it so an application starts almost as fast as it would from disk.

1.4 GiB → 453 MiB
packed into one image with 32 MiB blocks
0.73 s
first launch, mount included, against 0.50 s from a plain folder
0.50 s
every launch after that, the same as from a plain folder
437 MiB
held by the mount daemon while the application starts

Blender 5.2, a 1.4 GiB application tree, packed with the defaults and a hot list, then launched in the background on a 16-thread machine. The build took 86 seconds. How the defaults were chosen

What goes into an image

Start-up comes first

Files an application opens while starting go to the front of the image. Background workers decode them and hand the bytes to the kernel page cache before anything asks.

Deduplication inside files

Content-defined chunking finds shared runs of bytes between files that differ, so near-copies cost almost nothing.

Executables shrink further

Every block is also tried through an x86 branch filter, and the smaller encoding wins. Native code gives the compressor far more to work with.

Checksummed throughout

The superblock, every metadata section and every block carry an XXH3 digest. Nothing is returned before it is verified.

Lives inside other files

Every offset is relative to the image, so an image can sit at any position inside a launcher, an executable or an archive.

Specified, not just implemented

A normative spec, checked by an independent reader in the test suite, with a canonical encoding that makes builds reproducible.

A cold start, step by step

  1. 1

    Mount

    The superblock and metadata are verified, then the mount answers lookups at once.

  2. 2

    Warm

    Workers decode the hot region, one block each, in parallel.

  3. 3

    Store

    Decoded file bytes go straight into the kernel's page cache.

  4. 4

    Run

    The application reads from memory. Blocks it never asks for are never decoded.

Three commands

Build an image from a directory, verify every byte of it, and mount it. The same image can be extracted back to a directory or read straight from Rust.

Walk through the quick start →
$ mkstipple /usr/lib/python3.14 python.stipple
building python.stipple from /usr/lib/python3.14: block size 33554432, level 19, 16 threads
[    0.7s] placing      3595/3595 files, 69.2 MiB read
[   18.1s] compressing  2/2 blocks, 53.8 -> 12.3 MiB (22.9%), 3.1 MiB/s
wrote python.stipple (12959744 bytes) from /usr/lib/python3.14

$ stipple check python.stipple | tail -1
verified        72555234 bytes read and checksummed in 0.084 s (827.8 MB/s)

$ stipple mount python.stipple ~/mnt
mounted on /home/you/mnt, interrupt to unmount

Small format. Short spec. Fast start.

One Rust crate, two command-line tools, and a specification precise enough to write your own reader.

Released under the MIT or Apache 2.0 license, at your option.