停止 IMediaControl 永远不会结束

Stopping IMediaControl never ends

我正在为我的 C#/WPF 项目使用 DirectShowLib-2005。当相机启动时,我 运行 媒体控制:

m_FilterGraph = new FilterGraph() as IFilterGraph2;
/* Initializations */
IMediaControl mediaCtrl = m_FilterGraph as IMediaControl;
hr = mediaCtrl.Run();
DsError.ThrowExceptionForHR(hr);

应用程序运行,相机工作正常。但有时(并非总是)当我退出应用程序时冻结。我暂停了调试器,我看到应用程序在以下行停止:

if (m_FilterGraph != null)
{
    IMediaControl mediaCtrl = m_FilterGraph as IMediaControl;
    mediaCtrl.Stop();  // <= *** Blocked here ***
    Marshal.ReleaseComObject(m_FilterGraph);
    m_FilterGraph = null;
}

如何防止这种冻结?我可以添加超时或 try/catch 吗?

如果您look for it,您会发现周围有许多讨论试图停止流式传输的类似冻结症状的对话。

单独实施 IMediaControl.Stop 以及发布的代码片段都很好。重要的是流式传输是多线程的,调用涉及与流式线程的同步:发出停止信号并等待完成;这也涉及停止所有参与的过滤器。线程问题、任何过滤器或 - 通常 - 甚至从过滤器回调到控制代码粗心地忽略线程概念都可能导致死锁。

您对问题的描述不完整。当你面对这种冻结时,你需要:

  1. 确保您了解管道的拓扑结构;您需要了解(并包括在这样的问题中)有关参与过滤器和 pin 连接的详细信息
  2. 确保从正确的线程停止图形,特别是不是从某些过滤器回调
  3. 附加调试器并检查线程状态,但不仅仅是调用冻结 Stop 的线程(这可能有零有意义的细节),还有其他线程,以找到其他相关的阻止停止同步。

问题通常是您的代码导致流式传输停止时出现死锁,或者参与过滤器有问题。