Support per UID buffers
[lttng-tools.git] / src / bin / lttng-sessiond / main.c
index 2698fb46cb47e2d76ce1f0f22adba8155620f4a5..f57a5c911d11095a7efbdc1a5ad8a87d400f3d9f 100644 (file)
@@ -45,6 +45,7 @@
 #include <common/utils.h>
 
 #include "lttng-sessiond.h"
+#include "buffer-registry.h"
 #include "channel.h"
 #include "cmd.h"
 #include "consumer.h"
@@ -435,6 +436,7 @@ static void cleanup(void)
 
        DBG("Closing all UST sockets");
        ust_app_clean_list();
+       buffer_reg_destroy_registries();
 
        if (is_root && !opt_no_kernel) {
                DBG2("Closing kernel fd");
@@ -1244,41 +1246,25 @@ error_testpoint:
 }
 
 /*
- * Send the application sockets (cmd and notify) to the respective threads.
- * This is called from the dispatch UST registration thread once all sockets
- * are set for the application.
+ * Send a socket to a thread This is called from the dispatch UST registration
+ * thread once all sockets are set for the application.
  *
  * On success, return 0 else a negative value being the errno message of the
  * write().
  */
-static int send_app_sockets_to_threads(struct ust_app *app)
+static int send_socket_to_thread(int fd, int sock)
 {
        int ret;
 
-       assert(app);
        /* Sockets MUST be set or else this should not have been called. */
-       assert(app->sock >= 0);
-       assert(app->notify_sock >= 0);
-       assert(apps_cmd_pipe[1] >= 0);
-       assert(apps_cmd_notify_pipe[1] >= 0);
+       assert(fd >= 0);
+       assert(sock >= 0);
 
        do {
-               ret = write(apps_cmd_pipe[1], &app->sock, sizeof(app->sock));
+               ret = write(fd, &sock, sizeof(sock));
        } while (ret < 0 && errno == EINTR);
-       if (ret < 0 || ret != sizeof(app->sock)) {
-               PERROR("write apps cmd pipe %d", apps_cmd_pipe[1]);
-               if (ret < 0) {
-                       ret = -errno;
-               }
-               goto error;
-       }
-
-       do {
-               ret = write(apps_cmd_notify_pipe[1], &app->notify_sock,
-                               sizeof(app->notify_sock));
-       } while (ret < 0 && errno == EINTR);
-       if (ret < 0 || ret != sizeof(app->notify_sock)) {
-               PERROR("write apps notify cmd pipe %d", apps_cmd_notify_pipe[1]);
+       if (ret < 0 || ret != sizeof(sock)) {
+               PERROR("write apps pipe %d", fd);
                if (ret < 0) {
                        ret = -errno;
                }
@@ -1303,7 +1289,7 @@ static void *thread_dispatch_ust_registration(void *data)
        struct {
                struct ust_app *app;
                struct cds_list_head head;
-       } *wait_node = NULL;
+       } *wait_node = NULL, *tmp_wait_node;
 
        CDS_LIST_HEAD(wait_queue);
 
@@ -1315,6 +1301,7 @@ static void *thread_dispatch_ust_registration(void *data)
 
                do {
                        struct ust_app *app = NULL;
+                       ust_cmd = NULL;
 
                        /* Dequeue command for registration */
                        node = cds_wfq_dequeue_blocking(&ust_cmd_queue.queue);
@@ -1337,6 +1324,7 @@ static void *thread_dispatch_ust_registration(void *data)
                                wait_node = zmalloc(sizeof(*wait_node));
                                if (!wait_node) {
                                        PERROR("zmalloc wait_node dispatch");
+                                       free(ust_cmd);
                                        goto error;
                                }
                                CDS_INIT_LIST_HEAD(&wait_node->head);
@@ -1349,6 +1337,9 @@ static void *thread_dispatch_ust_registration(void *data)
                                        if (ret < 0) {
                                                PERROR("close ust sock dispatch %d", ust_cmd->sock);
                                        }
+                                       lttng_fd_put(1, LTTNG_FD_APPS);
+                                       free(wait_node);
+                                       free(ust_cmd);
                                        continue;
                                }
                                /*
@@ -1357,6 +1348,7 @@ static void *thread_dispatch_ust_registration(void *data)
                                 */
                                cds_list_add(&wait_node->head, &wait_queue);
 
+                               free(ust_cmd);
                                /*
                                 * We have to continue here since we don't have the notify
                                 * socket and the application MUST be added to the hash table
@@ -1368,7 +1360,8 @@ static void *thread_dispatch_ust_registration(void *data)
                                 * Look for the application in the local wait queue and set the
                                 * notify socket if found.
                                 */
-                               cds_list_for_each_entry(wait_node, &wait_queue, head) {
+                               cds_list_for_each_entry_safe(wait_node, tmp_wait_node,
+                                               &wait_queue, head) {
                                        if (wait_node->app->pid == ust_cmd->reg_msg.pid) {
                                                wait_node->app->notify_sock = ust_cmd->sock;
                                                cds_list_del(&wait_node->head);
@@ -1378,13 +1371,10 @@ static void *thread_dispatch_ust_registration(void *data)
                                                break;
                                        }
                                }
+                               free(ust_cmd);
                        }
 
                        if (app) {
-                               ret = send_app_sockets_to_threads(app);
-                               if (ret < 0) {
-                                       goto error;
-                               }
                                /*
                                 * @session_lock_list
                                 *
@@ -1394,29 +1384,52 @@ static void *thread_dispatch_ust_registration(void *data)
                                 */
                                session_lock_list();
                                rcu_read_lock();
+
                                /*
                                 * Add application to the global hash table. This needs to be
                                 * done before the update to the UST registry can locate the
                                 * application.
                                 */
                                ust_app_add(app);
-                               /*
-                                * Get app version.
-                                */
-                               ret = ust_app_version(app);
-                               if (ret) {
-                                       ERR("Unable to get app version");
+
+                               /* Set app version. This call will print an error if needed. */
+                               (void) ust_app_version(app);
+
+                               /* Send notify socket through the notify pipe. */
+                               ret = send_socket_to_thread(apps_cmd_notify_pipe[1],
+                                               app->notify_sock);
+                               if (ret < 0) {
+                                       rcu_read_unlock();
+                                       session_unlock_list();
+                                       /* No notify thread, stop the UST tracing. */
+                                       goto error;
                                }
+
                                /*
                                 * Update newly registered application with the tracing
                                 * registry info already enabled information.
                                 */
                                update_ust_app(app->sock);
-                               ret = ust_app_register_done(app->sock);
+
+                               /*
+                                * Don't care about return value. Let the manage apps threads
+                                * handle app unregistration upon socket close.
+                                */
+                               (void) ust_app_register_done(app->sock);
+
+                               /*
+                                * Even if the application socket has been closed, send the app
+                                * to the thread and unregistration will take place at that
+                                * place.
+                                */
+                               ret = send_socket_to_thread(apps_cmd_pipe[1], app->sock);
                                if (ret < 0) {
-                                       /* Remove application from the registry. */
-                                       ust_app_unregister(app->sock);
+                                       rcu_read_unlock();
+                                       session_unlock_list();
+                                       /* No apps. thread, stop the UST tracing. */
+                                       goto error;
                                }
+
                                rcu_read_unlock();
                                session_unlock_list();
                        } else {
@@ -1425,8 +1438,8 @@ static void *thread_dispatch_ust_registration(void *data)
                                if (ret < 0) {
                                        PERROR("close ust_cmd sock");
                                }
+                               lttng_fd_put(1, LTTNG_FD_APPS);
                        }
-                       free(ust_cmd);
                } while (node != NULL);
 
                /* Futex wait on queue. Blocking call on futex() */
@@ -1434,6 +1447,13 @@ static void *thread_dispatch_ust_registration(void *data)
        }
 
 error:
+       /* Clean up wait queue. */
+       cds_list_for_each_entry_safe(wait_node, tmp_wait_node,
+                       &wait_queue, head) {
+               cds_list_del(&wait_node->head);
+               free(wait_node);
+       }
+
        DBG("Dispatch thread dying");
        return NULL;
 }
@@ -1561,6 +1581,7 @@ static void *thread_registration_apps(void *data)
                                                sock = -1;
                                                continue;
                                        }
+
                                        health_code_update();
                                        ret = ust_app_recv_registration(sock, &ust_cmd->reg_msg);
                                        if (ret < 0) {
@@ -2595,13 +2616,13 @@ skip_domain:
        }
        case LTTNG_ENABLE_CHANNEL:
        {
-               ret = cmd_enable_channel(cmd_ctx->session, cmd_ctx->lsm->domain.type,
+               ret = cmd_enable_channel(cmd_ctx->session, &cmd_ctx->lsm->domain,
                                &cmd_ctx->lsm->u.channel.chan, kernel_poll_pipe[1]);
                break;
        }
        case LTTNG_ENABLE_EVENT:
        {
-               ret = cmd_enable_event(cmd_ctx->session, cmd_ctx->lsm->domain.type,
+               ret = cmd_enable_event(cmd_ctx->session, &cmd_ctx->lsm->domain,
                                cmd_ctx->lsm->u.enable.channel_name,
                                &cmd_ctx->lsm->u.enable.event, NULL, kernel_poll_pipe[1]);
                break;
@@ -2610,7 +2631,7 @@ skip_domain:
        {
                DBG("Enabling all events");
 
-               ret = cmd_enable_event_all(cmd_ctx->session, cmd_ctx->lsm->domain.type,
+               ret = cmd_enable_event_all(cmd_ctx->session, &cmd_ctx->lsm->domain,
                                cmd_ctx->lsm->u.enable.channel_name,
                                cmd_ctx->lsm->u.enable.event.type, NULL, kernel_poll_pipe[1]);
                break;
@@ -2959,7 +2980,7 @@ skip_domain:
                        goto error;
                }
 
-               ret = cmd_enable_event(cmd_ctx->session, cmd_ctx->lsm->domain.type,
+               ret = cmd_enable_event(cmd_ctx->session, &cmd_ctx->lsm->domain,
                                cmd_ctx->lsm->u.enable.channel_name,
                                &cmd_ctx->lsm->u.enable.event, bytecode, kernel_poll_pipe[1]);
                break;
@@ -4202,6 +4223,10 @@ int main(int argc, char **argv)
                goto exit;
        }
 
+       /* Initialize global buffer per UID and PID registry. */
+       buffer_reg_init_uid_registry();
+       buffer_reg_init_pid_registry();
+
        /* Init UST command queue. */
        cds_wfq_init(&ust_cmd_queue.queue);
 
This page took 0.027578 seconds and 4 git commands to generate.