Files
wireguard-admin/docs/ENVIRONMENT.md
T

7.0 KiB

Rust Development Environment

Pinned baseline

rust-toolchain.toml pins Rust 1.97.1, the minimal profile, and rustfmt/clippy. The native development host is x86_64-unknown-linux-gnu; the additional x86_64-unknown-linux-musl target is for executables running in Alpine integration containers. The host target is implicitly included by rustup. Do not force all Cargo builds to musl.

Use Rust edition 2024 when creating Cargo.toml. Set its rust-version to 1.97.1 as the initial supported compiler floor; this is distinct from the exact toolchain pin. Do not claim compatibility with older compilers without testing it. Keep Cargo.lock tracked once the package exists.

Toolchain selection

With rustup-managed Cargo/rustc proxies, entering the repository selects the toolchain file and may download missing components. Check rustup show and rustup target list --installed; explicit overrides may take precedence. Do not automatically install a global toolchain or modify the user's PATH.

This host currently uses system-packaged tools under /usr/bin, without rustup. Such binaries do not enforce rust-toolchain.toml. Before execution, verify the installed compiler and Cargo match the pin, and that formatter and Clippy are available. If versions differ, stop the affected build and report the mismatch rather than silently updating the pin.

Checks available before Cargo scaffolding:

rustc -Vv
cargo -V
rustfmt --version
cargo clippy --version

After scaffolding, use the completion commands in AGENTS.md. The first dependency resolution generates Cargo.lock; subsequent checks use --locked. Registry access or a populated cache is required for dependencies.

Alpine target

The toolchain file requests the musl Rust standard library; it does not supply all native compilers/linkers needed by a cross build. Establish the musl linker and any C dependency requirements before milestone 8, or build in a dedicated Alpine/musl builder. Keep build tools out of the small runtime test image.

The Alpine suite has two separate execution environments:

  • The host runs the Rust Testcontainers harness and must have the pinned Rust toolchain, approved development dependencies, and access to an explicitly selected disposable Docker-compatible Linux daemon. Testcontainers manages only scenario-owned networks/containers. Do not silently use a remote daemon or the default local daemon before it has been selected as disposable.
  • The daemon's Linux host must already provide kernel WireGuard support and IPv4 networking. Server and client containers share that kernel but receive only scoped NET_ADMIN in their own network namespaces. The suite verifies support in disposable probe containers on a private internal IPv4 network. It must not load modules, alter host sysctls, or create host interfaces. Missing kernel, daemon, IPv4, or namespace prerequisites are an incomplete explicit run, not a passing skip. IPv6 capability and traffic are intentionally not tested by M8; production dual-stack behavior remains unchanged.

The fixture image is pinned to an Alpine release or digest and records the resolved image identity and complete installed package closure. It contains runtime utilities only (wireguard-tools, iproute2, BusyBox tools actually used, and any justified additions). Driver and fixture inputs are staged per fresh scenario container; keys and configs must never enter the image build context or layers. The test-only server driver must be built for x86_64-unknown-linux-musl or inside a pinned Alpine/musl builder matching the repository toolchain, then checked for actual dynamic requirements and executed in the fixture image. A successful cross build alone does not establish Alpine compatibility.

The current host observation above records that the musl standard library is missing. Do not install it or a linker implicitly. The fixture recipe now lives in tests/containers/alpine/ and the exact image commands are in TESTING.md. The base is pinned to Alpine 3.22.7 for linux/amd64; the selected disposable daemon built and cached the image, and the exact installed closure is recorded in packages.lock. Compiler/toolchain layers stay out of this runtime image.

M8.4 provides an in-crate #[cfg(test)] library test driver so that its fixture command and restart seams stay inaccessible to the production executable. It includes an ignored test named container_driver::alpine_readiness, selected with libtest's --ignored --exact arguments. This harmless test checks only its Linux x86_64 execution environment. Once the musl standard library and a compatible linker are available, build the library test harness from the repository root with:

cargo test --locked --lib --no-run --target x86_64-unknown-linux-musl

The host cannot run this build directly because its musl target is absent. The digest-pinned official Rust 1.97.1 Alpine builder command in TESTING.md built the library test harness on 2026-10-23. file identified a static PIE and readelf -l showed no interpreter; the ignored readiness selector passed 1/1 in the pinned Alpine runtime using a read-only bind of the nonsecret binary. The selected-daemon M8.4 Testcontainers smoke copied the current binary into a fresh server container and passed the test-only Create/Commit/first delivery/fixture Apply sequence with real runtime observation. M8.5 and M8.7 subsequently completed and M8 was accepted for the documented IPv4 scope. The current integrated host gates and three fresh selected-daemon lifecycle runs are recorded in evidence/milestone-8.md. The runs covered IPv4 traffic, deletion, restore, import/reissue and mandatory-backup failure. The fixture Apply callback is not a systemd job. IPv6 capability/traffic and real systemd/D-Bus remain unverified. The readiness wrapper invokes the harness as PATH --ignored --exact container_driver::alpine_readiness --test-threads=1. Cargo printed the executable under /tmp/wga-m8-build-target/x86_64-unknown-linux-musl/debug/deps/wireguard_admin-<hash> for the builder command. Discover the current hash from each build; rebuild the driver after relevant code changes. A target name or successful compilation alone is not Alpine runtime evidence. Musl readiness is an M8 fixture build prerequisite; it is not a milestone 1 acceptance gate.

Observed preparation state

During preparation, local commands reported:

  • rustc: 1.97.1, host x86_64-unknown-linux-gnu.
  • Cargo: 1.97.1.
  • rustfmt: 1.9.0-stable.
  • Clippy: 0.1.97.
  • rustup and musl-gcc: not found in PATH.
  • The musl standard library directory reported by rustc does not exist.

No toolchain, component, target, or native package installation was performed. These observations establish tool availability, not a successful project build. Recheck the environment at execution time.

Reference: rustup toolchain files and overrides.