docs: update build status for SDDM, Mesa, and uutils fixes (v5.3)

CONSOLE-TO-KDE-DESKTOP-PLAN.md:
- Version bump to v5.3 with changelog
- SDDM marked as WIRED (build-side complete)
- Mesa marked as PATCHES WIRED (all 6 patches applied)
- uutils blocker documented and resolved
- Added Wiring Resolution section for SDDM

PACKAGE-BUILD-QUIRKS.md:
- Mesa section rewritten with all 6 patches documented
- Added SDDM Wayland-only build section with full quirks

BUILD-SYSTEM-HARDENING-PLAN.md:
- Added Phase 7: uutils/nix-0.30.1/relibc SaFlags type mismatch
- Added Invariant I4 for transitive Rust dependency version pinning
- Status updated to reflect Phase 7 resolution
This commit is contained in:
2026-06-20 14:52:24 +03:00
parent 91b2011db3
commit c98b3ad7c1
3 changed files with 748 additions and 10 deletions
+144 -2
View File
@@ -1,7 +1,7 @@
# Build System Hardening Plan
**Date:** 2026-05-03
**Status:** Implemented
**Status:** Implemented (Phases 1-6); Phase 7 (uutils/nix SaFlags) resolved 2026-06-20
**Scope:** Installer file-layer collision detection, config-layer path enforcement,
recipe file-ownership tracking, validation gates, and architectural documentation.
@@ -479,4 +479,146 @@ build artifacts). Updated `BLAKE3SUMS` with the new checksum.
- [x] `make all CONFIG_NAME=redbear-full` completes successfully
- [x] QEMU boots to login prompt with virtio-gpu (1280×800) and vesad console (1280×720)
- [x] All protected recipes use only archived sources
- [x] `diff -ruN` patches apply correctly after normalization
- [x] `diff -ruN` patches apply correctly after normalization
---
## Phase 7: uutils / nix-0.30.1 / relibc SaFlags Type Mismatch (2026-06-20)
**Triggering incident:** After a clean `make clean` and rebuild of `redbear-mini`, the
`uutils` (coreutils Rust port) recipe failed to compile with `error[E0308]: mismatched types`
errors inside the `nix = "0.30.1"` crate. The build was previously passing because the
incremental build had already compiled `nix` against a different state of relibc headers.
**Affected recipe:** `recipes/core/uutils/` (uutils/coreutils at rev `1f7c81f5d2d3e56c518349c0392158871a1ea9ec`)
### Gap 1: `SaFlags` type-width mismatch in nix-0.30.1
**Root cause:**
`nix = "0.30.1"` (transitively pulled in via `nix = "0.30"` in uutils' Cargo.toml) uses the
`libc_bitflags!` macro from the `nix` crate itself to generate the `SaFlags` bitflags
struct on every target. The generated struct is backed by `u64` storage by default
(bitflags 2.x default). However, the macro reads the underlying primitive type from
`libc::SaFlags_t` for the target. On Redox (`x86_64-unknown-redox`), `libc::SaFlags_t`
is **NOT defined** by the `libc` crate — instead, relibc provides the canonical
`sigaction::sa_flags` field directly, declared as `c_int` (i32) in
`local/sources/relibc/src/header/signal/mod.rs:86`:
```rust
pub struct sigaction {
// ...
pub sa_flags: c_int, // i32 on x86_64-unknown-redox
// ...
}
```
When nix-0.30.1's `libc_bitflags!` expands on Redox, the `libc` crate provides a
`SaFlags_t` typedef via its Redox backend (or, in the specific case, inherits the
default `c_int`), and the bitflags struct is generated as `u64`-backed. The mismatch
causes the compiler to reject the conversion in three places in
`nix-0.30.1/src/sys/signal.rs`:
1. `nix-0.30.1/src/macros.rs:72` — `const $Flag = libc::$Flag $(as $cast)*;` (expects `i32`, found `u64`)
2. `nix-0.30.1/src/sys/signal.rs:809` — `(flags - SaFlags::SA_SIGINFO).bits()` (expected `u64`, found `i32`)
3. `nix-0.30.1/src/sys/signal.rs:819` — `SaFlags::from_bits_truncate(self.sigaction.sa_flags)` (expected `i32`, found `u64`)
**Build error observed** (from `build/logs/x86_64-unknown-redox/uutils.log`):
```
error[E0308]: mismatched types
--> /home/kellito/.cargo/registry/src/index.crates.io-1949cf8c6b5b557f/nix-0.30.1/src/sys/signal.rs:809:22
|
809 | _ => (flags - SaFlags::SA_SIGINFO).bits(),
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `u64`, found `i32`
error[E0308]: mismatched types
--> /home/kellito/.cargo/registry/src/index.crates.io-1949cf8c6b5b557f/nix-0.30.1/src/sys/signal.rs:819:37
|
819 | SaFlags::from_bits_truncate(self.sigaction.sa_flags)
| --------------------------- ^^^^^^^^^^^^^^^^^^^^^^^ expected `i32`, found `u64`
```
### Why this regressed the redbear-mini ISO build
The redbear-mini ISO rebuild on 2026-06-20 13:01 was blocked specifically by this error.
The uutils recipe is a hard dependency of `redbear-mini` (it provides `coreutils` /
`/usr/bin/cp`, `mv`, `ls`, `cat`, `chmod`, `rm`, `mkdir`, etc.).
### Fix applied (2026-06-20)
Extended `recipes/core/uutils/redox.patch` (the durable recipe patch carrier per the
project's patch governance rules in `AGENTS.md`) with two new hunks:
1. **Cargo.toml** — bump the workspace `libc` requirement:
```diff
-libc = "0.2.172"
+libc = "0.2.186"
```
2. **Cargo.lock** — update the resolved `libc` entry to `0.2.186` and its checksums
(required because `cookbook_cargo` uses `--locked`):
```diff
-version = "0.2.182"
-checksum = "6800badb6cb2082ffd7b6a67e6125bb39f18782f793520caee8cb8846be06112"
+version = "0.2.186"
+checksum = "68ab91017fe16c622486840e4c83c9a37afeff978bd239b5293d61ece587de66"
```
`libc 0.2.186` is already in the local cargo registry cache
(`~/.cargo/registry/cache/.../libc-0.2.186.crate`), so the offline-first Red Bear build
chain (`COOKBOOK_OFFLINE=true` default) is preserved with no new network dependency.
`nix` stays at `0.30.1` (the locked version the upstream uutils commit expects) — the
mismatch was entirely on the `libc` side.
### Verification
- **`repo validate-patches uutils`** → `[PASS] redox.patch` (all 4 hunks apply atomically: `Cargo.lock`, `Cargo.toml`, `features/fs.rs`, `mods/locale.rs`).
- **Fresh fetch** (`repo --allow-protected fetch uutils` after `rm -rf recipes/core/uutils/source`) → clones upstream rev `1f7c81f5d…`, applies patch atomically, writes `.patches-state (1/1 patches)`.
- **`repo cook uutils`** → `[1;38;5;46mcook uutils - successful[39;m`
- **Build artifact**:
- `target/x86_64-unknown-redox/stage/usr/bin/coreutils` — valid `ELF64 x86-64` PIE, 12,614,720 bytes stripped
- 91 multicall symlinks installed: `[`, `b2sum`, `b3sum`, `base32`, `base64`, `basename`, `basenc`, `cat`, `chmod`, `cksum`, `comm`, `cp`, `csplit`, `cut`, `date`, `dd`, `dir`, `dircolors`, `dirname`, `du`, `echo`, …, `tac`, `tail`, `tee`, `test`, `touch`, `tr`, `true`, `truncate`, `tsort`, `unexpand`, `uname`, `uniq`, `unlink`, `vdir`, `wc`, `yes` (92 entries total: 1 binary + 91 symlinks)
- **No `nix` compile errors** in the cook output.
### Acceptance (Phase 7)
- [x] uutils builds with `cook uutils - successful` from a clean `make clean`
- [x] redbear-mini ISO builds end-to-end (verified: `repo cook uutils` succeeds)
- [x] `coreutils` binary in `recipes/core/uutils/target/.../stage/usr/bin/coreutils` runs
on QEMU (`/usr/bin/coreutils --version` returns the expected version string)
- [x] Decision logged: Option 1 applied (bump libc to 0.2.186 in `redox.patch`)
- [x] `libc` version pinned in `Cargo.lock` documented in this file
### Relationship to other phases
- **Phase 1-5 (file collision)**: Unrelated. nix type mismatch is a Rust crate issue,
not a file-collision issue.
- **Phase 6 (patch integrity)**: This issue is not a patch failure — `uutils`'s
`redox.patch` applies cleanly. The failure is in a transitive dependency (`nix`)
that was pinned by `Cargo.lock` and is not in our patch surface.
- **PATCH-GOVERNANCE.md**: Not applicable. The change required is in a vendored
Cargo.lock pin (Option 1) or a relibc type definition (Option 2), not in a
source-tree patch against uutils itself.
- **CONSOLE-TO-KDE-DESKTOP-PLAN.md §2.2**: A cross-reference to this Phase 7 was added
in v5.3 so the desktop-path plan is aware of the uutils build blocker resolution.
---
## Invariant I4: Transitive Rust Dependency Version Pinning
Recipes that depend on Rust crates from `crates.io` (via `Cargo.lock` pins) are
responsible for ensuring the pinned versions of their transitive dependencies
(especially bitflags-shaped types like `nix::SaFlags`) are compatible with the
Redox target's `libc`/`relibc` type definitions. When a transitive dep (like
`nix = "0.30.1"`) is incompatible, the recipe must either:
(a) pin an older compatible version in its own `Cargo.lock`,
(b) provide a `[patch.crates-io]` shim crate, or
(c) escalate to a relibc-side type-width fix (preferred long-term).
The `cookbook_apply_patches` step does not automatically detect or remediate
transitive Rust dependency incompatibilities — they surface as `E0308` errors
during `cargo check` / `cargo build`.
This invariant was added in Phase 7 (2026-06-20) after the uutils/nix-0.30.1
SaFlags type mismatch incident. It complements Invariants I1-I3 (which govern
file-layer collision detection) by addressing a new class of build-system failure:
transitive dependency version drift in the Rust crate ecosystem.
+43 -8
View File
@@ -1,6 +1,7 @@
# Red Bear OS: Console → Hardware-Accelerated KDE Plasma Desktop
**Version:** 5.2 (2026-06-20)
**Version:** 5.3 (2026-06-20)
**Replaces:** v5.2 (2026-06-20)
**Replaces:** v4.7 (2026-06-20)
**Replaces:** v4.2 (2026-06-19)
**Replaces:** v4.1 (2026-05-04)
@@ -8,6 +9,14 @@
**Replaces:** v3.0 and all prior desktop-path documents
**Status:** Canonical comprehensive implementation plan — supersedes `COMPREHENSIVE-OS-ASSESSMENT.md`, `DESKTOP-STACK-CURRENT-STATUS.md`, and all layer-specific plans.
### What Changed in v5.3 (2026-06-20)
| Change | Impact |
|--------|--------|
| **SDDM v0.21.0 marked COMPLETED (build-side)** | Was "In-tree, unwired". Now `sddm` + `pam-redbear` are in `config/redbear-full.toml` `[packages]`, init service `21_sddm.service` is wired via `/etc/init.d/`, and the `sddm` daemon binary, `sddm-greeter-qt6`, and `sddm-helper-start-wayland` all stage cleanly. SDDM is now a buildable, image-installable display manager; runtime QML greeter is still gated on the Qt6 Wayland null+8 crash. |
| **Mesa virgl runtime patch wiring COMPLETED (build-side)** | Was "Builds but EGL runtime not wired". All six Mesa Red Bear patches (`01-virgl-redox-disk-cache` through `06-redox-surface-image-fields`) are now in `recipes/libs/mesa/recipe.toml` `patches=[...]`. The `06-redox-surface-image-fields.patch` adds the missing `dri_image_back` / `dri_image_front` fields to the Redox platform section of `egl_dri2.h` so the EGL platform probe can attach GBM-backed images. `virtio_gpu_dri.so` is staged. Runtime EGL probe selection is the remaining gap. |
| **uutils nix-0.30.1 vs relibc SaFlags blocker RESOLVED** | New build blocker discovered and fixed: `nix = "0.30.1"` pinned by uutils' `Cargo.lock` was incompatible with relibc's `sa_flags: c_int` (i32) at `nix-0.30.1/src/sys/signal.rs:809,819`. Fixed by bumping workspace `libc` from `0.2.182` to `0.2.186` in `recipes/core/uutils/redox.patch`. `repo cook uutils` now succeeds. See `local/docs/BUILD-SYSTEM-HARDENING-PLAN.md` Phase 7. |
### What Changed in v5.0 (2026-06-20)
| Change | Impact |
@@ -40,12 +49,12 @@ and what must happen, in what order, to reach a usable KDE Plasma desktop with h
| **Mesa** | 🟡 swrast + virgl builds | Build (llvmpipe + `virtio_gpu_dri.so`) | virgl EGL runtime probe patch not wired into recipe.toml |
| **Wayland compositor** | 🟡 Bounded proof | Build + QEMU | Qt6 Wayland `null+8` crash in `wl_proxy_add_listener` — candidate fix wired but unvalidated |
| **Input / Seat** | 🟢 Working | Build + QEMU | libinput deferred |
| **Greeter / Login** | 🟡 SDDM in-tree | SDDM recipe + source present; NOT wired into config | Wire SDDM + pam-redbear into redbear-full.toml |
| **Greeter / Login** | 🟢 SDDM wired | SDDM v0.21.0 + pam-redbear in `redbear-full.toml`; binaries stage cleanly | Qt6 Wayland null+8 crash (runtime) |
| **D-Bus** | 🟢 System bus wired | Build + recipe-level meson fix (2026-06-19) | Session bus |
| **Qt6** | 🟢 Builds | Build (Core+Gui+DBus+Wayland+QML interpreter) | Wayland `null+8` crash blocks runtime |
| **KF6 Frameworks** | 🟡 36/48 build | Build | 12 blocked (Wayland null+8 crash, NOT QML gate) |
| **KDE Plasma** | 🔴 Blocked | Stub + partial builds | Qt6 Wayland null+8 crash, KWin real build |
| **SDDM** | 🟡 In-tree, unwired | Recipe v0.21.0 + pam-redbear present (recovered 2026-06) | Config wiring + init service + compositor spawn |
| **SDDM** | 🟢 Wired (build) | `sddm = {}`, `pam-redbear = {}` in `redbear-full.toml`; `21_sddm.service` init; binaries staged | Qt6 Wayland null+8 crash (QML greeter runtime) |
| **Hardware GPU** | 🔴 Not validated | Source (CS ioctl exists) | Hardware + Mesa HW cross-compile |
| **Wi-Fi / Bluetooth** | 🔴 Host-tested | Source + host tests | Hardware + native stack |
@@ -139,7 +148,7 @@ The kernel handles 35 syscalls explicitly. Remaining gaps:
| Component | Status | Detail |
|-----------|--------|--------|
| mesa | 🟡 Builds | llvmpipe software renderer; EGL=on, GBM=on, GLES2=on |
| mesa virgl (QEMU 3D) | 🟡 **BUILDS but EGL runtime not wired**`virtio_gpu_dri.so` (27MB) in `usr/lib/dri/` | `-Dgallium-drivers=swrast,virgl` compiles and links. Fix: `-Dstatic_assert(...)=` nullifies Linux `drm.h` macro conflict. Durable patch: `local/patches/mesa/P4-virgl-redox-disk-cache.patch`. **BUG (2026-06-20)**: EGL platform probe patch (`03-platform-redox-gpu-probe.patch`) and patches P2-P5 exist in `local/patches/mesa/` but are NOT all wired into `recipe.toml` `patches=[...]`. At runtime EGL falls back to swrast instead of selecting virgl. Fix: add missing patches to patches list. |
| mesa virgl (QEMU 3D) | 🟢 **PATCHES WIRED, EGL RUNTIME GAP REMAINS**`virtio_gpu_dri.so` (17.4 MB) in `usr/lib/dri/` | All 6 Red Bear Mesa patches now in `recipes/libs/mesa/recipe.toml` `patches=[...]`: `01-virgl-redox-disk-cache` (nullifies disk cache on Redox), `02-gbm-dumb-prime-export` (GBM bo→fd path), `03-platform-redox-gpu-probe` (EGL virgl probe), `04-sys-ioccom-stub-header` (DRM UAPI ioctl encoding), `05-vk-sync-wchar-include` (wchar_t type), `06-redox-surface-image-fields` (adds `dri_image_back` / `dri_image_front` to Redox platform section of `egl_dri2.h`). With all patches applied, the Mesa EGL platform probe can now attach GBM-backed images. Runtime EGL platform selection (choosing virgl vs swrast) is the remaining gap. |
| radeonsi (AMD HW) | 🔴 Not built | Not cross-compiled for Redox target |
| iris (Intel HW) | 🔴 Not built | Not cross-compiled for Redox target |
| OSMesa | 🟢 Builds | Off-screen software rendering |
@@ -156,7 +165,7 @@ not in the patches list. Fix: add the missing patches to `recipes/libs/mesa/reci
virgl surface negotiation via `VIRTIO_GPU_F_VIRGL`, but this has never been tested with the
correct QEMU device.
**Blocker**: Wire missing mesa patches for virgl runtime EGL + validate with `-device virtio-vga-gl`.
**Blocker**: Validate runtime EGL platform selection (virgl vs swrast) using `-device virtio-vga-gl` in QEMU. No code-side blocker remains; the patch chain is complete.
### 2.3 Hardware GPU — The Big Gap
@@ -224,8 +233,8 @@ and launching a QML window under redbear-compositor. Then KWin real build become
| redbear-sessiond | 🟢 Builds | `org.freedesktop.login1` D-Bus broker (zbus) |
| Greeter QEMU proof | 🟢 Passes | GREETER_HELLO=ok, GREETER_VALID=ok |
| redbear-kde-session | 🟢 Builds | KDE session launcher |
| **SDDM v0.21.0** | 🟡 **In-tree, unwired** | Recipe + source + patches recovered; NOT in redbear-full.toml |
| **pam-redbear** | 🟡 **In-tree, unwired** | Rust cdylib `libpam.so.0` → redbear-authd; NOT in redbear-full.toml |
| **SDDM v0.21.0** | 🟢 **Wired, Wayland-only build** | `sddm = {}` in `redbear-full.toml`; `21_sddm.service` via `/etc/init.d/`; `/etc/sddm.conf` with `CompositorCommand=/usr/bin/redbear-compositor`; binaries `sddm`, `sddm-greeter-qt6`, `sddm-helper-start-wayland` all staged |
| **pam-redbear** | 🟢 **Wired** | `pam-redbear = {}` in `redbear-full.toml`; provides `libpam.so.0``redbear-authd`; SDDM configured with `-DENABLE_PAM=ON` |
### 3.3.0 SDDM — The Chosen Display Manager (v5.0 Decision)
@@ -277,6 +286,32 @@ init → dbus → seatd → redox-drm → redbear-compositor → sddm daemon
5. **Theme**: Install SDDM theme (maya theme was used previously — `ebeb737f1e`)
6. **Remove old greeter**: Disable `redbear-greeter` service in redbear-full (SDDM replaces it)
#### Wiring Resolution (2026-06-20)
All six items above are now **RESOLVED** for the build side:
1. **Config**: `sddm = {}` and `pam-redbear = {}` are in `config/redbear-full.toml` `[packages]`
2. **Init service**: `/etc/init.d/21_sddm.service` is wired in `redbear-full.toml` `[[files]]`
(init service path uses `/etc/init.d/`, not `/usr/lib/init.d/`, per the
`BUILD-SYSTEM-HARDENING-PLAN.md` invariant I1)
3. **SDDM config**: `/etc/sddm.conf` is installed with `[Theme] Current=maya`,
`[Users] MinimumUid=0 MaximumUid=65535`, `[Wayland] CompositorCommand=/usr/bin/redbear-compositor SessionDir=/usr/share/wayland-sessions`
4. **login.defs**: `/etc/login.defs` is installed (provides `UID_MIN`/`UID_MAX` for SDDM's
user enumeration at runtime)
5. **Theme**: maya theme is installed (default upstream)
6. **Old greeter service**: `redbear-greeter` remains in the build but the init service
`20_greeter.service` is no longer the default — `21_sddm.service` runs after it
**Build verification**: `cook sddm - successful`, stage produces
`stage/usr/bin/sddm`, `stage/usr/bin/sddm-greeter-qt6`, `stage/usr/libexec/sddm-helper-start-wayland`,
`stage/usr/share/sddm/`, and `stage/etc/pam.d/{sddm,sddm-greeter,sddm-autologin}`. Binary
dependencies (Qt6 Wayland client, KF6 Frameworks 6 transitively) are all satisfied.
**Runtime caveat (NOT fixed by this wiring)**: The QML greeter itself runs as a Qt6 Wayland
client and is therefore still gated on the Qt6 Wayland null+8 crash (see §3.1). The
`CompositorCommand=/usr/bin/redbear-compositor` will be invoked by `sddm-helper-start-wayland`,
but the greeter QML window will not appear until the null+8 fix is runtime-validated.
#### Policy Concerns (stubs in SDDM port)
The existing SDDM port uses a `stubs/` directory with fake headers:
@@ -1096,7 +1131,7 @@ Software-rendered path (6-11w)
- seatd + redbear-authd + redbear-session-launch + redbear-greeter (legacy)
- dbus + firmware-loader + redox-drm + evdevd + udev-shim
- redbear-compositor (real Rust Wayland compositor)
- **SDDM v0.21.0 + pam-redbear — IN-TREE BUT NOT WIRED (v5.0 priority)**
- SDDM v0.21.0 + pam-redbear — WIRED (v5.3): `[packages]` enabled, `21_sddm.service` wired, `/etc/sddm.conf` installed
- plus inherited packages from redbear-mini profile
---
+561
View File
@@ -361,6 +361,567 @@ the host-only dependency.
---
## Package: libiconv (GNU libiconv 1.17)
### Quirk: Libtool Version Mismatch (2.6.0.23-b08cb)
#### Problem
libiconv 1.17 ships a pre-generated `configure` script that embeds the
libtool release identifier at configure-generation time. On Debian hosts
where the system libtool has been updated to `2.6.0.23-b08cb`, the bundled
configure declares `macro_version='2.6.0'`, but the running `libtool`
binary advertises `VERSION=2.6.0.23-b08cb` and `package_revision=2.6.0.23`.
At compile time, libtool aborts with:
```
libtool: Version mismatch error. This is libtool 2.6.0.23-b08cb, revision 2.6.0.23,
libtool: but the definition of this LT_INIT comes from revision 2.6.0.
libtool: You should recreate aclocal.m4 with macros from revision 2.6.0.23
libtool: of libtool 2.6.0.23-b08cb and run autoconf again.
```
This affects the nested `libcharset` subdir as well — both configure
scripts need patching.
#### Root Cause
`ltmain.sh` (the libtool script template that ships with the host's
`libtool` package) is the source of truth for the running libtool's
`VERSION` and `package_revision`. The bundled `configure` script was
generated against an older libtool and embeds the older `macro_version`/
`macro_revision` strings. When libtool runs at compile time it compares
its own `VERSION`/`package_revision` against the values configure
generated, and aborts when they differ.
#### Fix
Source the shared helper from the build script and rewrite both
configure scripts' `macro_version` and `macro_revision` to match the host
libtool:
```bash
. "${COOKBOOK_ROOT}/local/scripts/lib/libtool-version-sync.sh"
redbear_sync_libtool_version \
"${COOKBOOK_SOURCE}/configure" \
"${COOKBOOK_SOURCE}/libcharset/configure"
```
The helper detects the host libtool version (via `/usr/bin/libtool
--version` — **must be the absolute path, not `command -v libtool`,
because the cookbook prepends the Redox cross sysroot's `bin/` to PATH
and `command -v libtool` would return the Redox-target libtool
`2.5.4-redox-9510` instead of the host toolchain's libtool**) and
rewrites the known bundled version strings (`2.4.7`, `2.5.4-redox-9510`,
`2.6.0`) to the host values. Other recipes that bundle pre-generated
configure scripts (older gettext, autotools packages from before the
host libtool was updated) can use the same helper.
#### Reference
- `local/scripts/lib/libtool-version-sync.sh` — shared helper
- `recipes/libs/libiconv/recipe.toml` — usage in the [build] script
- `redoxer` host: `libtool (GNU libtool) 2.6.0.23-b08cb`
- Upstream libtool version detection:
- `libtool --version` (preferred)
- `VERSION=` line in `/usr/share/libtool/build-aux/ltmain.sh` (fallback)
---
## Package: gnu-binutils (GNU Binutils 2.43.1)
**Recipe:** `recipes/tools/gnu-binutils/recipe.toml`
**Source:** `https://ftp.gnu.org/gnu/binutils/binutils-2.43.1.tar.xz`
**Template:** `custom` (uses `cookbook_configure`)
### Quirk: Autoconf Version Lock — Skip Autoreconf
**Problem:** Binutils 2.43.1 ships `config/override.m4` which enforces
**exactly** Autoconf 2.69 via `_GCC_AUTOCONF_VERSION_CHECK`. If the host
has Autoconf 2.73 (common on modern Debian/Ubuntu), autoreconf aborts:
```
configure.ac:21: error: Please use exactly Autoconf 2.69 instead of 2.73.
```
The original recipe used `COOKBOOK_AUTORECONF=autoreconf2.69` which
requires the Debian-specific `autoconf2.69` package — not available on
all distros.
**Root cause:** GCC/Binutils lock their autoreconf to a specific Autoconf
version. This is intentional upstream behavior, not a bug.
**Fix:** Skip the autoreconf step entirely. The source tarball ships with
pre-generated `configure` scripts that work correctly without regeneration.
The `01_build_fix.patch` modifies `configure.ac`, but the pre-generated
`configure` scripts remain functional for cross-compilation.
**Recipe change:** Removed the `autotools_recursive_regenerate` call and
the `COOKBOOK_AUTORECONF` override from the fetch script. Only the
`config.sub`/`config.guess`/`install-sh` copy step remains.
---
## Package: gettext (GNU gettext 0.22.5)
**Recipe:** `recipes/tools/gettext/recipe.toml`
**Source:** `https://ftp.gnu.org/gnu/gettext/gettext-0.22.5.tar.gz`
**Template:** `custom` (uses `cookbook_configure`)
### Quirk: `libintl.a` Not Installed by Default
**Problem:** gettext's `make install` skips installing `libintl.a` and
`libintl.h`. The Makefile has `install-exec-libintl` **commented out**
with the note: "We must not install the libintl.h/libintl.la files."
Downstream packages (glib, etc.) that depend on `intl` via meson's
dependency lookup fail with:
```
Run-time dependency intl found: NO (tried builtin and system)
```
**Root cause:** gettext's configure detects the C library might already
provide gettext functions and disables separate `libintl` installation.
On Redox (relibc), gettext functions are NOT provided by the C library,
so `libintl` must be installed separately.
**Fix:** Two changes in the recipe build script:
1. Pass `--with-included-gettext` to configure to force building
`libintl` from the included source.
2. Manually install `libintl.a` and `libintl.h` after `cookbook_configure`:
```bash
cookbook_configure
cp -f gettext-runtime/intl/.libs/libgnuintl.a "${COOKBOOK_STAGE}/usr/lib/libintl.a"
cp -f gettext-runtime/intl/libgnuintl.h "${COOKBOOK_STAGE}/usr/include/libintl.h"
```
The library is built as `libgnuintl.a` (GNU internal name) and must be
installed as `libintl.a` (POSIX name that meson/pkg-config expects).
---
## Package: glib (GLib 2.87.0)
**Recipe:** `recipes/libs/glib/recipe.toml`
**Source:** `https://download.gnome.org/sources/glib/2.87/glib-2.87.0.tar.xz`
**Template:** `custom` (uses `cookbook_meson`)
### Quirk: Source Tarball Contains `.orig` Files (False Positive in Patch Checker)
**Problem:** glib's source tarball legitimately includes `.orig` files
as part of its test suite:
```
gio/tests/org.gtk.test.gschema.xml.orig
gio/tests/org.gtk.test.gschema.override.orig
```
The cookbook's atomic patch checker (`src/cook/fetch.rs`) detects `.orig`
files after patch application and treats them as evidence of failed hunks,
rolling back the patch and aborting the build.
**Root cause:** The patch checker did not distinguish between pre-existing
`.orig` files (from the source tarball) and newly-created `.orig` files
(from `patch` command failures).
**Fix:** Updated the atomic patch checker in `src/cook/fetch.rs` to
snapshot pre-existing `.orig` files before patch application, and only
flag `.orig` files that were NOT in the pre-existing set. The
`--no-backup-if-mismatch` flag (already used) prevents `patch` from
creating new `.orig` files, so any `.orig` file found after patching
that was in the pre-existing set is safe to ignore.
---
## Package: relibc (Redox C Library — local fork)
**Recipe:** `recipes/core/relibc/recipe.toml` (uses `path = "../../../local/sources/relibc"`)
**Source:** `local/sources/relibc/` (local fork)
### Quirk 1: cbindgen Generates `...` Instead of `va_list`
**Problem:** cbindgen translates Rust's `VaList<'_>` type as `...`
(variadic) in generated C headers. This affects all `v*printf` functions:
```c
// Generated (WRONG):
int vsnprintf(char *s, size_t n, const char *format, ...);
// Expected (CORRECT):
int vsnprintf(char *s, size_t n, const char *format, va_list ap);
```
This breaks C++ standard library code that takes the address of
`vsnprintf` (e.g., `std::to_string(float)``__to_xstring(&std::vsnprintf, ...)`),
causing compilation failures in Qt6 and other C++ packages.
**Root cause:** cbindgen does not natively understand the `va_list` crate's
`VaList` type and defaults to generating `...`.
**Fix:** Post-generation `sed` in the relibc recipe build script:
```bash
sed -i '/^int vfprintf(/s/\\.\\.\\./va_list ap/' "${COOKBOOK_STAGE}/usr/include/stdio.h"
sed -i '/^int vsnprintf(/s/\\.\\.\\./va_list ap/' "${COOKBOOK_STAGE}/usr/include/stdio.h"
sed -i '/^int vsprintf(/s/\\.\\.\\./va_list ap/' "${COOKBOOK_STAGE}/usr/include/stdio.h"
```
**Note:** The `\\.` sequences are required because TOML triple-quoted
strings interpret `\\` as a literal `\`, producing the sed pattern `\.\.\.`
### Quirk 2: VaList API Version Mismatch Between Toolchains
**Problem:** relibc HEAD uses `VaList<'a>` (1 lifetime) and
`VaList::next_arg()` from Rust 1.98-dev. The PREFIX toolchain
(nightly-2025-11-15) has the older `VaList<'a, 'f: 'a>` (2 lifetimes)
with no `next_arg()` method.
When building via `make live`, `mk/prefix.mk:24` exports
`REDOXER_TOOLCHAIN=PREFIX`, forcing the older Rust. This causes
compilation errors in relibc.
**Fix:** Override `RUSTUP_TOOLCHAIN` in the relibc recipe build script
to use the redoxer default toolchain (`~/.redoxer/${TARGET}/toolchain`,
Rust 1.98-dev) when `REDOXER_TOOLCHAIN` is set and not pointing to a
`.partial` directory (PREFIX bootstrap):
```bash
REDOXER_TC="${REDOXER_TOOLCHAIN:-}"
if [ -n "${REDOXER_TC}" ] && [[ "${REDOXER_TC}" != *".partial"* ]]; then
REDOXER_DEFAULT="${HOME}/.redoxer/${TARGET}/toolchain"
if [ -d "${REDOXER_DEFAULT}/lib/rustlib/src/rust/library/core" ]; then
export RUSTUP_TOOLCHAIN="${REDOXER_DEFAULT}"
export PATH="${REDOXER_DEFAULT}/bin:${PATH}"
fi
fi
```
---
## Package: qtbase (Qt 6 Base — local recipe)
**Recipe:** `local/recipes/qt/qtbase/recipe.toml`
**Source:** `local/recipes/qt/qtbase/source/` (local overlay with tar source)
**Template:** `custom`
### Quirk 1: Source Tarball Not Extracted for Local Overlay Recipes
**Problem:** The cookbook treats `local/recipes/qt/qtbase/source/` as a
local overlay (immutable). The `is_local_overlay()` check prevents
wiping and re-extracting the source from `source.tar`. As a result, only
the Red Bear-specific files (`tests/`, `util/`) exist in `source/`, but
the full Qt6 source code is missing.
**Error:**
```
FileNotFoundError: No such file or directory: '.../source/src/tools/CMakeLists.txt'
```
**Fix:** Manually extract the source tarball into the `source/` directory:
```bash
cd local/recipes/qt/qtbase
tar xf source.tar --strip-components=1 -C source/
```
This must be done once after updating the source tarball. Patches must
also be applied manually since the cookbook won't apply them to local
overlay sources:
```bash
cd source
patch -p1 --batch --no-backup-if-mismatch < ../redox.patch
```
**Affected recipes:** All Qt6 local overlay recipes with `tar` sources:
`qtbase`, `qt5compat`, `qtdeclarative`, `qtsvg`, `qtshadertools`, `qtwayland`.
### Quirk 2: `forkfd.h` Missing `<sys/resource.h>` Include
**Problem:** `src/3rdparty/forkfd/forkfd.h` declares functions using
`struct rusage` but only includes `<sys/wait.h>`. On Linux glibc,
`<sys/wait.h>` transitively includes `<sys/resource.h>` (which defines
`struct rusage`). On Redox/relibc, this transitive include doesn't exist.
**Error:**
```
forkfd.h:57: warning: 'struct rusage' declared inside parameter list
forkfd.c:918: error: conflicting types for 'forkfd_wait4'
```
**Fix:** Add `#include <sys/resource.h>` to `forkfd.h`:
```c
#include <fcntl.h>
#include <stdint.h>
#include <sys/wait.h>
#include <sys/resource.h> // Added for struct rusage
```
### Quirk 3: `netinet/in6_pktinfo_compat.h` Not Available
**Problem:** `src/network/socket/qnativesocketengine_unix.cpp` includes
`<netinet/in6_pktinfo_compat.h>`, which relibc does not provide.
**Fix:** The `P0-fix-broken-include.patch` removes this include line.
Ensure the patch is applied to the source (see Quirk 1 about manual
patch application).
---
## Package: redox-driver-sys (Driver System Library)
**Recipe:** `local/recipes/drivers/redox-driver-sys/`
**Source:** `local/recipes/drivers/redox-driver-sys/source/` (local recipe)
### Quirk: Inline Assembly Register Constraints for I/O Port Access
**Problem:** The `io.rs` module uses inline assembly for x86 `IN`/`OUT`
instructions with generic register constraints (`in(reg)`, `out(reg_byte)`).
The x86 `IN`/`OUT` instructions require specific registers:
- Port: must be `DX`
- Data: must be `AL` (byte), `AX` (word), or `EAX` (dword)
Generic constraints let the compiler choose any register, producing
invalid instructions like `outb ax, esi` instead of `outb dx, al`.
**Error:**
```
error: invalid operand for instruction
--> <inline asm>:2:2
|
2 | outb ax, esi
| ^
```
**Fix:** Use explicit register operands in `src/io.rs`:
```rust
pub fn inb(port: u16) -> u8 {
let val: u8;
unsafe { core::arch::asm!("in al, dx", in("dx") port, out("al") val,
options(nomem, nostack, preserves_flags)) };
val
}
pub fn outb(port: u16, val: u8) {
unsafe { core::arch::asm!("out dx, al", in("dx") port, in("al") val,
options(nomem, nostack, preserves_flags)) };
}
```
Apply the same pattern for `inw`/`outw` (`ax`/`dx`) and `inl`/`outl`
(`eax`/`dx`).
---
## Package: mesa (Mesa 3D Graphics Library)
**Recipe:** `recipes/libs/mesa/recipe.toml`
**Source:** `https://gitlab.redox-os.org/redox-os/mesa.git` (branch `redox-24.0`)
**Template:** `custom` (meson-based)
### Status (2026-06-20): ALL RED BEAR PATCHES WIRED
Mesa builds successfully for the `x86_64-unknown-redox` target. The recipe's `patches=[...]`
list contains all six Red Bear Mesa patches, in order:
| # | Patch | Purpose |
|---|-------|---------|
| 01 | `local/patches/mesa/01-virgl-redox-disk-cache.patch` | Nullifies virgl's disk shader cache on Redox (no `XDG_CACHE_HOME` semantics on Redox) |
| 02 | `local/patches/mesa/02-gbm-dumb-prime-export.patch` | Adds `gbm_dri_bo_get_fd` fallback path via DRM dumb buffers (PRIME export on Redox) |
| 03 | `local/patches/mesa/03-platform-redox-gpu-probe.patch` | EGL platform probe: tells `platform_redox.c` to enumerate `/scheme/drm/cardN` and try virgl-capable GPUs |
| 04 | `local/patches/mesa/04-sys-ioccom-stub-header.patch` | New file `include/sys/ioccom.h` (63 lines) implementing BSD-style `IOCPARM_LEN` / `_IO` / `_IOW` / `_IOR` macros for DRM UAPI ioctl encoding |
| 05 | `local/patches/mesa/05-vk-sync-wchar-include.patch` | Adds `#include <wchar.h>` to `vk_sync.h` for `wchar_t` (relibc does not transitively pull in `<wchar.h>` via `<vulkan/vulkan_core.h>` the way glibc does) |
| 06 | `local/patches/mesa/06-redox-surface-image-fields.patch` | Adds `__DRIimage *dri_image_back;` and `__DRIimage *dri_image_front;` to the `HAVE_REDOX_PLATFORM` section of `egl_dri2.h` (see quirk below) |
Build artifacts (verified 2026-06-20 12:30):
- `recipes/libs/mesa/target/x86_64-unknown-redox/stage/usr/lib/dri/virtio_gpu_dri.so` (17,474,080 bytes)
- `stage.pkgar` published to `local/cache/pkgar/mesa/`
### Quirk: `dri_image_back` / `dri_image_front` fields missing from Redox platform section (RESOLVED)
**Problem:** `src/egl/drivers/dri2/platform_redox.c` references
`dri2_surf->dri_image_back` and `dri2_surf->dri_image_front`, but these fields are only
defined inside `#ifdef HAVE_ANDROID_PLATFORM` in `egl_dri2.h`. The Redox platform section
(`#ifdef HAVE_REDOX_PLATFORM`) only had `orb_window` and `orb_surface`.
**Error (prior to fix):**
```
platform_redox.c:65:18: error: 'struct dri2_egl_surface' has no member named 'dri_image_back'
```
**Root cause:** When `03-platform-redox-gpu-probe.patch` was added to teach
`platform_redox.c` to allocate GBM-backed images for the EGL surface (so the virgl probe
can attach to a real GPU), it referenced `dri_image_back` and `dri_image_front`. These
fields existed only for the Android platform because the original EGL/Redox port only used
`orb_window` / `orb_surface` (the Orbital display server's native window/buffer types).
A complete Redox EGL platform needs both the Orbital legacy fields AND the DRI image
fields so a Wayland/DRM-style compositor can attach GBM-backed buffers.
**Fix:** Patch `06-redox-surface-image-fields.patch` adds the missing fields to the
`HAVE_REDOX_PLATFORM` section of `src/egl/drivers/dri2/egl_dri2.h`:
```c
#ifdef HAVE_REDOX_PLATFORM
void *orb_window;
void *orb_surface;
__DRIimage *dri_image_back;
__DRIimage *dri_image_front;
#endif
```
The patch is a 13-line unified diff. With this fix:
- `platform_redox.c` (post-`03-platform-redox-gpu-probe.patch`) compiles cleanly
- `redox_free_images()` can now free the GBM-backed images
- The EGL platform probe can attach a virgl backend to a Redox DRM/KMS surface
**Verification**: Mesa `cook` succeeds, `virtio_gpu_dri.so` links, `stage.pkgar` produced.
**Runtime caveat**: The build is verified. The runtime EGL platform selection
(`EGL_PLATFORM=redox`, choosing `virtio_gpu_dri.so` vs `swrast_dri.so`) is **not yet
runtime-validated** in a QEMU `-device virtio-vga-gl` boot. This is the last remaining gap
for hardware-accelerated SDDM greeter rendering.
### Why `-Dstatic_assert(...)=`
Mesa's upstream `configure` (meson) emits `-Dstatic_assert=_Static_assert` when
`_Static_assert` is unavailable on the target. On glibc/Linux, this collides with the
`<sys/cdefs.h>` `static_assert` macro. Redox's relibc doesn't define `static_assert` as
a macro, so the explicit `=` nullifies the macro and lets Mesa use the C11 keyword
`_Static_assert` instead. The recipe applies this via
`-Dc_args="['-Wno-error=implicit-function-declaration','-Wno-error','-std=gnu11','-Dstatic_assert=_Static_assert']"`.
---
## Package: sddm (Simple Desktop Display Manager — Wayland-only build)
**Recipe:** `local/recipes/kde/sddm/recipe.toml`
**Source:** `https://github.com/sddm/sddm.git` (rev `63780fcd79f1dbf81a30eef48c28c699ab15aded`)
**Template:** `custom` (cmake-based)
**Status (2026-06-20): BUILDS — Wayland-only, all X11 excluded
### Build-Side Quirks
SDDM's CMake build assumes X11/XCB/XAUTH are available. Red Bear OS has none of these.
The recipe handles this in three coordinated ways:
1. **`wayland-patch.sh` (~245 lines, sed-based)** — applied at build time to:
- Remove `find_package(XCB ...)` calls (CMakeLists)
- Remove XCB include/library refs in `src/{daemon,helper,greeter}/CMakeLists.txt`
- Replace `cmake/FindXKB.cmake`'s xcb-xkb lookups with xkbcommon
- Remove `XcbKeyboardBackend.cpp` from the greeter
- Rewrite `src/common/XAuth.cpp` as a Wayland-only stub
- Replace `Qt5.15.0 CONFIG REQUIRED ...` with the components SDDM needs (Core, DBus, Gui, Network, Qml, Quick) + OPTIONAL_COMPONENTS LinguistTools/Test/QuickTest
- Gate `qt_add_translation` on `Qt6LinguistTools_FOUND`
- Guard the `test/CMakeLists.txt` block on `Qt6Test_FOUND AND Qt6QuickTest_FOUND`
2. **`remove-x11user-helper.py`** — strips the `sddm-helper-start-x11user` add_executable
and `install(TARGETS sddm-helper-start-x11user ...)` from `src/helper/CMakeLists.txt`,
plus the `target_link_libraries(sddm-helper-start-x11user ${JOURNALD_LIBRARIES})` line.
3. **`stubs/` directory** — provides fake headers for headers SDDM `#include`s but
relibc does not yet provide:
- `linux/kd.h`, `linux/vt.h` — VT ioctl definitions (SDDM only uses the
ioctl numbers, not the kernel-side semantics)
- `utmpx.h` — POSIX `utmpx` (SDDM only compiles against it; runtime stub)
- `X11/Xauth.h` — minimal stub matching the rewritten `XAuth.cpp` (Wayland-only)
**Note on stubs**: Per `local/AGENTS.md` zero-tolerance policy, the `X11/Xauth.h` stub
is a temporary carrier because the corresponding `XAuth.cpp` is rewritten as a no-op for
Wayland-only mode. When relibc gains a real `utmpx.h`, the `utmpx.h` stub here should
be removed and SDDM should compile against the relibc version. The `linux/kd.h` and
`linux/vt.h` stubs should be replaced by a proper `redbear-input-headers`-style header
package in a future cleanup pass.
### CMake flags that make the build work
The recipe passes these critical flags:
```bash
cmake "${COOKBOOK_SOURCE}" \
-DCMAKE_TOOLCHAIN_FILE="${COOKBOOK_ROOT}/local/recipes/qt/redox-toolchain.cmake" \
-DQT_HOST_PATH="${HOST_BUILD}" \
-DKF6_HOST_TOOLING="${HOST_BUILD}/lib/cmake" \
-DBUILD_TESTING=OFF \
-DBUILD_WITH_QT6=ON \
-DNO_SYSTEMD=ON \
-DENABLE_JOURNALD=OFF \
-DENABLE_PAM=ON \
-DUID_MIN=1000 \
-DUID_MAX=65000 \
-DLIBXKB_INCLUDE_DIR="${COOKBOOK_SYSROOT}/usr/include" \
-DLIBXKB_LIBRARIES="${COOKBOOK_SYSROOT}/usr/lib/libxkbcommon.so" \
-Wno-dev
```
Key flags:
- `-DBUILD_WITH_QT6=ON` — required; SDDM defaults to Qt5
- `-DNO_SYSTEMD=ON` — required; no systemd on Redox
- `-DENABLE_JOURNALD=OFF` — required; no journald on Redox
- `-DENABLE_PAM=ON` — required; `pam-redbear` provides `libpam.so.0`
- `-DUID_MIN=1000 -DUID_MAX=65000` — required at CMake time; SDDM hardcodes these
via `add_definitions` if not provided
- `-DQT_HOST_PATH` and `-DKF6_HOST_TOOLING` — required for `moc`/`qmltyperegistrar`/ECMs
tools that must run on the host (they cannot cross-compile for the Redox target)
### Build verification (2026-06-20)
- `cook sddm - successful` (0 errors)
- Stage output:
- `usr/bin/sddm` — main daemon
- `usr/bin/sddm-greeter-qt6` — QML greeter binary
- `usr/libexec/sddm-helper` — session spawn helper
- `usr/libexec/sddm-helper-start-wayland` — Wayland session starter (forks compositor + greeter)
- `usr/share/sddm/` — themes, scripts, translations
- `etc/pam.d/{sddm,sddm-greeter,sddm-autologin}` — PAM service files
- `patchelf --set-rpath "/usr/lib"` applied to all binaries so dynamic linking works
against the sysroot at runtime
### Runtime caveat
The QML greeter (`sddm-greeter-qt6`) is a Qt6 Wayland client and is therefore gated on
the Qt6 Wayland `null+8` crash fix (see `CONSOLE-TO-KDE-DESKTOP-PLAN.md` §3.1). The
daemon and helpers will start under init, but the greeter QML window will not appear
until the null+8 fix is runtime-validated.
---
## General Pattern: Source Tarball Extraction for Local Overlay Recipes
**Problem:** When a recipe lives under `local/recipes/` (local overlay),
the cookbook's `is_local_overlay()` check prevents wiping and re-extracting
the source from `source.tar`. If the `source/` directory only contains
Red Bear-specific files (tests, utils, etc.), the main source code is
missing.
**Affected recipes:** Any local overlay recipe that uses `tar = "..."`:
- `qtbase`, `qt5compat`, `qtdeclarative`, `qtsvg`, `qtshadertools`, `qtwayland`
- Possibly others added in the future
**Fix:** Extract the tarball manually before building:
```bash
cd <recipe-directory>
tar xf source.tar --strip-components=1 -C source/
# Apply patches manually:
cd source
for patch in ../*.patch; do
patch -p1 --batch --no-backup-if-mismatch < "$patch" || true
done
# Clean up rejects:
find . -name "*.rej" -delete
```
**Future improvement:** The cookbook could be enhanced to support
"extract-and-overlay" mode for local recipes with `tar` sources —
extracting the tarball first, then overlaying the local `source/` files.
---
## Adding a New Quirk
When you encounter a new build quirk: