Fix: tests: fix unused-but-set warning in test_fd_tracker.c
[lttng-tools.git] / src / bin / lttng-sessiond / notification-thread-events.c
index 2772e6fa61b18fdec34a0a507c200e48a5a9e9c8..a295739f2c3adc3be22cedee490de6e56ad5e163 100644 (file)
@@ -36,7 +36,6 @@
 
 #include <time.h>
 #include <unistd.h>
-#include <assert.h>
 #include <inttypes.h>
 #include <fcntl.h>
 
@@ -311,7 +310,7 @@ int match_client_list_condition(struct cds_lfht_node *node, const void *key)
        struct notification_client_list *client_list;
        const struct lttng_condition *condition;
 
-       assert(condition_key);
+       LTTNG_ASSERT(condition_key);
 
        client_list = caa_container_of(node, struct notification_client_list,
                        notification_trigger_clients_ht_node);
@@ -526,7 +525,7 @@ void session_info_destroy(void *_data)
        struct session_info *session_info = _data;
        int ret;
 
-       assert(session_info);
+       LTTNG_ASSERT(session_info);
        if (session_info->channel_infos_ht) {
                ret = cds_lfht_destroy(session_info->channel_infos_ht, NULL);
                if (ret) {
@@ -568,7 +567,7 @@ struct session_info *session_info_create(const char *name, uid_t uid, gid_t gid,
 {
        struct session_info *session_info;
 
-       assert(name);
+       LTTNG_ASSERT(name);
 
        session_info = zmalloc(sizeof(*session_info));
        if (!session_info) {
@@ -655,7 +654,6 @@ error:
        return NULL;
 }
 
-LTTNG_HIDDEN
 bool notification_client_list_get(struct notification_client_list *list)
 {
        return urcu_ref_get_unless_zero(&list->ref);
@@ -690,7 +688,7 @@ void notification_client_list_release(struct urcu_ref *list_ref)
                free(client_list_element);
        }
 
-       assert(cds_list_empty(&list->triggers_list));
+       LTTNG_ASSERT(cds_list_empty(&list->triggers_list));
 
        pthread_mutex_destroy(&list->lock);
        call_rcu(&list->rcu_node, free_notification_client_list_rcu);
@@ -852,7 +850,7 @@ int evaluate_channel_condition_for_client(
                                        lttng_trigger_get_const_condition(
                                                element->trigger);
 
-                       assert(current_condition);
+                       LTTNG_ASSERT(current_condition);
                        if (!lttng_condition_is_equal(condition,
                                        current_condition)) {
                                continue;
@@ -882,7 +880,7 @@ int evaluate_channel_condition_for_client(
                        channel_key,
                        &iter);
        node = cds_lfht_iter_get_node(&iter);
-       assert(node);
+       LTTNG_ASSERT(node);
        channel_info = caa_container_of(node, struct channel_info,
                        channels_ht_node);
 
@@ -1038,10 +1036,10 @@ int evaluate_condition_for_client(const struct lttng_trigger *trigger,
        uid_t object_uid = 0;
        gid_t object_gid = 0;
 
-       assert(trigger);
-       assert(condition);
-       assert(client);
-       assert(state);
+       LTTNG_ASSERT(trigger);
+       LTTNG_ASSERT(condition);
+       LTTNG_ASSERT(client);
+       LTTNG_ASSERT(state);
 
        switch (get_condition_binding_object(condition)) {
        case LTTNG_OBJECT_TYPE_SESSION:
@@ -1371,18 +1369,18 @@ bool buffer_usage_condition_applies_to_channel(
 
        status = lttng_condition_buffer_usage_get_domain_type(condition,
                        &condition_domain);
-       assert(status == LTTNG_CONDITION_STATUS_OK);
+       LTTNG_ASSERT(status == LTTNG_CONDITION_STATUS_OK);
        if (channel_info->key.domain != condition_domain) {
                goto fail;
        }
 
        status = lttng_condition_buffer_usage_get_session_name(
                        condition, &condition_session_name);
-       assert((status == LTTNG_CONDITION_STATUS_OK) && condition_session_name);
+       LTTNG_ASSERT((status == LTTNG_CONDITION_STATUS_OK) && condition_session_name);
 
        status = lttng_condition_buffer_usage_get_channel_name(
                        condition, &condition_channel_name);
-       assert((status == LTTNG_CONDITION_STATUS_OK) && condition_channel_name);
+       LTTNG_ASSERT((status == LTTNG_CONDITION_STATUS_OK) && condition_channel_name);
 
        if (strcmp(channel_info->session_info->name, condition_session_name)) {
                goto fail;
@@ -1406,7 +1404,7 @@ bool session_consumed_size_condition_applies_to_channel(
 
        status = lttng_condition_session_consumed_size_get_session_name(
                        condition, &condition_session_name);
-       assert((status == LTTNG_CONDITION_STATUS_OK) && condition_session_name);
+       LTTNG_ASSERT((status == LTTNG_CONDITION_STATUS_OK) && condition_session_name);
 
        if (strcmp(channel_info->session_info->name, condition_session_name)) {
                goto fail;
@@ -1582,7 +1580,7 @@ bool trigger_applies_to_session(const struct lttng_trigger *trigger,
                        goto end;
                }
 
-               assert(condition_session_name);
+               LTTNG_ASSERT(condition_session_name);
                applies = !strcmp(condition_session_name, session_name);
                break;
        }
@@ -1663,8 +1661,8 @@ struct session_info *find_or_create_session_info(
                                name, uid, gid);
                session = caa_container_of(node, struct session_info,
                                sessions_ht_node);
-               assert(session->uid == uid);
-               assert(session->gid == gid);
+               LTTNG_ASSERT(session->uid == uid);
+               LTTNG_ASSERT(session->gid == gid);
                session_info_get(session);
                goto end;
        }
@@ -1875,7 +1873,7 @@ int handle_notification_thread_command_remove_channel(
                        &key,
                        &iter);
        node = cds_lfht_iter_get_node(&iter);
-       assert(node);
+       LTTNG_ASSERT(node);
        channel_info = caa_container_of(node, struct channel_info,
                        channels_ht_node);
        cds_lfht_del(state->channels_ht, node);
@@ -1937,7 +1935,7 @@ int handle_notification_thread_command_session_rotation(
 
                trigger = trigger_list_element->trigger;
                condition = lttng_trigger_get_const_condition(trigger);
-               assert(condition);
+               LTTNG_ASSERT(condition);
                condition_type = lttng_condition_get_type(condition);
 
                if (condition_type == LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING &&
@@ -2110,95 +2108,121 @@ end:
 }
 
 static
-int handle_notification_thread_command_remove_tracer_event_source(
-               struct notification_thread_state *state,
-               int tracer_event_source_fd,
-               enum lttng_error_code *_cmd_result)
+struct notification_event_tracer_event_source_element *
+find_tracer_event_source_element(struct notification_thread_state *state,
+               int tracer_event_source_fd)
 {
-       int ret = 0;
-       bool found = false;
-       enum lttng_error_code cmd_result = LTTNG_OK;
-       struct notification_event_tracer_event_source_element *source_element = NULL, *tmp;
+       struct notification_event_tracer_event_source_element *source_element;
 
-       cds_list_for_each_entry_safe(source_element, tmp,
+       cds_list_for_each_entry(source_element,
                        &state->tracer_event_sources_list, node) {
-               if (source_element->fd != tracer_event_source_fd) {
-                       continue;
+               if (source_element->fd == tracer_event_source_fd) {
+                       goto end;
                }
-
-               DBG("Removed tracer event source from poll set: tracer_event_source_fd = %d, domain = '%s'",
-                               tracer_event_source_fd,
-                               lttng_domain_type_str(source_element->domain));
-               cds_list_del(&source_element->node);
-               found = true;
-               break;
        }
 
-       if (!found) {
-               /*
-                * This is temporarily allowed since the poll activity set is
-                * not properly cleaned-up for the moment. This is adressed in
-                * an upcoming fix.
-                */
-               source_element = NULL;
-               goto end;
-       }
+       source_element = NULL;
+end:
+       return source_element;
+}
 
-       if (!source_element->is_fd_in_poll_set) {
-               /* Skip the poll set removal. */
-               goto end;
-       }
+static
+int remove_tracer_event_source_from_pollset(
+               struct notification_thread_state *state,
+               struct notification_event_tracer_event_source_element *source_element)
+{
+       int ret = 0;
+
+       LTTNG_ASSERT(source_element->is_fd_in_poll_set);
 
        DBG3("Removing tracer event source from poll set: tracer_event_source_fd = %d, domain = '%s'",
-                       tracer_event_source_fd,
+                       source_element->fd,
                        lttng_domain_type_str(source_element->domain));
 
        /* Removing the fd from the event poll set. */
-       ret = lttng_poll_del(&state->events, tracer_event_source_fd);
+       ret = lttng_poll_del(&state->events, source_element->fd);
        if (ret < 0) {
                ERR("Failed to remove tracer event source from poll set: tracer_event_source_fd = %d, domain = '%s'",
-                               tracer_event_source_fd,
+                               source_element->fd,
                                lttng_domain_type_str(source_element->domain));
-               cmd_result = LTTNG_ERR_FATAL;
+               ret = -1;
                goto end;
        }
 
        source_element->is_fd_in_poll_set = false;
 
-       ret = drain_event_notifier_notification_pipe(state, tracer_event_source_fd,
+       /*
+        * Force the notification thread to restart the poll() loop to ensure
+        * that any events from the removed fd are removed.
+        */
+       state->restart_poll = true;
+
+       ret = drain_event_notifier_notification_pipe(state, source_element->fd,
                        source_element->domain);
        if (ret) {
                ERR("Error draining event notifier notification: tracer_event_source_fd = %d, domain = %s",
-                               tracer_event_source_fd,
+                               source_element->fd,
                                lttng_domain_type_str(source_element->domain));
-               cmd_result = LTTNG_ERR_FATAL;
+               ret = -1;
                goto end;
        }
 
-       /*
-        * The drain_event_notifier_notification_pipe() call might have read
-        * data from an fd that we received in event in the latest _poll_wait()
-        * call. Make sure the thread call poll_wait() again to ensure we have
-        * a clean state.
-        */
-       state->restart_poll = true;
-
 end:
-       free(source_element);
-       *_cmd_result = cmd_result;
        return ret;
 }
 
-int handle_notification_thread_remove_tracer_event_source_no_result(
+int handle_notification_thread_tracer_event_source_died(
                struct notification_thread_state *state,
                int tracer_event_source_fd)
 {
-       int ret;
-       enum lttng_error_code cmd_result;
+       int ret = 0;
+       struct notification_event_tracer_event_source_element *source_element;
+
+       source_element = find_tracer_event_source_element(state,
+                       tracer_event_source_fd);
+
+       LTTNG_ASSERT(source_element);
+
+       ret = remove_tracer_event_source_from_pollset(state, source_element);
+       if (ret) {
+               ERR("Failed to remove dead tracer event source from poll set");
+       }
+
+       return ret;
+}
+
+static
+int handle_notification_thread_command_remove_tracer_event_source(
+               struct notification_thread_state *state,
+               int tracer_event_source_fd,
+               enum lttng_error_code *_cmd_result)
+{
+       int ret = 0;
+       enum lttng_error_code cmd_result = LTTNG_OK;
+       struct notification_event_tracer_event_source_element *source_element = NULL;
 
-       ret = handle_notification_thread_command_remove_tracer_event_source(
-                       state, tracer_event_source_fd, &cmd_result);
-       (void) cmd_result;
+       source_element = find_tracer_event_source_element(state,
+                       tracer_event_source_fd);
+
+       LTTNG_ASSERT(source_element);
+
+       /* Remove the tracer source from the list. */
+       cds_list_del(&source_element->node);
+
+       if (!source_element->is_fd_in_poll_set) {
+               /* Skip the poll set removal. */
+               goto end;
+       }
+
+       ret = remove_tracer_event_source_from_pollset(state, source_element);
+       if (ret) {
+               ERR("Failed to remove tracer event source from poll set");
+               cmd_result = LTTNG_ERR_FATAL;
+       }
+
+end:
+       free(source_element);
+       *_cmd_result = cmd_result;
        return ret;
 }
 
@@ -2276,7 +2300,7 @@ static inline void get_trigger_info_for_log(const struct lttng_trigger *trigger,
 
        trigger_status = lttng_trigger_get_owner_uid(trigger,
                        trigger_owner_uid);
-       assert(trigger_status == LTTNG_TRIGGER_STATUS_OK);
+       LTTNG_ASSERT(trigger_status == LTTNG_TRIGGER_STATUS_OK);
 }
 
 static int handle_notification_thread_command_get_trigger(
@@ -2334,7 +2358,7 @@ bool condition_is_supported(struct lttng_condition *condition)
 
                ret = lttng_condition_buffer_usage_get_domain_type(condition,
                                &domain);
-               assert(ret == 0);
+               LTTNG_ASSERT(ret == 0);
 
                if (domain != LTTNG_DOMAIN_KERNEL) {
                        is_supported = true;
@@ -2359,7 +2383,7 @@ bool condition_is_supported(struct lttng_condition *condition)
                                lttng_condition_event_rule_matches_get_rule(
                                                condition, &event_rule);
 
-               assert(status == LTTNG_CONDITION_STATUS_OK);
+               LTTNG_ASSERT(status == LTTNG_CONDITION_STATUS_OK);
 
                domain = lttng_event_rule_get_domain_type(event_rule);
                if (domain != LTTNG_DOMAIN_KERNEL) {
@@ -2456,7 +2480,7 @@ int bind_trigger_to_matching_channels(struct lttng_trigger *trigger,
                                &channel->key,
                                &lookup_iter);
                node = cds_lfht_iter_get_node(&lookup_iter);
-               assert(node);
+               LTTNG_ASSERT(node);
                trigger_list = caa_container_of(node,
                                struct lttng_channel_trigger_list,
                                channel_triggers_ht_node);
@@ -2486,7 +2510,7 @@ bool is_trigger_action_notify(const struct lttng_trigger *trigger)
                        lttng_trigger_get_const_action(trigger);
        enum lttng_action_type action_type;
 
-       assert(action);
+       LTTNG_ASSERT(action);
        action_type = lttng_action_get_type(action);
        if (action_type == LTTNG_ACTION_TYPE_NOTIFY) {
                is_notify = true;
@@ -2496,7 +2520,7 @@ bool is_trigger_action_notify(const struct lttng_trigger *trigger)
        }
 
        action_status = lttng_action_list_get_count(action, &count);
-       assert(action_status == LTTNG_ACTION_STATUS_OK);
+       LTTNG_ASSERT(action_status == LTTNG_ACTION_STATUS_OK);
 
        for (i = 0; i < count; i++) {
                const struct lttng_action *inner_action =
@@ -2550,7 +2574,7 @@ enum lttng_error_code generate_trigger_name(
                }
 
                status = lttng_trigger_get_name(trigger, name);
-               assert(status == LTTNG_TRIGGER_STATUS_OK);
+               LTTNG_ASSERT(status == LTTNG_TRIGGER_STATUS_OK);
 
                taken = trigger_name_taken(state, trigger);
        } while (taken || state->trigger_id.name_offset == UINT64_MAX);
@@ -2563,8 +2587,8 @@ void notif_thread_state_remove_trigger_ht_elem(
                struct notification_thread_state *state,
                struct lttng_trigger_ht_element *trigger_ht_element)
 {
-       assert(state);
-       assert(trigger_ht_element);
+       LTTNG_ASSERT(state);
+       LTTNG_ASSERT(trigger_ht_element);
 
        cds_lfht_del(state->triggers_ht, &trigger_ht_element->node);
        cds_lfht_del(state->triggers_by_name_uid_ht, &trigger_ht_element->node_by_name_uid);
@@ -2697,7 +2721,7 @@ int handle_notification_thread_command_register_trigger(
        }
 
        condition = lttng_trigger_get_condition(trigger);
-       assert(condition);
+       LTTNG_ASSERT(condition);
 
        /* Some conditions require tracers to implement a minimal ABI version. */
        if (!condition_is_supported(condition)) {
@@ -3057,7 +3081,7 @@ int handle_notification_thread_command_unregister_trigger(
                 * notification_trigger_clients_ht.
                 */
                client_list = get_client_list_from_condition(state, condition);
-               assert(client_list);
+               LTTNG_ASSERT(client_list);
 
                pthread_mutex_lock(&client_list->lock);
                cds_list_del(&trigger_ht_element->client_list_trigger_node);
@@ -3542,7 +3566,7 @@ enum client_transmission_status client_flush_outgoing_queue(
                 * If both data and fds are equal to zero, we are in an invalid
                 * state.
                 */
-               assert(fds_to_send_count != 0);
+               LTTNG_ASSERT(fds_to_send_count != 0);
                goto send_fds;
        }
 
@@ -3720,7 +3744,7 @@ int client_handle_message_unknown(struct notification_client *client,
         */
        const struct lttng_notification_channel_message *msg;
 
-       assert(sizeof(*msg) == client->communication.inbound.payload.buffer.size);
+       LTTNG_ASSERT(sizeof(*msg) == client->communication.inbound.payload.buffer.size);
        msg = (const struct lttng_notification_channel_message *)
                              client->communication.inbound.payload.buffer.data;
 
@@ -3794,9 +3818,11 @@ int client_handle_message_handshake(struct notification_client *client,
                        &client->communication.inbound.creds);
        client->gid = LTTNG_SOCK_GET_GID_CRED(
                        &client->communication.inbound.creds);
-       DBG("Received handshake from client (uid = %u, gid = %u) with version %i.%i",
+       client->is_sessiond = LTTNG_SOCK_GET_PID_CRED(&client->communication.inbound.creds) == getpid();
+       DBG("Received handshake from client: uid = %u, gid = %u, protocol version = %i.%i, client is sessiond = %s",
                        client->uid, client->gid, (int) client->major,
-                       (int) client->minor);
+                       (int) client->minor,
+                       client->is_sessiond ? "true" : "false");
 
        if (handshake_client->major !=
                        LTTNG_NOTIFICATION_CHANNEL_VERSION_MAJOR) {
@@ -3989,7 +4015,7 @@ int handle_notification_thread_client_in(
        }
 
 receive_fds:
-       assert(client->communication.inbound.bytes_to_receive == 0);
+       LTTNG_ASSERT(client->communication.inbound.bytes_to_receive == 0);
 
        /* Receive fds. */
        if (client->communication.inbound.fds_to_receive != 0) {
@@ -4007,7 +4033,7 @@ receive_fds:
                        expected_size = sizeof(int) *
                                        client->communication.inbound
                                                        .fds_to_receive;
-                       assert(ret == expected_size);
+                       LTTNG_ASSERT(ret == expected_size);
                        client->communication.inbound.fds_to_receive = 0;
                } else if (ret == 0) {
                        /* Received nothing. */
@@ -4019,7 +4045,7 @@ receive_fds:
        }
 
        /* At this point the message is complete.*/
-       assert(client->communication.inbound.bytes_to_receive == 0 &&
+       LTTNG_ASSERT(client->communication.inbound.bytes_to_receive == 0 &&
                        client->communication.inbound.fds_to_receive == 0);
        ret = client_dispatch_message(client, state);
        if (ret) {
@@ -4324,7 +4350,6 @@ int send_evaluation_to_clients(const struct lttng_trigger *trigger,
  * interference from external users (those could, for instance, unregister
  * their triggers).
  */
-LTTNG_HIDDEN
 int notification_client_list_send_evaluation(
                struct notification_client_list *client_list,
                const struct lttng_trigger *trigger,
@@ -4394,6 +4419,15 @@ int notification_client_list_send_evaluation(
                        goto skip_client;
                }
 
+               if (lttng_trigger_is_hidden(trigger) && !client->is_sessiond) {
+                       /*
+                        * Notifications resulting from an hidden trigger are
+                        * only sent to the session daemon.
+                        */
+                       DBG("Skipping client as the trigger is hidden and the client is not the session daemon");
+                       goto skip_client;
+               }
+
                if (source_object_creds) {
                        if (client->uid != lttng_credentials_get_uid(source_object_creds) &&
                                        client->gid != lttng_credentials_get_gid(source_object_creds) &&
@@ -4616,10 +4650,11 @@ int dispatch_one_event_notifier_notification(struct notification_thread_state *s
                        notification->capture_buf_size, false);
 
        if (evaluation == NULL) {
-               ERR("Failed to create event rule hit evaluation while creating and enqueuing action executor job");
+               ERR("Failed to create event rule matches evaluation while creating and enqueuing action executor job");
                ret = -1;
                goto end_unlock;
        }
+
        client_list = get_client_list_from_condition(state,
                        lttng_trigger_get_const_condition(element->trigger));
        executor_status = action_executor_enqueue_trigger(state->executor,
@@ -4879,7 +4914,7 @@ int handle_notification_thread_channel_sample(
                ret = 0;
                trigger = trigger_list_element->trigger;
                condition = lttng_trigger_get_const_condition(trigger);
-               assert(condition);
+               LTTNG_ASSERT(condition);
 
                /*
                 * Check if any client is subscribed to the result of this
This page took 0.031374 seconds and 4 git commands to generate.