在.Net生产应用程序中诊断CPU失控 [英] Diagnosing runaway CPU in a .Net production application

查看:100
本文介绍了在.Net生产应用程序中诊断CPU失控的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有人知道有什么工具可以帮助我找出为什么,我们在托管应用中看到CPU失控吗?



我做什么是不是在寻找:




    • 使用CLR分析(也称为ICorProfiler API)

    • 使用CLR调试(又名ICorDebug API)


    生产中有什么更好的方法?


    CLR调试API具有非常重要的作用相较于概要分析的优点,它们使您可以附加到运行过程。诊断生产中的性能问题时,这可能至关重要。在应用程序使用几天后,由于某些意外的代码执行分支,经常会弹出CPU失控状态。在那个时间点,重新启动应用程序(以便对其进行配置)是不可行的。


    cpu-analyzer.exe


    所以,我编写了一个没有安装程序的小工具,并使用ICorDebug执行上述基本解决方案。它基于 mdbg源合并而成


    它以可配置的时间间隔(默认为1000毫秒)为所有托管线程获取可配置(默认为10)个堆栈跟踪。 $ b

    这是示例输出:

     
    C:\> cpu-analyzer.exe evilapp
    ------ ------------------------------
    4948
    内核时间:0用户时间:89856576
    EvilApp.Program.MisterEvil
    EvilApp.Program.b__0
    System.Threading.ExecutionContext.Run
    System.Threading._ThreadPoolWaitCallback.PerformWaitCallbackInternal
    System.Threading._ThreadPoolWaitCallback.PerformWaitCallback

    ...省略更多数据...

    随意试用一下该工具。可以从我的网站上下载。博客


    编辑


    这是一个线程,显示了我如何使用cpu-analyzer来诊断此类问题生产应用。


    Does anyone know of a tool that can help me figure out why we are seeing runaway CPU in a managed app?

    What I am not looking for:

    1. Process explorer, it has this awesome feature that lets you see CPU per thread, but you do not get managed stack traces. Also, it requires a fairly proficient user.

    2. Windbg + SOS, it could probably be used to figure out what is going on, by grabbing a bunch of dumps. But it is non-trivial to automate and a bit to heavy for this.

    3. Fully fledged profiler (like dottrace or redgate), licensing is complex and the tool is an overkill which requires a reasonably heavy install.

    What I am looking for:

    1. A simple exe (with no installer) I can send to a customer. After they run it for 10 minutes, it generates a file that they send to me. The file contains details on the threads that consumed the most CPU and their stack traces during that time.

    Technically I know that a tool like this can be created (using ICorDebug), but do not want to invest any time if such a tool already exists.

    So, anyone know of anything like this?

    解决方案

    The basic solution

    1. Grab managed stack traces of each managed thread.
    2. Grab basic thread statistics for each managed thread (user mode and kernel time)
    3. Wait a bit
    4. Repeat (1-3)
    5. Analyze the results and find the threads consuming the largest amount of cpu usage, present the stack traces of those threads to the user.

    Managed Vs. Unmanged Stack Traces

    There is a big difference between managed and unmanged stack traces. Managed stack traces contain information about actual .Net calls whereas unmanaged ones contain a list of unmanaged function pointers. Since .Net is jitted the addressed of the unmanaged function pointers are of little use when diagnosing a problem with managed applications.

    How do you get an unmanaged stack trace for an arbitrary .Net process?

    There are two ways you could get managed stack traces for an managed application.

    • Use CLR profiling (aka. ICorProfiler API)
    • Use CLR Debugging (aka. ICorDebug API)

    What is better in production?

    The CLR Debugging APIs have a very important advantage over the profiling ones, they allow you to attach to a running process. This can be critical when diagnosing performance issues in production. Quite often runaway CPU pops up after days of application use due to some unexpected branch of code executing. At that point of time restarting the app (in order to profile it) is not an option.

    cpu-analyzer.exe

    So, I wrote a little tool that has no-installer and performs the basic solution above using ICorDebug. Its based off the mdbg source which is all merged into a single exe.

    It takes a configurable (default is 10) number of stack traces for all managed threads, at a configurable interval (default is 1000ms).

    Here is a sample output:

    C:\>cpu-analyzer.exe evilapp
    ------------------------------------
    4948
    Kernel Time: 0 User Time: 89856576
    EvilApp.Program.MisterEvil
    EvilApp.Program.b__0
    System.Threading.ExecutionContext.Run
    System.Threading._ThreadPoolWaitCallback.PerformWaitCallbackInternal
    System.Threading._ThreadPoolWaitCallback.PerformWaitCallback
    
    ... more data omitted ...
    

    Feel free to give the tool a shot. It can be downloaded from my blog.

    EDIT

    Here is a thread showing how I use cpu-analyzer to diagnose such an issue in a production app.

    这篇关于在.Net生产应用程序中诊断CPU失控的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆