22 #include <sys/utsname.h>
23 #include <sys/types.h>
49 #define MAX_CMDLEN 256
50 #define MAX_PROBE_ARGS 128
51 #define PERFPROBE_GROUP "probe"
55 #define semantic_error(msg ...) pr_err("Semantic error :" msg)
58 static int e_snprintf(
char *
str,
size_t size,
const char *
format, ...)
61 static
int e_snprintf(
char *str,
size_t size,
const char *format, ...)
79 static int init_vmlinux(
void)
90 pr_debug(
"Failed to init symbol map.\n");
99 pr_debug(
"machine__create_kernel_maps() failed.\n");
108 static struct symbol *__find_kernel_function_by_name(
const char *
name,
111 return machine__find_kernel_function_by_name(&
machine, name, mapp,
115 static struct map *kernel_get_module_map(
const char *
module)
121 if (module &&
strchr(module,
'/'))
130 pos->
dso->short_name_len - 2) == 0) {
137 static struct dso *kernel_get_module_dso(
const char *module)
141 const char *vmlinux_name;
149 pr_debug(
"Failed to find module %s.\n", module);
162 pr_debug(
"Failed to load kernel map.\n");
172 struct dso *dso = kernel_get_module_dso(module);
176 static int init_user_exec(
void)
185 pr_debug(
"Failed to init symbol map.\n");
206 static struct debuginfo *open_debuginfo(
const char *module)
211 if (module &&
strchr(module,
'/'))
217 pr_err(
"Failed to find path of %s module.\n",
236 struct debuginfo *dinfo;
238 sym = __find_kernel_function_by_name(tp->
symbol, &map);
247 (
unsigned long)addr, pp);
256 pr_debug(
"Failed to find corresponding probes from "
257 "debuginfo. Use kprobe event information.\n");
258 return convert_to_perf_probe_point(tp, pp);
266 int ntevs,
const char *module)
277 module = strdup(tmp + 1);
280 tmp =
strchr(module,
'.');
283 tmp = (
char *)module;
286 for (i = 0; i < ntevs; i++) {
287 tevs[
i].
point.module = strdup(module);
288 if (!tevs[i].
point.module) {
303 int max_tevs,
const char *
target)
306 struct debuginfo *dinfo;
311 pr_warning(
"Debuginfo-analysis is not yet supported"
312 " with -x/--exec option.\n");
315 return convert_name_to_addr(pev, target);
318 dinfo = open_debuginfo(target);
322 pr_warning(
"Failed to open debuginfo file.\n");
325 pr_debug(
"Could not open debuginfo. Try to use symbols.\n");
335 pr_debug(
"find %d probe_trace_events.\n", ntevs);
337 ret = add_module_to_probe_trace_events(*tevs, ntevs,
339 return ret < 0 ? ret : ntevs;
344 synthesize_perf_probe_point(&pev->
point));
348 pr_debug(
"An error occurred in debuginfo analysis (%d).\n", ntevs);
349 if (ntevs == -
EBADF) {
350 pr_warning(
"Warning: No dwarf info found in the vmlinux - "
351 "please rebuild kernel with CONFIG_DEBUG_INFO=y.\n");
353 pr_debug(
"Trying to use symbols.\n");
366 static int get_real_path(
const char *raw_path,
const char *comp_dir,
372 if (raw_path[0] !=
'/' && comp_dir)
376 if (
access(raw_path, R_OK) == 0) {
377 *new_path = strdup(raw_path);
389 sprintf(*new_path,
"%s/%s", prefix, raw_path);
391 if (
access(*new_path, R_OK) == 0)
403 raw_path =
strchr(++raw_path,
'/');
419 #define LINEBUF_SIZE 256
420 #define NR_ADDITIONAL_LINES 2
422 static int __show_one_line(FILE *
fp,
int l,
bool skip,
bool show_num)
424 char buf[LINEBUF_SIZE];
426 const char *prefix =
NULL;
429 if (fgets(buf, LINEBUF_SIZE, fp) ==
NULL)
434 prefix = show_num ?
"%7d " :
" ";
450 static int _show_one_line(FILE *fp,
int l,
bool skip,
bool show_num)
452 int rv = __show_one_line(fp, l, skip, show_num);
454 pr_warning(
"Source file is shorter than expected.\n");
460 #define show_one_line_with_num(f,l) _show_one_line(f,l,false,true)
461 #define show_one_line(f,l) _show_one_line(f,l,false,false)
462 #define skip_one_line(f,l) _show_one_line(f,l,true,false)
463 #define show_one_line_or_eof(f,l) __show_one_line(f,l,false,false)
473 struct debuginfo *dinfo;
479 ret = init_vmlinux();
483 dinfo = open_debuginfo(module);
485 pr_warning(
"Failed to open debuginfo file.\n");
492 pr_warning(
"Specified source line is not found.\n");
494 }
else if (ret < 0) {
495 pr_warning(
"Debuginfo analysis failed. (%d)\n", ret);
504 pr_warning(
"Failed to find source file. (%d)\n", ret);
516 fp = fopen(lr->
path,
"r");
523 while (l < lr->
start) {
524 ret = skip_one_line(fp, l++);
530 for (; ln->
line >
l; l++) {
531 ret = show_one_line(fp, l - lr->
offset);
535 ret = show_one_line_with_num(fp, l++ - lr->
offset);
541 lr->
end = l + NR_ADDITIONAL_LINES;
542 while (l <= lr->
end) {
543 ret = show_one_line_or_eof(fp, l++ - lr->
offset);
552 static int show_available_vars_at(
struct debuginfo *dinfo,
563 buf = synthesize_perf_probe_point(&pev->
point);
566 pr_debug(
"Searching variables at %s\n", buf);
571 pr_err(
"Failed to find variables at %s (%d)\n", buf, ret);
575 fprintf(stdout,
"Available variables at %s\n", buf);
576 for (i = 0; i <
ret; i++) {
582 fprintf(stdout,
"\t@<%s+%lu>\n", vl->point.symbol,
584 free(vl->point.symbol);
588 var =
strchr(node->
s,
'\t') + 1;
590 fprintf(stdout,
"\t\t%s\n", node->
s);
597 fprintf(stdout,
"\t\t(No matched variables)\n");
607 int max_vls,
const char *module,
611 struct debuginfo *dinfo;
613 ret = init_vmlinux();
617 dinfo = open_debuginfo(module);
619 pr_warning(
"Failed to open debuginfo file.\n");
625 for (i = 0; i < npevs && ret >= 0; i++)
626 ret = show_available_vars_at(dinfo, &pevs[i], max_vls, _filter,
640 sym = __find_kernel_function_by_name(tp->
symbol,
NULL);
642 pr_err(
"Failed to find symbol %s in kernel.\n", tp->
symbol);
646 return convert_to_perf_probe_point(tp, pp);
651 int max_tevs __maybe_unused,
const char *target)
654 pr_warning(
"Debuginfo-analysis is not supported.\n");
659 return convert_name_to_addr(pev, target);
665 const char *module __maybe_unused)
667 pr_warning(
"Debuginfo-analysis is not supported.\n");
672 int npevs __maybe_unused,
int max_vls __maybe_unused,
673 const char *module __maybe_unused,
675 bool externs __maybe_unused)
677 pr_warning(
"Debuginfo-analysis is not supported.\n");
682 static int parse_line_num(
char **
ptr,
int *
val,
const char *
what)
684 const char *start = *
ptr;
687 *val = strtol(*ptr, ptr, 0);
688 if (errno || *ptr == start) {
713 range =
strchr(name,
':');
717 err = parse_line_num(&range, &lr->
start,
"start line");
721 if (*range ==
'+' || *range ==
'-') {
722 const char c = *range++;
724 err = parse_line_num(&range, &lr->
end,
"end line");
745 " than end line.\n");
748 if (*range !=
'\0') {
757 lr->
file = strdup(++file);
763 }
else if (
strchr(name,
'.'))
775 static bool check_event_name(
const char *
name)
777 if (!
isalpha(*name) && *name !=
'_')
779 while (*++name !=
'\0') {
801 if (ptr && *ptr ==
'=') {
808 if (!check_event_name(arg)) {
810 "follow C symbol-naming rule.\n", arg);
813 pev->
event = strdup(arg);
853 pp->
line = strtoul(arg, &tmp, 0);
856 " in line number.\n");
861 pp->
offset = strtoul(arg, &tmp, 0);
873 pp->
file = strdup(arg);
878 if (
strcmp(arg,
"return") == 0) {
886 pr_err(
"This program has a bug at %s:%d.\n",
932 pr_debug(
"symbol:%s file:%s line:%d offset:%lu return:%d lazy:%s\n",
941 char *
tmp, *goodname;
944 pr_debug(
"parsing arg: %s into ", str);
948 arg->
name = strndup(str, tmp - str);
958 arg->
type = strdup(tmp + 1);
965 if (!is_c_varname(str) || !tmp) {
967 arg->
var = strdup(str);
975 arg->
var = strndup(str, tmp - str);
980 fieldp = &arg->
field;
988 (*fieldp)->index = strtol(str + 1, &tmp, 0);
989 (*fieldp)->ref =
true;
990 if (*tmp !=
']' || tmp == str + 1) {
1001 (*fieldp)->ref =
false;
1002 }
else if (tmp[1] ==
'>') {
1004 (*fieldp)->ref =
true;
1013 (*fieldp)->name = strndup(str, tmp - str);
1014 if ((*fieldp)->name ==
NULL)
1017 goodname = (*fieldp)->name;
1018 pr_debug(
"%s(%d), ", (*fieldp)->name, (*fieldp)->ref);
1019 fieldp = &(*fieldp)->
next;
1022 (*fieldp)->name = strdup(str);
1023 if ((*fieldp)->name ==
NULL)
1026 goodname = (*fieldp)->name;
1027 pr_debug(
"%s(%d)\n", (*fieldp)->name, (*fieldp)->ref);
1031 arg->
name = strdup(goodname);
1042 int argc,
i, ret = 0;
1046 pr_debug(
"Failed to split arguments.\n");
1055 ret = parse_perf_probe_point(argv[0], pev);
1060 pev->
nargs = argc - 1;
1066 for (i = 0; i < pev->
nargs && ret >= 0; i++) {
1067 ret = parse_perf_probe_arg(argv[i + 1], &pev->
args[i]);
1069 is_c_varname(pev->
args[i].var) && pev->
point.retprobe) {
1089 for (i = 0; i < pev->
nargs; i++)
1090 if (is_c_varname(pev->
args[i].var))
1097 static int parse_probe_trace_command(
const char *
cmd,
1103 char *argv0_str =
NULL, *
fmt, *fmt1_str, *fmt2_str, *fmt3_str;
1107 pr_debug(
"Parsing probe_events: %s\n", cmd);
1110 pr_debug(
"Failed to split arguments.\n");
1120 argv0_str = strdup(argv[0]);
1121 if (argv0_str ==
NULL) {
1125 fmt1_str = strtok_r(argv0_str,
":", &fmt);
1126 fmt2_str = strtok_r(
NULL,
"/", &fmt);
1127 fmt3_str = strtok_r(
NULL,
" \t", &fmt);
1128 if (fmt1_str ==
NULL ||
strlen(fmt1_str) != 1 || fmt2_str ==
NULL
1129 || fmt3_str ==
NULL) {
1135 tev->
group = strdup(fmt2_str);
1136 tev->
event = strdup(fmt3_str);
1146 p =
strchr(argv[1],
':');
1148 tp->
module = strndup(argv[1], p - argv[1]);
1152 fmt1_str = strtok_r(p,
"+", &fmt);
1153 tp->
symbol = strdup(fmt1_str);
1158 fmt2_str = strtok_r(
NULL,
"", &fmt);
1159 if (fmt2_str ==
NULL)
1164 tev->
nargs = argc - 2;
1170 for (i = 0; i < tev->
nargs; i++) {
1171 p =
strchr(argv[i + 2],
'=');
1176 tev->
args[
i].name = strdup(argv[i + 2]);
1178 tev->
args[
i].value = strdup(p);
1199 ret = e_snprintf(tmp, len,
"%s=%s", pa->
name, pa->
var);
1201 ret = e_snprintf(tmp, len,
"%s", pa->
name ? pa->
name : pa->
var);
1208 if (field->
name[0] ==
'[')
1209 ret = e_snprintf(tmp, len,
"%s", field->
name);
1211 ret = e_snprintf(tmp, len,
"%s%s",
1212 field->
ref ?
"->" :
".", field->
name);
1217 field = field->
next;
1221 ret = e_snprintf(tmp, len,
":%s", pa->
type);
1230 pr_debug(
"Failed to synthesize perf probe argument: %s\n",
1248 ret = e_snprintf(offs, 32,
"+%lu", pp->
offset);
1253 ret = e_snprintf(
line, 32,
":%d", pp->
line);
1262 tmp = tmp ? tmp + 1 : pp->
file + len - 30;
1264 ret = e_snprintf(
file, 32,
"@%s", tmp);
1280 pr_debug(
"Failed to synthesize perf probe point: %s\n",
1293 buf = synthesize_perf_probe_point(&pev->
point);
1298 for (i = 0; i < pev->
nargs; i++) {
1299 ret = e_snprintf(&buf[len],
MAX_CMDLEN - len,
" %s",
1313 char **buf,
size_t *
buflen,
1318 depth = __synthesize_probe_trace_arg_ref(ref->
next, buf,
1324 ret = e_snprintf(*buf, *buflen,
"%+ld(", ref->
offset);
1337 char *buf,
size_t buflen)
1345 ret = e_snprintf(buf, buflen,
" %s=", arg->
name);
1347 ret = e_snprintf(buf, buflen,
" ");
1354 if (arg->
value[0] ==
'@' && arg->
ref)
1359 depth = __synthesize_probe_trace_arg_ref(ref, &buf,
1366 if (arg->
value[0] ==
'@' && arg->
ref)
1367 ret = e_snprintf(buf, buflen,
"%s%+ld", arg->
value,
1370 ret = e_snprintf(buf, buflen,
"%s", arg->
value);
1378 ret = e_snprintf(buf, buflen,
")");
1386 ret = e_snprintf(buf, buflen,
":%s", arg->
type);
1406 len = e_snprintf(buf,
MAX_CMDLEN,
"%c:%s/%s %s:%s",
1411 len = e_snprintf(buf,
MAX_CMDLEN,
"%c:%s/%s %s%s%s+%lu",
1420 for (i = 0; i < tev->
nargs; i++) {
1421 ret = synthesize_probe_trace_arg(&tev->
args[i], buf + len,
1448 ret = kprobe_convert_to_perf_probe(&tev->
point, &pev->
point);
1450 ret = convert_to_perf_probe_point(&tev->
point, &pev->
point);
1460 for (i = 0; i < tev->
nargs && ret >= 0; i++) {
1461 if (tev->
args[i].name)
1462 pev->
args[
i].name = strdup(tev->
args[i].name);
1464 ret = synthesize_probe_trace_arg(&tev->
args[i],
1466 pev->
args[
i].name = strdup(buf);
1468 if (pev->
args[i].name ==
NULL && ret >= 0)
1494 for (i = 0; i < pev->
nargs; i++) {
1495 if (pev->
args[i].name)
1497 if (pev->
args[i].var)
1499 if (pev->
args[i].type)
1501 field = pev->
args[
i].field;
1512 memset(pev, 0,
sizeof(*pev));
1524 if (tev->
point.symbol)
1526 if (tev->
point.module)
1528 for (i = 0; i < tev->
nargs; i++) {
1529 if (tev->
args[i].name)
1531 if (tev->
args[i].value)
1533 if (tev->
args[i].type)
1535 ref = tev->
args[
i].ref;
1544 memset(tev, 0,
sizeof(*tev));
1547 static void print_warn_msg(
const char *
file,
bool is_kprobe)
1554 config =
"CONFIG_UPROBE_EVENTS";
1556 config =
"CONFIG_KPROBE_EVENTS";
1558 pr_warning(
"%s file does not exist - please rebuild kernel"
1559 " with %s.\n", file, config);
1561 pr_warning(
"Failed to open %s file: %s\n", file,
1565 static int open_probe_events(
const char *trace_file,
bool readwrite,
1569 const char *__debugfs;
1573 if (__debugfs ==
NULL) {
1578 ret = e_snprintf(buf,
PATH_MAX,
"%s/%s", __debugfs, trace_file);
1580 pr_debug(
"Opening %s write=%d\n", buf, readwrite);
1587 print_warn_msg(buf, is_kprobe);
1592 static int open_kprobe_events(
bool readwrite)
1594 return open_probe_events(
"tracing/kprobe_events", readwrite,
true);
1597 static int open_uprobe_events(
bool readwrite)
1599 return open_probe_events(
"tracing/uprobe_events", readwrite,
false);
1603 static struct strlist *get_probe_trace_command_rawlist(
int fd)
1613 fp = fdopen(dup(fd),
"r");
1642 place = synthesize_perf_probe_point(&pev->
point);
1646 ret = e_snprintf(buf, 128,
"%s:%s", pev->
group, pev->
event);
1650 printf(
" %-20s (on %s", buf, place);
1652 if (pev->
nargs > 0) {
1654 for (i = 0; i < pev->
nargs; i++) {
1667 static int __show_perf_probe_events(
int fd,
bool is_kprobe)
1675 memset(&tev, 0,
sizeof(tev));
1676 memset(&pev, 0,
sizeof(pev));
1678 rawlist = get_probe_trace_command_rawlist(fd);
1683 ret = parse_probe_trace_command(ent->
s, &tev);
1685 ret = convert_to_perf_probe_event(&tev, &pev,
1688 ret = show_perf_probe_event(&pev);
1691 clear_probe_trace_event(&tev);
1706 fd = open_kprobe_events(
false);
1711 ret = init_vmlinux();
1715 ret = __show_perf_probe_events(fd,
true);
1718 fd = open_uprobe_events(
false);
1720 ret = __show_perf_probe_events(fd,
false);
1728 static struct strlist *get_probe_trace_event_names(
int fd,
bool include_group)
1736 memset(&tev, 0,
sizeof(tev));
1737 rawlist = get_probe_trace_command_rawlist(fd);
1740 ret = parse_probe_trace_command(ent->
s, &tev);
1743 if (include_group) {
1744 ret = e_snprintf(buf, 128,
"%s:%s", tev.
group,
1750 clear_probe_trace_event(&tev);
1769 pr_debug(
"Failed to synthesize probe trace event.\n");
1773 pr_debug(
"Writing event: %s\n", buf);
1784 static int get_new_event_name(
char *buf,
size_t len,
const char *base,
1785 struct strlist *namelist,
bool allow_suffix)
1790 ret = e_snprintf(buf, len,
"%s", base);
1795 if (!strlist__has_entry(namelist, buf))
1798 if (!allow_suffix) {
1799 pr_warning(
"Error: event \"%s\" already exists. "
1800 "(Use -f to force duplicates.)\n", base);
1806 ret = e_snprintf(buf, len,
"%s_%d", base, i);
1811 if (!strlist__has_entry(namelist, buf))
1814 if (i == MAX_EVENT_INDEX) {
1815 pr_warning(
"Too many events are on the same function.\n");
1824 int ntevs,
bool allow_suffix)
1833 fd = open_uprobe_events(
true);
1835 fd = open_kprobe_events(
true);
1840 namelist = get_probe_trace_event_names(fd,
false);
1842 pr_debug(
"Failed to get current event list.\n");
1847 printf(
"Added new event%s\n", (ntevs > 1) ?
"s:" :
":");
1848 for (i = 0; i < ntevs; i++) {
1853 if (pev->
point.function)
1854 event = pev->
point.function;
1856 event = tev->
point.symbol;
1863 ret = get_new_event_name(buf, 64, event,
1864 namelist, allow_suffix);
1869 tev->
event = strdup(event);
1870 tev->
group = strdup(group);
1875 ret = write_probe_trace_event(fd, tev);
1886 show_perf_probe_event(pev);
1888 pev->
event = (
char *)event;
1889 pev->
group = (
char *)group;
1897 allow_suffix =
true;
1902 printf(
"\nYou can now use it in all perf tools, such as:\n\n");
1903 printf(
"\tperf record -e %s:%s -aR sleep 1\n\n", tev->
group,
1914 int max_tevs,
const char *target)
1921 ret = try_to_find_probe_trace_events(pev, tevs, max_tevs, target);
1931 tev->
point.symbol = strdup(pev->
point.function);
1938 tev->
point.module = strdup(target);
1957 for (i = 0; i < tev->
nargs; i++) {
1958 if (pev->
args[i].name) {
1959 tev->
args[
i].name = strdup(pev->
args[i].name);
1965 tev->
args[
i].value = strdup(pev->
args[i].var);
1970 if (pev->
args[i].type) {
1971 tev->
args[
i].type = strdup(pev->
args[i].type);
1984 sym = __find_kernel_function_by_name(tev->
point.symbol,
NULL);
1986 pr_warning(
"Kernel symbol \'%s\' not found.\n",
1991 pr_warning(
"Offset specified is greater than size of %s\n",
2000 clear_probe_trace_event(tev);
2013 int max_tevs,
const char *target,
bool force_add)
2026 ret = init_vmlinux();
2028 ret = init_user_exec();
2036 for (i = 0; i < npevs; i++) {
2037 pkgs[
i].
pev = &pevs[
i];
2039 ret = convert_to_probe_trace_events(pkgs[i].pev,
2049 for (i = 0; i < npevs; i++) {
2050 ret = __add_probe_trace_events(pkgs[i].pev, pkgs[i].tevs,
2051 pkgs[i].ntevs, force_add);
2057 for (i = 0; i < npevs; i++) {
2058 for (j = 0; j < pkgs[
i].
ntevs; j++)
2059 clear_probe_trace_event(&pkgs[i].tevs[j]);
2067 static int __del_trace_probe_event(
int fd,
struct str_node *ent)
2074 ret = e_snprintf(buf, 128,
"-:%s", ent->
s);
2078 p =
strchr(buf + 2,
':');
2080 pr_debug(
"Internal error: %s should have ':' but not.\n",
2087 pr_debug(
"Writing event: %s\n", buf);
2094 printf(
"Removed event: %s\n", ent->
s);
2101 static int del_trace_probe_event(
int fd,
const char *buf,
2110 ret = __del_trace_probe_event(fd, ent);
2118 ret = __del_trace_probe_event(fd, ent);
2129 int ret = -1, ufd = -1, kfd = -1;
2137 kfd = open_kprobe_events(
true);
2141 namelist = get_probe_trace_event_names(kfd,
true);
2142 ufd = open_uprobe_events(
true);
2145 unamelist = get_probe_trace_event_names(ufd,
true);
2147 if (namelist ==
NULL && unamelist ==
NULL)
2151 str = strdup(ent->
s);
2167 ret = e_snprintf(buf, 128,
"%s:%s", group, event);
2169 pr_err(
"Failed to copy event.");
2174 pr_debug(
"Group: %s, Event: %s\n", group, event);
2177 ret = del_trace_probe_event(kfd, buf, namelist);
2179 if (unamelist && ret != 0)
2180 ret = del_trace_probe_event(ufd, buf, unamelist);
2183 pr_info(
"Info: Event \"%s\" does not exist.\n", buf);
2203 static struct strfilter *available_func_filter;
2209 static int filter_available_functions(
struct map *map __maybe_unused,
2218 static int __show_available_funcs(
struct map *map)
2220 if (
map__load(map, filter_available_functions)) {
2221 pr_err(
"Failed to load map.\n");
2231 static int available_kernel_funcs(
const char *module)
2236 ret = init_vmlinux();
2240 map = kernel_get_module_map(module);
2242 pr_err(
"Failed to find %s map.\n", (module) ? :
"kernel");
2245 return __show_available_funcs(map);
2248 static int available_user_funcs(
const char *target)
2253 ret = init_user_exec();
2258 ret = __show_available_funcs(map);
2268 available_func_filter = _filter;
2271 return available_kernel_funcs(target);
2273 return available_user_funcs(target);
2284 struct map *map =
NULL;
2285 char *
function =
NULL, *name =
NULL;
2287 unsigned long long vaddr = 0;
2290 pr_warning(
"No function specified for uprobes");
2296 pr_warning(
"Failed to allocate memory by strdup.\n");
2301 name = realpath(exec,
NULL);
2303 pr_warning(
"Cannot find realpath for %s.\n", exec);
2308 pr_warning(
"Cannot find appropriate DSO for %s.\n", exec);
2312 if (
map__load(map, filter_available_functions)) {
2313 pr_err(
"Failed to load map.\n");
2319 pr_warning(
"Cannot find %s in DSO %s\n",
function, exec);
2329 pev->
event =
function;
2333 char *ptr1, *ptr2, *exec_copy;
2336 exec_copy = strdup(exec);
2343 ptr1 = strdup(basename(exec_copy));
2358 pr_warning(
"Failed to allocate memory by zalloc.\n");