From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1754845AbaCNOBS (ORCPT ); Fri, 14 Mar 2014 10:01:18 -0400 Received: from mx1.redhat.com ([209.132.183.28]:49090 "EHLO mx1.redhat.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1754784AbaCNOBP (ORCPT ); Fri, 14 Mar 2014 10:01:15 -0400 From: Jiri Olsa To: linux-kernel@vger.kernel.org Cc: Jiri Olsa , Don Zickus , Corey Ashford , David Ahern , Frederic Weisbecker , Ingo Molnar , Namhyung Kim , Paul Mackerras , Peter Zijlstra , Arnaldo Carvalho de Melo Subject: [PATCH 5/5] perf tools: Share process map groups within process threads Date: Fri, 14 Mar 2014 15:00:06 +0100 Message-Id: <1394805606-25883-6-git-send-email-jolsa@redhat.com> In-Reply-To: <1394805606-25883-1-git-send-email-jolsa@redhat.com> References: <1394805606-25883-1-git-send-email-jolsa@redhat.com> Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Sharing map groups within all process threads. This way there's only one copy of mmap info and it's reachale from any thread within the process. Signed-off-by: Jiri Olsa Cc: Don Zickus Cc: Corey Ashford Cc: David Ahern Cc: Frederic Weisbecker Cc: Ingo Molnar Cc: Namhyung Kim Cc: Paul Mackerras Cc: Peter Zijlstra Cc: Arnaldo Carvalho de Melo --- tools/perf/util/map.h | 2 ++ tools/perf/util/thread.c | 37 ++++++++++++++++++++++++++++++++++--- 2 files changed, 36 insertions(+), 3 deletions(-) diff --git a/tools/perf/util/map.h b/tools/perf/util/map.h index 99a6488..d4c8df2 100644 --- a/tools/perf/util/map.h +++ b/tools/perf/util/map.h @@ -59,6 +59,8 @@ struct map_groups { struct rb_root maps[MAP__NR_TYPES]; struct list_head removed_maps[MAP__NR_TYPES]; struct machine *machine; + /* Used for thread sharing */ + int refcnt; }; static inline struct kmap *map__kmap(struct map *map) diff --git a/tools/perf/util/thread.c b/tools/perf/util/thread.c index 7c1aad0..2599754 100644 --- a/tools/perf/util/thread.c +++ b/tools/perf/util/thread.c @@ -156,6 +156,16 @@ int thread__fork(struct thread *thread, struct thread *parent, u64 timestamp) return 0; } +static struct thread* thread__get_leader(struct thread *thread) +{ + pid_t pid = thread->pid_; + + if (pid == thread->tid) + return thread; + + return machine__findnew_thread(thread->machine, pid, pid); +} + static struct map_groups* thread__map_groups_alloc(struct thread *thread) { struct map_groups* mg = zalloc(sizeof(*mg)); @@ -172,13 +182,34 @@ struct map_groups* thread__map_groups_get(struct thread *thread) { struct map_groups* mg = thread->mg; - if (!mg) - mg = thread__map_groups_alloc(thread); + if (!mg) { + struct thread *leader = thread__get_leader(thread); + + if (!leader) + return NULL; + + if (leader->mg) + mg = leader->mg; + else + mg = thread__map_groups_alloc(leader); + + if (leader != thread) + thread->mg = mg; + + mg->refcnt++; + } return mg; } void thread__map_groups_put(struct thread *thread) { - zfree(&thread->mg); + struct map_groups* mg = thread->mg; + + if (mg) { + BUG_ON(!mg->refcnt); + + if (!--mg->refcnt) + zfree(&thread->mg); + } } -- 1.8.3.1