Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752355AbbHaShV (ORCPT ); Mon, 31 Aug 2015 14:37:21 -0400 Received: from mga01.intel.com ([192.55.52.88]:16618 "EHLO mga01.intel.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751701AbbHaShS (ORCPT ); Mon, 31 Aug 2015 14:37:18 -0400 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.17,442,1437462000"; d="scan'208";a="794799465" From: Kan Liang To: acme@kernel.org, jolsa@kernel.org Cc: ak@linux.intel.com, linux-kernel@vger.kernel.org, Kan Liang Subject: [PATCH V3 2/3] perf,tools: store cpu socket_id and core_id in perf.date Date: Mon, 31 Aug 2015 07:21:21 -0400 Message-Id: <1441020082-6345-2-git-send-email-kan.liang@intel.com> X-Mailer: git-send-email 1.8.3.1 In-Reply-To: <1441020082-6345-1-git-send-email-kan.liang@intel.com> References: <1441020082-6345-1-git-send-email-kan.liang@intel.com> Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Length: 6004 Lines: 228 From: Kan Liang This patch stores cpu socket_id and core_id in perf.date, and read them to perf_env in header process. Although the changes modify the CPU_TOPOLOGY feature, the old perf still can correctly read new perf.data. Because the new codes are added at the end of the cpu_topology section. The old perf can ignore the extra data. For reading old perf.data, new perf will error out and leave message in debug mode. So the user can upgrade the perf accordingly. Signed-off-by: Kan Liang --- Changes since V1: - Store core_id and socket_id in perf.date Changes since V2: - Use funcitons in cpumap.c to get core_id and socket_id - Modify changelog tools/perf/util/header.c | 72 ++++++++++++++++++++++++++++++++++++++++++++--- tools/perf/util/header.h | 6 ++++ tools/perf/util/session.c | 1 + 3 files changed, 75 insertions(+), 4 deletions(-) diff --git a/tools/perf/util/header.c b/tools/perf/util/header.c index 4181454..a1451f3 100644 --- a/tools/perf/util/header.c +++ b/tools/perf/util/header.c @@ -441,10 +441,13 @@ static int write_cmdline(int fd, struct perf_header *h __maybe_unused, "/sys/devices/system/cpu/cpu%d/topology/thread_siblings_list" struct cpu_topo { + u32 cpu_nr; u32 core_sib; u32 thread_sib; char **core_siblings; char **thread_siblings; + int *core_id; + int *phy_pkg_id; }; static int build_cpu_topo(struct cpu_topo *tp, int cpu) @@ -507,6 +510,9 @@ try_threads: } ret = 0; done: + tp->core_id[cpu] = cpu_map__get_core_id(cpu); + tp->phy_pkg_id[cpu] = cpu_map__get_socket_id(cpu); + if(fp) fclose(fp); free(buf); @@ -534,7 +540,7 @@ static struct cpu_topo *build_cpu_topology(void) struct cpu_topo *tp; void *addr; u32 nr, i; - size_t sz; + size_t sz, sz_id; long ncpus; int ret = -1; @@ -545,17 +551,22 @@ static struct cpu_topo *build_cpu_topology(void) nr = (u32)(ncpus & UINT_MAX); sz = nr * sizeof(char *); + sz_id = nr * sizeof(int); - addr = calloc(1, sizeof(*tp) + 2 * sz); + addr = calloc(1, sizeof(*tp) + 2 * sz + 2 * sz_id); if (!addr) return NULL; tp = addr; - + tp->cpu_nr = nr; addr += sizeof(*tp); tp->core_siblings = addr; addr += sz; tp->thread_siblings = addr; + addr += sz; + tp->core_id = addr; + addr += sz_id; + tp->phy_pkg_id = addr; for (i = 0; i < nr; i++) { ret = build_cpu_topo(tp, i); @@ -598,6 +609,15 @@ static int write_cpu_topology(int fd, struct perf_header *h __maybe_unused, if (ret < 0) break; } + + for (i = 0; i < tp->cpu_nr; i++) { + ret = do_write(fd, &tp->core_id[i], sizeof(int)); + if (ret < 0) + return ret; + ret = do_write(fd, &tp->phy_pkg_id[i], sizeof(int)); + if (ret < 0) + return ret; + } done: free_cpu_topo(tp); return ret; @@ -938,6 +958,7 @@ static void print_cpu_topology(struct perf_header *ph, int fd __maybe_unused, { int nr, i; char *str; + int cpu_nr = ph->env.nr_cpus_online; nr = ph->env.nr_sibling_cores; str = ph->env.sibling_cores; @@ -954,6 +975,10 @@ static void print_cpu_topology(struct perf_header *ph, int fd __maybe_unused, fprintf(fp, "# sibling threads : %s\n", str); str += strlen(str) + 1; } + + for (i = 0; i < cpu_nr; i++) + fprintf(fp, "# CPU %d: Core ID %d, Socket ID %d\n", i, + ph->env.cpu[i].core_id, ph->env.cpu[i].socket_id); } static void free_event_desc(struct perf_evsel *events) @@ -1590,10 +1615,15 @@ static int process_cpu_topology(struct perf_file_section *section __maybe_unused u32 nr, i; char *str; struct strbuf sb; + int cpu_nr = ph->env.nr_cpus_online; + + ph->env.cpu = calloc(cpu_nr, sizeof(*ph->env.cpu)); + if (!ph->env.cpu) + return -1; ret = readn(fd, &nr, sizeof(nr)); if (ret != sizeof(nr)) - return -1; + goto free_cpu; if (ph->needs_swap) nr = bswap_32(nr); @@ -1631,10 +1661,44 @@ static int process_cpu_topology(struct perf_file_section *section __maybe_unused free(str); } ph->env.sibling_threads = strbuf_detach(&sb, NULL); + + for (i = 0; i < (u32)cpu_nr; i++) { + ret = readn(fd, &nr, sizeof(nr)); + if (ret != sizeof(nr)) + goto free_cpu; + + if (ph->needs_swap) + nr = bswap_32(nr); + + if (nr > (u32)cpu_nr) { + pr_debug("core_id number is too big." + "You may need to upgrade the perf tool.\n"); + goto free_cpu; + } + ph->env.cpu[i].core_id = nr; + + ret = readn(fd, &nr, sizeof(nr)); + if (ret != sizeof(nr)) + goto free_cpu; + + if (ph->needs_swap) + nr = bswap_32(nr); + + if (nr > (u32)cpu_nr) { + pr_debug("socket_id number is too big." + "You may need to upgrade the perf tool.\n"); + goto free_cpu; + } + + ph->env.cpu[i].socket_id = nr; + } + return 0; error: strbuf_release(&sb); +free_cpu: + free(ph->env.cpu); return -1; } diff --git a/tools/perf/util/header.h b/tools/perf/util/header.h index 396e496..975d803 100644 --- a/tools/perf/util/header.h +++ b/tools/perf/util/header.h @@ -66,6 +66,11 @@ struct perf_header; int perf_file_header__read(struct perf_file_header *header, struct perf_header *ph, int fd); +struct cpu_topology_map { + int socket_id; + int core_id; +}; + struct perf_env { char *hostname; char *os_release; @@ -89,6 +94,7 @@ struct perf_env { char *sibling_threads; char *numa_nodes; char *pmu_mappings; + struct cpu_topology_map *cpu; }; struct perf_header { diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c index 8a4537e..61669be 100644 --- a/tools/perf/util/session.c +++ b/tools/perf/util/session.c @@ -185,6 +185,7 @@ static void perf_session_env__exit(struct perf_env *env) zfree(&env->sibling_threads); zfree(&env->numa_nodes); zfree(&env->pmu_mappings); + zfree(&env->cpu); } void perf_session__delete(struct perf_session *session) -- 1.8.3.1 -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/