From: Jérémie Galarneau Date: Tue, 26 Nov 2019 20:08:01 +0000 (-0500) Subject: relayd: add fd-cap option to limit the number of opened FDs X-Git-Tag: v2.12.0-rc1~67 X-Git-Url: https://git.lttng.org/?p=lttng-tools.git;a=commitdiff_plain;h=896010e38f60e85d757a43778e25a51b890a7443 relayd: add fd-cap option to limit the number of opened FDs Add an --fd-cap option to the relay daemon in order to allow the launch of the relay daemon with a maximal number of file descriptors to be open at any given moment. When the value of the --fd-cap parameter is left unset, the maximal number of file descriptors is set to the system's NOFILE soft limit (see GETRLIMIT(3P)). A minimal number of file descriptors of 30 is imposed, mainly to prevent absurd configurations (someone setting 1 fd) which would not even allow one target to connect and stream traces. This also allows a bit of leverage to open file descriptors that could be needed by future changes without "breaking" an existing configuration. Signed-off-by: Jérémie Galarneau Change-Id: Ibaf49b25ccf3e3a8013115c9478744ca3646e306 --- diff --git a/src/bin/lttng-relayd/main.c b/src/bin/lttng-relayd/main.c index 4e30ac498..f61f1f13e 100644 --- a/src/bin/lttng-relayd/main.c +++ b/src/bin/lttng-relayd/main.c @@ -34,6 +34,7 @@ #include #include #include +#include #include #include #include @@ -41,6 +42,7 @@ #include #include #include +#include #include #include @@ -160,6 +162,9 @@ static uint64_t last_relay_stream_id; */ static struct relay_conn_queue relay_conn_queue; +/* Cap of file desriptors to be in simultaneous use by the relay daemon. */ +static unsigned int lttng_opt_fd_cap; + /* Global relay stream hash table. */ struct lttng_ht *relay_streams_ht; @@ -181,6 +186,7 @@ static struct option long_options[] = { { "daemonize", 0, 0, 'd', }, { "background", 0, 0, 'b', }, { "group", 1, 0, 'g', }, + { "fd-cap", 1, 0, '\0', }, { "help", 0, 0, 'h', }, { "output", 1, 0, 'o', }, { "verbose", 0, 0, 'v', }, @@ -224,9 +230,34 @@ static int set_option(int opt, const char *arg, const char *optname) switch (opt) { case 0: - fprintf(stderr, "option %s", optname); - if (arg) { - fprintf(stderr, " with arg %s\n", arg); + if (!strcmp(optname, "fd-cap")) { + unsigned long v; + + errno = 0; + v = strtoul(arg, NULL, 0); + if (errno != 0 || !isdigit(arg[0])) { + ERR("Wrong value in --fd-cap parameter: %s", + arg); + ret = -1; + goto end; + } + if (v < DEFAULT_RELAYD_MINIMAL_FD_CAP) { + ERR("File descriptor cap must be set to at least %d", + DEFAULT_RELAYD_MINIMAL_FD_CAP); + } + if (v >= UINT_MAX) { + ERR("File descriptor cap overflow in --fd-cap parameter: %s", + arg); + ret = -1; + goto end; + } + lttng_opt_fd_cap = (unsigned int) v; + DBG3("File descriptor cap set to %u", lttng_opt_fd_cap); + } else { + fprintf(stderr, "unknown option %s", optname); + if (arg) { + fprintf(stderr, " with arg %s\n", arg); + } } break; case 'C': @@ -563,6 +594,18 @@ static int set_options(int argc, char **argv) goto exit; } } + if (lttng_opt_fd_cap == 0) { + int ret; + struct rlimit rlimit; + + ret = getrlimit(RLIMIT_NOFILE, &rlimit); + if (ret) { + PERROR("Failed to get file descriptor limit"); + retval = -1; + } + + lttng_opt_fd_cap = rlimit.rlim_cur; + } if (opt_group_output_by == RELAYD_GROUP_OUTPUT_BY_UNKNOWN) { opt_group_output_by = RELAYD_GROUP_OUTPUT_BY_HOST; diff --git a/src/common/defaults.h b/src/common/defaults.h index 2c3e80f43..e57e6495f 100644 --- a/src/common/defaults.h +++ b/src/common/defaults.h @@ -93,6 +93,8 @@ #define DEFAULT_RELAYD_RUNDIR "%s" #define DEFAULT_RELAYD_PATH DEFAULT_RELAYD_RUNDIR "/relayd" +#define DEFAULT_RELAYD_MINIMAL_FD_CAP 30 + /* Default lttng run directory */ #define DEFAULT_LTTNG_HOME_ENV_VAR "LTTNG_HOME" #define DEFAULT_LTTNG_FALLBACK_HOME_ENV_VAR "HOME"