Jump to content
Xtreme .Net Talk

Recommended Posts

Posted

We've got a thread in our application that does work.

 

If we need to make changes on the fly, we stop the thread by calling it's Abort() call, change settings to the parameters, and restart the thread.

 

The problem is, whenever we call Abort() on the thread, sometimes it just doesn't abort! I found this out when I put a "While (MyThread.ThreadState <> ThreadState.Stopped)" Loop into my routine, and it never returned.

 

How do I get the thread to stop, and really stop, so that I can make changes to the settings it uses and then restart the thread?

Posted (edited)
Does this help?
  Private m_thTCP As Thread
 Private m_listener As TcpListener
 Public Sub New()
   InitializeComponent() ' This call is required by the Windows Form Designer.
   m_thTCP = New Thread(AddressOf TCPServer)
   ThreadStart()
 End Sub
 Private Sub Form1_FormClosing(ByVal sender As Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing
   ThreadStop()
 End Sub
 Private Sub Restart_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles RestartButton.Click
   ThreadRestart()
 End Sub
 Private Sub ThreadStop() ' Stopping TCP Listener Service
   Try
     If (m_thTCP.ThreadState <> ThreadState.Stopped) Then
       Dim i As Int16 = 0
       m_listener.Stop()
       Application.DoEvents()
       Thread.Sleep(200)
       While ((i < 100) And (m_thTCP.ThreadState <> ThreadState.Stopped)) ' gives thread 5 secs to stop!
         m_thTCP.Abort()
         Application.DoEvents()
         Thread.Sleep(50)
         i += 1
       End While
     End If
   Catch ex As Exception
     MsgBox(ex.Message)
   Finally
     Console.WriteLine("ThreadState is {0}", m_thTCP.ThreadState.ToString())
     m_thTCP = Nothing
   End Try
 End Sub
 Public Sub ThreadRestart() ' Restarting TCP Listener Service
   Try
     ThreadStop()
     m_thTCP = New Thread(AddressOf TCPServer)
     ThreadStart()
   Catch ex As Exception
     MsgBox(ex.Message)
   End Try
 End Sub
 Private Sub ThreadStart()
   Try
     m_thTCP.Start()
   Catch ex As Exception
     MsgBox(ex.Message)
   End Try
 End Sub
 Private Sub TCPServer()
   Try ' Starting TCP Listener from thread
     m_listener = New TcpListener(IPAddress.Any, m_port)
     m_listener.Start()
     While True
       Dim client As TcpClient = m_listener.AcceptTcpClient() ' Waits until data is available on the network
       Dim stream As NetworkStream = client.GetStream()
       Dim bytes(client.ReceiveBufferSize) As Byte
       stream.Read(bytes, 0, CInt(client.ReceiveBufferSize))
       Dim data As String = Encoding.ASCII.GetString(bytes)
       data = data.TrimEnd(data.Substring(data.Length - 1))
       If (data.Substring(3) <> String.Empty) Then
         Dim item As String = data.Substring(3)
         If (item <> "") Then
           Console.WriteLine("Data Read: {0}", item)
         End If
       End If
       stream.Close()
       client.Close()
     End While
   Catch ex2 As SocketException
     Console.WriteLine("SocketException: {0}", ex2)
   Catch ex1 As ThreadAbortException ' dismiss this one
     Exit Sub
   Catch ex As Exception
     MsgBox(ex.Message)
   Finally
     Try
       m_listener.Stop()
     Catch ex As Exception ' Throws Exception if it never was opened
     End Try
   End Try
 End Sub

Edited by joe_pool_is
Posted

This line:

 

Dim client As TcpClient = m_listener.AcceptTcpClient() ' Waits until data is available on the network

 

is a blocking call. You even put a comment there to signify that it waits.

 

An ugly way to cancel the blocking call would be to call m_listener.Close() in the ThreadStop() method.

 

But, my recommendation would be to forgo threading in this case and use asynchronous callbacks, which are internally managed threads anyway. Use the BeginAcceptTcpClient method of TcpClient.

 

Another tip, when writing debug information, include the namspace System.Diagnostics and use the Debug class.

Posted

One of the things I like about forums is when they give me ideas I hadn't considered. You gave me 2 new ideas here that I've never used, and I suppose it is about time that I add them to the list of tricks I know.

 

One was asynchronous callbacks. I had seen BeginAcceptTcpClient and EndAcceptTcpClient methods in the TcpClient class, but couldn't see any reason that I'd want to use them. I'll be looking into this ...second thing!

 

First thing is the second thing you showed me, which was the System.Diagnostics namespace and the Debug class. I've never used them, so I'll be Googling shortly for an example on how to use it.

 

Thanks Diesel. I appreciate your time.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...