From fd9343579afac30a971f06643a669733d9acb407 Mon Sep 17 00:00:00 2001 From: "deraadt@openbsd.org" Date: Sun, 14 Nov 2021 18:47:43 +0000 Subject: [PATCH] upstream: use ppoll() instead of pselect() with djm OpenBSD-Commit-ID: 980f87c9564d5d2ad55722b7a6f44f21284cd215 --- sshd.c | 46 +++++++++++++++++++++++----------------------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/sshd.c b/sshd.c index ea63d0307..6953d04d8 100644 --- a/sshd.c +++ b/sshd.c @@ -1,4 +1,4 @@ -/* $OpenBSD: sshd.c,v 1.578 2021/07/19 02:21:50 dtucker Exp $ */ +/* $OpenBSD: sshd.c,v 1.579 2021/11/14 18:47:43 deraadt Exp $ */ /* * Author: Tatu Ylonen * Copyright (c) 1995 Tatu Ylonen , Espoo, Finland @@ -64,6 +64,7 @@ #include #endif #include +#include #include #include #include @@ -1132,8 +1133,8 @@ server_listen(void) static void server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) { - fd_set *fdset; - int i, j, ret, maxfd; + struct pollfd *pfd = NULL; + int i, j, ret; int ostartups = -1, startups = 0, listening = 0, lameduck = 0; int startup_p[2] = { -1 , -1 }; char c = 0; @@ -1143,12 +1144,6 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) u_char rnd[256]; sigset_t nsigset, osigset; - /* setup fd set for accept */ - fdset = NULL; - maxfd = 0; - for (i = 0; i < num_listen_socks; i++) - if (listen_socks[i] > maxfd) - maxfd = listen_socks[i]; /* pipes connected to unauthenticated child sshd processes */ startup_pipes = xcalloc(options.max_startups, sizeof(int)); startup_flags = xcalloc(options.max_startups, sizeof(int)); @@ -1158,7 +1153,7 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) /* * Prepare signal mask that we use to block signals that might set * received_sigterm or received_sighup, so that we are guaranteed - * to immediately wake up the pselect if a signal is received after + * to immediately wake up the ppoll if a signal is received after * the flag is checked. */ sigemptyset(&nsigset); @@ -1167,6 +1162,9 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) sigaddset(&nsigset, SIGTERM); sigaddset(&nsigset, SIGQUIT); + pfd = xcalloc(num_listen_socks + options.max_startups, + sizeof(struct pollfd)); + /* * Stay listening for connections until the system crashes or * the daemon is killed with a signal. @@ -1198,27 +1196,29 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) sighup_restart(); } } - free(fdset); - fdset = xcalloc(howmany(maxfd + 1, NFDBITS), - sizeof(fd_mask)); - for (i = 0; i < num_listen_socks; i++) - FD_SET(listen_socks[i], fdset); - for (i = 0; i < options.max_startups; i++) + for (i = 0; i < num_listen_socks; i++) { + pfd[i].fd = listen_socks[i]; + pfd[i].events = POLLIN; + } + for (i = 0; i < options.max_startups; i++) { + pfd[num_listen_socks+i].fd = startup_pipes[i]; if (startup_pipes[i] != -1) - FD_SET(startup_pipes[i], fdset); + pfd[num_listen_socks+i].events = POLLIN; + } /* Wait until a connection arrives or a child exits. */ - ret = pselect(maxfd+1, fdset, NULL, NULL, NULL, &osigset); + ret = ppoll(pfd, num_listen_socks + options.max_startups, + NULL, &osigset); if (ret == -1 && errno != EINTR) - error("pselect: %.100s", strerror(errno)); + error("ppoll: %.100s", strerror(errno)); sigprocmask(SIG_SETMASK, &osigset, NULL); if (ret == -1) continue; for (i = 0; i < options.max_startups; i++) { if (startup_pipes[i] == -1 || - !FD_ISSET(startup_pipes[i], fdset)) + !(pfd[num_listen_socks+i].revents & POLLIN)) continue; switch (read(startup_pipes[i], &c, sizeof(c))) { case -1: @@ -1249,7 +1249,7 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) } } for (i = 0; i < num_listen_socks; i++) { - if (!FD_ISSET(listen_socks[i], fdset)) + if (!(pfd[i].revents & POLLIN)) continue; fromlen = sizeof(from); *newsock = accept(listen_socks[i], @@ -1286,8 +1286,6 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) for (j = 0; j < options.max_startups; j++) if (startup_pipes[j] == -1) { startup_pipes[j] = startup_p[0]; - if (maxfd < startup_p[0]) - maxfd = startup_p[0]; startups++; startup_flags[j] = 1; break; @@ -1315,6 +1313,7 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) send_rexec_state(config_s[0], cfg); close(config_s[0]); } + free(pfd); return; } @@ -1357,6 +1356,7 @@ server_accept_loop(int *sock_in, int *sock_out, int *newsock, int *config_s) (void)atomicio(vwrite, startup_pipe, "\0", 1); } + free(pfd); return; }