4 * Babeltrace Copy Trace Structure
6 * Copyright 2017 Julien Desfossez <jdesfossez@efficios.com>
8 * Author: Julien Desfossez <jdesfossez@efficios.com>
10 * Permission is hereby granted, free of charge, to any person obtaining a copy
11 * of this software and associated documentation files (the "Software"), to deal
12 * in the Software without restriction, including without limitation the rights
13 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14 * copies of the Software, and to permit persons to whom the Software is
15 * furnished to do so, subject to the following conditions:
17 * The above copyright notice and this permission notice shall be included in
18 * all copies or substantial portions of the Software.
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
23 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
29 #define BT_LOG_TAG "PLUGIN-LTTNG-UTILS-DEBUG-INFO-FLT-COPY"
34 #include <babeltrace/ctf-ir/event.h>
35 #include <babeltrace/ctf-ir/packet.h>
36 #include <babeltrace/ctf-ir/event-class.h>
37 #include <babeltrace/ctf-ir/stream.h>
38 #include <babeltrace/ctf-ir/stream-class.h>
39 #include <babeltrace/ctf-ir/clock-class.h>
40 #include <babeltrace/ctf-ir/fields.h>
41 #include <babeltrace/ctf-writer/stream-class.h>
42 #include <babeltrace/ctf-writer/stream.h>
44 #include <ctfcopytrace.h>
45 #include "debug-info.h"
48 struct bt_ctf_stream
*insert_new_stream(
49 struct debug_info_iterator
*debug_it
,
50 struct bt_ctf_stream
*stream
,
51 struct debug_info_trace
*di_trace
);
54 void unref_stream(struct bt_ctf_stream
*stream
)
60 void unref_packet(struct bt_ctf_packet
*packet
)
66 void unref_stream_class(struct bt_ctf_stream_class
*stream_class
)
72 void unref_debug_info(struct debug_info
*debug_info
)
74 debug_info_destroy(debug_info
);
78 void destroy_stream_state_key(gpointer key
)
80 g_free((enum fs_writer_stream_state
*) key
);
84 struct bt_ctf_field
*get_payload_field(FILE *err
,
85 struct bt_ctf_event
*event
, const char *field_name
)
87 struct bt_ctf_field
*field
= NULL
, *payload
= NULL
;
88 struct bt_ctf_field_type
*payload_type
= NULL
;
90 payload
= bt_ctf_event_get_payload(event
, NULL
);
93 payload_type
= bt_ctf_field_get_type(payload
);
96 if (bt_ctf_field_type_get_type_id(payload_type
) != BT_CTF_FIELD_TYPE_ID_STRUCT
) {
97 BT_LOGE("Wrong type, expected struct: field-name=\"%s\"",
102 field
= bt_ctf_field_structure_get_field(payload
, field_name
);
105 bt_put(payload_type
);
111 struct bt_ctf_field
*get_stream_event_context_field(FILE *err
,
112 struct bt_ctf_event
*event
, const char *field_name
)
114 struct bt_ctf_field
*field
= NULL
, *sec
= NULL
;
115 struct bt_ctf_field_type
*sec_type
= NULL
;
117 sec
= bt_ctf_event_get_stream_event_context(event
);
122 sec_type
= bt_ctf_field_get_type(sec
);
125 if (bt_ctf_field_type_get_type_id(sec_type
) != BT_CTF_FIELD_TYPE_ID_STRUCT
) {
126 BT_LOGE("Wrong type, expected struct, field-name=\"%s\"",
131 field
= bt_ctf_field_structure_get_field(sec
, field_name
);
140 int get_stream_event_context_unsigned_int_field_value(FILE *err
,
141 struct bt_ctf_event
*event
, const char *field_name
,
145 struct bt_ctf_field
*field
= NULL
;
146 struct bt_ctf_field_type
*field_type
= NULL
;
148 field
= get_stream_event_context_field(err
, event
, field_name
);
153 field_type
= bt_ctf_field_get_type(field
);
156 if (bt_ctf_field_type_get_type_id(field_type
) != BT_CTF_FIELD_TYPE_ID_INTEGER
) {
157 BT_LOGE("Wrong type, expected integer: field-name=\"%s\"",
162 if (bt_ctf_field_type_integer_get_signed(field_type
) != 0) {
163 BT_LOGE("Wrong type, expected unsigned integer: field-name=\"%s\"",
168 ret
= bt_ctf_field_unsigned_integer_get_value(field
, value
);
170 BT_LOGE("Failed to get value: field-name=\"%s\"",
185 int get_stream_event_context_int_field_value(FILE *err
, struct bt_ctf_event
*event
,
186 const char *field_name
, int64_t *value
)
188 struct bt_ctf_field
*field
= NULL
;
189 struct bt_ctf_field_type
*field_type
= NULL
;
192 field
= get_stream_event_context_field(err
, event
, field_name
);
197 field_type
= bt_ctf_field_get_type(field
);
200 if (bt_ctf_field_type_get_type_id(field_type
) != BT_CTF_FIELD_TYPE_ID_INTEGER
) {
201 BT_LOGE("Wrong type, expected integer: field-name=\"%s\"", field_name
);
205 if (bt_ctf_field_type_integer_get_signed(field_type
) != 1) {
206 BT_LOGE("Wrong type, expected signed integer: field-name=\"%s\"",
211 ret
= bt_ctf_field_signed_integer_get_value(field
, value
);
223 int get_payload_unsigned_int_field_value(FILE *err
,
224 struct bt_ctf_event
*event
, const char *field_name
,
227 struct bt_ctf_field
*field
= NULL
;
228 struct bt_ctf_field_type
*field_type
= NULL
;
231 field
= get_payload_field(err
, event
, field_name
);
233 BT_LOGE("Failed to get payload: field-name=\"%s\"", field_name
);
237 field_type
= bt_ctf_field_get_type(field
);
240 if (bt_ctf_field_type_get_type_id(field_type
) != BT_CTF_FIELD_TYPE_ID_INTEGER
) {
241 BT_LOGE("Wrong type, expected integer: field-name=\"%s\"",
246 if (bt_ctf_field_type_integer_get_signed(field_type
) != 0) {
247 BT_LOGE("Wrong type, expected unsigned integer: field-name=\"%s\"",
252 ret
= bt_ctf_field_unsigned_integer_get_value(field
, value
);
254 BT_LOGE("Failed to get value: field-name=\"%s\"",
269 int get_payload_int_field_value(FILE *err
, struct bt_ctf_event
*event
,
270 const char *field_name
, int64_t *value
)
272 struct bt_ctf_field
*field
= NULL
;
273 struct bt_ctf_field_type
*field_type
= NULL
;
276 field
= get_payload_field(err
, event
, field_name
);
278 BT_LOGE("Failed to get payload: field-name=\"%s\"", field_name
);
282 field_type
= bt_ctf_field_get_type(field
);
285 if (bt_ctf_field_type_get_type_id(field_type
) != BT_CTF_FIELD_TYPE_ID_INTEGER
) {
286 BT_LOGE("Wrong type, expected integer: field-name=\"%s\"", field_name
);
290 if (bt_ctf_field_type_integer_get_signed(field_type
) != 1) {
291 BT_LOGE("Wrong type, expected signed integer field-name=\"%s\"",
296 ret
= bt_ctf_field_signed_integer_get_value(field
, value
);
298 BT_LOGE("Failed to get value: field-name=\"%s\"",
313 int get_payload_string_field_value(FILE *err
,
314 struct bt_ctf_event
*event
, const char *field_name
,
317 struct bt_ctf_field
*field
= NULL
;
318 struct bt_ctf_field_type
*field_type
= NULL
;
322 * The field might not exist, no error here.
324 field
= get_payload_field(err
, event
, field_name
);
329 field_type
= bt_ctf_field_get_type(field
);
332 if (bt_ctf_field_type_get_type_id(field_type
) != BT_CTF_FIELD_TYPE_ID_STRING
) {
333 BT_LOGE("Wrong type, expected string: field-name=\"%s\"",
338 *value
= bt_ctf_field_string_get_value(field
);
340 BT_LOGE("Failed to get value: field-name=\"%s\"",
357 int get_payload_build_id_field_value(FILE *err
,
358 struct bt_ctf_event
*event
, const char *field_name
,
359 uint8_t **build_id
, uint64_t *build_id_len
)
361 struct bt_ctf_field
*field
= NULL
, *seq_len
= NULL
;
362 struct bt_ctf_field_type
*field_type
= NULL
;
363 struct bt_ctf_field
*seq_field
= NULL
;
369 field
= get_payload_field(err
, event
, field_name
);
371 BT_LOGE("Failed to get payload: field-name=\"%s\"", field_name
);
375 field_type
= bt_ctf_field_get_type(field
);
378 if (bt_ctf_field_type_get_type_id(field_type
) != BT_CTF_FIELD_TYPE_ID_SEQUENCE
) {
379 BT_LOGE("Wrong type, expected sequence: field-name=\"%s\"", field_name
);
384 seq_len
= bt_ctf_field_sequence_get_length(field
);
387 ret
= bt_ctf_field_unsigned_integer_get_value(seq_len
, build_id_len
);
389 BT_LOGE("Failed to get value: field-name=\"%s\"",
395 *build_id
= g_new0(uint8_t, *build_id_len
);
397 BT_LOGE_STR("Failed to allocate build_id.");
401 for (i
= 0; i
< *build_id_len
; i
++) {
404 seq_field
= bt_ctf_field_sequence_get_field(field
, i
);
406 BT_LOGE("Failed to get field in sequence: sequence-name=\"%s\", index=%" PRIu64
,
411 ret
= bt_ctf_field_unsigned_integer_get_value(seq_field
, &tmp
);
413 BT_LOGE("Failed to get value: field-name=\"%s\"",
419 (*build_id
)[i
] = (uint8_t) tmp
;
434 struct debug_info
*lookup_trace_debug_info(struct debug_info_iterator
*debug_it
,
435 struct bt_ctf_trace
*writer_trace
,
436 struct debug_info_trace
*di_trace
)
438 return (struct debug_info
*) g_hash_table_lookup(
439 di_trace
->trace_debug_map
,
440 (gpointer
) writer_trace
);
444 struct debug_info
*insert_new_debug_info(struct debug_info_iterator
*debug_it
,
445 struct bt_ctf_trace
*writer_trace
,
446 struct debug_info_trace
*di_trace
)
448 struct debug_info
*debug_info
= NULL
;
449 struct bt_value
*field
= NULL
;
450 const char *str_value
;
451 enum bt_value_status ret
;
453 field
= bt_ctf_trace_get_environment_field_value_by_name(writer_trace
,
455 /* No domain field, no debug info */
459 ret
= bt_value_string_get(field
, &str_value
);
460 assert(ret
== BT_VALUE_STATUS_OK
);
462 /* Domain not ust, no debug info */
463 if (strcmp(str_value
, "ust") != 0) {
468 /* No tracer_name, no debug info */
469 field
= bt_ctf_trace_get_environment_field_value_by_name(writer_trace
,
471 /* No tracer_name, no debug info */
475 ret
= bt_value_string_get(field
, &str_value
);
476 assert(ret
== BT_VALUE_STATUS_OK
);
478 /* Tracer_name not lttng-ust, no debug info */
479 if (strcmp(str_value
, "lttng-ust") != 0) {
484 debug_info
= debug_info_create(debug_it
->debug_info_component
);
486 BT_LOGE_STR("Failed to create debug info.");
490 g_hash_table_insert(di_trace
->trace_debug_map
, (gpointer
) writer_trace
,
499 struct debug_info
*get_trace_debug_info(struct debug_info_iterator
*debug_it
,
500 struct bt_ctf_trace
*writer_trace
,
501 struct debug_info_trace
*di_trace
)
503 struct debug_info
*debug_info
;
505 debug_info
= lookup_trace_debug_info(debug_it
, writer_trace
, di_trace
);
510 debug_info
= insert_new_debug_info(debug_it
, writer_trace
, di_trace
);
517 struct debug_info_trace
*lookup_trace(struct debug_info_iterator
*debug_it
,
518 struct bt_ctf_trace
*trace
)
520 return (struct debug_info_trace
*) g_hash_table_lookup(
526 enum debug_info_stream_state
*insert_new_stream_state(
527 struct debug_info_iterator
*debug_it
,
528 struct debug_info_trace
*di_trace
, struct bt_ctf_stream
*stream
)
530 enum debug_info_stream_state
*v
= NULL
;
532 v
= g_new0(enum debug_info_stream_state
, 1);
534 BT_LOGE_STR("Failed to allocate debug_info_stream_state.");
537 *v
= DEBUG_INFO_UNKNOWN_STREAM
;
539 g_hash_table_insert(di_trace
->stream_states
, stream
, v
);
546 void check_completed_trace(gpointer key
, gpointer value
, gpointer user_data
)
548 enum debug_info_stream_state
*state
= value
;
549 int *trace_completed
= user_data
;
551 if (*state
!= DEBUG_INFO_COMPLETED_STREAM
) {
552 *trace_completed
= 0;
557 gboolean
empty_ht(gpointer key
, gpointer value
, gpointer user_data
)
563 void debug_info_close_trace(struct debug_info_iterator
*debug_it
,
564 struct debug_info_trace
*di_trace
)
566 if (di_trace
->static_listener_id
>= 0) {
567 bt_ctf_trace_remove_is_static_listener(di_trace
->trace
,
568 di_trace
->static_listener_id
);
571 /* Empty the stream class HT. */
572 g_hash_table_foreach_remove(di_trace
->stream_class_map
,
574 g_hash_table_destroy(di_trace
->stream_class_map
);
576 /* Empty the stream HT. */
577 g_hash_table_foreach_remove(di_trace
->stream_map
,
579 g_hash_table_destroy(di_trace
->stream_map
);
581 /* Empty the stream state HT. */
582 g_hash_table_foreach_remove(di_trace
->stream_states
,
584 g_hash_table_destroy(di_trace
->stream_states
);
586 /* Empty the packet HT. */
587 g_hash_table_foreach_remove(di_trace
->packet_map
,
589 g_hash_table_destroy(di_trace
->packet_map
);
591 /* Empty the trace_debug HT. */
592 g_hash_table_foreach_remove(di_trace
->trace_debug_map
,
594 g_hash_table_destroy(di_trace
->trace_debug_map
);
598 int sync_event_classes(struct debug_info_iterator
*debug_it
,
599 struct bt_ctf_stream
*stream
,
600 struct bt_ctf_stream
*writer_stream
)
603 struct bt_ctf_stream_class
*stream_class
= NULL
,
604 *writer_stream_class
= NULL
;
605 enum bt_component_status ret
;
607 stream_class
= bt_ctf_stream_get_class(stream
);
608 assert(stream_class
);
610 writer_stream_class
= bt_ctf_stream_get_class(writer_stream
);
611 assert(writer_stream_class
);
613 ret
= ctf_copy_event_classes(debug_it
->err
, stream_class
,
614 writer_stream_class
);
615 if (ret
!= BT_COMPONENT_STATUS_OK
) {
616 BT_LOGE_STR("Failed to copy event classes.");
626 bt_put(stream_class
);
627 bt_put(writer_stream_class
);
632 void trace_is_static_listener(struct bt_ctf_trace
*trace
, void *data
)
634 struct debug_info_trace
*di_trace
= data
;
635 int trace_completed
= 1, ret
, nr_stream
, i
;
636 struct bt_ctf_stream
*stream
= NULL
, *writer_stream
= NULL
;
637 struct bt_ctf_trace
*writer_trace
= di_trace
->writer_trace
;
640 * When the trace becomes static, make sure that we have all
641 * the event classes in our stream_class copies before setting it
644 nr_stream
= bt_ctf_trace_get_stream_count(trace
);
645 for (i
= 0; i
< nr_stream
; i
++) {
646 stream
= bt_ctf_trace_get_stream_by_index(trace
, i
);
649 writer_stream
= bt_ctf_trace_get_stream_by_index(writer_trace
, i
);
650 assert(writer_stream
);
652 ret
= sync_event_classes(di_trace
->debug_it
, stream
, writer_stream
);
654 BT_LOGE_STR("Failed to synchronize the event classes.");
658 BT_PUT(writer_stream
);
661 bt_ctf_trace_set_is_static(di_trace
->writer_trace
);
662 di_trace
->trace_static
= 1;
664 g_hash_table_foreach(di_trace
->stream_states
,
665 check_completed_trace
, &trace_completed
);
666 if (trace_completed
) {
667 debug_info_close_trace(di_trace
->debug_it
, di_trace
);
668 g_hash_table_remove(di_trace
->debug_it
->trace_map
,
673 bt_put(writer_stream
);
678 struct debug_info_trace
*insert_new_trace(struct debug_info_iterator
*debug_it
,
679 struct bt_ctf_stream
*stream
) {
680 struct bt_ctf_trace
*writer_trace
= NULL
;
681 struct debug_info_trace
*di_trace
= NULL
;
682 struct bt_ctf_trace
*trace
= NULL
;
683 struct bt_ctf_stream_class
*stream_class
= NULL
;
684 struct bt_ctf_stream
*writer_stream
= NULL
;
685 int ret
, nr_stream
, i
;
687 writer_trace
= bt_ctf_trace_create();
689 BT_LOGE_STR("Failed to create a new trace.");
693 stream_class
= bt_ctf_stream_get_class(stream
);
694 assert(stream_class
);
696 trace
= bt_ctf_stream_class_get_trace(stream_class
);
699 ret
= ctf_copy_trace(debug_it
->err
, trace
, writer_trace
);
700 if (ret
!= BT_COMPONENT_STATUS_OK
) {
701 BT_LOGE_STR("Failed to copy CTF trace.");
705 di_trace
= g_new0(struct debug_info_trace
, 1);
707 BT_LOGE_STR("Failed to allocate debug_info_trace.");
711 di_trace
->trace
= trace
;
712 di_trace
->writer_trace
= writer_trace
;
713 di_trace
->debug_info_component
= debug_it
->debug_info_component
;
714 di_trace
->debug_it
= debug_it
;
715 di_trace
->stream_map
= g_hash_table_new_full(g_direct_hash
,
716 g_direct_equal
, NULL
, (GDestroyNotify
) unref_stream
);
717 di_trace
->stream_class_map
= g_hash_table_new_full(g_direct_hash
,
718 g_direct_equal
, NULL
, (GDestroyNotify
) unref_stream_class
);
719 di_trace
->packet_map
= g_hash_table_new_full(g_direct_hash
,
720 g_direct_equal
, NULL
, (GDestroyNotify
) unref_packet
);
721 di_trace
->trace_debug_map
= g_hash_table_new_full(g_direct_hash
,
722 g_direct_equal
, NULL
, (GDestroyNotify
) unref_debug_info
);
723 di_trace
->stream_states
= g_hash_table_new_full(g_direct_hash
,
724 g_direct_equal
, NULL
, destroy_stream_state_key
);
725 g_hash_table_insert(debug_it
->trace_map
, (gpointer
) trace
, di_trace
);
727 /* Set all the existing streams in the unknown state. */
728 nr_stream
= bt_ctf_trace_get_stream_count(trace
);
729 for (i
= 0; i
< nr_stream
; i
++) {
730 stream
= bt_ctf_trace_get_stream_by_index(trace
, i
);
733 insert_new_stream_state(debug_it
, di_trace
, stream
);
734 writer_stream
= insert_new_stream(debug_it
, stream
, di_trace
);
735 if (!writer_stream
) {
736 BT_LOGE_STR("Failed to insert new stream.");
739 bt_get(writer_stream
);
740 ret
= sync_event_classes(debug_it
, stream
, writer_stream
);
742 BT_LOGE_STR("Failed to synchronize event classes.");
745 BT_PUT(writer_stream
);
749 /* Check if the trace is already static or register a listener. */
750 if (bt_ctf_trace_is_static(trace
)) {
751 di_trace
->trace_static
= 1;
752 di_trace
->static_listener_id
= -1;
753 bt_ctf_trace_set_is_static(writer_trace
);
755 ret
= bt_ctf_trace_add_is_static_listener(trace
,
756 trace_is_static_listener
, di_trace
);
758 di_trace
->static_listener_id
= ret
;
765 BT_PUT(writer_trace
);
770 bt_put(writer_stream
);
771 bt_put(stream_class
);
777 struct bt_ctf_packet
*lookup_packet(struct debug_info_iterator
*debug_it
,
778 struct bt_ctf_packet
*packet
,
779 struct debug_info_trace
*di_trace
)
781 return (struct bt_ctf_packet
*) g_hash_table_lookup(
782 di_trace
->packet_map
,
787 struct bt_ctf_packet
*insert_new_packet(struct debug_info_iterator
*debug_it
,
788 struct bt_ctf_packet
*packet
,
789 struct bt_ctf_stream
*writer_stream
,
790 struct debug_info_trace
*di_trace
)
792 struct bt_ctf_packet
*writer_packet
;
795 writer_packet
= bt_ctf_packet_create(writer_stream
);
796 if (!writer_packet
) {
797 BT_LOGE_STR("Failed to create new packet.");
801 ret
= ctf_packet_copy_header(debug_it
->err
, packet
, writer_packet
);
803 BT_LOGE_STR("Failed to copy packet header.");
807 g_hash_table_insert(di_trace
->packet_map
, (gpointer
) packet
,
812 BT_PUT(writer_packet
);
814 return writer_packet
;
818 int add_debug_info_fields(FILE *err
,
819 struct bt_ctf_field_type
*writer_event_context_type
,
820 struct debug_info_component
*component
)
822 struct bt_ctf_field_type
*ip_field
= NULL
, *debug_field_type
= NULL
,
823 *bin_field_type
= NULL
, *func_field_type
= NULL
,
824 *src_field_type
= NULL
;
827 ip_field
= bt_ctf_field_type_structure_get_field_type_by_name(
828 writer_event_context_type
, "_ip");
829 /* No ip field, so no debug info. */
835 debug_field_type
= bt_ctf_field_type_structure_get_field_type_by_name(
836 writer_event_context_type
,
837 component
->arg_debug_info_field_name
);
838 /* Already existing debug_info field, no need to add it. */
839 if (debug_field_type
) {
843 debug_field_type
= bt_ctf_field_type_structure_create();
844 if (!debug_field_type
) {
845 BT_LOGE_STR("Failed to create debug_info structure.");
849 bin_field_type
= bt_ctf_field_type_string_create();
850 if (!bin_field_type
) {
851 BT_LOGE_STR("Failed to create string for field=bin.");
855 func_field_type
= bt_ctf_field_type_string_create();
856 if (!func_field_type
) {
857 BT_LOGE_STR("Failed to create string for field=func.");
861 src_field_type
= bt_ctf_field_type_string_create();
862 if (!src_field_type
) {
863 BT_LOGE_STR("Failed to create string for field=src.");
867 ret
= bt_ctf_field_type_structure_add_field(debug_field_type
,
868 bin_field_type
, "bin");
870 BT_LOGE_STR("Failed to add a field to debug_info struct: field=bin.");
874 ret
= bt_ctf_field_type_structure_add_field(debug_field_type
,
875 func_field_type
, "func");
877 BT_LOGE_STR("Failed to add a field to debug_info struct: field=func.");
881 ret
= bt_ctf_field_type_structure_add_field(debug_field_type
,
882 src_field_type
, "src");
884 BT_LOGE_STR("Failed to add a field to debug_info struct: field=src.");
888 ret
= bt_ctf_field_type_structure_add_field(writer_event_context_type
,
889 debug_field_type
, component
->arg_debug_info_field_name
);
891 BT_LOGE_STR("Failed to add debug_info field to event_context.");
899 BT_PUT(debug_field_type
);
902 bt_put(src_field_type
);
903 bt_put(func_field_type
);
904 bt_put(bin_field_type
);
905 bt_put(debug_field_type
);
910 int create_debug_info_event_context_type(FILE *err
,
911 struct bt_ctf_field_type
*event_context_type
,
912 struct bt_ctf_field_type
*writer_event_context_type
,
913 struct debug_info_component
*component
)
915 int ret
, nr_fields
, i
;
917 nr_fields
= bt_ctf_field_type_structure_get_field_count(event_context_type
);
918 for (i
= 0; i
< nr_fields
; i
++) {
919 struct bt_ctf_field_type
*field_type
= NULL
;
920 const char *field_name
;
922 if (bt_ctf_field_type_structure_get_field(event_context_type
,
923 &field_name
, &field_type
, i
) < 0) {
924 BT_LOGE("Failed to get a field from the event-context: field-name=\"%s\"",
929 ret
= bt_ctf_field_type_structure_add_field(writer_event_context_type
,
930 field_type
, field_name
);
933 BT_LOGE("Failed to add a field to the event-context: field-name=\"%s\"",
939 ret
= add_debug_info_fields(err
, writer_event_context_type
,
950 struct bt_ctf_stream_class
*copy_stream_class_debug_info(FILE *err
,
951 struct bt_ctf_stream_class
*stream_class
,
952 struct bt_ctf_trace
*writer_trace
,
953 struct debug_info_component
*component
)
955 struct bt_ctf_field_type
*type
= NULL
;
956 struct bt_ctf_stream_class
*writer_stream_class
= NULL
;
957 struct bt_ctf_field_type
*writer_event_context_type
= NULL
;
959 const char *name
= bt_ctf_stream_class_get_name(stream_class
);
961 writer_stream_class
= bt_ctf_stream_class_create_empty(name
);
962 if (!writer_stream_class
) {
963 BT_LOGE_STR("Failed to create empty stream class.");
967 type
= bt_ctf_stream_class_get_packet_context_type(stream_class
);
969 ret_int
= bt_ctf_stream_class_set_packet_context_type(
970 writer_stream_class
, type
);
972 BT_LOGE_STR("Failed to set packet_context type.");
978 type
= bt_ctf_stream_class_get_event_header_type(stream_class
);
980 ret_int
= bt_ctf_stream_class_set_event_header_type(
981 writer_stream_class
, type
);
983 BT_LOGE_STR("Failed to set event_header type.");
989 type
= bt_ctf_stream_class_get_event_context_type(stream_class
);
991 writer_event_context_type
= bt_ctf_field_type_structure_create();
992 if (!writer_event_context_type
) {
993 BT_LOGE_STR("Failed to create writer_event_context struct type.");
996 ret_int
= create_debug_info_event_context_type(err
, type
,
997 writer_event_context_type
, component
);
999 BT_LOGE_STR("Failed to create debug_info event_context type.");
1004 ret_int
= bt_ctf_stream_class_set_event_context_type(
1005 writer_stream_class
, writer_event_context_type
);
1007 BT_LOGE_STR("Failed to set event_context type.");
1010 BT_PUT(writer_event_context_type
);
1016 BT_PUT(writer_stream_class
);
1018 bt_put(writer_event_context_type
);
1020 return writer_stream_class
;
1024 * Add the original clock classes to the new trace, we do not need to copy
1025 * them, and if we did, we would have to manually inspect the stream class
1026 * to update the integers mapping to a clock.
1029 int add_clock_classes(FILE *err
, struct bt_ctf_trace
*writer_trace
,
1030 struct bt_ctf_stream_class
*writer_stream_class
,
1031 struct bt_ctf_trace
*trace
)
1033 int ret
, clock_class_count
, i
;
1035 clock_class_count
= bt_ctf_trace_get_clock_class_count(trace
);
1037 for (i
= 0; i
< clock_class_count
; i
++) {
1038 struct bt_ctf_clock_class
*clock_class
=
1039 bt_ctf_trace_get_clock_class_by_index(trace
, i
);
1040 struct bt_ctf_clock_class
*existing_clock_class
= NULL
;
1042 assert(clock_class
);
1044 existing_clock_class
= bt_ctf_trace_get_clock_class_by_name(
1045 writer_trace
, bt_ctf_clock_class_get_name(clock_class
));
1046 bt_put(existing_clock_class
);
1047 if (existing_clock_class
) {
1048 bt_put(clock_class
);
1052 ret
= bt_ctf_trace_add_clock_class(writer_trace
, clock_class
);
1053 BT_PUT(clock_class
);
1055 BT_LOGE_STR("Failed to add clock_class.");
1071 struct bt_ctf_stream_class
*insert_new_stream_class(
1072 struct debug_info_iterator
*debug_it
,
1073 struct bt_ctf_stream_class
*stream_class
)
1075 struct bt_ctf_stream_class
*writer_stream_class
= NULL
;
1076 struct bt_ctf_trace
*trace
, *writer_trace
= NULL
;
1077 struct debug_info_trace
*di_trace
;
1078 enum bt_component_status ret
;
1081 trace
= bt_ctf_stream_class_get_trace(stream_class
);
1084 di_trace
= lookup_trace(debug_it
, trace
);
1086 BT_LOGE_STR("Failed to find existing trace.");
1087 ret
= BT_COMPONENT_STATUS_ERROR
;
1090 writer_trace
= di_trace
->writer_trace
;
1091 bt_get(writer_trace
);
1093 writer_stream_class
= copy_stream_class_debug_info(debug_it
->err
, stream_class
,
1094 writer_trace
, debug_it
->debug_info_component
);
1095 if (!writer_stream_class
) {
1096 BT_LOGE_STR("Failed to copy stream class.");
1100 int_ret
= bt_ctf_trace_add_stream_class(writer_trace
, writer_stream_class
);
1102 BT_LOGE_STR("Failed to add stream class.");
1106 ret
= add_clock_classes(debug_it
->err
, writer_trace
,
1107 writer_stream_class
, trace
);
1108 if (ret
!= BT_COMPONENT_STATUS_OK
) {
1109 BT_LOGE_STR("Failed to add clock classes.");
1113 g_hash_table_insert(di_trace
->stream_class_map
,
1114 (gpointer
) stream_class
, writer_stream_class
);
1119 BT_PUT(writer_stream_class
);
1122 bt_put(writer_trace
);
1123 return writer_stream_class
;
1127 struct bt_ctf_stream
*insert_new_stream(
1128 struct debug_info_iterator
*debug_it
,
1129 struct bt_ctf_stream
*stream
,
1130 struct debug_info_trace
*di_trace
)
1132 struct bt_ctf_stream
*writer_stream
= NULL
;
1133 struct bt_ctf_stream_class
*stream_class
= NULL
;
1134 struct bt_ctf_stream_class
*writer_stream_class
= NULL
;
1137 stream_class
= bt_ctf_stream_get_class(stream
);
1138 assert(stream_class
);
1140 writer_stream_class
= g_hash_table_lookup(
1141 di_trace
->stream_class_map
,
1142 (gpointer
) stream_class
);
1144 if (!writer_stream_class
) {
1145 writer_stream_class
= insert_new_stream_class(debug_it
,
1147 if (!writer_stream_class
) {
1148 BT_LOGE_STR("Failed to insert new stream class.");
1152 bt_get(writer_stream_class
);
1154 id
= bt_ctf_stream_get_id(stream
);
1156 writer_stream
= bt_ctf_stream_create(writer_stream_class
,
1157 bt_ctf_stream_get_name(stream
));
1159 writer_stream
= bt_ctf_stream_create_with_id(
1160 writer_stream_class
,
1161 bt_ctf_stream_get_name(stream
), id
);
1164 if (!writer_stream
) {
1165 BT_LOGE_STR("Failed to create writer_stream.");
1169 g_hash_table_insert(di_trace
->stream_map
, (gpointer
) stream
,
1175 BT_PUT(writer_stream
);
1177 bt_put(stream_class
);
1178 bt_put(writer_stream_class
);
1179 return writer_stream
;
1183 struct bt_ctf_stream
*lookup_stream(struct debug_info_iterator
*debug_it
,
1184 struct bt_ctf_stream
*stream
,
1185 struct debug_info_trace
*di_trace
)
1187 return (struct bt_ctf_stream
*) g_hash_table_lookup(
1188 di_trace
->stream_map
, (gpointer
) stream
);
1192 struct bt_ctf_event_class
*get_event_class(struct debug_info_iterator
*debug_it
,
1193 struct bt_ctf_stream_class
*writer_stream_class
,
1194 struct bt_ctf_event_class
*event_class
)
1196 return bt_ctf_stream_class_get_event_class_by_id(writer_stream_class
,
1197 bt_ctf_event_class_get_id(event_class
));
1201 struct debug_info_trace
*lookup_di_trace_from_stream(
1202 struct debug_info_iterator
*debug_it
,
1203 struct bt_ctf_stream
*stream
)
1205 struct bt_ctf_stream_class
*stream_class
= NULL
;
1206 struct bt_ctf_trace
*trace
= NULL
;
1207 struct debug_info_trace
*di_trace
= NULL
;
1209 stream_class
= bt_ctf_stream_get_class(stream
);
1210 assert(stream_class
);
1212 trace
= bt_ctf_stream_class_get_trace(stream_class
);
1215 di_trace
= (struct debug_info_trace
*) g_hash_table_lookup(
1216 debug_it
->trace_map
, (gpointer
) trace
);
1218 BT_PUT(stream_class
);
1224 struct bt_ctf_stream
*get_writer_stream(
1225 struct debug_info_iterator
*debug_it
,
1226 struct bt_ctf_packet
*packet
, struct bt_ctf_stream
*stream
)
1228 struct bt_ctf_stream_class
*stream_class
= NULL
;
1229 struct bt_ctf_stream
*writer_stream
= NULL
;
1230 struct debug_info_trace
*di_trace
= NULL
;
1232 stream_class
= bt_ctf_stream_get_class(stream
);
1233 assert(stream_class
);
1235 di_trace
= lookup_di_trace_from_stream(debug_it
, stream
);
1237 BT_LOGE_STR("Failed to find existing trace from stream.");
1241 writer_stream
= lookup_stream(debug_it
, stream
, di_trace
);
1242 if (!writer_stream
) {
1243 BT_LOGE_STR("Failed to find existing stream.");
1246 bt_get(writer_stream
);
1251 BT_PUT(writer_stream
);
1253 bt_put(stream_class
);
1254 return writer_stream
;
1258 struct bt_ctf_packet
*debug_info_new_packet(
1259 struct debug_info_iterator
*debug_it
,
1260 struct bt_ctf_packet
*packet
)
1262 struct bt_ctf_stream
*stream
= NULL
, *writer_stream
= NULL
;
1263 struct bt_ctf_packet
*writer_packet
= NULL
;
1264 struct bt_ctf_field
*packet_context
= NULL
;
1265 struct debug_info_trace
*di_trace
;
1268 stream
= bt_ctf_packet_get_stream(packet
);
1271 writer_stream
= get_writer_stream(debug_it
, packet
, stream
);
1272 if (!writer_stream
) {
1273 BT_LOGE_STR("Failed to get writer stream.");
1277 di_trace
= lookup_di_trace_from_stream(debug_it
, stream
);
1279 BT_LOGE_STR("Failed to find existing trace from stream.");
1284 * If a packet was already opened, close it and remove it from
1287 writer_packet
= lookup_packet(debug_it
, packet
, di_trace
);
1288 if (writer_packet
) {
1289 g_hash_table_remove(di_trace
->packet_map
, packet
);
1290 BT_PUT(writer_packet
);
1293 writer_packet
= insert_new_packet(debug_it
, packet
, writer_stream
,
1295 if (!writer_packet
) {
1296 BT_LOGE_STR("Failed to insert new packet.");
1300 packet_context
= bt_ctf_packet_get_context(packet
);
1301 if (packet_context
) {
1302 int_ret
= ctf_packet_copy_context(debug_it
->err
,
1303 packet
, writer_stream
, writer_packet
);
1305 BT_LOGE_STR("Failed to copy packet context.");
1308 BT_PUT(packet_context
);
1311 bt_get(writer_packet
);
1317 bt_put(packet_context
);
1318 bt_put(writer_stream
);
1320 return writer_packet
;
1324 struct bt_ctf_packet
*debug_info_close_packet(
1325 struct debug_info_iterator
*debug_it
,
1326 struct bt_ctf_packet
*packet
)
1328 struct bt_ctf_packet
*writer_packet
= NULL
;
1329 struct bt_ctf_stream
*stream
= NULL
;
1330 struct debug_info_trace
*di_trace
;
1332 stream
= bt_ctf_packet_get_stream(packet
);
1335 di_trace
= lookup_di_trace_from_stream(debug_it
, stream
);
1337 BT_LOGE_STR("Failed to find trace from stream.");
1341 writer_packet
= lookup_packet(debug_it
, packet
, di_trace
);
1342 if (!writer_packet
) {
1343 BT_LOGE_STR("Failed to find existing packet.");
1346 bt_get(writer_packet
);
1347 g_hash_table_remove(di_trace
->packet_map
, packet
);
1351 return writer_packet
;
1355 struct bt_ctf_stream
*debug_info_stream_begin(
1356 struct debug_info_iterator
*debug_it
,
1357 struct bt_ctf_stream
*stream
)
1359 struct bt_ctf_stream
*writer_stream
= NULL
;
1360 enum debug_info_stream_state
*state
;
1361 struct debug_info_trace
*di_trace
= NULL
;
1363 di_trace
= lookup_di_trace_from_stream(debug_it
, stream
);
1365 di_trace
= insert_new_trace(debug_it
, stream
);
1367 BT_LOGE_STR("Failed to insert new trace.");
1372 /* Set the stream as active */
1373 state
= g_hash_table_lookup(di_trace
->stream_states
, stream
);
1375 if (di_trace
->trace_static
) {
1376 BT_LOGE_STR("Failed to add a new stream, trace is static.");
1379 state
= insert_new_stream_state(debug_it
, di_trace
,
1382 BT_LOGE_STR("Failed to add new stream state.");
1386 if (*state
!= DEBUG_INFO_UNKNOWN_STREAM
) {
1387 BT_LOGE("Unexpected stream state: state=%d", *state
);
1390 *state
= DEBUG_INFO_ACTIVE_STREAM
;
1392 writer_stream
= lookup_stream(debug_it
, stream
, di_trace
);
1393 if (!writer_stream
) {
1394 writer_stream
= insert_new_stream(debug_it
, stream
, di_trace
);
1396 bt_get(writer_stream
);
1401 BT_PUT(writer_stream
);
1403 return writer_stream
;
1407 struct bt_ctf_stream
*debug_info_stream_end(struct debug_info_iterator
*debug_it
,
1408 struct bt_ctf_stream
*stream
)
1410 struct bt_ctf_stream
*writer_stream
= NULL
;
1411 struct debug_info_trace
*di_trace
= NULL
;
1412 enum debug_info_stream_state
*state
;
1414 di_trace
= lookup_di_trace_from_stream(debug_it
, stream
);
1416 BT_LOGE_STR("Failed to find existing trace from stream.");
1420 writer_stream
= lookup_stream(debug_it
, stream
, di_trace
);
1421 if (!writer_stream
) {
1422 BT_LOGE_STR("Failed to find existing stream.");
1426 * Take the ref on the stream and keep it until the notification
1429 bt_get(writer_stream
);
1431 state
= g_hash_table_lookup(di_trace
->stream_states
, stream
);
1432 if (*state
!= DEBUG_INFO_ACTIVE_STREAM
) {
1433 BT_LOGE("Unexpected stream state: state=%d", *state
);
1436 *state
= DEBUG_INFO_COMPLETED_STREAM
;
1438 g_hash_table_remove(di_trace
->stream_map
, stream
);
1440 if (di_trace
->trace_static
) {
1441 int trace_completed
= 1;
1443 g_hash_table_foreach(di_trace
->stream_states
,
1444 check_completed_trace
, &trace_completed
);
1445 if (trace_completed
) {
1446 debug_info_close_trace(debug_it
, di_trace
);
1447 g_hash_table_remove(debug_it
->trace_map
,
1455 BT_PUT(writer_stream
);
1458 return writer_stream
;
1462 struct debug_info_source
*lookup_debug_info(FILE *err
,
1463 struct bt_ctf_event
*event
,
1464 struct debug_info
*debug_info
)
1468 struct debug_info_source
*dbg_info_src
= NULL
;
1471 ret
= get_stream_event_context_int_field_value(err
, event
,
1477 ret
= get_stream_event_context_unsigned_int_field_value(err
, event
,
1483 /* Get debug info for this context. */
1484 dbg_info_src
= debug_info_query(debug_info
, vpid
, ip
);
1487 return dbg_info_src
;
1491 int set_debug_info_field(FILE *err
, struct bt_ctf_field
*debug_field
,
1492 struct debug_info_source
*dbg_info_src
,
1493 struct debug_info_component
*component
)
1495 int i
, nr_fields
, ret
= 0;
1496 struct bt_ctf_field_type
*debug_field_type
= NULL
;
1497 struct bt_ctf_field
*field
= NULL
;
1498 struct bt_ctf_field_type
*field_type
= NULL
;
1500 debug_field_type
= bt_ctf_field_get_type(debug_field
);
1501 assert(debug_field_type
);
1503 nr_fields
= bt_ctf_field_type_structure_get_field_count(debug_field_type
);
1504 for (i
= 0; i
< nr_fields
; i
++) {
1505 const char *field_name
;
1507 if (bt_ctf_field_type_structure_get_field(debug_field_type
,
1508 &field_name
, &field_type
, i
) < 0) {
1509 BT_LOGE("Failed to get field from debug_info struct: field-name=\"%s\"",
1515 field
= bt_ctf_field_structure_get_field_by_index(debug_field
, i
);
1516 if (!strcmp(field_name
, "bin")) {
1517 if (dbg_info_src
&& dbg_info_src
->bin_path
) {
1518 GString
*tmp
= g_string_new(NULL
);
1520 if (component
->arg_full_path
) {
1521 g_string_printf(tmp
, "%s%s",
1522 dbg_info_src
->bin_path
,
1523 dbg_info_src
->bin_loc
);
1525 g_string_printf(tmp
, "%s%s",
1526 dbg_info_src
->short_bin_path
,
1527 dbg_info_src
->bin_loc
);
1529 ret
= bt_ctf_field_string_set_value(field
, tmp
->str
);
1530 g_string_free(tmp
, true);
1532 ret
= bt_ctf_field_string_set_value(field
, "");
1534 } else if (!strcmp(field_name
, "func")) {
1535 if (dbg_info_src
&& dbg_info_src
->func
) {
1536 ret
= bt_ctf_field_string_set_value(field
,
1537 dbg_info_src
->func
);
1539 ret
= bt_ctf_field_string_set_value(field
, "");
1541 } else if (!strcmp(field_name
, "src")) {
1542 if (dbg_info_src
&& dbg_info_src
->src_path
) {
1543 GString
*tmp
= g_string_new(NULL
);
1545 if (component
->arg_full_path
) {
1546 g_string_printf(tmp
, "%s:%" PRId64
,
1547 dbg_info_src
->src_path
,
1548 dbg_info_src
->line_no
);
1550 g_string_printf(tmp
, "%s:%" PRId64
,
1551 dbg_info_src
->short_src_path
,
1552 dbg_info_src
->line_no
);
1554 ret
= bt_ctf_field_string_set_value(field
, tmp
->str
);
1555 g_string_free(tmp
, true);
1557 ret
= bt_ctf_field_string_set_value(field
, "");
1562 BT_LOGE("Failed to set value in debug-info struct: field-name=\"%s\"",
1575 bt_put(debug_field_type
);
1580 int copy_set_debug_info_stream_event_context(FILE *err
,
1581 struct bt_ctf_field
*event_context
,
1582 struct bt_ctf_event
*event
,
1583 struct bt_ctf_event
*writer_event
,
1584 struct debug_info
*debug_info
,
1585 struct debug_info_component
*component
)
1587 struct bt_ctf_field_type
*writer_event_context_type
= NULL
,
1588 *event_context_type
= NULL
;
1589 struct bt_ctf_field
*writer_event_context
= NULL
;
1590 struct bt_ctf_field
*field
= NULL
, *copy_field
= NULL
, *debug_field
= NULL
;
1591 struct bt_ctf_field_type
*field_type
= NULL
;
1592 struct debug_info_source
*dbg_info_src
;
1593 int ret
, nr_fields
, i
;
1595 writer_event_context
= bt_ctf_event_get_stream_event_context(writer_event
);
1596 assert(writer_event_context
);
1598 writer_event_context_type
= bt_ctf_field_get_type(writer_event_context
);
1599 assert(writer_event_context_type
);
1601 event_context_type
= bt_ctf_field_get_type(event_context
);
1602 assert(event_context_type
);
1605 * If it is not a structure, we did not modify it to add the debug info
1606 * fields, so just assign it as is.
1608 if (bt_ctf_field_type_get_type_id(writer_event_context_type
) != BT_CTF_FIELD_TYPE_ID_STRUCT
) {
1609 ret
= bt_ctf_event_set_event_context(writer_event
, event_context
);
1613 dbg_info_src
= lookup_debug_info(err
, event
, debug_info
);
1615 nr_fields
= bt_ctf_field_type_structure_get_field_count(writer_event_context_type
);
1616 for (i
= 0; i
< nr_fields
; i
++) {
1617 const char *field_name
;
1619 if (bt_ctf_field_type_structure_get_field(writer_event_context_type
,
1620 &field_name
, &field_type
, i
) < 0) {
1621 BT_LOGE("Failed to get field from event-context: field-name=\"%s\"",
1627 * Prevent illegal access in the event_context.
1629 if (i
< bt_ctf_field_type_structure_get_field_count(event_context_type
)) {
1630 field
= bt_ctf_field_structure_get_field_by_index(event_context
, i
);
1633 * The debug_info field, only exists in the writer event or
1634 * if it was set by a earlier pass of the debug_info plugin.
1636 if (!strcmp(field_name
, component
->arg_debug_info_field_name
) &&
1638 debug_field
= bt_ctf_field_structure_get_field_by_index(
1639 writer_event_context
, i
);
1640 assert(debug_field
);
1642 ret
= set_debug_info_field(err
, debug_field
,
1643 dbg_info_src
, component
);
1645 BT_LOGE_STR("Failed to set debug_info field.");
1648 BT_PUT(debug_field
);
1650 copy_field
= bt_ctf_field_copy(field
);
1652 BT_LOGE("Failed to copy field: field-name=\"%s\"",
1657 ret
= bt_ctf_field_structure_set_field_by_name(
1658 writer_event_context
,
1659 field_name
, copy_field
);
1661 BT_LOGE("Failed to set field: field-name=\"%s\"",
1677 bt_put(event_context_type
);
1678 bt_put(writer_event_context_type
);
1679 bt_put(writer_event_context
);
1682 bt_put(debug_field
);
1688 struct bt_ctf_clock_class
*stream_class_get_clock_class(FILE *err
,
1689 struct bt_ctf_stream_class
*stream_class
)
1691 struct bt_ctf_trace
*trace
= NULL
;
1692 struct bt_ctf_clock_class
*clock_class
= NULL
;
1694 trace
= bt_ctf_stream_class_get_trace(stream_class
);
1697 if (!bt_ctf_trace_get_clock_class_count(trace
)) {
1702 /* FIXME multi-clock? */
1703 clock_class
= bt_ctf_trace_get_clock_class_by_index(trace
, 0);
1712 struct bt_ctf_clock_class
*event_get_clock_class(FILE *err
, struct bt_ctf_event
*event
)
1714 struct bt_ctf_event_class
*event_class
= NULL
;
1715 struct bt_ctf_stream_class
*stream_class
= NULL
;
1716 struct bt_ctf_clock_class
*clock_class
= NULL
;
1718 event_class
= bt_ctf_event_get_class(event
);
1719 assert(event_class
);
1721 stream_class
= bt_ctf_event_class_get_stream_class(event_class
);
1722 assert(stream_class
);
1724 clock_class
= stream_class_get_clock_class(err
, stream_class
);
1728 bt_put(stream_class
);
1729 bt_put(event_class
);
1734 int set_event_clock_value(FILE *err
, struct bt_ctf_event
*event
,
1735 struct bt_ctf_event
*writer_event
)
1737 struct bt_ctf_clock_class
*clock_class
= NULL
;
1738 struct bt_ctf_clock_value
*clock_value
= NULL
;
1741 clock_class
= event_get_clock_class(err
, event
);
1743 /* No clock on input trace. */
1747 clock_value
= bt_ctf_event_get_clock_value(event
, clock_class
);
1754 * We share the same clocks, so we can assign the clock value to the
1757 ret
= bt_ctf_event_set_clock_value(writer_event
, clock_value
);
1759 BT_LOGE_STR("Failed to set clock value.");
1769 bt_put(clock_class
);
1770 bt_put(clock_value
);
1775 struct bt_ctf_event
*debug_info_copy_event(FILE *err
, struct bt_ctf_event
*event
,
1776 struct bt_ctf_event_class
*writer_event_class
,
1777 struct debug_info
*debug_info
,
1778 struct debug_info_component
*component
)
1780 struct bt_ctf_event
*writer_event
= NULL
;
1781 struct bt_ctf_field
*field
= NULL
, *copy_field
= NULL
;
1784 writer_event
= bt_ctf_event_create(writer_event_class
);
1785 if (!writer_event
) {
1786 BT_LOGE_STR("Failed to create new event.");
1790 ret
= set_event_clock_value(err
, event
, writer_event
);
1792 BT_LOGE_STR("Failed to set clock value.");
1796 /* Optional field, so it can fail silently. */
1797 field
= bt_ctf_event_get_header(event
);
1799 ret
= ctf_copy_event_header(err
, event
, writer_event_class
,
1800 writer_event
, field
);
1802 BT_LOGE_STR("Failed to copy event header.");
1808 /* Optional field, so it can fail silently. */
1809 field
= bt_ctf_event_get_stream_event_context(event
);
1811 ret
= copy_set_debug_info_stream_event_context(err
,
1812 field
, event
, writer_event
, debug_info
,
1815 BT_LOGE_STR("Failed to debug_info stream event context.");
1821 /* Optional field, so it can fail silently. */
1822 field
= bt_ctf_event_get_event_context(event
);
1824 copy_field
= bt_ctf_field_copy(field
);
1826 BT_LOGE_STR("Failed to copy field.");
1829 ret
= bt_ctf_event_set_event_context(writer_event
, copy_field
);
1831 BT_LOGE_STR("Failed to set event_context.");
1838 field
= bt_ctf_event_get_event_payload(event
);
1841 copy_field
= bt_ctf_field_copy(field
);
1843 ret
= bt_ctf_event_set_event_payload(writer_event
, copy_field
);
1845 BT_LOGE_STR("Failed to set event payload.");
1855 BT_PUT(writer_event
);
1859 return writer_event
;
1863 struct bt_ctf_event
*debug_info_output_event(
1864 struct debug_info_iterator
*debug_it
,
1865 struct bt_ctf_event
*event
)
1867 struct bt_ctf_event_class
*event_class
= NULL
, *writer_event_class
= NULL
;
1868 struct bt_ctf_stream_class
*stream_class
= NULL
, *writer_stream_class
= NULL
;
1869 struct bt_ctf_event
*writer_event
= NULL
;
1870 struct bt_ctf_packet
*packet
= NULL
, *writer_packet
= NULL
;
1871 struct bt_ctf_trace
*writer_trace
= NULL
;
1872 struct bt_ctf_stream
*stream
= NULL
;
1873 struct debug_info_trace
*di_trace
;
1874 struct debug_info
*debug_info
;
1877 event_class
= bt_ctf_event_get_class(event
);
1878 assert(event_class
);
1880 stream_class
= bt_ctf_event_class_get_stream_class(event_class
);
1881 assert(stream_class
);
1883 stream
= bt_ctf_event_get_stream(event
);
1886 di_trace
= lookup_di_trace_from_stream(debug_it
, stream
);
1888 BT_LOGE_STR("Failed to find existing trace from stream.");
1892 writer_stream_class
= g_hash_table_lookup(
1893 di_trace
->stream_class_map
,
1894 (gpointer
) stream_class
);
1895 if (!writer_stream_class
) {
1896 BT_LOGE_STR("Failed to find existing stream_class.");
1899 bt_get(writer_stream_class
);
1901 writer_event_class
= get_event_class(debug_it
,
1902 writer_stream_class
, event_class
);
1903 if (!writer_event_class
) {
1904 writer_event_class
= ctf_copy_event_class(debug_it
->err
,
1906 if (!writer_event_class
) {
1907 BT_LOGE_STR("Failed to copy event_class.");
1910 int_ret
= bt_ctf_stream_class_add_event_class(
1911 writer_stream_class
, writer_event_class
);
1913 BT_LOGE_STR("Failed to add event_class.");
1918 writer_trace
= bt_ctf_stream_class_get_trace(writer_stream_class
);
1919 assert(writer_trace
);
1921 debug_info
= get_trace_debug_info(debug_it
, writer_trace
, di_trace
);
1923 debug_info_handle_event(debug_it
->err
, event
, debug_info
);
1926 writer_event
= debug_info_copy_event(debug_it
->err
, event
,
1927 writer_event_class
, debug_info
,
1928 debug_it
->debug_info_component
);
1929 if (!writer_event
) {
1930 BT_LOGE("Failed to copy event: event-class-name=\"%s\"",
1931 bt_ctf_event_class_get_name(writer_event_class
));
1935 packet
= bt_ctf_event_get_packet(event
);
1938 writer_packet
= lookup_packet(debug_it
, packet
, di_trace
);
1939 if (!writer_packet
) {
1940 BT_LOGE_STR("Failed to find existing packet.");
1943 bt_get(writer_packet
);
1945 int_ret
= bt_ctf_event_set_packet(writer_event
, writer_packet
);
1947 BT_LOGE("Failed to append event to event-class-name=\"%s\"",
1948 bt_ctf_event_class_get_name(writer_event_class
));
1952 /* Keep the reference on the writer event */
1956 BT_PUT(writer_event
);
1960 bt_put(writer_trace
);
1961 bt_put(writer_packet
);
1963 bt_put(writer_event_class
);
1964 bt_put(writer_stream_class
);
1965 bt_put(stream_class
);
1966 bt_put(event_class
);
1967 return writer_event
;