PDA

Click to See Complete Forum and Search --> : Understanding packet arrival


Cowboy
Feb 11th, 2009, 08:54 AM
Hows it goin yall, i've got an issue with retrieving info via tcp/ip using the winsock control. Basically i'm trying to understand if I need to check packet length for an incomplete packet.

I have a server accepting multiple clients. Under the dataArrival sub on the server, I'm trying to understand how to interpret the incoming data.

So far I know to add delimiters to each message to break up the data...I know how to process this. But what happens when the string that is read in (with getData) has an incomplete message on the end? Could that happen and how do I handle that?

Let me give you an example in case this didn't make sense:

Delimiter is ':'

In dataArrival, sock1.GetData retrieves a string "msg1:msg2:msg3:ms" with 'msg4:' cut off. Could that happen? and if so, how would I go about handling getting the rest of the message and forming a whole message.

Atheist
Feb 11th, 2009, 10:10 AM
First off it is crucial to have the terminology right.
You are not receiving incomplete packets. Packets are dealt with at a much lower level in the networking layer.
When data is sent from a host, its computer will chop up the data in Tcp segments, and then into IP packets, which are then sent out into the network. As soon as you read from the socket in your application, all the data from the currently received packets are returned to your application. If all packets have not arrived yet, you wont get it all. You'll just have to keep reading until you do.
Thats basically how it works without going into all the details.

If the incoming message doesnt end with a colon (":"), you'll know that there is data that havent yet arrived.

AgentSmithers
Feb 11th, 2009, 11:59 AM
Yes The Gentelmen above is correct! You receive what I believe is know as frames which is Higher up in the OSI Model then TCP Segments. THat is what Triggers your DataArrival events \ Recv functions. If your using TCP keep in mind it is a STREAM Protocall and is not Message Oriented. meaning if you send "Hello" the remote computer may only get "He" on the first event then "llo" on the 2nd Event \ Recv, so yes put a Non-Normaly used char such as chr(255) or something you would not normaly type so when the other side recv's it, it can check for the end of the message then Parse the information then take action.

This is code that I love to use as an example on how to handle Data with TCP

vb6
Private Sub FileManagerSocket_DataArrival(ByVal Index As Variant, ByVal bytesTotal As Long)
FileManagerSocket.GetData Index, Data, vbString
'Data
'Data EOF
'Data EOF Data
'Data EOF Data EOF
'EOF Data
'EOF Data EOF
'EOF Data EOF Data
'EOF
'Must Write Code To Wrap All These Cases
If InStr(Data, Chr(255)) = bytesTotal Then
M_FileManager.HandleData Index, FileManagerSocketBuffer & Left$(Data, Len(Data) - 1), vbString 'Take Off The EOT
FileManagerSocketBuffer = vbNullString
ElseIf InStr(Data, Chr(255)) = 0 Then
FileManagerSocketBuffer = FileManagerSocketBuffer & Data
Debug.Print "Got Chunk Of Message"
Else
Dim ParseMsg() As String
ParseMsg = Split(Data, Chr(255))

For i = 0 To UBound(ParseMsg) - 1

M_FileManager.HandleData Index, FileManagerSocketBuffer & ParseMsg(i), vbString 'Take Off The EOT
FileManagerSocketBuffer = vbNullString

Next

FileManagerSocketBuffer = ParseMsg(i + 1) 'Store Last incomplete Chunk in the buffer
Debug.Print "Got Full Message Plus Extra For Next Message"
End If
Debug.Print Replace(Data, Chr(255), "(EOT)")
End Sub

as you can see the following Data Arrival events are possible

'Data
'Data EOF
'Data EOF Data
'Data EOF Data EOF
'EOF Data
'EOF Data EOF
'EOF Data EOF Data
'EOF

seeing you can get Multiple Messages at once or Multiple Messages + Chunks of another incomming message, Use a Global buffer to store the last Chunk before you exit the DataArrival Functions and lose the Data, FileManagerSocketBuffer being my Public Var!

CVMichael
Feb 11th, 2009, 12:27 PM
Don't use delimiters to send data... what if you have the delimiter as part of the data ?

Just send the length of the data you are about to send, then send it... on receiving side, read the length, then you know how much data to buffer until the whole thing is done.

See here how it's done: VB - How to send a file using the Winsock control (http://www.vbforums.com/showthread.php?t=377648)

AgentSmithers
Feb 11th, 2009, 01:48 PM
Yes I neglected to mentioned that Mine is only for Text/String Data Only, Binary Information my methed will not work.

dbasnett
Feb 11th, 2009, 02:50 PM
how is this being written? "msg1:msg2:msg3"

tcp can segment datagram's that will not fit in the underlying (IP) packet.

AgentSmithers
Feb 13th, 2009, 11:59 AM
Ummm as a Note do not use ":" as a deliminator its very much possible that it will be used due to it being a char on a keyboard unless you can be for sure that it wont ever be used unlike chr(255).

and TCP has nothing to do with the HEader IP above it when sending messages If Im reading your question correctly.

when a "Packet" is sent which you have little control over when doing TCP in Vb due to Service pack2 restrictions and whatnot it sends a Eth Header, IP Header and a TCP Header all concat'ed if that makes sence to you. if the packet is bigger then a certain size in today's standard its 1500 Bytes also known as the Maximum Transmission Unit (MTU) the packet will be split up then reassembled on the other side. Hoply this is what info you where looking for :wave:

dbasnett
Feb 13th, 2009, 03:33 PM
on 10/100 ethernets the frame from preamble to preamble is 1538 bytes. from the end of Ethertype/Length to the beginning of the CRC can be 1500 bytes maximum. from the 1500 you have 20+ bytes of overhead for IP. so the max user data is 1480.

using pings and sniffers on my local machine the most i have ever been able to get in the packet is 1472.

Cowboy
Feb 14th, 2009, 05:18 PM
Thanks for the reply's yall.

I guess what I need to ask is about dataarrival. This is called once something has arrived but what if the sub is still being processed when more data arrives? does it wait until the sub is exited and then jump into it again before starting a new sub? or does it just process it as if they are two different subs running simutaneously?

Also GetData returns whats in the buffer, but when does vb write to the buffer? as soon as it's received, or at the beggining of dataarrival sub?

My trouble is that i'm not sure how the flow of incoming data work from time its received to after it is processed. Can anyone give me a basic timeline of events?

AgentSmithers
Feb 16th, 2009, 05:31 PM
Ah your talking about Async Data event Arrival, In vb6 it is Handled I believe.. I BELIEVE WSAAync Window Messages and In that case through a Message pump which is handled through a Single Thread, Once it get's the Messages it will Start a new thread and Process the Data and will not look for new Data UNTIL the prev sub has finished. this may be 90% correct I may be off if its not handled through window messages but as for getting both subs running at once no, not endless you mess with the Underlying socket with Windows socket API. Umm as for the buffer question I don't really follow you but, using GetData moves Data from the Socket Buffer to a Buffer of your choice more then likely a String/Byte array. and by the example Ive given you, you want to move it to a Buffer that's Publicly Allocated so when the Sub returns with another TCP Segment it can Append to it finishing the End of the Message then when you find that its a finished / Complete Message you can then process it =)

Cowboy
Feb 17th, 2009, 07:07 AM
beautiful I love it. I'll give it a try