Fix: liblttng-ctl: unreported truncations when copying strings
[lttng-tools.git] / src / lib / lttng-ctl / load.c
1 /*
2 * Copyright (C) 2014 David Goulet <dgoulet@efficios.com>
3 *
4 * SPDX-License-Identifier: LGPL-2.1-only
5 *
6 */
7
8 #define _LGPL_SOURCE
9 #include <assert.h>
10 #include <string.h>
11 #include <limits.h>
12
13 #include <lttng/lttng-error.h>
14 #include <lttng/load.h>
15 #include <lttng/load-internal.h>
16 #include <common/sessiond-comm/sessiond-comm.h>
17 #include <common/config/session-config.h>
18 #include <common/uri.h>
19 #include <common/macros.h>
20 #include <common/compat/string.h>
21
22 #include "lttng-ctl-helper.h"
23
24 struct lttng_load_session_attr *lttng_load_session_attr_create(void)
25 {
26 return zmalloc(sizeof(struct lttng_load_session_attr));
27 }
28
29 static
30 void reset_load_session_attr_urls(struct lttng_load_session_attr *attr)
31 {
32 free(attr->raw_override_url);
33 free(attr->raw_override_path_url);
34 free(attr->raw_override_ctrl_url);
35 free(attr->raw_override_data_url);
36 if (attr->override_attr) {
37 free(attr->override_attr->path_url);
38 free(attr->override_attr->ctrl_url);
39 free(attr->override_attr->data_url);
40 free(attr->override_attr->session_name);
41 }
42 }
43
44 void lttng_load_session_attr_destroy(struct lttng_load_session_attr *attr)
45 {
46 if (attr) {
47 reset_load_session_attr_urls(attr);
48 free(attr->override_attr);
49 free(attr);
50 }
51 }
52
53 static int validate_attr(const struct lttng_load_session_attr *attr)
54 {
55 int ret = 0;
56
57 if (!attr) {
58 ret = -LTTNG_ERR_INVALID;
59 goto end;
60 }
61
62 if (!attr->override_attr) {
63 goto end;
64 }
65
66 /*
67 * Refuse override name if the objective is to load multiple session
68 * since this operation is ambiguous while loading multiple session.
69 */
70 if (attr->override_attr->session_name
71 && attr->session_name[0] == '\0') {
72 ret = -LTTNG_ERR_INVALID;
73 goto end;
74 }
75 end:
76 return ret;
77 }
78
79 const char *lttng_load_session_attr_get_session_name(
80 struct lttng_load_session_attr *attr)
81 {
82 const char *ret = NULL;
83
84 if (attr && attr->session_name[0]) {
85 ret = attr->session_name;
86 }
87
88 return ret;
89 }
90
91 const char *lttng_load_session_attr_get_input_url(
92 struct lttng_load_session_attr *attr)
93 {
94 const char *ret = NULL;
95
96 if (attr && attr->input_url[0]) {
97 ret = attr->input_url;
98 }
99
100 return ret;
101 }
102
103 int lttng_load_session_attr_get_overwrite(
104 struct lttng_load_session_attr *attr)
105 {
106 return attr ? attr->overwrite : -LTTNG_ERR_INVALID;
107 }
108
109 const char *lttng_load_session_attr_get_override_ctrl_url(
110 struct lttng_load_session_attr *attr)
111 {
112 const char *ret = NULL;
113
114 if (!attr || !attr->override_attr) {
115 goto end;
116 }
117
118 ret = attr->raw_override_ctrl_url;
119 end:
120 return ret;
121 }
122
123 const char *lttng_load_session_attr_get_override_data_url(
124 struct lttng_load_session_attr *attr)
125 {
126 const char *ret = NULL;
127
128 if (!attr || !attr->override_attr) {
129 goto end;
130 }
131
132 ret = attr->raw_override_data_url;
133 end:
134 return ret;
135 }
136
137 const char *lttng_load_session_attr_get_override_url(
138 struct lttng_load_session_attr *attr)
139 {
140 const char *ret = NULL;
141
142 if (!attr || !attr->override_attr) {
143 goto end;
144 }
145
146 if ((attr->override_attr->path_url ||
147 (attr->override_attr->ctrl_url &&
148 attr->override_attr->data_url))) {
149 ret = attr->raw_override_url;
150 }
151 end:
152 return ret;
153 }
154
155 const char *lttng_load_session_attr_get_override_session_name(
156 struct lttng_load_session_attr *attr)
157 {
158 const char *ret = NULL;
159
160 if (!attr || !attr->override_attr) {
161 goto end;
162 }
163
164 ret = attr->override_attr->session_name;
165 end:
166 return ret;
167 }
168
169 int lttng_load_session_attr_set_session_name(
170 struct lttng_load_session_attr *attr, const char *session_name)
171 {
172 int ret = 0;
173
174 if (!attr) {
175 ret = -LTTNG_ERR_INVALID;
176 goto error;
177 }
178
179 if (session_name) {
180 size_t len;
181
182 len = strlen(session_name);
183 if (len >= LTTNG_NAME_MAX) {
184 ret = -LTTNG_ERR_INVALID;
185 goto error;
186 }
187
188 ret = lttng_strncpy(attr->session_name, session_name,
189 sizeof(attr->session_name));
190 if (ret) {
191 ret = -LTTNG_ERR_INVALID;
192 goto error;
193 }
194 } else {
195 attr->session_name[0] = '\0';
196 }
197 error:
198 return ret;
199 }
200
201 int lttng_load_session_attr_set_input_url(
202 struct lttng_load_session_attr *attr, const char *url)
203 {
204 int ret = 0;
205 size_t len;
206 ssize_t size;
207 struct lttng_uri *uris = NULL;
208
209 if (!attr) {
210 ret = -LTTNG_ERR_INVALID;
211 goto error;
212 }
213
214 if (!url) {
215 attr->input_url[0] = '\0';
216 ret = 0;
217 goto end;
218 }
219
220 len = strlen(url);
221 if (len >= PATH_MAX) {
222 ret = -LTTNG_ERR_INVALID;
223 goto error;
224 }
225
226 size = uri_parse_str_urls(url, NULL, &uris);
227 if (size <= 0 || uris[0].dtype != LTTNG_DST_PATH) {
228 ret = -LTTNG_ERR_INVALID;
229 goto error;
230 }
231
232 /* Copy string plus the NULL terminated byte. */
233 ret = lttng_strncpy(attr->input_url, uris[0].dst.path,
234 sizeof(attr->input_url));
235 if (ret) {
236 ret = -LTTNG_ERR_INVALID;
237 goto error;
238 }
239
240 end:
241 error:
242 free(uris);
243 return ret;
244 }
245
246 int lttng_load_session_attr_set_overwrite(
247 struct lttng_load_session_attr *attr, int overwrite)
248 {
249 int ret = 0;
250
251 if (!attr) {
252 ret = -LTTNG_ERR_INVALID;
253 goto end;
254 }
255
256 attr->overwrite = !!overwrite;
257 end:
258 return ret;
259 }
260
261 int lttng_load_session_attr_set_override_ctrl_url(
262 struct lttng_load_session_attr *attr, const char *url)
263 {
264 int ret = 0;
265 ssize_t ret_size;
266 struct lttng_uri *uri = NULL;
267 char *url_str = NULL;
268 char *raw_str = NULL;
269
270 if (!attr) {
271 ret = -LTTNG_ERR_INVALID;
272 goto end;
273 }
274
275 if (!attr->override_attr) {
276 attr->override_attr = zmalloc(
277 sizeof(struct config_load_session_override_attr));
278 if (!attr->override_attr) {
279 ret = -LTTNG_ERR_NOMEM;
280 goto end;
281 }
282 }
283
284 if (attr->override_attr->path_url) {
285 /*
286 * Setting a ctrl override after a path override makes no sense.
287 */
288 ret = -LTTNG_ERR_INVALID;
289 goto end;
290 }
291
292 /*
293 * FIXME: uri_parse should be able to take as parameter the protocol
294 * type to validate "url". For now only check the parsing goes through;
295 * it will fail later on.
296 */
297 ret_size = uri_parse(url, &uri);
298 if (ret_size < 0) {
299 ret = -LTTNG_ERR_INVALID;
300 goto end;
301 }
302
303 if (uri[0].port == 0) {
304 uri[0].port = DEFAULT_NETWORK_CONTROL_PORT;
305 }
306
307 url_str = zmalloc(PATH_MAX);
308 if (!url_str) {
309 /* FIXME: return valid error */
310 ret = -LTTNG_ERR_NOMEM;
311 goto end;
312 }
313
314 ret = uri_to_str_url(&uri[0], url_str, PATH_MAX);
315 if (ret < 0) {
316 ret = -LTTNG_ERR_INVALID;
317 goto end;
318 }
319 ret = 0;
320
321 raw_str = lttng_strndup(url, PATH_MAX);
322 if (!raw_str) {
323 ret = -LTTNG_ERR_NOMEM;
324 goto end;
325 }
326
327 /* Squash old value if any */
328 free(attr->override_attr->ctrl_url);
329 free(attr->raw_override_ctrl_url);
330
331 /* Populate the object */
332 attr->override_attr->ctrl_url = url_str;
333 attr->raw_override_ctrl_url = raw_str;
334
335 /* Ownership passed to attr. */
336 url_str = NULL;
337 raw_str = NULL;
338
339 end:
340 free(raw_str);
341 free(url_str);
342 free(uri);
343 return ret;
344 }
345
346 int lttng_load_session_attr_set_override_data_url(
347 struct lttng_load_session_attr *attr, const char *url)
348 {
349 int ret = 0;
350 ssize_t ret_size;
351 struct lttng_uri *uri = NULL;
352 char *url_str = NULL;
353 char *raw_str = NULL;
354
355 if (!attr) {
356 ret = -LTTNG_ERR_INVALID;
357 goto end;
358 }
359
360 if (!attr->override_attr) {
361 attr->override_attr = zmalloc(
362 sizeof(struct config_load_session_override_attr));
363 if (!attr->override_attr) {
364 ret = -LTTNG_ERR_NOMEM;
365 goto end;
366 }
367 }
368
369 if (attr->override_attr->path_url) {
370 /*
371 * Setting a data override after a path override makes no sense.
372 */
373 ret = -LTTNG_ERR_INVALID;
374 goto end;
375 }
376
377 /*
378 * FIXME: uri_parse should be able to take as parameter the protocol
379 * type to validate "url". For now only check the parsing goes through;
380 * it will fail later on.
381 */
382 ret_size = uri_parse(url, &uri);
383 if (ret_size < 0) {
384 ret = -LTTNG_ERR_INVALID;
385 goto end;
386 }
387
388 if (uri[0].port == 0) {
389 uri[0].port = DEFAULT_NETWORK_DATA_PORT;
390 }
391
392 url_str = zmalloc(PATH_MAX);
393 if (!url_str) {
394 ret = -LTTNG_ERR_NOMEM;
395 goto end;
396 }
397
398 ret = uri_to_str_url(&uri[0], url_str, PATH_MAX);
399 if (ret < 0) {
400 ret = -LTTNG_ERR_INVALID;
401 goto end;
402 }
403 ret = 0;
404
405 raw_str = lttng_strndup(url, PATH_MAX);
406 if (!raw_str) {
407 ret = -LTTNG_ERR_NOMEM;
408 goto end;
409 }
410
411 /* Squash old value if any */
412 free(attr->override_attr->data_url);
413 free(attr->raw_override_data_url);
414
415 /* Populate the object */
416 attr->override_attr->data_url = url_str;
417 attr->raw_override_data_url = raw_str;
418
419 /* Ownership passed to attr. */
420 url_str = NULL;
421 raw_str = NULL;
422 end:
423 free(raw_str);
424 free(url_str);
425 free(uri);
426 return ret;
427 }
428
429 int lttng_load_session_attr_set_override_url(
430 struct lttng_load_session_attr *attr, const char *url)
431 {
432 int ret = 0;
433 ssize_t ret_size;
434 struct lttng_uri *uri = NULL;
435 char *raw_url_str = NULL;
436 char *raw_path_str = NULL;
437 char *path_str = NULL;
438 char *raw_ctrl_str = NULL;
439 char *ctrl_str = NULL;
440 char *raw_data_str = NULL;
441 char *data_str = NULL;
442 char buffer[PATH_MAX];
443
444 if (!attr || !url || strlen(url) >= PATH_MAX) {
445 ret = -LTTNG_ERR_INVALID;
446 goto end;
447 }
448
449 if (!attr->override_attr) {
450 attr->override_attr = zmalloc(
451 sizeof(struct config_load_session_override_attr));
452 if (!attr->override_attr) {
453 ret = -LTTNG_ERR_NOMEM;
454 goto end;
455 }
456 }
457
458 /*
459 * FIXME: uri_parse should be able to take as parameter the protocol
460 * type to validate "url". For now only check the parsing goes through;
461 * it will fail later on.
462 */
463 ret_size = uri_parse_str_urls(url, NULL, &uri);
464 if (ret_size < 0 || ret_size > 2) {
465 /* Unexpected URL format. */
466 ret = -LTTNG_ERR_INVALID;
467 goto end;
468 }
469
470 raw_url_str = lttng_strndup(url, PATH_MAX);
471 if (!raw_url_str) {
472 ret = -LTTNG_ERR_NOMEM;
473 goto end;
474 }
475
476 /* Get path | ctrl && data string URL. */
477 ret = uri_to_str_url(&uri[0], buffer, sizeof(buffer));
478 if (ret < 0 || ret >= PATH_MAX) {
479 ret = -LTTNG_ERR_INVALID;
480 goto end;
481 }
482 ret = 0;
483
484 switch (uri[0].dtype) {
485 case LTTNG_DST_PATH:
486 raw_path_str = lttng_strndup(buffer, PATH_MAX);
487 if (!raw_path_str) {
488 ret = -LTTNG_ERR_NOMEM;
489 goto end;
490 }
491
492 path_str = lttng_strndup(raw_path_str, PATH_MAX);
493 if (!path_str) {
494 ret = -LTTNG_ERR_NOMEM;
495 goto end;
496 }
497 break;
498 case LTTNG_DST_IPV4:
499 case LTTNG_DST_IPV6:
500 if (ret_size != 2) {
501 ret = -LTTNG_ERR_INVALID;
502 goto end;
503 }
504
505 raw_ctrl_str = lttng_strndup(buffer, PATH_MAX);
506 if (!raw_ctrl_str) {
507 ret = -LTTNG_ERR_NOMEM;
508 goto end;
509 }
510
511 ctrl_str = lttng_strndup(raw_ctrl_str, PATH_MAX);
512 if (!ctrl_str) {
513 ret = -LTTNG_ERR_NOMEM;
514 goto end;
515 }
516
517 /* Get the data uri. */
518 ret = uri_to_str_url(&uri[1], buffer, sizeof(buffer));
519 if (ret < 0) {
520 ret = -LTTNG_ERR_INVALID;
521 goto end;
522 }
523 ret = 0;
524
525 raw_data_str = lttng_strndup(buffer, PATH_MAX);
526 if (!raw_data_str) {
527 ret = -LTTNG_ERR_NOMEM;
528 goto end;
529 }
530
531 data_str = lttng_strndup(raw_data_str, PATH_MAX);
532 if (!data_str) {
533 ret = -LTTNG_ERR_NOMEM;
534 goto end;
535 }
536
537 break;
538 default:
539 ret = -LTTNG_ERR_INVALID;
540 goto end;
541 }
542
543 reset_load_session_attr_urls(attr);
544
545 attr->override_attr->path_url = path_str;
546 attr->override_attr->ctrl_url = ctrl_str;
547 attr->override_attr->data_url = data_str;
548
549 attr->raw_override_url = raw_url_str;
550 attr->raw_override_path_url = raw_path_str;
551 attr->raw_override_ctrl_url = raw_ctrl_str;
552 attr->raw_override_data_url = raw_data_str;
553
554 /* Pass data ownership to attr. */
555 raw_url_str = NULL;
556 raw_path_str = NULL;
557 path_str = NULL;
558 raw_ctrl_str = NULL;
559 ctrl_str = NULL;
560 raw_data_str = NULL;
561 data_str = NULL;
562
563 end:
564 free(raw_path_str);
565 free(path_str);
566 free(raw_ctrl_str);
567 free(ctrl_str);
568 free(raw_data_str);
569 free(data_str);
570 free(raw_url_str);
571 free(uri);
572 return ret;
573 }
574
575 int lttng_load_session_attr_set_override_session_name(
576 struct lttng_load_session_attr *attr, const char *session_name)
577 {
578 int ret = 0;
579 size_t len;
580
581 if (!attr ||!session_name) {
582 ret = -LTTNG_ERR_INVALID;
583 goto end;
584 }
585
586 if (!attr->override_attr) {
587 attr->override_attr = zmalloc(
588 sizeof(struct config_load_session_override_attr));
589 if (!attr->override_attr) {
590 ret = -LTTNG_ERR_NOMEM;
591 goto end;
592 }
593 }
594
595 len = strlen(session_name);
596 if (len >= LTTNG_NAME_MAX) {
597 ret = -LTTNG_ERR_INVALID;
598 goto end;
599 }
600
601 attr->override_attr->session_name = lttng_strndup(session_name,
602 len);
603 if (!attr->override_attr->session_name) {
604 ret = -LTTNG_ERR_NOMEM;
605 goto end;
606 }
607 end:
608 return ret;
609 }
610
611 int lttng_load_session(struct lttng_load_session_attr *attr)
612 {
613 int ret;
614 const char *url, *session_name;
615
616 if (!attr) {
617 ret = -LTTNG_ERR_INVALID;
618 goto end;
619 }
620
621 ret = validate_attr(attr);
622 if (ret) {
623 goto end;
624 }
625
626 url = attr->input_url[0] != '\0' ? attr->input_url : NULL;
627 session_name = attr->session_name[0] != '\0' ?
628 attr->session_name : NULL;
629
630 ret = config_load_session(url, session_name, attr->overwrite, 0,
631 attr->override_attr);
632
633 end:
634 return ret;
635 }
This page took 0.064293 seconds and 4 git commands to generate.