From 8ee5086c6c662a8bc7efb3f681d25be3328ce1f5 Mon Sep 17 00:00:00 2001 From: mikeb Date: Thu, 7 May 2015 09:19:31 +0000 Subject: [PATCH] Include the timestamp TCP option in keep alive packets as well. According to RFC 7323 "once TSopt has been successfully negotiated, ... [it] MUST be sent in every non- segment for the duration of the connection." Which means that keep alives which are just ACK packets must include that too. Pointed out and tested by Lauri Tirkkonen , thanks! ok mpi --- sys/netinet/tcp_subr.c | 25 +++++++++++++++++-------- 1 file changed, 17 insertions(+), 8 deletions(-) diff --git a/sys/netinet/tcp_subr.c b/sys/netinet/tcp_subr.c index c8c8e77275f..b98ecd29cba 100644 --- a/sys/netinet/tcp_subr.c +++ b/sys/netinet/tcp_subr.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tcp_subr.c,v 1.140 2015/03/14 03:38:52 jsg Exp $ */ +/* $OpenBSD: tcp_subr.c,v 1.141 2015/05/07 09:19:31 mikeb Exp $ */ /* $NetBSD: tcp_subr.c,v 1.22 1996/02/13 23:44:00 christos Exp $ */ /* @@ -297,9 +297,6 @@ tcp_template(tp) * In any case the ack and sequence number of the transmitted * segment are as specified by the parameters. */ -#ifdef INET6 -/* This function looks hairy, because it was so IPv4-dependent. */ -#endif /* INET6 */ void tcp_respond(struct tcpcb *tp, caddr_t template, struct tcphdr *th0, tcp_seq ack, tcp_seq seq, int flags, u_int rtableid) @@ -372,10 +369,6 @@ tcp_respond(struct tcpcb *tp, caddr_t template, struct tcphdr *th0, flags = TH_ACK; #undef xchg - m->m_len = tlen; - m->m_pkthdr.len = tlen; - m->m_pkthdr.rcvif = (struct ifnet *) 0; - m->m_pkthdr.csum_flags |= M_TCP_CSUM_OUT; th->th_seq = htonl(seq); th->th_ack = htonl(ack); th->th_x2 = 0; @@ -388,6 +381,22 @@ tcp_respond(struct tcpcb *tp, caddr_t template, struct tcphdr *th0, th->th_win = htons((u_int16_t)win); th->th_urp = 0; + if (tp && (tp->t_flags & (TF_REQ_TSTMP|TF_NOOPT)) == TF_REQ_TSTMP && + (flags & TH_RST) == 0 && (tp->t_flags & TF_RCVD_TSTMP)) { + u_int32_t *lp = (u_int32_t *)(th + 1); + /* Form timestamp option as shown in appendix A of RFC 1323. */ + *lp++ = htonl(TCPOPT_TSTAMP_HDR); + *lp++ = htonl(tcp_now + tp->ts_modulate); + *lp = htonl(tp->ts_recent); + tlen += TCPOLEN_TSTAMP_APPA; + th->th_off = (sizeof(struct tcphdr) + TCPOLEN_TSTAMP_APPA) >> 2; + } + + m->m_len = tlen; + m->m_pkthdr.len = tlen; + m->m_pkthdr.rcvif = (struct ifnet *) 0; + m->m_pkthdr.csum_flags |= M_TCP_CSUM_OUT; + /* force routing table */ if (tp) m->m_pkthdr.ph_rtableid = tp->t_inpcb->inp_rtableid; -- 2.20.1