Merge branch 'perf-probes-for-linus-2' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip
* 'perf-probes-for-linus-2' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip: x86: Issue at least one memory barrier in stop_machine_text_poke() perf probe: Correct probe syntax on command line help perf probe: Add lazy line matching support perf probe: Show more lines after last line perf probe: Check function address range strictly in line finder perf probe: Use libdw callback routines perf probe: Use elfutils-libdw for analyzing debuginfo perf probe: Rename probe finder functions perf probe: Fix bugs in line range finder perf probe: Update perf probe document perf probe: Do not show --line option without dwarf support kprobes: Add documents of jump optimization kprobes/x86: Support kprobes jump optimization on x86 x86: Add text_poke_smp for SMP cross modifying code kprobes/x86: Cleanup save/restore registers kprobes/x86: Boost probes when reentering kprobes: Jump optimization sysctl interface kprobes: Introduce kprobes jump optimization kprobes: Introduce generic insn_slot framework kprobes/x86: Cleanup RELATIVEJUMP_INSTRUCTION to RELATIVEJUMP_OPCODE
This commit is contained in:
@ -119,14 +119,14 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
char c, nc = 0;
|
||||
/*
|
||||
* <Syntax>
|
||||
* perf probe [EVENT=]SRC:LN
|
||||
* perf probe [EVENT=]FUNC[+OFFS|%return][@SRC]
|
||||
* perf probe [EVENT=]SRC[:LN|;PTN]
|
||||
* perf probe [EVENT=]FUNC[@SRC][+OFFS|%return|:LN|;PAT]
|
||||
*
|
||||
* TODO:Group name support
|
||||
*/
|
||||
|
||||
ptr = strchr(arg, '=');
|
||||
if (ptr) { /* Event name */
|
||||
ptr = strpbrk(arg, ";=@+%");
|
||||
if (ptr && *ptr == '=') { /* Event name */
|
||||
*ptr = '\0';
|
||||
tmp = ptr + 1;
|
||||
ptr = strchr(arg, ':');
|
||||
@ -139,7 +139,7 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
arg = tmp;
|
||||
}
|
||||
|
||||
ptr = strpbrk(arg, ":+@%");
|
||||
ptr = strpbrk(arg, ";:+@%");
|
||||
if (ptr) {
|
||||
nc = *ptr;
|
||||
*ptr++ = '\0';
|
||||
@ -156,7 +156,11 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
while (ptr) {
|
||||
arg = ptr;
|
||||
c = nc;
|
||||
ptr = strpbrk(arg, ":+@%");
|
||||
if (c == ';') { /* Lazy pattern must be the last part */
|
||||
pp->lazy_line = strdup(arg);
|
||||
break;
|
||||
}
|
||||
ptr = strpbrk(arg, ";:+@%");
|
||||
if (ptr) {
|
||||
nc = *ptr;
|
||||
*ptr++ = '\0';
|
||||
@ -165,13 +169,13 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
case ':': /* Line number */
|
||||
pp->line = strtoul(arg, &tmp, 0);
|
||||
if (*tmp != '\0')
|
||||
semantic_error("There is non-digit charactor"
|
||||
" in line number.");
|
||||
semantic_error("There is non-digit char"
|
||||
" in line number.");
|
||||
break;
|
||||
case '+': /* Byte offset from a symbol */
|
||||
pp->offset = strtoul(arg, &tmp, 0);
|
||||
if (*tmp != '\0')
|
||||
semantic_error("There is non-digit charactor"
|
||||
semantic_error("There is non-digit character"
|
||||
" in offset.");
|
||||
break;
|
||||
case '@': /* File name */
|
||||
@ -179,9 +183,6 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
semantic_error("SRC@SRC is not allowed.");
|
||||
pp->file = strdup(arg);
|
||||
DIE_IF(pp->file == NULL);
|
||||
if (ptr)
|
||||
semantic_error("@SRC must be the last "
|
||||
"option.");
|
||||
break;
|
||||
case '%': /* Probe places */
|
||||
if (strcmp(arg, "return") == 0) {
|
||||
@ -196,11 +197,18 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
}
|
||||
|
||||
/* Exclusion check */
|
||||
if (pp->lazy_line && pp->line)
|
||||
semantic_error("Lazy pattern can't be used with line number.");
|
||||
|
||||
if (pp->lazy_line && pp->offset)
|
||||
semantic_error("Lazy pattern can't be used with offset.");
|
||||
|
||||
if (pp->line && pp->offset)
|
||||
semantic_error("Offset can't be used with line number.");
|
||||
|
||||
if (!pp->line && pp->file && !pp->function)
|
||||
semantic_error("File always requires line number.");
|
||||
if (!pp->line && !pp->lazy_line && pp->file && !pp->function)
|
||||
semantic_error("File always requires line number or "
|
||||
"lazy pattern.");
|
||||
|
||||
if (pp->offset && !pp->function)
|
||||
semantic_error("Offset requires an entry function.");
|
||||
@ -208,11 +216,13 @@ static void parse_perf_probe_probepoint(char *arg, struct probe_point *pp)
|
||||
if (pp->retprobe && !pp->function)
|
||||
semantic_error("Return probe requires an entry function.");
|
||||
|
||||
if ((pp->offset || pp->line) && pp->retprobe)
|
||||
semantic_error("Offset/Line can't be used with return probe.");
|
||||
if ((pp->offset || pp->line || pp->lazy_line) && pp->retprobe)
|
||||
semantic_error("Offset/Line/Lazy pattern can't be used with "
|
||||
"return probe.");
|
||||
|
||||
pr_debug("symbol:%s file:%s line:%d offset:%d, return:%d\n",
|
||||
pp->function, pp->file, pp->line, pp->offset, pp->retprobe);
|
||||
pr_debug("symbol:%s file:%s line:%d offset:%d return:%d lazy:%s\n",
|
||||
pp->function, pp->file, pp->line, pp->offset, pp->retprobe,
|
||||
pp->lazy_line);
|
||||
}
|
||||
|
||||
/* Parse perf-probe event definition */
|
||||
@ -458,6 +468,8 @@ static void clear_probe_point(struct probe_point *pp)
|
||||
free(pp->function);
|
||||
if (pp->file)
|
||||
free(pp->file);
|
||||
if (pp->lazy_line)
|
||||
free(pp->lazy_line);
|
||||
for (i = 0; i < pp->nr_args; i++)
|
||||
free(pp->args[i]);
|
||||
if (pp->args)
|
||||
@ -719,6 +731,7 @@ void del_trace_kprobe_events(struct strlist *dellist)
|
||||
}
|
||||
|
||||
#define LINEBUF_SIZE 256
|
||||
#define NR_ADDITIONAL_LINES 2
|
||||
|
||||
static void show_one_line(FILE *fp, unsigned int l, bool skip, bool show_num)
|
||||
{
|
||||
@ -779,5 +792,11 @@ void show_line_range(struct line_range *lr)
|
||||
show_one_line(fp, (l++) - lr->offset, false, false);
|
||||
show_one_line(fp, (l++) - lr->offset, false, true);
|
||||
}
|
||||
|
||||
if (lr->end == INT_MAX)
|
||||
lr->end = l + NR_ADDITIONAL_LINES;
|
||||
while (l < lr->end && !feof(fp))
|
||||
show_one_line(fp, (l++) - lr->offset, false, false);
|
||||
|
||||
fclose(fp);
|
||||
}
|
||||
|
Reference in New Issue
Block a user