X-Git-Url: https://git.lttng.org/?p=lttng-tools.git;a=blobdiff_plain;f=src%2Fbin%2Flttng-sessiond%2Fkernel.cpp;h=f7d232ffc01aadb346b5fdf6d8c4928ea5163727;hp=22ce819b525b49523b17dca282aa1656644c7825;hb=HEAD;hpb=7966af5763c4aaca39df9bbfa9277ff15715c720 diff --git a/src/bin/lttng-sessiond/kernel.cpp b/src/bin/lttng-sessiond/kernel.cpp index 22ce819b5..4cc51a279 100644 --- a/src/bin/lttng-sessiond/kernel.cpp +++ b/src/bin/lttng-sessiond/kernel.cpp @@ -1,74 +1,127 @@ /* - * Copyright (C) 2011 David Goulet + * Copyright (C) 2011 EfficiOS Inc. * * SPDX-License-Identifier: GPL-2.0-only * */ #define _LGPL_SOURCE -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include +#include "condition-internal.hpp" +#include "consumer.hpp" +#include "event-notifier-error-accounting.hpp" +#include "kern-modules.hpp" +#include "kernel-consumer.hpp" +#include "kernel.hpp" +#include "lttng-sessiond.hpp" +#include "lttng-syscall.hpp" +#include "modprobe.hpp" +#include "notification-thread-commands.hpp" +#include "sessiond-config.hpp" +#include "tracker.hpp" +#include "utils.hpp" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include #include #include #include - +#include #include -#include -#include -#include -#include -#include -#include - -#include "event-notifier-error-accounting.h" -#include "lttng-sessiond.h" -#include "lttng-syscall.h" -#include "condition-internal.h" -#include "consumer.h" -#include "kernel.h" -#include "kernel-consumer.h" -#include "kern-modules.h" -#include "sessiond-config.h" -#include "utils.h" -#include "rotate.h" -#include "modprobe.h" -#include "tracker.h" -#include "notification-thread-commands.h" +#include +#include +#include +#include +#include +#include +#include + +namespace { /* * Key used to reference a channel between the sessiond and the consumer. This * is only read and updated with the session_list lock held. */ -static uint64_t next_kernel_channel_key; +uint64_t next_kernel_channel_key; -static const char *module_proc_lttng = "/proc/lttng"; +const char *module_proc_lttng = "/proc/lttng"; -static int kernel_tracer_fd = -1; -static int kernel_tracer_event_notifier_group_fd = -1; -static int kernel_tracer_event_notifier_group_notification_fd = -1; -static struct cds_lfht *kernel_token_to_event_notifier_rule_ht; +int kernel_tracer_fd = -1; +nonstd::optional kernel_tracer_status = nonstd::nullopt; +int kernel_tracer_event_notifier_group_fd = -1; +int kernel_tracer_event_notifier_group_notification_fd = -1; +struct cds_lfht *kernel_token_to_event_notifier_rule_ht; + +const char *kernel_tracer_status_to_str(lttng_kernel_tracer_status status) +{ + switch (status) { + case LTTNG_KERNEL_TRACER_STATUS_INITIALIZED: + return "LTTNG_KERNEL_TRACER_STATUS_INITIALIZED"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_UNKNOWN: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_UNKNOWN"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_NEED_ROOT: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_NEED_ROOT"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_NOTIFIER: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_NOTIFIER"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_OPEN_PROC_LTTNG: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_OPEN_PROC_LTTNG"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_VERSION_MISMATCH: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_VERSION_MISMATCH"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_UNKNOWN: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_UNKNOWN"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_MISSING: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_MISSING"; + case LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_SIGNATURE: + return "LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_SIGNATURE"; + } + + abort(); +} + +/* + * On some architectures, calling convention details are embedded in the symbol + * addresses. Uprobe requires a "clean" symbol offset (or at least, an address + * where an instruction boundary would be legal) to add + * instrumentation. sanitize_uprobe_offset implements that sanitization logic on + * a per-architecture basis. + */ +#if defined(__arm__) || defined(__aarch64__) +static inline uint64_t sanitize_uprobe_offset(uint64_t raw_offset) +{ + /* + * The least significant bit is used when branching to switch to thumb + * ISA. However, it's an invalid address for us; mask the least + * significant bit. + */ + return raw_offset &= ~0b1; +} +#else /* defined(__arm__) || defined(__aarch64__) */ +static inline uint64_t sanitize_uprobe_offset(uint64_t raw_offset) +{ + return raw_offset; +} +#endif +} /* namespace */ /* * Add context on a kernel channel. * * Assumes the ownership of ctx. */ -int kernel_add_channel_context(struct ltt_kernel_channel *chan, - struct ltt_kernel_context *ctx) +int kernel_add_channel_context(struct ltt_kernel_channel *chan, struct ltt_kernel_context *ctx) { int ret; @@ -98,7 +151,7 @@ int kernel_add_channel_context(struct ltt_kernel_channel *chan, end: cds_list_add_tail(&ctx->list, &chan->ctx_list); ctx->in_list = true; - ctx = NULL; + ctx = nullptr; error: if (ctx) { trace_kernel_destroy_context(ctx); @@ -119,7 +172,7 @@ int kernel_create_session(struct ltt_session *session) /* Allocate data structure */ lks = trace_kernel_create_session(); - if (lks == NULL) { + if (lks == nullptr) { ret = -1; goto error; } @@ -155,13 +208,15 @@ int kernel_create_session(struct ltt_session *session) } if (ret) { WARN("Could not set kernel session name for session %" PRIu64 " name: %s", - session->id, session->name); + session->id, + session->name); } ret = kernctl_session_set_creation_time(lks->fd, session->creation_time); if (ret) { WARN("Could not set kernel session creation time for session %" PRIu64 " name: %s", - session->id, session->name); + session->id, + session->name); } return 0; @@ -178,8 +233,7 @@ error: * Create a kernel channel, register it to the kernel tracer and add it to the * kernel session. */ -int kernel_create_channel(struct ltt_kernel_session *session, - struct lttng_channel *chan) +int kernel_create_channel(struct ltt_kernel_session *session, struct lttng_channel *chan) { int ret; struct ltt_kernel_channel *lkc; @@ -189,15 +243,19 @@ int kernel_create_channel(struct ltt_kernel_session *session, /* Allocate kernel channel */ lkc = trace_kernel_create_channel(chan); - if (lkc == NULL) { + if (lkc == nullptr) { goto error; } DBG3("Kernel create channel %s with attr: %d, %" PRIu64 ", %" PRIu64 ", %u, %u, %d, %d", - chan->name, lkc->channel->attr.overwrite, - lkc->channel->attr.subbuf_size, lkc->channel->attr.num_subbuf, - lkc->channel->attr.switch_timer_interval, lkc->channel->attr.read_timer_interval, - lkc->channel->attr.live_timer_interval, lkc->channel->attr.output); + chan->name, + lkc->channel->attr.overwrite, + lkc->channel->attr.subbuf_size, + lkc->channel->attr.num_subbuf, + lkc->channel->attr.switch_timer_interval, + lkc->channel->attr.read_timer_interval, + lkc->channel->attr.live_timer_interval, + lkc->channel->attr.output); /* Kernel tracer channel creation */ ret = kernctl_create_channel(session->fd, &lkc->channel->attr); @@ -221,7 +279,9 @@ int kernel_create_channel(struct ltt_kernel_session *session, lkc->key = ++next_kernel_channel_key; DBG("Kernel channel %s created (fd: %d, key: %" PRIu64 ")", - lkc->channel->name, lkc->fd, lkc->key); + lkc->channel->name, + lkc->fd, + lkc->key); return 0; @@ -258,7 +318,7 @@ static int kernel_create_event_notifier_group(int *event_notifier_group_fd) ret = fcntl(local_fd, F_SETFD, FD_CLOEXEC); if (ret < 0) { PERROR("Failed to set FD_CLOEXEC on kernel event notifier group file descriptor: fd = %d", - local_fd); + local_fd); goto error; } @@ -271,7 +331,7 @@ error: ret = close(local_fd); if (ret) { PERROR("Failed to close kernel event notifier group file descriptor: fd = %d", - local_fd); + local_fd); } } @@ -286,35 +346,33 @@ error: * elf symbol * Returns -1 on error */ -static -int extract_userspace_probe_offset_function_elf( - const struct lttng_userspace_probe_location *probe_location, - uid_t uid, gid_t gid, uint64_t *offset) +static int extract_userspace_probe_offset_function_elf( + const struct lttng_userspace_probe_location *probe_location, + uid_t uid, + gid_t gid, + uint64_t *offset) { int fd; int ret = 0; - const char *symbol = NULL; - const struct lttng_userspace_probe_location_lookup_method *lookup = NULL; + const char *symbol = nullptr; + const struct lttng_userspace_probe_location_lookup_method *lookup = nullptr; enum lttng_userspace_probe_location_lookup_method_type lookup_method_type; LTTNG_ASSERT(lttng_userspace_probe_location_get_type(probe_location) == - LTTNG_USERSPACE_PROBE_LOCATION_TYPE_FUNCTION); + LTTNG_USERSPACE_PROBE_LOCATION_TYPE_FUNCTION); - lookup = lttng_userspace_probe_location_get_lookup_method( - probe_location); + lookup = lttng_userspace_probe_location_get_lookup_method(probe_location); if (!lookup) { ret = -1; goto end; } - lookup_method_type = - lttng_userspace_probe_location_lookup_method_get_type(lookup); + lookup_method_type = lttng_userspace_probe_location_lookup_method_get_type(lookup); LTTNG_ASSERT(lookup_method_type == - LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_FUNCTION_ELF); + LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_FUNCTION_ELF); - symbol = lttng_userspace_probe_location_function_get_function_name( - probe_location); + symbol = lttng_userspace_probe_location_function_get_function_name(probe_location); if (!symbol) { ret = -1; goto end; @@ -329,11 +387,12 @@ int extract_userspace_probe_offset_function_elf( ret = run_as_extract_elf_symbol_offset(fd, symbol, uid, gid, offset); if (ret < 0) { DBG("userspace probe offset calculation failed for " - "function %s", symbol); + "function %s", + symbol); goto end; } - DBG("userspace probe elf offset for %s is 0x%jd", symbol, (intmax_t)(*offset)); + DBG("userspace probe elf offset for %s is 0x%jd", symbol, (intmax_t) (*offset)); end: return ret; } @@ -347,20 +406,21 @@ end: * SDT tracepoint. * Returns -1 on error. */ -static -int extract_userspace_probe_offset_tracepoint_sdt( - const struct lttng_userspace_probe_location *probe_location, - uid_t uid, gid_t gid, uint64_t **offsets, - uint32_t *offsets_count) +static int extract_userspace_probe_offset_tracepoint_sdt( + const struct lttng_userspace_probe_location *probe_location, + uid_t uid, + gid_t gid, + uint64_t **offsets, + uint32_t *offsets_count) { enum lttng_userspace_probe_location_lookup_method_type lookup_method_type; - const struct lttng_userspace_probe_location_lookup_method *lookup = NULL; - const char *probe_name = NULL, *provider_name = NULL; + const struct lttng_userspace_probe_location_lookup_method *lookup = nullptr; + const char *probe_name = nullptr, *provider_name = nullptr; int ret = 0; int fd, i; LTTNG_ASSERT(lttng_userspace_probe_location_get_type(probe_location) == - LTTNG_USERSPACE_PROBE_LOCATION_TYPE_TRACEPOINT); + LTTNG_USERSPACE_PROBE_LOCATION_TYPE_TRACEPOINT); lookup = lttng_userspace_probe_location_get_lookup_method(probe_location); if (!lookup) { @@ -368,22 +428,18 @@ int extract_userspace_probe_offset_tracepoint_sdt( goto end; } - lookup_method_type = - lttng_userspace_probe_location_lookup_method_get_type(lookup); + lookup_method_type = lttng_userspace_probe_location_lookup_method_get_type(lookup); LTTNG_ASSERT(lookup_method_type == - LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_TRACEPOINT_SDT); + LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_TRACEPOINT_SDT); - - probe_name = lttng_userspace_probe_location_tracepoint_get_probe_name( - probe_location); + probe_name = lttng_userspace_probe_location_tracepoint_get_probe_name(probe_location); if (!probe_name) { ret = -1; goto end; } - provider_name = lttng_userspace_probe_location_tracepoint_get_provider_name( - probe_location); + provider_name = lttng_userspace_probe_location_tracepoint_get_provider_name(probe_location); if (!provider_name) { ret = -1; goto end; @@ -395,11 +451,13 @@ int extract_userspace_probe_offset_tracepoint_sdt( goto end; } - ret = run_as_extract_sdt_probe_offsets(fd, provider_name, probe_name, - uid, gid, offsets, offsets_count); + ret = run_as_extract_sdt_probe_offsets( + fd, provider_name, probe_name, uid, gid, offsets, offsets_count); if (ret < 0) { DBG("userspace probe offset calculation failed for sdt " - "probe %s:%s", provider_name, probe_name); + "probe %s:%s", + provider_name, + probe_name); goto end; } @@ -409,20 +467,22 @@ int extract_userspace_probe_offset_tracepoint_sdt( } DBG("%u userspace probe SDT offsets found for %s:%s at:", - *offsets_count, provider_name, probe_name); + *offsets_count, + provider_name, + probe_name); for (i = 0; i < *offsets_count; i++) { - DBG("\t0x%jd", (intmax_t)((*offsets)[i])); + DBG("\t0x%jd", (intmax_t) ((*offsets)[i])); } end: return ret; } -static -int userspace_probe_add_callsite( - const struct lttng_userspace_probe_location *location, - uid_t uid, gid_t gid, int fd) +static int userspace_probe_add_callsite(const struct lttng_userspace_probe_location *location, + uid_t uid, + gid_t gid, + int fd) { - const struct lttng_userspace_probe_location_lookup_method *lookup_method = NULL; + const struct lttng_userspace_probe_location_lookup_method *lookup_method = nullptr; enum lttng_userspace_probe_location_lookup_method_type type; int ret; @@ -439,14 +499,13 @@ int userspace_probe_add_callsite( struct lttng_kernel_abi_event_callsite callsite; uint64_t offset; - ret = extract_userspace_probe_offset_function_elf(location, - uid, gid, &offset); + ret = extract_userspace_probe_offset_function_elf(location, uid, gid, &offset); if (ret) { ret = LTTNG_ERR_PROBE_LOCATION_INVAL; goto end; } - callsite.u.uprobe.offset = offset; + callsite.u.uprobe.offset = sanitize_uprobe_offset(offset); ret = kernctl_add_callsite(fd, &callsite); if (ret) { WARN("Failed to add callsite to ELF userspace probe."); @@ -458,7 +517,7 @@ int userspace_probe_add_callsite( case LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_TRACEPOINT_SDT: { int i; - uint64_t *offsets = NULL; + uint64_t *offsets = nullptr; uint32_t offsets_count; struct lttng_kernel_abi_event_callsite callsite; @@ -466,14 +525,14 @@ int userspace_probe_add_callsite( * This call allocates the offsets buffer. This buffer must be freed * by the caller */ - ret = extract_userspace_probe_offset_tracepoint_sdt(location, - uid, gid, &offsets, &offsets_count); + ret = extract_userspace_probe_offset_tracepoint_sdt( + location, uid, gid, &offsets, &offsets_count); if (ret) { ret = LTTNG_ERR_PROBE_LOCATION_INVAL; goto end; } for (i = 0; i < offsets_count; i++) { - callsite.u.uprobe.offset = offsets[i]; + callsite.u.uprobe.offset = sanitize_uprobe_offset(offsets[i]); ret = kernctl_add_callsite(fd, &callsite); if (ret) { WARN("Failed to add callsite to SDT userspace probe"); @@ -497,12 +556,12 @@ end: * Extract the offsets of the instrumentation point for the different lookup * methods. */ -static -int userspace_probe_event_add_callsites(struct lttng_event *ev, - struct ltt_kernel_session *session, int fd) +static int userspace_probe_event_add_callsites(struct lttng_event *ev, + struct ltt_kernel_session *session, + int fd) { int ret; - const struct lttng_userspace_probe_location *location = NULL; + const struct lttng_userspace_probe_location *location = nullptr; LTTNG_ASSERT(ev); LTTNG_ASSERT(ev->type == LTTNG_EVENT_USERSPACE_PROBE); @@ -513,11 +572,9 @@ int userspace_probe_event_add_callsites(struct lttng_event *ev, goto end; } - ret = userspace_probe_add_callsite(location, session->uid, session->gid, - fd); + ret = userspace_probe_add_callsite(location, session->uid, session->gid, fd); if (ret) { - WARN("Failed to add callsite to userspace probe event '%s'", - ev->name); + WARN("Failed to add callsite to userspace probe event '%s'", ev->name); } end: @@ -528,15 +585,14 @@ end: * Extract the offsets of the instrumentation point for the different look-up * methods. */ -static int userspace_probe_event_rule_add_callsites( - const struct lttng_event_rule *rule, - const struct lttng_credentials *creds, - int fd) +static int userspace_probe_event_rule_add_callsites(const struct lttng_event_rule *rule, + const struct lttng_credentials *creds, + int fd) { int ret; enum lttng_event_rule_status status; enum lttng_event_rule_type event_rule_type; - const struct lttng_userspace_probe_location *location = NULL; + const struct lttng_userspace_probe_location *location = nullptr; LTTNG_ASSERT(rule); LTTNG_ASSERT(creds); @@ -550,12 +606,10 @@ static int userspace_probe_event_rule_add_callsites( goto end; } - ret = userspace_probe_add_callsite(location, - lttng_credentials_get_uid(creds), - lttng_credentials_get_gid(creds), fd); + ret = userspace_probe_add_callsite( + location, lttng_credentials_get_uid(creds), lttng_credentials_get_gid(creds), fd); if (ret) { - WARN("Failed to add callsite to user space probe object: fd = %d", - fd); + WARN("Failed to add callsite to user space probe object: fd = %d", fd); } end: @@ -568,9 +622,9 @@ end: * We own filter_expression and filter. */ int kernel_create_event(struct lttng_event *ev, - struct ltt_kernel_channel *channel, - char *filter_expression, - struct lttng_bytecode *filter) + struct ltt_kernel_channel *channel, + char *filter_expression, + struct lttng_bytecode *filter) { int err, fd; enum lttng_error_code ret; @@ -580,8 +634,7 @@ int kernel_create_event(struct lttng_event *ev, LTTNG_ASSERT(channel); /* We pass ownership of filter_expression and filter */ - ret = trace_kernel_create_event(ev, filter_expression, - filter, &event); + ret = trace_kernel_create_event(ev, filter_expression, filter, &event); if (ret != LTTNG_OK) { goto error; } @@ -631,8 +684,8 @@ int kernel_create_event(struct lttng_event *ev, } if (ev->type == LTTNG_EVENT_USERSPACE_PROBE) { - ret = (lttng_error_code) userspace_probe_event_add_callsites(ev, channel->session, - event->fd); + ret = (lttng_error_code) userspace_probe_event_add_callsites( + ev, channel->session, event->fd); if (ret) { goto add_callsite_error; } @@ -663,14 +716,14 @@ int kernel_create_event(struct lttng_event *ev, add_callsite_error: enable_error: filter_error: - { - int closeret; +{ + int closeret; - closeret = close(event->fd); - if (closeret) { - PERROR("close event fd"); - } + closeret = close(event->fd); + if (closeret) { + PERROR("close event fd"); } +} free_event: free(event); error: @@ -692,9 +745,11 @@ int kernel_disable_channel(struct ltt_kernel_channel *chan) goto error; } - chan->enabled = 0; + chan->enabled = false; DBG("Kernel channel %s disabled (fd: %d, key: %" PRIu64 ")", - chan->channel->name, chan->fd, chan->key); + chan->channel->name, + chan->fd, + chan->key); return 0; @@ -717,9 +772,11 @@ int kernel_enable_channel(struct ltt_kernel_channel *chan) goto error; } - chan->enabled = 1; + chan->enabled = true; DBG("Kernel channel %s enabled (fd: %d, key: %" PRIu64 ")", - chan->channel->name, chan->fd, chan->key); + chan->channel->name, + chan->fd, + chan->key); return 0; @@ -749,7 +806,7 @@ int kernel_enable_event(struct ltt_kernel_event *event) goto error; } - event->enabled = 1; + event->enabled = true; DBG("Kernel event %s enabled (fd: %d)", event->event->name, event->fd); return 0; @@ -770,11 +827,12 @@ int kernel_disable_event(struct ltt_kernel_event *event) ret = kernctl_disable(event->fd); if (ret < 0) { PERROR("Failed to disable kernel event: name = '%s', fd = %d", - event->event->name, event->fd); + event->event->name, + event->fd); goto error; } - event->enabled = 0; + event->enabled = false; DBG("Kernel event %s disabled (fd: %d)", event->event->name, event->fd); return 0; @@ -786,36 +844,33 @@ error: /* * Disable a kernel event notifier. */ -static -int kernel_disable_event_notifier_rule(struct ltt_kernel_event_notifier_rule *event) +static int kernel_disable_event_notifier_rule(struct ltt_kernel_event_notifier_rule *event) { int ret; LTTNG_ASSERT(event); - rcu_read_lock(); + lttng::urcu::read_lock_guard read_lock; cds_lfht_del(kernel_token_to_event_notifier_rule_ht, &event->ht_node); - rcu_read_unlock(); ret = kernctl_disable(event->fd); if (ret < 0) { PERROR("Failed to disable kernel event notifier: fd = %d, token = %" PRIu64, - event->fd, event->token); + event->fd, + event->token); goto error; } - event->enabled = 0; - DBG("Disabled kernel event notifier: fd = %d, token = %" PRIu64, - event->fd, event->token); + event->enabled = false; + DBG("Disabled kernel event notifier: fd = %d, token = %" PRIu64, event->fd, event->token); error: return ret; } -static -struct process_attr_tracker *_kernel_get_process_attr_tracker( - struct ltt_kernel_session *session, - enum lttng_process_attr process_attr) +static struct process_attr_tracker * +_kernel_get_process_attr_tracker(struct ltt_kernel_session *session, + enum lttng_process_attr process_attr) { switch (process_attr) { case LTTNG_PROCESS_ATTR_PROCESS_ID: @@ -831,27 +886,27 @@ struct process_attr_tracker *_kernel_get_process_attr_tracker( case LTTNG_PROCESS_ATTR_VIRTUAL_GROUP_ID: return session->tracker_vgid; default: - return NULL; + return nullptr; } } -const struct process_attr_tracker *kernel_get_process_attr_tracker( - struct ltt_kernel_session *session, - enum lttng_process_attr process_attr) +const struct process_attr_tracker * +kernel_get_process_attr_tracker(struct ltt_kernel_session *session, + enum lttng_process_attr process_attr) { - return (const struct process_attr_tracker *) - _kernel_get_process_attr_tracker(session, process_attr); + return (const struct process_attr_tracker *) _kernel_get_process_attr_tracker(session, + process_attr); } -enum lttng_error_code kernel_process_attr_tracker_set_tracking_policy( - struct ltt_kernel_session *session, - enum lttng_process_attr process_attr, - enum lttng_tracking_policy policy) +enum lttng_error_code +kernel_process_attr_tracker_set_tracking_policy(struct ltt_kernel_session *session, + enum lttng_process_attr process_attr, + enum lttng_tracking_policy policy) { int ret; enum lttng_error_code ret_code = LTTNG_OK; struct process_attr_tracker *tracker = - _kernel_get_process_attr_tracker(session, process_attr); + _kernel_get_process_attr_tracker(session, process_attr); enum lttng_tracking_policy previous_policy; if (!tracker) { @@ -922,10 +977,10 @@ end: return ret_code; } -enum lttng_error_code kernel_process_attr_tracker_inclusion_set_add_value( - struct ltt_kernel_session *session, - enum lttng_process_attr process_attr, - const struct process_attr_value *value) +enum lttng_error_code +kernel_process_attr_tracker_inclusion_set_add_value(struct ltt_kernel_session *session, + enum lttng_process_attr process_attr, + const struct process_attr_value *value) { int ret, integral_value; enum lttng_error_code ret_code; @@ -946,8 +1001,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_add_value( if (value->type == LTTNG_PROCESS_ATTR_VALUE_TYPE_USER_NAME) { uid_t uid; - ret_code = utils_user_id_from_name( - value->value.user_name, &uid); + ret_code = utils_user_id_from_name(value->value.user_name, &uid); if (ret_code != LTTNG_OK) { goto end; } @@ -961,8 +1015,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_add_value( if (value->type == LTTNG_PROCESS_ATTR_VALUE_TYPE_GROUP_NAME) { gid_t gid; - ret_code = utils_group_id_from_name( - value->value.group_name, &gid); + ret_code = utils_group_id_from_name(value->value.group_name, &gid); if (ret_code != LTTNG_OK) { goto end; } @@ -1000,8 +1053,9 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_add_value( } DBG("Kernel track %s %d for session id %" PRIu64, - lttng_process_attr_to_string(process_attr), - integral_value, session->id); + lttng_process_attr_to_string(process_attr), + integral_value, + session->id); if (process_attr == LTTNG_PROCESS_ATTR_PROCESS_ID) { /* * Maintain a special case for the process ID process attribute @@ -1009,8 +1063,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_add_value( */ ret = kernctl_track_pid(session->fd, integral_value); } else { - ret = kernctl_track_id( - session->fd, process_attr, integral_value); + ret = kernctl_track_id(session->fd, process_attr, integral_value); } if (ret == 0) { ret_code = LTTNG_OK; @@ -1039,21 +1092,20 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_add_value( } /* Attempt to remove the value from the tracker. */ - status = process_attr_tracker_inclusion_set_remove_value( - tracker, value); + status = process_attr_tracker_inclusion_set_remove_value(tracker, value); if (status != PROCESS_ATTR_TRACKER_STATUS_OK) { ERR("Failed to roll-back the tracking of kernel %s process attribute %d while handling a kern-ctl error", - lttng_process_attr_to_string(process_attr), - integral_value); + lttng_process_attr_to_string(process_attr), + integral_value); } end: return ret_code; } -enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( - struct ltt_kernel_session *session, - enum lttng_process_attr process_attr, - const struct process_attr_value *value) +enum lttng_error_code +kernel_process_attr_tracker_inclusion_set_remove_value(struct ltt_kernel_session *session, + enum lttng_process_attr process_attr, + const struct process_attr_value *value) { int ret, integral_value; enum lttng_error_code ret_code; @@ -1074,8 +1126,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( if (value->type == LTTNG_PROCESS_ATTR_VALUE_TYPE_USER_NAME) { uid_t uid; - ret_code = utils_user_id_from_name( - value->value.user_name, &uid); + ret_code = utils_user_id_from_name(value->value.user_name, &uid); if (ret_code != LTTNG_OK) { goto end; } @@ -1089,8 +1140,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( if (value->type == LTTNG_PROCESS_ATTR_VALUE_TYPE_GROUP_NAME) { gid_t gid; - ret_code = utils_group_id_from_name( - value->value.group_name, &gid); + ret_code = utils_group_id_from_name(value->value.group_name, &gid); if (ret_code != LTTNG_OK) { goto end; } @@ -1110,8 +1160,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( goto end; } - status = process_attr_tracker_inclusion_set_remove_value( - tracker, value); + status = process_attr_tracker_inclusion_set_remove_value(tracker, value); if (status != PROCESS_ATTR_TRACKER_STATUS_OK) { switch (status) { case PROCESS_ATTR_TRACKER_STATUS_MISSING: @@ -1129,8 +1178,9 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( } DBG("Kernel track %s %d for session id %" PRIu64, - lttng_process_attr_to_string(process_attr), - integral_value, session->id); + lttng_process_attr_to_string(process_attr), + integral_value, + session->id); if (process_attr == LTTNG_PROCESS_ATTR_PROCESS_ID) { /* * Maintain a special case for the process ID process attribute @@ -1138,8 +1188,7 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( */ ret = kernctl_untrack_pid(session->fd, integral_value); } else { - ret = kernctl_untrack_id( - session->fd, process_attr, integral_value); + ret = kernctl_untrack_id(session->fd, process_attr, integral_value); } if (ret == 0) { ret_code = LTTNG_OK; @@ -1167,12 +1216,11 @@ enum lttng_error_code kernel_process_attr_tracker_inclusion_set_remove_value( } /* Attempt to add the value to the tracker. */ - status = process_attr_tracker_inclusion_set_add_value( - tracker, value); + status = process_attr_tracker_inclusion_set_add_value(tracker, value); if (status != PROCESS_ATTR_TRACKER_STATUS_OK) { ERR("Failed to roll-back the tracking of kernel %s process attribute %d while handling a kern-ctl error", - lttng_process_attr_to_string(process_attr), - integral_value); + lttng_process_attr_to_string(process_attr), + integral_value); } end: return ret_code; @@ -1185,13 +1233,13 @@ end: int kernel_open_metadata(struct ltt_kernel_session *session) { int ret; - struct ltt_kernel_metadata *lkm = NULL; + struct ltt_kernel_metadata *lkm = nullptr; LTTNG_ASSERT(session); /* Allocate kernel metadata */ lkm = trace_kernel_create_metadata(); - if (lkm == NULL) { + if (lkm == nullptr) { goto error; } @@ -1247,7 +1295,7 @@ error: /* * Make a kernel wait to make sure in-flight probe have completed. */ -void kernel_wait_quiescent(void) +void kernel_wait_quiescent() { int ret; int fd = kernel_tracer_fd; @@ -1290,13 +1338,12 @@ int kernel_flush_buffer(struct ltt_kernel_channel *channel) DBG("Flush buffer for channel %s", channel->channel->name); - cds_list_for_each_entry(stream, &channel->stream_list.head, list) { + cds_list_for_each_entry (stream, &channel->stream_list.head, list) { DBG("Flushing channel stream %d", stream->fd); ret = kernctl_buffer_flush(stream->fd); if (ret < 0) { PERROR("ioctl"); - ERR("Fail to flush buffer for stream %d (ret: %d)", - stream->fd, ret); + ERR("Fail to flush buffer for stream %d (ret: %d)", stream->fd, ret); } } @@ -1343,9 +1390,8 @@ int kernel_open_channel_stream(struct ltt_kernel_channel *channel) LTTNG_ASSERT(channel); while ((ret = kernctl_create_stream(channel->fd)) >= 0) { - lks = trace_kernel_create_stream(channel->channel->name, - channel->stream_count); - if (lks == NULL) { + lks = trace_kernel_create_stream(channel->channel->name, channel->stream_count); + if (lks == nullptr) { ret = close(ret); if (ret) { PERROR("close"); @@ -1367,8 +1413,7 @@ int kernel_open_channel_stream(struct ltt_kernel_channel *channel) cds_list_add(&lks->list, &channel->stream_list.head); channel->stream_count++; - DBG("Kernel stream %s created (fd: %d, state: %d)", lks->name, lks->fd, - lks->state); + DBG("Kernel stream %s created (fd: %d, state: %d)", lks->name, lks->fd, lks->state); } return channel->stream_count; @@ -1426,7 +1471,7 @@ ssize_t kernel_list_events(struct lttng_event **events) } fp = fdopen(fd, "r"); - if (fp == NULL) { + if (fp == nullptr) { PERROR("kernel tracepoint list fdopen"); goto error_fp; } @@ -1436,8 +1481,8 @@ ssize_t kernel_list_events(struct lttng_event **events) * See kernel-ctl.h for explanation of this value */ nbmem = KERNEL_EVENT_INIT_LIST_SIZE; - elist = (lttng_event *) zmalloc(sizeof(struct lttng_event) * nbmem); - if (elist == NULL) { + elist = calloc(nbmem); + if (elist == nullptr) { PERROR("alloc list events"); count = -ENOMEM; goto end; @@ -1449,10 +1494,10 @@ ssize_t kernel_list_events(struct lttng_event **events) size_t new_nbmem; new_nbmem = nbmem << 1; - DBG("Reallocating event list from %zu to %zu bytes", - nbmem, new_nbmem); - new_elist = (lttng_event *) realloc(elist, new_nbmem * sizeof(struct lttng_event)); - if (new_elist == NULL) { + DBG("Reallocating event list from %zu to %zu bytes", nbmem, new_nbmem); + new_elist = (lttng_event *) realloc(elist, + new_nbmem * sizeof(struct lttng_event)); + if (new_elist == nullptr) { PERROR("realloc list events"); free(event); free(elist); @@ -1460,8 +1505,9 @@ ssize_t kernel_list_events(struct lttng_event **events) goto end; } /* Zero the new memory */ - memset(new_elist + nbmem, 0, - (new_nbmem - nbmem) * sizeof(struct lttng_event)); + memset(new_elist + nbmem, + 0, + (new_nbmem - nbmem) * sizeof(struct lttng_event)); nbmem = new_nbmem; elist = new_elist; } @@ -1475,7 +1521,7 @@ ssize_t kernel_list_events(struct lttng_event **events) *events = elist; DBG("Kernel list events done (%zu events)", count); end: - ret = fclose(fp); /* closes both fp and fd */ + ret = fclose(fp); /* closes both fp and fd */ if (ret) { PERROR("fclose"); } @@ -1494,7 +1540,7 @@ error: * Get kernel version and validate it. */ int kernel_validate_version(struct lttng_kernel_abi_tracer_version *version, - struct lttng_kernel_abi_tracer_abi_version *abi_version) + struct lttng_kernel_abi_tracer_abi_version *abi_version) { int ret; @@ -1507,7 +1553,8 @@ int kernel_validate_version(struct lttng_kernel_abi_tracer_version *version, /* Validate version */ if (version->major != VERSION_MAJOR) { ERR("Kernel tracer major version (%d) is not compatible with lttng-tools major version (%d)", - version->major, VERSION_MAJOR); + version->major, + VERSION_MAJOR); goto error_version; } ret = kernctl_tracer_abi_version(kernel_tracer_fd, abi_version); @@ -1517,13 +1564,16 @@ int kernel_validate_version(struct lttng_kernel_abi_tracer_version *version, } if (abi_version->major != LTTNG_KERNEL_ABI_MAJOR_VERSION) { ERR("Kernel tracer ABI version (%d.%d) does not match the expected ABI major version (%d.*)", - abi_version->major, abi_version->minor, - LTTNG_KERNEL_ABI_MAJOR_VERSION); + abi_version->major, + abi_version->minor, + LTTNG_KERNEL_ABI_MAJOR_VERSION); goto error; } DBG2("Kernel tracer version validated (%d.%d, ABI %d.%d)", - version->major, version->minor, - abi_version->major, abi_version->minor); + version->major, + version->minor, + abi_version->major, + abi_version->minor); return 0; error_version: @@ -1537,7 +1587,7 @@ error: /* * Kernel work-arounds called at the start of sessiond main(). */ -int init_kernel_workarounds(void) +int init_kernel_workarounds() { int ret; FILE *fp; @@ -1574,7 +1624,7 @@ void kernel_destroy_session(struct ltt_kernel_session *ksess) { struct lttng_trace_chunk *trace_chunk; - if (ksess == NULL) { + if (ksess == nullptr) { DBG3("No kernel session when tearing down session"); return; } @@ -1593,13 +1643,14 @@ void kernel_destroy_session(struct ltt_kernel_session *ksess) struct lttng_ht_iter iter; /* For each consumer socket. */ - rcu_read_lock(); - cds_lfht_for_each_entry(ksess->consumer->socks->ht, &iter.iter, - socket, node.node) { + lttng::urcu::read_lock_guard read_lock; + + cds_lfht_for_each_entry ( + ksess->consumer->socks->ht, &iter.iter, socket, node.node) { struct ltt_kernel_channel *chan; /* For each channel, ask the consumer to destroy it. */ - cds_list_for_each_entry(chan, &ksess->channel_list.head, list) { + cds_list_for_each_entry (chan, &ksess->channel_list.head, list) { ret = kernel_consumer_destroy_channel(socket, chan); if (ret < 0) { /* Consumer is probably dead. Use next socket. */ @@ -1607,7 +1658,6 @@ void kernel_destroy_session(struct ltt_kernel_session *ksess) } } } - rcu_read_unlock(); } /* Close any relayd session */ @@ -1620,7 +1670,7 @@ void kernel_destroy_session(struct ltt_kernel_session *ksess) /* Teardown of data required by destroy notifiers. */ void kernel_free_session(struct ltt_kernel_session *ksess) { - if (ksess == NULL) { + if (ksess == nullptr) { return; } trace_kernel_free_session(ksess); @@ -1631,7 +1681,7 @@ void kernel_free_session(struct ltt_kernel_session *ksess) */ void kernel_destroy_channel(struct ltt_kernel_channel *kchan) { - struct ltt_kernel_session *ksess = NULL; + struct ltt_kernel_session *ksess = nullptr; LTTNG_ASSERT(kchan); LTTNG_ASSERT(kchan->channel); @@ -1661,17 +1711,16 @@ void kernel_destroy_channel(struct ltt_kernel_channel *kchan) * * Return LTTNG_OK on success or else return a LTTNG_ERR code. */ -enum lttng_error_code kernel_snapshot_record( - struct ltt_kernel_session *ksess, - const struct consumer_output *output, int wait, - uint64_t nb_packets_per_stream) +enum lttng_error_code kernel_snapshot_record(struct ltt_kernel_session *ksess, + const struct consumer_output *output, + uint64_t nb_packets_per_stream) { int err, ret, saved_metadata_fd; enum lttng_error_code status = LTTNG_OK; struct consumer_socket *socket; struct lttng_ht_iter iter; struct ltt_kernel_metadata *saved_metadata; - char *trace_path = NULL; + char *trace_path = nullptr; size_t consumer_path_offset = 0; LTTNG_ASSERT(ksess); @@ -1684,8 +1733,6 @@ enum lttng_error_code kernel_snapshot_record( saved_metadata = ksess->metadata; saved_metadata_fd = ksess->metadata_stream_fd; - rcu_read_lock(); - ret = kernel_open_metadata(ksess); if (ret < 0) { status = LTTNG_ERR_KERN_META_FAIL; @@ -1698,52 +1745,61 @@ enum lttng_error_code kernel_snapshot_record( goto error_open_stream; } - trace_path = setup_channel_trace_path(ksess->consumer, - "", &consumer_path_offset); + trace_path = setup_channel_trace_path(ksess->consumer, "", &consumer_path_offset); if (!trace_path) { status = LTTNG_ERR_INVALID; goto error; } - /* Send metadata to consumer and snapshot everything. */ - cds_lfht_for_each_entry(output->socks->ht, &iter.iter, - socket, node.node) { - struct ltt_kernel_channel *chan; - pthread_mutex_lock(socket->lock); - /* This stream must not be monitored by the consumer. */ - ret = kernel_consumer_add_metadata(socket, ksess, 0); - pthread_mutex_unlock(socket->lock); - if (ret < 0) { - status = LTTNG_ERR_KERN_META_FAIL; - goto error_consumer; - } + { + /* Send metadata to consumer and snapshot everything. */ + lttng::urcu::read_lock_guard read_lock; + + cds_lfht_for_each_entry (output->socks->ht, &iter.iter, socket, node.node) { + struct ltt_kernel_channel *chan; + + pthread_mutex_lock(socket->lock); + /* This stream must not be monitored by the consumer. */ + ret = kernel_consumer_add_metadata(socket, ksess, 0); + pthread_mutex_unlock(socket->lock); + if (ret < 0) { + status = LTTNG_ERR_KERN_META_FAIL; + goto error_consumer; + } + + /* For each channel, ask the consumer to snapshot it. */ + cds_list_for_each_entry (chan, &ksess->channel_list.head, list) { + status = + consumer_snapshot_channel(socket, + chan->key, + output, + 0, + &trace_path[consumer_path_offset], + nb_packets_per_stream); + if (status != LTTNG_OK) { + (void) kernel_consumer_destroy_metadata(socket, + ksess->metadata); + goto error_consumer; + } + } - /* For each channel, ask the consumer to snapshot it. */ - cds_list_for_each_entry(chan, &ksess->channel_list.head, list) { - status = consumer_snapshot_channel(socket, chan->key, output, 0, - ksess->uid, ksess->gid, - &trace_path[consumer_path_offset], wait, - nb_packets_per_stream); + /* Snapshot metadata, */ + status = consumer_snapshot_channel(socket, + ksess->metadata->key, + output, + 1, + &trace_path[consumer_path_offset], + 0); if (status != LTTNG_OK) { - (void) kernel_consumer_destroy_metadata(socket, - ksess->metadata); goto error_consumer; } - } - /* Snapshot metadata, */ - status = consumer_snapshot_channel(socket, ksess->metadata->key, output, - 1, ksess->uid, ksess->gid, &trace_path[consumer_path_offset], - wait, 0); - if (status != LTTNG_OK) { - goto error_consumer; + /* + * The metadata snapshot is done, ask the consumer to destroy it since + * it's not monitored on the consumer side. + */ + (void) kernel_consumer_destroy_metadata(socket, ksess->metadata); } - - /* - * The metadata snapshot is done, ask the consumer to destroy it since - * it's not monitored on the consumer side. - */ - (void) kernel_consumer_destroy_metadata(socket, ksess->metadata); } error_consumer: @@ -1759,7 +1815,6 @@ error: /* Restore metadata state.*/ ksess->metadata = saved_metadata; ksess->metadata_stream_fd = saved_metadata_fd; - rcu_read_unlock(); free(trace_path); return status; } @@ -1778,8 +1833,7 @@ int kernel_syscall_mask(int chan_fd, char **syscall_mask, uint32_t *nr_bits) return kernctl_syscall_mask(chan_fd, syscall_mask, nr_bits); } -static -int kernel_tracer_abi_greater_or_equal(unsigned int major, unsigned int minor) +static int kernel_tracer_abi_greater_or_equal(unsigned int major, unsigned int minor) { int ret; struct lttng_kernel_abi_tracer_abi_version abi; @@ -1802,7 +1856,7 @@ error: * Return 1 on success, 0 when feature is not supported, negative value in case * of errors. */ -int kernel_supports_ring_buffer_snapshot_sample_positions(void) +int kernel_supports_ring_buffer_snapshot_sample_positions() { /* * RING_BUFFER_SNAPSHOT_SAMPLE_POSITIONS was introduced in 2.3 @@ -1816,7 +1870,7 @@ int kernel_supports_ring_buffer_snapshot_sample_positions(void) * Return 1 on success, 0 when feature is not supported, negative value in case * of errors. */ -int kernel_supports_ring_buffer_packet_sequence_number(void) +int kernel_supports_ring_buffer_packet_sequence_number() { /* * Packet sequence number was introduced in LTTng 2.8, @@ -1831,7 +1885,7 @@ int kernel_supports_ring_buffer_packet_sequence_number(void) * Return 1 on success, 0 when feature is not supported, negative value in case * of errors. */ -int kernel_supports_event_notifiers(void) +int kernel_supports_event_notifiers() { /* * Event notifiers were introduced in LTTng 2.13, lttng-modules ABI 2.6. @@ -1855,56 +1909,58 @@ enum lttng_error_code kernel_rotate_session(struct ltt_session *session) LTTNG_ASSERT(ksess); LTTNG_ASSERT(ksess->consumer); - DBG("Rotate kernel session %s started (session %" PRIu64 ")", - session->name, session->id); + DBG("Rotate kernel session %s started (session %" PRIu64 ")", session->name, session->id); - rcu_read_lock(); + { + /* + * Note that this loop will end after one iteration given that there is + * only one kernel consumer. + */ + lttng::urcu::read_lock_guard read_lock; - /* - * Note that this loop will end after one iteration given that there is - * only one kernel consumer. - */ - cds_lfht_for_each_entry(ksess->consumer->socks->ht, &iter.iter, - socket, node.node) { - struct ltt_kernel_channel *chan; - - /* For each channel, ask the consumer to rotate it. */ - cds_list_for_each_entry(chan, &ksess->channel_list.head, list) { - DBG("Rotate kernel channel %" PRIu64 ", session %s", - chan->key, session->name); - ret = consumer_rotate_channel(socket, chan->key, - ksess->uid, ksess->gid, ksess->consumer, - /* is_metadata_channel */ false); + cds_lfht_for_each_entry ( + ksess->consumer->socks->ht, &iter.iter, socket, node.node) { + struct ltt_kernel_channel *chan; + + /* For each channel, ask the consumer to rotate it. */ + cds_list_for_each_entry (chan, &ksess->channel_list.head, list) { + DBG("Rotate kernel channel %" PRIu64 ", session %s", + chan->key, + session->name); + ret = consumer_rotate_channel(socket, + chan->key, + ksess->consumer, + /* is_metadata_channel */ false); + if (ret < 0) { + status = LTTNG_ERR_ROTATION_FAIL_CONSUMER; + goto error; + } + } + + /* + * Rotate the metadata channel. + */ + ret = consumer_rotate_channel(socket, + ksess->metadata->key, + ksess->consumer, + /* is_metadata_channel */ true); if (ret < 0) { status = LTTNG_ERR_ROTATION_FAIL_CONSUMER; goto error; } } - - /* - * Rotate the metadata channel. - */ - ret = consumer_rotate_channel(socket, ksess->metadata->key, - ksess->uid, ksess->gid, ksess->consumer, - /* is_metadata_channel */ true); - if (ret < 0) { - status = LTTNG_ERR_ROTATION_FAIL_CONSUMER; - goto error; - } } error: - rcu_read_unlock(); return status; } -enum lttng_error_code kernel_create_channel_subdirectories( - const struct ltt_kernel_session *ksess) +enum lttng_error_code kernel_create_channel_subdirectories(const struct ltt_kernel_session *ksess) { enum lttng_error_code ret = LTTNG_OK; enum lttng_trace_chunk_status chunk_status; - rcu_read_lock(); + lttng::urcu::read_lock_guard read_lock; LTTNG_ASSERT(ksess->current_trace_chunk); /* @@ -1912,28 +1968,74 @@ enum lttng_error_code kernel_create_channel_subdirectories( * of implicitly creating the channel's path. */ chunk_status = lttng_trace_chunk_create_subdirectory( - ksess->current_trace_chunk, - DEFAULT_KERNEL_TRACE_DIR "/" DEFAULT_INDEX_DIR); + ksess->current_trace_chunk, DEFAULT_KERNEL_TRACE_DIR "/" DEFAULT_INDEX_DIR); if (chunk_status != LTTNG_TRACE_CHUNK_STATUS_OK) { ret = LTTNG_ERR_CREATE_DIR_FAIL; goto error; } error: - rcu_read_unlock(); return ret; } +/* + * Get current kernel tracer status + */ +enum lttng_kernel_tracer_status get_kernel_tracer_status() +{ + if (!kernel_tracer_status) { + return LTTNG_KERNEL_TRACER_STATUS_ERR_UNKNOWN; + } + + return *kernel_tracer_status; +} + +/* + * Sets the kernel tracer status based on the positive errno code + */ +void set_kernel_tracer_status_from_modules_ret(int code) +{ + switch (code) { + case ENOENT: + { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_MISSING); + break; + } + case ENOKEY: + case EKEYEXPIRED: + case EKEYREVOKED: + case EKEYREJECTED: + { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_SIGNATURE); + break; + } + default: + { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_MODULES_UNKNOWN); + break; + } + } +} + /* * Setup necessary data for kernel tracer action. */ -int init_kernel_tracer(void) +int init_kernel_tracer() { int ret; bool is_root = !getuid(); + const auto log_status_on_exit = lttng::make_scope_exit([]() noexcept { + DBG_FMT("Kernel tracer status set to `{}`", + kernel_tracer_status_to_str(*kernel_tracer_status)); + }); + /* Modprobe lttng kernel modules */ ret = modprobe_lttng_control(); if (ret < 0) { + set_kernel_tracer_status_from_modules_ret(-ret); goto error; } @@ -1941,18 +2043,22 @@ int init_kernel_tracer(void) kernel_tracer_fd = open(module_proc_lttng, O_RDWR); if (kernel_tracer_fd < 0) { DBG("Failed to open %s", module_proc_lttng); + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_OPEN_PROC_LTTNG); goto error_open; } /* Validate kernel version */ - ret = kernel_validate_version(&the_kernel_tracer_version, - &the_kernel_tracer_abi_version); + ret = kernel_validate_version(&the_kernel_tracer_version, &the_kernel_tracer_abi_version); if (ret < 0) { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_VERSION_MISMATCH); goto error_version; } ret = modprobe_lttng_data(); if (ret < 0) { + set_kernel_tracer_status_from_modules_ret(-ret); goto error_modules; } @@ -1962,13 +2068,15 @@ int init_kernel_tracer(void) } if (ret < 1) { WARN("Kernel tracer does not support buffer monitoring. " - "The monitoring timer of channels in the kernel domain " - "will be set to 0 (disabled)."); + "The monitoring timer of channels in the kernel domain " + "will be set to 0 (disabled)."); } ret = kernel_supports_event_notifiers(); if (ret < 0) { ERR("Failed to check for kernel tracer event notifier support"); + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_NOTIFIER); goto error_modules; } ret = kernel_create_event_notifier_group(&kernel_tracer_event_notifier_group_fd); @@ -1979,59 +2087,64 @@ int init_kernel_tracer(void) } else { enum event_notifier_error_accounting_status error_accounting_status; enum lttng_error_code error_code_ret = - kernel_create_event_notifier_group_notification_fd( - &kernel_tracer_event_notifier_group_notification_fd); + kernel_create_event_notifier_group_notification_fd( + &kernel_tracer_event_notifier_group_notification_fd); if (error_code_ret != LTTNG_OK) { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_NOTIFIER); goto error_modules; } error_accounting_status = event_notifier_error_accounting_register_kernel( - kernel_tracer_event_notifier_group_fd); + kernel_tracer_event_notifier_group_fd); if (error_accounting_status != EVENT_NOTIFIER_ERROR_ACCOUNTING_STATUS_OK) { ERR("Failed to initialize event notifier error accounting for kernel tracer"); error_code_ret = LTTNG_ERR_EVENT_NOTIFIER_ERROR_ACCOUNTING; + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_NOTIFIER); goto error_modules; } kernel_token_to_event_notifier_rule_ht = cds_lfht_new( - DEFAULT_HT_SIZE, 1, 0, - CDS_LFHT_AUTO_RESIZE | CDS_LFHT_ACCOUNTING, - NULL); + DEFAULT_HT_SIZE, 1, 0, CDS_LFHT_AUTO_RESIZE | CDS_LFHT_ACCOUNTING, nullptr); if (!kernel_token_to_event_notifier_rule_ht) { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_NOTIFIER); goto error_token_ht; } } DBG("Kernel tracer initialized: kernel tracer fd = %d, event notifier group fd = %d, event notifier group notification fd = %d", - kernel_tracer_fd, kernel_tracer_event_notifier_group_fd, - kernel_tracer_event_notifier_group_notification_fd); + kernel_tracer_fd, + kernel_tracer_event_notifier_group_fd, + kernel_tracer_event_notifier_group_notification_fd); ret = syscall_init_table(kernel_tracer_fd); if (ret < 0) { ERR("Unable to populate syscall table. Syscall tracing won't " - "work for this session daemon."); + "work for this session daemon."); } + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_INITIALIZED); return 0; error_version: modprobe_remove_lttng_control(); ret = close(kernel_tracer_fd); if (ret) { - PERROR("Failed to close kernel tracer file descriptor: fd = %d", - kernel_tracer_fd); + PERROR("Failed to close kernel tracer file descriptor: fd = %d", kernel_tracer_fd); } kernel_tracer_fd = -1; return LTTNG_ERR_KERN_VERSION; - error_token_ht: ret = close(kernel_tracer_event_notifier_group_notification_fd); if (ret) { PERROR("Failed to close kernel tracer event notifier group notification file descriptor: fd = %d", - kernel_tracer_event_notifier_group_notification_fd); + kernel_tracer_event_notifier_group_notification_fd); } kernel_tracer_event_notifier_group_notification_fd = -1; @@ -2040,15 +2153,14 @@ error_modules: ret = close(kernel_tracer_event_notifier_group_fd); if (ret) { PERROR("Failed to close kernel tracer event notifier group file descriptor: fd = %d", - kernel_tracer_event_notifier_group_fd); + kernel_tracer_event_notifier_group_fd); } kernel_tracer_event_notifier_group_fd = -1; ret = close(kernel_tracer_fd); if (ret) { - PERROR("Failed to close kernel tracer file descriptor: fd = %d", - kernel_tracer_fd); + PERROR("Failed to close kernel tracer file descriptor: fd = %d", kernel_tracer_fd); } kernel_tracer_fd = -1; @@ -2060,19 +2172,21 @@ error: WARN("No kernel tracer available"); kernel_tracer_fd = -1; if (!is_root) { + kernel_tracer_status = nonstd::optional( + LTTNG_KERNEL_TRACER_STATUS_ERR_NEED_ROOT); return LTTNG_ERR_NEED_ROOT_SESSIOND; } else { return LTTNG_ERR_KERN_NA; } } -void cleanup_kernel_tracer(void) +void cleanup_kernel_tracer() { DBG2("Closing kernel event notifier group notification file descriptor"); if (kernel_tracer_event_notifier_group_notification_fd >= 0) { int ret = notification_thread_command_remove_tracer_event_source( - the_notification_thread_handle, - kernel_tracer_event_notifier_group_notification_fd); + the_notification_thread_handle, + kernel_tracer_event_notifier_group_notification_fd); if (ret != LTTNG_OK) { ERR("Failed to remove kernel event notifier notification from notification thread"); } @@ -2080,15 +2194,14 @@ void cleanup_kernel_tracer(void) ret = close(kernel_tracer_event_notifier_group_notification_fd); if (ret) { PERROR("Failed to close kernel event notifier group notification file descriptor: fd = %d", - kernel_tracer_event_notifier_group_notification_fd); + kernel_tracer_event_notifier_group_notification_fd); } kernel_tracer_event_notifier_group_notification_fd = -1; } if (kernel_token_to_event_notifier_rule_ht) { - const int ret = cds_lfht_destroy( - kernel_token_to_event_notifier_rule_ht, NULL); + const int ret = cds_lfht_destroy(kernel_token_to_event_notifier_rule_ht, nullptr); LTTNG_ASSERT(ret == 0); } @@ -2098,7 +2211,7 @@ void cleanup_kernel_tracer(void) if (ret) { PERROR("Failed to close kernel event notifier group file descriptor: fd = %d", - kernel_tracer_event_notifier_group_fd); + kernel_tracer_event_notifier_group_fd); } kernel_tracer_event_notifier_group_fd = -1; @@ -2110,16 +2223,17 @@ void cleanup_kernel_tracer(void) if (ret) { PERROR("Failed to close kernel tracer file descriptor: fd = %d", - kernel_tracer_fd); + kernel_tracer_fd); } kernel_tracer_fd = -1; } + kernel_tracer_status = nonstd::nullopt; free(syscall_table); } -bool kernel_tracer_is_initialized(void) +bool kernel_tracer_is_initialized() { return kernel_tracer_fd >= 0; } @@ -2140,10 +2254,7 @@ enum lttng_error_code kernel_clear_session(struct ltt_session *session) LTTNG_ASSERT(ksess); LTTNG_ASSERT(ksess->consumer); - DBG("Clear kernel session %s (session %" PRIu64 ")", - session->name, session->id); - - rcu_read_lock(); + DBG("Clear kernel session %s (session %" PRIu64 ")", session->name, session->id); if (ksess->active) { ERR("Expecting inactive session %s (%" PRIu64 ")", session->name, session->id); @@ -2151,41 +2262,46 @@ enum lttng_error_code kernel_clear_session(struct ltt_session *session) goto end; } - /* - * Note that this loop will end after one iteration given that there is - * only one kernel consumer. - */ - cds_lfht_for_each_entry(ksess->consumer->socks->ht, &iter.iter, - socket, node.node) { - struct ltt_kernel_channel *chan; - - /* For each channel, ask the consumer to clear it. */ - cds_list_for_each_entry(chan, &ksess->channel_list.head, list) { - DBG("Clear kernel channel %" PRIu64 ", session %s", - chan->key, session->name); - ret = consumer_clear_channel(socket, chan->key); - if (ret < 0) { - goto error; + { + /* + * Note that this loop will end after one iteration given that there is + * only one kernel consumer. + */ + lttng::urcu::read_lock_guard read_lock; + + cds_lfht_for_each_entry ( + ksess->consumer->socks->ht, &iter.iter, socket, node.node) { + struct ltt_kernel_channel *chan; + + /* For each channel, ask the consumer to clear it. */ + cds_list_for_each_entry (chan, &ksess->channel_list.head, list) { + DBG("Clear kernel channel %" PRIu64 ", session %s", + chan->key, + session->name); + ret = consumer_clear_channel(socket, chan->key); + if (ret < 0) { + goto error; + } + } + + if (!ksess->metadata) { + /* + * Nothing to do for the metadata. + * This is a snapshot session. + * The metadata is genererated on the fly. + */ + continue; } - } - if (!ksess->metadata) { /* - * Nothing to do for the metadata. - * This is a snapshot session. - * The metadata is genererated on the fly. + * Clear the metadata channel. + * Metadata channel is not cleared per se but we still need to + * perform a rotation operation on it behind the scene. */ - continue; - } - - /* - * Clear the metadata channel. - * Metadata channel is not cleared per se but we still need to - * perform a rotation operation on it behind the scene. - */ - ret = consumer_clear_channel(socket, ksess->metadata->key); - if (ret < 0) { - goto error; + ret = consumer_clear_channel(socket, ksess->metadata->key); + if (ret < 0) { + goto error; + } } } @@ -2193,19 +2309,18 @@ enum lttng_error_code kernel_clear_session(struct ltt_session *session) error: switch (-ret) { case LTTCOMM_CONSUMERD_RELAYD_CLEAR_DISALLOWED: - status = LTTNG_ERR_CLEAR_RELAY_DISALLOWED; - break; + status = LTTNG_ERR_CLEAR_RELAY_DISALLOWED; + break; default: - status = LTTNG_ERR_CLEAR_FAIL_CONSUMER; - break; + status = LTTNG_ERR_CLEAR_FAIL_CONSUMER; + break; } end: - rcu_read_unlock(); return status; } -enum lttng_error_code kernel_create_event_notifier_group_notification_fd( - int *event_notifier_group_notification_fd) +enum lttng_error_code +kernel_create_event_notifier_group_notification_fd(int *event_notifier_group_notification_fd) { int local_fd = -1, ret; enum lttng_error_code error_code_ret; @@ -2213,7 +2328,7 @@ enum lttng_error_code kernel_create_event_notifier_group_notification_fd( LTTNG_ASSERT(event_notifier_group_notification_fd); ret = kernctl_create_event_notifier_group_notification_fd( - kernel_tracer_event_notifier_group_fd); + kernel_tracer_event_notifier_group_fd); if (ret < 0) { PERROR("Failed to create kernel event notifier group notification file descriptor"); error_code_ret = LTTNG_ERR_EVENT_NOTIFIER_GROUP_NOTIFICATION_FD; @@ -2226,13 +2341,12 @@ enum lttng_error_code kernel_create_event_notifier_group_notification_fd( ret = fcntl(local_fd, F_SETFD, FD_CLOEXEC); if (ret < 0) { PERROR("Failed to set FD_CLOEXEC on kernel event notifier group notification file descriptor: fd = %d", - local_fd); + local_fd); error_code_ret = LTTNG_ERR_EVENT_NOTIFIER_GROUP_NOTIFICATION_FD; goto error; } - DBG("Created kernel notifier group notification file descriptor: fd = %d", - local_fd); + DBG("Created kernel notifier group notification file descriptor: fd = %d", local_fd); error_code_ret = LTTNG_OK; *event_notifier_group_notification_fd = local_fd; local_fd = -1; @@ -2242,55 +2356,51 @@ error: ret = close(local_fd); if (ret) { PERROR("Failed to close kernel event notifier group notification file descriptor: fd = %d", - local_fd); + local_fd); } } return error_code_ret; } -enum lttng_error_code kernel_destroy_event_notifier_group_notification_fd( - int event_notifier_group_notification_fd) +enum lttng_error_code +kernel_destroy_event_notifier_group_notification_fd(int event_notifier_group_notification_fd) { enum lttng_error_code ret_code = LTTNG_OK; DBG("Closing event notifier group notification file descriptor: fd = %d", - event_notifier_group_notification_fd); + event_notifier_group_notification_fd); if (event_notifier_group_notification_fd >= 0) { const int ret = close(event_notifier_group_notification_fd); if (ret) { PERROR("Failed to close event notifier group notification file descriptor: fd = %d", - event_notifier_group_notification_fd); + event_notifier_group_notification_fd); } } return ret_code; } -static -unsigned long hash_trigger(const struct lttng_trigger *trigger) +static unsigned long hash_trigger(const struct lttng_trigger *trigger) { - const struct lttng_condition *condition = - lttng_trigger_get_const_condition(trigger); + const struct lttng_condition *condition = lttng_trigger_get_const_condition(trigger); return lttng_condition_hash(condition); } -static -int match_trigger(struct cds_lfht_node *node, const void *key) +static int match_trigger(struct cds_lfht_node *node, const void *key) { const struct ltt_kernel_event_notifier_rule *event_notifier_rule; const struct lttng_trigger *trigger = (lttng_trigger *) key; - event_notifier_rule = caa_container_of(node, - const struct ltt_kernel_event_notifier_rule, ht_node); + event_notifier_rule = + caa_container_of(node, const struct ltt_kernel_event_notifier_rule, ht_node); return lttng_trigger_is_equal(trigger, event_notifier_rule->trigger); } static enum lttng_error_code kernel_create_event_notifier_rule( - struct lttng_trigger *trigger, - const struct lttng_credentials *creds, uint64_t token) + struct lttng_trigger *trigger, const struct lttng_credentials *creds, uint64_t token) { int err, fd, ret = 0; enum lttng_error_code error_code_ret; @@ -2300,8 +2410,8 @@ static enum lttng_error_code kernel_create_event_notifier_rule( struct ltt_kernel_event_notifier_rule *event_notifier_rule; struct lttng_kernel_abi_event_notifier kernel_event_notifier = {}; unsigned int capture_bytecode_count = 0, i; - const struct lttng_condition *condition = NULL; - const struct lttng_event_rule *event_rule = NULL; + const struct lttng_condition *condition = nullptr; + const struct lttng_event_rule *event_rule = nullptr; enum lttng_condition_status cond_status; LTTNG_ASSERT(trigger); @@ -2313,36 +2423,34 @@ static enum lttng_error_code kernel_create_event_notifier_rule( LTTNG_ASSERT(condition_type == LTTNG_CONDITION_TYPE_EVENT_RULE_MATCHES); /* Does not acquire a reference. */ - condition_status = lttng_condition_event_rule_matches_get_rule( - condition, &event_rule); + condition_status = lttng_condition_event_rule_matches_get_rule(condition, &event_rule); LTTNG_ASSERT(condition_status == LTTNG_CONDITION_STATUS_OK); LTTNG_ASSERT(event_rule); event_rule_type = lttng_event_rule_get_type(event_rule); LTTNG_ASSERT(event_rule_type != LTTNG_EVENT_RULE_TYPE_UNKNOWN); - error_code_ret = trace_kernel_create_event_notifier_rule(trigger, token, - lttng_condition_event_rule_matches_get_error_counter_index( - condition), - &event_notifier_rule); + error_code_ret = trace_kernel_create_event_notifier_rule( + trigger, + token, + lttng_condition_event_rule_matches_get_error_counter_index(condition), + &event_notifier_rule); if (error_code_ret != LTTNG_OK) { goto error; } - error_code_ret = trace_kernel_init_event_notifier_from_event_rule( - event_rule, &kernel_event_notifier); + error_code_ret = trace_kernel_init_event_notifier_from_event_rule(event_rule, + &kernel_event_notifier); if (error_code_ret != LTTNG_OK) { goto free_event; } kernel_event_notifier.event.token = event_notifier_rule->token; kernel_event_notifier.error_counter_idx = - lttng_condition_event_rule_matches_get_error_counter_index( - condition); + lttng_condition_event_rule_matches_get_error_counter_index(condition); - fd = kernctl_create_event_notifier( - kernel_tracer_event_notifier_group_fd, - &kernel_event_notifier); + fd = kernctl_create_event_notifier(kernel_tracer_event_notifier_group_fd, + &kernel_event_notifier); if (fd < 0) { switch (-fd) { case EEXIST: @@ -2354,12 +2462,13 @@ static enum lttng_error_code kernel_create_event_notifier_rule( break; case ENOENT: WARN("Failed to create kernel event notifier: not found: name = '%s'", - kernel_event_notifier.event.name); + kernel_event_notifier.event.name); error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL; break; default: PERROR("Failed to create kernel event notifier: error code = %d, name = '%s'", - fd, kernel_event_notifier.event.name); + fd, + kernel_event_notifier.event.name); error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL; } goto free_event; @@ -2370,7 +2479,7 @@ static enum lttng_error_code kernel_create_event_notifier_rule( err = fcntl(event_notifier_rule->fd, F_SETFD, FD_CLOEXEC); if (err < 0) { PERROR("Failed to set FD_CLOEXEC on kernel event notifier file descriptor: fd = %d", - fd); + fd); error_code_ret = LTTNG_ERR_FATAL; goto set_cloexec_error; } @@ -2390,10 +2499,9 @@ static enum lttng_error_code kernel_create_event_notifier_rule( } } - if (lttng_event_rule_get_type(event_rule) == - LTTNG_EVENT_RULE_TYPE_KERNEL_UPROBE) { + if (lttng_event_rule_get_type(event_rule) == LTTNG_EVENT_RULE_TYPE_KERNEL_UPROBE) { ret = userspace_probe_event_rule_add_callsites( - event_rule, creds, event_notifier_rule->fd); + event_rule, creds, event_notifier_rule->fd); if (ret) { error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL; goto add_callsite_error; @@ -2402,15 +2510,15 @@ static enum lttng_error_code kernel_create_event_notifier_rule( /* Set the capture bytecode if any. */ cond_status = lttng_condition_event_rule_matches_get_capture_descriptor_count( - condition, &capture_bytecode_count); + condition, &capture_bytecode_count); LTTNG_ASSERT(cond_status == LTTNG_CONDITION_STATUS_OK); for (i = 0; i < capture_bytecode_count; i++) { const struct lttng_bytecode *capture_bytecode = - lttng_condition_event_rule_matches_get_capture_bytecode_at_index( - condition, i); + lttng_condition_event_rule_matches_get_capture_bytecode_at_index(condition, + i); - if (capture_bytecode == NULL) { + if (capture_bytecode == nullptr) { ERR("Unexpected NULL capture bytecode on condition"); error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL; goto capture_error; @@ -2419,7 +2527,7 @@ static enum lttng_error_code kernel_create_event_notifier_rule( ret = kernctl_capture(event_notifier_rule->fd, capture_bytecode); if (ret < 0) { ERR("Failed to set capture bytecode on event notifier rule fd: fd = %d", - event_notifier_rule->fd); + event_notifier_rule->fd); error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL; goto capture_error; } @@ -2440,14 +2548,16 @@ static enum lttng_error_code kernel_create_event_notifier_rule( } /* Add trigger to kernel token mapping in the hash table. */ - rcu_read_lock(); - cds_lfht_add(kernel_token_to_event_notifier_rule_ht, hash_trigger(trigger), - &event_notifier_rule->ht_node); - rcu_read_unlock(); + { + lttng::urcu::read_lock_guard read_lock; + cds_lfht_add(kernel_token_to_event_notifier_rule_ht, + hash_trigger(trigger), + &event_notifier_rule->ht_node); + } DBG("Created kernel event notifier: name = '%s', fd = %d", - kernel_event_notifier.event.name, - event_notifier_rule->fd); + kernel_event_notifier.event.name, + event_notifier_rule->fd); return LTTNG_OK; @@ -2456,37 +2566,34 @@ add_callsite_error: enable_error: set_cloexec_error: filter_error: - { - const int close_ret = close(event_notifier_rule->fd); +{ + const int close_ret = close(event_notifier_rule->fd); - if (close_ret) { - PERROR("Failed to close kernel event notifier file descriptor: fd = %d", - event_notifier_rule->fd); - } + if (close_ret) { + PERROR("Failed to close kernel event notifier file descriptor: fd = %d", + event_notifier_rule->fd); } +} free_event: free(event_notifier_rule); error: return error_code_ret; } -enum lttng_error_code kernel_register_event_notifier( - struct lttng_trigger *trigger, - const struct lttng_credentials *cmd_creds) +enum lttng_error_code kernel_register_event_notifier(struct lttng_trigger *trigger, + const struct lttng_credentials *cmd_creds) { enum lttng_error_code ret; enum lttng_condition_status status; enum lttng_domain_type domain_type; const struct lttng_event_rule *event_rule; - const struct lttng_condition *const condition = - lttng_trigger_get_const_condition(trigger); + const struct lttng_condition *const condition = lttng_trigger_get_const_condition(trigger); const uint64_t token = lttng_trigger_get_tracer_token(trigger); LTTNG_ASSERT(condition); /* Does not acquire a reference to the event rule. */ - status = lttng_condition_event_rule_matches_get_rule( - condition, &event_rule); + status = lttng_condition_event_rule_matches_get_rule(condition, &event_rule); LTTNG_ASSERT(status == LTTNG_CONDITION_STATUS_OK); domain_type = lttng_event_rule_get_domain_type(event_rule); @@ -2500,8 +2607,7 @@ enum lttng_error_code kernel_register_event_notifier( return ret; } -enum lttng_error_code kernel_unregister_event_notifier( - const struct lttng_trigger *trigger) +enum lttng_error_code kernel_unregister_event_notifier(const struct lttng_trigger *trigger) { struct ltt_kernel_event_notifier_rule *token_event_rule_element; struct cds_lfht_node *node; @@ -2509,10 +2615,13 @@ enum lttng_error_code kernel_unregister_event_notifier( enum lttng_error_code error_code_ret; int ret; - rcu_read_lock(); + lttng::urcu::read_lock_guard read_lock; cds_lfht_lookup(kernel_token_to_event_notifier_rule_ht, - hash_trigger(trigger), match_trigger, trigger, &iter); + hash_trigger(trigger), + match_trigger, + trigger, + &iter); node = cds_lfht_iter_get_node(&iter); if (!node) { @@ -2520,8 +2629,8 @@ enum lttng_error_code kernel_unregister_event_notifier( goto error; } - token_event_rule_element = caa_container_of(node, - struct ltt_kernel_event_notifier_rule, ht_node); + token_event_rule_element = + caa_container_of(node, struct ltt_kernel_event_notifier_rule, ht_node); ret = kernel_disable_event_notifier_rule(token_event_rule_element); if (ret) { @@ -2533,12 +2642,11 @@ enum lttng_error_code kernel_unregister_event_notifier( error_code_ret = LTTNG_OK; error: - rcu_read_unlock(); return error_code_ret; } -int kernel_get_notification_fd(void) +int kernel_get_notification_fd() { return kernel_tracer_event_notifier_group_notification_fd; }