Skip to content

[BUG] VS Code: transcript >2 GiB causes infinite re-parse loop, extension host OOM kills all Claude tabs (2.1.282) #97229

Description

@BlackWhiteYellow

Preflight Checklist

  • I have searched existing issues and this hasn't been reported yet
  • This is a single bug report (please file separate reports for different bugs)
  • I am using the latest version of Claude Code

What's Wrong?

Once a session transcript (~/.claude/projects/<project>/<session-id>.jsonl) grows past 2 GiB, opening that session in the VS Code extension never completes: within ~15 s the extension host runs out of memory and crashes, and every Claude tab in the window drops with "Claude Code stopped responding in this tab, usually because the editor restarted its extensions." VS Code restarts the extension host, the restored tabs load again, and the host crashes again — a crash loop that survives window reloads, extension updates and rollbacks. The affected session can never be opened in the extension again. This is a time bomb for every long-running session: /compact appends to the transcript instead of shrinking it, so a busy session keeps growing (ours by ~23 MiB/day) until it crosses 2 GiB.

Cause: the transcript parser splits the file buffer into lines with buf.indexOf(10, pos) and treats only -1 as "not found" (extension.js 2.1.280, line 419 col 8008; the bundled SDK copy at line 389 col 44885). In VS Code's runtime (Electron 43.6.0 / Node 24.20.0), Buffer.prototype.indexOf returns a negative, int32-wrapped position for a match beyond byte 2^31; the current Node releases behave the same (v24.21.0 and v26.10.0 on Windows, v22.22.2 on Linux; upstream: nodejs/node#66294). The parser sets pos to that negative value + 1, walks backwards and re-parses the same lines forever, pushing duplicate records until the heap is exhausted. The path is reachable independently of compaction: a never-compacted transcript over 2 GiB is read in full and loops the same way.

The fix does not need to wait for upstream: treat any indexOf result < pos as an error and stop, or never search a window that extends beyond 2^31 (search subarray windows or parse per chunk).

What Should Happen?

The session opens, or at worst that single tab shows an error. A transcript larger than 2 GiB must not send the parser into a loop or crash the extension host shared by all tabs.

Error Messages/Logs

renderer.log:
[info]  Extension host (LocalProcess pid: <n>) is unresponsive.
[error] Extension host (LocalProcess pid: <n>) terminated unexpectedly. The following extensions were running: … Anthropic.claude-code …
[info]  Automatically restarting the extension host.

Claude VSCode.log, ~13 s before each crash:
Received message from webview: {"type":"request",…,"request":{"type":"get_session_request","sessionId":"<id>","purpose":"transcript_open"}}

Extension's own parser under plain Node (--max-old-space-size=4096), synthetic transcript generated with --target-mb 2200 (over 2 GiB):
FATAL ERROR: Ineffective mark-compacts near heap limit Allocation failed - JavaScript heap out of memory

crashpad: one dump per crash, exception code 0xE0000008 (out of memory). Dumps are not attached (they contain process memory); available privately on request.

Steps to Reproduce

  1. Download the gist https://gist.github.com/BlackWhiteYellow/f44e367254db24fbe20d7fe10002ab1f.
  2. In VS Code, open any folder and start one Claude session, so that its project directory exists under ~/.claude/projects/. Close the tab.
  3. Generate a never-compacted transcript larger than 2 GiB straight into that project directory: python gen_synthetic_transcript.py ~/.claude/projects/<that-project-dir> --target-mb 2200 --pad 20000 --boundary-every 0 (it is written as <session-id>.jsonl).
  4. Open that session from the Claude session list. Expected per our analysis: the extension host becomes unresponsive and crashes within ~15 s, and all Claude tabs drop. Warning: this also kills every other Claude tab in that window.
  5. Engine-level confirmation without VS Code: node indexof_2gib.js, or in VS Code's own runtime ELECTRON_RUN_AS_NODE=1 "<path to the VS Code executable>" indexof_2gib.js (PowerShell: $env:ELECTRON_RUN_AS_NODE=1; & "<path to Code.exe>" indexof_2gib.js), prints a negative position for a match beyond 2 GiB. Running the extension's own reader and parser on the step-3 file under plain Node, a guarded copy of the parse loop parses 105 188 lines correctly and then, at byte 2 147 465 580, gets indexOf = −2 147 481 317; unguarded, the parser exhausts a 4 GB heap.

Verification status: steps 3 and 5 were run; step 4 was observed with real transcripts (a 2.01 GiB session was opened right before 11 of 13 host crashes within 47 minutes on 2.1.282, 2.1.281 and 2.1.280; in the last crash it was the only session loading), not with the synthetic file.

Claude Model

None

Is this a regression?

No, this never worked

Last Working Version

No response

Claude Code Version

2.1.282 (Claude Code)

Platform

Anthropic API

Operating System

Windows

Terminal/Shell

Other

Additional Information

  • Environment: Claude Code VS Code extension 2.1.282 (latest); VS Code 1.139.0 (commit 2242ebbb54), Electron 43.6.0, Node 24.20.0, V8 15.0.245.31-electron.0; Windows 10 Home 22H2, build 19045.6466, 64 GB RAM.
  • Surface: the VS Code extension's graphical panel. Not model-specific.
  • Why "not a regression": the failure appears on 2.1.280, 2.1.281 and 2.1.282, 2.1.278 has the same parser code, and it started when the transcript crossed 2 GiB (the same session had opened the day before, at 1.98 GiB, on 2.1.281). Code locations were read in the 2.1.280 bundle.
  • Related, not duplicates: VS Code extension crashes on startup when most recent session file is large #23953 (the extension crashing on a 467 MB session file, closed as duplicate); this report gives a root cause for that crash class, still unfixed in 2.1.282. [BUG] VS Code extension host restart due to OOM caused by Claude Code loading histories of ALL sessions! #89075 (open): extension host OOM from loading the histories of all sessions for the session list, a different code path; here a single tab open loops forever once one transcript passes 2 GiB.
  • Transcript growth: [BUG] Second /compact in one process re-appends the history the first one summarized away, transcript grows quadratically #92089 (open) reports that repeated /compact in one process re-appends earlier history, so transcripts grow quadratically; that would make this limit reachable much sooner.
  • Workaround we validated: with the tab closed, replace the transcript with a tail that starts at a compact_boundary record whose parentUuid is null (keep the original elsewhere). The trimmed session (~96 MiB) opened in 0 s on the same version.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    area:idebugSomething isn't workinghas reproHas detailed reproduction stepsperf:memoryplatform:vscodeIssue specifically occurs in VS Codeplatform:windowsIssue specifically occurs on Windows

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions