diff options
author | Steven Rostedt <rostedt@goodmis.org> | 2008-10-01 13:14:09 -0400 |
---|---|---|
committer | Ingo Molnar <mingo@elte.hu> | 2008-10-14 04:39:09 -0400 |
commit | 38697053fa006411224a1790e2adb8216440ab0f (patch) | |
tree | 30daab3a6ba93f1c8c922397ffe8a0d6a220e8b1 /kernel/trace/trace.h | |
parent | e4c2ce82ca2710e17cb4df8eb2b249fa2eb5af30 (diff) |
ftrace: preempt disable over interrupt disable
With the new ring buffer infrastructure in ftrace, I'm trying to make
ftrace a little more light weight.
This patch converts a lot of the local_irq_save/restore into
preempt_disable/enable. The original preempt count in a lot of cases
has to be sent in as a parameter so that it can be recorded correctly.
Some places were recording it incorrectly before anyway.
This is also laying the ground work to make ftrace a little bit
more reentrant, and remove all locking. The function tracers must
still protect from reentrancy.
Note: All the function tracers must be careful when using preempt_disable.
It must do the following:
resched = need_resched();
preempt_disable_notrace();
[...]
if (resched)
preempt_enable_no_resched_notrace();
else
preempt_enable_notrace();
The reason is that if this function traces schedule() itself, the
preempt_enable_notrace() will cause a schedule, which will lead
us into a recursive failure.
If we needed to reschedule before calling preempt_disable, we
should have already scheduled. Since we did not, this is most
likely that we should not and are probably inside a schedule
function.
If resched was not set, we still need to catch the need resched
flag being set when preemption was off and the if case at the
end will catch that for us.
Signed-off-by: Steven Rostedt <srostedt@redhat.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
Diffstat (limited to 'kernel/trace/trace.h')
-rw-r--r-- | kernel/trace/trace.h | 13 |
1 files changed, 7 insertions, 6 deletions
diff --git a/kernel/trace/trace.h b/kernel/trace/trace.h index f02042d0d828..f1f99572cde7 100644 --- a/kernel/trace/trace.h +++ b/kernel/trace/trace.h | |||
@@ -288,35 +288,36 @@ void init_tracer_sysprof_debugfs(struct dentry *d_tracer); | |||
288 | struct trace_entry *tracing_get_trace_entry(struct trace_array *tr, | 288 | struct trace_entry *tracing_get_trace_entry(struct trace_array *tr, |
289 | struct trace_array_cpu *data); | 289 | struct trace_array_cpu *data); |
290 | void tracing_generic_entry_update(struct trace_entry *entry, | 290 | void tracing_generic_entry_update(struct trace_entry *entry, |
291 | unsigned long flags); | 291 | unsigned long flags, |
292 | int pc); | ||
292 | 293 | ||
293 | void ftrace(struct trace_array *tr, | 294 | void ftrace(struct trace_array *tr, |
294 | struct trace_array_cpu *data, | 295 | struct trace_array_cpu *data, |
295 | unsigned long ip, | 296 | unsigned long ip, |
296 | unsigned long parent_ip, | 297 | unsigned long parent_ip, |
297 | unsigned long flags); | 298 | unsigned long flags, int pc); |
298 | void tracing_sched_switch_trace(struct trace_array *tr, | 299 | void tracing_sched_switch_trace(struct trace_array *tr, |
299 | struct trace_array_cpu *data, | 300 | struct trace_array_cpu *data, |
300 | struct task_struct *prev, | 301 | struct task_struct *prev, |
301 | struct task_struct *next, | 302 | struct task_struct *next, |
302 | unsigned long flags); | 303 | unsigned long flags, int pc); |
303 | void tracing_record_cmdline(struct task_struct *tsk); | 304 | void tracing_record_cmdline(struct task_struct *tsk); |
304 | 305 | ||
305 | void tracing_sched_wakeup_trace(struct trace_array *tr, | 306 | void tracing_sched_wakeup_trace(struct trace_array *tr, |
306 | struct trace_array_cpu *data, | 307 | struct trace_array_cpu *data, |
307 | struct task_struct *wakee, | 308 | struct task_struct *wakee, |
308 | struct task_struct *cur, | 309 | struct task_struct *cur, |
309 | unsigned long flags); | 310 | unsigned long flags, int pc); |
310 | void trace_special(struct trace_array *tr, | 311 | void trace_special(struct trace_array *tr, |
311 | struct trace_array_cpu *data, | 312 | struct trace_array_cpu *data, |
312 | unsigned long arg1, | 313 | unsigned long arg1, |
313 | unsigned long arg2, | 314 | unsigned long arg2, |
314 | unsigned long arg3); | 315 | unsigned long arg3, int pc); |
315 | void trace_function(struct trace_array *tr, | 316 | void trace_function(struct trace_array *tr, |
316 | struct trace_array_cpu *data, | 317 | struct trace_array_cpu *data, |
317 | unsigned long ip, | 318 | unsigned long ip, |
318 | unsigned long parent_ip, | 319 | unsigned long parent_ip, |
319 | unsigned long flags); | 320 | unsigned long flags, int pc); |
320 | 321 | ||
321 | void tracing_start_cmdline_record(void); | 322 | void tracing_start_cmdline_record(void); |
322 | void tracing_stop_cmdline_record(void); | 323 | void tracing_stop_cmdline_record(void); |