diff options
Diffstat (limited to 'kernel/trace/trace_ksym.c')
-rw-r--r-- | kernel/trace/trace_ksym.c | 42 |
1 files changed, 20 insertions, 22 deletions
diff --git a/kernel/trace/trace_ksym.c b/kernel/trace/trace_ksym.c index c538b15b95d6..ddfa0fd43bc0 100644 --- a/kernel/trace/trace_ksym.c +++ b/kernel/trace/trace_ksym.c | |||
@@ -42,9 +42,7 @@ | |||
42 | 42 | ||
43 | struct trace_ksym { | 43 | struct trace_ksym { |
44 | struct perf_event **ksym_hbp; | 44 | struct perf_event **ksym_hbp; |
45 | unsigned long ksym_addr; | 45 | struct perf_event_attr attr; |
46 | int type; | ||
47 | int len; | ||
48 | #ifdef CONFIG_PROFILE_KSYM_TRACER | 46 | #ifdef CONFIG_PROFILE_KSYM_TRACER |
49 | unsigned long counter; | 47 | unsigned long counter; |
50 | #endif | 48 | #endif |
@@ -71,7 +69,7 @@ void ksym_collect_stats(unsigned long hbp_hit_addr) | |||
71 | 69 | ||
72 | rcu_read_lock(); | 70 | rcu_read_lock(); |
73 | hlist_for_each_entry_rcu(entry, node, &ksym_filter_head, ksym_hlist) { | 71 | hlist_for_each_entry_rcu(entry, node, &ksym_filter_head, ksym_hlist) { |
74 | if ((entry->ksym_addr == hbp_hit_addr) && | 72 | if ((entry->attr.bp_addr == hbp_hit_addr) && |
75 | (entry->counter <= MAX_UL_INT)) { | 73 | (entry->counter <= MAX_UL_INT)) { |
76 | entry->counter++; | 74 | entry->counter++; |
77 | break; | 75 | break; |
@@ -192,14 +190,15 @@ int process_new_ksym_entry(char *ksymname, int op, unsigned long addr) | |||
192 | if (!entry) | 190 | if (!entry) |
193 | return -ENOMEM; | 191 | return -ENOMEM; |
194 | 192 | ||
195 | entry->type = op; | 193 | hw_breakpoint_init(&entry->attr); |
196 | entry->ksym_addr = addr; | 194 | |
197 | entry->len = HW_BREAKPOINT_LEN_4; | 195 | entry->attr.bp_type = op; |
196 | entry->attr.bp_addr = addr; | ||
197 | entry->attr.bp_len = HW_BREAKPOINT_LEN_4; | ||
198 | 198 | ||
199 | ret = -EAGAIN; | 199 | ret = -EAGAIN; |
200 | entry->ksym_hbp = register_wide_hw_breakpoint(entry->ksym_addr, | 200 | entry->ksym_hbp = register_wide_hw_breakpoint(&entry->attr, |
201 | entry->len, entry->type, | 201 | ksym_hbp_handler); |
202 | ksym_hbp_handler, true); | ||
203 | 202 | ||
204 | if (IS_ERR(entry->ksym_hbp)) { | 203 | if (IS_ERR(entry->ksym_hbp)) { |
205 | ret = PTR_ERR(entry->ksym_hbp); | 204 | ret = PTR_ERR(entry->ksym_hbp); |
@@ -236,12 +235,12 @@ static ssize_t ksym_trace_filter_read(struct file *filp, char __user *ubuf, | |||
236 | mutex_lock(&ksym_tracer_mutex); | 235 | mutex_lock(&ksym_tracer_mutex); |
237 | 236 | ||
238 | hlist_for_each_entry(entry, node, &ksym_filter_head, ksym_hlist) { | 237 | hlist_for_each_entry(entry, node, &ksym_filter_head, ksym_hlist) { |
239 | ret = trace_seq_printf(s, "%pS:", (void *)entry->ksym_addr); | 238 | ret = trace_seq_printf(s, "%pS:", (void *)entry->attr.bp_addr); |
240 | if (entry->type == HW_BREAKPOINT_R) | 239 | if (entry->attr.bp_type == HW_BREAKPOINT_R) |
241 | ret = trace_seq_puts(s, "r--\n"); | 240 | ret = trace_seq_puts(s, "r--\n"); |
242 | else if (entry->type == HW_BREAKPOINT_W) | 241 | else if (entry->attr.bp_type == HW_BREAKPOINT_W) |
243 | ret = trace_seq_puts(s, "-w-\n"); | 242 | ret = trace_seq_puts(s, "-w-\n"); |
244 | else if (entry->type == (HW_BREAKPOINT_W | HW_BREAKPOINT_R)) | 243 | else if (entry->attr.bp_type == (HW_BREAKPOINT_W | HW_BREAKPOINT_R)) |
245 | ret = trace_seq_puts(s, "rw-\n"); | 244 | ret = trace_seq_puts(s, "rw-\n"); |
246 | WARN_ON_ONCE(!ret); | 245 | WARN_ON_ONCE(!ret); |
247 | } | 246 | } |
@@ -317,9 +316,9 @@ static ssize_t ksym_trace_filter_write(struct file *file, | |||
317 | 316 | ||
318 | ret = -EINVAL; | 317 | ret = -EINVAL; |
319 | hlist_for_each_entry(entry, node, &ksym_filter_head, ksym_hlist) { | 318 | hlist_for_each_entry(entry, node, &ksym_filter_head, ksym_hlist) { |
320 | if (entry->ksym_addr == ksym_addr) { | 319 | if (entry->attr.bp_addr == ksym_addr) { |
321 | /* Check for malformed request: (6) */ | 320 | /* Check for malformed request: (6) */ |
322 | if (entry->type != op) | 321 | if (entry->attr.bp_type != op) |
323 | changed = 1; | 322 | changed = 1; |
324 | else | 323 | else |
325 | goto out; | 324 | goto out; |
@@ -328,13 +327,12 @@ static ssize_t ksym_trace_filter_write(struct file *file, | |||
328 | } | 327 | } |
329 | if (changed) { | 328 | if (changed) { |
330 | unregister_wide_hw_breakpoint(entry->ksym_hbp); | 329 | unregister_wide_hw_breakpoint(entry->ksym_hbp); |
331 | entry->type = op; | 330 | entry->attr.bp_type = op; |
332 | ret = 0; | 331 | ret = 0; |
333 | if (op > 0) { | 332 | if (op > 0) { |
334 | entry->ksym_hbp = | 333 | entry->ksym_hbp = |
335 | register_wide_hw_breakpoint(entry->ksym_addr, | 334 | register_wide_hw_breakpoint(&entry->attr, |
336 | entry->len, entry->type, | 335 | ksym_hbp_handler); |
337 | ksym_hbp_handler, true); | ||
338 | if (IS_ERR(entry->ksym_hbp)) | 336 | if (IS_ERR(entry->ksym_hbp)) |
339 | ret = PTR_ERR(entry->ksym_hbp); | 337 | ret = PTR_ERR(entry->ksym_hbp); |
340 | else | 338 | else |
@@ -489,7 +487,7 @@ static int ksym_tracer_stat_show(struct seq_file *m, void *v) | |||
489 | 487 | ||
490 | entry = hlist_entry(stat, struct trace_ksym, ksym_hlist); | 488 | entry = hlist_entry(stat, struct trace_ksym, ksym_hlist); |
491 | 489 | ||
492 | access_type = entry->type; | 490 | access_type = entry->attr.bp_type; |
493 | 491 | ||
494 | switch (access_type) { | 492 | switch (access_type) { |
495 | case HW_BREAKPOINT_R: | 493 | case HW_BREAKPOINT_R: |
@@ -505,7 +503,7 @@ static int ksym_tracer_stat_show(struct seq_file *m, void *v) | |||
505 | seq_puts(m, " NA "); | 503 | seq_puts(m, " NA "); |
506 | } | 504 | } |
507 | 505 | ||
508 | if (lookup_symbol_name(entry->ksym_addr, fn_name) >= 0) | 506 | if (lookup_symbol_name(entry->attr.bp_addr, fn_name) >= 0) |
509 | seq_printf(m, " %-36s", fn_name); | 507 | seq_printf(m, " %-36s", fn_name); |
510 | else | 508 | else |
511 | seq_printf(m, " %-36s", "<NA>"); | 509 | seq_printf(m, " %-36s", "<NA>"); |