Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src - Introduce a new SO_RERROR socket option to explicitly turn on



details:   https://anonhg.NetBSD.org/src/rev/d0d971f56eda
branches:  trunk
changeset: 445589:d0d971f56eda
user:      christos <christos%NetBSD.org@localhost>
date:      Sun Nov 04 16:30:28 2018 +0000

description:
- Introduce a new SO_RERROR socket option to explicitly turn on
  receive overflow errors re-instating the default behavior to
  silently ignore them as before 2018-03-19.
- Introduce a new kern.sooptions sysctl to control the default
  behavior of socket options. Setting this to 0x4000 (SO_RERROR),
  turns on receive overflow error reporting for all sockets.
- Change dhcpcd to turn on SO_RERROR on all its sockets.

As discussed in tech-net.

diffstat:

 external/bsd/dhcpcd/dist/src/dhcp.c   |   5 ++++
 external/bsd/dhcpcd/dist/src/dhcp6.c  |   5 ++++
 external/bsd/dhcpcd/dist/src/if-bsd.c |   6 +++++
 external/bsd/dhcpcd/dist/src/ipv6nd.c |   7 ++++++
 lib/libc/sys/getsockopt.2             |  18 ++++++++++++++-
 share/man/man7/sysctl.7               |  18 ++++++++++-----
 sys/kern/uipc_socket.c                |  40 +++++++++++++++++++++++++++++++++-
 sys/kern/uipc_socket2.c               |  10 +++++---
 sys/sys/socket.h                      |  25 +++++++++++++++++++++-
 9 files changed, 119 insertions(+), 15 deletions(-)

diffs (truncated from 327 to 300 lines):

diff -r c12c2692e21e -r d0d971f56eda external/bsd/dhcpcd/dist/src/dhcp.c
--- a/external/bsd/dhcpcd/dist/src/dhcp.c       Sun Nov 04 13:48:27 2018 +0000
+++ b/external/bsd/dhcpcd/dist/src/dhcp.c       Sun Nov 04 16:30:28 2018 +0000
@@ -1604,6 +1604,11 @@
        n = 1;
        if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &n, sizeof(n)) == -1)
                goto eexit;
+#ifdef SO_RERROR
+       n = 1;
+       if (setsockopt(s, SOL_SOCKET, SO_RERROR, &n, sizeof(n)) == -1)
+               goto eexit;
+#endif
        memset(&sin, 0, sizeof(sin));
        sin.sin_family = AF_INET;
        sin.sin_port = htons(BOOTPC);
diff -r c12c2692e21e -r d0d971f56eda external/bsd/dhcpcd/dist/src/dhcp6.c
--- a/external/bsd/dhcpcd/dist/src/dhcp6.c      Sun Nov 04 13:48:27 2018 +0000
+++ b/external/bsd/dhcpcd/dist/src/dhcp6.c      Sun Nov 04 16:30:28 2018 +0000
@@ -3620,6 +3620,11 @@
        if (setsockopt(s, SOL_SOCKET, SO_BROADCAST, &n, sizeof(n)) == -1)
                goto errexit;
 
+#ifdef SO_RERROR
+       n = 1;
+       if (setsockopt(s, SOL_SOCKET, SO_RERROR, &n, sizeof(n)) == -1)
+               goto errexit;
+#endif
        memset(&sa, 0, sizeof(sa));
        sa.sin6_family = AF_INET6;
        sa.sin6_port = htons(DHCP6_CLIENT_PORT);
diff -r c12c2692e21e -r d0d971f56eda external/bsd/dhcpcd/dist/src/if-bsd.c
--- a/external/bsd/dhcpcd/dist/src/if-bsd.c     Sun Nov 04 13:48:27 2018 +0000
+++ b/external/bsd/dhcpcd/dist/src/if-bsd.c     Sun Nov 04 16:30:28 2018 +0000
@@ -161,6 +161,12 @@
        if (ctx->link_fd == -1)
                return -1;
 
+#ifdef SO_RERROR
+       int n = 1;
+       if (setsockopt(ctx->link_fd, SOL_SOCKET, SO_RERROR,
+           &n, sizeof(n)) == -1)
+               logerr(__func__);
+#endif
 #if defined(RO_MSGFILTER)
        if (setsockopt(ctx->link_fd, PF_ROUTE, RO_MSGFILTER,
            &msgfilter, sizeof(msgfilter)) == -1)
diff -r c12c2692e21e -r d0d971f56eda external/bsd/dhcpcd/dist/src/ipv6nd.c
--- a/external/bsd/dhcpcd/dist/src/ipv6nd.c     Sun Nov 04 13:48:27 2018 +0000
+++ b/external/bsd/dhcpcd/dist/src/ipv6nd.c     Sun Nov 04 16:30:28 2018 +0000
@@ -217,6 +217,13 @@
            &on, sizeof(on)) == -1)
                goto eexit;
 
+#ifdef SO_RERROR
+       on = 1;
+       if (setsockopt(ctx->nd_fd, SOL_SOCKET, SO_RERROR,
+           &on, sizeof(on)) == -1)
+               goto eexit;
+#endif
+
        ICMP6_FILTER_SETBLOCKALL(&filt);
        ICMP6_FILTER_SETPASS(ND_NEIGHBOR_ADVERT, &filt);
        ICMP6_FILTER_SETPASS(ND_ROUTER_ADVERT, &filt);
diff -r c12c2692e21e -r d0d971f56eda lib/libc/sys/getsockopt.2
--- a/lib/libc/sys/getsockopt.2 Sun Nov 04 13:48:27 2018 +0000
+++ b/lib/libc/sys/getsockopt.2 Sun Nov 04 16:30:28 2018 +0000
@@ -1,4 +1,4 @@
-.\"    $NetBSD: getsockopt.2,v 1.37 2018/07/31 22:28:26 sevan Exp $
+.\"    $NetBSD: getsockopt.2,v 1.38 2018/11/04 16:30:28 christos Exp $
 .\"
 .\" Copyright (c) 1983, 1991, 1993
 .\"    The Regents of the University of California.  All rights reserved.
@@ -29,7 +29,7 @@
 .\"
 .\"     @(#)getsockopt.2       8.4 (Berkeley) 5/2/95
 .\"
-.Dd July 31, 2018
+.Dd November 3, 2018
 .Dt GETSOCKOPT 2
 .Os
 .Sh NAME
@@ -179,6 +179,7 @@
 .It Dv SO_RCVTIMEO Ta "set timeout value for input"
 .It Dv SO_TIMESTAMP Ta "enables reception of a timestamp with datagrams"
 .It Dv SO_ACCEPTFILTER Ta "set accept filter on listening socket"
+.It Dv SO_RERROR Ta "enables receive size error reporting"
 .It Dv SO_NOSIGPIPE Ta
 controls generation of
 .Dv SIGPIPE
@@ -213,6 +214,19 @@
 bypass the standard routing facilities.
 Instead, messages are directed to the appropriate network interface
 according to the network portion of the destination address.
+.Dv SO_RERROR
+indicates that receive buffer overflows should be handled as errors.
+Historically receive buffer overflows have been ignored and programs
+could not tell if they missed messages or messages had been truncated
+because of overflows.
+Since programs historically do not expect to get receive overflow errors,
+this behavior is not the default, but the default can be changed by
+setting the
+.Dv SO_RERROR
+flag using
+.Xr sysctl 1
+and
+.Dv kern.sooptions .
 .Pp
 .Dv SO_LINGER
 controls the action taken when unsent messages
diff -r c12c2692e21e -r d0d971f56eda share/man/man7/sysctl.7
--- a/share/man/man7/sysctl.7   Sun Nov 04 13:48:27 2018 +0000
+++ b/share/man/man7/sysctl.7   Sun Nov 04 16:30:28 2018 +0000
@@ -1,4 +1,4 @@
-.\"    $NetBSD: sysctl.7,v 1.134 2018/10/30 19:41:21 kre Exp $
+.\"    $NetBSD: sysctl.7,v 1.135 2018/11/04 16:30:28 christos Exp $
 .\"
 .\" Copyright (c) 1993
 .\"    The Regents of the University of California.  All rights reserved.
@@ -29,7 +29,7 @@
 .\"
 .\"    @(#)sysctl.3    8.4 (Berkeley) 5/9/95
 .\"
-.Dd October 30, 2018
+.Dd November 3, 2018
 .Dt SYSCTL 7
 .Os
 .Sh NAME
@@ -359,6 +359,7 @@
 .It kern.sched node    not applicable
 .It kern.securelevel   integer raise only
 .It kern.somaxkva      integer yes
+.It kern.sooptions     integer yes
 .It kern.synchronized_io       integer no
 .It kern.timecounter   node    not applicable
 .It kern.timex struct  no
@@ -1062,8 +1063,7 @@
 .It Li kern.saved_ids ( Dv KERN_SAVED_IDS )
 Returns 1 if saved set-group and saved set-user ID is available.
 .It Li kern.sbmax ( Dv KERN_SBMAX )
-Maximum socket buffer size.
-.\" XXX units?
+Maximum socket buffer size in bytes.
 .It Li kern.securelevel ( Dv KERN_SECURELVL )
 See
 .Xr secmodel_securelevel 9 .
@@ -1166,8 +1166,14 @@
 .Xr sched 3 .
 .El
 .It Li kern.somaxkva ( Dv KERN_SOMAXKVA )
-Maximum amount of kernel memory to be used for socket buffers.
-.\" XXX units?
+Maximum amount of kernel memory to be used for socket buffers in bytes.
+.It Li kern.sooptions
+Set the default socket option flags for
+.Xr socket 2
+creation.
+See
+.Xr setsockopt 2
+for a list of supported flags.
 .It Li kern.synchronized_io ( Dv KERN_SYNCHRONIZED_IO )
 Returns 1 if the
 .St -p1003.1b-93
diff -r c12c2692e21e -r d0d971f56eda sys/kern/uipc_socket.c
--- a/sys/kern/uipc_socket.c    Sun Nov 04 13:48:27 2018 +0000
+++ b/sys/kern/uipc_socket.c    Sun Nov 04 16:30:28 2018 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: uipc_socket.c,v 1.265 2018/09/03 16:29:35 riastradh Exp $      */
+/*     $NetBSD: uipc_socket.c,v 1.266 2018/11/04 16:30:29 christos Exp $       */
 
 /*-
  * Copyright (c) 2002, 2007, 2008, 2009 The NetBSD Foundation, Inc.
@@ -71,7 +71,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: uipc_socket.c,v 1.265 2018/09/03 16:29:35 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: uipc_socket.c,v 1.266 2018/11/04 16:30:29 christos Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_compat_netbsd.h"
@@ -118,6 +118,7 @@
 
 extern const struct fileops socketops;
 
+static int     sooptions;
 extern int     somaxconn;                      /* patchable (XXX sysctl) */
 int            somaxconn = SOMAXCONN;
 kmutex_t       *softnet_lock;
@@ -537,6 +538,7 @@
        so->so_proto = prp;
        so->so_send = sosend;
        so->so_receive = soreceive;
+       so->so_options = sooptions;
 #ifdef MBUFTRACE
        so->so_rcv.sb_mowner = &prp->pr_domain->dom_mowner;
        so->so_snd.sb_mowner = &prp->pr_domain->dom_mowner;
@@ -1757,6 +1759,7 @@
        case SO_OOBINLINE:
        case SO_TIMESTAMP:
        case SO_NOSIGPIPE:
+       case SO_RERROR:
 #ifdef SO_OTIMESTAMP
        case SO_OTIMESTAMP:
 #endif
@@ -1958,6 +1961,7 @@
        case SO_OOBINLINE:
        case SO_TIMESTAMP:
        case SO_NOSIGPIPE:
+       case SO_RERROR:
 #ifdef SO_OTIMESTAMP
        case SO_OTIMESTAMP:
 #endif
@@ -2522,6 +2526,31 @@
        return (error);
 }
 
+/*
+ * sysctl helper routine for kern.sooptions. Ensures that only allowed
+ * options can be set.
+ */
+static int
+sysctl_kern_sooptions(SYSCTLFN_ARGS)
+{
+       int error, new_options;
+       struct sysctlnode node;
+
+       new_options = sooptions;
+       node = *rnode;
+       node.sysctl_data = &new_options;
+       error = sysctl_lookup(SYSCTLFN_CALL(&node));
+       if (error || newp == NULL)
+               return error;
+
+       if (new_options & ~SO_DEFOPTS)
+               return EINVAL;
+
+       sooptions = new_options;
+
+       return 0;
+}
+
 static void
 sysctl_kern_socket_setup(void)
 {
@@ -2542,4 +2571,11 @@
                       SYSCTL_DESCR("Maximum socket buffer size"),
                       sysctl_kern_sbmax, 0, NULL, 0,
                       CTL_KERN, KERN_SBMAX, CTL_EOL);
+
+       sysctl_createv(&socket_sysctllog, 0, NULL, NULL,
+                      CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
+                      CTLTYPE_INT, "sooptions",
+                      SYSCTL_DESCR("Default socket options"),
+                      sysctl_kern_sooptions, 0, NULL, 0,
+                      CTL_KERN, CTL_CREATE, CTL_EOL);
 }
diff -r c12c2692e21e -r d0d971f56eda sys/kern/uipc_socket2.c
--- a/sys/kern/uipc_socket2.c   Sun Nov 04 13:48:27 2018 +0000
+++ b/sys/kern/uipc_socket2.c   Sun Nov 04 16:30:28 2018 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: uipc_socket2.c,v 1.132 2018/09/03 16:29:35 riastradh Exp $     */
+/*     $NetBSD: uipc_socket2.c,v 1.133 2018/11/04 16:30:29 christos Exp $      */
 
 /*-
  * Copyright (c) 2008 The NetBSD Foundation, Inc.
@@ -58,7 +58,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: uipc_socket2.c,v 1.132 2018/09/03 16:29:35 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: uipc_socket2.c,v 1.133 2018/11/04 16:30:29 christos Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_ddb.h"
@@ -509,8 +509,10 @@
        KASSERT(solocked(so));
 
        so->so_rcv.sb_overflowed++;
-       so->so_rerror = ENOBUFS;
-       sorwakeup(so);
+       if (so->so_options & SO_RERROR)  {
+               so->so_rerror = ENOBUFS;
+               sorwakeup(so);
+       }
 }
 
 /*
diff -r c12c2692e21e -r d0d971f56eda sys/sys/socket.h
--- a/sys/sys/socket.h  Sun Nov 04 13:48:27 2018 +0000
+++ b/sys/sys/socket.h  Sun Nov 04 16:30:28 2018 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: socket.h,v 1.128 2018/09/16 20:40:20 mrg Exp $ */
+/*     $NetBSD: socket.h,v 1.129 2018/11/04 16:30:29 christos Exp $    */
 
 /*
  * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
@@ -132,7 +132,30 @@
 #define        SO_NOSIGPIPE    0x0800          /* no SIGPIPE from EPIPE */
 #define        SO_ACCEPTFILTER 0x1000          /* there is an accept filter */
 #define        SO_TIMESTAMP    0x2000          /* timestamp received dgram traffic */



Home | Main Index | Thread Index | Old Index