0

I'm dealing with my C# program memory usage I set up a memory control between the start and the end of my app to spot memory leaks. I got warning when using Entity Framework 6 with Firebird:

var m = GC.GetTotalMemory(true) / 1024 / 1024; // 2MB using (Entities context = new Entities(ConnectionString)) { m = GC.GetTotalMemory(true) / 1024 / 1024; //2MB context.MYTABLE.FirstOrDefault(); m = GC.GetTotalMemory(true) / 1024 / 1024; // 5MB } m = GC.GetTotalMemory(true) / 1024 / 1024; // 5MB ?? 

By commenting out the context.MYTABLE line, memory will remain at 2MB.

I know everything will be disposed when the application will end, but I would like to detect memory leaks on my objects and this EF problem prevent that.

Is there a way to dispose this extra memory used by EF?

Could this problem be caused by the Firebird EF driver?

Tia

6
  • It makes no much sense to measure the memory used by a small block of code in a world where you don't control memory allocation and deallocation in fine details. EF keeps things in memory to speed up things and you better don't try to play with that Commented Sep 10, 2017 at 7:57
  • Are you running Debug or Release build? Commented Sep 10, 2017 at 9:46
  • 1
    Did you try measuring the same code second, third etc. time? Because the very first time EF builds and caches the metadata model. Commented Sep 10, 2017 at 15:25
  • @mjwills, in debug mode Commented Sep 10, 2017 at 17:00
  • 2
    It's cached statically once per DbContext type and cannot be released (as usual with static variables). Commented Sep 10, 2017 at 17:13

2 Answers 2

3

There is no reason for the garbage collector to run after you exit the using block (using only guarantees that the Dispose method of context will be called). You can force a garbage collection using GC.Collect().

More generally, entities that are loaded using EF will generally live as long as the context they are associated with, unless you manually remove them from the context.

I cannot speak to a memory leak in the Firebird driver for EF, but what you are seeing is expected begaviour.

Sign up to request clarification or add additional context in comments.

1 Comment

GetTotalMemory(true) is supposed to do a GC.Collect. Explicitly adding the collect does not change anything.
0

Is there a way to dispose this extra memory used by EF?

No - there is no way to release that extra memory in a guaranteed way.

The documentation for GetTotalMemory(true) states:

Remarks If the forceFullCollection parameter is true, this method waits a short interval before returning while the system collects garbage and finalizes objects. The duration of the interval is an internally specified limit determined by the number of garbage collection cycles completed and the change in the amount of memory recovered between cycles. The garbage collector does not guarantee that all inaccessible memory is collected.

Note in particular the last sentence:

The garbage collector does not guarantee that all inaccessible memory is collected.

On top of this, Entity Framework (and / or Firebird driver) is likely keeping some information cached in RAM for the lifetime of the application. And some of that will likely never be GCed.

1 Comment

Thanks. I included the extra memory into my memory leaks detection.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.