lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <20180109153522.14116-7-jolsa@kernel.org>
Date:   Tue,  9 Jan 2018 16:34:39 +0100
From:   Jiri Olsa <jolsa@...nel.org>
To:     Arnaldo Carvalho de Melo <acme@...nel.org>
Cc:     Adrian Hunter <adrian.hunter@...el.com>,
        lkml <linux-kernel@...r.kernel.org>,
        Ingo Molnar <mingo@...nel.org>,
        Namhyung Kim <namhyung@...nel.org>,
        David Ahern <dsahern@...il.com>,
        Andi Kleen <ak@...ux.intel.com>,
        Alexander Shishkin <alexander.shishkin@...ux.intel.com>,
        Peter Zijlstra <a.p.zijlstra@...llo.nl>
Subject: [PATCH 06/49] perf tools: Create separate mmap for dummy tracking event

When indexed data file support is enabled, a dummy tracking event will
be used to track metadata (like task, comm and mmap events) for a
session and actual samples will be recorded in separate (intermediate)
files and then merged (with index table).

Provide separate mmap to the dummy tracking event.  The size is fixed
to 128KiB (+ 1 page) as the event rate will be lower than samples.  I
originally wanted to use a single mmap for this but cross-cpu sharing
is prohibited so it's per-cpu (or per-task) like normal mmaps.

Cc: Adrian Hunter <adrian.hunter@...el.com>
Link: http://lkml.kernel.org/n/tip-8vw9ocqkwqa7rsoolc25ezdt@git.kernel.org
Original-patch-by: Namhyung Kim <namhyung@...nel.org>
Signed-off-by: Jiri Olsa <jolsa@...nel.org>
---
 tools/perf/builtin-record.c |  9 ++++++++
 tools/perf/util/evlist.c    | 55 ++++++++++++++++++++++++++++++++++++---------
 tools/perf/util/evlist.h    |  3 +++
 tools/perf/util/mmap.h      |  1 +
 4 files changed, 58 insertions(+), 10 deletions(-)

diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 57994e16e30f..a792758e9aa3 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -510,6 +510,8 @@ static int record__mmap_read_evlist(struct record *rec, struct perf_evlist *evli
 
 	for (i = 0; i < evlist->nr_mmaps; i++) {
 		struct perf_mmap *map = &maps[i];
+		struct perf_mmap *track_map =  evlist->track_mmap ?
+					      &evlist->track_mmap[i] : NULL;
 
 		if (map->base) {
 			if (perf_mmap__push(map, overwrite, rec, record__pushfn) != 0) {
@@ -523,6 +525,13 @@ static int record__mmap_read_evlist(struct record *rec, struct perf_evlist *evli
 			rc = -1;
 			goto out;
 		}
+
+		if (track_map && track_map->base) {
+			if (perf_mmap__push(track_map, overwrite, rec, record__pushfn) != 0) {
+				rc = -1;
+				goto out;
+			}
+		}
 	}
 
 	/*
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index 4e5027e590e2..bb2c74865ba3 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -775,9 +775,15 @@ static void perf_evlist__munmap_nofree(struct perf_evlist *evlist)
 {
 	int i;
 
-	if (evlist->mmap)
+	if (evlist->mmap) {
 		for (i = 0; i < evlist->nr_mmaps; i++)
 			perf_mmap__munmap(&evlist->mmap[i]);
+	}
+
+	if (evlist->track_mmap) {
+		for (i = 0; i < evlist->nr_mmaps; i++)
+			perf_mmap__munmap(&evlist->track_mmap[i]);
+	}
 
 	if (evlist->overwrite_mmap)
 		for (i = 0; i < evlist->nr_mmaps; i++)
@@ -829,14 +835,20 @@ perf_evlist__should_poll(struct perf_evlist *evlist __maybe_unused,
 }
 
 static int perf_evlist__mmap_per_evsel(struct perf_evlist *evlist, int idx,
-				       struct mmap_params *mp, int cpu_idx,
-				       int thread, int *_output, int *_output_overwrite)
+				       struct mmap_params *_mp, int cpu_idx,
+				       int thread, int *_output, int *_output_overwrite,
+				       int *_output_track)
 {
+	struct mmap_params mp_track = {
+		.prot = PROT_READ | PROT_WRITE,
+		.mask = TRACK_MMAP_SIZE - page_size - 1,
+	};
 	struct perf_evsel *evsel;
 	int revent;
 	int evlist_cpu = cpu_map__cpu(evlist->cpus, cpu_idx);
 
 	evlist__for_each_entry(evlist, evsel) {
+		struct mmap_params *mp = _mp;
 		struct perf_mmap *maps = evlist->mmap;
 		int *output = _output;
 		int fd;
@@ -858,6 +870,12 @@ static int perf_evlist__mmap_per_evsel(struct perf_evlist *evlist, int idx,
 			mp->prot &= ~PROT_WRITE;
 		}
 
+		if (mp->track_mmap && perf_evsel__is_dummy_tracking(evsel)) {
+			output = _output_track;
+			maps   = evlist->track_mmap;
+			mp     = &mp_track;
+		}
+
 		if (evsel->system_wide && thread)
 			continue;
 
@@ -917,13 +935,15 @@ static int perf_evlist__mmap_per_cpu(struct perf_evlist *evlist,
 	for (cpu = 0; cpu < nr_cpus; cpu++) {
 		int output = -1;
 		int output_overwrite = -1;
+		int output_track = -1;
 
 		auxtrace_mmap_params__set_idx(&mp->auxtrace_mp, evlist, cpu,
 					      true);
 
 		for (thread = 0; thread < nr_threads; thread++) {
 			if (perf_evlist__mmap_per_evsel(evlist, cpu, mp, cpu,
-							thread, &output, &output_overwrite))
+							thread, &output, &output_overwrite,
+							&output_track))
 				goto out_unmap;
 		}
 	}
@@ -945,12 +965,13 @@ static int perf_evlist__mmap_per_thread(struct perf_evlist *evlist,
 	for (thread = 0; thread < nr_threads; thread++) {
 		int output = -1;
 		int output_overwrite = -1;
+		int output_track = -1;
 
 		auxtrace_mmap_params__set_idx(&mp->auxtrace_mp, evlist, thread,
 					      false);
 
 		if (perf_evlist__mmap_per_evsel(evlist, thread, mp, 0, thread,
-						&output, &output_overwrite))
+						&output, &output_overwrite, &output_track))
 			goto out_unmap;
 	}
 
@@ -1095,12 +1116,26 @@ int perf_evlist__mmap_ex(struct perf_evlist *evlist, unsigned int pages,
 	 * Its value is decided by evsel's write_backward.
 	 * So &mp should not be passed through const pointer.
 	 */
-	struct mmap_params mp;
+	struct mmap_params mp = {
+		.track_mmap = false,
+	};
 
-	if (!evlist->mmap)
-		evlist->mmap = perf_evlist__alloc_mmap(evlist);
-	if (!evlist->mmap)
-		return -ENOMEM;
+	if (!evlist->mmap) {
+		struct perf_mmap *map;
+
+		map = perf_evlist__alloc_mmap(evlist);
+		if (!map)
+			return -ENOMEM;
+
+		evlist->mmap = map;
+		if (mp.track_mmap) {
+			map = perf_evlist__alloc_mmap(evlist);
+			if (!map)
+				return -ENOMEM;
+
+			evlist->track_mmap = map;
+		}
+	}
 
 	if (evlist->pollfd.entries == NULL && perf_evlist__alloc_pollfd(evlist) < 0)
 		return -ENOMEM;
diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h
index dff82a5853ad..bbfe523b0509 100644
--- a/tools/perf/util/evlist.h
+++ b/tools/perf/util/evlist.h
@@ -25,6 +25,8 @@ struct record_opts;
 #define PERF_EVLIST__HLIST_BITS 8
 #define PERF_EVLIST__HLIST_SIZE (1 << PERF_EVLIST__HLIST_BITS)
 
+#define TRACK_MMAP_SIZE  (((128 * 1024 / page_size) + 1) * page_size)
+
 struct perf_evlist {
 	struct list_head entries;
 	struct hlist_head heads[PERF_EVLIST__HLIST_SIZE];
@@ -45,6 +47,7 @@ struct perf_evlist {
 	struct fdarray	 pollfd;
 	struct perf_mmap *mmap;
 	struct perf_mmap *overwrite_mmap;
+	struct perf_mmap *track_mmap;
 	struct thread_map *threads;
 	struct cpu_map	  *cpus;
 	struct perf_evsel *selected;
diff --git a/tools/perf/util/mmap.h b/tools/perf/util/mmap.h
index 52853eca7ef9..a1e39b131842 100644
--- a/tools/perf/util/mmap.h
+++ b/tools/perf/util/mmap.h
@@ -55,6 +55,7 @@ enum bkw_mmap_state {
 struct mmap_params {
 	int			    prot, mask;
 	struct auxtrace_mmap_params auxtrace_mp;
+	bool track_mmap;
 };
 
 int perf_mmap__mmap(struct perf_mmap *map, struct mmap_params *mp, int fd);
-- 
2.13.6

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ