#!/bin/bash
# desktop-strata-build.sh -- runs ON THE DESKTOP, as an operator, inside the user unit stage-strata.sh starts (Nice 19, CPUQuota 800 %,
# MemoryMax 10G, idle I/O: the EPYC carries the live seats). It builds the Strata engine at v0.1.39 from the copied
# clone, from source only (never setup.py, an installer, a release zip or a prebuilt binary; STRATA-DELTA-2 C-1, C-9),
# with build-strata.sh's flags (the laptop's, stage-new-receipts/scripts/build-strata-6f32ec07.sh) and the desktop's paths,
# plus the RPATH fix window 0's stage needed (desktop-window-0/STAGE.md section 4: CMake treats the staged toolkit's lib
# folder as implicit and leaves it out of RUNPATH, so the binaries resolved CUDA to the desktop's system 13.1; here
# -DCMAKE_BUILD_RPATH names the staged 13.4 lib folder from the first configure). Everything runs inside bwrap with NO
# network and a read-only root: only the build folder and a fresh HOME and TMPDIR under the stage folder are
# writable, so a fetch or a write anywhere else fails loudly instead of happening. A clean environment (env -i).
#
#   B=<the desktop's ~/bench-flashnext> bash desktop-strata-build.sh
#
# It writes only: $B/build/strata-6f32ec07/ (refused if it exists: launch once), $B/strata-stage/{configure.log,
# build.log, build.rc, build-home/, build-tmp/}. Its last line is the receipt: BUILD DONE strata <sha256> | BUILD STOP
# <why> (nothing built) | BUILD FAILED <step> rc <n>. The dry run (stage/tests/dryrun_stage.py) sets STAGE_STUB_DIR, a
# folder whose cmake must be the one found first (a stub); nothing else in this file reads it.
set -uo pipefail
B=${B:?B must name ~/bench-flashnext}
FULL=6f32ec070f23ced9f50e704d854d775da52591ab
GG_FULL=3cf03257f219afbe7334045ff7c6a06ac68c627d
SRC=$B/strata-6f32ec07
OUT=$B/build/strata-6f32ec07
GG=$B/llama.cpp-3cf03257
CUDA=$B/cuda-13.4
LIB=$CUDA/targets/x86_64-linux/lib
ST=$B/strata-stage
RC=$ST/build.rc
export GIT_CONFIG_NOSYSTEM=1 GIT_CONFIG_GLOBAL=/dev/null
PATH_IN=/usr/bin:/bin
if [ -n "${STAGE_STUB_DIR:-}" ]; then
  PATH_IN=$STAGE_STUB_DIR:$PATH_IN
  case "$(PATH=$PATH_IN command -v cmake)" in "$STAGE_STUB_DIR"/*) ;; *) echo "BUILD STOP STAGE_STUB_DIR is set but cmake is not its stub"; echo 9 > "$RC"; exit 9 ;; esac
fi
stop() { echo "BUILD STOP $*"; echo 3 > "$RC"; exit 3; }
fail() { echo "BUILD FAILED $1 rc $2"; echo "$2" > "$RC"; exit 4; }
mkdir -p "$ST"
rm -f "$RC"
echo "$(date -u +%FT%TZ) desktop-strata-build start (B=$B)"
# the pins, read before anything is written
got=$(git -C "$SRC" --no-optional-locks rev-parse HEAD 2>/dev/null)
tag=$(git -C "$SRC" --no-optional-locks rev-parse 'v0.1.39^{commit}' 2>/dev/null)
[ "$got" = "$FULL" ] || stop "$SRC is at '$got', not $FULL"
[ "$tag" = "$FULL" ] || stop "v0.1.39^{commit} in $SRC reads '$tag', not $FULL"
porc=$(git -C "$SRC" --no-optional-locks status --porcelain --ignored 2>&1) || stop "git status failed in $SRC"
[ -z "$porc" ] || stop "$SRC is not clean: $(printf '%s' "$porc" | head -3 | tr '\n' ' ')"
[ ! -e "$SRC/.gitmodules" ] || stop "$SRC carries a .gitmodules (the pinned commit has none)"
gg=$(git -C "$GG" --no-optional-locks rev-parse HEAD 2>/dev/null)
[ "$gg" = "$GG_FULL" ] || stop "$GG is at '$gg', not llama.cpp $GG_FULL (STRATA_GGML_DIR; window 0's clone)"
[ -x "$CUDA/bin/nvcc" ] || stop "$CUDA/bin/nvcc is absent (window 0's staged CUDA 13.4)"
nv=$("$CUDA/bin/nvcc" --version 2>&1 | grep -o 'V13\.4\.[0-9]*' | head -1)
[ -n "$nv" ] || stop "$CUDA/bin/nvcc does not report CUDA 13.4 ($("$CUDA/bin/nvcc" --version 2>&1 | tail -1))"
for l in libcudart.so.13 libcublas.so.13 libcublasLt.so.13; do [ -e "$LIB/$l" ] || stop "$LIB/$l is absent"; done
[ ! -e "$OUT" ] || stop "$OUT exists (launch once: the build runs once; read it, or remove it by its exact path first)"
# the sandbox probe: no network inside bwrap under the desktop's userns restriction, or no build (no network-on build without
# the lead's ruling; PLAN-W1 section 3.2)
/usr/bin/bwrap --ro-bind / / --dev /dev --proc /proc --unshare-net true 2>/dev/null || stop "bwrap --unshare-net does not run here (the userns restriction): no network-on build without the lead's ruling"
mkdir -p "$OUT" "$ST/build-home" "$ST/build-tmp"
SANDBOX=(/usr/bin/bwrap --unshare-net --die-with-parent --ro-bind / / --dev /dev --proc /proc --tmpfs /run
         --bind "$OUT" "$OUT" --bind "$ST/build-home" "$ST/build-home" --bind "$ST/build-tmp" "$ST/build-tmp" --
         /usr/bin/env -i PATH="$CUDA/bin:$PATH_IN" HOME="$ST/build-home" TMPDIR="$ST/build-tmp" LANG=C.UTF-8)
echo "$(date -u +%FT%TZ) configure (CUDA $nv; ggml from $GG at $gg; RPATH $LIB)"
"${SANDBOX[@]}" cmake -G Ninja -S "$SRC" -B "$OUT" -DCMAKE_BUILD_TYPE=Release -DSTRATA_ENABLE_CUDA=ON -DSTRATA_BUILD_TESTS=OFF \
  -DCMAKE_CUDA_ARCHITECTURES=120 -DCMAKE_CUDA_COMPILER="$CUDA/bin/nvcc" -DSTRATA_GGML_DIR="$GG" \
  -DCMAKE_BUILD_RPATH="$LIB" > "$ST/configure.log" 2>&1 || fail configure $?
echo "$(date -u +%FT%TZ) build (target strata, -j 8)"
"${SANDBOX[@]}" cmake --build "$OUT" --target strata -j 8 > "$ST/build.log" 2>&1 || fail build $?
[ -f "$OUT/strata" ] || fail "no-binary" 5
sha=$(sha256sum "$OUT/strata" | cut -c1-64)
echo 0 > "$RC"
echo "$(date -u +%FT%TZ) BUILD DONE strata $sha"
echo "BUILD DONE strata $sha"
