"This page is having a problem" - main window renderer crashes with STATUS_BREAKPOINT
- Langage dominant
- Aucune donnée de langage
- Étoiles
- 2.1k
- Forks
- 153
- Métriques de merge des PR
- Aucune PR mergée en 30 j
Description
The main app window intermittently goes blank and shows the WebView2 error page **"This page is having a problem"** with `Error code: STATUS_BREAKPOINT`. Clicking **Refresh** restores the UI, and running agent sessions are unaffected — they keep executing in their own processes. Docked canvas panels stay rendered while the main window is dead.
**Frequency:** measured from the app's own logs — **8 renderer crashes between 2026-08-16 and 2026-08-24**, across 140.6 h of app uptime, i.e. roughly **one per 17 h of use** (1–2 per day). That is a floor: it only covers the 8 days of logs still on disk. Not tied to any single action and not reproducible on demand.
| Date (UTC) | Crashes |
| --- | --- |
| 2026-08-17 | 1 |
| 2026-08-18 | 1 |
| 2026-08-19 | 1 |
| 2026-08-22 | 2 |
| 2026-08-23 | 1 |
| 2026-08-24 | 2 |
**Extensions:** not tested with extensions disabled — but the crashed renderer hosted only the app's own frame (`web-frame-count=1`, `loaded-origin-0=http://tauri.localhost`), and canvas panels run in *separate* WebView2 environments with their own `user-data-dir`, so extension code was not in the crashing process.
## Steps to reproduce
Not deterministic. At the time of the captured crash:
1. A project session was running (agent actively working).
2. A canvas extension panel was docked in the right-hand panel.
3. Interacting with the app chrome — clicking through the usage/plan view and the diff viewer.
4. The window blanked to "This page is having a problem".
The last UI request the backend logged, ~2.5 s before the renderer died, was an ordinary `get_workspace_file_diff` (5 KB diff). Nothing in the app log indicates a failure — only the websocket dropping when the renderer went away.
## Expected behavior
The main window should not crash. If the renderer does die, the app should reload the frame automatically rather than leaving the user on an error page.
## Environment
```text
App version 1.1.12
OS Windows 10 Enterprise 25H2 (build 26200.9106)
Architecture AMD64
WebView2 runtime 151.0.4129.107
Copilot CLI 1.0.80
Agency 2026.8.21.9
GPU 0 Intel(R) Graphics (32.0.101.8132)
GPU 1 NVIDIA GeForce RTX 5090 (32.0.16.1088)
WebView2 flags --disable-features=msWebOOUI,msPdfOOUI,msSmartScreenProtection,CalculateNativeWinOcclusion,UiaProvider
--force-renderer-accessibility
Latest crash 2026-08-24T15:28:13.737Z
report id e1774c4a-7f70-4185-839d-888258d62780
process type renderer
exception 0x80000003
module msedge.dll 151.0.4129.107 +82358569
```
## Suspected cause
The renderer aborts on a `CHECK` inside Blink's **accessibility tree serializer**, which runs on every frame because the app launches its WebView2 with `--force-renderer-accessibility`. Full analysis below.
## Diagnostics available
I have the Crashpad minidump (`e1774c4a-7f70-4185-839d-888258d62780`) preserved locally and can attach it on request. Note that Crashpad **deletes these once uploaded**, so most reporters will no longer have theirs by the time they are asked.
In-depth investigation
### Symbolized stack (crashing thread, `CrRendererMain`)
Resolved against `msedge.dll 151.0.4129.107` with public symbols from the Microsoft symbol server:
```text
content::RendererMain → base::RunLoop::Run
cc::ProxyMain::BeginMainFrame
blink::LocalFrameView::RunPostLifecycleSteps
blink::LocalFrameView::RunAccessibilitySteps
blink::AXObjectCacheImpl::SerializeAXUpdatesIfNeeded
blink::AXObjectCacheImpl::SerializeUpdatesAndEvents
blink::AXObjectCacheImpl::GetUpdatesAndEventsForSerialization
ui::AXTreeSerializer::SerializeChanges
ui::AXTreeSerializer<...>::SerializeChangedNodes x31 (recursive)
blink::AXObject::Serialize
blink::AXObject::SerializeInlineTextBox
blink::AXObject::SerializeLineAttributes
blink::AXInlineTextBox::NeighboringOnLineWithAXBlockFlowIterator
blink::AXBlockFlowIterator::PreviousOnLineAsIndex + 0x25
int 3 <- deliberate CHECK failure
```
### What the exception actually is
`0x80000003` is `EXCEPTION_BREAKPOINT`, not a memory fault. The crash site disassembles to a run of `int 3 / ud2` pairs — Chromium's `IMMEDIATE_CRASH()`, emitted once per `CHECK` so the address identifies which check failed. It fires `0x25` bytes into `PreviousOnLineAsIndex`, i.e. a precondition check at function entry. `rdx = 0x00000000ffffffff` at the fault is consistent with an invalid-index sentinel being passed in — plausibly a stale inline-layout index surviving a DOM mutation, though that last step is inference rather than measurement.
Not memory pressure: no `oom-*` crash keys, and the renderer held only 404 MB private / 1,056 MB committed.
### Why this looks like app configuration rather than user environment
The app's main WebView2 is launched with `--force-renderer-accessibility`, unconditionally. Confirmed three ways: the literal is compiled into `github.exe`, it is present on the live browser-process command line, and the dump records `ax_mode = kNativeAPIs | kWebContents | kInlineTextBoxes | kExtendedPropert…`.
That forces Blink to build and serialize a full accessibility tree — including inline text boxes, the most expensive variant — on every `BeginMainFrame`, whether or not any assistive technology is attached. The app's UI mutates continuously (streaming chat, long virtualized lists, live diffs), which keeps the serializer working over a constantly changing tree.
Corroborating contrast, taken from the live command lines: **canvas panels do not carry the flag.**
| WebView2 instance | Flags |
| --- | --- |
| Main app window | `--disable-features=…,UiaProvider` **`--force-renderer-accessibility`** |
| Canvas panels | `--disable-features=msWebOOUI,msPdfOOUI,msSmartScreenProtection` |
This matches the observed symptom that the main window dies while docked canvas panels keep rendering.
### Suggested fixes, cheapest first
1. Add `AccessibilityBlockFlowIterator` to the `--disable-features` list the app already passes — that is the Edge/WebView2 feature flag gating `AXBlockFlowIterator`, the class in the crashing frame.
2. Only pass `--force-renderer-accessibility` when an assistive technology is actually attached, rather than unconditionally.
3. Drop the flag.
Independently, auto-reloading the frame on `RenderProcessGone` would turn this from a visible crash into a blink.
### Reproducing the analysis
`%LOCALAPPDATA%\com.github.githubapp\EBWebView\Breadcrumbs` records `RenderProcessGone` with an elapsed-time stamp relative to app start, and `…\EBWebView\Crashpad\reports\*.dmp` holds the dump until it is uploaded.
### How the frequency number was derived
The app log itself carries a usable fingerprint. On every fresh document load the page asks the host for the websocket endpoint (`websocket: returning websocket info`); a load preceded by `websocket: client closed connection` in the same app run is therefore a page reload. A renderer crash parks the user on the WebView2 error page, so the gap is seconds-to-minutes, whereas an in-app navigation reconnects immediately. Machine sleep produces a long gap too, but is separable because the **host keeps logging throughout a renderer crash** (agent sessions carry on) and goes silent when the machine sleeps.
Applying that to 21 app logs gives 8 crashes and 1 sleep/resume, correctly excluded. The method was validated against the one crash with independent ground truth: the scan reports an error page from `15:28:14Z` to `15:28:36Z` on 2026-08-24, matching the Crashpad dump at `15:28:13.737Z` and the `RenderProcessGone` breadcrumb.
### Related
Same error code, filed via the in-app feedback button so they lack diagnostics: #2861, #2989, #3019. Suggest linking or consolidating.
Guide de contribution
Ouvrir le guide de contribution
Piste de recherche
Start at the main app's WebView2 setup that adds --force-renderer-accessibility and the existing browser-process or RenderProcessGone handling. Review the preserved Crashpad dump and Breadcrumbs entry for report e1774c4a-7f70-4185-839d-888258d62780, then compare the main window with canvas-panel configuration. Done means the renderer no longer repeatedly crashes, or a renderer failure reloads the frame instead of leaving the error page.
Rédigé par le modèle d'indexation à partir du texte de l'issue.
Évaluation
- Domaine
- desktop
- Type d'issue
- Bug
- Difficulté
- 4/5
- Temps estimé
- 3-5 jours
- Activité
- Active
- Clarté
- Plutôt claire
- Accessibilité débutants
- 48/100