繁体   English   中英

如何在.Net Web 应用程序中管理 COM 对象

[英]How to Manage COM Objects in .Net Web Application

必须从基于 a.Net 服务器的 windows 应用程序调用具有有时臭名昭著的 memory 泄漏问题的旧版 c++ 应用程序。 .Net garbage collection times are not determinable and sometime the c++ object are destroyed or not destroyed "on time" producing unpredictable results and generally crashing the c# web app. 将 c++ 对象尽可能频繁地推送到垃圾收集堆栈的最佳方法是什么,但不要经常删除.Net 对 COM object 的引用。 请记住,COM 对象可以产生子对象,因此 COM 对象的 .Net 引用计数可以通过 function 调用而改变,而不必是实例化。

由于 memory 发生泄漏并且 COM 对象没有被清理,性能下降,直到它非常慢以至于 IIS 自身跳闸几次然后崩溃。 重新启动 IIS 可修复此问题,直到下一次。 定期重新启动会有所帮助,但忙碌的一天可能会在工作日造成这种情况。

几年前我不得不使用.Net 1.1 解决这个问题。 想知道其他人是否有我的解决方案或更好的解决方案。 这不是 ASP.NET。 它是一个.Net dll。

最终结果并不完全令人满意,web 服务器每隔几个月就会崩溃一次。

您问“尽可能频繁地将 c++ 对象推送到垃圾收集堆栈的最佳方法是什么”,但 c++ 对象永远不会被垃圾收集。 也许这样看...

您有一个实例化一堆 c++ 对象的进程。 其中一些 c++ 对象实现了 COM 对象,因此它们的生命周期通过 AddRef/Release 进行管理。 其中一些 COM 对象被导入 .NET 世界,并用 RCW(运行时可调用包装器)包装。 只有 RCW 是 .NET object 并进入垃圾收集堆。

在没有您的任何干预的情况下,RCW 最终将被 GC 处理,并且当这种情况发生时,它将针对其底层 COM object 执行发布。 如果您想立即释放COM object,无需等待GC,您可以调用...

System.Runtime.InteropServices.Marshal.ReleaseComObject

...甚至 FinalReleaseComObject 如果您确定这是您想要的。

回到您的问题:您想知道如何删除 c++ 对象而不释放 .NET 对您的 COM ZA8CFDE6331149EB2AC96B86 的引用由于 .NET 堆中不存在 c++ 对象,因此无法直接实现此目的。 您可以从 COM object 中公开一个方法,该方法会删除其所有 c++ 对象,然后从您的 Z303CB0EF9EDB9082D61BBBE572 代码中简单地调用它。 但我想您的 COM object 是否有可能识别您已经这样做的所有泄露的 c++ 对象。

希望我已经解释了为什么无法实现您在问题中的建议,但是有很多工具可以帮助您查找和修复 memory 泄漏。 我建议使用 LeakDiag 之类的工具(搜索 StackOverflow)来找出 c++ 代码在哪里泄漏 memory。

如果您使用的是 IIS6 或更高版本,实用的解决方案是配置应用程序池回收。 您可以调整这些数字,以便在进程泄漏足够多的 memory 导致问题之前杀死并重新启动进程,并且它通常以用户不会注意到任何停机时间的方式工作。

创建一个 COM+ 应用程序并将您使用的 COM 类放入该应用程序中。 这样,所有 COM 对象都在单独的进程中实例化。 您可以定期释放所有 COM 对象,然后重新启动 COM+ 应用程序进程。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM