| 
    
     | 
    
    Forums -> Security Library Forum  
    
      
        
        
          
            | Asynchronous Server Socket | 
            
                             
                           | 
           
         
         | 
       
      
        
          
            
              by Harmeet Bedi [harmeet at kodemuse dot com] posted on 2003/11/08 | 
              
                 | 
             
           
        
        
        
        While attempting to do an Asynchronous Server I hit a few issues. 
 
- I wanted to use SecureTcpListener and SecureTcpClient. I had code 
  for a plain server and wanted to reuse. SecureTcpListener did not 
  seem to be amenable to Asychrounous communication. I got around this 
  by creating a SecureServerSocket, using 
  BeginAccept/OnAccept/EndAccept and creating a SecureTcpClient from 
  the Accepted Secure client socket. For that I had to make one minor 
  change to 1.0.1b in file SecureTcpClient.cs. 
 
 @@ -101,7 +101,7 @@ 
   		/// </summary> 
   		/// <param name="socket">The accepted socket.</param> 
   		/// <remarks>This constructor is used by the SecureTcpListener 
class.</remarks> 
  -		internal SecureTcpClient(SecureSocket socket) : base() { 
  +		public SecureTcpClient(SecureSocket socket) : base() { 
   			m_Client = socket; 
   			m_Active = true; 
   		} 
 
 
- With Server side SecureSocket I wanted to do Asychrounous Accept 
  handling using BeginAccept/OnAccept/EndAccept. The one problem was 
  that whenever I called EndAccept from my OnAccept in my application 
  listener, I always got ArgumentException. A patch to SecureSocket 
  fixed this. It appears that somewhere AsyncAcceptResult is getting 
  changed. I thought it was a problem on my end but I made an effort 
  to rule it out. Here is the patch 
 
  +++ SecureSocket.cs	2003/11/07 16:20:14	1.2 
  @@ -244,8 +244,13 @@ 
   				throw new ArgumentNullException(); 
   			if (m_AcceptResult == null) 
   				throw new InvalidOperationException(); 
  -			if (m_AcceptResult != asyncResult) 
  -				throw new ArgumentException(); 
  + 
  +            // asyncResults don't match for some reason. - HB 
  +            // investigate and uncomment. Asynch works with this code 
  +            // disabled 
  +			//if (m_AcceptResult != asyncResult) 
  +			//	throw new ArgumentException(); 
  + 
   			AsyncAcceptResult ar = m_AcceptResult; 
   			// Process the (secure) EndAccept 
   			// block if the operation hasn't ended yet 
 
Hope the first patch is accepted and second one can be verified. An 
example of AsychronousServerSocket like the client side 
AsychronousSocket in distribution would help enormously. 
 
thanks for the excellent code. I learnt a lot from it. 
  | 
       
      
        
          
            
              by Pieter Philippaerts [Pieter at mentalis dot org] posted on 2003/11/08 | 
              
                 | 
             
           
        
        
        
        The SecureTcpClient and SecureTcpListener implement exactly the same methods, properties and constructors as the TcpClient and TcpListener classes [apart from some extra methods to pass in security options]. These classes are indeed not well suited for asynchronous connections. 
 
I'm curious as to why you want to create a SecureTcpClient from the accepted SecureSocket. Isn't it easier to immediately create a SecureNetworkStream from the accepted socket? Apart from the GetStream() method in the SecureTcpClient, what other methods are you using? 
 
> It appears that somewhere AsyncAcceptResult is getting 
> changed. I thought it was a problem on my end but 
> I made an effort to rule it out. Here is the patch 
 
The constraint that the async results match is a necessary constraint and should be verified; we can't simply omit it. The check is there to make sure that the async result of a BeginAccept call on one socket is not passed to the EndAccept call of another socket. 
We've never had an issue with this check in BeginAccept/EndAccept [or one of the other methods -- all the asynchronous methods do this check]. 
Can you send me a small example program that shows what's going wrong?  | 
       
      
        
          
            
              by Harmeet Bedi [harmeet at kodemuse dot com] posted on 2003/11/08 | 
              
                 | 
             
           
        
        
        
        > The SecureTcpClient and SecureTcpListener implement exactly the same 
> methods, properties and constructors as the TcpClient and 
> TcpListener classes 
 
True, except that AcceptTcpClient() that I had this code periodically 
being called with Plain Sockets to check for newly 'accepted' 
connections. 
 
if ( listener.Pending() ) 
{ 
	client = listener.AcceptTcpClient(); 
        processConnection(client); 
} 
 
This did not work because Pending uses Poll and Poll does not work for 
secure sockets.  Wanted to reuse [Secure]TcpClient based code. I was 
just using GetStream() and have changed code to not use TcpClient and 
TcpListener. So all is good except that someone else may have the same 
pattern and problem. 
 
> Can you send me a small example program that shows what's going 
> wrong? 
 
I will attempt to. Alternatively if you could provide an example of 
Asynch Server just like the Asynch Client Socket example it would help 
a lot. I am relatively new to C# so may not be following the right 
pattern etc. I am hitting a few other issues, this time with 
SocketController. 
 
On a separate but related topic, why is there sycnhronization in 
SocketController ? Is it to prevent overlapped IO ? I am getting 
overlapped IO. BeginReceive is sometimes called more than once in a 
asynch server test with concurrent multiple connections. Do you think 
there could be a lurking problem in SocketController ? 
  | 
       
      
        
          
            
              by Pieter Philippaerts [Pieter at mentalis dot org] posted on 2003/11/09 | 
              
                 | 
             
           
        
        
        
        SecureTcpListener.Pending works perfectly because there's no difference between a 'normal' listener socket and an SSL listener socket. You say it didn't work.. What exactly didn't work? 
 
I'll make sure we add an asynchronous server example when we release the next version of the library. 
 
Synchronization in the SocketController class is necessary to avoid threading issues. And no, I don't think there's a lurking problem in the SocketController.  | 
       
      
        
          
            
              by Harmeet Bedi [harmeet at kodemuse dot com] posted on 2003/11/09 | 
              
                 | 
             
           
        
        
        
        > SecureTcpListener.Pending ... What exactly didn't work? 
 
here is SecureTcpListener::Pending 
  public virtual bool Pending() { 
    if (Server == null) 
      throw new InvalidOperationException(); 
    return Server.Poll(0, SelectMode.SelectRead); 
  } 
 
Server is SecureSocket 
 
and here is SecureSocket::Poll 
 
  public override bool Poll(int microSeconds, SelectMode mode) { 
    if (SecureProtocol != SecureProtocol.None) 
        throw new NotSupportedException("The Poll method is not supported in SSL or TLS mode. Use the asynchronous methods and the Available property instead."); 
    return base.Poll(microSeconds, mode); 
  } 
 
So not sure how it would work if the underlying SecureProtocol != None. 
 
> I'll make sure we add an asynchronous server example when we release 
> the next version of the library. 
 
That would be awesome. I'll wait for the example. I may be making 
mistakes due to my lack of understanding of C#, Mentalis, Asycnh APIs 
in .NET. I will test out the server side asynchronous example as soon 
as you have it. If you have the example before release that would be 
awesome too. 
 
> Synchronization in the SocketController class is necessary to avoid 
> threading issues. 
 
Cool. I didn't see why a SocketController would be shared by multiple 
threads. In asynchronous case, I would expect application thread and 
in synchronous case there would be one to one mapping between 
Application Thread and SecureSocket and as far as I could tell there 
is one to one mapping between SecureSocket and SocketController. This 
is not really an issue for me, just curious and wanted to know the 
intent. An extra lock or two to make thing safer is good. 
  | 
       
     
 | 
 |