【问题标题】:Has COM object been separated from its RCW?COM 对象是否已与其 RCW 分离?
【发布时间】:2011-07-29 21:43:18
【问题描述】:

我正在尝试解决“无法使用已与其底层 RCW 分离的 COM 对象”错误的问题,我认为导致该问题的原因是 COM 对象在未实例化它们的线程上使用。

我不允许进行太多重构,并且由于对象应该在多个线程上可用,我想知道是否有办法在对它们进行可能导致上述错误的操作之前找出它们是否已在当前线程上创建.如果还没有,请创建它们。

另外,我是这个互操作的新手,所以如果有人能帮助我理解,我将不胜感激:

一旦线程完成,COM 对象会发生什么,为什么 RCW 在另一个线程上仍然可用,即使它不再包含 COM 对象(为什么它不是 null?)。另外,为什么它会导致该错误并同时在 Marshal.IsCOMObject 上返回 true?

在以下使用引用计数、包装器和内存的情况下会发生什么:

  • 在线程 A 上创建 COM 对象 x
  • 传递它并保存在线程 B 上
  • 在线程 C 上创建另一个 x(或者,如果它是 y 会发生什么?)
  • 传递它并覆盖线程 B 上的 x

【问题讨论】:

    标签: c# com interop rcw


    【解决方案1】:

    线程结束后 COM 对象会发生什么

    COM 对象被 COM 自动销毁。当另一个线程继续使用它时,它将产生“已分离的 COM 对象”异常消息。你不能让线程退出。

    显然,您有一个单线程 COM 服务器,这是迄今为止最常见的一种。它与创建它的 STA 线程有关联。 COM 确保自动将在另一个线程上进行的任何调用编组到创建对象的线程。当线程消失时,这将不再起作用。还要注意你没有得到任何并发。

    获得此异常的另一种方法是错误地使用 Marshal.ReleaseComObject() 显式处理引用计数。也不是不可能,因为您应该收到 MDA 警告。

    【讨论】:

    • Marshal.ReleaseComObject() 到处都是,但这次它们不会导致它。通过在程序初始化阶段在主线程上初始化 COM 对象解决了问题。感谢您的输入,我需要保证它们可供其他线程使用,而无需在那里创建它们。但是,我想在将您标记为已接受之前等待更完整的答案,因为我仍然不明白一些提到的东西..
    猜你喜欢
    • 2011-11-21
    • 2012-04-27
    • 2011-07-03
    • 1970-01-01
    • 1970-01-01
    • 2022-08-09
    • 2011-03-11
    • 2011-04-26
    • 2021-09-23
    相关资源
    最近更新 更多