-
-
Notifications
You must be signed in to change notification settings - Fork 837
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
FIX Memory leak in DefaultRegisteredServicesTracker
#1423
FIX Memory leak in DefaultRegisteredServicesTracker
#1423
Conversation
…s if left undisposed. The latter is also more performant.
Codecov ReportAll modified and coverable lines are covered by tests ✅
Additional details and impacted files@@ Coverage Diff @@
## develop #1423 +/- ##
===========================================
- Coverage 78.57% 78.56% -0.02%
===========================================
Files 200 200
Lines 5713 5709 -4
Branches 1168 1168
===========================================
- Hits 4489 4485 -4
Misses 712 712
Partials 512 512 ☔ View full report in Codecov by Sentry. |
Thanks; can you please run our benchmarks for a comparison here, particularly the ones that touch on child unit-of-work scopes with their own dependencies? I'm thinking at least ChildScopeResolveBenchmark and ConcurrencyNestedScopeBenchmark. These sort of collection changes can have unintended perf implications. |
In the test environment we are very active in creating containers and child containers. We have found a memory leak. A lot of objects can't be GC'ed because the are active reference from ConcurrentBag internal structures (it store data in buckets in thread local storage). So eventually all IComponentRegistration will be gc rooted to static thread local. ClearRegistrations wont help much. Just one non-disposed container or child container (which can happens in real world full of bugs) can create a fake gc root for all ConcurrentBag instances. For me, having ConcurrentBag holding IComponentRegistration, that can hold anything in my app is already a performance bug. We will make bench for sure, when we finished local testing in our env. |
Yes, sure thing. Here you are:
ChildScopeResolveBenchmark
ConcurrencyBenchmark
ConcurrencyNestedScopeBenchmark
DeepGraphResolveBenchmark
RootContainerResolveBenchmark
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Great, thanks, sorry for the delay!
This change actually reverses the order of the Registrations collection unfortunately. However unless somebody depends on that it should be safe. |
It was a concurrentbag before right? Which is already technically an unordered set I believe. |
Yes, you are right, but in fact they are selected in reverse order of inserts. So in our case this fact helped to reveal some corner cases of duplicate registrations with different configs, for example. Some unit tests were failing because of that. It's not an issue I believe, but who knows how others are using this interface. |
ConcurrentBag
withConcurrentQueue
. It's causing memory leaks if left undisposed somewhere.ClearRegistrations
is not necessary anymore.List.Insert(0,...)
and.ToList()
calls