Fix a logical error in T/TCP: when we actively open a connection, we
have to decide whether to send a CC or CCnew option in our SYN segment depending on the contents of our TAO cache. This decision has to be made once when the connection starts. The earlier code delayed this decision until the segment was assembled in tcp_output() and retransmitted SYN segments could have different CC options. Reviewed by: Richard Stevens, davidg, wollman
This commit is contained in:
parent
042cd119d3
commit
a45d27261d
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=12045
@ -31,7 +31,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)tcp_output.c 8.4 (Berkeley) 5/24/95
|
||||
* $Id: tcp_output.c,v 1.14 1995/09/22 20:05:58 wollman Exp $
|
||||
* $Id: tcp_output.c,v 1.15 1995/10/16 18:21:12 wollman Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
@ -384,15 +384,8 @@ tcp_output(tp)
|
||||
case TH_SYN:
|
||||
opt[optlen++] = TCPOPT_NOP;
|
||||
opt[optlen++] = TCPOPT_NOP;
|
||||
|
||||
if (taop->tao_ccsent != 0 &&
|
||||
CC_GEQ(tp->cc_send, taop->tao_ccsent)) {
|
||||
opt[optlen++] = TCPOPT_CC;
|
||||
taop->tao_ccsent = tp->cc_send;
|
||||
} else {
|
||||
opt[optlen++] = TCPOPT_CCNEW;
|
||||
taop->tao_ccsent = 0;
|
||||
}
|
||||
opt[optlen++] = tp->t_flags & TF_SENDCCNEW ?
|
||||
TCPOPT_CCNEW : TCPOPT_CC;
|
||||
opt[optlen++] = TCPOLEN_CC;
|
||||
*(u_int32_t *)&opt[optlen] = htonl(tp->cc_send);
|
||||
optlen += 4;
|
||||
|
@ -31,7 +31,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* From: @(#)tcp_usrreq.c 8.2 (Berkeley) 1/3/94
|
||||
* $Id: tcp_usrreq.c,v 1.16 1995/09/13 17:54:03 wollman Exp $
|
||||
* $Id: tcp_usrreq.c,v 1.17 1995/10/29 21:30:25 olah Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
@ -407,6 +407,8 @@ tcp_connect(tp, nam)
|
||||
struct sockaddr_in *sin = mtod(nam, struct sockaddr_in *);
|
||||
struct sockaddr_in *ifaddr;
|
||||
int error;
|
||||
struct rmxp_tao *taop;
|
||||
struct rmxp_tao tao_noncached;
|
||||
|
||||
if (inp->inp_lport == 0) {
|
||||
error = in_pcbbind(inp, NULL);
|
||||
@ -459,7 +461,24 @@ tcp_connect(tp, nam)
|
||||
tp->t_timer[TCPT_KEEP] = TCPTV_KEEP_INIT;
|
||||
tp->iss = tcp_iss; tcp_iss += TCP_ISSINCR/2;
|
||||
tcp_sendseqinit(tp);
|
||||
|
||||
/*
|
||||
* Generate a CC value for this connection and
|
||||
* check whether CC or CCnew should be used.
|
||||
*/
|
||||
if ((taop = tcp_gettaocache(tp->t_inpcb)) == NULL) {
|
||||
taop = &tao_noncached;
|
||||
bzero(taop, sizeof(*taop));
|
||||
}
|
||||
|
||||
tp->cc_send = CC_INC(tcp_ccgen);
|
||||
if (taop->tao_ccsent != 0 &&
|
||||
CC_GEQ(tp->cc_send, taop->tao_ccsent)) {
|
||||
taop->tao_ccsent = tp->cc_send;
|
||||
} else {
|
||||
taop->tao_ccsent = 0;
|
||||
tp->t_flags |= TF_SENDCCNEW;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -31,7 +31,7 @@
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)tcp_var.h 8.4 (Berkeley) 5/24/95
|
||||
* $Id: tcp_var.h,v 1.20 1995/10/12 17:37:25 wollman Exp $
|
||||
* $Id: tcp_var.h,v 1.21 1995/10/16 18:21:26 wollman Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETINET_TCP_VAR_H_
|
||||
@ -70,6 +70,7 @@ struct tcpcb {
|
||||
#define TF_NOPUSH 0x1000 /* don't push */
|
||||
#define TF_REQ_CC 0x2000 /* have/will request CC */
|
||||
#define TF_RCVD_CC 0x4000 /* a CC was received in SYN */
|
||||
#define TF_SENDCCNEW 0x8000 /* send CCnew instead of CC in SYN */
|
||||
|
||||
struct tcpiphdr *t_template; /* skeletal packet for transmit */
|
||||
struct inpcb *t_inpcb; /* back pointer to internet pcb */
|
||||
|
Loading…
Reference in New Issue
Block a user