Commit | Line | Data |
---|---|---|
273b65be JG |
1 | /* |
2 | * event.c | |
3 | * | |
d2dc44b6 | 4 | * Babeltrace CTF IR - Event |
273b65be | 5 | * |
de9dd397 | 6 | * Copyright 2013, 2014 Jérémie Galarneau <jeremie.galarneau@efficios.com> |
273b65be JG |
7 | * |
8 | * Author: Jérémie Galarneau <jeremie.galarneau@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 | ||
7b010242 PP |
29 | #define BT_LOG_TAG "EVENT" |
30 | #include <babeltrace/lib-logging-internal.h> | |
31 | ||
2e33ac5a PP |
32 | #include <babeltrace/ctf-ir/fields-internal.h> |
33 | #include <babeltrace/ctf-ir/field-types-internal.h> | |
ac0c6bdd | 34 | #include <babeltrace/ctf-ir/clock-class.h> |
c057dea0 PP |
35 | #include <babeltrace/ctf-ir/clock-value.h> |
36 | #include <babeltrace/ctf-ir/clock-value-internal.h> | |
7b010242 | 37 | #include <babeltrace/ctf-ir/clock-class-internal.h> |
adc315b8 | 38 | #include <babeltrace/ctf-ir/event-internal.h> |
272df73e PP |
39 | #include <babeltrace/ctf-ir/event-class.h> |
40 | #include <babeltrace/ctf-ir/event-class-internal.h> | |
2f100782 | 41 | #include <babeltrace/ctf-ir/stream-class.h> |
c35a1669 | 42 | #include <babeltrace/ctf-ir/stream-class-internal.h> |
41ac640a | 43 | #include <babeltrace/ctf-ir/stream-internal.h> |
4ce9f9d0 PP |
44 | #include <babeltrace/ctf-ir/packet.h> |
45 | #include <babeltrace/ctf-ir/packet-internal.h> | |
bc37ae52 | 46 | #include <babeltrace/ctf-ir/trace-internal.h> |
09840de5 | 47 | #include <babeltrace/ctf-ir/validation-internal.h> |
5c3b707d | 48 | #include <babeltrace/ctf-ir/packet-internal.h> |
654c1444 | 49 | #include <babeltrace/ctf-ir/utils.h> |
dc3fffef | 50 | #include <babeltrace/ctf-writer/serialize-internal.h> |
2a3ced3c | 51 | #include <babeltrace/ctf-writer/clock-internal.h> |
83509119 | 52 | #include <babeltrace/ref.h> |
44e0a4f5 | 53 | #include <babeltrace/ctf-ir/attributes-internal.h> |
3d9990ac | 54 | #include <babeltrace/compiler-internal.h> |
7b010242 | 55 | #include <inttypes.h> |
273b65be | 56 | |
273b65be | 57 | static |
50842bdc | 58 | void bt_event_destroy(struct bt_object *obj); |
273b65be | 59 | |
50842bdc | 60 | struct bt_event *bt_event_create(struct bt_event_class *event_class) |
273b65be | 61 | { |
09840de5 | 62 | int ret; |
50842bdc PP |
63 | enum bt_validation_flag validation_flags = |
64 | BT_VALIDATION_FLAG_STREAM | | |
65 | BT_VALIDATION_FLAG_EVENT; | |
66 | struct bt_event *event = NULL; | |
67 | struct bt_trace *trace = NULL; | |
68 | struct bt_stream_class *stream_class = NULL; | |
69 | struct bt_field_type *packet_header_type = NULL; | |
70 | struct bt_field_type *packet_context_type = NULL; | |
71 | struct bt_field_type *event_header_type = NULL; | |
72 | struct bt_field_type *stream_event_ctx_type = NULL; | |
73 | struct bt_field_type *event_context_type = NULL; | |
74 | struct bt_field_type *event_payload_type = NULL; | |
75 | struct bt_field *event_header = NULL; | |
76 | struct bt_field *stream_event_context = NULL; | |
77 | struct bt_field *event_context = NULL; | |
78 | struct bt_field *event_payload = NULL; | |
09840de5 | 79 | struct bt_value *environment = NULL; |
50842bdc | 80 | struct bt_validation_output validation_output = { 0 }; |
09840de5 | 81 | int trace_valid = 0; |
2a3ced3c | 82 | struct bt_clock_class *expected_clock_class = NULL; |
273b65be | 83 | |
7b010242 PP |
84 | BT_LOGD("Creating event object: event-class-addr=%p, " |
85 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
86 | event_class, bt_event_class_get_name(event_class), |
87 | bt_event_class_get_id(event_class)); | |
7b010242 | 88 | |
273b65be | 89 | if (!event_class) { |
7b010242 | 90 | BT_LOGW_STR("Invalid parameter: event class is NULL."); |
e6a8e8e4 | 91 | goto error; |
273b65be JG |
92 | } |
93 | ||
50842bdc | 94 | stream_class = bt_event_class_get_stream_class(event_class); |
09840de5 | 95 | |
662e778c | 96 | /* |
e6a8e8e4 JG |
97 | * We disallow the creation of an event if its event class has not been |
98 | * associated to a stream class. | |
662e778c | 99 | */ |
e6a8e8e4 | 100 | if (!stream_class) { |
e0bcd1b0 | 101 | BT_LOGW_STR("Event class is not part of a stream class."); |
e6a8e8e4 | 102 | goto error; |
662e778c | 103 | } |
09840de5 | 104 | |
09840de5 PP |
105 | /* The event class was frozen when added to its stream class */ |
106 | assert(event_class->frozen); | |
107 | ||
2a3ced3c PP |
108 | if (!stream_class->frozen) { |
109 | if (stream_class->clock) { | |
110 | expected_clock_class = | |
111 | bt_get(stream_class->clock->clock_class); | |
112 | } | |
113 | ||
114 | /* | |
115 | * Because this function freezes the stream class, | |
116 | * validate that this stream class contains at most a | |
117 | * single clock class so that we set its expected clock | |
118 | * class for future checks. | |
119 | */ | |
120 | ret = bt_stream_class_validate_single_clock_class( | |
121 | stream_class, &expected_clock_class); | |
122 | if (ret) { | |
123 | BT_LOGW("Event class's stream class or one of its event " | |
124 | "classes contains a field type which is not " | |
125 | "recursively mapped to the expected " | |
126 | "clock class: " | |
127 | "stream-class-addr=%p, " | |
128 | "stream-class-id=%" PRId64 ", " | |
129 | "stream-class-name=\"%s\", " | |
130 | "expected-clock-class-addr=%p, " | |
131 | "expected-clock-class-name=\"%s\"", | |
132 | stream_class, bt_stream_class_get_id(stream_class), | |
133 | bt_stream_class_get_name(stream_class), | |
134 | expected_clock_class, | |
135 | expected_clock_class ? | |
136 | bt_clock_class_get_name(expected_clock_class) : | |
137 | NULL); | |
138 | goto error; | |
139 | } | |
140 | } | |
141 | ||
09840de5 | 142 | /* Validate the trace (if any), the stream class, and the event class */ |
50842bdc | 143 | trace = bt_stream_class_get_trace(stream_class); |
09840de5 | 144 | if (trace) { |
e0bcd1b0 | 145 | BT_LOGD_STR("Event's class is part of a trace."); |
50842bdc | 146 | packet_header_type = bt_trace_get_packet_header_type(trace); |
09840de5 PP |
147 | trace_valid = trace->valid; |
148 | assert(trace_valid); | |
149 | environment = trace->environment; | |
150 | } | |
151 | ||
50842bdc | 152 | packet_context_type = bt_stream_class_get_packet_context_type( |
09840de5 | 153 | stream_class); |
50842bdc | 154 | event_header_type = bt_stream_class_get_event_header_type( |
09840de5 | 155 | stream_class); |
50842bdc | 156 | stream_event_ctx_type = bt_stream_class_get_event_context_type( |
09840de5 | 157 | stream_class); |
50842bdc PP |
158 | event_context_type = bt_event_class_get_context_type(event_class); |
159 | event_payload_type = bt_event_class_get_payload_type(event_class); | |
160 | ret = bt_validate_class_types(environment, packet_header_type, | |
09840de5 PP |
161 | packet_context_type, event_header_type, stream_event_ctx_type, |
162 | event_context_type, event_payload_type, trace_valid, | |
163 | stream_class->valid, event_class->valid, | |
164 | &validation_output, validation_flags); | |
165 | BT_PUT(packet_header_type); | |
166 | BT_PUT(packet_context_type); | |
167 | BT_PUT(event_header_type); | |
168 | BT_PUT(stream_event_ctx_type); | |
169 | BT_PUT(event_context_type); | |
170 | BT_PUT(event_payload_type); | |
09840de5 PP |
171 | if (ret) { |
172 | /* | |
173 | * This means something went wrong during the validation | |
174 | * process, not that the objects are invalid. | |
175 | */ | |
e0bcd1b0 | 176 | BT_LOGE("Failed to validate event and parents: ret=%d", ret); |
09840de5 PP |
177 | goto error; |
178 | } | |
179 | ||
180 | if ((validation_output.valid_flags & validation_flags) != | |
181 | validation_flags) { | |
182 | /* Invalid trace/stream class/event class */ | |
3ee09f3a | 183 | BT_LOGW("Invalid trace, stream class, or event class: " |
e0bcd1b0 | 184 | "valid-flags=0x%x", validation_output.valid_flags); |
09840de5 PP |
185 | goto error; |
186 | } | |
187 | ||
188 | /* | |
189 | * At this point we know the trace (if associated to the stream | |
190 | * class), the stream class, and the event class, with their | |
191 | * current types, are valid. We may proceed with creating | |
192 | * the event. | |
193 | */ | |
50842bdc | 194 | event = g_new0(struct bt_event, 1); |
b8248cc0 | 195 | if (!event) { |
7b010242 | 196 | BT_LOGE_STR("Failed to allocate one event."); |
e6a8e8e4 | 197 | goto error; |
b8248cc0 PP |
198 | } |
199 | ||
50842bdc | 200 | bt_object_init(event, bt_event_destroy); |
09840de5 | 201 | |
e6a8e8e4 JG |
202 | /* |
203 | * event does not share a common ancestor with the event class; it has | |
204 | * to guarantee its existence by holding a reference. This reference | |
205 | * shall be released once the event is associated to a stream since, | |
206 | * from that point, the event and its class will share the same | |
207 | * lifetime. | |
208 | */ | |
209 | event->event_class = bt_get(event_class); | |
41ac640a | 210 | event->clock_values = g_hash_table_new_full(g_direct_hash, |
1556a1af | 211 | g_direct_equal, bt_put, bt_put); |
be514b0c PP |
212 | |
213 | if (validation_output.event_header_type) { | |
214 | BT_LOGD("Creating initial event header field: ft-addr=%p", | |
215 | validation_output.event_header_type); | |
216 | event_header = | |
50842bdc | 217 | bt_field_create(validation_output.event_header_type); |
be514b0c PP |
218 | if (!event_header) { |
219 | BT_LOGE_STR("Cannot create initial event header field object."); | |
220 | goto error; | |
221 | } | |
662e778c | 222 | } |
09840de5 | 223 | |
5fd2e9fd | 224 | if (validation_output.stream_event_ctx_type) { |
be514b0c PP |
225 | BT_LOGD("Creating initial stream event context field: ft-addr=%p", |
226 | validation_output.stream_event_ctx_type); | |
50842bdc | 227 | stream_event_context = bt_field_create( |
5fd2e9fd PP |
228 | validation_output.stream_event_ctx_type); |
229 | if (!stream_event_context) { | |
7b010242 | 230 | BT_LOGE_STR("Cannot create initial stream event context field object."); |
5fd2e9fd PP |
231 | goto error; |
232 | } | |
233 | } | |
234 | ||
09840de5 | 235 | if (validation_output.event_context_type) { |
be514b0c PP |
236 | BT_LOGD("Creating initial event context field: ft-addr=%p", |
237 | validation_output.event_context_type); | |
50842bdc | 238 | event_context = bt_field_create( |
09840de5 PP |
239 | validation_output.event_context_type); |
240 | if (!event_context) { | |
7b010242 | 241 | BT_LOGE_STR("Cannot create initial event context field object."); |
83509119 | 242 | goto error; |
662e778c | 243 | } |
f655a84d | 244 | } |
09840de5 PP |
245 | |
246 | if (validation_output.event_payload_type) { | |
be514b0c PP |
247 | BT_LOGD("Creating initial event payload field: ft-addr=%p", |
248 | validation_output.event_payload_type); | |
50842bdc | 249 | event_payload = bt_field_create( |
09840de5 PP |
250 | validation_output.event_payload_type); |
251 | if (!event_payload) { | |
7b010242 | 252 | BT_LOGE_STR("Cannot create initial event payload field object."); |
09840de5 PP |
253 | goto error; |
254 | } | |
662e778c JG |
255 | } |
256 | ||
09840de5 PP |
257 | /* |
258 | * At this point all the fields are created, potentially from | |
259 | * validated copies of field types, so that the field types and | |
260 | * fields can be replaced in the trace, stream class, | |
261 | * event class, and created event. | |
262 | */ | |
50842bdc | 263 | bt_validation_replace_types(trace, stream_class, |
09840de5 PP |
264 | event_class, &validation_output, validation_flags); |
265 | BT_MOVE(event->event_header, event_header); | |
5fd2e9fd | 266 | BT_MOVE(event->stream_event_context, stream_event_context); |
09840de5 PP |
267 | BT_MOVE(event->context_payload, event_context); |
268 | BT_MOVE(event->fields_payload, event_payload); | |
269 | ||
270 | /* | |
50842bdc | 271 | * Put what was not moved in bt_validation_replace_types(). |
09840de5 | 272 | */ |
50842bdc | 273 | bt_validation_output_put_types(&validation_output); |
09840de5 | 274 | |
662e778c JG |
275 | /* |
276 | * Freeze the stream class since the event header must not be changed | |
277 | * anymore. | |
278 | */ | |
50842bdc | 279 | bt_stream_class_freeze(stream_class); |
09840de5 | 280 | |
2a3ced3c PP |
281 | /* |
282 | * It is safe to set the stream class's unique clock class | |
283 | * now because the stream class is frozen. | |
284 | */ | |
285 | if (expected_clock_class) { | |
286 | BT_MOVE(stream_class->clock_class, expected_clock_class); | |
287 | } | |
288 | ||
09840de5 PP |
289 | /* |
290 | * Mark stream class, and event class as valid since | |
291 | * they're all frozen now. | |
292 | */ | |
293 | stream_class->valid = 1; | |
294 | event_class->valid = 1; | |
295 | ||
296 | /* Put stuff we borrowed from the event class */ | |
e6a8e8e4 | 297 | BT_PUT(stream_class); |
09840de5 | 298 | BT_PUT(trace); |
7b010242 PP |
299 | BT_LOGD("Created event object: addr=%p, event-class-name=\"%s\", " |
300 | "event-class-id=%" PRId64, | |
50842bdc PP |
301 | event, bt_event_class_get_name(event->event_class), |
302 | bt_event_class_get_id(event_class)); | |
273b65be | 303 | return event; |
09840de5 | 304 | |
83509119 | 305 | error: |
50842bdc | 306 | bt_validation_output_put_types(&validation_output); |
83509119 | 307 | BT_PUT(event); |
e6a8e8e4 | 308 | BT_PUT(stream_class); |
09840de5 PP |
309 | BT_PUT(trace); |
310 | BT_PUT(event_header); | |
5fd2e9fd | 311 | BT_PUT(stream_event_context); |
09840de5 PP |
312 | BT_PUT(event_context); |
313 | BT_PUT(event_payload); | |
2a3ced3c | 314 | bt_put(expected_clock_class); |
09840de5 PP |
315 | assert(!packet_header_type); |
316 | assert(!packet_context_type); | |
317 | assert(!event_header_type); | |
318 | assert(!stream_event_ctx_type); | |
319 | assert(!event_context_type); | |
320 | assert(!event_payload_type); | |
321 | ||
83509119 | 322 | return event; |
273b65be JG |
323 | } |
324 | ||
50842bdc | 325 | struct bt_event_class *bt_event_get_class(struct bt_event *event) |
2f100782 | 326 | { |
50842bdc | 327 | struct bt_event_class *event_class = NULL; |
2f100782 JG |
328 | |
329 | if (!event) { | |
7b010242 | 330 | BT_LOGW_STR("Invalid parameter: event is NULL."); |
2f100782 JG |
331 | goto end; |
332 | } | |
333 | ||
50842bdc | 334 | event_class = bt_get(bt_event_borrow_event_class(event)); |
2f100782 JG |
335 | end: |
336 | return event_class; | |
337 | } | |
338 | ||
50842bdc | 339 | struct bt_stream *bt_event_get_stream(struct bt_event *event) |
8e5003bb | 340 | { |
50842bdc | 341 | struct bt_stream *stream = NULL; |
cacf3147 PP |
342 | |
343 | if (!event) { | |
7b010242 | 344 | BT_LOGW_STR("Invalid parameter: event is NULL."); |
cacf3147 PP |
345 | goto end; |
346 | } | |
347 | ||
348 | /* | |
349 | * If the event has a parent, then this is its (writer) stream. | |
350 | * If the event has no parent, then if it has a packet, this | |
351 | * is its (non-writer) stream. | |
352 | */ | |
353 | if (event->base.parent) { | |
50842bdc | 354 | stream = (struct bt_stream *) bt_object_get_parent(event); |
cacf3147 PP |
355 | } else { |
356 | if (event->packet) { | |
357 | stream = bt_get(event->packet->stream); | |
358 | } | |
359 | } | |
360 | ||
361 | end: | |
362 | return stream; | |
8e5003bb JG |
363 | } |
364 | ||
50842bdc | 365 | int bt_event_set_payload(struct bt_event *event, |
273b65be | 366 | const char *name, |
50842bdc | 367 | struct bt_field *payload) |
273b65be JG |
368 | { |
369 | int ret = 0; | |
370 | ||
7b010242 PP |
371 | if (!event || !payload) { |
372 | BT_LOGW("Invalid parameter: event or payload field is NULL: " | |
373 | "event-addr=%p, payload-field-addr=%p", | |
374 | event, payload); | |
375 | ret = -1; | |
376 | goto end; | |
377 | } | |
378 | ||
379 | if (event->frozen) { | |
380 | BT_LOGW("Invalid parameter: event is frozen: addr=%p, " | |
381 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
382 | event, bt_event_class_get_name(event->event_class), |
383 | bt_event_class_get_id(event->event_class)); | |
273b65be JG |
384 | ret = -1; |
385 | goto end; | |
386 | } | |
387 | ||
c5a9aa19 | 388 | if (name) { |
50842bdc | 389 | ret = bt_field_structure_set_field_by_name( |
2225de6b | 390 | event->fields_payload, name, payload); |
c5a9aa19 | 391 | } else { |
50842bdc | 392 | struct bt_field_type *payload_type; |
c5a9aa19 | 393 | |
50842bdc | 394 | payload_type = bt_field_get_type(payload); |
09840de5 | 395 | |
50842bdc | 396 | if (bt_field_type_compare(payload_type, |
09840de5 | 397 | event->event_class->fields) == 0) { |
83509119 JG |
398 | bt_put(event->fields_payload); |
399 | bt_get(payload); | |
c5a9aa19 JG |
400 | event->fields_payload = payload; |
401 | } else { | |
7b010242 PP |
402 | BT_LOGW("Invalid parameter: payload field type is different from the expected field type: " |
403 | "event-addr=%p, event-class-name=\"%s\", " | |
404 | "event-class-id=%" PRId64, | |
405 | event, | |
50842bdc PP |
406 | bt_event_class_get_name(event->event_class), |
407 | bt_event_class_get_id(event->event_class)); | |
c5a9aa19 JG |
408 | ret = -1; |
409 | } | |
410 | ||
83509119 | 411 | bt_put(payload_type); |
c5a9aa19 | 412 | } |
7b010242 PP |
413 | |
414 | if (ret) { | |
415 | BT_LOGW("Failed to set event's payload field: event-addr=%p, " | |
416 | "event-class-name=\"%s\", event-class-id=%" PRId64 ", " | |
417 | "payload-field-name=\"%s\", payload-field-addr=%p", | |
50842bdc PP |
418 | event, bt_event_class_get_name(event->event_class), |
419 | bt_event_class_get_id(event->event_class), | |
7b010242 PP |
420 | name, payload); |
421 | } else { | |
422 | BT_LOGV("Set event's payload field: event-addr=%p, " | |
423 | "event-class-name=\"%s\", event-class-id=%" PRId64 ", " | |
424 | "payload-field-name=\"%s\", payload-field-addr=%p", | |
50842bdc PP |
425 | event, bt_event_class_get_name(event->event_class), |
426 | bt_event_class_get_id(event->event_class), | |
7b010242 PP |
427 | name, payload); |
428 | } | |
429 | ||
273b65be JG |
430 | end: |
431 | return ret; | |
432 | } | |
433 | ||
50842bdc | 434 | struct bt_field *bt_event_get_event_payload(struct bt_event *event) |
71362d53 | 435 | { |
50842bdc | 436 | struct bt_field *payload = NULL; |
71362d53 | 437 | |
7b010242 PP |
438 | if (!event) { |
439 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
440 | goto end; | |
441 | } | |
442 | ||
443 | if (!event->fields_payload) { | |
444 | BT_LOGV("Event has no current payload field: addr=%p, " | |
445 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
446 | event, bt_event_class_get_name(event->event_class), |
447 | bt_event_class_get_id(event->event_class)); | |
71362d53 PP |
448 | goto end; |
449 | } | |
450 | ||
451 | payload = event->fields_payload; | |
83509119 | 452 | bt_get(payload); |
71362d53 PP |
453 | end: |
454 | return payload; | |
455 | } | |
273b65be | 456 | |
50842bdc PP |
457 | int bt_event_set_event_payload(struct bt_event *event, |
458 | struct bt_field *payload) | |
e5e6eb3a | 459 | { |
50842bdc | 460 | return bt_event_set_payload(event, NULL, payload); |
e5e6eb3a JG |
461 | } |
462 | ||
50842bdc | 463 | struct bt_field *bt_event_get_payload(struct bt_event *event, |
273b65be JG |
464 | const char *name) |
465 | { | |
50842bdc | 466 | struct bt_field *field = NULL; |
273b65be | 467 | |
c5a9aa19 | 468 | if (!event) { |
7b010242 | 469 | BT_LOGW_STR("Invalid parameter: event is NULL."); |
273b65be JG |
470 | goto end; |
471 | } | |
472 | ||
c5a9aa19 | 473 | if (name) { |
50842bdc PP |
474 | field = bt_field_structure_get_field_by_name( |
475 | event->fields_payload, name); | |
c5a9aa19 JG |
476 | } else { |
477 | field = event->fields_payload; | |
83509119 | 478 | bt_get(field); |
c5a9aa19 | 479 | } |
273b65be JG |
480 | end: |
481 | return field; | |
482 | } | |
483 | ||
50842bdc PP |
484 | struct bt_field *bt_event_get_payload_by_index( |
485 | struct bt_event *event, uint64_t index) | |
2f100782 | 486 | { |
50842bdc | 487 | struct bt_field *field = NULL; |
2f100782 | 488 | |
9ac68eb1 | 489 | if (!event) { |
7b010242 | 490 | BT_LOGW_STR("Invalid parameter: event is NULL."); |
2f100782 JG |
491 | goto end; |
492 | } | |
493 | ||
50842bdc | 494 | field = bt_field_structure_get_field_by_index(event->fields_payload, |
2f100782 JG |
495 | index); |
496 | end: | |
497 | return field; | |
498 | } | |
499 | ||
50842bdc PP |
500 | struct bt_field *bt_event_get_header( |
501 | struct bt_event *event) | |
662e778c | 502 | { |
50842bdc | 503 | struct bt_field *header = NULL; |
662e778c | 504 | |
7b010242 PP |
505 | if (!event) { |
506 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
507 | goto end; | |
508 | } | |
509 | ||
510 | if (!event->event_header) { | |
511 | BT_LOGV("Event has no current header field: addr=%p, " | |
512 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
513 | event, bt_event_class_get_name(event->event_class), |
514 | bt_event_class_get_id(event->event_class)); | |
662e778c JG |
515 | goto end; |
516 | } | |
517 | ||
518 | header = event->event_header; | |
83509119 | 519 | bt_get(header); |
662e778c JG |
520 | end: |
521 | return header; | |
522 | } | |
523 | ||
50842bdc PP |
524 | int bt_event_set_header(struct bt_event *event, |
525 | struct bt_field *header) | |
662e778c JG |
526 | { |
527 | int ret = 0; | |
50842bdc PP |
528 | struct bt_field_type *field_type = NULL; |
529 | struct bt_stream_class *stream_class = NULL; | |
662e778c | 530 | |
7b010242 PP |
531 | if (!event) { |
532 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
533 | ret = -1; | |
534 | goto end; | |
535 | } | |
536 | ||
537 | if (event->frozen) { | |
538 | BT_LOGW("Invalid parameter: event is frozen: addr=%p, " | |
539 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
540 | event, bt_event_class_get_name(event->event_class), |
541 | bt_event_class_get_id(event->event_class)); | |
662e778c JG |
542 | ret = -1; |
543 | goto end; | |
544 | } | |
545 | ||
50842bdc | 546 | stream_class = (struct bt_stream_class *) bt_object_get_parent( |
835b2d10 | 547 | event->event_class); |
662e778c JG |
548 | /* |
549 | * Ensure the provided header's type matches the one registered to the | |
550 | * stream class. | |
551 | */ | |
c5c82c6e | 552 | if (header) { |
50842bdc PP |
553 | field_type = bt_field_get_type(header); |
554 | if (bt_field_type_compare(field_type, | |
c5c82c6e PP |
555 | stream_class->event_header_type)) { |
556 | BT_LOGW("Invalid parameter: header field type is different from the expected field type: " | |
557 | "event-addr=%p, event-class-name=\"%s\", " | |
558 | "event-class-id=%" PRId64, | |
559 | event, | |
50842bdc PP |
560 | bt_event_class_get_name(event->event_class), |
561 | bt_event_class_get_id(event->event_class)); | |
c5c82c6e PP |
562 | ret = -1; |
563 | goto end; | |
564 | } | |
565 | } else { | |
566 | if (stream_class->event_header_type) { | |
567 | BT_LOGW("Invalid parameter: setting no event header but event header field type is not NULL: " | |
568 | "event-addr=%p, event-class-name=\"%s\", " | |
569 | "event-class-id=%" PRId64 ", " | |
570 | "event-header-ft-addr=%p", | |
571 | event, | |
50842bdc PP |
572 | bt_event_class_get_name(event->event_class), |
573 | bt_event_class_get_id(event->event_class), | |
c5c82c6e PP |
574 | stream_class->event_header_type); |
575 | ret = -1; | |
576 | goto end; | |
577 | } | |
662e778c JG |
578 | } |
579 | ||
83509119 | 580 | bt_put(event->event_header); |
835b2d10 | 581 | event->event_header = bt_get(header); |
7b010242 PP |
582 | BT_LOGV("Set event's header field: event-addr=%p, " |
583 | "event-class-name=\"%s\", event-class-id=%" PRId64 ", " | |
584 | "header-field-addr=%p", | |
50842bdc PP |
585 | event, bt_event_class_get_name(event->event_class), |
586 | bt_event_class_get_id(event->event_class), header); | |
662e778c | 587 | end: |
e6a8e8e4 | 588 | bt_put(stream_class); |
83509119 | 589 | bt_put(field_type); |
662e778c JG |
590 | return ret; |
591 | } | |
592 | ||
50842bdc PP |
593 | struct bt_field *bt_event_get_event_context( |
594 | struct bt_event *event) | |
f655a84d | 595 | { |
50842bdc | 596 | struct bt_field *context = NULL; |
f655a84d | 597 | |
7b010242 PP |
598 | if (!event) { |
599 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
600 | goto end; | |
601 | } | |
602 | ||
603 | if (!event->context_payload) { | |
604 | BT_LOGV("Event has no current context field: addr=%p, " | |
605 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
606 | event, bt_event_class_get_name(event->event_class), |
607 | bt_event_class_get_id(event->event_class)); | |
f655a84d JG |
608 | goto end; |
609 | } | |
610 | ||
611 | context = event->context_payload; | |
83509119 | 612 | bt_get(context); |
f655a84d JG |
613 | end: |
614 | return context; | |
615 | } | |
616 | ||
50842bdc PP |
617 | int bt_event_set_event_context(struct bt_event *event, |
618 | struct bt_field *context) | |
f655a84d JG |
619 | { |
620 | int ret = 0; | |
50842bdc | 621 | struct bt_field_type *field_type = NULL; |
f655a84d | 622 | |
7b010242 PP |
623 | if (!event) { |
624 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
625 | ret = -1; | |
626 | goto end; | |
627 | } | |
628 | ||
629 | if (event->frozen) { | |
630 | BT_LOGW("Invalid parameter: event is frozen: addr=%p, " | |
631 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
632 | event, bt_event_class_get_name(event->event_class), |
633 | bt_event_class_get_id(event->event_class)); | |
f655a84d JG |
634 | ret = -1; |
635 | goto end; | |
636 | } | |
637 | ||
c5c82c6e | 638 | if (context) { |
50842bdc | 639 | field_type = bt_field_get_type(context); |
c5c82c6e | 640 | |
50842bdc | 641 | if (bt_field_type_compare(field_type, |
c5c82c6e PP |
642 | event->event_class->context)) { |
643 | BT_LOGW("Invalid parameter: context field type is different from the expected field type: " | |
644 | "event-addr=%p, event-class-name=\"%s\", " | |
645 | "event-class-id=%" PRId64, | |
646 | event, | |
50842bdc PP |
647 | bt_event_class_get_name(event->event_class), |
648 | bt_event_class_get_id(event->event_class)); | |
c5c82c6e PP |
649 | ret = -1; |
650 | goto end; | |
651 | } | |
652 | } else { | |
653 | if (event->event_class->context) { | |
654 | BT_LOGW("Invalid parameter: setting no event context but event context field type is not NULL: " | |
655 | "event-addr=%p, event-class-name=\"%s\", " | |
656 | "event-class-id=%" PRId64 ", " | |
657 | "event-context-ft-addr=%p", | |
658 | event, | |
50842bdc PP |
659 | bt_event_class_get_name(event->event_class), |
660 | bt_event_class_get_id(event->event_class), | |
c5c82c6e PP |
661 | event->event_class->context); |
662 | ret = -1; | |
663 | goto end; | |
664 | } | |
f655a84d JG |
665 | } |
666 | ||
83509119 | 667 | bt_put(event->context_payload); |
835b2d10 | 668 | event->context_payload = bt_get(context); |
7b010242 PP |
669 | BT_LOGV("Set event's context field: event-addr=%p, " |
670 | "event-class-name=\"%s\", event-class-id=%" PRId64 ", " | |
671 | "context-field-addr=%p", | |
50842bdc PP |
672 | event, bt_event_class_get_name(event->event_class), |
673 | bt_event_class_get_id(event->event_class), context); | |
f655a84d | 674 | end: |
83509119 | 675 | bt_put(field_type); |
f655a84d JG |
676 | return ret; |
677 | } | |
678 | ||
50842bdc PP |
679 | struct bt_field *bt_event_get_stream_event_context( |
680 | struct bt_event *event) | |
5fd2e9fd | 681 | { |
50842bdc | 682 | struct bt_field *stream_event_context = NULL; |
5fd2e9fd | 683 | |
7b010242 PP |
684 | if (!event) { |
685 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
686 | goto end; | |
687 | } | |
688 | ||
689 | if (!event->stream_event_context) { | |
690 | BT_LOGV("Event has no current stream event context field: addr=%p, " | |
691 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
692 | event, bt_event_class_get_name(event->event_class), |
693 | bt_event_class_get_id(event->event_class)); | |
5fd2e9fd PP |
694 | goto end; |
695 | } | |
696 | ||
697 | stream_event_context = event->stream_event_context; | |
698 | end: | |
699 | return bt_get(stream_event_context); | |
700 | } | |
701 | ||
50842bdc PP |
702 | int bt_event_set_stream_event_context(struct bt_event *event, |
703 | struct bt_field *stream_event_context) | |
5fd2e9fd PP |
704 | { |
705 | int ret = 0; | |
50842bdc PP |
706 | struct bt_field_type *field_type = NULL; |
707 | struct bt_stream_class *stream_class = NULL; | |
5fd2e9fd | 708 | |
7b010242 PP |
709 | if (!event) { |
710 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
711 | ret = -1; | |
712 | goto end; | |
713 | } | |
714 | ||
715 | if (event->frozen) { | |
716 | BT_LOGW("Invalid parameter: event is frozen: addr=%p, " | |
717 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
718 | event, bt_event_class_get_name(event->event_class), |
719 | bt_event_class_get_id(event->event_class)); | |
5fd2e9fd PP |
720 | ret = -1; |
721 | goto end; | |
722 | } | |
723 | ||
50842bdc | 724 | stream_class = bt_event_class_get_stream_class(event->event_class); |
5fd2e9fd PP |
725 | /* |
726 | * We should not have been able to create the event without associating | |
727 | * the event class to a stream class. | |
728 | */ | |
729 | assert(stream_class); | |
730 | ||
c5c82c6e | 731 | if (stream_event_context) { |
50842bdc PP |
732 | field_type = bt_field_get_type(stream_event_context); |
733 | if (bt_field_type_compare(field_type, | |
c5c82c6e PP |
734 | stream_class->event_context_type)) { |
735 | BT_LOGW("Invalid parameter: stream event context field type is different from the expected field type: " | |
736 | "event-addr=%p, event-class-name=\"%s\", " | |
737 | "event-class-id=%" PRId64, | |
738 | event, | |
50842bdc PP |
739 | bt_event_class_get_name(event->event_class), |
740 | bt_event_class_get_id(event->event_class)); | |
c5c82c6e PP |
741 | ret = -1; |
742 | goto end; | |
743 | } | |
744 | } else { | |
745 | if (stream_class->event_context_type) { | |
746 | BT_LOGW("Invalid parameter: setting no stream event context but stream event context field type is not NULL: " | |
747 | "event-addr=%p, event-class-name=\"%s\", " | |
748 | "event-class-id=%" PRId64 ", " | |
749 | "stream-event-context-ft-addr=%p", | |
750 | event, | |
50842bdc PP |
751 | bt_event_class_get_name(event->event_class), |
752 | bt_event_class_get_id(event->event_class), | |
c5c82c6e PP |
753 | stream_class->event_context_type); |
754 | ret = -1; | |
755 | goto end; | |
756 | } | |
5fd2e9fd PP |
757 | } |
758 | ||
759 | bt_get(stream_event_context); | |
760 | BT_MOVE(event->stream_event_context, stream_event_context); | |
7b010242 PP |
761 | BT_LOGV("Set event's stream event context field: event-addr=%p, " |
762 | "event-class-name=\"%s\", event-class-id=%" PRId64 ", " | |
763 | "stream-event-context-field-addr=%p", | |
50842bdc PP |
764 | event, bt_event_class_get_name(event->event_class), |
765 | bt_event_class_get_id(event->event_class), | |
7b010242 | 766 | stream_event_context); |
5fd2e9fd PP |
767 | end: |
768 | BT_PUT(stream_class); | |
769 | bt_put(field_type); | |
770 | return ret; | |
771 | } | |
772 | ||
7b010242 | 773 | /* Pre-2.0 CTF writer backward compatibility */ |
50842bdc | 774 | void bt_ctf_event_get(struct bt_event *event) |
273b65be | 775 | { |
83509119 | 776 | bt_get(event); |
273b65be JG |
777 | } |
778 | ||
7b010242 | 779 | /* Pre-2.0 CTF writer backward compatibility */ |
50842bdc | 780 | void bt_ctf_event_put(struct bt_event *event) |
273b65be | 781 | { |
83509119 | 782 | bt_put(event); |
273b65be JG |
783 | } |
784 | ||
50842bdc | 785 | void bt_event_destroy(struct bt_object *obj) |
273b65be | 786 | { |
50842bdc | 787 | struct bt_event *event; |
273b65be | 788 | |
50842bdc | 789 | event = container_of(obj, struct bt_event, base); |
7b010242 PP |
790 | BT_LOGD("Destroying event: addr=%p, " |
791 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
792 | event, bt_event_class_get_name(event->event_class), |
793 | bt_event_class_get_id(event->event_class)); | |
7b010242 | 794 | |
e6a8e8e4 JG |
795 | if (!event->base.parent) { |
796 | /* | |
797 | * Event was keeping a reference to its class since it shared no | |
798 | * common ancestor with it to guarantee they would both have the | |
799 | * same lifetime. | |
800 | */ | |
801 | bt_put(event->event_class); | |
802 | } | |
41ac640a | 803 | g_hash_table_destroy(event->clock_values); |
03039f21 | 804 | BT_LOGD_STR("Putting event's header field."); |
83509119 | 805 | bt_put(event->event_header); |
03039f21 | 806 | BT_LOGD_STR("Putting event's stream event context field."); |
5fd2e9fd | 807 | bt_put(event->stream_event_context); |
03039f21 | 808 | BT_LOGD_STR("Putting event's context field."); |
83509119 | 809 | bt_put(event->context_payload); |
03039f21 | 810 | BT_LOGD_STR("Putting event's payload field."); |
83509119 | 811 | bt_put(event->fields_payload); |
03039f21 | 812 | BT_LOGD_STR("Putting event's packet."); |
5c3b707d | 813 | bt_put(event->packet); |
273b65be JG |
814 | g_free(event); |
815 | } | |
816 | ||
50842bdc PP |
817 | struct bt_clock_value *bt_event_get_clock_value( |
818 | struct bt_event *event, struct bt_clock_class *clock_class) | |
78586d8a | 819 | { |
50842bdc | 820 | struct bt_clock_value *clock_value = NULL; |
78586d8a | 821 | |
ac0c6bdd | 822 | if (!event || !clock_class) { |
7b010242 PP |
823 | BT_LOGW("Invalid parameter: event or clock class is NULL: " |
824 | "event-addr=%p, clock-class-addr=%p", | |
825 | event, clock_class); | |
78586d8a JG |
826 | goto end; |
827 | } | |
828 | ||
ac0c6bdd | 829 | clock_value = g_hash_table_lookup(event->clock_values, clock_class); |
78586d8a | 830 | if (!clock_value) { |
7b010242 PP |
831 | BT_LOGV("No clock value associated to the given clock class: " |
832 | "event-addr=%p, event-class-name=\"%s\", " | |
833 | "event-class-id=%" PRId64 ", clock-class-addr=%p, " | |
834 | "clock-class-name=\"%s\"", event, | |
50842bdc PP |
835 | bt_event_class_get_name(event->event_class), |
836 | bt_event_class_get_id(event->event_class), | |
837 | clock_class, bt_clock_class_get_name(clock_class)); | |
78586d8a JG |
838 | goto end; |
839 | } | |
840 | ||
1556a1af JG |
841 | bt_get(clock_value); |
842 | end: | |
843 | return clock_value; | |
844 | } | |
845 | ||
50842bdc PP |
846 | int bt_event_set_clock_value(struct bt_event *event, |
847 | struct bt_clock_value *value) | |
662e778c JG |
848 | { |
849 | int ret = 0; | |
50842bdc PP |
850 | struct bt_trace *trace; |
851 | struct bt_stream_class *stream_class; | |
852 | struct bt_event_class *event_class; | |
853 | struct bt_clock_class *clock_class = NULL; | |
662e778c | 854 | |
7b010242 PP |
855 | if (!event || !value) { |
856 | BT_LOGW("Invalid parameter: event or clock value is NULL: " | |
857 | "event-addr=%p, clock-value-addr=%p", | |
858 | event, value); | |
859 | ret = -1; | |
860 | goto end; | |
861 | } | |
862 | ||
863 | if (event->frozen) { | |
864 | BT_LOGW("Invalid parameter: event is frozen: addr=%p, " | |
865 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
866 | event, bt_event_class_get_name(event->event_class), |
867 | bt_event_class_get_id(event->event_class)); | |
662e778c JG |
868 | ret = -1; |
869 | goto end; | |
870 | } | |
871 | ||
50842bdc PP |
872 | clock_class = bt_clock_value_get_class(value); |
873 | event_class = bt_event_borrow_event_class(event); | |
c9d90a34 | 874 | assert(event_class); |
50842bdc | 875 | stream_class = bt_event_class_borrow_stream_class(event_class); |
c9d90a34 | 876 | assert(stream_class); |
50842bdc | 877 | trace = bt_stream_class_borrow_trace(stream_class); |
c9d90a34 PP |
878 | assert(trace); |
879 | ||
50842bdc | 880 | if (!bt_trace_has_clock_class(trace, clock_class)) { |
7b010242 PP |
881 | BT_LOGW("Invalid parameter: clock class is not part of event's trace: " |
882 | "event-addr=%p, event-class-name=\"%s\", " | |
883 | "event-class-id=%" PRId64 ", clock-class-addr=%p, " | |
884 | "clock-class-name=\"%s\"", | |
50842bdc PP |
885 | event, bt_event_class_get_name(event->event_class), |
886 | bt_event_class_get_id(event->event_class), | |
887 | clock_class, bt_clock_class_get_name(clock_class)); | |
c9d90a34 PP |
888 | ret = -1; |
889 | goto end; | |
890 | } | |
891 | ||
892 | g_hash_table_insert(event->clock_values, clock_class, bt_get(value)); | |
7b010242 PP |
893 | BT_LOGV("Set event's clock value: " |
894 | "event-addr=%p, event-class-name=\"%s\", " | |
895 | "event-class-id=%" PRId64 ", clock-class-addr=%p, " | |
896 | "clock-class-name=\"%s\", clock-value-addr=%p, " | |
897 | "clock-value-cycles=%" PRIu64, | |
50842bdc PP |
898 | event, bt_event_class_get_name(event->event_class), |
899 | bt_event_class_get_id(event->event_class), | |
900 | clock_class, bt_clock_class_get_name(clock_class), | |
7b010242 | 901 | value, value->value); |
c9d90a34 PP |
902 | clock_class = NULL; |
903 | ||
662e778c | 904 | end: |
c9d90a34 | 905 | bt_put(clock_class); |
662e778c JG |
906 | return ret; |
907 | } | |
908 | ||
273b65be | 909 | BT_HIDDEN |
50842bdc | 910 | int bt_event_validate(struct bt_event *event) |
273b65be JG |
911 | { |
912 | /* Make sure each field's payload has been set */ | |
913 | int ret; | |
50842bdc | 914 | struct bt_stream_class *stream_class = NULL; |
273b65be JG |
915 | |
916 | assert(event); | |
06b019a7 | 917 | if (event->event_header) { |
50842bdc | 918 | ret = bt_field_validate(event->event_header); |
06b019a7 JD |
919 | if (ret) { |
920 | BT_LOGD("Invalid event's header field: " | |
921 | "event-addr=%p, event-class-name=\"%s\", " | |
922 | "event-class-id=%" PRId64, | |
50842bdc PP |
923 | event, bt_event_class_get_name(event->event_class), |
924 | bt_event_class_get_id(event->event_class)); | |
06b019a7 JD |
925 | goto end; |
926 | } | |
662e778c JG |
927 | } |
928 | ||
50842bdc | 929 | stream_class = bt_event_class_get_stream_class(event->event_class); |
5fd2e9fd PP |
930 | /* |
931 | * We should not have been able to create the event without associating | |
932 | * the event class to a stream class. | |
933 | */ | |
934 | assert(stream_class); | |
935 | if (stream_class->event_context_type) { | |
50842bdc | 936 | ret = bt_field_validate(event->stream_event_context); |
5fd2e9fd | 937 | if (ret) { |
7b010242 PP |
938 | BT_LOGD("Invalid event's stream event context field: " |
939 | "event-addr=%p, event-class-name=\"%s\", " | |
940 | "event-class-id=%" PRId64, | |
941 | event, | |
50842bdc PP |
942 | bt_event_class_get_name(event->event_class), |
943 | bt_event_class_get_id(event->event_class)); | |
5fd2e9fd PP |
944 | goto end; |
945 | } | |
946 | } | |
947 | ||
50842bdc | 948 | ret = bt_field_validate(event->fields_payload); |
273b65be | 949 | if (ret) { |
7b010242 PP |
950 | BT_LOGD("Invalid event's payload field: " |
951 | "event-addr=%p, event-class-name=\"%s\", " | |
952 | "event-class-id=%" PRId64, | |
953 | event, | |
50842bdc PP |
954 | bt_event_class_get_name(event->event_class), |
955 | bt_event_class_get_id(event->event_class)); | |
273b65be JG |
956 | goto end; |
957 | } | |
958 | ||
959 | if (event->event_class->context) { | |
7b010242 PP |
960 | BT_LOGD("Invalid event's context field: " |
961 | "event-addr=%p, event-class-name=\"%s\", " | |
962 | "event-class-id=%" PRId64, | |
963 | event, | |
50842bdc PP |
964 | bt_event_class_get_name(event->event_class), |
965 | bt_event_class_get_id(event->event_class)); | |
966 | ret = bt_field_validate(event->context_payload); | |
273b65be JG |
967 | } |
968 | end: | |
5fd2e9fd | 969 | bt_put(stream_class); |
273b65be JG |
970 | return ret; |
971 | } | |
972 | ||
973 | BT_HIDDEN | |
50842bdc PP |
974 | int bt_event_serialize(struct bt_event *event, |
975 | struct bt_stream_pos *pos, | |
976 | enum bt_byte_order native_byte_order) | |
273b65be JG |
977 | { |
978 | int ret = 0; | |
979 | ||
980 | assert(event); | |
981 | assert(pos); | |
dc3fffef | 982 | |
ffffc526 | 983 | BT_LOGV_STR("Serializing event's context field."); |
273b65be | 984 | if (event->context_payload) { |
50842bdc | 985 | ret = bt_field_serialize(event->context_payload, pos, |
dc3fffef | 986 | native_byte_order); |
273b65be | 987 | if (ret) { |
3ee09f3a | 988 | BT_LOGW("Cannot serialize event's context field: " |
7b010242 PP |
989 | "event-addr=%p, event-class-name=\"%s\", " |
990 | "event-class-id=%" PRId64, | |
991 | event, | |
50842bdc PP |
992 | bt_event_class_get_name(event->event_class), |
993 | bt_event_class_get_id(event->event_class)); | |
273b65be JG |
994 | goto end; |
995 | } | |
996 | } | |
997 | ||
ffffc526 | 998 | BT_LOGV_STR("Serializing event's payload field."); |
273b65be | 999 | if (event->fields_payload) { |
50842bdc | 1000 | ret = bt_field_serialize(event->fields_payload, pos, |
dc3fffef | 1001 | native_byte_order); |
273b65be | 1002 | if (ret) { |
3ee09f3a | 1003 | BT_LOGW("Cannot serialize event's payload field: " |
7b010242 PP |
1004 | "event-addr=%p, event-class-name=\"%s\", " |
1005 | "event-class-id=%" PRId64, | |
1006 | event, | |
50842bdc PP |
1007 | bt_event_class_get_name(event->event_class), |
1008 | bt_event_class_get_id(event->event_class)); | |
273b65be JG |
1009 | goto end; |
1010 | } | |
1011 | } | |
1012 | end: | |
1013 | return ret; | |
1014 | } | |
1015 | ||
50842bdc | 1016 | struct bt_packet *bt_event_get_packet(struct bt_event *event) |
5c0f40f4 | 1017 | { |
50842bdc | 1018 | struct bt_packet *packet = NULL; |
5c0f40f4 | 1019 | |
7b010242 PP |
1020 | if (!event) { |
1021 | BT_LOGW_STR("Invalid parameter: event is NULL."); | |
1022 | goto end; | |
1023 | } | |
1024 | ||
1025 | if (!event->packet) { | |
1026 | BT_LOGV("Event has no current packet: addr=%p, " | |
1027 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
1028 | event, bt_event_class_get_name(event->event_class), |
1029 | bt_event_class_get_id(event->event_class)); | |
5c0f40f4 JG |
1030 | goto end; |
1031 | } | |
1032 | ||
1033 | packet = bt_get(event->packet); | |
1034 | end: | |
1035 | return packet; | |
1036 | } | |
1037 | ||
50842bdc PP |
1038 | int bt_event_set_packet(struct bt_event *event, |
1039 | struct bt_packet *packet) | |
5c3b707d | 1040 | { |
50842bdc PP |
1041 | struct bt_stream_class *event_stream_class = NULL; |
1042 | struct bt_stream_class *packet_stream_class = NULL; | |
1043 | struct bt_stream *stream = NULL; | |
5c3b707d PP |
1044 | int ret = 0; |
1045 | ||
7b010242 PP |
1046 | if (!event || !packet) { |
1047 | BT_LOGW("Invalid parameter: event or packet is NULL: " | |
1048 | "event-addr=%p, packet-addr=%p", | |
1049 | event, packet); | |
1050 | ret = -1; | |
1051 | goto end; | |
1052 | } | |
1053 | ||
1054 | if (event->frozen) { | |
1055 | BT_LOGW("Invalid parameter: event is frozen: addr=%p, " | |
1056 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
1057 | event, bt_event_class_get_name(event->event_class), |
1058 | bt_event_class_get_id(event->event_class)); | |
5c3b707d PP |
1059 | ret = -1; |
1060 | goto end; | |
1061 | } | |
1062 | ||
1063 | /* | |
1064 | * Make sure the new packet was created by this event's | |
1065 | * stream, if it is set. | |
1066 | */ | |
50842bdc | 1067 | stream = bt_event_get_stream(event); |
5c3b707d PP |
1068 | if (stream) { |
1069 | if (packet->stream != stream) { | |
7b010242 PP |
1070 | BT_LOGW("Invalid parameter: packet's stream and event's stream differ: " |
1071 | "event-addr=%p, event-class-name=\"%s\", " | |
1072 | "event-class-id=%" PRId64 ", packet-stream-addr=%p, " | |
1073 | "event-stream-addr=%p", | |
50842bdc PP |
1074 | event, bt_event_class_get_name(event->event_class), |
1075 | bt_event_class_get_id(event->event_class), | |
7b010242 | 1076 | packet->stream, stream); |
5c3b707d PP |
1077 | ret = -1; |
1078 | goto end; | |
1079 | } | |
1080 | } else { | |
b2b635e9 | 1081 | event_stream_class = |
50842bdc | 1082 | bt_event_class_get_stream_class(event->event_class); |
b2b635e9 | 1083 | packet_stream_class = |
50842bdc | 1084 | bt_stream_get_class(packet->stream); |
b2b635e9 PP |
1085 | |
1086 | assert(event_stream_class); | |
1087 | assert(packet_stream_class); | |
1088 | ||
1089 | if (event_stream_class != packet_stream_class) { | |
7b010242 PP |
1090 | BT_LOGW("Invalid parameter: packet's stream class and event's stream class differ: " |
1091 | "event-addr=%p, event-class-name=\"%s\", " | |
1092 | "event-class-id=%" PRId64 ", packet-stream-class-addr=%p, " | |
1093 | "event-stream-class-addr=%p", | |
50842bdc PP |
1094 | event, bt_event_class_get_name(event->event_class), |
1095 | bt_event_class_get_id(event->event_class), | |
7b010242 | 1096 | packet_stream_class, event_stream_class); |
b2b635e9 PP |
1097 | ret = -1; |
1098 | goto end; | |
1099 | } | |
5c3b707d PP |
1100 | } |
1101 | ||
cacf3147 PP |
1102 | bt_get(packet); |
1103 | BT_MOVE(event->packet, packet); | |
7b010242 PP |
1104 | BT_LOGV("Set event's packet: event-addr=%p, " |
1105 | "event-class-name=\"%s\", event-class-id=%" PRId64 ", " | |
1106 | "packet-addr=%p", | |
50842bdc PP |
1107 | event, bt_event_class_get_name(event->event_class), |
1108 | bt_event_class_get_id(event->event_class), packet); | |
5c3b707d PP |
1109 | |
1110 | end: | |
1111 | BT_PUT(stream); | |
b2b635e9 PP |
1112 | BT_PUT(event_stream_class); |
1113 | BT_PUT(packet_stream_class); | |
5c3b707d PP |
1114 | |
1115 | return ret; | |
1116 | } | |
4ce9f9d0 PP |
1117 | |
1118 | BT_HIDDEN | |
50842bdc | 1119 | void bt_event_freeze(struct bt_event *event) |
4ce9f9d0 PP |
1120 | { |
1121 | assert(event); | |
7b010242 PP |
1122 | |
1123 | if (event->frozen) { | |
1124 | return; | |
1125 | } | |
1126 | ||
1127 | BT_LOGD("Freezing event: addr=%p, " | |
1128 | "event-class-name=\"%s\", event-class-id=%" PRId64, | |
50842bdc PP |
1129 | event, bt_event_class_get_name(event->event_class), |
1130 | bt_event_class_get_id(event->event_class)); | |
1131 | bt_packet_freeze(event->packet); | |
03039f21 | 1132 | BT_LOGD_STR("Freezing event's header field."); |
50842bdc | 1133 | bt_field_freeze(event->event_header); |
03039f21 | 1134 | BT_LOGD_STR("Freezing event's stream event context field."); |
50842bdc | 1135 | bt_field_freeze(event->stream_event_context); |
03039f21 | 1136 | BT_LOGD_STR("Freezing event's context field."); |
50842bdc | 1137 | bt_field_freeze(event->context_payload); |
03039f21 | 1138 | BT_LOGD_STR("Freezing event's payload field."); |
50842bdc | 1139 | bt_field_freeze(event->fields_payload); |
4ce9f9d0 PP |
1140 | event->frozen = 1; |
1141 | } |