|
-
Jul 13th, 2007, 08:35 AM
#1
[RESOLVED] TCP_server doesn't get messages from Client?
Hi,
I'm trying to get humbling in VB2005. This time it's the use of a TCP-listener.
I need to have a conection open in order to send and recieve messages on both sides.
So far I'm using a VB6 Client(that way I know it is working) and make trials on a Server.
Connecting is OK, Sending to the Client is OK however if the client is sending it doesn't show on the desired Textbox ("Messagetraffic"), why??
The VB6 Client is tested for sending correctly!
her is my code:
Code:
Public Class Form1
Dim Listener As Net.Sockets.TcpListener
Dim thrListen As New Threading.Thread(AddressOf DoListen)
Dim client As Net.Sockets.TcpClient
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
End Sub
Private Sub Listen_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Listen.Click
Dim basePort As Integer = 1360
Listener = New Net.Sockets.TcpListener(Net.IPAddress.Loopback, basePort)
Listener.Start()
Me.Refresh()
thrListen.IsBackground = True
thrListen.Start()
End Sub
Private Sub DoListen()
Dim sr As IO.StreamReader
Do
Try
client = Listener.AcceptTcpClient
sr = New IO.StreamReader(client.GetStream)
If sr.ReadToEnd.Length > 0 Then
Me.MessageTraffic.Text = Me.MessageTraffic.Text & Environment.NewLine & sr.ReadToEnd
sr.Close()
End If
Catch
End Try
Loop
End Sub
Private Sub Senden_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Senden.Click
Dim sw As New IO.StreamWriter(Client.GetStream)
sw.Write(MessageText.Text)
Me.MessageTraffic.Text = Me.MessageTraffic.Text & Environment.NewLine & MessageText.Text
MessageText.Text = vbNullChar
sw.Flush()
End Sub
End Class
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 13th, 2007, 03:30 PM
#2
Re: TCP_server doesn't get messages from Client?
You problem is this:
Dim thrListen As New Threading.Thread(AddressOf DoListen)
and this inside of DoListen:
Me.MessageTraffic.Text = Me.MessageTraffic.Text & Environment...
Since you're running on a seperate thread, "Me" and "MessageTraffic" aren't immediately visible and considered not "thread-safe." Here's the code for the listener you'll end up using:
Code:
Private tcpListener As Net.Sockets.TcpListener
Private thrdListen As Threading.Thread
Private Delegate Sub SetTextCallback(ByVal text As String)
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
tcpListener = New Net.Sockets.TcpListener(Net.Dns.GetHostEntry(My.Computer.Name).AddressList(0), 1360)
thrdListen = New Threading.Thread(AddressOf ListenPort)
End Sub
Private Sub Form1_FormClosing(ByVal sender As Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing
thrdListen.Abort()
tcpListener.Stop()
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
tcpListener.Start()
thrdListen.Start()
End Sub
Public Sub SetText(ByVal text As String)
If Me.TextBox1.InvokeRequired Then
Dim d As New SetTextCallback(AddressOf SetText)
Me.Invoke(d, New Object() {[text]})
Else
Me.TextBox1.Text = [text]
End If
End Sub
Public Sub ListenPort()
Dim buffer(1000) As Byte
SyncLock Threading.Thread.CurrentThread
While Not Threading.Thread.CurrentThread.ThreadState = Threading.ThreadState.AbortRequested
If tcpListener.Pending Then
tcpListener.AcceptSocket.Receive(buffer)
SetText(System.Text.ASCIIEncoding.ASCII.GetString(buffer).Trim)
End If
End While
End SyncLock
End Sub
And since I have it, here's the writer:
Code:
Private tcpRemoteSocket As Net.Sockets.TcpClient
Private bufferWriter As IO.BinaryWriter
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
tcpRemoteSocket = New Net.Sockets.TcpClient
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Try
tcpRemoteSocket.Connect(My.Computer.Name, 1360)
bufferWriter = New IO.BinaryWriter(tcpRemoteSocket.GetStream)
bufferWriter.Write(Me.TextBox1.Text)
bufferWriter.Flush()
Catch ex As Exception
Stop
Finally
bufferWriter.Close()
End Try
End Sub
For all the details you could every ask for and more on thread-safe calls, check out the article:
http://msdn2.microsoft.com/en-us/lib...28(VS.80).aspx
-
Jul 16th, 2007, 07:18 AM
#3
Re: TCP_server doesn't get messages from Client?
Thanks sevenhalo,
although I haven't got it to do what I want, I see the point on how the cross-threat information is handled.
Since the TCP connection is only half of my problem could you do me a favour and post the code you had for the UDP-example you used in post #10 of this thread
HTML Code:
http://www.vbforums.com/showthread.php?t=412281&highlight=UDPClient
Only if you still have it!! Thanks anyway, my rating is on the way!
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 16th, 2007, 03:52 PM
#4
Re: TCP_server doesn't get messages from Client?
I can't get it work
This is my actual code:
Code:
Public Class MainForm
Dim Listener As Net.Sockets.TcpListener
Dim thrListen As New Threading.Thread(AddressOf DoListen)
Dim client As Net.Sockets.TcpClient
Private Delegate Sub SetTextCallback(ByVal text As String)
Private Sub MainForm_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
'Button1 is starting the Listener
Dim basePort As Integer = 1360
Listener = New Net.Sockets.TcpListener(Net.IPAddress.Loopback, basePort)
Listener.Start()
Me.Refresh()
'thrListen.IsBackground = True
thrListen.Start()
End Sub
Private Sub DoListen()
Dim sr As IO.StreamReader
Do
SyncLock Threading.Thread.CurrentThread
While Not Threading.Thread.CurrentThread.ThreadState = Threading.ThreadState.AbortRequested
If Listener.Pending Then
client = Listener.AcceptTcpClient
'listener.AcceptSocket.Receive(Buffer)
sr = New IO.StreamReader(client.GetStream)
'If sr.ReadToEnd > 0 Then
SetText(sr.ReadToEnd)
'End If
sr.Close()
End If
End While
End SyncLock
Loop
End Sub
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
'Button2 is sending the TextBox1.Text!
Dim sw As New IO.StreamWriter(client.GetStream)
sw.Write(TextBox1.Text)
Me.TextBox2.Text = Me.TextBox2.Text & Environment.NewLine & TextBox1.Text
TextBox1.Text = vbNullChar
sw.Flush()
End Sub
Private Sub MainForm_FormClosing(ByVal sender As Object, ByVal e As System.Windows.Forms.FormClosingEventArgs) Handles Me.FormClosing
thrListen.Abort()
Listener.Stop()
End Sub
Public Sub SetText(ByVal text As String)
If Me.TextBox2.InvokeRequired Then
Dim d As New SetTextCallback(AddressOf SetText)
Me.Invoke(d, New Object() {[text]})
Else
Me.TextBox2.Text = [text]
End If
End Sub
End Class
The connecting and sending part is working, however I don't recieve te messages from the client during the lifetime of the connection. Only if the client closes, the messages are printed onto TextBox2!
Using a breakpoint in DoListen, it only gets hit until the connection is made, after that not any more!???
Last edited by opus; Jul 16th, 2007 at 03:58 PM.
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 16th, 2007, 04:30 PM
#5
Re: TCP_server doesn't get messages from Client?
Here's a thread that has some useful UDP stuff in it, though I got a bit pissed at the asker by the end of it:
http://www.vbforums.com/showthread.p...ight=UDPClient
The code Atheist put in there is a compact example of the use of UDP, while I have a more complicated, though stripped down class that I am using for sending and receiving through different ports using two differernt sockets. I removed a whole lot of app specific code from what I posted, but I don't think I took out anything that would break the class.
Can't look at the main question now, but if I read it right, the thing is pretty nearly working as is, with the exception that the message doesn't actually show up in TextBox2 until the connection closes, but at that time, it does show up properly?
My usual boring signature: Nothing
 
-
Jul 16th, 2007, 04:40 PM
#6
Re: TCP_server doesn't get messages from Client?
Yes, after the connection is closed by the client, all the messages are shown correctly, however I need them while the connection is established. It's for a gametype thing, the TCP connection is for single messages (like changes in behaviour), the UDP connection will be used for the broacast of the actual "whole" situation.All connections should be kept established!
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 16th, 2007, 04:45 PM
#7
Re: TCP_server doesn't get messages from Client?
If you were to put a breakpoint on the Invoke line in SetText(), when is it hit?
I haven't used Invoke, as my threads have never yet needed to deal with any UI controls, which is an option for you, but Invoke is there for that specific reason, so going around it makes no real sense. I have a couple ideas as to what is going on, but they depend on when Invoke is actually being called, whether it is right away (the data is in the control, but isn't being displayed), or after the connection closes (the data is never making it to the control). It should be the former.
My usual boring signature: Nothing
 
-
Jul 17th, 2007, 12:22 AM
#8
Re: TCP_server doesn't get messages from Client?
 Originally Posted by Shaggy Hiker
I haven't used Invoke, as my threads have never yet needed to deal with any UI controls, which is an option for you,
That last part of this sentence of yours is ringing a bell. Actually I don't need the information being displayed directly on a control, I'm using it this way only in a sort of testing software because I don't want to test "networking" in my game-thing.
In there I will send data that is normally held in global variables, like positions of objects or there behaviour (course, speed, use of equipment etc.) . Of course those values will end up being used to make a display.
On the test for the invoke, I have to delay that until this evening (European time). Thanks anyway!
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 17th, 2007, 09:12 AM
#9
Re: TCP_server doesn't get messages from Client?
You could create a SynchronizationContext object as a form member, and set it to SynchronizationContext.Current in the form load event. You can then use this to to call a sub on that synch context, which will be the UI thread. This is roughly similar to Invoke, but works for subs which don't deal with Invoke. I'm currently using that to raise events from a UDP class, and it works nicely.
My usual boring signature: Nothing
 
-
Jul 17th, 2007, 12:49 PM
#10
Re: TCP_server doesn't get messages from Client?
 Originally Posted by Shaggy Hiker
If you were to put a breakpoint on the Invoke line in SetText(), when is it hit?
Only when closing the connection from the client side the invoke is called.
Regarding the "SynchronizationContext object" I have idea what that is.
I just figured following:
If I close the connection from the client after sending, the message gets thru, I could reconnect just after that, however this shouldn't be the correct way!
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 17th, 2007, 06:15 PM
#11
Re: TCP_server doesn't get messages from Client?
Ok, ignore that stuff about the synchronization context, since the delay is happening prior to Invoke that suggestion is irrelevant.
I've been looking over some code I wrote a couple years back, which is the only time I have ever used TCP that I can remember. My code is very similar to yours, and it is somewhat hard to say where the difference lies. I use this code to read from the stream (my stream is called netStream, but it is no different from yours):
vb Code:
If netStream.DataAvailable Then
recCount = netStream.Read(recBuff, 0, recBuff.GetLength(0))
End If
where recCount is the number of bytes read, and recBuff is an array of Bytes. I was using a size of 1025, but for odd reasons.
The whole code was set up in a separate thread which created an instance of a class to wrap the TCPClient. The thread looped waiting for GetConnection to return True. GetConnection() is virtually the same code as yours, though I note that once I had the stream, I stopped the listener. I could do this because there was never going to be more than one-to-one connections in this app.
Once GetConnection confirmed that there was a connection, then I had a Send and Receive function that was all dealt with by the thread. The only difference in reading is as I noted earlier, and I only mention that there was a Send and Receive because the thread did a series of sends then receives. It sounds like your code never gets past that first receive, so mine is working despite the differences between the two being quite trivial.
You might try that Read method for reading from the stream. At the very least, you would be able to put a breakpoint in the code and watch to see that the buffer was actually filled.
My usual boring signature: Nothing
 
-
Jul 18th, 2007, 12:26 AM
#12
Re: TCP_server doesn't get messages from Client?
I'll try that read example, but where did you put that peace of code?
In your GetConnection?, my equivilant to that doesn't get hit using a breakpoint after the connection is made????. Where else would the .DataAvailabel be checked?
Maybe there should be another thread doing the reading, besides the one for getting the connection?
And again , can only test it later!
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 18th, 2007, 06:37 PM
#13
Re: TCP_server doesn't get messages from Client?
Here's the whole GetConnection function:
vb Code:
Public Function GetConnection() As Boolean
Try
If curListen.Pending Then
lSock = curListen.AcceptTcpClient
lSock.LingerState = linOpt
netStream = lSock.GetStream
curListen.Stop()
GetConnection = True
Else
GetConnection = False
End If
Catch ex As Exception
GetConnection = False
End Try
End Function
The linger state seems like it shouldn't have any impact on your situation, as it deals with whether writing is finished when a call comes to close the connection. This whole thing is called on a background thread, but all the reading and writing is also done on this background thread using the stream held in netStream.
From what you are saying, it sounds like the reading and writing that I do after the call to GetConnection would never occur in your scenario because you never move on from the GetStream call.
If you were to put a breakpoint on this line:
client = Listener.AcceptTcpClient
then step forward through the code, does it go anywhere after you get the stream?
My usual boring signature: Nothing
 
-
Jul 19th, 2007, 01:06 AM
#14
Re: TCP_server doesn't get messages from Client?
Good morning Shaggy,
sorry I didn't have time to check on your last two suggestions last night (I was only working on the somewhat related thread from Rack http://www.vbforums.com/showthread.php?t=478000).
One question I do have, since Rack has an TCPListener which is working (at least for sending/receiving) I checked the differences to mine, and one thing I found is the different stream. He is using a "System.Net.Sockets.NetworkStream" while I'm using "IO.StreamReader", maybe my problem is there? Which Stream are you using, can'T see that in the code posted.
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 19th, 2007, 03:24 PM
#15
Re: TCP_server doesn't get messages from Client?
Did some testing with the breakpoint at this line
Code:
client = Listener.AcceptTcpClient
When the client connects, the breapoint fires, stepping with F8 will run the lines
Code:
sr = New IO.StreamReader(client.GetStream)
Messagetext = sr.ReadToEnd
after this one the Form is shown again, only when disconnecting the next line will be done
Code:
SetText(Messagetext)
any clue on that one?
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
-
Jul 19th, 2007, 04:20 PM
#16
Member
Re: TCP_server doesn't get messages from Client?
Just posted an attachment on rack's post, it is a sample that works?
http://www.vbforums.com/attachment.p...1&d=1184878571
Hop it helps
-
Jul 19th, 2007, 04:44 PM
#17
Re: TCP_server doesn't get messages from Client?
Looks like I am using the NetworkStream, too:
Private netStream As System.Net.Sockets.NetworkStream
Having read up a bit on both techniques, there is only one line which suggests that this could be an issue ("By default, a StreamReader is not thread safe."), but there is no clear reason why streamreader would not work, or would fail in this fashion. It does appear that NetworkStream is intended for this specific purpose, but there is no statement as to why it would necessarily be superior.
After poking around a bit more, it looks like GetStream will return a NetworkStream object. I'm surprised that you could convert that to a streamreader without a cast of some sort, but it makes me even more suspicious that the problem might lie there. Do you have Option Strict On?
This seems like it might be a very subtle threading issue related to StreamReader, but I haven't found anything definitive in that direction.
My usual boring signature: Nothing
 
-
Jul 20th, 2007, 12:56 AM
#18
Re: TCP_server doesn't get messages from Client?
@Shaggy Hiker:
I'll look into this issue (NetworkStream vc. Streamreader) during my holiday. We are leaving for two weeks vacation in Denmark, so you won't get any answer from me for next couple of days. Thanks a lot so far.
@thered:
Thanks, I'll look into that example as well.
You're welcome to rate this post!
If your problem is solved, please use the Mark thread as resolved button
Wait, I'm too old to hurry!
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|