Reputation: 430
In my application I am using lots of com objects.
I am releasing all com object, which I declared but my application is triggering some other application which is also using some com object and that application creating memory leak.
Triggering part activates from a loop so I have a chance to release all com objects in every iteration. I wanted to know is there any way so that I can release all com objects which were used by another application.
I have used following code for releasing com object.
if (feature != null)
{
while (Marshal.ReleaseComObject(feature) > 0)
{ }
}
I understand that GC maintain a table which hold all entry related to all reference object but how GC behave if some other application creating heap inside my application space.
Upvotes: 1
Views: 165
Reputation: 10497
You're manually implementing what amounts to the same thing as FinalReleaseComObject. If you're going to do this, I would think you would want to just go ahead and use the built-in FinalReleaseComObject
method, since semantically it represents exactly what you're doing in your loop, and since it's a built-in part of the framework that's likely to get bug-fixing love from Microsoft if there's something wrong with it, and because using it adheres to DRY.
From Microsoft's MSDN page on FinalReleaseComObject
(emphasis is mine):
When the reference count on the COM object becomes 0, the COM object is usually freed, although this depends on the COM object's implementation and is beyond the control of the runtime. However, the RCW can still exist, waiting to be garbage-collected.
However, this article on CodeProject, as well Microsoft's Patterns and Practices, suggests that you not use FinalReleaseComObject
, and that instead you make darn sure that you call ReleaseComObject
in the opposite order of what you instantiated the objects in.
In other words, have one and only one ReleaseComObject
paired up with each assignment. Judicious use of try/finally is probably a good idea, to guarantee that the release occurs for each assignment.
Do this, and your RCW reference count for each COM object will naturally drop to 0 as you "unwind" your COM object graph, then if your COM object isn't ill-behaved it should be freed.
Note what the CodeProject article says about being sure to release COM objects returned from method calls. If you just ignore those return values, it doesn't mean they don't exist. You'll have references to them sitting around waiting for multiple generations of garbage collection. So you need to be sure to call ReleaseComObject
on those, as well:
Marshal.ReleaseComObject( myCom.ProcessError (5) ); //Release returned object
Marshal.ReleaseComObject( myCom );
Using FinalReleaseComObject
seems to be a little more like throwing a Hail Mary and praying for the best. It's kind of like you're saying "Hey, I didn't really pay attention when I was spinning up this object, but please try really hard to make it go away for me."
Upvotes: 2