From owner-freebsd-bugs@FreeBSD.ORG Tue Mar 1 05:50:17 2005 Return-Path: Delivered-To: freebsd-bugs@hub.freebsd.org Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id AC61F16A4CF for ; Tue, 1 Mar 2005 05:50:17 +0000 (GMT) Received: from freefall.freebsd.org (freefall.freebsd.org [216.136.204.21]) by mx1.FreeBSD.org (Postfix) with ESMTP id 6090B43D5E for ; Tue, 1 Mar 2005 05:50:17 +0000 (GMT) (envelope-from gnats@FreeBSD.org) Received: from freefall.freebsd.org (gnats@localhost [127.0.0.1]) by freefall.freebsd.org (8.13.1/8.13.1) with ESMTP id j215oH2R067730 for ; Tue, 1 Mar 2005 05:50:17 GMT (envelope-from gnats@freefall.freebsd.org) Received: (from gnats@localhost) by freefall.freebsd.org (8.13.1/8.13.1/Submit) id j215oHW9067729; Tue, 1 Mar 2005 05:50:17 GMT (envelope-from gnats) Resent-Date: Tue, 1 Mar 2005 05:50:17 GMT Resent-Message-Id: <200503010550.j215oHW9067729@freefall.freebsd.org> Resent-From: FreeBSD-gnats-submit@FreeBSD.org (GNATS Filer) Resent-To: freebsd-bugs@FreeBSD.org Resent-Reply-To: FreeBSD-gnats-submit@FreeBSD.org, Noritoshi Demizu Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id DDCF116A4CE for ; Tue, 1 Mar 2005 05:49:13 +0000 (GMT) Received: from www.freebsd.org (www.freebsd.org [216.136.204.117]) by mx1.FreeBSD.org (Postfix) with ESMTP id A114943D55 for ; Tue, 1 Mar 2005 05:49:13 +0000 (GMT) (envelope-from nobody@FreeBSD.org) Received: from www.freebsd.org (localhost [127.0.0.1]) by www.freebsd.org (8.13.1/8.13.1) with ESMTP id j215nDci068344 for ; Tue, 1 Mar 2005 05:49:13 GMT (envelope-from nobody@www.freebsd.org) Received: (from nobody@localhost) by www.freebsd.org (8.13.1/8.13.1/Submit) id j215nDjk068343; Tue, 1 Mar 2005 05:49:13 GMT (envelope-from nobody) Message-Id: <200503010549.j215nDjk068343@www.freebsd.org> Date: Tue, 1 Mar 2005 05:49:13 GMT From: Noritoshi Demizu To: freebsd-gnats-submit@FreeBSD.org X-Send-Pr-Version: www-2.3 Subject: kern/78226: rcv_lastsack in struct tcpcb is not updated when the right most SACK block expands. X-BeenThere: freebsd-bugs@freebsd.org X-Mailman-Version: 2.1.1 Precedence: list List-Id: Bug reports List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 01 Mar 2005 05:50:17 -0000 >Number: 78226 >Category: kern >Synopsis: rcv_lastsack in struct tcpcb is not updated when the right most SACK block expands. >Confidential: no >Severity: non-critical >Priority: medium >Responsible: freebsd-bugs >State: open >Quarter: >Keywords: >Date-Required: >Class: sw-bug >Submitter-Id: current-users >Arrival-Date: Tue Mar 01 05:50:16 GMT 2005 >Closed-Date: >Last-Modified: >Originator: Noritoshi Demizu >Release: FreeBSD 6.0 current (as of Mar 1, 2005) >Organization: NICT >Environment: FreeBSD xxx 6.0-CURRENT FreeBSD 6.0-CURRENT #7: Tue Mar 1 10:50:54 JST 2005 noritosi@xxx:/home/FreeBSD-current/src/sys/i386/compile/GENERIC i386 >Description: rcv_lastsack in struct tcpcb is "last seq number(+1) sack'd by rcv'r" according to the comment in tcp_var.h. In tcp_sack.c Rev 1.9, it is updated only when the first SACK block or a new right most SACK block is reported. In other words, it is not updated when the right most SACK block expands to the right. Hence, tcp_sack_adjust() may choose inappropriate snd_nxt at the last line. >How-To-Repeat: In my experimental environment, there are three machines: a sender, a router and a receiver. Dummynet runs on the router configured as RTT=40ms, bandwidth=10Mbps, queue=8pkts and plr=0.03. The sender's buffer size and the receiver's buffer size are 192k bytes. In the environment, when a fast retransmitted packet is lost, the sender has to wait for a timeout. But the sender keeps sending data segments until the timeout is triggered because buffer is big enough. In such case, just after the timeout, the sender keeps receiving ACK segments containing SACK information of segments sent before the timeout. Such SACK information can be used to avoid unnecessary retransmission. However, since rcv_lastsack is not updated when fack advances, sack'd data are sent unnecessarily. >Fix: The following patch fixes this problem in my environment. Since rcv_lastsack is referred only when snd_holes != NULL, this patch does not touch tcp_del_sackholes() and tcp_free_sackholes(). --- tcp_sack.c-ORG Mon Feb 28 10:43:29 2005 +++ tcp_sack.c Tue Mar 1 14:46:16 2005 @@ -431,6 +431,8 @@ tp->rcv_lastsack = sack.end; tp->snd_numholes++; } + if (SEQ_LT(tp->rcv_lastsack, sack.end)) + tp->rcv_lastsack = sack.end; } return (0); } >Release-Note: >Audit-Trail: >Unformatted: