git: 6890b588141a - main - sockbuf: improve sbcreatecontrol()
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Tue, 17 May 2022 17:11:59 UTC
The branch main has been updated by glebius: URL: https://cgit.FreeBSD.org/src/commit/?id=6890b588141a8298fc8a63700aeeea4ba36ca3f9 commit 6890b588141a8298fc8a63700aeeea4ba36ca3f9 Author: Gleb Smirnoff <glebius@FreeBSD.org> AuthorDate: 2022-05-17 17:10:42 +0000 Commit: Gleb Smirnoff <glebius@FreeBSD.org> CommitDate: 2022-05-17 17:10:42 +0000 sockbuf: improve sbcreatecontrol() o Constify memory pointer. Make length unsigned. o Make it never fail with M_WAITOK and assert that length is sane. --- sys/kern/uipc_sockbuf.c | 24 +++++++++++++++--------- sys/netinet6/ip6_input.c | 4 ++-- sys/sys/sockbuf.h | 3 ++- 3 files changed, 19 insertions(+), 12 deletions(-) diff --git a/sys/kern/uipc_sockbuf.c b/sys/kern/uipc_sockbuf.c index 884562510e61..e3a9f92d8da0 100644 --- a/sys/kern/uipc_sockbuf.c +++ b/sys/kern/uipc_sockbuf.c @@ -1760,29 +1760,35 @@ sbdroprecord(struct sockbuf *sb) * type for presentation on a socket buffer. */ struct mbuf * -sbcreatecontrol(void *p, int size, int type, int level, int wait) +sbcreatecontrol(const void *p, u_int size, int type, int level, int wait) { struct cmsghdr *cp; struct mbuf *m; MBUF_CHECKSLEEP(wait); - if (CMSG_SPACE((u_int)size) > MCLBYTES) - return ((struct mbuf *) NULL); - if (CMSG_SPACE((u_int)size) > MLEN) + + if (wait == M_NOWAIT) { + if (CMSG_SPACE(size) > MCLBYTES) + return (NULL); + } else + KASSERT(size <= MCLBYTES, ("%s: passed size %u > MCLBYTES", + __func__, size)); + + if (CMSG_SPACE(size) > MLEN) m = m_getcl(wait, MT_CONTROL, 0); else m = m_get(wait, MT_CONTROL); if (m == NULL) - return ((struct mbuf *) NULL); - cp = mtod(m, struct cmsghdr *); - m->m_len = 0; - KASSERT(CMSG_SPACE((u_int)size) <= M_TRAILINGSPACE(m), + return (NULL); + + KASSERT(CMSG_SPACE(size) <= M_TRAILINGSPACE(m), ("sbcreatecontrol: short mbuf")); /* * Don't leave the padding between the msg header and the * cmsg data and the padding after the cmsg data un-initialized. */ - bzero(cp, CMSG_SPACE((u_int)size)); + cp = mtod(m, struct cmsghdr *); + bzero(cp, CMSG_SPACE(size)); if (p != NULL) (void)memcpy(CMSG_DATA(cp), p, size); m->m_len = CMSG_SPACE(size); diff --git a/sys/netinet6/ip6_input.c b/sys/netinet6/ip6_input.c index 9835dc495f09..a9bc05f0c19c 100644 --- a/sys/netinet6/ip6_input.c +++ b/sys/netinet6/ip6_input.c @@ -1413,7 +1413,7 @@ ip6_savecontrol(struct inpcb *inp, struct mbuf *m, struct mbuf **mp) */ if (ip6->ip6_nxt == IPPROTO_HOPOPTS) { struct ip6_hbh *hbh; - int hbhlen; + u_int hbhlen; hbh = (struct ip6_hbh *)(ip6 + 1); hbhlen = (hbh->ip6h_len + 1) << 3; @@ -1445,7 +1445,7 @@ ip6_savecontrol(struct inpcb *inp, struct mbuf *m, struct mbuf **mp) */ while (1) { /* is explicit loop prevention necessary? */ struct ip6_ext *ip6e = NULL; - int elen; + u_int elen; /* * if it is not an extension header, don't try to diff --git a/sys/sys/sockbuf.h b/sys/sys/sockbuf.h index efa87b1f2378..753ebd1fbf35 100644 --- a/sys/sys/sockbuf.h +++ b/sys/sys/sockbuf.h @@ -158,7 +158,8 @@ void sbappendrecord(struct sockbuf *sb, struct mbuf *m0); void sbappendrecord_locked(struct sockbuf *sb, struct mbuf *m0); void sbcompress(struct sockbuf *sb, struct mbuf *m, struct mbuf *n); struct mbuf * - sbcreatecontrol(void *p, int size, int type, int level, int wait); + sbcreatecontrol(const void *p, u_int size, int type, int level, + int wait); void sbdestroy(struct socket *, sb_which); void sbdrop(struct sockbuf *sb, int len); void sbdrop_locked(struct sockbuf *sb, int len);