From: Mathieu Desnoyers Date: Mon, 21 Nov 2011 08:52:30 +0000 (-0500) Subject: Implement 32/64 bit consumer support X-Git-Tag: v2.0-pre15~93 X-Git-Url: https://git.lttng.org./?a=commitdiff_plain;h=7753dea8e1af2342c4d42d2efc5da62538709ca8;p=lttng-tools.git Implement 32/64 bit consumer support Signed-off-by: Mathieu Desnoyers --- diff --git a/configure.ac b/configure.ac index c602e2bae..973b95080 100644 --- a/configure.ac +++ b/configure.ac @@ -14,8 +14,10 @@ AC_CHECK_HEADERS([ \ getopt.h sys/ipc.h sys/shm.h popt.h grp.h \ ]) -AC_ARG_VAR([LTTNG_TOOLS_COMPAT_BIN_DIR], [Search for LTTng Tools 32-bit compatibility binaries in this location.]) -AC_DEFINE_UNQUOTED([CONFIG_COMPAT_BIN_DIR], $LTTNG_TOOLS_COMPAT_BIN_PREFIX, [Search for LTTng Tools 32-bit compatibility binaries in this location.]) +AC_ARG_VAR([LTTNG_TOOLS_32BIT_BINDIR], [Search for LTTng Tools 32-bit binaries in this location.]) +AC_DEFINE_UNQUOTED([CONFIG_32BIT_BINDIR], $LTTNG_TOOLS_32BIT_BINDIR, [Search for LTTng Tools 32-bit binaries in this location.]) +AC_ARG_VAR([LTTNG_TOOLS_64BIT_BINDIR], [Search for LTTng Tools 64-bit binaries in this location.]) +AC_DEFINE_UNQUOTED([CONFIG_64BIT_BINDIR], $LTTNG_TOOLS_64BIT_BINDIR, [Search for LTTng Tools 64-bit binaries in this location.]) # Check for pthread AC_CHECK_LIB([pthread], [pthread_create], [], diff --git a/include/lttng-consumerd.h b/include/lttng-consumerd.h index 8c240309e..1cd78571b 100644 --- a/include/lttng-consumerd.h +++ b/include/lttng-consumerd.h @@ -25,9 +25,14 @@ #define KCONSUMERD_CMD_SOCK_PATH KCONSUMERD_PATH "/command" #define KCONSUMERD_ERR_SOCK_PATH KCONSUMERD_PATH "/error" -/* UST consumer path */ -#define USTCONSUMERD_PATH LTTNG_RUNDIR "/ustconsumerd" -#define USTCONSUMERD_CMD_SOCK_PATH USTCONSUMERD_PATH "/command" -#define USTCONSUMERD_ERR_SOCK_PATH USTCONSUMERD_PATH "/error" +/* UST 64-bit consumer path */ +#define USTCONSUMERD64_PATH LTTNG_RUNDIR "/ustconsumerd64" +#define USTCONSUMERD64_CMD_SOCK_PATH USTCONSUMERD64_PATH "/command" +#define USTCONSUMERD64_ERR_SOCK_PATH USTCONSUMERD64_PATH "/error" + +/* UST 32-bit consumer path */ +#define USTCONSUMERD32_PATH LTTNG_RUNDIR "/ustconsumerd32" +#define USTCONSUMERD32_CMD_SOCK_PATH USTCONSUMERD32_PATH "/command" +#define USTCONSUMERD32_ERR_SOCK_PATH USTCONSUMERD32_PATH "/error" #endif /* _LTTNG_CONSUMERD_H */ diff --git a/include/lttng-sessiond-comm.h b/include/lttng-sessiond-comm.h index 55647faf0..d282f77de 100644 --- a/include/lttng-sessiond-comm.h +++ b/include/lttng-sessiond-comm.h @@ -125,7 +125,8 @@ enum lttcomm_return_code { LTTCOMM_UST_META_FAIL, /* UST open metadata failed */ LTTCOMM_UST_START_FAIL, /* UST start trace failed */ LTTCOMM_UST_STOP_FAIL, /* UST stop trace failed */ - LTTCOMM_UST_CONSUMER_FAIL, /* UST consumer start failed */ + LTTCOMM_UST_CONSUMER64_FAIL, /* 64-bit UST consumer start failed */ + LTTCOMM_UST_CONSUMER32_FAIL, /* 32-bit UST consumer start failed */ LTTCOMM_UST_STREAM_FAIL, /* UST create stream failed */ LTTCOMM_UST_DIR_FAIL, /* UST trace directory creation failed */ LTTCOMM_UST_DIR_EXIST, /* UST trace directory exist */ diff --git a/include/lttng/lttng-consumer.h b/include/lttng/lttng-consumer.h index 6f893a53a..e5672d7b7 100644 --- a/include/lttng/lttng-consumer.h +++ b/include/lttng/lttng-consumer.h @@ -68,7 +68,8 @@ struct lttng_consumer_stream_list { enum lttng_consumer_type { LTTNG_CONSUMER_UNKNOWN = 0, LTTNG_CONSUMER_KERNEL, - LTTNG_CONSUMER_UST, + LTTNG_CONSUMER64_UST, + LTTNG_CONSUMER32_UST, }; struct lttng_consumer_channel { diff --git a/liblttng-consumer/lttng-consumer.c b/liblttng-consumer/lttng-consumer.c index 0d8dd0014..893df7208 100644 --- a/liblttng-consumer/lttng-consumer.c +++ b/liblttng-consumer/lttng-consumer.c @@ -129,7 +129,8 @@ void consumer_del_stream(struct lttng_consumer_stream *stream) } } break; - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: lttng_ustconsumer_del_stream(stream); break; default: @@ -204,7 +205,8 @@ struct lttng_consumer_stream *consumer_allocate_stream( switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: break; - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: stream->cpu = stream->chan->cpucount++; ret = lttng_ustconsumer_allocate_stream(stream); if (ret) { @@ -244,7 +246,8 @@ int consumer_add_stream(struct lttng_consumer_stream *stream) switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: break; - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: /* Streams are in CPU number order (we rely on this) */ stream->cpu = stream->chan->nr_streams++; break; @@ -289,7 +292,8 @@ void consumer_del_channel(struct lttng_consumer_channel *channel) switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: break; - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: lttng_ustconsumer_del_channel(channel); break; default: @@ -344,7 +348,8 @@ struct lttng_consumer_channel *consumer_allocate_channel( channel->mmap_base = NULL; channel->mmap_len = 0; break; - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: ret = lttng_ustconsumer_allocate_channel(channel); if (ret) { free(channel); @@ -656,7 +661,8 @@ int lttng_consumer_on_read_subbuffer_mmap( switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_on_read_subbuffer_mmap(ctx, stream, len); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return lttng_ustconsumer_on_read_subbuffer_mmap(ctx, stream, len); default: ERR("Unknown consumer_data type"); @@ -676,7 +682,8 @@ int lttng_consumer_on_read_subbuffer_splice( switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_on_read_subbuffer_splice(ctx, stream, len); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return -ENOSYS; default: ERR("Unknown consumer_data type"); @@ -697,7 +704,8 @@ int lttng_consumer_take_snapshot(struct lttng_consumer_local_data *ctx, switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_take_snapshot(ctx, stream); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return lttng_ustconsumer_take_snapshot(ctx, stream); default: ERR("Unknown consumer_data type"); @@ -720,7 +728,8 @@ int lttng_consumer_get_produced_snapshot( switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_get_produced_snapshot(ctx, stream, pos); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return lttng_ustconsumer_get_produced_snapshot(ctx, stream, pos); default: ERR("Unknown consumer_data type"); @@ -735,7 +744,8 @@ int lttng_consumer_recv_cmd(struct lttng_consumer_local_data *ctx, switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_recv_cmd(ctx, sock, consumer_sockpoll); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return lttng_ustconsumer_recv_cmd(ctx, sock, consumer_sockpoll); default: ERR("Unknown consumer_data type"); @@ -862,7 +872,8 @@ void *lttng_consumer_thread_poll_fds(void *data) num_hup++; } else if ((pollfd[i].revents & POLLHUP) && !(pollfd[i].revents & POLLIN)) { - if (consumer_data.type == LTTNG_CONSUMER_UST) { + if (consumer_data.type == LTTNG_CONSUMER32_UST + || consumer_data.type == LTTNG_CONSUMER64_UST) { DBG("Polling fd %d tells it has hung up. Attempting flush and read.", pollfd[i].fd); if (!local_stream[i]->hangup_flush_done) { @@ -1034,7 +1045,8 @@ int lttng_consumer_read_subbuffer(struct lttng_consumer_stream *stream, switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_read_subbuffer(stream, ctx); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return lttng_ustconsumer_read_subbuffer(stream, ctx); default: ERR("Unknown consumer_data type"); @@ -1048,7 +1060,8 @@ int lttng_consumer_on_recv_stream(struct lttng_consumer_stream *stream) switch (consumer_data.type) { case LTTNG_CONSUMER_KERNEL: return lttng_kconsumer_on_recv_stream(stream); - case LTTNG_CONSUMER_UST: + case LTTNG_CONSUMER32_UST: + case LTTNG_CONSUMER64_UST: return lttng_ustconsumer_on_recv_stream(stream); default: ERR("Unknown consumer_data type"); diff --git a/liblttng-sessiond-comm/lttng-sessiond-comm.c b/liblttng-sessiond-comm/lttng-sessiond-comm.c index 9cea3fede..31e43de10 100644 --- a/liblttng-sessiond-comm/lttng-sessiond-comm.c +++ b/liblttng-sessiond-comm/lttng-sessiond-comm.c @@ -85,7 +85,8 @@ static const char *lttcomm_readable_code[] = { [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_META_FAIL) ] = "Opening metadata failed", [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_START_FAIL) ] = "Starting UST trace failed", [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_STOP_FAIL) ] = "Stoping UST trace failed", - [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_CONSUMER_FAIL) ] = "UST consumer start failed", + [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_CONSUMER64_FAIL) ] = "64-bit UST consumer start failed", + [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_CONSUMER32_FAIL) ] = "32-bit UST consumer start failed", [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_STREAM_FAIL) ] = "UST create stream failed", [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_DIR_FAIL) ] = "UST trace directory creation failed", [ LTTCOMM_ERR_INDEX(LTTCOMM_UST_DIR_EXIST) ] = "UST trace directory already exist", diff --git a/lttng-consumerd/lttng-consumerd.c b/lttng-consumerd/lttng-consumerd.c index 9bc86b0b3..dce188ace 100644 --- a/lttng-consumerd/lttng-consumerd.c +++ b/lttng-consumerd/lttng-consumerd.c @@ -38,6 +38,7 @@ #include #include #include +#include #include #include @@ -63,7 +64,7 @@ static char command_sock_path[PATH_MAX]; /* Global command socket path */ static char error_sock_path[PATH_MAX]; /* Global error path */ static enum lttng_consumer_type opt_type = LTTNG_CONSUMER_KERNEL; -/* the liblttngkconsumerd context */ +/* the liblttngconsumerd context */ static struct lttng_consumer_local_data *ctx; /* @@ -123,9 +124,9 @@ static void usage(void) fprintf(stderr, "Usage: %s OPTIONS\n\nOptions:\n", progname); fprintf(stderr, " -h, --help " "Display this usage.\n"); - fprintf(stderr, " -c, --kconsumerd-cmd-sock PATH " + fprintf(stderr, " -c, --consumerd-cmd-sock PATH " "Specify path for the command socket\n"); - fprintf(stderr, " -e, --kconsumerd-err-sock PATH " + fprintf(stderr, " -e, --consumerd-err-sock PATH " "Specify path for the error socket\n"); fprintf(stderr, " -d, --daemonize " "Start as a daemon.\n"); @@ -155,8 +156,8 @@ static void parse_args(int argc, char **argv) int c; static struct option long_options[] = { - { "kconsumerd-cmd-sock", 1, 0, 'c' }, - { "kconsumerd-err-sock", 1, 0, 'e' }, + { "consumerd-cmd-sock", 1, 0, 'c' }, + { "consumerd-err-sock", 1, 0, 'e' }, { "daemonize", 0, 0, 'd' }, { "help", 0, 0, 'h' }, { "quiet", 0, 0, 'q' }, @@ -209,7 +210,13 @@ static void parse_args(int argc, char **argv) break; #ifdef HAVE_LIBLTTNG_UST_CTL case 'u': - opt_type = LTTNG_CONSUMER_UST; +# if (CAA_BITS_PER_LONG == 64) + opt_type = LTTNG_CONSUMER64_UST; +# elif (CAA_BITS_PER_LONG == 32) + opt_type = LTTNG_CONSUMER32_UST; +# else +# error "Unknown bitness" +# endif break; #endif default: @@ -242,10 +249,20 @@ int main(int argc, char **argv) } if (strlen(command_sock_path) == 0) { - snprintf(command_sock_path, PATH_MAX, - opt_type == LTTNG_CONSUMER_KERNEL ? - KCONSUMERD_CMD_SOCK_PATH : - USTCONSUMERD_CMD_SOCK_PATH); + switch (opt_type) { + case LTTNG_CONSUMER_KERNEL: + strcpy(command_sock_path, KCONSUMERD_CMD_SOCK_PATH); + break; + case LTTNG_CONSUMER64_UST: + strcpy(command_sock_path, USTCONSUMERD64_CMD_SOCK_PATH); + break; + case LTTNG_CONSUMER32_UST: + strcpy(command_sock_path, USTCONSUMERD32_CMD_SOCK_PATH); + break; + default: + WARN("Unknown consumerd type"); + goto error; + } } /* create the consumer instance with and assign the callbacks */ ctx = lttng_consumer_create(opt_type, lttng_consumer_read_subbuffer, @@ -256,10 +273,20 @@ int main(int argc, char **argv) lttng_consumer_set_command_sock_path(ctx, command_sock_path); if (strlen(error_sock_path) == 0) { - snprintf(error_sock_path, PATH_MAX, - opt_type == LTTNG_CONSUMER_KERNEL ? - KCONSUMERD_ERR_SOCK_PATH : - USTCONSUMERD_ERR_SOCK_PATH); + switch (opt_type) { + case LTTNG_CONSUMER_KERNEL: + strcpy(error_sock_path, KCONSUMERD_ERR_SOCK_PATH); + break; + case LTTNG_CONSUMER64_UST: + strcpy(error_sock_path, USTCONSUMERD64_ERR_SOCK_PATH); + break; + case LTTNG_CONSUMER32_UST: + strcpy(error_sock_path, USTCONSUMERD32_ERR_SOCK_PATH); + break; + default: + WARN("Unknown consumerd type"); + goto error; + } } if (set_signal_handler() < 0) { diff --git a/lttng-sessiond/main.c b/lttng-sessiond/main.c index 2f80e2cee..d5b4c8db2 100644 --- a/lttng-sessiond/main.c +++ b/lttng-sessiond/main.c @@ -96,9 +96,18 @@ static pid_t ppid; /* Parent PID for --sig-parent option */ /* Consumer daemon specific control data */ static struct consumer_data kconsumer_data = { .type = LTTNG_CONSUMER_KERNEL, + .err_unix_sock_path = KCONSUMERD_ERR_SOCK_PATH, + .cmd_unix_sock_path = KCONSUMERD_CMD_SOCK_PATH, }; -static struct consumer_data ustconsumer_data = { - .type = LTTNG_CONSUMER_UST, +static struct consumer_data ustconsumer64_data = { + .type = LTTNG_CONSUMER64_UST, + .err_unix_sock_path = USTCONSUMERD64_ERR_SOCK_PATH, + .cmd_unix_sock_path = USTCONSUMERD64_CMD_SOCK_PATH, +}; +static struct consumer_data ustconsumer32_data = { + .type = LTTNG_CONSUMER32_UST, + .err_unix_sock_path = USTCONSUMERD32_ERR_SOCK_PATH, + .cmd_unix_sock_path = USTCONSUMERD32_CMD_SOCK_PATH, }; static int dispatch_thread_exit; @@ -157,23 +166,49 @@ static struct ust_cmd_queue ust_cmd_queue; */ static struct ltt_session_list *session_list_ptr; -int ust_consumer_fd; +int ust_consumerd64_fd = -1; +int ust_consumerd32_fd = -1; + +static const char *consumerd64_prog = "lttng-consumerd"; +static const char *consumerd32_prog = "lttng-consumerd"; -static const char *compat32_consumer_bindir = - __stringify(CONFIG_COMPAT_BIN_DIR); -static const char *compat32_consumer_prog = "lttng-consumerd"; +static const char *consumerd64_bindir = + __stringify(CONFIG_64BIT_BINDIR); +static const char *consumerd32_bindir = + __stringify(CONFIG_32BIT_BINDIR); static -void setup_compat32_consumer(void) +void setup_consumerd_path(void) { const char *bindir; + /* + * Allow INSTALL_BIN_PATH to be used as a target path for the + * native architecture size consumer if CONFIG_NBIT_BINDIR as + * not been defined. + */ +#if (CAA_BITS_PER_LONG == 64) + if (!consumerd64_bindir[0]) { + consumerd64_bindir = INSTALL_BIN_PATH; + } +#elif (CAA_BITS_PER_LONG == 32) + if (!consumerd32_bindir[0]) { + consumerd32_bindir = INSTALL_BIN_PATH; + } +#else +#error "Unknown bitness" +#endif + /* * runtime env. var. overrides the build default. */ - bindir = getenv("LTTNG_TOOLS_COMPAT_BIN_DIR"); + bindir = getenv("LTTNG_TOOLS_64BIT_BINDIR"); + if (bindir) { + consumerd64_bindir = bindir; + } + bindir = getenv("LTTNG_TOOLS_32BIT_BINDIR"); if (bindir) { - compat32_consumer_bindir = bindir; + consumerd32_bindir = bindir; } } @@ -1466,12 +1501,35 @@ static pid_t spawn_consumerd(struct consumer_data *consumer_data) switch (consumer_data->type) { case LTTNG_CONSUMER_KERNEL: execl(INSTALL_BIN_PATH "/lttng-consumerd", - "lttng-consumerd", verbosity, "-k", NULL); + "lttng-consumerd", verbosity, "-k", + "--consumerd-cmd-sock", consumer_data->cmd_unix_sock_path, + "--consumerd-err-sock", consumer_data->err_unix_sock_path, + NULL); break; - case LTTNG_CONSUMER_UST: - execl(INSTALL_BIN_PATH "/lttng-consumerd", - "lttng-consumerd", verbosity, "-u", NULL); + case LTTNG_CONSUMER64_UST: + { + char path[PATH_MAX]; + + snprintf(path, PATH_MAX, "%s/%s", + consumerd64_bindir, consumerd64_prog); + execl(path, verbosity, "-u", + "--consumerd-cmd-sock", consumer_data->cmd_unix_sock_path, + "--consumerd-err-sock", consumer_data->err_unix_sock_path, + NULL); break; + } + case LTTNG_CONSUMER32_UST: + { + char path[PATH_MAX]; + + snprintf(path, PATH_MAX, "%s/%s", + consumerd32_bindir, consumerd32_prog); + execl(path, verbosity, "-u", + "--consumerd-cmd-sock", consumer_data->cmd_unix_sock_path, + "--consumerd-err-sock", consumer_data->err_unix_sock_path, + NULL); + break; + } default: perror("unknown consumer type"); exit(EXIT_FAILURE); @@ -3022,20 +3080,38 @@ static int process_client_msg(struct command_ctx *cmd_ctx) goto error; } } - /* Start the kernel consumer daemon */ - pthread_mutex_lock(&ustconsumer_data.pid_mutex); - if (ustconsumer_data.pid == 0 && + /* Start the UST consumer daemons */ + /* 64-bit */ + pthread_mutex_lock(&ustconsumer64_data.pid_mutex); + if (consumerd64_bindir[0] != '\0' && + ustconsumer64_data.pid == 0 && cmd_ctx->lsm->cmd_type != LTTNG_REGISTER_CONSUMER) { - pthread_mutex_unlock(&ustconsumer_data.pid_mutex); - ret = start_consumerd(&ustconsumer_data); + pthread_mutex_unlock(&ustconsumer64_data.pid_mutex); + ret = start_consumerd(&ustconsumer64_data); if (ret < 0) { - ret = LTTCOMM_KERN_CONSUMER_FAIL; + ret = LTTCOMM_UST_CONSUMER64_FAIL; + ust_consumerd64_fd = -EINVAL; goto error; } - ust_consumer_fd = ustconsumer_data.cmd_sock; + ust_consumerd64_fd = ustconsumer64_data.cmd_sock; } else { - pthread_mutex_unlock(&ustconsumer_data.pid_mutex); + pthread_mutex_unlock(&ustconsumer64_data.pid_mutex); + } + /* 32-bit */ + if (consumerd32_bindir[0] != '\0' && + ustconsumer32_data.pid == 0 && + cmd_ctx->lsm->cmd_type != LTTNG_REGISTER_CONSUMER) { + pthread_mutex_unlock(&ustconsumer32_data.pid_mutex); + ret = start_consumerd(&ustconsumer32_data); + if (ret < 0) { + ret = LTTCOMM_UST_CONSUMER32_FAIL; + ust_consumerd32_fd = -EINVAL; + goto error; + } + ust_consumerd32_fd = ustconsumer32_data.cmd_sock; + } else { + pthread_mutex_unlock(&ustconsumer32_data.pid_mutex); } } break; @@ -3459,9 +3535,12 @@ static void usage(void) fprintf(stderr, " -a, --apps-sock PATH Specify path for apps unix socket\n"); fprintf(stderr, " --kconsumerd-err-sock PATH Specify path for the kernel consumer error socket\n"); fprintf(stderr, " --kconsumerd-cmd-sock PATH Specify path for the kernel consumer command socket\n"); - fprintf(stderr, " --ustconsumerd-err-sock PATH Specify path for the UST consumer error socket\n"); - fprintf(stderr, " --ustconsumerd-cmd-sock PATH Specify path for the UST consumer command socket\n"); - fprintf(stderr, " --ustconsumerd-compat32 PATH Specify path for the 32-bit UST consumer daemon binary\n"); + fprintf(stderr, " --ustconsumerd32-err-sock PATH Specify path for the 32-bit UST consumer error socket\n"); + fprintf(stderr, " --ustconsumerd64-err-sock PATH Specify path for the 64-bit UST consumer error socket\n"); + fprintf(stderr, " --ustconsumerd32-cmd-sock PATH Specify path for the 32-bit UST consumer command socket\n"); + fprintf(stderr, " --ustconsumerd64-cmd-sock PATH Specify path for the 64-bit UST consumer command socket\n"); + fprintf(stderr, " --ustconsumerd32 PATH Specify path for the 32-bit UST consumer daemon binary\n"); + fprintf(stderr, " --ustconsumerd64 PATH Specify path for the 64-bit UST consumer daemon binary\n"); fprintf(stderr, " -d, --daemonize Start as a daemon.\n"); fprintf(stderr, " -g, --group NAME Specify the tracing group name. (default: tracing)\n"); fprintf(stderr, " -V, --version Show version number.\n"); @@ -3483,9 +3562,12 @@ static int parse_args(int argc, char **argv) { "apps-sock", 1, 0, 'a' }, { "kconsumerd-cmd-sock", 1, 0, 'C' }, { "kconsumerd-err-sock", 1, 0, 'E' }, - { "ustconsumerd-cmd-sock", 1, 0, 'D' }, - { "ustconsumerd-err-sock", 1, 0, 'F' }, - { "ustconsumerd-compat32", 1, 0, 'u' }, + { "ustconsumerd64", 1, 0, 't' }, + { "ustconsumerd64-cmd-sock", 1, 0, 'D' }, + { "ustconsumerd64-err-sock", 1, 0, 'F' }, + { "ustconsumerd32", 1, 0, 'u' }, + { "ustconsumerd32-cmd-sock", 1, 0, 'G' }, + { "ustconsumerd32-err-sock", 1, 0, 'H' }, { "daemonize", 0, 0, 'd' }, { "sig-parent", 0, 0, 'S' }, { "help", 0, 0, 'h' }, @@ -3499,7 +3581,7 @@ static int parse_args(int argc, char **argv) while (1) { int option_index = 0; - c = getopt_long(argc, argv, "dhqvVS" "a:c:g:s:C:E:D:F:Z:u", + c = getopt_long(argc, argv, "dhqvVS" "a:c:g:s:C:E:D:F:Z:u:t", long_options, &option_index); if (c == -1) { break; @@ -3540,10 +3622,16 @@ static int parse_args(int argc, char **argv) snprintf(kconsumer_data.cmd_unix_sock_path, PATH_MAX, "%s", optarg); break; case 'F': - snprintf(ustconsumer_data.err_unix_sock_path, PATH_MAX, "%s", optarg); + snprintf(ustconsumer64_data.err_unix_sock_path, PATH_MAX, "%s", optarg); break; case 'D': - snprintf(ustconsumer_data.cmd_unix_sock_path, PATH_MAX, "%s", optarg); + snprintf(ustconsumer64_data.cmd_unix_sock_path, PATH_MAX, "%s", optarg); + break; + case 'H': + snprintf(ustconsumer32_data.err_unix_sock_path, PATH_MAX, "%s", optarg); + break; + case 'G': + snprintf(ustconsumer32_data.cmd_unix_sock_path, PATH_MAX, "%s", optarg); break; case 'q': opt_quiet = 1; @@ -3556,7 +3644,10 @@ static int parse_args(int argc, char **argv) opt_verbose_consumer += 1; break; case 'u': - compat32_consumer_bindir = optarg; + consumerd32_bindir = optarg; + break; + case 't': + consumerd64_bindir = optarg; break; default: /* Unknown option or other error. @@ -3681,10 +3772,17 @@ static int set_permissions(void) perror("chown"); } - /* ustconsumer error socket path */ - ret = chown(ustconsumer_data.err_unix_sock_path, 0, gid); + /* 64-bit ustconsumer error socket path */ + ret = chown(ustconsumer64_data.err_unix_sock_path, 0, gid); + if (ret < 0) { + ERR("Unable to set group on %s", ustconsumer64_data.err_unix_sock_path); + perror("chown"); + } + + /* 32-bit ustconsumer compat32 error socket path */ + ret = chown(ustconsumer32_data.err_unix_sock_path, 0, gid); if (ret < 0) { - ERR("Unable to set group on %s", ustconsumer_data.err_unix_sock_path); + ERR("Unable to set group on %s", ustconsumer32_data.err_unix_sock_path); perror("chown"); } @@ -3738,21 +3836,22 @@ error: static int set_consumer_sockets(struct consumer_data *consumer_data) { int ret; - const char *path = consumer_data->type == LTTNG_CONSUMER_KERNEL ? - KCONSUMERD_PATH : USTCONSUMERD_PATH; - - if (strlen(consumer_data->err_unix_sock_path) == 0) { - snprintf(consumer_data->err_unix_sock_path, PATH_MAX, - consumer_data->type == LTTNG_CONSUMER_KERNEL ? - KCONSUMERD_ERR_SOCK_PATH : - USTCONSUMERD_ERR_SOCK_PATH); - } + const char *path; - if (strlen(consumer_data->cmd_unix_sock_path) == 0) { - snprintf(consumer_data->cmd_unix_sock_path, PATH_MAX, - consumer_data->type == LTTNG_CONSUMER_KERNEL ? - KCONSUMERD_CMD_SOCK_PATH : - USTCONSUMERD_CMD_SOCK_PATH); + switch (consumer_data->type) { + case LTTNG_CONSUMER_KERNEL: + path = KCONSUMERD_PATH; + break; + case LTTNG_CONSUMER64_UST: + path = USTCONSUMERD64_PATH; + break; + case LTTNG_CONSUMER32_UST: + path = USTCONSUMERD32_PATH; + break; + default: + ERR("Consumer type unknown"); + ret = -EINVAL; + goto error; } ret = mkdir(path, S_IRWXU | S_IRWXG); @@ -3884,7 +3983,7 @@ int main(int argc, char **argv) goto error; } - setup_compat32_consumer(); + setup_consumerd_path(); /* Parse arguments */ progname = argv[0]; @@ -3981,10 +4080,16 @@ int main(int argc, char **argv) goto exit; } - ret = set_consumer_sockets(&ustconsumer_data); + ret = set_consumer_sockets(&ustconsumer64_data); if (ret < 0) { goto exit; } + + ret = set_consumer_sockets(&ustconsumer32_data); + if (ret < 0) { + goto exit; + } + /* Setup kernel tracer */ init_kernel_tracer(); diff --git a/lttng-sessiond/ust-app.c b/lttng-sessiond/ust-app.c index ab65f2b15..78c84bd75 100644 --- a/lttng-sessiond/ust-app.c +++ b/lttng-sessiond/ust-app.c @@ -835,21 +835,14 @@ int ust_app_register(struct ust_register_msg *msg, int sock) { struct ust_app *lta; - /* - * Currently support only tracing of application which share the - * same bitness as the consumer. Eventually implement dispatch - * to specific compat32 consumer. - */ - if (msg->bits_per_long != CAA_BITS_PER_LONG) { + if ((msg->bits_per_long == 64 && ust_consumerd64_fd == -EINVAL) + || (msg->bits_per_long == 32 && ust_consumerd32_fd == -EINVAL)) { ERR("Registration failed: application \"%s\" (pid: %d) has " - "%d-bit long, but only " - "%d-bit lttng-consumerd is available.\n", - msg->name, msg->pid, msg->bits_per_long, - CAA_BITS_PER_LONG); + "%d-bit long, but no consumerd for this long size is available.\n", + msg->name, msg->pid, msg->bits_per_long); close(sock); return -EINVAL; } - lta = zmalloc(sizeof(struct ust_app)); if (lta == NULL) { PERROR("malloc"); @@ -859,6 +852,7 @@ int ust_app_register(struct ust_register_msg *msg, int sock) lta->ppid = msg->ppid; lta->uid = msg->uid; lta->gid = msg->gid; + lta->bits_per_long = msg->bits_per_long; lta->v_major = msg->major; lta->v_minor = msg->minor; strncpy(lta->name, msg->name, sizeof(lta->name)); @@ -1140,6 +1134,7 @@ int ust_app_start_trace(struct ltt_ust_session *usess, struct ust_app *app) struct ust_app_session *ua_sess; struct ust_app_channel *ua_chan; struct ltt_ust_stream *ustream; + int consumerd_fd; DBG("Starting tracing for ust app pid %d", app->key.pid); @@ -1193,8 +1188,19 @@ int ust_app_start_trace(struct ltt_ust_session *usess, struct ust_app *app) } } + switch (app->bits_per_long) { + case 64: + consumerd_fd = ust_consumerd64_fd; + break; + case 32: + consumerd_fd = ust_consumerd32_fd; + break; + default: + ret = -EINVAL; + goto error_rcu_unlock; + } /* Setup UST consumer socket and send fds to it */ - ret = ust_consumer_send_session(ust_consumer_fd, ua_sess); + ret = ust_consumer_send_session(consumerd_fd, ua_sess); if (ret < 0) { goto error_rcu_unlock; } diff --git a/lttng-sessiond/ust-app.h b/lttng-sessiond/ust-app.h index ce18bb2f7..ec6bafdfe 100644 --- a/lttng-sessiond/ust-app.h +++ b/lttng-sessiond/ust-app.h @@ -26,7 +26,7 @@ #define UST_APP_EVENT_LIST_SIZE 32 -extern int ust_consumer_fd; +extern int ust_consumerd64_fd, ust_consumerd32_fd; /* * Application registration data structure. @@ -96,7 +96,8 @@ struct ust_app_session { struct ust_app { pid_t ppid; uid_t uid; /* User ID that owns the apps */ - gid_t gid; /* Group ID that owns the apps */ + gid_t gid; /* Group ID that owns the apps */ + int bits_per_long; uint32_t v_major; /* Verion major number */ uint32_t v_minor; /* Verion minor number */ char name[17]; /* Process name (short) */ diff --git a/lttng-sessiond/ust-consumer.c b/lttng-sessiond/ust-consumer.c index 866d7bd56..8a2ba728d 100644 --- a/lttng-sessiond/ust-consumer.c +++ b/lttng-sessiond/ust-consumer.c @@ -124,6 +124,11 @@ int ust_consumer_send_session(int consumer_fd, struct ust_app_session *usess) DBG("Sending metadata stream fd"); + if (consumer_fd < 0) { + ERR("Consumer has negative file descriptor"); + return -EINVAL; + } + if (usess->metadata->obj->shm_fd != 0) { int fd; int fds[2];