Implement filter bytecode support in lttng-session, and parse filter string
[lttng-tools.git] / src / lib / lttng-ctl / lttng-ctl.c
1 /*
2 * liblttngctl.c
3 *
4 * Linux Trace Toolkit Control Library
5 *
6 * Copyright (C) 2011 David Goulet <david.goulet@polymtl.ca>
7 *
8 * This library is free software; you can redistribute it and/or modify it
9 * under the terms of the GNU Lesser General Public License, version 2.1 only,
10 * as published by the Free Software Foundation.
11 *
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
16 *
17 * You should have received a copy of the GNU Lesser General Public License
18 * along with this library; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20 */
21
22 #define _GNU_SOURCE
23 #include <grp.h>
24 #include <errno.h>
25 #include <stdio.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <unistd.h>
29
30 #include <common/common.h>
31 #include <common/defaults.h>
32 #include <common/sessiond-comm/sessiond-comm.h>
33 #include <lttng/lttng.h>
34
35 #include "filter-parser.h"
36 #include "filter-ast.h"
37 #include "filter-bytecode.h"
38 #include "memstream.h"
39
40 #ifdef DEBUG
41 const int print_xml = 1;
42 #define dbg_printf(fmt, args...) \
43 printf("[debug liblttng-ctl] " fmt, ## args)
44 #else
45 const int print_xml = 0;
46 #define dbg_printf(fmt, args...) \
47 do { \
48 /* do nothing but check printf format */ \
49 if (0) \
50 printf("[debug liblttnctl] " fmt, ## args); \
51 } while (0)
52 #endif
53
54
55 /* Socket to session daemon for communication */
56 static int sessiond_socket;
57 static char sessiond_sock_path[PATH_MAX];
58
59 /* Variables */
60 static char *tracing_group;
61 static int connected;
62
63 /* Global */
64
65 /*
66 * Those two variables are used by error.h to silent or control the verbosity of
67 * error message. They are global to the library so application linking with it
68 * are able to compile correctly and also control verbosity of the library.
69 *
70 * Note that it is *not* possible to silent ERR() and PERROR() macros.
71 */
72 int lttng_opt_quiet;
73 int lttng_opt_verbose;
74
75 /*
76 * Copy string from src to dst and enforce null terminated byte.
77 */
78 static void copy_string(char *dst, const char *src, size_t len)
79 {
80 if (src && dst) {
81 strncpy(dst, src, len);
82 /* Enforce the NULL terminated byte */
83 dst[len - 1] = '\0';
84 } else if (dst) {
85 dst[0] = '\0';
86 }
87 }
88
89 /*
90 * Copy domain to lttcomm_session_msg domain.
91 *
92 * If domain is unknown, default domain will be the kernel.
93 */
94 static void copy_lttng_domain(struct lttng_domain *dst, struct lttng_domain *src)
95 {
96 if (src && dst) {
97 switch (src->type) {
98 case LTTNG_DOMAIN_KERNEL:
99 case LTTNG_DOMAIN_UST:
100 /*
101 case LTTNG_DOMAIN_UST_EXEC_NAME:
102 case LTTNG_DOMAIN_UST_PID:
103 case LTTNG_DOMAIN_UST_PID_FOLLOW_CHILDREN:
104 */
105 memcpy(dst, src, sizeof(struct lttng_domain));
106 break;
107 default:
108 memset(dst, 0, sizeof(struct lttng_domain));
109 dst->type = LTTNG_DOMAIN_KERNEL;
110 break;
111 }
112 }
113 }
114
115 /*
116 * Send lttcomm_session_msg to the session daemon.
117 *
118 * On success, returns the number of bytes sent (>=0)
119 * On error, returns -1
120 */
121 static int send_session_msg(struct lttcomm_session_msg *lsm)
122 {
123 int ret;
124
125 if (!connected) {
126 ret = -ENOTCONN;
127 goto end;
128 }
129
130 ret = lttcomm_send_creds_unix_sock(sessiond_socket, lsm,
131 sizeof(struct lttcomm_session_msg));
132
133 end:
134 return ret;
135 }
136
137 /*
138 * Send var len data to the session daemon.
139 *
140 * On success, returns the number of bytes sent (>=0)
141 * On error, returns -1
142 */
143 static int send_session_varlen(void *data, size_t len)
144 {
145 int ret;
146
147 if (!connected) {
148 ret = -ENOTCONN;
149 goto end;
150 }
151 if (!data || !len) {
152 ret = 0;
153 goto end;
154 }
155
156 ret = lttcomm_send_unix_sock(sessiond_socket, data, len);
157
158 end:
159 return ret;
160 }
161
162 /*
163 * Receive data from the sessiond socket.
164 *
165 * On success, returns the number of bytes received (>=0)
166 * On error, returns -1 (recvmsg() error) or -ENOTCONN
167 */
168 static int recv_data_sessiond(void *buf, size_t len)
169 {
170 int ret;
171
172 if (!connected) {
173 ret = -ENOTCONN;
174 goto end;
175 }
176
177 ret = lttcomm_recv_unix_sock(sessiond_socket, buf, len);
178
179 end:
180 return ret;
181 }
182
183 /*
184 * Check if we are in the specified group.
185 *
186 * If yes return 1, else return -1.
187 */
188 static int check_tracing_group(const char *grp_name)
189 {
190 struct group *grp_tracing; /* no free(). See getgrnam(3) */
191 gid_t *grp_list;
192 int grp_list_size, grp_id, i;
193 int ret = -1;
194
195 /* Get GID of group 'tracing' */
196 grp_tracing = getgrnam(grp_name);
197 if (!grp_tracing) {
198 /* If grp_tracing is NULL, the group does not exist. */
199 goto end;
200 }
201
202 /* Get number of supplementary group IDs */
203 grp_list_size = getgroups(0, NULL);
204 if (grp_list_size < 0) {
205 perror("getgroups");
206 goto end;
207 }
208
209 /* Alloc group list of the right size */
210 grp_list = malloc(grp_list_size * sizeof(gid_t));
211 if (!grp_list) {
212 perror("malloc");
213 goto end;
214 }
215 grp_id = getgroups(grp_list_size, grp_list);
216 if (grp_id < 0) {
217 perror("getgroups");
218 goto free_list;
219 }
220
221 for (i = 0; i < grp_list_size; i++) {
222 if (grp_list[i] == grp_tracing->gr_gid) {
223 ret = 1;
224 break;
225 }
226 }
227
228 free_list:
229 free(grp_list);
230
231 end:
232 return ret;
233 }
234
235 /*
236 * Try connect to session daemon with sock_path.
237 *
238 * Return 0 on success, else -1
239 */
240 static int try_connect_sessiond(const char *sock_path)
241 {
242 int ret;
243
244 /* If socket exist, we check if the daemon listens for connect. */
245 ret = access(sock_path, F_OK);
246 if (ret < 0) {
247 /* Not alive */
248 return -1;
249 }
250
251 ret = lttcomm_connect_unix_sock(sock_path);
252 if (ret < 0) {
253 /* Not alive */
254 return -1;
255 }
256
257 ret = lttcomm_close_unix_sock(ret);
258 if (ret < 0) {
259 perror("lttcomm_close_unix_sock");
260 }
261
262 return 0;
263 }
264
265 /*
266 * Set sessiond socket path by putting it in the global
267 * sessiond_sock_path variable.
268 * Returns 0 on success,
269 * -ENOMEM on failure (the sessiond socket path is somehow too long)
270 */
271 static int set_session_daemon_path(void)
272 {
273 int ret;
274 int in_tgroup = 0; /* In tracing group */
275 uid_t uid;
276
277 uid = getuid();
278
279 if (uid != 0) {
280 /* Are we in the tracing group ? */
281 in_tgroup = check_tracing_group(tracing_group);
282 }
283
284 if ((uid == 0) || in_tgroup) {
285 copy_string(sessiond_sock_path, DEFAULT_GLOBAL_CLIENT_UNIX_SOCK,
286 sizeof(sessiond_sock_path));
287 }
288
289 if (uid != 0) {
290 if (in_tgroup) {
291 /* Tracing group */
292 ret = try_connect_sessiond(sessiond_sock_path);
293 if (ret >= 0) {
294 goto end;
295 }
296 /* Global session daemon not available... */
297 }
298 /* ...or not in tracing group (and not root), default */
299
300 /*
301 * With GNU C < 2.1, snprintf returns -1 if the target buffer is too small;
302 * With GNU C >= 2.1, snprintf returns the required size (excluding closing null)
303 */
304 ret = snprintf(sessiond_sock_path, sizeof(sessiond_sock_path),
305 DEFAULT_HOME_CLIENT_UNIX_SOCK, getenv("HOME"));
306 if ((ret < 0) || (ret >= sizeof(sessiond_sock_path))) {
307 return -ENOMEM;
308 }
309 }
310 end:
311 return 0;
312 }
313
314 /*
315 * Connect to the LTTng session daemon.
316 *
317 * On success, return 0. On error, return -1.
318 */
319 static int connect_sessiond(void)
320 {
321 int ret;
322
323 ret = set_session_daemon_path();
324 if (ret < 0) {
325 return -1; /* set_session_daemon_path() returns -ENOMEM */
326 }
327
328 /* Connect to the sesssion daemon */
329 ret = lttcomm_connect_unix_sock(sessiond_sock_path);
330 if (ret < 0) {
331 return ret;
332 }
333
334 sessiond_socket = ret;
335 connected = 1;
336
337 return 0;
338 }
339
340 /*
341 * Clean disconnect from the session daemon.
342 * On success, return 0. On error, return -1.
343 */
344 static int disconnect_sessiond(void)
345 {
346 int ret = 0;
347
348 if (connected) {
349 ret = lttcomm_close_unix_sock(sessiond_socket);
350 sessiond_socket = 0;
351 connected = 0;
352 }
353
354 return ret;
355 }
356
357 /*
358 * Ask the session daemon a specific command and put the data into buf.
359 * Takes extra var. len. data as input to send to the session daemon.
360 *
361 * Return size of data (only payload, not header) or a negative error code.
362 */
363 static int ask_sessiond_varlen(struct lttcomm_session_msg *lsm,
364 void *vardata,
365 size_t varlen,
366 void **buf)
367 {
368 int ret;
369 size_t size;
370 void *data = NULL;
371 struct lttcomm_lttng_msg llm;
372
373 ret = connect_sessiond();
374 if (ret < 0) {
375 goto end;
376 }
377
378 /* Send command to session daemon */
379 ret = send_session_msg(lsm);
380 if (ret < 0) {
381 goto end;
382 }
383 /* Send var len data */
384 ret = send_session_varlen(vardata, varlen);
385 if (ret < 0) {
386 goto end;
387 }
388
389 /* Get header from data transmission */
390 ret = recv_data_sessiond(&llm, sizeof(llm));
391 if (ret < 0) {
392 goto end;
393 }
394
395 /* Check error code if OK */
396 if (llm.ret_code != LTTCOMM_OK) {
397 ret = -llm.ret_code;
398 goto end;
399 }
400
401 size = llm.data_size;
402 if (size == 0) {
403 /* If client free with size 0 */
404 if (buf != NULL) {
405 *buf = NULL;
406 }
407 ret = 0;
408 goto end;
409 }
410
411 data = (void*) malloc(size);
412
413 /* Get payload data */
414 ret = recv_data_sessiond(data, size);
415 if (ret < 0) {
416 free(data);
417 goto end;
418 }
419
420 /*
421 * Extra protection not to dereference a NULL pointer. If buf is NULL at
422 * this point, an error is returned and data is freed.
423 */
424 if (buf == NULL) {
425 ret = -1;
426 free(data);
427 goto end;
428 }
429
430 *buf = data;
431 ret = size;
432
433 end:
434 disconnect_sessiond();
435 return ret;
436 }
437
438 /*
439 * Ask the session daemon a specific command and put the data into buf.
440 *
441 * Return size of data (only payload, not header) or a negative error code.
442 */
443 static int ask_sessiond(struct lttcomm_session_msg *lsm, void **buf)
444 {
445 return ask_sessiond_varlen(lsm, NULL, 0, buf);
446 }
447
448 /*
449 * Create lttng handle and return pointer.
450 * The returned pointer will be NULL in case of malloc() error.
451 */
452 struct lttng_handle *lttng_create_handle(const char *session_name,
453 struct lttng_domain *domain)
454 {
455 struct lttng_handle *handle;
456
457 handle = malloc(sizeof(struct lttng_handle));
458 if (handle == NULL) {
459 perror("malloc handle");
460 goto end;
461 }
462
463 /* Copy session name */
464 copy_string(handle->session_name, session_name,
465 sizeof(handle->session_name));
466
467 /* Copy lttng domain */
468 copy_lttng_domain(&handle->domain, domain);
469
470 end:
471 return handle;
472 }
473
474 /*
475 * Destroy handle by free(3) the pointer.
476 */
477 void lttng_destroy_handle(struct lttng_handle *handle)
478 {
479 if (handle) {
480 free(handle);
481 }
482 }
483
484 /*
485 * Register an outside consumer.
486 * Returns size of returned session payload data or a negative error code.
487 */
488 int lttng_register_consumer(struct lttng_handle *handle,
489 const char *socket_path)
490 {
491 struct lttcomm_session_msg lsm;
492
493 lsm.cmd_type = LTTNG_REGISTER_CONSUMER;
494 copy_string(lsm.session.name, handle->session_name,
495 sizeof(lsm.session.name));
496 copy_lttng_domain(&lsm.domain, &handle->domain);
497
498 copy_string(lsm.u.reg.path, socket_path, sizeof(lsm.u.reg.path));
499
500 return ask_sessiond(&lsm, NULL);
501 }
502
503 /*
504 * Start tracing for all traces of the session.
505 * Returns size of returned session payload data or a negative error code.
506 */
507 int lttng_start_tracing(const char *session_name)
508 {
509 struct lttcomm_session_msg lsm;
510
511 if (session_name == NULL) {
512 return -1;
513 }
514
515 lsm.cmd_type = LTTNG_START_TRACE;
516
517 copy_string(lsm.session.name, session_name, sizeof(lsm.session.name));
518
519 return ask_sessiond(&lsm, NULL);
520 }
521
522 /*
523 * Stop tracing for all traces of the session.
524 * Returns size of returned session payload data or a negative error code.
525 */
526 int lttng_stop_tracing(const char *session_name)
527 {
528 struct lttcomm_session_msg lsm;
529
530 if (session_name == NULL) {
531 return -1;
532 }
533
534 lsm.cmd_type = LTTNG_STOP_TRACE;
535
536 copy_string(lsm.session.name, session_name, sizeof(lsm.session.name));
537
538 return ask_sessiond(&lsm, NULL);
539 }
540
541 /*
542 * Add context to event and/or channel.
543 * If event_name is NULL, the context is applied to all events of the channel.
544 * If channel_name is NULL, a lookup of the event's channel is done.
545 * If both are NULL, the context is applied to all events of all channels.
546 *
547 * Returns the size of the returned payload data or a negative error code.
548 */
549 int lttng_add_context(struct lttng_handle *handle,
550 struct lttng_event_context *ctx, const char *event_name,
551 const char *channel_name)
552 {
553 struct lttcomm_session_msg lsm;
554
555 /* Safety check. Both are mandatory */
556 if (handle == NULL || ctx == NULL) {
557 return -1;
558 }
559
560 memset(&lsm, 0, sizeof(lsm));
561
562 lsm.cmd_type = LTTNG_ADD_CONTEXT;
563
564 /* Copy channel name */
565 copy_string(lsm.u.context.channel_name, channel_name,
566 sizeof(lsm.u.context.channel_name));
567 /* Copy event name */
568 copy_string(lsm.u.context.event_name, event_name,
569 sizeof(lsm.u.context.event_name));
570
571 copy_lttng_domain(&lsm.domain, &handle->domain);
572
573 memcpy(&lsm.u.context.ctx, ctx, sizeof(struct lttng_event_context));
574
575 copy_string(lsm.session.name, handle->session_name,
576 sizeof(lsm.session.name));
577
578 return ask_sessiond(&lsm, NULL);
579 }
580
581 /*
582 * Enable event(s) for a channel.
583 * If no event name is specified, all events are enabled.
584 * If no channel name is specified, the default 'channel0' is used.
585 * Returns size of returned session payload data or a negative error code.
586 */
587 int lttng_enable_event(struct lttng_handle *handle,
588 struct lttng_event *ev, const char *channel_name)
589 {
590 struct lttcomm_session_msg lsm;
591
592 if (handle == NULL || ev == NULL) {
593 return -1;
594 }
595
596 memset(&lsm, 0, sizeof(lsm));
597
598 /* If no channel name, we put the default name */
599 if (channel_name == NULL) {
600 copy_string(lsm.u.enable.channel_name, DEFAULT_CHANNEL_NAME,
601 sizeof(lsm.u.enable.channel_name));
602 } else {
603 copy_string(lsm.u.enable.channel_name, channel_name,
604 sizeof(lsm.u.enable.channel_name));
605 }
606
607 copy_lttng_domain(&lsm.domain, &handle->domain);
608
609 if (ev->name[0] != '\0') {
610 lsm.cmd_type = LTTNG_ENABLE_EVENT;
611 } else {
612 lsm.cmd_type = LTTNG_ENABLE_ALL_EVENT;
613 }
614 memcpy(&lsm.u.enable.event, ev, sizeof(lsm.u.enable.event));
615
616 copy_string(lsm.session.name, handle->session_name,
617 sizeof(lsm.session.name));
618
619 return ask_sessiond(&lsm, NULL);
620 }
621
622 /*
623 * set filter for an event
624 * Return negative error value on error.
625 * Return size of returned session payload data if OK.
626 */
627
628 int lttng_set_event_filter(struct lttng_handle *handle,
629 const char *event_name, const char *channel_name,
630 const char *filter_expression)
631 {
632 struct lttcomm_session_msg lsm;
633 struct filter_parser_ctx *ctx;
634 FILE *fmem;
635 int ret = 0;
636
637 /* Safety check. */
638 if (handle == NULL) {
639 return -1;
640 }
641
642 if (!filter_expression) {
643 return 0;
644 }
645
646 /*
647 * casting const to non-const, as the underlying function will
648 * use it in read-only mode.
649 */
650 fmem = lttng_fmemopen((void *) filter_expression,
651 strlen(filter_expression), "r");
652 if (!fmem) {
653 fprintf(stderr, "Error opening memory as stream\n");
654 return -ENOMEM;
655 }
656 ctx = filter_parser_ctx_alloc(fmem);
657 if (!ctx) {
658 fprintf(stderr, "Error allocating parser\n");
659 ret = -ENOMEM;
660 goto alloc_error;
661 }
662 ret = filter_parser_ctx_append_ast(ctx);
663 if (ret) {
664 fprintf(stderr, "Parse error\n");
665 ret = -EINVAL;
666 goto parse_error;
667 }
668 ret = filter_visitor_set_parent(ctx);
669 if (ret) {
670 fprintf(stderr, "Set parent error\n");
671 ret = -EINVAL;
672 goto parse_error;
673 }
674 if (print_xml) {
675 ret = filter_visitor_print_xml(ctx, stdout, 0);
676 if (ret) {
677 fflush(stdout);
678 fprintf(stderr, "XML print error\n");
679 ret = -EINVAL;
680 goto parse_error;
681 }
682 }
683
684 dbg_printf("Generating IR... ");
685 fflush(stdout);
686 ret = filter_visitor_ir_generate(ctx);
687 if (ret) {
688 fprintf(stderr, "Generate IR error\n");
689 ret = -EINVAL;
690 goto parse_error;
691 }
692 dbg_printf("done\n");
693
694 dbg_printf("Validating IR... ");
695 fflush(stdout);
696 ret = filter_visitor_ir_check_binary_op_nesting(ctx);
697 if (ret) {
698 ret = -EINVAL;
699 goto parse_error;
700 }
701 dbg_printf("done\n");
702
703 dbg_printf("Generating bytecode... ");
704 fflush(stdout);
705 ret = filter_visitor_bytecode_generate(ctx);
706 if (ret) {
707 fprintf(stderr, "Generate bytecode error\n");
708 ret = -EINVAL;
709 goto parse_error;
710 }
711 dbg_printf("done\n");
712 dbg_printf("Size of bytecode generated: %u bytes.\n",
713 bytecode_get_len(&ctx->bytecode->b));
714
715 memset(&lsm, 0, sizeof(lsm));
716
717 lsm.cmd_type = LTTNG_SET_FILTER;
718
719 /* Copy channel name */
720 copy_string(lsm.u.filter.channel_name, channel_name,
721 sizeof(lsm.u.filter.channel_name));
722 /* Copy event name */
723 copy_string(lsm.u.filter.event_name, event_name,
724 sizeof(lsm.u.filter.event_name));
725 lsm.u.filter.bytecode_len = sizeof(ctx->bytecode->b)
726 + bytecode_get_len(&ctx->bytecode->b);
727
728 copy_lttng_domain(&lsm.domain, &handle->domain);
729
730 copy_string(lsm.session.name, handle->session_name,
731 sizeof(lsm.session.name));
732
733 ret = ask_sessiond_varlen(&lsm, &ctx->bytecode->b,
734 lsm.u.filter.bytecode_len, NULL);
735
736 filter_bytecode_free(ctx);
737 filter_ir_free(ctx);
738 filter_parser_ctx_free(ctx);
739 if (fclose(fmem) != 0) {
740 perror("fclose");
741 }
742 return ret;
743
744 parse_error:
745 filter_bytecode_free(ctx);
746 filter_ir_free(ctx);
747 filter_parser_ctx_free(ctx);
748 alloc_error:
749 if (fclose(fmem) != 0) {
750 perror("fclose");
751 }
752 return ret;
753 }
754
755 /*
756 * Disable event(s) of a channel and domain.
757 * If no event name is specified, all events are disabled.
758 * If no channel name is specified, the default 'channel0' is used.
759 * Returns size of returned session payload data or a negative error code.
760 */
761 int lttng_disable_event(struct lttng_handle *handle, const char *name,
762 const char *channel_name)
763 {
764 struct lttcomm_session_msg lsm;
765
766 if (handle == NULL) {
767 return -1;
768 }
769
770 memset(&lsm, 0, sizeof(lsm));
771
772 if (channel_name) {
773 copy_string(lsm.u.disable.channel_name, channel_name,
774 sizeof(lsm.u.disable.channel_name));
775 } else {
776 copy_string(lsm.u.disable.channel_name, DEFAULT_CHANNEL_NAME,
777 sizeof(lsm.u.disable.channel_name));
778 }
779
780 copy_lttng_domain(&lsm.domain, &handle->domain);
781
782 if (name != NULL) {
783 copy_string(lsm.u.disable.name, name, sizeof(lsm.u.disable.name));
784 lsm.cmd_type = LTTNG_DISABLE_EVENT;
785 } else {
786 lsm.cmd_type = LTTNG_DISABLE_ALL_EVENT;
787 }
788
789 copy_string(lsm.session.name, handle->session_name,
790 sizeof(lsm.session.name));
791
792 return ask_sessiond(&lsm, NULL);
793 }
794
795 /*
796 * Enable channel per domain
797 * Returns size of returned session payload data or a negative error code.
798 */
799 int lttng_enable_channel(struct lttng_handle *handle,
800 struct lttng_channel *chan)
801 {
802 struct lttcomm_session_msg lsm;
803
804 /*
805 * NULL arguments are forbidden. No default values.
806 */
807 if (handle == NULL || chan == NULL) {
808 return -1;
809 }
810
811 memset(&lsm, 0, sizeof(lsm));
812
813 memcpy(&lsm.u.channel.chan, chan, sizeof(lsm.u.channel.chan));
814
815 lsm.cmd_type = LTTNG_ENABLE_CHANNEL;
816
817 copy_lttng_domain(&lsm.domain, &handle->domain);
818
819 copy_string(lsm.session.name, handle->session_name,
820 sizeof(lsm.session.name));
821
822 return ask_sessiond(&lsm, NULL);
823 }
824
825 /*
826 * All tracing will be stopped for registered events of the channel.
827 * Returns size of returned session payload data or a negative error code.
828 */
829 int lttng_disable_channel(struct lttng_handle *handle, const char *name)
830 {
831 struct lttcomm_session_msg lsm;
832
833 /* Safety check. Both are mandatory */
834 if (handle == NULL || name == NULL) {
835 return -1;
836 }
837
838 memset(&lsm, 0, sizeof(lsm));
839
840 lsm.cmd_type = LTTNG_DISABLE_CHANNEL;
841
842 copy_string(lsm.u.disable.channel_name, name,
843 sizeof(lsm.u.disable.channel_name));
844
845 copy_lttng_domain(&lsm.domain, &handle->domain);
846
847 copy_string(lsm.session.name, handle->session_name,
848 sizeof(lsm.session.name));
849
850 return ask_sessiond(&lsm, NULL);
851 }
852
853 /*
854 * Lists all available tracepoints of domain.
855 * Sets the contents of the events array.
856 * Returns the number of lttng_event entries in events;
857 * on error, returns a negative value.
858 */
859 int lttng_list_tracepoints(struct lttng_handle *handle,
860 struct lttng_event **events)
861 {
862 int ret;
863 struct lttcomm_session_msg lsm;
864
865 if (handle == NULL) {
866 return -1;
867 }
868
869 lsm.cmd_type = LTTNG_LIST_TRACEPOINTS;
870 copy_lttng_domain(&lsm.domain, &handle->domain);
871
872 ret = ask_sessiond(&lsm, (void **) events);
873 if (ret < 0) {
874 return ret;
875 }
876
877 return ret / sizeof(struct lttng_event);
878 }
879
880 /*
881 * Lists all available tracepoint fields of domain.
882 * Sets the contents of the event field array.
883 * Returns the number of lttng_event_field entries in events;
884 * on error, returns a negative value.
885 */
886 int lttng_list_tracepoint_fields(struct lttng_handle *handle,
887 struct lttng_event_field **fields)
888 {
889 int ret;
890 struct lttcomm_session_msg lsm;
891
892 if (handle == NULL) {
893 return -1;
894 }
895
896 lsm.cmd_type = LTTNG_LIST_TRACEPOINT_FIELDS;
897 copy_lttng_domain(&lsm.domain, &handle->domain);
898
899 ret = ask_sessiond(&lsm, (void **) fields);
900 if (ret < 0) {
901 return ret;
902 }
903
904 return ret / sizeof(struct lttng_event_field);
905 }
906
907 /*
908 * Returns a human readable string describing
909 * the error code (a negative value).
910 */
911 const char *lttng_strerror(int code)
912 {
913 /* lttcomm error codes range from -LTTCOMM_OK down to -LTTCOMM_NR */
914 if (code > -LTTCOMM_OK) {
915 return "Ended with errors";
916 }
917
918 return lttcomm_get_readable_code(code);
919 }
920
921 /*
922 * Create a brand new session using name and path.
923 * Returns size of returned session payload data or a negative error code.
924 */
925 int lttng_create_session(const char *name, const char *path)
926 {
927 struct lttcomm_session_msg lsm;
928
929 lsm.cmd_type = LTTNG_CREATE_SESSION;
930 copy_string(lsm.session.name, name, sizeof(lsm.session.name));
931 copy_string(lsm.session.path, path, sizeof(lsm.session.path));
932
933 return ask_sessiond(&lsm, NULL);
934 }
935
936 /*
937 * Create a new tracing session using a name, URIs and a consumer enable flag.
938 */
939 int lttng_create_session_uri(const char *name, struct lttng_uri *ctrl_uri,
940 struct lttng_uri *data_uri, unsigned int enable_consumer)
941 {
942 struct lttcomm_session_msg lsm;
943
944 /* Name and ctrl_uri are mandatory */
945 if (name == NULL || ctrl_uri == NULL) {
946 return -1;
947 }
948
949 lsm.cmd_type = LTTNG_CREATE_SESSION_URI;
950
951 copy_string(lsm.session.name, name, sizeof(lsm.session.name));
952 /* Anything bigger than zero, the consumer(s) will be enabled */
953 lsm.u.create_uri.enable_consumer = enable_consumer;
954 memcpy(&lsm.u.create_uri.ctrl_uri, ctrl_uri,
955 sizeof(lsm.u.create_uri.ctrl_uri));
956 if (data_uri) {
957 /*
958 * The only possible scenario where data_uri is NULL is for a local
959 * consumer where the output is at a specified path name on the
960 * filesystem.
961 */
962 memcpy(&lsm.u.create_uri.data_uri, data_uri,
963 sizeof(lsm.u.create_uri.data_uri));
964 }
965
966 return ask_sessiond(&lsm, NULL);
967 }
968
969 /*
970 * Destroy session using name.
971 * Returns size of returned session payload data or a negative error code.
972 */
973 int lttng_destroy_session(const char *session_name)
974 {
975 struct lttcomm_session_msg lsm;
976
977 if (session_name == NULL) {
978 return -1;
979 }
980
981 lsm.cmd_type = LTTNG_DESTROY_SESSION;
982
983 copy_string(lsm.session.name, session_name, sizeof(lsm.session.name));
984
985 return ask_sessiond(&lsm, NULL);
986 }
987
988 /*
989 * Ask the session daemon for all available sessions.
990 * Sets the contents of the sessions array.
991 * Returns the number of lttng_session entries in sessions;
992 * on error, returns a negative value.
993 */
994 int lttng_list_sessions(struct lttng_session **sessions)
995 {
996 int ret;
997 struct lttcomm_session_msg lsm;
998
999 lsm.cmd_type = LTTNG_LIST_SESSIONS;
1000 ret = ask_sessiond(&lsm, (void**) sessions);
1001 if (ret < 0) {
1002 return ret;
1003 }
1004
1005 return ret / sizeof(struct lttng_session);
1006 }
1007
1008 /*
1009 * Ask the session daemon for all available domains of a session.
1010 * Sets the contents of the domains array.
1011 * Returns the number of lttng_domain entries in domains;
1012 * on error, returns a negative value.
1013 */
1014 int lttng_list_domains(const char *session_name,
1015 struct lttng_domain **domains)
1016 {
1017 int ret;
1018 struct lttcomm_session_msg lsm;
1019
1020 if (session_name == NULL) {
1021 return -1;
1022 }
1023
1024 lsm.cmd_type = LTTNG_LIST_DOMAINS;
1025
1026 copy_string(lsm.session.name, session_name, sizeof(lsm.session.name));
1027
1028 ret = ask_sessiond(&lsm, (void**) domains);
1029 if (ret < 0) {
1030 return ret;
1031 }
1032
1033 return ret / sizeof(struct lttng_domain);
1034 }
1035
1036 /*
1037 * Ask the session daemon for all available channels of a session.
1038 * Sets the contents of the channels array.
1039 * Returns the number of lttng_channel entries in channels;
1040 * on error, returns a negative value.
1041 */
1042 int lttng_list_channels(struct lttng_handle *handle,
1043 struct lttng_channel **channels)
1044 {
1045 int ret;
1046 struct lttcomm_session_msg lsm;
1047
1048 if (handle == NULL) {
1049 return -1;
1050 }
1051
1052 lsm.cmd_type = LTTNG_LIST_CHANNELS;
1053 copy_string(lsm.session.name, handle->session_name,
1054 sizeof(lsm.session.name));
1055
1056 copy_lttng_domain(&lsm.domain, &handle->domain);
1057
1058 ret = ask_sessiond(&lsm, (void**) channels);
1059 if (ret < 0) {
1060 return ret;
1061 }
1062
1063 return ret / sizeof(struct lttng_channel);
1064 }
1065
1066 /*
1067 * Ask the session daemon for all available events of a session channel.
1068 * Sets the contents of the events array.
1069 * Returns the number of lttng_event entries in events;
1070 * on error, returns a negative value.
1071 */
1072 int lttng_list_events(struct lttng_handle *handle,
1073 const char *channel_name, struct lttng_event **events)
1074 {
1075 int ret;
1076 struct lttcomm_session_msg lsm;
1077
1078 /* Safety check. An handle and channel name are mandatory */
1079 if (handle == NULL || channel_name == NULL) {
1080 return -1;
1081 }
1082
1083 lsm.cmd_type = LTTNG_LIST_EVENTS;
1084 copy_string(lsm.session.name, handle->session_name,
1085 sizeof(lsm.session.name));
1086 copy_string(lsm.u.list.channel_name, channel_name,
1087 sizeof(lsm.u.list.channel_name));
1088
1089 copy_lttng_domain(&lsm.domain, &handle->domain);
1090
1091 ret = ask_sessiond(&lsm, (void**) events);
1092 if (ret < 0) {
1093 return ret;
1094 }
1095
1096 return ret / sizeof(struct lttng_event);
1097 }
1098
1099 /*
1100 * Sets the tracing_group variable with name.
1101 * This function allocates memory pointed to by tracing_group.
1102 * On success, returns 0, on error, returns -1 (null name) or -ENOMEM.
1103 */
1104 int lttng_set_tracing_group(const char *name)
1105 {
1106 if (name == NULL) {
1107 return -1;
1108 }
1109
1110 if (asprintf(&tracing_group, "%s", name) < 0) {
1111 return -ENOMEM;
1112 }
1113
1114 return 0;
1115 }
1116
1117 /*
1118 * Returns size of returned session payload data or a negative error code.
1119 */
1120 int lttng_calibrate(struct lttng_handle *handle,
1121 struct lttng_calibrate *calibrate)
1122 {
1123 struct lttcomm_session_msg lsm;
1124
1125 /* Safety check. NULL pointer are forbidden */
1126 if (handle == NULL || calibrate == NULL) {
1127 return -1;
1128 }
1129
1130 lsm.cmd_type = LTTNG_CALIBRATE;
1131 copy_lttng_domain(&lsm.domain, &handle->domain);
1132
1133 memcpy(&lsm.u.calibrate, calibrate, sizeof(lsm.u.calibrate));
1134
1135 return ask_sessiond(&lsm, NULL);
1136 }
1137
1138 /*
1139 * Set default channel attributes.
1140 * If either or both of the arguments are null, attr content is zeroe'd.
1141 */
1142 void lttng_channel_set_default_attr(struct lttng_domain *domain,
1143 struct lttng_channel_attr *attr)
1144 {
1145 /* Safety check */
1146 if (attr == NULL || domain == NULL) {
1147 return;
1148 }
1149
1150 memset(attr, 0, sizeof(struct lttng_channel_attr));
1151
1152 switch (domain->type) {
1153 case LTTNG_DOMAIN_KERNEL:
1154 attr->overwrite = DEFAULT_CHANNEL_OVERWRITE;
1155 attr->switch_timer_interval = DEFAULT_CHANNEL_SWITCH_TIMER;
1156 attr->read_timer_interval = DEFAULT_CHANNEL_READ_TIMER;
1157
1158 attr->subbuf_size = DEFAULT_KERNEL_CHANNEL_SUBBUF_SIZE;
1159 attr->num_subbuf = DEFAULT_KERNEL_CHANNEL_SUBBUF_NUM;
1160 attr->output = DEFAULT_KERNEL_CHANNEL_OUTPUT;
1161 break;
1162 case LTTNG_DOMAIN_UST:
1163 #if 0
1164 case LTTNG_DOMAIN_UST_EXEC_NAME:
1165 case LTTNG_DOMAIN_UST_PID:
1166 case LTTNG_DOMAIN_UST_PID_FOLLOW_CHILDREN:
1167 #endif
1168 attr->overwrite = DEFAULT_CHANNEL_OVERWRITE;
1169 attr->switch_timer_interval = DEFAULT_CHANNEL_SWITCH_TIMER;
1170 attr->read_timer_interval = DEFAULT_CHANNEL_READ_TIMER;
1171
1172 attr->subbuf_size = DEFAULT_UST_CHANNEL_SUBBUF_SIZE;
1173 attr->num_subbuf = DEFAULT_UST_CHANNEL_SUBBUF_NUM;
1174 attr->output = DEFAULT_UST_CHANNEL_OUTPUT;
1175 break;
1176 default:
1177 /* Default behavior: leave set to 0. */
1178 break;
1179 }
1180 }
1181
1182 /*
1183 * Check if session daemon is alive.
1184 *
1185 * Return 1 if alive or 0 if not.
1186 * On error returns a negative value.
1187 */
1188 int lttng_session_daemon_alive(void)
1189 {
1190 int ret;
1191
1192 ret = set_session_daemon_path();
1193 if (ret < 0) {
1194 /* Error */
1195 return ret;
1196 }
1197
1198 if (strlen(sessiond_sock_path) == 0) {
1199 /* No socket path set. Weird error */
1200 return -1;
1201 }
1202
1203 ret = try_connect_sessiond(sessiond_sock_path);
1204 if (ret < 0) {
1205 /* Not alive */
1206 return 0;
1207 }
1208
1209 /* Is alive */
1210 return 1;
1211 }
1212
1213 /*
1214 * Set URI for a consumer for a session and domain.
1215 *
1216 * Return 0 on success, else a negative value.
1217 */
1218 int lttng_set_consumer_uri(struct lttng_handle *handle, struct lttng_uri *uri)
1219 {
1220 struct lttcomm_session_msg lsm;
1221
1222 if (handle == NULL || uri == NULL) {
1223 return -1;
1224 }
1225
1226 lsm.cmd_type = LTTNG_SET_CONSUMER_URI;
1227
1228 copy_string(lsm.session.name, handle->session_name,
1229 sizeof(lsm.session.name));
1230 copy_lttng_domain(&lsm.domain, &handle->domain);
1231
1232 memcpy(&lsm.u.uri, uri, sizeof(lsm.u.uri));
1233
1234 return ask_sessiond(&lsm, NULL);
1235 }
1236
1237 /*
1238 * Enable consumer for a session and domain.
1239 *
1240 * Return 0 on success, else a negative value.
1241 */
1242 int lttng_enable_consumer(struct lttng_handle *handle)
1243 {
1244 struct lttcomm_session_msg lsm;
1245
1246 if (handle == NULL) {
1247 return -1;
1248 }
1249
1250 lsm.cmd_type = LTTNG_ENABLE_CONSUMER;
1251
1252 copy_string(lsm.session.name, handle->session_name,
1253 sizeof(lsm.session.name));
1254 copy_lttng_domain(&lsm.domain, &handle->domain);
1255
1256 return ask_sessiond(&lsm, NULL);
1257 }
1258
1259 /*
1260 * Disable consumer for a session and domain.
1261 *
1262 * Return 0 on success, else a negative value.
1263 */
1264 int lttng_disable_consumer(struct lttng_handle *handle)
1265 {
1266 struct lttcomm_session_msg lsm;
1267
1268 if (handle == NULL) {
1269 return -1;
1270 }
1271
1272 lsm.cmd_type = LTTNG_DISABLE_CONSUMER;
1273
1274 copy_string(lsm.session.name, handle->session_name,
1275 sizeof(lsm.session.name));
1276 copy_lttng_domain(&lsm.domain, &handle->domain);
1277
1278 return ask_sessiond(&lsm, NULL);
1279 }
1280
1281 /*
1282 * lib constructor
1283 */
1284 static void __attribute__((constructor)) init()
1285 {
1286 /* Set default session group */
1287 lttng_set_tracing_group(DEFAULT_TRACING_GROUP);
1288 }
This page took 0.094799 seconds and 4 git commands to generate.