Fix: loglevel and model_emf_uri build fix
[lttng-ust.git] / include / lttng / ust-tracepoint-event.h
CommitLineData
1c324e59 1/*
e92f3e28 2 * Copyright (c) 2011-2012 - Mathieu Desnoyers <mathieu.desnoyers@efficios.com>
1c324e59 3 *
e92f3e28
MD
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is
9 * furnished to do so, subject to the following conditions:
1c324e59 10 *
e92f3e28
MD
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
d2428e87
MD
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20 * SOFTWARE.
1c324e59
MD
21 */
22
23#include <stdio.h>
7d381d6e 24#include <stdlib.h>
1c324e59 25#include <urcu/compiler.h>
f488575f 26#include <urcu/rculist.h>
1c324e59 27#include <lttng/ust-events.h>
1c324e59 28#include <lttng/ringbuffer-config.h>
a8909ba5 29#include <lttng/ust-compiler.h>
000b8662 30#include <lttng/tracepoint.h>
714c16c4 31#include <byteswap.h>
44c72f10 32#include <string.h>
1c324e59 33
000b8662
MD
34#undef tp_list_for_each_entry_rcu
35#define tp_list_for_each_entry_rcu(pos, head, member) \
36 for (pos = cds_list_entry(tp_rcu_dereference_bp((head)->next), __typeof__(*pos), member); \
37 &pos->member != (head); \
38 pos = cds_list_entry(tp_rcu_dereference_bp(pos->member.next), __typeof__(*pos), member))
39
1c324e59
MD
40/*
41 * TRACEPOINT_EVENT_CLASS declares a class of tracepoints receiving the
42 * same arguments and having the same field layout.
43 *
44 * TRACEPOINT_EVENT_INSTANCE declares an instance of a tracepoint, with
45 * its own provider and name. It refers to a class (template).
46 *
47 * TRACEPOINT_EVENT declared both a class and an instance and does a
48 * direct mapping from the instance to the class.
49 */
50
51#undef TRACEPOINT_EVENT
52#define TRACEPOINT_EVENT(_provider, _name, _args, _fields) \
53 TRACEPOINT_EVENT_CLASS(_provider, _name, \
54 _TP_PARAMS(_args), \
55 _TP_PARAMS(_fields)) \
56 TRACEPOINT_EVENT_INSTANCE(_provider, _name, _name, \
68755429 57 _TP_PARAMS(_args))
1c324e59
MD
58
59/* Helpers */
60#define _TP_ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0]))
61
62#define _tp_max_t(type, x, y) \
63 ({ \
64 type __max1 = (x); \
65 type __max2 = (y); \
66 __max1 > __max2 ? __max1: __max2; \
67 })
68
69/*
70 * Stage 0 of tracepoint event generation.
71 *
72 * Check that each TRACEPOINT_EVENT provider argument match the
73 * TRACEPOINT_PROVIDER by creating dummy callbacks.
74 */
75
76/* Reset all macros within TRACEPOINT_EVENT */
77#include <lttng/ust-tracepoint-event-reset.h>
78
7ce6b21d
PW
79static inline lttng_ust_notrace
80void _TP_COMBINE_TOKENS(__tracepoint_provider_mismatch_, TRACEPOINT_PROVIDER)(void);
1c324e59
MD
81static inline
82void _TP_COMBINE_TOKENS(__tracepoint_provider_mismatch_, TRACEPOINT_PROVIDER)(void)
83{
84}
85
86#undef TRACEPOINT_EVENT_CLASS
87#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
88 __tracepoint_provider_mismatch_##_provider();
89
90#undef TRACEPOINT_EVENT_INSTANCE
91#define TRACEPOINT_EVENT_INSTANCE(_provider, _template, _name, _args) \
92 __tracepoint_provider_mismatch_##_provider();
93
7ce6b21d
PW
94static inline lttng_ust_notrace
95void _TP_COMBINE_TOKENS(__tracepoint_provider_check_, TRACEPOINT_PROVIDER)(void);
e8bd1da7 96static inline
1c324e59
MD
97void _TP_COMBINE_TOKENS(__tracepoint_provider_check_, TRACEPOINT_PROVIDER)(void)
98{
99#include TRACEPOINT_INCLUDE
100}
101
f56cd1d5
MD
102/*
103 * Stage 0.1 of tracepoint event generation.
104 *
105 * Check that each TRACEPOINT_EVENT provider:name does not exceed the
106 * tracepoint name length limit.
107 */
108
109/* Reset all macros within TRACEPOINT_EVENT */
110#include <lttng/ust-tracepoint-event-reset.h>
111
112#undef TRACEPOINT_EVENT_INSTANCE
113#define TRACEPOINT_EVENT_INSTANCE(_provider, _template, _name, _args) \
114static const char \
115 __tp_name_len_check##_provider##___##_name[LTTNG_UST_SYM_NAME_LEN] \
116 __attribute__((unused)) = \
117 #_provider ":" #_name;
118
119#include TRACEPOINT_INCLUDE
120
1c324e59
MD
121/*
122 * Stage 1 of tracepoint event generation.
123 *
124 * Create event field type metadata section.
125 * Each event produce an array of fields.
126 */
127
128/* Reset all macros within TRACEPOINT_EVENT */
129#include <lttng/ust-tracepoint-event-reset.h>
4774c8f3
MD
130#include <lttng/ust-tracepoint-event-write.h>
131#include <lttng/ust-tracepoint-event-nowrite.h>
1c324e59 132
4774c8f3 133#undef _ctf_integer_ext
180901e6 134#define _ctf_integer_ext(_type, _item, _src, _byte_order, _base, _nowrite) \
1c324e59
MD
135 { \
136 .name = #_item, \
137 .type = __type_integer(_type, _byte_order, _base, none),\
180901e6 138 .nowrite = _nowrite, \
1c324e59
MD
139 },
140
4774c8f3 141#undef _ctf_float
180901e6 142#define _ctf_float(_type, _item, _src, _nowrite) \
1c324e59
MD
143 { \
144 .name = #_item, \
145 .type = __type_float(_type), \
180901e6 146 .nowrite = _nowrite, \
1c324e59
MD
147 },
148
4774c8f3 149#undef _ctf_array_encoded
180901e6 150#define _ctf_array_encoded(_type, _item, _src, _length, _encoding, _nowrite) \
1c324e59
MD
151 { \
152 .name = #_item, \
153 .type = \
154 { \
155 .atype = atype_array, \
46d52200 156 .u = \
1c324e59 157 { \
46d52200
ZT
158 .array = \
159 { \
160 .elem_type = __type_integer(_type, BYTE_ORDER, 10, _encoding), \
161 .length = _length, \
162 } \
163 } \
1c324e59 164 }, \
180901e6 165 .nowrite = _nowrite, \
1c324e59
MD
166 },
167
4774c8f3 168#undef _ctf_sequence_encoded
f968510a
PP
169#define _ctf_sequence_encoded(_type, _item, _src, \
170 _length_type, _src_length, _encoding, _nowrite, \
171 _elem_type_base) \
1c324e59
MD
172 { \
173 .name = #_item, \
174 .type = \
175 { \
176 .atype = atype_sequence, \
46d52200 177 .u = \
1c324e59 178 { \
46d52200
ZT
179 .sequence = \
180 { \
181 .length_type = __type_integer(_length_type, BYTE_ORDER, 10, none), \
f968510a 182 .elem_type = __type_integer(_type, BYTE_ORDER, _elem_type_base, _encoding), \
46d52200 183 }, \
1c324e59
MD
184 }, \
185 }, \
180901e6 186 .nowrite = _nowrite, \
1c324e59
MD
187 },
188
4774c8f3 189#undef _ctf_string
180901e6 190#define _ctf_string(_item, _src, _nowrite) \
1c324e59
MD
191 { \
192 .name = #_item, \
193 .type = \
194 { \
195 .atype = atype_string, \
46d52200
ZT
196 .u = \
197 { \
198 .basic = { .string = { .encoding = lttng_encode_UTF8 } } \
199 }, \
1c324e59 200 }, \
180901e6 201 .nowrite = _nowrite, \
1c324e59
MD
202 },
203
204#undef TP_FIELDS
2eda209b 205#define TP_FIELDS(...) __VA_ARGS__ /* Only one used in this phase */
1c324e59
MD
206
207#undef TRACEPOINT_EVENT_CLASS
208#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
209 static const struct lttng_event_field __event_fields___##_provider##___##_name[] = { \
210 _fields \
0febf018 211 ctf_integer(int, dummy, 0) /* Dummy, C99 forbids 0-len array. */ \
1c324e59
MD
212 };
213
214#include TRACEPOINT_INCLUDE
215
216/*
217 * Stage 2 of tracepoint event generation.
218 *
219 * Create probe callback prototypes.
220 */
221
222/* Reset all macros within TRACEPOINT_EVENT */
223#include <lttng/ust-tracepoint-event-reset.h>
224
225#undef TP_ARGS
2eda209b 226#define TP_ARGS(...) __VA_ARGS__
1c324e59
MD
227
228#undef TRACEPOINT_EVENT_CLASS
229#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
230static void __event_probe__##_provider##___##_name(_TP_ARGS_DATA_PROTO(_args));
231
232#include TRACEPOINT_INCLUDE
233
234/*
235 * Stage 3 of tracepoint event generation.
236 *
1c324e59
MD
237 * Create static inline function that calculates event size.
238 */
239
240/* Reset all macros within TRACEPOINT_EVENT */
241#include <lttng/ust-tracepoint-event-reset.h>
4774c8f3 242#include <lttng/ust-tracepoint-event-write.h>
1c324e59 243
4774c8f3 244#undef _ctf_integer_ext
180901e6 245#define _ctf_integer_ext(_type, _item, _src, _byte_order, _base, _nowrite) \
1c324e59
MD
246 __event_len += lib_ring_buffer_align(__event_len, lttng_alignof(_type)); \
247 __event_len += sizeof(_type);
248
4774c8f3 249#undef _ctf_float
180901e6 250#define _ctf_float(_type, _item, _src, _nowrite) \
1c324e59
MD
251 __event_len += lib_ring_buffer_align(__event_len, lttng_alignof(_type)); \
252 __event_len += sizeof(_type);
253
4774c8f3 254#undef _ctf_array_encoded
180901e6 255#define _ctf_array_encoded(_type, _item, _src, _length, _encoding, _nowrite) \
1c324e59
MD
256 __event_len += lib_ring_buffer_align(__event_len, lttng_alignof(_type)); \
257 __event_len += sizeof(_type) * (_length);
258
4774c8f3 259#undef _ctf_sequence_encoded
f968510a
PP
260#define _ctf_sequence_encoded(_type, _item, _src, _length_type, \
261 _src_length, _encoding, _nowrite, _elem_type_base) \
1c324e59
MD
262 __event_len += lib_ring_buffer_align(__event_len, lttng_alignof(_length_type)); \
263 __event_len += sizeof(_length_type); \
264 __event_len += lib_ring_buffer_align(__event_len, lttng_alignof(_type)); \
265 __dynamic_len[__dynamic_len_idx] = (_src_length); \
266 __event_len += sizeof(_type) * __dynamic_len[__dynamic_len_idx]; \
267 __dynamic_len_idx++;
268
4774c8f3 269#undef _ctf_string
180901e6 270#define _ctf_string(_item, _src, _nowrite) \
1c324e59
MD
271 __event_len += __dynamic_len[__dynamic_len_idx++] = strlen(_src) + 1;
272
273#undef TP_ARGS
2eda209b 274#define TP_ARGS(...) __VA_ARGS__
1c324e59
MD
275
276#undef TP_FIELDS
2eda209b 277#define TP_FIELDS(...) __VA_ARGS__
1c324e59
MD
278
279#undef TRACEPOINT_EVENT_CLASS
a8909ba5
PW
280#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
281static inline lttng_ust_notrace \
282size_t __event_get_size__##_provider##___##_name(size_t *__dynamic_len, _TP_ARGS_DATA_PROTO(_args)); \
283static inline \
284size_t __event_get_size__##_provider##___##_name(size_t *__dynamic_len, _TP_ARGS_DATA_PROTO(_args)) \
1c324e59
MD
285{ \
286 size_t __event_len = 0; \
287 unsigned int __dynamic_len_idx = 0; \
288 \
289 if (0) \
290 (void) __dynamic_len_idx; /* don't warn if unused */ \
291 _fields \
292 return __event_len; \
293}
294
295#include TRACEPOINT_INCLUDE
296
1ddfd641
MD
297/*
298 * Stage 3.1 of tracepoint event generation.
299 *
300 * Create static inline function that layout the filter stack data.
4774c8f3 301 * We make both write and nowrite data available to the filter.
1ddfd641
MD
302 */
303
304/* Reset all macros within TRACEPOINT_EVENT */
305#include <lttng/ust-tracepoint-event-reset.h>
4774c8f3
MD
306#include <lttng/ust-tracepoint-event-write.h>
307#include <lttng/ust-tracepoint-event-nowrite.h>
1ddfd641 308
4774c8f3 309#undef _ctf_integer_ext
180901e6 310#define _ctf_integer_ext(_type, _item, _src, _byte_order, _base, _nowrite) \
fa099471 311 if (lttng_is_signed_type(_type)) { \
3ebeea0d
MD
312 int64_t __ctf_tmp_int64; \
313 switch (sizeof(_type)) { \
314 case 1: \
315 { \
316 union { _type t; int8_t v; } __tmp = { (_type) (_src) }; \
317 __ctf_tmp_int64 = (int64_t) __tmp.v; \
318 break; \
319 } \
320 case 2: \
321 { \
322 union { _type t; int16_t v; } __tmp = { (_type) (_src) }; \
714c16c4
MD
323 if (_byte_order != BYTE_ORDER) \
324 __tmp.v = bswap_16(__tmp.v); \
3ebeea0d
MD
325 __ctf_tmp_int64 = (int64_t) __tmp.v; \
326 break; \
327 } \
328 case 4: \
329 { \
330 union { _type t; int32_t v; } __tmp = { (_type) (_src) }; \
714c16c4
MD
331 if (_byte_order != BYTE_ORDER) \
332 __tmp.v = bswap_32(__tmp.v); \
3ebeea0d
MD
333 __ctf_tmp_int64 = (int64_t) __tmp.v; \
334 break; \
335 } \
336 case 8: \
337 { \
338 union { _type t; int64_t v; } __tmp = { (_type) (_src) }; \
714c16c4
MD
339 if (_byte_order != BYTE_ORDER) \
340 __tmp.v = bswap_64(__tmp.v); \
3ebeea0d
MD
341 __ctf_tmp_int64 = (int64_t) __tmp.v; \
342 break; \
343 } \
344 default: \
345 abort(); \
346 }; \
fa099471
MD
347 memcpy(__stack_data, &__ctf_tmp_int64, sizeof(int64_t)); \
348 } else { \
3ebeea0d
MD
349 uint64_t __ctf_tmp_uint64; \
350 switch (sizeof(_type)) { \
351 case 1: \
352 { \
353 union { _type t; uint8_t v; } __tmp = { (_type) (_src) }; \
354 __ctf_tmp_uint64 = (uint64_t) __tmp.v; \
355 break; \
356 } \
357 case 2: \
358 { \
359 union { _type t; uint16_t v; } __tmp = { (_type) (_src) }; \
714c16c4
MD
360 if (_byte_order != BYTE_ORDER) \
361 __tmp.v = bswap_16(__tmp.v); \
3ebeea0d
MD
362 __ctf_tmp_uint64 = (uint64_t) __tmp.v; \
363 break; \
364 } \
365 case 4: \
366 { \
367 union { _type t; uint32_t v; } __tmp = { (_type) (_src) }; \
714c16c4
MD
368 if (_byte_order != BYTE_ORDER) \
369 __tmp.v = bswap_32(__tmp.v); \
3ebeea0d
MD
370 __ctf_tmp_uint64 = (uint64_t) __tmp.v; \
371 break; \
372 } \
373 case 8: \
374 { \
375 union { _type t; uint64_t v; } __tmp = { (_type) (_src) }; \
714c16c4
MD
376 if (_byte_order != BYTE_ORDER) \
377 __tmp.v = bswap_64(__tmp.v); \
3ebeea0d
MD
378 __ctf_tmp_uint64 = (uint64_t) __tmp.v; \
379 break; \
380 } \
381 default: \
382 abort(); \
383 }; \
fa099471
MD
384 memcpy(__stack_data, &__ctf_tmp_uint64, sizeof(uint64_t)); \
385 } \
1ddfd641
MD
386 __stack_data += sizeof(int64_t);
387
4774c8f3 388#undef _ctf_float
180901e6 389#define _ctf_float(_type, _item, _src, _nowrite) \
fa099471
MD
390 { \
391 double __ctf_tmp_double = (double) (_type) (_src); \
392 memcpy(__stack_data, &__ctf_tmp_double, sizeof(double)); \
393 __stack_data += sizeof(double); \
394 }
1ddfd641 395
4774c8f3 396#undef _ctf_array_encoded
180901e6 397#define _ctf_array_encoded(_type, _item, _src, _length, _encoding, _nowrite) \
fa099471
MD
398 { \
399 unsigned long __ctf_tmp_ulong = (unsigned long) (_length); \
59034aab 400 const void *__ctf_tmp_ptr = (_src); \
fa099471
MD
401 memcpy(__stack_data, &__ctf_tmp_ulong, sizeof(unsigned long)); \
402 __stack_data += sizeof(unsigned long); \
b1239ad6
MD
403 memcpy(__stack_data, &__ctf_tmp_ptr, sizeof(void *)); \
404 __stack_data += sizeof(void *); \
fa099471 405 }
1ddfd641 406
4774c8f3
MD
407#undef _ctf_sequence_encoded
408#define _ctf_sequence_encoded(_type, _item, _src, _length_type, \
f968510a 409 _src_length, _encoding, _nowrite, _elem_type_base) \
fa099471
MD
410 { \
411 unsigned long __ctf_tmp_ulong = (unsigned long) (_src_length); \
59034aab 412 const void *__ctf_tmp_ptr = (_src); \
fa099471
MD
413 memcpy(__stack_data, &__ctf_tmp_ulong, sizeof(unsigned long)); \
414 __stack_data += sizeof(unsigned long); \
b1239ad6
MD
415 memcpy(__stack_data, &__ctf_tmp_ptr, sizeof(void *)); \
416 __stack_data += sizeof(void *); \
fa099471 417 }
1ddfd641 418
4774c8f3 419#undef _ctf_string
180901e6 420#define _ctf_string(_item, _src, _nowrite) \
fa099471 421 { \
59034aab 422 const void *__ctf_tmp_ptr = (_src); \
b1239ad6
MD
423 memcpy(__stack_data, &__ctf_tmp_ptr, sizeof(void *)); \
424 __stack_data += sizeof(void *); \
fa099471 425 }
1ddfd641
MD
426
427#undef TP_ARGS
428#define TP_ARGS(...) __VA_ARGS__
429
430#undef TP_FIELDS
431#define TP_FIELDS(...) __VA_ARGS__
432
433#undef TRACEPOINT_EVENT_CLASS
434#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
435static inline \
436void __event_prepare_filter_stack__##_provider##___##_name(char *__stack_data,\
437 _TP_ARGS_DATA_PROTO(_args)) \
438{ \
439 _fields \
440}
441
442#include TRACEPOINT_INCLUDE
443
444
445
1c324e59 446/*
df854e41 447 * Stage 4 of tracepoint event generation.
1c324e59
MD
448 *
449 * Create static inline function that calculates event payload alignment.
450 */
451
452/* Reset all macros within TRACEPOINT_EVENT */
453#include <lttng/ust-tracepoint-event-reset.h>
4774c8f3 454#include <lttng/ust-tracepoint-event-write.h>
1c324e59 455
4774c8f3 456#undef _ctf_integer_ext
180901e6 457#define _ctf_integer_ext(_type, _item, _src, _byte_order, _base, _nowrite) \
1c324e59
MD
458 __event_align = _tp_max_t(size_t, __event_align, lttng_alignof(_type));
459
4774c8f3 460#undef _ctf_float
180901e6 461#define _ctf_float(_type, _item, _src, _nowrite) \
1c324e59
MD
462 __event_align = _tp_max_t(size_t, __event_align, lttng_alignof(_type));
463
4774c8f3 464#undef _ctf_array_encoded
180901e6 465#define _ctf_array_encoded(_type, _item, _src, _length, _encoding, _nowrite) \
1c324e59
MD
466 __event_align = _tp_max_t(size_t, __event_align, lttng_alignof(_type));
467
4774c8f3 468#undef _ctf_sequence_encoded
f968510a
PP
469#define _ctf_sequence_encoded(_type, _item, _src, _length_type, \
470 _src_length, _encoding, _nowrite, _elem_type_base) \
1c324e59
MD
471 __event_align = _tp_max_t(size_t, __event_align, lttng_alignof(_length_type)); \
472 __event_align = _tp_max_t(size_t, __event_align, lttng_alignof(_type));
473
4774c8f3 474#undef _ctf_string
180901e6 475#define _ctf_string(_item, _src, _nowrite)
1c324e59
MD
476
477#undef TP_ARGS
2eda209b 478#define TP_ARGS(...) __VA_ARGS__
1c324e59
MD
479
480#undef TP_FIELDS
2eda209b 481#define TP_FIELDS(...) __VA_ARGS__
1c324e59
MD
482
483#undef TRACEPOINT_EVENT_CLASS
484#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
a8909ba5
PW
485static inline lttng_ust_notrace \
486size_t __event_get_align__##_provider##___##_name(_TP_ARGS_PROTO(_args)); \
1c324e59
MD
487static inline \
488size_t __event_get_align__##_provider##___##_name(_TP_ARGS_PROTO(_args)) \
489{ \
490 size_t __event_align = 1; \
491 _fields \
492 return __event_align; \
493}
494
495#include TRACEPOINT_INCLUDE
496
497
498/*
df854e41 499 * Stage 5 of tracepoint event generation.
1c324e59
MD
500 *
501 * Create the probe function. This function calls event size calculation
502 * and writes event data into the buffer.
503 */
504
505/* Reset all macros within TRACEPOINT_EVENT */
506#include <lttng/ust-tracepoint-event-reset.h>
4774c8f3 507#include <lttng/ust-tracepoint-event-write.h>
1c324e59 508
4774c8f3 509#undef _ctf_integer_ext
180901e6 510#define _ctf_integer_ext(_type, _item, _src, _byte_order, _base, _nowrite) \
1c324e59
MD
511 { \
512 _type __tmp = (_src); \
513 lib_ring_buffer_align_ctx(&__ctx, lttng_alignof(__tmp));\
514 __chan->ops->event_write(&__ctx, &__tmp, sizeof(__tmp));\
515 }
516
4774c8f3 517#undef _ctf_float
180901e6 518#define _ctf_float(_type, _item, _src, _nowrite) \
1c324e59
MD
519 { \
520 _type __tmp = (_src); \
521 lib_ring_buffer_align_ctx(&__ctx, lttng_alignof(__tmp));\
522 __chan->ops->event_write(&__ctx, &__tmp, sizeof(__tmp));\
523 }
524
4774c8f3 525#undef _ctf_array_encoded
180901e6 526#define _ctf_array_encoded(_type, _item, _src, _length, _encoding, _nowrite) \
1c324e59
MD
527 lib_ring_buffer_align_ctx(&__ctx, lttng_alignof(_type)); \
528 __chan->ops->event_write(&__ctx, _src, sizeof(_type) * (_length));
529
4774c8f3
MD
530#undef _ctf_sequence_encoded
531#define _ctf_sequence_encoded(_type, _item, _src, _length_type, \
f968510a 532 _src_length, _encoding, _nowrite, _elem_type_base) \
1c324e59 533 { \
d71b57b9 534 _length_type __tmpl = __stackvar.__dynamic_len[__dynamic_len_idx]; \
1c324e59
MD
535 lib_ring_buffer_align_ctx(&__ctx, lttng_alignof(_length_type));\
536 __chan->ops->event_write(&__ctx, &__tmpl, sizeof(_length_type));\
537 } \
538 lib_ring_buffer_align_ctx(&__ctx, lttng_alignof(_type)); \
539 __chan->ops->event_write(&__ctx, _src, \
540 sizeof(_type) * __get_dynamic_len(dest));
541
a44c74d9
MD
542/*
543 * __chan->ops->u.has_strcpy is a flag letting us know if the LTTng-UST
544 * tracepoint provider ABI implements event_strcpy. This dynamic check
545 * can be removed when the tracepoint provider ABI moves to 2.
546 */
547#if (LTTNG_UST_PROVIDER_MAJOR > 1)
548#error "Tracepoint probe provider major version has changed. Please remove dynamic check for has_strcpy."
549#endif
550
4774c8f3 551#undef _ctf_string
180901e6 552#define _ctf_string(_item, _src, _nowrite) \
1c324e59 553 lib_ring_buffer_align_ctx(&__ctx, lttng_alignof(*(_src))); \
a44c74d9
MD
554 if (__chan->ops->u.has_strcpy) \
555 __chan->ops->event_strcpy(&__ctx, _src, \
556 __get_dynamic_len(dest)); \
557 else \
558 __chan->ops->event_write(&__ctx, _src, \
559 __get_dynamic_len(dest));
1c324e59
MD
560
561/* Beware: this get len actually consumes the len value */
562#undef __get_dynamic_len
d71b57b9 563#define __get_dynamic_len(field) __stackvar.__dynamic_len[__dynamic_len_idx++]
1c324e59
MD
564
565#undef TP_ARGS
2eda209b 566#define TP_ARGS(...) __VA_ARGS__
1c324e59
MD
567
568#undef TP_FIELDS
2eda209b 569#define TP_FIELDS(...) __VA_ARGS__
1c324e59 570
95c25348
PW
571/*
572 * For state dump, check that "session" argument (mandatory) matches the
573 * session this event belongs to. Ensures that we write state dump data only
574 * into the started session, not into all sessions.
575 */
576#undef _TP_SESSION_CHECK
577#ifdef TP_SESSION_CHECK
578#define _TP_SESSION_CHECK(session, csession) (session == csession)
579#else /* TP_SESSION_CHECK */
580#define _TP_SESSION_CHECK(session, csession) 1
581#endif /* TP_SESSION_CHECK */
582
800ceaa5
MD
583/*
584 * Use of __builtin_return_address(0) sometimes seems to cause stack
585 * corruption on 32-bit PowerPC. Disable this feature on that
586 * architecture for now by always using the NULL value for the ip
587 * context.
588 */
5dadb547
MD
589#undef _TP_IP_PARAM
590#ifdef TP_IP_PARAM
e1d09f9e 591#define _TP_IP_PARAM(x) (x)
5dadb547 592#else /* TP_IP_PARAM */
800ceaa5
MD
593
594#if defined(__PPC__) && !defined(__PPC64__)
595#define _TP_IP_PARAM(x) NULL
596#else /* #if defined(__PPC__) && !defined(__PPC64__) */
e1d09f9e 597#define _TP_IP_PARAM(x) __builtin_return_address(0)
800ceaa5
MD
598#endif /* #else #if defined(__PPC__) && !defined(__PPC64__) */
599
5dadb547
MD
600#endif /* TP_IP_PARAM */
601
1ddfd641
MD
602/*
603 * Using twice size for filter stack data to hold size and pointer for
604 * each field (worse case). For integers, max size required is 64-bit.
605 * Same for double-precision floats. Those fit within
606 * 2*sizeof(unsigned long) for all supported architectures.
61ce3223 607 * Perform UNION (||) of filter runtime list.
1ddfd641 608 */
1c324e59
MD
609#undef TRACEPOINT_EVENT_CLASS
610#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
a8909ba5
PW
611static lttng_ust_notrace \
612void __event_probe__##_provider##___##_name(_TP_ARGS_DATA_PROTO(_args)); \
613static \
614void __event_probe__##_provider##___##_name(_TP_ARGS_DATA_PROTO(_args)) \
1c324e59 615{ \
46d52200 616 struct lttng_event *__event = (struct lttng_event *) __tp_data; \
7dd08bec 617 struct lttng_channel *__chan = __event->chan; \
f280cb51 618 struct lttng_ust_lib_ring_buffer_ctx __ctx; \
1c324e59
MD
619 size_t __event_len, __event_align; \
620 size_t __dynamic_len_idx = 0; \
d71b57b9 621 union { \
0febf018
MD
622 size_t __dynamic_len[_TP_ARRAY_SIZE(__event_fields___##_provider##___##_name) - 1]; \
623 char __filter_stack_data[2 * sizeof(unsigned long) * (_TP_ARRAY_SIZE(__event_fields___##_provider##___##_name) - 1)]; \
d71b57b9 624 } __stackvar; \
1c324e59
MD
625 int __ret; \
626 \
627 if (0) \
628 (void) __dynamic_len_idx; /* don't warn if unused */ \
95c25348
PW
629 if (!_TP_SESSION_CHECK(session, __chan->session)) \
630 return; \
1c324e59
MD
631 if (caa_unlikely(!CMM_ACCESS_ONCE(__chan->session->active))) \
632 return; \
633 if (caa_unlikely(!CMM_ACCESS_ONCE(__chan->enabled))) \
634 return; \
635 if (caa_unlikely(!CMM_ACCESS_ONCE(__event->enabled))) \
636 return; \
1b436e01
MD
637 if (caa_unlikely(!TP_RCU_LINK_TEST())) \
638 return; \
e58095ef 639 if (caa_unlikely(!cds_list_empty(&__event->bytecode_runtime_head))) { \
f488575f 640 struct lttng_bytecode_runtime *bc_runtime; \
dcdeaff0 641 int __filter_record = __event->has_enablers_without_bytecode; \
f488575f 642 \
1ddfd641 643 __event_prepare_filter_stack__##_provider##___##_name(__stackvar.__filter_stack_data, \
f488575f 644 _TP_ARGS_DATA_VAR(_args)); \
000b8662 645 tp_list_for_each_entry_rcu(bc_runtime, &__event->bytecode_runtime_head, node) { \
61ce3223 646 if (caa_unlikely(bc_runtime->filter(bc_runtime, \
8a92ed2a
MD
647 __stackvar.__filter_stack_data) & LTTNG_FILTER_RECORD_FLAG)) \
648 __filter_record = 1; \
f488575f 649 } \
8a92ed2a 650 if (caa_likely(!__filter_record)) \
61ce3223 651 return; \
1ddfd641
MD
652 } \
653 __event_len = __event_get_size__##_provider##___##_name(__stackvar.__dynamic_len, \
1c324e59
MD
654 _TP_ARGS_DATA_VAR(_args)); \
655 __event_align = __event_get_align__##_provider##___##_name(_TP_ARGS_VAR(_args)); \
656 lib_ring_buffer_ctx_init(&__ctx, __chan->chan, __event, __event_len, \
657 __event_align, -1, __chan->handle); \
e1d09f9e 658 __ctx.ip = _TP_IP_PARAM(TP_IP_PARAM); \
1c324e59
MD
659 __ret = __chan->ops->event_reserve(&__ctx, __event->id); \
660 if (__ret < 0) \
661 return; \
662 _fields \
663 __chan->ops->event_commit(&__ctx); \
664}
665
666#include TRACEPOINT_INCLUDE
667
668#undef __get_dynamic_len
669
68755429
MD
670/*
671 * Stage 5.1 of tracepoint event generation.
672 *
673 * Create probe signature
674 */
675
676/* Reset all macros within TRACEPOINT_EVENT */
677#include <lttng/ust-tracepoint-event-reset.h>
678
679#undef TP_ARGS
2eda209b 680#define TP_ARGS(...) __VA_ARGS__
9eb06182
MD
681
682#define _TP_EXTRACT_STRING2(...) #__VA_ARGS__
68755429
MD
683
684#undef TRACEPOINT_EVENT_CLASS
685#define TRACEPOINT_EVENT_CLASS(_provider, _name, _args, _fields) \
686const char __tp_event_signature___##_provider##___##_name[] = \
9eb06182 687 _TP_EXTRACT_STRING2(_args);
68755429
MD
688
689#include TRACEPOINT_INCLUDE
690
9eb06182
MD
691#undef _TP_EXTRACT_STRING2
692
05ceaafd 693/*
882a56d7 694 * Stage 6 of tracepoint event generation.
1c324e59 695 *
df854e41
MD
696 * Tracepoint loglevel mapping definition generation. We generate a
697 * symbol for each mapping for a provider/event to ensure at most a 1 to
698 * 1 mapping between events and loglevels. If the symbol is repeated,
699 * the compiler will complain.
05ceaafd
MD
700 */
701
702/* Reset all macros within TRACEPOINT_EVENT */
703#include <lttng/ust-tracepoint-event-reset.h>
704
7645998a
MD
705/*
706 * Declare _loglevel___##__provider##___##__name as non-static, with
707 * hidden visibility for c++ handling of weakref. We do a weakref to the
708 * symbol in a later stage, which requires that the symbol is not
709 * mangled.
710 */
711#ifdef __cplusplus
712#define LTTNG_TP_EXTERN_C extern "C"
713#else
714#define LTTNG_TP_EXTERN_C
715#endif
716
05ceaafd 717#undef TRACEPOINT_LOGLEVEL
457a6b58
MD
718#define TRACEPOINT_LOGLEVEL(__provider, __name, __loglevel) \
719static const int _loglevel_value___##__provider##___##__name = __loglevel; \
7645998a
MD
720LTTNG_TP_EXTERN_C const int *_loglevel___##__provider##___##__name \
721 __attribute__((visibility("hidden"))) = \
457a6b58 722 &_loglevel_value___##__provider##___##__name;
df854e41
MD
723
724#include TRACEPOINT_INCLUDE
725
7645998a 726#undef LTTNG_TP_EXTERN_C
7645998a 727
6ddc916d
MD
728/*
729 * Stage 6.1 of tracepoint event generation.
730 *
731 * Tracepoint UML URI info.
732 */
733
734/* Reset all macros within TRACEPOINT_EVENT */
735#include <lttng/ust-tracepoint-event-reset.h>
736
7645998a
MD
737/*
738 * Declare _model_emf_uri___##__provider##___##__name as non-static,
739 * with hidden visibility for c++ handling of weakref. We do a weakref
740 * to the symbol in a later stage, which requires that the symbol is not
741 * mangled.
742 */
743#ifdef __cplusplus
744#define LTTNG_TP_EXTERN_C extern "C"
745#else
746#define LTTNG_TP_EXTERN_C
747#endif
748
6ddc916d
MD
749#undef TRACEPOINT_MODEL_EMF_URI
750#define TRACEPOINT_MODEL_EMF_URI(__provider, __name, __uri) \
7645998a 751LTTNG_TP_EXTERN_C const char *_model_emf_uri___##__provider##___##__name \
e7a6b809 752 __attribute__((visibility("hidden"))) = __uri; \
6ddc916d
MD
753
754#include TRACEPOINT_INCLUDE
755
7645998a 756#undef LTTNG_TP_EXTERN_C
7645998a 757
df854e41 758/*
882a56d7 759 * Stage 7.1 of tracepoint event generation.
df854e41
MD
760 *
761 * Create events description structures. We use a weakref because
762 * loglevels are optional. If not declared, the event will point to the
763 * a loglevel that contains NULL.
764 */
765
766/* Reset all macros within TRACEPOINT_EVENT */
767#include <lttng/ust-tracepoint-event-reset.h>
768
769#undef TRACEPOINT_EVENT_INSTANCE
770#define TRACEPOINT_EVENT_INSTANCE(_provider, _template, _name, _args) \
882a56d7
MD
771static const int * \
772 __ref_loglevel___##_provider##___##_name \
773 __attribute__((weakref ("_loglevel___" #_provider "___" #_name))); \
6ddc916d
MD
774static const char * \
775 __ref_model_emf_uri___##_provider##___##_name \
776 __attribute__((weakref ("_model_emf_uri___" #_provider "___" #_name)));\
df854e41 777const struct lttng_event_desc __event_desc___##_provider##_##_name = { \
df854e41 778 .name = #_provider ":" #_name, \
fbdeb5ec 779 .probe_callback = (void (*)(void)) &__event_probe__##_provider##___##_template,\
46d52200
ZT
780 .ctx = NULL, \
781 .fields = __event_fields___##_provider##___##_template, \
0febf018 782 .nr_fields = _TP_ARRAY_SIZE(__event_fields___##_provider##___##_template) - 1, \
882a56d7 783 .loglevel = &__ref_loglevel___##_provider##___##_name, \
68755429 784 .signature = __tp_event_signature___##_provider##___##_template, \
46d52200 785 .u = { .ext = { .model_emf_uri = &__ref_model_emf_uri___##_provider##___##_name } }, \
df854e41
MD
786};
787
788#include TRACEPOINT_INCLUDE
05ceaafd 789
df854e41 790/*
882a56d7 791 * Stage 7.2 of tracepoint event generation.
df854e41
MD
792 *
793 * Create array of events.
794 */
795
796/* Reset all macros within TRACEPOINT_EVENT */
797#include <lttng/ust-tracepoint-event-reset.h>
798
799#undef TRACEPOINT_EVENT_INSTANCE
800#define TRACEPOINT_EVENT_INSTANCE(_provider, _template, _name, _args) \
801 &__event_desc___##_provider##_##_name,
802
803static const struct lttng_event_desc *_TP_COMBINE_TOKENS(__event_desc___, TRACEPOINT_PROVIDER)[] = {
05ceaafd 804#include TRACEPOINT_INCLUDE
0febf018 805 NULL, /* Dummy, C99 forbids 0-len array. */
05ceaafd
MD
806};
807
df854e41 808
05ceaafd 809/*
882a56d7 810 * Stage 8 of tracepoint event generation.
05ceaafd
MD
811 *
812 * Create a toplevel descriptor for the whole probe.
813 */
814
815/* non-const because list head will be modified when registered. */
816static struct lttng_probe_desc _TP_COMBINE_TOKENS(__probe_desc___, TRACEPOINT_PROVIDER) = {
df854e41 817 .provider = __tp_stringify(TRACEPOINT_PROVIDER),
05ceaafd 818 .event_desc = _TP_COMBINE_TOKENS(__event_desc___, TRACEPOINT_PROVIDER),
0febf018 819 .nr_events = _TP_ARRAY_SIZE(_TP_COMBINE_TOKENS(__event_desc___, TRACEPOINT_PROVIDER)) - 1,
46d52200
ZT
820 .head = { NULL, NULL },
821 .lazy_init_head = { NULL, NULL },
822 .lazy = 0,
71d31690
MD
823 .major = LTTNG_UST_PROVIDER_MAJOR,
824 .minor = LTTNG_UST_PROVIDER_MINOR,
05ceaafd
MD
825};
826
f0cc794d
MD
827static int _TP_COMBINE_TOKENS(__probe_register_refcount___, TRACEPOINT_PROVIDER);
828
05ceaafd 829/*
882a56d7 830 * Stage 9 of tracepoint event generation.
05ceaafd 831 *
1c324e59 832 * Register/unregister probes at module load/unload.
628e1d81
MD
833 *
834 * Generate the constructor as an externally visible symbol for use when
835 * linking the probe statically.
f0cc794d
MD
836 *
837 * Register refcount is protected by libc dynamic loader mutex.
1c324e59
MD
838 */
839
840/* Reset all macros within TRACEPOINT_EVENT */
841#include <lttng/ust-tracepoint-event-reset.h>
a8909ba5
PW
842static void lttng_ust_notrace __attribute__((constructor))
843_TP_COMBINE_TOKENS(__lttng_events_init__, TRACEPOINT_PROVIDER)(void);
844static void
1c324e59
MD
845_TP_COMBINE_TOKENS(__lttng_events_init__, TRACEPOINT_PROVIDER)(void)
846{
847 int ret;
848
f0cc794d
MD
849 if (_TP_COMBINE_TOKENS(__probe_register_refcount___,
850 TRACEPOINT_PROVIDER)++) {
851 return;
852 }
e8bd1da7
MD
853 /*
854 * __tracepoint_provider_check_ ## TRACEPOINT_PROVIDER() is a
855 * static inline function that ensures every probe PROVIDER
856 * argument match the provider within which they appear. It
857 * calls empty static inline functions, and therefore has no
858 * runtime effect. However, if it detects an error, a linker
859 * error will appear.
860 */
861 _TP_COMBINE_TOKENS(__tracepoint_provider_check_, TRACEPOINT_PROVIDER)();
7dd08bec 862 ret = lttng_probe_register(&_TP_COMBINE_TOKENS(__probe_desc___, TRACEPOINT_PROVIDER));
7d381d6e
MD
863 if (ret) {
864 fprintf(stderr, "LTTng-UST: Error (%d) while registering tracepoint probe. Duplicate registration of tracepoint probes having the same name is not allowed.\n", ret);
865 abort();
866 }
1c324e59
MD
867}
868
a8909ba5
PW
869static void lttng_ust_notrace __attribute__((destructor))
870_TP_COMBINE_TOKENS(__lttng_events_exit__, TRACEPOINT_PROVIDER)(void);
871static void
1c324e59
MD
872_TP_COMBINE_TOKENS(__lttng_events_exit__, TRACEPOINT_PROVIDER)(void)
873{
f0cc794d
MD
874 if (--_TP_COMBINE_TOKENS(__probe_register_refcount___,
875 TRACEPOINT_PROVIDER)) {
876 return;
877 }
7dd08bec 878 lttng_probe_unregister(&_TP_COMBINE_TOKENS(__probe_desc___, TRACEPOINT_PROVIDER));
1c324e59 879}
628e1d81
MD
880
881int _TP_COMBINE_TOKENS(__tracepoint_provider_, TRACEPOINT_PROVIDER);
This page took 0.070747 seconds and 4 git commands to generate.