Re: [bpf-next 3/3] samples/bpf: Add soft irq execution time statistics

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Sun, Sep 20, 2020 at 7:47 AM Xin Hao <xhao@xxxxxxxxxxxxxxxxx> wrote:
>
> This patch is aimed to count the execution time of
> each soft irq and it supports log2 histogram display.
>
> Soft irq counts:
>      us              : count    distribution
>
>      0 -> 1          : 151      |****************************************|
>      2 -> 3          : 86       |**********************                  |
>      4 -> 7          : 59       |***************                         |
>      8 -> 15         : 20       |*****                                   |
>     16 -> 31         : 3        |                                        |
>
> Signed-off-by: Xin Hao <xhao@xxxxxxxxxxxxxxxxx>
> ---

I assume you saw softirqs tools ([0]) from libbpf-tools in BCC, right?
Could you mention in the commit message how this tool is different and
why there is a need for another one?

BTW, if you are interested in contributing more and making samples/bpf
better overall, consider looking at adding BPF skeleton integration
into samples/bpf, similarly to how all libbpf-tools use skeletons.

  [0] https://github.com/iovisor/bcc/pull/3076

>  samples/bpf/Makefile        |  3 ++
>  samples/bpf/soft_irq_kern.c | 87 ++++++++++++++++++++++++++++++++++++
>  samples/bpf/soft_irq_user.c | 88 +++++++++++++++++++++++++++++++++++++
>  3 files changed, 178 insertions(+)
>  create mode 100644 samples/bpf/soft_irq_kern.c
>  create mode 100644 samples/bpf/soft_irq_user.c
>
> diff --git a/samples/bpf/Makefile b/samples/bpf/Makefile
> index f87ee02073ba..0774f0fb8bdf 100644
> --- a/samples/bpf/Makefile
> +++ b/samples/bpf/Makefile
> @@ -53,6 +53,7 @@ tprogs-y += task_fd_query
>  tprogs-y += xdp_sample_pkts
>  tprogs-y += ibumad
>  tprogs-y += hbm
> +tprogs-y += soft_irq
>
>  # Libbpf dependencies
>  LIBBPF = $(TOOLS_PATH)/lib/bpf/libbpf.a
> @@ -109,6 +110,7 @@ task_fd_query-objs := bpf_load.o task_fd_query_user.o $(TRACE_HELPERS)
>  xdp_sample_pkts-objs := xdp_sample_pkts_user.o $(TRACE_HELPERS)
>  ibumad-objs := bpf_load.o ibumad_user.o $(TRACE_HELPERS)
>  hbm-objs := bpf_load.o hbm.o $(CGROUP_HELPERS)
> +soft_irq-objs := bpf_load.o soft_irq_user.o $(TRACE_HELPERS)
>
>  # Tell kbuild to always build the programs
>  always-y := $(tprogs-y)
> @@ -170,6 +172,7 @@ always-y += ibumad_kern.o
>  always-y += hbm_out_kern.o
>  always-y += hbm_edt_kern.o
>  always-y += xdpsock_kern.o
> +always-y += soft_irq_kern.o
>
>  ifeq ($(ARCH), arm)
>  # Strip all except -D__LINUX_ARM_ARCH__ option needed to handle linux
> diff --git a/samples/bpf/soft_irq_kern.c b/samples/bpf/soft_irq_kern.c
> new file mode 100644
> index 000000000000..e63f829cf7c7
> --- /dev/null
> +++ b/samples/bpf/soft_irq_kern.c
> @@ -0,0 +1,87 @@
> +/* SPDX-License-Identifier: GPL-2.0
> + *
> + * This program is free software; you can redistribute it and/or
> + * modify it under the terms of version 2 of the GNU General Public
> + * License as published by the Free Software Foundation.
> + */
> +
> +#include <uapi/linux/bpf.h>
> +#include <bpf/bpf_helpers.h>
> +#include <bpf/bpf_tracing.h>
> +#include <uapi/linux/ptrace.h>
> +#include <uapi/linux/perf_event.h>
> +#include <linux/version.h>
> +#include <linux/sched.h>
> +#include "common_kern.h"
> +
> +typedef struct key {
> +       u32 pid;
> +       u32 cpu;
> +} irqkey_t;
> +
> +typedef struct val {
> +       u64 ts;
> +       u32 vec;
> +} val_t;
> +
> +typedef struct delta_irq {
> +       u64 delta;
> +    u32 value;
> +} delta_irq_t;

kernel style generally discourages unnecessary typedefs, I think
following that is a good idea. I'm not sure those typedefs provide
much value and they save only few letters when typing.

> +
> +struct bpf_map_def SEC("maps") start = {
> +       .type = BPF_MAP_TYPE_HASH,
> +       .key_size = sizeof(irqkey_t),
> +       .value_size = sizeof(val_t),
> +       .max_entries = 1000,
> +};
> +
> +struct soft_irq {
> +       u64 pad;
> +    u32 vec;
> +};


it's a good idea to keep empty line between type declarations and
variables/functions

> +SEC("tracepoint/irq/softirq_entry")
> +int entryirq(struct soft_irq *ctx)
> +{
> +    irqkey_t entry_key = {};
> +       val_t val = {};
> +
> +       entry_key.pid = bpf_get_current_pid_tgid();
> +    entry_key.cpu = bpf_get_smp_processor_id();
> +
> +       val.ts = bpf_ktime_get_ns();
> +       val.vec = ctx->vec;
> +
> +       bpf_map_update_elem(&start, &entry_key, &val, BPF_ANY);
> +       return 0;
> +}
> +
> +struct bpf_map_def SEC("maps") over = {
> +       .type = BPF_MAP_TYPE_HASH,
> +       .key_size = sizeof(irqkey_t),
> +       .value_size = sizeof(delta_irq_t),
> +       .max_entries = 10000,
> +};

same

> +SEC("tracepoint/irq/softirq_exit")
> +int exitirq(struct soft_irq *ctx)
> +{
> +    irqkey_t entry_key = {};
> +       delta_irq_t delta_val = {};
> +       val_t *valp;
> +
> +       entry_key.pid = bpf_get_current_pid_tgid();
> +    entry_key.cpu = bpf_get_smp_processor_id();
> +
> +       valp = bpf_map_lookup_elem(&start, &entry_key);
> +       if (valp) {
> +               delta_val.delta = (bpf_ktime_get_ns() - valp->ts) / 1000; /* us */
> +               delta_val.value = log2l(delta_val.delta);
> +
> +               bpf_map_update_elem(&over, &entry_key, &delta_val, BPF_ANY);
> +               bpf_map_delete_elem(&start, valp);
> +       }
> +
> +       return 0;
> +}

here as well

> +char _license[] SEC("license") = "GPL";
> +u32 _version SEC("version") = LINUX_VERSION_CODE;

[...]



[Index of Archives]     [Linux Samsung SoC]     [Linux Rockchip SoC]     [Linux Actions SoC]     [Linux for Synopsys ARC Processors]     [Linux NFS]     [Linux NILFS]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]


  Powered by Linux