diff options
author | Arnaldo Carvalho de Melo <acme@redhat.com> | 2009-07-11 11:18:35 -0400 |
---|---|---|
committer | Ingo Molnar <mingo@elte.hu> | 2009-07-11 13:20:26 -0400 |
commit | 021191b35cdfb1b5ee6e78ed5ae010114a40902c (patch) | |
tree | c683b7a182373158842a50e9ff3ade2424d5eeb8 | |
parent | 27d0fd410c3cee00ece2e55f4354a7a9ec1a6a6a (diff) |
perf report: Make the output more compact
When we filter by column content we may end up with a column
that has the same value for all the lines. So remove that
column and tell its unique value on the top, as a comment.
Example:
[acme@doppio pahole]$ perf report --sort comm,dso,symbol -d ./build/libdwarves.so.1.0.0 -C pahole | head -15
# dso: ./build/libdwarves.so.1.0.0
# comm: pahole
# Samples: 58409
#
# Overhead Symbol
# ........ ......
#
20.93% [.] tag__recode_dwarf_type
14.94% [.] namespace__recode_dwarf_types
10.38% [.] cu__table_add_tag
6.69% [.] __die__process_tag
5.05% [.] die__process_function
4.70% [.] list__for_all_tags
3.68% [.] tag__init
3.48% [.] die__create_new_parameter
[acme@doppio pahole]$
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
LKML-Reference: <1247325517-12272-3-git-send-email-acme@redhat.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
-rw-r--r-- | tools/perf/builtin-report.c | 36 |
1 files changed, 21 insertions, 15 deletions
diff --git a/tools/perf/builtin-report.c b/tools/perf/builtin-report.c index 617f4cb7f163..f3422121d858 100644 --- a/tools/perf/builtin-report.c +++ b/tools/perf/builtin-report.c | |||
@@ -583,6 +583,7 @@ struct sort_entry { | |||
583 | int64_t (*collapse)(struct hist_entry *, struct hist_entry *); | 583 | int64_t (*collapse)(struct hist_entry *, struct hist_entry *); |
584 | size_t (*print)(FILE *fp, struct hist_entry *, unsigned int width); | 584 | size_t (*print)(FILE *fp, struct hist_entry *, unsigned int width); |
585 | unsigned int *width; | 585 | unsigned int *width; |
586 | bool elide; | ||
586 | }; | 587 | }; |
587 | 588 | ||
588 | static int64_t cmp_null(void *l, void *r) | 589 | static int64_t cmp_null(void *l, void *r) |
@@ -1024,7 +1025,7 @@ hist_entry__fprintf(FILE *fp, struct hist_entry *self, u64 total_samples) | |||
1024 | ret = fprintf(fp, field_sep ? "%lld" : "%12lld ", self->count); | 1025 | ret = fprintf(fp, field_sep ? "%lld" : "%12lld ", self->count); |
1025 | 1026 | ||
1026 | list_for_each_entry(se, &hist_entry__sort_list, list) { | 1027 | list_for_each_entry(se, &hist_entry__sort_list, list) { |
1027 | if (exclude_other && (se == &sort_parent)) | 1028 | if (se->elide) |
1028 | continue; | 1029 | continue; |
1029 | 1030 | ||
1030 | fprintf(fp, "%s", field_sep ?: " "); | 1031 | fprintf(fp, "%s", field_sep ?: " "); |
@@ -1079,7 +1080,7 @@ resolve_symbol(struct thread *thread, struct map **mapp, | |||
1079 | * with no symbol hit that has a name longer than | 1080 | * with no symbol hit that has a name longer than |
1080 | * the ones with symbols sampled. | 1081 | * the ones with symbols sampled. |
1081 | */ | 1082 | */ |
1082 | if (!map->dso->slen_calculated) | 1083 | if (!sort_dso.elide && !map->dso->slen_calculated) |
1083 | dso__calc_col_width(map->dso); | 1084 | dso__calc_col_width(map->dso); |
1084 | 1085 | ||
1085 | if (mapp) | 1086 | if (mapp) |
@@ -1356,14 +1357,12 @@ static size_t output__fprintf(FILE *fp, u64 total_samples) | |||
1356 | unsigned int width; | 1357 | unsigned int width; |
1357 | char *col_width = col_width_list_str; | 1358 | char *col_width = col_width_list_str; |
1358 | 1359 | ||
1359 | fprintf(fp, "\n"); | 1360 | fprintf(fp, "# Samples: %Ld\n", (u64)total_samples); |
1360 | fprintf(fp, "#\n"); | ||
1361 | fprintf(fp, "# (%Ld samples)\n", (u64)total_samples); | ||
1362 | fprintf(fp, "#\n"); | 1361 | fprintf(fp, "#\n"); |
1363 | 1362 | ||
1364 | fprintf(fp, "# Overhead"); | 1363 | fprintf(fp, "# Overhead"); |
1365 | list_for_each_entry(se, &hist_entry__sort_list, list) { | 1364 | list_for_each_entry(se, &hist_entry__sort_list, list) { |
1366 | if (exclude_other && (se == &sort_parent)) | 1365 | if (se->elide) |
1367 | continue; | 1366 | continue; |
1368 | if (field_sep) { | 1367 | if (field_sep) { |
1369 | fprintf(fp, "%c%s", *field_sep, se->header); | 1368 | fprintf(fp, "%c%s", *field_sep, se->header); |
@@ -1392,7 +1391,7 @@ static size_t output__fprintf(FILE *fp, u64 total_samples) | |||
1392 | list_for_each_entry(se, &hist_entry__sort_list, list) { | 1391 | list_for_each_entry(se, &hist_entry__sort_list, list) { |
1393 | unsigned int i; | 1392 | unsigned int i; |
1394 | 1393 | ||
1395 | if (exclude_other && (se == &sort_parent)) | 1394 | if (se->elide) |
1396 | continue; | 1395 | continue; |
1397 | 1396 | ||
1398 | fprintf(fp, " "); | 1397 | fprintf(fp, " "); |
@@ -2022,7 +2021,8 @@ static void setup_sorting(void) | |||
2022 | } | 2021 | } |
2023 | 2022 | ||
2024 | static void setup_list(struct strlist **list, const char *list_str, | 2023 | static void setup_list(struct strlist **list, const char *list_str, |
2025 | const char *list_name) | 2024 | struct sort_entry *se, const char *list_name, |
2025 | FILE *fp) | ||
2026 | { | 2026 | { |
2027 | if (list_str) { | 2027 | if (list_str) { |
2028 | *list = strlist__new(true, list_str); | 2028 | *list = strlist__new(true, list_str); |
@@ -2031,6 +2031,11 @@ static void setup_list(struct strlist **list, const char *list_str, | |||
2031 | list_name); | 2031 | list_name); |
2032 | exit(129); | 2032 | exit(129); |
2033 | } | 2033 | } |
2034 | if (strlist__nr_entries(*list) == 1) { | ||
2035 | fprintf(fp, "# %s: %s\n", list_name, | ||
2036 | strlist__entry(*list, 0)->s); | ||
2037 | se->elide = true; | ||
2038 | } | ||
2034 | } | 2039 | } |
2035 | } | 2040 | } |
2036 | 2041 | ||
@@ -2044,9 +2049,10 @@ int cmd_report(int argc, const char **argv, const char *prefix __used) | |||
2044 | 2049 | ||
2045 | setup_sorting(); | 2050 | setup_sorting(); |
2046 | 2051 | ||
2047 | if (parent_pattern != default_parent_pattern) | 2052 | if (parent_pattern != default_parent_pattern) { |
2048 | sort_dimension__add("parent"); | 2053 | sort_dimension__add("parent"); |
2049 | else | 2054 | sort_parent.elide = 1; |
2055 | } else | ||
2050 | exclude_other = 0; | 2056 | exclude_other = 0; |
2051 | 2057 | ||
2052 | /* | 2058 | /* |
@@ -2055,9 +2061,11 @@ int cmd_report(int argc, const char **argv, const char *prefix __used) | |||
2055 | if (argc) | 2061 | if (argc) |
2056 | usage_with_options(report_usage, options); | 2062 | usage_with_options(report_usage, options); |
2057 | 2063 | ||
2058 | setup_list(&dso_list, dso_list_str, "dso"); | 2064 | setup_pager(); |
2059 | setup_list(&comm_list, comm_list_str, "comm"); | 2065 | |
2060 | setup_list(&sym_list, sym_list_str, "symbol"); | 2066 | setup_list(&dso_list, dso_list_str, &sort_dso, "dso", stdout); |
2067 | setup_list(&comm_list, comm_list_str, &sort_comm, "comm", stdout); | ||
2068 | setup_list(&sym_list, sym_list_str, &sort_sym, "symbol", stdout); | ||
2061 | 2069 | ||
2062 | if (field_sep && *field_sep == '.') { | 2070 | if (field_sep && *field_sep == '.') { |
2063 | fputs("'.' is the only non valid --field-separator argument\n", | 2071 | fputs("'.' is the only non valid --field-separator argument\n", |
@@ -2065,7 +2073,5 @@ int cmd_report(int argc, const char **argv, const char *prefix __used) | |||
2065 | exit(129); | 2073 | exit(129); |
2066 | } | 2074 | } |
2067 | 2075 | ||
2068 | setup_pager(); | ||
2069 | |||
2070 | return __cmd_report(); | 2076 | return __cmd_report(); |
2071 | } | 2077 | } |