Link the inference engine for macOS in a zig container
`docker/macos` builds for aarch64-apple-darwin from Linux with cargo-zigbuild. Zig carries libSystem and the C headers, so tract's SIMD kernels compile and the engine's test binaries and examples link as Mach-O arm64 — the check `cargo check --target` could not do, because tract's build script needs a macOS C compiler. Crates that link an Apple framework (dr-plat's keyring, and so the app) still need the Xcode SDK and fail at the link; macos.md says so.
This commit is contained in:
@@ -0,0 +1,48 @@
|
|||||||
|
# DarkRoom — macOS link check
|
||||||
|
#
|
||||||
|
# Compiles and links for macOS from Linux, with zig as the linker
|
||||||
|
# (cargo-zigbuild). Zig carries macOS's libSystem stubs and C headers, so the
|
||||||
|
# crates that need only libSystem — the inference engine, dr-plat — build,
|
||||||
|
# link and produce Mach-O test binaries here. Nothing runs: there is no macOS
|
||||||
|
# to run them on (docs/dev/macos.md §2). The desktop app needs Apple's
|
||||||
|
# framework headers (AppKit, Metal, Security), which only the Xcode SDK
|
||||||
|
# carries, so it does not link here.
|
||||||
|
#
|
||||||
|
# Build: docker build -t darkroom-macos:latest docker/macos
|
||||||
|
# Use: ./docker/macos/build.sh cargo zigbuild --target aarch64-apple-darwin -p dr-inference-engine --all-targets
|
||||||
|
|
||||||
|
FROM docker.io/library/debian:trixie-slim
|
||||||
|
|
||||||
|
# Pinned, like the Windows and Android images. Rust matches rust-toolchain.toml.
|
||||||
|
ARG RUST_VERSION=1.92.0
|
||||||
|
ARG ZIG_VERSION=0.15.2
|
||||||
|
ARG ZIG_SHA256=02aa270f183da276e5b5920b1dac44a63f1a49e55050ebde3aecc9eb82f93239
|
||||||
|
ARG CARGO_ZIGBUILD_VERSION=0.23.4
|
||||||
|
|
||||||
|
ENV DEBIAN_FRONTEND=noninteractive \
|
||||||
|
CARGO_HOME=/opt/cargo \
|
||||||
|
RUSTUP_HOME=/opt/rustup \
|
||||||
|
PATH=/opt/zig:/opt/cargo/bin:$PATH
|
||||||
|
|
||||||
|
RUN apt-get update && apt-get install -y --no-install-recommends \
|
||||||
|
ca-certificates curl git xz-utils \
|
||||||
|
# A host C compiler: build scripts and proc-macros are Linux binaries.
|
||||||
|
gcc libc6-dev \
|
||||||
|
# `file` says Mach-O; the smoke check in build.sh reads it.
|
||||||
|
file \
|
||||||
|
&& rm -rf /var/lib/apt/lists/*
|
||||||
|
|
||||||
|
RUN curl -fsSL "https://ziglang.org/download/${ZIG_VERSION}/zig-x86_64-linux-${ZIG_VERSION}.tar.xz" -o /tmp/zig.tar.xz \
|
||||||
|
&& echo "${ZIG_SHA256} /tmp/zig.tar.xz" | sha256sum -c - \
|
||||||
|
&& mkdir /opt/zig && tar xJf /tmp/zig.tar.xz -C /opt/zig --strip-components=1 \
|
||||||
|
&& rm /tmp/zig.tar.xz && zig version
|
||||||
|
|
||||||
|
# The components rust-toolchain.toml lists, baked in so rustup does not fetch
|
||||||
|
# them inside every run.
|
||||||
|
RUN curl -fsSL https://sh.rustup.rs | sh -s -- -y --profile minimal \
|
||||||
|
--default-toolchain "${RUST_VERSION}" \
|
||||||
|
--component rustfmt,clippy,rust-analyzer \
|
||||||
|
--target aarch64-apple-darwin,x86_64-apple-darwin \
|
||||||
|
&& cargo install --locked "cargo-zigbuild@${CARGO_ZIGBUILD_VERSION}" \
|
||||||
|
&& rm -rf /opt/cargo/registry \
|
||||||
|
&& chmod -R a+rwX /opt/cargo /opt/rustup
|
||||||
Executable
+62
@@ -0,0 +1,62 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
# Run a command inside the DarkRoom macOS link-check container.
|
||||||
|
#
|
||||||
|
# ./docker/macos/build.sh cargo zigbuild --target aarch64-apple-darwin -p dr-inference-engine --all-targets
|
||||||
|
# ./docker/macos/build.sh # interactive shell
|
||||||
|
#
|
||||||
|
# Builds the image on first use; `--rebuild` after editing the Dockerfile.
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
IMAGE="darkroom-macos:latest"
|
||||||
|
HERE="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||||
|
REPO="$(cd "${HERE}/../.." && pwd)"
|
||||||
|
|
||||||
|
if command -v podman >/dev/null 2>&1; then
|
||||||
|
ENGINE=podman
|
||||||
|
elif command -v docker >/dev/null 2>&1; then
|
||||||
|
ENGINE=docker
|
||||||
|
else
|
||||||
|
echo "error: neither podman nor docker found" >&2
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ "${1:-}" == "--rebuild" ]]; then
|
||||||
|
shift
|
||||||
|
"${ENGINE}" build -t "${IMAGE}" "${HERE}"
|
||||||
|
elif ! "${ENGINE}" image inspect "${IMAGE}" >/dev/null 2>&1; then
|
||||||
|
echo "==> building ${IMAGE} (first run; a few minutes)"
|
||||||
|
"${ENGINE}" build -t "${IMAGE}" "${HERE}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Registry, target and zig's own cache persist across runs.
|
||||||
|
CACHE="${XDG_CACHE_HOME:-${HOME}/.cache}/darkroom-macos"
|
||||||
|
mkdir -p "${CACHE}/registry" "${CACHE}/target" "${CACHE}/home"
|
||||||
|
|
||||||
|
ARGS=(
|
||||||
|
--rm
|
||||||
|
-v "${REPO}:/work:z"
|
||||||
|
-v "${CACHE}/registry:/opt/cargo/registry:z"
|
||||||
|
-v "${CACHE}/target:/work/target-macos:z"
|
||||||
|
-v "${CACHE}/home:/tmp/home:z"
|
||||||
|
-e HOME=/tmp/home
|
||||||
|
-e CARGO_TARGET_DIR=/work/target-macos
|
||||||
|
-w /work
|
||||||
|
)
|
||||||
|
|
||||||
|
# Capped for the same reason as the Windows image: a cross build otherwise
|
||||||
|
# takes every thread on the host.
|
||||||
|
JOBS="${DARKROOM_BUILD_JOBS:-8}"
|
||||||
|
if [[ "${JOBS}" != "0" ]]; then
|
||||||
|
ARGS+=(--cpus "${JOBS}" -e "CARGO_BUILD_JOBS=${JOBS}")
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ "${ENGINE}" == "docker" ]]; then
|
||||||
|
ARGS+=(--user "$(id -u):$(id -g)")
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [[ $# -eq 0 ]]; then
|
||||||
|
ARGS+=(-it)
|
||||||
|
set -- /bin/bash
|
||||||
|
fi
|
||||||
|
|
||||||
|
exec "${ENGINE}" run "${ARGS[@]}" "${IMAGE}" "$@"
|
||||||
+12
-4
@@ -21,12 +21,20 @@ bundle, and signing. `dr-plat` sends every non-Android Unix to the X11/Wayland d
|
|||||||
|
|
||||||
## 2. Building
|
## 2. Building
|
||||||
|
|
||||||
The Rust side compile-checks from Linux:
|
`docker/macos` compiles and links for macOS from Linux, using zig as the linker
|
||||||
|
(`cargo-zigbuild`). Zig carries libSystem's stubs and the C headers, so tract's SIMD kernels
|
||||||
|
compile and anything that needs only libSystem links:
|
||||||
|
|
||||||
rustup target add aarch64-apple-darwin
|
./docker/macos/build.sh cargo zigbuild --target aarch64-apple-darwin -p dr-inference-engine --features native --all-targets
|
||||||
cargo check --target aarch64-apple-darwin -p dr-inference-engine --features native
|
./docker/macos/build.sh cargo-zigbuild clippy --target aarch64-apple-darwin -p dr-inference-engine --features native --all-targets -- -D warnings
|
||||||
|
|
||||||
Linking needs Apple's SDK, which means a Mac. On one:
|
That produces Mach-O arm64 test binaries and the `ladder` and `ep_probe` examples. Nothing runs
|
||||||
|
them. Anything that links an Apple framework needs the Xcode SDK, which zig does not carry. That
|
||||||
|
includes `dr-plat` (through the keyring's Security and CoreFoundation) and so the desktop app, and
|
||||||
|
its link fails with `unable to find framework`. `cargo check` for those still works in the
|
||||||
|
container.
|
||||||
|
|
||||||
|
Linking the app needs Apple's SDK, which means a Mac. On one:
|
||||||
|
|
||||||
cargo build --profile diagnostic -p darkroom-desktop
|
cargo build --profile diagnostic -p darkroom-desktop
|
||||||
./tools/fetch-desktop-runtime.sh # ONNX Runtime 1.29.0 with CoreML, Apple silicon only
|
./tools/fetch-desktop-runtime.sh # ONNX Runtime 1.29.0 with CoreML, Apple silicon only
|
||||||
|
|||||||
Reference in New Issue
Block a user