summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLaszlo Orban <laszlo.orban@quest.com>2020-01-21 14:26:53 +0100
committerLaszlo Orban <laszlo.orban@quest.com>2020-01-21 14:26:53 +0100
commitaa7eae2a9f0e0fd562631ea4d18cb4813178bd02 (patch)
tree8bcaf1f9a3b8da220798b81a8c4bbf4e248d46b4
parent77777dec3831c81ecd2b116ad3d520a85d1c2219 (diff)
downloadsudo-aa7eae2a9f0e0fd562631ea4d18cb4813178bd02.tar.gz
logserver: enable/disable SO_KEEPALIVE socket option based on tcp_keepalive configuration option in sudo_logsrvd.conf
-rw-r--r--examples/sudo_logsrvd.conf3
-rw-r--r--logsrvd/logsrvd.c12
-rw-r--r--logsrvd/logsrvd.h1
-rw-r--r--logsrvd/logsrvd_conf.c21
4 files changed, 37 insertions, 0 deletions
diff --git a/examples/sudo_logsrvd.conf b/examples/sudo_logsrvd.conf
index 7fd4306c8..fdc643525 100644
--- a/examples/sudo_logsrvd.conf
+++ b/examples/sudo_logsrvd.conf
@@ -21,6 +21,9 @@
# respond. A value of 0 will disable the timeout. The default value is 30.
#timeout = 30
+# If set, SO_KEEPALIVE socket option is set on the connected socket.
+#tcp_keepalive = true
+
# If set, secure connections with TLS 1.2 or 1.3.
# By default, server connections are not encrypted.
#tls = true
diff --git a/logsrvd/logsrvd.c b/logsrvd/logsrvd.c
index d88f3c9b1..01296ff87 100644
--- a/logsrvd/logsrvd.c
+++ b/logsrvd/logsrvd.c
@@ -20,6 +20,7 @@
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
+#include <netinet/tcp.h>
#include <arpa/inet.h>
#include <errno.h>
@@ -1508,6 +1509,17 @@ listener_cb(int fd, int what, void *v)
}
/* TODO: pause accepting on ENFILE and EMFILE */
}
+
+ /* set keepalive socket option on socket returned by accept */
+ if (logsrvd_conf_tcp_keepalive()) {
+ int keepalive = 1;
+ if (setsockopt(sock, SOL_SOCKET, SO_KEEPALIVE, &keepalive,
+ sizeof(keepalive)) == -1) {
+ sudo_debug_printf(SUDO_DEBUG_ERROR|SUDO_DEBUG_LINENO|SUDO_DEBUG_ERRNO,
+ "unable to set SO_KEEPALIVE option");
+ }
+ }
+
debug_return;
}
diff --git a/logsrvd/logsrvd.h b/logsrvd/logsrvd.h
index 1e081e025..ef5ab687d 100644
--- a/logsrvd/logsrvd.h
+++ b/logsrvd/logsrvd.h
@@ -176,6 +176,7 @@ bool logsrvd_conf_read(const char *path);
const char *logsrvd_conf_iolog_dir(void);
const char *logsrvd_conf_iolog_file(void);
struct listen_address_list *logsrvd_conf_listen_address(void);
+bool logsrvd_conf_tcp_keepalive(void);
struct timespec *logsrvd_conf_get_sock_timeout(void);
#if defined(HAVE_OPENSSL)
bool logsrvd_conf_get_tls_opt(void);
diff --git a/logsrvd/logsrvd_conf.c b/logsrvd/logsrvd_conf.c
index fb1056d3e..e9fb12618 100644
--- a/logsrvd/logsrvd_conf.c
+++ b/logsrvd/logsrvd_conf.c
@@ -74,6 +74,7 @@ static struct logsrvd_config {
struct logsrvd_config_server {
struct listen_address_list addresses;
struct timespec timeout;
+ bool tcp_keepalive;
#if defined(HAVE_OPENSSL)
bool tls;
struct logsrvd_tls_config tls_config;
@@ -134,6 +135,11 @@ logsrvd_conf_listen_address(void)
return &logsrvd_config->server.addresses;
}
+bool
+logsrvd_conf_tcp_keepalive(void)
+{
+ return logsrvd_config->server.tcp_keepalive;
+}
struct timespec *
logsrvd_conf_get_sock_timeout(void)
{
@@ -415,6 +421,19 @@ cb_timeout(struct logsrvd_config *config, const char *str)
debug_return_bool(true);
}
+static bool
+cb_keepalive(struct logsrvd_config *config, const char *str)
+{
+ int val;
+ debug_decl(cb_keepalive, SUDO_DEBUG_UTIL);
+
+ if ((val = sudo_strtobool(str)) == -1)
+ debug_return_bool(false);
+
+ config->server.tcp_keepalive = val;
+ debug_return_bool(true);
+}
+
#if defined(HAVE_OPENSSL)
static bool
cb_tls_opt(struct logsrvd_config *config, const char *str)
@@ -677,6 +696,7 @@ cb_logfile_time_format(struct logsrvd_config *config, const char *str)
static struct logsrvd_config_entry server_conf_entries[] = {
{ "listen_address", cb_listen_address },
{ "timeout", cb_timeout },
+ { "tcp_keepalive", cb_keepalive },
#if defined(HAVE_OPENSSL)
{ "tls", cb_tls_opt },
{ "tls_key", cb_tls_key },
@@ -857,6 +877,7 @@ logsrvd_conf_alloc(void)
/* Server defaults */
TAILQ_INIT(&config->server.addresses);
config->server.timeout.tv_sec = DEFAULT_SOCKET_TIMEOUT_SEC;
+ config->server.tcp_keepalive = true;
#if defined(HAVE_OPENSSL)
config->server.tls_config.cacert_path = strdup(DEFAULT_CA_CERT_PATH);