Should I dispose all disposable objects? - c#

Many objects in .NET (SQLCommand for instance) implement IDisposable. As a general rule, if I create an instance of an IDisposable object, should I always dispose it?

Yes, unless you're receiving it from a caller who needs it once you're done or has taken responsibility for calling Dispose(). The important thing is that someone calls Dispose() and if you are being passed an IDisposable instance, there needs to be an understanding ("contract") about whether you are taking ownership for it (and thus need to dispose it) or whether you are "borrowing it" and the caller will use/dispose it upon your return. These are the types of things good APIs have in their documentation.
If you are instantiating the object, make it easy on yourself to automatically dispose by using using.

Make sure to Dispose the items before they lose scope.
The best way is to use using statement, or you can manually call Dispose, but before it loses scope and becomes eligible for garbage collection.
You may see: CA2000: Dispose objects before losing scope
If a disposable object is not explicitly disposed before all
references to it are out of scope, the object will be disposed at some
indeterminate time when the garbage collector runs the finalizer of
the object. Because an exceptional event might occur that will prevent
the finalizer of the object from running, the object should be
explicitly disposed instead.

As a general rule, yes. The easiest way to do this is usually with the using statement.

Almost always yes, but here is an example of when disposing something borrowed can cause problems. I created a disposable repository with two constructors, one that takes a DbContext, and another default constructor that creates the DbContext itself. I ran into instances when my repository would be disposed, triggering the disposal of the DbContext (because I told it to), and that would sometimes cause problems because I still needed the DbContext that had been passed in elsewhere in the code.
In this case, the repository creates the DbContext and must take responsibility for it and dispose of it because no other code can, but when the DbContext is passed in by some other code then disposing of the DbContext should be the responsibility of the code that created it.

Not mandatory in all scenarios, but its a good practice to dispose an object. If you dont want to do it for each object, use using {} on which disposable is implemented.. It will take care of diposing the object when the code block is over.

Related

Thread safe disposable

I need to ensure thread safety when disposing an IDisposable resource. The resource is cached multiple times in memory. When entries are evicted from the cache we have a callback that calls Dispose().
Therefore if the resource is cached three times, we'll call Dispose() three times.
Is it the responsibility of the IDisposable resource to ensure thread safety or the caller?
It is the responsibility of the class implementing the IDisposable interface to ensure that the method can be called multiple times without throwing exception.
To help ensure that resources are always cleaned up appropriately, a Dispose method should be callable multiple times without throwing an exception.
http://msdn.microsoft.com/en-us/library/fs2xkftw(v=vs.110).aspx
After an object is disposed, calls that fail because the object is disposed can and likely should throw an ObjectDisposedException (to aid in future debugging). If it is important that external objects know whether or not an object is disposed before making calls (because the object is shared), then it is customary to add a public boolean property (IsDisposed/Disposed) that indicates the state of the object.
EDIT: To more clearly cast this answer to the phrasing of the question, the class implementing IDisposable should implementing thread-safety if it is expected the class will be used in a cross-threaded environment. The link I posted shows an example of this at the bottom of the page.
Either
The system which is evicting the values and calling Dispose must use synchronization to ensure the calls don't overlap
The object itself must implement Dispose in such a way that it can be safely called from multiple threads
Both of these are completely valid solutions to the problem. Which one is better will depend a lot on your system.
All other things being equal I would opt for #2. I prefer to have my objects be self sufficient and require as little help as possible to successfully execute in the environment they are designed for. Making it thread safe reduces the knowledge the rest of the system needs to use it correctly
The answer depends on whether the objects you want to dispose adhere to the guidelines or not.
If they do some things get simpler, from IDisposable.Dispose:
If an object's Dispose method is called more than once, the object must ignore all calls after the first one. The object must not throw an exception if its Dispose method is called multiple times. Instance methods other than Dispose can throw an ObjectDisposedException when resources are already disposed.
So if calling Dispose multiple times has no effect other than the first time it's called you only have to ensure that you don't call them at the same time. And that should absolutely be the responsibility of the caller.
Stephen Cleary wrote an article on CodeProject about how to implement IDisposable and the possible problems which I find extremely helpful.
Is it the responsibility of the IDisposable resource to ensure thread safety or the caller?
It is up to the caller to guarantee thread safety through lock primitive or Monitor class IDisposable has nothing to do with thread safety. It's just a signal that the object's instance is ready to be garbage collected.

When to return an object back to its pool

I want to use an object-pool in my C# application, and I know that there isn't any reference count in C#. If the same object can be passed to several threads, how can I know when there are no more references to the object so that I can return it to the object pool?
I thought of doing it in the dispose method, but that is too late, and it can't be returned to the pool since it is disposed.
Implementing object-pool in .Net can be done using a Finalizer.
Actually, most of the pools implemented in .Net are doing this also (for example - DB connection pool).
Using a finalizer allows you to know that the object isn't referenced anymore, as the finalizer is being called after the GC determine that there are not possible routes to the object.
The technique is not to do any destructive methods in your Dispose (i'll be getting this next) and finalize method.
Let's say that you have an PooledObject type, and an ObjectPool type that manages the pool.
In the ObjectPool, add an internal methods called ReturnToPool(PooledObject obj) that will get the object and make it available for other callers.
In the PooledObject type, you should add an internal method called ReleaseResources - which will only be called by the ObjectPool when the entire pool should be removed from memory - in this method you will implement your dispose logic (closing handles, releasing un-managed memory, etc..).
In the PooledObject Dispose and Finalize methods you should call the ReturnToPool methods in the ObjectPool (static, or internally stored in the pooled object) - this is called - resurrection.
When calling the ReturnToPool method in the finalizer you are actually resurrecting the object and making it available again.
Make sure you are re-registering PooledObject for finalization in the ReturnToPool method in ObjectPool - GC.ReRegisterForFinalize method.
Both of those types should be in the same assembly, of course. (to make sure they can call each other internal methods)
You should however implement the Dispose pattern either way. It will save time when object is not being used anymore (after leaving Using scope for example) and will return the object to the pool.
Hope this helps.
Ofir.
how can I know when there are no more references to the object so that I can return it to
the object pool.
Hm. You implement reference counting.
What also works is a proxy around it that has a Disposable method. WHen done with the Proxy, the dispose implementation puts the inner object to the pool (the outer object tuhs is VERY small).
But at the end you have to know when to release. This is called programming. This only makes sense for "fat" objets with significant initialization overhead, and then you really have to make sure you acutally know when to put them back by logic (i.e. custom counting etc.).
It should be in the Close/Release method. Responsibility of creating and disposing the instance lies with the ObjectPool itself.
To request/release an object from/to ObjectPool, use Open/Close or Acquire/Release.
A The Code Project article, C# Object Pooling, presents a nice lightweight custom object pool implementation.
You can also look at Connection Pooling Mechanism of ADO.NET to get hint of an object pooling example.

Do I need to call Dispose() on a static object?

If I have a static WebClient object, do I need to call Dispose() on it at the end of Main()?
You should always Dispose() objects when you're finished with them, regardless of where you put the object.
If the object is in a static field, it may be more difficult to figure out when you're finished with it.
As a general rule, you should dispose of any disposable objects. This will allow them to clean up any resources. However, there is no guarantee that dispose will be called on a disposable type - the consumer could neglect to call it, and the CLR does not automatically call it.
If a type really needs its clean-up logic to execute (such as when allocating unmanaged memory or creating a heap of files on the file system), it should implement a finalizer in conjunction with the dispose pattern. The CLR will call the finalizer on process exit if it hasn't already been called (typically through disposing the object). Yes, there are some caveats around this (a bad finalizer can spoil the party for other finalizable instances, for example) but the CLR guarantees to at least try to run all finalizers on process exit.
So technically, I don't there's any reason why you absolutely must call the dispose method in this case. However, it's a good habit to get into nevertheless.

IDisposable with destructor: requires thread-safe implementation?

This is pretty much only for me to make sure, I got this right:
We have a large resource class implementing the IDisposal pattern. It should (by design) be implemented in a way, that enables it to get called more than one time (even if we try to call it exactly one time of course). We also implement a finalizer, which also calls the Dispose() method - just as backup. If called manually, Dispose() will also call GC.SuppressFinalize(this).
There are several examples of disposal patterns around. Most of them call GC.SuppressFinalize(this) at the end of the disposing code. Some claim, it would be better, to call it at the beginning of the Dispose() method, before any cleaning. Latter argue, this would make sure, the GC doesn't call the finalizer concurrently, while we are still cleaning up.
Question:
It seems, placing GC.SuppressFinalize at the beginning doesn't do any better? We still have a race condition, right? So is it true, that we rather should implement Dispose() in a thread safe way instead?
The GC only cleans up objects that are not 'reachable'.
A class in which code is executing is still 'reachable' because it's this pointer is on the stack. So while dispose is executing, the finalizer won't be called.
So it does not matter if you call SuppressFinalize at the begin or end.
As commentors below indicated, the CLR implementation does not appear to guarantee that your object does not get garbage collected/finalized while instance methods are executing. The only possible 'dependable' reference keeping the object alive is the one used to invoke the method on the object, but I don't know enough about the JIT internals to make statements about that, and it's behaviour might change.
I'm leaving the answer here for access to the discussion below.
While it is sometimes possible for an object to be finalized while a seemingly-live reference exists, that can only happen when nothing else is going to ever refer to the object. The GC.SuppressFinalize(this) actively refers to the present object 'this', thus guaranteeing that it will not be finalized until the GC.SuppressFinalize executes. Further, the fact that the object reference existed to dispose the object, and was available to the Dispose method, guarantees that the finalizer couldn't have been queued before Dispose started running unless the object was dead and a finalizer somewhere (either its own finalizer, or that of some other object) resurrected it.
Because there are some scenarios where an object could be scheduled for finalization and resurrected without ever being aware of it, it may not be a bad idea to protect a dispose and finalize against redundant operation. Microsoft's pattern is not a good one, however. Finalizable objects shouldn't hold references to any objects not needed for finalization. If an object would hold a mixture of managed and unmanaged resources, the unmanaged resources should be moved into their own classes (effectively turning them into managed resources), so then the main object would hold nothing but managed resources.
Dispose should not throw any exceptions.
I would make sure all the code in Dispose is thread safe so that if it gets called it will not do anything strange. Usually adding checks if variables are null already should do the trick.
In the microsoft examples i've only seen GC.SuppressFinalize at the end of the Dispose function.

What are the kind of variables that must be disposed? (.NET/Java)

Three questions:
What kind of variables should be disposed manually in .NET/Java? I know that SqlConnection should always be either disposed manually or used in a using{} block. Is it right? What are the other kind of variables that should be disposed?
I read somewhere that unmanaged code must be disposed manually. Is that right? What exactly is unmanaged code and how do I know if a variable is managed or unmanaged?
Finally, how do I dispose variables? I know that the Dispose() method does not really dispose a variable. So what does Dispose() do? Should I set them to null()? What is the logic by which the garbage collector works?
This answer deals only with the .NET part of your question
What kind of variables should be disposed manually in .NET/Java? I know
that SqlConnection should always be
either disposed manually or used in a
using{} block. Is it right? What are
the other kind of variables that
should be disposed?
In .NET, all objects that implement IDisposable should be disposed explicitly (or used in a using block).
I read somewhere that unmanaged code must be disposed manually. Is
that right? What exactly is unmanaged
code and how do I know if a variable
is managed or unmanaged?
You probably mean unmanaged resources, as code can't be disposed... All classes that use unmanaged resources (memory allocated not on the managed heap, win32 handles...) should implement IDisposable, and should be disposed explictly, since they are not managed by the garbage collector.
Finally, how do I dispose variables? I know that the Dispose()
method does not really dispose a
variable. So what does Dispose() do?
Should I set them to null()? What is
the logic by which the garbage
collector works?
I'm not sure I understand your question... you don't dispose a variable, it is managed by the garbage collector. All managed memory is automatically released when it's not used anymore (i.e. it is not accessible by code because there are no references left to it). The IDisposable.Dispose method is only intended for resources that are not managed by the GC.
EDIT: as a side note, I would like to add that IDisposable is primarily intended to clean-up unmanaged resources, but is also frequently used to perform other cleanup actions and guarantee state or data integrity. For instance, IDbTransaction implements IDisposable in order to rollback the transaction if an exception occurs before the transaction was committed :
using (var trx = connection.BeginTransaction())
{
// Do some work in the transaction
...
// Commit
trx.Commit();
} // the transaction is implicitly rolled back when Dispose is called
In Java, you "close" rather than "dispose".
JDBC Connections, unless you got them from a pool.
JDBC ResultSets, depending on the JDBC connector.
InputStreams, OutputStreams, Readers and Writers (with the exception of those that are byte array and string backed).
Some third-party Java libraries or frameworks have classes that need to be manually disposed / closed / destroyed.
.NET
All objects that implement the IDisposable interface are asking that their Dispose methods are called when they are no longer required. The using block is just C# sugar for a try-finally block that disposes the IDiposable in the finally block, as long as it is not null. Consequently, disposal occurs even if an exception is thrown in the try block.
Unmanaged Code.
The Dispose method does whatever code the developer who wrote the Dispose method put in it! Typically this involves releasing 'unmanaged' resources, which are not managed by the runtime, such as database connections, window handles and file handles. Note that the GC manages the heap, so setting a reference to null just before the object it references becomes unreachable doesn't help all that much.
This is a good read.
This was mostly covered by Thomas, but to expand on the third point:
Finally, how do I dispose variables? I know that the Dispose()
method does not really dispose a
variable. So what does Dispose() do?
Should I set them to null()? What is
the logic by which the garbage
collector works?
They key is that the Dispose() tells the object to free any unmanaged resources that it currently holds, it does not free the object itself.
The garbage collector knows how to free the object, but for IDisposable objects, only the object itself knows how to dispose of it's private resources, so you have to make sure that Dispose() gets called before the garbage collector frees the object.
For Java:
SWT is a framework where we have to dispose resources (like images), because the framework uses native libs and system handles which have to released. SWT classes are documented and tell, when dispose is required.
Following up on other .NET solutions...
If your object owns unmanaged resources, it's not enough to simply clean them up on Dispose() calls, because you have no guarantee that Dispose will get called. The full solution is:
Add a finalizer for the class.
Add a public bool property called Disposed, which indicates that the object has been disposed.
Add a protected Dispose(bool) method. The public Dispose() method has no parameters.
When Dispose() is called, if the Disposed property is false, it will call Dispose(true), and call GC.SuppressFinalize() to disable the finalizer. Ths is essential to keep .NET's garbage collector happy. Classes with unspressed finalizers go to the end of the line for garbage collector cleanup, so they become almost a memory leak.
The public Dispose() method should then set the Disposed property to true.
The finalizer calls Dispose(false).
The Dispose(bool) will always clean up its own managed resources, but it will clean up unmanaged resources only when called as Dispose(true). Note that all resource cleanup is in the protected Dispose(bool) method, not in the public Dispose() method.
If the class is not sealed, then the protected Dispose(bool) method should be a virtual method. Subclasses that need to do cleanup can override Dispose(bool) and followht e same logic as above. In addition, they should call base.Dispose(bool) with the parameter they were given.
If .net, if you can use an object in a "using" statement, that means the object implements iDisposable and you should when practical call it's disposal method when you're done with it. Note that the disposal method may not always be called "Dispose", but you can always call it by casting the object to iDisposable and then calling Dispose on that.
Note that some types of "iDisposable" objects don't handle any unmanaged resources, but do subscribe to events. If such an object isn't properly disposed, it might not get garbage-collected unless or until all of the objects for which it holds subscribed events are themselves garbage-collected. In some cases, that may never happen until an application exits.
For example, the enumerator returned by an iEnumerable collection might subscribe to that object's "collection changed" event, unsubscribing when its dispose method is called. If the dispose method is never called, the enumerator would remain around as long as the collection did. If the collection itself stayed around a long time and was enumerated frequently, this could create a huge memory leak.
I'm in agreement with the above, I'll just add to the subsequent question about setting a variable to null.
You don't need to do this with variables used in a method (they will fall out of scope so it's only if they have state within them that must be signalled as needing clean-up, through IDisposable.Disopse that you have to worry abou this).
It's rarely useful for instance or static members, as memory isn't as precious a resource as people often think (it is a precious resource, but most attempts to deal with it in a few lines of code is like turning off your taps while you've a burst main.
It is though useful if you have a static or instance member of a class and (A) it is a large object (B) the "owning" object is likely to stay in memory for a long time and (C) you know you won't need that value gain, to set that member to null.
In practice this isn't a very common combination. If in doubt, just leave alone.
Now, do read the other answers here, as what they say about the Dispose() method is much more important.

Categories