Dear all,
I have written a TCP server as a windows service that accepts connections
using the System.Net.Sockets.Socket class. I use the various asynchronous
methods in the socket class. I'm having a problem at the moment when I shut
the service down. When I stop the service I attempt to shutdown and close
the socket. But when the service is started again and the Socket.Bind
statement is encountered, an error occurs telling me that it is already in
use? How can this be if I have shutdown and closed the socket?
Further more can anyone explain what happens when an Asynchronous method is
called. Is a new thread allocated for the callback? If the method has been
called before in the socket do you get the same thread? I have stepped
through the code using the debugger and I don't understand where the threads
have been created.
Any information on these things would be gratefully received!
Darren
Example Code:
The windows service calls the StartListener and StopListener methods
public void StartListener()
{
Socket ConnectionListener = new Socket( AddressFamily.InterNetwork,
SocketType.Stream, ProtocolType.Tcp );
ConnectionListener.Bind( new IPEndPoint( HostAddress, PortNumber ) );
ConnectionListener.Listen( 10 );
while (!ShuttingDown)
{
Listen.Reset();
ConnectionListener.BeginAccept( new AsyncCallback(
ConnectionRequest ), ConnectionListener );
Listen.WaitOne();
}
}
/// <summary>
/// Stop listening for clients
/// </summary>
public void StopListener()
{
ShuttingDown = true;
Socket ConnectionListener = new Socket( AddressFamily.InterNetwork,
SocketType.Stream, ProtocolType.Tcp );
ConnectionListener.Connect( new IPEndPoint( HostAddress, PortNumber ) );
ConnectionListener.Shutdown( SocketShutdown.Both );
ConnectionListener.Close();
ConnectionListener = null;
}
private void ConnectionRequest( IAsyncResult ar )
{
Socket Listener = (Socket) ar.AsyncState;
Socket WorkingSocket = Listener.EndAccept( ar );
if ( ConnectedClients.Count < MaximumClients )
AcceptClient( WorkingSocket );
else
RefuseClient( WorkingSocket );
Listen.Set();
}
private void AcceptClient( Socket WorkingSocket )
{
Client Client = new Client();
Client.Connected += new Client.ConnectHandler( AddClient );
Client.Disconnected += new Client.DisconnectHandler( RemoveClient );
Client.WorkingSocket = WorkingSocket;
}
private void RefuseClient( Socket WorkingSocket )
{
WorkingSocket.Send( Encoding.ASCII.GetBytes("To many Clients") );
WorkingSocket.Shutdown( SocketShutdown.Both );
WorkingSocket.Close();
}