Fix: lib: add NULL check for destroy_listeners in destroy_component_class
[babeltrace.git] / src / ctf-writer / clock-class.c
1 /*
2 * SPDX-License-Identifier: MIT
3 *
4 * Copyright 2013, 2014 Jérémie Galarneau <jeremie.galarneau@efficios.com>
5 *
6 * Babeltrace CTF writer - Clock class
7 */
8
9 #define BT_LOG_TAG "CTF-WRITER/CLOCK-CLASS"
10 #include "logging.h"
11
12 #include "common/uuid.h"
13 #include <babeltrace2-ctf-writer/utils.h>
14 #include <babeltrace2-ctf-writer/object.h>
15 #include "compat/compiler.h"
16 #include <babeltrace2/types.h>
17 #include "compat/string.h"
18 #include <stdbool.h>
19 #include <inttypes.h>
20 #include "common/assert.h"
21
22 #include "assert-pre.h"
23 #include "clock-class.h"
24 #include "object.h"
25
26 static
27 void bt_ctf_clock_class_destroy(struct bt_ctf_object *obj);
28
29 BT_HIDDEN
30 bt_ctf_bool bt_ctf_clock_class_is_valid(struct bt_ctf_clock_class *clock_class)
31 {
32 return clock_class && clock_class->name;
33 }
34
35 BT_HIDDEN
36 int bt_ctf_clock_class_set_name(struct bt_ctf_clock_class *clock_class,
37 const char *name)
38 {
39 int ret = 0;
40
41 if (!clock_class) {
42 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
43 ret = -1;
44 goto end;
45 }
46
47 if (clock_class->frozen) {
48 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
49 clock_class, bt_ctf_clock_class_get_name(clock_class));
50 ret = -1;
51 goto end;
52 }
53
54 if (!bt_ctf_identifier_is_valid(name)) {
55 BT_LOGW("Clock class's name is not a valid CTF identifier: "
56 "addr=%p, name=\"%s\"",
57 clock_class, name);
58 ret = -1;
59 goto end;
60 }
61
62 if (clock_class->name) {
63 g_string_assign(clock_class->name, name);
64 } else {
65 clock_class->name = g_string_new(name);
66 if (!clock_class->name) {
67 BT_LOGE_STR("Failed to allocate a GString.");
68 ret = -1;
69 goto end;
70 }
71 }
72
73 BT_LOGT("Set clock class's name: addr=%p, name=\"%s\"",
74 clock_class, name);
75
76 end:
77 return ret;
78 }
79
80 static
81 bool validate_freq(struct bt_ctf_clock_class *clock_class,
82 const char *name, uint64_t freq)
83 {
84 bool is_valid = true;
85
86 if (freq == -1ULL || freq == 0) {
87 BT_LOGW("Invalid parameter: frequency is invalid: "
88 "addr=%p, name=\"%s\", freq=%" PRIu64,
89 clock_class, name, freq);
90 is_valid = false;
91 goto end;
92 }
93
94 end:
95 return is_valid;
96 }
97
98 BT_HIDDEN
99 struct bt_ctf_clock_class *bt_ctf_clock_class_create(const char *name,
100 uint64_t freq)
101 {
102 int ret;
103 struct bt_ctf_clock_class *clock_class = NULL;
104
105 BT_LOGD("Creating default clock class object: name=\"%s\"",
106 name);
107
108 if (!validate_freq(NULL, name, freq)) {
109 /* validate_freq() logs errors */
110 goto error;
111 }
112
113 clock_class = g_new0(struct bt_ctf_clock_class, 1);
114 if (!clock_class) {
115 BT_LOGE_STR("Failed to allocate one clock class.");
116 goto error;
117 }
118
119 clock_class->precision = 1;
120 clock_class->frequency = freq;
121 bt_ctf_object_init_shared(&clock_class->base, bt_ctf_clock_class_destroy);
122
123 if (name) {
124 ret = bt_ctf_clock_class_set_name(clock_class, name);
125 if (ret) {
126 /* bt_ctf_clock_class_set_name() logs errors */
127 goto error;
128 }
129 }
130
131 BT_LOGD("Created clock class object: addr=%p, name=\"%s\"",
132 clock_class, name);
133 return clock_class;
134 error:
135 BT_CTF_OBJECT_PUT_REF_AND_RESET(clock_class);
136 return clock_class;
137 }
138
139 BT_HIDDEN
140 const char *bt_ctf_clock_class_get_name(struct bt_ctf_clock_class *clock_class)
141 {
142 const char *ret = NULL;
143
144 if (!clock_class) {
145 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
146 goto end;
147 }
148
149 if (clock_class->name) {
150 ret = clock_class->name->str;
151 }
152
153 end:
154 return ret;
155 }
156
157 BT_HIDDEN
158 const char *bt_ctf_clock_class_get_description(
159 struct bt_ctf_clock_class *clock_class)
160 {
161 const char *ret = NULL;
162
163 if (!clock_class) {
164 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
165 goto end;
166 }
167
168 if (clock_class->description) {
169 ret = clock_class->description->str;
170 }
171 end:
172 return ret;
173 }
174
175 BT_HIDDEN
176 int bt_ctf_clock_class_set_description(struct bt_ctf_clock_class *clock_class,
177 const char *desc)
178 {
179 int ret = 0;
180
181 if (!clock_class || !desc) {
182 BT_LOGW("Invalid parameter: clock class or description is NULL: "
183 "clock-class-addr=%p, name=\"%s\", desc-addr=%p",
184 clock_class, bt_ctf_clock_class_get_name(clock_class),
185 desc);
186 ret = -1;
187 goto end;
188 }
189
190 if (clock_class->frozen) {
191 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
192 clock_class, bt_ctf_clock_class_get_name(clock_class));
193 ret = -1;
194 goto end;
195 }
196
197 clock_class->description = g_string_new(desc);
198 ret = clock_class->description ? 0 : -1;
199 BT_LOGT("Set clock class's description: addr=%p, "
200 "name=\"%s\", desc=\"%s\"",
201 clock_class, bt_ctf_clock_class_get_name(clock_class), desc);
202 end:
203 return ret;
204 }
205
206 BT_HIDDEN
207 uint64_t bt_ctf_clock_class_get_frequency(
208 struct bt_ctf_clock_class *clock_class)
209 {
210 uint64_t ret = -1ULL;
211
212 if (!clock_class) {
213 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
214 goto end;
215 }
216
217 ret = clock_class->frequency;
218 end:
219 return ret;
220 }
221
222 BT_HIDDEN
223 int bt_ctf_clock_class_set_frequency(struct bt_ctf_clock_class *clock_class,
224 uint64_t freq)
225 {
226 int ret = 0;
227
228 if (!clock_class) {
229 BT_LOGW("Invalid parameter: clock class is NULL or frequency is invalid: "
230 "addr=%p, name=\"%s\"",
231 clock_class, bt_ctf_clock_class_get_name(clock_class));
232 ret = -1;
233 goto end;
234 }
235
236 if (!validate_freq(clock_class, bt_ctf_clock_class_get_name(clock_class),
237 freq)) {
238 /* validate_freq() logs errors */
239 goto end;
240 }
241
242 if (clock_class->frozen) {
243 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
244 clock_class, bt_ctf_clock_class_get_name(clock_class));
245 ret = -1;
246 goto end;
247 }
248
249 clock_class->frequency = freq;
250 BT_LOGT("Set clock class's frequency: addr=%p, name=\"%s\", freq=%" PRIu64,
251 clock_class, bt_ctf_clock_class_get_name(clock_class), freq);
252 end:
253 return ret;
254 }
255
256 BT_HIDDEN
257 uint64_t bt_ctf_clock_class_get_precision(struct bt_ctf_clock_class *clock_class)
258 {
259 uint64_t ret = -1ULL;
260
261 if (!clock_class) {
262 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
263 goto end;
264 }
265
266 ret = clock_class->precision;
267 end:
268 return ret;
269 }
270
271 BT_HIDDEN
272 int bt_ctf_clock_class_set_precision(struct bt_ctf_clock_class *clock_class,
273 uint64_t precision)
274 {
275 int ret = 0;
276
277 if (!clock_class || precision == -1ULL) {
278 BT_LOGW("Invalid parameter: clock class is NULL or precision is invalid: "
279 "addr=%p, name=\"%s\", precision=%" PRIu64,
280 clock_class, bt_ctf_clock_class_get_name(clock_class),
281 precision);
282 ret = -1;
283 goto end;
284 }
285
286 if (clock_class->frozen) {
287 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
288 clock_class, bt_ctf_clock_class_get_name(clock_class));
289 ret = -1;
290 goto end;
291 }
292
293 clock_class->precision = precision;
294 BT_LOGT("Set clock class's precision: addr=%p, name=\"%s\", precision=%" PRIu64,
295 clock_class, bt_ctf_clock_class_get_name(clock_class),
296 precision);
297 end:
298 return ret;
299 }
300
301 BT_HIDDEN
302 int bt_ctf_clock_class_get_offset_s(struct bt_ctf_clock_class *clock_class,
303 int64_t *offset_s)
304 {
305 int ret = 0;
306
307 if (!clock_class || !offset_s) {
308 BT_LOGW("Invalid parameter: clock class or offset pointer is NULL: "
309 "clock-class-addr=%p, name=\"%s\", offset-addr=%p",
310 clock_class, bt_ctf_clock_class_get_name(clock_class),
311 offset_s);
312 ret = -1;
313 goto end;
314 }
315
316 *offset_s = clock_class->offset_s;
317 end:
318 return ret;
319 }
320
321 BT_HIDDEN
322 int bt_ctf_clock_class_set_offset_s(struct bt_ctf_clock_class *clock_class,
323 int64_t offset_s)
324 {
325 int ret = 0;
326
327 if (!clock_class) {
328 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
329 ret = -1;
330 goto end;
331 }
332
333 if (clock_class->frozen) {
334 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
335 clock_class, bt_ctf_clock_class_get_name(clock_class));
336 ret = -1;
337 goto end;
338 }
339
340 clock_class->offset_s = offset_s;
341 BT_LOGT("Set clock class's offset (seconds): "
342 "addr=%p, name=\"%s\", offset-s=%" PRId64,
343 clock_class, bt_ctf_clock_class_get_name(clock_class),
344 offset_s);
345 end:
346 return ret;
347 }
348
349 BT_HIDDEN
350 int bt_ctf_clock_class_get_offset_cycles(struct bt_ctf_clock_class *clock_class,
351 int64_t *offset)
352 {
353 int ret = 0;
354
355 if (!clock_class || !offset) {
356 BT_LOGW("Invalid parameter: clock class or offset pointer is NULL: "
357 "clock-class-addr=%p, name=\"%s\", offset-addr=%p",
358 clock_class, bt_ctf_clock_class_get_name(clock_class),
359 offset);
360 ret = -1;
361 goto end;
362 }
363
364 *offset = clock_class->offset;
365 end:
366 return ret;
367 }
368
369 BT_HIDDEN
370 int bt_ctf_clock_class_set_offset_cycles(struct bt_ctf_clock_class *clock_class,
371 int64_t offset)
372 {
373 int ret = 0;
374
375 if (!clock_class) {
376 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
377 ret = -1;
378 goto end;
379 }
380
381 if (clock_class->frozen) {
382 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
383 clock_class, bt_ctf_clock_class_get_name(clock_class));
384 ret = -1;
385 goto end;
386 }
387
388 clock_class->offset = offset;
389 BT_LOGT("Set clock class's offset (cycles): addr=%p, name=\"%s\", offset-cycles=%" PRId64,
390 clock_class, bt_ctf_clock_class_get_name(clock_class), offset);
391 end:
392 return ret;
393 }
394
395 BT_HIDDEN
396 bt_ctf_bool bt_ctf_clock_class_is_absolute(struct bt_ctf_clock_class *clock_class)
397 {
398 int ret = -1;
399
400 if (!clock_class) {
401 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
402 goto end;
403 }
404
405 ret = clock_class->absolute;
406 end:
407 return ret;
408 }
409
410 BT_HIDDEN
411 int bt_ctf_clock_class_set_is_absolute(struct bt_ctf_clock_class *clock_class,
412 bt_ctf_bool is_absolute)
413 {
414 int ret = 0;
415
416 if (!clock_class) {
417 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
418 ret = -1;
419 goto end;
420 }
421
422 if (clock_class->frozen) {
423 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
424 clock_class, bt_ctf_clock_class_get_name(clock_class));
425 ret = -1;
426 goto end;
427 }
428
429 clock_class->absolute = !!is_absolute;
430 BT_LOGT("Set clock class's absolute flag: addr=%p, name=\"%s\", is-absolute=%d",
431 clock_class, bt_ctf_clock_class_get_name(clock_class),
432 is_absolute);
433 end:
434 return ret;
435 }
436
437 BT_HIDDEN
438 const uint8_t *bt_ctf_clock_class_get_uuid(
439 struct bt_ctf_clock_class *clock_class)
440 {
441 const uint8_t *ret;
442
443 if (!clock_class) {
444 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
445 ret = NULL;
446 goto end;
447 }
448
449 if (!clock_class->uuid_set) {
450 BT_LOGT("Clock class's UUID is not set: addr=%p, name=\"%s\"",
451 clock_class, bt_ctf_clock_class_get_name(clock_class));
452 ret = NULL;
453 goto end;
454 }
455
456 ret = clock_class->uuid;
457 end:
458 return ret;
459 }
460
461 BT_HIDDEN
462 int bt_ctf_clock_class_set_uuid(struct bt_ctf_clock_class *clock_class,
463 const uint8_t *uuid)
464 {
465 int ret = 0;
466
467 if (!clock_class || !uuid) {
468 BT_LOGW("Invalid parameter: clock class or UUID is NULL: "
469 "clock-class-addr=%p, name=\"%s\", uuid-addr=%p",
470 clock_class, bt_ctf_clock_class_get_name(clock_class),
471 uuid);
472 ret = -1;
473 goto end;
474 }
475
476 if (clock_class->frozen) {
477 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
478 clock_class, bt_ctf_clock_class_get_name(clock_class));
479 ret = -1;
480 goto end;
481 }
482
483 bt_uuid_copy(clock_class->uuid, uuid);
484 clock_class->uuid_set = 1;
485 BT_LOGT("Set clock class's UUID: addr=%p, name=\"%s\", uuid=\"" BT_UUID_FMT "\"",
486 clock_class, bt_ctf_clock_class_get_name(clock_class),
487 BT_UUID_FMT_VALUES(uuid));
488 end:
489 return ret;
490 }
491
492 BT_HIDDEN
493 void bt_ctf_clock_class_freeze(struct bt_ctf_clock_class *clock_class)
494 {
495 if (!clock_class || clock_class->frozen) {
496 return;
497 }
498
499 BT_LOGD("Freezing clock class: addr=%p, name=\"%s\"",
500 clock_class, bt_ctf_clock_class_get_name(clock_class));
501 clock_class->frozen = 1;
502 }
503
504 static
505 void bt_ctf_clock_class_destroy(struct bt_ctf_object *obj)
506 {
507 struct bt_ctf_clock_class *clock_class;
508
509 clock_class = container_of(obj, struct bt_ctf_clock_class, base);
510 BT_LOGD("Destroying clock class: addr=%p, name=\"%s\"",
511 obj, bt_ctf_clock_class_get_name(clock_class));
512
513 if (clock_class->name) {
514 g_string_free(clock_class->name, TRUE);
515 }
516
517 if (clock_class->description) {
518 g_string_free(clock_class->description, TRUE);
519 }
520
521 g_free(clock_class);
522 }
523
524 BT_HIDDEN
525 int bt_ctf_clock_class_compare(struct bt_ctf_clock_class *clock_class_a,
526 struct bt_ctf_clock_class *clock_class_b)
527 {
528 int ret = 1;
529 BT_ASSERT_DBG(clock_class_a);
530 BT_ASSERT_DBG(clock_class_b);
531
532 /* Name */
533 if (strcmp(clock_class_a->name->str, clock_class_b->name->str) != 0) {
534 BT_LOGT("Clock classes differ: different names: "
535 "cc-a-name=\"%s\", cc-b-name=\"%s\"",
536 clock_class_a->name->str,
537 clock_class_b->name->str);
538 goto end;
539 }
540
541 /* Description */
542 if (clock_class_a->description) {
543 if (!clock_class_b->description) {
544 BT_LOGT_STR("Clock classes differ: clock class A has a "
545 "description, but clock class B does not.");
546 goto end;
547 }
548
549 if (strcmp(clock_class_a->name->str, clock_class_b->name->str)
550 != 0) {
551 BT_LOGT("Clock classes differ: different descriptions: "
552 "cc-a-descr=\"%s\", cc-b-descr=\"%s\"",
553 clock_class_a->description->str,
554 clock_class_b->description->str);
555 goto end;
556 }
557 } else {
558 if (clock_class_b->description) {
559 BT_LOGT_STR("Clock classes differ: clock class A has "
560 "no description, but clock class B has one.");
561 goto end;
562 }
563 }
564
565 /* Frequency */
566 if (clock_class_a->frequency != clock_class_b->frequency) {
567 BT_LOGT("Clock classes differ: different frequencies: "
568 "cc-a-freq=%" PRIu64 ", cc-b-freq=%" PRIu64,
569 clock_class_a->frequency,
570 clock_class_b->frequency);
571 goto end;
572 }
573
574 /* Precision */
575 if (clock_class_a->precision != clock_class_b->precision) {
576 BT_LOGT("Clock classes differ: different precisions: "
577 "cc-a-freq=%" PRIu64 ", cc-b-freq=%" PRIu64,
578 clock_class_a->precision,
579 clock_class_b->precision);
580 goto end;
581 }
582
583 /* Offset (seconds) */
584 if (clock_class_a->offset_s != clock_class_b->offset_s) {
585 BT_LOGT("Clock classes differ: different offsets (seconds): "
586 "cc-a-offset-s=%" PRId64 ", cc-b-offset-s=%" PRId64,
587 clock_class_a->offset_s,
588 clock_class_b->offset_s);
589 goto end;
590 }
591
592 /* Offset (cycles) */
593 if (clock_class_a->offset != clock_class_b->offset) {
594 BT_LOGT("Clock classes differ: different offsets (cycles): "
595 "cc-a-offset-s=%" PRId64 ", cc-b-offset-s=%" PRId64,
596 clock_class_a->offset,
597 clock_class_b->offset);
598 goto end;
599 }
600
601 /* UUIDs */
602 if (clock_class_a->uuid_set) {
603 if (!clock_class_b->uuid_set) {
604 BT_LOGT_STR("Clock classes differ: clock class A has a "
605 "UUID, but clock class B does not.");
606 goto end;
607 }
608
609 if (bt_uuid_compare(clock_class_a->uuid, clock_class_b->uuid) != 0) {
610 BT_LOGT("Clock classes differ: different UUIDs: "
611 "cc-a-uuid=\"" BT_UUID_FMT "\", "
612 "cc-b-uuid=\"" BT_UUID_FMT "\"",
613 BT_UUID_FMT_VALUES(clock_class_a->uuid),
614 BT_UUID_FMT_VALUES(clock_class_b->uuid));
615 goto end;
616 }
617 } else {
618 if (clock_class_b->uuid_set) {
619 BT_LOGT_STR("Clock classes differ: clock class A has "
620 "no UUID, but clock class B has one.");
621 goto end;
622 }
623 }
624
625 /* Absolute */
626 if (!!clock_class_a->absolute != !!clock_class_b->absolute) {
627 BT_LOGT("Clock classes differ: one is absolute, the other "
628 "is not: cc-a-is-absolute=%d, cc-b-is-absolute=%d",
629 !!clock_class_a->absolute,
630 !!clock_class_b->absolute);
631 goto end;
632 }
633
634 /* Equal */
635 ret = 0;
636
637 end:
638 return ret;
639 }
This page took 0.042064 seconds and 4 git commands to generate.