Microsoft KB Archive/821625

= The TcpClient Close method does not close the underlying TCP connection =

Article ID: 821625

Article Last Modified on 5/17/2007

-

APPLIES TO


 * Microsoft .NET Framework 1.1
 * Microsoft .NET Framework 1.0
 * Microsoft Visual C# .NET 2003 Standard Edition
 * Microsoft Visual C# .NET 2002 Standard Edition

-



This article refers to the following Microsoft .NET Framework Class Library namespaces:
 * System.Net
 * System.Net.Sockets



SYMPTOMS
When you call the TcpClient Close method, you expect the underlying TCP connection to be closed as described in the &quot;TcpClient.Close Method&quot; topic of the .NET Framework Class Library documentation. For more information, visit the following Microsoft Web site:

http://msdn2.microsoft.com/en-us/library/system.net.sockets.tcpclient.close(vs.71).aspx



RESOLUTION
To resolve this problem, close the associated NetworkStream object that the TcpClient GetStream method returns.



Steps to reproduce the problem
  In a text editor such as Notepad, paste the following sample code. using System; using System.Net; using System.Net.Sockets; using System.Text;

class Server {   static void Main(string[] args) {       try {           const int portNumber = 10000; TcpListener tcpListener = new TcpListener(IPAddress.Loopback, portNumber);

tcpListener.Start;

Console.WriteLine(&quot;Waiting for a connection....&quot;);

//Accept the pending client connection, and then return a TcpClient that is initialized for communication. TcpClient tcpClient = tcpListener.AcceptTcpClient; Console.WriteLine(&quot;Connection accepted.&quot;);

NetworkStream networkStream = tcpClient.GetStream;

string responseString = &quot;You have successfully connected to me\n&quot;;

Byte[] sendBytes = Encoding.ASCII.GetBytes(responseString.ToCharArray); networkStream.Write(sendBytes, 0, sendBytes.Length);

Console.Write(&quot;Message Sent /> : &quot; + responseString);

//Close networkStream and TcpClient. //networkStream.Close; tcpClient.Close;

//Wait until you can see that the connection is closed in the client. Console.ReadLine; //Close the listener. tcpListener.Stop;

}       catch (Exception e)         { Console.WriteLine(e.ToString); }      } }  Save the file as Server.cs. Click Start, point to Programs, point to Microsoft Visual Studio .NET (for Microsoft Visual Studio .NET 2002) or Microsoft Visual Studio .NET 2003, point to Visual Studio .NET Tools, and then click Visual Studio .NET Command Prompt or Visual Studio .NET 2003 Command Prompt. At the command prompt, type the following command, and then press ENTER to compile Server.cs:

csc server.cs

 At the command prompt, type the following command, and then press ENTER:

start server.exe

 At the command prompt, type the following command, and then press ENTER:

netstat -p tcp -a

Notice that a TCP connection is opened at port 10000 and the connection is in the LISTENING state.</li>  In a text editor such as Notepad, paste the following sample code. using System; using System.Net; using System.Net.Sockets; using System.Text;

class Client {   static void Main(string[] args) {       try {           TcpClient tcpClient = new TcpClient; tcpClient.Connect(IPAddress.Loopback, 10000); NetworkStream networkStream = tcpClient.GetStream;

if(networkStream.CanWrite && networkStream.CanRead) {               // Reads the NetworkStream to a byte buffer. byte[] bytes = new byte[38]; networkStream.Read(bytes, 0, bytes.Length); // Returns to the console the data that is received from the host. string returndata = Encoding.ASCII.GetString(bytes); Console.Write(&quot;This is what the host returned to you: &quot; + returndata.TrimEnd(new char[] {' '})); Console.ReadLine; networkStream.Close; tcpClient.Close; }       }        catch (Exception e ) {           Console.WriteLine(e.ToString); }   } } </li> Save the file as Client.cs.</li> At the command prompt, type the following command, and then press ENTER to build Client.cs:

csc client.cs

</li> At the command prompt, type the following command, and then press ENTER:

start client.exe

</li> At the command prompt, type the following command, and then press ENTER:

netstat -p tcp -a

Notice that a TCP connection is opened, and that the connection is in the ESTABLISHED state.

Because the connection on the server side is closed, the server side socket connection should be in the FIN_WAIT_2 state, and the client side socket connection should be in the CLOSE_WAIT state. This behavior is described in RFC 793 - &quot;Transmission Control Protocol Darpa Internet Program Protocol Specification.&quot;</li>  Change the code in step 1 by uncommenting the following line: //networkStream.Close; Repeat steps 3 through 9.

Notice that the server side socket connection is in the FIN_WAIT_2 state, and the client side socket connection is in the CLOSE_WAIT state. This behavior occurs because the connection is closed on the server side. </li></ol>

<div class="references_section">