Reorder event field init
[libside.git] / src / tracer.c
CommitLineData
f611d0c3
MD
1// SPDX-License-Identifier: MIT
2/*
3 * Copyright 2022 Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
4 */
5
6#include <stdint.h>
7#include <inttypes.h>
8#include <stdlib.h>
9#include <stdio.h>
ea32e5fc 10#include <stdbool.h>
1d9c515c 11#include <string.h>
f611d0c3
MD
12
13#include <side/trace.h>
14
1d9c515c
MD
15enum tracer_display_base {
16 TRACER_DISPLAY_BASE_2,
17 TRACER_DISPLAY_BASE_8,
18 TRACER_DISPLAY_BASE_10,
19 TRACER_DISPLAY_BASE_16,
20};
21
1e8aec23
MD
22static struct side_tracer_handle *tracer_handle;
23
f611d0c3
MD
24static
25void tracer_print_struct(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc);
26static
27void tracer_print_array(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc);
28static
29void tracer_print_vla(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc);
30static
352a4b77 31void tracer_print_vla_visitor(const struct side_type_description *type_desc, void *app_ctx);
ba845af5
MD
32static
33void tracer_print_array_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item);
1533629f
MD
34static
35void tracer_print_vla_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item);
a2e2357e
MD
36static
37void tracer_print_dynamic(const struct side_arg_dynamic_vec *dynamic_item);
d8be25de
MD
38static
39void tracer_print_type(const struct side_type_description *type_desc, const struct side_arg_vec *item);
f611d0c3 40
1d9c515c
MD
41static
42int64_t get_attr_integer_value(const struct side_attr *attr)
43{
44 int64_t val;
45
46 switch (attr->value.type) {
47 case SIDE_ATTR_TYPE_U8:
48 val = attr->value.u.side_u8;
49 break;
50 case SIDE_ATTR_TYPE_U16:
51 val = attr->value.u.side_u16;
52 break;
53 case SIDE_ATTR_TYPE_U32:
54 val = attr->value.u.side_u32;
55 break;
56 case SIDE_ATTR_TYPE_U64:
57 val = attr->value.u.side_u64;
58 break;
59 case SIDE_ATTR_TYPE_S8:
60 val = attr->value.u.side_s8;
61 break;
62 case SIDE_ATTR_TYPE_S16:
63 val = attr->value.u.side_s16;
64 break;
65 case SIDE_ATTR_TYPE_S32:
66 val = attr->value.u.side_s32;
67 break;
68 case SIDE_ATTR_TYPE_S64:
69 val = attr->value.u.side_s64;
70 break;
71 default:
72 fprintf(stderr, "Unexpected attribute type\n");
73 abort();
74 }
75 return val;
76}
77
78static
79enum tracer_display_base get_attr_display_base(const struct side_attr *_attr, uint32_t nr_attr)
80{
81 uint32_t i;
82
83 for (i = 0; i < nr_attr; i++) {
84 const struct side_attr *attr = &_attr[i];
85
86 if (!strcmp(attr->key, "std.integer.base")) {
87 int64_t val = get_attr_integer_value(attr);
88
89 switch (val) {
90 case 2:
91 return TRACER_DISPLAY_BASE_2;
92 case 8:
93 return TRACER_DISPLAY_BASE_8;
94 case 10:
95 return TRACER_DISPLAY_BASE_10;
96 case 16:
97 return TRACER_DISPLAY_BASE_16;
98 default:
99 fprintf(stderr, "Unexpected integer display base: %" PRId64 "\n", val);
100 abort();
101 }
102 }
103 }
104 return TRACER_DISPLAY_BASE_10; /* Default */
105}
106
8bdd5c12
MD
107static
108bool type_to_host_reverse_bo(const struct side_type_description *type_desc)
109{
110 switch (type_desc->type) {
111 case SIDE_TYPE_U8:
112 case SIDE_TYPE_S8:
113 case SIDE_TYPE_BYTE:
114 return false;
115 case SIDE_TYPE_U16:
116 case SIDE_TYPE_U32:
117 case SIDE_TYPE_U64:
118 case SIDE_TYPE_S16:
119 case SIDE_TYPE_S32:
120 case SIDE_TYPE_S64:
dd6e76cb
MD
121 case SIDE_TYPE_POINTER32:
122 case SIDE_TYPE_POINTER64:
8bdd5c12
MD
123 if (type_desc->u.side_basic.byte_order != SIDE_TYPE_BYTE_ORDER_HOST)
124 return true;
125 else
126 return false;
127 break;
128 case SIDE_TYPE_FLOAT_BINARY16:
129 case SIDE_TYPE_FLOAT_BINARY32:
130 case SIDE_TYPE_FLOAT_BINARY64:
131 case SIDE_TYPE_FLOAT_BINARY128:
132 if (type_desc->u.side_basic.byte_order != SIDE_TYPE_FLOAT_WORD_ORDER_HOST)
133 return true;
134 else
135 return false;
136 break;
137 default:
138 fprintf(stderr, "Unexpected type\n");
139 abort();
140 }
141}
142
143static
144bool dynamic_type_to_host_reverse_bo(const struct side_arg_dynamic_vec *item)
145{
146 switch (item->dynamic_type) {
147 case SIDE_DYNAMIC_TYPE_U8:
148 case SIDE_DYNAMIC_TYPE_S8:
149 case SIDE_DYNAMIC_TYPE_BYTE:
150 return false;
151 case SIDE_DYNAMIC_TYPE_U16:
152 case SIDE_DYNAMIC_TYPE_U32:
153 case SIDE_DYNAMIC_TYPE_U64:
154 case SIDE_DYNAMIC_TYPE_S16:
155 case SIDE_DYNAMIC_TYPE_S32:
156 case SIDE_DYNAMIC_TYPE_S64:
dd6e76cb
MD
157 case SIDE_DYNAMIC_TYPE_POINTER32:
158 case SIDE_DYNAMIC_TYPE_POINTER64:
8bdd5c12
MD
159 if (item->u.side_basic.byte_order != SIDE_TYPE_BYTE_ORDER_HOST)
160 return true;
161 else
162 return false;
163 break;
164 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY16:
165 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY32:
166 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY64:
167 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY128:
168 if (item->u.side_basic.byte_order != SIDE_TYPE_FLOAT_WORD_ORDER_HOST)
169 return true;
170 else
171 return false;
172 break;
173 default:
174 fprintf(stderr, "Unexpected type\n");
175 abort();
176 }
177}
178
bc3c89b3 179static
905c328e 180void tracer_print_attr_type(const char *separator, const struct side_attr *attr)
bc3c89b3 181{
905c328e 182 printf("{ key%s \"%s\", value%s ", separator, attr->key, separator);
bc3c89b3
MD
183 switch (attr->value.type) {
184 case SIDE_ATTR_TYPE_BOOL:
185 printf("%s", attr->value.u.side_bool ? "true" : "false");
186 break;
187 case SIDE_ATTR_TYPE_U8:
188 printf("%" PRIu8, attr->value.u.side_u8);
189 break;
190 case SIDE_ATTR_TYPE_U16:
191 printf("%" PRIu16, attr->value.u.side_u16);
192 break;
193 case SIDE_ATTR_TYPE_U32:
194 printf("%" PRIu32, attr->value.u.side_u32);
195 break;
196 case SIDE_ATTR_TYPE_U64:
197 printf("%" PRIu64, attr->value.u.side_u64);
198 break;
199 case SIDE_ATTR_TYPE_S8:
200 printf("%" PRId8, attr->value.u.side_s8);
201 break;
202 case SIDE_ATTR_TYPE_S16:
203 printf("%" PRId16, attr->value.u.side_s16);
204 break;
205 case SIDE_ATTR_TYPE_S32:
206 printf("%" PRId32, attr->value.u.side_s32);
207 break;
208 case SIDE_ATTR_TYPE_S64:
209 printf("%" PRId64, attr->value.u.side_s64);
210 break;
dd6e76cb
MD
211 case SIDE_ATTR_TYPE_POINTER32:
212 printf("0x%" PRIx32, attr->value.u.side_u32);
213 break;
214 case SIDE_ATTR_TYPE_POINTER64:
215 printf("0x%" PRIx64, attr->value.u.side_u64);
f5e650d7 216 break;
bc3c89b3
MD
217 case SIDE_ATTR_TYPE_FLOAT_BINARY16:
218#if __HAVE_FLOAT16
219 printf("%g", (double) attr->value.u.side_float_binary16);
220 break;
221#else
de1b3cd2 222 fprintf(stderr, "ERROR: Unsupported binary16 float type\n");
bc3c89b3
MD
223 abort();
224#endif
225 case SIDE_ATTR_TYPE_FLOAT_BINARY32:
226#if __HAVE_FLOAT32
227 printf("%g", (double) attr->value.u.side_float_binary32);
228 break;
229#else
de1b3cd2 230 fprintf(stderr, "ERROR: Unsupported binary32 float type\n");
bc3c89b3
MD
231 abort();
232#endif
233 case SIDE_ATTR_TYPE_FLOAT_BINARY64:
234#if __HAVE_FLOAT64
235 printf("%g", (double) attr->value.u.side_float_binary64);
236 break;
237#else
de1b3cd2 238 fprintf(stderr, "ERROR: Unsupported binary64 float type\n");
bc3c89b3
MD
239 abort();
240#endif
241 case SIDE_ATTR_TYPE_FLOAT_BINARY128:
242#if __HAVE_FLOAT128
243 printf("%Lg", (long double) attr->value.u.side_float_binary128);
244 break;
245#else
de1b3cd2 246 fprintf(stderr, "ERROR: Unsupported binary128 float type\n");
bc3c89b3
MD
247 abort();
248#endif
249 case SIDE_ATTR_TYPE_STRING:
8549e629 250 printf("\"%s\"", (const char *)(uintptr_t) attr->value.u.string);
bc3c89b3
MD
251 break;
252 default:
de1b3cd2 253 fprintf(stderr, "ERROR: <UNKNOWN ATTRIBUTE TYPE>");
bc3c89b3
MD
254 abort();
255 }
256 printf(" }");
257}
258
7d21cf51 259static
905c328e
MD
260void print_attributes(const char *prefix_str, const char *separator,
261 const struct side_attr *attr, uint32_t nr_attr)
7d21cf51
MD
262{
263 int i;
264
265 if (!nr_attr)
266 return;
905c328e 267 printf("%s%s [ ", prefix_str, separator);
7d21cf51
MD
268 for (i = 0; i < nr_attr; i++) {
269 printf("%s", i ? ", " : "");
905c328e 270 tracer_print_attr_type(separator, &attr[i]);
7d21cf51
MD
271 }
272 printf(" ]");
273}
274
79f677ba 275static
d8be25de 276void print_enum(const struct side_type_description *type_desc, const struct side_arg_vec *item)
79f677ba 277{
d8be25de 278 const struct side_enum_mappings *mappings = type_desc->u.side_enum.mappings;
8bdd5c12 279 const struct side_type_description *elem_type = type_desc->u.side_enum.elem_type;
79f677ba 280 int i, print_count = 0;
d8be25de 281 int64_t value;
79f677ba 282
8bdd5c12 283 if (elem_type->type != item->type) {
de1b3cd2 284 fprintf(stderr, "ERROR: Unexpected enum element type\n");
d8be25de
MD
285 abort();
286 }
287 switch (item->type) {
288 case SIDE_TYPE_U8:
289 value = (int64_t) item->u.side_u8;
290 break;
291 case SIDE_TYPE_U16:
8bdd5c12
MD
292 {
293 uint16_t v;
294
295 v = item->u.side_u16;
296 if (type_to_host_reverse_bo(elem_type))
297 v = side_bswap_16(v);
298 value = (int64_t) v;
d8be25de 299 break;
8bdd5c12 300 }
d8be25de 301 case SIDE_TYPE_U32:
8bdd5c12
MD
302 {
303 uint32_t v;
304
305 v = item->u.side_u32;
306 if (type_to_host_reverse_bo(elem_type))
307 v = side_bswap_32(v);
308 value = (int64_t) v;
d8be25de 309 break;
8bdd5c12 310 }
d8be25de 311 case SIDE_TYPE_U64:
8bdd5c12
MD
312 {
313 uint64_t v;
314
315 v = item->u.side_u64;
316 if (type_to_host_reverse_bo(elem_type))
317 v = side_bswap_64(v);
318 value = (int64_t) v;
d8be25de 319 break;
8bdd5c12 320 }
d8be25de
MD
321 case SIDE_TYPE_S8:
322 value = (int64_t) item->u.side_s8;
323 break;
324 case SIDE_TYPE_S16:
8bdd5c12
MD
325 {
326 int16_t v;
327
328 v = item->u.side_s16;
329 if (type_to_host_reverse_bo(elem_type))
330 v = side_bswap_16(v);
331 value = (int64_t) v;
d8be25de 332 break;
8bdd5c12 333 }
d8be25de 334 case SIDE_TYPE_S32:
8bdd5c12
MD
335 {
336 int32_t v;
337
338 v = item->u.side_s32;
339 if (type_to_host_reverse_bo(elem_type))
340 v = side_bswap_32(v);
341 value = (int64_t) v;
d8be25de 342 break;
8bdd5c12 343 }
d8be25de 344 case SIDE_TYPE_S64:
8bdd5c12
MD
345 {
346 int64_t v;
347
348 v = item->u.side_s64;
349 if (type_to_host_reverse_bo(elem_type))
350 v = side_bswap_64(v);
351 value = v;
d8be25de 352 break;
8bdd5c12 353 }
d8be25de 354 default:
de1b3cd2 355 fprintf(stderr, "ERROR: Unexpected enum element type\n");
d8be25de
MD
356 abort();
357 }
905c328e 358 print_attributes("attr", ":", mappings->attr, mappings->nr_attr);
d8be25de
MD
359 printf("%s", mappings->nr_attr ? ", " : "");
360 tracer_print_type(type_desc->u.side_enum.elem_type, item);
361 printf(", labels: [ ");
362 for (i = 0; i < mappings->nr_mappings; i++) {
363 const struct side_enum_mapping *mapping = &mappings->mappings[i];
79f677ba 364
ea32e5fc 365 if (mapping->range_end < mapping->range_begin) {
de1b3cd2 366 fprintf(stderr, "ERROR: Unexpected enum range: %" PRIu64 "-%" PRIu64 "\n",
ea32e5fc
MD
367 mapping->range_begin, mapping->range_end);
368 abort();
369 }
79f677ba
MD
370 if (value >= mapping->range_begin && value <= mapping->range_end) {
371 printf("%s", print_count++ ? ", " : "");
372 printf("\"%s\"", mapping->label);
373 }
374 }
375 if (!print_count)
376 printf("<NO LABEL>");
377 printf(" ]");
378}
379
ea32e5fc 380static
bab5d6e4 381uint32_t enum_elem_type_to_stride(const struct side_type_description *elem_type)
ea32e5fc 382{
af6aa6e1
MD
383 uint32_t stride_bit;
384
bab5d6e4 385 switch (elem_type->type) {
4cc2880b
MD
386 case SIDE_TYPE_U8: /* Fall-through */
387 case SIDE_TYPE_BYTE:
af6aa6e1
MD
388 stride_bit = 8;
389 break;
af6aa6e1 390 case SIDE_TYPE_U16:
af6aa6e1
MD
391 stride_bit = 16;
392 break;
af6aa6e1 393 case SIDE_TYPE_U32:
af6aa6e1
MD
394 stride_bit = 32;
395 break;
af6aa6e1 396 case SIDE_TYPE_U64:
af6aa6e1
MD
397 stride_bit = 64;
398 break;
af6aa6e1 399 default:
de1b3cd2 400 fprintf(stderr, "ERROR: Unexpected enum element type\n");
af6aa6e1
MD
401 abort();
402 }
403 return stride_bit;
404}
405
406static
407void print_enum_bitmap(const struct side_type_description *type_desc,
408 const struct side_arg_vec *item)
409{
bab5d6e4
MD
410 const struct side_type_description *elem_type = type_desc->u.side_enum_bitmap.elem_type;
411 const struct side_enum_bitmap_mappings *side_enum_mappings = type_desc->u.side_enum_bitmap.mappings;
ea32e5fc 412 int i, print_count = 0;
af6aa6e1 413 uint32_t stride_bit, nr_items;
8bdd5c12 414 bool reverse_byte_order = false;
af6aa6e1
MD
415 const struct side_arg_vec *array_item;
416
bab5d6e4
MD
417 switch (elem_type->type) {
418 case SIDE_TYPE_U8: /* Fall-through */
4cc2880b 419 case SIDE_TYPE_BYTE: /* Fall-through */
bab5d6e4
MD
420 case SIDE_TYPE_U16: /* Fall-through */
421 case SIDE_TYPE_U32: /* Fall-through */
4cc2880b 422 case SIDE_TYPE_U64:
45392033 423 stride_bit = enum_elem_type_to_stride(elem_type);
8bdd5c12 424 reverse_byte_order = type_to_host_reverse_bo(elem_type);
af6aa6e1
MD
425 array_item = item;
426 nr_items = 1;
af6aa6e1 427 break;
bab5d6e4 428 case SIDE_TYPE_ARRAY:
45392033 429 stride_bit = enum_elem_type_to_stride(elem_type->u.side_array.elem_type);
8bdd5c12 430 reverse_byte_order = type_to_host_reverse_bo(elem_type->u.side_array.elem_type);
af6aa6e1 431 array_item = item->u.side_array->sav;
bab5d6e4 432 nr_items = type_desc->u.side_array.length;
af6aa6e1 433 break;
bab5d6e4 434 case SIDE_TYPE_VLA:
45392033 435 stride_bit = enum_elem_type_to_stride(elem_type->u.side_vla.elem_type);
8bdd5c12 436 reverse_byte_order = type_to_host_reverse_bo(elem_type->u.side_vla.elem_type);
af6aa6e1 437 array_item = item->u.side_vla->sav;
bab5d6e4 438 nr_items = item->u.side_vla->len;
af6aa6e1
MD
439 break;
440 default:
de1b3cd2 441 fprintf(stderr, "ERROR: Unexpected enum element type\n");
af6aa6e1
MD
442 abort();
443 }
ea32e5fc 444
905c328e 445 print_attributes("attr", ":", side_enum_mappings->attr, side_enum_mappings->nr_attr);
d4328528 446 printf("%s", side_enum_mappings->nr_attr ? ", " : "");
af6aa6e1 447 printf("labels: [ ");
ea32e5fc 448 for (i = 0; i < side_enum_mappings->nr_mappings; i++) {
66cff328 449 const struct side_enum_bitmap_mapping *mapping = &side_enum_mappings->mappings[i];
ea32e5fc 450 bool match = false;
9ff49ee4 451 uint64_t bit;
ea32e5fc 452
9ff49ee4 453 if (mapping->range_end < mapping->range_begin) {
de1b3cd2 454 fprintf(stderr, "ERROR: Unexpected enum bitmap range: %" PRIu64 "-%" PRIu64 "\n",
ea32e5fc
MD
455 mapping->range_begin, mapping->range_end);
456 abort();
457 }
458 for (bit = mapping->range_begin; bit <= mapping->range_end; bit++) {
af6aa6e1
MD
459 if (bit > (nr_items * stride_bit) - 1)
460 break;
461 switch (stride_bit) {
462 case 8:
463 {
464 uint8_t v = array_item[bit / 8].u.side_u8;
465 if (v & (1ULL << (bit % 8))) {
466 match = true;
467 goto match;
468 }
469 break;
470 }
471 case 16:
472 {
473 uint16_t v = array_item[bit / 16].u.side_u16;
8bdd5c12
MD
474 if (reverse_byte_order)
475 v = side_bswap_16(v);
af6aa6e1
MD
476 if (v & (1ULL << (bit % 16))) {
477 match = true;
478 goto match;
479 }
480 break;
481 }
482 case 32:
483 {
484 uint32_t v = array_item[bit / 32].u.side_u32;
8bdd5c12
MD
485 if (reverse_byte_order)
486 v = side_bswap_32(v);
af6aa6e1
MD
487 if (v & (1ULL << (bit % 32))) {
488 match = true;
489 goto match;
490 }
ea32e5fc
MD
491 break;
492 }
af6aa6e1
MD
493 case 64:
494 {
495 uint64_t v = array_item[bit / 64].u.side_u64;
8bdd5c12
MD
496 if (reverse_byte_order)
497 v = side_bswap_64(v);
af6aa6e1
MD
498 if (v & (1ULL << (bit % 64))) {
499 match = true;
500 goto match;
501 }
502 break;
503 }
504 default:
505 abort();
506 }
ea32e5fc 507 }
af6aa6e1 508match:
ea32e5fc
MD
509 if (match) {
510 printf("%s", print_count++ ? ", " : "");
511 printf("\"%s\"", mapping->label);
512 }
513 }
514 if (!print_count)
515 printf("<NO LABEL>");
516 printf(" ]");
517}
518
1d9c515c
MD
519static
520void print_integer_binary(uint64_t v, int bits)
521{
522 int i;
523
524 printf("0b");
525 v <<= 64 - bits;
526 for (i = 0; i < bits; i++) {
527 printf("%c", v & (1ULL << 63) ? '1' : '0');
528 v <<= 1;
529 }
530}
531
0e9be766
MD
532static
533void tracer_print_basic_type_header(const struct side_type_description *type_desc)
534{
905c328e 535 print_attributes("attr", ":", type_desc->u.side_basic.attr, type_desc->u.side_basic.nr_attr);
0e9be766
MD
536 printf("%s", type_desc->u.side_basic.nr_attr ? ", " : "");
537 printf("value: ");
538}
539
f611d0c3
MD
540static
541void tracer_print_type(const struct side_type_description *type_desc, const struct side_arg_vec *item)
542{
d8be25de 543 enum side_type type;
1d9c515c 544 enum tracer_display_base base = TRACER_DISPLAY_BASE_10;
d8be25de 545
45392033
MD
546 switch (type_desc->type) {
547 case SIDE_TYPE_ARRAY:
548 switch (item->type) {
549 case SIDE_TYPE_ARRAY_U8:
550 case SIDE_TYPE_ARRAY_U16:
551 case SIDE_TYPE_ARRAY_U32:
552 case SIDE_TYPE_ARRAY_U64:
553 case SIDE_TYPE_ARRAY_S8:
554 case SIDE_TYPE_ARRAY_S16:
555 case SIDE_TYPE_ARRAY_S32:
556 case SIDE_TYPE_ARRAY_S64:
dd6e76cb
MD
557 case SIDE_TYPE_ARRAY_POINTER32:
558 case SIDE_TYPE_ARRAY_POINTER64:
f7653b43 559 case SIDE_TYPE_ARRAY_BYTE:
45392033
MD
560 case SIDE_TYPE_ARRAY:
561 break;
562 default:
de1b3cd2 563 fprintf(stderr, "ERROR: type mismatch between description and arguments\n");
ba845af5 564 abort();
45392033 565 break;
ba845af5
MD
566 }
567 break;
45392033
MD
568
569 case SIDE_TYPE_VLA:
570 switch (item->type) {
571 case SIDE_TYPE_VLA_U8:
572 case SIDE_TYPE_VLA_U16:
573 case SIDE_TYPE_VLA_U32:
574 case SIDE_TYPE_VLA_U64:
575 case SIDE_TYPE_VLA_S8:
576 case SIDE_TYPE_VLA_S16:
577 case SIDE_TYPE_VLA_S32:
578 case SIDE_TYPE_VLA_S64:
f7653b43 579 case SIDE_TYPE_VLA_BYTE:
dd6e76cb
MD
580 case SIDE_TYPE_VLA_POINTER32:
581 case SIDE_TYPE_VLA_POINTER64:
45392033
MD
582 case SIDE_TYPE_VLA:
583 break;
584 default:
de1b3cd2 585 fprintf(stderr, "ERROR: type mismatch between description and arguments\n");
1533629f 586 abort();
45392033 587 break;
1533629f
MD
588 }
589 break;
590
45392033
MD
591 case SIDE_TYPE_ENUM:
592 switch (item->type) {
593 case SIDE_TYPE_U8:
594 case SIDE_TYPE_U16:
595 case SIDE_TYPE_U32:
596 case SIDE_TYPE_U64:
597 case SIDE_TYPE_S8:
598 case SIDE_TYPE_S16:
599 case SIDE_TYPE_S32:
600 case SIDE_TYPE_S64:
bab5d6e4
MD
601 break;
602 default:
de1b3cd2 603 fprintf(stderr, "ERROR: type mismatch between description and arguments\n");
45392033
MD
604 abort();
605 break;
606 }
607 break;
608
609 case SIDE_TYPE_ENUM_BITMAP:
610 switch (item->type) {
611 case SIDE_TYPE_U8:
4cc2880b 612 case SIDE_TYPE_BYTE:
45392033
MD
613 case SIDE_TYPE_U16:
614 case SIDE_TYPE_U32:
615 case SIDE_TYPE_U64:
616 case SIDE_TYPE_ARRAY:
617 case SIDE_TYPE_VLA:
618 break;
619 default:
de1b3cd2 620 fprintf(stderr, "ERROR: type mismatch between description and arguments\n");
45392033
MD
621 abort();
622 break;
d8be25de
MD
623 }
624 break;
625
ba845af5 626 default:
a2e2357e 627 if (type_desc->type != item->type) {
de1b3cd2 628 fprintf(stderr, "ERROR: type mismatch between description and arguments\n");
ba845af5
MD
629 abort();
630 }
631 break;
f611d0c3 632 }
d8be25de 633
bab5d6e4
MD
634 if (type_desc->type == SIDE_TYPE_ENUM || type_desc->type == SIDE_TYPE_ENUM_BITMAP)
635 type = type_desc->type;
d8be25de
MD
636 else
637 type = item->type;
638
1d9c515c
MD
639 switch (type) {
640 case SIDE_TYPE_U8:
641 case SIDE_TYPE_U16:
642 case SIDE_TYPE_U32:
643 case SIDE_TYPE_U64:
644 case SIDE_TYPE_S8:
645 case SIDE_TYPE_S16:
646 case SIDE_TYPE_S32:
647 case SIDE_TYPE_S64:
648 base = get_attr_display_base(type_desc->u.side_basic.attr,
649 type_desc->u.side_basic.nr_attr);
650 break;
651 default:
652 break;
653 }
654
a848763d 655 printf("{ ");
d8be25de 656 switch (type) {
4f40d951 657 case SIDE_TYPE_BOOL:
0e9be766 658 tracer_print_basic_type_header(type_desc);
4f40d951
MD
659 printf("%s", item->u.side_bool ? "true" : "false");
660 break;
f611d0c3 661 case SIDE_TYPE_U8:
1d9c515c
MD
662 {
663 uint8_t v;
664
665 v = item->u.side_u8;
0e9be766 666 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
667 switch (base) {
668 case TRACER_DISPLAY_BASE_2:
669 print_integer_binary(v, 8);
670 break;
671 case TRACER_DISPLAY_BASE_8:
672 printf("0%" PRIo8, v);
673 break;
674 case TRACER_DISPLAY_BASE_10:
675 printf("%" PRIu8, v);
676 break;
677 case TRACER_DISPLAY_BASE_16:
678 printf("0x%" PRIx8, v);
679 break;
680 default:
681 abort();
682 }
f611d0c3 683 break;
1d9c515c 684 }
f611d0c3 685 case SIDE_TYPE_U16:
8bdd5c12
MD
686 {
687 uint16_t v;
688
689 v = item->u.side_u16;
690 if (type_to_host_reverse_bo(type_desc))
691 v = side_bswap_16(v);
0e9be766 692 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
693 switch (base) {
694 case TRACER_DISPLAY_BASE_2:
695 print_integer_binary(v, 16);
696 break;
697 case TRACER_DISPLAY_BASE_8:
698 printf("0%" PRIo16, v);
699 break;
700 case TRACER_DISPLAY_BASE_10:
701 printf("%" PRIu16, v);
702 break;
703 case TRACER_DISPLAY_BASE_16:
704 printf("0x%" PRIx16, v);
705 break;
706 default:
707 abort();
708 }
f611d0c3 709 break;
8bdd5c12 710 }
f611d0c3 711 case SIDE_TYPE_U32:
8bdd5c12
MD
712 {
713 uint32_t v;
714
715 v = item->u.side_u32;
716 if (type_to_host_reverse_bo(type_desc))
717 v = side_bswap_32(v);
0e9be766 718 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
719 switch (base) {
720 case TRACER_DISPLAY_BASE_2:
721 print_integer_binary(v, 32);
722 break;
723 case TRACER_DISPLAY_BASE_8:
724 printf("0%" PRIo32, v);
725 break;
726 case TRACER_DISPLAY_BASE_10:
727 printf("%" PRIu32, v);
728 break;
729 case TRACER_DISPLAY_BASE_16:
730 printf("0x%" PRIx32, v);
731 break;
732 default:
733 abort();
734 }
f611d0c3 735 break;
8bdd5c12 736 }
f611d0c3 737 case SIDE_TYPE_U64:
8bdd5c12
MD
738 {
739 uint64_t v;
740
741 v = item->u.side_u64;
742 if (type_to_host_reverse_bo(type_desc))
743 v = side_bswap_64(v);
0e9be766 744 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
745 switch (base) {
746 case TRACER_DISPLAY_BASE_2:
747 print_integer_binary(v, 64);
748 break;
749 case TRACER_DISPLAY_BASE_8:
750 printf("0%" PRIo64, v);
751 break;
752 case TRACER_DISPLAY_BASE_10:
753 printf("%" PRIu64, v);
754 break;
755 case TRACER_DISPLAY_BASE_16:
756 printf("0x%" PRIx64, v);
757 break;
758 default:
759 abort();
760 }
f611d0c3 761 break;
8bdd5c12 762 }
f611d0c3 763 case SIDE_TYPE_S8:
1d9c515c
MD
764 {
765 int8_t v;
766
767 v = item->u.side_s8;
0e9be766 768 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
769 switch (base) {
770 case TRACER_DISPLAY_BASE_2:
771 print_integer_binary(v, 8);
772 break;
773 case TRACER_DISPLAY_BASE_8:
774 printf("0%" PRIo8, v);
775 break;
776 case TRACER_DISPLAY_BASE_10:
777 printf("%" PRId8, v);
778 break;
779 case TRACER_DISPLAY_BASE_16:
780 printf("0x%" PRIx8, v);
781 break;
782 default:
783 abort();
784 }
f611d0c3 785 break;
1d9c515c 786 }
f611d0c3 787 case SIDE_TYPE_S16:
8bdd5c12
MD
788 {
789 int16_t v;
790
791 v = item->u.side_s16;
792 if (type_to_host_reverse_bo(type_desc))
793 v = side_bswap_16(v);
0e9be766 794 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
795 switch (base) {
796 case TRACER_DISPLAY_BASE_2:
797 print_integer_binary(v, 16);
798 break;
799 case TRACER_DISPLAY_BASE_8:
800 printf("0%" PRIo16, v);
801 break;
802 case TRACER_DISPLAY_BASE_10:
803 printf("%" PRId16, v);
804 break;
805 case TRACER_DISPLAY_BASE_16:
806 printf("0x%" PRIx16, v);
807 break;
808 default:
809 abort();
810 }
f611d0c3 811 break;
8bdd5c12 812 }
f611d0c3 813 case SIDE_TYPE_S32:
8bdd5c12
MD
814 {
815 int32_t v;
816
817 v = item->u.side_s32;
818 if (type_to_host_reverse_bo(type_desc))
819 v = side_bswap_32(v);
0e9be766 820 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
821 switch (base) {
822 case TRACER_DISPLAY_BASE_2:
823 print_integer_binary(v, 32);
824 break;
825 case TRACER_DISPLAY_BASE_8:
826 printf("0%" PRIo32, v);
827 break;
828 case TRACER_DISPLAY_BASE_10:
829 printf("%" PRId32, v);
830 break;
831 case TRACER_DISPLAY_BASE_16:
832 printf("0x%" PRIx32, v);
833 break;
834 default:
835 abort();
836 }
f611d0c3 837 break;
8bdd5c12 838 }
f611d0c3 839 case SIDE_TYPE_S64:
8bdd5c12
MD
840 {
841 int64_t v;
842
843 v = item->u.side_s64;
844 if (type_to_host_reverse_bo(type_desc))
845 v = side_bswap_64(v);
0e9be766 846 tracer_print_basic_type_header(type_desc);
1d9c515c
MD
847 switch (base) {
848 case TRACER_DISPLAY_BASE_2:
849 print_integer_binary(v, 64);
850 break;
851 case TRACER_DISPLAY_BASE_8:
852 printf("0%" PRIo64, v);
853 break;
854 case TRACER_DISPLAY_BASE_10:
855 printf("%" PRId64, v);
856 break;
857 case TRACER_DISPLAY_BASE_16:
858 printf("0x%" PRIx64, v);
859 break;
860 default:
861 abort();
862 }
f611d0c3 863 break;
8bdd5c12 864 }
dd6e76cb 865 case SIDE_TYPE_POINTER32:
f5e650d7 866 {
dd6e76cb 867 uint32_t v;
f5e650d7 868
dd6e76cb 869 v = item->u.side_u32;
f5e650d7 870 if (type_to_host_reverse_bo(type_desc))
dd6e76cb 871 v = side_bswap_32(v);
f5e650d7 872 tracer_print_basic_type_header(type_desc);
dd6e76cb
MD
873 printf("0x%" PRIx32, v);
874 break;
875 }
876 case SIDE_TYPE_POINTER64:
877 {
878 uint64_t v;
879
880 v = item->u.side_u64;
881 if (type_to_host_reverse_bo(type_desc))
882 v = side_bswap_64(v);
883 tracer_print_basic_type_header(type_desc);
884 printf("0x%" PRIx64, v);
f5e650d7
MD
885 break;
886 }
f7653b43 887 case SIDE_TYPE_BYTE:
0e9be766 888 tracer_print_basic_type_header(type_desc);
f7653b43 889 printf("0x%" PRIx8, item->u.side_byte);
7aec0d09 890 break;
79f677ba 891
d8be25de
MD
892 case SIDE_TYPE_ENUM:
893 print_enum(type_desc, item);
79f677ba
MD
894 break;
895
bab5d6e4 896 case SIDE_TYPE_ENUM_BITMAP:
af6aa6e1 897 print_enum_bitmap(type_desc, item);
ea32e5fc
MD
898 break;
899
fb25b355 900 case SIDE_TYPE_FLOAT_BINARY16:
8bdd5c12 901 {
fb25b355 902#if __HAVE_FLOAT16
8bdd5c12
MD
903 union {
904 _Float16 f;
905 uint16_t u;
906 } float16 = {
907 .f = item->u.side_float_binary16,
908 };
909
910 if (type_to_host_reverse_bo(type_desc))
911 float16.u = side_bswap_16(float16.u);
912 tracer_print_basic_type_header(type_desc);
913 printf("%g", (double) float16.f);
fb25b355
MD
914 break;
915#else
de1b3cd2 916 fprintf(stderr, "ERROR: Unsupported binary16 float type\n");
fb25b355
MD
917 abort();
918#endif
8bdd5c12 919 }
fb25b355 920 case SIDE_TYPE_FLOAT_BINARY32:
8bdd5c12 921 {
fb25b355 922#if __HAVE_FLOAT32
8bdd5c12
MD
923 union {
924 _Float32 f;
925 uint32_t u;
926 } float32 = {
927 .f = item->u.side_float_binary32,
928 };
929
930 if (type_to_host_reverse_bo(type_desc))
931 float32.u = side_bswap_32(float32.u);
932 tracer_print_basic_type_header(type_desc);
933 printf("%g", (double) float32.f);
fb25b355
MD
934 break;
935#else
de1b3cd2 936 fprintf(stderr, "ERROR: Unsupported binary32 float type\n");
fb25b355
MD
937 abort();
938#endif
8bdd5c12 939 }
fb25b355 940 case SIDE_TYPE_FLOAT_BINARY64:
8bdd5c12 941 {
fb25b355 942#if __HAVE_FLOAT64
8bdd5c12
MD
943 union {
944 _Float64 f;
945 uint64_t u;
946 } float64 = {
947 .f = item->u.side_float_binary64,
948 };
949
950 if (type_to_host_reverse_bo(type_desc))
951 float64.u = side_bswap_64(float64.u);
952 tracer_print_basic_type_header(type_desc);
953 printf("%g", (double) float64.f);
fb25b355
MD
954 break;
955#else
de1b3cd2 956 fprintf(stderr, "ERROR: Unsupported binary64 float type\n");
fb25b355
MD
957 abort();
958#endif
8bdd5c12 959 }
fb25b355 960 case SIDE_TYPE_FLOAT_BINARY128:
8bdd5c12 961 {
fb25b355 962#if __HAVE_FLOAT128
8bdd5c12
MD
963 union {
964 _Float128 f;
965 char arr[16];
966 } float128 = {
967 .f = item->u.side_float_binary128,
968 };
969
970 if (type_to_host_reverse_bo(type_desc))
971 side_bswap_128p(float128.arr);
972 tracer_print_basic_type_header(type_desc);
973 printf("%Lg", (long double) float128.f);
fb25b355
MD
974 break;
975#else
de1b3cd2 976 fprintf(stderr, "ERROR: Unsupported binary128 float type\n");
fb25b355
MD
977 abort();
978#endif
8bdd5c12 979 }
f611d0c3 980 case SIDE_TYPE_STRING:
0e9be766 981 tracer_print_basic_type_header(type_desc);
8549e629 982 printf("\"%s\"", (const char *)(uintptr_t) item->u.string);
f611d0c3
MD
983 break;
984 case SIDE_TYPE_STRUCT:
985 tracer_print_struct(type_desc, item->u.side_struct);
986 break;
987 case SIDE_TYPE_ARRAY:
988 tracer_print_array(type_desc, item->u.side_array);
989 break;
990 case SIDE_TYPE_VLA:
991 tracer_print_vla(type_desc, item->u.side_vla);
992 break;
993 case SIDE_TYPE_VLA_VISITOR:
352a4b77 994 tracer_print_vla_visitor(type_desc, item->u.side_vla_app_visitor_ctx);
f611d0c3 995 break;
ba845af5
MD
996 case SIDE_TYPE_ARRAY_U8:
997 case SIDE_TYPE_ARRAY_U16:
998 case SIDE_TYPE_ARRAY_U32:
999 case SIDE_TYPE_ARRAY_U64:
1000 case SIDE_TYPE_ARRAY_S8:
1001 case SIDE_TYPE_ARRAY_S16:
1002 case SIDE_TYPE_ARRAY_S32:
1003 case SIDE_TYPE_ARRAY_S64:
f7653b43 1004 case SIDE_TYPE_ARRAY_BYTE:
dd6e76cb
MD
1005 case SIDE_TYPE_ARRAY_POINTER32:
1006 case SIDE_TYPE_ARRAY_POINTER64:
ba845af5
MD
1007 tracer_print_array_fixint(type_desc, item);
1008 break;
1533629f
MD
1009 case SIDE_TYPE_VLA_U8:
1010 case SIDE_TYPE_VLA_U16:
1011 case SIDE_TYPE_VLA_U32:
1012 case SIDE_TYPE_VLA_U64:
1013 case SIDE_TYPE_VLA_S8:
1014 case SIDE_TYPE_VLA_S16:
1015 case SIDE_TYPE_VLA_S32:
1016 case SIDE_TYPE_VLA_S64:
f7653b43 1017 case SIDE_TYPE_VLA_BYTE:
dd6e76cb
MD
1018 case SIDE_TYPE_VLA_POINTER32:
1019 case SIDE_TYPE_VLA_POINTER64:
1533629f
MD
1020 tracer_print_vla_fixint(type_desc, item);
1021 break;
a2e2357e 1022 case SIDE_TYPE_DYNAMIC:
0e9be766 1023 tracer_print_basic_type_header(type_desc);
a2e2357e
MD
1024 tracer_print_dynamic(&item->u.dynamic);
1025 break;
f611d0c3 1026 default:
de1b3cd2 1027 fprintf(stderr, "<UNKNOWN TYPE>");
f611d0c3
MD
1028 abort();
1029 }
a848763d 1030 printf(" }");
f611d0c3
MD
1031}
1032
1033static
1034void tracer_print_field(const struct side_event_field *item_desc, const struct side_arg_vec *item)
1035{
19fa6aa2 1036 printf("%s: ", item_desc->field_name);
f611d0c3 1037 tracer_print_type(&item_desc->side_type, item);
f611d0c3
MD
1038}
1039
1040static
1041void tracer_print_struct(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc)
1042{
1043 const struct side_arg_vec *sav = sav_desc->sav;
1044 uint32_t side_sav_len = sav_desc->len;
1045 int i;
1046
c7a14585 1047 if (type_desc->u.side_struct->nr_fields != side_sav_len) {
de1b3cd2 1048 fprintf(stderr, "ERROR: number of fields mismatch between description and arguments of structure\n");
f611d0c3
MD
1049 abort();
1050 }
905c328e 1051 print_attributes("attr", ":", type_desc->u.side_struct->attr, type_desc->u.side_struct->nr_attr);
73b2b0c2
MD
1052 printf("%s", type_desc->u.side_struct->nr_attr ? ", " : "");
1053 printf("fields: { ");
f611d0c3
MD
1054 for (i = 0; i < side_sav_len; i++) {
1055 printf("%s", i ? ", " : "");
c7a14585 1056 tracer_print_field(&type_desc->u.side_struct->fields[i], &sav[i]);
f611d0c3 1057 }
d4328528 1058 printf(" }");
f611d0c3
MD
1059}
1060
1061static
1062void tracer_print_array(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc)
1063{
1064 const struct side_arg_vec *sav = sav_desc->sav;
1065 uint32_t side_sav_len = sav_desc->len;
1066 int i;
1067
1068 if (type_desc->u.side_array.length != side_sav_len) {
de1b3cd2 1069 fprintf(stderr, "ERROR: length mismatch between description and arguments of array\n");
f611d0c3
MD
1070 abort();
1071 }
905c328e 1072 print_attributes("attr", ":", type_desc->u.side_array.attr, type_desc->u.side_array.nr_attr);
d4328528 1073 printf("%s", type_desc->u.side_array.nr_attr ? ", " : "");
20574104 1074 printf("elements: ");
f611d0c3
MD
1075 printf("[ ");
1076 for (i = 0; i < side_sav_len; i++) {
1077 printf("%s", i ? ", " : "");
1078 tracer_print_type(type_desc->u.side_array.elem_type, &sav[i]);
1079 }
1080 printf(" ]");
1081}
1082
1083static
1084void tracer_print_vla(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc)
1085{
1086 const struct side_arg_vec *sav = sav_desc->sav;
1087 uint32_t side_sav_len = sav_desc->len;
1088 int i;
1089
905c328e 1090 print_attributes("attr", ":", type_desc->u.side_vla.attr, type_desc->u.side_vla.nr_attr);
d4328528 1091 printf("%s", type_desc->u.side_vla.nr_attr ? ", " : "");
20574104 1092 printf("elements: ");
f611d0c3
MD
1093 printf("[ ");
1094 for (i = 0; i < side_sav_len; i++) {
1095 printf("%s", i ? ", " : "");
1096 tracer_print_type(type_desc->u.side_vla.elem_type, &sav[i]);
1097 }
1098 printf(" ]");
1099}
1100
352a4b77
MD
1101struct tracer_visitor_priv {
1102 const struct side_type_description *elem_type;
1103 int i;
1104};
1105
1106static
1107enum side_visitor_status tracer_write_elem_cb(const struct side_tracer_visitor_ctx *tracer_ctx,
1108 const struct side_arg_vec *elem)
1109{
1110 struct tracer_visitor_priv *tracer_priv = tracer_ctx->priv;
1111
1112 printf("%s", tracer_priv->i++ ? ", " : "");
1113 tracer_print_type(tracer_priv->elem_type, elem);
1114 return SIDE_VISITOR_STATUS_OK;
1115}
1116
f611d0c3 1117static
352a4b77 1118void tracer_print_vla_visitor(const struct side_type_description *type_desc, void *app_ctx)
f611d0c3
MD
1119{
1120 enum side_visitor_status status;
352a4b77
MD
1121 struct tracer_visitor_priv tracer_priv = {
1122 .elem_type = type_desc->u.side_vla_visitor.elem_type,
1123 .i = 0,
1124 };
1125 const struct side_tracer_visitor_ctx tracer_ctx = {
1126 .write_elem = tracer_write_elem_cb,
1127 .priv = &tracer_priv,
1128 };
f611d0c3 1129
905c328e 1130 print_attributes("attr", ":", type_desc->u.side_vla_visitor.attr, type_desc->u.side_vla_visitor.nr_attr);
d4328528 1131 printf("%s", type_desc->u.side_vla_visitor.nr_attr ? ", " : "");
20574104 1132 printf("elements: ");
352a4b77
MD
1133 printf("[ ");
1134 status = type_desc->u.side_vla_visitor.visitor(&tracer_ctx, app_ctx);
1135 switch (status) {
1136 case SIDE_VISITOR_STATUS_OK:
1137 break;
1138 case SIDE_VISITOR_STATUS_ERROR:
de1b3cd2 1139 fprintf(stderr, "ERROR: Visitor error\n");
f611d0c3 1140 abort();
f611d0c3
MD
1141 }
1142 printf(" ]");
f611d0c3
MD
1143}
1144
ba845af5
MD
1145void tracer_print_array_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item)
1146{
1147 const struct side_type_description *elem_type = type_desc->u.side_array.elem_type;
1148 uint32_t side_sav_len = type_desc->u.side_array.length;
1149 void *p = item->u.side_array_fixint;
1150 enum side_type side_type;
1151 int i;
1152
905c328e 1153 print_attributes("attr", ":", type_desc->u.side_array.attr, type_desc->u.side_array.nr_attr);
d4328528 1154 printf("%s", type_desc->u.side_array.nr_attr ? ", " : "");
20574104 1155 printf("elements: ");
1e8256c9
MD
1156 switch (item->type) {
1157 case SIDE_TYPE_ARRAY_U8:
1158 if (elem_type->type != SIDE_TYPE_U8)
1159 goto type_error;
1160 break;
1161 case SIDE_TYPE_ARRAY_U16:
1162 if (elem_type->type != SIDE_TYPE_U16)
1163 goto type_error;
1164 break;
1165 case SIDE_TYPE_ARRAY_U32:
1166 if (elem_type->type != SIDE_TYPE_U32)
1167 goto type_error;
1168 break;
1169 case SIDE_TYPE_ARRAY_U64:
1170 if (elem_type->type != SIDE_TYPE_U64)
1171 goto type_error;
1172 break;
1173 case SIDE_TYPE_ARRAY_S8:
1174 if (elem_type->type != SIDE_TYPE_S8)
1175 goto type_error;
1176 break;
1177 case SIDE_TYPE_ARRAY_S16:
1178 if (elem_type->type != SIDE_TYPE_S16)
1179 goto type_error;
1180 break;
1181 case SIDE_TYPE_ARRAY_S32:
1182 if (elem_type->type != SIDE_TYPE_S32)
1183 goto type_error;
1184 break;
1185 case SIDE_TYPE_ARRAY_S64:
1186 if (elem_type->type != SIDE_TYPE_S64)
1187 goto type_error;
1188 break;
f7653b43
MD
1189 case SIDE_TYPE_ARRAY_BYTE:
1190 if (elem_type->type != SIDE_TYPE_BYTE)
7aec0d09
MD
1191 goto type_error;
1192 break;
dd6e76cb
MD
1193 case SIDE_TYPE_ARRAY_POINTER32:
1194 if (elem_type->type != SIDE_TYPE_POINTER32)
1195 goto type_error;
1196 case SIDE_TYPE_ARRAY_POINTER64:
1197 if (elem_type->type != SIDE_TYPE_POINTER64)
f5e650d7
MD
1198 goto type_error;
1199 break;
1e8256c9
MD
1200 default:
1201 goto type_error;
ba845af5 1202 }
1e8256c9 1203 side_type = elem_type->type;
ba845af5 1204
1533629f
MD
1205 printf("[ ");
1206 for (i = 0; i < side_sav_len; i++) {
1207 struct side_arg_vec sav_elem = {
1208 .type = side_type,
1209 };
1210
1211 switch (side_type) {
1212 case SIDE_TYPE_U8:
1213 sav_elem.u.side_u8 = ((const uint8_t *) p)[i];
1214 break;
1215 case SIDE_TYPE_S8:
1216 sav_elem.u.side_s8 = ((const int8_t *) p)[i];
1217 break;
1218 case SIDE_TYPE_U16:
1219 sav_elem.u.side_u16 = ((const uint16_t *) p)[i];
1220 break;
1221 case SIDE_TYPE_S16:
1222 sav_elem.u.side_s16 = ((const int16_t *) p)[i];
1223 break;
1224 case SIDE_TYPE_U32:
1225 sav_elem.u.side_u32 = ((const uint32_t *) p)[i];
1226 break;
1227 case SIDE_TYPE_S32:
1228 sav_elem.u.side_s32 = ((const int32_t *) p)[i];
1229 break;
1230 case SIDE_TYPE_U64:
1231 sav_elem.u.side_u64 = ((const uint64_t *) p)[i];
1232 break;
1233 case SIDE_TYPE_S64:
1234 sav_elem.u.side_s64 = ((const int64_t *) p)[i];
1235 break;
f7653b43
MD
1236 case SIDE_TYPE_BYTE:
1237 sav_elem.u.side_byte = ((const uint8_t *) p)[i];
7aec0d09 1238 break;
dd6e76cb
MD
1239 case SIDE_TYPE_POINTER32:
1240 sav_elem.u.side_u32 = ((const uint32_t *) p)[i];
1241 break;
1242 case SIDE_TYPE_POINTER64:
1243 sav_elem.u.side_u64 = ((const uint64_t *) p)[i];
f5e650d7 1244 break;
1533629f
MD
1245
1246 default:
de1b3cd2 1247 fprintf(stderr, "ERROR: Unexpected type\n");
1533629f
MD
1248 abort();
1249 }
1250
1251 printf("%s", i ? ", " : "");
1252 tracer_print_type(elem_type, &sav_elem);
1253 }
1254 printf(" ]");
1255 return;
1256
1257type_error:
de1b3cd2 1258 fprintf(stderr, "ERROR: type mismatch\n");
1533629f
MD
1259 abort();
1260}
1261
1262void tracer_print_vla_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item)
1263{
1264 const struct side_type_description *elem_type = type_desc->u.side_vla.elem_type;
1265 uint32_t side_sav_len = item->u.side_vla_fixint.length;
1266 void *p = item->u.side_vla_fixint.p;
1267 enum side_type side_type;
1268 int i;
1269
905c328e 1270 print_attributes("attr", ":", type_desc->u.side_vla.attr, type_desc->u.side_vla.nr_attr);
d4328528 1271 printf("%s", type_desc->u.side_vla.nr_attr ? ", " : "");
20574104 1272 printf("elements: ");
a2e2357e
MD
1273 switch (item->type) {
1274 case SIDE_TYPE_VLA_U8:
1275 if (elem_type->type != SIDE_TYPE_U8)
1533629f 1276 goto type_error;
a2e2357e
MD
1277 break;
1278 case SIDE_TYPE_VLA_U16:
1279 if (elem_type->type != SIDE_TYPE_U16)
1533629f 1280 goto type_error;
a2e2357e
MD
1281 break;
1282 case SIDE_TYPE_VLA_U32:
1283 if (elem_type->type != SIDE_TYPE_U32)
1284 goto type_error;
1285 break;
1286 case SIDE_TYPE_VLA_U64:
1287 if (elem_type->type != SIDE_TYPE_U64)
1288 goto type_error;
1289 break;
1290 case SIDE_TYPE_VLA_S8:
1291 if (elem_type->type != SIDE_TYPE_S8)
1292 goto type_error;
1293 break;
1294 case SIDE_TYPE_VLA_S16:
1295 if (elem_type->type != SIDE_TYPE_S16)
1296 goto type_error;
1297 break;
1298 case SIDE_TYPE_VLA_S32:
1299 if (elem_type->type != SIDE_TYPE_S32)
1300 goto type_error;
1301 break;
1302 case SIDE_TYPE_VLA_S64:
1303 if (elem_type->type != SIDE_TYPE_S64)
1304 goto type_error;
1305 break;
f7653b43
MD
1306 case SIDE_TYPE_VLA_BYTE:
1307 if (elem_type->type != SIDE_TYPE_BYTE)
7aec0d09
MD
1308 goto type_error;
1309 break;
dd6e76cb
MD
1310 case SIDE_TYPE_VLA_POINTER32:
1311 if (elem_type->type != SIDE_TYPE_POINTER32)
1312 goto type_error;
1313 case SIDE_TYPE_VLA_POINTER64:
1314 if (elem_type->type != SIDE_TYPE_POINTER64)
f5e650d7
MD
1315 goto type_error;
1316 break;
a2e2357e
MD
1317 default:
1318 goto type_error;
1533629f 1319 }
a2e2357e 1320 side_type = elem_type->type;
1533629f 1321
ba845af5
MD
1322 printf("[ ");
1323 for (i = 0; i < side_sav_len; i++) {
1324 struct side_arg_vec sav_elem = {
1325 .type = side_type,
1326 };
1327
1328 switch (side_type) {
1329 case SIDE_TYPE_U8:
1330 sav_elem.u.side_u8 = ((const uint8_t *) p)[i];
1331 break;
1332 case SIDE_TYPE_S8:
1333 sav_elem.u.side_s8 = ((const int8_t *) p)[i];
1334 break;
1335 case SIDE_TYPE_U16:
1336 sav_elem.u.side_u16 = ((const uint16_t *) p)[i];
1337 break;
1338 case SIDE_TYPE_S16:
1339 sav_elem.u.side_s16 = ((const int16_t *) p)[i];
1340 break;
1341 case SIDE_TYPE_U32:
1342 sav_elem.u.side_u32 = ((const uint32_t *) p)[i];
1343 break;
1344 case SIDE_TYPE_S32:
1345 sav_elem.u.side_s32 = ((const int32_t *) p)[i];
1346 break;
1347 case SIDE_TYPE_U64:
1348 sav_elem.u.side_u64 = ((const uint64_t *) p)[i];
1349 break;
1350 case SIDE_TYPE_S64:
1351 sav_elem.u.side_s64 = ((const int64_t *) p)[i];
1352 break;
f7653b43
MD
1353 case SIDE_TYPE_BYTE:
1354 sav_elem.u.side_byte = ((const uint8_t *) p)[i];
7aec0d09 1355 break;
dd6e76cb
MD
1356 case SIDE_TYPE_POINTER32:
1357 sav_elem.u.side_u32 = ((const uint32_t *) p)[i];
1358 break;
1359 case SIDE_TYPE_POINTER64:
1360 sav_elem.u.side_u64 = ((const uint64_t *) p)[i];
f5e650d7 1361 break;
ba845af5
MD
1362
1363 default:
de1b3cd2 1364 fprintf(stderr, "ERROR: Unexpected type\n");
ba845af5
MD
1365 abort();
1366 }
1367
1368 printf("%s", i ? ", " : "");
1369 tracer_print_type(elem_type, &sav_elem);
1370 }
1371 printf(" ]");
1372 return;
1373
1374type_error:
de1b3cd2 1375 fprintf(stderr, "ERROR: type mismatch\n");
ba845af5
MD
1376 abort();
1377}
1378
a2e2357e 1379static
c208889e 1380void tracer_print_dynamic_struct(const struct side_arg_dynamic_event_struct *dynamic_struct)
a2e2357e 1381{
c208889e
MD
1382 const struct side_arg_dynamic_event_field *fields = dynamic_struct->fields;
1383 uint32_t len = dynamic_struct->len;
465e5e7e
MD
1384 int i;
1385
905c328e 1386 print_attributes("attr", "::", dynamic_struct->attr, dynamic_struct->nr_attr);
8d20e708 1387 printf("%s", dynamic_struct->nr_attr ? ", " : "");
f0061366 1388 printf("fields:: ");
465e5e7e
MD
1389 printf("[ ");
1390 for (i = 0; i < len; i++) {
1391 printf("%s", i ? ", " : "");
1392 printf("%s:: ", fields[i].field_name);
1393 tracer_print_dynamic(&fields[i].elem);
1394 }
1395 printf(" ]");
a2e2357e
MD
1396}
1397
2b359235
MD
1398struct tracer_dynamic_struct_visitor_priv {
1399 int i;
1400};
1401
1402static
1403enum side_visitor_status tracer_dynamic_struct_write_elem_cb(
1404 const struct side_tracer_dynamic_struct_visitor_ctx *tracer_ctx,
1405 const struct side_arg_dynamic_event_field *dynamic_field)
1406{
1407 struct tracer_dynamic_struct_visitor_priv *tracer_priv = tracer_ctx->priv;
1408
1409 printf("%s", tracer_priv->i++ ? ", " : "");
1410 printf("%s:: ", dynamic_field->field_name);
1411 tracer_print_dynamic(&dynamic_field->elem);
1412 return SIDE_VISITOR_STATUS_OK;
1413}
1414
a2e2357e 1415static
c208889e 1416void tracer_print_dynamic_struct_visitor(const struct side_arg_dynamic_vec *item)
a2e2357e 1417{
2b359235
MD
1418 enum side_visitor_status status;
1419 struct tracer_dynamic_struct_visitor_priv tracer_priv = {
1420 .i = 0,
1421 };
1422 const struct side_tracer_dynamic_struct_visitor_ctx tracer_ctx = {
1423 .write_field = tracer_dynamic_struct_write_elem_cb,
1424 .priv = &tracer_priv,
1425 };
1426 void *app_ctx = item->u.side_dynamic_struct_visitor.app_ctx;
1427
905c328e 1428 print_attributes("attr", "::", item->u.side_dynamic_struct_visitor.attr, item->u.side_dynamic_struct_visitor.nr_attr);
8d20e708 1429 printf("%s", item->u.side_dynamic_struct_visitor.nr_attr ? ", " : "");
f0061366 1430 printf("fields:: ");
2b359235
MD
1431 printf("[ ");
1432 status = item->u.side_dynamic_struct_visitor.visitor(&tracer_ctx, app_ctx);
1433 switch (status) {
1434 case SIDE_VISITOR_STATUS_OK:
1435 break;
1436 case SIDE_VISITOR_STATUS_ERROR:
de1b3cd2 1437 fprintf(stderr, "ERROR: Visitor error\n");
2b359235
MD
1438 abort();
1439 }
1440 printf(" ]");
a2e2357e
MD
1441}
1442
1443static
1444void tracer_print_dynamic_vla(const struct side_arg_dynamic_vec_vla *vla)
1445{
1446 const struct side_arg_dynamic_vec *sav = vla->sav;
1447 uint32_t side_sav_len = vla->len;
1448 int i;
1449
905c328e 1450 print_attributes("attr", "::", vla->attr, vla->nr_attr);
8d20e708 1451 printf("%s", vla->nr_attr ? ", " : "");
f0061366 1452 printf("elements:: ");
a2e2357e
MD
1453 printf("[ ");
1454 for (i = 0; i < side_sav_len; i++) {
1455 printf("%s", i ? ", " : "");
1456 tracer_print_dynamic(&sav[i]);
1457 }
1458 printf(" ]");
1459}
1460
8ceca0cd
MD
1461struct tracer_dynamic_vla_visitor_priv {
1462 int i;
1463};
1464
1465static
1466enum side_visitor_status tracer_dynamic_vla_write_elem_cb(
1467 const struct side_tracer_dynamic_vla_visitor_ctx *tracer_ctx,
1468 const struct side_arg_dynamic_vec *elem)
1469{
1470 struct tracer_dynamic_vla_visitor_priv *tracer_priv = tracer_ctx->priv;
1471
1472 printf("%s", tracer_priv->i++ ? ", " : "");
1473 tracer_print_dynamic(elem);
1474 return SIDE_VISITOR_STATUS_OK;
1475}
1476
a2e2357e
MD
1477static
1478void tracer_print_dynamic_vla_visitor(const struct side_arg_dynamic_vec *item)
1479{
8ceca0cd
MD
1480 enum side_visitor_status status;
1481 struct tracer_dynamic_vla_visitor_priv tracer_priv = {
1482 .i = 0,
1483 };
1484 const struct side_tracer_dynamic_vla_visitor_ctx tracer_ctx = {
1485 .write_elem = tracer_dynamic_vla_write_elem_cb,
1486 .priv = &tracer_priv,
1487 };
1488 void *app_ctx = item->u.side_dynamic_vla_visitor.app_ctx;
1489
905c328e 1490 print_attributes("attr", "::", item->u.side_dynamic_vla_visitor.attr, item->u.side_dynamic_vla_visitor.nr_attr);
8d20e708 1491 printf("%s", item->u.side_dynamic_vla_visitor.nr_attr ? ", " : "");
f0061366 1492 printf("elements:: ");
8ceca0cd
MD
1493 printf("[ ");
1494 status = item->u.side_dynamic_vla_visitor.visitor(&tracer_ctx, app_ctx);
1495 switch (status) {
1496 case SIDE_VISITOR_STATUS_OK:
1497 break;
1498 case SIDE_VISITOR_STATUS_ERROR:
de1b3cd2 1499 fprintf(stderr, "ERROR: Visitor error\n");
8ceca0cd
MD
1500 abort();
1501 }
1502 printf(" ]");
a2e2357e
MD
1503}
1504
0e9be766
MD
1505static
1506void tracer_print_dynamic_basic_type_header(const struct side_arg_dynamic_vec *item)
1507{
905c328e 1508 print_attributes("attr", "::", item->u.side_basic.attr, item->u.side_basic.nr_attr);
0e9be766
MD
1509 printf("%s", item->u.side_basic.nr_attr ? ", " : "");
1510 printf("value:: ");
1511}
1512
a2e2357e
MD
1513static
1514void tracer_print_dynamic(const struct side_arg_dynamic_vec *item)
1515{
1d9c515c
MD
1516 enum tracer_display_base base = TRACER_DISPLAY_BASE_10;
1517
1518 switch (item->dynamic_type) {
1519 case SIDE_DYNAMIC_TYPE_U8:
1520 case SIDE_DYNAMIC_TYPE_U16:
1521 case SIDE_DYNAMIC_TYPE_U32:
1522 case SIDE_DYNAMIC_TYPE_U64:
1523 case SIDE_DYNAMIC_TYPE_S8:
1524 case SIDE_DYNAMIC_TYPE_S16:
1525 case SIDE_DYNAMIC_TYPE_S32:
1526 case SIDE_DYNAMIC_TYPE_S64:
1527 base = get_attr_display_base(item->u.side_basic.attr,
1528 item->u.side_basic.nr_attr);
1529 break;
1530 default:
1531 break;
1532 }
1533
1534
808bd9bf 1535 printf("{ ");
1e8256c9 1536 switch (item->dynamic_type) {
a2e2357e 1537 case SIDE_DYNAMIC_TYPE_NULL:
0e9be766 1538 tracer_print_dynamic_basic_type_header(item);
a2e2357e
MD
1539 printf("<NULL TYPE>");
1540 break;
4f40d951 1541 case SIDE_DYNAMIC_TYPE_BOOL:
0e9be766 1542 tracer_print_dynamic_basic_type_header(item);
8d20e708 1543 printf("%s", item->u.side_basic.u.side_bool ? "true" : "false");
4f40d951 1544 break;
a2e2357e 1545 case SIDE_DYNAMIC_TYPE_U8:
1d9c515c
MD
1546 {
1547 uint8_t v;
1548
1549 v = item->u.side_basic.u.side_u8;
0e9be766 1550 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1551 switch (base) {
1552 case TRACER_DISPLAY_BASE_2:
1553 print_integer_binary(v, 8);
1554 break;
1555 case TRACER_DISPLAY_BASE_8:
1556 printf("0%" PRIo8, v);
1557 break;
1558 case TRACER_DISPLAY_BASE_10:
1559 printf("%" PRIu8, v);
1560 break;
1561 case TRACER_DISPLAY_BASE_16:
1562 printf("0x%" PRIx8, v);
1563 break;
1564 default:
1565 abort();
1566 }
a2e2357e 1567 break;
1d9c515c 1568 }
a2e2357e 1569 case SIDE_DYNAMIC_TYPE_U16:
8bdd5c12
MD
1570 {
1571 uint16_t v;
1572
1573 v = item->u.side_basic.u.side_u16;
1574 if (dynamic_type_to_host_reverse_bo(item))
1575 v = side_bswap_16(v);
0e9be766 1576 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1577 switch (base) {
1578 case TRACER_DISPLAY_BASE_2:
1579 print_integer_binary(v, 16);
1580 break;
1581 case TRACER_DISPLAY_BASE_8:
1582 printf("0%" PRIo16, v);
1583 break;
1584 case TRACER_DISPLAY_BASE_10:
1585 printf("%" PRIu16, v);
1586 break;
1587 case TRACER_DISPLAY_BASE_16:
1588 printf("0x%" PRIx16, v);
1589 break;
1590 default:
1591 abort();
1592 }
a2e2357e 1593 break;
8bdd5c12 1594 }
a2e2357e 1595 case SIDE_DYNAMIC_TYPE_U32:
8bdd5c12
MD
1596 {
1597 uint32_t v;
1598
1599 v = item->u.side_basic.u.side_u32;
1600 if (dynamic_type_to_host_reverse_bo(item))
1601 v = side_bswap_32(v);
0e9be766 1602 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1603 switch (base) {
1604 case TRACER_DISPLAY_BASE_2:
1605 print_integer_binary(v, 32);
1606 break;
1607 case TRACER_DISPLAY_BASE_8:
1608 printf("0%" PRIo32, v);
1609 break;
1610 case TRACER_DISPLAY_BASE_10:
1611 printf("%" PRIu32, v);
1612 break;
1613 case TRACER_DISPLAY_BASE_16:
1614 printf("0x%" PRIx32, v);
1615 break;
1616 default:
1617 abort();
1618 }
a2e2357e 1619 break;
8bdd5c12 1620 }
a2e2357e 1621 case SIDE_DYNAMIC_TYPE_U64:
8bdd5c12
MD
1622 {
1623 uint64_t v;
1624
1625 v = item->u.side_basic.u.side_u64;
1626 if (dynamic_type_to_host_reverse_bo(item))
1627 v = side_bswap_64(v);
0e9be766 1628 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1629 switch (base) {
1630 case TRACER_DISPLAY_BASE_2:
1631 print_integer_binary(v, 64);
1632 break;
1633 case TRACER_DISPLAY_BASE_8:
1634 printf("0%" PRIo64, v);
1635 break;
1636 case TRACER_DISPLAY_BASE_10:
1637 printf("%" PRIu64, v);
1638 break;
1639 case TRACER_DISPLAY_BASE_16:
1640 printf("0x%" PRIx64, v);
1641 break;
1642 default:
1643 abort();
1644 }
a2e2357e 1645 break;
8bdd5c12 1646 }
a2e2357e 1647 case SIDE_DYNAMIC_TYPE_S8:
1d9c515c
MD
1648 {
1649 int8_t v;
1650
1651 v = item->u.side_basic.u.side_s8;
0e9be766 1652 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1653 switch (base) {
1654 case TRACER_DISPLAY_BASE_2:
1655 print_integer_binary(v, 8);
1656 break;
1657 case TRACER_DISPLAY_BASE_8:
1658 printf("0%" PRIo8, v);
1659 break;
1660 case TRACER_DISPLAY_BASE_10:
1661 printf("%" PRId8, v);
1662 break;
1663 case TRACER_DISPLAY_BASE_16:
1664 printf("0x%" PRIx8, v);
1665 break;
1666 default:
1667 abort();
1668 }
a2e2357e 1669 break;
1d9c515c 1670 }
a2e2357e 1671 case SIDE_DYNAMIC_TYPE_S16:
8bdd5c12
MD
1672 {
1673 int16_t v;
1674
1675 v = item->u.side_basic.u.side_u16;
1676 if (dynamic_type_to_host_reverse_bo(item))
1677 v = side_bswap_16(v);
0e9be766 1678 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1679 switch (base) {
1680 case TRACER_DISPLAY_BASE_2:
1681 print_integer_binary(v, 16);
1682 break;
1683 case TRACER_DISPLAY_BASE_8:
1684 printf("0%" PRIo16, v);
1685 break;
1686 case TRACER_DISPLAY_BASE_10:
1687 printf("%" PRId16, v);
1688 break;
1689 case TRACER_DISPLAY_BASE_16:
1690 printf("0x%" PRIx16, v);
1691 break;
1692 default:
1693 abort();
1694 }
a2e2357e 1695 break;
8bdd5c12 1696 }
a2e2357e 1697 case SIDE_DYNAMIC_TYPE_S32:
8bdd5c12
MD
1698 {
1699 int32_t v;
1700
1701 v = item->u.side_basic.u.side_u32;
1702 if (dynamic_type_to_host_reverse_bo(item))
1703 v = side_bswap_32(v);
0e9be766 1704 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1705 switch (base) {
1706 case TRACER_DISPLAY_BASE_2:
1707 print_integer_binary(v, 32);
1708 break;
1709 case TRACER_DISPLAY_BASE_8:
1710 printf("0%" PRIo32, v);
1711 break;
1712 case TRACER_DISPLAY_BASE_10:
1713 printf("%" PRId32, v);
1714 break;
1715 case TRACER_DISPLAY_BASE_16:
1716 printf("0x%" PRIx32, v);
1717 break;
1718 default:
1719 abort();
1720 }
a2e2357e 1721 break;
8bdd5c12 1722 }
a2e2357e 1723 case SIDE_DYNAMIC_TYPE_S64:
8bdd5c12
MD
1724 {
1725 int64_t v;
1726
1727 v = item->u.side_basic.u.side_u64;
1728 if (dynamic_type_to_host_reverse_bo(item))
1729 v = side_bswap_64(v);
0e9be766 1730 tracer_print_dynamic_basic_type_header(item);
1d9c515c
MD
1731 switch (base) {
1732 case TRACER_DISPLAY_BASE_2:
1733 print_integer_binary(v, 64);
1734 break;
1735 case TRACER_DISPLAY_BASE_8:
1736 printf("0%" PRIo64, v);
1737 break;
1738 case TRACER_DISPLAY_BASE_10:
1739 printf("%" PRId64, v);
1740 break;
1741 case TRACER_DISPLAY_BASE_16:
1742 printf("0x%" PRIx64, v);
1743 break;
1744 default:
1745 abort();
1746 }
a2e2357e 1747 break;
8bdd5c12 1748 }
f7653b43 1749 case SIDE_DYNAMIC_TYPE_BYTE:
0e9be766 1750 tracer_print_dynamic_basic_type_header(item);
f7653b43 1751 printf("0x%" PRIx8, item->u.side_basic.u.side_byte);
199e7aa9 1752 break;
dd6e76cb 1753 case SIDE_DYNAMIC_TYPE_POINTER32:
f5e650d7 1754 {
dd6e76cb 1755 uint32_t v;
f5e650d7 1756
dd6e76cb 1757 v = item->u.side_basic.u.side_u32;
f5e650d7 1758 if (dynamic_type_to_host_reverse_bo(item))
dd6e76cb
MD
1759 v = side_bswap_32(v);
1760 tracer_print_dynamic_basic_type_header(item);
1761 printf("0x%" PRIx32, v);
1762 break;
1763 }
1764
1765 case SIDE_DYNAMIC_TYPE_POINTER64:
1766 {
1767 uint64_t v;
1768
1769 v = item->u.side_basic.u.side_u64;
1770 if (dynamic_type_to_host_reverse_bo(item))
1771 v = side_bswap_64(v);
f5e650d7 1772 tracer_print_dynamic_basic_type_header(item);
dd6e76cb 1773 printf("0x%" PRIx64, v);
f5e650d7
MD
1774 break;
1775 }
199e7aa9 1776
fb25b355 1777 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY16:
8bdd5c12 1778 {
fb25b355 1779#if __HAVE_FLOAT16
8bdd5c12
MD
1780 union {
1781 _Float16 f;
1782 uint16_t u;
1783 } float16 = {
1784 .f = item->u.side_basic.u.side_float_binary16,
1785 };
1786
1787 if (dynamic_type_to_host_reverse_bo(item))
1788 float16.u = side_bswap_16(float16.u);
1789 tracer_print_dynamic_basic_type_header(item);
1790 printf("%g", (double) float16.f);
fb25b355
MD
1791 break;
1792#else
de1b3cd2 1793 fprintf(stderr, "ERROR: Unsupported binary16 float type\n");
fb25b355
MD
1794 abort();
1795#endif
8bdd5c12 1796 }
fb25b355 1797 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY32:
8bdd5c12 1798 {
fb25b355 1799#if __HAVE_FLOAT32
8bdd5c12
MD
1800 union {
1801 _Float32 f;
1802 uint32_t u;
1803 } float32 = {
1804 .f = item->u.side_basic.u.side_float_binary32,
1805 };
1806
1807 if (dynamic_type_to_host_reverse_bo(item))
1808 float32.u = side_bswap_32(float32.u);
1809 tracer_print_dynamic_basic_type_header(item);
1810 printf("%g", (double) float32.f);
fb25b355
MD
1811 break;
1812#else
de1b3cd2 1813 fprintf(stderr, "ERROR: Unsupported binary32 float type\n");
fb25b355
MD
1814 abort();
1815#endif
8bdd5c12 1816 }
fb25b355 1817 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY64:
8bdd5c12 1818 {
fb25b355 1819#if __HAVE_FLOAT64
8bdd5c12
MD
1820 union {
1821 _Float64 f;
1822 uint64_t u;
1823 } float64 = {
1824 .f = item->u.side_basic.u.side_float_binary64,
1825 };
1826
1827 if (dynamic_type_to_host_reverse_bo(item))
1828 float64.u = side_bswap_64(float64.u);
1829 tracer_print_dynamic_basic_type_header(item);
1830 printf("%g", (double) float64.f);
fb25b355
MD
1831 break;
1832#else
de1b3cd2 1833 fprintf(stderr, "ERROR: Unsupported binary64 float type\n");
fb25b355
MD
1834 abort();
1835#endif
8bdd5c12 1836 }
fb25b355 1837 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY128:
8bdd5c12 1838 {
fb25b355 1839#if __HAVE_FLOAT128
8bdd5c12
MD
1840 union {
1841 _Float128 f;
1842 char arr[16];
1843 } float128 = {
1844 .f = item->u.side_basic.u.side_float_binary128,
1845 };
1846
1847 if (dynamic_type_to_host_reverse_bo(item))
1848 side_bswap_128p(float128.arr);
1849 tracer_print_dynamic_basic_type_header(item);
1850 printf("%Lg", (long double) float128.f);
fb25b355
MD
1851 break;
1852#else
de1b3cd2 1853 fprintf(stderr, "ERROR: Unsupported binary128 float type\n");
fb25b355
MD
1854 abort();
1855#endif
8bdd5c12 1856 }
a2e2357e 1857 case SIDE_DYNAMIC_TYPE_STRING:
0e9be766 1858 tracer_print_dynamic_basic_type_header(item);
8549e629 1859 printf("\"%s\"", (const char *)(uintptr_t) item->u.side_basic.u.string);
a2e2357e 1860 break;
c208889e
MD
1861 case SIDE_DYNAMIC_TYPE_STRUCT:
1862 tracer_print_dynamic_struct(item->u.side_dynamic_struct);
a2e2357e 1863 break;
c208889e
MD
1864 case SIDE_DYNAMIC_TYPE_STRUCT_VISITOR:
1865 tracer_print_dynamic_struct_visitor(item);
a2e2357e
MD
1866 break;
1867 case SIDE_DYNAMIC_TYPE_VLA:
1868 tracer_print_dynamic_vla(item->u.side_dynamic_vla);
1869 break;
1870 case SIDE_DYNAMIC_TYPE_VLA_VISITOR:
1871 tracer_print_dynamic_vla_visitor(item);
1872 break;
1873 default:
de1b3cd2 1874 fprintf(stderr, "<UNKNOWN TYPE>");
a2e2357e
MD
1875 abort();
1876 }
808bd9bf 1877 printf(" }");
a2e2357e
MD
1878}
1879
68f8cfbe
MD
1880static
1881void tracer_print_static_fields(const struct side_event_description *desc,
1882 const struct side_arg_vec_description *sav_desc,
1883 int *nr_items)
f611d0c3
MD
1884{
1885 const struct side_arg_vec *sav = sav_desc->sav;
1886 uint32_t side_sav_len = sav_desc->len;
1887 int i;
1888
65010f43 1889 printf("provider: %s, event: %s", desc->provider_name, desc->event_name);
f611d0c3 1890 if (desc->nr_fields != side_sav_len) {
de1b3cd2 1891 fprintf(stderr, "ERROR: number of fields mismatch between description and arguments\n");
f611d0c3
MD
1892 abort();
1893 }
905c328e 1894 print_attributes(", attr", ":", desc->attr, desc->nr_attr);
a848763d 1895 printf("%s", side_sav_len ? ", fields: [ " : "");
f611d0c3
MD
1896 for (i = 0; i < side_sav_len; i++) {
1897 printf("%s", i ? ", " : "");
1898 tracer_print_field(&desc->fields[i], &sav[i]);
1899 }
68f8cfbe
MD
1900 if (nr_items)
1901 *nr_items = i;
c7d338e2
MD
1902 if (side_sav_len)
1903 printf(" ]");
68f8cfbe
MD
1904}
1905
4a7d8700
MD
1906void tracer_call(const struct side_event_description *desc,
1907 const struct side_arg_vec_description *sav_desc,
1908 void *priv __attribute__((unused)))
68f8cfbe 1909{
a848763d
MD
1910 int nr_fields = 0;
1911
a848763d 1912 tracer_print_static_fields(desc, sav_desc, &nr_fields);
f611d0c3
MD
1913 printf("\n");
1914}
19fa6aa2
MD
1915
1916void tracer_call_variadic(const struct side_event_description *desc,
4a7d8700
MD
1917 const struct side_arg_vec_description *sav_desc,
1918 const struct side_arg_dynamic_event_struct *var_struct,
1919 void *priv __attribute__((unused)))
19fa6aa2 1920{
68f8cfbe
MD
1921 uint32_t var_struct_len = var_struct->len;
1922 int nr_fields = 0, i;
19fa6aa2 1923
68f8cfbe
MD
1924 tracer_print_static_fields(desc, sav_desc, &nr_fields);
1925
8a25ce77 1926 if (side_unlikely(!(desc->flags & SIDE_EVENT_FLAG_VARIADIC))) {
de1b3cd2 1927 fprintf(stderr, "ERROR: unexpected non-variadic event description\n");
8a25ce77
MD
1928 abort();
1929 }
905c328e
MD
1930 print_attributes(", attr ", "::", var_struct->attr, var_struct->nr_attr);
1931 printf("%s", var_struct_len ? ", fields:: [ " : "");
68f8cfbe 1932 for (i = 0; i < var_struct_len; i++, nr_fields++) {
c7d338e2 1933 printf("%s", i ? ", " : "");
68f8cfbe
MD
1934 printf("%s:: ", var_struct->fields[i].field_name);
1935 tracer_print_dynamic(&var_struct->fields[i].elem);
19fa6aa2 1936 }
a848763d
MD
1937 if (i)
1938 printf(" ]");
19fa6aa2
MD
1939 printf("\n");
1940}
1e8aec23
MD
1941
1942void tracer_event_notification(enum side_tracer_notification notif,
1943 struct side_event_description **events, uint32_t nr_events, void *priv)
1944{
1945 uint32_t i;
314c22c3 1946 int ret;
1e8aec23
MD
1947
1948 printf("----------------------------------------------------------\n");
1949 printf("Tracer notified of events %s\n",
314c22c3 1950 notif == SIDE_TRACER_NOTIFICATION_INSERT_EVENTS ? "inserted" : "removed");
1e8aec23
MD
1951 for (i = 0; i < nr_events; i++) {
1952 struct side_event_description *event = events[i];
1953
1954 /* Skip NULL pointers */
1955 if (!event)
1956 continue;
1957 printf("provider: %s, event: %s\n",
1958 event->provider_name, event->event_name);
314c22c3
MD
1959 if (notif == SIDE_TRACER_NOTIFICATION_INSERT_EVENTS) {
1960 if (event->flags & SIDE_EVENT_FLAG_VARIADIC) {
1961 ret = side_tracer_callback_variadic_register(event, tracer_call_variadic, NULL);
1962 if (ret)
1963 abort();
1964 } else {
1965 ret = side_tracer_callback_register(event, tracer_call, NULL);
1966 if (ret)
1967 abort();
1968 }
1969 } else {
1970 if (event->flags & SIDE_EVENT_FLAG_VARIADIC) {
1971 ret = side_tracer_callback_variadic_unregister(event, tracer_call_variadic, NULL);
1972 if (ret)
1973 abort();
1974 } else {
1975 ret = side_tracer_callback_unregister(event, tracer_call, NULL);
1976 if (ret)
1977 abort();
1978 }
1979 }
1e8aec23
MD
1980 }
1981 printf("----------------------------------------------------------\n");
1982}
1983
1984static __attribute__((constructor))
1985void tracer_init(void);
1986static
1987void tracer_init(void)
1988{
1989 tracer_handle = side_tracer_event_notification_register(tracer_event_notification, NULL);
1990 if (!tracer_handle)
1991 abort();
1992}
1993
1994static __attribute__((destructor))
1995void tracer_exit(void);
1996static
1997void tracer_exit(void)
1998{
1999 side_tracer_event_notification_unregister(tracer_handle);
2000}
This page took 0.117107 seconds and 4 git commands to generate.