From nobody Sun Dec 14 12:02:53 2025 Received: from mail-yw1-f201.google.com (mail-yw1-f201.google.com [209.85.128.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id AF0981527BE for ; Fri, 10 May 2024 05:38:07 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.128.201 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319489; cv=none; b=BcQeKQLedQyBl8TFn+KMT8Ljx4XJrCFjA6x1bAqJ31pzrPrsKO3HqtC85cW7jc/Ah0lsIN79I9WSOr/xOs/CpPyFDxsimh+YTl6NVRaVynrweoJWWQXQL59ZW8lPtDQrNbASulE9lt19i/2emEPZfMoiNix7Po+Tyep6bGwgatk= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319489; c=relaxed/simple; bh=iQp86WhJwgC1NI9vANYNuDRZL+PBh+5rBgpbw6bQX+I=; h=Date:In-Reply-To:Message-Id:Mime-Version:References:Subject:From: To:Content-Type; b=SIu3yxz7Rs+7NfMsmjudAUfubYEYu0JJIOteuG3L1cGKOaTF+5JBrxmpH45wdFa+n5tx1rzZ26xuJ8ovpYjUtdvjgz4/kHfymchCX3bH9KkEKDccaAuUbmrvl2tjGJAWD4KDSkqljexJjGIIf0wswasLL7yw1FXPVXjW8J/WvOg= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=pTs1V4RE; arc=none smtp.client-ip=209.85.128.201 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="pTs1V4RE" Received: by mail-yw1-f201.google.com with SMTP id 00721157ae682-61be26af113so27900157b3.1 for ; Thu, 09 May 2024 22:38:07 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1715319486; x=1715924286; darn=vger.kernel.org; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :from:to:cc:subject:date:message-id:reply-to; bh=SA0P+oT0/VAImEkmD4noOd22el5UFzWPyOCiJ0gQY+o=; b=pTs1V4REuN3s3Jb8Gsf8UmW7QxEsemZQIizY8USyy1sQCLg3Cs6u2CgINUel9iHHf1 s+YQUFkYvTvUqIan02PRgUOIPIJbCPfQSvuXYYM077ZnZbbfqvJsahirqbDEgWfyGKwi 0s07Ab1m44P+lJMhOlchKGbRwwXUwtm92dVU3Ka3KI+ZFkYhsRIFBluG36r4ZT64pUnE lZvhEBGcalla/fFgLGBrC3QN1g5Ajq64pNSXGstwX7gUxP+tCjzOQJ11pD3EFXdOaRoe aKn5sKL9zDzI0EvC1ervv73XA4SWyzuAbIV/szWXP66U5WmP5tVwjV3A0aDmoKJZWexU hhtQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1715319486; x=1715924286; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=SA0P+oT0/VAImEkmD4noOd22el5UFzWPyOCiJ0gQY+o=; b=X7AO0aTp2W6ocRPaQFmDXrM6+GKonyO4pgPWX9YSWEJFXVGRiqdS7rmdEyUCx8Q4ur 7XeOst0+AUWJ3tVifJgBPUUKxn+zUm37ZCLgtj6I0qqUOVie5Za24bsEn0SocQtksEyI l4sjiyqALgC/IrfBCActj8hlwYa2sw/JCTc7Lva29zOaP9o7cJXVRaTNmjG1l1ojZ8d/ JClAQFA3lqaoJsFpIyIxt5XLR+aBrX9bf7WRAcOJYaE8ytl+1ZqN6Q/1ZVlfg2VyQwhg 3SQUg+3/3odygJ2xf/+uiwkdhMBBTCXeH3E3J5xDFfLo+DWqgeyOYKd6XMWlpilhBv8f 2leg== X-Forwarded-Encrypted: i=1; AJvYcCVW9OIwudVl0fwNJ6f+x5x69TgYJ7NrxNFHFNUAFqSWnqg5otTkwBNP2OF5W6nFiEh2Dx+Ee2lrH1MLBiOAzmzGkxCvnyfaq2ojKBZM X-Gm-Message-State: AOJu0YwX4vi+eU1UMZI95Pm+qCci8AR4YVlRi23lB2wiezshwbUOqZ3c IS2qgvz3jzwIfRGxHfH8HEQ17/fTpX5GJ4lP8f+ytNJCSAKXIPUzn+2yXskQsYOQU1GsVR44kyj V+LSbBg== X-Google-Smtp-Source: AGHT+IFx9uSqqUpY1vOJkuteO3S7PtFgtmXqFQAlFsZba51Zp/FAznyfk763w6RecjMzVymrpIlaSZuUA4Lg X-Received: from irogers.svl.corp.google.com ([2620:15c:2a3:200:79ed:c375:51e3:ed39]) (user=irogers job=sendgmr) by 2002:a05:6902:150a:b0:dc2:2ace:860 with SMTP id 3f1490d57ef6-dee4f3117c3mr139280276.2.1715319486529; Thu, 09 May 2024 22:38:06 -0700 (PDT) Date: Thu, 9 May 2024 22:37:01 -0700 In-Reply-To: <20240510053705.2462258-1-irogers@google.com> Message-Id: <20240510053705.2462258-2-irogers@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20240510053705.2462258-1-irogers@google.com> X-Mailer: git-send-email 2.45.0.118.g7fe29c98d7-goog Subject: [PATCH v3 1/5] perf evsel: Add alternate_hw_config and use in evsel__match From: Ian Rogers To: Peter Zijlstra , Ingo Molnar , Arnaldo Carvalho de Melo , Namhyung Kim , Mark Rutland , Alexander Shishkin , Jiri Olsa , Ian Rogers , Adrian Hunter , Kan Liang , Ravi Bangoria , James Clark , Yang Jihong , Ze Gao , Leo Yan , Song Liu , K Prateek Nayak , Kaige Ye , Yicong Yang , linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" There are cases where we want to match events like instructions and cycles with legacy hardware values, in particular in stat-shadow's hard coded metrics. An evsel's name isn't a good point of reference as it gets altered, strstr would be too imprecise and re-parsing the event from its name is silly. Instead, hold the legacy hardware event name, determined during parsing, in the evsel for this matching case. Inline evsel__match2 that is only used in builtin-diff. Signed-off-by: Ian Rogers --- tools/perf/builtin-diff.c | 6 ++-- tools/perf/util/evsel.c | 21 ++++++++++++++ tools/perf/util/evsel.h | 19 ++----------- tools/perf/util/parse-events.c | 51 +++++++++++++++++++++------------- tools/perf/util/parse-events.h | 6 ++++ tools/perf/util/pmu.c | 6 +++- tools/perf/util/pmu.h | 2 +- 7 files changed, 70 insertions(+), 41 deletions(-) diff --git a/tools/perf/builtin-diff.c b/tools/perf/builtin-diff.c index 57d300d8e570..500a8f9e7c0d 100644 --- a/tools/perf/builtin-diff.c +++ b/tools/perf/builtin-diff.c @@ -483,13 +483,13 @@ static struct perf_diff pdiff =3D { }, }; =20 -static struct evsel *evsel_match(struct evsel *evsel, - struct evlist *evlist) +static struct evsel *evsel_match(struct evsel *evsel, struct evlist *evlis= t) { struct evsel *e; =20 evlist__for_each_entry(evlist, e) { - if (evsel__match2(evsel, e)) + if ((evsel->core.attr.type =3D=3D e->core.attr.type) && + (evsel->core.attr.config =3D=3D e->core.attr.config)) return e; } =20 diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c index 3536404e9447..dfdb60c7a364 100644 --- a/tools/perf/util/evsel.c +++ b/tools/perf/util/evsel.c @@ -295,6 +295,7 @@ void evsel__init(struct evsel *evsel, evsel->pmu_name =3D NULL; evsel->group_pmu_name =3D NULL; evsel->skippable =3D false; + evsel->alternate_hw_config =3D PERF_COUNT_HW_MAX; } =20 struct evsel *evsel__new_idx(struct perf_event_attr *attr, int idx) @@ -441,6 +442,8 @@ struct evsel *evsel__clone(struct evsel *orig) if (evsel__copy_config_terms(evsel, orig) < 0) goto out_err; =20 + evsel->alternate_hw_config =3D orig->alternate_hw_config; + return evsel; =20 out_err: @@ -1600,6 +1603,24 @@ static int evsel__read_group(struct evsel *leader, i= nt cpu_map_idx, int thread) return evsel__process_group_data(leader, cpu_map_idx, thread, data); } =20 +bool __evsel__match(const struct evsel *evsel, u32 type, u64 config) +{ + + u32 e_type =3D evsel->core.attr.type; + u64 e_config =3D evsel->core.attr.config; + + if (e_type !=3D type) { + return type =3D=3D PERF_TYPE_HARDWARE && evsel->pmu && evsel->pmu->is_co= re && + evsel->alternate_hw_config =3D=3D config; + } + + if ((type =3D=3D PERF_TYPE_HARDWARE || type =3D=3D PERF_TYPE_HW_CACHE) && + perf_pmus__supports_extended_type()) + e_config &=3D PERF_HW_EVENT_MASK; + + return e_config =3D=3D config; +} + int evsel__read_counter(struct evsel *evsel, int cpu_map_idx, int thread) { u64 read_format =3D evsel->core.attr.read_format; diff --git a/tools/perf/util/evsel.h b/tools/perf/util/evsel.h index 517cff431de2..46e3589314f1 100644 --- a/tools/perf/util/evsel.h +++ b/tools/perf/util/evsel.h @@ -101,6 +101,7 @@ struct evsel { int bpf_fd; struct bpf_object *bpf_obj; struct list_head config_terms; + u64 alternate_hw_config; }; =20 /* @@ -354,26 +355,10 @@ u64 format_field__intval(struct tep_format_field *fie= ld, struct perf_sample *sam struct tep_format_field *evsel__field(struct evsel *evsel, const char *nam= e); struct tep_format_field *evsel__common_field(struct evsel *evsel, const ch= ar *name); =20 -static inline bool __evsel__match(const struct evsel *evsel, u32 type, u64= config) -{ - if (evsel->core.attr.type !=3D type) - return false; - - if ((type =3D=3D PERF_TYPE_HARDWARE || type =3D=3D PERF_TYPE_HW_CACHE) && - perf_pmus__supports_extended_type()) - return (evsel->core.attr.config & PERF_HW_EVENT_MASK) =3D=3D config; - - return evsel->core.attr.config =3D=3D config; -} +bool __evsel__match(const struct evsel *evsel, u32 type, u64 config); =20 #define evsel__match(evsel, t, c) __evsel__match(evsel, PERF_TYPE_##t, PER= F_COUNT_##c) =20 -static inline bool evsel__match2(struct evsel *e1, struct evsel *e2) -{ - return (e1->core.attr.type =3D=3D e2->core.attr.type) && - (e1->core.attr.config =3D=3D e2->core.attr.config); -} - int evsel__read_counter(struct evsel *evsel, int cpu_map_idx, int thread); =20 int __evsel__read_on_cpu(struct evsel *evsel, int cpu_map_idx, int thread,= bool scale); diff --git a/tools/perf/util/parse-events.c b/tools/perf/util/parse-events.c index 2b9ede311c31..c72e1722b1fb 100644 --- a/tools/perf/util/parse-events.c +++ b/tools/perf/util/parse-events.c @@ -230,7 +230,7 @@ __add_event(struct list_head *list, int *idx, bool init_attr, const char *name, const char *metric_id, struct perf_pmu *pmu, struct list_head *config_terms, bool auto_merge_stats, - const char *cpu_list) + const char *cpu_list, u64 alternate_hw_config) { struct evsel *evsel; struct perf_cpu_map *cpus =3D pmu ? perf_cpu_map__get(pmu->cpus) : @@ -266,6 +266,7 @@ __add_event(struct list_head *list, int *idx, evsel->auto_merge_stats =3D auto_merge_stats; evsel->pmu =3D pmu; evsel->pmu_name =3D pmu ? strdup(pmu->name) : NULL; + evsel->alternate_hw_config =3D alternate_hw_config; =20 if (name) evsel->name =3D strdup(name); @@ -288,16 +289,19 @@ struct evsel *parse_events__add_event(int idx, struct= perf_event_attr *attr, { return __add_event(/*list=3D*/NULL, &idx, attr, /*init_attr=3D*/false, na= me, metric_id, pmu, /*config_terms=3D*/NULL, - /*auto_merge_stats=3D*/false, /*cpu_list=3D*/NULL); + /*auto_merge_stats=3D*/false, /*cpu_list=3D*/NULL, + /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX); } =20 static int add_event(struct list_head *list, int *idx, struct perf_event_attr *attr, const char *name, - const char *metric_id, struct list_head *config_terms) + const char *metric_id, struct list_head *config_terms, + u64 alternate_hw_config) { return __add_event(list, idx, attr, /*init_attr*/true, name, metric_id, /*pmu=3D*/NULL, config_terms, - /*auto_merge_stats=3D*/false, /*cpu_list=3D*/NULL) ? 0 : -ENOMEM; + /*auto_merge_stats=3D*/false, /*cpu_list=3D*/NULL, + alternate_hw_config) ? 0 : -ENOMEM; } =20 static int add_event_tool(struct list_head *list, int *idx, @@ -312,7 +316,8 @@ static int add_event_tool(struct list_head *list, int *= idx, evsel =3D __add_event(list, idx, &attr, /*init_attr=3D*/true, /*name=3D*/= NULL, /*metric_id=3D*/NULL, /*pmu=3D*/NULL, /*config_terms=3D*/NULL, /*auto_merge_stats=3D*/false, - /*cpu_list=3D*/"0"); + /*cpu_list=3D*/"0", + /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX); if (!evsel) return -ENOMEM; evsel->tool_event =3D tool_event; @@ -446,7 +451,7 @@ bool parse_events__filter_pmu(const struct parse_events= _state *parse_state, static int parse_events_add_pmu(struct parse_events_state *parse_state, struct list_head *list, struct perf_pmu *pmu, const struct parse_events_terms *const_parsed_terms, - bool auto_merge_stats); + bool auto_merge_stats, u64 alternate_hw_config); =20 int parse_events_add_cache(struct list_head *list, int *idx, const char *n= ame, struct parse_events_state *parse_state, @@ -472,7 +477,8 @@ int parse_events_add_cache(struct list_head *list, int = *idx, const char *name, */ ret =3D parse_events_add_pmu(parse_state, list, pmu, parsed_terms, - perf_pmu__auto_merge_stats(pmu)); + perf_pmu__auto_merge_stats(pmu), + /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX); if (ret) return ret; continue; @@ -503,7 +509,8 @@ int parse_events_add_cache(struct list_head *list, int = *idx, const char *name, =20 if (__add_event(list, idx, &attr, /*init_attr*/true, config_name ?: name, metric_id, pmu, &config_terms, /*auto_merge_stats=3D*/false, - /*cpu_list=3D*/NULL) =3D=3D NULL) + /*cpu_list=3D*/NULL, + /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX) =3D=3D NULL) return -ENOMEM; =20 free_config_terms(&config_terms); @@ -743,7 +750,7 @@ int parse_events_add_breakpoint(struct parse_events_sta= te *parse_state, name =3D get_config_name(head_config); =20 return add_event(list, &parse_state->idx, &attr, name, /*mertic_id=3D*/NU= LL, - &config_terms); + &config_terms, /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX); } =20 static int check_type_val(struct parse_events_term *term, @@ -1043,6 +1050,7 @@ static int config_term_pmu(struct perf_event_attr *at= tr, if (perf_pmu__have_event(pmu, term->config)) { term->type_term =3D PARSE_EVENTS__TERM_TYPE_USER; term->no_value =3D true; + term->alternate_hw_config =3D true; } else { attr->type =3D PERF_TYPE_HARDWARE; attr->config =3D term->val.num; @@ -1354,8 +1362,9 @@ static int __parse_events_add_numeric(struct parse_ev= ents_state *parse_state, name =3D get_config_name(head_config); metric_id =3D get_config_metric_id(head_config); ret =3D __add_event(list, &parse_state->idx, &attr, /*init_attr*/true, na= me, - metric_id, pmu, &config_terms, /*auto_merge_stats=3D*/false, - /*cpu_list=3D*/NULL) ? 0 : -ENOMEM; + metric_id, pmu, &config_terms, /*auto_merge_stats=3D*/false, + /*cpu_list=3D*/NULL, /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX + ) =3D=3D NULL ? -ENOMEM : 0; free_config_terms(&config_terms); return ret; } @@ -1413,7 +1422,7 @@ static bool config_term_percore(struct list_head *con= fig_terms) static int parse_events_add_pmu(struct parse_events_state *parse_state, struct list_head *list, struct perf_pmu *pmu, const struct parse_events_terms *const_parsed_terms, - bool auto_merge_stats) + bool auto_merge_stats, u64 alternate_hw_config) { struct perf_event_attr attr; struct perf_pmu_info info; @@ -1450,7 +1459,7 @@ static int parse_events_add_pmu(struct parse_events_s= tate *parse_state, /*init_attr=3D*/true, /*name=3D*/NULL, /*metric_id=3D*/NULL, pmu, /*config_terms=3D*/NULL, auto_merge_stats, - /*cpu_list=3D*/NULL); + /*cpu_list=3D*/NULL, alternate_hw_config); return evsel ? 0 : -ENOMEM; } =20 @@ -1471,7 +1480,8 @@ static int parse_events_add_pmu(struct parse_events_s= tate *parse_state, =20 /* Look for event names in the terms and rewrite into format based terms.= */ if (!parse_state->fake_pmu && perf_pmu__check_alias(pmu, &parsed_terms, - &info, &alias_rewrote_terms, err)) { + &info, &alias_rewrote_terms, + &alternate_hw_config, err)) { parse_events_terms__exit(&parsed_terms); return -EINVAL; } @@ -1517,7 +1527,8 @@ static int parse_events_add_pmu(struct parse_events_s= tate *parse_state, evsel =3D __add_event(list, &parse_state->idx, &attr, /*init_attr=3D*/tru= e, get_config_name(&parsed_terms), get_config_metric_id(&parsed_terms), pmu, - &config_terms, auto_merge_stats, /*cpu_list=3D*/NULL); + &config_terms, auto_merge_stats, /*cpu_list=3D*/NULL, + alternate_hw_config); if (!evsel) { parse_events_terms__exit(&parsed_terms); return -ENOMEM; @@ -1596,7 +1607,7 @@ int parse_events_multi_pmu_add(struct parse_events_st= ate *parse_state, =20 auto_merge_stats =3D perf_pmu__auto_merge_stats(pmu); if (!parse_events_add_pmu(parse_state, list, pmu, - &parsed_terms, auto_merge_stats)) { + &parsed_terms, auto_merge_stats, hw_config)) { struct strbuf sb; =20 strbuf_init(&sb, /*hint=3D*/ 0); @@ -1611,7 +1622,7 @@ int parse_events_multi_pmu_add(struct parse_events_st= ate *parse_state, =20 if (parse_state->fake_pmu) { if (!parse_events_add_pmu(parse_state, list, parse_state->fake_pmu, &par= sed_terms, - /*auto_merge_stats=3D*/true)) { + /*auto_merge_stats=3D*/true, hw_config)) { struct strbuf sb; =20 strbuf_init(&sb, /*hint=3D*/ 0); @@ -1664,7 +1675,8 @@ int parse_events_multi_pmu_add_or_add_pmu(struct pars= e_events_state *parse_state /* Attempt to add to list assuming event_or_pmu is a PMU name. */ pmu =3D parse_state->fake_pmu ?: perf_pmus__find(event_or_pmu); if (pmu && !parse_events_add_pmu(parse_state, *listp, pmu, const_parsed_t= erms, - /*auto_merge_stats=3D*/false)) + /*auto_merge_stats=3D*/false, + /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX)) return 0; =20 pmu =3D NULL; @@ -1676,7 +1688,8 @@ int parse_events_multi_pmu_add_or_add_pmu(struct pars= e_events_state *parse_state =20 if (!parse_events_add_pmu(parse_state, *listp, pmu, const_parsed_terms, - auto_merge_stats)) { + auto_merge_stats, + /*alternate_hw_config=3D*/PERF_COUNT_HW_MAX)) { ok++; parse_state->wild_card_pmus =3D true; } diff --git a/tools/perf/util/parse-events.h b/tools/perf/util/parse-events.h index e7ac1f13376d..8dd426b8aeb9 100644 --- a/tools/perf/util/parse-events.h +++ b/tools/perf/util/parse-events.h @@ -127,6 +127,12 @@ struct parse_events_term { * value is assumed to be 1. An event name also has no value. */ bool no_value; + /** + * @alternate_hw_config: config is the event name but num is an + * alternate PERF_TYPE_HARDWARE config value which is often nice for the + * sake of quick matching. + */ + bool alternate_hw_config; }; =20 struct parse_events_error { diff --git a/tools/perf/util/pmu.c b/tools/perf/util/pmu.c index b3b072feef02..8f02fc5365aa 100644 --- a/tools/perf/util/pmu.c +++ b/tools/perf/util/pmu.c @@ -1547,7 +1547,7 @@ static int check_info_data(struct perf_pmu *pmu, */ int perf_pmu__check_alias(struct perf_pmu *pmu, struct parse_events_terms = *head_terms, struct perf_pmu_info *info, bool *rewrote_terms, - struct parse_events_error *err) + u64 *alternate_hw_config, struct parse_events_error *err) { struct parse_events_term *term, *h; struct perf_pmu_alias *alias; @@ -1575,6 +1575,7 @@ int perf_pmu__check_alias(struct perf_pmu *pmu, struc= t parse_events_terms *head_ NULL); return ret; } + *rewrote_terms =3D true; ret =3D check_info_data(pmu, alias, info, err, term->err_term); if (ret) @@ -1583,6 +1584,9 @@ int perf_pmu__check_alias(struct perf_pmu *pmu, struc= t parse_events_terms *head_ if (alias->per_pkg) info->per_pkg =3D true; =20 + if (term->alternate_hw_config) + *alternate_hw_config =3D term->val.num; + list_del_init(&term->list); parse_events_term__delete(term); } diff --git a/tools/perf/util/pmu.h b/tools/perf/util/pmu.h index 561716aa2b25..a4df58ce70ce 100644 --- a/tools/perf/util/pmu.h +++ b/tools/perf/util/pmu.h @@ -211,7 +211,7 @@ __u64 perf_pmu__format_bits(struct perf_pmu *pmu, const= char *name); int perf_pmu__format_type(struct perf_pmu *pmu, const char *name); int perf_pmu__check_alias(struct perf_pmu *pmu, struct parse_events_terms = *head_terms, struct perf_pmu_info *info, bool *rewrote_terms, - struct parse_events_error *err); + u64 *alternate_hw_config, struct parse_events_error *err); int perf_pmu__find_event(struct perf_pmu *pmu, const char *event, void *st= ate, pmu_event_callback cb); =20 void perf_pmu_format__set_value(void *format, int config, unsigned long *b= its); --=20 2.45.0.118.g7fe29c98d7-goog From nobody Sun Dec 14 12:02:53 2025 Received: from mail-yw1-f202.google.com (mail-yw1-f202.google.com [209.85.128.202]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id C365515E800 for ; Fri, 10 May 2024 05:38:09 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.128.202 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319491; cv=none; b=tJZan7rTgIWsfIhGQtJhFnDsQFJIeu214AvLfu6T/n47g83X06inz2sGf5Hf41FFt/ufr0KkRj2hshOPL56sQzfGEMb3uIk0V8gnales7z1FUzZLN6Jy3shRiYkV+sovUmAaeVq1tQOWszgU9D89pNiqLmu//G/VEEpVarLOrPE= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319491; c=relaxed/simple; bh=zNU/+vvLwssObyq665v420J21ONwE2lm3SPbdGLqo8o=; h=Date:In-Reply-To:Message-Id:Mime-Version:References:Subject:From: To:Content-Type; b=BWhpY0IUwRTV1/gg0cSwWMsDT9Ove+0YCybBrcj6O6j3lyxZ/gm5uiT9WuckfQxaGTM/F1hY3tKbZGO7ETdg5+tc0S0rzu8G3NI/IJ0oIzc5bTyeeCpH5P6c/YhNL4zuxhqANTzen7USy8+m54SVxzTFHWdwe9D/b1NENPaBh0E= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=E9Ay2NYv; arc=none smtp.client-ip=209.85.128.202 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="E9Ay2NYv" Received: by mail-yw1-f202.google.com with SMTP id 00721157ae682-61be4601434so30386637b3.3 for ; Thu, 09 May 2024 22:38:09 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1715319489; x=1715924289; darn=vger.kernel.org; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :from:to:cc:subject:date:message-id:reply-to; bh=U81cdFZOryTWzARq4P9O2qKcBTbob0BFWgpG3EYHhxM=; b=E9Ay2NYvkOyVjbvspBHGn2SUF5FAS5vWERXYyVUdbqm86SmN90aurIgG9tsiWqNGdT aKPQJQeEONSvpOTKNswD8nJgAXIEoyazcu7mJVk1HmVlnlz6pCdnbXtyDJDPib3akSwT mBfBFrGu3fWlSyNiMP58SosJ2KDMkNMHjqDriupJEt7IcIGM/kvJ40Q1Hy6OP2XJQ/Pk plxRkB0TFj/zzLaLYHxUlTaeILCBIpa9KsUZMydMSprsPl9rmyIKB1sqc1ngM4lr/KGX jGcJ3g5ffs1D1dZCqs4gLZRHAkJWWUGlqpBABK+eU1kYrD9W6qrfGV2ADgRz3Uey8xEy +S4g== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1715319489; x=1715924289; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=U81cdFZOryTWzARq4P9O2qKcBTbob0BFWgpG3EYHhxM=; b=Pj7zcgiTQdHyQoy7ERCxXriY/UdnGbd+ZcA3RofYkEHw6GS8Qf/n+pPONIACyjTLqp 7+PLLggt60N6lxP5GJKg9I4DmP5Elf8zFmp4t+JJ+fNZA9zuRwVGwqXVX7h23a9BLZiQ DHO5lCbDzMxipcrcsOxNEb9ufyqA30ZGLe1imq0o+iEYbVL1AX0WbzmG9fEgJS1q2tI0 Sk+vjzzpyjvI2JMIWNI1YI8Cn/c+zHUB9Tl/rhD7nhFj1zLGTq9NjhqoWATsvKFnJIzt Fu1byDHd/7qjW9ngZtJr7TuUJFzk39MbD/2b9xWKZT5JF1FvcV8HVsFlbqEmPyreuq1r od5w== X-Forwarded-Encrypted: i=1; AJvYcCUPN85lkyLcDe9c3Lq8hj/YmxqbevQb0HZvVgDo8H2mv5VDixS4MfaTw4+Ih4JGS2NCc8Spa2b3qaLJ8qwjr3mwLrvWHZaqCGPTItaD X-Gm-Message-State: AOJu0Yz3m9EJbn2ozVTj9dhdasQzbyy6y7egJHZhXRnLMTqIdkXuG0Ks umMUMLCJZ/npgkPowrgLHmiywg+eOpwKecuGBVJzcjgXSKbnuKRC0aDjciQFf9ZR5ihtq6+RBeR F7CH6jw== X-Google-Smtp-Source: AGHT+IFRjnvnZQt14aMD9YvF6AMr7sQg6gNtp9//xebqaPSpiEn6kA1W44VXfwdCT4L4dEfFyxzpxvgkU6NV X-Received: from irogers.svl.corp.google.com ([2620:15c:2a3:200:79ed:c375:51e3:ed39]) (user=irogers job=sendgmr) by 2002:a05:690c:284:b0:614:f416:9415 with SMTP id 00721157ae682-622b0163084mr4450367b3.7.1715319488741; Thu, 09 May 2024 22:38:08 -0700 (PDT) Date: Thu, 9 May 2024 22:37:02 -0700 In-Reply-To: <20240510053705.2462258-1-irogers@google.com> Message-Id: <20240510053705.2462258-3-irogers@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20240510053705.2462258-1-irogers@google.com> X-Mailer: git-send-email 2.45.0.118.g7fe29c98d7-goog Subject: [PATCH v3 2/5] perf stat: Uniquify event name improvements From: Ian Rogers To: Peter Zijlstra , Ingo Molnar , Arnaldo Carvalho de Melo , Namhyung Kim , Mark Rutland , Alexander Shishkin , Jiri Olsa , Ian Rogers , Adrian Hunter , Kan Liang , Ravi Bangoria , James Clark , Yang Jihong , Ze Gao , Leo Yan , Song Liu , K Prateek Nayak , Kaige Ye , Yicong Yang , linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Without aggregation on Intel: ``` $ perf stat -e instructions,cycles ... ``` Will use "cycles" for the name of the legacy cycles event but as "instructions" has a sysfs name it will and a "[cpu]" PMU suffix. This often breaks things as the space between the event and the PMU name look like an extra column. The existing uniquify logic was also uniquifying in cases when all events are core and not with uncore events, it was not correctly handling modifiers, etc. Change the logic so that an initial pass that can disable uniquification is run. For individual counters, disable uniquification in more cases such as for consistency with legacy events or for libpfm4 events. Don't use the "[pmu]" style suffix in uniquification, always use "pmu/.../". Change how modifiers/terms are handled in the uniquification so that they look like parse-able events. This fixes "102: perf stat metrics (shadow stat) test:" that has been failing due to "instructions [cpu]" breaking its column/awk logic when values aren't aggregated. This started happening when instructions could match a sysfs rather than a legacy event, so the fixes tag reflects this. Fixes: 617824a7f0f7 ("perf parse-events: Prefer sysfs/JSON hardware events = over legacy") Signed-off-by: Ian Rogers --- tools/perf/util/stat-display.c | 101 +++++++++++++++++++++++++-------- 1 file changed, 78 insertions(+), 23 deletions(-) diff --git a/tools/perf/util/stat-display.c b/tools/perf/util/stat-display.c index bfc1d705f437..ea11e3437444 100644 --- a/tools/perf/util/stat-display.c +++ b/tools/perf/util/stat-display.c @@ -868,38 +868,66 @@ static void printout(struct perf_stat_config *config,= struct outstate *os, =20 static void uniquify_event_name(struct evsel *counter) { - char *new_name; - char *config; - int ret =3D 0; + const char *name, *pmu_name; + char *new_name, *config; + int ret; =20 - if (counter->uniquified_name || counter->use_config_name || - !counter->pmu_name || !strncmp(evsel__name(counter), counter->pmu_nam= e, - strlen(counter->pmu_name))) + /* The evsel was already uniquified. */ + if (counter->uniquified_name) return; =20 - config =3D strchr(counter->name, '/'); + /* Avoid checking to uniquify twice. */ + counter->uniquified_name =3D true; + + /* The evsel has a "name=3D" config term or is from libpfm. */ + if (counter->use_config_name || counter->is_libpfm_event) + return; + + /* Legacy no PMU event, don't uniquify. */ + if (!counter->pmu || + (counter->pmu->type < PERF_TYPE_MAX && counter->pmu->type !=3D PERF_= TYPE_RAW)) + return; + + /* A sysfs or json event replacing a legacy event, don't uniquify. */ + if (counter->pmu->is_core && counter->alternate_hw_config !=3D PERF_COUNT= _HW_MAX) + return; + + name =3D evsel__name(counter); + pmu_name =3D counter->pmu->name; + /* Already prefixed by the PMU name. */ + if (!strncmp(name, pmu_name, strlen(pmu_name))) + return; + + config =3D strchr(name, '/'); if (config) { - if (asprintf(&new_name, - "%s%s", counter->pmu_name, config) > 0) { - free(counter->name); - counter->name =3D new_name; - } - } else { - if (evsel__is_hybrid(counter)) { - ret =3D asprintf(&new_name, "%s/%s/", - counter->pmu_name, counter->name); + int len =3D config - name; + + if (config[1] =3D=3D '/') { + /* case: event// */ + ret =3D asprintf(&new_name, "%s/%.*s/%s", pmu_name, len, name, config += 2); } else { - ret =3D asprintf(&new_name, "%s [%s]", - counter->name, counter->pmu_name); + /* case: event/.../ */ + ret =3D asprintf(&new_name, "%s/%.*s,%s", pmu_name, len, name, config += 1); } + } else { + config =3D strchr(name, ':'); + if (config) { + /* case: event:.. */ + int len =3D config - name; =20 - if (ret) { - free(counter->name); - counter->name =3D new_name; + ret =3D asprintf(&new_name, "%s/%.*s/%s", pmu_name, len, name, config += 1); + } else { + /* case: event */ + ret =3D asprintf(&new_name, "%s/%s/", pmu_name, name); } } - - counter->uniquified_name =3D true; + if (ret > 0) { + free(counter->name); + counter->name =3D new_name; + } else { + /* ENOMEM from asprintf. */ + counter->uniquified_name =3D false; + } } =20 static bool hybrid_uniquify(struct evsel *evsel, struct perf_stat_config *= config) @@ -1541,6 +1569,31 @@ static void print_cgroup_counter(struct perf_stat_co= nfig *config, struct evlist print_metric_end(config, os); } =20 +static void disable_uniquify(struct evlist *evlist) +{ + struct evsel *counter; + struct perf_pmu *last_pmu =3D NULL; + bool first =3D true; + + evlist__for_each_entry(evlist, counter) { + /* If PMUs vary then uniquify can be useful. */ + if (!first && counter->pmu !=3D last_pmu) + return; + first =3D false; + if (counter->pmu) { + /* Allow uniquify for uncore PMUs. */ + if (!counter->pmu->is_core) + return; + /* Keep hybrid event names uniquified for clarity. */ + if (perf_pmus__num_core_pmus() > 1) + return; + } + } + evlist__for_each_entry_continue(evlist, counter) { + counter->uniquified_name =3D true; + } +} + void evlist__print_counters(struct evlist *evlist, struct perf_stat_config= *config, struct target *_target, struct timespec *ts, int argc, const char **argv) @@ -1554,6 +1607,8 @@ void evlist__print_counters(struct evlist *evlist, st= ruct perf_stat_config *conf .first =3D true, }; =20 + disable_uniquify(evlist); + if (config->iostat_run) evlist->selected =3D evlist__first(evlist); =20 --=20 2.45.0.118.g7fe29c98d7-goog From nobody Sun Dec 14 12:02:53 2025 Received: from mail-yw1-f201.google.com (mail-yw1-f201.google.com [209.85.128.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 1245E1607A8 for ; Fri, 10 May 2024 05:38:11 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.128.201 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319494; cv=none; b=Hy7M7ydCqQwGlNHPEc+9L93/UqBxOu8IiQn/0V1WveB0ZiJMmbtjF3s9dXAR1wHU1tbQLVQh/GACo6KgzubgZ+vVxja8XvzJud1ynqb7BbCyKkBs19oHP9wveVOs5lWJwuDnjskCQUo+XbuTwSZJFDLBJYLMBFFvEPVBDTrare4= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319494; c=relaxed/simple; bh=PgcIXM8GrKKDGkwx22khJ5WaAGU9MxwL4zfLCpkfP0U=; h=Date:In-Reply-To:Message-Id:Mime-Version:References:Subject:From: To:Content-Type; b=GNf/aU0zOPUfWDvVv+wmCqgpBHMUW0BMqgnuAaN8vidyNaqpYhVuC80+CgBQnpWc45KK6B+NiHkUUn3G80bpmCRuXvrnkvSP791//Q2vee7/guMC9zlsMrkAI6NAHjSNay8MRKNuBza6PsCKptKUHWKCxODc5HlalYz1npHmqhU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=WwBiXuAM; arc=none smtp.client-ip=209.85.128.201 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="WwBiXuAM" Received: by mail-yw1-f201.google.com with SMTP id 00721157ae682-6204c4f4240so24970287b3.3 for ; Thu, 09 May 2024 22:38:11 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1715319491; x=1715924291; darn=vger.kernel.org; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :from:to:cc:subject:date:message-id:reply-to; bh=FlqknsHKKIGFlacVLAcRcLtuVwmZ+sPk6Aq264GDY2o=; b=WwBiXuAMcEBba1bWTfYy9ZYM7rSKzAjpPChgAr6a7RvHL5he/ahlfhOs9Y8EtAOlh8 ip1A6W5w8b4FCG1TUO26+3l/J4cFwZMMIphDM4WpiGtIs4ZeBqPHM5wd1127VfZJEPNf TBhjSLIUUNn/25BA1OeUyqtFS+LPNRNEKvLu5DLvZjoltLtmCR4fVK4SH4UTuKoXcPVM HIXe0MaCOIuxjxECfENCKtfvOoQnnjvROexzpy3TV0TQWrjGjvbHRJQWm9b6Ikl6AWtF ZLoABCRC1nlxP74jnblqe+Y6T32yFlTBTzz3fdJAyVeK8F4K68Lrc1qCHVYMF+X9s1jS Z7mw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1715319491; x=1715924291; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=FlqknsHKKIGFlacVLAcRcLtuVwmZ+sPk6Aq264GDY2o=; b=oQufGfd1rFAFX3SUm4XOJpyX0/4kiRy22VTHm9t8T+cbursfxyXBzn3T+H2OZbiXSW kL97T8x7w07jttkkn/TRoSdp2Ljk2Ve9NFvkqTmNBH1XLEWNc76r5fHCuZXhiCsOm0QZ igsPIs5vmN3d7i4HDqkyI1CqAN0z5+1IdmI+XGZ9+dHSRgG+N2rfdaPQDlB9+TsNTYnH SODGWikEcDrILTJHmIjaJkBMDRBjuLkye4jw8sPUiyDghcJUrZhvR1WIDyyr6+cHKqfR r1iDI505twcrgL5uU1nZarT8/HlKLDyKAG+hcNEQfZkch3m9P09yCRoezBtK01UzfIee Bu4Q== X-Forwarded-Encrypted: i=1; AJvYcCXxRh/UWn6J+OqjgCwb6kn0dY+wm9nRQbdVdJ7fI0VnWaHRYhoUtauq8XkkE8HZWu6fe5UpYilp6dQEHMOH4bxyuyWBhAYrL7hnHptW X-Gm-Message-State: AOJu0YyvytpYELaparibGdmC6xVOZtkcZ4TVL3VHWeorzeKvAwyaXnzm okRcnxRgkf8UDwVhiB7IFEN20JNzQHmYCFjH2uUbhA8b5DHjswE8tR4/3UFSERWl1BffcL1Nntt ohvbarw== X-Google-Smtp-Source: AGHT+IGGtRcP1zxVW6voY7Vo4i/vJ6R6NHhlJPUh2gdK+l0Xj9c0mygLm66G+niYKxHSRjiSMqMJxNFWX8qL X-Received: from irogers.svl.corp.google.com ([2620:15c:2a3:200:79ed:c375:51e3:ed39]) (user=irogers job=sendgmr) by 2002:a05:690c:284:b0:61b:982:4da0 with SMTP id 00721157ae682-622afd3697cmr4610267b3.0.1715319491168; Thu, 09 May 2024 22:38:11 -0700 (PDT) Date: Thu, 9 May 2024 22:37:03 -0700 In-Reply-To: <20240510053705.2462258-1-irogers@google.com> Message-Id: <20240510053705.2462258-4-irogers@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20240510053705.2462258-1-irogers@google.com> X-Mailer: git-send-email 2.45.0.118.g7fe29c98d7-goog Subject: [PATCH v3 3/5] perf stat: Remove evlist__add_default_attrs use strings From: Ian Rogers To: Peter Zijlstra , Ingo Molnar , Arnaldo Carvalho de Melo , Namhyung Kim , Mark Rutland , Alexander Shishkin , Jiri Olsa , Ian Rogers , Adrian Hunter , Kan Liang , Ravi Bangoria , James Clark , Yang Jihong , Ze Gao , Leo Yan , Song Liu , K Prateek Nayak , Kaige Ye , Yicong Yang , linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" add_default_atttributes would add evsels by having pre-created perf_event_attr, however, this needed fixing for hybrid as the extended PMU type was necessary for each core PMU. The logic for this was in an arch specific x86 function and wasn't present for ARM, meaning that default events weren't being opened on all PMUs on ARM. Change the creation of the default events to use parse_events and strings as that will open the events on all PMUs. Rather than try to detect events on PMUs before parsing, parse the event but skip its output in stat-display. The previous order of hardware events was: cycles, stalled-cycles-frontend, stalled-cycles-backend, instructions. As instructions is a more fundamental concept the order is changed to: instructions, cycles, stalled-cycles-frontend, stalled-cycles-backend. Closes: https://lore.kernel.org/lkml/CAP-5=3DfVABSBZnsmtRn1uF-k-G1GWM-L5Sgi= inhPTfHbQsKXb_g@mail.gmail.com/ Signed-off-by: Ian Rogers Reviewed-by: Kan Liang --- tools/perf/arch/x86/util/evlist.c | 74 +------- tools/perf/builtin-stat.c | 291 ++++++++++++------------------ tools/perf/util/evlist.c | 43 ----- tools/perf/util/evlist.h | 12 -- tools/perf/util/stat-shadow.c | 4 +- 5 files changed, 117 insertions(+), 307 deletions(-) diff --git a/tools/perf/arch/x86/util/evlist.c b/tools/perf/arch/x86/util/e= vlist.c index b1ce0c52d88d..fb8e314aa364 100644 --- a/tools/perf/arch/x86/util/evlist.c +++ b/tools/perf/arch/x86/util/evlist.c @@ -1,78 +1,10 @@ // SPDX-License-Identifier: GPL-2.0 -#include -#include "util/pmu.h" -#include "util/pmus.h" -#include "util/evlist.h" -#include "util/parse-events.h" -#include "util/event.h" +#include +#include "../../../util/evlist.h" +#include "../../../util/evsel.h" #include "topdown.h" #include "evsel.h" =20 -static int ___evlist__add_default_attrs(struct evlist *evlist, - struct perf_event_attr *attrs, - size_t nr_attrs) -{ - LIST_HEAD(head); - size_t i =3D 0; - - for (i =3D 0; i < nr_attrs; i++) - event_attr_init(attrs + i); - - if (perf_pmus__num_core_pmus() =3D=3D 1) - return evlist__add_attrs(evlist, attrs, nr_attrs); - - for (i =3D 0; i < nr_attrs; i++) { - struct perf_pmu *pmu =3D NULL; - - if (attrs[i].type =3D=3D PERF_TYPE_SOFTWARE) { - struct evsel *evsel =3D evsel__new(attrs + i); - - if (evsel =3D=3D NULL) - goto out_delete_partial_list; - list_add_tail(&evsel->core.node, &head); - continue; - } - - while ((pmu =3D perf_pmus__scan_core(pmu)) !=3D NULL) { - struct perf_cpu_map *cpus; - struct evsel *evsel; - - evsel =3D evsel__new(attrs + i); - if (evsel =3D=3D NULL) - goto out_delete_partial_list; - evsel->core.attr.config |=3D (__u64)pmu->type << PERF_PMU_TYPE_SHIFT; - cpus =3D perf_cpu_map__get(pmu->cpus); - evsel->core.cpus =3D cpus; - evsel->core.own_cpus =3D perf_cpu_map__get(cpus); - evsel->pmu_name =3D strdup(pmu->name); - list_add_tail(&evsel->core.node, &head); - } - } - - evlist__splice_list_tail(evlist, &head); - - return 0; - -out_delete_partial_list: - { - struct evsel *evsel, *n; - - __evlist__for_each_entry_safe(&head, n, evsel) - evsel__delete(evsel); - } - return -1; -} - -int arch_evlist__add_default_attrs(struct evlist *evlist, - struct perf_event_attr *attrs, - size_t nr_attrs) -{ - if (!nr_attrs) - return 0; - - return ___evlist__add_default_attrs(evlist, attrs, nr_attrs); -} - int arch_evlist__cmp(const struct evsel *lhs, const struct evsel *rhs) { if (topdown_sys_has_perf_metrics() && diff --git a/tools/perf/builtin-stat.c b/tools/perf/builtin-stat.c index 35f79b48e8dc..758e22576b30 100644 --- a/tools/perf/builtin-stat.c +++ b/tools/perf/builtin-stat.c @@ -1934,130 +1934,25 @@ static int perf_stat_init_aggr_mode_file(struct pe= rf_stat *st) } =20 /* - * Add default attributes, if there were no attributes specified or + * Add default events, if there were no attributes specified or * if -d/--detailed, -d -d or -d -d -d is used: */ -static int add_default_attributes(void) +static int add_default_events(void) { - struct perf_event_attr default_attrs0[] =3D { - - { .type =3D PERF_TYPE_SOFTWARE, .config =3D PERF_COUNT_SW_TASK_CLOCK }, - { .type =3D PERF_TYPE_SOFTWARE, .config =3D PERF_COUNT_SW_CONTEXT_SWITCH= ES }, - { .type =3D PERF_TYPE_SOFTWARE, .config =3D PERF_COUNT_SW_CPU_MIGRATIONS= }, - { .type =3D PERF_TYPE_SOFTWARE, .config =3D PERF_COUNT_SW_PAGE_FAULTS }, - - { .type =3D PERF_TYPE_HARDWARE, .config =3D PERF_COUNT_HW_CPU_CYCLES }, -}; - struct perf_event_attr frontend_attrs[] =3D { - { .type =3D PERF_TYPE_HARDWARE, .config =3D PERF_COUNT_HW_STALLED_CYCLES= _FRONTEND }, -}; - struct perf_event_attr backend_attrs[] =3D { - { .type =3D PERF_TYPE_HARDWARE, .config =3D PERF_COUNT_HW_STALLED_CYCLES= _BACKEND }, -}; - struct perf_event_attr default_attrs1[] =3D { - { .type =3D PERF_TYPE_HARDWARE, .config =3D PERF_COUNT_HW_INSTRUCTIONS = }, - { .type =3D PERF_TYPE_HARDWARE, .config =3D PERF_COUNT_HW_BRANCH_INSTRUC= TIONS }, - { .type =3D PERF_TYPE_HARDWARE, .config =3D PERF_COUNT_HW_BRANCH_MISSES = }, - -}; - -/* - * Detailed stats (-d), covering the L1 and last level data caches: - */ - struct perf_event_attr detailed_attrs[] =3D { - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_L1D << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_ACCESS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_L1D << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_MISS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_LL << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_ACCESS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_LL << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_MISS << 16) }, -}; - -/* - * Very detailed stats (-d -d), covering the instruction cache and the TLB= caches: - */ - struct perf_event_attr very_detailed_attrs[] =3D { - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_L1I << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_ACCESS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_L1I << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_MISS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_DTLB << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_ACCESS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_DTLB << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_MISS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_ITLB << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_ACCESS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_ITLB << 0 | - (PERF_COUNT_HW_CACHE_OP_READ << 8) | - (PERF_COUNT_HW_CACHE_RESULT_MISS << 16) }, - -}; + const char *pmu =3D parse_events_option_args.pmu_filter ?: "all"; + struct parse_events_error err; + struct evlist *evlist =3D evlist__new(); + struct evsel *evsel; + int ret =3D 0; =20 -/* - * Very, very detailed stats (-d -d -d), adding prefetch events: - */ - struct perf_event_attr very_very_detailed_attrs[] =3D { - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_L1D << 0 | - (PERF_COUNT_HW_CACHE_OP_PREFETCH << 8) | - (PERF_COUNT_HW_CACHE_RESULT_ACCESS << 16) }, - - { .type =3D PERF_TYPE_HW_CACHE, - .config =3D - PERF_COUNT_HW_CACHE_L1D << 0 | - (PERF_COUNT_HW_CACHE_OP_PREFETCH << 8) | - (PERF_COUNT_HW_CACHE_RESULT_MISS << 16) }, -}; + if (!evlist) + return -ENOMEM; =20 - struct perf_event_attr default_null_attrs[] =3D {}; - const char *pmu =3D parse_events_option_args.pmu_filter ?: "all"; + parse_events_error__init(&err); =20 /* Set attrs if no event is selected and !null_run: */ if (stat_config.null_run) - return 0; + goto out; =20 if (transaction_run) { /* Handle -T as -M transaction. Once platform specific metrics @@ -2067,9 +1962,10 @@ static int add_default_attributes(void) */ if (!metricgroup__has_metric(pmu, "transaction")) { pr_err("Missing transaction metrics\n"); - return -1; + ret =3D -1; + goto out; } - return metricgroup__parse_groups(evsel_list, pmu, "transaction", + ret =3D metricgroup__parse_groups(evlist, pmu, "transaction", stat_config.metric_no_group, stat_config.metric_no_merge, stat_config.metric_no_threshold, @@ -2077,6 +1973,7 @@ static int add_default_attributes(void) stat_config.system_wide, stat_config.hardware_aware_grouping, &stat_config.metric_events); + goto out; } =20 if (smi_cost) { @@ -2084,26 +1981,29 @@ static int add_default_attributes(void) =20 if (sysfs__read_int(FREEZE_ON_SMI_PATH, &smi) < 0) { pr_err("freeze_on_smi is not supported.\n"); - return -1; + ret =3D -1; + goto out; } =20 if (!smi) { if (sysfs__write_int(FREEZE_ON_SMI_PATH, 1) < 0) { - fprintf(stderr, "Failed to set freeze_on_smi.\n"); - return -1; + pr_err("Failed to set freeze_on_smi.\n"); + ret =3D -1; + goto out; } smi_reset =3D true; } =20 if (!metricgroup__has_metric(pmu, "smi")) { pr_err("Missing smi metrics\n"); - return -1; + ret =3D -1; + goto out; } =20 if (!force_metric_only) stat_config.metric_only =3D true; =20 - return metricgroup__parse_groups(evsel_list, pmu, "smi", + ret =3D metricgroup__parse_groups(evlist, pmu, "smi", stat_config.metric_no_group, stat_config.metric_no_merge, stat_config.metric_no_threshold, @@ -2111,6 +2011,7 @@ static int add_default_attributes(void) stat_config.system_wide, stat_config.hardware_aware_grouping, &stat_config.metric_events); + goto out; } =20 if (topdown_run) { @@ -2123,21 +2024,23 @@ static int add_default_attributes(void) if (!max_level) { pr_err("Topdown requested but the topdown metric groups aren't present.= \n" "(See perf list the metric groups have names like TopdownL1)\n"); - return -1; + ret =3D -1; + goto out; } if (stat_config.topdown_level > max_level) { pr_err("Invalid top-down metrics level. The max level is %u.\n", max_le= vel); - return -1; - } else if (!stat_config.topdown_level) + ret =3D -1; + goto out; + } else if (!stat_config.topdown_level) { stat_config.topdown_level =3D 1; - + } if (!stat_config.interval && !stat_config.metric_only) { fprintf(stat_config.output, "Topdown accuracy may decrease when measuring long periods.\n" "Please print the result regularly, e.g. -I1000\n"); } str[8] =3D stat_config.topdown_level + '0'; - if (metricgroup__parse_groups(evsel_list, + if (metricgroup__parse_groups(evlist, pmu, str, /*metric_no_group=3D*/false, /*metric_no_merge=3D*/false, @@ -2145,41 +2048,49 @@ static int add_default_attributes(void) stat_config.user_requested_cpu_list, stat_config.system_wide, stat_config.hardware_aware_grouping, - &stat_config.metric_events) < 0) - return -1; + &stat_config.metric_events) < 0) { + ret =3D -1; + goto out; + } } =20 if (!stat_config.topdown_level) stat_config.topdown_level =3D 1; =20 - if (!evsel_list->core.nr_entries) { + if (!evlist->core.nr_entries && !evsel_list->core.nr_entries) { /* No events so add defaults. */ if (target__has_cpu(&target)) - default_attrs0[0].config =3D PERF_COUNT_SW_CPU_CLOCK; + ret =3D parse_events(evlist, "cpu-clock", &err); + else + ret =3D parse_events(evlist, "task-clock", &err); + if (ret) + goto out; + + ret =3D parse_events(evlist, + "context-switches," + "cpu-migrations," + "page-faults," + "instructions," + "cycles," + "stalled-cycles-frontend," + "stalled-cycles-backend," + "branches," + "branch-misses", + &err); + if (ret) + goto out; =20 - if (evlist__add_default_attrs(evsel_list, default_attrs0) < 0) - return -1; - if (perf_pmus__have_event("cpu", "stalled-cycles-frontend")) { - if (evlist__add_default_attrs(evsel_list, frontend_attrs) < 0) - return -1; - } - if (perf_pmus__have_event("cpu", "stalled-cycles-backend")) { - if (evlist__add_default_attrs(evsel_list, backend_attrs) < 0) - return -1; - } - if (evlist__add_default_attrs(evsel_list, default_attrs1) < 0) - return -1; /* * Add TopdownL1 metrics if they exist. To minimize * multiplexing, don't request threshold computation. */ if (metricgroup__has_metric(pmu, "Default")) { struct evlist *metric_evlist =3D evlist__new(); - struct evsel *metric_evsel; - - if (!metric_evlist) - return -1; =20 + if (!metric_evlist) { + ret =3D -ENOMEM; + goto out; + } if (metricgroup__parse_groups(metric_evlist, pmu, "Default", /*metric_no_group=3D*/false, /*metric_no_merge=3D*/false, @@ -2187,43 +2098,65 @@ static int add_default_attributes(void) stat_config.user_requested_cpu_list, stat_config.system_wide, stat_config.hardware_aware_grouping, - &stat_config.metric_events) < 0) - return -1; - - evlist__for_each_entry(metric_evlist, metric_evsel) { - metric_evsel->skippable =3D true; - metric_evsel->default_metricgroup =3D true; + &stat_config.metric_events) < 0) { + ret =3D -1; + goto out; } - evlist__splice_list_tail(evsel_list, &metric_evlist->core.entries); + + evlist__for_each_entry(metric_evlist, evsel) + evsel->default_metricgroup =3D true; + + evlist__splice_list_tail(evlist, &metric_evlist->core.entries); evlist__delete(metric_evlist); } - - /* Platform specific attrs */ - if (evlist__add_default_attrs(evsel_list, default_null_attrs) < 0) - return -1; } =20 /* Detailed events get appended to the event list: */ =20 - if (detailed_run < 1) - return 0; - - /* Append detailed run extra attributes: */ - if (evlist__add_default_attrs(evsel_list, detailed_attrs) < 0) - return -1; - - if (detailed_run < 2) - return 0; - - /* Append very detailed run extra attributes: */ - if (evlist__add_default_attrs(evsel_list, very_detailed_attrs) < 0) - return -1; - - if (detailed_run < 3) - return 0; - - /* Append very, very detailed run extra attributes: */ - return evlist__add_default_attrs(evsel_list, very_very_detailed_attrs); + if (!ret && detailed_run >=3D 1) { + /* + * Detailed stats (-d), covering the L1 and last level data + * caches: + */ + ret =3D parse_events(evlist, + "L1-dcache-loads," + "L1-dcache-load-misses," + "LLC-loads," + "LLC-load-misses", + &err); + } + if (!ret && detailed_run >=3D 2) { + /* + * Very detailed stats (-d -d), covering the instruction cache + * and the TLB caches: + */ + ret =3D parse_events(evlist, + "L1-icache-loads," + "L1-icache-load-misses," + "dTLB-loads," + "dTLB-load-misses," + "iTLB-loads," + "iTLB-load-misses", + &err); + } + if (!ret && detailed_run >=3D 3) { + /* + * Very, very detailed stats (-d -d -d), adding prefetch events: + */ + ret =3D parse_events(evlist, + "L1-dcache-prefetches," + "L1-dcache-prefetch-misses", + &err); + } +out: + if (!ret) { + evlist__for_each_entry(evlist, evsel) + evsel->skippable =3D true; + } + parse_events_error__exit(&err); + evlist__splice_list_tail(evsel_list, &evlist->core.entries); + evlist__delete(evlist); + return ret; } =20 static const char * const stat_record_usage[] =3D { @@ -2731,7 +2664,7 @@ int cmd_stat(int argc, const char **argv) } } =20 - if (add_default_attributes()) + if (add_default_events()) goto out; =20 if (stat_config.cgroup_list) { diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c index 55a300a0977b..de498ba5ac1c 100644 --- a/tools/perf/util/evlist.c +++ b/tools/perf/util/evlist.c @@ -314,49 +314,6 @@ struct evsel *evlist__add_sched_switch(struct evlist *= evlist, bool system_wide) } #endif =20 -int evlist__add_attrs(struct evlist *evlist, struct perf_event_attr *attrs= , size_t nr_attrs) -{ - struct evsel *evsel, *n; - LIST_HEAD(head); - size_t i; - - for (i =3D 0; i < nr_attrs; i++) { - evsel =3D evsel__new_idx(attrs + i, evlist->core.nr_entries + i); - if (evsel =3D=3D NULL) - goto out_delete_partial_list; - list_add_tail(&evsel->core.node, &head); - } - - evlist__splice_list_tail(evlist, &head); - - return 0; - -out_delete_partial_list: - __evlist__for_each_entry_safe(&head, n, evsel) - evsel__delete(evsel); - return -1; -} - -int __evlist__add_default_attrs(struct evlist *evlist, struct perf_event_a= ttr *attrs, size_t nr_attrs) -{ - size_t i; - - for (i =3D 0; i < nr_attrs; i++) - event_attr_init(attrs + i); - - return evlist__add_attrs(evlist, attrs, nr_attrs); -} - -__weak int arch_evlist__add_default_attrs(struct evlist *evlist, - struct perf_event_attr *attrs, - size_t nr_attrs) -{ - if (!nr_attrs) - return 0; - - return __evlist__add_default_attrs(evlist, attrs, nr_attrs); -} - struct evsel *evlist__find_tracepoint_by_id(struct evlist *evlist, int id) { struct evsel *evsel; diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h index cb91dc9117a2..947a78cbd7f0 100644 --- a/tools/perf/util/evlist.h +++ b/tools/perf/util/evlist.h @@ -100,18 +100,6 @@ void evlist__delete(struct evlist *evlist); void evlist__add(struct evlist *evlist, struct evsel *entry); void evlist__remove(struct evlist *evlist, struct evsel *evsel); =20 -int evlist__add_attrs(struct evlist *evlist, struct perf_event_attr *attrs= , size_t nr_attrs); - -int __evlist__add_default_attrs(struct evlist *evlist, - struct perf_event_attr *attrs, size_t nr_attrs); - -int arch_evlist__add_default_attrs(struct evlist *evlist, - struct perf_event_attr *attrs, - size_t nr_attrs); - -#define evlist__add_default_attrs(evlist, array) \ - arch_evlist__add_default_attrs(evlist, array, ARRAY_SIZE(array)) - int arch_evlist__cmp(const struct evsel *lhs, const struct evsel *rhs); =20 int evlist__add_dummy(struct evlist *evlist); diff --git a/tools/perf/util/stat-shadow.c b/tools/perf/util/stat-shadow.c index 3466aa952442..ffdd53a07654 100644 --- a/tools/perf/util/stat-shadow.c +++ b/tools/perf/util/stat-shadow.c @@ -76,7 +76,7 @@ void perf_stat__reset_shadow_stats(void) memset(&ru_stats, 0, sizeof(ru_stats)); } =20 -static enum stat_type evsel__stat_type(const struct evsel *evsel) +static enum stat_type evsel__stat_type(struct evsel *evsel) { /* Fake perf_hw_cache_op_id values for use with evsel__match. */ u64 PERF_COUNT_hw_cache_l1d_miss =3D PERF_COUNT_HW_CACHE_L1D | @@ -152,7 +152,7 @@ static const char *get_ratio_color(const double ratios[= 3], double val) =20 static double find_stat(const struct evsel *evsel, int aggr_idx, enum stat= _type type) { - const struct evsel *cur; + struct evsel *cur; int evsel_ctx =3D evsel_context(evsel); =20 evlist__for_each_entry(evsel->evlist, cur) { --=20 2.45.0.118.g7fe29c98d7-goog From nobody Sun Dec 14 12:02:53 2025 Received: from mail-yw1-f202.google.com (mail-yw1-f202.google.com [209.85.128.202]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 592ED16132C for ; Fri, 10 May 2024 05:38:14 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.128.202 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319495; cv=none; b=Njs66bkcnEluwblu0Pl61wWkRfLMQyo9IB/02f6ZHSN74gMbbo3WI0GPSsDn3akih52XO1IeSCadWk3873qPLw2mjYP6PJGJ/x97KRaFrpW7Kt3GlsW/b5UVyJ/7sXZalMQmZtZggKP1OfBDXOYzf5/v/rFTfv+DA4kghmEVMw4= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319495; c=relaxed/simple; bh=vw95n4rn5vnmJbH7gGbwuIcX3seEX/vyVpcGLsRC0No=; h=Date:In-Reply-To:Message-Id:Mime-Version:References:Subject:From: To:Content-Type; b=JAlgD+IwZpgGUBhn9z+fqVMWr//t93aV5mdCIbT3PCKror7ikdIq34QLdiWuxv1vnnKmCPRpOYi5MlF5gDk59RqTH18P1RJgGOS9E+rbsF++4GtS5Ve8EbA6H2rFblDnpCRbV5Ja1ryN8Z0a8Vt7gzGETWXqefHsDFNHCNfbnIc= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=4JTSuiMJ; arc=none smtp.client-ip=209.85.128.202 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="4JTSuiMJ" Received: by mail-yw1-f202.google.com with SMTP id 00721157ae682-61be621bd84so27318457b3.1 for ; Thu, 09 May 2024 22:38:14 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1715319493; x=1715924293; darn=vger.kernel.org; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :from:to:cc:subject:date:message-id:reply-to; bh=z8mUHoTTwTNDR6VMgnmgQcaPuyAY5QRbZWhXDi0dIfE=; b=4JTSuiMJLVY8bHFBZZoTCM9E7syHvTDgq9MDftf/n+P0XVdFSuWNdonxzacEkOVNd6 ZDQlROgcvIvxPm/FTqUbBsEOsaDJqGr5ytD5b7kYWo0xoGGcLMtr9hi29pjQVRYCnJH2 In27JKn3VZAAbo0Plw8dfBOT/GBKJUPHcKG3DtMqU1Ass+e4Rn15CY08JibAPTGIgLHj OBSMS5ElcN9NyuQ/fPoc+4oh5/2jwBO+4J/HpjnexnBBxUCLLjgErC6/Uho/7QJRWKI8 HR4DnN9+xKXND0xa8Dx21iKz/B+sfQRRu1lYpCZX5kAmxkakTpnybl8/suD35MgAGfc3 AVAw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1715319493; x=1715924293; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=z8mUHoTTwTNDR6VMgnmgQcaPuyAY5QRbZWhXDi0dIfE=; b=VGBp7FCi1MSueG0mabjMiRpc/i34ahBi3p97i1AXsHg1H93/3GUhY5fGKyg4Du8uyp RDN5jKScRQFFZhdl5KL1DknwJyBLgga6JobK8KfcNck16zjoGJhErdJ96Xn2yymnsi4u V6k7DNsG8+XlxbwC17hss4yUEEV75G00oyaQNgpE6eWoULFWW/aOGDU2TTHw8arWvg62 x7ElO0crpDVTVHZBlIqHzfQ4MxJP5wruXcIJtCOOGNsFH1yvSQ7QKtR6qiw32HLJa3WX 5YyDrC9C6pBSqKa+nxYPH9/1f85OI44t2VT41iI+wbTUrm2EV9Vf6JXx7QuHYnUPeLhl MG6A== X-Forwarded-Encrypted: i=1; AJvYcCV/ZPRCSZCdbjyLVkYQXgi13q/7NIuHJnzl3V9yNXZf8PhwFpEebJvyTjwG+w0+IYsfdvI/Dhu9zFBYXUMR6TQfsxTGN0V5pLDkK9Ui X-Gm-Message-State: AOJu0YxS9zom4X1GRWVklTzHFk8Xp9B6uvKbfNU102BqjvaaEsHwsf1T L9etVnQoS1pvg3n+RLLjpaxMF9IwUmXIalCosYqXYyxb1ZI4WSAOYki2VngpFtHIrQmnUJzaeHb 4/Iy4RQ== X-Google-Smtp-Source: AGHT+IEuORGK6XeqhS3knqXzuXQaKfa5sKPSvjks/Ef2jBveYaz1Jn8BtFQlW24dzkX+bRKresX4hrFHlWLd X-Received: from irogers.svl.corp.google.com ([2620:15c:2a3:200:79ed:c375:51e3:ed39]) (user=irogers job=sendgmr) by 2002:a05:690c:6010:b0:618:876d:b87d with SMTP id 00721157ae682-622b013431emr3642737b3.5.1715319493366; Thu, 09 May 2024 22:38:13 -0700 (PDT) Date: Thu, 9 May 2024 22:37:04 -0700 In-Reply-To: <20240510053705.2462258-1-irogers@google.com> Message-Id: <20240510053705.2462258-5-irogers@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20240510053705.2462258-1-irogers@google.com> X-Mailer: git-send-email 2.45.0.118.g7fe29c98d7-goog Subject: [PATCH v3 4/5] perf evsel x86: Make evsel__has_perf_metrics work for legacy events From: Ian Rogers To: Peter Zijlstra , Ingo Molnar , Arnaldo Carvalho de Melo , Namhyung Kim , Mark Rutland , Alexander Shishkin , Jiri Olsa , Ian Rogers , Adrian Hunter , Kan Liang , Ravi Bangoria , James Clark , Yang Jihong , Ze Gao , Leo Yan , Song Liu , K Prateek Nayak , Kaige Ye , Yicong Yang , linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" Use PMU interface to better detect core PMU for legacy events. Look for slots event on core PMU if it is appropriate for the event. Signed-off-by: Ian Rogers --- tools/perf/arch/x86/util/evsel.c | 31 ++++++++++++++++++++++++++----- 1 file changed, 26 insertions(+), 5 deletions(-) diff --git a/tools/perf/arch/x86/util/evsel.c b/tools/perf/arch/x86/util/ev= sel.c index 090d0f371891..1eaae8819c5e 100644 --- a/tools/perf/arch/x86/util/evsel.c +++ b/tools/perf/arch/x86/util/evsel.c @@ -21,7 +21,8 @@ void arch_evsel__set_sample_weight(struct evsel *evsel) /* Check whether the evsel's PMU supports the perf metrics */ bool evsel__sys_has_perf_metrics(const struct evsel *evsel) { - const char *pmu_name =3D evsel->pmu_name ? evsel->pmu_name : "cpu"; + struct perf_pmu *pmu; + u32 type =3D evsel->core.attr.type; =20 /* * The PERF_TYPE_RAW type is the core PMU type, e.g., "cpu" PMU @@ -31,11 +32,31 @@ bool evsel__sys_has_perf_metrics(const struct evsel *ev= sel) * Checking both the PERF_TYPE_RAW type and the slots event * should be good enough to detect the perf metrics feature. */ - if ((evsel->core.attr.type =3D=3D PERF_TYPE_RAW) && - perf_pmus__have_event(pmu_name, "slots")) - return true; +again: + switch (type) { + case PERF_TYPE_HARDWARE: + case PERF_TYPE_HW_CACHE: + type =3D evsel->core.attr.config >> PERF_PMU_TYPE_SHIFT; + if (type) + goto again; + break; + case PERF_TYPE_RAW: + break; + default: + return false; + } + + pmu =3D evsel->pmu; + if (pmu =3D=3D &perf_pmu__fake) + pmu =3D NULL; =20 - return false; + if (!pmu) { + while ((pmu =3D perf_pmus__scan_core(pmu)) !=3D NULL) { + if (pmu->type =3D=3D PERF_TYPE_RAW) + break; + } + } + return pmu && perf_pmu__have_event(pmu, "slots"); } =20 bool arch_evsel__must_be_in_group(const struct evsel *evsel) --=20 2.45.0.118.g7fe29c98d7-goog From nobody Sun Dec 14 12:02:54 2025 Received: from mail-yb1-f202.google.com (mail-yb1-f202.google.com [209.85.219.202]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A01111635B7 for ; Fri, 10 May 2024 05:38:16 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.219.202 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319498; cv=none; b=b0UcKISdM6rZzywrHWHz9D5Uh5Mfx0A/bu0jCDfZpXxWRI9y1CL2OOxrrpnk8Aos5r1sRLDEwTjRrjf7TIFTYGAYB6dv0OhbEFzB6Ef2+3hVkJUgVyIEIYpllZMNgxn79ScJPoaggRw2QKxM+RSn3wQy1JivUFw+krkzH7X60DU= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1715319498; c=relaxed/simple; bh=pQ/ykMTJPVdVXsWcWvxI9IBewGKlSl0x/rod7UQD6Fo=; h=Date:In-Reply-To:Message-Id:Mime-Version:References:Subject:From: To:Content-Type; b=iEFjE6eW83U/G38jpMq0hlIqdclsNmKII9in2vhBZEVUXvBhlCBnqaIQ4e5qSKgwSRt5dCxUD5XSNZAxiMMcIJ1G9lMFqQy6i6UJ9OWGGc6Lt3LtRb6Am8YMSMpMYzq5WEyMfbhOhHGfwikdDi+5T8qdo1J4SuJ5QqDfgsbYygU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b=Ojo9ixwN; arc=none smtp.client-ip=209.85.219.202 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=flex--irogers.bounces.google.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=google.com header.i=@google.com header.b="Ojo9ixwN" Received: by mail-yb1-f202.google.com with SMTP id 3f1490d57ef6-de54be7066bso2624697276.0 for ; Thu, 09 May 2024 22:38:16 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20230601; t=1715319495; x=1715924295; darn=vger.kernel.org; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :from:to:cc:subject:date:message-id:reply-to; bh=DWRbHF2FL8sVbDNcBMzaCLG3938X5gekbCQ/hc2HZYQ=; b=Ojo9ixwNFyBnXHQIT9XIf7XkJuPpTf3Xu3/QOwcEHwIGChjsfGvwrTJN59z+SmspKf PgzqxBYd4Y8M0aKJjuLhOV8AucwfTy47Ia48KNFjnhCSSOF7PTljBgeFBD4KwPb4gcDe peBKaM+TaHA1Taz6LQi6tbTzIZFmXnvMWYNlzWjh7iMOlh9VUDB7lqG2gcuREsjCx3SJ rrwr4k3o+1fTMQye3yxUfupvuwRLdB/BFrXlNNQt1miYd272N4GpjkcT7pLmMwuHXPA8 zLCgKZDA94xlyCv1LAtMFIwBQf/sX/q/spb6JKUIhDfCSz8EzMMQvkqhl33BO55JzdMW FkJw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1715319495; x=1715924295; h=to:from:subject:references:mime-version:message-id:in-reply-to:date :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=DWRbHF2FL8sVbDNcBMzaCLG3938X5gekbCQ/hc2HZYQ=; b=tETDH4qGduHhqWL35JkBMsI0kWOROfwqTtrOcOiUQEKMYZzghFtJQoUcDrTxECAgS1 XyNb183Y6QxDZNRjIfBOK7FC32cXX8X2tUR6U2DVnlCGbEbIa14JNUY2QjSlFg/hFbfS 50BCmqhO91zoWzliBZCutZsIM6qaNruRpbqOXiA3zfjya5K/VhsXjUkfDiJS8d/z+xe6 gYLT6P5Lgjidyg1c2PCwZwz2DKHnz3xFeBvMLG9ngA9XHe0Inv7zY8Iuoa4H7w19ne0i op6gujQ1hk1FF0K6aVIuzezl5woKBO3M7XnS4JujMrjacBivfFQz9YDMtT0GptqFR1HL eqjg== X-Forwarded-Encrypted: i=1; AJvYcCWIhGnDHjSWc4LM1eU4UO01ConUgIE8rmr7AiVdxZefOzIsn6VgIXyDKPtm4fZQG6TyPg574IDnU9O2GzKTHdalVCdJ5BlUYMXbQOZl X-Gm-Message-State: AOJu0Ywen9yeNV5si1bwhi2tNo5eHZqwnAn7JolZXT2YJJtjBbSYlvZ+ bDIkD5oOVpfB8r38fIX/aCDQm+A3U4NFOERBzzm8Bq/PPdovhisqf7EKTcF1OhYPby1sX594YXz C4C7i5A== X-Google-Smtp-Source: AGHT+IFeUmjBzCgQiTLgDbTRXxGnHHjpPKJPlbHrSS5XJyvbba6JPHgKv0issznoGEKCJQgRGkXbxkPmB+cv X-Received: from irogers.svl.corp.google.com ([2620:15c:2a3:200:79ed:c375:51e3:ed39]) (user=irogers job=sendgmr) by 2002:a05:6902:728:b0:de5:319b:a226 with SMTP id 3f1490d57ef6-dee4f2c3b29mr452416276.1.1715319495565; Thu, 09 May 2024 22:38:15 -0700 (PDT) Date: Thu, 9 May 2024 22:37:05 -0700 In-Reply-To: <20240510053705.2462258-1-irogers@google.com> Message-Id: <20240510053705.2462258-6-irogers@google.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: Mime-Version: 1.0 References: <20240510053705.2462258-1-irogers@google.com> X-Mailer: git-send-email 2.45.0.118.g7fe29c98d7-goog Subject: [PATCH v3 5/5] perf evsel: Remove pmu_name From: Ian Rogers To: Peter Zijlstra , Ingo Molnar , Arnaldo Carvalho de Melo , Namhyung Kim , Mark Rutland , Alexander Shishkin , Jiri Olsa , Ian Rogers , Adrian Hunter , Kan Liang , Ravi Bangoria , James Clark , Yang Jihong , Ze Gao , Leo Yan , Song Liu , K Prateek Nayak , Kaige Ye , Yicong Yang , linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" "evsel->pmu_name" is only ever assigned a strdup of "pmu->name", a strdup of "evsel->pmu_name" or NULL. As such, prefer to use "pmu->name" directly and even to directly compare PMUs than PMU names. For safety, add some additional NULL tests. Signed-off-by: Ian Rogers --- tools/perf/arch/x86/util/evsel.c | 4 ++-- tools/perf/tests/parse-events.c | 2 +- tools/perf/util/evlist.c | 3 ++- tools/perf/util/evsel.c | 7 ------- tools/perf/util/evsel.h | 3 +-- tools/perf/util/metricgroup.c | 4 ++-- tools/perf/util/parse-events.c | 1 - tools/perf/util/stat-shadow.c | 10 +++++----- tools/perf/util/stat.c | 2 +- 9 files changed, 14 insertions(+), 22 deletions(-) diff --git a/tools/perf/arch/x86/util/evsel.c b/tools/perf/arch/x86/util/ev= sel.c index 1eaae8819c5e..fe8a817d2061 100644 --- a/tools/perf/arch/x86/util/evsel.c +++ b/tools/perf/arch/x86/util/evsel.c @@ -84,7 +84,7 @@ int arch_evsel__hw_name(struct evsel *evsel, char *bf, si= ze_t size) return scnprintf(bf, size, "%s", event_name); =20 return scnprintf(bf, size, "%s/%s/", - evsel->pmu_name ? evsel->pmu_name : "cpu", + evsel->pmu ? evsel->pmu->name : "cpu", event_name); } =20 @@ -129,7 +129,7 @@ int arch_evsel__open_strerror(struct evsel *evsel, char= *msg, size_t size) return 0; =20 if (!evsel->core.attr.precise_ip && - !(evsel->pmu_name && !strncmp(evsel->pmu_name, "ibs", 3))) + !(evsel->pmu && !strncmp(evsel->pmu->name, "ibs", 3))) return 0; =20 /* More verbose IBS errors. */ diff --git a/tools/perf/tests/parse-events.c b/tools/perf/tests/parse-event= s.c index 993e482f094c..c7c0edf3d4ca 100644 --- a/tools/perf/tests/parse-events.c +++ b/tools/perf/tests/parse-events.c @@ -730,7 +730,7 @@ static int test__checkevent_pmu_events(struct evlist *e= vlist) =20 TEST_ASSERT_VAL("wrong number of entries", 1 =3D=3D evlist->core.nr_entri= es); TEST_ASSERT_VAL("wrong type", PERF_TYPE_RAW =3D=3D evsel->core.attr.type = || - strcmp(evsel->pmu_name, "cpu")); + strcmp(evsel->pmu->name, "cpu")); TEST_ASSERT_VAL("wrong exclude_user", !evsel->core.attr.exclude_user); TEST_ASSERT_VAL("wrong exclude_kernel", diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c index de498ba5ac1c..2e3f4f876792 100644 --- a/tools/perf/util/evlist.c +++ b/tools/perf/util/evlist.c @@ -2504,7 +2504,8 @@ void evlist__uniquify_name(struct evlist *evlist) else attributes =3D empty_attributes; =20 - if (asprintf(&new_name, "%s/%s/%s", pos->pmu_name, pos->name, attributes= + 1)) { + if (asprintf(&new_name, "%s/%s/%s", pos->pmu ? "" : pos->pmu->name, + pos->name, attributes + 1)) { free(pos->name); pos->name =3D new_name; } else { diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c index dfdb60c7a364..96b545f4d8b0 100644 --- a/tools/perf/util/evsel.c +++ b/tools/perf/util/evsel.c @@ -292,7 +292,6 @@ void evsel__init(struct evsel *evsel, evsel->metric_events =3D NULL; evsel->per_pkg_mask =3D NULL; evsel->collect_stat =3D false; - evsel->pmu_name =3D NULL; evsel->group_pmu_name =3D NULL; evsel->skippable =3D false; evsel->alternate_hw_config =3D PERF_COUNT_HW_MAX; @@ -390,11 +389,6 @@ struct evsel *evsel__clone(struct evsel *orig) if (evsel->group_name =3D=3D NULL) goto out_err; } - if (orig->pmu_name) { - evsel->pmu_name =3D strdup(orig->pmu_name); - if (evsel->pmu_name =3D=3D NULL) - goto out_err; - } if (orig->group_pmu_name) { evsel->group_pmu_name =3D strdup(orig->group_pmu_name); if (evsel->group_pmu_name =3D=3D NULL) @@ -1481,7 +1475,6 @@ void evsel__exit(struct evsel *evsel) zfree(&evsel->group_name); zfree(&evsel->name); zfree(&evsel->filter); - zfree(&evsel->pmu_name); zfree(&evsel->group_pmu_name); zfree(&evsel->unit); zfree(&evsel->metric_id); diff --git a/tools/perf/util/evsel.h b/tools/perf/util/evsel.h index 46e3589314f1..2f99cc8bfa7d 100644 --- a/tools/perf/util/evsel.h +++ b/tools/perf/util/evsel.h @@ -72,7 +72,6 @@ struct evsel { struct { char *name; char *group_name; - const char *pmu_name; const char *group_pmu_name; #ifdef HAVE_LIBTRACEEVENT struct tep_event *tp_format; @@ -169,7 +168,7 @@ struct evsel { unsigned long open_flags; int precise_ip_original; =20 - /* for missing_features */ + /* The PMU the event is from. Used for missing_features, PMU name, etc. */ struct perf_pmu *pmu; }; =20 diff --git a/tools/perf/util/metricgroup.c b/tools/perf/util/metricgroup.c index 9be406524617..b0700db6e1cc 100644 --- a/tools/perf/util/metricgroup.c +++ b/tools/perf/util/metricgroup.c @@ -297,8 +297,8 @@ static int setup_metric_events(const char *pmu, struct = hashmap *ids, struct expr_id_data *val_ptr; =20 /* Don't match events for the wrong hybrid PMU. */ - if (!all_pmus && ev->pmu_name && evsel__is_hybrid(ev) && - strcmp(ev->pmu_name, pmu)) + if (!all_pmus && ev->pmu && evsel__is_hybrid(ev) && + strcmp(ev->pmu->name, pmu)) continue; /* * Check for duplicate events with the same name. For diff --git a/tools/perf/util/parse-events.c b/tools/perf/util/parse-events.c index c72e1722b1fb..01d502d802ee 100644 --- a/tools/perf/util/parse-events.c +++ b/tools/perf/util/parse-events.c @@ -265,7 +265,6 @@ __add_event(struct list_head *list, int *idx, evsel->core.is_pmu_core =3D pmu ? pmu->is_core : false; evsel->auto_merge_stats =3D auto_merge_stats; evsel->pmu =3D pmu; - evsel->pmu_name =3D pmu ? strdup(pmu->name) : NULL; evsel->alternate_hw_config =3D alternate_hw_config; =20 if (name) diff --git a/tools/perf/util/stat-shadow.c b/tools/perf/util/stat-shadow.c index ffdd53a07654..7bf39b069c5b 100644 --- a/tools/perf/util/stat-shadow.c +++ b/tools/perf/util/stat-shadow.c @@ -566,7 +566,7 @@ static void perf_stat__print_metricgroup_header(struct = perf_stat_config *config, { bool need_full_name =3D perf_pmus__num_core_pmus() > 1; static const char *last_name; - static const char *last_pmu; + static const struct perf_pmu *last_pmu; char full_name[64]; =20 /* @@ -577,21 +577,21 @@ static void perf_stat__print_metricgroup_header(struc= t perf_stat_config *config, * different metric events. */ if (last_name && !strcmp(last_name, name)) { - if (!need_full_name || !strcmp(last_pmu, evsel->pmu_name)) { + if (!need_full_name || last_pmu !=3D evsel->pmu) { out->print_metricgroup_header(config, ctxp, NULL); return; } } =20 - if (need_full_name) - scnprintf(full_name, sizeof(full_name), "%s (%s)", name, evsel->pmu_name= ); + if (need_full_name && evsel->pmu) + scnprintf(full_name, sizeof(full_name), "%s (%s)", name, evsel->pmu->nam= e); else scnprintf(full_name, sizeof(full_name), "%s", name); =20 out->print_metricgroup_header(config, ctxp, full_name); =20 last_name =3D name; - last_pmu =3D evsel->pmu_name; + last_pmu =3D evsel->pmu; } =20 /** diff --git a/tools/perf/util/stat.c b/tools/perf/util/stat.c index 0bd5467389e4..7c2ccdcc3fdb 100644 --- a/tools/perf/util/stat.c +++ b/tools/perf/util/stat.c @@ -553,7 +553,7 @@ static bool evsel__is_alias(struct evsel *evsel_a, stru= ct evsel *evsel_b) if (evsel__is_clock(evsel_a) !=3D evsel__is_clock(evsel_b)) return false; =20 - return !!strcmp(evsel_a->pmu_name, evsel_b->pmu_name); + return evsel_a->pmu !=3D evsel_b->pmu; } =20 static void evsel__merge_aliases(struct evsel *evsel) --=20 2.45.0.118.g7fe29c98d7-goog