Skip to content

ADR-0026: Pin Pi OS base release to Debian Trixie (13)

The KN-86 system image is built with pi-gen targeting Raspberry Pi OS Lite (arm64) (docs/device/os/system-image-build.md §“Pipeline choice”). The base-release pin held that the underlying Debian release was “currently the Bookworm-based release” (Debian 12), with the exact snapshot.debian.org timestamp and pi-gen tag deferred to Stage 0 bring-up.

Two facts converged in April 2026:

  1. Debian 13 “trixie” released March 2026. Trixie carries libsdl3-dev 3.2.10+ds-1 in the apt repos. SDL3 is not in the bookworm apt archive; bookworm builds would have to vendor SDL3 from source or pull from bookworm-backports, neither of which is durable for the device path.
  2. The KN-86 ship target is Q4 2027. That is roughly 18 months of trixie field-soak between adoption and shipping hardware — by Q4 2027 trixie will be deeply stable, on par with where bookworm sits in 2026.

Concurrent with this ADR, the SDL2 → SDL3 migration is moving forward (the emulator path is on SDL3 already; the device path is gated on libsdl3-dev being available in the base apt archive). Holding the system-image pin at bookworm forces the device path into a vendored-SDL3 build for the entire window between now and ship — which costs build time, complicates the pi-gen stage layout, and creates a divergence between the emulator and device toolchains that has no architectural justification once trixie is on the table.

This ADR closes the base-release decision.

  1. SDL3 availability in apt. Trixie ships libsdl3-dev 3.2.10+ds-1 in main. Bookworm does not. The device path needs SDL3 by the time the SDL3 migration lands; the cheapest way to get it is the apt-supplied package on the base release, not a vendored build inside the pi-gen stage tree.
  2. Q4 2027 ship target. Trixie released March 2026 — ~18 months of field soak between adoption and ship. Past the point at which “trixie is fresh” stops being a meaningful objection.
  3. Pin is not yet hard. The base-release pin in system-image-build.md was deliberately “TBD pending bring-up.” No pi-gen-pin.env file has been committed yet. Switching releases now is a doc edit; switching after pi-gen-pin.env is committed costs a re-pin plus a re-run of the 50-cycle USB-MSC regression test. Now is the cheap window.
  4. Toolchain alignment with the emulator path. The desktop emulator already targets SDL3 (Homebrew on macOS, apt on Linux). Pinning the device base release to trixie keeps both compile targets on a single SDL major version with no vendored-from-source bridge.
  • The pi-gen tag must support trixie. As of April 2026 the upstream pi-gen master branch tracks the latest Raspberry Pi OS release, which is now trixie-based. The exact tag is captured at bring-up time, not in this ADR.
  • The 50-cycle USB-MSC regression test from ADR-0011 §Risks #1 still gates the pin. Switching the base release does not relax that test — it makes re-running it mandatory before any v1 pin is committed.
  • No snapshot.debian.org timestamp in this PR. Per the task brief, the pin specifics are recorded as “Debian 13 trixie, exact snapshot.debian.org timestamp + pi-gen tag TBD pending Stage 0 bring-up.” A speculative timestamp pinned now would just need to be re-pinned after bring-up validates the actual triplet.
  • No system image partition/layout changes. The six-partition A/B layout from ADR-0011 §SD partition layout is unchanged. The base-release swap is package-level, not block-layout-level.

The KN-86 system image base release is Debian 13 “trixie” via Raspberry Pi OS Lite (arm64). Concrete commitments:

  • Distribution: Raspberry Pi OS Lite (arm64).
  • Underlying Debian release: Debian 13 “trixie” (released March 2026).
  • Pin specifics: Debian 13 trixie, exact snapshot.debian.org timestamp + pi-gen tag TBD pending Stage 0 bring-up. Once Stage 0 of ../device/hardware/build-specification.md §4 lands a known-good kernel + Raspberry Pi OS Lite (arm64) trixie combination that survives the 50-cycle USB-MSC regression test in ADR-0011 §Risks #1, the triplet (kernel version, pi-gen tag, snapshot.debian.org timestamp) becomes the v1 pin and is committed to tools/sd-provision/pi-gen-pin.env.

The bookworm-based pin previously implied by system-image-build.md is retired. The doc-wide sweep for stale bookworm / Debian 12 references lands in this PR (see “Documentation Updates” below). Permitted to remain after the sweep:

  • This ADR’s Context and Options-Considered sections (historical narrative).
  • The DOS easter-egg research memo’s reference to a third-party DOSBox Staging issue that itself names bookworm (the link target is upstream — we don’t rewrite their bug title; the surrounding KN-86 prose does flip to trixie).

3. The 50-cycle USB-MSC regression test still gates the pin

Section titled “3. The 50-cycle USB-MSC regression test still gates the pin”

ADR-0011 §Risks #1 specifies a 50-cycle write/read/verify update-loop test across macOS, Windows, and Linux hosts as the gating criterion before any base-image pin is committed to pi-gen-pin.env. Switching the base release from bookworm to trixie does not change this gate — the same matrix runs against the trixie base image at Stage 0 bring-up, and a clean 50-cycle pass is the precondition for committing the v1 pin.

With trixie as the base release, libsdl3-dev is installed via the stage-kn86-runtime apt step; no meson + ninja SDL3 build inside the pi-gen chroot, no vendored SDL3 tarball in the source tree. This is the immediate payoff of this ADR for the SDL3 migration’s device path.

5. No CLAUDE.md canonical-spec value shifts

Section titled “5. No CLAUDE.md canonical-spec value shifts”

The Canonical Hardware Specification in CLAUDE.md does not change. The base Debian release is build-pipeline metadata (which system-image-build.md owns), not a canonical hardware spec value. Per Spec Hygiene Rule 3, the absence of a CLAUDE.md edit is intentional and is called out in the PR description.


Option A: Pin to Debian 13 trixie (ACCEPTED)

Section titled “Option A: Pin to Debian 13 trixie (ACCEPTED)”

Described above. Trixie released March 2026, ships libsdl3-dev 3.2.10+ds-1 in apt, gives ~18 months of field soak before the Q4 2027 ship target.

Keep the bookworm pin and vendor SDL3 from source inside the pi-gen stage-kn86-runtime (or pull from bookworm-backports if and when SDL3 lands there).

Rejected because:

  1. SDL3 is not in the bookworm apt archive. Vendoring SDL3 from source adds ~5–10 minutes to the build, complicates the pi-gen stage layout, and creates a maintenance burden every time SDL3 patches.
  2. bookworm-backports is a moving target — relying on a backport for a load-bearing dep is exactly the kind of pin-drift the ADR-0011 50-cycle test is designed to catch, except it would catch it on every backport refresh instead of once at bring-up.
  3. Ship target is Q4 2027. By then bookworm is the previous stable release (oldstable), not the current one. Shipping on oldstable is a worse field-stability story than shipping on stable.
  4. The cost of switching now is a doc edit. The cost of switching after pi-gen-pin.env is committed is a re-pin plus a re-run of the 50-cycle USB-MSC regression test. Now is the cheap window.

Option C: Pin to Debian 14 (next release after trixie)

Section titled “Option C: Pin to Debian 14 (next release after trixie)”

Skip trixie entirely; wait for Debian 14 (release date TBD, projected late 2027 / early 2028).

Rejected because:

  1. Debian 14 has no release date as of April 2026. Projecting late 2027 / early 2028 puts the base release behind the ship target — KN-86 would ship on a non-existent base release.
  2. Even if Debian 14 lands by Q4 2027, it would have zero field soak. Shipping on a brand-new Debian release is the precise scenario this ADR rejects when it argues bookworm is too old by Q4 2027.
  3. Trixie hits the sweet spot: stable enough by ship time, fresh enough to carry SDL3.

Option D: Pin to bookworm now, plan a trixie migration ADR before ship

Section titled “Option D: Pin to bookworm now, plan a trixie migration ADR before ship”

Two-step path: keep bookworm for the v0.1 / v0.2 bring-up cycle, write a separate trixie-migration ADR for the v1.0 ship build.

Rejected because:

  1. The v0.1 bench-test matrix (50-cycle USB-MSC regression test, kernel pin, pi-gen tag pin) is what locks the base release. Re-running that matrix on a different base release is the entire cost — there is no “small bookworm version” we save by doing it twice.
  2. Splitting the decision across two ADRs forks the bring-up procedure. The Stage 0 bench-test plan would have to either (a) run twice (once on bookworm, once on trixie) or (b) skip the bookworm validation and effectively make this ADR moot.
  3. There is no architectural reason bookworm beats trixie for the bring-up cycle. The forcing function (SDL3 in apt) is already live; the trade-off (field soak) tilts toward trixie by the time hardware ships.

Against Option B (stay on bookworm), Option A wins on:

  • SDL3 availability. apt-supplied vs. vendored-from-source — the apt-supplied path is durable, the vendored path is build-time and maintenance burden.
  • Field soak at ship. Trixie at Q4 2027 is ~18 months stable; bookworm at Q4 2027 is oldstable. Trixie is the better field-stability story by ship time.
  • Toolchain alignment with the emulator path. Both compile targets on a single SDL major version, no vendored bridge.

The cost of Option A vs. Option B:

  • Less battle-tested in the field today. True, but the relevant comparison is “trixie at ship time,” not “trixie today.” 18 months of soak resolves this.
  • Some packages may see version churn before trixie hits its first point release. Mitigated by the snapshot.debian.org timestamp pin — once Stage 0 commits a snapshot timestamp, the build is reproducible regardless of what trixie does upstream.

Against Option C (Debian 14), Option A wins on schedule certainty — Debian 14 has no release date and may post-date ship.

Against Option D (bookworm now, trixie ADR later), Option A wins on cost — the bring-up matrix runs once, not twice. There is no salvageable v0.1 work in a bookworm bring-up that would not be redone in a trixie bring-up.


  • Unblocks the SDL3 migration on the device path. libsdl3-dev from apt; no vendored build, no bookworm-backports dependency.
  • Better field-stability story at ship time. Trixie at Q4 2027 is mid-stable; bookworm at Q4 2027 is oldstable.
  • Toolchain alignment. Emulator and device targets both on SDL3 from a packaged source, no vendored divergence.
  • Cheap to land now. Pre-pi-gen-pin.env. Doc edit, no rebuild infrastructure changes.
  • No CLAUDE.md canonical-spec change. Base release is build-pipeline metadata; the canonical hardware spec is unchanged.
  • Less battle-tested today. Trixie released March 2026; field-tested for ~1 month at the time of this ADR. Resolved by Q4 2027 ship.
  • Stage 0 bench-test must run on trixie, not bookworm. Same 50-cycle USB-MSC matrix from ADR-0011 §Risks #1; the underlying base release shifts. No incremental work over a bookworm bench plan — the matrix is the matrix.
  • Some tools/sd-provision/ install scripts and the bench-test plan reference bookworm in TODO comments and pre-condition lists. The doc sweep in this PR updates the bench-test plan and the public-facing research memo; the tools/sd-provision/ install-script comments are intentionally deferred to the follow-on pi-gen-stage implementation task in this sprint (where the install scripts are un-stubbed against the live pin). See “Documentation Updates” below.
  • F1 — Stage 0 bring-up validates the trixie triplet. Kernel version + pi-gen tag + snapshot.debian.org timestamp. Triplet committed to tools/sd-provision/pi-gen-pin.env after a clean 50-cycle USB-MSC pass.
  • F2 — pi-gen stage trixie support. Sprint 6 separate task — un-stub 00-install-legacy-terminal.sh and the rest of tools/sd-provision/pi-gen-stages/* against trixie’s apt archive; reconcile any package-name drift (e.g., umoria packaging differences between bookworm and trixie). Out of scope for this PR.
  • F3 — SDL3 device-path integration. Separate SDL3 migration work — once trixie is the base release, the device-path SDL3 migration consumes libsdl3-dev from apt rather than vendoring.

  1. Trixie point-release churn before Stage 0 bring-up. Mitigated by the snapshot.debian.org timestamp pin once Stage 0 lands a known-good triplet. Until then, bring-up is run against trixie’s then-current apt archive; if a regression appears between trixie release (March 2026) and Stage 0 bring-up, the snapshot pin captures the working state.
  2. Package-name drift between bookworm and trixie. Some packages (notably dosbox-staging, umoria, and other niche utilities used by the Legacy Terminal stage in ADR-0021) may be packaged differently or absent in trixie. Mitigated by the Stage 0 bench-test plan, which exercises the install path package-by-package and falls back to source builds where apt cannot supply.
  3. 50-cycle USB-MSC regression test outcome on trixie. The test must pass on trixie for the pin to commit. Mitigated by it being the explicit gate — a failure aborts the pin and forces a kernel or pi-gen tag revisit, not a base-release rollback (the SDL3 forcing function makes a bookworm rollback worse, not better).
  4. Trixie kernel ABI vs. Pi Zero 2 W vendor kernel. Raspberry Pi OS Lite (arm64) ships with a Pi-flavored kernel that tracks upstream LTS plus Raspberry Pi-specific patches. The Pi-vendor kernel for trixie was current as of the Raspberry Pi OS trixie release, but the device-tree overlays for SSD1322 OLED and the USB hub topology must be re-verified against the trixie kernel. Mitigated by the Stage 0 bench-test exercising the overlay path.

The “migration” in this ADR is from the implicit bookworm pin in system-image-build.md to an explicit trixie pin. Concrete steps:

  1. Land this PR. Updates system-image-build.md line 27 (base release) and line 76 (Docker base image), the bench-test plan’s pre-conditions, and the DOS easter-egg research memo’s KN-86-side prose. ADR README index updated.
  2. Stage 0 bring-up runs the 50-cycle USB-MSC regression test against the trixie image. Per ADR-0011 §Risks #1.
  3. Stage 0 bring-up commits the triplet to tools/sd-provision/pi-gen-pin.env. Kernel version, pi-gen tag, snapshot.debian.org timestamp.
  4. Sprint 6 follow-on task un-stubs the pi-gen stage install scripts against the trixie apt archive. Out of scope for this PR.

There is no in-field migration component — no devices have shipped on bookworm. This is a pre-bring-up base-release decision, not a field-update story.


Documentation Updates (REQUIRED — part of the decision, not aspirational)

Section titled “Documentation Updates (REQUIRED — part of the decision, not aspirational)”
  • docs/adr/ADR-0026-pi-os-trixie-base-pin.md — this ADR.
  • docs/adr/README.md — append entry for ADR-0026.
  • docs/device/os/system-image-build.md — line 27 base release: bookworm → trixie. Line 76 Docker --platform=linux/amd64 base image: debian:bookwormdebian:trixie.
  • docs/research/KN-86-DOS-Easter-Egg-bench-test-plan.md — pre-conditions and matrix table reference Raspberry Pi OS Lite (arm64) trixie, not bookworm. Note: the upstream dosbox-staging issue link in KN-86-DOS-Easter-Egg-Research.md retains its own bookworm reference because the upstream issue was filed against bookworm — that’s a third-party fact, not a KN-86 commitment.
  • docs/research/KN-86-DOS-Easter-Egg-Research.md — KN-86-side prose updated to reference trixie. The third-party dosbox-staging issue title itself stays as-filed.
  • Project-wide grep sweep. git grep -i bookworm and git grep -i 'debian 12'. After the sweep, the only remaining hits are:
    • This ADR’s own narrative.
    • The tools/sd-provision/pi-gen-stages/stage-kn86-runtime/legacy-terminal/ install-script comments and README — intentionally deferred to the Sprint 6 pi-gen stage implementation task per this ADR’s Consequences §“Negative” item 3.
    • The third-party dosbox-staging issue link context in the research memo.
  • CLAUDE.md — no change. Base Debian release is build-pipeline metadata, not a canonical hardware spec value. The Canonical Hardware Specification table is untouched.

A PR that lands this ADR without ticking the open boxes (README.md index, system-image-build.md, both research memos) fails review.