All of lore.kernel.org
 help / color / mirror / Atom feed
From: Ian Rogers <irogers@google.com>
To: Peter Zijlstra <peterz@infradead.org>,
	Ingo Molnar <mingo@redhat.com>,
	Arnaldo Carvalho de Melo <acme@kernel.org>,
	Mark Rutland <mark.rutland@arm.com>,
	Alexander Shishkin <alexander.shishkin@linux.intel.com>,
	Jiri Olsa <jolsa@kernel.org>, Namhyung Kim <namhyung@kernel.org>,
	Ian Rogers <irogers@google.com>,
	Adrian Hunter <adrian.hunter@intel.com>,
	James Clark <james.clark@arm.com>,
	Kan Liang <kan.liang@linux.intel.com>,
	John Garry <john.g.garry@oracle.com>,
	Kajol Jain <kjain@linux.ibm.com>,
	Jing Zhang <renyu.zj@linux.alibaba.com>,
	Ravi Bangoria <ravi.bangoria@amd.com>,
	Rob Herring <robh@kernel.org>,
	Gaosheng Cui <cuigaosheng1@huawei.com>,
	linux-perf-users@vger.kernel.org, linux-kernel@vger.kernel.org
Subject: [PATCH v2 07/18] perf pmu-events: Reduce processed events by passing PMU
Date: Wed, 23 Aug 2023 21:13:19 -0700	[thread overview]
Message-ID: <20230824041330.266337-8-irogers@google.com> (raw)
In-Reply-To: <20230824041330.266337-1-irogers@google.com>

Pass the PMU to pmu_events_table__for_each_event so that entries that
don't match don't need to be processed by callback. If a NULL PMU is
passed then all PMUs are processed. perf bench internals pmu-scan
"Average PMU scanning" performance is reduced by about 5% on an Intel
tigerlake.

Signed-off-by: Ian Rogers <irogers@google.com>
---
 tools/perf/pmu-events/empty-pmu-events.c | 15 ++++++----
 tools/perf/pmu-events/jevents.py         | 18 ++++++++----
 tools/perf/pmu-events/pmu-events.h       |  4 ++-
 tools/perf/tests/pmu-events.c            |  6 ++--
 tools/perf/util/pmu.c                    | 35 +++++++-----------------
 tools/perf/util/pmu.h                    |  1 +
 6 files changed, 41 insertions(+), 38 deletions(-)

diff --git a/tools/perf/pmu-events/empty-pmu-events.c b/tools/perf/pmu-events/empty-pmu-events.c
index 807f2e55c17c..2d6f748280ac 100644
--- a/tools/perf/pmu-events/empty-pmu-events.c
+++ b/tools/perf/pmu-events/empty-pmu-events.c
@@ -266,12 +266,16 @@ static const struct pmu_sys_events pmu_sys_event_tables[] = {
 	},
 };
 
-int pmu_events_table__for_each_event(const struct pmu_events_table *table, pmu_event_iter_fn fn,
-				    void *data)
+int pmu_events_table__for_each_event(const struct pmu_events_table *table, struct perf_pmu *pmu,
+				     pmu_event_iter_fn fn, void *data)
 {
 	for (const struct pmu_event *pe = &table->entries[0]; pe->name; pe++) {
-		int ret = fn(pe, table, data);
+		int ret;
 
+                if (pmu && !pmu__name_match(pmu, pe->pmu))
+                        continue;
+
+		ret = fn(pe, table, data);
 		if (ret)
 			return ret;
 	}
@@ -371,7 +375,8 @@ const struct pmu_metrics_table *find_core_metrics_table(const char *arch, const
 int pmu_for_each_core_event(pmu_event_iter_fn fn, void *data)
 {
 	for (const struct pmu_events_map *tables = &pmu_events_map[0]; tables->arch; tables++) {
-		int ret = pmu_events_table__for_each_event(&tables->event_table, fn, data);
+		int ret = pmu_events_table__for_each_event(&tables->event_table,
+							   /*pmu=*/ NULL, fn, data);
 
 		if (ret)
 			return ret;
@@ -408,7 +413,7 @@ int pmu_for_each_sys_event(pmu_event_iter_fn fn, void *data)
 	for (const struct pmu_sys_events *tables = &pmu_sys_event_tables[0];
 	     tables->name;
 	     tables++) {
-		int ret = pmu_events_table__for_each_event(&tables->table, fn, data);
+		int ret = pmu_events_table__for_each_event(&tables->table, /*pmu=*/ NULL, fn, data);
 
 		if (ret)
 			return ret;
diff --git a/tools/perf/pmu-events/jevents.py b/tools/perf/pmu-events/jevents.py
index 1ad20140114c..396af53e0e45 100755
--- a/tools/perf/pmu-events/jevents.py
+++ b/tools/perf/pmu-events/jevents.py
@@ -826,14 +826,20 @@ static int pmu_events_table__for_each_event_pmu(const struct pmu_events_table *t
  }
 
 int pmu_events_table__for_each_event(const struct pmu_events_table *table,
+                                    struct perf_pmu *pmu,
                                     pmu_event_iter_fn fn,
                                     void *data)
 {
         for (size_t i = 0; i < table->num_pmus; i++) {
-                int ret = pmu_events_table__for_each_event_pmu(table, &table->pmus[i],
-                                                               fn, data);
+                const struct pmu_table_entry *table_pmu = &table->pmus[i];
+                const char *pmu_name = &big_c_string[table_pmu->pmu_name.offset];
+                int ret;
 
-                if (ret)
+                if (pmu && !pmu__name_match(pmu, pmu_name))
+                        continue;
+
+                ret = pmu_events_table__for_each_event_pmu(table, table_pmu, fn, data);
+                if (pmu || ret)
                         return ret;
         }
         return 0;
@@ -955,7 +961,8 @@ int pmu_for_each_core_event(pmu_event_iter_fn fn, void *data)
         for (const struct pmu_events_map *tables = &pmu_events_map[0];
              tables->arch;
              tables++) {
-                int ret = pmu_events_table__for_each_event(&tables->event_table, fn, data);
+                int ret = pmu_events_table__for_each_event(&tables->event_table,
+                                                           /*pmu=*/ NULL, fn, data);
 
                 if (ret)
                         return ret;
@@ -992,7 +999,8 @@ int pmu_for_each_sys_event(pmu_event_iter_fn fn, void *data)
         for (const struct pmu_sys_events *tables = &pmu_sys_event_tables[0];
              tables->name;
              tables++) {
-                int ret = pmu_events_table__for_each_event(&tables->event_table, fn, data);
+                int ret = pmu_events_table__for_each_event(&tables->event_table,
+                                                           /*pmu=*/ NULL, fn, data);
 
                 if (ret)
                         return ret;
diff --git a/tools/perf/pmu-events/pmu-events.h b/tools/perf/pmu-events/pmu-events.h
index 6557381b7de1..c0303ba42e97 100644
--- a/tools/perf/pmu-events/pmu-events.h
+++ b/tools/perf/pmu-events/pmu-events.h
@@ -77,7 +77,9 @@ typedef int (*pmu_metric_iter_fn)(const struct pmu_metric *pm,
 				  const struct pmu_metrics_table *table,
 				  void *data);
 
-int pmu_events_table__for_each_event(const struct pmu_events_table *table, pmu_event_iter_fn fn,
+int pmu_events_table__for_each_event(const struct pmu_events_table *table,
+				    struct perf_pmu *pmu,
+				    pmu_event_iter_fn fn,
 				    void *data);
 int pmu_metrics_table__for_each_metric(const struct pmu_metrics_table *table, pmu_metric_iter_fn fn,
 				     void *data);
diff --git a/tools/perf/tests/pmu-events.c b/tools/perf/tests/pmu-events.c
index 0b6efabc3d20..92d1f6f0e666 100644
--- a/tools/perf/tests/pmu-events.c
+++ b/tools/perf/tests/pmu-events.c
@@ -483,12 +483,14 @@ static int test__pmu_event_table(struct test_suite *test __maybe_unused,
 	if (!table || !sys_event_table)
 		return -1;
 
-	err = pmu_events_table__for_each_event(table, test__pmu_event_table_core_callback,
+	err = pmu_events_table__for_each_event(table, /*pmu=*/ NULL,
+					      test__pmu_event_table_core_callback,
 					      &map_events);
 	if (err)
 		return err;
 
-	err = pmu_events_table__for_each_event(sys_event_table, test__pmu_event_table_sys_callback,
+	err = pmu_events_table__for_each_event(sys_event_table, /*pmu=*/ NULL,
+					      test__pmu_event_table_sys_callback,
 					      &map_events);
 	if (err)
 		return err;
diff --git a/tools/perf/util/pmu.c b/tools/perf/util/pmu.c
index 0c82bbeea7d6..9ba9ac3d3d96 100644
--- a/tools/perf/util/pmu.c
+++ b/tools/perf/util/pmu.c
@@ -859,28 +859,14 @@ static bool pmu_uncore_alias_match(const char *pmu_name, const char *name)
 	return res;
 }
 
-struct pmu_add_cpu_aliases_map_data {
-	/* List being added to. */
-	struct list_head *head;
-	/* If a pmu_event lacks a given PMU the default used. */
-	char *default_pmu_name;
-	/* The PMU that we're searching for events for. */
-	struct perf_pmu *pmu;
-};
-
 static int pmu_add_cpu_aliases_map_callback(const struct pmu_event *pe,
 					const struct pmu_events_table *table __maybe_unused,
 					void *vdata)
 {
-	struct pmu_add_cpu_aliases_map_data *data = vdata;
-	const char *pname = pe->pmu ?: data->default_pmu_name;
+	struct list_head *head = vdata;
 
-	if (!strcmp(pname, data->pmu->name) ||
-	    (data->pmu->is_uncore && pmu_uncore_alias_match(pname, data->pmu->name))) {
-		/* need type casts to override 'const' */
-		__perf_pmu__new_alias(data->head, -1, (char *)pe->name, (char *)pe->desc,
-				      (char *)pe->event, pe);
-	}
+	/* need type casts to override 'const' */
+	__perf_pmu__new_alias(head, -1, (char *)pe->name, (char *)pe->desc, (char *)pe->event, pe);
 	return 0;
 }
 
@@ -890,14 +876,7 @@ static int pmu_add_cpu_aliases_map_callback(const struct pmu_event *pe,
  */
 void pmu_add_cpu_aliases_table(struct perf_pmu *pmu, const struct pmu_events_table *table)
 {
-	struct pmu_add_cpu_aliases_map_data data = {
-		.head = &pmu->aliases,
-		.default_pmu_name = perf_pmus__default_pmu_name(),
-		.pmu = pmu,
-	};
-
-	pmu_events_table__for_each_event(table, pmu_add_cpu_aliases_map_callback, &data);
-	free(data.default_pmu_name);
+	pmu_events_table__for_each_event(table, pmu, pmu_add_cpu_aliases_map_callback, &pmu->aliases);
 }
 
 static void pmu_add_cpu_aliases(struct perf_pmu *pmu)
@@ -1713,6 +1692,12 @@ int perf_pmu__for_each_event(const struct perf_pmu *pmu, void *state, pmu_event_
 	return ret;
 }
 
+bool pmu__name_match(const struct perf_pmu *pmu, const char *pmu_name)
+{
+	return !strcmp(pmu->name, pmu_name) ||
+		(pmu->is_uncore && pmu_uncore_alias_match(pmu_name, pmu->name));
+}
+
 bool perf_pmu__is_software(const struct perf_pmu *pmu)
 {
 	if (pmu->is_core || pmu->is_uncore || pmu->auxtrace)
diff --git a/tools/perf/util/pmu.h b/tools/perf/util/pmu.h
index 03211de345c1..2b1730152bc0 100644
--- a/tools/perf/util/pmu.h
+++ b/tools/perf/util/pmu.h
@@ -198,6 +198,7 @@ bool perf_pmu__auto_merge_stats(const struct perf_pmu *pmu);
 bool perf_pmu__have_event(const struct perf_pmu *pmu, const char *name);
 size_t perf_pmu__num_events(const struct perf_pmu *pmu);
 int perf_pmu__for_each_event(const struct perf_pmu *pmu, void *state, pmu_event_callback cb);
+bool pmu__name_match(const struct perf_pmu *pmu, const char *pmu_name);
 
 /**
  * perf_pmu_is_software - is the PMU a software PMU as in it uses the
-- 
2.42.0.rc1.204.g551eb34607-goog


  parent reply	other threads:[~2023-08-24  4:14 UTC|newest]

Thread overview: 39+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-08-24  4:13 [PATCH v2 00/18] Lazily load PMU data Ian Rogers
2023-08-24  4:13 ` [PATCH v2 01/18] perf pmu: Make the loading of formats lazy Ian Rogers
2023-08-24  4:13 ` [PATCH v2 02/18] perf pmu: Abstract alias/event struct Ian Rogers
2023-08-24  4:13 ` [PATCH v2 03/18] perf pmu-events: Add extra underscore to function names Ian Rogers
2023-08-24  4:13 ` [PATCH v2 04/18] perf jevents: Group events by PMU Ian Rogers
2023-08-29 15:28   ` James Clark
2023-08-29 15:34     ` Ian Rogers
2023-08-24  4:13 ` [PATCH v2 05/18] perf parse-events: Improve error message for double setting Ian Rogers
2023-08-24  4:13 ` [PATCH v2 06/18] perf s390 s390_cpumcfdg_dump: Don't scan all PMUs Ian Rogers
2023-08-24 13:59   ` Arnaldo Carvalho de Melo
2023-08-24 17:31     ` Ian Rogers
2023-08-25  8:19     ` Thomas Richter
2023-08-25 13:14       ` Ian Rogers
2023-08-25 14:39         ` Thomas Richter
2023-08-25 20:56           ` Arnaldo Carvalho de Melo
2023-08-25 22:56             ` Ian Rogers
2023-08-26  1:38               ` Arnaldo Carvalho de Melo
2023-08-26  6:28                 ` Ian Rogers
2023-08-28 17:44               ` Arnaldo Carvalho de Melo
2023-08-28 17:53                 ` Arnaldo Carvalho de Melo
2023-08-28 21:39                   ` Arnaldo Carvalho de Melo
2023-08-29  0:59                   ` Ian Rogers
2023-08-29  9:20                     ` Jing Zhang
2023-08-29 13:20                       ` Arnaldo Carvalho de Melo
2023-08-29 11:28                     ` Arnaldo Carvalho de Melo
2023-08-24  4:13 ` Ian Rogers [this message]
2023-08-24  4:13 ` [PATCH v2 08/18] perf pmu-events: Add pmu_events_table__find_event Ian Rogers
2023-08-24  4:13 ` [PATCH v2 09/18] perf pmu: Parse sysfs events directly from a file Ian Rogers
2023-08-24  4:13 ` [PATCH v2 10/18] perf pmu: Prefer passing pmu to aliases list Ian Rogers
2023-08-24  4:13 ` [PATCH v2 11/18] perf pmu: Merge json events with sysfs at load time Ian Rogers
2023-08-24  4:13 ` [PATCH v2 12/18] perf pmu: Cache json events table Ian Rogers
2023-08-24  4:13 ` [PATCH v2 13/18] perf pmu: Lazily add json events Ian Rogers
2023-08-24  4:13 ` [PATCH v2 14/18] perf pmu: Scan type early to fail an invalid PMU quickly Ian Rogers
2023-08-24  4:13 ` [PATCH v2 15/18] perf pmu: Be lazy about loading event info files from sysfs Ian Rogers
2023-08-24  4:13 ` [PATCH v2 16/18] perf pmu: Lazily load sysfs aliases Ian Rogers
2023-08-24  4:13 ` [PATCH v2 17/18] perf jevents: Sort strings in the big C string to reduce faults Ian Rogers
2023-08-24  4:13 ` [PATCH v2 18/18] perf jevents: Don't append Unit to desc Ian Rogers
2023-08-24 14:52 ` [PATCH v2 00/18] Lazily load PMU data Arnaldo Carvalho de Melo
2023-08-24 18:01   ` Ian Rogers

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20230824041330.266337-8-irogers@google.com \
    --to=irogers@google.com \
    --cc=acme@kernel.org \
    --cc=adrian.hunter@intel.com \
    --cc=alexander.shishkin@linux.intel.com \
    --cc=cuigaosheng1@huawei.com \
    --cc=james.clark@arm.com \
    --cc=john.g.garry@oracle.com \
    --cc=jolsa@kernel.org \
    --cc=kan.liang@linux.intel.com \
    --cc=kjain@linux.ibm.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-perf-users@vger.kernel.org \
    --cc=mark.rutland@arm.com \
    --cc=mingo@redhat.com \
    --cc=namhyung@kernel.org \
    --cc=peterz@infradead.org \
    --cc=ravi.bangoria@amd.com \
    --cc=renyu.zj@linux.alibaba.com \
    --cc=robh@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.