Over the course of the last year I have been tasked with analyzing our production environments, specifically looking at performances issues, hangs and crash analysis using the Debug Diagnostic Tool, Performance Monitor and Debugging Tools for Windows (WinDbg).
WinDbg is an ancient and primordial tool of the Windows ecosystem, it is one of the oldest native debuggers I am aware of. Its age means that it really does not know, in a direct way, what the more modern .NET is or even does. In order for WinDbg to be able to give meaningful information about the .NET framework and how objects are collected and released we need to load a couple of extensions.
- Open WinDbg as an Administrator.
- Hit CTRL-D and navigate to your hang dump to load it into WinDbg.
- Load the .NET 4 managed (as appropriate) code extension and SOS extension with the following commands:
- .load psscor4
- .loadby sos clr
After loading these extension you now have access to commands that will allow you to analyze the hang dump. Here are the basic commands I tend to use for high memory, high CPU/hangs, and app crashes.
WinDbg - High memory scenarios
eeheap will shows information on the memory heaps used by GC. It will display a heap info for each logical processor, so if you have hyper threading on a dual core machine you would see four heaps.
What objects are consuming the memory, that have not been collected, first column output is the method table which is an index to the type of object.
!dumpheap –mt methodtable
Dumps out a list of all objects of that type (based on method table, first column output is the address.
A short cut for !dumpobj and shows properties of the specific objects including the objects value.
Converts the value into a readable output.
This command detects which objects reference this address. Useful for tracking down what might have a reference to stubborn objects.
WinDbg - Hangs and Performance Issues
This command shows CPU Usage percentages, be careful using this on multi use boxes, CPU is a function of the is CPU if this is not a dedicated box.
This extension display information about the time consumed by each thread. Very useful if you want to know if a specific thread is consuming way more time than other threads.
~* e !ClrStack
This command sequence is designed to show the .NET call stack for all threads
Tells us how many threads are waiting for a lock MonitorHeld. This can be important for threads that are blocked, it is important to remember that it only covers .NET locks.
Shows all the locks that have no conflicts.
WinDbg – Crash scenarios
Display exception information with the verbose switch gives as much information as possible.
Dumps all the available exceptions.
A few other useful WinDbg commands
~ 13 s
Set the current context to the thread id of 13.
Show the .NET stack for current thread context
Dumps the HttpContexts found on thread and lists the URI in various states of request and response.
Gives a list of objects stored in your web cache
Having the tools and commands is one thing, understanding context is a whole other question, if you need help with that I would strongly recommend visiting the blog of Tess Fernandez. A few years back she produced a legendary series of detailed hang analysis articles that remain wholly relevant today.