ok yasuoka
On Fri, 2 Sep 2022 14:44:29 +0200
Alexander Bluhm <alexander.bl...@gmx.net> wrote:
> + now = READ_ONCE(tcp_now);
> +
> /*
> * Determine length of data that should be transmitted,
> * and flags that will be used.
> @@ -228,7 +231,7 @@ tcp_output(struct tcpcb *tp)
> * to send, then transmit; otherwise, investigate further.
> */
> idle = (tp->t_flags & TF_LASTIDLE) || (tp->snd_max == tp->snd_una);
> - if (idle && (tcp_now - tp->t_rcvtime) >= tp->t_rxtcur)
> + if (idle && (now - tp->t_rcvtime) >= tp->t_rxtcur)
> /*
> * We have been idle for "a while" and no acks are
> * expected to clock out any data we send --
> @@ -539,13 +542,13 @@ send:
>
> /* 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(now + tp->ts_modulate);
> *lp = htonl(tp->ts_recent);
> optlen += TCPOLEN_TSTAMP_APPA;
>
> /* Set receive buffer autosizing timestamp. */
> if (tp->rfbuf_ts == 0)
> - tp->rfbuf_ts = tcp_now;
> + tp->rfbuf_ts = now;
>
> }
>
> @@ -691,7 +694,7 @@ send:
> */
> if (off + len == so->so_snd.sb_cc && !soissending(so))
> flags |= TH_PUSH;
> - tp->t_sndtime = tcp_now;
> + tp->t_sndtime = now;
> } else {
> if (tp->t_flags & TF_ACKNOW)
> tcpstat_inc(tcps_sndacks);
> @@ -924,7 +927,7 @@ send:
> * not currently timing anything.
> */
> if (tp->t_rtttime == 0) {
> - tp->t_rtttime = tcp_now;
> + tp->t_rtttime = now;
> tp->t_rtseq = startseq;
> tcpstat_inc(tcps_segstimed);
> }
> @@ -1123,7 +1126,7 @@ out:
> if (win > 0 && SEQ_GT(tp->rcv_nxt+win, tp->rcv_adv))
> tp->rcv_adv = tp->rcv_nxt + win;
> tp->last_ack_sent = tp->rcv_nxt;
> - tp->t_sndacktime = tcp_now;
> + tp->t_sndacktime = now;
> tp->t_flags &= ~TF_ACKNOW;
> TCP_TIMER_DISARM(tp, TCPT_DELACK);
> if (sendalot)
> Index: netinet/tcp_subr.c
> ===================================================================
> RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/tcp_subr.c,v
> retrieving revision 1.186
> diff -u -p -r1.186 tcp_subr.c
> --- netinet/tcp_subr.c 30 Aug 2022 11:53:04 -0000 1.186
> +++ netinet/tcp_subr.c 1 Sep 2022 14:47:22 -0000
> @@ -71,6 +71,7 @@
> #include <sys/param.h>
> #include <sys/systm.h>
> #include <sys/mbuf.h>
> +#include <sys/mutex.h>
> #include <sys/socket.h>
> #include <sys/socketvar.h>
> #include <sys/timeout.h>
> @@ -98,6 +99,14 @@
> #include <crypto/md5.h>
> #include <crypto/sha2.h>
>
> +/*
> + * Locks used to protect struct members in this file:
> + * I immutable after creation
> + * T tcp_timer_mtx global tcp timer data structures
> + */
> +
> +struct mutex tcp_timer_mtx;
> +
> /* patchable/settable parameters for tcp */
> int tcp_mssdflt = TCP_MSS;
> int tcp_rttdflt = TCPTV_SRTTDFLT / PR_SLOWHZ;
> @@ -111,8 +120,6 @@ int tcp_do_ecn = 0; /* RFC3168 ECN enab
> #endif
> int tcp_do_rfc3390 = 2; /* Increase TCP's Initial Window to 10*mss */
>
> -u_int32_t tcp_now = 1;
> -
> #ifndef TCB_INITIAL_HASH_SIZE
> #define TCB_INITIAL_HASH_SIZE 128
> #endif
> @@ -126,9 +133,10 @@ struct pool sackhl_pool;
>
> struct cpumem *tcpcounters; /* tcp statistics */
>
> -u_char tcp_secret[16];
> -SHA2_CTX tcp_secret_ctx;
> -tcp_seq tcp_iss;
> +u_char tcp_secret[16]; /* [I] */
> +SHA2_CTX tcp_secret_ctx; /* [I] */
> +tcp_seq tcp_iss; /* [T] updated by timer and connection
> */
> +uint32_t tcp_now; /* [T] incremented by slow timer */
>
> /*
> * Tcp initialization
> @@ -137,6 +145,7 @@ void
> tcp_init(void)
> {
> tcp_iss = 1; /* wrong */
> + tcp_now = 1;
> pool_init(&tcpcb_pool, sizeof(struct tcpcb), 0, IPL_SOFTNET, 0,
> "tcpcb", NULL);
> pool_init(&tcpqe_pool, sizeof(struct tcpqent), 0, IPL_SOFTNET, 0,
> @@ -281,7 +290,7 @@ tcp_template(struct tcpcb *tp)
> */
> void
> tcp_respond(struct tcpcb *tp, caddr_t template, struct tcphdr *th0,
> - tcp_seq ack, tcp_seq seq, int flags, u_int rtableid)
> + tcp_seq ack, tcp_seq seq, int flags, u_int rtableid, uint32_t now)
> {
> int tlen;
> int win = 0;
> @@ -362,7 +371,7 @@ tcp_respond(struct tcpcb *tp, caddr_t te
> 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(now + tp->ts_modulate);
> *lp = htonl(tp->ts_recent);
> tlen += TCPOLEN_TSTAMP_APPA;
> th->th_off = (sizeof(struct tcphdr) + TCPOLEN_TSTAMP_APPA) >> 2;
> @@ -913,6 +922,12 @@ tcp_set_iss_tsm(struct tcpcb *tp)
> uint32_t words[2];
> } digest;
> u_int rdomain = rtable_l2(tp->t_inpcb->inp_rtableid);
> + tcp_seq iss;
> +
> + mtx_enter(&tcp_timer_mtx);
> + tcp_iss += TCP_ISS_CONN_INC;
> + iss = tcp_iss;
> + mtx_leave(&tcp_timer_mtx);
>
> ctx = tcp_secret_ctx;
> SHA512Update(&ctx, &rdomain, sizeof(rdomain));
> @@ -930,8 +945,7 @@ tcp_set_iss_tsm(struct tcpcb *tp)
> sizeof(struct in_addr));
> }
> SHA512Final(digest.bytes, &ctx);
> - tcp_iss += TCP_ISS_CONN_INC;
> - tp->iss = digest.words[0] + tcp_iss;
> + tp->iss = digest.words[0] + iss;
> tp->ts_modulate = digest.words[1];
> }
>
> Index: netinet/tcp_timer.c
> ===================================================================
> RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/tcp_timer.c,v
> retrieving revision 1.69
> diff -u -p -r1.69 tcp_timer.c
> --- netinet/tcp_timer.c 2 Jan 2022 22:36:04 -0000 1.69
> +++ netinet/tcp_timer.c 1 Sep 2022 14:47:22 -0000
> @@ -55,11 +55,16 @@
> #include <netinet/ip_icmp.h>
> #include <netinet/tcp_seq.h>
>
> +/*
> + * Locks used to protect struct members in this file:
> + * T tcp_timer_mtx global tcp timer data structures
> + */
> +
> int tcp_always_keepalive;
> int tcp_keepidle;
> int tcp_keepintvl;
> int tcp_maxpersistidle; /* max idle time in persist */
> -int tcp_maxidle;
> +int tcp_maxidle; /* [T] max idle time for keep alive */
>
> /*
> * Time to delay the ACK. This is initialized in tcp_init(), unless
> @@ -144,13 +149,11 @@ tcp_timer_delack(void *arg)
> void
> tcp_slowtimo(void)
> {
> - NET_LOCK();
> -
> + mtx_enter(&tcp_timer_mtx);
> tcp_maxidle = TCPTV_KEEPCNT * tcp_keepintvl;
> tcp_iss += TCP_ISSINCR2/PR_SLOWHZ; /* increment iss */
> tcp_now++; /* for timestamps */
> -
> - NET_UNLOCK();
> + mtx_leave(&tcp_timer_mtx);
> }
>
> /*
> @@ -392,6 +395,7 @@ tcp_timer_persist(void *arg)
> struct tcpcb *otp = NULL, *tp = arg;
> uint32_t rto;
> short ostate;
> + uint32_t now;
>
> NET_LOCK();
> /* Ignore canceled timeouts or timeouts that have been rescheduled. */
> @@ -418,9 +422,10 @@ tcp_timer_persist(void *arg)
> rto = TCP_REXMTVAL(tp);
> if (rto < tp->t_rttmin)
> rto = tp->t_rttmin;
> + now = READ_ONCE(tcp_now);
> if (tp->t_rxtshift == TCP_MAXRXTSHIFT &&
> - ((tcp_now - tp->t_rcvtime) >= tcp_maxpersistidle ||
> - (tcp_now - tp->t_rcvtime) >= rto * tcp_totbackoff)) {
> + ((now - tp->t_rcvtime) >= tcp_maxpersistidle ||
> + (now - tp->t_rcvtime) >= rto * tcp_totbackoff)) {
> tcpstat_inc(tcps_persistdrop);
> tp = tcp_drop(tp, ETIMEDOUT);
> goto out;
> @@ -458,8 +463,13 @@ tcp_timer_keep(void *arg)
> if ((tcp_always_keepalive ||
> tp->t_inpcb->inp_socket->so_options & SO_KEEPALIVE) &&
> tp->t_state <= TCPS_CLOSING) {
> - if ((tcp_maxidle > 0) &&
> - ((tcp_now - tp->t_rcvtime) >= tcp_keepidle + tcp_maxidle))
> + int maxidle;
> + uint32_t now;
> +
> + maxidle = READ_ONCE(tcp_maxidle);
> + now = READ_ONCE(tcp_now);
> + if ((maxidle > 0) &&
> + ((now - tp->t_rcvtime) >= tcp_keepidle + maxidle))
> goto dropit;
> /*
> * Send a packet designed to force a response
> @@ -475,7 +485,7 @@ tcp_timer_keep(void *arg)
> */
> tcpstat_inc(tcps_keepprobe);
> tcp_respond(tp, mtod(tp->t_template, caddr_t),
> - NULL, tp->rcv_nxt, tp->snd_una - 1, 0, 0);
> + NULL, tp->rcv_nxt, tp->snd_una - 1, 0, 0, now);
> TCP_TIMER_ARM(tp, TCPT_KEEP, tcp_keepintvl);
> } else
> TCP_TIMER_ARM(tp, TCPT_KEEP, tcp_keepidle);
> @@ -496,6 +506,8 @@ tcp_timer_2msl(void *arg)
> {
> struct tcpcb *otp = NULL, *tp = arg;
> short ostate;
> + int maxidle;
> + uint32_t now;
>
> NET_LOCK();
> /* Ignore canceled timeouts or timeouts that have been rescheduled. */
> @@ -510,8 +522,10 @@ tcp_timer_2msl(void *arg)
> }
> tcp_timer_freesack(tp);
>
> + maxidle = READ_ONCE(tcp_maxidle);
> + now = READ_ONCE(tcp_now);
> if (tp->t_state != TCPS_TIME_WAIT &&
> - ((tcp_maxidle == 0) || ((tcp_now - tp->t_rcvtime) <= tcp_maxidle)))
> + ((maxidle == 0) || ((now - tp->t_rcvtime) <= maxidle)))
> TCP_TIMER_ARM(tp, TCPT_2MSL, tcp_keepintvl);
> else
> tp = tcp_close(tp);
> Index: netinet/tcp_usrreq.c
> ===================================================================
> RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/tcp_usrreq.c,v
> retrieving revision 1.202
> diff -u -p -r1.202 tcp_usrreq.c
> --- netinet/tcp_usrreq.c 31 Aug 2022 21:23:02 -0000 1.202
> +++ netinet/tcp_usrreq.c 1 Sep 2022 14:47:22 -0000
> @@ -274,6 +274,7 @@ tcp_fill_info(struct tcpcb *tp, struct s
> struct proc *p = curproc;
> struct tcp_info *ti;
> u_int t = 1000000 / PR_SLOWHZ;
> + uint32_t now;
>
> if (sizeof(*ti) > MLEN) {
> MCLGETL(m, M_WAITOK, sizeof(*ti));
> @@ -283,6 +284,7 @@ tcp_fill_info(struct tcpcb *tp, struct s
> ti = mtod(m, struct tcp_info *);
> m->m_len = sizeof(*ti);
> memset(ti, 0, sizeof(*ti));
> + now = READ_ONCE(tcp_now);
>
> ti->tcpi_state = tp->t_state;
> if ((tp->t_flags & TF_REQ_TSTMP) && (tp->t_flags & TF_RCVD_TSTMP))
> @@ -303,10 +305,10 @@ tcp_fill_info(struct tcpcb *tp, struct s
> ti->tcpi_snd_mss = tp->t_maxseg;
> ti->tcpi_rcv_mss = tp->t_peermss;
>
> - ti->tcpi_last_data_sent = (tcp_now - tp->t_sndtime) * t;
> - ti->tcpi_last_ack_sent = (tcp_now - tp->t_sndacktime) * t;
> - ti->tcpi_last_data_recv = (tcp_now - tp->t_rcvtime) * t;
> - ti->tcpi_last_ack_recv = (tcp_now - tp->t_rcvacktime) * t;
> + ti->tcpi_last_data_sent = (now - tp->t_sndtime) * t;
> + ti->tcpi_last_ack_sent = (now - tp->t_sndacktime) * t;
> + ti->tcpi_last_data_recv = (now - tp->t_rcvtime) * t;
> + ti->tcpi_last_ack_recv = (now - tp->t_rcvacktime) * t;
>
> ti->tcpi_rtt = ((uint64_t)tp->t_srtt * t) >>
> (TCP_RTT_SHIFT + TCP_RTT_BASE_SHIFT);
> @@ -344,9 +346,9 @@ tcp_fill_info(struct tcpcb *tp, struct s
> ti->tcpi_snd_max = tp->snd_max - tp->iss;
>
> ti->tcpi_ts_recent = tp->ts_recent; /* XXX value from the wire */
> - ti->tcpi_ts_recent_age = (tcp_now - tp->ts_recent_age) * t;
> + ti->tcpi_ts_recent_age = (now - tp->ts_recent_age) * t;
> ti->tcpi_rfbuf_cnt = tp->rfbuf_cnt;
> - ti->tcpi_rfbuf_ts = (tcp_now - tp->rfbuf_ts) * t;
> + ti->tcpi_rfbuf_ts = (now - tp->rfbuf_ts) * t;
>
> ti->tcpi_so_rcv_sb_cc = so->so_rcv.sb_cc;
> ti->tcpi_so_rcv_sb_hiwat = so->so_rcv.sb_hiwat;
> Index: netinet/tcp_var.h
> ===================================================================
> RCS file: /data/mirror/openbsd/cvs/src/sys/netinet/tcp_var.h,v
> retrieving revision 1.153
> diff -u -p -r1.153 tcp_var.h
> --- netinet/tcp_var.h 31 Aug 2022 21:23:02 -0000 1.153
> +++ netinet/tcp_var.h 1 Sep 2022 14:47:22 -0000
> @@ -638,10 +638,11 @@ tcpstat_pkt(enum tcpstat_counters pcount
> counters_pkt(tcpcounters, pcounter, bcounter, v);
> }
>
> +extern struct mutex tcp_timer_mtx;
> extern const struct pr_usrreqs tcp_usrreqs;
> extern struct pool tcpcb_pool;
> extern struct inpcbtable tcbtable; /* head of queue of active
> tcpcb's */
> -extern u_int32_t tcp_now; /* for RFC 1323 timestamps */
> +extern uint32_t tcp_now; /* for RFC 1323 timestamps */
> extern int tcp_do_rfc1323; /* enabled/disabled? */
> extern int tcptv_keep_init; /* time to keep alive the initial SYN
> packet */
> extern int tcp_mssdflt; /* default maximum segment size */
> @@ -677,7 +678,7 @@ struct tcpcb *
> struct tcpcb *
> tcp_drop(struct tcpcb *, int);
> int tcp_dooptions(struct tcpcb *, u_char *, int, struct tcphdr *,
> - struct mbuf *, int, struct tcp_opt_info *, u_int);
> + struct mbuf *, int, struct tcp_opt_info *, u_int, uint32_t);
> void tcp_init(void);
> int tcp_input(struct mbuf **, int *, int, int);
> int tcp_mss(struct tcpcb *, int);
> @@ -697,7 +698,7 @@ void tcp_pulloutofband(struct socket *,
> int tcp_reass(struct tcpcb *, struct tcphdr *, struct mbuf *, int *);