Refactor enum type
[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>
f611d0c3
MD
11
12#include <side/trace.h>
13
14static
15void tracer_print_struct(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc);
16static
17void tracer_print_array(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc);
18static
19void tracer_print_vla(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc);
20static
352a4b77 21void tracer_print_vla_visitor(const struct side_type_description *type_desc, void *app_ctx);
ba845af5
MD
22static
23void tracer_print_array_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item);
1533629f
MD
24static
25void tracer_print_vla_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item);
a2e2357e
MD
26static
27void tracer_print_dynamic(const struct side_arg_dynamic_vec *dynamic_item);
d8be25de
MD
28static
29void tracer_print_type(const struct side_type_description *type_desc, const struct side_arg_vec *item);
f611d0c3 30
bc3c89b3
MD
31static
32void tracer_print_attr_type(const struct side_attr *attr)
33{
34 printf("{ key: \"%s\", value: ", attr->key);
35 switch (attr->value.type) {
36 case SIDE_ATTR_TYPE_BOOL:
37 printf("%s", attr->value.u.side_bool ? "true" : "false");
38 break;
39 case SIDE_ATTR_TYPE_U8:
40 printf("%" PRIu8, attr->value.u.side_u8);
41 break;
42 case SIDE_ATTR_TYPE_U16:
43 printf("%" PRIu16, attr->value.u.side_u16);
44 break;
45 case SIDE_ATTR_TYPE_U32:
46 printf("%" PRIu32, attr->value.u.side_u32);
47 break;
48 case SIDE_ATTR_TYPE_U64:
49 printf("%" PRIu64, attr->value.u.side_u64);
50 break;
51 case SIDE_ATTR_TYPE_S8:
52 printf("%" PRId8, attr->value.u.side_s8);
53 break;
54 case SIDE_ATTR_TYPE_S16:
55 printf("%" PRId16, attr->value.u.side_s16);
56 break;
57 case SIDE_ATTR_TYPE_S32:
58 printf("%" PRId32, attr->value.u.side_s32);
59 break;
60 case SIDE_ATTR_TYPE_S64:
61 printf("%" PRId64, attr->value.u.side_s64);
62 break;
63 case SIDE_ATTR_TYPE_FLOAT_BINARY16:
64#if __HAVE_FLOAT16
65 printf("%g", (double) attr->value.u.side_float_binary16);
66 break;
67#else
68 printf("ERROR: Unsupported binary16 float type\n");
69 abort();
70#endif
71 case SIDE_ATTR_TYPE_FLOAT_BINARY32:
72#if __HAVE_FLOAT32
73 printf("%g", (double) attr->value.u.side_float_binary32);
74 break;
75#else
76 printf("ERROR: Unsupported binary32 float type\n");
77 abort();
78#endif
79 case SIDE_ATTR_TYPE_FLOAT_BINARY64:
80#if __HAVE_FLOAT64
81 printf("%g", (double) attr->value.u.side_float_binary64);
82 break;
83#else
84 printf("ERROR: Unsupported binary64 float type\n");
85 abort();
86#endif
87 case SIDE_ATTR_TYPE_FLOAT_BINARY128:
88#if __HAVE_FLOAT128
89 printf("%Lg", (long double) attr->value.u.side_float_binary128);
90 break;
91#else
92 printf("ERROR: Unsupported binary128 float type\n");
93 abort();
94#endif
95 case SIDE_ATTR_TYPE_STRING:
96 printf("\"%s\"", attr->value.u.string);
97 break;
98 default:
99 printf("<UNKNOWN TYPE>");
100 abort();
101 }
102 printf(" }");
103}
104
7d21cf51 105static
a848763d 106void print_attributes(const char *prefix_str, const struct side_attr *attr, uint32_t nr_attr)
7d21cf51
MD
107{
108 int i;
109
110 if (!nr_attr)
111 return;
a848763d 112 printf("%s[ ", prefix_str);
7d21cf51
MD
113 for (i = 0; i < nr_attr; i++) {
114 printf("%s", i ? ", " : "");
bc3c89b3 115 tracer_print_attr_type(&attr[i]);
7d21cf51
MD
116 }
117 printf(" ]");
118}
119
79f677ba 120static
d8be25de 121void print_enum(const struct side_type_description *type_desc, const struct side_arg_vec *item)
79f677ba 122{
d8be25de 123 const struct side_enum_mappings *mappings = type_desc->u.side_enum.mappings;
79f677ba 124 int i, print_count = 0;
d8be25de 125 int64_t value;
79f677ba 126
d8be25de
MD
127 if (type_desc->u.side_enum.elem_type->type != item->type) {
128 printf("ERROR: Unexpected enum element type\n");
129 abort();
130 }
131 switch (item->type) {
132 case SIDE_TYPE_U8:
133 value = (int64_t) item->u.side_u8;
134 break;
135 case SIDE_TYPE_U16:
136 value = (int64_t) item->u.side_u16;
137 break;
138 case SIDE_TYPE_U32:
139 value = (int64_t) item->u.side_u32;
140 break;
141 case SIDE_TYPE_U64:
142 value = (int64_t) item->u.side_u64;
143 break;
144 case SIDE_TYPE_S8:
145 value = (int64_t) item->u.side_s8;
146 break;
147 case SIDE_TYPE_S16:
148 value = (int64_t) item->u.side_s16;
149 break;
150 case SIDE_TYPE_S32:
151 value = (int64_t) item->u.side_s32;
152 break;
153 case SIDE_TYPE_S64:
154 value = (int64_t) item->u.side_s64;
155 break;
156 default:
157 printf("ERROR: Unexpected enum element type\n");
158 abort();
159 }
160 print_attributes("attr: ", mappings->attr, mappings->nr_attr);
161 printf("%s", mappings->nr_attr ? ", " : "");
162 tracer_print_type(type_desc->u.side_enum.elem_type, item);
163 printf(", labels: [ ");
164 for (i = 0; i < mappings->nr_mappings; i++) {
165 const struct side_enum_mapping *mapping = &mappings->mappings[i];
79f677ba 166
ea32e5fc
MD
167 if (mapping->range_end < mapping->range_begin) {
168 printf("ERROR: Unexpected enum range: %" PRIu64 "-%" PRIu64 "\n",
169 mapping->range_begin, mapping->range_end);
170 abort();
171 }
79f677ba
MD
172 if (value >= mapping->range_begin && value <= mapping->range_end) {
173 printf("%s", print_count++ ? ", " : "");
174 printf("\"%s\"", mapping->label);
175 }
176 }
177 if (!print_count)
178 printf("<NO LABEL>");
179 printf(" ]");
180}
181
ea32e5fc 182static
af6aa6e1 183uint32_t enum_type_to_stride(const struct side_type_description *type_desc)
ea32e5fc 184{
af6aa6e1
MD
185 uint32_t stride_bit;
186
187 switch (type_desc->type) {
188 case SIDE_TYPE_ENUM_BITMAP8:
189 case SIDE_TYPE_U8:
190 case SIDE_TYPE_S8:
191 stride_bit = 8;
192 break;
193 case SIDE_TYPE_ENUM_BITMAP16:
194 case SIDE_TYPE_U16:
195 case SIDE_TYPE_S16:
196 stride_bit = 16;
197 break;
198 case SIDE_TYPE_ENUM_BITMAP32:
199 case SIDE_TYPE_U32:
200 case SIDE_TYPE_S32:
201 stride_bit = 32;
202 break;
203 case SIDE_TYPE_ENUM_BITMAP64:
204 case SIDE_TYPE_U64:
205 case SIDE_TYPE_S64:
206 stride_bit = 64;
207 break;
208 case SIDE_TYPE_ENUM_BITMAP_ARRAY:
209 stride_bit = enum_type_to_stride(type_desc->u.side_enum_bitmap_array.elem_type);
210 break;
211 case SIDE_TYPE_ENUM_BITMAP_VLA:
212 stride_bit = enum_type_to_stride(type_desc->u.side_enum_bitmap_vla.elem_type);
213 break;
214 default:
215 abort();
216 }
217 return stride_bit;
218}
219
220static
221void print_enum_bitmap(const struct side_type_description *type_desc,
222 const struct side_arg_vec *item)
223{
224 const struct side_enum_bitmap_mappings *side_enum_mappings;
ea32e5fc 225 int i, print_count = 0;
af6aa6e1
MD
226 uint32_t stride_bit, nr_items;
227 const struct side_arg_vec *array_item;
228
229 stride_bit = enum_type_to_stride(type_desc);
230
231 switch (type_desc->type) {
232 case SIDE_TYPE_ENUM_BITMAP8: /* Fall-through */
233 case SIDE_TYPE_ENUM_BITMAP16: /* Fall-through */
234 case SIDE_TYPE_ENUM_BITMAP32: /* Fall-through */
235 case SIDE_TYPE_ENUM_BITMAP64:
236 array_item = item;
237 nr_items = 1;
238 side_enum_mappings = type_desc->u.side_enum_bitmap_mappings;
239 break;
240 case SIDE_TYPE_ENUM_BITMAP_ARRAY:
241 nr_items = type_desc->u.side_enum_bitmap_array.length;
242 array_item = item->u.side_array->sav;
243 side_enum_mappings = type_desc->u.side_enum_bitmap_array.mappings;
244 break;
245 case SIDE_TYPE_ENUM_BITMAP_VLA:
246 nr_items = item->u.side_vla->len;
247 array_item = item->u.side_vla->sav;
248 side_enum_mappings = type_desc->u.side_enum_bitmap_vla.mappings;
249 break;
250 default:
251 abort();
252 }
ea32e5fc 253
d4328528
MD
254 print_attributes("attr: ", side_enum_mappings->attr, side_enum_mappings->nr_attr);
255 printf("%s", side_enum_mappings->nr_attr ? ", " : "");
af6aa6e1 256 printf("labels: [ ");
ea32e5fc 257 for (i = 0; i < side_enum_mappings->nr_mappings; i++) {
66cff328 258 const struct side_enum_bitmap_mapping *mapping = &side_enum_mappings->mappings[i];
ea32e5fc
MD
259 bool match = false;
260 int64_t bit;
261
af6aa6e1 262 if (mapping->range_begin < 0 || mapping->range_end < mapping->range_begin) {
ea32e5fc
MD
263 printf("ERROR: Unexpected enum bitmap range: %" PRIu64 "-%" PRIu64 "\n",
264 mapping->range_begin, mapping->range_end);
265 abort();
266 }
267 for (bit = mapping->range_begin; bit <= mapping->range_end; bit++) {
af6aa6e1
MD
268 if (bit > (nr_items * stride_bit) - 1)
269 break;
270 switch (stride_bit) {
271 case 8:
272 {
273 uint8_t v = array_item[bit / 8].u.side_u8;
274 if (v & (1ULL << (bit % 8))) {
275 match = true;
276 goto match;
277 }
278 break;
279 }
280 case 16:
281 {
282 uint16_t v = array_item[bit / 16].u.side_u16;
283 if (v & (1ULL << (bit % 16))) {
284 match = true;
285 goto match;
286 }
287 break;
288 }
289 case 32:
290 {
291 uint32_t v = array_item[bit / 32].u.side_u32;
292 if (v & (1ULL << (bit % 32))) {
293 match = true;
294 goto match;
295 }
ea32e5fc
MD
296 break;
297 }
af6aa6e1
MD
298 case 64:
299 {
300 uint64_t v = array_item[bit / 64].u.side_u64;
301 if (v & (1ULL << (bit % 64))) {
302 match = true;
303 goto match;
304 }
305 break;
306 }
307 default:
308 abort();
309 }
ea32e5fc 310 }
af6aa6e1 311match:
ea32e5fc
MD
312 if (match) {
313 printf("%s", print_count++ ? ", " : "");
314 printf("\"%s\"", mapping->label);
315 }
316 }
317 if (!print_count)
318 printf("<NO LABEL>");
319 printf(" ]");
320}
321
0e9be766
MD
322static
323void tracer_print_basic_type_header(const struct side_type_description *type_desc)
324{
325 print_attributes("attr: ", type_desc->u.side_basic.attr, type_desc->u.side_basic.nr_attr);
326 printf("%s", type_desc->u.side_basic.nr_attr ? ", " : "");
327 printf("value: ");
328}
329
f611d0c3
MD
330static
331void tracer_print_type(const struct side_type_description *type_desc, const struct side_arg_vec *item)
332{
d8be25de
MD
333 enum side_type type;
334
ba845af5
MD
335 switch (item->type) {
336 case SIDE_TYPE_ARRAY_U8:
337 case SIDE_TYPE_ARRAY_U16:
338 case SIDE_TYPE_ARRAY_U32:
339 case SIDE_TYPE_ARRAY_U64:
340 case SIDE_TYPE_ARRAY_S8:
341 case SIDE_TYPE_ARRAY_S16:
342 case SIDE_TYPE_ARRAY_S32:
343 case SIDE_TYPE_ARRAY_S64:
7aec0d09 344 case SIDE_TYPE_ARRAY_BLOB:
ba845af5
MD
345 if (type_desc->type != SIDE_TYPE_ARRAY) {
346 printf("ERROR: type mismatch between description and arguments\n");
347 abort();
348 }
349 break;
1533629f
MD
350 case SIDE_TYPE_VLA_U8:
351 case SIDE_TYPE_VLA_U16:
352 case SIDE_TYPE_VLA_U32:
353 case SIDE_TYPE_VLA_U64:
354 case SIDE_TYPE_VLA_S8:
355 case SIDE_TYPE_VLA_S16:
356 case SIDE_TYPE_VLA_S32:
357 case SIDE_TYPE_VLA_S64:
7aec0d09 358 case SIDE_TYPE_VLA_BLOB:
1533629f
MD
359 if (type_desc->type != SIDE_TYPE_VLA) {
360 printf("ERROR: type mismatch between description and arguments\n");
361 abort();
362 }
363 break;
364
d8be25de
MD
365 case SIDE_TYPE_U8:
366 case SIDE_TYPE_U16:
367 case SIDE_TYPE_U32:
368 case SIDE_TYPE_U64:
369 case SIDE_TYPE_S8:
370 case SIDE_TYPE_S16:
371 case SIDE_TYPE_S32:
372 case SIDE_TYPE_S64:
373 if (type_desc->type != item->type && type_desc->type != SIDE_TYPE_ENUM) {
374 printf("ERROR: type mismatch between description and arguments\n");
375 abort();
376 }
377 break;
378
ba845af5 379 default:
a2e2357e 380 if (type_desc->type != item->type) {
ba845af5
MD
381 printf("ERROR: type mismatch between description and arguments\n");
382 abort();
383 }
384 break;
f611d0c3 385 }
d8be25de
MD
386
387 if (type_desc->type == SIDE_TYPE_ENUM)
388 type = SIDE_TYPE_ENUM;
389 else
390 type = item->type;
391
a848763d 392 printf("{ ");
d8be25de 393 switch (type) {
4f40d951 394 case SIDE_TYPE_BOOL:
0e9be766 395 tracer_print_basic_type_header(type_desc);
4f40d951
MD
396 printf("%s", item->u.side_bool ? "true" : "false");
397 break;
f611d0c3 398 case SIDE_TYPE_U8:
0e9be766 399 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
400 printf("%" PRIu8, item->u.side_u8);
401 break;
402 case SIDE_TYPE_U16:
0e9be766 403 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
404 printf("%" PRIu16, item->u.side_u16);
405 break;
406 case SIDE_TYPE_U32:
0e9be766 407 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
408 printf("%" PRIu32, item->u.side_u32);
409 break;
410 case SIDE_TYPE_U64:
0e9be766 411 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
412 printf("%" PRIu64, item->u.side_u64);
413 break;
414 case SIDE_TYPE_S8:
0e9be766 415 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
416 printf("%" PRId8, item->u.side_s8);
417 break;
418 case SIDE_TYPE_S16:
0e9be766 419 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
420 printf("%" PRId16, item->u.side_s16);
421 break;
422 case SIDE_TYPE_S32:
0e9be766 423 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
424 printf("%" PRId32, item->u.side_s32);
425 break;
426 case SIDE_TYPE_S64:
0e9be766 427 tracer_print_basic_type_header(type_desc);
f611d0c3
MD
428 printf("%" PRId64, item->u.side_s64);
429 break;
7aec0d09 430 case SIDE_TYPE_BLOB:
0e9be766 431 tracer_print_basic_type_header(type_desc);
7aec0d09
MD
432 printf("0x%" PRIx8, item->u.side_blob);
433 break;
79f677ba 434
d8be25de
MD
435 case SIDE_TYPE_ENUM:
436 print_enum(type_desc, item);
79f677ba
MD
437 break;
438
af6aa6e1
MD
439 case SIDE_TYPE_ENUM_BITMAP8: /* Fall-through */
440 case SIDE_TYPE_ENUM_BITMAP16: /* Fall-through */
441 case SIDE_TYPE_ENUM_BITMAP32: /* Fall-through */
ea32e5fc 442 case SIDE_TYPE_ENUM_BITMAP64:
af6aa6e1
MD
443 case SIDE_TYPE_ENUM_BITMAP_ARRAY:
444 case SIDE_TYPE_ENUM_BITMAP_VLA:
445 print_enum_bitmap(type_desc, item);
ea32e5fc
MD
446 break;
447
fb25b355 448 case SIDE_TYPE_FLOAT_BINARY16:
0e9be766 449 tracer_print_basic_type_header(type_desc);
fb25b355
MD
450#if __HAVE_FLOAT16
451 printf("%g", (double) item->u.side_float_binary16);
452 break;
453#else
454 printf("ERROR: Unsupported binary16 float type\n");
455 abort();
456#endif
457 case SIDE_TYPE_FLOAT_BINARY32:
0e9be766 458 tracer_print_basic_type_header(type_desc);
fb25b355
MD
459#if __HAVE_FLOAT32
460 printf("%g", (double) item->u.side_float_binary32);
461 break;
462#else
463 printf("ERROR: Unsupported binary32 float type\n");
464 abort();
465#endif
466 case SIDE_TYPE_FLOAT_BINARY64:
0e9be766 467 tracer_print_basic_type_header(type_desc);
fb25b355
MD
468#if __HAVE_FLOAT64
469 printf("%g", (double) item->u.side_float_binary64);
470 break;
471#else
472 printf("ERROR: Unsupported binary64 float type\n");
473 abort();
474#endif
475 case SIDE_TYPE_FLOAT_BINARY128:
0e9be766 476 tracer_print_basic_type_header(type_desc);
fb25b355
MD
477#if __HAVE_FLOAT128
478 printf("%Lg", (long double) item->u.side_float_binary128);
479 break;
480#else
481 printf("ERROR: Unsupported binary128 float type\n");
482 abort();
483#endif
f611d0c3 484 case SIDE_TYPE_STRING:
0e9be766 485 tracer_print_basic_type_header(type_desc);
a2e2357e 486 printf("\"%s\"", item->u.string);
f611d0c3
MD
487 break;
488 case SIDE_TYPE_STRUCT:
489 tracer_print_struct(type_desc, item->u.side_struct);
490 break;
491 case SIDE_TYPE_ARRAY:
492 tracer_print_array(type_desc, item->u.side_array);
493 break;
494 case SIDE_TYPE_VLA:
495 tracer_print_vla(type_desc, item->u.side_vla);
496 break;
497 case SIDE_TYPE_VLA_VISITOR:
352a4b77 498 tracer_print_vla_visitor(type_desc, item->u.side_vla_app_visitor_ctx);
f611d0c3 499 break;
ba845af5
MD
500 case SIDE_TYPE_ARRAY_U8:
501 case SIDE_TYPE_ARRAY_U16:
502 case SIDE_TYPE_ARRAY_U32:
503 case SIDE_TYPE_ARRAY_U64:
504 case SIDE_TYPE_ARRAY_S8:
505 case SIDE_TYPE_ARRAY_S16:
506 case SIDE_TYPE_ARRAY_S32:
507 case SIDE_TYPE_ARRAY_S64:
7aec0d09 508 case SIDE_TYPE_ARRAY_BLOB:
ba845af5
MD
509 tracer_print_array_fixint(type_desc, item);
510 break;
1533629f
MD
511 case SIDE_TYPE_VLA_U8:
512 case SIDE_TYPE_VLA_U16:
513 case SIDE_TYPE_VLA_U32:
514 case SIDE_TYPE_VLA_U64:
515 case SIDE_TYPE_VLA_S8:
516 case SIDE_TYPE_VLA_S16:
517 case SIDE_TYPE_VLA_S32:
518 case SIDE_TYPE_VLA_S64:
7aec0d09 519 case SIDE_TYPE_VLA_BLOB:
1533629f
MD
520 tracer_print_vla_fixint(type_desc, item);
521 break;
a2e2357e 522 case SIDE_TYPE_DYNAMIC:
0e9be766 523 tracer_print_basic_type_header(type_desc);
a2e2357e
MD
524 tracer_print_dynamic(&item->u.dynamic);
525 break;
f611d0c3
MD
526 default:
527 printf("<UNKNOWN TYPE>");
528 abort();
529 }
a848763d 530 printf(" }");
f611d0c3
MD
531}
532
533static
534void tracer_print_field(const struct side_event_field *item_desc, const struct side_arg_vec *item)
535{
19fa6aa2 536 printf("%s: ", item_desc->field_name);
f611d0c3 537 tracer_print_type(&item_desc->side_type, item);
f611d0c3
MD
538}
539
540static
541void tracer_print_struct(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc)
542{
543 const struct side_arg_vec *sav = sav_desc->sav;
544 uint32_t side_sav_len = sav_desc->len;
545 int i;
546
c7a14585 547 if (type_desc->u.side_struct->nr_fields != side_sav_len) {
f611d0c3
MD
548 printf("ERROR: number of fields mismatch between description and arguments of structure\n");
549 abort();
550 }
73b2b0c2
MD
551 print_attributes("attr: ", type_desc->u.side_struct->attr, type_desc->u.side_struct->nr_attr);
552 printf("%s", type_desc->u.side_struct->nr_attr ? ", " : "");
553 printf("fields: { ");
f611d0c3
MD
554 for (i = 0; i < side_sav_len; i++) {
555 printf("%s", i ? ", " : "");
c7a14585 556 tracer_print_field(&type_desc->u.side_struct->fields[i], &sav[i]);
f611d0c3 557 }
d4328528 558 printf(" }");
f611d0c3
MD
559}
560
561static
562void tracer_print_array(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc)
563{
564 const struct side_arg_vec *sav = sav_desc->sav;
565 uint32_t side_sav_len = sav_desc->len;
566 int i;
567
568 if (type_desc->u.side_array.length != side_sav_len) {
569 printf("ERROR: length mismatch between description and arguments of array\n");
570 abort();
571 }
d4328528
MD
572 print_attributes("attr: ", type_desc->u.side_array.attr, type_desc->u.side_array.nr_attr);
573 printf("%s", type_desc->u.side_array.nr_attr ? ", " : "");
20574104 574 printf("elements: ");
f611d0c3
MD
575 printf("[ ");
576 for (i = 0; i < side_sav_len; i++) {
577 printf("%s", i ? ", " : "");
578 tracer_print_type(type_desc->u.side_array.elem_type, &sav[i]);
579 }
580 printf(" ]");
581}
582
583static
584void tracer_print_vla(const struct side_type_description *type_desc, const struct side_arg_vec_description *sav_desc)
585{
586 const struct side_arg_vec *sav = sav_desc->sav;
587 uint32_t side_sav_len = sav_desc->len;
588 int i;
589
d4328528
MD
590 print_attributes("attr: ", type_desc->u.side_vla.attr, type_desc->u.side_vla.nr_attr);
591 printf("%s", type_desc->u.side_vla.nr_attr ? ", " : "");
20574104 592 printf("elements: ");
f611d0c3
MD
593 printf("[ ");
594 for (i = 0; i < side_sav_len; i++) {
595 printf("%s", i ? ", " : "");
596 tracer_print_type(type_desc->u.side_vla.elem_type, &sav[i]);
597 }
598 printf(" ]");
599}
600
352a4b77
MD
601struct tracer_visitor_priv {
602 const struct side_type_description *elem_type;
603 int i;
604};
605
606static
607enum side_visitor_status tracer_write_elem_cb(const struct side_tracer_visitor_ctx *tracer_ctx,
608 const struct side_arg_vec *elem)
609{
610 struct tracer_visitor_priv *tracer_priv = tracer_ctx->priv;
611
612 printf("%s", tracer_priv->i++ ? ", " : "");
613 tracer_print_type(tracer_priv->elem_type, elem);
614 return SIDE_VISITOR_STATUS_OK;
615}
616
f611d0c3 617static
352a4b77 618void tracer_print_vla_visitor(const struct side_type_description *type_desc, void *app_ctx)
f611d0c3
MD
619{
620 enum side_visitor_status status;
352a4b77
MD
621 struct tracer_visitor_priv tracer_priv = {
622 .elem_type = type_desc->u.side_vla_visitor.elem_type,
623 .i = 0,
624 };
625 const struct side_tracer_visitor_ctx tracer_ctx = {
626 .write_elem = tracer_write_elem_cb,
627 .priv = &tracer_priv,
628 };
f611d0c3 629
d4328528
MD
630 print_attributes("attr: ", type_desc->u.side_vla_visitor.attr, type_desc->u.side_vla_visitor.nr_attr);
631 printf("%s", type_desc->u.side_vla_visitor.nr_attr ? ", " : "");
20574104 632 printf("elements: ");
352a4b77
MD
633 printf("[ ");
634 status = type_desc->u.side_vla_visitor.visitor(&tracer_ctx, app_ctx);
635 switch (status) {
636 case SIDE_VISITOR_STATUS_OK:
637 break;
638 case SIDE_VISITOR_STATUS_ERROR:
f611d0c3
MD
639 printf("ERROR: Visitor error\n");
640 abort();
f611d0c3
MD
641 }
642 printf(" ]");
f611d0c3
MD
643}
644
ba845af5
MD
645void tracer_print_array_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item)
646{
647 const struct side_type_description *elem_type = type_desc->u.side_array.elem_type;
648 uint32_t side_sav_len = type_desc->u.side_array.length;
649 void *p = item->u.side_array_fixint;
650 enum side_type side_type;
651 int i;
652
d4328528
MD
653 print_attributes("attr: ", type_desc->u.side_array.attr, type_desc->u.side_array.nr_attr);
654 printf("%s", type_desc->u.side_array.nr_attr ? ", " : "");
20574104 655 printf("elements: ");
1e8256c9
MD
656 switch (item->type) {
657 case SIDE_TYPE_ARRAY_U8:
658 if (elem_type->type != SIDE_TYPE_U8)
659 goto type_error;
660 break;
661 case SIDE_TYPE_ARRAY_U16:
662 if (elem_type->type != SIDE_TYPE_U16)
663 goto type_error;
664 break;
665 case SIDE_TYPE_ARRAY_U32:
666 if (elem_type->type != SIDE_TYPE_U32)
667 goto type_error;
668 break;
669 case SIDE_TYPE_ARRAY_U64:
670 if (elem_type->type != SIDE_TYPE_U64)
671 goto type_error;
672 break;
673 case SIDE_TYPE_ARRAY_S8:
674 if (elem_type->type != SIDE_TYPE_S8)
675 goto type_error;
676 break;
677 case SIDE_TYPE_ARRAY_S16:
678 if (elem_type->type != SIDE_TYPE_S16)
679 goto type_error;
680 break;
681 case SIDE_TYPE_ARRAY_S32:
682 if (elem_type->type != SIDE_TYPE_S32)
683 goto type_error;
684 break;
685 case SIDE_TYPE_ARRAY_S64:
686 if (elem_type->type != SIDE_TYPE_S64)
687 goto type_error;
688 break;
7aec0d09
MD
689 case SIDE_TYPE_ARRAY_BLOB:
690 if (elem_type->type != SIDE_TYPE_BLOB)
691 goto type_error;
692 break;
1e8256c9
MD
693 default:
694 goto type_error;
ba845af5 695 }
1e8256c9 696 side_type = elem_type->type;
ba845af5 697
1533629f
MD
698 printf("[ ");
699 for (i = 0; i < side_sav_len; i++) {
700 struct side_arg_vec sav_elem = {
701 .type = side_type,
702 };
703
704 switch (side_type) {
705 case SIDE_TYPE_U8:
706 sav_elem.u.side_u8 = ((const uint8_t *) p)[i];
707 break;
708 case SIDE_TYPE_S8:
709 sav_elem.u.side_s8 = ((const int8_t *) p)[i];
710 break;
711 case SIDE_TYPE_U16:
712 sav_elem.u.side_u16 = ((const uint16_t *) p)[i];
713 break;
714 case SIDE_TYPE_S16:
715 sav_elem.u.side_s16 = ((const int16_t *) p)[i];
716 break;
717 case SIDE_TYPE_U32:
718 sav_elem.u.side_u32 = ((const uint32_t *) p)[i];
719 break;
720 case SIDE_TYPE_S32:
721 sav_elem.u.side_s32 = ((const int32_t *) p)[i];
722 break;
723 case SIDE_TYPE_U64:
724 sav_elem.u.side_u64 = ((const uint64_t *) p)[i];
725 break;
726 case SIDE_TYPE_S64:
727 sav_elem.u.side_s64 = ((const int64_t *) p)[i];
728 break;
7aec0d09
MD
729 case SIDE_TYPE_BLOB:
730 sav_elem.u.side_blob = ((const uint8_t *) p)[i];
731 break;
1533629f
MD
732
733 default:
734 printf("ERROR: Unexpected type\n");
735 abort();
736 }
737
738 printf("%s", i ? ", " : "");
739 tracer_print_type(elem_type, &sav_elem);
740 }
741 printf(" ]");
742 return;
743
744type_error:
745 printf("ERROR: type mismatch\n");
746 abort();
747}
748
749void tracer_print_vla_fixint(const struct side_type_description *type_desc, const struct side_arg_vec *item)
750{
751 const struct side_type_description *elem_type = type_desc->u.side_vla.elem_type;
752 uint32_t side_sav_len = item->u.side_vla_fixint.length;
753 void *p = item->u.side_vla_fixint.p;
754 enum side_type side_type;
755 int i;
756
d4328528
MD
757 print_attributes("attr: ", type_desc->u.side_vla.attr, type_desc->u.side_vla.nr_attr);
758 printf("%s", type_desc->u.side_vla.nr_attr ? ", " : "");
20574104 759 printf("elements: ");
a2e2357e
MD
760 switch (item->type) {
761 case SIDE_TYPE_VLA_U8:
762 if (elem_type->type != SIDE_TYPE_U8)
1533629f 763 goto type_error;
a2e2357e
MD
764 break;
765 case SIDE_TYPE_VLA_U16:
766 if (elem_type->type != SIDE_TYPE_U16)
1533629f 767 goto type_error;
a2e2357e
MD
768 break;
769 case SIDE_TYPE_VLA_U32:
770 if (elem_type->type != SIDE_TYPE_U32)
771 goto type_error;
772 break;
773 case SIDE_TYPE_VLA_U64:
774 if (elem_type->type != SIDE_TYPE_U64)
775 goto type_error;
776 break;
777 case SIDE_TYPE_VLA_S8:
778 if (elem_type->type != SIDE_TYPE_S8)
779 goto type_error;
780 break;
781 case SIDE_TYPE_VLA_S16:
782 if (elem_type->type != SIDE_TYPE_S16)
783 goto type_error;
784 break;
785 case SIDE_TYPE_VLA_S32:
786 if (elem_type->type != SIDE_TYPE_S32)
787 goto type_error;
788 break;
789 case SIDE_TYPE_VLA_S64:
790 if (elem_type->type != SIDE_TYPE_S64)
791 goto type_error;
792 break;
7aec0d09
MD
793 case SIDE_TYPE_VLA_BLOB:
794 if (elem_type->type != SIDE_TYPE_BLOB)
795 goto type_error;
796 break;
a2e2357e
MD
797 default:
798 goto type_error;
1533629f 799 }
a2e2357e 800 side_type = elem_type->type;
1533629f 801
ba845af5
MD
802 printf("[ ");
803 for (i = 0; i < side_sav_len; i++) {
804 struct side_arg_vec sav_elem = {
805 .type = side_type,
806 };
807
808 switch (side_type) {
809 case SIDE_TYPE_U8:
810 sav_elem.u.side_u8 = ((const uint8_t *) p)[i];
811 break;
812 case SIDE_TYPE_S8:
813 sav_elem.u.side_s8 = ((const int8_t *) p)[i];
814 break;
815 case SIDE_TYPE_U16:
816 sav_elem.u.side_u16 = ((const uint16_t *) p)[i];
817 break;
818 case SIDE_TYPE_S16:
819 sav_elem.u.side_s16 = ((const int16_t *) p)[i];
820 break;
821 case SIDE_TYPE_U32:
822 sav_elem.u.side_u32 = ((const uint32_t *) p)[i];
823 break;
824 case SIDE_TYPE_S32:
825 sav_elem.u.side_s32 = ((const int32_t *) p)[i];
826 break;
827 case SIDE_TYPE_U64:
828 sav_elem.u.side_u64 = ((const uint64_t *) p)[i];
829 break;
830 case SIDE_TYPE_S64:
831 sav_elem.u.side_s64 = ((const int64_t *) p)[i];
832 break;
7aec0d09
MD
833 case SIDE_TYPE_BLOB:
834 sav_elem.u.side_blob = ((const uint8_t *) p)[i];
835 break;
ba845af5
MD
836
837 default:
838 printf("ERROR: Unexpected type\n");
839 abort();
840 }
841
842 printf("%s", i ? ", " : "");
843 tracer_print_type(elem_type, &sav_elem);
844 }
845 printf(" ]");
846 return;
847
848type_error:
849 printf("ERROR: type mismatch\n");
850 abort();
851}
852
a2e2357e 853static
c208889e 854void tracer_print_dynamic_struct(const struct side_arg_dynamic_event_struct *dynamic_struct)
a2e2357e 855{
c208889e
MD
856 const struct side_arg_dynamic_event_field *fields = dynamic_struct->fields;
857 uint32_t len = dynamic_struct->len;
465e5e7e
MD
858 int i;
859
8d20e708
MD
860 print_attributes("attr:: ", dynamic_struct->attr, dynamic_struct->nr_attr);
861 printf("%s", dynamic_struct->nr_attr ? ", " : "");
f0061366 862 printf("fields:: ");
465e5e7e
MD
863 printf("[ ");
864 for (i = 0; i < len; i++) {
865 printf("%s", i ? ", " : "");
866 printf("%s:: ", fields[i].field_name);
867 tracer_print_dynamic(&fields[i].elem);
868 }
869 printf(" ]");
a2e2357e
MD
870}
871
2b359235
MD
872struct tracer_dynamic_struct_visitor_priv {
873 int i;
874};
875
876static
877enum side_visitor_status tracer_dynamic_struct_write_elem_cb(
878 const struct side_tracer_dynamic_struct_visitor_ctx *tracer_ctx,
879 const struct side_arg_dynamic_event_field *dynamic_field)
880{
881 struct tracer_dynamic_struct_visitor_priv *tracer_priv = tracer_ctx->priv;
882
883 printf("%s", tracer_priv->i++ ? ", " : "");
884 printf("%s:: ", dynamic_field->field_name);
885 tracer_print_dynamic(&dynamic_field->elem);
886 return SIDE_VISITOR_STATUS_OK;
887}
888
a2e2357e 889static
c208889e 890void tracer_print_dynamic_struct_visitor(const struct side_arg_dynamic_vec *item)
a2e2357e 891{
2b359235
MD
892 enum side_visitor_status status;
893 struct tracer_dynamic_struct_visitor_priv tracer_priv = {
894 .i = 0,
895 };
896 const struct side_tracer_dynamic_struct_visitor_ctx tracer_ctx = {
897 .write_field = tracer_dynamic_struct_write_elem_cb,
898 .priv = &tracer_priv,
899 };
900 void *app_ctx = item->u.side_dynamic_struct_visitor.app_ctx;
901
8d20e708
MD
902 print_attributes("attr:: ", item->u.side_dynamic_struct_visitor.attr, item->u.side_dynamic_struct_visitor.nr_attr);
903 printf("%s", item->u.side_dynamic_struct_visitor.nr_attr ? ", " : "");
f0061366 904 printf("fields:: ");
2b359235
MD
905 printf("[ ");
906 status = item->u.side_dynamic_struct_visitor.visitor(&tracer_ctx, app_ctx);
907 switch (status) {
908 case SIDE_VISITOR_STATUS_OK:
909 break;
910 case SIDE_VISITOR_STATUS_ERROR:
911 printf("ERROR: Visitor error\n");
912 abort();
913 }
914 printf(" ]");
a2e2357e
MD
915}
916
917static
918void tracer_print_dynamic_vla(const struct side_arg_dynamic_vec_vla *vla)
919{
920 const struct side_arg_dynamic_vec *sav = vla->sav;
921 uint32_t side_sav_len = vla->len;
922 int i;
923
8d20e708
MD
924 print_attributes("attr:: ", vla->attr, vla->nr_attr);
925 printf("%s", vla->nr_attr ? ", " : "");
f0061366 926 printf("elements:: ");
a2e2357e
MD
927 printf("[ ");
928 for (i = 0; i < side_sav_len; i++) {
929 printf("%s", i ? ", " : "");
930 tracer_print_dynamic(&sav[i]);
931 }
932 printf(" ]");
933}
934
8ceca0cd
MD
935struct tracer_dynamic_vla_visitor_priv {
936 int i;
937};
938
939static
940enum side_visitor_status tracer_dynamic_vla_write_elem_cb(
941 const struct side_tracer_dynamic_vla_visitor_ctx *tracer_ctx,
942 const struct side_arg_dynamic_vec *elem)
943{
944 struct tracer_dynamic_vla_visitor_priv *tracer_priv = tracer_ctx->priv;
945
946 printf("%s", tracer_priv->i++ ? ", " : "");
947 tracer_print_dynamic(elem);
948 return SIDE_VISITOR_STATUS_OK;
949}
950
a2e2357e
MD
951static
952void tracer_print_dynamic_vla_visitor(const struct side_arg_dynamic_vec *item)
953{
8ceca0cd
MD
954 enum side_visitor_status status;
955 struct tracer_dynamic_vla_visitor_priv tracer_priv = {
956 .i = 0,
957 };
958 const struct side_tracer_dynamic_vla_visitor_ctx tracer_ctx = {
959 .write_elem = tracer_dynamic_vla_write_elem_cb,
960 .priv = &tracer_priv,
961 };
962 void *app_ctx = item->u.side_dynamic_vla_visitor.app_ctx;
963
8d20e708
MD
964 print_attributes("attr:: ", item->u.side_dynamic_vla_visitor.attr, item->u.side_dynamic_vla_visitor.nr_attr);
965 printf("%s", item->u.side_dynamic_vla_visitor.nr_attr ? ", " : "");
f0061366 966 printf("elements:: ");
8ceca0cd
MD
967 printf("[ ");
968 status = item->u.side_dynamic_vla_visitor.visitor(&tracer_ctx, app_ctx);
969 switch (status) {
970 case SIDE_VISITOR_STATUS_OK:
971 break;
972 case SIDE_VISITOR_STATUS_ERROR:
973 printf("ERROR: Visitor error\n");
974 abort();
975 }
976 printf(" ]");
a2e2357e
MD
977}
978
0e9be766
MD
979static
980void tracer_print_dynamic_basic_type_header(const struct side_arg_dynamic_vec *item)
981{
982 print_attributes("attr:: ", item->u.side_basic.attr, item->u.side_basic.nr_attr);
983 printf("%s", item->u.side_basic.nr_attr ? ", " : "");
984 printf("value:: ");
985}
986
a2e2357e
MD
987static
988void tracer_print_dynamic(const struct side_arg_dynamic_vec *item)
989{
808bd9bf 990 printf("{ ");
1e8256c9 991 switch (item->dynamic_type) {
a2e2357e 992 case SIDE_DYNAMIC_TYPE_NULL:
0e9be766 993 tracer_print_dynamic_basic_type_header(item);
a2e2357e
MD
994 printf("<NULL TYPE>");
995 break;
4f40d951 996 case SIDE_DYNAMIC_TYPE_BOOL:
0e9be766 997 tracer_print_dynamic_basic_type_header(item);
8d20e708 998 printf("%s", item->u.side_basic.u.side_bool ? "true" : "false");
4f40d951 999 break;
a2e2357e 1000 case SIDE_DYNAMIC_TYPE_U8:
0e9be766 1001 tracer_print_dynamic_basic_type_header(item);
8d20e708 1002 printf("%" PRIu8, item->u.side_basic.u.side_u8);
a2e2357e
MD
1003 break;
1004 case SIDE_DYNAMIC_TYPE_U16:
0e9be766 1005 tracer_print_dynamic_basic_type_header(item);
8d20e708 1006 printf("%" PRIu16, item->u.side_basic.u.side_u16);
a2e2357e
MD
1007 break;
1008 case SIDE_DYNAMIC_TYPE_U32:
0e9be766 1009 tracer_print_dynamic_basic_type_header(item);
8d20e708 1010 printf("%" PRIu32, item->u.side_basic.u.side_u32);
a2e2357e
MD
1011 break;
1012 case SIDE_DYNAMIC_TYPE_U64:
0e9be766 1013 tracer_print_dynamic_basic_type_header(item);
8d20e708 1014 printf("%" PRIu64, item->u.side_basic.u.side_u64);
a2e2357e
MD
1015 break;
1016 case SIDE_DYNAMIC_TYPE_S8:
0e9be766 1017 tracer_print_dynamic_basic_type_header(item);
8d20e708 1018 printf("%" PRId8, item->u.side_basic.u.side_s8);
a2e2357e
MD
1019 break;
1020 case SIDE_DYNAMIC_TYPE_S16:
0e9be766 1021 tracer_print_dynamic_basic_type_header(item);
8d20e708 1022 printf("%" PRId16, item->u.side_basic.u.side_s16);
a2e2357e
MD
1023 break;
1024 case SIDE_DYNAMIC_TYPE_S32:
0e9be766 1025 tracer_print_dynamic_basic_type_header(item);
8d20e708 1026 printf("%" PRId32, item->u.side_basic.u.side_s32);
a2e2357e
MD
1027 break;
1028 case SIDE_DYNAMIC_TYPE_S64:
0e9be766 1029 tracer_print_dynamic_basic_type_header(item);
8d20e708 1030 printf("%" PRId64, item->u.side_basic.u.side_s64);
a2e2357e 1031 break;
199e7aa9 1032 case SIDE_DYNAMIC_TYPE_BLOB:
0e9be766 1033 tracer_print_dynamic_basic_type_header(item);
8d20e708 1034 printf("0x%" PRIx8, item->u.side_basic.u.side_blob);
199e7aa9
MD
1035 break;
1036
fb25b355 1037 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY16:
0e9be766 1038 tracer_print_dynamic_basic_type_header(item);
fb25b355 1039#if __HAVE_FLOAT16
8d20e708 1040 printf("%g", (double) item->u.side_basic.u.side_float_binary16);
fb25b355
MD
1041 break;
1042#else
1043 printf("ERROR: Unsupported binary16 float type\n");
1044 abort();
1045#endif
1046 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY32:
0e9be766 1047 tracer_print_dynamic_basic_type_header(item);
fb25b355 1048#if __HAVE_FLOAT32
8d20e708 1049 printf("%g", (double) item->u.side_basic.u.side_float_binary32);
fb25b355
MD
1050 break;
1051#else
1052 printf("ERROR: Unsupported binary32 float type\n");
1053 abort();
1054#endif
1055 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY64:
0e9be766 1056 tracer_print_dynamic_basic_type_header(item);
fb25b355 1057#if __HAVE_FLOAT64
8d20e708 1058 printf("%g", (double) item->u.side_basic.u.side_float_binary64);
fb25b355
MD
1059 break;
1060#else
1061 printf("ERROR: Unsupported binary64 float type\n");
1062 abort();
1063#endif
1064 case SIDE_DYNAMIC_TYPE_FLOAT_BINARY128:
0e9be766 1065 tracer_print_dynamic_basic_type_header(item);
fb25b355 1066#if __HAVE_FLOAT128
8d20e708 1067 printf("%Lg", (long double) item->u.side_basic.u.side_float_binary128);
fb25b355
MD
1068 break;
1069#else
1070 printf("ERROR: Unsupported binary128 float type\n");
1071 abort();
1072#endif
a2e2357e 1073 case SIDE_DYNAMIC_TYPE_STRING:
0e9be766 1074 tracer_print_dynamic_basic_type_header(item);
8d20e708 1075 printf("\"%s\"", item->u.side_basic.u.string);
a2e2357e 1076 break;
c208889e
MD
1077 case SIDE_DYNAMIC_TYPE_STRUCT:
1078 tracer_print_dynamic_struct(item->u.side_dynamic_struct);
a2e2357e 1079 break;
c208889e
MD
1080 case SIDE_DYNAMIC_TYPE_STRUCT_VISITOR:
1081 tracer_print_dynamic_struct_visitor(item);
a2e2357e
MD
1082 break;
1083 case SIDE_DYNAMIC_TYPE_VLA:
1084 tracer_print_dynamic_vla(item->u.side_dynamic_vla);
1085 break;
1086 case SIDE_DYNAMIC_TYPE_VLA_VISITOR:
1087 tracer_print_dynamic_vla_visitor(item);
1088 break;
1089 default:
1090 printf("<UNKNOWN TYPE>");
1091 abort();
1092 }
808bd9bf 1093 printf(" }");
a2e2357e
MD
1094}
1095
68f8cfbe
MD
1096static
1097void tracer_print_static_fields(const struct side_event_description *desc,
1098 const struct side_arg_vec_description *sav_desc,
1099 int *nr_items)
f611d0c3
MD
1100{
1101 const struct side_arg_vec *sav = sav_desc->sav;
1102 uint32_t side_sav_len = sav_desc->len;
1103 int i;
1104
65010f43 1105 printf("provider: %s, event: %s", desc->provider_name, desc->event_name);
f611d0c3
MD
1106 if (desc->nr_fields != side_sav_len) {
1107 printf("ERROR: number of fields mismatch between description and arguments\n");
1108 abort();
1109 }
a848763d
MD
1110 print_attributes(", attributes: ", desc->attr, desc->nr_attr);
1111 printf("%s", side_sav_len ? ", fields: [ " : "");
f611d0c3
MD
1112 for (i = 0; i < side_sav_len; i++) {
1113 printf("%s", i ? ", " : "");
1114 tracer_print_field(&desc->fields[i], &sav[i]);
1115 }
68f8cfbe
MD
1116 if (nr_items)
1117 *nr_items = i;
c7d338e2
MD
1118 if (side_sav_len)
1119 printf(" ]");
68f8cfbe
MD
1120}
1121
4a7d8700
MD
1122void tracer_call(const struct side_event_description *desc,
1123 const struct side_arg_vec_description *sav_desc,
1124 void *priv __attribute__((unused)))
68f8cfbe 1125{
a848763d
MD
1126 int nr_fields = 0;
1127
a848763d 1128 tracer_print_static_fields(desc, sav_desc, &nr_fields);
f611d0c3
MD
1129 printf("\n");
1130}
19fa6aa2
MD
1131
1132void tracer_call_variadic(const struct side_event_description *desc,
4a7d8700
MD
1133 const struct side_arg_vec_description *sav_desc,
1134 const struct side_arg_dynamic_event_struct *var_struct,
1135 void *priv __attribute__((unused)))
19fa6aa2 1136{
68f8cfbe
MD
1137 uint32_t var_struct_len = var_struct->len;
1138 int nr_fields = 0, i;
19fa6aa2 1139
68f8cfbe
MD
1140 tracer_print_static_fields(desc, sav_desc, &nr_fields);
1141
8a25ce77
MD
1142 if (side_unlikely(!(desc->flags & SIDE_EVENT_FLAG_VARIADIC))) {
1143 printf("ERROR: unexpected non-variadic event description\n");
1144 abort();
1145 }
c7d338e2
MD
1146 printf("%s", var_struct->nr_attr && nr_fields ? ", " : "");
1147 print_attributes("attributes:: ", var_struct->attr, var_struct->nr_attr);
1148 printf("%s", var_struct_len && (nr_fields || var_struct->nr_attr) ? ", fields:: [ " : "");
68f8cfbe 1149 for (i = 0; i < var_struct_len; i++, nr_fields++) {
c7d338e2 1150 printf("%s", i ? ", " : "");
68f8cfbe
MD
1151 printf("%s:: ", var_struct->fields[i].field_name);
1152 tracer_print_dynamic(&var_struct->fields[i].elem);
19fa6aa2 1153 }
a848763d
MD
1154 if (i)
1155 printf(" ]");
19fa6aa2
MD
1156 printf("\n");
1157}
This page took 0.077575 seconds and 4 git commands to generate.