lib: add user attributes property to metadata, stream, and trace objects
[babeltrace.git] / src / plugins / lttng-utils / debug-info / trace-ir-metadata-field-class-copy.c
CommitLineData
ca9f27f3
FD
1/*
2 * Babeltrace - Trace IR field copy
3 *
4 * Copyright (c) 2015-2019 EfficiOS Inc. and Linux Foundation
5 * Copyright (c) 2018 Philippe Proulx <pproulx@efficios.com>
6 * Copyright (c) 2019 Francis Deslauriers <francis.deslauriers@efficios.com>
7 *
8 * Permission is hereby granted, free of charge, to any person obtaining a copy
9 * of this software and associated documentation files (the "Software"), to deal
10 * in the Software without restriction, including without limitation the rights
11 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12 * copies of the Software, and to permit persons to whom the Software is
13 * furnished to do so, subject to the following conditions:
14 *
15 * The above copyright notice and this permission notice shall be included in
16 * all copies or substantial portions of the Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
21 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
24 * SOFTWARE.
25 */
26
91bc8451 27#define BT_COMP_LOG_SELF_COMP (md_maps->self_comp)
3a3d15f3 28#define BT_LOG_OUTPUT_LEVEL (md_maps->log_level)
350ad6c1 29#define BT_LOG_TAG "PLUGIN/FLT.LTTNG-UTILS.DEBUG-INFO/TRACE-IR-META-FC-COPY"
d9c39b0a 30#include "logging/comp-logging.h"
ca9f27f3 31
578e048b
MJ
32#include "common/assert.h"
33#include "common/common.h"
34#include "compat/compiler.h"
3fadfbc0 35#include <babeltrace2/babeltrace.h>
ca9f27f3
FD
36
37#include "trace-ir-metadata-copy.h"
38#include "trace-ir-metadata-field-class-copy.h"
39
40/*
41 * This fonction walks througth the nested structures field class to resolve a
42 * field path object. A field path is made of indexes inside possibly nested
43 * structures ultimately leading to a field class.
44 */
45static
3a3d15f3
PP
46const bt_field_class *walk_field_path(struct trace_ir_metadata_maps *md_maps,
47 const bt_field_path *fp, const bt_field_class *fc)
ca9f27f3 48{
66ddcddf 49 uint64_t i, fp_item_count;
ca9f27f3
FD
50 const bt_field_class *curr_fc;
51
52 BT_ASSERT(bt_field_class_get_type(fc) == BT_FIELD_CLASS_TYPE_STRUCTURE);
91bc8451 53 BT_COMP_LOGD("Walking field path on field class: fp-addr=%p, fc-addr=%p",
ca9f27f3
FD
54 fp, fc);
55
66ddcddf 56 fp_item_count = bt_field_path_get_item_count(fp);
ca9f27f3 57 curr_fc = fc;
66ddcddf 58 for (i = 0; i < fp_item_count; i++) {
ca9f27f3 59 bt_field_class_type fc_type = bt_field_class_get_type(curr_fc);
66ddcddf
PP
60 const bt_field_path_item *fp_item =
61 bt_field_path_borrow_item_by_index_const(fp, i);
ca9f27f3
FD
62
63 switch (fc_type) {
64 case BT_FIELD_CLASS_TYPE_STRUCTURE:
1e6fd1d7 65 {
66ddcddf
PP
66 const bt_field_class_structure_member *member;
67
68 BT_ASSERT(bt_field_path_item_get_type(fp_item) ==
69 BT_FIELD_PATH_ITEM_TYPE_INDEX);
70 member = bt_field_class_structure_borrow_member_by_index_const(
71 curr_fc,
72 bt_field_path_item_index_get_index(fp_item));
1e6fd1d7
PP
73 curr_fc = bt_field_class_structure_member_borrow_field_class_const(
74 member);
ca9f27f3 75 break;
1e6fd1d7 76 }
f29ef814
PP
77 case BT_FIELD_CLASS_TYPE_OPTION:
78 {
79 BT_ASSERT(bt_field_path_item_get_type(fp_item) ==
80 BT_FIELD_PATH_ITEM_TYPE_CURRENT_OPTION_CONTENT);
81 curr_fc = bt_field_class_option_borrow_field_class_const(
82 curr_fc);
83 break;
84 }
45c51519
PP
85 case BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR:
86 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR:
87 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR:
1e6fd1d7 88 {
66ddcddf
PP
89 const bt_field_class_variant_option *option;
90
91 BT_ASSERT(bt_field_path_item_get_type(fp_item) ==
92 BT_FIELD_PATH_ITEM_TYPE_INDEX);
93 option = bt_field_class_variant_borrow_option_by_index_const(
94 curr_fc,
95 bt_field_path_item_index_get_index(fp_item));
1e6fd1d7
PP
96 curr_fc = bt_field_class_variant_option_borrow_field_class_const(
97 option);
ca9f27f3 98 break;
1e6fd1d7 99 }
66ddcddf
PP
100 case BT_FIELD_CLASS_TYPE_STATIC_ARRAY:
101 case BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY:
102 {
103 BT_ASSERT(bt_field_path_item_get_type(fp_item) ==
104 BT_FIELD_PATH_ITEM_TYPE_CURRENT_ARRAY_ELEMENT);
105 curr_fc = bt_field_class_array_borrow_element_field_class_const(
106 curr_fc);
107 break;
108 }
ca9f27f3
FD
109 default:
110 abort();
111 }
112 }
113
114 return curr_fc;
115}
116
117static
118const bt_field_class *resolve_field_path_to_field_class(const bt_field_path *fp,
119 struct trace_ir_metadata_maps *md_maps)
120{
121 struct field_class_resolving_context *fc_resolving_ctx;
122 const bt_field_class *fc;
e7ceb9df 123 bt_field_path_scope fp_scope;
ca9f27f3 124
91bc8451 125 BT_COMP_LOGD("Resolving field path: fp-addr=%p", fp);
ca9f27f3
FD
126
127 fc_resolving_ctx = md_maps->fc_resolving_ctx;
128 fp_scope = bt_field_path_get_root_scope(fp);
129
130 switch (fp_scope) {
e7ceb9df 131 case BT_FIELD_PATH_SCOPE_PACKET_CONTEXT:
3a3d15f3
PP
132 fc = walk_field_path(md_maps, fp,
133 fc_resolving_ctx->packet_context);
ca9f27f3 134 break;
e7ceb9df 135 case BT_FIELD_PATH_SCOPE_EVENT_COMMON_CONTEXT:
3a3d15f3
PP
136 fc = walk_field_path(md_maps, fp,
137 fc_resolving_ctx->event_common_context);
ca9f27f3 138 break;
e7ceb9df 139 case BT_FIELD_PATH_SCOPE_EVENT_SPECIFIC_CONTEXT:
3a3d15f3
PP
140 fc = walk_field_path(md_maps, fp,
141 fc_resolving_ctx->event_specific_context);
ca9f27f3 142 break;
e7ceb9df 143 case BT_FIELD_PATH_SCOPE_EVENT_PAYLOAD:
3a3d15f3
PP
144 fc = walk_field_path(md_maps, fp,
145 fc_resolving_ctx->event_payload);
ca9f27f3
FD
146 break;
147 default:
148 abort();
149 }
150
151 return fc;
152}
153
154static inline
155void field_class_integer_set_props(const bt_field_class *input_fc,
156 bt_field_class *output_fc)
157{
158 bt_field_class_integer_set_preferred_display_base(output_fc,
159 bt_field_class_integer_get_preferred_display_base(input_fc));
160 bt_field_class_integer_set_field_value_range(output_fc,
161 bt_field_class_integer_get_field_value_range(input_fc));
162}
163
f7cfbcc3
PP
164static inline
165int field_class_bool_copy(
166 struct trace_ir_metadata_maps *md_maps,
167 const bt_field_class *in_field_class,
168 bt_field_class *out_field_class)
169{
170 BT_COMP_LOGD("Copying content of boolean field class: "
171 "in-fc-addr=%p, out-fc-addr=%p",
172 in_field_class, out_field_class);
173 BT_COMP_LOGD("Copied content of boolean field class: "
174 "in-fc-addr=%p, out-fc-addr=%p",
175 in_field_class, out_field_class);
176 return 0;
177}
178
dc7ac074
PP
179static inline
180int field_class_bit_array_copy(
181 struct trace_ir_metadata_maps *md_maps,
182 const bt_field_class *in_field_class,
183 bt_field_class *out_field_class)
184{
185 BT_COMP_LOGD("Copying content of bit array field class: "
186 "in-fc-addr=%p, out-fc-addr=%p",
187 in_field_class, out_field_class);
188 BT_COMP_LOGD("Copied content of bit array field class: "
189 "in-fc-addr=%p, out-fc-addr=%p",
190 in_field_class, out_field_class);
191 return 0;
192}
193
ca9f27f3
FD
194static inline
195int field_class_unsigned_integer_copy(
196 struct trace_ir_metadata_maps *md_maps,
197 const bt_field_class *in_field_class,
198 bt_field_class *out_field_class)
199{
91bc8451 200 BT_COMP_LOGD("Copying content of unsigned integer field class: "
ca9f27f3
FD
201 "in-fc-addr=%p, out-fc-addr=%p",
202 in_field_class, out_field_class);
203
204 field_class_integer_set_props(in_field_class, out_field_class);
205
91bc8451 206 BT_COMP_LOGD("Copied content of unsigned integer field class: "
ca9f27f3
FD
207 "in-fc-addr=%p, out-fc-addr=%p",
208 in_field_class, out_field_class);
209 return 0;
210}
211
212static inline
213int field_class_signed_integer_copy(
214 struct trace_ir_metadata_maps *md_maps,
215 const bt_field_class *in_field_class,
216 bt_field_class *out_field_class)
217{
91bc8451 218 BT_COMP_LOGD("Copying content of signed integer field class: "
ca9f27f3
FD
219 "in-fc-addr=%p, out-fc-addr=%p",
220 in_field_class, out_field_class);
221
222 field_class_integer_set_props(in_field_class, out_field_class);
223
91bc8451 224 BT_COMP_LOGD("Copied content of signed integer field class: "
ca9f27f3
FD
225 "in-fc-addr=%p, out-fc-addr=%p",
226 in_field_class, out_field_class);
227 return 0;
228}
229
230BT_HIDDEN
231int field_class_unsigned_enumeration_copy(
232 struct trace_ir_metadata_maps *md_maps,
233 const bt_field_class *in_field_class,
234 bt_field_class *out_field_class)
235{
236 uint64_t i, enum_mapping_count;
237 int ret = 0;
238
91bc8451 239 BT_COMP_LOGD("Copying content of unsigned enumeration field class: "
ca9f27f3
FD
240 "in-fc-addr=%p, out-fc-addr=%p",
241 in_field_class, out_field_class);
242
243 /* Copy properties of the inner integer. */
244 field_class_integer_set_props(in_field_class, out_field_class);
245
246 /* Copy all enumeration entries. */
247 enum_mapping_count = bt_field_class_enumeration_get_mapping_count(in_field_class);
248 for (i = 0; i < enum_mapping_count; i++) {
249 const char *label;
45c51519 250 const bt_integer_range_set_unsigned *range_set;
9c08c816 251 const bt_field_class_enumeration_unsigned_mapping *u_mapping;
8f3ccfbc 252 const bt_field_class_enumeration_mapping *mapping;
ca9f27f3 253
9c08c816 254 u_mapping = bt_field_class_enumeration_unsigned_borrow_mapping_by_index_const(
8f3ccfbc 255 in_field_class, i);
9c08c816 256 mapping = bt_field_class_enumeration_unsigned_mapping_as_mapping_const(
8f3ccfbc 257 u_mapping);
45c51519 258 label = bt_field_class_enumeration_mapping_get_label(mapping);
9c08c816 259 range_set = bt_field_class_enumeration_unsigned_mapping_borrow_ranges_const(
45c51519 260 u_mapping);
9c08c816 261 ret = bt_field_class_enumeration_unsigned_add_mapping(
45c51519
PP
262 out_field_class, label, range_set);
263 if (ret) {
264 goto error;
ca9f27f3
FD
265 }
266 }
267
91bc8451 268 BT_COMP_LOGD("Copied content of unsigned enumeration field class: "
ca9f27f3
FD
269 "in-fc-addr=%p, out-fc-addr=%p",
270 in_field_class, out_field_class);
271
272error:
273 return ret;
274}
275
276static inline
277int field_class_signed_enumeration_copy(
278 struct trace_ir_metadata_maps *md_maps,
279 const bt_field_class *in_field_class,
280 bt_field_class *out_field_class)
281{
282 uint64_t i, enum_mapping_count;
283 int ret = 0;
284
91bc8451 285 BT_COMP_LOGD("Copying content of signed enumeration field class: "
ca9f27f3
FD
286 "in-fc-addr=%p, out-fc-addr=%p",
287 in_field_class, out_field_class);
288
289 /* Copy properties of the inner integer. */
290 field_class_integer_set_props(in_field_class, out_field_class);
291
292 /* Copy all enumeration entries. */
293 enum_mapping_count =
294 bt_field_class_enumeration_get_mapping_count(in_field_class);
295 for (i = 0; i < enum_mapping_count; i++) {
296 const char *label;
45c51519 297 const bt_integer_range_set_signed *range_set;
9c08c816 298 const bt_field_class_enumeration_signed_mapping *s_mapping;
8f3ccfbc 299 const bt_field_class_enumeration_mapping *mapping;
ca9f27f3 300
9c08c816 301 s_mapping = bt_field_class_enumeration_signed_borrow_mapping_by_index_const(
8f3ccfbc 302 in_field_class, i);
9c08c816 303 mapping = bt_field_class_enumeration_signed_mapping_as_mapping_const(
45c51519
PP
304 s_mapping);
305 label = bt_field_class_enumeration_mapping_get_label(mapping);
9c08c816 306 range_set = bt_field_class_enumeration_signed_mapping_borrow_ranges_const(
45c51519 307 s_mapping);
9c08c816 308 ret = bt_field_class_enumeration_signed_add_mapping(
45c51519
PP
309 out_field_class, label, range_set);
310 if (ret) {
311 goto error;
ca9f27f3
FD
312 }
313 }
314
91bc8451 315 BT_COMP_LOGD("Copied content of signed enumeration field class: "
ca9f27f3
FD
316 "in-fc-addr=%p, out-fc-addr=%p",
317 in_field_class, out_field_class);
318
319error:
320 return ret;
321}
322
323static inline
324int field_class_real_copy(
325 struct trace_ir_metadata_maps *md_maps,
326 const bt_field_class *in_field_class,
327 bt_field_class *out_field_class)
328{
91bc8451 329 BT_COMP_LOGD("Copying content of real field class: "
ca9f27f3
FD
330 "in-fc-addr=%p, out-fc-addr=%p",
331 in_field_class, out_field_class);
332
333 bt_field_class_real_set_is_single_precision(out_field_class,
334 bt_field_class_real_is_single_precision(in_field_class));
335
91bc8451 336 BT_COMP_LOGD("Copied content real field class: in-fc-addr=%p, "
ca9f27f3
FD
337 "out-fc-addr=%p", in_field_class, out_field_class);
338
339 return 0;
340}
341
342static inline
343int field_class_structure_copy(
344 struct trace_ir_metadata_maps *md_maps,
345 const bt_field_class *in_field_class,
346 bt_field_class *out_field_class)
347{
348 uint64_t i, struct_member_count;
ca9f27f3
FD
349 int ret = 0;
350
91bc8451 351 BT_COMP_LOGD("Copying content of structure field class: "
ca9f27f3
FD
352 "in-fc-addr=%p, out-fc-addr=%p",
353 in_field_class, out_field_class);
354 /* Get the number of member in that struct. */
355 struct_member_count =
356 bt_field_class_structure_get_member_count(in_field_class);
357
358 /* Iterate over all the members of the struct. */
359 for (i = 0; i < struct_member_count; i++) {
1e6fd1d7 360 const bt_field_class_structure_member *member;
ca9f27f3
FD
361 const char *member_name;
362 const bt_field_class *member_fc;
363 bt_field_class *out_member_field_class;
364
1e6fd1d7
PP
365 member = bt_field_class_structure_borrow_member_by_index_const(
366 in_field_class, i);
367 member_fc = bt_field_class_structure_member_borrow_field_class_const(
368 member);
369 member_name = bt_field_class_structure_member_get_name(member);
91bc8451 370 BT_COMP_LOGD("Copying structure field class's field: "
ca9f27f3
FD
371 "index=%" PRId64 ", "
372 "member-fc-addr=%p, field-name=\"%s\"",
373 i, member_fc, member_name);
374
375 out_member_field_class = create_field_class_copy(md_maps,
376 member_fc);
377 if (!out_member_field_class) {
91bc8451 378 BT_COMP_LOGE("Cannot copy structure field class's field: "
ca9f27f3
FD
379 "index=%" PRId64 ", "
380 "field-fc-addr=%p, field-name=\"%s\"",
381 i, member_fc, member_name);
382 ret = -1;
383 goto error;
384 }
385 ret = copy_field_class_content(md_maps, member_fc,
386 out_member_field_class);
387 if (ret) {
388 goto error;
389 }
390
d24d5663
PP
391 if (bt_field_class_structure_append_member(out_field_class,
392 member_name, out_member_field_class) !=
393 BT_FIELD_CLASS_STRUCTURE_APPEND_MEMBER_STATUS_OK) {
91bc8451 394 BT_COMP_LOGE("Cannot append structure field class's field: "
ca9f27f3
FD
395 "index=%" PRId64 ", "
396 "field-fc-addr=%p, field-name=\"%s\"",
397 i, member_fc, member_name);
398 BT_FIELD_CLASS_PUT_REF_AND_RESET(out_member_field_class);
399 ret = -1;
400 goto error;
401 }
402 }
403
91bc8451 404 BT_COMP_LOGD("Copied structure field class: original-fc-addr=%p, copy-fc-addr=%p",
ca9f27f3
FD
405 in_field_class, out_field_class);
406
407error:
408 return ret;
409}
410
411static inline
412int field_class_variant_copy(
413 struct trace_ir_metadata_maps *md_maps,
414 const bt_field_class *in_field_class,
415 bt_field_class *out_field_class)
416{
1ec009b2 417 bt_field_class *out_tag_field_class = NULL;
ca9f27f3 418 uint64_t i, variant_option_count;
45c51519 419 bt_field_class_type fc_type = bt_field_class_get_type(in_field_class);
ca9f27f3
FD
420 int ret = 0;
421
91bc8451 422 BT_COMP_LOGD("Copying content of variant field class: "
ca9f27f3
FD
423 "in-fc-addr=%p, out-fc-addr=%p",
424 in_field_class, out_field_class);
ca9f27f3
FD
425 variant_option_count =
426 bt_field_class_variant_get_option_count(in_field_class);
427 for (i = 0; i < variant_option_count; i++) {
1e6fd1d7 428 const bt_field_class *option_fc;
ca9f27f3
FD
429 const char *option_name;
430 bt_field_class *out_option_field_class;
1e6fd1d7 431 const bt_field_class_variant_option *option;
ca9f27f3 432
1e6fd1d7
PP
433 option = bt_field_class_variant_borrow_option_by_index_const(
434 in_field_class, i);
435 option_fc = bt_field_class_variant_option_borrow_field_class_const(
436 option);
437 option_name = bt_field_class_variant_option_get_name(option);
ca9f27f3 438 out_option_field_class = create_field_class_copy_internal(
1e6fd1d7 439 md_maps, option_fc);
ca9f27f3 440 if (!out_option_field_class) {
91bc8451 441 BT_COMP_LOGE_STR("Cannot copy field class.");
ca9f27f3
FD
442 ret = -1;
443 goto error;
444 }
1e6fd1d7 445 ret = copy_field_class_content_internal(md_maps, option_fc,
ca9f27f3
FD
446 out_option_field_class);
447 if (ret) {
91bc8451 448 BT_COMP_LOGE_STR("Error copying content of option variant "
ca9f27f3
FD
449 "field class'");
450 goto error;
451 }
452
45c51519 453 if (fc_type == BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR) {
9c08c816
PP
454 const bt_field_class_variant_with_selector_unsigned_option *spec_opt =
455 bt_field_class_variant_with_selector_unsigned_borrow_option_by_index_const(
45c51519
PP
456 in_field_class, i);
457 const bt_integer_range_set_unsigned *ranges =
9c08c816 458 bt_field_class_variant_with_selector_unsigned_option_borrow_ranges_const(
45c51519
PP
459 spec_opt);
460
9c08c816 461 if (bt_field_class_variant_with_selector_unsigned_append_option(
45c51519
PP
462 out_field_class, option_name,
463 out_option_field_class, ranges) !=
464 BT_FIELD_CLASS_VARIANT_WITH_SELECTOR_APPEND_OPTION_STATUS_OK) {
465 BT_COMP_LOGE_STR("Cannot append option to variant field class with unsigned selector'");
466 BT_FIELD_CLASS_PUT_REF_AND_RESET(out_tag_field_class);
467 ret = -1;
468 goto error;
469 }
470 } else if (fc_type == BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR) {
9c08c816
PP
471 const bt_field_class_variant_with_selector_signed_option *spec_opt =
472 bt_field_class_variant_with_selector_signed_borrow_option_by_index_const(
45c51519
PP
473 in_field_class, i);
474 const bt_integer_range_set_signed *ranges =
9c08c816 475 bt_field_class_variant_with_selector_signed_option_borrow_ranges_const(
45c51519
PP
476 spec_opt);
477
9c08c816 478 if (bt_field_class_variant_with_selector_signed_append_option(
45c51519
PP
479 out_field_class, option_name,
480 out_option_field_class, ranges) !=
481 BT_FIELD_CLASS_VARIANT_WITH_SELECTOR_APPEND_OPTION_STATUS_OK) {
482 BT_COMP_LOGE_STR("Cannot append option to variant field class with signed selector'");
483 BT_FIELD_CLASS_PUT_REF_AND_RESET(out_tag_field_class);
484 ret = -1;
485 goto error;
486 }
487 } else {
488 BT_ASSERT(fc_type == BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR);
489
490 if (bt_field_class_variant_without_selector_append_option(
491 out_field_class, option_name,
492 out_option_field_class) !=
493 BT_FIELD_CLASS_VARIANT_WITHOUT_SELECTOR_APPEND_OPTION_STATUS_OK) {
494 BT_COMP_LOGE_STR("Cannot append option to variant field class'");
495 BT_FIELD_CLASS_PUT_REF_AND_RESET(out_tag_field_class);
496 ret = -1;
497 goto error;
498 }
ca9f27f3
FD
499 }
500 }
501
91bc8451 502 BT_COMP_LOGD("Copied content of variant field class: in-fc-addr=%p, "
ca9f27f3
FD
503 "out-fc-addr=%p", in_field_class, out_field_class);
504
505error:
506 return ret;
507}
508
509static inline
510int field_class_static_array_copy(
511 struct trace_ir_metadata_maps *md_maps,
512 const bt_field_class *in_field_class,
513 bt_field_class *out_field_class)
514{
91bc8451 515 BT_COMP_LOGD("Copying content of static array field class: in-fc-addr=%p, "
ca9f27f3
FD
516 "out-fc-addr=%p", in_field_class, out_field_class);
517 /*
518 * There is no content to copy. Keep this function call anyway for
519 * logging purposes.
520 */
91bc8451 521 BT_COMP_LOGD("Copied content of static array field class: in-fc-addr=%p, "
ca9f27f3
FD
522 "out-fc-addr=%p", in_field_class, out_field_class);
523
524 return 0;
525}
526
527static inline
528int field_class_dynamic_array_copy(
529 struct trace_ir_metadata_maps *md_maps,
530 const bt_field_class *in_field_class,
531 bt_field_class *out_field_class)
532{
91bc8451 533 BT_COMP_LOGD("Copying content of dynamic array field class: "
ca9f27f3
FD
534 "in-fc-addr=%p, out-fc-addr=%p",
535 in_field_class, out_field_class);
536
1367bc7c
PP
537 /*
538 * There is no content to copy. Keep this function call anyway for
539 * logging purposes.
540 */
91bc8451 541 BT_COMP_LOGD("Copied dynamic array field class: in-fc-addr=%p, "
ca9f27f3
FD
542 "out-fc-addr=%p", in_field_class, out_field_class);
543
1367bc7c 544 return 0;
ca9f27f3
FD
545}
546
f29ef814
PP
547static inline
548int field_class_option_copy(
549 struct trace_ir_metadata_maps *md_maps,
550 const bt_field_class *in_field_class,
551 bt_field_class *out_field_class)
552{
553 BT_COMP_LOGD("Copying content of option field class: "
554 "in-fc-addr=%p, out-fc-addr=%p",
555 in_field_class, out_field_class);
556
557 /*
558 * There is no content to copy. Keep this function call anyway for
559 * logging purposes.
560 */
561 BT_COMP_LOGD("Copied option field class: in-fc-addr=%p, "
562 "out-fc-addr=%p", in_field_class, out_field_class);
563
564 return 0;
565}
566
ca9f27f3
FD
567static inline
568int field_class_string_copy(struct trace_ir_metadata_maps *md_maps,
569 const bt_field_class *in_field_class,
570 bt_field_class *out_field_class)
571{
91bc8451 572 BT_COMP_LOGD("Copying content of string field class: in-fc-addr=%p, "
ca9f27f3
FD
573 "out-fc-addr=%p", in_field_class, out_field_class);
574 /*
575 * There is no content to copy. Keep this function call anyway for
576 * logging purposes.
577 */
91bc8451 578 BT_COMP_LOGD("Copied content of string field class: in-fc-addr=%p, "
ca9f27f3
FD
579 "out-fc-addr=%p", in_field_class, out_field_class);
580
581 return 0;
582}
583
584static
585bt_field_class *copy_field_class_array_element(struct trace_ir_metadata_maps *md_maps,
586 const bt_field_class *in_elem_fc)
587{
588 int ret;
589 bt_field_class *out_elem_fc =
590 create_field_class_copy_internal(md_maps, in_elem_fc);
591 if (!out_elem_fc) {
91bc8451 592 BT_COMP_LOGE("Error creating output elem field class "
ca9f27f3
FD
593 "from input elem field class for static array: "
594 "in-fc-addr=%p", in_elem_fc);
595 goto error;
596 }
597
598 ret = copy_field_class_content_internal(md_maps, in_elem_fc, out_elem_fc);
599 if (ret) {
91bc8451 600 BT_COMP_LOGE("Error creating output elem field class "
ca9f27f3
FD
601 "from input elem field class for static array: "
602 "in-fc-addr=%p", in_elem_fc);
603 BT_FIELD_CLASS_PUT_REF_AND_RESET(out_elem_fc);
604 goto error;
605 }
606
607error:
608 return out_elem_fc;
609}
610
611BT_HIDDEN
612bt_field_class *create_field_class_copy_internal(struct trace_ir_metadata_maps *md_maps,
613 const bt_field_class *in_field_class)
614{
615 bt_field_class *out_field_class = NULL;
45c51519 616 bt_field_class_type fc_type = bt_field_class_get_type(in_field_class);
ca9f27f3 617
91bc8451 618 BT_COMP_LOGD("Creating bare field class based on field class: in-fc-addr=%p",
ca9f27f3
FD
619 in_field_class);
620
45c51519 621 switch (fc_type) {
f7cfbcc3
PP
622 case BT_FIELD_CLASS_TYPE_BOOL:
623 out_field_class = bt_field_class_bool_create(
624 md_maps->output_trace_class);
625 break;
dc7ac074
PP
626 case BT_FIELD_CLASS_TYPE_BIT_ARRAY:
627 out_field_class = bt_field_class_bit_array_create(
628 md_maps->output_trace_class,
629 bt_field_class_bit_array_get_length(
630 in_field_class));
631 break;
ca9f27f3 632 case BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER:
9c08c816 633 out_field_class = bt_field_class_integer_unsigned_create(
ca9f27f3
FD
634 md_maps->output_trace_class);
635 break;
636 case BT_FIELD_CLASS_TYPE_SIGNED_INTEGER:
9c08c816 637 out_field_class = bt_field_class_integer_signed_create(
ca9f27f3
FD
638 md_maps->output_trace_class);
639 break;
640 case BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION:
9c08c816 641 out_field_class = bt_field_class_enumeration_unsigned_create(
ca9f27f3
FD
642 md_maps->output_trace_class);
643 break;
644 case BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION:
9c08c816 645 out_field_class = bt_field_class_enumeration_signed_create(
ca9f27f3
FD
646 md_maps->output_trace_class);
647 break;
648 case BT_FIELD_CLASS_TYPE_REAL:
649 out_field_class = bt_field_class_real_create(
650 md_maps->output_trace_class);
651 break;
652 case BT_FIELD_CLASS_TYPE_STRING:
653 out_field_class = bt_field_class_string_create(
654 md_maps->output_trace_class);
655 break;
656 case BT_FIELD_CLASS_TYPE_STRUCTURE:
657 out_field_class = bt_field_class_structure_create(
658 md_maps->output_trace_class);
659 break;
660 case BT_FIELD_CLASS_TYPE_STATIC_ARRAY:
661 {
662 const bt_field_class *in_elem_fc =
663 bt_field_class_array_borrow_element_field_class_const(
664 in_field_class);
665 uint64_t array_len =
9c08c816 666 bt_field_class_array_static_get_length(in_field_class);
ca9f27f3
FD
667
668 bt_field_class *out_elem_fc = copy_field_class_array_element(
669 md_maps, in_elem_fc);
670 if (!out_elem_fc) {
671 out_field_class = NULL;
672 goto error;
673 }
674
9c08c816 675 out_field_class = bt_field_class_array_static_create(
ca9f27f3
FD
676 md_maps->output_trace_class,
677 out_elem_fc, array_len);
678 break;
679 }
680 case BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY:
681 {
682 const bt_field_class *in_elem_fc =
683 bt_field_class_array_borrow_element_field_class_const(
684 in_field_class);
1367bc7c 685 const bt_field_path *length_fp =
9c08c816 686 bt_field_class_array_dynamic_borrow_length_field_path_const(
1367bc7c
PP
687 in_field_class);
688 bt_field_class *out_length_fc = NULL;
ca9f27f3
FD
689
690 bt_field_class *out_elem_fc = copy_field_class_array_element(
1367bc7c 691 md_maps, in_elem_fc);
ca9f27f3
FD
692 if (!out_elem_fc) {
693 out_field_class = NULL;
694 goto error;
695 }
696
1367bc7c
PP
697 if (length_fp) {
698 const bt_field_class *in_length_fc =
699 resolve_field_path_to_field_class(length_fp,
700 md_maps);
701
702 BT_ASSERT(in_length_fc);
703 out_length_fc = g_hash_table_lookup(md_maps->field_class_map,
704 in_length_fc);
705 BT_ASSERT(out_length_fc);
706 }
707
9c08c816 708 out_field_class = bt_field_class_array_dynamic_create(
ca9f27f3 709 md_maps->output_trace_class,
1367bc7c 710 out_elem_fc, out_length_fc);
ca9f27f3
FD
711 break;
712 }
f29ef814
PP
713 case BT_FIELD_CLASS_TYPE_OPTION:
714 {
715 const bt_field_class *in_content_fc =
716 bt_field_class_option_borrow_field_class_const(
717 in_field_class);
718 const bt_field_path *in_selector_fp =
719 bt_field_class_option_borrow_selector_field_path_const(
720 in_field_class);
721 bt_field_class *out_selector_fc = NULL;
722 bt_field_class *out_content_fc;
723 int ret;
724
725 out_content_fc = create_field_class_copy_internal(
726 md_maps, in_content_fc);
727 if (!out_content_fc) {
728 BT_COMP_LOGE_STR("Cannot copy option's content field class.");
729 goto error;
730 }
731
732 ret = copy_field_class_content_internal(md_maps,
733 in_content_fc, out_content_fc);
734 if (ret) {
735 BT_COMP_LOGE_STR("Error copying content of option's "
736 "content field class");
737 goto error;
738 }
739
740 if (in_selector_fp) {
741 const bt_field_class *in_selector_fc =
742 resolve_field_path_to_field_class(
743 in_selector_fp, md_maps);
744
745 BT_ASSERT(in_selector_fc);
746 out_selector_fc = g_hash_table_lookup(
747 md_maps->field_class_map, in_selector_fc);
748 BT_ASSERT(out_selector_fc);
749 }
750
751 out_field_class = bt_field_class_option_create(
752 md_maps->output_trace_class,
753 out_content_fc, out_selector_fc);
754 break;
755 }
45c51519
PP
756 case BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR:
757 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR:
758 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR:
759 {
760 bt_field_class *out_sel_fc = NULL;
761
762 if (fc_type == BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR ||
763 fc_type == BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR) {
764 const bt_field_class *in_sel_fc;
765 const bt_field_path *sel_fp =
766 bt_field_class_variant_with_selector_borrow_selector_field_path_const(
767 in_field_class);
768
769 BT_ASSERT(sel_fp);
770 in_sel_fc = resolve_field_path_to_field_class(sel_fp,
771 md_maps);
772 BT_ASSERT(in_sel_fc);
773 out_sel_fc = g_hash_table_lookup(
774 md_maps->field_class_map, in_sel_fc);
775 BT_ASSERT(out_sel_fc);
776 }
777
ca9f27f3 778 out_field_class = bt_field_class_variant_create(
45c51519 779 md_maps->output_trace_class, out_sel_fc);
ca9f27f3 780 break;
45c51519 781 }
ca9f27f3
FD
782 default:
783 abort();
784 }
785
786 /*
787 * Add mapping from in_field_class to out_field_class. This simplifies
788 * the resolution of field paths in variant and dynamic array field
789 * classes.
790 */
791 g_hash_table_insert(md_maps->field_class_map,
792 (gpointer) in_field_class, out_field_class);
793
794error:
795 if(out_field_class){
91bc8451 796 BT_COMP_LOGD("Created bare field class based on field class: in-fc-addr=%p, "
ca9f27f3
FD
797 "out-fc-addr=%p", in_field_class, out_field_class);
798 } else {
91bc8451 799 BT_COMP_LOGE("Error creating output field class from input field "
ca9f27f3
FD
800 "class: in-fc-addr=%p", in_field_class);
801 }
802
803 return out_field_class;
804}
805
806BT_HIDDEN
807int copy_field_class_content_internal(
808 struct trace_ir_metadata_maps *md_maps,
809 const bt_field_class *in_field_class,
810 bt_field_class *out_field_class)
811{
812 int ret = 0;
813 switch(bt_field_class_get_type(in_field_class)) {
f7cfbcc3
PP
814 case BT_FIELD_CLASS_TYPE_BOOL:
815 ret = field_class_bool_copy(md_maps,
816 in_field_class, out_field_class);
817 break;
dc7ac074
PP
818 case BT_FIELD_CLASS_TYPE_BIT_ARRAY:
819 ret = field_class_bit_array_copy(md_maps,
820 in_field_class, out_field_class);
821 break;
ca9f27f3
FD
822 case BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER:
823 ret = field_class_unsigned_integer_copy(md_maps,
824 in_field_class, out_field_class);
825 break;
826 case BT_FIELD_CLASS_TYPE_SIGNED_INTEGER:
827 ret = field_class_signed_integer_copy(md_maps,
828 in_field_class, out_field_class);
829 break;
830 case BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION:
831 ret = field_class_unsigned_enumeration_copy(md_maps,
832 in_field_class, out_field_class);
833 break;
834 case BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION:
835 ret = field_class_signed_enumeration_copy(md_maps,
836 in_field_class, out_field_class);
837 break;
838 case BT_FIELD_CLASS_TYPE_REAL:
839 ret = field_class_real_copy(md_maps,
840 in_field_class, out_field_class);
841 break;
842 case BT_FIELD_CLASS_TYPE_STRING:
843 ret = field_class_string_copy(md_maps,
844 in_field_class, out_field_class);
845 break;
846 case BT_FIELD_CLASS_TYPE_STRUCTURE:
847 ret = field_class_structure_copy(md_maps,
848 in_field_class, out_field_class);
849 break;
850 case BT_FIELD_CLASS_TYPE_STATIC_ARRAY:
851 ret = field_class_static_array_copy(md_maps,
852 in_field_class, out_field_class);
853 break;
854 case BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY:
855 ret = field_class_dynamic_array_copy(md_maps,
856 in_field_class, out_field_class);
857 break;
f29ef814
PP
858 case BT_FIELD_CLASS_TYPE_OPTION:
859 ret = field_class_option_copy(md_maps,
860 in_field_class, out_field_class);
861 break;
45c51519
PP
862 case BT_FIELD_CLASS_TYPE_VARIANT_WITHOUT_SELECTOR:
863 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_UNSIGNED_SELECTOR:
864 case BT_FIELD_CLASS_TYPE_VARIANT_WITH_SIGNED_SELECTOR:
ca9f27f3
FD
865 ret = field_class_variant_copy(md_maps,
866 in_field_class, out_field_class);
867 break;
868 default:
869 abort();
870 }
871
872 return ret;
873}
This page took 0.074677 seconds and 4 git commands to generate.