ManagementObjectSearcher在全局挂钩中不起作用 [英] ManagementObjectSearcher does not work within global hook

查看:68
本文介绍了ManagementObjectSearcher在全局挂钩中不起作用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

当我尝试在鼠标事件处理程序中获取所有正在运行的进程时,它将引发异常.首先,我认为问题仍然存在,因为我将 async 关键字放在了鼠标事件处理程序之前,但事实并非如此,因为非异步方法也会引发异常.

When I try to get all running processes inside mouse event handler it throws an exception. First I thought that the problem persists because I put async keyword before mouse event handler, but it was not the case, as the exception is thrown also for non-asynchronous methods.

我正在使用 MouseKeyHook 库.

异常消息:

其他信息:转换到COM上下文0x1ac936a0,用于此RuntimeCallableWrapper失败,出现以下错误:An由于应用程序正在调度呼叫,因此无法进行拨出呼叫输入同步调用.(来自HRESULT的异常:0x8001010D(RPC_E_CANTCALLOUT_ININPUTSYNCCALL).

Additional information: Transition into COM context 0x1ac936a0 for this RuntimeCallableWrapper failed with the following error: An outgoing call cannot be made since the application is dispatching an input-synchronous call. (Exception from HRESULT: 0x8001010D (RPC_E_CANTCALLOUT_ININPUTSYNCCALL)).

从中获取所有进程的事件处理程序:

private async void MouseUp(object sender, System.Windows.Forms.MouseEventArgs e)
{
    List<ProcessInfo> allRunningProcesses = Logic.GetAllProcesses();
    // ...
}

使用 ManagementObjectSearcher 获取所有进程:

Get all processes by using ManagementObjectSearcher:

public static List<ProcessInfo> GetAllProcesses()
{   
     using (var searcher = new ManagementObjectSearcher(wmiQueryString))
            using (var results = searcher.Get()) // EXCEPTION THROWN!
            {
                // ...
            }
}

如您所见,调用 searcher.Get()时会引发异常.注意:如果在鼠标事件处理程序( MouseUp )之外使用此方法,则不会出现任何问题.

As you can see the exception is thrown when calling searcher.Get(). Note: This method works without any issues if used outside the mouse event handler (MouseUp).

推荐答案

事实证明,如果存在MTA,COM要求您在STA上运行代码您需要在 SendMessage()中使用 ManagementObjectSearcher 方法.
因此,我需要做的是在差异线程并将 SetApartmentState 设置为 ApartmentState.STA .

As it turns out, COM requires you to run your code on STA if there is MTA involved and you are using the ManagementObjectSearcher methods within SendMessage().
So, what I needed to do is to run my code on differet thread and set SetApartmentState to ApartmentState.STA.

List<ProcessInfo> allRunningProcesses = null;

Thread threadProc = new Thread(() =>
{
    allRunningProcesses = Logic.GetAllProcesses();
});

threadProc.SetApartmentState(ApartmentState.STA);
threadProc.Start();
threadProc.Join();

有用的链接:

msdn- 了解和使用COM线程模型
stackoverflow- 如何在STA线程中运行某些东西

这篇关于ManagementObjectSearcher在全局挂钩中不起作用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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