lib: make trace IR API const-correct
[babeltrace.git] / plugins / libctfcopytrace / ctfcopytrace.c
CommitLineData
91b73004
JD
1/*
2 * copytrace.c
3 *
4 * Babeltrace library to create a copy of a CTF trace
5 *
6 * Copyright 2017 Julien Desfossez <jdesfossez@efficios.com>
7 *
8 * Author: Julien Desfossez <jdesfossez@efficios.com>
9 *
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:
16 *
17 * The above copyright notice and this permission notice shall be included in
18 * all copies or substantial portions of the Software.
19 *
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
26 * SOFTWARE.
27 */
28
3e4f69d3
JD
29#define BT_LOG_TAG "PLUGIN-CTFCOPYTRACE-LIB"
30#include "logging.h"
31
9d408fca 32#include <babeltrace/babeltrace.h>
f6ccaed9 33#include <babeltrace/assert-internal.h>
91b73004
JD
34
35#include "ctfcopytrace.h"
b2f1f465 36#include "clock-fields.h"
91b73004 37
9ac68eb1 38BT_HIDDEN
40f4ba76
PP
39const struct bt_clock_class *ctf_copy_clock_class(FILE *err,
40 const struct bt_clock_class *clock_class)
91b73004
JD
41{
42 int64_t offset, offset_s;
43 int int_ret;
44 uint64_t u64_ret;
45 const char *name, *description;
40f4ba76 46 const struct bt_clock_class *writer_clock_class = NULL;
91b73004 47
f6ccaed9 48 BT_ASSERT(err && clock_class);
91b73004 49
50842bdc 50 name = bt_clock_class_get_name(clock_class);
f6ccaed9 51 BT_ASSERT(name);
91b73004 52
50842bdc
PP
53 writer_clock_class = bt_clock_class_create(name,
54 bt_clock_class_get_frequency(clock_class));
91b73004 55 if (!writer_clock_class) {
3e4f69d3 56 BT_LOGE_STR("Failed to create clock class.");
91b73004
JD
57 goto end;
58 }
59
50842bdc 60 description = bt_clock_class_get_description(clock_class);
16cd0c80 61 if (description) {
50842bdc 62 int_ret = bt_clock_class_set_description(writer_clock_class,
16cd0c80 63 description);
f6ccaed9 64 BT_ASSERT(!int_ret);
91b73004
JD
65 }
66
50842bdc 67 u64_ret = bt_clock_class_get_precision(clock_class);
f6ccaed9 68 BT_ASSERT(u64_ret != -1ULL);
3e4f69d3 69
50842bdc 70 int_ret = bt_clock_class_set_precision(writer_clock_class,
91b73004 71 u64_ret);
f6ccaed9 72 BT_ASSERT(!int_ret);
91b73004 73
50842bdc 74 int_ret = bt_clock_class_get_offset_s(clock_class, &offset_s);
f6ccaed9 75 BT_ASSERT(!int_ret);
91b73004 76
50842bdc 77 int_ret = bt_clock_class_set_offset_s(writer_clock_class, offset_s);
f6ccaed9 78 BT_ASSERT(!int_ret);
91b73004 79
50842bdc 80 int_ret = bt_clock_class_get_offset_cycles(clock_class, &offset);
f6ccaed9 81 BT_ASSERT(!int_ret);
91b73004 82
50842bdc 83 int_ret = bt_clock_class_set_offset_cycles(writer_clock_class, offset);
f6ccaed9 84 BT_ASSERT(!int_ret);
91b73004 85
50842bdc 86 int_ret = bt_clock_class_is_absolute(clock_class);
f6ccaed9 87 BT_ASSERT(int_ret >= 0);
91b73004 88
50842bdc 89 int_ret = bt_clock_class_set_is_absolute(writer_clock_class, int_ret);
f6ccaed9 90 BT_ASSERT(!int_ret);
91b73004 91
91b73004
JD
92end:
93 return writer_clock_class;
94}
95
9ac68eb1 96BT_HIDDEN
91b73004 97enum bt_component_status ctf_copy_clock_classes(FILE *err,
40f4ba76
PP
98 const struct bt_trace *writer_trace,
99 const struct bt_stream_class *writer_stream_class,
100 const struct bt_trace *trace)
91b73004
JD
101{
102 enum bt_component_status ret;
91b73004
JD
103 int int_ret, clock_class_count, i;
104
50842bdc 105 clock_class_count = bt_trace_get_clock_class_count(trace);
91b73004
JD
106
107 for (i = 0; i < clock_class_count; i++) {
40f4ba76
PP
108 const struct bt_clock_class *writer_clock_class;
109 const struct bt_clock_class *clock_class =
50842bdc 110 bt_trace_get_clock_class_by_index(trace, i);
91b73004 111
f6ccaed9 112 BT_ASSERT(clock_class);
91b73004
JD
113
114 writer_clock_class = ctf_copy_clock_class(err, clock_class);
65300d60 115 bt_object_put_ref(clock_class);
91b73004 116 if (!writer_clock_class) {
3e4f69d3 117 BT_LOGE_STR("Failed to copy clock class.");
91b73004
JD
118 ret = BT_COMPONENT_STATUS_ERROR;
119 goto end;
120 }
121
50842bdc 122 int_ret = bt_trace_add_clock_class(writer_trace, writer_clock_class);
91b73004 123 if (int_ret != 0) {
65300d60 124 BT_OBJECT_PUT_REF_AND_RESET(writer_clock_class);
3e4f69d3 125 BT_LOGE_STR("Failed to add clock class.");
91b73004
JD
126 ret = BT_COMPONENT_STATUS_ERROR;
127 goto end;
128 }
129
130 /*
b2f1f465 131 * Ownership transferred to the trace.
91b73004 132 */
65300d60 133 bt_object_put_ref(writer_clock_class);
91b73004
JD
134 }
135
136 ret = BT_COMPONENT_STATUS_OK;
137
138end:
139 return ret;
140}
141
4a2fffdb 142static
40f4ba76 143void replace_clock_classes(const struct bt_trace *trace_copy,
4a2fffdb
PP
144 struct bt_field_type *field_type)
145{
146 int ret;
147
f6ccaed9
PP
148 BT_ASSERT(trace_copy);
149 BT_ASSERT(field_type);
4a2fffdb
PP
150
151 switch (bt_field_type_get_type_id(field_type)) {
152 case BT_FIELD_TYPE_ID_INTEGER:
153 {
40f4ba76 154 const struct bt_clock_class *mapped_clock_class =
4a2fffdb 155 bt_field_type_integer_get_mapped_clock_class(field_type);
40f4ba76 156 const struct bt_clock_class *clock_class_copy = NULL;
4a2fffdb
PP
157 const char *name;
158
159 if (!mapped_clock_class) {
160 break;
161 }
162
163 name = bt_clock_class_get_name(mapped_clock_class);
f6ccaed9 164 BT_ASSERT(name);
4a2fffdb
PP
165 clock_class_copy = bt_trace_get_clock_class_by_name(
166 trace_copy, name);
f6ccaed9 167 BT_ASSERT(clock_class_copy);
4a2fffdb
PP
168 ret = bt_field_type_integer_set_mapped_clock_class(
169 field_type, clock_class_copy);
f6ccaed9 170 BT_ASSERT(ret == 0);
65300d60
PP
171 bt_object_put_ref(mapped_clock_class);
172 bt_object_put_ref(clock_class_copy);
4a2fffdb
PP
173 break;
174 }
175 case BT_FIELD_TYPE_ID_ENUM:
176 case BT_FIELD_TYPE_ID_ARRAY:
177 case BT_FIELD_TYPE_ID_SEQUENCE:
178 {
179 struct bt_field_type *subtype = NULL;
180
181 switch (bt_field_type_get_type_id(field_type)) {
182 case BT_FIELD_TYPE_ID_ENUM:
183 subtype = bt_field_type_enumeration_get_container_type(
184 field_type);
185 break;
186 case BT_FIELD_TYPE_ID_ARRAY:
187 subtype = bt_field_type_array_get_element_type(
188 field_type);
189 break;
190 case BT_FIELD_TYPE_ID_SEQUENCE:
191 subtype = bt_field_type_sequence_get_element_type(
192 field_type);
193 break;
194 default:
195 BT_LOGF("Unexpected field type ID: id=%d",
196 bt_field_type_get_type_id(field_type));
197 abort();
198 }
199
f6ccaed9 200 BT_ASSERT(subtype);
4a2fffdb 201 replace_clock_classes(trace_copy, subtype);
65300d60 202 bt_object_put_ref(subtype);
4a2fffdb
PP
203 break;
204 }
205 case BT_FIELD_TYPE_ID_STRUCT:
206 {
207 uint64_t i;
208 int64_t count = bt_field_type_structure_get_field_count(
209 field_type);
210
211 for (i = 0; i < count; i++) {
212 const char *name;
213 struct bt_field_type *member_type;
214
215 ret = bt_field_type_structure_get_field_by_index(
216 field_type, &name, &member_type, i);
f6ccaed9 217 BT_ASSERT(ret == 0);
4a2fffdb 218 replace_clock_classes(trace_copy, member_type);
65300d60 219 bt_object_put_ref(member_type);
4a2fffdb
PP
220 }
221
222 break;
223 }
224 case BT_FIELD_TYPE_ID_VARIANT:
225 {
226 uint64_t i;
227 int64_t count = bt_field_type_variant_get_field_count(
228 field_type);
229
230 for (i = 0; i < count; i++) {
231 const char *name;
232 struct bt_field_type *member_type;
233
234 ret = bt_field_type_variant_get_field_by_index(
235 field_type, &name, &member_type, i);
f6ccaed9 236 BT_ASSERT(ret == 0);
4a2fffdb 237 replace_clock_classes(trace_copy, member_type);
65300d60 238 bt_object_put_ref(member_type);
4a2fffdb
PP
239 }
240
241 break;
242 }
243 default:
244 break;
245 }
246}
247
9ac68eb1 248BT_HIDDEN
40f4ba76
PP
249const struct bt_event_class *ctf_copy_event_class(FILE *err,
250 const struct bt_trace *trace_copy,
251 const struct bt_event_class *event_class)
91b73004 252{
40f4ba76 253 const struct bt_event_class *writer_event_class = NULL;
4a2fffdb 254 struct bt_field_type *context = NULL, *payload_type = NULL;
91b73004 255 const char *name;
cf76ce92
PP
256 int ret;
257 int64_t id;
50842bdc 258 enum bt_event_class_log_level log_level;
cf76ce92 259 const char *emf_uri;
91b73004 260
50842bdc 261 name = bt_event_class_get_name(event_class);
91b73004 262
40f4ba76 263 writer_event_class = bt_event_class_create(name);
f6ccaed9 264 BT_ASSERT(writer_event_class);
91b73004 265
50842bdc 266 id = bt_event_class_get_id(event_class);
f6ccaed9 267 BT_ASSERT(id >= 0);
91b73004 268
50842bdc 269 ret = bt_event_class_set_id(writer_event_class, id);
cf76ce92 270 if (ret) {
3e4f69d3 271 BT_LOGE_STR("Failed to set event_class id.");
cf76ce92
PP
272 goto error;
273 }
91b73004 274
50842bdc 275 log_level = bt_event_class_get_log_level(event_class);
cf76ce92 276 if (log_level < 0) {
3e4f69d3 277 BT_LOGE_STR("Failed to get log_level.");
cf76ce92
PP
278 goto error;
279 }
280
40f4ba76 281 ret = bt_event_class_set_log_level(writer_event_class, log_level);
cf76ce92 282 if (ret) {
3e4f69d3 283 BT_LOGE_STR("Failed to set log_level.");
cf76ce92
PP
284 goto error;
285 }
286
50842bdc 287 emf_uri = bt_event_class_get_emf_uri(event_class);
cf76ce92 288 if (emf_uri) {
40f4ba76 289 ret = bt_event_class_set_emf_uri(writer_event_class,
cf76ce92
PP
290 emf_uri);
291 if (ret) {
3e4f69d3 292 BT_LOGE_STR("Failed to set emf uri.");
9ae49d3d 293 goto error;
91b73004
JD
294 }
295 }
296
50842bdc 297 payload_type = bt_event_class_get_payload_type(event_class);
f87fb9b4 298 if (payload_type) {
4a2fffdb
PP
299 struct bt_field_type *ft_copy =
300 bt_field_type_copy(payload_type);
301
302 if (!ft_copy) {
303 BT_LOGE_STR("Cannot copy payload field type.");
304 }
305
306 replace_clock_classes(trace_copy, ft_copy);
50842bdc 307 ret = bt_event_class_set_payload_type(writer_event_class,
4a2fffdb 308 ft_copy);
65300d60 309 bt_object_put_ref(ft_copy);
91b73004 310 if (ret < 0) {
3e4f69d3 311 BT_LOGE_STR("Failed to set payload type.");
9ae49d3d 312 goto error;
91b73004 313 }
91b73004
JD
314 }
315
50842bdc 316 context = bt_event_class_get_context_type(event_class);
279c77d0 317 if (context) {
4a2fffdb
PP
318 struct bt_field_type *ft_copy =
319 bt_field_type_copy(context);
320
321 if (!ft_copy) {
322 BT_LOGE_STR("Cannot copy context field type.");
323 }
324
50842bdc 325 ret = bt_event_class_set_context_type(
4a2fffdb 326 writer_event_class, ft_copy);
65300d60 327 bt_object_put_ref(ft_copy);
279c77d0 328 if (ret < 0) {
3e4f69d3 329 BT_LOGE_STR("Failed to set context type.");
279c77d0
JD
330 goto error;
331 }
332 }
333
9ae49d3d
JD
334 goto end;
335
336error:
65300d60 337 BT_OBJECT_PUT_REF_AND_RESET(writer_event_class);
91b73004 338end:
65300d60
PP
339 BT_OBJECT_PUT_REF_AND_RESET(context);
340 BT_OBJECT_PUT_REF_AND_RESET(payload_type);
91b73004
JD
341 return writer_event_class;
342}
343
9ac68eb1 344BT_HIDDEN
91b73004 345enum bt_component_status ctf_copy_event_classes(FILE *err,
40f4ba76
PP
346 const struct bt_stream_class *stream_class,
347 const struct bt_stream_class *writer_stream_class)
91b73004
JD
348{
349 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
40f4ba76 350 const struct bt_event_class *event_class = NULL, *writer_event_class = NULL;
91b73004 351 int count, i;
40f4ba76 352 const struct bt_trace *writer_trace =
4a2fffdb 353 bt_stream_class_get_trace(writer_stream_class);
91b73004 354
f6ccaed9 355 BT_ASSERT(writer_trace);
50842bdc 356 count = bt_stream_class_get_event_class_count(stream_class);
f6ccaed9 357 BT_ASSERT(count >= 0);
91b73004
JD
358
359 for (i = 0; i < count; i++) {
91b73004
JD
360 int int_ret;
361
50842bdc 362 event_class = bt_stream_class_get_event_class_by_index(
91b73004 363 stream_class, i);
f6ccaed9 364 BT_ASSERT(event_class);
3e4f69d3 365
50842bdc
PP
366 if (i < bt_stream_class_get_event_class_count(writer_stream_class)) {
367 writer_event_class = bt_stream_class_get_event_class_by_index(
cb0a5cf8
JD
368 writer_stream_class, i);
369 if (writer_event_class) {
370 /*
371 * If the writer_event_class already exists,
372 * just skip it. It can be used to resync the
373 * event_classes after a trace has become
374 * static.
375 */
65300d60
PP
376 BT_OBJECT_PUT_REF_AND_RESET(writer_event_class);
377 BT_OBJECT_PUT_REF_AND_RESET(event_class);
cb0a5cf8
JD
378 continue;
379 }
380 }
381
4a2fffdb
PP
382 writer_event_class = ctf_copy_event_class(err, writer_trace,
383 event_class);
91b73004 384 if (!writer_event_class) {
3e4f69d3 385 BT_LOGE_STR("Failed to copy event_class.");
91b73004 386 ret = BT_COMPONENT_STATUS_ERROR;
9ae49d3d 387 goto error;
91b73004
JD
388 }
389
50842bdc 390 int_ret = bt_stream_class_add_event_class(writer_stream_class,
91b73004
JD
391 writer_event_class);
392 if (int_ret < 0) {
3e4f69d3 393 BT_LOGE_STR("Failed to add event class.");
91b73004 394 ret = BT_COMPONENT_STATUS_ERROR;
9ae49d3d 395 goto error;
91b73004 396 }
65300d60
PP
397 BT_OBJECT_PUT_REF_AND_RESET(writer_event_class);
398 BT_OBJECT_PUT_REF_AND_RESET(event_class);
91b73004
JD
399 }
400
9ae49d3d
JD
401 goto end;
402
403error:
65300d60
PP
404 bt_object_put_ref(event_class);
405 bt_object_put_ref(writer_event_class);
91b73004 406end:
65300d60 407 bt_object_put_ref(writer_trace);
91b73004
JD
408 return ret;
409}
410
9ac68eb1 411BT_HIDDEN
40f4ba76
PP
412const struct bt_stream_class *ctf_copy_stream_class(FILE *err,
413 const struct bt_stream_class *stream_class,
414 const struct bt_trace *writer_trace,
b2f1f465 415 bool override_ts64)
91b73004 416{
50842bdc 417 struct bt_field_type *type = NULL;
4a2fffdb 418 struct bt_field_type *type_copy = NULL;
40f4ba76 419 const struct bt_stream_class *writer_stream_class = NULL;
91b73004 420 int ret_int;
50842bdc 421 const char *name = bt_stream_class_get_name(stream_class);
91b73004 422
50842bdc 423 writer_stream_class = bt_stream_class_create_empty(name);
f6ccaed9 424 BT_ASSERT(writer_stream_class);
91b73004 425
50842bdc 426 type = bt_stream_class_get_packet_context_type(stream_class);
cfb74f3d 427 if (type) {
4a2fffdb
PP
428 type_copy = bt_field_type_copy(type);
429 if (!type_copy) {
430 BT_LOGE_STR("Cannot copy packet context field type.");
431 }
432
433 replace_clock_classes(writer_trace, type_copy);
50842bdc 434 ret_int = bt_stream_class_set_packet_context_type(
4a2fffdb 435 writer_stream_class, type_copy);
65300d60 436 BT_OBJECT_PUT_REF_AND_RESET(type_copy);
cfb74f3d 437 if (ret_int < 0) {
3e4f69d3 438 BT_LOGE_STR("Failed to set packet_context type.");
cfb74f3d
JD
439 goto error;
440 }
65300d60 441 BT_OBJECT_PUT_REF_AND_RESET(type);
91b73004
JD
442 }
443
50842bdc 444 type = bt_stream_class_get_event_header_type(stream_class);
06b019a7 445 if (type) {
4a2fffdb
PP
446 type_copy = bt_field_type_copy(type);
447 if (!type_copy) {
448 BT_LOGE_STR("Cannot copy event header field type.");
449 }
450
50842bdc 451 ret_int = bt_trace_get_clock_class_count(writer_trace);
f6ccaed9 452 BT_ASSERT(ret_int >= 0);
d23979be 453 if (override_ts64 && ret_int > 0) {
50842bdc 454 struct bt_field_type *new_event_header_type;
06b019a7 455
4a2fffdb 456 new_event_header_type = override_header_type(err, type_copy,
06b019a7
JD
457 writer_trace);
458 if (!new_event_header_type) {
3e4f69d3 459 BT_LOGE_STR("Failed to override header type.");
06b019a7
JD
460 goto error;
461 }
4a2fffdb 462 replace_clock_classes(writer_trace, type_copy);
50842bdc 463 ret_int = bt_stream_class_set_event_header_type(
06b019a7 464 writer_stream_class, new_event_header_type);
65300d60
PP
465 BT_OBJECT_PUT_REF_AND_RESET(type_copy);
466 BT_OBJECT_PUT_REF_AND_RESET(new_event_header_type);
06b019a7 467 if (ret_int < 0) {
3e4f69d3 468 BT_LOGE_STR("Failed to set event_header type.");
06b019a7
JD
469 goto error;
470 }
471 } else {
4a2fffdb 472 replace_clock_classes(writer_trace, type_copy);
50842bdc 473 ret_int = bt_stream_class_set_event_header_type(
4a2fffdb 474 writer_stream_class, type_copy);
65300d60 475 BT_OBJECT_PUT_REF_AND_RESET(type_copy);
06b019a7 476 if (ret_int < 0) {
3e4f69d3 477 BT_LOGE_STR("Failed to set event_header type.");
06b019a7
JD
478 goto error;
479 }
0f29db56 480 }
65300d60 481 BT_OBJECT_PUT_REF_AND_RESET(type);
91b73004
JD
482 }
483
50842bdc 484 type = bt_stream_class_get_event_context_type(stream_class);
91b73004 485 if (type) {
4a2fffdb
PP
486 type_copy = bt_field_type_copy(type);
487 if (!type_copy) {
488 BT_LOGE_STR("Cannot copy event context field type.");
489 }
490
491 replace_clock_classes(writer_trace, type_copy);
50842bdc 492 ret_int = bt_stream_class_set_event_context_type(
4a2fffdb 493 writer_stream_class, type_copy);
65300d60 494 BT_OBJECT_PUT_REF_AND_RESET(type_copy);
91b73004 495 if (ret_int < 0) {
3e4f69d3 496 BT_LOGE_STR("Failed to set event_contexttype.");
91b73004
JD
497 goto error;
498 }
499 }
65300d60 500 BT_OBJECT_PUT_REF_AND_RESET(type);
91b73004
JD
501
502 goto end;
503
504error:
65300d60 505 BT_OBJECT_PUT_REF_AND_RESET(writer_stream_class);
91b73004 506end:
65300d60
PP
507 bt_object_put_ref(type);
508 bt_object_put_ref(type_copy);
91b73004
JD
509 return writer_stream_class;
510}
511
387483fc 512BT_HIDDEN
40f4ba76
PP
513int ctf_stream_copy_packet_header(FILE *err, const struct bt_packet *packet,
514 const struct bt_stream *writer_stream)
387483fc 515{
40f4ba76 516 const struct bt_field *packet_header = NULL, *writer_packet_header = NULL;
387483fc
JD
517 int ret = 0;
518
50842bdc 519 packet_header = bt_packet_get_header(packet);
387483fc
JD
520 if (!packet_header) {
521 goto end;
522 }
523
50842bdc 524 writer_packet_header = bt_field_copy(packet_header);
387483fc 525 if (!writer_packet_header) {
3e4f69d3 526 BT_LOGE_STR("Failed to copy field from stream packet header.");
387483fc
JD
527 goto error;
528 }
529
50842bdc 530 ret = bt_stream_set_packet_header(writer_stream,
387483fc
JD
531 writer_packet_header);
532 if (ret) {
3e4f69d3 533 BT_LOGE_STR("Failed to set stream packet header.");
387483fc
JD
534 goto error;
535 }
536
537 goto end;
538
539error:
540 ret = -1;
541end:
65300d60
PP
542 bt_object_put_ref(writer_packet_header);
543 bt_object_put_ref(packet_header);
387483fc
JD
544 return ret;
545}
546
547BT_HIDDEN
40f4ba76
PP
548int ctf_packet_copy_header(FILE *err, const struct bt_packet *packet,
549 const struct bt_packet *writer_packet)
387483fc 550{
40f4ba76 551 const struct bt_field *packet_header = NULL, *writer_packet_header = NULL;
387483fc
JD
552 int ret = 0;
553
50842bdc 554 packet_header = bt_packet_get_header(packet);
387483fc
JD
555 if (!packet_header) {
556 goto end;
557 }
558
50842bdc 559 writer_packet_header = bt_field_copy(packet_header);
387483fc 560 if (!writer_packet_header) {
3e4f69d3 561 BT_LOGE_STR("Failed to copy field from packet header.");
387483fc
JD
562 goto error;
563 }
564
50842bdc 565 ret = bt_packet_set_header(writer_packet, writer_packet_header);
387483fc 566 if (ret) {
3e4f69d3 567 BT_LOGE_STR("Failed to set packet header.");
387483fc
JD
568 goto error;
569 }
570
571 goto end;
572
573error:
574 ret = -1;
575end:
65300d60
PP
576 bt_object_put_ref(packet_header);
577 bt_object_put_ref(writer_packet_header);
387483fc
JD
578 return ret;
579}
580
9ac68eb1 581BT_HIDDEN
40f4ba76
PP
582int ctf_stream_copy_packet_context(FILE *err, const struct bt_packet *packet,
583 const struct bt_stream *writer_stream)
91b73004 584{
40f4ba76 585 const struct bt_field *packet_context = NULL, *writer_packet_context = NULL;
9877e1aa 586 int ret = 0;
91b73004 587
50842bdc 588 packet_context = bt_packet_get_context(packet);
9877e1aa 589 if (!packet_context) {
91b73004
JD
590 goto end;
591 }
592
50842bdc 593 writer_packet_context = bt_field_copy(packet_context);
9877e1aa 594 if (!writer_packet_context) {
3e4f69d3 595 BT_LOGE_STR("Failed to copy field from stream packet context.");
9877e1aa 596 goto error;
91b73004
JD
597 }
598
50842bdc 599 ret = bt_stream_set_packet_context(writer_stream,
9877e1aa
JD
600 writer_packet_context);
601 if (ret) {
3e4f69d3 602 BT_LOGE_STR("Failed to set stream packet context.");
9877e1aa 603 goto error;
91b73004
JD
604 }
605
9ae49d3d
JD
606 goto end;
607
608error:
9877e1aa 609 ret = -1;
91b73004 610end:
65300d60
PP
611 bt_object_put_ref(packet_context);
612 bt_object_put_ref(writer_packet_context);
91b73004
JD
613 return ret;
614}
615
9ac68eb1 616BT_HIDDEN
40f4ba76
PP
617int ctf_packet_copy_context(FILE *err, const struct bt_packet *packet,
618 const struct bt_stream *writer_stream,
619 const struct bt_packet *writer_packet)
91b73004 620{
40f4ba76 621 const struct bt_field *packet_context = NULL, *writer_packet_context = NULL;
9877e1aa 622 int ret = 0;
91b73004 623
50842bdc 624 packet_context = bt_packet_get_context(packet);
91b73004 625 if (!packet_context) {
60ef553b 626 goto end;
91b73004
JD
627 }
628
50842bdc 629 writer_packet_context = bt_field_copy(packet_context);
9877e1aa 630 if (!writer_packet_context) {
3e4f69d3 631 BT_LOGE_STR("Failed to copy field from packet context.");
9ae49d3d 632 goto error;
91b73004
JD
633 }
634
50842bdc 635 ret = bt_packet_set_context(writer_packet, writer_packet_context);
9877e1aa 636 if (ret) {
3e4f69d3 637 BT_LOGE_STR("Failed to set packet context.");
9ae49d3d 638 goto error;
91b73004
JD
639 }
640
9ae49d3d
JD
641 goto end;
642
643error:
9877e1aa 644 ret = -1;
9ae49d3d 645end:
65300d60
PP
646 bt_object_put_ref(writer_packet_context);
647 bt_object_put_ref(packet_context);
9877e1aa 648 return ret;
b2f1f465
JD
649}
650
9ac68eb1 651BT_HIDDEN
40f4ba76
PP
652int ctf_copy_event_header(FILE *err, const struct bt_event *event,
653 const struct bt_event_class *writer_event_class,
654 const struct bt_event *writer_event,
655 const struct bt_field *event_header)
b2f1f465 656{
40f4ba76 657 const struct bt_clock_class *clock_class = NULL, *writer_clock_class = NULL;
50842bdc 658 struct bt_clock_value *clock_value = NULL, *writer_clock_value = NULL;
b2f1f465
JD
659
660 int ret;
40f4ba76 661 const struct bt_field *writer_event_header = NULL;
0f29db56 662 uint64_t value;
b2f1f465 663
0f29db56
JD
664 clock_class = event_get_clock_class(err, event);
665 if (!clock_class) {
3e4f69d3 666 BT_LOGE_STR("Failed to get event clock_class.");
0f29db56
JD
667 goto error;
668 }
669
50842bdc 670 clock_value = bt_event_get_clock_value(event, clock_class);
65300d60 671 BT_OBJECT_PUT_REF_AND_RESET(clock_class);
f6ccaed9 672 BT_ASSERT(clock_value);
0f29db56 673
50842bdc 674 ret = bt_clock_value_get_value(clock_value, &value);
65300d60 675 BT_OBJECT_PUT_REF_AND_RESET(clock_value);
0f29db56 676 if (ret) {
3e4f69d3 677 BT_LOGE_STR("Failed to get clock value.");
0f29db56 678 goto error;
b2f1f465
JD
679 }
680
681 writer_clock_class = event_get_clock_class(err, writer_event);
682 if (!writer_clock_class) {
3e4f69d3 683 BT_LOGE_STR("Failed to get event clock_class.");
b2f1f465
JD
684 goto error;
685 }
686
50842bdc 687 writer_clock_value = bt_clock_value_create(writer_clock_class, value);
65300d60 688 BT_OBJECT_PUT_REF_AND_RESET(writer_clock_class);
0f29db56 689 if (!writer_clock_value) {
3e4f69d3 690 BT_LOGE_STR("Failed to create clock value.");
9ae49d3d 691 goto error;
b2f1f465
JD
692 }
693
50842bdc 694 ret = bt_event_set_clock_value(writer_event, writer_clock_value);
65300d60 695 BT_OBJECT_PUT_REF_AND_RESET(writer_clock_value);
b2f1f465 696 if (ret) {
3e4f69d3 697 BT_LOGE_STR("Failed to set clock value.");
b2f1f465
JD
698 goto error;
699 }
700
50842bdc 701 writer_event_header = bt_field_copy(event_header);
0f29db56 702 if (!writer_event_header) {
3e4f69d3 703 BT_LOGE_STR("Failed to copy event_header.");
0f29db56
JD
704 goto end;
705 }
706
50842bdc 707 ret = bt_event_set_header(writer_event, writer_event_header);
65300d60 708 BT_OBJECT_PUT_REF_AND_RESET(writer_event_header);
b2f1f465 709 if (ret < 0) {
3e4f69d3 710 BT_LOGE_STR("Failed to set event_header.");
b2f1f465
JD
711 goto error;
712 }
b2f1f465
JD
713
714 ret = 0;
715
716 goto end;
717
718error:
b2f1f465 719 ret = -1;
91b73004
JD
720end:
721 return ret;
722}
723
d23979be 724static
40f4ba76
PP
725const struct bt_trace *event_class_get_trace(FILE *err,
726 const struct bt_event_class *event_class)
d23979be 727{
40f4ba76
PP
728 const struct bt_trace *trace = NULL;
729 const struct bt_stream_class *stream_class = NULL;
d23979be 730
50842bdc 731 stream_class = bt_event_class_get_stream_class(event_class);
f6ccaed9 732 BT_ASSERT(stream_class);
d23979be 733
50842bdc 734 trace = bt_stream_class_get_trace(stream_class);
f6ccaed9 735 BT_ASSERT(trace);
d23979be 736
65300d60 737 bt_object_put_ref(stream_class);
d23979be
JD
738 return trace;
739}
740
9ac68eb1 741BT_HIDDEN
40f4ba76
PP
742const struct bt_event *ctf_copy_event(FILE *err, const struct bt_event *event,
743 const struct bt_event_class *writer_event_class,
b2f1f465 744 bool override_ts64)
91b73004 745{
40f4ba76
PP
746 const struct bt_event *writer_event = NULL;
747 const struct bt_field *field = NULL, *copy_field = NULL;
748 const struct bt_trace *writer_trace = NULL;
91b73004
JD
749 int ret;
750
50842bdc 751 writer_event = bt_event_create(writer_event_class);
91b73004 752 if (!writer_event) {
3e4f69d3 753 BT_LOGE_STR("Failed to create event.");
d23979be
JD
754 goto error;
755 }
756
757 writer_trace = event_class_get_trace(err, writer_event_class);
758 if (!writer_trace) {
3e4f69d3 759 BT_LOGE_STR("Failed to get trace from event_class.");
d23979be 760 goto error;
91b73004
JD
761 }
762
50842bdc 763 field = bt_event_get_header(event);
06b019a7
JD
764 if (field) {
765 /*
d23979be
JD
766 * If override_ts64, we override all integer fields mapped to a
767 * clock to a uint64_t field type, otherwise, we just copy it as
768 * is.
06b019a7 769 */
50842bdc 770 ret = bt_trace_get_clock_class_count(writer_trace);
f6ccaed9 771 BT_ASSERT(ret >= 0);
3e4f69d3 772
d23979be 773 if (override_ts64 && ret > 0) {
50842bdc 774 copy_field = bt_event_get_header(writer_event);
f6ccaed9 775 BT_ASSERT(copy_field);
b2f1f465 776
06b019a7
JD
777 ret = copy_override_field(err, event, writer_event, field,
778 copy_field);
779 if (ret) {
3e4f69d3 780 BT_LOGE_STR("Failed to copy and override field.");
06b019a7
JD
781 goto error;
782 }
65300d60 783 BT_OBJECT_PUT_REF_AND_RESET(copy_field);
06b019a7
JD
784 } else {
785 ret = ctf_copy_event_header(err, event, writer_event_class,
786 writer_event, field);
787 if (ret) {
3e4f69d3 788 BT_LOGE_STR("Failed to copy event_header.");
06b019a7
JD
789 goto error;
790 }
91b73004 791 }
65300d60 792 BT_OBJECT_PUT_REF_AND_RESET(field);
91b73004
JD
793 }
794
795 /* Optional field, so it can fail silently. */
50842bdc 796 field = bt_event_get_stream_event_context(event);
961ec227 797 if (field) {
50842bdc 798 copy_field = bt_field_copy(field);
961ec227 799 if (!copy_field) {
3e4f69d3 800 BT_LOGE_STR("Failed to copy field.");
961ec227
JD
801 goto error;
802 }
50842bdc 803 ret = bt_event_set_stream_event_context(writer_event,
91b73004 804 copy_field);
91b73004 805 if (ret < 0) {
3e4f69d3 806 BT_LOGE_STR("Failed to set stream_event_context.");
91b73004
JD
807 goto error;
808 }
65300d60
PP
809 BT_OBJECT_PUT_REF_AND_RESET(field);
810 BT_OBJECT_PUT_REF_AND_RESET(copy_field);
91b73004
JD
811 }
812
813 /* Optional field, so it can fail silently. */
50842bdc 814 field = bt_event_get_event_context(event);
961ec227 815 if (field) {
50842bdc 816 copy_field = bt_field_copy(field);
961ec227 817 if (!copy_field) {
3e4f69d3 818 BT_LOGE_STR("Failed to copy field.");
961ec227
JD
819 goto error;
820 }
50842bdc 821 ret = bt_event_set_event_context(writer_event, copy_field);
91b73004 822 if (ret < 0) {
3e4f69d3 823 BT_LOGE_STR("Failed to set event_context.");
91b73004
JD
824 goto error;
825 }
65300d60
PP
826 BT_OBJECT_PUT_REF_AND_RESET(field);
827 BT_OBJECT_PUT_REF_AND_RESET(copy_field);
91b73004
JD
828 }
829
50842bdc 830 field = bt_event_get_event_payload(event);
961ec227 831 if (field) {
50842bdc 832 copy_field = bt_field_copy(field);
961ec227 833 if (!copy_field) {
3e4f69d3 834 BT_LOGE_STR("Failed to copy field.");
961ec227
JD
835 goto error;
836 }
50842bdc 837 ret = bt_event_set_event_payload(writer_event, copy_field);
91b73004 838 if (ret < 0) {
3e4f69d3 839 BT_LOGE_STR("Failed to set event_payload.");
91b73004
JD
840 goto error;
841 }
65300d60
PP
842 BT_OBJECT_PUT_REF_AND_RESET(field);
843 BT_OBJECT_PUT_REF_AND_RESET(copy_field);
91b73004 844 }
9ae49d3d 845
91b73004
JD
846 goto end;
847
848error:
65300d60 849 BT_OBJECT_PUT_REF_AND_RESET(writer_event);
91b73004 850end:
65300d60
PP
851 bt_object_put_ref(field);
852 bt_object_put_ref(copy_field);
853 bt_object_put_ref(writer_trace);
91b73004
JD
854 return writer_event;
855}
856
9ac68eb1 857BT_HIDDEN
40f4ba76
PP
858enum bt_component_status ctf_copy_trace(FILE *err, const struct bt_trace *trace,
859 const struct bt_trace *writer_trace)
91b73004
JD
860{
861 enum bt_component_status ret = BT_COMPONENT_STATUS_OK;
862 int field_count, i, int_ret;
50842bdc
PP
863 struct bt_field_type *header_type = NULL;
864 enum bt_byte_order order;
0ac862b4 865 const char *trace_name;
40b9ea67 866 const unsigned char *trace_uuid;
91b73004 867
50842bdc 868 field_count = bt_trace_get_environment_field_count(trace);
91b73004
JD
869 for (i = 0; i < field_count; i++) {
870 int ret_int;
871 const char *name;
9ae49d3d 872 struct bt_value *value = NULL;
91b73004 873
50842bdc 874 name = bt_trace_get_environment_field_name_by_index(
9ac68eb1 875 trace, i);
f6ccaed9 876 BT_ASSERT(name);
3e4f69d3 877
50842bdc 878 value = bt_trace_get_environment_field_value_by_index(
9ac68eb1 879 trace, i);
f6ccaed9 880 BT_ASSERT(value);
91b73004 881
50842bdc 882 ret_int = bt_trace_set_environment_field(writer_trace,
91b73004 883 name, value);
65300d60 884 BT_OBJECT_PUT_REF_AND_RESET(value);
91b73004 885 if (ret_int < 0) {
3e4f69d3 886 BT_LOGE("Failed to set environment: field-name=\"%s\"",
91b73004
JD
887 name);
888 ret = BT_COMPONENT_STATUS_ERROR;
9ae49d3d 889 goto end;
91b73004
JD
890 }
891 }
892
50842bdc 893 order = bt_trace_get_native_byte_order(trace);
f6ccaed9 894 BT_ASSERT(order != BT_BYTE_ORDER_UNKNOWN);
6468dbd6 895
d41cff38
PP
896 /*
897 * Only explicitly set the writer trace's native byte order if
898 * the original trace has a specific one. Otherwise leave what
899 * the CTF writer object chooses, which is the machine's native
900 * byte order.
901 */
50842bdc
PP
902 if (order != BT_BYTE_ORDER_UNSPECIFIED) {
903 ret = bt_trace_set_native_byte_order(writer_trace, order);
d41cff38 904 if (ret) {
3e4f69d3 905 BT_LOGE_STR("Failed to set native byte order.");
d41cff38
PP
906 ret = BT_COMPONENT_STATUS_ERROR;
907 goto end;
908 }
6468dbd6
JD
909 }
910
50842bdc 911 header_type = bt_trace_get_packet_header_type(trace);
944eed39 912 if (header_type) {
50842bdc 913 int_ret = bt_trace_set_packet_header_type(writer_trace, header_type);
65300d60 914 BT_OBJECT_PUT_REF_AND_RESET(header_type);
944eed39 915 if (int_ret < 0) {
3e4f69d3 916 BT_LOGE_STR("Failed to set packet header type.");
944eed39
JD
917 ret = BT_COMPONENT_STATUS_ERROR;
918 goto end;
919 }
91b73004
JD
920 }
921
50842bdc 922 trace_name = bt_trace_get_name(trace);
0ac862b4 923 if (trace_name) {
50842bdc 924 int_ret = bt_trace_set_name(writer_trace, trace_name);
0ac862b4 925 if (int_ret < 0) {
3e4f69d3 926 BT_LOGE_STR("Failed to set trace name.");
0ac862b4
JD
927 ret = BT_COMPONENT_STATUS_ERROR;
928 goto end;
929 }
930 }
931
50842bdc 932 trace_uuid = bt_trace_get_uuid(trace);
40b9ea67 933 if (trace_uuid) {
50842bdc 934 int_ret = bt_trace_set_uuid(writer_trace, trace_uuid);
40b9ea67 935 if (int_ret < 0) {
3e4f69d3 936 BT_LOGE_STR("Failed to set trace UUID.");
40b9ea67
PP
937 ret = BT_COMPONENT_STATUS_ERROR;
938 goto end;
939 }
940 }
941
9ae49d3d 942end:
91b73004
JD
943 return ret;
944}
This page took 0.081796 seconds and 4 git commands to generate.