Headless SDK-spawned CLI burns a constant ~33% CPU per session (futex/sched_yield spin) — still present in 2.1.220
Summary
Every Claude Code process spawned via @anthropic-ai/claude-agent-sdk query() sustains a near-constant ~33% of one core for its entire lifetime. The percentage is essentially identical across concurrent instances and does not drop between tokens — strace shows the time goes to a futex/sched_yield busy-wait, not productive syscalls. This is the same fingerprint as #17142 (closed stale, unfixed) and the same syscall family as #34518.
Environment
@anthropic-ai/claude-agent-sdk0.3.220 (bundled CLI 2.1.220, native binaryclaude-agent-sdk-linux-x64)- Headless server (no TTY): Ubuntu, kernel 6.x, 4 cores / 8 GB, Node 24
- CLI spawned per job via SDK
query()withsettingSources: [],CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC=1,DISABLE_TELEMETRY=1
Observed
Per-process CPU sampled every 15 s from /proc (top-style, % of one core) while 1→3 concurrent coding sessions run:
| concurrency | per-process CPU | total |
|---|---|---|
| 1 | ~32% | 32% |
| 3 | 33–36% each | ~100% |
The flat per-instance value regardless of concurrency indicates a fixed-duty-cycle loop rather than on-demand work. Windows (win32-x64 binary, CLI 2.1.220) shows ~26%, so this is cross-platform.
strace (10 s, active session, CLI 2.1.220)
% time seconds usecs/call calls errors syscall
------ ----------- ----------- --------- --------- ----------------
86.03 0.170188 9 18087 355 futex
8.07 0.015956 26 611 epoll_pwait2
4.54 0.008991 7 1255 sched_yield
0.68 0.001340 6 207 write
0.63 0.001241 2 438 pread64
~1,800 futex/sec + ~125 sched_yield/sec; productive write syscalls are <1% of the total. Older binary 2.1.202 shows the identical profile (16,771 futex / 88.4%), so this is not a recent regression in 2.1.220.
Expected
A session driving a single SSE stream should mostly block in epoll; thread-pool synchronization should not dominate syscall time. Ideally the wait strategy backs off (blocking futex wait) instead of yield-spinning.
Reproduction
- Spawn any session via the agent SDK on a headless Linux host.
pid=$(pgrep -x claude | head -1); strace -c -p $pidfor 10 s.- Observe futex dominating syscall time and a steady ~33% CPU for the whole session.
References
- #17142 — same 27–33% magnitude and same futex/sched_yield fingerprint (closed as stale, not fixed)
- #34518 — idle-variant with the same syscall family (statm pread64 / sched_yield / futex)
- oven-sh/bun#21081, oven-sh/bun#27490 — upstream Bun candidates for the spin behavior
This issue has 2 comments on GitHub. Read the full discussion on GitHub ↗