2 * Copyright (C) 2021 Simon Marchi <simon.marchi@efficios.com>
4 * SPDX-License-Identifier: GPL-2.0-only
10 #include "../command.h"
12 #include "common/argpar/argpar.h"
13 #include "common/dynamic-array.h"
14 #include "common/mi-lttng.h"
15 /* For lttng_condition_type_str(). */
16 #include "lttng/condition/condition-internal.h"
17 #include "lttng/condition/on-event.h"
18 #include "lttng/condition/on-event-internal.h"
19 /* For lttng_domain_type_str(). */
20 #include "lttng/domain-internal.h"
21 #include "../loglevel.h"
22 #include <lttng/lttng.h>
24 #ifdef LTTNG_EMBED_HELP
25 static const char help_msg
[] =
26 #include <lttng-list-triggers.1.h>
36 struct argpar_opt_descr list_trigger_options
[] = {
37 { OPT_HELP
, 'h', "help", false },
38 { OPT_LIST_OPTIONS
, '\0', "list-options", false },
39 ARGPAR_OPT_DESCR_SENTINEL
,
43 * Returns the human-readable log level name associated with a numerical value
44 * if there is one. The Log4j and JUL domains have discontinuous log level
45 * values (a value can fall between two labels). In those cases, NULL is
48 static const char *get_pretty_loglevel_name(
49 enum lttng_domain_type domain
, int loglevel
)
51 const char *name
= NULL
;
54 case LTTNG_DOMAIN_UST
:
55 name
= loglevel_value_to_name(loglevel
);
57 case LTTNG_DOMAIN_LOG4J
:
58 name
= loglevel_log4j_value_to_name(loglevel
);
60 case LTTNG_DOMAIN_JUL
:
61 name
= loglevel_jul_value_to_name(loglevel
);
63 case LTTNG_DOMAIN_PYTHON
:
64 name
= loglevel_python_value_to_name(loglevel
);
74 void print_event_rule_tracepoint(const struct lttng_event_rule
*event_rule
)
76 enum lttng_event_rule_status event_rule_status
;
77 enum lttng_domain_type domain_type
;
81 const struct lttng_log_level_rule
*log_level_rule
= NULL
;
82 unsigned int exclusions_count
;
85 event_rule_status
= lttng_event_rule_tracepoint_get_pattern(
86 event_rule
, &pattern
);
87 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
);
89 event_rule_status
= lttng_event_rule_tracepoint_get_domain_type(
90 event_rule
, &domain_type
);
91 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
);
93 _MSG(" rule: %s (type: tracepoint, domain: %s", pattern
,
94 lttng_domain_type_str(domain_type
));
96 event_rule_status
= lttng_event_rule_tracepoint_get_filter(
98 if (event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
) {
99 _MSG(", filter: %s", filter
);
101 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_UNSET
);
104 event_rule_status
= lttng_event_rule_tracepoint_get_log_level_rule(
105 event_rule
, &log_level_rule
);
106 if (event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
) {
107 enum lttng_log_level_rule_status llr_status
;
108 const char *log_level_op
;
109 const char *pretty_loglevel_name
;
111 switch (lttng_log_level_rule_get_type(log_level_rule
)) {
112 case LTTNG_LOG_LEVEL_RULE_TYPE_EXACTLY
:
114 llr_status
= lttng_log_level_rule_exactly_get_level(
115 log_level_rule
, &log_level
);
117 case LTTNG_LOG_LEVEL_RULE_TYPE_AT_LEAST_AS_SEVERE_AS
:
118 log_level_op
= "at least";
119 llr_status
= lttng_log_level_rule_at_least_as_severe_as_get_level(
120 log_level_rule
, &log_level
);
126 assert(llr_status
== LTTNG_LOG_LEVEL_RULE_STATUS_OK
);
128 pretty_loglevel_name
= get_pretty_loglevel_name(
129 domain_type
, log_level
);
130 if (pretty_loglevel_name
) {
131 _MSG(", log level %s %s", log_level_op
,
132 pretty_loglevel_name
);
134 _MSG(", log level %s %d", log_level_op
, log_level
);
137 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_UNSET
);
140 event_rule_status
= lttng_event_rule_tracepoint_get_exclusions_count(
141 event_rule
, &exclusions_count
);
142 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
);
143 if (exclusions_count
> 0) {
144 _MSG(", exclusions: ");
145 for (i
= 0; i
< exclusions_count
; i
++) {
146 const char *exclusion
;
148 event_rule_status
= lttng_event_rule_tracepoint_get_exclusion_at_index(
149 event_rule
, i
, &exclusion
);
150 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
);
152 _MSG("%s%s", i
> 0 ? "," : "", exclusion
);
159 static void print_kernel_probe_location(
160 const struct lttng_kernel_probe_location
*location
)
162 enum lttng_kernel_probe_location_status status
;
163 switch (lttng_kernel_probe_location_get_type(location
)) {
164 case LTTNG_KERNEL_PROBE_LOCATION_TYPE_ADDRESS
:
168 status
= lttng_kernel_probe_location_address_get_address(
170 if (status
!= LTTNG_KERNEL_PROBE_LOCATION_STATUS_OK
) {
171 ERR("Getting kernel probe location address failed.");
175 _MSG("0x%" PRIx64
, address
);
179 case LTTNG_KERNEL_PROBE_LOCATION_TYPE_SYMBOL_OFFSET
:
182 const char *symbol_name
;
184 symbol_name
= lttng_kernel_probe_location_symbol_get_name(
187 ERR("Getting kernel probe location symbol name failed.");
191 status
= lttng_kernel_probe_location_symbol_get_offset(
193 if (status
!= LTTNG_KERNEL_PROBE_LOCATION_STATUS_OK
) {
194 ERR("Getting kernel probe location address failed.");
199 _MSG("%s", symbol_name
);
201 _MSG("%s+0x%" PRIx64
, symbol_name
, offset
);
214 void print_event_rule_kernel_probe(const struct lttng_event_rule
*event_rule
)
216 enum lttng_event_rule_status event_rule_status
;
218 const struct lttng_kernel_probe_location
*location
;
220 assert(lttng_event_rule_get_type(event_rule
) == LTTNG_EVENT_RULE_TYPE_KERNEL_PROBE
);
222 event_rule_status
= lttng_event_rule_kernel_probe_get_event_name(event_rule
, &name
);
223 if (event_rule_status
!= LTTNG_EVENT_RULE_STATUS_OK
) {
224 ERR("Failed to get kprobe event rule's name.");
228 event_rule_status
= lttng_event_rule_kernel_probe_get_location(
229 event_rule
, &location
);
230 if (event_rule_status
!= LTTNG_EVENT_RULE_STATUS_OK
) {
231 ERR("Failed to get kprobe event rule's location.");
235 _MSG(" rule: %s (type: probe, location: ", name
);
237 print_kernel_probe_location(location
);
246 void print_event_rule_userspace_probe(const struct lttng_event_rule
*event_rule
)
248 enum lttng_event_rule_status event_rule_status
;
250 const struct lttng_userspace_probe_location
*location
;
251 enum lttng_userspace_probe_location_type userspace_probe_location_type
;
253 assert(lttng_event_rule_get_type(event_rule
) == LTTNG_EVENT_RULE_TYPE_USERSPACE_PROBE
);
255 event_rule_status
= lttng_event_rule_userspace_probe_get_event_name(
257 if (event_rule_status
!= LTTNG_EVENT_RULE_STATUS_OK
) {
258 ERR("Failed to get uprobe event rule's name.");
262 event_rule_status
= lttng_event_rule_userspace_probe_get_location(
263 event_rule
, &location
);
264 if (event_rule_status
!= LTTNG_EVENT_RULE_STATUS_OK
) {
265 ERR("Failed to get uprobe event rule's location.");
269 _MSG(" rule: %s (type: userspace probe, ", name
);
271 userspace_probe_location_type
=
272 lttng_userspace_probe_location_get_type(location
);
274 switch (userspace_probe_location_type
) {
275 case LTTNG_USERSPACE_PROBE_LOCATION_TYPE_FUNCTION
:
277 const char *binary_path
, *function_name
;
279 binary_path
= lttng_userspace_probe_location_function_get_binary_path(
281 function_name
= lttng_userspace_probe_location_function_get_function_name(
284 _MSG("location type: ELF, location: %s:%s", binary_path
, function_name
);
287 case LTTNG_USERSPACE_PROBE_LOCATION_TYPE_TRACEPOINT
:
289 const char *binary_path
, *provider_name
, *probe_name
;
291 binary_path
= lttng_userspace_probe_location_tracepoint_get_binary_path(
293 provider_name
= lttng_userspace_probe_location_tracepoint_get_provider_name(
295 probe_name
= lttng_userspace_probe_location_tracepoint_get_probe_name(
297 _MSG("location type: SDT, location: %s:%s:%s", binary_path
, provider_name
, probe_name
);
311 void print_event_rule_syscall(const struct lttng_event_rule
*event_rule
)
313 const char *pattern
, *filter
;
314 enum lttng_event_rule_status event_rule_status
;
316 assert(lttng_event_rule_get_type(event_rule
) == LTTNG_EVENT_RULE_TYPE_SYSCALL
);
318 event_rule_status
= lttng_event_rule_syscall_get_pattern(
319 event_rule
, &pattern
);
320 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
);
322 _MSG(" rule: %s (type: syscall", pattern
);
324 event_rule_status
= lttng_event_rule_syscall_get_filter(
325 event_rule
, &filter
);
326 if (event_rule_status
== LTTNG_EVENT_RULE_STATUS_OK
) {
327 _MSG(", filter: %s", filter
);
329 assert(event_rule_status
== LTTNG_EVENT_RULE_STATUS_UNSET
);
336 void print_event_rule(const struct lttng_event_rule
*event_rule
)
338 const enum lttng_event_rule_type event_rule_type
=
339 lttng_event_rule_get_type(event_rule
);
341 switch (event_rule_type
) {
342 case LTTNG_EVENT_RULE_TYPE_TRACEPOINT
:
343 print_event_rule_tracepoint(event_rule
);
345 case LTTNG_EVENT_RULE_TYPE_KERNEL_PROBE
:
346 print_event_rule_kernel_probe(event_rule
);
348 case LTTNG_EVENT_RULE_TYPE_USERSPACE_PROBE
:
349 print_event_rule_userspace_probe(event_rule
);
351 case LTTNG_EVENT_RULE_TYPE_SYSCALL
:
352 print_event_rule_syscall(event_rule
);
360 void print_one_event_expr(const struct lttng_event_expr
*event_expr
)
362 enum lttng_event_expr_type type
;
364 type
= lttng_event_expr_get_type(event_expr
);
367 case LTTNG_EVENT_EXPR_TYPE_EVENT_PAYLOAD_FIELD
:
371 name
= lttng_event_expr_event_payload_field_get_name(
377 case LTTNG_EVENT_EXPR_TYPE_CHANNEL_CONTEXT_FIELD
:
381 name
= lttng_event_expr_channel_context_field_get_name(
383 _MSG("$ctx.%s", name
);
387 case LTTNG_EVENT_EXPR_TYPE_APP_SPECIFIC_CONTEXT_FIELD
:
389 const char *provider_name
;
390 const char *type_name
;
392 provider_name
= lttng_event_expr_app_specific_context_field_get_provider_name(
394 type_name
= lttng_event_expr_app_specific_context_field_get_type_name(
397 _MSG("$app.%s:%s", provider_name
, type_name
);
401 case LTTNG_EVENT_EXPR_TYPE_ARRAY_FIELD_ELEMENT
:
404 const struct lttng_event_expr
*parent_expr
;
405 enum lttng_event_expr_status status
;
407 parent_expr
= lttng_event_expr_array_field_element_get_parent_expr(
409 assert(parent_expr
!= NULL
);
411 print_one_event_expr(parent_expr
);
413 status
= lttng_event_expr_array_field_element_get_index(
415 assert(status
== LTTNG_EVENT_EXPR_STATUS_OK
);
427 void print_condition_on_event(const struct lttng_condition
*condition
)
429 const struct lttng_event_rule
*event_rule
;
430 enum lttng_condition_status condition_status
;
431 unsigned int cap_desc_count
, i
;
434 lttng_condition_on_event_get_rule(condition
, &event_rule
);
435 assert(condition_status
== LTTNG_CONDITION_STATUS_OK
);
437 print_event_rule(event_rule
);
440 lttng_condition_on_event_get_capture_descriptor_count(
441 condition
, &cap_desc_count
);
442 assert(condition_status
== LTTNG_CONDITION_STATUS_OK
);
444 if (cap_desc_count
> 0) {
447 for (i
= 0; i
< cap_desc_count
; i
++) {
448 const struct lttng_event_expr
*cap_desc
=
449 lttng_condition_on_event_get_capture_descriptor_at_index(
453 print_one_event_expr(cap_desc
);
460 void print_action_errors(const struct lttng_trigger
*trigger
,
461 const struct lttng_action
*action
)
463 unsigned int i
, count
, printed_errors_count
= 0;
464 enum lttng_error_code error_query_ret
;
465 enum lttng_error_query_results_status results_status
;
466 struct lttng_error_query_results
*results
= NULL
;
467 const char *trigger_name
;
469 enum lttng_trigger_status trigger_status
;
470 struct lttng_error_query
*query
=
471 lttng_error_query_action_create(trigger
, action
);
475 trigger_status
= lttng_trigger_get_name(trigger
, &trigger_name
);
476 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
478 trigger_status
= lttng_trigger_get_owner_uid(trigger
, &trigger_uid
);
479 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
481 error_query_ret
= lttng_error_query_execute(
482 query
, lttng_session_daemon_command_endpoint
, &results
);
483 if (error_query_ret
!= LTTNG_OK
) {
484 ERR("Failed to query errors of trigger '%s' (owner uid: %d): %s",
485 trigger_name
, (int) trigger_uid
,
486 lttng_strerror(-error_query_ret
));
490 results_status
= lttng_error_query_results_get_count(results
, &count
);
491 assert(results_status
== LTTNG_ERROR_QUERY_RESULTS_STATUS_OK
);
495 for (i
= 0; i
< count
; i
++) {
496 const struct lttng_error_query_result
*result
;
497 enum lttng_error_query_result_status result_status
;
498 const char *result_name
;
499 const char *result_description
;
500 uint64_t result_value
;
502 results_status
= lttng_error_query_results_get_result(
503 results
, &result
, i
);
504 assert(results_status
== LTTNG_ERROR_QUERY_RESULTS_STATUS_OK
);
506 result_status
= lttng_error_query_result_get_name(
507 result
, &result_name
);
508 assert(result_status
== LTTNG_ERROR_QUERY_RESULT_STATUS_OK
);
509 result_status
= lttng_error_query_result_get_description(
510 result
, &result_description
);
511 assert(result_status
== LTTNG_ERROR_QUERY_RESULT_STATUS_OK
);
513 if (lttng_error_query_result_get_type(result
) ==
514 LTTNG_ERROR_QUERY_RESULT_TYPE_COUNTER
) {
515 result_status
= lttng_error_query_result_counter_get_value(
516 result
, &result_value
);
517 assert(result_status
==
518 LTTNG_ERROR_QUERY_RESULT_STATUS_OK
);
519 if (result_value
== 0) {
524 _MSG(" %s: %" PRIu64
, result_name
,
526 printed_errors_count
++;
528 _MSG(" Unknown error query result type for result '%s' (%s)",
529 result_name
, result_description
);
534 if (printed_errors_count
== 0) {
540 lttng_error_query_destroy(query
);
541 lttng_error_query_results_destroy(results
);
545 void print_one_action(const struct lttng_trigger
*trigger
,
546 const struct lttng_action
*action
)
548 enum lttng_action_type action_type
;
549 enum lttng_action_status action_status
;
550 const struct lttng_rate_policy
*policy
= NULL
;
553 action_type
= lttng_action_get_type(action
);
554 assert(action_type
!= LTTNG_ACTION_TYPE_GROUP
);
556 switch (action_type
) {
557 case LTTNG_ACTION_TYPE_NOTIFY
:
560 action_status
= lttng_action_notify_get_rate_policy(
562 if (action_status
!= LTTNG_ACTION_STATUS_OK
) {
563 ERR("Failed to retrieve rate policy.");
567 case LTTNG_ACTION_TYPE_START_SESSION
:
568 action_status
= lttng_action_start_session_get_session_name(
570 assert(action_status
== LTTNG_ACTION_STATUS_OK
);
571 _MSG("start session `%s`", value
);
573 action_status
= lttng_action_start_session_get_rate_policy(
575 if (action_status
!= LTTNG_ACTION_STATUS_OK
) {
576 ERR("Failed to retrieve rate policy.");
580 case LTTNG_ACTION_TYPE_STOP_SESSION
:
581 action_status
= lttng_action_stop_session_get_session_name(
583 assert(action_status
== LTTNG_ACTION_STATUS_OK
);
584 _MSG("stop session `%s`", value
);
586 action_status
= lttng_action_stop_session_get_rate_policy(
588 if (action_status
!= LTTNG_ACTION_STATUS_OK
) {
589 ERR("Failed to retrieve rate policy.");
593 case LTTNG_ACTION_TYPE_ROTATE_SESSION
:
594 action_status
= lttng_action_rotate_session_get_session_name(
596 assert(action_status
== LTTNG_ACTION_STATUS_OK
);
597 _MSG("rotate session `%s`", value
);
599 action_status
= lttng_action_rotate_session_get_rate_policy(
601 if (action_status
!= LTTNG_ACTION_STATUS_OK
) {
602 ERR("Failed to retrieve rate policy.");
606 case LTTNG_ACTION_TYPE_SNAPSHOT_SESSION
:
608 const struct lttng_snapshot_output
*output
;
610 action_status
= lttng_action_snapshot_session_get_session_name(
612 assert(action_status
== LTTNG_ACTION_STATUS_OK
);
613 _MSG("snapshot session `%s`", value
);
615 action_status
= lttng_action_snapshot_session_get_output(
617 if (action_status
== LTTNG_ACTION_STATUS_OK
) {
620 const char *ctrl_url
, *data_url
;
621 bool starts_with_file
, starts_with_net
, starts_with_net6
;
623 ctrl_url
= lttng_snapshot_output_get_ctrl_url(output
);
624 assert(ctrl_url
&& strlen(ctrl_url
) > 0);
626 data_url
= lttng_snapshot_output_get_data_url(output
);
629 starts_with_file
= strncmp(ctrl_url
, "file://", strlen("file://")) == 0;
630 starts_with_net
= strncmp(ctrl_url
, "net://", strlen("net://")) == 0;
631 starts_with_net6
= strncmp(ctrl_url
, "net6://", strlen("net6://")) == 0;
633 if (ctrl_url
[0] == '/' || starts_with_file
) {
634 if (starts_with_file
) {
635 ctrl_url
+= strlen("file://");
638 _MSG(", path: %s", ctrl_url
);
639 } else if (starts_with_net
|| starts_with_net6
) {
640 _MSG(", url: %s", ctrl_url
);
642 assert(strlen(data_url
) > 0);
644 _MSG(", control url: %s, data url: %s", ctrl_url
, data_url
);
647 name
= lttng_snapshot_output_get_name(output
);
649 if (strlen(name
) > 0) {
650 _MSG(", name: %s", name
);
653 max_size
= lttng_snapshot_output_get_maxsize(output
);
654 if (max_size
!= -1ULL) {
655 _MSG(", max size: %" PRIu64
, max_size
);
659 action_status
= lttng_action_snapshot_session_get_rate_policy(
661 if (action_status
!= LTTNG_ACTION_STATUS_OK
) {
662 ERR("Failed to retrieve rate policy.");
672 enum lttng_rate_policy_type policy_type
;
673 enum lttng_rate_policy_status policy_status
;
674 uint64_t policy_value
= 0;
676 policy_type
= lttng_rate_policy_get_type(policy
);
678 switch (policy_type
) {
679 case LTTNG_RATE_POLICY_TYPE_EVERY_N
:
680 policy_status
= lttng_rate_policy_every_n_get_interval(
681 policy
, &policy_value
);
682 if (policy_status
!= LTTNG_RATE_POLICY_STATUS_OK
) {
683 ERR("Failed to get action rate policy interval");
686 if (policy_value
> 1) {
687 /* The default is 1 so print only when it is a
690 _MSG(", rate policy: after every %" PRIu64
695 case LTTNG_RATE_POLICY_TYPE_ONCE_AFTER_N
:
696 policy_status
= lttng_rate_policy_once_after_n_get_threshold(
697 policy
, &policy_value
);
698 if (policy_status
!= LTTNG_RATE_POLICY_STATUS_OK
) {
699 ERR("Failed to get action rate policy interval");
702 _MSG(", rate policy: once after %" PRIu64
712 print_action_errors(trigger
, action
);
719 void print_trigger_errors(const struct lttng_trigger
*trigger
)
721 unsigned int i
, count
, printed_errors_count
= 0;
722 enum lttng_error_code error_query_ret
;
723 enum lttng_error_query_results_status results_status
;
724 struct lttng_error_query_results
*results
= NULL
;
725 enum lttng_trigger_status trigger_status
;
726 const char *trigger_name
;
728 struct lttng_error_query
*query
=
729 lttng_error_query_trigger_create(trigger
);
733 trigger_status
= lttng_trigger_get_name(trigger
, &trigger_name
);
734 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
736 trigger_status
= lttng_trigger_get_owner_uid(trigger
, &trigger_uid
);
737 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
739 error_query_ret
= lttng_error_query_execute(
740 query
, lttng_session_daemon_command_endpoint
, &results
);
741 if (error_query_ret
!= LTTNG_OK
) {
742 ERR("Failed to query errors of trigger '%s' (owner uid: %d): %s",
743 trigger_name
, (int) trigger_uid
,
744 lttng_strerror(-error_query_ret
));
748 results_status
= lttng_error_query_results_get_count(results
, &count
);
749 assert(results_status
== LTTNG_ERROR_QUERY_RESULTS_STATUS_OK
);
753 for (i
= 0; i
< count
; i
++) {
754 const struct lttng_error_query_result
*result
;
755 enum lttng_error_query_result_status result_status
;
756 const char *result_name
;
757 const char *result_description
;
758 uint64_t result_value
;
760 results_status
= lttng_error_query_results_get_result(
761 results
, &result
, i
);
762 assert(results_status
== LTTNG_ERROR_QUERY_RESULTS_STATUS_OK
);
764 result_status
= lttng_error_query_result_get_name(
765 result
, &result_name
);
766 assert(result_status
== LTTNG_ERROR_QUERY_RESULT_STATUS_OK
);
767 result_status
= lttng_error_query_result_get_description(
768 result
, &result_description
);
769 assert(result_status
== LTTNG_ERROR_QUERY_RESULT_STATUS_OK
);
771 if (lttng_error_query_result_get_type(result
) ==
772 LTTNG_ERROR_QUERY_RESULT_TYPE_COUNTER
) {
773 result_status
= lttng_error_query_result_counter_get_value(
774 result
, &result_value
);
775 assert(result_status
==
776 LTTNG_ERROR_QUERY_RESULT_STATUS_OK
);
777 if (result_value
== 0) {
782 _MSG(" %s: %" PRIu64
, result_name
,
784 printed_errors_count
++;
786 _MSG(" Unknown error query result type for result '%s' (%s)",
787 result_name
, result_description
);
792 if (printed_errors_count
== 0) {
798 lttng_error_query_destroy(query
);
799 lttng_error_query_results_destroy(results
);
803 void print_one_trigger(const struct lttng_trigger
*trigger
)
805 const struct lttng_condition
*condition
;
806 enum lttng_condition_type condition_type
;
807 const struct lttng_action
*action
;
808 enum lttng_action_type action_type
;
809 enum lttng_trigger_status trigger_status
;
813 trigger_status
= lttng_trigger_get_name(trigger
, &name
);
814 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
816 trigger_status
= lttng_trigger_get_owner_uid(trigger
, &trigger_uid
);
817 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
819 MSG("- name: %s", name
);
820 MSG(" user id: %d", trigger_uid
);
822 condition
= lttng_trigger_get_const_condition(trigger
);
823 condition_type
= lttng_condition_get_type(condition
);
824 MSG(" condition: %s", lttng_condition_type_str(condition_type
));
825 switch (condition_type
) {
826 case LTTNG_CONDITION_TYPE_ON_EVENT
:
827 print_condition_on_event(condition
);
830 MSG(" (condition type not handled in %s)", __func__
);
834 action
= lttng_trigger_get_const_action(trigger
);
835 action_type
= lttng_action_get_type(action
);
836 if (action_type
== LTTNG_ACTION_TYPE_GROUP
) {
837 unsigned int count
, i
;
838 enum lttng_action_status action_status
;
842 action_status
= lttng_action_group_get_count(action
, &count
);
843 assert(action_status
== LTTNG_ACTION_STATUS_OK
);
845 for (i
= 0; i
< count
; i
++) {
846 const struct lttng_action
*subaction
=
847 lttng_action_group_get_at_index(
851 print_one_action(trigger
, subaction
);
855 print_one_action(trigger
, action
);
858 print_trigger_errors(trigger
);
862 int compare_triggers_by_name(const void *a
, const void *b
)
864 const struct lttng_trigger
*trigger_a
= *((const struct lttng_trigger
**) a
);
865 const struct lttng_trigger
*trigger_b
= *((const struct lttng_trigger
**) b
);
866 const char *name_a
, *name_b
;
867 enum lttng_trigger_status trigger_status
;
869 trigger_status
= lttng_trigger_get_name(trigger_a
, &name_a
);
870 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
872 trigger_status
= lttng_trigger_get_name(trigger_b
, &name_b
);
873 assert(trigger_status
== LTTNG_TRIGGER_STATUS_OK
);
875 return strcmp(name_a
, name_b
);
878 int cmd_list_triggers(int argc
, const char **argv
)
881 struct argpar_parse_ret argpar_parse_ret
= {};
882 struct lttng_triggers
*triggers
= NULL
;
884 struct lttng_dynamic_pointer_array sorted_triggers
;
885 enum lttng_trigger_status trigger_status
;
886 unsigned int num_triggers
;
888 lttng_dynamic_pointer_array_init(&sorted_triggers
, NULL
);
890 argpar_parse_ret
= argpar_parse(
891 argc
- 1, argv
+ 1, list_trigger_options
, true);
892 if (!argpar_parse_ret
.items
) {
893 ERR("%s", argpar_parse_ret
.error
);
897 for (i
= 0; i
< argpar_parse_ret
.items
->n_items
; i
++) {
898 const struct argpar_item
*item
=
899 argpar_parse_ret
.items
->items
[i
];
901 if (item
->type
== ARGPAR_ITEM_TYPE_OPT
) {
902 const struct argpar_item_opt
*item_opt
=
903 (const struct argpar_item_opt
*) item
;
905 switch (item_opt
->descr
->id
) {
911 case OPT_LIST_OPTIONS
:
912 list_cmd_options_argpar(stdout
,
913 list_trigger_options
);
922 const struct argpar_item_non_opt
*item_non_opt
=
923 (const struct argpar_item_non_opt
*) item
;
925 ERR("Unexpected argument: %s", item_non_opt
->arg
);
929 ret
= lttng_list_triggers(&triggers
);
930 if (ret
!= LTTNG_OK
) {
931 ERR("Error listing triggers: %s.", lttng_strerror(-ret
));
935 trigger_status
= lttng_triggers_get_count(triggers
, &num_triggers
);
936 if (trigger_status
!= LTTNG_TRIGGER_STATUS_OK
) {
937 ERR("Failed to get trigger count.");
941 for (i
= 0; i
< num_triggers
; i
++) {
942 const int add_ret
= lttng_dynamic_pointer_array_add_pointer(
944 (void *) lttng_triggers_get_at_index(triggers
, i
));
947 ERR("Failed to allocate array of struct lttng_trigger *.");
952 qsort(sorted_triggers
.array
.buffer
.data
, num_triggers
,
953 sizeof(struct lttng_trigger
*),
954 compare_triggers_by_name
);
956 for (i
= 0; i
< num_triggers
; i
++) {
957 const struct lttng_trigger
*trigger_to_print
=
958 (const struct lttng_trigger
*)
959 lttng_dynamic_pointer_array_get_pointer(
960 &sorted_triggers
, i
);
962 print_one_trigger(trigger_to_print
);
972 argpar_parse_ret_fini(&argpar_parse_ret
);
973 lttng_triggers_destroy(triggers
);
974 lttng_dynamic_pointer_array_reset(&sorted_triggers
);