Launch the rotation thread using lttng_thread
authorJérémie Galarneau <jeremie.galarneau@efficios.com>
Wed, 28 Nov 2018 21:53:53 +0000 (16:53 -0500)
committerJérémie Galarneau <jeremie.galarneau@efficios.com>
Wed, 5 Dec 2018 17:25:11 +0000 (12:25 -0500)
Signed-off-by: Jérémie Galarneau <jeremie.galarneau@efficios.com>
src/bin/lttng-sessiond/main.c
src/bin/lttng-sessiond/rotation-thread.c
src/bin/lttng-sessiond/rotation-thread.h

index 4749f8621b62d1b0512304dcbac6677fd1e79124..0c207309dbb0714ed24c78e55c8072b1f15154b1 100644 (file)
@@ -194,7 +194,6 @@ static pthread_t kernel_thread;
 static pthread_t dispatch_thread;
 static pthread_t agent_reg_thread;
 static pthread_t load_session_thread;
-static pthread_t rotation_thread;
 static pthread_t timer_thread;
 
 /*
@@ -255,9 +254,6 @@ static const char * const config_section_name = "sessiond";
 /* Am I root or not. Set to 1 if the daemon is running as root */
 static int is_root;
 
-/* Rotation thread handle. */
-static struct rotation_thread_handle *rotation_thread_handle;
-
 /*
  * Stop all threads by closing the thread quit pipe.
  */
@@ -5496,10 +5492,11 @@ int main(int argc, char **argv)
        struct lttng_pipe *ust32_channel_monitor_pipe = NULL,
                        *ust64_channel_monitor_pipe = NULL,
                        *kernel_channel_monitor_pipe = NULL;
-       bool rotation_thread_launched = false;
        bool timer_thread_launched = false;
        struct lttng_thread *ht_cleanup_thread = NULL;
        struct timer_thread_parameters timer_thread_ctx;
+       /* Rotation thread handle. */
+       struct rotation_thread_handle *rotation_thread_handle = NULL;
        /* Queue of rotation jobs populated by the sessiond-timer. */
        struct rotation_thread_timer_queue *rotation_timer_queue = NULL;
 
@@ -5892,16 +5889,10 @@ int main(int argc, char **argv)
        }
 
        /* Create rotation thread. */
-       ret = pthread_create(&rotation_thread, default_pthread_attr(),
-                       thread_rotation, rotation_thread_handle);
-       if (ret) {
-               errno = ret;
-               PERROR("pthread_create rotation");
+       if (!launch_rotation_thread(rotation_thread_handle)) {
                retval = -1;
-               stop_threads();
                goto exit_rotation;
        }
-       rotation_thread_launched = true;
 
        /* Create thread to manage the client socket */
        ret = pthread_create(&client_thread, default_pthread_attr(),
@@ -6098,18 +6089,6 @@ exit_init_data:
         */
        rcu_barrier();
 
-       if (rotation_thread_handle) {
-               if (rotation_thread_launched) {
-                       ret = pthread_join(rotation_thread, &status);
-                       if (ret) {
-                               errno = ret;
-                               PERROR("pthread_join rotation thread");
-                               retval = -1;
-                       }
-               }
-               rotation_thread_handle_destroy(rotation_thread_handle);
-       }
-
        if (timer_thread_launched) {
                timer_exit();
                ret = pthread_join(timer_thread, &status);
@@ -6125,15 +6104,18 @@ exit_init_data:
                lttng_thread_put(ht_cleanup_thread);
        }
 
+       rcu_thread_offline();
+       rcu_unregister_thread();
+
+       if (rotation_thread_handle) {
+               rotation_thread_handle_destroy(rotation_thread_handle);
+       }
+
        /*
         * After the rotation and timer thread have quit, we can safely destroy
         * the rotation_timer_queue.
         */
        rotation_thread_timer_queue_destroy(rotation_timer_queue);
-
-       rcu_thread_offline();
-       rcu_unregister_thread();
-
        /*
         * The teardown of the notification system is performed after the
         * session daemon's teardown in order to allow it to be notified
index 043993a60484130450dbe3dd75818b72ea9f4b66..9a1d803b795846a380fa53b157616b370f2d2e05 100644 (file)
@@ -44,6 +44,8 @@
 #include "session.h"
 #include "timer.h"
 #include "notification-thread-commands.h"
+#include "utils.h"
+#include "thread.h"
 
 #include <urcu.h>
 #include <urcu/list.h>
@@ -75,6 +77,8 @@ struct rotation_thread_handle {
        struct rotation_thread_timer_queue *rotation_timer_queue;
        /* Access to the notification thread cmd_queue */
        struct notification_thread_handle *notification_thread_handle;
+       /* Thread-specific quit pipe. */
+       struct lttng_pipe *quit_pipe;
 };
 
 static
@@ -137,8 +141,6 @@ void log_job_destruction(const struct rotation_thread_job *job)
 void rotation_thread_timer_queue_destroy(
                struct rotation_thread_timer_queue *queue)
 {
-       struct rotation_thread_job *job, *tmp_job;
-
        if (!queue) {
                return;
        }
@@ -146,12 +148,7 @@ void rotation_thread_timer_queue_destroy(
        lttng_pipe_destroy(queue->event_pipe);
 
        pthread_mutex_lock(&queue->lock);
-       /* Empty wait queue. */
-       cds_list_for_each_entry_safe(job, tmp_job, &queue->list, head) {
-               log_job_destruction(job);
-               cds_list_del(&job->head);
-               free(job);
-       }
+       assert(cds_list_empty(&queue->list));
        pthread_mutex_unlock(&queue->lock);
        pthread_mutex_destroy(&queue->lock);
        free(queue);
@@ -163,6 +160,7 @@ void rotation_thread_timer_queue_destroy(
 void rotation_thread_handle_destroy(
                struct rotation_thread_handle *handle)
 {
+       lttng_pipe_destroy(handle->quit_pipe);
        free(handle);
 }
 
@@ -179,9 +177,16 @@ struct rotation_thread_handle *rotation_thread_handle_create(
 
        handle->rotation_timer_queue = rotation_timer_queue;
        handle->notification_thread_handle = notification_thread_handle;
+       handle->quit_pipe = lttng_pipe_open(FD_CLOEXEC);
+       if (!handle->quit_pipe) {
+               goto error;
+       }
 
 end:
        return handle;
+error:
+       rotation_thread_handle_destroy(handle);
+       return NULL;
 }
 
 /*
@@ -271,19 +276,29 @@ int init_poll_set(struct lttng_poll_event *poll_set,
        int ret;
 
        /*
-        * Create pollset with size 2:
-        *      - quit pipe,
+        * Create pollset with size 3:
+        *      - rotation thread quit pipe,
         *      - rotation thread timer queue pipe,
+        *      - notification channel sock,
         */
-       ret = sessiond_set_thread_pollset(poll_set, 2);
-       if (ret) {
+       ret = lttng_poll_create(poll_set, 5, LTTNG_CLOEXEC);
+       if (ret < 0) {
                goto error;
        }
+
+       ret = lttng_poll_add(poll_set,
+                       lttng_pipe_get_readfd(handle->quit_pipe),
+                       LPOLLIN | LPOLLERR);
+       if (ret < 0) {
+               ERR("[rotation-thread] Failed to add quit pipe read fd to poll set");
+               goto error;
+       }
+
        ret = lttng_poll_add(poll_set,
                        lttng_pipe_get_readfd(handle->rotation_timer_queue->event_pipe),
                        LPOLLIN | LPOLLERR);
        if (ret < 0) {
-               ERR("[rotation-thread] Failed to add rotate_pending fd to pollset");
+               ERR("[rotation-thread] Failed to add rotate_pending fd to poll set");
                goto error;
        }
 
@@ -914,6 +929,8 @@ void *thread_rotation(void *data)
        int ret;
        struct rotation_thread_handle *handle = data;
        struct rotation_thread thread;
+       const int queue_pipe_fd = lttng_pipe_get_readfd(
+                       handle->rotation_timer_queue->event_pipe);
 
        DBG("[rotation-thread] Started rotation thread");
 
@@ -977,17 +994,6 @@ void *thread_rotation(void *data)
                                }
                        } else {
                                /* Job queue or quit pipe activity. */
-                               if (fd == lttng_pipe_get_readfd(
-                                               handle->rotation_timer_queue->event_pipe)) {
-                                       char buf;
-
-                                       ret = lttng_read(fd, &buf, 1);
-                                       if (ret != 1) {
-                                               ERR("[rotation-thread] Failed to read from wakeup pipe (fd = %i)", fd);
-                                               ret = -1;
-                                               goto error;
-                                       }
-                               }
 
                                /*
                                 * The job queue is serviced if there is
@@ -1002,7 +1008,16 @@ void *thread_rotation(void *data)
                                        goto error;
                                }
 
-                               if (sessiond_check_thread_quit_pipe(fd, revents)) {
+                               if (fd == queue_pipe_fd) {
+                                       char buf;
+
+                                       ret = lttng_read(fd, &buf, 1);
+                                       if (ret != 1) {
+                                               ERR("[rotation-thread] Failed to read from wakeup pipe (fd = %i)", fd);
+                                               ret = -1;
+                                               goto error;
+                                       }
+                               } else {
                                        DBG("[rotation-thread] Quit pipe activity");
                                        goto exit;
                                }
@@ -1019,3 +1034,30 @@ error:
 end:
        return NULL;
 }
+
+static
+bool shutdown_rotation_thread(void *thread_data)
+{
+       struct rotation_thread_handle *handle = thread_data;
+       const int write_fd = lttng_pipe_get_writefd(handle->quit_pipe);
+
+       return notify_thread_pipe(write_fd) == 1;
+}
+
+bool launch_rotation_thread(struct rotation_thread_handle *handle)
+{
+       struct lttng_thread *thread;
+
+       thread = lttng_thread_create("Rotation",
+                       thread_rotation,
+                       shutdown_rotation_thread,
+                       NULL,
+                       handle);
+       if (!thread) {
+               goto error;
+       }
+       lttng_thread_put(thread);
+       return true;
+error:
+       return false;
+}
index c4516095622e3b9e35c76765db0f209e4d7a9c6f..b83745786b977528181993f9b7591f8f593a514f 100644 (file)
@@ -56,6 +56,6 @@ void rotation_thread_enqueue_job(struct rotation_thread_timer_queue *queue,
                enum rotation_thread_job_type job_type,
                struct ltt_session *session);
 
-void *thread_rotation(void *data);
+bool launch_rotation_thread(struct rotation_thread_handle *handle);
 
 #endif /* ROTATION_THREAD_H */
This page took 0.045653 seconds and 5 git commands to generate.