You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
feat(linux): M2-12 — UEFI bzImage boot smoke green
Closes M2-12 (end-to-end Linux bzImage boot under QEMU UEFI).
`cargo run -p zamak-test -- --suite linux-bzimage` now prints
`[PASS] uefi-linux-boot` locally; the CI `qemu-smoke` job runs
the new suite case alongside the existing UEFI boot-smoke and
asm-verification.
Observed serial:
[ INFO] Booting entry: zamak-linux-stub (PROTOCOL=linux)
[ INFO] Linux kernel body: 577 bytes loaded at phys 0xe36e000
[ INFO] Linux: converted 118 UEFI entries to E820
[ INFO] Linux BootParams at phys 0xe369000, entry 0xe36e200
[ INFO] Exiting boot services and jumping to Linux kernel
at 0xe36e200 (RSI=0xe369000)
Linux version 0.0.0-zamak-stub
(QEMU exits with code 0x63 via isa-debug-exit)
Pieces:
1. **New `zamak-linux-stub-kernel/` crate** (workspace-excluded,
built through `build-images.sh`). Produces a minimal
Linux-Boot-Protocol-2.15 bzImage entirely from a `global_asm!`
hand-laid byte stream: real-mode-halt stub + setup header
with `HdrS` magic + 64-bit entry at `setup_end + 0x200` that
writes `Linux version 0.0.0-zamak-stub\n` to COM1 and exits
QEMU via isa-debug-exit. NOT a real Linux kernel — smoke tests
ZAMAK's handoff plumbing without external downloads or initrd
complexity. A future `linux-full-boot` suite can add real
kernel coverage.
2. **`zamak-core::linux_boot::prepare_linux_boot`** — new
orchestrator that walks `parse_setup_header` + allocates a
`BootParams` zero page + populates `code32_start` / cmdline
pointer / optional initrd / E820 entries from a caller-supplied
`[MemoryRegion]`. Returns a `LinuxBootImage { boot_params,
entry_point }`. 6 new unit tests covering tiny-image, bad
magic, 4-GiB overflow on each address, and a happy-path that
round-trips cmdline/initrd/E820 through the zero-page offsets.
3. **`zamak-uefi` protocol dispatch** — kmain now branches on
`entry.protocol.eq_ignore_ascii_case("linux")`. The new
`load_linux_kernel()` helper allocates UEFI `LOADER_DATA`
pages for the kernel body, cmdline (NUL-terminated), optional
initrd (first module if present), and BootParams zero page;
translates the UEFI memory map to E820 types via
`uefi_mem_ty_to_e820()`; and calls `prepare_linux_boot`.
Output is wrapped in a new `KernelHandoff` enum so the
post-ExitBootServices match dispatches to the right handoff.
4. **`zamak-uefi::handoff::jump_to_linux_kernel`** (x86_64) —
`cli` + `mov rsi, bp` + `jmp entry`, no CR3 write (Linux
builds its own page tables over UEFI's identity map). Earlier
draft zeroed every GPR before the jump, which clobbered the
compiler-allocated temporaries holding `bp` and `entry` and
sent RIP to 0xA0000 with RSI=0 — kept the Linux-required RSI
set, dropped the over-zealous clear.
5. **`build-images.sh`** — new section builds the stub crate,
extracts the `.boot` section via `objcopy --dump-section`
(rust-lld still emits `.dynsym`/`.gnu.hash` in static-PIE
ELFs, so plain `-O binary` would prepend garbage), and
assembles `target/linux-esp.img` with `BOOTX64.EFI` +
`zamak.conf` (`PROTOCOL=linux`, `KERNEL_PATH=/bzImage`,
`CMDLINE=console=ttyS0`) + `/bzImage`.
6. **CI wiring** — `.github/workflows/ci.yml` and the forgejo
mirror: `qemu-smoke` job now runs `--suite linux-bzimage
--timeout 60` after `--suite boot-smoke`. Same env/OVMF
config; no new dependencies.
7. **TODO.md** — M2-12 flipped to `[✓]`. Remaining `[~]`: M1-16
(call_bios_int), M6-1 (rustc upstream), M6-3 (hardware). Down
from 4 to 3. CHANGELOG's `[Unreleased]` gets the entry.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
| M2-11 |`[✓]`| Linux Boot Protocol support — x86 bzImage setup header parsing, BootParams zero page, E820 population (§FR-PROTO-002) |
137
-
| M2-12 |`[~]`| End-to-end Linux bzImage boot under QEMU UEFI — `linux-bzimage` suite + `ZAMAK_LINUX_ESP` env in `zamak-test`; awaits real bzImage + UEFI initrd in CI |
137
+
| M2-12 |`[✓]`| End-to-end Linux bzImage boot under QEMU UEFI — new `zamak-linux-stub-kernel` crate produces a spec-compliant protocol-2.15 bzImage blob; `zamak-uefi` dispatches on `PROTOCOL=linux`, populates BootParams + E820 from UEFI mmap, jumps via a Linux-specific handoff that sets RSI pre-`jmp`. `cargo run -p zamak-test -- --suite linux-bzimage` prints `[PASS] uefi-linux-boot` locally and in CI. Real Linux kernel coverage is a future `linux-full-boot` suite.|
138
138
| M2-13 |`[✓]`| Build and produce `BOOTX64.EFI` release artifact (`Makefile.uefi` with ESP image + QEMU target) |
**No items are fully not-started.** The 4 remaining `[~]` items are:
321
+
**No items are fully not-started.** The 3 remaining `[~]` items are:
322
322
323
-
-**CI artifact confirmation** (2 items): `bios-boot-smoke` on `zamak-test-kernel` (M1-16) — needs real stage1 MBR chain; Linux bzImage UEFI smoke (M2-12) — needs a real bzImage committed or synthesized by CI. TEST-4 and TEST-5 are now`[✓]` for the UEFI x86-64 path.
323
+
-**CI artifact confirmation** (1 item): `bios-boot-smoke` on `zamak-test-kernel` (M1-16) — needs the `call_bios_int` trampoline fix or real-mode I/O refactor. M2-12 now satisfied via the `zamak-linux-stub-kernel` synthetic bzImage; TEST-4 and TEST-5 are `[✓]` for the UEFI x86-64 path.
324
324
-**LoongArch UEFI target** (M6-1): blocked on rustc upstream — `loongarch64-unknown-uefi` target does not yet exist, and `uefi-services`' `efiapi` ABI is unsupported on `loongarch64-unknown-none`. Paging builder + handoff code are implemented and compile for the bare-metal target; flips to `[✓]` when rustc lands the UEFI triple.
0 commit comments