# ports/: third-party C programs One directory per program ("a port"), the way Alpine's APKBUILDs and the BSD ports trees do it: ``` ports// ├── .sha256 the pinned release tarball: "SHA256 file-name" ├── .url where to download it, one URL per line: upstream, then mirrors ├── patches/ our changes, applied in order (0001-*.patch, ...) └── build.sh unpack -> patch -> CC=toolchain/foundry-cc configure -> make -> install into out/staging ``` Every port is built as a **static-PIE** with `toolchain/foundry-cc` (see docs/porting.md). No tarball is ever committed; `cache/` is git-ignored and every download is checked against the SHA256 here. `ports/fetch.sh NAME` downloads into `cache/` (trying each URL until one gives the pinned SHA256); `make ports` fetches and builds every port listed in `FOUNDRY_PORTS` (`config.mk`) and the image gets each one as `/bin/NAME`. ## dash 0.5.12 The first port: `CC=toolchain/foundry-cc ./configure --host=x86_64-linux-musl && make`, no patches needed. About 216 KB, a static-PIE. Installed as **`/bin/dash`**, *not* `/bin/sh`: the kernel starts `/bin/sh` as its shell, and that stays `rbsh` until kernel request K5 (contract v2); then dash becomes `/bin/sh` for POSIX scripts while `rbsh` stays the login shell. `make test` runs `dash /mnt/disk0/scripts/dash-test.sh` (15 checks: arithmetic, functions, case, globbing, pipes into our Rust tools, redirections, here-documents, background jobs + `wait`, `trap`, ...). Download note: upstream (gondor.apana.org.au) answered HTTP 500 on 2026-10-31; Debian's `dash_0.5.12.orig.tar.gz` is byte-identical (same SHA256) and is the second URL. ## sbase 0.1 (M4) [sbase](https://core.suckless.org/sbase/) is suckless's set of small Unix tools: one short C file per tool (`sort.c`, `sed.c`, ...), 97 tools in release 0.1 (2025-03-14). It has no configure step, so the build is just `make CC=toolchain/foundry-cc` (ports/sbase/build.sh); every tool is its own static-PIE, 5.7 MB together. - **Where it goes**: **`/usr/lib/sbase/`** on the ext2 root (contract v2 only), *off* the default `PATH`. The Foundry OS Rust tools (`/bin/ls`, `/bin/cat`, ...) stay the default. Run an sbase tool by its full path: ```sh /usr/lib/sbase/sort -n numbers.txt /usr/lib/sbase/ls -l /etc ``` or put it in front of `PATH` for one shell: `PATH=/usr/lib/sbase:$PATH`. - **Patch 0001**: the 0.1 tarball forgot `scripts/getconf.sh` (its Makefile needs it to build `getconf`); the patch adds it unchanged from the upstream git tag `0.1`. - **Tested by** `dash /scripts/sbase-test.sh` in the v2 self-test (see docs/syscall-gaps.md for what fails and why). - **Not in sbase**: `df`, `id`, `mount`, `ps` and other Linux-specific tools live in its sister project *ubase*; busybox (M5) will cover them. - The tools are small and POSIX-minded, so some GNU options are missing: no `sed -i`, no `head -c`, `od -c` is spelled `od -t c`, and `sleep` takes whole seconds only. Later: **busybox** (M5). Its applets go to `/usr/lib/busybox`, also off the default `PATH`.