tcp: Correct sending idle detection and implement part of RFC2861
authorSepherosa Ziehau <sephe@dragonflybsd.org>
Wed, 18 Apr 2012 07:31:26 +0000 (15:31 +0800)
committerSepherosa Ziehau <sephe@dragonflybsd.org>
Wed, 18 Apr 2012 09:31:07 +0000 (17:31 +0800)
commit3d127502478783869f3689073fdde11ca8bcad2f
tree416f6b397e0c0e606cd93fac051df7adb2d197c4
parent0df7608b226e4ad0abf093ea14497079306ed4e3
tcp: Correct sending idle detection and implement part of RFC2861

This commit mainly changes how cwnd is shinked after idle period on
the send side.

- Properly detect sending idle period according to RFC5681.  The problem
  of using reception time to detect sending idle period is described in
  RFC5681 as:

  "...
   Using the last time a segment was received to determine whether or
   not to decrease cwnd can fail to deflate cwnd in the common case of
   persistent HTTP connections [HTH98].  In this case, a Web server
   receives a request before transmitting data to the Web client.  The
   reception of the request makes the test for an idle connection fail,
   and allows the TCP to begin transmission with a possibly
   inappropriately large cwnd.
   ..."

  This mainly affects HTTP/1.1 persistent connection performance after
  the connection is idled for a long time.  The impact probably should not
  be drastic, since 80% HTTP/1.1 persistent connection delay between two
  requests are less then minimum RTO (1 second) as discovered by:
  "Overclocking the Yahoo! CDN for Faster Web Page Loads"
    http://conferences.sigcomm.org/imc/2011/docs/p569.pdf

  Sysctl node net.inet.tcp.idle_restart is added to disable the cwnd
  shinking after idle period.  It is on by default.  And you can set it
  to 0 to restore old behaviour against HTTP/1.1 persistent connection.

- Implement part of RFC2861, which decays cwnd after idle period according
  to the length of sending idle period.  The main difference between our
  implementation and the RFC2861 is that we don't let cwnd go below the
  value allowed by RFC5861.

  Sysctl node net.inet.tcp.idle_cwv is added to disable CWV after sending
  idle period.  It is on by default.  Disable net.inet.tcp.idle_restart
  will also indirectly disable CWV after sending idle period.

  The CWV during the application-limited period is not implemented by this
  commit.  It is just too conservative, as discovered by:
  "Analysing TCP for Bursty Traffic, Int'l J. of Communications,
   Network and System Sciences, 7(3), July 2010."

- Add statistics about how much sending idle happened
sys/netinet/tcp_output.c
sys/netinet/tcp_subr.c
sys/netinet/tcp_var.h
usr.bin/netstat/inet.c