Skip to content

Commit d8a450a

Browse files
committed
Merge tag 'perf-tools-fixes-for-v6.0-2022-09-08' of git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux
Pull perf tools fixes from Arnaldo Carvalho de Melo: - Fix per-thread mmaps for multi-threaded targets, noticed with 'perf top --pid' with multithreaded targets - Fix synthesis failure warnings in 'perf record' - Fix L2 Topdown metrics disappearance for raw events in 'perf stat' - Fix out of bound access in some CPU masks - Fix segfault if there is no CPU PMU table and a metric is sought, noticed when building with NO_JEVENTS=1 - Skip dummy event attr check in 'perf script' fixing nonsensical warning about UREGS attribute not set, as 'dummy' events have no samples - Fix 'iregs' field handling with dummy events on hybrid systems in 'perf script' - Prevent potential memory leak in c2c_he_zalloc() in 'perf c2c' - Don't install data files with x permissions - Fix types for print format in dlfilter-show-cycles - Switch deprecated openssl MD5_* functions to new EVP API in 'genelf' - Remove redundant word 'contention' in 'perf lock' help message * tag 'perf-tools-fixes-for-v6.0-2022-09-08' of git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux: perf record: Fix synthesis failure warnings perf tools: Don't install data files with x permissions perf script: Fix Cannot print 'iregs' field for hybrid systems perf lock: Remove redundant word 'contention' in help message perf dlfilter dlfilter-show-cycles: Fix types for print format libperf evlist: Fix per-thread mmaps for multi-threaded targets perf c2c: Prevent potential memory leak in c2c_he_zalloc() perf genelf: Switch deprecated openssl MD5_* functions to new EVP API tools/perf: Fix out of bound access to cpu mask array perf affinity: Fix out of bound access to "sched_cpus" mask perf stat: Fix L2 Topdown metrics disappear for raw events perf script: Skip dummy event attr check perf metric: Return early if no CPU PMU table exists
2 parents 460a75a + faf59ec commit d8a450a

File tree

11 files changed

+129
-39
lines changed

11 files changed

+129
-39
lines changed

tools/lib/perf/evlist.c

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -486,6 +486,7 @@ mmap_per_evsel(struct perf_evlist *evlist, struct perf_evlist_mmap_ops *ops,
486486
if (ops->idx)
487487
ops->idx(evlist, evsel, mp, idx);
488488

489+
pr_debug("idx %d: mmapping fd %d\n", idx, *output);
489490
if (ops->mmap(map, mp, *output, evlist_cpu) < 0)
490491
return -1;
491492

@@ -494,6 +495,7 @@ mmap_per_evsel(struct perf_evlist *evlist, struct perf_evlist_mmap_ops *ops,
494495
if (!idx)
495496
perf_evlist__set_mmap_first(evlist, map, overwrite);
496497
} else {
498+
pr_debug("idx %d: set output fd %d -> %d\n", idx, fd, *output);
497499
if (ioctl(fd, PERF_EVENT_IOC_SET_OUTPUT, *output) != 0)
498500
return -1;
499501

@@ -519,6 +521,48 @@ mmap_per_evsel(struct perf_evlist *evlist, struct perf_evlist_mmap_ops *ops,
519521
return 0;
520522
}
521523

524+
static int
525+
mmap_per_thread(struct perf_evlist *evlist, struct perf_evlist_mmap_ops *ops,
526+
struct perf_mmap_param *mp)
527+
{
528+
int nr_threads = perf_thread_map__nr(evlist->threads);
529+
int nr_cpus = perf_cpu_map__nr(evlist->all_cpus);
530+
int cpu, thread, idx = 0;
531+
int nr_mmaps = 0;
532+
533+
pr_debug("%s: nr cpu values (may include -1) %d nr threads %d\n",
534+
__func__, nr_cpus, nr_threads);
535+
536+
/* per-thread mmaps */
537+
for (thread = 0; thread < nr_threads; thread++, idx++) {
538+
int output = -1;
539+
int output_overwrite = -1;
540+
541+
if (mmap_per_evsel(evlist, ops, idx, mp, 0, thread, &output,
542+
&output_overwrite, &nr_mmaps))
543+
goto out_unmap;
544+
}
545+
546+
/* system-wide mmaps i.e. per-cpu */
547+
for (cpu = 1; cpu < nr_cpus; cpu++, idx++) {
548+
int output = -1;
549+
int output_overwrite = -1;
550+
551+
if (mmap_per_evsel(evlist, ops, idx, mp, cpu, 0, &output,
552+
&output_overwrite, &nr_mmaps))
553+
goto out_unmap;
554+
}
555+
556+
if (nr_mmaps != evlist->nr_mmaps)
557+
pr_err("Miscounted nr_mmaps %d vs %d\n", nr_mmaps, evlist->nr_mmaps);
558+
559+
return 0;
560+
561+
out_unmap:
562+
perf_evlist__munmap(evlist);
563+
return -1;
564+
}
565+
522566
static int
523567
mmap_per_cpu(struct perf_evlist *evlist, struct perf_evlist_mmap_ops *ops,
524568
struct perf_mmap_param *mp)
@@ -528,6 +572,8 @@ mmap_per_cpu(struct perf_evlist *evlist, struct perf_evlist_mmap_ops *ops,
528572
int nr_mmaps = 0;
529573
int cpu, thread;
530574

575+
pr_debug("%s: nr cpu values %d nr threads %d\n", __func__, nr_cpus, nr_threads);
576+
531577
for (cpu = 0; cpu < nr_cpus; cpu++) {
532578
int output = -1;
533579
int output_overwrite = -1;
@@ -569,6 +615,7 @@ int perf_evlist__mmap_ops(struct perf_evlist *evlist,
569615
struct perf_evlist_mmap_ops *ops,
570616
struct perf_mmap_param *mp)
571617
{
618+
const struct perf_cpu_map *cpus = evlist->all_cpus;
572619
struct perf_evsel *evsel;
573620

574621
if (!ops || !ops->get || !ops->mmap)
@@ -588,6 +635,9 @@ int perf_evlist__mmap_ops(struct perf_evlist *evlist,
588635
if (evlist->pollfd.entries == NULL && perf_evlist__alloc_pollfd(evlist) < 0)
589636
return -ENOMEM;
590637

638+
if (perf_cpu_map__empty(cpus))
639+
return mmap_per_thread(evlist, ops, mp);
640+
591641
return mmap_per_cpu(evlist, ops, mp);
592642
}
593643

tools/perf/Makefile.perf

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -954,11 +954,11 @@ ifndef NO_LIBBPF
954954
$(call QUIET_INSTALL, bpf-headers) \
955955
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf'; \
956956
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf/linux'; \
957-
$(INSTALL) include/bpf/*.h -t '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf'; \
958-
$(INSTALL) include/bpf/linux/*.h -t '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf/linux'
957+
$(INSTALL) include/bpf/*.h -m 644 -t '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf'; \
958+
$(INSTALL) include/bpf/linux/*.h -m 644 -t '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf/linux'
959959
$(call QUIET_INSTALL, bpf-examples) \
960960
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perf_examples_instdir_SQ)/bpf'; \
961-
$(INSTALL) examples/bpf/*.c -t '$(DESTDIR_SQ)$(perf_examples_instdir_SQ)/bpf'
961+
$(INSTALL) examples/bpf/*.c -m 644 -t '$(DESTDIR_SQ)$(perf_examples_instdir_SQ)/bpf'
962962
endif
963963
$(call QUIET_INSTALL, perf-archive) \
964964
$(INSTALL) $(OUTPUT)perf-archive -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)'
@@ -967,13 +967,13 @@ endif
967967
ifndef NO_LIBAUDIT
968968
$(call QUIET_INSTALL, strace/groups) \
969969
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(STRACE_GROUPS_INSTDIR_SQ)'; \
970-
$(INSTALL) trace/strace/groups/* -t '$(DESTDIR_SQ)$(STRACE_GROUPS_INSTDIR_SQ)'
970+
$(INSTALL) trace/strace/groups/* -m 644 -t '$(DESTDIR_SQ)$(STRACE_GROUPS_INSTDIR_SQ)'
971971
endif
972972
ifndef NO_LIBPERL
973973
$(call QUIET_INSTALL, perl-scripts) \
974974
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl/Perf-Trace-Util/lib/Perf/Trace'; \
975-
$(INSTALL) scripts/perl/Perf-Trace-Util/lib/Perf/Trace/* -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl/Perf-Trace-Util/lib/Perf/Trace'; \
976-
$(INSTALL) scripts/perl/*.pl -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl'; \
975+
$(INSTALL) scripts/perl/Perf-Trace-Util/lib/Perf/Trace/* -m 644 -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl/Perf-Trace-Util/lib/Perf/Trace'; \
976+
$(INSTALL) scripts/perl/*.pl -m 644 -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl'; \
977977
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl/bin'; \
978978
$(INSTALL) scripts/perl/bin/* -t '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/scripts/perl/bin'
979979
endif
@@ -990,23 +990,23 @@ endif
990990
$(INSTALL) $(DLFILTERS) '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/dlfilters';
991991
$(call QUIET_INSTALL, perf_completion-script) \
992992
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(sysconfdir_SQ)/bash_completion.d'; \
993-
$(INSTALL) perf-completion.sh '$(DESTDIR_SQ)$(sysconfdir_SQ)/bash_completion.d/perf'
993+
$(INSTALL) perf-completion.sh -m 644 '$(DESTDIR_SQ)$(sysconfdir_SQ)/bash_completion.d/perf'
994994
$(call QUIET_INSTALL, perf-tip) \
995995
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(tip_instdir_SQ)'; \
996-
$(INSTALL) Documentation/tips.txt -t '$(DESTDIR_SQ)$(tip_instdir_SQ)'
996+
$(INSTALL) Documentation/tips.txt -m 644 -t '$(DESTDIR_SQ)$(tip_instdir_SQ)'
997997

998998
install-tests: all install-gtk
999999
$(call QUIET_INSTALL, tests) \
10001000
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests'; \
1001-
$(INSTALL) tests/attr.py '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests'; \
1001+
$(INSTALL) tests/attr.py -m 644 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests'; \
10021002
$(INSTALL) tests/pe-file.exe* '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests'; \
10031003
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/attr'; \
1004-
$(INSTALL) tests/attr/* '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/attr'; \
1004+
$(INSTALL) tests/attr/* -m 644 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/attr'; \
10051005
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell'; \
10061006
$(INSTALL) tests/shell/*.sh '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell'; \
10071007
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell/lib'; \
1008-
$(INSTALL) tests/shell/lib/*.sh '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell/lib'; \
1009-
$(INSTALL) tests/shell/lib/*.py '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell/lib'
1008+
$(INSTALL) tests/shell/lib/*.sh -m 644 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell/lib'; \
1009+
$(INSTALL) tests/shell/lib/*.py -m 644 '$(DESTDIR_SQ)$(perfexec_instdir_SQ)/tests/shell/lib'
10101010

10111011
install-bin: install-tools install-tests install-traceevent-plugins
10121012

tools/perf/builtin-c2c.c

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -146,15 +146,15 @@ static void *c2c_he_zalloc(size_t size)
146146

147147
c2c_he->cpuset = bitmap_zalloc(c2c.cpus_cnt);
148148
if (!c2c_he->cpuset)
149-
return NULL;
149+
goto out_free;
150150

151151
c2c_he->nodeset = bitmap_zalloc(c2c.nodes_cnt);
152152
if (!c2c_he->nodeset)
153-
return NULL;
153+
goto out_free;
154154

155155
c2c_he->node_stats = zalloc(c2c.nodes_cnt * sizeof(*c2c_he->node_stats));
156156
if (!c2c_he->node_stats)
157-
return NULL;
157+
goto out_free;
158158

159159
init_stats(&c2c_he->cstats.lcl_hitm);
160160
init_stats(&c2c_he->cstats.rmt_hitm);
@@ -163,6 +163,12 @@ static void *c2c_he_zalloc(size_t size)
163163
init_stats(&c2c_he->cstats.load);
164164

165165
return &c2c_he->he;
166+
167+
out_free:
168+
free(c2c_he->nodeset);
169+
free(c2c_he->cpuset);
170+
free(c2c_he);
171+
return NULL;
166172
}
167173

168174
static void c2c_he_free(void *he)

tools/perf/builtin-lock.c

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1874,8 +1874,7 @@ int cmd_lock(int argc, const char **argv)
18741874
NULL
18751875
};
18761876
const char *const lock_subcommands[] = { "record", "report", "script",
1877-
"info", "contention",
1878-
"contention", NULL };
1877+
"info", "contention", NULL };
18791878
const char *lock_usage[] = {
18801879
NULL,
18811880
NULL

tools/perf/builtin-record.c

Lines changed: 26 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1906,14 +1906,18 @@ static int record__synthesize(struct record *rec, bool tail)
19061906

19071907
err = perf_event__synthesize_bpf_events(session, process_synthesized_event,
19081908
machine, opts);
1909-
if (err < 0)
1909+
if (err < 0) {
19101910
pr_warning("Couldn't synthesize bpf events.\n");
1911+
err = 0;
1912+
}
19111913

19121914
if (rec->opts.synth & PERF_SYNTH_CGROUP) {
19131915
err = perf_event__synthesize_cgroups(tool, process_synthesized_event,
19141916
machine);
1915-
if (err < 0)
1917+
if (err < 0) {
19161918
pr_warning("Couldn't synthesize cgroup events.\n");
1919+
err = 0;
1920+
}
19171921
}
19181922

19191923
if (rec->opts.nr_threads_synthesize > 1) {
@@ -3358,16 +3362,22 @@ static struct option __record_options[] = {
33583362

33593363
struct option *record_options = __record_options;
33603364

3361-
static void record__mmap_cpu_mask_init(struct mmap_cpu_mask *mask, struct perf_cpu_map *cpus)
3365+
static int record__mmap_cpu_mask_init(struct mmap_cpu_mask *mask, struct perf_cpu_map *cpus)
33623366
{
33633367
struct perf_cpu cpu;
33643368
int idx;
33653369

33663370
if (cpu_map__is_dummy(cpus))
3367-
return;
3371+
return 0;
33683372

3369-
perf_cpu_map__for_each_cpu(cpu, idx, cpus)
3373+
perf_cpu_map__for_each_cpu(cpu, idx, cpus) {
3374+
/* Return ENODEV is input cpu is greater than max cpu */
3375+
if ((unsigned long)cpu.cpu > mask->nbits)
3376+
return -ENODEV;
33703377
set_bit(cpu.cpu, mask->bits);
3378+
}
3379+
3380+
return 0;
33713381
}
33723382

33733383
static int record__mmap_cpu_mask_init_spec(struct mmap_cpu_mask *mask, const char *mask_spec)
@@ -3379,7 +3389,9 @@ static int record__mmap_cpu_mask_init_spec(struct mmap_cpu_mask *mask, const cha
33793389
return -ENOMEM;
33803390

33813391
bitmap_zero(mask->bits, mask->nbits);
3382-
record__mmap_cpu_mask_init(mask, cpus);
3392+
if (record__mmap_cpu_mask_init(mask, cpus))
3393+
return -ENODEV;
3394+
33833395
perf_cpu_map__put(cpus);
33843396

33853397
return 0;
@@ -3461,7 +3473,12 @@ static int record__init_thread_masks_spec(struct record *rec, struct perf_cpu_ma
34613473
pr_err("Failed to allocate CPUs mask\n");
34623474
return ret;
34633475
}
3464-
record__mmap_cpu_mask_init(&cpus_mask, cpus);
3476+
3477+
ret = record__mmap_cpu_mask_init(&cpus_mask, cpus);
3478+
if (ret) {
3479+
pr_err("Failed to init cpu mask\n");
3480+
goto out_free_cpu_mask;
3481+
}
34653482

34663483
ret = record__thread_mask_alloc(&full_mask, cpu__max_cpu().cpu);
34673484
if (ret) {
@@ -3702,7 +3719,8 @@ static int record__init_thread_default_masks(struct record *rec, struct perf_cpu
37023719
if (ret)
37033720
return ret;
37043721

3705-
record__mmap_cpu_mask_init(&rec->thread_masks->maps, cpus);
3722+
if (record__mmap_cpu_mask_init(&rec->thread_masks->maps, cpus))
3723+
return -ENODEV;
37063724

37073725
rec->nr_threads = 1;
37083726

tools/perf/builtin-script.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -445,6 +445,9 @@ static int evsel__check_attr(struct evsel *evsel, struct perf_session *session)
445445
struct perf_event_attr *attr = &evsel->core.attr;
446446
bool allow_user_set;
447447

448+
if (evsel__is_dummy_event(evsel))
449+
return 0;
450+
448451
if (perf_header__has_feat(&session->header, HEADER_STAT))
449452
return 0;
450453

@@ -566,6 +569,8 @@ static struct evsel *find_first_output_type(struct evlist *evlist,
566569
struct evsel *evsel;
567570

568571
evlist__for_each_entry(evlist, evsel) {
572+
if (evsel__is_dummy_event(evsel))
573+
continue;
569574
if (output_type(evsel->core.attr.type) == (int)type)
570575
return evsel;
571576
}

tools/perf/builtin-stat.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1932,6 +1932,9 @@ static int add_default_attributes(void)
19321932
free(str);
19331933
}
19341934

1935+
if (!stat_config.topdown_level)
1936+
stat_config.topdown_level = TOPDOWN_MAX_LEVEL;
1937+
19351938
if (!evsel_list->core.nr_entries) {
19361939
if (target__has_cpu(&target))
19371940
default_attrs0[0].config = PERF_COUNT_SW_CPU_CLOCK;
@@ -1948,8 +1951,6 @@ static int add_default_attributes(void)
19481951
}
19491952
if (evlist__add_default_attrs(evsel_list, default_attrs1) < 0)
19501953
return -1;
1951-
1952-
stat_config.topdown_level = TOPDOWN_MAX_LEVEL;
19531954
/* Platform specific attrs */
19541955
if (evlist__add_default_attrs(evsel_list, default_null_attrs) < 0)
19551956
return -1;

tools/perf/dlfilters/dlfilter-show-cycles.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -98,9 +98,9 @@ int filter_event_early(void *data, const struct perf_dlfilter_sample *sample, vo
9898
static void print_vals(__u64 cycles, __u64 delta)
9999
{
100100
if (delta)
101-
printf("%10llu %10llu ", cycles, delta);
101+
printf("%10llu %10llu ", (unsigned long long)cycles, (unsigned long long)delta);
102102
else
103-
printf("%10llu %10s ", cycles, "");
103+
printf("%10llu %10s ", (unsigned long long)cycles, "");
104104
}
105105

106106
int filter_event(void *data, const struct perf_dlfilter_sample *sample, void *ctx)

tools/perf/util/affinity.c

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,14 @@ void affinity__set(struct affinity *a, int cpu)
4949
{
5050
int cpu_set_size = get_cpu_set_size();
5151

52-
if (cpu == -1)
52+
/*
53+
* Return:
54+
* - if cpu is -1
55+
* - restrict out of bound access to sched_cpus
56+
*/
57+
if (cpu == -1 || ((cpu >= (cpu_set_size * 8))))
5358
return;
59+
5460
a->changed = true;
5561
set_bit(cpu, a->sched_cpus);
5662
/*

tools/perf/util/genelf.c

Lines changed: 11 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -30,10 +30,6 @@
3030

3131
#define BUILD_ID_URANDOM /* different uuid for each run */
3232

33-
// FIXME, remove this and fix the deprecation warnings before its removed and
34-
// We'll break for good here...
35-
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
36-
3733
#ifdef HAVE_LIBCRYPTO_SUPPORT
3834

3935
#define BUILD_ID_MD5
@@ -45,6 +41,7 @@
4541
#endif
4642

4743
#ifdef BUILD_ID_MD5
44+
#include <openssl/evp.h>
4845
#include <openssl/md5.h>
4946
#endif
5047
#endif
@@ -142,15 +139,20 @@ gen_build_id(struct buildid_note *note,
142139
static void
143140
gen_build_id(struct buildid_note *note, unsigned long load_addr, const void *code, size_t csize)
144141
{
145-
MD5_CTX context;
142+
EVP_MD_CTX *mdctx;
146143

147144
if (sizeof(note->build_id) < 16)
148145
errx(1, "build_id too small for MD5");
149146

150-
MD5_Init(&context);
151-
MD5_Update(&context, &load_addr, sizeof(load_addr));
152-
MD5_Update(&context, code, csize);
153-
MD5_Final((unsigned char *)note->build_id, &context);
147+
mdctx = EVP_MD_CTX_new();
148+
if (!mdctx)
149+
errx(2, "failed to create EVP_MD_CTX");
150+
151+
EVP_DigestInit_ex(mdctx, EVP_md5(), NULL);
152+
EVP_DigestUpdate(mdctx, &load_addr, sizeof(load_addr));
153+
EVP_DigestUpdate(mdctx, code, csize);
154+
EVP_DigestFinal_ex(mdctx, (unsigned char *)note->build_id, NULL);
155+
EVP_MD_CTX_free(mdctx);
154156
}
155157
#endif
156158

0 commit comments

Comments
 (0)