Date: Thu, 7 Jun 2012 16:28:39 -0400 From: George Neville-Neil <gnn@neville-neil.com> To: Navdeep Parhar <np@FreeBSD.org> Cc: freebsd-net@freebsd.org Subject: Re: seq# of RST in tcp_dropwithreset Message-ID: <FF186C52-48D4-4812-9CEF-B33A79341C19@neville-neil.com> In-Reply-To: <CAPFoGT9eEmMwvpO3O3nLmWCpj=NQis9K1DD_WyZDVwMCZjT6Fg@mail.gmail.com> References: <CAPFoGT9eEmMwvpO3O3nLmWCpj=NQis9K1DD_WyZDVwMCZjT6Fg@mail.gmail.com>
next in thread | previous in thread | raw e-mail | index | archive | help
On Mar 27, 2012, at 18:13 , Navdeep Parhar wrote: > When the kernel decides to respond with a RST to an incoming TCP > segment, it uses its ack# (if valid) as the seq# of the RST. See this > in tcp_dropwithreset: >=20 > if (th->th_flags & TH_ACK) { > tcp_respond(tp, mtod(m, void *), th, m, (tcp_seq)0, > th->th_ack, TH_RST); > } else { > if (th->th_flags & TH_SYN) > tlen++; > tcp_respond(tp, mtod(m, void *), th, m, th->th_seq+tlen, > (tcp_seq)0, TH_RST|TH_ACK); > } >=20 > This can have some unexpected results. I observed this on a link with > a very high delay (B is FreeBSD, A could be anything). >=20 > 1. There is a segment in flight from A to B. The ack# is X (all tx > from B to A is up to date and acknowledged). > 2. socket is closed on B. B sends a FIN with seq# X. > 3. The segment from A arrives and elicits a RST from B. The seq# of > this RST will again be X. A receives the FIN and then the RST with > identical sequence numbers. The situation resolves itself eventually, > when A retransmits and the retransmitted segment ACKs the FIN too and > so the next time around B sends a RST with the "correct" seq# (one > after the FIN). >=20 > If there is a local tcpcb for the connection with state >=3D > ESTABLISHED, wouldn't it be more accurate to use its snd_max as the > seq# of the RST? >=20 Hi Navdeep, Sorry I missed this so many months ago, but jhb@ was kind enough to = point this query out to me. My understanding of correct operation in this case, is = that we=20 do not want to move the sequence number until we have received the ACK = of our FIN, as any other value would indicate to the TCP on A that we have = received their ACK of our FIN, which, in this case, we have not. The fact that there = isn't a better way to indicate the error is a tad annoying, but, and others can correct = me if they think I'm wrong, this is the correct way for the stacks to come to eventual = agreement on the closing of the connection. Best, George
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?FF186C52-48D4-4812-9CEF-B33A79341C19>