Loading include/trace/sched_event_types.h +6 −1 Original line number Diff line number Diff line Loading @@ -71,10 +71,15 @@ TRACE_EVENT_FORMAT(sched_switch, TRACE_STRUCT( TRACE_FIELD(pid_t, prev_pid, prev->pid) TRACE_FIELD(int, prev_prio, prev->prio) TRACE_FIELD_SPECIAL(char next_comm[TASK_COMM_LEN], next_comm, TPCMD(memcpy(TRACE_ENTRY->next_comm, next->comm, TASK_COMM_LEN))) TRACE_FIELD(pid_t, next_pid, next->pid) TRACE_FIELD(int, next_prio, next->prio) ), TPRAWFMT("prev %d:%d ==> next %d:%d") TPRAWFMT("prev %d:%d ==> next %s:%d:%d") ); TRACE_EVENT_FORMAT(sched_migrate_task, Loading kernel/trace/trace.c +5 −12 Original line number Diff line number Diff line Loading @@ -342,13 +342,6 @@ __update_max_tr(struct trace_array *tr, struct task_struct *tsk, int cpu) tracing_record_cmdline(tsk); } static void trace_seq_reset(struct trace_seq *s) { s->len = 0; s->readpos = 0; } ssize_t trace_seq_to_user(struct trace_seq *s, char __user *ubuf, size_t cnt) { int len; Loading Loading @@ -395,7 +388,7 @@ trace_print_seq(struct seq_file *m, struct trace_seq *s) s->buffer[len] = 0; seq_puts(m, s->buffer); trace_seq_reset(s); trace_seq_init(s); } /** Loading Loading @@ -2620,7 +2613,7 @@ tracing_read_pipe(struct file *filp, char __user *ubuf, if (sret != -EBUSY) return sret; trace_seq_reset(&iter->seq); trace_seq_init(&iter->seq); /* copy the tracer to avoid using a global lock all around */ mutex_lock(&trace_types_lock); Loading Loading @@ -2682,7 +2675,7 @@ tracing_read_pipe(struct file *filp, char __user *ubuf, /* Now copy what we have to the user */ sret = trace_seq_to_user(&iter->seq, ubuf, cnt); if (iter->seq.readpos >= iter->seq.len) trace_seq_reset(&iter->seq); trace_seq_init(&iter->seq); /* * If there was nothing to send to user, inspite of consuming trace Loading Loading @@ -2819,7 +2812,7 @@ static ssize_t tracing_splice_read_pipe(struct file *filp, partial[i].offset = 0; partial[i].len = iter->seq.len; trace_seq_reset(&iter->seq); trace_seq_init(&iter->seq); } mutex_unlock(&iter->mutex); Loading Loading @@ -3631,7 +3624,7 @@ trace_printk_seq(struct trace_seq *s) printk(KERN_TRACE "%s", s->buffer); trace_seq_reset(s); trace_seq_init(s); } void ftrace_dump(void) Loading kernel/trace/trace.h +9 −0 Original line number Diff line number Diff line Loading @@ -395,6 +395,14 @@ struct trace_seq { unsigned int readpos; }; static inline void trace_seq_init(struct trace_seq *s) { s->len = 0; s->readpos = 0; } #define TRACE_PIPE_ALL_CPU -1 /* Loading Loading @@ -746,6 +754,7 @@ struct ftrace_event_call { int (*raw_init)(void); int (*raw_reg)(void); void (*raw_unreg)(void); int (*show_format)(struct trace_seq *s); }; void event_trace_printk(unsigned long ip, const char *fmt, ...); Loading kernel/trace/trace_events.c +92 −2 Original line number Diff line number Diff line Loading @@ -3,6 +3,9 @@ * * Copyright (C) 2008 Red Hat Inc, Steven Rostedt <srostedt@redhat.com> * * - Added format output of fields of the trace point. * This was based off of work by Tom Zanussi <tzanussi@gmail.com>. * */ #include <linux/debugfs.h> Loading @@ -10,10 +13,12 @@ #include <linux/module.h> #include <linux/ctype.h> #include "trace.h" #include "trace_output.h" #define TRACE_SYSTEM "TRACE_SYSTEM" static DEFINE_MUTEX(event_mutex); #define events_for_each(event) \ for (event = __start_ftrace_events; \ (unsigned long)event < (unsigned long)__stop_ftrace_events; \ Loading Loading @@ -104,6 +109,7 @@ static int ftrace_set_clr_event(char *buf, int set) event = NULL; } mutex_lock(&event_mutex); events_for_each(call) { if (!call->name) Loading @@ -124,6 +130,8 @@ static int ftrace_set_clr_event(char *buf, int set) ret = 0; } mutex_unlock(&event_mutex); return ret; } Loading Loading @@ -324,7 +332,9 @@ event_enable_write(struct file *filp, const char __user *ubuf, size_t cnt, switch (val) { case 0: case 1: mutex_lock(&event_mutex); ftrace_event_enable_disable(call, val); mutex_unlock(&event_mutex); break; default: Loading Loading @@ -437,6 +447,71 @@ event_available_types_read(struct file *filp, char __user *ubuf, size_t cnt, return simple_read_from_buffer(ubuf, cnt, ppos, buf, r); } #undef FIELD #define FIELD(type, name) \ #type, #name, offsetof(typeof(field), name), sizeof(field.name) static int trace_write_header(struct trace_seq *s) { struct trace_entry field; /* struct trace_entry */ return trace_seq_printf(s, "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\n", FIELD(unsigned char, type), FIELD(unsigned char, flags), FIELD(unsigned char, preempt_count), FIELD(int, pid), FIELD(int, tgid)); } static ssize_t event_format_read(struct file *filp, char __user *ubuf, size_t cnt, loff_t *ppos) { struct ftrace_event_call *call = filp->private_data; struct trace_seq *s; char *buf; int r; s = kmalloc(sizeof(*s), GFP_KERNEL); if (!s) return -ENOMEM; trace_seq_init(s); if (*ppos) return 0; /* If any of the first writes fail, so will the show_format. */ trace_seq_printf(s, "name: %s\n", call->name); trace_seq_printf(s, "ID: %d\n", call->id); trace_seq_printf(s, "format:\n"); trace_write_header(s); r = call->show_format(s); if (!r) { /* * ug! The format output is bigger than a PAGE!! */ buf = "FORMAT TOO BIG\n"; r = simple_read_from_buffer(ubuf, cnt, ppos, buf, strlen(buf)); goto out; } r = simple_read_from_buffer(ubuf, cnt, ppos, s->buffer, s->len); out: kfree(s); return r; } static const struct seq_operations show_event_seq_ops = { .start = t_start, .next = t_next, Loading Loading @@ -483,6 +558,11 @@ static const struct file_operations ftrace_available_types_fops = { .read = event_available_types_read, }; static const struct file_operations ftrace_event_format_fops = { .open = tracing_open_generic, .read = event_format_read, }; static struct dentry *event_trace_events_dir(void) { static struct dentry *d_tracer; Loading Loading @@ -595,7 +675,17 @@ event_create_dir(struct ftrace_event_call *call, struct dentry *d_events) &ftrace_available_types_fops); if (!entry) pr_warning("Could not create debugfs " "'%s/type' available_types\n", call->name); "'%s/available_types' entry\n", call->name); /* A trace may not want to export its format */ if (!call->show_format) return 0; entry = debugfs_create_file("format", 0444, call->dir, call, &ftrace_event_format_fops); if (!entry) pr_warning("Could not create debugfs " "'%s/format' entry\n", call->name); return 0; } Loading kernel/trace/trace_events_stage_1.h +2 −0 Original line number Diff line number Diff line Loading @@ -30,5 +30,7 @@ #define TRACE_FIELD(type, item, assign) \ type item; #define TRACE_FIELD_SPECIAL(type_item, item, cmd) \ type_item; #include <trace/trace_event_types.h> Loading
include/trace/sched_event_types.h +6 −1 Original line number Diff line number Diff line Loading @@ -71,10 +71,15 @@ TRACE_EVENT_FORMAT(sched_switch, TRACE_STRUCT( TRACE_FIELD(pid_t, prev_pid, prev->pid) TRACE_FIELD(int, prev_prio, prev->prio) TRACE_FIELD_SPECIAL(char next_comm[TASK_COMM_LEN], next_comm, TPCMD(memcpy(TRACE_ENTRY->next_comm, next->comm, TASK_COMM_LEN))) TRACE_FIELD(pid_t, next_pid, next->pid) TRACE_FIELD(int, next_prio, next->prio) ), TPRAWFMT("prev %d:%d ==> next %d:%d") TPRAWFMT("prev %d:%d ==> next %s:%d:%d") ); TRACE_EVENT_FORMAT(sched_migrate_task, Loading
kernel/trace/trace.c +5 −12 Original line number Diff line number Diff line Loading @@ -342,13 +342,6 @@ __update_max_tr(struct trace_array *tr, struct task_struct *tsk, int cpu) tracing_record_cmdline(tsk); } static void trace_seq_reset(struct trace_seq *s) { s->len = 0; s->readpos = 0; } ssize_t trace_seq_to_user(struct trace_seq *s, char __user *ubuf, size_t cnt) { int len; Loading Loading @@ -395,7 +388,7 @@ trace_print_seq(struct seq_file *m, struct trace_seq *s) s->buffer[len] = 0; seq_puts(m, s->buffer); trace_seq_reset(s); trace_seq_init(s); } /** Loading Loading @@ -2620,7 +2613,7 @@ tracing_read_pipe(struct file *filp, char __user *ubuf, if (sret != -EBUSY) return sret; trace_seq_reset(&iter->seq); trace_seq_init(&iter->seq); /* copy the tracer to avoid using a global lock all around */ mutex_lock(&trace_types_lock); Loading Loading @@ -2682,7 +2675,7 @@ tracing_read_pipe(struct file *filp, char __user *ubuf, /* Now copy what we have to the user */ sret = trace_seq_to_user(&iter->seq, ubuf, cnt); if (iter->seq.readpos >= iter->seq.len) trace_seq_reset(&iter->seq); trace_seq_init(&iter->seq); /* * If there was nothing to send to user, inspite of consuming trace Loading Loading @@ -2819,7 +2812,7 @@ static ssize_t tracing_splice_read_pipe(struct file *filp, partial[i].offset = 0; partial[i].len = iter->seq.len; trace_seq_reset(&iter->seq); trace_seq_init(&iter->seq); } mutex_unlock(&iter->mutex); Loading Loading @@ -3631,7 +3624,7 @@ trace_printk_seq(struct trace_seq *s) printk(KERN_TRACE "%s", s->buffer); trace_seq_reset(s); trace_seq_init(s); } void ftrace_dump(void) Loading
kernel/trace/trace.h +9 −0 Original line number Diff line number Diff line Loading @@ -395,6 +395,14 @@ struct trace_seq { unsigned int readpos; }; static inline void trace_seq_init(struct trace_seq *s) { s->len = 0; s->readpos = 0; } #define TRACE_PIPE_ALL_CPU -1 /* Loading Loading @@ -746,6 +754,7 @@ struct ftrace_event_call { int (*raw_init)(void); int (*raw_reg)(void); void (*raw_unreg)(void); int (*show_format)(struct trace_seq *s); }; void event_trace_printk(unsigned long ip, const char *fmt, ...); Loading
kernel/trace/trace_events.c +92 −2 Original line number Diff line number Diff line Loading @@ -3,6 +3,9 @@ * * Copyright (C) 2008 Red Hat Inc, Steven Rostedt <srostedt@redhat.com> * * - Added format output of fields of the trace point. * This was based off of work by Tom Zanussi <tzanussi@gmail.com>. * */ #include <linux/debugfs.h> Loading @@ -10,10 +13,12 @@ #include <linux/module.h> #include <linux/ctype.h> #include "trace.h" #include "trace_output.h" #define TRACE_SYSTEM "TRACE_SYSTEM" static DEFINE_MUTEX(event_mutex); #define events_for_each(event) \ for (event = __start_ftrace_events; \ (unsigned long)event < (unsigned long)__stop_ftrace_events; \ Loading Loading @@ -104,6 +109,7 @@ static int ftrace_set_clr_event(char *buf, int set) event = NULL; } mutex_lock(&event_mutex); events_for_each(call) { if (!call->name) Loading @@ -124,6 +130,8 @@ static int ftrace_set_clr_event(char *buf, int set) ret = 0; } mutex_unlock(&event_mutex); return ret; } Loading Loading @@ -324,7 +332,9 @@ event_enable_write(struct file *filp, const char __user *ubuf, size_t cnt, switch (val) { case 0: case 1: mutex_lock(&event_mutex); ftrace_event_enable_disable(call, val); mutex_unlock(&event_mutex); break; default: Loading Loading @@ -437,6 +447,71 @@ event_available_types_read(struct file *filp, char __user *ubuf, size_t cnt, return simple_read_from_buffer(ubuf, cnt, ppos, buf, r); } #undef FIELD #define FIELD(type, name) \ #type, #name, offsetof(typeof(field), name), sizeof(field.name) static int trace_write_header(struct trace_seq *s) { struct trace_entry field; /* struct trace_entry */ return trace_seq_printf(s, "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\tfield:%s %s;\toffset:%lu;\tsize:%lu;\n" "\n", FIELD(unsigned char, type), FIELD(unsigned char, flags), FIELD(unsigned char, preempt_count), FIELD(int, pid), FIELD(int, tgid)); } static ssize_t event_format_read(struct file *filp, char __user *ubuf, size_t cnt, loff_t *ppos) { struct ftrace_event_call *call = filp->private_data; struct trace_seq *s; char *buf; int r; s = kmalloc(sizeof(*s), GFP_KERNEL); if (!s) return -ENOMEM; trace_seq_init(s); if (*ppos) return 0; /* If any of the first writes fail, so will the show_format. */ trace_seq_printf(s, "name: %s\n", call->name); trace_seq_printf(s, "ID: %d\n", call->id); trace_seq_printf(s, "format:\n"); trace_write_header(s); r = call->show_format(s); if (!r) { /* * ug! The format output is bigger than a PAGE!! */ buf = "FORMAT TOO BIG\n"; r = simple_read_from_buffer(ubuf, cnt, ppos, buf, strlen(buf)); goto out; } r = simple_read_from_buffer(ubuf, cnt, ppos, s->buffer, s->len); out: kfree(s); return r; } static const struct seq_operations show_event_seq_ops = { .start = t_start, .next = t_next, Loading Loading @@ -483,6 +558,11 @@ static const struct file_operations ftrace_available_types_fops = { .read = event_available_types_read, }; static const struct file_operations ftrace_event_format_fops = { .open = tracing_open_generic, .read = event_format_read, }; static struct dentry *event_trace_events_dir(void) { static struct dentry *d_tracer; Loading Loading @@ -595,7 +675,17 @@ event_create_dir(struct ftrace_event_call *call, struct dentry *d_events) &ftrace_available_types_fops); if (!entry) pr_warning("Could not create debugfs " "'%s/type' available_types\n", call->name); "'%s/available_types' entry\n", call->name); /* A trace may not want to export its format */ if (!call->show_format) return 0; entry = debugfs_create_file("format", 0444, call->dir, call, &ftrace_event_format_fops); if (!entry) pr_warning("Could not create debugfs " "'%s/format' entry\n", call->name); return 0; } Loading
kernel/trace/trace_events_stage_1.h +2 −0 Original line number Diff line number Diff line Loading @@ -30,5 +30,7 @@ #define TRACE_FIELD(type, item, assign) \ type item; #define TRACE_FIELD_SPECIAL(type_item, item, cmd) \ type_item; #include <trace/trace_event_types.h>