1*387f9dfdSAndroid Build Coastguard Worker // SPDX-License-Identifier: GPL-2.0
2*387f9dfdSAndroid Build Coastguard Worker // Copyright (c) 2020 Wenbo Zhang
3*387f9dfdSAndroid Build Coastguard Worker #include <vmlinux.h>
4*387f9dfdSAndroid Build Coastguard Worker #include <bpf/bpf_helpers.h>
5*387f9dfdSAndroid Build Coastguard Worker #include <bpf/bpf_core_read.h>
6*387f9dfdSAndroid Build Coastguard Worker #include <bpf/bpf_tracing.h>
7*387f9dfdSAndroid Build Coastguard Worker #include "runqlen.h"
8*387f9dfdSAndroid Build Coastguard Worker
9*387f9dfdSAndroid Build Coastguard Worker const volatile bool targ_per_cpu = false;
10*387f9dfdSAndroid Build Coastguard Worker const volatile bool targ_host = false;
11*387f9dfdSAndroid Build Coastguard Worker
12*387f9dfdSAndroid Build Coastguard Worker struct hist hists[MAX_CPU_NR] = {};
13*387f9dfdSAndroid Build Coastguard Worker
14*387f9dfdSAndroid Build Coastguard Worker SEC("perf_event")
do_sample(struct bpf_perf_event_data * ctx)15*387f9dfdSAndroid Build Coastguard Worker int do_sample(struct bpf_perf_event_data *ctx)
16*387f9dfdSAndroid Build Coastguard Worker {
17*387f9dfdSAndroid Build Coastguard Worker struct task_struct *task;
18*387f9dfdSAndroid Build Coastguard Worker struct hist *hist;
19*387f9dfdSAndroid Build Coastguard Worker u64 slot, cpu = 0;
20*387f9dfdSAndroid Build Coastguard Worker
21*387f9dfdSAndroid Build Coastguard Worker task = (void*)bpf_get_current_task();
22*387f9dfdSAndroid Build Coastguard Worker if (targ_host)
23*387f9dfdSAndroid Build Coastguard Worker slot = BPF_CORE_READ(task, se.cfs_rq, rq, nr_running);
24*387f9dfdSAndroid Build Coastguard Worker else
25*387f9dfdSAndroid Build Coastguard Worker slot = BPF_CORE_READ(task, se.cfs_rq, nr_running);
26*387f9dfdSAndroid Build Coastguard Worker /*
27*387f9dfdSAndroid Build Coastguard Worker * Calculate run queue length by subtracting the currently running task,
28*387f9dfdSAndroid Build Coastguard Worker * if present. len 0 == idle, len 1 == one running task.
29*387f9dfdSAndroid Build Coastguard Worker */
30*387f9dfdSAndroid Build Coastguard Worker if (slot > 0)
31*387f9dfdSAndroid Build Coastguard Worker slot--;
32*387f9dfdSAndroid Build Coastguard Worker if (targ_per_cpu) {
33*387f9dfdSAndroid Build Coastguard Worker cpu = bpf_get_smp_processor_id();
34*387f9dfdSAndroid Build Coastguard Worker /*
35*387f9dfdSAndroid Build Coastguard Worker * When the program is started, the user space will immediately
36*387f9dfdSAndroid Build Coastguard Worker * exit when it detects this situation, here just to pass the
37*387f9dfdSAndroid Build Coastguard Worker * verifier's check.
38*387f9dfdSAndroid Build Coastguard Worker */
39*387f9dfdSAndroid Build Coastguard Worker if (cpu >= MAX_CPU_NR)
40*387f9dfdSAndroid Build Coastguard Worker return 0;
41*387f9dfdSAndroid Build Coastguard Worker }
42*387f9dfdSAndroid Build Coastguard Worker hist = &hists[cpu];
43*387f9dfdSAndroid Build Coastguard Worker if (slot >= MAX_SLOTS)
44*387f9dfdSAndroid Build Coastguard Worker slot = MAX_SLOTS - 1;
45*387f9dfdSAndroid Build Coastguard Worker if (targ_per_cpu)
46*387f9dfdSAndroid Build Coastguard Worker hist->slots[slot]++;
47*387f9dfdSAndroid Build Coastguard Worker else
48*387f9dfdSAndroid Build Coastguard Worker __sync_fetch_and_add(&hist->slots[slot], 1);
49*387f9dfdSAndroid Build Coastguard Worker return 0;
50*387f9dfdSAndroid Build Coastguard Worker }
51*387f9dfdSAndroid Build Coastguard Worker
52*387f9dfdSAndroid Build Coastguard Worker char LICENSE[] SEC("license") = "GPL";
53