Fix: add index destruction in destroy stream call
[lttng-tools.git] / src / bin / lttng-relayd / main.c
index ba97ab3d78a05bd2cec21c564b8ce4ca6bf35262..59888c280c341cc1c16a5c89d652a88802787ec2 100644 (file)
@@ -101,9 +101,6 @@ static struct relay_cmd_queue relay_cmd_queue;
 static char *data_buffer;
 static unsigned int data_buffer_size;
 
-/* Global hash table that stores relay index object. */
-static struct lttng_ht *indexes_ht;
-
 /* We need those values for the file/dir creation. */
 static uid_t relayd_uid;
 static gid_t relayd_gid;
@@ -111,6 +108,12 @@ static gid_t relayd_gid;
 /* Global relay stream hash table. */
 struct lttng_ht *relay_streams_ht;
 
+/* Global relay viewer stream hash table. */
+struct lttng_ht *viewer_streams_ht;
+
+/* Global hash table that stores relay index object. */
+struct lttng_ht *indexes_ht;
+
 /*
  * usage function on stderr
  */
@@ -761,15 +764,20 @@ void deferred_free_session(struct rcu_head *head)
        free(session);
 }
 
-static void close_stream(struct relay_stream *stream,
-               struct lttng_ht *viewer_streams_ht, struct lttng_ht *ctf_traces_ht)
+/*
+ * Close a given stream. The stream is freed using a call RCU.
+ *
+ * RCU read side lock MUST be acquired. If NO close_stream_check() was called
+ * BEFORE the stream lock MUST be acquired.
+ */
+static void destroy_stream(struct relay_stream *stream,
+               struct lttng_ht *ctf_traces_ht)
 {
        int delret;
        struct relay_viewer_stream *vstream;
        struct lttng_ht_iter iter;
 
        assert(stream);
-       assert(viewer_streams_ht);
 
        delret = close(stream->fd);
        if (delret < 0) {
@@ -783,8 +791,7 @@ static void close_stream(struct relay_stream *stream,
                }
        }
 
-       vstream = live_find_viewer_stream_by_id(stream->stream_handle,
-                       viewer_streams_ht);
+       vstream = live_find_viewer_stream_by_id(stream->stream_handle);
        if (vstream) {
                /*
                 * Set the last good value into the viewer stream. This is done
@@ -795,6 +802,9 @@ static void close_stream(struct relay_stream *stream,
                vstream->total_index_received = stream->total_index_received;
        }
 
+       /* Cleanup index of that stream. */
+       relay_index_destroy_by_stream_id(stream->stream_handle);
+
        iter.iter.node = &stream->stream_n.node;
        delret = lttng_ht_del(relay_streams_ht, &iter);
        assert(!delret);
@@ -827,29 +837,20 @@ void relay_delete_session(struct relay_command *cmd,
        rcu_read_lock();
        cds_lfht_for_each_entry(relay_streams_ht->ht, &iter.iter, node, node) {
                node = lttng_ht_iter_get_node_ulong(&iter);
-               if (node) {
-                       stream = caa_container_of(node,
-                                       struct relay_stream, stream_n);
-                       if (stream->session == cmd->session) {
-                               ret = close(stream->fd);
-                               if (ret < 0) {
-                                       PERROR("close stream fd on delete session");
-                               }
-                               ret = lttng_ht_del(relay_streams_ht, &iter);
-                               assert(!ret);
-                               call_rcu(&stream->rcu_node,
-                                       deferred_free_stream);
-                       }
-                       /* Cleanup index of that stream. */
-                       relay_index_destroy_by_stream_id(stream->stream_handle,
-                                       indexes_ht);
+               if (!node) {
+                       continue;
+               }
+               stream = caa_container_of(node, struct relay_stream, stream_n);
+               if (stream->session == cmd->session) {
+                       destroy_stream(stream, cmd->ctf_traces_ht);
                }
        }
+
+       /* Make this session not visible anymore. */
        iter.iter.node = &cmd->session->session_n.node;
        ret = lttng_ht_del(sessions_ht, &iter);
        assert(!ret);
-       call_rcu(&cmd->session->rcu_node,
-                       deferred_free_session);
+       call_rcu(&cmd->session->rcu_node, deferred_free_session);
        rcu_read_unlock();
 }
 
@@ -1073,7 +1074,7 @@ err_free_stream:
  */
 static
 int relay_close_stream(struct lttcomm_relayd_hdr *recv_hdr,
-               struct relay_command *cmd, struct lttng_ht *viewer_streams_ht)
+               struct relay_command *cmd)
 {
        int ret, send_ret;
        struct relay_session *session = cmd->session;
@@ -1113,7 +1114,7 @@ int relay_close_stream(struct lttcomm_relayd_hdr *recv_hdr,
        stream->close_flag = 1;
 
        if (close_stream_check(stream)) {
-               close_stream(stream, viewer_streams_ht, cmd->ctf_traces_ht);
+               destroy_stream(stream, cmd->ctf_traces_ht);
        }
 
 end_unlock:
@@ -1652,7 +1653,7 @@ end_no_session:
  */
 static
 int relay_recv_index(struct lttcomm_relayd_hdr *recv_hdr,
-               struct relay_command *cmd, struct lttng_ht *indexes_ht)
+               struct relay_command *cmd)
 {
        int ret, send_ret, index_created = 0;
        struct relay_session *session = cmd->session;
@@ -1663,7 +1664,6 @@ int relay_recv_index(struct lttcomm_relayd_hdr *recv_hdr,
        uint64_t net_seq_num;
 
        assert(cmd);
-       assert(indexes_ht);
 
        DBG("Relay receiving index");
 
@@ -1711,7 +1711,7 @@ int relay_recv_index(struct lttcomm_relayd_hdr *recv_hdr,
                stream->beacon_ts_end = -1ULL;
        }
 
-       index = relay_index_find(stream->stream_handle, net_seq_num, indexes_ht);
+       index = relay_index_find(stream->stream_handle, net_seq_num);
        if (!index) {
                /* A successful creation will add the object to the HT. */
                index = relay_index_create(stream->stream_handle, net_seq_num);
@@ -1729,7 +1729,7 @@ int relay_recv_index(struct lttcomm_relayd_hdr *recv_hdr,
                 * already exist, destroy back the index created, set the data in this
                 * object and write it on disk.
                 */
-               relay_index_add(index, indexes_ht, &wr_index);
+               relay_index_add(index, &wr_index);
                if (wr_index) {
                        copy_index_control_data(wr_index, &index_info);
                        free(index);
@@ -1752,7 +1752,7 @@ int relay_recv_index(struct lttcomm_relayd_hdr *recv_hdr,
                        stream->index_fd = ret;
                }
 
-               ret = relay_index_write(wr_index->fd, wr_index, indexes_ht);
+               ret = relay_index_write(wr_index->fd, wr_index);
                if (ret < 0) {
                        goto end_rcu_unlock;
                }
@@ -1803,7 +1803,7 @@ int relay_process_control(struct lttcomm_relayd_hdr *recv_hdr,
                ret = relay_send_version(recv_hdr, cmd, ctx->sessions_ht);
                break;
        case RELAYD_CLOSE_STREAM:
-               ret = relay_close_stream(recv_hdr, cmd, ctx->viewer_streams_ht);
+               ret = relay_close_stream(recv_hdr, cmd);
                break;
        case RELAYD_DATA_PENDING:
                ret = relay_data_pending(recv_hdr, cmd);
@@ -1818,7 +1818,7 @@ int relay_process_control(struct lttcomm_relayd_hdr *recv_hdr,
                ret = relay_end_data_pending(recv_hdr, cmd);
                break;
        case RELAYD_SEND_INDEX:
-               ret = relay_recv_index(recv_hdr, cmd, indexes_ht);
+               ret = relay_recv_index(recv_hdr, cmd);
                break;
        case RELAYD_UPDATE_SYNC_INFO:
        default:
@@ -1836,8 +1836,7 @@ end:
  * relay_process_data: Process the data received on the data socket
  */
 static
-int relay_process_data(struct relay_command *cmd,
-               struct lttng_ht *indexes_ht, struct lttng_ht *viewer_streams_ht)
+int relay_process_data(struct relay_command *cmd)
 {
        int ret = 0, rotate_index = 0, index_created = 0;
        struct relay_stream *stream;
@@ -1924,7 +1923,7 @@ int relay_process_data(struct relay_command *cmd,
         * exists, the control thread already received the data for it thus we need
         * to write it on disk.
         */
-       index = relay_index_find(stream_id, net_seq_num, indexes_ht);
+       index = relay_index_find(stream_id, net_seq_num);
        if (!index) {
                /* A successful creation will add the object to the HT. */
                index = relay_index_create(stream->stream_handle, net_seq_num);
@@ -1954,7 +1953,7 @@ int relay_process_data(struct relay_command *cmd,
                 * Try to add the relay index object to the hash table. If an object
                 * already exist, destroy back the index created and set the data.
                 */
-               relay_index_add(index, indexes_ht, &wr_index);
+               relay_index_add(index, &wr_index);
                if (wr_index) {
                        /* Copy back data from the created index. */
                        wr_index->fd = index->fd;
@@ -1980,7 +1979,7 @@ int relay_process_data(struct relay_command *cmd,
                        stream->index_fd = ret;
                }
 
-               ret = relay_index_write(wr_index->fd, wr_index, indexes_ht);
+               ret = relay_index_write(wr_index->fd, wr_index);
                if (ret < 0) {
                        goto end_rcu_unlock;
                }
@@ -2009,7 +2008,7 @@ int relay_process_data(struct relay_command *cmd,
 
        /* Check if we need to close the FD */
        if (close_stream_check(stream)) {
-               close_stream(stream, viewer_streams_ht, cmd->ctf_traces_ht);
+               destroy_stream(stream, cmd->ctf_traces_ht);
        }
 
 end_rcu_unlock:
@@ -2311,8 +2310,7 @@ restart:
                                                continue;
                                        }
 
-                                       ret = relay_process_data(relay_connection, indexes_ht,
-                                                       relay_ctx->viewer_streams_ht);
+                                       ret = relay_process_data(relay_connection);
                                        /* connection closed */
                                        if (ret < 0) {
                                                relay_cleanup_poll_connection(&events, pollfd);
@@ -2356,7 +2354,7 @@ error_poll_create:
        {
                struct relay_index *index;
                cds_lfht_for_each_entry(indexes_ht->ht, &iter.iter, index, index_n.node) {
-                       relay_index_delete(index, indexes_ht);
+                       relay_index_delete(index);
                }
                lttng_ht_destroy(indexes_ht);
        }
@@ -2482,8 +2480,8 @@ int main(int argc, char **argv)
        }
 
        /* tables of streams indexed by stream ID */
-       relay_ctx->viewer_streams_ht = lttng_ht_new(0, LTTNG_HT_TYPE_U64);
-       if (!relay_ctx->viewer_streams_ht) {
+       viewer_streams_ht = lttng_ht_new(0, LTTNG_HT_TYPE_U64);
+       if (!viewer_streams_ht) {
                goto exit_relay_ctx_viewer_streams;
        }
 
@@ -2536,7 +2534,7 @@ exit_dispatcher:
                PERROR("pthread_join");
                goto error;     /* join error, exit without cleanup */
        }
-       lttng_ht_destroy(relay_ctx->viewer_streams_ht);
+       lttng_ht_destroy(viewer_streams_ht);
 
 exit_relay_ctx_viewer_streams:
        lttng_ht_destroy(relay_streams_ht);
This page took 0.027246 seconds and 4 git commands to generate.