perf tools: Add test_and_set_bit function
Jiri Olsa
reviewerPATCH 1/3 perf tools: Add test_and_set_bit function
Set a bit and return its old value. Stolen from kernel sources, will be used in next patches.
--- tools/perf/util/include/linux/bitmap.h | 17 +++++++++++++++++ tools/perf/util/include/linux/bitops.h | 2 ++ 2 files changed, 19 insertions(+)
tools/perf/util/include/linux/bitmap.h +17 -0
@@ -46,4 +46,21 @@ static inline void bitmap_or(unsigned long *dst, const unsigned long *src1, __bitmap_or(dst, src1, src2, nbits); } +/** +* test_and_set_bit - Set a bit and return its old value +* @nr: Bit to set +* @addr: Address to count from +*/ +static inline int test_and_set_bit (int nr,unsigned long *addr) +{ +unsigned long mask =BIT_MASK (nr); +unsigned long *p = ((unsigned long *)addr) +BIT_WORD (nr); +unsigned long old; + + old = *p; + *p = old | mask; + +return (old & mask) !=0 ; +} +#endif /* _PERF_BITOPS_H */
tools/perf/util/include/linux/bitops.h +2 -0
@@ -15,6 +15,8 @@#define BITS_TO_U64 (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u64))#define BITS_TO_U32 (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u32))#define BITS_TO_BYTES (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE) +#define BIT_WORD (nr) ((nr) / BITS_PER_LONG) +#define BIT_MASK (nr) (1UL << ((nr) % BITS_PER_LONG))#define for_each_set_bit (bit, addr, size) \ for ((bit) = find_first_bit((addr), (size)); \
Signature · 1 line
1.9.3
Jiri Olsa
reviewerPATCH 2/3 perf script perl: Removing event cache as it's no longer needed
We don't need to maintain cache of 'struct event_format' objects. Currently the 'struct perf_evsel' holds this reference already.
Adding events_defined bitmap to keep track of defined events, which is much cheaper than array of pointers.
--- .../perf/util/scripting-engines/trace-event-perl.c | 29 +++++----------------- 1 file changed, 6 insertions(+), 23 deletions(-)
tools/perf/util/scripting-engines/trace-event-perl.c +6 -23
@@ -24,6 +24,7 @@#include <string.h> #include <ctype.h> #include <errno.h> +#include <linux/bitmap.h> #include "../util.h" #include <EXTERN.h>
@@ -57,7 +58,7 @@ INTERP my_perl;#define FTRACE_MAX_EVENT \ ((1 << (sizeof(unsigned short) * 8)) - 1) -struct event_format *events[FTRACE_MAX_EVENT ]; +static DECLARE_BITMAP(events_defined, FTRACE_MAX_EVENT);extern struct scripting_context *scripting_context;
@@ -238,35 +239,15 @@ static void define_event_symbols(struct event_format *event,define_event_symbols (event, ev_name, args->next); } -static inline struct event_format *find_cache_event (struct perf_evsel *evsel) -{ -static char ev_name[256 ]; -struct event_format *event; -int type = evsel->attr.config; - -if (events[type]) -return events[type]; - - events[type] = event = evsel->tp_format; -if (!event) -return NULL ; - -sprintf (ev_name,"%s::%s" , event->system, event->name); - -define_event_symbols (event, ev_name, event->print_fmt.args); - -return event; -} -static void perl_process_tracepoint (struct perf_sample *sample,struct perf_evsel *evsel,struct thread *thread) { +struct event_format *event = evsel->tp_format;struct format_field *field;static char handler[256 ];unsigned long long val;unsigned long s, ns; -struct event_format *event;int pid;int cpu = sample->cpu;void *data = sample->raw_data;
@@ -278,7 +259,6 @@ static void perl_process_tracepoint(struct perf_sample *sample,if (evsel->attr.type !=PERF_TYPE_TRACEPOINT )return ; - event =find_cache_event (evsel);if (!event)die ("ug! no event found for type %" PRIu64, (u64 )evsel->attr.config);
@@ -286,6 +266,9 @@ static void perl_process_tracepoint(struct perf_sample *sample,sprintf (handler,"%s::%s" , event->system, event->name); +if (!test_and_set_bit (event->id, events_defined)) +define_event_symbols (event, handler, event->print_fmt.args); + s = nsecs /NSECS_PER_SEC ; ns = nsecs - s *NSECS_PER_SEC ;
Signature · 1 line
1.9.3
tip-bot for Jiri Olsa
merge bot[tip:perf/core] perf script perl: Removing event cache as it' s no longer needed
perf script perl: Removing event cache as it's no longer needed
Commit-ID: cdae2d1e936457bf72673cb77e7f5f4b9d4c451e Gitweb: http://git.kernel.org/tip/cdae2d1e936457bf72673cb77e7f5f4b9d4c451e Author: Jiri Olsa <[email protected]> AuthorDate: Sun, 26 Oct 2014 23:44:04 +0100 Committer: Arnaldo Carvalho de Melo <[email protected]> CommitDate: Thu, 6 Nov 2014 17:42:47 -0300
perf script perl: Removing event cache as it's no longer needed
We don't need to maintain cache of 'struct event_format' objects. Currently the 'struct perf_evsel' holds this reference already.
Adding events_defined bitmap to keep track of defined events, which is much cheaper than array of pointers.
--- .../perf/util/scripting-engines/trace-event-perl.c | 29 +++++----------------- 1 file changed, 6 insertions(+), 23 deletions(-)
tools/perf/util/scripting-engines/trace-event-perl.c +6 -23
@@ -24,6 +24,7 @@#include <string.h> #include <ctype.h> #include <errno.h> +#include <linux/bitmap.h> #include "../util.h" #include <EXTERN.h>
@@ -57,7 +58,7 @@ INTERP my_perl;#define FTRACE_MAX_EVENT \ ((1 << (sizeof(unsigned short) * 8)) - 1) -struct event_format *events[FTRACE_MAX_EVENT ]; +static DECLARE_BITMAP(events_defined, FTRACE_MAX_EVENT);extern struct scripting_context *scripting_context;
@@ -238,35 +239,15 @@ static void define_event_symbols(struct event_format *event,define_event_symbols (event, ev_name, args->next); } -static inline struct event_format *find_cache_event (struct perf_evsel *evsel) -{ -static char ev_name[256 ]; -struct event_format *event; -int type = evsel->attr.config; - -if (events[type]) -return events[type]; - - events[type] = event = evsel->tp_format; -if (!event) -return NULL ; - -sprintf (ev_name,"%s::%s" , event->system, event->name); - -define_event_symbols (event, ev_name, event->print_fmt.args); - -return event; -} -static void perl_process_tracepoint (struct perf_sample *sample,struct perf_evsel *evsel,struct thread *thread) { +struct event_format *event = evsel->tp_format;struct format_field *field;static char handler[256 ];unsigned long long val;unsigned long s, ns; -struct event_format *event;int pid;int cpu = sample->cpu;void *data = sample->raw_data;
@@ -278,7 +259,6 @@ static void perl_process_tracepoint(struct perf_sample *sample,if (evsel->attr.type !=PERF_TYPE_TRACEPOINT )return ; - event =find_cache_event (evsel);if (!event)die ("ug! no event found for type %" PRIu64, (u64 )evsel->attr.config);
@@ -286,6 +266,9 @@ static void perl_process_tracepoint(struct perf_sample *sample,sprintf (handler,"%s::%s" , event->system, event->name); +if (!test_and_set_bit (event->id, events_defined)) +define_event_symbols (event, handler, event->print_fmt.args); + s = nsecs /NSECS_PER_SEC ; ns = nsecs - s *NSECS_PER_SEC ;
Jiri Olsa
reviewerPATCH 3/3 perf script python: Removing event cache as it's no longer needed
In reply to Jiri OlsaWe don't need to maintain cache of 'struct event_format' objects. Currently the 'struct perf_evsel' holds this reference already.
Adding events_defined bitmap to keep track of defined events, which is much cheaper than array of pointers.
--- .../util/scripting-engines/trace-event-python.c | 34 ++++------------------ 1 file changed, 6 insertions(+), 28 deletions(-)
tools/perf/util/scripting-engines/trace-event-python.c +6 -28
@@ -26,6 +26,7 @@#include <string.h> #include <stdbool.h> #include <errno.h> +#include <linux/bitmap.h> #include "../../perf.h" #include "../debug.h"
@@ -45,7 +46,7 @@ PyMODINIT_FUNC initperf_trace_context(void);#define FTRACE_MAX_EVENT \ ((1 << (sizeof(unsigned short) * 8)) - 1) -struct event_format *events[FTRACE_MAX_EVENT ]; +static DECLARE_BITMAP(events_defined, FTRACE_MAX_EVENT);#define MAX_FIELDS 64#define N_COMMON_FIELDS 7
@@ -251,31 +252,6 @@ static void define_event_symbols(struct event_format *event,define_event_symbols (event, ev_name, args->next); } -static inline struct event_format *find_cache_event (struct perf_evsel *evsel) -{ -static char ev_name[256 ]; -struct event_format *event; -int type = evsel->attr.config; - -/* -* XXX: Do we really need to cache this since now we have evsel->tp_format -* cached already? Need to re-read this "cache" routine that as well calls -* define_event_symbols() :-\ -*/ -if (events[type]) -return events[type]; - - events[type] = event = evsel->tp_format; -if (!event) -return NULL ; - -sprintf (ev_name,"%s__%s" , event->system, event->name); - -define_event_symbols (event, ev_name, event->print_fmt.args); - -return event; -} -static PyObject *get_field_numeric_entry (struct event_format *event,struct format_field *field,void *data) {
@@ -399,12 +375,12 @@ static void python_process_tracepoint(struct perf_sample *sample,struct thread *thread, struct addr_location *al) { + struct event_format *event = evsel->tp_format;PyObject *handler, *context, *t, *obj, *callchain;PyObject *dict =NULL ;static char handler_name[256 ];struct format_field *field;unsigned long s, ns; -struct event_format *event;unsigned n =0 ;int pid;int cpu = sample->cpu;
@@ -416,7 +392,6 @@ static void python_process_tracepoint(struct perf_sample *sample,if (!t)Py_FatalError ("couldn't create Python tuple" ); - event =find_cache_event (evsel);if (!event)die ("ug! no event found for type %d" , (int )evsel->attr.config);
@@ -424,6 +399,9 @@ static void python_process_tracepoint(struct perf_sample *sample,sprintf (handler_name,"%s__%s" , event->system, event->name); +if (!test_and_set_bit (event->id, events_defined)) +define_event_symbols (event, handler_name, event->print_fmt.args); + handler =get_handler (handler_name);if (!handler) { dict =PyDict_New ();
Signature · 1 line
1.9.3
tip-bot for Jiri Olsa
merge bot[tip:perf/core] perf script python: Removing event cache as it' s no longer needed
perf script python: Removing event cache as it's no longer needed
Commit-ID: adf5bcf39583c4db1bf30069f8957400e61ccb18 Gitweb: http://git.kernel.org/tip/adf5bcf39583c4db1bf30069f8957400e61ccb18 Author: Jiri Olsa <[email protected]> AuthorDate: Sun, 26 Oct 2014 23:44:05 +0100 Committer: Arnaldo Carvalho de Melo <[email protected]> CommitDate: Thu, 6 Nov 2014 17:44:06 -0300
perf script python: Removing event cache as it's no longer needed
We don't need to maintain cache of 'struct event_format' objects. Currently the 'struct perf_evsel' holds this reference already.
Adding events_defined bitmap to keep track of defined events, which is much cheaper than array of pointers.
--- .../util/scripting-engines/trace-event-python.c | 34 ++++------------------ 1 file changed, 6 insertions(+), 28 deletions(-)
tools/perf/util/scripting-engines/trace-event-python.c +6 -28
@@ -26,6 +26,7 @@#include <string.h> #include <stdbool.h> #include <errno.h> +#include <linux/bitmap.h> #include "../../perf.h" #include "../debug.h"
@@ -46,7 +47,7 @@ PyMODINIT_FUNC initperf_trace_context(void);#define FTRACE_MAX_EVENT \ ((1 << (sizeof(unsigned short) * 8)) - 1) -struct event_format *events[FTRACE_MAX_EVENT ]; +static DECLARE_BITMAP(events_defined, FTRACE_MAX_EVENT);#define MAX_FIELDS 64#define N_COMMON_FIELDS 7
@@ -255,31 +256,6 @@ static void define_event_symbols(struct event_format *event,define_event_symbols (event, ev_name, args->next); } -static inline struct event_format *find_cache_event (struct perf_evsel *evsel) -{ -static char ev_name[256 ]; -struct event_format *event; -int type = evsel->attr.config; - -/* -* XXX: Do we really need to cache this since now we have evsel->tp_format -* cached already? Need to re-read this "cache" routine that as well calls -* define_event_symbols() :-\ -*/ -if (events[type]) -return events[type]; - - events[type] = event = evsel->tp_format; -if (!event) -return NULL ; - -sprintf (ev_name,"%s__%s" , event->system, event->name); - -define_event_symbols (event, ev_name, event->print_fmt.args); - -return event; -} -static PyObject *get_field_numeric_entry (struct event_format *event,struct format_field *field,void *data) {
@@ -403,12 +379,12 @@ static void python_process_tracepoint(struct perf_sample *sample,struct thread *thread, struct addr_location *al) { + struct event_format *event = evsel->tp_format;PyObject *handler, *context, *t, *obj, *callchain;PyObject *dict =NULL ;static char handler_name[256 ];struct format_field *field;unsigned long s, ns; -struct event_format *event;unsigned n =0 ;int pid;int cpu = sample->cpu;
@@ -420,7 +396,6 @@ static void python_process_tracepoint(struct perf_sample *sample,if (!t)Py_FatalError ("couldn't create Python tuple" ); - event =find_cache_event (evsel);if (!event)die ("ug! no event found for type %d" , (int )evsel->attr.config);
@@ -428,6 +403,9 @@ static void python_process_tracepoint(struct perf_sample *sample,sprintf (handler_name,"%s__%s" , event->system, event->name); +if (!test_and_set_bit (event->id, events_defined)) +define_event_symbols (event, handler_name, event->print_fmt.args); + handler =get_handler (handler_name);if (!handler) { dict =PyDict_New ();
Hi Jiri,
Quoted 11 lines · Jiri Olsa
Set a bit and return its old value. Stolen from kernel sources, will be used in next patches.
Cc Adrian Hunter <[email protected]>Cc Arnaldo Carvalho de Melo <[email protected]>Cc David Ahern <[email protected]>Cc Frederic Weisbecker <[email protected]>Cc Ingo Molnar <[email protected]>Cc Paul Mackerras <[email protected]>Cc Peter Zijlstra <[email protected]>Signed-off-by Jiri Olsa <[email protected]>
For all 3 patches,
Thanks,
Namhyung
Quoted 44 lines
--- tools/perf/util/include/linux/bitmap.h | 17 +++++++++++++++++ tools/perf/util/include/linux/bitops.h | 2 ++ 2 files changed, 19 insertions(+)tools/perf/util/include/linux/bitmap.h +17
-0@@ -46,4 +46,21 @@ static inline void bitmap_or(unsigned long *dst, const unsigned long *src1, __bitmap_or(dst, src1, src2, nbits); } +/** +* test_and_set_bit - Set a bit and return its old value +* @nr: Bit to set +* @addr: Address to count from +*/ +static inline int test_and_set_bit (int nr,unsigned long *addr) +{ +unsigned long mask =BIT_MASK (nr); +unsigned long *p = ((unsigned long *)addr) +BIT_WORD (nr); +unsigned long old; + + old = *p; + *p = old | mask; + +return (old & mask) !=0 ; +} +#endif /* _PERF_BITOPS_H */ tools/perf/util/include/linux/bitops.h +2
-0@@ -15,6 +15,8 @@#define BITS_TO_U64 (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u64))#define BITS_TO_U32 (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u32))#define BITS_TO_BYTES (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE) +#define BIT_WORD (nr) ((nr) / BITS_PER_LONG) +#define BIT_MASK (nr) (1UL << ((nr) % BITS_PER_LONG))#define for_each_set_bit (bit, addr, size) \ for ((bit) = find_first_bit((addr), (size)); \
tip-bot for Jiri Olsa
merge botperf tools: Add test_and_set_bit function
Commit-ID: 416c419cc3799ddf7ea467c9adcb4cd038bd94a4 Gitweb: http://git.kernel.org/tip/416c419cc3799ddf7ea467c9adcb4cd038bd94a4 Author: Jiri Olsa <[email protected]> AuthorDate: Sun, 26 Oct 2014 23:44:03 +0100 Committer: Arnaldo Carvalho de Melo <[email protected]> CommitDate: Thu, 6 Nov 2014 17:42:13 -0300
perf tools: Add test_and_set_bit function
Set a bit and return its old value. Stolen from kernel sources, will be used in next patches.
--- tools/perf/util/include/linux/bitmap.h | 17 +++++++++++++++++ tools/perf/util/include/linux/bitops.h | 2 ++ 2 files changed, 19 insertions(+)
tools/perf/util/include/linux/bitmap.h +17 -0
@@ -46,4 +46,21 @@ static inline void bitmap_or(unsigned long *dst, const unsigned long *src1, __bitmap_or(dst, src1, src2, nbits); } +/** +* test_and_set_bit - Set a bit and return its old value +* @nr: Bit to set +* @addr: Address to count from +*/ +static inline int test_and_set_bit (int nr,unsigned long *addr) +{ +unsigned long mask =BIT_MASK (nr); +unsigned long *p = ((unsigned long *)addr) +BIT_WORD (nr); +unsigned long old; + + old = *p; + *p = old | mask; + +return (old & mask) !=0 ; +} +#endif /* _PERF_BITOPS_H */
tools/perf/util/include/linux/bitops.h +2 -0
@@ -15,6 +15,8 @@#define BITS_TO_U64 (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u64))#define BITS_TO_U32 (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u32))#define BITS_TO_BYTES (nr) DIV_ROUND_UP(nr, BITS_PER_BYTE) +#define BIT_WORD (nr) ((nr) / BITS_PER_LONG) +#define BIT_MASK (nr) (1UL << ((nr) % BITS_PER_LONG))#define for_each_set_bit (bit, addr, size) \ for ((bit) = find_first_bit((addr), (size)); \