Skip to content

Extension host crash loop: EXC_BREAKPOINT on V8Worker thread during Maglev concurrent compilation (macOS arm64, VS Code 1.126+/Electron 42.2.0) #324639

Description

@miles-augment

vscode-maglev-crash-minidumps.zip

this issue occur when all extensions are disabled?: No — the trigger requires a
sustained extension-host JS workload (see Steps to Reproduce). However, the crash site is
entirely inside V8's background compiler; there are no extension frames on the crashing stack.

  • VS Code Version: 1.126.0, 1.127.0, and 1.128.0-insider commit 86df0e5 (all reproduce; stock downloads, untouched)
  • OS Version: macOS 15.x, Apple Silicon (arm64)
  • Electron: 42.2.0, Node 22.x

Summary

Under a sustained agent-style chat workload, the extension host process
(Code Helper (Plugin)) deterministically crashes with exit code 5 after
2–8 minutes. The crash is an EXC_BREAKPOINT (V8 CHECK/trap, brk #0) on a
background V8Worker thread, at a byte-identical PC in every crash:

Electron Framework +0x8fa45c

We collected 9 Crashpad minidumps across three VS Code versions (including
1.128.0-insider), two storage backends, an automated test harness and an
interactive developer session. All 8 stable-build dumps have a frame-for-frame
identical crash-thread stack (heatmap below), the Insiders dump shows the same
EXC_BREAKPOINT-in-Electron-Framework-background-thread signature (different raw
offsets, as Insiders ships a different Electron Framework build), and disabling
V8's Maglev compiler (--js-flags=--no-maglev) makes the crash disappear
entirely in an otherwise unchanged A/B.

Conclusion: a V8 Maglev concurrent (background) compilation bug in
Electron 42.2.0 tripping an internal CHECK while compiling extension-host JS.

Dump heatmap (8/8 dumps, single failure path)

Symbolicated against stock Electron 42.2.0 breakpad symbols. VS Code ships a
patched Electron build, so some neighboring symbol names are approximate (*),
but the Maglev frames form the exact real nesting order of a concurrent Maglev
compile — not producible by symbol skew.

Heat Frame Symbol
8/8 pc, lr +0x8fa45c / +0x8fa1fc — CHECK/trap site (*)
8/8 frame[0] turboshaft::GraphEmitter<...> (*)
8/8 frame[1] v8::internal::maglev::MaglevGraphBuilder::VisitSingleBytecode()
8/8 frame[2] (*)
8/8 frame[3] v8::internal::maglev::MaglevGraphBuilder::Build()
8/8 frame[4,5] v8::internal::maglev::MaglevCompiler::Compile(LocalIsolate*, ...)
8/8 frame[6,7] v8::internal::maglev::MaglevConcurrentDispatcher::JobTask::Run(v8::JobDelegate*)
8/8 frame[8,9] worker-pool thread bootstrap (*)
8/8 frame[10,11] libsystem_pthread (_pthread_start)

Zero variance across all 8 dumps: same PC, same LR, same 12-frame stack.

The discriminating A/B: --js-flags=--no-maglev

Same machine, same day, same stock 1.127.0 binary, same test, same config:

Run --js-flags=--no-maglev Outcome
A yes passed — 1031 s sustained session, 45 chat turns, clean exit 0, peak ext-host RSS 405 MB
B (30 min later) no crashed — 334 s, exit code 5, minidump with the identical +0x8fa45c stack

Two flagged runs survived a combined ~33 minutes of the workload that reliably
kills unflagged instances in 2–8 minutes.

Ruled out

  • Native modules — reproduced with the extension's only native module
    (classic-level.node / LevelDB) fully replaced by an in-memory Map.
  • Window reloads — reproduced with reload cycles disabled.
  • Version-specific regression — reproduces on 1.126.0, 1.127.0, and
    1.128.0-insider (commit 86df0e5, 2026-07-06 build): extension host crashed
    with code 5 at t=344s (16 turns), t=99s (4 turns) on retry, and t=454s
    (13 turns) in a third run that captured a minidump (included in the
    attachment): EXC_BREAKPOINT, PC in Electron Framework +0x6f72d8, background
    (pthread) thread — same signature class; raw offsets differ because Insiders
    ships a different Electron Framework build.
  • Memory pressure / OOM — ext-host RSS stays < ~500 MB throughout; crash
    is a CHECK trap, not FatalProcessOutOfMemory.
  • Extension/JS code — crash thread is a V8 background compiler thread; no
    extension frames on the crashing stack.

Steps to Reproduce

  1. Install our extension (Augment) in stock VS Code 1.126.0, 1.127.0, or 1.128.0-insider on macOS arm64.
  2. Run a long-lived AI-agent chat session in the extension host: repeated
    multi-turn streaming requests, large JSON message payloads, and periodic
    state persistence, sustained for up to 30 minutes.
  3. The extension host (Code Helper (Plugin)) crashes with exit code 5 after
    2–8 minutes (149–480 s across runs in our automated Playwright harness).
  4. Repeat with --js-flags=--no-maglev on the extension host (e.g. via
    argv.json): the identical workload runs to completion.

The workload requires our extension + backend, so it is not trivially
portable; we are happy to run the reproducer on request, capture additional
dumps, or test candidate fixes/flag combinations. The crashing stack itself
contains no extension frames.

Crash log excerpt (renderer/main log)

Extension host with pid <N> exited with code: 5, signal: unknown.
[UtilityProcess type: extensionHost, pid: <N>]: crashed with code 5 and reason 'crashed'

Crashed thread name: V8Worker; exception: EXC_BREAKPOINT (SIGTRAP).

Workaround

--js-flags=--no-maglev on the extension-host process fully mitigates.

Verified end-user delivery path: adding "js-flags": "--no-maglev" to
argv.json propagates the flag to the extension-host utility process
(Code Helper (Plugin), --utility-sub-type=node.mojom.NodeService — flag
visible on its command line), as well as renderer and other utility
processes. A stock instance without the argv.json entry does not carry the
flag (negative control).

Attachments

  • 9 Crashpad minidumps (.dmp): 8 from VS Code 1.126.0/1.127.0 and 1 from
    1.128.0-insider (insiders-crash-52340899.dmp, commit 86df0e5)
  • Symbolicated per-dump stacks (identical across the 8 stable dumps;
    representative one below)
pc        +0x8fa45c   (CHECK/trap site)
frame[1]  +0x2e481c   v8::internal::maglev::MaglevGraphBuilder::VisitSingleBytecode()
frame[3]  +0x35f45c   v8::internal::maglev::MaglevGraphBuilder::Build()
frame[4]  +0x7d4f4c   v8::internal::maglev::MaglevCompiler::Compile(...)
frame[5]  +0x7d4d2c   v8::internal::maglev::MaglevCompiler::Compile(...)
frame[6]  +0x4d9730   v8::internal::maglev::MaglevConcurrentDispatcher::JobTask::Run(...)
frame[7]  +0x4d92f8   v8::internal::maglev::MaglevConcurrentDispatcher::JobTask::Run(...)
frame[10] libsystem_pthread +0x6bc8
frame[11] libsystem_pthread +0x1b80   (_pthread_start)

Dump UUIDs: 1d1aa1cd, 25e67d29, 3debc2ad, 43f6e320, a9dc47d0, aa8d9657, af77f303, c6ed8c2b (stable); 52340899 (1.128.0-insider)

Insiders dump crash thread (raw offsets, Insiders Electron Framework build):

pc        Electron Framework +0x6f72d8   (EXC_BREAKPOINT / trap site)
lr        Electron Framework +0x6f7178
frames    Electron Framework +0x6f6fe8, +0x11cedf0, +0x72ea40, +0x86c1c8,
          +0x24571cc, +0x1413534, +0x251c158, +0xfebc9c
          libsystem_pthread +0x6bc8, +0x1b80 (_pthread_start)

Metadata

Metadata

Assignees

Labels

bugIssue identified by VS Code Team member as probable bugfreeze-slow-crash-leakVS Code crashing, performance, freeze and memory leak issuesupstreamIssue identified as 'upstream' component related (exists outside of VS Code)upstream-issue-fixedThe underlying upstream issue has been fixed

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions