#include <sys/stat.h>
#include <sys/types.h>
#include <sys/wait.h>
+#include <sys/resource.h>
#include <inttypes.h>
#include <urcu/futex.h>
#include <urcu/uatomic.h>
#include <unistd.h>
#include <fcntl.h>
#include <strings.h>
+#include <ctype.h>
#include <lttng/lttng.h>
#include <common/common.h>
*/
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;
{ "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', },
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':
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;
free(opt_output_path);
free(opt_working_directory);
+ if (health_relayd) {
+ health_app_destroy(health_relayd);
+ }
/* Close thread quit pipes */
+ utils_close_pipe(health_quit_pipe);
utils_close_pipe(thread_quit_pipe);
+ if (sessiond_trace_chunk_registry) {
+ sessiond_trace_chunk_registry_destroy(
+ sessiond_trace_chunk_registry);
+ }
+
uri_free(control_uri);
uri_free(data_uri);
/* Live URI is freed in the live thread. */
if (!sessiond_trace_chunk_registry) {
ERR("Failed to initialize session daemon trace chunk registry");
retval = -1;
- goto exit_sessiond_trace_chunk_registry;
+ goto exit_options;
}
/* Initialize thread health monitoring */
if (!health_relayd) {
PERROR("health_app_create error");
retval = -1;
- goto exit_health_app_create;
+ goto exit_options;
}
/* Create thread quit pipe */
if (init_thread_quit_pipe()) {
retval = -1;
- goto exit_init_data;
+ goto exit_options;
}
/* Setup the thread apps communication pipe. */
if (create_relay_conn_pipe()) {
retval = -1;
- goto exit_init_data;
+ goto exit_options;
}
/* Init relay command queue. */
sessions_ht = lttng_ht_new(0, LTTNG_HT_TYPE_U64);
if (!sessions_ht) {
retval = -1;
- goto exit_init_data;
+ goto exit_options;
}
/* tables of streams indexed by stream ID */
relay_streams_ht = lttng_ht_new(0, LTTNG_HT_TYPE_U64);
if (!relay_streams_ht) {
retval = -1;
- goto exit_init_data;
+ goto exit_options;
}
/* tables of streams indexed by stream ID */
viewer_streams_ht = lttng_ht_new(0, LTTNG_HT_TYPE_U64);
if (!viewer_streams_ht) {
retval = -1;
- goto exit_init_data;
+ goto exit_options;
}
ret = utils_create_pipe(health_quit_pipe);
if (ret) {
retval = -1;
- goto exit_health_quit_pipe;
+ goto exit_options;
}
/* Create thread to manage the client socket */
errno = ret;
PERROR("pthread_create health");
retval = -1;
- goto exit_health_thread;
+ goto exit_options;
}
/* Setup the dispatcher thread */
PERROR("pthread_join health_thread");
retval = -1;
}
-exit_health_thread:
-
- utils_close_pipe(health_quit_pipe);
-exit_health_quit_pipe:
-
-exit_init_data:
- health_app_destroy(health_relayd);
- sessiond_trace_chunk_registry_destroy(sessiond_trace_chunk_registry);
-exit_health_app_create:
-exit_sessiond_trace_chunk_registry:
exit_options:
/*
* Wait for all pending call_rcu work to complete before tearing