# Phase 16.1: model FreeBSD source inputs explicitly Date: 2026-04-03 ## Goal Phase 16.1 introduces a first-class Fruix model for FreeBSD source inputs so the native base path is no longer described only as "whatever `/usr/src` is on the host". This step does **not** yet fetch or materialize remote source trees. It makes the source declaration explicit and records it through the package, system, and CLI metadata layers so later phases can replace ambient `/usr/src` with fetched or materialized inputs cleanly. ## Implementation ### New declarative FreeBSD source record Added in `modules/fruix/packages/freebsd.scm`: - `freebsd-source` - `freebsd-source?` - accessors for: - `name` - `kind` - `url` - `path` - `ref` - `commit` - `sha256` - `%default-freebsd-source` Supported source kinds are now modeled explicitly as: - `local-tree` - `git` - `src-txz` The default source remains a local-tree declaration for: - `/usr/src` ### FreeBSD bases now carry a declared source object Extended `freebsd-base` so it now records: - the transitional `source-root` still used by the current native build path - a new `source` record describing the declared FreeBSD source input Added/exported: - `freebsd-base-source` This keeps the validated `/usr/src` path working while giving the base a source object that can later point at fetched Git or `src.txz` materializations. ### Native package plans and metadata now record the declared source `modules/fruix/packages/freebsd.scm` now threads source fields into native package install plans. `modules/fruix/system/freebsd.scm` now records a `declared-source` block in: - native package manifests - `.freebsd-native-build-info.scm` This means native kernel, bootloader, and runtime outputs now remember both: - the declared base - the declared source input ### Operating-system validation now checks source declarations Added source validation in `modules/fruix/system/freebsd.scm`. Current accepted source declarations are: - `local-tree` - requires a path - `git` - requires a URL and at least a ref or commit - `src-txz` - requires a URL This is intentionally enough for Phase 16.1 modeling without yet enforcing the later fetch/materialization policy. ### Closure metadata now includes a dedicated source file System closures now generate: - `metadata/freebsd-source.scm` and embed source information in: - `metadata/freebsd-base.scm` - `metadata/store-layout.scm` - `parameters.scm` ### CLI metadata now exposes the declared FreeBSD source `scripts/fruix.scm` now emits the following for `fruix system build` and `image`: - `freebsd_source_name` - `freebsd_source_kind` - `freebsd_source_url` - `freebsd_source_path` - `freebsd_source_ref` - `freebsd_source_commit` - `freebsd_source_sha256` - `freebsd_source_file` ## Guix comparison This follows the same broad idea as Guix source modeling: - Guix uses `origin` in `guix/packages.scm` - Git-backed sources are modeled with `git-reference` in `guix/git-download.scm` Phase 16.1 does not copy Guix mechanically, but it adopts the same useful architectural boundary: - source identity should be a declarative object - builds should record that source object explicitly For Fruix, the source kinds are FreeBSD-oriented: - local source tree snapshots for development - FreeBSD Git refs/commits - official FreeBSD `src.txz` archives ## Upstream source forms verified during this step Verified usable upstream source forms include: - Git: - `https://git.FreeBSD.org/src.git` - release archive: - `https://download.freebsd.org/releases/amd64/15.0-RELEASE/src.txz` - snapshot archive: - `https://download.freebsd.org/snapshots/amd64/15.0-STABLE/src.txz` The shorter release URL form above is treated as the canonical example in this phase. ## New files Added: - `docs/PLAN_4.md` - `tests/system/phase16-declarative-source-operating-system.scm.in` - `tests/system/run-phase16-declarative-source-build.sh` - `tests/system/validate-phase16-freebsd-source.scm` ## Validation Passing run: - `PASS phase16-declarative-source-build` - workdir: - `/tmp/fruix-phase16-declarative-source.0LRvaC` The source model probe confirmed: ```text local_kind=local-tree local_path=/usr/src git_kind=git git_url=https://git.FreeBSD.org/src.git git_ref=stable/15 txz_kind=src-txz txz_url=https://download.freebsd.org/releases/amd64/15.0-RELEASE/src.txz txz_sha256=example-sha256 base_source_accessor=ok ``` The closure build confirmed: ```text closure_path=/frx/store/ac73a2a89c3c3f794462ccde0d9f0952362dc2ae32e631a7e99e07e7363e6118-fruix-system-fruix-freebsd kernel_store=/frx/store/c2f771a794f94cf168ae26a421ffab33e0ae4765f23882257d5bb7b2947d493d-freebsd-native-kernel-15.0-STABLE-source-model bootloader_store=/frx/store/a146c9c2fcacdc02454fe3bfd3afb5c5dbea54b6514242d53df0783ef4ee34fd-freebsd-native-bootloader-15.0-STABLE-source-model runtime_store=/frx/store/530e96440a518821a701db03f9437d7646c0447f8ea55c5df08417e9274dead1-freebsd-native-runtime-15.0-STABLE-source-model native_base_store_count=3 host_base_store_count=0 freebsd_source_name=host-usr-src freebsd_source_kind=local-tree freebsd_source_path=/usr/src freebsd_source_file=/frx/store/ac73a2a89c3c3f794462ccde0d9f0952362dc2ae32e631a7e99e07e7363e6118-fruix-system-fruix-freebsd/metadata/freebsd-source.scm declarative_source_model=ok ``` The harness also verified that: - `metadata/freebsd-source.scm` exists - `metadata/freebsd-base.scm` contains a nested source block - `metadata/store-layout.scm` records the declared source explicitly - native build info files contain a `declared-source` block with: - `kind . local-tree` - `path . "/usr/src"` ## Result Phase 16.1 is complete. Fruix now has an explicit source declaration layer for FreeBSD bases while preserving the current validated `/usr/src`-driven native build path. That means Phase 16.2 can focus narrowly on the next real boundary: - fetching or materializing declared FreeBSD source inputs under Fruix control - instead of just describing them