I originally encountered this issue with a client in 2006.
If you use the Close and Dispose methods of a Connection object in ADO.NET is the connection immediately returned to the pool? You might think so, but not really.
After doing some research I found out that closing the connection .NET doesn't actually close it. Once a connection is closed in .NET, the connection is marked as dead but remains open. The CLR then cleans up, finally closes, these connections every 4-8 minutes. All connections will close if the app domain that launched the app shuts down. Per Microsoft, this is by design.
I tested this out to verify by running a test app that executes a SqlDataReader. After the SqlDataReader is executed and the Close method is called I ran sp_who. Sure enough the connection was still open. I continued to run sp_who every 30 seconds. After 6 minutes, the connection finally closed.
What to do, what to do. After doing a little more digging I found a method new to .NET 2.0. Enter SqlConnection.ClearPool(SqlConnection connection). By calling this method all inactive connections in the pool are cleaned up (closed) immediately.
Not trusting MSFT I decided to try this out. I modified my test app to have a max pool size of 10, launch 10 threads with each thread executing a SqlDataReader 1000 times. The first time I ran it without calling ClearPool. I then monitored the connections via sp_who. Sure enough 10 connections showed up. After the SqlDateaders finished executing the connections remained opened for 7 minutes.
I then ran the app again utilizing the ClearPool method after each SqlDateader finished executing. This time as when I executed sp_who I saw the number of connections increase and decrease depending on the number of active SqlDataReaders. Once all readers were done executing no connections remained open.
What does all this mean? I'm not quite sure, but I will say that it is important to consider how you handle your connections with .NET, especially in a high transactional environment.
As an addendum, when running on Vista this issue never occurs. It looks MSFT has updated garbage collection to prevent this from happening.
ag