Skip to content

[Bug]: Project search on Windows fails for minutes after every Defender definition update: the content index takes 3.6 min to build for this repo (7 s in WSL, 2.4 s for git grep) #37086

Closed

Description

@juliusmarminge

Problem

On Windows with Microsoft Defender at its default settings, project search (Ctrl+Shift+F) does not work for the first several minutes in a repository of ordinary size, and that repeats after every Defender definition update and in every new clone or worktree.

The first search waits 16 s and then shows "Failed to search workspace contents in ''." Every further search fails within 10 ms. On this repository (32,281 files, 378 MB of working tree) the content index needs 3.6 minutes to build the first time, because Defender scans each file the first time the server reads it; the server gives the build 15 seconds. The same build takes 7 s in WSL on the same machine, 1.9 s with Defender's real-time scanning off, and git grep answers the same query over the same working tree in 2.4 s with Defender on.

Steps to reproduce

  1. Windows with Defender real-time protection on and no exclusion for the project folder.
  2. Clone a repository with a few thousand files or more (I used this repository) and add it as a project on the Windows backend.
  3. Open a thread, press Ctrl+Shift+F and type a word that occurs in the code.
  4. After about 16 s the dialog shows "Failed to search workspace contents". Try again every 30 s.

To repeat it on a repository that already works, run Update-MpSignature in an elevated PowerShell (Defender does this on its own several times a day) and search again.

Numbers

Windows Server 2025, 4 vCPU (Xeon Platinum 8473C), 16 GB, NTFS, Node 26.13.1, Git for Windows 2.56.1, commit a62bc81. The Linux baseline is WSL2 Ubuntu 24.04 (ext4) on the same machine. Defender CPU is the processor time of MsMpEng.exe during the build.

Time for the content index to become ready, created the way the server creates it (FileFinder.create({ basePath, disableMmapCache: true, disableContentIndexing: false, aiMode: false }), then waitForIndexReady), on this repository:

Where First build Built again straight away
Windows, fresh clone, Defender default 221.7 s (Defender CPU 436 s) 2.6 s
Windows, an older clone whose files had not been read yet 175.8 s 2.6 s
Windows, same clone after Update-MpSignature 218.5 s (Defender CPU 432 s) 2.9 s
Windows, fresh clone, real-time scanning off 1.9 s 1.7 s
Windows, fresh clone, folder in Defender's exclusions 7.0 s 2.4 s
WSL, same repository 6.9 s 0.7 to 0.8 s

Smaller trees on a second machine of the same kind, fresh copies, Defender default: 2,043 files (29 MB) 10.8 s; 1,640 files 8.9 s; 1,373 files 7.2 s. That is about 5 ms per file, so roughly 2,800 files are enough to pass the 15 s limit.

The cost is Defender scanning files on their first read by the server process, not the index library. After resetting Defender's cache each time:

Reading the same 32,321 files Time Defender CPU
Content index build 212.9 s 415 s
Plain fs.readFile from Node, 8 at a time 127.3 s 482 s
The same Node reads a second time 2.1 s 1.4 s
git grep -l "bench edit" (text that exists only in uncommitted edits, 360 files matched) 2.4 s 1.6 s
git grep --untracked -l 2.5 s 1.1 s

Reads made by git.exe are not charged by Defender and do not warm its cache either: the Node read pass that ran straight after the git grep runs still took 127 s.

In the app (dev server from source, Windows backend, fresh clone, headless Chromium), one search attempt about every 33 s:

Result
This commit first attempt fails after 16.1 s; 13 further attempts through 450 s each fail in 0 to 10 ms
This commit, no attempts for 16.8 minutes after the first failure the next search answers in 4.2 s
With the server and web changes of #33138 applied attempts fail through 217 s; the attempt at 250 s answers in 294 ms
WSL backend, same repository first search answers in 2.1 s

The file picker (Ctrl+P) is not affected: its paths-only index is ready in 0.34 to 0.37 s on Windows.

Where it comes from

apps/server/src/workspace/WorkspaceSearchIndex.ts: the content variant builds an index that reads every file (createFinder, line 495) and make (line 546) fails with WorkspaceSearchIndexScanTimedOut when waitForIndexReady passes WORKSPACE_INDEX_SCAN_TIMEOUT (15 seconds, line 47). The failed entry stays in WorkspaceSearchIndexMap until it has been idle for 15 minutes, which is why retries fail instantly.

#33138 makes the search recover once the build finishes. It does not shorten the build, so with it a Windows user still has no project search for about four minutes after each definition update, with Defender using a full core or more for that time.

Expected

Project search on Windows answers in seconds on the first use in a repository, as it does in WSL, and does not stop working after a Defender definition update.

git grep shows this is reachable on the same machine with Defender on: 2.4 s for the first search over the same working tree, uncommitted and untracked files included.

Not covered

Whether a reboot alone resets Defender's cache was not measured.

Activity

  1. added
    bugSomething is broken or behaving incorrectly.
    needs-triageIssue needs maintainer review and initial categorization.
    on Nov 15, 2026
  2. juliusmarminge commented on Nov 15, 2026

    @juliusmarminge
    MemberAuthor

    One more data point: the shipped desktop build pays the same cost, so this is not specific to running the server from source under node.exe.

    Reading the same 32,321 files with plain fs.readFile under the desktop app's own binary (T3 Code (Nightly).exe 0.1.10-nightly.20261114.4709 with ELECTRON_RUN_AS_NODE=1, the way the app starts its server), straight after Defender's cache was reset: 127.9 s, Defender CPU 480 s. Under node.exe it was 127.3 s and 482 s. Both binaries are code-signed.

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

    bugSomething is broken or behaving incorrectly.needs-triageIssue needs maintainer review and initial categorization.

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions