109 lines
4.3 KiB
Nix
109 lines
4.3 KiB
Nix
# debugging:
|
|
# - `man named`
|
|
# - `man named.conf`
|
|
# - `systemctl stop bind`
|
|
# - `sudo /nix/store/0zpdy93sd3fgbxgvf8dsxhn8fbbya8d2-bind-9.18.28/sbin/named -g -u named -4 -c /nix/store/f1mp0myzmfms71h9vinwxpn2i9362a9a-named.conf`
|
|
# - `-g` = don't fork
|
|
# - `-u named` = start as superuser (to claim port 53), then drop to user `named`
|
|
{ config, lib, pkgs, ... }:
|
|
let
|
|
hostCfg = config.sane.hosts.by-name."${config.networking.hostName}";
|
|
bindCfg = config.services.bind;
|
|
in
|
|
{
|
|
config = lib.mkIf (!config.sane.services.hickory-dns.asSystemResolver) {
|
|
services.resolved.enable = lib.mkForce false;
|
|
|
|
networking.nameservers = [
|
|
# be compatible with systemd-resolved
|
|
# "127.0.0.53"
|
|
# or don't be compatible with systemd-resolved, but with libc and pasta instead
|
|
# see <pkgs/by-name/sane-scripts/src/sane-vpn>
|
|
"127.0.0.1"
|
|
# enable IPv6, or don't; unbound is spammy when IPv6 is enabled but unroutable
|
|
# "::1"
|
|
];
|
|
|
|
networking.resolvconf.extraConfig = ''
|
|
# DNS serviced by `BIND` recursive resolver
|
|
name_servers='127.0.0.1'
|
|
'';
|
|
|
|
services.bind.enable = lib.mkDefault true;
|
|
services.bind.forwarders = []; #< don't forward queries to upstream resolvers
|
|
services.bind.cacheNetworks = [
|
|
"127.0.0.0/24"
|
|
"::1/128"
|
|
"10.0.10.0/24" #< wireguard clients (servo)
|
|
];
|
|
services.bind.listenOn = [
|
|
"127.0.0.1"
|
|
] ++ lib.optionals (hostCfg.wg-home.ip != null) [
|
|
# allow wireguard clients to use us as a recursive resolver (only needed for servo)
|
|
hostCfg.wg-home.ip
|
|
];
|
|
services.bind.listenOnIpv6 = [
|
|
# "::1"
|
|
];
|
|
|
|
services.bind.ipv4Only = true; # unbound is spammy when it tries IPv6 without a routable address
|
|
|
|
# when testing, deploy on a port other than 53
|
|
# services.bind.extraOptions = ''
|
|
# listen-on port 953 { any; };
|
|
# '';
|
|
|
|
networking.resolvconf.useLocalResolver = false; #< we manage resolvconf explicitly, above
|
|
|
|
# TODO: how to exempt `pool.ntp.org` from DNSSEC checks, as i did when using unbound?
|
|
|
|
# allow runtime insertion of zones or other config changes:
|
|
# add your supplemental config as a toplevel file in /run/named/dhcp-configs/, then `systemctl restart bind`
|
|
services.bind.extraConfig = ''
|
|
include "/run/named/dhcp-configs.conf";
|
|
'';
|
|
services.bind.extraOptions = ''
|
|
// we can't guarantee that all forwarders support DNSSEC,
|
|
// and as of 2025-01-30 BIND9 gives no way to disable DNSSEC per-forwarder/zone,
|
|
// so just disable it globally
|
|
dnssec-validation no;
|
|
'';
|
|
# re-implement the nixos default bind config, but without `options { forwarders { }; };`,
|
|
# as having an empty `forwarders` at the top-level prevents me from forwarding the `.` zone in a separate statement
|
|
# (which i want to do to allow sane-vpn to forward all DNS).
|
|
services.bind.configFile = pkgs.writeText "named.conf" ''
|
|
include "/etc/bind/rndc.key";
|
|
controls {
|
|
inet 127.0.0.1 allow {localhost;} keys {"rndc-key";};
|
|
};
|
|
|
|
acl cachenetworks { ${lib.concatMapStrings (entry: " ${entry}; ") bindCfg.cacheNetworks} };
|
|
acl badnetworks { ${lib.concatMapStrings (entry: " ${entry}; ") bindCfg.blockedNetworks} };
|
|
|
|
options {
|
|
listen-on { ${lib.concatMapStrings (entry: " ${entry}; ") bindCfg.listenOn} };
|
|
listen-on-v6 { ${lib.concatMapStrings (entry: " ${entry}; ") bindCfg.listenOnIpv6} };
|
|
allow-query-cache { cachenetworks; };
|
|
blackhole { badnetworks; };
|
|
//v disable top-level forwards, so that i can do forwarding more generically in `zone FOO { ... }` directives.
|
|
// forward ${bindCfg.forward};
|
|
// forwarders { ${lib.concatMapStrings (entry: " ${entry}; ") bindCfg.forwarders} };
|
|
directory "${bindCfg.directory}";
|
|
pid-file "/run/named/named.pid";
|
|
${bindCfg.extraOptions}
|
|
};
|
|
|
|
${bindCfg.extraConfig}
|
|
'';
|
|
|
|
systemd.services.bind.serviceConfig.ExecStartPre = pkgs.writeShellScript "named-generate-config" ''
|
|
mkdir -p /run/named/dhcp-configs
|
|
chmod g+w /run/named/dhcp-configs
|
|
echo "// FILE GENERATED BY bind.service's ExecStartPre: CHANGES TO THIS FILE WILL BE OVERWRITTEN" > /run/named/dhcp-configs.conf
|
|
for c in $(ls /run/named/dhcp-configs/); do
|
|
cat "/run/named/dhcp-configs/$c" >> /run/named/dhcp-configs.conf
|
|
done
|
|
'';
|
|
};
|
|
}
|