ust-consumer.cpp ust-consumer.hpp notify-apps.cpp \
ust-metadata.cpp ust-clock.hpp agent-thread.cpp agent-thread.hpp \
ust-field-utils.hpp ust-field-utils.cpp \
- ust-sigbus.cpp
+ ust-sigbus.cpp \
+ ust-registry-session.cpp \
+ ust-registry-session-uid.cpp \
+ ust-registry-session-pid.cpp
+
endif
# link on liblttngctl for check if sessiond is already alive.
switch (domain) {
case LTTNG_DOMAIN_UST:
ust_registry_session_destroy(regp->reg.ust);
- free(regp->reg.ust);
break;
default:
abort();
switch (regp->domain) {
case LTTNG_DOMAIN_UST:
- if (regp->registry->reg.ust->metadata_key) {
+ if (regp->registry->reg.ust->_metadata_key) {
/* Return value does not matter. This call will print errors. */
(void) consumer_close_metadata(socket,
- regp->registry->reg.ust->metadata_key);
+ regp->registry->reg.ust->_metadata_key);
}
break;
default:
struct buffer_reg_session {
/* Registry per domain. */
union {
- struct ust_registry_session *ust;
+ ust_registry_session *ust;
} reg;
/* Contains buffer registry channel indexed by tracing channel key. */
rcu_read_lock();
cds_list_for_each_entry(uid_reg, &usess->buffer_reg_uid_list, lnode) {
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
struct ust_registry_channel *chan;
struct lttng_ht_iter iter_chan;
session_reg = uid_reg->registry;
registry = session_reg->reg.ust;
- pthread_mutex_lock(®istry->lock);
- registry->metadata_len_sent = 0;
- memset(registry->metadata, 0, registry->metadata_alloc_len);
- registry->metadata_len = 0;
- registry->metadata_version++;
- if (registry->metadata_fd > 0) {
+ pthread_mutex_lock(®istry->_lock);
+ registry->_metadata_len_sent = 0;
+ memset(registry->_metadata, 0, registry->_metadata_alloc_len);
+ registry->_metadata_len = 0;
+ registry->_metadata_version++;
+ if (registry->_metadata_fd > 0) {
/* Clear the metadata file's content. */
- ret = clear_metadata_file(registry->metadata_fd);
+ ret = clear_metadata_file(registry->_metadata_fd);
if (ret) {
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
goto end;
}
}
- ret = ust_metadata_session_statedump(registry, NULL,
- registry->major, registry->minor);
+ ret = ust_metadata_session_statedump(registry);
if (ret) {
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
ERR("Failed to generate session metadata (err = %d)",
ret);
goto end;
}
- cds_lfht_for_each_entry(registry->channels->ht, &iter_chan.iter,
+ cds_lfht_for_each_entry(registry->_channels->ht, &iter_chan.iter,
chan, node.node) {
struct ust_registry_event *event;
struct lttng_ht_iter iter_event;
ret = ust_metadata_channel_statedump(registry, chan);
if (ret) {
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
ERR("Failed to generate channel metadata "
"(err = %d)", ret);
goto end;
ret = ust_metadata_event_statedump(registry,
chan, event);
if (ret) {
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
ERR("Failed to generate event metadata "
"(err = %d)", ret);
goto end;
}
}
}
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
}
end:
* A registry per UID object MUST exists before calling this function or else
* it LTTNG_ASSERT() if not found. RCU read side lock must be acquired.
*/
-static struct ust_registry_session *get_session_registry(
+static ust_registry_session *get_session_registry(
struct ust_app_session *ua_sess)
{
- struct ust_registry_session *registry = NULL;
+ ust_registry_session *registry = NULL;
LTTNG_ASSERT(ua_sess);
struct ust_app_event *ua_event;
struct ust_app_ctx *ua_ctx;
struct ust_app_stream *stream, *stmp;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
LTTNG_ASSERT(ua_chan);
ASSERT_RCU_READ_LOCKED();
* but it can be caused by recoverable errors (e.g. the application has
* terminated concurrently).
*/
-ssize_t ust_app_push_metadata(struct ust_registry_session *registry,
+ssize_t ust_app_push_metadata(ust_registry_session *registry,
struct consumer_socket *socket, int send_zero_data)
{
int ret;
LTTNG_ASSERT(socket);
ASSERT_RCU_READ_LOCKED();
- metadata_key = registry->metadata_key;
+ metadata_key = registry->_metadata_key;
/*
* Means that no metadata was assigned to the session. This can
return 0;
}
- offset = registry->metadata_len_sent;
- len = registry->metadata_len - registry->metadata_len_sent;
- new_metadata_len_sent = registry->metadata_len;
- metadata_version = registry->metadata_version;
+ offset = registry->_metadata_len_sent;
+ len = registry->_metadata_len - registry->_metadata_len_sent;
+ new_metadata_len_sent = registry->_metadata_len;
+ metadata_version = registry->_metadata_version;
if (len == 0) {
DBG3("No metadata to push for metadata key %" PRIu64,
- registry->metadata_key);
+ registry->_metadata_key);
ret_val = len;
if (send_zero_data) {
DBG("No metadata to push");
goto error;
}
/* Copy what we haven't sent out. */
- memcpy(metadata_str, registry->metadata + offset, len);
+ memcpy(metadata_str, registry->_metadata + offset, len);
push_data:
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
/*
* We need to unlock the registry while we push metadata to
* break a circular dependency between the consumerd metadata
*/
ret = consumer_push_metadata(socket, metadata_key,
metadata_str, len, offset, metadata_version);
- pthread_mutex_lock(®istry->lock);
+ pthread_mutex_lock(®istry->_lock);
if (ret < 0) {
/*
* There is an acceptable race here between the registry
* largest metadata_len_sent value of the concurrent
* send.
*/
- registry->metadata_len_sent =
- std::max(registry->metadata_len_sent,
+ registry->_metadata_len_sent =
+ std::max(registry->_metadata_len_sent,
new_metadata_len_sent);
}
free(metadata_str);
* the metadata cache has been destroyed on the
* consumer.
*/
- registry->metadata_closed = 1;
+ registry->_metadata_closed = true;
}
error_push:
free(metadata_str);
* but it can be caused by recoverable errors (e.g. the application has
* terminated concurrently).
*/
-static int push_metadata(struct ust_registry_session *registry,
+static int push_metadata(ust_registry_session *registry,
struct consumer_output *consumer)
{
int ret_val;
LTTNG_ASSERT(consumer);
ASSERT_RCU_READ_LOCKED();
- pthread_mutex_lock(®istry->lock);
- if (registry->metadata_closed) {
+ pthread_mutex_lock(®istry->_lock);
+ if (registry->_metadata_closed) {
ret_val = -EPIPE;
goto error;
}
/* Get consumer socket to use to push the metadata.*/
- socket = consumer_find_socket_by_bitness(registry->bits_per_long,
+ socket = consumer_find_socket_by_bitness(registry->_bits_per_long,
consumer);
if (!socket) {
ret_val = -1;
ret_val = ret;
goto error;
}
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
return 0;
error:
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
return ret_val;
}
*
* Return 0 on success else a negative value.
*/
-static int close_metadata(struct ust_registry_session *registry,
+static int close_metadata(ust_registry_session *registry,
struct consumer_output *consumer)
{
int ret;
rcu_read_lock();
- pthread_mutex_lock(®istry->lock);
- metadata_key = registry->metadata_key;
- registry_was_already_closed = registry->metadata_closed;
+ pthread_mutex_lock(®istry->_lock);
+ metadata_key = registry->_metadata_key;
+ registry_was_already_closed = registry->_metadata_closed;
if (metadata_key != 0) {
/*
* Metadata closed. Even on error this means that the consumer
* is not responding or not found so either way a second close
* should NOT be emit for this registry.
*/
- registry->metadata_closed = 1;
+ registry->_metadata_closed = true;
}
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
if (metadata_key == 0 || registry_was_already_closed) {
ret = 0;
}
/* Get consumer socket to use to push the metadata.*/
- socket = consumer_find_socket_by_bitness(registry->bits_per_long,
+ socket = consumer_find_socket_by_bitness(registry->_bits_per_long,
consumer);
if (!socket) {
ret = -1;
int ret;
struct lttng_ht_iter iter;
struct ust_app_channel *ua_chan;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
LTTNG_ASSERT(ua_sess);
ASSERT_RCU_READ_LOCKED();
}
/* Initialize registry. */
- ret = ust_registry_session_init(®_pid->registry->reg.ust, app,
+ reg_pid->registry->reg.ust = ust_registry_session_per_pid_create(app,
app->bits_per_long, app->uint8_t_alignment,
app->uint16_t_alignment, app->uint32_t_alignment,
app->uint64_t_alignment, app->long_alignment,
reg_pid->root_shm_path, reg_pid->shm_path,
lttng_credentials_get_uid(&ua_sess->effective_credentials),
lttng_credentials_get_gid(&ua_sess->effective_credentials),
- ua_sess->tracing_id,
- app->uid);
- if (ret < 0) {
+ ua_sess->tracing_id);
+ if (!reg_pid->registry->reg.ust) {
/*
* reg_pid->registry->reg.ust is NULL upon error, so we need to
* destroy the buffer registry, because it is always expected
}
/* Initialize registry. */
- ret = ust_registry_session_init(®_uid->registry->reg.ust, NULL,
+ reg_uid->registry->reg.ust = ust_registry_session_per_uid_create(
app->bits_per_long, app->uint8_t_alignment,
app->uint16_t_alignment, app->uint32_t_alignment,
app->uint64_t_alignment, app->long_alignment,
app->version.minor, reg_uid->root_shm_path,
reg_uid->shm_path, usess->uid, usess->gid,
ua_sess->tracing_id, app->uid);
- if (ret < 0) {
+ if (!reg_uid->registry->reg.ust) {
/*
* reg_uid->registry->reg.ust is NULL upon error, so we need to
* destroy the buffer registry, because it is always expected
buffer_reg_uid_destroy(reg_uid, NULL);
goto error;
}
+
/* Add node to teardown list of the session. */
cds_list_add(®_uid->lnode, &usess->buffer_reg_uid_list);
*/
static int do_consumer_create_channel(struct ltt_ust_session *usess,
struct ust_app_session *ua_sess, struct ust_app_channel *ua_chan,
- int bitness, struct ust_registry_session *registry)
+ int bitness, ust_registry_session *registry)
{
int ret;
unsigned int nb_fd = 0;
}
/* Notify the notification subsystem of the channel's creation. */
- pthread_mutex_lock(®_uid->registry->reg.ust->lock);
+ pthread_mutex_lock(®_uid->registry->reg.ust->_lock);
ust_reg_chan = ust_registry_channel_find(reg_uid->registry->reg.ust,
ua_chan->tracing_channel_id);
LTTNG_ASSERT(ust_reg_chan);
ust_reg_chan->consumer_key = ua_chan->key;
ust_reg_chan = NULL;
- pthread_mutex_unlock(®_uid->registry->reg.ust->lock);
+ pthread_mutex_unlock(®_uid->registry->reg.ust->_lock);
notification_ret = notification_thread_command_add_channel(
the_notification_thread_handle, session->name,
struct ust_app_channel *ua_chan)
{
int ret;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
enum lttng_error_code cmd_ret;
struct ltt_session *session = NULL;
uint64_t chan_reg_key;
}
chan_reg_key = ua_chan->key;
- pthread_mutex_lock(®istry->lock);
+ pthread_mutex_lock(®istry->_lock);
ust_reg_chan = ust_registry_channel_find(registry, chan_reg_key);
LTTNG_ASSERT(ust_reg_chan);
ust_reg_chan->consumer_key = ua_chan->key;
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
cmd_ret = notification_thread_command_add_channel(
the_notification_thread_handle, session->name,
int ret = 0;
struct ust_app_channel *metadata;
struct consumer_socket *socket;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
struct ltt_session *session = NULL;
LTTNG_ASSERT(ua_sess);
/* The UST app session is held registry shall not be null. */
LTTNG_ASSERT(registry);
- pthread_mutex_lock(®istry->lock);
+ pthread_mutex_lock(®istry->_lock);
/* Metadata already exists for this registry or it was closed previously */
- if (registry->metadata_key || registry->metadata_closed) {
+ if (registry->_metadata_key || registry->_metadata_closed) {
ret = 0;
goto error;
}
* consumer requesting the metadata and the ask_channel call on our side
* did not returned yet.
*/
- registry->metadata_key = metadata->key;
+ registry->_metadata_key = metadata->key;
session = session_find_by_id(ua_sess->tracing_id);
LTTNG_ASSERT(session);
registry, session->current_trace_chunk);
if (ret < 0) {
/* Nullify the metadata key so we don't try to close it later on. */
- registry->metadata_key = 0;
+ registry->_metadata_key = 0;
goto error_consumer;
}
ret = consumer_setup_metadata(socket, metadata->key);
if (ret < 0) {
/* Nullify the metadata key so we don't try to close it later on. */
- registry->metadata_key = 0;
+ registry->_metadata_key = 0;
goto error_consumer;
}
lttng_fd_put(LTTNG_FD_APPS, 1);
delete_ust_app_channel(-1, metadata, app);
error:
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
if (session) {
session_put(session);
}
*/
cds_lfht_for_each_entry(lta->sessions->ht, &iter.iter, ua_sess,
node.node) {
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
ret = lttng_ht_del(lta->sessions, &iter);
if (ret) {
{
int ret = 0;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
DBG("Stopping tracing for ust app pid %d", app->pid);
/* Flush all per UID buffers associated to that session. */
cds_list_for_each_entry(reg, &usess->buffer_reg_uid_list, lnode) {
- struct ust_registry_session *ust_session_reg;
+ ust_registry_session *ust_session_reg;
struct buffer_reg_channel *buf_reg_chan;
struct consumer_socket *socket;
struct ust_app *app;
struct ust_app_channel *ua_chan;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
struct ust_registry_channel *ust_reg_chan;
rcu_read_lock();
chan_reg_key = ua_chan->key;
}
- pthread_mutex_lock(®istry->lock);
+ pthread_mutex_lock(®istry->_lock);
ust_reg_chan = ust_registry_channel_find(registry, chan_reg_key);
LTTNG_ASSERT(ust_reg_chan);
ust_reg_chan->register_done = 1;
error:
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
error_rcu_unlock:
rcu_read_unlock();
free(fields);
struct ust_app *app;
struct ust_app_channel *ua_chan;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
rcu_read_lock();
chan_reg_key = ua_chan->key;
}
- pthread_mutex_lock(®istry->lock);
+ pthread_mutex_lock(®istry->_lock);
/*
* From this point on, this call acquires the ownership of the sig, fields
name, event_id);
error:
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
error_rcu_unlock:
rcu_read_unlock();
free(sig);
int ret = 0, ret_code;
struct ust_app *app;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
uint64_t enum_id = -1ULL;
rcu_read_lock();
goto error_rcu_unlock;
}
- pthread_mutex_lock(®istry->lock);
+ pthread_mutex_lock(®istry->_lock);
/*
* From this point on, the callee acquires the ownership of
DBG3("UST registry enum %s added successfully or already found", name);
error:
- pthread_mutex_unlock(®istry->lock);
+ pthread_mutex_unlock(®istry->_lock);
error_rcu_unlock:
rcu_read_unlock();
return ret;
char pathname[PATH_MAX];
size_t consumer_path_offset = 0;
- if (!reg->registry->reg.ust->metadata_key) {
+ if (!reg->registry->reg.ust->_metadata_key) {
/* Skip since no metadata is present */
continue;
}
}
}
status = consumer_snapshot_channel(socket,
- reg->registry->reg.ust->metadata_key, output, 1,
+ reg->registry->reg.ust->_metadata_key, output, 1,
&trace_path[consumer_path_offset], 0);
if (status != LTTNG_OK) {
goto error;
struct lttng_ht_iter chan_iter;
struct ust_app_channel *ua_chan;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
char pathname[PATH_MAX];
size_t consumer_path_offset = 0;
continue;
}
status = consumer_snapshot_channel(socket,
- registry->metadata_key, output, 1,
+ registry->_metadata_key, output, 1,
&trace_path[consumer_path_offset], 0);
switch (status) {
case LTTNG_OK:
* operations (i.e add context) and lead to data
* channels created with no metadata channel.
*/
- if (!reg->registry->reg.ust->metadata_key) {
+ if (!reg->registry->reg.ust->_metadata_key) {
/* Skip since no metadata is present. */
continue;
}
(void) push_metadata(reg->registry->reg.ust, usess->consumer);
ret = consumer_rotate_channel(socket,
- reg->registry->reg.ust->metadata_key,
+ reg->registry->reg.ust->_metadata_key,
usess->consumer,
/* is_metadata_channel */ true);
if (ret < 0) {
struct lttng_ht_iter chan_iter;
struct ust_app_channel *ua_chan;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
ua_sess = lookup_session_by_app(usess, app);
if (!ua_sess) {
/* Rotate the metadata channel. */
(void) push_metadata(registry, usess->consumer);
ret = consumer_rotate_channel(socket,
- registry->metadata_key,
+ registry->_metadata_key,
ua_sess->consumer,
/* is_metadata_channel */ true);
if (ret < 0) {
cds_lfht_for_each_entry(ust_app_ht->ht, &iter.iter, app,
pid_n.node) {
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
ua_sess = lookup_session_by_app(usess, app);
if (!ua_sess) {
* perform a rotation operation on it behind the scene.
*/
ret = consumer_clear_channel(socket,
- reg->registry->reg.ust->metadata_key);
+ reg->registry->reg.ust->_metadata_key);
if (ret < 0) {
goto error;
}
struct lttng_ht_iter chan_iter;
struct ust_app_channel *ua_chan;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
ua_sess = lookup_session_by_app(usess, app);
if (!ua_sess) {
* Metadata channel is not cleared per se but we still need to
* perform rotation operation on it behind the scene.
*/
- ret = consumer_clear_channel(socket, registry->metadata_key);
+ ret = consumer_clear_channel(socket, registry->_metadata_key);
if (ret < 0) {
/* Per-PID buffer and application going away. */
if (ret == -LTTNG_ERR_CHAN_NOT_FOUND) {
struct lttng_ht_iter chan_iter;
struct ust_app_channel *ua_chan;
struct ust_app_session *ua_sess;
- struct ust_registry_session *registry;
+ ust_registry_session *registry;
ua_sess = lookup_session_by_app(usess, app);
if (!ua_sess) {
void ust_app_add(struct ust_app *app);
struct ust_app *ust_app_create(struct ust_register_msg *msg, int sock);
void ust_app_notify_sock_unregister(int sock);
-ssize_t ust_app_push_metadata(struct ust_registry_session *registry,
+ssize_t ust_app_push_metadata(ust_registry_session *registry,
struct consumer_socket *socket, int send_zero_data);
void ust_app_destroy(struct ust_app *app);
enum lttng_error_code ust_app_snapshot_record(
static inline
ssize_t ust_app_push_metadata(
- struct ust_registry_session *registry __attribute__((unused)),
+ ust_registry_session *registry __attribute__((unused)),
struct consumer_socket *socket __attribute__((unused)),
int send_zero_data __attribute__((unused)))
{
struct ust_app_channel *ua_chan,
struct consumer_output *consumer,
struct consumer_socket *socket,
- struct ust_registry_session *registry,
+ ust_registry_session *registry,
struct lttng_trace_chunk *trace_chunk)
{
int ret, output;
ua_chan->name,
consumer->net_seq_index,
ua_chan->key,
- registry->uuid,
+ registry->_uuid,
chan_id,
ua_chan->tracefile_size,
ua_chan->tracefile_count,
struct ust_app_channel *ua_chan,
struct consumer_output *consumer,
struct consumer_socket *socket,
- struct ust_registry_session *registry,
+ ust_registry_session *registry,
struct lttng_trace_chunk * trace_chunk)
{
int ret;
ssize_t ret_push;
struct lttcomm_metadata_request_msg request;
struct buffer_reg_uid *reg_uid;
- struct ust_registry_session *ust_reg;
+ ust_registry_session *ust_reg;
struct lttcomm_consumer_msg msg;
LTTNG_ASSERT(socket);
}
LTTNG_ASSERT(ust_reg);
- pthread_mutex_lock(&ust_reg->lock);
+ pthread_mutex_lock(&ust_reg->_lock);
ret_push = ust_app_push_metadata(ust_reg, socket, 1);
- pthread_mutex_unlock(&ust_reg->lock);
+ pthread_mutex_unlock(&ust_reg->_lock);
if (ret_push == -EPIPE) {
DBG("Application or relay closed while pushing metadata");
} else if (ret_push < 0) {
struct ust_app_channel *ua_chan,
struct consumer_output *consumer,
struct consumer_socket *socket,
- struct ust_registry_session *registry,
+ ust_registry_session *registry,
struct lttng_trace_chunk *trace_chunk);
int ust_consumer_get_channel(struct consumer_socket *socket,
} /* namespace */
static
-int _lttng_field_statedump(struct ust_registry_session *session,
+int _lttng_field_statedump(ust_registry_session *session,
const struct lttng_ust_ctl_field *fields, size_t nr_fields,
size_t *iter_field, size_t nesting);
* Returns offset where to write in metadata array, or negative error value on error.
*/
static
-ssize_t metadata_reserve(struct ust_registry_session *session, size_t len)
+ssize_t metadata_reserve(ust_registry_session *session, size_t len)
{
- size_t new_len = session->metadata_len + len;
+ size_t new_len = session->_metadata_len + len;
size_t new_alloc_len = new_len;
- size_t old_alloc_len = session->metadata_alloc_len;
+ size_t old_alloc_len = session->_metadata_alloc_len;
ssize_t ret;
if (new_alloc_len > (UINT32_MAX >> 1))
new_alloc_len =
std::max<size_t>(1U << get_count_order(new_alloc_len), old_alloc_len << 1);
- newptr = (char *) realloc(session->metadata, new_alloc_len);
+ newptr = (char *) realloc(session->_metadata, new_alloc_len);
if (!newptr)
return -ENOMEM;
- session->metadata = newptr;
+ session->_metadata = newptr;
/* We zero directly the memory from start of allocation. */
- memset(&session->metadata[old_alloc_len], 0, new_alloc_len - old_alloc_len);
- session->metadata_alloc_len = new_alloc_len;
+ memset(&session->_metadata[old_alloc_len], 0, new_alloc_len - old_alloc_len);
+ session->_metadata_alloc_len = new_alloc_len;
}
- ret = session->metadata_len;
- session->metadata_len += len;
+ ret = session->_metadata_len;
+ session->_metadata_len += len;
return ret;
}
static
-int metadata_file_append(struct ust_registry_session *session,
+int metadata_file_append(ust_registry_session *session,
const char *str, size_t len)
{
ssize_t written;
- if (session->metadata_fd < 0) {
+ if (session->_metadata_fd < 0) {
return 0;
}
/* Write to metadata file */
- written = lttng_write(session->metadata_fd, str, len);
+ written = lttng_write(session->_metadata_fd, str, len);
if (written != len) {
return -1;
}
* protects us from concurrent writes.
*/
static ATTR_FORMAT_PRINTF(2, 3)
-int lttng_metadata_printf(struct ust_registry_session *session,
+int lttng_metadata_printf(ust_registry_session *session,
const char *fmt, ...)
{
char *str = NULL;
ret = offset;
goto end;
}
- memcpy(&session->metadata[offset], str, len);
+ memcpy(&session->_metadata[offset], str, len);
ret = metadata_file_append(session, str, len);
if (ret) {
PERROR("Error appending to metadata file");
}
static
-int print_tabs(struct ust_registry_session *session, size_t nesting)
+int print_tabs(ust_registry_session *session, size_t nesting)
{
size_t i;
}
static
-int print_escaped_ctf_string(struct ust_registry_session *session, const char *string)
+int print_escaped_ctf_string(ust_registry_session *session, const char *string)
{
int ret = 0;
size_t i;
/* Called with session registry mutex held. */
static
-int ust_metadata_enum_statedump(struct ust_registry_session *session,
+int ust_metadata_enum_statedump(ust_registry_session *session,
const char *enum_name,
uint64_t enum_id,
const struct lttng_ust_ctl_integer_type *container_type,
}
static
-int _lttng_variant_statedump(struct ust_registry_session *session,
+int _lttng_variant_statedump(ust_registry_session *session,
uint32_t nr_choices, const char *tag_name,
uint32_t alignment,
const struct lttng_ust_ctl_field *fields, size_t nr_fields,
}
static
-int _lttng_field_statedump(struct ust_registry_session *session,
+int _lttng_field_statedump(ust_registry_session *session,
const struct lttng_ust_ctl_field *fields, size_t nr_fields,
size_t *iter_field, size_t nesting)
{
}
field = &fields[*iter_field];
- if (session->byte_order == BIG_ENDIAN) {
+ if (session->_byte_order == BIG_ENDIAN) {
bo_reverse = bo_le;
} else {
bo_reverse = bo_be;
}
static
-int _lttng_context_metadata_statedump(struct ust_registry_session *session,
+int _lttng_context_metadata_statedump(ust_registry_session *session,
size_t nr_ctx_fields,
struct lttng_ust_ctl_field *ctx)
{
}
static
-int _lttng_fields_metadata_statedump(struct ust_registry_session *session,
+int _lttng_fields_metadata_statedump(ust_registry_session *session,
struct ust_registry_event *event)
{
int ret = 0;
/*
* Should be called with session registry mutex held.
*/
-int ust_metadata_event_statedump(struct ust_registry_session *session,
+int ust_metadata_event_statedump(ust_registry_session *session,
struct ust_registry_channel *chan,
struct ust_registry_event *event)
{
*
* RCU read lock must be held by the caller.
*/
-int ust_metadata_channel_statedump(struct ust_registry_session *session,
+int ust_metadata_channel_statedump(ust_registry_session *session,
struct ust_registry_channel *chan)
{
int ret;
}
static
-int _lttng_stream_packet_context_declare(struct ust_registry_session *session)
+int _lttng_stream_packet_context_declare(ust_registry_session *session)
{
return lttng_metadata_printf(session,
"struct packet_context {\n"
* id 65535 is reserved to indicate an extended header.
*/
static
-int _lttng_event_header_declare(struct ust_registry_session *session)
+int _lttng_event_header_declare(ust_registry_session *session)
{
return lttng_metadata_printf(session,
"struct event_header_compact {\n"
" } extended;\n"
" } v;\n"
"} align(%u);\n\n",
- session->uint32_t_alignment,
- session->uint16_t_alignment
+ session->_uint32_t_alignment,
+ session->_uint16_t_alignment
);
}
}
static
-int print_metadata_session_information(struct ust_registry_session *registry)
+int print_metadata_session_information(ust_registry_session *registry)
{
int ret;
struct ltt_session *session = NULL;
char creation_datetime[ISO8601_STR_LEN];
rcu_read_lock();
- session = session_find_by_id(registry->tracing_id);
+ session = session_find_by_id(registry->_tracing_id);
if (!session) {
ret = -1;
goto error;
}
static
-int print_metadata_app_information(struct ust_registry_session *registry,
- struct ust_app *app)
+int print_metadata_app_information(ust_registry_session *registry)
{
- int ret;
- char datetime[ISO8601_STR_LEN];
-
- if (!app) {
- ret = 0;
- goto end;
+ if (registry->get_buffering_scheme() != LTTNG_BUFFER_PER_PID) {
+ return 0;
}
- ret = time_to_iso8601_str(
- app->registration_time, datetime, sizeof(datetime));
+ const auto *per_pid_session = static_cast<const ust_registry_session_per_pid *>(registry);
+
+ char datetime[ISO8601_STR_LEN];
+ int ret = time_to_iso8601_str(
+ per_pid_session->_app_creation_time, datetime, sizeof(datetime));
if (ret) {
- goto end;
+ return ret;
}
ret = lttng_metadata_printf(registry,
- " tracer_patchlevel = %u;\n"
- " vpid = %d;\n"
- " procname = \"%s\";\n"
- " vpid_datetime = \"%s\";\n",
- app->version.patchlevel, (int) app->pid, app->name,
- datetime);
-
-end:
+ " tracer_patchlevel = %u;\n"
+ " vpid = %d;\n"
+ " procname = \"%s\";\n"
+ " vpid_datetime = \"%s\";\n",
+ per_pid_session->_tracer_patch_level_version, (int) per_pid_session->_vpid,
+ per_pid_session->_procname.c_str(), datetime);
return ret;
}
/*
* Should be called with session registry mutex held.
*/
-int ust_metadata_session_statedump(struct ust_registry_session *session,
- struct ust_app *app,
- uint32_t major,
- uint32_t minor)
+int ust_metadata_session_statedump(ust_registry_session *session)
{
- char uuid_s[LTTNG_UUID_STR_LEN],
- clock_uuid_s[LTTNG_UUID_STR_LEN];
+ char uuid_s[LTTNG_UUID_STR_LEN], clock_uuid_s[LTTNG_UUID_STR_LEN];
int ret = 0;
LTTNG_ASSERT(session);
- lttng_uuid_to_str(session->uuid, uuid_s);
+ lttng_uuid_to_str(session->_uuid, uuid_s);
/* For crash ABI */
ret = lttng_metadata_printf(session,
" uint64_t stream_instance_id;\n"
" };\n"
"};\n\n",
- session->uint8_t_alignment,
- session->uint16_t_alignment,
- session->uint32_t_alignment,
- session->uint64_t_alignment,
- session->bits_per_long,
- session->long_alignment,
+ session->_uint8_t_alignment,
+ session->_uint16_t_alignment,
+ session->_uint32_t_alignment,
+ session->_uint64_t_alignment,
+ session->_bits_per_long,
+ session->_long_alignment,
CTF_SPEC_MAJOR,
CTF_SPEC_MINOR,
uuid_s,
- session->byte_order == BIG_ENDIAN ? "be" : "le"
+ session->_byte_order == BIG_ENDIAN ? "be" : "le"
);
if (ret) {
goto end;
" tracer_buffering_scheme = \"%s\";\n"
" tracer_buffering_id = %u;\n"
" architecture_bit_width = %u;\n",
- major,
- minor,
- app ? "pid" : "uid",
- app ? (int) app->pid : (int) session->tracing_uid,
- session->bits_per_long);
+ session->_app_tracer_version_major, session->_app_tracer_version_minor,
+ session->get_buffering_scheme() == LTTNG_BUFFER_PER_PID ? "pid" : "uid",
+ session->get_buffering_scheme() == LTTNG_BUFFER_PER_PID ?
+ (int) static_cast<ust_registry_session_per_pid *>(session)->_vpid :
+ (int) static_cast<ust_registry_session_per_uid *>(session)->_tracing_uid,
+ session->_bits_per_long);
if (ret) {
goto end;
}
* If per-application registry, we can output extra information
* about the application.
*/
- ret = print_metadata_app_information(session, app);
+ ret = print_metadata_app_information(session);
if (ret) {
goto end;
}
" map = clock.%s.value;\n"
"} := uint64_clock_monotonic_t;\n\n",
trace_clock_name(),
- session->uint32_t_alignment,
+ session->_uint32_t_alignment,
trace_clock_name(),
- session->uint64_t_alignment,
+ session->_uint64_t_alignment,
trace_clock_name()
);
if (ret) {
--- /dev/null
+/*
+ * Copyright (C) 2022 Jérémie Galarneau <jeremie.galarneau@efficios.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0-only
+ *
+ */
+
+#include "ust-app.hpp"
+#include "ust-registry.hpp"
+
+ust_registry_session_per_pid::ust_registry_session_per_pid(const struct ust_app &app,
+ uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id) :
+ ust_registry_session{bits_per_long, uint8_t_alignment, uint16_t_alignment,
+ uint32_t_alignment, uint64_t_alignment, long_alignment, byte_order, major,
+ minor, root_shm_path, shm_path, euid, egid, tracing_id},
+ _tracer_patch_level_version{app.version.patchlevel},
+ _vpid{app.pid},
+ _procname{app.name},
+ _app_creation_time{app.registration_time}
+{
+ statedump();
+}
+
+lttng_buffer_type ust_registry_session_per_pid::get_buffering_scheme() const noexcept
+{
+ return LTTNG_BUFFER_PER_PID;
+}
--- /dev/null
+/*
+ * Copyright (C) 2022 Jérémie Galarneau <jeremie.galarneau@efficios.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0-only
+ *
+ */
+
+#include "ust-registry.hpp"
+
+ust_registry_session_per_uid::ust_registry_session_per_uid(uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id,
+ uid_t tracing_uid) :
+ ust_registry_session{bits_per_long, uint8_t_alignment, uint16_t_alignment,
+ uint32_t_alignment, uint64_t_alignment, long_alignment, byte_order, major,
+ minor, root_shm_path, shm_path, euid, egid, tracing_id},
+ _tracing_uid{tracing_uid}
+{
+ statedump();
+}
+
+lttng_buffer_type ust_registry_session_per_uid::get_buffering_scheme() const noexcept
+{
+ return LTTNG_BUFFER_PER_UID;
+}
--- /dev/null
+/*
+ * Copyright (C) 2022 Jérémie Galarneau <jeremie.galarneau@efficios.com>
+ *
+ * SPDX-License-Identifier: GPL-2.0-only
+ *
+ */
+
+#include "ust-registry.hpp"
+
+#include <common/compat/directory-handle.hpp>
+#include <common/error.hpp>
+#include <common/exception.hpp>
+#include <common/runas.hpp>
+
+#include <fcntl.h>
+#include <sstream>
+#include <string>
+
+ust_registry_session::ust_registry_session(uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id) :
+ _bits_per_long{bits_per_long},
+ _uint8_t_alignment{uint8_t_alignment},
+ _uint16_t_alignment{uint16_t_alignment},
+ _uint32_t_alignment{uint32_t_alignment},
+ _uint64_t_alignment{uint64_t_alignment},
+ _long_alignment{long_alignment},
+ _byte_order{byte_order},
+ _uid{euid},
+ _gid{egid},
+ _app_tracer_version_major{major},
+ _app_tracer_version_minor{minor},
+ _tracing_id{tracing_id}
+{
+ pthread_mutex_init(&_lock, NULL);
+ strncpy(_root_shm_path, root_shm_path, sizeof(_root_shm_path));
+ _root_shm_path[sizeof(_root_shm_path) - 1] = '\0';
+ if (shm_path[0]) {
+ strncpy(_shm_path, shm_path, sizeof(_shm_path));
+ _shm_path[sizeof(_shm_path) - 1] = '\0';
+ strncpy(_metadata_path, shm_path, sizeof(_metadata_path));
+ _metadata_path[sizeof(_metadata_path) - 1] = '\0';
+ strncat(_metadata_path, "/metadata",
+ sizeof(_metadata_path) - strlen(_metadata_path) - 1);
+ }
+
+ if (_shm_path[0]) {
+ if (run_as_mkdir_recursive(_shm_path, S_IRWXU | S_IRWXG, euid, egid)) {
+ LTTNG_THROW_POSIX("run_as_mkdir_recursive", errno);
+ }
+ }
+
+ if (_metadata_path[0]) {
+ /* Create metadata file. */
+ const int ret = run_as_open(_metadata_path, O_WRONLY | O_CREAT | O_EXCL,
+ S_IRUSR | S_IWUSR, euid, egid);
+
+ if (ret < 0) {
+ std::stringstream ss;
+
+ ss << "Opening metadata file '" << _metadata_path << "'";
+ LTTNG_THROW_POSIX(ss.str(), errno);
+ }
+
+ _metadata_fd = ret;
+ }
+
+ _enums.reset(lttng_ht_new(0, LTTNG_HT_TYPE_STRING));
+ if (!_enums) {
+ LTTNG_THROW_POSIX("Failed to create enums hash table", ENOMEM);
+ }
+
+ /* hash/match functions are specified at call site. */
+ _enums->match_fct = NULL;
+ _enums->hash_fct = NULL;
+
+ _channels.reset(lttng_ht_new(0, LTTNG_HT_TYPE_U64));
+ if (!_channels) {
+ LTTNG_THROW_POSIX("Failed to create channels hash table", ENOMEM);
+ }
+
+ if (lttng_uuid_generate(_uuid)) {
+ LTTNG_THROW_POSIX("Failed to generate UST uuid", errno);
+ }
+}
+
+ust_registry_session::~ust_registry_session()
+{
+ int ret;
+ struct lttng_ht_iter iter;
+ struct ust_registry_channel *chan;
+ struct ust_registry_enum *reg_enum;
+
+ /* On error, EBUSY can be returned if lock. Code flow error. */
+ ret = pthread_mutex_destroy(&_lock);
+ LTTNG_ASSERT(!ret);
+
+ if (_channels) {
+ rcu_read_lock();
+ /* Destroy all event associated with this registry. */
+ cds_lfht_for_each_entry (_channels->ht, &iter.iter, chan, node.node) {
+ /* Delete the node from the ht and free it. */
+ ret = lttng_ht_del(_channels.get(), &iter);
+ LTTNG_ASSERT(!ret);
+ ust_registry_channel_destroy(chan, true);
+ }
+
+ rcu_read_unlock();
+ }
+
+ free(_metadata);
+ if (_metadata_fd >= 0) {
+ ret = close(_metadata_fd);
+ if (ret) {
+ PERROR("close");
+ }
+
+ ret = run_as_unlink(_metadata_path, _uid, _gid);
+ if (ret) {
+ PERROR("unlink");
+ }
+ }
+
+ if (_root_shm_path[0]) {
+ /* Try to delete the directory hierarchy. */
+ (void) run_as_rmdir_recursive(_root_shm_path, _uid, _gid,
+ LTTNG_DIRECTORY_HANDLE_SKIP_NON_EMPTY_FLAG);
+ }
+
+ /* Destroy the enum hash table */
+ if (_enums) {
+ rcu_read_lock();
+ /* Destroy all enum entries associated with this registry. */
+ cds_lfht_for_each_entry (_enums->ht, &iter.iter, reg_enum, node.node) {
+ ust_registry_destroy_enum(this, reg_enum);
+ }
+
+ rcu_read_unlock();
+ }
+}
+
+void ust_registry_session::statedump()
+{
+ pthread_mutex_lock(&_lock);
+ const int ret = ust_metadata_session_statedump(this);
+ pthread_mutex_unlock(&_lock);
+ if (ret) {
+ LTTNG_THROW_ERROR(
+ "Failed to generate session metadata during registry session creation");
+ }
+}
#include <common/common.hpp>
#include <common/hashtable/utils.hpp>
+#include <common/exception.hpp>
#include <lttng/lttng.h>
#include "ust-registry.hpp"
*
* Should be called with session registry mutex held.
*/
-int ust_registry_create_event(struct ust_registry_session *session,
+int ust_registry_create_event(ust_registry_session *session,
uint64_t chan_key, int session_objd, int channel_objd, char *name,
char *sig, size_t nr_fields, struct lttng_ust_ctl_field *fields,
int loglevel_value, char *model_emf_uri, int buffer_type,
* Needs to be called from RCU read-side critical section.
*/
static struct ust_registry_enum *ust_registry_lookup_enum(
- struct ust_registry_session *session,
+ ust_registry_session *session,
const struct ust_registry_enum *reg_enum_lookup)
{
struct ust_registry_enum *reg_enum = NULL;
ASSERT_RCU_READ_LOCKED();
- cds_lfht_lookup(session->enums->ht,
+ cds_lfht_lookup(session->_enums->ht,
ht_hash_enum((void *) reg_enum_lookup, lttng_ht_seed),
ht_match_enum, reg_enum_lookup, &iter.iter);
node = lttng_ht_iter_get_node_str(&iter);
* Needs to be called from RCU read-side critical section.
*/
struct ust_registry_enum *
- ust_registry_lookup_enum_by_id(struct ust_registry_session *session,
+ ust_registry_lookup_enum_by_id(ust_registry_session *session,
const char *enum_name, uint64_t enum_id)
{
struct ust_registry_enum *reg_enum = NULL;
strncpy(reg_enum_lookup.name, enum_name, LTTNG_UST_ABI_SYM_NAME_LEN);
reg_enum_lookup.name[LTTNG_UST_ABI_SYM_NAME_LEN - 1] = '\0';
reg_enum_lookup.id = enum_id;
- cds_lfht_lookup(session->enums->ht,
+ cds_lfht_lookup(session->_enums->ht,
ht_hash_enum((void *) ®_enum_lookup, lttng_ht_seed),
ht_match_enum_id, ®_enum_lookup, &iter.iter);
node = lttng_ht_iter_get_node_str(&iter);
*
* We receive ownership of entries.
*/
-int ust_registry_create_or_find_enum(struct ust_registry_session *session,
+int ust_registry_create_or_find_enum(ust_registry_session *session,
int session_objd, char *enum_name,
struct lttng_ust_ctl_enum_entry *entries, size_t nr_entries,
uint64_t *enum_id)
} else {
DBG("UST registry creating enum: %s, sess_objd: %u",
enum_name, session_objd);
- if (session->next_enum_id == -1ULL) {
+ if (session->_next_enum_id == -1ULL) {
ret = -EOVERFLOW;
destroy_enum(reg_enum);
goto end;
}
- reg_enum->id = session->next_enum_id++;
+ reg_enum->id = session->_next_enum_id++;
cds_lfht_node_init(®_enum->node.node);
- nodep = cds_lfht_add_unique(session->enums->ht,
+ nodep = cds_lfht_add_unique(session->_enums->ht,
ht_hash_enum(reg_enum, lttng_ht_seed),
ht_match_enum_id, reg_enum,
®_enum->node.node);
* the enumeration.
* This MUST be called within a RCU read side lock section.
*/
-static void ust_registry_destroy_enum(struct ust_registry_session *reg_session,
+void ust_registry_destroy_enum(ust_registry_session *reg_session,
struct ust_registry_enum *reg_enum)
{
int ret;
/* Delete the node first. */
iter.iter.node = ®_enum->node.node;
- ret = lttng_ht_del(reg_session->enums, &iter);
+ ret = lttng_ht_del(reg_session->_enums.get(), &iter);
LTTNG_ASSERT(!ret);
call_rcu(®_enum->rcu_head, destroy_enum_rcu);
}
* free the registry pointer since it might not have been allocated before so
* it's the caller responsability.
*/
-static void destroy_channel(struct ust_registry_channel *chan, bool notif)
+void ust_registry_channel_destroy(struct ust_registry_channel *chan, bool notify)
{
struct lttng_ht_iter iter;
struct ust_registry_event *event;
LTTNG_ASSERT(chan);
- if (notif) {
+ if (notify) {
cmd_ret = notification_thread_command_remove_channel(
the_notification_thread_handle,
chan->consumer_key, LTTNG_DOMAIN_UST);
/*
* Initialize registry with default values.
*/
-int ust_registry_channel_add(struct ust_registry_session *session,
+int ust_registry_channel_add(ust_registry_session *session,
uint64_t key)
{
int ret = 0;
* *before* the channel notify so the ID needs to be set at this point so
* the metadata can be dumped for that event.
*/
- if (ust_registry_is_max_id(session->used_channel_id)) {
+ if (ust_registry_is_max_id(session->_used_channel_id)) {
ret = -1;
goto error;
}
rcu_read_lock();
lttng_ht_node_init_u64(&chan->node, key);
- lttng_ht_add_unique_u64(session->channels, &chan->node);
+ lttng_ht_add_unique_u64(session->_channels.get(), &chan->node);
rcu_read_unlock();
return 0;
error:
- destroy_channel(chan, false);
+ ust_registry_channel_destroy(chan, false);
error_alloc:
return ret;
}
* On success, the pointer is returned else NULL.
*/
struct ust_registry_channel *ust_registry_channel_find(
- struct ust_registry_session *session, uint64_t key)
+ ust_registry_session *session, uint64_t key)
{
struct lttng_ht_node_u64 *node;
struct lttng_ht_iter iter;
struct ust_registry_channel *chan = NULL;
LTTNG_ASSERT(session);
- LTTNG_ASSERT(session->channels);
+ LTTNG_ASSERT(session->_channels);
ASSERT_RCU_READ_LOCKED();
DBG3("UST registry channel finding key %" PRIu64, key);
- lttng_ht_lookup(session->channels, &key, &iter);
+ lttng_ht_lookup(session->_channels.get(), &key, &iter);
node = lttng_ht_iter_get_node_u64(&iter);
if (!node) {
goto end;
/*
* Remove channel using key from registry and free memory.
*/
-void ust_registry_channel_del_free(struct ust_registry_session *session,
+void ust_registry_channel_del_free(ust_registry_session *session,
uint64_t key, bool notif)
{
struct lttng_ht_iter iter;
}
iter.iter.node = &chan->node.node;
- ret = lttng_ht_del(session->channels, &iter);
+ ret = lttng_ht_del(session->_channels.get(), &iter);
LTTNG_ASSERT(!ret);
rcu_read_unlock();
- destroy_channel(chan, notif);
+ ust_registry_channel_destroy(chan, notif);
end:
return;
}
-/*
- * Initialize registry with default values and set the newly allocated session
- * pointer to sessionp.
- *
- * Return 0 on success and sessionp is set or else return -1 and sessionp is
- * kept untouched.
- */
-int ust_registry_session_init(struct ust_registry_session **sessionp,
- struct ust_app *app,
- uint32_t bits_per_long,
+ust_registry_session *ust_registry_session_per_uid_create(uint32_t bits_per_long,
uint32_t uint8_t_alignment,
uint32_t uint16_t_alignment,
uint32_t uint32_t_alignment,
uint64_t tracing_id,
uid_t tracing_uid)
{
- int ret;
- struct ust_registry_session *session;
-
- LTTNG_ASSERT(sessionp);
-
- session = zmalloc<ust_registry_session>();
- if (!session) {
- PERROR("zmalloc ust registry session");
- goto error_alloc;
- }
-
- pthread_mutex_init(&session->lock, NULL);
- session->bits_per_long = bits_per_long;
- session->uint8_t_alignment = uint8_t_alignment;
- session->uint16_t_alignment = uint16_t_alignment;
- session->uint32_t_alignment = uint32_t_alignment;
- session->uint64_t_alignment = uint64_t_alignment;
- session->long_alignment = long_alignment;
- session->byte_order = byte_order;
- session->metadata_fd = -1;
- session->uid = euid;
- session->gid = egid;
- session->next_enum_id = 0;
- session->major = major;
- session->minor = minor;
- strncpy(session->root_shm_path, root_shm_path,
- sizeof(session->root_shm_path));
- session->root_shm_path[sizeof(session->root_shm_path) - 1] = '\0';
- if (shm_path[0]) {
- strncpy(session->shm_path, shm_path,
- sizeof(session->shm_path));
- session->shm_path[sizeof(session->shm_path) - 1] = '\0';
- strncpy(session->metadata_path, shm_path,
- sizeof(session->metadata_path));
- session->metadata_path[sizeof(session->metadata_path) - 1] = '\0';
- strncat(session->metadata_path, "/metadata",
- sizeof(session->metadata_path)
- - strlen(session->metadata_path) - 1);
+ try {
+ return new ust_registry_session_per_uid(bits_per_long, uint8_t_alignment,
+ uint16_t_alignment, uint32_t_alignment, uint64_t_alignment,
+ long_alignment, byte_order, major, minor, root_shm_path, shm_path,
+ euid, egid, tracing_id, tracing_uid);
+ } catch (const std::exception &ex) {
+ ERR("Failed to create per-uid registry session: %s", ex.what());
+ return nullptr;
}
- if (session->shm_path[0]) {
- ret = run_as_mkdir_recursive(session->shm_path,
- S_IRWXU | S_IRWXG,
- euid, egid);
- if (ret) {
- PERROR("run_as_mkdir_recursive");
- goto error;
- }
- }
- if (session->metadata_path[0]) {
- /* Create metadata file */
- ret = run_as_open(session->metadata_path,
- O_WRONLY | O_CREAT | O_EXCL,
- S_IRUSR | S_IWUSR, euid, egid);
- if (ret < 0) {
- PERROR("Opening metadata file");
- goto error;
- }
- session->metadata_fd = ret;
- }
-
- session->enums = lttng_ht_new(0, LTTNG_HT_TYPE_STRING);
- if (!session->enums) {
- ERR("Failed to create enums hash table");
- goto error;
- }
- /* hash/match functions are specified at call site. */
- session->enums->match_fct = NULL;
- session->enums->hash_fct = NULL;
-
- session->channels = lttng_ht_new(0, LTTNG_HT_TYPE_U64);
- if (!session->channels) {
- goto error;
- }
-
- ret = lttng_uuid_generate(session->uuid);
- if (ret) {
- ERR("Failed to generate UST uuid (errno = %d)", ret);
- goto error;
- }
-
- session->tracing_id = tracing_id;
- session->tracing_uid = tracing_uid;
+}
- pthread_mutex_lock(&session->lock);
- ret = ust_metadata_session_statedump(session, app, major, minor);
- pthread_mutex_unlock(&session->lock);
- if (ret) {
- ERR("Failed to generate session metadata (errno = %d)", ret);
- goto error;
+ust_registry_session *ust_registry_session_per_pid_create(struct ust_app *app,
+ uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id)
+{
+ try {
+ return new ust_registry_session_per_pid(*app, bits_per_long, uint8_t_alignment,
+ uint16_t_alignment, uint32_t_alignment, uint64_t_alignment,
+ long_alignment, byte_order, major, minor, root_shm_path, shm_path,
+ euid, egid, tracing_id);
+ } catch (const std::exception &ex) {
+ ERR("Failed to create per-pid registry session: %s", ex.what());
+ return nullptr;
}
-
- *sessionp = session;
-
- return 0;
-
-error:
- ust_registry_session_destroy(session);
- free(session);
-error_alloc:
- return -1;
}
/*
* Destroy session registry. This does NOT free the given pointer since it
* might get passed as a reference. The registry lock should NOT be acquired.
*/
-void ust_registry_session_destroy(struct ust_registry_session *reg)
+void ust_registry_session_destroy(ust_registry_session *reg)
{
- int ret;
- struct lttng_ht_iter iter;
- struct ust_registry_channel *chan;
- struct ust_registry_enum *reg_enum;
-
- if (!reg) {
- return;
- }
-
- /* On error, EBUSY can be returned if lock. Code flow error. */
- ret = pthread_mutex_destroy(®->lock);
- LTTNG_ASSERT(!ret);
-
- if (reg->channels) {
- rcu_read_lock();
- /* Destroy all event associated with this registry. */
- cds_lfht_for_each_entry(reg->channels->ht, &iter.iter, chan,
- node.node) {
- /* Delete the node from the ht and free it. */
- ret = lttng_ht_del(reg->channels, &iter);
- LTTNG_ASSERT(!ret);
- destroy_channel(chan, true);
- }
- rcu_read_unlock();
- lttng_ht_destroy(reg->channels);
- }
-
- free(reg->metadata);
- if (reg->metadata_fd >= 0) {
- ret = close(reg->metadata_fd);
- if (ret) {
- PERROR("close");
- }
- ret = run_as_unlink(reg->metadata_path,
- reg->uid, reg->gid);
- if (ret) {
- PERROR("unlink");
- }
- }
- if (reg->root_shm_path[0]) {
- /*
- * Try deleting the directory hierarchy.
- */
- (void) run_as_rmdir_recursive(reg->root_shm_path,
- reg->uid, reg->gid,
- LTTNG_DIRECTORY_HANDLE_SKIP_NON_EMPTY_FLAG);
- }
- /* Destroy the enum hash table */
- if (reg->enums) {
- rcu_read_lock();
- /* Destroy all enum entries associated with this registry. */
- cds_lfht_for_each_entry(reg->enums->ht, &iter.iter, reg_enum,
- node.node) {
- ust_registry_destroy_enum(reg, reg_enum);
- }
- rcu_read_unlock();
- lttng_ht_destroy(reg->enums);
- }
+ delete reg;
}
/*
* Copyright (C) 2013 David Goulet <dgoulet@efficios.com>
+ * Copyright (C) 2022 Jérémie Galarneau <jeremie.galarneau@efficios.com>
*
* SPDX-License-Identifier: GPL-2.0-only
*
#include <pthread.h>
#include <stdint.h>
+#include <ctime>
+#include <string>
+#include <memory>
#include <common/hashtable/hashtable.hpp>
#include <common/uuid.hpp>
+#include <lttng/domain.h>
+
#include "lttng-ust-ctl.hpp"
#define CTF_SPEC_MAJOR 1
struct ust_app;
-struct ust_registry_session {
+class ust_registry_session {
+public:
+ virtual lttng_buffer_type get_buffering_scheme() const = 0;
+ virtual ~ust_registry_session();
+
+protected:
+ /* Prevent instanciation of this base class. */
+ ust_registry_session(unsigned int bits_per_long,
+ unsigned int uint8_t_alignment,
+ unsigned int uint16_t_alignment,
+ unsigned int uint32_t_alignment,
+ unsigned int uint64_t_alignment,
+ unsigned int long_alignment,
+ int byte_order,
+ unsigned int app_tracer_version_major,
+ unsigned int app_tracer_version_minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id);
+
+ void statedump();
+
+public:
/*
* With multiple writers and readers, use this lock to access
* the registry. Can nest within the ust app session lock.
* sessiond to the consumerd.
* The consumer socket lock nests within this lock.
*/
- pthread_mutex_t lock;
+ pthread_mutex_t _lock;
/* Next channel ID available for a newly registered channel. */
- uint32_t next_channel_id;
+ uint32_t _next_channel_id = 0;
/* Once this value reaches UINT32_MAX, no more id can be allocated. */
- uint32_t used_channel_id;
+ uint32_t _used_channel_id = 0;
/* Next enumeration ID available. */
- uint64_t next_enum_id;
+ uint64_t _next_enum_id = 0;
/* Universal unique identifier used by the tracer. */
- unsigned char uuid[LTTNG_UUID_LEN];
+ unsigned char _uuid[LTTNG_UUID_LEN] = {};
/* session ABI description */
/* Size of long, in bits */
- unsigned int bits_per_long;
+ unsigned int _bits_per_long;
/* Alignment, in bits */
- unsigned int uint8_t_alignment,
- uint16_t_alignment,
- uint32_t_alignment,
- uint64_t_alignment,
- long_alignment;
- /* endianness */
- int byte_order; /* BIG_ENDIAN or LITTLE_ENDIAN */
+ unsigned int _uint8_t_alignment, _uint16_t_alignment, _uint32_t_alignment,
+ _uint64_t_alignment, _long_alignment;
+ /* endianness: BIG_ENDIAN or LITTLE_ENDIAN */
+ int _byte_order;
/* Generated metadata. */
- char *metadata; /* NOT null-terminated ! Use memcpy. */
- size_t metadata_len, metadata_alloc_len;
+ char *_metadata = nullptr; /* NOT null-terminated ! Use memcpy. */
+ size_t _metadata_len = 0, _metadata_alloc_len = 0;
/* Length of bytes sent to the consumer. */
- size_t metadata_len_sent;
+ size_t _metadata_len_sent = 0;
/* Current version of the metadata. */
- uint64_t metadata_version;
+ uint64_t _metadata_version = 0;
/*
* Those fields are only used when a session is created with
*
* metadata_path contains the full path to the metadata file that
* is kept for the "crash buffer" extraction:
- * e.g. /tmp/my_shm/my_session-20180612-135822/ust/uid/1000/64-bit/metadata
+ * e.g.
+ * /tmp/my_shm/my_session-20180612-135822/ust/uid/1000/64-bit/metadata
*
* Note that this is not the trace's final metadata file. It is
* only meant to be used to read the contents of the ring buffers
* metadata_fd is a file descriptor that points to the file at
* 'metadata_path'.
*/
- char root_shm_path[PATH_MAX];
- char shm_path[PATH_MAX];
- char metadata_path[PATH_MAX];
- int metadata_fd; /* file-backed metadata FD */
+ char _root_shm_path[PATH_MAX] = {};
+ char _shm_path[PATH_MAX] = {};
+ char _metadata_path[PATH_MAX] = {};
+ /* File-backed metadata FD */
+ int _metadata_fd = -1;
/*
* Hash table containing channels sent by the UST tracer. MUST
* be accessed with a RCU read side lock acquired.
*/
- struct lttng_ht *channels;
+ lttng_ht::uptr _channels;
+
/*
* Unique key to identify the metadata on the consumer side.
*/
- uint64_t metadata_key;
+ uint64_t _metadata_key = 0;
/*
* Indicates if the metadata is closed on the consumer side. This is to
* avoid double close of metadata when an application unregisters AND
* deletes its sessions.
*/
- unsigned int metadata_closed;
+ bool _metadata_closed = false;
/* User and group owning the session. */
- uid_t uid;
- gid_t gid;
+ uid_t _uid = -1;
+ gid_t _gid = -1;
/* Enumerations table. */
- struct lttng_ht *enums;
+ lttng_ht::uptr _enums;
/*
* Copy of the tracer version when the first app is registered.
* It is used if we need to regenerate the metadata.
*/
- uint32_t major;
- uint32_t minor;
+ uint32_t _app_tracer_version_major = 0;
+ uint32_t _app_tracer_version_minor = 0;
/* The id of the parent session */
- uint64_t tracing_id;
- uid_t tracing_uid;
+ uint64_t _tracing_id = -1ULL;
+};
+
+class ust_registry_session_per_uid : public ust_registry_session {
+public:
+ ust_registry_session_per_uid(uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id,
+ uid_t tracing_uid);
+
+ virtual lttng_buffer_type get_buffering_scheme() const noexcept override final;
+
+ const uid_t _tracing_uid;
+};
+
+class ust_registry_session_per_pid : public ust_registry_session {
+public:
+ ust_registry_session_per_pid(const struct ust_app &app,
+ uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id);
+
+ virtual lttng_buffer_type get_buffering_scheme() const noexcept override final;
+
+ pid_t get_vpid() const
+ {
+ return _vpid;
+ }
+
+ const unsigned int _tracer_patch_level_version;
+ const pid_t _vpid;
+ const std::string _procname;
+ const std::time_t _app_creation_time;
};
struct ust_registry_channel {
* is returned.
*/
static inline uint32_t ust_registry_get_next_chan_id(
- struct ust_registry_session *r)
+ ust_registry_session *r)
{
- if (ust_registry_is_max_id(r->used_channel_id)) {
- return r->used_channel_id;
+ if (ust_registry_is_max_id(r->_used_channel_id)) {
+ return r->_used_channel_id;
}
- r->used_channel_id++;
- return r->next_channel_id++;
+ r->_used_channel_id++;
+ return r->_next_channel_id++;
}
/*
#ifdef HAVE_LIBLTTNG_UST_CTL
-void ust_registry_channel_destroy(struct ust_registry_session *session,
+void ust_registry_channel_destroy(ust_registry_session *session,
struct ust_registry_channel *chan);
struct ust_registry_channel *ust_registry_channel_find(
- struct ust_registry_session *session, uint64_t key);
-int ust_registry_channel_add(struct ust_registry_session *session,
+ ust_registry_session *session, uint64_t key);
+int ust_registry_channel_add(ust_registry_session *session,
uint64_t key);
-void ust_registry_channel_del_free(struct ust_registry_session *session,
+void ust_registry_channel_del_free(ust_registry_session *session,
uint64_t key, bool notif);
+void ust_registry_channel_destroy(struct ust_registry_channel *chan, bool notify);
-int ust_registry_session_init(struct ust_registry_session **sessionp,
- struct ust_app *app,
+/*
+ * Create per-uid registry with default values.
+ *
+ * Return new instance on success, nullptr on error.
+ */
+ust_registry_session *ust_registry_session_per_uid_create(
uint32_t bits_per_long,
uint32_t uint8_t_alignment,
uint32_t uint16_t_alignment,
gid_t egid,
uint64_t tracing_id,
uid_t tracing_uid);
-void ust_registry_session_destroy(struct ust_registry_session *session);
-int ust_registry_create_event(struct ust_registry_session *session,
+/*
+ * Create per-pid registry with default values.
+ *
+ * Return new instance on success, nullptr on error.
+ */
+ust_registry_session *ust_registry_session_per_pid_create(struct ust_app *app,
+ uint32_t bits_per_long,
+ uint32_t uint8_t_alignment,
+ uint32_t uint16_t_alignment,
+ uint32_t uint32_t_alignment,
+ uint32_t uint64_t_alignment,
+ uint32_t long_alignment,
+ int byte_order,
+ uint32_t major,
+ uint32_t minor,
+ const char *root_shm_path,
+ const char *shm_path,
+ uid_t euid,
+ gid_t egid,
+ uint64_t tracing_id);
+void ust_registry_session_destroy(ust_registry_session *session);
+
+int ust_registry_create_event(ust_registry_session *session,
uint64_t chan_key, int session_objd, int channel_objd, char *name,
char *sig, size_t nr_fields, struct lttng_ust_ctl_field *fields,
int loglevel_value, char *model_emf_uri, int buffer_type,
struct ust_registry_event *event);
/* app can be NULL for registry shared across applications. */
-int ust_metadata_session_statedump(struct ust_registry_session *session,
- struct ust_app *app, uint32_t major, uint32_t minor);
-int ust_metadata_channel_statedump(struct ust_registry_session *session,
+int ust_metadata_session_statedump(ust_registry_session *session);
+int ust_metadata_channel_statedump(ust_registry_session *session,
struct ust_registry_channel *chan);
-int ust_metadata_event_statedump(struct ust_registry_session *session,
+int ust_metadata_event_statedump(ust_registry_session *session,
struct ust_registry_channel *chan,
struct ust_registry_event *event);
-int ust_registry_create_or_find_enum(struct ust_registry_session *session,
+int ust_registry_create_or_find_enum(ust_registry_session *session,
int session_objd, char *name,
struct lttng_ust_ctl_enum_entry *entries, size_t nr_entries,
uint64_t *enum_id);
struct ust_registry_enum *
- ust_registry_lookup_enum_by_id(struct ust_registry_session *session,
+ ust_registry_lookup_enum_by_id(ust_registry_session *session,
const char *name, uint64_t id);
+void ust_registry_destroy_enum(ust_registry_session *reg_session,
+ struct ust_registry_enum *reg_enum);
#else /* HAVE_LIBLTTNG_UST_CTL */
-static inline
-void ust_registry_channel_destroy(
- struct ust_registry_session *session __attribute__((unused)),
- struct ust_registry_channel *chan __attribute__((unused)))
-{}
+static inline void ust_registry_channel_destroy(
+ struct ust_registry_channel *chan __attribute__((unused)),
+ bool notify __attribute__((unused)))
+{
+}
static inline
struct ust_registry_channel *ust_registry_channel_find(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
uint64_t key __attribute__((unused)))
{
return NULL;
static inline
int ust_registry_channel_add(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
uint64_t key __attribute__((unused)))
{
return 0;
static inline
void ust_registry_channel_del_free(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
uint64_t key __attribute__((unused)),
bool notif __attribute__((unused)))
{}
static inline
-int ust_registry_session_init(
- struct ust_registry_session **sessionp __attribute__((unused)),
- struct ust_app *app __attribute__((unused)),
+ust_registry_session *ust_registry_session_per_uid_create(
uint32_t bits_per_long __attribute__((unused)),
uint32_t uint8_t_alignment __attribute__((unused)),
uint32_t uint16_t_alignment __attribute__((unused)),
uint64_t tracing_id __attribute__((unused)),
uid_t tracing_uid __attribute__((unused)))
{
- return 0;
+ return nullptr;
+}
+
+static inline
+ust_registry_session *ust_registry_session_per_pid_create(
+ struct ust_app *app __attribute__((unused)),
+ uint32_t bits_per_long __attribute__((unused)),
+ uint32_t uint8_t_alignment __attribute__((unused)),
+ uint32_t uint16_t_alignment __attribute__((unused)),
+ uint32_t uint32_t_alignment __attribute__((unused)),
+ uint32_t uint64_t_alignment __attribute__((unused)),
+ uint32_t long_alignment __attribute__((unused)),
+ int byte_order __attribute__((unused)),
+ uint32_t major __attribute__((unused)),
+ uint32_t minor __attribute__((unused)),
+ const char *root_shm_path __attribute__((unused)),
+ const char *shm_path __attribute__((unused)),
+ uid_t euid __attribute__((unused)),
+ gid_t egid __attribute__((unused)),
+ uint64_t tracing_id __attribute__((unused)))
+{
+ return nullptr;
}
static inline
void ust_registry_session_destroy(
- struct ust_registry_session *session __attribute__((unused)))
+ ust_registry_session *session __attribute__((unused)))
{}
static inline
int ust_registry_create_event(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
uint64_t chan_key __attribute__((unused)),
int session_objd __attribute__((unused)),
int channel_objd __attribute__((unused)),
/* The app object can be NULL for registry shared across applications. */
static inline
int ust_metadata_session_statedump(
- struct ust_registry_session *session __attribute__((unused)),
- struct ust_app *app __attribute__((unused)),
- uint32_t major __attribute__((unused)),
- uint32_t minor __attribute__((unused)))
+ ust_registry_session *session __attribute__((unused)))
{
return 0;
}
static inline
int ust_metadata_channel_statedump(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
struct ust_registry_channel *chan __attribute__((unused)))
{
return 0;
static inline
int ust_metadata_event_statedump(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
struct ust_registry_channel *chan __attribute__((unused)),
struct ust_registry_event *event __attribute__((unused)))
{
static inline
int ust_registry_create_or_find_enum(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
int session_objd __attribute__((unused)),
char *name __attribute__((unused)),
struct lttng_ust_ctl_enum_entry *entries __attribute__((unused)),
static inline
struct ust_registry_enum *
ust_registry_lookup_enum_by_id(
- struct ust_registry_session *session __attribute__((unused)),
+ ust_registry_session *session __attribute__((unused)),
const char *name __attribute__((unused)),
uint64_t id __attribute__((unused)))
{
return NULL;
}
+static inline
+void ust_registry_destroy_enum(ust_registry_session *reg_session __attribute__((unused)),
+ struct ust_registry_enum *reg_enum __attribute__((unused)))
+{}
+
#endif /* HAVE_LIBLTTNG_UST_CTL */
#endif /* LTTNG_UST_REGISTRY_H */
msg + " " + format_throw_location(file_name, function_name, line_number))
{
}
+
+lttng::runtime_error::runtime_error(const std::string &msg,
+ const char *file_name,
+ const char *function_name,
+ unsigned int line_number) :
+ std::runtime_error(msg + " " + format_throw_location(file_name, function_name, line_number))
+{
+}
throw lttng::ctl::error(msg, error_code, __FILE__, __func__, __LINE__)
#define LTTNG_THROW_POSIX(msg, errno_code) \
throw lttng::posix_error(msg, errno_code, __FILE__, __func__, __LINE__)
+#define LTTNG_THROW_ERROR(msg) \
+ throw lttng::runtime_error(msg, __FILE__, __func__, __LINE__)
namespace lttng {
unsigned int line_number);
};
+class runtime_error : public std::runtime_error {
+public:
+ explicit runtime_error(const std::string &msg,
+ const char *file_name,
+ const char *function_name,
+ unsigned int line_number);
+};
+
}; /* namespace lttng */
#endif /* LTTNG_EXCEPTION_H_ */
#include <urcu.h>
#include <stdint.h>
+#include <memory>
#include <common/macros.hpp>
#include <lttng/lttng-export.h>
LTTNG_HT_TYPE_TWO_U64,
};
+struct lttng_ht_deleter;
+
struct lttng_ht {
+ using uptr = std::unique_ptr<lttng_ht, lttng_ht_deleter>;
struct cds_lfht *ht;
cds_lfht_match_fct match_fct;
hash_fct_type hash_fct;
/* Hashtable new and destroy */
struct lttng_ht *lttng_ht_new(unsigned long size, enum lttng_ht_type type);
void lttng_ht_destroy(struct lttng_ht *ht);
+struct lttng_ht_deleter {
+ void operator()(lttng_ht *ht) { lttng_ht_destroy(ht); };
+};
/* Specialized node init and free functions */
void lttng_ht_node_init_str(struct lttng_ht_node_str *node, char *key);
{
int i, ret = 0;
- if (uuid_out == NULL) {
- ret = -1;
- goto end;
- }
+ LTTNG_ASSERT(uuid_out);
if (!lttng_uuid_is_init) {
/*
ret = -1;
goto end;
}
- srand(epoch);
+ srand(epoch);
lttng_uuid_is_init = true;
}