Date: Tue, 03 Dec 2002 17:19:15 -0500 From: Aniruddha Bohra <bohra@cs.rutgers.edu> To: freebsd-net <freebsd-net@freebsd.org>, freebsd-hackers@freebsd.org Cc: bohra@cs.rutgers.edu Subject: tcp_usrreq bug ?? Message-ID: <3DED2DE3.7040002@cs.rutgers.edu>
next in thread | raw e-mail | index | archive | help
Hello
The following code snippet is from netinet/tcp_usrreq.c
As in the comment (and presumably correct behaviour) a RST should
be sent on close if the connection is embryonic. However,
if (tp->t_state < TCPS_ESTABLISHED)
tp = tcp_close(tp);
does not do it. One can imagine a scenario when a client would just
do a connect() and close() and an overloaded server would have its
listen queue crowded by connections that were not synchronized but closed.
I have seen this happen in my lab test, where I use httperf to measure
Apache
webserver throughput. There are several listen queue overflows and resets.
The interesting part is that the client _NEVER_ has more than 3200 open
descriptors
yet a queue of 4096 on the server gets filled up.
Is there a reason for not sending a RST or is it a bug? Please help.
Thanks
Aniruddha
/*
* Initiate (or continue) disconnect.
* If embryonic state, just send reset (once).
* If in ``let data drain'' option and linger null, just drop.
* Otherwise (hard), mark socket disconnecting and drop
* current input data; switch states based on user close, and
* send segment to peer (with FIN).
*/
static struct tcpcb *
tcp_disconnect(tp)
register struct tcpcb *tp;
{
struct socket *so = tp->t_inpcb->inp_socket;
if (tp->t_state < TCPS_ESTABLISHED)
tp = tcp_close(tp);
else if ((so->so_options & SO_LINGER) && so->so_linger == 0)
tp = tcp_drop(tp, 0);
else {
soisdisconnecting(so);
sbflush(&so->so_rcv);
tp = tcp_usrclosed(tp);
if (tp)
(void) tcp_output(tp);
}
return (tp);
}
To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-hackers" in the body of the message
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?3DED2DE3.7040002>
