Fix: sessiond: kernel error accounting fd still open when unloading modules
[lttng-tools.git] / src / bin / lttng-sessiond / kernel.c
index 3216ffcf519f6fc53749b8a10e13d94db8322ac3..eebe119d2701dc8e3875c9f5e2f482a0849fd452 100644 (file)
 
 #include <lttng/userspace-probe.h>
 #include <lttng/userspace-probe-internal.h>
-#include <lttng/condition/event-rule.h>
-#include <lttng/condition/event-rule-internal.h>
+#include <lttng/condition/on-event.h>
+#include <lttng/condition/on-event-internal.h>
 #include <lttng/event-rule/event-rule.h>
 #include <lttng/event-rule/event-rule-internal.h>
-#include <lttng/event-rule/uprobe-internal.h>
+#include <lttng/event-rule/userspace-probe-internal.h>
 
+#include "event-notifier-error-accounting.h"
 #include "lttng-sessiond.h"
 #include "lttng-syscall.h"
 #include "condition-internal.h"
@@ -41,6 +42,7 @@
 #include "kernel.h"
 #include "kernel-consumer.h"
 #include "kern-modules.h"
+#include "sessiond-config.h"
 #include "utils.h"
 #include "rotate.h"
 #include "modprobe.h"
@@ -540,9 +542,9 @@ static int userspace_probe_event_rule_add_callsites(
        assert(creds);
 
        event_rule_type = lttng_event_rule_get_type(rule);
-       assert(event_rule_type == LTTNG_EVENT_RULE_TYPE_UPROBE);
+       assert(event_rule_type == LTTNG_EVENT_RULE_TYPE_USERSPACE_PROBE);
 
-       status = lttng_event_rule_uprobe_get_location(rule, &location);
+       status = lttng_event_rule_userspace_probe_get_location(rule, &location);
        if (status != LTTNG_EVENT_RULE_STATUS_OK || !location) {
                ret = -1;
                goto end;
@@ -568,7 +570,7 @@ end:
 int kernel_create_event(struct lttng_event *ev,
                struct ltt_kernel_channel *channel,
                char *filter_expression,
-               struct lttng_filter_bytecode *filter)
+               struct lttng_bytecode *filter)
 {
        int err, fd;
        enum lttng_error_code ret;
@@ -1989,7 +1991,8 @@ int init_kernel_tracer(void)
                WARN("Failed to create kernel event notifier group");
                kernel_tracer_event_notifier_group_fd = -1;
        } else {
-               const enum lttng_error_code error_code_ret =
+               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);
 
@@ -1997,6 +2000,14 @@ int init_kernel_tracer(void)
                        goto error_modules;
                }
 
+               error_accounting_status = event_notifier_error_accounting_register_kernel(
+                               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;
+                       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,
@@ -2113,8 +2124,6 @@ void cleanup_kernel_tracer(void)
                kernel_tracer_fd = -1;
        }
 
-       DBG("Unloading kernel modules");
-       modprobe_remove_lttng_all();
        free(syscall_table);
 }
 
@@ -2299,8 +2308,10 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
        enum lttng_event_rule_type event_rule_type;
        struct ltt_kernel_event_notifier_rule *event_notifier_rule;
        struct lttng_kernel_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;
+       enum lttng_condition_status cond_status;
 
        assert(trigger);
 
@@ -2308,10 +2319,10 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
        assert(condition);
 
        condition_type = lttng_condition_get_type(condition);
-       assert(condition_type == LTTNG_CONDITION_TYPE_EVENT_RULE_HIT);
+       assert(condition_type == LTTNG_CONDITION_TYPE_ON_EVENT);
 
        /* Does not acquire a reference. */
-       condition_status = lttng_condition_event_rule_get_rule(
+       condition_status = lttng_condition_on_event_get_rule(
                        condition, &event_rule);
        assert(condition_status == LTTNG_CONDITION_STATUS_OK);
        assert(event_rule);
@@ -2320,6 +2331,7 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
        assert(event_rule_type != LTTNG_EVENT_RULE_TYPE_UNKNOWN);
 
        error_code_ret = trace_kernel_create_event_notifier_rule(trigger, token,
+                       lttng_condition_on_event_get_error_counter_index(condition),
                        &event_notifier_rule);
        if (error_code_ret != LTTNG_OK) {
                goto error;
@@ -2328,10 +2340,12 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
        error_code_ret = trace_kernel_init_event_notifier_from_event_rule(
                        event_rule, &kernel_event_notifier);
        if (error_code_ret != LTTNG_OK) {
-               goto error;
+               goto free_event;
        }
 
        kernel_event_notifier.event.token = event_notifier_rule->token;
+       kernel_event_notifier.error_counter_idx =
+                       lttng_condition_on_event_get_error_counter_index(condition);
 
        fd = kernctl_create_event_notifier(
                        kernel_tracer_event_notifier_group_fd,
@@ -2384,7 +2398,7 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
        }
 
        if (lttng_event_rule_get_type(event_rule) ==
-                       LTTNG_EVENT_RULE_TYPE_UPROBE) {
+                       LTTNG_EVENT_RULE_TYPE_USERSPACE_PROBE) {
                ret = userspace_probe_event_rule_add_callsites(
                                event_rule, creds, event_notifier_rule->fd);
                if (ret) {
@@ -2393,6 +2407,31 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
                }
        }
 
+       /* Set the capture bytecode if any. */
+       cond_status = lttng_condition_on_event_get_capture_descriptor_count(
+                       condition, &capture_bytecode_count);
+       assert(cond_status == LTTNG_CONDITION_STATUS_OK);
+
+       for (i = 0; i < capture_bytecode_count; i++) {
+               const struct lttng_bytecode *capture_bytecode =
+                               lttng_condition_on_event_get_capture_bytecode_at_index(
+                                               condition, i);
+
+               if (capture_bytecode == NULL) {
+                       ERR("Unexpected NULL capture bytecode on condition");
+                       error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL;
+                       goto capture_error;
+               }
+
+               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);
+                       error_code_ret = LTTNG_ERR_KERN_ENABLE_FAIL;
+                       goto capture_error;
+               }
+       }
+
        err = kernctl_enable(event_notifier_rule->fd);
        if (err < 0) {
                switch (-err) {
@@ -2419,6 +2458,7 @@ static enum lttng_error_code kernel_create_event_notifier_rule(
 
        return LTTNG_OK;
 
+capture_error:
 add_callsite_error:
 enable_error:
 set_cloexec_error:
@@ -2452,7 +2492,7 @@ enum lttng_error_code kernel_register_event_notifier(
        assert(condition);
 
        /* Does not acquire a reference to the event rule. */
-       status = lttng_condition_event_rule_get_rule(
+       status = lttng_condition_on_event_get_rule(
                        condition, &event_rule);
        assert(status == LTTNG_CONDITION_STATUS_OK);
 
@@ -2461,7 +2501,7 @@ enum lttng_error_code kernel_register_event_notifier(
 
        ret = kernel_create_event_notifier_rule(trigger, cmd_creds, token);
        if (ret != LTTNG_OK) {
-               ERR("Failed to create kernel trigger");
+               ERR("Failed to create kernel event notifier rule");
        }
 
        return ret;
This page took 0.026376 seconds and 4 git commands to generate.