diff --git a/docs/ARCHITECTURE.md b/docs/ARCHITECTURE.md index a59c6c5..eb0ae6b 100644 --- a/docs/ARCHITECTURE.md +++ b/docs/ARCHITECTURE.md @@ -316,6 +316,7 @@ rewriting the document. | 5 | Rust for on-Orin services, Python for off-car tooling, Dart for the display client | Accepted | 2026-09-04 | | 21 | Two clocks per envelope; `monotonic` orders, `timestamp` references | Accepted | 2026-09-05 | | 22 | `signals.json` is the single source for signal name and unit; both are derived, never authored twice | Accepted | 2026-09-05 | +| 23 | Services build natively on the development Orin; both units stay on the same L4T release | Accepted | 2026-09-05 | | 6 | Local logging first; off-board LTE telemetry deferred | Accepted | 2026-08-14 | | 7 | Camera/AI inference is a later, separate task | Accepted | 2026-08-14 | | 8 | Self-hosted offline navigation (MapLibre GL + Valhalla + PMTiles) over a cloud maps SDK | Accepted | 2026-09-03 | diff --git a/docs/REPOS.md b/docs/REPOS.md index a5e3493..54cac0a 100644 --- a/docs/REPOS.md +++ b/docs/REPOS.md @@ -145,35 +145,46 @@ libraries. #### Building for the Orin -Services cross-compile from the workstation: +Services build **natively on the development Orin**. The sysroot is then the +target's own, so a binary cannot reference a symbol the car unit lacks — the +guarantee is structural rather than configured. -```bash -cargo build --release --target aarch64-unknown-linux-gnu -``` +Two Orin Nanos, and they have different jobs: -Each service repo's `.cargo/config.toml` points at `aarch64-linux-gnu-gcc`, from -the `gcc-aarch64-linux-gnu` package. +| Unit | Role | +|---|---| +| Development Orin | Build, CI runner, bench testing. Always powered, on the LAN | +| Car Orin | Deployment target only | -⚠ **The linker binds each symbol to the newest version present in the sysroot**, -so the cross sysroot (glibc 2.43) sets the floor, not the toolchain. Rust std -itself targets 2.17 — making the toolchain older changes nothing. +⚠ **The guarantee is version parity, not architecture.** An aarch64 binary built +on a newer userland still fails to load on an older one. A JetPack or Ubuntu +upgrade applied to one unit and not the other reintroduces the problem, silently +and only at runtime. **Upgrade both, or neither.** -Currently the highest referenced version is **2.34**, below the Orin's 2.35. Every -symbol above 2.30 comes from one event: glibc 2.34 merged `libpthread` and -`libdl` into `libc` and re-versioned the moved symbols (`__libc_start_main`, the -`pthread_*` family). Re-versioning is rare, so this ceiling is stable — exceeding -it would take a **dependency** calling a glibc function introduced after 2.35. - -That failure lands at **runtime**, on the car, as a loader error; the build -succeeds. Check before deploying: +The check that catches drift between them: ```bash objdump -T | grep -o 'GLIBC_[0-9.]*' | sort -Vu | tail -1 ``` -At or below `GLIBC_2.35` it will run. Above it, the control is the **sysroot**: -build in a container supplying an older one — `cross` does this with the host's -own toolchain — or build on the Orin. +It detects, it does not fix — its job is to fail the build rather than let a bad +binary reach the car, and to name the symbol that caused it. + +##### Cross-compiling from the workstation + +Available as a fallback. Each service repo's `.cargo/config.toml` points at +`aarch64-linux-gnu-gcc`, from the `gcc-aarch64-linux-gnu` package: + +```bash +cargo build --release --target aarch64-unknown-linux-gnu +``` + +⚠ **The linker binds each symbol to the newest version present in the sysroot**, +so the workstation's glibc 2.43 sets the floor — not the toolchain, which targets +2.17. Currently the highest referenced version is 2.34, below the Orin's 2.35, +because everything above 2.30 comes from one event: glibc 2.34 merged +`libpthread` and `libdl` into `libc` and re-versioned the moved symbols. Stable, +but not guaranteed the way a native build is. ### Writing style