This nix flake cooks Windows images that can be run with QEMU. It aims to produce images that are ready to use, without bloat, Windows Updates and Windows Defender.
Right now this flake builds the following Windows versions:
| Version | Package | Size | Time | Boot |
|---|---|---|---|---|
| Windows 11 25H2 Enterprise | windows-11-25h2 |
8.1G | 31m | EFI |
| Windows 11 24H2 Enterprise | windows-11-24h2 |
6.5G | 25m | EFI |
| Windows 11 23H2 Enterprise | windows-11-23h2 |
6.8G | 21m | MBR |
| Windows 3.11 | windows-3.11 |
12M | 150s | MBR |
| MS-DOS 6.22 | dos-6.22 |
3.9M | 44s | MBR |
The goal is to support many versions of Windows, including historical ones.
Being the build deterministic, whatever is produced here, will be reproducible until the end of time (or until Microsoft stops distributing the ISOs).
Things you need to know
To build the image:
$ # The following command will install nix-portable, if necessary.
$ ./nix build .#windows-11-25h2
$ ./result/bin/prepare-vm
$ cd vm
$ ./vm start
Other facts:
- Username:
user - Password:
password - This not for production use. It's for when you need to try something quickly on Windows and you don't want any noise. Just a clean (not updated), Windows installation.
Features
- Installation is performed in a nix derivation. No Internet, all the inputs are collected ahead of time. The output is reasonably deterministic.
- Installation has QEMU Guest Additions, VirtIO drivers and the SPICE agent.
- Windows Update is disabled.
- Windows Defender is disabled.
- Search Indexer is disabled.
- Various debloating using Raphire/Win11Debloat.
- Some useful software is preinstalled: the SysinternalsSuite, Firefox, Google Chrome, Notepad++, Git for Windows, Chocolatey, Everything, SystemInformer (was: Process Hacker), Dependency Walker, Dependencies.
- Free space is zeroed out to get a smaller final image.
- Produce lossless video of the installation process.
- While the VM is off, you can mount its partitions on the host system using the
./mountscript.
FAQ
- How can I watch the installation process?
The build runs in QEMU, which exposes a VNC service on port 5900.
To access it, you need to enter the network namespace of the nix builder process.
Use
./connect-to-vncto do that. - Why not VirtualBox?
I love QEMU, once you invoke it with the right incantations, it's the best. Thanks to
quickemu, the incantations are not that hard nowadays. Also, apparently the VirtualBox kernel driver is (used to be?) quite bad. - Why not libvirt? I love QEMU. Libvirt feels like extra layers of XML to get to the command line of QEMU I actually want to run.
- How do you pilot the installation?
For recent systems, you can do 99% of things via the answer file
autounattend.xml. Due to some limitations, sometimes it's still necessary to simulate key inputs, usingvncdo key. For older systems (e.g., Windows 3.11), the installation is piloted via VNC key presses. However, almost nosleeps are used: screenshots are taken via VNC (vncdo snapshot), OCR is performed on the screenshot with Tesseract and then we keep waiting until a certain text pops up.sleeps are bad for reproducibility.
TODO
- Implement
nix run. - Disable more auto-updates, in particular Chrome and Edge.
- Add support for more Windows versions.
- Disable firewall
- Install SSH
- Make images actually reproducible, byte-by-byte.
Credits
The following projects have been useful: