使用WMI处理启动事件 - 未检测到所有进程启动

Xen*_*non 8 c# wmi events process wql

我在Windows服务(运行方式NT_AUTHORITY\SYSTEM)中使用以下C#代码来创建用于接收进程创建事件的事件处理程序(使用WMI和WQL):

string queryString = "SELECT * FROM Win32_ProcessStartTrace";
ManagementEventWatcher watcher = new ManagementEventWatcher(new WqlEventQuery(queryString));
watcher.EventArrived += new EventArrivedEventHandler(ProcessStartEvent);
watcher.Start();
Run Code Online (Sandbox Code Playgroud)

ProcessStartEvent:

int processId = int.Parse(e.NewEvent.Properties["ProcessId"].Value.ToString());
Process proc = Process.GetProcessById(processId);

Out("Received process: " + proc.ProcessName);
Run Code Online (Sandbox Code Playgroud)

我遇到的问题是(出于一些奇怪的原因)并非每个进程启动都被程序捕获并报告.如果我同时开始大约6个进程,则可能不会在输出中显示.

我曾尝试使用WMI对捕获进程创建事件进行一些研究,但是可用的信息有限.我已经看到使用类似的东西捕获进程开始也是可能的:

SELECT TargetInstance
FROM __InstanceCreationEvent
WITHIN  2
WHERE TargetInstance ISA 'Win32_Process'
Run Code Online (Sandbox Code Playgroud)

(如此Stack Overflow答案中所示)

使用__InstanceCreationEvent和之间是否有任何重大差异Win32_ProcessStartTrace?这可能是我的问题的原因吗?

有没有解释为什么我没有收到所有流程启动的事件?有什么比这更明显的我在这里做错了吗?

RRU*_*RUZ 7

两种方法都有效,但以不同的方式工作.

当您使用__InstanceCreationEventWMI类时,您正在使用内部事件,这意味着您正在监视标准WMI数据模型中的更改(这类似于表中的触发器).

当你使用Win32_ProcessStartTrace你使用的是外在的事件,这意味着你使用的是在这种情况下,为特定任务作出了专门的事件类监视进程创建.

现在回到你的问题,避免某些事件"丢失"的最好方法是创建一个permanent event consumer.

  • 为了回答为什么某些事件丢失,有必要深入研究WMI的内部,WMI使用内部缓冲区来保存事件,有时缓冲区不足以容纳事件的吞吐量.我和WMI有很多[经验](http://code.google.com/p/wmi-delphi-code-creator/)并且相信我对这个问题没有简短的答案.如果你想我可以推荐你的书籍来了解WMI的内部. (3认同)