Repository navigation
Every CLI invocation pays 3.5-6.5s of new startup cost (php corpus: 1.4s on 0.9.0 vs 7.9s / 4.9s warm on 0.10.5) #1670
Description
Version
0.10.5 (regression against 0.9.0)
Platform
macOS arm64; shipped release binaries of both versions
Summary
Every CLI invocation pays a fixed startup cost that 0.9.0 did not. On a small corpus (php, 2,807 files) where 0.9.0 completes in 1.4 s, 0.10.5 takes ~7.9 s — and 4.9 s even with a warm daemon, so roughly 3.5 s is not recoverable by the documented mitigation.
Measurement
Same corpus, same host, --mode full --persistence true.
| wall | |
|---|---|
| v0.9.0 | 1.4 s |
| v0.10.5, no daemon running | 8.0 s / 7.9 s / 7.9 s |
v0.10.5, after daemon start |
4.9 s / 4.9 s |
The three no-daemon runs used the same HOME and CBM_CACHE_DIR consecutively, so this is not a cold-cache artifact — the daemon does not persist between CLI invocations on its own, and each command re-pays the bootstrap. That is what the emitted hint is pointing at:
hint: this command started a temporary CBM daemon. `codebase-memory-mcp daemon start` keeps one
warm and removes this startup cost from every CLI command.
But "removes" overstates it: daemon start takes 7.9 s → 4.9 s, still 3.5 s above 0.9.0.
Why it matters
The absolute number is small, but it is paid per invocation, so it dominates exactly the workflows that call the CLI repeatedly:
- hook-driven usage (
hook_augment, PostToolUse hooks) fires per tool call - scripts and CI steps that invoke several commands in sequence
- any small-repo or incremental use, where 3.5–6.5 s of fixed cost exceeds the actual work
It also distorts benchmarking: on small corpora the fixed cost is most of the wall time (perl: 0.6 s → 6.9 s is almost entirely this, not throughput).
Reproduction
W=$(mktemp -d)
for i in 1 2 3; do
time env HOME="$W" CBM_CACHE_DIR="$W/.cache" ./codebase-memory-mcp cli index_repository \
--repo-path /path/to/small-repo --mode full --name "run$i" --persistence true
doneQuestions for triage
- How much of the 3.5 s warm floor is the version-cohort lease / rendezvous handshake, and can it be skipped when the daemon is already known-compatible?
- Should a CLI invocation start a temporary daemon at all when it is going to retire it moments later, or should the one-shot path bypass daemon coordination entirely?
- If the daemon is the intended steady state, should
daemon startbe part of install rather than a hint printed after the cost has already been paid?
Context: found while A/B-benching 0.9.0 vs 0.10.5 across 11 corpora for #1654. Separate from #1654 (Linux memory) and #1669 (cross-LSP throughput) — this one is platform-independent and affects every invocation.
Activity
vitalca commentedon Aug 19, 2026
The 0.10.x branch is totally unusable. I am on Linux, a lot of java, cpp, frontend repos. It's incredibly slooow!
I downgraded back to 0.9.0
AgathaCrystal commentedon Sep 19, 2026
Still present in 0.11.0 on macOS arm64, and it looks like the executable self-hash.
Measured on Apple Silicon, v0.11.0 installed at ~/.local/bin, binary size 301 MB:
codebase-memory-mcp --version returns in 8 ms.
Any one-shot call, e.g. codebase-memory-mcp cli list_projects, takes 3.5–5 s wall-clock with about 3.4 s of user CPU. With --progress it prints Preparing one-shot local CBM command... and then Completed list_projects (110 ms). The tool is fast; the preparation is not.
The same ~3.4 s of CPU burns with HOME pointed at an empty cache folder. It then fails at admission with active cache ; requested cache . So the cost does not depend on index size.
In stdio MCP mode the initialize reply arrives after 3.5 s. Every query after that takes 17–104 ms.
sample on the stripped binary shows a single tight CPU loop plus pread calls on the main thread.
For comparison, v0.9.0 on the same machine, with a fresh cache and one small repo indexed:
one-shot cli list_projects: 0.10 s
cli get_code_snippet: 15 ms
stdio initialize: 25 ms
This matches what the source describes. main_build_identity() calls cbm_index_supervisor_capture_build_fingerprint(), whose comment says computing the real fingerprint "hashes the ENTIRE executable image". src/main.c also notes that "the identity hash costs ~1.1 s of user CPU per invocation". On a 301 MB image that hash is the whole warm floor. The only skip, CBM_TEST_BUILD_FINGERPRINT, sits behind CBM_CLI_ENABLE_TEST_API and is not in release builds.
Possible fixes:
Cache the fingerprint under ${CBM_CACHE_DIR}, keyed by executable path, size, mtime and inode, so an unchanged binary is hashed once.
Hash a bounded prefix, a suffix and the size, instead of the full image.
Let the running daemon vouch for a client whose executable path and inode match the one it already verified.
Related: #2058 (same cost on the hook path) and PR #1767, which caches the fingerprint per process only. That does not help one-shot CLI calls, where every invocation is a new process.
Impact for us: scripts and hooks that need a single lookup pay 3.5 s each. Agent sessions are fine, because they pay it once.
This was the summary i got from fable 5.1 after i ran into the same problem. I hope it helps!
DeusData commentedon Sep 19, 2026
Thank you for the startup measurements. Current startup still computes a full executable fingerprint once per fresh process;
index_supervisor.ccaches it only within that process. A warm daemon therefore does not eliminate this first hash from the next CLI invocation. This supports a real fresh-process cost, but does not attribute every reported second to hashing. A weaker fingerprint is not an approved fix.DeusData commentedon Oct 19, 2026
Thank you for the measurements and the follow-up on 0.11.0. The distinction between fresh-process startup and work done after initialization remains useful here. I do not have a verified fix or new timing result to share in this follow-up; the previously noted fingerprint trade-off still needs a maintainer decision.
DeusData commentedon Oct 25, 2026
Thank you for the fresh-process startup measurements. The fingerprint cost and safe mitigation still need a maintainer decision; there is no new timing result to report. Sorry for the delay; this is waiting on maintainer follow-up, and I’ll follow up soon.