cd ~/>cat multi-boot-partitioning-the-layout.md

Multi-boot partitioning / The layout

#linux#btrfs#partitioning#void#arch#multiboot

The machine

WD Black SN770 2TB NVMe (/dev/nvme0n1). One disk, three operating systems. The layout was not designed all at once — it evolved under real constraints. What follows is the current state and the reasoning behind it.

/dev/nvme0n1
├── p1   /boot/efi    fat32    1.0G    ESP  (UUID: 1A4A-CE0B)
├── p2   MSR          ntfs      16M    Windows metadata
├── p3   Windows      ntfs     431G    (shrunk from 487G)
├── p4   BSD          —         31G    empty — future experimentation
├── p5   btrfs pool   btrfs    887G    UUID: d7a98795-1604-4baa-ae07-05e29a3ff1e6
├── p7   Arch         btrfs    487G    UUID: 275bce6c-f037-43f9-be0f-650efb12cf1e
├── p8   /boot        ext4     7.6G    UUID: fba989bd-2a90-4e11-9aa2-4c941d3e0460
└── p9   recovery     ext4    18.6G    empty — future Arch recovery

p5 is the main Linux pool. It holds all Void subvolumes, the shared home, shared data, shared Docker storage, and the cache subvolume. p7 is Arch’s separate btrfs root. p8 is the shared /boot that both distros write kernels into.

Partition by partition

p1 — ESP

The EFI System Partition holds only bootloader binaries. GRUB’s EFI stub is a few megabytes. 1G is generous but causes no harm. Formatted fat32, shared across all operating systems. There is one GRUB installation here — Arch owns it. Void does not install its own EFI entry.

p2 — MSR

Windows requires a Microsoft Reserved Partition on GPT disks for its own metadata. Non-negotiable if Windows is on a GPT disk. 16M, ntfs, not mounted by Linux.

p3 — Windows

Shrunk from 487G to 431G using the Windows disk management tool. The shrink was done from within Windows rather than from Linux — ntfs resize from Linux with ntfsresize requires the volume to be cleanly unmounted, and the Windows fast-startup feature leaves it in a hibernate state. Easier to shrink it from the inside.

p4 — BSD placeholder

Empty, unformatted. Reserved for future experimentation with DragonFlyBSD or FreeBSD. BSD partitions do not sit well inside Linux partition tables without dedicated space planned upfront.

p5 — btrfs pool

887G, the result of merging two separate partitions. Originally p5 was 430G and p6 was 457G. Merging them into a single pool eliminated artificial boundaries between subvolumes and simplified the fstab. The merge process is covered in [Multi-boot partitioning / Merging btrfs partitions].

This partition hosts the following subvolumes:

@void              /
@void-var          /var
@void-snapshots    /.snapshots
@home              /home
@data              /data
@docker            /var/lib/docker
@home-cache        ~/.cache

p7 — Arch btrfs root

Arch predates the unified pool. Its btrfs partition is separate and carries its own subvolume layout. Migrating it into p5 is technically possible but adds no practical benefit for how this machine is used.

p8 — shared /boot

The original /boot lived on a 1G partition. It filled up. Two Linux kernels with headers and initramfs images exhaust 1G faster than expected. p8 is 7.6G — enough for both distros to keep multiple kernel versions without pressure. Both Void and Arch write their kernels here. GRUB reads from here. See [Multi-boot partitioning / Shared GRUB partition].

p9 — recovery

Empty ext4 partition. Reserved for a future Arch rescue environment or a minimal live system. Not currently in use.

Why not LVM

LVM adds logical volume management on top of block devices: resize volumes without repartitioning, group physical devices, thin provisioning. btrfs subvolumes do the same thing inside a single filesystem — create, destroy, snapshot, and resize namespaces without touching the partition table.

For a single-disk setup, LVM on top of btrfs is two abstraction layers for no gain. The one thing LVM provides that btrfs subvolumes don’t is spanning multiple physical block devices. btrfs supports this too (btrfs RAID), but on a single NVMe the point is moot.

What forced the layout to evolve

Two constraints drove the major structural changes.

The first was the 1G /boot filling up. Arch’s kernel packages — linux, linux-lts, linux-headers — each consume several hundred MB. Two kernels plus initramfs images exhausted 1G. Managing it meant manually dropping old kernels, which is error-prone. Migrating to a 7.6G partition eliminated the pressure and made room for Void to coexist.

The second was the p5+p6 boundary. Two separate btrfs partitions meant two mount points, two sets of fstab entries, and no clean way to share subvolumes across them. A @home subvolume on p5 cannot be accessed from p6 without explicit cross-mount plumbing. Merging into a single pool resolved this structurally — shared subvolumes become trivial.

// END OF TRANSMISSION
See you, Space Cowboy.

Connection closed. Returning to terminal...