使用WinDug工具调试c#程序或c++程序的dmp崩溃文件,调试内存泄漏

1.调试c#程序内存泄漏步骤

  1. 设置symbol符号路径: SRV*c:\mysymbol* http://msdl.microsoft.com/download/symbols;d:/你的pdb文件路径  然后保存工作空间
  2. 加载dmp文件。
  3. 加载sos文件  
    .load C:\Windows\Microsoft.NET\Framework\v2.0.50727\sos
    
  4.  加载clr
    .loadby sos clr
    .load clr
  5. 加载堆
    !dumpheap –stat 
    
  6. 根据堆的大小,判断是哪种类型的文件占用内存比较高
    !dumpheap -type System.Double[]
    
  7. 调试相关的地址,找到调用堆栈
    > !gcroot 31daa0d0 
    

2.调试c++代码的内存泄漏

  1. 跟c#的前两步骤一样,加载文件
  2. 获取堆的概述信息,s的意思是summery
    !heap –s    
    

      会得到下列数据:

    Heap Flags Reserv Commit Virt Free List UCR Virt Lock Fast
    (k) (k) (k) (k) length blocks cont. heap
    00130000 08000002 97344 97296 97344 278 626 10 13 e

  3. 比如程序会增长内存,那么堆的大小一般情况下会变大。这时候过几分钟或过几秒,再进行一下第二步,比较两次得到的信息,比较后找到有异常的项。 找到符合条件的特殊的堆代号,然后统计这个堆的句柄。stat是统计statistic的意思,h意思是handle。
    !heap –stat –h 00130000  
    

      

    size #blocks total ( %) (percent of total busy bytes)
    800 2cce0 - 16670000 (75.42)
    200 2cce1 - 599c200 (18.86)
    98 2ccdf - 1a9a468 (5.60)

  4. 根据第三步的结果,会看到一个百分比列表,找到你认为不正常的数据,比如第一个,大小为800字节,块有2cce0个,总大小为16M,这个时候用过滤的方法,过滤大小为800的句柄。flt意思是filter过滤,s意思是size
    !heap -flt s 800 
    

      

    HEAP_ENTRY Size Prev Flags UserPtr UserSize - state
    60b79f8 0103 0000 [00] 060b7a10 00800 - (busy)
    mscoreei!_iob
    060ba168 0103 0103 [00] 060ba180 00800 - (busy)

  5. 第四步会得到很多的信息,随便找一条试试,找到userPtr那一列,即用户指针。然后获取这个指针的所有信息。PageHeapOptions all information。如果找不到就换一条试试。一般情况下很容易找的。
    !heap -p -a 060b7a10 
    

      

    MyTestD!MyTest::Dosomething+0x000000c6 
  6. 第五步如果顺利的话,就可以看到一些方法了,然后就可以根据方法的全名去查看线程了
    u MyTestD!MyTest::Dosomething+0x000000c6
  7. 第六步如果顺利的话就找到了基本的代码行数和对应的位置了

猜你喜欢

转载自www.cnblogs.com/chlm/p/9439348.html