Re: Selecting optimum block sizes for data transmission

From: Martin Harvey (Demon Account) (martin_at__nospam_pergolesi.demon.co.uk)
Date: 04/07/04


Date: Tue, 06 Apr 2004 23:38:30 +0100

On Fri, 2 Apr 2004 10:45:53 +0100, Catherine Rees Lay
<spamtrap@polyhedron.org.uk> wrote:

>...anyone got any suggestions or can point me towards some information
>on this? I may be transmitting anything from a few bytes to several
>hundred Mb of data.

Okay - I'll have a shot.

>It's working quite happily, but I'm fairly sure my fixed block size of
>1Kb isn't the most appropriate for large files. The Indy default buffer
>size is 8192 bytes but I can't find any information on when it's
>appropriate to change this (and also it's set in Create, so what would I
>do if I need to transmit 1000 lots of 1kb followed by 1 lot of 100Mb?)
>Basically I know there's no one answer but I'm sure I should be able to
>do better than "think of a number".
>
>Any pointers welcome!

I'm not particularly familiar with Indy in particular, but I seem to
recall their sockets model is blocking, using multiple threads (I got
asked if I'd like to help write parts of the sockets library given my
multithreading experience - but alas, I didn't have the time).

Luckily, whether the API provided to you is blocking or asynchronous,
it doesn't affect the answer much. I'll give you two answers, the
short and the long.

Short answer:

- Send as much as you can, as soon as you can. Feel free to fill the
socket up with data until it either tells you you can't send any more
at the moment, or blocks your thread. Don't go overboard though -
allocating 1 meg buffers for huge send calls just wastes memory - for
optimum efficiency, 8k to 64k should be fine.

Long answer

Once you've make a call to send data, the TCP/IP stack does a huge
number of things to optimise both the latency of data for small sends,
and the bandwidth of data for big sends. In no particular order it:

- Keeps track of the round trip time via a smoothed average, and
estimates the bandwidth delay product. (smoothed RTT estimators).
- Keeps track of packet loss and congestion thresholds, and throttles
back if it's losing data, via an exponential backoff timer. (RTO
determined by RTT).
- Maintains a congestion window to limit data flow in the face of long
term network congestion. (SSTHRESH and CWND).
- Attempts to avoid wasteful sends of very small packets, (silly
window syndrome) by only advertising decent sized windws.
- Attempts to batch small application level send calls into bigger
packets (Nagle algorithm).
- Uses a variety of retransmit methods to try and minimise the number
of unneeded packet retransmissions (go back N versus selective
retransmit).
- Keeps track of what size packets the network can handle without
dropping them - local ethernets will cope with 1500 byte packets, but
the internet standard is only 576 bytes (MSS and path MTU discovery).

So you can see, that the packets that actually get sent on the wire
will only bear a resemblance to your application send calls at a very
low data rate, or by sheer coincidence.

For small volumes of data (ie bytes typed at a console) which need to
be delivered fast:

- Send each character as it arrives without waiting for more.
- If quick feedback is *crucial* (eg mouse movements on a virtual
console), then consider disabling the nagle algorithm for the socket,
and, if you're using Winsock2 stack directly, set the quality of
service bits (QoS) to minimum delay.

For bulk data:

- Feel free to make big send calls.
- Some stacks on high bandwidth networks with a long delay are limited
by the size of the send window on the host machine - see if your stack
uses the window scaling option, and whether it does it automatically,
or whether you have to issue calls to enable it.
- Set the quality of service bits for the socket to maximum
throughput.

Hope this helps,

Martin H.



Relevant Pages

  • Re: Socket Disconnect
    ... That is, if you are periodically sending packets, you'll find out ... > dies that the connection is broken. ... In that case, the stack will detect ... > but, when all of those attempts fail, it will close the socket and you'll ...
    (microsoft.public.dotnet.framework.compactframework)
  • Re: Socket Disconnect
    ... To notice that a connection has been broken, you either have to try to send ... In that case, the stack will detect ... but, when all of those attempts fail, it will close the socket and you'll ... If you are sitting around waiting to receive packets, though, you'll never ...
    (microsoft.public.dotnet.framework.compactframework)
  • Re: Socket Disconnect
    ... g_socClient.SetSocketOption(Socket, KeepAlive, 1), is what I'd try. ... That is, if you are periodically sending packets, you'll find out ... >> dies that the connection is broken. ... In that case, the stack will detect ...
    (microsoft.public.dotnet.framework.compactframework)
  • Re: Problem with writing fast UDP server
    ... UDP packets per second. ... socket and threads. ... I wrote a simple case test: client and server. ... The maximum theoretical limit is 14,880 frames per ...
    (comp.lang.python)
  • RE: *warning* student question
    ... What option is this supposed CRC or hash supposed to be? ... >their shell session you're taking over their network socket. ... Systems will also drop TCP packets with bad checksums. ... We provide Ethical Hacking, Advanced Ethical Hacking, Intrusion ...
    (Security-Basics)