Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. C#
  4. Newbie threading questions (data exchange + shutdown)

Newbie threading questions (data exchange + shutdown)

Scheduled Pinned Locked Moved C#
questionsysadminhelptutorialworkspace
6 Posts 3 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • M Offline
    M Offline
    Metal76
    wrote on last edited by
    #1

    I'm writing a simple multi-threaded TCP socket server, in which a new thread is created for each incoming connection (I only have to handle few connection so this should be ok). It is something like this:

    static void Main(string[] args)
    {
    ...

    // Setup server socket
    TcpListener listener = new TcpListener(IPAddress.Any, servPort);
    listener.Start();
    
    while(true)
    {
      try
      {
          // Block waiting for connection
          Socket clntSock = listener.AcceptSocket();
    
          // Connection detected: launch worker thread
          MyProtocol protocol = new MyProtocol();
          Thread thread = new Thread(new ThreadStart(protocol.HandleClient));
          thread.Start();
      }
      catch (System.IO.IOException e)
      {
          // Perform error handling
          ...
      }
    }    
    

    }

    public class MyProtocol
    {
    public void HandleClient()
    {
    // Code to handle incoming data from client
    ...
    }
    }

    I have several newbie questions: 1) How can I access data living in the worker threads? I was thinking to use properties in MyProtocol class for this purpose, like:

    public class MyProtocol
    {
    // Value used inside HandleClient()
    public int Data
    {
    get { return _Data; }
    set { _Data = value; }
    }
    private int _Data;

    public void HandleClient() {...}
    

    }

    The main thread keeps a reference to the MyProtocol objects created, and uses the Data property to exchange data with the thread (with appropriate synchronization using lock to avoid race conditions). Is this ok? Is there any better approach? 2) Which is the correct way to shut down the connection threads? For example, if I want to close the server application, I think I should deal with terminating the connections in a correct manner. Best regards, Andrea

    N N 2 Replies Last reply
    0
    • M Metal76

      I'm writing a simple multi-threaded TCP socket server, in which a new thread is created for each incoming connection (I only have to handle few connection so this should be ok). It is something like this:

      static void Main(string[] args)
      {
      ...

      // Setup server socket
      TcpListener listener = new TcpListener(IPAddress.Any, servPort);
      listener.Start();
      
      while(true)
      {
        try
        {
            // Block waiting for connection
            Socket clntSock = listener.AcceptSocket();
      
            // Connection detected: launch worker thread
            MyProtocol protocol = new MyProtocol();
            Thread thread = new Thread(new ThreadStart(protocol.HandleClient));
            thread.Start();
        }
        catch (System.IO.IOException e)
        {
            // Perform error handling
            ...
        }
      }    
      

      }

      public class MyProtocol
      {
      public void HandleClient()
      {
      // Code to handle incoming data from client
      ...
      }
      }

      I have several newbie questions: 1) How can I access data living in the worker threads? I was thinking to use properties in MyProtocol class for this purpose, like:

      public class MyProtocol
      {
      // Value used inside HandleClient()
      public int Data
      {
      get { return _Data; }
      set { _Data = value; }
      }
      private int _Data;

      public void HandleClient() {...}
      

      }

      The main thread keeps a reference to the MyProtocol objects created, and uses the Data property to exchange data with the thread (with appropriate synchronization using lock to avoid race conditions). Is this ok? Is there any better approach? 2) Which is the correct way to shut down the connection threads? For example, if I want to close the server application, I think I should deal with terminating the connections in a correct manner. Best regards, Andrea

      N Offline
      N Offline
      N a v a n e e t h
      wrote on last edited by
      #2

      Metal76 wrote:

      The main thread keeps a reference to the MyProtocol objects created, and uses the Data property to exchange data with the thread (with appropriate synchronization using lock to avoid race conditions). Is this ok? Is there any better approach?

      Yeah. This would be OK.

      Metal76 wrote:

      Which is the correct way to shut down the connection threads?

      I would add a Stop() method to MyProtocol class. See the below example

      volatile bool canContinue = true;
      public void HandleClient(){
      while(canContinue){
      ......
      }
      }

      public void Stop(){
      canContinue = false;
      }

      You need to call Stop on all the MyProtocol instances created. Alternatively, you can make the thread as background.

      MyProtocol protocol = new MyProtocol();
      Thread thread = new Thread(new ThreadStart(protocol.HandleClient));
      thread.IsBackground = true;
      thread.Start();

      So it ends when the main thread ends. But the first one would be the better choice.

      M 1 Reply Last reply
      0
      • N N a v a n e e t h

        Metal76 wrote:

        The main thread keeps a reference to the MyProtocol objects created, and uses the Data property to exchange data with the thread (with appropriate synchronization using lock to avoid race conditions). Is this ok? Is there any better approach?

        Yeah. This would be OK.

        Metal76 wrote:

        Which is the correct way to shut down the connection threads?

        I would add a Stop() method to MyProtocol class. See the below example

        volatile bool canContinue = true;
        public void HandleClient(){
        while(canContinue){
        ......
        }
        }

        public void Stop(){
        canContinue = false;
        }

        You need to call Stop on all the MyProtocol instances created. Alternatively, you can make the thread as background.

        MyProtocol protocol = new MyProtocol();
        Thread thread = new Thread(new ThreadStart(protocol.HandleClient));
        thread.IsBackground = true;
        thread.Start();

        So it ends when the main thread ends. But the first one would be the better choice.

        M Offline
        M Offline
        Metal76
        wrote on last edited by
        #3

        Hi Navaneeth, thanks for fast and really useful reply! I have an additional doubt regarding thread shutdown. At the moment, the HandleClient() is something like this:

        void HandleClient()
        {
        ...

        // Block until data is available from socket or client disconnected
        while ((recvMsgSize = clntSock.Receive(rcvBuffer, 0, rcvBuffer.Length, SocketFlags.None)) > 0)
        {
        // Process received data
        ...
        }

        // Client disconnected, return from function --> terminate thread
        }

        So when shutting down the application I'd like to shutdown any active client connection and release any network resource. In order to use your solution (polling the canContinue flag) I think I should avoid blocking calls like the socket Receive() one. Am I right? And can you suggest a "graceful" way to shutdown alive connections? Thanks in advance and regards, Andrea

        N 1 Reply Last reply
        0
        • M Metal76

          Hi Navaneeth, thanks for fast and really useful reply! I have an additional doubt regarding thread shutdown. At the moment, the HandleClient() is something like this:

          void HandleClient()
          {
          ...

          // Block until data is available from socket or client disconnected
          while ((recvMsgSize = clntSock.Receive(rcvBuffer, 0, rcvBuffer.Length, SocketFlags.None)) > 0)
          {
          // Process received data
          ...
          }

          // Client disconnected, return from function --> terminate thread
          }

          So when shutting down the application I'd like to shutdown any active client connection and release any network resource. In order to use your solution (polling the canContinue flag) I think I should avoid blocking calls like the socket Receive() one. Am I right? And can you suggest a "graceful" way to shutdown alive connections? Thanks in advance and regards, Andrea

          N Offline
          N Offline
          N a v a n e e t h
          wrote on last edited by
          #4

          It depends from where you are calling Stop() method. If it is called from main thread, you can shutdown the socket inside the Stop() method. I am not sure that this is the graceful way.

          Navaneeth How to use google | Ask smart questions

          1 Reply Last reply
          0
          • M Metal76

            I'm writing a simple multi-threaded TCP socket server, in which a new thread is created for each incoming connection (I only have to handle few connection so this should be ok). It is something like this:

            static void Main(string[] args)
            {
            ...

            // Setup server socket
            TcpListener listener = new TcpListener(IPAddress.Any, servPort);
            listener.Start();
            
            while(true)
            {
              try
              {
                  // Block waiting for connection
                  Socket clntSock = listener.AcceptSocket();
            
                  // Connection detected: launch worker thread
                  MyProtocol protocol = new MyProtocol();
                  Thread thread = new Thread(new ThreadStart(protocol.HandleClient));
                  thread.Start();
              }
              catch (System.IO.IOException e)
              {
                  // Perform error handling
                  ...
              }
            }    
            

            }

            public class MyProtocol
            {
            public void HandleClient()
            {
            // Code to handle incoming data from client
            ...
            }
            }

            I have several newbie questions: 1) How can I access data living in the worker threads? I was thinking to use properties in MyProtocol class for this purpose, like:

            public class MyProtocol
            {
            // Value used inside HandleClient()
            public int Data
            {
            get { return _Data; }
            set { _Data = value; }
            }
            private int _Data;

            public void HandleClient() {...}
            

            }

            The main thread keeps a reference to the MyProtocol objects created, and uses the Data property to exchange data with the thread (with appropriate synchronization using lock to avoid race conditions). Is this ok? Is there any better approach? 2) Which is the correct way to shut down the connection threads? For example, if I want to close the server application, I think I should deal with terminating the connections in a correct manner. Best regards, Andrea

            N Offline
            N Offline
            Nicholas Butler
            wrote on last edited by
            #5

            Hi Andrea, You should use one of the asynchronous patterns available on Socket: either BeginReceive or the new ReceiveAsync. It is not necessary ( or beneficial ) to create a thread for each connection. BeginReceive[^] ReceiveAsync[^], good example[^] In answer to your questions: 1) To pass the received data to your main thread, MyProtocol should publish an event which it raises when a whole useful "message" has been received. 2) To handle application shutdown, keep a list of open sockets in MyProtocol and expose a method that, for each socket, sends any command messages required by the protocol to end the connection, and then calls Shutdown and Dispose on the Socket. Nick

            ---------------------------------- Be excellent to each other :)

            M 1 Reply Last reply
            0
            • N Nicholas Butler

              Hi Andrea, You should use one of the asynchronous patterns available on Socket: either BeginReceive or the new ReceiveAsync. It is not necessary ( or beneficial ) to create a thread for each connection. BeginReceive[^] ReceiveAsync[^], good example[^] In answer to your questions: 1) To pass the received data to your main thread, MyProtocol should publish an event which it raises when a whole useful "message" has been received. 2) To handle application shutdown, keep a list of open sockets in MyProtocol and expose a method that, for each socket, sends any command messages required by the protocol to end the connection, and then calls Shutdown and Dispose on the Socket. Nick

              ---------------------------------- Be excellent to each other :)

              M Offline
              M Offline
              Metal76
              wrote on last edited by
              #6

              Thanks Nick, great suggestion! I have to work with a console application and I thought an event-based solution would not fit, but now I think I'll reconsider the whole approach. Regards, Andrea

              1 Reply Last reply
              0
              Reply
              • Reply as topic
              Log in to reply
              • Oldest to Newest
              • Newest to Oldest
              • Most Votes


              • Login

              • Don't have an account? Register

              • Login or register to search.
              • First post
                Last post
              0
              • Categories
              • Recent
              • Tags
              • Popular
              • World
              • Users
              • Groups