• Home
  • Raw
  • Download

Lines Matching +full:end +full:- +full:point

1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * probe-event.c : perf-probe definition to probe_events format converter
23 #include "build-id.h"
36 #include "trace-event.h" /* For __maybe_unused */
37 #include "probe-event.h"
38 #include "probe-finder.h"
39 #include "probe-file.h"
69 ret = -E2BIG; in e_snprintf()
97 ret = -1; in init_probe_symbol_maps()
127 return kmap->ref_reloc_sym; in kernel_get_ref_reloc_sym()
139 if (reloc_sym && strcmp(name, reloc_sym->name) == 0) in kernel_get_symbol_address_by_name()
140 *addr = (!map__reloc(map) || reloc) ? reloc_sym->addr : in kernel_get_symbol_address_by_name()
141 reloc_sym->unrelocated_addr; in kernel_get_symbol_address_by_name()
145 return -ENOENT; in kernel_get_symbol_address_by_name()
146 *addr = map__unmap_ip(map, sym->start) - in kernel_get_symbol_address_by_name()
147 ((reloc) ? 0 : map__reloc(map)) - in kernel_get_symbol_address_by_name()
158 /* A file path -- this is an offline module */ in kernel_get_module_map()
170 struct dso *dso = map__dso(pos->map); in kernel_get_module_map()
171 const char *short_name = dso->short_name; in kernel_get_module_map()
172 u16 short_name_len = dso->short_name_len; in kernel_get_module_map()
175 short_name_len - 2) == 0 && in kernel_get_module_map()
176 module[short_name_len - 2] == '\0') { in kernel_get_module_map()
177 return map__get(pos->map); in kernel_get_module_map()
193 mutex_lock(&dso->lock); in get_target_map()
194 nsinfo__put(dso->nsinfo); in get_target_map()
195 dso->nsinfo = nsinfo__get(nsi); in get_target_map()
196 mutex_unlock(&dso->lock); in get_target_map()
212 return -ENOMEM; in convert_exec_to_group()
216 ret = -EINVAL; in convert_exec_to_group()
232 ret = *result ? 0 : -ENOMEM; in convert_exec_to_group()
241 zfree(&pp->file); in clear_perf_probe_point()
242 zfree(&pp->function); in clear_perf_probe_point()
243 zfree(&pp->lazy_line); in clear_perf_probe_point()
308 if (!data || !data->d_buf) in find_module_name()
317 * exposed to user-space. Offset of 'name' has remained same from long in find_module_name()
325 mod_name = strdup((char *)data->d_buf + name_offset); in find_module_name()
353 return -ENOENT; in kernel_get_module_dso()
358 if (!dso->has_build_id) in kernel_get_module_dso()
362 dso->load_errno = 0; in kernel_get_module_dso()
375 * symbol from map, we can translate the address back to the probe point.
386 int ret = -ENOENT; in find_alternative_probe_point()
389 /* This can work only for function-name based one */ in find_alternative_probe_point()
390 if (!pp->function || pp->file) in find_alternative_probe_point()
391 return -ENOTSUP; in find_alternative_probe_point()
395 return -EINVAL; in find_alternative_probe_point()
398 map__for_each_symbol_by_name(map, pp->function, sym, idx) { in find_alternative_probe_point()
400 address = sym->start; in find_alternative_probe_point()
401 if (sym->type == STT_GNU_IFUNC) in find_alternative_probe_point()
404 pp->function); in find_alternative_probe_point()
406 address = map__unmap_ip(map, sym->start) - map__reloc(map); in find_alternative_probe_point()
410 ret = -ENOENT; in find_alternative_probe_point()
414 pp->function, address); in find_alternative_probe_point()
418 ret = (!ret) ? -ENOENT : ret; in find_alternative_probe_point()
420 result->offset += pp->offset; in find_alternative_probe_point()
421 result->line += pp->line; in find_alternative_probe_point()
422 result->retprobe = pp->retprobe; in find_alternative_probe_point()
438 memcpy(tmp, &pev->point, sizeof(*tmp)); in get_alternative_probe_event()
439 memset(&pev->point, 0, sizeof(pev->point)); in get_alternative_probe_event()
440 ret = find_alternative_probe_point(dinfo, tmp, &pev->point, pev->target, in get_alternative_probe_event()
441 pev->nsi, pev->uprobes); in get_alternative_probe_event()
443 memcpy(&pev->point, tmp, sizeof(*tmp)); in get_alternative_probe_event()
452 struct perf_probe_point pp = { .function = lr->function, in get_alternative_line_range()
453 .file = lr->file, in get_alternative_line_range()
454 .line = lr->start }; in get_alternative_line_range()
460 if (lr->end != INT_MAX) in get_alternative_line_range()
461 len = lr->end - lr->start; in get_alternative_line_range()
465 lr->function = result.function; in get_alternative_line_range()
466 lr->file = result.file; in get_alternative_line_range()
467 lr->start = result.line; in get_alternative_line_range()
468 if (lr->end != INT_MAX) in get_alternative_line_range()
469 lr->end = lr->start + len; in get_alternative_line_range()
489 build_id__sprintf(&dso->bid, sbuild_id); in open_from_debuginfod()
532 if (!dso || dso->load_errno == 0) { in open_debuginfo()
533 if (!str_error_r(-err, reason, STRERR_BUFSIZE)) in open_debuginfo()
549 path = dso->long_name; in open_debuginfo()
558 pr_warning("Rebuild with -g, "); in open_debuginfo()
610 int fd, ret = -ENOENT; in get_text_start_address()
617 return -errno; in get_text_start_address()
621 ret = -EINVAL; in get_text_start_address()
631 *address = shdr.sh_addr - shdr.sh_offset; in get_text_start_address()
642 * Convert trace point to probe point with debuginfo
650 u64 addr = tp->address; in find_perf_probe_point_from_dwarf()
651 int ret = -ENOENT; in find_perf_probe_point_from_dwarf()
656 ret = -EINVAL; in find_perf_probe_point_from_dwarf()
659 ret = get_text_start_address(tp->module, &stext, NULL); in find_perf_probe_point_from_dwarf()
663 } else if (tp->symbol) { in find_perf_probe_point_from_dwarf()
665 ret = kernel_get_symbol_address_by_name(tp->symbol, &addr, in find_perf_probe_point_from_dwarf()
666 false, !!tp->module); in find_perf_probe_point_from_dwarf()
669 addr += tp->offset; in find_perf_probe_point_from_dwarf()
673 tp->module ? : "kernel"); in find_perf_probe_point_from_dwarf()
675 dinfo = debuginfo_cache__open(tp->module, verbose <= 0); in find_perf_probe_point_from_dwarf()
679 ret = -ENOENT; in find_perf_probe_point_from_dwarf()
682 pp->retprobe = tp->retprobe; in find_perf_probe_point_from_dwarf()
687 return ret ? : -ENOENT; in find_perf_probe_point_from_dwarf()
695 u64 addr = tp->address - offs; in post_process_probe_trace_point()
703 return (symbol_conf.ignore_vmlinux_buildid) ? 0 : -ENOENT; in post_process_probe_trace_point()
706 if (strcmp(sym->name, tp->symbol)) { in post_process_probe_trace_point()
708 if (!tp->realname) in post_process_probe_trace_point()
709 tp->realname = tp->symbol; in post_process_probe_trace_point()
711 free(tp->symbol); in post_process_probe_trace_point()
712 tp->symbol = strdup(sym->name); in post_process_probe_trace_point()
713 if (!tp->symbol) in post_process_probe_trace_point()
714 return -ENOMEM; in post_process_probe_trace_point()
716 tp->offset = addr - sym->start; in post_process_probe_trace_point()
717 tp->address -= offs; in post_process_probe_trace_point()
723 * Rename DWARF symbols to ELF symbols -- gcc sometimes optimizes functions
742 return -EINVAL; in post_process_offline_probe_trace_events()
746 ret = post_process_probe_trace_point(&tevs[i].point, in post_process_offline_probe_trace_events()
771 /* point.address is the address of point.symbol + point.offset */ in add_exec_to_probe_trace_events()
772 tevs[i].point.address -= stext; in add_exec_to_probe_trace_events()
773 tevs[i].point.module = strdup(exec); in add_exec_to_probe_trace_events()
774 if (!tevs[i].point.module) { in add_exec_to_probe_trace_events()
775 ret = -ENOMEM; in add_exec_to_probe_trace_events()
800 return -EINVAL; in post_process_module_probe_trace_events()
805 ret = post_process_probe_trace_point(&tevs[i].point, in post_process_module_probe_trace_events()
809 tevs[i].point.module = in post_process_module_probe_trace_events()
811 if (!tevs[i].point.module) { in post_process_module_probe_trace_events()
812 ret = -ENOMEM; in post_process_module_probe_trace_events()
843 return -EINVAL; in post_process_kernel_probe_trace_events()
847 if (!tevs[i].point.address) in post_process_kernel_probe_trace_events()
849 if (tevs[i].point.retprobe && !kretprobe_offset_is_supported()) in post_process_kernel_probe_trace_events()
856 if (kprobe_warn_out_range(tevs[i].point.symbol, in post_process_kernel_probe_trace_events()
857 map__objdump_2mem(map, tevs[i].point.address))) { in post_process_kernel_probe_trace_events()
861 tmp = strdup(reloc_sym->name); in post_process_kernel_probe_trace_events()
863 return -ENOMEM; in post_process_kernel_probe_trace_events()
866 if (!tevs[i].point.realname) in post_process_kernel_probe_trace_events()
867 tevs[i].point.realname = tevs[i].point.symbol; in post_process_kernel_probe_trace_events()
869 free(tevs[i].point.symbol); in post_process_kernel_probe_trace_events()
870 tevs[i].point.symbol = tmp; in post_process_kernel_probe_trace_events()
871 tevs[i].point.offset = tevs[i].point.address - in post_process_kernel_probe_trace_events()
872 (map__reloc(map) ? reloc_sym->unrelocated_addr : in post_process_kernel_probe_trace_events()
873 reloc_sym->addr); in post_process_kernel_probe_trace_events()
894 pev->nsi); in post_process_probe_trace_events()
919 * compiled by gcc with -fpatchable-function-entry option enabled. The in try_to_find_probe_trace_events()
924 if (pev->point.retprobe) in try_to_find_probe_trace_events()
927 dinfo = open_debuginfo(pev->target, pev->nsi, !need_dwarf); in try_to_find_probe_trace_events()
930 return -ENODATA; in try_to_find_probe_trace_events()
935 pr_debug("Try to find probe point from debuginfo.\n"); in try_to_find_probe_trace_events()
947 clear_perf_probe_point(&pev->point); in try_to_find_probe_trace_events()
948 memcpy(&pev->point, &tmp, sizeof(tmp)); in try_to_find_probe_trace_events()
955 pev->target, pev->uprobes, dinfo); in try_to_find_probe_trace_events()
966 if (ntevs == 0) { /* No error but failed to find probe point. */ in try_to_find_probe_trace_events()
967 char *probe_point = synthesize_perf_probe_point(&pev->point); in try_to_find_probe_trace_events()
968 pr_warning("Probe point '%s' not found.\n", probe_point); in try_to_find_probe_trace_events()
970 return -ENODEV; in try_to_find_probe_trace_events()
974 if (ntevs == -EBADF) in try_to_find_probe_trace_events()
975 pr_warning("Warning: No dwarf info found in the vmlinux - " in try_to_find_probe_trace_events()
1012 return -1; in __show_one_line()
1022 rv = -1; in _show_one_line()
1033 * Show line-range always requires debuginfo to find source file and
1052 return -ENOENT; in __show_line_range()
1060 if (dinfo->build_id) { in __show_line_range()
1061 build_id__init(&bid, dinfo->build_id, BUILD_ID_SIZE); in __show_line_range()
1065 if (ret == 0 || ret == -ENOENT) { in __show_line_range()
1067 return -ENOENT; in __show_line_range()
1074 tmp = lr->path; in __show_line_range()
1075 ret = find_source_path(tmp, sbuild_id, lr->comp_dir, &lr->path); in __show_line_range()
1078 if (tmp != lr->path) in __show_line_range()
1088 if (lr->function) in __show_line_range()
1089 fprintf(stdout, "<%s@%s:%d>\n", lr->function, lr->path, in __show_line_range()
1090 lr->start - lr->offset); in __show_line_range()
1092 fprintf(stdout, "<%s:%d>\n", lr->path, lr->start); in __show_line_range()
1094 fp = fopen(lr->path, "r"); in __show_line_range()
1096 pr_warning("Failed to open %s: %s\n", lr->path, in __show_line_range()
1098 return -errno; in __show_line_range()
1101 while (l < lr->start) { in __show_line_range()
1104 goto end; in __show_line_range()
1107 intlist__for_each_entry(ln, lr->line_list) { in __show_line_range()
1108 for (; ln->i > (unsigned long)l; l++) { in __show_line_range()
1109 ret = show_one_line(fp, l - lr->offset); in __show_line_range()
1111 goto end; in __show_line_range()
1113 ret = show_one_line_with_num(fp, l++ - lr->offset); in __show_line_range()
1115 goto end; in __show_line_range()
1118 if (lr->end == INT_MAX) in __show_line_range()
1119 lr->end = l + NR_ADDITIONAL_LINES; in __show_line_range()
1120 while (l <= lr->end) { in __show_line_range()
1121 ret = show_one_line_or_eof(fp, l++ - lr->offset); in __show_line_range()
1125 end: in __show_line_range()
1158 buf = synthesize_perf_probe_point(&pev->point); in show_available_vars_at()
1160 return -EINVAL; in show_available_vars_at()
1174 if (ret == 0 || ret == -ENOENT) { in show_available_vars_at()
1176 ret = -ENOENT; in show_available_vars_at()
1179 goto end; in show_available_vars_at()
1187 * A probe point might be converted to in show_available_vars_at()
1190 fprintf(stdout, "\t@<%s+%lu>\n", vl->point.symbol, in show_available_vars_at()
1191 vl->point.offset); in show_available_vars_at()
1192 zfree(&vl->point.symbol); in show_available_vars_at()
1194 if (vl->vars) { in show_available_vars_at()
1195 strlist__for_each_entry(node, vl->vars) { in show_available_vars_at()
1196 var = strchr(node->s, '\t') + 1; in show_available_vars_at()
1198 fprintf(stdout, "\t\t%s\n", node->s); in show_available_vars_at()
1202 strlist__delete(vl->vars); in show_available_vars_at()
1208 end: in show_available_vars_at()
1213 /* Show available variables on given probe point */
1220 ret = init_probe_symbol_maps(pevs->uprobes); in show_available_vars()
1224 dinfo = open_debuginfo(pevs->target, pevs->nsi, false); in show_available_vars()
1226 ret = -ENOENT; in show_available_vars()
1252 return -ENOSYS; in find_perf_probe_point_from_dwarf()
1259 pr_warning("Debuginfo-analysis is not supported.\n"); in try_to_find_probe_trace_events()
1260 return -ENOSYS; in try_to_find_probe_trace_events()
1271 pr_warning("Debuginfo-analysis is not supported.\n"); in show_line_range()
1272 return -ENOSYS; in show_line_range()
1279 pr_warning("Debuginfo-analysis is not supported.\n"); in show_available_vars()
1280 return -ENOSYS; in show_available_vars()
1286 zfree(&lr->function); in line_range__clear()
1287 zfree(&lr->file); in line_range__clear()
1288 zfree(&lr->path); in line_range__clear()
1289 zfree(&lr->comp_dir); in line_range__clear()
1290 intlist__delete(lr->line_list); in line_range__clear()
1296 lr->line_list = intlist__new(NULL); in line_range__init()
1297 if (!lr->line_list) in line_range__init()
1298 return -ENOMEM; in line_range__init()
1311 return -EINVAL; in parse_line_num()
1332 * SRC[:SLN[+NUM|-ELN]]
1333 * FNC[@SRC][:SLN[+NUM|-ELN]]
1341 return -ENOMEM; in parse_line_range_desc()
1343 lr->start = 0; in parse_line_range_desc()
1344 lr->end = INT_MAX; in parse_line_range_desc()
1350 err = parse_line_num(&range, &lr->start, "start line"); in parse_line_range_desc()
1354 if (*range == '+' || *range == '-') { in parse_line_range_desc()
1357 err = parse_line_num(&range, &lr->end, "end line"); in parse_line_range_desc()
1362 lr->end += lr->start; in parse_line_range_desc()
1366 * end of line should be equal to in parse_line_range_desc()
1369 lr->end--; in parse_line_range_desc()
1373 pr_debug("Line range is %d to %d\n", lr->start, lr->end); in parse_line_range_desc()
1375 err = -EINVAL; in parse_line_range_desc()
1376 if (lr->start > lr->end) { in parse_line_range_desc()
1378 " than end line.\n"); in parse_line_range_desc()
1390 lr->file = strdup(++file); in parse_line_range_desc()
1391 if (lr->file == NULL) { in parse_line_range_desc()
1392 err = -ENOMEM; in parse_line_range_desc()
1395 lr->function = name; in parse_line_range_desc()
1397 lr->file = name; in parse_line_range_desc()
1399 lr->function = name; in parse_line_range_desc()
1402 err = -EINVAL; in parse_line_range_desc()
1419 if (!pev->sdt && !is_c_func_name(*arg)) in parse_perf_probe_event_name()
1421 pev->group = strdup_esc(*arg); in parse_perf_probe_event_name()
1422 if (!pev->group) in parse_perf_probe_event_name()
1423 return -ENOMEM; in parse_perf_probe_event_name()
1426 pev->group = NULL; in parse_perf_probe_event_name()
1428 pev->event = strdup_esc(*arg); in parse_perf_probe_event_name()
1429 if (pev->event == NULL) in parse_perf_probe_event_name()
1430 return -ENOMEM; in parse_perf_probe_event_name()
1432 if (!pev->sdt && !is_c_func_name(pev->event)) { in parse_perf_probe_event_name()
1433 zfree(&pev->event); in parse_perf_probe_event_name()
1435 zfree(&pev->group); in parse_perf_probe_event_name()
1436 semantic_error("%s is bad for event name -it must " in parse_perf_probe_event_name()
1437 "follow C symbol-naming rule.\n", *arg); in parse_perf_probe_event_name()
1438 return -EINVAL; in parse_perf_probe_event_name()
1446 struct perf_probe_point *pp = &pev->point; in parse_perf_probe_point()
1459 return -EINVAL; in parse_perf_probe_point()
1462 pev->sdt = true; in parse_perf_probe_point()
1468 if (pev->sdt) { in parse_perf_probe_point()
1473 return -EINVAL; in parse_perf_probe_point()
1478 pev->target = build_id_cache__origname(tmp); in parse_perf_probe_point()
1481 pev->target = strdup_esc(ptr + 1); in parse_perf_probe_point()
1482 if (!pev->target) in parse_perf_probe_point()
1483 return -ENOMEM; in parse_perf_probe_point()
1488 if (asprintf(&pev->point.function, "%%%s", pev->event) < 0) in parse_perf_probe_point()
1489 ret = -errno; in parse_perf_probe_point()
1509 * - it does not include any of "+@%", in parse_perf_probe_point()
1510 * - it includes one of ":;", and in parse_perf_probe_point()
1511 * - it has a period '.' in the name. in parse_perf_probe_point()
1518 if (ptr && memchr(arg, '.', ptr - arg)) in parse_perf_probe_point()
1533 return -ENOMEM; in parse_perf_probe_point()
1537 pp->file = tmp; in parse_perf_probe_point()
1539 pp->function = tmp; in parse_perf_probe_point()
1542 * Keep pp->function even if this is absolute address, in parse_perf_probe_point()
1551 pp->abs_address = strtoull(pp->function, &tmp, 0); in parse_perf_probe_point()
1554 return -EINVAL; in parse_perf_probe_point()
1564 pp->lazy_line = strdup(arg); /* let leave escapes */ in parse_perf_probe_point()
1565 if (pp->lazy_line == NULL) in parse_perf_probe_point()
1566 return -ENOMEM; in parse_perf_probe_point()
1576 pp->line = strtoul(arg, &tmp, 0); in parse_perf_probe_point()
1578 semantic_error("There is non-digit char" in parse_perf_probe_point()
1580 return -EINVAL; in parse_perf_probe_point()
1584 pp->offset = strtoul(arg, &tmp, 0); in parse_perf_probe_point()
1586 semantic_error("There is non-digit character" in parse_perf_probe_point()
1588 return -EINVAL; in parse_perf_probe_point()
1592 if (pp->file) { in parse_perf_probe_point()
1594 return -EINVAL; in parse_perf_probe_point()
1596 pp->file = strdup_esc(arg); in parse_perf_probe_point()
1597 if (pp->file == NULL) in parse_perf_probe_point()
1598 return -ENOMEM; in parse_perf_probe_point()
1602 pp->retprobe = 1; in parse_perf_probe_point()
1605 return -ENOTSUP; in parse_perf_probe_point()
1611 return -ENOTSUP; in parse_perf_probe_point()
1617 if (pp->lazy_line && pp->line) { in parse_perf_probe_point()
1620 return -EINVAL; in parse_perf_probe_point()
1623 if (pp->lazy_line && pp->offset) { in parse_perf_probe_point()
1625 return -EINVAL; in parse_perf_probe_point()
1628 if (pp->line && pp->offset) { in parse_perf_probe_point()
1630 return -EINVAL; in parse_perf_probe_point()
1633 if (!pp->line && !pp->lazy_line && pp->file && !pp->function) { in parse_perf_probe_point()
1636 return -EINVAL; in parse_perf_probe_point()
1639 if (pp->offset && !pp->function) { in parse_perf_probe_point()
1641 return -EINVAL; in parse_perf_probe_point()
1644 if ((pp->offset || pp->line || pp->lazy_line) && pp->retprobe) { in parse_perf_probe_point()
1647 return -EINVAL; in parse_perf_probe_point()
1651 pp->function, pp->file, pp->line, pp->offset, pp->retprobe, in parse_perf_probe_point()
1652 pp->lazy_line); in parse_perf_probe_point()
1656 /* Parse perf-probe event argument */
1666 arg->name = strndup(str, tmp - str); in parse_perf_probe_arg()
1667 if (arg->name == NULL) in parse_perf_probe_arg()
1668 return -ENOMEM; in parse_perf_probe_arg()
1669 pr_debug("name:%s ", arg->name); in parse_perf_probe_arg()
1677 return -EINVAL; in parse_perf_probe_arg()
1680 arg->user_access = true; in parse_perf_probe_arg()
1687 arg->type = strdup(tmp + 1); in parse_perf_probe_arg()
1688 if (arg->type == NULL) in parse_perf_probe_arg()
1689 return -ENOMEM; in parse_perf_probe_arg()
1690 pr_debug("type:%s ", arg->type); in parse_perf_probe_arg()
1693 tmp = strpbrk(str, "-.["); in parse_perf_probe_arg()
1696 arg->var = strdup(str); in parse_perf_probe_arg()
1697 if (arg->var == NULL) in parse_perf_probe_arg()
1698 return -ENOMEM; in parse_perf_probe_arg()
1699 pr_debug("%s\n", arg->var); in parse_perf_probe_arg()
1704 arg->var = strndup(str, tmp - str); in parse_perf_probe_arg()
1705 if (arg->var == NULL) in parse_perf_probe_arg()
1706 return -ENOMEM; in parse_perf_probe_arg()
1707 goodname = arg->var; in parse_perf_probe_arg()
1708 pr_debug("%s, ", arg->var); in parse_perf_probe_arg()
1709 fieldp = &arg->field; in parse_perf_probe_arg()
1714 return -ENOMEM; in parse_perf_probe_arg()
1717 (*fieldp)->index = strtol(str + 1, &tmp, 0); in parse_perf_probe_arg()
1718 (*fieldp)->ref = true; in parse_perf_probe_arg()
1722 return -EINVAL; in parse_perf_probe_arg()
1730 (*fieldp)->ref = false; in parse_perf_probe_arg()
1733 (*fieldp)->ref = true; in parse_perf_probe_arg()
1737 return -EINVAL; in parse_perf_probe_arg()
1739 tmp = strpbrk(str, "-.["); in parse_perf_probe_arg()
1742 (*fieldp)->name = strndup(str, tmp - str); in parse_perf_probe_arg()
1743 if ((*fieldp)->name == NULL) in parse_perf_probe_arg()
1744 return -ENOMEM; in parse_perf_probe_arg()
1746 goodname = (*fieldp)->name; in parse_perf_probe_arg()
1747 pr_debug("%s(%d), ", (*fieldp)->name, (*fieldp)->ref); in parse_perf_probe_arg()
1748 fieldp = &(*fieldp)->next; in parse_perf_probe_arg()
1751 (*fieldp)->name = strdup(str); in parse_perf_probe_arg()
1752 if ((*fieldp)->name == NULL) in parse_perf_probe_arg()
1753 return -ENOMEM; in parse_perf_probe_arg()
1755 goodname = (*fieldp)->name; in parse_perf_probe_arg()
1756 pr_debug("%s(%d)\n", (*fieldp)->name, (*fieldp)->ref); in parse_perf_probe_arg()
1759 if (!arg->name) { in parse_perf_probe_arg()
1760 arg->name = strdup(goodname); in parse_perf_probe_arg()
1761 if (arg->name == NULL) in parse_perf_probe_arg()
1762 return -ENOMEM; in parse_perf_probe_arg()
1767 /* Parse perf-probe event command */
1776 return -ENOMEM; in parse_perf_probe_command()
1778 if (argc - 1 > MAX_PROBE_ARGS) { in parse_perf_probe_command()
1779 semantic_error("Too many probe arguments (%d).\n", argc - 1); in parse_perf_probe_command()
1780 ret = -ERANGE; in parse_perf_probe_command()
1783 /* Parse probe point */ in parse_perf_probe_command()
1789 if (!pev->event && pev->point.function && pev->point.line in parse_perf_probe_command()
1790 && !pev->point.lazy_line && !pev->point.offset) { in parse_perf_probe_command()
1791 if (asprintf(&pev->event, "%s_L%d", pev->point.function, in parse_perf_probe_command()
1792 pev->point.line) < 0) { in parse_perf_probe_command()
1793 ret = -ENOMEM; in parse_perf_probe_command()
1799 pev->nargs = argc - 1; in parse_perf_probe_command()
1800 pev->args = zalloc(sizeof(struct perf_probe_arg) * pev->nargs); in parse_perf_probe_command()
1801 if (pev->args == NULL) { in parse_perf_probe_command()
1802 ret = -ENOMEM; in parse_perf_probe_command()
1805 for (i = 0; i < pev->nargs && ret >= 0; i++) { in parse_perf_probe_command()
1806 ret = parse_perf_probe_arg(argv[i + 1], &pev->args[i]); in parse_perf_probe_command()
1808 is_c_varname(pev->args[i].var) && pev->point.retprobe) { in parse_perf_probe_command()
1811 ret = -EINVAL; in parse_perf_probe_command()
1825 for (i = 0; i < pev->nargs; i++) in perf_probe_with_var()
1826 if (is_c_varname(pev->args[i].var) || in perf_probe_with_var()
1827 !strcmp(pev->args[i].var, PROBE_ARG_PARAMS) || in perf_probe_with_var()
1828 !strcmp(pev->args[i].var, PROBE_ARG_VARS)) in perf_probe_with_var()
1836 if (pev->point.file || pev->point.line || pev->point.lazy_line) in perf_probe_event_need_dwarf()
1848 struct probe_trace_point *tp = &tev->point; in parse_probe_trace_command()
1859 return -ENOMEM; in parse_probe_trace_command()
1863 ret = -ERANGE; in parse_probe_trace_command()
1870 ret = -ENOMEM; in parse_probe_trace_command()
1878 ret = -EINVAL; in parse_probe_trace_command()
1882 tev->group = strdup(fmt2_str); in parse_probe_trace_command()
1883 tev->event = strdup(fmt3_str); in parse_probe_trace_command()
1884 if (tev->group == NULL || tev->event == NULL) { in parse_probe_trace_command()
1885 ret = -ENOMEM; in parse_probe_trace_command()
1888 pr_debug("Group:%s Event:%s probe:%c\n", tev->group, tev->event, pr); in parse_probe_trace_command()
1890 tp->retprobe = (pr == 'r'); in parse_probe_trace_command()
1895 tp->module = strndup(argv[1], p - argv[1]); in parse_probe_trace_command()
1896 if (!tp->module) { in parse_probe_trace_command()
1897 ret = -ENOMEM; in parse_probe_trace_command()
1900 tev->uprobes = (tp->module[0] == '/'); in parse_probe_trace_command()
1910 * p:probe_libc/abs_0 /lib/libc-2.18.so:0x (null) arg1=%ax in parse_probe_trace_command()
1916 ret = -EINVAL; in parse_probe_trace_command()
1919 tp->address = 0; in parse_probe_trace_command()
1926 argc -= 1; in parse_probe_trace_command()
1928 tp->address = strtoull(fmt1_str, NULL, 0); in parse_probe_trace_command()
1930 /* Only the symbol-based probe has offset */ in parse_probe_trace_command()
1931 tp->symbol = strdup(fmt1_str); in parse_probe_trace_command()
1932 if (tp->symbol == NULL) { in parse_probe_trace_command()
1933 ret = -ENOMEM; in parse_probe_trace_command()
1938 tp->offset = 0; in parse_probe_trace_command()
1940 tp->offset = strtoul(fmt2_str, NULL, 10); in parse_probe_trace_command()
1943 if (tev->uprobes) { in parse_probe_trace_command()
1946 tp->ref_ctr_offset = strtoul(fmt2_str + 1, NULL, 0); in parse_probe_trace_command()
1949 tev->nargs = argc - 2; in parse_probe_trace_command()
1950 tev->args = zalloc(sizeof(struct probe_trace_arg) * tev->nargs); in parse_probe_trace_command()
1951 if (tev->args == NULL) { in parse_probe_trace_command()
1952 ret = -ENOMEM; in parse_probe_trace_command()
1955 for (i = 0; i < tev->nargs; i++) { in parse_probe_trace_command()
1961 tev->args[i].name = strdup(argv[i + 2]); in parse_probe_trace_command()
1963 tev->args[i].value = strdup(p); in parse_probe_trace_command()
1964 if (tev->args[i].name == NULL || tev->args[i].value == NULL) { in parse_probe_trace_command()
1965 ret = -ENOMEM; in parse_probe_trace_command()
1979 struct perf_probe_arg_field *field = pa->field; in synthesize_perf_probe_arg()
1987 if (pa->name && pa->var) in synthesize_perf_probe_arg()
1988 err = strbuf_addf(&buf, "%s=%s", pa->name, pa->var); in synthesize_perf_probe_arg()
1990 err = strbuf_addstr(&buf, pa->name ?: pa->var); in synthesize_perf_probe_arg()
1995 if (field->name[0] == '[') in synthesize_perf_probe_arg()
1996 err = strbuf_addstr(&buf, field->name); in synthesize_perf_probe_arg()
1998 err = strbuf_addf(&buf, "%s%s", field->ref ? "->" : ".", in synthesize_perf_probe_arg()
1999 field->name); in synthesize_perf_probe_arg()
2000 field = field->next; in synthesize_perf_probe_arg()
2005 if (pa->type) in synthesize_perf_probe_arg()
2006 if (strbuf_addf(&buf, ":%s", pa->type) < 0) in synthesize_perf_probe_arg()
2015 /* Compose only probe point (not argument) */
2025 if (pp->function) { in synthesize_perf_probe_point()
2026 if (strbuf_addstr(&buf, pp->function) < 0) in synthesize_perf_probe_point()
2028 if (pp->offset) in synthesize_perf_probe_point()
2029 err = strbuf_addf(&buf, "+%lu", pp->offset); in synthesize_perf_probe_point()
2030 else if (pp->line) in synthesize_perf_probe_point()
2031 err = strbuf_addf(&buf, ":%d", pp->line); in synthesize_perf_probe_point()
2032 else if (pp->retprobe) in synthesize_perf_probe_point()
2037 if (pp->file) { in synthesize_perf_probe_point()
2038 tmp = pp->file; in synthesize_perf_probe_point()
2041 tmp = strchr(pp->file + len - 30, '/'); in synthesize_perf_probe_point()
2042 tmp = tmp ? tmp + 1 : pp->file + len - 30; in synthesize_perf_probe_point()
2045 if (!err && !pp->function && pp->line) in synthesize_perf_probe_point()
2046 err = strbuf_addf(&buf, ":%d", pp->line); in synthesize_perf_probe_point()
2063 if (pev->event) in synthesize_perf_probe_command()
2064 if (strbuf_addf(&buf, "%s:%s=", pev->group ?: PERFPROBE_GROUP, in synthesize_perf_probe_command()
2065 pev->event) < 0) in synthesize_perf_probe_command()
2068 tmp = synthesize_perf_probe_point(&pev->point); in synthesize_perf_probe_command()
2075 for (i = 0; i < pev->nargs; i++) { in synthesize_perf_probe_command()
2076 tmp = synthesize_perf_probe_arg(pev->args + i); in synthesize_perf_probe_command()
2094 if (ref->next) { in __synthesize_probe_trace_arg_ref()
2095 depth = __synthesize_probe_trace_arg_ref(ref->next, buf, in __synthesize_probe_trace_arg_ref()
2100 if (ref->user_access) in __synthesize_probe_trace_arg_ref()
2101 err = strbuf_addf(buf, "%s%ld(", "+u", ref->offset); in __synthesize_probe_trace_arg_ref()
2103 err = strbuf_addf(buf, "%+ld(", ref->offset); in __synthesize_probe_trace_arg_ref()
2110 struct probe_trace_arg_ref *ref = arg->ref; in synthesize_probe_trace_arg()
2114 if (arg->name) in synthesize_probe_trace_arg()
2115 err = strbuf_addf(buf, " %s=", arg->name); in synthesize_probe_trace_arg()
2122 if (arg->value[0] == '@' && arg->ref) in synthesize_probe_trace_arg()
2123 ref = ref->next; in synthesize_probe_trace_arg()
2133 if (arg->value[0] == '@' && arg->ref) in synthesize_probe_trace_arg()
2134 err = strbuf_addf(buf, "%s%+ld", arg->value, arg->ref->offset); in synthesize_probe_trace_arg()
2136 err = strbuf_addstr(buf, arg->value); in synthesize_probe_trace_arg()
2139 while (!err && depth--) in synthesize_probe_trace_arg()
2143 if (!err && arg->type) in synthesize_probe_trace_arg()
2144 err = strbuf_addf(buf, ":%s", arg->type); in synthesize_probe_trace_arg()
2154 for (i = 0; i < tev->nargs && ret >= 0; i++) in synthesize_probe_trace_args()
2155 ret = synthesize_probe_trace_arg(&tev->args[i], buf); in synthesize_probe_trace_args()
2165 /* Uprobes must have tp->module */ in synthesize_uprobe_trace_def()
2166 if (!tp->module) in synthesize_uprobe_trace_def()
2167 return -EINVAL; in synthesize_uprobe_trace_def()
2169 * If tp->address == 0, then this point must be a in synthesize_uprobe_trace_def()
2172 * tp->symbol to "0x0". in synthesize_uprobe_trace_def()
2174 if (!tp->address && (!tp->symbol || strcmp(tp->symbol, "0x0"))) in synthesize_uprobe_trace_def()
2175 return -EINVAL; in synthesize_uprobe_trace_def()
2177 /* Use the tp->address for uprobes */ in synthesize_uprobe_trace_def()
2178 err = strbuf_addf(buf, "%s:0x%" PRIx64, tp->module, tp->address); in synthesize_uprobe_trace_def()
2180 if (err >= 0 && tp->ref_ctr_offset) { in synthesize_uprobe_trace_def()
2182 return -EINVAL; in synthesize_uprobe_trace_def()
2183 err = strbuf_addf(buf, "(0x%lx)", tp->ref_ctr_offset); in synthesize_uprobe_trace_def()
2191 if (!strncmp(tp->symbol, "0x", 2)) { in synthesize_kprobe_trace_def()
2193 return strbuf_addf(buf, "%s%s0x%" PRIx64, tp->module ?: "", in synthesize_kprobe_trace_def()
2194 tp->module ? ":" : "", tp->address); in synthesize_kprobe_trace_def()
2196 return strbuf_addf(buf, "%s%s%s+%lu", tp->module ?: "", in synthesize_kprobe_trace_def()
2197 tp->module ? ":" : "", tp->symbol, tp->offset); in synthesize_kprobe_trace_def()
2203 struct probe_trace_point *tp = &tev->point; in synthesize_probe_trace_command()
2211 if (strbuf_addf(&buf, "%c:%s/%s ", tp->retprobe ? 'r' : 'p', in synthesize_probe_trace_command()
2212 tev->group, tev->event) < 0) in synthesize_probe_trace_command()
2215 if (tev->uprobes) in synthesize_probe_trace_command()
2236 u64 addr = tp->address; in find_perf_probe_point_from_map()
2237 int ret = -ENOENT; in find_perf_probe_point_from_map()
2240 map = dso__new_map(tp->module); in find_perf_probe_point_from_map()
2245 if (tp->symbol && !addr) { in find_perf_probe_point_from_map()
2246 if (kernel_get_symbol_address_by_name(tp->symbol, in find_perf_probe_point_from_map()
2251 addr += tp->offset; in find_perf_probe_point_from_map()
2259 pp->retprobe = tp->retprobe; in find_perf_probe_point_from_map()
2260 pp->offset = addr - map__unmap_ip(map, sym->start); in find_perf_probe_point_from_map()
2261 pp->function = strdup(sym->name); in find_perf_probe_point_from_map()
2262 ret = pp->function ? 0 : -ENOMEM; in find_perf_probe_point_from_map()
2286 pr_debug("Failed to find probe point from both of dwarf and map.\n"); in convert_to_perf_probe_point()
2288 if (tp->symbol) { in convert_to_perf_probe_point()
2289 pp->function = strdup(tp->symbol); in convert_to_perf_probe_point()
2290 pp->offset = tp->offset; in convert_to_perf_probe_point()
2292 ret = e_snprintf(buf, 128, "0x%" PRIx64, tp->address); in convert_to_perf_probe_point()
2295 pp->function = strdup(buf); in convert_to_perf_probe_point()
2296 pp->offset = 0; in convert_to_perf_probe_point()
2298 if (pp->function == NULL) in convert_to_perf_probe_point()
2299 return -ENOMEM; in convert_to_perf_probe_point()
2301 pp->retprobe = tp->retprobe; in convert_to_perf_probe_point()
2313 pev->event = strdup(tev->event); in convert_to_perf_probe_event()
2314 pev->group = strdup(tev->group); in convert_to_perf_probe_event()
2315 if (pev->event == NULL || pev->group == NULL) in convert_to_perf_probe_event()
2316 return -ENOMEM; in convert_to_perf_probe_event()
2319 ret = convert_to_perf_probe_point(&tev->point, &pev->point, is_kprobe); in convert_to_perf_probe_event()
2324 pev->nargs = tev->nargs; in convert_to_perf_probe_event()
2325 pev->args = zalloc(sizeof(struct perf_probe_arg) * pev->nargs); in convert_to_perf_probe_event()
2326 if (pev->args == NULL) in convert_to_perf_probe_event()
2327 return -ENOMEM; in convert_to_perf_probe_event()
2328 for (i = 0; i < tev->nargs && ret >= 0; i++) { in convert_to_perf_probe_event()
2329 if (tev->args[i].name) in convert_to_perf_probe_event()
2330 pev->args[i].name = strdup(tev->args[i].name); in convert_to_perf_probe_event()
2334 ret = synthesize_probe_trace_arg(&tev->args[i], &buf); in convert_to_perf_probe_event()
2335 pev->args[i].name = strbuf_detach(&buf, NULL); in convert_to_perf_probe_event()
2337 if (pev->args[i].name == NULL && ret >= 0) in convert_to_perf_probe_event()
2338 ret = -ENOMEM; in convert_to_perf_probe_event()
2352 zfree(&pev->event); in clear_perf_probe_event()
2353 zfree(&pev->group); in clear_perf_probe_event()
2354 zfree(&pev->target); in clear_perf_probe_event()
2355 clear_perf_probe_point(&pev->point); in clear_perf_probe_event()
2357 for (i = 0; i < pev->nargs; i++) { in clear_perf_probe_event()
2358 zfree(&pev->args[i].name); in clear_perf_probe_event()
2359 zfree(&pev->args[i].var); in clear_perf_probe_event()
2360 zfree(&pev->args[i].type); in clear_perf_probe_event()
2361 field = pev->args[i].field; in clear_perf_probe_event()
2363 next = field->next; in clear_perf_probe_event()
2364 zfree(&field->name); in clear_perf_probe_event()
2369 pev->nargs = 0; in clear_perf_probe_event()
2370 zfree(&pev->args); in clear_perf_probe_event()
2379 dst->file = strdup_or_goto(src->file, out_err); in perf_probe_point__copy()
2380 dst->function = strdup_or_goto(src->function, out_err); in perf_probe_point__copy()
2381 dst->lazy_line = strdup_or_goto(src->lazy_line, out_err); in perf_probe_point__copy()
2382 dst->line = src->line; in perf_probe_point__copy()
2383 dst->retprobe = src->retprobe; in perf_probe_point__copy()
2384 dst->offset = src->offset; in perf_probe_point__copy()
2389 return -ENOMEM; in perf_probe_point__copy()
2397 dst->name = strdup_or_goto(src->name, out_err); in perf_probe_arg__copy()
2398 dst->var = strdup_or_goto(src->var, out_err); in perf_probe_arg__copy()
2399 dst->type = strdup_or_goto(src->type, out_err); in perf_probe_arg__copy()
2401 field = src->field; in perf_probe_arg__copy()
2402 ppfield = &(dst->field); in perf_probe_arg__copy()
2407 (*ppfield)->name = strdup_or_goto(field->name, out_err); in perf_probe_arg__copy()
2408 (*ppfield)->index = field->index; in perf_probe_arg__copy()
2409 (*ppfield)->ref = field->ref; in perf_probe_arg__copy()
2410 field = field->next; in perf_probe_arg__copy()
2411 ppfield = &((*ppfield)->next); in perf_probe_arg__copy()
2415 return -ENOMEM; in perf_probe_arg__copy()
2423 dst->event = strdup_or_goto(src->event, out_err); in perf_probe_event__copy()
2424 dst->group = strdup_or_goto(src->group, out_err); in perf_probe_event__copy()
2425 dst->target = strdup_or_goto(src->target, out_err); in perf_probe_event__copy()
2426 dst->uprobes = src->uprobes; in perf_probe_event__copy()
2428 if (perf_probe_point__copy(&dst->point, &src->point) < 0) in perf_probe_event__copy()
2431 dst->args = zalloc(sizeof(struct perf_probe_arg) * src->nargs); in perf_probe_event__copy()
2432 if (!dst->args) in perf_probe_event__copy()
2434 dst->nargs = src->nargs; in perf_probe_event__copy()
2436 for (i = 0; i < src->nargs; i++) in perf_probe_event__copy()
2437 if (perf_probe_arg__copy(&dst->args[i], &src->args[i]) < 0) in perf_probe_event__copy()
2443 return -ENOMEM; in perf_probe_event__copy()
2451 zfree(&tev->event); in clear_probe_trace_event()
2452 zfree(&tev->group); in clear_probe_trace_event()
2453 zfree(&tev->point.symbol); in clear_probe_trace_event()
2454 zfree(&tev->point.realname); in clear_probe_trace_event()
2455 zfree(&tev->point.module); in clear_probe_trace_event()
2456 for (i = 0; i < tev->nargs; i++) { in clear_probe_trace_event()
2457 zfree(&tev->args[i].name); in clear_probe_trace_event()
2458 zfree(&tev->args[i].value); in clear_probe_trace_event()
2459 zfree(&tev->args[i].type); in clear_probe_trace_event()
2460 ref = tev->args[i].ref; in clear_probe_trace_event()
2462 next = ref->next; in clear_probe_trace_event()
2467 zfree(&tev->args); in clear_probe_trace_event()
2468 tev->nargs = 0; in clear_probe_trace_event()
2474 u64 end; member
2485 list_del_init(&node->list); in kprobe_blacklist__delete()
2486 zfree(&node->symbol); in kprobe_blacklist__delete()
2500 return -ENOTSUP; in kprobe_blacklist__load()
2508 return -errno; in kprobe_blacklist__load()
2514 ret = -ENOMEM; in kprobe_blacklist__load()
2517 INIT_LIST_HEAD(&node->list); in kprobe_blacklist__load()
2518 list_add_tail(&node->list, blacklist); in kprobe_blacklist__load()
2519 if (sscanf(buf, "0x%" PRIx64 "-0x%" PRIx64, &node->start, &node->end) != 2) { in kprobe_blacklist__load()
2520 ret = -EINVAL; in kprobe_blacklist__load()
2526 if (p[strlen(p) - 1] == '\n') in kprobe_blacklist__load()
2527 p[strlen(p) - 1] = '\0'; in kprobe_blacklist__load()
2530 node->symbol = strdup(p); in kprobe_blacklist__load()
2531 if (!node->symbol) { in kprobe_blacklist__load()
2532 ret = -ENOMEM; in kprobe_blacklist__load()
2535 pr_debug2("Blacklist: 0x%" PRIx64 "-0x%" PRIx64 ", %s\n", in kprobe_blacklist__load()
2536 node->start, node->end, node->symbol); in kprobe_blacklist__load()
2552 if (node->start <= address && address < node->end) in kprobe_blacklist__find_by_address()
2589 return -errno; in perf_probe_event__sprintf()
2590 ret = strbuf_addf(result, " %-20s (on ", buf); in perf_probe_event__sprintf()
2595 /* Synthesize only event probe point */ in perf_probe_event__sprintf()
2596 buf = synthesize_perf_probe_point(&pev->point); in perf_probe_event__sprintf()
2598 return -ENOMEM; in perf_probe_event__sprintf()
2605 if (!ret && pev->nargs > 0) { in perf_probe_event__sprintf()
2607 for (i = 0; !ret && i < pev->nargs; i++) { in perf_probe_event__sprintf()
2608 buf = synthesize_perf_probe_arg(&pev->args[i]); in perf_probe_event__sprintf()
2610 return -ENOMEM; in perf_probe_event__sprintf()
2647 if (strfilter__compare(filter, tev->event)) in filter_probe_trace_event()
2651 if (e_snprintf(tmp, 128, "%s:%s", tev->group, tev->event) < 0) in filter_probe_trace_event()
2670 return -ENOMEM; in __show_perf_probe_events()
2673 ret = parse_probe_trace_command(ent->s, &tev); in __show_perf_probe_events()
2682 &pev, tev.point.module, in __show_perf_probe_events()
2698 /* List up current perf-probe events */
2740 return -ENOMEM; in get_new_event_name()
2758 " Hint: Remove existing event by 'perf probe -d'\n" in get_new_event_name()
2759 " or force duplicates by 'perf probe -f'\n" in get_new_event_name()
2762 ret = -EEXIST; in get_new_event_name()
2778 ret = -ERANGE; in get_new_event_name()
2788 ret = -EINVAL; in get_new_event_name()
2799 struct probe_trace_point *tp = &tev->point; in warn_uprobe_event_compat()
2801 if (tp->ref_ctr_offset && !uprobe_ref_ctr_is_supported()) { in warn_uprobe_event_compat()
2804 tev->group, tev->event); in warn_uprobe_event_compat()
2808 if (!tev->uprobes || tev->nargs == 0 || !buf) in warn_uprobe_event_compat()
2811 for (i = 0; i < tev->nargs; i++) { in warn_uprobe_event_compat()
2812 if (strchr(tev->args[i].value, '@')) { in warn_uprobe_event_compat()
2814 tev->args[i].value); in warn_uprobe_event_compat()
2817 if (strglobmatch(tev->args[i].value, "[$+-]*")) { in warn_uprobe_event_compat()
2819 tev->args[i].value); in warn_uprobe_event_compat()
2838 if (pev->event && !pev->sdt) in probe_trace_event__set_name()
2839 event = pev->event; in probe_trace_event__set_name()
2840 else if (tev->event) in probe_trace_event__set_name()
2841 event = tev->event; in probe_trace_event__set_name()
2843 /* Or generate new one from probe point */ in probe_trace_event__set_name()
2844 if (pev->point.function && in probe_trace_event__set_name()
2845 (strncmp(pev->point.function, "0x", 2) != 0) && in probe_trace_event__set_name()
2846 !strisglob(pev->point.function)) in probe_trace_event__set_name()
2847 event = pev->point.function; in probe_trace_event__set_name()
2849 event = tev->point.realname; in probe_trace_event__set_name()
2851 if (pev->group && !pev->sdt) in probe_trace_event__set_name()
2852 group = pev->group; in probe_trace_event__set_name()
2853 else if (tev->group) in probe_trace_event__set_name()
2854 group = tev->group; in probe_trace_event__set_name()
2860 tev->point.retprobe, allow_suffix); in probe_trace_event__set_name()
2866 tev->event = strdup(event); in probe_trace_event__set_name()
2867 tev->group = strdup(group); in probe_trace_event__set_name()
2868 if (tev->event == NULL || tev->group == NULL) in probe_trace_event__set_name()
2869 return -ENOMEM; in probe_trace_event__set_name()
2895 return -ENOMEM; in __open_probe_file_and_namelist()
2904 int i, fd[2] = {-1, -1}, up, ret; in __add_probe_trace_events()
2910 up = pev->uprobes ? 1 : 0; in __add_probe_trace_events()
2918 up = tev->uprobes ? 1 : 0; in __add_probe_trace_events()
2919 if (fd[up] == -1) { /* Open the kprobe/uprobe_events */ in __add_probe_trace_events()
2926 if (!tev->point.symbol && !pev->uprobes) in __add_probe_trace_events()
2935 nsinfo__mountns_enter(pev->nsi, &nsc); in __add_probe_trace_events()
2949 if (ret == -EINVAL && pev->uprobes) in __add_probe_trace_events()
2952 cache = probe_cache__new(pev->target, pev->nsi); in __add_probe_trace_events()
2980 return -EACCES; /* Possible permission error to load symbols */ in find_probe_functions()
2987 norm = arch__normalize_symbol_name(sym->name); in find_probe_functions()
2995 buf = strndup(norm, ver - norm); in find_probe_functions()
2997 return -ENOMEM; in find_probe_functions()
3005 syms[found - 1] = sym; in find_probe_functions()
3042 struct perf_probe_point *pp = &pev->point; in find_probe_trace_events_from_map()
3048 map = get_target_map(pev->target, pev->nsi, pev->uprobes); in find_probe_trace_events_from_map()
3050 ret = -EINVAL; in find_probe_trace_events_from_map()
3056 ret = -ENOMEM; in find_probe_trace_events_from_map()
3064 num_matched_functions = find_probe_functions(map, pp->function, syms); in find_probe_trace_events_from_map()
3066 if (num_matched_functions == -EACCES) { in find_probe_trace_events_from_map()
3068 pev->target ?: "/proc/kallsyms"); in find_probe_trace_events_from_map()
3069 if (pev->target) in find_probe_trace_events_from_map()
3074 pr_err("Failed to find symbol %s in %s\n", pp->function, in find_probe_trace_events_from_map()
3075 pev->target ? : "kernel"); in find_probe_trace_events_from_map()
3076 ret = -ENOENT; in find_probe_trace_events_from_map()
3080 pev->target ? : "kernel"); in find_probe_trace_events_from_map()
3081 ret = -E2BIG; in find_probe_trace_events_from_map()
3086 if (!pev->uprobes && !pev->target && in find_probe_trace_events_from_map()
3087 (!pp->retprobe || kretprobe_offset_is_supported())) { in find_probe_trace_events_from_map()
3094 ret = -EINVAL; in find_probe_trace_events_from_map()
3099 /* Setup result trace-probe-events */ in find_probe_trace_events_from_map()
3102 ret = -ENOMEM; in find_probe_trace_events_from_map()
3111 if (sym->type != STT_FUNC) in find_probe_trace_events_from_map()
3116 if (sym->start == syms[i]->start) { in find_probe_trace_events_from_map()
3118 sym->name, sym->start); in find_probe_trace_events_from_map()
3125 tp = &tev->point; in find_probe_trace_events_from_map()
3132 if (pp->offset > sym->end - sym->start) { in find_probe_trace_events_from_map()
3134 pp->offset, sym->name); in find_probe_trace_events_from_map()
3135 ret = -ENOENT; in find_probe_trace_events_from_map()
3138 /* Add one probe point */ in find_probe_trace_events_from_map()
3139 tp->address = map__unmap_ip(map, sym->start) + pp->offset; in find_probe_trace_events_from_map()
3142 if (!pev->uprobes && !pev->target && in find_probe_trace_events_from_map()
3143 kprobe_warn_out_range(sym->name, tp->address)) { in find_probe_trace_events_from_map()
3144 tp->symbol = NULL; /* Skip it */ in find_probe_trace_events_from_map()
3147 tp->symbol = strdup_or_goto(reloc_sym->name, nomem_out); in find_probe_trace_events_from_map()
3148 tp->offset = tp->address - reloc_sym->addr; in find_probe_trace_events_from_map()
3150 tp->symbol = strdup_or_goto(sym->name, nomem_out); in find_probe_trace_events_from_map()
3151 tp->offset = pp->offset; in find_probe_trace_events_from_map()
3153 tp->realname = strdup_or_goto(sym->name, nomem_out); in find_probe_trace_events_from_map()
3155 tp->retprobe = pp->retprobe; in find_probe_trace_events_from_map()
3156 if (pev->target) { in find_probe_trace_events_from_map()
3157 if (pev->uprobes) { in find_probe_trace_events_from_map()
3158 tev->point.module = strdup_or_goto(pev->target, in find_probe_trace_events_from_map()
3161 mod_name = find_module_name(pev->target); in find_probe_trace_events_from_map()
3162 tev->point.module = in find_probe_trace_events_from_map()
3163 strdup(mod_name ? mod_name : pev->target); in find_probe_trace_events_from_map()
3165 if (!tev->point.module) in find_probe_trace_events_from_map()
3169 tev->uprobes = pev->uprobes; in find_probe_trace_events_from_map()
3170 tev->nargs = pev->nargs; in find_probe_trace_events_from_map()
3171 if (tev->nargs) { in find_probe_trace_events_from_map()
3172 tev->args = zalloc(sizeof(struct probe_trace_arg) * in find_probe_trace_events_from_map()
3173 tev->nargs); in find_probe_trace_events_from_map()
3174 if (tev->args == NULL) in find_probe_trace_events_from_map()
3177 for (i = 0; i < tev->nargs; i++) { in find_probe_trace_events_from_map()
3178 if (pev->args[i].name) in find_probe_trace_events_from_map()
3179 tev->args[i].name = in find_probe_trace_events_from_map()
3180 strdup_or_goto(pev->args[i].name, in find_probe_trace_events_from_map()
3183 tev->args[i].value = strdup_or_goto(pev->args[i].var, in find_probe_trace_events_from_map()
3185 if (pev->args[i].type) in find_probe_trace_events_from_map()
3186 tev->args[i].type = in find_probe_trace_events_from_map()
3187 strdup_or_goto(pev->args[i].type, in find_probe_trace_events_from_map()
3193 ret = -ENOENT; in find_probe_trace_events_from_map()
3203 ret = -ENOMEM; in find_probe_trace_events_from_map()
3213 struct perf_probe_point *pp = &pev->point; in try_to_find_absolute_address()
3218 if (!(pev->point.function && !strncmp(pev->point.function, "0x", 2))) in try_to_find_absolute_address()
3219 return -EINVAL; in try_to_find_absolute_address()
3221 return -EINVAL; in try_to_find_absolute_address()
3231 return -ENOMEM; in try_to_find_absolute_address()
3234 tp = &tev->point; in try_to_find_absolute_address()
3237 * Don't use tp->offset, use address directly, because in try_to_find_absolute_address()
3241 tp->address = pev->point.abs_address; in try_to_find_absolute_address()
3242 tp->retprobe = pp->retprobe; in try_to_find_absolute_address()
3243 tev->uprobes = pev->uprobes; in try_to_find_absolute_address()
3245 err = -ENOMEM; in try_to_find_absolute_address()
3251 if (asprintf(&tp->symbol, "0x%" PRIx64, tp->address) < 0) in try_to_find_absolute_address()
3255 if ((!tev->uprobes) && in try_to_find_absolute_address()
3256 (kprobe_warn_out_range(tev->point.symbol, in try_to_find_absolute_address()
3257 tev->point.address))) { in try_to_find_absolute_address()
3258 err = -EACCES; in try_to_find_absolute_address()
3262 if (asprintf(&tp->realname, "abs_%" PRIx64, tp->address) < 0) in try_to_find_absolute_address()
3265 if (pev->target) { in try_to_find_absolute_address()
3266 tp->module = strdup(pev->target); in try_to_find_absolute_address()
3267 if (!tp->module) in try_to_find_absolute_address()
3271 if (tev->group) { in try_to_find_absolute_address()
3272 tev->group = strdup(pev->group); in try_to_find_absolute_address()
3273 if (!tev->group) in try_to_find_absolute_address()
3277 if (pev->event) { in try_to_find_absolute_address()
3278 tev->event = strdup(pev->event); in try_to_find_absolute_address()
3279 if (!tev->event) in try_to_find_absolute_address()
3283 tev->nargs = pev->nargs; in try_to_find_absolute_address()
3284 tev->args = zalloc(sizeof(struct probe_trace_arg) * tev->nargs); in try_to_find_absolute_address()
3285 if (!tev->args) in try_to_find_absolute_address()
3288 for (i = 0; i < tev->nargs; i++) in try_to_find_absolute_address()
3289 copy_to_probe_trace_arg(&tev->args[i], &pev->args[i]); in try_to_find_absolute_address()
3327 ret = -E2BIG; in concat_probe_trace_events()
3333 ret = -ENOMEM; in concat_probe_trace_events()
3361 cache = probe_cache__new(target, pev->nsi); in find_cached_events()
3368 if (!entry->pev.event || !entry->pev.group) in find_cached_events()
3370 if ((!pev->group || strglobmatch(entry->pev.group, pev->group)) && in find_cached_events()
3371 strglobmatch(entry->pev.event, pev->event)) { in find_cached_events()
3387 pev->uprobes = true; in find_cached_events()
3407 ret = -errno; in find_cached_events_all()
3414 pathname = build_id_cache__origname(nd->s); in find_cached_events_all()
3444 if (pev->sdt) { in find_probe_trace_events_from_cache()
3446 if (!pev->target) in find_probe_trace_events_from_cache()
3449 return find_cached_events(pev, tevs, pev->target); in find_probe_trace_events_from_cache()
3451 cache = probe_cache__new(pev->target, pev->nsi); in find_probe_trace_events_from_cache()
3458 ret = pev->sdt ? -ENOENT : 0; in find_probe_trace_events_from_cache()
3462 ret = strlist__nr_entries(entry->tevlist); in find_probe_trace_events_from_cache()
3465 pev->target ? : "kernel"); in find_probe_trace_events_from_cache()
3466 ret = -E2BIG; in find_probe_trace_events_from_cache()
3472 ret = -ENOMEM; in find_probe_trace_events_from_cache()
3477 strlist__for_each_entry(node, entry->tevlist) { in find_probe_trace_events_from_cache()
3479 ret = parse_probe_trace_command(node->s, tev); in find_probe_trace_events_from_cache()
3483 tev->uprobes = pev->uprobes; in find_probe_trace_events_from_cache()
3497 if (!pev->group && !pev->sdt) { in convert_to_probe_trace_events()
3499 if (!pev->uprobes) { in convert_to_probe_trace_events()
3500 pev->group = strdup(PERFPROBE_GROUP); in convert_to_probe_trace_events()
3501 ret = pev->group ? 0 : -ENOMEM; in convert_to_probe_trace_events()
3503 ret = convert_exec_to_group(pev->target, &pev->group); in convert_to_probe_trace_events()
3516 if (ret > 0 || pev->sdt) /* SDT can be found only in the cache */ in convert_to_probe_trace_events()
3517 return ret == 0 ? -ENOENT : ret; /* Found in probe cache */ in convert_to_probe_trace_events()
3554 return -EINVAL; in show_probe_trace_event()
3572 return -ENOMEM; in show_probe_trace_events()
3576 for (i = 0; i < pev->ntevs && !ret; i++) { in show_probe_trace_events()
3577 tev = &pev->tevs[i]; in show_probe_trace_events()
3579 if (!tev->point.symbol && !pev->uprobes) in show_probe_trace_events()
3596 struct probe_trace_point *tp = &tev->point; in show_bootconfig_event()
3602 return -ENOMEM; in show_bootconfig_event()
3628 return -ENOMEM; in show_bootconfig_events()
3632 if (pev->group && strcmp(pev->group, "probe")) in show_bootconfig_events()
3633 pr_warning("WARN: Group name %s is ignored\n", pev->group); in show_bootconfig_events()
3634 if (pev->uprobes) { in show_bootconfig_events()
3636 ret = -EINVAL; in show_bootconfig_events()
3639 for (i = 0; i < pev->ntevs && !ret; i++) { in show_bootconfig_events()
3640 tev = &pev->tevs[i]; in show_bootconfig_events()
3642 if (!tev->point.symbol && !pev->uprobes) in show_bootconfig_events()
3651 if (!cur_name || strcmp(cur_name, tev->event)) { in show_bootconfig_events()
3653 cur_name ? "\n" : "", tev->event); in show_bootconfig_events()
3654 cur_name = tev->event; in show_bootconfig_events()
3693 nsinfo__zput(pev->nsi); in cleanup_perf_probe_events()
3702 ret = init_probe_symbol_maps(pevs->uprobes); in add_perf_probe_events()
3718 int ret, ret2, ufd = -1, kfd = -1; in del_perf_probe_events()
3722 return -EINVAL; in del_perf_probe_events()
3730 if (ret < 0 && ret != -ENOENT) in del_perf_probe_events()
3734 if (ret2 < 0 && ret2 != -ENOENT) { in del_perf_probe_events()
3766 return -EINVAL; in show_available_funcs()
3771 if (ret == -2) { in show_available_funcs()
3779 goto end; in show_available_funcs()
3787 for (size_t i = 0; i < dso->symbol_names_len; i++) { in show_available_funcs()
3788 struct symbol *pos = dso->symbol_names[i]; in show_available_funcs()
3790 if (strfilter__compare(_filter, pos->name)) in show_available_funcs()
3791 printf("%s\n", pos->name); in show_available_funcs()
3793 end: in show_available_funcs()
3803 tvar->value = strdup(pvar->var); in copy_to_probe_trace_arg()
3804 if (tvar->value == NULL) in copy_to_probe_trace_arg()
3805 return -ENOMEM; in copy_to_probe_trace_arg()
3806 if (pvar->type) { in copy_to_probe_trace_arg()
3807 tvar->type = strdup(pvar->type); in copy_to_probe_trace_arg()
3808 if (tvar->type == NULL) in copy_to_probe_trace_arg()
3809 return -ENOMEM; in copy_to_probe_trace_arg()
3811 if (pvar->name) { in copy_to_probe_trace_arg()
3812 tvar->name = strdup(pvar->name); in copy_to_probe_trace_arg()
3813 if (tvar->name == NULL) in copy_to_probe_trace_arg()
3814 return -ENOMEM; in copy_to_probe_trace_arg()
3816 tvar->name = NULL; in copy_to_probe_trace_arg()