Skip to content

Commit

Permalink
trace: fix undefined behavior in register
Browse files Browse the repository at this point in the history
Passing the tracepoint handler casted to a void (*)(void) means that,
at runtime, the registering code will invoke each handler with no stack
allocated.
This is an undefined behavior with reading current stack, but doing
nothing with the values.
This can be seen with UBsan.

Signed-off-by: David Marchand <[email protected]>
  • Loading branch information
david-marchand committed Jan 30, 2025
1 parent 27a7fb0 commit f077fc2
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 10 deletions.
4 changes: 4 additions & 0 deletions lib/eal/include/rte_trace_point.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,8 @@ extern "C" {
/** The tracepoint object. */
typedef RTE_ATOMIC(uint64_t) rte_trace_point_t;

#ifndef _RTE_TRACE_POINT_REGISTER_H_

/**
* Macro to define the tracepoint arguments in RTE_TRACE_POINT macro.
Expand All @@ -53,6 +55,8 @@ _tp _args \
__VA_ARGS__ \
}

#endif /* _RTE_TRACE_POINT_REGISTER_H_ */

/**
* Create a tracepoint.
*
Expand Down
50 changes: 40 additions & 10 deletions lib/eal/include/rte_trace_point_register.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,43 @@ extern "C" {

RTE_DECLARE_PER_LCORE(volatile int, trace_point_sz);

#define RTE_TRACE_POINT_ARGS_COUNT_(_0,_1,_2,_3,_4,_5,_6,_7,_8,_9,_10,_11,_12,_13,_14,_15,N, ...) \
N
#define RTE_TRACE_POINT_ARGS_COUNT(...) \
RTE_TRACE_POINT_ARGS_COUNT_(__VA_ARGS__,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0)

#define RTE_TRACE_POINT_ARGS_1(a) __rte_unused a
#define RTE_TRACE_POINT_ARGS_2(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_1(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_3(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_2(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_4(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_3(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_5(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_4(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_6(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_5(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_7(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_6(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_8(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_7(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_9(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_8(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_10(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_9(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_11(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_10(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_12(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_11(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_13(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_12(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_14(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_13(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_15(a, ...) __rte_unused a, RTE_TRACE_POINT_ARGS_14(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS_FUNC(a) RTE_TRACE_POINT_ARGS_ ## a
#define RTE_TRACE_POINT_ARGS_EXPAND(...) __VA_ARGS__
#define RTE_TRACE_POINT_ARGS_(N, ...) \
RTE_TRACE_POINT_ARGS_EXPAND(RTE_TRACE_POINT_ARGS_FUNC(N))(__VA_ARGS__)
#define RTE_TRACE_POINT_ARGS(...) \
(RTE_TRACE_POINT_ARGS_(RTE_TRACE_POINT_ARGS_COUNT(0, __VA_ARGS__), __VA_ARGS__))

#define __RTE_TRACE_POINT(_mode, _tp, _args, ...) \
extern rte_trace_point_t __##_tp; \
static __rte_always_inline void _tp _args { } \
static __rte_always_inline void \
_tp ## _register (void) \
{ \
__rte_trace_point_emit_header_##_mode(&__##_tp); \
__VA_ARGS__ \
}

#define RTE_TRACE_POINT_REGISTER(trace, name) \
rte_trace_point_t __rte_section("__rte_trace_point") __##trace; \
static const char __##trace##_name[] = RTE_STR(name); \
Expand All @@ -26,7 +63,7 @@ RTE_INIT(trace##_init) \
if (!rte_trace_feature_is_enabled()) \
return; \
__rte_trace_point_register(&__##trace, __##trace##_name, \
(void (*)(void)) trace); \
trace ## _register); \
}

#define __rte_trace_point_emit_header_generic(t) \
Expand All @@ -36,22 +73,15 @@ RTE_INIT(trace##_init) \
__rte_trace_point_emit_header_generic(t)

#define __rte_trace_point_emit(in, type) \
do { \
RTE_SET_USED(in); \
__rte_trace_point_emit_field(sizeof(type), RTE_STR(in), \
RTE_STR(type)); \
} while (0)
RTE_STR(type))

#define rte_trace_point_emit_string(in) \
do { \
RTE_SET_USED(in); \
__rte_trace_point_emit_field(__RTE_TRACE_EMIT_STRING_LEN_MAX, \
RTE_STR(in)"[32]", "string_bounded_t"); \
} while (0)
RTE_STR(in)"[32]", "string_bounded_t")

#define rte_trace_point_emit_blob(in, len) \
do { \
RTE_SET_USED(in); \
__rte_trace_point_emit(len, uint8_t); \
__rte_trace_point_emit_field(RTE_TRACE_BLOB_LEN_MAX, \
RTE_STR(in)"[" RTE_STR(RTE_TRACE_BLOB_LEN_MAX)"]", \
Expand Down

0 comments on commit f077fc2

Please sign in to comment.