On Fri, Jun 28, 2024 at 2:33 AM Mina Almasry <almasrymina@xxxxxxxxxx> wrote: > > Add an interface for the user to notify the kernel that it is done > reading the devmem dmabuf frags returned as cmsg. The kernel will > drop the reference on the frags to make them available for reuse. > > Signed-off-by: Willem de Bruijn <willemb@xxxxxxxxxx> > Signed-off-by: Kaiyuan Zhang <kaiyuanz@xxxxxxxxxx> > Signed-off-by: Mina Almasry <almasrymina@xxxxxxxxxx> > > --- > > v10: > - Fix leak of tokens (Nikolay). > > v7: > - Updated SO_DEVMEM_* uapi to use the next available entry (Arnd). > > v6: > - Squash in locking optimizations from edumazet@xxxxxxxxxx. With his > changes we lock the xarray once per sock_devmem_dontneed operation > rather than once per frag. > > Changes in v1: > - devmemtoken -> dmabuf_token (David). > - Use napi_pp_put_page() for refcounting (Yunsheng). > - Fix build error with missing socket options on other asms. > > --- > arch/alpha/include/uapi/asm/socket.h | 1 + > arch/mips/include/uapi/asm/socket.h | 1 + > arch/parisc/include/uapi/asm/socket.h | 1 + > arch/sparc/include/uapi/asm/socket.h | 1 + > include/uapi/asm-generic/socket.h | 1 + > include/uapi/linux/uio.h | 4 ++ > net/core/sock.c | 61 +++++++++++++++++++++++++++ > 7 files changed, 70 insertions(+) > > > +struct dmabuf_token { > + __u32 token_start; > + __u32 token_count; > +}; > /* > * UIO_MAXIOV shall be at least 16 1003.1g (5.4.1.1) > */ > diff --git a/net/core/sock.c b/net/core/sock.c > index 9abc4fe259535..040c66ac26244 100644 > --- a/net/core/sock.c > +++ b/net/core/sock.c > @@ -124,6 +124,7 @@ > #include <linux/netdevice.h> > #include <net/protocol.h> > #include <linux/skbuff.h> > +#include <linux/skbuff_ref.h> > #include <net/net_namespace.h> > #include <net/request_sock.h> > #include <net/sock.h> > @@ -1049,6 +1050,62 @@ static int sock_reserve_memory(struct sock *sk, int bytes) > return 0; > } > > +#ifdef CONFIG_PAGE_POOL > +static noinline_for_stack int > +sock_devmem_dontneed(struct sock *sk, sockptr_t optval, unsigned int optlen) > +{ > + unsigned int num_tokens, i, j, k, netmem_num = 0; > + struct dmabuf_token *tokens; > + netmem_ref netmems[16]; > + int ret = 0; > + > + if (sk->sk_type != SOCK_STREAM || sk->sk_protocol != IPPROTO_TCP) > + return -EBADF; This might use sk_is_tcp() helper. > + > + if (optlen % sizeof(struct dmabuf_token) || > + optlen > sizeof(*tokens) * 128) > + return -EINVAL; > + > + tokens = kvmalloc_array(128, sizeof(*tokens), GFP_KERNEL); This allocates 8192 bytes even for small optlen ? Probably no big deal, no need to send a new version. Reviewed-by: Eric Dumazet <edumazet@xxxxxxxxxx>