restic: Use QoS instead of uploadLimit
This implements a crude mechanism for signalling my router to add the packets to its own qdisc. The way in which this is implemented with nftables is hacky because of NixOS’ limitations on build-time checking (which obviously can’t know about the existence of cgroups on the target).
This commit is contained in:
parent
afc9013506
commit
816004e80b
|
@ -17,7 +17,7 @@
|
||||||
nginx.hardening.enable = true;
|
nginx.hardening.enable = true;
|
||||||
restic.system = {
|
restic.system = {
|
||||||
enable = true;
|
enable = true;
|
||||||
uploadLimit = 250;
|
qos = true;
|
||||||
extraPaths = [
|
extraPaths = [
|
||||||
"/data"
|
"/data"
|
||||||
];
|
];
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
mullvad.enable = true;
|
mullvad.enable = true;
|
||||||
restic.system = {
|
restic.system = {
|
||||||
enable = true;
|
enable = true;
|
||||||
uploadLimit = 250;
|
qos = true;
|
||||||
extraPaths = [
|
extraPaths = [
|
||||||
"/data"
|
"/data"
|
||||||
];
|
];
|
||||||
|
|
|
@ -17,7 +17,7 @@
|
||||||
mullvad.enable = true;
|
mullvad.enable = true;
|
||||||
restic.system = {
|
restic.system = {
|
||||||
enable = true;
|
enable = true;
|
||||||
uploadLimit = 250;
|
qos = true;
|
||||||
};
|
};
|
||||||
unfree.allowSoftware = true;
|
unfree.allowSoftware = true;
|
||||||
wireguard.home.enable = true;
|
wireguard.home.enable = true;
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
gui.enable = true;
|
gui.enable = true;
|
||||||
restic.system = {
|
restic.system = {
|
||||||
enable = true;
|
enable = true;
|
||||||
uploadLimit = 250;
|
qos = true;
|
||||||
};
|
};
|
||||||
unfree.allowSoftware = true;
|
unfree.allowSoftware = true;
|
||||||
wireguard.home.enable = true;
|
wireguard.home.enable = true;
|
||||||
|
|
|
@ -72,6 +72,9 @@ table inet tc {
|
||||||
|
|
||||||
meta l4proto udp ip dscp af13 meta priority set 1:5 ip dscp set cs0 counter return comment "fuuko torrent"
|
meta l4proto udp ip dscp af13 meta priority set 1:5 ip dscp set cs0 counter return comment "fuuko torrent"
|
||||||
|
|
||||||
|
ip daddr 168.119.176.53 tcp dport 443 ip dscp af12 meta priority set 1:9 counter return comment "restic (4)"
|
||||||
|
ip6 daddr 2a01:4f8:c012:2f4::1 tcp dport 443 ip6 dscp af12 meta priority set 1:9 counter return comment "restic (6)"
|
||||||
|
|
||||||
meta l4proto { tcp, udp } th dport 443 meta priority set 1:6 counter return comment "HTTPS"
|
meta l4proto { tcp, udp } th dport 443 meta priority set 1:6 counter return comment "HTTPS"
|
||||||
|
|
||||||
ip daddr 168.119.176.53 udp dport 51820 meta priority set 1:7 counter return comment "wg-home"
|
ip daddr 168.119.176.53 udp dport 51820 meta priority set 1:7 counter return comment "wg-home"
|
||||||
|
|
|
@ -38,6 +38,25 @@ let
|
||||||
--repo "${repository}" \
|
--repo "${repository}" \
|
||||||
$@
|
$@
|
||||||
'';
|
'';
|
||||||
|
|
||||||
|
# HACK: NixOS’ nftables implementation runs nft -c inside the build sandbox,
|
||||||
|
# where the target host’s cgroups are not available,
|
||||||
|
# and therefore fails.
|
||||||
|
# This is there to allow my home router to put backup traffic into the right qdisc,
|
||||||
|
# as the ip address and port are also used for other things.
|
||||||
|
# This is somewhat of an abuse of the DSCP mark.
|
||||||
|
qosRules = pkgs.writeText "restic-qos.nft" ''
|
||||||
|
table inet restic
|
||||||
|
delete table inet restic
|
||||||
|
|
||||||
|
table inet restic {
|
||||||
|
chain output {
|
||||||
|
type filter hook output priority mangle
|
||||||
|
ip version 4 socket cgroupv2 level 1 "restic.slice" ip dscp set af12 return
|
||||||
|
ip6 version 6 socket cgroupv2 level 1 "restic.slice" ip6 dscp set af12 return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
'';
|
||||||
in
|
in
|
||||||
{
|
{
|
||||||
options.sbruder.restic.system = {
|
options.sbruder.restic.system = {
|
||||||
|
@ -62,6 +81,7 @@ in
|
||||||
type = lib.types.nullOr lib.types.int;
|
type = lib.types.nullOr lib.types.int;
|
||||||
default = null;
|
default = null;
|
||||||
};
|
};
|
||||||
|
qos = (lib.mkEnableOption "QoS marking (DSCP AF12) of outgoing packets") // { default = !(lib.isNull cfg.uploadLimit); };
|
||||||
prune = lib.mkEnableOption "pruning";
|
prune = lib.mkEnableOption "pruning";
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -99,6 +119,13 @@ in
|
||||||
"Nice" = 10;
|
"Nice" = 10;
|
||||||
"IOSchedulingClass" = "best-effort";
|
"IOSchedulingClass" = "best-effort";
|
||||||
"IOSchedulingPriority" = 7;
|
"IOSchedulingPriority" = 7;
|
||||||
|
ExecStartPre = [
|
||||||
|
"${pkgs.nftables}/bin/nft -f ${qosRules}"
|
||||||
|
];
|
||||||
|
ExecStopPost = [
|
||||||
|
"${pkgs.nftables}/bin/nft delete table inet restic"
|
||||||
|
];
|
||||||
|
Slice = "restic.slice";
|
||||||
};
|
};
|
||||||
|
|
||||||
services.restic.backups.system-prune = lib.mkIf cfg.prune {
|
services.restic.backups.system-prune = lib.mkIf cfg.prune {
|
||||||
|
|
Loading…
Reference in a new issue