Search code examples
c#garbage-collectionprofiler

What is the Visual Studio Performance Profiler "Force GC" button actually doing?


I am trying to track down memory leaks in my application using the Visual Studio Performance Profiler

I use the profiler to:

  1. carry out actions
  2. Snapshot
  3. Force GC
  4. snapshot again

And I see all my object garbage collected correctly.

enter image description here

I do the same thing but using my application:

  1. carry out actions
  2. Snapshot
  3. Force GC at runtime using the code:

    GC.Collect(); GC.WaitForPendingFinalizers(); GC.Collect();

  4. snapshot again

But this time the objects are not collected and are still in memory.

So what is the difference between the Force GC button and the code GC.Collect() that I'm calling?


Solution

  • So Thanks to @Lass V. Karlsen for pointing me in the right direction with this comment: What is the Visual Studio Performance Profiler "Force GC" button actually doing?

    It was completely obvious when I think about it.

    My Page was disposing of itself and in the Dispose method I as calling:

    GC.Collect();
    GC.WaitForPendingFinalizers();
    GC.Collect();
    

    and of course because the page was still alive at that point it wasn't being garbage collected.

    My solution was to do the following instead:

    #if DEBUG
         Task.Run(async () =>
         {
             await Task.Delay(500);                   
             GC.Collect();
             GC.WaitForPendingFinalizers();
             GC.Collect();
         });
    #endif
    

    Notice I've wrapped it with a DEBUG compiler directive as I don't think this is the advised way of doing it, but for the purpose of hunting memory leaks it works well