+ goto free_error;
+ }
+
+ rcu_read_lock();
+ snapshot_add_output(&session->snapshot, new_output);
+ if (id) {
+ *id = new_output->id;
+ }
+ rcu_read_unlock();
+
+ return LTTNG_OK;
+
+free_error:
+ snapshot_output_destroy(new_output);
+error:
+ return ret;
+}
+
+/*
+ * Command LTTNG_SNAPSHOT_DEL_OUTPUT from lib lttng ctl.
+ *
+ * Return LTTNG_OK on success or else a LTTNG_ERR code.
+ */
+int cmd_snapshot_del_output(struct ltt_session *session,
+ struct lttng_snapshot_output *output)
+{
+ int ret;
+ struct snapshot_output *sout = NULL;
+
+ assert(session);
+ assert(output);
+
+ rcu_read_lock();
+
+ /*
+ * Permission denied to create an output if the session is not
+ * set in no output mode.
+ */
+ if (session->output_traces) {
+ ret = LTTNG_ERR_EPERM;
+ goto error;
+ }
+
+ if (output->id) {
+ DBG("Cmd snapshot del output id %" PRIu32 " for session %s", output->id,
+ session->name);
+ sout = snapshot_find_output_by_id(output->id, &session->snapshot);
+ } else if (*output->name != '\0') {
+ DBG("Cmd snapshot del output name %s for session %s", output->name,
+ session->name);
+ sout = snapshot_find_output_by_name(output->name, &session->snapshot);
+ }
+ if (!sout) {
+ ret = LTTNG_ERR_INVALID;
+ goto error;
+ }
+
+ snapshot_delete_output(&session->snapshot, sout);
+ snapshot_output_destroy(sout);
+ ret = LTTNG_OK;
+
+error:
+ rcu_read_unlock();
+ return ret;
+}
+
+/*
+ * Command LTTNG_SNAPSHOT_LIST_OUTPUT from lib lttng ctl.
+ *
+ * If no output is available, outputs is untouched and 0 is returned.
+ *
+ * Return the size of the newly allocated outputs or a negative LTTNG_ERR code.
+ */
+ssize_t cmd_snapshot_list_outputs(struct ltt_session *session,
+ struct lttng_snapshot_output **outputs)
+{
+ int ret, idx = 0;
+ struct lttng_snapshot_output *list;
+ struct lttng_ht_iter iter;
+ struct snapshot_output *output;
+
+ assert(session);
+ assert(outputs);
+
+ DBG("Cmd snapshot list outputs for session %s", session->name);
+
+ /*
+ * Permission denied to create an output if the session is not
+ * set in no output mode.
+ */
+ if (session->output_traces) {
+ ret = LTTNG_ERR_EPERM;
+ goto error;
+ }
+
+ if (session->snapshot.nb_output == 0) {
+ ret = 0;
+ goto error;
+ }