ci: de-nix macOS binary libiconv via install_name_tool + re-sign
macos-build-test / build (push) Successful in 2m11s
build-ci-image / build (push) Successful in 9m49s
ci / gate (push) Successful in 2m50s

libiconv is the only /nix/store dep the darwin stdenv bakes in (everything
else is system frameworks + libSystem/libobjc). The smoke-test now rewrites
that load path to /usr/lib/libiconv.2.dylib (ABI-compatible, present on
every Mac), re-signs ad-hoc (install_name_tool breaks the sig; arm64
requires a valid one), then verifies no /nix/store paths remain, the
signature is valid, and the native binary launches. Flake comment updated
to reflect the propagated-libiconv reality.
This commit is contained in:
claude@clouddev1
2026-06-14 21:43:01 +00:00
parent 4d004f5847
commit 9a126782f1
2 changed files with 30 additions and 14 deletions
+24 -9
View File
@@ -25,21 +25,36 @@ jobs:
NIX_CONFIG: "experimental-features = nix-command flakes" NIX_CONFIG: "experimental-features = nix-command flakes"
steps: steps:
- uses: actions/checkout@v4 - uses: actions/checkout@v4
- name: build both darwin targets through the flake - name: build, de-nix, sign, verify both darwin targets
run: | run: |
set -e set -e
for t in aarch64-apple-darwin x86_64-apple-darwin; do for t in aarch64-apple-darwin x86_64-apple-darwin; do
echo "==================== $t ====================" echo "==================== $t ===================="
nix develop -c cargo build --release --target "$t" nix develop -c cargo build --release --target "$t"
f="target/$t/release/rdbms-playground" f="target/$t/release/rdbms-playground"
file "$f"
echo "--- linked libs (otool -L) ---" # The darwin stdenv bakes a /nix/store libiconv load path into the
otool -L "$f" # binary. Rewrite it to the system libiconv (every Mac has it, ABI-
# Portability guard: a distributable macOS binary must link only # compatible), then re-sign ad-hoc — install_name_tool invalidates
# system libs (/usr/lib, /System/Library) — never a /nix/store path. # the signature and arm64 won't run an unsigned/broken-sig binary.
for l in $(otool -L "$f" | awk '/\/nix\/store.*libiconv.*dylib/ {print $1}'); do
echo "rewrite $l -> /usr/lib/libiconv.2.dylib"
install_name_tool -change "$l" /usr/lib/libiconv.2.dylib "$f"
done
codesign --force --sign - "$f"
echo "--- linked libs ---"; otool -L "$f"
if otool -L "$f" | grep -q /nix/store; then if otool -L "$f" | grep -q /nix/store; then
echo "ERROR: $t binary links a /nix/store dylib — not portable"; exit 1 echo "ERROR: $t still links a /nix/store dylib"; exit 1
fi fi
echo "OK: $t links only system libraries" codesign --verify --verbose=2 "$f" && echo "signature OK"
# Smoke-run the natively-runnable target (this VM is arm64).
if [ "$t" = "aarch64-apple-darwin" ]; then
echo "--- run --help ---"; "$f" --help | head -1
else
echo "(skip run: $t needs Rosetta)"
fi
echo "OK: $t portable"
done done
echo "=== both darwin targets built + portable ===" echo "=== both darwin targets built, de-nixed, signed, verified ==="
+6 -5
View File
@@ -63,11 +63,12 @@
buildInputs = buildInputs ++ pkgs.lib.optionals pkgs.stdenv.isDarwin [ buildInputs = buildInputs ++ pkgs.lib.optionals pkgs.stdenv.isDarwin [
# macOS release builds (aarch64/x86_64-apple-darwin) link AppKit # macOS release builds (aarch64/x86_64-apple-darwin) link AppKit
# (arboard) + libSystem; the Apple SDK provides those framework/ # (arboard) + libSystem; the Apple SDK provides those framework/
# system-lib stubs as *system* paths (/usr/lib, /System/Library), so # system-lib stubs as *system* paths (/usr/lib, /System/Library).
# the resulting binary is portable. NOTE: do NOT add `pkgs.libiconv` # NOTE: the darwin stdenv still propagates a *nix-store* libiconv and
# — it makes the linker prefer the nix-store libiconv.dylib, baking a # links it regardless of inputs, so the release workflow rewrites that
# /nix/store path into the binary (non-portable). The SDK's own # one load path to /usr/lib/libiconv.2.dylib (install_name_tool) and
# libiconv stub resolves `-liconv` to /usr/lib/libiconv instead. # re-signs — see release-macos / the macOS smoke-test. Adding
# `pkgs.libiconv` here would only reinforce the wrong path, so don't.
pkgs.apple-sdk pkgs.apple-sdk
]; ];
nativeBuildInputs = nativeBuildInputs ++ [ nativeBuildInputs = nativeBuildInputs ++ [