views:

138

answers:

3

I have a TCP client connecting to my server which is sending raw data packets. How, using Boost.Asio, can I get the "whole" packet every time (asynchronously, of course)? Assume these packets can be any size up to the full size of my memory.

Basically, I want to avoid creating a statically sized buffer.

+1  A: 

TCP doesn't operate with packets. It provides you one contiguous stream. You can ask for the next N bytes, or for all the data received so far, but there is no "packet" boundary, no way to distinguish what is or is not a packet.

jalf
Then what's wireshark showing?
Clark Gaebel
The underlying packets. TCP is implemented on top of the IP protocol, which is packet-based. But those packets are an internal implementation detail. They are not seen by the application.
jalf
+1  A: 

typically, when you do async IO, your protocol should support it. one easy way is to prefix a byte array with it's length at the logical level, and have the reading code buffer up until it has a full buffer ready for parsing.

if you don't do it, you will end up with this logic scattered all over the place (think about reading a null terminated string, and what it means if you just get a part of it every time select/poll returns).

Omry
Haha, this was actually already done - I wondered why there was a packet header! I thought it was all handled by the TCP protocol - guess I was wrong.
Clark Gaebel
yes, as jalf mentioned - tcp presents a stream to the application, not packets. so you need to logically separate your packets.
Omry
A: 

Typically when you build a custom protocol on the top of TCP/IP you use a simple message format where first 4 bytes is an unsigned integer containing the message length and the rest is the message data. If you have such a protocol then the reception loop is as simple as below (not sure what is ASIO notation, so it's just an idea)

for(;;) {
  uint_32_t len = 0u;
  read(socket, &len, 4);
  len = ntohl(len);
  assert (len < my_max_len);
  char* buf = new char[len];
  read(socket, buf, len);
  ...
}
bobah