linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCHv2 00/25] perf tool: Add support for multiple data file storage
@ 2013-09-01 10:36 Jiri Olsa
  2013-09-01 10:36 ` [PATCH 01/25] perf tools: Check mmap pages value early Jiri Olsa
                   ` (26 more replies)
  0 siblings, 27 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

hi,
sending the support for multiple file storage. Initial
RFC is here:
http://marc.info/?l=linux-kernel&m=137408381902423&w=2

v2 changes:
  - reworked perf mmap size setup to be able to get
    the mmap size value easily later
  - added perf.data read/write test for v2 and v3
    for both endianity
  - added record '-M time' support

It's reachable here:
git://git.kernel.org/pub/scm/linux/kernel/git/jolsa/perf.git
perf/core_file

thanks,
jirka

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
Jiri Olsa (25):
      perf tools: Check mmap pages value early
      perf tools: Add possibility to specify mmap size
      perf tools: Introduce perf_evlist__new_default function
      perf tools: Adding throttle event data struct support
      perf tests: Add simple session read/write test
      perf tests: Add session reading test for little endian perf data
      perf tests: Add session reading test for big endian perf data
      perf doc: Add perf data file documentation
      perf tools: Introduce perf data file version CHECK macro
      perf tools: Introduce swap_features function
      perf tools: Introduce swap_header function
      perf tools: Separate version 2 specific perf data header bits
      perf tools: Using evlist as a holder for event_desc feature
      perf tools: Introduce perf.data version 3 format
      perf tools: Add perf data version 3 header swap
      perf tools: Add perf data version 3 header read
      perf tools: Add perf.data version 3 header write
      perf tools: Get rid of post_processing_offset in record command
      perf tools: Move synthesizing into single function
      perf tools: Add perf_data_file__open interface to data object
      perf tools: Separating data file properties from session
      perf tests: Add session reading test for little endian perf data v3
      perf tests: Add session reading test for big endian perf data v3
      perf tools: Add multi file '-M' option for record command
      perf tools: Have the process properly sythesized in subsequent data files

 tools/perf/Documentation/perf-data-file-v2.txt | 265 ++++++++++++++++++++++++++++++++++
 tools/perf/Documentation/perf-data-file-v3.txt |  63 ++++++++
 tools/perf/Documentation/perf-kvm.txt          |   4 +-
 tools/perf/Documentation/perf-record.txt       |  18 ++-
 tools/perf/Documentation/perf-top.txt          |   4 +-
 tools/perf/Documentation/perf-trace.txt        |   4 +-
 tools/perf/Makefile                            |   6 +
 tools/perf/builtin-annotate.c                  |  11 +-
 tools/perf/builtin-buildid-cache.c             |   8 +-
 tools/perf/builtin-buildid-list.c              |  11 +-
 tools/perf/builtin-diff.c                      |  19 ++-
 tools/perf/builtin-evlist.c                    |   7 +-
 tools/perf/builtin-inject.c                    |  10 +-
 tools/perf/builtin-kmem.c                      |   7 +-
 tools/perf/builtin-kvm.c                       |  18 ++-
 tools/perf/builtin-lock.c                      |   8 +-
 tools/perf/builtin-mem.c                       |   9 +-
 tools/perf/builtin-record.c                    | 484 ++++++++++++++++++++++++++++++++++++++++++++------------------
 tools/perf/builtin-report.c                    |  18 ++-
 tools/perf/builtin-sched.c                     |   6 +-
 tools/perf/builtin-script.c                    |  17 ++-
 tools/perf/builtin-timechart.c                 |  10 +-
 tools/perf/builtin-top.c                       |  12 +-
 tools/perf/builtin-trace.c                     |  13 +-
 tools/perf/perf.h                              |  15 +-
 tools/perf/tests/builtin-test.c                |   4 +
 tools/perf/tests/perf-record.c                 |  12 +-
 tools/perf/tests/perf.data.v2.be.h             | 265 ++++++++++++++++++++++++++++++++++
 tools/perf/tests/perf.data.v2.le.h             | 219 ++++++++++++++++++++++++++++
 tools/perf/tests/perf.data.v3.be.h             | 258 +++++++++++++++++++++++++++++++++
 tools/perf/tests/perf.data.v3.le.h             | 212 +++++++++++++++++++++++++++
 tools/perf/tests/session-simple.c              | 658 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 tools/perf/tests/task-exit.c                   |  14 +-
 tools/perf/tests/tests.h                       |   1 +
 tools/perf/util/data.c                         | 120 ++++++++++++++++
 tools/perf/util/data.h                         |  48 +++++++
 tools/perf/util/event.h                        |   7 +
 tools/perf/util/evlist.c                       |  78 ++++++++--
 tools/perf/util/evlist.h                       |   9 +-
 tools/perf/util/evsel.c                        |  24 ++++
 tools/perf/util/header.c                       | 446 +++++++++++++++++++++++++++++++++------------------------
 tools/perf/util/header.h                       |  31 +++-
 tools/perf/util/python.c                       |   7 -
 tools/perf/util/session.c                      | 138 ++++++++----------
 tools/perf/util/session.h                      |  11 +-
 tools/perf/util/util.c                         |  25 ++++
 tools/perf/util/util.h                         |  14 ++
 47 files changed, 3137 insertions(+), 511 deletions(-)
 create mode 100644 tools/perf/Documentation/perf-data-file-v2.txt
 create mode 100644 tools/perf/Documentation/perf-data-file-v3.txt
 create mode 100644 tools/perf/tests/perf.data.v2.be.h
 create mode 100644 tools/perf/tests/perf.data.v2.le.h
 create mode 100644 tools/perf/tests/perf.data.v3.be.h
 create mode 100644 tools/perf/tests/perf.data.v3.le.h
 create mode 100644 tools/perf/tests/session-simple.c
 create mode 100644 tools/perf/util/data.c
 create mode 100644 tools/perf/util/data.h

^ permalink raw reply	[flat|nested] 48+ messages in thread

* [PATCH 01/25] perf tools: Check mmap pages value early
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-10-15  5:24   ` [tip:perf/core] " tip-bot for Jiri Olsa
  2013-09-01 10:36 ` [PATCH 02/25] perf tools: Add possibility to specify mmap size Jiri Olsa
                   ` (25 subsequent siblings)
  26 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Moving the check of the mmap_pages value into the options
parsing time, so we could relay on this value on other
parts of code. Related changes come in next patches.

Also changins perf_evlist::mmap_len to proper size_t type.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/builtin-kvm.c    |  5 +++--
 tools/perf/builtin-record.c |  9 +++------
 tools/perf/builtin-top.c    |  5 +++--
 tools/perf/builtin-trace.c  |  5 +++--
 tools/perf/util/evlist.c    | 46 ++++++++++++++++++++++++++++++++++++---------
 tools/perf/util/evlist.h    |  6 +++++-
 6 files changed, 54 insertions(+), 22 deletions(-)

diff --git a/tools/perf/builtin-kvm.c b/tools/perf/builtin-kvm.c
index 47b3540..f89f7d6 100644
--- a/tools/perf/builtin-kvm.c
+++ b/tools/perf/builtin-kvm.c
@@ -1426,8 +1426,9 @@ static int kvm_events_live(struct perf_kvm_stat *kvm,
 	const struct option live_options[] = {
 		OPT_STRING('p', "pid", &kvm->opts.target.pid, "pid",
 			"record events on existing process id"),
-		OPT_UINTEGER('m', "mmap-pages", &kvm->opts.mmap_pages,
-			"number of mmap data pages"),
+		OPT_CALLBACK('m', "mmap-pages", &kvm->opts.mmap_pages, "pages",
+			"number of mmap data pages",
+			perf_evlist__parse_mmap_pages),
 		OPT_INCR('v', "verbose", &verbose,
 			"be more verbose (show counter open errors, etc)"),
 		OPT_BOOLEAN('a', "all-cpus", &kvm->opts.target.system_wide,
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index a41ac415..351ede3 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -234,10 +234,6 @@ try_again:
 			       "or try again with a smaller value of -m/--mmap_pages.\n"
 			       "(current value: %d)\n", opts->mmap_pages);
 			rc = -errno;
-		} else if (!is_power_of_2(opts->mmap_pages) &&
-			   (opts->mmap_pages != UINT_MAX)) {
-			pr_err("--mmap_pages/-m value must be a power of two.");
-			rc = -EINVAL;
 		} else {
 			pr_err("failed to mmap with %d (%s)\n", errno, strerror(errno));
 			rc = -errno;
@@ -854,8 +850,9 @@ const struct option record_options[] = {
 	OPT_BOOLEAN('i', "no-inherit", &record.opts.no_inherit,
 		    "child tasks do not inherit counters"),
 	OPT_UINTEGER('F', "freq", &record.opts.user_freq, "profile at this frequency"),
-	OPT_UINTEGER('m', "mmap-pages", &record.opts.mmap_pages,
-		     "number of mmap data pages"),
+	OPT_CALLBACK('m', "mmap-pages", &record.opts.mmap_pages, "pages",
+		     "number of mmap data pages",
+		     perf_evlist__parse_mmap_pages),
 	OPT_BOOLEAN(0, "group", &record.opts.group,
 		    "put the counters into a counter group"),
 	OPT_CALLBACK_DEFAULT('g', "call-graph", &record.opts,
diff --git a/tools/perf/builtin-top.c b/tools/perf/builtin-top.c
index 2122141..0a84334 100644
--- a/tools/perf/builtin-top.c
+++ b/tools/perf/builtin-top.c
@@ -1076,8 +1076,9 @@ int cmd_top(int argc, const char **argv, const char *prefix __maybe_unused)
 		   "file", "vmlinux pathname"),
 	OPT_BOOLEAN('K', "hide_kernel_symbols", &top.hide_kernel_symbols,
 		    "hide kernel symbols"),
-	OPT_UINTEGER('m', "mmap-pages", &opts->mmap_pages,
-		     "number of mmap data pages"),
+	OPT_CALLBACK('m', "mmap-pages", &opts->mmap_pages, "pages",
+		     "number of mmap data pages",
+		     perf_evlist__parse_mmap_pages),
 	OPT_INTEGER('r', "realtime", &top.realtime_prio,
 		    "collect data with this RT SCHED_FIFO priority"),
 	OPT_INTEGER('d', "delay", &top.delay_secs,
diff --git a/tools/perf/builtin-trace.c b/tools/perf/builtin-trace.c
index 69a065e..9967a56 100644
--- a/tools/perf/builtin-trace.c
+++ b/tools/perf/builtin-trace.c
@@ -1042,8 +1042,9 @@ int cmd_trace(int argc, const char **argv, const char *prefix __maybe_unused)
 		    "list of cpus to monitor"),
 	OPT_BOOLEAN(0, "no-inherit", &trace.opts.no_inherit,
 		    "child tasks do not inherit counters"),
-	OPT_UINTEGER('m', "mmap-pages", &trace.opts.mmap_pages,
-		     "number of mmap data pages"),
+	OPT_CALLBACK('m', "mmap-pages", &trace.opts.mmap_pages, "pages",
+		     "number of mmap data pages",
+		     perf_evlist__parse_mmap_pages),
 	OPT_STRING('u', "uid", &trace.opts.target.uid_str, "user",
 		   "user to profile"),
 	OPT_CALLBACK(0, "duration", &trace, "float",
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index 5df4ca9..4780b9e 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -18,6 +18,7 @@
 #include <unistd.h>
 
 #include "parse-events.h"
+#include "parse-options.h"
 
 #include <sys/mman.h>
 
@@ -619,6 +620,40 @@ out_unmap:
 	return -1;
 }
 
+static size_t perf_evlist__mmap_size(unsigned long pages)
+{
+	/* 512 kiB: default amount of unprivileged mlocked memory */
+	if (pages == UINT_MAX)
+		pages = (512 * 1024) / page_size;
+	else if (!is_power_of_2(pages))
+		return 0;
+
+	return (pages + 1) * page_size;
+}
+
+int perf_evlist__parse_mmap_pages(const struct option *opt, const char *str,
+				  int unset __maybe_unused)
+{
+	unsigned int pages, *mmap_pages = opt->value;
+	size_t size;
+	char *eptr;
+
+	pages = strtoul(str, &eptr, 10);
+	if (*eptr != '\0') {
+		pr_err("failed to parse --mmap_pages/-m value\n");
+		return -1;
+	}
+
+	size = perf_evlist__mmap_size(pages);
+	if (!size) {
+		pr_err("--mmap_pages/-m value must be a power of two.");
+		return -1;
+	}
+
+	*mmap_pages = pages;
+	return 0;
+}
+
 /** perf_evlist__mmap - Create per cpu maps to receive events
  *
  * @evlist - list of events
@@ -642,14 +677,6 @@ int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 	const struct thread_map *threads = evlist->threads;
 	int prot = PROT_READ | (overwrite ? 0 : PROT_WRITE), mask;
 
-        /* 512 kiB: default amount of unprivileged mlocked memory */
-        if (pages == UINT_MAX)
-                pages = (512 * 1024) / page_size;
-	else if (!is_power_of_2(pages))
-		return -EINVAL;
-
-	mask = pages * page_size - 1;
-
 	if (evlist->mmap == NULL && perf_evlist__alloc_mmap(evlist) < 0)
 		return -ENOMEM;
 
@@ -657,7 +684,8 @@ int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 		return -ENOMEM;
 
 	evlist->overwrite = overwrite;
-	evlist->mmap_len = (pages + 1) * page_size;
+	evlist->mmap_len = perf_evlist__mmap_size(pages);
+	mask = evlist->mmap_len - page_size - 1;
 
 	list_for_each_entry(evsel, &evlist->entries, node) {
 		if ((evsel->attr.read_format & PERF_FORMAT_ID) &&
diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h
index 841a394..cae0bf5 100644
--- a/tools/perf/util/evlist.h
+++ b/tools/perf/util/evlist.h
@@ -31,7 +31,7 @@ struct perf_evlist {
 	int		 nr_groups;
 	int		 nr_fds;
 	int		 nr_mmaps;
-	int		 mmap_len;
+	size_t		 mmap_len;
 	int		 id_pos;
 	int		 is_pos;
 	u64		 combined_sample_type;
@@ -103,6 +103,10 @@ int perf_evlist__prepare_workload(struct perf_evlist *evlist,
 				  bool want_signal);
 int perf_evlist__start_workload(struct perf_evlist *evlist);
 
+int perf_evlist__parse_mmap_pages(const struct option *opt,
+				  const char *str,
+				  int unset);
+
 int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 		      bool overwrite);
 void perf_evlist__munmap(struct perf_evlist *evlist);
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 02/25] perf tools: Add possibility to specify mmap size
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
  2013-09-01 10:36 ` [PATCH 01/25] perf tools: Check mmap pages value early Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-10-15  5:25   ` [tip:perf/core] " tip-bot for Jiri Olsa
  2013-09-01 10:36 ` [PATCH 03/25] perf tools: Introduce perf_evlist__new_default function Jiri Olsa
                   ` (24 subsequent siblings)
  26 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding possibility to specify mmap size via -m/--mmap-pages
by appending unit size character (B/K/M/G) to the
number, like:
  $ perf record -m 8K ls
  $ perf record -m 2M ls

The size is rounded up appropriately to follow perf
mmap restrictions.

If no unit is specified the number provides pages as
of now, like:
  $ perf record -m 8 ls

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Documentation/perf-kvm.txt    |  4 +++-
 tools/perf/Documentation/perf-record.txt |  4 +++-
 tools/perf/Documentation/perf-top.txt    |  4 +++-
 tools/perf/Documentation/perf-trace.txt  |  4 +++-
 tools/perf/util/evlist.c                 | 32 ++++++++++++++++++++++++++------
 tools/perf/util/util.c                   | 25 +++++++++++++++++++++++++
 tools/perf/util/util.h                   | 14 ++++++++++++++
 7 files changed, 77 insertions(+), 10 deletions(-)

diff --git a/tools/perf/Documentation/perf-kvm.txt b/tools/perf/Documentation/perf-kvm.txt
index ac84db2..6a06cef 100644
--- a/tools/perf/Documentation/perf-kvm.txt
+++ b/tools/perf/Documentation/perf-kvm.txt
@@ -109,7 +109,9 @@ STAT LIVE OPTIONS
 
 -m::
 --mmap-pages=::
-    Number of mmap data pages. Must be a power of two.
+    Number of mmap data pages (must be a power of two) or size
+    specification with appended unit character - B/K/M/G. The
+    size is rounded up to have nearest pages power of two value.
 
 -a::
 --all-cpus::
diff --git a/tools/perf/Documentation/perf-record.txt b/tools/perf/Documentation/perf-record.txt
index e297b74..400e9bb 100644
--- a/tools/perf/Documentation/perf-record.txt
+++ b/tools/perf/Documentation/perf-record.txt
@@ -87,7 +87,9 @@ OPTIONS
 
 -m::
 --mmap-pages=::
-	Number of mmap data pages. Must be a power of two.
+	Number of mmap data pages (must be a power of two) or size
+	specification with appended unit character - B/K/M/G. The
+	size is rounded up to have nearest pages power of two value.
 
 -g::
 --call-graph::
diff --git a/tools/perf/Documentation/perf-top.txt b/tools/perf/Documentation/perf-top.txt
index 58d6598..19ab69e 100644
--- a/tools/perf/Documentation/perf-top.txt
+++ b/tools/perf/Documentation/perf-top.txt
@@ -68,7 +68,9 @@ Default is to monitor all CPUS.
 
 -m <pages>::
 --mmap-pages=<pages>::
-	Number of mmapped data pages.
+	Number of mmap data pages (must be a power of two) or size
+	specification with appended unit character - B/K/M/G. The
+	size is rounded up to have nearest pages power of two value.
 
 -p <pid>::
 --pid=<pid>::
diff --git a/tools/perf/Documentation/perf-trace.txt b/tools/perf/Documentation/perf-trace.txt
index daccd2c..d390efa 100644
--- a/tools/perf/Documentation/perf-trace.txt
+++ b/tools/perf/Documentation/perf-trace.txt
@@ -59,7 +59,9 @@ OPTIONS
 
 -m::
 --mmap-pages=::
-	Number of mmap data pages. Must be a power of two.
+	Number of mmap data pages (must be a power of two) or size
+	specification with appended unit character - B/K/M/G. The
+	size is rounded up to have nearest pages power of two value.
 
 -C::
 --cpu::
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index 4780b9e..8ea933f 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -634,14 +634,33 @@ static size_t perf_evlist__mmap_size(unsigned long pages)
 int perf_evlist__parse_mmap_pages(const struct option *opt, const char *str,
 				  int unset __maybe_unused)
 {
-	unsigned int pages, *mmap_pages = opt->value;
+	unsigned int pages, val, *mmap_pages = opt->value;
 	size_t size;
-	char *eptr;
+	static struct parse_tag tags[] = {
+		{ .tag  = 'B', .mult = 1       },
+		{ .tag  = 'K', .mult = 1 << 10 },
+		{ .tag  = 'M', .mult = 1 << 20 },
+		{ .tag  = 'G', .mult = 1 << 30 },
+		{ .tag  = 0 },
+	};
 
-	pages = strtoul(str, &eptr, 10);
-	if (*eptr != '\0') {
-		pr_err("failed to parse --mmap_pages/-m value\n");
-		return -1;
+	val = parse_tag_value(str, tags);
+	if (val != (unsigned int) -1) {
+		/* we got file size value */
+		pages = PERF_ALIGN(val, page_size) / page_size;
+		if (!is_power_of_2(pages)) {
+			pages = next_pow2(pages);
+			pr_info("rounding mmap pages size to %u (%u pages)\n",
+				pages * page_size, pages);
+		}
+	} else {
+		/* we got pages count value */
+		char *eptr;
+		pages = strtoul(str, &eptr, 10);
+		if (*eptr != '\0') {
+			pr_err("failed to parse --mmap_pages/-m value\n");
+			return -1;
+		}
 	}
 
 	size = perf_evlist__mmap_size(pages);
@@ -685,6 +704,7 @@ int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 
 	evlist->overwrite = overwrite;
 	evlist->mmap_len = perf_evlist__mmap_size(pages);
+	pr_debug("mmap size %luB\n", evlist->mmap_len);
 	mask = evlist->mmap_len - page_size - 1;
 
 	list_for_each_entry(evsel, &evlist->entries, node) {
diff --git a/tools/perf/util/util.c b/tools/perf/util/util.c
index 6d17b18..141317e 100644
--- a/tools/perf/util/util.c
+++ b/tools/perf/util/util.c
@@ -361,3 +361,28 @@ int parse_nsec_time(const char *str, u64 *ptime)
 	*ptime = time_sec * NSEC_PER_SEC + time_nsec;
 	return 0;
 }
+
+unsigned long parse_tag_value(const char *str, struct parse_tag *tags)
+{
+	struct parse_tag *i = tags;
+
+	while (i->tag) {
+		char *s;
+
+		s = strchr(str, i->tag);
+		if (s) {
+			unsigned long int value;
+			char *endptr;
+
+			value = strtoul(str, &endptr, 10);
+			if (s != endptr)
+				break;
+
+			value *= i->mult;
+			return value;
+		}
+		i++;
+	}
+
+	return (unsigned long) -1;
+}
diff --git a/tools/perf/util/util.h b/tools/perf/util/util.h
index a535359..c29ecaa 100644
--- a/tools/perf/util/util.h
+++ b/tools/perf/util/util.h
@@ -270,6 +270,13 @@ bool is_power_of_2(unsigned long n)
 	return (n != 0 && ((n & (n - 1)) == 0));
 }
 
+static inline unsigned next_pow2(unsigned x)
+{
+	if (!x)
+		return 1;
+	return 1ULL << (32 - __builtin_clz(x - 1));
+}
+
 size_t hex_width(u64 v);
 int hex2u64(const char *ptr, u64 *val);
 
@@ -281,4 +288,11 @@ void dump_stack(void);
 extern unsigned int page_size;
 
 void get_term_dimensions(struct winsize *ws);
+
+struct parse_tag {
+	char tag;
+	int mult;
+};
+
+unsigned long parse_tag_value(const char *str, struct parse_tag *tags);
 #endif /* GIT_COMPAT_UTIL_H */
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 03/25] perf tools: Introduce perf_evlist__new_default function
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
  2013-09-01 10:36 ` [PATCH 01/25] perf tools: Check mmap pages value early Jiri Olsa
  2013-09-01 10:36 ` [PATCH 02/25] perf tools: Add possibility to specify mmap size Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-10-15  5:25   ` [tip:perf/core] perf evlist: " tip-bot for Jiri Olsa
  2013-09-01 10:36 ` [PATCH 04/25] perf tools: Adding throttle event data struct support Jiri Olsa
                   ` (23 subsequent siblings)
  26 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding new common function to create evlist with default
event. It spares some code lines in automated tests.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/tests/perf-record.c | 12 +-----------
 tools/perf/tests/task-exit.c   | 14 ++------------
 tools/perf/util/evlist.c       | 12 ++++++++++++
 tools/perf/util/evlist.h       |  1 +
 4 files changed, 16 insertions(+), 23 deletions(-)

diff --git a/tools/perf/tests/perf-record.c b/tools/perf/tests/perf-record.c
index 72d8881..6143b06 100644
--- a/tools/perf/tests/perf-record.c
+++ b/tools/perf/tests/perf-record.c
@@ -45,7 +45,7 @@ int test__PERF_RECORD(void)
 	};
 	cpu_set_t cpu_mask;
 	size_t cpu_mask_size = sizeof(cpu_mask);
-	struct perf_evlist *evlist = perf_evlist__new();
+	struct perf_evlist *evlist = perf_evlist__new_default();
 	struct perf_evsel *evsel;
 	struct perf_sample sample;
 	const char *cmd = "sleep";
@@ -66,16 +66,6 @@ int test__PERF_RECORD(void)
 	}
 
 	/*
-	 * We need at least one evsel in the evlist, use the default
-	 * one: "cycles".
-	 */
-	err = perf_evlist__add_default(evlist);
-	if (err < 0) {
-		pr_debug("Not enough memory to create evsel\n");
-		goto out_delete_evlist;
-	}
-
-	/*
 	 * Create maps of threads and cpus to monitor. In this case
 	 * we start with all threads and cpus (-1, -1) but then in
 	 * perf_evlist__prepare_workload we'll fill in the only thread
diff --git a/tools/perf/tests/task-exit.c b/tools/perf/tests/task-exit.c
index 28fe589..b07f8a1 100644
--- a/tools/perf/tests/task-exit.c
+++ b/tools/perf/tests/task-exit.c
@@ -37,20 +37,11 @@ int test__task_exit(void)
 	signal(SIGCHLD, sig_handler);
 	signal(SIGUSR1, sig_handler);
 
-	evlist = perf_evlist__new();
+	evlist = perf_evlist__new_default();
 	if (evlist == NULL) {
-		pr_debug("perf_evlist__new\n");
+		pr_debug("perf_evlist__new_default\n");
 		return -1;
 	}
-	/*
-	 * We need at least one evsel in the evlist, use the default
-	 * one: "cycles".
-	 */
-	err = perf_evlist__add_default(evlist);
-	if (err < 0) {
-		pr_debug("Not enough memory to create evsel\n");
-		goto out_free_evlist;
-	}
 
 	/*
 	 * Create maps of threads and cpus to monitor. In this case
@@ -117,7 +108,6 @@ out_close_evlist:
 	perf_evlist__close(evlist);
 out_delete_maps:
 	perf_evlist__delete_maps(evlist);
-out_free_evlist:
 	perf_evlist__delete(evlist);
 	return err;
 }
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index 8ea933f..998e0d1 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -50,6 +50,18 @@ struct perf_evlist *perf_evlist__new(void)
 	return evlist;
 }
 
+struct perf_evlist *perf_evlist__new_default(void)
+{
+	struct perf_evlist *evlist = perf_evlist__new();
+
+	if (evlist && perf_evlist__add_default(evlist)) {
+		perf_evlist__delete(evlist);
+		evlist = NULL;
+	}
+
+	return evlist;
+}
+
 /**
  * perf_evlist__set_id_pos - set the positions of event ids.
  * @evlist: selected event list
diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h
index cae0bf5..ca016b1 100644
--- a/tools/perf/util/evlist.h
+++ b/tools/perf/util/evlist.h
@@ -53,6 +53,7 @@ struct perf_evsel_str_handler {
 };
 
 struct perf_evlist *perf_evlist__new(void);
+struct perf_evlist *perf_evlist__new_default(void);
 void perf_evlist__init(struct perf_evlist *evlist, struct cpu_map *cpus,
 		       struct thread_map *threads);
 void perf_evlist__exit(struct perf_evlist *evlist);
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 04/25] perf tools: Adding throttle event data struct support
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (2 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 03/25] perf tools: Introduce perf_evlist__new_default function Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-10-15  5:25   ` [tip:perf/core] " tip-bot for Jiri Olsa
  2013-09-01 10:36 ` [PATCH 05/25] perf tests: Add simple session read/write test Jiri Olsa
                   ` (22 subsequent siblings)
  26 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Moving 'struct throttle_event' out of python code and
making it global as any other event.

There's no usage of throttling events in any perf commands
so far (besides python support), but we'll need this event
data backup for upcomming test.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/event.h   |  7 +++++++
 tools/perf/util/python.c  |  7 -------
 tools/perf/util/session.c | 13 +++++++++++++
 3 files changed, 20 insertions(+), 7 deletions(-)

diff --git a/tools/perf/util/event.h b/tools/perf/util/event.h
index 93130d8..4971bfc 100644
--- a/tools/perf/util/event.h
+++ b/tools/perf/util/event.h
@@ -48,6 +48,12 @@ struct read_event {
 	u64 id;
 };
 
+struct throttle_event {
+	struct perf_event_header header;
+	u64 time;
+	u64 id;
+	u64 stream_id;
+};
 
 #define PERF_SAMPLE_MASK				\
 	(PERF_SAMPLE_IP | PERF_SAMPLE_TID |		\
@@ -163,6 +169,7 @@ union perf_event {
 	struct fork_event		fork;
 	struct lost_event		lost;
 	struct read_event		read;
+	struct throttle_event		throttle;
 	struct sample_event		sample;
 	struct attr_event		attr;
 	struct event_type_event		event_type;
diff --git a/tools/perf/util/python.c b/tools/perf/util/python.c
index 381f4fd..aa76519 100644
--- a/tools/perf/util/python.c
+++ b/tools/perf/util/python.c
@@ -33,13 +33,6 @@ int eprintf(int level, const char *fmt, ...)
 # define PyVarObject_HEAD_INIT(type, size) PyObject_HEAD_INIT(type) size,
 #endif
 
-struct throttle_event {
-	struct perf_event_header header;
-	u64			 time;
-	u64			 id;
-	u64			 stream_id;
-};
-
 PyMODINIT_FUNC initperf(void);
 
 #define member_def(type, member, ptype, help) \
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c
index 07642a7..787c234 100644
--- a/tools/perf/util/session.c
+++ b/tools/perf/util/session.c
@@ -376,6 +376,17 @@ static void perf_event__read_swap(union perf_event *event, bool sample_id_all)
 		swap_sample_id_all(event, &event->read + 1);
 }
 
+static void perf_event__throttle_swap(union perf_event *event,
+				      bool sample_id_all)
+{
+	event->throttle.time	  = bswap_64(event->throttle.time);
+	event->throttle.id	  = bswap_64(event->throttle.id);
+	event->throttle.stream_id = bswap_64(event->throttle.stream_id);
+
+	if (sample_id_all)
+		swap_sample_id_all(event, &event->throttle + 1);
+}
+
 static u8 revbyte(u8 b)
 {
 	int rev = (b >> 4) | ((b & 0xf) << 4);
@@ -460,6 +471,8 @@ static perf_event__swap_op perf_event__swap_ops[] = {
 	[PERF_RECORD_EXIT]		  = perf_event__task_swap,
 	[PERF_RECORD_LOST]		  = perf_event__all64_swap,
 	[PERF_RECORD_READ]		  = perf_event__read_swap,
+	[PERF_RECORD_THROTTLE]		  = perf_event__throttle_swap,
+	[PERF_RECORD_UNTHROTTLE]	  = perf_event__throttle_swap,
 	[PERF_RECORD_SAMPLE]		  = perf_event__all64_swap,
 	[PERF_RECORD_HEADER_ATTR]	  = perf_event__hdr_attr_swap,
 	[PERF_RECORD_HEADER_EVENT_TYPE]	  = perf_event__event_type_swap,
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 05/25] perf tests: Add simple session read/write test
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (3 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 04/25] perf tools: Adding throttle event data struct support Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 06/25] perf tests: Add session reading test for little endian perf data Jiri Olsa
                   ` (21 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding simple session read/write test to keep up
with file format changes.

Dumping the session to the file with several events
and reading it again back.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Makefile               |   1 +
 tools/perf/tests/builtin-test.c   |   4 +
 tools/perf/tests/session-simple.c | 602 ++++++++++++++++++++++++++++++++++++++
 tools/perf/tests/tests.h          |   1 +
 4 files changed, 608 insertions(+)
 create mode 100644 tools/perf/tests/session-simple.c

diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index ecebfd0..7484119 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -394,6 +394,7 @@ ifeq ($(ARCH),x86)
 LIB_OBJS += $(OUTPUT)tests/perf-time-to-tsc.o
 endif
 LIB_OBJS += $(OUTPUT)tests/code-reading.o
+LIB_OBJS += $(OUTPUT)tests/session-simple.o
 
 BUILTIN_OBJS += $(OUTPUT)builtin-annotate.o
 BUILTIN_OBJS += $(OUTPUT)builtin-bench.o
diff --git a/tools/perf/tests/builtin-test.c b/tools/perf/tests/builtin-test.c
index 8ad9415..e40aec9 100644
--- a/tools/perf/tests/builtin-test.c
+++ b/tools/perf/tests/builtin-test.c
@@ -108,6 +108,10 @@ static struct test {
 		.func = test__sample_parsing,
 	},
 	{
+		.desc = "Test session - simple read/write",
+		.func = test__session_simple,
+	},
+	{
 		.func = NULL,
 	},
 };
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
new file mode 100644
index 0000000..612f84d
--- /dev/null
+++ b/tools/perf/tests/session-simple.c
@@ -0,0 +1,602 @@
+
+/*
+ * FIXME Missing test for PERF_RECORD_READ event.
+ */
+
+#include <stdlib.h>
+#include <linux/kernel.h>
+
+#include "tests.h"
+#include "session.h"
+#include "header.h"
+#include "util.h"
+#include "evlist.h"
+
+#define EVENTS_MMAP 5
+#define EVENTS_LOST 6
+#define EVENTS_COMM 3
+#define EVENTS_EXIT 4
+#define EVENTS_FORK 8
+#define EVENTS_THROTTLE 2
+#define EVENTS_UNTHROTTLE 3
+#define EVENTS_SAMPLE 4
+
+static int events_mmap;
+static int events_lost;
+static int events_comm;
+static int events_exit;
+static int events_fork;
+static int events_throttle;
+static int events_unthrottle;
+static int events_sample;
+
+/* global sample type for sample */
+static u64 sample_type = PERF_SAMPLE_IP |
+			 PERF_SAMPLE_TID |
+			 PERF_SAMPLE_TIME |
+			 PERF_SAMPLE_ADDR |
+			 PERF_SAMPLE_ID |
+			 PERF_SAMPLE_CPU |
+			 PERF_SAMPLE_PERIOD |
+			 PERF_SAMPLE_STREAM_ID |
+			 PERF_SAMPLE_WEIGHT |
+			 PERF_SAMPLE_DATA_SRC;
+
+static char *get_file(void)
+{
+	static char buf[PATH_MAX];
+	int fd;
+
+	snprintf(buf, PATH_MAX, "/tmp/perf-test-session-simple-data-XXXXXX");
+	fd = mkstemp(buf);
+	if (fd < 0) {
+		pr_err("mkstemp failed");
+		return NULL;
+	}
+
+	close(fd);
+
+	pr_debug("data file %s\n", buf);
+	return buf;
+}
+
+static union perf_event *get_event_MMAP(void)
+{
+	static union perf_event event;
+	size_t size;
+
+	size = snprintf(event.mmap.filename, sizeof(event.mmap.filename),
+			"krava") + 1;
+	size = PERF_ALIGN(size, sizeof(u64));
+
+	event.header.type = PERF_RECORD_MMAP;
+	event.header.misc = PERF_RECORD_MISC_KERNEL;
+	event.header.size = sizeof(event.mmap) -
+			    (sizeof(event.mmap.filename) - size);
+
+	event.mmap.pgoff = 10;
+	event.mmap.start = 0;
+	event.mmap.len   = 10;
+	event.mmap.pid   = 123;
+
+	return &event;
+}
+
+static int process_mmap(struct perf_tool *tool __maybe_unused,
+			union perf_event *event,
+			struct perf_sample *sample __maybe_unused,
+			struct machine *machine __maybe_unused)
+{
+	pr_debug("event MMAP misc %d, pgoff %lu, start %lu,"
+		 " len %lu, pid %d, filename '%s'\n",
+		 event->header.misc,
+		 event->mmap.pgoff,
+		 event->mmap.start,
+		 event->mmap.len,
+		 event->mmap.pid,
+		 event->mmap.filename);
+
+	TEST_ASSERT_VAL("wrong MMAP misc\n",
+		event->header.misc == PERF_RECORD_MISC_KERNEL);
+
+	TEST_ASSERT_VAL("wrong MMAP pgoff\n",
+		event->mmap.pgoff == 10);
+
+	TEST_ASSERT_VAL("wrong MMAP start\n",
+		event->mmap.start == 0);
+
+	TEST_ASSERT_VAL("wrong MMAP len\n",
+		event->mmap.len == 10);
+
+	TEST_ASSERT_VAL("wrong MMAP pid\n",
+		event->mmap.pid == 123);
+
+	TEST_ASSERT_VAL("wrong MMAP filename\n",
+		!strcmp(event->mmap.filename, "krava"));
+
+	TEST_ASSERT_VAL("wrong MMAP misc\n",
+		event->header.misc == PERF_RECORD_MISC_KERNEL);
+
+	TEST_ASSERT_VAL("wrong MMAP pgoff\n",
+		event->mmap.pgoff == 10);
+
+	TEST_ASSERT_VAL("wrong MMAP start\n",
+		event->mmap.start == 0);
+
+	TEST_ASSERT_VAL("wrong MMAP len\n",
+		event->mmap.len == 10);
+
+	TEST_ASSERT_VAL("wrong MMAP pid\n",
+		event->mmap.pid == 123);
+
+	TEST_ASSERT_VAL("wrong MMAP filename\n",
+		!strcmp(event->mmap.filename, "krava"));
+
+	events_mmap++;
+	return 0;
+}
+
+static union perf_event *get_event_LOST(void)
+{
+	static union perf_event event;
+
+	event.header.type = PERF_RECORD_LOST;
+	event.header.misc = PERF_RECORD_MISC_USER;
+	event.header.size = sizeof(event.lost);
+
+	event.lost.id   = 12345;
+	event.lost.lost = 293467890514143;
+	return &event;
+}
+
+static int process_lost(struct perf_tool *tool __maybe_unused,
+			union perf_event *event,
+			struct perf_sample *sample __maybe_unused,
+			struct machine *machine __maybe_unused)
+{
+	pr_debug("event LOST id %lu, lost %lu\n",
+		 event->lost.id,
+		 event->lost.lost);
+
+	TEST_ASSERT_VAL("wrong LOST id\n",
+		event->lost.id == 12345);
+
+	TEST_ASSERT_VAL("wrong LOST lost\n",
+		event->lost.lost == 293467890514143);
+
+	events_lost++;
+	return 0;
+}
+
+static union perf_event *get_event_COMM(void)
+{
+	static union perf_event event;
+	size_t size;
+
+	size = snprintf(event.comm.comm, sizeof(event.comm.comm),
+			"krava") + 1;
+	size = PERF_ALIGN(size, sizeof(u64));
+
+	event.header.type = PERF_RECORD_COMM;
+	event.header.size = sizeof(event.comm) -
+			    (sizeof(event.comm.comm) - size);
+
+	event.comm.pid = 1234;
+	event.comm.tid = 4321;
+
+	return &event;
+}
+
+static int process_comm(struct perf_tool *tool __maybe_unused,
+			union perf_event *event,
+			struct perf_sample *sample __maybe_unused,
+			struct machine *machine __maybe_unused)
+{
+	pr_debug("event COMM pid %d, tid %d, comm '%s'\n",
+		 event->comm.pid,
+		 event->comm.tid,
+		 event->comm.comm);
+
+	TEST_ASSERT_VAL("wrong COMM pid\n",
+		event->comm.pid == 1234);
+
+	TEST_ASSERT_VAL("wrong COMM tid\n",
+		event->comm.tid == 4321);
+
+	TEST_ASSERT_VAL("wrong COMM comm\n",
+		!strcmp(event->comm.comm, "krava"));
+
+	events_comm++;
+	return 0;
+}
+
+static union perf_event *get_event_EXIT(void)
+{
+	static union perf_event event;
+
+	event.header.type = PERF_RECORD_EXIT;
+	event.header.size = sizeof(event.fork);
+
+	event.fork.pid = 2322;
+	event.fork.tid = 2232;
+	event.fork.ppid = 10;
+	event.fork.ptid = 1;
+	event.fork.time = 0xB16B00B5;
+
+	return &event;
+}
+
+static int process_exit(struct perf_tool *tool __maybe_unused,
+			union perf_event *event,
+			struct perf_sample *sample __maybe_unused,
+			struct machine *machine __maybe_unused)
+{
+	pr_debug("event EXIT pid %d, tid %d, ppid %d, ptid %d, time 0x%lx\n",
+		 event->fork.pid, event->fork.tid,
+		 event->fork.ppid, event->fork.ptid,
+		 event->fork.time);
+
+	TEST_ASSERT_VAL("wrong EXIT pid\n",
+		event->fork.pid == 2322);
+
+	TEST_ASSERT_VAL("wrong EXIT tid\n",
+		event->fork.tid == 2232);
+
+	TEST_ASSERT_VAL("wrong EXIT ppid\n",
+		event->fork.ppid == 10);
+
+	TEST_ASSERT_VAL("wrong EXIT ptid\n",
+		event->fork.ptid == 1);
+
+	TEST_ASSERT_VAL("wrong EXIT time\n",
+		event->fork.time == 0xB16B00B5);
+
+	events_exit++;
+	return 0;
+}
+
+static union perf_event *get_event_FORK(void)
+{
+	static union perf_event event;
+
+	event.header.type = PERF_RECORD_FORK;
+	event.header.size = sizeof(event.fork);
+
+	event.fork.pid  = 4321;
+	event.fork.tid  = 1234;
+	event.fork.ppid = 14321;
+	event.fork.ptid = 11234;
+	event.fork.time = 0xdeadbeef;
+
+	return &event;
+}
+
+static int process_fork(struct perf_tool *tool __maybe_unused,
+			union perf_event *event,
+			struct perf_sample *sample __maybe_unused,
+			struct machine *machine __maybe_unused)
+{
+	pr_debug("event FORK pid %d, tid %d, ppid %d, ptid %d, time 0x%lx\n",
+		 event->fork.pid, event->fork.tid,
+		 event->fork.ppid, event->fork.ptid,
+		 event->fork.time);
+
+	TEST_ASSERT_VAL("wrong FORK pid\n",
+		event->fork.pid == 4321);
+
+	TEST_ASSERT_VAL("wrong FORK tid\n",
+		event->fork.tid == 1234);
+
+	TEST_ASSERT_VAL("wrong FORK ppid\n",
+		event->fork.ppid == 14321);
+
+	TEST_ASSERT_VAL("wrong FORK ptid\n",
+		event->fork.ptid == 11234);
+
+	TEST_ASSERT_VAL("wrong FORK time\n",
+		event->fork.time == 0xdeadbeef);
+
+	events_fork++;
+	return 0;
+}
+
+static union perf_event *get_event_THROTTLE(void)
+{
+	static union perf_event event;
+
+	event.header.type = PERF_RECORD_THROTTLE;
+	event.header.size = sizeof(event.throttle);
+
+	event.throttle.time      = 0xdeadbeef;
+	event.throttle.id        = 123;
+	event.throttle.stream_id = 987;
+
+	return &event;
+}
+
+static int process_throttle(struct perf_tool *tool __maybe_unused,
+			    union perf_event *event,
+			    struct perf_sample *sample __maybe_unused,
+			    struct machine *machine __maybe_unused)
+{
+	pr_debug("event THROTTLE time 0x%lx, id 0x%lx, stream_id 0x%lx\n",
+		 event->throttle.time, event->throttle.id,
+		 event->throttle.stream_id);
+
+	TEST_ASSERT_VAL("wrong THROTTLE time\n",
+		event->throttle.time == 0xdeadbeef);
+
+	TEST_ASSERT_VAL("wrong THROTTLE id\n",
+		event->throttle.id == 123);
+
+	TEST_ASSERT_VAL("wrong THROTTLE id\n",
+		event->throttle.stream_id == 987);
+
+	events_throttle++;
+	return 0;
+}
+
+static union perf_event *get_event_UNTHROTTLE(void)
+{
+	static union perf_event event;
+
+	event.header.type = PERF_RECORD_UNTHROTTLE;
+	event.header.size = sizeof(event.throttle);
+
+	event.throttle.time      = 0xdeadbeef;
+	event.throttle.id        = 542318590;
+	event.throttle.stream_id = 2341238951;
+
+	return &event;
+}
+
+static int process_unthrottle(struct perf_tool *tool __maybe_unused,
+			      union perf_event *event,
+			      struct perf_sample *sample __maybe_unused,
+			      struct machine *machine __maybe_unused)
+{
+	pr_debug("event UNTHROTTLE time 0x%lx, id 0x%lx, stream_id 0x%lx\n",
+		 event->throttle.time, event->throttle.id,
+		 event->throttle.stream_id);
+
+	TEST_ASSERT_VAL("wrong UNTHROTTLE time\n",
+		event->throttle.time == 0xdeadbeef);
+
+	TEST_ASSERT_VAL("wrong UNTHROTTLE id\n",
+		event->throttle.id == 542318590);
+
+	TEST_ASSERT_VAL("wrong UNTHROTTLE id\n",
+		event->throttle.stream_id == 2341238951);
+
+	events_unthrottle++;
+	return 0;
+}
+
+static union perf_event *get_event_SAMPLE(void)
+{
+	static unsigned char buf[4096];
+	static union perf_event *event = (union perf_event *) buf;
+	struct perf_sample sample = {
+		.ip		= 0xaaa,
+		.pid		= 0xedfa,
+		.tid		= 0xabc,
+		.time		= 123456789,
+		.addr		= 0xabababab,
+		.id		= 0xedf234abf,
+		.stream_id	= 9273651,
+		.period		= 0xdead,
+		.weight		= 1,
+		.cpu		= 1024,
+		.data_src	= 3,
+	};
+	size_t sz;
+	int ret;
+
+	sz = perf_event__sample_event_size(&sample, sample_type, 0, 0);
+
+	event->header.type = PERF_RECORD_SAMPLE;
+	event->header.misc = 0;
+	event->header.size = sz;
+
+	ret = perf_event__synthesize_sample(event, sample_type, 0, 0,
+					    &sample, false);
+	return ret ? NULL : event;
+}
+
+static int process_sample(struct perf_tool *tool __maybe_unused,
+			  union perf_event *event __maybe_unused,
+			  struct perf_sample *sample,
+			  struct perf_evsel *evsel __maybe_unused,
+			  struct machine *machine __maybe_unused)
+{
+	pr_debug("event SAMPLE ip %lx, pid %x, tid %x, time %lx, "
+		 "addr %lx, id %lx, stream_id %lx, period %lx, "
+		 "weight %lx, cpu %x, data_src %lx\n",
+		 sample->ip, sample->pid, sample->tid, sample->time,
+		 sample->addr, sample->id, sample->stream_id,
+		 sample->period, sample->weight, sample->cpu,
+		 sample->data_src);
+
+	TEST_ASSERT_VAL("wrong SAMPLE ip\n", sample->ip == 0xaaa);
+	TEST_ASSERT_VAL("wrong SAMPLE pid\n", sample->pid == 0xedfa);
+	TEST_ASSERT_VAL("wrong SAMPLE tid\n", sample->tid == 0xabc);
+	TEST_ASSERT_VAL("wrong SAMPLE time\n", sample->time == 123456789);
+	TEST_ASSERT_VAL("wrong SAMPLE addr\n", sample->addr == 0xabababab);
+	TEST_ASSERT_VAL("wrong SAMPLE id\n", sample->id == 0xedf234abf);
+	TEST_ASSERT_VAL("wrong SAMPLE stream_id\n",
+			sample->stream_id == 9273651);
+	TEST_ASSERT_VAL("wrong SAMPLE period\n", sample->period == 0xdead);
+	TEST_ASSERT_VAL("wrong SAMPLE weight\n", sample->weight == 1);
+	TEST_ASSERT_VAL("wrong SAMPLE cpu\n", sample->cpu == 1024);
+	TEST_ASSERT_VAL("wrong SAMPLE data_src\n", sample->data_src == 3);
+
+	events_sample++;
+	return 0;
+}
+
+static int store_event(int fd, union perf_event *event, size_t *size)
+{
+	TEST_ASSERT_VAL("no event\n", event);
+	*size += event->header.size;
+	return write(fd, event, event->header.size) > 0 ? 0 : -1;
+}
+
+static int session_write(char *file)
+{
+	struct perf_session *session;
+	struct perf_evlist *evlist;
+	size_t size = 0;
+	int feat, fd;
+
+	fd = open(file, O_RDWR);
+	TEST_ASSERT_VAL("failed to open data file", fd >= 0);
+
+	evlist = perf_evlist__new_default();
+	TEST_ASSERT_VAL("failed to get evlist", evlist);
+
+	perf_evlist__first(evlist)->attr.sample_type = sample_type;
+
+	pr_debug("session writing start\n");
+
+	session = perf_session__new(file, O_WRONLY, true, false, NULL);
+	TEST_ASSERT_VAL("failed to create session", session);
+
+	session->evlist = evlist;
+	session->fd     = fd;
+
+	for (feat = HEADER_FIRST_FEATURE; feat < HEADER_LAST_FEATURE; feat++)
+		perf_header__set_feat(&session->header, feat);
+
+	perf_header__clear_feat(&session->header, HEADER_BUILD_ID);
+	perf_header__clear_feat(&session->header, HEADER_TRACING_DATA);
+	perf_header__clear_feat(&session->header, HEADER_BRANCH_STACK);
+
+	TEST_ASSERT_VAL("failed to write header",
+		!perf_session__write_header(session, evlist, fd, false));
+
+#define STORE_EVENTS(str, func, cnt)				\
+do {								\
+	int i;							\
+	for (i = 0; i < cnt; i++) {				\
+		TEST_ASSERT_VAL(str,				\
+			!store_event(fd, func(), &size));	\
+	}							\
+} while (0)
+
+	STORE_EVENTS("failed to store MMAP event",
+		     get_event_MMAP, EVENTS_MMAP);
+
+	STORE_EVENTS("failed to store LOST event",
+		     get_event_LOST, EVENTS_LOST);
+
+	STORE_EVENTS("failed to store COMM event",
+		     get_event_COMM, EVENTS_COMM);
+
+	STORE_EVENTS("failed to store EXIT event",
+		     get_event_EXIT, EVENTS_EXIT);
+
+	STORE_EVENTS("failed to store FORK event",
+		     get_event_FORK, EVENTS_FORK);
+
+	STORE_EVENTS("failed to store THROTTLE event",
+		     get_event_THROTTLE, EVENTS_THROTTLE);
+
+	STORE_EVENTS("failed to store UNTHROTTLE event",
+		     get_event_UNTHROTTLE, EVENTS_UNTHROTTLE);
+
+	STORE_EVENTS("failed to store SAMPLE event",
+		     get_event_SAMPLE, EVENTS_SAMPLE);
+
+#undef STORE_EVENTS
+
+	session->header.data_size += size;
+
+	TEST_ASSERT_VAL("failed to write header",
+		!perf_session__write_header(session, evlist, fd, true));
+
+	perf_session__delete(session);
+	perf_evlist__delete(evlist);
+
+	pr_debug("session writing stop\n");
+	return 0;
+}
+
+static int __session_read(char *file)
+{
+	struct perf_session *session;
+	struct perf_tool tool = {
+		.mmap = process_mmap,
+		.lost = process_lost,
+		.comm = process_comm,
+		.exit = process_exit,
+		.fork = process_fork,
+		.throttle = process_throttle,
+		.unthrottle = process_unthrottle,
+		.sample = process_sample,
+	};
+
+	pr_debug("session reading start\n");
+
+	session = perf_session__new(file, O_RDONLY, false, false, &tool);
+	TEST_ASSERT_VAL("failed to create session", session);
+
+	TEST_ASSERT_VAL("failed to process events",
+		perf_session__process_events(session, &tool) == 0);
+
+	perf_session__delete(session);
+
+	pr_debug("session reading stop\n");
+	return 0;
+}
+
+static int session_read(char *file)
+{
+	events_mmap = 0;
+	events_lost = 0;
+	events_comm = 0;
+	events_exit = 0;
+	events_fork = 0;
+	events_throttle = 0;
+	events_unthrottle = 0;
+	events_sample = 0;
+
+	if (__session_read(file))
+		return -1;
+
+	TEST_ASSERT_VAL("wrong MMAP events count", events_mmap == EVENTS_MMAP);
+	TEST_ASSERT_VAL("wrong LOST events count", events_lost == EVENTS_LOST);
+	TEST_ASSERT_VAL("wrong COMM events count", events_comm == EVENTS_COMM);
+	TEST_ASSERT_VAL("wrong EXIT events count", events_exit == EVENTS_EXIT);
+	TEST_ASSERT_VAL("wrong FORK events count", events_fork == EVENTS_FORK);
+	TEST_ASSERT_VAL("wrong THROTTLE events count",
+			events_throttle == EVENTS_THROTTLE);
+	TEST_ASSERT_VAL("wrong UNTHROTTLE events count",
+			events_unthrottle == EVENTS_UNTHROTTLE);
+	TEST_ASSERT_VAL("wrong SAMPLE events count",
+			events_sample == EVENTS_SAMPLE);
+	return 0;
+}
+
+static int test_generated_data(void)
+{
+	char *file = get_file();
+	int err = 0;
+
+	TEST_ASSERT_VAL("failed to get temporary file", file);
+
+	err = session_write(file);
+	if (!err)
+		err = session_read(file);
+
+	unlink(file);
+	return err;
+}
+
+int test__session_simple(void)
+{
+	int err;
+
+	pr_debug("Testing generated data\n");
+	err = test_generated_data();
+	return err;
+}
diff --git a/tools/perf/tests/tests.h b/tools/perf/tests/tests.h
index 83d5b71..94b04cd 100644
--- a/tools/perf/tests/tests.h
+++ b/tools/perf/tests/tests.h
@@ -38,5 +38,6 @@ int test__sw_clock_freq(void);
 int test__perf_time_to_tsc(void);
 int test__code_reading(void);
 int test__sample_parsing(void);
+int test__session_simple(void);
 
 #endif /* TESTS_H */
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 06/25] perf tests: Add session reading test for little endian perf data
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (4 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 05/25] perf tests: Add simple session read/write test Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 07/25] perf tests: Add session reading test for big " Jiri Olsa
                   ` (20 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding session reading test for little endian perf data
included as binary data in the test object.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Makefile                |   1 +
 tools/perf/tests/perf.data.v2.le.h | 219 +++++++++++++++++++++++++++++++++++++
 tools/perf/tests/session-simple.c  |  33 ++++++
 3 files changed, 253 insertions(+)
 create mode 100644 tools/perf/tests/perf.data.v2.le.h

diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index 7484119..c4498c2 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -292,6 +292,7 @@ LIB_H += ui/helpline.h
 LIB_H += ui/progress.h
 LIB_H += ui/util.h
 LIB_H += ui/ui.h
+LIB_H += tests/perf.data.v2.le.h
 
 LIB_OBJS += $(OUTPUT)util/abspath.o
 LIB_OBJS += $(OUTPUT)util/alias.o
diff --git a/tools/perf/tests/perf.data.v2.le.h b/tools/perf/tests/perf.data.v2.le.h
new file mode 100644
index 0000000..b5aa5f7
--- /dev/null
+++ b/tools/perf/tests/perf.data.v2.le.h
@@ -0,0 +1,219 @@
+/*
+ * generated by:
+ * od -v -t x1 data | cut -f2- -d' ' -s | sed 's/\([a-f0-9][a-f0-9]\)/0x\1,/g' > tests/perf.data.v2.le.h
+ */
+
+0x50, 0x45, 0x52, 0x46, 0x49, 0x4c, 0x45, 0x32, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xd8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x48, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf8, 0x7f, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xcf, 0xc3, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00,
+0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00, 0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00,
+0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00, 0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00,
+0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00, 0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe1, 0x10, 0x00, 0x00, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0xd2, 0x04, 0x00, 0x00, 0xe1, 0x10, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe1, 0x10, 0x00, 0x00, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdb, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdb, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0xfe, 0x1f, 0x53, 0x20, 0x00, 0x00, 0x00, 0x00, 0xa7, 0x78, 0x8c, 0x8b, 0x00, 0x00, 0x00, 0x00,
+0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0xfe, 0x1f, 0x53, 0x20, 0x00, 0x00, 0x00, 0x00, 0xa7, 0x78, 0x8c, 0x8b, 0x00, 0x00, 0x00, 0x00,
+0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0xfe, 0x1f, 0x53, 0x20, 0x00, 0x00, 0x00, 0x00, 0xa7, 0x78, 0x8c, 0x8b, 0x00, 0x00, 0x00, 0x00,
+0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00, 0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00,
+0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00, 0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00,
+0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00,
+0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00,
+0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00, 0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00, 0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00,
+0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00, 0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00,
+0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00,
+0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00,
+0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00, 0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x44, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x88, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xcc, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x10, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x18, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x5c, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xa0, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xa8, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xbc, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6c, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xd4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x40, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x9c, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb4, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x50, 0x0d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x40, 0x00, 0x00, 0x00, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x33, 0x2e, 0x39, 0x2e, 0x38, 0x2d, 0x31, 0x30,
+0x30, 0x2e, 0x66, 0x63, 0x31, 0x37, 0x2e, 0x78, 0x38, 0x36, 0x5f, 0x36, 0x34, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x33, 0x2e, 0x31, 0x31,
+0x2e, 0x72, 0x63, 0x31, 0x2e, 0x67, 0x65, 0x30, 0x31, 0x39, 0x35, 0x31, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x78, 0x38, 0x36, 0x5f, 0x36, 0x34, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x49, 0x6e, 0x74, 0x65,
+0x6c, 0x28, 0x52, 0x29, 0x20, 0x43, 0x6f, 0x72, 0x65, 0x28, 0x54, 0x4d, 0x29, 0x20, 0x69, 0x37,
+0x2d, 0x32, 0x36, 0x34, 0x30, 0x4d, 0x20, 0x43, 0x50, 0x55, 0x20, 0x40, 0x20, 0x32, 0x2e, 0x38,
+0x30, 0x47, 0x48, 0x7a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x47, 0x65, 0x6e, 0x75, 0x69, 0x6e, 0x65, 0x49, 0x6e, 0x74, 0x65, 0x6c, 0x2c, 0x36, 0x2c, 0x34,
+0x32, 0x2c, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xac, 0xf5, 0x7a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x2f, 0x68, 0x6f, 0x6d, 0x65, 0x2f, 0x6a, 0x6f, 0x6c, 0x73, 0x61, 0x2f, 0x6b, 0x65, 0x72, 0x6e,
+0x65, 0x6c, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x6c, 0x69, 0x6e, 0x75, 0x78, 0x2d, 0x70, 0x65, 0x72,
+0x66, 0x2f, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x2f, 0x70, 0x65, 0x72, 0x66, 0x2f, 0x70, 0x65, 0x72,
+0x66, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x40, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x73, 0x65, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x2d, 0x76, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
+0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xcf, 0xc3, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x63, 0x79, 0x63, 0x6c,
+0x65, 0x73, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
+0x40, 0x00, 0x00, 0x00, 0x30, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x30, 0x2d, 0x31, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x32, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf0, 0x2c, 0x7e, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xe4, 0xc0, 0x4d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x30, 0x2d, 0x33, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x63, 0x70, 0x75, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72, 0x65, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x74, 0x72, 0x61, 0x63, 0x65, 0x70, 0x6f, 0x69,
+0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x75, 0x6e, 0x63, 0x6f, 0x72, 0x65, 0x5f, 0x63, 0x62, 0x6f, 0x78, 0x5f, 0x30, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x75, 0x6e, 0x63, 0x6f, 0x72, 0x65, 0x5f, 0x63,
+0x62, 0x6f, 0x78, 0x5f, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x62, 0x72, 0x65, 0x61, 0x6b, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00,
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index 612f84d..e975ec3 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -21,6 +21,10 @@
 #define EVENTS_UNTHROTTLE 3
 #define EVENTS_SAMPLE 4
 
+char data_file_v2_le[] = {
+#include "perf.data.v2.le.h"
+};
+
 static int events_mmap;
 static int events_lost;
 static int events_comm;
@@ -592,11 +596,40 @@ static int test_generated_data(void)
 	return err;
 }
 
+static int file_write(char *file, char *data, ssize_t size)
+{
+	int fd = open(file, O_TRUNC|O_RDWR);
+	int err = 0;
+
+	if (size != write(fd, data, size))
+		err = -1;
+
+	close(fd);
+	return err;
+}
+
+static int test_file_data(char *data, ssize_t size)
+{
+	char *file = get_file();
+	int err = 0;
+
+	TEST_ASSERT_VAL("failed to get temporary file", file);
+
+	err = file_write(file, data, size);
+	if (!err)
+		err = session_read(file);
+
+	unlink(file);
+	return err;
+}
+
 int test__session_simple(void)
 {
 	int err;
 
 	pr_debug("Testing generated data\n");
 	err = test_generated_data();
+	pr_debug("Testing v2 LE data\n");
+	err |= test_file_data(data_file_v2_le, sizeof(data_file_v2_le));
 	return err;
 }
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 07/25] perf tests: Add session reading test for big endian perf data
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (5 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 06/25] perf tests: Add session reading test for little endian perf data Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 08/25] perf doc: Add perf data file documentation Jiri Olsa
                   ` (19 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding session reading test for big endian perf data
included as binary data in the test object.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Makefile                |   1 +
 tools/perf/tests/perf.data.v2.be.h | 265 +++++++++++++++++++++++++++++++++++++
 tools/perf/tests/session-simple.c  |   6 +
 3 files changed, 272 insertions(+)
 create mode 100644 tools/perf/tests/perf.data.v2.be.h

diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index c4498c2..2510355 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -293,6 +293,7 @@ LIB_H += ui/progress.h
 LIB_H += ui/util.h
 LIB_H += ui/ui.h
 LIB_H += tests/perf.data.v2.le.h
+LIB_H += tests/perf.data.v2.be.h
 
 LIB_OBJS += $(OUTPUT)util/abspath.o
 LIB_OBJS += $(OUTPUT)util/alias.o
diff --git a/tools/perf/tests/perf.data.v2.be.h b/tools/perf/tests/perf.data.v2.be.h
new file mode 100644
index 0000000..ce2c0ba
--- /dev/null
+++ b/tools/perf/tests/perf.data.v2.be.h
@@ -0,0 +1,265 @@
+/*
+ * generated by:
+ * od -v -t x1 data | cut -f2- -d' ' -s | sed 's/\([a-f0-9][a-f0-9]\)/0x\1,/g' > tests/perf.data.v2.be.h
+ */
+
+0x32, 0x45, 0x4c, 0x49, 0x46, 0x52, 0x45, 0x50, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xd8,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x48, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x7f, 0xf8,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc3, 0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39, 0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf,
+0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
+0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf, 0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39, 0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf,
+0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
+0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf, 0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39, 0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf,
+0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
+0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x18,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x10, 0xe1, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x10, 0xe1,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x18,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x10, 0xe1, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0xdb,
+0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0xdb,
+0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x20, 0x53, 0x1f, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x8c, 0x78, 0xa7,
+0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x20, 0x53, 0x1f, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x8c, 0x78, 0xa7,
+0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x20, 0x53, 0x1f, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x8c, 0x78, 0xa7,
+0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa,
+0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15,
+0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa, 0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab,
+0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33,
+0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03,
+0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa,
+0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15,
+0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa, 0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab,
+0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33,
+0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x88, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0xcc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x5c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0xa0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0xa8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x14,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb0,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x6c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x48,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0xb4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5c,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x24,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x34, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04,
+0x00, 0x00, 0x00, 0x40, 0x69, 0x62, 0x6d, 0x2d, 0x70, 0x37, 0x35, 0x30, 0x65, 0x2d, 0x30, 0x31,
+0x2d, 0x6c, 0x70, 0x31, 0x2e, 0x72, 0x68, 0x74, 0x73, 0x2e, 0x65, 0x6e, 0x67, 0x2e, 0x62, 0x6f,
+0x73, 0x2e, 0x72, 0x65, 0x64, 0x68, 0x61, 0x74, 0x2e, 0x63, 0x6f, 0x6d, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x33, 0x2e, 0x37, 0x2e, 0x30, 0x2d, 0x30, 0x2e,
+0x33, 0x36, 0x2e, 0x65, 0x6c, 0x37, 0x2e, 0x70, 0x70, 0x63, 0x36, 0x34, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x33, 0x2e, 0x39, 0x2e,
+0x72, 0x63, 0x32, 0x2e, 0x67, 0x65, 0x30, 0x31, 0x39, 0x35, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x70, 0x70, 0x63, 0x36, 0x34, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x40, 0x50, 0x4f, 0x57, 0x45,
+0x52, 0x37, 0x20, 0x28, 0x61, 0x72, 0x63, 0x68, 0x69, 0x74, 0x65, 0x63, 0x74, 0x65, 0x64, 0x29,
+0x2c, 0x20, 0x61, 0x6c, 0x74, 0x69, 0x76, 0x65, 0x63, 0x20, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72,
+0x74, 0x65, 0x64, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x36, 0x33, 0x2c, 0x35, 0x31, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0xf6, 0xad, 0x40, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40,
+0x2f, 0x72, 0x6f, 0x6f, 0x74, 0x2f, 0x6c, 0x69, 0x6e, 0x75, 0x78, 0x2d, 0x70, 0x65, 0x72, 0x66,
+0x2f, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x2f, 0x70, 0x65, 0x72, 0x66, 0x2f, 0x70, 0x65, 0x72, 0x66,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x74, 0x65, 0x73, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x73, 0x65, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x2d, 0x76, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0xc3, 0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x63, 0x79, 0x63, 0x6c,
+0x65, 0x73, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
+0x00, 0x00, 0x00, 0x40, 0x30, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x34, 0x2d, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x38, 0x2d, 0x31, 0x31,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x31, 0x32, 0x2d, 0x31, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x31, 0x36, 0x2d, 0x31, 0x39, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x32, 0x30, 0x2d, 0x32, 0x33, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x32, 0x34, 0x2d, 0x32,
+0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x32, 0x38, 0x2d, 0x33, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x40, 0x30, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x34, 0x2d, 0x37, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x38, 0x2d, 0x31, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x31, 0x32, 0x2d, 0x31, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x31, 0x36, 0x2d, 0x31, 0x39, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x32, 0x30, 0x2d, 0x32,
+0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x32, 0x34, 0x2d, 0x32, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x32, 0x38, 0x2d, 0x33, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x95, 0x11, 0x40, 0x00, 0x00, 0x00, 0x40,
+0x30, 0x2d, 0x33, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40, 0x63, 0x70, 0x75, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x40, 0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72, 0x65, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x40, 0x74, 0x72, 0x61, 0x63,
+0x65, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05,
+0x00, 0x00, 0x00, 0x40, 0x62, 0x72, 0x65, 0x61, 0x6b, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index e975ec3..4f58c0f 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -25,6 +25,10 @@ char data_file_v2_le[] = {
 #include "perf.data.v2.le.h"
 };
 
+char data_file_v2_be[] = {
+#include "perf.data.v2.be.h"
+};
+
 static int events_mmap;
 static int events_lost;
 static int events_comm;
@@ -631,5 +635,7 @@ int test__session_simple(void)
 	err = test_generated_data();
 	pr_debug("Testing v2 LE data\n");
 	err |= test_file_data(data_file_v2_le, sizeof(data_file_v2_le));
+	pr_debug("Testing v2 BE data\n");
+	err |= test_file_data(data_file_v2_be, sizeof(data_file_v2_be));
 	return err;
 }
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 08/25] perf doc: Add perf data file documentation
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (6 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 07/25] perf tests: Add session reading test for big " Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 09/25] perf tools: Introduce perf data file version CHECK macro Jiri Olsa
                   ` (18 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding perf data file documentation.

TODO Finish the FEATURES section

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Documentation/perf-data-file-v2.txt | 264 +++++++++++++++++++++++++
 1 file changed, 264 insertions(+)
 create mode 100644 tools/perf/Documentation/perf-data-file-v2.txt

diff --git a/tools/perf/Documentation/perf-data-file-v2.txt b/tools/perf/Documentation/perf-data-file-v2.txt
new file mode 100644
index 0000000..f5c1d5b8
--- /dev/null
+++ b/tools/perf/Documentation/perf-data-file-v2.txt
@@ -0,0 +1,264 @@
+perf-data-file-v2(5)
+====================
+
+NAME
+----
+perf-data-file-v2 - The perf tool file format version 2
+
+
+DESCRIPTION
+-----------
+Following text describes version 2 of the perf data file format,
+which is version that is currently used by perf tool.
+
+The perf data file format is composed of several sections
+describing monitored events and the data itself.
+
+High level view of the format:
+  FILE HEADER
+  EVENT IDS
+  EVENT ATTRIBUTES
+  EVENT TYPES
+  EVENT DATA
+  FEATURES
+
+
+COMMON PRIMITIVES
+-----------------
+Following definitions are used as primitives on multiple places
+within the perf data file.
+
+struct perf_file_section::
+  Used to determine location of data sections within the file.
+
+  struct perf_file_section {
+        u64 offset;
+        u64 size;
+  };
+
+  offset  section location (offset) within the file
+  size    section size in bytes
+
+
+FILE HEADER
+-----------
+Starting point of the data file with magic bytes and global
+section information.
+
+The section contains following data:
+  struct perf_file_header header
+
+struct perf_file_header::
+  struct perf_file_header {
+        u64                             magic;
+        u64                             size;
+        u64                             attr_size;
+        struct perf_file_section        attrs;
+        struct perf_file_section        data;
+        struct perf_file_section        event_types;
+        DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
+  }
+
+  magic           ID 'PERFFILE|PERFILE2'
+  size            header size sizeof(struct perf_file_header)
+  attr_size       attribute size sizeof(struct perf_file_attr)
+                  (see EVENT ATTRIBUTES)
+  attrs           location of 'EVENT ATTRIBUTES'
+  data            location of 'EVENT DATA'
+  event_types     location of 'EVENT TYPES'
+  adds_features   'FEATURES' bitmask
+
+
+EVENT IDS
+---------
+This section contains CPU related IDs for each monitored event.
+It is used only if there was more than 1 events monitored. The
+reason is to be able to map event's data to event definition.
+
+The section contains following data:
+  u64  event1_ids[]
+  u64  event2_ids[]
+  ...
+  u64  eventX_ids[]
+
+eventX_ids::
+  per-cpu event X IDs array
+  this array is referenced in 'EVENT ATTRIBUTES'
+
+
+EVENT ATTRIBUTES
+----------------
+This section contains attribute information together with the
+location of the IDs array for each event.
+
+The section contains following data:
+  struct perf_file_attr  attrs[]
+
+struct perf_file_attr::
+  struct perf_file_attr {
+        struct perf_event_attr    attr;
+        struct perf_file_section  ids;
+  }
+
+  attr  perf event interface structure for each event
+  ids   IDs location for event in 'EVENT IDS' section
+
+
+EVENT TYPES
+-----------
+This section map event's config value (struct perf_event_attr::config)
+with the event name.
+
+The section contains following data:
+  struct perf_trace_event_type  types[]
+
+#define MAX_EVENT_NAME 64
+
+struct perf_trace_event_type::
+  struct perf_trace_event_type {
+        u64   event_id;
+        char  name[MAX_EVENT_NAME];
+  };
+
+  event_id  struct perf_event_attr::config value
+  name      event name
+
+NOTE This section got deprecated and its data are no longer stored.
+     The 'event_types' location in the header is zero-ed.
+
+
+EVENT DATA
+----------
+This section contains blob of all events data - auxiliary events
+and samples.
+
+
+FEATURES
+--------
+This section contains various configuration data and its contents
+depends on the header's adds_features bitmask. Each bit in this
+bitmask represent a single feature (0 - NOT present, 1 present).
+
+The section contains following data:
+  struct perf_file_section feature_locations[nr_features];
+
+  nr_features        number of present features bitmap_weight(adds_features)
+  feature_locations  location of each feature data
+
+Available features (possible max 256):
+  enum {
+        HEADER_RESERVED         = 0,
+        HEADER_TRACING_DATA     = 1,
+        HEADER_BUILD_ID,
+        HEADER_HOSTNAME,
+        HEADER_OSRELEASE,
+        HEADER_VERSION,
+        HEADER_ARCH,
+        HEADER_NRCPUS,
+        HEADER_CPUDESC,
+        HEADER_CPUID,
+        HEADER_TOTAL_MEM,
+        HEADER_CMDLINE,
+        HEADER_EVENT_DESC,
+        HEADER_CPU_TOPOLOGY,
+        HEADER_NUMA_TOPOLOGY,
+        HEADER_BRANCH_STACK,
+        HEADER_PMU_MAPPINGS,
+        HEADER_GROUP_DESC,
+        HEADER_LAST_FEATURE,
+        HEADER_FEAT_BITS        = 256,
+  }
+
+
+TODO finish FEATURES::* sections descriptions.
+
+FEATURES::HEADER_RESERVED
+-------------------------
+allways zero bit
+
+
+FEATURES::HEADER_TRACING_DATA
+-----------------------------
+tracing data
+
+
+FEATURES::HEADER_BUILD_ID
+-------------------------
+build ids
+
+
+FEATURES::HEADER_HOSTNAME
+-------------------------
+uname hostname
+
+
+FEATURES::HEADER_OSRELEASE
+--------------------------
+uname osrelease
+
+
+FEATURES::HEADER_VERSION
+------------------------
+perf version
+
+
+FEATURES::HEADER_ARCH
+---------------------
+uname arch
+
+
+FEATURES::HEADER_NRCPUS
+-----------------------
+offset          size(B) description
+0               4       sysconf(_SC_NPROCESSORS_CONF)
+4               4       sysconf(_SC_NPROCESSORS_ONLN)
+
+
+FEATURES::HEADER_CPUDESC
+------------------------
+/proc/cpuinfo data for 'Model name'
+
+
+FEATURES::HEADER_CPUID
+----------------------
+'vendor,family,model,step'
+
+
+FEATURES::HEADER_TOTAL_MEM
+--------------------------
+/proc/meminfo data for 'MemTotal'
+
+
+FEATURES::HEADER_CMDLINE
+------------------------
+perf complete command line
+
+
+FEATURES::HEADER_EVENT_DESC
+---------------------------
+event attributes plus related info(ids)
+
+
+FEATURES::HEADER_CPU_TOPOLOGY
+-----------------------------
+cpu topology
+
+
+FEATURES::HEADER_NUMA_TOPOLOGY
+------------------------------
+numa topology
+
+
+FEATURES::HEADER_BRANCH_STACK
+-----------------------------
+nothing
+
+
+FEATURES::HEADER_PMU_MAPPINGS
+-----------------------------
+available pmus
+
+
+FEATURES::HEADER_GROUP_DESC
+---------------------------
+event groups info
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 09/25] perf tools: Introduce perf data file version CHECK macro
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (7 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 08/25] perf doc: Add perf data file documentation Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 10/25] perf tools: Introduce swap_features function Jiri Olsa
                   ` (17 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Introducing perf data file version CHECK macro, so the check
is easily extensible for new versions.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 27 ++++++++++++++++-----------
 1 file changed, 16 insertions(+), 11 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index a33197a..bcded62 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -2496,18 +2496,23 @@ static int check_magic_endian(u64 magic, uint64_t hdr_sz,
 	 * - encode endianness of file
 	 */
 
-	/* check magic number with one endianness */
-	if (magic == __perf_magic2)
-		return 0;
-
-	/* check magic number with opposite endianness */
-	if (magic != __perf_magic2_sw)
-		return -1;
+#define CHECK(__m, __v)						\
+do {								\
+	/* check magic number with one endianness */		\
+	if (magic == __m)					\
+		goto v ## __v;					\
+	/* check magic number with opposite endianness */	\
+	if (magic != __m ## _sw)				\
+		break;						\
+	ph->needs_swap = true;					\
+ v ## __v:							\
+	ph->version = __v;					\
+	return 0;						\
+} while (0)
+
+	CHECK(__perf_magic2, PERF_HEADER_VERSION_2);
 
-	ph->needs_swap = true;
-	ph->version = PERF_HEADER_VERSION_2;
-
-	return 0;
+	return -1;
 }
 
 int perf_file_header__read(struct perf_file_header *header,
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 10/25] perf tools: Introduce swap_features function
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (8 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 09/25] perf tools: Introduce perf data file version CHECK macro Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 11/25] perf tools: Introduce swap_header function Jiri Olsa
                   ` (16 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Introducing swap_features function to make the swapping
code more clear and extensible.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 69 ++++++++++++++++++++++++------------------------
 1 file changed, 35 insertions(+), 34 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index bcded62..164510e 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -2515,6 +2515,39 @@ do {								\
 	return -1;
 }
 
+static void swap_features(unsigned long *adds_features)
+{
+	/*
+	 * feature bitmap is declared as an array of unsigned longs --
+	 * not good since its size can differ between the host that
+	 * generated the data file and the host analyzing the file.
+	 *
+	 * We need to handle endianness, but we don't know the size of
+	 * the unsigned long where the file was generated. Take a best
+	 * guess at determining it: try 64-bit swap first (ie., file
+	 * created on a 64-bit host), and check if the hostname feature
+	 * bit is set (this feature bit is forced on as of fbe96f2).
+	 * If the bit is not, undo the 64-bit swap and try a 32-bit
+	 * swap. If the hostname bit is still not set (e.g., older data
+	 * file), punt and fallback to the original behavior --
+	 * clearing all feature bits and setting buildid.
+	 */
+	mem_bswap_64(adds_features, BITS_TO_U64(HEADER_FEAT_BITS));
+
+	if (!test_bit(HEADER_HOSTNAME, adds_features)) {
+		/* unswap as u64 */
+		mem_bswap_64(adds_features, BITS_TO_U64(HEADER_FEAT_BITS));
+
+		/* unswap as u32 */
+		mem_bswap_32(adds_features, BITS_TO_U32(HEADER_FEAT_BITS));
+	}
+
+	if (!test_bit(HEADER_HOSTNAME, adds_features)) {
+		bitmap_zero(adds_features, HEADER_FEAT_BITS);
+		set_bit(HEADER_BUILD_ID, adds_features);
+	}
+}
+
 int perf_file_header__read(struct perf_file_header *header,
 			   struct perf_header *ph, int fd)
 {
@@ -2543,40 +2576,8 @@ int perf_file_header__read(struct perf_file_header *header,
 			bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
 		else
 			return -1;
-	} else if (ph->needs_swap) {
-		/*
-		 * feature bitmap is declared as an array of unsigned longs --
-		 * not good since its size can differ between the host that
-		 * generated the data file and the host analyzing the file.
-		 *
-		 * We need to handle endianness, but we don't know the size of
-		 * the unsigned long where the file was generated. Take a best
-		 * guess at determining it: try 64-bit swap first (ie., file
-		 * created on a 64-bit host), and check if the hostname feature
-		 * bit is set (this feature bit is forced on as of fbe96f2).
-		 * If the bit is not, undo the 64-bit swap and try a 32-bit
-		 * swap. If the hostname bit is still not set (e.g., older data
-		 * file), punt and fallback to the original behavior --
-		 * clearing all feature bits and setting buildid.
-		 */
-		mem_bswap_64(&header->adds_features,
-			    BITS_TO_U64(HEADER_FEAT_BITS));
-
-		if (!test_bit(HEADER_HOSTNAME, header->adds_features)) {
-			/* unswap as u64 */
-			mem_bswap_64(&header->adds_features,
-				    BITS_TO_U64(HEADER_FEAT_BITS));
-
-			/* unswap as u32 */
-			mem_bswap_32(&header->adds_features,
-				    BITS_TO_U32(HEADER_FEAT_BITS));
-		}
-
-		if (!test_bit(HEADER_HOSTNAME, header->adds_features)) {
-			bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
-			set_bit(HEADER_BUILD_ID, header->adds_features);
-		}
-	}
+	} else if (ph->needs_swap)
+		swap_features(header->adds_features);
 
 	memcpy(&ph->adds_features, &header->adds_features,
 	       sizeof(ph->adds_features));
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 11/25] perf tools: Introduce swap_header function
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (9 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 10/25] perf tools: Introduce swap_features function Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 12/25] perf tools: Separate version 2 specific perf data header bits Jiri Olsa
                   ` (15 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Introducing swap_header function to make the swapping
code more clear and extensible.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 31 ++++++++++++++++++-------------
 1 file changed, 18 insertions(+), 13 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 164510e..fba6a9a 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -2548,6 +2548,22 @@ static void swap_features(unsigned long *adds_features)
 	}
 }
 
+static int swap_header(struct perf_file_header *header)
+{
+	mem_bswap_64(header, offsetof(struct perf_file_header, adds_features));
+
+	if (header->size != sizeof(*header)) {
+		/* Support the previous format */
+		if (header->size == offsetof(typeof(*header), adds_features))
+			bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
+		else
+			return -1;
+	} else
+		swap_features(header->adds_features);
+
+	return 0;
+}
+
 int perf_file_header__read(struct perf_file_header *header,
 			   struct perf_header *ph, int fd)
 {
@@ -2565,19 +2581,8 @@ int perf_file_header__read(struct perf_file_header *header,
 		return -1;
 	}
 
-	if (ph->needs_swap) {
-		mem_bswap_64(header, offsetof(struct perf_file_header,
-			     adds_features));
-	}
-
-	if (header->size != sizeof(*header)) {
-		/* Support the previous format */
-		if (header->size == offsetof(typeof(*header), adds_features))
-			bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
-		else
-			return -1;
-	} else if (ph->needs_swap)
-		swap_features(header->adds_features);
+	if (ph->needs_swap && swap_header(header))
+		return -1;
 
 	memcpy(&ph->adds_features, &header->adds_features,
 	       sizeof(ph->adds_features));
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 12/25] perf tools: Separate version 2 specific perf data header bits
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (10 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 11/25] perf tools: Introduce swap_header function Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 13/25] perf tools: Using evlist as a holder for event_desc feature Jiri Olsa
                   ` (14 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Separating version 2 specific perf data header bits,
so the code could be extented with new format version.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 122 +++++++++++++++++++++++++++++++----------------
 tools/perf/util/header.h |  16 +++++--
 2 files changed, 92 insertions(+), 46 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index fba6a9a..3f58a3f 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -2319,18 +2319,21 @@ int perf_session__write_header(struct perf_session *session,
 		.magic	   = PERF_MAGIC,
 		.size	   = sizeof(f_header),
 		.attr_size = sizeof(f_attr),
-		.attrs = {
-			.offset = attr_offset,
-			.size   = evlist->nr_entries * sizeof(f_attr),
-		},
-		.data = {
-			.offset = header->data_offset,
-			.size	= header->data_size,
-		},
+		.v2        = {
+			.attrs = {
+				.offset = attr_offset,
+				.size   = evlist->nr_entries * sizeof(f_attr),
+			},
+			.data = {
+				.offset = header->data_offset,
+				.size	= header->data_size,
+			},
 		/* event_types is ignored, store zeros */
+		},
 	};
 
-	memcpy(&f_header.adds_features, &header->adds_features, sizeof(header->adds_features));
+	memcpy(&f_header.v2.adds_features, &header->adds_features,
+	       sizeof(header->adds_features));
 
 	lseek(fd, 0, SEEK_SET);
 	err = do_write(fd, &f_header, sizeof(f_header));
@@ -2548,22 +2551,34 @@ static void swap_features(unsigned long *adds_features)
 	}
 }
 
-static int swap_header(struct perf_file_header *header)
+static int swap_header_v2(struct perf_file_header *header)
 {
-	mem_bswap_64(header, offsetof(struct perf_file_header, adds_features));
+	struct perf_file_header_v2 *v2 = &header->v2;
+
+	mem_bswap_64(v2, offsetof(struct perf_file_header_v2,
+		     adds_features));
 
 	if (header->size != sizeof(*header)) {
 		/* Support the previous format */
-		if (header->size == offsetof(typeof(*header), adds_features))
-			bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
+		if (header->size == offsetof(typeof(*header), v2.adds_features))
+			bitmap_zero(v2->adds_features, HEADER_FEAT_BITS);
 		else
 			return -1;
 	} else
-		swap_features(header->adds_features);
+		swap_features(v2->adds_features);
 
 	return 0;
 }
 
+static int swap_header(struct perf_file_header *header)
+{
+	/* swap the generic part */
+	mem_bswap_64(header, offsetof(struct perf_file_header, v2));
+
+	/* version specific swap */
+	return swap_header_v2(header);
+}
+
 int perf_file_header__read(struct perf_file_header *header,
 			   struct perf_header *ph, int fd)
 {
@@ -2581,16 +2596,7 @@ int perf_file_header__read(struct perf_file_header *header,
 		return -1;
 	}
 
-	if (ph->needs_swap && swap_header(header))
-		return -1;
-
-	memcpy(&ph->adds_features, &header->adds_features,
-	       sizeof(ph->adds_features));
-
-	ph->data_offset  = header->data.offset;
-	ph->data_size	 = header->data.size;
-	ph->feat_offset  = header->data.offset + header->data.size;
-	return 0;
+	return ph->needs_swap ? swap_header(header) : 0;
 }
 
 static int perf_file_section__process(struct perf_file_section *section,
@@ -2742,12 +2748,13 @@ static int perf_evlist__prepare_tracepoint_events(struct perf_evlist *evlist,
 	return 0;
 }
 
-int perf_session__read_header(struct perf_session *session)
+static int __perf_session__read_header_v2(struct perf_session *session,
+					  struct perf_file_header *header)
 {
-	struct perf_header *header = &session->header;
-	struct perf_file_header	f_header;
-	struct perf_file_attr	f_attr;
-	u64			f_id;
+	struct perf_header		*ph = &session->header;
+	struct perf_file_header_v2	*v2 = &header->v2;
+	struct perf_file_attr		f_attr;
+	u64				f_id;
 	int nr_attrs, nr_ids, i, j;
 	int fd = session->fd;
 
@@ -2755,23 +2762,17 @@ int perf_session__read_header(struct perf_session *session)
 	if (session->evlist == NULL)
 		return -ENOMEM;
 
-	if (session->fd_pipe)
-		return perf_header__read_pipe(session);
-
-	if (perf_file_header__read(&f_header, header, fd) < 0)
-		return -EINVAL;
-
-	nr_attrs = f_header.attrs.size / f_header.attr_size;
-	lseek(fd, f_header.attrs.offset, SEEK_SET);
+	nr_attrs = v2->attrs.size / header->attr_size;
+	lseek(fd, v2->attrs.offset, SEEK_SET);
 
 	for (i = 0; i < nr_attrs; i++) {
 		struct perf_evsel *evsel;
 		off_t tmp;
 
-		if (read_attr(fd, header, &f_attr) < 0)
+		if (read_attr(fd, ph, &f_attr) < 0)
 			goto out_errno;
 
-		if (header->needs_swap)
+		if (ph->needs_swap)
 			perf_event__attr_swap(&f_attr.attr);
 
 		tmp = lseek(fd, 0, SEEK_CUR);
@@ -2780,7 +2781,7 @@ int perf_session__read_header(struct perf_session *session)
 		if (evsel == NULL)
 			goto out_delete_evlist;
 
-		evsel->needs_swap = header->needs_swap;
+		evsel->needs_swap = ph->needs_swap;
 		/*
 		 * Do it before so that if perf_evsel__alloc_id fails, this
 		 * entry gets purged too at perf_evlist__delete().
@@ -2799,7 +2800,8 @@ int perf_session__read_header(struct perf_session *session)
 		lseek(fd, f_attr.ids.offset, SEEK_SET);
 
 		for (j = 0; j < nr_ids; j++) {
-			if (perf_header__getbuffer64(header, fd, &f_id, sizeof(f_id)))
+			if (perf_header__getbuffer64(ph, fd, &f_id,
+						     sizeof(f_id)))
 				goto out_errno;
 
 			perf_evlist__id_add(session->evlist, evsel, 0, j, f_id);
@@ -2810,7 +2812,7 @@ int perf_session__read_header(struct perf_session *session)
 
 	symbol_conf.nr_events = nr_attrs;
 
-	perf_header__process_sections(header, fd, &session->pevent,
+	perf_header__process_sections(ph, fd, &session->pevent,
 				      perf_file_section__process);
 
 	if (perf_evlist__prepare_tracepoint_events(session->evlist,
@@ -2827,6 +2829,42 @@ out_delete_evlist:
 	return -ENOMEM;
 }
 
+
+static int perf_session__read_header_v2(struct perf_session *session,
+					struct perf_file_header *header)
+{
+	struct perf_header *ph = &session->header;
+	struct perf_file_header_v2 *v2 = &header->v2;
+
+	memcpy(&ph->adds_features, &v2->adds_features,
+	       sizeof(ph->adds_features));
+
+	ph->data_offset  = v2->data.offset;
+	ph->data_size	 = v2->data.size;
+	ph->feat_offset  = v2->data.offset + v2->data.size;
+
+	return __perf_session__read_header_v2(session, header);
+}
+
+static int perf_header_read_file(struct perf_session *session)
+{
+	struct perf_file_header header;
+
+	if (perf_file_header__read(&header, &session->header, session->fd))
+		return -1;
+
+	/* read v2 specific data */
+	return perf_session__read_header_v2(session, &header);
+}
+
+int perf_session__read_header(struct perf_session *session)
+{
+	if (session->fd_pipe)
+		return perf_header__read_pipe(session);
+
+	return perf_header_read_file(session) < 0 ? -EINVAL : 0;
+}
+
 int perf_event__synthesize_attr(struct perf_tool *tool,
 				struct perf_event_attr *attr, u32 ids, u64 *id,
 				perf_event__handler_t process)
diff --git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 307c9ae..c6ea4603 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -44,10 +44,7 @@ struct perf_file_section {
 	u64 size;
 };
 
-struct perf_file_header {
-	u64				magic;
-	u64				size;
-	u64				attr_size;
+struct perf_file_header_v2 {
 	struct perf_file_section	attrs;
 	struct perf_file_section	data;
 	/* event_types is ignored */
@@ -55,6 +52,17 @@ struct perf_file_header {
 	DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
 };
 
+struct perf_file_header {
+	u64	magic;
+	u64	size;
+	u64	attr_size;
+
+	/* version specific data */
+	union {
+		struct perf_file_header_v2 v2;
+	};
+};
+
 struct perf_pipe_file_header {
 	u64				magic;
 	u64				size;
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 13/25] perf tools: Using evlist as a holder for event_desc feature
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (11 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 12/25] perf tools: Separate version 2 specific perf data header bits Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 14/25] perf tools: Introduce perf.data version 3 format Jiri Olsa
                   ` (13 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Using evlist as a holder for events stored via event_desc
feature. The event_desc events data is same as the one
stored via main header. We will use event_desc data to
replace the main header data source in next patches.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 84 ++++++++++++++++++++++--------------------------
 1 file changed, 38 insertions(+), 46 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 3f58a3f..e43879e 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -1208,28 +1208,11 @@ static void print_cpu_topology(struct perf_header *ph, int fd __maybe_unused,
 	}
 }
 
-static void free_event_desc(struct perf_evsel *events)
-{
-	struct perf_evsel *evsel;
-
-	if (!events)
-		return;
-
-	for (evsel = events; evsel->attr.size; evsel++) {
-		if (evsel->name)
-			free(evsel->name);
-		if (evsel->id)
-			free(evsel->id);
-	}
-
-	free(events);
-}
-
-static struct perf_evsel *
+static struct perf_evlist *
 read_event_desc(struct perf_header *ph, int fd)
 {
-	struct perf_evsel *evsel, *events = NULL;
-	u64 *id;
+	struct perf_evlist *evlist = NULL;
+	struct perf_evsel *evsel;
 	void *buf = NULL;
 	u32 nre, sz, nr, i, j;
 	ssize_t ret;
@@ -1255,18 +1238,15 @@ read_event_desc(struct perf_header *ph, int fd)
 	if (!buf)
 		goto error;
 
-	/* the last event terminates with evsel->attr.size == 0: */
-	events = calloc(nre + 1, sizeof(*events));
-	if (!events)
+	evlist = perf_evlist__new();
+	if (!evlist)
 		goto error;
 
 	msz = sizeof(evsel->attr);
 	if (sz < msz)
 		msz = sz;
 
-	for (i = 0, evsel = events; i < nre; evsel++, i++) {
-		evsel->idx = i;
-
+	for (i = 0; i < nre; i++) {
 		/*
 		 * must read entire on-file attr struct to
 		 * sync up with layout.
@@ -1275,6 +1255,10 @@ read_event_desc(struct perf_header *ph, int fd)
 		if (ret != (ssize_t)sz)
 			goto error;
 
+		evsel = perf_evsel__new(buf, i);
+		if (!evsel)
+			goto error;
+
 		if (ph->needs_swap)
 			perf_event__attr_swap(buf);
 
@@ -1289,49 +1273,55 @@ read_event_desc(struct perf_header *ph, int fd)
 			evsel->needs_swap = true;
 		}
 
+		perf_evlist__add(evlist, evsel);
+
 		evsel->name = do_read_string(fd, ph);
 
 		if (!nr)
 			continue;
 
-		id = calloc(nr, sizeof(*id));
-		if (!id)
+		if (perf_evsel__alloc_id(evsel, 1, nr))
 			goto error;
+
 		evsel->ids = nr;
-		evsel->id = id;
 
 		for (j = 0 ; j < nr; j++) {
-			ret = readn(fd, id, sizeof(*id));
-			if (ret != (ssize_t)sizeof(*id))
+			u64 id;
+
+			ret = readn(fd, &id, sizeof(id));
+			if (ret != (ssize_t)sizeof(id))
 				goto error;
 			if (ph->needs_swap)
-				*id = bswap_64(*id);
-			id++;
+				id = bswap_64(id);
+
+			perf_evlist__id_add(evlist, evsel, 0, j, id);
 		}
 	}
 out:
 	if (buf)
 		free(buf);
-	return events;
+	return evlist;
 error:
-	if (events)
-		free_event_desc(events);
-	events = NULL;
+	if (evlist)
+		perf_evlist__delete(evlist);
+	evlist = NULL;
 	goto out;
 }
 
 static void print_event_desc(struct perf_header *ph, int fd, FILE *fp)
 {
-	struct perf_evsel *evsel, *events = read_event_desc(ph, fd);
+	struct perf_evlist *evlist;
+	struct perf_evsel *evsel;
 	u32 j;
 	u64 *id;
 
-	if (!events) {
+	evlist = read_event_desc(ph, fd);
+	if (!evlist) {
 		fprintf(fp, "# event desc: not available or unable to read\n");
 		return;
 	}
 
-	for (evsel = events; evsel->attr.size; evsel++) {
+	list_for_each_entry(evsel, &evlist->entries, node) {
 		fprintf(fp, "# event : name = %s, ", evsel->name);
 
 		fprintf(fp, "type = %d, config = 0x%"PRIx64
@@ -1364,7 +1354,7 @@ static void print_event_desc(struct perf_header *ph, int fd, FILE *fp)
 		fputc('\n', fp);
 	}
 
-	free_event_desc(events);
+	perf_evlist__delete(evlist);
 }
 
 static void print_total_mem(struct perf_header *ph, int fd __maybe_unused,
@@ -1785,17 +1775,19 @@ process_event_desc(struct perf_file_section *section __maybe_unused,
 		   void *data __maybe_unused)
 {
 	struct perf_session *session;
-	struct perf_evsel *evsel, *events = read_event_desc(header, fd);
+	struct perf_evlist *evlist;
+	struct perf_evsel *evsel;
 
-	if (!events)
+	evlist = read_event_desc(header, fd);
+	if (!evlist)
 		return 0;
 
 	session = container_of(header, struct perf_session, header);
-	for (evsel = events; evsel->attr.size; evsel++)
-		perf_evlist__set_event_name(session->evlist, evsel);
 
-	free_event_desc(events);
+	list_for_each_entry(evsel, &evlist->entries, node)
+		perf_evlist__set_event_name(session->evlist, evsel);
 
+	perf_evlist__delete(evlist);
 	return 0;
 }
 
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 14/25] perf tools: Introduce perf.data version 3 format
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (12 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 13/25] perf tools: Using evlist as a holder for event_desc feature Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 15/25] perf tools: Add perf data version 3 header swap Jiri Olsa
                   ` (12 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Introducing perf.data version 3 format. No functional change,
just introducing doc, magic bytes and the struct.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Documentation/perf-data-file-v3.txt | 63 ++++++++++++++++++++++++++
 tools/perf/util/header.c                       |  8 +++-
 tools/perf/util/header.h                       |  8 ++++
 3 files changed, 78 insertions(+), 1 deletion(-)
 create mode 100644 tools/perf/Documentation/perf-data-file-v3.txt

diff --git a/tools/perf/Documentation/perf-data-file-v3.txt b/tools/perf/Documentation/perf-data-file-v3.txt
new file mode 100644
index 0000000..9bf9464
--- /dev/null
+++ b/tools/perf/Documentation/perf-data-file-v3.txt
@@ -0,0 +1,63 @@
+perf-data-file-v3(5)
+====================
+
+NAME
+----
+perf-data-file-v3 - The perf tool file format version 3
+
+
+DESCRIPTION
+-----------
+Following text describes version 3 of the perf data file format,
+which is version that is currently used by perf tool.
+
+In version 3 we got rid of following sections:
+  EVENT IDS
+  EVENT ATTRIBUTES
+  EVENT TYPES
+
+and keep only data and features sections. All the data
+from above listed sections are now read from specific
+FEATURES sections.
+
+High level view of the format:
+  FILE HEADER
+  EVENT DATA
+  FEATURES
+
+
+FILE HEADER
+-----------
+Starting point of the data file with magic bytes and global
+section information.
+
+The section contains following data:
+  struct perf_file_header header
+
+struct perf_file_header::
+  struct perf_file_header {
+        u64  magic;
+        u64  size;
+        u64  attr_size;
+        struct perf_file_section  data;
+        struct perf_file_section  features;
+        DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
+  }
+
+  magic           ID 'PERFILE3'
+  size            header size sizeof(struct perf_file_header)
+  attr_size       attribute size sizeof(struct perf_file_attr)
+  data            location of 'EVENT DATA'
+  features        location of 'EVENT TYPES'
+  adds_features   'FEATURES' bitmask
+
+
+EVENT DATA
+----------
+This section contains blob of all events' data - auxiliary events
+and samples.
+
+
+FEATURES
+--------
+Same as in version 2.
diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index e43879e..db6b131 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -30,6 +30,7 @@ static const char **header_argv;
 
 /*
  * magic2 = "PERFILE2"
+ * magic3 = "PERFILE3"
  * must be a numerical value to let the endianness
  * determine the memory layout. That way we are able
  * to detect endianness when reading the perf.data file
@@ -40,6 +41,8 @@ static const char **header_argv;
 static const char *__perf_magic1 = "PERFFILE";
 static const u64 __perf_magic2    = 0x32454c4946524550ULL;
 static const u64 __perf_magic2_sw = 0x50455246494c4532ULL;
+static const u64 __perf_magic3    = 0x33454c4946524550ULL;
+static const u64 __perf_magic3_sw = 0x50455246494c4533ULL;
 
 #define PERF_MAGIC	__perf_magic2
 
@@ -2464,7 +2467,9 @@ bool is_perf_magic(u64 magic)
 {
 	if (!memcmp(&magic, __perf_magic1, sizeof(magic))
 		|| magic == __perf_magic2
-		|| magic == __perf_magic2_sw)
+		|| magic == __perf_magic2_sw
+		|| magic == __perf_magic3
+		|| magic == __perf_magic3_sw)
 		return true;
 
 	return false;
@@ -2506,6 +2511,7 @@ do {								\
 } while (0)
 
 	CHECK(__perf_magic2, PERF_HEADER_VERSION_2);
+	CHECK(__perf_magic3, PERF_HEADER_VERSION_3);
 
 	return -1;
 }
diff --git a/tools/perf/util/header.h b/tools/perf/util/header.h
index c6ea4603..bcd3e64 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -37,6 +37,7 @@ enum {
 enum perf_header_version {
 	PERF_HEADER_VERSION_1,
 	PERF_HEADER_VERSION_2,
+	PERF_HEADER_VERSION_3,
 };
 
 struct perf_file_section {
@@ -52,6 +53,12 @@ struct perf_file_header_v2 {
 	DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
 };
 
+struct perf_file_header_v3 {
+	struct perf_file_section	data;
+	struct perf_file_section	features;
+	DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
+};
+
 struct perf_file_header {
 	u64	magic;
 	u64	size;
@@ -60,6 +67,7 @@ struct perf_file_header {
 	/* version specific data */
 	union {
 		struct perf_file_header_v2 v2;
+		struct perf_file_header_v3 v3;
 	};
 };
 
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 15/25] perf tools: Add perf data version 3 header swap
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (13 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 14/25] perf tools: Introduce perf.data version 3 format Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 16/25] perf tools: Add perf data version 3 header read Jiri Olsa
                   ` (11 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding perf data version 3 header swap same way
as it's done for v2.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 21 ++++++++++++++++++---
 1 file changed, 18 insertions(+), 3 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index db6b131..77d588f 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -2568,13 +2568,28 @@ static int swap_header_v2(struct perf_file_header *header)
 	return 0;
 }
 
-static int swap_header(struct perf_file_header *header)
+static int swap_header_v3(struct perf_file_header *header)
+{
+	struct perf_file_header_v3 *v3 = &header->v3;
+
+	mem_bswap_64(v3, offsetof(struct perf_file_header_v3,
+		     adds_features));
+
+	swap_features(v3->adds_features);
+	return 0;
+}
+
+static int swap_header(struct perf_header *ph,
+		       struct perf_file_header *header)
 {
 	/* swap the generic part */
 	mem_bswap_64(header, offsetof(struct perf_file_header, v2));
 
 	/* version specific swap */
-	return swap_header_v2(header);
+	if (ph->version <= PERF_HEADER_VERSION_2)
+		return swap_header_v2(header);
+
+	return swap_header_v3(header);
 }
 
 int perf_file_header__read(struct perf_file_header *header,
@@ -2594,7 +2609,7 @@ int perf_file_header__read(struct perf_file_header *header,
 		return -1;
 	}
 
-	return ph->needs_swap ? swap_header(header) : 0;
+	return ph->needs_swap ? swap_header(ph, header) : 0;
 }
 
 static int perf_file_section__process(struct perf_file_section *section,
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 16/25] perf tools: Add perf data version 3 header read
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (14 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 15/25] perf tools: Add perf data version 3 header swap Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 17/25] perf tools: Add perf.data version 3 header write Jiri Olsa
                   ` (10 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding perf data version 3 header read code to load
data for v3 format.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/util/header.c | 46 +++++++++++++++++++++++++++++++++++++++-------
 1 file changed, 39 insertions(+), 7 deletions(-)

diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 77d588f..0bf0164 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -1780,17 +1780,26 @@ process_event_desc(struct perf_file_section *section __maybe_unused,
 	struct perf_session *session;
 	struct perf_evlist *evlist;
 	struct perf_evsel *evsel;
+	struct perf_header *ph;
+
+	session = container_of(header, struct perf_session, header);
 
 	evlist = read_event_desc(header, fd);
 	if (!evlist)
-		return 0;
+		return -1;
 
-	session = container_of(header, struct perf_session, header);
+	ph = &session->header;
 
-	list_for_each_entry(evsel, &evlist->entries, node)
-		perf_evlist__set_event_name(session->evlist, evsel);
+	if (ph->version <= PERF_HEADER_VERSION_2) {
+		list_for_each_entry(evsel, &evlist->entries, node)
+			perf_evlist__set_event_name(session->evlist, evsel);
+
+		perf_evlist__delete(evlist);
+	} else {
+		session->evlist = session->evlist ?: evlist;
+		symbol_conf.nr_events = evlist->nr_entries;
+	}
 
-	perf_evlist__delete(evlist);
 	return 0;
 }
 
@@ -2859,15 +2868,38 @@ static int perf_session__read_header_v2(struct perf_session *session,
 	return __perf_session__read_header_v2(session, header);
 }
 
+static int perf_session__read_header_v3(struct perf_session *session,
+					struct perf_file_header *header)
+{
+	struct perf_header *ph = &session->header;
+	struct perf_file_header_v3 *v3 = &header->v3;
+
+	memcpy(&ph->adds_features, &v3->adds_features,
+	       sizeof(ph->adds_features));
+
+	ph->data_offset  = v3->data.offset;
+	ph->data_size	 = v3->data.size;
+	ph->feat_offset  = v3->features.offset;
+
+	perf_header__process_sections(ph, session->fd, &session->pevent,
+				      perf_file_section__process);
+
+	return 0;
+}
+
 static int perf_header_read_file(struct perf_session *session)
 {
 	struct perf_file_header header;
+	struct perf_header *ph = &session->header;
 
 	if (perf_file_header__read(&header, &session->header, session->fd))
 		return -1;
 
-	/* read v2 specific data */
-	return perf_session__read_header_v2(session, &header);
+	/* read version specific data */
+	if (ph->version <= PERF_HEADER_VERSION_2)
+		return perf_session__read_header_v2(session, &header);
+
+	return perf_session__read_header_v3(session, &header);
 }
 
 int perf_session__read_header(struct perf_session *session)
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 17/25] perf tools: Add perf.data version 3 header write
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (15 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 16/25] perf tools: Add perf data version 3 header read Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 18/25] perf tools: Get rid of post_processing_offset in record command Jiri Olsa
                   ` (9 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding perf data version 3 header write code and
switch perf tool storing to version 3.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Documentation/perf-data-file-v2.txt |  5 +-
 tools/perf/builtin-inject.c                    |  3 +-
 tools/perf/builtin-record.c                    |  5 +-
 tools/perf/tests/session-simple.c              |  4 +-
 tools/perf/util/header.c                       | 70 ++++++++------------------
 tools/perf/util/header.h                       |  6 ++-
 6 files changed, 36 insertions(+), 57 deletions(-)

diff --git a/tools/perf/Documentation/perf-data-file-v2.txt b/tools/perf/Documentation/perf-data-file-v2.txt
index f5c1d5b8..0d29753 100644
--- a/tools/perf/Documentation/perf-data-file-v2.txt
+++ b/tools/perf/Documentation/perf-data-file-v2.txt
@@ -8,8 +8,9 @@ perf-data-file-v2 - The perf tool file format version 2
 
 DESCRIPTION
 -----------
-Following text describes version 2 of the perf data file format,
-which is version that is currently used by perf tool.
+Following text describes version 2 of the perf data file format.
+The perf tool supports this format for reading, but for writing
+it uses version 3 format perf-data-file-v3(1).
 
 The perf data file format is composed of several sections
 describing monitored events and the data itself.
diff --git a/tools/perf/builtin-inject.c b/tools/perf/builtin-inject.c
index 9b336fd..6dd8ed1 100644
--- a/tools/perf/builtin-inject.c
+++ b/tools/perf/builtin-inject.c
@@ -376,7 +376,8 @@ static int __cmd_inject(struct perf_inject *inject)
 
 	if (!inject->pipe_output) {
 		session->header.data_size = inject->bytes_written;
-		perf_session__write_header(session, session->evlist, inject->output, true);
+		perf_session__write_header(session, session->evlist,
+					   inject->output);
 	}
 
 	perf_session__delete(session);
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 351ede3..fdbcd51 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -273,7 +273,7 @@ static void perf_record__exit(int status, void *arg)
 		if (!rec->no_buildid)
 			process_buildids(rec);
 		perf_session__write_header(rec->session, rec->evlist,
-					   rec->output, true);
+					   rec->output);
 		perf_session__delete(rec->session);
 		perf_evlist__delete(rec->evlist);
 		symbol__exit();
@@ -444,8 +444,7 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 		if (err < 0)
 			goto out_delete_session;
 	} else {
-		err = perf_session__write_header(session, evsel_list,
-						 output, false);
+		err = perf_session__prepare_header(output);
 		if (err < 0)
 			goto out_delete_session;
 	}
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index 4f58c0f..215b6dc 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -480,7 +480,7 @@ static int session_write(char *file)
 	perf_header__clear_feat(&session->header, HEADER_BRANCH_STACK);
 
 	TEST_ASSERT_VAL("failed to write header",
-		!perf_session__write_header(session, evlist, fd, false));
+		!perf_session__prepare_header(fd));
 
 #define STORE_EVENTS(str, func, cnt)				\
 do {								\
@@ -520,7 +520,7 @@ do {								\
 	session->header.data_size += size;
 
 	TEST_ASSERT_VAL("failed to write header",
-		!perf_session__write_header(session, evlist, fd, true));
+		!perf_session__write_header(session, evlist, fd));
 
 	perf_session__delete(session);
 	perf_evlist__delete(evlist);
diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 0bf0164..36206b5 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -44,7 +44,7 @@ static const u64 __perf_magic2_sw = 0x50455246494c4532ULL;
 static const u64 __perf_magic3    = 0x33454c4946524550ULL;
 static const u64 __perf_magic3_sw = 0x50455246494c4533ULL;
 
-#define PERF_MAGIC	__perf_magic2
+#define PERF_MAGIC	__perf_magic3
 
 struct perf_file_attr {
 	struct perf_event_attr	attr;
@@ -2240,6 +2240,7 @@ static int perf_header__adds_write(struct perf_header *header,
 			perf_header__clear_feat(header, feat);
 	}
 
+	header->feat_size = lseek(fd, 0, SEEK_CUR) - sec_start;
 	lseek(fd, sec_start, SEEK_SET);
 	/*
 	 * may write more than needed due to dropped feature, but
@@ -2271,72 +2272,45 @@ int perf_header__write_pipe(int fd)
 	return 0;
 }
 
+int perf_session__prepare_header(int fd)
+{
+	off_t off = lseek(fd, PERF_FILE_HEADER__DATA_OFFSET, SEEK_SET);
+	return off == PERF_FILE_HEADER__DATA_OFFSET ? 0 : -1;
+}
+
 int perf_session__write_header(struct perf_session *session,
 			       struct perf_evlist *evlist,
-			       int fd, bool at_exit)
+			       int fd)
 {
 	struct perf_file_header f_header;
 	struct perf_file_attr   f_attr;
 	struct perf_header *header = &session->header;
-	struct perf_evsel *evsel;
-	u64 attr_offset;
 	int err;
 
-	lseek(fd, sizeof(f_header), SEEK_SET);
-
-	list_for_each_entry(evsel, &evlist->entries, node) {
-		evsel->id_offset = lseek(fd, 0, SEEK_CUR);
-		err = do_write(fd, evsel->id, evsel->ids * sizeof(u64));
-		if (err < 0) {
-			pr_debug("failed to write perf header\n");
-			return err;
-		}
-	}
-
-	attr_offset = lseek(fd, 0, SEEK_CUR);
-
-	list_for_each_entry(evsel, &evlist->entries, node) {
-		f_attr = (struct perf_file_attr){
-			.attr = evsel->attr,
-			.ids  = {
-				.offset = evsel->id_offset,
-				.size   = evsel->ids * sizeof(u64),
-			}
-		};
-		err = do_write(fd, &f_attr, sizeof(f_attr));
-		if (err < 0) {
-			pr_debug("failed to write perf header attribute\n");
-			return err;
-		}
-	}
-
-	header->data_offset = lseek(fd, 0, SEEK_CUR);
-	header->feat_offset = header->data_offset + header->data_size;
+	header->feat_offset = PERF_FILE_HEADER__DATA_OFFSET +
+			      header->data_size;
 
-	if (at_exit) {
-		err = perf_header__adds_write(header, evlist, fd);
-		if (err < 0)
-			return err;
-	}
+	err = perf_header__adds_write(header, evlist, fd);
+	if (err < 0)
+		return err;
 
 	f_header = (struct perf_file_header){
 		.magic	   = PERF_MAGIC,
 		.size	   = sizeof(f_header),
 		.attr_size = sizeof(f_attr),
-		.v2        = {
-			.attrs = {
-				.offset = attr_offset,
-				.size   = evlist->nr_entries * sizeof(f_attr),
-			},
+		.v3        = {
 			.data = {
-				.offset = header->data_offset,
+				.offset = PERF_FILE_HEADER__DATA_OFFSET,
 				.size	= header->data_size,
 			},
-		/* event_types is ignored, store zeros */
+			.features = {
+				.offset = header->feat_offset,
+				.size   = header->feat_size,
+			},
 		},
 	};
 
-	memcpy(&f_header.v2.adds_features, &header->adds_features,
+	memcpy(&f_header.v3.adds_features, &header->adds_features,
 	       sizeof(header->adds_features));
 
 	lseek(fd, 0, SEEK_SET);
@@ -2345,7 +2319,6 @@ int perf_session__write_header(struct perf_session *session,
 		pr_debug("failed to write perf header\n");
 		return err;
 	}
-	lseek(fd, header->data_offset + header->data_size, SEEK_SET);
 
 	return 0;
 }
@@ -2880,6 +2853,7 @@ static int perf_session__read_header_v3(struct perf_session *session,
 	ph->data_offset  = v3->data.offset;
 	ph->data_size	 = v3->data.size;
 	ph->feat_offset  = v3->features.offset;
+	ph->feat_size    = v3->features.size;
 
 	perf_header__process_sections(ph, session->fd, &session->pevent,
 				      perf_file_section__process);
diff --git a/tools/perf/util/header.h b/tools/perf/util/header.h
index bcd3e64..4982e04 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -53,6 +53,8 @@ struct perf_file_header_v2 {
 	DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
 };
 
+#define PERF_FILE_HEADER__DATA_OFFSET (sizeof(struct perf_file_header))
+
 struct perf_file_header_v3 {
 	struct perf_file_section	data;
 	struct perf_file_section	features;
@@ -111,6 +113,7 @@ struct perf_header {
 	u64				data_offset;
 	u64				data_size;
 	u64				feat_offset;
+	u64				feat_size;
 	DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
 	struct perf_session_env 	env;
 };
@@ -119,9 +122,10 @@ struct perf_evlist;
 struct perf_session;
 
 int perf_session__read_header(struct perf_session *session);
+int perf_session__prepare_header(int fd);
 int perf_session__write_header(struct perf_session *session,
 			       struct perf_evlist *evlist,
-			       int fd, bool at_exit);
+			       int fd);
 int perf_header__write_pipe(int fd);
 
 void perf_header__set_feat(struct perf_header *header, int feat);
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 18/25] perf tools: Get rid of post_processing_offset in record command
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (16 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 17/25] perf tools: Add perf.data version 3 header write Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 19/25] perf tools: Move synthesizing into single function Jiri Olsa
                   ` (8 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

No need to use post_processing_offset variable now when
we know where the data starts.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/builtin-record.c | 13 ++++++-------
 1 file changed, 6 insertions(+), 7 deletions(-)

diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index fdbcd51..4011698 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -75,7 +75,6 @@ struct perf_record {
 	bool			no_buildid;
 	bool			no_buildid_cache;
 	long			samples;
-	off_t			post_processing_offset;
 };
 
 static void advance_output(struct perf_record *rec, size_t size)
@@ -249,15 +248,17 @@ out:
 
 static int process_buildids(struct perf_record *rec)
 {
-	u64 size = lseek(rec->output, 0, SEEK_CUR);
+	struct perf_session *session = rec->session;
+	u64 data_offset              = PERF_FILE_HEADER__DATA_OFFSET;
+	u64 size                     = session->header.data_size;
 
 	if (size == 0)
 		return 0;
 
 	rec->session->fd = rec->output;
-	return __perf_session__process_events(rec->session, rec->post_processing_offset,
-					      size - rec->post_processing_offset,
-					      size, &build_id__mark_dso_hit_ops);
+	return __perf_session__process_events(session, data_offset,
+					      size - data_offset, size,
+					      &build_id__mark_dso_hit_ops);
 }
 
 static void perf_record__exit(int status, void *arg)
@@ -457,8 +458,6 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 		goto out_delete_session;
 	}
 
-	rec->post_processing_offset = lseek(output, 0, SEEK_CUR);
-
 	machine = &session->machines.host;
 
 	if (opts->pipe_output) {
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 19/25] perf tools: Move synthesizing into single function
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (17 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 18/25] perf tools: Get rid of post_processing_offset in record command Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 20/25] perf tools: Add perf_data_file__open interface to data object Jiri Olsa
                   ` (7 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Moving synthesizing into single function, so it
could be reused.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/builtin-annotate.c      |   9 +-
 tools/perf/builtin-buildid-cache.c |   8 +-
 tools/perf/builtin-buildid-list.c  |   9 +-
 tools/perf/builtin-diff.c          |  19 ++--
 tools/perf/builtin-evlist.c        |   7 +-
 tools/perf/builtin-inject.c        |   7 +-
 tools/perf/builtin-kmem.c          |   7 +-
 tools/perf/builtin-kvm.c           |  13 ++-
 tools/perf/builtin-lock.c          |   8 +-
 tools/perf/builtin-mem.c           |   9 +-
 tools/perf/builtin-record.c        | 204 +++++++++++++++++++++----------------
 tools/perf/builtin-report.c        |  10 +-
 tools/perf/builtin-sched.c         |   6 +-
 tools/perf/builtin-script.c        |  15 ++-
 tools/perf/builtin-timechart.c     |  10 +-
 tools/perf/builtin-top.c           |   6 +-
 tools/perf/builtin-trace.c         |   8 +-
 tools/perf/perf.h                  |   1 -
 tools/perf/tests/session-simple.c  |  30 ++++--
 tools/perf/util/data.h             |  29 ++++++
 tools/perf/util/session.c          |  12 +--
 tools/perf/util/session.h          |   6 +-
 22 files changed, 290 insertions(+), 143 deletions(-)
 create mode 100644 tools/perf/util/data.h

diff --git a/tools/perf/builtin-annotate.c b/tools/perf/builtin-annotate.c
index f988d38..64eae2c 100644
--- a/tools/perf/builtin-annotate.c
+++ b/tools/perf/builtin-annotate.c
@@ -28,6 +28,7 @@
 #include "util/hist.h"
 #include "util/session.h"
 #include "util/tool.h"
+#include "util/data.h"
 #include "arch/common.h"
 
 #include <linux/bitmap.h>
@@ -188,9 +189,13 @@ static int __cmd_annotate(struct perf_annotate *ann)
 	struct perf_session *session;
 	struct perf_evsel *pos;
 	u64 total_nr_samples;
+	struct perf_data_file file = {
+		.path  = input_name,
+		.mode  = PERF_DATA_MODE_READ,
+		.force = ann->force,
+	};
 
-	session = perf_session__new(input_name, O_RDONLY,
-				    ann->force, false, &ann->tool);
+	session = perf_session__new(&file, false, &ann->tool);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-buildid-cache.c b/tools/perf/builtin-buildid-cache.c
index c96c8fa..581c62a 100644
--- a/tools/perf/builtin-buildid-cache.c
+++ b/tools/perf/builtin-buildid-cache.c
@@ -82,8 +82,12 @@ static bool dso__missing_buildid_cache(struct dso *dso, int parm __maybe_unused)
 
 static int build_id_cache__fprintf_missing(const char *filename, bool force, FILE *fp)
 {
-	struct perf_session *session = perf_session__new(filename, O_RDONLY,
-							 force, false, NULL);
+	struct perf_data_file file = {
+		.path  = filename,
+		.mode  = PERF_DATA_MODE_READ,
+		.force = force,
+	};
+	struct perf_session *session = perf_session__new(&file, false, NULL);
 	if (session == NULL)
 		return -1;
 
diff --git a/tools/perf/builtin-buildid-list.c b/tools/perf/builtin-buildid-list.c
index e74366a..0164c1c 100644
--- a/tools/perf/builtin-buildid-list.c
+++ b/tools/perf/builtin-buildid-list.c
@@ -15,6 +15,7 @@
 #include "util/parse-options.h"
 #include "util/session.h"
 #include "util/symbol.h"
+#include "util/data.h"
 
 static int sysfs__fprintf_build_id(FILE *fp)
 {
@@ -52,6 +53,11 @@ static bool dso__skip_buildid(struct dso *dso, int with_hits)
 static int perf_session__list_build_ids(bool force, bool with_hits)
 {
 	struct perf_session *session;
+	struct perf_data_file file = {
+		.path  = input_name,
+		.mode  = PERF_DATA_MODE_READ,
+		.force = force,
+	};
 
 	symbol__elf_init();
 	/*
@@ -60,8 +66,7 @@ static int perf_session__list_build_ids(bool force, bool with_hits)
 	if (filename__fprintf_build_id(input_name, stdout))
 		goto out;
 
-	session = perf_session__new(input_name, O_RDONLY, force, false,
-				    &build_id__mark_dso_hit_ops);
+	session = perf_session__new(&file, false, &build_id__mark_dso_hit_ops);
 	if (session == NULL)
 		return -1;
 	/*
diff --git a/tools/perf/builtin-diff.c b/tools/perf/builtin-diff.c
index f28799e..3fb2d46 100644
--- a/tools/perf/builtin-diff.c
+++ b/tools/perf/builtin-diff.c
@@ -16,6 +16,7 @@
 #include "util/sort.h"
 #include "util/symbol.h"
 #include "util/util.h"
+#include "util/data.h"
 
 #include <stdlib.h>
 #include <math.h>
@@ -42,7 +43,7 @@ struct diff_hpp_fmt {
 
 struct data__file {
 	struct perf_session	*session;
-	const char		*file;
+	struct perf_data_file	file;
 	int			 idx;
 	struct hists		*hists;
 	struct diff_hpp_fmt	 fmt[PERF_HPP_DIFF__MAX_INDEX];
@@ -599,7 +600,7 @@ static void data__fprintf(void)
 
 	data__for_each_file(i, d)
 		fprintf(stdout, "#  [%d] %s %s\n",
-			d->idx, d->file,
+			d->idx, d->file.path,
 			!d->idx ? "(Baseline)" : "");
 
 	fprintf(stdout, "#\n");
@@ -661,17 +662,16 @@ static int __cmd_diff(void)
 	int ret = -EINVAL, i;
 
 	data__for_each_file(i, d) {
-		d->session = perf_session__new(d->file, O_RDONLY, force,
-					       false, &tool);
+		d->session = perf_session__new(&d->file, false, &tool);
 		if (!d->session) {
-			pr_err("Failed to open %s\n", d->file);
+			pr_err("Failed to open %s\n", d->file.path);
 			ret = -ENOMEM;
 			goto out_delete;
 		}
 
 		ret = perf_session__process_events(d->session, &tool);
 		if (ret) {
-			pr_err("Failed to process %s\n", d->file);
+			pr_err("Failed to process %s\n", d->file.path);
 			goto out_delete;
 		}
 
@@ -1014,7 +1014,12 @@ static int data_init(int argc, const char **argv)
 		return -ENOMEM;
 
 	data__for_each_file(i, d) {
-		d->file = use_default ? defaults[i] : argv[i];
+		struct perf_data_file *file = &d->file;
+
+		file->path  = use_default ? defaults[i] : argv[i];
+		file->mode  = PERF_DATA_MODE_READ,
+		file->force = force,
+
 		d->idx  = i;
 	}
 
diff --git a/tools/perf/builtin-evlist.c b/tools/perf/builtin-evlist.c
index 05bd9df..20b0f12 100644
--- a/tools/perf/builtin-evlist.c
+++ b/tools/perf/builtin-evlist.c
@@ -14,13 +14,18 @@
 #include "util/parse-events.h"
 #include "util/parse-options.h"
 #include "util/session.h"
+#include "util/data.h"
 
 static int __cmd_evlist(const char *file_name, struct perf_attr_details *details)
 {
 	struct perf_session *session;
 	struct perf_evsel *pos;
+	struct perf_data_file file = {
+		.path = file_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 
-	session = perf_session__new(file_name, O_RDONLY, 0, false, NULL);
+	session = perf_session__new(&file, 0, NULL);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-inject.c b/tools/perf/builtin-inject.c
index 6dd8ed1..1ec5246 100644
--- a/tools/perf/builtin-inject.c
+++ b/tools/perf/builtin-inject.c
@@ -15,6 +15,7 @@
 #include "util/tool.h"
 #include "util/debug.h"
 #include "util/build-id.h"
+#include "util/data.h"
 
 #include "util/parse-options.h"
 
@@ -334,6 +335,10 @@ static int __cmd_inject(struct perf_inject *inject)
 {
 	struct perf_session *session;
 	int ret = -EINVAL;
+	struct perf_data_file file = {
+		.path = inject->input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 
 	signal(SIGINT, sig_handler);
 
@@ -343,7 +348,7 @@ static int __cmd_inject(struct perf_inject *inject)
 		inject->tool.tracing_data = perf_event__repipe_tracing_data;
 	}
 
-	session = perf_session__new(inject->input_name, O_RDONLY, false, true, &inject->tool);
+	session = perf_session__new(&file, true, &inject->tool);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-kmem.c b/tools/perf/builtin-kmem.c
index c2dff9c..a4bff1c 100644
--- a/tools/perf/builtin-kmem.c
+++ b/tools/perf/builtin-kmem.c
@@ -13,6 +13,7 @@
 
 #include "util/parse-options.h"
 #include "util/trace-event.h"
+#include "util/data.h"
 
 #include "util/debug.h"
 
@@ -486,8 +487,12 @@ static int __cmd_kmem(void)
 		{ "kmem:kfree",			perf_evsel__process_free_event, },
     		{ "kmem:kmem_cache_free",	perf_evsel__process_free_event, },
 	};
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 
-	session = perf_session__new(input_name, O_RDONLY, 0, false, &perf_kmem);
+	session = perf_session__new(&file, false, &perf_kmem);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-kvm.c b/tools/perf/builtin-kvm.c
index f89f7d6..187848c 100644
--- a/tools/perf/builtin-kvm.c
+++ b/tools/perf/builtin-kvm.c
@@ -17,6 +17,7 @@
 #include "util/tool.h"
 #include "util/stat.h"
 #include "util/top.h"
+#include "util/data.h"
 
 #include <sys/prctl.h>
 #include <sys/timerfd.h>
@@ -1215,10 +1216,13 @@ static int read_events(struct perf_kvm_stat *kvm)
 		.comm			= perf_event__process_comm,
 		.ordered_samples	= true,
 	};
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 
 	kvm->tool = eops;
-	kvm->session = perf_session__new(kvm->file_name, O_RDONLY, 0, false,
-					 &kvm->tool);
+	kvm->session = perf_session__new(&file, false, &kvm->tool);
 	if (!kvm->session) {
 		pr_err("Initializing perf session failed\n");
 		return -EINVAL;
@@ -1450,6 +1454,9 @@ static int kvm_events_live(struct perf_kvm_stat *kvm,
 		"perf kvm stat live [<options>]",
 		NULL
 	};
+	struct perf_data_file file = {
+		.mode = PERF_DATA_MODE_WRITE,
+	};
 
 
 	/* event handling */
@@ -1514,7 +1521,7 @@ static int kvm_events_live(struct perf_kvm_stat *kvm,
 	/*
 	 * perf session
 	 */
-	kvm->session = perf_session__new(NULL, O_WRONLY, false, false, &kvm->tool);
+	kvm->session = perf_session__new(&file, false, &kvm->tool);
 	if (kvm->session == NULL) {
 		err = -ENOMEM;
 		goto out;
diff --git a/tools/perf/builtin-lock.c b/tools/perf/builtin-lock.c
index ee33ba2..c3b685c 100644
--- a/tools/perf/builtin-lock.c
+++ b/tools/perf/builtin-lock.c
@@ -15,6 +15,7 @@
 #include "util/debug.h"
 #include "util/session.h"
 #include "util/tool.h"
+#include "util/data.h"
 
 #include <sys/types.h>
 #include <sys/prctl.h>
@@ -836,7 +837,12 @@ static int read_events(void)
 		.comm		 = perf_event__process_comm,
 		.ordered_samples = true,
 	};
-	session = perf_session__new(input_name, O_RDONLY, 0, false, &eops);
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
+
+	session = perf_session__new(&file, false, &eops);
 	if (!session) {
 		pr_err("Initializing perf session failed\n");
 		return -1;
diff --git a/tools/perf/builtin-mem.c b/tools/perf/builtin-mem.c
index 791b432..1b703da 100644
--- a/tools/perf/builtin-mem.c
+++ b/tools/perf/builtin-mem.c
@@ -5,6 +5,7 @@
 #include "util/trace-event.h"
 #include "util/tool.h"
 #include "util/session.h"
+#include "util/data.h"
 
 #define MEM_OPERATION_LOAD	"load"
 #define MEM_OPERATION_STORE	"store"
@@ -119,10 +120,14 @@ static int process_sample_event(struct perf_tool *tool,
 
 static int report_raw_events(struct perf_mem *mem)
 {
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 	int err = -EINVAL;
 	int ret;
-	struct perf_session *session = perf_session__new(input_name, O_RDONLY,
-							 0, false, &mem->tool);
+	struct perf_session *session = perf_session__new(&file, false,
+							 &mem->tool);
 
 	if (session == NULL)
 		return -ENOMEM;
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 4011698..1887b20 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -24,6 +24,7 @@
 #include "util/symbol.h"
 #include "util/cpumap.h"
 #include "util/thread_map.h"
+#include "util/data.h"
 
 #include <unistd.h>
 #include <sched.h>
@@ -65,11 +66,11 @@ struct perf_record {
 	struct perf_tool	tool;
 	struct perf_record_opts	opts;
 	u64			bytes_written;
-	const char		*output_name;
+	struct perf_data_file	file_base;
+	struct perf_data_file	*file;
 	struct perf_evlist	*evlist;
 	struct perf_session	*session;
 	const char		*progname;
-	int			output;
 	unsigned int		page_size;
 	int			realtime_prio;
 	bool			no_buildid;
@@ -84,8 +85,10 @@ static void advance_output(struct perf_record *rec, size_t size)
 
 static int write_output(struct perf_record *rec, void *buf, size_t size)
 {
+	struct perf_data_file *file = rec->file;
+
 	while (size) {
-		int ret = write(rec->output, buf, size);
+		int ret = write(file->fd, buf, size);
 
 		if (ret < 0) {
 			pr_err("failed to write\n");
@@ -248,6 +251,7 @@ out:
 
 static int process_buildids(struct perf_record *rec)
 {
+	struct perf_data_file *file  = rec->file;
 	struct perf_session *session = rec->session;
 	u64 data_offset              = PERF_FILE_HEADER__DATA_OFFSET;
 	u64 size                     = session->header.data_size;
@@ -255,7 +259,7 @@ static int process_buildids(struct perf_record *rec)
 	if (size == 0)
 		return 0;
 
-	rec->session->fd = rec->output;
+	rec->session->fd = file->fd;
 	return __perf_session__process_events(session, data_offset,
 					      size - data_offset, size,
 					      &build_id__mark_dso_hit_ops);
@@ -264,17 +268,18 @@ static int process_buildids(struct perf_record *rec)
 static void perf_record__exit(int status, void *arg)
 {
 	struct perf_record *rec = arg;
+	struct perf_data_file *file = rec->file;
 
 	if (status != 0)
 		return;
 
-	if (!rec->opts.pipe_output) {
+	if (!file->is_pipe) {
 		rec->session->header.data_size += rec->bytes_written;
 
 		if (!rec->no_buildid)
 			process_buildids(rec);
 		perf_session__write_header(rec->session, rec->evlist,
-					   rec->output);
+					   file->fd);
 		perf_session__delete(rec->session);
 		perf_evlist__delete(rec->evlist);
 		symbol__exit();
@@ -313,6 +318,92 @@ static void perf_event__synthesize_guest_os(struct machine *machine, void *data)
 		       " relocation symbol.\n", machine->pid);
 }
 
+static int synthesize_record_pipe(struct perf_record *rec)
+{
+	struct perf_session  *session = rec->session;
+	struct perf_tool        *tool = &rec->tool;
+	struct perf_evlist    *evlist = rec->evlist;
+	struct perf_data_file   *file = rec->file;
+	int err;
+
+	err = perf_event__synthesize_attrs(tool, session,
+					   process_synthesized_event);
+	if (err < 0) {
+		pr_err("Couldn't synthesize attrs.\n");
+		return err;
+	}
+
+	if (have_tracepoints(&evlist->entries)) {
+		err = perf_event__synthesize_tracing_data(tool, file->fd,
+						evlist,
+						process_synthesized_event);
+		if (err <= 0) {
+			pr_err("Couldn't record tracing data.\n");
+			return err;
+		}
+		advance_output(rec, err);
+	}
+
+	return 0;
+}
+
+static int synthesize_record_file(struct perf_record *rec)
+{
+	struct perf_session  *session = rec->session;
+	struct perf_tool        *tool = &rec->tool;
+	struct perf_record_opts *opts = &rec->opts;
+	struct machine       *machine = &session->machines.host;
+	struct perf_evlist    *evlist = rec->evlist;
+	int err;
+
+	err = perf_event__synthesize_kernel_mmap(tool,
+					process_synthesized_event,
+					 machine, "_text");
+	if (err < 0)
+		err = perf_event__synthesize_kernel_mmap(tool,
+						process_synthesized_event,
+						 machine, "_stext");
+	if (err < 0)
+		pr_err("Couldn't record kernel reference relocation symbol\n"
+		       "Symbol resolution may be skewed if relocation was used (e.g. kexec).\n"
+		       "Check /proc/kallsyms permission or run as root.\n");
+
+	err = perf_event__synthesize_modules(tool, process_synthesized_event,
+					     machine);
+	if (err < 0)
+		pr_err("Couldn't record kernel module information.\n"
+		       "Symbol resolution may be skewed if relocation was used (e.g. kexec).\n"
+		       "Check /proc/modules permission or run as root.\n");
+
+	if (perf_guest)
+		machines__process_guests(&session->machines,
+					 perf_event__synthesize_guest_os, tool);
+
+	if (perf_target__has_task(&opts->target))
+		err = perf_event__synthesize_thread_map(tool, evlist->threads,
+						  process_synthesized_event,
+						  machine);
+	else if (perf_target__has_cpu(&opts->target))
+		err = perf_event__synthesize_threads(tool,
+						process_synthesized_event,
+						machine);
+	else /* command specified */
+		err = 0;
+
+	return err;
+}
+
+static int synthesize_record(struct perf_record *rec)
+{
+	struct perf_data_file *file = rec->file;
+	int err = 0;
+
+	if (file->is_pipe)
+		err = synthesize_record_pipe(rec);
+
+	return err ? err : synthesize_record_file(rec);
+}
+
 static struct perf_event_header finished_round_event = {
 	.size = sizeof(struct perf_event_header),
 	.type = PERF_RECORD_FINISHED_ROUND,
@@ -344,14 +435,13 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 {
 	struct stat st;
 	int flags;
-	int err, output, feat;
+	int err, feat;
 	unsigned long waking = 0;
 	const bool forks = argc > 0;
-	struct machine *machine;
-	struct perf_tool *tool = &rec->tool;
 	struct perf_record_opts *opts = &rec->opts;
 	struct perf_evlist *evsel_list = rec->evlist;
-	const char *output_name = rec->output_name;
+	struct perf_data_file *file = rec->file;
+	const char *output_name = file->path;
 	struct perf_session *session;
 	bool disabled = false;
 
@@ -367,13 +457,13 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 
 	if (!output_name) {
 		if (!fstat(STDOUT_FILENO, &st) && S_ISFIFO(st.st_mode))
-			opts->pipe_output = true;
+			file->is_pipe = true;
 		else
-			rec->output_name = output_name = "perf.data";
+			file->path = output_name = "perf.data";
 	}
 	if (output_name) {
 		if (!strcmp(output_name, "-"))
-			opts->pipe_output = true;
+			file->is_pipe = true;
 		else if (!stat(output_name, &st) && st.st_size) {
 			char oldname[PATH_MAX];
 			snprintf(oldname, sizeof(oldname), "%s.old",
@@ -385,19 +475,16 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 
 	flags = O_CREAT|O_RDWR|O_TRUNC;
 
-	if (opts->pipe_output)
-		output = STDOUT_FILENO;
+	if (file->is_pipe)
+		file->fd = STDOUT_FILENO;
 	else
-		output = open(output_name, flags, S_IRUSR | S_IWUSR);
-	if (output < 0) {
+		file->fd = open(output_name, flags, S_IRUSR | S_IWUSR);
+	if (file->fd < 0) {
 		perror("failed to create output file");
 		return -1;
 	}
 
-	rec->output = output;
-
-	session = perf_session__new(output_name, O_WRONLY,
-				    true, false, NULL);
+	session = perf_session__new(file, false, NULL);
 	if (session == NULL) {
 		pr_err("Not enough memory for reading perf file header\n");
 		return -1;
@@ -419,7 +506,7 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 
 	if (forks) {
 		err = perf_evlist__prepare_workload(evsel_list, &opts->target,
-						    argv, opts->pipe_output,
+						    argv, file->is_pipe,
 						    true);
 		if (err < 0) {
 			pr_err("Couldn't run the workload!\n");
@@ -440,12 +527,12 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 	 */
 	on_exit(perf_record__exit, rec);
 
-	if (opts->pipe_output) {
-		err = perf_header__write_pipe(output);
+	if (file->is_pipe) {
+		err = perf_header__write_pipe(file->fd);
 		if (err < 0)
 			goto out_delete_session;
 	} else {
-		err = perf_session__prepare_header(output);
+		err = perf_session__prepare_header(file->fd);
 		if (err < 0)
 			goto out_delete_session;
 	}
@@ -458,68 +545,8 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 		goto out_delete_session;
 	}
 
-	machine = &session->machines.host;
-
-	if (opts->pipe_output) {
-		err = perf_event__synthesize_attrs(tool, session,
-						   process_synthesized_event);
-		if (err < 0) {
-			pr_err("Couldn't synthesize attrs.\n");
-			goto out_delete_session;
-		}
-
-		if (have_tracepoints(&evsel_list->entries)) {
-			/*
-			 * FIXME err <= 0 here actually means that
-			 * there were no tracepoints so its not really
-			 * an error, just that we don't need to
-			 * synthesize anything.  We really have to
-			 * return this more properly and also
-			 * propagate errors that now are calling die()
-			 */
-			err = perf_event__synthesize_tracing_data(tool, output, evsel_list,
-								  process_synthesized_event);
-			if (err <= 0) {
-				pr_err("Couldn't record tracing data.\n");
-				goto out_delete_session;
-			}
-			advance_output(rec, err);
-		}
-	}
-
-	err = perf_event__synthesize_kernel_mmap(tool, process_synthesized_event,
-						 machine, "_text");
-	if (err < 0)
-		err = perf_event__synthesize_kernel_mmap(tool, process_synthesized_event,
-							 machine, "_stext");
-	if (err < 0)
-		pr_err("Couldn't record kernel reference relocation symbol\n"
-		       "Symbol resolution may be skewed if relocation was used (e.g. kexec).\n"
-		       "Check /proc/kallsyms permission or run as root.\n");
-
-	err = perf_event__synthesize_modules(tool, process_synthesized_event,
-					     machine);
-	if (err < 0)
-		pr_err("Couldn't record kernel module information.\n"
-		       "Symbol resolution may be skewed if relocation was used (e.g. kexec).\n"
-		       "Check /proc/modules permission or run as root.\n");
-
-	if (perf_guest) {
-		machines__process_guests(&session->machines,
-					 perf_event__synthesize_guest_os, tool);
-	}
-
-	if (perf_target__has_task(&opts->target))
-		err = perf_event__synthesize_thread_map(tool, evsel_list->threads,
-						  process_synthesized_event,
-						  machine);
-	else if (perf_target__has_cpu(&opts->target))
-		err = perf_event__synthesize_threads(tool, process_synthesized_event,
-					       machine);
-	else /* command specified */
-		err = 0;
-
-	if (err != 0)
+	err = synthesize_record(rec);
+	if (err)
 		goto out_delete_session;
 
 	if (rec->realtime_prio) {
@@ -805,6 +832,7 @@ static struct perf_record record = {
 			.uses_mmap   = true,
 		},
 	},
+	.file = &record.file_base,
 };
 
 #define CALLCHAIN_HELP "do call-graph (stack chain/backtrace) recording: "
@@ -843,7 +871,7 @@ const struct option record_options[] = {
 	OPT_STRING('C', "cpu", &record.opts.target.cpu_list, "cpu",
 		    "list of cpus to monitor"),
 	OPT_U64('c', "count", &record.opts.user_interval, "event period to sample"),
-	OPT_STRING('o', "output", &record.output_name, "file",
+	OPT_STRING('o', "output", &record.file_base.path, "file",
 		    "output file name"),
 	OPT_BOOLEAN('i', "no-inherit", &record.opts.no_inherit,
 		    "child tasks do not inherit counters"),
diff --git a/tools/perf/builtin-report.c b/tools/perf/builtin-report.c
index 9725aa3..815866d 100644
--- a/tools/perf/builtin-report.c
+++ b/tools/perf/builtin-report.c
@@ -33,6 +33,7 @@
 #include "util/thread.h"
 #include "util/sort.h"
 #include "util/hist.h"
+#include "util/data.h"
 #include "arch/common.h"
 
 #include <linux/bitmap.h>
@@ -843,6 +844,9 @@ int cmd_report(int argc, const char **argv, const char *prefix __maybe_unused)
 		     "Don't show entries under that percent", parse_percent_limit),
 	OPT_END()
 	};
+	struct perf_data_file file = {
+		.mode  = PERF_DATA_MODE_READ,
+	};
 
 	perf_config(perf_report_config, &report);
 
@@ -872,9 +876,11 @@ int cmd_report(int argc, const char **argv, const char *prefix __maybe_unused)
 		perf_hpp__init();
 	}
 
+	file.path  = input_name;
+	file.force = report.force;
+
 repeat:
-	session = perf_session__new(input_name, O_RDONLY,
-				    report.force, false, &report.tool);
+	session = perf_session__new(&file, false, &report.tool);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c
index d8c51b2..5a46b10 100644
--- a/tools/perf/builtin-sched.c
+++ b/tools/perf/builtin-sched.c
@@ -1446,8 +1446,12 @@ static int perf_sched__read_events(struct perf_sched *sched,
 		{ "sched:sched_migrate_task", process_sched_migrate_task_event, },
 	};
 	struct perf_session *session;
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 
-	session = perf_session__new(input_name, O_RDONLY, 0, false, &sched->tool);
+	session = perf_session__new(&file, false, &sched->tool);
 	if (session == NULL) {
 		pr_debug("No Memory for session\n");
 		return -1;
diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c
index 93a34ce..32103c2 100644
--- a/tools/perf/builtin-script.c
+++ b/tools/perf/builtin-script.c
@@ -15,6 +15,7 @@
 #include "util/evlist.h"
 #include "util/evsel.h"
 #include "util/sort.h"
+#include "util/data.h"
 #include <linux/bitmap.h>
 
 static char const		*script_name;
@@ -1114,10 +1115,14 @@ int find_scripts(char **scripts_array, char **scripts_path_array)
 	char scripts_path[MAXPATHLEN], lang_path[MAXPATHLEN];
 	DIR *scripts_dir, *lang_dir;
 	struct perf_session *session;
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
 	char *temp;
 	int i = 0;
 
-	session = perf_session__new(input_name, O_RDONLY, 0, false, NULL);
+	session = perf_session__new(&file, false, NULL);
 	if (!session)
 		return -1;
 
@@ -1318,12 +1323,17 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused)
 		"perf script [<options>] <top-script> [script-args]",
 		NULL
 	};
+	struct perf_data_file file = {
+		.mode = PERF_DATA_MODE_READ,
+	};
 
 	setup_scripting();
 
 	argc = parse_options(argc, argv, options, script_usage,
 			     PARSE_OPT_STOP_AT_NON_OPTION);
 
+	file.path = input_name;
+
 	if (argc > 1 && !strncmp(argv[0], "rec", strlen("rec"))) {
 		rec_script_path = get_script_path(argv[1], RECORD_SUFFIX);
 		if (!rec_script_path)
@@ -1487,8 +1497,7 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused)
 	if (!script_name)
 		setup_pager();
 
-	session = perf_session__new(input_name, O_RDONLY, 0, false,
-				    &perf_script);
+	session = perf_session__new(&file, false, &perf_script);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-timechart.c b/tools/perf/builtin-timechart.c
index c2e0231..e11c61d 100644
--- a/tools/perf/builtin-timechart.c
+++ b/tools/perf/builtin-timechart.c
@@ -36,6 +36,7 @@
 #include "util/session.h"
 #include "util/svghelper.h"
 #include "util/tool.h"
+#include "util/data.h"
 
 #define SUPPORT_OLD_POWER_EVENTS 1
 #define PWR_EVENT_EXIT -1
@@ -990,8 +991,13 @@ static int __cmd_timechart(const char *output_name)
 		{ "power:power_frequency",	process_sample_power_frequency },
 #endif
 	};
-	struct perf_session *session = perf_session__new(input_name, O_RDONLY,
-							 0, false, &perf_timechart);
+	struct perf_data_file file = {
+		.path = input_name,
+		.mode = PERF_DATA_MODE_READ,
+	};
+
+	struct perf_session *session = perf_session__new(&file, false,
+							 &perf_timechart);
 	int ret = -EINVAL;
 
 	if (session == NULL)
diff --git a/tools/perf/builtin-top.c b/tools/perf/builtin-top.c
index 0a84334..46489cb 100644
--- a/tools/perf/builtin-top.c
+++ b/tools/perf/builtin-top.c
@@ -930,11 +930,15 @@ static int __cmd_top(struct perf_top *top)
 	struct perf_record_opts *opts = &top->record_opts;
 	pthread_t thread;
 	int ret;
+	struct perf_data_file file = {
+		.mode = PERF_DATA_MODE_WRITE,
+	};
+
 	/*
 	 * FIXME: perf_session__new should allow passing a O_MMAP, so that all this
 	 * mmap reading, etc is encapsulated in it. Use O_WRONLY for now.
 	 */
-	top->session = perf_session__new(NULL, O_WRONLY, false, false, NULL);
+	top->session = perf_session__new(&file, false, NULL);
 	if (top->session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/builtin-trace.c b/tools/perf/builtin-trace.c
index 9967a56..d80b628 100644
--- a/tools/perf/builtin-trace.c
+++ b/tools/perf/builtin-trace.c
@@ -873,7 +873,10 @@ static int trace__replay(struct trace *trace)
 		{ "raw_syscalls:sys_enter",  trace__sys_enter, },
 		{ "raw_syscalls:sys_exit",   trace__sys_exit, },
 	};
-
+	struct perf_data_file file = {
+		.path  = input_name,
+		.mode  = PERF_DATA_MODE_READ,
+	};
 	struct perf_session *session;
 	int err = -1;
 
@@ -895,8 +898,7 @@ static int trace__replay(struct trace *trace)
 	if (symbol__init() < 0)
 		return -1;
 
-	session = perf_session__new(input_name, O_RDONLY, 0, false,
-				    &trace->tool);
+	session = perf_session__new(&file, false, &trace->tool);
 	if (session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/perf.h b/tools/perf/perf.h
index cf20187..0914630 100644
--- a/tools/perf/perf.h
+++ b/tools/perf/perf.h
@@ -218,7 +218,6 @@ struct perf_record_opts {
 	bool	     no_delay;
 	bool	     no_inherit;
 	bool	     no_samples;
-	bool	     pipe_output;
 	bool	     raw_samples;
 	bool	     sample_address;
 	bool	     sample_weight;
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index 215b6dc..e2b1037 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -11,6 +11,7 @@
 #include "header.h"
 #include "util.h"
 #include "evlist.h"
+#include "data.h"
 
 #define EVENTS_MMAP 5
 #define EVENTS_LOST 6
@@ -449,15 +450,19 @@ static int store_event(int fd, union perf_event *event, size_t *size)
 	return write(fd, event, event->header.size) > 0 ? 0 : -1;
 }
 
-static int session_write(char *file)
+static int session_write(char *path)
 {
+	struct perf_data_file file = {
+		.mode = PERF_DATA_MODE_WRITE,
+		.path = path,
+	};
 	struct perf_session *session;
 	struct perf_evlist *evlist;
 	size_t size = 0;
-	int feat, fd;
+	int feat;
 
-	fd = open(file, O_RDWR);
-	TEST_ASSERT_VAL("failed to open data file", fd >= 0);
+	file.fd = open(file.path, O_RDWR);
+	TEST_ASSERT_VAL("failed to open data file", file.fd >= 0);
 
 	evlist = perf_evlist__new_default();
 	TEST_ASSERT_VAL("failed to get evlist", evlist);
@@ -466,11 +471,10 @@ static int session_write(char *file)
 
 	pr_debug("session writing start\n");
 
-	session = perf_session__new(file, O_WRONLY, true, false, NULL);
+	session = perf_session__new(&file, false, NULL);
 	TEST_ASSERT_VAL("failed to create session", session);
 
 	session->evlist = evlist;
-	session->fd     = fd;
 
 	for (feat = HEADER_FIRST_FEATURE; feat < HEADER_LAST_FEATURE; feat++)
 		perf_header__set_feat(&session->header, feat);
@@ -480,14 +484,14 @@ static int session_write(char *file)
 	perf_header__clear_feat(&session->header, HEADER_BRANCH_STACK);
 
 	TEST_ASSERT_VAL("failed to write header",
-		!perf_session__prepare_header(fd));
+		!perf_session__prepare_header(file.fd));
 
 #define STORE_EVENTS(str, func, cnt)				\
 do {								\
 	int i;							\
 	for (i = 0; i < cnt; i++) {				\
 		TEST_ASSERT_VAL(str,				\
-			!store_event(fd, func(), &size));	\
+			!store_event(file.fd, func(), &size));	\
 	}							\
 } while (0)
 
@@ -520,7 +524,7 @@ do {								\
 	session->header.data_size += size;
 
 	TEST_ASSERT_VAL("failed to write header",
-		!perf_session__write_header(session, evlist, fd));
+		!perf_session__write_header(session, evlist, file.fd));
 
 	perf_session__delete(session);
 	perf_evlist__delete(evlist);
@@ -529,7 +533,7 @@ do {								\
 	return 0;
 }
 
-static int __session_read(char *file)
+static int __session_read(char *path)
 {
 	struct perf_session *session;
 	struct perf_tool tool = {
@@ -542,10 +546,14 @@ static int __session_read(char *file)
 		.unthrottle = process_unthrottle,
 		.sample = process_sample,
 	};
+	struct perf_data_file file = {
+		.mode = PERF_DATA_MODE_READ,
+		.path = path,
+	};
 
 	pr_debug("session reading start\n");
 
-	session = perf_session__new(file, O_RDONLY, false, false, &tool);
+	session = perf_session__new(&file, false, &tool);
 	TEST_ASSERT_VAL("failed to create session", session);
 
 	TEST_ASSERT_VAL("failed to process events",
diff --git a/tools/perf/util/data.h b/tools/perf/util/data.h
new file mode 100644
index 0000000..ffa0186
--- /dev/null
+++ b/tools/perf/util/data.h
@@ -0,0 +1,29 @@
+#ifndef __PERF_DATA_H
+#define __PERF_DATA_H
+
+#include <stdbool.h>
+
+enum perf_data_mode {
+	PERF_DATA_MODE_WRITE,
+	PERF_DATA_MODE_READ,
+};
+
+struct perf_data_file {
+	const char *path;
+	int fd;
+	bool is_pipe;
+	bool force;
+	enum perf_data_mode mode;
+};
+
+static inline bool perf_data_file__is_read(struct perf_data_file *file)
+{
+	return file->mode == PERF_DATA_MODE_READ;
+}
+
+static inline bool perf_data_file__is_write(struct perf_data_file *file)
+{
+	return file->mode == PERF_DATA_MODE_WRITE;
+}
+
+#endif /* __PERF_DATA_H */
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c
index 787c234..023a5b4 100644
--- a/tools/perf/util/session.c
+++ b/tools/perf/util/session.c
@@ -106,11 +106,11 @@ static void perf_session__destroy_kernel_maps(struct perf_session *self)
 	machines__destroy_kernel_maps(&self->machines);
 }
 
-struct perf_session *perf_session__new(const char *filename, int mode,
-				       bool force, bool repipe,
-				       struct perf_tool *tool)
+struct perf_session *perf_session__new(struct perf_data_file *file,
+				       bool repipe, struct perf_tool *tool)
 {
 	struct perf_session *self;
+	const char *filename = file->path;
 	struct stat st;
 	size_t len;
 
@@ -134,11 +134,11 @@ struct perf_session *perf_session__new(const char *filename, int mode,
 	INIT_LIST_HEAD(&self->ordered_samples.to_free);
 	machines__init(&self->machines);
 
-	if (mode == O_RDONLY) {
-		if (perf_session__open(self, force) < 0)
+	if (perf_data_file__is_read(file)) {
+		if (perf_session__open(self, file->force) < 0)
 			goto out_delete;
 		perf_session__set_id_hdr_size(self);
-	} else if (mode == O_WRONLY) {
+	} else if (perf_data_file__is_write(file)) {
 		/*
 		 * In O_RDONLY mode this will be performed when reading the
 		 * kernel MMAP event, in perf_event__process_mmap().
diff --git a/tools/perf/util/session.h b/tools/perf/util/session.h
index 3aa75fb..1e4d813 100644
--- a/tools/perf/util/session.h
+++ b/tools/perf/util/session.h
@@ -7,6 +7,7 @@
 #include "machine.h"
 #include "symbol.h"
 #include "thread.h"
+#include "data.h"
 #include <linux/rbtree.h>
 #include <linux/perf_event.h>
 
@@ -49,9 +50,8 @@ struct perf_session {
 
 struct perf_tool;
 
-struct perf_session *perf_session__new(const char *filename, int mode,
-				       bool force, bool repipe,
-				       struct perf_tool *tool);
+struct perf_session *perf_session__new(struct perf_data_file *file,
+				       bool repipe, struct perf_tool *tool);
 void perf_session__delete(struct perf_session *session);
 
 void perf_event_header__bswap(struct perf_event_header *self);
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 20/25] perf tools: Add perf_data_file__open interface to data object
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (18 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 19/25] perf tools: Move synthesizing into single function Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 21/25] perf tools: Separating data file properties from session Jiri Olsa
                   ` (6 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding perf_data_file__open interface to data object
to open the perf.data file for both read and write.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Makefile               |   1 +
 tools/perf/builtin-record.c       |  34 +----------
 tools/perf/builtin-top.c          |   9 +--
 tools/perf/tests/session-simple.c |   3 -
 tools/perf/util/data.c            | 120 ++++++++++++++++++++++++++++++++++++++
 tools/perf/util/data.h            |   4 ++
 tools/perf/util/session.c         |  95 ++++++++++--------------------
 tools/perf/util/session.h         |   2 +-
 8 files changed, 158 insertions(+), 110 deletions(-)
 create mode 100644 tools/perf/util/data.c

diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index 2510355..7c80443 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -363,6 +363,7 @@ LIB_OBJS += $(OUTPUT)util/intlist.o
 LIB_OBJS += $(OUTPUT)util/vdso.o
 LIB_OBJS += $(OUTPUT)util/stat.o
 LIB_OBJS += $(OUTPUT)util/record.o
+LIB_OBJS += $(OUTPUT)util/data.o
 
 LIB_OBJS += $(OUTPUT)ui/setup.o
 LIB_OBJS += $(OUTPUT)ui/helpline.o
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 1887b20..ace16f8 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -433,15 +433,12 @@ out:
 
 static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 {
-	struct stat st;
-	int flags;
 	int err, feat;
 	unsigned long waking = 0;
 	const bool forks = argc > 0;
 	struct perf_record_opts *opts = &rec->opts;
 	struct perf_evlist *evsel_list = rec->evlist;
 	struct perf_data_file *file = rec->file;
-	const char *output_name = file->path;
 	struct perf_session *session;
 	bool disabled = false;
 
@@ -455,35 +452,6 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 	signal(SIGUSR1, sig_handler);
 	signal(SIGTERM, sig_handler);
 
-	if (!output_name) {
-		if (!fstat(STDOUT_FILENO, &st) && S_ISFIFO(st.st_mode))
-			file->is_pipe = true;
-		else
-			file->path = output_name = "perf.data";
-	}
-	if (output_name) {
-		if (!strcmp(output_name, "-"))
-			file->is_pipe = true;
-		else if (!stat(output_name, &st) && st.st_size) {
-			char oldname[PATH_MAX];
-			snprintf(oldname, sizeof(oldname), "%s.old",
-				 output_name);
-			unlink(oldname);
-			rename(output_name, oldname);
-		}
-	}
-
-	flags = O_CREAT|O_RDWR|O_TRUNC;
-
-	if (file->is_pipe)
-		file->fd = STDOUT_FILENO;
-	else
-		file->fd = open(output_name, flags, S_IRUSR | S_IWUSR);
-	if (file->fd < 0) {
-		perror("failed to create output file");
-		return -1;
-	}
-
 	session = perf_session__new(file, false, NULL);
 	if (session == NULL) {
 		pr_err("Not enough memory for reading perf file header\n");
@@ -611,7 +579,7 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 	fprintf(stderr,
 		"[ perf record: Captured and wrote %.3f MB %s (~%" PRIu64 " samples) ]\n",
 		(double)rec->bytes_written / 1024.0 / 1024.0,
-		output_name,
+		file->path,
 		rec->bytes_written / 24);
 
 	return 0;
diff --git a/tools/perf/builtin-top.c b/tools/perf/builtin-top.c
index 46489cb..1cfc14c 100644
--- a/tools/perf/builtin-top.c
+++ b/tools/perf/builtin-top.c
@@ -930,15 +930,8 @@ static int __cmd_top(struct perf_top *top)
 	struct perf_record_opts *opts = &top->record_opts;
 	pthread_t thread;
 	int ret;
-	struct perf_data_file file = {
-		.mode = PERF_DATA_MODE_WRITE,
-	};
 
-	/*
-	 * FIXME: perf_session__new should allow passing a O_MMAP, so that all this
-	 * mmap reading, etc is encapsulated in it. Use O_WRONLY for now.
-	 */
-	top->session = perf_session__new(&file, false, NULL);
+	top->session = perf_session__new(NULL, false, NULL);
 	if (top->session == NULL)
 		return -ENOMEM;
 
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index e2b1037..6a459d9 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -461,9 +461,6 @@ static int session_write(char *path)
 	size_t size = 0;
 	int feat;
 
-	file.fd = open(file.path, O_RDWR);
-	TEST_ASSERT_VAL("failed to open data file", file.fd >= 0);
-
 	evlist = perf_evlist__new_default();
 	TEST_ASSERT_VAL("failed to get evlist", evlist);
 
diff --git a/tools/perf/util/data.c b/tools/perf/util/data.c
new file mode 100644
index 0000000..7d09faf
--- /dev/null
+++ b/tools/perf/util/data.c
@@ -0,0 +1,120 @@
+#include <linux/compiler.h>
+#include <linux/kernel.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#include <string.h>
+
+#include "data.h"
+#include "util.h"
+
+static bool check_pipe(struct perf_data_file *file)
+{
+	struct stat st;
+	bool is_pipe = false;
+	int fd = perf_data_file__is_read(file) ?
+		 STDIN_FILENO : STDOUT_FILENO;
+
+	if (!file->path) {
+		if (!fstat(fd, &st) && S_ISFIFO(st.st_mode))
+			is_pipe = true;
+	} else {
+		if (!strcmp(file->path, "-"))
+			is_pipe = true;
+	}
+
+	if (is_pipe)
+		file->fd = fd;
+
+	return file->is_pipe = is_pipe;
+}
+
+static int check_backup(struct perf_data_file *file)
+{
+	struct stat st;
+
+	if (!stat(file->path, &st) && st.st_size) {
+		/* TODO check errors properly */
+		char oldname[PATH_MAX];
+		snprintf(oldname, sizeof(oldname), "%s.old",
+			 file->path);
+		unlink(oldname);
+		rename(file->path, oldname);
+	}
+
+	return 0;
+}
+
+static int open_file_read(struct perf_data_file *file)
+{
+	struct stat st;
+	int fd;
+
+	fd = open(file->path, O_RDONLY);
+	if (fd < 0) {
+		int err = errno;
+
+		pr_err("failed to open %s: %s", file->path, strerror(err));
+		if (err == ENOENT && !strcmp(file->path, "perf.data"))
+			pr_err("  (try 'perf record' first)");
+		pr_err("\n");
+		return -err;
+	}
+
+	if (fstat(fd, &st) < 0)
+		goto out_close;
+
+	if (!file->force && st.st_uid && (st.st_uid != geteuid())) {
+		pr_err("file %s not owned by current user or root\n",
+		       file->path);
+		goto out_close;
+	}
+
+	if (!st.st_size) {
+		pr_info("zero-sized file (%s), nothing to do!\n",
+			file->path);
+		goto out_close;
+	}
+
+	file->size = st.st_size;
+	return fd;
+
+ out_close:
+	close(fd);
+	return -1;
+}
+
+static int open_file_write(struct perf_data_file *file)
+{
+	if (check_backup(file))
+		return -1;
+
+	return open(file->path, O_CREAT|O_RDWR|O_TRUNC, S_IRUSR|S_IWUSR);
+}
+
+static int open_file(struct perf_data_file *file)
+{
+	int fd;
+
+	fd = perf_data_file__is_read(file) ?
+	     open_file_read(file) : open_file_write(file);
+
+	file->fd = fd;
+	return fd < 0 ? -1 : 0;
+}
+
+int perf_data_file__open(struct perf_data_file *file)
+{
+	if (check_pipe(file))
+		return 0;
+
+	if (!file->path)
+		file->path = "perf.data";
+
+	return open_file(file);
+}
+
+void perf_data_file__close(struct perf_data_file *file)
+{
+	close(file->fd);
+}
diff --git a/tools/perf/util/data.h b/tools/perf/util/data.h
index ffa0186..d6c262e 100644
--- a/tools/perf/util/data.h
+++ b/tools/perf/util/data.h
@@ -13,6 +13,7 @@ struct perf_data_file {
 	int fd;
 	bool is_pipe;
 	bool force;
+	unsigned long size;
 	enum perf_data_mode mode;
 };
 
@@ -26,4 +27,7 @@ static inline bool perf_data_file__is_write(struct perf_data_file *file)
 	return file->mode == PERF_DATA_MODE_WRITE;
 }
 
+int perf_data_file__open(struct perf_data_file *file);
+void perf_data_file__close(struct perf_data_file *file);
+
 #endif /* __PERF_DATA_H */
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c
index 023a5b4..b9ceccb 100644
--- a/tools/perf/util/session.c
+++ b/tools/perf/util/session.c
@@ -16,73 +16,35 @@
 #include "perf_regs.h"
 #include "vdso.h"
 
-static int perf_session__open(struct perf_session *self, bool force)
+static int perf_session__open(struct perf_session *self)
 {
-	struct stat input_stat;
-
-	if (!strcmp(self->filename, "-")) {
-		self->fd_pipe = true;
-		self->fd = STDIN_FILENO;
-
+	if (self->fd_pipe) {
 		if (perf_session__read_header(self) < 0)
 			pr_err("incompatible file format (rerun with -v to learn more)");
-
 		return 0;
 	}
 
-	self->fd = open(self->filename, O_RDONLY);
-	if (self->fd < 0) {
-		int err = errno;
-
-		pr_err("failed to open %s: %s", self->filename, strerror(err));
-		if (err == ENOENT && !strcmp(self->filename, "perf.data"))
-			pr_err("  (try 'perf record' first)");
-		pr_err("\n");
-		return -errno;
-	}
-
-	if (fstat(self->fd, &input_stat) < 0)
-		goto out_close;
-
-	if (!force && input_stat.st_uid && (input_stat.st_uid != geteuid())) {
-		pr_err("file %s not owned by current user or root\n",
-		       self->filename);
-		goto out_close;
-	}
-
-	if (!input_stat.st_size) {
-		pr_info("zero-sized file (%s), nothing to do!\n",
-			self->filename);
-		goto out_close;
-	}
-
 	if (perf_session__read_header(self) < 0) {
 		pr_err("incompatible file format (rerun with -v to learn more)");
-		goto out_close;
+		return -1;
 	}
 
 	if (!perf_evlist__valid_sample_type(self->evlist)) {
 		pr_err("non matching sample_type");
-		goto out_close;
+		return -1;
 	}
 
 	if (!perf_evlist__valid_sample_id_all(self->evlist)) {
 		pr_err("non matching sample_id_all");
-		goto out_close;
+		return -1;
 	}
 
 	if (!perf_evlist__valid_read_format(self->evlist)) {
 		pr_err("non matching read_format");
-		goto out_close;
+		return -1;
 	}
 
-	self->size = input_stat.st_size;
 	return 0;
-
-out_close:
-	close(self->fd);
-	self->fd = -1;
-	return -1;
 }
 
 void perf_session__set_id_hdr_size(struct perf_session *session)
@@ -110,35 +72,35 @@ struct perf_session *perf_session__new(struct perf_data_file *file,
 				       bool repipe, struct perf_tool *tool)
 {
 	struct perf_session *self;
-	const char *filename = file->path;
-	struct stat st;
-	size_t len;
-
-	if (!filename || !strlen(filename)) {
-		if (!fstat(STDIN_FILENO, &st) && S_ISFIFO(st.st_mode))
-			filename = "-";
-		else
-			filename = "perf.data";
-	}
 
-	len = strlen(filename);
-	self = zalloc(sizeof(*self) + len);
-
-	if (self == NULL)
+	self = zalloc(sizeof(*self));
+	if (!self)
 		goto out;
 
-	memcpy(self->filename, filename, len);
 	self->repipe = repipe;
 	INIT_LIST_HEAD(&self->ordered_samples.samples);
 	INIT_LIST_HEAD(&self->ordered_samples.sample_cache);
 	INIT_LIST_HEAD(&self->ordered_samples.to_free);
 	machines__init(&self->machines);
 
-	if (perf_data_file__is_read(file)) {
-		if (perf_session__open(self, file->force) < 0)
+	if (file) {
+		if (perf_data_file__open(file))
 			goto out_delete;
-		perf_session__set_id_hdr_size(self);
-	} else if (perf_data_file__is_write(file)) {
+
+		self->fd       = file->fd;
+		self->fd_pipe  = file->is_pipe;
+		self->filename = file->path;
+		self->size     = file->size;
+
+		if (perf_data_file__is_read(file)) {
+			if (perf_session__open(self) < 0)
+				goto out_close;
+
+			perf_session__set_id_hdr_size(self);
+		}
+	}
+
+	if (!file || perf_data_file__is_write(file)) {
 		/*
 		 * In O_RDONLY mode this will be performed when reading the
 		 * kernel MMAP event, in perf_event__process_mmap().
@@ -153,10 +115,13 @@ struct perf_session *perf_session__new(struct perf_data_file *file,
 		tool->ordered_samples = false;
 	}
 
-out:
 	return self;
-out_delete:
+
+ out_close:
+	perf_data_file__close(file);
+ out_delete:
 	perf_session__delete(self);
+ out:
 	return NULL;
 }
 
diff --git a/tools/perf/util/session.h b/tools/perf/util/session.h
index 1e4d813..c6a21d9 100644
--- a/tools/perf/util/session.h
+++ b/tools/perf/util/session.h
@@ -39,7 +39,7 @@ struct perf_session {
 	bool			fd_pipe;
 	bool			repipe;
 	struct ordered_samples	ordered_samples;
-	char			filename[1];
+	const char		*filename;
 };
 
 #define PRINT_IP_OPT_IP		(1<<0)
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 21/25] perf tools: Separating data file properties from session
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (19 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 20/25] perf tools: Add perf_data_file__open interface to data object Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 22/25] perf tests: Add session reading test for little endian perf data v3 Jiri Olsa
                   ` (5 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Removing 'fd, fd_pipe, filename, size' from struct perf_session
and replacing it with struct perf_data_file.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/builtin-annotate.c     |  2 +-
 tools/perf/builtin-buildid-list.c |  2 +-
 tools/perf/builtin-record.c       |  2 --
 tools/perf/builtin-report.c       |  8 +++++---
 tools/perf/builtin-script.c       |  2 +-
 tools/perf/util/data.h            | 15 +++++++++++++++
 tools/perf/util/header.c          | 30 ++++++++++++++++++++----------
 tools/perf/util/header.h          |  1 +
 tools/perf/util/session.c         | 36 +++++++++++++++++++-----------------
 tools/perf/util/session.h         |  5 +----
 10 files changed, 64 insertions(+), 39 deletions(-)

diff --git a/tools/perf/builtin-annotate.c b/tools/perf/builtin-annotate.c
index 64eae2c..1cb8861 100644
--- a/tools/perf/builtin-annotate.c
+++ b/tools/perf/builtin-annotate.c
@@ -248,7 +248,7 @@ static int __cmd_annotate(struct perf_annotate *ann)
 	}
 
 	if (total_nr_samples == 0) {
-		ui__error("The %s file has no samples!\n", session->filename);
+		ui__error("The %s file has no samples!\n", file.path);
 		goto out_delete;
 	}
 
diff --git a/tools/perf/builtin-buildid-list.c b/tools/perf/builtin-buildid-list.c
index 0164c1c..ed3873b 100644
--- a/tools/perf/builtin-buildid-list.c
+++ b/tools/perf/builtin-buildid-list.c
@@ -73,7 +73,7 @@ static int perf_session__list_build_ids(bool force, bool with_hits)
 	 * in pipe-mode, the only way to get the buildids is to parse
 	 * the record stream. Buildids are stored as RECORD_HEADER_BUILD_ID
 	 */
-	if (with_hits || session->fd_pipe)
+	if (with_hits || perf_data_file__is_pipe(&file))
 		perf_session__process_events(session, &build_id__mark_dso_hit_ops);
 
 	perf_session__fprintf_dsos_buildid(session, stdout, dso__skip_buildid, with_hits);
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index ace16f8..046ddda 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -251,7 +251,6 @@ out:
 
 static int process_buildids(struct perf_record *rec)
 {
-	struct perf_data_file *file  = rec->file;
 	struct perf_session *session = rec->session;
 	u64 data_offset              = PERF_FILE_HEADER__DATA_OFFSET;
 	u64 size                     = session->header.data_size;
@@ -259,7 +258,6 @@ static int process_buildids(struct perf_record *rec)
 	if (size == 0)
 		return 0;
 
-	rec->session->fd = file->fd;
 	return __perf_session__process_events(session, data_offset,
 					      size - data_offset, size,
 					      &build_id__mark_dso_hit_ops);
diff --git a/tools/perf/builtin-report.c b/tools/perf/builtin-report.c
index 815866d..af594c5 100644
--- a/tools/perf/builtin-report.c
+++ b/tools/perf/builtin-report.c
@@ -367,8 +367,9 @@ static int perf_report__setup_sample_type(struct perf_report *rep)
 {
 	struct perf_session *self = rep->session;
 	u64 sample_type = perf_evlist__combined_sample_type(self->evlist);
+	bool is_pipe = perf_data_file__is_pipe(self->file);
 
-	if (!self->fd_pipe && !(sample_type & PERF_SAMPLE_CALLCHAIN)) {
+	if (!is_pipe && !(sample_type & PERF_SAMPLE_CALLCHAIN)) {
 		if (sort__has_parent) {
 			ui__error("Selected --sort parent, but no "
 				    "callchain data. Did you call "
@@ -391,7 +392,7 @@ static int perf_report__setup_sample_type(struct perf_report *rep)
 	}
 
 	if (sort__mode == SORT_MODE__BRANCH) {
-		if (!self->fd_pipe &&
+		if (!is_pipe &&
 		    !(sample_type & PERF_SAMPLE_BRANCH_STACK)) {
 			ui__error("Selected -b but no branch data. "
 				  "Did you call perf record without -b?\n");
@@ -489,6 +490,7 @@ static int __cmd_report(struct perf_report *rep)
 	struct map *kernel_map;
 	struct kmap *kernel_kmap;
 	const char *help = "For a higher level overview, try: perf report --sort comm,dso";
+	struct perf_data_file *file = session->file;
 
 	signal(SIGINT, sig_handler);
 
@@ -570,7 +572,7 @@ static int __cmd_report(struct perf_report *rep)
 	}
 
 	if (nr_samples == 0) {
-		ui__error("The %s file has no samples!\n", session->filename);
+		ui__error("The %s file has no samples!\n", file->path);
 		return 0;
 	}
 
diff --git a/tools/perf/builtin-script.c b/tools/perf/builtin-script.c
index 32103c2..a88063d 100644
--- a/tools/perf/builtin-script.c
+++ b/tools/perf/builtin-script.c
@@ -1524,7 +1524,7 @@ int cmd_script(int argc, const char **argv, const char *prefix __maybe_unused)
 			return -1;
 		}
 
-		input = open(session->filename, O_RDONLY);	/* input_name */
+		input = open(file.path, O_RDONLY);	/* input_name */
 		if (input < 0) {
 			perror("failed to open file");
 			return -1;
diff --git a/tools/perf/util/data.h b/tools/perf/util/data.h
index d6c262e..8c2df80 100644
--- a/tools/perf/util/data.h
+++ b/tools/perf/util/data.h
@@ -27,6 +27,21 @@ static inline bool perf_data_file__is_write(struct perf_data_file *file)
 	return file->mode == PERF_DATA_MODE_WRITE;
 }
 
+static inline int perf_data_file__is_pipe(struct perf_data_file *file)
+{
+	return file->is_pipe;
+}
+
+static inline int perf_data_file__fd(struct perf_data_file *file)
+{
+	return file->fd;
+}
+
+static inline unsigned long perf_data_file__size(struct perf_data_file *file)
+{
+	return file->size;
+}
+
 int perf_data_file__open(struct perf_data_file *file);
 void perf_data_file__close(struct perf_data_file *file);
 
diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 36206b5..080252a 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -2175,7 +2175,7 @@ int perf_header__fprintf_info(struct perf_session *session, FILE *fp, bool full)
 {
 	struct header_print_data hd;
 	struct perf_header *header = &session->header;
-	int fd = session->fd;
+	int fd = perf_data_file__fd(session->file);
 	hd.fp = fp;
 	hd.full = full;
 
@@ -2643,8 +2643,10 @@ static int perf_header__read_pipe(struct perf_session *session)
 {
 	struct perf_header *header = &session->header;
 	struct perf_pipe_file_header f_header;
+	struct perf_data_file *file = session->file;
 
-	if (perf_file_header__read_pipe(&f_header, header, session->fd,
+	if (perf_file_header__read_pipe(&f_header, header,
+					perf_data_file__fd(file),
 					session->repipe) < 0) {
 		pr_debug("incompatible file format\n");
 		return -EINVAL;
@@ -2746,12 +2748,13 @@ static int perf_evlist__prepare_tracepoint_events(struct perf_evlist *evlist,
 static int __perf_session__read_header_v2(struct perf_session *session,
 					  struct perf_file_header *header)
 {
+	struct perf_data_file		*file = session->file;
 	struct perf_header		*ph = &session->header;
 	struct perf_file_header_v2	*v2 = &header->v2;
 	struct perf_file_attr		f_attr;
 	u64				f_id;
 	int nr_attrs, nr_ids, i, j;
-	int fd = session->fd;
+	int fd = perf_data_file__fd(file);
 
 	session->evlist = perf_evlist__new();
 	if (session->evlist == NULL)
@@ -2846,6 +2849,8 @@ static int perf_session__read_header_v3(struct perf_session *session,
 {
 	struct perf_header *ph = &session->header;
 	struct perf_file_header_v3 *v3 = &header->v3;
+	struct perf_data_file *file = session->file;
+	int fd = perf_data_file__fd(file);
 
 	memcpy(&ph->adds_features, &v3->adds_features,
 	       sizeof(ph->adds_features));
@@ -2855,7 +2860,7 @@ static int perf_session__read_header_v3(struct perf_session *session,
 	ph->feat_offset  = v3->features.offset;
 	ph->feat_size    = v3->features.size;
 
-	perf_header__process_sections(ph, session->fd, &session->pevent,
+	perf_header__process_sections(ph, fd, &session->pevent,
 				      perf_file_section__process);
 
 	return 0;
@@ -2865,8 +2870,10 @@ static int perf_header_read_file(struct perf_session *session)
 {
 	struct perf_file_header header;
 	struct perf_header *ph = &session->header;
+	struct perf_data_file *file = session->file;
 
-	if (perf_file_header__read(&header, &session->header, session->fd))
+	if (perf_file_header__read(&header, &session->header,
+				   perf_data_file__fd(file)))
 		return -1;
 
 	/* read version specific data */
@@ -2878,7 +2885,9 @@ static int perf_header_read_file(struct perf_session *session)
 
 int perf_session__read_header(struct perf_session *session)
 {
-	if (session->fd_pipe)
+	struct perf_data_file *file = session->file;
+
+	if (perf_data_file__is_pipe(file))
 		return perf_header__read_pipe(session);
 
 	return perf_header_read_file(session) < 0 ? -EINVAL : 0;
@@ -3028,18 +3037,19 @@ int perf_event__process_tracing_data(struct perf_tool *tool __maybe_unused,
 				     struct perf_session *session)
 {
 	ssize_t size_read, padding, size = event->tracing_data.size;
-	off_t offset = lseek(session->fd, 0, SEEK_CUR);
+	int fd = perf_data_file__fd(session->file);
+	off_t offset = lseek(fd, 0, SEEK_CUR);
 	char buf[BUFSIZ];
 
 	/* setup for reading amidst mmap */
-	lseek(session->fd, offset + sizeof(struct tracing_data_event),
+	lseek(fd, offset + sizeof(struct tracing_data_event),
 	      SEEK_SET);
 
-	size_read = trace_report(session->fd, &session->pevent,
+	size_read = trace_report(fd, &session->pevent,
 				 session->repipe);
 	padding = PERF_ALIGN(size_read, sizeof(u64)) - size_read;
 
-	if (readn(session->fd, buf, padding) < 0) {
+	if (readn(fd, buf, padding) < 0) {
 		pr_err("%s: reading input file", __func__);
 		return -1;
 	}
diff --git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 4982e04..a5875f2 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -6,6 +6,7 @@
 #include <stdbool.h>
 #include "types.h"
 #include "event.h"
+#include "data.h"
 
 #include <linux/bitmap.h>
 
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c
index b9ceccb..dfefe78 100644
--- a/tools/perf/util/session.c
+++ b/tools/perf/util/session.c
@@ -18,17 +18,16 @@
 
 static int perf_session__open(struct perf_session *self)
 {
-	if (self->fd_pipe) {
-		if (perf_session__read_header(self) < 0)
-			pr_err("incompatible file format (rerun with -v to learn more)");
-		return 0;
-	}
+	struct perf_data_file *file = self->file;
 
 	if (perf_session__read_header(self) < 0) {
 		pr_err("incompatible file format (rerun with -v to learn more)");
 		return -1;
 	}
 
+	if (perf_data_file__is_pipe(file))
+		return 0;
+
 	if (!perf_evlist__valid_sample_type(self->evlist)) {
 		pr_err("non matching sample_type");
 		return -1;
@@ -87,10 +86,7 @@ struct perf_session *perf_session__new(struct perf_data_file *file,
 		if (perf_data_file__open(file))
 			goto out_delete;
 
-		self->fd       = file->fd;
-		self->fd_pipe  = file->is_pipe;
-		self->filename = file->path;
-		self->size     = file->size;
+		self->file = file;
 
 		if (perf_data_file__is_read(file)) {
 			if (perf_session__open(self) < 0)
@@ -158,7 +154,8 @@ void perf_session__delete(struct perf_session *self)
 	perf_session__delete_threads(self);
 	perf_session_env__delete(&self->header.env);
 	machines__exit(&self->machines);
-	close(self->fd);
+	if (self->file)
+		perf_data_file__close(self->file);
 	free(self);
 	vdso__exit();
 }
@@ -980,6 +977,7 @@ static int perf_session_deliver_event(struct perf_session *session,
 static int perf_session__process_user_event(struct perf_session *session, union perf_event *event,
 					    struct perf_tool *tool, u64 file_offset)
 {
+	int fd = perf_data_file__fd(session->file);
 	int err;
 
 	dump_event(session, event, file_offset, NULL);
@@ -993,7 +991,7 @@ static int perf_session__process_user_event(struct perf_session *session, union
 		return err;
 	case PERF_RECORD_HEADER_TRACING_DATA:
 		/* setup for reading amidst mmap */
-		lseek(session->fd, file_offset, SEEK_SET);
+		lseek(fd, file_offset, SEEK_SET);
 		return tool->tracing_data(tool, event, session);
 	case PERF_RECORD_HEADER_BUILD_ID:
 		return tool->build_id(tool, event, session);
@@ -1120,6 +1118,7 @@ volatile int session_done;
 static int __perf_session__process_pipe_events(struct perf_session *self,
 					       struct perf_tool *tool)
 {
+	int fd = perf_data_file__fd(self->file);
 	union perf_event *event;
 	uint32_t size, cur_size = 0;
 	void *buf = NULL;
@@ -1138,7 +1137,7 @@ static int __perf_session__process_pipe_events(struct perf_session *self,
 		return -errno;
 more:
 	event = buf;
-	err = readn(self->fd, event, sizeof(struct perf_event_header));
+	err = readn(fd, event, sizeof(struct perf_event_header));
 	if (err <= 0) {
 		if (err == 0)
 			goto done;
@@ -1170,7 +1169,7 @@ more:
 	p += sizeof(struct perf_event_header);
 
 	if (size - sizeof(struct perf_event_header)) {
-		err = readn(self->fd, p, size - sizeof(struct perf_event_header));
+		err = readn(fd, p, size - sizeof(struct perf_event_header));
 		if (err <= 0) {
 			if (err == 0) {
 				pr_err("unexpected end of event stream\n");
@@ -1249,6 +1248,7 @@ int __perf_session__process_events(struct perf_session *session,
 				   u64 data_offset, u64 data_size,
 				   u64 file_size, struct perf_tool *tool)
 {
+	int fd = perf_data_file__fd(session->file);
 	u64 head, page_offset, file_offset, file_pos, progress_next;
 	int err, mmap_prot, mmap_flags, map_idx = 0;
 	size_t	mmap_size;
@@ -1281,7 +1281,7 @@ int __perf_session__process_events(struct perf_session *session,
 		mmap_flags = MAP_PRIVATE;
 	}
 remap:
-	buf = mmap(NULL, mmap_size, mmap_prot, mmap_flags, session->fd,
+	buf = mmap(NULL, mmap_size, mmap_prot, mmap_flags, fd,
 		   file_offset);
 	if (buf == MAP_FAILED) {
 		pr_err("failed to mmap file\n");
@@ -1343,16 +1343,17 @@ out_err:
 int perf_session__process_events(struct perf_session *self,
 				 struct perf_tool *tool)
 {
+	u64 size = perf_data_file__size(self->file);
 	int err;
 
 	if (perf_session__register_idle_thread(self) == NULL)
 		return -ENOMEM;
 
-	if (!self->fd_pipe)
+	if (!perf_data_file__is_pipe(self->file))
 		err = __perf_session__process_events(self,
 						     self->header.data_offset,
 						     self->header.data_size,
-						     self->size, tool);
+						     size, tool);
 	else
 		err = __perf_session__process_pipe_events(self, tool);
 
@@ -1575,13 +1576,14 @@ int perf_session__cpu_bitmap(struct perf_session *session,
 void perf_session__fprintf_info(struct perf_session *session, FILE *fp,
 				bool full)
 {
+	int fd = perf_data_file__fd(session->file);
 	struct stat st;
 	int ret;
 
 	if (session == NULL || fp == NULL)
 		return;
 
-	ret = fstat(session->fd, &st);
+	ret = fstat(fd, &st);
 	if (ret == -1)
 		return;
 
diff --git a/tools/perf/util/session.h b/tools/perf/util/session.h
index c6a21d9..5748198 100644
--- a/tools/perf/util/session.h
+++ b/tools/perf/util/session.h
@@ -30,16 +30,13 @@ struct ordered_samples {
 
 struct perf_session {
 	struct perf_header	header;
-	unsigned long		size;
 	struct machines		machines;
 	struct perf_evlist	*evlist;
 	struct pevent		*pevent;
 	struct events_stats	stats;
-	int			fd;
-	bool			fd_pipe;
 	bool			repipe;
 	struct ordered_samples	ordered_samples;
-	const char		*filename;
+	struct perf_data_file	*file;
 };
 
 #define PRINT_IP_OPT_IP		(1<<0)
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 22/25] perf tests: Add session reading test for little endian perf data v3
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (20 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 21/25] perf tools: Separating data file properties from session Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 23/25] perf tests: Add session reading test for big " Jiri Olsa
                   ` (4 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding session reading test for little endian perf data
version 3 included as binary data in the test object.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Makefile                |   1 +
 tools/perf/tests/perf.data.v3.le.h | 212 +++++++++++++++++++++++++++++++++++++
 tools/perf/tests/session-simple.c  |   6 ++
 3 files changed, 219 insertions(+)
 create mode 100644 tools/perf/tests/perf.data.v3.le.h

diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index 7c80443..54f41f5 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -294,6 +294,7 @@ LIB_H += ui/util.h
 LIB_H += ui/ui.h
 LIB_H += tests/perf.data.v2.le.h
 LIB_H += tests/perf.data.v2.be.h
+LIB_H += tests/perf.data.v3.le.h
 
 LIB_OBJS += $(OUTPUT)util/abspath.o
 LIB_OBJS += $(OUTPUT)util/alias.o
diff --git a/tools/perf/tests/perf.data.v3.le.h b/tools/perf/tests/perf.data.v3.le.h
new file mode 100644
index 0000000..dd131d4
--- /dev/null
+++ b/tools/perf/tests/perf.data.v3.le.h
@@ -0,0 +1,212 @@
+/*
+ * generated by:
+ * od -v -t x1 data | cut -f2- -d' ' -s | sed 's/\([a-f0-9][a-f0-9]\)/0x\1,/g' > tests/perf.data.v3.le.h
+ */
+
+0x50, 0x45, 0x52, 0x46, 0x49, 0x4c, 0x45, 0x33, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x48, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb0, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x34, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf8, 0x7f, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x30, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00,
+0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00, 0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00,
+0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00, 0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00, 0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00,
+0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x02, 0x00, 0x18, 0x00, 0x39, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xdf, 0xf8, 0x5d, 0x51, 0xe8, 0x0a, 0x01, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe1, 0x10, 0x00, 0x00, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0xd2, 0x04, 0x00, 0x00, 0xe1, 0x10, 0x00, 0x00,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe1, 0x10, 0x00, 0x00, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0x12, 0x09, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00,
+0xb8, 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0xb5, 0x00, 0x6b, 0xb1, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xe1, 0x10, 0x00, 0x00, 0xf1, 0x37, 0x00, 0x00,
+0xd2, 0x04, 0x00, 0x00, 0xe2, 0x2b, 0x00, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdb, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xdb, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0xfe, 0x1f, 0x53, 0x20, 0x00, 0x00, 0x00, 0x00, 0xa7, 0x78, 0x8c, 0x8b, 0x00, 0x00, 0x00, 0x00,
+0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0xfe, 0x1f, 0x53, 0x20, 0x00, 0x00, 0x00, 0x00, 0xa7, 0x78, 0x8c, 0x8b, 0x00, 0x00, 0x00, 0x00,
+0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00, 0xef, 0xbe, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00,
+0xfe, 0x1f, 0x53, 0x20, 0x00, 0x00, 0x00, 0x00, 0xa7, 0x78, 0x8c, 0x8b, 0x00, 0x00, 0x00, 0x00,
+0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00, 0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00,
+0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00, 0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00,
+0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00,
+0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00,
+0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00, 0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00, 0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00,
+0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00, 0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00,
+0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58, 0x00,
+0xaa, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfa, 0xed, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00,
+0x15, 0xcd, 0x5b, 0x07, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x00,
+0xbf, 0x4a, 0x23, 0xdf, 0x0e, 0x00, 0x00, 0x00, 0x33, 0x81, 0x8d, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x04, 0x00, 0x00, 0xbc, 0x0a, 0x00, 0x00, 0xad, 0xde, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x90, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xd4, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x18, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x5c, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xa0, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xa8, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xec, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x30, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x38, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x4c, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xfc, 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xd4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xd0, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x2c, 0x0b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb4, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xe0, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x40, 0x00, 0x00, 0x00, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x33, 0x2e, 0x39, 0x2e, 0x38, 0x2d, 0x31, 0x30,
+0x30, 0x2e, 0x66, 0x63, 0x31, 0x37, 0x2e, 0x78, 0x38, 0x36, 0x5f, 0x36, 0x34, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x33, 0x2e, 0x31, 0x31,
+0x2e, 0x72, 0x63, 0x31, 0x2e, 0x67, 0x34, 0x32, 0x61, 0x35, 0x35, 0x38, 0x35, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x78, 0x38, 0x36, 0x5f, 0x36, 0x34, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x49, 0x6e, 0x74, 0x65,
+0x6c, 0x28, 0x52, 0x29, 0x20, 0x43, 0x6f, 0x72, 0x65, 0x28, 0x54, 0x4d, 0x29, 0x20, 0x69, 0x37,
+0x2d, 0x32, 0x36, 0x34, 0x30, 0x4d, 0x20, 0x43, 0x50, 0x55, 0x20, 0x40, 0x20, 0x32, 0x2e, 0x38,
+0x30, 0x47, 0x48, 0x7a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x47, 0x65, 0x6e, 0x75, 0x69, 0x6e, 0x65, 0x49, 0x6e, 0x74, 0x65, 0x6c, 0x2c, 0x36, 0x2c, 0x34,
+0x32, 0x2c, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0xac, 0xf5, 0x7a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x2f, 0x68, 0x6f, 0x6d, 0x65, 0x2f, 0x6a, 0x6f, 0x6c, 0x73, 0x61, 0x2f, 0x6b, 0x65, 0x72, 0x6e,
+0x65, 0x6c, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x6c, 0x69, 0x6e, 0x75, 0x78, 0x2d, 0x70, 0x65, 0x72,
+0x66, 0x2f, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x2f, 0x70, 0x65, 0x72, 0x66, 0x2f, 0x70, 0x65, 0x72,
+0x66, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x40, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x73, 0x65, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x2d, 0x76, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
+0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xcf, 0xc3, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x63, 0x79, 0x63, 0x6c,
+0x65, 0x73, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
+0x40, 0x00, 0x00, 0x00, 0x30, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x30, 0x2d, 0x31, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x32, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf0, 0x2c, 0x7e, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x24, 0xd0, 0x4e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x30, 0x2d, 0x33, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00,
+0x04, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x63, 0x70, 0x75, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72, 0x65, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x02, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x74, 0x72, 0x61, 0x63, 0x65, 0x70, 0x6f, 0x69,
+0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x75, 0x6e, 0x63, 0x6f, 0x72, 0x65, 0x5f, 0x63, 0x62, 0x6f, 0x78, 0x5f, 0x30, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x07, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x75, 0x6e, 0x63, 0x6f, 0x72, 0x65, 0x5f, 0x63,
+0x62, 0x6f, 0x78, 0x5f, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00,
+0x62, 0x72, 0x65, 0x61, 0x6b, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00,
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index 6a459d9..e397342 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -30,6 +30,10 @@ char data_file_v2_be[] = {
 #include "perf.data.v2.be.h"
 };
 
+char data_file_v3_le[] = {
+#include "perf.data.v3.le.h"
+};
+
 static int events_mmap;
 static int events_lost;
 static int events_comm;
@@ -642,5 +646,7 @@ int test__session_simple(void)
 	err |= test_file_data(data_file_v2_le, sizeof(data_file_v2_le));
 	pr_debug("Testing v2 BE data\n");
 	err |= test_file_data(data_file_v2_be, sizeof(data_file_v2_be));
+	pr_debug("Testing v3 LE data\n");
+	err |= test_file_data(data_file_v3_le, sizeof(data_file_v3_le));
 	return err;
 }
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 23/25] perf tests: Add session reading test for big endian perf data v3
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (21 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 22/25] perf tests: Add session reading test for little endian perf data v3 Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-01 10:36 ` [PATCH 24/25] perf tools: Add multi file '-M' option for record command Jiri Olsa
                   ` (3 subsequent siblings)
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Adding session reading test for big endian perf data
version 3 included as binary data in the test object.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Makefile                |   1 +
 tools/perf/tests/perf.data.v3.be.h | 258 +++++++++++++++++++++++++++++++++++++
 tools/perf/tests/session-simple.c  |   6 +
 3 files changed, 265 insertions(+)
 create mode 100644 tools/perf/tests/perf.data.v3.be.h

diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index 54f41f5..f2e31d5 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -295,6 +295,7 @@ LIB_H += ui/ui.h
 LIB_H += tests/perf.data.v2.le.h
 LIB_H += tests/perf.data.v2.be.h
 LIB_H += tests/perf.data.v3.le.h
+LIB_H += tests/perf.data.v3.be.h
 
 LIB_OBJS += $(OUTPUT)util/abspath.o
 LIB_OBJS += $(OUTPUT)util/alias.o
diff --git a/tools/perf/tests/perf.data.v3.be.h b/tools/perf/tests/perf.data.v3.be.h
new file mode 100644
index 0000000..bcee87f
--- /dev/null
+++ b/tools/perf/tests/perf.data.v3.be.h
@@ -0,0 +1,258 @@
+/*
+ * generated by:
+ * od -v -t x1 data | cut -f2- -d' ' -s | sed 's/\([a-f0-9][a-f0-9]\)/0x\1,/g' > tests/perf.data.v3.be.h
+ */
+
+0x33, 0x45, 0x4c, 0x49, 0x46, 0x52, 0x45, 0x50, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x48, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0xb0,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x7f, 0xf8,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01, 0x00, 0x30,
+0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39, 0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf,
+0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
+0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf, 0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39, 0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf,
+0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
+0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf, 0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39, 0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf,
+0x00, 0x00, 0x00, 0x02, 0x00, 0x02, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
+0x00, 0x01, 0x0a, 0xe8, 0x51, 0x5d, 0xf8, 0xdf, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x18,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x10, 0xe1, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x10, 0xe1,
+0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x18,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x10, 0xe1, 0x6b, 0x72, 0x61, 0x76, 0x61, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x09, 0x12, 0x00, 0x00, 0x00, 0x0a,
+0x00, 0x00, 0x08, 0xb8, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0xb1, 0x6b, 0x00, 0xb5,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x10, 0xe1, 0x00, 0x00, 0x37, 0xf1,
+0x00, 0x00, 0x04, 0xd2, 0x00, 0x00, 0x2b, 0xe2, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0xdb,
+0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7b, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0xdb,
+0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x20, 0x53, 0x1f, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x8c, 0x78, 0xa7,
+0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x20, 0x53, 0x1f, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x8c, 0x78, 0xa7,
+0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0xbe, 0xef,
+0x00, 0x00, 0x00, 0x00, 0x20, 0x53, 0x1f, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x8b, 0x8c, 0x78, 0xa7,
+0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa,
+0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15,
+0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa, 0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab,
+0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33,
+0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03,
+0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa,
+0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15,
+0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab, 0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x58,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0xaa, 0x00, 0x00, 0xed, 0xfa, 0x00, 0x00, 0x0a, 0xbc,
+0x00, 0x00, 0x00, 0x00, 0x07, 0x5b, 0xcd, 0x15, 0x00, 0x00, 0x00, 0x00, 0xab, 0xab, 0xab, 0xab,
+0x00, 0x00, 0x00, 0x0e, 0xdf, 0x23, 0x4a, 0xbf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8d, 0x81, 0x33,
+0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x0a, 0xbc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xde, 0xad,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x90, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0xd4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x5c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0xa0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0xa8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0xec, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x38, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x14,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0x4c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xb0,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x09, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x48,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x44, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5c,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0e, 0xa0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x24,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xc4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04,
+0x00, 0x00, 0x00, 0x40, 0x69, 0x62, 0x6d, 0x2d, 0x70, 0x37, 0x35, 0x30, 0x65, 0x2d, 0x30, 0x31,
+0x2d, 0x6c, 0x70, 0x31, 0x2e, 0x72, 0x68, 0x74, 0x73, 0x2e, 0x65, 0x6e, 0x67, 0x2e, 0x62, 0x6f,
+0x73, 0x2e, 0x72, 0x65, 0x64, 0x68, 0x61, 0x74, 0x2e, 0x63, 0x6f, 0x6d, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x33, 0x2e, 0x37, 0x2e, 0x30, 0x2d, 0x30, 0x2e,
+0x33, 0x36, 0x2e, 0x65, 0x6c, 0x37, 0x2e, 0x70, 0x70, 0x63, 0x36, 0x34, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x33, 0x2e, 0x39, 0x2e,
+0x72, 0x63, 0x32, 0x2e, 0x67, 0x35, 0x66, 0x37, 0x33, 0x35, 0x31, 0x38, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x70, 0x70, 0x63, 0x36, 0x34, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x40, 0x50, 0x4f, 0x57, 0x45,
+0x52, 0x37, 0x20, 0x28, 0x61, 0x72, 0x63, 0x68, 0x69, 0x74, 0x65, 0x63, 0x74, 0x65, 0x64, 0x29,
+0x2c, 0x20, 0x61, 0x6c, 0x74, 0x69, 0x76, 0x65, 0x63, 0x20, 0x73, 0x75, 0x70, 0x70, 0x6f, 0x72,
+0x74, 0x65, 0x64, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x36, 0x33, 0x2c, 0x35, 0x31, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0xf6, 0xad, 0x40, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40,
+0x2f, 0x72, 0x6f, 0x6f, 0x74, 0x2f, 0x6c, 0x69, 0x6e, 0x75, 0x78, 0x2d, 0x70, 0x65, 0x72, 0x66,
+0x2f, 0x74, 0x6f, 0x6f, 0x6c, 0x73, 0x2f, 0x70, 0x65, 0x72, 0x66, 0x2f, 0x70, 0x65, 0x72, 0x66,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x74, 0x65, 0x73, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x73, 0x65, 0x73, 0x73, 0x69, 0x6f, 0x6e, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x2d, 0x76, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0xc3, 0xcf, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x63, 0x79, 0x63, 0x6c,
+0x65, 0x73, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08,
+0x00, 0x00, 0x00, 0x40, 0x30, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x34, 0x2d, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x38, 0x2d, 0x31, 0x31,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x31, 0x32, 0x2d, 0x31, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x31, 0x36, 0x2d, 0x31, 0x39, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x32, 0x30, 0x2d, 0x32, 0x33, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x32, 0x34, 0x2d, 0x32,
+0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x32, 0x38, 0x2d, 0x33, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x40, 0x30, 0x2d, 0x33, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x34, 0x2d, 0x37, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x38, 0x2d, 0x31, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x31, 0x32, 0x2d, 0x31, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x31, 0x36, 0x2d, 0x31, 0x39, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x32, 0x30, 0x2d, 0x32,
+0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40,
+0x32, 0x34, 0x2d, 0x32, 0x37, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x40, 0x32, 0x38, 0x2d, 0x33, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x94, 0xe2, 0x40, 0x00, 0x00, 0x00, 0x40,
+0x30, 0x2d, 0x33, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x40, 0x63, 0x70, 0x75, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
+0x00, 0x00, 0x00, 0x40, 0x73, 0x6f, 0x66, 0x74, 0x77, 0x61, 0x72, 0x65, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x40, 0x74, 0x72, 0x61, 0x63,
+0x65, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05,
+0x00, 0x00, 0x00, 0x40, 0x62, 0x72, 0x65, 0x61, 0x6b, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
diff --git a/tools/perf/tests/session-simple.c b/tools/perf/tests/session-simple.c
index e397342..175efd5 100644
--- a/tools/perf/tests/session-simple.c
+++ b/tools/perf/tests/session-simple.c
@@ -34,6 +34,10 @@ char data_file_v3_le[] = {
 #include "perf.data.v3.le.h"
 };
 
+char data_file_v3_be[] = {
+#include "perf.data.v3.be.h"
+};
+
 static int events_mmap;
 static int events_lost;
 static int events_comm;
@@ -648,5 +652,7 @@ int test__session_simple(void)
 	err |= test_file_data(data_file_v2_be, sizeof(data_file_v2_be));
 	pr_debug("Testing v3 LE data\n");
 	err |= test_file_data(data_file_v3_le, sizeof(data_file_v3_le));
+	pr_debug("Testing v3 BE data\n");
+	err |= test_file_data(data_file_v3_be, sizeof(data_file_v3_be));
 	return err;
 }
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 24/25] perf tools: Add multi file '-M' option for record command
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (22 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 23/25] perf tests: Add session reading test for big " Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-02  7:52   ` Adrian Hunter
  2013-09-01 10:36 ` [PATCH 25/25] perf tools: Have the process properly sythesized in subsequent data files Jiri Olsa
                   ` (2 subsequent siblings)
  26 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

split event data into multiple files based on the file
size or time delta specified as an argument to the option.

Adding multi file '-M' option for record command to store
output perf.data into multiple files based on the size
threshold.

The threshold is specified either as size (B/K/M/G) or time
(s/m/h) by appending the size with appropriate unit, like:
  -M 5M for 5 megabytes threshold
  -M 1h for 1 hour threshold
The generated name for each data file is appended with sequential
number (prepended by 5 zeros).For default output file name it
will be:
  perf.data-00000
  perf.data-00001
  perf.data-00002
  ...

Also watermark/wakeup_watermark is set accordingly to get
wake ups more often so we could get close enough to the
file size promise.

Example:
  $ perf record -M 5M yes > /dev/null
  ^C[ perf record: Woken up 228 times to write data ]
  [ perf record: Captured and wrote 20.246 MB perf.data-[0-4](~884542 samples) ]
  yes: Interrupt
  $ ls -l perf.data-0*
  -rw------- 1 jolsa jolsa 5289856 Aug 16 16:07 perf.data-00000
  -rw------- 1 jolsa jolsa 5296008 Aug 16 16:08 perf.data-00001
  -rw------- 1 jolsa jolsa 5344968 Aug 16 16:09 perf.data-00002
  -rw------- 1 jolsa jolsa 5309144 Aug 16 16:09 perf.data-00003
  -rw------- 1 jolsa jolsa 2358268 Aug 16 16:09 perf.data-00004
  $ ./perf diff perf.data-0000*
  # Event 'cycles'
  #
  # Data files:
  #  [0] perf.data-00000 (Baseline)
  #  [1] perf.data-00001
  #  [2] perf.data-00002
  #  [3] perf.data-00003
  #  [4] perf.data-00004
  #
  # Baseline/0  Delta/1  Delta/2  Delta/3  Delta/4      Shared Object                                      Symbol
  # ..........  .......  .......  .......  .......  .................  ..........................................
  #
        37.70%   -0.17%   -0.42%   -0.24%   -0.31%  libc-2.15.so       [.] _IO_file_xsputn@@GLIBC_2.2.5
        30.31%   +0.28%   +0.22%   +0.07%   +0.06%  yes                [.] main
        16.73%   +0.02%   +0.10%   -0.03%   +0.11%  libc-2.15.so       [.] __strlen_sse2
        14.22%   -0.30%   -0.10%   -0.31%   -0.14%  libc-2.15.so       [.] fputs_unlocked
         0.39%                              -0.01%  yes                [.] fputs_unlocked@plt
         0.06%                                      [kernel.kallsyms]  [k] system_call
         0.06%                     +0.01%           [kernel.kallsyms]  [k] __srcu_read_lock
         0.05%                     +0.01%           [kernel.kallsyms]  [k] __srcu_read_unlock
  ...

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/Documentation/perf-record.txt |  14 ++
 tools/perf/builtin-record.c              | 246 ++++++++++++++++++++++++++++---
 tools/perf/perf.h                        |  14 ++
 tools/perf/util/evlist.c                 |   2 +-
 tools/perf/util/evlist.h                 |   2 +
 tools/perf/util/evsel.c                  |  24 +++
 6 files changed, 280 insertions(+), 22 deletions(-)

diff --git a/tools/perf/Documentation/perf-record.txt b/tools/perf/Documentation/perf-record.txt
index 400e9bb..f77658b 100644
--- a/tools/perf/Documentation/perf-record.txt
+++ b/tools/perf/Documentation/perf-record.txt
@@ -184,6 +184,20 @@ Enable weightened sampling. An additional weight is recorded per sample and can
 displayed with the weight and local_weight sort keys.  This currently works for TSX
 abort events and some memory events in precise mode on modern Intel CPUs.
 
+-M::
+--multi::
+Store output perf.data into multiple files based on the size threshold.
+The threshold is specified either as size (B/K/M/G) or time (s/m/h)
+by appending the size with appropriate unit, like:
+  -M 5M for 5 megabytes threshold
+  -M 1h for 1 hour threshold
+The generated name for each data file is appended with sequential number
+(prepended by 5 zeros).  For default output file name it will be:
+  perf.data-00000
+  perf.data-00001
+  perf.data-00002
+  ...
+
 SEE ALSO
 --------
 linkperf:perf-stat[1], linkperf:perf-list[1]
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 046ddda..b0c5937 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -66,6 +66,9 @@ struct perf_record {
 	struct perf_tool	tool;
 	struct perf_record_opts	opts;
 	u64			bytes_written;
+	u64			multi_bytes_written;
+	unsigned int		multi_idx;
+	time_t			multi_time;
 	struct perf_data_file	file_base;
 	struct perf_data_file	*file;
 	struct perf_evlist	*evlist;
@@ -249,11 +252,10 @@ out:
 	return rc;
 }
 
-static int process_buildids(struct perf_record *rec)
+static int process_buildids(struct perf_session *session)
 {
-	struct perf_session *session = rec->session;
-	u64 data_offset              = PERF_FILE_HEADER__DATA_OFFSET;
-	u64 size                     = session->header.data_size;
+	u64 data_offset = PERF_FILE_HEADER__DATA_OFFSET;
+	u64 size        = session->header.data_size;
 
 	if (size == 0)
 		return 0;
@@ -263,6 +265,19 @@ static int process_buildids(struct perf_record *rec)
 					      &build_id__mark_dso_hit_ops);
 }
 
+static int file_finish(struct perf_record *rec,
+		       struct perf_data_file *file,
+		       struct perf_session *session,
+		       u64 bytes_written)
+{
+	session->header.data_size = bytes_written;
+
+	if (!rec->no_buildid)
+		process_buildids(session);
+
+	return perf_session__write_header(session, session->evlist, file->fd);
+}
+
 static void perf_record__exit(int status, void *arg)
 {
 	struct perf_record *rec = arg;
@@ -272,12 +287,8 @@ static void perf_record__exit(int status, void *arg)
 		return;
 
 	if (!file->is_pipe) {
-		rec->session->header.data_size += rec->bytes_written;
-
-		if (!rec->no_buildid)
-			process_buildids(rec);
-		perf_session__write_header(rec->session, rec->evlist,
-					   file->fd);
+		file_finish(rec, rec->file, rec->session,
+			    rec->bytes_written);
 		perf_session__delete(rec->session);
 		perf_evlist__delete(rec->evlist);
 		symbol__exit();
@@ -402,6 +413,172 @@ static int synthesize_record(struct perf_record *rec)
 	return err ? err : synthesize_record_file(rec);
 }
 
+static void set_multi_value(struct perf_record_opts *opts,
+			    u64 value, int type)
+{
+	if ((type == MULTI_TYPE__SIZE) &&
+	    (value < MULTI_LIMIT__MIN_SIZE)) {
+		pr_info("setting size to minimal size of the data file %dK\n",
+			MULTI_LIMIT__MIN_SIZE / 1024);
+		value = MULTI_LIMIT__MIN_SIZE;
+	}
+
+	pr_debug("-M/--multi value %lu (%s)\n",
+		 value, type == MULTI_TYPE__SIZE ? "size" : "time");
+
+	opts->multi_limit = true;
+	opts->multi_value = value;
+	opts->multi_type  = type;
+}
+
+static int parse_multi(const struct option *opt, const char *str,
+		       int unset __maybe_unused)
+{
+	static struct parse_tag tags_size[] = {
+		{ .tag  = 'B', .mult = 1       },
+		{ .tag  = 'K', .mult = 1 << 10 },
+		{ .tag  = 'M', .mult = 1 << 20 },
+		{ .tag  = 'G', .mult = 1 << 30 },
+		{ .tag  = 0 },
+	};
+	static struct parse_tag tags_time[] = {
+		{ .tag  = 's', .mult = 1    },
+		{ .tag  = 'm', .mult = 60   },
+		{ .tag  = 'h', .mult = 3600 },
+		{ .tag  = 0 },
+	};
+	struct perf_record_opts *opts = opt->value;
+	unsigned long value;
+
+	value = parse_tag_value(str, tags_size);
+	if (value != (unsigned long) -1) {
+		set_multi_value(opts, value, MULTI_TYPE__SIZE);
+		return 0;
+	}
+
+	value = parse_tag_value(str, tags_time);
+	if (value != (unsigned long) -1) {
+		set_multi_value(opts, value, MULTI_TYPE__TIME);
+		return 0;
+	}
+
+	pr_err("failed to parse -M/--multi size value\n");
+	return -1;
+}
+
+static const char *multi_file_base(struct perf_data_file *file)
+{
+	static const char *base;
+
+	if (!base)
+		base = file->path;
+	if (!base)
+		base = "perf.data";
+
+	return base;
+}
+
+static int multi_file_name(struct perf_data_file *file, unsigned int idx)
+{
+	char path[PATH_MAX];
+
+	snprintf(path, PATH_MAX, "%s-%05u",
+		 multi_file_base(file), idx);
+	file->path = strdup(path);
+
+	return file->path ? 0 : -ENOMEM;
+}
+
+static int multi_file_finish(struct perf_record *rec)
+{
+	struct perf_data_file *file = rec->file;
+	struct perf_session *session;
+	int err;
+
+	/* TODO create perf_session__dup(session) */
+	session = perf_session__new(NULL, false, NULL);
+	if (!session)
+		return -ENOMEM;
+
+	session->evlist = rec->evlist;
+	session->file   = file;
+	session->header = rec->session->header;
+
+	err = file_finish(rec, file, session, rec->bytes_written);
+	if (!err)
+		pr_debug("multi: written file %s [%s]\n",
+			 file->path, err ? "failed" : "ok");
+
+	perf_session__delete(session);
+	return err;
+}
+
+static int multi_file_init(struct perf_record *rec)
+{
+	struct perf_data_file *file = rec->file;
+	int err;
+
+	if (multi_file_name(rec->file, rec->multi_idx++))
+		return -ENOMEM;
+
+	err = perf_data_file__open(file);
+	if (err)
+		return err;
+
+	err = perf_session__prepare_header(file->fd);
+	if (err)
+		goto out_close;
+
+	err = synthesize_record_file(rec);
+	if (err)
+		goto out_close;
+
+	return 0;
+
+ out_close:
+	perf_data_file__close(file);
+	return err;
+}
+
+static bool multi_trigger(struct perf_record *rec)
+{
+	u64 value = rec->opts.multi_value;
+	time_t now;
+
+	switch (rec->opts.multi_type) {
+	case MULTI_TYPE__SIZE:
+		return rec->bytes_written > value;
+
+	case MULTI_TYPE__TIME:
+		now = time(NULL);
+		return (now - rec->multi_time) > (time_t) value;
+	default:
+		BUG_ON(1);
+	};
+}
+
+/*
+ * TODO Setup SIGALRM to wakeup for time threshold
+ * even if there's no data.
+ * */
+static int multi_file_threshold(struct perf_record *rec)
+{
+	int err;
+
+	if (!rec->opts.multi_limit || !multi_trigger(rec))
+		return 0;
+
+	pr_debug("multi: file limit crossed %lu B\n", rec->bytes_written);
+
+	err = multi_file_finish(rec);
+
+	rec->multi_bytes_written += rec->bytes_written;
+	rec->bytes_written = 0;
+	rec->multi_time    = time(NULL);
+
+	return err ? err : multi_file_init(rec);
+}
+
 static struct perf_event_header finished_round_event = {
 	.size = sizeof(struct perf_event_header),
 	.type = PERF_RECORD_FINISHED_ROUND,
@@ -421,6 +598,9 @@ static int perf_record__mmap_read_all(struct perf_record *rec)
 		}
 	}
 
+	if (multi_file_threshold(rec))
+		return -1;
+
 	if (perf_header__has_feat(&rec->session->header, HEADER_TRACING_DATA))
 		rc = write_output(rec, &finished_round_event,
 				  sizeof(finished_round_event));
@@ -429,6 +609,28 @@ out:
 	return rc;
 }
 
+static void display_exit_msg(struct perf_record *rec, unsigned long waking)
+{
+	struct perf_data_file *file = rec->file;
+	bool multi = rec->opts.multi_limit > 0;
+	char buf[PATH_MAX];
+	u64  bytes = multi ? rec->multi_bytes_written : rec->bytes_written;
+	char *path = multi ? buf : (char *) file->path;
+
+	if (multi)
+		snprintf(path, PATH_MAX, "%s-[0-%u]",
+			 multi_file_base(file), rec->multi_idx - 1);
+
+	fprintf(stderr, "[ perf record: Woken up %ld times to write data ]\n", waking);
+
+	/*
+	 * Approximate RIP event size: 24 bytes.
+	 */
+	fprintf(stderr,
+		"[ perf record: Captured and wrote %.3f MB %s(~%" PRIu64 " samples) ]\n",
+		(double) bytes / 1024.0 / 1024.0, path, bytes / 24);
+}
+
 static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 {
 	int err, feat;
@@ -450,6 +652,12 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 	signal(SIGUSR1, sig_handler);
 	signal(SIGTERM, sig_handler);
 
+	if (rec->opts.multi_limit &&
+	    multi_file_name(file, rec->multi_idx++)) {
+		pr_err("Not enough memory\n");
+		return -1;
+	}
+
 	session = perf_session__new(file, false, NULL);
 	if (session == NULL) {
 		pr_err("Not enough memory for reading perf file header\n");
@@ -515,6 +723,9 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 	if (err)
 		goto out_delete_session;
 
+	if (rec->opts.multi_type == MULTI_TYPE__TIME)
+		rec->multi_time = time(NULL);
+
 	if (rec->realtime_prio) {
 		struct sched_param param;
 
@@ -569,17 +780,7 @@ static int __cmd_record(struct perf_record *rec, int argc, const char **argv)
 	if (quiet || signr == SIGUSR1)
 		return 0;
 
-	fprintf(stderr, "[ perf record: Woken up %ld times to write data ]\n", waking);
-
-	/*
-	 * Approximate RIP event size: 24 bytes.
-	 */
-	fprintf(stderr,
-		"[ perf record: Captured and wrote %.3f MB %s (~%" PRIu64 " samples) ]\n",
-		(double)rec->bytes_written / 1024.0 / 1024.0,
-		file->path,
-		rec->bytes_written / 24);
-
+	display_exit_msg(rec, waking);
 	return 0;
 
 out_delete_session:
@@ -845,6 +1046,9 @@ const struct option record_options[] = {
 	OPT_CALLBACK('m', "mmap-pages", &record.opts.mmap_pages, "pages",
 		     "number of mmap data pages",
 		     perf_evlist__parse_mmap_pages),
+	OPT_CALLBACK('M', "multi", &record.opts, "spec",
+		     "split data into more data files",
+		     parse_multi),
 	OPT_BOOLEAN(0, "group", &record.opts.group,
 		    "put the counters into a counter group"),
 	OPT_CALLBACK_DEFAULT('g', "call-graph", &record.opts,
diff --git a/tools/perf/perf.h b/tools/perf/perf.h
index 0914630..76b7ae0 100644
--- a/tools/perf/perf.h
+++ b/tools/perf/perf.h
@@ -210,6 +210,17 @@ enum perf_call_graph_mode {
 	CALLCHAIN_DWARF
 };
 
+enum perf_record_multi_limits {
+	MULTI_LIMIT__MIN_SIZE       = 100 * 1024, /* 100K */
+	MULTI_LIMIT__MIN_WATTERMARK = 10  * 1024, /* 10K */
+	MULTI_LIMIT__MAX_WATTERMARK = MULTI_LIMIT__MIN_SIZE,
+};
+
+enum perf_record_multi_type {
+	MULTI_TYPE__SIZE,
+	MULTI_TYPE__TIME,
+};
+
 struct perf_record_opts {
 	struct perf_target target;
 	int	     call_graph;
@@ -223,6 +234,7 @@ struct perf_record_opts {
 	bool	     sample_weight;
 	bool	     sample_time;
 	bool	     period;
+	bool	     multi_limit;
 	unsigned int freq;
 	unsigned int mmap_pages;
 	unsigned int user_freq;
@@ -230,6 +242,8 @@ struct perf_record_opts {
 	u64	     default_interval;
 	u64	     user_interval;
 	u16	     stack_dump_size;
+	u64	     multi_value;
+	int	     multi_type;
 };
 
 #endif
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index 998e0d1..a862937 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -632,7 +632,7 @@ out_unmap:
 	return -1;
 }
 
-static size_t perf_evlist__mmap_size(unsigned long pages)
+size_t perf_evlist__mmap_size(unsigned long pages)
 {
 	/* 512 kiB: default amount of unprivileged mlocked memory */
 	if (pages == UINT_MAX)
diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h
index ca016b1..59bcf52 100644
--- a/tools/perf/util/evlist.h
+++ b/tools/perf/util/evlist.h
@@ -104,6 +104,8 @@ int perf_evlist__prepare_workload(struct perf_evlist *evlist,
 				  bool want_signal);
 int perf_evlist__start_workload(struct perf_evlist *evlist);
 
+size_t perf_evlist__mmap_size(unsigned long pages);
+
 int perf_evlist__parse_mmap_pages(const struct option *opt,
 				  const char *str,
 				  int unset);
diff --git a/tools/perf/util/evsel.c b/tools/perf/util/evsel.c
index e8745fb..122511d 100644
--- a/tools/perf/util/evsel.c
+++ b/tools/perf/util/evsel.c
@@ -672,6 +672,30 @@ void perf_evsel__config(struct perf_evsel *evsel,
 		attr->branch_sample_type = opts->branch_stack;
 	}
 
+	if (opts->multi_limit) {
+		u64 wm = MULTI_LIMIT__MIN_WATTERMARK;
+		attr->watermark = 1;
+
+		if (opts->multi_type == MULTI_TYPE__SIZE) {
+			/*
+			 * The watermark could not get under 10K because
+			 * of the minimal file limit and we are guarded
+			 * with 100K for max wattermark.
+			 */
+			wm = opts->multi_value;
+			wm = min(wm / 10, (u64) MULTI_LIMIT__MAX_WATTERMARK);
+
+			/*
+			 * We also dont want to have watermark close to the size
+			 * of the mmap to ensure data would always cross it and
+			 * we get poll notification.
+			 */
+			wm = min(wm, (u64) perf_evlist__mmap_size(opts->mmap_pages) - 100);
+		}
+
+		attr->wakeup_watermark = wm;
+	}
+
 	if (opts->sample_weight)
 		attr->sample_type	|= PERF_SAMPLE_WEIGHT;
 
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [PATCH 25/25] perf tools: Have the process properly sythesized in subsequent data files
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (23 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 24/25] perf tools: Add multi file '-M' option for record command Jiri Olsa
@ 2013-09-01 10:36 ` Jiri Olsa
  2013-09-02  2:42 ` [PATCHv2 00/25] perf tool: Add support for multiple data file storage Andi Kleen
  2013-09-09 11:17 ` Peter Zijlstra
  26 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-01 10:36 UTC (permalink / raw)
  To: linux-kernel
  Cc: Jiri Olsa, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

Change the target so the sythesizing routine would think
it needs to synthesized whole process, because there's no
exec COMM event for subsequent data files.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: David Ahern <dsahern@gmail.com>
---
 tools/perf/builtin-record.c | 11 +++++++++++
 1 file changed, 11 insertions(+)

diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index b0c5937..0dbf9a3 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -516,6 +516,8 @@ static int multi_file_finish(struct perf_record *rec)
 static int multi_file_init(struct perf_record *rec)
 {
 	struct perf_data_file *file = rec->file;
+	struct perf_record_opts *opts = &rec->opts;
+	static bool target_change;
 	int err;
 
 	if (multi_file_name(rec->file, rec->multi_idx++))
@@ -529,6 +531,15 @@ static int multi_file_init(struct perf_record *rec)
 	if (err)
 		goto out_close;
 
+	/*
+	 * XXX HACK - Make the target looks like we have pid
+	 * so we get the process fully synthetised.
+	 */
+	if (perf_target__none(&opts->target) && !target_change) {
+		target_change = true;
+		opts->target.pid = "multi";
+	}
+
 	err = synthesize_record_file(rec);
 	if (err)
 		goto out_close;
-- 
1.7.11.7


^ permalink raw reply related	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (24 preceding siblings ...)
  2013-09-01 10:36 ` [PATCH 25/25] perf tools: Have the process properly sythesized in subsequent data files Jiri Olsa
@ 2013-09-02  2:42 ` Andi Kleen
  2013-09-09 11:17 ` Peter Zijlstra
  26 siblings, 0 replies; 48+ messages in thread
From: Andi Kleen @ 2013-09-02  2:42 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, David Ahern

On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
> hi,
> sending the support for multiple file storage. Initial
> RFC is here:
> http://marc.info/?l=linux-kernel&m=137408381902423&w=2

Just a general comment. If you repost please always keep the overview
description/motivation in 0/0.

-Andi


^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCH 24/25] perf tools: Add multi file '-M' option for record command
  2013-09-01 10:36 ` [PATCH 24/25] perf tools: Add multi file '-M' option for record command Jiri Olsa
@ 2013-09-02  7:52   ` Adrian Hunter
  2013-09-02  8:37     ` Jiri Olsa
  0 siblings, 1 reply; 48+ messages in thread
From: Adrian Hunter @ 2013-09-02  7:52 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

On 01/09/13 13:36, Jiri Olsa wrote:
> split event data into multiple files based on the file
> size or time delta specified as an argument to the option.
> 
> Adding multi file '-M' option for record command to store
> output perf.data into multiple files based on the size
> threshold.
> 
> The threshold is specified either as size (B/K/M/G) or time
> (s/m/h) by appending the size with appropriate unit, like:
>   -M 5M for 5 megabytes threshold
>   -M 1h for 1 hour threshold
> The generated name for each data file is appended with sequential
> number (prepended by 5 zeros).For default output file name it
> will be:
>   perf.data-00000
>   perf.data-00001
>   perf.data-00002
>   ...
> 
> Also watermark/wakeup_watermark is set accordingly to get
> wake ups more often so we could get close enough to the
> file size promise.
> 
> Example:
>   $ perf record -M 5M yes > /dev/null
>   ^C[ perf record: Woken up 228 times to write data ]
>   [ perf record: Captured and wrote 20.246 MB perf.data-[0-4](~884542 samples) ]
>   yes: Interrupt
>   $ ls -l perf.data-0*
>   -rw------- 1 jolsa jolsa 5289856 Aug 16 16:07 perf.data-00000
>   -rw------- 1 jolsa jolsa 5296008 Aug 16 16:08 perf.data-00001
>   -rw------- 1 jolsa jolsa 5344968 Aug 16 16:09 perf.data-00002
>   -rw------- 1 jolsa jolsa 5309144 Aug 16 16:09 perf.data-00003
>   -rw------- 1 jolsa jolsa 2358268 Aug 16 16:09 perf.data-00004

Did you consider doing this with "perf inject" instead of "perf record"?
That way you could get the split exactly right, and you could split the same
file different ways.



^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCH 24/25] perf tools: Add multi file '-M' option for record command
  2013-09-02  7:52   ` Adrian Hunter
@ 2013-09-02  8:37     ` Jiri Olsa
  2013-09-02  9:11       ` Adrian Hunter
  0 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-02  8:37 UTC (permalink / raw)
  To: Adrian Hunter
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

On Mon, Sep 02, 2013 at 10:52:46AM +0300, Adrian Hunter wrote:
> On 01/09/13 13:36, Jiri Olsa wrote:
> > split event data into multiple files based on the file
> > size or time delta specified as an argument to the option.
> > 
> > Adding multi file '-M' option for record command to store
> > output perf.data into multiple files based on the size
> > threshold.
> > 
> > The threshold is specified either as size (B/K/M/G) or time
> > (s/m/h) by appending the size with appropriate unit, like:
> >   -M 5M for 5 megabytes threshold
> >   -M 1h for 1 hour threshold
> > The generated name for each data file is appended with sequential
> > number (prepended by 5 zeros).For default output file name it
> > will be:
> >   perf.data-00000
> >   perf.data-00001
> >   perf.data-00002
> >   ...
> > 
> > Also watermark/wakeup_watermark is set accordingly to get
> > wake ups more often so we could get close enough to the
> > file size promise.
> > 
> > Example:
> >   $ perf record -M 5M yes > /dev/null
> >   ^C[ perf record: Woken up 228 times to write data ]
> >   [ perf record: Captured and wrote 20.246 MB perf.data-[0-4](~884542 samples) ]
> >   yes: Interrupt
> >   $ ls -l perf.data-0*
> >   -rw------- 1 jolsa jolsa 5289856 Aug 16 16:07 perf.data-00000
> >   -rw------- 1 jolsa jolsa 5296008 Aug 16 16:08 perf.data-00001
> >   -rw------- 1 jolsa jolsa 5344968 Aug 16 16:09 perf.data-00002
> >   -rw------- 1 jolsa jolsa 5309144 Aug 16 16:09 perf.data-00003
> >   -rw------- 1 jolsa jolsa 2358268 Aug 16 16:09 perf.data-00004
> 
> Did you consider doing this with "perf inject" instead of "perf record"?
> That way you could get the split exactly right, and you could split the same
> file different ways.

right, this could be added into inject command as well

jirka

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCH 24/25] perf tools: Add multi file '-M' option for record command
  2013-09-02  8:37     ` Jiri Olsa
@ 2013-09-02  9:11       ` Adrian Hunter
  2013-09-02  9:40         ` Jiri Olsa
  0 siblings, 1 reply; 48+ messages in thread
From: Adrian Hunter @ 2013-09-02  9:11 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

On 02/09/13 11:37, Jiri Olsa wrote:
> On Mon, Sep 02, 2013 at 10:52:46AM +0300, Adrian Hunter wrote:
>> On 01/09/13 13:36, Jiri Olsa wrote:
>>> split event data into multiple files based on the file
>>> size or time delta specified as an argument to the option.
>>>
>>> Adding multi file '-M' option for record command to store
>>> output perf.data into multiple files based on the size
>>> threshold.
>>>
>>> The threshold is specified either as size (B/K/M/G) or time
>>> (s/m/h) by appending the size with appropriate unit, like:
>>>   -M 5M for 5 megabytes threshold
>>>   -M 1h for 1 hour threshold
>>> The generated name for each data file is appended with sequential
>>> number (prepended by 5 zeros).For default output file name it
>>> will be:
>>>   perf.data-00000
>>>   perf.data-00001
>>>   perf.data-00002
>>>   ...
>>>
>>> Also watermark/wakeup_watermark is set accordingly to get
>>> wake ups more often so we could get close enough to the
>>> file size promise.
>>>
>>> Example:
>>>   $ perf record -M 5M yes > /dev/null
>>>   ^C[ perf record: Woken up 228 times to write data ]
>>>   [ perf record: Captured and wrote 20.246 MB perf.data-[0-4](~884542 samples) ]
>>>   yes: Interrupt
>>>   $ ls -l perf.data-0*
>>>   -rw------- 1 jolsa jolsa 5289856 Aug 16 16:07 perf.data-00000
>>>   -rw------- 1 jolsa jolsa 5296008 Aug 16 16:08 perf.data-00001
>>>   -rw------- 1 jolsa jolsa 5344968 Aug 16 16:09 perf.data-00002
>>>   -rw------- 1 jolsa jolsa 5309144 Aug 16 16:09 perf.data-00003
>>>   -rw------- 1 jolsa jolsa 2358268 Aug 16 16:09 perf.data-00004
>>
>> Did you consider doing this with "perf inject" instead of "perf record"?
>> That way you could get the split exactly right, and you could split the same
>> file different ways.
> 
> right, this could be added into inject command as well

I was really thinking "instead" not "as well" e.g.

	perf record yes | perf inject -M 5M


^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCH 24/25] perf tools: Add multi file '-M' option for record command
  2013-09-02  9:11       ` Adrian Hunter
@ 2013-09-02  9:40         ` Jiri Olsa
  0 siblings, 0 replies; 48+ messages in thread
From: Jiri Olsa @ 2013-09-02  9:40 UTC (permalink / raw)
  To: Adrian Hunter
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Peter Zijlstra,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

On Mon, Sep 02, 2013 at 12:11:35PM +0300, Adrian Hunter wrote:
> On 02/09/13 11:37, Jiri Olsa wrote:
> > On Mon, Sep 02, 2013 at 10:52:46AM +0300, Adrian Hunter wrote:
> >> On 01/09/13 13:36, Jiri Olsa wrote:
> >>> split event data into multiple files based on the file
> >>> size or time delta specified as an argument to the option.
> >>>
> >>> Adding multi file '-M' option for record command to store
> >>> output perf.data into multiple files based on the size
> >>> threshold.
> >>>
> >>> The threshold is specified either as size (B/K/M/G) or time
> >>> (s/m/h) by appending the size with appropriate unit, like:
> >>>   -M 5M for 5 megabytes threshold
> >>>   -M 1h for 1 hour threshold
> >>> The generated name for each data file is appended with sequential
> >>> number (prepended by 5 zeros).For default output file name it
> >>> will be:
> >>>   perf.data-00000
> >>>   perf.data-00001
> >>>   perf.data-00002
> >>>   ...
> >>>
> >>> Also watermark/wakeup_watermark is set accordingly to get
> >>> wake ups more often so we could get close enough to the
> >>> file size promise.
> >>>
> >>> Example:
> >>>   $ perf record -M 5M yes > /dev/null
> >>>   ^C[ perf record: Woken up 228 times to write data ]
> >>>   [ perf record: Captured and wrote 20.246 MB perf.data-[0-4](~884542 samples) ]
> >>>   yes: Interrupt
> >>>   $ ls -l perf.data-0*
> >>>   -rw------- 1 jolsa jolsa 5289856 Aug 16 16:07 perf.data-00000
> >>>   -rw------- 1 jolsa jolsa 5296008 Aug 16 16:08 perf.data-00001
> >>>   -rw------- 1 jolsa jolsa 5344968 Aug 16 16:09 perf.data-00002
> >>>   -rw------- 1 jolsa jolsa 5309144 Aug 16 16:09 perf.data-00003
> >>>   -rw------- 1 jolsa jolsa 2358268 Aug 16 16:09 perf.data-00004
> >>
> >> Did you consider doing this with "perf inject" instead of "perf record"?
> >> That way you could get the split exactly right, and you could split the same
> >> file different ways.
> > 
> > right, this could be added into inject command as well
> 
> I was really thinking "instead" not "as well" e.g.
> 
> 	perf record yes | perf inject -M 5M
> 

yep, got it.. this gives you more fine grained size resolution
and lets you split already stored data files, nice

But while I think this is nice feature to have, two things keeps
me thinking we should leave the support in record command as well:
  - the extra inject command overhead, that needs to parse the whole
    stream, which might not be wanted in some cases
  - AFAIU the vast majority of perf users do just record/report
    and would be restrained from this feature ;-)

jirka

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
                   ` (25 preceding siblings ...)
  2013-09-02  2:42 ` [PATCHv2 00/25] perf tool: Add support for multiple data file storage Andi Kleen
@ 2013-09-09 11:17 ` Peter Zijlstra
  2013-09-09 11:36   ` Jiri Olsa
                     ` (2 more replies)
  26 siblings, 3 replies; 48+ messages in thread
From: Peter Zijlstra @ 2013-09-09 11:17 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Arnaldo Carvalho de Melo,
	Andi Kleen, David Ahern

On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
> hi,
> sending the support for multiple file storage. Initial
> RFC is here:
> http://marc.info/?l=linux-kernel&m=137408381902423&w=2
> 
> v2 changes:
>   - reworked perf mmap size setup to be able to get
>     the mmap size value easily later
>   - added perf.data read/write test for v2 and v3
>     for both endianity
>   - added record '-M time' support

So this 0/n post seems to have forgotten to list the rationale for doing
all this.. 

The only reason I wanted this is so that each thread can write its own
data. The current one file thing is an immense bottle-neck for big
machines.

However your earlier patches didn't do it because of that -- I forgot
why they did it and you're now not telling.



^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 11:17 ` Peter Zijlstra
@ 2013-09-09 11:36   ` Jiri Olsa
  2013-09-09 11:55     ` Peter Zijlstra
  2013-09-10  6:54   ` Adrian Hunter
  2013-09-10  8:57   ` Namhyung Kim
  2 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-09 11:36 UTC (permalink / raw)
  To: Peter Zijlstra
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Arnaldo Carvalho de Melo,
	Andi Kleen, David Ahern

On Mon, Sep 09, 2013 at 01:17:49PM +0200, Peter Zijlstra wrote:
> On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
> > hi,
> > sending the support for multiple file storage. Initial
> > RFC is here:
> > http://marc.info/?l=linux-kernel&m=137408381902423&w=2
> > 
> > v2 changes:
> >   - reworked perf mmap size setup to be able to get
> >     the mmap size value easily later
> >   - added perf.data read/write test for v2 and v3
> >     for both endianity
> >   - added record '-M time' support
> 
> So this 0/n post seems to have forgotten to list the rationale for doing
> all this.. 

here it is:

This patchset is actually doing 3 essential things:
  1) adds new perf data format version (v3)
  2) adds class/object to handle perf data file
  3) adds record '-M size' option

ad 1) Along the way I realized it'd be much easier to have the
      format simplified. I ended up with just 'DATA' and 'FEATURES'
      sections making the file format more generic.

      The easier/generic format will be for example useful for the
      cpu hotplug notification (and maybe even for ftrace data files
      features?)

      The version 2 should be still readable by perf, while it
      produces data in version 3 from this patchset onwards.

ad 2) I needed to unify perf data file handling to make the -M
      implementation clear.

> 
> The only reason I wanted this is so that each thread can write its own
> data. The current one file thing is an immense bottle-neck for big
> machines.
> 

I haven't considered the thread based storage yet, but I
think having the simplified format and centralized file
handling will only help.

jirka

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 11:36   ` Jiri Olsa
@ 2013-09-09 11:55     ` Peter Zijlstra
  2013-09-09 14:03       ` Jiri Olsa
  0 siblings, 1 reply; 48+ messages in thread
From: Peter Zijlstra @ 2013-09-09 11:55 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Arnaldo Carvalho de Melo,
	Andi Kleen, David Ahern

On Mon, Sep 09, 2013 at 01:36:41PM +0200, Jiri Olsa wrote:
> On Mon, Sep 09, 2013 at 01:17:49PM +0200, Peter Zijlstra wrote:
> > On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
> This patchset is actually doing 3 essential things:
>   1) adds new perf data format version (v3)
>   2) adds class/object to handle perf data file
>   3) adds record '-M size' option

So the -M thing is where the multiple files stuff comes from, right?
What's the purpose of this? Why would I care how big these files get,
surely filesystems handle 4g+ files these days.

> > The only reason I wanted this is so that each thread can write its own
> > data. The current one file thing is an immense bottle-neck for big
> > machines.
> > 
> 
> I haven't considered the thread based storage yet, but I
> think having the simplified format and centralized file
> handling will only help.

Please do consider it now, it'd suck to have to change the file format
thing yet again.

With both per-thread and size limited your filename generation needs
some extra bits I suppose.

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 11:55     ` Peter Zijlstra
@ 2013-09-09 14:03       ` Jiri Olsa
  2013-09-09 14:11         ` David Ahern
  0 siblings, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-09 14:03 UTC (permalink / raw)
  To: Peter Zijlstra
  Cc: linux-kernel, Corey Ashford, Frederic Weisbecker, Ingo Molnar,
	Namhyung Kim, Paul Mackerras, Arnaldo Carvalho de Melo,
	Andi Kleen, David Ahern

On Mon, Sep 09, 2013 at 01:55:18PM +0200, Peter Zijlstra wrote:
> On Mon, Sep 09, 2013 at 01:36:41PM +0200, Jiri Olsa wrote:
> > On Mon, Sep 09, 2013 at 01:17:49PM +0200, Peter Zijlstra wrote:
> > > On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
> > This patchset is actually doing 3 essential things:
> >   1) adds new perf data format version (v3)
> >   2) adds class/object to handle perf data file
> >   3) adds record '-M size' option
> 
> So the -M thing is where the multiple files stuff comes from, right?
> What's the purpose of this? Why would I care how big these files get,
> surely filesystems handle 4g+ files these days.

my usage currently is to having this running during the day:
(well whenever I remember to run it.. ;-) )

  [jolsa@krava perf]$ sudo ./perf record -g -M 1m -a

and checking report when the system or app get stuck

with multiple files I can just easily (or automaticaly)
remove old ones without restarting session

> 
> > > The only reason I wanted this is so that each thread can write its own
> > > data. The current one file thing is an immense bottle-neck for big
> > > machines.
> > > 
> > 
> > I haven't considered the thread based storage yet, but I
> > think having the simplified format and centralized file
> > handling will only help.
> 
> Please do consider it now, it'd suck to have to change the file format
> thing yet again.

ook

> 
> With both per-thread and size limited your filename generation needs
> some extra bits I suppose.

yep, and probably some merging at the end

jirka

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 14:03       ` Jiri Olsa
@ 2013-09-09 14:11         ` David Ahern
  2013-09-09 14:31           ` Jiri Olsa
  2013-09-09 16:06           ` Ingo Molnar
  0 siblings, 2 replies; 48+ messages in thread
From: David Ahern @ 2013-09-09 14:11 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: Peter Zijlstra, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen

On 9/9/13 7:03 AM, Jiri Olsa wrote:
> my usage currently is to having this running during the day:
> (well whenever I remember to run it.. ;-) )
>
>    [jolsa@krava perf]$ sudo ./perf record -g -M 1m -a
>
> and checking report when the system or app get stuck
>
> with multiple files I can just easily (or automaticaly)
> remove old ones without restarting session

Aren't you losing potentially important events by doing that -- FORK, 
COMM, MMAP?

I have a flight recorder style command that address this problem 
(long-running/daemons) by processing task events and then stashing the 
sample events on a time-ordered list with chopping to maintain the time 
window.

David

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 14:11         ` David Ahern
@ 2013-09-09 14:31           ` Jiri Olsa
  2013-09-09 15:03             ` David Ahern
  2013-09-09 16:06           ` Ingo Molnar
  1 sibling, 1 reply; 48+ messages in thread
From: Jiri Olsa @ 2013-09-09 14:31 UTC (permalink / raw)
  To: David Ahern
  Cc: Peter Zijlstra, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen

On Mon, Sep 09, 2013 at 07:11:11AM -0700, David Ahern wrote:
> On 9/9/13 7:03 AM, Jiri Olsa wrote:
> >my usage currently is to having this running during the day:
> >(well whenever I remember to run it.. ;-) )
> >
> >   [jolsa@krava perf]$ sudo ./perf record -g -M 1m -a
> >
> >and checking report when the system or app get stuck
> >
> >with multiple files I can just easily (or automaticaly)
> >remove old ones without restarting session
> 
> Aren't you losing potentially important events by doing that --
> FORK, COMM, MMAP?

those are synthesized for each file via synthesize_record
function, see:

[PATCH 19/25] perf tools: Move synthesizing into single function

> 
> I have a flight recorder style command that address this problem
> (long-running/daemons) by processing task events and then stashing
> the sample events on a time-ordered list with chopping to maintain
> the time window.

so far I noticed there could be race among EXIT and remaining
SAMPLE events on another CPU mmap than EXIT event.. ending up
with EXIT being stored in the old file, while SAMPLEs will get
to the new one

I was thinking about some 'perf daemon' so I dont need to run that
manually.. seems similar to what you did

jirka

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 14:31           ` Jiri Olsa
@ 2013-09-09 15:03             ` David Ahern
  2013-09-14 18:32               ` David Ahern
  0 siblings, 1 reply; 48+ messages in thread
From: David Ahern @ 2013-09-09 15:03 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: Peter Zijlstra, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen

On 9/9/13 7:31 AM, Jiri Olsa wrote:
> On Mon, Sep 09, 2013 at 07:11:11AM -0700, David Ahern wrote:
>> On 9/9/13 7:03 AM, Jiri Olsa wrote:
>>> my usage currently is to having this running during the day:
>>> (well whenever I remember to run it.. ;-) )
>>>
>>>    [jolsa@krava perf]$ sudo ./perf record -g -M 1m -a
>>>
>>> and checking report when the system or app get stuck
>>>
>>> with multiple files I can just easily (or automaticaly)
>>> remove old ones without restarting session
>>
>> Aren't you losing potentially important events by doing that --
>> FORK, COMM, MMAP?
>
> those are synthesized for each file via synthesize_record
> function, see:
>
> [PATCH 19/25] perf tools: Move synthesizing into single function

Ok. haven't had time to look through your 2 large patch sets.

Seems like a lot of repetitive work on a loaded system. The overhead of 
the task events will dominate compared to the samples.

>
>>
>> I have a flight recorder style command that address this problem
>> (long-running/daemons) by processing task events and then stashing
>> the sample events on a time-ordered list with chopping to maintain
>> the time window.
>
> so far I noticed there could be race among EXIT and remaining
> SAMPLE events on another CPU mmap than EXIT event.. ending up
> with EXIT being stored in the old file, while SAMPLEs will get
> to the new one
>
> I was thinking about some 'perf daemon' so I dont need to run that
> manually.. seems similar to what you did

Right now I focus on scheduling events. This latest version of it can be 
easily recycled for other use cases. Some work would be needed to dump 
events to a file versus dumping processed information.

I am in San Jose this week. Not sure if I will have time to finish it to 
a point of pushing out patches, but maybe I can push to github in the 
next couple of days.

David

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 14:11         ` David Ahern
  2013-09-09 14:31           ` Jiri Olsa
@ 2013-09-09 16:06           ` Ingo Molnar
  2013-09-10 17:29             ` David Ahern
  1 sibling, 1 reply; 48+ messages in thread
From: Ingo Molnar @ 2013-09-09 16:06 UTC (permalink / raw)
  To: David Ahern
  Cc: Jiri Olsa, Peter Zijlstra, linux-kernel, Corey Ashford,
	Frederic Weisbecker, Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen


* David Ahern <dsahern@gmail.com> wrote:

> On 9/9/13 7:03 AM, Jiri Olsa wrote:
> >my usage currently is to having this running during the day:
> >(well whenever I remember to run it.. ;-) )
> >
> >   [jolsa@krava perf]$ sudo ./perf record -g -M 1m -a
> >
> >and checking report when the system or app get stuck
> >
> >with multiple files I can just easily (or automaticaly)
> >remove old ones without restarting session
> 
> Aren't you losing potentially important events by doing that -- FORK, 
> COMM, MMAP?

I suspect these could/should be tracked and emitted fully (in bulk) when a 
new data file is opened, so that each partial data file is fully 
consistent?

> I have a flight recorder style command that address this problem 
> (long-running/daemons) by processing task events and then stashing the 
> sample events on a time-ordered list with chopping to maintain the time 
> window.

Could this be used to emit currently relevant task context?

Btw., I also think it would be useful to have kernel support for that - 
the 'collections' stuff I talked about a good while ago: the kernel would 
work with user-space to iterate over all MMAPs and all running COMMs at 
the opening of a tracing session.

That way we could avoid racy access to /proc, we could make sure that all 
information that is emitted by FORK/COMM/MMAP is also emitted for the 
'bulk' data, etc.

Thanks,

	Ingo

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 11:17 ` Peter Zijlstra
  2013-09-09 11:36   ` Jiri Olsa
@ 2013-09-10  6:54   ` Adrian Hunter
  2013-09-10  9:15     ` Peter Zijlstra
  2013-09-10  8:57   ` Namhyung Kim
  2 siblings, 1 reply; 48+ messages in thread
From: Adrian Hunter @ 2013-09-10  6:54 UTC (permalink / raw)
  To: Peter Zijlstra
  Cc: Jiri Olsa, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

On 09/09/13 14:17, Peter Zijlstra wrote:
> On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
>> hi,
>> sending the support for multiple file storage. Initial
>> RFC is here:
>> http://marc.info/?l=linux-kernel&m=137408381902423&w=2
>>
>> v2 changes:
>>   - reworked perf mmap size setup to be able to get
>>     the mmap size value easily later
>>   - added perf.data read/write test for v2 and v3
>>     for both endianity
>>   - added record '-M time' support
> 
> So this 0/n post seems to have forgotten to list the rationale for doing
> all this.. 
> 
> The only reason I wanted this is so that each thread can write its own
> data. The current one file thing is an immense bottle-neck for big
> machines.

Do you need multiple files for that?  Why not just feed writes to a pool of
threads?


^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 11:17 ` Peter Zijlstra
  2013-09-09 11:36   ` Jiri Olsa
  2013-09-10  6:54   ` Adrian Hunter
@ 2013-09-10  8:57   ` Namhyung Kim
  2 siblings, 0 replies; 48+ messages in thread
From: Namhyung Kim @ 2013-09-10  8:57 UTC (permalink / raw)
  To: Peter Zijlstra
  Cc: Jiri Olsa, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Paul Mackerras, Arnaldo Carvalho de Melo,
	Andi Kleen, David Ahern

Hi Peter and Jiri,

On Mon, 9 Sep 2013 13:17:49 +0200, Peter Zijlstra wrote:
> On Sun, Sep 01, 2013 at 12:36:11PM +0200, Jiri Olsa wrote:
>> hi,
>> sending the support for multiple file storage. Initial
>> RFC is here:
>> http://marc.info/?l=linux-kernel&m=137408381902423&w=2
>> 
>> v2 changes:
>>   - reworked perf mmap size setup to be able to get
>>     the mmap size value easily later
>>   - added perf.data read/write test for v2 and v3
>>     for both endianity
>>   - added record '-M time' support
>
> So this 0/n post seems to have forgotten to list the rationale for doing
> all this.. 
>
> The only reason I wanted this is so that each thread can write its own
> data. The current one file thing is an immense bottle-neck for big
> machines.

Per-thread or per-cpu?  In my perf ftrace patchset, I used to per-cpu
data file for this reason.  Do you think per-thread approach is better
than per-cpu one?

Jiri, one of my colleagues asked me about the multiple file support
separated by time while ago.  At that time I just added --time-filter
option to perf report, but it'd better if perf record can support it.
(Unfortunately the patch seems to buried in the list).

Anyway, as Peter said, please consider per-thread or per-cpu multiple
file support with your series.  It will help further developments.

Thanks,
Namhyung

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-10  6:54   ` Adrian Hunter
@ 2013-09-10  9:15     ` Peter Zijlstra
  0 siblings, 0 replies; 48+ messages in thread
From: Peter Zijlstra @ 2013-09-10  9:15 UTC (permalink / raw)
  To: Adrian Hunter
  Cc: Jiri Olsa, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen, David Ahern

On Tue, Sep 10, 2013 at 09:54:38AM +0300, Adrian Hunter wrote:
> On 09/09/13 14:17, Peter Zijlstra wrote:

> > The only reason I wanted this is so that each thread can write its own
> > data. The current one file thing is an immense bottle-neck for big
> > machines.
> 
> Do you need multiple files for that?  Why not just feed writes to a pool of
> threads?

Not sure I understand what you mean there. Since we have a (or multiple)
event per cpu it doesn't make sense to read that data from another cpu
and have that write it to disk. That completely destroys the locality.

Instead the suggestion was to have a thread per cpu (bound) to empty out
the per cpu mmap buffer(s) and write them to disk.

Now the only way to coherently do that into a single file is to do some
streams implementation, which I suppose is possible. Pre-allocate
large-ish sections per thread and mark them as such, then let the thread
spool data into it, when full allocate a new section.

However this would result in allocation-block-size*nr_cpus minimal file
sizes, which wouldn't be a problem per-se since they can be sparse.

It will however pretty much mess up Jolsa's max-MBs per file thing and
it is of course slightly more complex than having a file per cpu/thread.
And is more likely to create kernel lock contention; the pagecache locks
are typically per inode, bouncing those around the machine isn't nice
either.

^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 16:06           ` Ingo Molnar
@ 2013-09-10 17:29             ` David Ahern
  0 siblings, 0 replies; 48+ messages in thread
From: David Ahern @ 2013-09-10 17:29 UTC (permalink / raw)
  To: Ingo Molnar
  Cc: Jiri Olsa, Peter Zijlstra, linux-kernel, Corey Ashford,
	Frederic Weisbecker, Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen

On 9/9/13 9:06 AM, Ingo Molnar wrote:
>> Aren't you losing potentially important events by doing that -- FORK,
>> COMM, MMAP?
>
> I suspect these could/should be tracked and emitted fully (in bulk) when a
> new data file is opened, so that each partial data file is fully
> consistent?

In my case I am not saving task events, but processing them. In Jiri's 
case where events are written to a file it should be possible to stash 
the unprocessed events on a list, when the exit happens move them to a 
dead threads list which can be cleaned up from time to time and then on 
file dump requests dump the task events followed by the sample events.

>
>> I have a flight recorder style command that address this problem
>> (long-running/daemons) by processing task events and then stashing the
>> sample events on a time-ordered list with chopping to maintain the time
>> window.
>
> Could this be used to emit currently relevant task context?

sure.

>
> Btw., I also think it would be useful to have kernel support for that -
> the 'collections' stuff I talked about a good while ago: the kernel would
> work with user-space to iterate over all MMAPs and all running COMMs at
> the opening of a tracing session.
>
> That way we could avoid racy access to /proc, we could make sure that all
> information that is emitted by FORK/COMM/MMAP is also emitted for the
> 'bulk' data, etc.

Walking the task list and emitting events would be better but wouldn't 
that be a performance hit holding the task lock (tasklist_lock?)? (I 
thought that one is needed when walking the task list.)

David


^ permalink raw reply	[flat|nested] 48+ messages in thread

* Re: [PATCHv2 00/25] perf tool: Add support for multiple data file storage
  2013-09-09 15:03             ` David Ahern
@ 2013-09-14 18:32               ` David Ahern
  0 siblings, 0 replies; 48+ messages in thread
From: David Ahern @ 2013-09-14 18:32 UTC (permalink / raw)
  To: Jiri Olsa
  Cc: Peter Zijlstra, linux-kernel, Corey Ashford, Frederic Weisbecker,
	Ingo Molnar, Namhyung Kim, Paul Mackerras,
	Arnaldo Carvalho de Melo, Andi Kleen

On 9/9/13 9:03 AM, David Ahern wrote:
>>> I have a flight recorder style command that address this problem
>>> (long-running/daemons) by processing task events and then stashing
>>> the sample events on a time-ordered list with chopping to maintain
>>> the time window.
>>
>> so far I noticed there could be race among EXIT and remaining
>> SAMPLE events on another CPU mmap than EXIT event.. ending up
>> with EXIT being stored in the old file, while SAMPLEs will get
>> to the new one
>>
>> I was thinking about some 'perf daemon' so I dont need to run that
>> manually.. seems similar to what you did
>
> Right now I focus on scheduling events. This latest version of it can be
> easily recycled for other use cases. Some work would be needed to dump
> events to a file versus dumping processed information.
>
> I am in San Jose this week. Not sure if I will have time to finish it to
> a point of pushing out patches, but maybe I can push to github in the
> next couple of days.

https://github.com/dsahern/linux/tree/perf-sched-timehist-3.11

Take a look at tools/perf/schedmon.c. Task events are processed and 
sample events are stashed on a list (daemon__process_sample). Could 
easily do something similar for mmap, comm, fork events and then on exit 
event flush events for terminated tasks. Then you will have both the 
task and sample events which can be dumped to a file for later processing.

David

^ permalink raw reply	[flat|nested] 48+ messages in thread

* [tip:perf/core] perf tools: Check mmap pages value early
  2013-09-01 10:36 ` [PATCH 01/25] perf tools: Check mmap pages value early Jiri Olsa
@ 2013-10-15  5:24   ` tip-bot for Jiri Olsa
  0 siblings, 0 replies; 48+ messages in thread
From: tip-bot for Jiri Olsa @ 2013-10-15  5:24 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: acme, linux-kernel, paulus, hpa, mingo, a.p.zijlstra, namhyung,
	jolsa, fweisbec, ak, dsahern, tglx, cjashfor, mingo

Commit-ID:  994a1f78b191df0c9d6caca3f3afb03e247aff26
Gitweb:     http://git.kernel.org/tip/994a1f78b191df0c9d6caca3f3afb03e247aff26
Author:     Jiri Olsa <jolsa@redhat.com>
AuthorDate: Sun, 1 Sep 2013 12:36:12 +0200
Committer:  Arnaldo Carvalho de Melo <acme@redhat.com>
CommitDate: Wed, 9 Oct 2013 11:24:10 -0300

perf tools: Check mmap pages value early

Move the check of the mmap_pages value to the options parsing time, so
we could rely on this value on other parts of code.

Related changes come in the next patches.

Also changes perf_evlist::mmap_len to proper size_t type.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: David Ahern <dsahern@gmail.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Link: http://lkml.kernel.org/r/1378031796-17892-2-git-send-email-jolsa@redhat.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
---
 tools/perf/builtin-kvm.c    |  5 +++--
 tools/perf/builtin-record.c |  9 +++------
 tools/perf/builtin-top.c    |  5 +++--
 tools/perf/builtin-trace.c  |  5 +++--
 tools/perf/util/evlist.c    | 46 ++++++++++++++++++++++++++++++++++++---------
 tools/perf/util/evlist.h    |  6 +++++-
 6 files changed, 54 insertions(+), 22 deletions(-)

diff --git a/tools/perf/builtin-kvm.c b/tools/perf/builtin-kvm.c
index 935d522..cfa0b79 100644
--- a/tools/perf/builtin-kvm.c
+++ b/tools/perf/builtin-kvm.c
@@ -1426,8 +1426,9 @@ static int kvm_events_live(struct perf_kvm_stat *kvm,
 	const struct option live_options[] = {
 		OPT_STRING('p', "pid", &kvm->opts.target.pid, "pid",
 			"record events on existing process id"),
-		OPT_UINTEGER('m', "mmap-pages", &kvm->opts.mmap_pages,
-			"number of mmap data pages"),
+		OPT_CALLBACK('m', "mmap-pages", &kvm->opts.mmap_pages, "pages",
+			"number of mmap data pages",
+			perf_evlist__parse_mmap_pages),
 		OPT_INCR('v', "verbose", &verbose,
 			"be more verbose (show counter open errors, etc)"),
 		OPT_BOOLEAN('a', "all-cpus", &kvm->opts.target.system_wide,
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 0aacd62..92ca541 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -233,10 +233,6 @@ try_again:
 			       "or try again with a smaller value of -m/--mmap_pages.\n"
 			       "(current value: %d)\n", opts->mmap_pages);
 			rc = -errno;
-		} else if (!is_power_of_2(opts->mmap_pages) &&
-			   (opts->mmap_pages != UINT_MAX)) {
-			pr_err("--mmap_pages/-m value must be a power of two.");
-			rc = -EINVAL;
 		} else {
 			pr_err("failed to mmap with %d (%s)\n", errno, strerror(errno));
 			rc = -errno;
@@ -854,8 +850,9 @@ const struct option record_options[] = {
 	OPT_BOOLEAN('i', "no-inherit", &record.opts.no_inherit,
 		    "child tasks do not inherit counters"),
 	OPT_UINTEGER('F', "freq", &record.opts.user_freq, "profile at this frequency"),
-	OPT_UINTEGER('m', "mmap-pages", &record.opts.mmap_pages,
-		     "number of mmap data pages"),
+	OPT_CALLBACK('m', "mmap-pages", &record.opts.mmap_pages, "pages",
+		     "number of mmap data pages",
+		     perf_evlist__parse_mmap_pages),
 	OPT_BOOLEAN(0, "group", &record.opts.group,
 		    "put the counters into a counter group"),
 	OPT_CALLBACK_DEFAULT('g', "call-graph", &record.opts,
diff --git a/tools/perf/builtin-top.c b/tools/perf/builtin-top.c
index b3e0229..e846695 100644
--- a/tools/perf/builtin-top.c
+++ b/tools/perf/builtin-top.c
@@ -1075,8 +1075,9 @@ int cmd_top(int argc, const char **argv, const char *prefix __maybe_unused)
 		   "file", "vmlinux pathname"),
 	OPT_BOOLEAN('K', "hide_kernel_symbols", &top.hide_kernel_symbols,
 		    "hide kernel symbols"),
-	OPT_UINTEGER('m', "mmap-pages", &opts->mmap_pages,
-		     "number of mmap data pages"),
+	OPT_CALLBACK('m', "mmap-pages", &opts->mmap_pages, "pages",
+		     "number of mmap data pages",
+		     perf_evlist__parse_mmap_pages),
 	OPT_INTEGER('r', "realtime", &top.realtime_prio,
 		    "collect data with this RT SCHED_FIFO priority"),
 	OPT_INTEGER('d', "delay", &top.delay_secs,
diff --git a/tools/perf/builtin-trace.c b/tools/perf/builtin-trace.c
index be65843..f3ddbb0 100644
--- a/tools/perf/builtin-trace.c
+++ b/tools/perf/builtin-trace.c
@@ -1528,8 +1528,9 @@ int cmd_trace(int argc, const char **argv, const char *prefix __maybe_unused)
 		    "list of cpus to monitor"),
 	OPT_BOOLEAN(0, "no-inherit", &trace.opts.no_inherit,
 		    "child tasks do not inherit counters"),
-	OPT_UINTEGER('m', "mmap-pages", &trace.opts.mmap_pages,
-		     "number of mmap data pages"),
+	OPT_CALLBACK('m', "mmap-pages", &trace.opts.mmap_pages, "pages",
+		     "number of mmap data pages",
+		     perf_evlist__parse_mmap_pages),
 	OPT_STRING('u', "uid", &trace.opts.target.uid_str, "user",
 		   "user to profile"),
 	OPT_CALLBACK(0, "duration", &trace, "float",
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index f9f77be..4283f49 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -18,6 +18,7 @@
 #include <unistd.h>
 
 #include "parse-events.h"
+#include "parse-options.h"
 
 #include <sys/mman.h>
 
@@ -672,6 +673,40 @@ out_unmap:
 	return -1;
 }
 
+static size_t perf_evlist__mmap_size(unsigned long pages)
+{
+	/* 512 kiB: default amount of unprivileged mlocked memory */
+	if (pages == UINT_MAX)
+		pages = (512 * 1024) / page_size;
+	else if (!is_power_of_2(pages))
+		return 0;
+
+	return (pages + 1) * page_size;
+}
+
+int perf_evlist__parse_mmap_pages(const struct option *opt, const char *str,
+				  int unset __maybe_unused)
+{
+	unsigned int pages, *mmap_pages = opt->value;
+	size_t size;
+	char *eptr;
+
+	pages = strtoul(str, &eptr, 10);
+	if (*eptr != '\0') {
+		pr_err("failed to parse --mmap_pages/-m value\n");
+		return -1;
+	}
+
+	size = perf_evlist__mmap_size(pages);
+	if (!size) {
+		pr_err("--mmap_pages/-m value must be a power of two.");
+		return -1;
+	}
+
+	*mmap_pages = pages;
+	return 0;
+}
+
 /** perf_evlist__mmap - Create per cpu maps to receive events
  *
  * @evlist - list of events
@@ -695,14 +730,6 @@ int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 	const struct thread_map *threads = evlist->threads;
 	int prot = PROT_READ | (overwrite ? 0 : PROT_WRITE), mask;
 
-        /* 512 kiB: default amount of unprivileged mlocked memory */
-        if (pages == UINT_MAX)
-                pages = (512 * 1024) / page_size;
-	else if (!is_power_of_2(pages))
-		return -EINVAL;
-
-	mask = pages * page_size - 1;
-
 	if (evlist->mmap == NULL && perf_evlist__alloc_mmap(evlist) < 0)
 		return -ENOMEM;
 
@@ -710,7 +737,8 @@ int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 		return -ENOMEM;
 
 	evlist->overwrite = overwrite;
-	evlist->mmap_len = (pages + 1) * page_size;
+	evlist->mmap_len = perf_evlist__mmap_size(pages);
+	mask = evlist->mmap_len - page_size - 1;
 
 	list_for_each_entry(evsel, &evlist->entries, node) {
 		if ((evsel->attr.read_format & PERF_FORMAT_ID) &&
diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h
index 880d713..4edb500 100644
--- a/tools/perf/util/evlist.h
+++ b/tools/perf/util/evlist.h
@@ -31,7 +31,7 @@ struct perf_evlist {
 	int		 nr_groups;
 	int		 nr_fds;
 	int		 nr_mmaps;
-	int		 mmap_len;
+	size_t		 mmap_len;
 	int		 id_pos;
 	int		 is_pos;
 	u64		 combined_sample_type;
@@ -103,6 +103,10 @@ int perf_evlist__prepare_workload(struct perf_evlist *evlist,
 				  bool want_signal);
 int perf_evlist__start_workload(struct perf_evlist *evlist);
 
+int perf_evlist__parse_mmap_pages(const struct option *opt,
+				  const char *str,
+				  int unset);
+
 int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 		      bool overwrite);
 void perf_evlist__munmap(struct perf_evlist *evlist);

^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [tip:perf/core] perf tools: Add possibility to specify mmap size
  2013-09-01 10:36 ` [PATCH 02/25] perf tools: Add possibility to specify mmap size Jiri Olsa
@ 2013-10-15  5:25   ` tip-bot for Jiri Olsa
  0 siblings, 0 replies; 48+ messages in thread
From: tip-bot for Jiri Olsa @ 2013-10-15  5:25 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: acme, linux-kernel, paulus, hpa, mingo, a.p.zijlstra, namhyung,
	jolsa, fweisbec, ak, dsahern, tglx, cjashfor, mingo

Commit-ID:  27050f530dc4fd88dc93d85c177e000efe970d12
Gitweb:     http://git.kernel.org/tip/27050f530dc4fd88dc93d85c177e000efe970d12
Author:     Jiri Olsa <jolsa@redhat.com>
AuthorDate: Sun, 1 Sep 2013 12:36:13 +0200
Committer:  Arnaldo Carvalho de Melo <acme@redhat.com>
CommitDate: Wed, 9 Oct 2013 11:24:20 -0300

perf tools: Add possibility to specify mmap size

Adding possibility to specify mmap size via -m/--mmap-pages
by appending unit size character (B/K/M/G) to the
number, like:
  $ perf record -m 8K ls
  $ perf record -m 2M ls

The size is rounded up appropriately to follow perf
mmap restrictions.

If no unit is specified the number provides pages as
of now, like:
  $ perf record -m 8 ls

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: David Ahern <dsahern@gmail.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Link: http://lkml.kernel.org/r/1378031796-17892-3-git-send-email-jolsa@redhat.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
---
 tools/perf/Documentation/perf-kvm.txt    |  4 +++-
 tools/perf/Documentation/perf-record.txt |  4 +++-
 tools/perf/Documentation/perf-top.txt    |  4 +++-
 tools/perf/Documentation/perf-trace.txt  |  4 +++-
 tools/perf/util/evlist.c                 | 32 ++++++++++++++++++++++++++------
 tools/perf/util/util.c                   | 25 +++++++++++++++++++++++++
 tools/perf/util/util.h                   | 14 ++++++++++++++
 7 files changed, 77 insertions(+), 10 deletions(-)

diff --git a/tools/perf/Documentation/perf-kvm.txt b/tools/perf/Documentation/perf-kvm.txt
index ac84db2..6a06cef 100644
--- a/tools/perf/Documentation/perf-kvm.txt
+++ b/tools/perf/Documentation/perf-kvm.txt
@@ -109,7 +109,9 @@ STAT LIVE OPTIONS
 
 -m::
 --mmap-pages=::
-    Number of mmap data pages. Must be a power of two.
+    Number of mmap data pages (must be a power of two) or size
+    specification with appended unit character - B/K/M/G. The
+    size is rounded up to have nearest pages power of two value.
 
 -a::
 --all-cpus::
diff --git a/tools/perf/Documentation/perf-record.txt b/tools/perf/Documentation/perf-record.txt
index f732eaa..f10ab63 100644
--- a/tools/perf/Documentation/perf-record.txt
+++ b/tools/perf/Documentation/perf-record.txt
@@ -87,7 +87,9 @@ OPTIONS
 
 -m::
 --mmap-pages=::
-	Number of mmap data pages. Must be a power of two.
+	Number of mmap data pages (must be a power of two) or size
+	specification with appended unit character - B/K/M/G. The
+	size is rounded up to have nearest pages power of two value.
 
 -g::
 --call-graph::
diff --git a/tools/perf/Documentation/perf-top.txt b/tools/perf/Documentation/perf-top.txt
index 6d70fbf..f65777c 100644
--- a/tools/perf/Documentation/perf-top.txt
+++ b/tools/perf/Documentation/perf-top.txt
@@ -68,7 +68,9 @@ Default is to monitor all CPUS.
 
 -m <pages>::
 --mmap-pages=<pages>::
-	Number of mmapped data pages.
+	Number of mmap data pages (must be a power of two) or size
+	specification with appended unit character - B/K/M/G. The
+	size is rounded up to have nearest pages power of two value.
 
 -p <pid>::
 --pid=<pid>::
diff --git a/tools/perf/Documentation/perf-trace.txt b/tools/perf/Documentation/perf-trace.txt
index 3777385..7f70d36 100644
--- a/tools/perf/Documentation/perf-trace.txt
+++ b/tools/perf/Documentation/perf-trace.txt
@@ -59,7 +59,9 @@ OPTIONS
 
 -m::
 --mmap-pages=::
-	Number of mmap data pages. Must be a power of two.
+	Number of mmap data pages (must be a power of two) or size
+	specification with appended unit character - B/K/M/G. The
+	size is rounded up to have nearest pages power of two value.
 
 -C::
 --cpu::
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index 4283f49..d21ab08 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -687,14 +687,33 @@ static size_t perf_evlist__mmap_size(unsigned long pages)
 int perf_evlist__parse_mmap_pages(const struct option *opt, const char *str,
 				  int unset __maybe_unused)
 {
-	unsigned int pages, *mmap_pages = opt->value;
+	unsigned int pages, val, *mmap_pages = opt->value;
 	size_t size;
-	char *eptr;
+	static struct parse_tag tags[] = {
+		{ .tag  = 'B', .mult = 1       },
+		{ .tag  = 'K', .mult = 1 << 10 },
+		{ .tag  = 'M', .mult = 1 << 20 },
+		{ .tag  = 'G', .mult = 1 << 30 },
+		{ .tag  = 0 },
+	};
 
-	pages = strtoul(str, &eptr, 10);
-	if (*eptr != '\0') {
-		pr_err("failed to parse --mmap_pages/-m value\n");
-		return -1;
+	val = parse_tag_value(str, tags);
+	if (val != (unsigned int) -1) {
+		/* we got file size value */
+		pages = PERF_ALIGN(val, page_size) / page_size;
+		if (!is_power_of_2(pages)) {
+			pages = next_pow2(pages);
+			pr_info("rounding mmap pages size to %u (%u pages)\n",
+				pages * page_size, pages);
+		}
+	} else {
+		/* we got pages count value */
+		char *eptr;
+		pages = strtoul(str, &eptr, 10);
+		if (*eptr != '\0') {
+			pr_err("failed to parse --mmap_pages/-m value\n");
+			return -1;
+		}
 	}
 
 	size = perf_evlist__mmap_size(pages);
@@ -738,6 +757,7 @@ int perf_evlist__mmap(struct perf_evlist *evlist, unsigned int pages,
 
 	evlist->overwrite = overwrite;
 	evlist->mmap_len = perf_evlist__mmap_size(pages);
+	pr_debug("mmap size %luB\n", evlist->mmap_len);
 	mask = evlist->mmap_len - page_size - 1;
 
 	list_for_each_entry(evsel, &evlist->entries, node) {
diff --git a/tools/perf/util/util.c b/tools/perf/util/util.c
index ccfdeb6..ab71d62 100644
--- a/tools/perf/util/util.c
+++ b/tools/perf/util/util.c
@@ -361,3 +361,28 @@ int parse_nsec_time(const char *str, u64 *ptime)
 	*ptime = time_sec * NSEC_PER_SEC + time_nsec;
 	return 0;
 }
+
+unsigned long parse_tag_value(const char *str, struct parse_tag *tags)
+{
+	struct parse_tag *i = tags;
+
+	while (i->tag) {
+		char *s;
+
+		s = strchr(str, i->tag);
+		if (s) {
+			unsigned long int value;
+			char *endptr;
+
+			value = strtoul(str, &endptr, 10);
+			if (s != endptr)
+				break;
+
+			value *= i->mult;
+			return value;
+		}
+		i++;
+	}
+
+	return (unsigned long) -1;
+}
diff --git a/tools/perf/util/util.h b/tools/perf/util/util.h
index a535359..c29ecaa 100644
--- a/tools/perf/util/util.h
+++ b/tools/perf/util/util.h
@@ -270,6 +270,13 @@ bool is_power_of_2(unsigned long n)
 	return (n != 0 && ((n & (n - 1)) == 0));
 }
 
+static inline unsigned next_pow2(unsigned x)
+{
+	if (!x)
+		return 1;
+	return 1ULL << (32 - __builtin_clz(x - 1));
+}
+
 size_t hex_width(u64 v);
 int hex2u64(const char *ptr, u64 *val);
 
@@ -281,4 +288,11 @@ void dump_stack(void);
 extern unsigned int page_size;
 
 void get_term_dimensions(struct winsize *ws);
+
+struct parse_tag {
+	char tag;
+	int mult;
+};
+
+unsigned long parse_tag_value(const char *str, struct parse_tag *tags);
 #endif /* GIT_COMPAT_UTIL_H */

^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [tip:perf/core] perf evlist: Introduce perf_evlist__new_default function
  2013-09-01 10:36 ` [PATCH 03/25] perf tools: Introduce perf_evlist__new_default function Jiri Olsa
@ 2013-10-15  5:25   ` tip-bot for Jiri Olsa
  0 siblings, 0 replies; 48+ messages in thread
From: tip-bot for Jiri Olsa @ 2013-10-15  5:25 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: acme, linux-kernel, paulus, hpa, mingo, a.p.zijlstra, namhyung,
	jolsa, fweisbec, ak, dsahern, tglx, cjashfor, mingo

Commit-ID:  b22d54b09a5448d3706929c6f0eae36429f4ec5d
Gitweb:     http://git.kernel.org/tip/b22d54b09a5448d3706929c6f0eae36429f4ec5d
Author:     Jiri Olsa <jolsa@redhat.com>
AuthorDate: Sun, 1 Sep 2013 12:36:14 +0200
Committer:  Arnaldo Carvalho de Melo <acme@redhat.com>
CommitDate: Wed, 9 Oct 2013 11:24:34 -0300

perf evlist: Introduce perf_evlist__new_default function

Adding new common function to create evlist with default event. It
spares some code lines in automated tests.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: David Ahern <dsahern@gmail.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Link: http://lkml.kernel.org/r/1378031796-17892-4-git-send-email-jolsa@redhat.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
---
 tools/perf/tests/perf-record.c | 12 +-----------
 tools/perf/tests/task-exit.c   | 14 ++------------
 tools/perf/util/evlist.c       | 12 ++++++++++++
 tools/perf/util/evlist.h       |  1 +
 4 files changed, 16 insertions(+), 23 deletions(-)

diff --git a/tools/perf/tests/perf-record.c b/tools/perf/tests/perf-record.c
index b8a7056..82ac715 100644
--- a/tools/perf/tests/perf-record.c
+++ b/tools/perf/tests/perf-record.c
@@ -45,7 +45,7 @@ int test__PERF_RECORD(void)
 	};
 	cpu_set_t cpu_mask;
 	size_t cpu_mask_size = sizeof(cpu_mask);
-	struct perf_evlist *evlist = perf_evlist__new();
+	struct perf_evlist *evlist = perf_evlist__new_default();
 	struct perf_evsel *evsel;
 	struct perf_sample sample;
 	const char *cmd = "sleep";
@@ -66,16 +66,6 @@ int test__PERF_RECORD(void)
 	}
 
 	/*
-	 * We need at least one evsel in the evlist, use the default
-	 * one: "cycles".
-	 */
-	err = perf_evlist__add_default(evlist);
-	if (err < 0) {
-		pr_debug("Not enough memory to create evsel\n");
-		goto out_delete_evlist;
-	}
-
-	/*
 	 * Create maps of threads and cpus to monitor. In this case
 	 * we start with all threads and cpus (-1, -1) but then in
 	 * perf_evlist__prepare_workload we'll fill in the only thread
diff --git a/tools/perf/tests/task-exit.c b/tools/perf/tests/task-exit.c
index 28fe589..b07f8a1 100644
--- a/tools/perf/tests/task-exit.c
+++ b/tools/perf/tests/task-exit.c
@@ -37,20 +37,11 @@ int test__task_exit(void)
 	signal(SIGCHLD, sig_handler);
 	signal(SIGUSR1, sig_handler);
 
-	evlist = perf_evlist__new();
+	evlist = perf_evlist__new_default();
 	if (evlist == NULL) {
-		pr_debug("perf_evlist__new\n");
+		pr_debug("perf_evlist__new_default\n");
 		return -1;
 	}
-	/*
-	 * We need at least one evsel in the evlist, use the default
-	 * one: "cycles".
-	 */
-	err = perf_evlist__add_default(evlist);
-	if (err < 0) {
-		pr_debug("Not enough memory to create evsel\n");
-		goto out_free_evlist;
-	}
 
 	/*
 	 * Create maps of threads and cpus to monitor. In this case
@@ -117,7 +108,6 @@ out_close_evlist:
 	perf_evlist__close(evlist);
 out_delete_maps:
 	perf_evlist__delete_maps(evlist);
-out_free_evlist:
 	perf_evlist__delete(evlist);
 	return err;
 }
diff --git a/tools/perf/util/evlist.c b/tools/perf/util/evlist.c
index d21ab08..f0d71a9 100644
--- a/tools/perf/util/evlist.c
+++ b/tools/perf/util/evlist.c
@@ -50,6 +50,18 @@ struct perf_evlist *perf_evlist__new(void)
 	return evlist;
 }
 
+struct perf_evlist *perf_evlist__new_default(void)
+{
+	struct perf_evlist *evlist = perf_evlist__new();
+
+	if (evlist && perf_evlist__add_default(evlist)) {
+		perf_evlist__delete(evlist);
+		evlist = NULL;
+	}
+
+	return evlist;
+}
+
 /**
  * perf_evlist__set_id_pos - set the positions of event ids.
  * @evlist: selected event list
diff --git a/tools/perf/util/evlist.h b/tools/perf/util/evlist.h
index 4edb500..871b55a 100644
--- a/tools/perf/util/evlist.h
+++ b/tools/perf/util/evlist.h
@@ -53,6 +53,7 @@ struct perf_evsel_str_handler {
 };
 
 struct perf_evlist *perf_evlist__new(void);
+struct perf_evlist *perf_evlist__new_default(void);
 void perf_evlist__init(struct perf_evlist *evlist, struct cpu_map *cpus,
 		       struct thread_map *threads);
 void perf_evlist__exit(struct perf_evlist *evlist);

^ permalink raw reply related	[flat|nested] 48+ messages in thread

* [tip:perf/core] perf tools: Adding throttle event data struct support
  2013-09-01 10:36 ` [PATCH 04/25] perf tools: Adding throttle event data struct support Jiri Olsa
@ 2013-10-15  5:25   ` tip-bot for Jiri Olsa
  0 siblings, 0 replies; 48+ messages in thread
From: tip-bot for Jiri Olsa @ 2013-10-15  5:25 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: acme, linux-kernel, paulus, hpa, mingo, a.p.zijlstra, namhyung,
	jolsa, fweisbec, ak, dsahern, tglx, cjashfor, mingo

Commit-ID:  dd96c46b5c765a779d8c35cc7d1df7515b4c7baf
Gitweb:     http://git.kernel.org/tip/dd96c46b5c765a779d8c35cc7d1df7515b4c7baf
Author:     Jiri Olsa <jolsa@redhat.com>
AuthorDate: Sun, 1 Sep 2013 12:36:15 +0200
Committer:  Arnaldo Carvalho de Melo <acme@redhat.com>
CommitDate: Wed, 9 Oct 2013 11:39:18 -0300

perf tools: Adding throttle event data struct support

Moving 'struct throttle_event' out of python code and making it global
as any other event.

There's no usage of throttling events in any perf commands so far
(besides python support), but we'll need this event data backup for
upcoming test.

Signed-off-by: Jiri Olsa <jolsa@redhat.com>
Cc: Andi Kleen <ak@linux.intel.com>
Cc: Corey Ashford <cjashfor@linux.vnet.ibm.com>
Cc: David Ahern <dsahern@gmail.com>
Cc: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: Namhyung Kim <namhyung@kernel.org>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
Link: http://lkml.kernel.org/r/1378031796-17892-5-git-send-email-jolsa@redhat.com
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
---
 tools/perf/util/event.h   |  7 +++++++
 tools/perf/util/python.c  |  7 -------
 tools/perf/util/session.c | 13 +++++++++++++
 3 files changed, 20 insertions(+), 7 deletions(-)

diff --git a/tools/perf/util/event.h b/tools/perf/util/event.h
index 17d9e16..9b7d4d3 100644
--- a/tools/perf/util/event.h
+++ b/tools/perf/util/event.h
@@ -61,6 +61,12 @@ struct read_event {
 	u64 id;
 };
 
+struct throttle_event {
+	struct perf_event_header header;
+	u64 time;
+	u64 id;
+	u64 stream_id;
+};
 
 #define PERF_SAMPLE_MASK				\
 	(PERF_SAMPLE_IP | PERF_SAMPLE_TID |		\
@@ -178,6 +184,7 @@ union perf_event {
 	struct fork_event		fork;
 	struct lost_event		lost;
 	struct read_event		read;
+	struct throttle_event		throttle;
 	struct sample_event		sample;
 	struct attr_event		attr;
 	struct event_type_event		event_type;
diff --git a/tools/perf/util/python.c b/tools/perf/util/python.c
index a24ce0a..06efd02 100644
--- a/tools/perf/util/python.c
+++ b/tools/perf/util/python.c
@@ -33,13 +33,6 @@ int eprintf(int level, const char *fmt, ...)
 # define PyVarObject_HEAD_INIT(type, size) PyObject_HEAD_INIT(type) size,
 #endif
 
-struct throttle_event {
-	struct perf_event_header header;
-	u64			 time;
-	u64			 id;
-	u64			 stream_id;
-};
-
 PyMODINIT_FUNC initperf(void);
 
 #define member_def(type, member, ptype, help) \
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c
index b97f468..d1e4495 100644
--- a/tools/perf/util/session.c
+++ b/tools/perf/util/session.c
@@ -397,6 +397,17 @@ static void perf_event__read_swap(union perf_event *event, bool sample_id_all)
 		swap_sample_id_all(event, &event->read + 1);
 }
 
+static void perf_event__throttle_swap(union perf_event *event,
+				      bool sample_id_all)
+{
+	event->throttle.time	  = bswap_64(event->throttle.time);
+	event->throttle.id	  = bswap_64(event->throttle.id);
+	event->throttle.stream_id = bswap_64(event->throttle.stream_id);
+
+	if (sample_id_all)
+		swap_sample_id_all(event, &event->throttle + 1);
+}
+
 static u8 revbyte(u8 b)
 {
 	int rev = (b >> 4) | ((b & 0xf) << 4);
@@ -482,6 +493,8 @@ static perf_event__swap_op perf_event__swap_ops[] = {
 	[PERF_RECORD_EXIT]		  = perf_event__task_swap,
 	[PERF_RECORD_LOST]		  = perf_event__all64_swap,
 	[PERF_RECORD_READ]		  = perf_event__read_swap,
+	[PERF_RECORD_THROTTLE]		  = perf_event__throttle_swap,
+	[PERF_RECORD_UNTHROTTLE]	  = perf_event__throttle_swap,
 	[PERF_RECORD_SAMPLE]		  = perf_event__all64_swap,
 	[PERF_RECORD_HEADER_ATTR]	  = perf_event__hdr_attr_swap,
 	[PERF_RECORD_HEADER_EVENT_TYPE]	  = perf_event__event_type_swap,

^ permalink raw reply related	[flat|nested] 48+ messages in thread

end of thread, other threads:[~2013-10-15  5:45 UTC | newest]

Thread overview: 48+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2013-09-01 10:36 [PATCHv2 00/25] perf tool: Add support for multiple data file storage Jiri Olsa
2013-09-01 10:36 ` [PATCH 01/25] perf tools: Check mmap pages value early Jiri Olsa
2013-10-15  5:24   ` [tip:perf/core] " tip-bot for Jiri Olsa
2013-09-01 10:36 ` [PATCH 02/25] perf tools: Add possibility to specify mmap size Jiri Olsa
2013-10-15  5:25   ` [tip:perf/core] " tip-bot for Jiri Olsa
2013-09-01 10:36 ` [PATCH 03/25] perf tools: Introduce perf_evlist__new_default function Jiri Olsa
2013-10-15  5:25   ` [tip:perf/core] perf evlist: " tip-bot for Jiri Olsa
2013-09-01 10:36 ` [PATCH 04/25] perf tools: Adding throttle event data struct support Jiri Olsa
2013-10-15  5:25   ` [tip:perf/core] " tip-bot for Jiri Olsa
2013-09-01 10:36 ` [PATCH 05/25] perf tests: Add simple session read/write test Jiri Olsa
2013-09-01 10:36 ` [PATCH 06/25] perf tests: Add session reading test for little endian perf data Jiri Olsa
2013-09-01 10:36 ` [PATCH 07/25] perf tests: Add session reading test for big " Jiri Olsa
2013-09-01 10:36 ` [PATCH 08/25] perf doc: Add perf data file documentation Jiri Olsa
2013-09-01 10:36 ` [PATCH 09/25] perf tools: Introduce perf data file version CHECK macro Jiri Olsa
2013-09-01 10:36 ` [PATCH 10/25] perf tools: Introduce swap_features function Jiri Olsa
2013-09-01 10:36 ` [PATCH 11/25] perf tools: Introduce swap_header function Jiri Olsa
2013-09-01 10:36 ` [PATCH 12/25] perf tools: Separate version 2 specific perf data header bits Jiri Olsa
2013-09-01 10:36 ` [PATCH 13/25] perf tools: Using evlist as a holder for event_desc feature Jiri Olsa
2013-09-01 10:36 ` [PATCH 14/25] perf tools: Introduce perf.data version 3 format Jiri Olsa
2013-09-01 10:36 ` [PATCH 15/25] perf tools: Add perf data version 3 header swap Jiri Olsa
2013-09-01 10:36 ` [PATCH 16/25] perf tools: Add perf data version 3 header read Jiri Olsa
2013-09-01 10:36 ` [PATCH 17/25] perf tools: Add perf.data version 3 header write Jiri Olsa
2013-09-01 10:36 ` [PATCH 18/25] perf tools: Get rid of post_processing_offset in record command Jiri Olsa
2013-09-01 10:36 ` [PATCH 19/25] perf tools: Move synthesizing into single function Jiri Olsa
2013-09-01 10:36 ` [PATCH 20/25] perf tools: Add perf_data_file__open interface to data object Jiri Olsa
2013-09-01 10:36 ` [PATCH 21/25] perf tools: Separating data file properties from session Jiri Olsa
2013-09-01 10:36 ` [PATCH 22/25] perf tests: Add session reading test for little endian perf data v3 Jiri Olsa
2013-09-01 10:36 ` [PATCH 23/25] perf tests: Add session reading test for big " Jiri Olsa
2013-09-01 10:36 ` [PATCH 24/25] perf tools: Add multi file '-M' option for record command Jiri Olsa
2013-09-02  7:52   ` Adrian Hunter
2013-09-02  8:37     ` Jiri Olsa
2013-09-02  9:11       ` Adrian Hunter
2013-09-02  9:40         ` Jiri Olsa
2013-09-01 10:36 ` [PATCH 25/25] perf tools: Have the process properly sythesized in subsequent data files Jiri Olsa
2013-09-02  2:42 ` [PATCHv2 00/25] perf tool: Add support for multiple data file storage Andi Kleen
2013-09-09 11:17 ` Peter Zijlstra
2013-09-09 11:36   ` Jiri Olsa
2013-09-09 11:55     ` Peter Zijlstra
2013-09-09 14:03       ` Jiri Olsa
2013-09-09 14:11         ` David Ahern
2013-09-09 14:31           ` Jiri Olsa
2013-09-09 15:03             ` David Ahern
2013-09-14 18:32               ` David Ahern
2013-09-09 16:06           ` Ingo Molnar
2013-09-10 17:29             ` David Ahern
2013-09-10  6:54   ` Adrian Hunter
2013-09-10  9:15     ` Peter Zijlstra
2013-09-10  8:57   ` Namhyung Kim

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).