2 * Copyright 2017-2018 Philippe Proulx <pproulx@efficios.com>
3 * Copyright 2013, 2014 Jérémie Galarneau <jeremie.galarneau@efficios.com>
5 * Permission is hereby granted, free of charge, to any person obtaining a copy
6 * of this software and associated documentation files (the "Software"), to deal
7 * in the Software without restriction, including without limitation the rights
8 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 * copies of the Software, and to permit persons to whom the Software is
10 * furnished to do so, subject to the following conditions:
12 * The above copyright notice and this permission notice shall be included in
13 * all copies or substantial portions of the Software.
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
24 #define BT_LOG_TAG "LIB/FIELD-CLASS"
25 #include "lib/logging.h"
27 #include "lib/assert-pre.h"
28 #include <babeltrace2/trace-ir/field-class.h>
29 #include <babeltrace2/trace-ir/field-class-const.h>
30 #include <babeltrace2/trace-ir/field-const.h>
31 #include <babeltrace2/trace-ir/field.h>
32 #include <babeltrace2/trace-ir/clock-class.h>
33 #include "lib/object.h"
34 #include "compat/compiler.h"
35 #include "compat/endian.h"
36 #include "common/assert.h"
37 #include "compat/glib.h"
42 #include "clock-class.h"
43 #include "field-class.h"
45 #include "field-path.h"
47 #include "lib/func-status.h"
48 #include "lib/integer-range-set.h"
50 enum bt_field_class_type
bt_field_class_get_type(
51 const struct bt_field_class
*fc
)
53 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
58 void init_field_class(struct bt_field_class
*fc
, enum bt_field_class_type type
,
59 bt_object_release_func release_func
)
62 BT_ASSERT(release_func
);
63 bt_object_init_shared(&fc
->base
, release_func
);
68 void destroy_bit_array_field_class(struct bt_object
*obj
)
71 BT_LIB_LOGD("Destroying bit array field class object: %!+F", obj
);
75 struct bt_field_class
*bt_field_class_bit_array_create(
76 struct bt_trace_class
*trace_class
, uint64_t length
)
78 struct bt_field_class_bit_array
*ba_fc
= NULL
;
80 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
81 BT_ASSERT_PRE(length
> 0 && length
<= 64,
82 "Unsupported length for bit array field class "
83 "(minimum is 1, maximum is 64): length=%" PRIu64
, length
);
84 BT_LOGD("Creating default bit array field class object.");
85 ba_fc
= g_new0(struct bt_field_class_bit_array
, 1);
87 BT_LIB_LOGE_APPEND_CAUSE(
88 "Failed to allocate one bit array field class.");
92 init_field_class((void *) ba_fc
, BT_FIELD_CLASS_TYPE_BIT_ARRAY
,
93 destroy_bit_array_field_class
);
94 ba_fc
->length
= length
;
95 BT_LIB_LOGD("Created bit array field class object: %!+F", ba_fc
);
99 BT_OBJECT_PUT_REF_AND_RESET(ba_fc
);
102 return (void *) ba_fc
;
105 uint64_t bt_field_class_bit_array_get_length(const struct bt_field_class
*fc
)
107 const struct bt_field_class_bit_array
*ba_fc
= (const void *) fc
;
109 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
110 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_BIT_ARRAY
,
112 return ba_fc
->length
;
116 void destroy_bool_field_class(struct bt_object
*obj
)
119 BT_LIB_LOGD("Destroying boolean field class object: %!+F", obj
);
123 struct bt_field_class
*bt_field_class_bool_create(
124 bt_trace_class
*trace_class
)
126 struct bt_field_class_bool
*bool_fc
= NULL
;
128 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
129 BT_LOGD("Creating default boolean field class object.");
130 bool_fc
= g_new0(struct bt_field_class_bool
, 1);
132 BT_LIB_LOGE_APPEND_CAUSE(
133 "Failed to allocate one boolean field class.");
137 init_field_class((void *) bool_fc
, BT_FIELD_CLASS_TYPE_BOOL
,
138 destroy_bool_field_class
);
139 BT_LIB_LOGD("Created boolean field class object: %!+F", bool_fc
);
143 BT_OBJECT_PUT_REF_AND_RESET(bool_fc
);
146 return (void *) bool_fc
;
150 void init_integer_field_class(struct bt_field_class_integer
*fc
,
151 enum bt_field_class_type type
,
152 bt_object_release_func release_func
)
154 init_field_class((void *) fc
, type
, release_func
);
156 fc
->base
= BT_FIELD_CLASS_INTEGER_PREFERRED_DISPLAY_BASE_DECIMAL
;
160 void destroy_integer_field_class(struct bt_object
*obj
)
163 BT_LIB_LOGD("Destroying integer field class object: %!+F", obj
);
168 struct bt_field_class
*create_integer_field_class(bt_trace_class
*trace_class
,
169 enum bt_field_class_type type
)
171 struct bt_field_class_integer
*int_fc
= NULL
;
173 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
174 BT_LOGD("Creating default integer field class object: type=%s",
175 bt_common_field_class_type_string(type
));
176 int_fc
= g_new0(struct bt_field_class_integer
, 1);
178 BT_LIB_LOGE_APPEND_CAUSE(
179 "Failed to allocate one integer field class.");
183 init_integer_field_class(int_fc
, type
, destroy_integer_field_class
);
184 BT_LIB_LOGD("Created integer field class object: %!+F", int_fc
);
188 BT_OBJECT_PUT_REF_AND_RESET(int_fc
);
191 return (void *) int_fc
;
194 struct bt_field_class
*bt_field_class_integer_unsigned_create(
195 bt_trace_class
*trace_class
)
197 return create_integer_field_class(trace_class
,
198 BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER
);
201 struct bt_field_class
*bt_field_class_integer_signed_create(
202 bt_trace_class
*trace_class
)
204 return create_integer_field_class(trace_class
,
205 BT_FIELD_CLASS_TYPE_SIGNED_INTEGER
);
208 uint64_t bt_field_class_integer_get_field_value_range(
209 const struct bt_field_class
*fc
)
211 const struct bt_field_class_integer
*int_fc
= (const void *) fc
;
213 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
214 BT_ASSERT_PRE_DEV_FC_IS_INT(fc
, "Field class");
215 return int_fc
->range
;
219 bool size_is_valid_for_enumeration_field_class(struct bt_field_class
*fc
,
226 void bt_field_class_integer_set_field_value_range(
227 struct bt_field_class
*fc
, uint64_t size
)
229 struct bt_field_class_integer
*int_fc
= (void *) fc
;
231 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
232 BT_ASSERT_PRE_FC_IS_INT(fc
, "Field class");
233 BT_ASSERT_PRE_DEV_FC_HOT(fc
, "Field class");
234 BT_ASSERT_PRE(size
<= 64,
235 "Unsupported size for integer field class's field value range "
236 "(maximum is 64): size=%" PRIu64
, size
);
238 int_fc
->common
.type
== BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER
||
239 int_fc
->common
.type
== BT_FIELD_CLASS_TYPE_SIGNED_INTEGER
||
240 size_is_valid_for_enumeration_field_class(fc
, size
),
241 "Invalid field value range for enumeration field class: "
242 "at least one of the current mapping ranges contains values "
243 "which are outside this range: %!+F, size=%" PRIu64
, fc
, size
);
244 int_fc
->range
= size
;
245 BT_LIB_LOGD("Set integer field class's field value range: %!+F", fc
);
248 enum bt_field_class_integer_preferred_display_base
249 bt_field_class_integer_get_preferred_display_base(const struct bt_field_class
*fc
)
251 const struct bt_field_class_integer
*int_fc
= (const void *) fc
;
253 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
254 BT_ASSERT_PRE_DEV_FC_IS_INT(fc
, "Field class");
258 void bt_field_class_integer_set_preferred_display_base(
259 struct bt_field_class
*fc
,
260 enum bt_field_class_integer_preferred_display_base base
)
262 struct bt_field_class_integer
*int_fc
= (void *) fc
;
264 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
265 BT_ASSERT_PRE_FC_IS_INT(fc
, "Field class");
266 BT_ASSERT_PRE_DEV_FC_HOT(fc
, "Field class");
268 BT_LIB_LOGD("Set integer field class's preferred display base: %!+F", fc
);
272 void finalize_enumeration_field_class_mapping(
273 struct bt_field_class_enumeration_mapping
*mapping
)
277 if (mapping
->label
) {
278 g_string_free(mapping
->label
, TRUE
);
279 mapping
->label
= NULL
;
282 BT_OBJECT_PUT_REF_AND_RESET(mapping
->range_set
);
286 void destroy_enumeration_field_class(struct bt_object
*obj
)
288 struct bt_field_class_enumeration
*fc
= (void *) obj
;
291 BT_LIB_LOGD("Destroying enumeration field class object: %!+F", fc
);
296 for (i
= 0; i
< fc
->mappings
->len
; i
++) {
297 finalize_enumeration_field_class_mapping(
298 BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(fc
, i
));
301 g_array_free(fc
->mappings
, TRUE
);
306 g_ptr_array_free(fc
->label_buf
, TRUE
);
307 fc
->label_buf
= NULL
;
314 struct bt_field_class
*create_enumeration_field_class(
315 bt_trace_class
*trace_class
, enum bt_field_class_type type
)
317 struct bt_field_class_enumeration
*enum_fc
= NULL
;
319 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
320 BT_LOGD("Creating default enumeration field class object: type=%s",
321 bt_common_field_class_type_string(type
));
322 enum_fc
= g_new0(struct bt_field_class_enumeration
, 1);
324 BT_LIB_LOGE_APPEND_CAUSE(
325 "Failed to allocate one enumeration field class.");
329 init_integer_field_class((void *) enum_fc
, type
,
330 destroy_enumeration_field_class
);
331 enum_fc
->mappings
= g_array_new(FALSE
, TRUE
,
332 sizeof(struct bt_field_class_enumeration_mapping
));
333 if (!enum_fc
->mappings
) {
334 BT_LIB_LOGE_APPEND_CAUSE("Failed to allocate a GArray.");
338 enum_fc
->label_buf
= g_ptr_array_new();
339 if (!enum_fc
->label_buf
) {
340 BT_LIB_LOGE_APPEND_CAUSE("Failed to allocate a GArray.");
344 BT_LIB_LOGD("Created enumeration field class object: %!+F", enum_fc
);
348 BT_OBJECT_PUT_REF_AND_RESET(enum_fc
);
351 return (void *) enum_fc
;
354 struct bt_field_class
*bt_field_class_enumeration_unsigned_create(
355 bt_trace_class
*trace_class
)
357 return create_enumeration_field_class(trace_class
,
358 BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION
);
361 struct bt_field_class
*bt_field_class_enumeration_signed_create(
362 bt_trace_class
*trace_class
)
364 return create_enumeration_field_class(trace_class
,
365 BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION
);
368 uint64_t bt_field_class_enumeration_get_mapping_count(
369 const struct bt_field_class
*fc
)
371 const struct bt_field_class_enumeration
*enum_fc
= (const void *) fc
;
373 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
374 BT_ASSERT_PRE_DEV_FC_IS_ENUM(fc
, "Field class");
375 return (uint64_t) enum_fc
->mappings
->len
;
378 const struct bt_field_class_enumeration_unsigned_mapping
*
379 bt_field_class_enumeration_unsigned_borrow_mapping_by_index_const(
380 const struct bt_field_class
*fc
, uint64_t index
)
382 const struct bt_field_class_enumeration
*enum_fc
= (const void *) fc
;
384 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
385 BT_ASSERT_PRE_DEV_VALID_INDEX(index
, enum_fc
->mappings
->len
);
386 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION
,
388 return (const void *) BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(fc
, index
);
391 const struct bt_field_class_enumeration_signed_mapping
*
392 bt_field_class_enumeration_signed_borrow_mapping_by_index_const(
393 const struct bt_field_class
*fc
, uint64_t index
)
395 const struct bt_field_class_enumeration
*enum_fc
= (const void *) fc
;
397 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
398 BT_ASSERT_PRE_DEV_VALID_INDEX(index
, enum_fc
->mappings
->len
);
399 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION
,
401 return (const void *) BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(fc
, index
);
405 const struct bt_field_class_enumeration_mapping
*
406 borrow_enumeration_field_class_mapping_by_label(
407 const struct bt_field_class_enumeration
*fc
, const char *label
)
409 struct bt_field_class_enumeration_mapping
*mapping
= NULL
;
413 BT_ASSERT_PRE_DEV_NON_NULL(label
, "Label");
415 for (i
= 0; i
< fc
->mappings
->len
; i
++) {
416 struct bt_field_class_enumeration_mapping
*this_mapping
=
417 BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(fc
, i
);
419 if (strcmp(this_mapping
->label
->str
, label
) == 0) {
420 mapping
= this_mapping
;
429 const struct bt_field_class_enumeration_signed_mapping
*
430 bt_field_class_enumeration_signed_borrow_mapping_by_label_const(
431 const struct bt_field_class
*fc
, const char *label
)
433 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
434 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION
,
436 return (const void *) borrow_enumeration_field_class_mapping_by_label(
437 (const void *) fc
, label
);
440 const struct bt_field_class_enumeration_unsigned_mapping
*
441 bt_field_class_enumeration_unsigned_borrow_mapping_by_label_const(
442 const struct bt_field_class
*fc
, const char *label
)
444 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
445 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
,
446 BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION
, "Field class");
447 return (const void *) borrow_enumeration_field_class_mapping_by_label(
448 (const void *) fc
, label
);
451 const char *bt_field_class_enumeration_mapping_get_label(
452 const struct bt_field_class_enumeration_mapping
*mapping
)
454 BT_ASSERT_PRE_DEV_NON_NULL(mapping
, "Enumeration field class mapping");
455 return mapping
->label
->str
;
458 const struct bt_integer_range_set_unsigned
*
459 bt_field_class_enumeration_unsigned_mapping_borrow_ranges_const(
460 const struct bt_field_class_enumeration_unsigned_mapping
*u_mapping
)
462 const struct bt_field_class_enumeration_mapping
*mapping
=
463 (const void *) u_mapping
;
465 BT_ASSERT_PRE_DEV_NON_NULL(mapping
, "Enumeration field class mapping");
466 return (const void *) mapping
->range_set
;
469 const struct bt_integer_range_set_signed
*
470 bt_field_class_enumeration_signed_mapping_borrow_ranges_const(
471 const struct bt_field_class_enumeration_signed_mapping
*s_mapping
)
473 const struct bt_field_class_enumeration_mapping
*mapping
=
474 (const void *) s_mapping
;
476 BT_ASSERT_PRE_DEV_NON_NULL(mapping
, "Enumeration field class mapping");
477 return (const void *) mapping
->range_set
;
480 enum bt_field_class_enumeration_get_mapping_labels_for_value_status
481 bt_field_class_enumeration_unsigned_get_mapping_labels_for_value(
482 const struct bt_field_class
*fc
, uint64_t value
,
483 bt_field_class_enumeration_mapping_label_array
*label_array
,
486 const struct bt_field_class_enumeration
*enum_fc
= (const void *) fc
;
489 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
490 BT_ASSERT_PRE_DEV_NON_NULL(label_array
, "Label array (output)");
491 BT_ASSERT_PRE_DEV_NON_NULL(count
, "Count (output)");
492 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION
,
494 g_ptr_array_set_size(enum_fc
->label_buf
, 0);
496 for (i
= 0; i
< enum_fc
->mappings
->len
; i
++) {
498 const struct bt_field_class_enumeration_mapping
*mapping
=
499 BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(enum_fc
, i
);
501 for (j
= 0; j
< mapping
->range_set
->ranges
->len
; j
++) {
502 const struct bt_integer_range
*range
= (const void *)
503 BT_INTEGER_RANGE_SET_RANGE_AT_INDEX(
504 mapping
->range_set
, j
);
506 if (value
>= range
->lower
.u
&&
507 value
<= range
->upper
.u
) {
508 g_ptr_array_add(enum_fc
->label_buf
,
509 mapping
->label
->str
);
515 *label_array
= (void *) enum_fc
->label_buf
->pdata
;
516 *count
= (uint64_t) enum_fc
->label_buf
->len
;
517 return BT_FUNC_STATUS_OK
;
520 enum bt_field_class_enumeration_get_mapping_labels_for_value_status
521 bt_field_class_enumeration_signed_get_mapping_labels_for_value(
522 const struct bt_field_class
*fc
, int64_t value
,
523 bt_field_class_enumeration_mapping_label_array
*label_array
,
526 const struct bt_field_class_enumeration
*enum_fc
= (const void *) fc
;
529 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
530 BT_ASSERT_PRE_DEV_NON_NULL(label_array
, "Label array (output)");
531 BT_ASSERT_PRE_DEV_NON_NULL(count
, "Count (output)");
532 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION
,
534 g_ptr_array_set_size(enum_fc
->label_buf
, 0);
536 for (i
= 0; i
< enum_fc
->mappings
->len
; i
++) {
538 const struct bt_field_class_enumeration_mapping
*mapping
=
539 BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(enum_fc
, i
);
541 for (j
= 0; j
< mapping
->range_set
->ranges
->len
; j
++) {
542 const struct bt_integer_range
*range
= (const void *)
543 BT_INTEGER_RANGE_SET_RANGE_AT_INDEX(
544 mapping
->range_set
, j
);
546 if (value
>= range
->lower
.i
&&
547 value
<= range
->upper
.i
) {
548 g_ptr_array_add(enum_fc
->label_buf
,
549 mapping
->label
->str
);
555 *label_array
= (void *) enum_fc
->label_buf
->pdata
;
556 *count
= (uint64_t) enum_fc
->label_buf
->len
;
557 return BT_FUNC_STATUS_OK
;
561 bool enumeration_field_class_has_mapping_with_label(
562 const struct bt_field_class_enumeration
*enum_fc
,
571 for (i
= 0; i
< enum_fc
->mappings
->len
; i
++) {
572 struct bt_field_class_enumeration_mapping
*mapping_candidate
=
573 BT_FIELD_CLASS_ENUM_MAPPING_AT_INDEX(enum_fc
, i
);
575 if (strcmp(mapping_candidate
->label
->str
, label
) == 0) {
586 enum bt_field_class_enumeration_add_mapping_status
587 add_mapping_to_enumeration_field_class(struct bt_field_class
*fc
,
588 const char *label
, const struct bt_integer_range_set
*range_set
)
590 enum bt_field_class_enumeration_add_mapping_status status
=
592 struct bt_field_class_enumeration
*enum_fc
= (void *) fc
;
593 struct bt_field_class_enumeration_mapping mapping
= { 0 };
596 BT_ASSERT_PRE_NON_NULL(label
, "Label");
597 BT_ASSERT_PRE_NON_NULL(range_set
, "Integer range set");
598 BT_ASSERT_PRE(!enumeration_field_class_has_mapping_with_label(
600 "Duplicate mapping name in enumeration field class: "
601 "%![enum-fc-]+F, label=\"%s\"", fc
, label
);
602 mapping
.range_set
= range_set
;
603 bt_object_get_ref(mapping
.range_set
);
604 mapping
.label
= g_string_new(label
);
605 if (!mapping
.label
) {
606 finalize_enumeration_field_class_mapping(&mapping
);
607 status
= BT_FUNC_STATUS_MEMORY_ERROR
;
611 g_array_append_val(enum_fc
->mappings
, mapping
);
612 BT_LIB_LOGD("Added mapping to enumeration field class: "
613 "%![fc-]+F, label=\"%s\"", fc
, label
);
619 enum bt_field_class_enumeration_add_mapping_status
620 bt_field_class_enumeration_unsigned_add_mapping(
621 struct bt_field_class
*fc
, const char *label
,
622 const struct bt_integer_range_set_unsigned
*range_set
)
624 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
625 BT_ASSERT_PRE_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION
,
627 return add_mapping_to_enumeration_field_class(fc
, label
,
628 (const void *) range_set
);
631 enum bt_field_class_enumeration_add_mapping_status
632 bt_field_class_enumeration_signed_add_mapping(
633 struct bt_field_class
*fc
, const char *label
,
634 const struct bt_integer_range_set_signed
*range_set
)
636 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
637 BT_ASSERT_PRE_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION
,
639 return add_mapping_to_enumeration_field_class(fc
, label
,
640 (const void *) range_set
);
644 void destroy_real_field_class(struct bt_object
*obj
)
647 BT_LIB_LOGD("Destroying real field class object: %!+F", obj
);
651 struct bt_field_class
*bt_field_class_real_create(bt_trace_class
*trace_class
)
653 struct bt_field_class_real
*real_fc
= NULL
;
655 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
656 BT_LOGD_STR("Creating default real field class object.");
657 real_fc
= g_new0(struct bt_field_class_real
, 1);
659 BT_LIB_LOGE_APPEND_CAUSE("Failed to allocate one real field class.");
663 init_field_class((void *) real_fc
, BT_FIELD_CLASS_TYPE_REAL
,
664 destroy_real_field_class
);
665 BT_LIB_LOGD("Created real field class object: %!+F", real_fc
);
669 BT_OBJECT_PUT_REF_AND_RESET(real_fc
);
672 return (void *) real_fc
;
675 bt_bool
bt_field_class_real_is_single_precision(const struct bt_field_class
*fc
)
677 const struct bt_field_class_real
*real_fc
= (const void *) fc
;
679 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
680 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_REAL
, "Field class");
681 return real_fc
->is_single_precision
;
684 void bt_field_class_real_set_is_single_precision(struct bt_field_class
*fc
,
685 bt_bool is_single_precision
)
687 struct bt_field_class_real
*real_fc
= (void *) fc
;
689 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
690 BT_ASSERT_PRE_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_REAL
, "Field class");
691 BT_ASSERT_PRE_DEV_FC_HOT(fc
, "Field class");
692 real_fc
->is_single_precision
= (bool) is_single_precision
;
693 BT_LIB_LOGD("Set real field class's \"is single precision\" property: "
698 int init_named_field_classes_container(
699 struct bt_field_class_named_field_class_container
*fc
,
700 enum bt_field_class_type type
,
701 bt_object_release_func fc_release_func
,
702 GDestroyNotify named_fc_destroy_func
)
706 init_field_class((void *) fc
, type
, fc_release_func
);
707 fc
->named_fcs
= g_ptr_array_new_with_free_func(named_fc_destroy_func
);
708 if (!fc
->named_fcs
) {
709 BT_LIB_LOGE_APPEND_CAUSE("Failed to allocate a GPtrArray.");
714 fc
->name_to_index
= g_hash_table_new(g_str_hash
, g_str_equal
);
715 if (!fc
->name_to_index
) {
716 BT_LIB_LOGE_APPEND_CAUSE("Failed to allocate a GHashTable.");
726 void finalize_named_field_class(struct bt_named_field_class
*named_fc
)
729 BT_LIB_LOGD("Finalizing named field class: "
730 "addr=%p, name=\"%s\", %![fc-]+F",
731 named_fc
, named_fc
->name
? named_fc
->name
->str
: NULL
,
734 if (named_fc
->name
) {
735 g_string_free(named_fc
->name
, TRUE
);
736 named_fc
->name
= NULL
;
739 BT_LOGD_STR("Putting named field class's field class.");
740 BT_OBJECT_PUT_REF_AND_RESET(named_fc
->fc
);
744 void destroy_named_field_class(gpointer ptr
)
747 finalize_named_field_class(ptr
);
753 void destroy_variant_with_selector_option(gpointer ptr
)
755 struct bt_field_class_variant_with_selector_option
*opt
= ptr
;
758 finalize_named_field_class(&opt
->common
);
759 BT_OBJECT_PUT_REF_AND_RESET(opt
->range_set
);
765 void finalize_named_field_classes_container(
766 struct bt_field_class_named_field_class_container
*fc
)
771 g_ptr_array_free(fc
->named_fcs
, TRUE
);
772 fc
->named_fcs
= NULL
;
776 if (fc
->name_to_index
) {
777 g_hash_table_destroy(fc
->name_to_index
);
778 fc
->name_to_index
= NULL
;
783 void destroy_structure_field_class(struct bt_object
*obj
)
786 BT_LIB_LOGD("Destroying structure field class object: %!+F", obj
);
787 finalize_named_field_classes_container((void *) obj
);
791 struct bt_field_class
*bt_field_class_structure_create(
792 bt_trace_class
*trace_class
)
795 struct bt_field_class_structure
*struct_fc
= NULL
;
797 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
798 BT_LOGD_STR("Creating default structure field class object.");
799 struct_fc
= g_new0(struct bt_field_class_structure
, 1);
801 BT_LIB_LOGE_APPEND_CAUSE(
802 "Failed to allocate one structure field class.");
806 ret
= init_named_field_classes_container((void *) struct_fc
,
807 BT_FIELD_CLASS_TYPE_STRUCTURE
, destroy_structure_field_class
,
808 destroy_named_field_class
);
810 /* init_named_field_classes_container() logs errors */
814 BT_LIB_LOGD("Created structure field class object: %!+F", struct_fc
);
818 BT_OBJECT_PUT_REF_AND_RESET(struct_fc
);
821 return (void *) struct_fc
;
825 int init_named_field_class(struct bt_named_field_class
*named_fc
,
826 const char *name
, struct bt_field_class
*fc
)
828 int status
= BT_FUNC_STATUS_OK
;
833 named_fc
->name
= g_string_new(name
);
834 if (!named_fc
->name
) {
835 BT_LIB_LOGE_APPEND_CAUSE("Failed to allocate a GString.");
836 status
= BT_FUNC_STATUS_MEMORY_ERROR
;
841 bt_object_get_no_null_check(named_fc
->fc
);
842 bt_named_field_class_freeze(named_fc
);
849 struct bt_named_field_class
*create_named_field_class(const char *name
,
850 struct bt_field_class
*fc
)
852 struct bt_named_field_class
*named_fc
= g_new0(
853 struct bt_named_field_class
, 1);
856 BT_LIB_LOGE_APPEND_CAUSE(
857 "Failed to allocate a named field class.");
861 if (init_named_field_class(named_fc
, name
, fc
)) {
862 /* init_named_field_class() logs errors */
869 destroy_named_field_class(named_fc
);
877 struct bt_field_class_variant_with_selector_option
*
878 create_variant_with_selector_option(
879 const char *name
, struct bt_field_class
*fc
,
880 const struct bt_integer_range_set
*range_set
)
882 struct bt_field_class_variant_with_selector_option
*opt
= g_new0(
883 struct bt_field_class_variant_with_selector_option
, 1);
885 BT_ASSERT(range_set
);
888 BT_LIB_LOGE_APPEND_CAUSE(
889 "Failed to allocate a named field class.");
893 if (init_named_field_class(&opt
->common
, name
, fc
)) {
897 opt
->range_set
= range_set
;
898 bt_object_get_no_null_check(opt
->range_set
);
899 bt_integer_range_set_freeze(range_set
);
903 destroy_variant_with_selector_option(opt
);
911 int append_named_field_class_to_container_field_class(
912 struct bt_field_class_named_field_class_container
*container_fc
,
913 struct bt_named_field_class
*named_fc
)
915 BT_ASSERT(container_fc
);
917 BT_ASSERT_PRE_DEV_FC_HOT(container_fc
, "Field class");
918 BT_ASSERT_PRE(!bt_g_hash_table_contains(container_fc
->name_to_index
,
919 named_fc
->name
->str
),
920 "Duplicate member/option name in structure/variant field class: "
921 "%![container-fc-]+F, name=\"%s\"", container_fc
,
922 named_fc
->name
->str
);
923 g_ptr_array_add(container_fc
->named_fcs
, named_fc
);
924 g_hash_table_insert(container_fc
->name_to_index
, named_fc
->name
->str
,
925 GUINT_TO_POINTER(container_fc
->named_fcs
->len
- 1));
926 return BT_FUNC_STATUS_OK
;
929 enum bt_field_class_structure_append_member_status
930 bt_field_class_structure_append_member(
931 struct bt_field_class
*fc
, const char *name
,
932 struct bt_field_class
*member_fc
)
934 enum bt_field_class_structure_append_member_status status
;
935 struct bt_named_field_class
*named_fc
= NULL
;
937 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
938 BT_ASSERT_PRE_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STRUCTURE
,
940 named_fc
= create_named_field_class(name
, member_fc
);
942 /* create_named_field_class() logs errors */
943 status
= BT_FUNC_STATUS_MEMORY_ERROR
;
947 status
= append_named_field_class_to_container_field_class((void *) fc
,
949 if (status
== BT_FUNC_STATUS_OK
) {
950 /* Moved to the container */
958 uint64_t bt_field_class_structure_get_member_count(
959 const struct bt_field_class
*fc
)
961 struct bt_field_class_structure
*struct_fc
= (void *) fc
;
963 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
964 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STRUCTURE
,
966 return (uint64_t) struct_fc
->common
.named_fcs
->len
;
970 struct bt_named_field_class
*
971 borrow_named_field_class_from_container_field_class_at_index(
972 struct bt_field_class_named_field_class_container
*fc
,
976 BT_ASSERT_PRE_DEV_VALID_INDEX(index
, fc
->named_fcs
->len
);
977 return fc
->named_fcs
->pdata
[index
];
980 const struct bt_field_class_structure_member
*
981 bt_field_class_structure_borrow_member_by_index_const(
982 const struct bt_field_class
*fc
, uint64_t index
)
984 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
985 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STRUCTURE
,
987 return (const void *)
988 borrow_named_field_class_from_container_field_class_at_index(
992 struct bt_field_class_structure_member
*
993 bt_field_class_structure_borrow_member_by_index(
994 struct bt_field_class
*fc
, uint64_t index
)
996 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
997 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STRUCTURE
,
1000 borrow_named_field_class_from_container_field_class_at_index(
1001 (void *) fc
, index
);
1005 struct bt_named_field_class
*
1006 borrow_named_field_class_from_container_field_class_by_name(
1007 struct bt_field_class_named_field_class_container
*fc
,
1010 struct bt_named_field_class
*named_fc
= NULL
;
1015 BT_ASSERT_PRE_DEV_NON_NULL(name
, "Name");
1016 if (!g_hash_table_lookup_extended(fc
->name_to_index
, name
, &orig_key
,
1021 named_fc
= fc
->named_fcs
->pdata
[GPOINTER_TO_UINT(value
)];
1027 const struct bt_field_class_structure_member
*
1028 bt_field_class_structure_borrow_member_by_name_const(
1029 const struct bt_field_class
*fc
, const char *name
)
1031 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1032 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STRUCTURE
,
1034 return (const void *)
1035 borrow_named_field_class_from_container_field_class_by_name(
1039 struct bt_field_class_structure_member
*
1040 bt_field_class_structure_borrow_member_by_name(
1041 struct bt_field_class
*fc
, const char *name
)
1043 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1044 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STRUCTURE
,
1047 borrow_named_field_class_from_container_field_class_by_name(
1051 const char *bt_field_class_structure_member_get_name(
1052 const struct bt_field_class_structure_member
*member
)
1054 const struct bt_named_field_class
*named_fc
= (const void *) member
;
1056 BT_ASSERT_PRE_DEV_NON_NULL(member
, "Structure field class member");
1057 return named_fc
->name
->str
;
1060 const struct bt_field_class
*
1061 bt_field_class_structure_member_borrow_field_class_const(
1062 const struct bt_field_class_structure_member
*member
)
1064 const struct bt_named_field_class
*named_fc
= (const void *) member
;
1066 BT_ASSERT_PRE_DEV_NON_NULL(member
, "Structure field class member");
1067 return named_fc
->fc
;
1071 void destroy_option_field_class(struct bt_object
*obj
)
1073 struct bt_field_class_option
*fc
= (void *) obj
;
1076 BT_LIB_LOGD("Destroying option field class object: %!+F", fc
);
1077 BT_LOGD_STR("Putting content field class.");
1078 BT_OBJECT_PUT_REF_AND_RESET(fc
->content_fc
);
1079 BT_LOGD_STR("Putting selector field path.");
1080 BT_OBJECT_PUT_REF_AND_RESET(fc
->selector_field_path
);
1081 BT_LOGD_STR("Putting selector field class.");
1082 BT_OBJECT_PUT_REF_AND_RESET(fc
->selector_fc
);
1086 struct bt_field_class
*bt_field_class_option_create(bt_trace_class
*trace_class
,
1087 bt_field_class
*content_fc
, bt_field_class
*selector_fc
)
1089 struct bt_field_class_option
*opt_fc
= NULL
;
1091 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
1092 BT_ASSERT_PRE_NON_NULL(content_fc
, "Content field class");
1093 BT_LIB_LOGD("Creating option field class: "
1094 "%![content-fc-]+F, %![sel-fc-]+F", content_fc
, selector_fc
);
1095 opt_fc
= g_new0(struct bt_field_class_option
, 1);
1097 BT_LIB_LOGE_APPEND_CAUSE(
1098 "Failed to allocate one option field class.");
1102 init_field_class((void *) opt_fc
, BT_FIELD_CLASS_TYPE_OPTION
,
1103 destroy_option_field_class
);
1104 opt_fc
->content_fc
= content_fc
;
1105 bt_object_get_no_null_check(opt_fc
->content_fc
);
1106 bt_field_class_freeze(opt_fc
->content_fc
);
1109 BT_ASSERT_PRE_FC_HAS_ID(selector_fc
, BT_FIELD_CLASS_TYPE_BOOL
,
1110 "Selector field class");
1111 opt_fc
->selector_fc
= selector_fc
;
1112 bt_object_get_no_null_check(opt_fc
->selector_fc
);
1113 bt_field_class_freeze(selector_fc
);
1116 BT_LIB_LOGD("Created option field class object: "
1117 "%![opt-fc-]+F, %![sel-fc-]+F", opt_fc
, selector_fc
);
1121 BT_OBJECT_PUT_REF_AND_RESET(opt_fc
);
1124 return (void *) opt_fc
;
1127 const struct bt_field_class
*bt_field_class_option_borrow_field_class_const(
1128 const struct bt_field_class
*fc
)
1130 struct bt_field_class_option
*opt_fc
= (void *) fc
;
1132 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
1133 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_OPTION
,
1135 return opt_fc
->content_fc
;
1138 const struct bt_field_path
*
1139 bt_field_class_option_borrow_selector_field_path_const(
1140 const struct bt_field_class
*fc
)
1142 struct bt_field_class_option
*opt_fc
= (void *) fc
;
1144 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
1145 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_OPTION
,
1147 return opt_fc
->selector_field_path
;
1151 void finalize_variant_field_class(struct bt_field_class_variant
*var_fc
)
1154 BT_LIB_LOGD("Finalizing variant field class object: %!+F", var_fc
);
1155 finalize_named_field_classes_container((void *) var_fc
);
1159 void destroy_variant_field_class(struct bt_object
*obj
)
1161 struct bt_field_class_variant
*fc
= (void *) obj
;
1164 finalize_variant_field_class(fc
);
1169 void destroy_variant_with_selector_field_class(struct bt_object
*obj
)
1171 struct bt_field_class_variant_with_selector
*fc
= (void *) obj
;
1174 finalize_variant_field_class(&fc
->common
);
1175 BT_LOGD_STR("Putting selector field path.");
1176 BT_OBJECT_PUT_REF_AND_RESET(fc
->selector_field_path
);
1177 BT_LOGD_STR("Putting selector field class.");
1178 BT_OBJECT_PUT_REF_AND_RESET(fc
->selector_fc
);
1182 struct bt_field_class
*bt_field_class_variant_create(
1183 bt_trace_class
*trace_class
, bt_field_class
*selector_fc
)
1186 struct bt_field_class_variant
*var_fc
= NULL
;
1187 struct bt_field_class_variant_with_selector
*var_with_sel_fc
= NULL
;
1188 enum bt_field_class_type fc_type
;
1190 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
1193 BT_ASSERT_PRE_FC_IS_INT(selector_fc
, "Selector field class");
1196 BT_LIB_LOGD("Creating default variant field class: %![sel-fc-]+F",
1200 var_with_sel_fc
= g_new0(
1201 struct bt_field_class_variant_with_selector
, 1);
1202 if (!var_with_sel_fc
) {
1203 BT_LIB_LOGE_APPEND_CAUSE(
1204 "Failed to allocate one variant field class with selector.");
1208 if (selector_fc
->type
== BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER
||
1209 selector_fc
->type
== BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION
) {
1210 fc_type
= BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR
;
1212 fc_type
= BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
;
1215 ret
= init_named_field_classes_container(
1216 (void *) var_with_sel_fc
, fc_type
,
1217 destroy_variant_with_selector_field_class
,
1218 destroy_variant_with_selector_option
);
1220 /* init_named_field_classes_container() logs errors */
1224 var_with_sel_fc
->selector_fc
= selector_fc
;
1225 bt_object_get_no_null_check(var_with_sel_fc
->selector_fc
);
1226 bt_field_class_freeze(selector_fc
);
1227 var_fc
= (void *) var_with_sel_fc
;
1229 var_fc
= g_new0(struct bt_field_class_variant
, 1);
1231 BT_LIB_LOGE_APPEND_CAUSE(
1232 "Failed to allocate one variant field class without selector.");
1236 ret
= init_named_field_classes_container((void *) var_fc
,
1237 BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR
,
1238 destroy_variant_field_class
, destroy_named_field_class
);
1240 /* init_named_field_classes_container() logs errors */
1246 BT_LIB_LOGD("Created default variant field class with selector object: "
1247 "%![var-fc-]+F, %![sel-fc-]+F", var_fc
, selector_fc
);
1251 BT_OBJECT_PUT_REF_AND_RESET(var_fc
);
1254 return (void *) var_fc
;
1257 enum bt_field_class_variant_without_selector_append_option_status
1258 bt_field_class_variant_without_selector_append_option(struct bt_field_class
*fc
,
1259 const char *name
, struct bt_field_class
*option_fc
)
1261 enum bt_field_class_variant_without_selector_append_option_status status
;
1262 struct bt_named_field_class
*named_fc
= NULL
;
1264 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
1265 BT_ASSERT_PRE_NON_NULL(name
, "Name");
1266 BT_ASSERT_PRE_NON_NULL(option_fc
, "Option field class");
1267 BT_ASSERT_PRE_FC_HAS_ID(fc
,
1268 BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR
, "Field class");
1269 named_fc
= create_named_field_class(name
, option_fc
);
1271 /* create_named_field_class() logs errors */
1272 status
= BT_FUNC_STATUS_MEMORY_ERROR
;
1276 status
= append_named_field_class_to_container_field_class((void *) fc
,
1278 if (status
== BT_FUNC_STATUS_OK
) {
1279 /* Moved to the container */
1285 destroy_named_field_class(named_fc
);
1292 int ranges_overlap(GPtrArray
*var_fc_opts
, const struct bt_integer_range_set
*range_set
,
1293 bool is_signed
, bool *has_overlap
)
1295 int status
= BT_FUNC_STATUS_OK
;
1296 struct bt_integer_range_set
*full_range_set
;
1299 *has_overlap
= false;
1302 * Build a single range set with all the ranges and test for
1306 full_range_set
= (void *) bt_integer_range_set_signed_create();
1308 full_range_set
= (void *) bt_integer_range_set_unsigned_create();
1311 if (!full_range_set
) {
1312 BT_LOGE_STR("Failed to create a range set.");
1313 status
= BT_FUNC_STATUS_MEMORY_ERROR
;
1317 /* Add existing option ranges */
1318 for (i
= 0; i
< var_fc_opts
->len
; i
++) {
1319 struct bt_field_class_variant_with_selector_option
*opt
=
1320 var_fc_opts
->pdata
[i
];
1323 for (j
= 0; j
< opt
->range_set
->ranges
->len
; j
++) {
1324 struct bt_integer_range
*range
= BT_INTEGER_RANGE_SET_RANGE_AT_INDEX(
1328 status
= bt_integer_range_set_signed_add_range(
1329 (void *) full_range_set
, range
->lower
.i
,
1332 status
= bt_integer_range_set_unsigned_add_range(
1333 (void *) full_range_set
, range
->lower
.u
,
1343 /* Add new ranges */
1344 for (i
= 0; i
< range_set
->ranges
->len
; i
++) {
1345 struct bt_integer_range
*range
= BT_INTEGER_RANGE_SET_RANGE_AT_INDEX(
1349 status
= bt_integer_range_set_signed_add_range(
1350 (void *) full_range_set
, range
->lower
.i
,
1353 status
= bt_integer_range_set_unsigned_add_range(
1354 (void *) full_range_set
, range
->lower
.u
,
1363 /* Check overlaps */
1365 *has_overlap
= bt_integer_range_set_signed_has_overlaps(full_range_set
);
1367 *has_overlap
= bt_integer_range_set_unsigned_has_overlaps(
1372 bt_object_put_ref(full_range_set
);
1377 int append_option_to_variant_with_selector_field_class(
1378 struct bt_field_class
*fc
, const char *name
,
1379 struct bt_field_class
*option_fc
,
1380 const struct bt_integer_range_set
*range_set
,
1381 enum bt_field_class_type expected_type
)
1384 struct bt_field_class_variant_with_selector
*var_fc
= (void *) fc
;
1385 struct bt_field_class_variant_with_selector_option
*opt
= NULL
;
1388 BT_ASSERT_PRE_NON_NULL(fc
, "Field class");
1389 BT_ASSERT_PRE_NON_NULL(name
, "Name");
1390 BT_ASSERT_PRE_NON_NULL(option_fc
, "Option field class");
1391 BT_ASSERT_PRE_NON_NULL(range_set
, "Integer range set");
1392 BT_ASSERT_PRE_FC_HAS_ID(fc
, expected_type
, "Field class");
1393 BT_ASSERT_PRE(range_set
->ranges
->len
> 0,
1394 "Integer range set is empty: %!+R", range_set
);
1395 status
= ranges_overlap(var_fc
->common
.common
.named_fcs
, range_set
,
1396 expected_type
== BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
,
1399 /* ranges_overlap() logs errors */
1403 BT_ASSERT_PRE(!has_overlap
,
1404 "Integer range set's ranges and existing ranges have an overlap: "
1406 opt
= create_variant_with_selector_option(name
, option_fc
, range_set
);
1408 /* create_variant_with_selector_option() logs errors */
1409 status
= BT_FUNC_STATUS_MEMORY_ERROR
;
1413 status
= append_named_field_class_to_container_field_class((void *) fc
,
1415 if (status
== BT_FUNC_STATUS_OK
) {
1416 /* Moved to the container */
1422 destroy_variant_with_selector_option(opt
);
1428 enum bt_field_class_variant_with_selector_append_option_status
1429 bt_field_class_variant_with_selector_unsigned_append_option(
1430 struct bt_field_class
*fc
, const char *name
,
1431 struct bt_field_class
*option_fc
,
1432 const struct bt_integer_range_set_unsigned
*range_set
)
1434 return append_option_to_variant_with_selector_field_class(fc
,
1435 name
, option_fc
, (const void *) range_set
,
1436 BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR
);
1439 enum bt_field_class_variant_with_selector_append_option_status
1440 bt_field_class_variant_with_selector_signed_append_option(
1441 struct bt_field_class
*fc
, const char *name
,
1442 struct bt_field_class
*option_fc
,
1443 const struct bt_integer_range_set_signed
*range_set
)
1445 return append_option_to_variant_with_selector_field_class(fc
,
1446 name
, option_fc
, (const void *) range_set
,
1447 BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
);
1450 uint64_t bt_field_class_variant_get_option_count(const struct bt_field_class
*fc
)
1452 const struct bt_field_class_variant
*var_fc
= (const void *) fc
;
1454 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1455 BT_ASSERT_PRE_DEV_FC_IS_VARIANT(fc
, "Field class");
1456 return (uint64_t) var_fc
->common
.named_fcs
->len
;
1459 const struct bt_field_class_variant_option
*
1460 bt_field_class_variant_borrow_option_by_name_const(
1461 const struct bt_field_class
*fc
, const char *name
)
1463 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1464 BT_ASSERT_PRE_DEV_FC_IS_VARIANT(fc
, "Field class");
1465 return (const void *)
1466 borrow_named_field_class_from_container_field_class_by_name(
1470 const struct bt_field_class_variant_option
*
1471 bt_field_class_variant_borrow_option_by_index_const(
1472 const struct bt_field_class
*fc
, uint64_t index
)
1474 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1475 BT_ASSERT_PRE_DEV_FC_IS_VARIANT(fc
, "Field class");
1476 return (const void *)
1477 borrow_named_field_class_from_container_field_class_at_index(
1478 (void *) fc
, index
);
1481 struct bt_field_class_variant_option
*
1482 bt_field_class_variant_borrow_option_by_name(
1483 struct bt_field_class
*fc
, const char *name
)
1485 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1486 BT_ASSERT_PRE_DEV_FC_IS_VARIANT(fc
, "Field class");
1488 borrow_named_field_class_from_container_field_class_by_name(
1492 struct bt_field_class_variant_option
*
1493 bt_field_class_variant_borrow_option_by_index(
1494 struct bt_field_class
*fc
, uint64_t index
)
1496 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1497 BT_ASSERT_PRE_DEV_FC_IS_VARIANT(fc
, "Field class");
1499 borrow_named_field_class_from_container_field_class_at_index(
1500 (void *) fc
, index
);
1503 const struct bt_field_class_variant_with_selector_unsigned_option
*
1504 bt_field_class_variant_with_selector_unsigned_borrow_option_by_name_const(
1505 const struct bt_field_class
*fc
, const char *name
)
1507 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1508 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
,
1509 BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR
,
1511 return (const void *)
1512 borrow_named_field_class_from_container_field_class_by_name(
1516 const struct bt_field_class_variant_with_selector_unsigned_option
*
1517 bt_field_class_variant_with_selector_unsigned_borrow_option_by_index_const(
1518 const struct bt_field_class
*fc
, uint64_t index
)
1520 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1521 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
,
1522 BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR
,
1524 return (const void *)
1525 borrow_named_field_class_from_container_field_class_at_index(
1526 (void *) fc
, index
);
1529 const struct bt_field_class_variant_with_selector_signed_option
*
1530 bt_field_class_variant_with_selector_signed_borrow_option_by_name_const(
1531 const struct bt_field_class
*fc
, const char *name
)
1533 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1534 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
,
1535 BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
,
1537 return (const void *)
1538 borrow_named_field_class_from_container_field_class_by_name(
1542 const struct bt_field_class_variant_with_selector_signed_option
*
1543 bt_field_class_variant_with_selector_signed_borrow_option_by_index_const(
1544 const struct bt_field_class
*fc
, uint64_t index
)
1546 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1547 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
,
1548 BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
,
1550 return (const void *)
1551 borrow_named_field_class_from_container_field_class_at_index(
1552 (void *) fc
, index
);
1555 const char *bt_field_class_variant_option_get_name(
1556 const struct bt_field_class_variant_option
*option
)
1558 const struct bt_named_field_class
*named_fc
= (const void *) option
;
1560 BT_ASSERT_PRE_DEV_NON_NULL(option
, "Variant field class option");
1561 return named_fc
->name
->str
;
1564 const struct bt_field_class
*
1565 bt_field_class_variant_option_borrow_field_class_const(
1566 const struct bt_field_class_variant_option
*option
)
1568 const struct bt_named_field_class
*named_fc
= (const void *) option
;
1570 BT_ASSERT_PRE_DEV_NON_NULL(option
, "Variant field class option");
1571 return named_fc
->fc
;
1574 const struct bt_integer_range_set_unsigned
*
1575 bt_field_class_variant_with_selector_unsigned_option_borrow_ranges_const(
1576 const struct bt_field_class_variant_with_selector_unsigned_option
*option
)
1578 const struct bt_field_class_variant_with_selector_option
*opt
=
1579 (const void *) option
;
1581 BT_ASSERT_PRE_DEV_NON_NULL(option
, "Variant field class option");
1582 return (const void *) opt
->range_set
;
1585 const struct bt_integer_range_set_signed
*
1586 bt_field_class_variant_with_selector_signed_option_borrow_ranges_const(
1587 const struct bt_field_class_variant_with_selector_signed_option
*option
)
1589 const struct bt_field_class_variant_with_selector_option
*opt
=
1590 (const void *) option
;
1592 BT_ASSERT_PRE_DEV_NON_NULL(option
, "Variant field class option");
1593 return (const void *) opt
->range_set
;
1596 const struct bt_field_path
*
1597 bt_field_class_variant_with_selector_borrow_selector_field_path_const(
1598 const struct bt_field_class
*fc
)
1600 const struct bt_field_class_variant_with_selector
*var_fc
=
1603 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1604 BT_ASSERT_PRE_DEV_FC_IS_VARIANT_WITH_SEL(fc
, "Field class");
1605 return var_fc
->selector_field_path
;
1609 void init_array_field_class(struct bt_field_class_array
*fc
,
1610 enum bt_field_class_type type
, bt_object_release_func release_func
,
1611 struct bt_field_class
*element_fc
)
1613 BT_ASSERT(element_fc
);
1614 init_field_class((void *) fc
, type
, release_func
);
1615 fc
->element_fc
= element_fc
;
1616 bt_object_get_no_null_check(fc
->element_fc
);
1617 bt_field_class_freeze(element_fc
);
1621 void finalize_array_field_class(struct bt_field_class_array
*array_fc
)
1623 BT_ASSERT(array_fc
);
1624 BT_LOGD_STR("Putting element field class.");
1625 BT_OBJECT_PUT_REF_AND_RESET(array_fc
->element_fc
);
1629 void destroy_static_array_field_class(struct bt_object
*obj
)
1632 BT_LIB_LOGD("Destroying static array field class object: %!+F", obj
);
1633 finalize_array_field_class((void *) obj
);
1637 struct bt_field_class
*
1638 bt_field_class_array_static_create(bt_trace_class
*trace_class
,
1639 struct bt_field_class
*element_fc
, uint64_t length
)
1641 struct bt_field_class_array_static
*array_fc
= NULL
;
1643 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
1644 BT_ASSERT_PRE_NON_NULL(element_fc
, "Element field class");
1645 BT_LOGD_STR("Creating default static array field class object.");
1646 array_fc
= g_new0(struct bt_field_class_array_static
, 1);
1648 BT_LIB_LOGE_APPEND_CAUSE(
1649 "Failed to allocate one static array field class.");
1653 init_array_field_class((void *) array_fc
, BT_FIELD_CLASS_TYPE_STATIC_ARRAY
,
1654 destroy_static_array_field_class
, element_fc
);
1655 array_fc
->length
= length
;
1656 BT_LIB_LOGD("Created static array field class object: %!+F", array_fc
);
1660 BT_OBJECT_PUT_REF_AND_RESET(array_fc
);
1663 return (void *) array_fc
;
1666 const struct bt_field_class
*
1667 bt_field_class_array_borrow_element_field_class_const(
1668 const struct bt_field_class
*fc
)
1670 const struct bt_field_class_array
*array_fc
= (const void *) fc
;
1672 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1673 BT_ASSERT_PRE_DEV_FC_IS_ARRAY(fc
, "Field class");
1674 return array_fc
->element_fc
;
1677 struct bt_field_class
*
1678 bt_field_class_array_borrow_element_field_class(struct bt_field_class
*fc
)
1680 struct bt_field_class_array
*array_fc
= (void *) fc
;
1682 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1683 BT_ASSERT_PRE_DEV_FC_IS_ARRAY(fc
, "Field class");
1684 return array_fc
->element_fc
;
1687 uint64_t bt_field_class_array_static_get_length(const struct bt_field_class
*fc
)
1689 const struct bt_field_class_array_static
*array_fc
= (const void *) fc
;
1691 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1692 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_STATIC_ARRAY
,
1694 return (uint64_t) array_fc
->length
;
1698 void destroy_dynamic_array_field_class(struct bt_object
*obj
)
1700 struct bt_field_class_array_dynamic
*fc
= (void *) obj
;
1703 BT_LIB_LOGD("Destroying dynamic array field class object: %!+F", fc
);
1704 finalize_array_field_class((void *) fc
);
1705 BT_LOGD_STR("Putting length field path.");
1706 BT_OBJECT_PUT_REF_AND_RESET(fc
->length_field_path
);
1707 BT_LOGD_STR("Putting length field class.");
1708 BT_OBJECT_PUT_REF_AND_RESET(fc
->length_fc
);
1712 struct bt_field_class
*bt_field_class_array_dynamic_create(
1713 struct bt_trace_class
*trace_class
,
1714 struct bt_field_class
*element_fc
,
1715 struct bt_field_class
*length_fc
)
1717 struct bt_field_class_array_dynamic
*array_fc
= NULL
;
1719 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
1720 BT_ASSERT_PRE_NON_NULL(element_fc
, "Element field class");
1721 BT_LOGD_STR("Creating default dynamic array field class object.");
1722 array_fc
= g_new0(struct bt_field_class_array_dynamic
, 1);
1724 BT_LIB_LOGE_APPEND_CAUSE(
1725 "Failed to allocate one dynamic array field class.");
1729 init_array_field_class((void *) array_fc
,
1730 BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY
,
1731 destroy_dynamic_array_field_class
, element_fc
);
1734 BT_ASSERT_PRE_FC_IS_UNSIGNED_INT(length_fc
,
1735 "Length field class");
1736 array_fc
->length_fc
= length_fc
;
1737 bt_object_get_no_null_check(array_fc
->length_fc
);
1738 bt_field_class_freeze(length_fc
);
1741 BT_LIB_LOGD("Created dynamic array field class object: %!+F", array_fc
);
1745 BT_OBJECT_PUT_REF_AND_RESET(array_fc
);
1748 return (void *) array_fc
;
1751 const struct bt_field_path
*
1752 bt_field_class_array_dynamic_borrow_length_field_path_const(
1753 const struct bt_field_class
*fc
)
1755 const struct bt_field_class_array_dynamic
*seq_fc
= (const void *) fc
;
1757 BT_ASSERT_PRE_DEV_NON_NULL(fc
, "Field class");
1758 BT_ASSERT_PRE_DEV_FC_HAS_ID(fc
, BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY
,
1760 return seq_fc
->length_field_path
;
1764 void destroy_string_field_class(struct bt_object
*obj
)
1767 BT_LIB_LOGD("Destroying string field class object: %!+F", obj
);
1771 struct bt_field_class
*bt_field_class_string_create(bt_trace_class
*trace_class
)
1773 struct bt_field_class_string
*string_fc
= NULL
;
1775 BT_ASSERT_PRE_NON_NULL(trace_class
, "Trace class");
1776 BT_LOGD_STR("Creating default string field class object.");
1777 string_fc
= g_new0(struct bt_field_class_string
, 1);
1779 BT_LIB_LOGE_APPEND_CAUSE(
1780 "Failed to allocate one string field class.");
1784 init_field_class((void *) string_fc
, BT_FIELD_CLASS_TYPE_STRING
,
1785 destroy_string_field_class
);
1786 BT_LIB_LOGD("Created string field class object: %!+F", string_fc
);
1790 BT_OBJECT_PUT_REF_AND_RESET(string_fc
);
1793 return (void *) string_fc
;
1797 void _bt_field_class_freeze(const struct bt_field_class
*c_fc
)
1799 struct bt_field_class
*fc
= (void *) c_fc
;
1802 * Element/member/option field classes are frozen when added to
1809 case BT_FIELD_CLASS_TYPE_STRUCTURE
:
1810 case BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR
:
1811 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR
:
1812 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
:
1814 struct bt_field_class_named_field_class_container
*container_fc
=
1818 for (i
= 0; i
< container_fc
->named_fcs
->len
; i
++) {
1819 bt_named_field_class_freeze(
1820 container_fc
->named_fcs
->pdata
[i
]);
1831 void _bt_named_field_class_freeze(const struct bt_named_field_class
*named_fc
)
1833 BT_ASSERT(named_fc
);
1834 ((struct bt_named_field_class
*) named_fc
)->frozen
= true;
1835 bt_field_class_freeze(named_fc
->fc
);
1839 void bt_field_class_make_part_of_trace_class(const struct bt_field_class
*c_fc
)
1841 struct bt_field_class
*fc
= (void *) c_fc
;
1844 BT_ASSERT_PRE(!fc
->part_of_trace_class
,
1845 "Field class is already part of a trace: %!+F", fc
);
1846 fc
->part_of_trace_class
= true;
1849 case BT_FIELD_CLASS_TYPE_STRUCTURE
:
1850 case BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR
:
1851 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR
:
1852 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR
:
1854 struct bt_field_class_named_field_class_container
*container_fc
=
1858 for (i
= 0; i
< container_fc
->named_fcs
->len
; i
++) {
1859 struct bt_named_field_class
*named_fc
=
1860 container_fc
->named_fcs
->pdata
[i
];
1862 bt_field_class_make_part_of_trace_class(named_fc
->fc
);
1867 case BT_FIELD_CLASS_TYPE_STATIC_ARRAY
:
1868 case BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY
:
1870 struct bt_field_class_array
*array_fc
= (void *) fc
;
1872 bt_field_class_make_part_of_trace_class(array_fc
->element_fc
);
1880 void bt_field_class_get_ref(const struct bt_field_class
*field_class
)
1882 bt_object_get_ref(field_class
);
1885 void bt_field_class_put_ref(const struct bt_field_class
*field_class
)
1887 bt_object_put_ref(field_class
);