Re: soreceive() with shared netlock for raw sockets

2022-09-12 Thread Alexander Bluhm
On Sat, Sep 10, 2022 at 10:49:40PM +0300, Vitaliy Makkoveev wrote:
> As it was done for udp and divert sockets.

I have no stess test for parallel receive yet.
Diff looks reasonable.

OK bluhm@

> Index: sys/netinet/ip_var.h
> ===
> RCS file: /cvs/src/sys/netinet/ip_var.h,v
> retrieving revision 1.104
> diff -u -p -r1.104 ip_var.h
> --- sys/netinet/ip_var.h  3 Sep 2022 22:43:38 -   1.104
> +++ sys/netinet/ip_var.h  10 Sep 2022 19:41:56 -
> @@ -258,6 +258,8 @@ intrip_output(struct mbuf *, struct so
>   struct mbuf *);
>  int   rip_attach(struct socket *, int);
>  int   rip_detach(struct socket *);
> +void  rip_lock(struct socket *);
> +void  rip_unlock(struct socket *);
>  int   rip_bind(struct socket *so, struct mbuf *, struct proc *);
>  int   rip_connect(struct socket *, struct mbuf *);
>  int   rip_disconnect(struct socket *);
> Index: sys/netinet/raw_ip.c
> ===
> RCS file: /cvs/src/sys/netinet/raw_ip.c,v
> retrieving revision 1.147
> diff -u -p -r1.147 raw_ip.c
> --- sys/netinet/raw_ip.c  3 Sep 2022 22:43:38 -   1.147
> +++ sys/netinet/raw_ip.c  10 Sep 2022 19:41:56 -
> @@ -106,6 +106,8 @@ struct inpcbtable rawcbtable;
>  const struct pr_usrreqs rip_usrreqs = {
>   .pru_attach = rip_attach,
>   .pru_detach = rip_detach,
> + .pru_lock   = rip_lock,
> + .pru_unlock = rip_unlock,
>   .pru_bind   = rip_bind,
>   .pru_connect= rip_connect,
>   .pru_disconnect = rip_disconnect,
> @@ -220,12 +222,19 @@ rip_input(struct mbuf **mp, int *offp, i
>   else
>   n = m_copym(m, 0, M_COPYALL, M_NOWAIT);
>   if (n != NULL) {
> + int ret;
> +
>   if (inp->inp_flags & INP_CONTROLOPTS ||
>   inp->inp_socket->so_options & SO_TIMESTAMP)
>   ip_savecontrol(inp, , ip, n);
> - if (sbappendaddr(inp->inp_socket,
> +
> + mtx_enter(>inp_mtx);
> + ret = sbappendaddr(inp->inp_socket,
>   >inp_socket->so_rcv,
> - sintosa(), n, opts) == 0) {
> + sintosa(), n, opts);
> + mtx_leave(>inp_mtx);
> +
> + if (ret == 0) {
>   /* should notify about lost packet */
>   m_freem(n);
>   m_freem(opts);
> @@ -498,6 +507,24 @@ rip_detach(struct socket *so)
>   in_pcbdetach(inp);
>  
>   return (0);
> +}
> +
> +void
> +rip_lock(struct socket *so)
> +{
> + struct inpcb *inp = sotoinpcb(so);
> +
> + NET_ASSERT_LOCKED();
> + mtx_enter(>inp_mtx);
> +}
> +
> +void
> +rip_unlock(struct socket *so)
> +{
> + struct inpcb *inp = sotoinpcb(so);
> +
> + NET_ASSERT_LOCKED();
> + mtx_leave(>inp_mtx);
>  }
>  
>  int
> Index: sys/netinet6/ip6_var.h
> ===
> RCS file: /cvs/src/sys/netinet6/ip6_var.h,v
> retrieving revision 1.102
> diff -u -p -r1.102 ip6_var.h
> --- sys/netinet6/ip6_var.h3 Sep 2022 22:43:38 -   1.102
> +++ sys/netinet6/ip6_var.h10 Sep 2022 19:41:56 -
> @@ -353,6 +353,8 @@ int   rip6_output(struct mbuf *, struct so
>   struct mbuf *);
>  int  rip6_attach(struct socket *, int);
>  int  rip6_detach(struct socket *);
> +void rip6_lock(struct socket *);
> +void rip6_unlock(struct socket *);
>  int  rip6_bind(struct socket *, struct mbuf *, struct proc *);
>  int  rip6_connect(struct socket *, struct mbuf *);
>  int  rip6_disconnect(struct socket *);
> Index: sys/netinet6/raw_ip6.c
> ===
> RCS file: /cvs/src/sys/netinet6/raw_ip6.c,v
> retrieving revision 1.168
> diff -u -p -r1.168 raw_ip6.c
> --- sys/netinet6/raw_ip6.c3 Sep 2022 22:43:38 -   1.168
> +++ sys/netinet6/raw_ip6.c10 Sep 2022 19:41:56 -
> @@ -108,6 +108,8 @@ struct cpumem *rip6counters;
>  const struct pr_usrreqs rip6_usrreqs = {
>   .pru_attach = rip6_attach,
>   .pru_detach = rip6_detach,
> + .pru_lock   = rip6_lock,
> + .pru_unlock = rip6_unlock,
>   .pru_bind   = rip6_bind,
>   .pru_connect= rip6_connect,
>   .pru_disconnect = rip6_disconnect,
> @@ -261,13 +263,20 @@ rip6_input(struct mbuf **mp, int *offp, 
>   else
>   n = m_copym(m, 0, M_COPYALL, M_NOWAIT);
>   if (n != NULL) {
> + int ret;
> +
>   if (in6p->inp_flags & IN6P_CONTROLOPTS)
>   ip6_savecontrol(in6p, n, );
>   /* strip intermediate headers */
>   m_adj(n, *offp);
> - if 

soreceive() with shared netlock for raw sockets

2022-09-10 Thread Vitaliy Makkoveev
As it was done for udp and divert sockets.

Index: sys/netinet/ip_var.h
===
RCS file: /cvs/src/sys/netinet/ip_var.h,v
retrieving revision 1.104
diff -u -p -r1.104 ip_var.h
--- sys/netinet/ip_var.h3 Sep 2022 22:43:38 -   1.104
+++ sys/netinet/ip_var.h10 Sep 2022 19:41:56 -
@@ -258,6 +258,8 @@ int  rip_output(struct mbuf *, struct so
struct mbuf *);
 int rip_attach(struct socket *, int);
 int rip_detach(struct socket *);
+voidrip_lock(struct socket *);
+voidrip_unlock(struct socket *);
 int rip_bind(struct socket *so, struct mbuf *, struct proc *);
 int rip_connect(struct socket *, struct mbuf *);
 int rip_disconnect(struct socket *);
Index: sys/netinet/raw_ip.c
===
RCS file: /cvs/src/sys/netinet/raw_ip.c,v
retrieving revision 1.147
diff -u -p -r1.147 raw_ip.c
--- sys/netinet/raw_ip.c3 Sep 2022 22:43:38 -   1.147
+++ sys/netinet/raw_ip.c10 Sep 2022 19:41:56 -
@@ -106,6 +106,8 @@ struct inpcbtable rawcbtable;
 const struct pr_usrreqs rip_usrreqs = {
.pru_attach = rip_attach,
.pru_detach = rip_detach,
+   .pru_lock   = rip_lock,
+   .pru_unlock = rip_unlock,
.pru_bind   = rip_bind,
.pru_connect= rip_connect,
.pru_disconnect = rip_disconnect,
@@ -220,12 +222,19 @@ rip_input(struct mbuf **mp, int *offp, i
else
n = m_copym(m, 0, M_COPYALL, M_NOWAIT);
if (n != NULL) {
+   int ret;
+
if (inp->inp_flags & INP_CONTROLOPTS ||
inp->inp_socket->so_options & SO_TIMESTAMP)
ip_savecontrol(inp, , ip, n);
-   if (sbappendaddr(inp->inp_socket,
+
+   mtx_enter(>inp_mtx);
+   ret = sbappendaddr(inp->inp_socket,
>inp_socket->so_rcv,
-   sintosa(), n, opts) == 0) {
+   sintosa(), n, opts);
+   mtx_leave(>inp_mtx);
+
+   if (ret == 0) {
/* should notify about lost packet */
m_freem(n);
m_freem(opts);
@@ -498,6 +507,24 @@ rip_detach(struct socket *so)
in_pcbdetach(inp);
 
return (0);
+}
+
+void
+rip_lock(struct socket *so)
+{
+   struct inpcb *inp = sotoinpcb(so);
+
+   NET_ASSERT_LOCKED();
+   mtx_enter(>inp_mtx);
+}
+
+void
+rip_unlock(struct socket *so)
+{
+   struct inpcb *inp = sotoinpcb(so);
+
+   NET_ASSERT_LOCKED();
+   mtx_leave(>inp_mtx);
 }
 
 int
Index: sys/netinet6/ip6_var.h
===
RCS file: /cvs/src/sys/netinet6/ip6_var.h,v
retrieving revision 1.102
diff -u -p -r1.102 ip6_var.h
--- sys/netinet6/ip6_var.h  3 Sep 2022 22:43:38 -   1.102
+++ sys/netinet6/ip6_var.h  10 Sep 2022 19:41:56 -
@@ -353,6 +353,8 @@ int rip6_output(struct mbuf *, struct so
struct mbuf *);
 intrip6_attach(struct socket *, int);
 intrip6_detach(struct socket *);
+void   rip6_lock(struct socket *);
+void   rip6_unlock(struct socket *);
 intrip6_bind(struct socket *, struct mbuf *, struct proc *);
 intrip6_connect(struct socket *, struct mbuf *);
 intrip6_disconnect(struct socket *);
Index: sys/netinet6/raw_ip6.c
===
RCS file: /cvs/src/sys/netinet6/raw_ip6.c,v
retrieving revision 1.168
diff -u -p -r1.168 raw_ip6.c
--- sys/netinet6/raw_ip6.c  3 Sep 2022 22:43:38 -   1.168
+++ sys/netinet6/raw_ip6.c  10 Sep 2022 19:41:56 -
@@ -108,6 +108,8 @@ struct cpumem *rip6counters;
 const struct pr_usrreqs rip6_usrreqs = {
.pru_attach = rip6_attach,
.pru_detach = rip6_detach,
+   .pru_lock   = rip6_lock,
+   .pru_unlock = rip6_unlock,
.pru_bind   = rip6_bind,
.pru_connect= rip6_connect,
.pru_disconnect = rip6_disconnect,
@@ -261,13 +263,20 @@ rip6_input(struct mbuf **mp, int *offp, 
else
n = m_copym(m, 0, M_COPYALL, M_NOWAIT);
if (n != NULL) {
+   int ret;
+
if (in6p->inp_flags & IN6P_CONTROLOPTS)
ip6_savecontrol(in6p, n, );
/* strip intermediate headers */
m_adj(n, *offp);
-   if (sbappendaddr(in6p->inp_socket,
+
+   mtx_enter(>inp_mtx);
+   ret = sbappendaddr(in6p->inp_socket,
>inp_socket->so_rcv,
-   sin6tosa(), n, opts) == 0) {
+