请考虑以下情形:

我在本机API(P / Invoke)上创建了一个托管包装器 .
此API运行USB设备,该设备在专用线程上执行I / O操作 .
此外,此API是单线程的,因此调用其方法并最终确定它必须在已初始化它的同一线程上完成 .
它的要点是:

//Runs in the context of a new System.Threading.Thread instance
void Loopback()
{
 InitializeAPI();
 try
 {

 while(_work)
 {
  //Poll API
 }
 }
 finally
 {
  FinalizeAPI()
  //Unblock disposing thread
 }
}

void Dispose()
{
  _work=false;
  //Block untill Loopback method returns
}

在WPF应用程序的上下文中使用上述包装器时,我在Application.OnExit覆盖中调用我的包装器类的Dispose方法 . 这会导致死锁 .

单击VS中的Thread窗口,可以清楚地看到专用于本机API的工作线程停留在与当前WPF Dispatcher关联的某个等待句柄上 . 我想这是有道理的,因为WPF希望在最终确定时暂停所有内容 .

另一方面,我的Dispose方法 - 在设备的API完成之前不得返回,因此我在专用线程完成时连接了TaskCompletionSource以完成其任务 .

我的Dispose方法的作用是通过切换循环条件变量并立即阻止TaskCompletionSource的任务来启动线程的结束 .

专用线程永远不会完成,因为它被WPF阻止,并且UI线程永远不会完成,因为它阻塞了永远不会完成的任务,因此死锁 .

有没有办法克服这个问题,同时保持与包装器端的客户端框架无关?

非常感谢帮助!