Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright(C) 2020 Marvell International Ltd.
3 : : */
4 : :
5 : : #ifndef _RTE_TRACE_POINT_H_
6 : : #define _RTE_TRACE_POINT_H_
7 : :
8 : : /**
9 : : * @file
10 : : *
11 : : * RTE Tracepoint API
12 : : *
13 : : * This file provides the tracepoint API to RTE applications.
14 : : *
15 : : * @warning
16 : : * @b EXPERIMENTAL: this API may change without prior notice
17 : : */
18 : :
19 : : #include <stdbool.h>
20 : : #include <stdio.h>
21 : : #include <time.h>
22 : :
23 : : #include <rte_branch_prediction.h>
24 : : #include <rte_common.h>
25 : : #include <rte_compat.h>
26 : : #include <rte_cycles.h>
27 : : #include <rte_per_lcore.h>
28 : : #include <rte_stdatomic.h>
29 : : #include <rte_string_fns.h>
30 : : #include <rte_trace.h>
31 : : #include <rte_uuid.h>
32 : :
33 : : #ifdef __cplusplus
34 : : extern "C" {
35 : : #endif
36 : :
37 : : /** The tracepoint object. */
38 : : typedef RTE_ATOMIC(uint64_t) rte_trace_point_t;
39 : :
40 : : #ifndef _RTE_TRACE_POINT_REGISTER_H_
41 : :
42 : : /**
43 : : * Macro to define the tracepoint arguments in RTE_TRACE_POINT macro.
44 : :
45 : : * @see RTE_TRACE_POINT, RTE_TRACE_POINT_FP
46 : : */
47 : : #define RTE_TRACE_POINT_ARGS
48 : :
49 : : /** @internal Helper macro to support RTE_TRACE_POINT and RTE_TRACE_POINT_FP */
50 : : #define __RTE_TRACE_POINT(_mode, _tp, _args, ...) \
51 : : extern rte_trace_point_t __##_tp; \
52 : : static __rte_always_inline void \
53 : : _tp _args \
54 : : { \
55 : : __rte_trace_point_emit_header_##_mode(&__##_tp); \
56 : : __VA_ARGS__ \
57 : : }
58 : :
59 : : #endif /* _RTE_TRACE_POINT_REGISTER_H_ */
60 : :
61 : : /**
62 : : * Create a tracepoint.
63 : : *
64 : : * A tracepoint is defined by specifying:
65 : : * - its input arguments: they are the C function style parameters to define
66 : : * the arguments of tracepoint function. These input arguments are embedded
67 : : * using the RTE_TRACE_POINT_ARGS macro.
68 : : * - its output event fields: they are the sources of event fields that form
69 : : * the payload of any event that the execution of the tracepoint macro emits
70 : : * for this particular tracepoint. The application uses
71 : : * rte_trace_point_emit_* macros to emit the output event fields.
72 : : *
73 : : * @param tp
74 : : * Tracepoint object. Before using the tracepoint, an application needs to
75 : : * define the tracepoint using RTE_TRACE_POINT_REGISTER macro.
76 : : * @param args
77 : : * C function style input arguments to define the arguments to tracepoint
78 : : * function.
79 : : * @param ...
80 : : * Define the payload of trace function. The payload will be formed using
81 : : * rte_trace_point_emit_* macros. Use ";" delimiter between two payloads.
82 : : *
83 : : * @see RTE_TRACE_POINT_ARGS, RTE_TRACE_POINT_REGISTER, rte_trace_point_emit_*
84 : : */
85 : : #define RTE_TRACE_POINT(tp, args, ...) \
86 : : __RTE_TRACE_POINT(generic, tp, args, __VA_ARGS__)
87 : :
88 : : /**
89 : : * Create a tracepoint for fast path.
90 : : *
91 : : * Similar to RTE_TRACE_POINT, except that it is removed at compilation time
92 : : * unless the RTE_ENABLE_TRACE_FP configuration parameter is set.
93 : : *
94 : : * @param tp
95 : : * Tracepoint object. Before using the tracepoint, an application needs to
96 : : * define the tracepoint using RTE_TRACE_POINT_REGISTER macro.
97 : : * @param args
98 : : * C function style input arguments to define the arguments to tracepoint.
99 : : * function.
100 : : * @param ...
101 : : * Define the payload of trace function. The payload will be formed using
102 : : * rte_trace_point_emit_* macros, Use ";" delimiter between two payloads.
103 : : *
104 : : * @see RTE_TRACE_POINT
105 : : */
106 : : #define RTE_TRACE_POINT_FP(tp, args, ...) \
107 : : __RTE_TRACE_POINT(fp, tp, args, __VA_ARGS__)
108 : :
109 : : #ifdef __DOXYGEN__
110 : :
111 : : /**
112 : : * Register a tracepoint.
113 : : *
114 : : * @param trace
115 : : * The tracepoint object created using RTE_TRACE_POINT_REGISTER.
116 : : * @param name
117 : : * The name of the tracepoint object.
118 : : * @return
119 : : * - 0: Successfully registered the tracepoint.
120 : : * - <0: Failure to register the tracepoint.
121 : : */
122 : : #define RTE_TRACE_POINT_REGISTER(trace, name)
123 : :
124 : : /** Tracepoint function payload for uint64_t datatype */
125 : : #define rte_trace_point_emit_u64(val)
126 : : /** Tracepoint function payload for int64_t datatype */
127 : : #define rte_trace_point_emit_i64(val)
128 : : /** Tracepoint function payload for uint32_t datatype */
129 : : #define rte_trace_point_emit_u32(val)
130 : : /** Tracepoint function payload for int32_t datatype */
131 : : #define rte_trace_point_emit_i32(val)
132 : : /** Tracepoint function payload for uint16_t datatype */
133 : : #define rte_trace_point_emit_u16(val)
134 : : /** Tracepoint function payload for int16_t datatype */
135 : : #define rte_trace_point_emit_i16(val)
136 : : /** Tracepoint function payload for uint8_t datatype */
137 : : #define rte_trace_point_emit_u8(val)
138 : : /** Tracepoint function payload for int8_t datatype */
139 : : #define rte_trace_point_emit_i8(val)
140 : : /** Tracepoint function payload for int datatype */
141 : : #define rte_trace_point_emit_int(val)
142 : : /** Tracepoint function payload for long datatype */
143 : : #define rte_trace_point_emit_long(val)
144 : : /** Tracepoint function payload for size_t datatype */
145 : : #define rte_trace_point_emit_size_t(val)
146 : : /** Tracepoint function payload for float datatype */
147 : : #define rte_trace_point_emit_float(val)
148 : : /** Tracepoint function payload for double datatype */
149 : : #define rte_trace_point_emit_double(val)
150 : : /** Tracepoint function payload for pointer datatype */
151 : : #define rte_trace_point_emit_ptr(val)
152 : : /** Tracepoint function payload for string datatype */
153 : : #define rte_trace_point_emit_string(val)
154 : : /** Tracepoint function payload for time_t datatype */
155 : : #define rte_trace_point_emit_time_t(val)
156 : : /**
157 : : * Tracepoint function to capture a blob.
158 : : *
159 : : * @param val
160 : : * Pointer to the array to be captured.
161 : : * @param len
162 : : * Length to be captured. The maximum supported length is
163 : : * RTE_TRACE_BLOB_LEN_MAX bytes.
164 : : */
165 : : #define rte_trace_point_emit_blob(val, len)
166 : :
167 : : #endif /* __DOXYGEN__ */
168 : :
169 : : /** @internal Macro to define maximum emit length of string datatype. */
170 : : #define __RTE_TRACE_EMIT_STRING_LEN_MAX 32
171 : : /** @internal Macro to define event header size. */
172 : : #define __RTE_TRACE_EVENT_HEADER_SZ sizeof(uint64_t)
173 : :
174 : : /** Macro to define maximum emit length of blob. */
175 : : #define RTE_TRACE_BLOB_LEN_MAX 64
176 : :
177 : : /**
178 : : * Enable recording events of the given tracepoint in the trace buffer.
179 : : *
180 : : * @param tp
181 : : * The tracepoint object to enable.
182 : : * @return
183 : : * - 0: Success.
184 : : * - (-ERANGE): Trace object is not registered.
185 : : */
186 : : __rte_experimental
187 : : int rte_trace_point_enable(rte_trace_point_t *tp);
188 : :
189 : : /**
190 : : * Disable recording events of the given tracepoint in the trace buffer.
191 : : *
192 : : * @param tp
193 : : * The tracepoint object to disable.
194 : : * @return
195 : : * - 0: Success.
196 : : * - (-ERANGE): Trace object is not registered.
197 : : */
198 : : __rte_experimental
199 : : int rte_trace_point_disable(rte_trace_point_t *tp);
200 : :
201 : : /**
202 : : * Test if recording events from the given tracepoint is enabled.
203 : : *
204 : : * @param tp
205 : : * The tracepoint object.
206 : : * @return
207 : : * true if tracepoint is enabled, false otherwise.
208 : : */
209 : : __rte_experimental
210 : : bool rte_trace_point_is_enabled(rte_trace_point_t *tp);
211 : :
212 : : /**
213 : : * Lookup a tracepoint object from its name.
214 : : *
215 : : * @param name
216 : : * The name of the tracepoint.
217 : : * @return
218 : : * The tracepoint object or NULL if not found.
219 : : */
220 : : __rte_experimental
221 : : rte_trace_point_t *rte_trace_point_lookup(const char *name);
222 : :
223 : : /**
224 : : * @internal
225 : : *
226 : : * Test if the tracepoint fast path compile-time option is enabled.
227 : : *
228 : : * @return
229 : : * true if tracepoint fast path enabled, false otherwise.
230 : : */
231 : : __rte_experimental
232 : : static __rte_always_inline bool
233 : : __rte_trace_point_fp_is_enabled(void)
234 : : {
235 : : #ifdef RTE_ENABLE_TRACE_FP
236 : : return true;
237 : : #else
238 : : return false;
239 : : #endif
240 : : }
241 : :
242 : : /**
243 : : * @internal
244 : : *
245 : : * Allocate trace memory buffer per thread.
246 : : */
247 : : __rte_experimental
248 : : void __rte_trace_mem_per_thread_alloc(void);
249 : :
250 : : /**
251 : : * @internal
252 : : *
253 : : * Helper function to emit field.
254 : : *
255 : : * @param sz
256 : : * The tracepoint size.
257 : : * @param field
258 : : * The name of the trace event.
259 : : * @param type
260 : : * The datatype of the trace event as string.
261 : : * @return
262 : : * - 0: Success.
263 : : * - <0: Failure.
264 : : */
265 : : __rte_experimental
266 : : void __rte_trace_point_emit_field(size_t sz, const char *field,
267 : : const char *type);
268 : :
269 : : /**
270 : : * @internal
271 : : *
272 : : * Helper function to register a dynamic tracepoint.
273 : : * Use RTE_TRACE_POINT_REGISTER macro for tracepoint registration.
274 : : *
275 : : * @param trace
276 : : * The tracepoint object created using RTE_TRACE_POINT_REGISTER.
277 : : * @param name
278 : : * The name of the tracepoint object.
279 : : * @param register_fn
280 : : * Trace registration function.
281 : : * @return
282 : : * - 0: Successfully registered the tracepoint.
283 : : * - <0: Failure to register the tracepoint.
284 : : */
285 : : __rte_experimental
286 : : int __rte_trace_point_register(rte_trace_point_t *trace, const char *name,
287 : : void (*register_fn)(void));
288 : :
289 : : #ifndef __DOXYGEN__
290 : :
291 : : #ifndef _RTE_TRACE_POINT_REGISTER_H_
292 : : #ifdef ALLOW_EXPERIMENTAL_API
293 : :
294 : : #define __RTE_TRACE_EVENT_HEADER_ID_SHIFT (48)
295 : :
296 : : #define __RTE_TRACE_FIELD_SIZE_SHIFT 0
297 : : #define __RTE_TRACE_FIELD_SIZE_MASK (0xffffULL << __RTE_TRACE_FIELD_SIZE_SHIFT)
298 : : #define __RTE_TRACE_FIELD_ID_SHIFT (16)
299 : : #define __RTE_TRACE_FIELD_ID_MASK (0xffffULL << __RTE_TRACE_FIELD_ID_SHIFT)
300 : : #define __RTE_TRACE_FIELD_ENABLE_MASK (1ULL << 63)
301 : : #define __RTE_TRACE_FIELD_ENABLE_DISCARD (1ULL << 62)
302 : :
303 : : struct __rte_trace_stream_header {
304 : : uint32_t magic;
305 : : rte_uuid_t uuid;
306 : : uint32_t lcore_id;
307 : : char thread_name[__RTE_TRACE_EMIT_STRING_LEN_MAX];
308 : : };
309 : :
310 : : struct __rte_trace_header {
311 : : uint32_t offset;
312 : : uint32_t len;
313 : : struct __rte_trace_stream_header stream_header;
314 : : uint8_t mem[];
315 : : };
316 : :
317 : : RTE_DECLARE_PER_LCORE(void *, trace_mem);
318 : :
319 : : static __rte_always_inline void *
320 : : __rte_trace_mem_get(uint64_t in)
321 : : {
322 : 35 : struct __rte_trace_header *trace =
323 : : (struct __rte_trace_header *)(RTE_PER_LCORE(trace_mem));
324 : 35 : const uint16_t sz = in & __RTE_TRACE_FIELD_SIZE_MASK;
325 : :
326 : : /* Trace memory is not initialized for this thread */
327 [ - + - + : 35 : if (unlikely(trace == NULL)) {
- + - + -
+ - + - +
- + - + -
+ - + - +
- + - + -
+ - + - +
- + - + -
+ - + - -
+ + # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# ]
328 : 1 : __rte_trace_mem_per_thread_alloc();
329 : 1 : trace = (struct __rte_trace_header *)(RTE_PER_LCORE(trace_mem));
330 [ - - - - : 1 : if (unlikely(trace == NULL))
- - - - -
- - - - -
- - - - -
- - - - -
- - - - -
- - - - -
- - - - -
- - - - -
+ - # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# ]
331 : : return NULL;
332 : : }
333 : : /* Check the wrap around case */
334 : 35 : uint32_t offset = RTE_ALIGN_CEIL(trace->offset, __RTE_TRACE_EVENT_HEADER_SZ);
335 [ - + - + : 35 : if (unlikely((offset + sz) >= trace->len)) {
- + - + -
+ - + - +
- + - + -
+ - + - +
- + - + -
+ - + - +
- + - + -
+ - + - -
- + # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# ]
336 : : /* Disable the trace event if it in DISCARD mode */
337 [ # # # # : 0 : if (unlikely(in & __RTE_TRACE_FIELD_ENABLE_DISCARD))
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# ]
338 : : return NULL;
339 : :
340 : : offset = 0;
341 : : }
342 : 35 : void *mem = RTE_PTR_ADD(&trace->mem[0], offset);
343 : 35 : offset += sz;
344 : 35 : trace->offset = offset;
345 : :
346 : 35 : return mem;
347 : : }
348 : :
349 : : static __rte_always_inline void *
350 : : __rte_trace_point_emit_ev_header(void *mem, uint64_t in)
351 : : {
352 : : uint64_t val;
353 : :
354 : : /* Event header [63:0] = id [63:48] | timestamp [47:0] */
355 : 35 : val = rte_get_tsc_cycles() &
356 : : ~(0xffffULL << __RTE_TRACE_EVENT_HEADER_ID_SHIFT);
357 : 35 : val |= ((in & __RTE_TRACE_FIELD_ID_MASK) <<
358 : : (__RTE_TRACE_EVENT_HEADER_ID_SHIFT -
359 : : __RTE_TRACE_FIELD_ID_SHIFT));
360 : :
361 : 13 : *(uint64_t *)mem = val;
362 [ + - + - : 34 : return RTE_PTR_ADD(mem, __RTE_TRACE_EVENT_HEADER_SZ);
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # # # #
# # ]
363 : : }
364 : :
365 : : #define __rte_trace_point_emit_header_generic(t) \
366 : : void *mem; \
367 : : do { \
368 : : if (!rte_trace_feature_is_enabled()) \
369 : : return; \
370 : : const uint64_t val = rte_atomic_load_explicit(t, rte_memory_order_acquire); \
371 : : if (likely(!(val & __RTE_TRACE_FIELD_ENABLE_MASK))) \
372 : : return; \
373 : : mem = __rte_trace_mem_get(val); \
374 : : if (unlikely(mem == NULL)) \
375 : : return; \
376 : : mem = __rte_trace_point_emit_ev_header(mem, val); \
377 : : } while (0)
378 : :
379 : : #define __rte_trace_point_emit_header_fp(t) \
380 : : if (!__rte_trace_point_fp_is_enabled()) \
381 : : return; \
382 : : __rte_trace_point_emit_header_generic(t)
383 : :
384 : : #define __rte_trace_point_emit(name, in, type) \
385 : : do { \
386 : : RTE_BUILD_BUG_ON(sizeof(type) != sizeof(typeof(*in))); \
387 : : memcpy(mem, in, sizeof(*in)); \
388 : : mem = RTE_PTR_ADD(mem, sizeof(*in)); \
389 : : } while (0)
390 : :
391 : : #define rte_trace_point_emit_string(in) \
392 : : do { \
393 : : if (unlikely(in == NULL)) \
394 : : return; \
395 : : rte_strscpy((char *)mem, in, __RTE_TRACE_EMIT_STRING_LEN_MAX); \
396 : : mem = RTE_PTR_ADD(mem, __RTE_TRACE_EMIT_STRING_LEN_MAX); \
397 : : } while (0)
398 : :
399 : : #define rte_trace_point_emit_blob(in, len) \
400 : : do { \
401 : : uint8_t size = len; \
402 : : if (unlikely(in == NULL)) \
403 : : return; \
404 : : if (size > RTE_TRACE_BLOB_LEN_MAX) \
405 : : size = RTE_TRACE_BLOB_LEN_MAX; \
406 : : __rte_trace_point_emit("size", &size, uint8_t); \
407 : : memcpy(mem, in, size); \
408 : : memset(RTE_PTR_ADD(mem, size), 0, RTE_TRACE_BLOB_LEN_MAX - size); \
409 : : mem = RTE_PTR_ADD(mem, RTE_TRACE_BLOB_LEN_MAX); \
410 : : } while (0)
411 : :
412 : : #else
413 : :
414 : : #define __rte_trace_point_emit_header_generic(t) RTE_SET_USED(t)
415 : : #define __rte_trace_point_emit_header_fp(t) RTE_SET_USED(t)
416 : : #define __rte_trace_point_emit(name, in, type) RTE_SET_USED(in)
417 : : #define rte_trace_point_emit_string(in) RTE_SET_USED(in)
418 : : #define rte_trace_point_emit_blob(in, len) \
419 : : do { \
420 : : RTE_SET_USED(in); \
421 : : RTE_SET_USED(len); \
422 : : } while (0)
423 : :
424 : :
425 : : #endif /* ALLOW_EXPERIMENTAL_API */
426 : : #endif /* _RTE_TRACE_POINT_REGISTER_H_ */
427 : :
428 : : #define rte_trace_point_emit_u64(in) __rte_trace_point_emit(RTE_STR(in), &in, uint64_t)
429 : : #define rte_trace_point_emit_i64(in) __rte_trace_point_emit(RTE_STR(in), &in, int64_t)
430 : : #define rte_trace_point_emit_u32(in) __rte_trace_point_emit(RTE_STR(in), &in, uint32_t)
431 : : #define rte_trace_point_emit_i32(in) __rte_trace_point_emit(RTE_STR(in), &in, int32_t)
432 : : #define rte_trace_point_emit_u16(in) __rte_trace_point_emit(RTE_STR(in), &in, uint16_t)
433 : : #define rte_trace_point_emit_i16(in) __rte_trace_point_emit(RTE_STR(in), &in, int16_t)
434 : : #define rte_trace_point_emit_u8(in) __rte_trace_point_emit(RTE_STR(in), &in, uint8_t)
435 : : #define rte_trace_point_emit_i8(in) __rte_trace_point_emit(RTE_STR(in), &in, int8_t)
436 : : #define rte_trace_point_emit_int(in) __rte_trace_point_emit(RTE_STR(in), &in, int32_t)
437 : : #define rte_trace_point_emit_long(in) __rte_trace_point_emit(RTE_STR(in), &in, long)
438 : : #define rte_trace_point_emit_size_t(in) __rte_trace_point_emit(RTE_STR(in), &in, size_t)
439 : : #define rte_trace_point_emit_float(in) __rte_trace_point_emit(RTE_STR(in), &in, float)
440 : : #define rte_trace_point_emit_double(in) __rte_trace_point_emit(RTE_STR(in), &in, double)
441 : : #define rte_trace_point_emit_ptr(in) __rte_trace_point_emit(RTE_STR(in), &in, uintptr_t)
442 : : #define rte_trace_point_emit_time_t(in) __rte_trace_point_emit(RTE_STR(in), &in, time_t)
443 : :
444 : : #define rte_trace_point_emit_u64_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, uint64_t)
445 : : #define rte_trace_point_emit_i64_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, int64_t)
446 : : #define rte_trace_point_emit_u32_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, uint32_t)
447 : : #define rte_trace_point_emit_i32_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, int32_t)
448 : : #define rte_trace_point_emit_u16_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, uint16_t)
449 : : #define rte_trace_point_emit_i16_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, int16_t)
450 : : #define rte_trace_point_emit_u8_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, uint8_t)
451 : : #define rte_trace_point_emit_i8_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, int8_t)
452 : : #define rte_trace_point_emit_int_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, int32_t)
453 : : #define rte_trace_point_emit_long_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, long)
454 : : #define rte_trace_point_emit_size_t_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, size_t)
455 : : #define rte_trace_point_emit_float_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, float)
456 : : #define rte_trace_point_emit_double_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, double)
457 : : #define rte_trace_point_emit_time_t_ptr(in) __rte_trace_point_emit(RTE_STR(in)"_val", in, time_t)
458 : :
459 : : #endif /* __DOXYGEN__ */
460 : :
461 : : #ifdef __cplusplus
462 : : }
463 : : #endif
464 : :
465 : : #endif /* _RTE_TRACE_POINT_H_ */
|