summaryrefslogtreecommitdiff
path: root/serverloop.c
diff options
context:
space:
mode:
authordtucker@openbsd.org <dtucker@openbsd.org>2017-08-11 03:58:36 +0000
committerDamien Miller <djm@mindrot.org>2017-08-12 16:47:10 +1000
commitb60ff20051ef96dfb207b6bfa45c0ad6c34a542a (patch)
tree5aba8318170dd597a9805e72e152b0c70a9f9397 /serverloop.c
parent94bc1e7ffba3cbdea8c7dcdab8376bf29283128f (diff)
upstream commit
Keep track of the last time we actually heard from the client and use this to also schedule a client_alive_check(). Prevents activity on a forwarded port from indefinitely preventing the select timeout so that client_alive_check() will eventually (although not optimally) be called. Analysis by willchan at google com via bz#2756, feedback & ok djm@ Upstream-ID: c08721e0bbda55c6d18e2760f3fe1b17fb71169e
Diffstat (limited to 'serverloop.c')
-rw-r--r--serverloop.c18
1 files changed, 15 insertions, 3 deletions
diff --git a/serverloop.c b/serverloop.c
index b5eb3440a..4b8d5ba68 100644
--- a/serverloop.c
+++ b/serverloop.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: serverloop.c,v 1.193 2017/05/31 07:00:13 markus Exp $ */ 1/* $OpenBSD: serverloop.c,v 1.194 2017/08/11 03:58:36 dtucker Exp $ */
2/* 2/*
3 * Author: Tatu Ylonen <ylo@cs.hut.fi> 3 * Author: Tatu Ylonen <ylo@cs.hut.fi>
4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland 4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@@ -204,6 +204,7 @@ wait_until_can_do_something(int connection_in, int connection_out,
204 int ret; 204 int ret;
205 time_t minwait_secs = 0; 205 time_t minwait_secs = 0;
206 int client_alive_scheduled = 0; 206 int client_alive_scheduled = 0;
207 static time_t last_client_time;
207 208
208 /* Allocate and update select() masks for channel descriptors. */ 209 /* Allocate and update select() masks for channel descriptors. */
209 channel_prepare_select(readsetp, writesetp, maxfdp, nallocp, 210 channel_prepare_select(readsetp, writesetp, maxfdp, nallocp,
@@ -268,8 +269,19 @@ wait_until_can_do_something(int connection_in, int connection_out,
268 memset(*writesetp, 0, *nallocp); 269 memset(*writesetp, 0, *nallocp);
269 if (errno != EINTR) 270 if (errno != EINTR)
270 error("select: %.100s", strerror(errno)); 271 error("select: %.100s", strerror(errno));
271 } else if (ret == 0 && client_alive_scheduled) 272 } else if (client_alive_scheduled) {
272 client_alive_check(); 273 time_t now = monotime();
274
275 if (ret == 0) { /* timeout */
276 client_alive_check();
277 } else if (FD_ISSET(connection_in, *readsetp)) {
278 last_client_time = now;
279 } else if (last_client_time != 0 && last_client_time +
280 options.client_alive_interval < now) {
281 client_alive_check();
282 last_client_time = now;
283 }
284 }
273 285
274 notify_done(*readsetp); 286 notify_done(*readsetp);
275} 287}