Skip to main content

.Net Garbage Collection and Finalization Queue

Finalize is a special method that is automatically called by the garbage collector (GC) before the object is collected. This method is only called by the GC. Destructor in C# are automatically translated into Finalize. You can see the IL code using IDASM where you will see that destructor is renamed to finalize.

  1. public class A
  2. {
  3. ~A()
  4. {
  5. Console.WriteLine("Class A Destructor");
  6. //Clean up unmanaged resources here
  7. }
  8. }
The CLR translate the above C# destructor to like this:
  1. public override void Finalize()
  2. {
  3. try
  4. {
  5. Console.WriteLine("Class A Destructor");
  6. //Clean up unmanaged resources here
  7. }
  8. finally
  9. {
  10. base.Finalize();
  11. }
  12. }

Fundamental of Finalization

When a new object is created, the memory is allocated in the managed heap. If newly created object have a Finalize() method or a destructor then a pointer pointing to that object is put into the finalization queue. Basically, finalization queue is an internal data structure that is controlled and managed by the GC. Hence each pointer in finalization queue points to an object that have its Finalize method call before the memory is reclaimed.
In the below fig. the managed heap contains 10 objects and objects 2,3,5,6,and 10 also contains the Finalize method. Hence pointers to these objects were added to the finalization queue.
When the garbage collector starts go through the roots, it make a graph of all the objects reachable from the roots. The below fig. shows a heap with allocated objects. In this heap the application roots directly refer to the objects 1,3,4,6 and object 3 & 6 refers to the objects 8 & 10. Hence all these objects will become the part of the live objects graph.
The objects which are not reachable from application's roots, are considered as garbage since these are not accessible by the application. In above heap objects 2,5,7,9 will be considered as dead objects.
Before the collections for dead objects, the garbage collector looks into the finalization queue for pointers identifies these objects. If the pointer found, then the pointer is flushed from the finalization queue and append to the freachable queue .The freachable queue is also an internal data structure and controlled by the garbage collector. Now each and every pointer with in the freachable queue will identify an object that is ready to have its Finalize method called.
After the collection, the managed heap looks like below Fig. Here, you see that the memory occupied by objects 7 and 9 has been reclaimed because these objects did not have a Finalize method. However, the memory occupied by objects 2 and 5 could not be reclaimed because their Finalize method has not been called yet.
When an object's pointer entry move from the finalization queue to the freachable queue, the object is not considered garbage and its memory is not reclaimed. There is a special run-time thread that is dedicated for calling Finalize methods. When there is no entry in the freachable queue then this thread sleeps. But when there is entry in the freachable queue, this thread wakes and removes each entry from the queue by calling each object's Finalize method.
The next time the garbage collector is invoked, it sees that the finalized objects are truly garbage, since the application's roots don't point to it and the freachable queue no longer points to it. Now the memory for the object is simply reclaimed.

Note

  1. The two GCs are required to reclaim memory used by objects that have Finalize method.

Comments

Popular posts from this blog

Accessing File Stored in Windows Azure Blob Storage Using jQuery

Did you know it was possible to access the Windows Azure Blob Storage directly from JavaScript, for example using jQuery? At first, it sounds obvious, since Blobs are after all accessible from a public UR. But in practice, there is a very big hurdle: the Web browser’s Same Origine Policy or SOP, that restricts JavaScript code to accessing resources originating from the same site the script was loaded from. This means that you will never be able to load a Windows Azure Blob using XMLHttpRequest for example! Fortunately, there is a popular workaround called JSONP (“JSON with Padding”). The idea behind this technique is that the script tag is not submitted to the SOP: an HTML page can thus load a JavaScript file from any site. So, if you expose your data in an “executable” form in JavaScript, a page will be able to load this data using a script tag. For example: <script type=”text/javascript” src=”http://www.sandeepknarware.in/exemple.jsonp”> </script> But how can ...

Support for debugging lambda expressions with Visual Studio 2015

Anyone who uses LINQ (or lambdas in general) and the debugger will quickly discover the dreaded message “Expression cannot contain lambda expressions”. Lack of lambda support has been a limitation of the Visual Studio Debugger ever since Lambdas were added to C# and Visual Basic.  With visual studio 2015 Microsoft has added support for debugging lambda expressions. Let’s first look at an example, and then I’ll walk you through current limitations. Example To try this yourself, create a new C# Console app with this code: using System.Diagnostics; using System.Linq; class Program { static void Main() { float[] values = Enumerable.Range(0, 100).Select(i => (float)i / 10).ToArray(); Debugger.Break(); } } Then compile, start debugging, and add “values.Where(v => (int)v == 3).ToArray()” in the Watch window. You’ll be happy to see the same as what the screenshot above shows you. I am using Visual Studio 2015 Preview and it has some limitati...

gcAllowVeryLargeObjects Element

There are numerous new features coming with .NET 4.5 and here, on this blog, you can find several posts about it. But the feature we are goint to talk about today is very exciting, because we were waiting for it more than 10 years. Since .NET 1.0 the memory limit of .NET object is 2GB. This means you cannot for example create array which contains elements with more than 2GB in total. If try to create such array, you will get the OutOfMemoryException. Let’s see an example how to produce OutOfMemoryException. Before that Open Visual Studio 2012, and create C# Console Application, like picture below. First lets create simple struct with two double members like example below: 1 2 3 4 5 6 7 8 9 10 11 12 public struct ComplexNumber {      public double Re;      public double Im;      public ComplexNumber( double re, double im)      {    ...