How To Tell Which GC Mode Your Application Is Using


I posted previously about how to set the GC mode your application.  So now that you’re running your app, how do you know it’s running in that GC mode?

If you’re using v1.0 or v1.1, the CLR loads a different dll based on which GC mode (mscorwks.dll for workstation, mscorsvr.dll for server).  You can use tasklist.exe (ships with Windows XP and up) or tlist.exe (ships with Windows Debugging Tools) to determine which processes are using which dll.  To list all the applications running with server GC:

   tasklist /m mscorsvr.dll
   or 
   tlist /m mscorsvr.dll

In Whidbey, we’ve condensed all the GC code into one library: mscorwks.dll.  This means that all managed applications load mscorwks.dll, making the old method useless.  Luckily we have two new ways to determine the GC mode:

System.Runtime.GCSettings.IsServerGC will return true if we’re in server GC mode, and false if in workstation.  Note, this API is in a different location from Whidbey Beta 1.

The other way is using SOS, the debugger extension to WinDBG and Visual Studio.  When your assembly is running, you can query the GC mode with:

   !EEVersion

One thing to note is that this will only return the GC mode and the number of heaps after the heap (or heaps) has been initialized.

Comments (8)

  1. B. Honeydew says:

    Until Whidbey how about P/Invoking GetModuleHandle for "mscorsvr.dll" or "mscorwks.dll"

  2. Chris says:

    Sure, any method that gives the currently loaded modules will work.

  3. Is there a way to tell if you are using the concurrent version of the workstation GC?

  4. clyon says:

    Anthony,

    No, there is no way to tell directly.

    Concurrent is enable dby default on WorkStation

    and disabled by default on Server GC.  

    Also, you can check the app config file to see if concurrent is explicitly disabled.

    Is there a particular reason why you need to know, or just curious?

  5. Just curious actually — and I like to verify things.  I am a bit surprised that concurrent is the default workstation mode, because I thought the default was for the GC to run on the main thread.

    Am I correct in my understanding that with concurrent GC (whether on single or multi proc) the GC runs on a separate thread?

  6. clyon says:

    Concurrent GC runs on a different thread, but it behaves differently than workstation (and doesn’t run all the time).

    Maoni has a great explanation here:

    http://blogs.msdn.com/maoni/archive/2004/09/25/234273.aspx

    Hope that helps!

  7. Yes, that did help!  In fact, the answer is that, for an app running with the default concurrent workstation GC, the Gen0 and Gen1 collections will take place on the main app thread, suspending the thread while the GC takes place.  This is because those collections are pretty quick.

    But when a Gen2 collection takes place, the CLR will fire up a background thread to do that and only suspend the main thread for as little time as possilbe.  This is best for UI apps, where you want the interface to remain as responsive as possible.