fireperf

Find out what your network can really take - and what is in between.

fireperf measures bandwidth like iperf3 does, but it has been built to test firewalls, routers and everything else that keeps state for every connection. It moves data at line rate on every CPU without copying it, opens hundreds of thousands of connections per second, and tells you exactly what happened to every one of them.

fireperf showing the traffic of three clients

Why fireperf?

Tests The Firewall, Not Just The Cable

iperf3 tells you how much data gets from one machine to another. A firewall rarely struggles with that. It struggles with thousands of new connections every second and with keeping track of all of them. fireperf tests exactly that.

Tells You Why Connections Fail

When a connection cannot be made, iperf3 gives up. fireperf counts every connection that failed and tells you why: whether it timed out, was refused, or whether the machine running the test ran out of resources.

Finds Connections That Have Been Dropped

Firewalls quietly drop connections that have been idle for too long - the reason why SSH sessions freeze after lunch. fireperf keeps connections open, checks regularly whether they still work, and tells you how many the firewall has dropped.

Everybody Can Test At Once

An iperf3 server turns everybody away until the current test is done. A fireperf server takes any number of clients at the same time, each running its own test, all on one port.

A Seventh Of The CPU

fireperf needs a seventh of the CPU time that iperf3 needs to send the same amount of data. So you measure your network, not the machine running the test - and if it ever is the machine, fireperf tells you.

Works With iperf3 And iperf

No need to replace anything at once: fireperf talks to iperf3 and iperf servers, and iperf3 clients can test against a fireperf server.

Shows You What Is Going On

A live graph of the traffic in both directions, the numbers that matter, and every client with its connections and traffic - right in your terminal. It finds out whether your terminal is dark or light, and looks good on both.

Without a terminal, fireperf prints a line every second, and --json gives you one JSON object per second for your scripts and dashboards.

fireperf on a terminal with a light background

How It Compares

fireperf iperf3
Several clients, each with its own test, at once one at a time
Opens connections at a fixed rate
Tells why connections could not be established
Handshake times across all connections
Finds connections that a firewall has dropped
Request and response on every connection
Sends without copying always with -Z
Live graph in the terminal
JSON output
Talks to iperf3 and iperf -

In Numbers

Sending from one VM (2 cores) to another over virtio, eight connections, CPU time of the sender per GiB that it has sent (less is better):

Sender Gbit/s CPU seconds per GiB
fireperf (io_uring) 19.0 0.071
fireperf (epoll) 19.4 0.151
iperf3 -Z 17.9 0.153
iperf3 15.9 0.505
iperf 2 15.7 0.509

That is a seventh of the CPU time that iperf3 and iperf need by default, and half of what iperf3 needs with --zerocopy - CPU time that is left to push the network instead of the benchmark.

Opening and closing connections over loopback on a 16-core machine, fireperf gets through more than 230,000 connections per second, about 20 µs of CPU time on the server for every one of them.

Getting Started

Start a server:

fireperf --server

And point a client at it:

# How fast is it? The server sends, the client receives.
fireperf --client server.example.com

# Both directions at once, over 16 connections
fireperf --client server.example.com --duplex --parallel 16

# Can the firewall open 10,000 connections per second?
fireperf --client 192.0.2.1 --rate 10000 --close

# Like a web server: 100 bytes request, 10 KB response, 5,000 times per second
fireperf --client 192.0.2.1 --exchange 100:10000 --rate 5000

# Keep 100,000 connections open, and find those that the firewall forgets
fireperf --client 192.0.2.1 --parallel 100000 --keepalive

# Talk to an iperf3 server (which listens on another port)
fireperf --client iperf3.example.org --port 5201

# Feed your scripts
fireperf --client server.example.com --timeout 10 --json | jq .

fireperf(8) explains every option, and how to run a connection test that tells you something about the firewall rather than about the machines on either side. fireperf-design(7) explains how fireperf works and why.

Install

fireperf is being built and signed for Debian, Arch Linux, RHEL (and AlmaLinux, Rocky Linux and the other clones) and openSUSE Tumbleweed.

Debian

For bookworm, trixie, forky and sid, on amd64, arm64, armel, armhf, i386, loong64, ppc64el, riscv64 and s390x, as far as the release has them:

sudo curl -o /usr/share/keyrings/fireperf.asc \
	https://repo.ipfire.org/debian/fireperf/master/fireperf.asc
echo "deb [signed-by=/usr/share/keyrings/fireperf.asc] https://repo.ipfire.org/debian/fireperf/master $(. /etc/os-release && echo $VERSION_CODENAME) main" \
	| sudo tee /etc/apt/sources.list.d/fireperf.list
sudo apt update && sudo apt install fireperf
Arch Linux

Import the key:

curl https://repo.ipfire.org/archlinux/fireperf/master/fireperf.asc | sudo pacman-key --add -
sudo pacman-key --lsign-key 274205B524A108FD0416482AA49D90BBC489A8E7

And add the repository to /etc/pacman.conf:

[fireperf]
Server = https://repo.ipfire.org/archlinux/fireperf/master/$arch
RHEL 9 & 10

And its clones - add this as /etc/yum.repos.d/fireperf.repo and install it with dnf install fireperf:

[fireperf]
name=fireperf
baseurl=https://repo.ipfire.org/el/fireperf/master/$releasever/
gpgcheck=1
repo_gpgcheck=1
gpgkey=https://repo.ipfire.org/el/fireperf/master/$releasever/RPM-GPG-KEY-fireperf
openSUSE Tumbleweed
sudo rpm --import https://repo.ipfire.org/opensuse/fireperf/master/tumbleweed/RPM-GPG-KEY-fireperf
sudo zypper addrepo https://repo.ipfire.org/opensuse/fireperf/master/tumbleweed/ fireperf
sudo zypper install fireperf
Source

fireperf is free software, licensed under the GNU General Public License, version 3 or later. You need a C compiler, autotools, pkg-config, ncursesw, gettext and intltool. liburing (2.3 or later) is optional but recommended.

./autogen.sh
./configure
make
make check
sudo make install