c# – 检测/诊断线程饥饿

我正在对IIS应用程序进行一些性能/可伸缩性测试,这些测试偶尔似乎会减慢到生产中的爬行速度.我能够使用NUnit一致地重现慢度.

在测试期间或生产中发生缓慢时,cpu和内存不会出现峰值.我强烈怀疑应用程序正在遭受线程饥饿,因为它似乎不是导致瓶颈的cpu,内存,I / O或数据库访问.我确实看到了看似线索饥饿的迹象;例如,NLog的异步日志文件写入往往具有长时间的,随后是具有较旧时间戳的活动突发(即,较低优先级的线程正在等待线程释放以便写入).

我可以采取哪些步骤来明确确定应用程序确实是线程缺乏的,并且(假设是这种情况)确定导致问题的系统的确切区域?

编辑

我忽略了几乎所有的代码都是同步的(它是遗留系统).

解决方法

根据Sinatr的评论,我在ThreadPool.SetMinThreads和TaskCreationoptions.LongRunning上做了一些阅读,包括When to use TaskCreationOptions.LongRunning?的回答

将MinThreads设置为更高的认值会对我的情况产生巨大影响.我创建了一个简单的后台进程,以查看ThreadPool中的可用线程在测试运行过程中是否发生了显着变化,并且超过了MinThreads值(它是).

这是我用来诊断的一些代码.这不适用于生产用途,此处显示的线程使用情况报告只会在最初增加时才会引起注意.另请注意,Timer过去需要一个线程,因此还需要等待一个可用的线程.

静态变量:

private static Timer _timer;
    private static int _lastActiveThreads;
    private static int _lastAvailableThreads;
    private static int _maxThreads;
    private static int _minThreads;

在启动时运行:

int completionPortThreads;

    ThreadPool.GetMaxThreads(out _maxThreads,out completionPortThreads);
    ThreadPool.GetMinThreads(out _minThreads,out completionPortThreads);

    _timer = new Timer
    {
        AutoReset = true,Interval = 500,};

    _timer.Elapsed += TimerElasped;
    _timer.Start();

经过的方法

private static void TimerElasped(object sender,ElapsedEventArgs e)
    {
        int minWorkerThreads;
        int availWorkerThreads;
        int completionPortThreads;

        ThreadPool.GetMinThreads(out minWorkerThreads,out completionPortThreads);
        ThreadPool.GetAvailableThreads(out availWorkerThreads,out completionPortThreads);

        var activeThreads = _maxThreads - availWorkerThreads;

        if (availWorkerThreads != _lastAvailableThreads)
        {
            _lastAvailableThreads = availWorkerThreads;
            if (activeThreads > _lastActiveThreads)
            {
                _lastActiveThreads = activeThreads;
                Logger.Log($"+++++ Active Threads is Now: {activeThreads}");

                if (activeThreads > _minThreads)
                {
                    var diff = activeThreads - _minThreads;
                    Logger.Log($"+++++ Active threads is Now {activeThreads},which is {diff} more than minThread value of {_minThreads}.  This may be causing delays.");
                }
            }
        }
    }

相关文章

原文地址:http://msdn.microsoft.com/en-us/magazine/cc163...
前言 随着近些年微服务的流行,有越来越多的开发者和团队所采...
最近因为比较忙,好久没有写博客了,这篇主要给大家分享一下...
在多核CPU在今天和不久的将来,计算机将拥有更多的内核,Mic...
c语言输入成绩怎么判断等级
字符型数据在内存中的存储形式是什么