与它的基础RCW分开的COM对象不能使用

ama*_*nth 2 c# com ajax service interop

我用OPC服务器编写XML AJAX服务。基于示例的XML AJAX服务。我使用单一属性进行服务:

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
Run Code Online (Sandbox Code Playgroud)

下一步,我创建类析构函数:

~BoilerService()
{
    try
    {
        ReadTimer.Dispose();
        group.ReadCompleted -= new ReadCompleteEventHandler(group_ReadCompleted);
        group.Remove(true);
        server.Disconnect();
    }
    catch (Exception e)
    {
        System.IO.StreamWriter sw = new System.IO.StreamWriter("log.txt", true);
        sw.WriteLine(DateTime.Now.ToString() +e.Message+ " "+ e.Source+" "+e.StackTrace +  " destructor called.");
        sw.Close();
        sw.Dispose();
    }
}
Run Code Online (Sandbox Code Playgroud)

但是,当我在VS中重建解决方案时(在应用程序路径中替换了文件),我得到了wp3.exe未处理的异常错误窗口(Windows 7)。在Windows事件日志中,我看到以下文字:

Exception: System.Runtime.InteropServices.InvalidComObjectException

Message: COM object that has been separated from its underlying RCW cannot be used.

StackTrace:    at System.StubHelpers.StubHelpers.GetCOMIPFromRCW(Object objSrc, IntPtr pCPCMD, Boolean& pfNeedsRelease)
   at OPC.Data.Interface.IOPCServer.RemoveGroup(Int32 hServerGroup, Boolean bForce)
   at OPC.Data.OpcGroup.Remove(Boolean bForce)
   at OPC.Data.OpcGroup.Finalize()
Run Code Online (Sandbox Code Playgroud)

我做错什么了?


VS 2010会发出警告:1.'System.Runtime.InteropServices.UCOMIEnumString'已过时:'请改用System.Runtime.InteropServices.ComTypes.IEnumString。http://go.microsoft.com/fwlink/?linkid=14202。2.“ System.Runtime.InteropServices.UCOMIConnectionPointContainer”已过时:“改用System.Runtime.InteropServices.ComTypes.IConnectionPointContainer。http://go.microsoft.com/fwlink/?linkid=14202 '

可能由于此警告而出现此错误?

Jus*_*tin 5

根据MSDN文档

即使一个对象引用了另一个对象,也不能保证两个对象的终结器以任何特定顺序运行。也就是说,如果对象A引用了对象B并且都具有终结器,则当对象A的终结器启动时,对象B可能已经终结。

这意味着如果group可以在与您的OpcGroup实例同时进行收集的情况下(看起来很有可能),则很有可能group已经完成,这很容易成为您失败的原因。

它看起来像你从C ++背景,在这种情况下,你应该知道,finalisers在C#中的工作方式不同未来-它非常罕见的,你永远需要实现一个finaliser。我建议不要在终结器中进行清理,而应实现IDisposable并在处理对象时进行此工作。

同样,您通常不需要解钩事件处理程序(除非事件可能仍被触发并在释放对象后可能导致异常)。这种清理工作已为您完成。