X-Git-Url: https://git.lttng.org/?a=blobdiff_plain;f=src%2Fbin%2Flttng-sessiond%2Fust-app.c;h=56cbb8578544fa56c9f2e6bdf8085483f22064ec;hb=2bba9e532ca1910822005ff7f67400a2e871467c;hp=07c75031a63e493821ee688faca8951ba3501754;hpb=d5d629b58bff4ded0814e352d7dbdda6d1b6c9c2;p=lttng-tools.git diff --git a/src/bin/lttng-sessiond/ust-app.c b/src/bin/lttng-sessiond/ust-app.c index 07c75031a..56cbb8578 100644 --- a/src/bin/lttng-sessiond/ust-app.c +++ b/src/bin/lttng-sessiond/ust-app.c @@ -1440,6 +1440,7 @@ static void shadow_copy_session(struct ust_app_session *ua_sess, ua_sess->bits_per_long = app->bits_per_long; /* There is only one consumer object per session possible. */ ua_sess->consumer = usess->consumer; + ua_sess->output_traces = usess->output_traces; switch (ua_sess->buffer_type) { case LTTNG_BUFFER_PER_PID: @@ -1946,9 +1947,11 @@ static int do_consumer_create_channel(struct ltt_ust_session *usess, * Now get the channel from the consumer. This call wil populate the stream * list of that channel and set the ust objects. */ - ret = ust_consumer_get_channel(socket, ua_chan); - if (ret < 0) { - goto error_destroy; + if (usess->consumer->enabled) { + ret = ust_consumer_get_channel(socket, ua_chan); + if (ret < 0) { + goto error_destroy; + } } rcu_read_unlock(); @@ -2610,10 +2613,8 @@ static int create_ust_app_metadata(struct ust_app_session *ua_sess, ret = ust_consumer_ask_channel(ua_sess, metadata, consumer, socket, registry); if (ret < 0) { - /* - * Safe because the metadata obj pointer is not set so the delete below - * will not put a FD back again. - */ + /* Nullify the metadata key so we don't try to close it later on. */ + registry->metadata_key = 0; goto error_consumer; } @@ -2625,10 +2626,8 @@ static int create_ust_app_metadata(struct ust_app_session *ua_sess, */ ret = consumer_setup_metadata(socket, metadata->key); if (ret < 0) { - /* - * Safe because the metadata obj pointer is not set so the delete below - * will not put a FD back again. - */ + /* Nullify the metadata key so we don't try to close it later on. */ + registry->metadata_key = 0; goto error_consumer; } @@ -4847,3 +4846,66 @@ void ust_app_destroy(struct ust_app *app) call_rcu(&app->pid_n.head, delete_ust_app_rcu); } + +/* + * Take a snapshot for a given UST session. The snapshot is sent to the given + * output. + * + * Return 0 on success or else a negative value. + */ +int ust_app_snapshot_record(struct ltt_ust_session *usess, + struct snapshot_output *output, int wait) +{ + int ret = 0; + struct lttng_ht_iter iter; + struct ust_app *app; + + assert(usess); + assert(output); + + rcu_read_lock(); + + cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app, pid_n.node) { + struct consumer_socket *socket; + struct lttng_ht_iter chan_iter; + struct ust_app_channel *ua_chan; + struct ust_app_session *ua_sess; + struct ust_registry_session *registry; + + ua_sess = lookup_session_by_app(usess, app); + if (!ua_sess) { + /* Session not associated with this app. */ + continue; + } + + /* Get the right consumer socket for the application. */ + socket = consumer_find_socket_by_bitness(app->bits_per_long, + output->consumer); + if (!socket) { + ret = -EINVAL; + goto error; + } + + cds_lfht_for_each_entry(ua_sess->channels->ht, &chan_iter.iter, + ua_chan, node.node) { + ret = consumer_snapshot_channel(socket, ua_chan->key, output, 0, + ua_sess->euid, ua_sess->egid, wait); + if (ret < 0) { + goto error; + } + } + + registry = get_session_registry(ua_sess); + assert(registry); + ret = consumer_snapshot_channel(socket, registry->metadata_key, output, + 1, ua_sess->euid, ua_sess->egid, wait); + if (ret < 0) { + goto error; + } + + } + +error: + rcu_read_unlock(); + return ret; +}