sqm-scripts & systemd-networkd
I recently found the sqm-scripts repository and decided I wanted to use it on my home router, but I could never make the service run as expected on my setup (Debian 11, systemd-networkd) with the default service definition.
Why? Because I like cake…eh…I want a controlled delay even when my family is trying their best to use all available bandwidth. This was a simple way of fixing bufferbloat so I took it! :-)
sqm-scripts will create a virtual interface for your WAN facing interface
(ifb4<interface>
), as traffic shaping only can be applied on outgoing traffic
from an interface. It will then apply limiting on this virtual interface, and
on your real outgoing interface. Pretty neat, actually!
Installing #
Clone the repository somewhere and run make install
.
# git clone https://github.com/tohojo/sqm-scripts.git
# cd sqm-scripts
# make install
This will copy a bunch of files to a bunch of places on your system. One
important such place is /etc/sqm
in which default.conf
which you copy to
/etc/sqm/<interface>.iface.conf
(enp1s0
in my case) and customize it’s
values.
Here’s my /etc/sqm/enp1s0.iface.conf
:
# cat /etc/sqm/enp1s0.iface.conf
UPLINK=90000
DOWNLINK=225000
SCRIPT=piece_of_cake.qos
ENABLED=1
QDISC=cake
I have a 250/100 Mbps service, and my values are probably much lower than necessary.
Enable and start the service:
# systemctl enable --now sqm@enp1s0.service
Now test with fast.com,
speedtest.net and/or
dslreports.com and check the
loaded/unloaded ping times, they should be very close now. You should also
have a new interface named something like ifb4enp1s0
, but you still apply
firewall rules on your ‘real’ WAN facing interface.
Making the sqm service run as expected #
I’m not sure this service definition file is exactly what equivalent to the original one, but this one runs after my network is up as expected!
# Install as sqm@.service and place it in /etc/systemd/system
# Then run systemctl daemon-reload and enable it for your internet
# facing interface.
[Unit]
Description=SQM scripts for iface %i
Wants=network-online.target
After=network.target network-online.target
[Service]
Type=oneshot
EnvironmentFile=/etc/sqm/default.conf
EnvironmentFile=-/etc/sqm/%i.iface.conf
Environment=IFACE=%i ENABLED=1
ExecStart=/usr/lib/sqm/start-sqm
ExecStop=/usr/lib/sqm/stop-sqm
RemainAfterExit=1
[Install]
WantedBy=multi-user.target
I’ve also been very clear with my systemd-networkd on when I want it to
consider my network to be up – after my internet facing interface is up. One
way to do this is by customizing the service file for
systemd-networkd-wait-online.service
like so:
# Save as /etc/systemd/system/systemd-networkd-wait-online.service.d/wait-for-main-interface.conf
[Service]
ExecStart=
ExecStart=/usr/lib/systemd/systemd-networkd-wait-online -i enp1s0
Ansible role #
I wrote an Ansible role for setting this up on a Debian system. If does nothing more than what is described here, but it Feels Good™ to have it automated.