summaryrefslogtreecommitdiffstats
path: root/kernel/trace/trace.h
diff options
context:
space:
mode:
authorSteven Rostedt (Red Hat)2013-07-02 21:30:53 +0200
committerSteven Rostedt2013-07-02 23:13:34 +0200
commit8e2e2fa47129532a30cff6c25a47078dc97d9260 (patch)
tree6cc93f432b3186200c7afeaca1a432e497ad949c /kernel/trace/trace.h
parenttracing: Get trace_array ref counts when accessing trace files (diff)
downloadkernel-qcow2-linux-8e2e2fa47129532a30cff6c25a47078dc97d9260.tar.gz
kernel-qcow2-linux-8e2e2fa47129532a30cff6c25a47078dc97d9260.tar.xz
kernel-qcow2-linux-8e2e2fa47129532a30cff6c25a47078dc97d9260.zip
tracing: Add trace_array_get/put() to event handling
Commit a695cb58162 "tracing: Prevent deleting instances when they are being read" tried to fix a race between deleting a trace instance and reading contents of a trace file. But it wasn't good enough. The following could crash the kernel: # cd /sys/kernel/debug/tracing/instances # ( while :; do mkdir foo; rmdir foo; done ) & # ( while :; do echo 1 > foo/events/sched/sched_switch 2> /dev/null; done ) & Luckily this can only be done by root user, but it should be fixed regardless. The problem is that a delete of the file can happen after the write to the event is opened, but before the enabling happens. The solution is to make sure the trace_array is available before succeeding in opening for write, and incerment the ref counter while opened. Now the instance can be deleted when the events are writing to the buffer, but the deletion of the instance will disable all events before the instance is actually deleted. Cc: stable@vger.kernel.org # 3.10 Reported-by: Alexander Lam <azl@google.com> Signed-off-by: Steven Rostedt <rostedt@goodmis.org>
Diffstat (limited to 'kernel/trace/trace.h')
-rw-r--r--kernel/trace/trace.h3
1 files changed, 3 insertions, 0 deletions
diff --git a/kernel/trace/trace.h b/kernel/trace/trace.h
index 2c3cba59552d..c7fbf93f1b7c 100644
--- a/kernel/trace/trace.h
+++ b/kernel/trace/trace.h
@@ -226,6 +226,9 @@ extern struct list_head ftrace_trace_arrays;
extern struct mutex trace_types_lock;
+extern int trace_array_get(struct trace_array *tr);
+extern void trace_array_put(struct trace_array *tr);
+
/*
* The global tracer (top) should be the first trace array added,
* but we check the flag anyway.