diff options
Diffstat (limited to 'kernel/trace')
| -rw-r--r-- | kernel/trace/Makefile | 4 | ||||
| -rw-r--r-- | kernel/trace/ftrace.c | 2 | ||||
| -rw-r--r-- | kernel/trace/power-traces.c | 1 | ||||
| -rw-r--r-- | kernel/trace/ring_buffer.c | 42 | ||||
| -rw-r--r-- | kernel/trace/ring_buffer_benchmark.c | 18 | ||||
| -rw-r--r-- | kernel/trace/trace.c | 194 | ||||
| -rw-r--r-- | kernel/trace/trace.h | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_branch.c | 1 | ||||
| -rw-r--r-- | kernel/trace/trace_event_perf.c | 4 | ||||
| -rw-r--r-- | kernel/trace/trace_events.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_export.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_functions_graph.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_irqsoff.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_kprobe.c | 6 | ||||
| -rw-r--r-- | kernel/trace/trace_nop.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_output.c | 44 | ||||
| -rw-r--r-- | kernel/trace/trace_printk.c | 4 | ||||
| -rw-r--r-- | kernel/trace/trace_sched_switch.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_sched_wakeup.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_seq.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_stack.c | 4 | ||||
| -rw-r--r-- | kernel/trace/trace_stat.c | 2 | ||||
| -rw-r--r-- | kernel/trace/trace_syscalls.c | 4 | ||||
| -rw-r--r-- | kernel/trace/trace_uprobe.c | 4 |
24 files changed, 190 insertions, 162 deletions
diff --git a/kernel/trace/Makefile b/kernel/trace/Makefile index 979ccde26720..98f26588255e 100644 --- a/kernel/trace/Makefile +++ b/kernel/trace/Makefile | |||
| @@ -3,11 +3,11 @@ | |||
| 3 | 3 | ||
| 4 | ifdef CONFIG_FUNCTION_TRACER | 4 | ifdef CONFIG_FUNCTION_TRACER |
| 5 | ORIG_CFLAGS := $(KBUILD_CFLAGS) | 5 | ORIG_CFLAGS := $(KBUILD_CFLAGS) |
| 6 | KBUILD_CFLAGS = $(subst -pg,,$(ORIG_CFLAGS)) | 6 | KBUILD_CFLAGS = $(subst $(CC_FLAGS_FTRACE),,$(ORIG_CFLAGS)) |
| 7 | 7 | ||
| 8 | ifdef CONFIG_FTRACE_SELFTEST | 8 | ifdef CONFIG_FTRACE_SELFTEST |
| 9 | # selftest needs instrumentation | 9 | # selftest needs instrumentation |
| 10 | CFLAGS_trace_selftest_dynamic.o = -pg | 10 | CFLAGS_trace_selftest_dynamic.o = $(CC_FLAGS_FTRACE) |
| 11 | obj-y += trace_selftest_dynamic.o | 11 | obj-y += trace_selftest_dynamic.o |
| 12 | endif | 12 | endif |
| 13 | endif | 13 | endif |
diff --git a/kernel/trace/ftrace.c b/kernel/trace/ftrace.c index 224e768bdc73..45e5cb143d17 100644 --- a/kernel/trace/ftrace.c +++ b/kernel/trace/ftrace.c | |||
| @@ -5456,7 +5456,7 @@ static __init int ftrace_init_debugfs(void) | |||
| 5456 | struct dentry *d_tracer; | 5456 | struct dentry *d_tracer; |
| 5457 | 5457 | ||
| 5458 | d_tracer = tracing_init_dentry(); | 5458 | d_tracer = tracing_init_dentry(); |
| 5459 | if (!d_tracer) | 5459 | if (IS_ERR(d_tracer)) |
| 5460 | return 0; | 5460 | return 0; |
| 5461 | 5461 | ||
| 5462 | ftrace_init_dyn_debugfs(d_tracer); | 5462 | ftrace_init_dyn_debugfs(d_tracer); |
diff --git a/kernel/trace/power-traces.c b/kernel/trace/power-traces.c index 1c71382b283d..eb4220a132ec 100644 --- a/kernel/trace/power-traces.c +++ b/kernel/trace/power-traces.c | |||
| @@ -13,5 +13,6 @@ | |||
| 13 | #define CREATE_TRACE_POINTS | 13 | #define CREATE_TRACE_POINTS |
| 14 | #include <trace/events/power.h> | 14 | #include <trace/events/power.h> |
| 15 | 15 | ||
| 16 | EXPORT_TRACEPOINT_SYMBOL_GPL(suspend_resume); | ||
| 16 | EXPORT_TRACEPOINT_SYMBOL_GPL(cpu_idle); | 17 | EXPORT_TRACEPOINT_SYMBOL_GPL(cpu_idle); |
| 17 | 18 | ||
diff --git a/kernel/trace/ring_buffer.c b/kernel/trace/ring_buffer.c index 7a4104cb95cb..5040d44fe5a3 100644 --- a/kernel/trace/ring_buffer.c +++ b/kernel/trace/ring_buffer.c | |||
| @@ -9,7 +9,6 @@ | |||
| 9 | #include <linux/trace_seq.h> | 9 | #include <linux/trace_seq.h> |
| 10 | #include <linux/spinlock.h> | 10 | #include <linux/spinlock.h> |
| 11 | #include <linux/irq_work.h> | 11 | #include <linux/irq_work.h> |
| 12 | #include <linux/debugfs.h> | ||
| 13 | #include <linux/uaccess.h> | 12 | #include <linux/uaccess.h> |
| 14 | #include <linux/hardirq.h> | 13 | #include <linux/hardirq.h> |
| 15 | #include <linux/kthread.h> /* for self test */ | 14 | #include <linux/kthread.h> /* for self test */ |
| @@ -23,7 +22,6 @@ | |||
| 23 | #include <linux/hash.h> | 22 | #include <linux/hash.h> |
| 24 | #include <linux/list.h> | 23 | #include <linux/list.h> |
| 25 | #include <linux/cpu.h> | 24 | #include <linux/cpu.h> |
| 26 | #include <linux/fs.h> | ||
| 27 | 25 | ||
| 28 | #include <asm/local.h> | 26 | #include <asm/local.h> |
| 29 | 27 | ||
| @@ -447,7 +445,10 @@ int ring_buffer_print_page_header(struct trace_seq *s) | |||
| 447 | struct rb_irq_work { | 445 | struct rb_irq_work { |
| 448 | struct irq_work work; | 446 | struct irq_work work; |
| 449 | wait_queue_head_t waiters; | 447 | wait_queue_head_t waiters; |
| 448 | wait_queue_head_t full_waiters; | ||
| 450 | bool waiters_pending; | 449 | bool waiters_pending; |
| 450 | bool full_waiters_pending; | ||
| 451 | bool wakeup_full; | ||
| 451 | }; | 452 | }; |
| 452 | 453 | ||
| 453 | /* | 454 | /* |
| @@ -529,6 +530,10 @@ static void rb_wake_up_waiters(struct irq_work *work) | |||
| 529 | struct rb_irq_work *rbwork = container_of(work, struct rb_irq_work, work); | 530 | struct rb_irq_work *rbwork = container_of(work, struct rb_irq_work, work); |
| 530 | 531 | ||
| 531 | wake_up_all(&rbwork->waiters); | 532 | wake_up_all(&rbwork->waiters); |
| 533 | if (rbwork->wakeup_full) { | ||
| 534 | rbwork->wakeup_full = false; | ||
| 535 | wake_up_all(&rbwork->full_waiters); | ||
| 536 | } | ||
| 532 | } | 537 | } |
| 533 | 538 | ||
| 534 | /** | 539 | /** |
| @@ -553,9 +558,11 @@ int ring_buffer_wait(struct ring_buffer *buffer, int cpu, bool full) | |||
| 553 | * data in any cpu buffer, or a specific buffer, put the | 558 | * data in any cpu buffer, or a specific buffer, put the |
| 554 | * caller on the appropriate wait queue. | 559 | * caller on the appropriate wait queue. |
| 555 | */ | 560 | */ |
| 556 | if (cpu == RING_BUFFER_ALL_CPUS) | 561 | if (cpu == RING_BUFFER_ALL_CPUS) { |
| 557 | work = &buffer->irq_work; | 562 | work = &buffer->irq_work; |
| 558 | else { | 563 | /* Full only makes sense on per cpu reads */ |
| 564 | full = false; | ||
| 565 | } else { | ||
| 559 | if (!cpumask_test_cpu(cpu, buffer->cpumask)) | 566 | if (!cpumask_test_cpu(cpu, buffer->cpumask)) |
| 560 | return -ENODEV; | 567 | return -ENODEV; |
| 561 | cpu_buffer = buffer->buffers[cpu]; | 568 | cpu_buffer = buffer->buffers[cpu]; |
| @@ -564,7 +571,10 @@ int ring_buffer_wait(struct ring_buffer *buffer, int cpu, bool full) | |||
| 564 | 571 | ||
| 565 | 572 | ||
| 566 | while (true) { | 573 | while (true) { |
| 567 | prepare_to_wait(&work->waiters, &wait, TASK_INTERRUPTIBLE); | 574 | if (full) |
| 575 | prepare_to_wait(&work->full_waiters, &wait, TASK_INTERRUPTIBLE); | ||
| 576 | else | ||
| 577 | prepare_to_wait(&work->waiters, &wait, TASK_INTERRUPTIBLE); | ||
| 568 | 578 | ||
| 569 | /* | 579 | /* |
| 570 | * The events can happen in critical sections where | 580 | * The events can happen in critical sections where |
| @@ -586,7 +596,10 @@ int ring_buffer_wait(struct ring_buffer *buffer, int cpu, bool full) | |||
| 586 | * that is necessary is that the wake up happens after | 596 | * that is necessary is that the wake up happens after |
| 587 | * a task has been queued. It's OK for spurious wake ups. | 597 | * a task has been queued. It's OK for spurious wake ups. |
| 588 | */ | 598 | */ |
| 589 | work->waiters_pending = true; | 599 | if (full) |
| 600 | work->full_waiters_pending = true; | ||
| 601 | else | ||
| 602 | work->waiters_pending = true; | ||
| 590 | 603 | ||
| 591 | if (signal_pending(current)) { | 604 | if (signal_pending(current)) { |
| 592 | ret = -EINTR; | 605 | ret = -EINTR; |
| @@ -615,7 +628,10 @@ int ring_buffer_wait(struct ring_buffer *buffer, int cpu, bool full) | |||
| 615 | schedule(); | 628 | schedule(); |
| 616 | } | 629 | } |
| 617 | 630 | ||
| 618 | finish_wait(&work->waiters, &wait); | 631 | if (full) |
| 632 | finish_wait(&work->full_waiters, &wait); | ||
| 633 | else | ||
| 634 | finish_wait(&work->waiters, &wait); | ||
| 619 | 635 | ||
| 620 | return ret; | 636 | return ret; |
| 621 | } | 637 | } |
| @@ -1230,6 +1246,7 @@ rb_allocate_cpu_buffer(struct ring_buffer *buffer, int nr_pages, int cpu) | |||
| 1230 | init_completion(&cpu_buffer->update_done); | 1246 | init_completion(&cpu_buffer->update_done); |
| 1231 | init_irq_work(&cpu_buffer->irq_work.work, rb_wake_up_waiters); | 1247 | init_irq_work(&cpu_buffer->irq_work.work, rb_wake_up_waiters); |
| 1232 | init_waitqueue_head(&cpu_buffer->irq_work.waiters); | 1248 | init_waitqueue_head(&cpu_buffer->irq_work.waiters); |
| 1249 | init_waitqueue_head(&cpu_buffer->irq_work.full_waiters); | ||
| 1233 | 1250 | ||
| 1234 | bpage = kzalloc_node(ALIGN(sizeof(*bpage), cache_line_size()), | 1251 | bpage = kzalloc_node(ALIGN(sizeof(*bpage), cache_line_size()), |
| 1235 | GFP_KERNEL, cpu_to_node(cpu)); | 1252 | GFP_KERNEL, cpu_to_node(cpu)); |
| @@ -2801,6 +2818,8 @@ static void rb_commit(struct ring_buffer_per_cpu *cpu_buffer, | |||
| 2801 | static __always_inline void | 2818 | static __always_inline void |
| 2802 | rb_wakeups(struct ring_buffer *buffer, struct ring_buffer_per_cpu *cpu_buffer) | 2819 | rb_wakeups(struct ring_buffer *buffer, struct ring_buffer_per_cpu *cpu_buffer) |
| 2803 | { | 2820 | { |
| 2821 | bool pagebusy; | ||
| 2822 | |||
| 2804 | if (buffer->irq_work.waiters_pending) { | 2823 | if (buffer->irq_work.waiters_pending) { |
| 2805 | buffer->irq_work.waiters_pending = false; | 2824 | buffer->irq_work.waiters_pending = false; |
| 2806 | /* irq_work_queue() supplies it's own memory barriers */ | 2825 | /* irq_work_queue() supplies it's own memory barriers */ |
| @@ -2812,6 +2831,15 @@ rb_wakeups(struct ring_buffer *buffer, struct ring_buffer_per_cpu *cpu_buffer) | |||
| 2812 | /* irq_work_queue() supplies it's own memory barriers */ | 2831 | /* irq_work_queue() supplies it's own memory barriers */ |
| 2813 | irq_work_queue(&cpu_buffer->irq_work.work); | 2832 | irq_work_queue(&cpu_buffer->irq_work.work); |
| 2814 | } | 2833 | } |
| 2834 | |||
| 2835 | pagebusy = cpu_buffer->reader_page == cpu_buffer->commit_page; | ||
| 2836 | |||
| 2837 | if (!pagebusy && cpu_buffer->irq_work.full_waiters_pending) { | ||
| 2838 | cpu_buffer->irq_work.wakeup_full = true; | ||
| 2839 | cpu_buffer->irq_work.full_waiters_pending = false; | ||
| 2840 | /* irq_work_queue() supplies it's own memory barriers */ | ||
| 2841 | irq_work_queue(&cpu_buffer->irq_work.work); | ||
| 2842 | } | ||
| 2815 | } | 2843 | } |
| 2816 | 2844 | ||
| 2817 | /** | 2845 | /** |
diff --git a/kernel/trace/ring_buffer_benchmark.c b/kernel/trace/ring_buffer_benchmark.c index 3f9e328c30b5..13d945c0d03f 100644 --- a/kernel/trace/ring_buffer_benchmark.c +++ b/kernel/trace/ring_buffer_benchmark.c | |||
| @@ -7,7 +7,7 @@ | |||
| 7 | #include <linux/completion.h> | 7 | #include <linux/completion.h> |
| 8 | #include <linux/kthread.h> | 8 | #include <linux/kthread.h> |
| 9 | #include <linux/module.h> | 9 | #include <linux/module.h> |
| 10 | #include <linux/time.h> | 10 | #include <linux/ktime.h> |
| 11 | #include <asm/local.h> | 11 | #include <asm/local.h> |
| 12 | 12 | ||
| 13 | struct rb_page { | 13 | struct rb_page { |
| @@ -17,7 +17,7 @@ struct rb_page { | |||
| 17 | }; | 17 | }; |
| 18 | 18 | ||
| 19 | /* run time and sleep time in seconds */ | 19 | /* run time and sleep time in seconds */ |
| 20 | #define RUN_TIME 10 | 20 | #define RUN_TIME 10ULL |
| 21 | #define SLEEP_TIME 10 | 21 | #define SLEEP_TIME 10 |
| 22 | 22 | ||
| 23 | /* number of events for writer to wake up the reader */ | 23 | /* number of events for writer to wake up the reader */ |
| @@ -212,8 +212,7 @@ static void ring_buffer_consumer(void) | |||
| 212 | 212 | ||
| 213 | static void ring_buffer_producer(void) | 213 | static void ring_buffer_producer(void) |
| 214 | { | 214 | { |
| 215 | struct timeval start_tv; | 215 | ktime_t start_time, end_time, timeout; |
| 216 | struct timeval end_tv; | ||
| 217 | unsigned long long time; | 216 | unsigned long long time; |
| 218 | unsigned long long entries; | 217 | unsigned long long entries; |
| 219 | unsigned long long overruns; | 218 | unsigned long long overruns; |
| @@ -227,7 +226,8 @@ static void ring_buffer_producer(void) | |||
| 227 | * make the system stall) | 226 | * make the system stall) |
| 228 | */ | 227 | */ |
| 229 | trace_printk("Starting ring buffer hammer\n"); | 228 | trace_printk("Starting ring buffer hammer\n"); |
| 230 | do_gettimeofday(&start_tv); | 229 | start_time = ktime_get(); |
| 230 | timeout = ktime_add_ns(start_time, RUN_TIME * NSEC_PER_SEC); | ||
| 231 | do { | 231 | do { |
| 232 | struct ring_buffer_event *event; | 232 | struct ring_buffer_event *event; |
| 233 | int *entry; | 233 | int *entry; |
| @@ -244,7 +244,7 @@ static void ring_buffer_producer(void) | |||
| 244 | ring_buffer_unlock_commit(buffer, event); | 244 | ring_buffer_unlock_commit(buffer, event); |
| 245 | } | 245 | } |
| 246 | } | 246 | } |
| 247 | do_gettimeofday(&end_tv); | 247 | end_time = ktime_get(); |
| 248 | 248 | ||
| 249 | cnt++; | 249 | cnt++; |
| 250 | if (consumer && !(cnt % wakeup_interval)) | 250 | if (consumer && !(cnt % wakeup_interval)) |
| @@ -264,7 +264,7 @@ static void ring_buffer_producer(void) | |||
| 264 | cond_resched(); | 264 | cond_resched(); |
| 265 | #endif | 265 | #endif |
| 266 | 266 | ||
| 267 | } while (end_tv.tv_sec < (start_tv.tv_sec + RUN_TIME) && !kill_test); | 267 | } while (ktime_before(end_time, timeout) && !kill_test); |
| 268 | trace_printk("End ring buffer hammer\n"); | 268 | trace_printk("End ring buffer hammer\n"); |
| 269 | 269 | ||
| 270 | if (consumer) { | 270 | if (consumer) { |
| @@ -280,9 +280,7 @@ static void ring_buffer_producer(void) | |||
| 280 | wait_for_completion(&read_done); | 280 | wait_for_completion(&read_done); |
| 281 | } | 281 | } |
| 282 | 282 | ||
| 283 | time = end_tv.tv_sec - start_tv.tv_sec; | 283 | time = ktime_us_delta(end_time, start_time); |
| 284 | time *= USEC_PER_SEC; | ||
| 285 | time += (long long)((long)end_tv.tv_usec - (long)start_tv.tv_usec); | ||
| 286 | 284 | ||
| 287 | entries = ring_buffer_entries(buffer); | 285 | entries = ring_buffer_entries(buffer); |
| 288 | overruns = ring_buffer_overruns(buffer); | 286 | overruns = ring_buffer_overruns(buffer); |
diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c index 4a9079b9f082..62c6506d663f 100644 --- a/kernel/trace/trace.c +++ b/kernel/trace/trace.c | |||
| @@ -2036,7 +2036,8 @@ void trace_printk_init_buffers(void) | |||
| 2036 | 2036 | ||
| 2037 | /* trace_printk() is for debug use only. Don't use it in production. */ | 2037 | /* trace_printk() is for debug use only. Don't use it in production. */ |
| 2038 | 2038 | ||
| 2039 | pr_warning("\n**********************************************************\n"); | 2039 | pr_warning("\n"); |
| 2040 | pr_warning("**********************************************************\n"); | ||
| 2040 | pr_warning("** NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE **\n"); | 2041 | pr_warning("** NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE NOTICE **\n"); |
| 2041 | pr_warning("** **\n"); | 2042 | pr_warning("** **\n"); |
| 2042 | pr_warning("** trace_printk() being used. Allocating extra memory. **\n"); | 2043 | pr_warning("** trace_printk() being used. Allocating extra memory. **\n"); |
| @@ -3352,12 +3353,12 @@ tracing_cpumask_read(struct file *filp, char __user *ubuf, | |||
| 3352 | 3353 | ||
| 3353 | mutex_lock(&tracing_cpumask_update_lock); | 3354 | mutex_lock(&tracing_cpumask_update_lock); |
| 3354 | 3355 | ||
| 3355 | len = cpumask_scnprintf(mask_str, count, tr->tracing_cpumask); | 3356 | len = snprintf(mask_str, count, "%*pb\n", |
| 3356 | if (count - len < 2) { | 3357 | cpumask_pr_args(tr->tracing_cpumask)); |
| 3358 | if (len >= count) { | ||
| 3357 | count = -EINVAL; | 3359 | count = -EINVAL; |
| 3358 | goto out_err; | 3360 | goto out_err; |
| 3359 | } | 3361 | } |
| 3360 | len += sprintf(mask_str + len, "\n"); | ||
| 3361 | count = simple_read_from_buffer(ubuf, count, ppos, mask_str, NR_CPUS+1); | 3362 | count = simple_read_from_buffer(ubuf, count, ppos, mask_str, NR_CPUS+1); |
| 3362 | 3363 | ||
| 3363 | out_err: | 3364 | out_err: |
| @@ -4140,6 +4141,12 @@ static int tracing_set_tracer(struct trace_array *tr, const char *buf) | |||
| 4140 | goto out; | 4141 | goto out; |
| 4141 | } | 4142 | } |
| 4142 | 4143 | ||
| 4144 | /* If trace pipe files are being read, we can't change the tracer */ | ||
| 4145 | if (tr->current_trace->ref) { | ||
| 4146 | ret = -EBUSY; | ||
| 4147 | goto out; | ||
| 4148 | } | ||
| 4149 | |||
| 4143 | trace_branch_disable(); | 4150 | trace_branch_disable(); |
| 4144 | 4151 | ||
| 4145 | tr->current_trace->enabled--; | 4152 | tr->current_trace->enabled--; |
| @@ -4326,17 +4333,7 @@ static int tracing_open_pipe(struct inode *inode, struct file *filp) | |||
| 4326 | } | 4333 | } |
| 4327 | 4334 | ||
| 4328 | trace_seq_init(&iter->seq); | 4335 | trace_seq_init(&iter->seq); |
| 4329 | 4336 | iter->trace = tr->current_trace; | |
| 4330 | /* | ||
| 4331 | * We make a copy of the current tracer to avoid concurrent | ||
| 4332 | * changes on it while we are reading. | ||
| 4333 | */ | ||
| 4334 | iter->trace = kmalloc(sizeof(*iter->trace), GFP_KERNEL); | ||
| 4335 | if (!iter->trace) { | ||
| 4336 | ret = -ENOMEM; | ||
| 4337 | goto fail; | ||
| 4338 | } | ||
| 4339 | *iter->trace = *tr->current_trace; | ||
| 4340 | 4337 | ||
| 4341 | if (!alloc_cpumask_var(&iter->started, GFP_KERNEL)) { | 4338 | if (!alloc_cpumask_var(&iter->started, GFP_KERNEL)) { |
| 4342 | ret = -ENOMEM; | 4339 | ret = -ENOMEM; |
| @@ -4363,6 +4360,8 @@ static int tracing_open_pipe(struct inode *inode, struct file *filp) | |||
| 4363 | iter->trace->pipe_open(iter); | 4360 | iter->trace->pipe_open(iter); |
| 4364 | 4361 | ||
| 4365 | nonseekable_open(inode, filp); | 4362 | nonseekable_open(inode, filp); |
| 4363 | |||
| 4364 | tr->current_trace->ref++; | ||
| 4366 | out: | 4365 | out: |
| 4367 | mutex_unlock(&trace_types_lock); | 4366 | mutex_unlock(&trace_types_lock); |
| 4368 | return ret; | 4367 | return ret; |
| @@ -4382,6 +4381,8 @@ static int tracing_release_pipe(struct inode *inode, struct file *file) | |||
| 4382 | 4381 | ||
| 4383 | mutex_lock(&trace_types_lock); | 4382 | mutex_lock(&trace_types_lock); |
| 4384 | 4383 | ||
| 4384 | tr->current_trace->ref--; | ||
| 4385 | |||
| 4385 | if (iter->trace->pipe_close) | 4386 | if (iter->trace->pipe_close) |
| 4386 | iter->trace->pipe_close(iter); | 4387 | iter->trace->pipe_close(iter); |
| 4387 | 4388 | ||
| @@ -4389,7 +4390,6 @@ static int tracing_release_pipe(struct inode *inode, struct file *file) | |||
| 4389 | 4390 | ||
| 4390 | free_cpumask_var(iter->started); | 4391 | free_cpumask_var(iter->started); |
| 4391 | mutex_destroy(&iter->mutex); | 4392 | mutex_destroy(&iter->mutex); |
| 4392 | kfree(iter->trace); | ||
| 4393 | kfree(iter); | 4393 | kfree(iter); |
| 4394 | 4394 | ||
| 4395 | trace_array_put(tr); | 4395 | trace_array_put(tr); |
| @@ -4422,7 +4422,7 @@ tracing_poll_pipe(struct file *filp, poll_table *poll_table) | |||
| 4422 | return trace_poll(iter, filp, poll_table); | 4422 | return trace_poll(iter, filp, poll_table); |
| 4423 | } | 4423 | } |
| 4424 | 4424 | ||
| 4425 | /* Must be called with trace_types_lock mutex held. */ | 4425 | /* Must be called with iter->mutex held. */ |
| 4426 | static int tracing_wait_pipe(struct file *filp) | 4426 | static int tracing_wait_pipe(struct file *filp) |
| 4427 | { | 4427 | { |
| 4428 | struct trace_iterator *iter = filp->private_data; | 4428 | struct trace_iterator *iter = filp->private_data; |
| @@ -4467,7 +4467,6 @@ tracing_read_pipe(struct file *filp, char __user *ubuf, | |||
| 4467 | size_t cnt, loff_t *ppos) | 4467 | size_t cnt, loff_t *ppos) |
| 4468 | { | 4468 | { |
| 4469 | struct trace_iterator *iter = filp->private_data; | 4469 | struct trace_iterator *iter = filp->private_data; |
| 4470 | struct trace_array *tr = iter->tr; | ||
| 4471 | ssize_t sret; | 4470 | ssize_t sret; |
| 4472 | 4471 | ||
| 4473 | /* return any leftover data */ | 4472 | /* return any leftover data */ |
| @@ -4477,12 +4476,6 @@ tracing_read_pipe(struct file *filp, char __user *ubuf, | |||
| 4477 | 4476 | ||
| 4478 | trace_seq_init(&iter->seq); | 4477 | trace_seq_init(&iter->seq); |
| 4479 | 4478 | ||
| 4480 | /* copy the tracer to avoid using a global lock all around */ | ||
| 4481 | mutex_lock(&trace_types_lock); | ||
| 4482 | if (unlikely(iter->trace->name != tr->current_trace->name)) | ||
| 4483 | *iter->trace = *tr->current_trace; | ||
| 4484 | mutex_unlock(&trace_types_lock); | ||
| 4485 | |||
| 4486 | /* | 4479 | /* |
| 4487 | * Avoid more than one consumer on a single file descriptor | 4480 | * Avoid more than one consumer on a single file descriptor |
| 4488 | * This is just a matter of traces coherency, the ring buffer itself | 4481 | * This is just a matter of traces coherency, the ring buffer itself |
| @@ -4642,7 +4635,6 @@ static ssize_t tracing_splice_read_pipe(struct file *filp, | |||
| 4642 | .ops = &tracing_pipe_buf_ops, | 4635 | .ops = &tracing_pipe_buf_ops, |
| 4643 | .spd_release = tracing_spd_release_pipe, | 4636 | .spd_release = tracing_spd_release_pipe, |
| 4644 | }; | 4637 | }; |
| 4645 | struct trace_array *tr = iter->tr; | ||
| 4646 | ssize_t ret; | 4638 | ssize_t ret; |
| 4647 | size_t rem; | 4639 | size_t rem; |
| 4648 | unsigned int i; | 4640 | unsigned int i; |
| @@ -4650,12 +4642,6 @@ static ssize_t tracing_splice_read_pipe(struct file *filp, | |||
| 4650 | if (splice_grow_spd(pipe, &spd)) | 4642 | if (splice_grow_spd(pipe, &spd)) |
| 4651 | return -ENOMEM; | 4643 | return -ENOMEM; |
| 4652 | 4644 | ||
| 4653 | /* copy the tracer to avoid using a global lock all around */ | ||
| 4654 | mutex_lock(&trace_types_lock); | ||
| 4655 | if (unlikely(iter->trace->name != tr->current_trace->name)) | ||
| 4656 | *iter->trace = *tr->current_trace; | ||
| 4657 | mutex_unlock(&trace_types_lock); | ||
| 4658 | |||
| 4659 | mutex_lock(&iter->mutex); | 4645 | mutex_lock(&iter->mutex); |
| 4660 | 4646 | ||
| 4661 | if (iter->trace->splice_read) { | 4647 | if (iter->trace->splice_read) { |
| @@ -4942,7 +4928,7 @@ tracing_mark_write(struct file *filp, const char __user *ubuf, | |||
| 4942 | *fpos += written; | 4928 | *fpos += written; |
| 4943 | 4929 | ||
| 4944 | out_unlock: | 4930 | out_unlock: |
| 4945 | for (i = 0; i < nr_pages; i++){ | 4931 | for (i = nr_pages - 1; i >= 0; i--) { |
| 4946 | kunmap_atomic(map_page[i]); | 4932 | kunmap_atomic(map_page[i]); |
| 4947 | put_page(pages[i]); | 4933 | put_page(pages[i]); |
| 4948 | } | 4934 | } |
| @@ -5331,6 +5317,8 @@ static int tracing_buffers_open(struct inode *inode, struct file *filp) | |||
| 5331 | 5317 | ||
| 5332 | filp->private_data = info; | 5318 | filp->private_data = info; |
| 5333 | 5319 | ||
| 5320 | tr->current_trace->ref++; | ||
| 5321 | |||
| 5334 | mutex_unlock(&trace_types_lock); | 5322 | mutex_unlock(&trace_types_lock); |
| 5335 | 5323 | ||
| 5336 | ret = nonseekable_open(inode, filp); | 5324 | ret = nonseekable_open(inode, filp); |
| @@ -5361,21 +5349,16 @@ tracing_buffers_read(struct file *filp, char __user *ubuf, | |||
| 5361 | if (!count) | 5349 | if (!count) |
| 5362 | return 0; | 5350 | return 0; |
| 5363 | 5351 | ||
| 5364 | mutex_lock(&trace_types_lock); | ||
| 5365 | |||
| 5366 | #ifdef CONFIG_TRACER_MAX_TRACE | 5352 | #ifdef CONFIG_TRACER_MAX_TRACE |
| 5367 | if (iter->snapshot && iter->tr->current_trace->use_max_tr) { | 5353 | if (iter->snapshot && iter->tr->current_trace->use_max_tr) |
| 5368 | size = -EBUSY; | 5354 | return -EBUSY; |
| 5369 | goto out_unlock; | ||
| 5370 | } | ||
| 5371 | #endif | 5355 | #endif |
| 5372 | 5356 | ||
| 5373 | if (!info->spare) | 5357 | if (!info->spare) |
| 5374 | info->spare = ring_buffer_alloc_read_page(iter->trace_buffer->buffer, | 5358 | info->spare = ring_buffer_alloc_read_page(iter->trace_buffer->buffer, |
| 5375 | iter->cpu_file); | 5359 | iter->cpu_file); |
| 5376 | size = -ENOMEM; | ||
| 5377 | if (!info->spare) | 5360 | if (!info->spare) |
| 5378 | goto out_unlock; | 5361 | return -ENOMEM; |
| 5379 | 5362 | ||
| 5380 | /* Do we have previous read data to read? */ | 5363 | /* Do we have previous read data to read? */ |
| 5381 | if (info->read < PAGE_SIZE) | 5364 | if (info->read < PAGE_SIZE) |
| @@ -5391,21 +5374,16 @@ tracing_buffers_read(struct file *filp, char __user *ubuf, | |||
| 5391 | 5374 | ||
| 5392 | if (ret < 0) { | 5375 | if (ret < 0) { |
| 5393 | if (trace_empty(iter)) { | 5376 | if (trace_empty(iter)) { |
| 5394 | if ((filp->f_flags & O_NONBLOCK)) { | 5377 | if ((filp->f_flags & O_NONBLOCK)) |
| 5395 | size = -EAGAIN; | 5378 | return -EAGAIN; |
| 5396 | goto out_unlock; | 5379 | |
| 5397 | } | ||
| 5398 | mutex_unlock(&trace_types_lock); | ||
| 5399 | ret = wait_on_pipe(iter, false); | 5380 | ret = wait_on_pipe(iter, false); |
| 5400 | mutex_lock(&trace_types_lock); | 5381 | if (ret) |
| 5401 | if (ret) { | 5382 | return ret; |
| 5402 | size = ret; | 5383 | |
| 5403 | goto out_unlock; | ||
| 5404 | } | ||
| 5405 | goto again; | 5384 | goto again; |
| 5406 | } | 5385 | } |
| 5407 | size = 0; | 5386 | return 0; |
| 5408 | goto out_unlock; | ||
| 5409 | } | 5387 | } |
| 5410 | 5388 | ||
| 5411 | info->read = 0; | 5389 | info->read = 0; |
| @@ -5415,18 +5393,14 @@ tracing_buffers_read(struct file *filp, char __user *ubuf, | |||
| 5415 | size = count; | 5393 | size = count; |
| 5416 | 5394 | ||
| 5417 | ret = copy_to_user(ubuf, info->spare + info->read, size); | 5395 | ret = copy_to_user(ubuf, info->spare + info->read, size); |
| 5418 | if (ret == size) { | 5396 | if (ret == size) |
| 5419 | size = -EFAULT; | 5397 | return -EFAULT; |
| 5420 | goto out_unlock; | 5398 | |
| 5421 | } | ||
| 5422 | size -= ret; | 5399 | size -= ret; |
| 5423 | 5400 | ||
| 5424 | *ppos += size; | 5401 | *ppos += size; |
| 5425 | info->read += size; | 5402 | info->read += size; |
| 5426 | 5403 | ||
| 5427 | out_unlock: | ||
| 5428 | mutex_unlock(&trace_types_lock); | ||
| 5429 | |||
| 5430 | return size; | 5404 | return size; |
| 5431 | } | 5405 | } |
| 5432 | 5406 | ||
| @@ -5437,6 +5411,8 @@ static int tracing_buffers_release(struct inode *inode, struct file *file) | |||
| 5437 | 5411 | ||
| 5438 | mutex_lock(&trace_types_lock); | 5412 | mutex_lock(&trace_types_lock); |
| 5439 | 5413 | ||
| 5414 | iter->tr->current_trace->ref--; | ||
| 5415 | |||
| 5440 | __trace_array_put(iter->tr); | 5416 | __trace_array_put(iter->tr); |
| 5441 | 5417 | ||
| 5442 | if (info->spare) | 5418 | if (info->spare) |
| @@ -5522,30 +5498,20 @@ tracing_buffers_splice_read(struct file *file, loff_t *ppos, | |||
| 5522 | int entries, size, i; | 5498 | int entries, size, i; |
| 5523 | ssize_t ret = 0; | 5499 | ssize_t ret = 0; |
| 5524 | 5500 | ||
| 5525 | mutex_lock(&trace_types_lock); | ||
| 5526 | |||
| 5527 | #ifdef CONFIG_TRACER_MAX_TRACE | 5501 | #ifdef CONFIG_TRACER_MAX_TRACE |
| 5528 | if (iter->snapshot && iter->tr->current_trace->use_max_tr) { | 5502 | if (iter->snapshot && iter->tr->current_trace->use_max_tr) |
| 5529 | ret = -EBUSY; | 5503 | return -EBUSY; |
| 5530 | goto out; | ||
| 5531 | } | ||
| 5532 | #endif | 5504 | #endif |
| 5533 | 5505 | ||
| 5534 | if (splice_grow_spd(pipe, &spd)) { | 5506 | if (splice_grow_spd(pipe, &spd)) |
| 5535 | ret = -ENOMEM; | 5507 | return -ENOMEM; |
| 5536 | goto out; | ||
| 5537 | } | ||
| 5538 | 5508 | ||
| 5539 | if (*ppos & (PAGE_SIZE - 1)) { | 5509 | if (*ppos & (PAGE_SIZE - 1)) |
| 5540 | ret = -EINVAL; | 5510 | return -EINVAL; |
| 5541 | goto out; | ||
| 5542 | } | ||
| 5543 | 5511 | ||
| 5544 | if (len & (PAGE_SIZE - 1)) { | 5512 | if (len & (PAGE_SIZE - 1)) { |
| 5545 | if (len < PAGE_SIZE) { | 5513 | if (len < PAGE_SIZE) |
| 5546 | ret = -EINVAL; | 5514 | return -EINVAL; |
| 5547 | goto out; | ||
| 5548 | } | ||
| 5549 | len &= PAGE_MASK; | 5515 | len &= PAGE_MASK; |
| 5550 | } | 5516 | } |
| 5551 | 5517 | ||
| @@ -5606,25 +5572,20 @@ tracing_buffers_splice_read(struct file *file, loff_t *ppos, | |||
| 5606 | /* did we read anything? */ | 5572 | /* did we read anything? */ |
| 5607 | if (!spd.nr_pages) { | 5573 | if (!spd.nr_pages) { |
| 5608 | if (ret) | 5574 | if (ret) |
| 5609 | goto out; | 5575 | return ret; |
| 5576 | |||
| 5577 | if ((file->f_flags & O_NONBLOCK) || (flags & SPLICE_F_NONBLOCK)) | ||
| 5578 | return -EAGAIN; | ||
| 5610 | 5579 | ||
| 5611 | if ((file->f_flags & O_NONBLOCK) || (flags & SPLICE_F_NONBLOCK)) { | ||
| 5612 | ret = -EAGAIN; | ||
| 5613 | goto out; | ||
| 5614 | } | ||
| 5615 | mutex_unlock(&trace_types_lock); | ||
| 5616 | ret = wait_on_pipe(iter, true); | 5580 | ret = wait_on_pipe(iter, true); |
| 5617 | mutex_lock(&trace_types_lock); | ||
| 5618 | if (ret) | 5581 | if (ret) |
| 5619 | goto out; | 5582 | return ret; |
| 5620 | 5583 | ||
| 5621 | goto again; | 5584 | goto again; |
| 5622 | } | 5585 | } |
| 5623 | 5586 | ||
| 5624 | ret = splice_to_pipe(pipe, &spd); | 5587 | ret = splice_to_pipe(pipe, &spd); |
| 5625 | splice_shrink_spd(&spd); | 5588 | splice_shrink_spd(&spd); |
| 5626 | out: | ||
| 5627 | mutex_unlock(&trace_types_lock); | ||
| 5628 | 5589 | ||
| 5629 | return ret; | 5590 | return ret; |
| 5630 | } | 5591 | } |
| @@ -5854,28 +5815,11 @@ static __init int register_snapshot_cmd(void) | |||
| 5854 | static inline __init int register_snapshot_cmd(void) { return 0; } | 5815 | static inline __init int register_snapshot_cmd(void) { return 0; } |
| 5855 | #endif /* defined(CONFIG_TRACER_SNAPSHOT) && defined(CONFIG_DYNAMIC_FTRACE) */ | 5816 | #endif /* defined(CONFIG_TRACER_SNAPSHOT) && defined(CONFIG_DYNAMIC_FTRACE) */ |
| 5856 | 5817 | ||
| 5857 | struct dentry *tracing_init_dentry_tr(struct trace_array *tr) | 5818 | static struct dentry *tracing_get_dentry(struct trace_array *tr) |
| 5858 | { | 5819 | { |
| 5859 | if (tr->dir) | ||
| 5860 | return tr->dir; | ||
| 5861 | |||
| 5862 | if (!debugfs_initialized()) | ||
| 5863 | return NULL; | ||
| 5864 | |||
| 5865 | if (tr->flags & TRACE_ARRAY_FL_GLOBAL) | ||
| 5866 | tr->dir = debugfs_create_dir("tracing", NULL); | ||
| 5867 | |||
| 5868 | if (!tr->dir) | ||
| 5869 | pr_warn_once("Could not create debugfs directory 'tracing'\n"); | ||
| 5870 | |||
| 5871 | return tr->dir; | 5820 | return tr->dir; |
| 5872 | } | 5821 | } |
| 5873 | 5822 | ||
| 5874 | struct dentry *tracing_init_dentry(void) | ||
| 5875 | { | ||
| 5876 | return tracing_init_dentry_tr(&global_trace); | ||
| 5877 | } | ||
| 5878 | |||
| 5879 | static struct dentry *tracing_dentry_percpu(struct trace_array *tr, int cpu) | 5823 | static struct dentry *tracing_dentry_percpu(struct trace_array *tr, int cpu) |
| 5880 | { | 5824 | { |
| 5881 | struct dentry *d_tracer; | 5825 | struct dentry *d_tracer; |
| @@ -5883,8 +5827,8 @@ static struct dentry *tracing_dentry_percpu(struct trace_array *tr, int cpu) | |||
| 5883 | if (tr->percpu_dir) | 5827 | if (tr->percpu_dir) |
| 5884 | return tr->percpu_dir; | 5828 | return tr->percpu_dir; |
| 5885 | 5829 | ||
| 5886 | d_tracer = tracing_init_dentry_tr(tr); | 5830 | d_tracer = tracing_get_dentry(tr); |
| 5887 | if (!d_tracer) | 5831 | if (IS_ERR(d_tracer)) |
| 5888 | return NULL; | 5832 | return NULL; |
| 5889 | 5833 | ||
| 5890 | tr->percpu_dir = debugfs_create_dir("per_cpu", d_tracer); | 5834 | tr->percpu_dir = debugfs_create_dir("per_cpu", d_tracer); |
| @@ -6086,8 +6030,8 @@ static struct dentry *trace_options_init_dentry(struct trace_array *tr) | |||
| 6086 | if (tr->options) | 6030 | if (tr->options) |
| 6087 | return tr->options; | 6031 | return tr->options; |
| 6088 | 6032 | ||
| 6089 | d_tracer = tracing_init_dentry_tr(tr); | 6033 | d_tracer = tracing_get_dentry(tr); |
| 6090 | if (!d_tracer) | 6034 | if (IS_ERR(d_tracer)) |
| 6091 | return NULL; | 6035 | return NULL; |
| 6092 | 6036 | ||
| 6093 | tr->options = debugfs_create_dir("options", d_tracer); | 6037 | tr->options = debugfs_create_dir("options", d_tracer); |
| @@ -6416,7 +6360,7 @@ static int instance_delete(const char *name) | |||
| 6416 | goto out_unlock; | 6360 | goto out_unlock; |
| 6417 | 6361 | ||
| 6418 | ret = -EBUSY; | 6362 | ret = -EBUSY; |
| 6419 | if (tr->ref) | 6363 | if (tr->ref || (tr->current_trace && tr->current_trace->ref)) |
| 6420 | goto out_unlock; | 6364 | goto out_unlock; |
| 6421 | 6365 | ||
| 6422 | list_del(&tr->list); | 6366 | list_del(&tr->list); |
| @@ -6571,6 +6515,33 @@ init_tracer_debugfs(struct trace_array *tr, struct dentry *d_tracer) | |||
| 6571 | 6515 | ||
| 6572 | } | 6516 | } |
| 6573 | 6517 | ||
| 6518 | /** | ||
| 6519 | * tracing_init_dentry - initialize top level trace array | ||
| 6520 | * | ||
| 6521 | * This is called when creating files or directories in the tracing | ||
| 6522 | * directory. It is called via fs_initcall() by any of the boot up code | ||
| 6523 | * and expects to return the dentry of the top level tracing directory. | ||
| 6524 | */ | ||
| 6525 | struct dentry *tracing_init_dentry(void) | ||
| 6526 | { | ||
| 6527 | struct trace_array *tr = &global_trace; | ||
| 6528 | |||
| 6529 | if (tr->dir) | ||
| 6530 | return tr->dir; | ||
| 6531 | |||
| 6532 | if (WARN_ON(!debugfs_initialized())) | ||
| 6533 | return ERR_PTR(-ENODEV); | ||
| 6534 | |||
| 6535 | tr->dir = debugfs_create_dir("tracing", NULL); | ||
| 6536 | |||
| 6537 | if (!tr->dir) { | ||
| 6538 | pr_warn_once("Could not create debugfs directory 'tracing'\n"); | ||
| 6539 | return ERR_PTR(-ENOMEM); | ||
| 6540 | } | ||
| 6541 | |||
| 6542 | return tr->dir; | ||
| 6543 | } | ||
| 6544 | |||
| 6574 | static __init int tracer_init_debugfs(void) | 6545 | static __init int tracer_init_debugfs(void) |
| 6575 | { | 6546 | { |
| 6576 | struct dentry *d_tracer; | 6547 | struct dentry *d_tracer; |
| @@ -6578,7 +6549,7 @@ static __init int tracer_init_debugfs(void) | |||
| 6578 | trace_access_lock_init(); | 6549 | trace_access_lock_init(); |
| 6579 | 6550 | ||
| 6580 | d_tracer = tracing_init_dentry(); | 6551 | d_tracer = tracing_init_dentry(); |
| 6581 | if (!d_tracer) | 6552 | if (IS_ERR(d_tracer)) |
| 6582 | return 0; | 6553 | return 0; |
| 6583 | 6554 | ||
| 6584 | init_tracer_debugfs(&global_trace, d_tracer); | 6555 | init_tracer_debugfs(&global_trace, d_tracer); |
| @@ -6811,7 +6782,6 @@ __init static int tracer_alloc_buffers(void) | |||
| 6811 | int ring_buf_size; | 6782 | int ring_buf_size; |
| 6812 | int ret = -ENOMEM; | 6783 | int ret = -ENOMEM; |
| 6813 | 6784 | ||
| 6814 | |||
| 6815 | if (!alloc_cpumask_var(&tracing_buffer_mask, GFP_KERNEL)) | 6785 | if (!alloc_cpumask_var(&tracing_buffer_mask, GFP_KERNEL)) |
| 6816 | goto out; | 6786 | goto out; |
| 6817 | 6787 | ||
diff --git a/kernel/trace/trace.h b/kernel/trace/trace.h index 8de48bac1ce2..dd8205a35760 100644 --- a/kernel/trace/trace.h +++ b/kernel/trace/trace.h | |||
| @@ -388,6 +388,7 @@ struct tracer { | |||
| 388 | struct tracer *next; | 388 | struct tracer *next; |
| 389 | struct tracer_flags *flags; | 389 | struct tracer_flags *flags; |
| 390 | int enabled; | 390 | int enabled; |
| 391 | int ref; | ||
| 391 | bool print_max; | 392 | bool print_max; |
| 392 | bool allow_instances; | 393 | bool allow_instances; |
| 393 | #ifdef CONFIG_TRACER_MAX_TRACE | 394 | #ifdef CONFIG_TRACER_MAX_TRACE |
| @@ -541,7 +542,6 @@ struct dentry *trace_create_file(const char *name, | |||
| 541 | void *data, | 542 | void *data, |
| 542 | const struct file_operations *fops); | 543 | const struct file_operations *fops); |
| 543 | 544 | ||
| 544 | struct dentry *tracing_init_dentry_tr(struct trace_array *tr); | ||
| 545 | struct dentry *tracing_init_dentry(void); | 545 | struct dentry *tracing_init_dentry(void); |
| 546 | 546 | ||
| 547 | struct ring_buffer_event; | 547 | struct ring_buffer_event; |
diff --git a/kernel/trace/trace_branch.c b/kernel/trace/trace_branch.c index 7d6e2afde669..57cbf1efdd44 100644 --- a/kernel/trace/trace_branch.c +++ b/kernel/trace/trace_branch.c | |||
| @@ -7,7 +7,6 @@ | |||
| 7 | #include <linux/seq_file.h> | 7 | #include <linux/seq_file.h> |
| 8 | #include <linux/spinlock.h> | 8 | #include <linux/spinlock.h> |
| 9 | #include <linux/irqflags.h> | 9 | #include <linux/irqflags.h> |
| 10 | #include <linux/debugfs.h> | ||
| 11 | #include <linux/uaccess.h> | 10 | #include <linux/uaccess.h> |
| 12 | #include <linux/module.h> | 11 | #include <linux/module.h> |
| 13 | #include <linux/ftrace.h> | 12 | #include <linux/ftrace.h> |
diff --git a/kernel/trace/trace_event_perf.c b/kernel/trace/trace_event_perf.c index 4b9c114ee9de..6fa484de2ba1 100644 --- a/kernel/trace/trace_event_perf.c +++ b/kernel/trace/trace_event_perf.c | |||
| @@ -261,7 +261,7 @@ void perf_trace_del(struct perf_event *p_event, int flags) | |||
| 261 | } | 261 | } |
| 262 | 262 | ||
| 263 | void *perf_trace_buf_prepare(int size, unsigned short type, | 263 | void *perf_trace_buf_prepare(int size, unsigned short type, |
| 264 | struct pt_regs *regs, int *rctxp) | 264 | struct pt_regs **regs, int *rctxp) |
| 265 | { | 265 | { |
| 266 | struct trace_entry *entry; | 266 | struct trace_entry *entry; |
| 267 | unsigned long flags; | 267 | unsigned long flags; |
| @@ -280,6 +280,8 @@ void *perf_trace_buf_prepare(int size, unsigned short type, | |||
| 280 | if (*rctxp < 0) | 280 | if (*rctxp < 0) |
| 281 | return NULL; | 281 | return NULL; |
| 282 | 282 | ||
| 283 | if (regs) | ||
| 284 | *regs = this_cpu_ptr(&__perf_regs[*rctxp]); | ||
| 283 | raw_data = this_cpu_ptr(perf_trace_buf[*rctxp]); | 285 | raw_data = this_cpu_ptr(perf_trace_buf[*rctxp]); |
| 284 | 286 | ||
| 285 | /* zero the dead bytes from align to not leak stack to user */ | 287 | /* zero the dead bytes from align to not leak stack to user */ |
diff --git a/kernel/trace/trace_events.c b/kernel/trace/trace_events.c index b03a0ea77b99..db54dda10ccc 100644 --- a/kernel/trace/trace_events.c +++ b/kernel/trace/trace_events.c | |||
| @@ -2531,7 +2531,7 @@ static __init int event_trace_init(void) | |||
| 2531 | return -ENODEV; | 2531 | return -ENODEV; |
| 2532 | 2532 | ||
| 2533 | d_tracer = tracing_init_dentry(); | 2533 | d_tracer = tracing_init_dentry(); |
| 2534 | if (!d_tracer) | 2534 | if (IS_ERR(d_tracer)) |
| 2535 | return 0; | 2535 | return 0; |
| 2536 | 2536 | ||
| 2537 | entry = debugfs_create_file("available_events", 0444, d_tracer, | 2537 | entry = debugfs_create_file("available_events", 0444, d_tracer, |
diff --git a/kernel/trace/trace_export.c b/kernel/trace/trace_export.c index d4ddde28a81a..12e2b99be862 100644 --- a/kernel/trace/trace_export.c +++ b/kernel/trace/trace_export.c | |||
| @@ -6,12 +6,10 @@ | |||
| 6 | #include <linux/stringify.h> | 6 | #include <linux/stringify.h> |
| 7 | #include <linux/kallsyms.h> | 7 | #include <linux/kallsyms.h> |
| 8 | #include <linux/seq_file.h> | 8 | #include <linux/seq_file.h> |
| 9 | #include <linux/debugfs.h> | ||
| 10 | #include <linux/uaccess.h> | 9 | #include <linux/uaccess.h> |
| 11 | #include <linux/ftrace.h> | 10 | #include <linux/ftrace.h> |
| 12 | #include <linux/module.h> | 11 | #include <linux/module.h> |
| 13 | #include <linux/init.h> | 12 | #include <linux/init.h> |
| 14 | #include <linux/fs.h> | ||
| 15 | 13 | ||
| 16 | #include "trace_output.h" | 14 | #include "trace_output.h" |
| 17 | 15 | ||
diff --git a/kernel/trace/trace_functions_graph.c b/kernel/trace/trace_functions_graph.c index ba476009e5de..2d25ad1526bb 100644 --- a/kernel/trace/trace_functions_graph.c +++ b/kernel/trace/trace_functions_graph.c | |||
| @@ -1437,7 +1437,7 @@ static __init int init_graph_debugfs(void) | |||
| 1437 | struct dentry *d_tracer; | 1437 | struct dentry *d_tracer; |
| 1438 | 1438 | ||
| 1439 | d_tracer = tracing_init_dentry(); | 1439 | d_tracer = tracing_init_dentry(); |
| 1440 | if (!d_tracer) | 1440 | if (IS_ERR(d_tracer)) |
| 1441 | return 0; | 1441 | return 0; |
| 1442 | 1442 | ||
| 1443 | trace_create_file("max_graph_depth", 0644, d_tracer, | 1443 | trace_create_file("max_graph_depth", 0644, d_tracer, |
diff --git a/kernel/trace/trace_irqsoff.c b/kernel/trace/trace_irqsoff.c index 9bb104f748d0..8523ea345f2b 100644 --- a/kernel/trace/trace_irqsoff.c +++ b/kernel/trace/trace_irqsoff.c | |||
| @@ -10,11 +10,9 @@ | |||
| 10 | * Copyright (C) 2004 Nadia Yvette Chambers | 10 | * Copyright (C) 2004 Nadia Yvette Chambers |
| 11 | */ | 11 | */ |
| 12 | #include <linux/kallsyms.h> | 12 | #include <linux/kallsyms.h> |
| 13 | #include <linux/debugfs.h> | ||
| 14 | #include <linux/uaccess.h> | 13 | #include <linux/uaccess.h> |
| 15 | #include <linux/module.h> | 14 | #include <linux/module.h> |
| 16 | #include <linux/ftrace.h> | 15 | #include <linux/ftrace.h> |
| 17 | #include <linux/fs.h> | ||
| 18 | 16 | ||
| 19 | #include "trace.h" | 17 | #include "trace.h" |
| 20 | 18 | ||
diff --git a/kernel/trace/trace_kprobe.c b/kernel/trace/trace_kprobe.c index 5edb518be345..d73f565b4e06 100644 --- a/kernel/trace/trace_kprobe.c +++ b/kernel/trace/trace_kprobe.c | |||
| @@ -1148,7 +1148,7 @@ kprobe_perf_func(struct trace_kprobe *tk, struct pt_regs *regs) | |||
| 1148 | size = ALIGN(__size + sizeof(u32), sizeof(u64)); | 1148 | size = ALIGN(__size + sizeof(u32), sizeof(u64)); |
| 1149 | size -= sizeof(u32); | 1149 | size -= sizeof(u32); |
| 1150 | 1150 | ||
| 1151 | entry = perf_trace_buf_prepare(size, call->event.type, regs, &rctx); | 1151 | entry = perf_trace_buf_prepare(size, call->event.type, NULL, &rctx); |
| 1152 | if (!entry) | 1152 | if (!entry) |
| 1153 | return; | 1153 | return; |
| 1154 | 1154 | ||
| @@ -1179,7 +1179,7 @@ kretprobe_perf_func(struct trace_kprobe *tk, struct kretprobe_instance *ri, | |||
| 1179 | size = ALIGN(__size + sizeof(u32), sizeof(u64)); | 1179 | size = ALIGN(__size + sizeof(u32), sizeof(u64)); |
| 1180 | size -= sizeof(u32); | 1180 | size -= sizeof(u32); |
| 1181 | 1181 | ||
| 1182 | entry = perf_trace_buf_prepare(size, call->event.type, regs, &rctx); | 1182 | entry = perf_trace_buf_prepare(size, call->event.type, NULL, &rctx); |
| 1183 | if (!entry) | 1183 | if (!entry) |
| 1184 | return; | 1184 | return; |
| 1185 | 1185 | ||
| @@ -1320,7 +1320,7 @@ static __init int init_kprobe_trace(void) | |||
| 1320 | return -EINVAL; | 1320 | return -EINVAL; |
| 1321 | 1321 | ||
| 1322 | d_tracer = tracing_init_dentry(); | 1322 | d_tracer = tracing_init_dentry(); |
| 1323 | if (!d_tracer) | 1323 | if (IS_ERR(d_tracer)) |
| 1324 | return 0; | 1324 | return 0; |
| 1325 | 1325 | ||
| 1326 | entry = debugfs_create_file("kprobe_events", 0644, d_tracer, | 1326 | entry = debugfs_create_file("kprobe_events", 0644, d_tracer, |
diff --git a/kernel/trace/trace_nop.c b/kernel/trace/trace_nop.c index fcf0a9e48916..8bb2071474dd 100644 --- a/kernel/trace/trace_nop.c +++ b/kernel/trace/trace_nop.c | |||
| @@ -6,8 +6,6 @@ | |||
| 6 | */ | 6 | */ |
| 7 | 7 | ||
| 8 | #include <linux/module.h> | 8 | #include <linux/module.h> |
| 9 | #include <linux/fs.h> | ||
| 10 | #include <linux/debugfs.h> | ||
| 11 | #include <linux/ftrace.h> | 9 | #include <linux/ftrace.h> |
| 12 | 10 | ||
| 13 | #include "trace.h" | 11 | #include "trace.h" |
diff --git a/kernel/trace/trace_output.c b/kernel/trace/trace_output.c index b77b9a697619..692bf7184c8c 100644 --- a/kernel/trace/trace_output.c +++ b/kernel/trace/trace_output.c | |||
| @@ -177,6 +177,50 @@ ftrace_print_hex_seq(struct trace_seq *p, const unsigned char *buf, int buf_len) | |||
| 177 | } | 177 | } |
| 178 | EXPORT_SYMBOL(ftrace_print_hex_seq); | 178 | EXPORT_SYMBOL(ftrace_print_hex_seq); |
| 179 | 179 | ||
| 180 | const char * | ||
| 181 | ftrace_print_array_seq(struct trace_seq *p, const void *buf, int buf_len, | ||
| 182 | size_t el_size) | ||
| 183 | { | ||
| 184 | const char *ret = trace_seq_buffer_ptr(p); | ||
| 185 | const char *prefix = ""; | ||
| 186 | void *ptr = (void *)buf; | ||
| 187 | |||
| 188 | trace_seq_putc(p, '{'); | ||
| 189 | |||
| 190 | while (ptr < buf + buf_len) { | ||
| 191 | switch (el_size) { | ||
| 192 | case 1: | ||
| 193 | trace_seq_printf(p, "%s0x%x", prefix, | ||
| 194 | *(u8 *)ptr); | ||
| 195 | break; | ||
| 196 | case 2: | ||
| 197 | trace_seq_printf(p, "%s0x%x", prefix, | ||
| 198 | *(u16 *)ptr); | ||
| 199 | break; | ||
| 200 | case 4: | ||
| 201 | trace_seq_printf(p, "%s0x%x", prefix, | ||
| 202 | *(u32 *)ptr); | ||
| 203 | break; | ||
| 204 | case 8: | ||
| 205 | trace_seq_printf(p, "%s0x%llx", prefix, | ||
| 206 | *(u64 *)ptr); | ||
| 207 | break; | ||
| 208 | default: | ||
| 209 | trace_seq_printf(p, "BAD SIZE:%zu 0x%x", el_size, | ||
| 210 | *(u8 *)ptr); | ||
| 211 | el_size = 1; | ||
| 212 | } | ||
| 213 | prefix = ","; | ||
| 214 | ptr += el_size; | ||
| 215 | } | ||
| 216 | |||
| 217 | trace_seq_putc(p, '}'); | ||
| 218 | trace_seq_putc(p, 0); | ||
| 219 | |||
| 220 | return ret; | ||
| 221 | } | ||
| 222 | EXPORT_SYMBOL(ftrace_print_array_seq); | ||
| 223 | |||
| 180 | int ftrace_raw_output_prep(struct trace_iterator *iter, | 224 | int ftrace_raw_output_prep(struct trace_iterator *iter, |
| 181 | struct trace_event *trace_event) | 225 | struct trace_event *trace_event) |
| 182 | { | 226 | { |
diff --git a/kernel/trace/trace_printk.c b/kernel/trace/trace_printk.c index c4e70b6bd7fa..36c1455b7567 100644 --- a/kernel/trace/trace_printk.c +++ b/kernel/trace/trace_printk.c | |||
| @@ -5,7 +5,6 @@ | |||
| 5 | * | 5 | * |
| 6 | */ | 6 | */ |
| 7 | #include <linux/seq_file.h> | 7 | #include <linux/seq_file.h> |
| 8 | #include <linux/debugfs.h> | ||
| 9 | #include <linux/uaccess.h> | 8 | #include <linux/uaccess.h> |
| 10 | #include <linux/kernel.h> | 9 | #include <linux/kernel.h> |
| 11 | #include <linux/ftrace.h> | 10 | #include <linux/ftrace.h> |
| @@ -15,7 +14,6 @@ | |||
| 15 | #include <linux/ctype.h> | 14 | #include <linux/ctype.h> |
| 16 | #include <linux/list.h> | 15 | #include <linux/list.h> |
| 17 | #include <linux/slab.h> | 16 | #include <linux/slab.h> |
| 18 | #include <linux/fs.h> | ||
| 19 | 17 | ||
| 20 | #include "trace.h" | 18 | #include "trace.h" |
| 21 | 19 | ||
| @@ -349,7 +347,7 @@ static __init int init_trace_printk_function_export(void) | |||
| 349 | struct dentry *d_tracer; | 347 | struct dentry *d_tracer; |
| 350 | 348 | ||
| 351 | d_tracer = tracing_init_dentry(); | 349 | d_tracer = tracing_init_dentry(); |
| 352 | if (!d_tracer) | 350 | if (IS_ERR(d_tracer)) |
| 353 | return 0; | 351 | return 0; |
| 354 | 352 | ||
| 355 | trace_create_file("printk_formats", 0444, d_tracer, | 353 | trace_create_file("printk_formats", 0444, d_tracer, |
diff --git a/kernel/trace/trace_sched_switch.c b/kernel/trace/trace_sched_switch.c index 2e293beb186e..419ca37e72c9 100644 --- a/kernel/trace/trace_sched_switch.c +++ b/kernel/trace/trace_sched_switch.c | |||
| @@ -5,8 +5,6 @@ | |||
| 5 | * | 5 | * |
| 6 | */ | 6 | */ |
| 7 | #include <linux/module.h> | 7 | #include <linux/module.h> |
| 8 | #include <linux/fs.h> | ||
| 9 | #include <linux/debugfs.h> | ||
| 10 | #include <linux/kallsyms.h> | 8 | #include <linux/kallsyms.h> |
| 11 | #include <linux/uaccess.h> | 9 | #include <linux/uaccess.h> |
| 12 | #include <linux/ftrace.h> | 10 | #include <linux/ftrace.h> |
diff --git a/kernel/trace/trace_sched_wakeup.c b/kernel/trace/trace_sched_wakeup.c index 8fb84b362816..d6e1003724e9 100644 --- a/kernel/trace/trace_sched_wakeup.c +++ b/kernel/trace/trace_sched_wakeup.c | |||
| @@ -10,8 +10,6 @@ | |||
| 10 | * Copyright (C) 2004 Nadia Yvette Chambers | 10 | * Copyright (C) 2004 Nadia Yvette Chambers |
| 11 | */ | 11 | */ |
| 12 | #include <linux/module.h> | 12 | #include <linux/module.h> |
| 13 | #include <linux/fs.h> | ||
| 14 | #include <linux/debugfs.h> | ||
| 15 | #include <linux/kallsyms.h> | 13 | #include <linux/kallsyms.h> |
| 16 | #include <linux/uaccess.h> | 14 | #include <linux/uaccess.h> |
| 17 | #include <linux/ftrace.h> | 15 | #include <linux/ftrace.h> |
diff --git a/kernel/trace/trace_seq.c b/kernel/trace/trace_seq.c index f8b45d8792f9..e694c9f9efa4 100644 --- a/kernel/trace/trace_seq.c +++ b/kernel/trace/trace_seq.c | |||
| @@ -120,7 +120,7 @@ void trace_seq_bitmask(struct trace_seq *s, const unsigned long *maskp, | |||
| 120 | 120 | ||
| 121 | __trace_seq_init(s); | 121 | __trace_seq_init(s); |
| 122 | 122 | ||
| 123 | seq_buf_bitmask(&s->seq, maskp, nmaskbits); | 123 | seq_buf_printf(&s->seq, "%*pb", nmaskbits, maskp); |
| 124 | 124 | ||
| 125 | if (unlikely(seq_buf_has_overflowed(&s->seq))) { | 125 | if (unlikely(seq_buf_has_overflowed(&s->seq))) { |
| 126 | s->seq.len = save_len; | 126 | s->seq.len = save_len; |
diff --git a/kernel/trace/trace_stack.c b/kernel/trace/trace_stack.c index 16eddb308c33..c3e4fcfddd45 100644 --- a/kernel/trace/trace_stack.c +++ b/kernel/trace/trace_stack.c | |||
| @@ -7,12 +7,10 @@ | |||
| 7 | #include <linux/seq_file.h> | 7 | #include <linux/seq_file.h> |
| 8 | #include <linux/spinlock.h> | 8 | #include <linux/spinlock.h> |
| 9 | #include <linux/uaccess.h> | 9 | #include <linux/uaccess.h> |
| 10 | #include <linux/debugfs.h> | ||
| 11 | #include <linux/ftrace.h> | 10 | #include <linux/ftrace.h> |
| 12 | #include <linux/module.h> | 11 | #include <linux/module.h> |
| 13 | #include <linux/sysctl.h> | 12 | #include <linux/sysctl.h> |
| 14 | #include <linux/init.h> | 13 | #include <linux/init.h> |
| 15 | #include <linux/fs.h> | ||
| 16 | 14 | ||
| 17 | #include <asm/setup.h> | 15 | #include <asm/setup.h> |
| 18 | 16 | ||
| @@ -462,7 +460,7 @@ static __init int stack_trace_init(void) | |||
| 462 | struct dentry *d_tracer; | 460 | struct dentry *d_tracer; |
| 463 | 461 | ||
| 464 | d_tracer = tracing_init_dentry(); | 462 | d_tracer = tracing_init_dentry(); |
| 465 | if (!d_tracer) | 463 | if (IS_ERR(d_tracer)) |
| 466 | return 0; | 464 | return 0; |
| 467 | 465 | ||
| 468 | trace_create_file("stack_max_size", 0644, d_tracer, | 466 | trace_create_file("stack_max_size", 0644, d_tracer, |
diff --git a/kernel/trace/trace_stat.c b/kernel/trace/trace_stat.c index 7af67360b330..75e19e86c954 100644 --- a/kernel/trace/trace_stat.c +++ b/kernel/trace/trace_stat.c | |||
| @@ -276,7 +276,7 @@ static int tracing_stat_init(void) | |||
| 276 | struct dentry *d_tracing; | 276 | struct dentry *d_tracing; |
| 277 | 277 | ||
| 278 | d_tracing = tracing_init_dentry(); | 278 | d_tracing = tracing_init_dentry(); |
| 279 | if (!d_tracing) | 279 | if (IS_ERR(d_tracing)) |
| 280 | return 0; | 280 | return 0; |
| 281 | 281 | ||
| 282 | stat_dir = debugfs_create_dir("trace_stat", d_tracing); | 282 | stat_dir = debugfs_create_dir("trace_stat", d_tracing); |
diff --git a/kernel/trace/trace_syscalls.c b/kernel/trace/trace_syscalls.c index c6ee36fcbf90..f97f6e3a676c 100644 --- a/kernel/trace/trace_syscalls.c +++ b/kernel/trace/trace_syscalls.c | |||
| @@ -574,7 +574,7 @@ static void perf_syscall_enter(void *ignore, struct pt_regs *regs, long id) | |||
| 574 | size -= sizeof(u32); | 574 | size -= sizeof(u32); |
| 575 | 575 | ||
| 576 | rec = (struct syscall_trace_enter *)perf_trace_buf_prepare(size, | 576 | rec = (struct syscall_trace_enter *)perf_trace_buf_prepare(size, |
| 577 | sys_data->enter_event->event.type, regs, &rctx); | 577 | sys_data->enter_event->event.type, NULL, &rctx); |
| 578 | if (!rec) | 578 | if (!rec) |
| 579 | return; | 579 | return; |
| 580 | 580 | ||
| @@ -647,7 +647,7 @@ static void perf_syscall_exit(void *ignore, struct pt_regs *regs, long ret) | |||
| 647 | size -= sizeof(u32); | 647 | size -= sizeof(u32); |
| 648 | 648 | ||
| 649 | rec = (struct syscall_trace_exit *)perf_trace_buf_prepare(size, | 649 | rec = (struct syscall_trace_exit *)perf_trace_buf_prepare(size, |
| 650 | sys_data->exit_event->event.type, regs, &rctx); | 650 | sys_data->exit_event->event.type, NULL, &rctx); |
| 651 | if (!rec) | 651 | if (!rec) |
| 652 | return; | 652 | return; |
| 653 | 653 | ||
diff --git a/kernel/trace/trace_uprobe.c b/kernel/trace/trace_uprobe.c index 8520acc34b18..7dc1c8abecd6 100644 --- a/kernel/trace/trace_uprobe.c +++ b/kernel/trace/trace_uprobe.c | |||
| @@ -1111,7 +1111,7 @@ static void __uprobe_perf_func(struct trace_uprobe *tu, | |||
| 1111 | if (hlist_empty(head)) | 1111 | if (hlist_empty(head)) |
| 1112 | goto out; | 1112 | goto out; |
| 1113 | 1113 | ||
| 1114 | entry = perf_trace_buf_prepare(size, call->event.type, regs, &rctx); | 1114 | entry = perf_trace_buf_prepare(size, call->event.type, NULL, &rctx); |
| 1115 | if (!entry) | 1115 | if (!entry) |
| 1116 | goto out; | 1116 | goto out; |
| 1117 | 1117 | ||
| @@ -1321,7 +1321,7 @@ static __init int init_uprobe_trace(void) | |||
| 1321 | struct dentry *d_tracer; | 1321 | struct dentry *d_tracer; |
| 1322 | 1322 | ||
| 1323 | d_tracer = tracing_init_dentry(); | 1323 | d_tracer = tracing_init_dentry(); |
| 1324 | if (!d_tracer) | 1324 | if (IS_ERR(d_tracer)) |
| 1325 | return 0; | 1325 | return 0; |
| 1326 | 1326 | ||
| 1327 | trace_create_file("uprobe_events", 0644, d_tracer, | 1327 | trace_create_file("uprobe_events", 0644, d_tracer, |
