linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] tracing: Move tracepoint callbacks into DEFINE
@ 2009-08-18  7:23 Josh Stone
  2009-08-18 14:19 ` Jason Baron
                   ` (3 more replies)
  0 siblings, 4 replies; 70+ messages in thread
From: Josh Stone @ 2009-08-18  7:23 UTC (permalink / raw)
  To: linux-kernel
  Cc: fweisbec, mingo, laijs, rostedt, peterz, mathieu.desnoyers,
	jiayingz, mbligh, lizf, Josh Stone, Jason Baron

It's not strictly correct for the tracepoint reg/unreg callbacks to
occur when a client is hooking up, because the actual tracepoint may no
be present yet.  This happens to be fine for syscall, since that's in
the core kernel, but it would cause problems for tracepoints defined in
a module that hasn't been loaded yet.  It also means the reg/unreg has
to be EXPORTed for any modules to use the tracepoint (as in SystemTap).

This patch removes DECLARE_TRACE_WITH_CALLBACK, and instead introduces
DEFINE_TRACE_WITH_CALLBACK which stores the callbacks in struct
tracepoint.  The callbacks are used now when the active state of the
tracepoint changes in set_tracepoint & disable_tracepoint.

This also introduces TRACE_EVENT_WITH_CALLBACK, so those events can also
provide callbacks if needed.

Signed-off-by: Josh Stone <jistone@redhat.com>
Cc: Jason Baron <jbaron@redhat.com>
---
 arch/x86/kernel/ptrace.c     |    4 ++--
 include/linux/tracepoint.h   |   41 +++++++++++++++--------------------------
 include/trace/define_trace.h |    5 +++++
 include/trace/ftrace.h       |    9 +++++++++
 include/trace/syscall.h      |   12 ++++--------
 kernel/tracepoint.c          |   15 +++++++++------
 6 files changed, 44 insertions(+), 42 deletions(-)

diff --git a/arch/x86/kernel/ptrace.c b/arch/x86/kernel/ptrace.c
index 34dd6f1..692fc14 100644
--- a/arch/x86/kernel/ptrace.c
+++ b/arch/x86/kernel/ptrace.c
@@ -37,8 +37,8 @@
 
 #include <trace/syscall.h>
 
-DEFINE_TRACE(syscall_enter);
-DEFINE_TRACE(syscall_exit);
+DEFINE_TRACE_WITH_CALLBACK(syscall_enter, syscall_regfunc, syscall_unregfunc);
+DEFINE_TRACE_WITH_CALLBACK(syscall_exit, syscall_regfunc, syscall_unregfunc);
 
 #include "tls.h"
 
diff --git a/include/linux/tracepoint.h b/include/linux/tracepoint.h
index 5984ed0..7ffc7b6 100644
--- a/include/linux/tracepoint.h
+++ b/include/linux/tracepoint.h
@@ -23,6 +23,8 @@ struct tracepoint;
 struct tracepoint {
 	const char *name;		/* Tracepoint name */
 	int state;			/* State. */
+	void (*regfunc)(void);
+	void (*unregfunc)(void);
 	void **funcs;
 } __attribute__((aligned(32)));		/*
 					 * Aligned on 32 bytes because it is
@@ -63,7 +65,7 @@ struct tracepoint {
  * An optional set of (un)registration functions can be passed to perform any
  * additional (un)registration work.
  */
-#define DECLARE_TRACE_WITH_CALLBACK(name, proto, args, reg, unreg)	\
+#define DECLARE_TRACE(name, proto, args)				\
 	extern struct tracepoint __tracepoint_##name;			\
 	static inline void trace_##name(proto)				\
 	{								\
@@ -73,36 +75,23 @@ struct tracepoint {
 	}								\
 	static inline int register_trace_##name(void (*probe)(proto))	\
 	{								\
-		int ret;						\
-		void (*func)(void) = reg;				\
-									\
-		ret = tracepoint_probe_register(#name, (void *)probe);	\
-		if (func && !ret)					\
-			func();						\
-		return ret;						\
+		return tracepoint_probe_register(#name, (void *)probe);	\
 	}								\
 	static inline int unregister_trace_##name(void (*probe)(proto))	\
 	{								\
-		int ret;						\
-		void (*func)(void) = unreg;				\
-									\
-		ret = tracepoint_probe_unregister(#name, (void *)probe);\
-		if (func && !ret)					\
-			func();						\
-		return ret;						\
+		return tracepoint_probe_unregister(#name, (void *)probe);\
 	}
 
 
-#define DECLARE_TRACE(name, proto, args)				 \
-	DECLARE_TRACE_WITH_CALLBACK(name, TP_PROTO(proto), TP_ARGS(args),\
-					NULL, NULL);
-
-#define DEFINE_TRACE(name)						\
+#define DEFINE_TRACE_WITH_CALLBACK(name, reg, unreg)			\
 	static const char __tpstrtab_##name[]				\
 	__attribute__((section("__tracepoints_strings"))) = #name;	\
 	struct tracepoint __tracepoint_##name				\
 	__attribute__((section("__tracepoints"), aligned(32))) =	\
-		{ __tpstrtab_##name, 0, NULL }
+		{ __tpstrtab_##name, 0, reg, unreg, NULL }
+
+#define DEFINE_TRACE(name)						\
+	DEFINE_TRACE_WITH_CALLBACK(name, NULL, NULL);
 
 #define EXPORT_TRACEPOINT_SYMBOL_GPL(name)				\
 	EXPORT_SYMBOL_GPL(__tracepoint_##name)
@@ -113,7 +102,7 @@ extern void tracepoint_update_probe_range(struct tracepoint *begin,
 	struct tracepoint *end);
 
 #else /* !CONFIG_TRACEPOINTS */
-#define DECLARE_TRACE_WITH_CALLBACK(name, proto, args, reg, unreg)	\
+#define DECLARE_TRACE(name, proto, args)				\
 	static inline void _do_trace_##name(struct tracepoint *tp, proto) \
 	{ }								\
 	static inline void trace_##name(proto)				\
@@ -127,10 +116,7 @@ extern void tracepoint_update_probe_range(struct tracepoint *begin,
 		return -ENOSYS;						\
 	}
 
-#define DECLARE_TRACE(name, proto, args)				 \
-	DECLARE_TRACE_WITH_CALLBACK(name, TP_PROTO(proto), TP_ARGS(args),\
-					NULL, NULL);
-
+#define DEFINE_TRACE_WITH_CALLBACK(name, reg, unreg)
 #define DEFINE_TRACE(name)
 #define EXPORT_TRACEPOINT_SYMBOL_GPL(name)
 #define EXPORT_TRACEPOINT_SYMBOL(name)
@@ -286,6 +272,9 @@ static inline void tracepoint_synchronize_unregister(void)
 
 #define TRACE_EVENT(name, proto, args, struct, assign, print)	\
 	DECLARE_TRACE(name, PARAMS(proto), PARAMS(args))
+#define TRACE_EVENT_WITH_CALLBACK(name, proto, args, struct,	\
+		assign, print, reg, unreg)			\
+	DECLARE_TRACE(name, PARAMS(proto), PARAMS(args))
 #endif
 
 #endif
diff --git a/include/trace/define_trace.h b/include/trace/define_trace.h
index f7a7ae1..82c623a 100644
--- a/include/trace/define_trace.h
+++ b/include/trace/define_trace.h
@@ -26,6 +26,11 @@
 #define TRACE_EVENT(name, proto, args, tstruct, assign, print)	\
 	DEFINE_TRACE(name)
 
+#undef TRACE_EVENT_WITH_CALLBACK
+#define TRACE_EVENT_WITH_CALLBACK(name, proto, args, tstruct,	\
+		assign, print, reg, unreg)			\
+	DEFINE_TRACE_WITH_CALLBACK(name, reg, unreg)
+
 #undef DECLARE_TRACE
 #define DECLARE_TRACE(name, proto, args)	\
 	DEFINE_TRACE(name)
diff --git a/include/trace/ftrace.h b/include/trace/ftrace.h
index b250b06..61ed0ab 100644
--- a/include/trace/ftrace.h
+++ b/include/trace/ftrace.h
@@ -42,6 +42,15 @@
 	};							\
 	static struct ftrace_event_call event_##name
 
+/* Callbacks are meaningless to ftrace. */
+#undef TRACE_EVENT_WITH_CALLBACK
+#define TRACE_EVENT_WITH_CALLBACK(name, proto, args, tstruct,	\
+		assign, print, reg, unreg)			\
+	TRACE_EVENT(name, TP_PROTO(proto), TP_ARGS(args),	\
+		TP_STRUCT__entry(tstruct),			\
+		TP_fast_assign(assign),				\
+		TP_printk(print))
+
 #include TRACE_INCLUDE(TRACE_INCLUDE_FILE)
 
 
diff --git a/include/trace/syscall.h b/include/trace/syscall.h
index 0cb0362..49e7ec2 100644
--- a/include/trace/syscall.h
+++ b/include/trace/syscall.h
@@ -11,18 +11,14 @@
 extern void syscall_regfunc(void);
 extern void syscall_unregfunc(void);
 
-DECLARE_TRACE_WITH_CALLBACK(syscall_enter,
+DECLARE_TRACE(syscall_enter,
 	TP_PROTO(struct pt_regs *regs, long id),
-	TP_ARGS(regs, id),
-	syscall_regfunc,
-	syscall_unregfunc
+	TP_ARGS(regs, id)
 );
 
-DECLARE_TRACE_WITH_CALLBACK(syscall_exit,
+DECLARE_TRACE(syscall_exit,
 	TP_PROTO(struct pt_regs *regs, long ret),
-	TP_ARGS(regs, ret),
-	syscall_regfunc,
-	syscall_unregfunc
+	TP_ARGS(regs, ret)
 );
 
 /*
diff --git a/kernel/tracepoint.c b/kernel/tracepoint.c
index 35dd27a..1865c09 100644
--- a/kernel/tracepoint.c
+++ b/kernel/tracepoint.c
@@ -243,6 +243,11 @@ static void set_tracepoint(struct tracepoint_entry **entry,
 {
 	WARN_ON(strcmp((*entry)->name, elem->name) != 0);
 
+	if (elem->regfunc && !elem->state && active)
+		elem->regfunc();
+	else if (elem->unregfunc && elem->state && !active)
+		elem->unregfunc();
+
 	/*
 	 * rcu_assign_pointer has a smp_wmb() which makes sure that the new
 	 * probe callbacks array is consistent before setting a pointer to it.
@@ -262,6 +267,9 @@ static void set_tracepoint(struct tracepoint_entry **entry,
  */
 static void disable_tracepoint(struct tracepoint *elem)
 {
+	if (elem->unregfunc && elem->state)
+		elem->unregfunc();
+
 	elem->state = 0;
 	rcu_assign_pointer(elem->funcs, NULL);
 }
@@ -581,15 +589,13 @@ __initcall(init_tracepoints);
 
 #ifdef CONFIG_FTRACE_SYSCALLS
 
-static DEFINE_MUTEX(regfunc_mutex);
-static int sys_tracepoint_refcount;
+static int sys_tracepoint_refcount; /* guarded by tracepoints_mutex */
 
 void syscall_regfunc(void)
 {
 	unsigned long flags;
 	struct task_struct *g, *t;
 
-	mutex_lock(&regfunc_mutex);
 	if (!sys_tracepoint_refcount) {
 		read_lock_irqsave(&tasklist_lock, flags);
 		do_each_thread(g, t) {
@@ -598,7 +604,6 @@ void syscall_regfunc(void)
 		read_unlock_irqrestore(&tasklist_lock, flags);
 	}
 	sys_tracepoint_refcount++;
-	mutex_unlock(&regfunc_mutex);
 }
 
 void syscall_unregfunc(void)
@@ -606,7 +611,6 @@ void syscall_unregfunc(void)
 	unsigned long flags;
 	struct task_struct *g, *t;
 
-	mutex_lock(&regfunc_mutex);
 	sys_tracepoint_refcount--;
 	if (!sys_tracepoint_refcount) {
 		read_lock_irqsave(&tasklist_lock, flags);
@@ -615,6 +619,5 @@ void syscall_unregfunc(void)
 		} while_each_thread(g, t);
 		read_unlock_irqrestore(&tasklist_lock, flags);
 	}
-	mutex_unlock(&regfunc_mutex);
 }
 #endif
-- 
1.6.2.5


^ permalink raw reply related	[flat|nested] 70+ messages in thread

end of thread, other threads:[~2009-08-28 12:29 UTC | newest]

Thread overview: 70+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-08-18  7:23 [PATCH] tracing: Move tracepoint callbacks into DEFINE Josh Stone
2009-08-18 14:19 ` Jason Baron
2009-08-18 22:11   ` Josh Stone
2009-08-18 22:25 ` [PATCH] tracing: Create generic syscall TRACE_EVENTs Josh Stone
2009-08-19  1:32   ` Li Zefan
2009-08-19  3:05     ` Josh Stone
2009-08-19 13:05       ` Ingo Molnar
2009-08-19 13:50         ` Mathieu Desnoyers
2009-08-19 16:16   ` Jason Baron
2009-08-19 17:43     ` Frederic Weisbecker
2009-08-19 16:13 ` [PATCH] tracing: Move tracepoint callbacks into DEFINE Jason Baron
2009-08-20 17:25   ` Josh Stone
2009-08-20 19:09 ` [PATCH v2 1/2] " Josh Stone
2009-08-20 19:09   ` [PATCH v2 2/2] tracing: Create generic syscall TRACE_EVENTs Josh Stone
2009-08-21 17:57     ` Jason Baron
2009-08-21 19:37       ` Josh Stone
2009-08-21 20:08         ` Jason Baron
2009-08-21 14:47   ` [PATCH v2 1/2] tracing: Move tracepoint callbacks into DEFINE Ingo Molnar
2009-08-21 19:34     ` Josh Stone
2009-08-21 17:52   ` Jason Baron
2009-08-21 19:34     ` Josh Stone
2009-08-21 20:06       ` Jason Baron
2009-08-23 20:29         ` Frederic Weisbecker
2009-08-23 20:15       ` Frederic Weisbecker
2009-08-22  4:58   ` [PATCH v3 0/4] tracing: tweaks for generic syscall events Josh Stone
2009-08-22  4:58     ` [PATCH v3 1/4] tracing: Rename TIF_SYSCALL_FTRACE->_TRACEPOINT Josh Stone
2009-08-22  4:58       ` [PATCH v3 2/4] tracing: Make syscall_(un)regfunc arch-specific Josh Stone
2009-08-22  4:58         ` [PATCH v3 3/4] tracing: Move tracepoint callbacks into DEFINE Josh Stone
2009-08-22  4:58           ` [PATCH v3 4/4] tracing: Create generic syscall TRACE_EVENTs Josh Stone
2009-08-23 21:14         ` [PATCH v3 2/4] tracing: Make syscall_(un)regfunc arch-specific Frederic Weisbecker
2009-08-24  1:40           ` Paul Mundt
2009-08-24  8:41             ` Ingo Molnar
2009-08-24  8:59               ` Paul Mundt
2009-08-24  9:56                 ` Ingo Molnar
2009-08-24 10:32                   ` Paul Mundt
2009-08-24 11:00                     ` Ingo Molnar
2009-08-24 11:15                       ` Paul Mundt
2009-08-24 11:32                         ` Ingo Molnar
2009-08-24 11:52                     ` Ingo Molnar
2009-08-24 12:14                       ` Peter Zijlstra
2009-08-24 11:01                   ` Ingo Molnar
2009-08-24 11:02                     ` Paul Mundt
2009-08-24 19:31           ` Josh Stone
2009-08-24 19:58             ` Frederic Weisbecker
2009-08-24 20:00               ` Josh Stone
2009-08-24 20:12                 ` Frederic Weisbecker
2009-08-23 21:16       ` [PATCH v3 1/4] tracing: Rename TIF_SYSCALL_FTRACE->_TRACEPOINT Frederic Weisbecker
2009-08-24  8:42         ` Ingo Molnar
2009-08-24 11:11           ` Frederic Weisbecker
2009-08-24 11:24             ` Ingo Molnar
2009-08-24 11:29               ` Paul Mundt
2009-08-24 11:36                 ` Ingo Molnar
2009-08-24 21:43     ` [PATCH v4 0/4] tracing: tweaks for generic syscall events Josh Stone
2009-08-24 21:43       ` [PATCH v4 1/4] tracing: Rename FTRACE_SYSCALLS for tracepoints Josh Stone
2009-08-24 21:43         ` [PATCH v4 2/4] tracing: Make syscall tracepoints conditional Josh Stone
2009-08-24 21:43           ` [PATCH v4 3/4] tracing: Move tracepoint callbacks into DEFINE Josh Stone
2009-08-24 21:43             ` [PATCH v4 4/4] tracing: Create generic syscall TRACE_EVENTs Josh Stone
2009-08-26  7:22               ` [tip:tracing/core] " tip-bot for Josh Stone
2009-08-26  7:22             ` [tip:tracing/core] tracing: Move tracepoint callbacks from declaration to definition tip-bot for Josh Stone
2009-08-27 22:50               ` [PATCH] tracing: Fix double CPP substitution in TRACE_EVENT_FN Frederic Weisbecker
2009-08-28  0:38                 ` Josh Stone
2009-08-28 12:29                 ` [tip:tracing/core] " tip-bot for Frederic Weisbecker
2009-08-26  7:21           ` [tip:tracing/core] tracing: Make syscall tracepoints conditional tip-bot for Josh Stone
2009-08-26  7:21         ` [tip:tracing/core] tracing: Rename FTRACE_SYSCALLS for tracepoints tip-bot for Josh Stone
2009-08-24 23:05       ` [PATCH v4 0/4] tracing: tweaks for generic syscall events Frederic Weisbecker
2009-08-25 10:28         ` Ingo Molnar
2009-08-25 13:42           ` Frederic Weisbecker
2009-08-25 14:41             ` Jason Baron
2009-08-25 21:08               ` Frederic Weisbecker
2009-08-25 21:44       ` Frederic Weisbecker

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).