Hi,

I think a daemon should run with non-blocking sockets.  Especially
the upcoming tcp listen socket needs this.  Replace the existing
fcntl(O_NONBLOCK) with the simpler SOCK_NONBLOCK and add it to the
receive sockets.  React to EWOULDBLOCK although it should not happen.

ok?

bluhm

Index: usr.sbin/syslogd/syslogd.c
===================================================================
RCS file: /data/mirror/openbsd/cvs/src/usr.sbin/syslogd/syslogd.c,v
retrieving revision 1.168
diff -u -p -r1.168 syslogd.c
--- usr.sbin/syslogd/syslogd.c  2 Jul 2015 16:24:48 -0000       1.168
+++ usr.sbin/syslogd/syslogd.c  2 Jul 2015 21:27:30 -0000
@@ -703,8 +703,8 @@ socket_bind(const char *proto, const cha
                if (*fdp >= 0)
                        continue;
 
-               if ((*fdp = socket(res->ai_family, res->ai_socktype,
-                   res->ai_protocol)) == -1)
+               if ((*fdp = socket(res->ai_family,
+                   res->ai_socktype | SOCK_NONBLOCK, res->ai_protocol)) == -1)
                        continue;
 
                if (getnameinfo(res->ai_addr, res->ai_addrlen, hostname,
@@ -784,7 +784,7 @@ udp_readcb(int fd, short event, void *ar
                cvthname((struct sockaddr *)&sa, resolve, sizeof(resolve));
                dprintf("cvthname res: %s\n", resolve);
                printline(resolve, linebuf);
-       } else if (n < 0 && errno != EINTR)
+       } else if (n < 0 && errno != EINTR && errno != EWOULDBLOCK)
                logerror("recvfrom udp");
 }
 
@@ -800,32 +800,23 @@ unix_readcb(int fd, short event, void *a
        if (n > 0) {
                linebuf[n] = '\0';
                printline(LocalHostName, linebuf);
-       } else if (n < 0 && errno != EINTR)
+       } else if (n < 0 && errno != EINTR && errno != EWOULDBLOCK)
                logerror("recvfrom unix");
 }
 
 int
 tcp_socket(struct filed *f)
 {
-       int      s, flags;
+       int      s;
        char     ebuf[ERRBUFSIZE];
 
-       if ((s = socket(f->f_un.f_forw.f_addr.ss_family, SOCK_STREAM,
-           IPPROTO_TCP)) == -1) {
+       if ((s = socket(f->f_un.f_forw.f_addr.ss_family,
+           SOCK_STREAM | SOCK_NONBLOCK, IPPROTO_TCP)) == -1) {
                snprintf(ebuf, sizeof(ebuf), "socket \"%s\"",
                    f->f_un.f_forw.f_loghost);
                logerror(ebuf);
                return (-1);
        }
-       /* Connect must not block the process. */
-       if ((flags = fcntl(s, F_GETFL)) == -1 ||
-           fcntl(s, F_SETFL, flags | O_NONBLOCK) == -1) {
-               snprintf(ebuf, sizeof(ebuf), "fcntl \"%s\" O_NONBLOCK",
-                   f->f_un.f_forw.f_loghost);
-               logerror(ebuf);
-               close(s);
-               return (-1);
-       }
        if (connect(s, (struct sockaddr *)&f->f_un.f_forw.f_addr,
            f->f_un.f_forw.f_addr.ss_len) == -1 && errno != EINPROGRESS) {
                snprintf(ebuf, sizeof(ebuf), "connect \"%s\"",
@@ -2453,10 +2444,9 @@ void
 ctlsock_acceptcb(int fd, short event, void *arg)
 {
        struct event            *ev = arg;
-       int                      flags;
 
        dprintf("Accepting control connection\n");
-       fd = accept(fd, NULL, NULL);
+       fd = accept4(fd, NULL, NULL, SOCK_NONBLOCK);
        if (fd == -1) {
                if (errno != EINTR && errno != EWOULDBLOCK &&
                    errno != ECONNABORTED)
@@ -2470,13 +2460,6 @@ ctlsock_acceptcb(int fd, short event, vo
        /* Only one connection at a time */
        event_del(ev);
 
-       if ((flags = fcntl(fd, F_GETFL)) == -1 ||
-           fcntl(fd, F_SETFL, flags | O_NONBLOCK) == -1) {
-               logerror("fcntl ctlconn O_NONBLOCK");
-               close(fd);
-               return;
-       }
-
        fd_ctlconn = fd;
        /* file descriptor has changed, reset event */
        event_set(&ev_ctlread, fd_ctlconn, EV_READ|EV_PERSIST,
@@ -2523,6 +2506,8 @@ ctlconn_readcb(int fd, short event, void
        case -1:
                if (errno == EINTR)
                        goto retry;
+               if (errno == EWOULDBLOCK)
+                       return;
                logerror("ctlconn read");
                /* FALLTHROUGH */
        case 0:
@@ -2652,6 +2637,8 @@ ctlconn_writecb(int fd, short event, voi
        case -1:
                if (errno == EINTR)
                        goto retry;
+               if (errno == EWOULDBLOCK)
+                       return;
                if (errno != EPIPE)
                        logerror("ctlconn write");
                /* FALLTHROUGH */

Reply via email to