summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Tuexen <tuexen@FreeBSD.org>2017-06-01 14:58:26 +0000
committerMichael Tuexen <tuexen@FreeBSD.org>2017-06-01 14:58:26 +0000
commitcf8c4175fa40026a5d7800dba1fdc2031ae69cd7 (patch)
tree5958b5d8aece4498df9e1b605c49d0ca7d1e46ae
parentbfccc82170863098c1277c536e8e3d42a9a229d8 (diff)
Notes
-rw-r--r--sys/netinet/tcp_input.c17
-rw-r--r--sys/netinet/tcp_stacks/fastpath.c35
2 files changed, 38 insertions, 14 deletions
diff --git a/sys/netinet/tcp_input.c b/sys/netinet/tcp_input.c
index be461dce08f6..69fc6cb0e490 100644
--- a/sys/netinet/tcp_input.c
+++ b/sys/netinet/tcp_input.c
@@ -1607,6 +1607,16 @@ tcp_do_segment(struct mbuf *m, struct tcphdr *th, struct socket *so,
}
/*
+ * If a segment with the ACK-bit set arrives in the SYN-SENT state
+ * check SEQ.ACK first.
+ */
+ if ((tp->t_state == TCPS_SYN_SENT) && (thflags & TH_ACK) &&
+ (SEQ_LEQ(th->th_ack, tp->iss) || SEQ_GT(th->th_ack, tp->snd_max))) {
+ rstreason = BANDLIM_UNLIMITED;
+ goto dropwithreset;
+ }
+
+ /*
* Segment received on connection.
* Reset idle time and keep-alive timer.
* XXX: This should be done after segment
@@ -1984,7 +1994,6 @@ tcp_do_segment(struct mbuf *m, struct tcphdr *th, struct socket *so,
/*
* If the state is SYN_SENT:
- * if seg contains an ACK, but not for our SYN, drop the input.
* if seg contains a RST, then drop the connection.
* if seg does not contain SYN, then drop it.
* Otherwise this is an acceptable SYN segment
@@ -1997,12 +2006,6 @@ tcp_do_segment(struct mbuf *m, struct tcphdr *th, struct socket *so,
* continue processing rest of data/controls, beginning with URG
*/
case TCPS_SYN_SENT:
- if ((thflags & TH_ACK) &&
- (SEQ_LEQ(th->th_ack, tp->iss) ||
- SEQ_GT(th->th_ack, tp->snd_max))) {
- rstreason = BANDLIM_UNLIMITED;
- goto dropwithreset;
- }
if ((thflags & (TH_ACK|TH_RST)) == (TH_ACK|TH_RST)) {
TCP_PROBE5(connect__refused, NULL, tp,
m, tp, th);
diff --git a/sys/netinet/tcp_stacks/fastpath.c b/sys/netinet/tcp_stacks/fastpath.c
index f2c493e1956f..84a151985048 100644
--- a/sys/netinet/tcp_stacks/fastpath.c
+++ b/sys/netinet/tcp_stacks/fastpath.c
@@ -485,7 +485,6 @@ tcp_do_slowpath(struct mbuf *m, struct tcphdr *th, struct socket *so,
/*
* If the state is SYN_SENT:
- * if seg contains an ACK, but not for our SYN, drop the input.
* if seg contains a RST, then drop the connection.
* if seg does not contain SYN, then drop it.
* Otherwise this is an acceptable SYN segment
@@ -498,12 +497,6 @@ tcp_do_slowpath(struct mbuf *m, struct tcphdr *th, struct socket *so,
* continue processing rest of data/controls, beginning with URG
*/
case TCPS_SYN_SENT:
- if ((thflags & TH_ACK) &&
- (SEQ_LEQ(th->th_ack, tp->iss) ||
- SEQ_GT(th->th_ack, tp->snd_max))) {
- rstreason = BANDLIM_UNLIMITED;
- goto dropwithreset;
- }
if ((thflags & (TH_ACK|TH_RST)) == (TH_ACK|TH_RST)) {
TCP_PROBE5(connect__refused, NULL, tp, m, tp, th);
tp = tcp_drop(tp, ECONNREFUSED);
@@ -1744,6 +1737,20 @@ tcp_do_segment_fastslow(struct mbuf *m, struct tcphdr *th, struct socket *so,
m_freem(m);
return;
}
+
+ /*
+ * If a segment with the ACK-bit set arrives in the SYN-SENT state
+ * check SEQ.ACK first.
+ */
+ if ((tp->t_state == TCPS_SYN_SENT) && (thflags & TH_ACK) &&
+ (SEQ_LEQ(th->th_ack, tp->iss) || SEQ_GT(th->th_ack, tp->snd_max))) {
+ tcp_dropwithreset(m, th, tp, tlen, BANDLIM_UNLIMITED);
+ if (ti_locked == TI_RLOCKED) {
+ INP_INFO_RUNLOCK(&V_tcbinfo);
+ }
+ INP_WUNLOCK(tp->t_inpcb);
+ return;
+ }
tp->sackhint.last_sack_ack = 0;
@@ -2203,6 +2210,20 @@ tcp_do_segment_fastack(struct mbuf *m, struct tcphdr *th, struct socket *so,
return;
}
+ /*
+ * If a segment with the ACK-bit set arrives in the SYN-SENT state
+ * check SEQ.ACK first.
+ */
+ if ((tp->t_state == TCPS_SYN_SENT) && (thflags & TH_ACK) &&
+ (SEQ_LEQ(th->th_ack, tp->iss) || SEQ_GT(th->th_ack, tp->snd_max))) {
+ tcp_dropwithreset(m, th, tp, tlen, BANDLIM_UNLIMITED);
+ if (ti_locked == TI_RLOCKED) {
+ INP_INFO_RUNLOCK(&V_tcbinfo);
+ }
+ INP_WUNLOCK(tp->t_inpcb);
+ return;
+ }
+
tp->sackhint.last_sack_ack = 0;
/*