0

I'm trying to learn the basics of TCP (and hopefully soon UDP) to make some multi-client applications. I've noticed that every example I've seen has a buffer like so:

            serverStream = clientSocket.GetStream();
            byte[] inStream = new byte[10025];
            serverStream.Read(inStream, 0, clientSocket.ReceiveBufferSize);
            string returndata = System.Text.Encoding.ASCII.GetString(inStream);

I notice it always has a set size for the byte buffer and am curious as to whether this is a requirement/better way of doing things and why this is better than what I wrote:

            serverStream = clientSocket.GetStream();
            byte[] inStream = new byte[clientSocket.ReceiveBufferSize];
            serverStream.Read(inStream, 0, clientSocket.ReceiveBufferSize);
            string returndata = System.Text.Encoding.ASCII.GetString(inStream);
Dom Hall
  • 53
  • 9
  • The power of the Internet to spread information, both good and bad, is truly amazing. – Eric J. Dec 14 '15 at 20:10
  • You never use the `int` returned from `Read` this is a bug that will bite you. `Read` will only read **up to** `clientSocket.ReceiveBufferSize` bytes, you need to check the returned value to see how many bytes where actually read. You will likely need to loop and keep reading over and over till you read all the bytes you expected to read. How do you know how many bytes you expect to read? [Message framing](http://blog.stephencleary.com/2009/04/message-framing.html) – Scott Chamberlain Dec 14 '15 at 20:12
  • @ScottChamberlain I don't intend to be sending much at a time; mostly just numbers/text to update my program (unlikely to send 2 billion bytes which I'm assuming is the limit of clientSocket.ReceiveBufferSize). Thanks for pointing out the limit, and the link, though I'll have to read up on this. However it's possible that I'll need to read more in future. – Dom Hall Dec 14 '15 at 21:02
  • Even if you are not sending much, if you are trying to read 2 or more bytes you open yourself up to bugs due to only 1 being returned. Usually people like to wrap the stream in a [BinaryReader](https://msdn.microsoft.com/en-us/library/system.io.binaryreader(v=vs.110).aspx) on the receiver and [BinaryWriter](https://msdn.microsoft.com/en-us/library/system.io.binarywriter(v=vs.110).aspx) on the sender to abstract away the need to do the looping, then they can just do stuff like "ReadString" and "ReadInt32" – Scott Chamberlain Dec 14 '15 at 21:27
  • @ScottChamberlain Sorry; I don't see why only 1 byte is returned – Dom Hall Dec 14 '15 at 21:29
  • 1
    Beceause that is how Read works. You ask for 2000 bytes and it is allowed to read 1, 2, 3, .... 1998, 1999, or 2000 bytes. the returned int tells you how many bytes of the `byte[]` you passed in was filled with useful information. – Scott Chamberlain Dec 14 '15 at 21:30
  • @ScottChamberlain In my tests .Read filled the array with all the data I sent – Dom Hall Dec 14 '15 at 21:34
  • 1
    Yes, and when you run those same tests over a slow internet connection that is being clogged up because a low end consumer grade router can't handle the load of someone doing a torrent on the same network as your machine .Read will not fill the array with all the data you sent. That's why bugs like this are very bad, they don't show up in ideal test environments because they only break when the system is under stress. – Scott Chamberlain Dec 14 '15 at 21:37
  • 1
    OR the other bug you might encounter is if the reading side is too slow two messages you sent on the sending side may be combined in to a single Read call if your buffer is bigger than your message. Go read the article on Meassage framing I linked, it goes in to detail about that. – Scott Chamberlain Dec 14 '15 at 21:39
  • Thanks a lot! I'll be reading up – Dom Hall Dec 14 '15 at 21:52

0 Answers0