zoukankan      html  css  js  c++  java
  • 使用PerfView诊断.Net GC的问题

    PerfView 概述:

    PerfView是一个可以帮助你分析CPU和内存问题的工具软件。它非常轻量级也不会入侵诊断的程序,在诊断过程中对诊断的程序影响甚微。

    Visual Studio自带的性能分析功能在CPU占用、时间消耗、内存分配等方面的诊断效果还算不错,但PerfView可以提供更加丰富的诊断分析信息。

    在这篇文章中,我将使用PerfView给你展现如下功能:

    • GC回收发生的频率以及回收所消耗的时间;
    • 获取导致Large object分配的原因;
    • 内存被谁占用了;
    • 对比哪个托管对象增大的最快。

    测试程序

    现在我们准备一个将会导致内存泄露的程序,用来确保使用PerfView可以达到我们所期望的效果。它是一个WinForm应用程序,后台代码如下:

        public partial class Form1 : Form
        {
            private List<int[]> arrays = new List<int[]>();
            Random random = new Random();
    
            public Form1()
            {
                InitializeComponent();
    
                Thread thread = new Thread(Start);
                thread.IsBackground = true;
                thread.Start();
            }
    
            private void Start(object obj)
            {
                while (true)
                {
                    int[] a = new int[random.Next(90000, 100000)];
                    arrays.Add(a);
                    Thread.Sleep(10);
                }
            }
        }

    使用PerfView进行跟踪

    开启PerfView,你将会看到如下窗口:

    PerfView的使用手册被集成在这个程序中,你可以菜单栏来进行访问。

    然后点击菜单“Collect-->Collect”来进行数据采集,用来分析生成诊断结果:

    无需修改任何初始化配置,点击“Start Collection”按钮,PerfView将会开始采集所有进程的事件数据。

    数十秒之后,你可以点击“Stop Collection”按钮,PerfView将会停止采集并生成诊断文件“PerfViewData.etl.zip”:

    获取GC Stats

    双击“GCStats”报表,将会弹出一个窗口,窗口中显示了每一个进程GC信息,找到我们的测试程序。

    关于测试程序我们将会得到如下汇总信息表:

    进一步往下看,还会显示GC触发的原因:

    如上图所示,这次GC的collection的发生是因为large object的分配。

    获取导致large object分配的原因

    从PerfView的主界面,双击打开“GC Heap Alloc Stacks”窗口,然后双击测试程序的进程,之后弹出的窗口将根据内存分配从大到小的次序显示堆栈信息:

    PerfView会将所有的large object分配都归类在LargeObject节点下面,双击该节点可以看到如下信息:

    备注:如果你在上图所示的界面中看到“OTHER<<clr?>>”,可以对其鼠标右击,然后点击“Lookup Symbols”,来获取CLR和Windows的功能名称。

    上图中主要列的说明如下:

    Inc%:表示该对象分配的字节占所有记录分配的百分比;

    Inc:该对象分配字节的总数;

    Inc Ct:该对象分配的次数。

    从上图可以看出,巨多的large object都是来自Start方法的Int32数组,PerView精确地诊断出我们预期的效果。

    谁造成了内存泄露

     PerfView可以通过heap dump来查看占用内存的对象的路径。

    从主界面点击菜单项“Memory-->Tale Heap Snapshot”,弹出窗口如下图所示:

    找到我们的测试程序并选中,然后点击“Dump GC Heap”按钮,数秒后再点击“CLose”按钮,最后会生成一个“.gcdump”文件。

    双击打开“WindowsFormsApplication1.gcdump”窗口,显示如下所示:

    PrefView精确地诊断出,是static variables占用了内存。

    使用两个Heap Dump来查看对象所占内存的变化情况

    在应用程序连续运行的情况下,对其进行两次Take Heap Sanpshot,确保两次生成的文件名称不一致。同时打开这两个.gcdump文件的窗口,通过任一一个窗口的diff菜单项功能,都能以另一个窗口的数据为基准进行对比。 

  • 相关阅读:
    KMP的next数组性质运用
    谁说前端不需要懂-Nginx反向代理与负载均衡
    Vue源码
    js学习网站
    CSS文本溢出显示省略号
    Js中带有小数的值相加产生的问题
    使用ueditor的时候,style样式传递到后台时被过滤没了
    实现div里的内容垂直居中
    安装sass报错
    js方法
  • 原文地址:https://www.cnblogs.com/lenshen/p/3961026.html
Copyright © 2011-2022 走看看