lib: private functions: do not repeat `private` word
[babeltrace.git] / plugins / text / pretty / print.c
CommitLineData
af9a82eb
JG
1/*
2 * print.c
3 *
4 * Babeltrace CTF Text Output Plugin Event Printing
5 *
6 * Copyright 2016 Jérémie Galarneau <jeremie.galarneau@efficios.com>
f504043c 7 * Copyright 2016 Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
af9a82eb
JG
8 *
9 * Author: Jérémie Galarneau <jeremie.galarneau@efficios.com>
10 *
11 * Permission is hereby granted, free of charge, to any person obtaining a copy
12 * of this software and associated documentation files (the "Software"), to deal
13 * in the Software without restriction, including without limitation the rights
14 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
15 * copies of the Software, and to permit persons to whom the Software is
16 * furnished to do so, subject to the following conditions:
17 *
18 * The above copyright notice and this permission notice shall be included in
19 * all copies or substantial portions of the Software.
20 *
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
22 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
23 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
24 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
25 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
26 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
27 * SOFTWARE.
28 */
29
9d408fca 30#include <babeltrace/babeltrace.h>
3d9990ac 31#include <babeltrace/bitfield-internal.h>
ad96d936 32#include <babeltrace/common-internal.h>
58a2480d 33#include <babeltrace/compat/time-internal.h>
f6ccaed9 34#include <babeltrace/assert-internal.h>
6a18b281 35#include <inttypes.h>
93a4161c 36#include <ctype.h>
3228cc1d 37#include "pretty.h"
af9a82eb 38
1556a1af
JG
39#define NSEC_PER_SEC 1000000000LL
40
5280f742 41#define COLOR_NAME BT_COMMON_COLOR_BOLD
08899d39 42#define COLOR_FIELD_NAME BT_COMMON_COLOR_FG_CYAN
5280f742
PP
43#define COLOR_RST BT_COMMON_COLOR_RESET
44#define COLOR_STRING_VALUE BT_COMMON_COLOR_BOLD
45#define COLOR_NUMBER_VALUE BT_COMMON_COLOR_BOLD
46#define COLOR_ENUM_MAPPING_NAME BT_COMMON_COLOR_BOLD
47#define COLOR_UNKNOWN BT_COMMON_COLOR_BOLD BT_COMMON_COLOR_FG_RED
08899d39 48#define COLOR_EVENT_NAME BT_COMMON_COLOR_BOLD BT_COMMON_COLOR_FG_MAGENTA
5280f742 49#define COLOR_TIMESTAMP BT_COMMON_COLOR_BOLD BT_COMMON_COLOR_FG_YELLOW
ad96d936 50
af9a82eb
JG
51struct timestamp {
52 int64_t real_timestamp; /* Relative to UNIX epoch. */
53 uint64_t clock_value; /* In cycles. */
54};
55
6a18b281 56static
3228cc1d 57enum bt_component_status print_field(struct pretty_component *pretty,
50842bdc 58 struct bt_field *field, bool print_names,
2b4c4a7c 59 GQuark *filters_fields, int filter_array_len);
6a18b281 60
ad96d936 61static
3228cc1d 62void print_name_equal(struct pretty_component *pretty, const char *name)
ad96d936 63{
3228cc1d 64 if (pretty->use_colors) {
5280f742
PP
65 g_string_append_printf(pretty->string, "%s%s%s = ", COLOR_NAME,
66 name, COLOR_RST);
ad96d936 67 } else {
5280f742 68 g_string_append_printf(pretty->string, "%s = ", name);
ad96d936
PP
69 }
70}
71
72static
3228cc1d 73void print_field_name_equal(struct pretty_component *pretty, const char *name)
ad96d936 74{
3228cc1d 75 if (pretty->use_colors) {
5280f742
PP
76 g_string_append_printf(pretty->string, "%s%s%s = ",
77 COLOR_FIELD_NAME, name, COLOR_RST);
ad96d936 78 } else {
5280f742 79 g_string_append_printf(pretty->string, "%s = ", name);
ad96d936
PP
80 }
81}
82
af9a82eb 83static
3228cc1d 84void print_timestamp_cycles(struct pretty_component *pretty,
50842bdc 85 struct bt_event *event)
af9a82eb 86{
50842bdc 87 struct bt_clock_value *clock_value;
1556a1af 88 uint64_t cycles;
44c440bc 89 enum bt_clock_value_status cv_status;
1556a1af 90
44c440bc
PP
91 cv_status = bt_event_borrow_default_clock_value(event, &clock_value);
92 if (cv_status != BT_CLOCK_VALUE_STATUS_KNOWN || !clock_value) {
5280f742 93 g_string_append(pretty->string, "????????????????????");
1556a1af
JG
94 return;
95 }
96
44c440bc 97 cycles = bt_clock_value_get_value(clock_value);
5280f742 98 g_string_append_printf(pretty->string, "%020" PRIu64, cycles);
3af83b5a 99
3228cc1d
PP
100 if (pretty->last_cycles_timestamp != -1ULL) {
101 pretty->delta_cycles = cycles - pretty->last_cycles_timestamp;
3af83b5a 102 }
3228cc1d 103 pretty->last_cycles_timestamp = cycles;
af9a82eb
JG
104}
105
106static
3228cc1d 107void print_timestamp_wall(struct pretty_component *pretty,
50842bdc 108 struct bt_clock_value *clock_value)
af9a82eb 109{
1556a1af 110 int ret;
1556a1af
JG
111 int64_t ts_nsec = 0; /* add configurable offset */
112 int64_t ts_sec = 0; /* add configurable offset */
113 uint64_t ts_sec_abs, ts_nsec_abs;
114 bool is_negative;
af9a82eb 115
1556a1af 116 if (!clock_value) {
5280f742 117 g_string_append(pretty->string, "??:??:??.?????????");
1556a1af
JG
118 return;
119 }
120
44c440bc 121 ret = bt_clock_value_get_ns_from_origin(clock_value, &ts_nsec);
1556a1af 122 if (ret) {
5280f742
PP
123 // TODO: log, this is unexpected
124 g_string_append(pretty->string, "Error");
1556a1af
JG
125 return;
126 }
127
3228cc1d
PP
128 if (pretty->last_real_timestamp != -1ULL) {
129 pretty->delta_real_timestamp = ts_nsec - pretty->last_real_timestamp;
3af83b5a 130 }
3af83b5a 131
5280f742 132 pretty->last_real_timestamp = ts_nsec;
1556a1af
JG
133 ts_sec += ts_nsec / NSEC_PER_SEC;
134 ts_nsec = ts_nsec % NSEC_PER_SEC;
5280f742 135
1556a1af
JG
136 if (ts_sec >= 0 && ts_nsec >= 0) {
137 is_negative = false;
138 ts_sec_abs = ts_sec;
139 ts_nsec_abs = ts_nsec;
140 } else if (ts_sec > 0 && ts_nsec < 0) {
141 is_negative = false;
142 ts_sec_abs = ts_sec - 1;
143 ts_nsec_abs = NSEC_PER_SEC + ts_nsec;
144 } else if (ts_sec == 0 && ts_nsec < 0) {
145 is_negative = true;
146 ts_sec_abs = ts_sec;
147 ts_nsec_abs = -ts_nsec;
148 } else if (ts_sec < 0 && ts_nsec > 0) {
149 is_negative = true;
150 ts_sec_abs = -(ts_sec + 1);
151 ts_nsec_abs = NSEC_PER_SEC - ts_nsec;
152 } else if (ts_sec < 0 && ts_nsec == 0) {
153 is_negative = true;
154 ts_sec_abs = -ts_sec;
155 ts_nsec_abs = ts_nsec;
156 } else { /* (ts_sec < 0 && ts_nsec < 0) */
157 is_negative = true;
158 ts_sec_abs = -ts_sec;
159 ts_nsec_abs = -ts_nsec;
160 }
161
3228cc1d 162 if (!pretty->options.clock_seconds) {
1556a1af
JG
163 struct tm tm;
164 time_t time_s = (time_t) ts_sec_abs;
165
18adbd19 166 if (is_negative && !pretty->negative_timestamp_warning_done) {
5280f742 167 // TODO: log instead
1556a1af 168 fprintf(stderr, "[warning] Fallback to [sec.ns] to print negative time value. Use --clock-seconds.\n");
18adbd19 169 pretty->negative_timestamp_warning_done = true;
1556a1af
JG
170 goto seconds;
171 }
172
3228cc1d 173 if (!pretty->options.clock_gmt) {
1556a1af
JG
174 struct tm *res;
175
58a2480d 176 res = bt_localtime_r(&time_s, &tm);
1556a1af 177 if (!res) {
5280f742 178 // TODO: log instead
1556a1af
JG
179 fprintf(stderr, "[warning] Unable to get localtime.\n");
180 goto seconds;
181 }
182 } else {
183 struct tm *res;
184
58a2480d 185 res = bt_gmtime_r(&time_s, &tm);
1556a1af 186 if (!res) {
5280f742 187 // TODO: log instead
1556a1af
JG
188 fprintf(stderr, "[warning] Unable to get gmtime.\n");
189 goto seconds;
190 }
191 }
3228cc1d 192 if (pretty->options.clock_date) {
1556a1af
JG
193 char timestr[26];
194 size_t res;
195
196 /* Print date and time */
197 res = strftime(timestr, sizeof(timestr),
4d2a94f1 198 "%Y-%m-%d ", &tm);
1556a1af 199 if (!res) {
5280f742 200 // TODO: log instead
1556a1af
JG
201 fprintf(stderr, "[warning] Unable to print ascii time.\n");
202 goto seconds;
203 }
5280f742
PP
204
205 g_string_append(pretty->string, timestr);
1556a1af 206 }
5280f742 207
1556a1af 208 /* Print time in HH:MM:SS.ns */
5280f742
PP
209 g_string_append_printf(pretty->string,
210 "%02d:%02d:%02d.%09" PRIu64, tm.tm_hour, tm.tm_min,
211 tm.tm_sec, ts_nsec_abs);
1556a1af
JG
212 goto end;
213 }
214seconds:
5280f742
PP
215 g_string_append_printf(pretty->string, "%s%" PRId64 ".%09" PRIu64,
216 is_negative ? "-" : "", ts_sec_abs, ts_nsec_abs);
1556a1af
JG
217end:
218 return;
af9a82eb
JG
219}
220
221static
3228cc1d 222enum bt_component_status print_event_timestamp(struct pretty_component *pretty,
e22b45d0 223 struct bt_event *event, bool *start_line)
af9a82eb 224{
3228cc1d 225 bool print_names = pretty->options.print_header_field_names;
af9a82eb 226 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc
PP
227 struct bt_stream *stream = NULL;
228 struct bt_stream_class *stream_class = NULL;
229 struct bt_trace *trace = NULL;
e22b45d0 230 struct bt_clock_value *clock_value = NULL;
44c440bc 231 enum bt_clock_value_status cv_status;
af9a82eb 232
a82e90e8 233 stream = bt_event_borrow_stream(event);
af9a82eb
JG
234 if (!stream) {
235 ret = BT_COMPONENT_STATUS_ERROR;
236 goto end;
237 }
238
a82e90e8 239 stream_class = bt_stream_borrow_class(stream);
f504043c
MD
240 if (!stream_class) {
241 ret = BT_COMPONENT_STATUS_ERROR;
242 goto end;
243 }
a82e90e8 244 trace = bt_stream_class_borrow_trace(stream_class);
f504043c
MD
245 if (!trace) {
246 ret = BT_COMPONENT_STATUS_ERROR;
247 goto end;
248 }
d9f65f09 249
44c440bc
PP
250 cv_status = bt_event_borrow_default_clock_value(event, &clock_value);
251 if (cv_status != BT_CLOCK_VALUE_STATUS_KNOWN || !clock_value) {
e22b45d0 252 /* No default clock value: skip the timestamp without an error */
f504043c
MD
253 goto end;
254 }
af9a82eb 255
ad96d936 256 if (print_names) {
3228cc1d 257 print_name_equal(pretty, "timestamp");
ad96d936 258 } else {
5280f742 259 g_string_append(pretty->string, "[");
ad96d936 260 }
3228cc1d 261 if (pretty->use_colors) {
5280f742 262 g_string_append(pretty->string, COLOR_TIMESTAMP);
ad96d936 263 }
3228cc1d 264 if (pretty->options.print_timestamp_cycles) {
e22b45d0 265 print_timestamp_cycles(pretty, event);
af9a82eb 266 } else {
44c440bc
PP
267 clock_value = NULL;
268 cv_status = bt_event_borrow_default_clock_value(event,
269 &clock_value);
08899d39 270 print_timestamp_wall(pretty, clock_value);
af9a82eb 271 }
3228cc1d 272 if (pretty->use_colors) {
5280f742 273 g_string_append(pretty->string, COLOR_RST);
ad96d936 274 }
af9a82eb 275
c3c30b08 276 if (!print_names)
5280f742 277 g_string_append(pretty->string, "] ");
c3c30b08 278
3228cc1d 279 if (pretty->options.print_delta_field) {
ad96d936 280 if (print_names) {
5280f742 281 g_string_append(pretty->string, ", ");
3228cc1d 282 print_name_equal(pretty, "delta");
ad96d936 283 } else {
5280f742 284 g_string_append(pretty->string, "(");
ad96d936 285 }
3228cc1d
PP
286 if (pretty->options.print_timestamp_cycles) {
287 if (pretty->delta_cycles == -1ULL) {
5280f742
PP
288 g_string_append(pretty->string,
289 "+??????????\?\?) "); /* Not a trigraph. */
3af83b5a 290 } else {
5280f742
PP
291 g_string_append_printf(pretty->string,
292 "+%012" PRIu64, pretty->delta_cycles);
3af83b5a
MD
293 }
294 } else {
3228cc1d 295 if (pretty->delta_real_timestamp != -1ULL) {
3af83b5a 296 uint64_t delta_sec, delta_nsec, delta;
f504043c 297
3228cc1d 298 delta = pretty->delta_real_timestamp;
3af83b5a
MD
299 delta_sec = delta / NSEC_PER_SEC;
300 delta_nsec = delta % NSEC_PER_SEC;
5280f742
PP
301 g_string_append_printf(pretty->string,
302 "+%" PRIu64 ".%09" PRIu64,
3af83b5a
MD
303 delta_sec, delta_nsec);
304 } else {
5280f742 305 g_string_append(pretty->string, "+?.?????????");
3af83b5a
MD
306 }
307 }
308 if (!print_names) {
5280f742 309 g_string_append(pretty->string, ") ");
3af83b5a
MD
310 }
311 }
312 *start_line = !print_names;
f504043c 313
af9a82eb 314end:
af9a82eb
JG
315 return ret;
316}
317
6a18b281 318static
3228cc1d 319enum bt_component_status print_event_header(struct pretty_component *pretty,
e22b45d0 320 struct bt_event *event)
af9a82eb 321{
3228cc1d 322 bool print_names = pretty->options.print_header_field_names;
6a18b281 323 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc
PP
324 struct bt_event_class *event_class = NULL;
325 struct bt_stream_class *stream_class = NULL;
326 struct bt_trace *trace_class = NULL;
60535549 327 int dom_print = 0;
44c440bc 328 enum bt_property_availability prop_avail;
af9a82eb 329
a82e90e8 330 event_class = bt_event_borrow_class(event);
6a18b281
MD
331 if (!event_class) {
332 ret = BT_COMPONENT_STATUS_ERROR;
333 goto end;
334 }
a82e90e8 335 stream_class = bt_event_class_borrow_stream_class(event_class);
c3c30b08
MD
336 if (!stream_class) {
337 ret = BT_COMPONENT_STATUS_ERROR;
338 goto end;
339 }
a82e90e8 340 trace_class = bt_stream_class_borrow_trace(stream_class);
c3c30b08
MD
341 if (!trace_class) {
342 ret = BT_COMPONENT_STATUS_ERROR;
343 goto end;
344 }
e22b45d0 345 ret = print_event_timestamp(pretty, event, &pretty->start_line);
af9a82eb
JG
346 if (ret != BT_COMPONENT_STATUS_OK) {
347 goto end;
348 }
3228cc1d 349 if (pretty->options.print_trace_field) {
c3c30b08
MD
350 const char *name;
351
50842bdc 352 name = bt_trace_get_name(trace_class);
c3c30b08 353 if (name) {
3228cc1d 354 if (!pretty->start_line) {
5280f742 355 g_string_append(pretty->string, ", ");
c3c30b08 356 }
c3c30b08 357 if (print_names) {
3228cc1d 358 print_name_equal(pretty, "trace");
c3c30b08 359 }
5280f742
PP
360
361 g_string_append(pretty->string, name);
362
60535549 363 if (!print_names) {
5280f742 364 g_string_append(pretty->string, " ");
60535549 365 }
c3c30b08
MD
366 }
367 }
3228cc1d 368 if (pretty->options.print_trace_hostname_field) {
c3c30b08
MD
369 struct bt_value *hostname_str;
370
44c440bc 371 hostname_str = bt_trace_borrow_environment_entry_value_by_name(
a82e90e8 372 trace_class, "hostname");
c3c30b08
MD
373 if (hostname_str) {
374 const char *str;
375
3228cc1d 376 if (!pretty->start_line) {
5280f742 377 g_string_append(pretty->string, ", ");
c3c30b08 378 }
c3c30b08 379 if (print_names) {
3228cc1d 380 print_name_equal(pretty, "trace:hostname");
c3c30b08 381 }
601b0d3c
PP
382 str = bt_value_string_get(hostname_str);
383 g_string_append(pretty->string, str);
60535549 384 dom_print = 1;
c3c30b08
MD
385 }
386 }
3228cc1d 387 if (pretty->options.print_trace_domain_field) {
c3c30b08
MD
388 struct bt_value *domain_str;
389
44c440bc 390 domain_str = bt_trace_borrow_environment_entry_value_by_name(
a82e90e8 391 trace_class, "domain");
c3c30b08
MD
392 if (domain_str) {
393 const char *str;
394
3228cc1d 395 if (!pretty->start_line) {
5280f742 396 g_string_append(pretty->string, ", ");
c3c30b08 397 }
c3c30b08 398 if (print_names) {
3228cc1d 399 print_name_equal(pretty, "trace:domain");
60535549 400 } else if (dom_print) {
5280f742 401 g_string_append(pretty->string, ":");
c3c30b08 402 }
601b0d3c
PP
403 str = bt_value_string_get(domain_str);
404 g_string_append(pretty->string, str);
60535549 405 dom_print = 1;
c3c30b08
MD
406 }
407 }
3228cc1d 408 if (pretty->options.print_trace_procname_field) {
c3c30b08
MD
409 struct bt_value *procname_str;
410
44c440bc 411 procname_str = bt_trace_borrow_environment_entry_value_by_name(
a82e90e8 412 trace_class, "procname");
c3c30b08
MD
413 if (procname_str) {
414 const char *str;
415
3228cc1d 416 if (!pretty->start_line) {
5280f742 417 g_string_append(pretty->string, ", ");
c3c30b08 418 }
c3c30b08 419 if (print_names) {
3228cc1d 420 print_name_equal(pretty, "trace:procname");
60535549 421 } else if (dom_print) {
5280f742 422 g_string_append(pretty->string, ":");
c3c30b08 423 }
601b0d3c
PP
424 str = bt_value_string_get(procname_str);
425 g_string_append(pretty->string, str);
60535549 426 dom_print = 1;
c3c30b08
MD
427 }
428 }
3228cc1d 429 if (pretty->options.print_trace_vpid_field) {
c3c30b08
MD
430 struct bt_value *vpid_value;
431
44c440bc 432 vpid_value = bt_trace_borrow_environment_entry_value_by_name(
a82e90e8 433 trace_class, "vpid");
c3c30b08
MD
434 if (vpid_value) {
435 int64_t value;
436
3228cc1d 437 if (!pretty->start_line) {
5280f742 438 g_string_append(pretty->string, ", ");
c3c30b08 439 }
c3c30b08 440 if (print_names) {
3228cc1d 441 print_name_equal(pretty, "trace:vpid");
60535549 442 } else if (dom_print) {
5280f742 443 g_string_append(pretty->string, ":");
c3c30b08 444 }
601b0d3c
PP
445 value = bt_value_integer_get(vpid_value);
446 g_string_append_printf(pretty->string,
447 "(%" PRId64 ")", value);
60535549 448 dom_print = 1;
c3c30b08
MD
449 }
450 }
3228cc1d 451 if (pretty->options.print_loglevel_field) {
cf76ce92 452 static const char *log_level_names[] = {
50842bdc
PP
453 [ BT_EVENT_CLASS_LOG_LEVEL_EMERGENCY ] = "TRACE_EMERG",
454 [ BT_EVENT_CLASS_LOG_LEVEL_ALERT ] = "TRACE_ALERT",
455 [ BT_EVENT_CLASS_LOG_LEVEL_CRITICAL ] = "TRACE_CRIT",
456 [ BT_EVENT_CLASS_LOG_LEVEL_ERROR ] = "TRACE_ERR",
457 [ BT_EVENT_CLASS_LOG_LEVEL_WARNING ] = "TRACE_WARNING",
458 [ BT_EVENT_CLASS_LOG_LEVEL_NOTICE ] = "TRACE_NOTICE",
459 [ BT_EVENT_CLASS_LOG_LEVEL_INFO ] = "TRACE_INFO",
460 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_SYSTEM ] = "TRACE_DEBUG_SYSTEM",
461 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_PROGRAM ] = "TRACE_DEBUG_PROGRAM",
462 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_PROCESS ] = "TRACE_DEBUG_PROCESS",
463 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_MODULE ] = "TRACE_DEBUG_MODULE",
464 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_UNIT ] = "TRACE_DEBUG_UNIT",
465 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_FUNCTION ] = "TRACE_DEBUG_FUNCTION",
466 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG_LINE ] = "TRACE_DEBUG_LINE",
467 [ BT_EVENT_CLASS_LOG_LEVEL_DEBUG ] = "TRACE_DEBUG",
cf76ce92 468 };
50842bdc 469 enum bt_event_class_log_level log_level;
cf76ce92
PP
470 const char *log_level_str = NULL;
471
44c440bc
PP
472 prop_avail = bt_event_class_get_log_level(event_class,
473 &log_level);
474 if (prop_avail == BT_PROPERTY_AVAILABILITY_AVAILABLE) {
cf76ce92 475 log_level_str = log_level_names[log_level];
44c440bc 476 BT_ASSERT(log_level_str);
c3c30b08 477
3228cc1d 478 if (!pretty->start_line) {
5280f742 479 g_string_append(pretty->string, ", ");
c3c30b08 480 }
c3c30b08 481 if (print_names) {
3228cc1d 482 print_name_equal(pretty, "loglevel");
60535549 483 } else if (dom_print) {
5280f742 484 g_string_append(pretty->string, ":");
c3c30b08 485 }
cf76ce92
PP
486
487 g_string_append(pretty->string, log_level_str);
488 g_string_append_printf(
489 pretty->string, " (%d)", (int) log_level);
60535549 490 dom_print = 1;
c3c30b08
MD
491 }
492 }
3228cc1d 493 if (pretty->options.print_emf_field) {
cf76ce92 494 const char *uri_str;
c3c30b08 495
50842bdc 496 uri_str = bt_event_class_get_emf_uri(event_class);
c3c30b08 497 if (uri_str) {
3228cc1d 498 if (!pretty->start_line) {
5280f742 499 g_string_append(pretty->string, ", ");
c3c30b08 500 }
c3c30b08 501 if (print_names) {
3228cc1d 502 print_name_equal(pretty, "model.emf.uri");
60535549 503 } else if (dom_print) {
5280f742 504 g_string_append(pretty->string, ":");
c3c30b08 505 }
c3c30b08 506
cf76ce92 507 g_string_append(pretty->string, uri_str);
60535549 508 dom_print = 1;
c3c30b08
MD
509 }
510 }
60535549 511 if (dom_print && !print_names) {
5280f742 512 g_string_append(pretty->string, " ");
60535549 513 }
3228cc1d 514 if (!pretty->start_line) {
5280f742 515 g_string_append(pretty->string, ", ");
c3c30b08 516 }
3228cc1d 517 pretty->start_line = true;
6a18b281 518 if (print_names) {
3228cc1d 519 print_name_equal(pretty, "name");
ad96d936 520 }
3228cc1d 521 if (pretty->use_colors) {
5280f742 522 g_string_append(pretty->string, COLOR_EVENT_NAME);
6a18b281 523 }
50842bdc 524 g_string_append(pretty->string, bt_event_class_get_name(event_class));
3228cc1d 525 if (pretty->use_colors) {
5280f742 526 g_string_append(pretty->string, COLOR_RST);
ad96d936 527 }
60535549 528 if (!print_names) {
5280f742 529 g_string_append(pretty->string, ": ");
60535549 530 } else {
5280f742 531 g_string_append(pretty->string, ", ");
60535549 532 }
a82e90e8 533
af9a82eb 534end:
6a18b281
MD
535 return ret;
536}
537
538static
3228cc1d 539enum bt_component_status print_integer(struct pretty_component *pretty,
50842bdc 540 struct bt_field *field)
6a18b281
MD
541{
542 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
5cd6d0e5
PP
543 enum bt_field_class_integer_preferred_display_base base;
544 struct bt_field_class *int_fc;
6a18b281
MD
545 union {
546 uint64_t u;
547 int64_t s;
548 } v;
ad96d936 549 bool rst_color = false;
864cad70 550 enum bt_field_class_type ft_type;
6a18b281 551
5cd6d0e5
PP
552 int_fc = bt_field_borrow_class(field);
553 BT_ASSERT(int_fc);
864cad70
PP
554 ft_type = bt_field_get_class_type(field);
555 if (ft_type == BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER ||
556 ft_type == BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION) {
44c440bc 557 v.u = bt_field_unsigned_integer_get_value(field);
6a18b281 558 } else {
44c440bc 559 v.s = bt_field_signed_integer_get_value(field);
6a18b281
MD
560 }
561
3228cc1d 562 if (pretty->use_colors) {
5280f742 563 g_string_append(pretty->string, COLOR_NUMBER_VALUE);
ad96d936
PP
564 rst_color = true;
565 }
566
5cd6d0e5 567 base = bt_field_class_integer_get_preferred_display_base(int_fc);
6a18b281 568 switch (base) {
5cd6d0e5 569 case BT_FIELD_CLASS_INTEGER_PREFERRED_DISPLAY_BASE_BINARY:
6a18b281
MD
570 {
571 int bitnr, len;
572
5cd6d0e5 573 len = bt_field_class_integer_get_field_value_range(int_fc);
5280f742 574 g_string_append(pretty->string, "0b");
6a18b281
MD
575 v.u = _bt_piecewise_lshift(v.u, 64 - len);
576 for (bitnr = 0; bitnr < len; bitnr++) {
5280f742 577 g_string_append_printf(pretty->string, "%u", (v.u & (1ULL << 63)) ? 1 : 0);
6a18b281
MD
578 v.u = _bt_piecewise_lshift(v.u, 1);
579 }
580 break;
581 }
5cd6d0e5 582 case BT_FIELD_CLASS_INTEGER_PREFERRED_DISPLAY_BASE_OCTAL:
6a18b281 583 {
864cad70
PP
584 if (ft_type == BT_FIELD_CLASS_TYPE_SIGNED_INTEGER ||
585 ft_type == BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION) {
6a18b281
MD
586 int len;
587
5cd6d0e5
PP
588 len = bt_field_class_integer_get_field_value_range(
589 int_fc);
6a18b281
MD
590 if (len < 64) {
591 size_t rounded_len;
592
f6ccaed9 593 BT_ASSERT(len != 0);
6a18b281
MD
594 /* Round length to the nearest 3-bit */
595 rounded_len = (((len - 1) / 3) + 1) * 3;
596 v.u &= ((uint64_t) 1 << rounded_len) - 1;
597 }
598 }
599
5280f742 600 g_string_append_printf(pretty->string, "0%" PRIo64, v.u);
6a18b281
MD
601 break;
602 }
5cd6d0e5 603 case BT_FIELD_CLASS_INTEGER_PREFERRED_DISPLAY_BASE_DECIMAL:
864cad70
PP
604 if (ft_type == BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER ||
605 ft_type == BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION) {
5280f742 606 g_string_append_printf(pretty->string, "%" PRIu64, v.u);
6a18b281 607 } else {
5280f742 608 g_string_append_printf(pretty->string, "%" PRId64, v.s);
6a18b281
MD
609 }
610 break;
5cd6d0e5 611 case BT_FIELD_CLASS_INTEGER_PREFERRED_DISPLAY_BASE_HEXADECIMAL:
6a18b281
MD
612 {
613 int len;
614
5cd6d0e5 615 len = bt_field_class_integer_get_field_value_range(int_fc);
6a18b281
MD
616 if (len < 64) {
617 /* Round length to the nearest nibble */
618 uint8_t rounded_len = ((len + 3) & ~0x3);
619
620 v.u &= ((uint64_t) 1 << rounded_len) - 1;
621 }
622
5280f742 623 g_string_append_printf(pretty->string, "0x%" PRIX64, v.u);
6a18b281
MD
624 break;
625 }
626 default:
627 ret = BT_COMPONENT_STATUS_ERROR;
628 goto end;
629 }
630end:
ad96d936 631 if (rst_color) {
5280f742 632 g_string_append(pretty->string, COLOR_RST);
ad96d936 633 }
6a18b281
MD
634 return ret;
635}
636
93a4161c 637static
3228cc1d 638void print_escape_string(struct pretty_component *pretty, const char *str)
93a4161c
JD
639{
640 int i;
641
5280f742
PP
642 g_string_append_c(pretty->string, '"');
643
93a4161c
JD
644 for (i = 0; i < strlen(str); i++) {
645 /* Escape sequences not recognized by iscntrl(). */
646 switch (str[i]) {
647 case '\\':
5280f742 648 g_string_append(pretty->string, "\\\\");
93a4161c
JD
649 continue;
650 case '\'':
5280f742 651 g_string_append(pretty->string, "\\\'");
93a4161c
JD
652 continue;
653 case '\"':
5280f742 654 g_string_append(pretty->string, "\\\"");
93a4161c
JD
655 continue;
656 case '\?':
5280f742 657 g_string_append(pretty->string, "\\\?");
93a4161c
JD
658 continue;
659 }
660
661 /* Standard characters. */
662 if (!iscntrl(str[i])) {
5280f742 663 g_string_append_c(pretty->string, str[i]);
93a4161c
JD
664 continue;
665 }
666
667 switch (str[i]) {
668 case '\0':
5280f742 669 g_string_append(pretty->string, "\\0");
93a4161c
JD
670 break;
671 case '\a':
5280f742 672 g_string_append(pretty->string, "\\a");
93a4161c
JD
673 break;
674 case '\b':
5280f742 675 g_string_append(pretty->string, "\\b");
93a4161c
JD
676 break;
677 case '\e':
5280f742 678 g_string_append(pretty->string, "\\e");
93a4161c
JD
679 break;
680 case '\f':
5280f742 681 g_string_append(pretty->string, "\\f");
93a4161c
JD
682 break;
683 case '\n':
5280f742 684 g_string_append(pretty->string, "\\n");
93a4161c
JD
685 break;
686 case '\r':
5280f742 687 g_string_append(pretty->string, "\\r");
93a4161c
JD
688 break;
689 case '\t':
5280f742 690 g_string_append(pretty->string, "\\t");
93a4161c
JD
691 break;
692 case '\v':
5280f742 693 g_string_append(pretty->string, "\\v");
93a4161c
JD
694 break;
695 default:
696 /* Unhandled control-sequence, print as hex. */
5280f742 697 g_string_append_printf(pretty->string, "\\x%02x", str[i]);
93a4161c
JD
698 break;
699 }
700 }
5280f742
PP
701
702 g_string_append_c(pretty->string, '"');
93a4161c
JD
703}
704
6a18b281 705static
3228cc1d 706enum bt_component_status print_enum(struct pretty_component *pretty,
50842bdc 707 struct bt_field *field)
6a18b281
MD
708{
709 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
5cd6d0e5
PP
710 struct bt_field_class *enumeration_field_class = NULL;
711 bt_field_class_enumeration_mapping_label_array label_array;
44c440bc
PP
712 uint64_t label_count;
713 uint64_t i;
96e8f959 714
5cd6d0e5
PP
715 enumeration_field_class = bt_field_borrow_class(field);
716 if (!enumeration_field_class) {
96e8f959
MD
717 ret = BT_COMPONENT_STATUS_ERROR;
718 goto end;
719 }
44c440bc 720
864cad70
PP
721 switch (bt_field_get_class_type(field)) {
722 case BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION:
44c440bc
PP
723 ret = bt_field_unsigned_enumeration_get_mapping_labels(field,
724 &label_array, &label_count);
725 break;
864cad70 726 case BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION:
44c440bc
PP
727 ret = bt_field_signed_enumeration_get_mapping_labels(field,
728 &label_array, &label_count);
729 break;
730 default:
731 abort();
96e8f959 732 }
44c440bc
PP
733
734 if (ret) {
96e8f959
MD
735 ret = BT_COMPONENT_STATUS_ERROR;
736 goto end;
737 }
44c440bc 738
83ef3205 739 g_string_append(pretty->string, "( ");
44c440bc 740 if (label_count == 0) {
83ef3205
MD
741 if (pretty->use_colors) {
742 g_string_append(pretty->string, COLOR_UNKNOWN);
743 }
744 g_string_append(pretty->string, "<unknown>");
745 if (pretty->use_colors) {
746 g_string_append(pretty->string, COLOR_RST);
747 }
748 goto skip_loop;
96e8f959 749 }
44c440bc
PP
750 for (i = 0; i < label_count; i++) {
751 const char *mapping_name = label_array[i];
96e8f959 752
44c440bc 753 if (i == 0) {
5280f742 754 g_string_append(pretty->string, ", ");
44c440bc 755 }
3228cc1d 756 if (pretty->use_colors) {
5280f742 757 g_string_append(pretty->string, COLOR_ENUM_MAPPING_NAME);
ad96d936 758 }
3228cc1d
PP
759 print_escape_string(pretty, mapping_name);
760 if (pretty->use_colors) {
5280f742 761 g_string_append(pretty->string, COLOR_RST);
ad96d936 762 }
96e8f959 763 }
83ef3205 764skip_loop:
5280f742 765 g_string_append(pretty->string, " : container = ");
312c056a 766 ret = print_integer(pretty, field);
6a18b281
MD
767 if (ret != BT_COMPONENT_STATUS_OK) {
768 goto end;
769 }
5280f742 770 g_string_append(pretty->string, " )");
6a18b281 771end:
6a18b281
MD
772 return ret;
773}
774
2b4c4a7c 775static
3228cc1d 776int filter_field_name(struct pretty_component *pretty, const char *field_name,
2b4c4a7c
JD
777 GQuark *filter_fields, int filter_array_len)
778{
779 int i;
780 GQuark field_quark = g_quark_try_string(field_name);
781
3228cc1d 782 if (!field_quark || pretty->options.verbose) {
2b4c4a7c
JD
783 return 1;
784 }
785
786 for (i = 0; i < filter_array_len; i++) {
787 if (field_quark == filter_fields[i]) {
788 return 0;
789 }
790 }
791 return 1;
792}
793
6a18b281 794static
3228cc1d 795enum bt_component_status print_struct_field(struct pretty_component *pretty,
50842bdc 796 struct bt_field *_struct,
5cd6d0e5 797 struct bt_field_class *struct_class,
44c440bc 798 uint64_t i, bool print_names, uint64_t *nr_printed_fields,
2b4c4a7c 799 GQuark *filter_fields, int filter_array_len)
6a18b281
MD
800{
801 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
802 const char *field_name;
50842bdc 803 struct bt_field *field = NULL;
5cd6d0e5 804 struct bt_field_class *field_class = NULL;;
6a18b281 805
44c440bc 806 field = bt_field_structure_borrow_member_field_by_index(_struct, i);
6a18b281
MD
807 if (!field) {
808 ret = BT_COMPONENT_STATUS_ERROR;
809 goto end;
810 }
44c440bc 811
5cd6d0e5
PP
812 bt_field_class_structure_borrow_member_by_index(struct_class, i,
813 &field_name, &field_class);
6a18b281 814
3228cc1d 815 if (filter_fields && !filter_field_name(pretty, field_name,
2b4c4a7c
JD
816 filter_fields, filter_array_len)) {
817 ret = BT_COMPONENT_STATUS_OK;
818 goto end;
819 }
820
821 if (*nr_printed_fields > 0) {
5280f742 822 g_string_append(pretty->string, ", ");
6a18b281 823 } else {
5280f742 824 g_string_append(pretty->string, " ");
6a18b281
MD
825 }
826 if (print_names) {
6acddae3 827 print_field_name_equal(pretty, field_name);
6a18b281 828 }
3228cc1d 829 ret = print_field(pretty, field, print_names, NULL, 0);
2b4c4a7c 830 *nr_printed_fields += 1;
a82e90e8 831
6a18b281 832end:
6a18b281
MD
833 return ret;
834}
835
836static
3228cc1d 837enum bt_component_status print_struct(struct pretty_component *pretty,
50842bdc 838 struct bt_field *_struct, bool print_names,
2b4c4a7c 839 GQuark *filter_fields, int filter_array_len)
6a18b281
MD
840{
841 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
5cd6d0e5 842 struct bt_field_class *struct_class = NULL;
44c440bc 843 uint64_t nr_fields, i, nr_printed_fields;
6a18b281 844
5cd6d0e5
PP
845 struct_class = bt_field_borrow_class(_struct);
846 if (!struct_class) {
6a18b281
MD
847 ret = BT_COMPONENT_STATUS_ERROR;
848 goto end;
849 }
5cd6d0e5 850 nr_fields = bt_field_class_structure_get_member_count(struct_class);
6a18b281
MD
851 if (nr_fields < 0) {
852 ret = BT_COMPONENT_STATUS_ERROR;
853 goto end;
854 }
5280f742 855 g_string_append(pretty->string, "{");
3228cc1d 856 pretty->depth++;
2b4c4a7c 857 nr_printed_fields = 0;
6a18b281 858 for (i = 0; i < nr_fields; i++) {
5cd6d0e5 859 ret = print_struct_field(pretty, _struct, struct_class, i,
2b4c4a7c
JD
860 print_names, &nr_printed_fields, filter_fields,
861 filter_array_len);
6a18b281
MD
862 if (ret != BT_COMPONENT_STATUS_OK) {
863 goto end;
864 }
865 }
3228cc1d 866 pretty->depth--;
5280f742 867 g_string_append(pretty->string, " }");
a82e90e8 868
6a18b281 869end:
6a18b281
MD
870 return ret;
871}
872
873static
3228cc1d 874enum bt_component_status print_array_field(struct pretty_component *pretty,
44c440bc 875 struct bt_field *array, uint64_t i, bool print_names)
6a18b281 876{
50842bdc 877 struct bt_field *field = NULL;
6a18b281 878
44c440bc
PP
879 if (i != 0) {
880 g_string_append(pretty->string, ", ");
881 } else {
882 g_string_append(pretty->string, " ");
6a18b281 883 }
44c440bc
PP
884 if (print_names) {
885 g_string_append_printf(pretty->string, "[%" PRIu64 "] = ", i);
6a18b281 886 }
a82e90e8 887
44c440bc
PP
888 field = bt_field_array_borrow_element_field_by_index(array, i);
889 BT_ASSERT(field);
890 return print_field(pretty, field, print_names, NULL, 0);
6a18b281
MD
891}
892
893static
3228cc1d 894enum bt_component_status print_array(struct pretty_component *pretty,
50842bdc 895 struct bt_field *array, bool print_names)
6a18b281
MD
896{
897 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
5cd6d0e5 898 struct bt_field_class *array_class = NULL;
44c440bc 899 uint64_t len;
6a18b281 900 uint64_t i;
6a18b281 901
5cd6d0e5
PP
902 array_class = bt_field_borrow_class(array);
903 if (!array_class) {
6a18b281
MD
904 ret = BT_COMPONENT_STATUS_ERROR;
905 goto end;
906 }
44c440bc
PP
907 len = bt_field_array_get_length(array);
908 g_string_append(pretty->string, "[");
3228cc1d 909 pretty->depth++;
6a18b281 910 for (i = 0; i < len; i++) {
44c440bc 911 ret = print_array_field(pretty, array, i, print_names);
6a18b281
MD
912 if (ret != BT_COMPONENT_STATUS_OK) {
913 goto end;
914 }
915 }
3228cc1d 916 pretty->depth--;
44c440bc 917 g_string_append(pretty->string, " ]");
a82e90e8 918
6a18b281 919end:
6a18b281
MD
920 return ret;
921}
922
923static
3228cc1d 924enum bt_component_status print_sequence_field(struct pretty_component *pretty,
44c440bc 925 struct bt_field *seq, uint64_t i, bool print_names)
6a18b281 926{
50842bdc 927 struct bt_field *field = NULL;
6a18b281 928
44c440bc
PP
929 if (i != 0) {
930 g_string_append(pretty->string, ", ");
931 } else {
932 g_string_append(pretty->string, " ");
6a18b281 933 }
44c440bc
PP
934 if (print_names) {
935 g_string_append_printf(pretty->string, "[%" PRIu64 "] = ", i);
6a18b281 936 }
a82e90e8 937
44c440bc
PP
938 field = bt_field_array_borrow_element_field_by_index(seq, i);
939 BT_ASSERT(field);
940 return print_field(pretty, field, print_names, NULL, 0);
6a18b281
MD
941}
942
943static
3228cc1d 944enum bt_component_status print_sequence(struct pretty_component *pretty,
50842bdc 945 struct bt_field *seq, bool print_names)
6a18b281
MD
946{
947 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
44c440bc 948 uint64_t len;
6a18b281 949 uint64_t i;
6a18b281 950
44c440bc 951 len = bt_field_array_get_length(seq);
312c056a 952 if (len < 0) {
6a18b281
MD
953 ret = BT_COMPONENT_STATUS_ERROR;
954 goto end;
955 }
6a18b281 956
44c440bc 957 g_string_append(pretty->string, "[");
6a18b281 958
3228cc1d 959 pretty->depth++;
6a18b281 960 for (i = 0; i < len; i++) {
44c440bc 961 ret = print_sequence_field(pretty, seq, i, print_names);
6a18b281
MD
962 if (ret != BT_COMPONENT_STATUS_OK) {
963 goto end;
964 }
965 }
3228cc1d 966 pretty->depth--;
44c440bc 967 g_string_append(pretty->string, " ]");
a82e90e8 968
6a18b281 969end:
6a18b281
MD
970 return ret;
971}
972
973static
3228cc1d 974enum bt_component_status print_variant(struct pretty_component *pretty,
50842bdc 975 struct bt_field *variant, bool print_names)
6a18b281
MD
976{
977 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc 978 struct bt_field *field = NULL;
6a18b281 979
44c440bc
PP
980 field = bt_field_variant_borrow_selected_option_field(variant);
981 BT_ASSERT(field);
5280f742 982 g_string_append(pretty->string, "{ ");
3228cc1d 983 pretty->depth++;
6a18b281 984 if (print_names) {
44c440bc
PP
985 // TODO: find tag's name using field path
986 // print_field_name_equal(pretty, tag_choice);
6a18b281 987 }
3228cc1d 988 ret = print_field(pretty, field, print_names, NULL, 0);
6a18b281
MD
989 if (ret != BT_COMPONENT_STATUS_OK) {
990 goto end;
991 }
3228cc1d 992 pretty->depth--;
5280f742 993 g_string_append(pretty->string, " }");
a82e90e8 994
6a18b281 995end:
6a18b281
MD
996 return ret;
997}
998
999static
3228cc1d 1000enum bt_component_status print_field(struct pretty_component *pretty,
50842bdc 1001 struct bt_field *field, bool print_names,
2b4c4a7c 1002 GQuark *filter_fields, int filter_array_len)
6a18b281 1003{
864cad70 1004 enum bt_field_class_type class_id;
6a18b281 1005
864cad70 1006 class_id = bt_field_get_class_type(field);
5cd6d0e5 1007 switch (class_id) {
864cad70
PP
1008 case BT_FIELD_CLASS_TYPE_UNSIGNED_INTEGER:
1009 case BT_FIELD_CLASS_TYPE_SIGNED_INTEGER:
3228cc1d 1010 return print_integer(pretty, field);
864cad70 1011 case BT_FIELD_CLASS_TYPE_REAL:
6a18b281
MD
1012 {
1013 double v;
1014
44c440bc 1015 v = bt_field_real_get_value(field);
3228cc1d 1016 if (pretty->use_colors) {
5280f742 1017 g_string_append(pretty->string, COLOR_NUMBER_VALUE);
ad96d936 1018 }
5280f742 1019 g_string_append_printf(pretty->string, "%g", v);
3228cc1d 1020 if (pretty->use_colors) {
5280f742 1021 g_string_append(pretty->string, COLOR_RST);
ad96d936 1022 }
6a18b281
MD
1023 return BT_COMPONENT_STATUS_OK;
1024 }
864cad70
PP
1025 case BT_FIELD_CLASS_TYPE_UNSIGNED_ENUMERATION:
1026 case BT_FIELD_CLASS_TYPE_SIGNED_ENUMERATION:
3228cc1d 1027 return print_enum(pretty, field);
864cad70 1028 case BT_FIELD_CLASS_TYPE_STRING:
95a518bf
JG
1029 {
1030 const char *str;
1031
50842bdc 1032 str = bt_field_string_get_value(field);
95a518bf
JG
1033 if (!str) {
1034 return BT_COMPONENT_STATUS_ERROR;
1035 }
1036
3228cc1d 1037 if (pretty->use_colors) {
5280f742 1038 g_string_append(pretty->string, COLOR_STRING_VALUE);
ad96d936 1039 }
95a518bf 1040 print_escape_string(pretty, str);
3228cc1d 1041 if (pretty->use_colors) {
5280f742 1042 g_string_append(pretty->string, COLOR_RST);
ad96d936 1043 }
6a18b281 1044 return BT_COMPONENT_STATUS_OK;
95a518bf 1045 }
864cad70 1046 case BT_FIELD_CLASS_TYPE_STRUCTURE:
3228cc1d 1047 return print_struct(pretty, field, print_names, filter_fields,
2b4c4a7c 1048 filter_array_len);
864cad70 1049 case BT_FIELD_CLASS_TYPE_VARIANT:
3228cc1d 1050 return print_variant(pretty, field, print_names);
864cad70 1051 case BT_FIELD_CLASS_TYPE_STATIC_ARRAY:
3228cc1d 1052 return print_array(pretty, field, print_names);
864cad70 1053 case BT_FIELD_CLASS_TYPE_DYNAMIC_ARRAY:
3228cc1d 1054 return print_sequence(pretty, field, print_names);
6a18b281 1055 default:
5280f742 1056 // TODO: log instead
5cd6d0e5 1057 fprintf(pretty->err, "[error] Unknown type id: %d\n", (int) class_id);
6a18b281
MD
1058 return BT_COMPONENT_STATUS_ERROR;
1059 }
1060}
1061
1062static
3228cc1d 1063enum bt_component_status print_stream_packet_context(struct pretty_component *pretty,
50842bdc 1064 struct bt_event *event)
6a18b281
MD
1065{
1066 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc
PP
1067 struct bt_packet *packet = NULL;
1068 struct bt_field *main_field = NULL;
6a18b281 1069
a82e90e8 1070 packet = bt_event_borrow_packet(event);
6a18b281
MD
1071 if (!packet) {
1072 ret = BT_COMPONENT_STATUS_ERROR;
1073 goto end;
1074 }
44c440bc 1075 main_field = bt_packet_borrow_context_field(packet);
6a18b281 1076 if (!main_field) {
6a18b281
MD
1077 goto end;
1078 }
3228cc1d 1079 if (!pretty->start_line) {
5280f742 1080 g_string_append(pretty->string, ", ");
6e1bc0df 1081 }
3228cc1d
PP
1082 pretty->start_line = false;
1083 if (pretty->options.print_scope_field_names) {
1084 print_name_equal(pretty, "stream.packet.context");
6a18b281 1085 }
3228cc1d
PP
1086 ret = print_field(pretty, main_field,
1087 pretty->options.print_context_field_names,
2b4c4a7c
JD
1088 stream_packet_context_quarks,
1089 STREAM_PACKET_CONTEXT_QUARKS_LEN);
a82e90e8 1090
6a18b281 1091end:
6a18b281
MD
1092 return ret;
1093}
1094
1095static
3228cc1d 1096enum bt_component_status print_event_header_raw(struct pretty_component *pretty,
50842bdc 1097 struct bt_event *event)
6a18b281
MD
1098{
1099 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc 1100 struct bt_field *main_field = NULL;
6a18b281 1101
44c440bc 1102 main_field = bt_event_borrow_header_field(event);
6a18b281 1103 if (!main_field) {
6a18b281
MD
1104 goto end;
1105 }
3228cc1d 1106 if (!pretty->start_line) {
5280f742 1107 g_string_append(pretty->string, ", ");
6e1bc0df 1108 }
3228cc1d
PP
1109 pretty->start_line = false;
1110 if (pretty->options.print_scope_field_names) {
1111 print_name_equal(pretty, "stream.event.header");
6a18b281 1112 }
3228cc1d
PP
1113 ret = print_field(pretty, main_field,
1114 pretty->options.print_header_field_names, NULL, 0);
a82e90e8 1115
6a18b281 1116end:
6a18b281
MD
1117 return ret;
1118}
1119
1120static
3228cc1d 1121enum bt_component_status print_stream_event_context(struct pretty_component *pretty,
50842bdc 1122 struct bt_event *event)
6a18b281
MD
1123{
1124 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc 1125 struct bt_field *main_field = NULL;
6a18b281 1126
44c440bc 1127 main_field = bt_event_borrow_common_context_field(event);
6a18b281 1128 if (!main_field) {
6a18b281
MD
1129 goto end;
1130 }
3228cc1d 1131 if (!pretty->start_line) {
5280f742 1132 g_string_append(pretty->string, ", ");
6e1bc0df 1133 }
3228cc1d
PP
1134 pretty->start_line = false;
1135 if (pretty->options.print_scope_field_names) {
1136 print_name_equal(pretty, "stream.event.context");
6a18b281 1137 }
3228cc1d
PP
1138 ret = print_field(pretty, main_field,
1139 pretty->options.print_context_field_names, NULL, 0);
a82e90e8 1140
6a18b281 1141end:
6a18b281
MD
1142 return ret;
1143}
1144
1145static
3228cc1d 1146enum bt_component_status print_event_context(struct pretty_component *pretty,
50842bdc 1147 struct bt_event *event)
6a18b281
MD
1148{
1149 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc 1150 struct bt_field *main_field = NULL;
6a18b281 1151
44c440bc 1152 main_field = bt_event_borrow_specific_context_field(event);
6a18b281 1153 if (!main_field) {
6a18b281
MD
1154 goto end;
1155 }
3228cc1d 1156 if (!pretty->start_line) {
5280f742 1157 g_string_append(pretty->string, ", ");
6e1bc0df 1158 }
3228cc1d
PP
1159 pretty->start_line = false;
1160 if (pretty->options.print_scope_field_names) {
1161 print_name_equal(pretty, "event.context");
6a18b281 1162 }
3228cc1d
PP
1163 ret = print_field(pretty, main_field,
1164 pretty->options.print_context_field_names, NULL, 0);
a82e90e8 1165
6a18b281 1166end:
6a18b281
MD
1167 return ret;
1168}
1169
1170static
3228cc1d 1171enum bt_component_status print_event_payload(struct pretty_component *pretty,
50842bdc 1172 struct bt_event *event)
6a18b281
MD
1173{
1174 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
50842bdc 1175 struct bt_field *main_field = NULL;
6a18b281 1176
44c440bc 1177 main_field = bt_event_borrow_payload_field(event);
6a18b281 1178 if (!main_field) {
6a18b281
MD
1179 goto end;
1180 }
3228cc1d 1181 if (!pretty->start_line) {
5280f742 1182 g_string_append(pretty->string, ", ");
6e1bc0df 1183 }
3228cc1d
PP
1184 pretty->start_line = false;
1185 if (pretty->options.print_scope_field_names) {
1186 print_name_equal(pretty, "event.fields");
6a18b281 1187 }
3228cc1d
PP
1188 ret = print_field(pretty, main_field,
1189 pretty->options.print_payload_field_names, NULL, 0);
a82e90e8 1190
6a18b281 1191end:
af9a82eb
JG
1192 return ret;
1193}
1194
08899d39 1195static
0f6bea4e 1196int flush_buf(FILE *stream, struct pretty_component *pretty)
08899d39
PP
1197{
1198 int ret = 0;
1199
1200 if (pretty->string->len == 0) {
1201 goto end;
1202 }
1203
0f6bea4e 1204 if (fwrite(pretty->string->str, pretty->string->len, 1, stream) != 1) {
08899d39
PP
1205 ret = -1;
1206 }
1207
1208end:
1209 return ret;
1210}
1211
af9a82eb 1212BT_HIDDEN
3228cc1d 1213enum bt_component_status pretty_print_event(struct pretty_component *pretty,
d9f65f09 1214 struct bt_notification *event_notif)
af9a82eb
JG
1215{
1216 enum bt_component_status ret;
50842bdc 1217 struct bt_event *event =
a82e90e8 1218 bt_notification_event_borrow_event(event_notif);
af9a82eb 1219
f6ccaed9 1220 BT_ASSERT(event);
3228cc1d 1221 pretty->start_line = true;
5280f742 1222 g_string_assign(pretty->string, "");
e22b45d0 1223 ret = print_event_header(pretty, event);
af9a82eb
JG
1224 if (ret != BT_COMPONENT_STATUS_OK) {
1225 goto end;
1226 }
6a18b281 1227
3228cc1d 1228 ret = print_stream_packet_context(pretty, event);
6a18b281
MD
1229 if (ret != BT_COMPONENT_STATUS_OK) {
1230 goto end;
1231 }
6a18b281 1232
3228cc1d
PP
1233 if (pretty->options.verbose) {
1234 ret = print_event_header_raw(pretty, event);
60535549
JD
1235 if (ret != BT_COMPONENT_STATUS_OK) {
1236 goto end;
1237 }
6a18b281 1238 }
6a18b281 1239
3228cc1d 1240 ret = print_stream_event_context(pretty, event);
6a18b281
MD
1241 if (ret != BT_COMPONENT_STATUS_OK) {
1242 goto end;
1243 }
6a18b281 1244
3228cc1d 1245 ret = print_event_context(pretty, event);
6a18b281
MD
1246 if (ret != BT_COMPONENT_STATUS_OK) {
1247 goto end;
1248 }
6a18b281 1249
3228cc1d 1250 ret = print_event_payload(pretty, event);
6a18b281
MD
1251 if (ret != BT_COMPONENT_STATUS_OK) {
1252 goto end;
1253 }
af9a82eb 1254
5280f742 1255 g_string_append_c(pretty->string, '\n');
0f6bea4e 1256 if (flush_buf(pretty->out, pretty)) {
5280f742
PP
1257 ret = BT_COMPONENT_STATUS_ERROR;
1258 goto end;
1259 }
1260
af9a82eb
JG
1261end:
1262 return ret;
1263}
0f6bea4e
PP
1264
1265static
1266enum bt_component_status print_discarded_elements_msg(
1267 struct pretty_component *pretty, struct bt_packet *packet,
1268 uint64_t count, const char *elem_type)
1269{
44c440bc 1270#if 0
0f6bea4e
PP
1271 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
1272 struct bt_stream *stream = NULL;
1273 struct bt_stream_class *stream_class = NULL;
1274 struct bt_trace *trace = NULL;
1275 const char *stream_name;
1276 const char *trace_name;
1277 const unsigned char *trace_uuid;
1278 int64_t stream_class_id;
1279 int64_t stream_id;
1280 struct bt_clock_value *begin_clock_value = NULL;
1281 struct bt_clock_value *end_clock_value = NULL;
1282
1283 /* Stream name */
1284 BT_ASSERT(packet);
1285 stream = bt_packet_borrow_stream(packet);
1286 BT_ASSERT(stream);
1287 stream_name = bt_stream_get_name(stream);
1288
1289 /* Stream class ID */
1290 stream_class = bt_stream_borrow_class(stream);
1291 BT_ASSERT(stream_class);
1292 stream_class_id = bt_stream_class_get_id(stream_class);
1293
1294 /* Stream ID */
1295 stream_id = bt_stream_get_id(stream);
1296
1297 /* Trace name */
1298 trace = bt_stream_class_borrow_trace(stream_class);
1299 BT_ASSERT(trace);
1300 trace_name = bt_trace_get_name(trace);
1301 if (!trace_name) {
1302 trace_name = "(unknown)";
1303 }
1304
1305 /* Trace UUID */
1306 trace_uuid = bt_trace_get_uuid(trace);
1307
1308 /* Beginning and end times */
1309 (void) bt_packet_borrow_previous_packet_default_end_clock_value(
1310 packet, &begin_clock_value);
1311 (void) bt_packet_borrow_default_end_clock_value(packet,
1312 &end_clock_value);
1313
1314 /* Format message */
1315 g_string_assign(pretty->string, "");
1316 g_string_append_printf(pretty->string,
1317 "%s%sWARNING%s%s: Tracer discarded %" PRId64 " %s%s ",
1318 bt_common_color_fg_yellow(),
1319 bt_common_color_bold(),
1320 bt_common_color_reset(),
1321 bt_common_color_fg_yellow(),
1322 count, elem_type, count == 1 ? "" : "s");
1323
1324 if (begin_clock_value && end_clock_value) {
1325 g_string_append(pretty->string, "between [");
1326 print_timestamp_wall(pretty, begin_clock_value);
1327 g_string_append(pretty->string, "] and [");
1328 print_timestamp_wall(pretty, end_clock_value);
1329 g_string_append(pretty->string, "]");
1330 } else {
1331 g_string_append(pretty->string, "(unknown time range)");
1332 }
1333
1334 g_string_append_printf(pretty->string, " in trace \"%s\" ", trace_name);
1335
1336 if (trace_uuid) {
1337 g_string_append_printf(pretty->string,
1338 "(UUID: %02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x) ",
1339 trace_uuid[0],
1340 trace_uuid[1],
1341 trace_uuid[2],
1342 trace_uuid[3],
1343 trace_uuid[4],
1344 trace_uuid[5],
1345 trace_uuid[6],
1346 trace_uuid[7],
1347 trace_uuid[8],
1348 trace_uuid[9],
1349 trace_uuid[10],
1350 trace_uuid[11],
1351 trace_uuid[12],
1352 trace_uuid[13],
1353 trace_uuid[14],
1354 trace_uuid[15]);
1355 } else {
1356 g_string_append(pretty->string, "(no UUID) ");
1357 }
1358
1359 g_string_append_printf(pretty->string,
1360 "within stream \"%s\" (stream class ID: %" PRId64 ", ",
1361 stream_name, stream_class_id);
1362
1363 if (stream_id >= 0) {
1364 g_string_append_printf(pretty->string,
1365 "stream ID: %" PRId64, stream_id);
1366 } else {
1367 g_string_append(pretty->string, "no stream ID");
1368 }
1369
1370 g_string_append_printf(pretty->string, ").%s\n",
1371 bt_common_color_reset());
1372
1373 /*
1374 * Print to standard error stream to remain backward compatible
1375 * with Babeltrace 1.
1376 */
1377 if (flush_buf(stderr, pretty)) {
1378 ret = BT_COMPONENT_STATUS_ERROR;
1379 }
1380
1381 return ret;
44c440bc
PP
1382#endif
1383 return 0;
0f6bea4e
PP
1384}
1385
1386BT_HIDDEN
1387enum bt_component_status pretty_print_packet(struct pretty_component *pretty,
1388 struct bt_notification *packet_beginning_notif)
1389{
44c440bc 1390#if 0
0f6bea4e
PP
1391 struct bt_packet *packet = bt_notification_packet_begin_borrow_packet(
1392 packet_beginning_notif);
1393 uint64_t count;
1394 enum bt_component_status status = BT_COMPONENT_STATUS_OK;
1395
1396 if (bt_packet_get_discarded_event_count(packet, &count) ==
1397 BT_PACKET_PROPERTY_AVAILABILITY_AVAILABLE &&
1398 count > 0) {
1399 status = print_discarded_elements_msg(pretty, packet,
1400 count, "event");
1401 if (status != BT_COMPONENT_STATUS_OK) {
1402 goto end;
1403 }
1404 }
1405
1406 if (bt_packet_get_discarded_packet_count(packet, &count) ==
1407 BT_PACKET_PROPERTY_AVAILABILITY_AVAILABLE &&
1408 count > 0) {
1409 status = print_discarded_elements_msg(pretty, packet,
1410 count, "packet");
1411 if (status != BT_COMPONENT_STATUS_OK) {
1412 goto end;
1413 }
1414 }
1415
1416end:
1417 return status;
44c440bc
PP
1418#endif
1419 return 0;
0f6bea4e 1420}
This page took 0.117733 seconds and 4 git commands to generate.