Index: sys/netinet/tcp_input.c =================================================================== --- sys/netinet/tcp_input.c +++ sys/netinet/tcp_input.c @@ -3435,7 +3435,13 @@ INP_WLOCK_ASSERT(tp->t_inpcb); TCPSTAT_INC(tcps_rttupdated); - tp->t_rttupdated++; + if (tp->t_rttupdated < UTYPE_MAX(tp->t_rttupdated)) { + /* + * track updates to RTT in tcpcb only the initial few + * rounds explicitly, to save space in tcpcb + */ + tp->t_rttupdated++; + } if ((tp->t_srtt != 0) && (tp->t_rxtshift <= TCP_RTT_INVALIDATE)) { /* * srtt is stored as fixed point with 5 bits after the Index: sys/netinet/tcp_stacks/rack.c =================================================================== --- sys/netinet/tcp_stacks/rack.c +++ sys/netinet/tcp_stacks/rack.c @@ -3680,7 +3680,13 @@ } TCPSTAT_INC(tcps_rttupdated); rack_log_rtt_upd(tp, rack, rtt, o_srtt, o_var); - tp->t_rttupdated++; + if (tp->t_rttupdated < UTYPE_MAX(tp->t_rttupdated)) { + /* + * track updates to RTT in tcpcb only the initial few + * rounds explicitly, to save space in tcpcb + */ + tp->t_rttupdated++; + } #ifdef NETFLIX_STATS stats_voi_update_abs_u32(tp->t_stats, VOI_TCP_RTT, imax(0, rtt)); #endif Index: sys/netinet/tcp_usrreq.c =================================================================== --- sys/netinet/tcp_usrreq.c +++ sys/netinet/tcp_usrreq.c @@ -2622,7 +2622,7 @@ tp->t_rttbest); db_print_indent(indent); - db_printf("t_rttupdated: %lu max_sndwnd: %u t_softerror: %d\n", + db_printf("t_rttupdated: %u max_sndwnd: %u t_softerror: %d\n", tp->t_rttupdated, tp->max_sndwnd, tp->t_softerror); db_print_indent(indent); Index: sys/netinet/tcp_var.h =================================================================== --- sys/netinet/tcp_var.h +++ sys/netinet/tcp_var.h @@ -178,9 +178,9 @@ uint32_t snd_cwnd_prev; /* cwnd prior to retransmit */ uint32_t snd_ssthresh_prev; /* ssthresh prior to retransmit */ tcp_seq snd_recover_prev; /* snd_recover prior to retransmit */ - int t_sndzerowin; /* zero-window updates sent */ - u_long t_rttupdated; /* number of times rtt sampled */ - int snd_numholes; /* number of holes seen by sender */ + uint32_t t_sndzerowin; /* zero-window updates sent (per-flow-stats only) */ + uint8_t t_rttupdated; /* number of times rtt sampled */ + int32_t snd_numholes; /* number of holes seen by sender */ u_int t_badrxtwin; /* window for retransmit recovery */ TAILQ_HEAD(sackhole_head, sackhole) snd_holes; /* SACK scoreboard (sorted) */ @@ -192,18 +192,18 @@ int t_rttlow; /* smallest observerved RTT */ int rfbuf_cnt; /* recv buffer autoscaling byte count */ struct toedev *tod; /* toedev handling this connection */ - int t_sndrexmitpack; /* retransmit packets sent */ - int t_rcvoopack; /* out-of-order packets received */ + uint32_t t_sndrexmitpack; /* retransmit packets sent (per-flow-stats only) */ + uint32_t t_rcvoopack; /* out-of-order packets received (per-flow-stats only) */ void *t_toe; /* TOE pcb pointer */ struct cc_algo *cc_algo; /* congestion control algorithm */ struct cc_var *ccv; /* congestion control specific vars */ struct osd *osd; /* storage for Khelp module data */ - int t_bytes_acked; /* # bytes acked during current RTT */ - u_int t_maxunacktime; - u_int t_keepinit; /* time to establish connection */ - u_int t_keepidle; /* time before keepalive probes begin */ - u_int t_keepintvl; /* interval between keepalives */ - u_int t_keepcnt; /* number of keepalives before close */ + uint32_t t_bytes_acked; /* # bytes acked during current RTT */ + uint32_t t_maxunacktime; + uint32_t t_keepinit; /* time to establish connection */ + uint32_t t_keepidle; /* time before keepalive probes begin */ + uint32_t t_keepintvl; /* interval between keepalives */ + uint32_t t_keepcnt; /* number of keepalives before close */ int t_dupacks; /* consecutive dup acks recd */ int t_lognum; /* Number of log entries */ struct tcp_log_stailq t_logs; /* Log buffer */ @@ -495,6 +495,14 @@ max((tp)->t_rttmin, (((tp)->t_srtt >> (TCP_RTT_SHIFT - TCP_DELTA_SHIFT)) \ + (tp)->t_rttvar) >> TCP_DELTA_SHIFT) +/* + * programmatically determine the maximum value of + * a signed or unsigned type, without integer overflow + */ +#define UTYPE_MAX(x) \ + ((((1 << (sizeof(x)*8 - 1)) - 1) * 2) + 1) +#define TYPE_MAX(x) \ + ((((1 << (sizeof(x)*8 - 2)) - 1) * 2) + 1) /* * TCP statistics. * Many of these should be kept per connection, @@ -696,9 +704,9 @@ int64_t spare64[8]; int32_t t_state; /* (s,p) */ uint32_t t_flags; /* (s,p) */ - int32_t t_sndzerowin; /* (s) */ - int32_t t_sndrexmitpack; /* (s) */ - int32_t t_rcvoopack; /* (s) */ + uint32_t t_sndzerowin; /* (s) */ + uint32_t t_sndrexmitpack; /* (s) */ + uint32_t t_rcvoopack; /* (s) */ int32_t t_rcvtime; /* (s) */ int32_t tt_rexmt; /* (s) */ int32_t tt_persist; /* (s) */