* [PATCH] perf tools: Add a new generic section in perf.data
@ 2009-10-15 21:10 Frederic Weisbecker
2009-10-16 7:10 ` Ingo Molnar
0 siblings, 1 reply; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-15 21:10 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Frederic Weisbecker, Peter Zijlstra,
Arnaldo Carvalho de Melo, Mike Galbraith, Paul Mackerras,
Steven Rostedt
Add a new generic section into the perf.data file. This section simply
stands as a set of subsections that can be added once it is needed.
This section is versioned so that it's flexible enough to carry a
backward and forward compatibility with other versions of this generic
section.
For now it only handles the trace_info subsection.
This whole change is backward compatible with .32 perf.data but
not with the current development version for .33
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
---
| 104 ++++++++++++++++++++++++++++++++--------------
| 4 +-
2 files changed, 75 insertions(+), 33 deletions(-)
--git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 9aae360..d11c467 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -64,8 +64,8 @@ struct perf_header *perf_header__new(void)
self->data_offset = 0;
self->data_size = 0;
- self->trace_info_offset = 0;
- self->trace_info_size = 0;
+ self->adds_offset = 0;
+ self->adds_size = 0;
return self;
}
@@ -142,6 +142,15 @@ struct perf_file_attr {
struct perf_file_section ids;
};
+/*
+ * Version 0: contains trace_info section only
+ */
+struct perf_file_additionals {
+ u64 version;
+ struct perf_file_section trace_info;
+};
+
+
struct perf_file_header {
u64 magic;
u64 size;
@@ -149,7 +158,7 @@ struct perf_file_header {
struct perf_file_section attrs;
struct perf_file_section data;
struct perf_file_section event_types;
- struct perf_file_section trace_info;
+ struct perf_file_section adds;
};
static int trace_info;
@@ -172,6 +181,34 @@ static void do_write(int fd, void *buf, size_t size)
}
}
+static void perf_header__adds_write(struct perf_header *self, int fd)
+{
+ struct perf_file_additionals adds = {
+ .version = 0,
+ .trace_info = {
+ .offset = 0,
+ .size = 0,
+ },
+ };
+
+ self->adds_offset = lseek(fd, 0, SEEK_CUR);
+ lseek(fd, sizeof(adds), SEEK_CUR);
+
+ if (trace_info) {
+ adds.trace_info.offset = lseek(fd, 0, SEEK_CUR);
+ read_tracing_data(fd, attrs, nr_counters);
+ adds.trace_info.size = lseek(fd, 0, SEEK_CUR) -
+ adds.trace_info.offset;
+ }
+
+ self->adds_size = lseek(fd, 0, SEEK_CUR) - self->adds_offset;
+
+ /* Write adds headers */
+ lseek(fd, self->adds_offset, SEEK_SET);
+ do_write(fd, &adds, sizeof(adds));
+ lseek(fd, self->adds_offset + self->adds_size, SEEK_SET);
+};
+
void perf_header__write(struct perf_header *self, int fd)
{
struct perf_file_header f_header;
@@ -210,23 +247,7 @@ void perf_header__write(struct perf_header *self, int fd)
if (events)
do_write(fd, events, self->event_size);
- if (trace_info) {
- static int trace_info_written;
-
- /*
- * Write it only once
- */
- if (!trace_info_written) {
- self->trace_info_offset = lseek(fd, 0, SEEK_CUR);
- read_tracing_data(fd, attrs, nr_counters);
- self->trace_info_size = lseek(fd, 0, SEEK_CUR) -
- self->trace_info_offset;
- trace_info_written = 1;
- } else {
- lseek(fd, self->trace_info_offset +
- self->trace_info_size, SEEK_SET);
- }
- }
+ perf_header__adds_write(self, fd);
self->data_offset = lseek(fd, 0, SEEK_CUR);
@@ -246,9 +267,9 @@ void perf_header__write(struct perf_header *self, int fd)
.offset = self->event_offset,
.size = self->event_size,
},
- .trace_info = {
- .offset = self->trace_info_offset,
- .size = self->trace_info_size,
+ .adds = {
+ .offset = self->adds_offset,
+ .size = self->adds_size,
},
};
@@ -274,6 +295,30 @@ static void do_read(int fd, void *buf, size_t size)
}
}
+/*
+ * Version 0: only need to read trace info
+ */
+static void perf_header__adds_read(struct perf_header *self, int fd)
+{
+ struct perf_file_additionals adds;
+
+ /* Previous versions don't have adds section */
+ if (!self->adds_size)
+ return;
+
+ lseek(fd, self->adds_offset, SEEK_SET);
+ do_read(fd, &adds, sizeof(adds));
+
+ /*
+ * Every adds section versions need to handle at least
+ * the trace info
+ */
+ if (adds.trace_info.size) {
+ lseek(fd, adds.trace_info.offset, SEEK_SET);
+ trace_report(fd);
+ }
+};
+
struct perf_header *perf_header__read(int fd)
{
struct perf_header *self = perf_header__new();
@@ -292,8 +337,8 @@ struct perf_header *perf_header__read(int fd)
if (f_header.size != sizeof(f_header)) {
/* Support the previous format */
- if (f_header.size == offsetof(typeof(f_header), trace_info))
- f_header.trace_info.size = 0;
+ if (f_header.size == offsetof(typeof(f_header), adds))
+ f_header.adds.size = 0;
else
die("incompatible file format");
}
@@ -330,13 +375,10 @@ struct perf_header *perf_header__read(int fd)
event_count = f_header.event_types.size / sizeof(struct perf_trace_event_type);
}
- self->trace_info_offset = f_header.trace_info.offset;
- self->trace_info_size = f_header.trace_info.size;
+ self->adds_offset = f_header.adds.offset;
+ self->adds_size = f_header.adds.size;
- if (self->trace_info_size) {
- lseek(fd, self->trace_info_offset, SEEK_SET);
- trace_report(fd);
- }
+ perf_header__adds_read(self, fd);
self->event_offset = f_header.event_types.offset;
self->event_size = f_header.event_types.size;
--git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 30aee51..8198022 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -21,8 +21,8 @@ struct perf_header {
u64 data_size;
u64 event_offset;
u64 event_size;
- u64 trace_info_offset;
- u64 trace_info_size;
+ u64 adds_offset;
+ u64 adds_size;
};
struct perf_header *perf_header__read(int fd);
--
1.6.2.3
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH] perf tools: Add a new generic section in perf.data
2009-10-15 21:10 [PATCH] perf tools: Add a new generic section in perf.data Frederic Weisbecker
@ 2009-10-16 7:10 ` Ingo Molnar
2009-10-16 7:33 ` Frederic Weisbecker
0 siblings, 1 reply; 13+ messages in thread
From: Ingo Molnar @ 2009-10-16 7:10 UTC (permalink / raw)
To: Frederic Weisbecker
Cc: LKML, Peter Zijlstra, Arnaldo Carvalho de Melo, Mike Galbraith,
Paul Mackerras, Steven Rostedt
* Frederic Weisbecker <fweisbec@gmail.com> wrote:
> +/*
> + * Version 0: contains trace_info section only
> + */
> +struct perf_file_additionals {
> + u64 version;
> + struct perf_file_section trace_info;
> +};
i dont disagree with the change - but it would be even nicer to simply
define a features bitmask, instead of a flat version - and add the
trace_info section as a feature.
That way it's all a lot more manageable: we dont know about versions per
se, we know about features. Individual features could be developed (and
backported) in a distributed way - without having to worry about a flat
version model.
So i'd suggest something like a bitmask in the perf.data file header:
DECLARE_BITMAP(features, 256);
Plus every perf version knows about the features it supports:
DECLARE_BITMAP(features_supported, 256);
The compatibility rule is: perf only touches attributes that belong to
features it knows about.
Ingo
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH] perf tools: Add a new generic section in perf.data
2009-10-16 7:10 ` Ingo Molnar
@ 2009-10-16 7:33 ` Frederic Weisbecker
2009-10-16 7:42 ` Ingo Molnar
0 siblings, 1 reply; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-16 7:33 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Peter Zijlstra, Arnaldo Carvalho de Melo, Mike Galbraith,
Paul Mackerras, Steven Rostedt
On Fri, Oct 16, 2009 at 09:10:46AM +0200, Ingo Molnar wrote:
>
> * Frederic Weisbecker <fweisbec@gmail.com> wrote:
>
> > +/*
> > + * Version 0: contains trace_info section only
> > + */
> > +struct perf_file_additionals {
> > + u64 version;
> > + struct perf_file_section trace_info;
> > +};
>
> i dont disagree with the change - but it would be even nicer to simply
> define a features bitmask, instead of a flat version - and add the
> trace_info section as a feature.
>
> That way it's all a lot more manageable: we dont know about versions per
> se, we know about features. Individual features could be developed (and
> backported) in a distributed way - without having to worry about a flat
> version model.
>
> So i'd suggest something like a bitmask in the perf.data file header:
>
> DECLARE_BITMAP(features, 256);
>
> Plus every perf version knows about the features it supports:
>
> DECLARE_BITMAP(features_supported, 256);
>
> The compatibility rule is: perf only touches attributes that belong to
> features it knows about.
>
> Ingo
Yeah, I've thought about that too but feared about the limitation
of bitweight(u64), although it's probably enough, we never know.
That said I can take a bunch of four u64 to draw this bitmap and 256
features is enough.
Indeed that's way much better as a bitmap. Will do that instead.
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH] perf tools: Add a new generic section in perf.data
2009-10-16 7:33 ` Frederic Weisbecker
@ 2009-10-16 7:42 ` Ingo Molnar
2009-10-17 15:12 ` [PATCH 1/2] perf tools: Use kernel bitmap library Frederic Weisbecker
` (2 more replies)
0 siblings, 3 replies; 13+ messages in thread
From: Ingo Molnar @ 2009-10-16 7:42 UTC (permalink / raw)
To: Frederic Weisbecker
Cc: LKML, Peter Zijlstra, Arnaldo Carvalho de Melo, Mike Galbraith,
Paul Mackerras, Steven Rostedt
* Frederic Weisbecker <fweisbec@gmail.com> wrote:
> On Fri, Oct 16, 2009 at 09:10:46AM +0200, Ingo Molnar wrote:
> >
> > * Frederic Weisbecker <fweisbec@gmail.com> wrote:
> >
> > > +/*
> > > + * Version 0: contains trace_info section only
> > > + */
> > > +struct perf_file_additionals {
> > > + u64 version;
> > > + struct perf_file_section trace_info;
> > > +};
> >
> > i dont disagree with the change - but it would be even nicer to simply
> > define a features bitmask, instead of a flat version - and add the
> > trace_info section as a feature.
> >
> > That way it's all a lot more manageable: we dont know about versions per
> > se, we know about features. Individual features could be developed (and
> > backported) in a distributed way - without having to worry about a flat
> > version model.
> >
> > So i'd suggest something like a bitmask in the perf.data file header:
> >
> > DECLARE_BITMAP(features, 256);
> >
> > Plus every perf version knows about the features it supports:
> >
> > DECLARE_BITMAP(features_supported, 256);
> >
> > The compatibility rule is: perf only touches attributes that belong to
> > features it knows about.
> >
> > Ingo
>
>
> Yeah, I've thought about that too but feared about the limitation of
> bitweight(u64), although it's probably enough, we never know. That
> said I can take a bunch of four u64 to draw this bitmap and 256
> features is enough.
>
> Indeed that's way much better as a bitmap. Will do that instead.
Yeah, but please reuse linux/bitmap.h instead of some open-coded array
of 4x u64's.
Ingo
^ permalink raw reply [flat|nested] 13+ messages in thread
* [PATCH 1/2] perf tools: Use kernel bitmap library
2009-10-16 7:42 ` Ingo Molnar
@ 2009-10-17 15:12 ` Frederic Weisbecker
2009-10-19 7:55 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
2009-10-17 15:12 ` [PATCH 2/2] perf tools: Introduce bitmask'ed additional headers Frederic Weisbecker
2009-10-17 15:57 ` [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array Frederic Weisbecker
2 siblings, 1 reply; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-17 15:12 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Frederic Weisbecker, Peter Zijlstra,
Arnaldo Carvalho de Melo, Mike Galbraith, Paul Mackerras,
Steven Rostedt
Use the kernel bitmap library for internal perf tools uses.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
---
tools/perf/Makefile | 16 ++++++++
tools/perf/builtin-record.c | 3 --
tools/perf/builtin-sched.c | 2 -
tools/perf/util/include/asm/bitops.h | 6 +++
tools/perf/util/include/asm/byteorder.h | 2 +
tools/perf/util/include/asm/swab.h | 1 +
tools/perf/util/include/asm/types.h | 17 +++++++++
tools/perf/util/include/asm/uaccess.h | 14 +++++++
tools/perf/util/include/linux/bitmap.h | 2 +
tools/perf/util/include/linux/bitops.h | 27 ++++++++++++++
tools/perf/util/include/linux/compiler.h | 10 +++++
tools/perf/util/include/linux/ctype.h | 1 +
tools/perf/util/include/linux/kernel.h | 59 ++++++++++++++++++++++++++++++
tools/perf/util/include/linux/types.h | 1 +
14 files changed, 156 insertions(+), 5 deletions(-)
create mode 100644 tools/perf/util/include/asm/bitops.h
create mode 100644 tools/perf/util/include/asm/byteorder.h
create mode 100644 tools/perf/util/include/asm/swab.h
create mode 100644 tools/perf/util/include/asm/types.h
create mode 100644 tools/perf/util/include/asm/uaccess.h
create mode 100644 tools/perf/util/include/linux/bitmap.h
create mode 100644 tools/perf/util/include/linux/bitops.h
create mode 100644 tools/perf/util/include/linux/compiler.h
create mode 100644 tools/perf/util/include/linux/ctype.h
create mode 100644 tools/perf/util/include/linux/types.h
diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index 106c150..2400e50 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -363,6 +363,9 @@ LIB_OBJS += util/parse-options.o
LIB_OBJS += util/parse-events.o
LIB_OBJS += util/path.o
LIB_OBJS += util/rbtree.o
+LIB_OBJS += util/bitmap.o
+LIB_OBJS += util/hweight.o
+LIB_OBJS += util/find_next_bit.o
LIB_OBJS += util/run-command.o
LIB_OBJS += util/quote.o
LIB_OBJS += util/strbuf.o
@@ -790,6 +793,19 @@ util/config.o: util/config.c PERF-CFLAGS
util/rbtree.o: ../../lib/rbtree.c PERF-CFLAGS
$(QUIET_CC)$(CC) -o util/rbtree.o -c $(ALL_CFLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+# some perf warning policies can't fit to lib/bitmap.c, eg: it warns about variable shadowing
+# from <string.h> that comes from kernel headers wrapping.
+KBITMAP_FLAGS=`echo $(ALL_CFLAGS) | sed s/-Wshadow// | sed s/-Wswitch-default// | sed s/-Wextra//`
+
+util/bitmap.o: ../../lib/bitmap.c PERF-CFLAGS
+ $(QUIET_CC)$(CC) -o util/bitmap.o -c $(KBITMAP_FLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
+util/hweight.o: ../../lib/hweight.c PERF-CFLAGS
+ $(QUIET_CC)$(CC) -o util/hweight.o -c $(ALL_CFLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
+util/find_next_bit.o: ../../lib/find_next_bit.c PERF-CFLAGS
+ $(QUIET_CC)$(CC) -o util/find_next_bit.o -c $(ALL_CFLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
perf-%$X: %.o $(PERFLIBS)
$(QUIET_LINK)$(CC) $(ALL_CFLAGS) -o $@ $(ALL_LDFLAGS) $(filter %.o,$^) $(LIBS)
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 8b2c860..fc3709c 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -21,9 +21,6 @@
#include <unistd.h>
#include <sched.h>
-#define ALIGN(x, a) __ALIGN_MASK(x, (typeof(x))(a)-1)
-#define __ALIGN_MASK(x, mask) (((x)+(mask))&~(mask))
-
static int fd[MAX_NR_CPUS][MAX_COUNTERS];
static long default_interval = 0;
diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c
index c9c6856..e32c946 100644
--- a/tools/perf/builtin-sched.c
+++ b/tools/perf/builtin-sched.c
@@ -38,8 +38,6 @@ static int cwdlen;
#define PR_SET_NAME 15 /* Set process name */
#define MAX_CPUS 4096
-#define BUG_ON(x) assert(!(x))
-
static u64 run_measurement_overhead;
static u64 sleep_measurement_overhead;
diff --git a/tools/perf/util/include/asm/bitops.h b/tools/perf/util/include/asm/bitops.h
new file mode 100644
index 0000000..fbe4d92
--- /dev/null
+++ b/tools/perf/util/include/asm/bitops.h
@@ -0,0 +1,6 @@
+#include "../../../../include/asm-generic/bitops/__fls.h"
+#include "../../../../include/asm-generic/bitops/fls.h"
+#include "../../../../include/asm-generic/bitops/fls64.h"
+#include "../../../../include/asm-generic/bitops/__ffs.h"
+#include "../../../../include/asm-generic/bitops/ffz.h"
+#include "../../../../include/asm-generic/bitops/hweight.h"
diff --git a/tools/perf/util/include/asm/byteorder.h b/tools/perf/util/include/asm/byteorder.h
new file mode 100644
index 0000000..39f367c
--- /dev/null
+++ b/tools/perf/util/include/asm/byteorder.h
@@ -0,0 +1,2 @@
+#include "../asm/types.h"
+#include "../../../../include/linux/swab.h"
diff --git a/tools/perf/util/include/asm/swab.h b/tools/perf/util/include/asm/swab.h
new file mode 100644
index 0000000..ed53894
--- /dev/null
+++ b/tools/perf/util/include/asm/swab.h
@@ -0,0 +1 @@
+/* stub */
diff --git a/tools/perf/util/include/asm/types.h b/tools/perf/util/include/asm/types.h
new file mode 100644
index 0000000..06703c6
--- /dev/null
+++ b/tools/perf/util/include/asm/types.h
@@ -0,0 +1,17 @@
+#ifndef PERF_ASM_TYPES_H_
+#define PERF_ASM_TYPES_H_
+
+#include <linux/compiler.h>
+#include "../../types.h"
+#include <sys/types.h>
+
+/* CHECKME: Not sure both always match */
+#define BITS_PER_LONG __WORDSIZE
+
+typedef u64 __u64;
+typedef u32 __u32;
+typedef u16 __u16;
+typedef u8 __u8;
+typedef s64 __s64;
+
+#endif /* PERF_ASM_TYPES_H_ */
diff --git a/tools/perf/util/include/asm/uaccess.h b/tools/perf/util/include/asm/uaccess.h
new file mode 100644
index 0000000..d0f72b8
--- /dev/null
+++ b/tools/perf/util/include/asm/uaccess.h
@@ -0,0 +1,14 @@
+#ifndef _PERF_ASM_UACCESS_H_
+#define _PERF_ASM_UACCESS_H_
+
+#define __get_user(src, dest) \
+({ \
+ (src) = *dest; \
+ 0; \
+})
+
+#define get_user __get_user
+
+#define access_ok(type, addr, size) 1
+
+#endif
diff --git a/tools/perf/util/include/linux/bitmap.h b/tools/perf/util/include/linux/bitmap.h
new file mode 100644
index 0000000..821c103
--- /dev/null
+++ b/tools/perf/util/include/linux/bitmap.h
@@ -0,0 +1,2 @@
+#include "../../../../include/linux/bitmap.h"
+#include "../../../../include/asm-generic/bitops/find.h"
diff --git a/tools/perf/util/include/linux/bitops.h b/tools/perf/util/include/linux/bitops.h
new file mode 100644
index 0000000..ace57c3
--- /dev/null
+++ b/tools/perf/util/include/linux/bitops.h
@@ -0,0 +1,27 @@
+#ifndef _PERF_LINUX_BITOPS_H_
+#define _PERF_LINUX_BITOPS_H_
+
+#define __KERNEL__
+
+#define CONFIG_GENERIC_FIND_NEXT_BIT
+#define CONFIG_GENERIC_FIND_FIRST_BIT
+#include "../../../../include/linux/bitops.h"
+
+static inline void set_bit(int nr, unsigned long *addr)
+{
+ addr[nr / BITS_PER_LONG] |= 1UL << (nr % BITS_PER_LONG);
+}
+
+static __always_inline int test_bit(unsigned int nr, const unsigned long *addr)
+{
+ return ((1UL << (nr % BITS_PER_LONG)) &
+ (((unsigned long *)addr)[nr / BITS_PER_LONG])) != 0;
+}
+
+unsigned long generic_find_next_zero_le_bit(const unsigned long *addr, unsigned
+ long size, unsigned long offset);
+
+unsigned long generic_find_next_le_bit(const unsigned long *addr, unsigned
+ long size, unsigned long offset);
+
+#endif
diff --git a/tools/perf/util/include/linux/compiler.h b/tools/perf/util/include/linux/compiler.h
new file mode 100644
index 0000000..dfb0713
--- /dev/null
+++ b/tools/perf/util/include/linux/compiler.h
@@ -0,0 +1,10 @@
+#ifndef _PERF_LINUX_COMPILER_H_
+#define _PERF_LINUX_COMPILER_H_
+
+#ifndef __always_inline
+#define __always_inline inline
+#endif
+#define __user
+#define __attribute_const__
+
+#endif
diff --git a/tools/perf/util/include/linux/ctype.h b/tools/perf/util/include/linux/ctype.h
new file mode 100644
index 0000000..bae5783
--- /dev/null
+++ b/tools/perf/util/include/linux/ctype.h
@@ -0,0 +1 @@
+#include "../../../../include/linux/ctype.h"
diff --git a/tools/perf/util/include/linux/kernel.h b/tools/perf/util/include/linux/kernel.h
index a6b8739..4b9204d 100644
--- a/tools/perf/util/include/linux/kernel.h
+++ b/tools/perf/util/include/linux/kernel.h
@@ -1,6 +1,16 @@
#ifndef PERF_LINUX_KERNEL_H_
#define PERF_LINUX_KERNEL_H_
+#include <stdarg.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <assert.h>
+
+#define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
+
+#define ALIGN(x,a) __ALIGN_MASK(x,(typeof(x))(a)-1)
+#define __ALIGN_MASK(x,mask) (((x)+(mask))&~(mask))
+
#ifndef offsetof
#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
#endif
@@ -26,4 +36,53 @@
_max1 > _max2 ? _max1 : _max2; })
#endif
+#ifndef min
+#define min(x, y) ({ \
+ typeof(x) _min1 = (x); \
+ typeof(y) _min2 = (y); \
+ (void) (&_min1 == &_min2); \
+ _min1 < _min2 ? _min1 : _min2; })
+#endif
+
+#ifndef BUG_ON
+#define BUG_ON(cond) assert(!(cond))
+#endif
+
+/*
+ * Both need more care to handle endianness
+ * (Don't use bitmap_copy_le() for now)
+ */
+#define cpu_to_le64(x) (x)
+#define cpu_to_le32(x) (x)
+
+static inline int
+vscnprintf(char *buf, size_t size, const char *fmt, va_list args)
+{
+ int i;
+ ssize_t ssize = size;
+
+ i = vsnprintf(buf, size, fmt, args);
+
+ return (i >= ssize) ? (ssize - 1) : i;
+}
+
+static inline int scnprintf(char * buf, size_t size, const char * fmt, ...)
+{
+ va_list args;
+ ssize_t ssize = size;
+ int i;
+
+ va_start(args, fmt);
+ i = vsnprintf(buf, size, fmt, args);
+ va_end(args);
+
+ return (i >= ssize) ? (ssize - 1) : i;
+}
+
+static inline unsigned long
+simple_strtoul(const char *nptr, char **endptr, int base)
+{
+ return strtoul(nptr, endptr, base);
+}
+
#endif
diff --git a/tools/perf/util/include/linux/types.h b/tools/perf/util/include/linux/types.h
new file mode 100644
index 0000000..ed53894
--- /dev/null
+++ b/tools/perf/util/include/linux/types.h
@@ -0,0 +1 @@
+/* stub */
--
1.6.2.3
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH 2/2] perf tools: Introduce bitmask'ed additional headers
2009-10-16 7:42 ` Ingo Molnar
2009-10-17 15:12 ` [PATCH 1/2] perf tools: Use kernel bitmap library Frederic Weisbecker
@ 2009-10-17 15:12 ` Frederic Weisbecker
2009-10-19 7:56 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
2009-10-17 15:57 ` [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array Frederic Weisbecker
2 siblings, 1 reply; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-17 15:12 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Frederic Weisbecker, Peter Zijlstra,
Arnaldo Carvalho de Melo, Mike Galbraith, Paul Mackerras,
Steven Rostedt
This provides a new set of bitmasked headers. A new field is added
in the perf headers that implements a bitmap storing optional features
present in the perf.data file.
The layout can be pictured like this:
(Usual perf headers)(Features bitmap)[Feature 0][Feature n][Feature 255]
If the bit n is set, then the feature n is used in this file. They are
all set in order. This brings a backward and forward compatibility.
The trace_info section has moved into such optional features, this is
the first and only one for now.
This is backward compatible with the .32 file version although it
doesn't support the previous separate trace.info file.
And finally it doesn't support the current interim development version.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
---
tools/perf/builtin-record.c | 4 +-
| 100 ++++++++++++++++++++++++-------------------
| 30 +++++++++----
3 files changed, 78 insertions(+), 56 deletions(-)
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index fc3709c..f0467ff 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -574,11 +574,11 @@ static int __cmd_record(int argc, const char **argv)
header = perf_header__new();
if (raw_samples) {
- perf_header__set_trace_info();
+ perf_header__feat_trace_info(header);
} else {
for (i = 0; i < nr_counters; i++) {
if (attrs[i].sample_type & PERF_SAMPLE_RAW) {
- perf_header__set_trace_info();
+ perf_header__feat_trace_info(header);
break;
}
}
--git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 9aae360..171d51b 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -8,6 +8,8 @@
#include "../perf.h"
#include "trace-event.h"
+#include <linux/bitmap.h>
+
/*
* Create new perf.data header attribute:
*/
@@ -48,25 +50,17 @@ void perf_header_attr__add_id(struct perf_header_attr *self, u64 id)
*/
struct perf_header *perf_header__new(void)
{
- struct perf_header *self = malloc(sizeof(*self));
+ struct perf_header *self = calloc(sizeof(*self), 1);
if (!self)
die("nomem");
- self->frozen = 0;
-
- self->attrs = 0;
self->size = 1;
self->attr = malloc(sizeof(void *));
if (!self->attr)
die("nomem");
- self->data_offset = 0;
- self->data_size = 0;
- self->trace_info_offset = 0;
- self->trace_info_size = 0;
-
return self;
}
@@ -149,14 +143,12 @@ struct perf_file_header {
struct perf_file_section attrs;
struct perf_file_section data;
struct perf_file_section event_types;
- struct perf_file_section trace_info;
+ feat_mask_t adds_features;
};
-static int trace_info;
-
-void perf_header__set_trace_info(void)
+void perf_header__feat_trace_info(struct perf_header *header)
{
- trace_info = 1;
+ set_bit(HEADER_TRACE_INFO, perf_header__adds_mask(header));
}
static void do_write(int fd, void *buf, size_t size)
@@ -172,6 +164,32 @@ static void do_write(int fd, void *buf, size_t size)
}
}
+static void perf_header__adds_write(struct perf_header *self, int fd)
+{
+ struct perf_file_section trace_sec;
+ u64 cur_offset = lseek(fd, 0, SEEK_CUR);
+ unsigned long *feat_mask = perf_header__adds_mask(self);
+
+ if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
+ /* Write trace info */
+ trace_sec.offset = lseek(fd, sizeof(trace_sec), SEEK_CUR);
+ read_tracing_data(fd, attrs, nr_counters);
+ trace_sec.size = lseek(fd, 0, SEEK_CUR) - trace_sec.offset;
+
+ /* Write trace info headers */
+ lseek(fd, cur_offset, SEEK_SET);
+ do_write(fd, &trace_sec, sizeof(trace_sec));
+
+ /*
+ * Update cur_offset. So that other (future)
+ * features can set their own infos in this place. But if we are
+ * the only feature, at least that seeks to the place the data
+ * should begin.
+ */
+ cur_offset = lseek(fd, trace_sec.offset + trace_sec.size, SEEK_SET);
+ }
+};
+
void perf_header__write(struct perf_header *self, int fd)
{
struct perf_file_header f_header;
@@ -210,23 +228,7 @@ void perf_header__write(struct perf_header *self, int fd)
if (events)
do_write(fd, events, self->event_size);
- if (trace_info) {
- static int trace_info_written;
-
- /*
- * Write it only once
- */
- if (!trace_info_written) {
- self->trace_info_offset = lseek(fd, 0, SEEK_CUR);
- read_tracing_data(fd, attrs, nr_counters);
- self->trace_info_size = lseek(fd, 0, SEEK_CUR) -
- self->trace_info_offset;
- trace_info_written = 1;
- } else {
- lseek(fd, self->trace_info_offset +
- self->trace_info_size, SEEK_SET);
- }
- }
+ perf_header__adds_write(self, fd);
self->data_offset = lseek(fd, 0, SEEK_CUR);
@@ -246,12 +248,10 @@ void perf_header__write(struct perf_header *self, int fd)
.offset = self->event_offset,
.size = self->event_size,
},
- .trace_info = {
- .offset = self->trace_info_offset,
- .size = self->trace_info_size,
- },
};
+ memcpy(&f_header.adds_features, &self->adds_features, sizeof(feat_mask_t));
+
lseek(fd, 0, SEEK_SET);
do_write(fd, &f_header, sizeof(f_header));
lseek(fd, self->data_offset + self->data_size, SEEK_SET);
@@ -274,6 +274,20 @@ static void do_read(int fd, void *buf, size_t size)
}
}
+static void perf_header__adds_read(struct perf_header *self, int fd)
+{
+ const unsigned long *feat_mask = perf_header__adds_mask(self);
+
+ if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
+ struct perf_file_section trace_sec;
+
+ do_read(fd, &trace_sec, sizeof(trace_sec));
+ lseek(fd, trace_sec.offset, SEEK_SET);
+ trace_report(fd);
+ lseek(fd, trace_sec.offset + trace_sec.size, SEEK_SET);
+ }
+};
+
struct perf_header *perf_header__read(int fd)
{
struct perf_header *self = perf_header__new();
@@ -292,9 +306,11 @@ struct perf_header *perf_header__read(int fd)
if (f_header.size != sizeof(f_header)) {
/* Support the previous format */
- if (f_header.size == offsetof(typeof(f_header), trace_info))
- f_header.trace_info.size = 0;
- else
+ if (f_header.size == offsetof(typeof(f_header), adds_features)) {
+ unsigned long *mask = (unsigned long *)(void *)
+ &f_header.adds_features;
+ bitmap_zero(mask, HEADER_FEAT_BITS);
+ } else
die("incompatible file format");
}
nr_attrs = f_header.attrs.size / sizeof(f_attr);
@@ -330,13 +346,9 @@ struct perf_header *perf_header__read(int fd)
event_count = f_header.event_types.size / sizeof(struct perf_trace_event_type);
}
- self->trace_info_offset = f_header.trace_info.offset;
- self->trace_info_size = f_header.trace_info.size;
+ memcpy(&self->adds_features, &f_header.adds_features, sizeof(feat_mask_t));
- if (self->trace_info_size) {
- lseek(fd, self->trace_info_offset, SEEK_SET);
- trace_report(fd);
- }
+ perf_header__adds_read(self, fd);
self->event_offset = f_header.event_types.offset;
self->event_size = f_header.event_types.size;
--git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 30aee51..0eb4a91 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -12,19 +12,29 @@ struct perf_header_attr {
off_t id_offset;
};
+#define HEADER_TRACE_INFO 1
+
+#define HEADER_FEAT_BITS 256
+
+typedef typeof(u64[HEADER_FEAT_BITS / 8]) feat_mask_t;
+
struct perf_header {
- int frozen;
- int attrs, size;
+ int frozen;
+ int attrs, size;
struct perf_header_attr **attr;
- s64 attr_offset;
- u64 data_offset;
- u64 data_size;
- u64 event_offset;
- u64 event_size;
- u64 trace_info_offset;
- u64 trace_info_size;
+ s64 attr_offset;
+ u64 data_offset;
+ u64 data_size;
+ u64 event_offset;
+ u64 event_size;
+ feat_mask_t adds_features;
};
+static inline unsigned long *perf_header__adds_mask(struct perf_header *self)
+{
+ return (unsigned long *)(void *)&self->adds_features;
+}
+
struct perf_header *perf_header__read(int fd);
void perf_header__write(struct perf_header *self, int fd);
@@ -42,7 +52,7 @@ void perf_header_attr__add_id(struct perf_header_attr *self, u64 id);
u64 perf_header__sample_type(struct perf_header *header);
struct perf_event_attr *
perf_header__find_attr(u64 id, struct perf_header *header);
-void perf_header__set_trace_info(void);
+void perf_header__feat_trace_info(struct perf_header *header);
struct perf_header *perf_header__new(void);
--
1.6.2.3
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array
2009-10-16 7:42 ` Ingo Molnar
2009-10-17 15:12 ` [PATCH 1/2] perf tools: Use kernel bitmap library Frederic Weisbecker
2009-10-17 15:12 ` [PATCH 2/2] perf tools: Introduce bitmask'ed additional headers Frederic Weisbecker
@ 2009-10-17 15:57 ` Frederic Weisbecker
2009-10-17 16:03 ` Frederic Weisbecker
2009-10-19 7:56 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
2 siblings, 2 replies; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-17 15:57 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Frederic Weisbecker, Peter Zijlstra,
Arnaldo Carvalho de Melo, Mike Galbraith, Paul Mackerras,
Steven Rostedt
Use DECLARE_BITMAP instead of an open coded array for our bitmap
of featured sections.
This makes the array an unsigned long instead of a u64 but since
we use a 256 bits bitmap, the array size shouldn't vary between
different boxes.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
---
| 22 +++++++++-------------
| 11 +++--------
tools/perf/util/include/asm/asm-offsets.h | 1 +
tools/perf/util/include/linux/types.h | 8 +++++++-
4 files changed, 20 insertions(+), 22 deletions(-)
create mode 100644 tools/perf/util/include/asm/asm-offsets.h
--git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 171d51b..622c60e 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -8,8 +8,6 @@
#include "../perf.h"
#include "trace-event.h"
-#include <linux/bitmap.h>
-
/*
* Create new perf.data header attribute:
*/
@@ -143,12 +141,12 @@ struct perf_file_header {
struct perf_file_section attrs;
struct perf_file_section data;
struct perf_file_section event_types;
- feat_mask_t adds_features;
+ DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
};
void perf_header__feat_trace_info(struct perf_header *header)
{
- set_bit(HEADER_TRACE_INFO, perf_header__adds_mask(header));
+ set_bit(HEADER_TRACE_INFO, header->adds_features);
}
static void do_write(int fd, void *buf, size_t size)
@@ -168,7 +166,7 @@ static void perf_header__adds_write(struct perf_header *self, int fd)
{
struct perf_file_section trace_sec;
u64 cur_offset = lseek(fd, 0, SEEK_CUR);
- unsigned long *feat_mask = perf_header__adds_mask(self);
+ unsigned long *feat_mask = self->adds_features;
if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
/* Write trace info */
@@ -250,7 +248,7 @@ void perf_header__write(struct perf_header *self, int fd)
},
};
- memcpy(&f_header.adds_features, &self->adds_features, sizeof(feat_mask_t));
+ memcpy(&f_header.adds_features, &self->adds_features, sizeof(self->adds_features));
lseek(fd, 0, SEEK_SET);
do_write(fd, &f_header, sizeof(f_header));
@@ -276,7 +274,7 @@ static void do_read(int fd, void *buf, size_t size)
static void perf_header__adds_read(struct perf_header *self, int fd)
{
- const unsigned long *feat_mask = perf_header__adds_mask(self);
+ const unsigned long *feat_mask = self->adds_features;
if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
struct perf_file_section trace_sec;
@@ -306,11 +304,9 @@ struct perf_header *perf_header__read(int fd)
if (f_header.size != sizeof(f_header)) {
/* Support the previous format */
- if (f_header.size == offsetof(typeof(f_header), adds_features)) {
- unsigned long *mask = (unsigned long *)(void *)
- &f_header.adds_features;
- bitmap_zero(mask, HEADER_FEAT_BITS);
- } else
+ if (f_header.size == offsetof(typeof(f_header), adds_features))
+ bitmap_zero(f_header.adds_features, HEADER_FEAT_BITS);
+ else
die("incompatible file format");
}
nr_attrs = f_header.attrs.size / sizeof(f_attr);
@@ -346,7 +342,7 @@ struct perf_header *perf_header__read(int fd)
event_count = f_header.event_types.size / sizeof(struct perf_trace_event_type);
}
- memcpy(&self->adds_features, &f_header.adds_features, sizeof(feat_mask_t));
+ memcpy(&self->adds_features, &f_header.adds_features, sizeof(f_header.adds_features));
perf_header__adds_read(self, fd);
--git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 0eb4a91..2ea9dfb 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -5,6 +5,8 @@
#include <sys/types.h>
#include "types.h"
+#include <linux/bitmap.h>
+
struct perf_header_attr {
struct perf_event_attr attr;
int ids, size;
@@ -16,8 +18,6 @@ struct perf_header_attr {
#define HEADER_FEAT_BITS 256
-typedef typeof(u64[HEADER_FEAT_BITS / 8]) feat_mask_t;
-
struct perf_header {
int frozen;
int attrs, size;
@@ -27,14 +27,9 @@ struct perf_header {
u64 data_size;
u64 event_offset;
u64 event_size;
- feat_mask_t adds_features;
+ DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
};
-static inline unsigned long *perf_header__adds_mask(struct perf_header *self)
-{
- return (unsigned long *)(void *)&self->adds_features;
-}
-
struct perf_header *perf_header__read(int fd);
void perf_header__write(struct perf_header *self, int fd);
diff --git a/tools/perf/util/include/asm/asm-offsets.h b/tools/perf/util/include/asm/asm-offsets.h
new file mode 100644
index 0000000..ed53894
--- /dev/null
+++ b/tools/perf/util/include/asm/asm-offsets.h
@@ -0,0 +1 @@
+/* stub */
diff --git a/tools/perf/util/include/linux/types.h b/tools/perf/util/include/linux/types.h
index ed53894..858a38d 100644
--- a/tools/perf/util/include/linux/types.h
+++ b/tools/perf/util/include/linux/types.h
@@ -1 +1,7 @@
-/* stub */
+#ifndef _PERF_LINUX_TYPES_H_
+#define _PERF_LINUX_TYPES_H_
+
+#define DECLARE_BITMAP(name,bits) \
+ unsigned long name[BITS_TO_LONGS(bits)]
+
+#endif
--
1.6.2.3
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array
2009-10-17 15:57 ` [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array Frederic Weisbecker
@ 2009-10-17 16:03 ` Frederic Weisbecker
2009-10-19 7:30 ` Ingo Molnar
2009-10-19 7:56 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
1 sibling, 1 reply; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-17 16:03 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Peter Zijlstra, Arnaldo Carvalho de Melo, Mike Galbraith,
Paul Mackerras, Steven Rostedt
On Sat, Oct 17, 2009 at 05:57:18PM +0200, Frederic Weisbecker wrote:
> Use DECLARE_BITMAP instead of an open coded array for our bitmap
> of featured sections.
>
> This makes the array an unsigned long instead of a u64 but since
> we use a 256 bits bitmap, the array size shouldn't vary between
> different boxes.
That said I would really feel more comfortable if someone can
confirm that.
> @@ -143,12 +141,12 @@ struct perf_file_header {
> struct perf_file_section attrs;
> struct perf_file_section data;
> struct perf_file_section event_types;
> - feat_mask_t adds_features;
> + DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
I think having adds_features as an unsigned long won't
hurt because we have HEAD_FEAT_BITS % 64 == 0
It would certainly hurt if we had, say, HEAD_FEAT_BITS = 257
But may be I forget a corner case. I hope someone can double
check that. Thanks.
^ permalink raw reply [flat|nested] 13+ messages in thread
* Re: [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array
2009-10-17 16:03 ` Frederic Weisbecker
@ 2009-10-19 7:30 ` Ingo Molnar
2009-10-19 19:40 ` Frederic Weisbecker
0 siblings, 1 reply; 13+ messages in thread
From: Ingo Molnar @ 2009-10-19 7:30 UTC (permalink / raw)
To: Frederic Weisbecker
Cc: LKML, Peter Zijlstra, Arnaldo Carvalho de Melo, Mike Galbraith,
Paul Mackerras, Steven Rostedt
* Frederic Weisbecker <fweisbec@gmail.com> wrote:
> On Sat, Oct 17, 2009 at 05:57:18PM +0200, Frederic Weisbecker wrote:
> > Use DECLARE_BITMAP instead of an open coded array for our bitmap
> > of featured sections.
> >
> > This makes the array an unsigned long instead of a u64 but since we
> > use a 256 bits bitmap, the array size shouldn't vary between
> > different boxes.
>
> That said I would really feel more comfortable if someone can confirm
> that.
Should be size-invariant for the bitmap size of 256 bits due to:
#define DECLARE_BITMAP(name,bits) \
unsigned long name[BITS_TO_LONGS(bits)]
but it's not little-endian/big-endian invariant.
We should at minimum save the CPU architecture (and endianness
parameters) the data got generated on, and reject
endianness-incompatible uses - so that if someone wants to add
cross-endian support it can be implemented cleanly.
Ingo
^ permalink raw reply [flat|nested] 13+ messages in thread
* [tip:perf/core] perf tools: Use kernel bitmap library
2009-10-17 15:12 ` [PATCH 1/2] perf tools: Use kernel bitmap library Frederic Weisbecker
@ 2009-10-19 7:55 ` tip-bot for Frederic Weisbecker
0 siblings, 0 replies; 13+ messages in thread
From: tip-bot for Frederic Weisbecker @ 2009-10-19 7:55 UTC (permalink / raw)
To: linux-tip-commits
Cc: linux-kernel, paulus, acme, hpa, mingo, efault, peterz, fweisbec,
rostedt, tglx, mingo
Commit-ID: 5a116dd2797677cad48fee2f42267e3cb69f5502
Gitweb: http://git.kernel.org/tip/5a116dd2797677cad48fee2f42267e3cb69f5502
Author: Frederic Weisbecker <fweisbec@gmail.com>
AuthorDate: Sat, 17 Oct 2009 17:12:33 +0200
Committer: Ingo Molnar <mingo@elte.hu>
CommitDate: Mon, 19 Oct 2009 09:26:34 +0200
perf tools: Use kernel bitmap library
Use the kernel bitmap library for internal perf tools uses.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
LKML-Reference: <1255792354-11304-1-git-send-email-fweisbec@gmail.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
---
tools/perf/Makefile | 16 ++++++++
tools/perf/builtin-record.c | 3 --
tools/perf/builtin-sched.c | 2 -
tools/perf/util/include/asm/bitops.h | 6 +++
tools/perf/util/include/asm/byteorder.h | 2 +
tools/perf/util/include/asm/swab.h | 1 +
tools/perf/util/include/asm/types.h | 17 +++++++++
tools/perf/util/include/asm/uaccess.h | 14 +++++++
tools/perf/util/include/linux/bitmap.h | 2 +
tools/perf/util/include/linux/bitops.h | 27 ++++++++++++++
tools/perf/util/include/linux/compiler.h | 10 +++++
tools/perf/util/include/linux/ctype.h | 1 +
tools/perf/util/include/linux/kernel.h | 59 ++++++++++++++++++++++++++++++
tools/perf/util/include/linux/types.h | 1 +
14 files changed, 156 insertions(+), 5 deletions(-)
diff --git a/tools/perf/Makefile b/tools/perf/Makefile
index 106c150..2400e50 100644
--- a/tools/perf/Makefile
+++ b/tools/perf/Makefile
@@ -363,6 +363,9 @@ LIB_OBJS += util/parse-options.o
LIB_OBJS += util/parse-events.o
LIB_OBJS += util/path.o
LIB_OBJS += util/rbtree.o
+LIB_OBJS += util/bitmap.o
+LIB_OBJS += util/hweight.o
+LIB_OBJS += util/find_next_bit.o
LIB_OBJS += util/run-command.o
LIB_OBJS += util/quote.o
LIB_OBJS += util/strbuf.o
@@ -790,6 +793,19 @@ util/config.o: util/config.c PERF-CFLAGS
util/rbtree.o: ../../lib/rbtree.c PERF-CFLAGS
$(QUIET_CC)$(CC) -o util/rbtree.o -c $(ALL_CFLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+# some perf warning policies can't fit to lib/bitmap.c, eg: it warns about variable shadowing
+# from <string.h> that comes from kernel headers wrapping.
+KBITMAP_FLAGS=`echo $(ALL_CFLAGS) | sed s/-Wshadow// | sed s/-Wswitch-default// | sed s/-Wextra//`
+
+util/bitmap.o: ../../lib/bitmap.c PERF-CFLAGS
+ $(QUIET_CC)$(CC) -o util/bitmap.o -c $(KBITMAP_FLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
+util/hweight.o: ../../lib/hweight.c PERF-CFLAGS
+ $(QUIET_CC)$(CC) -o util/hweight.o -c $(ALL_CFLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
+util/find_next_bit.o: ../../lib/find_next_bit.c PERF-CFLAGS
+ $(QUIET_CC)$(CC) -o util/find_next_bit.o -c $(ALL_CFLAGS) -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
perf-%$X: %.o $(PERFLIBS)
$(QUIET_LINK)$(CC) $(ALL_CFLAGS) -o $@ $(ALL_LDFLAGS) $(filter %.o,$^) $(LIBS)
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index 8b2c860..fc3709c 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -21,9 +21,6 @@
#include <unistd.h>
#include <sched.h>
-#define ALIGN(x, a) __ALIGN_MASK(x, (typeof(x))(a)-1)
-#define __ALIGN_MASK(x, mask) (((x)+(mask))&~(mask))
-
static int fd[MAX_NR_CPUS][MAX_COUNTERS];
static long default_interval = 0;
diff --git a/tools/perf/builtin-sched.c b/tools/perf/builtin-sched.c
index 57ad3f4..807ca66 100644
--- a/tools/perf/builtin-sched.c
+++ b/tools/perf/builtin-sched.c
@@ -38,8 +38,6 @@ static int cwdlen;
#define PR_SET_NAME 15 /* Set process name */
#define MAX_CPUS 4096
-#define BUG_ON(x) assert(!(x))
-
static u64 run_measurement_overhead;
static u64 sleep_measurement_overhead;
diff --git a/tools/perf/util/include/asm/bitops.h b/tools/perf/util/include/asm/bitops.h
new file mode 100644
index 0000000..fbe4d92
--- /dev/null
+++ b/tools/perf/util/include/asm/bitops.h
@@ -0,0 +1,6 @@
+#include "../../../../include/asm-generic/bitops/__fls.h"
+#include "../../../../include/asm-generic/bitops/fls.h"
+#include "../../../../include/asm-generic/bitops/fls64.h"
+#include "../../../../include/asm-generic/bitops/__ffs.h"
+#include "../../../../include/asm-generic/bitops/ffz.h"
+#include "../../../../include/asm-generic/bitops/hweight.h"
diff --git a/tools/perf/util/include/asm/byteorder.h b/tools/perf/util/include/asm/byteorder.h
new file mode 100644
index 0000000..39f367c
--- /dev/null
+++ b/tools/perf/util/include/asm/byteorder.h
@@ -0,0 +1,2 @@
+#include "../asm/types.h"
+#include "../../../../include/linux/swab.h"
diff --git a/tools/perf/util/include/asm/swab.h b/tools/perf/util/include/asm/swab.h
new file mode 100644
index 0000000..ed53894
--- /dev/null
+++ b/tools/perf/util/include/asm/swab.h
@@ -0,0 +1 @@
+/* stub */
diff --git a/tools/perf/util/include/asm/types.h b/tools/perf/util/include/asm/types.h
new file mode 100644
index 0000000..06703c6
--- /dev/null
+++ b/tools/perf/util/include/asm/types.h
@@ -0,0 +1,17 @@
+#ifndef PERF_ASM_TYPES_H_
+#define PERF_ASM_TYPES_H_
+
+#include <linux/compiler.h>
+#include "../../types.h"
+#include <sys/types.h>
+
+/* CHECKME: Not sure both always match */
+#define BITS_PER_LONG __WORDSIZE
+
+typedef u64 __u64;
+typedef u32 __u32;
+typedef u16 __u16;
+typedef u8 __u8;
+typedef s64 __s64;
+
+#endif /* PERF_ASM_TYPES_H_ */
diff --git a/tools/perf/util/include/asm/uaccess.h b/tools/perf/util/include/asm/uaccess.h
new file mode 100644
index 0000000..d0f72b8
--- /dev/null
+++ b/tools/perf/util/include/asm/uaccess.h
@@ -0,0 +1,14 @@
+#ifndef _PERF_ASM_UACCESS_H_
+#define _PERF_ASM_UACCESS_H_
+
+#define __get_user(src, dest) \
+({ \
+ (src) = *dest; \
+ 0; \
+})
+
+#define get_user __get_user
+
+#define access_ok(type, addr, size) 1
+
+#endif
diff --git a/tools/perf/util/include/linux/bitmap.h b/tools/perf/util/include/linux/bitmap.h
new file mode 100644
index 0000000..821c103
--- /dev/null
+++ b/tools/perf/util/include/linux/bitmap.h
@@ -0,0 +1,2 @@
+#include "../../../../include/linux/bitmap.h"
+#include "../../../../include/asm-generic/bitops/find.h"
diff --git a/tools/perf/util/include/linux/bitops.h b/tools/perf/util/include/linux/bitops.h
new file mode 100644
index 0000000..ace57c3
--- /dev/null
+++ b/tools/perf/util/include/linux/bitops.h
@@ -0,0 +1,27 @@
+#ifndef _PERF_LINUX_BITOPS_H_
+#define _PERF_LINUX_BITOPS_H_
+
+#define __KERNEL__
+
+#define CONFIG_GENERIC_FIND_NEXT_BIT
+#define CONFIG_GENERIC_FIND_FIRST_BIT
+#include "../../../../include/linux/bitops.h"
+
+static inline void set_bit(int nr, unsigned long *addr)
+{
+ addr[nr / BITS_PER_LONG] |= 1UL << (nr % BITS_PER_LONG);
+}
+
+static __always_inline int test_bit(unsigned int nr, const unsigned long *addr)
+{
+ return ((1UL << (nr % BITS_PER_LONG)) &
+ (((unsigned long *)addr)[nr / BITS_PER_LONG])) != 0;
+}
+
+unsigned long generic_find_next_zero_le_bit(const unsigned long *addr, unsigned
+ long size, unsigned long offset);
+
+unsigned long generic_find_next_le_bit(const unsigned long *addr, unsigned
+ long size, unsigned long offset);
+
+#endif
diff --git a/tools/perf/util/include/linux/compiler.h b/tools/perf/util/include/linux/compiler.h
new file mode 100644
index 0000000..dfb0713
--- /dev/null
+++ b/tools/perf/util/include/linux/compiler.h
@@ -0,0 +1,10 @@
+#ifndef _PERF_LINUX_COMPILER_H_
+#define _PERF_LINUX_COMPILER_H_
+
+#ifndef __always_inline
+#define __always_inline inline
+#endif
+#define __user
+#define __attribute_const__
+
+#endif
diff --git a/tools/perf/util/include/linux/ctype.h b/tools/perf/util/include/linux/ctype.h
new file mode 100644
index 0000000..bae5783
--- /dev/null
+++ b/tools/perf/util/include/linux/ctype.h
@@ -0,0 +1 @@
+#include "../../../../include/linux/ctype.h"
diff --git a/tools/perf/util/include/linux/kernel.h b/tools/perf/util/include/linux/kernel.h
index a6b8739..4b9204d 100644
--- a/tools/perf/util/include/linux/kernel.h
+++ b/tools/perf/util/include/linux/kernel.h
@@ -1,6 +1,16 @@
#ifndef PERF_LINUX_KERNEL_H_
#define PERF_LINUX_KERNEL_H_
+#include <stdarg.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <assert.h>
+
+#define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
+
+#define ALIGN(x,a) __ALIGN_MASK(x,(typeof(x))(a)-1)
+#define __ALIGN_MASK(x,mask) (((x)+(mask))&~(mask))
+
#ifndef offsetof
#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
#endif
@@ -26,4 +36,53 @@
_max1 > _max2 ? _max1 : _max2; })
#endif
+#ifndef min
+#define min(x, y) ({ \
+ typeof(x) _min1 = (x); \
+ typeof(y) _min2 = (y); \
+ (void) (&_min1 == &_min2); \
+ _min1 < _min2 ? _min1 : _min2; })
+#endif
+
+#ifndef BUG_ON
+#define BUG_ON(cond) assert(!(cond))
+#endif
+
+/*
+ * Both need more care to handle endianness
+ * (Don't use bitmap_copy_le() for now)
+ */
+#define cpu_to_le64(x) (x)
+#define cpu_to_le32(x) (x)
+
+static inline int
+vscnprintf(char *buf, size_t size, const char *fmt, va_list args)
+{
+ int i;
+ ssize_t ssize = size;
+
+ i = vsnprintf(buf, size, fmt, args);
+
+ return (i >= ssize) ? (ssize - 1) : i;
+}
+
+static inline int scnprintf(char * buf, size_t size, const char * fmt, ...)
+{
+ va_list args;
+ ssize_t ssize = size;
+ int i;
+
+ va_start(args, fmt);
+ i = vsnprintf(buf, size, fmt, args);
+ va_end(args);
+
+ return (i >= ssize) ? (ssize - 1) : i;
+}
+
+static inline unsigned long
+simple_strtoul(const char *nptr, char **endptr, int base)
+{
+ return strtoul(nptr, endptr, base);
+}
+
#endif
diff --git a/tools/perf/util/include/linux/types.h b/tools/perf/util/include/linux/types.h
new file mode 100644
index 0000000..ed53894
--- /dev/null
+++ b/tools/perf/util/include/linux/types.h
@@ -0,0 +1 @@
+/* stub */
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [tip:perf/core] perf tools: Introduce bitmask'ed additional headers
2009-10-17 15:12 ` [PATCH 2/2] perf tools: Introduce bitmask'ed additional headers Frederic Weisbecker
@ 2009-10-19 7:56 ` tip-bot for Frederic Weisbecker
0 siblings, 0 replies; 13+ messages in thread
From: tip-bot for Frederic Weisbecker @ 2009-10-19 7:56 UTC (permalink / raw)
To: linux-tip-commits
Cc: linux-kernel, paulus, acme, hpa, mingo, efault, peterz, fweisbec,
rostedt, tglx, mingo
Commit-ID: 2ba0825075e76236d22a20decd8e2346a99faabe
Gitweb: http://git.kernel.org/tip/2ba0825075e76236d22a20decd8e2346a99faabe
Author: Frederic Weisbecker <fweisbec@gmail.com>
AuthorDate: Sat, 17 Oct 2009 17:12:34 +0200
Committer: Ingo Molnar <mingo@elte.hu>
CommitDate: Mon, 19 Oct 2009 09:26:35 +0200
perf tools: Introduce bitmask'ed additional headers
This provides a new set of bitmasked headers. A new field is
added in the perf headers that implements a bitmap storing
optional features present in the perf.data file.
The layout can be pictured like this:
(Usual perf headers)(Features bitmap)[Feature 0][Feature
n][Feature 255]
If the bit n is set, then the feature n is used in this file.
They are all set in order. This brings a backward and forward
compatibility.
The trace_info section has moved into such optional features,
this is the first and only one for now.
This is backward compatible with the .32 file version although
it doesn't support the previous separate trace.info file.
And finally it doesn't support the current interim development
version.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
LKML-Reference: <1255792354-11304-2-git-send-email-fweisbec@gmail.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
---
tools/perf/builtin-record.c | 4 +-
| 100 ++++++++++++++++++++++++-------------------
| 30 +++++++++----
3 files changed, 78 insertions(+), 56 deletions(-)
diff --git a/tools/perf/builtin-record.c b/tools/perf/builtin-record.c
index fc3709c..f0467ff 100644
--- a/tools/perf/builtin-record.c
+++ b/tools/perf/builtin-record.c
@@ -574,11 +574,11 @@ static int __cmd_record(int argc, const char **argv)
header = perf_header__new();
if (raw_samples) {
- perf_header__set_trace_info();
+ perf_header__feat_trace_info(header);
} else {
for (i = 0; i < nr_counters; i++) {
if (attrs[i].sample_type & PERF_SAMPLE_RAW) {
- perf_header__set_trace_info();
+ perf_header__feat_trace_info(header);
break;
}
}
--git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 9aae360..171d51b 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -8,6 +8,8 @@
#include "../perf.h"
#include "trace-event.h"
+#include <linux/bitmap.h>
+
/*
* Create new perf.data header attribute:
*/
@@ -48,25 +50,17 @@ void perf_header_attr__add_id(struct perf_header_attr *self, u64 id)
*/
struct perf_header *perf_header__new(void)
{
- struct perf_header *self = malloc(sizeof(*self));
+ struct perf_header *self = calloc(sizeof(*self), 1);
if (!self)
die("nomem");
- self->frozen = 0;
-
- self->attrs = 0;
self->size = 1;
self->attr = malloc(sizeof(void *));
if (!self->attr)
die("nomem");
- self->data_offset = 0;
- self->data_size = 0;
- self->trace_info_offset = 0;
- self->trace_info_size = 0;
-
return self;
}
@@ -149,14 +143,12 @@ struct perf_file_header {
struct perf_file_section attrs;
struct perf_file_section data;
struct perf_file_section event_types;
- struct perf_file_section trace_info;
+ feat_mask_t adds_features;
};
-static int trace_info;
-
-void perf_header__set_trace_info(void)
+void perf_header__feat_trace_info(struct perf_header *header)
{
- trace_info = 1;
+ set_bit(HEADER_TRACE_INFO, perf_header__adds_mask(header));
}
static void do_write(int fd, void *buf, size_t size)
@@ -172,6 +164,32 @@ static void do_write(int fd, void *buf, size_t size)
}
}
+static void perf_header__adds_write(struct perf_header *self, int fd)
+{
+ struct perf_file_section trace_sec;
+ u64 cur_offset = lseek(fd, 0, SEEK_CUR);
+ unsigned long *feat_mask = perf_header__adds_mask(self);
+
+ if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
+ /* Write trace info */
+ trace_sec.offset = lseek(fd, sizeof(trace_sec), SEEK_CUR);
+ read_tracing_data(fd, attrs, nr_counters);
+ trace_sec.size = lseek(fd, 0, SEEK_CUR) - trace_sec.offset;
+
+ /* Write trace info headers */
+ lseek(fd, cur_offset, SEEK_SET);
+ do_write(fd, &trace_sec, sizeof(trace_sec));
+
+ /*
+ * Update cur_offset. So that other (future)
+ * features can set their own infos in this place. But if we are
+ * the only feature, at least that seeks to the place the data
+ * should begin.
+ */
+ cur_offset = lseek(fd, trace_sec.offset + trace_sec.size, SEEK_SET);
+ }
+};
+
void perf_header__write(struct perf_header *self, int fd)
{
struct perf_file_header f_header;
@@ -210,23 +228,7 @@ void perf_header__write(struct perf_header *self, int fd)
if (events)
do_write(fd, events, self->event_size);
- if (trace_info) {
- static int trace_info_written;
-
- /*
- * Write it only once
- */
- if (!trace_info_written) {
- self->trace_info_offset = lseek(fd, 0, SEEK_CUR);
- read_tracing_data(fd, attrs, nr_counters);
- self->trace_info_size = lseek(fd, 0, SEEK_CUR) -
- self->trace_info_offset;
- trace_info_written = 1;
- } else {
- lseek(fd, self->trace_info_offset +
- self->trace_info_size, SEEK_SET);
- }
- }
+ perf_header__adds_write(self, fd);
self->data_offset = lseek(fd, 0, SEEK_CUR);
@@ -246,12 +248,10 @@ void perf_header__write(struct perf_header *self, int fd)
.offset = self->event_offset,
.size = self->event_size,
},
- .trace_info = {
- .offset = self->trace_info_offset,
- .size = self->trace_info_size,
- },
};
+ memcpy(&f_header.adds_features, &self->adds_features, sizeof(feat_mask_t));
+
lseek(fd, 0, SEEK_SET);
do_write(fd, &f_header, sizeof(f_header));
lseek(fd, self->data_offset + self->data_size, SEEK_SET);
@@ -274,6 +274,20 @@ static void do_read(int fd, void *buf, size_t size)
}
}
+static void perf_header__adds_read(struct perf_header *self, int fd)
+{
+ const unsigned long *feat_mask = perf_header__adds_mask(self);
+
+ if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
+ struct perf_file_section trace_sec;
+
+ do_read(fd, &trace_sec, sizeof(trace_sec));
+ lseek(fd, trace_sec.offset, SEEK_SET);
+ trace_report(fd);
+ lseek(fd, trace_sec.offset + trace_sec.size, SEEK_SET);
+ }
+};
+
struct perf_header *perf_header__read(int fd)
{
struct perf_header *self = perf_header__new();
@@ -292,9 +306,11 @@ struct perf_header *perf_header__read(int fd)
if (f_header.size != sizeof(f_header)) {
/* Support the previous format */
- if (f_header.size == offsetof(typeof(f_header), trace_info))
- f_header.trace_info.size = 0;
- else
+ if (f_header.size == offsetof(typeof(f_header), adds_features)) {
+ unsigned long *mask = (unsigned long *)(void *)
+ &f_header.adds_features;
+ bitmap_zero(mask, HEADER_FEAT_BITS);
+ } else
die("incompatible file format");
}
nr_attrs = f_header.attrs.size / sizeof(f_attr);
@@ -330,13 +346,9 @@ struct perf_header *perf_header__read(int fd)
event_count = f_header.event_types.size / sizeof(struct perf_trace_event_type);
}
- self->trace_info_offset = f_header.trace_info.offset;
- self->trace_info_size = f_header.trace_info.size;
+ memcpy(&self->adds_features, &f_header.adds_features, sizeof(feat_mask_t));
- if (self->trace_info_size) {
- lseek(fd, self->trace_info_offset, SEEK_SET);
- trace_report(fd);
- }
+ perf_header__adds_read(self, fd);
self->event_offset = f_header.event_types.offset;
self->event_size = f_header.event_types.size;
--git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 30aee51..0eb4a91 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -12,19 +12,29 @@ struct perf_header_attr {
off_t id_offset;
};
+#define HEADER_TRACE_INFO 1
+
+#define HEADER_FEAT_BITS 256
+
+typedef typeof(u64[HEADER_FEAT_BITS / 8]) feat_mask_t;
+
struct perf_header {
- int frozen;
- int attrs, size;
+ int frozen;
+ int attrs, size;
struct perf_header_attr **attr;
- s64 attr_offset;
- u64 data_offset;
- u64 data_size;
- u64 event_offset;
- u64 event_size;
- u64 trace_info_offset;
- u64 trace_info_size;
+ s64 attr_offset;
+ u64 data_offset;
+ u64 data_size;
+ u64 event_offset;
+ u64 event_size;
+ feat_mask_t adds_features;
};
+static inline unsigned long *perf_header__adds_mask(struct perf_header *self)
+{
+ return (unsigned long *)(void *)&self->adds_features;
+}
+
struct perf_header *perf_header__read(int fd);
void perf_header__write(struct perf_header *self, int fd);
@@ -42,7 +52,7 @@ void perf_header_attr__add_id(struct perf_header_attr *self, u64 id);
u64 perf_header__sample_type(struct perf_header *header);
struct perf_event_attr *
perf_header__find_attr(u64 id, struct perf_header *header);
-void perf_header__set_trace_info(void);
+void perf_header__feat_trace_info(struct perf_header *header);
struct perf_header *perf_header__new(void);
^ permalink raw reply related [flat|nested] 13+ messages in thread
* [tip:perf/core] perf tools: Use DECLARE_BITMAP instead of an open-coded array
2009-10-17 15:57 ` [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array Frederic Weisbecker
2009-10-17 16:03 ` Frederic Weisbecker
@ 2009-10-19 7:56 ` tip-bot for Frederic Weisbecker
1 sibling, 0 replies; 13+ messages in thread
From: tip-bot for Frederic Weisbecker @ 2009-10-19 7:56 UTC (permalink / raw)
To: linux-tip-commits
Cc: linux-kernel, paulus, acme, hpa, mingo, efault, peterz, fweisbec,
rostedt, tglx, mingo
Commit-ID: db9f11e36d0125a5e3e595ea9ef2e4b89f7e8737
Gitweb: http://git.kernel.org/tip/db9f11e36d0125a5e3e595ea9ef2e4b89f7e8737
Author: Frederic Weisbecker <fweisbec@gmail.com>
AuthorDate: Sat, 17 Oct 2009 17:57:18 +0200
Committer: Ingo Molnar <mingo@elte.hu>
CommitDate: Mon, 19 Oct 2009 09:26:35 +0200
perf tools: Use DECLARE_BITMAP instead of an open-coded array
Use DECLARE_BITMAP instead of an open coded array for our bitmap
of featured sections.
This makes the array an unsigned long instead of a u64 but since
we use a 256 bits bitmap, the array size shouldn't vary between
different boxes.
Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Mike Galbraith <efault@gmx.de>
Cc: Paul Mackerras <paulus@samba.org>
Cc: Steven Rostedt <rostedt@goodmis.org>
LKML-Reference: <1255795038-13751-1-git-send-email-fweisbec@gmail.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
---
| 22 ++++++++-----------
| 11 ++-------
.../util/include/asm/{swab.h => asm-offsets.h} | 0
tools/perf/util/include/linux/types.h | 8 ++++++-
4 files changed, 19 insertions(+), 22 deletions(-)
--git a/tools/perf/util/header.c b/tools/perf/util/header.c
index 171d51b..622c60e 100644
--- a/tools/perf/util/header.c
+++ b/tools/perf/util/header.c
@@ -8,8 +8,6 @@
#include "../perf.h"
#include "trace-event.h"
-#include <linux/bitmap.h>
-
/*
* Create new perf.data header attribute:
*/
@@ -143,12 +141,12 @@ struct perf_file_header {
struct perf_file_section attrs;
struct perf_file_section data;
struct perf_file_section event_types;
- feat_mask_t adds_features;
+ DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
};
void perf_header__feat_trace_info(struct perf_header *header)
{
- set_bit(HEADER_TRACE_INFO, perf_header__adds_mask(header));
+ set_bit(HEADER_TRACE_INFO, header->adds_features);
}
static void do_write(int fd, void *buf, size_t size)
@@ -168,7 +166,7 @@ static void perf_header__adds_write(struct perf_header *self, int fd)
{
struct perf_file_section trace_sec;
u64 cur_offset = lseek(fd, 0, SEEK_CUR);
- unsigned long *feat_mask = perf_header__adds_mask(self);
+ unsigned long *feat_mask = self->adds_features;
if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
/* Write trace info */
@@ -250,7 +248,7 @@ void perf_header__write(struct perf_header *self, int fd)
},
};
- memcpy(&f_header.adds_features, &self->adds_features, sizeof(feat_mask_t));
+ memcpy(&f_header.adds_features, &self->adds_features, sizeof(self->adds_features));
lseek(fd, 0, SEEK_SET);
do_write(fd, &f_header, sizeof(f_header));
@@ -276,7 +274,7 @@ static void do_read(int fd, void *buf, size_t size)
static void perf_header__adds_read(struct perf_header *self, int fd)
{
- const unsigned long *feat_mask = perf_header__adds_mask(self);
+ const unsigned long *feat_mask = self->adds_features;
if (test_bit(HEADER_TRACE_INFO, feat_mask)) {
struct perf_file_section trace_sec;
@@ -306,11 +304,9 @@ struct perf_header *perf_header__read(int fd)
if (f_header.size != sizeof(f_header)) {
/* Support the previous format */
- if (f_header.size == offsetof(typeof(f_header), adds_features)) {
- unsigned long *mask = (unsigned long *)(void *)
- &f_header.adds_features;
- bitmap_zero(mask, HEADER_FEAT_BITS);
- } else
+ if (f_header.size == offsetof(typeof(f_header), adds_features))
+ bitmap_zero(f_header.adds_features, HEADER_FEAT_BITS);
+ else
die("incompatible file format");
}
nr_attrs = f_header.attrs.size / sizeof(f_attr);
@@ -346,7 +342,7 @@ struct perf_header *perf_header__read(int fd)
event_count = f_header.event_types.size / sizeof(struct perf_trace_event_type);
}
- memcpy(&self->adds_features, &f_header.adds_features, sizeof(feat_mask_t));
+ memcpy(&self->adds_features, &f_header.adds_features, sizeof(f_header.adds_features));
perf_header__adds_read(self, fd);
--git a/tools/perf/util/header.h b/tools/perf/util/header.h
index 0eb4a91..2ea9dfb 100644
--- a/tools/perf/util/header.h
+++ b/tools/perf/util/header.h
@@ -5,6 +5,8 @@
#include <sys/types.h>
#include "types.h"
+#include <linux/bitmap.h>
+
struct perf_header_attr {
struct perf_event_attr attr;
int ids, size;
@@ -16,8 +18,6 @@ struct perf_header_attr {
#define HEADER_FEAT_BITS 256
-typedef typeof(u64[HEADER_FEAT_BITS / 8]) feat_mask_t;
-
struct perf_header {
int frozen;
int attrs, size;
@@ -27,14 +27,9 @@ struct perf_header {
u64 data_size;
u64 event_offset;
u64 event_size;
- feat_mask_t adds_features;
+ DECLARE_BITMAP(adds_features, HEADER_FEAT_BITS);
};
-static inline unsigned long *perf_header__adds_mask(struct perf_header *self)
-{
- return (unsigned long *)(void *)&self->adds_features;
-}
-
struct perf_header *perf_header__read(int fd);
void perf_header__write(struct perf_header *self, int fd);
diff --git a/tools/perf/util/include/asm/swab.h b/tools/perf/util/include/asm/asm-offsets.h
similarity index 100%
copy from tools/perf/util/include/asm/swab.h
copy to tools/perf/util/include/asm/asm-offsets.h
diff --git a/tools/perf/util/include/linux/types.h b/tools/perf/util/include/linux/types.h
index ed53894..858a38d 100644
--- a/tools/perf/util/include/linux/types.h
+++ b/tools/perf/util/include/linux/types.h
@@ -1 +1,7 @@
-/* stub */
+#ifndef _PERF_LINUX_TYPES_H_
+#define _PERF_LINUX_TYPES_H_
+
+#define DECLARE_BITMAP(name,bits) \
+ unsigned long name[BITS_TO_LONGS(bits)]
+
+#endif
^ permalink raw reply related [flat|nested] 13+ messages in thread
* Re: [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array
2009-10-19 7:30 ` Ingo Molnar
@ 2009-10-19 19:40 ` Frederic Weisbecker
0 siblings, 0 replies; 13+ messages in thread
From: Frederic Weisbecker @ 2009-10-19 19:40 UTC (permalink / raw)
To: Ingo Molnar
Cc: LKML, Peter Zijlstra, Arnaldo Carvalho de Melo, Mike Galbraith,
Paul Mackerras, Steven Rostedt
On Mon, Oct 19, 2009 at 09:30:39AM +0200, Ingo Molnar wrote:
>
> * Frederic Weisbecker <fweisbec@gmail.com> wrote:
>
> > On Sat, Oct 17, 2009 at 05:57:18PM +0200, Frederic Weisbecker wrote:
> > > Use DECLARE_BITMAP instead of an open coded array for our bitmap
> > > of featured sections.
> > >
> > > This makes the array an unsigned long instead of a u64 but since we
> > > use a 256 bits bitmap, the array size shouldn't vary between
> > > different boxes.
> >
> > That said I would really feel more comfortable if someone can confirm
> > that.
>
> Should be size-invariant for the bitmap size of 256 bits due to:
>
> #define DECLARE_BITMAP(name,bits) \
> unsigned long name[BITS_TO_LONGS(bits)]
>
> but it's not little-endian/big-endian invariant.
>
> We should at minimum save the CPU architecture (and endianness
> parameters) the data got generated on, and reject
> endianness-incompatible uses - so that if someone wants to add
> cross-endian support it can be implemented cleanly.
>
> Ingo
Oh right, I'll add an endianness field then.
Thanks.
^ permalink raw reply [flat|nested] 13+ messages in thread
end of thread, other threads:[~2009-10-19 19:40 UTC | newest]
Thread overview: 13+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-10-15 21:10 [PATCH] perf tools: Add a new generic section in perf.data Frederic Weisbecker
2009-10-16 7:10 ` Ingo Molnar
2009-10-16 7:33 ` Frederic Weisbecker
2009-10-16 7:42 ` Ingo Molnar
2009-10-17 15:12 ` [PATCH 1/2] perf tools: Use kernel bitmap library Frederic Weisbecker
2009-10-19 7:55 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
2009-10-17 15:12 ` [PATCH 2/2] perf tools: Introduce bitmask'ed additional headers Frederic Weisbecker
2009-10-19 7:56 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
2009-10-17 15:57 ` [PATCH 3/2] perf tools: Use DECLARE_BITMAP instead of an open-coded array Frederic Weisbecker
2009-10-17 16:03 ` Frederic Weisbecker
2009-10-19 7:30 ` Ingo Molnar
2009-10-19 19:40 ` Frederic Weisbecker
2009-10-19 7:56 ` [tip:perf/core] " tip-bot for Frederic Weisbecker
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox