From b60ff20051ef96dfb207b6bfa45c0ad6c34a542a Mon Sep 17 00:00:00 2001 From: "dtucker@openbsd.org" Date: Fri, 11 Aug 2017 03:58:36 +0000 Subject: 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 --- serverloop.c | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) (limited to 'serverloop.c') diff --git a/serverloop.c b/serverloop.c index b5eb3440..4b8d5ba6 100644 --- a/serverloop.c +++ b/serverloop.c @@ -1,4 +1,4 @@ -/* $OpenBSD: serverloop.c,v 1.193 2017/05/31 07:00:13 markus Exp $ */ +/* $OpenBSD: serverloop.c,v 1.194 2017/08/11 03:58:36 dtucker Exp $ */ /* * Author: Tatu Ylonen * Copyright (c) 1995 Tatu Ylonen , Espoo, Finland @@ -204,6 +204,7 @@ wait_until_can_do_something(int connection_in, int connection_out, int ret; time_t minwait_secs = 0; int client_alive_scheduled = 0; + static time_t last_client_time; /* Allocate and update select() masks for channel descriptors. */ channel_prepare_select(readsetp, writesetp, maxfdp, nallocp, @@ -268,8 +269,19 @@ wait_until_can_do_something(int connection_in, int connection_out, memset(*writesetp, 0, *nallocp); if (errno != EINTR) error("select: %.100s", strerror(errno)); - } else if (ret == 0 && client_alive_scheduled) - client_alive_check(); + } else if (client_alive_scheduled) { + time_t now = monotime(); + + if (ret == 0) { /* timeout */ + client_alive_check(); + } else if (FD_ISSET(connection_in, *readsetp)) { + last_client_time = now; + } else if (last_client_time != 0 && last_client_time + + options.client_alive_interval < now) { + client_alive_check(); + last_client_time = now; + } + } notify_done(*readsetp); } -- cgit v1.2.3