Landing blocker for #61 and #63: the deployment checkout is 12 commits behind and `merge --ff-only` refuses while tracked paths are dirty. Discard is not available here (workspace policy: no `checkout`/`stash` on shared state), so the dirt is committed. - `agent/APPEND_SYSTEM.md`: the point-of-use / one-work-log / PR-link doctrine, already byte-identical to `origin/main` (`cmp` against the trunk blob: no difference). No new prose — the commit exists so the trunk merge can proceed. - `agent/config.yml` and `agent/managed-skills/**`: the machine-live tier the heartbeat owns (AGENTS.md § Live-sync tiers). `ALLOW_SECRETS=1` was used, deliberately and after auditing the staged diff by hand: the only credential-shaped strings in it are two copies of `AKIA0000000000000EXAMPLE` — the inert all-zero AWS example id — and they appear inside the two skill pages that teach that exact placeholder shape. This checkout is still running the pre-#61 hook; the merged gate (value-scoped placeholder filter, `71601f7`) exempts this value, so the refusal dies with this landing. No `--no-verify` was used: the gate ran and its verdict is recorded here. Refs #61
4.1 KiB
name, description
| name | description |
|---|---|
| rescue-loose-home-scripts | Promote a durable loose $HOME script into dank/command-center: archive-first, black-box bats red-first with env seams, docs page + index + log entry, one atomic commit per instrument, PR to main. |
Rescue a throwaway-looking $HOME script into the command-center repo as a maintained instrument. Used for remote-job.sh + scripts/probes/*.hip (PR #54, Refs #53); the archive still holds ~120 candidates.
1. Archive first, never delete
Loose scripts at $HOME root move to ~/.AGENTTRASH/home-scripts-<date>/ (rm is forbidden; deletion is a pruning session with Frank). Consolidate bulk media separately (~/audiosamples). Then check the archive for instruments, not convenience: something that answers a question you will ask again, or that carries a trap you paid for.
2. Tests first, and black-box
Write tests/<name>.bats before the script; confirm red (bats tests/<name>.bats → all not ok because the script is absent).
- Assert output, exit codes, and on-disk ordering only — never internals, never "variable X equals Y".
- A test that asserts a race outcome (file exists immediately after a detached
start) is wrong: assert the contract instead (statusreports RUN/PENDING and exits 1). Rewrite the test, not the code, when the failure is your own assumption. - Design env seams so the untestable path becomes testable off the target hardware:
*_SYSFS,*_KFD,*_HIPCC,*_SRC,*_BUILD. A refusal that can only be exercised on a card box is an untested refusal. Stub the toolchain in$PATH/via env to drive build-failure and busy-device paths.
3. Safety law in the tool, not the docs
Anything that measures a GPU must refuse before it builds or runs when the device is busy (gpu_busy_percent over threshold, or any process holding /dev/kfd) and must stop nothing: unloading a production endpoint is a human decision (--force). Pin the refusal-before-build ordering in a test — otherwise a reordered guard silently reintroduces contention beside a live service.
Exit-code taxonomy worth reusing: 0 did the work · 2 usage/missing inputs · 3 refused (would have contended) · 4 toolchain/build failure. A client box without the SDK must exit 4 loudly, never report an empty success.
4. An instrument that crashes is not an instrument
hipGetDeviceProperties segfaults on the fleet's ROCm build while hipGetDeviceCount works fine. The shipped probes called it only to print device name + PCI bus id — replaced by the sysfs topology block the driver prints (current_link_width/current_link_speed vs max_*). Record the trap as a comment in the sources so it is not reintroduced.
5. Docs, three places, in the same commit as the code
omp-docs/tools/<name>.md— frontmatter per OKF (type: reference, title, description, tags,verified,timestamp); sections: contract (command table + exit status), the law + why, how to read the output, failure-modes table, test seams. Point-of-use only: measured numbers do not live here (they belong with the endpoint's runbook vault).omp-docs/tools/index.md— one alphabetical bullet per page.omp-docs/log.md— dated entry above the newest one: what changed + the durable laws, a few lines.
Gates before commit: bash scripts/kb-lint.sh (0 violations) and full bats tests/ green.
6. Land it
One commit per instrument (stage that page's index line only — re-add the next page's line for its own commit), message = imperative what + why + Refs #N, hooks armed (never --no-verify). Push to the local Gitea, open the PR with gitea-pr-api-cycle (token from ~/.config/secrets/gitea via curl -K; body ends with --- then cwd: <session cwd> · session: <live transcript UUID>), then xdg-open <PR-URL>. Never merge without Frank's explicit OK.
7. Report the gap you could not close
Verification on a client box proves the guard/refusal/usage paths only. If compile-or-run needs the hardware box, say so in the PR under "Not done here" and offer the exact low-risk command rather than implying the artifact is proven.