[Devel] [PATCH 1/2] ms/tracing: Introduce tracepoint extended structure
Eva Kurchatova
eva.kurchatova at virtuozzo.com
Sun May 17 22:28:03 MSK 2026
From: Mathieu Desnoyers <mathieu.desnoyers at efficios.com>
Commit 1d562f197d01a ("ms/objtool: Exclude __tracepoints data from
ENDBR checks") was backported from mainstream, which excludes the
__tracepoints section from objtool's IBT validation. This causes
regfunc/unregfunc function pointers stored directly in struct tracepoint
to have their ENDBR instructions incorrectly sealed at boot, resulting
in a kernel crash when called indirectly with CONFIG_X86_KERNEL_IBT=y.
In mainstream, this commit amends the crash by moving regfunc/unregfunc
into a separate struct tracepoint_ext outside the __tracepoints section,
and should be backported alongside it.
Tested-by: Jordan Rife <jrife at google.com>
Cc: Michael Jeanson <mjeanson at efficios.com>
Cc: Thomas Gleixner <tglx at linutronix.de>
Cc: Masami Hiramatsu <mhiramat at kernel.org>
Cc: Peter Zijlstra <peterz at infradead.org>
Cc: Alexei Starovoitov <ast at kernel.org>
Cc: Yonghong Song <yhs at fb.com>
Cc: Paul E. McKenney <paulmck at kernel.org>
Cc: Ingo Molnar <mingo at redhat.com>
Cc: Arnaldo Carvalho de Melo <acme at kernel.org>
Cc: Mark Rutland <mark.rutland at arm.com>
Cc: Alexander Shishkin <alexander.shishkin at linux.intel.com>
Cc: Namhyung Kim <namhyung at kernel.org>
Cc: Andrii Nakryiko <andrii.nakryiko at gmail.com>
Cc: bpf at vger.kernel.org
Cc: Joel Fernandes <joel at joelfernandes.org>
Cc: Jordan Rife <jrife at google.com>
Cc: linux-trace-kernel at vger.kernel.org
Link: https://lore.kernel.org/20241031152056.744137-2-mathieu.desnoyers@efficios.com
Signed-off-by: Mathieu Desnoyers <mathieu.desnoyers at efficios.com>
Signed-off-by: Steven Rostedt (Google) <rostedt at goodmis.org>
(cherry picked from commit a9cfb8778c43fc473ae16cddb6e9611705721b31)
Signed-off-by: Eva Kurchatova <eva.kurchatova at virtuozzo.com>
https://virtuozzo.atlassian.net/browse/VSTOR-131560
Feature: fix tracepoint
---
include/linux/tracepoint-defs.h | 8 ++++++--
include/linux/tracepoint.h | 19 +++++++++++++------
kernel/tracepoint.c | 8 ++++----
3 files changed, 23 insertions(+), 12 deletions(-)
diff --git a/include/linux/tracepoint-defs.h b/include/linux/tracepoint-defs.h
index 4dc4955f0fbf..e1af02e375d6 100644
--- a/include/linux/tracepoint-defs.h
+++ b/include/linux/tracepoint-defs.h
@@ -29,6 +29,11 @@ struct tracepoint_func {
int prio;
};
+struct tracepoint_ext {
+ int (*regfunc)(void);
+ void (*unregfunc)(void);
+};
+
struct tracepoint {
const char *name; /* Tracepoint name */
struct static_key key;
@@ -36,9 +41,8 @@ struct tracepoint {
void *static_call_tramp;
void *iterator;
void *probestub;
- int (*regfunc)(void);
- void (*unregfunc)(void);
struct tracepoint_func __rcu *funcs;
+ struct tracepoint_ext *ext;
};
#ifdef CONFIG_HAVE_ARCH_PREL32_RELOCATIONS
diff --git a/include/linux/tracepoint.h b/include/linux/tracepoint.h
index 93a9f3070b48..583d962abcc3 100644
--- a/include/linux/tracepoint.h
+++ b/include/linux/tracepoint.h
@@ -319,7 +319,7 @@ static inline struct tracepoint *tracepoint_ptr_deref(tracepoint_ptr_t *p)
* structures, so we create an array of pointers that will be used for iteration
* on the tracepoints.
*/
-#define DEFINE_TRACE_FN(_name, _reg, _unreg, proto, args) \
+#define __DEFINE_TRACE_EXT(_name, _ext, proto, args) \
static const char __tpstrtab_##_name[] \
__section("__tracepoints_strings") = #_name; \
extern struct static_call_key STATIC_CALL_KEY(tp_func_##_name); \
@@ -333,9 +333,9 @@ static inline struct tracepoint *tracepoint_ptr_deref(tracepoint_ptr_t *p)
.static_call_tramp = STATIC_CALL_TRAMP_ADDR(tp_func_##_name), \
.iterator = &__traceiter_##_name, \
.probestub = &__probestub_##_name, \
- .regfunc = _reg, \
- .unregfunc = _unreg, \
- .funcs = NULL }; \
+ .funcs = NULL, \
+ .ext = _ext, \
+ }; \
__TRACEPOINT_ENTRY(_name); \
int __traceiter_##_name(void *__data, proto) \
{ \
@@ -358,8 +358,15 @@ static inline struct tracepoint *tracepoint_ptr_deref(tracepoint_ptr_t *p)
} \
DEFINE_STATIC_CALL(tp_func_##_name, __traceiter_##_name);
-#define DEFINE_TRACE(name, proto, args) \
- DEFINE_TRACE_FN(name, NULL, NULL, PARAMS(proto), PARAMS(args));
+#define DEFINE_TRACE_FN(_name, _reg, _unreg, _proto, _args) \
+ static struct tracepoint_ext __tracepoint_ext_##_name = { \
+ .regfunc = _reg, \
+ .unregfunc = _unreg, \
+ }; \
+ __DEFINE_TRACE_EXT(_name, &__tracepoint_ext_##_name, PARAMS(_proto), PARAMS(_args));
+
+#define DEFINE_TRACE(_name, _proto, _args) \
+ __DEFINE_TRACE_EXT(_name, NULL, PARAMS(_proto), PARAMS(_args));
#define EXPORT_TRACEPOINT_SYMBOL_GPL(name) \
EXPORT_SYMBOL_GPL(__tracepoint_##name); \
diff --git a/kernel/tracepoint.c b/kernel/tracepoint.c
index 8879da16ef4d..ebab4290d486 100644
--- a/kernel/tracepoint.c
+++ b/kernel/tracepoint.c
@@ -327,8 +327,8 @@ static int tracepoint_add_func(struct tracepoint *tp,
struct tracepoint_func *old, *tp_funcs;
int ret;
- if (tp->regfunc && !static_key_enabled(&tp->key)) {
- ret = tp->regfunc();
+ if (tp->ext && tp->ext->regfunc && !static_key_enabled(&tp->key)) {
+ ret = tp->ext->regfunc();
if (ret < 0)
return ret;
}
@@ -411,8 +411,8 @@ static int tracepoint_remove_func(struct tracepoint *tp,
switch (nr_func_state(tp_funcs)) {
case TP_FUNC_0: /* 1->0 */
/* Removed last function */
- if (tp->unregfunc && static_key_enabled(&tp->key))
- tp->unregfunc();
+ if (tp->ext && tp->ext->unregfunc && static_key_enabled(&tp->key))
+ tp->ext->unregfunc();
static_key_disable(&tp->key);
/* Set iterator static call */
--
2.54.0
More information about the Devel
mailing list