我尝试使用 Visual Studio 分析器分析应用程序以查看潜在的线程争用问题,但问题是分析器将信号等待视为最严重的违规者(因为消耗线程大部分时间都在等待信号),而在现实中,看到生产方面的竞争会更有趣。
例如,我正在使用 log4net 的异步附加程序来减少日志记录对实际工作人员的影响,它基本上是一个包装器BlockingCollection<T>
:
readonly BlockingCollection<LoggingEventContext> _queue;
protected override void Append(LoggingEvent e)
{
// instead of appending, push to the queue
_queue.Add(new LoggingEventContext(e, HttpContext), _loggingCancelationToken);
}
void StartForwarding()
{
_queue = new BlockingCollection<LoggingEventContext>(BufferSize);
_loggingCancelationTokenSource = new CancellationTokenSource();
_loggingCancelationToken = _loggingCancelationTokenSource.Token;
_loggingTask = new Task(SubscriberLoop, _loggingCancelationToken);
_loggingTask.Start();
}
长时间运行的任务是将事件转发到实际附加程序的地方:
void SubscriberLoop()
{
try
{
// this is the blocking call which is reported as the source of contention
foreach (var entry in _queue.GetConsumingEnumerable(_loggingCancelationToken))
{
HttpContext = entry.HttpContext;
ForwardLoggingEvent(entry.LoggingEvent, ThisType);
}
}
catch (OperationCanceledException ex)
{
...
}
catch (ThreadAbortException ex)
{
...
}
}
我的问题是:我做错了什么吗?使用分析器识别实际热点的正确方法是什么?