Disk layout
What install writes, sector by sector, with no partitions or filesystem. Useful with a hex editor and a disk image.
The map
Sectors are 512 bytes.
LBA 0 MBR
LBA 1-16 stage 2
LBA 64 the kernel, as many sectors as it needs
LBA 4096 the state header, "SVSTATE1"
LBA 4097 slot 0, root, 2048 sectors
LBA 6145 slot 1, tab 1
LBA 8193 slot 2, tab 2
LBA 10241 slot 3, tab 3
LBA 12289 slot 4, tab 4
LBA 14337 the end of everything Subverge uses
About 7 MiB in all. install refuses any drive smaller than 8M. Anything past the end is ignored.
The kernel gets the sectors from 64 up to 4095, which is just under 2 MiB. If a kernel you've built doesn't fit, install fails with the kernel doesn't fit in its slot. The current one is under a megabyte.
The kernel copy
install doesn't write the running kernel. At boot, before anything else runs, the kernel copies its own .data section aside, and install writes the code from memory followed by that untouched copy of the data. So an installed kernel boots fresh, without whatever state the live system had built up, and without anything you poked into it.
The state header
One sector at LBA 4096:
| Offset | Size | Field |
|---|---|---|
| 0 | 8 | SVSTATE1 |
| 8 | 5 × 4 | the length in bytes of each slot's contents |
| 28 | 5 × 4 | an FNV-1a checksum of each slot's contents |
| 48 | 8 | how many saves have ever happened |
| 56 | padding to 512 |
If the magic is wrong, the header is treated as empty, and every slot as unused. When a slot is saved, its data is written first and the header second, so a save interrupted halfway leaves the old header pointing at a slot whose checksum no longer matches, and that slot is ignored at the next boot rather than loaded half-written.
The slots
Each slot is 2048 sectors, 1 MiB, and holds plain omega source with a zero byte after it, padded to a whole sector. Slot 0 is root, every unit after its #>> name line. Slots 1 to 4 are the worlds of tabs 1 to 4. See saving for what's in them and when they're written.
A slot whose length is 0, too big, or whose checksum doesn't match is treated as empty.
Finding the home drive
At boot the kernel reads sector 1 of each of the four IDE drives, and the first one with SUBVERGE at byte 8 is home. If two drives both have Subverge installed, the first one wins, and the other one is just a disk.
Looking at it
On the host, with the VM shut down:
$ dd if=disk.img bs=512 skip=4096 count=1 | xxd | head -4
$ dd if=disk.img bs=512 skip=6145 count=4 | strings
shows you the header and the start of tab 1's world. Don't write to the image while QEMU has it open.
subverge