On Tue, Feb 02, 2021 at 06:23:26PM +1100, Alexey Kardashevskiy wrote:
> When executing a tracepoint, the tracepoint's func is dereferenced twice -
> in __DO_TRACE() (where the returned pointer is checked) and later on in
> __traceiter_##_name where the returned pointer is dereferenced without
> checking which leads to races against tracepoint_removal_sync() and
> crashes.
>
> This adds a check before referencing the pointer in tracepoint_ptr_deref.
Agreed, a reload got added and it doesn't check the value again.
> Fixes: d25e37d89dd2f ("tracepoint: Optimize using static_call()")
> Signed-off-by: Alexey Kardashevskiy <[email protected]>
> it_func_ptr = \
> rcu_dereference_raw((&__tracepoint_##_name)->funcs); \
> + if (it_func_ptr) { \
> + do { \
> + it_func = (it_func_ptr)->func; \
> + __data = (it_func_ptr)->data; \
> + ((void(*)(void *, proto))(it_func))(__data,
> args); \
> + } while ((++it_func_ptr)->func); \
> + } \
> return 0; \
Acked-by: Peter Zijlstra (Intel) <[email protected]>