]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
sd-netlink: don't give up on netlink on ENOBUFS
authorLennart Poettering <lennart@poettering.net>
Tue, 21 Feb 2017 15:25:02 +0000 (16:25 +0100)
committerLennart Poettering <lennart@poettering.net>
Tue, 21 Feb 2017 20:41:32 +0000 (21:41 +0100)
If our netlink input buffer overruns the kernel will send us ENOBUFS on
the next recvmsg(). Don't consider this a complete failure resulting in
closing of the netlink socket. Instead, simply continue (after debug
logging).

Of course, ideally we'd have a better strategy for this, and would have
a way to resync if this happens (as well as a scheme for cancelling all
ongoing asynchronous transactions), but for now let's at least not choke
fatally, and simply accept that we lost some messages and continue.

Note that if we lose messages when synchronously waiting for an
operation to complete, we'll still propagate the ENOBUFS up, to make the
individual transaction fail.

See: #5398

(This bug does not properly fix the issue, hence we should leave the bug
open.)

src/libsystemd/sd-netlink/netlink-socket.c
src/libsystemd/sd-netlink/sd-netlink.c

index a0fd8a3ac9e58d29711c046979da2d48771f98bb..129bfd2d806318a25622b66809570493b45a9560 100644 (file)
@@ -281,7 +281,7 @@ static int socket_recv_message(int fd, struct iovec *iov, uint32_t *_group, bool
                 else if (errno == EAGAIN)
                         log_debug("rtnl: no data in socket");
 
-                return (errno == EAGAIN || errno == EINTR) ? 0 : -errno;
+                return IN_SET(errno, EAGAIN, EINTR) ? 0 : -errno;
         }
 
         if (sender.nl.nl_pid != 0) {
@@ -292,7 +292,7 @@ static int socket_recv_message(int fd, struct iovec *iov, uint32_t *_group, bool
                         /* drop the message */
                         r = recvmsg(fd, &msg, 0);
                         if (r < 0)
-                                return (errno == EAGAIN || errno == EINTR) ? 0 : -errno;
+                                return IN_SET(errno, EAGAIN, EINTR) ? 0 : -errno;
                 }
 
                 return 0;
index 43114eb825c5390661319654e142470ad522c572..68435564deebc2f1a7e27959aef863609dc39b4e 100644 (file)
@@ -276,6 +276,10 @@ static int dispatch_rqueue(sd_netlink *rtnl, sd_netlink_message **message) {
         if (rtnl->rqueue_size <= 0) {
                 /* Try to read a new message */
                 r = socket_read_message(rtnl);
+                if (r == -ENOBUFS) { /* FIXME: ignore buffer overruns for now */
+                        log_debug_errno(r, "Got ENOBUFS from netlink socket, ignoring.");
+                        return 1;
+                }
                 if (r <= 0)
                         return r;
         }