From: Mathieu Desnoyers Date: Tue, 10 Dec 2019 15:55:03 +0000 (-0500) Subject: sessiond: implement clear command X-Git-Url: http://git.efficios.com/?p=lttng-tools.git;a=commitdiff_plain;h=022349df3783b538b41cf4a3cd55e7b231603bdd sessiond: implement clear command Signed-off-by: Mathieu Desnoyers Change-Id: Iaff1df7693858f5c9b24a6c8d1411fd76cc83714 Signed-off-by: Jérémie Galarneau --- diff --git a/src/bin/lttng-sessiond/Makefile.am b/src/bin/lttng-sessiond/Makefile.am index ebb8cb284..481a3e3b3 100644 --- a/src/bin/lttng-sessiond/Makefile.am +++ b/src/bin/lttng-sessiond/Makefile.am @@ -50,7 +50,8 @@ lttng_sessiond_SOURCES = utils.c utils.h \ register.c register.h \ manage-apps.c manage-apps.h \ manage-kernel.c manage-kernel.h \ - manage-consumer.c manage-consumer.h + manage-consumer.c manage-consumer.h \ + clear.c clear.h if HAVE_LIBLTTNG_UST_CTL lttng_sessiond_SOURCES += trace-ust.c ust-registry.c ust-app.c \ diff --git a/src/bin/lttng-sessiond/clear.c b/src/bin/lttng-sessiond/clear.c new file mode 100644 index 000000000..38f4796dc --- /dev/null +++ b/src/bin/lttng-sessiond/clear.c @@ -0,0 +1,212 @@ +/* + * Copyright (C) 2019 - Jonathan Rajotte + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License, version 2 only, as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along with + * this program; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#define _LGPL_SOURCE +#include +#include +#include +#include + +#include +#include +#include + +#include "clear.h" +#include "session.h" +#include "ust-app.h" +#include "kernel.h" +#include "cmd.h" + +struct cmd_clear_session_reply_context { + int reply_sock_fd; +}; + +static +void cmd_clear_session_reply(const struct ltt_session *session, + void *_reply_context) +{ + int ret; + ssize_t comm_ret; + const struct cmd_clear_session_reply_context *reply_context = + _reply_context; + struct lttcomm_lttng_msg llm = { + .cmd_type = LTTNG_CLEAR_SESSION, + .ret_code = LTTNG_OK, + .pid = UINT32_MAX, + .cmd_header_size = 0, + .data_size = 0, + }; + + DBG("End of clear command: replying to client"); + comm_ret = lttcomm_send_unix_sock(reply_context->reply_sock_fd, + &llm, sizeof(llm)); + if (comm_ret != (ssize_t) sizeof(llm)) { + ERR("Failed to send result of session \"%s\" clear to client", + session->name); + } + ret = close(reply_context->reply_sock_fd); + if (ret) { + PERROR("Failed to close client socket in deferred session clear reply"); + } + free(_reply_context); +} + +int cmd_clear_session(struct ltt_session *session, int *sock_fd) +{ + int ret = LTTNG_OK; + struct cmd_clear_session_reply_context *reply_context = NULL; + bool session_was_active = false; + struct ltt_kernel_session *ksession; + struct ltt_ust_session *usess; + + ksession = session->kernel_session; + usess = session->ust_session; + + if (sock_fd) { + reply_context = zmalloc(sizeof(*reply_context)); + if (!reply_context) { + ret = LTTNG_ERR_NOMEM; + goto end; + } + reply_context->reply_sock_fd = *sock_fd; + } + + if (!session->has_been_started) { + /* + * Nothing to be cleared, this is not an error: there is + * indeed nothing to do, and there is no reason why we + * should return an error to the user. + */ + goto end; + } + + /* Unsupported feature in lttng-relayd before 2.11. */ + if (session->consumer->type == CONSUMER_DST_NET && + (session->consumer->relay_major_version == 2 && + session->consumer->relay_minor_version < 12)) { + ret = LTTNG_ERR_CLEAR_NOT_AVAILABLE_RELAY; + goto end; + } + if (session->consumer->type == CONSUMER_DST_NET && + !session->consumer->relay_allows_clear) { + ret = LTTNG_ERR_CLEAR_NOT_AVAILABLE_RELAY; + goto end; + } + + /* + * After a stop followed by a clear, all subsequent clear are + * effect-less until start is performed. + */ + if (session->cleared_after_last_stop) { + ret = LTTNG_OK; + goto end; + } + + /* + * After a stop followed by a rotation, all subsequent clear are effect-less + * until start is performed. + */ + if (session->rotated_after_last_stop) { + ret = LTTNG_OK; + goto end; + } + + session_was_active = session->active; + if (session_was_active) { + ret = stop_kernel_session(ksession); + if (ret != LTTNG_OK) { + goto end; + } + if (usess && usess->active) { + ret = ust_app_stop_trace_all(usess); + if (ret < 0) { + ret = LTTNG_ERR_UST_STOP_FAIL; + goto end; + } + } + } + + /* + * Clear active kernel and UST session buffers. + */ + if (session->kernel_session) { + ret = kernel_clear_session(session); + if (ret != LTTNG_OK) { + goto end; + } + } + if (session->ust_session) { + ret = ust_app_clear_session(session); + if (ret != LTTNG_OK) { + goto end; + } + } + + if (session->output_traces) { + /* + * Use rotation to delete local and remote stream files. + */ + if (reply_context) { + ret = session_add_clear_notifier(session, + cmd_clear_session_reply, + (void *) reply_context); + if (ret) { + ret = LTTNG_ERR_FATAL; + goto end; + } + /* + * On success, ownership of reply_context has been + * passed to session_add_clear_notifier(). + */ + reply_context = NULL; + *sock_fd = -1; + } + ret = cmd_rotate_session(session, NULL, true, + LTTNG_TRACE_CHUNK_COMMAND_TYPE_DELETE); + if (ret != LTTNG_OK) { + goto end; + } + } + if (!session->active) { + session->cleared_after_last_stop = true; + } + if (session_was_active) { + /* Kernel tracing */ + if (ksession != NULL) { + DBG("Start kernel tracing session \"%s\"", + session->name); + ret = start_kernel_session(ksession); + if (ret != LTTNG_OK) { + goto end; + } + } + + /* Flag session that trace should start automatically */ + if (usess) { + int int_ret = ust_app_start_trace_all(usess); + + if (int_ret < 0) { + ret = LTTNG_ERR_UST_START_FAIL; + goto end; + } + } + } + ret = LTTNG_OK; +end: + free(reply_context); + return ret; +} diff --git a/src/bin/lttng-sessiond/clear.h b/src/bin/lttng-sessiond/clear.h new file mode 100644 index 000000000..1f8985c27 --- /dev/null +++ b/src/bin/lttng-sessiond/clear.h @@ -0,0 +1,25 @@ +/* + * Copyright (C) 2019 - Jonathan Rajotte + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License, version 2 only, as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for + * more details. + * + * You should have received a copy of the GNU General Public License along with + * this program; if not, write to the Free Software Foundation, Inc., 51 + * Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#ifndef CLEAR_H +#define CLEAR_H + +#include "session.h" + +int cmd_clear_session(struct ltt_session *session, int *sock_fd); + +#endif /* CLEAT_H */ diff --git a/src/bin/lttng-sessiond/client.c b/src/bin/lttng-sessiond/client.c index 551295efb..30ec11119 100644 --- a/src/bin/lttng-sessiond/client.c +++ b/src/bin/lttng-sessiond/client.c @@ -38,6 +38,7 @@ #include "testpoint.h" #include "utils.h" #include "manage-consumer.h" +#include "clear.h" static bool is_root; @@ -747,6 +748,7 @@ static int process_client_msg(struct command_ctx *cmd_ctx, int *sock, case LTTNG_ROTATION_GET_INFO: case LTTNG_ROTATION_SET_SCHEDULE: case LTTNG_SESSION_LIST_ROTATION_SCHEDULES: + case LTTNG_CLEAR_SESSION: need_domain = 0; break; default: @@ -1935,6 +1937,11 @@ error_add_context: ret = LTTNG_OK; break; } + case LTTNG_CLEAR_SESSION: + { + ret = cmd_clear_session(cmd_ctx->session, sock); + break; + } default: ret = LTTNG_ERR_UND; break;