[Bug] v2.1.109 / Opus 4.7 — silent stuck-turn during tool execution (two distinct failure modes)

Resolved 💬 9 comments Opened Apr 19, 2026 by Axiom89 Closed Apr 19, 2026

[Bug] Claude Code v2.1.109 / Opus 4.7 — silent stuck-turn during tool execution (two distinct failure modes)

Summary

Running a long-lived interactive session via claude --channels plugin:telegram@claude-plugins-official under systemd, we hit the model in a permanently stuck state — stop_reason: tool_use but no follow-on activity. The session stops processing, no error is emitted, the process stays alive. Two distinct stuck flavors observed in a single day, both on the same agent doing the same task class.

Environment

  • Claude Code CLI: v2.1.109
  • Model: claude-opus-4-7 (1M context)
  • Host: Ubuntu 24.04 on AWS EC2 t3.micro (1.9 GB RAM)
  • Launched via: script -qec "claude --channels plugin:telegram@claude-plugins-official --dangerously-skip-permissions --disallowedTools mcp__telegram-mcp__tg_send" /dev/null under systemd Restart=always
  • Working directory: a git repo with CLAUDE.md, .mcp.json, a local .claude/skills/ tree
  • Effort level: CLAUDE_CODE_EFFORT_LEVEL=max
  • Auto-memory disabled: CLAUDE_CODE_DISABLE_AUTO_MEMORY=1
  • Auto-updater disabled: DISABLE_AUTOUPDATER=1

Failure mode A — Edit tool_use with no tool_result

When: 2026-04-19 11:13:43 UTC
Session: 1a642596-ee80-4d9e-bf8a-eee474d4e82a
Last JSONL assistant entry:

{
  "type": "tool_use",
  "id": "toolu_01NeNUJdzhBeeckre3Zxm5TD",
  "name": "Edit",
  "input": {
    "file_path": ".../skills/holder-scanner/scripts/scan_holders.sh",
    "old_string": "<263 chars, ASCII-only, a bash variable block>",
    "new_string": "<626 chars, ASCII-only, adds a sourced helper block>",
    "replace_all": false
  }
}

stop_reason: tool_use. No matching tool_result ever written to JSONL. File on disk untouched. Subsequent queue-operation enqueue entries from the TG plugin piled up but the session could not dispatch them (turn still open).

Preceding context: 14 tool calls (Bash, Grep, Read, Write chains) in the 90 seconds before the stuck Edit. No errors in any of those results.

Failure mode B — assistant never emits next message after a successful tool_result

When: 2026-04-19 09:36:29 UTC
Session: fc891dc4-a248-4d22-949e-3b061660c307
Last JSONL assistant entry:

{
  "type": "tool_use",
  "name": "Read",
  "input": {
    "file_path": ".../skills/holder-scanner/scripts/scan_holders.sh",
    "offset": 1,
    "limit": 40
  }
}

This is different from mode A. The tool_result WAS written (file content returned normally). But the model never produced the next assistant message — no text, no further tool_use, no end_turn. The stop_reason of that last assistant entry was tool_use, meaning the model expected to continue the turn. It just... stopped.

All tool_use/tool_result IDs matched cleanly (60/60). The turn was not closed. JSONL stopped growing except for a single queue-operation enqueue 7 minutes later when the user's follow-up message arrived (also never dispatched).

Shared signature

Both sessions exhibited tool_use:end_turn stop ratios far outside the norm:

| Session | tool_use stops | end_turn stops | Ratio |
|---|---|---|---|
| fc891dc4 (mode B, 09:36) | 60 | 2 | 30.0 |
| 1a642596 (mode A, 11:13) | 32 | 1 | 32.0 |
| Baseline across 10 healthy sessions Apr 17-18 | — | — | 3.0 — 7.0 |

So the stuck-turn correlates with the model chaining unusually many tools before the hang. Both runs involved heavy compound work (committing coordinated code changes after a peer review, touching multiple files).

What we ruled out

  • TG channel plugin is not involved — it only delivers inbound messages and handles the reply tool. The hang is upstream of message delivery, inside Claude Code's tool execution / turn generation.
  • bun subprocess was alive and healthy throughout both hangs.
  • MCP configuration — we cycled between ENABLE_TOOL_SEARCH=false (eager) and default (deferred), and between full .mcp.json and {"mcpServers": {}}. Both stuck-turns recurred across configurations.
  • Memory pressure — not at OOM; ~700 MB used of 1.9 GB. No OOM entries in dmesg/journal.
  • Edit payload in mode A is a straightforward ASCII text replacement in a .sh file, 626-char new_string, replace_all: false. Nothing unusual — no emoji, no regex specials, no huge size.
  • Disk state — project files fine, no I/O errors, the Edit never actually ran.

Request

  1. Is there telemetry / logging we can enable on the CLI to catch the handoff between model response and tool execution (mode A) and the handoff between tool_result and next model turn (mode B)?
  2. Is the 30x tool_use:end_turn ratio a known precursor to tool-execution hangs in v2.1.109 / Opus 4.7?
  3. Is there a way to surface the hang as an error (exit code, SIGTERM, or at least an error line in the JSONL) instead of silent freeze? Currently there's no signal from the CLI — the process stays running, the session stays "active," but no tool is executing and no assistant turn is advancing.

Happy to pull the full JSONLs and attach them to this issue if it helps. Both stuck sessions are preserved at:

  • /home/ubuntu/.claude/projects/-home-ubuntu-nolix/1a642596-ee80-4d9e-bf8a-eee474d4e82a.jsonl.stuck-20260419-edit1113
  • /home/ubuntu/.claude/projects/-home-ubuntu-nolix/fc891dc4-a248-4d22-949e-3b061660c307.jsonl.stuck-20260419

View original on GitHub ↗

This issue has 9 comments on GitHub. Read the full discussion on GitHub ↗