aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/linux/interrupt.h2
-rw-r--r--include/trace/events/irq.h54
-rw-r--r--kernel/softirq.c16
3 files changed, 30 insertions, 42 deletions
diff --git a/include/linux/interrupt.h b/include/linux/interrupt.h
index 531495db1708..0ac194946fec 100644
--- a/include/linux/interrupt.h
+++ b/include/linux/interrupt.h
@@ -410,7 +410,7 @@ extern void open_softirq(int nr, void (*action)(struct softirq_action *));
410extern void softirq_init(void); 410extern void softirq_init(void);
411static inline void __raise_softirq_irqoff(unsigned int nr) 411static inline void __raise_softirq_irqoff(unsigned int nr)
412{ 412{
413 trace_softirq_raise((struct softirq_action *)(unsigned long)nr, NULL); 413 trace_softirq_raise(nr);
414 or_softirq_pending(1UL << nr); 414 or_softirq_pending(1UL << nr);
415} 415}
416 416
diff --git a/include/trace/events/irq.h b/include/trace/events/irq.h
index 6fa7cbab7d93..1c09820df585 100644
--- a/include/trace/events/irq.h
+++ b/include/trace/events/irq.h
@@ -86,76 +86,62 @@ TRACE_EVENT(irq_handler_exit,
86 86
87DECLARE_EVENT_CLASS(softirq, 87DECLARE_EVENT_CLASS(softirq,
88 88
89 TP_PROTO(struct softirq_action *h, struct softirq_action *vec), 89 TP_PROTO(unsigned int vec_nr),
90 90
91 TP_ARGS(h, vec), 91 TP_ARGS(vec_nr),
92 92
93 TP_STRUCT__entry( 93 TP_STRUCT__entry(
94 __field( int, vec ) 94 __field( unsigned int, vec )
95 ), 95 ),
96 96
97 TP_fast_assign( 97 TP_fast_assign(
98 if (vec) 98 __entry->vec = vec_nr;
99 __entry->vec = (int)(h - vec);
100 else
101 __entry->vec = (int)(long)h;
102 ), 99 ),
103 100
104 TP_printk("vec=%d [action=%s]", __entry->vec, 101 TP_printk("vec=%u [action=%s]", __entry->vec,
105 show_softirq_name(__entry->vec)) 102 show_softirq_name(__entry->vec))
106); 103);
107 104
108/** 105/**
109 * softirq_entry - called immediately before the softirq handler 106 * softirq_entry - called immediately before the softirq handler
110 * @h: pointer to struct softirq_action 107 * @vec_nr: softirq vector number
111 * @vec: pointer to first struct softirq_action in softirq_vec array
112 * 108 *
113 * The @h parameter, contains a pointer to the struct softirq_action 109 * When used in combination with the softirq_exit tracepoint
114 * which has a pointer to the action handler that is called. By subtracting 110 * we can determine the softirq handler runtine.
115 * the @vec pointer from the @h pointer, we can determine the softirq
116 * number. Also, when used in combination with the softirq_exit tracepoint
117 * we can determine the softirq latency.
118 */ 111 */
119DEFINE_EVENT(softirq, softirq_entry, 112DEFINE_EVENT(softirq, softirq_entry,
120 113
121 TP_PROTO(struct softirq_action *h, struct softirq_action *vec), 114 TP_PROTO(unsigned int vec_nr),
122 115
123 TP_ARGS(h, vec) 116 TP_ARGS(vec_nr)
124); 117);
125 118
126/** 119/**
127 * softirq_exit - called immediately after the softirq handler returns 120 * softirq_exit - called immediately after the softirq handler returns
128 * @h: pointer to struct softirq_action 121 * @vec_nr: softirq vector number
129 * @vec: pointer to first struct softirq_action in softirq_vec array
130 * 122 *
131 * The @h parameter contains a pointer to the struct softirq_action 123 * When used in combination with the softirq_entry tracepoint
132 * that has handled the softirq. By subtracting the @vec pointer from 124 * we can determine the softirq handler runtine.
133 * the @h pointer, we can determine the softirq number. Also, when used in
134 * combination with the softirq_entry tracepoint we can determine the softirq
135 * latency.
136 */ 125 */
137DEFINE_EVENT(softirq, softirq_exit, 126DEFINE_EVENT(softirq, softirq_exit,
138 127
139 TP_PROTO(struct softirq_action *h, struct softirq_action *vec), 128 TP_PROTO(unsigned int vec_nr),
140 129
141 TP_ARGS(h, vec) 130 TP_ARGS(vec_nr)
142); 131);
143 132
144/** 133/**
145 * softirq_raise - called immediately when a softirq is raised 134 * softirq_raise - called immediately when a softirq is raised
146 * @h: pointer to struct softirq_action 135 * @vec_nr: softirq vector number
147 * @vec: pointer to first struct softirq_action in softirq_vec array
148 * 136 *
149 * The @h parameter contains a pointer to the softirq vector number which is 137 * When used in combination with the softirq_entry tracepoint
150 * raised. @vec is NULL and it means @h includes vector number not 138 * we can determine the softirq raise to run latency.
151 * softirq_action. When used in combination with the softirq_entry tracepoint
152 * we can determine the softirq raise latency.
153 */ 139 */
154DEFINE_EVENT(softirq, softirq_raise, 140DEFINE_EVENT(softirq, softirq_raise,
155 141
156 TP_PROTO(struct softirq_action *h, struct softirq_action *vec), 142 TP_PROTO(unsigned int vec_nr),
157 143
158 TP_ARGS(h, vec) 144 TP_ARGS(vec_nr)
159); 145);
160 146
161#endif /* _TRACE_IRQ_H */ 147#endif /* _TRACE_IRQ_H */
diff --git a/kernel/softirq.c b/kernel/softirq.c
index 07b4f1b1a73a..b3cb1dc15795 100644
--- a/kernel/softirq.c
+++ b/kernel/softirq.c
@@ -212,18 +212,20 @@ restart:
212 212
213 do { 213 do {
214 if (pending & 1) { 214 if (pending & 1) {
215 unsigned int vec_nr = h - softirq_vec;
215 int prev_count = preempt_count(); 216 int prev_count = preempt_count();
216 kstat_incr_softirqs_this_cpu(h - softirq_vec);
217 217
218 trace_softirq_entry(h, softirq_vec); 218 kstat_incr_softirqs_this_cpu(vec_nr);
219
220 trace_softirq_entry(vec_nr);
219 h->action(h); 221 h->action(h);
220 trace_softirq_exit(h, softirq_vec); 222 trace_softirq_exit(vec_nr);
221 if (unlikely(prev_count != preempt_count())) { 223 if (unlikely(prev_count != preempt_count())) {
222 printk(KERN_ERR "huh, entered softirq %td %s %p" 224 printk(KERN_ERR "huh, entered softirq %u %s %p"
223 "with preempt_count %08x," 225 "with preempt_count %08x,"
224 " exited with %08x?\n", h - softirq_vec, 226 " exited with %08x?\n", vec_nr,
225 softirq_to_name[h - softirq_vec], 227 softirq_to_name[vec_nr], h->action,
226 h->action, prev_count, preempt_count()); 228 prev_count, preempt_count());
227 preempt_count() = prev_count; 229 preempt_count() = prev_count;
228 } 230 }
229 231