diff options
author | Namhyung Kim <namhyung@kernel.org> | 2022-12-09 11:07:26 -0800 |
---|---|---|
committer | Arnaldo Carvalho de Melo <acme@redhat.com> | 2022-12-14 11:24:31 -0300 |
commit | 688d2e8de231c54e289b640547af246343732348 (patch) | |
tree | 5b9f5c578a77035a26cdb4efa403977d9197c559 /tools/perf/util | |
parent | eca949b2b4addd941d369d4c2014b87f3c3e203b (diff) | |
download | linux-688d2e8de231c54e289b640547af246343732348.tar.bz2 |
perf lock contention: Add -l/--lock-addr option
The -l/--lock-addr option is to implement per-lock-instance contention
stat using LOCK_AGGR_ADDR. It displays lock address and optionally
symbol name if exists.
$ sudo ./perf lock con -abl sleep 1
contended total wait max wait avg wait address symbol
1 36.28 us 36.28 us 36.28 us ffff92615d6448b8
9 10.91 us 1.84 us 1.21 us ffffffffbaed50c0 rcu_state
1 10.49 us 10.49 us 10.49 us ffff9262ac4f0c80
8 4.68 us 1.67 us 585 ns ffffffffbae07a40 jiffies_lock
3 3.03 us 1.45 us 1.01 us ffff9262277861e0
1 924 ns 924 ns 924 ns ffff926095ba9d20
1 436 ns 436 ns 436 ns ffff9260bfda4f60
Signed-off-by: Namhyung Kim <namhyung@kernel.org>
Cc: Adrian Hunter <adrian.hunter@intel.com>
Cc: Blake Jones <blakejones@google.com>
Cc: Ian Rogers <irogers@google.com>
Cc: Ingo Molnar <mingo@kernel.org>
Cc: Jiri Olsa <jolsa@kernel.org>
Cc: Peter Zijlstra <peterz@infradead.org>
Cc: Song Liu <song@kernel.org>
Cc: bpf@vger.kernel.org
Link: https://lore.kernel.org/r/20221209190727.759804-4-namhyung@kernel.org
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Diffstat (limited to 'tools/perf/util')
-rw-r--r-- | tools/perf/util/bpf_lock_contention.c | 23 | ||||
-rw-r--r-- | tools/perf/util/bpf_skel/lock_contention.bpf.c | 17 | ||||
-rw-r--r-- | tools/perf/util/bpf_skel/lock_data.h | 2 |
3 files changed, 31 insertions, 11 deletions
diff --git a/tools/perf/util/bpf_lock_contention.c b/tools/perf/util/bpf_lock_contention.c index 1590a9f05145..8e1b791dc58f 100644 --- a/tools/perf/util/bpf_lock_contention.c +++ b/tools/perf/util/bpf_lock_contention.c @@ -137,11 +137,15 @@ int lock_contention_read(struct lock_contention *con) thread__set_comm(idle, "swapper", /*timestamp=*/0); } + /* make sure it loads the kernel map */ + map__load(maps__first(machine->kmaps)); + prev_key = NULL; while (!bpf_map_get_next_key(fd, prev_key, &key)) { struct map *kmap; struct symbol *sym; int idx = 0; + s32 stack_id; /* to handle errors in the loop body */ err = -1; @@ -160,24 +164,31 @@ int lock_contention_read(struct lock_contention *con) st->avg_wait_time = data.total_time / data.count; st->flags = data.flags; + st->addr = key.aggr_key; if (con->aggr_mode == LOCK_AGGR_TASK) { struct contention_task_data task; struct thread *t; - - st->addr = key.stack_or_task_id; + int pid = key.aggr_key; /* do not update idle comm which contains CPU number */ if (st->addr) { - bpf_map_lookup_elem(task_fd, &key, &task); - t = __machine__findnew_thread(machine, /*pid=*/-1, - key.stack_or_task_id); + bpf_map_lookup_elem(task_fd, &pid, &task); + t = __machine__findnew_thread(machine, /*pid=*/-1, pid); thread__set_comm(t, task.comm, /*timestamp=*/0); } goto next; } - bpf_map_lookup_elem(stack, &key, stack_trace); + if (con->aggr_mode == LOCK_AGGR_ADDR) { + sym = machine__find_kernel_symbol(machine, st->addr, &kmap); + if (sym) + st->name = strdup(sym->name); + goto next; + } + + stack_id = key.aggr_key; + bpf_map_lookup_elem(stack, &stack_id, stack_trace); /* skip lock internal functions */ while (machine__is_lock_function(machine, stack_trace[idx]) && diff --git a/tools/perf/util/bpf_skel/lock_contention.bpf.c b/tools/perf/util/bpf_skel/lock_contention.bpf.c index cd405adcd252..11b0fc7ee53b 100644 --- a/tools/perf/util/bpf_skel/lock_contention.bpf.c +++ b/tools/perf/util/bpf_skel/lock_contention.bpf.c @@ -168,11 +168,20 @@ int contention_end(u64 *ctx) duration = bpf_ktime_get_ns() - pelem->timestamp; - if (aggr_mode == LOCK_AGGR_CALLER) { - key.stack_or_task_id = pelem->stack_id; - } else { - key.stack_or_task_id = pid; + switch (aggr_mode) { + case LOCK_AGGR_CALLER: + key.aggr_key = pelem->stack_id; + break; + case LOCK_AGGR_TASK: + key.aggr_key = pid; update_task_data(pid); + break; + case LOCK_AGGR_ADDR: + key.aggr_key = pelem->lock; + break; + default: + /* should not happen */ + return 0; } data = bpf_map_lookup_elem(&lock_stat, &key); diff --git a/tools/perf/util/bpf_skel/lock_data.h b/tools/perf/util/bpf_skel/lock_data.h index dbdf4caedc4a..ce71cf1a7e1e 100644 --- a/tools/perf/util/bpf_skel/lock_data.h +++ b/tools/perf/util/bpf_skel/lock_data.h @@ -4,7 +4,7 @@ #define UTIL_BPF_SKEL_LOCK_DATA_H struct contention_key { - s32 stack_or_task_id; + u64 aggr_key; /* can be stack_id, pid or lock addr */ }; #define TASK_COMM_LEN 16 |