Skip to content

Commit

Permalink
function-graph: move initialization of new tasks up in fork
Browse files Browse the repository at this point in the history
When the function graph tracer is enabled, all new tasks must allocate
a ret_stack to place the return address of functions. This is because
the function graph tracer will replace the real return address with a
call to the tracing of the exit function.

This initialization happens in fork, but it happens too late. If fork
fails, then it will call free_task and that calls the freeing of this
ret_stack. But before initialization happens, the new (failed) task
points to its parents ret_stack. If a fork failure happens during
the function trace, it would be catastrophic for the parent.

Also, there's no need to call ftrace_graph_exit_task from fork, since
it is called by free_task which fork calls on failure.

[ Impact: prevent crash during failed fork running function graph tracer ]

Signed-off-by: Steven Rostedt <rostedt@goodmis.org>
  • Loading branch information
Steven Rostedt authored and Steven Rostedt committed Jun 2, 2009
1 parent 26c0162 commit f7e8b61
Showing 1 changed file with 4 additions and 6 deletions.
10 changes: 4 additions & 6 deletions kernel/fork.c
Original file line number Diff line number Diff line change
Expand Up @@ -982,6 +982,8 @@ static struct task_struct *copy_process(unsigned long clone_flags,
if (!p)
goto fork_out;

ftrace_graph_init_task(p);

rt_mutex_init_task(p);

#ifdef CONFIG_PROVE_LOCKING
Expand Down Expand Up @@ -1131,8 +1133,6 @@ static struct task_struct *copy_process(unsigned long clone_flags,
}
}

ftrace_graph_init_task(p);

p->pid = pid_nr(pid);
p->tgid = p->pid;
if (clone_flags & CLONE_THREAD)
Expand All @@ -1141,7 +1141,7 @@ static struct task_struct *copy_process(unsigned long clone_flags,
if (current->nsproxy != p->nsproxy) {
retval = ns_cgroup_clone(p, pid);
if (retval)
goto bad_fork_free_graph;
goto bad_fork_free_pid;
}

p->set_child_tid = (clone_flags & CLONE_CHILD_SETTID) ? child_tidptr : NULL;
Expand Down Expand Up @@ -1233,7 +1233,7 @@ static struct task_struct *copy_process(unsigned long clone_flags,
spin_unlock(&current->sighand->siglock);
write_unlock_irq(&tasklist_lock);
retval = -ERESTARTNOINTR;
goto bad_fork_free_graph;
goto bad_fork_free_pid;
}

if (clone_flags & CLONE_THREAD) {
Expand Down Expand Up @@ -1268,8 +1268,6 @@ static struct task_struct *copy_process(unsigned long clone_flags,
cgroup_post_fork(p);
return p;

bad_fork_free_graph:
ftrace_graph_exit_task(p);
bad_fork_free_pid:
if (pid != &init_struct_pid)
free_pid(pid);
Expand Down

0 comments on commit f7e8b61

Please sign in to comment.