Skip to content

Commit

Permalink
[analyzer] Clear watcher subscriptions to avoid leaking package:watch…
Browse files Browse the repository at this point in the history
…er data

Analyzer adds watchers to all root folders it has opened.
When editing, say, a pubspec.yaml file it ~starts over, cancels the
old subscriptions and creates new ones. It keeps references to the old
subscriptions too though.

This in turn leaks data.

On Linux internally in package:watcher it clears some stuff as it's
cancelled, but it doesn't on Windows, nor on Mac.

The means it can leak an infinite amount of `_Entry` classes,
and for instance in #52447 a
user has 40+ million of those classes.

Reproducing this I got to 40+ million too, at which point the
"Retained size" of all the `_Entry` objects was 7.39GB.

This fixes the leak by clearing the list.

Change-Id: I718e8edc81b763b66affa16c3b3f6d4b8a97fd1e
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/308940
Reviewed-by: Konstantin Shcheglov <[email protected]>
Reviewed-by: Brian Wilkerson <[email protected]>
Commit-Queue: Jens Johansen <[email protected]>
  • Loading branch information
jensjoha authored and Commit Queue committed Jun 13, 2023
1 parent 6bdb88b commit 5aee0f6
Showing 1 changed file with 5 additions and 3 deletions.
8 changes: 5 additions & 3 deletions pkg/analysis_server/lib/src/context_manager.dart
Original file line number Diff line number Diff line change
Expand Up @@ -734,11 +734,13 @@ class ContextManagerImpl implements ContextManager {
}

Future<void> _destroyAnalysisContexts() async {
for (final subscription in watcherSubscriptions) {
await subscription.cancel();
}
watcherSubscriptions.clear();

final collection = _collection;
if (collection != null) {
for (final subscription in watcherSubscriptions) {
await subscription.cancel();
}
for (final analysisContext in collection.contexts) {
_destroyAnalysisContext(analysisContext);
}
Expand Down

0 comments on commit 5aee0f6

Please sign in to comment.