bpftune uses BPF to auto-tune Linux systems
bpftune aims to provide lightweight, always-on auto-tuning of system behaviour. The key benefit it provides are
The Linux kernel contains a large number of tunables; these often take the form of sysctl(8) parameters, and are usually introduced for situations where there is no one "right" answer for a configuration choice. The number of tunables available is quite daunting. On a 6.2 kernel we see
# sysctl --all 2>/dev/null|wc -l
1624See here for an excellent writeup on network-related tunables..
At the same time, individual systems get a lot less care and adminstrator attention than they used to; phrases like "cattle not pets" exemplify this. Given the modern cloud architectures used for most deployments, most systems never have any human adminstrator interaction after initial provisioning; in fact given the scale requirements, this is often an explicit design goal - "no ssh'ing in!".
These two observations are not unrelated; in an earlier era of fewer, larger systems, tuning by administrators was more feasible.
These trends - system complexity combined with minimal admin interaction suggest a rethink in terms of tunable management.
A lot of lore accumulates around these tunables, and to help clarify why we developed bpftune, we will use a straw-man version of the approach taken with tunables:
"find the set of magic numbers that will work for the system forever"
This is obviously a caricature of how administrators approach the problem, but it does highlight a critical implicit assumption - that systems are static.
And that gets to the "BPF" in bpftune; BPF provides means to carry out low-overhead observability of systems. So not only can we observe the system and tune appropriately, we can also observe the effect of that tuning and re-tune if necessary.
The key components are
tuners: each tuner manages tunables and handles events sent from BPF programs to userspace via the shared ring buffer. Each tuner has an associated set of tunables that it manages.
optional strategies: a tuner can specify multiple strategies; after running for a while a strategy times out and we assess if a better strategy is available. Each strategy specifies a
Strategies are optional and should be set in the tuner init() method via bpftune_strategies_add(). See test/strategy for a coded example. When a strategy times out, the various evaluation functions are called and the highest-value evaluation dictates the next stratgey.
Strategies provide a way of providing multiple schemes for auto-tuning the same set of tunables, where the choice is guided by an evaluation of the effectiveness of the strategies.
events specify a
the tuner then responds to the event guided by the active strategy; increase or decrease a tunable value, etc. Describing the event in the log is key; this allows an admin to understand what changed and why.
Both core bpftune.c and individual tuners use the libbpftune library. It handles logging, tuner init/fini, and BPF init/fini.
Each tuner shared object defines an init(), fini() and event_handler() function. These respectively set up and clean up BPF and handle events that originate from the BPF code.
If building the repository manually, simply run
$ make ; sudo make installat the top-level of the repository. bpftune also supports a
$ make pkgtarget, which will make a bpftune RPM. See ./buildrpm/bpftune.spec
By default, we disable openrc script installation to avoid unneeded package dependencies; to enable this add
--with openrcto the rpmbuild command.
We can also build with non-standard libdir for distros which do not use /usr/lib64 like CachyOS; in this case to install to /usr/lib instead
$ make libdir=lib
$ sudo make install libdir=libTo build the following packages are needed (names may vary by distro);
The bpf components in bpftune can be built via GCC BPF support. See https://gcc.gnu.org/wiki/BPFBackEnd for details on the BPF backend. To build with gcc bpf, specify
$ GCC_BPF=bpf-unknown-none-gcc makeFrom the kernel side, the kernel needs to support BPF ring buffer (around the 5.6 kernel, though 5.4 is supported on Oracle Linux as ring buffer support was backported), and kernel BTF is required (CONFIG_DEBUG_INFO_BTF=y). Verify /sys/kernel/btf/vmlinux is present.
To enable bpftune as a service
$ sudo service bpftune start...and to enable it by default
$ sudo systemctl enable bpftunebpftune logs to syslog so /var/log/messages will contain details of any tuning carried out.
bpftune can also be run in the foreground as a program; to redirect output to stdout/stderr, run
$ sudo bpftune -sOn exit, bpftune will summarize any tuning done.
Queries of bpftune state can be done via bpftune -q.
Support has been added to export bpftune tunable values to Performance Co-Pilot via a PMDA (Performance Metric Domain Agent). It uses bpftune quereies to populate metrics in PCP via a python-based PMDA. See src/pcp/pmdabpftune.python.
To install the PMDA (ensuring pcp and python3-pcp packages are installed first), simply run
$ sudo make install
$ cd /var/lib/pcp/pmdas/bpftune
$ sudo ./Install
Once the above has been done, PCP metrics will be available for bpftune tunables. To see these:
$ pminfo -f bpftune
bpftune.udp_buffer.net.core.rmem_default
value 212992
bpftune.udp_buffer.net.core.rmem_max
value 3099438
...The PMDA is also packaged in bpftune-pcp-pmda; see buildrpm/bpftune.spec.
To create grafana dashboards using bpftune tunables, see the blog entry here for details on setting up grafana to handle PCP metric visualization.
From there it is necessary to ensure that pmlogger is logging the metrics regularly; add something like the following to
/var/lib/pcp/config/pmlogger/config.default
log advisory on default {
bpftune.tcp_buffer.net.ipv4.tcp_rmem
bpftune.tcp_buffer.net.ipv4.tcp_wmem
bpftune.tcp_buffer.net.ipv4.tcp_mem
}...and restart pmlogger
$ sudo service pmlogger restartOnce that is done, it should be possible to create dashboards with queries of bpftune metrics. For example here is a simple dashboard created for the tcp_buffer tuner:
Information: If you are using an Fedora Upstream based Distribution you have to enable the correct repository based on the system you are using, because the libbpf-devel package is getting shipped on additional repository, based on the Distribution. You can look it up here: https://pkgs.org/search/?q=libbpf-devel
…Tests are supplied for each tuner in the tests/ subdirectory. "make test" runs all the tests. Tests use network namespaces to simulate interactions with remote hosts. See .
No open issues yet, or sync has not completed.