qmd/test
Tobi Lutke c162ed1319
fix: disable libggml-metal residency sets on darwin
The libggml-metal static device destructor asserts on a non-empty
residency set during libc `exit()` → `__cxa_finalize_ranges`
(ggml-org/llama.cpp#17869). The residency set's 180 s keep_alive timer
hasn't expired by exit, so `GGML_ASSERT([rsets->data count] == 0)`
fails and `ggml_abort` dumps a multi-kB backtrace to stderr after the
user-visible output. Every llama-using CLI command (`query`,
`vsearch`, `embed`) was affected, plus the `bun test` runner.

No JS-side dispose path can prevent it: the static destructor runs
after every JS-reachable cleanup, and Node's `reallyExit` calls libc
`exit()` not `_exit()` (verified in node/src/api/environment.cc),
so it does NOT skip C++ static destructors as we'd assumed.

The actual fix is to disable residency sets via
`GGML_METAL_NO_RESIDENCY=1` before the native binding loads. For
QMD's short-lived CLI workflow there's no measurable cost
(benchmarked: identical wall time with and without on M3 Pro).

Three propagation points are needed:
- `bin/qmd` exports the env var before spawning node/bun. This
  covers all production CLI invocations.
- `src/test-preload.ts` mirrors the launcher for `bun test` runs.
  Bun does NOT sync `process.env` mutations to libc `setenv()`
  (verified empirically — Node does, via uv_os_setenv), so on Bun we
  reach for `bun:ffi` to call `setenv()` directly. vitest forks
  per-test-file so its parent never loads the binding.
- `qmd doctor` reports the mitigation state via the new
  `isDarwinMetalMitigationActive()` predicate so users can verify it
  in their environment.

Opt back in with `QMD_METAL_KEEP_RESIDENCY=1` (long-lived qmd
processes, MCP daemon hot reload, upstream fix triage). The old
`QMD_DISABLE_DARWIN_QUERY_JSON_SAFE_EXIT` is removed — its per-command
bypass mechanism didn't actually work on Node (it called
`process.reallyExit` which goes through libc exit) and is fully
replaced by the launcher env var.

Removed the old broken `installDarwinExitGuard()` mechanism from
LlamaCpp; kept the function name as a no-op shim for back-compat.
2026-05-28 13:40:14 -07:00
..
eval-docs Add 6 synthetic evaluation documents 2025-12-21 13:10:35 -04:00
ast-chunking.test.ts chore: migrate AST chunking tests to vitest 2026-04-05 17:19:59 -04:00
ast.test.ts Fix AST grammar packaging for Bun installs 2026-05-09 18:13:58 +00:00
bench-score.test.ts feat: support project-local indexes in bench 2026-05-16 18:22:04 +00:00
bin-wrapper.test.ts fix(launcher): prefer Node+tsx over Bun in source mode when both lockfiles exist 2026-05-28 11:57:30 -07:00
cli-exit-lifecycle.test.ts fix: disable libggml-metal residency sets on darwin 2026-05-28 13:40:14 -07:00
cli-lazy-llm-import.test.ts fix(cli): keep status from importing llama 2026-05-09 18:12:45 +00:00
cli.test.ts fix: disable libggml-metal residency sets on darwin 2026-05-28 13:40:14 -07:00
collections-config.test.ts feat: add local init and doctor diagnostics 2026-05-19 14:27:33 -04:00
Containerfile Expand install smoke harness 2026-05-19 23:05:49 +00:00
esm-ambiguous-module.test.ts chore: strengthen package test task 2026-05-19 14:27:38 -04:00
eval-bm25.test.ts test: move all tests to flat test/ directory 2026-02-15 21:37:47 -04:00
eval-deep-research.jsonl Merge origin/main into feat/ast-aware-chunking 2026-03-28 20:00:49 -04:00
eval-deep-research.ts Merge origin/main into feat/ast-aware-chunking 2026-03-28 20:00:49 -04:00
eval-harness.ts refactor: move CLI and MCP to subdirectories, MCP consumes SDK 2026-03-10 11:39:55 -04:00
eval.test.ts test: move all tests to flat test/ directory 2026-02-15 21:37:47 -04:00
formatter.test.ts Add line to JSON search output 2026-04-05 10:08:57 +00:00
intent.test.ts refactor: move CLI and MCP to subdirectories, MCP consumes SDK 2026-03-10 11:39:55 -04:00
launcher-detection.test.sh fix: prioritize package-lock.json in launcher to prevent Bun false positive 2026-03-12 01:46:38 -07:00
llm.test.ts Improve qmd diagnostics and embed resilience 2026-05-19 21:39:48 +00:00
local-config.test.ts Fix QMD CI test runtime assumptions 2026-05-16 23:52:53 +00:00
mcp.test.ts feat: add qmd doctor vector diagnostics 2026-05-18 01:52:05 +00:00
multi-collection-filter.test.ts refactor: replace bash wrapper with standard #!/usr/bin/env node shebang 2026-02-22 11:09:36 -04:00
package.test.ts docs(qmd-skill): structured-query-first; cite docid + lines; no sed 2026-05-28 10:56:13 -07:00
rrf-trace.test.ts feat(query): add --explain score traces for hybrid search 2026-03-07 14:35:10 -04:00
sdk.test.ts fix: forward candidateLimit through search APIs 2026-05-11 20:25:34 -10:00
smoke-install.sh Expand install smoke harness 2026-05-19 23:05:49 +00:00
store-paths.test.ts test: move all tests to flat test/ directory 2026-02-15 21:37:47 -04:00
store.helpers.unit.test.ts fix: preserve original case in handelize() 2026-04-09 07:59:22 +09:00
store.test.ts feat(search,query): --full-path swaps qmd:// for on-disk paths 2026-05-28 11:18:03 -07:00
structured-search.test.ts Merge pull request #384 from rymalia/fix/semantic-query-hyphen-validation 2026-05-02 20:16:30 -04:00