tcp_timer.c revision 130989
142421Syokota/* 242421Syokota * Copyright (c) 1982, 1986, 1988, 1990, 1993, 1995 342421Syokota * The Regents of the University of California. All rights reserved. 442421Syokota * 542421Syokota * Redistribution and use in source and binary forms, with or without 642421Syokota * modification, are permitted provided that the following conditions 742421Syokota * are met: 842421Syokota * 1. Redistributions of source code must retain the above copyright 942421Syokota * notice, this list of conditions and the following disclaimer. 1042421Syokota * 2. Redistributions in binary form must reproduce the above copyright 1142421Syokota * notice, this list of conditions and the following disclaimer in the 1242421Syokota * documentation and/or other materials provided with the distribution. 1342421Syokota * 4. Neither the name of the University nor the names of its contributors 1442421Syokota * may be used to endorse or promote products derived from this software 1542421Syokota * without specific prior written permission. 1642421Syokota * 1742421Syokota * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 1842421Syokota * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1942421Syokota * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2042421Syokota * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 2142421Syokota * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2242421Syokota * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2342421Syokota * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2442421Syokota * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2542421Syokota * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2642421Syokota * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2742421Syokota * SUCH DAMAGE. 28119418Sobrien * 29119418Sobrien * @(#)tcp_timer.c 8.2 (Berkeley) 5/24/95 30119418Sobrien * $FreeBSD: head/sys/netinet/tcp_timer.c 130989 2004-06-23 21:04:37Z ps $ 3142421Syokota */ 3242421Syokota 3342421Syokota#include "opt_inet6.h" 3442421Syokota#include "opt_tcpdebug.h" 3542421Syokota#include "opt_tcp_sack.h" 3642421Syokota 3742421Syokota#include <sys/param.h> 38139193Sphk#include <sys/kernel.h> 3942421Syokota#include <sys/lock.h> 40164033Srwatson#include <sys/mbuf.h> 41112050Sdwmalone#include <sys/mutex.h> 42180777Sed#include <sys/protosw.h> 43112050Sdwmalone#include <sys/socket.h> 4442421Syokota#include <sys/socketvar.h> 4542421Syokota#include <sys/sysctl.h> 4666834Sphk#include <sys/systm.h> 4742421Syokota 4842421Syokota#include <net/route.h> 4942421Syokota 50183397Sed#include <netinet/in.h> 5150154Syokota#include <netinet/in_pcb.h> 52193512Sed#include <netinet/in_systm.h> 53193512Sed#ifdef INET6 54193512Sed#include <netinet6/in6_pcb.h> 5550154Syokota#endif 5650154Syokota#include <netinet/ip_var.h> 5750154Syokota#include <netinet/tcp.h> 5850154Syokota#include <netinet/tcp_fsm.h> 59193512Sed#include <netinet/tcp_timer.h> 60193512Sed#include <netinet/tcp_var.h> 61193512Sed#include <netinet/tcpip.h> 6250154Syokota#ifdef TCPDEBUG 6350154Syokota#include <netinet/tcp_debug.h> 6460938Sjake#endif 65127751Sdes 6654545Syokotastatic int 6778161Spetersysctl_msec_to_ticks(SYSCTL_HANDLER_ARGS) 6878161Speter{ 6942421Syokota int error, s, tt; 7042421Syokota 7142421Syokota tt = *(int *)oidp->oid_arg1; 7242421Syokota s = (int)((int64_t)tt * 1000 / hz); 7342421Syokota 7442421Syokota error = sysctl_handle_int(oidp, &s, 0, req); 7542421Syokota if (error || !req->newptr) 7642564Syokota return (error); 7742564Syokota 7842421Syokota tt = (int)((int64_t)s * hz / 1000); 7942564Syokota if (tt < 1) 8042421Syokota return (EINVAL); 8142421Syokota 8242421Syokota *(int *)oidp->oid_arg1 = tt; 83112050Sdwmalone return (0); 84227309Sed} 85112050Sdwmalone 86112050Sdwmaloneint tcp_keepinit; 87112050SdwmaloneSYSCTL_PROC(_net_inet_tcp, TCPCTL_KEEPINIT, keepinit, CTLTYPE_INT|CTLFLAG_RW, 8842421Syokota &tcp_keepinit, 0, sysctl_msec_to_ticks, "I", ""); 8942421Syokota 9044628Syokotaint tcp_keepidle; 9142421SyokotaSYSCTL_PROC(_net_inet_tcp, TCPCTL_KEEPIDLE, keepidle, CTLTYPE_INT|CTLFLAG_RW, 9242421Syokota &tcp_keepidle, 0, sysctl_msec_to_ticks, "I", ""); 9342421Syokota 9442421Syokotaint tcp_keepintvl; 9542421SyokotaSYSCTL_PROC(_net_inet_tcp, TCPCTL_KEEPINTVL, keepintvl, CTLTYPE_INT|CTLFLAG_RW, 9642421Syokota &tcp_keepintvl, 0, sysctl_msec_to_ticks, "I", ""); 9742421Syokota 9842421Syokotaint tcp_delacktime; 99298848SpfgSYSCTL_PROC(_net_inet_tcp, TCPCTL_DELACKTIME, delacktime, 10069781Sdwmalone CTLTYPE_INT|CTLFLAG_RW, &tcp_delacktime, 0, sysctl_msec_to_ticks, "I", 10144628Syokota "Time before a delayed ACK is sent"); 10244628Syokota 103127752Sdesint tcp_msl; 10444628SyokotaSYSCTL_PROC(_net_inet_tcp, OID_AUTO, msl, CTLTYPE_INT|CTLFLAG_RW, 10569781Sdwmalone &tcp_msl, 0, sysctl_msec_to_ticks, "I", "Maximum segment lifetime"); 10669781Sdwmalone 10744628Syokotaint tcp_rexmit_min; 10844628SyokotaSYSCTL_PROC(_net_inet_tcp, OID_AUTO, rexmit_min, CTLTYPE_INT|CTLFLAG_RW, 10944628Syokota &tcp_rexmit_min, 0, sysctl_msec_to_ticks, "I", "Minimum Retransmission Timeout"); 110127752Sdes 11144628Syokotaint tcp_rexmit_slop; 11242421SyokotaSYSCTL_PROC(_net_inet_tcp, OID_AUTO, rexmit_slop, CTLTYPE_INT|CTLFLAG_RW, 11342421Syokota &tcp_rexmit_slop, 0, sysctl_msec_to_ticks, "I", "Retransmission Timer Slop"); 11442421Syokota 11542421Syokotastatic int always_keepalive = 1; 11642421SyokotaSYSCTL_INT(_net_inet_tcp, OID_AUTO, always_keepalive, CTLFLAG_RW, 11742421Syokota &always_keepalive , 0, "Assume SO_KEEPALIVE on all TCP connections"); 11842421Syokota 11942421Syokotastatic int tcp_keepcnt = TCPTV_KEEPCNT; 12042421Syokota /* max idle probes */ 12142421Syokotaint tcp_maxpersistidle; 12242421Syokota /* max idle time in persist */ 12342421Syokotaint tcp_maxidle; 12442421Syokota 12544628Syokota/* 126127752Sdes * Tcp protocol timeout routine called every 500 ms. 12742421Syokota * Updates timestamps used for TCP 12842421Syokota * causes finite state machine actions if timers expire. 12942421Syokota */ 13042421Syokotavoid 13142421Syokotatcp_slowtimo() 13242421Syokota{ 13342421Syokota int s; 13442421Syokota 13542421Syokota s = splnet(); 13642421Syokota tcp_maxidle = tcp_keepcnt * tcp_keepintvl; 13742421Syokota splx(s); 13842421Syokota INP_INFO_WLOCK(&tcbinfo); 13942421Syokota (void) tcp_timer_2msl_tw(0); 14042421Syokota INP_INFO_WUNLOCK(&tcbinfo); 14142421Syokota} 14242421Syokota 14342421Syokota/* 14442421Syokota * Cancel all timers for TCP tp. 14544628Syokota */ 14642421Syokotavoid 14742421Syokotatcp_canceltimers(tp) 14842421Syokota struct tcpcb *tp; 14942421Syokota{ 15042421Syokota callout_stop(tp->tt_2msl); 15142421Syokota callout_stop(tp->tt_persist); 15242421Syokota callout_stop(tp->tt_keep); 15342421Syokota callout_stop(tp->tt_rexmt); 15444628Syokota} 15544628Syokota 15654382Syokotaint tcp_syn_backoff[TCP_MAXRXTSHIFT + 1] = 15780040Syokota { 1, 1, 1, 1, 1, 2, 4, 8, 16, 32, 64, 64, 64 }; 15842421Syokota 15942421Syokotaint tcp_backoff[TCP_MAXRXTSHIFT + 1] = 16042421Syokota { 1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 512, 512, 512 }; 16142421Syokota 16242421Syokotastatic int tcp_totbackoff = 2559; /* sum of tcp_backoff[] */ 16342421Syokota 16442421Syokota/* 16542421Syokota * TCP timer processing. 16642421Syokota */ 16742421Syokota 16842421Syokotavoid 16942421Syokotatcp_timer_delack(xtp) 17054545Syokota void *xtp; 17154545Syokota{ 17254545Syokota struct tcpcb *tp = xtp; 17354545Syokota int s; 17454545Syokota struct inpcb *inp; 175127752Sdes 17654545Syokota s = splnet(); 177127752Sdes INP_INFO_RLOCK(&tcbinfo); 17854545Syokota inp = tp->t_inpcb; 17954545Syokota if (!inp) { 18054545Syokota INP_INFO_RUNLOCK(&tcbinfo); 18154545Syokota splx(s); 18254545Syokota return; 18360938Sjake } 18454545Syokota INP_LOCK(inp); 185127752Sdes INP_INFO_RUNLOCK(&tcbinfo); 18654545Syokota if (callout_pending(tp->tt_delack) || !callout_active(tp->tt_delack)) { 18754545Syokota INP_UNLOCK(inp); 18842421Syokota splx(s); 18942421Syokota return; 19042421Syokota } 19142421Syokota callout_deactivate(tp->tt_delack); 19247295Syokota 19347295Syokota tp->t_flags |= TF_ACKNOW; 194156126Semax tcpstat.tcps_delack++; 195156126Semax (void) tcp_output(tp); 19642421Syokota INP_UNLOCK(inp); 19742421Syokota splx(s); 198156126Semax} 199156126Semax 20042421Syokotavoid 20142421Syokotatcp_timer_2msl(xtp) 20242421Syokota void *xtp; 20342421Syokota{ 20444628Syokota struct tcpcb *tp = xtp; 20544628Syokota int s; 206127752Sdes struct inpcb *inp; 20744628Syokota#ifdef TCPDEBUG 20842421Syokota int ostate; 20942421Syokota 21042421Syokota ostate = tp->t_state; 21142421Syokota#endif 21242421Syokota s = splnet(); 21342421Syokota INP_INFO_WLOCK(&tcbinfo); 21442421Syokota inp = tp->t_inpcb; 21542421Syokota if (!inp) { 21642421Syokota INP_INFO_WUNLOCK(&tcbinfo); 21754545Syokota splx(s); 21854545Syokota return; 21954545Syokota } 22054545Syokota INP_LOCK(inp); 221156126Semax tcp_free_sackholes(tp); 222156126Semax if (callout_pending(tp->tt_2msl) || !callout_active(tp->tt_2msl)) { 223156126Semax INP_UNLOCK(tp->t_inpcb); 224156126Semax INP_INFO_WUNLOCK(&tcbinfo); 225156126Semax splx(s); 226156126Semax return; 227213770Srpaulo } 228156126Semax callout_deactivate(tp->tt_2msl); 229156126Semax /* 230127752Sdes * 2 MSL timeout in shutdown went off. If we're closed but 23154545Syokota * still waiting for peer to close and connection has been idle 23254545Syokota * too long, or if 2MSL time is up from TIME_WAIT, delete connection 23378161Speter * control block. Otherwise, check again in a bit. 23478161Speter */ 23542421Syokota if (tp->t_state != TCPS_TIME_WAIT && 23642421Syokota (ticks - tp->t_rcvtime) <= tcp_maxidle) 23742421Syokota callout_reset(tp->tt_2msl, tcp_keepintvl, 238156126Semax tcp_timer_2msl, tp); 239156126Semax else 240156126Semax tp = tcp_close(tp); 241156126Semax 242156126Semax#ifdef TCPDEBUG 243156126Semax if (tp && (tp->t_inpcb->inp_socket->so_options & SO_DEBUG)) 244213770Srpaulo tcp_trace(TA_USER, ostate, tp, (void *)0, (struct tcphdr *)0, 245156126Semax PRU_SLOWTIMO); 246156126Semax#endif 247127752Sdes if (tp) 24842421Syokota INP_UNLOCK(inp); 24942421Syokota INP_INFO_WUNLOCK(&tcbinfo); 25042421Syokota splx(s); 251127752Sdes} 25242421Syokota 25342421Syokotastruct twlist { 25442421Syokota LIST_HEAD(, tcptw) tw_list; 25542421Syokota struct tcptw tw_tail; 25642421Syokota}; 25742421Syokota#define TWLIST_NLISTS 2 25842421Syokotastatic struct twlist twl_2msl[TWLIST_NLISTS]; 25942421Syokotastatic struct twlist *tw_2msl_list[] = { &twl_2msl[0], &twl_2msl[1], NULL }; 26042421Syokota 261127752Sdesvoid 26242421Syokotatcp_timer_init(void) 263127752Sdes{ 26442421Syokota int i; 26542421Syokota struct twlist *twl; 26642421Syokota 26742421Syokota for (i = 0; i < TWLIST_NLISTS; i++) { 268127752Sdes twl = &twl_2msl[i]; 26942421Syokota LIST_INIT(&twl->tw_list); 27042421Syokota LIST_INSERT_HEAD(&twl->tw_list, &twl->tw_tail, tw_2msl); 271127752Sdes } 27242421Syokota} 27342421Syokota 27442421Syokotavoid 275127752Sdestcp_timer_2msl_reset(struct tcptw *tw, int timeo) 27642421Syokota{ 27742421Syokota int i; 27842421Syokota struct tcptw *tw_tail; 27942421Syokota 28042421Syokota if (tw->tw_time != 0) 28142421Syokota LIST_REMOVE(tw, tw_2msl); 28242421Syokota tw->tw_time = timeo + ticks; 283127752Sdes i = timeo > tcp_msl ? 1 : 0; 28442421Syokota tw_tail = &twl_2msl[i].tw_tail; 28542421Syokota LIST_INSERT_BEFORE(tw_tail, tw, tw_2msl); 286298955Spfg} 28742421Syokota 28842421Syokotavoid 28942421Syokotatcp_timer_2msl_stop(struct tcptw *tw) 29047295Syokota{ 29147295Syokota 29242421Syokota if (tw->tw_time != 0) 29354545Syokota LIST_REMOVE(tw, tw_2msl); 29454545Syokota} 295127752Sdes 29654545Syokotastruct tcptw * 29778161Spetertcp_timer_2msl_tw(int reuse) 29878161Speter{ 29942421Syokota struct tcptw *tw, *tw_tail; 300127752Sdes struct twlist *twl; 30142421Syokota int i; 30242421Syokota 303127752Sdes for (i = 0; i < 2; i++) { 30442421Syokota twl = tw_2msl_list[i]; 30542421Syokota tw_tail = &twl->tw_tail; 30642421Syokota for (;;) { 30742421Syokota tw = LIST_FIRST(&twl->tw_list); 30842421Syokota if (tw == tw_tail || (!reuse && tw->tw_time > ticks)) 30942421Syokota break; 31042421Syokota INP_LOCK(tw->tw_inpcb); 31142421Syokota if (tcp_twclose(tw, reuse) != NULL) 31242421Syokota return (tw); 313147980Semax } 314147980Semax } 315147980Semax return (NULL); 316147980Semax} 31742421Syokota 318147980Semaxvoid 31942421Syokotatcp_timer_keep(xtp) 32042421Syokota void *xtp; 32142421Syokota{ 322147980Semax struct tcpcb *tp = xtp; 323147980Semax struct tcptemp *t_template; 324147980Semax int s; 325147980Semax struct inpcb *inp; 32642421Syokota#ifdef TCPDEBUG 32742421Syokota int ostate; 32842421Syokota 32942421Syokota ostate = tp->t_state; 33042421Syokota#endif 33142421Syokota s = splnet(); 33242421Syokota INP_INFO_WLOCK(&tcbinfo); 33342421Syokota inp = tp->t_inpcb; 334127752Sdes if (!inp) { 33542421Syokota INP_INFO_WUNLOCK(&tcbinfo); 336147980Semax splx(s); 337127752Sdes return; 33842421Syokota } 33942421Syokota INP_LOCK(inp); 340147980Semax if (callout_pending(tp->tt_keep) || !callout_active(tp->tt_keep)) { 341147980Semax INP_UNLOCK(inp); 342147980Semax INP_INFO_WUNLOCK(&tcbinfo); 343147980Semax splx(s); 344147980Semax return; 345147980Semax } 346147980Semax callout_deactivate(tp->tt_keep); 34742421Syokota /* 34842421Syokota * Keep-alive timer went off; send something 34942421Syokota * or drop connection if idle for too long. 35042421Syokota */ 35142421Syokota tcpstat.tcps_keeptimeo++; 35242421Syokota if (tp->t_state < TCPS_ESTABLISHED) 35342421Syokota goto dropit; 35442421Syokota if ((always_keepalive || inp->inp_socket->so_options & SO_KEEPALIVE) && 35542421Syokota tp->t_state <= TCPS_CLOSING) { 356127752Sdes if ((ticks - tp->t_rcvtime) >= tcp_keepidle + tcp_maxidle) 35742421Syokota goto dropit; 35842421Syokota /* 35942421Syokota * Send a packet designed to force a response 36042421Syokota * if the peer is up and reachable: 36142421Syokota * either an ACK if the connection is still alive, 36242421Syokota * or an RST if the peer has closed the connection 363127752Sdes * due to timeout or reboot. 36442421Syokota * Using sequence number tp->snd_una-1 36542421Syokota * causes the transmitted zero-length segment 36642421Syokota * to lie outside the receive window; 36742421Syokota * by the protocol spec, this requires the 36842421Syokota * correspondent TCP to respond. 369174984Swkoszek */ 37042421Syokota tcpstat.tcps_keepprobe++; 37142421Syokota t_template = tcpip_maketemplate(inp); 372127752Sdes if (t_template) { 37342421Syokota tcp_respond(tp, t_template->tt_ipgen, 37442421Syokota &t_template->tt_t, (struct mbuf *)NULL, 37542421Syokota tp->rcv_nxt, tp->snd_una - 1, 0); 37642421Syokota (void) m_free(dtom(t_template)); 37742421Syokota } 37842421Syokota callout_reset(tp->tt_keep, tcp_keepintvl, tcp_timer_keep, tp); 37942421Syokota } else 38042421Syokota callout_reset(tp->tt_keep, tcp_keepidle, tcp_timer_keep, tp); 38142421Syokota 38242421Syokota#ifdef TCPDEBUG 38342421Syokota if (inp->inp_socket->so_options & SO_DEBUG) 38442421Syokota tcp_trace(TA_USER, ostate, tp, (void *)0, (struct tcphdr *)0, 38542421Syokota PRU_SLOWTIMO); 38642421Syokota#endif 38742421Syokota INP_UNLOCK(inp); 38842421Syokota INP_INFO_WUNLOCK(&tcbinfo); 38942421Syokota splx(s); 39042421Syokota return; 391174984Swkoszek 39242421Syokotadropit: 39342421Syokota tcpstat.tcps_keepdrops++; 39442421Syokota tp = tcp_drop(tp, ETIMEDOUT); 395127752Sdes 39642421Syokota#ifdef TCPDEBUG 39742421Syokota if (tp && (tp->t_inpcb->inp_socket->so_options & SO_DEBUG)) 39842421Syokota tcp_trace(TA_USER, ostate, tp, (void *)0, (struct tcphdr *)0, 39942421Syokota PRU_SLOWTIMO); 40042421Syokota#endif 40142421Syokota if (tp) 40242421Syokota INP_UNLOCK(tp->t_inpcb); 40342421Syokota INP_INFO_WUNLOCK(&tcbinfo); 40442421Syokota splx(s); 40542421Syokota} 40642421Syokota 40742421Syokotavoid 40842421Syokotatcp_timer_persist(xtp) 40942421Syokota void *xtp; 41042421Syokota{ 41142421Syokota struct tcpcb *tp = xtp; 41242421Syokota int s; 41342421Syokota struct inpcb *inp; 41442421Syokota#ifdef TCPDEBUG 41542421Syokota int ostate; 41642421Syokota 41742421Syokota ostate = tp->t_state; 418127752Sdes#endif 41942421Syokota s = splnet(); 42042421Syokota INP_INFO_WLOCK(&tcbinfo); 42142421Syokota inp = tp->t_inpcb; 42242421Syokota if (!inp) { 42342421Syokota INP_INFO_WUNLOCK(&tcbinfo); 42442421Syokota splx(s); 42542421Syokota return; 426127752Sdes } 42750154Syokota INP_LOCK(inp); 428127752Sdes if (callout_pending(tp->tt_persist) || !callout_active(tp->tt_persist)){ 42942421Syokota INP_UNLOCK(inp); 430127752Sdes INP_INFO_WUNLOCK(&tcbinfo); 431127752Sdes splx(s); 43242421Syokota return; 43342421Syokota } 43442421Syokota callout_deactivate(tp->tt_persist); 43542421Syokota /* 43642421Syokota * Persistance timer into zero window. 43742421Syokota * Force a byte to be output, if possible. 43842421Syokota */ 43942421Syokota tcpstat.tcps_persisttimeo++; 44042421Syokota /* 44142421Syokota * Hack: if the peer is dead/unreachable, we do not 44242421Syokota * time out if the window is closed. After a full 44347295Syokota * backoff, drop the connection if the idle time 44447295Syokota * (no responses to probes) reaches the maximum 44542421Syokota * backoff that we would use if retransmitting. 44654545Syokota */ 44754545Syokota if (tp->t_rxtshift == TCP_MAXRXTSHIFT && 44854545Syokota ((ticks - tp->t_rcvtime) >= tcp_maxpersistidle || 44954545Syokota (ticks - tp->t_rcvtime) >= TCP_REXMTVAL(tp) * tcp_totbackoff)) { 45078161Speter tcpstat.tcps_persistdrop++; 45178161Speter tp = tcp_drop(tp, ETIMEDOUT); 45242421Syokota goto out; 45342421Syokota } 45442421Syokota tcp_setpersist(tp); 45542421Syokota tp->t_force = 1; 456127752Sdes (void) tcp_output(tp); 45742421Syokota tp->t_force = 0; 45842421Syokota 45942421Syokotaout: 46042421Syokota#ifdef TCPDEBUG 46142421Syokota if (tp && tp->t_inpcb->inp_socket->so_options & SO_DEBUG) 46242421Syokota tcp_trace(TA_USER, ostate, tp, (void *)0, (struct tcphdr *)0, 46342421Syokota PRU_SLOWTIMO); 46442421Syokota#endif 46542421Syokota if (tp) 46642421Syokota INP_UNLOCK(inp); 467183397Sed INP_INFO_WUNLOCK(&tcbinfo); 46842421Syokota splx(s); 46950154Syokota} 47050154Syokota 47150154Syokotavoid 47250154Syokotatcp_timer_rexmt(xtp) 47350154Syokota void *xtp; 47450154Syokota{ 47542421Syokota struct tcpcb *tp = xtp; 47642421Syokota int s; 47742421Syokota int rexmt; 478126080Sphk int headlocked; 479126080Sphk struct inpcb *inp; 480111815Sphk#ifdef TCPDEBUG 481111815Sphk int ostate; 482111815Sphk 483111815Sphk ostate = tp->t_state; 484111815Sphk#endif 485111815Sphk s = splnet(); 486111815Sphk INP_INFO_WLOCK(&tcbinfo); 48742421Syokota headlocked = 1; 48842421Syokota inp = tp->t_inpcb; 48942421Syokota if (!inp) { 49050154Syokota INP_INFO_WUNLOCK(&tcbinfo); 49142421Syokota splx(s); 49242421Syokota return; 49342421Syokota } 494127752Sdes INP_LOCK(inp); 49542421Syokota if (callout_pending(tp->tt_rexmt) || !callout_active(tp->tt_rexmt)) { 496127752Sdes INP_UNLOCK(inp); 49742421Syokota INP_INFO_WUNLOCK(&tcbinfo); 498127751Sdes splx(s); 499127751Sdes return; 500125087Sdes } 501120502Sphk callout_deactivate(tp->tt_rexmt); 502127751Sdes tcp_free_sackholes(tp); 50342421Syokota /* 504127752Sdes * Retransmission timer went off. Message has not 50542421Syokota * been acked within retransmit interval. Back off 50642421Syokota * to a longer retransmit interval and retransmit one segment. 50742421Syokota */ 50850154Syokota if (++tp->t_rxtshift > TCP_MAXRXTSHIFT) { 50942421Syokota tp->t_rxtshift = TCP_MAXRXTSHIFT; 51054545Syokota tcpstat.tcps_timeoutdrop++; 51142421Syokota tp = tcp_drop(tp, tp->t_softerror ? 512127752Sdes tp->t_softerror : ETIMEDOUT); 51342421Syokota goto out; 514127752Sdes } 51542421Syokota INP_INFO_WUNLOCK(&tcbinfo); 516120502Sphk headlocked = 0; 517120502Sphk if (tp->t_rxtshift == 1) { 51854545Syokota /* 519127752Sdes * first retransmit; record ssthresh and cwnd so they can 52042421Syokota * be recovered if this turns out to be a "bad" retransmit. 52142421Syokota * A retransmit is considered "bad" if an ACK for this 52242421Syokota * segment is received within RTT/2 interval; the assumption 52342421Syokota * here is that the ACK was already in flight. See 52442421Syokota * "On Estimating End-to-End Network Path Properties" by 52542421Syokota * Allman and Paxson for more details. 52642421Syokota */ 52742421Syokota tp->snd_cwnd_prev = tp->snd_cwnd; 528193512Sed tp->snd_ssthresh_prev = tp->snd_ssthresh; 529193512Sed tp->snd_recover_prev = tp->snd_recover; 530193512Sed if (IN_FASTRECOVERY(tp)) 531193512Sed tp->t_flags |= TF_WASFRECOVERY; 53242421Syokota else 533193512Sed tp->t_flags &= ~TF_WASFRECOVERY; 534193512Sed tp->t_badrxtwin = ticks + (tp->t_srtt >> (TCP_RTT_SHIFT + 1)); 535193512Sed } 536193512Sed tcpstat.tcps_rexmttimeo++; 537193512Sed if (tp->t_state == TCPS_SYN_SENT) 538193512Sed rexmt = TCP_REXMTVAL(tp) * tcp_syn_backoff[tp->t_rxtshift]; 539193512Sed else 540193512Sed rexmt = TCP_REXMTVAL(tp) * tcp_backoff[tp->t_rxtshift]; 541193512Sed TCPT_RANGESET(tp->t_rxtcur, rexmt, 542193512Sed tp->t_rttmin, TCPTV_REXMTMAX); 543193512Sed /* 544193512Sed * Disable rfc1323 and rfc1644 if we havn't got any response to 545193512Sed * our third SYN to work-around some broken terminal servers 546193512Sed * (most of which have hopefully been retired) that have bad VJ 547193512Sed * header compression code which trashes TCP segments containing 548193512Sed * unknown-to-them TCP options. 549193512Sed */ 550193512Sed if ((tp->t_state == TCPS_SYN_SENT) && (tp->t_rxtshift == 3)) 551193512Sed tp->t_flags &= ~(TF_REQ_SCALE|TF_REQ_TSTMP|TF_REQ_CC); 552193512Sed /* 553193512Sed * If we backed off this far, our srtt estimate is probably bogus. 554193512Sed * Clobber it so we'll take the next rtt measurement as our srtt; 555193512Sed * move the current srtt into rttvar to keep the current 556193512Sed * retransmit times until then. 557193512Sed */ 558193512Sed if (tp->t_rxtshift > TCP_MAXRXTSHIFT / 4) { 559193512Sed#ifdef INET6 560193512Sed if ((tp->t_inpcb->inp_vflag & INP_IPV6) != 0) 56142421Syokota in6_losing(tp->t_inpcb); 56242421Syokota else 56350154Syokota#endif 564130585Sphk tp->t_rttvar += (tp->t_srtt >> TCP_RTT_SHIFT); 56542421Syokota tp->t_srtt = 0; 56650154Syokota } 56750154Syokota tp->snd_nxt = tp->snd_una; 56842421Syokota tp->snd_recover = tp->snd_max; 56942421Syokota /* 57042421Syokota * Force a segment to be sent. 57142421Syokota */ 57250154Syokota tp->t_flags |= TF_ACKNOW; 57350154Syokota /* 57450154Syokota * If timing a segment in this window, stop the timer. 57542421Syokota */ 576127752Sdes tp->t_rtttime = 0; 57742421Syokota /* 57842421Syokota * Close the congestion window down to one segment 579127751Sdes * (we'll open it by one segment for each ack we get). 58042421Syokota * Since we probably have a window's worth of unacked 58142421Syokota * data accumulated, this "slow start" keeps us from 582127752Sdes * dumping all that data as back-to-back packets (which 58342421Syokota * might overwhelm an intermediate gateway). 58442421Syokota * 58542421Syokota * There are two phases to the opening: Initially we 58642421Syokota * open by one mss on each ack. This makes the window 58742421Syokota * size increase exponentially with time. If the 58842421Syokota * window is larger than the path can handle, this 58942421Syokota * exponential growth results in dropped packet(s) 59042421Syokota * almost immediately. To get more time between 59142421Syokota * drops but still "push" the network to take advantage 592193512Sed * of improving conditions, we switch from exponential 59342421Syokota * to linear window opening at some threshhold size. 59442421Syokota * For a threshhold, we use half the current window 595127752Sdes * size, truncated to a multiple of the mss. 59642421Syokota * 59742421Syokota * (the minimum cwnd that will give us exponential 59850154Syokota * growth is 2 mss. We don't allow the threshhold 599130585Sphk * to go below this.) 60042421Syokota */ 60150154Syokota { 60250154Syokota u_int win = min(tp->snd_wnd, tp->snd_cwnd) / 2 / tp->t_maxseg; 60342421Syokota if (win < 2) 60442421Syokota win = 2; 60542421Syokota tp->snd_cwnd = tp->t_maxseg; 60642421Syokota tp->snd_ssthresh = win * tp->t_maxseg; 60750154Syokota tp->t_dupacks = 0; 60842421Syokota } 60942421Syokota EXIT_FASTRECOVERY(tp); 61050154Syokota (void) tcp_output(tp); 61150154Syokota 61250154Syokotaout: 61350154Syokota#ifdef TCPDEBUG 61450154Syokota if (tp && (tp->t_inpcb->inp_socket->so_options & SO_DEBUG)) 61550154Syokota tcp_trace(TA_USER, ostate, tp, (void *)0, (struct tcphdr *)0, 61650154Syokota PRU_SLOWTIMO); 61742421Syokota#endif 618127752Sdes if (tp) 61942421Syokota INP_UNLOCK(inp); 62042421Syokota if (headlocked) 62150154Syokota INP_INFO_WUNLOCK(&tcbinfo); 622130585Sphk splx(s); 62342421Syokota} 62450154Syokota