The branch main has been updated by melifaro:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=7b660faa9e30c15d3be9b2c44c3ca046a33331f4

commit 7b660faa9e30c15d3be9b2c44c3ca046a33331f4
Author:     Alexander V. Chernikov <melif...@freebsd.org>
AuthorDate: 2022-09-27 13:52:11 +0000
Commit:     Alexander V. Chernikov <melif...@freebsd.org>
CommitDate: 2022-09-28 10:20:09 +0000

    sockbufs: add sbreserve_locked_limit() with custom maxsockbuf limit.
    
    Protocols such as netlink may need a large socket receive buffer,
     measured in tens of megabytes. This change allows netlink to
     set larger socket buffers (given the privs are in place), without
     requiring user to manuall bump maxsockbuf.
    
    Reviewed by:    glebius
    Differential Revision: https://reviews.freebsd.org/D36747
---
 sys/kern/uipc_sockbuf.c | 22 +++++++++++++++-------
 sys/sys/sockbuf.h       |  2 ++
 2 files changed, 17 insertions(+), 7 deletions(-)

diff --git a/sys/kern/uipc_sockbuf.c b/sys/kern/uipc_sockbuf.c
index a2d3fc28bbec..61ec0c794270 100644
--- a/sys/kern/uipc_sockbuf.c
+++ b/sys/kern/uipc_sockbuf.c
@@ -66,9 +66,10 @@ void (*aio_swake)(struct socket *, struct sockbuf *);
  * Primitive routines for operating on socket buffers
  */
 
+#define        BUF_MAX_ADJ(_sz)        (((u_quad_t)(_sz)) * MCLBYTES / (MSIZE 
+ MCLBYTES))
+
 u_long sb_max = SB_MAX;
-u_long sb_max_adj =
-       (quad_t)SB_MAX * MCLBYTES / (MSIZE + MCLBYTES); /* adjusted sb_max */
+u_long sb_max_adj = BUF_MAX_ADJ(SB_MAX);
 
 static u_long sb_efficiency = 8;       /* parameter for sbreserve() */
 
@@ -611,7 +612,7 @@ sysctl_handle_sb_max(SYSCTL_HANDLER_ARGS)
        if (tmp_sb_max < MSIZE + MCLBYTES)
                return (EINVAL);
        sb_max = tmp_sb_max;
-       sb_max_adj = (u_quad_t)sb_max * MCLBYTES / (MSIZE + MCLBYTES);
+       sb_max_adj = BUF_MAX_ADJ(sb_max);
        return (0);
 }
 
@@ -620,8 +621,8 @@ sysctl_handle_sb_max(SYSCTL_HANDLER_ARGS)
  * become limiting if buffering efficiency is near the normal case.
  */
 bool
-sbreserve_locked(struct socket *so, sb_which which, u_long cc,
-    struct thread *td)
+sbreserve_locked_limit(struct socket *so, sb_which which, u_long cc,
+    u_long buf_max, struct thread *td)
 {
        struct sockbuf *sb = sobuf(so, which);
        rlim_t sbsize_limit;
@@ -635,7 +636,7 @@ sbreserve_locked(struct socket *so, sb_which which, u_long 
cc,
         * appropriate thread resource limits are available.  In that case,
         * we don't apply a process limit.
         */
-       if (cc > sb_max_adj)
+       if (cc > BUF_MAX_ADJ(buf_max))
                return (false);
        if (td != NULL) {
                sbsize_limit = lim_cur(td, RLIMIT_SBSIZE);
@@ -644,12 +645,19 @@ sbreserve_locked(struct socket *so, sb_which which, 
u_long cc,
        if (!chgsbsize(so->so_cred->cr_uidinfo, &sb->sb_hiwat, cc,
            sbsize_limit))
                return (false);
-       sb->sb_mbmax = min(cc * sb_efficiency, sb_max);
+       sb->sb_mbmax = min(cc * sb_efficiency, buf_max);
        if (sb->sb_lowat > sb->sb_hiwat)
                sb->sb_lowat = sb->sb_hiwat;
        return (true);
 }
 
+bool
+sbreserve_locked(struct socket *so, sb_which which, u_long cc,
+    struct thread *td)
+{
+       return (sbreserve_locked_limit(so, which, cc, sb_max, td));
+}
+
 int
 sbsetopt(struct socket *so, struct sockopt *sopt)
 {
diff --git a/sys/sys/sockbuf.h b/sys/sys/sockbuf.h
index a0c6fd10116a..33c0abb381a3 100644
--- a/sys/sys/sockbuf.h
+++ b/sys/sys/sockbuf.h
@@ -231,6 +231,8 @@ void        sbrelease_locked(struct socket *, sb_which);
 int    sbsetopt(struct socket *so, struct sockopt *);
 bool   sbreserve_locked(struct socket *so, sb_which which, u_long cc,
            struct thread *td);
+bool   sbreserve_locked_limit(struct socket *so, sb_which which, u_long cc,
+           u_long buf_max, struct thread *td);
 void   sbsndptr_adv(struct sockbuf *sb, struct mbuf *mb, u_int len);
 struct mbuf *
        sbsndptr_noadv(struct sockbuf *sb, u_int off, u_int *moff);

Reply via email to