kernel: Add new counter ABI IOCTL macros
[lttng-tools.git] / src / common / conditions / session-rotation.cpp
CommitLineData
c19092cd 1/*
ab5be9fa 2 * Copyright (C) 2017 Jérémie Galarneau <jeremie.galarneau@efficios.com>
c19092cd 3 *
ab5be9fa 4 * SPDX-License-Identifier: LGPL-2.1-only
c19092cd 5 *
c19092cd
JG
6 */
7
c9e313bc
SM
8#include <common/error.hpp>
9#include <common/macros.hpp>
10#include <common/mi-lttng.hpp>
28ab034a 11
c9e313bc
SM
12#include <lttng/condition/condition-internal.hpp>
13#include <lttng/condition/session-rotation-internal.hpp>
14#include <lttng/location-internal.hpp>
28ab034a 15
c19092cd
JG
16#include <stdbool.h>
17
28ab034a
JG
18static bool lttng_condition_session_rotation_validate(const struct lttng_condition *condition);
19static int lttng_condition_session_rotation_serialize(const struct lttng_condition *condition,
20 struct lttng_payload *payload);
21static bool lttng_condition_session_rotation_is_equal(const struct lttng_condition *_a,
22 const struct lttng_condition *_b);
23static void lttng_condition_session_rotation_destroy(struct lttng_condition *condition);
24
25static enum lttng_error_code
26lttng_condition_session_rotation_mi_serialize(const struct lttng_condition *condition,
27 struct mi_writer *writer);
28
29static const struct lttng_condition rotation_condition_template = {
a6bc4ca9
SM
30 {},
31 LTTNG_CONDITION_TYPE_UNKNOWN, /* type unset, shall be set on creation. */
32 lttng_condition_session_rotation_validate,
33 lttng_condition_session_rotation_serialize,
34 lttng_condition_session_rotation_is_equal,
35 lttng_condition_session_rotation_destroy,
36 lttng_condition_session_rotation_mi_serialize,
c19092cd
JG
37};
38
28ab034a
JG
39static int lttng_evaluation_session_rotation_serialize(const struct lttng_evaluation *evaluation,
40 struct lttng_payload *payload);
41static void lttng_evaluation_session_rotation_destroy(struct lttng_evaluation *evaluation);
c19092cd 42
28ab034a 43static const struct lttng_evaluation rotation_evaluation_template = {
a6bc4ca9
SM
44 LTTNG_CONDITION_TYPE_UNKNOWN, /* type unset, shall be set on creation. */
45 lttng_evaluation_session_rotation_serialize,
46 lttng_evaluation_session_rotation_destroy,
c19092cd
JG
47};
48
28ab034a 49static bool is_rotation_condition(const struct lttng_condition *condition)
c19092cd 50{
07c4863f 51 const lttng_condition_type type = lttng_condition_get_type(condition);
c19092cd
JG
52
53 return type == LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING ||
28ab034a 54 type == LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED;
c19092cd
JG
55}
56
28ab034a 57static bool is_rotation_evaluation(const struct lttng_evaluation *evaluation)
c19092cd 58{
07c4863f 59 const lttng_condition_type type = lttng_evaluation_get_type(evaluation);
c19092cd
JG
60
61 return type == LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING ||
28ab034a 62 type == LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED;
c19092cd
JG
63}
64
28ab034a 65static bool lttng_condition_session_rotation_validate(const struct lttng_condition *condition)
c19092cd
JG
66{
67 bool valid = false;
68 struct lttng_condition_session_rotation *rotation;
69
70 if (!condition) {
71 goto end;
72 }
73
28ab034a 74 rotation = lttng::utils::container_of(condition, &lttng_condition_session_rotation::parent);
c19092cd
JG
75 if (!rotation->session_name) {
76 ERR("Invalid session rotation condition: a target session name must be set.");
77 goto end;
78 }
79
80 valid = true;
81end:
82 return valid;
83}
84
28ab034a
JG
85static int lttng_condition_session_rotation_serialize(const struct lttng_condition *condition,
86 struct lttng_payload *payload)
c19092cd
JG
87{
88 int ret;
89 size_t session_name_len;
90 struct lttng_condition_session_rotation *rotation;
91 struct lttng_condition_session_rotation_comm rotation_comm;
92
93 if (!condition || !is_rotation_condition(condition)) {
94 ret = -1;
95 goto end;
96 }
97
98 DBG("Serializing session rotation condition");
28ab034a 99 rotation = lttng::utils::container_of(condition, &lttng_condition_session_rotation::parent);
c19092cd
JG
100
101 session_name_len = strlen(rotation->session_name) + 1;
102 if (session_name_len > LTTNG_NAME_MAX) {
103 ret = -1;
104 goto end;
105 }
106
107 rotation_comm.session_name_len = session_name_len;
28ab034a 108 ret = lttng_dynamic_buffer_append(&payload->buffer, &rotation_comm, sizeof(rotation_comm));
c19092cd
JG
109 if (ret) {
110 goto end;
111 }
28ab034a
JG
112 ret = lttng_dynamic_buffer_append(
113 &payload->buffer, rotation->session_name, session_name_len);
c19092cd
JG
114 if (ret) {
115 goto end;
116 }
117end:
118 return ret;
119}
120
28ab034a
JG
121static bool lttng_condition_session_rotation_is_equal(const struct lttng_condition *_a,
122 const struct lttng_condition *_b)
c19092cd
JG
123{
124 bool is_equal = false;
125 struct lttng_condition_session_rotation *a, *b;
126
0114db0e
JG
127 a = lttng::utils::container_of(_a, &lttng_condition_session_rotation::parent);
128 b = lttng::utils::container_of(_b, &lttng_condition_session_rotation::parent);
c19092cd
JG
129
130 /* Both session names must be set or both must be unset. */
28ab034a 131 if ((a->session_name && !b->session_name) || (!a->session_name && b->session_name)) {
c19092cd
JG
132 WARN("Comparing session rotation conditions with uninitialized session names.");
133 goto end;
134 }
135
5c7248cd 136 if (a->session_name && b->session_name && strcmp(a->session_name, b->session_name) != 0) {
c19092cd
JG
137 goto end;
138 }
139
140 is_equal = true;
141end:
142 return is_equal;
143}
144
28ab034a 145static void lttng_condition_session_rotation_destroy(struct lttng_condition *condition)
c19092cd
JG
146{
147 struct lttng_condition_session_rotation *rotation;
148
28ab034a 149 rotation = lttng::utils::container_of(condition, &lttng_condition_session_rotation::parent);
c19092cd
JG
150
151 free(rotation->session_name);
152 free(rotation);
153}
154
28ab034a
JG
155static struct lttng_condition *
156lttng_condition_session_rotation_create(enum lttng_condition_type type)
c19092cd
JG
157{
158 struct lttng_condition_session_rotation *condition;
159
64803277 160 condition = zmalloc<lttng_condition_session_rotation>();
c19092cd 161 if (!condition) {
cd9adb8b 162 return nullptr;
c19092cd
JG
163 }
164
28ab034a 165 memcpy(&condition->parent, &rotation_condition_template, sizeof(condition->parent));
c19092cd
JG
166 lttng_condition_init(&condition->parent, type);
167 return &condition->parent;
168}
169
170struct lttng_condition *lttng_condition_session_rotation_ongoing_create(void)
171{
172 return lttng_condition_session_rotation_create(
28ab034a 173 LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING);
c19092cd
JG
174}
175
176struct lttng_condition *lttng_condition_session_rotation_completed_create(void)
177{
178 return lttng_condition_session_rotation_create(
28ab034a 179 LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED);
c19092cd
JG
180}
181
28ab034a
JG
182static ssize_t init_condition_from_payload(struct lttng_condition *condition,
183 struct lttng_payload_view *src_view)
c19092cd
JG
184{
185 ssize_t ret, condition_size;
186 enum lttng_condition_status status;
c19092cd
JG
187 const char *session_name;
188 struct lttng_buffer_view name_view;
3e6e0df2 189 const struct lttng_condition_session_rotation_comm *condition_comm;
07c4863f 190 const lttng_payload_view condition_comm_view =
28ab034a 191 lttng_payload_view_from_view(src_view, 0, sizeof(*condition_comm));
c19092cd 192
3e6e0df2 193 if (!lttng_payload_view_is_valid(&condition_comm_view)) {
c19092cd
JG
194 ERR("Failed to initialize from malformed condition buffer: buffer too short to contain header");
195 ret = -1;
196 goto end;
197 }
198
c0a66c84 199 condition_comm = (typeof(condition_comm)) src_view->buffer.data;
28ab034a
JG
200 name_view = lttng_buffer_view_from_view(
201 &src_view->buffer, sizeof(*condition_comm), condition_comm->session_name_len);
c19092cd 202
3e6e0df2
JG
203 if (!lttng_buffer_view_is_valid(&name_view)) {
204 ERR("Failed to initialize from malformed condition buffer: buffer too short to contain session name");
c19092cd
JG
205 ret = -1;
206 goto end;
207 }
208
3e6e0df2
JG
209 if (condition_comm->session_name_len > LTTNG_NAME_MAX) {
210 ERR("Failed to initialize from malformed condition buffer: name exceeds LTTNG_MAX_NAME");
c19092cd
JG
211 ret = -1;
212 goto end;
213 }
214
215 session_name = name_view.data;
216 if (*(session_name + condition_comm->session_name_len - 1) != '\0') {
217 ERR("Malformed session name encountered in condition buffer");
218 ret = -1;
219 goto end;
220 }
221
28ab034a 222 status = lttng_condition_session_rotation_set_session_name(condition, session_name);
c19092cd
JG
223 if (status != LTTNG_CONDITION_STATUS_OK) {
224 ERR("Failed to set buffer consumed session name");
225 ret = -1;
226 goto end;
227 }
228
229 if (!lttng_condition_validate(condition)) {
230 ret = -1;
231 goto end;
232 }
233
28ab034a 234 condition_size = sizeof(*condition_comm) + (ssize_t) condition_comm->session_name_len;
c19092cd
JG
235 ret = condition_size;
236end:
237 return ret;
238}
239
28ab034a
JG
240static ssize_t
241lttng_condition_session_rotation_create_from_payload(struct lttng_payload_view *view,
242 struct lttng_condition **_condition,
243 enum lttng_condition_type type)
c19092cd
JG
244{
245 ssize_t ret;
cd9adb8b 246 struct lttng_condition *condition = nullptr;
c19092cd
JG
247
248 switch (type) {
249 case LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING:
250 condition = lttng_condition_session_rotation_ongoing_create();
251 break;
252 case LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED:
253 condition = lttng_condition_session_rotation_completed_create();
254 break;
255 default:
256 ret = -1;
257 goto error;
258 }
259
260 if (!_condition || !condition) {
261 ret = -1;
262 goto error;
263 }
264
c0a66c84 265 ret = init_condition_from_payload(condition, view);
c19092cd
JG
266 if (ret < 0) {
267 goto error;
268 }
269
270 *_condition = condition;
271 return ret;
272error:
273 lttng_condition_destroy(condition);
274 return ret;
275}
276
28ab034a
JG
277ssize_t
278lttng_condition_session_rotation_ongoing_create_from_payload(struct lttng_payload_view *view,
279 struct lttng_condition **condition)
c19092cd 280{
28ab034a
JG
281 return lttng_condition_session_rotation_create_from_payload(
282 view, condition, LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING);
c19092cd
JG
283}
284
28ab034a
JG
285ssize_t
286lttng_condition_session_rotation_completed_create_from_payload(struct lttng_payload_view *view,
287 struct lttng_condition **condition)
c19092cd 288{
28ab034a
JG
289 return lttng_condition_session_rotation_create_from_payload(
290 view, condition, LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED);
c19092cd
JG
291}
292
28ab034a
JG
293static struct lttng_evaluation *lttng_evaluation_session_rotation_create(
294 enum lttng_condition_type type, uint64_t id, struct lttng_trace_archive_location *location)
c19092cd
JG
295{
296 struct lttng_evaluation_session_rotation *evaluation;
297
64803277 298 evaluation = zmalloc<lttng_evaluation_session_rotation>();
c19092cd 299 if (!evaluation) {
cd9adb8b 300 return nullptr;
c19092cd
JG
301 }
302
28ab034a 303 memcpy(&evaluation->parent, &rotation_evaluation_template, sizeof(evaluation->parent));
c19092cd
JG
304 lttng_evaluation_init(&evaluation->parent, type);
305 evaluation->id = id;
d3740619
JR
306 if (location) {
307 lttng_trace_archive_location_get(location);
308 }
c19092cd
JG
309 evaluation->location = location;
310 return &evaluation->parent;
311}
312
28ab034a
JG
313static ssize_t create_evaluation_from_payload(enum lttng_condition_type type,
314 struct lttng_payload_view *view,
315 struct lttng_evaluation **_evaluation)
c19092cd
JG
316{
317 ssize_t ret, size;
cd9adb8b
JG
318 struct lttng_evaluation *evaluation = nullptr;
319 struct lttng_trace_archive_location *location = nullptr;
3e6e0df2 320 const struct lttng_evaluation_session_rotation_comm *comm;
07c4863f
JG
321 const lttng_payload_view comm_view =
322 lttng_payload_view_from_view(view, 0, sizeof(*comm));
c19092cd 323
3e6e0df2 324 if (!lttng_payload_view_is_valid(&comm_view)) {
c19092cd
JG
325 goto error;
326 }
327
3e6e0df2 328 comm = (typeof(comm)) comm_view.buffer.data;
c19092cd
JG
329 size = sizeof(*comm);
330 if (comm->has_location) {
3e6e0df2 331 const struct lttng_buffer_view location_view =
28ab034a 332 lttng_buffer_view_from_view(&view->buffer, sizeof(*comm), -1);
3e6e0df2
JG
333
334 if (!lttng_buffer_view_is_valid(&location_view)) {
c19092cd
JG
335 goto error;
336 }
337
28ab034a 338 ret = lttng_trace_archive_location_create_from_buffer(&location_view, &location);
c19092cd
JG
339 if (ret < 0) {
340 goto error;
341 }
342 size += ret;
343 }
344
28ab034a 345 evaluation = lttng_evaluation_session_rotation_create(type, comm->id, location);
c19092cd
JG
346 if (!evaluation) {
347 goto error;
348 }
349
d3740619 350 lttng_trace_archive_location_put(location);
c19092cd
JG
351 ret = size;
352 *_evaluation = evaluation;
353 return ret;
354error:
d3740619 355 lttng_trace_archive_location_put(location);
cd9adb8b 356 evaluation = nullptr;
c19092cd
JG
357 return -1;
358}
359
28ab034a
JG
360static ssize_t
361lttng_evaluation_session_rotation_create_from_payload(enum lttng_condition_type type,
362 struct lttng_payload_view *view,
363 struct lttng_evaluation **_evaluation)
c19092cd
JG
364{
365 ssize_t ret;
cd9adb8b 366 struct lttng_evaluation *evaluation = nullptr;
c19092cd
JG
367
368 if (!_evaluation) {
369 ret = -1;
370 goto error;
371 }
372
c0a66c84 373 ret = create_evaluation_from_payload(type, view, &evaluation);
c19092cd
JG
374 if (ret < 0) {
375 goto error;
376 }
377
378 *_evaluation = evaluation;
379 return ret;
380error:
381 lttng_evaluation_destroy(evaluation);
382 return ret;
383}
384
28ab034a
JG
385ssize_t
386lttng_evaluation_session_rotation_ongoing_create_from_payload(struct lttng_payload_view *view,
387 struct lttng_evaluation **evaluation)
c19092cd 388{
c0a66c84 389 return lttng_evaluation_session_rotation_create_from_payload(
28ab034a 390 LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING, view, evaluation);
c19092cd
JG
391}
392
c0a66c84 393ssize_t lttng_evaluation_session_rotation_completed_create_from_payload(
28ab034a 394 struct lttng_payload_view *view, struct lttng_evaluation **evaluation)
c19092cd 395{
c0a66c84 396 return lttng_evaluation_session_rotation_create_from_payload(
28ab034a 397 LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED, view, evaluation);
c19092cd
JG
398}
399
28ab034a 400struct lttng_evaluation *lttng_evaluation_session_rotation_ongoing_create(uint64_t id)
c19092cd
JG
401{
402 return lttng_evaluation_session_rotation_create(
cd9adb8b 403 LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING, id, nullptr);
c19092cd
JG
404}
405
28ab034a
JG
406struct lttng_evaluation *
407lttng_evaluation_session_rotation_completed_create(uint64_t id,
408 struct lttng_trace_archive_location *location)
c19092cd
JG
409{
410 return lttng_evaluation_session_rotation_create(
28ab034a 411 LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED, id, location);
c19092cd
JG
412}
413
414enum lttng_condition_status
28ab034a
JG
415lttng_condition_session_rotation_get_session_name(const struct lttng_condition *condition,
416 const char **session_name)
c19092cd
JG
417{
418 struct lttng_condition_session_rotation *rotation;
419 enum lttng_condition_status status = LTTNG_CONDITION_STATUS_OK;
420
421 if (!condition || !is_rotation_condition(condition) || !session_name) {
422 status = LTTNG_CONDITION_STATUS_INVALID;
423 goto end;
424 }
425
28ab034a 426 rotation = lttng::utils::container_of(condition, &lttng_condition_session_rotation::parent);
c19092cd
JG
427 if (!rotation->session_name) {
428 status = LTTNG_CONDITION_STATUS_UNSET;
429 goto end;
430 }
431 *session_name = rotation->session_name;
432end:
433 return status;
434}
435
436enum lttng_condition_status
28ab034a
JG
437lttng_condition_session_rotation_set_session_name(struct lttng_condition *condition,
438 const char *session_name)
c19092cd
JG
439{
440 char *session_name_copy;
441 struct lttng_condition_session_rotation *rotation;
442 enum lttng_condition_status status = LTTNG_CONDITION_STATUS_OK;
443
28ab034a
JG
444 if (!condition || !is_rotation_condition(condition) || !session_name ||
445 strlen(session_name) == 0) {
c19092cd
JG
446 status = LTTNG_CONDITION_STATUS_INVALID;
447 goto end;
448 }
449
28ab034a 450 rotation = lttng::utils::container_of(condition, &lttng_condition_session_rotation::parent);
c19092cd
JG
451 session_name_copy = strdup(session_name);
452 if (!session_name_copy) {
453 status = LTTNG_CONDITION_STATUS_ERROR;
454 goto end;
455 }
456
457 free(rotation->session_name);
458 rotation->session_name = session_name_copy;
459end:
460 return status;
461}
462
28ab034a
JG
463static int lttng_evaluation_session_rotation_serialize(const struct lttng_evaluation *evaluation,
464 struct lttng_payload *payload)
c19092cd
JG
465{
466 int ret;
467 struct lttng_evaluation_session_rotation *rotation;
1c9a0b0e 468 struct lttng_evaluation_session_rotation_comm comm = {};
c19092cd 469
28ab034a
JG
470 rotation =
471 lttng::utils::container_of(evaluation, &lttng_evaluation_session_rotation::parent);
c19092cd
JG
472 comm.id = rotation->id;
473 comm.has_location = !!rotation->location;
28ab034a 474 ret = lttng_dynamic_buffer_append(&payload->buffer, &comm, sizeof(comm));
c19092cd
JG
475 if (ret) {
476 goto end;
477 }
478 if (!rotation->location) {
479 goto end;
480 }
28ab034a 481 ret = lttng_trace_archive_location_serialize(rotation->location, &payload->buffer);
c19092cd
JG
482end:
483 return ret;
484}
485
28ab034a 486static void lttng_evaluation_session_rotation_destroy(struct lttng_evaluation *evaluation)
c19092cd
JG
487{
488 struct lttng_evaluation_session_rotation *rotation;
489
28ab034a
JG
490 rotation =
491 lttng::utils::container_of(evaluation, &lttng_evaluation_session_rotation::parent);
d3740619 492 lttng_trace_archive_location_put(rotation->location);
c19092cd
JG
493 free(rotation);
494}
495
496enum lttng_evaluation_status
28ab034a 497lttng_evaluation_session_rotation_get_id(const struct lttng_evaluation *evaluation, uint64_t *id)
c19092cd
JG
498{
499 const struct lttng_evaluation_session_rotation *rotation;
500 enum lttng_evaluation_status status = LTTNG_EVALUATION_STATUS_OK;
501
502 if (!evaluation || !id || !is_rotation_evaluation(evaluation)) {
503 status = LTTNG_EVALUATION_STATUS_INVALID;
504 goto end;
505 }
506
28ab034a
JG
507 rotation =
508 lttng::utils::container_of(evaluation, &lttng_evaluation_session_rotation::parent);
c19092cd
JG
509 *id = rotation->id;
510end:
511 return status;
512}
513
d3740619
JR
514/*
515 * The public API assumes that trace archive locations are always provided as
516 * "constant". This means that the user of liblttng-ctl never has to destroy a
517 * trace archive location. Hence, users of liblttng-ctl have no visibility of
518 * the reference counting of archive locations.
519 */
28ab034a
JG
520enum lttng_evaluation_status lttng_evaluation_session_rotation_completed_get_location(
521 const struct lttng_evaluation *evaluation,
522 const struct lttng_trace_archive_location **location)
c19092cd
JG
523{
524 const struct lttng_evaluation_session_rotation *rotation;
525 enum lttng_evaluation_status status = LTTNG_EVALUATION_STATUS_OK;
526
527 if (!evaluation || !location ||
28ab034a 528 evaluation->type != LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED) {
c19092cd
JG
529 status = LTTNG_EVALUATION_STATUS_INVALID;
530 goto end;
531 }
532
28ab034a
JG
533 rotation =
534 lttng::utils::container_of(evaluation, &lttng_evaluation_session_rotation::parent);
c19092cd
JG
535 *location = rotation->location;
536end:
537 return status;
538}
6a751b95 539
28ab034a
JG
540static enum lttng_error_code
541lttng_condition_session_rotation_mi_serialize(const struct lttng_condition *condition,
542 struct mi_writer *writer)
6a751b95
JR
543{
544 int ret;
545 enum lttng_error_code ret_code;
546 enum lttng_condition_status status;
cd9adb8b
JG
547 const char *session_name = nullptr;
548 const char *type_element_str = nullptr;
6a751b95 549
a0377dfe
FD
550 LTTNG_ASSERT(condition);
551 LTTNG_ASSERT(writer);
552 LTTNG_ASSERT(is_rotation_condition(condition));
6a751b95
JR
553
554 switch (lttng_condition_get_type(condition)) {
555 case LTTNG_CONDITION_TYPE_SESSION_ROTATION_COMPLETED:
28ab034a 556 type_element_str = mi_lttng_element_condition_session_rotation_completed;
6a751b95
JR
557 break;
558 case LTTNG_CONDITION_TYPE_SESSION_ROTATION_ONGOING:
28ab034a 559 type_element_str = mi_lttng_element_condition_session_rotation_ongoing;
6a751b95
JR
560 break;
561 default:
562 abort();
563 break;
564 }
565
28ab034a 566 status = lttng_condition_session_rotation_get_session_name(condition, &session_name);
a0377dfe
FD
567 LTTNG_ASSERT(status == LTTNG_CONDITION_STATUS_OK);
568 LTTNG_ASSERT(session_name);
6a751b95
JR
569
570 /* Open condition session rotation_* element. */
571 ret = mi_lttng_writer_open_element(writer, type_element_str);
572 if (ret) {
573 goto mi_error;
574 }
575
576 /* Session name. */
577 ret = mi_lttng_writer_write_element_string(
28ab034a 578 writer, mi_lttng_element_session_name, session_name);
6a751b95
JR
579 if (ret) {
580 goto mi_error;
581 }
582
583 /* Close condition session rotation element. */
584 ret = mi_lttng_writer_close_element(writer);
585 if (ret) {
586 goto mi_error;
587 }
588
589 ret_code = LTTNG_OK;
590 goto end;
591
592mi_error:
593 ret_code = LTTNG_ERR_MI_IO_FAIL;
594end:
595 return ret_code;
596}
This page took 0.095895 seconds and 5 git commands to generate.