Commit 38ceb592 authored by Lai Jiangshan's avatar Lai Jiangshan Committed by Frederic Weisbecker

tracing: Fix invalid function_graph entry

When print_graph_entry() computes a function call entry event, it needs
to also check the next entry to guess if it matches the return event of
the current function entry.
In order to look at this next event, it needs to consume the current
entry before going ahead in the ring buffer.

However, if the current event that gets consumed is the last one in the
ring buffer head page, the ring_buffer may reuse the page for writers.
The consumed entry will then become invalid because of possible
racy overwriting.

Me must then handle this entry by making a copy of it.

The fix also applies on 2.6.30
Signed-off-by: default avatarLai Jiangshan <laijs@cn.fujitsu.com>
Cc: Steven Rostedt <rostedt@goodmis.org>
Cc: stable@kernel.org
LKML-Reference: <4A6EEAEC.3050508@cn.fujitsu.com>
Signed-off-by: default avatarFrederic Weisbecker <fweisbec@gmail.com>
parent 4733fd32
...@@ -843,9 +843,16 @@ print_graph_function(struct trace_iterator *iter) ...@@ -843,9 +843,16 @@ print_graph_function(struct trace_iterator *iter)
switch (entry->type) { switch (entry->type) {
case TRACE_GRAPH_ENT: { case TRACE_GRAPH_ENT: {
struct ftrace_graph_ent_entry *field; /*
* print_graph_entry() may consume the current event,
* thus @field may become invalid, so we need to save it.
* sizeof(struct ftrace_graph_ent_entry) is very small,
* it can be safely saved at the stack.
*/
struct ftrace_graph_ent_entry *field, saved;
trace_assign_type(field, entry); trace_assign_type(field, entry);
return print_graph_entry(field, s, iter); saved = *field;
return print_graph_entry(&saved, s, iter);
} }
case TRACE_GRAPH_RET: { case TRACE_GRAPH_RET: {
struct ftrace_graph_ret_entry *field; struct ftrace_graph_ret_entry *field;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment