4 * Babeltrace CTF writer - Clock class
6 * Copyright 2013, 2014 Jérémie Galarneau <jeremie.galarneau@efficios.com>
8 * Author: Jérémie Galarneau <jeremie.galarneau@efficios.com>
10 * Permission is hereby granted, free of charge, to any person obtaining a copy
11 * of this software and associated documentation files (the "Software"), to deal
12 * in the Software without restriction, including without limitation the rights
13 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14 * copies of the Software, and to permit persons to whom the Software is
15 * furnished to do so, subject to the following conditions:
17 * The above copyright notice and this permission notice shall be included in
18 * all copies or substantial portions of the Software.
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
21 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
23 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
24 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
29 #define BT_LOG_TAG "CTF-WRITER/CLOCK-CLASS"
32 #include "common/uuid.h"
33 #include <babeltrace2/ctf-writer/utils.h>
34 #include <babeltrace2/ctf-writer/object.h>
35 #include "compat/compiler.h"
36 #include <babeltrace2/types.h>
37 #include "compat/string.h"
39 #include "common/assert.h"
41 #include "assert-pre.h"
42 #include "clock-class.h"
46 void bt_ctf_clock_class_destroy(struct bt_ctf_object
*obj
);
49 bt_bool
bt_ctf_clock_class_is_valid(struct bt_ctf_clock_class
*clock_class
)
51 return clock_class
&& clock_class
->name
;
55 int bt_ctf_clock_class_set_name(struct bt_ctf_clock_class
*clock_class
,
61 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
66 if (clock_class
->frozen
) {
67 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
68 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
73 if (!bt_ctf_identifier_is_valid(name
)) {
74 BT_LOGW("Clock class's name is not a valid CTF identifier: "
75 "addr=%p, name=\"%s\"",
81 if (clock_class
->name
) {
82 g_string_assign(clock_class
->name
, name
);
84 clock_class
->name
= g_string_new(name
);
85 if (!clock_class
->name
) {
86 BT_LOGE_STR("Failed to allocate a GString.");
92 BT_LOGT("Set clock class's name: addr=%p, name=\"%s\"",
100 bool validate_freq(struct bt_ctf_clock_class
*clock_class
,
101 const char *name
, uint64_t freq
)
103 bool is_valid
= true;
105 if (freq
== -1ULL || freq
== 0) {
106 BT_LOGW("Invalid parameter: frequency is invalid: "
107 "addr=%p, name=\"%s\", freq=%" PRIu64
,
108 clock_class
, name
, freq
);
118 struct bt_ctf_clock_class
*bt_ctf_clock_class_create(const char *name
,
122 struct bt_ctf_clock_class
*clock_class
= NULL
;
124 BT_LOGD("Creating default clock class object: name=\"%s\"",
127 if (!validate_freq(NULL
, name
, freq
)) {
128 /* validate_freq() logs errors */
132 clock_class
= g_new0(struct bt_ctf_clock_class
, 1);
134 BT_LOGE_STR("Failed to allocate one clock class.");
138 clock_class
->precision
= 1;
139 clock_class
->frequency
= freq
;
140 bt_ctf_object_init_shared(&clock_class
->base
, bt_ctf_clock_class_destroy
);
143 ret
= bt_ctf_clock_class_set_name(clock_class
, name
);
145 /* bt_ctf_clock_class_set_name() logs errors */
150 BT_LOGD("Created clock class object: addr=%p, name=\"%s\"",
154 BT_CTF_OBJECT_PUT_REF_AND_RESET(clock_class
);
159 const char *bt_ctf_clock_class_get_name(struct bt_ctf_clock_class
*clock_class
)
161 const char *ret
= NULL
;
164 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
168 if (clock_class
->name
) {
169 ret
= clock_class
->name
->str
;
177 const char *bt_ctf_clock_class_get_description(
178 struct bt_ctf_clock_class
*clock_class
)
180 const char *ret
= NULL
;
183 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
187 if (clock_class
->description
) {
188 ret
= clock_class
->description
->str
;
195 int bt_ctf_clock_class_set_description(struct bt_ctf_clock_class
*clock_class
,
200 if (!clock_class
|| !desc
) {
201 BT_LOGW("Invalid parameter: clock class or description is NULL: "
202 "clock-class-addr=%p, name=\"%s\", desc-addr=%p",
203 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
209 if (clock_class
->frozen
) {
210 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
211 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
216 clock_class
->description
= g_string_new(desc
);
217 ret
= clock_class
->description
? 0 : -1;
218 BT_LOGT("Set clock class's description: addr=%p, "
219 "name=\"%s\", desc=\"%s\"",
220 clock_class
, bt_ctf_clock_class_get_name(clock_class
), desc
);
226 uint64_t bt_ctf_clock_class_get_frequency(
227 struct bt_ctf_clock_class
*clock_class
)
229 uint64_t ret
= -1ULL;
232 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
236 ret
= clock_class
->frequency
;
242 int bt_ctf_clock_class_set_frequency(struct bt_ctf_clock_class
*clock_class
,
248 BT_LOGW("Invalid parameter: clock class is NULL or frequency is invalid: "
249 "addr=%p, name=\"%s\"",
250 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
255 if (!validate_freq(clock_class
, bt_ctf_clock_class_get_name(clock_class
),
257 /* validate_freq() logs errors */
261 if (clock_class
->frozen
) {
262 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
263 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
268 clock_class
->frequency
= freq
;
269 BT_LOGT("Set clock class's frequency: addr=%p, name=\"%s\", freq=%" PRIu64
,
270 clock_class
, bt_ctf_clock_class_get_name(clock_class
), freq
);
276 uint64_t bt_ctf_clock_class_get_precision(struct bt_ctf_clock_class
*clock_class
)
278 uint64_t ret
= -1ULL;
281 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
285 ret
= clock_class
->precision
;
291 int bt_ctf_clock_class_set_precision(struct bt_ctf_clock_class
*clock_class
,
296 if (!clock_class
|| precision
== -1ULL) {
297 BT_LOGW("Invalid parameter: clock class is NULL or precision is invalid: "
298 "addr=%p, name=\"%s\", precision=%" PRIu64
,
299 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
305 if (clock_class
->frozen
) {
306 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
307 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
312 clock_class
->precision
= precision
;
313 BT_LOGT("Set clock class's precision: addr=%p, name=\"%s\", precision=%" PRIu64
,
314 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
321 int bt_ctf_clock_class_get_offset_s(struct bt_ctf_clock_class
*clock_class
,
326 if (!clock_class
|| !offset_s
) {
327 BT_LOGW("Invalid parameter: clock class or offset pointer is NULL: "
328 "clock-class-addr=%p, name=\"%s\", offset-addr=%p",
329 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
335 *offset_s
= clock_class
->offset_s
;
341 int bt_ctf_clock_class_set_offset_s(struct bt_ctf_clock_class
*clock_class
,
347 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
352 if (clock_class
->frozen
) {
353 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
354 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
359 clock_class
->offset_s
= offset_s
;
360 BT_LOGT("Set clock class's offset (seconds): "
361 "addr=%p, name=\"%s\", offset-s=%" PRId64
,
362 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
369 int bt_ctf_clock_class_get_offset_cycles(struct bt_ctf_clock_class
*clock_class
,
374 if (!clock_class
|| !offset
) {
375 BT_LOGW("Invalid parameter: clock class or offset pointer is NULL: "
376 "clock-class-addr=%p, name=\"%s\", offset-addr=%p",
377 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
383 *offset
= clock_class
->offset
;
389 int bt_ctf_clock_class_set_offset_cycles(struct bt_ctf_clock_class
*clock_class
,
395 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
400 if (clock_class
->frozen
) {
401 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
402 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
407 clock_class
->offset
= offset
;
408 BT_LOGT("Set clock class's offset (cycles): addr=%p, name=\"%s\", offset-cycles=%" PRId64
,
409 clock_class
, bt_ctf_clock_class_get_name(clock_class
), offset
);
415 bt_bool
bt_ctf_clock_class_is_absolute(struct bt_ctf_clock_class
*clock_class
)
420 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
424 ret
= clock_class
->absolute
;
430 int bt_ctf_clock_class_set_is_absolute(struct bt_ctf_clock_class
*clock_class
,
436 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
441 if (clock_class
->frozen
) {
442 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
443 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
448 clock_class
->absolute
= !!is_absolute
;
449 BT_LOGT("Set clock class's absolute flag: addr=%p, name=\"%s\", is-absolute=%d",
450 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
457 const uint8_t *bt_ctf_clock_class_get_uuid(
458 struct bt_ctf_clock_class
*clock_class
)
463 BT_LOGW_STR("Invalid parameter: clock class is NULL.");
468 if (!clock_class
->uuid_set
) {
469 BT_LOGT("Clock class's UUID is not set: addr=%p, name=\"%s\"",
470 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
475 ret
= clock_class
->uuid
;
481 int bt_ctf_clock_class_set_uuid(struct bt_ctf_clock_class
*clock_class
,
486 if (!clock_class
|| !uuid
) {
487 BT_LOGW("Invalid parameter: clock class or UUID is NULL: "
488 "clock-class-addr=%p, name=\"%s\", uuid-addr=%p",
489 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
495 if (clock_class
->frozen
) {
496 BT_LOGW("Invalid parameter: clock class is frozen: addr=%p, name=\"%s\"",
497 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
502 bt_uuid_copy(clock_class
->uuid
, uuid
);
503 clock_class
->uuid_set
= 1;
504 BT_LOGT("Set clock class's UUID: addr=%p, name=\"%s\", uuid=\"" BT_UUID_FMT
"\"",
505 clock_class
, bt_ctf_clock_class_get_name(clock_class
),
506 BT_UUID_FMT_VALUES(uuid
));
512 void bt_ctf_clock_class_freeze(struct bt_ctf_clock_class
*clock_class
)
514 if (!clock_class
|| clock_class
->frozen
) {
518 BT_LOGD("Freezing clock class: addr=%p, name=\"%s\"",
519 clock_class
, bt_ctf_clock_class_get_name(clock_class
));
520 clock_class
->frozen
= 1;
524 void bt_ctf_clock_class_destroy(struct bt_ctf_object
*obj
)
526 struct bt_ctf_clock_class
*clock_class
;
528 clock_class
= container_of(obj
, struct bt_ctf_clock_class
, base
);
529 BT_LOGD("Destroying clock class: addr=%p, name=\"%s\"",
530 obj
, bt_ctf_clock_class_get_name(clock_class
));
532 if (clock_class
->name
) {
533 g_string_free(clock_class
->name
, TRUE
);
536 if (clock_class
->description
) {
537 g_string_free(clock_class
->description
, TRUE
);
544 int bt_ctf_clock_class_compare(struct bt_ctf_clock_class
*clock_class_a
,
545 struct bt_ctf_clock_class
*clock_class_b
)
548 BT_ASSERT(clock_class_a
);
549 BT_ASSERT(clock_class_b
);
552 if (strcmp(clock_class_a
->name
->str
, clock_class_b
->name
->str
) != 0) {
553 BT_LOGT("Clock classes differ: different names: "
554 "cc-a-name=\"%s\", cc-b-name=\"%s\"",
555 clock_class_a
->name
->str
,
556 clock_class_b
->name
->str
);
561 if (clock_class_a
->description
) {
562 if (!clock_class_b
->description
) {
563 BT_LOGT_STR("Clock classes differ: clock class A has a "
564 "description, but clock class B does not.");
568 if (strcmp(clock_class_a
->name
->str
, clock_class_b
->name
->str
)
570 BT_LOGT("Clock classes differ: different descriptions: "
571 "cc-a-descr=\"%s\", cc-b-descr=\"%s\"",
572 clock_class_a
->description
->str
,
573 clock_class_b
->description
->str
);
577 if (clock_class_b
->description
) {
578 BT_LOGT_STR("Clock classes differ: clock class A has "
579 "no description, but clock class B has one.");
585 if (clock_class_a
->frequency
!= clock_class_b
->frequency
) {
586 BT_LOGT("Clock classes differ: different frequencies: "
587 "cc-a-freq=%" PRIu64
", cc-b-freq=%" PRIu64
,
588 clock_class_a
->frequency
,
589 clock_class_b
->frequency
);
594 if (clock_class_a
->precision
!= clock_class_b
->precision
) {
595 BT_LOGT("Clock classes differ: different precisions: "
596 "cc-a-freq=%" PRIu64
", cc-b-freq=%" PRIu64
,
597 clock_class_a
->precision
,
598 clock_class_b
->precision
);
602 /* Offset (seconds) */
603 if (clock_class_a
->offset_s
!= clock_class_b
->offset_s
) {
604 BT_LOGT("Clock classes differ: different offsets (seconds): "
605 "cc-a-offset-s=%" PRId64
", cc-b-offset-s=%" PRId64
,
606 clock_class_a
->offset_s
,
607 clock_class_b
->offset_s
);
611 /* Offset (cycles) */
612 if (clock_class_a
->offset
!= clock_class_b
->offset
) {
613 BT_LOGT("Clock classes differ: different offsets (cycles): "
614 "cc-a-offset-s=%" PRId64
", cc-b-offset-s=%" PRId64
,
615 clock_class_a
->offset
,
616 clock_class_b
->offset
);
621 if (clock_class_a
->uuid_set
) {
622 if (!clock_class_b
->uuid_set
) {
623 BT_LOGT_STR("Clock classes differ: clock class A has a "
624 "UUID, but clock class B does not.");
628 if (bt_uuid_compare(clock_class_a
->uuid
, clock_class_b
->uuid
) != 0) {
629 BT_LOGT("Clock classes differ: different UUIDs: "
630 "cc-a-uuid=\"" BT_UUID_FMT
"\", "
631 "cc-b-uuid=\"" BT_UUID_FMT
"\"",
632 BT_UUID_FMT_VALUES(clock_class_a
->uuid
),
633 BT_UUID_FMT_VALUES(clock_class_b
->uuid
));
637 if (clock_class_b
->uuid_set
) {
638 BT_LOGT_STR("Clock classes differ: clock class A has "
639 "no UUID, but clock class B has one.");
645 if (!!clock_class_a
->absolute
!= !!clock_class_b
->absolute
) {
646 BT_LOGT("Clock classes differ: one is absolute, the other "
647 "is not: cc-a-is-absolute=%d, cc-b-is-absolute=%d",
648 !!clock_class_a
->absolute
,
649 !!clock_class_b
->absolute
);