lib: decouple variant FC option names from selector FC mapping names
[babeltrace.git] / src / plugins / ctf / common / metadata / ctf-meta.h
1 #ifndef _CTF_META_H
2 #define _CTF_META_H
3
4 /*
5 * Copyright 2018 - Philippe Proulx <pproulx@efficios.com>
6 *
7 * Permission is hereby granted, free of charge, to any person obtaining a copy
8 * of this software and associated documentation files (the "Software"), to deal
9 * in the Software without restriction, including without limitation the rights
10 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11 * copies of the Software, and to permit persons to whom the Software is
12 * furnished to do so, subject to the following conditions:
13 *
14 * The above copyright notice and this permission notice shall be included in
15 * all copies or substantial portions of the Software.
16 */
17
18 #include <babeltrace2/babeltrace.h>
19 #include "common/common.h"
20 #include "common/uuid.h"
21 #include "common/assert.h"
22 #include <glib.h>
23 #include <stdint.h>
24 #include <string.h>
25
26 enum ctf_field_class_type {
27 CTF_FIELD_CLASS_TYPE_INT,
28 CTF_FIELD_CLASS_TYPE_ENUM,
29 CTF_FIELD_CLASS_TYPE_FLOAT,
30 CTF_FIELD_CLASS_TYPE_STRING,
31 CTF_FIELD_CLASS_TYPE_STRUCT,
32 CTF_FIELD_CLASS_TYPE_ARRAY,
33 CTF_FIELD_CLASS_TYPE_SEQUENCE,
34 CTF_FIELD_CLASS_TYPE_VARIANT,
35 };
36
37 enum ctf_field_class_meaning {
38 CTF_FIELD_CLASS_MEANING_NONE,
39 CTF_FIELD_CLASS_MEANING_PACKET_BEGINNING_TIME,
40 CTF_FIELD_CLASS_MEANING_PACKET_END_TIME,
41 CTF_FIELD_CLASS_MEANING_EVENT_CLASS_ID,
42 CTF_FIELD_CLASS_MEANING_STREAM_CLASS_ID,
43 CTF_FIELD_CLASS_MEANING_DATA_STREAM_ID,
44 CTF_FIELD_CLASS_MEANING_MAGIC,
45 CTF_FIELD_CLASS_MEANING_PACKET_COUNTER_SNAPSHOT,
46 CTF_FIELD_CLASS_MEANING_DISC_EV_REC_COUNTER_SNAPSHOT,
47 CTF_FIELD_CLASS_MEANING_EXP_PACKET_TOTAL_SIZE,
48 CTF_FIELD_CLASS_MEANING_EXP_PACKET_CONTENT_SIZE,
49 CTF_FIELD_CLASS_MEANING_UUID,
50 };
51
52 enum ctf_byte_order {
53 CTF_BYTE_ORDER_DEFAULT,
54 CTF_BYTE_ORDER_LITTLE,
55 CTF_BYTE_ORDER_BIG,
56 };
57
58 enum ctf_encoding {
59 CTF_ENCODING_NONE,
60 CTF_ENCODING_UTF8,
61 };
62
63 enum ctf_scope {
64 CTF_SCOPE_PACKET_HEADER,
65 CTF_SCOPE_PACKET_CONTEXT,
66 CTF_SCOPE_EVENT_HEADER,
67 CTF_SCOPE_EVENT_COMMON_CONTEXT,
68 CTF_SCOPE_EVENT_SPECIFIC_CONTEXT,
69 CTF_SCOPE_EVENT_PAYLOAD,
70 };
71
72 struct ctf_clock_class {
73 GString *name;
74 GString *description;
75 uint64_t frequency;
76 uint64_t precision;
77 int64_t offset_seconds;
78 uint64_t offset_cycles;
79 bt_uuid_t uuid;
80 bool has_uuid;
81 bool is_absolute;
82
83 /* Weak, set during translation */
84 bt_clock_class *ir_cc;
85 };
86
87 struct ctf_field_class {
88 enum ctf_field_class_type type;
89 unsigned int alignment;
90 bool is_compound;
91 bool in_ir;
92
93 /* Weak, set during translation. NULL if `in_ir` is false below. */
94 bt_field_class *ir_fc;
95 };
96
97 struct ctf_field_class_bit_array {
98 struct ctf_field_class base;
99 enum ctf_byte_order byte_order;
100 unsigned int size;
101 };
102
103 struct ctf_field_class_int {
104 struct ctf_field_class_bit_array base;
105 enum ctf_field_class_meaning meaning;
106 bool is_signed;
107 bt_field_class_integer_preferred_display_base disp_base;
108 enum ctf_encoding encoding;
109 int64_t storing_index;
110
111 /* Weak */
112 struct ctf_clock_class *mapped_clock_class;
113 };
114
115 struct ctf_range {
116 union {
117 uint64_t u;
118 int64_t i;
119 } lower;
120
121 union {
122 uint64_t u;
123 int64_t i;
124 } upper;
125 };
126
127 struct ctf_field_class_enum_mapping {
128 GString *label;
129
130 /* Array of `struct ctf_range` */
131 GArray *ranges;
132 };
133
134 struct ctf_field_class_enum {
135 struct ctf_field_class_int base;
136
137 /* Array of `struct ctf_field_class_enum_mapping` */
138 GArray *mappings;
139 };
140
141 struct ctf_field_class_float {
142 struct ctf_field_class_bit_array base;
143 };
144
145 struct ctf_field_class_string {
146 struct ctf_field_class base;
147 enum ctf_encoding encoding;
148 };
149
150 struct ctf_named_field_class {
151 /* Original name which can include a leading `_` */
152 GString *orig_name;
153
154 /* Name as translated to trace IR (leading `_` removed) */
155 GString *name;
156
157 /* Owned by this */
158 struct ctf_field_class *fc;
159 };
160
161 struct ctf_field_class_struct {
162 struct ctf_field_class base;
163
164 /* Array of `struct ctf_named_field_class` */
165 GArray *members;
166 };
167
168 struct ctf_field_path {
169 enum ctf_scope root;
170
171 /* Array of `int64_t` */
172 GArray *path;
173 };
174
175 struct ctf_field_class_variant_range {
176 struct ctf_range range;
177 uint64_t option_index;
178 };
179
180 struct ctf_field_class_variant {
181 struct ctf_field_class base;
182 GString *tag_ref;
183 struct ctf_field_path tag_path;
184 uint64_t stored_tag_index;
185
186 /* Array of `struct ctf_named_field_class` */
187 GArray *options;
188
189 /* Array of `struct ctf_field_class_variant_range` */
190 GArray *ranges;
191
192 /* Weak */
193 struct ctf_field_class_enum *tag_fc;
194 };
195
196 struct ctf_field_class_array_base {
197 struct ctf_field_class base;
198 struct ctf_field_class *elem_fc;
199 bool is_text;
200 };
201
202 struct ctf_field_class_array {
203 struct ctf_field_class_array_base base;
204 enum ctf_field_class_meaning meaning;
205 uint64_t length;
206 };
207
208 struct ctf_field_class_sequence {
209 struct ctf_field_class_array_base base;
210 GString *length_ref;
211 struct ctf_field_path length_path;
212 uint64_t stored_length_index;
213
214 /* Weak */
215 struct ctf_field_class_int *length_fc;
216 };
217
218 struct ctf_event_class {
219 GString *name;
220 uint64_t id;
221 GString *emf_uri;
222 bt_event_class_log_level log_level;
223 bool is_translated;
224
225 /* Owned by this */
226 struct ctf_field_class *spec_context_fc;
227
228 /* Owned by this */
229 struct ctf_field_class *payload_fc;
230
231 /* Weak, set during translation */
232 bt_event_class *ir_ec;
233 };
234
235 struct ctf_stream_class {
236 uint64_t id;
237 bool is_translated;
238 bool packets_have_ts_begin;
239 bool packets_have_ts_end;
240 bool has_discarded_events;
241 bool has_discarded_packets;
242 bool discarded_events_have_default_cs;
243 bool discarded_packets_have_default_cs;
244
245 /* Owned by this */
246 struct ctf_field_class *packet_context_fc;
247
248 /* Owned by this */
249 struct ctf_field_class *event_header_fc;
250
251 /* Owned by this */
252 struct ctf_field_class *event_common_context_fc;
253
254 /* Array of `struct ctf_event_class *`, owned by this */
255 GPtrArray *event_classes;
256
257 /*
258 * Hash table mapping event class IDs to `struct ctf_event_class *`,
259 * weak.
260 */
261 GHashTable *event_classes_by_id;
262
263 /* Weak */
264 struct ctf_clock_class *default_clock_class;
265
266 /* Weak, set during translation */
267 bt_stream_class *ir_sc;
268 };
269
270 enum ctf_trace_class_env_entry_type {
271 CTF_TRACE_CLASS_ENV_ENTRY_TYPE_INT,
272 CTF_TRACE_CLASS_ENV_ENTRY_TYPE_STR,
273 };
274
275 struct ctf_trace_class_env_entry {
276 enum ctf_trace_class_env_entry_type type;
277 GString *name;
278
279 struct {
280 int64_t i;
281 GString *str;
282 } value;
283 };
284
285 struct ctf_trace_class {
286 unsigned int major;
287 unsigned int minor;
288 bt_uuid_t uuid;
289 bool is_uuid_set;
290 enum ctf_byte_order default_byte_order;
291
292 /* Owned by this */
293 struct ctf_field_class *packet_header_fc;
294
295 uint64_t stored_value_count;
296
297 /* Array of `struct ctf_clock_class *` (owned by this) */
298 GPtrArray *clock_classes;
299
300 /* Array of `struct ctf_stream_class *` */
301 GPtrArray *stream_classes;
302
303 /* Array of `struct ctf_trace_class_env_entry` */
304 GArray *env_entries;
305
306 bool is_translated;
307
308 /* Weak, set during translation */
309 bt_trace_class *ir_tc;
310 };
311
312 static inline
313 void ctf_field_class_destroy(struct ctf_field_class *fc);
314
315 static inline
316 void _ctf_field_class_init(struct ctf_field_class *fc,
317 enum ctf_field_class_type type, unsigned int alignment)
318 {
319 BT_ASSERT(fc);
320 fc->type = type;
321 fc->alignment = alignment;
322 fc->in_ir = false;
323 }
324
325 static inline
326 void _ctf_field_class_bit_array_init(struct ctf_field_class_bit_array *fc,
327 enum ctf_field_class_type type)
328 {
329 _ctf_field_class_init((void *) fc, type, 1);
330 }
331
332 static inline
333 void _ctf_field_class_int_init(struct ctf_field_class_int *fc,
334 enum ctf_field_class_type type)
335 {
336 _ctf_field_class_bit_array_init((void *) fc, type);
337 fc->meaning = CTF_FIELD_CLASS_MEANING_NONE;
338 fc->storing_index = -1;
339 }
340
341 static inline
342 void ctf_field_path_init(struct ctf_field_path *field_path)
343 {
344 BT_ASSERT(field_path);
345 field_path->path = g_array_new(FALSE, TRUE, sizeof(int64_t));
346 BT_ASSERT(field_path->path);
347 }
348
349 static inline
350 void ctf_field_path_fini(struct ctf_field_path *field_path)
351 {
352 BT_ASSERT(field_path);
353
354 if (field_path->path) {
355 g_array_free(field_path->path, TRUE);
356 }
357 }
358
359 static inline
360 void _ctf_named_field_class_init(struct ctf_named_field_class *named_fc)
361 {
362 BT_ASSERT(named_fc);
363 named_fc->name = g_string_new(NULL);
364 BT_ASSERT(named_fc->name);
365 named_fc->orig_name = g_string_new(NULL);
366 BT_ASSERT(named_fc->orig_name);
367 }
368
369 static inline
370 void _ctf_named_field_class_fini(struct ctf_named_field_class *named_fc)
371 {
372 BT_ASSERT(named_fc);
373
374 if (named_fc->name) {
375 g_string_free(named_fc->name, TRUE);
376 }
377
378 if (named_fc->orig_name) {
379 g_string_free(named_fc->orig_name, TRUE);
380 }
381
382 ctf_field_class_destroy(named_fc->fc);
383 }
384
385 static inline
386 void _ctf_field_class_enum_mapping_init(
387 struct ctf_field_class_enum_mapping *mapping)
388 {
389 BT_ASSERT(mapping);
390 mapping->label = g_string_new(NULL);
391 BT_ASSERT(mapping->label);
392 mapping->ranges = g_array_new(FALSE, TRUE, sizeof(struct ctf_range));
393 BT_ASSERT(mapping->ranges);
394 }
395
396 static inline
397 void _ctf_field_class_enum_mapping_fini(
398 struct ctf_field_class_enum_mapping *mapping)
399 {
400 BT_ASSERT(mapping);
401
402 if (mapping->label) {
403 g_string_free(mapping->label, TRUE);
404 }
405
406 if (mapping->ranges) {
407 g_array_free(mapping->ranges, TRUE);
408 }
409 }
410
411 static inline
412 struct ctf_field_class_int *ctf_field_class_int_create(void)
413 {
414 struct ctf_field_class_int *fc = g_new0(struct ctf_field_class_int, 1);
415
416 BT_ASSERT(fc);
417 _ctf_field_class_int_init(fc, CTF_FIELD_CLASS_TYPE_INT);
418 return fc;
419 }
420
421 static inline
422 struct ctf_field_class_float *ctf_field_class_float_create(void)
423 {
424 struct ctf_field_class_float *fc =
425 g_new0(struct ctf_field_class_float, 1);
426
427 BT_ASSERT(fc);
428 _ctf_field_class_bit_array_init((void *) fc, CTF_FIELD_CLASS_TYPE_FLOAT);
429 return fc;
430 }
431
432 static inline
433 struct ctf_field_class_string *ctf_field_class_string_create(void)
434 {
435 struct ctf_field_class_string *fc =
436 g_new0(struct ctf_field_class_string, 1);
437
438 BT_ASSERT(fc);
439 _ctf_field_class_init((void *) fc, CTF_FIELD_CLASS_TYPE_STRING, 8);
440 return fc;
441 }
442
443 static inline
444 struct ctf_field_class_enum *ctf_field_class_enum_create(void)
445 {
446 struct ctf_field_class_enum *fc = g_new0(struct ctf_field_class_enum, 1);
447
448 BT_ASSERT(fc);
449 _ctf_field_class_int_init((void *) fc, CTF_FIELD_CLASS_TYPE_ENUM);
450 fc->mappings = g_array_new(FALSE, TRUE,
451 sizeof(struct ctf_field_class_enum_mapping));
452 BT_ASSERT(fc->mappings);
453 return fc;
454 }
455
456 static inline
457 struct ctf_field_class_struct *ctf_field_class_struct_create(void)
458 {
459 struct ctf_field_class_struct *fc =
460 g_new0(struct ctf_field_class_struct, 1);
461
462 BT_ASSERT(fc);
463 _ctf_field_class_init((void *) fc, CTF_FIELD_CLASS_TYPE_STRUCT, 1);
464 fc->members = g_array_new(FALSE, TRUE,
465 sizeof(struct ctf_named_field_class));
466 BT_ASSERT(fc->members);
467 fc->base.is_compound = true;
468 return fc;
469 }
470
471 static inline
472 struct ctf_field_class_variant *ctf_field_class_variant_create(void)
473 {
474 struct ctf_field_class_variant *fc =
475 g_new0(struct ctf_field_class_variant, 1);
476
477 BT_ASSERT(fc);
478 _ctf_field_class_init((void *) fc, CTF_FIELD_CLASS_TYPE_VARIANT, 1);
479 fc->options = g_array_new(FALSE, TRUE,
480 sizeof(struct ctf_named_field_class));
481 BT_ASSERT(fc->options);
482 fc->ranges = g_array_new(FALSE, TRUE,
483 sizeof(struct ctf_field_class_variant_range));
484 BT_ASSERT(fc->ranges);
485 fc->tag_ref = g_string_new(NULL);
486 BT_ASSERT(fc->tag_ref);
487 ctf_field_path_init(&fc->tag_path);
488 fc->base.is_compound = true;
489 return fc;
490 }
491
492 static inline
493 struct ctf_field_class_array *ctf_field_class_array_create(void)
494 {
495 struct ctf_field_class_array *fc =
496 g_new0(struct ctf_field_class_array, 1);
497
498 BT_ASSERT(fc);
499 _ctf_field_class_init((void *) fc, CTF_FIELD_CLASS_TYPE_ARRAY, 1);
500 fc->base.base.is_compound = true;
501 return fc;
502 }
503
504 static inline
505 struct ctf_field_class_sequence *ctf_field_class_sequence_create(void)
506 {
507 struct ctf_field_class_sequence *fc =
508 g_new0(struct ctf_field_class_sequence, 1);
509
510 BT_ASSERT(fc);
511 _ctf_field_class_init((void *) fc, CTF_FIELD_CLASS_TYPE_SEQUENCE, 1);
512 fc->length_ref = g_string_new(NULL);
513 BT_ASSERT(fc->length_ref);
514 ctf_field_path_init(&fc->length_path);
515 fc->base.base.is_compound = true;
516 return fc;
517 }
518
519 static inline
520 void _ctf_field_class_int_destroy(struct ctf_field_class_int *fc)
521 {
522 BT_ASSERT(fc);
523 g_free(fc);
524 }
525
526 static inline
527 void _ctf_field_class_enum_destroy(struct ctf_field_class_enum *fc)
528 {
529 BT_ASSERT(fc);
530
531 if (fc->mappings) {
532 uint64_t i;
533
534 for (i = 0; i < fc->mappings->len; i++) {
535 struct ctf_field_class_enum_mapping *mapping =
536 &g_array_index(fc->mappings,
537 struct ctf_field_class_enum_mapping, i);
538
539 _ctf_field_class_enum_mapping_fini(mapping);
540 }
541
542 g_array_free(fc->mappings, TRUE);
543 }
544
545 g_free(fc);
546 }
547
548 static inline
549 void _ctf_field_class_float_destroy(struct ctf_field_class_float *fc)
550 {
551 BT_ASSERT(fc);
552 g_free(fc);
553 }
554
555 static inline
556 void _ctf_field_class_string_destroy(struct ctf_field_class_string *fc)
557 {
558 BT_ASSERT(fc);
559 g_free(fc);
560 }
561
562 static inline
563 void _ctf_field_class_struct_destroy(struct ctf_field_class_struct *fc)
564 {
565 BT_ASSERT(fc);
566
567 if (fc->members) {
568 uint64_t i;
569
570 for (i = 0; i < fc->members->len; i++) {
571 struct ctf_named_field_class *named_fc =
572 &g_array_index(fc->members,
573 struct ctf_named_field_class, i);
574
575 _ctf_named_field_class_fini(named_fc);
576 }
577
578 g_array_free(fc->members, TRUE);
579 }
580
581 g_free(fc);
582 }
583
584 static inline
585 void _ctf_field_class_array_base_fini(struct ctf_field_class_array_base *fc)
586 {
587 BT_ASSERT(fc);
588 ctf_field_class_destroy(fc->elem_fc);
589 }
590
591 static inline
592 void _ctf_field_class_array_destroy(struct ctf_field_class_array *fc)
593 {
594 BT_ASSERT(fc);
595 _ctf_field_class_array_base_fini((void *) fc);
596 g_free(fc);
597 }
598
599 static inline
600 void _ctf_field_class_sequence_destroy(struct ctf_field_class_sequence *fc)
601 {
602 BT_ASSERT(fc);
603 _ctf_field_class_array_base_fini((void *) fc);
604
605 if (fc->length_ref) {
606 g_string_free(fc->length_ref, TRUE);
607 }
608
609 ctf_field_path_fini(&fc->length_path);
610 g_free(fc);
611 }
612
613 static inline
614 void _ctf_field_class_variant_destroy(struct ctf_field_class_variant *fc)
615 {
616 BT_ASSERT(fc);
617
618 if (fc->options) {
619 uint64_t i;
620
621 for (i = 0; i < fc->options->len; i++) {
622 struct ctf_named_field_class *named_fc =
623 &g_array_index(fc->options,
624 struct ctf_named_field_class, i);
625
626 _ctf_named_field_class_fini(named_fc);
627 }
628
629 g_array_free(fc->options, TRUE);
630 }
631
632 if (fc->ranges) {
633 g_array_free(fc->ranges, TRUE);
634 }
635
636 if (fc->tag_ref) {
637 g_string_free(fc->tag_ref, TRUE);
638 }
639
640 ctf_field_path_fini(&fc->tag_path);
641 g_free(fc);
642 }
643
644 static inline
645 void ctf_field_class_destroy(struct ctf_field_class *fc)
646 {
647 if (!fc) {
648 return;
649 }
650
651 switch (fc->type) {
652 case CTF_FIELD_CLASS_TYPE_INT:
653 _ctf_field_class_int_destroy((void *) fc);
654 break;
655 case CTF_FIELD_CLASS_TYPE_ENUM:
656 _ctf_field_class_enum_destroy((void *) fc);
657 break;
658 case CTF_FIELD_CLASS_TYPE_FLOAT:
659 _ctf_field_class_float_destroy((void *) fc);
660 break;
661 case CTF_FIELD_CLASS_TYPE_STRING:
662 _ctf_field_class_string_destroy((void *) fc);
663 break;
664 case CTF_FIELD_CLASS_TYPE_STRUCT:
665 _ctf_field_class_struct_destroy((void *) fc);
666 break;
667 case CTF_FIELD_CLASS_TYPE_ARRAY:
668 _ctf_field_class_array_destroy((void *) fc);
669 break;
670 case CTF_FIELD_CLASS_TYPE_SEQUENCE:
671 _ctf_field_class_sequence_destroy((void *) fc);
672 break;
673 case CTF_FIELD_CLASS_TYPE_VARIANT:
674 _ctf_field_class_variant_destroy((void *) fc);
675 break;
676 default:
677 abort();
678 }
679 }
680
681 static inline
682 struct ctf_range *ctf_field_class_enum_mapping_borrow_range_by_index(
683 struct ctf_field_class_enum_mapping *mapping, uint64_t index)
684 {
685 BT_ASSERT(mapping);
686 BT_ASSERT(index < mapping->ranges->len);
687 return &g_array_index(mapping->ranges, struct ctf_range, index);
688 }
689
690 static inline
691 struct ctf_field_class_enum_mapping *ctf_field_class_enum_borrow_mapping_by_index(
692 struct ctf_field_class_enum *fc, uint64_t index)
693 {
694 BT_ASSERT(fc);
695 BT_ASSERT(index < fc->mappings->len);
696 return &g_array_index(fc->mappings, struct ctf_field_class_enum_mapping,
697 index);
698 }
699
700 static inline
701 struct ctf_field_class_enum_mapping *ctf_field_class_enum_borrow_mapping_by_label(
702 struct ctf_field_class_enum *fc, const char *label)
703 {
704 struct ctf_field_class_enum_mapping *ret_mapping = NULL;
705 uint64_t i;
706
707 BT_ASSERT(fc);
708 BT_ASSERT(label);
709
710 for (i = 0; i < fc->mappings->len; i++) {
711 struct ctf_field_class_enum_mapping *mapping =
712 ctf_field_class_enum_borrow_mapping_by_index(fc, i);
713
714 if (strcmp(mapping->label->str, label) == 0) {
715 ret_mapping = mapping;
716 goto end;
717 }
718 }
719
720 end:
721 return ret_mapping;
722 }
723
724 static inline
725 void ctf_field_class_enum_map_range(struct ctf_field_class_enum *fc,
726 const char *label, uint64_t u_lower, uint64_t u_upper)
727 {
728 struct ctf_field_class_enum_mapping *mapping = NULL;
729 struct ctf_range range = {
730 .lower.u = u_lower,
731 .upper.u = u_upper,
732 };
733 uint64_t i;
734
735 BT_ASSERT(fc);
736 BT_ASSERT(label);
737
738 for (i = 0; i < fc->mappings->len; i++) {
739 mapping = ctf_field_class_enum_borrow_mapping_by_index(
740 fc, i);
741
742 if (strcmp(mapping->label->str, label) == 0) {
743 break;
744 }
745 }
746
747 if (i == fc->mappings->len) {
748 mapping = NULL;
749 }
750
751 if (!mapping) {
752 g_array_set_size(fc->mappings, fc->mappings->len + 1);
753 mapping = ctf_field_class_enum_borrow_mapping_by_index(
754 fc, fc->mappings->len - 1);
755 _ctf_field_class_enum_mapping_init(mapping);
756 g_string_assign(mapping->label, label);
757 }
758
759 g_array_append_val(mapping->ranges, range);
760 }
761
762 static inline
763 struct ctf_named_field_class *ctf_field_class_struct_borrow_member_by_index(
764 struct ctf_field_class_struct *fc, uint64_t index)
765 {
766 BT_ASSERT(fc);
767 BT_ASSERT(index < fc->members->len);
768 return &g_array_index(fc->members, struct ctf_named_field_class,
769 index);
770 }
771
772 static inline
773 struct ctf_named_field_class *ctf_field_class_struct_borrow_member_by_name(
774 struct ctf_field_class_struct *fc, const char *name)
775 {
776 uint64_t i;
777 struct ctf_named_field_class *ret_named_fc = NULL;
778
779 BT_ASSERT(fc);
780 BT_ASSERT(name);
781
782 for (i = 0; i < fc->members->len; i++) {
783 struct ctf_named_field_class *named_fc =
784 ctf_field_class_struct_borrow_member_by_index(fc, i);
785
786 if (strcmp(name, named_fc->name->str) == 0) {
787 ret_named_fc = named_fc;
788 goto end;
789 }
790 }
791
792 end:
793 return ret_named_fc;
794 }
795
796 static inline
797 struct ctf_field_class *ctf_field_class_struct_borrow_member_field_class_by_name(
798 struct ctf_field_class_struct *struct_fc, const char *name)
799 {
800 struct ctf_named_field_class *named_fc = NULL;
801 struct ctf_field_class *fc = NULL;
802
803 if (!struct_fc) {
804 goto end;
805 }
806
807 named_fc = ctf_field_class_struct_borrow_member_by_name(struct_fc, name);
808 if (!named_fc) {
809 goto end;
810 }
811
812 fc = named_fc->fc;
813
814 end:
815 return fc;
816 }
817
818 static inline
819 struct ctf_field_class_int *
820 ctf_field_class_struct_borrow_member_int_field_class_by_name(
821 struct ctf_field_class_struct *struct_fc, const char *name)
822 {
823 struct ctf_field_class_int *int_fc = NULL;
824
825 int_fc = (void *)
826 ctf_field_class_struct_borrow_member_field_class_by_name(
827 struct_fc, name);
828 if (!int_fc) {
829 goto end;
830 }
831
832 if (int_fc->base.base.type != CTF_FIELD_CLASS_TYPE_INT &&
833 int_fc->base.base.type != CTF_FIELD_CLASS_TYPE_ENUM) {
834 int_fc = NULL;
835 goto end;
836 }
837
838 end:
839 return int_fc;
840 }
841
842 static inline
843 void _ctf_named_field_class_unescape_orig_name(
844 struct ctf_named_field_class *named_fc)
845 {
846 const char *name = named_fc->orig_name->str;
847
848 if (name[0] == '_') {
849 name++;
850 }
851
852 g_string_assign(named_fc->name, name);
853 }
854
855 static inline
856 void ctf_field_class_struct_append_member(struct ctf_field_class_struct *fc,
857 const char *orig_name, struct ctf_field_class *member_fc)
858 {
859 struct ctf_named_field_class *named_fc;
860
861 BT_ASSERT(fc);
862 BT_ASSERT(orig_name);
863 g_array_set_size(fc->members, fc->members->len + 1);
864
865 named_fc = &g_array_index(fc->members, struct ctf_named_field_class,
866 fc->members->len - 1);
867 _ctf_named_field_class_init(named_fc);
868 g_string_assign(named_fc->orig_name, orig_name);
869 _ctf_named_field_class_unescape_orig_name(named_fc);
870 named_fc->fc = member_fc;
871
872 if (member_fc->alignment > fc->base.alignment) {
873 fc->base.alignment = member_fc->alignment;
874 }
875 }
876
877 static inline
878 struct ctf_named_field_class *ctf_field_class_variant_borrow_option_by_index(
879 struct ctf_field_class_variant *fc, uint64_t index)
880 {
881 BT_ASSERT(fc);
882 BT_ASSERT(index < fc->options->len);
883 return &g_array_index(fc->options, struct ctf_named_field_class,
884 index);
885 }
886
887 static inline
888 struct ctf_named_field_class *ctf_field_class_variant_borrow_option_by_name(
889 struct ctf_field_class_variant *fc, const char *name)
890 {
891 uint64_t i;
892 struct ctf_named_field_class *ret_named_fc = NULL;
893
894 BT_ASSERT(fc);
895 BT_ASSERT(name);
896
897 for (i = 0; i < fc->options->len; i++) {
898 struct ctf_named_field_class *named_fc =
899 ctf_field_class_variant_borrow_option_by_index(fc, i);
900
901 if (strcmp(name, named_fc->name->str) == 0) {
902 ret_named_fc = named_fc;
903 goto end;
904 }
905 }
906
907 end:
908 return ret_named_fc;
909 }
910
911 static inline
912 struct ctf_field_class_variant_range *
913 ctf_field_class_variant_borrow_range_by_index(
914 struct ctf_field_class_variant *fc, uint64_t index)
915 {
916 BT_ASSERT(fc);
917 BT_ASSERT(index < fc->ranges->len);
918 return &g_array_index(fc->ranges, struct ctf_field_class_variant_range,
919 index);
920 }
921
922 static inline
923 void ctf_field_class_variant_append_option(struct ctf_field_class_variant *fc,
924 const char *orig_name, struct ctf_field_class *option_fc)
925 {
926 struct ctf_named_field_class *named_fc;
927
928 BT_ASSERT(fc);
929 BT_ASSERT(orig_name);
930 g_array_set_size(fc->options, fc->options->len + 1);
931
932 named_fc = &g_array_index(fc->options, struct ctf_named_field_class,
933 fc->options->len - 1);
934 _ctf_named_field_class_init(named_fc);
935 g_string_assign(named_fc->orig_name, orig_name);
936 _ctf_named_field_class_unescape_orig_name(named_fc);
937 named_fc->fc = option_fc;
938 }
939
940 static inline
941 void ctf_field_class_variant_set_tag_field_class(
942 struct ctf_field_class_variant *fc,
943 struct ctf_field_class_enum *tag_fc)
944 {
945 uint64_t option_i;
946
947 BT_ASSERT(fc);
948 BT_ASSERT(tag_fc);
949 fc->tag_fc = tag_fc;
950
951 for (option_i = 0; option_i < fc->options->len; option_i++) {
952 uint64_t range_i;
953 struct ctf_named_field_class *named_fc =
954 ctf_field_class_variant_borrow_option_by_index(
955 fc, option_i);
956 struct ctf_field_class_enum_mapping *mapping;
957
958 mapping = ctf_field_class_enum_borrow_mapping_by_label(
959 tag_fc, named_fc->orig_name->str);
960 if (!mapping) {
961 continue;
962 }
963
964 for (range_i = 0; range_i < mapping->ranges->len;
965 range_i++) {
966 struct ctf_range *range =
967 ctf_field_class_enum_mapping_borrow_range_by_index(
968 mapping, range_i);
969 struct ctf_field_class_variant_range var_range;
970
971 var_range.range = *range;
972 var_range.option_index = option_i;
973 g_array_append_val(fc->ranges, var_range);
974 }
975 }
976 }
977
978 static inline
979 struct ctf_field_class *ctf_field_class_compound_borrow_field_class_by_index(
980 struct ctf_field_class *comp_fc, uint64_t index)
981 {
982 struct ctf_field_class *fc = NULL;
983
984 switch (comp_fc->type) {
985 case CTF_FIELD_CLASS_TYPE_STRUCT:
986 {
987 struct ctf_named_field_class *named_fc =
988 ctf_field_class_struct_borrow_member_by_index(
989 (void *) comp_fc, index);
990
991 BT_ASSERT(named_fc);
992 fc = named_fc->fc;
993 break;
994 }
995 case CTF_FIELD_CLASS_TYPE_VARIANT:
996 {
997 struct ctf_named_field_class *named_fc =
998 ctf_field_class_variant_borrow_option_by_index(
999 (void *) comp_fc, index);
1000
1001 BT_ASSERT(named_fc);
1002 fc = named_fc->fc;
1003 break;
1004 }
1005 case CTF_FIELD_CLASS_TYPE_ARRAY:
1006 case CTF_FIELD_CLASS_TYPE_SEQUENCE:
1007 {
1008 struct ctf_field_class_array_base *array_fc = (void *) comp_fc;
1009
1010 fc = array_fc->elem_fc;
1011 break;
1012 }
1013 default:
1014 break;
1015 }
1016
1017 return fc;
1018 }
1019
1020 static inline
1021 uint64_t ctf_field_class_compound_get_field_class_count(struct ctf_field_class *fc)
1022 {
1023 uint64_t field_count;
1024
1025 switch (fc->type) {
1026 case CTF_FIELD_CLASS_TYPE_STRUCT:
1027 {
1028 struct ctf_field_class_struct *struct_fc = (void *) fc;
1029
1030 field_count = struct_fc->members->len;
1031 break;
1032 }
1033 case CTF_FIELD_CLASS_TYPE_VARIANT:
1034 {
1035 struct ctf_field_class_variant *var_fc = (void *) fc;
1036
1037 field_count = var_fc->options->len;
1038 break;
1039 }
1040 case CTF_FIELD_CLASS_TYPE_ARRAY:
1041 case CTF_FIELD_CLASS_TYPE_SEQUENCE:
1042 /*
1043 * Array and sequence types always contain a single
1044 * member (the element type).
1045 */
1046 field_count = 1;
1047 break;
1048 default:
1049 abort();
1050 }
1051
1052 return field_count;
1053 }
1054
1055 static inline
1056 int64_t ctf_field_class_compound_get_field_class_index_from_orig_name(
1057 struct ctf_field_class *fc, const char *orig_name)
1058 {
1059 int64_t ret_index = -1;
1060 uint64_t i;
1061
1062 switch (fc->type) {
1063 case CTF_FIELD_CLASS_TYPE_STRUCT:
1064 {
1065 struct ctf_field_class_struct *struct_fc = (void *) fc;
1066
1067 for (i = 0; i < struct_fc->members->len; i++) {
1068 struct ctf_named_field_class *named_fc =
1069 ctf_field_class_struct_borrow_member_by_index(
1070 struct_fc, i);
1071
1072 if (strcmp(orig_name, named_fc->orig_name->str) == 0) {
1073 ret_index = (int64_t) i;
1074 goto end;
1075 }
1076 }
1077
1078 break;
1079 }
1080 case CTF_FIELD_CLASS_TYPE_VARIANT:
1081 {
1082 struct ctf_field_class_variant *var_fc = (void *) fc;
1083
1084 for (i = 0; i < var_fc->options->len; i++) {
1085 struct ctf_named_field_class *named_fc =
1086 ctf_field_class_variant_borrow_option_by_index(
1087 var_fc, i);
1088
1089 if (strcmp(orig_name, named_fc->orig_name->str) == 0) {
1090 ret_index = (int64_t) i;
1091 goto end;
1092 }
1093 }
1094
1095 break;
1096 }
1097 default:
1098 break;
1099 }
1100
1101 end:
1102 return ret_index;
1103 }
1104
1105 static inline
1106 void ctf_field_path_append_index(struct ctf_field_path *fp, int64_t index)
1107 {
1108 BT_ASSERT(fp);
1109 g_array_append_val(fp->path, index);
1110 }
1111
1112 static inline
1113 int64_t ctf_field_path_borrow_index_by_index(struct ctf_field_path *fp,
1114 uint64_t index)
1115 {
1116 BT_ASSERT(fp);
1117 BT_ASSERT(index < fp->path->len);
1118 return g_array_index(fp->path, int64_t, index);
1119 }
1120
1121 static inline
1122 void ctf_field_path_clear(struct ctf_field_path *fp)
1123 {
1124 BT_ASSERT(fp);
1125 g_array_set_size(fp->path, 0);
1126 }
1127
1128 static inline
1129 const char *ctf_scope_string(enum ctf_scope scope)
1130 {
1131 switch (scope) {
1132 case CTF_SCOPE_PACKET_HEADER:
1133 return "CTF_SCOPE_PACKET_HEADER";
1134 case CTF_SCOPE_PACKET_CONTEXT:
1135 return "CTF_SCOPE_PACKET_CONTEXT";
1136 case CTF_SCOPE_EVENT_HEADER:
1137 return "CTF_SCOPE_EVENT_HEADER";
1138 case CTF_SCOPE_EVENT_COMMON_CONTEXT:
1139 return "CTF_SCOPE_EVENT_COMMON_CONTEXT";
1140 case CTF_SCOPE_EVENT_SPECIFIC_CONTEXT:
1141 return "CTF_SCOPE_EVENT_SPECIFIC_CONTEXT";
1142 case CTF_SCOPE_EVENT_PAYLOAD:
1143 return "CTF_SCOPE_EVENT_PAYLOAD";
1144 default:
1145 abort();
1146 }
1147 }
1148
1149 static inline
1150 GString *ctf_field_path_string(struct ctf_field_path *path)
1151 {
1152 GString *str = g_string_new(NULL);
1153 uint64_t i;
1154
1155 BT_ASSERT(path);
1156
1157 if (!str) {
1158 goto end;
1159 }
1160
1161 g_string_append_printf(str, "[%s", ctf_scope_string(path->root));
1162
1163 for (i = 0; i < path->path->len; i++) {
1164 g_string_append_printf(str, ", %" PRId64,
1165 ctf_field_path_borrow_index_by_index(path, i));
1166 }
1167
1168 g_string_append(str, "]");
1169
1170 end:
1171 return str;
1172 }
1173
1174 static inline
1175 struct ctf_field_class *ctf_field_path_borrow_field_class(
1176 struct ctf_field_path *field_path,
1177 struct ctf_trace_class *tc,
1178 struct ctf_stream_class *sc,
1179 struct ctf_event_class *ec)
1180 {
1181 uint64_t i;
1182 struct ctf_field_class *fc;
1183
1184 switch (field_path->root) {
1185 case CTF_SCOPE_PACKET_HEADER:
1186 fc = tc->packet_header_fc;
1187 break;
1188 case CTF_SCOPE_PACKET_CONTEXT:
1189 fc = sc->packet_context_fc;
1190 break;
1191 case CTF_SCOPE_EVENT_HEADER:
1192 fc = sc->event_header_fc;
1193 break;
1194 case CTF_SCOPE_EVENT_COMMON_CONTEXT:
1195 fc = sc->event_common_context_fc;
1196 break;
1197 case CTF_SCOPE_EVENT_SPECIFIC_CONTEXT:
1198 fc = ec->spec_context_fc;
1199 break;
1200 case CTF_SCOPE_EVENT_PAYLOAD:
1201 fc = ec->payload_fc;
1202 break;
1203 default:
1204 abort();
1205 }
1206
1207 BT_ASSERT(fc);
1208
1209 for (i = 0; i < field_path->path->len; i++) {
1210 int64_t child_index =
1211 ctf_field_path_borrow_index_by_index(field_path, i);
1212 struct ctf_field_class *child_fc =
1213 ctf_field_class_compound_borrow_field_class_by_index(
1214 fc, child_index);
1215 BT_ASSERT(child_fc);
1216 fc = child_fc;
1217 }
1218
1219 BT_ASSERT(fc);
1220 return fc;
1221 }
1222
1223 static inline
1224 struct ctf_field_class *ctf_field_class_copy(struct ctf_field_class *fc);
1225
1226 static inline
1227 void ctf_field_class_bit_array_copy_content(
1228 struct ctf_field_class_bit_array *dst_fc,
1229 struct ctf_field_class_bit_array *src_fc)
1230 {
1231 BT_ASSERT(dst_fc);
1232 BT_ASSERT(src_fc);
1233 dst_fc->byte_order = src_fc->byte_order;
1234 dst_fc->size = src_fc->size;
1235 }
1236
1237 static inline
1238 void ctf_field_class_int_copy_content(
1239 struct ctf_field_class_int *dst_fc,
1240 struct ctf_field_class_int *src_fc)
1241 {
1242 ctf_field_class_bit_array_copy_content((void *) dst_fc, (void *) src_fc);
1243 dst_fc->meaning = src_fc->meaning;
1244 dst_fc->is_signed = src_fc->is_signed;
1245 dst_fc->disp_base = src_fc->disp_base;
1246 dst_fc->encoding = src_fc->encoding;
1247 dst_fc->mapped_clock_class = src_fc->mapped_clock_class;
1248 dst_fc->storing_index = src_fc->storing_index;
1249 }
1250
1251 static inline
1252 struct ctf_field_class_int *_ctf_field_class_int_copy(
1253 struct ctf_field_class_int *fc)
1254 {
1255 struct ctf_field_class_int *copy_fc = ctf_field_class_int_create();
1256
1257 BT_ASSERT(copy_fc);
1258 ctf_field_class_int_copy_content(copy_fc, fc);
1259 return copy_fc;
1260 }
1261
1262 static inline
1263 struct ctf_field_class_enum *_ctf_field_class_enum_copy(
1264 struct ctf_field_class_enum *fc)
1265 {
1266 struct ctf_field_class_enum *copy_fc = ctf_field_class_enum_create();
1267 uint64_t i;
1268
1269 BT_ASSERT(copy_fc);
1270 ctf_field_class_int_copy_content((void *) copy_fc, (void *) fc);
1271
1272 for (i = 0; i < fc->mappings->len; i++) {
1273 uint64_t range_i;
1274
1275 struct ctf_field_class_enum_mapping *mapping =
1276 &g_array_index(fc->mappings,
1277 struct ctf_field_class_enum_mapping, i);
1278
1279 for (range_i = 0; range_i < mapping->ranges->len; range_i++) {
1280 struct ctf_range *range =
1281 &g_array_index(mapping->ranges,
1282 struct ctf_range, range_i);
1283
1284 ctf_field_class_enum_map_range(copy_fc,
1285 mapping->label->str, range->lower.u,
1286 range->upper.u);
1287 }
1288 }
1289
1290 return copy_fc;
1291 }
1292
1293 static inline
1294 struct ctf_field_class_float *_ctf_field_class_float_copy(
1295 struct ctf_field_class_float *fc)
1296 {
1297 struct ctf_field_class_float *copy_fc = ctf_field_class_float_create();
1298
1299 BT_ASSERT(copy_fc);
1300 ctf_field_class_bit_array_copy_content((void *) copy_fc, (void *) fc);
1301 return copy_fc;
1302 }
1303
1304 static inline
1305 struct ctf_field_class_string *_ctf_field_class_string_copy(
1306 struct ctf_field_class_string *fc)
1307 {
1308 struct ctf_field_class_string *copy_fc = ctf_field_class_string_create();
1309
1310 BT_ASSERT(copy_fc);
1311 return copy_fc;
1312 }
1313
1314 static inline
1315 struct ctf_field_class_struct *_ctf_field_class_struct_copy(
1316 struct ctf_field_class_struct *fc)
1317 {
1318 struct ctf_field_class_struct *copy_fc = ctf_field_class_struct_create();
1319 uint64_t i;
1320
1321 BT_ASSERT(copy_fc);
1322
1323 for (i = 0; i < fc->members->len; i++) {
1324 struct ctf_named_field_class *named_fc =
1325 &g_array_index(fc->members,
1326 struct ctf_named_field_class, i);
1327
1328 ctf_field_class_struct_append_member(copy_fc,
1329 named_fc->name->str,
1330 ctf_field_class_copy(named_fc->fc));
1331 }
1332
1333 return copy_fc;
1334 }
1335
1336 static inline
1337 void ctf_field_path_copy_content(struct ctf_field_path *dst_fp,
1338 struct ctf_field_path *src_fp)
1339 {
1340 uint64_t i;
1341
1342 BT_ASSERT(dst_fp);
1343 BT_ASSERT(src_fp);
1344 dst_fp->root = src_fp->root;
1345 ctf_field_path_clear(dst_fp);
1346
1347 for (i = 0; i < src_fp->path->len; i++) {
1348 int64_t index = ctf_field_path_borrow_index_by_index(
1349 src_fp, i);
1350
1351 ctf_field_path_append_index(dst_fp, index);
1352 }
1353 }
1354
1355 static inline
1356 struct ctf_field_class_variant *_ctf_field_class_variant_copy(
1357 struct ctf_field_class_variant *fc)
1358 {
1359 struct ctf_field_class_variant *copy_fc =
1360 ctf_field_class_variant_create();
1361 uint64_t i;
1362
1363 BT_ASSERT(copy_fc);
1364
1365 for (i = 0; i < fc->options->len; i++) {
1366 struct ctf_named_field_class *named_fc =
1367 &g_array_index(fc->options,
1368 struct ctf_named_field_class, i);
1369
1370 ctf_field_class_variant_append_option(copy_fc,
1371 named_fc->name->str,
1372 ctf_field_class_copy(named_fc->fc));
1373 }
1374
1375 for (i = 0; i < fc->ranges->len; i++) {
1376 struct ctf_field_class_variant_range *range =
1377 &g_array_index(fc->ranges,
1378 struct ctf_field_class_variant_range, i);
1379
1380 g_array_append_val(copy_fc->ranges, *range);
1381 }
1382
1383 ctf_field_path_copy_content(&copy_fc->tag_path, &fc->tag_path);
1384 g_string_assign(copy_fc->tag_ref, fc->tag_ref->str);
1385 copy_fc->stored_tag_index = fc->stored_tag_index;
1386 return copy_fc;
1387 }
1388
1389 static inline
1390 void ctf_field_class_array_base_copy_content(
1391 struct ctf_field_class_array_base *dst_fc,
1392 struct ctf_field_class_array_base *src_fc)
1393 {
1394 BT_ASSERT(dst_fc);
1395 BT_ASSERT(src_fc);
1396 dst_fc->elem_fc = ctf_field_class_copy(src_fc->elem_fc);
1397 dst_fc->is_text = src_fc->is_text;
1398 }
1399
1400 static inline
1401 struct ctf_field_class_array *_ctf_field_class_array_copy(
1402 struct ctf_field_class_array *fc)
1403 {
1404 struct ctf_field_class_array *copy_fc = ctf_field_class_array_create();
1405
1406 BT_ASSERT(copy_fc);
1407 ctf_field_class_array_base_copy_content((void *) copy_fc, (void *) fc);
1408 copy_fc->length = fc->length;
1409 return copy_fc;
1410 }
1411
1412 static inline
1413 struct ctf_field_class_sequence *_ctf_field_class_sequence_copy(
1414 struct ctf_field_class_sequence *fc)
1415 {
1416 struct ctf_field_class_sequence *copy_fc =
1417 ctf_field_class_sequence_create();
1418
1419 BT_ASSERT(copy_fc);
1420 ctf_field_class_array_base_copy_content((void *) copy_fc, (void *) fc);
1421 ctf_field_path_copy_content(&copy_fc->length_path, &fc->length_path);
1422 g_string_assign(copy_fc->length_ref, fc->length_ref->str);
1423 copy_fc->stored_length_index = fc->stored_length_index;
1424 return copy_fc;
1425 }
1426
1427 static inline
1428 struct ctf_field_class *ctf_field_class_copy(struct ctf_field_class *fc)
1429 {
1430 struct ctf_field_class *copy_fc = NULL;
1431
1432 if (!fc) {
1433 goto end;
1434 }
1435
1436 /*
1437 * Translation should not have happened yet.
1438 */
1439 BT_ASSERT(!fc->ir_fc);
1440
1441 switch (fc->type) {
1442 case CTF_FIELD_CLASS_TYPE_INT:
1443 copy_fc = (void *) _ctf_field_class_int_copy((void *) fc);
1444 break;
1445 case CTF_FIELD_CLASS_TYPE_ENUM:
1446 copy_fc = (void *) _ctf_field_class_enum_copy((void *) fc);
1447 break;
1448 case CTF_FIELD_CLASS_TYPE_FLOAT:
1449 copy_fc = (void *) _ctf_field_class_float_copy((void *) fc);
1450 break;
1451 case CTF_FIELD_CLASS_TYPE_STRING:
1452 copy_fc = (void *) _ctf_field_class_string_copy((void *) fc);
1453 break;
1454 case CTF_FIELD_CLASS_TYPE_STRUCT:
1455 copy_fc = (void *) _ctf_field_class_struct_copy((void *) fc);
1456 break;
1457 case CTF_FIELD_CLASS_TYPE_ARRAY:
1458 copy_fc = (void *) _ctf_field_class_array_copy((void *) fc);
1459 break;
1460 case CTF_FIELD_CLASS_TYPE_SEQUENCE:
1461 copy_fc = (void *) _ctf_field_class_sequence_copy((void *) fc);
1462 break;
1463 case CTF_FIELD_CLASS_TYPE_VARIANT:
1464 copy_fc = (void *) _ctf_field_class_variant_copy((void *) fc);
1465 break;
1466 default:
1467 abort();
1468 }
1469
1470 copy_fc->type = fc->type;
1471 copy_fc->alignment = fc->alignment;
1472 copy_fc->in_ir = fc->in_ir;
1473
1474 end:
1475 return copy_fc;
1476 }
1477
1478 static inline
1479 struct ctf_event_class *ctf_event_class_create(void)
1480 {
1481 struct ctf_event_class *ec = g_new0(struct ctf_event_class, 1);
1482
1483 BT_ASSERT(ec);
1484 ec->name = g_string_new(NULL);
1485 BT_ASSERT(ec->name);
1486 ec->emf_uri = g_string_new(NULL);
1487 BT_ASSERT(ec->emf_uri);
1488 ec->log_level = -1;
1489 return ec;
1490 }
1491
1492 static inline
1493 void ctf_event_class_destroy(struct ctf_event_class *ec)
1494 {
1495 if (!ec) {
1496 return;
1497 }
1498
1499 if (ec->name) {
1500 g_string_free(ec->name, TRUE);
1501 }
1502
1503 if (ec->emf_uri) {
1504 g_string_free(ec->emf_uri, TRUE);
1505 }
1506
1507 ctf_field_class_destroy(ec->spec_context_fc);
1508 ctf_field_class_destroy(ec->payload_fc);
1509 g_free(ec);
1510 }
1511
1512 static inline
1513 struct ctf_stream_class *ctf_stream_class_create(void)
1514 {
1515 struct ctf_stream_class *sc = g_new0(struct ctf_stream_class, 1);
1516
1517 BT_ASSERT(sc);
1518 sc->event_classes = g_ptr_array_new_with_free_func(
1519 (GDestroyNotify) ctf_event_class_destroy);
1520 BT_ASSERT(sc->event_classes);
1521 sc->event_classes_by_id = g_hash_table_new(g_direct_hash,
1522 g_direct_equal);
1523 BT_ASSERT(sc->event_classes_by_id);
1524 return sc;
1525 }
1526
1527 static inline
1528 void ctf_stream_class_destroy(struct ctf_stream_class *sc)
1529 {
1530 if (!sc) {
1531 return;
1532 }
1533
1534 if (sc->event_classes) {
1535 g_ptr_array_free(sc->event_classes, TRUE);
1536 }
1537
1538 if (sc->event_classes_by_id) {
1539 g_hash_table_destroy(sc->event_classes_by_id);
1540 }
1541
1542 ctf_field_class_destroy(sc->packet_context_fc);
1543 ctf_field_class_destroy(sc->event_header_fc);
1544 ctf_field_class_destroy(sc->event_common_context_fc);
1545 g_free(sc);
1546 }
1547
1548 static inline
1549 void ctf_stream_class_append_event_class(struct ctf_stream_class *sc,
1550 struct ctf_event_class *ec)
1551 {
1552 g_ptr_array_add(sc->event_classes, ec);
1553 g_hash_table_insert(sc->event_classes_by_id,
1554 GUINT_TO_POINTER((guint) ec->id), ec);
1555 }
1556
1557 static inline
1558 struct ctf_event_class *ctf_stream_class_borrow_event_class_by_id(
1559 struct ctf_stream_class *sc, uint64_t type)
1560 {
1561 BT_ASSERT(sc);
1562 return g_hash_table_lookup(sc->event_classes_by_id,
1563 GUINT_TO_POINTER((guint) type));
1564 }
1565
1566 static inline
1567 void _ctf_trace_class_env_entry_init(struct ctf_trace_class_env_entry *entry)
1568 {
1569 BT_ASSERT(entry);
1570 entry->name = g_string_new(NULL);
1571 BT_ASSERT(entry->name);
1572 entry->value.str = g_string_new(NULL);
1573 BT_ASSERT(entry->value.str);
1574 }
1575
1576 static inline
1577 void _ctf_trace_class_env_entry_fini(struct ctf_trace_class_env_entry *entry)
1578 {
1579 BT_ASSERT(entry);
1580
1581 if (entry->name) {
1582 g_string_free(entry->name, TRUE);
1583 }
1584
1585 if (entry->value.str) {
1586 g_string_free(entry->value.str, TRUE);
1587 }
1588 }
1589
1590 static inline
1591 struct ctf_clock_class *ctf_clock_class_create(void)
1592 {
1593 struct ctf_clock_class *cc = g_new0(struct ctf_clock_class, 1);
1594
1595 BT_ASSERT(cc);
1596 cc->name = g_string_new(NULL);
1597 BT_ASSERT(cc->name);
1598 cc->description = g_string_new(NULL);
1599 BT_ASSERT(cc->description);
1600 return cc;
1601 }
1602
1603 static inline
1604 void ctf_clock_class_destroy(struct ctf_clock_class *cc)
1605 {
1606 if (!cc) {
1607 return;
1608 }
1609
1610 if (cc->name) {
1611 g_string_free(cc->name, TRUE);
1612 }
1613
1614 if (cc->description) {
1615 g_string_free(cc->description, TRUE);
1616 }
1617
1618 bt_clock_class_put_ref(cc->ir_cc);
1619 g_free(cc);
1620 }
1621
1622 static inline
1623 struct ctf_trace_class *ctf_trace_class_create(void)
1624 {
1625 struct ctf_trace_class *tc = g_new0(struct ctf_trace_class, 1);
1626
1627 BT_ASSERT(tc);
1628 tc->default_byte_order = -1;
1629 tc->clock_classes = g_ptr_array_new_with_free_func(
1630 (GDestroyNotify) ctf_clock_class_destroy);
1631 BT_ASSERT(tc->clock_classes);
1632 tc->stream_classes = g_ptr_array_new_with_free_func(
1633 (GDestroyNotify) ctf_stream_class_destroy);
1634 BT_ASSERT(tc->stream_classes);
1635 tc->env_entries = g_array_new(FALSE, TRUE,
1636 sizeof(struct ctf_trace_class_env_entry));
1637 return tc;
1638 }
1639
1640 static inline
1641 void ctf_trace_class_destroy(struct ctf_trace_class *tc)
1642 {
1643 if (!tc) {
1644 return;
1645 }
1646
1647 ctf_field_class_destroy(tc->packet_header_fc);
1648
1649 if (tc->clock_classes) {
1650 g_ptr_array_free(tc->clock_classes, TRUE);
1651 }
1652
1653 if (tc->stream_classes) {
1654 g_ptr_array_free(tc->stream_classes, TRUE);
1655 }
1656
1657 if (tc->env_entries) {
1658 uint64_t i;
1659
1660 for (i = 0; i < tc->env_entries->len; i++) {
1661 struct ctf_trace_class_env_entry *entry =
1662 &g_array_index(tc->env_entries,
1663 struct ctf_trace_class_env_entry, i);
1664
1665 _ctf_trace_class_env_entry_fini(entry);
1666 }
1667
1668 g_array_free(tc->env_entries, TRUE);
1669 }
1670
1671 g_free(tc);
1672 }
1673
1674 static inline
1675 void ctf_trace_class_append_env_entry(struct ctf_trace_class *tc,
1676 const char *name, enum ctf_trace_class_env_entry_type type,
1677 const char *str_value, int64_t i_value)
1678 {
1679 struct ctf_trace_class_env_entry *entry;
1680
1681 BT_ASSERT(tc);
1682 BT_ASSERT(name);
1683 g_array_set_size(tc->env_entries, tc->env_entries->len + 1);
1684
1685 entry = &g_array_index(tc->env_entries,
1686 struct ctf_trace_class_env_entry, tc->env_entries->len - 1);
1687 entry->type = type;
1688 _ctf_trace_class_env_entry_init(entry);
1689 g_string_assign(entry->name, name);
1690
1691 if (str_value) {
1692 g_string_assign(entry->value.str, str_value);
1693 }
1694
1695 entry->value.i = i_value;
1696 }
1697
1698 static inline
1699 struct ctf_stream_class *ctf_trace_class_borrow_stream_class_by_id(
1700 struct ctf_trace_class *tc, uint64_t id)
1701 {
1702 uint64_t i;
1703 struct ctf_stream_class *ret_sc = NULL;
1704
1705 BT_ASSERT(tc);
1706
1707 for (i = 0; i < tc->stream_classes->len; i++) {
1708 struct ctf_stream_class *sc = tc->stream_classes->pdata[i];
1709
1710 if (sc->id == id) {
1711 ret_sc = sc;
1712 goto end;
1713 }
1714 }
1715
1716 end:
1717 return ret_sc;
1718 }
1719
1720 static inline
1721 struct ctf_clock_class *ctf_trace_class_borrow_clock_class_by_name(
1722 struct ctf_trace_class *tc, const char *name)
1723 {
1724 uint64_t i;
1725 struct ctf_clock_class *ret_cc = NULL;
1726
1727 BT_ASSERT(tc);
1728 BT_ASSERT(name);
1729
1730 for (i = 0; i < tc->clock_classes->len; i++) {
1731 struct ctf_clock_class *cc = tc->clock_classes->pdata[i];
1732
1733 BT_ASSERT(cc->name);
1734 if (strcmp(cc->name->str, name) == 0) {
1735 ret_cc = cc;
1736 goto end;
1737 }
1738 }
1739
1740 end:
1741 return ret_cc;
1742 }
1743
1744 static inline
1745 struct ctf_trace_class_env_entry *ctf_trace_class_borrow_env_entry_by_index(
1746 struct ctf_trace_class *tc, uint64_t index)
1747 {
1748 BT_ASSERT(tc);
1749 BT_ASSERT(index < tc->env_entries->len);
1750 return &g_array_index(tc->env_entries, struct ctf_trace_class_env_entry,
1751 index);
1752 }
1753
1754 static inline
1755 struct ctf_trace_class_env_entry *ctf_trace_class_borrow_env_entry_by_name(
1756 struct ctf_trace_class *tc, const char *name)
1757 {
1758 struct ctf_trace_class_env_entry *ret_entry = NULL;
1759 uint64_t i;
1760
1761 BT_ASSERT(tc);
1762 BT_ASSERT(name);
1763
1764 for (i = 0; i < tc->env_entries->len; i++) {
1765 struct ctf_trace_class_env_entry *env_entry =
1766 ctf_trace_class_borrow_env_entry_by_index(tc, i);
1767
1768 if (strcmp(env_entry->name->str, name) == 0) {
1769 ret_entry = env_entry;
1770 goto end;
1771 }
1772 }
1773
1774 end:
1775 return ret_entry;
1776 }
1777
1778 #endif /* _CTF_META_H */
This page took 0.097514 seconds and 4 git commands to generate.