mirror of
https://github.com/opnsense/src.git
synced 2026-06-11 09:41:03 -04:00
cxgbe/t4_tom: restore socket's protosw before entering TIME_WAIT.
This fixes a panic due to stale so->so_proto if t4_tom is unloaded and
one or more connections that were previously offloaded are still around
in TIME_WAIT state.
Reviewed by: jhb@
Sponsored by: Chelsio Communications
Differential Revision: https://reviews.freebsd.org/D29503
(cherry picked from commit 5394893269)
This commit is contained in:
parent
95a3005326
commit
248bc9784a
3 changed files with 15 additions and 2 deletions
|
|
@ -1263,6 +1263,7 @@ do_peer_close(struct sge_iq *iq, const struct rss_header *rss, struct mbuf *m)
|
|||
break;
|
||||
|
||||
case TCPS_FIN_WAIT_2:
|
||||
restore_so_proto(so, inp->inp_vflag & INP_IPV6);
|
||||
tcp_twstart(tp);
|
||||
INP_UNLOCK_ASSERT(inp); /* safe, we have a ref on the inp */
|
||||
NET_EPOCH_EXIT(et);
|
||||
|
|
@ -1323,6 +1324,7 @@ do_close_con_rpl(struct sge_iq *iq, const struct rss_header *rss,
|
|||
|
||||
switch (tp->t_state) {
|
||||
case TCPS_CLOSING: /* see TCPS_FIN_WAIT_2 in do_peer_close too */
|
||||
restore_so_proto(so, inp->inp_vflag & INP_IPV6);
|
||||
tcp_twstart(tp);
|
||||
release:
|
||||
INP_UNLOCK_ASSERT(inp); /* safe, we have a ref on the inp */
|
||||
|
|
|
|||
|
|
@ -79,9 +79,11 @@ __FBSDID("$FreeBSD$");
|
|||
#include "tom/t4_tom.h"
|
||||
#include "tom/t4_tls.h"
|
||||
|
||||
static struct protosw *tcp_protosw;
|
||||
static struct protosw toe_protosw;
|
||||
static struct pr_usrreqs toe_usrreqs;
|
||||
|
||||
static struct protosw *tcp6_protosw;
|
||||
static struct protosw toe6_protosw;
|
||||
static struct pr_usrreqs toe6_usrreqs;
|
||||
|
||||
|
|
@ -263,6 +265,15 @@ offload_socket(struct socket *so, struct toepcb *toep)
|
|||
mtx_unlock(&td->toep_list_lock);
|
||||
}
|
||||
|
||||
void
|
||||
restore_so_proto(struct socket *so, bool v6)
|
||||
{
|
||||
if (v6)
|
||||
so->so_proto = tcp6_protosw;
|
||||
else
|
||||
so->so_proto = tcp_protosw;
|
||||
}
|
||||
|
||||
/* This is _not_ the normal way to "unoffload" a socket. */
|
||||
void
|
||||
undo_offload_socket(struct socket *so)
|
||||
|
|
@ -282,6 +293,7 @@ undo_offload_socket(struct socket *so)
|
|||
sb = &so->so_rcv;
|
||||
SOCKBUF_LOCK(sb);
|
||||
sb->sb_flags &= ~SB_NOCOALESCE;
|
||||
restore_so_proto(so, inp->inp_vflag & INP_IPV6);
|
||||
SOCKBUF_UNLOCK(sb);
|
||||
|
||||
tp->tod = NULL;
|
||||
|
|
@ -1837,8 +1849,6 @@ t4_ctloutput_tom(struct socket *so, struct sockopt *sopt)
|
|||
static int
|
||||
t4_tom_mod_load(void)
|
||||
{
|
||||
struct protosw *tcp_protosw, *tcp6_protosw;
|
||||
|
||||
/* CPL handlers */
|
||||
t4_register_cpl_handler(CPL_GET_TCB_RPL, do_get_tcb_rpl);
|
||||
t4_register_shared_cpl_handler(CPL_L2T_WRITE_RPL, do_l2t_write_rpl2,
|
||||
|
|
|
|||
|
|
@ -352,6 +352,7 @@ int init_toepcb(struct vi_info *, struct toepcb *);
|
|||
struct toepcb *hold_toepcb(struct toepcb *);
|
||||
void free_toepcb(struct toepcb *);
|
||||
void offload_socket(struct socket *, struct toepcb *);
|
||||
void restore_so_proto(struct socket *, bool);
|
||||
void undo_offload_socket(struct socket *);
|
||||
void final_cpl_received(struct toepcb *);
|
||||
void insert_tid(struct adapter *, int, void *, int);
|
||||
|
|
|
|||
Loading…
Reference in a new issue