Like a simplfied 'dd' with extra security checks!
  • C 67.4%
  • Shell 21.5%
  • Makefile 9.5%
  • BitBake 1.6%
Find a file
2026-03-15 09:03:51 +01:00
completions Move bash completions into ./completions 2026-03-15 06:16:29 +01:00
docs Rewrite outdated documentation in DESIGN.md 2026-03-15 08:46:02 +01:00
packaging Bump packaging 2026-03-15 09:03:51 +01:00
test Test setup script renames 2026-03-15 06:35:20 +01:00
.clang-format Clang-format 2026-02-07 17:20:00 +01:00
.gitignore Gitignore for *amalgamation.c 2026-03-15 07:05:45 +01:00
crc32.h Rewrote the CRC library to be more 'imperative' 2026-03-15 03:57:39 +01:00
INSTALL Include notes about release and amalgamation in INSTALL 2026-03-15 07:22:54 +01:00
LICENSE License 2026-03-15 08:03:58 +01:00
Makefile Rename macro define VERSION to WRITEIMG_VERSION 2026-03-15 08:01:15 +01:00
README.md Include note about TODO in README 2026-03-15 08:47:17 +01:00
writeimg.c Start by zeroing out the buffer for extra security 2026-03-15 08:30:26 +01:00

WriteIMG Image Writer

WriteIMG is a simple dd-like image writer with additional security checks for Linux, FreeBSD and OpenBSD! It tells you what you're about to do and warns you about potential problems before they occur. It also features automatic image verifications, and uses a suitable block size for fast and gentle writing.

Say goodbye to fried flash and overwritten bootloaders, no more footguns!

Usage

# Write it, ask for confirmation
writeimg -d /dev/mmcblk0 alpine-rpi-3.23.3-aarch64.img

# Write it without asking for confirmation
writeimg -nd /dev/mmcblk0 alpine-rpi-3.23.3-aarch64.img

# Do this file correspond to whats written on device?
writeimg -vd /dev/mmcblk0 alpine-rpi-3.23.3-aarch64.img

Technical Info

The internal buffer is allocated in .bss, meaning this program is entirely free of allocations! The buffer size is static, and is set at compile time.

Since this is sensitive code meant to run as a privileged user, extra care is taken. In OpenBSD, we use unveil() to limit allowed paths. In FreeBSD, we use Capsicum on the file descriptors. Linux-analogues are quite a bit more complex, but Landlock seems to be maturing and should be a suitable option in time. We are also considering Seccomp.

The code is regularly vetted and tested on all supported platforms. Feedback is greatly appreciated, if only to nitpick on style. If you take interest in this code by either reading, forking or just using it, i'd love to hear about it at imbus64@protonmail.com. Patches welcome!

We provide a manpage, which targets OpenBSD-level quality. Incorrect or outdated information is a bug. Small, readable and informative.

For in-depth technical notes, see DESIGN.md
For development tasks in pipeline, see TODO.md

Building and Installing

For general info: make help

As simple as:

  • Install: make install
  • Uninstall: make uninstall

The uninstall target cleans all artifacts. For manpages and completions, see below.

In linux, we depend on the kernel headers for ioctl numbers. This is because we need to know low level details about sector sizes and block devices.

sudo dnf install kernel-headers kernel-devel  # Fedora
sudo apt install linux-headers-generic        # Debian
sudo pacman -S linux-headers                  # Arch
sudo apk add linux-headers                    # Alpine

If you also want the manpage: make install_manpage. You will need scdoc installed. For bash completion: make install_bash. See make help for notes, bash has no standard location for sourcing completions.

Reproducible Build

Simply building with SOURCE_DATE_EPOCH defined will automatically do a reproducible build.

make SOURCE_DATE_EPOCH=0

Testing

For testing, there is a shell script "test.sh" included. Setup scripts for Linux, FreeBSD and OpenBSD are provided. Here are the manual steps for those interested:

truncate -s 128M /tmp/tempdisk.img       # Generate disk img
losetup --find --show /tmp/tempdisk.img  # Set it up as loopdev
losetup -a                               # List all loop devices
./writeimg -d /dev/loop[n] yourfile.img  # Write something to it
losedup -d /dev/loop[n]                  # Delete it
rm /tmp/tempdisk.img                     # Remove the actual file

Writes to a regular files is not currently in scope, although it would simplify testing, which currently require elevated privileges.