summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYonit <yhalperi@redhat.com>2009-07-06 11:25:49 +0300
committerYonit <yhalperi@redhat.com>2009-07-06 11:25:49 +0300
commite3cf8ba5350388174f03aa3943e137e6e3e7e140 (patch)
tree82812c15e359554a5915bcefec59ec4769ac5908
parentaa25b55655a7acdd4a59104af1bd3527860516c8 (diff)
A hook for a bug where tp->rcv_nxt > tp->rcv_adv. The bug corrupted the tcp window
-rw-r--r--tcp_input.c9
-rw-r--r--tcp_output.c11
2 files changed, 19 insertions, 1 deletions
diff --git a/tcp_input.c b/tcp_input.c
index d40eb8a..73e8d76 100644
--- a/tcp_input.c
+++ b/tcp_input.c
@@ -646,6 +646,15 @@ findso:
win = sbspace(&so->so_rcv);
if (win < 0)
win = 0;
+
+ /* a hook for the case that tp->rcv_nxt > tp->rcv_adv. It can happen
+ when 1) there is more space in so_rcv than in the window last advertised and
+ 2) we received more data than the the size of the window last advertised.
+ For example: it happens when we receive zero window probes of len=1 and a space
+ in so_rcv is available */
+ if (SEQ_LT(tp->rcv_adv, tp->rcv_nxt)) {
+ tp->rcv_adv = tp->rcv_nxt;
+ }
tp->rcv_wnd = max(win, (int)(tp->rcv_adv - tp->rcv_nxt));
}
diff --git a/tcp_output.c b/tcp_output.c
index 4f252c0..abe29b4 100644
--- a/tcp_output.c
+++ b/tcp_output.c
@@ -176,6 +176,15 @@ again:
win = sbspace(&so->so_rcv);
+ /* a hook for the case that tp->rcv_nxt > tp->rcv_adv. It can happen
+ when 1) there is more space in so_rcv than in the window last advertised and
+ 2) we received more data than the the size of the window last advertised.
+ For example: it happens when we receive zero window probes of len=1 and a space
+ in so_rcv is available */
+ if (SEQ_LT(tp->rcv_adv, tp->rcv_nxt)) {
+ tp->rcv_adv = tp->rcv_nxt;
+ }
+
/*
* Sender silly window avoidance. If connection is idle
* and can send all data, a maximum segment,
@@ -214,7 +223,7 @@ again:
* TCP_MAXWIN << tp->rcv_scale.
*/
long adv = min(win, (long)TCP_MAXWIN << tp->rcv_scale) -
- (tp->rcv_adv - tp->rcv_nxt);
+ (tp->rcv_adv - tp->rcv_nxt);
if (adv >= (long) (2 * tp->t_maxseg))
goto send;