mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-13 14:24:11 +08:00
perf tools: Print lost samples due to BPF filter
Print the actual dropped sample count in the event stat. $ sudo perf record -o- -e cycles --filter 'period < 10000' \ -e instructions --filter 'ip > 0x8000000000000000' perf test -w noploop | \ perf report --stat -i- [ perf record: Woken up 1 times to write data ] [ perf record: Captured and wrote 0.058 MB - ] Aggregated stats: TOTAL events: 469 MMAP events: 268 (57.1%) COMM events: 2 ( 0.4%) EXIT events: 1 ( 0.2%) SAMPLE events: 16 ( 3.4%) MMAP2 events: 22 ( 4.7%) LOST_SAMPLES events: 2 ( 0.4%) KSYMBOL events: 89 (19.0%) BPF_EVENT events: 39 ( 8.3%) ATTR events: 2 ( 0.4%) FINISHED_ROUND events: 1 ( 0.2%) ID_INDEX events: 1 ( 0.2%) THREAD_MAP events: 1 ( 0.2%) CPU_MAP events: 1 ( 0.2%) EVENT_UPDATE events: 2 ( 0.4%) TIME_CONV events: 1 ( 0.2%) FEATURE events: 20 ( 4.3%) FINISHED_INIT events: 1 ( 0.2%) cycles stats: SAMPLE events: 2 LOST_SAMPLES (BPF) events: 4010 instructions stats: SAMPLE events: 14 LOST_SAMPLES (BPF) events: 3990 Signed-off-by: Namhyung Kim <namhyung@kernel.org> Cc: Adrian Hunter <adrian.hunter@intel.com> Cc: Ian Rogers <irogers@google.com> Cc: Ingo Molnar <mingo@kernel.org> Cc: Jiri Olsa <jolsa@kernel.org> Cc: KP Singh <kpsingh@kernel.org> Cc: Kan Liang <kan.liang@linux.intel.com> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Song Liu <song@kernel.org> Link: https://lore.kernel.org/r/20240820154504.128923-2-namhyung@kernel.org Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
This commit is contained in:
parent
0fe2b18ddc
commit
1a5474a779
@ -795,8 +795,13 @@ static int count_lost_samples_event(const struct perf_tool *tool,
|
||||
|
||||
evsel = evlist__id2evsel(rep->session->evlist, sample->id);
|
||||
if (evsel) {
|
||||
hists__inc_nr_lost_samples(evsel__hists(evsel),
|
||||
event->lost_samples.lost);
|
||||
struct hists *hists = evsel__hists(evsel);
|
||||
u32 count = event->lost_samples.lost;
|
||||
|
||||
if (event->header.misc & PERF_RECORD_MISC_LOST_SAMPLES_BPF)
|
||||
hists__inc_nr_dropped_samples(hists, count);
|
||||
else
|
||||
hists__inc_nr_lost_samples(hists, count);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -913,11 +913,11 @@ size_t events_stats__fprintf(struct events_stats *stats, FILE *fp)
|
||||
continue;
|
||||
|
||||
if (i && total) {
|
||||
ret += fprintf(fp, "%16s events: %10d (%4.1f%%)\n",
|
||||
ret += fprintf(fp, "%20s events: %10d (%4.1f%%)\n",
|
||||
name, stats->nr_events[i],
|
||||
100.0 * stats->nr_events[i] / total);
|
||||
} else {
|
||||
ret += fprintf(fp, "%16s events: %10d\n",
|
||||
ret += fprintf(fp, "%20s events: %10d\n",
|
||||
name, stats->nr_events[i]);
|
||||
}
|
||||
}
|
||||
|
@ -18,7 +18,18 @@
|
||||
* PERF_RECORD_LOST_SAMPLES event. The number of lost-samples events is stored
|
||||
* in .nr_events[PERF_RECORD_LOST_SAMPLES] while total_lost_samples tells
|
||||
* exactly how many samples the kernel in fact dropped, i.e. it is the sum of
|
||||
* all struct perf_record_lost_samples.lost fields reported.
|
||||
* all struct perf_record_lost_samples.lost fields reported without setting the
|
||||
* misc field in the header.
|
||||
*
|
||||
* The BPF program can discard samples according to the filter expressions given
|
||||
* by the user. This number is kept in a BPF map and dumped at the end of perf
|
||||
* record in a PERF_RECORD_LOST_SAMPLES event. To differentiate it from other
|
||||
* lost samples, perf tools sets PERF_RECORD_MISC_LOST_SAMPLES_BPF flag in the
|
||||
* header.misc field. The number of dropped-samples events is stored in
|
||||
* .nr_events[PERF_RECORD_LOST_SAMPLES] while total_dropped_samples tells
|
||||
* exactly how many samples the BPF program in fact dropped, i.e. it is the sum
|
||||
* of all struct perf_record_lost_samples.lost fields reported with the misc
|
||||
* field set in the header.
|
||||
*
|
||||
* The total_period is needed because by default auto-freq is used, so
|
||||
* multiplying nr_events[PERF_EVENT_SAMPLE] by a frequency isn't possible to get
|
||||
@ -28,6 +39,7 @@
|
||||
struct events_stats {
|
||||
u64 total_lost;
|
||||
u64 total_lost_samples;
|
||||
u64 total_dropped_samples;
|
||||
u64 total_aux_lost;
|
||||
u64 total_aux_partial;
|
||||
u64 total_aux_collision;
|
||||
@ -48,6 +60,7 @@ struct hists_stats {
|
||||
u32 nr_samples;
|
||||
u32 nr_non_filtered_samples;
|
||||
u32 nr_lost_samples;
|
||||
u32 nr_dropped_samples;
|
||||
};
|
||||
|
||||
void events_stats__inc(struct events_stats *stats, u32 type);
|
||||
|
@ -2385,6 +2385,11 @@ void hists__inc_nr_lost_samples(struct hists *hists, u32 lost)
|
||||
hists->stats.nr_lost_samples += lost;
|
||||
}
|
||||
|
||||
void hists__inc_nr_dropped_samples(struct hists *hists, u32 lost)
|
||||
{
|
||||
hists->stats.nr_dropped_samples += lost;
|
||||
}
|
||||
|
||||
static struct hist_entry *hists__add_dummy_entry(struct hists *hists,
|
||||
struct hist_entry *pair)
|
||||
{
|
||||
@ -2729,18 +2734,24 @@ size_t evlist__fprintf_nr_events(struct evlist *evlist, FILE *fp)
|
||||
|
||||
evlist__for_each_entry(evlist, pos) {
|
||||
struct hists *hists = evsel__hists(pos);
|
||||
u64 total_samples = hists->stats.nr_samples;
|
||||
|
||||
if (symbol_conf.skip_empty && !hists->stats.nr_samples &&
|
||||
!hists->stats.nr_lost_samples)
|
||||
total_samples += hists->stats.nr_lost_samples;
|
||||
total_samples += hists->stats.nr_dropped_samples;
|
||||
|
||||
if (symbol_conf.skip_empty && total_samples == 0)
|
||||
continue;
|
||||
|
||||
ret += fprintf(fp, "%s stats:\n", evsel__name(pos));
|
||||
if (hists->stats.nr_samples)
|
||||
ret += fprintf(fp, "%16s events: %10d\n",
|
||||
ret += fprintf(fp, "%20s events: %10d\n",
|
||||
"SAMPLE", hists->stats.nr_samples);
|
||||
if (hists->stats.nr_lost_samples)
|
||||
ret += fprintf(fp, "%16s events: %10d\n",
|
||||
ret += fprintf(fp, "%20s events: %10d\n",
|
||||
"LOST_SAMPLES", hists->stats.nr_lost_samples);
|
||||
if (hists->stats.nr_dropped_samples)
|
||||
ret += fprintf(fp, "%20s events: %10d\n",
|
||||
"LOST_SAMPLES (BPF)", hists->stats.nr_dropped_samples);
|
||||
}
|
||||
|
||||
return ret;
|
||||
|
@ -372,6 +372,7 @@ void hists__inc_stats(struct hists *hists, struct hist_entry *h);
|
||||
void hists__inc_nr_events(struct hists *hists);
|
||||
void hists__inc_nr_samples(struct hists *hists, bool filtered);
|
||||
void hists__inc_nr_lost_samples(struct hists *hists, u32 lost);
|
||||
void hists__inc_nr_dropped_samples(struct hists *hists, u32 lost);
|
||||
|
||||
size_t hists__fprintf(struct hists *hists, bool show_header, int max_rows,
|
||||
int max_cols, float min_pcnt, FILE *fp,
|
||||
|
@ -642,8 +642,9 @@ int machine__process_lost_event(struct machine *machine __maybe_unused,
|
||||
int machine__process_lost_samples_event(struct machine *machine __maybe_unused,
|
||||
union perf_event *event, struct perf_sample *sample)
|
||||
{
|
||||
dump_printf(": id:%" PRIu64 ": lost samples :%" PRI_lu64 "\n",
|
||||
sample->id, event->lost_samples.lost);
|
||||
dump_printf(": id:%" PRIu64 ": lost samples :%" PRI_lu64 "%s\n",
|
||||
sample->id, event->lost_samples.lost,
|
||||
event->header.misc & PERF_RECORD_MISC_LOST_SAMPLES_BPF ? " (BPF)" : "");
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1290,8 +1290,9 @@ static int machines__deliver_event(struct machines *machines,
|
||||
evlist->stats.total_lost += event->lost.lost;
|
||||
return tool->lost(tool, event, sample, machine);
|
||||
case PERF_RECORD_LOST_SAMPLES:
|
||||
if (tool->lost_samples == perf_event__process_lost_samples &&
|
||||
!(event->header.misc & PERF_RECORD_MISC_LOST_SAMPLES_BPF))
|
||||
if (event->header.misc & PERF_RECORD_MISC_LOST_SAMPLES_BPF)
|
||||
evlist->stats.total_dropped_samples += event->lost_samples.lost;
|
||||
else if (tool->lost_samples == perf_event__process_lost_samples)
|
||||
evlist->stats.total_lost_samples += event->lost_samples.lost;
|
||||
return tool->lost_samples(tool, event, sample, machine);
|
||||
case PERF_RECORD_READ:
|
||||
|
Loading…
Reference in New Issue
Block a user