Skip to content

Commit

Permalink
Merge tag 'perf-core-for-mingo-4.18-20180519' of git://git.kernel.org…
Browse files Browse the repository at this point in the history
…/pub/scm/linux/kernel/git/acme/linux into perf/core

Pull perf/core improvements and fixes from Arnaldo Carvalho de Melo:

- Record min/max LBR cycles (>= Skylake) and add 'perf annotate' TUI
  hotkey to show it (c) (Jin Yao)

- Fix machine->kernel_start for PTI on x86 (Adrian Hunter)

- Make machine->env->arch always available, e.g. in 'perf top', not
  just when reading that info from perf.data files (Adrian Hunter)

- Reduce the number of files read at 'perf' start, leaving information such as
  cacheline size, tracefs mount point determination, max_stack, etc, to be
  lazily read as tools needs then (Arnaldo Carvalho de Melo)

- Fix up BPF include and examples install messages (Arnaldo Carvalho de Melo)

- Fix up callchain addresses and symbol offsets in 'perf script', to help
  correlating with objdump output (Sandipan Das)

Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Signed-off-by: Ingo Molnar <mingo@kernel.org>
  • Loading branch information
Ingo Molnar committed May 19, 2018
2 parents 5aafae8 + 19422a9 commit 2996123
Show file tree
Hide file tree
Showing 28 changed files with 279 additions and 120 deletions.
3 changes: 3 additions & 0 deletions tools/include/linux/compiler-gcc.h
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@
/* &a[0] degrades to a pointer: a different type from an array */
#define __must_be_array(a) BUILD_BUG_ON_ZERO(__same_type((a), &(a)[0]))

#ifndef __pure
#define __pure __attribute__((pure))
#endif
#define noinline __attribute__((noinline))
#ifndef __packed
#define __packed __attribute__((packed))
Expand Down
40 changes: 33 additions & 7 deletions tools/lib/api/fs/tracing_path.c
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,9 @@

#include "tracing_path.h"


char tracing_mnt[PATH_MAX] = "/sys/kernel/debug";
char tracing_path[PATH_MAX] = "/sys/kernel/debug/tracing";
char tracing_events_path[PATH_MAX] = "/sys/kernel/debug/tracing/events";

static char tracing_mnt[PATH_MAX] = "/sys/kernel/debug";
static char tracing_path[PATH_MAX] = "/sys/kernel/debug/tracing";
static char tracing_events_path[PATH_MAX] = "/sys/kernel/debug/tracing/events";

static void __tracing_path_set(const char *tracing, const char *mountpoint)
{
Expand Down Expand Up @@ -76,7 +74,7 @@ char *get_tracing_file(const char *name)
{
char *file;

if (asprintf(&file, "%s/%s", tracing_path, name) < 0)
if (asprintf(&file, "%s/%s", tracing_path_mount(), name) < 0)
return NULL;

return file;
Expand All @@ -87,6 +85,34 @@ void put_tracing_file(char *file)
free(file);
}

char *get_events_file(const char *name)
{
char *file;

if (asprintf(&file, "%s/events/%s", tracing_path_mount(), name) < 0)
return NULL;

return file;
}

void put_events_file(char *file)
{
free(file);
}

DIR *tracing_events__opendir(void)
{
DIR *dir = NULL;
char *path = get_tracing_file("events");

if (path) {
dir = opendir(path);
put_events_file(path);
}

return dir;
}

int tracing_path__strerror_open_tp(int err, char *buf, size_t size,
const char *sys, const char *name)
{
Expand Down Expand Up @@ -129,7 +155,7 @@ int tracing_path__strerror_open_tp(int err, char *buf, size_t size,
snprintf(buf, size,
"Error:\tNo permissions to read %s/%s\n"
"Hint:\tTry 'sudo mount -o remount,mode=755 %s'\n",
tracing_events_path, filename, tracing_mnt);
tracing_events_path, filename, tracing_path_mount());
}
break;
default:
Expand Down
9 changes: 7 additions & 2 deletions tools/lib/api/fs/tracing_path.h
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,20 @@
#define __API_FS_TRACING_PATH_H

#include <linux/types.h>
#include <dirent.h>

extern char tracing_path[];
extern char tracing_events_path[];
DIR *tracing_events__opendir(void);

void tracing_path_set(const char *mountpoint);
const char *tracing_path_mount(void);

char *get_tracing_file(const char *name);
void put_tracing_file(char *file);

char *get_events_file(const char *name);
void put_events_file(char *file);

#define zput_events_file(ptr) ({ free(*ptr); *ptr = NULL; })

int tracing_path__strerror_open_tp(int err, char *buf, size_t size, const char *sys, const char *name);
#endif /* __API_FS_TRACING_PATH_H */
2 changes: 2 additions & 0 deletions tools/perf/Makefile.perf
Original file line number Diff line number Diff line change
Expand Up @@ -770,9 +770,11 @@ endif
ifndef NO_LIBBPF
$(call QUIET_INSTALL, lib) \
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf'
$(call QUIET_INSTALL, include/bpf) \
$(INSTALL) include/bpf/*.h '$(DESTDIR_SQ)$(perf_include_instdir_SQ)/bpf'
$(call QUIET_INSTALL, lib) \
$(INSTALL) -d -m 755 '$(DESTDIR_SQ)$(perf_examples_instdir_SQ)/bpf'
$(call QUIET_INSTALL, examples/bpf) \
$(INSTALL) examples/bpf/*.c '$(DESTDIR_SQ)$(perf_examples_instdir_SQ)/bpf'
endif
$(call QUIET_INSTALL, perf-archive) \
Expand Down
26 changes: 14 additions & 12 deletions tools/perf/builtin-script.c
Original file line number Diff line number Diff line change
Expand Up @@ -153,8 +153,8 @@ static struct {
.fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
PERF_OUTPUT_PERIOD,
PERF_OUTPUT_SYM | PERF_OUTPUT_SYMOFFSET |
PERF_OUTPUT_DSO | PERF_OUTPUT_PERIOD,

.invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
},
Expand All @@ -165,8 +165,9 @@ static struct {
.fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
PERF_OUTPUT_PERIOD | PERF_OUTPUT_BPF_OUTPUT,
PERF_OUTPUT_SYM | PERF_OUTPUT_SYMOFFSET |
PERF_OUTPUT_DSO | PERF_OUTPUT_PERIOD |
PERF_OUTPUT_BPF_OUTPUT,

.invalid_fields = PERF_OUTPUT_TRACE,
},
Expand All @@ -185,10 +186,10 @@ static struct {
.fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
PERF_OUTPUT_PERIOD | PERF_OUTPUT_ADDR |
PERF_OUTPUT_DATA_SRC | PERF_OUTPUT_WEIGHT |
PERF_OUTPUT_PHYS_ADDR,
PERF_OUTPUT_SYM | PERF_OUTPUT_SYMOFFSET |
PERF_OUTPUT_DSO | PERF_OUTPUT_PERIOD |
PERF_OUTPUT_ADDR | PERF_OUTPUT_DATA_SRC |
PERF_OUTPUT_WEIGHT | PERF_OUTPUT_PHYS_ADDR,

.invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
},
Expand All @@ -199,8 +200,8 @@ static struct {
.fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
PERF_OUTPUT_PERIOD,
PERF_OUTPUT_SYM | PERF_OUTPUT_SYMOFFSET |
PERF_OUTPUT_DSO | PERF_OUTPUT_PERIOD,

.invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
},
Expand All @@ -211,8 +212,8 @@ static struct {
.fields = PERF_OUTPUT_COMM | PERF_OUTPUT_TID |
PERF_OUTPUT_CPU | PERF_OUTPUT_TIME |
PERF_OUTPUT_EVNAME | PERF_OUTPUT_IP |
PERF_OUTPUT_SYM | PERF_OUTPUT_DSO |
PERF_OUTPUT_SYNTH,
PERF_OUTPUT_SYM | PERF_OUTPUT_SYMOFFSET |
PERF_OUTPUT_DSO | PERF_OUTPUT_SYNTH,

.invalid_fields = PERF_OUTPUT_TRACE | PERF_OUTPUT_BPF_OUTPUT,
},
Expand Down Expand Up @@ -544,6 +545,7 @@ static int perf_session__check_output_opt(struct perf_session *session)
if (attr->sample_type & PERF_SAMPLE_CALLCHAIN) {
output[j].fields |= PERF_OUTPUT_IP;
output[j].fields |= PERF_OUTPUT_SYM;
output[j].fields |= PERF_OUTPUT_SYMOFFSET;
output[j].fields |= PERF_OUTPUT_DSO;
set_print_ip_opts(attr);
goto out;
Expand Down
2 changes: 1 addition & 1 deletion tools/perf/builtin-top.c
Original file line number Diff line number Diff line change
Expand Up @@ -1264,7 +1264,7 @@ int cmd_top(int argc, const char **argv)
.proc_map_timeout = 500,
.overwrite = 1,
},
.max_stack = sysctl_perf_event_max_stack,
.max_stack = sysctl__max_stack(),
.sym_pcnt_filter = 5,
.nr_threads_synthesize = UINT_MAX,
};
Expand Down
2 changes: 1 addition & 1 deletion tools/perf/builtin-trace.c
Original file line number Diff line number Diff line change
Expand Up @@ -3162,7 +3162,7 @@ int cmd_trace(int argc, const char **argv)
mmap_pages_user_set = false;

if (trace.max_stack == UINT_MAX) {
trace.max_stack = input_name ? PERF_MAX_STACK_DEPTH : sysctl_perf_event_max_stack;
trace.max_stack = input_name ? PERF_MAX_STACK_DEPTH : sysctl__max_stack();
max_stack_user_set = false;
}

Expand Down
24 changes: 1 addition & 23 deletions tools/perf/perf.c
Original file line number Diff line number Diff line change
Expand Up @@ -238,7 +238,7 @@ static int handle_options(const char ***argv, int *argc, int *envchanged)
(*argc)--;
} else if (strstarts(cmd, CMD_DEBUGFS_DIR)) {
tracing_path_set(cmd + strlen(CMD_DEBUGFS_DIR));
fprintf(stderr, "dir: %s\n", tracing_path);
fprintf(stderr, "dir: %s\n", tracing_path_mount());
if (envchanged)
*envchanged = 1;
} else if (!strcmp(cmd, "--list-cmds")) {
Expand Down Expand Up @@ -421,52 +421,30 @@ void pthread__unblock_sigwinch(void)
pthread_sigmask(SIG_UNBLOCK, &set, NULL);
}

#ifdef _SC_LEVEL1_DCACHE_LINESIZE
#define cache_line_size(cacheline_sizep) *cacheline_sizep = sysconf(_SC_LEVEL1_DCACHE_LINESIZE)
#else
static void cache_line_size(int *cacheline_sizep)
{
if (sysfs__read_int("devices/system/cpu/cpu0/cache/index0/coherency_line_size", cacheline_sizep))
pr_debug("cannot determine cache line size");
}
#endif

int main(int argc, const char **argv)
{
int err;
const char *cmd;
char sbuf[STRERR_BUFSIZE];
int value;

/* libsubcmd init */
exec_cmd_init("perf", PREFIX, PERF_EXEC_PATH, EXEC_PATH_ENVIRONMENT);
pager_init(PERF_PAGER_ENVIRONMENT);

/* The page_size is placed in util object. */
page_size = sysconf(_SC_PAGE_SIZE);
cache_line_size(&cacheline_size);

if (sysctl__read_int("kernel/perf_event_max_stack", &value) == 0)
sysctl_perf_event_max_stack = value;

if (sysctl__read_int("kernel/perf_event_max_contexts_per_stack", &value) == 0)
sysctl_perf_event_max_contexts_per_stack = value;

cmd = extract_argv0_path(argv[0]);
if (!cmd)
cmd = "perf-help";

srandom(time(NULL));

perf_config__init();
err = perf_config(perf_default_config, NULL);
if (err)
return err;
set_buildid_dir(NULL);

/* get debugfs/tracefs mount point from /proc/mounts */
tracing_path_mount();

/*
* "perf-xxxx" is the same as "perf xxxx", but we obviously:
*
Expand Down
9 changes: 5 additions & 4 deletions tools/perf/tests/parse-events.c
Original file line number Diff line number Diff line change
Expand Up @@ -1323,12 +1323,12 @@ static int count_tracepoints(void)
DIR *events_dir;
int cnt = 0;

events_dir = opendir(tracing_events_path);
events_dir = tracing_events__opendir();

TEST_ASSERT_VAL("Can't open events dir", events_dir);

while ((events_ent = readdir(events_dir))) {
char sys_path[PATH_MAX];
char *sys_path;
struct dirent *sys_ent;
DIR *sys_dir;

Expand All @@ -1339,8 +1339,8 @@ static int count_tracepoints(void)
|| !strcmp(events_ent->d_name, "header_page"))
continue;

scnprintf(sys_path, PATH_MAX, "%s/%s",
tracing_events_path, events_ent->d_name);
sys_path = get_events_file(events_ent->d_name);
TEST_ASSERT_VAL("Can't get sys path", sys_path);

sys_dir = opendir(sys_path);
TEST_ASSERT_VAL("Can't open sys dir", sys_dir);
Expand All @@ -1356,6 +1356,7 @@ static int count_tracepoints(void)
}

closedir(sys_dir);
put_events_file(sys_path);
}

closedir(events_dir);
Expand Down
12 changes: 6 additions & 6 deletions tools/perf/tests/shell/record+probe_libc_inet_pton.sh
Original file line number Diff line number Diff line change
Expand Up @@ -16,18 +16,18 @@ nm -g $libc 2>/dev/null | fgrep -q inet_pton || exit 254
trace_libc_inet_pton_backtrace() {
idx=0
expected[0]="ping[][0-9 \.:]+probe_libc:inet_pton: \([[:xdigit:]]+\)"
expected[1]=".*inet_pton[[:space:]]\($libc|inlined\)$"
expected[1]=".*inet_pton\+0x[[:xdigit:]]+[[:space:]]\($libc|inlined\)$"
case "$(uname -m)" in
s390x)
eventattr='call-graph=dwarf,max-stack=4'
expected[2]="gaih_inet.*[[:space:]]\($libc|inlined\)$"
expected[3]="(__GI_)?getaddrinfo[[:space:]]\($libc|inlined\)$"
expected[4]="main[[:space:]]\(.*/bin/ping.*\)$"
expected[2]="gaih_inet.*\+0x[[:xdigit:]]+[[:space:]]\($libc|inlined\)$"
expected[3]="(__GI_)?getaddrinfo\+0x[[:xdigit:]]+[[:space:]]\($libc|inlined\)$"
expected[4]="main\+0x[[:xdigit:]]+[[:space:]]\(.*/bin/ping.*\)$"
;;
*)
eventattr='max-stack=3'
expected[2]="getaddrinfo[[:space:]]\($libc\)$"
expected[3]=".*\(.*/bin/ping.*\)$"
expected[2]="getaddrinfo\+0x[[:xdigit:]]+[[:space:]]\($libc\)$"
expected[3]=".*\+0x[[:xdigit:]]+[[:space:]]\(.*/bin/ping.*\)$"
;;
esac

Expand Down
8 changes: 8 additions & 0 deletions tools/perf/ui/browsers/annotate.c
Original file line number Diff line number Diff line change
Expand Up @@ -695,6 +695,7 @@ static int annotate_browser__run(struct annotate_browser *browser,
"O Bump offset level (jump targets -> +call -> all -> cycle thru)\n"
"s Toggle source code view\n"
"t Circulate percent, total period, samples view\n"
"c Show min/max cycle\n"
"/ Search string\n"
"k Toggle line numbers\n"
"P Print to [symbol_name].annotation file.\n"
Expand Down Expand Up @@ -791,6 +792,13 @@ static int annotate_browser__run(struct annotate_browser *browser,
notes->options->show_total_period = true;
annotation__update_column_widths(notes);
continue;
case 'c':
if (notes->options->show_minmax_cycle)
notes->options->show_minmax_cycle = false;
else
notes->options->show_minmax_cycle = true;
annotation__update_column_widths(notes);
continue;
case K_LEFT:
case K_ESC:
case 'q':
Expand Down
Loading

0 comments on commit 2996123

Please sign in to comment.