Messages in this thread Patch in this message | | | From | Shaohua Li <> | Subject | [PATCH 2/2 --resend] perf: update userspace page info for software event | Date | Thu, 5 Feb 2015 15:55:32 -0800 |
| |
For hardware event, the userspace page of the event gets updated in context switch, so if we read time in the page, we get updated info. For software event, this is missed currently. This patch makes the behavior consistency.
With this patch, we can implement clock_gettime(THREAD_CPUTIME) with PERF_COUNT_SW_DUMMY in userspace as suggested by Andy and Peter. Code likes this:
if (pc->cap_user_time) { do { seq = pc->lock; barrier();
running = pc->time_running; cyc = rdtsc(); time_mult = pc->time_mult; time_shift = pc->time_shift; time_offset = pc->time_offset;
barrier(); } while (pc->lock != seq);
quot = (cyc >> time_shift); rem = cyc & ((1 << time_shift) - 1); delta = time_offset + quot * time_mult + ((rem * time_mult) >> time_shift);
running += delta; return running; }
I tried in a busy system, the userspace page updating hasn't noticeable overhead.
Cc: Arnaldo Carvalho de Melo <acme@redhat.com> Cc: Frederic Weisbecker <fweisbec@gmail.com> Cc: Paul Mackerras <paulus@samba.org> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Andy Lutomirski <luto@amacapital.net> Cc: Ingo Molnar <mingo@kernel.org> Signed-off-by: Shaohua Li <shli@fb.com> --- kernel/events/core.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/kernel/events/core.c b/kernel/events/core.c index 04d8b48..98105cf 100644 --- a/kernel/events/core.c +++ b/kernel/events/core.c @@ -5950,6 +5950,7 @@ static int perf_swevent_add(struct perf_event *event, int flags) } hlist_add_head_rcu(&event->hlist_entry, head); + perf_event_update_userpage(event); return 0; } @@ -6419,6 +6420,7 @@ static int cpu_clock_event_add(struct perf_event *event, int flags) { if (flags & PERF_EF_START) cpu_clock_event_start(event, flags); + perf_event_update_userpage(event); return 0; } @@ -6493,6 +6495,7 @@ static int task_clock_event_add(struct perf_event *event, int flags) { if (flags & PERF_EF_START) task_clock_event_start(event, flags); + perf_event_update_userpage(event); return 0; } -- 1.8.1
| |