tcp: When we have an out-of-order FIN we do want to strip off the FIN bit.
The last set of commits fixed both a panic (in rack) and an ACK-war (in freebsd and bbr). However there was a missing case, i.e. where we get an out-of-order FIN by itself. In such a case we don't want to leave the FIN bit set, otherwise we will do the wrong thing and ack the FIN incorrectly. Instead we need to go through the tcp_reasm() code and that way the FIN will be stripped and all will be well. Reviewed by: mtuexen,rscheff Sponsored by: Netflix Inc Differential Revision: https://reviews.freebsd.org/D30497
This commit is contained in:
parent
4cc8a9da49
commit
8c69d988a8
@ -3191,7 +3191,12 @@ tcp_do_segment(struct mbuf *m, struct tcphdr *th, struct socket *so,
|
|||||||
* when trimming from the head.
|
* when trimming from the head.
|
||||||
*/
|
*/
|
||||||
tcp_seq temp = save_start;
|
tcp_seq temp = save_start;
|
||||||
if (tlen) {
|
if (tlen || (th->th_seq != tp->rcv_nxt)) {
|
||||||
|
/*
|
||||||
|
* We add the th_seq != rcv_nxt to
|
||||||
|
* catch the case of a stand alone out
|
||||||
|
* of order FIN.
|
||||||
|
*/
|
||||||
thflags = tcp_reass(tp, th, &temp, &tlen, m);
|
thflags = tcp_reass(tp, th, &temp, &tlen, m);
|
||||||
tp->t_flags |= TF_ACKNOW;
|
tp->t_flags |= TF_ACKNOW;
|
||||||
}
|
}
|
||||||
|
@ -8320,7 +8320,12 @@ bbr_process_data(struct mbuf *m, struct tcphdr *th, struct socket *so,
|
|||||||
* trimming from the head.
|
* trimming from the head.
|
||||||
*/
|
*/
|
||||||
tcp_seq temp = save_start;
|
tcp_seq temp = save_start;
|
||||||
if (tlen) {
|
if (tlen || (th->th_seq != tp->rcv_nxt)) {
|
||||||
|
/*
|
||||||
|
* We add the th_seq != rcv_nxt to
|
||||||
|
* catch the case of a stand alone out
|
||||||
|
* of order FIN.
|
||||||
|
*/
|
||||||
thflags = tcp_reass(tp, th, &temp, &tlen, m);
|
thflags = tcp_reass(tp, th, &temp, &tlen, m);
|
||||||
tp->t_flags |= TF_ACKNOW;
|
tp->t_flags |= TF_ACKNOW;
|
||||||
}
|
}
|
||||||
|
@ -10235,7 +10235,12 @@ rack_process_data(struct mbuf *m, struct tcphdr *th, struct socket *so,
|
|||||||
* trimming from the head.
|
* trimming from the head.
|
||||||
*/
|
*/
|
||||||
tcp_seq temp = save_start;
|
tcp_seq temp = save_start;
|
||||||
if (tlen) {
|
if (tlen || (th->th_seq != tp->rcv_nxt)) {
|
||||||
|
/*
|
||||||
|
* We add the th_seq != rcv_nxt to
|
||||||
|
* catch the case of a stand alone out
|
||||||
|
* of order FIN.
|
||||||
|
*/
|
||||||
thflags = tcp_reass(tp, th, &temp, &tlen, m);
|
thflags = tcp_reass(tp, th, &temp, &tlen, m);
|
||||||
tp->t_flags |= TF_ACKNOW;
|
tp->t_flags |= TF_ACKNOW;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user