繁体   English   中英

如何识别无响应的过程?

[英]How to identify an unresponsive process?

我正在为在Windows Server 2008 R2和Windows Server 2012环境中部署的客户端重构自定义过程监视应用程序。

监视应用程序需要识别崩溃的无响应进程(在任务管理器中标识为“无响应”),强行杀死它们并重新启动。 监视的进程可以是基于控制台的应用程序,也可以是基于Win32的应用程序,主要是基于控制台的应用程序。

在此特定情况下, Process.Responding属性没有用,因为它确定UI是否正在响应(可能使用与下面类似的“幕后”方法来更新此属性)。

如果导入了IsHungAppWindow方法,因为基于控制台的应用程序不满足以下条件,则该方法也没有用:

如果应用程序未等待输入,未处于启动处理中且未在5秒钟的内部超时时间内调用PeekMessage,则认为该应用程序没有响应。

如果我监视使用WMI系统类的进程,则Win32_Process WMI类的Status属性没有用:

未实现此属性,并且不会为此类的任何实例填充此属性。 始终为NULL。

Win32_Process WMI类的ExecutionState属性没有用,因为它似乎也未实现。 尽管没有明确说明,但在运行本地测试后,它会反复返回NULL并由第三方指示。

如何合理确定进程是否无响应?

我能确定的最佳答案和解决方案是从Windows事件查看器应用程序日志中监视Application ErrorApplication Hang事件。

从.NET 3.5开始,实现了一个方便的类,以避免读取和过滤整个事件日志: EventLogWatcher允许监视特定事件。

这是一个非常基本的示例,使用XPath查询按EventIDLevelApplicationName进行过滤:

using System.Globalization;
using System.Diagnostics.Eventing.Reader;

EventLogQuery filter = new EventLogQuery("Application", PathType.LogName, "Event[System[Level=2 and (EventID = 1000 or EventID = 1002)] and EventData[Data[1] = \"example.exe\"]]")
EventLogWatcher watcher = new EventLogWatcher(filter);

watcher.EventRecordWritten += Watcher_ApplicationError; // Register our handler
watcher.Enabled = true; // Start delivering events to the handler

private void Watcher_ApplicationError(object sender, EventRecordWrittenEventArgs e) 
{
     String rawId = e.EventRecord.Properties[8].Value.ToString(); // Faulting process id

     Int32 id = -1;
     if (!Int32.TryParse(rawId, out id)) // If not integer, possibly hexadecimal
     {
         if (!Int32.TryParse(rawId, NumberStyles.HexNumber, CultureInfo.InvariantCulture, out id)
             return; // Unable to read the process id successfully
     }

     Process unresponsive = Process.GetProcessById(id); // Get the unresponsive process
     unresponsive.Kill(); // Kill it
}

这可以很容易地扩展到完全合格的错误应用程序执行路径Properties[10]进行过滤。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM