MI: support double element
[lttng-tools.git] / src / common / mi-lttng.c
1 /*
2 * Copyright (C) 2014 Jonathan Rajotte <jonathan.r.julien@gmail.com>
3 * Copyright (C) 2014 Olivier Cotte <olivier.cotte@polymtl.ca>
4 * Copyright (C) 2016 Jérémie Galarneau <jeremie.galarneau@efficios.com>
5 *
6 * SPDX-License-Identifier: GPL-2.0-only
7 *
8 */
9
10 #include "lttng/tracker.h"
11 #define _LGPL_SOURCE
12 #include "mi-lttng.h"
13 #include <common/config/session-config.h>
14 #include <common/defaults.h>
15 #include <common/tracker.h>
16 #include <lttng/channel.h>
17 #include <lttng/snapshot-internal.h>
18
19 #include <assert.h>
20
21 #define MI_SCHEMA_MAJOR_VERSION 4
22 #define MI_SCHEMA_MINOR_VERSION 0
23
24 /* Machine interface namespace URI */
25 LTTNG_HIDDEN const char * const mi_lttng_xmlns = "xmlns";
26 LTTNG_HIDDEN const char * const mi_lttng_xmlns_xsi = "xmlns:xsi";
27 LTTNG_HIDDEN const char * const mi_lttng_w3_schema_uri = "http://www.w3.org/2001/XMLSchema-instance";
28 LTTNG_HIDDEN const char * const mi_lttng_schema_location = "xsi:schemaLocation";
29 LTTNG_HIDDEN const char * const mi_lttng_schema_location_uri =
30 DEFAULT_LTTNG_MI_NAMESPACE " "
31 "https://lttng.org/xml/schemas/lttng-mi/" XSTR(MI_SCHEMA_MAJOR_VERSION)
32 "/lttng-mi-" XSTR(MI_SCHEMA_MAJOR_VERSION) "."
33 XSTR(MI_SCHEMA_MINOR_VERSION) ".xsd";
34 LTTNG_HIDDEN const char * const mi_lttng_schema_version = "schemaVersion";
35 LTTNG_HIDDEN const char * const mi_lttng_schema_version_value = XSTR(MI_SCHEMA_MAJOR_VERSION)
36 "." XSTR(MI_SCHEMA_MINOR_VERSION);
37
38 /* Strings related to command */
39 const char * const mi_lttng_element_command = "command";
40 const char * const mi_lttng_element_command_action = "snapshot_action";
41 const char * const mi_lttng_element_command_add_context = "add-context";
42 const char * const mi_lttng_element_command_create = "create";
43 const char * const mi_lttng_element_command_destroy = "destroy";
44 const char * const mi_lttng_element_command_disable_channel = "disable-channel";
45 const char * const mi_lttng_element_command_disable_event = "disable-event";
46 const char * const mi_lttng_element_command_enable_channels = "enable-channel";
47 const char * const mi_lttng_element_command_enable_event = "enable-event";
48 const char * const mi_lttng_element_command_list = "list";
49 const char * const mi_lttng_element_command_load = "load";
50 LTTNG_HIDDEN const char * const mi_lttng_element_command_metadata = "metadata";
51 LTTNG_HIDDEN const char * const mi_lttng_element_command_metadata_action = "metadata_action";
52 LTTNG_HIDDEN const char * const mi_lttng_element_command_regenerate = "regenerate";
53 LTTNG_HIDDEN const char * const mi_lttng_element_command_regenerate_action = "regenerate_action";
54 const char * const mi_lttng_element_command_name = "name";
55 const char * const mi_lttng_element_command_output = "output";
56 const char * const mi_lttng_element_command_save = "save";
57 const char * const mi_lttng_element_command_set_session = "set-session";
58 const char * const mi_lttng_element_command_snapshot = "snapshot";
59 const char * const mi_lttng_element_command_snapshot_add = "add_snapshot";
60 const char * const mi_lttng_element_command_snapshot_del = "del_snapshot";
61 const char * const mi_lttng_element_command_snapshot_list = "list_snapshot";
62 const char * const mi_lttng_element_command_snapshot_record = "record_snapshot";
63 const char * const mi_lttng_element_command_start = "start";
64 const char * const mi_lttng_element_command_stop = "stop";
65 const char * const mi_lttng_element_command_success = "success";
66 const char * const mi_lttng_element_command_track = "track";
67 const char * const mi_lttng_element_command_untrack = "untrack";
68 const char * const mi_lttng_element_command_version = "version";
69 LTTNG_HIDDEN const char * const mi_lttng_element_command_rotate = "rotate";
70 LTTNG_HIDDEN const char * const mi_lttng_element_command_enable_rotation = "enable-rotation";
71 LTTNG_HIDDEN const char * const mi_lttng_element_command_disable_rotation = "disable-rotation";
72 LTTNG_HIDDEN const char * const mi_lttng_element_command_clear = "clear";
73
74 /* Strings related to version command */
75 const char * const mi_lttng_element_version = "version";
76 const char * const mi_lttng_element_version_commit = "commit";
77 const char * const mi_lttng_element_version_description = "description";
78 const char * const mi_lttng_element_version_license = "license";
79 const char * const mi_lttng_element_version_major = "major";
80 const char * const mi_lttng_element_version_minor = "minor";
81 const char * const mi_lttng_element_version_patch_level = "patchLevel";
82 const char * const mi_lttng_element_version_str = "string";
83 const char * const mi_lttng_element_version_web = "url";
84
85 /* String related to a lttng_event_field */
86 const char * const mi_lttng_element_event_field = "event_field";
87 const char * const mi_lttng_element_event_fields = "event_fields";
88
89 /* String related to lttng_event_perf_counter_ctx */
90 const char * const mi_lttng_element_perf_counter_context = "perf";
91
92 /* Strings related to pid */
93 const char * const mi_lttng_element_pid_id = "id";
94
95 /* Strings related to save command */
96 const char * const mi_lttng_element_save = "save";
97
98 /* Strings related to load command */
99 const char * const mi_lttng_element_load = "load";
100 LTTNG_HIDDEN const char * const mi_lttng_element_load_overrides = "overrides";
101 LTTNG_HIDDEN const char * const mi_lttng_element_load_override_url = "url";
102
103 /* General elements of mi_lttng */
104 const char * const mi_lttng_element_empty = "";
105 const char * const mi_lttng_element_id = "id";
106 const char * const mi_lttng_element_nowrite = "nowrite";
107 const char * const mi_lttng_element_success = "success";
108 const char * const mi_lttng_element_type_enum = "ENUM";
109 const char * const mi_lttng_element_type_float = "FLOAT";
110 const char * const mi_lttng_element_type_integer = "INTEGER";
111 const char * const mi_lttng_element_type_other = "OTHER";
112 const char * const mi_lttng_element_type_string = "STRING";
113
114 /* String related to loglevel */
115 const char * const mi_lttng_loglevel_str_alert = "TRACE_ALERT";
116 const char * const mi_lttng_loglevel_str_crit = "TRACE_CRIT";
117 const char * const mi_lttng_loglevel_str_debug = "TRACE_DEBUG";
118 const char * const mi_lttng_loglevel_str_debug_function = "TRACE_DEBUG_FUNCTION";
119 const char * const mi_lttng_loglevel_str_debug_line = "TRACE_DEBUG_LINE";
120 const char * const mi_lttng_loglevel_str_debug_module = "TRACE_DEBUG_MODULE";
121 const char * const mi_lttng_loglevel_str_debug_process = "TRACE_DEBUG_PROCESS";
122 const char * const mi_lttng_loglevel_str_debug_program = "TRACE_DEBUG_PROGRAM";
123 const char * const mi_lttng_loglevel_str_debug_system = "TRACE_DEBUG_SYSTEM";
124 const char * const mi_lttng_loglevel_str_debug_unit = "TRACE_DEBUG_UNIT";
125 const char * const mi_lttng_loglevel_str_emerg = "TRACE_EMERG";
126 const char * const mi_lttng_loglevel_str_err = "TRACE_ERR";
127 const char * const mi_lttng_loglevel_str_info = "TRACE_INFO";
128 const char * const mi_lttng_loglevel_str_notice = "TRACE_NOTICE";
129 const char * const mi_lttng_loglevel_str_unknown = "UNKNOWN";
130 const char * const mi_lttng_loglevel_str_warning = "TRACE_WARNING";
131
132 /* String related to loglevel JUL */
133 const char * const mi_lttng_loglevel_str_jul_all = "JUL_ALL";
134 const char * const mi_lttng_loglevel_str_jul_config = "JUL_CONFIG";
135 const char * const mi_lttng_loglevel_str_jul_fine = "JUL_FINE";
136 const char * const mi_lttng_loglevel_str_jul_finer = "JUL_FINER";
137 const char * const mi_lttng_loglevel_str_jul_finest = "JUL_FINEST";
138 const char * const mi_lttng_loglevel_str_jul_info = "JUL_INFO";
139 const char * const mi_lttng_loglevel_str_jul_off = "JUL_OFF";
140 const char * const mi_lttng_loglevel_str_jul_severe = "JUL_SEVERE";
141 const char * const mi_lttng_loglevel_str_jul_warning = "JUL_WARNING";
142
143 /* String related to loglevel LOG4J */
144 const char * const mi_lttng_loglevel_str_log4j_off = "LOG4J_OFF";
145 const char * const mi_lttng_loglevel_str_log4j_fatal = "LOG4J_FATAL";
146 const char * const mi_lttng_loglevel_str_log4j_error = "LOG4J_ERROR";
147 const char * const mi_lttng_loglevel_str_log4j_warn = "LOG4J_WARN";
148 const char * const mi_lttng_loglevel_str_log4j_info = "LOG4J_INFO";
149 const char * const mi_lttng_loglevel_str_log4j_debug = "LOG4J_DEBUG";
150 const char * const mi_lttng_loglevel_str_log4j_trace = "LOG4J_TRACE";
151 const char * const mi_lttng_loglevel_str_log4j_all = "LOG4J_ALL";
152
153 /* String related to loglevel Python */
154 const char * const mi_lttng_loglevel_str_python_critical = "PYTHON_CRITICAL";
155 const char * const mi_lttng_loglevel_str_python_error = "PYTHON_ERROR";
156 const char * const mi_lttng_loglevel_str_python_warning = "PYTHON_WARNING";
157 const char * const mi_lttng_loglevel_str_python_info = "PYTHON_INFO";
158 const char * const mi_lttng_loglevel_str_python_debug = "PYTHON_DEBUG";
159 const char * const mi_lttng_loglevel_str_python_notset = "PYTHON_NOTSET";
160
161 /* String related to loglevel type */
162 const char * const mi_lttng_loglevel_type_all = "ALL";
163 const char * const mi_lttng_loglevel_type_range = "RANGE";
164 const char * const mi_lttng_loglevel_type_single = "SINGLE";
165 const char * const mi_lttng_loglevel_type_unknown = "UNKNOWN";
166
167 /* String related to a lttng_snapshot_output */
168 const char * const mi_lttng_element_snapshot_ctrl_url = "ctrl_url";
169 const char * const mi_lttng_element_snapshot_data_url = "data_url";
170 const char * const mi_lttng_element_snapshot_max_size = "max_size";
171 const char * const mi_lttng_element_snapshot_n_ptr = "n_ptr";
172 const char * const mi_lttng_element_snapshot_session_name = "session_name";
173 const char * const mi_lttng_element_snapshots = "snapshots";
174
175 /* String related to track/untrack command */
176 const char * const mi_lttng_element_track_untrack_all_wildcard = "*";
177
178 LTTNG_HIDDEN const char * const mi_lttng_element_session_name = "session_name";
179
180 /* String related to rotate command */
181 LTTNG_HIDDEN const char * const mi_lttng_element_rotation = "rotation";
182 LTTNG_HIDDEN const char * const mi_lttng_element_rotate_status = "status";
183 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule = "rotation_schedule";
184 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedules = "rotation_schedules";
185 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule_result = "rotation_schedule_result";
186 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule_results = "rotation_schedule_results";
187 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule_periodic = "periodic";
188 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule_periodic_time_us = "time_us";
189 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule_size_threshold = "size_threshold";
190 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_schedule_size_threshold_bytes = "bytes";
191 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_state = "state";
192 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location = "location";
193 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_local = "local";
194 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_local_absolute_path = "absolute_path";
195 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_relay = "relay";
196 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_relay_host = "host";
197 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_relay_control_port = "control_port";
198 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_relay_data_port = "data_port";
199 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_relay_protocol = "protocol";
200 LTTNG_HIDDEN const char * const mi_lttng_element_rotation_location_relay_relative_path = "relative_path";
201
202 /* String related to enum lttng_rotation_state */
203 LTTNG_HIDDEN const char * const mi_lttng_rotation_state_str_ongoing = "ONGOING";
204 LTTNG_HIDDEN const char * const mi_lttng_rotation_state_str_completed = "COMPLETED";
205 LTTNG_HIDDEN const char * const mi_lttng_rotation_state_str_expired = "EXPIRED";
206 LTTNG_HIDDEN const char * const mi_lttng_rotation_state_str_error = "ERROR";
207
208 /* String related to enum lttng_trace_archive_location_relay_protocol_type */
209 LTTNG_HIDDEN const char * const mi_lttng_rotation_location_relay_protocol_str_tcp = "TCP";
210
211 /* String related to add-context command */
212 LTTNG_HIDDEN const char * const mi_lttng_element_context_symbol = "symbol";
213
214 /* Deprecated symbols preserved for ABI compatibility. */
215 const char * const mi_lttng_context_type_perf_counter;
216 const char * const mi_lttng_context_type_perf_cpu_counter;
217 const char * const mi_lttng_context_type_perf_thread_counter;
218 const char * const mi_lttng_element_track_untrack_pid_target;
219 const char * const mi_lttng_element_track_untrack_targets;
220 const char * const mi_lttng_element_calibrate;
221 const char * const mi_lttng_element_calibrate_function;
222 const char * const mi_lttng_element_command_calibrate;
223
224 /* This is a merge of jul loglevel and regular loglevel
225 * Those should never overlap by definition
226 * (see struct lttng_event loglevel)
227 */
228 LTTNG_HIDDEN
229 const char *mi_lttng_loglevel_string(int value, enum lttng_domain_type domain)
230 {
231 switch (domain) {
232 case LTTNG_DOMAIN_KERNEL:
233 case LTTNG_DOMAIN_UST:
234 switch (value) {
235 case -1:
236 return mi_lttng_element_empty;
237 case LTTNG_LOGLEVEL_EMERG:
238 return mi_lttng_loglevel_str_emerg;
239 case LTTNG_LOGLEVEL_ALERT:
240 return mi_lttng_loglevel_str_alert;
241 case LTTNG_LOGLEVEL_CRIT:
242 return mi_lttng_loglevel_str_crit;
243 case LTTNG_LOGLEVEL_ERR:
244 return mi_lttng_loglevel_str_err;
245 case LTTNG_LOGLEVEL_WARNING:
246 return mi_lttng_loglevel_str_warning;
247 case LTTNG_LOGLEVEL_NOTICE:
248 return mi_lttng_loglevel_str_notice;
249 case LTTNG_LOGLEVEL_INFO:
250 return mi_lttng_loglevel_str_info;
251 case LTTNG_LOGLEVEL_DEBUG_SYSTEM:
252 return mi_lttng_loglevel_str_debug_system;
253 case LTTNG_LOGLEVEL_DEBUG_PROGRAM:
254 return mi_lttng_loglevel_str_debug_program;
255 case LTTNG_LOGLEVEL_DEBUG_PROCESS:
256 return mi_lttng_loglevel_str_debug_process;
257 case LTTNG_LOGLEVEL_DEBUG_MODULE:
258 return mi_lttng_loglevel_str_debug_module;
259 case LTTNG_LOGLEVEL_DEBUG_UNIT:
260 return mi_lttng_loglevel_str_debug_unit;
261 case LTTNG_LOGLEVEL_DEBUG_FUNCTION:
262 return mi_lttng_loglevel_str_debug_function;
263 case LTTNG_LOGLEVEL_DEBUG_LINE:
264 return mi_lttng_loglevel_str_debug_line;
265 case LTTNG_LOGLEVEL_DEBUG:
266 return mi_lttng_loglevel_str_debug;
267 default:
268 return mi_lttng_loglevel_str_unknown;
269 }
270 break;
271 case LTTNG_DOMAIN_LOG4J:
272 switch (value) {
273 case -1:
274 return mi_lttng_element_empty;
275 case LTTNG_LOGLEVEL_LOG4J_OFF:
276 return mi_lttng_loglevel_str_log4j_off;
277 case LTTNG_LOGLEVEL_LOG4J_FATAL:
278 return mi_lttng_loglevel_str_log4j_fatal;
279 case LTTNG_LOGLEVEL_LOG4J_ERROR:
280 return mi_lttng_loglevel_str_log4j_error;
281 case LTTNG_LOGLEVEL_LOG4J_WARN:
282 return mi_lttng_loglevel_str_log4j_warn;
283 case LTTNG_LOGLEVEL_LOG4J_INFO:
284 return mi_lttng_loglevel_str_log4j_info;
285 case LTTNG_LOGLEVEL_LOG4J_DEBUG:
286 return mi_lttng_loglevel_str_log4j_debug;
287 case LTTNG_LOGLEVEL_LOG4J_TRACE:
288 return mi_lttng_loglevel_str_log4j_trace;
289 case LTTNG_LOGLEVEL_LOG4J_ALL:
290 return mi_lttng_loglevel_str_log4j_all;
291 default:
292 return mi_lttng_loglevel_str_unknown;
293 }
294 break;
295 case LTTNG_DOMAIN_JUL:
296 switch (value) {
297 case -1:
298 return mi_lttng_element_empty;
299 case LTTNG_LOGLEVEL_JUL_OFF:
300 return mi_lttng_loglevel_str_jul_off;
301 case LTTNG_LOGLEVEL_JUL_SEVERE:
302 return mi_lttng_loglevel_str_jul_severe;
303 case LTTNG_LOGLEVEL_JUL_WARNING:
304 return mi_lttng_loglevel_str_jul_warning;
305 case LTTNG_LOGLEVEL_JUL_INFO:
306 return mi_lttng_loglevel_str_jul_info;
307 case LTTNG_LOGLEVEL_JUL_CONFIG:
308 return mi_lttng_loglevel_str_jul_config;
309 case LTTNG_LOGLEVEL_JUL_FINE:
310 return mi_lttng_loglevel_str_jul_fine;
311 case LTTNG_LOGLEVEL_JUL_FINER:
312 return mi_lttng_loglevel_str_jul_finer;
313 case LTTNG_LOGLEVEL_JUL_FINEST:
314 return mi_lttng_loglevel_str_jul_finest;
315 case LTTNG_LOGLEVEL_JUL_ALL:
316 return mi_lttng_loglevel_str_jul_all;
317 default:
318 return mi_lttng_loglevel_str_unknown;
319 }
320 break;
321 case LTTNG_DOMAIN_PYTHON:
322 switch (value) {
323 case LTTNG_LOGLEVEL_PYTHON_CRITICAL:
324 return mi_lttng_loglevel_str_python_critical;
325 case LTTNG_LOGLEVEL_PYTHON_ERROR:
326 return mi_lttng_loglevel_str_python_error;
327 case LTTNG_LOGLEVEL_PYTHON_WARNING:
328 return mi_lttng_loglevel_str_python_warning;
329 case LTTNG_LOGLEVEL_PYTHON_INFO:
330 return mi_lttng_loglevel_str_python_info;
331 case LTTNG_LOGLEVEL_PYTHON_DEBUG:
332 return mi_lttng_loglevel_str_python_debug;
333 case LTTNG_LOGLEVEL_PYTHON_NOTSET:
334 return mi_lttng_loglevel_str_python_notset;
335 default:
336 return mi_lttng_loglevel_str_unknown;
337 }
338 break;
339 default:
340 return mi_lttng_loglevel_str_unknown;
341 }
342 }
343
344 LTTNG_HIDDEN
345 const char *mi_lttng_logleveltype_string(enum lttng_loglevel_type value)
346 {
347 switch (value) {
348 case LTTNG_EVENT_LOGLEVEL_ALL:
349 return mi_lttng_loglevel_type_all;
350 case LTTNG_EVENT_LOGLEVEL_RANGE:
351 return mi_lttng_loglevel_type_range;
352 case LTTNG_EVENT_LOGLEVEL_SINGLE:
353 return mi_lttng_loglevel_type_single;
354 default:
355 return mi_lttng_loglevel_type_unknown;
356 }
357 }
358
359 static
360 const char *mi_lttng_eventtype_string(enum lttng_event_type value)
361 {
362 switch (value) {
363 case LTTNG_EVENT_ALL:
364 return config_event_type_all;
365 case LTTNG_EVENT_TRACEPOINT:
366 return config_event_type_tracepoint;
367 case LTTNG_EVENT_PROBE:
368 return config_event_type_probe;
369 case LTTNG_EVENT_USERSPACE_PROBE:
370 return config_event_type_userspace_probe;
371 case LTTNG_EVENT_FUNCTION:
372 return config_event_type_function;
373 case LTTNG_EVENT_FUNCTION_ENTRY:
374 return config_event_type_function_entry;
375 case LTTNG_EVENT_SYSCALL:
376 return config_event_type_syscall;
377 case LTTNG_EVENT_NOOP:
378 return config_event_type_noop;
379 default:
380 return mi_lttng_element_empty;
381 }
382 }
383
384 static
385 const char *mi_lttng_event_contexttype_string(enum lttng_event_context_type val)
386 {
387 switch (val) {
388 case LTTNG_EVENT_CONTEXT_PID:
389 return config_event_context_pid;
390 case LTTNG_EVENT_CONTEXT_PROCNAME:
391 return config_event_context_procname;
392 case LTTNG_EVENT_CONTEXT_PRIO:
393 return config_event_context_prio;
394 case LTTNG_EVENT_CONTEXT_NICE:
395 return config_event_context_nice;
396 case LTTNG_EVENT_CONTEXT_VPID:
397 return config_event_context_vpid;
398 case LTTNG_EVENT_CONTEXT_TID:
399 return config_event_context_tid;
400 case LTTNG_EVENT_CONTEXT_VTID:
401 return config_event_context_vtid;
402 case LTTNG_EVENT_CONTEXT_PPID:
403 return config_event_context_ppid;
404 case LTTNG_EVENT_CONTEXT_VPPID:
405 return config_event_context_vppid;
406 case LTTNG_EVENT_CONTEXT_PTHREAD_ID:
407 return config_event_context_pthread_id;
408 case LTTNG_EVENT_CONTEXT_HOSTNAME:
409 return config_event_context_hostname;
410 case LTTNG_EVENT_CONTEXT_IP:
411 return config_event_context_ip;
412 case LTTNG_EVENT_CONTEXT_INTERRUPTIBLE:
413 return config_event_context_interruptible;
414 case LTTNG_EVENT_CONTEXT_PREEMPTIBLE:
415 return config_event_context_preemptible;
416 case LTTNG_EVENT_CONTEXT_NEED_RESCHEDULE:
417 return config_event_context_need_reschedule;
418 case LTTNG_EVENT_CONTEXT_MIGRATABLE:
419 return config_event_context_migratable;
420 case LTTNG_EVENT_CONTEXT_CALLSTACK_USER:
421 return config_event_context_callstack_user;
422 case LTTNG_EVENT_CONTEXT_CALLSTACK_KERNEL:
423 return config_event_context_callstack_kernel;
424 case LTTNG_EVENT_CONTEXT_CGROUP_NS:
425 return config_event_context_cgroup_ns;
426 case LTTNG_EVENT_CONTEXT_IPC_NS:
427 return config_event_context_ipc_ns;
428 case LTTNG_EVENT_CONTEXT_MNT_NS:
429 return config_event_context_mnt_ns;
430 case LTTNG_EVENT_CONTEXT_NET_NS:
431 return config_event_context_net_ns;
432 case LTTNG_EVENT_CONTEXT_PID_NS:
433 return config_event_context_pid_ns;
434 case LTTNG_EVENT_CONTEXT_TIME_NS:
435 return config_event_context_time_ns;
436 case LTTNG_EVENT_CONTEXT_USER_NS:
437 return config_event_context_user_ns;
438 case LTTNG_EVENT_CONTEXT_UTS_NS:
439 return config_event_context_uts_ns;
440 case LTTNG_EVENT_CONTEXT_UID:
441 return config_event_context_uid;
442 case LTTNG_EVENT_CONTEXT_EUID:
443 return config_event_context_euid;
444 case LTTNG_EVENT_CONTEXT_SUID:
445 return config_event_context_suid;
446 case LTTNG_EVENT_CONTEXT_GID:
447 return config_event_context_gid;
448 case LTTNG_EVENT_CONTEXT_EGID:
449 return config_event_context_egid;
450 case LTTNG_EVENT_CONTEXT_SGID:
451 return config_event_context_sgid;
452 case LTTNG_EVENT_CONTEXT_VUID:
453 return config_event_context_vuid;
454 case LTTNG_EVENT_CONTEXT_VEUID:
455 return config_event_context_veuid;
456 case LTTNG_EVENT_CONTEXT_VSUID:
457 return config_event_context_vsuid;
458 case LTTNG_EVENT_CONTEXT_VGID:
459 return config_event_context_vgid;
460 case LTTNG_EVENT_CONTEXT_VEGID:
461 return config_event_context_vegid;
462 case LTTNG_EVENT_CONTEXT_VSGID:
463 return config_event_context_vsgid;
464 default:
465 return NULL;
466 }
467 }
468
469 LTTNG_HIDDEN
470 const char *mi_lttng_eventfieldtype_string(enum lttng_event_field_type val)
471 {
472 switch (val) {
473 case(LTTNG_EVENT_FIELD_INTEGER):
474 return mi_lttng_element_type_integer;
475 case(LTTNG_EVENT_FIELD_ENUM):
476 return mi_lttng_element_type_enum;
477 case(LTTNG_EVENT_FIELD_FLOAT):
478 return mi_lttng_element_type_float;
479 case(LTTNG_EVENT_FIELD_STRING):
480 return mi_lttng_element_type_string;
481 default:
482 return mi_lttng_element_type_other;
483 }
484 }
485
486 LTTNG_HIDDEN
487 const char *mi_lttng_domaintype_string(enum lttng_domain_type value)
488 {
489 /* Note: This is a *duplicate* of get_domain_str from bin/lttng/utils.c */
490 switch (value) {
491 case LTTNG_DOMAIN_KERNEL:
492 return config_domain_type_kernel;
493 case LTTNG_DOMAIN_UST:
494 return config_domain_type_ust;
495 case LTTNG_DOMAIN_JUL:
496 return config_domain_type_jul;
497 case LTTNG_DOMAIN_LOG4J:
498 return config_domain_type_log4j;
499 case LTTNG_DOMAIN_PYTHON:
500 return config_domain_type_python;
501 default:
502 /* Should not have an unknown domain */
503 assert(0);
504 return NULL;
505 }
506 }
507
508 LTTNG_HIDDEN
509 const char *mi_lttng_buffertype_string(enum lttng_buffer_type value)
510 {
511 switch (value) {
512 case LTTNG_BUFFER_PER_PID:
513 return config_buffer_type_per_pid;
514 case LTTNG_BUFFER_PER_UID:
515 return config_buffer_type_per_uid;
516 case LTTNG_BUFFER_GLOBAL:
517 return config_buffer_type_global;
518 default:
519 /* Should not have an unknow buffer type */
520 assert(0);
521 return NULL;
522 }
523 }
524
525 LTTNG_HIDDEN
526 const char *mi_lttng_rotation_state_string(enum lttng_rotation_state value)
527 {
528 switch (value) {
529 case LTTNG_ROTATION_STATE_ONGOING:
530 return mi_lttng_rotation_state_str_ongoing;
531 case LTTNG_ROTATION_STATE_COMPLETED:
532 return mi_lttng_rotation_state_str_completed;
533 case LTTNG_ROTATION_STATE_EXPIRED:
534 return mi_lttng_rotation_state_str_expired;
535 case LTTNG_ROTATION_STATE_ERROR:
536 return mi_lttng_rotation_state_str_error;
537 default:
538 /* Should not have an unknow rotation state. */
539 assert(0);
540 return NULL;
541 }
542 }
543
544 LTTNG_HIDDEN
545 const char *mi_lttng_trace_archive_location_relay_protocol_type_string(
546 enum lttng_trace_archive_location_relay_protocol_type value)
547 {
548 switch (value) {
549 case LTTNG_TRACE_ARCHIVE_LOCATION_RELAY_PROTOCOL_TYPE_TCP:
550 return mi_lttng_rotation_location_relay_protocol_str_tcp;
551 default:
552 /* Should not have an unknow relay protocol. */
553 assert(0);
554 return NULL;
555 }
556 }
557
558 LTTNG_HIDDEN
559 struct mi_writer *mi_lttng_writer_create(int fd_output, int mi_output_type)
560 {
561 struct mi_writer *mi_writer;
562
563 mi_writer = zmalloc(sizeof(struct mi_writer));
564 if (!mi_writer) {
565 PERROR("zmalloc mi_writer_create");
566 goto end;
567 }
568 if (mi_output_type == LTTNG_MI_XML) {
569 mi_writer->writer = config_writer_create(fd_output, 0);
570 if (!mi_writer->writer) {
571 goto err_destroy;
572 }
573 mi_writer->type = LTTNG_MI_XML;
574 } else {
575 goto err_destroy;
576 }
577
578 end:
579 return mi_writer;
580
581 err_destroy:
582 free(mi_writer);
583 return NULL;
584 }
585
586 LTTNG_HIDDEN
587 int mi_lttng_writer_destroy(struct mi_writer *writer)
588 {
589 int ret;
590
591 if (!writer) {
592 ret = -EINVAL;
593 goto end;
594 }
595
596 ret = config_writer_destroy(writer->writer);
597 if (ret < 0) {
598 goto end;
599 }
600
601 free(writer);
602 end:
603 return ret;
604 }
605
606 LTTNG_HIDDEN
607 int mi_lttng_writer_command_open(struct mi_writer *writer, const char *command)
608 {
609 int ret;
610
611 /*
612 * A command is always the MI's root node, it must declare the current
613 * namespace and schema URIs and the schema's version.
614 */
615 ret = config_writer_open_element(writer->writer,
616 mi_lttng_element_command);
617 if (ret) {
618 goto end;
619 }
620
621 ret = config_writer_write_attribute(writer->writer,
622 mi_lttng_xmlns, DEFAULT_LTTNG_MI_NAMESPACE);
623 if (ret) {
624 goto end;
625 }
626
627 ret = config_writer_write_attribute(writer->writer,
628 mi_lttng_xmlns_xsi, mi_lttng_w3_schema_uri);
629 if (ret) {
630 goto end;
631 }
632
633 ret = config_writer_write_attribute(writer->writer,
634 mi_lttng_schema_location,
635 mi_lttng_schema_location_uri);
636 if (ret) {
637 goto end;
638 }
639
640 ret = config_writer_write_attribute(writer->writer,
641 mi_lttng_schema_version,
642 mi_lttng_schema_version_value);
643 if (ret) {
644 goto end;
645 }
646
647 ret = mi_lttng_writer_write_element_string(writer,
648 mi_lttng_element_command_name, command);
649 end:
650 return ret;
651 }
652
653 LTTNG_HIDDEN
654 int mi_lttng_writer_command_close(struct mi_writer *writer)
655 {
656 return mi_lttng_writer_close_element(writer);
657 }
658
659 LTTNG_HIDDEN
660 int mi_lttng_writer_open_element(struct mi_writer *writer,
661 const char *element_name)
662 {
663 return config_writer_open_element(writer->writer, element_name);
664 }
665
666 LTTNG_HIDDEN
667 int mi_lttng_writer_close_element(struct mi_writer *writer)
668 {
669 return config_writer_close_element(writer->writer);
670 }
671
672 LTTNG_HIDDEN
673 int mi_lttng_close_multi_element(struct mi_writer *writer,
674 unsigned int nb_element)
675 {
676 int ret, i;
677
678 if (nb_element < 1) {
679 ret = 0;
680 goto end;
681 }
682 for (i = 0; i < nb_element; i++) {
683 ret = mi_lttng_writer_close_element(writer);
684 if (ret) {
685 goto end;
686 }
687 }
688 end:
689 return ret;
690 }
691
692 LTTNG_HIDDEN
693 int mi_lttng_writer_write_element_unsigned_int(struct mi_writer *writer,
694 const char *element_name, uint64_t value)
695 {
696 return config_writer_write_element_unsigned_int(writer->writer,
697 element_name, value);
698 }
699
700 LTTNG_HIDDEN
701 int mi_lttng_writer_write_element_signed_int(struct mi_writer *writer,
702 const char *element_name, int64_t value)
703 {
704 return config_writer_write_element_signed_int(writer->writer,
705 element_name, value);
706 }
707
708 LTTNG_HIDDEN
709 int mi_lttng_writer_write_element_bool(struct mi_writer *writer,
710 const char *element_name, int value)
711 {
712 return config_writer_write_element_bool(writer->writer,
713 element_name, value);
714 }
715
716 LTTNG_HIDDEN
717 int mi_lttng_writer_write_element_string(struct mi_writer *writer,
718 const char *element_name, const char *value)
719 {
720 return config_writer_write_element_string(writer->writer,
721 element_name, value);
722 }
723
724 LTTNG_HIDDEN
725 int mi_lttng_writer_write_element_double(struct mi_writer *writer,
726 const char *element_name,
727 double value)
728 {
729 return config_writer_write_element_double(
730 writer->writer, element_name, value);
731 }
732
733 LTTNG_HIDDEN
734 int mi_lttng_version(struct mi_writer *writer, struct mi_lttng_version *version,
735 const char *lttng_description, const char *lttng_license)
736 {
737 int ret;
738
739 /* Open version */
740 ret = mi_lttng_writer_open_element(writer, mi_lttng_element_version);
741 if (ret) {
742 goto end;
743 }
744
745 /* Version string (contain info like rc etc.) */
746 ret = mi_lttng_writer_write_element_string(writer,
747 mi_lttng_element_version_str, version->version);
748 if (ret) {
749 goto end;
750 }
751
752 /* Major version number */
753 ret = mi_lttng_writer_write_element_unsigned_int(writer,
754 mi_lttng_element_version_major, version->version_major);
755 if (ret) {
756 goto end;
757 }
758
759 /* Minor version number */
760 ret = mi_lttng_writer_write_element_unsigned_int(writer,
761 mi_lttng_element_version_minor, version->version_minor);
762 if (ret) {
763 goto end;
764 }
765
766 /* Commit version number */
767 ret = mi_lttng_writer_write_element_string(writer,
768 mi_lttng_element_version_commit, version->version_commit);
769 if (ret) {
770 goto end;
771 }
772
773 /* Patch number */
774 ret = mi_lttng_writer_write_element_unsigned_int(writer,
775 mi_lttng_element_version_patch_level, version->version_patchlevel);
776 if (ret) {
777 goto end;
778 }
779
780 /* Name of the version */
781 ret = mi_lttng_writer_write_element_string(writer,
782 config_element_name, version->version_name);
783 if (ret) {
784 goto end;
785 }
786
787 /* Description mostly related to beer... */
788 ret = mi_lttng_writer_write_element_string(writer,
789 mi_lttng_element_version_description, lttng_description);
790 if (ret) {
791 goto end;
792 }
793
794 /* url */
795 ret = mi_lttng_writer_write_element_string(writer,
796 mi_lttng_element_version_web, version->package_url);
797 if (ret) {
798 goto end;
799 }
800
801 /* License: free as in free beer...no...*speech* */
802 ret = mi_lttng_writer_write_element_string(writer,
803 mi_lttng_element_version_license, lttng_license);
804 if (ret) {
805 goto end;
806 }
807
808 /* Close version element */
809 ret = mi_lttng_writer_close_element(writer);
810
811 end:
812 return ret;
813 }
814
815 LTTNG_HIDDEN
816 int mi_lttng_sessions_open(struct mi_writer *writer)
817 {
818 return mi_lttng_writer_open_element(writer, config_element_sessions);
819 }
820
821 LTTNG_HIDDEN
822 int mi_lttng_session(struct mi_writer *writer,
823 struct lttng_session *session, int is_open)
824 {
825 int ret;
826
827 assert(session);
828
829 /* Open sessions element */
830 ret = mi_lttng_writer_open_element(writer,
831 config_element_session);
832 if (ret) {
833 goto end;
834 }
835
836 /* Name of the session */
837 ret = mi_lttng_writer_write_element_string(writer,
838 config_element_name, session->name);
839 if (ret) {
840 goto end;
841 }
842
843 /* Path */
844 ret = mi_lttng_writer_write_element_string(writer,
845 config_element_path, session->path);
846 if (ret) {
847 goto end;
848 }
849
850 /* Enabled ? */
851 ret = mi_lttng_writer_write_element_bool(writer,
852 config_element_enabled, session->enabled);
853 if (ret) {
854 goto end;
855 }
856
857 /* Snapshot mode */
858 ret = mi_lttng_writer_write_element_unsigned_int(writer,
859 config_element_snapshot_mode, session->snapshot_mode);
860 if (ret) {
861 goto end;
862 }
863
864 /* Live timer interval in usec */
865 ret = mi_lttng_writer_write_element_unsigned_int(writer,
866 config_element_live_timer_interval,
867 session->live_timer_interval);
868 if (ret) {
869 goto end;
870 }
871
872 if (!is_open) {
873 /* Closing session element */
874 ret = mi_lttng_writer_close_element(writer);
875 }
876 end:
877 return ret;
878
879 }
880
881 LTTNG_HIDDEN
882 int mi_lttng_domains_open(struct mi_writer *writer)
883 {
884 return mi_lttng_writer_open_element(writer, config_element_domains);
885 }
886
887 LTTNG_HIDDEN
888 int mi_lttng_domain(struct mi_writer *writer,
889 struct lttng_domain *domain, int is_open)
890 {
891 int ret = 0;
892 const char *str_domain;
893 const char *str_buffer;
894
895 assert(domain);
896
897 /* Open domain element */
898 ret = mi_lttng_writer_open_element(writer, config_element_domain);
899 if (ret) {
900 goto end;
901 }
902
903 /* Domain Type */
904 str_domain = mi_lttng_domaintype_string(domain->type);
905 ret = mi_lttng_writer_write_element_string(writer, config_element_type,
906 str_domain);
907 if (ret) {
908 goto end;
909 }
910
911 /* Buffer Type */
912 str_buffer= mi_lttng_buffertype_string(domain->buf_type);
913 ret = mi_lttng_writer_write_element_string(writer,
914 config_element_buffer_type, str_buffer);
915 if (ret) {
916 goto end;
917 }
918
919 /* TODO: union attr
920 * This union is not currently used and was added for
921 * future ust domain support.
922 * Date: 25-06-2014
923 * */
924
925 if (!is_open) {
926 /* Closing domain element */
927 ret = mi_lttng_writer_close_element(writer);
928 }
929
930 end:
931 return ret;
932
933 }
934
935 LTTNG_HIDDEN
936 int mi_lttng_channels_open(struct mi_writer *writer)
937 {
938 return mi_lttng_writer_open_element(writer, config_element_channels);
939 }
940
941 LTTNG_HIDDEN
942 int mi_lttng_channel(struct mi_writer *writer,
943 struct lttng_channel *channel, int is_open)
944 {
945 int ret = 0;
946
947 assert(channel);
948
949 /* Opening channel element */
950 ret = mi_lttng_writer_open_element(writer, config_element_channel);
951 if (ret) {
952 goto end;
953 }
954
955 /* Name */
956 ret = mi_lttng_writer_write_element_string(writer, config_element_name,
957 channel->name);
958 if (ret) {
959 goto end;
960 }
961
962 /* Enabled ? */
963 ret = mi_lttng_writer_write_element_bool(writer,
964 config_element_enabled, channel->enabled);
965 if (ret) {
966 goto end;
967 }
968
969 /* Attribute */
970 ret = mi_lttng_channel_attr(writer, &channel->attr);
971 if (ret) {
972 goto end;
973 }
974
975 if (!is_open) {
976 /* Closing channel element */
977 ret = mi_lttng_writer_close_element(writer);
978 if (ret) {
979 goto end;
980 }
981 }
982 end:
983 return ret;
984 }
985
986 LTTNG_HIDDEN
987 int mi_lttng_channel_attr(struct mi_writer *writer,
988 struct lttng_channel_attr *attr)
989 {
990 int ret = 0;
991 struct lttng_channel *chan = caa_container_of(attr,
992 struct lttng_channel, attr);
993 uint64_t discarded_events, lost_packets, monitor_timer_interval;
994 int64_t blocking_timeout;
995
996 assert(attr);
997
998 ret = lttng_channel_get_discarded_event_count(chan, &discarded_events);
999 if (ret) {
1000 goto end;
1001 }
1002
1003 ret = lttng_channel_get_lost_packet_count(chan, &lost_packets);
1004 if (ret) {
1005 goto end;
1006 }
1007
1008 ret = lttng_channel_get_monitor_timer_interval(chan,
1009 &monitor_timer_interval);
1010 if (ret) {
1011 goto end;
1012 }
1013
1014 ret = lttng_channel_get_blocking_timeout(chan,
1015 &blocking_timeout);
1016 if (ret) {
1017 goto end;
1018 }
1019
1020 /* Opening Attributes */
1021 ret = mi_lttng_writer_open_element(writer, config_element_attributes);
1022 if (ret) {
1023 goto end;
1024 }
1025
1026 /* Overwrite */
1027 ret = mi_lttng_writer_write_element_string(writer,
1028 config_element_overwrite_mode,
1029 attr->overwrite ? config_overwrite_mode_overwrite :
1030 config_overwrite_mode_discard);
1031 if (ret) {
1032 goto end;
1033 }
1034
1035 /* Sub buffer size in byte */
1036 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1037 config_element_subbuf_size, attr->subbuf_size);
1038 if (ret) {
1039 goto end;
1040 }
1041
1042 /* Number of subbuffer (power of two) */
1043 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1044 config_element_num_subbuf,
1045 attr->num_subbuf);
1046 if (ret) {
1047 goto end;
1048 }
1049
1050 /* Switch timer interval in usec */
1051 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1052 config_element_switch_timer_interval,
1053 attr->switch_timer_interval);
1054 if (ret) {
1055 goto end;
1056 }
1057
1058 /* Read timer interval in usec */
1059 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1060 config_element_read_timer_interval,
1061 attr->read_timer_interval);
1062 if (ret) {
1063 goto end;
1064 }
1065
1066 /* Monitor timer interval in usec */
1067 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1068 config_element_monitor_timer_interval,
1069 monitor_timer_interval);
1070 if (ret) {
1071 goto end;
1072 }
1073
1074 /* Retry timeout in usec */
1075 ret = mi_lttng_writer_write_element_signed_int(writer,
1076 config_element_blocking_timeout,
1077 blocking_timeout);
1078 if (ret) {
1079 goto end;
1080 }
1081
1082 /* Event output */
1083 ret = mi_lttng_writer_write_element_string(writer,
1084 config_element_output_type,
1085 attr->output == LTTNG_EVENT_SPLICE ?
1086 config_output_type_splice : config_output_type_mmap);
1087 if (ret) {
1088 goto end;
1089 }
1090
1091 /* Tracefile size in bytes */
1092 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1093 config_element_tracefile_size, attr->tracefile_size);
1094 if (ret) {
1095 goto end;
1096 }
1097
1098 /* Count of tracefiles */
1099 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1100 config_element_tracefile_count,
1101 attr->tracefile_count);
1102 if (ret) {
1103 goto end;
1104 }
1105
1106 /* Live timer interval in usec*/
1107 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1108 config_element_live_timer_interval,
1109 attr->live_timer_interval);
1110 if (ret) {
1111 goto end;
1112 }
1113
1114 /* Discarded events */
1115 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1116 config_element_discarded_events,
1117 discarded_events);
1118 if (ret) {
1119 goto end;
1120 }
1121
1122 /* Lost packets */
1123 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1124 config_element_lost_packets,
1125 lost_packets);
1126 if (ret) {
1127 goto end;
1128 }
1129
1130 /* Closing attributes */
1131 ret = mi_lttng_writer_close_element(writer);
1132 if (ret) {
1133 goto end;
1134 }
1135 end:
1136 return ret;
1137
1138 }
1139
1140 LTTNG_HIDDEN
1141 int mi_lttng_event_common_attributes(struct mi_writer *writer,
1142 struct lttng_event *event)
1143 {
1144 int ret;
1145 const char *filter_expression;
1146
1147 /* Open event element */
1148 ret = mi_lttng_writer_open_element(writer, config_element_event);
1149 if (ret) {
1150 goto end;
1151 }
1152
1153 /* Event name */
1154 ret = mi_lttng_writer_write_element_string(writer,
1155 config_element_name, event->name);
1156 if (ret) {
1157 goto end;
1158 }
1159
1160 /* Event type */
1161 ret = mi_lttng_writer_write_element_string(writer,
1162 config_element_type, mi_lttng_eventtype_string(event->type));
1163 if (ret) {
1164 goto end;
1165 }
1166
1167 /* Is event enabled */
1168 ret = mi_lttng_writer_write_element_bool(writer,
1169 config_element_enabled, event->enabled);
1170 if (ret) {
1171 goto end;
1172 }
1173
1174 /* Event filter expression */
1175 ret = lttng_event_get_filter_expression(event, &filter_expression);
1176 if (ret) {
1177 goto end;
1178 }
1179
1180 if (filter_expression) {
1181 ret = mi_lttng_writer_write_element_string(writer,
1182 config_element_filter_expression,
1183 filter_expression);
1184 if (ret) {
1185 goto end;
1186 }
1187 }
1188
1189 end:
1190 return ret;
1191 }
1192
1193 static int write_event_exclusions(struct mi_writer *writer,
1194 struct lttng_event *event)
1195 {
1196 int i;
1197 int ret;
1198 int exclusion_count;
1199
1200 /* Open event exclusions */
1201 ret = mi_lttng_writer_open_element(writer, config_element_exclusions);
1202 if (ret) {
1203 goto end;
1204 }
1205
1206 exclusion_count = lttng_event_get_exclusion_name_count(event);
1207 if (exclusion_count < 0) {
1208 ret = exclusion_count;
1209 goto end;
1210 }
1211
1212 for (i = 0; i < exclusion_count; i++) {
1213 const char *name;
1214
1215 ret = lttng_event_get_exclusion_name(event, i, &name);
1216 if (ret) {
1217 /* Close exclusions */
1218 mi_lttng_writer_close_element(writer);
1219 goto end;
1220 }
1221
1222 ret = mi_lttng_writer_write_element_string(writer,
1223 config_element_exclusion, name);
1224 if (ret) {
1225 /* Close exclusions */
1226 mi_lttng_writer_close_element(writer);
1227 goto end;
1228 }
1229 }
1230
1231 /* Close exclusions */
1232 ret = mi_lttng_writer_close_element(writer);
1233
1234 end:
1235 return ret;
1236 }
1237
1238 LTTNG_HIDDEN
1239 int mi_lttng_event_tracepoint_loglevel(struct mi_writer *writer,
1240 struct lttng_event *event, enum lttng_domain_type domain)
1241 {
1242 int ret;
1243
1244 /* Event loglevel */
1245 ret = mi_lttng_writer_write_element_string(writer,
1246 config_element_loglevel,
1247 mi_lttng_loglevel_string(event->loglevel, domain));
1248 if (ret) {
1249 goto end;
1250 }
1251
1252 /* Log level type */
1253 ret = mi_lttng_writer_write_element_string(writer,
1254 config_element_loglevel_type,
1255 mi_lttng_logleveltype_string(event->loglevel_type));
1256 if (ret) {
1257 goto end;
1258 }
1259
1260 /* Event exclusions */
1261 ret = write_event_exclusions(writer, event);
1262
1263 end:
1264 return ret;
1265 }
1266
1267 LTTNG_HIDDEN
1268 int mi_lttng_event_tracepoint_no_loglevel(struct mi_writer *writer,
1269 struct lttng_event *event)
1270 {
1271 /* event exclusion filter */
1272 return write_event_exclusions(writer, event);
1273 }
1274
1275 LTTNG_HIDDEN
1276 int mi_lttng_event_function_probe(struct mi_writer *writer,
1277 struct lttng_event *event)
1278 {
1279 int ret;
1280
1281 ret = mi_lttng_writer_open_element(writer, config_element_attributes);
1282 if (ret) {
1283 goto end;
1284 }
1285
1286 ret = mi_lttng_writer_open_element(writer, config_element_probe_attributes);
1287 if (ret) {
1288 goto end;
1289 }
1290
1291 if (event->attr.probe.addr != 0) {
1292 /* event probe address */
1293 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1294 config_element_address, event->attr.probe.addr);
1295 if (ret) {
1296 goto end;
1297 }
1298 } else {
1299 /* event probe offset */
1300 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1301 config_element_offset, event->attr.probe.offset);
1302 if (ret) {
1303 goto end;
1304 }
1305
1306 /* event probe symbol_name */
1307 ret = mi_lttng_writer_write_element_string(writer,
1308 config_element_symbol_name, event->attr.probe.symbol_name);
1309 if (ret) {
1310 goto end;
1311 }
1312 }
1313
1314 /* Close probe_attributes and attributes */
1315 ret = mi_lttng_close_multi_element(writer, 2);
1316 end:
1317 return ret;
1318 }
1319
1320 static
1321 int mi_lttng_event_userspace_probe(struct mi_writer *writer,
1322 struct lttng_event *event)
1323 {
1324 int ret;
1325 const struct lttng_userspace_probe_location *location;
1326 const struct lttng_userspace_probe_location_lookup_method *lookup_method;
1327 enum lttng_userspace_probe_location_lookup_method_type lookup_type;
1328
1329 location = lttng_event_get_userspace_probe_location(event);
1330 if (!location) {
1331 ret = -LTTNG_ERR_INVALID;
1332 goto end;
1333 }
1334
1335 lookup_method = lttng_userspace_probe_location_get_lookup_method(location);
1336 if (!lookup_method) {
1337 ret = -LTTNG_ERR_INVALID;
1338 goto end;
1339 }
1340
1341 lookup_type = lttng_userspace_probe_location_lookup_method_get_type(lookup_method);
1342
1343 ret = mi_lttng_writer_open_element(writer, config_element_attributes);
1344 if (ret) {
1345 goto end;
1346 }
1347
1348 switch (lttng_userspace_probe_location_get_type(location)) {
1349 case LTTNG_USERSPACE_PROBE_LOCATION_TYPE_FUNCTION:
1350 {
1351 const char *function_name;
1352 const char *binary_path;
1353
1354 ret = mi_lttng_writer_open_element(writer,
1355 config_element_userspace_probe_function_attributes);
1356 if (ret) {
1357 goto end;
1358 }
1359
1360 switch (lookup_type) {
1361 case LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_FUNCTION_ELF:
1362 ret = mi_lttng_writer_write_element_string(writer,
1363 config_element_userspace_probe_lookup,
1364 config_element_userspace_probe_lookup_function_elf);
1365 if (ret) {
1366 goto end;
1367 }
1368 break;
1369 case LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_FUNCTION_DEFAULT:
1370 ret = mi_lttng_writer_write_element_string(writer,
1371 config_element_userspace_probe_lookup,
1372 config_element_userspace_probe_lookup_function_default);
1373 if (ret) {
1374 goto end;
1375 }
1376 break;
1377 default:
1378 goto end;
1379 }
1380
1381 binary_path = lttng_userspace_probe_location_function_get_binary_path(location);
1382 ret = mi_lttng_writer_write_element_string(writer,
1383 config_element_userspace_probe_location_binary_path, binary_path);
1384 if (ret) {
1385 goto end;
1386 }
1387
1388 function_name = lttng_userspace_probe_location_function_get_function_name(location);
1389 ret = mi_lttng_writer_write_element_string(writer,
1390 config_element_userspace_probe_function_location_function_name,
1391 function_name);
1392 if (ret) {
1393 goto end;
1394 }
1395
1396 break;
1397 }
1398 case LTTNG_USERSPACE_PROBE_LOCATION_TYPE_TRACEPOINT:
1399 {
1400 const char *probe_name, *provider_name;
1401 const char *binary_path;
1402
1403 ret = mi_lttng_writer_open_element(writer,
1404 config_element_userspace_probe_function_attributes);
1405 if (ret) {
1406 goto end;
1407 }
1408
1409 switch (lookup_type) {
1410 case LTTNG_USERSPACE_PROBE_LOCATION_LOOKUP_METHOD_TYPE_TRACEPOINT_SDT:
1411 ret = mi_lttng_writer_write_element_string(writer,
1412 config_element_userspace_probe_lookup,
1413 config_element_userspace_probe_lookup_tracepoint_sdt);
1414 if (ret) {
1415 goto end;
1416 }
1417 break;
1418 default:
1419 goto end;
1420 }
1421
1422 binary_path = lttng_userspace_probe_location_tracepoint_get_binary_path(location);
1423 ret = mi_lttng_writer_write_element_string(writer,
1424 config_element_userspace_probe_location_binary_path,
1425 binary_path);
1426 if (ret) {
1427 goto end;
1428 }
1429
1430 provider_name = lttng_userspace_probe_location_tracepoint_get_provider_name(location);
1431 ret = mi_lttng_writer_write_element_string(writer,
1432 config_element_userspace_probe_tracepoint_location_provider_name,
1433 provider_name);
1434 if (ret) {
1435 goto end;
1436 }
1437
1438 probe_name = lttng_userspace_probe_location_tracepoint_get_probe_name(location);
1439 ret = mi_lttng_writer_write_element_string(writer,
1440 config_element_userspace_probe_tracepoint_location_probe_name, probe_name);
1441 if (ret) {
1442 goto end;
1443 }
1444 break;
1445 }
1446 default:
1447 ERR("Invalid probe type encountered");
1448 }
1449 /* Close probe_attributes and attributes */
1450 ret = mi_lttng_close_multi_element(writer, 2);
1451 end:
1452 return ret;
1453 }
1454
1455 LTTNG_HIDDEN
1456 int mi_lttng_event_function_entry(struct mi_writer *writer,
1457 struct lttng_event *event)
1458 {
1459 int ret;
1460
1461 ret = mi_lttng_writer_open_element(writer, config_element_attributes);
1462 if (ret) {
1463 goto end;
1464 }
1465
1466 ret = mi_lttng_writer_open_element(writer, config_element_probe_attributes);
1467 if (ret) {
1468 goto end;
1469 }
1470
1471 /* event probe symbol_name */
1472 ret = mi_lttng_writer_write_element_string(writer,
1473 config_element_symbol_name, event->attr.ftrace.symbol_name);
1474 if (ret) {
1475 goto end;
1476 }
1477
1478 /* Close function_attributes and attributes */
1479 ret = mi_lttng_close_multi_element(writer, 2);
1480 end:
1481 return ret;
1482 }
1483
1484 LTTNG_HIDDEN
1485 int mi_lttng_events_open(struct mi_writer *writer)
1486 {
1487 return mi_lttng_writer_open_element(writer, config_element_events);
1488 }
1489
1490 LTTNG_HIDDEN
1491 int mi_lttng_event(struct mi_writer *writer,
1492 struct lttng_event *event, int is_open, enum lttng_domain_type domain)
1493 {
1494 int ret;
1495
1496 ret = mi_lttng_event_common_attributes(writer, event);
1497 if (ret) {
1498 goto end;
1499 }
1500
1501 switch (event->type) {
1502 case LTTNG_EVENT_TRACEPOINT:
1503 {
1504 if (event->loglevel != -1) {
1505 ret = mi_lttng_event_tracepoint_loglevel(writer, event, domain);
1506 } else {
1507 ret = mi_lttng_event_tracepoint_no_loglevel(writer, event);
1508 }
1509 break;
1510 }
1511 case LTTNG_EVENT_FUNCTION:
1512 /* Fallthrough */
1513 case LTTNG_EVENT_PROBE:
1514 ret = mi_lttng_event_function_probe(writer, event);
1515 break;
1516 case LTTNG_EVENT_FUNCTION_ENTRY:
1517 ret = mi_lttng_event_function_entry(writer, event);
1518 break;
1519 case LTTNG_EVENT_USERSPACE_PROBE:
1520 ret = mi_lttng_event_userspace_probe(writer, event);
1521 break;
1522 case LTTNG_EVENT_ALL:
1523 /* Fallthrough */
1524 default:
1525 break;
1526 }
1527
1528 if (ret) {
1529 goto end;
1530 }
1531
1532 if (!is_open) {
1533 ret = mi_lttng_writer_close_element(writer);
1534 }
1535
1536 end:
1537 return ret;
1538 }
1539
1540 LTTNG_HIDDEN
1541 int mi_lttng_trackers_open(struct mi_writer *writer)
1542 {
1543 return mi_lttng_writer_open_element(
1544 writer, config_element_process_attr_trackers);
1545 }
1546
1547 static int get_tracker_elements(enum lttng_process_attr process_attr,
1548 const char **element_process_attr_tracker,
1549 const char **element_process_attr_value)
1550 {
1551 int ret = 0;
1552
1553 switch (process_attr) {
1554 case LTTNG_PROCESS_ATTR_PROCESS_ID:
1555 *element_process_attr_tracker =
1556 config_element_process_attr_tracker_pid;
1557 *element_process_attr_value =
1558 config_element_process_attr_pid_value;
1559 break;
1560 case LTTNG_PROCESS_ATTR_VIRTUAL_PROCESS_ID:
1561 *element_process_attr_tracker =
1562 config_element_process_attr_tracker_vpid;
1563 *element_process_attr_value =
1564 config_element_process_attr_vpid_value;
1565 break;
1566 case LTTNG_PROCESS_ATTR_USER_ID:
1567 *element_process_attr_tracker =
1568 config_element_process_attr_tracker_uid;
1569 *element_process_attr_value =
1570 config_element_process_attr_uid_value;
1571 break;
1572 case LTTNG_PROCESS_ATTR_VIRTUAL_USER_ID:
1573 *element_process_attr_tracker =
1574 config_element_process_attr_tracker_vuid;
1575 *element_process_attr_value =
1576 config_element_process_attr_vuid_value;
1577 break;
1578 case LTTNG_PROCESS_ATTR_GROUP_ID:
1579 *element_process_attr_tracker =
1580 config_element_process_attr_tracker_gid;
1581 *element_process_attr_value =
1582 config_element_process_attr_gid_value;
1583 break;
1584 case LTTNG_PROCESS_ATTR_VIRTUAL_GROUP_ID:
1585 *element_process_attr_tracker =
1586 config_element_process_attr_tracker_vgid;
1587 *element_process_attr_value =
1588 config_element_process_attr_vgid_value;
1589 break;
1590 default:
1591 ret = LTTNG_ERR_SAVE_IO_FAIL;
1592 }
1593 return ret;
1594 }
1595
1596 LTTNG_HIDDEN
1597 int mi_lttng_process_attribute_tracker_open(
1598 struct mi_writer *writer, enum lttng_process_attr process_attr)
1599 {
1600 int ret;
1601 const char *element_tracker, *element_value;
1602
1603 ret = get_tracker_elements(
1604 process_attr, &element_tracker, &element_value);
1605 if (ret) {
1606 return ret;
1607 }
1608
1609 /* Open process attribute tracker element */
1610 ret = mi_lttng_writer_open_element(writer, element_tracker);
1611 if (ret) {
1612 goto end;
1613 }
1614
1615 /* Open values element */
1616 ret = mi_lttng_process_attr_values_open(writer);
1617 end:
1618 return ret;
1619 }
1620
1621 LTTNG_HIDDEN
1622 int mi_lttng_pids_open(struct mi_writer *writer)
1623 {
1624 return mi_lttng_writer_open_element(writer, config_element_pids);
1625 }
1626
1627 /*
1628 * TODO: move the listing of pid for user agent to process semantic on
1629 * mi api bump. The use of process element break the mi api.
1630 */
1631 LTTNG_HIDDEN
1632 int mi_lttng_pid(struct mi_writer *writer,
1633 pid_t pid,
1634 const char *name,
1635 int is_open)
1636 {
1637 int ret;
1638
1639 /* Open pid process */
1640 ret = mi_lttng_writer_open_element(writer, config_element_pid);
1641 if (ret) {
1642 goto end;
1643 }
1644
1645 /* Writing pid number */
1646 ret = mi_lttng_writer_write_element_signed_int(writer,
1647 mi_lttng_element_pid_id, (int)pid);
1648 if (ret) {
1649 goto end;
1650 }
1651
1652 /* Writing name of the process */
1653 if (name) {
1654 ret = mi_lttng_writer_write_element_string(writer, config_element_name,
1655 name);
1656 if (ret) {
1657 goto end;
1658 }
1659 }
1660
1661 if (!is_open) {
1662 /* Closing Pid */
1663 ret = mi_lttng_writer_close_element(writer);
1664 }
1665
1666 end:
1667 return ret;
1668 }
1669
1670 LTTNG_HIDDEN
1671 int mi_lttng_process_attr_values_open(struct mi_writer *writer)
1672 {
1673 return mi_lttng_writer_open_element(
1674 writer, config_element_process_attr_values);
1675 }
1676
1677 LTTNG_HIDDEN
1678 int mi_lttng_all_process_attribute_value(struct mi_writer *writer,
1679 enum lttng_process_attr process_attr,
1680 bool is_open)
1681 {
1682 int ret;
1683 const char *element_id_tracker, *element_target_id;
1684
1685 ret = get_tracker_elements(
1686 process_attr, &element_id_tracker, &element_target_id);
1687 if (ret) {
1688 return ret;
1689 }
1690
1691 ret = mi_lttng_writer_open_element(writer, element_target_id);
1692 if (ret) {
1693 goto end;
1694 }
1695
1696 ret = mi_lttng_writer_open_element(writer, config_element_type);
1697 if (ret) {
1698 goto end;
1699 }
1700
1701 ret = mi_lttng_writer_write_element_bool(writer, config_element_all, 1);
1702 if (ret) {
1703 goto end;
1704 }
1705
1706 ret = mi_lttng_writer_close_element(writer);
1707 if (ret) {
1708 goto end;
1709 }
1710
1711 if (!is_open) {
1712 ret = mi_lttng_writer_close_element(writer);
1713 if (ret) {
1714 goto end;
1715 }
1716 }
1717 end:
1718 return ret;
1719 }
1720
1721 LTTNG_HIDDEN
1722 int mi_lttng_integral_process_attribute_value(struct mi_writer *writer,
1723 enum lttng_process_attr process_attr,
1724 int64_t value,
1725 bool is_open)
1726 {
1727 int ret;
1728 const char *element_id_tracker, *element_target_id;
1729
1730 ret = get_tracker_elements(
1731 process_attr, &element_id_tracker, &element_target_id);
1732 if (ret) {
1733 return ret;
1734 }
1735
1736 ret = mi_lttng_writer_open_element(writer, element_target_id);
1737 if (ret) {
1738 goto end;
1739 }
1740
1741 ret = mi_lttng_writer_open_element(writer, config_element_type);
1742 if (ret) {
1743 goto end;
1744 }
1745
1746 ret = mi_lttng_writer_write_element_signed_int(
1747 writer, config_element_process_attr_id, value);
1748 if (ret) {
1749 goto end;
1750 }
1751
1752 ret = mi_lttng_writer_close_element(writer);
1753 if (ret) {
1754 goto end;
1755 }
1756
1757 if (!is_open) {
1758 ret = mi_lttng_writer_close_element(writer);
1759 if (ret) {
1760 goto end;
1761 }
1762 }
1763
1764 end:
1765 return ret;
1766 }
1767
1768 LTTNG_HIDDEN
1769 int mi_lttng_string_process_attribute_value(struct mi_writer *writer,
1770 enum lttng_process_attr process_attr,
1771 const char *value,
1772 bool is_open)
1773
1774 {
1775 int ret;
1776 const char *element_id_tracker, *element_target_id;
1777
1778 ret = get_tracker_elements(
1779 process_attr, &element_id_tracker, &element_target_id);
1780 if (ret) {
1781 return ret;
1782 }
1783
1784 ret = mi_lttng_writer_open_element(writer, element_target_id);
1785 if (ret) {
1786 goto end;
1787 }
1788
1789 ret = mi_lttng_writer_open_element(writer, config_element_type);
1790 if (ret) {
1791 goto end;
1792 }
1793
1794 ret = mi_lttng_writer_write_element_string(
1795 writer, config_element_name, value);
1796 if (ret) {
1797 goto end;
1798 }
1799
1800 ret = mi_lttng_writer_close_element(writer);
1801 if (ret) {
1802 goto end;
1803 }
1804
1805 if (!is_open) {
1806 ret = mi_lttng_writer_close_element(writer);
1807 if (ret) {
1808 goto end;
1809 }
1810 }
1811
1812 end:
1813 return ret;
1814 }
1815
1816 LTTNG_HIDDEN
1817 int mi_lttng_event_fields_open(struct mi_writer *writer)
1818 {
1819 return mi_lttng_writer_open_element(writer, mi_lttng_element_event_fields);
1820 }
1821
1822 LTTNG_HIDDEN
1823 int mi_lttng_event_field(struct mi_writer *writer,
1824 struct lttng_event_field *field)
1825 {
1826 int ret;
1827
1828 if (!field->field_name[0]) {
1829 ret = 0;
1830 goto end;
1831 }
1832
1833 /* Open field */
1834 ret = mi_lttng_writer_open_element(writer, mi_lttng_element_event_field);
1835 if (ret) {
1836 goto end;
1837 }
1838
1839 if (!field->field_name[0]) {
1840 goto close;
1841 }
1842
1843 /* Name */
1844 ret = mi_lttng_writer_write_element_string(writer, config_element_name,
1845 field->field_name);
1846 if (ret) {
1847 goto end;
1848 }
1849
1850 /* Type */
1851 ret = mi_lttng_writer_write_element_string(writer, config_element_type,
1852 mi_lttng_eventfieldtype_string(field->type));
1853 if (ret) {
1854 goto end;
1855 }
1856
1857 /* nowrite */
1858 ret = mi_lttng_writer_write_element_signed_int(writer,
1859 mi_lttng_element_nowrite, field->nowrite);
1860 if (ret) {
1861 goto end;
1862 }
1863
1864 close:
1865 /* Close field element */
1866 ret = mi_lttng_writer_close_element(writer);
1867
1868 end:
1869 return ret;
1870 }
1871
1872 LTTNG_HIDDEN
1873 int mi_lttng_perf_counter_context(struct mi_writer *writer,
1874 struct lttng_event_perf_counter_ctx *perf_context)
1875 {
1876 int ret;
1877
1878 /* Open perf_counter_context */
1879 ret = mi_lttng_writer_open_element(writer,
1880 mi_lttng_element_perf_counter_context);
1881 if (ret) {
1882 goto end;
1883 }
1884
1885 /* Type */
1886 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1887 config_element_type, perf_context->type);
1888 if (ret) {
1889 goto end;
1890 }
1891
1892 /* Config */
1893 ret = mi_lttng_writer_write_element_unsigned_int(writer,
1894 config_element_config, perf_context->config);
1895 if (ret) {
1896 goto end;
1897 }
1898
1899 /* Name of the perf counter */
1900 ret = mi_lttng_writer_write_element_string(writer,
1901 config_element_name, perf_context->name);
1902 if (ret) {
1903 goto end;
1904 }
1905
1906 /* Close perf_counter_context */
1907 ret = mi_lttng_writer_close_element(writer);
1908 end:
1909 return ret;
1910 }
1911
1912 static
1913 int mi_lttng_app_context(struct mi_writer *writer,
1914 const char *provider_name, const char *ctx_name)
1915 {
1916 int ret;
1917
1918 /* Open app */
1919 ret = mi_lttng_writer_open_element(writer,
1920 config_element_context_app);
1921 if (ret) {
1922 goto end;
1923 }
1924
1925 /* provider_name */
1926 ret = mi_lttng_writer_write_element_string(writer,
1927 config_element_context_app_provider_name,
1928 provider_name);
1929 if (ret) {
1930 goto end;
1931 }
1932
1933 /* ctx_name */
1934 ret = mi_lttng_writer_write_element_string(writer,
1935 config_element_context_app_ctx_name, ctx_name);
1936 if (ret) {
1937 goto end;
1938 }
1939
1940 /* Close app */
1941 ret = mi_lttng_writer_close_element(writer);
1942 end:
1943 return ret;
1944 }
1945
1946 LTTNG_HIDDEN
1947 int mi_lttng_context(struct mi_writer *writer,
1948 struct lttng_event_context *context, int is_open)
1949 {
1950 int ret;
1951
1952 /* Open context */
1953 ret = mi_lttng_writer_open_element(writer , config_element_context);
1954 if (ret) {
1955 goto end;
1956 }
1957
1958 /* Special case for PERF_*_COUNTER
1959 * print the lttng_event_perf_counter_ctx*/
1960 switch (context->ctx) {
1961 case LTTNG_EVENT_CONTEXT_PERF_COUNTER:
1962 case LTTNG_EVENT_CONTEXT_PERF_THREAD_COUNTER:
1963 case LTTNG_EVENT_CONTEXT_PERF_CPU_COUNTER:
1964 {
1965 struct lttng_event_perf_counter_ctx *perf_context =
1966 &context->u.perf_counter;
1967 ret = mi_lttng_perf_counter_context(writer, perf_context);
1968 if (ret) {
1969 goto end;
1970 }
1971 break;
1972 }
1973 case LTTNG_EVENT_CONTEXT_APP_CONTEXT:
1974 {
1975 ret = mi_lttng_app_context(writer,
1976 context->u.app_ctx.provider_name,
1977 context->u.app_ctx.ctx_name);
1978 if (ret) {
1979 goto end;
1980 }
1981 break;
1982 }
1983 default:
1984 {
1985 const char *type_string = mi_lttng_event_contexttype_string(
1986 context->ctx);
1987 if (!type_string) {
1988 ret = -LTTNG_ERR_INVALID;
1989 goto end;
1990 }
1991
1992 /* Print context type */
1993 ret = mi_lttng_writer_write_element_string(writer,
1994 config_element_type, type_string);
1995 break;
1996 }
1997 }
1998
1999 /* Close context */
2000 if (!is_open) {
2001 ret = mi_lttng_writer_close_element(writer);
2002 }
2003
2004 end:
2005 return ret;
2006 }
2007
2008 LTTNG_HIDDEN
2009 int mi_lttng_snapshot_output_session_name(struct mi_writer *writer,
2010 const char *session_name)
2011 {
2012 int ret;
2013
2014 /* Open session element */
2015 ret = mi_lttng_writer_open_element(writer, config_element_session);
2016 if (ret) {
2017 goto end;
2018 }
2019
2020 /* Snapshot output list for current session name */
2021 ret = mi_lttng_writer_write_element_string(writer, config_element_name,
2022 session_name);
2023 if (ret) {
2024 goto end;
2025 }
2026
2027 /* Open element snapshots (sequence one snapshot) */
2028 ret = mi_lttng_writer_open_element(writer, mi_lttng_element_snapshots);
2029 if (ret) {
2030 goto end;
2031 }
2032
2033 end:
2034 return ret;
2035 }
2036
2037 LTTNG_HIDDEN
2038 int mi_lttng_snapshot_list_output(struct mi_writer *writer,
2039 struct lttng_snapshot_output *output)
2040 {
2041 int ret;
2042
2043 /* Open element snapshot output */
2044 ret = mi_lttng_writer_open_element(writer,
2045 mi_lttng_element_command_snapshot);
2046 if (ret) {
2047 goto end;
2048 }
2049
2050 /* ID of the snapshot output */
2051 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2052 mi_lttng_element_id, output->id);
2053 if (ret) {
2054 goto end;
2055 }
2056
2057 /* Name of the output */
2058 ret = mi_lttng_writer_write_element_string(writer, config_element_name,
2059 output->name);
2060 if (ret) {
2061 goto end;
2062 }
2063
2064 /* Destination of the output (ctrl_url)*/
2065 ret = mi_lttng_writer_write_element_string(writer,
2066 mi_lttng_element_snapshot_ctrl_url, output->ctrl_url);
2067 if (ret) {
2068 goto end;
2069 }
2070
2071 /* Destination of the output (data_url) */
2072 ret = mi_lttng_writer_write_element_string(writer,
2073 mi_lttng_element_snapshot_data_url, output->data_url);
2074 if (ret) {
2075 goto end;
2076 }
2077
2078 /* total size of all stream combined */
2079 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2080 mi_lttng_element_snapshot_max_size, output->max_size);
2081 if (ret) {
2082 goto end;
2083 }
2084
2085 /* Close snapshot output element */
2086 ret = mi_lttng_writer_close_element(writer);
2087
2088 end:
2089 return ret;
2090 }
2091
2092 LTTNG_HIDDEN
2093 int mi_lttng_snapshot_del_output(struct mi_writer *writer, int id,
2094 const char *name, const char *current_session_name)
2095 {
2096 int ret;
2097
2098 /* Open element del_snapshot */
2099 ret = mi_lttng_writer_open_element(writer,
2100 mi_lttng_element_command_snapshot);
2101 if (ret) {
2102 goto end;
2103 }
2104
2105
2106 if (id != UINT32_MAX) {
2107 /* "Snapshot output "id" successfully deleted
2108 * for "current_session_name"
2109 * ID of the snapshot output
2110 */
2111 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2112 mi_lttng_element_id, id);
2113 if (ret) {
2114 goto end;
2115 }
2116 } else {
2117 /* "Snapshot output "name" successfully deleted
2118 * for session "current_session_name"
2119 * Name of the output
2120 */
2121 ret = mi_lttng_writer_write_element_string(writer, config_element_name,
2122 name);
2123 if (ret) {
2124 goto end;
2125 }
2126 }
2127
2128 /* Snapshot was deleted for session "current_session_name"*/
2129 ret = mi_lttng_writer_write_element_string(writer,
2130 mi_lttng_element_snapshot_session_name,
2131 current_session_name);
2132 if (ret) {
2133 goto end;
2134 }
2135
2136 /* Close snapshot element */
2137 ret = mi_lttng_writer_close_element(writer);
2138
2139 end:
2140 return ret;
2141 }
2142
2143 LTTNG_HIDDEN
2144 int mi_lttng_snapshot_add_output(struct mi_writer *writer,
2145 const char *current_session_name, const char *n_ptr,
2146 struct lttng_snapshot_output *output)
2147 {
2148 int ret;
2149
2150 /* Open element snapshot */
2151 ret = mi_lttng_writer_open_element(writer,
2152 mi_lttng_element_command_snapshot);
2153 if (ret) {
2154 goto end;
2155 }
2156
2157 /* Snapshot output id */
2158 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2159 mi_lttng_element_id, output->id);
2160 if (ret) {
2161 goto end;
2162 }
2163
2164 /* Snapshot output names */
2165 ret = mi_lttng_writer_write_element_string(writer,
2166 config_element_name, n_ptr);
2167 if (ret) {
2168 goto end;
2169 }
2170
2171 /* Destination of the output (ctrl_url)*/
2172 ret = mi_lttng_writer_write_element_string(writer,
2173 mi_lttng_element_snapshot_ctrl_url, output->ctrl_url);
2174 if (ret) {
2175 goto end;
2176 }
2177
2178 /* Snapshot added for session "current_session_name"*/
2179 ret = mi_lttng_writer_write_element_string(writer,
2180 mi_lttng_element_snapshot_session_name, current_session_name);
2181 if (ret) {
2182 goto end;
2183 }
2184
2185 /* total size of all stream combined */
2186 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2187 mi_lttng_element_snapshot_max_size, output->max_size);
2188 if (ret) {
2189 goto end;
2190 }
2191
2192 /* Close snapshot element */
2193 ret = mi_lttng_writer_close_element(writer);
2194
2195 end:
2196 return ret;
2197 }
2198
2199 LTTNG_HIDDEN
2200 int mi_lttng_snapshot_record(struct mi_writer *writer,
2201 const char *current_session_name, const char *url,
2202 const char *cmdline_ctrl_url, const char *cmdline_data_url)
2203 {
2204 int ret;
2205
2206 /* Open element snapshot */
2207 ret = mi_lttng_writer_open_element(writer,
2208 mi_lttng_element_command_snapshot);
2209 if (ret) {
2210 goto end;
2211 }
2212
2213 /*
2214 * If a valid an URL was given, serialize it,
2215 * else take the command line data and ctrl urls*/
2216 if (url) {
2217 /* Destination of the output (ctrl_url)*/
2218 ret = mi_lttng_writer_write_element_string(writer,
2219 mi_lttng_element_snapshot_ctrl_url, url);
2220 if (ret) {
2221 goto end;
2222 }
2223 } else if (cmdline_ctrl_url) {
2224 /* Destination of the output (ctrl_url)*/
2225 ret = mi_lttng_writer_write_element_string(writer,
2226 mi_lttng_element_snapshot_ctrl_url, cmdline_ctrl_url);
2227 if (ret) {
2228 goto end;
2229 }
2230
2231 /* Destination of the output (data_url) */
2232 ret = mi_lttng_writer_write_element_string(writer,
2233 mi_lttng_element_snapshot_data_url, cmdline_data_url);
2234 if (ret) {
2235 goto end;
2236 }
2237 }
2238
2239 /* Close record_snapshot element */
2240 ret = mi_lttng_writer_close_element(writer);
2241
2242 end:
2243 return ret;
2244 }
2245
2246 LTTNG_HIDDEN
2247 int mi_lttng_rotation_schedule(struct mi_writer *writer,
2248 const struct lttng_rotation_schedule *schedule)
2249 {
2250 int ret = 0;
2251 enum lttng_rotation_status status;
2252 uint64_t value;
2253 const char *element_name;
2254 const char *value_name;
2255 bool empty_schedule = false;
2256
2257 switch (lttng_rotation_schedule_get_type(schedule)) {
2258 case LTTNG_ROTATION_SCHEDULE_TYPE_PERIODIC:
2259 status = lttng_rotation_schedule_periodic_get_period(schedule,
2260 &value);
2261 element_name = mi_lttng_element_rotation_schedule_periodic;
2262 value_name = mi_lttng_element_rotation_schedule_periodic_time_us;
2263 break;
2264 case LTTNG_ROTATION_SCHEDULE_TYPE_SIZE_THRESHOLD:
2265 status = lttng_rotation_schedule_size_threshold_get_threshold(
2266 schedule, &value);
2267 element_name = mi_lttng_element_rotation_schedule_size_threshold;
2268 value_name = mi_lttng_element_rotation_schedule_size_threshold_bytes;
2269 break;
2270 default:
2271 ret = -1;
2272 goto end;
2273 }
2274
2275 if (status != LTTNG_ROTATION_STATUS_OK) {
2276 if (status == LTTNG_ROTATION_STATUS_UNAVAILABLE) {
2277 empty_schedule = true;
2278 } else {
2279 ret = -1;
2280 goto end;
2281 }
2282 }
2283
2284 ret = mi_lttng_writer_open_element(writer, element_name);
2285 if (ret) {
2286 goto end;
2287 }
2288
2289 if (!empty_schedule) {
2290 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2291 value_name, value);
2292 if (ret) {
2293 goto end;
2294 }
2295 }
2296
2297 /* Close schedule descriptor element. */
2298 ret = mi_lttng_writer_close_element(writer);
2299 if (ret) {
2300 goto end;
2301 }
2302 end:
2303 return ret;
2304 }
2305
2306 LTTNG_HIDDEN
2307 int mi_lttng_rotation_schedule_result(struct mi_writer *writer,
2308 const struct lttng_rotation_schedule *schedule,
2309 bool success)
2310 {
2311 int ret = 0;
2312
2313 ret = mi_lttng_writer_open_element(writer,
2314 mi_lttng_element_rotation_schedule_result);
2315 if (ret) {
2316 goto end;
2317 }
2318
2319 ret = mi_lttng_writer_open_element(writer,
2320 mi_lttng_element_rotation_schedule);
2321 if (ret) {
2322 goto end;
2323 }
2324
2325 ret = mi_lttng_rotation_schedule(writer, schedule);
2326 if (ret) {
2327 goto end;
2328 }
2329
2330 /* Close rotation_schedule element */
2331 ret = mi_lttng_writer_close_element(writer);
2332 if (ret) {
2333 goto end;
2334 }
2335
2336 ret = mi_lttng_writer_write_element_bool(writer,
2337 mi_lttng_element_command_success, success);
2338 if (ret) {
2339 goto end;
2340 }
2341
2342 /* Close rotation_schedule_result element */
2343 ret = mi_lttng_writer_close_element(writer);
2344 if (ret) {
2345 goto end;
2346 }
2347 end:
2348 return ret;
2349 }
2350
2351 static
2352 int mi_lttng_location(struct mi_writer *writer,
2353 const struct lttng_trace_archive_location *location)
2354 {
2355 int ret = 0;
2356 enum lttng_trace_archive_location_type location_type;
2357 enum lttng_trace_archive_location_status status;
2358
2359 location_type = lttng_trace_archive_location_get_type(location);
2360
2361 switch (location_type) {
2362 case LTTNG_TRACE_ARCHIVE_LOCATION_TYPE_LOCAL:
2363 {
2364 const char *absolute_path;
2365
2366 status = lttng_trace_archive_location_local_get_absolute_path(
2367 location, &absolute_path);
2368 if (status != LTTNG_TRACE_ARCHIVE_LOCATION_STATUS_OK) {
2369 ret = -1;
2370 goto end;
2371 }
2372
2373 ret = mi_lttng_writer_open_element(writer,
2374 mi_lttng_element_rotation_location_local);
2375 if (ret) {
2376 goto end;
2377 }
2378
2379
2380 ret = mi_lttng_writer_write_element_string(writer,
2381 mi_lttng_element_rotation_location_local_absolute_path,
2382 absolute_path);
2383 if (ret) {
2384 goto end;
2385 }
2386
2387 /* Close local element */
2388 ret = mi_lttng_writer_close_element(writer);
2389 if (ret) {
2390 goto end;
2391 }
2392 break;
2393 }
2394 case LTTNG_TRACE_ARCHIVE_LOCATION_TYPE_RELAY:
2395 {
2396 uint16_t control_port, data_port;
2397 const char *host, *relative_path;
2398 enum lttng_trace_archive_location_relay_protocol_type protocol;
2399
2400 /* Fetch all relay location parameters. */
2401 status = lttng_trace_archive_location_relay_get_protocol_type(
2402 location, &protocol);
2403 if (status != LTTNG_TRACE_ARCHIVE_LOCATION_STATUS_OK) {
2404 ret = -1;
2405 goto end;
2406 }
2407
2408 status = lttng_trace_archive_location_relay_get_host(
2409 location, &host);
2410 if (status != LTTNG_TRACE_ARCHIVE_LOCATION_STATUS_OK) {
2411 ret = -1;
2412 goto end;
2413 }
2414
2415 status = lttng_trace_archive_location_relay_get_control_port(
2416 location, &control_port);
2417 if (status != LTTNG_TRACE_ARCHIVE_LOCATION_STATUS_OK) {
2418 ret = -1;
2419 goto end;
2420 }
2421
2422 status = lttng_trace_archive_location_relay_get_data_port(
2423 location, &data_port);
2424 if (status != LTTNG_TRACE_ARCHIVE_LOCATION_STATUS_OK) {
2425 ret = -1;
2426 goto end;
2427 }
2428
2429 status = lttng_trace_archive_location_relay_get_relative_path(
2430 location, &relative_path);
2431 if (status != LTTNG_TRACE_ARCHIVE_LOCATION_STATUS_OK) {
2432 ret = -1;
2433 goto end;
2434 }
2435
2436 ret = mi_lttng_writer_open_element(writer,
2437 mi_lttng_element_rotation_location_relay);
2438 if (ret) {
2439 goto end;
2440 }
2441
2442 ret = mi_lttng_writer_write_element_string(writer,
2443 mi_lttng_element_rotation_location_relay_host,
2444 host);
2445 if (ret) {
2446 goto end;
2447 }
2448
2449 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2450 mi_lttng_element_rotation_location_relay_control_port,
2451 control_port);
2452 if (ret) {
2453 goto end;
2454 }
2455
2456 ret = mi_lttng_writer_write_element_unsigned_int(writer,
2457 mi_lttng_element_rotation_location_relay_data_port,
2458 data_port);
2459 if (ret) {
2460 goto end;
2461 }
2462
2463 ret = mi_lttng_writer_write_element_string(writer,
2464 mi_lttng_element_rotation_location_relay_protocol,
2465 mi_lttng_trace_archive_location_relay_protocol_type_string(protocol));
2466 if (ret) {
2467 goto end;
2468 }
2469
2470 ret = mi_lttng_writer_write_element_string(writer,
2471 mi_lttng_element_rotation_location_relay_relative_path,
2472 relative_path);
2473 if (ret) {
2474 goto end;
2475 }
2476
2477 /* Close relay element */
2478 ret = mi_lttng_writer_close_element(writer);
2479 if (ret) {
2480 goto end;
2481 }
2482 break;
2483 }
2484 default:
2485 abort();
2486 }
2487 end:
2488 return ret;
2489 }
2490
2491 LTTNG_HIDDEN
2492 int mi_lttng_rotate(struct mi_writer *writer,
2493 const char *session_name,
2494 enum lttng_rotation_state rotation_state,
2495 const struct lttng_trace_archive_location *location)
2496 {
2497 int ret;
2498
2499 ret = mi_lttng_writer_open_element(writer,
2500 mi_lttng_element_rotation);
2501 if (ret) {
2502 goto end;
2503 }
2504
2505 ret = mi_lttng_writer_write_element_string(writer,
2506 mi_lttng_element_session_name,
2507 session_name);
2508 if (ret) {
2509 goto end;
2510 }
2511
2512 ret = mi_lttng_writer_write_element_string(writer,
2513 mi_lttng_element_rotation_state,
2514 mi_lttng_rotation_state_string(rotation_state));
2515 if (ret) {
2516 goto end;
2517 }
2518
2519 if (!location) {
2520 /* Not a serialization error. */
2521 goto close_rotation;
2522 }
2523
2524 ret = mi_lttng_writer_open_element(writer,
2525 mi_lttng_element_rotation_location);
2526 if (ret) {
2527 goto end;
2528 }
2529
2530 ret = mi_lttng_location(writer, location);
2531 if (ret) {
2532 goto close_location;
2533 }
2534
2535 close_location:
2536 /* Close location element */
2537 ret = mi_lttng_writer_close_element(writer);
2538 if (ret) {
2539 goto end;
2540 }
2541
2542 close_rotation:
2543 /* Close rotation element */
2544 ret = mi_lttng_writer_close_element(writer);
2545 if (ret) {
2546 goto end;
2547 }
2548 end:
2549 return ret;
2550 }
This page took 0.135145 seconds and 5 git commands to generate.