Question: I have the code below to query records from a stored procedure but am concerned I may not be disposing what I need to or am disposing when the object would be cleared by the Garbage Collector shortly afterward anyway.

Do I need to dispose the SqlDataReader since it is within the try catch block?  

Do I need to run both cmd.Dispose and cmd.Connection.Close or does one infer the other?

Would the garbage collector eventually dispose of all these objects anyway (maybe not timely enough) or do these objects implictly require dispose possibly because of using unmanaged code?

```
public void GetData(string studentID)
    {
        SqlCommand cmd = new SqlCommand("sp_stored_proc", 
                new SqlConnection(Settings.Default.connectionString)) 
                { CommandType = CommandType.StoredProcedure };
        try
        {
            cmd.Connection.Open();
            cmd.Parameters.AddWithValue("@student_id", studentID);
            SqlDataReader dr = cmd.ExecuteReader();

         //do something with the data

            if (dr != null)
                dr.Dispose();
        }
        catch
        {
            //error handling
        }
        finally
        {
            if (cmd != null)
            {
                cmd.Dispose();
                cmd.Connection.Close();
            }

        }

    }

```

Answer: 
You should dispose the data reader, and the command. No need to separately close the connection if you dispose the command. You should ideally do both using a `using` block:

```
using (SqlCommand cmd = new...)
{
    // do stuff
    using (SqlDataReader dr = cmd.ExecuteReader())
    {
        // do stuff
    }
}

```

If you need exception handling do that separately either inside or around the using blocks - no need for the finally for the `Dispose` calls though with `using`.
To make a long story short; if it implements [`IDisposable`](http://msdn.microsoft.com/en-us/library/system.idisposable.aspx), you should call `Dispose`.

Even if you use Reflector to figure out that `Dispose` in one object invokes `Dispose` on another object, I would still recommend to call `Dispose` on both, since *this is internal implementation details that may change* in some future release, so you should not rely on that always being true. 

So, `Dispose` anything that is `IDisposable`.