Skip to content

fix: use NonRecursive mode for individual file watchers (APP-4657)#12188

Draft
warp-dev-github-integration[bot] wants to merge 1 commit into
masterfrom
fix/inotify-recursive-watch-memory-APP-4657
Draft

fix: use NonRecursive mode for individual file watchers (APP-4657)#12188
warp-dev-github-integration[bot] wants to merge 1 commit into
masterfrom
fix/inotify-recursive-watch-memory-APP-4657

Conversation

@warp-dev-github-integration
Copy link
Copy Markdown

Description

Fix excessive memory usage from inotify recursive watch registration on Linux.

register_file_path() and fallback_to_individual_watchers() in warp_files/src/lib.rs were using RecursiveMode::Recursive with WatchFilter::accept_all() when falling back to individual file watchers. On Linux with inotify, this causes the notify crate to walk the entire directory tree and register a watch on every subdirectory. In large directory trees, this creates millions of PathBuf entries in the internal watches HashMap, consuming gigabytes of memory (observed 4.8 GB in Sentry heap profiles — 96.5% of sampled heap in notify::inotify::EventLoop::add_watch).

The fix aligns both code paths with the approach already used by open(), which watches the parent directory with NonRecursive mode. This is sufficient for detecting file changes while avoiding the explosive inotify watch growth. The unsubscribe() cleanup already expected parent-directory-based watching.

Linked Issue

APP-4657
Sentry Issue

Testing

  • Verified code compiles with cargo check -p warp_files
  • Verified clippy passes with cargo clippy -p warp_files -- -D warnings
  • I have manually tested my changes locally with ./script/run

Agent Mode

  • Warp Agent Mode - This PR was created via Warp's AI Agent Mode

Conversation: https://staging.warp.dev/conversation/322f80c3-3bfc-4435-92dc-497b389fbb70
Run: https://oz.staging.warp.dev/runs/019e91d1-786f-7cd1-8825-283b9314965b

This PR was generated with Oz.

register_file_path() and fallback_to_individual_watchers() were using
RecursiveMode::Recursive with WatchFilter::accept_all() when falling
back to individual file watchers. On Linux, this causes the inotify
backend to walk the entire directory tree and register a watch on every
subdirectory, which can consume gigabytes of memory in large trees
(observed 4.8 GB in heap profiles from Sentry).

The fix aligns both code paths with the approach already used by open(),
which watches the parent directory with NonRecursive mode. This is
sufficient for detecting file changes while avoiding the explosive
inotify watch growth.

Co-Authored-By: Oz <oz-agent@warp.dev>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant