Commit | Line | Data |
---|---|---|
44c440bc | 1 | /* |
0235b0db | 2 | * SPDX-License-Identifier: MIT |
44c440bc | 3 | * |
0235b0db | 4 | * Copyright 2018 Philippe Proulx <pproulx@efficios.com> |
44c440bc PP |
5 | */ |
6 | ||
3fadfbc0 | 7 | #include <babeltrace2/babeltrace.h> |
91d81473 | 8 | #include "common/macros.h" |
578e048b | 9 | #include "common/assert.h" |
44c440bc | 10 | #include <glib.h> |
c4f23e30 | 11 | #include <stdbool.h> |
44c440bc PP |
12 | #include <stdint.h> |
13 | #include <string.h> | |
14 | #include <inttypes.h> | |
15 | ||
087cd0f5 | 16 | #include "ctf-meta-visitors.hpp" |
44c440bc | 17 | |
83ebb7f1 | 18 | struct ctx { |
f7b785ac | 19 | bt_self_component *self_comp; |
83ebb7f1 PP |
20 | bt_trace_class *ir_tc; |
21 | bt_stream_class *ir_sc; | |
22 | struct ctf_trace_class *tc; | |
23 | struct ctf_stream_class *sc; | |
24 | struct ctf_event_class *ec; | |
25 | enum ctf_scope scope; | |
26 | }; | |
27 | ||
44c440bc | 28 | static inline |
83ebb7f1 PP |
29 | bt_field_class *ctf_field_class_to_ir(struct ctx *ctx, |
30 | struct ctf_field_class *fc); | |
44c440bc PP |
31 | |
32 | static inline | |
5cd6d0e5 | 33 | void ctf_field_class_int_set_props(struct ctf_field_class_int *fc, |
b19ff26f | 34 | bt_field_class *ir_fc) |
44c440bc | 35 | { |
40f4ba76 | 36 | bt_field_class_integer_set_field_value_range(ir_fc, |
e5be10ef | 37 | fc->base.size); |
40f4ba76 | 38 | bt_field_class_integer_set_preferred_display_base(ir_fc, |
5cd6d0e5 | 39 | fc->disp_base); |
44c440bc PP |
40 | } |
41 | ||
42 | static inline | |
83ebb7f1 | 43 | bt_field_class *ctf_field_class_int_to_ir(struct ctx *ctx, |
e5be10ef | 44 | struct ctf_field_class_int *fc) |
44c440bc | 45 | { |
b19ff26f | 46 | bt_field_class *ir_fc; |
44c440bc | 47 | |
5cd6d0e5 | 48 | if (fc->is_signed) { |
9c08c816 | 49 | ir_fc = bt_field_class_integer_signed_create(ctx->ir_tc); |
44c440bc | 50 | } else { |
9c08c816 | 51 | ir_fc = bt_field_class_integer_unsigned_create(ctx->ir_tc); |
44c440bc PP |
52 | } |
53 | ||
5cd6d0e5 PP |
54 | BT_ASSERT(ir_fc); |
55 | ctf_field_class_int_set_props(fc, ir_fc); | |
56 | return ir_fc; | |
44c440bc PP |
57 | } |
58 | ||
59 | static inline | |
83ebb7f1 | 60 | bt_field_class *ctf_field_class_enum_to_ir(struct ctx *ctx, |
e5be10ef | 61 | struct ctf_field_class_enum *fc) |
44c440bc PP |
62 | { |
63 | int ret; | |
b19ff26f | 64 | bt_field_class *ir_fc; |
44c440bc PP |
65 | uint64_t i; |
66 | ||
5cd6d0e5 | 67 | if (fc->base.is_signed) { |
9c08c816 | 68 | ir_fc = bt_field_class_enumeration_signed_create(ctx->ir_tc); |
44c440bc | 69 | } else { |
9c08c816 | 70 | ir_fc = bt_field_class_enumeration_unsigned_create(ctx->ir_tc); |
44c440bc PP |
71 | } |
72 | ||
5cd6d0e5 | 73 | BT_ASSERT(ir_fc); |
087cd0f5 | 74 | ctf_field_class_int_set_props(&fc->base, ir_fc); |
44c440bc | 75 | |
5cd6d0e5 PP |
76 | for (i = 0; i < fc->mappings->len; i++) { |
77 | struct ctf_field_class_enum_mapping *mapping = | |
78 | ctf_field_class_enum_borrow_mapping_by_index(fc, i); | |
087cd0f5 SM |
79 | bt_integer_range_set_signed *range_set_signed = NULL; |
80 | bt_integer_range_set_unsigned *range_set_unsigned = NULL; | |
45c51519 | 81 | uint64_t range_i; |
44c440bc | 82 | |
5cd6d0e5 | 83 | if (fc->base.is_signed) { |
087cd0f5 SM |
84 | range_set_signed = bt_integer_range_set_signed_create(); |
85 | BT_ASSERT(range_set_signed); | |
44c440bc | 86 | } else { |
087cd0f5 SM |
87 | range_set_unsigned = bt_integer_range_set_unsigned_create(); |
88 | BT_ASSERT(range_set_unsigned); | |
45c51519 PP |
89 | } |
90 | ||
45c51519 PP |
91 | for (range_i = 0; range_i < mapping->ranges->len; range_i++) { |
92 | struct ctf_range *range = | |
93 | ctf_field_class_enum_mapping_borrow_range_by_index( | |
94 | mapping, range_i); | |
95 | ||
96 | if (fc->base.is_signed) { | |
97 | ret = bt_integer_range_set_signed_add_range( | |
087cd0f5 | 98 | range_set_signed, range->lower.i, |
45c51519 PP |
99 | range->upper.i); |
100 | } else { | |
101 | ret = bt_integer_range_set_unsigned_add_range( | |
087cd0f5 | 102 | range_set_unsigned, range->lower.u, |
45c51519 PP |
103 | range->upper.u); |
104 | } | |
105 | ||
106 | BT_ASSERT(ret == 0); | |
107 | } | |
108 | ||
109 | if (fc->base.is_signed) { | |
9c08c816 | 110 | ret = bt_field_class_enumeration_signed_add_mapping( |
087cd0f5 SM |
111 | ir_fc, mapping->label->str, range_set_signed); |
112 | BT_INTEGER_RANGE_SET_SIGNED_PUT_REF_AND_RESET(range_set_signed); | |
45c51519 | 113 | } else { |
9c08c816 | 114 | ret = bt_field_class_enumeration_unsigned_add_mapping( |
087cd0f5 SM |
115 | ir_fc, mapping->label->str, range_set_unsigned); |
116 | BT_INTEGER_RANGE_SET_UNSIGNED_PUT_REF_AND_RESET(range_set_unsigned); | |
44c440bc PP |
117 | } |
118 | ||
119 | BT_ASSERT(ret == 0); | |
120 | } | |
121 | ||
5cd6d0e5 | 122 | return ir_fc; |
44c440bc PP |
123 | } |
124 | ||
125 | static inline | |
83ebb7f1 | 126 | bt_field_class *ctf_field_class_float_to_ir(struct ctx *ctx, |
5cd6d0e5 | 127 | struct ctf_field_class_float *fc) |
44c440bc | 128 | { |
b19ff26f | 129 | bt_field_class *ir_fc; |
44c440bc | 130 | |
5cd6d0e5 | 131 | if (fc->base.size == 32) { |
fe4df857 FD |
132 | ir_fc = bt_field_class_real_single_precision_create(ctx->ir_tc); |
133 | } else { | |
134 | ir_fc = bt_field_class_real_double_precision_create(ctx->ir_tc); | |
44c440bc | 135 | } |
fe4df857 | 136 | BT_ASSERT(ir_fc); |
44c440bc | 137 | |
5cd6d0e5 | 138 | return ir_fc; |
44c440bc PP |
139 | } |
140 | ||
141 | static inline | |
83ebb7f1 | 142 | bt_field_class *ctf_field_class_string_to_ir(struct ctx *ctx, |
5cd6d0e5 | 143 | struct ctf_field_class_string *fc) |
44c440bc | 144 | { |
83ebb7f1 | 145 | bt_field_class *ir_fc = bt_field_class_string_create(ctx->ir_tc); |
44c440bc | 146 | |
5cd6d0e5 PP |
147 | BT_ASSERT(ir_fc); |
148 | return ir_fc; | |
44c440bc PP |
149 | } |
150 | ||
151 | static inline | |
83ebb7f1 PP |
152 | void translate_struct_field_class_members(struct ctx *ctx, |
153 | struct ctf_field_class_struct *fc, bt_field_class *ir_fc, | |
154 | bool with_header_prefix, | |
155 | struct ctf_field_class_struct *context_fc) | |
44c440bc | 156 | { |
44c440bc | 157 | uint64_t i; |
83ebb7f1 | 158 | int ret; |
44c440bc | 159 | |
5cd6d0e5 PP |
160 | for (i = 0; i < fc->members->len; i++) { |
161 | struct ctf_named_field_class *named_fc = | |
162 | ctf_field_class_struct_borrow_member_by_index(fc, i); | |
b19ff26f | 163 | bt_field_class *member_ir_fc; |
83ebb7f1 | 164 | const char *name = named_fc->name->str; |
44c440bc | 165 | |
5cd6d0e5 | 166 | if (!named_fc->fc->in_ir) { |
44c440bc PP |
167 | continue; |
168 | } | |
169 | ||
83ebb7f1 | 170 | member_ir_fc = ctf_field_class_to_ir(ctx, named_fc->fc); |
5cd6d0e5 | 171 | BT_ASSERT(member_ir_fc); |
83ebb7f1 PP |
172 | ret = bt_field_class_structure_append_member(ir_fc, name, |
173 | member_ir_fc); | |
44c440bc | 174 | BT_ASSERT(ret == 0); |
c5b9b441 | 175 | bt_field_class_put_ref(member_ir_fc); |
44c440bc | 176 | } |
83ebb7f1 | 177 | } |
44c440bc | 178 | |
83ebb7f1 PP |
179 | static inline |
180 | bt_field_class *ctf_field_class_struct_to_ir(struct ctx *ctx, | |
181 | struct ctf_field_class_struct *fc) | |
182 | { | |
183 | bt_field_class *ir_fc = bt_field_class_structure_create(ctx->ir_tc); | |
184 | ||
185 | BT_ASSERT(ir_fc); | |
186 | translate_struct_field_class_members(ctx, fc, ir_fc, false, NULL); | |
5cd6d0e5 | 187 | return ir_fc; |
44c440bc PP |
188 | } |
189 | ||
190 | static inline | |
83ebb7f1 PP |
191 | bt_field_class *borrow_ir_fc_from_field_path(struct ctx *ctx, |
192 | struct ctf_field_path *field_path) | |
44c440bc | 193 | { |
b19ff26f | 194 | bt_field_class *ir_fc = NULL; |
5cd6d0e5 | 195 | struct ctf_field_class *fc = ctf_field_path_borrow_field_class( |
83ebb7f1 | 196 | field_path, ctx->tc, ctx->sc, ctx->ec); |
44c440bc | 197 | |
5cd6d0e5 | 198 | BT_ASSERT(fc); |
44c440bc | 199 | |
5cd6d0e5 PP |
200 | if (fc->in_ir) { |
201 | ir_fc = fc->ir_fc; | |
44c440bc PP |
202 | } |
203 | ||
5cd6d0e5 | 204 | return ir_fc; |
44c440bc PP |
205 | } |
206 | ||
45c51519 | 207 | static inline |
087cd0f5 SM |
208 | const bt_field_class_enumeration_mapping *find_ir_enum_field_class_mapping_by_label( |
209 | const bt_field_class *fc, const char *label, bool is_signed) | |
45c51519 | 210 | { |
087cd0f5 | 211 | const bt_field_class_enumeration_mapping *mapping = NULL; |
45c51519 PP |
212 | uint64_t i; |
213 | ||
214 | for (i = 0; i < bt_field_class_enumeration_get_mapping_count(fc); i++) { | |
215 | const bt_field_class_enumeration_mapping *this_mapping; | |
087cd0f5 SM |
216 | const bt_field_class_enumeration_signed_mapping *signed_this_mapping = NULL; |
217 | const bt_field_class_enumeration_unsigned_mapping *unsigned_this_mapping = NULL; | |
45c51519 PP |
218 | |
219 | if (is_signed) { | |
087cd0f5 | 220 | signed_this_mapping = |
9c08c816 | 221 | bt_field_class_enumeration_signed_borrow_mapping_by_index_const( |
45c51519 | 222 | fc, i); |
087cd0f5 | 223 | BT_ASSERT(signed_this_mapping); |
45c51519 | 224 | this_mapping = |
9c08c816 | 225 | bt_field_class_enumeration_signed_mapping_as_mapping_const( |
087cd0f5 | 226 | signed_this_mapping); |
45c51519 | 227 | } else { |
087cd0f5 | 228 | unsigned_this_mapping = |
9c08c816 | 229 | bt_field_class_enumeration_unsigned_borrow_mapping_by_index_const( |
45c51519 | 230 | fc, i); |
087cd0f5 | 231 | BT_ASSERT(unsigned_this_mapping); |
45c51519 | 232 | this_mapping = |
9c08c816 | 233 | bt_field_class_enumeration_unsigned_mapping_as_mapping_const( |
087cd0f5 | 234 | unsigned_this_mapping); |
45c51519 PP |
235 | } |
236 | ||
237 | BT_ASSERT(this_mapping); | |
45c51519 PP |
238 | |
239 | if (strcmp(bt_field_class_enumeration_mapping_get_label( | |
240 | this_mapping), label) == 0) { | |
087cd0f5 | 241 | mapping = this_mapping; |
45c51519 PP |
242 | goto end; |
243 | } | |
244 | } | |
245 | ||
246 | end: | |
247 | return mapping; | |
248 | } | |
249 | ||
44c440bc | 250 | static inline |
83ebb7f1 PP |
251 | bt_field_class *ctf_field_class_variant_to_ir(struct ctx *ctx, |
252 | struct ctf_field_class_variant *fc) | |
44c440bc PP |
253 | { |
254 | int ret; | |
45c51519 | 255 | bt_field_class *ir_fc; |
44c440bc | 256 | uint64_t i; |
45c51519 | 257 | bt_field_class *ir_tag_fc = NULL; |
83ebb7f1 PP |
258 | |
259 | if (fc->tag_path.root != CTF_SCOPE_PACKET_HEADER && | |
260 | fc->tag_path.root != CTF_SCOPE_EVENT_HEADER) { | |
45c51519 PP |
261 | ir_tag_fc = borrow_ir_fc_from_field_path(ctx, &fc->tag_path); |
262 | BT_ASSERT(ir_tag_fc); | |
83ebb7f1 | 263 | } |
44c440bc | 264 | |
45c51519 PP |
265 | ir_fc = bt_field_class_variant_create(ctx->ir_tc, ir_tag_fc); |
266 | BT_ASSERT(ir_fc); | |
267 | ||
5cd6d0e5 PP |
268 | for (i = 0; i < fc->options->len; i++) { |
269 | struct ctf_named_field_class *named_fc = | |
270 | ctf_field_class_variant_borrow_option_by_index(fc, i); | |
b19ff26f | 271 | bt_field_class *option_ir_fc; |
44c440bc | 272 | |
5cd6d0e5 | 273 | BT_ASSERT(named_fc->fc->in_ir); |
83ebb7f1 | 274 | option_ir_fc = ctf_field_class_to_ir(ctx, named_fc->fc); |
5cd6d0e5 | 275 | BT_ASSERT(option_ir_fc); |
45c51519 PP |
276 | |
277 | if (ir_tag_fc) { | |
278 | /* | |
279 | * At this point the trace IR selector | |
280 | * (enumeration) field class already exists if | |
281 | * the variant is tagged (`ir_tag_fc`). This one | |
282 | * already contains range sets for its mappings, | |
283 | * so we just reuse the same, finding them by | |
284 | * matching a variant field class's option's | |
285 | * _original_ name (with a leading underscore, | |
286 | * possibly) with a selector field class's | |
287 | * mapping name. | |
288 | */ | |
289 | if (fc->tag_fc->base.is_signed) { | |
9c08c816 | 290 | const bt_field_class_enumeration_signed_mapping *mapping = |
087cd0f5 SM |
291 | (bt_field_class_enumeration_signed_mapping *) |
292 | find_ir_enum_field_class_mapping_by_label( | |
293 | ir_tag_fc, | |
294 | named_fc->orig_name->str, true); | |
45c51519 PP |
295 | const bt_integer_range_set_signed *range_set; |
296 | ||
297 | BT_ASSERT(mapping); | |
298 | range_set = | |
9c08c816 | 299 | bt_field_class_enumeration_signed_mapping_borrow_ranges_const( |
45c51519 PP |
300 | mapping); |
301 | BT_ASSERT(range_set); | |
de821fe5 | 302 | ret = bt_field_class_variant_with_selector_field_integer_signed_append_option( |
45c51519 PP |
303 | ir_fc, named_fc->name->str, |
304 | option_ir_fc, range_set); | |
305 | } else { | |
9c08c816 | 306 | const bt_field_class_enumeration_unsigned_mapping *mapping = |
087cd0f5 SM |
307 | (bt_field_class_enumeration_unsigned_mapping *) |
308 | find_ir_enum_field_class_mapping_by_label( | |
309 | ir_tag_fc, | |
310 | named_fc->orig_name->str, | |
311 | false); | |
45c51519 PP |
312 | const bt_integer_range_set_unsigned *range_set; |
313 | ||
314 | BT_ASSERT(mapping); | |
315 | range_set = | |
9c08c816 | 316 | bt_field_class_enumeration_unsigned_mapping_borrow_ranges_const( |
45c51519 PP |
317 | mapping); |
318 | BT_ASSERT(range_set); | |
de821fe5 | 319 | ret = bt_field_class_variant_with_selector_field_integer_unsigned_append_option( |
45c51519 PP |
320 | ir_fc, named_fc->name->str, |
321 | option_ir_fc, range_set); | |
322 | } | |
323 | } else { | |
324 | ret = bt_field_class_variant_without_selector_append_option( | |
325 | ir_fc, named_fc->name->str, option_ir_fc); | |
326 | } | |
327 | ||
44c440bc | 328 | BT_ASSERT(ret == 0); |
c5b9b441 | 329 | bt_field_class_put_ref(option_ir_fc); |
44c440bc PP |
330 | } |
331 | ||
5cd6d0e5 | 332 | return ir_fc; |
44c440bc PP |
333 | } |
334 | ||
335 | static inline | |
83ebb7f1 PP |
336 | bt_field_class *ctf_field_class_array_to_ir(struct ctx *ctx, |
337 | struct ctf_field_class_array *fc) | |
44c440bc | 338 | { |
b19ff26f PP |
339 | bt_field_class *ir_fc; |
340 | bt_field_class *elem_ir_fc; | |
44c440bc | 341 | |
5cd6d0e5 | 342 | if (fc->base.is_text) { |
83ebb7f1 | 343 | ir_fc = bt_field_class_string_create(ctx->ir_tc); |
5cd6d0e5 | 344 | BT_ASSERT(ir_fc); |
44c440bc PP |
345 | goto end; |
346 | } | |
347 | ||
83ebb7f1 | 348 | elem_ir_fc = ctf_field_class_to_ir(ctx, fc->base.elem_fc); |
5cd6d0e5 | 349 | BT_ASSERT(elem_ir_fc); |
9c08c816 | 350 | ir_fc = bt_field_class_array_static_create(ctx->ir_tc, elem_ir_fc, |
e5be10ef | 351 | fc->length); |
5cd6d0e5 | 352 | BT_ASSERT(ir_fc); |
c5b9b441 | 353 | bt_field_class_put_ref(elem_ir_fc); |
44c440bc PP |
354 | |
355 | end: | |
5cd6d0e5 | 356 | return ir_fc; |
44c440bc PP |
357 | } |
358 | ||
359 | static inline | |
83ebb7f1 PP |
360 | bt_field_class *ctf_field_class_sequence_to_ir(struct ctx *ctx, |
361 | struct ctf_field_class_sequence *fc) | |
44c440bc | 362 | { |
b19ff26f PP |
363 | bt_field_class *ir_fc; |
364 | bt_field_class *elem_ir_fc; | |
1367bc7c | 365 | bt_field_class *length_fc = NULL; |
44c440bc | 366 | |
5cd6d0e5 | 367 | if (fc->base.is_text) { |
83ebb7f1 | 368 | ir_fc = bt_field_class_string_create(ctx->ir_tc); |
5cd6d0e5 | 369 | BT_ASSERT(ir_fc); |
44c440bc PP |
370 | goto end; |
371 | } | |
372 | ||
83ebb7f1 | 373 | elem_ir_fc = ctf_field_class_to_ir(ctx, fc->base.elem_fc); |
5cd6d0e5 | 374 | BT_ASSERT(elem_ir_fc); |
83ebb7f1 PP |
375 | |
376 | if (fc->length_path.root != CTF_SCOPE_PACKET_HEADER && | |
377 | fc->length_path.root != CTF_SCOPE_EVENT_HEADER) { | |
1367bc7c PP |
378 | length_fc = borrow_ir_fc_from_field_path(ctx, &fc->length_path); |
379 | BT_ASSERT(length_fc); | |
83ebb7f1 | 380 | } |
44c440bc | 381 | |
9c08c816 | 382 | ir_fc = bt_field_class_array_dynamic_create(ctx->ir_tc, elem_ir_fc, |
1367bc7c PP |
383 | length_fc); |
384 | BT_ASSERT(ir_fc); | |
385 | bt_field_class_put_ref(elem_ir_fc); | |
386 | BT_ASSERT(ir_fc); | |
387 | ||
44c440bc | 388 | end: |
5cd6d0e5 | 389 | return ir_fc; |
44c440bc PP |
390 | } |
391 | ||
392 | static inline | |
83ebb7f1 PP |
393 | bt_field_class *ctf_field_class_to_ir(struct ctx *ctx, |
394 | struct ctf_field_class *fc) | |
44c440bc | 395 | { |
b19ff26f | 396 | bt_field_class *ir_fc = NULL; |
44c440bc | 397 | |
5cd6d0e5 PP |
398 | BT_ASSERT(fc); |
399 | BT_ASSERT(fc->in_ir); | |
44c440bc | 400 | |
864cad70 PP |
401 | switch (fc->type) { |
402 | case CTF_FIELD_CLASS_TYPE_INT: | |
087cd0f5 | 403 | ir_fc = ctf_field_class_int_to_ir(ctx, ctf_field_class_as_int(fc)); |
44c440bc | 404 | break; |
864cad70 | 405 | case CTF_FIELD_CLASS_TYPE_ENUM: |
087cd0f5 | 406 | ir_fc = ctf_field_class_enum_to_ir(ctx, ctf_field_class_as_enum(fc)); |
44c440bc | 407 | break; |
864cad70 | 408 | case CTF_FIELD_CLASS_TYPE_FLOAT: |
087cd0f5 | 409 | ir_fc = ctf_field_class_float_to_ir(ctx, ctf_field_class_as_float(fc)); |
44c440bc | 410 | break; |
864cad70 | 411 | case CTF_FIELD_CLASS_TYPE_STRING: |
087cd0f5 | 412 | ir_fc = ctf_field_class_string_to_ir(ctx, ctf_field_class_as_string(fc)); |
44c440bc | 413 | break; |
864cad70 | 414 | case CTF_FIELD_CLASS_TYPE_STRUCT: |
087cd0f5 | 415 | ir_fc = ctf_field_class_struct_to_ir(ctx, ctf_field_class_as_struct(fc)); |
44c440bc | 416 | break; |
864cad70 | 417 | case CTF_FIELD_CLASS_TYPE_ARRAY: |
087cd0f5 | 418 | ir_fc = ctf_field_class_array_to_ir(ctx, ctf_field_class_as_array(fc)); |
44c440bc | 419 | break; |
864cad70 | 420 | case CTF_FIELD_CLASS_TYPE_SEQUENCE: |
087cd0f5 | 421 | ir_fc = ctf_field_class_sequence_to_ir(ctx, ctf_field_class_as_sequence(fc)); |
44c440bc | 422 | break; |
864cad70 | 423 | case CTF_FIELD_CLASS_TYPE_VARIANT: |
087cd0f5 | 424 | ir_fc = ctf_field_class_variant_to_ir(ctx, ctf_field_class_as_variant(fc)); |
44c440bc PP |
425 | break; |
426 | default: | |
498e7994 | 427 | bt_common_abort(); |
44c440bc PP |
428 | } |
429 | ||
5cd6d0e5 PP |
430 | fc->ir_fc = ir_fc; |
431 | return ir_fc; | |
44c440bc PP |
432 | } |
433 | ||
434 | static inline | |
5cd6d0e5 PP |
435 | bool ctf_field_class_struct_has_immediate_member_in_ir( |
436 | struct ctf_field_class_struct *fc) | |
44c440bc PP |
437 | { |
438 | uint64_t i; | |
439 | bool has_immediate_member_in_ir = false; | |
440 | ||
b2c863b0 PP |
441 | /* |
442 | * If the structure field class has no members at all, then it | |
443 | * was an empty structure in the beginning, so leave it existing | |
444 | * and empty. | |
445 | */ | |
446 | if (fc->members->len == 0) { | |
447 | has_immediate_member_in_ir = true; | |
448 | goto end; | |
449 | } | |
450 | ||
5cd6d0e5 PP |
451 | for (i = 0; i < fc->members->len; i++) { |
452 | struct ctf_named_field_class *named_fc = | |
453 | ctf_field_class_struct_borrow_member_by_index(fc, i); | |
44c440bc | 454 | |
5cd6d0e5 | 455 | if (named_fc->fc->in_ir) { |
44c440bc PP |
456 | has_immediate_member_in_ir = true; |
457 | goto end; | |
458 | } | |
459 | } | |
460 | ||
461 | end: | |
462 | return has_immediate_member_in_ir; | |
463 | } | |
464 | ||
465 | static inline | |
83ebb7f1 | 466 | bt_field_class *scope_ctf_field_class_to_ir(struct ctx *ctx) |
44c440bc | 467 | { |
b19ff26f | 468 | bt_field_class *ir_fc = NULL; |
83ebb7f1 | 469 | struct ctf_field_class *fc = NULL; |
44c440bc | 470 | |
83ebb7f1 PP |
471 | switch (ctx->scope) { |
472 | case CTF_SCOPE_PACKET_CONTEXT: | |
473 | fc = ctx->sc->packet_context_fc; | |
474 | break; | |
475 | case CTF_SCOPE_EVENT_COMMON_CONTEXT: | |
476 | fc = ctx->sc->event_common_context_fc; | |
477 | break; | |
478 | case CTF_SCOPE_EVENT_SPECIFIC_CONTEXT: | |
479 | fc = ctx->ec->spec_context_fc; | |
480 | break; | |
481 | case CTF_SCOPE_EVENT_PAYLOAD: | |
482 | fc = ctx->ec->payload_fc; | |
483 | break; | |
484 | default: | |
498e7994 | 485 | bt_common_abort(); |
44c440bc PP |
486 | } |
487 | ||
83ebb7f1 | 488 | if (fc && ctf_field_class_struct_has_immediate_member_in_ir( |
087cd0f5 | 489 | ctf_field_class_as_struct(fc))) { |
83ebb7f1 | 490 | ir_fc = ctf_field_class_to_ir(ctx, fc); |
44c440bc PP |
491 | } |
492 | ||
5cd6d0e5 | 493 | return ir_fc; |
44c440bc PP |
494 | } |
495 | ||
44c440bc | 496 | static inline |
83ebb7f1 | 497 | void ctf_event_class_to_ir(struct ctx *ctx) |
44c440bc PP |
498 | { |
499 | int ret; | |
b19ff26f | 500 | bt_event_class *ir_ec = NULL; |
83ebb7f1 | 501 | bt_field_class *ir_fc; |
44c440bc | 502 | |
83ebb7f1 PP |
503 | BT_ASSERT(ctx->ec); |
504 | ||
505 | if (ctx->ec->is_translated) { | |
40f4ba76 | 506 | ir_ec = bt_stream_class_borrow_event_class_by_id( |
83ebb7f1 | 507 | ctx->ir_sc, ctx->ec->id); |
44c440bc PP |
508 | BT_ASSERT(ir_ec); |
509 | goto end; | |
510 | } | |
511 | ||
83ebb7f1 | 512 | ir_ec = bt_event_class_create_with_id(ctx->ir_sc, ctx->ec->id); |
44c440bc | 513 | BT_ASSERT(ir_ec); |
c5b9b441 | 514 | bt_event_class_put_ref(ir_ec); |
83ebb7f1 PP |
515 | ctx->scope = CTF_SCOPE_EVENT_SPECIFIC_CONTEXT; |
516 | ir_fc = scope_ctf_field_class_to_ir(ctx); | |
517 | if (ir_fc) { | |
518 | ret = bt_event_class_set_specific_context_field_class( | |
519 | ir_ec, ir_fc); | |
520 | BT_ASSERT(ret == 0); | |
521 | bt_field_class_put_ref(ir_fc); | |
44c440bc PP |
522 | } |
523 | ||
83ebb7f1 PP |
524 | ctx->scope = CTF_SCOPE_EVENT_PAYLOAD; |
525 | ir_fc = scope_ctf_field_class_to_ir(ctx); | |
526 | if (ir_fc) { | |
527 | ret = bt_event_class_set_payload_field_class(ir_ec, | |
528 | ir_fc); | |
529 | BT_ASSERT(ret == 0); | |
530 | bt_field_class_put_ref(ir_fc); | |
44c440bc PP |
531 | } |
532 | ||
83ebb7f1 PP |
533 | if (ctx->ec->name->len > 0) { |
534 | ret = bt_event_class_set_name(ir_ec, ctx->ec->name->str); | |
44c440bc PP |
535 | BT_ASSERT(ret == 0); |
536 | } | |
537 | ||
83ebb7f1 PP |
538 | if (ctx->ec->emf_uri->len > 0) { |
539 | ret = bt_event_class_set_emf_uri(ir_ec, ctx->ec->emf_uri->str); | |
44c440bc PP |
540 | BT_ASSERT(ret == 0); |
541 | } | |
542 | ||
6da709aa | 543 | if (ctx->ec->is_log_level_set) { |
83ebb7f1 | 544 | bt_event_class_set_log_level(ir_ec, ctx->ec->log_level); |
44c440bc PP |
545 | } |
546 | ||
83ebb7f1 PP |
547 | ctx->ec->is_translated = true; |
548 | ctx->ec->ir_ec = ir_ec; | |
44c440bc PP |
549 | |
550 | end: | |
83ebb7f1 | 551 | return; |
44c440bc PP |
552 | } |
553 | ||
554 | ||
555 | static inline | |
83ebb7f1 | 556 | void ctf_stream_class_to_ir(struct ctx *ctx) |
44c440bc PP |
557 | { |
558 | int ret; | |
83ebb7f1 | 559 | bt_field_class *ir_fc; |
44c440bc | 560 | |
83ebb7f1 | 561 | BT_ASSERT(ctx->sc); |
44c440bc | 562 | |
83ebb7f1 PP |
563 | if (ctx->sc->is_translated) { |
564 | ctx->ir_sc = bt_trace_class_borrow_stream_class_by_id( | |
565 | ctx->ir_tc, ctx->sc->id); | |
566 | BT_ASSERT(ctx->ir_sc); | |
567 | goto end; | |
44c440bc PP |
568 | } |
569 | ||
83ebb7f1 PP |
570 | ctx->ir_sc = bt_stream_class_create_with_id(ctx->ir_tc, ctx->sc->id); |
571 | BT_ASSERT(ctx->ir_sc); | |
572 | bt_stream_class_put_ref(ctx->ir_sc); | |
26fc5aed PP |
573 | |
574 | if (ctx->sc->default_clock_class) { | |
575 | BT_ASSERT(ctx->sc->default_clock_class->ir_cc); | |
576 | ret = bt_stream_class_set_default_clock_class(ctx->ir_sc, | |
577 | ctx->sc->default_clock_class->ir_cc); | |
578 | BT_ASSERT(ret == 0); | |
579 | } | |
580 | ||
581 | bt_stream_class_set_supports_packets(ctx->ir_sc, BT_TRUE, | |
582 | ctx->sc->packets_have_ts_begin, ctx->sc->packets_have_ts_end); | |
583 | bt_stream_class_set_supports_discarded_events(ctx->ir_sc, | |
584 | ctx->sc->has_discarded_events, | |
585 | ctx->sc->discarded_events_have_default_cs); | |
586 | bt_stream_class_set_supports_discarded_packets(ctx->ir_sc, | |
587 | ctx->sc->has_discarded_packets, | |
588 | ctx->sc->discarded_packets_have_default_cs); | |
83ebb7f1 PP |
589 | ctx->scope = CTF_SCOPE_PACKET_CONTEXT; |
590 | ir_fc = scope_ctf_field_class_to_ir(ctx); | |
591 | if (ir_fc) { | |
592 | ret = bt_stream_class_set_packet_context_field_class( | |
593 | ctx->ir_sc, ir_fc); | |
594 | BT_ASSERT(ret == 0); | |
595 | bt_field_class_put_ref(ir_fc); | |
44c440bc PP |
596 | } |
597 | ||
83ebb7f1 PP |
598 | ctx->scope = CTF_SCOPE_EVENT_COMMON_CONTEXT; |
599 | ir_fc = scope_ctf_field_class_to_ir(ctx); | |
600 | if (ir_fc) { | |
601 | ret = bt_stream_class_set_event_common_context_field_class( | |
602 | ctx->ir_sc, ir_fc); | |
603 | BT_ASSERT(ret == 0); | |
604 | bt_field_class_put_ref(ir_fc); | |
44c440bc PP |
605 | } |
606 | ||
83ebb7f1 | 607 | bt_stream_class_set_assigns_automatic_event_class_id(ctx->ir_sc, |
44c440bc | 608 | BT_FALSE); |
83ebb7f1 | 609 | bt_stream_class_set_assigns_automatic_stream_id(ctx->ir_sc, BT_FALSE); |
44c440bc | 610 | |
83ebb7f1 PP |
611 | ctx->sc->is_translated = true; |
612 | ctx->sc->ir_sc = ctx->ir_sc; | |
44c440bc PP |
613 | |
614 | end: | |
83ebb7f1 | 615 | return; |
44c440bc PP |
616 | } |
617 | ||
618 | static inline | |
0f2d58c9 PP |
619 | void ctf_clock_class_to_ir(bt_clock_class *ir_cc, struct ctf_clock_class *cc) |
620 | { | |
621 | int ret; | |
622 | ||
623 | if (strlen(cc->name->str) > 0) { | |
624 | ret = bt_clock_class_set_name(ir_cc, cc->name->str); | |
625 | BT_ASSERT(ret == 0); | |
626 | } | |
627 | ||
628 | if (strlen(cc->description->str) > 0) { | |
629 | ret = bt_clock_class_set_description(ir_cc, cc->description->str); | |
630 | BT_ASSERT(ret == 0); | |
631 | } | |
632 | ||
633 | bt_clock_class_set_frequency(ir_cc, cc->frequency); | |
634 | bt_clock_class_set_precision(ir_cc, cc->precision); | |
635 | bt_clock_class_set_offset(ir_cc, cc->offset_seconds, cc->offset_cycles); | |
636 | ||
637 | if (cc->has_uuid) { | |
638 | bt_clock_class_set_uuid(ir_cc, cc->uuid); | |
639 | } | |
640 | ||
5552377a | 641 | bt_clock_class_set_origin_is_unix_epoch(ir_cc, cc->is_absolute); |
0f2d58c9 PP |
642 | } |
643 | ||
644 | static inline | |
83ebb7f1 | 645 | int ctf_trace_class_to_ir(struct ctx *ctx) |
44c440bc PP |
646 | { |
647 | int ret = 0; | |
648 | uint64_t i; | |
649 | ||
83ebb7f1 PP |
650 | BT_ASSERT(ctx->tc); |
651 | BT_ASSERT(ctx->ir_tc); | |
44c440bc | 652 | |
83ebb7f1 PP |
653 | if (ctx->tc->is_translated) { |
654 | goto end; | |
44c440bc PP |
655 | } |
656 | ||
83ebb7f1 | 657 | for (i = 0; i < ctx->tc->clock_classes->len; i++) { |
087cd0f5 | 658 | ctf_clock_class *cc = (ctf_clock_class *) ctx->tc->clock_classes->pdata[i]; |
0f2d58c9 | 659 | |
f7b785ac | 660 | cc->ir_cc = bt_clock_class_create(ctx->self_comp); |
0f2d58c9 PP |
661 | ctf_clock_class_to_ir(cc->ir_cc, cc); |
662 | } | |
663 | ||
83ebb7f1 | 664 | bt_trace_class_set_assigns_automatic_stream_class_id(ctx->ir_tc, |
44c440bc | 665 | BT_FALSE); |
83ebb7f1 PP |
666 | ctx->tc->is_translated = true; |
667 | ctx->tc->ir_tc = ctx->ir_tc; | |
44c440bc PP |
668 | |
669 | end: | |
670 | return ret; | |
671 | } | |
672 | ||
673 | BT_HIDDEN | |
f7b785ac | 674 | int ctf_trace_class_translate(bt_self_component *self_comp, |
7fcdb0a9 | 675 | bt_trace_class *ir_tc, struct ctf_trace_class *tc) |
44c440bc PP |
676 | { |
677 | int ret = 0; | |
678 | uint64_t i; | |
83ebb7f1 | 679 | struct ctx ctx = { 0 }; |
44c440bc | 680 | |
7fcdb0a9 | 681 | ctx.self_comp = self_comp; |
83ebb7f1 PP |
682 | ctx.tc = tc; |
683 | ctx.ir_tc = ir_tc; | |
684 | ret = ctf_trace_class_to_ir(&ctx); | |
44c440bc PP |
685 | if (ret) { |
686 | goto end; | |
687 | } | |
688 | ||
689 | for (i = 0; i < tc->stream_classes->len; i++) { | |
690 | uint64_t j; | |
087cd0f5 | 691 | ctx.sc = (ctf_stream_class *) tc->stream_classes->pdata[i]; |
44c440bc | 692 | |
83ebb7f1 | 693 | ctf_stream_class_to_ir(&ctx); |
44c440bc | 694 | |
83ebb7f1 | 695 | for (j = 0; j < ctx.sc->event_classes->len; j++) { |
087cd0f5 | 696 | ctx.ec = (ctf_event_class *) ctx.sc->event_classes->pdata[j]; |
44c440bc | 697 | |
83ebb7f1 PP |
698 | ctf_event_class_to_ir(&ctx); |
699 | ctx.ec = NULL; | |
44c440bc | 700 | } |
83ebb7f1 PP |
701 | |
702 | ctx.sc = NULL; | |
44c440bc PP |
703 | } |
704 | ||
705 | end: | |
706 | return ret; | |
707 | } |