getting visual studio ultimate “Debug Managed Memo

2019-09-02 18:22发布

问题:

Is it possible to obtain summary information for managed objects on the heap in WINDBG that's similar to the summary presented by Visual Studio Ultimate's 'Debug Managed Memory' option.

I can obtain some of the information, but it's on a case by case basis, and is quite tedious. Is there a macro or set of commands that can produce similar output using WINDBG?

Visual Studio seems to have a neat little routine where it collects all the roots and shows a summary of the root object classes and their total memory.

回答1:

Like for any .NET issue, you'll first need the SOS extension

.loadby sos clr; .loadby sos mscorwks

You can then get a list of objects using

!dumpheap -stat; * Statistics output, good if you don't know what you're looking for
!dumpheap -type <SubstringOfClass>; * If you know what type you're after
!dumpheap -mt <MethodTable>; * If the class substring is not unique enough

To get the inclusive size, you can use

!objsize <address>

To find the root of an object, use

!gcroot <address>

Note that IMHO there is no convenient way of showing all root objects.

I'm not sure if Visual Studio lists objects on the stack. In WinDbg this would be

~*e !dso

Example walkthrough:

0:005> !dumpheap -stat
Statistics:
              MT    Count    TotalSize Class Name
000007fef2611ec8        1           24 System.Collections.Generic.ObjectEqualityComparer`1[[System.Runtime.Serialization.MemberHolder, mscorlib]]
...
000007fef2622968        1           64 System.BaseConfigHandler+CreateAttributeCallback
...
000007fef25fa690      396       117910 System.Byte[]
000007fef25a4458     1570       227560 System.Object[]
000007fef25f6508     3300       234762 System.String
Total 17883 objects

0:005> !dumpheap -stat -type Handler
Statistics:
              MT    Count    TotalSize Class Name
000007fef2622968        1           64 System.BaseConfigHandler+CreateAttributeCallback
000007fef26228b0        1           64 System.BaseConfigHandler+CreateNodeCallback
000007fef26227f8        1           64 System.BaseConfigHandler+ErrorCallback
Total 3 objects

0:005> !dumpheap -mt 000007fef2622968
         Address               MT     Size
0000000002594848 000007fef2622968       64     

Statistics:
              MT    Count    TotalSize Class Name
000007fef2622968        1           64 System.BaseConfigHandler+CreateAttributeCallback
Total 1 objects

0:005> !objsize 0000000002594848 
sizeof(0000000002594848) = 168728 (0x29318) bytes (System.BaseConfigHandler+CreateAttributeCallback)

0:005> !gcroot 0000000002594848 
Found 0 unique roots (run '!GCRoot -all' to see all roots).

0:005> !gcroot -all 0000000002594848 
Found 0 roots.

So it seems that this object has no more references and will be garbage collected during next GC.

0:001> !dso
OS Thread Id: 0xb2c (1)
RSP/REG          Object           Name
00000000024B0000 00000000024b1048 System.Exception


回答2:

These would get you the managed Memory, Heap Summary and Heap Consumption for specific types and just in case you are trying to find strings on the heap:

!EEHeap
!DumpHeap -stat 
!DumpHeap -strings 
!DumpHeap -Type <TypeSpec> 

This will let you have a bin file which can be used in CLRProfiler:

!traverseheap

For more refer to SOS Help. sosex is another extension but I not used it to debug leaks. CLRProfiler and Visual Studio Standalone Profiler are the best tools to debug these issues than Windbg IMHO.