mirror of
https://github.com/opnsense/src.git
synced 2026-06-05 06:42:56 -04:00
tcp: simplify endpoint creation at the passive side
Use the intended TCP stack when creating a TCP endpoint instead of creating it the endpoint the default stack first and after that switching it to use the intended TCP stack. Reviewed by: Peter Lei, rrs and jtl (older version) Sponsored by: Netflix, Inc. Differential Revision: https://reviews.freebsd.org/D45411
This commit is contained in:
parent
646c28ea80
commit
baee801c92
4 changed files with 25 additions and 37 deletions
|
|
@ -2180,9 +2180,11 @@ tcp_respond(struct tcpcb *tp, void *ipgen, struct tcphdr *th, struct mbuf *m,
|
|||
* Create a new TCP control block, making an empty reassembly queue and hooking
|
||||
* it to the argument protocol control block. The `inp' parameter must have
|
||||
* come from the zone allocator set up by tcpcbstor declaration.
|
||||
* The caller can provide a pointer to a tcpcb of the listener to inherit the
|
||||
* TCP function block from the listener.
|
||||
*/
|
||||
struct tcpcb *
|
||||
tcp_newtcpcb(struct inpcb *inp)
|
||||
tcp_newtcpcb(struct inpcb *inp, struct tcpcb *listening_tcb)
|
||||
{
|
||||
struct tcpcb *tp = intotcpcb(inp);
|
||||
#ifdef INET6
|
||||
|
|
@ -2200,8 +2202,21 @@ tcp_newtcpcb(struct inpcb *inp)
|
|||
tp->t_ccv.type = IPPROTO_TCP;
|
||||
tp->t_ccv.ccvc.tcp = tp;
|
||||
rw_rlock(&tcp_function_lock);
|
||||
tp->t_fb = V_tcp_func_set_ptr;
|
||||
if (listening_tcb != NULL) {
|
||||
INP_LOCK_ASSERT(tptoinpcb(listening_tcb));
|
||||
KASSERT(listening_tcb->t_fb != NULL,
|
||||
("tcp_newtcpcb: listening_tcb->t_fb is NULL"));
|
||||
if (listening_tcb->t_fb->tfb_flags & TCP_FUNC_BEING_REMOVED) {
|
||||
rw_runlock(&tcp_function_lock);
|
||||
return (NULL);
|
||||
}
|
||||
tp->t_fb = listening_tcb->t_fb;
|
||||
} else {
|
||||
tp->t_fb = V_tcp_func_set_ptr;
|
||||
}
|
||||
refcount_acquire(&tp->t_fb->tfb_refcnt);
|
||||
KASSERT((tp->t_fb->tfb_flags & TCP_FUNC_BEING_REMOVED) == 0,
|
||||
("tcp_newtcpcb: using TFB being removed"));
|
||||
rw_runlock(&tcp_function_lock);
|
||||
/*
|
||||
* Use the current system default CC algorithm.
|
||||
|
|
|
|||
|
|
@ -777,7 +777,7 @@ done:
|
|||
static struct socket *
|
||||
syncache_socket(struct syncache *sc, struct socket *lso, struct mbuf *m)
|
||||
{
|
||||
struct tcp_function_block *blk;
|
||||
struct tcpcb *listening_tcb;
|
||||
struct inpcb *inp = NULL;
|
||||
struct socket *so;
|
||||
struct tcpcb *tp;
|
||||
|
|
@ -802,7 +802,11 @@ syncache_socket(struct syncache *sc, struct socket *lso, struct mbuf *m)
|
|||
goto allocfail;
|
||||
}
|
||||
inp = sotoinpcb(so);
|
||||
if ((tp = tcp_newtcpcb(inp)) == NULL) {
|
||||
if (V_functions_inherit_listen_socket_stack)
|
||||
listening_tcb = sototcpcb(lso);
|
||||
else
|
||||
listening_tcb = NULL;
|
||||
if ((tp = tcp_newtcpcb(inp, listening_tcb)) == NULL) {
|
||||
in_pcbfree(inp);
|
||||
sodealloc(so);
|
||||
goto allocfail;
|
||||
|
|
@ -912,37 +916,6 @@ syncache_socket(struct syncache *sc, struct socket *lso, struct mbuf *m)
|
|||
tp->t_port = sc->sc_port;
|
||||
tcp_rcvseqinit(tp);
|
||||
tcp_sendseqinit(tp);
|
||||
blk = sototcpcb(lso)->t_fb;
|
||||
if (V_functions_inherit_listen_socket_stack && blk != tp->t_fb) {
|
||||
/*
|
||||
* Our parents t_fb was not the default,
|
||||
* we need to release our ref on tp->t_fb and
|
||||
* pickup one on the new entry.
|
||||
*/
|
||||
struct tcp_function_block *rblk;
|
||||
void *ptr = NULL;
|
||||
|
||||
rblk = find_and_ref_tcp_fb(blk);
|
||||
KASSERT(rblk != NULL,
|
||||
("cannot find blk %p out of syncache?", blk));
|
||||
|
||||
if (rblk->tfb_tcp_fb_init == NULL ||
|
||||
(*rblk->tfb_tcp_fb_init)(tp, &ptr) == 0) {
|
||||
/* Release the old stack */
|
||||
if (tp->t_fb->tfb_tcp_fb_fini != NULL)
|
||||
(*tp->t_fb->tfb_tcp_fb_fini)(tp, 0);
|
||||
refcount_release(&tp->t_fb->tfb_refcnt);
|
||||
/* Now set in all the pointers */
|
||||
tp->t_fb = rblk;
|
||||
tp->t_fb_ptr = ptr;
|
||||
} else {
|
||||
/*
|
||||
* Initialization failed. Release the reference count on
|
||||
* the looked up default stack.
|
||||
*/
|
||||
refcount_release(&rblk->tfb_refcnt);
|
||||
}
|
||||
}
|
||||
tp->snd_wl1 = sc->sc_irs;
|
||||
tp->snd_max = tp->iss + 1;
|
||||
tp->snd_nxt = tp->iss + 1;
|
||||
|
|
|
|||
|
|
@ -172,7 +172,7 @@ tcp_usr_attach(struct socket *so, int proto, struct thread *td)
|
|||
if (error)
|
||||
goto out;
|
||||
inp = sotoinpcb(so);
|
||||
tp = tcp_newtcpcb(inp);
|
||||
tp = tcp_newtcpcb(inp, NULL);
|
||||
if (tp == NULL) {
|
||||
error = ENOBUFS;
|
||||
in_pcbfree(inp);
|
||||
|
|
|
|||
|
|
@ -1454,7 +1454,7 @@ void tcp_mss_update(struct tcpcb *, int, int, struct hc_metrics_lite *,
|
|||
void tcp_mss(struct tcpcb *, int);
|
||||
int tcp_mssopt(struct in_conninfo *);
|
||||
struct tcpcb *
|
||||
tcp_newtcpcb(struct inpcb *);
|
||||
tcp_newtcpcb(struct inpcb *, struct tcpcb *);
|
||||
int tcp_default_output(struct tcpcb *);
|
||||
void tcp_state_change(struct tcpcb *, int);
|
||||
void tcp_respond(struct tcpcb *, void *,
|
||||
|
|
|
|||
Loading…
Reference in a new issue