[Windows Desktop] Full-process PowerShell/WMI polling remains in 26.721.4979.0 and contributes to system-wide input lag
\[!IMPORTANT\]<br>Creating this to better document and consolidate information for an on-going issue that multiple people have reported. Including additional information about suspected causes and what has been done locally to a patched copy of the desktop app to temporarily resolve the issue on my machine.
What version of the Codex App are you using (From “About Codex” dialog)?
26.721.41059
What subscription do you have?
Pro
What platform is your computer?
Microsoft Windows NT 10.0.26200.0 x64
What issue are you seeing?
Summary
Codex Desktop on Windows can cause intermittent mouse and keyboard stalls across the entire operating system, not only inside the app.
The strongest confirmed contributor is repeated full-machine process discovery launched by the Desktop app through short-lived PowerShell processes and WMI/CIM queries.
The current Store package tested here, OpenAI.Codex 26.721.4979.0, still contains and executes these process-inventory paths.
A 30-second stock capture recorded five Desktop-descendant WMI-inventory PowerShell starts, seven total PowerShell starts, 79 conhost.exe starts, and 172 captured descendant starts.
A narrowly patched copy of the same current runtime recorded zero WMI-inventory PowerShell starts in two separate 30-second runs. It retained the same 13 live runtime processes and remained alive in both runs.
An earlier controlled A/B on package 26.707.3351.0 isolated the command-registry discovery path. Suppressing that path reduced:
- WMI PowerShell starts from 26 to 0 per minute;
- paired WMI
conhost.exestarts from 26 to 0; - maximum low-level mouse-event delivery delay from 234 ms to 16 ms;
- events delayed over 100 ms from 1 to 0.
That is direct intervention evidence that Desktop-generated process discovery materially contributes to the system-wide stalls.
Automatic repository-origin discovery is a second process-amplification path. In a matched A/B on 26.707.3351.0, suppressing it reduced git.exe starts from 206 to 22 in about 47 seconds.
The current local mitigation is an unsupported diagnostic patch, not a production-ready fix. It disables optional discovery features in a copied runtime while leaving the signed Microsoft Store package untouched.
This issue consolidates the root cause, current patch, measurements, and related public reports into one tracker.
The earlier reports are linked below rather than restated as separate claims. This report adds current-build reproduction, the 26.721.4979.0 patch port, fresh validation, and one cross-issue technical map not present in a single existing issue.
Affected environment
<!-- linear:table-colwidths:400,400 -->
| Item | Value |
| -- | -- |
| Platform | Windows 11 x64 |
| Distribution | Microsoft Store/MSIX |
| Current affected package | OpenAI.Codex 26.721.4979.0 |
| Internal app version | 26.721.41059 |
| Internal build | 5848 |
| Desktop executable | ChatGPT.exe |
| Executable file version | 150.0.7871.128 |
| Current-build validation date | 2026-07-27 |
| Earlier causal A/B build | 26.707.3351.0 |
Independent reports show the same query families across older and newer releases. Examples range from 26.506.3741.0 in [#22912](<https://github.com/openai/codex/issues/22912>) through the 26.715 reports listed below.
User-visible impact
- Mouse movement and typing intermittently stall across unrelated Windows applications.
- The problem is often most visible during launch, command execution, project refresh, or task switching.
- Local captures show PowerShell, console-host, WMI, and Git activity. Related public reports also correlate some events with Defender or cleanup-process spikes.
- Some reports observe continued background activity after the app window closes, until the remaining Desktop process tree is terminated.
- The symptom is not limited to renderer frame rate. A low-level Windows hook measured delayed event delivery before downstream application rendering.
Actual behavior
Several independent Desktop paths can request overlapping global process snapshots. Each snapshot creates process-launch, console-host, WMI-provider, serialization, and teardown work.
Other paths can concurrently fan out Git commands or repeatedly attempt process cleanup. Together, these can create sustained machine-wide contention and visible input stalls.
What steps can reproduce the bug?
The exact trigger is state-dependent, but the underlying process-inventory work is directly observable.
- Launch the Windows Desktop app.
- Open a project and use a task that executes local commands.
- Observe the full
ChatGPT.exedescendant tree with Process Monitor, Process Explorer, System Informer, ETW, or a native Toolhelp-based ancestry monitor. - Record process command lines and WMI Provider Host activity.
- Watch for short-lived
powershell.exe,conhost.exe,git.exe, andtaskkill.exechildren or descendants. - Check whether mouse or keyboard delivery stalls in another foreground application at the same time.
The two characteristic WMI query families are:
Get-CimInstance Win32_Process |
Select-Object ProcessId, ParentProcessId |
ConvertTo-Json -Depth 2
and:
$cpuByPid = @{}
Get-CimInstance Win32_PerfFormattedData_PerfProc_Process |
ForEach-Object {
$cpuByPid[[int]$_.IDProcess] = [double]$_.PercentProcessorTime
}
Get-CimInstance Win32_Process
The second command also collects process details such as command line and working-set size.
What is the expected behavior?
Routine Desktop operation should not repeatedly launch PowerShell to enumerate every process on the machine.
Process tracking should be scoped to app-owned children, coalesced, cached, bounded, and implemented without degrading input delivery in unrelated applications.
Repository metadata work should be proportional to unique repository roots, not the number of submitted working directories or UI refreshes.
Additional information
Technical root cause
The packaged Electron application contains several separate process-discovery consumers. They do not share one cached, single-flight snapshot.
1\. Telemetry/process-snapshot worker
The bundled worker is:
.vite/build/child-process-snapshot-worker.js
The current call path is:
30-second focused heartbeat, renderer-ready event, or renderer snapshot request
-> Electron sampler collectSnapshotFields()
-> addChildProcessFields()
-> child-process-snapshot-worker.js
-> Win32_Process parent scan
-> Win32_PerfFormattedData_PerfProc_Process
plus Win32_Process detail scan
The current main bundle has a 30-second heartbeat and a 5-second minimum gate for non-heartbeat triggers.
On Windows, the worker launches fresh PowerShell processes for both WMI query families.
PID detail work is chunked, so one snapshot can involve one parent scan and one or more detail scans.
2\. Shared process-subtree discovery
The current shared bundle is:
.vite/build/src-BPbHdvxe.js
In package 26.721.4979.0, the module-exported seam is:
export Tn
-> internal IW
-> full Win32_Process parent scan
-> filtered descendant resolution
-> performance/process-detail WMI scan
This implementation is separate from the telemetry worker and can independently execute the same global inventory work.
3\. Chat-process registry private dependencies
The current registry class captures the original implementations in a private dependency object:
$Y = {
listDetachedProcessCandidates: LW,
listProcessSubtrees: IW
}
Its mutation path is:
registry upsert() / complete()
-> resolve a missing osPid
-> retry at approximately 0, 100, 300, and 600 ms
-> privately captured listProcessSubtrees()
-> detached-process fallback if still unmatched
-> PowerShell/WMI
Each subtree attempt can execute two PowerShell/WMI inventory commands. The final detached fallback can execute another.
Source inspection therefore permits up to nine PowerShell/WMI inventory invocations for one unmatched mutation. A command may invoke the mutation at both start and completion.
Replacing only the exported process-snapshot function does not affect these privately captured references.
This registry path produced the strongest controlled process and input-delivery A/B.
4\. Chrome native-host cleanup
The current release contains another process-inventory consumer:
export gn
-> internal BK
-> default Windows listProcesses()
-> detached-process inventory
-> WMI
Its confirmation loop uses delays of approximately 0, 100, 200, 400, and 800 ms.
Internal callers can retain the original dependency rather than looking up the public export. An export-only override is therefore insufficient for the current build.
This is another global process-inventory and cleanup consumer.
The broader taskkill.exe/conhost.exe reports may reflect a related lifecycle defect, but this trace does not establish that BK/gn launches taskkill.exe. The verified cleanup here uses process.kill.
5\. Automatic Git-origin discovery
The Git worker accepts lists of directories and resolves them concurrently:
git-origins worker request
-> normalize and deduplicate submitted directories
-> Promise.all(directory resolutions)
-> repository metadata and origin lookup
Representative commands include:
git rev-parse --show-toplevel
git rev-parse --git-common-dir
git config --get remote.origin.url
git config --null --get core.fsmonitor
Multiple UI directory sets, malformed or empty .git directories, and cache invalidation can recreate the fan-out.
This is a separate contributor to process churn. It should not be conflated with the command-registry WMI path that produced the direct input-latency A/B.
Why an app-local defect affects the whole system
The local captures directly demonstrate operating-system-wide work rather than only renderer work:
- repeated PowerShell and console-host creation and teardown;
- global WMI process and performance inventory;
- concurrent Git and console-host creation;
- process-tree construction and JSON serialization;
- delayed low-level input-hook delivery.
The linked reports separately document WMI quota exhaustion, Defender load, taskkill storms, DWM degradation, and kernel-resource pressure.
Those reports show the breadth of the Windows process-lifecycle problem. They are not all locally reproduced mechanisms in the current experiment.
The historical input probe measured delay at the low-level Windows hook callback. That places the observed stall before any affected foreground application renders the input.
Current diagnostic patch
\[!WARNING\]<br>This is an unsupported diagnostic mitigation for confirming and containing the bug. It is build-specific, reduces functionality, and is not a substitute for an upstream fix.
The patch is applied to a copied runtime. The signed Store installation remains untouched.
Current build-specific mapping
The minified identifiers changed between releases. For 26.721.4979.0, the exact ordinal, case-sensitive mappings are:
<!-- linear:table-colwidths:266,266,266 -->
| Behavior | Internal symbol | Export |
| -- | -- | -- |
| Process-subtree discovery | IW | Tn |
| Chat-process registry | tX | en |
| Chrome native-host cleanup | BK | gn |
These identifiers must be rediscovered for every build.
There are important case hazards in this release:
- lowercase
knexportsxW, a browser/Chrome configuration object; - lowercase
rnexportswY, an instruction-builder function; - uppercase
Gnis unrelated to lowercasegn.
Reusing the older build's mappings, or comparing names case-insensitively, can silently patch unrelated functionality.
Packaging procedure
- Leave the signed Store package untouched.
- Copy the entire matching Store
appdirectory into a separate versioned runtime. - Archive and extract
resources/app.asar. - Preserve the original JavaScript files beside or outside the extracted source.
- Install three wrapper files implementing the six mitigation behaviors below.
- Repack the ASAR with the matching native-module layout.
- Overlay the new
app.asarandapp.asar.unpackedinto the copied runtime. - Verify that all non-ASAR executables and resources still match the same Store release.
- Do not run the Store runtime and copied runtime simultaneously because they share application state.
The repack command used for the current build was:
npx.cmd --yes '@electron/asar@4.2.0' pack <source> <output> `
--unpack-dir '{node_modules/better-sqlite3,node_modules/node-pty}' `
--unpack '**/*.node'
The matching app.asar.unpacked directory must remain beside the ASAR.
Do not combine a new ASAR with an older executable or runtime. Electron, native-module ABI, Codex binaries, and packaged resources may all change between releases.
Patch 1: return an empty optional telemetry snapshot
Replace the telemetry child-process worker while preserving its successful response contract:
parentPort.postMessage({ type: "ok", value: [] });
This prevents that worker from launching either PowerShell/WMI query family.
Patch 2: intercept only automatic git-origins
Preserve the original Git worker as worker-original.js.
Install a wrapper at the expected worker.js path before loading the original. Intercept only messages satisfying all three conditions:
workerData.workerId === "git"
message.type === "worker-request"
message.request.method === "git-origins"
Return a successful result containing:
{ origins: [] }
The response must retain the original request identifier and worker protocol. Delegate every other request and event to worker-original.js.
Patch 3: suppress the exported shared process snapshot
Preserve the current shared module as:
.vite/build/src-original-BPbHdvxe.js
Leave a wrapper at the original src-BPbHdvxe.js path.
On Windows, replace only export Tn with:
const emptyProcessSnapshot = async () => [];
Pass every unrelated export through unchanged.
Patch 4: stop registry mutations from scanning
On Windows, replace export en with a subclass of the original registry.
Inherited reads remain available. Only the two mutation methods that trigger private process discovery become no-ops:
class NonScanningChatProcessRegistry extends original.en {
async upsert() {}
async complete() {}
}
This intentionally reduces command-lifecycle registry persistence.
Patch 5: inject an empty process list into native-host cleanup
Wrap export gn and call the original implementation with its normal options plus a replacement nested dependency:
original.gn({
...options,
dependencies: {
...options?.dependencies,
listProcesses: async () => [],
},
});
All other cleanup checks remain in the original function.
This prevents this exported cleanup path from performing a global process inventory.
Patch 6: cover private module closures during initialization
Exports alone do not cover private references captured while the original shared module initializes.
Temporarily wrap child_process.execFile only while importing src-original-BPbHdvxe.js.
The interception predicate requires all of the following:
executable basename is powershell.exe
command contains Get-CimInstance
command contains Win32_Process
or Win32_PerfFormattedData_PerfProc_Process
Matching commands receive JSON []. Unrelated child-process calls delegate to the original execFile.
The wrapper must implement the correct util.promisify.custom behavior because the preserved module uses a promisified form.
Restore the global child_process.execFile in a finally block immediately after module initialization.
The preserved module captures the promisified wrapper during initialization. Its private helpers therefore retain the narrow filter for later calls after the global execFile has been restored.
The effective shared-module behavior is:
Tn -> async () => []
en -> non-scanning registry subclass
gn -> original cleanup with listProcesses: async () => []
unrelated exports -> original implementation
private WMI helpers captured during original-module initialization
-> matching calls made later return JSON []
unrelated execFile calls -> original implementation
Validation
Original causal A/B: package 26.707.3351.0
The registry comparison used identical diagnostic settings for all other patched paths. The only changed variable was whether registry mutations retained WMI discovery.
One-minute process-ancestry comparison
<!-- linear:table-colwidths:266,266,266 -->
| Measurement | Registry WMI active | Registry WMI suppressed |
| -- | -- | -- |
| Desktop-descendant WMI PowerShell starts | 26 | 0 |
| Paired WMI conhost.exe starts | 26 | 0 |
| Time with at least one WMI helper alive | 94.8% | 0% |
| Desktop core-process restarts | 0 | 0 |
Low-level input-delivery comparison
<!-- linear:table-colwidths:266,266,266 -->
| Measurement | Registry WMI active | Registry WMI suppressed |
| -- | -- | -- |
| Mouse events | 4,022 | 8,317 |
| Maximum hook-delivery delay | 234 ms | 16 ms |
| Events delayed over 16 ms | 2 | 0 |
| Events delayed over 100 ms | 1 | 0 |
The probe compared each event timestamp with the time its WH_MOUSE_LL or WH_KEYBOARD_LL callback ran. It measured delivery to the hook, not renderer latency.
Matched Git-origin comparison
<!-- linear:table-colwidths:266,266,266 -->
| Measurement | Stock | Origin discovery suppressed |
| -- | -- | -- |
| git.exe starts | 206 | 22 |
| conhost.exe starts | 185 | 55 |
| All observed process starts | 496 | 165 |
The launch windows were approximately 47 seconds. A separate ancestry capture confirmed that the large Git burst descended from Desktop.
Current patch port: package 26.721.4979.0
Two patched 30-second process-ancestry runs were compared with a stock 30-second run:
<!-- linear:table-colwidths:200,200,200,200 -->
| Measurement | Stock | Patched run 1 | Patched run 2 |
| -- | -- | -- | -- |
| WMI-inventory PowerShell starts | 5 | 0 | 0 |
| Automatic git-origins probes | 0 | 0 | 0 |
| All PowerShell starts | 7 | 1 | 1 |
| conhost.exe starts | 79 | 31 | 25 |
| Captured descendant starts | 172 | 93 | 74 |
| Live runtime processes | 13 | 13 | 13 |
| Desktop remained alive | Yes | Yes | Yes |
After each probe, the harness closed the main window, force-stopped any remaining copied-runtime processes, and verified that zero remained.
The current stock window did not happen to contain an automatic Git-origin probe. Current Git coverage therefore combines a worker contract test with the earlier matched process A/B.
The three current captures were separate launch windows without a matched active-command workload.
Total descendant and conhost.exe counts are descriptive, not precise performance deltas. The deterministic pass criteria were zero classified WMI inventories and zero automatic origin probes, backed by contract tests.
The current tests prove that the identified WMI and automatic-origin hot paths were absent during the measured windows. They do not prove that every source of Desktop lag or every cleanup loop is fixed.
Patch verification gates
The current build passed:
- JavaScript syntax checks for wrappers and preserved originals;
- exact telemetry-worker response-contract checks;
git-originsinterception and non-origin delegation tests;- behavior checks for
Tn,en, andgn; - restoration checks for global
child_process.execFile; - guards proving
kn,rn, andGnremain identical to their original unrelated exports; - packed-ASAR extraction comparisons;
- native-module layout checks;
- comparisons of ten critical executable, Codex, Electron, and
rg.exeresources against the matching Store payload.
Only the intended app.asar and matching app.asar.unpacked overlay differed from the copied Store runtime.
At final verification, the live Store ASAR still matched the archived source ASAR. The Store installation was not modified.
Limitations and functional tradeoffs
- All consumers of the telemetry worker snapshot or
Tnreceive no descendants. This includes Desktop child-process observation and its process-list/kill UI. - Registry insertion/update and completion/removal through
upsert()andcomplete()are disabled. - Automatic repository-origin discovery returns no origins. Repository grouping and project metadata may therefore be less accurate.
- Chrome native-host cleanup cannot discover candidate processes through global inventory. Stale native-host or extension-host candidates may not be terminated through that path.
- The patch does not prove that every
taskkill.execleanup path is disabled. - Ordinary Git operations, non-
git-originsworker traffic, and unrelated PowerShell or child-process calls remain enabled. - The copied runtime does not receive Store updates and must be rebuilt for each release.
- The minified bundle names and exports are build-specific and must never be carried forward without source inspection.
Evidentiary limits
- The current build refresh includes direct process-creation validation but no new low-level input-latency A/B.
- The
234 msto16 msresult is a controlled single-run comparison on the earlier affected build, not a long-duration benchmark. - The current stock capture contained no automatic origin probes, so the current run is not a fresh Git process-count A/B.
- The Toolhelp ancestry monitor sampled every 25 ms. It can miss very short-lived processes.
- Command-line classification can miss a process that exits before its command line is read. The reported counts are lower bounds.
- The low-level hook probe measured delivery to its callback, not downstream app rendering.
- Elevated ETW was not used to isolate the final Windows kernel contention point.
- Not every PowerShell, Git, console-host, or cleanup process is necessarily unnecessary.
The causal conclusion is based on source tracing, process ancestry, a narrow intervention, and symptom-boundary input measurements.
Recommended upstream fix
The affected features can be preserved without routine global PowerShell/WMI scans.
- Track app-owned processes at the shared spawn boundary.
- Route all process-discovery consumers through one replaceable dependency.
- If enumeration is unavoidable, use one native snapshot, cache it briefly, coalesce concurrent requests, and cancel superseded work.
- Do not retry optional process telemetry when discovery is unavailable.
- Make PID resolution bounded and event-driven instead of performing several global scans at command start and completion.
- Separate process observation from cleanup. Cleanup should act only on explicitly owned PIDs with start-time or process-handle validation.
- Canonicalize and deduplicate repository paths before origin lookup.
- Cache origin data per repository root, use bounded concurrency, and cancel stale requests.
- Ignore malformed or empty
.gitmarkers rather than repeatedly probing them. - Keep process inventory behind one testable interface so private closures cannot bypass throttling or caching.
Suggested Windows regression budgets
- Zero routine Desktop-descendant PowerShell commands containing
Win32_ProcessorWin32_PerfFormattedData_PerfProc_Process. - Process starts proportional to unique repository roots, not submitted directory count.
- At most one in-flight process snapshot for all consumers.
- No unbounded
taskkill.exeorconhost.exeloops. - No measurable low-level mouse or keyboard delivery regression during active command traffic.
- Bounded process cleanup after app exit.
Requested outcome
Please use this issue as a canonical tracker for the Windows process-inventory and process-fan-out defect family.
The requested product outcomes are:
- replace routine PowerShell/WMI process inventory with bounded, app-owned process tracking;
- coalesce and cache any unavoidable native snapshots;
- make process cleanup ownership-aware and bounded;
- bound and cache repository-origin discovery;
- add Windows process-creation and low-level input regression tests;
- provide a supported feature flag or temporary mitigation until the upstream implementation ships.
I can provide sanitized command-line captures, ancestry data, wrapper-contract tests, and additional measurements if maintainers need them.
Related public reports
The index below was checked against GitHub on 2026-07-28.
It includes the original report, every issue linked from that report, the existing discussion, direct WMI/Git/cleanup reports found in a fresh search, and a separate group of similar symptoms.
The categories matter. The first four groups contain direct mechanism or close process-lifecycle evidence. The final groups are included for context and are not presented as proof of the same cause.
Primary history
<!-- linear:table-colwidths:266,266,266 -->
| Link | State | Relevance |
| -- | -- | -- |
| [#28855 — original Windows system-input-lag report](<https://github.com/openai/codex/issues/28855>) | Open | Reports whole-system mouse and typing stalls beginning with Desktop 26.611.8604.0. |
| [Discussion #29949 — Windows Desktop performance visibility thread](<https://github.com/openai/codex/discussions/29949>) | Public discussion | Community thread collecting Windows performance reports. |
| [Existing root-cause and patch comment](<https://github.com/openai/codex/discussions/29949#discussioncomment-17597798>) | Public comment | Earlier full writeup and original causal A/B on 26.707.3351.0. |
Direct WMI and process-snapshot evidence
<!-- linear:table-colwidths:266,266,266 -->
| Link | State | Relevance |
| -- | -- | -- |
| [#22912 — Electron sampler WMI snapshot failures and freezes](<https://github.com/openai/codex/issues/22912>) | Open | Shows both WMI query families in Desktop 26.506.3741.0. |
| [#25453 — PowerShell full-process polling](<https://github.com/openai/codex/issues/25453>) | Open | Measures 23 PowerShell starts in 30.05 seconds on 26.527.31326. |
| [#29499 — WMI Provider Host CPU and system freezes](<https://github.com/openai/codex/issues/29499>) | Open | Reports WMI CPU near 50% and recurring mouse freezes on 26.616.51431. |
| [#32562 — starting a task saturates WMI Provider Host](<https://github.com/openai/codex/issues/32562>) | Open | Confirms both query families in 26.707.3748.0. |
| [#33875 — WMI and Defender load on the home screen](<https://github.com/openai/codex/issues/33875>) | Open | Reproduces before opening a project on 26.715.2305.0. |
| [#33940 — sustained WMI CPU and system stutter](<https://github.com/openai/codex/issues/33940>) | Closed as duplicate of openai/codex#33875 | Reports repeated Win32_Process scans and mouse stalls on 26.715.31251. |
| [#34014 — Desktop WMI saturation while VS Code remains normal](<https://github.com/openai/codex/issues/34014>) | Open | Isolates the behavior to Desktop on 26.715.12143. |
| [#34050 — repeated PowerShell creation and hard freeze](<https://github.com/openai/codex/issues/34050>) | Open | Reports hundreds of launches and WMI quota failures on 26.715.4045.0. |
| [#34158 — system-wide mouse stutter with sampler queries](<https://github.com/openai/codex/issues/34158>) | Open | Stutter persists until the remaining process tree is killed on 26.715.4045.0. |
| [#34580 — sampler retries WMI snapshots indefinitely](<https://github.com/openai/codex/issues/34580>) | Open | Identifies missing backoff/single-flight behavior in 26.715.8383.0. |
| [#34592 — WMI loop spawns about ten helpers per second](<https://github.com/openai/codex/issues/34592>) | Open | Measures 235 helpers in 25 seconds on 26.715.7063.0. |
| [#34666 — WMI/Defender CPU and mouse stutter stop on full exit](<https://github.com/openai/codex/issues/34666>) | Open | Correlated lifecycle evidence on 26.715.8383.0; the exact provider is not isolated. |
| [#34854 — Git/PowerShell churn drives WMI and Defender CPU](<https://github.com/openai/codex/issues/34854>) | Open | Recent mixed-path reproduction on 26.715.10079.0. |
| [#34879 — launch saturates CPU through WMI Provider Host](<https://github.com/openai/codex/issues/34879>) | Open | Recent all-core reproduction on 26.715.10079.0. |
Cleanup-loop and taskkill.exe/conhost.exe evidence
<!-- linear:table-colwidths:266,266,266 -->
| Link | State | Relevance |
| -- | -- | -- |
| [#33776 — hundreds of taskkill/conhost children, WMI storms, and DWM degradation](<https://github.com/openai/codex/issues/33776>) | Open | Reports 987 failed WMI queries in package 26.707.12708.0. |
| [#33778 — taskkill/conhost storm during local tool execution](<https://github.com/openai/codex/issues/33778>) | Open | Counts 178 taskkill and 197 conhost processes on 26.715.2305.0. |
| [#34001 — built-in agent cleanup runaway loop](<https://github.com/openai/codex/issues/34001>) | Open | Reports roughly 300 each of taskkill and conhost on 26.715.4045.0. |
| [#34025 — cold launch creates 300+ cleanup helpers](<https://github.com/openai/codex/issues/34025>) | Open | Storm begins after launch without a tool call on 26.715.3651.0. |
| [#34260 — cleanup storm exhausts WMI](<https://github.com/openai/codex/issues/34260>) | Open | Reports 457 taskkill, 473 conhost, and 1,388 total processes on 26.715.4045.0. |
| [#34302 — stuck cleanup helpers cause system-wide UI delays](<https://github.com/openai/codex/issues/34302>) | Open | Reports taskkill/conhost buildup on 26.715.31925. |
| [#34548 — mixed Git/WMI/taskkill storm and disk saturation](<https://github.com/openai/codex/issues/34548>) | Closed | Mixed process-storm report on 26.715.8383.0. |
| [#34691 — sustained WMI CPU with cleanup helpers](<https://github.com/openai/codex/issues/34691>) | Open | A 20-second sample finds 408/410 taskkill helpers as direct Desktop children. |
| [#34929 — process-manager polling launches 12–15 taskkill processes per second](<https://github.com/openai/codex/issues/34929>) | Open | Measures 226 launches in 15 idle seconds on 26.715.10079.0. |
These reports establish a close process-lifecycle failure family. The local patch covers known snapshot, registry, origin, and native-host inventory paths, but this issue does not claim it disables every cleanup path.
Git-origin, repository-discovery, and kernel-pressure evidence
<!-- linear:table-colwidths:266,266,266 -->
| Link | State | Relevance |
| -- | -- | -- |
| [#17229 — repeated Git status and orphan Git/conhost processes](<https://github.com/openai/codex/issues/17229>) | Open | Early report of the Windows Git/conhost family in 26.325.3894.0. |
| [#16786 — repeated Git creation with NTFS pool growth](<https://github.com/openai/codex/issues/16786>) | Open | Connects Git process churn with Windows kernel-pool pressure. |
| [#20567 — roughly 1,000 Git commands per minute](<https://github.com/openai/codex/issues/20567>) | Open | Independent high-rate Git process report. |
| [#29858 — continuous Git in a non-repository workspace](<https://github.com/openai/codex/issues/29858>) | Open | Git/conhost creation stops after the directory becomes a valid repository. |
| [#29911 — empty .git directories trigger repeated origin scanning](<https://github.com/openai/codex/issues/29911>) | Open | Explicit git-origins, Git config, console-host, and Defender loop. |
| [#30926 — Git process creation drives kernel Token/Toke growth](<https://github.com/openai/codex/issues/30926>) | Open | ETW captures 263 Desktop-parented Git starts and 55 PowerShell starts in about 55 seconds. |
| [#29436 — persistent kernel-pool growth and system slowdown](<https://github.com/openai/codex/issues/29436>) | Open | Related kernel-pressure report. openai/codex#30926 shows a plausible mechanism for one process-churn variant, not proof that openai/codex#29436 has the same cause. |
| [#29729 — stale Git/process-token objects](<https://github.com/openai/codex/issues/29729>) | Closed as duplicate | Additional report in the same Git/process-token cluster. |
| [#35775 — same-build git-origins storm in the VS Code extension](<https://github.com/openai/codex/issues/35775>) | Open | Non-Desktop corroboration only: internal build 26.721.41059 produced 474 Git and 360 console-host starts in three minutes. |
Similar Windows symptoms without confirmed shared cause
<!-- linear:table-colwidths:266,266,266 -->
| Link | State | Distinction |
| -- | -- | -- |
| [#20214 — frequent freezes and stutters on Windows](<https://github.com/openai/codex/issues/20214>) | Open | Similar in-app freeze/stutter; the reporter says the rest of Windows remains responsive. |
| [#27394 — high CPU after an update](<https://github.com/openai/codex/issues/27394>) | Closed | Similar performance symptom; mechanism not established here. |
| [#28440 — renderer CPU usage](<https://github.com/openai/codex/issues/28440>) | Closed as duplicate | Renderer-focused rather than proven process-inventory work. |
| [#28735 — chat switching and composer lag](<https://github.com/openai/codex/issues/28735>) | Closed | In-app lag without direct evidence of this mechanism. |
| [#29187 — slow Codex thread switching on Windows](<https://github.com/openai/codex/issues/29187>) | Open | Similar transition-time symptom. |
| [#29281 — idle CPU/GPU activity](<https://github.com/openai/codex/issues/29281>) | Open | Similar background pressure, without an established shared cause. |
| [#29543 — first-typing freeze](<https://github.com/openai/codex/issues/29543>) | Open | Similar input symptom, without direct WMI attribution. |
| [#29590 — previous-task loading stalls](<https://github.com/openai/codex/issues/29590>) | Open | Similar UI stall, without direct process-polling evidence. |
| [#29700 — Windows memory growth](<https://github.com/openai/codex/issues/29700>) | Open | Resource-growth report without a confirmed common mechanism. |
| [#29821 — UI stutters during launch and first typing](<https://github.com/openai/codex/issues/29821>) | Open | Reporter observed low WMI usage, so likely a different initialization path. |
| [#33074 — mouse stutter without CPU/disk saturation](<https://github.com/openai/codex/issues/33074>) | Open | Similar symptom, but the reported resource profile differs. |
| [#33258 — cursor jitter when Desktop becomes idle](<https://github.com/openai/codex/issues/33258>) | Open | Evidence points toward DWM composition; reducing Git churn did not remove it. |
| [#33382 — system stutter during task switching](<https://github.com/openai/codex/issues/33382>) | Open | DPC/ISR and crash evidence, not established as WMI polling. |
| [#30389 — kernel-memory retention](<https://github.com/openai/codex/issues/30389>) | Closed | Outcome-level kernel-resource report without direct Git/process evidence. |
Logging and SQLite pressure referenced by the original report
These can cause severe Desktop slowdowns but are not evidence for the WMI/Git mechanism.
<!-- linear:table-colwidths:266,266,266 -->
| Link | State | Distinction |
| -- | -- | -- |
| [#24275 — rapid logs_2.sqlite and WAL growth](<https://github.com/openai/codex/issues/24275>) | Open | macOS logging/storage pressure referenced by the original report. |
| [#27741 — large log database can prevent launch](<https://github.com/openai/codex/issues/27741>) | Open | Database startup failure. |
| [#29177 — SQLite I/O and system stalls](<https://github.com/openai/codex/issues/29177>) | Open | Storage-pressure symptom. |
| [#29463 — TRACE logging despite a warning-level setting](<https://github.com/openai/codex/issues/29463>) | Open | Excess logging rather than process polling. |
| [#29674 — TRACE logging and SSD pressure](<https://github.com/openai/codex/issues/29674>) | Open | Excess write pressure. |
| [#29799 — app-server TRACE and WAL writes](<https://github.com/openai/codex/issues/29799>) | Open | Logging/database write pressure. |
| [#29832 — persistent disk writes after update](<https://github.com/openai/codex/issues/29832>) | Open | Storage activity without proof of this process-discovery path. |
Non-Windows reports linked by the original issue
The original issue also referenced these as broad performance comparisons. They are not part of the Windows WMI/Git causal cluster.
- [#20547 — Desktop sluggishness after an update](<https://github.com/openai/codex/issues/20547>) — Open
- [#21326 — macOS renderer CPU and UI lag](<https://github.com/openai/codex/issues/21326>) — Closed
Technical references
- [Original public root-cause and patch writeup](<https://github.com/openai/codex/discussions/29949#discussioncomment-17597798>)
- [OpenAI: ChatGPT for Windows](<https://learn.chatgpt.com/docs/windows/windows-app>)
- [Microsoft:
Win32_Process](<https://learn.microsoft.com/en-us/windows/win32/cimwin32prov/win32-process>) - [Microsoft: low-level mouse hook event data](<https://learn.microsoft.com/en-us/windows/win32/api/winuser/ns-winuser-msllhookstruct>)
- [Microsoft: low-level keyboard hook event data](<https://learn.microsoft.com/en-us/windows/win32/api/winuser/ns-winuser-kbdllhookstruct>)
- [Microsoft: taking a process snapshot with Toolhelp](<https://learn.microsoft.com/en-us/windows/win32/toolhelp/taking-a-snapshot-and-viewing-processes>)
- [Electron: application distribution](<https://www.electronjs.org/docs/latest/tutorial/application-distribution/>)
- [Electron: ASAR archives](<https://www.electronjs.org/docs/latest/tutorial/asar-archives>)
11 Comments
Potential duplicates detected. Please review them and close your issue if it is a duplicate.
Powered by Codex Action
Consolidating all information for this issue, as well as what was done locally on my machine to produce a patched copy of the desktop app that resolves the system-wide performance impacts. Additional information can likely be found here that is not in existing issues, including direct cause info beyond just describing the issue itself. I have created this issue in the hope that someone at OpenAI will see this, see all of the associated issues that have been reported, all of the information dropped here including the literal "fix" I'm currently using, and will actually do something about it.
There have been multiple versions now, and this has been happening for months. I very much just want to get this resolved.
Same issue on my side, although WMI is no longer observed in task manager to be utilizing a very high percentage of CPU, severe system-wide stalls are still happening when codex is running tasks. It would cause every other program I have running (e.g. Google Chrome) to become unresponsive, and even the ChatGPT app itself. As a result of such, I am unable to use my computer at all when codex is running a task. Consequently, Codex also takes significantly longer to run scientific simulation tasks due to the system-wide stalls.
Confirmed again on package
26.727.6591.0This is still present in the current Microsoft Store/MSIX package on Windows.
Environment
OpenAI.Codex_26.727.6591.0_x64Observed process creation
During a 45-second capture, Codex launched these short-lived commands:
powershell.exe -NoProfile -NonInteractive -CommandcontainingGet-CimInstance Win32_PerfFormattedData_PerfProc_ProcessplusWin32_Processto collect CPU, command line, working set, and process age.Get-CimInstance Win32_Process | Select-Object ProcessId,ParentProcessId | ConvertTo-Jsonto reconstruct the process tree.The effective cadence was approximately one new PowerShell process every 1–1.5 seconds while the relevant task/process UI was visible. This creates continuous process startup, WMI/CIM, JSON serialization, console-host, and teardown work.
Current package source confirmation
Read-only inspection of the packaged
resources/app.asarconfirms that the Windows implementation still hard-codes:The implementation selects this path using
process.platform === "win32"; the non-Windows branch usesps. Therefore changing the configured terminal from PowerShell to Git Bash, or changing theSHELLenvironment variable, does not affect this polling path.The packaged UI call sites also still configure both process queries at a one-second interval:
This explains why keeping the task summary/background-process or process-manager UI visible can maintain the polling loop. Hiding that UI appears to be only a partial workaround; it is not a supported global disable switch.
Resource impact
In the same affected installation, accumulated
codex-command-runnerandnode_replprocesses were also observed. Terminating the stale processes released approximately 10.8 GB of committed memory. That retention may be a separate lifecycle bug, but it makes the repeated process-enumeration workload substantially more expensive and can push the machine toward a system-wide stall.Requested fix / temporary mitigation
Please either:
A prompt,
AGENTS.md, terminal-shell setting, orSHELLoverride cannot mitigate this because the Desktop bundle invokespowershell.exedirectly.Reproduced on a newer Windows Desktop build: 26.727.6591.0 (Microsoft Store, x64), on 2026-08-03.
This reproduction matches the full-process PowerShell/WMI sampler path described here.
Observed behavior
The app repeatedly launched:
The second query selected process metadata including
ProcessId,ParentProcessId,CommandLine,WorkingSetSize, CPU percentage, and process age.Local app-bundle inspection mapped the command to:
.vite/build/child-process-snapshot-worker.jselectron-samplerchild-process snapshot pathMeasurements
Win32_ProcesssnapshotsWin32_ProcessenumerationsWmiPrvSE.exehostingCIMWin32/cimwin32.dll0x80041032and0x800706BA("Could not send status to client"), plus memory-quota throttling messagesThe PowerShell clients explicitly used
-NoProfile, ruling out the user's PowerShell profile as the source.This looks like the sampler requests overlapping or retrying after WMI slows, creating positive feedback: short-lived clients exit or time out while
CIMWin32continues processing increasingly expensive snapshots.No username, repository path, session transcript, or raw logs are attached here. A sanitized event summary can be provided if maintainers need more detail.
thanks for the detailed reports and investigation here: they were really helpful 💖
26.730.7989.0that address some major sources of powershell/wmi stormstaskkill.execan still be started by other process-cleanup paths, and we’re continuing to work on reducing that separatelyif you’re still seeing sustained wmi cpu usage or system-wide lag after
26.730.7989.0, please share an updated/feedbackidAdditional Windows kernel paged-pool / Token evidence on
26.707.3748.0I reproduced the same Desktop-generated Git and PowerShell/WMI process churn on Windows 11 25H2 (Build 26200.8875), and captured a fresh 20-minute elevated Xperf trace with
POOLallocation/free stack walking after a reboot.Environment:
OpenAI.Codex_26.707.3748.0_x64ChatGPT.exeProcess-tree results:
git.exestarts (~607.5/min)conhost.exestarts (~327.2/min)git ... rev-parse --show-toplevelgit config --null --get core.fsmonitorChatGPT.exe -> git.exestartsWin32_PerfFormattedData_PerfProc_ProcessplusWin32_ProcessWin32_ProcessKernel pool/Token results:
Toke: 1,049,024,256 bytes (1,000.427 MiB)Toke: 1,050,068,096 bytes (1,001.423 MiB)Tokeallocation difference: approximately 585,000 objectsTokeobject count)Toke+SeAt+SeTd+SeDtduring the windowSepDuplicateToken -> SepCreateClientSecurityEx / SeCreateClientSecurity -> ALPC/RPC -> fastprox.dll / wbemcore.dllSeSubProcessToken -> PspInitializeProcessSecurity -> NtCreateUserProcesswas also present.A system-wide Token-handle census shows that the roughly 585k
Tokeobjects are overwhelmingly held through kernel references/security contexts rather than ordinary user-mode Token handles. This supplies a kernel-memory impact mechanism in addition to the CPU/input-lag reports: sustained Desktop-generated process, ALPC/RPC, and WMI churn can accumulate approximately 1 GiB ofTokepaged pool after boot on this system.Other-source cross-checks:
The 2.3 GiB ETL contains local paths and command lines, so I am not attaching it publicly. I can provide a sanitized report or an ETL through a private OpenAI upload channel if maintainers need it.
I see the maintainer note that major WMI sources were addressed in
26.730.7989.0. I will retest this same PoolMon/Xperf workflow after that build is available on this device, with particular attention to whether the Git-origin storm and long-termTokeaccumulation are also reduced.the powershell/wmi process-snapshot issue here was addressed in
26.730.7989.0and is tracked in #25453the separate runaway
git.exelaunches and kernel token/paged-pool growth are tracked in #30926The current version on Windows (updated a few minutes ago) seems to be
26.730.61639according to the app's "About" popup. Was the patch not released yet? Still hitting the same issues with the most recent update as of this morning with severe system-wide performance impact the moment it's opened.@Sceleratis sorry for the confusion, we use different version numbers for the msix. you're on the latest version; mind submitting another feedback ID?
I found it may be caused by the remote connection. I can still reproduce it after running more than 24 hours remotely.