Blame view

kernel/trace/trace_sched_switch.c 5.79 KB
35e8e302e   Steven Rostedt   ftrace: add traci...
1
2
3
4
5
6
7
8
9
10
11
  /*
   * trace context switch
   *
   * Copyright (C) 2007 Steven Rostedt <srostedt@redhat.com>
   *
   */
  #include <linux/module.h>
  #include <linux/fs.h>
  #include <linux/debugfs.h>
  #include <linux/kallsyms.h>
  #include <linux/uaccess.h>
35e8e302e   Steven Rostedt   ftrace: add traci...
12
  #include <linux/ftrace.h>
ad8d75fff   Steven Rostedt   tracing/events: m...
13
  #include <trace/events/sched.h>
35e8e302e   Steven Rostedt   ftrace: add traci...
14
15
16
17
18
  
  #include "trace.h"
  
  static struct trace_array	*ctx_trace;
  static int __read_mostly	tracer_enabled;
efade6e78   Frederic Weisbecker   tracing/ftrace: t...
19
20
  static int			sched_ref;
  static DEFINE_MUTEX(sched_register_mutex);
5fec6ddcb   Steven Rostedt   tracing: make sch...
21
  static int			sched_stopped;
35e8e302e   Steven Rostedt   ftrace: add traci...
22

82e04af49   Frederic Weisbecker   tracing: Move sch...
23
24
25
26
27
28
29
30
  
  void
  tracing_sched_switch_trace(struct trace_array *tr,
  			   struct task_struct *prev,
  			   struct task_struct *next,
  			   unsigned long flags, int pc)
  {
  	struct ftrace_event_call *call = &event_context_switch;
e77405ad8   Steven Rostedt   tracing: pass aro...
31
  	struct ring_buffer *buffer = tr->buffer;
82e04af49   Frederic Weisbecker   tracing: Move sch...
32
33
  	struct ring_buffer_event *event;
  	struct ctx_switch_entry *entry;
e77405ad8   Steven Rostedt   tracing: pass aro...
34
  	event = trace_buffer_lock_reserve(buffer, TRACE_CTX,
82e04af49   Frederic Weisbecker   tracing: Move sch...
35
36
37
38
39
40
41
42
43
44
45
  					  sizeof(*entry), flags, pc);
  	if (!event)
  		return;
  	entry	= ring_buffer_event_data(event);
  	entry->prev_pid			= prev->pid;
  	entry->prev_prio		= prev->prio;
  	entry->prev_state		= prev->state;
  	entry->next_pid			= next->pid;
  	entry->next_prio		= next->prio;
  	entry->next_state		= next->state;
  	entry->next_cpu	= task_cpu(next);
e77405ad8   Steven Rostedt   tracing: pass aro...
46
47
  	if (!filter_check_discard(call, entry, buffer, event))
  		trace_buffer_unlock_commit(buffer, event, flags, pc);
82e04af49   Frederic Weisbecker   tracing: Move sch...
48
  }
e309b41dd   Ingo Molnar   ftrace: remove no...
49
  static void
38516ab59   Steven Rostedt   tracing: Let trac...
50
  probe_sched_switch(void *ignore, struct task_struct *prev, struct task_struct *next)
35e8e302e   Steven Rostedt   ftrace: add traci...
51
  {
35e8e302e   Steven Rostedt   ftrace: add traci...
52
53
  	struct trace_array_cpu *data;
  	unsigned long flags;
35e8e302e   Steven Rostedt   ftrace: add traci...
54
  	int cpu;
38697053f   Steven Rostedt   ftrace: preempt d...
55
  	int pc;
35e8e302e   Steven Rostedt   ftrace: add traci...
56

dcef788eb   Zhaolei   ftrace: clean up ...
57
  	if (unlikely(!sched_ref))
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
58
  		return;
41bc8144d   Steven Rostedt   ftrace: fix up cm...
59
60
  	tracing_record_cmdline(prev);
  	tracing_record_cmdline(next);
dcef788eb   Zhaolei   ftrace: clean up ...
61
  	if (!tracer_enabled || sched_stopped)
35e8e302e   Steven Rostedt   ftrace: add traci...
62
  		return;
38697053f   Steven Rostedt   ftrace: preempt d...
63
  	pc = preempt_count();
18cef379d   Steven Rostedt   ftrace: don't use...
64
  	local_irq_save(flags);
35e8e302e   Steven Rostedt   ftrace: add traci...
65
  	cpu = raw_smp_processor_id();
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
66
  	data = ctx_trace->data[cpu];
35e8e302e   Steven Rostedt   ftrace: add traci...
67

3ea2e6d71   Steven Rostedt   ftrace: make some...
68
  	if (likely(!atomic_read(&data->disabled)))
7be421510   Arnaldo Carvalho de Melo   trace: Remove unu...
69
  		tracing_sched_switch_trace(ctx_trace, prev, next, flags, pc);
35e8e302e   Steven Rostedt   ftrace: add traci...
70

18cef379d   Steven Rostedt   ftrace: don't use...
71
  	local_irq_restore(flags);
35e8e302e   Steven Rostedt   ftrace: add traci...
72
  }
82e04af49   Frederic Weisbecker   tracing: Move sch...
73
74
75
76
77
78
79
80
81
  void
  tracing_sched_wakeup_trace(struct trace_array *tr,
  			   struct task_struct *wakee,
  			   struct task_struct *curr,
  			   unsigned long flags, int pc)
  {
  	struct ftrace_event_call *call = &event_wakeup;
  	struct ring_buffer_event *event;
  	struct ctx_switch_entry *entry;
e77405ad8   Steven Rostedt   tracing: pass aro...
82
  	struct ring_buffer *buffer = tr->buffer;
82e04af49   Frederic Weisbecker   tracing: Move sch...
83

e77405ad8   Steven Rostedt   tracing: pass aro...
84
  	event = trace_buffer_lock_reserve(buffer, TRACE_WAKE,
82e04af49   Frederic Weisbecker   tracing: Move sch...
85
86
87
88
89
90
91
92
93
94
95
  					  sizeof(*entry), flags, pc);
  	if (!event)
  		return;
  	entry	= ring_buffer_event_data(event);
  	entry->prev_pid			= curr->pid;
  	entry->prev_prio		= curr->prio;
  	entry->prev_state		= curr->state;
  	entry->next_pid			= wakee->pid;
  	entry->next_prio		= wakee->prio;
  	entry->next_state		= wakee->state;
  	entry->next_cpu			= task_cpu(wakee);
e77405ad8   Steven Rostedt   tracing: pass aro...
96
97
98
99
  	if (!filter_check_discard(call, entry, buffer, event))
  		ring_buffer_unlock_commit(buffer, event);
  	ftrace_trace_stack(tr->buffer, flags, 6, pc);
  	ftrace_trace_userstack(tr->buffer, flags, pc);
82e04af49   Frederic Weisbecker   tracing: Move sch...
100
  }
4e6555190   Ingo Molnar   ftrace: sched tra...
101
  static void
38516ab59   Steven Rostedt   tracing: Let trac...
102
  probe_sched_wakeup(void *ignore, struct task_struct *wakee, int success)
57422797d   Ingo Molnar   ftrace: add wakeu...
103
  {
57422797d   Ingo Molnar   ftrace: add wakeu...
104
105
  	struct trace_array_cpu *data;
  	unsigned long flags;
38697053f   Steven Rostedt   ftrace: preempt d...
106
  	int cpu, pc;
57422797d   Ingo Molnar   ftrace: add wakeu...
107

dcef788eb   Zhaolei   ftrace: clean up ...
108
  	if (unlikely(!sched_ref))
57422797d   Ingo Molnar   ftrace: add wakeu...
109
  		return;
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
110
  	tracing_record_cmdline(current);
d9af56fbd   Ingo Molnar   ftrace: fix cmdli...
111

dcef788eb   Zhaolei   ftrace: clean up ...
112
  	if (!tracer_enabled || sched_stopped)
8bcae09b9   Zhaolei   ftrace: Add check...
113
  		return;
dcef788eb   Zhaolei   ftrace: clean up ...
114
  	pc = preempt_count();
57422797d   Ingo Molnar   ftrace: add wakeu...
115
116
  	local_irq_save(flags);
  	cpu = raw_smp_processor_id();
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
117
  	data = ctx_trace->data[cpu];
57422797d   Ingo Molnar   ftrace: add wakeu...
118

3ea2e6d71   Steven Rostedt   ftrace: make some...
119
  	if (likely(!atomic_read(&data->disabled)))
7be421510   Arnaldo Carvalho de Melo   trace: Remove unu...
120
  		tracing_sched_wakeup_trace(ctx_trace, wakee, current,
38697053f   Steven Rostedt   ftrace: preempt d...
121
  					   flags, pc);
57422797d   Ingo Molnar   ftrace: add wakeu...
122

57422797d   Ingo Molnar   ftrace: add wakeu...
123
124
  	local_irq_restore(flags);
  }
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
125
126
127
  static int tracing_sched_register(void)
  {
  	int ret;
38516ab59   Steven Rostedt   tracing: Let trac...
128
  	ret = register_trace_sched_wakeup(probe_sched_wakeup, NULL);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
129
  	if (ret) {
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
130
  		pr_info("wakeup trace: Couldn't activate tracepoint"
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
131
132
133
134
  			" probe to kernel_sched_wakeup
  ");
  		return ret;
  	}
38516ab59   Steven Rostedt   tracing: Let trac...
135
  	ret = register_trace_sched_wakeup_new(probe_sched_wakeup, NULL);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
136
  	if (ret) {
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
137
  		pr_info("wakeup trace: Couldn't activate tracepoint"
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
138
139
140
141
  			" probe to kernel_sched_wakeup_new
  ");
  		goto fail_deprobe;
  	}
38516ab59   Steven Rostedt   tracing: Let trac...
142
  	ret = register_trace_sched_switch(probe_sched_switch, NULL);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
143
  	if (ret) {
b07c3f193   Mathieu Desnoyers   ftrace: port to t...
144
  		pr_info("sched trace: Couldn't activate tracepoint"
73d8b8bc4   Wenji Huang   tracing: fix typi...
145
146
  			" probe to kernel_sched_switch
  ");
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
147
148
149
150
151
  		goto fail_deprobe_wake_new;
  	}
  
  	return ret;
  fail_deprobe_wake_new:
38516ab59   Steven Rostedt   tracing: Let trac...
152
  	unregister_trace_sched_wakeup_new(probe_sched_wakeup, NULL);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
153
  fail_deprobe:
38516ab59   Steven Rostedt   tracing: Let trac...
154
  	unregister_trace_sched_wakeup(probe_sched_wakeup, NULL);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
155
156
157
158
159
  	return ret;
  }
  
  static void tracing_sched_unregister(void)
  {
38516ab59   Steven Rostedt   tracing: Let trac...
160
161
162
  	unregister_trace_sched_switch(probe_sched_switch, NULL);
  	unregister_trace_sched_wakeup_new(probe_sched_wakeup, NULL);
  	unregister_trace_sched_wakeup(probe_sched_wakeup, NULL);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
163
  }
f22529351   Ingo Molnar   namespacecheck: f...
164
  static void tracing_start_sched_switch(void)
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
165
  {
efade6e78   Frederic Weisbecker   tracing/ftrace: t...
166
  	mutex_lock(&sched_register_mutex);
e168e0516   Steven Rostedt   ftrace: fix sched...
167
  	if (!(sched_ref++))
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
168
  		tracing_sched_register();
efade6e78   Frederic Weisbecker   tracing/ftrace: t...
169
  	mutex_unlock(&sched_register_mutex);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
170
  }
f22529351   Ingo Molnar   namespacecheck: f...
171
  static void tracing_stop_sched_switch(void)
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
172
  {
efade6e78   Frederic Weisbecker   tracing/ftrace: t...
173
  	mutex_lock(&sched_register_mutex);
e168e0516   Steven Rostedt   ftrace: fix sched...
174
  	if (!(--sched_ref))
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
175
  		tracing_sched_unregister();
efade6e78   Frederic Weisbecker   tracing/ftrace: t...
176
  	mutex_unlock(&sched_register_mutex);
5b82a1b08   Mathieu Desnoyers   Port ftrace to ma...
177
  }
41bc8144d   Steven Rostedt   ftrace: fix up cm...
178
179
180
181
182
183
184
185
186
  void tracing_start_cmdline_record(void)
  {
  	tracing_start_sched_switch();
  }
  
  void tracing_stop_cmdline_record(void)
  {
  	tracing_stop_sched_switch();
  }
75f5c47da   Steven Rostedt   ftrace: fix boot ...
187
  /**
e168e0516   Steven Rostedt   ftrace: fix sched...
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
   * tracing_start_sched_switch_record - start tracing context switches
   *
   * Turns on context switch tracing for a tracer.
   */
  void tracing_start_sched_switch_record(void)
  {
  	if (unlikely(!ctx_trace)) {
  		WARN_ON(1);
  		return;
  	}
  
  	tracing_start_sched_switch();
  
  	mutex_lock(&sched_register_mutex);
  	tracer_enabled++;
  	mutex_unlock(&sched_register_mutex);
  }
  
  /**
   * tracing_stop_sched_switch_record - start tracing context switches
   *
   * Turns off context switch tracing for a tracer.
   */
  void tracing_stop_sched_switch_record(void)
  {
  	mutex_lock(&sched_register_mutex);
  	tracer_enabled--;
  	WARN_ON(tracer_enabled < 0);
  	mutex_unlock(&sched_register_mutex);
  
  	tracing_stop_sched_switch();
  }
  
  /**
   * tracing_sched_switch_assign_trace - assign a trace array for ctx switch
75f5c47da   Steven Rostedt   ftrace: fix boot ...
223
224
225
226
227
228
   * @tr: trace array pointer to assign
   *
   * Some tracers might want to record the context switches in their
   * trace. This function lets those tracers assign the trace array
   * to use.
   */
e168e0516   Steven Rostedt   ftrace: fix sched...
229
  void tracing_sched_switch_assign_trace(struct trace_array *tr)
75f5c47da   Steven Rostedt   ftrace: fix boot ...
230
231
232
  {
  	ctx_trace = tr;
  }