aboutsummaryrefslogtreecommitdiffstats
path: root/tools/perf/util/probe-event.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/perf/util/probe-event.c')
-rw-r--r--tools/perf/util/probe-event.c105
1 files changed, 104 insertions, 1 deletions
diff --git a/tools/perf/util/probe-event.c b/tools/perf/util/probe-event.c
index fde17b090a47..8f0568849691 100644
--- a/tools/perf/util/probe-event.c
+++ b/tools/perf/util/probe-event.c
@@ -37,6 +37,8 @@
37#include "string.h" 37#include "string.h"
38#include "strlist.h" 38#include "strlist.h"
39#include "debug.h" 39#include "debug.h"
40#include "cache.h"
41#include "color.h"
40#include "parse-events.h" /* For debugfs_path */ 42#include "parse-events.h" /* For debugfs_path */
41#include "probe-event.h" 43#include "probe-event.h"
42 44
@@ -62,6 +64,42 @@ static int e_snprintf(char *str, size_t size, const char *format, ...)
62 return ret; 64 return ret;
63} 65}
64 66
67void parse_line_range_desc(const char *arg, struct line_range *lr)
68{
69 const char *ptr;
70 char *tmp;
71 /*
72 * <Syntax>
73 * SRC:SLN[+NUM|-ELN]
74 * FUNC[:SLN[+NUM|-ELN]]
75 */
76 ptr = strchr(arg, ':');
77 if (ptr) {
78 lr->start = (unsigned int)strtoul(ptr + 1, &tmp, 0);
79 if (*tmp == '+')
80 lr->end = lr->start + (unsigned int)strtoul(tmp + 1,
81 &tmp, 0);
82 else if (*tmp == '-')
83 lr->end = (unsigned int)strtoul(tmp + 1, &tmp, 0);
84 else
85 lr->end = 0;
86 pr_debug("Line range is %u to %u\n", lr->start, lr->end);
87 if (lr->end && lr->start > lr->end)
88 semantic_error("Start line must be smaller"
89 " than end line.");
90 if (*tmp != '\0')
91 semantic_error("Tailing with invalid character '%d'.",
92 *tmp);
93 tmp = strndup(arg, (ptr - arg));
94 } else
95 tmp = strdup(arg);
96
97 if (strchr(tmp, '.'))
98 lr->file = tmp;
99 else
100 lr->function = tmp;
101}
102
65/* Check the name is good for event/group */ 103/* Check the name is good for event/group */
66static bool check_event_name(const char *name) 104static bool check_event_name(const char *name)
67{ 105{
@@ -370,7 +408,7 @@ static int open_kprobe_events(int flags, int mode)
370 if (ret < 0) { 408 if (ret < 0) {
371 if (errno == ENOENT) 409 if (errno == ENOENT)
372 die("kprobe_events file does not exist -" 410 die("kprobe_events file does not exist -"
373 " please rebuild with CONFIG_KPROBE_TRACER."); 411 " please rebuild with CONFIG_KPROBE_EVENT.");
374 else 412 else
375 die("Could not open kprobe_events file: %s", 413 die("Could not open kprobe_events file: %s",
376 strerror(errno)); 414 strerror(errno));
@@ -457,6 +495,8 @@ void show_perf_probe_events(void)
457 struct strlist *rawlist; 495 struct strlist *rawlist;
458 struct str_node *ent; 496 struct str_node *ent;
459 497
498 setup_pager();
499
460 memset(&pp, 0, sizeof(pp)); 500 memset(&pp, 0, sizeof(pp));
461 fd = open_kprobe_events(O_RDONLY, 0); 501 fd = open_kprobe_events(O_RDONLY, 0);
462 rawlist = get_trace_kprobe_event_rawlist(fd); 502 rawlist = get_trace_kprobe_event_rawlist(fd);
@@ -678,3 +718,66 @@ void del_trace_kprobe_events(struct strlist *dellist)
678 close(fd); 718 close(fd);
679} 719}
680 720
721#define LINEBUF_SIZE 256
722
723static void show_one_line(FILE *fp, unsigned int l, bool skip, bool show_num)
724{
725 char buf[LINEBUF_SIZE];
726 const char *color = PERF_COLOR_BLUE;
727
728 if (fgets(buf, LINEBUF_SIZE, fp) == NULL)
729 goto error;
730 if (!skip) {
731 if (show_num)
732 fprintf(stdout, "%7u %s", l, buf);
733 else
734 color_fprintf(stdout, color, " %s", buf);
735 }
736
737 while (strlen(buf) == LINEBUF_SIZE - 1 &&
738 buf[LINEBUF_SIZE - 2] != '\n') {
739 if (fgets(buf, LINEBUF_SIZE, fp) == NULL)
740 goto error;
741 if (!skip) {
742 if (show_num)
743 fprintf(stdout, "%s", buf);
744 else
745 color_fprintf(stdout, color, "%s", buf);
746 }
747 }
748 return;
749error:
750 if (feof(fp))
751 die("Source file is shorter than expected.");
752 else
753 die("File read error: %s", strerror(errno));
754}
755
756void show_line_range(struct line_range *lr)
757{
758 unsigned int l = 1;
759 struct line_node *ln;
760 FILE *fp;
761
762 setup_pager();
763
764 if (lr->function)
765 fprintf(stdout, "<%s:%d>\n", lr->function,
766 lr->start - lr->offset);
767 else
768 fprintf(stdout, "<%s:%d>\n", lr->file, lr->start);
769
770 fp = fopen(lr->path, "r");
771 if (fp == NULL)
772 die("Failed to open %s: %s", lr->path, strerror(errno));
773 /* Skip to starting line number */
774 while (l < lr->start)
775 show_one_line(fp, l++, true, false);
776
777 list_for_each_entry(ln, &lr->line_list, list) {
778 while (ln->line > l)
779 show_one_line(fp, (l++) - lr->offset, false, false);
780 show_one_line(fp, (l++) - lr->offset, false, true);
781 }
782 fclose(fp);
783}