+ /*
+ * This will only compile on platforms that support
+ * dirfd (POSIX.2008). This is fine as the session daemon
+ * is only built for such platforms.
+ *
+ * The ownership of the chunk directory handle's is maintained
+ * by the trace chunk.
+ */
+ chunk_dirfd = lttng_directory_handle_get_dirfd(
+ chunk_directory_handle);
+ assert(chunk_dirfd >= 0);
+ }
+
+ chunk_status = lttng_trace_chunk_get_credentials(chunk,
+ &chunk_credentials);
+ if (chunk_status != LTTNG_TRACE_CHUNK_STATUS_OK) {
+ /*
+ * Not associating credentials to a sessiond chunk is a fatal
+ * internal error.
+ */
+ ret = -LTTNG_ERR_FATAL;
+ goto error;
+ }
+ msg.u.create_trace_chunk.credentials.uid = chunk_credentials.uid;
+ msg.u.create_trace_chunk.credentials.gid = chunk_credentials.gid;
+
+ DBG("Sending consumer create trace chunk command: relayd_id = %" PRId64
+ ", session_id = %" PRIu64 ", chunk_id = %" PRIu64
+ ", creation_timestamp = %s",
+ relayd_id, session_id, chunk_id,
+ creation_timestamp_str);
+ health_code_update();
+ ret = consumer_send_msg(socket, &msg);
+ health_code_update();
+ if (ret < 0) {
+ ERR("Trace chunk creation error on consumer");
+ ret = -LTTNG_ERR_CREATE_TRACE_CHUNK_FAIL_CONSUMER;
+ goto error;
+ }
+
+ if (chunk_has_local_output) {
+ DBG("Sending trace chunk directory fd to consumer");
+ health_code_update();
+ ret = consumer_send_fds(socket, &chunk_dirfd, 1);
+ health_code_update();
+ if (ret < 0) {
+ ERR("Trace chunk creation error on consumer");
+ ret = -LTTNG_ERR_CREATE_TRACE_CHUNK_FAIL_CONSUMER;
+ goto error;
+ }
+ }
+error:
+ return ret;
+}
+
+/*
+ * Ask the consumer to close a trace chunk for a given session.
+ *
+ * Called with the consumer socket lock held.
+ */
+int consumer_close_trace_chunk(struct consumer_socket *socket,
+ uint64_t relayd_id, uint64_t session_id,
+ struct lttng_trace_chunk *chunk)
+{
+ int ret;
+ enum lttng_trace_chunk_status chunk_status;
+ struct lttcomm_consumer_msg msg = {
+ .cmd_type = LTTNG_CONSUMER_CLOSE_TRACE_CHUNK,
+ .u.close_trace_chunk.session_id = session_id,
+ };
+ uint64_t chunk_id;
+ time_t close_timestamp;
+
+ assert(socket);
+
+ if (relayd_id != -1ULL) {
+ LTTNG_OPTIONAL_SET(&msg.u.close_trace_chunk.relayd_id,
+ relayd_id);