
Stop sending naked documents. Firemark watermarks images & PDFs in one command. Optimized to tackle AI watermark removal. Written in Rust.
A fast, single-binary watermarking tool for images and PDFs. Built in Rust.
Every year, millions of people fall victim to identity fraud that starts with a simple document exchange. A common scenario: you're looking for a flat to rent. The landlord — or someone posing as one — asks for a copy of your ID, a pay stub, a tax notice. You send them unmarked. The "landlord" disappears, and your documents are now used to open bank accounts, take out loans, or forge identities in your name.
Watermarking every document you send out is the single most effective defence. A visible overlay that reads "Sent to XYZ agency — March 2026 — flat rental application only" makes the document useless for any other purpose. If it leaks, you know exactly where it came from.
firemark makes this effortless: one command, any image or PDF, 17 visual styles, cryptographic filigrane patterns that resist editing, and batch processing for entire folders.
Before and after — one command, document is now traceable and tamper-evident.
Pre-built binary (Linux & macOS, x86_64 & arm64) — downloads the latest release into ~/.local/bin:
curl -fsSL https://raw.githubusercontent.com/Vitruves/firemark/main/install.sh | sh
Windows binaries are attached to each release.
From crates.io:
cargo install firemark
From source:
git clone https://github.com/Vitruves/firemark.git
cd firemark
cargo install --path .
Produces a single optimized binary (~5 MB).
# Watermark a single image
firemark photo_id.png -m "Flat rental — SCI Dupont — March 2026"
# Watermark a PDF
firemark tax_notice.pdf -m "CONFIDENTIAL" -s "Do not distribute"
# Watermark an entire folder recursively
firemark ./documents/ -R -m "Sent to Agency X" -t stamp
# Preview without writing files
firemark id_card.jpg -m "Draft" -n
Output is saved alongside the input as {name}-watermarked.{ext} by default.
Use -o to set an explicit output path, or -S for a custom suffix.
| Flag | Style | Description |
|---|---|---|
diagonal | Diagonal grid | Full-page repeating diagonal text (default) |
stamp | Rubber stamp | Large centred stamp with double border |
stencil | Stencil | Full-width military stencil lettering |
typewriter | Typewriter | Monospaced typewriter text |
handwritten | Signature | Handwritten-style signature with underline |
redacted | Redaction | Full-width black redaction bars |
badge | Shield | Security shield/badge emblem |
ribbon | Ribbon | Diagonal corner ribbon banner |
seal | Seal | Circular notary-style seal |
frame | Frame | Full-page decorative border |
tile | Tile | Dense uniform text grid |
mosaic | Mosaic | Randomised scattered text |
weave | Weave | Interlocking diagonal weave |
ghost | Ghost | Ultra-subtle embossed text |
watercolor | Watercolour | Soft blurred wash effect |
noise | Noise | Distressed text with pixel noise |
halftone | Halftone | Text as halftone dot grid |
firemark doc.pdf -t stamp -m "CONFIDENTIAL" --border --color red
firemark overlays cryptographic filigrane patterns inspired by banknote security features. These fine geometric patterns are extremely difficult to remove with image editors.
| Style | Description |
|---|---|
guilloche | Sinusoidal wave envelope bands (default) |
rosette | Spirograph + corner rose curves |
crosshatch | Fine diagonal diamond lattice |
border | Wavy nested security border |
lissajous | Parametric Lissajous figures |
moire | Concentric circle interference |
spiral | Archimedean spiral vortex |
mesh | Hexagonal honeycomb grid |
plume | Flowing feather-like curves scattered across the surface |
constellation | Star nodes connected by a fine geometric web |
ripple | Overlapping elliptical wave fronts from random origins |
full | All patterns combined |
none | Disable filigrane |
firemark id.png -m "Rental application" --filigrane moire
firemark id.png -m "Rental application" --filigrane none # disable
Every render is non-deterministic by default. firemark applies universal post-render perturbation (alpha jitter, sub-pixel color noise, edge micro-dots, sparse ghost pixels) and per-renderer randomization so that no two outputs are pixel-identical — even with the same settings. This makes it impossible for AI vision models to learn a predictable pattern to subtract.
On top of that, adversarial prompt-injection strips are embedded by default to
confuse AI watermark removal tools. Disable with --no-anti-ai if you don't
want the visible prompt text:
firemark doc.png -m "CONFIDENTIAL" --no-anti-ai